TSP: The Transport Sample Protocol



Main Page | Modules | Alphabetical List | Data Structures | File List | Data Fields | Globals | Related Pages

gdisp_kernel.c

Go to the documentation of this file.
00001 
00044 /*
00045  * System includes.
00046  */
00047 #include <stdio.h>
00048 #include <stdlib.h>
00049 #include <assert.h>
00050 #include <string.h>
00051 #include <errno.h>
00052 
00053 
00054 /*
00055  * GDISP+ includes.
00056  */
00057 #include "gdisp_kernel.h"
00058 #include "gdisp_prototypes.h"
00059 
00060 
00061 /*
00062  --------------------------------------------------------------------
00063                              STATIC ROUTINES
00064  --------------------------------------------------------------------
00065 */
00066 
00067 static void*
00068 gdisp_mutexNew (void)
00069 {
00070 
00071   guint            status = 0;
00072   pthread_mutex_t *mutex  = (pthread_mutex_t*)NULL;
00073 
00074   mutex = (pthread_mutex_t*)g_malloc0(sizeof(pthread_mutex_t));
00075   assert(mutex);
00076 
00077   status = pthread_mutex_init(mutex,(pthread_mutexattr_t*)NULL);
00078 
00079   return (void*)mutex;
00080 
00081 }
00082 
00083 
00084 static void
00085 gdisp_mutexLock (Kernel_T *kernel,
00086                  void     *mutex)
00087 {
00088 
00089   guint    status = 0;
00090   GString *error  = (GString*)NULL;
00091 
00092   status = pthread_mutex_lock((pthread_mutex_t*)mutex);
00093   switch (status) {
00094 
00095   case EINVAL :
00096     error = g_string_new("The mutex has not been properly initialized.");
00097     kernel->outputFunc(kernel,error,GD_ERROR);
00098     break;
00099 
00100   case EDEADLK :
00101     error = g_string_new("The mutex is already locked by the calling thread.");
00102     kernel->outputFunc(kernel,error,GD_ERROR);
00103     break;
00104 
00105   default :
00106     break;
00107 
00108   }
00109 
00110 }
00111 
00112 
00113 static gboolean
00114 gdisp_mutexTrylock (Kernel_T *kernel,
00115                     void     *mutex)
00116 {
00117 
00118   guint     status  = 0;
00119   gboolean  gStatus = TRUE;
00120   GString  *error   = (GString*)NULL;
00121 
00122   status = pthread_mutex_trylock((pthread_mutex_t*)mutex);
00123   switch (status) {
00124 
00125   case EINVAL :
00126     error = g_string_new("The mutex has not been properly initialized.");
00127     kernel->outputFunc(kernel,error,GD_ERROR);
00128     gStatus = FALSE;
00129     break;
00130 
00131   case EBUSY  :
00132     error = g_string_new("The mutex could not be acquired"
00133                          "because it was currently locked.");
00134     kernel->outputFunc(kernel,error,GD_ERROR);
00135     gStatus = FALSE;
00136     break;
00137 
00138   default :
00139     gStatus = TRUE;
00140     break;
00141 
00142   }
00143 
00144   return gStatus;
00145 
00146 }
00147 
00148 
00149 static void
00150 gdisp_mutexUnlock (Kernel_T *kernel,
00151                    void     *mutex)
00152 {
00153 
00154   guint    status = 0;
00155   GString *error  = (GString*)NULL;
00156 
00157   status = pthread_mutex_unlock((pthread_mutex_t*)mutex);
00158   switch (status) {
00159 
00160   case EINVAL :
00161     error = g_string_new("The mutex has not been properly initialized.");
00162     kernel->outputFunc(kernel,error,GD_ERROR);
00163     break;
00164 
00165   case EPERM :
00166     error = g_string_new("The calling thread does not own the mutex");
00167     kernel->outputFunc(kernel,error,GD_ERROR);
00168     break;
00169 
00170   default :
00171     break;
00172 
00173   }
00174 
00175 }
00176 
00177 
00178 static void
00179 gdisp_mutexFree (Kernel_T *kernel,
00180                  void     *mutex)
00181 {
00182 
00183   guint    status = 0;
00184   GString *error  = (GString*)NULL;
00185 
00186   status = pthread_mutex_destroy((pthread_mutex_t*)mutex);
00187   switch (status) {
00188 
00189   case EBUSY :
00190     error = g_string_new("The mutex is currently locked.");
00191     kernel->outputFunc(kernel,error,GD_ERROR);
00192     return;
00193     break;
00194 
00195   default :
00196     break;
00197 
00198   }
00199 
00200   memset(mutex,0,sizeof(pthread_mutex_t));
00201   g_free(mutex);
00202 
00203 }
00204 
00205 /* --------------------------------------------------------------- */
00206 
00207 static void
00208 gdisp_registerAction ( Kernel_T  *kernel,
00209                        void     (*action)(Kernel_T*) )
00210 {
00211 
00212   g_ptr_array_add(kernel->kernelRegisteredActions,
00213                   (gpointer)action);
00214 
00215 }
00216 
00217 
00218 static void
00219 gdisp_unRegisterAction ( Kernel_T  *kernel,
00220                          void     (*action)(Kernel_T*) )
00221 {
00222 
00223   g_ptr_array_remove_fast(kernel->kernelRegisteredActions,
00224                           (gpointer)action);
00225 
00226 }
00227 
00228 
00229 static gint
00230 gdisp_activateRegisteredActions ( void *data )
00231 {
00232 
00233   Kernel_T  *kernel             = (Kernel_T*)data;
00234   void     (*action)(Kernel_T*) = (void(*)(Kernel_T*))NULL;
00235   guint      cptAction          = 0;
00236   guint      nbActions          = 0;
00237 
00238   /*
00239    * Loop over all registered actions and activate them.
00240    */
00241   nbActions = kernel->kernelRegisteredActions->len;
00242   for (cptAction=0; cptAction<nbActions; cptAction++) {
00243 
00244     action = (void(*)(Kernel_T*))
00245              g_ptr_array_index(kernel->kernelRegisteredActions,cptAction);
00246 
00247     (*action)(kernel);
00248 
00249   }
00250 
00251   return TRUE; /* keep on running */
00252 
00253 }
00254 
00255 
00256 /*
00257  --------------------------------------------------------------------
00258                              PUBLIC ROUTINES
00259  --------------------------------------------------------------------
00260 */
00261 
00262 
00263 /*
00264  * Allocate memory for GDISP+ Kernel.
00265  */
00266 Kernel_T*
00267 gdisp_createKernel (gint    argc,
00268                    gchar **argv)
00269 {
00270 
00271   Kernel_T        *kernel          =       (Kernel_T*)NULL;
00272   PlotSystem_T    *plotSystem      =   (PlotSystem_T*)NULL;
00273   PlotType_T       plotType        =       GD_PLOT_DEFAULT;
00274   guint            functionSetSize =                     0;
00275   guint            functionCpt     =                     0;
00276   guint            functionNb      =                     0;
00277   FunctionTable_T  functionTable   = (FunctionTable_T)NULL;
00278 
00279   /*
00280    * Memory allocation.
00281    */
00282   kernel = (Kernel_T*)g_malloc0(sizeof(Kernel_T));
00283   assert(kernel);
00284 
00285   /*
00286    * Defaults.
00287    */
00288   kernel->isThreadSafe           = FALSE;
00289   kernel->sortingMethod          = GD_SORT_BY_PROVIDER;
00290   kernel->dndScope               = GD_DND_UNICAST;
00291   kernel->argCounter             = argc;
00292   kernel->argTable               = argv;
00293   kernel->stepTimerPeriod        = GD_TIMER_MIN_PERIOD; /* milli-seconds */
00294   kernel->samplingThreadMustExit = TRUE;
00295 
00296   /*
00297    * Try to know whether a multi-threaded environment is available ?
00298    */
00299 
00300   /*
00301    * We must provide our own thread-safe system.
00302    */
00303   kernel->mutexNew     = gdisp_mutexNew;
00304   kernel->mutexLock    = gdisp_mutexLock;
00305   kernel->mutexTrylock = gdisp_mutexTrylock;
00306   kernel->mutexUnlock  = gdisp_mutexUnlock;
00307   kernel->mutexFree    = gdisp_mutexFree;
00308 
00309   /*
00310    * Use this system to create a mutex.
00311    */
00312   kernel->isThreadSafe = TRUE;
00313 
00314   /*
00315    * Initialise all fonts.
00316    */
00317   gdisp_loadFonts(kernel->fonts);
00318 
00319 
00320   /*
00321    * Initialise all plot systems.
00322    * Each plot system that is supported may provide several functions.
00323    */
00324   kernel->currentPlotType = GD_PLOT_2D;
00325 
00326   /* Remove size of 'psIsSupported' */
00327   functionSetSize = sizeof(PlotSystem_T) - sizeof(gboolean);
00328   functionNb      = functionSetSize / sizeof(aFunction_T);
00329 
00330   for (plotType=GD_PLOT_DEFAULT; plotType<GD_MAX_PLOT; plotType++) {
00331 
00332     plotSystem = &kernel->plotSystems[plotType];
00333     switch (plotType) {
00334 
00335     case GD_PLOT_DEFAULT :
00336       gdisp_initDefaultPlotSystem(kernel,plotSystem);
00337       break;
00338 
00339     case GD_PLOT_2D :
00340       gdisp_initPlot2DSystem(kernel,plotSystem);
00341       break;
00342 
00343     case GD_PLOT_TEXT :
00344       gdisp_initPlotTextSystem(kernel,plotSystem);
00345       break;
00346 
00347     default :
00348       break;
00349 
00350     }
00351 
00352     /*
00353      * We must check out, at kernel level, that all functions have been
00354      * initialised by each plot system.
00355      */
00356 
00357     /* By default, the plot system is supported */
00358     plotSystem->psIsSupported = TRUE;
00359     functionTable             = (FunctionTable_T)plotSystem;
00360 
00361     for (functionCpt=0; functionCpt<functionNb; functionCpt++) {
00362 
00363       if (functionTable[functionCpt] == (aFunction_T)NULL) {
00364 
00365         plotSystem->psIsSupported = FALSE;
00366 
00367       } /* if */
00368 
00369     } /* for 'functionCpt' */
00370 
00371   } /* for 'plotType' */
00372 
00373   /*
00374    * Remember how to register periodic actions.
00375    */
00376   kernel->kernelRegisteredActions = g_ptr_array_new();
00377 
00378   kernel->registerAction          = gdisp_registerAction;
00379   kernel->unRegisterAction        = gdisp_unRegisterAction;
00380 
00381   kernel->kernelTimerIdentity =
00382     gtk_timeout_add(1000, /* milli-seconds */
00383                     gdisp_activateRegisteredActions,
00384                     (void*)kernel);
00385 
00386   /*
00387    * Remember how to assign symbols to providers for sampling purpose.
00388    */
00389   kernel->assignSymbolsToProviders = gdisp_affectRequestedSymbolsToProvider;
00390 
00391   /*
00392    * Return the kernel itself.
00393    */
00394   return kernel;
00395 
00396 }
00397 
00398 
00399 /*
00400  * Free memory used by GDISP+ Kernel.
00401  */
00402 void
00403 gdisp_destroyKernel (Kernel_T *kernel)
00404 {
00405 
00406   assert(kernel);
00407 
00408   /*
00409    * Destroy all fonts and pixmaps.
00410    */
00411   gdisp_destroyFonts  (kernel->fonts);
00412   gdisp_destroyPixmaps(kernel);
00413 
00414   /*
00415    * Free Kernel.
00416    */
00417   gtk_timeout_remove(kernel->kernelTimerIdentity);
00418   g_ptr_array_free(kernel->kernelRegisteredActions,FALSE);
00419 
00420   memset(kernel,0,sizeof(Kernel_T));
00421   g_free(kernel);
00422 
00423 }
00424 
00425 
Framework Home Page.

Beware !! TSP wave is coming...