/home/dko/projects/mobilec/trunk/src/include/macros.h

Go to the documentation of this file.
00001 /*[
00002  * Copyright (c) 2007 Integration Engineering Laboratory
00003                       University of California, Davis
00004  *
00005  * Permission to use, copy, and distribute this software and its
00006  * documentation for any purpose with or without fee is hereby granted,
00007  * provided that the above copyright notice appear in all copies and
00008  * that both that copyright notice and this permission notice appear
00009  * in supporting documentation.
00010  *
00011  * Permission to modify the software is granted, but not the right to
00012  * distribute the complete modified source code.  Modifications are to
00013  * be distributed as patches to the released version.  Permission to
00014  * distribute binaries produced by compiling modified sources is granted,
00015  * provided you
00016  *   1. distribute the corresponding source modifications from the
00017  *    released version in the form of a patch file along with the binaries,
00018  *   2. add special version identification to distinguish your version
00019  *    in addition to the base release version number,
00020  *   3. provide your name and address as the primary contact for the
00021  *    support of your modified version, and
00022  *   4. retain our contact information in regard to use of the base
00023  *    software.
00024  * Permission to distribute the released version of the source code along
00025  * with corresponding source modifications in the form of a patch file is
00026  * granted with same provisions 2 through 4 for binary distributions.
00027  *
00028  * This software is provided "as is" without express or implied warranty
00029  * to the extent permitted by applicable law.
00030 ]*/
00031 
00032 /* Macro Synopses
00033  *
00034  *      Error Checking
00035  *
00036  * CHECK_NULL(var, action) : Checks value of 'var' for NULL. If it is 
00037  *      null, an error message is printed to stderr and 'action' is 
00038  *      performed.
00039  *
00040  *      Thread Creation/Cancellation
00041  *
00042  * GET_THREAD_MODE(started_threads, thread): Returns 1 if 'thread' is set 
00043  *      run in 'started_threads'.
00044  * SET_THREAD_ON(a, b) : Sets thread 'b' to 'on' in status 'a'.
00045  * SET_THREAD_OFF(a, b) : See SET_THREAD_ON
00046  *
00047  *      Thread Syncronization
00048  *
00049  * MUTEX_T : Platform independant mutex data type.
00050  * COND_T : Platform independant condition variable data type.
00051  * MUTEX_INIT( mutex ) : Platform ind. mutex initialization.
00052  * COND_INIT(cond) : Platform ind. condition variable initialization.
00053  * MUTEX_DESTROY(mutex) : Platform ind. mutex variable destruction.
00054  * COND_DESTROY(cond) : Platform ind. cond variable destruction.
00055  * MUTEX_LOCK(mutex) : Locks mutex 'mutex'.
00056  * MUTEX_UNLOCK(mutex) : Unlocks mutex 'mutex'.
00057  * SIGNAL(cond, mutex, action) : Sends a signal to condition variable
00058  *      'cond' protected by mutex 'mutex'. Executes action 'action' after
00059  *      locking mutex 'mutex' but before signalling the condition 
00060  *      variable.
00061  * WAKE_QUEUE(queue) : Signals and activates a thread sleeping on one
00062  *      of the system queues.
00063  * COND_SLEEP(cond, mutex) : Causes a thread to sleep on a condition 
00064  *      variable 'cond', protected by 'mutex'.
00065  * COND_RESET(cond, mutex) : Resets condition variables after being
00066  *      woken from COND_SLEEP.
00067  *
00068  *      Ch Datatype Conversions
00069  *
00070  * CH_DATATYPE_SIZE(type, size) : Takes 'ChType_t type' as input,
00071  *      fills 'size' with the byte size of 'type'.
00072  * CH_DATATYPE_STRING(type, string) : Takes 'ChType_t type' as input,
00073  *      fills 'char* string' with a string of the type. 
00074  * CH_STRING_DATATYPE(string, type) : Takes 'char* string' as input
00075  *      and fills 'ChType_t type'
00076  * Ch_DATATYPE_STR_TO_VAL(type, string, val) : Takes 'ChType_t type' and
00077  *      'char* string' as input and fills 'void* val' with the value
00078  *      contained within 'string'.
00079  */
00080 #ifndef _MACROS_H_
00081 #define _MACROS_H_
00082 
00083 #ifndef _WIN32
00084 #include <pthread.h>
00085 #include <semaphore.h>
00086 #include "config.h"
00087 #else
00088 #include <windows.h>
00089 #endif
00090 
00091 /* * * * * * * * * * * * * * *
00092  * T H R E A D   S T A T U S *
00093  * * * * * * * * * * * * * * */
00094 
00095 /*************************************
00096  * AI => Agent Initializing Thread   * 
00097  * AM => Agent Managing Thread       * 
00098  * CL => Connection Listening Thread * 
00099  * DF => Directory Facilitator Thr.  *
00100  * MR => Message Receiving Thread    * 
00101  * MS => Message Sending Thread      * 
00102  * CP => Command Prompt Thread       * 
00103  *************************************/
00104 
00105 /* GET_THREAD_MODE Macro:
00106  * Usage: GET_THREAD_MODE(runthreads, MC_THREAD_AM)
00107  * Returns 1 if thread is set to run, 0 otherwise. */
00108 #define GET_THREAD_MODE(a, b) ( (a & (1<<b)) / (1<<b) )
00109 
00110 /* SET_THREAD_XXX(runthreads, XX_THREAD); */
00111 #define SET_THREAD_ON(a, b) a = (a | (1<<b))
00112 #define SET_THREAD_OFF(a, b) a = (a & (~(1<<b)))
00113 
00114 
00115 /* Struct Macro */
00116 #define STRUCT( name, members ) \
00117   typedef struct name##_s { \
00118     members \
00119   } name##_t; \
00120 typedef name##_t* name##_p;
00121 
00122 
00123 /* * * * * * * * * * * * *
00124  * U N I X   M A C R O S *
00125  * * * * * * * * * * * * */               /* Windows macros follow */
00126 #ifndef _WIN32
00127 
00128 /* ****** *
00129  * THREAD *
00130  * ****** */
00131 #define PTHREAD_STACK_SIZE 131072 /* This is PTHREAD_STACK_MIN * 8 for me */
00132 #define THREAD_T pthread_t
00133 #define THREAD_CREATE( thread_handle, function, arg ) \
00134   pthread_create( \
00135       thread_handle, \
00136       &attr, \
00137       function, \
00138       (void*) arg \
00139       )
00140 
00141 #define THREAD_CANCEL( thread_handle ) \
00142   pthread_cancel( thread_handle )
00143 
00144 #define THREAD_JOIN(thread_handle ) \
00145   pthread_join( thread_handle, NULL )
00146 
00147 /* ***** */
00148 /* MUTEX */
00149 /* ***** */
00150 
00151 /* Typedef */
00152 #define MUTEX_T pthread_mutex_t
00153 /* Init */
00154 #define MUTEX_INIT(mutex) \
00155   pthread_mutex_init(mutex, NULL)
00156 /* Destroy */
00157 #define MUTEX_DESTROY(mutex) \
00158   pthread_mutex_destroy(mutex)
00159 /* functions */
00160 #define MUTEX_LOCK(mutex)                                                   \
00161   if (pthread_mutex_lock( mutex ))                                        \
00162 fprintf(stderr, "pthread lock error: %s:%d\n", __FILE__, __LINE__)
00163 #define MUTEX_UNLOCK(mutex) \
00164   pthread_mutex_unlock( mutex )
00165 #define MUTEX_NEW(mutex) \
00166   mutex = (pthread_mutex_t*)malloc(sizeof(pthread_mutex_t)); \
00167   if (mutex == NULL)  \
00168     fprintf(stderr, "Memory Error. %s:%d\n", __FILE__,__LINE__); \
00169 
00170 /* **** *
00171  * COND *
00172  * **** */
00173 /* Typedef */
00174 #define COND_T pthread_cond_t
00175 /* Init */
00176 #define COND_INIT(cond) \
00177   pthread_cond_init(cond, NULL)
00178 /* Destroy */
00179 #define COND_DESTROY(cond) \
00180   pthread_cond_destroy(cond)
00181 /* functions */
00182 #define COND_WAIT( cond , mutex ) \
00183   pthread_cond_wait(cond, mutex )
00184 /* Wait until 'test' is true */
00185 #define COND_SLEEP( cond, mutex, test )       \
00186   if (pthread_mutex_lock( mutex ))    \
00187 printf("pthread lock error: %s:%d\n", __FILE__, __LINE__); \
00188 if (!test) { \
00189   pthread_cond_wait( cond, mutex ); \
00190 } 
00191 #define COND_RESET( cond, mutex ) \
00192   pthread_mutex_unlock( mutex );
00193 #define COND_SLEEP_ACTION(cond, mutex, action) \
00194   if (pthread_mutex_lock( mutex )) \
00195 printf("pthread lock error: %s:%d\n", __FILE__, __LINE__); \
00196 action; \
00197 pthread_cond_wait( cond, mutex ); 
00198 #define SIGNAL(cond, mutex, action) \
00199   pthread_mutex_lock( mutex ); \
00200 action; \
00201 pthread_cond_signal( cond ); \
00202 pthread_mutex_unlock( mutex )
00203 #define COND_BROADCAST(cond) \
00204   pthread_cond_broadcast( cond )
00205 #define COND_SIGNAL(cond) \
00206   pthread_cond_signal( cond )
00207 
00208 /* ********* *
00209  * SEMAPHORE *
00210  * ********* */
00211 /* Typedef */
00212 #define SEMAPHORE_T sem_t
00213 /* Init */
00214 #define SEMAPHORE_INIT(sem) \
00215   sem_init(sem, 0, 0)
00216 /* Destroy */
00217 #define SEMAPHORE_DESTROY(sem) \
00218   sem_destroy(sem)
00219 /* Functions */
00220 #define SEMAPHORE_WAIT(sem) \
00221   sem_wait(sem)
00222 #define SEMAPHORE_POST(sem) \
00223   sem_post(sem)
00224 
00225 /* ******* *
00226  * RW_LOCK *
00227  * ******* */
00228 /* Typedef */
00229 #ifdef HAVE_PTHREAD_RWLOCK_T
00230 #define RWLOCK_T pthread_rwlock_t
00231 #else
00232 #define RWLOCK_T mc_rwlock_t
00233 #endif
00234 /* Init */
00235 #ifdef HAVE_PTHREAD_RWLOCK_T
00236 #define RWLOCK_INIT(rwlock) \
00237   pthread_rwlock_init(rwlock, NULL)
00238 #else
00239 #define RWLOCK_INIT(rwlock) \
00240   mc_rwlock_init(rwlock)
00241 #endif
00242 /* Destroy */
00243 #ifdef HAVE_PTHREAD_RWLOCK_T
00244 #define RWLOCK_DESTROY(rwlock) \
00245   pthread_rwlock_destroy(rwlock)
00246 #else
00247 #define RWLOCK_DESTROY(rwlock) \
00248   mc_rwlock_destroy(rwlock)
00249 #endif
00250 /* Functions */
00251 #ifdef HAVE_PTHREAD_RWLOCK_T
00252 #define RWLOCK_RDLOCK(rwlock) \
00253   if (pthread_rwlock_rdlock(rwlock)) \
00254 fprintf(stderr, "rwlock error: %s:%d\n", __FILE__, __LINE__)
00255 #define RWLOCK_RDUNLOCK(rwlock) \
00256   if (pthread_rwlock_unlock(rwlock)) \
00257 fprintf(stderr, "rwunlock error: %s:%d\n", __FILE__, __LINE__)
00258 #define RWLOCK_WRLOCK(rwlock) \
00259   if (pthread_rwlock_wrlock(rwlock)) \
00260 fprintf(stderr, "rwlock error: %s:%d\n", __FILE__, __LINE__)
00261 #define RWLOCK_WRUNLOCK(rwlock) \
00262   if (pthread_rwlock_unlock(rwlock)) \
00263 fprintf(stderr, "rwunlock error: %s:%d\n", __FILE__, __LINE__)
00264 #else
00265 #define RWLOCK_RDLOCK(rwlock) \
00266   mc_rwlock_rdlock(rwlock)
00267 #define RWLOCK_RDUNLOCK(rwlock) \
00268   mc_rwlock_rdunlock(rwlock)
00269 #define RWLOCK_WRLOCK(rwlock) \
00270   mc_rwlock_wrlock(rwlock)
00271 #define RWLOCK_WRUNLOCK(rwlock) \
00272   mc_rwlock_wrunlock(rwlock)
00273 #endif
00274 
00275 
00276 /* ***************** *
00277  * SYSTEM QUEUE SYNC *
00278  * ***************** */
00279 #define WAKE_QUEUE(queue, action)                \
00280   if (pthread_mutex_trylock( queue->lock ) == 0) {    \
00281     action;                                                 \
00282     pthread_cond_signal( queue->cond);           \
00283     pthread_mutex_unlock( queue->lock);            \
00284   }                                           
00285 #define SLEEP_QUEUE( queue )                                        \
00286   if (pthread_mutex_lock( queue->thread_mutex ))                  \
00287 printf("pthread lock error: %s:%d\n", __FILE__, __LINE__);  \
00288 pthread_cond_wait( queue->touched_signal, queue->thread_mutex )
00289 #define SLEEP_RESET( queue )                        \
00290   pthread_mutex_unlock( queue->thread_mutex )
00291 
00292 
00293 
00294 #else 
00295 /* * * * * * * * * * * * * * * *
00296  * W I N D O W S   M A C R O S *
00297  * * * * * * * * * * * * * * * */
00298 
00299 /* ******* *
00300  * THREADS *
00301  * ******* */
00302 #define THREAD_T HANDLE
00303 #define THREAD_CREATE(thread_handle, function, arg) \
00304   *(thread_handle) = CreateThread( \
00305       NULL, \
00306       (SIZE_T)stack_size, \
00307       function, \
00308       arg, \
00309       0, \
00310       NULL \
00311       )
00312 
00313 #define THREAD_CANCEL(thread_handle)  \
00314   TerminateThread( thread_handle, 0)
00315 
00316 #define THREAD_JOIN(thread_handle) \
00317   WaitForSingleObject(thread_handle, INFINITE)
00318 
00319 /* ***** */
00320 /* MUTEX */
00321 /* ***** */
00322 /* Typedef */
00323 #define MUTEX_T HANDLE
00324 /* Init */
00325 #define MUTEX_INIT(mutex) \
00326   *mutex = CreateMutex(NULL, FALSE, NULL)
00327 /* Destroy */
00328 #define MUTEX_DESTROY(mutex)
00329 /* Functions */
00330 #define MUTEX_LOCK(mutex)           \
00331   WaitForSingleObject(            \
00332       *mutex ,                 \
00333       INFINITE)
00334 #define MUTEX_UNLOCK(mutex)         \
00335   ReleaseMutex( *mutex )
00336 #define MUTEX_NEW(mutex) \
00337   mutex = (HANDLE*)malloc(sizeof(HANDLE)); \
00338   if(mutex == NULL) \
00339     fprintf(stderr, "Memory Error. %s:%d\n", __FILE__, __LINE__)
00340 
00341 
00342 /* **** *
00343  * COND *
00344  * **** */
00345 /* Typedef */
00346 #define COND_T HANDLE
00347 /* Init */
00348 #define COND_INIT(cond) \
00349   *cond = CreateEvent(NULL, TRUE, TRUE, NULL);\
00350   ResetEvent(*cond)
00351 /* Destroy */
00352 #define COND_DESTROY(cond)
00353 /* Functions */
00354 
00355 #define COND_WAIT( cond , mutex ) \
00356 ResetEvent(*cond); \
00357 ReleaseMutex(*mutex); \
00358 WaitForSingleObject( *cond, INFINITE)
00359 #define COND_SLEEP( cond, mutex, test )   \
00360   ResetEvent( *cond );             \
00361 if (!test){ \
00362   WaitForSingleObject( *cond, INFINITE); \
00363 }
00364 #define COND_RESET( cond, mutex ) \
00365         ResetEvent(*cond)
00366 #define COND_SLEEP_ACTION(cond, mutex, action) \
00367   ResetEvent( *cond ); \
00368 action; \
00369 WaitForSingleObject( *cond, INFINITE)
00370 #define SIGNAL(cond, mutex, action) \
00371   action; \
00372 SetEvent( *cond )
00373 #define COND_BROADCAST(cond) \
00374   SetEvent(*cond)
00375 #define COND_SIGNAL(cond) \
00376   SetEvent(*cond)
00377 
00378 
00379 /* ********* *
00380  * SEMAPHORE *
00381  * ********* */
00382 /* Typedef */
00383 #define SEMAPHORE_T HANDLE
00384 /* Init */
00385 #define SEMAPHORE_INIT(sem) \
00386   sem = CreateSemaphore( \
00387       NULL, \
00388       0, \
00389       1024, \
00390       NULL ) 
00391 /* Destroy */
00392 #define SEMAPHORE_DESTROY(sem) 
00393 /* Functions */
00394 #define SEMAPHORE_WAIT(sem) \
00395   WaitForSingleObject(sem, INFINITE)
00396 #define SEMAPHORE_POST(sem) \
00397   ReleaseSemaphore(sem, 1, NULL)
00398 
00399 
00400 /* ******* *
00401  * RW_LOCK *
00402  * ******* */
00403 /* Typedef */
00404 #define RWLOCK_T mc_rwlock_t
00405 /* Init */
00406 #define RWLOCK_INIT(rwlock) \
00407   mc_rwlock_init(rwlock)
00408 /* Destroy */
00409 #define RWLOCK_DESTROY(rwlock) mc_rwlock_destroy(rwlock)
00410 /* Functions */
00411 #define RWLOCK_RDLOCK(rwlock) \
00412   mc_rwlock_rdlock(rwlock)
00413 #define RWLOCK_RDUNLOCK(rwlock) \
00414   mc_rwlock_rdunlock(rwlock)
00415 #define RWLOCK_WRLOCK(rwlock) \
00416   mc_rwlock_wrlock(rwlock)
00417 #define RWLOCK_WRUNLOCK(rwlock) \
00418   mc_rwlock_wrunlock(rwlock)
00419 
00420 
00421 /* ***************** *
00422  * SYSTEM QUEUE SYNC *
00423  * ***************** */
00424 #define SLEEP_QUEUE( queue )                                    \
00425   ResetEvent( *(queue->touched_signal) );                        \
00426 WaitForSingleObject( *(queue->touched_signal), INFINITE )
00427 #define WAKE_QUEUE(queue, action)               \
00428   action;                             \
00429   SetEvent( *(queue->cond))
00430 #define SLEEP_RESET( queue ) 
00431 
00432 #endif /* End unix/windows macros */
00433 
00434 
00435 
00436 /* * * * * * * * * * * * * * *
00437  * M I S C E L L A N E O U S *
00438  * * * * * * * * * * * * * * */
00439 /* Check to see if a data structure is NULL: Perform 'action' if it is null */
00440 #define CHECK_NULL( var, action )                                  \
00441   if ( var == NULL ) {                                        \
00442     fprintf(stderr, "Pointer var is null: expected otherwise.\n");    \
00443     fprintf(stderr, "Error occured at %s:%d", __FILE__, __LINE__);    \
00444     action; \
00445   }
00446 
00447 #define WARN( message ) \
00448   fprintf(stderr, "WARNING: "); \
00449   fprintf(stderr, message ); \
00450   fprintf(stderr, " %s:%d\n", __FILE__, __LINE__ )
00451 
00452 /* Macro for determining size of a CH data type */
00453 /* Arguments:
00454  *  type: CH_Type_t type
00455  *  size: int
00456  *  */
00457 #define CH_DATATYPE_SIZE(type, size)                            \
00458   switch(type) {                                              \
00459     case CH_CHARTYPE:                                       \
00460                                                             size = sizeof(char);                                \
00461     break;                                              \
00462     case CH_INTTYPE:                                        \
00463                                                             size = sizeof(int);                                 \
00464     break;                                              \
00465     case CH_UINTTYPE:                                       \
00466                                                             size = sizeof(unsigned int);                        \
00467     break;                                              \
00468     case CH_SHORTTYPE:                                      \
00469                                                             size = sizeof(short);                               \
00470     break;                                              \
00471     case CH_USHORTTYPE:                                     \
00472                                                             size = sizeof(unsigned short);                      \
00473     break;                                              \
00474     case CH_FLOATTYPE:                                      \
00475                                                             size = sizeof(float);                               \
00476     break;                                              \
00477     case CH_DOUBLETYPE:                                     \
00478                                                             size = sizeof(double);                              \
00479     break;                                              \
00480     default:                                                \
00481                                                             fprintf(stderr, "Unknown data type: %d at %s:%d",   \
00482                                                                 type, __FILE__, __LINE__);                  \
00483     size=0;                                             \
00484   }
00485 
00486 /* Macro for converting a CH_Type_t into a string */
00487 /* Argument 'string' must be an allocated array of characters. */
00488 #define CH_DATATYPE_STRING(type, string)                    \
00489   switch(type) {                                          \
00490     case CH_CHARTYPE:                                   \
00491       strcpy(string, "char");                         \
00492     break;                                          \
00493     case CH_INTTYPE:                                    \
00494       strcpy(string, "int");                          \
00495     break;                                          \
00496     case CH_UINTTYPE:                                   \
00497       strcpy(string, "unsigned int");                 \
00498     break;                                          \
00499     case CH_SHORTTYPE:                                  \
00500       strcpy(string, "short");                        \
00501     break;                                          \
00502     case CH_USHORTTYPE:                                 \
00503       strcpy(string, "unsigned short");               \
00504     break;                                          \
00505     case CH_FLOATTYPE:                                  \
00506       strcpy(string, "float");                        \
00507     break;                                          \
00508     case CH_DOUBLETYPE:                                 \
00509       strcpy(string, "double");                       \
00510     break;                                          \
00511     default:                                            \
00512       fprintf(stderr,                                 \
00513       "Unsupported data type: %d %s:%d\n",    \
00514       type, __FILE__, __LINE__ );             \
00515   }
00516 
00517 /* CH_DATATYPE_VALUE_STRING
00518  * A Macro for converting data pointed to by a pointer into 
00519  * a string. */
00520 #define CH_DATATYPE_VALUE_STRING(type, string, p) \
00521   switch(type) {                                      \
00522     case CH_INTTYPE:                                \
00523       sprintf(string, "%d", *((int*)p));          \
00524     break;                                      \
00525     case CH_UINTTYPE:                               \
00526       sprintf(string, "%d", *((unsigned int*)p)); \
00527     break;                                      \
00528     case CH_SHORTTYPE:                              \
00529       sprintf(string, "%d", *((short*)p));         \
00530     break;                                      \
00531     case CH_USHORTTYPE:                             \
00532       sprintf(string, "%d", *((unsigned short*)p)); \
00533     break;                                      \
00534     case CH_FLOATTYPE:                              \
00535       sprintf(string, "%f", *((float*)p));        \
00536     break;                                      \
00537     case CH_DOUBLETYPE:                             \
00538       sprintf(string, "%f", *((double*)p));       \
00539     break;                                      \
00540     default:                                        \
00541       fprintf(stderr,                             \
00542       "Unsupported data type: %d %s:%d\n",    \
00543       type, __FILE__, __LINE__);          \
00544   }
00545 
00546 #define CH_STRING_DATATYPE(string, type) \
00547   if (!strcmp(string, "int")) {                       \
00548     type = CH_INTTYPE;                              \
00549   } else if (!strcmp(string, "float")) {              \
00550     type = CH_FLOATTYPE;                            \
00551   } else if (!strcmp(string, "double")) {             \
00552     type = CH_DOUBLETYPE;                           \
00553   } else if (!strcmp(string, "unsigned int")) {       \
00554     type = CH_UINTTYPE;                             \
00555   } else if (!strcmp(string, "short")) {              \
00556     type = CH_SHORTTYPE;                            \
00557   } else if (!strcmp(string, "unsigned short")) {     \
00558     type = CH_USHORTTYPE;                           \
00559   } else {                                            \
00560     fprintf(stderr,                                 \
00561         "Unsupported data type: %d %s:%d\n",    \
00562         type, __FILE__, __LINE__ );             \
00563   }
00564 
00565 #ifndef _WIN32
00566 #define CH_DATATYPE_STR_TO_VAL(type, string, val) \
00567   switch (type) { \
00568     case CH_INTTYPE: \
00569                      *(int*)val = atoi(string); \
00570     break; \
00571     case CH_UINTTYPE: \
00572                       *(unsigned int*)val = atoi(string); \
00573     break; \
00574     case CH_SHORTTYPE: \
00575                        *(short*)val = (short)atoi(string); /*FIXME*/ \
00576     break; \
00577     case CH_USHORTTYPE: \
00578                         *(unsigned short*)val = (unsigned short)atoi(string); /*FIXME*/ \
00579     break; \
00580     case CH_FLOATTYPE: \
00581                        *(float*)val = strtof(string, NULL); \
00582     break; \
00583     case CH_DOUBLETYPE: \
00584                         *(double*)val = strtod(string, NULL); \
00585     break; \
00586     default: \
00587              fprintf(stderr, \
00588                  "Unsupported data type: %d %s:%d\n", \
00589                  type, __FILE__, __LINE__ ); \
00590   }
00591 #else
00592 #define CH_DATATYPE_STR_TO_VAL(type, string, val) \
00593   switch (type) { \
00594     case CH_INTTYPE: \
00595                      *(int*)val = atoi(string); \
00596     break; \
00597     case CH_UINTTYPE: \
00598                       *(unsigned int*)val = atoi(string); \
00599     break; \
00600     case CH_SHORTTYPE: \
00601                        *(short*)val = (short)atoi(string); /*FIXME*/ \
00602     break; \
00603     case CH_USHORTTYPE: \
00604                         *(unsigned short*)val = (unsigned short)atoi(string); /*FIXME*/ \
00605     break; \
00606     case CH_FLOATTYPE: \
00607                        *(float*)val = (double)strtod(string, NULL); \
00608     break; \
00609     case CH_DOUBLETYPE: \
00610                         *(double*)val = strtod(string, NULL); \
00611     break; \
00612     default: \
00613              fprintf(stderr, \
00614                  "Unsupported data type: %d %s:%d\n", \
00615                  type, __FILE__, __LINE__ ); \
00616   }
00617 #endif
00618 
00619 
00620 #endif

Generated on Fri May 16 14:49:54 2008 for Mobile-C by  doxygen 1.5.4