00001
00002 #include <vxWorks.h>
00003 #include <stdio.h>
00004 #include <stddef.h>
00005 #include <stdlib.h>
00006 #include <semLib.h>
00007 #include <sysLib.h>
00008 #include <taskLib.h>
00009 #include "_table.h"
00010 #include "_timer.h"
00011 #include "dbg_mem.h"
00012
00013 int task_lock_sem_stuff = 1;
00014
00015
00016 _RCS_TABLE rcs_sem_table;
00017 int rcs_sem_table_inited = 0;
00018 int print_rcs_sem_warnings = 1;
00019
00020
00021
00022 void
00023 rcs_sem_table_print ()
00024 {
00025 if (!rcs_sem_table_inited)
00026 {
00027 printf ("RCS Semaphore table NOT initialized.\n");
00028 return;
00029 }
00030 table_print (&rcs_sem_table);
00031 printf ("\tid\tkey\t(struct semaphore *)\n");
00032 }
00033
00034 void
00035 rcs_sem_table_clear ()
00036 {
00037 if (task_lock_sem_stuff)
00038 taskLock ();
00039 rcs_sem_table_inited = 0;
00040 table_clearall (&rcs_sem_table);
00041 if (task_lock_sem_stuff)
00042 taskUnlock ();
00043 }
00044
00045
00046
00047
00048
00049 int
00050 rcs_sem_init (rcs_sem_t * sem, int pshared, unsigned int value)
00051 {
00052 if (NULL == sem)
00053 {
00054 return ERROR;
00055 }
00056 return -1;
00057 }
00058
00059 int
00060 rcs_sem_destroy (rcs_sem_t * sem)
00061 {
00062 int retval = 0;
00063 if (task_lock_sem_stuff)
00064 taskLock ();
00065 if (NULL == sem)
00066 {
00067 if (task_lock_sem_stuff)
00068 taskUnlock ();
00069 return ERROR;
00070 }
00071 if (((int) sem->sem_id) <= 0 || ((int) sem->sem_id) == ERROR)
00072 {
00073 if (task_lock_sem_stuff)
00074 taskUnlock ();
00075 return ERROR;
00076 }
00077 retval = semDelete (sem->sem_id) == ERROR ? -1 : 0;
00078 table_clear (&rcs_sem_table, sem->key);
00079 sem->sem_id = NULL;
00080
00081 if (task_lock_sem_stuff)
00082 taskUnlock ();
00083 sem->sem_id = NULL;
00084 return retval;
00085 }
00086
00087
00088 int
00089 rcs_sem_clear (rcs_sem_t * sem)
00090 {
00091
00092 if (NULL == sem)
00093 {
00094 return ERROR;
00095 }
00096 return (0);
00097 }
00098
00099
00100 rcs_sem_t *
00101 rcs_sem_open (const char *name, int oflag, ...)
00102 {
00103 int tid = taskIdSelf ();
00104 rcs_sem_t *sem = NULL;
00105 sem = (rcs_sem_t *) DEBUG_MALLOC (sizeof (rcs_sem_t));
00106 sem->sem_id = (SEM_ID) ERROR;
00107
00108 if (task_lock_sem_stuff)
00109 taskLock ();
00110
00111
00112
00113 if (!rcs_sem_table_inited)
00114 {
00115
00116 table_new (&rcs_sem_table, sizeof (rcs_sem_t));
00117 rcs_print_error ("Semaphore table not initialized.\n");
00118 rcs_sem_table_inited = 1;
00119 if (task_lock_sem_stuff)
00120 taskUnlock ();
00121 return NULL;
00122 }
00123
00124
00125 if (table_get (&rcs_sem_table, (unsigned long int) name, sem) < 0)
00126 {
00127 if (task_lock_sem_stuff)
00128 taskUnlock ();
00129 rcs_print_error
00130 ("Error: RCS Semaphore table contains no entry for (%d(0x%X)).\n",
00131 sem->key, sem->key);
00132 rcs_print_error
00133 ("Error: Make this process(%d(0x%X)) the master or start the master first to avoid this Error.\n",
00134 tid, tid);
00135 DEBUG_FREE (sem);
00136 sem = NULL;
00137 return NULL;
00138 }
00139
00140 if (task_lock_sem_stuff)
00141 taskUnlock ();
00142
00143 if (sem->key != (int) name)
00144 {
00145 rcs_print_error
00146 ("Semaphore retrieved from table does not have the correct key. (%d) != (%d).\n");
00147 DEBUG_FREE (sem);
00148 sem = NULL;
00149 return NULL;
00150 }
00151
00152 if (((int) sem->sem_id) <= 0 || ((int) sem->sem_id) == ERROR)
00153 {
00154 rcs_print_error ("Bad id for the semaphore in the table.\n");
00155 table_clear (&rcs_sem_table, sem->key);
00156 DEBUG_FREE (sem);
00157 sem = NULL;
00158 return NULL;
00159 }
00160 return sem;
00161 }
00162
00163 int
00164 rcs_sem_close (rcs_sem_t * sem)
00165 {
00166 sem->sem_id = NULL;
00167 DEBUG_FREE (sem);
00168 return (0);
00169 }
00170
00171 int
00172 rcs_sem_flush (rcs_sem_t * sem)
00173 {
00174 if (NULL == sem)
00175 {
00176 return -1;
00177 }
00178 if (((SEM_ID) NULL) == sem->sem_id || ((SEM_ID) ERROR) == sem->sem_id)
00179 {
00180 return -1;
00181 }
00182 return (semFlush (sem->sem_id) == ERROR ? -1 : 0);
00183 }
00184
00185 int
00186 rcs_sem_unlink (const char *name)
00187 {
00188 return 0;
00189 }
00190
00191 int
00192 rcs_sem_wait (rcs_sem_t * sem, double sem_timeout)
00193 {
00194 int ticks = 0;
00195 int semTakeReturnValue = 0;
00196
00197
00198
00199 if (NULL == sem)
00200 {
00201 return -1;
00202 }
00203 if (((int) sem->sem_id) <= 0 || ERROR == ((int) sem->sem_id)
00204 || sem->key < 1)
00205 {
00206 return -1;
00207 }
00208
00209
00210 ticks = covertSecondsToTicks (sem_timeout);
00211
00212
00213 semTakeReturnValue = semTake (sem->sem_id, ticks);
00214
00215
00216 if (semTakeReturnValue == ERROR)
00217 {
00218 if (ticks == NO_WAIT)
00219 {
00220 return -1;
00221 }
00222 else
00223 {
00224 return -2;
00225 }
00226 }
00227 return 0;
00228 }
00229
00230 int
00231 rcs_sem_trywait (rcs_sem_t * sem)
00232 {
00233 if (NULL == sem)
00234 {
00235 return -1;
00236 }
00237 if (sem->sem_id <= 0 || ERROR == ((int) sem->sem_id) || sem->key < 1)
00238 {
00239 return -1;
00240 }
00241 return semTake (sem->sem_id, NO_WAIT) == ERROR ? -1 : 0;
00242 }
00243
00244 int
00245 rcs_sem_post (rcs_sem_t * sem)
00246 {
00247 if (NULL == sem)
00248 {
00249 return -1;
00250 }
00251 if (((int) sem->sem_id) <= 0 || ERROR == ((int) sem->sem_id)
00252 || sem->key < 1)
00253 {
00254 return -1;
00255 }
00256 return semGive (sem->sem_id) == ERROR ? -1 : 0;
00257 }
00258
00259
00260 int
00261 rcs_sem_getvalue (rcs_sem_t * sem, unsigned int *sval)
00262 {
00263 return -1;
00264 #if 0
00265 if (NULL == sem)
00266 {
00267 return -1;
00268 }
00269 if (((int) sem->sem_id) <= 0 || ERROR == sem->sem_id || sem->key < 1)
00270 {
00271 return -1;
00272 }
00273 return sem->sem->semCount;
00274 #endif
00275 }
00276
00277 rcs_sem_t *
00278 rcs_sem_create (unsigned long int key, int mode, int state)
00279 {
00280 rcs_sem_t *sem = NULL;
00281 int tid = taskIdSelf ();
00282 if (task_lock_sem_stuff)
00283 taskLock ();
00284 sem = (rcs_sem_t *) DEBUG_MALLOC (sizeof (rcs_sem_t));
00285 sem->sem_id = NULL;
00286
00287 if (table_get (&rcs_sem_table, (unsigned long int) key, sem) >= 0)
00288 {
00289 if (sem->key != (int) key)
00290 {
00291 if (task_lock_sem_stuff)
00292 taskUnlock ();
00293 rcs_print_error
00294 ("Semaphore retrieved from table does not have the correct key. (%d) != (%d).\n");
00295 return NULL;
00296 }
00297 if (((int) sem->sem_id) == ERROR || ((int) sem->sem_id) <= 0)
00298 {
00299 table_clear (&rcs_sem_table, sem->key);
00300 DEBUG_FREE (sem);
00301 return NULL;
00302 }
00303 if (task_lock_sem_stuff)
00304 taskUnlock ();
00305 if (print_rcs_sem_warnings)
00306 {
00307 rcs_print_error ("\n");
00308 rcs_print_error
00309 ("Warning: This process(%d(0x%X)) was configured to create a semaphore with key = (%d(0x%X)),\n",
00310 tid, tid, sem->key, sem->key);
00311 rcs_print_error
00312 ("Warning: but a semaphore with this key has already been created.\n");
00313 rcs_print_error ("Warning: The existing semaphore will be used.");
00314 rcs_print_error
00315 ("Warning: Make this process a non-master or start it first to avoid this warning.\n");
00316 rcs_print_error
00317 ("Warning: You may also set print_rcs_sem_warnings=0 to avoid this warning.");
00318 rcs_print_error ("\n");
00319 }
00320 return sem;
00321 }
00322
00323
00324
00325
00326 sem->key = key;
00327 if (state)
00328 {
00329 sem->sem_id = semMCreate (SEM_Q_PRIORITY | SEM_INVERSION_SAFE);
00330 if (NULL == sem->sem_id)
00331 {
00332 rcs_print_error
00333 ("semMCreate(SEM_Q_PRIORITY | SEM_INVERSION_SAFE) returned NULL.\n");
00334 return NULL;
00335 }
00336 }
00337 else
00338 {
00339 sem->sem_id = semBCreate (SEM_Q_PRIORITY, SEM_EMPTY);
00340 if (NULL == sem->sem_id)
00341 {
00342 rcs_print_error
00343 ("semBCreate(SEM_Q_PRIORITY, SEM_EMPTY) returned NULL.\n");
00344 return NULL;
00345 }
00346 }
00347
00348
00349 if (!rcs_sem_table_inited)
00350 {
00351
00352 table_new (&rcs_sem_table, sizeof (rcs_sem_t));
00353 rcs_sem_table_inited = 1;
00354 }
00355 table_add (&rcs_sem_table, key, sem);
00356 if (task_lock_sem_stuff)
00357 taskUnlock ();
00358 return sem;
00359 }