Projects
Multimedia
libhdhomerun
Sign Up
Log In
Username
Password
Overview
Repositories
Revisions
Requests
Users
Attributes
Meta
Expand all
Collapse all
Changes of Revision 5
View file
libhdhomerun.changes
Changed
@@ -1,4 +1,11 @@ ------------------------------------------------------------------- +Tue Oct 29 11:39:22 UTC 2019 - <manfred.h@gmx.net> + +- Update patch: libhdhomerun-fix_makefile.patch +- Version update to 20190621 + https://www.silicondust.com/support/downloads/software-changelog/ + +------------------------------------------------------------------- Sat Oct 08 11:13:29 UTC 2016 - joerg.lorenzen@ki.tng.de - Removed service file because build often fails with 'bad temdir'
View file
libhdhomerun.spec
Changed
@@ -4,8 +4,8 @@ # package are under the same license as the package itself. Name: libhdhomerun -Version: 20150826 -%define soname %{version} +Version: 20190621 +%define soname 2 Release: 1.pm Summary: HD library for your pc Group: System/Libraries @@ -47,10 +47,10 @@ %setup -q -n libhdhomerun %patch1 %__chmod 0644 * -%__sed -i -e 's/\r$//' README +%__sed -i -e 's/\r$//' README.md %build -%__make %{?_smp_flags} SONAME="%{version}" OPTFLAGS="%{optflags}" +%__make %{?_smp_flags} SONAME="%{soname}" OPTFLAGS="%{optflags}" %install %__install -D -m0755 hdhomerun_config "%{buildroot}%{_bindir}/hdhomerun_config" @@ -85,7 +85,7 @@ %files -n %{name}%{soname} %defattr(-,root,root) -%doc README +%doc README.md %{_libdir}/libhdhomerun.so.%{soname} %files devel
View file
libhdhomerun-fix_makefile.patch
Changed
@@ -1,20 +1,20 @@ ---- Makefile.orig 2016-03-10 19:11:44.787338293 +0200 -+++ Makefile 2016-03-10 19:12:33.744628657 +0200 -@@ -12,11 +12,10 @@ +--- Makefile.orig 2019-05-03 19:45:43.000000000 +0200 ++++ Makefile 2019-10-29 12:52:20.222262688 +0100 +@@ -12,11 +12,10 @@ LIBSRCS += hdhomerun_sock_posix.c LIBSRCS += hdhomerun_video.c CC := $(CROSS_COMPILE)gcc -STRIP := $(CROSS_COMPILE)strip --CFLAGS += -Wall -O2 -Wmissing-declarations -Wmissing-prototypes -Wstrict-prototypes -Wpointer-arith -+CFLAGS += -Wall -Wmissing-declarations -Wmissing-prototypes -Wstrict-prototypes -Wpointer-arith $(OPTFLAGS) +-CFLAGS += -O2 -Wall -Wextra -Wmissing-declarations -Wmissing-prototypes -Wstrict-prototypes -Wpointer-arith -Wno-unused-parameter ++CFLAGS += $(OPTFLAGS) -Wall -Wextra -Wmissing-declarations -Wmissing-prototypes -Wstrict-prototypes -Wpointer-arith -Wno-unused-parameter LDFLAGS += -lpthread -SHARED = -shared -Wl,-soname,libhdhomerun$(LIBEXT) +SHARED = -shared -Wl,-soname,libhdhomerun$(LIBEXT).$(SONAME) ifeq ($(OS),Windows_NT) BINEXT := .exe -@@ -42,10 +41,10 @@ +@@ -42,10 +41,10 @@ all : hdhomerun_config$(BINEXT) libhdhom hdhomerun_config$(BINEXT) : hdhomerun_config.c $(LIBSRCS) $(CC) $(CFLAGS) $+ $(LDFLAGS) -o $@ @@ -23,7 +23,7 @@ libhdhomerun$(LIBEXT) : $(LIBSRCS) - $(CC) $(CFLAGS) -fPIC -DDLL_EXPORT $(SHARED) $+ $(LDFLAGS) -o $@ + $(CC) $(CFLAGS) -fPIC -DDLL_EXPORT $(SHARED) $+ $(LDFLAGS) -o $@.$(SONAME) -+ ln -s $@.$(SONAME) $@ ++ ln -sf $@.$(SONAME) $@ clean : -rm -f hdhomerun_config$(BINEXT)
View file
libhdhomerun_20150826.tgz/README
Deleted
@@ -1,29 +0,0 @@ -/* - * README - * - * Copyright © 2005-2009 Silicondust USA Inc. <www.silicondust.com>. - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; either - * version 2.1 of the License, or (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - */ - -Top level include file: hdhomerun.h - -Top level API: hdhomerun_device. See hdhomerun_device.h for documentation. - -The hdhomerun_device API should be used rather than the low level control and video APIs required with previous versions. - -Additional libraries required: -- pthread -- iphlpapi (windows only)
View file
libhdhomerun_20150826.tgz/lgpl.txt
Deleted
@@ -1,502 +0,0 @@ - GNU LESSER GENERAL PUBLIC LICENSE - Version 2.1, February 1999 - - Copyright (C) 1991, 1999 Free Software Foundation, Inc. - 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - Everyone is permitted to copy and distribute verbatim copies - of this license document, but changing it is not allowed. - -[This is the first released version of the Lesser GPL. It also counts - as the successor of the GNU Library Public License, version 2, hence - the version number 2.1.] - - Preamble - - The licenses for most software are designed to take away your -freedom to share and change it. By contrast, the GNU General Public -Licenses are intended to guarantee your freedom to share and change -free software--to make sure the software is free for all its users. - - This license, the Lesser General Public License, applies to some -specially designated software packages--typically libraries--of the -Free Software Foundation and other authors who decide to use it. You -can use it too, but we suggest you first think carefully about whether -this license or the ordinary General Public License is the better -strategy to use in any particular case, based on the explanations below. - - When we speak of free software, we are referring to freedom of use, -not price. Our General Public Licenses are designed to make sure that -you have the freedom to distribute copies of free software (and charge -for this service if you wish); that you receive source code or can get -it if you want it; that you can change the software and use pieces of -it in new free programs; and that you are informed that you can do -these things. - - To protect your rights, we need to make restrictions that forbid -distributors to deny you these rights or to ask you to surrender these -rights. These restrictions translate to certain responsibilities for -you if you distribute copies of the library or if you modify it. - - For example, if you distribute copies of the library, whether gratis -or for a fee, you must give the recipients all the rights that we gave -you. You must make sure that they, too, receive or can get the source -code. If you link other code with the library, you must provide -complete object files to the recipients, so that they can relink them -with the library after making changes to the library and recompiling -it. And you must show them these terms so they know their rights. - - We protect your rights with a two-step method: (1) we copyright the -library, and (2) we offer you this license, which gives you legal -permission to copy, distribute and/or modify the library. - - To protect each distributor, we want to make it very clear that -there is no warranty for the free library. Also, if the library is -modified by someone else and passed on, the recipients should know -that what they have is not the original version, so that the original -author's reputation will not be affected by problems that might be -introduced by others. - - Finally, software patents pose a constant threat to the existence of -any free program. We wish to make sure that a company cannot -effectively restrict the users of a free program by obtaining a -restrictive license from a patent holder. Therefore, we insist that -any patent license obtained for a version of the library must be -consistent with the full freedom of use specified in this license. - - Most GNU software, including some libraries, is covered by the -ordinary GNU General Public License. This license, the GNU Lesser -General Public License, applies to certain designated libraries, and -is quite different from the ordinary General Public License. We use -this license for certain libraries in order to permit linking those -libraries into non-free programs. - - When a program is linked with a library, whether statically or using -a shared library, the combination of the two is legally speaking a -combined work, a derivative of the original library. The ordinary -General Public License therefore permits such linking only if the -entire combination fits its criteria of freedom. The Lesser General -Public License permits more lax criteria for linking other code with -the library. - - We call this license the "Lesser" General Public License because it -does Less to protect the user's freedom than the ordinary General -Public License. It also provides other free software developers Less -of an advantage over competing non-free programs. These disadvantages -are the reason we use the ordinary General Public License for many -libraries. However, the Lesser license provides advantages in certain -special circumstances. - - For example, on rare occasions, there may be a special need to -encourage the widest possible use of a certain library, so that it becomes -a de-facto standard. To achieve this, non-free programs must be -allowed to use the library. A more frequent case is that a free -library does the same job as widely used non-free libraries. In this -case, there is little to gain by limiting the free library to free -software only, so we use the Lesser General Public License. - - In other cases, permission to use a particular library in non-free -programs enables a greater number of people to use a large body of -free software. For example, permission to use the GNU C Library in -non-free programs enables many more people to use the whole GNU -operating system, as well as its variant, the GNU/Linux operating -system. - - Although the Lesser General Public License is Less protective of the -users' freedom, it does ensure that the user of a program that is -linked with the Library has the freedom and the wherewithal to run -that program using a modified version of the Library. - - The precise terms and conditions for copying, distribution and -modification follow. Pay close attention to the difference between a -"work based on the library" and a "work that uses the library". The -former contains code derived from the library, whereas the latter must -be combined with the library in order to run. - - GNU LESSER GENERAL PUBLIC LICENSE - TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION - - 0. This License Agreement applies to any software library or other -program which contains a notice placed by the copyright holder or -other authorized party saying it may be distributed under the terms of -this Lesser General Public License (also called "this License"). -Each licensee is addressed as "you". - - A "library" means a collection of software functions and/or data -prepared so as to be conveniently linked with application programs -(which use some of those functions and data) to form executables. - - The "Library", below, refers to any such software library or work -which has been distributed under these terms. A "work based on the -Library" means either the Library or any derivative work under -copyright law: that is to say, a work containing the Library or a -portion of it, either verbatim or with modifications and/or translated -straightforwardly into another language. (Hereinafter, translation is -included without limitation in the term "modification".) - - "Source code" for a work means the preferred form of the work for -making modifications to it. For a library, complete source code means -all the source code for all modules it contains, plus any associated -interface definition files, plus the scripts used to control compilation -and installation of the library. - - Activities other than copying, distribution and modification are not -covered by this License; they are outside its scope. The act of -running a program using the Library is not restricted, and output from -such a program is covered only if its contents constitute a work based -on the Library (independent of the use of the Library in a tool for -writing it). Whether that is true depends on what the Library does -and what the program that uses the Library does. - - 1. You may copy and distribute verbatim copies of the Library's -complete source code as you receive it, in any medium, provided that -you conspicuously and appropriately publish on each copy an -appropriate copyright notice and disclaimer of warranty; keep intact -all the notices that refer to this License and to the absence of any -warranty; and distribute a copy of this License along with the -Library. - - You may charge a fee for the physical act of transferring a copy, -and you may at your option offer warranty protection in exchange for a -fee. - - 2. You may modify your copy or copies of the Library or any portion -of it, thus forming a work based on the Library, and copy and -distribute such modifications or work under the terms of Section 1 -above, provided that you also meet all of these conditions: - - a) The modified work must itself be a software library. - - b) You must cause the files modified to carry prominent notices - stating that you changed the files and the date of any change. - - c) You must cause the whole of the work to be licensed at no - charge to all third parties under the terms of this License. - - d) If a facility in the modified Library refers to a function or a - table of data to be supplied by an application program that uses - the facility, other than as an argument passed when the facility - is invoked, then you must make a good faith effort to ensure that, - in the event an application does not supply such function or - table, the facility still operates, and performs whatever part of - its purpose remains meaningful. - - (For example, a function in a library to compute square roots has - a purpose that is entirely well-defined independent of the - application. Therefore, Subsection 2d requires that any - application-supplied function or table used by this function must - be optional: if the application does not supply it, the square - root function must still compute square roots.) - -These requirements apply to the modified work as a whole. If -identifiable sections of that work are not derived from the Library, -and can be reasonably considered independent and separate works in -themselves, then this License, and its terms, do not apply to those -sections when you distribute them as separate works. But when you -distribute the same sections as part of a whole which is a work based -on the Library, the distribution of the whole must be on the terms of -this License, whose permissions for other licensees extend to the -entire whole, and thus to each and every part regardless of who wrote -it. - -Thus, it is not the intent of this section to claim rights or contest -your rights to work written entirely by you; rather, the intent is to -exercise the right to control the distribution of derivative or -collective works based on the Library. - -In addition, mere aggregation of another work not based on the Library -with the Library (or with a work based on the Library) on a volume of -a storage or distribution medium does not bring the other work under -the scope of this License. - - 3. You may opt to apply the terms of the ordinary GNU General Public -License instead of this License to a given copy of the Library. To do -this, you must alter all the notices that refer to this License, so -that they refer to the ordinary GNU General Public License, version 2, -instead of to this License. (If a newer version than version 2 of the -ordinary GNU General Public License has appeared, then you can specify -that version instead if you wish.) Do not make any other change in -these notices. - - Once this change is made in a given copy, it is irreversible for -that copy, so the ordinary GNU General Public License applies to all -subsequent copies and derivative works made from that copy. - - This option is useful when you wish to copy part of the code of -the Library into a program that is not a library. - - 4. You may copy and distribute the Library (or a portion or -derivative of it, under Section 2) in object code or executable form -under the terms of Sections 1 and 2 above provided that you accompany -it with the complete corresponding machine-readable source code, which -must be distributed under the terms of Sections 1 and 2 above on a -medium customarily used for software interchange. - - If distribution of object code is made by offering access to copy -from a designated place, then offering equivalent access to copy the -source code from the same place satisfies the requirement to -distribute the source code, even though third parties are not -compelled to copy the source along with the object code. - - 5. A program that contains no derivative of any portion of the -Library, but is designed to work with the Library by being compiled or -linked with it, is called a "work that uses the Library". Such a -work, in isolation, is not a derivative work of the Library, and -therefore falls outside the scope of this License. - - However, linking a "work that uses the Library" with the Library -creates an executable that is a derivative of the Library (because it -contains portions of the Library), rather than a "work that uses the -library". The executable is therefore covered by this License. -Section 6 states terms for distribution of such executables. - - When a "work that uses the Library" uses material from a header file -that is part of the Library, the object code for the work may be a -derivative work of the Library even though the source code is not. -Whether this is true is especially significant if the work can be -linked without the Library, or if the work is itself a library. The -threshold for this to be true is not precisely defined by law. - - If such an object file uses only numerical parameters, data -structure layouts and accessors, and small macros and small inline -functions (ten lines or less in length), then the use of the object -file is unrestricted, regardless of whether it is legally a derivative -work. (Executables containing this object code plus portions of the -Library will still fall under Section 6.) - - Otherwise, if the work is a derivative of the Library, you may -distribute the object code for the work under the terms of Section 6. -Any executables containing that work also fall under Section 6, -whether or not they are linked directly with the Library itself. - - 6. As an exception to the Sections above, you may also combine or -link a "work that uses the Library" with the Library to produce a -work containing portions of the Library, and distribute that work -under terms of your choice, provided that the terms permit -modification of the work for the customer's own use and reverse -engineering for debugging such modifications. - - You must give prominent notice with each copy of the work that the -Library is used in it and that the Library and its use are covered by -this License. You must supply a copy of this License. If the work -during execution displays copyright notices, you must include the -copyright notice for the Library among them, as well as a reference -directing the user to the copy of this License. Also, you must do one -of these things: - - a) Accompany the work with the complete corresponding - machine-readable source code for the Library including whatever - changes were used in the work (which must be distributed under - Sections 1 and 2 above); and, if the work is an executable linked - with the Library, with the complete machine-readable "work that - uses the Library", as object code and/or source code, so that the - user can modify the Library and then relink to produce a modified - executable containing the modified Library. (It is understood - that the user who changes the contents of definitions files in the - Library will not necessarily be able to recompile the application - to use the modified definitions.) - - b) Use a suitable shared library mechanism for linking with the - Library. A suitable mechanism is one that (1) uses at run time a - copy of the library already present on the user's computer system, - rather than copying library functions into the executable, and (2) - will operate properly with a modified version of the library, if - the user installs one, as long as the modified version is - interface-compatible with the version that the work was made with. - - c) Accompany the work with a written offer, valid for at - least three years, to give the same user the materials - specified in Subsection 6a, above, for a charge no more - than the cost of performing this distribution. - - d) If distribution of the work is made by offering access to copy - from a designated place, offer equivalent access to copy the above - specified materials from the same place. - - e) Verify that the user has already received a copy of these - materials or that you have already sent this user a copy. - - For an executable, the required form of the "work that uses the -Library" must include any data and utility programs needed for -reproducing the executable from it. However, as a special exception, -the materials to be distributed need not include anything that is -normally distributed (in either source or binary form) with the major -components (compiler, kernel, and so on) of the operating system on -which the executable runs, unless that component itself accompanies -the executable. - - It may happen that this requirement contradicts the license -restrictions of other proprietary libraries that do not normally -accompany the operating system. Such a contradiction means you cannot -use both them and the Library together in an executable that you -distribute. - - 7. You may place library facilities that are a work based on the -Library side-by-side in a single library together with other library -facilities not covered by this License, and distribute such a combined -library, provided that the separate distribution of the work based on -the Library and of the other library facilities is otherwise -permitted, and provided that you do these two things: - - a) Accompany the combined library with a copy of the same work - based on the Library, uncombined with any other library - facilities. This must be distributed under the terms of the - Sections above. - - b) Give prominent notice with the combined library of the fact - that part of it is a work based on the Library, and explaining - where to find the accompanying uncombined form of the same work. - - 8. You may not copy, modify, sublicense, link with, or distribute -the Library except as expressly provided under this License. Any -attempt otherwise to copy, modify, sublicense, link with, or -distribute the Library is void, and will automatically terminate your -rights under this License. However, parties who have received copies, -or rights, from you under this License will not have their licenses -terminated so long as such parties remain in full compliance. - - 9. You are not required to accept this License, since you have not -signed it. However, nothing else grants you permission to modify or -distribute the Library or its derivative works. These actions are -prohibited by law if you do not accept this License. Therefore, by -modifying or distributing the Library (or any work based on the -Library), you indicate your acceptance of this License to do so, and -all its terms and conditions for copying, distributing or modifying -the Library or works based on it. - - 10. Each time you redistribute the Library (or any work based on the -Library), the recipient automatically receives a license from the -original licensor to copy, distribute, link with or modify the Library -subject to these terms and conditions. You may not impose any further -restrictions on the recipients' exercise of the rights granted herein. -You are not responsible for enforcing compliance by third parties with -this License. - - 11. If, as a consequence of a court judgment or allegation of patent -infringement or for any other reason (not limited to patent issues), -conditions are imposed on you (whether by court order, agreement or -otherwise) that contradict the conditions of this License, they do not -excuse you from the conditions of this License. If you cannot -distribute so as to satisfy simultaneously your obligations under this -License and any other pertinent obligations, then as a consequence you -may not distribute the Library at all. For example, if a patent -license would not permit royalty-free redistribution of the Library by -all those who receive copies directly or indirectly through you, then -the only way you could satisfy both it and this License would be to -refrain entirely from distribution of the Library. - -If any portion of this section is held invalid or unenforceable under any -particular circumstance, the balance of the section is intended to apply, -and the section as a whole is intended to apply in other circumstances. - -It is not the purpose of this section to induce you to infringe any -patents or other property right claims or to contest validity of any -such claims; this section has the sole purpose of protecting the -integrity of the free software distribution system which is -implemented by public license practices. Many people have made -generous contributions to the wide range of software distributed -through that system in reliance on consistent application of that -system; it is up to the author/donor to decide if he or she is willing -to distribute software through any other system and a licensee cannot -impose that choice. - -This section is intended to make thoroughly clear what is believed to -be a consequence of the rest of this License. - - 12. If the distribution and/or use of the Library is restricted in -certain countries either by patents or by copyrighted interfaces, the -original copyright holder who places the Library under this License may add -an explicit geographical distribution limitation excluding those countries, -so that distribution is permitted only in or among countries not thus -excluded. In such case, this License incorporates the limitation as if -written in the body of this License. - - 13. The Free Software Foundation may publish revised and/or new -versions of the Lesser General Public License from time to time. -Such new versions will be similar in spirit to the present version, -but may differ in detail to address new problems or concerns. - -Each version is given a distinguishing version number. If the Library -specifies a version number of this License which applies to it and -"any later version", you have the option of following the terms and -conditions either of that version or of any later version published by -the Free Software Foundation. If the Library does not specify a -license version number, you may choose any version ever published by -the Free Software Foundation. - - 14. If you wish to incorporate parts of the Library into other free -programs whose distribution conditions are incompatible with these, -write to the author to ask for permission. For software which is -copyrighted by the Free Software Foundation, write to the Free -Software Foundation; we sometimes make exceptions for this. Our -decision will be guided by the two goals of preserving the free status -of all derivatives of our free software and of promoting the sharing -and reuse of software generally. - - NO WARRANTY - - 15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO -WARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW. -EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR -OTHER PARTIES PROVIDE THE LIBRARY "AS IS" WITHOUT WARRANTY OF ANY -KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE -IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR -PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE -LIBRARY IS WITH YOU. SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME -THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION. - - 16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN -WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY -AND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU -FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR -CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE -LIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING -RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A -FAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF -SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH -DAMAGES. - - END OF TERMS AND CONDITIONS - - How to Apply These Terms to Your New Libraries - - If you develop a new library, and you want it to be of the greatest -possible use to the public, we recommend making it free software that -everyone can redistribute and change. You can do so by permitting -redistribution under these terms (or, alternatively, under the terms of the -ordinary General Public License). - - To apply these terms, attach the following notices to the library. It is -safest to attach them to the start of each source file to most effectively -convey the exclusion of warranty; and each file should have at least the -"copyright" line and a pointer to where the full notice is found. - - <one line to give the library's name and a brief idea of what it does.> - Copyright (C) <year> <name of author> - - This library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public - License as published by the Free Software Foundation; either - version 2.1 of the License, or (at your option) any later version. - - This library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with this library; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA - -Also add information on how to contact you by electronic and paper mail. - -You should also get your employer (if you work as a programmer) or your -school, if any, to sign a "copyright disclaimer" for the library, if -necessary. Here is a sample; alter the names: - - Yoyodyne, Inc., hereby disclaims all copyright interest in the - library `Frob' (a library for tweaking knobs) written by James Random Hacker. - - <signature of Ty Coon>, 1 April 1990 - Ty Coon, President of Vice - -That's all there is to it!
View file
libhdhomerun_20190621.tgz/LICENSE
Added
@@ -0,0 +1,504 @@ + GNU LESSER GENERAL PUBLIC LICENSE + Version 2.1, February 1999 + + Copyright (C) 1991, 1999 Free Software Foundation, Inc. + 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + Everyone is permitted to copy and distribute verbatim copies + of this license document, but changing it is not allowed. + +(This is the first released version of the Lesser GPL. It also counts + as the successor of the GNU Library Public License, version 2, hence + the version number 2.1.) + + Preamble + + The licenses for most software are designed to take away your +freedom to share and change it. By contrast, the GNU General Public +Licenses are intended to guarantee your freedom to share and change +free software--to make sure the software is free for all its users. + + This license, the Lesser General Public License, applies to some +specially designated software packages--typically libraries--of the +Free Software Foundation and other authors who decide to use it. You +can use it too, but we suggest you first think carefully about whether +this license or the ordinary General Public License is the better +strategy to use in any particular case, based on the explanations below. + + When we speak of free software, we are referring to freedom of use, +not price. Our General Public Licenses are designed to make sure that +you have the freedom to distribute copies of free software (and charge +for this service if you wish); that you receive source code or can get +it if you want it; that you can change the software and use pieces of +it in new free programs; and that you are informed that you can do +these things. + + To protect your rights, we need to make restrictions that forbid +distributors to deny you these rights or to ask you to surrender these +rights. These restrictions translate to certain responsibilities for +you if you distribute copies of the library or if you modify it. + + For example, if you distribute copies of the library, whether gratis +or for a fee, you must give the recipients all the rights that we gave +you. You must make sure that they, too, receive or can get the source +code. If you link other code with the library, you must provide +complete object files to the recipients, so that they can relink them +with the library after making changes to the library and recompiling +it. And you must show them these terms so they know their rights. + + We protect your rights with a two-step method: (1) we copyright the +library, and (2) we offer you this license, which gives you legal +permission to copy, distribute and/or modify the library. + + To protect each distributor, we want to make it very clear that +there is no warranty for the free library. Also, if the library is +modified by someone else and passed on, the recipients should know +that what they have is not the original version, so that the original +author's reputation will not be affected by problems that might be +introduced by others. + + Finally, software patents pose a constant threat to the existence of +any free program. We wish to make sure that a company cannot +effectively restrict the users of a free program by obtaining a +restrictive license from a patent holder. Therefore, we insist that +any patent license obtained for a version of the library must be +consistent with the full freedom of use specified in this license. + + Most GNU software, including some libraries, is covered by the +ordinary GNU General Public License. This license, the GNU Lesser +General Public License, applies to certain designated libraries, and +is quite different from the ordinary General Public License. We use +this license for certain libraries in order to permit linking those +libraries into non-free programs. + + When a program is linked with a library, whether statically or using +a shared library, the combination of the two is legally speaking a +combined work, a derivative of the original library. The ordinary +General Public License therefore permits such linking only if the +entire combination fits its criteria of freedom. The Lesser General +Public License permits more lax criteria for linking other code with +the library. + + We call this license the "Lesser" General Public License because it +does Less to protect the user's freedom than the ordinary General +Public License. It also provides other free software developers Less +of an advantage over competing non-free programs. These disadvantages +are the reason we use the ordinary General Public License for many +libraries. However, the Lesser license provides advantages in certain +special circumstances. + + For example, on rare occasions, there may be a special need to +encourage the widest possible use of a certain library, so that it becomes +a de-facto standard. To achieve this, non-free programs must be +allowed to use the library. A more frequent case is that a free +library does the same job as widely used non-free libraries. In this +case, there is little to gain by limiting the free library to free +software only, so we use the Lesser General Public License. + + In other cases, permission to use a particular library in non-free +programs enables a greater number of people to use a large body of +free software. For example, permission to use the GNU C Library in +non-free programs enables many more people to use the whole GNU +operating system, as well as its variant, the GNU/Linux operating +system. + + Although the Lesser General Public License is Less protective of the +users' freedom, it does ensure that the user of a program that is +linked with the Library has the freedom and the wherewithal to run +that program using a modified version of the Library. + + The precise terms and conditions for copying, distribution and +modification follow. Pay close attention to the difference between a +"work based on the library" and a "work that uses the library". The +former contains code derived from the library, whereas the latter must +be combined with the library in order to run. + + GNU LESSER GENERAL PUBLIC LICENSE + TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION + + 0. This License Agreement applies to any software library or other +program which contains a notice placed by the copyright holder or +other authorized party saying it may be distributed under the terms of +this Lesser General Public License (also called "this License"). +Each licensee is addressed as "you". + + A "library" means a collection of software functions and/or data +prepared so as to be conveniently linked with application programs +(which use some of those functions and data) to form executables. + + The "Library", below, refers to any such software library or work +which has been distributed under these terms. A "work based on the +Library" means either the Library or any derivative work under +copyright law: that is to say, a work containing the Library or a +portion of it, either verbatim or with modifications and/or translated +straightforwardly into another language. (Hereinafter, translation is +included without limitation in the term "modification".) + + "Source code" for a work means the preferred form of the work for +making modifications to it. For a library, complete source code means +all the source code for all modules it contains, plus any associated +interface definition files, plus the scripts used to control compilation +and installation of the library. + + Activities other than copying, distribution and modification are not +covered by this License; they are outside its scope. The act of +running a program using the Library is not restricted, and output from +such a program is covered only if its contents constitute a work based +on the Library (independent of the use of the Library in a tool for +writing it). Whether that is true depends on what the Library does +and what the program that uses the Library does. + + 1. You may copy and distribute verbatim copies of the Library's +complete source code as you receive it, in any medium, provided that +you conspicuously and appropriately publish on each copy an +appropriate copyright notice and disclaimer of warranty; keep intact +all the notices that refer to this License and to the absence of any +warranty; and distribute a copy of this License along with the +Library. + + You may charge a fee for the physical act of transferring a copy, +and you may at your option offer warranty protection in exchange for a +fee. + + 2. You may modify your copy or copies of the Library or any portion +of it, thus forming a work based on the Library, and copy and +distribute such modifications or work under the terms of Section 1 +above, provided that you also meet all of these conditions: + + a) The modified work must itself be a software library. + + b) You must cause the files modified to carry prominent notices + stating that you changed the files and the date of any change. + + c) You must cause the whole of the work to be licensed at no + charge to all third parties under the terms of this License. + + d) If a facility in the modified Library refers to a function or a + table of data to be supplied by an application program that uses + the facility, other than as an argument passed when the facility + is invoked, then you must make a good faith effort to ensure that, + in the event an application does not supply such function or + table, the facility still operates, and performs whatever part of + its purpose remains meaningful. + + (For example, a function in a library to compute square roots has + a purpose that is entirely well-defined independent of the + application. Therefore, Subsection 2d requires that any + application-supplied function or table used by this function must + be optional: if the application does not supply it, the square + root function must still compute square roots.) + +These requirements apply to the modified work as a whole. If +identifiable sections of that work are not derived from the Library, +and can be reasonably considered independent and separate works in +themselves, then this License, and its terms, do not apply to those +sections when you distribute them as separate works. But when you +distribute the same sections as part of a whole which is a work based +on the Library, the distribution of the whole must be on the terms of +this License, whose permissions for other licensees extend to the +entire whole, and thus to each and every part regardless of who wrote +it. + +Thus, it is not the intent of this section to claim rights or contest +your rights to work written entirely by you; rather, the intent is to +exercise the right to control the distribution of derivative or +collective works based on the Library. + +In addition, mere aggregation of another work not based on the Library +with the Library (or with a work based on the Library) on a volume of +a storage or distribution medium does not bring the other work under +the scope of this License. + + 3. You may opt to apply the terms of the ordinary GNU General Public +License instead of this License to a given copy of the Library. To do +this, you must alter all the notices that refer to this License, so +that they refer to the ordinary GNU General Public License, version 2, +instead of to this License. (If a newer version than version 2 of the +ordinary GNU General Public License has appeared, then you can specify +that version instead if you wish.) Do not make any other change in +these notices. + + Once this change is made in a given copy, it is irreversible for +that copy, so the ordinary GNU General Public License applies to all +subsequent copies and derivative works made from that copy. + + This option is useful when you wish to copy part of the code of +the Library into a program that is not a library. + + 4. You may copy and distribute the Library (or a portion or +derivative of it, under Section 2) in object code or executable form +under the terms of Sections 1 and 2 above provided that you accompany +it with the complete corresponding machine-readable source code, which +must be distributed under the terms of Sections 1 and 2 above on a +medium customarily used for software interchange. + + If distribution of object code is made by offering access to copy +from a designated place, then offering equivalent access to copy the +source code from the same place satisfies the requirement to +distribute the source code, even though third parties are not +compelled to copy the source along with the object code. + + 5. A program that contains no derivative of any portion of the +Library, but is designed to work with the Library by being compiled or +linked with it, is called a "work that uses the Library". Such a +work, in isolation, is not a derivative work of the Library, and +therefore falls outside the scope of this License. + + However, linking a "work that uses the Library" with the Library +creates an executable that is a derivative of the Library (because it +contains portions of the Library), rather than a "work that uses the +library". The executable is therefore covered by this License. +Section 6 states terms for distribution of such executables. + + When a "work that uses the Library" uses material from a header file +that is part of the Library, the object code for the work may be a +derivative work of the Library even though the source code is not. +Whether this is true is especially significant if the work can be +linked without the Library, or if the work is itself a library. The +threshold for this to be true is not precisely defined by law. + + If such an object file uses only numerical parameters, data +structure layouts and accessors, and small macros and small inline +functions (ten lines or less in length), then the use of the object +file is unrestricted, regardless of whether it is legally a derivative +work. (Executables containing this object code plus portions of the +Library will still fall under Section 6.) + + Otherwise, if the work is a derivative of the Library, you may +distribute the object code for the work under the terms of Section 6. +Any executables containing that work also fall under Section 6, +whether or not they are linked directly with the Library itself. + + 6. As an exception to the Sections above, you may also combine or +link a "work that uses the Library" with the Library to produce a +work containing portions of the Library, and distribute that work +under terms of your choice, provided that the terms permit +modification of the work for the customer's own use and reverse +engineering for debugging such modifications. + + You must give prominent notice with each copy of the work that the +Library is used in it and that the Library and its use are covered by +this License. You must supply a copy of this License. If the work +during execution displays copyright notices, you must include the +copyright notice for the Library among them, as well as a reference +directing the user to the copy of this License. Also, you must do one +of these things: + + a) Accompany the work with the complete corresponding + machine-readable source code for the Library including whatever + changes were used in the work (which must be distributed under + Sections 1 and 2 above); and, if the work is an executable linked + with the Library, with the complete machine-readable "work that + uses the Library", as object code and/or source code, so that the + user can modify the Library and then relink to produce a modified + executable containing the modified Library. (It is understood + that the user who changes the contents of definitions files in the + Library will not necessarily be able to recompile the application + to use the modified definitions.) + + b) Use a suitable shared library mechanism for linking with the + Library. A suitable mechanism is one that (1) uses at run time a + copy of the library already present on the user's computer system, + rather than copying library functions into the executable, and (2) + will operate properly with a modified version of the library, if + the user installs one, as long as the modified version is + interface-compatible with the version that the work was made with. + + c) Accompany the work with a written offer, valid for at + least three years, to give the same user the materials + specified in Subsection 6a, above, for a charge no more + than the cost of performing this distribution. + + d) If distribution of the work is made by offering access to copy + from a designated place, offer equivalent access to copy the above + specified materials from the same place. + + e) Verify that the user has already received a copy of these + materials or that you have already sent this user a copy. + + For an executable, the required form of the "work that uses the +Library" must include any data and utility programs needed for +reproducing the executable from it. However, as a special exception, +the materials to be distributed need not include anything that is +normally distributed (in either source or binary form) with the major +components (compiler, kernel, and so on) of the operating system on +which the executable runs, unless that component itself accompanies +the executable. + + It may happen that this requirement contradicts the license +restrictions of other proprietary libraries that do not normally +accompany the operating system. Such a contradiction means you cannot +use both them and the Library together in an executable that you +distribute. + + 7. You may place library facilities that are a work based on the +Library side-by-side in a single library together with other library +facilities not covered by this License, and distribute such a combined +library, provided that the separate distribution of the work based on +the Library and of the other library facilities is otherwise +permitted, and provided that you do these two things: + + a) Accompany the combined library with a copy of the same work + based on the Library, uncombined with any other library + facilities. This must be distributed under the terms of the + Sections above. + + b) Give prominent notice with the combined library of the fact + that part of it is a work based on the Library, and explaining + where to find the accompanying uncombined form of the same work. + + 8. You may not copy, modify, sublicense, link with, or distribute +the Library except as expressly provided under this License. Any +attempt otherwise to copy, modify, sublicense, link with, or +distribute the Library is void, and will automatically terminate your +rights under this License. However, parties who have received copies, +or rights, from you under this License will not have their licenses +terminated so long as such parties remain in full compliance. + + 9. You are not required to accept this License, since you have not +signed it. However, nothing else grants you permission to modify or +distribute the Library or its derivative works. These actions are +prohibited by law if you do not accept this License. Therefore, by +modifying or distributing the Library (or any work based on the +Library), you indicate your acceptance of this License to do so, and +all its terms and conditions for copying, distributing or modifying +the Library or works based on it. + + 10. Each time you redistribute the Library (or any work based on the +Library), the recipient automatically receives a license from the +original licensor to copy, distribute, link with or modify the Library +subject to these terms and conditions. You may not impose any further +restrictions on the recipients' exercise of the rights granted herein. +You are not responsible for enforcing compliance by third parties with +this License. + + 11. If, as a consequence of a court judgment or allegation of patent +infringement or for any other reason (not limited to patent issues), +conditions are imposed on you (whether by court order, agreement or +otherwise) that contradict the conditions of this License, they do not +excuse you from the conditions of this License. If you cannot +distribute so as to satisfy simultaneously your obligations under this +License and any other pertinent obligations, then as a consequence you +may not distribute the Library at all. For example, if a patent +license would not permit royalty-free redistribution of the Library by +all those who receive copies directly or indirectly through you, then +the only way you could satisfy both it and this License would be to +refrain entirely from distribution of the Library. + +If any portion of this section is held invalid or unenforceable under any +particular circumstance, the balance of the section is intended to apply, +and the section as a whole is intended to apply in other circumstances. + +It is not the purpose of this section to induce you to infringe any +patents or other property right claims or to contest validity of any +such claims; this section has the sole purpose of protecting the +integrity of the free software distribution system which is +implemented by public license practices. Many people have made +generous contributions to the wide range of software distributed +through that system in reliance on consistent application of that +system; it is up to the author/donor to decide if he or she is willing +to distribute software through any other system and a licensee cannot +impose that choice. + +This section is intended to make thoroughly clear what is believed to +be a consequence of the rest of this License. + + 12. If the distribution and/or use of the Library is restricted in +certain countries either by patents or by copyrighted interfaces, the +original copyright holder who places the Library under this License may add +an explicit geographical distribution limitation excluding those countries, +so that distribution is permitted only in or among countries not thus +excluded. In such case, this License incorporates the limitation as if +written in the body of this License. + + 13. The Free Software Foundation may publish revised and/or new +versions of the Lesser General Public License from time to time. +Such new versions will be similar in spirit to the present version, +but may differ in detail to address new problems or concerns. + +Each version is given a distinguishing version number. If the Library +specifies a version number of this License which applies to it and +"any later version", you have the option of following the terms and +conditions either of that version or of any later version published by +the Free Software Foundation. If the Library does not specify a +license version number, you may choose any version ever published by +the Free Software Foundation. + + 14. If you wish to incorporate parts of the Library into other free +programs whose distribution conditions are incompatible with these, +write to the author to ask for permission. For software which is +copyrighted by the Free Software Foundation, write to the Free +Software Foundation; we sometimes make exceptions for this. Our +decision will be guided by the two goals of preserving the free status +of all derivatives of our free software and of promoting the sharing +and reuse of software generally. + + NO WARRANTY + + 15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO +WARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW. +EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR +OTHER PARTIES PROVIDE THE LIBRARY "AS IS" WITHOUT WARRANTY OF ANY +KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE +IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR +PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE +LIBRARY IS WITH YOU. SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME +THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION. + + 16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN +WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY +AND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU +FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR +CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE +LIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING +RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A +FAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF +SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH +DAMAGES. + + END OF TERMS AND CONDITIONS + + How to Apply These Terms to Your New Libraries + + If you develop a new library, and you want it to be of the greatest +possible use to the public, we recommend making it free software that +everyone can redistribute and change. You can do so by permitting +redistribution under these terms (or, alternatively, under the terms of the +ordinary General Public License). + + To apply these terms, attach the following notices to the library. It is +safest to attach them to the start of each source file to most effectively +convey the exclusion of warranty; and each file should have at least the +"copyright" line and a pointer to where the full notice is found. + + {description} + Copyright (C) {year} {fullname} + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with this library; if not, write to the Free Software + Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 + USA + +Also add information on how to contact you by electronic and paper mail. + +You should also get your employer (if you work as a programmer) or your +school, if any, to sign a "copyright disclaimer" for the library, if +necessary. Here is a sample; alter the names: + + Yoyodyne, Inc., hereby disclaims all copyright interest in the + library `Frob' (a library for tweaking knobs) written by James Random + Hacker. + + {signature of Ty Coon}, 1 April 1990 + Ty Coon, President of Vice + +That's all there is to it!
View file
libhdhomerun_20150826.tgz/Makefile -> libhdhomerun_20190621.tgz/Makefile
Changed
@@ -14,7 +14,7 @@ CC := $(CROSS_COMPILE)gcc STRIP := $(CROSS_COMPILE)strip -CFLAGS += -Wall -O2 -Wmissing-declarations -Wmissing-prototypes -Wstrict-prototypes -Wpointer-arith +CFLAGS += -O2 -Wall -Wextra -Wmissing-declarations -Wmissing-prototypes -Wstrict-prototypes -Wpointer-arith -Wno-unused-parameter LDFLAGS += -lpthread SHARED = -shared -Wl,-soname,libhdhomerun$(LIBEXT) @@ -32,7 +32,7 @@ LDFLAGS += -lsocket endif ifeq ($(OS),Darwin) - CFLAGS += -arch i386 -arch x86_64 + CFLAGS += -arch x86_64 LIBEXT := .dylib SHARED := -dynamiclib -install_name libhdhomerun$(LIBEXT) endif
View file
libhdhomerun_20190621.tgz/README.md
Added
@@ -0,0 +1,12 @@ +Copyright © 2005-2017 Silicondust USA Inc. <www.silicondust.com>. + +This library implements the libhdhomerun protocol for use with Silicondust HDHomeRun TV tuners. + +To compile simply "make" - this will compile both the library and the hdhomerun_config command line +utility suitable for sending commands or scripting control of a HDHomeRun. + +The top level API is hdhomerun_device - see hdhomerun_device.h for documentation. + +Additional libraries required: +- pthread (osx, linux, bsd) +- iphlpapi (windows)
View file
libhdhomerun_20150826.tgz/hdhomerun_channels.c -> libhdhomerun_20190621.tgz/hdhomerun_channels.c
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_channels.c * - * Copyright © 2007-2008 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2007-2014 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -83,6 +83,13 @@ { 0, 0, 0, 0} }; +/* TW antenna channels. */ +static const struct hdhomerun_channelmap_range_t hdhomerun_channelmap_range_tw_bcast[] = { + { 7, 13, 177000000, 6000000}, + { 14, 69, 473000000, 6000000}, + { 0, 0, 0, 0} +}; + /* US antenna channels. */ static const struct hdhomerun_channelmap_range_t hdhomerun_channelmap_range_us_bcast[] = { { 2, 4, 57000000, 6000000}, @@ -136,7 +143,7 @@ {"au-cable", hdhomerun_channelmap_range_eu_cable, "au-cable", "AU"}, {"eu-bcast", hdhomerun_channelmap_range_eu_bcast, "eu-bcast", NULL}, {"eu-cable", hdhomerun_channelmap_range_eu_cable, "eu-cable", NULL}, - {"tw-bcast", hdhomerun_channelmap_range_us_bcast, "tw-bcast", "TW"}, + {"tw-bcast", hdhomerun_channelmap_range_tw_bcast, "tw-bcast", "TW"}, {"tw-cable", hdhomerun_channelmap_range_us_cable, "tw-cable", "TW"}, {"kr-bcast", hdhomerun_channelmap_range_us_bcast, "kr-bcast", "KR"},
View file
libhdhomerun_20150826.tgz/hdhomerun_channels.h -> libhdhomerun_20190621.tgz/hdhomerun_channels.h
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_channels.h * - * Copyright © 2007-2008 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2007-2015 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -25,27 +25,27 @@ struct hdhomerun_channel_entry_t; struct hdhomerun_channel_list_t; -extern LIBTYPE const char *hdhomerun_channelmap_get_channelmap_from_country_source(const char *countrycode, const char *source, const char *supported); -extern LIBTYPE const char *hdhomerun_channelmap_get_channelmap_scan_group(const char *channelmap); +extern LIBHDHOMERUN_API const char *hdhomerun_channelmap_get_channelmap_from_country_source(const char *countrycode, const char *source, const char *supported); +extern LIBHDHOMERUN_API const char *hdhomerun_channelmap_get_channelmap_scan_group(const char *channelmap); -extern LIBTYPE uint16_t hdhomerun_channel_entry_channel_number(struct hdhomerun_channel_entry_t *entry); -extern LIBTYPE uint32_t hdhomerun_channel_entry_frequency(struct hdhomerun_channel_entry_t *entry); -extern LIBTYPE const char *hdhomerun_channel_entry_name(struct hdhomerun_channel_entry_t *entry); +extern LIBHDHOMERUN_API uint16_t hdhomerun_channel_entry_channel_number(struct hdhomerun_channel_entry_t *entry); +extern LIBHDHOMERUN_API uint32_t hdhomerun_channel_entry_frequency(struct hdhomerun_channel_entry_t *entry); +extern LIBHDHOMERUN_API const char *hdhomerun_channel_entry_name(struct hdhomerun_channel_entry_t *entry); -extern LIBTYPE struct hdhomerun_channel_list_t *hdhomerun_channel_list_create(const char *channelmap); -extern LIBTYPE void hdhomerun_channel_list_destroy(struct hdhomerun_channel_list_t *channel_list); +extern LIBHDHOMERUN_API struct hdhomerun_channel_list_t *hdhomerun_channel_list_create(const char *channelmap); +extern LIBHDHOMERUN_API void hdhomerun_channel_list_destroy(struct hdhomerun_channel_list_t *channel_list); -extern LIBTYPE struct hdhomerun_channel_entry_t *hdhomerun_channel_list_first(struct hdhomerun_channel_list_t *channel_list); -extern LIBTYPE struct hdhomerun_channel_entry_t *hdhomerun_channel_list_last(struct hdhomerun_channel_list_t *channel_list); -extern LIBTYPE struct hdhomerun_channel_entry_t *hdhomerun_channel_list_next(struct hdhomerun_channel_list_t *channel_list, struct hdhomerun_channel_entry_t *entry); -extern LIBTYPE struct hdhomerun_channel_entry_t *hdhomerun_channel_list_prev(struct hdhomerun_channel_list_t *channel_list, struct hdhomerun_channel_entry_t *entry); -extern LIBTYPE uint32_t hdhomerun_channel_list_total_count(struct hdhomerun_channel_list_t *channel_list); -extern LIBTYPE uint32_t hdhomerun_channel_list_frequency_count(struct hdhomerun_channel_list_t *channel_list); +extern LIBHDHOMERUN_API struct hdhomerun_channel_entry_t *hdhomerun_channel_list_first(struct hdhomerun_channel_list_t *channel_list); +extern LIBHDHOMERUN_API struct hdhomerun_channel_entry_t *hdhomerun_channel_list_last(struct hdhomerun_channel_list_t *channel_list); +extern LIBHDHOMERUN_API struct hdhomerun_channel_entry_t *hdhomerun_channel_list_next(struct hdhomerun_channel_list_t *channel_list, struct hdhomerun_channel_entry_t *entry); +extern LIBHDHOMERUN_API struct hdhomerun_channel_entry_t *hdhomerun_channel_list_prev(struct hdhomerun_channel_list_t *channel_list, struct hdhomerun_channel_entry_t *entry); +extern LIBHDHOMERUN_API uint32_t hdhomerun_channel_list_total_count(struct hdhomerun_channel_list_t *channel_list); +extern LIBHDHOMERUN_API uint32_t hdhomerun_channel_list_frequency_count(struct hdhomerun_channel_list_t *channel_list); -extern LIBTYPE uint32_t hdhomerun_channel_frequency_round(uint32_t frequency, uint32_t resolution); -extern LIBTYPE uint32_t hdhomerun_channel_frequency_round_normal(uint32_t frequency); -extern LIBTYPE uint32_t hdhomerun_channel_number_to_frequency(struct hdhomerun_channel_list_t *channel_list, uint16_t channel_number); -extern LIBTYPE uint16_t hdhomerun_channel_frequency_to_number(struct hdhomerun_channel_list_t *channel_list, uint32_t frequency); +extern LIBHDHOMERUN_API uint32_t hdhomerun_channel_frequency_round(uint32_t frequency, uint32_t resolution); +extern LIBHDHOMERUN_API uint32_t hdhomerun_channel_frequency_round_normal(uint32_t frequency); +extern LIBHDHOMERUN_API uint32_t hdhomerun_channel_number_to_frequency(struct hdhomerun_channel_list_t *channel_list, uint16_t channel_number); +extern LIBHDHOMERUN_API uint16_t hdhomerun_channel_frequency_to_number(struct hdhomerun_channel_list_t *channel_list, uint32_t frequency); #ifdef __cplusplus }
View file
libhdhomerun_20150826.tgz/hdhomerun_channelscan.c -> libhdhomerun_20190621.tgz/hdhomerun_channelscan.c
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_channelscan.c * - * Copyright © 2007-2010 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2007-2015 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -127,10 +127,10 @@ program->name[length] = 0; } -static int channelscan_detect_programs(struct hdhomerun_channelscan_t *scan, struct hdhomerun_channelscan_result_t *result, bool_t *pchanged, bool_t *pincomplete) +static int channelscan_detect_programs(struct hdhomerun_channelscan_t *scan, struct hdhomerun_channelscan_result_t *result, bool *pchanged, bool *pincomplete) { - *pchanged = FALSE; - *pincomplete = FALSE; + *pchanged = false; + *pincomplete = false; char *streaminfo; int ret = hdhomerun_device_get_tuner_streaminfo(scan->hd, &streaminfo); @@ -152,15 +152,15 @@ unsigned int transport_stream_id; if (sscanf(line, "tsid=0x%x", &transport_stream_id) == 1) { - result->transport_stream_id = transport_stream_id; - result->transport_stream_id_detected = TRUE; + result->transport_stream_id = (uint16_t)transport_stream_id; + result->transport_stream_id_detected = true; continue; } unsigned int original_network_id; if (sscanf(line, "onid=0x%x", &original_network_id) == 1) { - result->original_network_id = original_network_id; - result->original_network_id_detected = TRUE; + result->original_network_id = (uint16_t)original_network_id; + result->original_network_id_detected = true; continue; } @@ -182,9 +182,9 @@ virtual_minor = 0; } - program.program_number = program_number; - program.virtual_major = virtual_major; - program.virtual_minor = virtual_minor; + program.program_number = (uint16_t)program_number; + program.virtual_major = (uint16_t)virtual_major; + program.virtual_minor = (uint16_t)virtual_minor; channelscan_extract_name(&program, line); @@ -194,28 +194,28 @@ program.type = HDHOMERUN_CHANNELSCAN_PROGRAM_ENCRYPTED; } else if (strstr(line, "(no data)")) { program.type = HDHOMERUN_CHANNELSCAN_PROGRAM_NODATA; - *pincomplete = TRUE; + *pincomplete = true; } else { program.type = HDHOMERUN_CHANNELSCAN_PROGRAM_NORMAL; if ((program.virtual_major == 0) || (program.name[0] == 0)) { - *pincomplete = TRUE; + *pincomplete = true; } } if (memcmp(&result->programs[program_count], &program, sizeof(program)) != 0) { memcpy(&result->programs[program_count], &program, sizeof(program)); - *pchanged = TRUE; + *pchanged = true; } program_count++; } if (program_count == 0) { - *pincomplete = TRUE; + *pincomplete = true; } if (result->program_count != program_count) { result->program_count = program_count; - *pchanged = TRUE; + *pchanged = true; } return 1; @@ -282,7 +282,7 @@ uint64_t complete_time = getcurrenttime() + 1000; while (1) { - bool_t changed, incomplete; + bool changed, incomplete; ret = channelscan_detect_programs(scan, result, &changed, &incomplete); if (ret <= 0) { return ret; @@ -343,5 +343,5 @@ } } - return scan->scanned_channels * 100 / (scan->scanned_channels + channels_remaining); + return (uint8_t) (scan->scanned_channels * 100 / (scan->scanned_channels + channels_remaining)); }
View file
libhdhomerun_20150826.tgz/hdhomerun_channelscan.h -> libhdhomerun_20190621.tgz/hdhomerun_channelscan.h
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_channelscan.h * - * Copyright © 2007-2008 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2007-2015 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -29,12 +29,12 @@ struct hdhomerun_channelscan_t; -extern LIBTYPE struct hdhomerun_channelscan_t *channelscan_create(struct hdhomerun_device_t *hd, const char *channelmap); -extern LIBTYPE void channelscan_destroy(struct hdhomerun_channelscan_t *scan); +extern LIBHDHOMERUN_API struct hdhomerun_channelscan_t *channelscan_create(struct hdhomerun_device_t *hd, const char *channelmap); +extern LIBHDHOMERUN_API void channelscan_destroy(struct hdhomerun_channelscan_t *scan); -extern LIBTYPE int channelscan_advance(struct hdhomerun_channelscan_t *scan, struct hdhomerun_channelscan_result_t *result); -extern LIBTYPE int channelscan_detect(struct hdhomerun_channelscan_t *scan, struct hdhomerun_channelscan_result_t *result); -extern LIBTYPE uint8_t channelscan_get_progress(struct hdhomerun_channelscan_t *scan); +extern LIBHDHOMERUN_API int channelscan_advance(struct hdhomerun_channelscan_t *scan, struct hdhomerun_channelscan_result_t *result); +extern LIBHDHOMERUN_API int channelscan_detect(struct hdhomerun_channelscan_t *scan, struct hdhomerun_channelscan_result_t *result); +extern LIBHDHOMERUN_API uint8_t channelscan_get_progress(struct hdhomerun_channelscan_t *scan); #ifdef __cplusplus }
View file
libhdhomerun_20150826.tgz/hdhomerun_config.c -> libhdhomerun_20190621.tgz/hdhomerun_config.c
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_config.c * - * Copyright © 2006-2008 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2006-2017 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -20,16 +20,6 @@ #include "hdhomerun.h" -/* - * The console output format should be set to UTF-8, however in XP and Vista this breaks batch file processing. - * Attempting to restore on exit fails to restore if the program is terminated by the user. - * Solution - set the output format each printf. - */ -#if defined(__WINDOWS__) -#define printf console_printf -#define vprintf console_vprintf -#endif - static const char *appname; struct hdhomerun_device_t *hd; @@ -60,23 +50,23 @@ appname = argv0; } -static bool_t contains(const char *arg, const char *cmpstr) +static bool contains(const char *arg, const char *cmpstr) { if (strcmp(arg, cmpstr) == 0) { - return TRUE; + return true; } if (*arg++ != '-') { - return FALSE; + return false; } if (*arg++ != '-') { - return FALSE; + return false; } if (strcmp(arg, cmpstr) == 0) { - return TRUE; + return true; } - return FALSE; + return false; } static uint32_t parse_ip_addr(const char *str) @@ -101,27 +91,37 @@ } struct hdhomerun_discover_device_t result_list[64]; - int count = hdhomerun_discover_find_devices_custom_v2(target_ip, HDHOMERUN_DEVICE_TYPE_TUNER, HDHOMERUN_DEVICE_ID_WILDCARD, result_list, 64); - if (count < 0) { + int result_count = hdhomerun_discover_find_devices_custom_v2(target_ip, HDHOMERUN_DEVICE_TYPE_WILDCARD, HDHOMERUN_DEVICE_ID_WILDCARD, result_list, 64); + if (result_count < 0) { fprintf(stderr, "error sending discover request\n"); return -1; } - if (count == 0) { - printf("no devices found\n"); - return 0; - } - int index; - for (index = 0; index < count; index++) { - struct hdhomerun_discover_device_t *result = &result_list[index]; + struct hdhomerun_discover_device_t *result = result_list; + struct hdhomerun_discover_device_t *result_end = result_list + result_count; + + int valid_count = 0; + while (result < result_end) { + if (result->device_id == 0) { + result++; + continue; + } + printf("hdhomerun device %08X found at %u.%u.%u.%u\n", (unsigned int)result->device_id, (unsigned int)(result->ip_addr >> 24) & 0x0FF, (unsigned int)(result->ip_addr >> 16) & 0x0FF, (unsigned int)(result->ip_addr >> 8) & 0x0FF, (unsigned int)(result->ip_addr >> 0) & 0x0FF ); + + valid_count++; + result++; + } + + if (valid_count == 0) { + printf("no devices found\n"); } - return count; + return valid_count; } static int cmd_get(const char *item) @@ -190,17 +190,17 @@ return cmd_set_internal(item, value); } -static volatile sig_atomic_t sigabort_flag = FALSE; -static volatile sig_atomic_t siginfo_flag = FALSE; +static volatile sig_atomic_t sigabort_flag = false; +static volatile sig_atomic_t siginfo_flag = false; static void sigabort_handler(int arg) { - sigabort_flag = TRUE; + sigabort_flag = true; } static void siginfo_handler(int arg) { - siginfo_flag = TRUE; + siginfo_flag = true; } static void register_signal_handlers(sig_t sigpipe_handler, sig_t sigint_handler, sig_t siginfo_handler) @@ -389,7 +389,7 @@ if (siginfo_flag) { fprintf(stderr, "\n"); cmd_save_print_stats(); - siginfo_flag = FALSE; + siginfo_flag = false; } size_t actual_size; @@ -413,7 +413,7 @@ } /* Windows - indicate activity to suppress auto sleep mode. */ - #if defined(__WINDOWS__) + #if defined(_WIN32) SetThreadExecutionState(ES_SYSTEM_REQUIRED); #endif @@ -570,7 +570,7 @@ if (argc < 2) { return help(); } - uint32_t lockkey = strtoul(argv[0], NULL, 0); + uint32_t lockkey = (uint32_t)strtoul(argv[0], NULL, 0); hdhomerun_device_tuner_lockkey_use_value(hd, lockkey); cmd = argv[1]; @@ -625,7 +625,9 @@ static int main_internal(int argc, char *argv[]) { -#if defined(__WINDOWS__) +#if defined(_WIN32) + /* Configure console for UTF-8. */ + SetConsoleOutputCP(CP_UTF8); /* Initialize network socket support. */ WORD wVersionRequested = MAKEWORD(2, 0); WSADATA wsaData;
View file
libhdhomerun_20150826.tgz/hdhomerun_control.c -> libhdhomerun_20190621.tgz/hdhomerun_control.c
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_control.c * - * Copyright © 2006-2010 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2006-2016 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -30,7 +30,7 @@ uint32_t desired_device_ip; uint32_t actual_device_id; uint32_t actual_device_ip; - hdhomerun_sock_t sock; + struct hdhomerun_sock_t *sock; struct hdhomerun_debug_t *dbg; struct hdhomerun_pkt_t tx_pkt; struct hdhomerun_pkt_t rx_pkt; @@ -38,12 +38,12 @@ static void hdhomerun_control_close_sock(struct hdhomerun_control_sock_t *cs) { - if (cs->sock == HDHOMERUN_SOCK_INVALID) { + if (!cs->sock) { return; } hdhomerun_sock_destroy(cs->sock); - cs->sock = HDHOMERUN_SOCK_INVALID; + cs->sock = NULL; } void hdhomerun_control_set_device(struct hdhomerun_control_sock_t *cs, uint32_t device_id, uint32_t device_ip) @@ -65,7 +65,6 @@ } cs->dbg = dbg; - cs->sock = HDHOMERUN_SOCK_INVALID; hdhomerun_control_set_device(cs, device_id, device_ip); return cs; @@ -77,46 +76,46 @@ free(cs); } -static bool_t hdhomerun_control_connect_sock(struct hdhomerun_control_sock_t *cs) +static bool hdhomerun_control_connect_sock(struct hdhomerun_control_sock_t *cs) { - if (cs->sock != HDHOMERUN_SOCK_INVALID) { - return TRUE; + if (cs->sock) { + return true; } if ((cs->desired_device_id == 0) && (cs->desired_device_ip == 0)) { hdhomerun_debug_printf(cs->dbg, "hdhomerun_control_connect_sock: no device specified\n"); - return FALSE; + return false; } if (hdhomerun_discover_is_ip_multicast(cs->desired_device_ip)) { hdhomerun_debug_printf(cs->dbg, "hdhomerun_control_connect_sock: cannot use multicast ip address for device operations\n"); - return FALSE; + return false; } /* Find device. */ struct hdhomerun_discover_device_t result; if (hdhomerun_discover_find_devices_custom_v2(cs->desired_device_ip, HDHOMERUN_DEVICE_TYPE_WILDCARD, cs->desired_device_id, &result, 1) <= 0) { hdhomerun_debug_printf(cs->dbg, "hdhomerun_control_connect_sock: device not found\n"); - return FALSE; + return false; } cs->actual_device_ip = result.ip_addr; cs->actual_device_id = result.device_id; /* Create socket. */ cs->sock = hdhomerun_sock_create_tcp(); - if (cs->sock == HDHOMERUN_SOCK_INVALID) { + if (!cs->sock) { hdhomerun_debug_printf(cs->dbg, "hdhomerun_control_connect_sock: failed to create socket (%d)\n", hdhomerun_sock_getlasterror()); - return FALSE; + return false; } /* Initiate connection. */ if (!hdhomerun_sock_connect(cs->sock, cs->actual_device_ip, HDHOMERUN_CONTROL_TCP_PORT, HDHOMERUN_CONTROL_CONNECT_TIMEOUT)) { hdhomerun_debug_printf(cs->dbg, "hdhomerun_control_connect_sock: failed to connect (%d)\n", hdhomerun_sock_getlasterror()); hdhomerun_control_close_sock(cs); - return FALSE; + return false; } /* Success. */ - return TRUE; + return true; } uint32_t hdhomerun_control_get_device_id(struct hdhomerun_control_sock_t *cs) @@ -165,18 +164,18 @@ return addr; } -static bool_t hdhomerun_control_send_sock(struct hdhomerun_control_sock_t *cs, struct hdhomerun_pkt_t *tx_pkt) +static bool hdhomerun_control_send_sock(struct hdhomerun_control_sock_t *cs, struct hdhomerun_pkt_t *tx_pkt) { if (!hdhomerun_sock_send(cs->sock, tx_pkt->start, tx_pkt->end - tx_pkt->start, HDHOMERUN_CONTROL_SEND_TIMEOUT)) { hdhomerun_debug_printf(cs->dbg, "hdhomerun_control_send_sock: send failed (%d)\n", hdhomerun_sock_getlasterror()); hdhomerun_control_close_sock(cs); - return FALSE; + return false; } - return TRUE; + return true; } -static bool_t hdhomerun_control_recv_sock(struct hdhomerun_control_sock_t *cs, struct hdhomerun_pkt_t *rx_pkt, uint16_t *ptype, uint64_t recv_timeout) +static bool hdhomerun_control_recv_sock(struct hdhomerun_control_sock_t *cs, struct hdhomerun_pkt_t *rx_pkt, uint16_t *ptype, uint64_t recv_timeout) { uint64_t stop_time = getcurrenttime() + recv_timeout; hdhomerun_pkt_reset(rx_pkt); @@ -186,14 +185,14 @@ if (current_time >= stop_time) { hdhomerun_debug_printf(cs->dbg, "hdhomerun_control_recv_sock: timeout\n"); hdhomerun_control_close_sock(cs); - return FALSE; + return false; } size_t length = rx_pkt->limit - rx_pkt->end; if (!hdhomerun_sock_recv(cs->sock, rx_pkt->end, &length, stop_time - current_time)) { hdhomerun_debug_printf(cs->dbg, "hdhomerun_control_recv_sock: recv failed (%d)\n", hdhomerun_sock_getlasterror()); hdhomerun_control_close_sock(cs); - return FALSE; + return false; } rx_pkt->end += length; @@ -202,10 +201,10 @@ if (ret < 0) { hdhomerun_debug_printf(cs->dbg, "hdhomerun_control_recv_sock: frame error\n"); hdhomerun_control_close_sock(cs); - return FALSE; + return false; } if (ret > 0) { - return TRUE; + return true; } } } @@ -216,7 +215,7 @@ int i; for (i = 0; i < 2; i++) { - if (cs->sock == HDHOMERUN_SOCK_INVALID) { + if (!cs->sock) { if (!hdhomerun_control_connect_sock(cs)) { hdhomerun_debug_printf(cs->dbg, "hdhomerun_control_send_recv: connect failed\n"); return -1; @@ -260,7 +259,7 @@ /* Request. */ hdhomerun_pkt_reset(tx_pkt); - int name_len = (int)strlen(name) + 1; + size_t name_len = strlen(name) + 1; if (tx_pkt->end + 3 + name_len > tx_pkt->limit) { hdhomerun_debug_printf(cs->dbg, "hdhomerun_control_get_set: request too long\n"); return -1; @@ -270,7 +269,7 @@ hdhomerun_pkt_write_mem(tx_pkt, (const void *)name, name_len); if (value) { - int value_len = (int)strlen(value) + 1; + size_t value_len = strlen(value) + 1; if (tx_pkt->end + 3 + value_len > tx_pkt->limit) { hdhomerun_debug_printf(cs->dbg, "hdhomerun_control_get_set: request too long\n"); return -1; @@ -328,6 +327,9 @@ } return 0; + + default: + break; } rx_pkt->pos = next; @@ -356,7 +358,7 @@ { struct hdhomerun_pkt_t *tx_pkt = &cs->tx_pkt; struct hdhomerun_pkt_t *rx_pkt = &cs->rx_pkt; - bool_t upload_delay = FALSE; + bool upload_delay = false; uint32_t sequence = 0; /* Special case detection. */
View file
libhdhomerun_20150826.tgz/hdhomerun_control.h -> libhdhomerun_20190621.tgz/hdhomerun_control.h
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_control.h * - * Copyright © 2006 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2006-2015 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -37,20 +37,20 @@ * * When no longer needed, the socket should be destroyed by calling hdhomerun_control_destroy. */ -extern LIBTYPE struct hdhomerun_control_sock_t *hdhomerun_control_create(uint32_t device_id, uint32_t device_ip, struct hdhomerun_debug_t *dbg); -extern LIBTYPE void hdhomerun_control_destroy(struct hdhomerun_control_sock_t *cs); +extern LIBHDHOMERUN_API struct hdhomerun_control_sock_t *hdhomerun_control_create(uint32_t device_id, uint32_t device_ip, struct hdhomerun_debug_t *dbg); +extern LIBHDHOMERUN_API void hdhomerun_control_destroy(struct hdhomerun_control_sock_t *cs); /* * Get the actual device id or ip of the device. * * Returns 0 if the device id cannot be determined. */ -extern LIBTYPE uint32_t hdhomerun_control_get_device_id(struct hdhomerun_control_sock_t *cs); -extern LIBTYPE uint32_t hdhomerun_control_get_device_ip(struct hdhomerun_control_sock_t *cs); -extern LIBTYPE uint32_t hdhomerun_control_get_device_id_requested(struct hdhomerun_control_sock_t *cs); -extern LIBTYPE uint32_t hdhomerun_control_get_device_ip_requested(struct hdhomerun_control_sock_t *cs); +extern LIBHDHOMERUN_API uint32_t hdhomerun_control_get_device_id(struct hdhomerun_control_sock_t *cs); +extern LIBHDHOMERUN_API uint32_t hdhomerun_control_get_device_ip(struct hdhomerun_control_sock_t *cs); +extern LIBHDHOMERUN_API uint32_t hdhomerun_control_get_device_id_requested(struct hdhomerun_control_sock_t *cs); +extern LIBHDHOMERUN_API uint32_t hdhomerun_control_get_device_ip_requested(struct hdhomerun_control_sock_t *cs); -extern LIBTYPE void hdhomerun_control_set_device(struct hdhomerun_control_sock_t *cs, uint32_t device_id, uint32_t device_ip); +extern LIBHDHOMERUN_API void hdhomerun_control_set_device(struct hdhomerun_control_sock_t *cs, uint32_t device_id, uint32_t device_ip); /* * Get the local machine IP address used when communicating with the device. @@ -59,12 +59,12 @@ * * Returns 32-bit IP address with native endianness, or 0 on error. */ -extern LIBTYPE uint32_t hdhomerun_control_get_local_addr(struct hdhomerun_control_sock_t *cs); +extern LIBHDHOMERUN_API uint32_t hdhomerun_control_get_local_addr(struct hdhomerun_control_sock_t *cs); /* * Low-level communication. */ -extern LIBTYPE int hdhomerun_control_send_recv(struct hdhomerun_control_sock_t *cs, struct hdhomerun_pkt_t *tx_pkt, struct hdhomerun_pkt_t *rx_pkt, uint16_t type); +extern LIBHDHOMERUN_API int hdhomerun_control_send_recv(struct hdhomerun_control_sock_t *cs, struct hdhomerun_pkt_t *tx_pkt, struct hdhomerun_pkt_t *rx_pkt, uint16_t type); /* * Get/set a control variable on the device. @@ -83,9 +83,9 @@ * Returns 0 if the operation was rejected (pvalue NULL, perror set). * Returns -1 if a communication error occurs. */ -extern LIBTYPE int hdhomerun_control_get(struct hdhomerun_control_sock_t *cs, const char *name, char **pvalue, char **perror); -extern LIBTYPE int hdhomerun_control_set(struct hdhomerun_control_sock_t *cs, const char *name, const char *value, char **pvalue, char **perror); -extern LIBTYPE int hdhomerun_control_set_with_lockkey(struct hdhomerun_control_sock_t *cs, const char *name, const char *value, uint32_t lockkey, char **pvalue, char **perror); +extern LIBHDHOMERUN_API int hdhomerun_control_get(struct hdhomerun_control_sock_t *cs, const char *name, char **pvalue, char **perror); +extern LIBHDHOMERUN_API int hdhomerun_control_set(struct hdhomerun_control_sock_t *cs, const char *name, const char *value, char **pvalue, char **perror); +extern LIBHDHOMERUN_API int hdhomerun_control_set_with_lockkey(struct hdhomerun_control_sock_t *cs, const char *name, const char *value, uint32_t lockkey, char **pvalue, char **perror); /* * Upload new firmware to the device. @@ -96,7 +96,7 @@ * Returns 0 if the upload was rejected. * Returns -1 if an error occurs. */ -extern LIBTYPE int hdhomerun_control_upgrade(struct hdhomerun_control_sock_t *cs, FILE *upgrade_file); +extern LIBHDHOMERUN_API int hdhomerun_control_upgrade(struct hdhomerun_control_sock_t *cs, FILE *upgrade_file); #ifdef __cplusplus }
View file
libhdhomerun_20150826.tgz/hdhomerun_debug.c -> libhdhomerun_20190621.tgz/hdhomerun_debug.c
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_debug.c * - * Copyright © 2006-2010 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2007-2016 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -42,21 +42,21 @@ struct hdhomerun_debug_message_t { struct hdhomerun_debug_message_t *next; - struct hdhomerun_debug_message_t *prev; char buffer[2048]; }; struct hdhomerun_debug_t { - pthread_t thread; - volatile bool_t enabled; - volatile bool_t terminate; + thread_task_t thread; + volatile bool enabled; + volatile bool terminate; char *prefix; - pthread_mutex_t print_lock; - pthread_mutex_t queue_lock; - pthread_mutex_t send_lock; + thread_mutex_t print_lock; + thread_mutex_t queue_lock; + thread_mutex_t send_lock; + thread_cond_t queue_cond; struct hdhomerun_debug_message_t *queue_head; struct hdhomerun_debug_message_t *queue_tail; uint32_t queue_depth; @@ -65,10 +65,10 @@ char *file_name; FILE *file_fp; - hdhomerun_sock_t sock; + struct hdhomerun_sock_t *sock; }; -static THREAD_FUNC_PREFIX hdhomerun_debug_thread_execute(void *arg); +static void hdhomerun_debug_thread_execute(void *arg); struct hdhomerun_debug_t *hdhomerun_debug_create(void) { @@ -77,13 +77,12 @@ return NULL; } - dbg->sock = HDHOMERUN_SOCK_INVALID; + thread_mutex_init(&dbg->print_lock); + thread_mutex_init(&dbg->queue_lock); + thread_mutex_init(&dbg->send_lock); + thread_cond_init(&dbg->queue_cond); - pthread_mutex_init(&dbg->print_lock, NULL); - pthread_mutex_init(&dbg->queue_lock, NULL); - pthread_mutex_init(&dbg->send_lock, NULL); - - if (pthread_create(&dbg->thread, NULL, &hdhomerun_debug_thread_execute, dbg) != 0) { + if (!thread_task_create(&dbg->thread, &hdhomerun_debug_thread_execute, dbg)) { free(dbg); return NULL; } @@ -97,8 +96,9 @@ return; } - dbg->terminate = TRUE; - pthread_join(dbg->thread, NULL); + dbg->terminate = true; + thread_cond_signal(&dbg->queue_cond); + thread_task_join(dbg->thread); if (dbg->prefix) { free(dbg->prefix); @@ -109,10 +109,14 @@ if (dbg->file_fp) { fclose(dbg->file_fp); } - if (dbg->sock != HDHOMERUN_SOCK_INVALID) { + if (dbg->sock) { hdhomerun_sock_destroy(dbg->sock); } + thread_cond_dispose(&dbg->queue_cond); + thread_mutex_dispose(&dbg->print_lock); + thread_mutex_dispose(&dbg->queue_lock); + thread_mutex_dispose(&dbg->send_lock); free(dbg); } @@ -124,9 +128,9 @@ dbg->file_fp = NULL; } - if (dbg->sock != HDHOMERUN_SOCK_INVALID) { + if (dbg->sock) { hdhomerun_sock_destroy(dbg->sock); - dbg->sock = HDHOMERUN_SOCK_INVALID; + dbg->sock = NULL; } } @@ -140,10 +144,10 @@ hdhomerun_debug_flush(dbg, timeout); } - pthread_mutex_lock(&dbg->send_lock); + thread_mutex_lock(&dbg->send_lock); hdhomerun_debug_close_internal(dbg); dbg->connect_delay = 0; - pthread_mutex_unlock(&dbg->send_lock); + thread_mutex_unlock(&dbg->send_lock); } void hdhomerun_debug_set_filename(struct hdhomerun_debug_t *dbg, const char *filename) @@ -152,15 +156,15 @@ return; } - pthread_mutex_lock(&dbg->send_lock); + thread_mutex_lock(&dbg->send_lock); if (!filename && !dbg->file_name) { - pthread_mutex_unlock(&dbg->send_lock); + thread_mutex_unlock(&dbg->send_lock); return; } if (filename && dbg->file_name) { if (strcmp(filename, dbg->file_name) == 0) { - pthread_mutex_unlock(&dbg->send_lock); + thread_mutex_unlock(&dbg->send_lock); return; } } @@ -176,7 +180,7 @@ dbg->file_name = strdup(filename); } - pthread_mutex_unlock(&dbg->send_lock); + thread_mutex_unlock(&dbg->send_lock); } void hdhomerun_debug_set_prefix(struct hdhomerun_debug_t *dbg, const char *prefix) @@ -185,7 +189,7 @@ return; } - pthread_mutex_lock(&dbg->print_lock); + thread_mutex_lock(&dbg->print_lock); if (dbg->prefix) { free(dbg->prefix); @@ -196,7 +200,7 @@ dbg->prefix = strdup(prefix); } - pthread_mutex_unlock(&dbg->print_lock); + thread_mutex_unlock(&dbg->print_lock); } void hdhomerun_debug_enable(struct hdhomerun_debug_t *dbg) @@ -204,8 +208,12 @@ if (!dbg) { return; } + if (dbg->enabled) { + return; + } - dbg->enabled = TRUE; + dbg->enabled = true; + thread_cond_signal(&dbg->queue_cond); } void hdhomerun_debug_disable(struct hdhomerun_debug_t *dbg) @@ -214,13 +222,13 @@ return; } - dbg->enabled = FALSE; + dbg->enabled = false; } -bool_t hdhomerun_debug_enabled(struct hdhomerun_debug_t *dbg) +bool hdhomerun_debug_enabled(struct hdhomerun_debug_t *dbg) { if (!dbg) { - return FALSE; + return false; } return dbg->enabled; @@ -235,15 +243,15 @@ timeout = getcurrenttime() + timeout; while (getcurrenttime() < timeout) { - pthread_mutex_lock(&dbg->queue_lock); - struct hdhomerun_debug_message_t *message = dbg->queue_tail; - pthread_mutex_unlock(&dbg->queue_lock); + thread_mutex_lock(&dbg->queue_lock); + struct hdhomerun_debug_message_t *message = dbg->queue_head; + thread_mutex_unlock(&dbg->queue_lock); if (!message) { return; } - msleep_approx(10); + msleep_approx(16); } } @@ -260,15 +268,14 @@ if (!dbg) { return; } - if (!dbg->enabled) { - return; - } struct hdhomerun_debug_message_t *message = (struct hdhomerun_debug_message_t *)malloc(sizeof(struct hdhomerun_debug_message_t)); if (!message) { return; } + message->next = NULL; + char *ptr = message->buffer; char *end = message->buffer + sizeof(message->buffer) - 2; *end = 0; @@ -285,14 +292,14 @@ /* * Debug prefix. */ - pthread_mutex_lock(&dbg->print_lock); + thread_mutex_lock(&dbg->print_lock); if (dbg->prefix) { hdhomerun_sprintf(ptr, end, "%s ", dbg->prefix); ptr = strchr(ptr, 0); } - pthread_mutex_unlock(&dbg->print_lock); + thread_mutex_unlock(&dbg->print_lock); /* * Message text. @@ -310,125 +317,126 @@ /* * Enqueue. */ - pthread_mutex_lock(&dbg->queue_lock); + thread_mutex_lock(&dbg->queue_lock); - message->prev = NULL; - message->next = dbg->queue_head; - dbg->queue_head = message; - if (message->next) { - message->next->prev = message; + if (dbg->queue_tail) { + dbg->queue_tail->next = message; } else { - dbg->queue_tail = message; + dbg->queue_head = message; } + dbg->queue_tail = message; dbg->queue_depth++; - pthread_mutex_unlock(&dbg->queue_lock); + bool signal_thread = dbg->enabled || (dbg->queue_depth > 1024 + 100); + + thread_mutex_unlock(&dbg->queue_lock); + + if (signal_thread) { + thread_cond_signal(&dbg->queue_cond); + } } /* Send lock held by caller */ -static bool_t hdhomerun_debug_output_message_file(struct hdhomerun_debug_t *dbg, struct hdhomerun_debug_message_t *message) +static bool hdhomerun_debug_output_message_file(struct hdhomerun_debug_t *dbg, struct hdhomerun_debug_message_t *message) { if (!dbg->file_fp) { uint64_t current_time = getcurrenttime(); if (current_time < dbg->connect_delay) { - return FALSE; + return false; } dbg->connect_delay = current_time + 30*1000; dbg->file_fp = fopen(dbg->file_name, "a"); if (!dbg->file_fp) { - return FALSE; + return false; } } fprintf(dbg->file_fp, "%s", message->buffer); fflush(dbg->file_fp); - return TRUE; + return true; } /* Send lock held by caller */ -static bool_t hdhomerun_debug_output_message_sock(struct hdhomerun_debug_t *dbg, struct hdhomerun_debug_message_t *message) +static bool hdhomerun_debug_output_message_sock(struct hdhomerun_debug_t *dbg, struct hdhomerun_debug_message_t *message) { - if (dbg->sock == HDHOMERUN_SOCK_INVALID) { + if (!dbg->sock) { uint64_t current_time = getcurrenttime(); if (current_time < dbg->connect_delay) { - return FALSE; + return false; } dbg->connect_delay = current_time + HDHOMERUN_DEBUG_CONNECT_RETRY_TIME; dbg->sock = hdhomerun_sock_create_tcp(); - if (dbg->sock == HDHOMERUN_SOCK_INVALID) { - return FALSE; + if (!dbg->sock) { + return false; } uint32_t remote_addr = hdhomerun_sock_getaddrinfo_addr(dbg->sock, HDHOMERUN_DEBUG_HOST); if (remote_addr == 0) { hdhomerun_debug_close_internal(dbg); - return FALSE; + return false; } if (!hdhomerun_sock_connect(dbg->sock, remote_addr, HDHOMERUN_DEBUG_PORT, HDHOMERUN_DEBUG_CONNECT_TIMEOUT)) { hdhomerun_debug_close_internal(dbg); - return FALSE; + return false; } } size_t length = strlen(message->buffer); if (!hdhomerun_sock_send(dbg->sock, message->buffer, length, HDHOMERUN_DEBUG_SEND_TIMEOUT)) { hdhomerun_debug_close_internal(dbg); - return FALSE; + return false; } - return TRUE; + return true; } -static bool_t hdhomerun_debug_output_message(struct hdhomerun_debug_t *dbg, struct hdhomerun_debug_message_t *message) +static bool hdhomerun_debug_output_message(struct hdhomerun_debug_t *dbg, struct hdhomerun_debug_message_t *message) { - pthread_mutex_lock(&dbg->send_lock); + thread_mutex_lock(&dbg->send_lock); - bool_t ret; + bool ret; if (dbg->file_name) { ret = hdhomerun_debug_output_message_file(dbg, message); } else { ret = hdhomerun_debug_output_message_sock(dbg, message); } - pthread_mutex_unlock(&dbg->send_lock); + thread_mutex_unlock(&dbg->send_lock); return ret; } static void hdhomerun_debug_pop_and_free_message(struct hdhomerun_debug_t *dbg) { - pthread_mutex_lock(&dbg->queue_lock); + thread_mutex_lock(&dbg->queue_lock); - struct hdhomerun_debug_message_t *message = dbg->queue_tail; - dbg->queue_tail = message->prev; - if (message->prev) { - message->prev->next = NULL; - } else { - dbg->queue_head = NULL; + struct hdhomerun_debug_message_t *message = dbg->queue_head; + dbg->queue_head = message->next; + if (!dbg->queue_head) { + dbg->queue_tail = NULL; } dbg->queue_depth--; - pthread_mutex_unlock(&dbg->queue_lock); + thread_mutex_unlock(&dbg->queue_lock); free(message); } -static THREAD_FUNC_PREFIX hdhomerun_debug_thread_execute(void *arg) +static void hdhomerun_debug_thread_execute(void *arg) { struct hdhomerun_debug_t *dbg = (struct hdhomerun_debug_t *)arg; while (!dbg->terminate) { - - pthread_mutex_lock(&dbg->queue_lock); - struct hdhomerun_debug_message_t *message = dbg->queue_tail; + thread_mutex_lock(&dbg->queue_lock); + struct hdhomerun_debug_message_t *message = dbg->queue_head; uint32_t queue_depth = dbg->queue_depth; - pthread_mutex_unlock(&dbg->queue_lock); + thread_mutex_unlock(&dbg->queue_lock); if (!message) { - msleep_approx(250); + thread_cond_wait(&dbg->queue_cond); continue; } @@ -437,13 +445,16 @@ continue; } + if (!dbg->enabled) { + thread_cond_wait(&dbg->queue_cond); + continue; + } + if (!hdhomerun_debug_output_message(dbg, message)) { - msleep_approx(250); + msleep_approx(1000); continue; } hdhomerun_debug_pop_and_free_message(dbg); } - - return 0; }
View file
libhdhomerun_20150826.tgz/hdhomerun_debug.h -> libhdhomerun_20190621.tgz/hdhomerun_debug.h
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_debug.h * - * Copyright © 2006 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2007-2015 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -32,20 +32,20 @@ struct hdhomerun_debug_t; -extern LIBTYPE struct hdhomerun_debug_t *hdhomerun_debug_create(void); -extern LIBTYPE void hdhomerun_debug_destroy(struct hdhomerun_debug_t *dbg); +extern LIBHDHOMERUN_API struct hdhomerun_debug_t *hdhomerun_debug_create(void); +extern LIBHDHOMERUN_API void hdhomerun_debug_destroy(struct hdhomerun_debug_t *dbg); -extern LIBTYPE void hdhomerun_debug_set_prefix(struct hdhomerun_debug_t *dbg, const char *prefix); -extern LIBTYPE void hdhomerun_debug_set_filename(struct hdhomerun_debug_t *dbg, const char *filename); -extern LIBTYPE void hdhomerun_debug_enable(struct hdhomerun_debug_t *dbg); -extern LIBTYPE void hdhomerun_debug_disable(struct hdhomerun_debug_t *dbg); -extern LIBTYPE bool_t hdhomerun_debug_enabled(struct hdhomerun_debug_t *dbg); +extern LIBHDHOMERUN_API void hdhomerun_debug_set_prefix(struct hdhomerun_debug_t *dbg, const char *prefix); +extern LIBHDHOMERUN_API void hdhomerun_debug_set_filename(struct hdhomerun_debug_t *dbg, const char *filename); +extern LIBHDHOMERUN_API void hdhomerun_debug_enable(struct hdhomerun_debug_t *dbg); +extern LIBHDHOMERUN_API void hdhomerun_debug_disable(struct hdhomerun_debug_t *dbg); +extern LIBHDHOMERUN_API bool hdhomerun_debug_enabled(struct hdhomerun_debug_t *dbg); -extern LIBTYPE void hdhomerun_debug_flush(struct hdhomerun_debug_t *dbg, uint64_t timeout); -extern LIBTYPE void hdhomerun_debug_close(struct hdhomerun_debug_t *dbg, uint64_t timeout); +extern LIBHDHOMERUN_API void hdhomerun_debug_flush(struct hdhomerun_debug_t *dbg, uint64_t timeout); +extern LIBHDHOMERUN_API void hdhomerun_debug_close(struct hdhomerun_debug_t *dbg, uint64_t timeout); -extern LIBTYPE void hdhomerun_debug_printf(struct hdhomerun_debug_t *dbg, const char *fmt, ...); -extern LIBTYPE void hdhomerun_debug_vprintf(struct hdhomerun_debug_t *dbg, const char *fmt, va_list args); +extern LIBHDHOMERUN_API void hdhomerun_debug_printf(struct hdhomerun_debug_t *dbg, const char *fmt, ...); +extern LIBHDHOMERUN_API void hdhomerun_debug_vprintf(struct hdhomerun_debug_t *dbg, const char *fmt, va_list args); #ifdef __cplusplus }
View file
libhdhomerun_20150826.tgz/hdhomerun_device.c -> libhdhomerun_20190621.tgz/hdhomerun_device.c
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_device.c * - * Copyright © 2006-2010 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2006-2015 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -215,7 +215,7 @@ */ unsigned int port; if (sscanf(device_str, "%u.%u.%u.%u:%u", &a[0], &a[1], &a[2], &a[3], &port) == 5) { - return hdhomerun_device_create_multicast(ip_addr, port, dbg); + return hdhomerun_device_create_multicast(ip_addr, (uint16_t)port, dbg); } /* @@ -339,7 +339,7 @@ return hd->vs; } - bool_t allow_port_reuse = (hd->multicast_port != 0); + bool allow_port_reuse = (hd->multicast_port != 0); hd->vs = hdhomerun_video_create(hd->multicast_port, allow_port_reuse, VIDEO_DATA_BUFFER_SIZE_1S * 2, hd->dbg); if (!hd->vs) { @@ -372,22 +372,22 @@ return (uint32_t)value; } -static bool_t hdhomerun_device_get_tuner_status_lock_is_bcast(struct hdhomerun_tuner_status_t *status) +static bool hdhomerun_device_get_tuner_status_lock_is_bcast(struct hdhomerun_tuner_status_t *status) { if (strcmp(status->lock_str, "8vsb") == 0) { - return TRUE; + return true; } if (strncmp(status->lock_str, "t8", 2) == 0) { - return TRUE; + return true; } if (strncmp(status->lock_str, "t7", 2) == 0) { - return TRUE; + return true; } if (strncmp(status->lock_str, "t6", 2) == 0) { - return TRUE; + return true; } - return FALSE; + return false; } uint32_t hdhomerun_device_get_tuner_status_ss_color(struct hdhomerun_tuner_status_t *status) @@ -481,9 +481,9 @@ if (strcmp(status->lock_str, "none") != 0) { if (status->lock_str[0] == '(') { - status->lock_unsupported = TRUE; + status->lock_unsupported = true; } else { - status->lock_supported = TRUE; + status->lock_supported = true; } } } @@ -579,21 +579,21 @@ } if (strncmp(vstatus->auth, "not-subscribed", 14) == 0) { - vstatus->not_subscribed = TRUE; + vstatus->not_subscribed = true; } if (strncmp(vstatus->auth, "error", 5) == 0) { - vstatus->not_available = TRUE; + vstatus->not_available = true; } if (strncmp(vstatus->auth, "dialog", 6) == 0) { - vstatus->not_available = TRUE; + vstatus->not_available = true; } if (strncmp(vstatus->cci, "protected", 9) == 0) { - vstatus->copy_protected = TRUE; + vstatus->copy_protected = true; } if (strncmp(vstatus->cgms, "protected", 9) == 0) { - vstatus->copy_protected = TRUE; + vstatus->copy_protected = true; } } @@ -885,7 +885,7 @@ return hdhomerun_control_set_with_lockkey(hd->cs, name, filter, hd->lockkey, NULL, NULL); } -static bool_t hdhomerun_device_set_tuner_filter_by_array_append(char *ptr, char *end, uint16_t range_begin, uint16_t range_end) +static bool hdhomerun_device_set_tuner_filter_by_array_append(char *ptr, char *end, uint16_t range_begin, uint16_t range_end) { if (range_begin == range_end) { return hdhomerun_sprintf(ptr, end, "0x%04x ", (unsigned int)range_begin); @@ -1145,6 +1145,8 @@ return -1; } + hdhomerun_video_set_keepalive(hd->vs, 0, 0, 0); + /* Set target. */ if (hd->multicast_ip != 0) { int ret = hdhomerun_video_join_multicast_group(hd->vs, hd->multicast_ip, 0); @@ -1159,6 +1161,9 @@ if (ret <= 0) { return ret; } + + uint32_t remote_ip = hdhomerun_control_get_device_ip(hd->cs); + hdhomerun_video_set_keepalive(hd->vs, remote_ip, 5004, hd->lockkey); } /* Flush video buffer. */
View file
libhdhomerun_20150826.tgz/hdhomerun_device.h -> libhdhomerun_20190621.tgz/hdhomerun_device.h
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_device.h * - * Copyright © 2006-2008 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2006-2015 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -63,25 +63,25 @@ * <tuner index> * /tuner<tuner index> */ -extern LIBTYPE struct hdhomerun_device_t *hdhomerun_device_create(uint32_t device_id, uint32_t device_ip, unsigned int tuner, struct hdhomerun_debug_t *dbg); -extern LIBTYPE struct hdhomerun_device_t *hdhomerun_device_create_multicast(uint32_t multicast_ip, uint16_t multicast_port, struct hdhomerun_debug_t *dbg); -extern LIBTYPE struct hdhomerun_device_t *hdhomerun_device_create_from_str(const char *device_str, struct hdhomerun_debug_t *dbg); -extern LIBTYPE void hdhomerun_device_destroy(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API struct hdhomerun_device_t *hdhomerun_device_create(uint32_t device_id, uint32_t device_ip, unsigned int tuner, struct hdhomerun_debug_t *dbg); +extern LIBHDHOMERUN_API struct hdhomerun_device_t *hdhomerun_device_create_multicast(uint32_t multicast_ip, uint16_t multicast_port, struct hdhomerun_debug_t *dbg); +extern LIBHDHOMERUN_API struct hdhomerun_device_t *hdhomerun_device_create_from_str(const char *device_str, struct hdhomerun_debug_t *dbg); +extern LIBHDHOMERUN_API void hdhomerun_device_destroy(struct hdhomerun_device_t *hd); /* * Get the device id, ip, or tuner of the device instance. */ -extern LIBTYPE const char *hdhomerun_device_get_name(struct hdhomerun_device_t *hd); -extern LIBTYPE uint32_t hdhomerun_device_get_device_id(struct hdhomerun_device_t *hd); -extern LIBTYPE uint32_t hdhomerun_device_get_device_ip(struct hdhomerun_device_t *hd); -extern LIBTYPE uint32_t hdhomerun_device_get_device_id_requested(struct hdhomerun_device_t *hd); -extern LIBTYPE uint32_t hdhomerun_device_get_device_ip_requested(struct hdhomerun_device_t *hd); -extern LIBTYPE unsigned int hdhomerun_device_get_tuner(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API const char *hdhomerun_device_get_name(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API uint32_t hdhomerun_device_get_device_id(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API uint32_t hdhomerun_device_get_device_ip(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API uint32_t hdhomerun_device_get_device_id_requested(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API uint32_t hdhomerun_device_get_device_ip_requested(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API unsigned int hdhomerun_device_get_tuner(struct hdhomerun_device_t *hd); -extern LIBTYPE int hdhomerun_device_set_device(struct hdhomerun_device_t *hd, uint32_t device_id, uint32_t device_ip); -extern LIBTYPE int hdhomerun_device_set_multicast(struct hdhomerun_device_t *hd, uint32_t multicast_ip, uint16_t multicast_port); -extern LIBTYPE int hdhomerun_device_set_tuner(struct hdhomerun_device_t *hd, unsigned int tuner); -extern LIBTYPE int hdhomerun_device_set_tuner_from_str(struct hdhomerun_device_t *hd, const char *tuner_str); +extern LIBHDHOMERUN_API int hdhomerun_device_set_device(struct hdhomerun_device_t *hd, uint32_t device_id, uint32_t device_ip); +extern LIBHDHOMERUN_API int hdhomerun_device_set_multicast(struct hdhomerun_device_t *hd, uint32_t multicast_ip, uint16_t multicast_port); +extern LIBHDHOMERUN_API int hdhomerun_device_set_tuner(struct hdhomerun_device_t *hd, unsigned int tuner); +extern LIBHDHOMERUN_API int hdhomerun_device_set_tuner_from_str(struct hdhomerun_device_t *hd, const char *tuner_str); /* * Get the local machine IP address used when communicating with the device. @@ -90,7 +90,7 @@ * * Returns 32-bit IP address with native endianness, or 0 on error. */ -extern LIBTYPE uint32_t hdhomerun_device_get_local_machine_addr(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API uint32_t hdhomerun_device_get_local_machine_addr(struct hdhomerun_device_t *hd); /* * Get operations. @@ -103,29 +103,29 @@ * Returns 0 if the operation was rejected. * Returns -1 if a communication error occurred. */ -extern LIBTYPE int hdhomerun_device_get_tuner_status(struct hdhomerun_device_t *hd, char **pstatus_str, struct hdhomerun_tuner_status_t *status); -extern LIBTYPE int hdhomerun_device_get_tuner_vstatus(struct hdhomerun_device_t *hd, char **pvstatus_str, struct hdhomerun_tuner_vstatus_t *vstatus); -extern LIBTYPE int hdhomerun_device_get_tuner_streaminfo(struct hdhomerun_device_t *hd, char **pstreaminfo); -extern LIBTYPE int hdhomerun_device_get_tuner_channel(struct hdhomerun_device_t *hd, char **pchannel); -extern LIBTYPE int hdhomerun_device_get_tuner_vchannel(struct hdhomerun_device_t *hd, char **pvchannel); -extern LIBTYPE int hdhomerun_device_get_tuner_channelmap(struct hdhomerun_device_t *hd, char **pchannelmap); -extern LIBTYPE int hdhomerun_device_get_tuner_filter(struct hdhomerun_device_t *hd, char **pfilter); -extern LIBTYPE int hdhomerun_device_get_tuner_program(struct hdhomerun_device_t *hd, char **pprogram); -extern LIBTYPE int hdhomerun_device_get_tuner_target(struct hdhomerun_device_t *hd, char **ptarget); -extern LIBTYPE int hdhomerun_device_get_tuner_plotsample(struct hdhomerun_device_t *hd, struct hdhomerun_plotsample_t **psamples, size_t *pcount); -extern LIBTYPE int hdhomerun_device_get_tuner_lockkey_owner(struct hdhomerun_device_t *hd, char **powner); -extern LIBTYPE int hdhomerun_device_get_oob_status(struct hdhomerun_device_t *hd, char **pstatus_str, struct hdhomerun_tuner_status_t *status); -extern LIBTYPE int hdhomerun_device_get_oob_plotsample(struct hdhomerun_device_t *hd, struct hdhomerun_plotsample_t **psamples, size_t *pcount); -extern LIBTYPE int hdhomerun_device_get_ir_target(struct hdhomerun_device_t *hd, char **ptarget); -extern LIBTYPE int hdhomerun_device_get_version(struct hdhomerun_device_t *hd, char **pversion_str, uint32_t *pversion_num); -extern LIBTYPE int hdhomerun_device_get_supported(struct hdhomerun_device_t *hd, char *prefix, char **pstr); +extern LIBHDHOMERUN_API int hdhomerun_device_get_tuner_status(struct hdhomerun_device_t *hd, char **pstatus_str, struct hdhomerun_tuner_status_t *status); +extern LIBHDHOMERUN_API int hdhomerun_device_get_tuner_vstatus(struct hdhomerun_device_t *hd, char **pvstatus_str, struct hdhomerun_tuner_vstatus_t *vstatus); +extern LIBHDHOMERUN_API int hdhomerun_device_get_tuner_streaminfo(struct hdhomerun_device_t *hd, char **pstreaminfo); +extern LIBHDHOMERUN_API int hdhomerun_device_get_tuner_channel(struct hdhomerun_device_t *hd, char **pchannel); +extern LIBHDHOMERUN_API int hdhomerun_device_get_tuner_vchannel(struct hdhomerun_device_t *hd, char **pvchannel); +extern LIBHDHOMERUN_API int hdhomerun_device_get_tuner_channelmap(struct hdhomerun_device_t *hd, char **pchannelmap); +extern LIBHDHOMERUN_API int hdhomerun_device_get_tuner_filter(struct hdhomerun_device_t *hd, char **pfilter); +extern LIBHDHOMERUN_API int hdhomerun_device_get_tuner_program(struct hdhomerun_device_t *hd, char **pprogram); +extern LIBHDHOMERUN_API int hdhomerun_device_get_tuner_target(struct hdhomerun_device_t *hd, char **ptarget); +extern LIBHDHOMERUN_API int hdhomerun_device_get_tuner_plotsample(struct hdhomerun_device_t *hd, struct hdhomerun_plotsample_t **psamples, size_t *pcount); +extern LIBHDHOMERUN_API int hdhomerun_device_get_tuner_lockkey_owner(struct hdhomerun_device_t *hd, char **powner); +extern LIBHDHOMERUN_API int hdhomerun_device_get_oob_status(struct hdhomerun_device_t *hd, char **pstatus_str, struct hdhomerun_tuner_status_t *status); +extern LIBHDHOMERUN_API int hdhomerun_device_get_oob_plotsample(struct hdhomerun_device_t *hd, struct hdhomerun_plotsample_t **psamples, size_t *pcount); +extern LIBHDHOMERUN_API int hdhomerun_device_get_ir_target(struct hdhomerun_device_t *hd, char **ptarget); +extern LIBHDHOMERUN_API int hdhomerun_device_get_version(struct hdhomerun_device_t *hd, char **pversion_str, uint32_t *pversion_num); +extern LIBHDHOMERUN_API int hdhomerun_device_get_supported(struct hdhomerun_device_t *hd, char *prefix, char **pstr); -extern LIBTYPE uint32_t hdhomerun_device_get_tuner_status_ss_color(struct hdhomerun_tuner_status_t *status); -extern LIBTYPE uint32_t hdhomerun_device_get_tuner_status_snq_color(struct hdhomerun_tuner_status_t *status); -extern LIBTYPE uint32_t hdhomerun_device_get_tuner_status_seq_color(struct hdhomerun_tuner_status_t *status); +extern LIBHDHOMERUN_API uint32_t hdhomerun_device_get_tuner_status_ss_color(struct hdhomerun_tuner_status_t *status); +extern LIBHDHOMERUN_API uint32_t hdhomerun_device_get_tuner_status_snq_color(struct hdhomerun_tuner_status_t *status); +extern LIBHDHOMERUN_API uint32_t hdhomerun_device_get_tuner_status_seq_color(struct hdhomerun_tuner_status_t *status); -extern LIBTYPE const char *hdhomerun_device_get_hw_model_str(struct hdhomerun_device_t *hd); -extern LIBTYPE const char *hdhomerun_device_get_model_str(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API const char *hdhomerun_device_get_hw_model_str(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API const char *hdhomerun_device_get_model_str(struct hdhomerun_device_t *hd); /* * Set operations. @@ -136,15 +136,15 @@ * Returns 0 if the operation was rejected. * Returns -1 if a communication error occurred. */ -extern LIBTYPE int hdhomerun_device_set_tuner_channel(struct hdhomerun_device_t *hd, const char *channel); -extern LIBTYPE int hdhomerun_device_set_tuner_vchannel(struct hdhomerun_device_t *hd, const char *vchannel); -extern LIBTYPE int hdhomerun_device_set_tuner_channelmap(struct hdhomerun_device_t *hd, const char *channelmap); -extern LIBTYPE int hdhomerun_device_set_tuner_filter(struct hdhomerun_device_t *hd, const char *filter); -extern LIBTYPE int hdhomerun_device_set_tuner_filter_by_array(struct hdhomerun_device_t *hd, unsigned char filter_array[0x2000]); -extern LIBTYPE int hdhomerun_device_set_tuner_program(struct hdhomerun_device_t *hd, const char *program); -extern LIBTYPE int hdhomerun_device_set_tuner_target(struct hdhomerun_device_t *hd, const char *target); -extern LIBTYPE int hdhomerun_device_set_ir_target(struct hdhomerun_device_t *hd, const char *target); -extern LIBTYPE int hdhomerun_device_set_sys_dvbc_modulation(struct hdhomerun_device_t *hd, const char *modulation_list); +extern LIBHDHOMERUN_API int hdhomerun_device_set_tuner_channel(struct hdhomerun_device_t *hd, const char *channel); +extern LIBHDHOMERUN_API int hdhomerun_device_set_tuner_vchannel(struct hdhomerun_device_t *hd, const char *vchannel); +extern LIBHDHOMERUN_API int hdhomerun_device_set_tuner_channelmap(struct hdhomerun_device_t *hd, const char *channelmap); +extern LIBHDHOMERUN_API int hdhomerun_device_set_tuner_filter(struct hdhomerun_device_t *hd, const char *filter); +extern LIBHDHOMERUN_API int hdhomerun_device_set_tuner_filter_by_array(struct hdhomerun_device_t *hd, unsigned char filter_array[0x2000]); +extern LIBHDHOMERUN_API int hdhomerun_device_set_tuner_program(struct hdhomerun_device_t *hd, const char *program); +extern LIBHDHOMERUN_API int hdhomerun_device_set_tuner_target(struct hdhomerun_device_t *hd, const char *target); +extern LIBHDHOMERUN_API int hdhomerun_device_set_ir_target(struct hdhomerun_device_t *hd, const char *target); +extern LIBHDHOMERUN_API int hdhomerun_device_set_sys_dvbc_modulation(struct hdhomerun_device_t *hd, const char *modulation_list); /* * Get/set a named control variable on the device. @@ -163,8 +163,8 @@ * Returns 0 if the operation was rejected (pvalue NULL, perror set). * Returns -1 if a communication error occurs. */ -extern LIBTYPE int hdhomerun_device_get_var(struct hdhomerun_device_t *hd, const char *name, char **pvalue, char **perror); -extern LIBTYPE int hdhomerun_device_set_var(struct hdhomerun_device_t *hd, const char *name, const char *value, char **pvalue, char **perror); +extern LIBHDHOMERUN_API int hdhomerun_device_get_var(struct hdhomerun_device_t *hd, const char *name, char **pvalue, char **perror); +extern LIBHDHOMERUN_API int hdhomerun_device_set_var(struct hdhomerun_device_t *hd, const char *name, const char *value, char **pvalue, char **perror); /* * Tuner locking. @@ -179,14 +179,14 @@ * previously held lock. If locking is used then this function must be called * before destroying the hdhomerun_device object. */ -extern LIBTYPE int hdhomerun_device_tuner_lockkey_request(struct hdhomerun_device_t *hd, char **perror); -extern LIBTYPE int hdhomerun_device_tuner_lockkey_release(struct hdhomerun_device_t *hd); -extern LIBTYPE int hdhomerun_device_tuner_lockkey_force(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API int hdhomerun_device_tuner_lockkey_request(struct hdhomerun_device_t *hd, char **perror); +extern LIBHDHOMERUN_API int hdhomerun_device_tuner_lockkey_release(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API int hdhomerun_device_tuner_lockkey_force(struct hdhomerun_device_t *hd); /* * Intended only for non persistent connections; eg, hdhomerun_config. */ -extern LIBTYPE void hdhomerun_device_tuner_lockkey_use_value(struct hdhomerun_device_t *hd, uint32_t lockkey); +extern LIBHDHOMERUN_API void hdhomerun_device_tuner_lockkey_use_value(struct hdhomerun_device_t *hd, uint32_t lockkey); /* * Wait for tuner lock after channel change. @@ -198,7 +198,7 @@ * It will return quickly if there is no signal detected. * Worst case it will time out after 1.5 seconds - the case where there is signal but no lock. */ -extern LIBTYPE int hdhomerun_device_wait_for_lock(struct hdhomerun_device_t *hd, struct hdhomerun_tuner_status_t *status); +extern LIBHDHOMERUN_API int hdhomerun_device_wait_for_lock(struct hdhomerun_device_t *hd, struct hdhomerun_tuner_status_t *status); /* * Stream a filtered program or the unfiltered stream. @@ -216,18 +216,18 @@ * * The hdhomerun_device_stream_stop function tells the device to stop streaming data. */ -extern LIBTYPE int hdhomerun_device_stream_start(struct hdhomerun_device_t *hd); -extern LIBTYPE uint8_t *hdhomerun_device_stream_recv(struct hdhomerun_device_t *hd, size_t max_size, size_t *pactual_size); -extern LIBTYPE void hdhomerun_device_stream_flush(struct hdhomerun_device_t *hd); -extern LIBTYPE void hdhomerun_device_stream_stop(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API int hdhomerun_device_stream_start(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API uint8_t *hdhomerun_device_stream_recv(struct hdhomerun_device_t *hd, size_t max_size, size_t *pactual_size); +extern LIBHDHOMERUN_API void hdhomerun_device_stream_flush(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API void hdhomerun_device_stream_stop(struct hdhomerun_device_t *hd); /* * Channel scan API. */ -extern LIBTYPE int hdhomerun_device_channelscan_init(struct hdhomerun_device_t *hd, const char *channelmap); -extern LIBTYPE int hdhomerun_device_channelscan_advance(struct hdhomerun_device_t *hd, struct hdhomerun_channelscan_result_t *result); -extern LIBTYPE int hdhomerun_device_channelscan_detect(struct hdhomerun_device_t *hd, struct hdhomerun_channelscan_result_t *result); -extern LIBTYPE uint8_t hdhomerun_device_channelscan_get_progress(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API int hdhomerun_device_channelscan_init(struct hdhomerun_device_t *hd, const char *channelmap); +extern LIBHDHOMERUN_API int hdhomerun_device_channelscan_advance(struct hdhomerun_device_t *hd, struct hdhomerun_channelscan_result_t *result); +extern LIBHDHOMERUN_API int hdhomerun_device_channelscan_detect(struct hdhomerun_device_t *hd, struct hdhomerun_channelscan_result_t *result); +extern LIBHDHOMERUN_API uint8_t hdhomerun_device_channelscan_get_progress(struct hdhomerun_device_t *hd); /* * Upload new firmware to the device. @@ -238,19 +238,19 @@ * Returns 0 if the upload was rejected. * Returns -1 if an error occurs. */ -extern LIBTYPE int hdhomerun_device_upgrade(struct hdhomerun_device_t *hd, FILE *upgrade_file); +extern LIBHDHOMERUN_API int hdhomerun_device_upgrade(struct hdhomerun_device_t *hd, FILE *upgrade_file); /* * Low level accessor functions. */ -extern LIBTYPE struct hdhomerun_control_sock_t *hdhomerun_device_get_control_sock(struct hdhomerun_device_t *hd); -extern LIBTYPE struct hdhomerun_video_sock_t *hdhomerun_device_get_video_sock(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API struct hdhomerun_control_sock_t *hdhomerun_device_get_control_sock(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API struct hdhomerun_video_sock_t *hdhomerun_device_get_video_sock(struct hdhomerun_device_t *hd); /* * Debug print internal stats. */ -extern LIBTYPE void hdhomerun_device_debug_print_video_stats(struct hdhomerun_device_t *hd); -extern LIBTYPE void hdhomerun_device_get_video_stats(struct hdhomerun_device_t *hd, struct hdhomerun_video_stats_t *stats); +extern LIBHDHOMERUN_API void hdhomerun_device_debug_print_video_stats(struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API void hdhomerun_device_get_video_stats(struct hdhomerun_device_t *hd, struct hdhomerun_video_stats_t *stats); #ifdef __cplusplus }
View file
libhdhomerun_20150826.tgz/hdhomerun_device_selector.c -> libhdhomerun_20190621.tgz/hdhomerun_device_selector.c
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_device_selector.c * - * Copyright © 2009-2010 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2009-2016 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -39,7 +39,7 @@ return hds; } -void hdhomerun_device_selector_destroy(struct hdhomerun_device_selector_t *hds, bool_t destroy_devices) +void hdhomerun_device_selector_destroy(struct hdhomerun_device_selector_t *hds, bool destroy_devices) { if (destroy_devices) { size_t index; @@ -56,7 +56,7 @@ free(hds); } -LIBTYPE int hdhomerun_device_selector_get_device_count(struct hdhomerun_device_selector_t *hds) +int hdhomerun_device_selector_get_device_count(struct hdhomerun_device_selector_t *hds) { return (int)hds->hd_count; } @@ -71,12 +71,13 @@ } } - hds->hd_list = (struct hdhomerun_device_t **)realloc(hds->hd_list, (hds->hd_count + 1) * sizeof(struct hdhomerun_device_selector_t *)); - if (!hds->hd_list) { + struct hdhomerun_device_t **hd_list = (struct hdhomerun_device_t **)realloc(hds->hd_list, (hds->hd_count + 1) * sizeof(struct hdhomerun_device_t *)); + if (!hd_list) { hdhomerun_debug_printf(hds->dbg, "hdhomerun_device_selector_add_device: failed to allocate device list\n"); return; } + hds->hd_list = hd_list; hds->hd_list[hds->hd_count++] = hd; } @@ -124,25 +125,22 @@ static int hdhomerun_device_selector_load_from_str_discover(struct hdhomerun_device_selector_t *hds, uint32_t target_ip, uint32_t device_id) { - struct hdhomerun_discover_device_t result_list[64]; - int discover_count = hdhomerun_discover_find_devices_custom_v2(target_ip, HDHOMERUN_DEVICE_TYPE_TUNER, device_id, result_list, 64); + struct hdhomerun_discover_device_t result; + int discover_count = hdhomerun_discover_find_devices_custom_v2(target_ip, HDHOMERUN_DEVICE_TYPE_TUNER, device_id, &result, 1); + if (discover_count != 1) { + return 0; + } int count = 0; - int result_index; - struct hdhomerun_discover_device_t *result = result_list; - for (result_index = 0; result_index < discover_count; result_index++) { - unsigned int tuner_index; - for (tuner_index = 0; tuner_index < result->tuner_count; tuner_index++) { - struct hdhomerun_device_t *hd = hdhomerun_device_create(result->device_id, result->ip_addr, tuner_index, hds->dbg); - if (!hd) { - continue; - } - - hdhomerun_device_selector_add_device(hds, hd); - count++; + unsigned int tuner_index; + for (tuner_index = 0; tuner_index < result.tuner_count; tuner_index++) { + struct hdhomerun_device_t *hd = hdhomerun_device_create(result.device_id, result.ip_addr, tuner_index, hds->dbg); + if (!hd) { + continue; } - result++; + hdhomerun_device_selector_add_device(hds, hd); + count++; } return count; @@ -162,7 +160,7 @@ */ unsigned int port; if (sscanf(device_str, "%u.%u.%u.%u:%u", &a[0], &a[1], &a[2], &a[3], &port) == 5) { - struct hdhomerun_device_t *hd = hdhomerun_device_create_multicast(ip_addr, port, hds->dbg); + struct hdhomerun_device_t *hd = hdhomerun_device_create_multicast(ip_addr, (uint16_t)port, hds->dbg); if (!hd) { return 0; } @@ -263,7 +261,7 @@ return count; } -#if defined(__WINDOWS__) +#if defined(_WIN32) && !defined(_WINRT) int hdhomerun_device_selector_load_from_windows_registry(struct hdhomerun_device_selector_t *hds, wchar_t *wsource) { HKEY tuners_key; @@ -315,22 +313,22 @@ } #endif -static bool_t hdhomerun_device_selector_choose_test(struct hdhomerun_device_selector_t *hds, struct hdhomerun_device_t *test_hd) +static bool hdhomerun_device_selector_choose_test(struct hdhomerun_device_selector_t *hds, struct hdhomerun_device_t *test_hd) { const char *name = hdhomerun_device_get_name(test_hd); /* * Attempt to aquire lock. */ - char *error; + char *error = NULL; int ret = hdhomerun_device_tuner_lockkey_request(test_hd, &error); if (ret > 0) { hdhomerun_debug_printf(hds->dbg, "hdhomerun_device_selector_choose_test: device %s chosen\n", name); - return TRUE; + return true; } if (ret < 0) { hdhomerun_debug_printf(hds->dbg, "hdhomerun_device_selector_choose_test: device %s communication error\n", name); - return FALSE; + return false; } /* @@ -340,52 +338,52 @@ ret = hdhomerun_device_get_tuner_target(test_hd, &target); if (ret < 0) { hdhomerun_debug_printf(hds->dbg, "hdhomerun_device_selector_choose_test: device %s communication error\n", name); - return FALSE; + return false; } if (ret == 0) { hdhomerun_debug_printf(hds->dbg, "hdhomerun_device_selector_choose_test: device %s in use, failed to read target\n", name); - return FALSE; + return false; } if (strcmp(target, "none") == 0) { hdhomerun_debug_printf(hds->dbg, "hdhomerun_device_selector_choose_test: device %s in use, no target set\n", name); - return FALSE; + return false; } if ((strncmp(target, "udp://", 6) != 0) && (strncmp(target, "rtp://", 6) != 0)) { hdhomerun_debug_printf(hds->dbg, "hdhomerun_device_selector_choose_test: device %s in use by %s\n", name, target); - return FALSE; + return false; } unsigned int a[4]; unsigned int target_port; if (sscanf(target + 6, "%u.%u.%u.%u:%u", &a[0], &a[1], &a[2], &a[3], &target_port) != 5) { hdhomerun_debug_printf(hds->dbg, "hdhomerun_device_selector_choose_test: device %s in use, unexpected target set (%s)\n", name, target); - return FALSE; + return false; } uint32_t target_ip = (uint32_t)((a[0] << 24) | (a[1] << 16) | (a[2] << 8) | (a[3] << 0)); uint32_t local_ip = hdhomerun_device_get_local_machine_addr(test_hd); if (target_ip != local_ip) { hdhomerun_debug_printf(hds->dbg, "hdhomerun_device_selector_choose_test: device %s in use by %s\n", name, target); - return FALSE; + return false; } /* * Test local port. */ - hdhomerun_sock_t test_sock = hdhomerun_sock_create_udp(); - if (test_sock == HDHOMERUN_SOCK_INVALID) { + struct hdhomerun_sock_t *test_sock = hdhomerun_sock_create_udp(); + if (!test_sock) { hdhomerun_debug_printf(hds->dbg, "hdhomerun_device_selector_choose_test: device %s in use, failed to create test sock\n", name); - return FALSE; + return false; } - bool_t inuse = (hdhomerun_sock_bind(test_sock, INADDR_ANY, (uint16_t)target_port, FALSE) == FALSE); + bool inuse = (hdhomerun_sock_bind(test_sock, INADDR_ANY, (uint16_t)target_port, false) == false); hdhomerun_sock_destroy(test_sock); if (inuse) { hdhomerun_debug_printf(hds->dbg, "hdhomerun_device_selector_choose_test: device %s in use by local machine\n", name); - return FALSE; + return false; } /* @@ -394,11 +392,11 @@ ret = hdhomerun_device_tuner_lockkey_force(test_hd); if (ret < 0) { hdhomerun_debug_printf(hds->dbg, "hdhomerun_device_selector_choose_test: device %s communication error\n", name); - return FALSE; + return false; } if (ret == 0) { hdhomerun_debug_printf(hds->dbg, "hdhomerun_device_selector_choose_test: device %s in use by local machine, dead target, failed to force release lockkey\n", name); - return FALSE; + return false; } hdhomerun_debug_printf(hds->dbg, "hdhomerun_device_selector_choose_test: device %s in use by local machine, dead target, lockkey force successful\n", name); @@ -409,15 +407,15 @@ ret = hdhomerun_device_tuner_lockkey_request(test_hd, &error); if (ret > 0) { hdhomerun_debug_printf(hds->dbg, "hdhomerun_device_selector_choose_test: device %s chosen\n", name); - return TRUE; + return true; } if (ret < 0) { hdhomerun_debug_printf(hds->dbg, "hdhomerun_device_selector_choose_test: device %s communication error\n", name); - return FALSE; + return false; } hdhomerun_debug_printf(hds->dbg, "hdhomerun_device_selector_choose_test: device %s still in use after lockkey force (%s)\n", name, error); - return FALSE; + return false; } struct hdhomerun_device_t *hdhomerun_device_selector_choose_and_lock(struct hdhomerun_device_selector_t *hds, struct hdhomerun_device_t *prefered)
View file
libhdhomerun_20150826.tgz/hdhomerun_device_selector.h -> libhdhomerun_20190621.tgz/hdhomerun_device_selector.h
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_device_selector.h * - * Copyright © 2009 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2009-2015 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -27,34 +27,35 @@ * All tuners registered with a specific device selector instance must have the same signal source. * The dbg parameter may be null. */ -extern LIBTYPE struct hdhomerun_device_selector_t *hdhomerun_device_selector_create(struct hdhomerun_debug_t *dbg); -extern LIBTYPE void hdhomerun_device_selector_destroy(struct hdhomerun_device_selector_t *hds, bool_t destroy_devices); +extern LIBHDHOMERUN_API struct hdhomerun_device_selector_t *hdhomerun_device_selector_create(struct hdhomerun_debug_t *dbg); +extern LIBHDHOMERUN_API void hdhomerun_device_selector_destroy(struct hdhomerun_device_selector_t *hds, bool destroy_devices); /* * Get the number of devices in the list. */ -extern LIBTYPE int hdhomerun_device_selector_get_device_count(struct hdhomerun_device_selector_t *hds); +extern LIBHDHOMERUN_API int hdhomerun_device_selector_get_device_count(struct hdhomerun_device_selector_t *hds); /* * Populate device selector with devices from given source. * Returns the number of devices populated. */ -extern LIBTYPE int hdhomerun_device_selector_load_from_str(struct hdhomerun_device_selector_t *hds, char *device_str); -extern LIBTYPE int hdhomerun_device_selector_load_from_file(struct hdhomerun_device_selector_t *hds, char *filename); -#if defined(__WINDOWS__) -extern LIBTYPE int hdhomerun_device_selector_load_from_windows_registry(struct hdhomerun_device_selector_t *hds, wchar_t *wsource); +extern LIBHDHOMERUN_API int hdhomerun_device_selector_load_from_str(struct hdhomerun_device_selector_t *hds, char *device_str); +extern LIBHDHOMERUN_API int hdhomerun_device_selector_load_from_file(struct hdhomerun_device_selector_t *hds, char *filename); + +#if defined(_WIN32) && !defined(_WINRT) +extern LIBHDHOMERUN_API int hdhomerun_device_selector_load_from_windows_registry(struct hdhomerun_device_selector_t *hds, wchar_t *wsource); #endif /* * Add/remove a device from the selector list. */ -extern LIBTYPE void hdhomerun_device_selector_add_device(struct hdhomerun_device_selector_t *hds, struct hdhomerun_device_t *hd); -extern LIBTYPE void hdhomerun_device_selector_remove_device(struct hdhomerun_device_selector_t *hds, struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API void hdhomerun_device_selector_add_device(struct hdhomerun_device_selector_t *hds, struct hdhomerun_device_t *hd); +extern LIBHDHOMERUN_API void hdhomerun_device_selector_remove_device(struct hdhomerun_device_selector_t *hds, struct hdhomerun_device_t *hd); /* * Find a device in the selector list. */ -extern LIBTYPE struct hdhomerun_device_t *hdhomerun_device_selector_find_device(struct hdhomerun_device_selector_t *hds, uint32_t device_id, unsigned int tuner_index); +extern LIBHDHOMERUN_API struct hdhomerun_device_t *hdhomerun_device_selector_find_device(struct hdhomerun_device_selector_t *hds, uint32_t device_id, unsigned int tuner_index); /* * Select and lock an available device. @@ -79,7 +80,7 @@ * to refresh the lock. If this function succeeds then the same device can be used. If this fucntion fails * then call hdhomerun_device_selector_choose_and_lock() to choose and lock an available tuner. */ -extern LIBTYPE struct hdhomerun_device_t *hdhomerun_device_selector_choose_and_lock(struct hdhomerun_device_selector_t *hds, struct hdhomerun_device_t *prefered); +extern LIBHDHOMERUN_API struct hdhomerun_device_t *hdhomerun_device_selector_choose_and_lock(struct hdhomerun_device_selector_t *hds, struct hdhomerun_device_t *prefered); #ifdef __cplusplus }
View file
libhdhomerun_20150826.tgz/hdhomerun_discover.c -> libhdhomerun_20190621.tgz/hdhomerun_discover.c
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_discover.c * - * Copyright © 2006-2015 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2006-2017 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -20,60 +20,61 @@ #include "hdhomerun.h" -#define HDHOMERUN_DISOCVER_MAX_SOCK_COUNT 16 +#define HDHOMERUN_DISCOVER_MAX_SOCK_COUNT 16 struct hdhomerun_discover_sock_t { - hdhomerun_sock_t sock; - bool_t detected; + struct hdhomerun_sock_t *sock; + bool detected; uint32_t local_ip; uint32_t subnet_mask; }; struct hdhomerun_discover_t { - struct hdhomerun_discover_sock_t socks[HDHOMERUN_DISOCVER_MAX_SOCK_COUNT]; + struct hdhomerun_discover_sock_t socks[HDHOMERUN_DISCOVER_MAX_SOCK_COUNT]; unsigned int sock_count; struct hdhomerun_pkt_t tx_pkt; struct hdhomerun_pkt_t rx_pkt; struct hdhomerun_debug_t *dbg; }; -static bool_t hdhomerun_discover_sock_add(struct hdhomerun_discover_t *ds, uint32_t local_ip, uint32_t subnet_mask) +static bool hdhomerun_discover_sock_add(struct hdhomerun_discover_t *ds, uint32_t local_ip, uint32_t subnet_mask) { unsigned int i; for (i = 1; i < ds->sock_count; i++) { struct hdhomerun_discover_sock_t *dss = &ds->socks[i]; if ((dss->local_ip == local_ip) && (dss->subnet_mask == subnet_mask)) { - dss->detected = TRUE; - return TRUE; + dss->detected = true; + return true; } } - if (ds->sock_count >= HDHOMERUN_DISOCVER_MAX_SOCK_COUNT) { - return FALSE; + if (ds->sock_count >= HDHOMERUN_DISCOVER_MAX_SOCK_COUNT) { + return false; } /* Create socket. */ - hdhomerun_sock_t sock = hdhomerun_sock_create_udp(); - if (sock == HDHOMERUN_SOCK_INVALID) { - return FALSE; + struct hdhomerun_sock_t *sock = hdhomerun_sock_create_udp(); + if (!sock) { + hdhomerun_debug_printf(ds->dbg, "discover: failed to allocate socket (%d)\n", hdhomerun_sock_getlasterror()); + return false; } /* Bind socket. */ - if (!hdhomerun_sock_bind(sock, local_ip, 0, FALSE)) { + if (!hdhomerun_sock_bind(sock, local_ip, 0, false)) { hdhomerun_debug_printf(ds->dbg, "discover: failed to bind to %u.%u.%u.%u:0\n", (unsigned int)(local_ip >> 24) & 0xFF, (unsigned int)(local_ip >> 16) & 0xFF, (unsigned int)(local_ip >> 8) & 0xFF, (unsigned int)(local_ip >> 0) & 0xFF); hdhomerun_sock_destroy(sock); - return FALSE; + return false; } /* Write sock entry. */ struct hdhomerun_discover_sock_t *dss = &ds->socks[ds->sock_count++]; dss->sock = sock; - dss->detected = TRUE; + dss->detected = true; dss->local_ip = local_ip; dss->subnet_mask = subnet_mask; - return TRUE; + return true; } struct hdhomerun_discover_t *hdhomerun_discover_create(struct hdhomerun_debug_t *dbg) @@ -111,18 +112,18 @@ unsigned int i; for (i = 1; i < ds->sock_count; i++) { struct hdhomerun_discover_sock_t *dss = &ds->socks[i]; - dss->detected = FALSE; + dss->detected = false; } - struct hdhomerun_local_ip_info_t ip_info_list[HDHOMERUN_DISOCVER_MAX_SOCK_COUNT]; - int count = hdhomerun_local_ip_info(ip_info_list, HDHOMERUN_DISOCVER_MAX_SOCK_COUNT); + struct hdhomerun_local_ip_info_t ip_info_list[HDHOMERUN_DISCOVER_MAX_SOCK_COUNT]; + int count = hdhomerun_local_ip_info(ip_info_list, HDHOMERUN_DISCOVER_MAX_SOCK_COUNT); if (count < 0) { hdhomerun_debug_printf(ds->dbg, "discover: hdhomerun_local_ip_info returned error\n"); count = 0; } - if (count > HDHOMERUN_DISOCVER_MAX_SOCK_COUNT) { + if (count > HDHOMERUN_DISCOVER_MAX_SOCK_COUNT) { hdhomerun_debug_printf(ds->dbg, "discover: too many local IP addresses\n"); - count = HDHOMERUN_DISOCVER_MAX_SOCK_COUNT; + count = HDHOMERUN_DISCOVER_MAX_SOCK_COUNT; } int index; @@ -148,10 +149,10 @@ count++; } - ds->sock_count = count; + ds->sock_count = (unsigned int)count; } -static bool_t hdhomerun_discover_send_internal(struct hdhomerun_discover_t *ds, struct hdhomerun_discover_sock_t *dss, uint32_t target_ip, uint32_t device_type, uint32_t device_id) +static bool hdhomerun_discover_send_internal(struct hdhomerun_discover_t *ds, struct hdhomerun_discover_sock_t *dss, uint32_t target_ip, uint32_t device_type, uint32_t device_id) { struct hdhomerun_pkt_t *tx_pkt = &ds->tx_pkt; hdhomerun_pkt_reset(tx_pkt); @@ -167,35 +168,13 @@ return hdhomerun_sock_sendto(dss->sock, target_ip, HDHOMERUN_DISCOVER_UDP_PORT, tx_pkt->start, tx_pkt->end - tx_pkt->start, 0); } -static bool_t hdhomerun_discover_send_wildcard_ip(struct hdhomerun_discover_t *ds, uint32_t device_type, uint32_t device_id) +static bool hdhomerun_discover_send(struct hdhomerun_discover_t *ds, uint32_t target_ip, uint32_t device_type, uint32_t device_id) { - bool_t result = FALSE; - - /* - * Send subnet broadcast using each local ip socket. - * This will work with multiple separate 169.254.x.x interfaces. - */ - unsigned int i; - for (i = 1; i < ds->sock_count; i++) { - struct hdhomerun_discover_sock_t *dss = &ds->socks[i]; - uint32_t target_ip = dss->local_ip | ~dss->subnet_mask; - result |= hdhomerun_discover_send_internal(ds, dss, target_ip, device_type, device_id); - } - - /* - * If no local ip sockets then fall back to sending a global broadcast letting the OS choose the interface. - */ - if (!result) { - struct hdhomerun_discover_sock_t *dss = &ds->socks[0]; - result = hdhomerun_discover_send_internal(ds, dss, 0xFFFFFFFF, device_type, device_id); + if (target_ip == 0x00000000) { + target_ip = 0xFFFFFFFF; } - return result; -} - -static bool_t hdhomerun_discover_send_target_ip(struct hdhomerun_discover_t *ds, uint32_t target_ip, uint32_t device_type, uint32_t device_id) -{ - bool_t result = FALSE; + bool result = false; /* * Send targeted packet from any local ip that is in the same subnet. @@ -204,8 +183,14 @@ unsigned int i; for (i = 1; i < ds->sock_count; i++) { struct hdhomerun_discover_sock_t *dss = &ds->socks[i]; - if ((target_ip & dss->subnet_mask) != (dss->local_ip & dss->subnet_mask)) { - continue; + + if (target_ip != 0xFFFFFFFF) { + if (dss->subnet_mask == 0) { + continue; + } + if ((target_ip & dss->subnet_mask) != (dss->local_ip & dss->subnet_mask)) { + continue; + } } result |= hdhomerun_discover_send_internal(ds, dss, target_ip, device_type, device_id); @@ -222,16 +207,7 @@ return result; } -static bool_t hdhomerun_discover_send(struct hdhomerun_discover_t *ds, uint32_t target_ip, uint32_t device_type, uint32_t device_id) -{ - if (target_ip == 0) { - return hdhomerun_discover_send_wildcard_ip(ds, device_type, device_id); - } else { - return hdhomerun_discover_send_target_ip(ds, target_ip, device_type, device_id); - } -} - -static bool_t hdhomerun_discover_is_legacy(uint32_t device_id) +static bool hdhomerun_discover_is_legacy(uint32_t device_id) { switch (device_id >> 20) { case 0x100: /* TECH-US/TECH3-US */ @@ -246,14 +222,14 @@ case 0x111: /* HDHR3-DT */ case 0x121: /* HDHR-EU */ case 0x122: /* HDHR3-EU */ - return TRUE; + return true; default: - return FALSE; + return false; } } -static bool_t hdhomerun_discover_recv_internal(struct hdhomerun_discover_t *ds, struct hdhomerun_discover_sock_t *dss, struct hdhomerun_discover_device_t *result) +static bool hdhomerun_discover_recv_internal(struct hdhomerun_discover_t *ds, struct hdhomerun_discover_sock_t *dss, size_t result_struct_size, struct hdhomerun_discover_device_t *result) { static char hdhomerun_discover_recv_base64_encode_table[64 + 1] = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"; struct hdhomerun_pkt_t *rx_pkt = &ds->rx_pkt; @@ -263,26 +239,23 @@ uint16_t remote_port; size_t length = rx_pkt->limit - rx_pkt->end; if (!hdhomerun_sock_recvfrom(dss->sock, &remote_addr, &remote_port, rx_pkt->end, &length, 0)) { - return FALSE; + return false; } rx_pkt->end += length; uint16_t type; if (hdhomerun_pkt_open_frame(rx_pkt, &type) <= 0) { - return FALSE; + return false; } if (type != HDHOMERUN_TYPE_DISCOVER_RPY) { - return FALSE; + return false; } - memset(result, 0, sizeof(struct hdhomerun_discover_device_t)); + struct hdhomerun_discover_device_v3_t *result_v3 = (result_struct_size >= sizeof(struct hdhomerun_discover_device_v3_t)) ? (struct hdhomerun_discover_device_v3_t *)(void *)result : NULL; + memset(result, 0, result_struct_size); result->ip_addr = remote_addr; - hdhomerun_sprintf(result->base_url, result->base_url + sizeof(result->base_url), "http://%u.%u.%u.%u:80", - (remote_addr >> 24) & 0xFF, (remote_addr >> 16) & 0xFF, (remote_addr >> 8) & 0xFF, (remote_addr >> 0) & 0xFF - ); - while (1) { uint8_t tag; size_t len; @@ -323,13 +296,13 @@ result->device_auth[len] = 0; break; - case HDHOMERUN_TAG_DEVICE_AUTH_BIN: + case HDHOMERUN_TAG_DEVICE_AUTH_BIN_DEPRECATED: if (len != 18) { break; } for (i = 0; i < 24; i += 4) { uint32_t raw24; - raw24 = (uint32_t)hdhomerun_pkt_read_u8(rx_pkt) << 16; + raw24 = (uint32_t)hdhomerun_pkt_read_u8(rx_pkt) << 16; raw24 |= (uint32_t)hdhomerun_pkt_read_u8(rx_pkt) << 8; raw24 |= (uint32_t)hdhomerun_pkt_read_u8(rx_pkt) << 0; result->device_auth[i + 0] = hdhomerun_discover_recv_base64_encode_table[(raw24 >> 18) & 0x3F]; @@ -348,6 +321,39 @@ result->base_url[len] = 0; break; + case HDHOMERUN_TAG_STORAGE_ID: + if (!result_v3) { + break; + } + if (len >= sizeof(result_v3->storage_id)) { + break; + } + hdhomerun_pkt_read_mem(rx_pkt, result_v3->storage_id, len); + result_v3->storage_id[len] = 0; + break; + + case HDHOMERUN_TAG_LINEUP_URL: + if (!result_v3) { + break; + } + if (len >= sizeof(result_v3->lineup_url)) { + break; + } + hdhomerun_pkt_read_mem(rx_pkt, result_v3->lineup_url, len); + result_v3->lineup_url[len] = 0; + break; + + case HDHOMERUN_TAG_STORAGE_URL: + if (!result_v3) { + break; + } + if (len >= sizeof(result_v3->storage_url)) { + break; + } + hdhomerun_pkt_read_mem(rx_pkt, result_v3->storage_url, len); + result_v3->storage_url[len] = 0; + break; + default: break; } @@ -355,92 +361,110 @@ rx_pkt->pos = next; } - /* Fixup for old firmware. */ - if (result->tuner_count == 0) { - switch (result->device_id >> 20) { - case 0x102: - result->tuner_count = 1; - break; + /* + * Fixup for old firmware. + */ + if (result->device_type == HDHOMERUN_DEVICE_TYPE_TUNER) { + if (result->tuner_count == 0) { + switch (result->device_id >> 20) { + case 0x102: + result->tuner_count = 1; + break; - case 0x100: - case 0x101: - case 0x121: - result->tuner_count = 2; - break; + case 0x100: + case 0x101: + case 0x121: + result->tuner_count = 2; + break; - default: - break; + default: + break; + } + } + + if (!result->base_url[0]) { + hdhomerun_sprintf(result->base_url, result->base_url + sizeof(result->base_url), "http://%u.%u.%u.%u:80", + (remote_addr >> 24) & 0xFF, (remote_addr >> 16) & 0xFF, (remote_addr >> 8) & 0xFF, (remote_addr >> 0) & 0xFF + ); } } - return TRUE; + return true; } -static bool_t hdhomerun_discover_recv(struct hdhomerun_discover_t *ds, struct hdhomerun_discover_device_t *result) +static bool hdhomerun_discover_recv(struct hdhomerun_discover_t *ds, size_t result_struct_size, struct hdhomerun_discover_device_t *result) { unsigned int i; for (i = 0; i < ds->sock_count; i++) { struct hdhomerun_discover_sock_t *dss = &ds->socks[i]; - if (hdhomerun_discover_recv_internal(ds, dss, result)) { - return TRUE; + if (hdhomerun_discover_recv_internal(ds, dss, result_struct_size, result)) { + return true; } } - return FALSE; + return false; +} + +static struct hdhomerun_discover_device_t *hdhomerun_discover_result_by_index(size_t result_struct_size, struct hdhomerun_discover_device_t result_list[], int index) +{ + uint8_t *ptr = (uint8_t *)(void *)result_list; + ptr += result_struct_size * index; + return (struct hdhomerun_discover_device_t *)(void *)ptr; } -static struct hdhomerun_discover_device_t *hdhomerun_discover_find_in_list(struct hdhomerun_discover_device_t result_list[], int count, struct hdhomerun_discover_device_t *lookup) +static struct hdhomerun_discover_device_t *hdhomerun_discover_find_in_list(size_t result_struct_size, struct hdhomerun_discover_device_t result_list[], int count, struct hdhomerun_discover_device_t *lookup) { int index; for (index = 0; index < count; index++) { - struct hdhomerun_discover_device_t *entry = &result_list[index]; - if (memcmp(lookup, entry, sizeof(struct hdhomerun_discover_device_t)) == 0) { - return entry; + struct hdhomerun_discover_device_t *entry = hdhomerun_discover_result_by_index(result_struct_size, result_list, index); + if (lookup->ip_addr != entry->ip_addr) { + continue; + } + + if (strcmp(lookup->base_url, entry->base_url) != 0) { + continue; } + + return entry; } return NULL; } -int hdhomerun_discover_find_devices_v2(struct hdhomerun_discover_t *ds, uint32_t target_ip, uint32_t device_type, uint32_t device_id, struct hdhomerun_discover_device_t result_list[], int max_count) +static int hdhomerun_discover_find_devices(struct hdhomerun_discover_t *ds, uint32_t target_ip, uint32_t device_type_match, uint32_t device_id_match, size_t result_struct_size, struct hdhomerun_discover_device_t result_list[], int max_count) { hdhomerun_discover_sock_detect(ds); int count = 0; int attempt; for (attempt = 0; attempt < 2; attempt++) { - if (!hdhomerun_discover_send(ds, target_ip, device_type, device_id)) { + if (!hdhomerun_discover_send(ds, target_ip, device_type_match, device_id_match)) { return -1; } uint64_t timeout = getcurrenttime() + 200; while (1) { - struct hdhomerun_discover_device_t *result = &result_list[count]; - memset(result, 0, sizeof(struct hdhomerun_discover_device_t)); + struct hdhomerun_discover_device_t *result = hdhomerun_discover_result_by_index(result_struct_size, result_list, count); - if (!hdhomerun_discover_recv(ds, result)) { + if (!hdhomerun_discover_recv(ds, result_struct_size, result)) { if (getcurrenttime() >= timeout) { break; } - msleep_approx(10); + msleep_approx(16); continue; } - /* Filter. */ - if (device_type != HDHOMERUN_DEVICE_TYPE_WILDCARD) { - if (device_type != result->device_type) { - continue; - } + /* Filter */ + if ((device_type_match != HDHOMERUN_DEVICE_TYPE_WILDCARD) && (result->device_type != device_type_match)) { + continue; } - if (device_id != HDHOMERUN_DEVICE_ID_WILDCARD) { - if (device_id != result->device_id) { - continue; - } + if ((device_id_match != HDHOMERUN_DEVICE_ID_WILDCARD) && (result->device_id != device_id_match)) { + continue; } /* Ensure not already in list. */ - if (hdhomerun_discover_find_in_list(result_list, count, result)) { + if (hdhomerun_discover_find_in_list(result_struct_size, result_list, count, result)) { continue; } @@ -455,24 +479,41 @@ return count; } -int hdhomerun_discover_find_devices_custom_v2(uint32_t target_ip, uint32_t device_type, uint32_t device_id, struct hdhomerun_discover_device_t result_list[], int max_count) +int hdhomerun_discover_find_devices_v3(struct hdhomerun_discover_t *ds, uint32_t target_ip, uint32_t device_type_match, uint32_t device_id_match, struct hdhomerun_discover_device_v3_t result_list[], int max_count) { - if (hdhomerun_discover_is_ip_multicast(target_ip)) { - return 0; - } + return hdhomerun_discover_find_devices(ds, target_ip, device_type_match, device_id_match, sizeof(struct hdhomerun_discover_device_v3_t), (struct hdhomerun_discover_device_t *)(void *)result_list, max_count); +} + +int hdhomerun_discover_find_devices_v2(struct hdhomerun_discover_t *ds, uint32_t target_ip, uint32_t device_type_match, uint32_t device_id_match, struct hdhomerun_discover_device_t result_list[], int max_count) +{ + return hdhomerun_discover_find_devices(ds, target_ip, device_type_match, device_id_match, sizeof(struct hdhomerun_discover_device_t), (struct hdhomerun_discover_device_t *)(void *)result_list, max_count); +} +int hdhomerun_discover_find_devices_custom_v3(uint32_t target_ip, uint32_t device_type_match, uint32_t device_id_match, struct hdhomerun_discover_device_v3_t result_list[], int max_count) +{ struct hdhomerun_discover_t *ds = hdhomerun_discover_create(NULL); if (!ds) { return -1; } - int ret = hdhomerun_discover_find_devices_v2(ds, target_ip, device_type, device_id, result_list, max_count); + int ret = hdhomerun_discover_find_devices(ds, target_ip, device_type_match, device_id_match, sizeof(struct hdhomerun_discover_device_v3_t), (struct hdhomerun_discover_device_t *)(void *)result_list, max_count); + hdhomerun_discover_destroy(ds); + return ret; +} + +int hdhomerun_discover_find_devices_custom_v2(uint32_t target_ip, uint32_t device_type_match, uint32_t device_id_match, struct hdhomerun_discover_device_t result_list[], int max_count) +{ + struct hdhomerun_discover_t *ds = hdhomerun_discover_create(NULL); + if (!ds) { + return -1; + } + int ret = hdhomerun_discover_find_devices(ds, target_ip, device_type_match, device_id_match, sizeof(struct hdhomerun_discover_device_t), (struct hdhomerun_discover_device_t *)(void *)result_list, max_count); hdhomerun_discover_destroy(ds); return ret; } -bool_t hdhomerun_discover_validate_device_id(uint32_t device_id) +bool hdhomerun_discover_validate_device_id(uint32_t device_id) { static uint8_t lookup_table[16] = {0xA, 0x5, 0xF, 0x6, 0x7, 0xC, 0x1, 0xB, 0x9, 0x2, 0x8, 0xD, 0x4, 0x3, 0xE, 0x0}; @@ -490,7 +531,7 @@ return (checksum == 0); } -bool_t hdhomerun_discover_is_ip_multicast(uint32_t ip_addr) +bool hdhomerun_discover_is_ip_multicast(uint32_t ip_addr) { return (ip_addr >= 0xE0000000) && (ip_addr < 0xF0000000); }
View file
libhdhomerun_20150826.tgz/hdhomerun_discover.h -> libhdhomerun_20190621.tgz/hdhomerun_discover.h
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_discover.h * - * Copyright © 2006-2015 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2006-2019 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -26,17 +26,31 @@ uint32_t device_type; uint32_t device_id; uint8_t tuner_count; - bool_t is_legacy; + bool is_legacy; char device_auth[25]; char base_url[29]; }; +struct hdhomerun_discover_device_v3_t { + uint32_t ip_addr; + uint32_t device_type; + uint32_t device_id; + uint8_t tuner_count; + bool is_legacy; + char device_auth[25]; + char base_url[29]; + + char storage_id[37]; + char lineup_url[128]; + char storage_url[128]; +}; + /* * Find devices. * * The device information is stored in caller-supplied array of hdhomerun_discover_device_t vars. * Multiple attempts are made to find devices. - * Execution time is typically 400ms if max_count is not reached. + * Execution time is typically 400ms unless max_count is reached. * * Set target_ip to zero to auto-detect the IP address. * Set device_type to HDHOMERUN_DEVICE_TYPE_TUNER to detect HDHomeRun tuner devices. @@ -45,14 +59,16 @@ * Returns the number of devices found. * Retruns -1 on error. */ -extern LIBTYPE int hdhomerun_discover_find_devices_custom_v2(uint32_t target_ip, uint32_t device_type, uint32_t device_id, struct hdhomerun_discover_device_t result_list[], int max_count); +extern LIBHDHOMERUN_API int hdhomerun_discover_find_devices_custom_v2(uint32_t target_ip, uint32_t device_type_match, uint32_t device_id_match, struct hdhomerun_discover_device_t result_list[], int max_count); +extern LIBHDHOMERUN_API int hdhomerun_discover_find_devices_custom_v3(uint32_t target_ip, uint32_t device_type_match, uint32_t device_id_match, struct hdhomerun_discover_device_v3_t result_list[], int max_count); /* * Optional: persistent discover instance available for discover polling use. */ -extern LIBTYPE struct hdhomerun_discover_t *hdhomerun_discover_create(struct hdhomerun_debug_t *dbg); -extern LIBTYPE void hdhomerun_discover_destroy(struct hdhomerun_discover_t *ds); -extern LIBTYPE int hdhomerun_discover_find_devices_v2(struct hdhomerun_discover_t *ds, uint32_t target_ip, uint32_t device_type, uint32_t device_id, struct hdhomerun_discover_device_t result_list[], int max_count); +extern LIBHDHOMERUN_API struct hdhomerun_discover_t *hdhomerun_discover_create(struct hdhomerun_debug_t *dbg); +extern LIBHDHOMERUN_API void hdhomerun_discover_destroy(struct hdhomerun_discover_t *ds); +extern LIBHDHOMERUN_API int hdhomerun_discover_find_devices_v2(struct hdhomerun_discover_t *ds, uint32_t target_ip, uint32_t device_type_match, uint32_t device_id_match, struct hdhomerun_discover_device_t result_list[], int max_count); +extern LIBHDHOMERUN_API int hdhomerun_discover_find_devices_v3(struct hdhomerun_discover_t *ds, uint32_t target_ip, uint32_t device_type_match, uint32_t device_id_match, struct hdhomerun_discover_device_v3_t result_list[], int max_count); /* * Verify that the device ID given is valid. @@ -60,18 +76,18 @@ * The device ID contains a self-check sequence that detects common user input errors including * single-digit errors and two digit transposition errors. * - * Returns TRUE if valid. - * Returns FALSE if not valid. + * Returns true if valid. + * Returns false if not valid. */ -extern LIBTYPE bool_t hdhomerun_discover_validate_device_id(uint32_t device_id); +extern LIBHDHOMERUN_API bool hdhomerun_discover_validate_device_id(uint32_t device_id); /* * Detect if an IP address is multicast. * - * Returns TRUE if multicast. - * Returns FALSE if zero, unicast, expermental, or broadcast. + * Returns true if multicast. + * Returns false if zero, unicast, expermental, or broadcast. */ -extern LIBTYPE bool_t hdhomerun_discover_is_ip_multicast(uint32_t ip_addr); +extern LIBHDHOMERUN_API bool hdhomerun_discover_is_ip_multicast(uint32_t ip_addr); #ifdef __cplusplus }
View file
libhdhomerun_20150826.tgz/hdhomerun_os.h -> libhdhomerun_20190621.tgz/hdhomerun_os.h
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_os.h * - * Copyright © 2006-2008 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2006-2015 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -18,20 +18,8 @@ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ -#if defined(_WIN32) || defined(_WIN64) -#define __WINDOWS__ -#endif - -#if defined(__WINDOWS__) +#if defined(_WIN32) #include "hdhomerun_os_windows.h" #else #include "hdhomerun_os_posix.h" #endif - -#if !defined(TRUE) -#define TRUE 1 -#endif - -#if !defined(FALSE) -#define FALSE 0 -#endif
View file
libhdhomerun_20150826.tgz/hdhomerun_os_posix.c -> libhdhomerun_20190621.tgz/hdhomerun_os_posix.c
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_os_posix.c * - * Copyright © 2006-2010 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2006-2017 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -21,8 +21,48 @@ #include "hdhomerun_os.h" #if defined(__APPLE__) + #include <mach/clock.h> #include <mach/mach.h> + +static pthread_once_t clock_monotonic_once = PTHREAD_ONCE_INIT; +static clock_serv_t clock_monotonic_clock_serv; + +static void clock_monotonic_init(void) +{ + host_get_clock_service(mach_host_self(), SYSTEM_CLOCK, &clock_monotonic_clock_serv); +} + +static inline void clock_monotonic_timespec(struct timespec *ts) +{ + pthread_once(&clock_monotonic_once, clock_monotonic_init); + + struct mach_timespec mt; + clock_get_time(clock_monotonic_clock_serv, &mt); + ts->tv_nsec = mt.tv_nsec; + ts->tv_sec = mt.tv_sec; +} + +static inline void clock_realtime_timespec(struct timespec *ts) +{ + struct timeval tv; + gettimeofday(&tv, NULL); + ts->tv_nsec = tv.tv_usec * 1000; + ts->tv_sec = tv.tv_sec; +} + +#else + +static inline void clock_monotonic_timespec(struct timespec *ts) +{ + clock_gettime(CLOCK_MONOTONIC, ts); +} + +static inline void clock_realtime_timespec(struct timespec *ts) +{ + clock_gettime(CLOCK_REALTIME, ts); +} + #endif static pthread_once_t random_get32_once = PTHREAD_ONCE_INIT; @@ -51,35 +91,22 @@ uint64_t getcurrenttime(void) { -#if defined(CLOCK_MONOTONIC) - struct timespec t; - clock_gettime(CLOCK_MONOTONIC, &t); - return ((uint64_t)t.tv_sec * 1000) + (t.tv_nsec / 1000000); -#elif defined(__APPLE__) - clock_serv_t clock_serv; - host_get_clock_service(mach_host_self(), SYSTEM_CLOCK, &clock_serv); - - struct mach_timespec t; - clock_get_time(clock_serv, &t); - - mach_port_deallocate(mach_task_self(), clock_serv); - return ((uint64_t)t.tv_sec * 1000) + (t.tv_nsec / 1000000); -#else -#error no clock source for getcurrenttime() -#endif + struct timespec ts; + clock_monotonic_timespec(&ts); + return ((uint64_t)ts.tv_sec * 1000) + (ts.tv_nsec / 1000000); } void msleep_approx(uint64_t ms) { - unsigned int delay_s = ms / 1000; + uint64_t delay_s = ms / 1000; if (delay_s > 0) { - sleep(delay_s); + sleep((unsigned int)delay_s); ms -= delay_s * 1000; } - unsigned int delay_us = ms * 1000; + uint64_t delay_us = ms * 1000; if (delay_us > 0) { - usleep(delay_us); + usleep((useconds_t)delay_us); } } @@ -97,32 +124,139 @@ } } -bool_t hdhomerun_vsprintf(char *buffer, char *end, const char *fmt, va_list ap) +struct thread_task_execute_args_t { + thread_task_func_t func; + void *arg; +}; + +static void *thread_task_execute(void *arg) +{ + struct thread_task_execute_args_t *execute_args = (struct thread_task_execute_args_t *)arg; + execute_args->func(execute_args->arg); + free(execute_args); + return NULL; +} + +bool thread_task_create(thread_task_t *tid, thread_task_func_t func, void *arg) +{ + struct thread_task_execute_args_t *execute_args = (struct thread_task_execute_args_t *)malloc(sizeof(struct thread_task_execute_args_t)); + if (!execute_args) { + return false; + } + + execute_args->func = func; + execute_args->arg = arg; + + if (pthread_create(tid, NULL, thread_task_execute, execute_args) != 0) { + free(execute_args); + return false; + } + + return true; +} + +void thread_task_join(thread_task_t tid) +{ + pthread_join(tid, NULL); +} + +void thread_mutex_init(thread_mutex_t *mutex) +{ + pthread_mutex_init(mutex, NULL); +} + +void thread_mutex_dispose(pthread_mutex_t *mutex) +{ +} + +void thread_mutex_lock(thread_mutex_t *mutex) +{ + pthread_mutex_lock(mutex); +} + +void thread_mutex_unlock(thread_mutex_t *mutex) +{ + pthread_mutex_unlock(mutex); +} + +void thread_cond_init(thread_cond_t *cond) +{ + cond->signaled = false; + pthread_mutex_init(&cond->lock, NULL); + pthread_cond_init(&cond->cond, NULL); +} + +void thread_cond_dispose(thread_cond_t *cond) +{ +} + +void thread_cond_signal(thread_cond_t *cond) +{ + pthread_mutex_lock(&cond->lock); + + cond->signaled = true; + pthread_cond_signal(&cond->cond); + + pthread_mutex_unlock(&cond->lock); +} + +void thread_cond_wait(thread_cond_t *cond) +{ + pthread_mutex_lock(&cond->lock); + + if (!cond->signaled) { + pthread_cond_wait(&cond->cond, &cond->lock); + } + + cond->signaled = false; + pthread_mutex_unlock(&cond->lock); +} + +void thread_cond_wait_with_timeout(thread_cond_t *cond, uint64_t max_wait_time) +{ + pthread_mutex_lock(&cond->lock); + + if (!cond->signaled) { + struct timespec ts; + clock_realtime_timespec(&ts); + + uint64_t tv_nsec = (uint64_t)ts.tv_nsec + (max_wait_time * 1000000); + ts.tv_nsec = (long)(tv_nsec % 1000000000); + ts.tv_sec += (time_t)(tv_nsec / 1000000000); + + pthread_cond_timedwait(&cond->cond, &cond->lock, &ts); + } + + cond->signaled = false; + pthread_mutex_unlock(&cond->lock); +} + +bool hdhomerun_vsprintf(char *buffer, char *end, const char *fmt, va_list ap) { if (buffer >= end) { - return FALSE; + return false; } int length = vsnprintf(buffer, end - buffer - 1, fmt, ap); if (length < 0) { *buffer = 0; - return FALSE; + return false; } if (buffer + length + 1 > end) { *(end - 1) = 0; - return FALSE; + return false; } - return TRUE; + return true; } -bool_t hdhomerun_sprintf(char *buffer, char *end, const char *fmt, ...) +bool hdhomerun_sprintf(char *buffer, char *end, const char *fmt, ...) { va_list ap; va_start(ap, fmt); - bool_t result = hdhomerun_vsprintf(buffer, end, fmt, ap); + bool result = hdhomerun_vsprintf(buffer, end, fmt, ap); va_end(ap); return result; }
View file
libhdhomerun_20150826.tgz/hdhomerun_os_posix.h -> libhdhomerun_20190621.tgz/hdhomerun_os_posix.h
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_os_posix.h * - * Copyright © 2006-2010 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2006-2017 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -22,6 +22,8 @@ #include <stdlib.h> #include <stdio.h> #include <stdarg.h> +#include <stdint.h> +#include <stdbool.h> #include <string.h> #include <unistd.h> #include <errno.h> @@ -29,8 +31,8 @@ #include <signal.h> #include <sys/types.h> #include <sys/socket.h> +#include <sys/stat.h> #include <sys/time.h> -#include <sys/timeb.h> #include <sys/wait.h> #include <netinet/in.h> #include <arpa/inet.h> @@ -38,25 +40,48 @@ #include <netdb.h> #include <pthread.h> -typedef int bool_t; typedef void (*sig_t)(int); +typedef void (*thread_task_func_t)(void *arg); +typedef pthread_t thread_task_t; +typedef pthread_mutex_t thread_mutex_t; -#define LIBTYPE -#define console_vprintf vprintf -#define console_printf printf -#define THREAD_FUNC_PREFIX void * +typedef struct { + volatile bool signaled; + pthread_mutex_t lock; + pthread_cond_t cond; +} thread_cond_t; + +#define LIBHDHOMERUN_API + +#if !defined(alignas) && !defined(__cplusplus) +#define alignas(n) __attribute__((aligned(n))) +#endif #ifdef __cplusplus extern "C" { #endif -extern LIBTYPE uint32_t random_get32(void); -extern LIBTYPE uint64_t getcurrenttime(void); -extern LIBTYPE void msleep_approx(uint64_t ms); -extern LIBTYPE void msleep_minimum(uint64_t ms); +extern LIBHDHOMERUN_API uint32_t random_get32(void); +extern LIBHDHOMERUN_API uint64_t getcurrenttime(void); +extern LIBHDHOMERUN_API void msleep_approx(uint64_t ms); +extern LIBHDHOMERUN_API void msleep_minimum(uint64_t ms); + +extern LIBHDHOMERUN_API bool thread_task_create(thread_task_t *tid, thread_task_func_t func, void *arg); +extern LIBHDHOMERUN_API void thread_task_join(thread_task_t tid); + +extern LIBHDHOMERUN_API void thread_mutex_init(thread_mutex_t *mutex); +extern LIBHDHOMERUN_API void thread_mutex_dispose(thread_mutex_t *mutex); +extern LIBHDHOMERUN_API void thread_mutex_lock(thread_mutex_t *mutex); +extern LIBHDHOMERUN_API void thread_mutex_unlock(thread_mutex_t *mutex); + +extern LIBHDHOMERUN_API void thread_cond_init(thread_cond_t *cond); +extern LIBHDHOMERUN_API void thread_cond_dispose(thread_cond_t *cond); +extern LIBHDHOMERUN_API void thread_cond_signal(thread_cond_t *cond); +extern LIBHDHOMERUN_API void thread_cond_wait(thread_cond_t *cond); +extern LIBHDHOMERUN_API void thread_cond_wait_with_timeout(thread_cond_t *cond, uint64_t max_wait_time); -extern LIBTYPE bool_t hdhomerun_vsprintf(char *buffer, char *end, const char *fmt, va_list ap); -extern LIBTYPE bool_t hdhomerun_sprintf(char *buffer, char *end, const char *fmt, ...); +extern LIBHDHOMERUN_API bool hdhomerun_vsprintf(char *buffer, char *end, const char *fmt, va_list ap); +extern LIBHDHOMERUN_API bool hdhomerun_sprintf(char *buffer, char *end, const char *fmt, ...); #ifdef __cplusplus }
View file
libhdhomerun_20150826.tgz/hdhomerun_os_windows.c -> libhdhomerun_20190621.tgz/hdhomerun_os_windows.c
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_os_windows.c * - * Copyright © 2006-2010 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2006-2017 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -18,12 +18,21 @@ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ -#include "hdhomerun_os.h" - -static DWORD random_get32_context_tls = TlsAlloc(); +#include "hdhomerun.h" +#if defined(_WINRT) +uint32_t random_get32(void) +{ + return (uint32_t)getcurrenttime(); +} +#else uint32_t random_get32(void) { + static DWORD random_get32_context_tls = 0xFFFFFFFF; + if (random_get32_context_tls == 0xFFFFFFFF) { + random_get32_context_tls = TlsAlloc(); + } + HCRYPTPROV *phProv = (HCRYPTPROV *)TlsGetValue(random_get32_context_tls); if (!phProv) { phProv = (HCRYPTPROV *)calloc(1, sizeof(HCRYPTPROV)); @@ -38,6 +47,7 @@ return Result; } +#endif uint64_t getcurrenttime(void) { @@ -63,90 +73,122 @@ } } -int pthread_create(pthread_t *tid, void *attr, LPTHREAD_START_ROUTINE start, void *arg) +struct thread_task_execute_args_t { + thread_task_func_t func; + void *arg; +}; + +static DWORD WINAPI thread_task_execute(void *arg) +{ + struct thread_task_execute_args_t *execute_args = (struct thread_task_execute_args_t *)arg; + execute_args->func(execute_args->arg); + free(execute_args); + return 0; +} + +bool thread_task_create(thread_task_t *tid, thread_task_func_t func, void *arg) { - *tid = CreateThread(NULL, 0, start, arg, 0, NULL); + struct thread_task_execute_args_t *execute_args = (struct thread_task_execute_args_t *)malloc(sizeof(struct thread_task_execute_args_t)); + if (!execute_args) { + return false; + } + + execute_args->func = func; + execute_args->arg = arg; + + *tid = CreateThread(NULL, 0, thread_task_execute, execute_args, 0, NULL); if (!*tid) { - return (int)GetLastError(); + free(execute_args); + return false; } - return 0; + + return true; } -int pthread_join(pthread_t tid, void **value_ptr) +void thread_task_join(thread_task_t tid) { while (1) { DWORD ExitCode = 0; if (!GetExitCodeThread(tid, &ExitCode)) { - return (int)GetLastError(); + return; } if (ExitCode != STILL_ACTIVE) { - return 0; + return; } } } -void pthread_mutex_init(pthread_mutex_t *mutex, void *attr) +void thread_mutex_init(thread_mutex_t *mutex) { - *mutex = CreateMutex(NULL, FALSE, NULL); + *mutex = CreateMutex(NULL, false, NULL); } -void pthread_mutex_lock(pthread_mutex_t *mutex) +void thread_mutex_dispose(thread_mutex_t *mutex) +{ + CloseHandle(*mutex); +} + +void thread_mutex_lock(thread_mutex_t *mutex) { WaitForSingleObject(*mutex, INFINITE); } -void pthread_mutex_unlock(pthread_mutex_t *mutex) +void thread_mutex_unlock(thread_mutex_t *mutex) { ReleaseMutex(*mutex); } -bool_t hdhomerun_vsprintf(char *buffer, char *end, const char *fmt, va_list ap) +void thread_cond_init(thread_cond_t *cond) +{ + *cond = CreateEvent(NULL, false, false, NULL); +} + +void thread_cond_dispose(thread_cond_t *cond) +{ + CloseHandle(*cond); +} + +void thread_cond_signal(thread_cond_t *cond) +{ + SetEvent(*cond); +} + +void thread_cond_wait(thread_cond_t *cond) +{ + WaitForSingleObject(*cond, INFINITE); +} + +void thread_cond_wait_with_timeout(thread_cond_t *cond, uint64_t max_wait_time) +{ + WaitForSingleObject(*cond, (DWORD)max_wait_time); +} + +bool hdhomerun_vsprintf(char *buffer, char *end, const char *fmt, va_list ap) { if (buffer >= end) { - return FALSE; + return false; } int length = _vsnprintf(buffer, end - buffer - 1, fmt, ap); if (length < 0) { *buffer = 0; - return FALSE; + return false; } if (buffer + length + 1 > end) { *(end - 1) = 0; - return FALSE; + return false; } - return TRUE; + return true; } -bool_t hdhomerun_sprintf(char *buffer, char *end, const char *fmt, ...) +bool hdhomerun_sprintf(char *buffer, char *end, const char *fmt, ...) { va_list ap; va_start(ap, fmt); - bool_t result = hdhomerun_vsprintf(buffer, end, fmt, ap); + bool result = hdhomerun_vsprintf(buffer, end, fmt, ap); va_end(ap); return result; } - -/* - * The console output format should be set to UTF-8, however in XP and Vista this breaks batch file processing. - * Attempting to restore on exit fails to restore if the program is terminated by the user. - * Solution - set the output format each printf. - */ -void console_vprintf(const char *fmt, va_list ap) -{ - UINT cp = GetConsoleOutputCP(); - SetConsoleOutputCP(CP_UTF8); - vprintf(fmt, ap); - SetConsoleOutputCP(cp); -} - -void console_printf(const char *fmt, ...) -{ - va_list ap; - va_start(ap, fmt); - console_vprintf(fmt, ap); - va_end(ap); -}
View file
libhdhomerun_20150826.tgz/hdhomerun_os_windows.h -> libhdhomerun_20190621.tgz/hdhomerun_os_windows.h
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_os_windows.h * - * Copyright © 2006-2010 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2006-2017 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -18,40 +18,57 @@ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ -#define _WINSOCKAPI_ -#include <windows.h> +#ifdef _WINRT +#include <SDKDDKVer.h> +#endif + +#ifndef _WIN32_WINNT +#define _WIN32_WINNT _WIN32_WINNT_VISTA +#endif +#ifndef _CRT_SECURE_NO_WARNINGS +#define _CRT_SECURE_NO_WARNINGS +#endif +#ifndef _WINSOCK_DEPRECATED_NO_WARNINGS +#define _WINSOCK_DEPRECATED_NO_WARNINGS +#endif + #include <winsock2.h> +#include <windows.h> #include <ws2tcpip.h> #include <wspiapi.h> #include <stdlib.h> #include <stdio.h> #include <stdarg.h> +#include <stdint.h> +#include <stdbool.h> #include <string.h> #include <signal.h> #include <time.h> #include <sys/types.h> -#include <sys/timeb.h> - -#if defined(DLL_IMPORT) -#define LIBTYPE __declspec( dllexport ) -#elif defined(DLL_EXPORT) -#define LIBTYPE __declspec( dllimport ) -#else -#define LIBTYPE + +#ifdef LIBHDHOMERUN_DLLEXPORT +#define LIBHDHOMERUN_API __declspec(dllexport) +#endif +#ifdef LIBHDHOMERUN_DLLIMPORT +#define LIBHDHOMERUN_API __declspec(dllimport) +#endif +#ifndef LIBHDHOMERUN_API +#define LIBHDHOMERUN_API +#endif + +#if !defined(__unused) +#define __unused __pragma(warning(suppress: 4100 4101)) +#endif + +#if !defined(alignas) && !defined(__cplusplus) +#define alignas(n) __declspec(align(n)) #endif -typedef int bool_t; -typedef signed __int8 int8_t; -typedef signed __int16 int16_t; -typedef signed __int32 int32_t; -typedef signed __int64 int64_t; -typedef unsigned __int8 uint8_t; -typedef unsigned __int16 uint16_t; -typedef unsigned __int32 uint32_t; -typedef unsigned __int64 uint64_t; typedef void (*sig_t)(int); -typedef HANDLE pthread_t; -typedef HANDLE pthread_mutex_t; +typedef void (*thread_task_func_t)(void *arg); +typedef HANDLE thread_task_t; +typedef HANDLE thread_mutex_t; +typedef HANDLE thread_cond_t; #if !defined(va_copy) #define va_copy(x, y) x = y @@ -60,35 +77,35 @@ #define atoll _atoi64 #define strdup _strdup #define strcasecmp _stricmp +#define strncasecmp _strnicmp #define fseeko _fseeki64 #define ftello _ftelli64 -#define THREAD_FUNC_PREFIX DWORD WINAPI #ifdef __cplusplus extern "C" { #endif -extern LIBTYPE uint32_t random_get32(void); -extern LIBTYPE uint64_t getcurrenttime(void); -extern LIBTYPE void msleep_approx(uint64_t ms); -extern LIBTYPE void msleep_minimum(uint64_t ms); +extern LIBHDHOMERUN_API uint32_t random_get32(void); +extern LIBHDHOMERUN_API uint64_t getcurrenttime(void); +extern LIBHDHOMERUN_API void msleep_approx(uint64_t ms); +extern LIBHDHOMERUN_API void msleep_minimum(uint64_t ms); -extern LIBTYPE int pthread_create(pthread_t *tid, void *attr, LPTHREAD_START_ROUTINE start, void *arg); -extern LIBTYPE int pthread_join(pthread_t tid, void **value_ptr); -extern LIBTYPE void pthread_mutex_init(pthread_mutex_t *mutex, void *attr); -extern LIBTYPE void pthread_mutex_lock(pthread_mutex_t *mutex); -extern LIBTYPE void pthread_mutex_unlock(pthread_mutex_t *mutex); +extern LIBHDHOMERUN_API bool thread_task_create(thread_task_t *tid, thread_task_func_t func, void *arg); +extern LIBHDHOMERUN_API void thread_task_join(thread_task_t tid); -extern LIBTYPE bool_t hdhomerun_vsprintf(char *buffer, char *end, const char *fmt, va_list ap); -extern LIBTYPE bool_t hdhomerun_sprintf(char *buffer, char *end, const char *fmt, ...); +extern LIBHDHOMERUN_API void thread_mutex_init(thread_mutex_t *mutex); +extern LIBHDHOMERUN_API void thread_mutex_dispose(thread_mutex_t *mutex); +extern LIBHDHOMERUN_API void thread_mutex_lock(thread_mutex_t *mutex); +extern LIBHDHOMERUN_API void thread_mutex_unlock(thread_mutex_t *mutex); -/* - * The console output format should be set to UTF-8, however in XP and Vista this breaks batch file processing. - * Attempting to restore on exit fails to restore if the program is terminated by the user. - * Solution - set the output format each printf. - */ -extern LIBTYPE void console_vprintf(const char *fmt, va_list ap); -extern LIBTYPE void console_printf(const char *fmt, ...); +extern LIBHDHOMERUN_API void thread_cond_init(thread_cond_t *cond); +extern LIBHDHOMERUN_API void thread_cond_dispose(thread_cond_t *cond); +extern LIBHDHOMERUN_API void thread_cond_signal(thread_cond_t *cond); +extern LIBHDHOMERUN_API void thread_cond_wait(thread_cond_t *cond); +extern LIBHDHOMERUN_API void thread_cond_wait_with_timeout(thread_cond_t *cond, uint64_t max_wait_time); + +extern LIBHDHOMERUN_API bool hdhomerun_vsprintf(char *buffer, char *end, const char *fmt, va_list ap); +extern LIBHDHOMERUN_API bool hdhomerun_sprintf(char *buffer, char *end, const char *fmt, ...); #ifdef __cplusplus }
View file
libhdhomerun_20150826.tgz/hdhomerun_pkt.c -> libhdhomerun_20190621.tgz/hdhomerun_pkt.c
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_pkt.c * - * Copyright © 2005-2006 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2006-2014 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public
View file
libhdhomerun_20150826.tgz/hdhomerun_pkt.h -> libhdhomerun_20190621.tgz/hdhomerun_pkt.h
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_pkt.h * - * Copyright © 2005-2006 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2006-2015 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -127,12 +127,16 @@ #define HDHOMERUN_TAG_GETSET_LOCKKEY 0x15 #define HDHOMERUN_TAG_ERROR_MESSAGE 0x05 #define HDHOMERUN_TAG_TUNER_COUNT 0x10 -#define HDHOMERUN_TAG_DEVICE_AUTH_BIN 0x29 +#define HDHOMERUN_TAG_LINEUP_URL 0x27 +#define HDHOMERUN_TAG_STORAGE_URL 0x28 +#define HDHOMERUN_TAG_DEVICE_AUTH_BIN_DEPRECATED 0x29 #define HDHOMERUN_TAG_BASE_URL 0x2A #define HDHOMERUN_TAG_DEVICE_AUTH_STR 0x2B +#define HDHOMERUN_TAG_STORAGE_ID 0x2C #define HDHOMERUN_DEVICE_TYPE_WILDCARD 0xFFFFFFFF #define HDHOMERUN_DEVICE_TYPE_TUNER 0x00000001 +#define HDHOMERUN_DEVICE_TYPE_STORAGE 0x00000005 #define HDHOMERUN_DEVICE_ID_WILDCARD 0xFFFFFFFF #define HDHOMERUN_MIN_PEEK_LENGTH 4 @@ -145,25 +149,25 @@ uint8_t buffer[3074]; }; -extern LIBTYPE struct hdhomerun_pkt_t *hdhomerun_pkt_create(void); -extern LIBTYPE void hdhomerun_pkt_destroy(struct hdhomerun_pkt_t *pkt); -extern LIBTYPE void hdhomerun_pkt_reset(struct hdhomerun_pkt_t *pkt); +extern LIBHDHOMERUN_API struct hdhomerun_pkt_t *hdhomerun_pkt_create(void); +extern LIBHDHOMERUN_API void hdhomerun_pkt_destroy(struct hdhomerun_pkt_t *pkt); +extern LIBHDHOMERUN_API void hdhomerun_pkt_reset(struct hdhomerun_pkt_t *pkt); -extern LIBTYPE uint8_t hdhomerun_pkt_read_u8(struct hdhomerun_pkt_t *pkt); -extern LIBTYPE uint16_t hdhomerun_pkt_read_u16(struct hdhomerun_pkt_t *pkt); -extern LIBTYPE uint32_t hdhomerun_pkt_read_u32(struct hdhomerun_pkt_t *pkt); -extern LIBTYPE size_t hdhomerun_pkt_read_var_length(struct hdhomerun_pkt_t *pkt); -extern LIBTYPE uint8_t *hdhomerun_pkt_read_tlv(struct hdhomerun_pkt_t *pkt, uint8_t *ptag, size_t *plength); -extern LIBTYPE void hdhomerun_pkt_read_mem(struct hdhomerun_pkt_t *pkt, void *mem, size_t length); +extern LIBHDHOMERUN_API uint8_t hdhomerun_pkt_read_u8(struct hdhomerun_pkt_t *pkt); +extern LIBHDHOMERUN_API uint16_t hdhomerun_pkt_read_u16(struct hdhomerun_pkt_t *pkt); +extern LIBHDHOMERUN_API uint32_t hdhomerun_pkt_read_u32(struct hdhomerun_pkt_t *pkt); +extern LIBHDHOMERUN_API size_t hdhomerun_pkt_read_var_length(struct hdhomerun_pkt_t *pkt); +extern LIBHDHOMERUN_API uint8_t *hdhomerun_pkt_read_tlv(struct hdhomerun_pkt_t *pkt, uint8_t *ptag, size_t *plength); +extern LIBHDHOMERUN_API void hdhomerun_pkt_read_mem(struct hdhomerun_pkt_t *pkt, void *mem, size_t length); -extern LIBTYPE void hdhomerun_pkt_write_u8(struct hdhomerun_pkt_t *pkt, uint8_t v); -extern LIBTYPE void hdhomerun_pkt_write_u16(struct hdhomerun_pkt_t *pkt, uint16_t v); -extern LIBTYPE void hdhomerun_pkt_write_u32(struct hdhomerun_pkt_t *pkt, uint32_t v); -extern LIBTYPE void hdhomerun_pkt_write_var_length(struct hdhomerun_pkt_t *pkt, size_t v); -extern LIBTYPE void hdhomerun_pkt_write_mem(struct hdhomerun_pkt_t *pkt, const void *mem, size_t length); +extern LIBHDHOMERUN_API void hdhomerun_pkt_write_u8(struct hdhomerun_pkt_t *pkt, uint8_t v); +extern LIBHDHOMERUN_API void hdhomerun_pkt_write_u16(struct hdhomerun_pkt_t *pkt, uint16_t v); +extern LIBHDHOMERUN_API void hdhomerun_pkt_write_u32(struct hdhomerun_pkt_t *pkt, uint32_t v); +extern LIBHDHOMERUN_API void hdhomerun_pkt_write_var_length(struct hdhomerun_pkt_t *pkt, size_t v); +extern LIBHDHOMERUN_API void hdhomerun_pkt_write_mem(struct hdhomerun_pkt_t *pkt, const void *mem, size_t length); -extern LIBTYPE bool_t hdhomerun_pkt_open_frame(struct hdhomerun_pkt_t *pkt, uint16_t *ptype); -extern LIBTYPE void hdhomerun_pkt_seal_frame(struct hdhomerun_pkt_t *pkt, uint16_t frame_type); +extern LIBHDHOMERUN_API int hdhomerun_pkt_open_frame(struct hdhomerun_pkt_t *pkt, uint16_t *ptype); +extern LIBHDHOMERUN_API void hdhomerun_pkt_seal_frame(struct hdhomerun_pkt_t *pkt, uint16_t frame_type); #ifdef __cplusplus }
View file
libhdhomerun_20150826.tgz/hdhomerun_sock.h -> libhdhomerun_20190621.tgz/hdhomerun_sock.h
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_sock.h * - * Copyright © 2010 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2010-2016 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -26,33 +26,37 @@ uint32_t subnet_mask; }; -extern LIBTYPE int hdhomerun_local_ip_info(struct hdhomerun_local_ip_info_t ip_info_list[], int max_count); +extern LIBHDHOMERUN_API int hdhomerun_local_ip_info(struct hdhomerun_local_ip_info_t ip_info_list[], int max_count); +extern LIBHDHOMERUN_API void hdhomerun_local_ip_info_set_str(const char *ip_info_str); /* WinRT only */ -#define HDHOMERUN_SOCK_INVALID -1 +struct hdhomerun_sock_t; -typedef int hdhomerun_sock_t; +extern LIBHDHOMERUN_API struct hdhomerun_sock_t *hdhomerun_sock_create_udp(void); +extern LIBHDHOMERUN_API struct hdhomerun_sock_t *hdhomerun_sock_create_tcp(void); +extern LIBHDHOMERUN_API void hdhomerun_sock_stop(struct hdhomerun_sock_t *sock); +extern LIBHDHOMERUN_API void hdhomerun_sock_destroy(struct hdhomerun_sock_t *sock); -extern LIBTYPE hdhomerun_sock_t hdhomerun_sock_create_udp(void); -extern LIBTYPE hdhomerun_sock_t hdhomerun_sock_create_tcp(void); -extern LIBTYPE void hdhomerun_sock_destroy(hdhomerun_sock_t sock); +extern LIBHDHOMERUN_API void hdhomerun_sock_set_send_buffer_size(struct hdhomerun_sock_t *sock, size_t size); +extern LIBHDHOMERUN_API void hdhomerun_sock_set_recv_buffer_size(struct hdhomerun_sock_t *sock, size_t size); +extern LIBHDHOMERUN_API void hdhomerun_sock_set_allow_reuse(struct hdhomerun_sock_t *sock); -extern LIBTYPE int hdhomerun_sock_getlasterror(void); -extern LIBTYPE uint32_t hdhomerun_sock_getsockname_addr(hdhomerun_sock_t sock); -extern LIBTYPE uint16_t hdhomerun_sock_getsockname_port(hdhomerun_sock_t sock); -extern LIBTYPE uint32_t hdhomerun_sock_getpeername_addr(hdhomerun_sock_t sock); -extern LIBTYPE uint32_t hdhomerun_sock_getaddrinfo_addr(hdhomerun_sock_t sock, const char *name); +extern LIBHDHOMERUN_API int hdhomerun_sock_getlasterror(void); +extern LIBHDHOMERUN_API uint32_t hdhomerun_sock_getsockname_addr(struct hdhomerun_sock_t *sock); +extern LIBHDHOMERUN_API uint16_t hdhomerun_sock_getsockname_port(struct hdhomerun_sock_t *sock); +extern LIBHDHOMERUN_API uint32_t hdhomerun_sock_getpeername_addr(struct hdhomerun_sock_t *sock); +extern LIBHDHOMERUN_API uint32_t hdhomerun_sock_getaddrinfo_addr(struct hdhomerun_sock_t *sock, const char *name); -extern LIBTYPE bool_t hdhomerun_sock_join_multicast_group(hdhomerun_sock_t sock, uint32_t multicast_ip, uint32_t local_ip); -extern LIBTYPE bool_t hdhomerun_sock_leave_multicast_group(hdhomerun_sock_t sock, uint32_t multicast_ip, uint32_t local_ip); +extern LIBHDHOMERUN_API bool hdhomerun_sock_join_multicast_group(struct hdhomerun_sock_t *sock, uint32_t multicast_ip, uint32_t local_ip); +extern LIBHDHOMERUN_API bool hdhomerun_sock_leave_multicast_group(struct hdhomerun_sock_t *sock, uint32_t multicast_ip, uint32_t local_ip); -extern LIBTYPE bool_t hdhomerun_sock_bind(hdhomerun_sock_t sock, uint32_t local_addr, uint16_t local_port, bool_t allow_reuse); -extern LIBTYPE bool_t hdhomerun_sock_connect(hdhomerun_sock_t sock, uint32_t remote_addr, uint16_t remote_port, uint64_t timeout); +extern LIBHDHOMERUN_API bool hdhomerun_sock_bind(struct hdhomerun_sock_t *sock, uint32_t local_addr, uint16_t local_port, bool allow_reuse); +extern LIBHDHOMERUN_API bool hdhomerun_sock_connect(struct hdhomerun_sock_t *sock, uint32_t remote_addr, uint16_t remote_port, uint64_t timeout); -extern LIBTYPE bool_t hdhomerun_sock_send(hdhomerun_sock_t sock, const void *data, size_t length, uint64_t timeout); -extern LIBTYPE bool_t hdhomerun_sock_sendto(hdhomerun_sock_t sock, uint32_t remote_addr, uint16_t remote_port, const void *data, size_t length, uint64_t timeout); +extern LIBHDHOMERUN_API bool hdhomerun_sock_send(struct hdhomerun_sock_t *sock, const void *data, size_t length, uint64_t timeout); +extern LIBHDHOMERUN_API bool hdhomerun_sock_sendto(struct hdhomerun_sock_t *sock, uint32_t remote_addr, uint16_t remote_port, const void *data, size_t length, uint64_t timeout); -extern LIBTYPE bool_t hdhomerun_sock_recv(hdhomerun_sock_t sock, void *data, size_t *length, uint64_t timeout); -extern LIBTYPE bool_t hdhomerun_sock_recvfrom(hdhomerun_sock_t sock, uint32_t *remote_addr, uint16_t *remote_port, void *data, size_t *length, uint64_t timeout); +extern LIBHDHOMERUN_API bool hdhomerun_sock_recv(struct hdhomerun_sock_t *sock, void *data, size_t *length, uint64_t timeout); +extern LIBHDHOMERUN_API bool hdhomerun_sock_recvfrom(struct hdhomerun_sock_t *sock, uint32_t *remote_addr, uint16_t *remote_port, void *data, size_t *length, uint64_t timeout); #ifdef __cplusplus }
View file
libhdhomerun_20150826.tgz/hdhomerun_sock_posix.c -> libhdhomerun_20190621.tgz/hdhomerun_sock_posix.c
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_sock_posix.c * - * Copyright © 2010 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2010-2019 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -18,170 +18,230 @@ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ -/* - * Implementation notes: - * - * API specifies timeout for each operation (or zero for non-blocking). - * - * It is not possible to rely on the OS socket timeout as this will fail to - * detect the command-response situation where data is sent successfully and - * the other end chooses not to send a response (other than the TCP ack). - * - * The select() cannot be used with high socket numbers (typically max 1024) - * so the code works as follows: - * - Use non-blocking sockets to allow operation without select. - * - Use select where safe (low socket numbers). - * - Poll with short sleep when select cannot be used safely. - */ - #include "hdhomerun.h" -#include <net/if.h> +#if defined(LIBHDHOMERUN_USE_SIOCGIFCONF) #include <sys/ioctl.h> - -#ifndef SIOCGIFCONF -#include <sys/sockio.h> +#else +#include <ifaddrs.h> #endif -#ifndef _SIZEOF_ADDR_IFREQ -#define _SIZEOF_ADDR_IFREQ(x) sizeof(x) -#endif +#include <net/if.h> #ifndef MSG_NOSIGNAL #define MSG_NOSIGNAL 0 #endif +struct hdhomerun_sock_t { + int sock; +}; + +#if defined(LIBHDHOMERUN_USE_SIOCGIFCONF) int hdhomerun_local_ip_info(struct hdhomerun_local_ip_info_t ip_info_list[], int max_count) { - int sock = socket(AF_INET, SOCK_DGRAM, 0); - if (sock == HDHOMERUN_SOCK_INVALID) { + int sock = socket(AF_INET, SOCK_DGRAM, IPPROTO_IP); + if (sock == -1) { + return -1; + } + + int ifreq_buffer_size = 128 * sizeof(struct ifreq); + char *ifreq_buffer = (char *)calloc(ifreq_buffer_size, 1); + if (!ifreq_buffer) { + close(sock); return -1; } struct ifconf ifc; - size_t ifreq_buffer_size = 1024; + ifc.ifc_len = ifreq_buffer_size; + ifc.ifc_buf = ifreq_buffer; - while (1) { + if (ioctl(sock, SIOCGIFCONF, &ifc) != 0) { + free(ifreq_buffer); + close(sock); + return -1; + } + + if (ifc.ifc_len > ifreq_buffer_size) { ifc.ifc_len = ifreq_buffer_size; - ifc.ifc_buf = (char *)malloc(ifreq_buffer_size); - if (!ifc.ifc_buf) { - close(sock); - return -1; - } - - memset(ifc.ifc_buf, 0, ifreq_buffer_size); - - if (ioctl(sock, SIOCGIFCONF, &ifc) != 0) { - free(ifc.ifc_buf); - close(sock); - return -1; - } - - if (ifc.ifc_len < ifreq_buffer_size) { - break; - } - - free(ifc.ifc_buf); - ifreq_buffer_size += 1024; } + struct hdhomerun_local_ip_info_t *ip_info = ip_info_list; + int count = 0; + char *ptr = ifc.ifc_buf; char *end = ifc.ifc_buf + ifc.ifc_len; - int count = 0; - while (ptr < end) { + while (ptr + sizeof(struct ifreq) <= end) { struct ifreq *ifr = (struct ifreq *)ptr; - ptr += _SIZEOF_ADDR_IFREQ(*ifr); + ptr += sizeof(struct ifreq); + + /* Local IP address. */ + struct sockaddr_in *ip_addr_in = (struct sockaddr_in *)&ifr->ifr_addr; + uint32_t ip_addr = ntohl(ip_addr_in->sin_addr.s_addr); + if (ip_addr == 0) { + continue; + } /* Flags. */ if (ioctl(sock, SIOCGIFFLAGS, ifr) != 0) { continue; } - if ((ifr->ifr_flags & IFF_UP) == 0) { + unsigned int flags = ifr->ifr_flags & (IFF_LOOPBACK | IFF_POINTOPOINT | IFF_UP | IFF_RUNNING); + if (flags != (IFF_UP | IFF_RUNNING)) { continue; } - if ((ifr->ifr_flags & IFF_RUNNING) == 0) { + + /* Subnet mask. */ + if (ioctl(sock, SIOCGIFNETMASK, ifr) != 0) { continue; } - /* Local IP address. */ - if (ioctl(sock, SIOCGIFADDR, ifr) != 0) { + struct sockaddr_in *subnet_mask_in = (struct sockaddr_in *)&ifr->ifr_addr; + uint32_t subnet_mask = ntohl(subnet_mask_in->sin_addr.s_addr); + + /* Result. */ + if (count < max_count) { + ip_info->ip_addr = ip_addr; + ip_info->subnet_mask = subnet_mask; + ip_info++; + } + + count++; + } + + free(ifreq_buffer); + close(sock); + return count; +} +#else +int hdhomerun_local_ip_info(struct hdhomerun_local_ip_info_t ip_info_list[], int max_count) +{ + struct ifaddrs *ifaddrs; + if (getifaddrs(&ifaddrs) != 0) { + return -1; + } + + struct hdhomerun_local_ip_info_t *ip_info = ip_info_list; + struct ifaddrs *ifa = ifaddrs; + int count = 0; + + while (ifa) { + if (ifa->ifa_addr == NULL) { + ifa = ifa->ifa_next; continue; } - struct sockaddr_in *ip_addr_in = (struct sockaddr_in *)&(ifr->ifr_addr); - uint32_t ip_addr = ntohl(ip_addr_in->sin_addr.s_addr); - if (ip_addr == 0) { + if (ifa->ifa_addr->sa_family != AF_INET) { + ifa = ifa->ifa_next; continue; } - /* Subnet mask. */ - if (ioctl(sock, SIOCGIFNETMASK, ifr) != 0) { + unsigned int flags = ifa->ifa_flags & (IFF_LOOPBACK | IFF_POINTOPOINT | IFF_UP | IFF_RUNNING); + if (flags != (IFF_UP | IFF_RUNNING)) { + ifa = ifa->ifa_next; continue; } - struct sockaddr_in *subnet_mask_in = (struct sockaddr_in *)&(ifr->ifr_addr); - uint32_t subnet_mask = ntohl(subnet_mask_in->sin_addr.s_addr); + struct sockaddr_in *addr_in = (struct sockaddr_in *)ifa->ifa_addr; + uint32_t ip_addr = ntohl(addr_in->sin_addr.s_addr); + + struct sockaddr_in *netmask_in = (struct sockaddr_in *)ifa->ifa_netmask; + uint32_t subnet_mask = ntohl(netmask_in->sin_addr.s_addr); + + ifa = ifa->ifa_next; - /* Report. */ if (count < max_count) { - struct hdhomerun_local_ip_info_t *ip_info = &ip_info_list[count]; ip_info->ip_addr = ip_addr; ip_info->subnet_mask = subnet_mask; + ip_info++; } count++; } - free(ifc.ifc_buf); - close(sock); + freeifaddrs(ifaddrs); return count; } +#endif -hdhomerun_sock_t hdhomerun_sock_create_udp(void) +static struct hdhomerun_sock_t *hdhomerun_sock_create_internal(int protocol) { + struct hdhomerun_sock_t *sock = (struct hdhomerun_sock_t *)calloc(1, sizeof(struct hdhomerun_sock_t)); + if (!sock) { + return NULL; + } + /* Create socket. */ - hdhomerun_sock_t sock = (hdhomerun_sock_t)socket(AF_INET, SOCK_DGRAM, 0); - if (sock == -1) { - return HDHOMERUN_SOCK_INVALID; + sock->sock = socket(AF_INET, protocol, 0); + if (sock->sock == -1) { + free(sock); + return NULL; } /* Set non-blocking */ - if (fcntl(sock, F_SETFL, O_NONBLOCK) != 0) { - close(sock); - return HDHOMERUN_SOCK_INVALID; + if (fcntl(sock->sock, F_SETFL, O_NONBLOCK) != 0) { + hdhomerun_sock_destroy(sock); + return NULL; } - /* Allow broadcast. */ - int sock_opt = 1; - setsockopt(sock, SOL_SOCKET, SO_BROADCAST, (char *)&sock_opt, sizeof(sock_opt)); + /* Configure socket not to generate pipe-error signal (BSD/OSX). */ +#if defined(SO_NOSIGPIPE) + int set = 1; + setsockopt(sock->sock, SOL_SOCKET, SO_NOSIGPIPE, (char *)&set, sizeof(set)); +#endif /* Success. */ return sock; } -hdhomerun_sock_t hdhomerun_sock_create_tcp(void) +struct hdhomerun_sock_t *hdhomerun_sock_create_udp(void) { - /* Create socket. */ - hdhomerun_sock_t sock = (hdhomerun_sock_t)socket(AF_INET, SOCK_STREAM, 0); - if (sock == -1) { - return HDHOMERUN_SOCK_INVALID; + struct hdhomerun_sock_t *sock = hdhomerun_sock_create_internal(SOCK_DGRAM); + if (!sock) { + return NULL; } - /* Set non-blocking */ - if (fcntl(sock, F_SETFL, O_NONBLOCK) != 0) { - close(sock); - return HDHOMERUN_SOCK_INVALID; - } + /* Allow broadcast. */ + int sock_opt = 1; + setsockopt(sock->sock, SOL_SOCKET, SO_BROADCAST, (char *)&sock_opt, sizeof(sock_opt)); /* Success. */ return sock; } -void hdhomerun_sock_destroy(hdhomerun_sock_t sock) +struct hdhomerun_sock_t *hdhomerun_sock_create_tcp(void) { - close(sock); + return hdhomerun_sock_create_internal(SOCK_STREAM); +} + +void hdhomerun_sock_destroy(struct hdhomerun_sock_t *sock) +{ + close(sock->sock); + free(sock); +} + +void hdhomerun_sock_stop(struct hdhomerun_sock_t *sock) +{ + shutdown(sock->sock, SHUT_RDWR); +} + +void hdhomerun_sock_set_send_buffer_size(struct hdhomerun_sock_t *sock, size_t size) +{ + int size_opt = (int)size; + setsockopt(sock->sock, SOL_SOCKET, SO_SNDBUF, (char *)&size_opt, sizeof(size_opt)); +} + +void hdhomerun_sock_set_recv_buffer_size(struct hdhomerun_sock_t *sock, size_t size) +{ + int size_opt = (int)size; + setsockopt(sock->sock, SOL_SOCKET, SO_RCVBUF, (char *)&size_opt, sizeof(size_opt)); +} + +void hdhomerun_sock_set_allow_reuse(struct hdhomerun_sock_t *sock) +{ + int sock_opt = 1; + setsockopt(sock->sock, SOL_SOCKET, SO_REUSEADDR, (char *)&sock_opt, sizeof(sock_opt)); } int hdhomerun_sock_getlasterror(void) @@ -189,43 +249,43 @@ return errno; } -uint32_t hdhomerun_sock_getsockname_addr(hdhomerun_sock_t sock) +uint32_t hdhomerun_sock_getsockname_addr(struct hdhomerun_sock_t *sock) { struct sockaddr_in sock_addr; socklen_t sockaddr_size = sizeof(sock_addr); - if (getsockname(sock, (struct sockaddr *)&sock_addr, &sockaddr_size) != 0) { + if (getsockname(sock->sock, (struct sockaddr *)&sock_addr, &sockaddr_size) != 0) { return 0; } return ntohl(sock_addr.sin_addr.s_addr); } -uint16_t hdhomerun_sock_getsockname_port(hdhomerun_sock_t sock) +uint16_t hdhomerun_sock_getsockname_port(struct hdhomerun_sock_t *sock) { struct sockaddr_in sock_addr; socklen_t sockaddr_size = sizeof(sock_addr); - if (getsockname(sock, (struct sockaddr *)&sock_addr, &sockaddr_size) != 0) { + if (getsockname(sock->sock, (struct sockaddr *)&sock_addr, &sockaddr_size) != 0) { return 0; } return ntohs(sock_addr.sin_port); } -uint32_t hdhomerun_sock_getpeername_addr(hdhomerun_sock_t sock) +uint32_t hdhomerun_sock_getpeername_addr(struct hdhomerun_sock_t *sock) { struct sockaddr_in sock_addr; socklen_t sockaddr_size = sizeof(sock_addr); - if (getpeername(sock, (struct sockaddr *)&sock_addr, &sockaddr_size) != 0) { + if (getpeername(sock->sock, (struct sockaddr *)&sock_addr, &sockaddr_size) != 0) { return 0; } return ntohl(sock_addr.sin_addr.s_addr); } -uint32_t hdhomerun_sock_getaddrinfo_addr(hdhomerun_sock_t sock, const char *name) +uint32_t hdhomerun_sock_getaddrinfo_addr(struct hdhomerun_sock_t *sock, const char *name) { struct addrinfo hints; memset(&hints, 0, sizeof(hints)); @@ -245,38 +305,38 @@ return addr; } -bool_t hdhomerun_sock_join_multicast_group(hdhomerun_sock_t sock, uint32_t multicast_ip, uint32_t local_ip) +bool hdhomerun_sock_join_multicast_group(struct hdhomerun_sock_t *sock, uint32_t multicast_ip, uint32_t local_ip) { struct ip_mreq imr; memset(&imr, 0, sizeof(imr)); imr.imr_multiaddr.s_addr = htonl(multicast_ip); imr.imr_interface.s_addr = htonl(local_ip); - if (setsockopt(sock, IPPROTO_IP, IP_ADD_MEMBERSHIP, (const char *)&imr, sizeof(imr)) != 0) { - return FALSE; + if (setsockopt(sock->sock, IPPROTO_IP, IP_ADD_MEMBERSHIP, (const char *)&imr, sizeof(imr)) != 0) { + return false; } - return TRUE; + return true; } -bool_t hdhomerun_sock_leave_multicast_group(hdhomerun_sock_t sock, uint32_t multicast_ip, uint32_t local_ip) +bool hdhomerun_sock_leave_multicast_group(struct hdhomerun_sock_t *sock, uint32_t multicast_ip, uint32_t local_ip) { struct ip_mreq imr; memset(&imr, 0, sizeof(imr)); imr.imr_multiaddr.s_addr = htonl(multicast_ip); imr.imr_interface.s_addr = htonl(local_ip); - if (setsockopt(sock, IPPROTO_IP, IP_DROP_MEMBERSHIP, (const char *)&imr, sizeof(imr)) != 0) { - return FALSE; + if (setsockopt(sock->sock, IPPROTO_IP, IP_DROP_MEMBERSHIP, (const char *)&imr, sizeof(imr)) != 0) { + return false; } - return TRUE; + return true; } -bool_t hdhomerun_sock_bind(hdhomerun_sock_t sock, uint32_t local_addr, uint16_t local_port, bool_t allow_reuse) +bool hdhomerun_sock_bind(struct hdhomerun_sock_t *sock, uint32_t local_addr, uint16_t local_port, bool allow_reuse) { int sock_opt = allow_reuse; - setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, (char *)&sock_opt, sizeof(sock_opt)); + setsockopt(sock->sock, SOL_SOCKET, SO_REUSEADDR, (char *)&sock_opt, sizeof(sock_opt)); struct sockaddr_in sock_addr; memset(&sock_addr, 0, sizeof(sock_addr)); @@ -284,168 +344,239 @@ sock_addr.sin_addr.s_addr = htonl(local_addr); sock_addr.sin_port = htons(local_port); - if (bind(sock, (struct sockaddr *)&sock_addr, sizeof(sock_addr)) != 0) { - return FALSE; + if (bind(sock->sock, (struct sockaddr *)&sock_addr, sizeof(sock_addr)) != 0) { + return false; } - return TRUE; + return true; } -static bool_t hdhomerun_sock_wait_for_event(hdhomerun_sock_t sock, short event_type, uint64_t stop_time) +bool hdhomerun_sock_connect(struct hdhomerun_sock_t *sock, uint32_t remote_addr, uint16_t remote_port, uint64_t timeout) { - uint64_t current_time = getcurrenttime(); - if (current_time >= stop_time) { - return FALSE; + struct sockaddr_in sock_addr; + memset(&sock_addr, 0, sizeof(sock_addr)); + sock_addr.sin_family = AF_INET; + sock_addr.sin_addr.s_addr = htonl(remote_addr); + sock_addr.sin_port = htons(remote_port); + + if (connect(sock->sock, (struct sockaddr *)&sock_addr, sizeof(sock_addr)) != 0) { + if ((errno != EAGAIN) && (errno != EWOULDBLOCK) && (errno != EINPROGRESS)) { + return false; + } } struct pollfd poll_event; - poll_event.fd = sock; - poll_event.events = event_type; + poll_event.fd = sock->sock; + poll_event.events = POLLOUT; poll_event.revents = 0; - uint64_t timeout = stop_time - current_time; - if (poll(&poll_event, 1, (int)timeout) <= 0) { - return FALSE; + return false; } - if ((poll_event.revents & event_type) == 0) { - return FALSE; + if ((poll_event.revents & POLLOUT) == 0) { + return false; } - return TRUE; + return true; } -bool_t hdhomerun_sock_connect(hdhomerun_sock_t sock, uint32_t remote_addr, uint16_t remote_port, uint64_t timeout) +bool hdhomerun_sock_send(struct hdhomerun_sock_t *sock, const void *data, size_t length, uint64_t timeout) { - struct sockaddr_in sock_addr; - memset(&sock_addr, 0, sizeof(sock_addr)); - sock_addr.sin_family = AF_INET; - sock_addr.sin_addr.s_addr = htonl(remote_addr); - sock_addr.sin_port = htons(remote_port); + const uint8_t *ptr = (const uint8_t *)data; + ssize_t ret = send(sock->sock, ptr, length, MSG_NOSIGNAL); + if (ret >= (ssize_t)length) { + return true; + } - if (connect(sock, (struct sockaddr *)&sock_addr, sizeof(sock_addr)) != 0) { - if ((errno != EAGAIN) && (errno != EWOULDBLOCK) && (errno != EINPROGRESS)) { - return FALSE; - } + if ((ret < 0) && (errno != EAGAIN) && (errno != EWOULDBLOCK) && (errno != EINPROGRESS)) { + return false; } - uint64_t stop_time = getcurrenttime() + timeout; - return hdhomerun_sock_wait_for_event(sock, POLLOUT, stop_time); -} + if (ret > 0) { + ptr += ret; + length -= ret; + } -bool_t hdhomerun_sock_send(hdhomerun_sock_t sock, const void *data, size_t length, uint64_t timeout) -{ uint64_t stop_time = getcurrenttime() + timeout; - const uint8_t *ptr = (const uint8_t *)data; while (1) { - int ret = send(sock, ptr, length, MSG_NOSIGNAL); - if (ret <= 0) { - if ((errno != EAGAIN) && (errno != EWOULDBLOCK) && (errno != EINPROGRESS)) { - return FALSE; - } - if (!hdhomerun_sock_wait_for_event(sock, POLLOUT, stop_time)) { - return FALSE; - } - continue; + struct pollfd poll_event; + poll_event.fd = sock->sock; + poll_event.events = POLLOUT; + poll_event.revents = 0; + + if (poll(&poll_event, 1, (int)timeout) <= 0) { + return false; + } + + if ((poll_event.revents & POLLOUT) == 0) { + return false; + } + + ret = send(sock->sock, ptr, length, MSG_NOSIGNAL); + if (ret >= (ssize_t)length) { + return true; + } + + if ((ret < 0) && (errno != EAGAIN) && (errno != EWOULDBLOCK) && (errno != EINPROGRESS)) { + return false; } - if (ret < (int)length) { + if (ret > 0) { ptr += ret; length -= ret; - continue; } - return TRUE; + uint64_t current_time = getcurrenttime(); + if (current_time >= stop_time) { + return false; + } + + timeout = stop_time - current_time; } } -bool_t hdhomerun_sock_sendto(hdhomerun_sock_t sock, uint32_t remote_addr, uint16_t remote_port, const void *data, size_t length, uint64_t timeout) +bool hdhomerun_sock_sendto(struct hdhomerun_sock_t *sock, uint32_t remote_addr, uint16_t remote_port, const void *data, size_t length, uint64_t timeout) { - uint64_t stop_time = getcurrenttime() + timeout; + struct sockaddr_in sock_addr; + memset(&sock_addr, 0, sizeof(sock_addr)); + sock_addr.sin_family = AF_INET; + sock_addr.sin_addr.s_addr = htonl(remote_addr); + sock_addr.sin_port = htons(remote_port); + const uint8_t *ptr = (const uint8_t *)data; + ssize_t ret = sendto(sock->sock, ptr, length, 0, (struct sockaddr *)&sock_addr, sizeof(sock_addr)); + if (ret >= (ssize_t)length) { + return true; + } + + if ((ret < 0) && (errno != EAGAIN) && (errno != EWOULDBLOCK) && (errno != EINPROGRESS)) { + return false; + } + + if (ret > 0) { + ptr += ret; + length -= ret; + } + + uint64_t stop_time = getcurrenttime() + timeout; while (1) { - struct sockaddr_in sock_addr; - memset(&sock_addr, 0, sizeof(sock_addr)); - sock_addr.sin_family = AF_INET; - sock_addr.sin_addr.s_addr = htonl(remote_addr); - sock_addr.sin_port = htons(remote_port); - - int ret = sendto(sock, ptr, length, 0, (struct sockaddr *)&sock_addr, sizeof(sock_addr)); - if (ret <= 0) { - if ((errno != EAGAIN) && (errno != EWOULDBLOCK) && (errno != EINPROGRESS)) { - return FALSE; - } - if (!hdhomerun_sock_wait_for_event(sock, POLLOUT, stop_time)) { - return FALSE; - } - continue; + struct pollfd poll_event; + poll_event.fd = sock->sock; + poll_event.events = POLLOUT; + poll_event.revents = 0; + + if (poll(&poll_event, 1, (int)timeout) <= 0) { + return false; + } + + if ((poll_event.revents & POLLOUT) == 0) { + return false; } - if (ret < (int)length) { + ret = sendto(sock->sock, ptr, length, 0, (struct sockaddr *)&sock_addr, sizeof(sock_addr)); + if (ret >= (ssize_t)length) { + return true; + } + + if ((ret < 0) && (errno != EAGAIN) && (errno != EWOULDBLOCK) && (errno != EINPROGRESS)) { + return false; + } + + if (ret > 0) { ptr += ret; length -= ret; - continue; } - return TRUE; + uint64_t current_time = getcurrenttime(); + if (current_time >= stop_time) { + return false; + } + + timeout = stop_time - current_time; } } -bool_t hdhomerun_sock_recv(hdhomerun_sock_t sock, void *data, size_t *length, uint64_t timeout) +bool hdhomerun_sock_recv(struct hdhomerun_sock_t *sock, void *data, size_t *length, uint64_t timeout) { - uint64_t stop_time = getcurrenttime() + timeout; + ssize_t ret = recv(sock->sock, data, *length, 0); + if (ret > 0) { + *length = (size_t)ret; + return true; + } - while (1) { - int ret = recv(sock, data, *length, 0); - if (ret < 0) { - if ((errno != EAGAIN) && (errno != EWOULDBLOCK) && (errno != EINPROGRESS)) { - return FALSE; - } - if (!hdhomerun_sock_wait_for_event(sock, POLLIN, stop_time)) { - return FALSE; - } - continue; - } + if (ret == 0) { + return false; + } + if ((errno != EAGAIN) && (errno != EWOULDBLOCK) && (errno != EINPROGRESS)) { + return false; + } - if (ret == 0) { - return FALSE; - } + struct pollfd poll_event; + poll_event.fd = sock->sock; + poll_event.events = POLLIN; + poll_event.revents = 0; + + if (poll(&poll_event, 1, (int)timeout) <= 0) { + return false; + } - *length = ret; - return TRUE; + if ((poll_event.revents & POLLIN) == 0) { + return false; } + + ret = recv(sock->sock, data, *length, 0); + if (ret > 0) { + *length = (size_t)ret; + return true; + } + + return false; } -bool_t hdhomerun_sock_recvfrom(hdhomerun_sock_t sock, uint32_t *remote_addr, uint16_t *remote_port, void *data, size_t *length, uint64_t timeout) +bool hdhomerun_sock_recvfrom(struct hdhomerun_sock_t *sock, uint32_t *remote_addr, uint16_t *remote_port, void *data, size_t *length, uint64_t timeout) { - uint64_t stop_time = getcurrenttime() + timeout; + struct sockaddr_in sock_addr; + memset(&sock_addr, 0, sizeof(sock_addr)); + socklen_t sockaddr_size = sizeof(sock_addr); - while (1) { - struct sockaddr_in sock_addr; - memset(&sock_addr, 0, sizeof(sock_addr)); - socklen_t sockaddr_size = sizeof(sock_addr); - - int ret = recvfrom(sock, data, *length, 0, (struct sockaddr *)&sock_addr, &sockaddr_size); - if (ret < 0) { - if ((errno != EAGAIN) && (errno != EWOULDBLOCK) && (errno != EINPROGRESS)) { - return FALSE; - } - if (!hdhomerun_sock_wait_for_event(sock, POLLIN, stop_time)) { - return FALSE; - } - continue; - } + ssize_t ret = recvfrom(sock->sock, data, *length, 0, (struct sockaddr *)&sock_addr, &sockaddr_size); + if (ret > 0) { + *remote_addr = ntohl(sock_addr.sin_addr.s_addr); + *remote_port = ntohs(sock_addr.sin_port); + *length = (size_t)ret; + return true; + } - if (ret == 0) { - return FALSE; - } + if (ret == 0) { + return false; + } + if ((errno != EAGAIN) && (errno != EWOULDBLOCK) && (errno != EINPROGRESS)) { + return false; + } + + struct pollfd poll_event; + poll_event.fd = sock->sock; + poll_event.events = POLLIN; + poll_event.revents = 0; + if (poll(&poll_event, 1, (int)timeout) <= 0) { + return false; + } + + if ((poll_event.revents & POLLIN) == 0) { + return false; + } + + ret = recvfrom(sock->sock, data, *length, 0, (struct sockaddr *)&sock_addr, &sockaddr_size); + if (ret > 0) { *remote_addr = ntohl(sock_addr.sin_addr.s_addr); *remote_port = ntohs(sock_addr.sin_port); - *length = ret; - return TRUE; + *length = (size_t)ret; + return true; } + + return false; }
View file
libhdhomerun_20150826.tgz/hdhomerun_sock_windows.c -> libhdhomerun_20190621.tgz/hdhomerun_sock_windows.c
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_sock_windows.c * - * Copyright © 2010 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2010-2016 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -18,25 +18,67 @@ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ +#include "hdhomerun.h" +#include <iphlpapi.h> + +struct hdhomerun_sock_t { + SOCKET sock; + HANDLE event; + long events_selected; +}; + +#if defined(_WINRT) +static char *hdhomerun_local_ip_info_str = NULL; + /* - * Implementation notes: - * - * API specifies timeout for each operation (or zero for non-blocking). - * - * It is not possible to rely on the OS socket timeout as this will fail to - * detect the command-response situation where data is sent successfully and - * the other end chooses not to send a response (other than the TCP ack). - * - * Windows supports select() however native WSA events are used to: - * - avoid problems with socket numbers above 1024. - * - wait without allowing other events handlers to run (important for use - * with win7 WMC). + * String format: ip address '/' subnet mask bits <space> ... + * Example: "192.168.0.100/24 169.254.0.100/16" */ +void hdhomerun_local_ip_info_set_str(const char *ip_info_str) +{ + if (hdhomerun_local_ip_info_str) { + free(hdhomerun_local_ip_info_str); + } -#include "hdhomerun.h" -#include <windows.h> -#include <iphlpapi.h> + hdhomerun_local_ip_info_str = strdup(ip_info_str); +} + +int hdhomerun_local_ip_info(struct hdhomerun_local_ip_info_t ip_info_list[], int max_count) +{ + const char *ptr = hdhomerun_local_ip_info_str; + if (!ptr) { + return 0; + } + + struct hdhomerun_local_ip_info_t *ip_info = ip_info_list; + int count = 0; + + while (count < max_count) { + unsigned int a[4]; + unsigned int mask_bitcount; + if (sscanf(ptr, "%u.%u.%u.%u/%u", &a[0], &a[1], &a[2], &a[3], &mask_bitcount) != 5) { + break; + } + + ip_info->ip_addr = (uint32_t)((a[0] << 24) | (a[1] << 16) | (a[2] << 8) | (a[3] << 0)); + ip_info->subnet_mask = 0xFFFFFFFF << (32 - mask_bitcount); + ip_info++; + count++; + + ptr = strchr(ptr, ' '); + if (!ptr) { + break; + } + + ptr++; + } + + return count; +} +#endif + +#if !defined(_WINRT) int hdhomerun_local_ip_info(struct hdhomerun_local_ip_info_t ip_info_list[], int max_count) { PIP_ADAPTER_INFO AdapterInfo; @@ -99,52 +141,91 @@ free(AdapterInfo); return count; } +#endif -hdhomerun_sock_t hdhomerun_sock_create_udp(void) +static struct hdhomerun_sock_t *hdhomerun_sock_create_internal(int protocol) { + struct hdhomerun_sock_t *sock = (struct hdhomerun_sock_t *)calloc(1, sizeof(struct hdhomerun_sock_t)); + if (!sock) { + return NULL; + } + /* Create socket. */ - hdhomerun_sock_t sock = (hdhomerun_sock_t)socket(AF_INET, SOCK_DGRAM, 0); - if (sock == -1) { - return HDHOMERUN_SOCK_INVALID; + sock->sock = socket(AF_INET, protocol, 0); + if (sock->sock == INVALID_SOCKET) { + free(sock); + return NULL; } /* Set non-blocking */ unsigned long mode = 1; - if (ioctlsocket(sock, FIONBIO, &mode) != 0) { - closesocket(sock); - return HDHOMERUN_SOCK_INVALID; + if (ioctlsocket(sock->sock, FIONBIO, &mode) != 0) { + hdhomerun_sock_destroy(sock); + return NULL; } - /* Allow broadcast. */ - int sock_opt = 1; - setsockopt(sock, SOL_SOCKET, SO_BROADCAST, (char *)&sock_opt, sizeof(sock_opt)); + /* Event */ + sock->event = CreateEvent(NULL, false, false, NULL); + if (!sock->event) { + hdhomerun_sock_destroy(sock); + return NULL; + } /* Success. */ return sock; } -hdhomerun_sock_t hdhomerun_sock_create_tcp(void) +struct hdhomerun_sock_t *hdhomerun_sock_create_udp(void) { - /* Create socket. */ - hdhomerun_sock_t sock = (hdhomerun_sock_t)socket(AF_INET, SOCK_STREAM, 0); - if (sock == -1) { - return HDHOMERUN_SOCK_INVALID; + struct hdhomerun_sock_t *sock = hdhomerun_sock_create_internal(SOCK_DGRAM); + if (!sock) { + return NULL; } - /* Set non-blocking */ - unsigned long mode = 1; - if (ioctlsocket(sock, FIONBIO, &mode) != 0) { - closesocket(sock); - return HDHOMERUN_SOCK_INVALID; - } + /* Allow broadcast. */ + int sock_opt = 1; + setsockopt(sock->sock, SOL_SOCKET, SO_BROADCAST, (char *)&sock_opt, sizeof(sock_opt)); /* Success. */ return sock; } -void hdhomerun_sock_destroy(hdhomerun_sock_t sock) +struct hdhomerun_sock_t *hdhomerun_sock_create_tcp(void) { - closesocket(sock); + return hdhomerun_sock_create_internal(SOCK_STREAM); +} + +void hdhomerun_sock_destroy(struct hdhomerun_sock_t *sock) +{ + if (sock->event) { + CloseHandle(sock->event); + } + + closesocket(sock->sock); + free(sock); +} + +void hdhomerun_sock_stop(struct hdhomerun_sock_t *sock) +{ + shutdown(sock->sock, SD_BOTH); +} + +void hdhomerun_sock_set_send_buffer_size(struct hdhomerun_sock_t *sock, size_t size) +{ + int size_opt = (int)size; + setsockopt(sock->sock, SOL_SOCKET, SO_SNDBUF, (char *)&size_opt, sizeof(size_opt)); +} + +void hdhomerun_sock_set_recv_buffer_size(struct hdhomerun_sock_t *sock, size_t size) +{ + int size_opt = (int)size; + setsockopt(sock->sock, SOL_SOCKET, SO_RCVBUF, (char *)&size_opt, sizeof(size_opt)); +} + +void hdhomerun_sock_set_allow_reuse(struct hdhomerun_sock_t *sock) +{ + int sock_opt = 1; + setsockopt(sock->sock, SOL_SOCKET, SO_REUSEADDR, (char *)&sock_opt, sizeof(sock_opt)); } int hdhomerun_sock_getlasterror(void) @@ -152,43 +233,43 @@ return WSAGetLastError(); } -uint32_t hdhomerun_sock_getsockname_addr(hdhomerun_sock_t sock) +uint32_t hdhomerun_sock_getsockname_addr(struct hdhomerun_sock_t *sock) { struct sockaddr_in sock_addr; int sockaddr_size = sizeof(sock_addr); - if (getsockname(sock, (struct sockaddr *)&sock_addr, &sockaddr_size) != 0) { + if (getsockname(sock->sock, (struct sockaddr *)&sock_addr, &sockaddr_size) != 0) { return 0; } return ntohl(sock_addr.sin_addr.s_addr); } -uint16_t hdhomerun_sock_getsockname_port(hdhomerun_sock_t sock) +uint16_t hdhomerun_sock_getsockname_port(struct hdhomerun_sock_t *sock) { struct sockaddr_in sock_addr; int sockaddr_size = sizeof(sock_addr); - if (getsockname(sock, (struct sockaddr *)&sock_addr, &sockaddr_size) != 0) { + if (getsockname(sock->sock, (struct sockaddr *)&sock_addr, &sockaddr_size) != 0) { return 0; } return ntohs(sock_addr.sin_port); } -uint32_t hdhomerun_sock_getpeername_addr(hdhomerun_sock_t sock) +uint32_t hdhomerun_sock_getpeername_addr(struct hdhomerun_sock_t *sock) { struct sockaddr_in sock_addr; int sockaddr_size = sizeof(sock_addr); - if (getpeername(sock, (struct sockaddr *)&sock_addr, &sockaddr_size) != 0) { + if (getpeername(sock->sock, (struct sockaddr *)&sock_addr, &sockaddr_size) != 0) { return 0; } return ntohl(sock_addr.sin_addr.s_addr); } -uint32_t hdhomerun_sock_getaddrinfo_addr(hdhomerun_sock_t sock, const char *name) +uint32_t hdhomerun_sock_getaddrinfo_addr(struct hdhomerun_sock_t *sock, const char *name) { struct addrinfo hints; memset(&hints, 0, sizeof(hints)); @@ -208,38 +289,38 @@ return addr; } -bool_t hdhomerun_sock_join_multicast_group(hdhomerun_sock_t sock, uint32_t multicast_ip, uint32_t local_ip) +bool hdhomerun_sock_join_multicast_group(struct hdhomerun_sock_t *sock, uint32_t multicast_ip, uint32_t local_ip) { struct ip_mreq imr; memset(&imr, 0, sizeof(imr)); imr.imr_multiaddr.s_addr = htonl(multicast_ip); imr.imr_interface.s_addr = htonl(local_ip); - if (setsockopt(sock, IPPROTO_IP, IP_ADD_MEMBERSHIP, (const char *)&imr, sizeof(imr)) != 0) { - return FALSE; + if (setsockopt(sock->sock, IPPROTO_IP, IP_ADD_MEMBERSHIP, (const char *)&imr, sizeof(imr)) != 0) { + return false; } - return TRUE; + return true; } -bool_t hdhomerun_sock_leave_multicast_group(hdhomerun_sock_t sock, uint32_t multicast_ip, uint32_t local_ip) +bool hdhomerun_sock_leave_multicast_group(struct hdhomerun_sock_t *sock, uint32_t multicast_ip, uint32_t local_ip) { struct ip_mreq imr; memset(&imr, 0, sizeof(imr)); imr.imr_multiaddr.s_addr = htonl(multicast_ip); imr.imr_interface.s_addr = htonl(local_ip); - if (setsockopt(sock, IPPROTO_IP, IP_DROP_MEMBERSHIP, (const char *)&imr, sizeof(imr)) != 0) { - return FALSE; + if (setsockopt(sock->sock, IPPROTO_IP, IP_DROP_MEMBERSHIP, (const char *)&imr, sizeof(imr)) != 0) { + return false; } - return TRUE; + return true; } -bool_t hdhomerun_sock_bind(hdhomerun_sock_t sock, uint32_t local_addr, uint16_t local_port, bool_t allow_reuse) +bool hdhomerun_sock_bind(struct hdhomerun_sock_t *sock, uint32_t local_addr, uint16_t local_port, bool allow_reuse) { int sock_opt = allow_reuse; - setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, (char *)&sock_opt, sizeof(sock_opt)); + setsockopt(sock->sock, SOL_SOCKET, SO_REUSEADDR, (char *)&sock_opt, sizeof(sock_opt)); struct sockaddr_in sock_addr; memset(&sock_addr, 0, sizeof(sock_addr)); @@ -247,204 +328,202 @@ sock_addr.sin_addr.s_addr = htonl(local_addr); sock_addr.sin_port = htons(local_port); - if (bind(sock, (struct sockaddr *)&sock_addr, sizeof(sock_addr)) != 0) { - return FALSE; + if (bind(sock->sock, (struct sockaddr *)&sock_addr, sizeof(sock_addr)) != 0) { + return false; + } + + return true; +} + +static bool hdhomerun_sock_event_select(struct hdhomerun_sock_t *sock, long events) +{ + if (sock->events_selected != events) { + if (WSAEventSelect(sock->sock, sock->event, events) == SOCKET_ERROR) { + return false; + } + sock->events_selected = events; } - return TRUE; + ResetEvent(sock->event); + return true; } -bool_t hdhomerun_sock_connect(hdhomerun_sock_t sock, uint32_t remote_addr, uint16_t remote_port, uint64_t timeout) +bool hdhomerun_sock_connect(struct hdhomerun_sock_t *sock, uint32_t remote_addr, uint16_t remote_port, uint64_t timeout) { - /* Connect (non-blocking). */ + if (!hdhomerun_sock_event_select(sock, FD_WRITE | FD_CLOSE)) { + return false; + } + struct sockaddr_in sock_addr; memset(&sock_addr, 0, sizeof(sock_addr)); sock_addr.sin_family = AF_INET; sock_addr.sin_addr.s_addr = htonl(remote_addr); sock_addr.sin_port = htons(remote_port); - if (connect(sock, (struct sockaddr *)&sock_addr, sizeof(sock_addr)) != 0) { + if (connect(sock->sock, (struct sockaddr *)&sock_addr, sizeof(sock_addr)) != 0) { if (WSAGetLastError() != WSAEWOULDBLOCK) { - return FALSE; + return false; } } - /* Wait for connect to complete (both success and failure will signal). */ - WSAEVENT wsa_event = WSACreateEvent(); - if (wsa_event == WSA_INVALID_EVENT) { - return FALSE; + DWORD wait_ret = WaitForSingleObjectEx(sock->event, (DWORD)timeout, false); + if (wait_ret != WAIT_OBJECT_0) { + return false; } - if (WSAEventSelect(sock, wsa_event, FD_WRITE | FD_CLOSE) == SOCKET_ERROR) { - WSACloseEvent(wsa_event); - return FALSE; + WSANETWORKEVENTS network_events; + if (WSAEnumNetworkEvents(sock->sock, sock->event, &network_events) == SOCKET_ERROR) { + return false; } - - DWORD ret = WaitForSingleObjectEx(wsa_event, (DWORD)timeout, FALSE); - WSACloseEvent(wsa_event); - if (ret != WAIT_OBJECT_0) { - return FALSE; + if ((network_events.lNetworkEvents & FD_WRITE) == 0) { + return false; } - - /* Detect success/failure. */ - wsa_event = WSACreateEvent(); - if (wsa_event == WSA_INVALID_EVENT) { - return FALSE; - } - - if (WSAEventSelect(sock, wsa_event, FD_CLOSE) == SOCKET_ERROR) { - WSACloseEvent(wsa_event); - return FALSE; + if (network_events.lNetworkEvents & FD_CLOSE) { + return false; } - ret = WaitForSingleObjectEx(wsa_event, 0, FALSE); - WSACloseEvent(wsa_event); - if (ret == WAIT_OBJECT_0) { - return FALSE; - } - - return TRUE; + return true; } -static bool_t hdhomerun_sock_wait_for_event(hdhomerun_sock_t sock, long event_type, uint64_t stop_time) +bool hdhomerun_sock_send(struct hdhomerun_sock_t *sock, const void *data, size_t length, uint64_t timeout) { - uint64_t current_time = getcurrenttime(); - if (current_time >= stop_time) { - return FALSE; - } - - WSAEVENT wsa_event = WSACreateEvent(); - if (wsa_event == WSA_INVALID_EVENT) { - return FALSE; - } - - if (WSAEventSelect(sock, wsa_event, event_type) == SOCKET_ERROR) { - WSACloseEvent(wsa_event); - return FALSE; + if (!hdhomerun_sock_event_select(sock, FD_WRITE | FD_CLOSE)) { + return false; } - DWORD ret = WaitForSingleObjectEx(wsa_event, (DWORD)(stop_time - current_time), FALSE); - WSACloseEvent(wsa_event); - - if (ret != WAIT_OBJECT_0) { - return FALSE; - } - - return TRUE; -} - -bool_t hdhomerun_sock_send(hdhomerun_sock_t sock, const void *data, size_t length, uint64_t timeout) -{ uint64_t stop_time = getcurrenttime() + timeout; const uint8_t *ptr = (uint8_t *)data; while (1) { - int ret = send(sock, (char *)ptr, (int)length, 0); - if (ret <= 0) { - if (WSAGetLastError() != WSAEWOULDBLOCK) { - return FALSE; - } - if (!hdhomerun_sock_wait_for_event(sock, FD_WRITE | FD_CLOSE, stop_time)) { - return FALSE; - } - continue; + int ret = send(sock->sock, (char *)ptr, (int)length, 0); + if (ret >= (int)length) { + return true; + } + + if ((ret == SOCKET_ERROR) && (WSAGetLastError() != WSAEWOULDBLOCK)) { + return false; } - if (ret < (int)length) { + if (ret > 0) { ptr += ret; length -= ret; - continue; } - return TRUE; + uint64_t current_time = getcurrenttime(); + if (current_time >= stop_time) { + return false; + } + + if (WaitForSingleObjectEx(sock->event, (DWORD)(stop_time - current_time), false) != WAIT_OBJECT_0) { + return false; + } } } -bool_t hdhomerun_sock_sendto(hdhomerun_sock_t sock, uint32_t remote_addr, uint16_t remote_port, const void *data, size_t length, uint64_t timeout) +bool hdhomerun_sock_sendto(struct hdhomerun_sock_t *sock, uint32_t remote_addr, uint16_t remote_port, const void *data, size_t length, uint64_t timeout) { - uint64_t stop_time = getcurrenttime() + timeout; - const uint8_t *ptr = (uint8_t *)data; + if (!hdhomerun_sock_event_select(sock, FD_WRITE | FD_CLOSE)) { + return false; + } - while (1) { - struct sockaddr_in sock_addr; - memset(&sock_addr, 0, sizeof(sock_addr)); - sock_addr.sin_family = AF_INET; - sock_addr.sin_addr.s_addr = htonl(remote_addr); - sock_addr.sin_port = htons(remote_port); - - int ret = sendto(sock, (char *)ptr, (int)length, 0, (struct sockaddr *)&sock_addr, sizeof(sock_addr)); - if (ret <= 0) { - if (WSAGetLastError() != WSAEWOULDBLOCK) { - return FALSE; - } - if (!hdhomerun_sock_wait_for_event(sock, FD_WRITE | FD_CLOSE, stop_time)) { - return FALSE; - } - continue; - } + struct sockaddr_in sock_addr; + memset(&sock_addr, 0, sizeof(sock_addr)); + sock_addr.sin_family = AF_INET; + sock_addr.sin_addr.s_addr = htonl(remote_addr); + sock_addr.sin_port = htons(remote_port); - if (ret < (int)length) { - ptr += ret; - length -= ret; - continue; - } + int ret = sendto(sock->sock, (char *)data, (int)length, 0, (struct sockaddr *)&sock_addr, sizeof(sock_addr)); + if (ret >= (int)length) { + return true; + } + + if (ret >= 0) { + return false; + } + if (WSAGetLastError() != WSAEWOULDBLOCK) { + return false; + } - return TRUE; + if (WaitForSingleObjectEx(sock->event, (DWORD)timeout, false) != WAIT_OBJECT_0) { + return false; } + + ret = sendto(sock->sock, (char *)data, (int)length, 0, (struct sockaddr *)&sock_addr, sizeof(sock_addr)); + if (ret >= (int)length) { + return true; + } + + return false; } -bool_t hdhomerun_sock_recv(hdhomerun_sock_t sock, void *data, size_t *length, uint64_t timeout) +bool hdhomerun_sock_recv(struct hdhomerun_sock_t *sock, void *data, size_t *length, uint64_t timeout) { - uint64_t stop_time = getcurrenttime() + timeout; + if (!hdhomerun_sock_event_select(sock, FD_READ | FD_CLOSE)) { + return false; + } - while (1) { - int ret = recv(sock, (char *)data, (int)(*length), 0); - if (ret < 0) { - if (WSAGetLastError() != WSAEWOULDBLOCK) { - return FALSE; - } - if (!hdhomerun_sock_wait_for_event(sock, FD_READ | FD_CLOSE, stop_time)) { - return FALSE; - } - continue; - } + int ret = recv(sock->sock, (char *)data, (int)(*length), 0); + if (ret > 0) { + *length = ret; + return true; + } - if (ret == 0) { - return FALSE; - } + if (ret == 0) { + return false; + } + if (WSAGetLastError() != WSAEWOULDBLOCK) { + return false; + } + if (WaitForSingleObjectEx(sock->event, (DWORD)timeout, false) != WAIT_OBJECT_0) { + return false; + } + + ret = recv(sock->sock, (char *)data, (int)(*length), 0); + if (ret > 0) { *length = ret; - return TRUE; + return true; } + + return false; } -bool_t hdhomerun_sock_recvfrom(hdhomerun_sock_t sock, uint32_t *remote_addr, uint16_t *remote_port, void *data, size_t *length, uint64_t timeout) +bool hdhomerun_sock_recvfrom(struct hdhomerun_sock_t *sock, uint32_t *remote_addr, uint16_t *remote_port, void *data, size_t *length, uint64_t timeout) { - uint64_t stop_time = getcurrenttime() + timeout; + if (!hdhomerun_sock_event_select(sock, FD_READ | FD_CLOSE)) { + return false; + } - while (1) { - struct sockaddr_in sock_addr; - memset(&sock_addr, 0, sizeof(sock_addr)); - int sockaddr_size = sizeof(sock_addr); - - int ret = recvfrom(sock, (char *)data, (int)(*length), 0, (struct sockaddr *)&sock_addr, &sockaddr_size); - if (ret < 0) { - if (WSAGetLastError() != WSAEWOULDBLOCK) { - return FALSE; - } - if (!hdhomerun_sock_wait_for_event(sock, FD_READ | FD_CLOSE, stop_time)) { - return FALSE; - } - continue; - } + struct sockaddr_in sock_addr; + memset(&sock_addr, 0, sizeof(sock_addr)); + int sockaddr_size = sizeof(sock_addr); - if (ret == 0) { - return FALSE; - } + int ret = recvfrom(sock->sock, (char *)data, (int)(*length), 0, (struct sockaddr *)&sock_addr, &sockaddr_size); + if (ret > 0) { + *remote_addr = ntohl(sock_addr.sin_addr.s_addr); + *remote_port = ntohs(sock_addr.sin_port); + *length = ret; + return true; + } + if (ret == 0) { + return false; + } + if (WSAGetLastError() != WSAEWOULDBLOCK) { + return false; + } + + if (WaitForSingleObjectEx(sock->event, (DWORD)timeout, false) != WAIT_OBJECT_0) { + return false; + } + + ret = recvfrom(sock->sock, (char *)data, (int)(*length), 0, (struct sockaddr *)&sock_addr, &sockaddr_size); + if (ret > 0) { *remote_addr = ntohl(sock_addr.sin_addr.s_addr); *remote_port = ntohs(sock_addr.sin_port); *length = ret; - return TRUE; + return true; } + + return false; }
View file
libhdhomerun_20150826.tgz/hdhomerun_types.h -> libhdhomerun_20190621.tgz/hdhomerun_types.h
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_types.h * - * Copyright © 2008-2009 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2008-2015 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -29,9 +29,9 @@ struct hdhomerun_tuner_status_t { char channel[32]; char lock_str[32]; - bool_t signal_present; - bool_t lock_supported; - bool_t lock_unsupported; + bool signal_present; + bool lock_supported; + bool lock_unsupported; unsigned int signal_strength; unsigned int signal_to_noise_quality; unsigned int symbol_error_quality; @@ -45,9 +45,9 @@ char auth[32]; char cci[32]; char cgms[32]; - bool_t not_subscribed; - bool_t not_available; - bool_t copy_protected; + bool not_subscribed; + bool not_available; + bool copy_protected; }; struct hdhomerun_channelscan_program_t { @@ -68,8 +68,8 @@ struct hdhomerun_tuner_status_t status; int program_count; struct hdhomerun_channelscan_program_t programs[HDHOMERUN_CHANNELSCAN_MAX_PROGRAM_COUNT]; - bool_t transport_stream_id_detected; - bool_t original_network_id_detected; + bool transport_stream_id_detected; + bool original_network_id_detected; uint16_t transport_stream_id; uint16_t original_network_id; };
View file
libhdhomerun_20150826.tgz/hdhomerun_video.c -> libhdhomerun_20190621.tgz/hdhomerun_video.c
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_video.c * - * Copyright © 2006-2010 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2006-2016 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -21,9 +21,14 @@ #include "hdhomerun.h" struct hdhomerun_video_sock_t { - pthread_mutex_t lock; + thread_mutex_t lock; struct hdhomerun_debug_t *dbg; - hdhomerun_sock_t sock; + struct hdhomerun_sock_t *sock; + + uint32_t keepalive_lockkey; + uint32_t keepalive_addr; + uint16_t keepalive_port; + volatile bool keepalive_start; volatile size_t head; volatile size_t tail; @@ -31,8 +36,8 @@ size_t buffer_size; size_t advance; - pthread_t thread; - volatile bool_t terminate; + thread_task_t thread; + volatile bool terminate; volatile uint32_t packet_count; volatile uint32_t transport_error_count; @@ -44,9 +49,9 @@ volatile uint8_t sequence[0x2000]; }; -static THREAD_FUNC_PREFIX hdhomerun_video_thread_execute(void *arg); +static void hdhomerun_video_thread_execute(void *arg); -struct hdhomerun_video_sock_t *hdhomerun_video_create(uint16_t listen_port, bool_t allow_port_reuse, size_t buffer_size, struct hdhomerun_debug_t *dbg) +struct hdhomerun_video_sock_t *hdhomerun_video_create(uint16_t listen_port, bool allow_port_reuse, size_t buffer_size, struct hdhomerun_debug_t *dbg) { /* Create object. */ struct hdhomerun_video_sock_t *vs = (struct hdhomerun_video_sock_t *)calloc(1, sizeof(struct hdhomerun_video_sock_t)); @@ -56,8 +61,7 @@ } vs->dbg = dbg; - vs->sock = HDHOMERUN_SOCK_INVALID; - pthread_mutex_init(&vs->lock, NULL); + thread_mutex_init(&vs->lock); /* Reset sequence tracking. */ hdhomerun_video_flush(vs); @@ -79,14 +83,13 @@ /* Create socket. */ vs->sock = hdhomerun_sock_create_udp(); - if (vs->sock == HDHOMERUN_SOCK_INVALID) { + if (!vs->sock) { hdhomerun_debug_printf(dbg, "hdhomerun_video_create: failed to allocate socket\n"); goto error; } /* Expand socket buffer size. */ - int rx_size = 1024 * 1024; - setsockopt(vs->sock, SOL_SOCKET, SO_RCVBUF, (char *)&rx_size, sizeof(rx_size)); + hdhomerun_sock_set_recv_buffer_size(vs->sock, 1024 * 1024); /* Bind socket. */ if (!hdhomerun_sock_bind(vs->sock, INADDR_ANY, listen_port, allow_port_reuse)) { @@ -95,7 +98,7 @@ } /* Start thread. */ - if (pthread_create(&vs->thread, NULL, &hdhomerun_video_thread_execute, vs) != 0) { + if (!thread_task_create(&vs->thread, &hdhomerun_video_thread_execute, vs)) { hdhomerun_debug_printf(dbg, "hdhomerun_video_create: failed to start thread\n"); goto error; } @@ -104,28 +107,48 @@ return vs; error: - if (vs->sock != HDHOMERUN_SOCK_INVALID) { + if (vs->sock) { hdhomerun_sock_destroy(vs->sock); } + if (vs->buffer) { free(vs->buffer); } + + thread_mutex_dispose(&vs->lock); + free(vs); return NULL; } void hdhomerun_video_destroy(struct hdhomerun_video_sock_t *vs) { - vs->terminate = TRUE; - pthread_join(vs->thread, NULL); + vs->terminate = true; + thread_task_join(vs->thread); hdhomerun_sock_destroy(vs->sock); + thread_mutex_dispose(&vs->lock); free(vs->buffer); free(vs); } -hdhomerun_sock_t hdhomerun_video_get_sock(struct hdhomerun_video_sock_t *vs) +void hdhomerun_video_set_keepalive(struct hdhomerun_video_sock_t *vs, uint32_t remote_addr, uint16_t remote_port, uint32_t lockkey) +{ + thread_mutex_lock(&vs->lock); + + vs->keepalive_addr = remote_addr; + vs->keepalive_port = remote_port; + vs->keepalive_lockkey = lockkey; + + if ((remote_addr != 0) && (remote_port != 0)) { + vs->keepalive_start = true; + } + + thread_mutex_unlock(&vs->lock); +} + +struct hdhomerun_sock_t *hdhomerun_video_get_sock(struct hdhomerun_video_sock_t *vs) { return vs->sock; } @@ -160,18 +183,26 @@ static void hdhomerun_video_stats_ts_pkt(struct hdhomerun_video_sock_t *vs, uint8_t *ptr) { - uint16_t packet_identifier = ((uint16_t)(ptr[1] & 0x1F) << 8) | (uint16_t)ptr[2]; - if (packet_identifier == 0x1FFF) { - return; - } + uint16_t packet_identifier; + packet_identifier = (uint16_t)(ptr[1] & 0x1F) << 8; + packet_identifier |= (uint16_t)ptr[2] << 0; - bool_t transport_error = ptr[1] >> 7; + bool transport_error = (ptr[1] & 0x80) != 0; if (transport_error) { vs->transport_error_count++; vs->sequence[packet_identifier] = 0xFF; return; } + if (packet_identifier == 0x1FFF) { + return; + } + + bool payload_present = (ptr[3] & 0x10) != 0; + if (!payload_present) { + return; + } + uint8_t sequence = ptr[3] & 0x0F; uint8_t previous_sequence = vs->sequence[packet_identifier]; @@ -183,9 +214,6 @@ if (sequence == ((previous_sequence + 1) & 0x0F)) { return; } - if (sequence == previous_sequence) { - return; - } vs->sequence_error_count++; } @@ -219,26 +247,51 @@ } } -static THREAD_FUNC_PREFIX hdhomerun_video_thread_execute(void *arg) +static void hdhomerun_video_thread_send_keepalive(struct hdhomerun_video_sock_t *vs) +{ + thread_mutex_lock(&vs->lock); + uint32_t keepalive_lockkey = vs->keepalive_lockkey; + uint32_t keepalive_addr = vs->keepalive_addr; + uint16_t keepalive_port = vs->keepalive_port; + vs->keepalive_start = false; + thread_mutex_unlock(&vs->lock); + + if ((keepalive_addr == 0) || (keepalive_port == 0)) { + return; + } + + struct hdhomerun_pkt_t pkt; + hdhomerun_pkt_reset(&pkt); + hdhomerun_pkt_write_u32(&pkt, keepalive_lockkey); + hdhomerun_sock_sendto(vs->sock, keepalive_addr, keepalive_port, pkt.start, pkt.end - pkt.start, 25); +} + +static void hdhomerun_video_thread_execute(void *arg) { struct hdhomerun_video_sock_t *vs = (struct hdhomerun_video_sock_t *)arg; - struct hdhomerun_pkt_t pkt_inst; + uint64_t send_time = getcurrenttime(); while (!vs->terminate) { - struct hdhomerun_pkt_t *pkt = &pkt_inst; - hdhomerun_pkt_reset(pkt); + uint64_t current_time = getcurrenttime(); + if (vs->keepalive_start || (current_time >= send_time)) { + hdhomerun_video_thread_send_keepalive(vs); + send_time = current_time + 1000; + } /* Receive. */ + struct hdhomerun_pkt_t pkt; + hdhomerun_pkt_reset(&pkt); + size_t length = VIDEO_RTP_DATA_PACKET_SIZE; - if (!hdhomerun_sock_recv(vs->sock, pkt->end, &length, 25)) { + if (!hdhomerun_sock_recv(vs->sock, pkt.end, &length, 25)) { continue; } - pkt->end += length; + pkt.end += length; if (length == VIDEO_RTP_DATA_PACKET_SIZE) { - hdhomerun_video_parse_rtp(vs, pkt); - length = (int)(pkt->end - pkt->pos); + hdhomerun_video_parse_rtp(vs, &pkt); + length = pkt.end - pkt.pos; } if (length != VIDEO_DATA_PACKET_SIZE) { @@ -246,12 +299,12 @@ continue; } - pthread_mutex_lock(&vs->lock); + thread_mutex_lock(&vs->lock); /* Store in ring buffer. */ size_t head = vs->head; uint8_t *ptr = vs->buffer + head; - memcpy(ptr, pkt->pos, length); + memcpy(ptr, pkt.pos, length); /* Stats. */ vs->packet_count++; @@ -272,21 +325,19 @@ /* Check for buffer overflow. */ if (head == vs->tail) { vs->overflow_error_count++; - pthread_mutex_unlock(&vs->lock); + thread_mutex_unlock(&vs->lock); continue; } vs->head = head; - pthread_mutex_unlock(&vs->lock); + thread_mutex_unlock(&vs->lock); } - - return NULL; } uint8_t *hdhomerun_video_recv(struct hdhomerun_video_sock_t *vs, size_t max_size, size_t *pactual_size) { - pthread_mutex_lock(&vs->lock); + thread_mutex_lock(&vs->lock); size_t head = vs->head; size_t tail = vs->tail; @@ -303,7 +354,7 @@ if (head == tail) { vs->advance = 0; *pactual_size = 0; - pthread_mutex_unlock(&vs->lock); + thread_mutex_unlock(&vs->lock); return NULL; } @@ -311,7 +362,7 @@ if (size == 0) { vs->advance = 0; *pactual_size = 0; - pthread_mutex_unlock(&vs->lock); + thread_mutex_unlock(&vs->lock); return NULL; } @@ -328,13 +379,13 @@ *pactual_size = size; uint8_t *result = vs->buffer + tail; - pthread_mutex_unlock(&vs->lock); + thread_mutex_unlock(&vs->lock); return result; } void hdhomerun_video_flush(struct hdhomerun_video_sock_t *vs) { - pthread_mutex_lock(&vs->lock); + thread_mutex_lock(&vs->lock); vs->tail = vs->head; vs->advance = 0; @@ -352,7 +403,7 @@ vs->sequence_error_count = 0; vs->overflow_error_count = 0; - pthread_mutex_unlock(&vs->lock); + thread_mutex_unlock(&vs->lock); } void hdhomerun_video_debug_print_stats(struct hdhomerun_video_sock_t *vs) @@ -371,7 +422,7 @@ { memset(stats, 0, sizeof(struct hdhomerun_video_stats_t)); - pthread_mutex_lock(&vs->lock); + thread_mutex_lock(&vs->lock); stats->packet_count = vs->packet_count; stats->network_error_count = vs->network_error_count; @@ -379,5 +430,5 @@ stats->sequence_error_count = vs->sequence_error_count; stats->overflow_error_count = vs->overflow_error_count; - pthread_mutex_unlock(&vs->lock); + thread_mutex_unlock(&vs->lock); }
View file
libhdhomerun_20150826.tgz/hdhomerun_video.h -> libhdhomerun_20190621.tgz/hdhomerun_video.h
Changed
@@ -1,7 +1,7 @@ /* * hdhomerun_video.h * - * Copyright © 2006 Silicondust USA Inc. <www.silicondust.com>. + * Copyright © 2006-2016 Silicondust USA Inc. <www.silicondust.com>. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -48,21 +48,26 @@ * * When no longer needed, the socket should be destroyed by calling hdhomerun_control_destroy. */ -extern LIBTYPE struct hdhomerun_video_sock_t *hdhomerun_video_create(uint16_t listen_port, bool_t allow_port_reuse, size_t buffer_size, struct hdhomerun_debug_t *dbg); -extern LIBTYPE void hdhomerun_video_destroy(struct hdhomerun_video_sock_t *vs); +extern LIBHDHOMERUN_API struct hdhomerun_video_sock_t *hdhomerun_video_create(uint16_t listen_port, bool allow_port_reuse, size_t buffer_size, struct hdhomerun_debug_t *dbg); +extern LIBHDHOMERUN_API void hdhomerun_video_destroy(struct hdhomerun_video_sock_t *vs); + +/* + * Configure to send a keepalive packet every second. + */ +extern LIBHDHOMERUN_API void hdhomerun_video_set_keepalive(struct hdhomerun_video_sock_t *vs, uint32_t remote_addr, uint16_t remote_port, uint32_t lockkey); /* * Get the port the socket is listening on. * * Returns 16-bit port with native endianness, or 0 on error. */ -extern LIBTYPE uint16_t hdhomerun_video_get_local_port(struct hdhomerun_video_sock_t *vs); +extern LIBHDHOMERUN_API uint16_t hdhomerun_video_get_local_port(struct hdhomerun_video_sock_t *vs); /* * Join/leave multicast group. */ -extern LIBTYPE int hdhomerun_video_join_multicast_group(struct hdhomerun_video_sock_t *vs, uint32_t multicast_ip, uint32_t local_ip); -extern LIBTYPE void hdhomerun_video_leave_multicast_group(struct hdhomerun_video_sock_t *vs, uint32_t multicast_ip, uint32_t local_ip); +extern LIBHDHOMERUN_API int hdhomerun_video_join_multicast_group(struct hdhomerun_video_sock_t *vs, uint32_t multicast_ip, uint32_t local_ip); +extern LIBHDHOMERUN_API void hdhomerun_video_leave_multicast_group(struct hdhomerun_video_sock_t *vs, uint32_t multicast_ip, uint32_t local_ip); /* * Read data from buffer. @@ -81,23 +86,23 @@ * The buffer is implemented as a ring buffer. It is possible for this function to return a small * amount of data when more is available due to the wrap-around case. */ -extern LIBTYPE uint8_t *hdhomerun_video_recv(struct hdhomerun_video_sock_t *vs, size_t max_size, size_t *pactual_size); +extern LIBHDHOMERUN_API uint8_t *hdhomerun_video_recv(struct hdhomerun_video_sock_t *vs, size_t max_size, size_t *pactual_size); /* * Flush the buffer. */ -extern LIBTYPE void hdhomerun_video_flush(struct hdhomerun_video_sock_t *vs); +extern LIBHDHOMERUN_API void hdhomerun_video_flush(struct hdhomerun_video_sock_t *vs); /* * Debug print internal stats. */ -extern LIBTYPE void hdhomerun_video_debug_print_stats(struct hdhomerun_video_sock_t *vs); -extern LIBTYPE void hdhomerun_video_get_stats(struct hdhomerun_video_sock_t *vs, struct hdhomerun_video_stats_t *stats); +extern LIBHDHOMERUN_API void hdhomerun_video_debug_print_stats(struct hdhomerun_video_sock_t *vs); +extern LIBHDHOMERUN_API void hdhomerun_video_get_stats(struct hdhomerun_video_sock_t *vs, struct hdhomerun_video_stats_t *stats); /* * Internal use only. */ -extern LIBTYPE hdhomerun_sock_t hdhomerun_video_get_sock(struct hdhomerun_video_sock_t *vs); +extern LIBHDHOMERUN_API struct hdhomerun_sock_t *hdhomerun_video_get_sock(struct hdhomerun_video_sock_t *vs); #ifdef __cplusplus }
Locations
Projects
Search
Status Monitor
Help
Open Build Service
OBS Manuals
API Documentation
OBS Portal
Reporting a Bug
Contact
Mailing List
Forums
Chat (IRC)
Twitter
Open Build Service (OBS)
is an
openSUSE project
.