Compare commits
	
		
			26 Commits
		
	
	
		
			release-1.
			...
			release-1.
		
	
	| Author | SHA1 | Date | |
|---|---|---|---|
|   | 46cc47b167 | ||
|   | 13a1fff7a1 | ||
|   | c9463545a8 | ||
|   | de1d7e81a3 | ||
|   | f87dbf8115 | ||
|   | 83ee32afb7 | ||
|   | 4f960c4e34 | ||
|   | c85537df11 | ||
|   | 20905cb7a7 | ||
|   | 5b744169d5 | ||
|   | c69e16b347 | ||
|   | cb7e6b7472 | ||
|   | fd80e5a8ff | ||
|   | b29de32110 | ||
|   | 6455ac6eea | ||
|   | f7bb1f9582 | ||
|   | 0728ab3b25 | ||
|   | cb9ee8254c | ||
|   | f08fdac9b6 | ||
|   | 0db035cc7b | ||
|   | da11e52924 | ||
|   | bc7b0c9d4d | ||
|   | b2757d9d55 | ||
|   | 7967a0cd45 | ||
|   | 67b51187b9 | ||
|   | 491f5ffef6 | 
							
								
								
									
										64
									
								
								ChangeLog
									
									
									
									
									
								
							
							
						
						
									
										64
									
								
								ChangeLog
									
									
									
									
									
								
							| @@ -1,3 +1,67 @@ | ||||
| ******************************************************************************* | ||||
| Version 1.6.1 | ||||
| ******************************************************************************* | ||||
|  | ||||
| 2007-11-07 Marcelo Jimenez <mroberto(at)users.sourceforge.net> | ||||
| 	* SF Bug Tracker [ 1825278 ] AdvertiseAndReply sleeps with handle lock out | ||||
| 	Applied patch from Alex (afaucher) to change some write locks to read | ||||
| 	locks. | ||||
|  | ||||
| 2007-11-06 Marcelo Jimenez <mroberto(at)users.sourceforge.net> | ||||
| 	* Adjusting libtool library numbers to reflect the last changes. | ||||
|  | ||||
| 2007-11-06 Marcelo Jimenez <mroberto(at)users.sourceforge.net> | ||||
| 	* SF Bug Tracker [ 1825278 ] AdvertiseAndReply sleeps with handle lock out | ||||
| 	GlobalHndMutex, which was a mutex is now GlobalHndRWLock, which is a | ||||
| 	rwlock. HandleLock() is mapped to HandleWriteLock() while all other | ||||
| 	instances have not been checked. One instance in AdvertiseAndReply() | ||||
| 	has been changed to HandleReadLock(). Thanks to Alex (afaucher) for the  | ||||
| 	bug report and suggestions. | ||||
|  | ||||
| 2007-11-06 Marcelo Jimenez <mroberto(at)users.sourceforge.net> | ||||
| 	* Added support for rwlocks. | ||||
|  | ||||
| 2007-11-05 Marcelo Jimenez <mroberto(at)users.sourceforge.net> | ||||
| 	* SF Bug Tracker [ 1825929 ] woker thread still alive after UpnpFinish() | ||||
| 	Submitted By: Luke Kim - nereusuj | ||||
| 	Worker thread still alive after calling UpnpFinish() because | ||||
| 	ThreadPoolShutdown() is in the #ifdef DEBUG block. | ||||
| 	421 | ||||
| 	422 #ifdef DEBUG | ||||
| 	423 ThreadPoolShutdown( &gSendThreadPool ); | ||||
| 	424 ThreadPoolShutdown( &gRecvThreadPool ); | ||||
|  | ||||
| 2007-08-28 Marcelo Jimenez <mroberto(at)users.sourceforge.net> | ||||
| 	* Changed the calls to virtualDirCallback.open(filename, UPNP_WRITE) | ||||
| 	to (virtualDirCallback.open)(filename, UPNP_WRITE) (notice the | ||||
| 	parenthesis) due to a change in glibc that produces compilation | ||||
| 	errors. | ||||
|  | ||||
| 2007-08-28 Marcelo Jimenez <mroberto(at)users.sourceforge.net> | ||||
| 	* Initialization of the "randomness" struct so that valgrind does not | ||||
| 	complain. | ||||
|  | ||||
| 2007-08-06 Marcelo Jimenez <mroberto(at)users.sourceforge.net> | ||||
| 	* Merge of patch submitted By Keith Brindley - brindlk | ||||
| 	SF Bug Tracker [ 1762758 ] Seek not working for large files | ||||
| 	Problem: | ||||
| 	Requests from the uPnP client to seek to a position beyond 2GB in a large | ||||
| 	file are handled as a request to see from the 2GB point. | ||||
|  | ||||
| 	Impact: | ||||
| 	Varies depending on client. The Xbox 360 kills the connection when it | ||||
| 	realises. | ||||
|  | ||||
| 	Solution: | ||||
| 	GetNextRange function (webserver.c) is updated to handle large file sizes. | ||||
| 	Fix should also recognise when built on a 32bit platform rather than 64 and | ||||
| 	handle accordingly. | ||||
|  | ||||
| 2007-08-05 Marcelo Jimenez <mroberto(at)users.sourceforge.net> | ||||
| 	* Merge of Mac OS X patch from St<53>phane Corth<74>sy (davelopper), | ||||
| 	SF Bug Tracker [ 1686420 ] Modifications for MacOSX. | ||||
| 	Some of the proposed changes were already done by Rene Hexel's patch. | ||||
|  | ||||
| ******************************************************************************* | ||||
| Version 1.6.0 | ||||
| ******************************************************************************* | ||||
|   | ||||
							
								
								
									
										5
									
								
								THANKS
									
									
									
									
									
								
							
							
						
						
									
										5
									
								
								THANKS
									
									
									
									
									
								
							| @@ -6,6 +6,7 @@ suggesting various improvements or submitting actual code. | ||||
| Here is a list of these people. Help us keep it complete and | ||||
| exempt of errors. | ||||
|  | ||||
| - Alex (afaucher) | ||||
| - Arno Willig | ||||
| - Bob Ciora | ||||
| - Chaos | ||||
| @@ -20,10 +21,11 @@ exempt of errors. | ||||
| - Jiri Zouhar | ||||
| - John Dennis | ||||
| - Jonathan (no_dice) | ||||
| - Keith Brindley | ||||
| - Leuk_He | ||||
| - Loigu | ||||
| - Luke Kim | ||||
| - Marcelo Roberto Jimenez | ||||
| - Marcelo Roberto Jimenez (mroberto) | ||||
| - Markus Strobl | ||||
| - Nektarios K. Papadopoulos | ||||
| - Oskar Liljeblad | ||||
| @@ -31,6 +33,7 @@ exempt of errors. | ||||
| - Paul Vixie | ||||
| - Rene Hexel | ||||
| - Siva Chandran | ||||
| - Stéphane Corthésy | ||||
| - Timothy Redaelli | ||||
| - Titus Winters | ||||
|  | ||||
|   | ||||
| @@ -261,7 +261,7 @@ | ||||
|  | ||||
| /** @name Other debugging features | ||||
|           The UPnP SDK contains other features to aid in debugging: | ||||
| 	  see <upnp/upnpdebug.h> | ||||
| 	  see <upnp/inc/upnpdebug.h> | ||||
|  */ | ||||
|  | ||||
| #define DEBUG_ALL		1 | ||||
|   | ||||
							
								
								
									
										50
									
								
								configure.ac
									
									
									
									
									
								
							
							
						
						
									
										50
									
								
								configure.ac
									
									
									
									
									
								
							| @@ -4,14 +4,15 @@ | ||||
| # | ||||
| # Process this file with autoconf to produce a configure script. | ||||
| # | ||||
| # (C) Copyright 2005-2006 R<>mi Turboult <r3mi@users.sourceforge.net> | ||||
| # (C) Copyright 2005-2007 R<>mi Turboult <r3mi@users.sourceforge.net> | ||||
| # | ||||
|  | ||||
| AC_PREREQ(2.60) | ||||
|  | ||||
| AC_INIT([libupnp], [1.6.0], [mroberto@users.sourceforge.net]) | ||||
| AC_INIT([libupnp], [1.6.1], [mroberto@users.sourceforge.net]) | ||||
| ############################################################################### | ||||
| # *Independently* of the above libupnp package version, the libtool version | ||||
| # of the 3 libraries need to be updated whenever there is a change released : | ||||
| # of the 3 libraries need to be updated whenever there is a change released: | ||||
| # "current:revision:age" (this is NOT the same as the package version), where: | ||||
| # 	- library code modified:		revision++ | ||||
| # 	- interfaces changed/added/removed:	current++ and revision=0 | ||||
| @@ -19,11 +20,14 @@ AC_INIT([libupnp], [1.6.0], [mroberto@users.sourceforge.net]) | ||||
| # 	- interfaces removed:			age=0 | ||||
| # *please update only once, before a formal release, not for each change* | ||||
| # | ||||
| # For release 1.4.1, we had: | ||||
| ############################################################################### | ||||
| # Release 1.4.1: | ||||
| #AC_SUBST([LT_VERSION_IXML],       [2:2:0]) | ||||
| #AC_SUBST([LT_VERSION_THREADUTIL], [2:2:0]) | ||||
| #AC_SUBST([LT_VERSION_UPNP],       [2:2:0]) | ||||
| # | ||||
| ############################################################################### | ||||
| # Release 1.4.6: | ||||
| # "current:revision:age" | ||||
| # | ||||
| # - Code has changed in ixml | ||||
| @@ -37,11 +41,12 @@ AC_INIT([libupnp], [1.6.0], [mroberto@users.sourceforge.net]) | ||||
| # - Code has changed in upnp | ||||
| #	revision: 2 -> 3 | ||||
| # | ||||
| # For release 1.4.6, we had: | ||||
| #AC_SUBST([LT_VERSION_IXML],       [2:3:0]) | ||||
| #AC_SUBST([LT_VERSION_THREADUTIL], [3:0:1]) | ||||
| #AC_SUBST([LT_VERSION_UPNP],       [2:3:0]) | ||||
| # | ||||
| ############################################################################### | ||||
| # Release 1.6.0: | ||||
| # "current:revision:age" | ||||
| # | ||||
| # - Code has changed in ixml | ||||
| @@ -56,21 +61,50 @@ AC_INIT([libupnp], [1.6.0], [mroberto@users.sourceforge.net]) | ||||
| # - Interface removed in upnp | ||||
| #	age: 0 -> 0 | ||||
| # | ||||
| # For release 1.6.0, we had: | ||||
| #AC_SUBST([LT_VERSION_IXML],       [2:4:0]) | ||||
| #AC_SUBST([LT_VERSION_THREADUTIL], [3:1:1]) | ||||
| #AC_SUBST([LT_VERSION_UPNP],       [3:0:0]) | ||||
| # | ||||
| ############################################################################### | ||||
| # Release 1.6.1: | ||||
| # "current:revision:age" | ||||
| # | ||||
| # - Code has changed in threadutil | ||||
| #	revision: 1 -> 2 | ||||
| # - Interface added in threadutil | ||||
| #	current: 3 -> 4 | ||||
| #	revision: 2 -> 0 | ||||
| # - Interface added in threadutil | ||||
| #	age: 1 -> 2 | ||||
| # - Code has changed in upnp | ||||
| #	revision: 0 -> 1 | ||||
| # | ||||
| #AC_SUBST([LT_VERSION_IXML],       [2:4:0]) | ||||
| #AC_SUBST([LT_VERSION_THREADUTIL], [4:0:2]) | ||||
| #AC_SUBST([LT_VERSION_UPNP],       [3:1:0]) | ||||
| # | ||||
| ############################################################################### | ||||
| AC_SUBST([LT_VERSION_IXML],       [2:4:0]) | ||||
| AC_SUBST([LT_VERSION_THREADUTIL], [3:1:1]) | ||||
| AC_SUBST([LT_VERSION_UPNP],       [3:0:0]) | ||||
| AC_SUBST([LT_VERSION_THREADUTIL], [4:0:2]) | ||||
| AC_SUBST([LT_VERSION_UPNP],       [3:1:0]) | ||||
| ############################################################################### | ||||
| # Repeating the algorithm so that it is closer to the modificatin place: | ||||
| # 	- library code modified:		revision++ | ||||
| # 	- interfaces changed/added/removed:	current++ and revision=0 | ||||
| # 	- interfaces added: 			age++ | ||||
| # 	- interfaces removed:			age=0 | ||||
| # *please update only once, before a formal release, not for each change* | ||||
| ############################################################################### | ||||
|  | ||||
|  | ||||
| AC_CONFIG_AUX_DIR(config.aux) | ||||
| AC_CONFIG_MACRO_DIR(m4) | ||||
| AC_CONFIG_SRCDIR(upnp/inc/upnp.h) | ||||
|  | ||||
|  | ||||
| AM_INIT_AUTOMAKE([1.8 -Wall foreign subdir-objects dist-bzip2]) | ||||
|  | ||||
|  | ||||
| # | ||||
| # Get canonical host names in host and host_os | ||||
| # | ||||
|   | ||||
| @@ -547,6 +547,10 @@ int TPAttrSetMaxJobsTotal(ThreadPoolAttr *attr, int maxJobsTotal); | ||||
| 	EXPORT int ThreadPoolGetStats(ThreadPool *tp, ThreadPoolStats *stats); | ||||
|  | ||||
| 	EXPORT void ThreadPoolPrintStats(ThreadPoolStats *stats); | ||||
| #else | ||||
| 	static UPNP_INLINE int ThreadPoolGetStats(ThreadPool *tp, ThreadPoolStats *stats) {} | ||||
|  | ||||
| 	static UPNP_INLINE void ThreadPoolPrintStats(ThreadPoolStats *stats) {} | ||||
| #endif | ||||
|  | ||||
| #ifdef __cplusplus | ||||
|   | ||||
| @@ -42,131 +42,158 @@ extern "C" { | ||||
| #endif | ||||
|  | ||||
| #ifdef __FreeBSD__ | ||||
| #define PTHREAD_MUTEX_RECURSIVE_NP PTHREAD_MUTEX_RECURSIVE | ||||
| 	#define PTHREAD_MUTEX_RECURSIVE_NP PTHREAD_MUTEX_RECURSIVE | ||||
| #endif | ||||
|  | ||||
| #ifdef PTHREAD_MUTEX_RECURSIVE | ||||
| /* This system has SuS2-compliant mutex attributes. | ||||
|  * E.g. on Cygwin, where we don't have the old nonportable (NP) symbols | ||||
|  */ | ||||
| #define ITHREAD_MUTEX_FAST_NP PTHREAD_MUTEX_NORMAL | ||||
| #define ITHREAD_MUTEX_RECURSIVE_NP PTHREAD_MUTEX_RECURSIVE | ||||
| #define ITHREAD_MUTEX_ERRORCHECK_NP PTHREAD_MUTEX_ERRORCHECK | ||||
| #else | ||||
| #define ITHREAD_MUTEX_FAST_NP PTHREAD_MUTEX_FAST_NP | ||||
| #define ITHREAD_MUTEX_RECURSIVE_NP PTHREAD_MUTEX_RECURSIVE_NP | ||||
| #define ITHREAD_MUTEX_ERRORCHECK_NP PTHREAD_MUTEX_ERRORCHECK_NP | ||||
| #endif | ||||
| 	/* This system has SuS2-compliant mutex attributes. | ||||
| 	 * E.g. on Cygwin, where we don't have the old nonportable (NP) symbols | ||||
| 	 */ | ||||
| 	#define ITHREAD_MUTEX_FAST_NP       PTHREAD_MUTEX_NORMAL | ||||
| 	#define ITHREAD_MUTEX_RECURSIVE_NP  PTHREAD_MUTEX_RECURSIVE | ||||
| 	#define ITHREAD_MUTEX_ERRORCHECK_NP PTHREAD_MUTEX_ERRORCHECK | ||||
| #else /* PTHREAD_MUTEX_RECURSIVE */ | ||||
| 	#define ITHREAD_MUTEX_FAST_NP       PTHREAD_MUTEX_FAST_NP | ||||
| 	#define ITHREAD_MUTEX_RECURSIVE_NP  PTHREAD_MUTEX_RECURSIVE_NP | ||||
| 	#define ITHREAD_MUTEX_ERRORCHECK_NP PTHREAD_MUTEX_ERRORCHECK_NP | ||||
| #endif /* PTHREAD_MUTEX_RECURSIVE */ | ||||
|  | ||||
|  | ||||
| #define ITHREAD_PROCESS_PRIVATE PTHREAD_PROCESS_PRIVATE | ||||
| #define ITHREAD_PROCESS_SHARED  PTHREAD_PROCESS_SHARED | ||||
|  | ||||
|  | ||||
| #define ITHREAD_CANCELED PTHREAD_CANCELED | ||||
|  | ||||
|    | ||||
|   /*************************************************************************** | ||||
|    * Name: ithread_t | ||||
|    * | ||||
|    *  Description: | ||||
|    *      Thread handle. | ||||
|    *      typedef to pthread_t. | ||||
|    *      Internal Use Only. | ||||
|    ***************************************************************************/ | ||||
|   typedef pthread_t ithread_t;  | ||||
| /*************************************************************************** | ||||
|  * Name: ithread_t | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Thread handle. | ||||
|  *      typedef to pthread_t. | ||||
|  *      Internal Use Only. | ||||
|  ***************************************************************************/ | ||||
| typedef pthread_t ithread_t;  | ||||
|    | ||||
|   /**************************************************************************** | ||||
|    * Name: ithread_attr_t | ||||
|    * | ||||
|    *  Description: | ||||
|    *      Thread attribute. | ||||
|    *      typedef to pthread_attr_t | ||||
|    *      Internal Use Only | ||||
|    ***************************************************************************/ | ||||
|   typedef pthread_attr_t ithread_attr_t;	 | ||||
| /**************************************************************************** | ||||
|  * Name: ithread_attr_t | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Thread attribute. | ||||
|  *      typedef to pthread_attr_t | ||||
|  *      Internal Use Only | ||||
|  ***************************************************************************/ | ||||
| typedef pthread_attr_t ithread_attr_t;	 | ||||
|  | ||||
|  | ||||
|   /**************************************************************************** | ||||
|    * Name: start_routine | ||||
|    * | ||||
|    *  Description: | ||||
|    *      Thread start routine  | ||||
|    *      Internal Use Only. | ||||
|    ***************************************************************************/ | ||||
|   typedef void * (*start_routine) (void *arg); | ||||
| /**************************************************************************** | ||||
|  * Name: start_routine | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Thread start routine  | ||||
|  *      Internal Use Only. | ||||
|  ***************************************************************************/ | ||||
| typedef void * (*start_routine) (void *arg); | ||||
|  | ||||
|    | ||||
|   /**************************************************************************** | ||||
|    * Name: ithread_cond_t | ||||
|    * | ||||
|    *  Description: | ||||
|    *      condition variable. | ||||
|    *      typedef to pthread_cond_t | ||||
|    *      Internal Use Only. | ||||
|    ***************************************************************************/ | ||||
|   typedef pthread_cond_t ithread_cond_t; | ||||
| /**************************************************************************** | ||||
|  * Name: ithread_cond_t | ||||
|  * | ||||
|  *  Description: | ||||
|  *      condition variable. | ||||
|  *      typedef to pthread_cond_t | ||||
|  *      Internal Use Only. | ||||
|  ***************************************************************************/ | ||||
| typedef pthread_cond_t ithread_cond_t; | ||||
|  | ||||
|  | ||||
|   /**************************************************************************** | ||||
|    * Name: ithread_mutexattr_t | ||||
|    * | ||||
|    *  Description: | ||||
|    *      Mutex attribute. | ||||
|    *      typedef to pthread_mutexattr_t | ||||
|    *      Internal Use Only | ||||
|    ***************************************************************************/ | ||||
|   typedef pthread_mutexattr_t ithread_mutexattr_t;	 | ||||
| /**************************************************************************** | ||||
|  * Name: ithread_mutexattr_t | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Mutex attribute. | ||||
|  *      typedef to pthread_mutexattr_t | ||||
|  *      Internal Use Only | ||||
|  ***************************************************************************/ | ||||
| typedef pthread_mutexattr_t ithread_mutexattr_t;	 | ||||
|  | ||||
|  | ||||
|   /**************************************************************************** | ||||
|    * Name: ithread_mutex_t | ||||
|    * | ||||
|    *  Description: | ||||
|    *      Mutex. | ||||
|    *      typedef to pthread_mutex_t | ||||
|    *      Internal Use Only. | ||||
|    ***************************************************************************/ | ||||
|   typedef pthread_mutex_t ithread_mutex_t; | ||||
| /**************************************************************************** | ||||
|  * Name: ithread_mutex_t | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Mutex. | ||||
|  *      typedef to pthread_mutex_t | ||||
|  *      Internal Use Only. | ||||
|  ***************************************************************************/ | ||||
| typedef pthread_mutex_t ithread_mutex_t; | ||||
|  | ||||
|  | ||||
|   /**************************************************************************** | ||||
|    * Name: ithread_condattr_t | ||||
|    * | ||||
|    *  Description: | ||||
|    *      Condition attribute. | ||||
|    *      typedef to pthread_condattr_t | ||||
|    *      NOT USED | ||||
|    *      Internal Use Only | ||||
|    ***************************************************************************/ | ||||
|   typedef pthread_condattr_t ithread_condattr_t;	 | ||||
| /**************************************************************************** | ||||
|  * Name: ithread_condattr_t | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Condition attribute. | ||||
|  *      typedef to pthread_condattr_t | ||||
|  *      NOT USED | ||||
|  *      Internal Use Only | ||||
|  ***************************************************************************/ | ||||
| typedef pthread_condattr_t ithread_condattr_t;	 | ||||
|  | ||||
|   /**************************************************************************** | ||||
|    * Function: ithread_mutexattr_init | ||||
|    * | ||||
|    *  Description: | ||||
|    *      Initializes a mutex attribute variable. | ||||
|    *      Used to set the type of the mutex. | ||||
|    *  Parameters: | ||||
|    *      ithread_mutexattr_init * attr (must be valid non NULL pointer to  | ||||
|    *                                     pthread_mutexattr_t) | ||||
|    *  Returns: | ||||
|    *      0 on success, Nonzero on failure. | ||||
|    *      Always returns 0. | ||||
|    *      See man page for pthread_mutexattr_init | ||||
|    ***************************************************************************/ | ||||
|  | ||||
| /**************************************************************************** | ||||
|  * Name: ithread_rwlockattr_t | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Mutex attribute. | ||||
|  *      typedef to pthread_rwlockattr_t | ||||
|  *      Internal Use Only | ||||
|  ***************************************************************************/ | ||||
| typedef pthread_rwlockattr_t ithread_rwlockattr_t;	 | ||||
|  | ||||
|  | ||||
| /**************************************************************************** | ||||
|  * Name: ithread_rwlock_t | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Condition attribute. | ||||
|  *      typedef to pthread_rwlock_t | ||||
|  *      Internal Use Only | ||||
|  ***************************************************************************/ | ||||
| typedef pthread_rwlock_t ithread_rwlock_t;	 | ||||
|  | ||||
| /**************************************************************************** | ||||
|  * Function: ithread_mutexattr_init | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Initializes a mutex attribute variable. | ||||
|  *      Used to set the type of the mutex. | ||||
|  *  Parameters: | ||||
|  *      ithread_mutexattr_init * attr (must be valid non NULL pointer to  | ||||
|  *                                     pthread_mutexattr_t) | ||||
|  *  Returns: | ||||
|  *      0 on success, Nonzero on failure. | ||||
|  *      Always returns 0. | ||||
|  *      See man page for pthread_mutexattr_init | ||||
|  ***************************************************************************/ | ||||
| #define ithread_mutexattr_init pthread_mutexattr_init | ||||
|  | ||||
|   /**************************************************************************** | ||||
|    * Function: ithread_mutexattr_destroy | ||||
|    * | ||||
|    *  Description: | ||||
|    *      Releases any resources held by the mutex attribute. | ||||
|    *      Currently there are no resources associated with the attribute | ||||
|    *  Parameters: | ||||
|    *      ithread_mutexattr_t * attr (must be valid non NULL pointer to  | ||||
|    *                                  pthread_mutexattr_t) | ||||
|    *  Returns: | ||||
|    *      0 on success, Nonzero on failure. | ||||
|    *      Always returns 0. | ||||
|    *      See man page for pthread_mutexattr_destroy | ||||
|    ***************************************************************************/ | ||||
|  | ||||
| /**************************************************************************** | ||||
|  * Function: ithread_mutexattr_destroy | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Releases any resources held by the mutex attribute. | ||||
|  *      Currently there are no resources associated with the attribute | ||||
|  *  Parameters: | ||||
|  *      ithread_mutexattr_t * attr (must be valid non NULL pointer to  | ||||
|  *                                  pthread_mutexattr_t) | ||||
|  *  Returns: | ||||
|  *      0 on success, Nonzero on failure. | ||||
|  *      Always returns 0. | ||||
|  *      See man page for pthread_mutexattr_destroy | ||||
|  ***************************************************************************/ | ||||
| #define ithread_mutexattr_destroy pthread_mutexattr_destroy | ||||
|    | ||||
|    | ||||
| @@ -180,7 +207,7 @@ extern "C" { | ||||
|  *                       ITHREAD_MUTEX_ERRORCHECK_NP | ||||
|  * | ||||
|  *  Parameters: | ||||
|  *      ithread_mutexattr_t * mutex (must be valid non NULL pointer to  | ||||
|  *      ithread_mutexattr_t * attr (must be valid non NULL pointer to  | ||||
|  *                                   ithread_mutexattr_t) | ||||
|  *      int kind (one of ITHREAD_MUTEX_FAST_NP or ITHREAD_MUTEX_RECURSIVE_NP | ||||
|  *                or ITHREAD_MUTEX_ERRORCHECK_NP) | ||||
| @@ -190,9 +217,9 @@ extern "C" { | ||||
|  *      See man page for pthread_mutexattr_setkind_np | ||||
|  *****************************************************************************/ | ||||
| #ifdef PTHREAD_MUTEX_RECURSIVE | ||||
| #define ithread_mutexattr_setkind_np pthread_mutexattr_settype | ||||
| 	#define ithread_mutexattr_setkind_np pthread_mutexattr_settype | ||||
| #else | ||||
| #define ithread_mutexattr_setkind_np pthread_mutexattr_setkind_np | ||||
| 	#define ithread_mutexattr_setkind_np pthread_mutexattr_setkind_np | ||||
| #endif | ||||
|  | ||||
| /**************************************************************************** | ||||
| @@ -205,7 +232,7 @@ extern "C" { | ||||
|  *                       ITHREAD_MUTEX_ERRORCHECK_NP | ||||
|  * | ||||
|  *  Parameters: | ||||
|  *      ithread_mutexattr_t * mutex (must be valid non NULL pointer to  | ||||
|  *      ithread_mutexattr_t * attr (must be valid non NULL pointer to  | ||||
|  *                                   pthread_mutexattr_t) | ||||
|  *      int *kind (one of ITHREAD_MUTEX_FAST_NP or ITHREAD_MUTEX_RECURSIVE_NP | ||||
|  *                or ITHREAD_MUTEX_ERRORCHECK_NP) | ||||
| @@ -215,9 +242,9 @@ extern "C" { | ||||
|  *      See man page for pthread_mutexattr_getkind_np | ||||
|  *****************************************************************************/ | ||||
| #ifdef PTHREAD_MUTEX_RECURSIVE | ||||
| #define ithread_mutexattr_getkind_np pthread_mutexattr_gettype | ||||
| 	#define ithread_mutexattr_getkind_np pthread_mutexattr_gettype | ||||
| #else | ||||
| #define ithread_mutexattr_getkind_np pthread_mutexattr_getkind_np | ||||
| 	#define ithread_mutexattr_getkind_np pthread_mutexattr_getkind_np | ||||
| #endif | ||||
|  | ||||
|    | ||||
| @@ -238,6 +265,7 @@ extern "C" { | ||||
|  *****************************************************************************/ | ||||
| #define ithread_mutex_init pthread_mutex_init | ||||
|  | ||||
|  | ||||
| /**************************************************************************** | ||||
|  * Function: ithread_mutex_lock | ||||
|  * | ||||
| @@ -292,6 +320,169 @@ extern "C" { | ||||
| #define ithread_mutex_destroy pthread_mutex_destroy | ||||
|  | ||||
|  | ||||
| /**************************************************************************** | ||||
|  * Function: ithread_rwlockattr_init | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Initializes a rwlock attribute variable to default values. | ||||
|  *  Parameters: | ||||
|  *      const ithread_rwlockattr_init *attr (must be valid non NULL pointer to  | ||||
|  *                                           pthread_rwlockattr_t) | ||||
|  *  Returns: | ||||
|  *      0 on success, Nonzero on failure. | ||||
|  *      Always returns 0. | ||||
|  *      See man page for pthread_rwlockattr_init | ||||
|  ***************************************************************************/ | ||||
| #define ithread_rwlockattr_init pthread_rwlockattr_init | ||||
|  | ||||
|  | ||||
| /**************************************************************************** | ||||
|  * Function: ithread_rwlockattr_destroy | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Releases any resources held by the rwlock attribute. | ||||
|  *  Parameters: | ||||
|  *      ithread_rwlockattr_t *attr (must be valid non NULL pointer to  | ||||
|  *                                  pthread_rwlockattr_t) | ||||
|  *  Returns: | ||||
|  *      0 on success, Nonzero on failure. | ||||
|  *      Always returns 0. | ||||
|  *      See man page for pthread_rwlockattr_destroy | ||||
|  ***************************************************************************/ | ||||
| #define ithread_rwlockattr_destroy pthread_rwlockattr_destroy | ||||
|    | ||||
|    | ||||
| /**************************************************************************** | ||||
|  * Function: ithread_rwlockatttr_setpshared | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Sets the rwlock type in the attribute. | ||||
|  *      Valid types are: ITHREAD_PROCESS_PRIVATE  | ||||
|  *                       ITHREAD_PROCESS_SHARED | ||||
|  * | ||||
|  *  Parameters: | ||||
|  *      ithread_rwlockattr_t * attr (must be valid non NULL pointer to  | ||||
|  *                                   ithread_rwlockattr_t) | ||||
|  *      int kind (one of ITHREAD_PROCESS_PRIVATE or ITHREAD_PROCESS_SHARED) | ||||
|  * | ||||
|  *  Returns: | ||||
|  *      0 on success. Nonzero on failure. | ||||
|  *      Returns EINVAL if the kind is not supported. | ||||
|  *      See man page for pthread_rwlockattr_setkind_np | ||||
|  *****************************************************************************/ | ||||
| #define ithread_rwlockatttr_setpshared pthread_rwlockatttr_setpshared | ||||
|  | ||||
|  | ||||
| /**************************************************************************** | ||||
|  * Function: ithread_rwlockatttr_getpshared | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Gets the rwlock type in the attribute. | ||||
|  *      Valid types are: ITHREAD_PROCESS_PRIVATE  | ||||
|  *                       ITHREAD_PROCESS_SHARED  | ||||
|  * | ||||
|  *  Parameters: | ||||
|  *      ithread_rwlockattr_t * attr (must be valid non NULL pointer to  | ||||
|  *                                   pthread_rwlockattr_t) | ||||
|  *      int *kind (one of ITHREAD_PROCESS_PRIVATE or ITHREAD_PROCESS_SHARED) | ||||
|  * | ||||
|  *  Returns: | ||||
|  *      0 on success. Nonzero on failure. | ||||
|  *      Always returns 0. | ||||
|  *      See man page for pthread_rwlockatttr_getpshared | ||||
|  *****************************************************************************/ | ||||
| #define ithread_rwlockatttr_getpshared pthread_rwlockatttr_getpshared | ||||
|  | ||||
|    | ||||
| /**************************************************************************** | ||||
|  * Function: ithread_rwlock_init | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Initializes rwlock. | ||||
|  *      Must be called before use. | ||||
|  *       | ||||
|  *  Parameters: | ||||
|  *      ithread_rwlock_t * rwlock (must be valid non NULL pointer to pthread_rwlock_t) | ||||
|  *      const ithread_rwlockattr_t * rwlock_attr  | ||||
|  *  Returns: | ||||
|  *      0 on success, Nonzero on failure. | ||||
|  *      Always returns 0. | ||||
|  *      See man page for pthread_rwlock_init | ||||
|  *****************************************************************************/ | ||||
| #define ithread_rwlock_init pthread_rwlock_init | ||||
|  | ||||
|  | ||||
| /**************************************************************************** | ||||
|  * Function: ithread_rwlock_rdlock | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Locks rwlock for reading. | ||||
|  *  Parameters: | ||||
|  *      ithread_rwlock_t * rwlock (must be valid non NULL pointer to pthread_rwlock_t) | ||||
|  *      rwlock must be initialized. | ||||
|  *       | ||||
|  *  Returns: | ||||
|  *      0 on success, Nonzero on failure. | ||||
|  *      Always returns 0. | ||||
|  *      See man page for pthread_rwlock_rdlock | ||||
|  *****************************************************************************/ | ||||
| #define ithread_rwlock_rdlock pthread_rwlock_rdlock | ||||
|  | ||||
|  | ||||
| /**************************************************************************** | ||||
|  * Function: ithread_rwlock_wrlock | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Locks rwlock for writting. | ||||
|  *  Parameters: | ||||
|  *      ithread_rwlock_t * rwlock (must be valid non NULL pointer to pthread_rwlock_t) | ||||
|  *      rwlock must be initialized. | ||||
|  *       | ||||
|  *  Returns: | ||||
|  *      0 on success, Nonzero on failure. | ||||
|  *      Always returns 0. | ||||
|  *      See man page for pthread_rwlock_wrlock | ||||
|  *****************************************************************************/ | ||||
| #define ithread_rwlock_wrlock pthread_rwlock_wrlock | ||||
|  | ||||
|  | ||||
| /**************************************************************************** | ||||
|  * Function: ithread_rwlock_unlock | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Unlocks rwlock. | ||||
|  * | ||||
|  *  Parameters: | ||||
|  *      ithread_rwlock_t * rwlock (must be valid non NULL pointer to pthread_rwlock_t) | ||||
|  *      rwlock must be initialized. | ||||
|  *       | ||||
|  *  Returns: | ||||
|  *      0 on success, Nonzero on failure. | ||||
|  *      Always returns 0. | ||||
|  *      See man page for pthread_rwlock_unlock | ||||
|  *****************************************************************************/ | ||||
| #define ithread_rwlock_unlock pthread_rwlock_unlock | ||||
|  | ||||
|  | ||||
| /**************************************************************************** | ||||
|  * Function: ithread_rwlock_destroy | ||||
|  * | ||||
|  *  Description: | ||||
|  *      Releases any resources held by the rwlock.  | ||||
|  *		rwlock can no longer be used after this call. | ||||
|  *		rwlock is only destroyed when there are no longer any threads waiting on it.  | ||||
|  *		rwlock cannot be destroyed if it is locked. | ||||
|  *  Parameters: | ||||
|  *      ithread_rwlock_t * rwlock (must be valid non NULL pointer to pthread_rwlock_t) | ||||
|  *      rwlock must be initialized. | ||||
|  *  Returns: | ||||
|  *      0 on success. Nonzero on failure. | ||||
|  *      Always returns 0. | ||||
|  *      See man page for pthread_rwlock_destroy | ||||
|  *****************************************************************************/ | ||||
| #define ithread_rwlock_destroy pthread_rwlock_destroy | ||||
|  | ||||
|  | ||||
| /**************************************************************************** | ||||
|  * Function: ithread_cond_init | ||||
|  * | ||||
|   | ||||
| @@ -31,7 +31,7 @@ | ||||
|  | ||||
| #include "LinkedList.h" | ||||
| #include <sys/param.h> | ||||
| #if (defined(BSD) && BSD >= 199306) | ||||
| #if (defined(BSD) && BSD >= 199306) || defined(__OSX__) | ||||
| #include <stdlib.h> | ||||
| #else | ||||
| #include <malloc.h> | ||||
|   | ||||
| @@ -90,22 +90,23 @@ FreeThreadPoolJob( ThreadPool * tp, | ||||
| static int | ||||
| SetPolicyType( PolicyType in ) | ||||
| { | ||||
|     #ifdef __CYGWIN__ | ||||
|      /* TODO not currently working... */ | ||||
|      return 0; | ||||
|     #else | ||||
|     #ifdef WIN32 | ||||
| #ifdef __CYGWIN__ | ||||
|     /* TODO not currently working... */ | ||||
|     return 0; | ||||
| #elif defined(__OSX__) | ||||
|     setpriority(PRIO_PROCESS, 0, 0); | ||||
|     return 0; | ||||
| #elif defined(WIN32) | ||||
|      return sched_setscheduler( 0, in); | ||||
|     #elif defined(_POSIX_PRIORITY_SCHEDULING) && _POSIX_PRIORITY_SCHEDULING > 0 | ||||
| #elif defined(_POSIX_PRIORITY_SCHEDULING) && _POSIX_PRIORITY_SCHEDULING > 0 | ||||
|      struct sched_param current; | ||||
|  | ||||
|      sched_getparam( 0, ¤t ); | ||||
|      current.sched_priority = DEFAULT_SCHED_PARAM; | ||||
|      return sched_setscheduler( 0, in, ¤t ); | ||||
|     #else | ||||
| #else | ||||
|      return 0; | ||||
|     #endif | ||||
|     #endif | ||||
| #endif | ||||
| } | ||||
|  | ||||
| /**************************************************************************** | ||||
| @@ -364,7 +365,7 @@ static void SetSeed() { | ||||
| 	ftime( &t ); | ||||
| #if defined(WIN32) | ||||
| 	srand( ( unsigned int )t.millitm + (unsigned int)ithread_get_current_thread_id().p ); | ||||
| #elif defined(__FreeBSD__) | ||||
| #elif defined(__FreeBSD__) || defined(__OSX__) | ||||
| 	srand( ( unsigned int )t.millitm + (unsigned int)ithread_get_current_thread_id() ); | ||||
| #elif defined(__linux__) | ||||
| 	srand( ( unsigned int )t.millitm + ithread_get_current_thread_id() ); | ||||
| @@ -1510,36 +1511,33 @@ static void SetSeed() { | ||||
|     } | ||||
|  | ||||
| #ifdef STATS | ||||
|     void ThreadPoolPrintStats( ThreadPoolStats * stats ) { | ||||
|                assert( stats != NULL ); if( stats == NULL ) { | ||||
|                return;} | ||||
| void ThreadPoolPrintStats(ThreadPoolStats * stats) | ||||
| { | ||||
| 	assert( stats != NULL ); | ||||
| 	if (stats == NULL) { | ||||
| 		return; | ||||
| 	} | ||||
|  | ||||
| 	       #ifdef __FreeBSD__ | ||||
|                printf( "ThreadPoolStats at Time: %d\n", time( NULL ) ); | ||||
| 	       #else | ||||
|                printf( "ThreadPoolStats at Time: %ld\n", time( NULL ) ); | ||||
| 	       #endif | ||||
|                printf | ||||
|                ( "Average Wait in High Priority Q in milliseconds: %f\n", | ||||
|                  stats->avgWaitHQ ); | ||||
|                printf | ||||
|                ( "Average Wait in Med Priority Q in milliseconds: %f\n", | ||||
|                  stats->avgWaitMQ ); | ||||
|                printf | ||||
|                ( "Averate Wait in Low Priority Q in milliseconds: %f\n", | ||||
|                  stats->avgWaitLQ ); | ||||
|                printf( "Max Threads Active: %d\n", stats->maxThreads ); | ||||
|                printf( "Current Worker Threads: %d\n", | ||||
|                        stats->workerThreads ); | ||||
|                printf( "Current Persistent Threads: %d\n", | ||||
|                        stats->persistentThreads ); | ||||
|                printf( "Current Idle Threads: %d\n", stats->idleThreads ); | ||||
|                printf( "Total Threads : %d\n", stats->totalThreads ); | ||||
|                printf( "Total Time spent Working in seconds: %f\n", | ||||
|                        stats->totalWorkTime ); | ||||
|                printf( "Total Time spent Idle in seconds : %f\n", | ||||
|                        stats->totalIdleTime );} | ||||
| #endif | ||||
| #ifdef __FreeBSD__ | ||||
| 	printf("ThreadPoolStats at Time: %d\n", time(NULL)); | ||||
| #else /* __FreeBSD__ */ | ||||
| 	printf("ThreadPoolStats at Time: %ld\n", time(NULL)); | ||||
| #endif /* __FreeBSD__ */ | ||||
| 	printf("High Jobs pending: %d\n", stats->currentJobsHQ); | ||||
| 	printf("Med Jobs Pending: %d\n", stats->currentJobsMQ); | ||||
| 	printf("Low Jobs Pending: %d\n", stats->currentJobsLQ); | ||||
| 	printf("Average Wait in High Priority Q in milliseconds: %f\n", stats->avgWaitHQ); | ||||
| 	printf("Average Wait in Med Priority Q in milliseconds: %f\n", stats->avgWaitMQ); | ||||
| 	printf("Averate Wait in Low Priority Q in milliseconds: %f\n", stats->avgWaitLQ); | ||||
| 	printf("Max Threads Active: %d\n", stats->maxThreads); | ||||
| 	printf("Current Worker Threads: %d\n", stats->workerThreads); | ||||
| 	printf("Current Persistent Threads: %d\n", stats->persistentThreads); | ||||
| 	printf("Current Idle Threads: %d\n", stats->idleThreads); | ||||
| 	printf("Total Threads : %d\n", stats->totalThreads); | ||||
| 	printf("Total Time spent Working in seconds: %f\n", stats->totalWorkTime); | ||||
| 	printf("Total Time spent Idle in seconds : %f\n", stats->totalIdleTime); | ||||
| } | ||||
| #endif /* STATS */ | ||||
|  | ||||
|  /**************************************************************************** | ||||
|  * Function: TPAttrSetMaxJobsTotal | ||||
| @@ -1552,17 +1550,19 @@ static void SetSeed() { | ||||
|  *  Returns: | ||||
|  *      Always returns 0. | ||||
|  *****************************************************************************/ | ||||
|     int TPAttrSetMaxJobsTotal( ThreadPoolAttr * attr, | ||||
|                                int  maxJobsTotal ) { | ||||
|         assert( attr != NULL ); | ||||
| int TPAttrSetMaxJobsTotal( | ||||
| 	ThreadPoolAttr * attr, | ||||
| 	int  maxJobsTotal ) | ||||
| { | ||||
| 	assert( attr != NULL ); | ||||
|  | ||||
|         if( attr == NULL ) { | ||||
|             return EINVAL; | ||||
|         } | ||||
| 	if( attr == NULL ) { | ||||
| 		return EINVAL; | ||||
| 	} | ||||
|  | ||||
|         attr->maxJobsTotal = maxJobsTotal; | ||||
|         return 0; | ||||
|     } | ||||
| 	attr->maxJobsTotal = maxJobsTotal; | ||||
| 	return 0; | ||||
| } | ||||
|  | ||||
| /**************************************************************************** | ||||
|  * Function: ThreadPoolGetStats | ||||
| @@ -1579,40 +1579,54 @@ static void SetSeed() { | ||||
|  *****************************************************************************/ | ||||
| #ifdef STATS | ||||
| int | ||||
|                    ThreadPoolGetStats( ThreadPool * tp, | ||||
|                                        ThreadPoolStats * stats ) { | ||||
| ThreadPoolGetStats( | ||||
|     ThreadPool *tp, | ||||
|     ThreadPoolStats *stats) | ||||
| { | ||||
| 	assert(tp != NULL); | ||||
| 	assert(stats != NULL); | ||||
|  | ||||
|                    assert( tp != NULL ); | ||||
|                    assert( stats != NULL ); | ||||
|                    if( ( tp == NULL ) || ( stats == NULL ) ) { | ||||
|                    return EINVAL;} | ||||
| 	if (tp == NULL || stats == NULL) { | ||||
| 		return EINVAL; | ||||
| 	} | ||||
|  | ||||
|                    //if not shutdown then acquire mutex | ||||
|                    if( !tp->shutdown ) { | ||||
|                    ithread_mutex_lock( &tp->mutex );} | ||||
| 	//if not shutdown then acquire mutex | ||||
| 	if (!tp->shutdown) { | ||||
| 		ithread_mutex_lock(&tp->mutex); | ||||
| 	} | ||||
|  | ||||
|                    ( *stats ) = tp->stats; if( stats->totalJobsHQ > 0 ) | ||||
|                    stats->avgWaitHQ = | ||||
|                    stats->totalTimeHQ / stats->totalJobsHQ; | ||||
|                    else | ||||
|                    stats->avgWaitHQ = 0; if( stats->totalJobsMQ > 0 ) | ||||
|                    stats->avgWaitMQ = | ||||
|                    stats->totalTimeMQ / stats->totalJobsMQ; | ||||
|                    else | ||||
|                    stats->avgWaitMQ = 0; if( stats->totalJobsLQ > 0 ) | ||||
|                    stats->avgWaitLQ = | ||||
|                    stats->totalTimeLQ / stats->totalJobsLQ; | ||||
|                    else | ||||
|                    stats->avgWaitLQ = 0; | ||||
|                    stats->totalThreads = tp->totalThreads; | ||||
|                    stats->persistentThreads = tp->persistentThreads; | ||||
|                    stats->currentJobsHQ = ListSize( &tp->highJobQ ); | ||||
|                    stats->currentJobsLQ = ListSize( &tp->lowJobQ ); | ||||
|                    stats->currentJobsMQ = ListSize( &tp->medJobQ ); | ||||
|                    //if not shutdown then release mutex | ||||
|                    if( !tp->shutdown ) { | ||||
|                    ithread_mutex_unlock( &tp->mutex );} | ||||
| 	*stats = tp->stats; | ||||
| 	if (stats->totalJobsHQ > 0) { | ||||
| 		stats->avgWaitHQ = stats->totalTimeHQ / stats->totalJobsHQ; | ||||
| 	} else { | ||||
| 		stats->avgWaitHQ = 0; | ||||
| 	} | ||||
| 	 | ||||
|                    return 0;} | ||||
| 	if( stats->totalJobsMQ > 0 ) { | ||||
| 		stats->avgWaitMQ = stats->totalTimeMQ / stats->totalJobsMQ; | ||||
| 	} else { | ||||
| 		stats->avgWaitMQ = 0; | ||||
| 	} | ||||
| 	 | ||||
| 	if( stats->totalJobsLQ > 0 ) { | ||||
| 		stats->avgWaitLQ = stats->totalTimeLQ / stats->totalJobsLQ; | ||||
| 	} else { | ||||
| 		stats->avgWaitLQ = 0; | ||||
| 	} | ||||
|  | ||||
| 	stats->totalThreads = tp->totalThreads; | ||||
| 	stats->persistentThreads = tp->persistentThreads; | ||||
| 	stats->currentJobsHQ = ListSize( &tp->highJobQ ); | ||||
| 	stats->currentJobsLQ = ListSize( &tp->lowJobQ ); | ||||
| 	stats->currentJobsMQ = ListSize( &tp->medJobQ ); | ||||
|  | ||||
| 	//if not shutdown then release mutex | ||||
| 	if( !tp->shutdown ) { | ||||
| 		ithread_mutex_unlock( &tp->mutex ); | ||||
| 	} | ||||
|  | ||||
| 	return 0; | ||||
| } | ||||
|  | ||||
| #endif /* STATS */ | ||||
|  | ||||
| #endif | ||||
|   | ||||
| @@ -32,7 +32,7 @@ | ||||
| #include <stdarg.h> | ||||
| #include <assert.h> | ||||
| #include <sys/param.h> | ||||
| #if (defined(BSD) && BSD >= 199306) | ||||
| #if (defined(BSD) && BSD >= 199306) || defined(__OSX__) | ||||
| #include <stdlib.h> | ||||
| #else | ||||
| #include <malloc.h> | ||||
|   | ||||
| @@ -258,7 +258,7 @@ void UpnpPrintf( | ||||
| 	__attribute__((format (__printf__, 5, 6))) | ||||
| #endif | ||||
| ; | ||||
| #else | ||||
| #else /* DEBUG */ | ||||
| static UPNP_INLINE void UpnpPrintf( | ||||
| 	Upnp_LogLevel DLevel, | ||||
| 	Dbg_Module Module, | ||||
| @@ -266,7 +266,7 @@ static UPNP_INLINE void UpnpPrintf( | ||||
| 	int DbgLineNo, | ||||
| 	const char* FmtStr, | ||||
| 	...) {} | ||||
| #endif | ||||
| #endif /* DEBUG */ | ||||
|  | ||||
|  | ||||
| /*************************************************************************** | ||||
|   | ||||
| @@ -1362,7 +1362,7 @@ TvCtrlPointStart( print_string printFunctionPtr, | ||||
|  | ||||
|     ithread_mutex_init( &DeviceListMutex, 0 ); | ||||
|  | ||||
|     SampleUtil_Print( "Intializing UPnP with ipaddress=%s port=%d", | ||||
|     SampleUtil_Print( "Initializing UPnP with ipaddress=%s port=%d", | ||||
|                       ip_address, port ); | ||||
|     rc = UpnpInit( ip_address, port ); | ||||
|     if( UPNP_E_SUCCESS != rc ) { | ||||
|   | ||||
| @@ -84,8 +84,8 @@ virtualDirList *pVirtualDirList; | ||||
| // Mutex to synchronize the subscription handling at the client side | ||||
| CLIENTONLY( ithread_mutex_t GlobalClientSubscribeMutex; ) | ||||
|  | ||||
| //Mutex to synchronize handles ( root device or control point handle) | ||||
|     ithread_mutex_t GlobalHndMutex; | ||||
| // rwlock to synchronize handles (root device or control point handle) | ||||
|     ithread_rwlock_t GlobalHndRWLock; | ||||
|  | ||||
| // Mutex to synchronize the uuid creation process | ||||
|     ithread_mutex_t gUUIDMutex; | ||||
| @@ -213,26 +213,26 @@ int UpnpInit( IN const char *HostIP, | ||||
| #ifdef __CYGWIN__ | ||||
|         /* On Cygwin, pthread_mutex_init() fails without this memset. */ | ||||
|         /* TODO: Fix Cygwin so we don't need this memset(). */ | ||||
|         memset(&GlobalHndMutex, 0, sizeof(GlobalHndMutex)); | ||||
|         memset(&GlobalHndRWLock, 0, sizeof(GlobalHndRWLock)); | ||||
| #endif | ||||
|         if( ithread_mutex_init( &GlobalHndMutex, NULL ) != 0 ) { | ||||
|     if (ithread_rwlock_init(&GlobalHndRWLock, NULL) != 0) { | ||||
|         return UPNP_E_INIT_FAILED; | ||||
|     } | ||||
|  | ||||
|     if( ithread_mutex_init( &gUUIDMutex, NULL ) != 0 ) { | ||||
|     if (ithread_mutex_init(&gUUIDMutex, NULL) != 0) { | ||||
|         return UPNP_E_INIT_FAILED; | ||||
|     } | ||||
|     // initialize subscribe mutex | ||||
| #ifdef INCLUDE_CLIENT_APIS | ||||
|     if ( ithread_mutex_init( &GlobalClientSubscribeMutex, NULL ) != 0 ) { | ||||
|     if (ithread_mutex_init(&GlobalClientSubscribeMutex, NULL) != 0) { | ||||
|         return UPNP_E_INIT_FAILED; | ||||
|     } | ||||
| #endif | ||||
|  | ||||
|         HandleLock(); | ||||
|     if( HostIP != NULL ) | ||||
|     HandleLock(); | ||||
|     if( HostIP != NULL ) { | ||||
|         strcpy( LOCAL_HOST, HostIP ); | ||||
|     else { | ||||
|     } else { | ||||
|         if( getlocalhostname( LOCAL_HOST ) != UPNP_E_SUCCESS ) { | ||||
|             HandleUnlock(); | ||||
|             return UPNP_E_INIT_FAILED; | ||||
| @@ -323,27 +323,54 @@ int UpnpInit( IN const char *HostIP, | ||||
|  | ||||
| #ifdef DEBUG | ||||
| static void  | ||||
| PrintThreadPoolStats (const char* DbgFileName, int DbgLineNo, | ||||
| 		      const char* msg, const ThreadPoolStats* const stats) | ||||
| PrintThreadPoolStats( | ||||
| 	ThreadPool *tp,  | ||||
| 	const char *DbgFileName, | ||||
| 	int DbgLineNo, | ||||
| 	const char *msg) | ||||
| { | ||||
| 	UpnpPrintf (UPNP_INFO, API, DbgFileName, DbgLineNo,  | ||||
| 		    "%s \n High Jobs pending = %d \nMed Jobs Pending = %d\n" | ||||
| 		    " Low Jobs Pending = %d \nWorker Threads = %d\n" | ||||
| 		    "Idle Threads = %d\nPersistent Threads = %d\n" | ||||
| 		    "Average Time spent in High Q = %lf\n" | ||||
| 		    "Average Time spent in Med Q = %lf\n" | ||||
| 		    "Average Time spent in Low Q = %lf\n" | ||||
| 		    "Max Threads Used: %d\nTotal Work Time= %lf\n" | ||||
| 		    "Total Idle Time = %lf\n", | ||||
| 		    msg, | ||||
| 		    stats->currentJobsHQ, stats->currentJobsMQ, | ||||
| 		    stats->currentJobsLQ, stats->workerThreads, | ||||
| 		    stats->idleThreads, stats->persistentThreads, | ||||
| 		    stats->avgWaitHQ, stats->avgWaitMQ, stats->avgWaitLQ, | ||||
| 		    stats->maxThreads, stats->totalWorkTime, | ||||
| 		    stats->totalIdleTime ); | ||||
| 	ThreadPoolStats stats; | ||||
| 	ThreadPoolGetStats(tp, &stats); | ||||
| 	UpnpPrintf(UPNP_INFO, API, DbgFileName, DbgLineNo,  | ||||
| 		"%s \n" | ||||
| 		"High Jobs pending: %d\n" | ||||
| 		"Med Jobs Pending: %d\n" | ||||
| 		"Low Jobs Pending: %d\n" | ||||
| 		"Average wait in High Q in milliseconds: %lf\n" | ||||
| 		"Average wait in Med Q in milliseconds: %lf\n" | ||||
| 		"Average wait in Low Q in milliseconds: %lf\n" | ||||
| 		"Max Threads Used: %d\n" | ||||
| 		"Worker Threads: %d\n" | ||||
| 		"Persistent Threads: %d\n" | ||||
| 		"Idle Threads: %d\n" | ||||
| 		"Total Threads: %d\n" | ||||
| 		"Total Work Time: %lf\n" | ||||
| 		"Total Idle Time: %lf\n", | ||||
| 		msg, | ||||
| 		stats.currentJobsHQ, | ||||
| 		stats.currentJobsMQ, | ||||
| 		stats.currentJobsLQ, | ||||
| 		stats.avgWaitHQ, | ||||
| 		stats.avgWaitMQ, | ||||
| 		stats.avgWaitLQ, | ||||
| 		stats.maxThreads, | ||||
| 		stats.workerThreads, | ||||
| 		stats.persistentThreads, | ||||
| 		stats.idleThreads, | ||||
| 		stats.totalThreads, | ||||
| 		stats.totalWorkTime, | ||||
| 		stats.totalIdleTime); | ||||
| } | ||||
| #endif | ||||
| #else /* DEBUG */ | ||||
| static UPNP_INLINE void  | ||||
| PrintThreadPoolStats( | ||||
| 	ThreadPool *tp,  | ||||
| 	const char *DbgFileName, | ||||
| 	int DbgLineNo, | ||||
| 	const char *msg) | ||||
| { | ||||
| } | ||||
| #endif /* DEBUG */ | ||||
|  | ||||
|  | ||||
| /**************************************************************************** | ||||
| @@ -374,10 +401,6 @@ UpnpFinish() | ||||
| #endif | ||||
|     struct Handle_Info *temp; | ||||
|  | ||||
| #ifdef DEBUG | ||||
|     ThreadPoolStats stats; | ||||
| #endif | ||||
|  | ||||
| #ifdef WIN32 | ||||
| //	WSACleanup( ); | ||||
| #endif | ||||
| @@ -389,18 +412,12 @@ UpnpFinish() | ||||
|     UpnpPrintf( UPNP_INFO, API, __FILE__, __LINE__, | ||||
|         "Inside UpnpFinish : UpnpSdkInit is :%d:\n", | ||||
|         UpnpSdkInit ); | ||||
| #ifdef DEBUG | ||||
|     if( UpnpSdkInit == 1 ) { | ||||
|         UpnpPrintf( UPNP_INFO, API, __FILE__, __LINE__, | ||||
|             "UpnpFinish : UpnpSdkInit is ONE\n" ); | ||||
|     } | ||||
|     ThreadPoolGetStats( &gRecvThreadPool, &stats ); | ||||
|     PrintThreadPoolStats (__FILE__, __LINE__, | ||||
| 	"Recv Thread Pool", &stats); | ||||
|     ThreadPoolGetStats( &gSendThreadPool, &stats ); | ||||
|     PrintThreadPoolStats (__FILE__, __LINE__, | ||||
| 	"Send Thread Pool", &stats); | ||||
| #endif | ||||
|     PrintThreadPoolStats(&gRecvThreadPool, __FILE__, __LINE__, "Recv Thread Pool"); | ||||
|     PrintThreadPoolStats(&gSendThreadPool, __FILE__, __LINE__, "Send Thread Pool"); | ||||
| #ifdef INCLUDE_DEVICE_APIS | ||||
|     if( GetDeviceHandleInfo( &device_handle, &temp ) == HND_DEVICE ) | ||||
|         UpnpUnRegisterRootDevice( device_handle ); | ||||
| @@ -419,44 +436,38 @@ UpnpFinish() | ||||
|     web_server_destroy(); | ||||
| #endif | ||||
|  | ||||
| #ifdef DEBUG | ||||
|     ThreadPoolShutdown( &gSendThreadPool ); | ||||
|     ThreadPoolShutdown( &gRecvThreadPool ); | ||||
|     ThreadPoolShutdown(&gSendThreadPool); | ||||
|     ThreadPoolShutdown(&gRecvThreadPool); | ||||
|     UpnpPrintf( UPNP_INFO, API, __FILE__, __LINE__, | ||||
|         "Exiting UpnpFinish : UpnpSdkInit is :%d:\n", | ||||
| 	UpnpSdkInit ); | ||||
|     ThreadPoolGetStats( &gRecvThreadPool, &stats ); | ||||
|     PrintThreadPoolStats( __FILE__, __LINE__, | ||||
|         "Recv Thread Pool", &stats); | ||||
|     ThreadPoolGetStats( &gSendThreadPool, &stats ); | ||||
|     PrintThreadPoolStats(__FILE__, __LINE__, | ||||
|         "Send Thread Pool", &stats); | ||||
|         "Exiting UpnpFinish : UpnpSdkInit is :%d:\n", UpnpSdkInit); | ||||
|     PrintThreadPoolStats(&gRecvThreadPool, __FILE__, __LINE__, "Recv Thread Pool"); | ||||
|     PrintThreadPoolStats(&gSendThreadPool, __FILE__, __LINE__, "Send Thread Pool"); | ||||
|     UpnpCloseLog(); | ||||
| #endif | ||||
|  | ||||
| #ifdef INCLUDE_CLIENT_APIS | ||||
|     ithread_mutex_destroy( &GlobalClientSubscribeMutex ); | ||||
|     ithread_mutex_destroy(&GlobalClientSubscribeMutex); | ||||
| #endif | ||||
|     ithread_mutex_destroy( &GlobalHndMutex ); | ||||
|     ithread_mutex_destroy( &gUUIDMutex ); | ||||
|     ithread_rwlock_destroy(&GlobalHndRWLock); | ||||
|     ithread_mutex_destroy(&gUUIDMutex); | ||||
|  | ||||
|     // remove all virtual dirs | ||||
|     UpnpRemoveAllVirtualDirs(); | ||||
|     // leuk_he allow static linking: | ||||
|  | ||||
|     // allow static linking | ||||
| #ifdef WIN32 | ||||
| #ifdef PTW32_STATIC_LIB | ||||
|     pthread_win32_thread_detach_np (); | ||||
| #endif | ||||
| #endif | ||||
|  | ||||
|  | ||||
|     UpnpSdkInit = 0; | ||||
|  | ||||
|     return UPNP_E_SUCCESS; | ||||
|  | ||||
| }  /********************* End of  UpnpFinish  *************************/ | ||||
| } | ||||
| /*************************** End of  UpnpFinish  *****************************/ | ||||
|  | ||||
| /**************************************************************************** | ||||
| /****************************************************************************** | ||||
|  * Function: UpnpGetServerPort | ||||
|  * | ||||
|  * Parameters: NONE | ||||
| @@ -953,7 +964,7 @@ GetDescDocumentAndURL( IN Upnp_DescType descriptionType, | ||||
|     char *temp_str = NULL; | ||||
|     FILE *fp = NULL; | ||||
|     off_t fileLen; | ||||
|     unsigned num_read; | ||||
|     size_t num_read; | ||||
|     time_t last_modified; | ||||
|     struct stat file_info; | ||||
|     struct sockaddr_in serverAddr; | ||||
| @@ -1559,7 +1570,7 @@ UpnpSearchAsync( IN UpnpClient_Handle Hnd, | ||||
|     UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|         "Inside UpnpSearchAsync \n" ); | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_CLIENT ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
| @@ -1735,7 +1746,7 @@ UpnpSubscribeAsync( IN UpnpClient_Handle Hnd, | ||||
|     UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|         "Inside UpnpSubscribeAsync \n" ); | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_CLIENT ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
| @@ -1752,15 +1763,13 @@ UpnpSubscribeAsync( IN UpnpClient_Handle Hnd, | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_PARAM; | ||||
|     } | ||||
|     HandleUnlock(); | ||||
|  | ||||
|     Param = | ||||
|         ( struct UpnpNonblockParam * ) | ||||
|         malloc( sizeof( struct UpnpNonblockParam ) ); | ||||
|     Param = (struct UpnpNonblockParam *) | ||||
|         malloc(sizeof (struct UpnpNonblockParam)); | ||||
|     if( Param == NULL ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_OUTOF_MEMORY; | ||||
|     } | ||||
|     HandleUnlock(); | ||||
|  | ||||
|     Param->FunName = SUBSCRIBE; | ||||
|     Param->Handle = Hnd; | ||||
| @@ -1820,7 +1829,7 @@ UpnpSubscribe( IN UpnpClient_Handle Hnd, | ||||
|     UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|         "Inside UpnpSubscribe \n" ); | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_CLIENT ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
| @@ -1880,7 +1889,7 @@ UpnpUnSubscribe( IN UpnpClient_Handle Hnd, | ||||
|     UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|         "Inside UpnpUnSubscribe \n" ); | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_CLIENT ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
| @@ -1939,7 +1948,7 @@ UpnpUnSubscribeAsync( IN UpnpClient_Handle Hnd, | ||||
|     UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|         "Inside UpnpUnSubscribeAsync \n" ); | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_CLIENT ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
| @@ -2013,7 +2022,7 @@ UpnpRenewSubscription( IN UpnpClient_Handle Hnd, | ||||
|     UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|         "Inside UpnpRenewSubscription \n" ); | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_CLIENT ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
| @@ -2078,7 +2087,7 @@ UpnpRenewSubscriptionAsync( IN UpnpClient_Handle Hnd, | ||||
|  | ||||
|     UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|         "Inside UpnpRenewSubscriptionAsync \n" ); | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_CLIENT ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
| @@ -2173,7 +2182,7 @@ UpnpNotify( IN UpnpDevice_Handle Hnd, | ||||
|     UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|         "Inside UpnpNotify \n" ); | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_DEVICE ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
| @@ -2244,7 +2253,7 @@ UpnpNotifyExt( IN UpnpDevice_Handle Hnd, | ||||
|     UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|         "Inside UpnpNotify \n" ); | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_DEVICE ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
| @@ -2321,7 +2330,7 @@ UpnpAcceptSubscription( IN UpnpDevice_Handle Hnd, | ||||
|     UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|         "Inside UpnpAcceptSubscription \n" ); | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_DEVICE ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
| @@ -2397,7 +2406,7 @@ UpnpAcceptSubscriptionExt( IN UpnpDevice_Handle Hnd, | ||||
|     UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|         "Inside UpnpAcceptSubscription \n" ); | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_DEVICE ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
| @@ -2493,7 +2502,7 @@ UpnpSendAction( IN UpnpClient_Handle Hnd, | ||||
|     } | ||||
|     DevUDN_const = NULL; | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_CLIENT ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
| @@ -2577,7 +2586,7 @@ UpnpSendActionEx( IN UpnpClient_Handle Hnd, | ||||
|         return retVal; | ||||
|     } | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_CLIENT ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
| @@ -2653,7 +2662,7 @@ UpnpSendActionAsync( IN UpnpClient_Handle Hnd, | ||||
|     UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|         "Inside UpnpSendActionAsync \n" ); | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_CLIENT ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
| @@ -2773,7 +2782,7 @@ UpnpSendActionExAsync( IN UpnpClient_Handle Hnd, | ||||
|         return retVal; | ||||
|     } | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_CLIENT ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
| @@ -2887,7 +2896,7 @@ UpnpGetServiceVarStatusAsync( IN UpnpClient_Handle Hnd, | ||||
|     UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|         "Inside UpnpGetServiceVarStatusAsync \n" ); | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_CLIENT ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
| @@ -2967,7 +2976,7 @@ UpnpGetServiceVarStatus( IN UpnpClient_Handle Hnd, | ||||
|     UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|         "Inside UpnpGetServiceVarStatus \n" ); | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_CLIENT ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
| @@ -3300,9 +3309,9 @@ UpnpDownloadXmlDoc( const char *url, | ||||
|         UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|             "****************** END OF Parsed XML Doc *****************\n" ); | ||||
|         ixmlFreeDOMString( xml_buf ); | ||||
| #endif | ||||
|         UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|             "Exiting UpnpDownloadXmlDoc\n" ); | ||||
| #endif | ||||
|         return UPNP_E_SUCCESS; | ||||
|     } | ||||
| } | ||||
| @@ -3635,7 +3644,6 @@ int PrintHandleInfo( IN UpnpClient_Handle Hnd ) | ||||
|     struct Handle_Info * HndInfo; | ||||
|     if (HandleTable[Hnd] != NULL) { | ||||
|         HndInfo = HandleTable[Hnd]; | ||||
| #ifdef DEBUG | ||||
|             UpnpPrintf(UPNP_ALL, API, __FILE__, __LINE__, | ||||
|                 "Printing information for Handle_%d\n", Hnd); | ||||
|             UpnpPrintf(UPNP_ALL, API, __FILE__, __LINE__, | ||||
| @@ -3644,7 +3652,6 @@ int PrintHandleInfo( IN UpnpClient_Handle Hnd ) | ||||
|                 if(HndInfo->HType != HND_CLIENT) | ||||
|                     UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|                         "DescURL_%s\n", HndInfo->DescURL ); | ||||
| #endif | ||||
| #endif | ||||
|     } else { | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
|   | ||||
| @@ -36,7 +36,7 @@ | ||||
| #include "uri.h" | ||||
| #define HEADER_LENGTH 2000 | ||||
|  | ||||
| //Structure to maintain a error code and string associated with the  | ||||
| // Structure to maintain a error code and string associated with the  | ||||
| // error code | ||||
| struct ErrorString { | ||||
|     int rc;                     /* error code */ | ||||
| @@ -44,7 +44,7 @@ struct ErrorString { | ||||
|  | ||||
| }; | ||||
|  | ||||
| //Intializing the array of error structures.  | ||||
| // Initializing the array of error structures.  | ||||
| struct ErrorString ErrorMessages[] = { {UPNP_E_SUCCESS, "UPNP_E_SUCCESS"}, | ||||
| {UPNP_E_INVALID_HANDLE, "UPNP_E_INVALID_HANDLE"}, | ||||
| {UPNP_E_INVALID_PARAM, "UPNP_E_INVALID_PARAM"}, | ||||
| @@ -155,7 +155,7 @@ UpnpResolveURL( IN const char *BaseURL, | ||||
| * | ||||
| * Parameters: | ||||
| *	IN int response: flag to tell if the ActionDoc is for response | ||||
| *					or request | ||||
| *		or request | ||||
| *	INOUT IXML_Document **ActionDoc: request or response document | ||||
| *	IN char *ActionName: Name of the action request or response | ||||
| *	IN char *ServType: Service type | ||||
| @@ -234,7 +234,7 @@ addToAction( IN int response, | ||||
| * | ||||
| * Parameters: | ||||
| *	IN int response: flag to tell if the ActionDoc is for response | ||||
| *					or request | ||||
| *		or request | ||||
| *	IN char * ActionName: Name of the action request or response | ||||
| *	IN char * ServType: Service type | ||||
| *	IN int NumArg :Number of arguments in the action request or response | ||||
| @@ -581,4 +581,5 @@ UpnpCreatePropertySet( IN int NumArg, | ||||
|     return PropSet; | ||||
| } | ||||
|  | ||||
| #endif | ||||
| #endif // EXCLUDE_DOM == 0 | ||||
|  | ||||
|   | ||||
| @@ -93,7 +93,7 @@ GenaAutoRenewSubscription( IN void *input ) | ||||
|         } | ||||
|     } | ||||
|     if( send_callback ) { | ||||
|         HandleLock(); | ||||
|         HandleReadLock(); | ||||
|         if( GetHandleInfo( event->handle, &handle_info ) != HND_CLIENT ) { | ||||
|             HandleUnlock(); | ||||
|             free_upnp_timeout( event ); | ||||
| @@ -543,10 +543,10 @@ genaSubscribe( IN UpnpClient_Handle client_handle, | ||||
|  | ||||
|     UpnpPrintf( UPNP_INFO, GENA, __FILE__, __LINE__, | ||||
|         "GENA SUBSCRIBE BEGIN" ); | ||||
|     HandleLock(); | ||||
|  | ||||
|     memset( out_sid, 0, sizeof( Upnp_SID ) ); | ||||
|  | ||||
|     HandleReadLock(); | ||||
|     // validate handle | ||||
|     if( GetHandleInfo( client_handle, &handle_info ) != HND_CLIENT ) { | ||||
|         HandleUnlock(); | ||||
| @@ -881,3 +881,4 @@ gena_process_notification_event( IN SOCKINFO * info, | ||||
|  | ||||
| #endif // INCLUDE_CLIENT_APIS | ||||
| #endif // EXCLUDE_GENA | ||||
|  | ||||
|   | ||||
| @@ -365,7 +365,7 @@ genaNotifyThread( IN void *input ) | ||||
|     struct Handle_Info *handle_info; | ||||
|     ThreadPoolJob job; | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|     //validate context | ||||
|  | ||||
|     if( GetHandleInfo( in->device_handle, &handle_info ) != HND_DEVICE ) { | ||||
|   | ||||
| @@ -349,7 +349,7 @@ http_SendMessage( IN SOCKINFO * info, | ||||
|             filename = ( char * )va_arg( argp, char * ); | ||||
|  | ||||
|             if( Instr && Instr->IsVirtualFile ) | ||||
|                 Fp = virtualDirCallback.open( filename, UPNP_READ ); | ||||
|                 Fp = (virtualDirCallback.open)( filename, UPNP_READ ); | ||||
|             else | ||||
|                 Fp = fopen( filename, "rb" ); | ||||
|  | ||||
| @@ -475,11 +475,13 @@ http_SendMessage( IN SOCKINFO * info, | ||||
|             buf_length = ( size_t ) va_arg( argp, size_t ); | ||||
|             if( buf_length > 0 ) { | ||||
|                 num_written = sock_write( info, buf, buf_length, TimeOut ); | ||||
|                 UpnpPrintf( UPNP_INFO, HTTP, __FILE__, __LINE__, | ||||
|                     ">>> (SENT) >>>\n" | ||||
| 		    "%.*s\nbuf_length=%d, num_written=%d\n" | ||||
| 		    "------------\n", | ||||
|                     (int)buf_length, buf, (int)buf_length, num_written ); | ||||
|                 if( ( size_t ) num_written != buf_length ) | ||||
|                     goto end; | ||||
|                 UpnpPrintf( UPNP_INFO, HTTP, __FILE__, __LINE__, | ||||
|                     ">>> (SENT) >>>\n%.*s\n------------\n", | ||||
|                     ( int )buf_length, buf ); | ||||
|             } | ||||
|         } | ||||
|     } | ||||
|   | ||||
| @@ -880,22 +880,24 @@ GetNextRange( char **SrcRangeStr, | ||||
|               off_t *FirstByte, | ||||
|               off_t *LastByte ) | ||||
| { | ||||
|     char *Ptr, | ||||
|      *Tok; | ||||
|     int i, | ||||
|       F = -1, | ||||
|       L = -1; | ||||
|     char *Ptr; | ||||
|     char *Tok; | ||||
|     int i; | ||||
|     int64_t F = -1; | ||||
|     int64_t L = -1; | ||||
|     int Is_Suffix_byte_Range = 1; | ||||
|  | ||||
|     if( *SrcRangeStr == NULL ) | ||||
|     if( *SrcRangeStr == NULL ) { | ||||
|         return -1; | ||||
|     } | ||||
|  | ||||
|     Tok = StrTok( SrcRangeStr, "," ); | ||||
|  | ||||
|     if( ( Ptr = strstr( Tok, "-" ) ) == NULL ) | ||||
|     if( ( Ptr = strstr( Tok, "-" ) ) == NULL ) { | ||||
|         return -1; | ||||
|     } | ||||
|     *Ptr = ' '; | ||||
|     sscanf( Tok, "%d%d", &F, &L ); | ||||
|     sscanf( Tok, "%"SCNd64"%"SCNd64, &F, &L ); | ||||
|  | ||||
|     if( F == -1 || L == -1 ) { | ||||
|         *Ptr = '-'; | ||||
| @@ -910,16 +912,15 @@ GetNextRange( char **SrcRangeStr, | ||||
|         } | ||||
|  | ||||
|         if( Is_Suffix_byte_Range ) { | ||||
|             *FirstByte = L; | ||||
|             *LastByte = F; | ||||
|             *FirstByte = (off_t)L; | ||||
|             *LastByte = (off_t)F; | ||||
|             return 1; | ||||
|         } | ||||
|     } | ||||
|     *FirstByte = (off_t)F; | ||||
|     *LastByte = (off_t)L; | ||||
|  | ||||
|     *FirstByte = F; | ||||
|     *LastByte = L; | ||||
|     return 1; | ||||
|  | ||||
| } | ||||
|  | ||||
| /************************************************************************ | ||||
| @@ -1531,7 +1532,7 @@ http_RecvPostMessage( http_parser_t * parser, | ||||
|  | ||||
|     if( Instr && Instr->IsVirtualFile ) { | ||||
|  | ||||
|         Fp = virtualDirCallback.open( filename, UPNP_WRITE ); | ||||
|         Fp = (virtualDirCallback.open)( filename, UPNP_WRITE ); | ||||
|         if( Fp == NULL ) { | ||||
|             return HTTP_INTERNAL_SERVER_ERROR; | ||||
|         } | ||||
|   | ||||
| @@ -555,7 +555,7 @@ parse_hostport( const char *in, | ||||
|     int begin_port; | ||||
|     int hostport_size = 0; | ||||
|     int host_size = 0; | ||||
| #ifndef WIN32 | ||||
| #if !defined(WIN32) && !defined(__OSX__) | ||||
|     char temp_hostbyname_buff[BUFFER_SIZE]; | ||||
|     struct hostent h_buf; | ||||
| #endif | ||||
| @@ -626,54 +626,61 @@ parse_hostport( const char *in, | ||||
|         // TODO: Use autoconf to discover this rather than the | ||||
|         // platform-specific stuff below | ||||
| #if defined(WIN32) || defined(__CYGWIN__) | ||||
|         h=gethostbyname(temp_host_name); | ||||
|         h = gethostbyname(temp_host_name); | ||||
| #elif defined(SPARC_SOLARIS) | ||||
|         errCode = gethostbyname_r( temp_host_name, | ||||
|                                    &h, | ||||
|                                    temp_hostbyname_buff, | ||||
|                                    BUFFER_SIZE, &errcode ); | ||||
|         errCode = gethostbyname_r( | ||||
|                 temp_host_name, | ||||
|                 &h, | ||||
|                 temp_hostbyname_buff, | ||||
|                 BUFFER_SIZE, &errcode ); | ||||
| #elif defined(__FreeBSD__) && __FreeBSD_version < 601103 | ||||
|         h = lwres_gethostbyname_r( temp_host_name, | ||||
|                                    &h_buf, | ||||
|                                    temp_hostbyname_buff, | ||||
|                                    BUFFER_SIZE, &errcode ); | ||||
|         h = lwres_gethostbyname_r( | ||||
|                 temp_host_name, | ||||
|                 &h_buf, | ||||
|                 temp_hostbyname_buff, | ||||
|                 BUFFER_SIZE, &errcode ); | ||||
|         if ( h == NULL ) { | ||||
|             errCode = 1; | ||||
|                 errCode = 1; | ||||
|         } | ||||
| #elif defined(__OSX__) | ||||
|         h = gethostbyname(temp_host_name); | ||||
|         if ( h == NULL ) { | ||||
|                 errCode = 1; | ||||
|         } | ||||
| #elif defined(__linux__) | ||||
|         errCode = gethostbyname_r( temp_host_name, | ||||
|                                    &h_buf, | ||||
|                                    temp_hostbyname_buff, | ||||
|                                    BUFFER_SIZE, &h, &errcode ); | ||||
|         errCode = gethostbyname_r( | ||||
|                 temp_host_name, | ||||
|                 &h_buf, | ||||
|                 temp_hostbyname_buff, | ||||
|                 BUFFER_SIZE, &h, &errcode ); | ||||
| #else | ||||
| { | ||||
|            struct addrinfo hints, *res, *res0; | ||||
|         { | ||||
|         struct addrinfo hints, *res, *res0; | ||||
|  | ||||
| 	   h = NULL; | ||||
|            memset(&hints, 0, sizeof(hints)); | ||||
|            hints.ai_family = PF_INET; | ||||
|            hints.ai_socktype = SOCK_STREAM; | ||||
|            errCode = getaddrinfo(temp_host_name, "http", &hints, &res0); | ||||
|         h = NULL; | ||||
|         memset(&hints, 0, sizeof(hints)); | ||||
|         hints.ai_family = PF_INET; | ||||
|         hints.ai_socktype = SOCK_STREAM; | ||||
|         errCode = getaddrinfo(temp_host_name, "http", &hints, &res0); | ||||
|  | ||||
|            if (!errCode) { | ||||
|                for (res = res0; res; res = res->ai_next) { | ||||
|                    if (res->ai_family == PF_INET && | ||||
|                        res->ai_addr->sa_family == AF_INET) | ||||
|                    { | ||||
|                        h = &h_buf; | ||||
|                        h->h_addrtype = res->ai_addr->sa_family; | ||||
|                        h->h_length = 4; | ||||
|                        h->h_addr = (void *) temp_hostbyname_buff; | ||||
|                        *(struct in_addr *)h->h_addr = | ||||
| 				((struct sockaddr_in *)res->ai_addr)->sin_addr; | ||||
|                        break; | ||||
|                    } | ||||
|                } | ||||
|                freeaddrinfo(res0); | ||||
|            } | ||||
| } | ||||
|         if (!errCode) { | ||||
|             for (res = res0; res; res = res->ai_next) { | ||||
|                 if (res->ai_family == PF_INET && | ||||
|                     res->ai_addr->sa_family == AF_INET) | ||||
|                 { | ||||
|                     h = &h_buf; | ||||
|                     h->h_addrtype = res->ai_addr->sa_family; | ||||
|                     h->h_length = 4; | ||||
|                     h->h_addr = (void *) temp_hostbyname_buff; | ||||
|                     *(struct in_addr *)h->h_addr = | ||||
|                         ((struct sockaddr_in *)res->ai_addr)->sin_addr; | ||||
|                         break; | ||||
|                 } | ||||
|             } | ||||
|             freeaddrinfo(res0); | ||||
|         } | ||||
|         } | ||||
| #endif  | ||||
|  | ||||
|         if( errCode == 0 ) { | ||||
|             if( h ) { | ||||
|                 if( ( h->h_addrtype == AF_INET ) && ( h->h_length == 4 ) ) { | ||||
|   | ||||
| @@ -261,7 +261,7 @@ | ||||
|  | ||||
| /** @name Other debugging features | ||||
|           The UPnP SDK contains other features to aid in debugging: | ||||
| 	  see <upnp/upnpdebug.h> | ||||
| 	  see <upnp/inc/upnpdebug.h> | ||||
|  */ | ||||
|  | ||||
| #define DEBUG_ALL		1 | ||||
|   | ||||
| @@ -98,18 +98,25 @@ struct Handle_Info | ||||
|     int   aliasInstalled;       // 0 = not installed; otherwise installed | ||||
| }; | ||||
|  | ||||
| extern ithread_mutex_t GlobalHndMutex; | ||||
| extern ithread_rwlock_t GlobalHndRWLock; | ||||
| Upnp_Handle_Type GetHandleInfo(int Hnd, struct Handle_Info **HndInfo);  | ||||
|  | ||||
| #define HandleLock()  \ | ||||
| 	UpnpPrintf(UPNP_INFO, API, __FILE__, __LINE__, "Trying Lock"); \ | ||||
| 	ithread_mutex_lock(&GlobalHndMutex); \ | ||||
| 	UpnpPrintf(UPNP_INFO, API, __FILE__, __LINE__, "LOCK"); | ||||
| #define HandleLock() HandleWriteLock() | ||||
|  | ||||
| #define HandleWriteLock()  \ | ||||
| 	UpnpPrintf(UPNP_INFO, API, __FILE__, __LINE__, "Trying a write lock"); \ | ||||
| 	ithread_rwlock_wrlock(&GlobalHndRWLock); \ | ||||
| 	UpnpPrintf(UPNP_INFO, API, __FILE__, __LINE__, "Write lock acquired"); | ||||
|  | ||||
| #define HandleReadLock()  \ | ||||
| 	UpnpPrintf(UPNP_INFO, API, __FILE__, __LINE__, "Trying a read lock"); \ | ||||
| 	ithread_rwlock_rdlock(&GlobalHndRWLock); \ | ||||
| 	UpnpPrintf(UPNP_INFO, API, __FILE__, __LINE__, "Read lock acquired"); | ||||
|  | ||||
| #define HandleUnlock() \ | ||||
| 	UpnpPrintf(UPNP_INFO, API,__FILE__, __LINE__, "Trying Unlock"); \ | ||||
| 	ithread_mutex_unlock(&GlobalHndMutex); \ | ||||
| 	UpnpPrintf(UPNP_INFO, API, __FILE__, __LINE__, "Unlock"); | ||||
| 	ithread_rwlock_unlock(&GlobalHndRWLock); \ | ||||
| 	UpnpPrintf(UPNP_INFO, API, __FILE__, __LINE__, "Unlocked rwlock"); | ||||
|  | ||||
| Upnp_Handle_Type GetClientHandleInfo(int *client_handle_out,  | ||||
|                                      struct Handle_Info **HndInfo); | ||||
|   | ||||
| @@ -125,7 +125,7 @@ ssdp_handle_ctrlpt_msg( IN http_message_t * hmsg, | ||||
|  | ||||
|     // we are assuming that there can be only one client supported at a time | ||||
|  | ||||
|     HandleLock(); | ||||
|     HandleReadLock(); | ||||
|  | ||||
|     if( GetClientHandleInfo( &handle, &ctrlpt_info ) != HND_CLIENT ) { | ||||
|         HandleUnlock(); | ||||
| @@ -538,8 +538,7 @@ SearchByTarget( IN int Mx, | ||||
|     if( ReqBuf == NULL ) | ||||
|         return UPNP_E_OUTOF_MEMORY; | ||||
|  | ||||
|     UpnpPrintf( UPNP_INFO, SSDP, __FILE__, __LINE__, | ||||
|         ">>> SSDP SEND >>>\n%s\n", ReqBuf ); | ||||
|     UpnpPrintf(UPNP_INFO, SSDP, __FILE__, __LINE__, ">>> SSDP SEND >>>\n"); | ||||
|  | ||||
|     timeTillRead = Mx; | ||||
|  | ||||
|   | ||||
| @@ -242,7 +242,7 @@ NewRequestHandler( IN struct sockaddr_in *DestAddr, | ||||
|         // "If a multicast resource would send a response(s) to any copy of the  | ||||
|         //  request, it SHOULD send its response(s) to each copy of the request  | ||||
|         //  it receives. It MUST NOT repeat its response(s) per copy of the  | ||||
|         //  reuqest." | ||||
|         //  request." | ||||
|         //   | ||||
|         // http://www.upnp.org/download/draft-goland-http-udp-04.txt | ||||
|         // | ||||
| @@ -270,7 +270,7 @@ NewRequestHandler( IN struct sockaddr_in *DestAddr, | ||||
| * | ||||
| * Parameters: | ||||
| *	IN int msg_type : type of the message ( Search Reply, Advertisement | ||||
| *												or Shutdown ) | ||||
| *		or Shutdown ) | ||||
| *	IN char * nt : ssdp type | ||||
| *	IN char * usn : unique service name ( go in the HTTP Header) | ||||
| *	IN char * location :Location URL. | ||||
| @@ -280,7 +280,7 @@ NewRequestHandler( IN struct sockaddr_in *DestAddr, | ||||
| * Description: | ||||
| *	This function creates a HTTP request packet.  Depending | ||||
| *	on the input parameter it either creates a service advertisement | ||||
| *   request or service shutdown request etc. | ||||
| *	request or service shutdown request etc. | ||||
| * | ||||
| * Returns: void | ||||
| * | ||||
| @@ -530,7 +530,6 @@ SendReply( IN struct sockaddr_in *DestAddr, | ||||
| *	IN char * Udn: Device UDN | ||||
| *	IN char * Location: Location of Device description document. | ||||
| *	IN int  Duration :Life time of this device. | ||||
|  | ||||
| * Description: | ||||
| *	This function creates the reply packet based on the input parameter,  | ||||
| *	and send it to the client address given in its input parameter DestAddr. | ||||
| @@ -607,11 +606,9 @@ DeviceReply( IN struct sockaddr_in *DestAddr, | ||||
| *	IN char *ServType: Service Type. | ||||
| *	IN char * Location: Location of Device description document. | ||||
| *	IN int  Duration :Life time of this device. | ||||
|  | ||||
| * Description: | ||||
| *	This function creates the advertisement packet based | ||||
| *	on the input parameter, and send it to the multicast channel. | ||||
|  | ||||
| * | ||||
| * Returns: int | ||||
| *	UPNP_E_SUCCESS if successful else appropriate error | ||||
| @@ -656,11 +653,9 @@ ServiceAdvertisement( IN char *Udn, | ||||
| *	IN char *ServType: Service Type. | ||||
| *	IN char * Location: Location of Device description document. | ||||
| *	IN int  Duration :Life time of this device. | ||||
|  | ||||
| * Description: | ||||
| *	This function creates the advertisement packet based  | ||||
| *	on the input parameter, and send it to the multicast channel. | ||||
|  | ||||
| * | ||||
| * Returns: int | ||||
| *	UPNP_E_SUCCESS if successful else appropriate error | ||||
| @@ -700,7 +695,6 @@ ServiceReply( IN struct sockaddr_in *DestAddr, | ||||
| *	IN char *ServType: Service Type. | ||||
| *	IN char * Location: Location of Device description document. | ||||
| *	IN int  Duration :Service duration in sec. | ||||
|  | ||||
| * Description: | ||||
| *	This function creates a HTTP service shutdown request packet  | ||||
| *	and sent it to the multicast channel through RequestHandler. | ||||
| @@ -821,3 +815,4 @@ DeviceShutdown( IN char *DevType, | ||||
|  | ||||
| #endif // EXCLUDE_SSDP | ||||
| #endif // INCLUDE_DEVICE_APIS | ||||
|  | ||||
|   | ||||
| @@ -75,8 +75,10 @@ CLIENTONLY( SOCKET gSsdpReqSocket = 0; | ||||
| * Function : AdvertiseAndReply | ||||
| * | ||||
| * Parameters: | ||||
| *	IN int AdFlag: -1 = Send shutdown, 0 = send reply,  | ||||
| *					1 = Send Advertisement | ||||
| *	IN int AdFlag: | ||||
| *		-1 = Send shutdown, | ||||
| *		 0 = send reply,  | ||||
| *		 1 = Send Advertisement | ||||
| *	IN UpnpDevice_Handle Hnd: Device handle | ||||
| *	IN enum SsdpSearchType SearchType:Search type for sending replies | ||||
| *	IN struct sockaddr_in *DestAddr:Destination address | ||||
| @@ -120,16 +122,13 @@ int AdvertiseAndReply( IN int AdFlag, | ||||
|         "Inside AdvertiseAndReply with AdFlag = %d\n", | ||||
|         AdFlag ); | ||||
|  | ||||
|     HandleLock(); | ||||
|     // Use a read lock | ||||
|     HandleReadLock(); | ||||
|     if( GetHandleInfo( Hnd, &SInfo ) != HND_DEVICE ) { | ||||
|         HandleUnlock(); | ||||
|         return UPNP_E_INVALID_HANDLE; | ||||
|     } | ||||
|     defaultExp = SInfo->MaxAge; | ||||
|  | ||||
|     //Modifed to prevent more than one thread from accessing the  | ||||
|     //UpnpDocument stored with the handle at the same time | ||||
|     // HandleUnlock(); | ||||
|     nodeList = NULL; | ||||
|  | ||||
|     //get server info | ||||
| @@ -150,15 +149,13 @@ int AdvertiseAndReply( IN int AdFlag, | ||||
|         } | ||||
|  | ||||
|         dbgStr = ixmlNode_getNodeName( tmpNode ); | ||||
|                  UpnpPrintf( UPNP_INFO, API, __FILE__, __LINE__, | ||||
|                      "Extracting device type once for %s\n", | ||||
|                      dbgStr ); | ||||
|             // extract device type  | ||||
|             ixmlNodeList_free( nodeList ); | ||||
|         UpnpPrintf( UPNP_INFO, API, __FILE__, __LINE__, | ||||
|             "Extracting device type once for %s\n", dbgStr ); | ||||
|         // extract device type  | ||||
|         ixmlNodeList_free( nodeList ); | ||||
|         nodeList = NULL; | ||||
|         nodeList = | ||||
|             ixmlElement_getElementsByTagName( ( IXML_Element * ) tmpNode, | ||||
|                                               "deviceType" ); | ||||
|         nodeList = ixmlElement_getElementsByTagName( | ||||
|             ( IXML_Element * ) tmpNode, "deviceType" ); | ||||
|         if( nodeList == NULL ) { | ||||
|             continue; | ||||
|         } | ||||
| @@ -166,7 +163,6 @@ int AdvertiseAndReply( IN int AdFlag, | ||||
|         dbgStr = ixmlNode_getNodeName( tmpNode ); | ||||
|         UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|             "Extracting UDN for %s\n", dbgStr ); | ||||
|  | ||||
|         UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|             "Extracting device type\n" ); | ||||
|  | ||||
| @@ -236,13 +232,12 @@ int AdvertiseAndReply( IN int AdFlag, | ||||
|  | ||||
|         UpnpPrintf( UPNP_INFO, API, __FILE__, __LINE__, | ||||
|             "Sending UDNStr = %s \n", UDNstr ); | ||||
|             if( AdFlag ) { | ||||
|         if( AdFlag ) { | ||||
|             // send the device advertisement  | ||||
|             if( AdFlag == 1 ) { | ||||
|                 DeviceAdvertisement( devType, i == 0, | ||||
|                                      UDNstr, SInfo->DescURL, Exp ); | ||||
|             } else              // AdFlag == -1 | ||||
|             { | ||||
|             } else {             // AdFlag == -1 | ||||
|                 DeviceShutdown( devType, i == 0, UDNstr, | ||||
|                                 SERVER, SInfo->DescURL, Exp ); | ||||
|             } | ||||
| @@ -324,8 +319,9 @@ int AdvertiseAndReply( IN int AdFlag, | ||||
|         } | ||||
|         for( j = 0;; j++ ) { | ||||
|             tmpNode = ixmlNodeList_item( nodeList, j ); | ||||
|             if( tmpNode == NULL ) | ||||
|             if( tmpNode == NULL ) { | ||||
|                 break; | ||||
|             } | ||||
|  | ||||
|             ixmlNodeList_free( tmpNodeList ); | ||||
|             tmpNodeList = NULL; | ||||
| @@ -334,7 +330,7 @@ int AdvertiseAndReply( IN int AdFlag, | ||||
|             if( tmpNodeList == NULL ) { | ||||
|                 UpnpPrintf( UPNP_CRITICAL, API, __FILE__, __LINE__, | ||||
|                     "ServiceType not found \n" ); | ||||
|                     continue; | ||||
|                 continue; | ||||
|             } | ||||
|             tmpNode2 = ixmlNodeList_item( tmpNodeList, 0 ); | ||||
|             if( tmpNode2 == NULL ) { | ||||
| @@ -367,26 +363,21 @@ int AdvertiseAndReply( IN int AdFlag, | ||||
|             } else { | ||||
|                 switch ( SearchType ) { | ||||
|                     case SSDP_ALL: | ||||
|                         { | ||||
|                             ServiceReply( DestAddr, servType, | ||||
|                                           UDNstr, SInfo->DescURL, | ||||
|                                           defaultExp ); | ||||
|                             break; | ||||
|                         } | ||||
|                         ServiceReply( DestAddr, servType, | ||||
|                                       UDNstr, SInfo->DescURL, | ||||
|                                       defaultExp ); | ||||
|                         break; | ||||
|                     case SSDP_SERVICE: | ||||
|                         { | ||||
|                             if( ServiceType != NULL ) { | ||||
|                                 if( !strncasecmp( ServiceType, | ||||
|                                                   servType, | ||||
|                                                   strlen( ServiceType ) ) ) | ||||
|                                 { | ||||
|                                     ServiceReply( DestAddr, servType, | ||||
|                                                   UDNstr, SInfo->DescURL, | ||||
|                                                   defaultExp ); | ||||
|                                 } | ||||
|                         if( ServiceType != NULL ) { | ||||
|                             if( !strncasecmp( ServiceType, | ||||
|                                               servType, | ||||
|                                               strlen( ServiceType ) ) ) { | ||||
|                                 ServiceReply( DestAddr, servType, | ||||
|                                               UDNstr, SInfo->DescURL, | ||||
|                                               defaultExp ); | ||||
|                             } | ||||
|                             break; | ||||
|                         } | ||||
|                         break; | ||||
|                     default: | ||||
|                         break; | ||||
|                 }               // switch(SearchType)                | ||||
| @@ -401,7 +392,7 @@ int AdvertiseAndReply( IN int AdFlag, | ||||
|     UpnpPrintf( UPNP_ALL, API, __FILE__, __LINE__, | ||||
|         "Exiting AdvertiseAndReply : \n" ); | ||||
|  | ||||
|     HandleUnlock(  ); | ||||
|     HandleUnlock(); | ||||
|  | ||||
|     return UPNP_E_SUCCESS; | ||||
|  | ||||
| @@ -445,7 +436,7 @@ Make_Socket_NoBlocking( int sock ) | ||||
| * Parameters: | ||||
| *	IN char *cmd: Service Name string | ||||
| *	OUT SsdpEvent *Evt: The SSDP event structure partially filled | ||||
| *						by all the function. | ||||
| *		by all the function. | ||||
| * | ||||
| * Description: | ||||
| *	This function fills the fields of the event structure like DeviceType, | ||||
| @@ -819,18 +810,20 @@ readFromSSDPSocket( SOCKET socket ) | ||||
|                              ( struct sockaddr * )&clientAddr, &socklen ); | ||||
|  | ||||
|     if( byteReceived > 0 ) { | ||||
|  | ||||
|         requestBuf[byteReceived] = '\0'; | ||||
|         UpnpPrintf( UPNP_INFO, SSDP, | ||||
|                              __FILE__, __LINE__, | ||||
|                              "Received response !!!  " | ||||
|                              "%s From host %s \n", | ||||
|                              requestBuf, | ||||
|                              inet_ntoa( clientAddr.sin_addr ) ); | ||||
|  | ||||
|             __FILE__, __LINE__, | ||||
|             "Start of received response ----------------------------------------------------\n" | ||||
|             "%s\n" | ||||
|             "End of received response ------------------------------------------------------\n" | ||||
|             "From host %s\n", | ||||
|             requestBuf, | ||||
|             inet_ntoa( clientAddr.sin_addr ) ); | ||||
|         UpnpPrintf( UPNP_PACKET, SSDP, __FILE__, __LINE__, | ||||
|             "Received multicast packet:" | ||||
|             "\n %s\n", requestBuf ); | ||||
|             "Start of received multicast packet --------------------------------------------\n" | ||||
|             "%s\n" | ||||
|             "End of received multicast packet ----------------------------------------------\n", | ||||
|             requestBuf ); | ||||
|         //add thread pool job to handle request | ||||
|         if( data != NULL ) { | ||||
|             data->parser.msg.msg.length += byteReceived; | ||||
| @@ -869,8 +862,7 @@ get_ssdp_sockets( MiniServerSockArray * out ) | ||||
| { | ||||
|     SOCKET ssdpSock; | ||||
|  | ||||
|     CLIENTONLY( SOCKET ssdpReqSock; | ||||
|          ) | ||||
|     CLIENTONLY( SOCKET ssdpReqSock; ) | ||||
|     int onOff = 1; | ||||
|     u_char ttl = 4; | ||||
|     struct ip_mreq ssdpMcastAddr; | ||||
| @@ -878,32 +870,31 @@ get_ssdp_sockets( MiniServerSockArray * out ) | ||||
|     int option = 1; | ||||
|     struct in_addr addr; | ||||
|  | ||||
|     CLIENTONLY( if( ( ssdpReqSock = socket( AF_INET, SOCK_DGRAM, 0 ) ) | ||||
|                     == UPNP_INVALID_SOCKET ) { | ||||
|                 UpnpPrintf( UPNP_CRITICAL, | ||||
|                     SSDP, __FILE__, __LINE__, | ||||
|                     "Error in socket operation !!!\n" ); | ||||
|                 return UPNP_E_OUTOF_SOCKET;} | ||||
|                 setsockopt( ssdpReqSock, | ||||
|                             IPPROTO_IP, | ||||
|                             IP_MULTICAST_TTL, &ttl, sizeof( ttl ) ); | ||||
|                 // just do it, regardless if fails or not. | ||||
|                 Make_Socket_NoBlocking( ssdpReqSock ); gSsdpReqSocket = ssdpReqSock; )  //CLIENTONLY | ||||
|  | ||||
|         if( ( ssdpSock = socket( AF_INET, SOCK_DGRAM, 0 ) ) | ||||
|             == UPNP_INVALID_SOCKET ) { | ||||
|             UpnpPrintf( UPNP_CRITICAL, | ||||
|                 SSDP, __FILE__, __LINE__, | ||||
|                 "Error in socket operation !!!\n" ); | ||||
|             CLIENTONLY( shutdown( ssdpReqSock, SD_BOTH ) ); | ||||
|             CLIENTONLY( UpnpCloseSocket( ssdpReqSock ) ); | ||||
| CLIENTONLY( | ||||
|     if( ( ssdpReqSock = socket( AF_INET, SOCK_DGRAM, 0 ) ) == UPNP_INVALID_SOCKET ) { | ||||
|         UpnpPrintf( UPNP_CRITICAL, | ||||
|             SSDP, __FILE__, __LINE__, | ||||
|             "Error in socket operation !!!\n" ); | ||||
|             return UPNP_E_OUTOF_SOCKET; | ||||
|         } | ||||
|     } | ||||
|     setsockopt( ssdpReqSock, IPPROTO_IP, IP_MULTICAST_TTL, &ttl, sizeof( ttl ) ); | ||||
|     // just do it, regardless if fails or not. | ||||
|     Make_Socket_NoBlocking( ssdpReqSock ); | ||||
|     gSsdpReqSocket = ssdpReqSock; ) | ||||
| // END CLIENTONLY | ||||
|  | ||||
|     if( ( ssdpSock = socket( AF_INET, SOCK_DGRAM, 0 ) ) == UPNP_INVALID_SOCKET ) { | ||||
|         UpnpPrintf( UPNP_CRITICAL, | ||||
|             SSDP, __FILE__, __LINE__, | ||||
|             "Error in socket operation !!!\n" ); | ||||
|         CLIENTONLY( shutdown( ssdpReqSock, SD_BOTH ) ); | ||||
|         CLIENTONLY( UpnpCloseSocket( ssdpReqSock ) ); | ||||
|         return UPNP_E_OUTOF_SOCKET; | ||||
|     } | ||||
|  | ||||
|     onOff = 1; | ||||
|     if( setsockopt( ssdpSock, SOL_SOCKET, SO_REUSEADDR, | ||||
|                     ( char * )&onOff, sizeof( onOff ) ) != 0 ) { | ||||
|  | ||||
|             ( char * )&onOff, sizeof( onOff ) ) != 0 ) { | ||||
|         UpnpPrintf( UPNP_CRITICAL, | ||||
|             SSDP, __FILE__, __LINE__, | ||||
|             "Error in set reuse addr !!!\n" ); | ||||
| @@ -916,8 +907,7 @@ get_ssdp_sockets( MiniServerSockArray * out ) | ||||
|      | ||||
|     #ifdef __FreeBSD__ | ||||
|     if( setsockopt( ssdpSock, SOL_SOCKET, SO_REUSEPORT, | ||||
|                     ( char * )&onOff, sizeof( onOff ) ) != 0 ) { | ||||
|  | ||||
|             ( char * )&onOff, sizeof( onOff ) ) != 0 ) { | ||||
|         UpnpPrintf( UPNP_CRITICAL, | ||||
|             SSDP, __FILE__, __LINE__, | ||||
|             "Error in set reuse port !!!\n" ); | ||||
| @@ -934,9 +924,8 @@ get_ssdp_sockets( MiniServerSockArray * out ) | ||||
|     //  ssdpAddr.sin_addr.s_addr = inet_addr(LOCAL_HOST); | ||||
|     ssdpAddr.sin_addr.s_addr = htonl( INADDR_ANY ); | ||||
|     ssdpAddr.sin_port = htons( SSDP_PORT ); | ||||
|     if( bind | ||||
|         ( ssdpSock, ( struct sockaddr * )&ssdpAddr, | ||||
|           sizeof( ssdpAddr ) ) != 0 ) { | ||||
|     if( bind( ssdpSock, ( struct sockaddr * )&ssdpAddr, | ||||
|             sizeof( ssdpAddr ) ) != 0 ) { | ||||
|         UpnpPrintf( UPNP_CRITICAL, | ||||
|             SSDP, __FILE__, __LINE__, | ||||
|             "Error in binding !!!\n" ); | ||||
| @@ -951,8 +940,7 @@ get_ssdp_sockets( MiniServerSockArray * out ) | ||||
|     ssdpMcastAddr.imr_interface.s_addr = inet_addr( LOCAL_HOST ); | ||||
|     ssdpMcastAddr.imr_multiaddr.s_addr = inet_addr( SSDP_IP ); | ||||
|     if( setsockopt( ssdpSock, IPPROTO_IP, IP_ADD_MEMBERSHIP, | ||||
|                     ( char * )&ssdpMcastAddr, | ||||
|                     sizeof( struct ip_mreq ) ) != 0 ) { | ||||
|             ( char * )&ssdpMcastAddr, sizeof( struct ip_mreq ) ) != 0 ) { | ||||
|         UpnpPrintf( UPNP_CRITICAL, | ||||
|             SSDP, __FILE__, __LINE__, | ||||
|             "Error in joining" " multicast group !!!\n" ); | ||||
| @@ -966,8 +954,8 @@ get_ssdp_sockets( MiniServerSockArray * out ) | ||||
|     /* Set multicast interface. */ | ||||
|     memset( ( void * )&addr, 0, sizeof( struct in_addr )); | ||||
|     addr.s_addr = inet_addr(LOCAL_HOST); | ||||
|     if (setsockopt(ssdpSock, IPPROTO_IP, IP_MULTICAST_IF, | ||||
|                    (char *)&addr, sizeof addr) != 0) { | ||||
|     if ( setsockopt(ssdpSock, IPPROTO_IP, IP_MULTICAST_IF, | ||||
|             (char *)&addr, sizeof addr) != 0) { | ||||
|         UpnpPrintf( UPNP_INFO, SSDP, __FILE__, __LINE__, | ||||
|             "Couldn't set multicast interface.\n" ); | ||||
|         /* This is probably not a critical error, so let's continue. */ | ||||
| @@ -977,7 +965,7 @@ get_ssdp_sockets( MiniServerSockArray * out ) | ||||
|     setsockopt( ssdpSock, IPPROTO_IP, | ||||
|                 IP_MULTICAST_TTL, &ttl, sizeof( ttl ) ); | ||||
|     if( setsockopt( ssdpSock, SOL_SOCKET, SO_BROADCAST, | ||||
|                     ( char * )&option, sizeof( option ) ) != 0 ) { | ||||
|             (char *)&option, sizeof(option) ) != 0) { | ||||
|         UpnpPrintf( UPNP_CRITICAL, | ||||
|             SSDP, __FILE__, __LINE__, | ||||
|             "Error in setting broadcast !!!\n" ); | ||||
| @@ -988,10 +976,10 @@ get_ssdp_sockets( MiniServerSockArray * out ) | ||||
|         return UPNP_E_NETWORK_ERROR; | ||||
|     } | ||||
|  | ||||
|     CLIENTONLY( out->ssdpReqSock = ssdpReqSock; | ||||
|          ); | ||||
|     CLIENTONLY( out->ssdpReqSock = ssdpReqSock; ); | ||||
|     out->ssdpSock = ssdpSock; | ||||
|     return UPNP_E_SUCCESS; | ||||
| } | ||||
|  | ||||
| #endif // EXCLUDE_SSDP | ||||
|  | ||||
|   | ||||
| @@ -50,22 +50,11 @@ | ||||
| #define S43 15 | ||||
| #define S44 21 | ||||
|  | ||||
| static void MD5Transform PROTO_LIST( ( UINT4[4], | ||||
|                                        unsigned char[64] ) ); | ||||
| static void Encode PROTO_LIST( ( unsigned char *, | ||||
|                                  UINT4 *, | ||||
|                                  unsigned int ) ); | ||||
|  | ||||
| static void Decode PROTO_LIST( ( UINT4 *, | ||||
|                                  unsigned char *, | ||||
|                                  unsigned int ) ); | ||||
|  | ||||
| static void MD5_memcpy PROTO_LIST( ( POINTER, | ||||
|                                      POINTER, | ||||
|                                      unsigned int ) ); | ||||
| static void MD5_memset PROTO_LIST( ( POINTER, | ||||
|                                      int, | ||||
|                                      unsigned int ) ); | ||||
| static void MD5Transform PROTO_LIST((UINT4[4], unsigned char[64])); | ||||
| static void Encode PROTO_LIST((unsigned char *, UINT4 *, unsigned int)); | ||||
| static void Decode PROTO_LIST((UINT4 *, unsigned char *, unsigned int)); | ||||
| static void MD5_memcpy PROTO_LIST((POINTER, POINTER, unsigned int)); | ||||
| static void MD5_memset PROTO_LIST((POINTER, int, unsigned int)); | ||||
|  | ||||
| static unsigned char PADDING[64] = { | ||||
|     0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, | ||||
| @@ -118,14 +107,10 @@ static unsigned char PADDING[64] = { | ||||
|    MD5 initialization. Begins an MD5 operation, writing a new context.  | ||||
|  */ | ||||
| void | ||||
| MD5Init( context ) | ||||
|      MD5_CTX *context;          /* context */ | ||||
| MD5Init(MD5_CTX * context) | ||||
| { | ||||
|     context->count[0] = context->count[1] = 0; | ||||
|  | ||||
|     /* | ||||
|        Load magic initialization constants. | ||||
|      */ | ||||
|     /* Load magic initialization constants. */ | ||||
|     context->state[0] = 0x67452301; | ||||
|     context->state[1] = 0xefcdab89; | ||||
|     context->state[2] = 0x98badcfe; | ||||
| @@ -139,114 +124,72 @@ MD5Init( context ) | ||||
|  */ | ||||
|  | ||||
| void | ||||
| MD5Update( context, | ||||
|            input, | ||||
|            inputLen ) | ||||
|      MD5_CTX *context;          /* context */ | ||||
|      unsigned char *input;      /* input block */ | ||||
|      unsigned int inputLen;     /* length of input block */ | ||||
| MD5Update(MD5_CTX *context, unsigned char *input, unsigned int inputLen) | ||||
| { | ||||
|     unsigned int i, | ||||
|       index, | ||||
|       partLen; | ||||
| 	unsigned int i; | ||||
| 	unsigned int index; | ||||
| 	unsigned int partLen; | ||||
|  | ||||
|     /* | ||||
|        Compute number of bytes mod 64  | ||||
|      */ | ||||
|     index = ( unsigned int )( ( context->count[0] >> 3 ) & 0x3F ); | ||||
| 	/* Compute number of bytes mod 64 */ | ||||
| 	index = (unsigned int)((context->count[0] >> 3) & 0x3F); | ||||
|  | ||||
|     /* | ||||
|        Update number of bits  | ||||
|      */ | ||||
|     if( ( context->count[0] += | ||||
|           ( ( UINT4 ) inputLen << 3 ) ) < ( ( UINT4 ) inputLen << 3 ) ) | ||||
|         context->count[1]++; | ||||
| 	/* Update number of bits */ | ||||
| 	if ((context->count[0] += ((UINT4)inputLen << 3)) < ((UINT4)inputLen << 3)) { | ||||
| 		context->count[1]++; | ||||
| 	} | ||||
| 	context->count[1] += ((UINT4)inputLen >> 29); | ||||
| 	partLen = 64 - index; | ||||
|  | ||||
|     context->count[1] += ( ( UINT4 ) inputLen >> 29 ); | ||||
|  | ||||
|     partLen = 64 - index; | ||||
|  | ||||
|     /* | ||||
|        Transform as many times as possible. | ||||
|      */ | ||||
|     if( inputLen >= partLen ) { | ||||
|  | ||||
|         MD5_memcpy | ||||
|             ( ( POINTER ) & context->buffer[index], ( POINTER ) input, | ||||
|               partLen ); | ||||
|         MD5Transform( context->state, context->buffer ); | ||||
|  | ||||
|         for( i = partLen; i + 63 < inputLen; i += 64 ) | ||||
|             MD5Transform( context->state, &input[i] ); | ||||
|  | ||||
|         index = 0; | ||||
|     } else | ||||
|         i = 0; | ||||
|  | ||||
|     /* | ||||
|        Buffer remaining input  | ||||
|      */ | ||||
|     MD5_memcpy | ||||
|         ( ( POINTER ) & context->buffer[index], ( POINTER ) & input[i], | ||||
|           inputLen - i ); | ||||
| 	/* Transform as many times as possible. */ | ||||
| 	if (inputLen >= partLen) { | ||||
| 		MD5_memcpy((POINTER)&context->buffer[index], (POINTER)input, partLen); | ||||
| 		MD5Transform(context->state, context->buffer); | ||||
| 		for (i = partLen; i + 63 < inputLen; i += 64) { | ||||
| 			MD5Transform(context->state, &input[i]); | ||||
| 		} | ||||
| 		index = 0; | ||||
| 	} else { | ||||
| 		i = 0; | ||||
| 	} | ||||
|  | ||||
| 	/* Buffer remaining input */ | ||||
| 	MD5_memcpy((POINTER)&context->buffer[index], (POINTER)&input[i], inputLen - i); | ||||
| } | ||||
|  | ||||
| /* | ||||
|    MD5 finalization. Ends an MD5 message-digest operation, writing the | ||||
|    the message digest and zeroizing the context. | ||||
|  */ | ||||
|  | ||||
| void | ||||
| MD5Final( digest, | ||||
|           context ) | ||||
|      unsigned char digest[16];  /* message digest */ | ||||
|      MD5_CTX *context;          /* context */ | ||||
| MD5Final(unsigned char digest[16], MD5_CTX *context) | ||||
| { | ||||
|  | ||||
|     unsigned char bits[8]; | ||||
|     unsigned int index, | ||||
|       padLen; | ||||
|     unsigned int index; | ||||
|     unsigned int padLen; | ||||
|  | ||||
|     /* | ||||
|        Save number of bits  | ||||
|      */ | ||||
|     Encode( bits, context->count, 8 ); | ||||
|     /* Save number of bits */ | ||||
|     Encode(bits, context->count, 8); | ||||
|  | ||||
|     /* | ||||
|        Pad out to 56 mod 64. | ||||
|      */ | ||||
|     index = ( unsigned int )( ( context->count[0] >> 3 ) & 0x3f ); | ||||
|     /* Pad out to 56 mod 64. */ | ||||
|     index = (unsigned int)((context->count[0] >> 3) & 0x3f); | ||||
|     padLen = (index < 56) ? (56 - index) : (120 - index); | ||||
|     MD5Update(context, PADDING, padLen); | ||||
|  | ||||
|     padLen = ( index < 56 ) ? ( 56 - index ) : ( 120 - index ); | ||||
|     /* Append length (before padding) */ | ||||
|     MD5Update(context, bits, 8); | ||||
|  | ||||
|     MD5Update( context, PADDING, padLen ); | ||||
|  | ||||
|     /* | ||||
|        Append length (before padding)  | ||||
|      */ | ||||
|     MD5Update( context, bits, 8 ); | ||||
|  | ||||
|     /* | ||||
|        Store state in digest  | ||||
|      */ | ||||
|     Encode( digest, context->state, 16 ); | ||||
|  | ||||
|     /* | ||||
|        Zeroize sensitive information. | ||||
|      */ | ||||
|     MD5_memset( ( POINTER ) context, 0, sizeof( *context ) ); | ||||
|     /* Store state in digest */ | ||||
|     Encode(digest, context->state, 16); | ||||
|  | ||||
|     /* Zeroize sensitive information. */ | ||||
|     MD5_memset((POINTER)context, 0, sizeof(*context)); | ||||
| } | ||||
|  | ||||
| /* | ||||
|    MD5 basic transformation. Transforms state based on block.  | ||||
|  */ | ||||
| static void | ||||
| MD5Transform( state, | ||||
|               block ) | ||||
|      UINT4 state[4]; | ||||
|      unsigned char block[64]; | ||||
| MD5Transform(UINT4 state[4], unsigned char block[64]) | ||||
| { | ||||
|     UINT4 a = state[0], | ||||
|       b = state[1], | ||||
| @@ -353,23 +296,16 @@ MD5Transform( state, | ||||
|    a multiple of 4. | ||||
|  */ | ||||
| static void | ||||
| Encode( output, | ||||
|         input, | ||||
|         len ) | ||||
|      unsigned char *output; | ||||
|      UINT4 *input; | ||||
|      unsigned int len; | ||||
| Encode(unsigned char *output, UINT4 *input, unsigned int len) | ||||
| { | ||||
|     unsigned int i, | ||||
|       j; | ||||
|  | ||||
|     for( i = 0, j = 0; j < len; i++, j += 4 ) { | ||||
|         output[j] = ( unsigned char )( input[i] & 0xff ); | ||||
|         output[j + 1] = ( unsigned char )( ( input[i] >> 8 ) & 0xff ); | ||||
|         output[j + 2] = ( unsigned char )( ( input[i] >> 16 ) & 0xff ); | ||||
|         output[j + 3] = ( unsigned char )( ( input[i] >> 24 ) & 0xff ); | ||||
|     } | ||||
|  | ||||
| 	unsigned int i; | ||||
| 	unsigned int j; | ||||
| 	for (i = 0, j = 0; j < len; ++i, j += 4) { | ||||
| 		output[j+0] = (unsigned char)((input[i] >>  0) & 0xff); | ||||
| 		output[j+1] = (unsigned char)((input[i] >>  8) & 0xff); | ||||
| 		output[j+2] = (unsigned char)((input[i] >> 16) & 0xff); | ||||
| 		output[j+3] = (unsigned char)((input[i] >> 24) & 0xff); | ||||
| 	} | ||||
| } | ||||
|  | ||||
| /* | ||||
| @@ -378,55 +314,40 @@ Encode( output, | ||||
|  */ | ||||
|  | ||||
| static void | ||||
| Decode( output, | ||||
|         input, | ||||
|         len ) | ||||
|      UINT4 *output; | ||||
|      unsigned char *input; | ||||
|      unsigned int len; | ||||
| Decode(UINT4 *output, unsigned char *input, unsigned int len) | ||||
| { | ||||
|     unsigned int i, | ||||
|       j; | ||||
|  | ||||
|     for( i = 0, j = 0; j < len; i++, j += 4 ) | ||||
|         output[i] = | ||||
|             ( ( UINT4 ) input[j] ) | ( ( ( UINT4 ) input[j + 1] ) << 8 ) | | ||||
|             ( ( ( UINT4 ) input[j + 2] ) << 16 ) | | ||||
|             ( ( ( UINT4 ) input[j + 3] ) << 24 ); | ||||
| 	unsigned int i; | ||||
| 	unsigned int j; | ||||
| 	for (i = 0, j = 0; j < len; ++i, j += 4) { | ||||
| 		output[i] = | ||||
| 			(((UINT4)input[j+0]) <<  0) | | ||||
| 			(((UINT4)input[j+1]) <<  8) | | ||||
| 			(((UINT4)input[j+2]) << 16) | | ||||
| 			(((UINT4)input[j+3]) << 24); | ||||
| 	} | ||||
| } | ||||
|  | ||||
| /* | ||||
|    Note: Replace "for loop" with standard memcpy if possible. | ||||
|    Note: Replace for loop with standard memcpy if possible. | ||||
|  */ | ||||
| static void | ||||
| MD5_memcpy( output, | ||||
|             input, | ||||
|             len ) | ||||
|      POINTER output; | ||||
|      POINTER input; | ||||
|      unsigned int len; | ||||
| MD5_memcpy(POINTER  output, POINTER  input, unsigned int len) | ||||
| { | ||||
|     unsigned int i; | ||||
|  | ||||
|     for( i = 0; i < len; i++ ) | ||||
|         output[i] = input[i]; | ||||
|  | ||||
| 	unsigned int i; | ||||
| 	for (i = 0; i < len; ++i) { | ||||
| 		output[i] = input[i]; | ||||
| 	} | ||||
| } | ||||
|  | ||||
| /* | ||||
|    Note: Replace "for loop" with standard memset if possible. | ||||
|    Note: Replace for loop with standard memset if possible. | ||||
|  */ | ||||
| static void | ||||
| MD5_memset( output, | ||||
|             value, | ||||
|             len ) | ||||
|      POINTER output; | ||||
|      int value; | ||||
|      unsigned int len; | ||||
| MD5_memset(POINTER output, int value, unsigned int len) | ||||
| { | ||||
|     unsigned int i; | ||||
|  | ||||
|     for( i = 0; i < len; i++ ) | ||||
|         ( ( char * )output )[i] = ( char )value; | ||||
|  | ||||
| 	unsigned int i; | ||||
| 	for (i = 0; i < len; ++i) { | ||||
| 		((char *)output)[i] = (char)value; | ||||
| 	} | ||||
| } | ||||
|  | ||||
|   | ||||
| @@ -33,17 +33,16 @@ | ||||
|    This sample implementation generates a random node ID | ||||
|  */ | ||||
| void | ||||
| get_ieee_node_identifier( uuid_node_t * node ) | ||||
| get_ieee_node_identifier(uuid_node_t *node) | ||||
| { | ||||
|     char seed[16]; | ||||
|     static int inited = 0; | ||||
|     static uuid_node_t saved_node; | ||||
|  | ||||
|     if( !inited ) { | ||||
|         get_random_info( seed ); | ||||
|     if (!inited) { | ||||
|         get_random_info(seed); | ||||
|         seed[0] |= 0x80; | ||||
|         memcpy( &saved_node, seed, sizeof( uuid_node_t ) ); | ||||
|  | ||||
|         memcpy(&saved_node, seed, sizeof (uuid_node_t)); | ||||
|         inited = 1; | ||||
|     }; | ||||
|  | ||||
| @@ -83,52 +82,48 @@ get_system_time( uuid_time_t * uuid_time ) | ||||
|  | ||||
| /*-----------------------------------------------------------------------------*/ | ||||
| void | ||||
| get_random_info( char seed[16] ) | ||||
| get_random_info(char seed[16]) | ||||
| { | ||||
|     MD5_CTX c; | ||||
|     typedef struct { | ||||
|         MEMORYSTATUS m; | ||||
|         SYSTEM_INFO s; | ||||
|         FILETIME t; | ||||
|         LARGE_INTEGER pc; | ||||
|         DWORD tc; | ||||
|         DWORD l; | ||||
|         char hostname[MAX_COMPUTERNAME_LENGTH + 1]; | ||||
|     } randomness; | ||||
|     randomness r; | ||||
| 	MD5_CTX c; | ||||
| 	typedef struct { | ||||
| 		MEMORYSTATUS m; | ||||
| 		SYSTEM_INFO s; | ||||
| 		FILETIME t; | ||||
| 		LARGE_INTEGER pc; | ||||
| 		DWORD tc; | ||||
| 		DWORD l; | ||||
| 		char hostname[MAX_COMPUTERNAME_LENGTH + 1]; | ||||
| 	} randomness; | ||||
| 	randomness r; | ||||
|  | ||||
|     MD5Init( &c ); | ||||
|     /* | ||||
|        memory usage stats  | ||||
|      */ | ||||
|     GlobalMemoryStatus( &r.m ); | ||||
|     /* | ||||
|        random system stats  | ||||
|      */ | ||||
|     GetSystemInfo( &r.s ); | ||||
|     /* | ||||
|        100ns resolution (nominally) time of day  | ||||
|      */ | ||||
|     GetSystemTimeAsFileTime( &r.t ); | ||||
|     /* | ||||
|        high resolution performance counter  | ||||
|      */ | ||||
|     QueryPerformanceCounter( &r.pc ); | ||||
|     /* | ||||
|        milliseconds since last boot  | ||||
|      */ | ||||
|     r.tc = GetTickCount(  ); | ||||
|     r.l = MAX_COMPUTERNAME_LENGTH + 1; | ||||
| 	/* Initialize memory area so that valgrind does not complain */ | ||||
| 	memset(&r, 0, sizeof r); | ||||
|  | ||||
|     GetComputerName( r.hostname, &r.l ); | ||||
|     MD5Update( &c, &r, sizeof( randomness ) ); | ||||
|     MD5Final( seed, &c ); | ||||
| 	/* memory usage stats */ | ||||
| 	GlobalMemoryStatus( &r.m ); | ||||
| 	/* random system stats */ | ||||
| 	GetSystemInfo( &r.s ); | ||||
| 	/* 100ns resolution (nominally) time of day */ | ||||
| 	GetSystemTimeAsFileTime( &r.t ); | ||||
| 	/* high resolution performance counter */ | ||||
| 	QueryPerformanceCounter( &r.pc ); | ||||
| 	/* milliseconds since last boot */ | ||||
| 	r.tc = GetTickCount(); | ||||
| 	r.l = MAX_COMPUTERNAME_LENGTH + 1; | ||||
|  | ||||
| 	GetComputerName( r.hostname, &r.l ); | ||||
|  | ||||
| 	/* MD5 it */ | ||||
| 	MD5Init(&c); | ||||
| 	MD5Update(&c, &r, sizeof r); | ||||
| 	MD5Final(seed, &c); | ||||
| }; | ||||
| #else | ||||
|  | ||||
| #else /* _WINDOWS_ */ | ||||
|  | ||||
| /*-----------------------------------------------------------------------------*/ | ||||
| void | ||||
| get_system_time( uuid_time_t * uuid_time ) | ||||
| get_system_time(uuid_time_t *uuid_time) | ||||
| { | ||||
|     struct timeval tp; | ||||
|  | ||||
| @@ -145,22 +140,28 @@ get_system_time( uuid_time_t * uuid_time ) | ||||
|  | ||||
| /*-----------------------------------------------------------------------------*/ | ||||
| void | ||||
| get_random_info( char seed[16] ) | ||||
| get_random_info(char seed[16]) | ||||
| { | ||||
|     MD5_CTX c; | ||||
|     typedef struct { | ||||
| //        struct sysinfo s; | ||||
|         struct timeval t; | ||||
|         char hostname[257]; | ||||
|     } randomness; | ||||
|     randomness r; | ||||
| 	MD5_CTX c; | ||||
| 	typedef struct { | ||||
| 		//struct sysinfo s; | ||||
| 		struct timeval t; | ||||
| 		char hostname[257]; | ||||
| 	} randomness; | ||||
| 	randomness r; | ||||
|  | ||||
|     MD5Init( &c ); | ||||
| 	/* Initialize memory area so that valgrind does not complain */ | ||||
| 	memset(&r, 0, sizeof r); | ||||
|  | ||||
|     gettimeofday( &r.t, ( struct timezone * )0 ); | ||||
|     gethostname( r.hostname, 256 ); | ||||
|     MD5Update( &c, &r, sizeof( randomness ) ); | ||||
|     MD5Final( seed, &c ); | ||||
| 	/* Get some random stuff */ | ||||
| 	gettimeofday(&r.t, (struct timezone *)0); | ||||
| 	gethostname(r.hostname, 256 ); | ||||
|  | ||||
| 	/* MD5 it */ | ||||
| 	MD5Init(&c); | ||||
| 	MD5Update(&c, &r, sizeof r); | ||||
| 	MD5Final(seed, &c); | ||||
| }; | ||||
|  | ||||
| #endif | ||||
| #endif /* _WINDOWS_ */ | ||||
|  | ||||
|   | ||||
| @@ -53,10 +53,10 @@ static unsigned16 true_random( void ); | ||||
|    uuid_create -- generator a UUID  | ||||
|  */ | ||||
| int | ||||
| uuid_create( uuid_upnp * uid ) | ||||
| uuid_create(uuid_upnp *uid) | ||||
| { | ||||
|     uuid_time_t timestamp, | ||||
|       last_time; | ||||
|     uuid_time_t timestamp; | ||||
|     uuid_time_t last_time; | ||||
|     unsigned16 clockseq; | ||||
|     uuid_node_t node; | ||||
|     uuid_node_t last_node; | ||||
| @@ -65,61 +65,64 @@ uuid_create( uuid_upnp * uid ) | ||||
|     /* | ||||
|        acquire system wide lock so we're alone  | ||||
|      */ | ||||
|     UUIDLock(  ); | ||||
|     UUIDLock(); | ||||
|  | ||||
|     /* | ||||
|        get current time  | ||||
|      */ | ||||
|     get_current_time( ×tamp ); | ||||
|     get_current_time(×tamp); | ||||
|  | ||||
|     /* | ||||
|        get node ID  | ||||
|      */ | ||||
|     get_ieee_node_identifier( &node ); | ||||
|     get_ieee_node_identifier(&node); | ||||
|  | ||||
|     /* | ||||
|        get saved state from NV storage  | ||||
|      */ | ||||
|     f = read_state( &clockseq, &last_time, &last_node ); | ||||
|     f = read_state(&clockseq, &last_time, &last_node); | ||||
|  | ||||
|     /* | ||||
|        if no NV state, or if clock went backwards, or node ID changed | ||||
|        (e.g., net card swap) change clockseq  | ||||
|      */ | ||||
|     if( !f || memcmp( &node, &last_node, sizeof( uuid_node_t ) ) ) | ||||
|         clockseq = true_random(  ); | ||||
|     else if( timestamp < last_time ) | ||||
|     if (!f || memcmp(&node, &last_node, sizeof(uuid_node_t))) { | ||||
|         clockseq = true_random(); | ||||
|     } else if (timestamp < last_time) { | ||||
|         clockseq++; | ||||
|     } | ||||
|  | ||||
|     /* | ||||
|        stuff fields into the UUID  | ||||
|      */ | ||||
|     format_uuid_v1( uid, clockseq, timestamp, node ); | ||||
|     format_uuid_v1(uid, clockseq, timestamp, node); | ||||
|  | ||||
|     /* | ||||
|        save the state for next time  | ||||
|      */ | ||||
|     write_state( clockseq, timestamp, node ); | ||||
|     write_state(clockseq, timestamp, node); | ||||
|  | ||||
|     UUIDUnlock(  ); | ||||
|     return ( 1 ); | ||||
|     UUIDUnlock(); | ||||
|     return 1; | ||||
| }; | ||||
|  | ||||
| /*-----------------------------------------------------------------------------*/ | ||||
| void | ||||
| uuid_unpack( uuid_upnp * u, | ||||
|              char *out ) | ||||
| uuid_unpack(uuid_upnp *u, char *out) | ||||
| { | ||||
|  | ||||
|     sprintf( out, | ||||
|              "%8.8x-%4.4x-%4.4x-%2.2x%2.2x-%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x", | ||||
|              ( unsigned int )u->time_low, u->time_mid, | ||||
|              u->time_hi_and_version, u->clock_seq_hi_and_reserved, | ||||
|              u->clock_seq_low, u->node[0], u->node[1], u->node[2], | ||||
|              u->node[3], u->node[4], u->node[5] ); | ||||
|  | ||||
|     *( out + 36 ) = '\0'; | ||||
|  | ||||
| 	sprintf(out, | ||||
| 		"%8.8x-%4.4x-%4.4x-%2.2x%2.2x-%2.2x%2.2x%2.2x%2.2x%2.2x%2.2x", | ||||
| 		(unsigned int)u->time_low, | ||||
| 		u->time_mid, | ||||
| 		u->time_hi_and_version, | ||||
| 		u->clock_seq_hi_and_reserved, | ||||
| 		u->clock_seq_low, | ||||
| 		u->node[0], | ||||
| 		u->node[1], | ||||
| 		u->node[2], | ||||
| 		u->node[3], | ||||
| 		u->node[4], | ||||
| 		u->node[5]); | ||||
| }; | ||||
|  | ||||
| /*-----------------------------------------------------------------------------*/ | ||||
| @@ -137,11 +140,10 @@ format_uuid_v1( uuid_upnp * uid, | ||||
|        Construct a version 1 uuid with the information we've gathered | ||||
|        * plus a few constants.  | ||||
|      */ | ||||
|     uid->time_low = ( unsigned long )( timestamp & 0xFFFFFFFF ); | ||||
|     uid->time_mid = ( unsigned short )( ( timestamp >> 32 ) & 0xFFFF ); | ||||
|     uid->time_hi_and_version = ( unsigned short )( ( timestamp >> 48 ) & | ||||
|                                                    0x0FFF ); | ||||
|     uid->time_hi_and_version |= ( 1 << 12 ); | ||||
|     uid->time_low = (unsigned long)(timestamp & 0xFFFFFFFF); | ||||
|     uid->time_mid = (unsigned short)((timestamp >> 32) & 0xFFFF); | ||||
|     uid->time_hi_and_version = (unsigned short)((timestamp >> 48) & 0x0FFF); | ||||
|     uid->time_hi_and_version |= (1 << 12); | ||||
|     uid->clock_seq_low = clock_seq & 0xFF; | ||||
|     uid->clock_seq_hi_and_reserved = ( clock_seq & 0x3F00 ) >> 8; | ||||
|     uid->clock_seq_hi_and_reserved |= 0x80; | ||||
| @@ -227,7 +229,6 @@ get_current_time( uuid_time_t * timestamp ) | ||||
|     static int inited = 0; | ||||
|  | ||||
|     if( !inited ) { | ||||
|         get_system_time( &time_now ); | ||||
|         uuids_this_tick = UUIDS_PER_TICK; | ||||
|         inited = 1; | ||||
|     }; | ||||
|   | ||||
| @@ -105,7 +105,7 @@ main (int argc, char* argv[]) | ||||
| 	 * Test library initialisation | ||||
| 	 */ | ||||
| 	printf ("\n"); | ||||
| 	printf ("Intializing UPnP ... \n"); | ||||
| 	printf ("Initializing UPnP ... \n"); | ||||
| 	rc = UpnpInit (NULL, 0); | ||||
| 	if ( UPNP_E_SUCCESS == rc ) { | ||||
| 		const char* ip_address = UpnpGetServerIpAddress(); | ||||
|   | ||||
		Reference in New Issue
	
	Block a user