72 static volatile enum {
79 #define TASKWD_DELAY 6.0 83 static union twdNode *allocNode(
void);
84 static void freeNode(
union twdNode *);
88 static void twdTask(
void *arg)
114 tName, (
void *)pt->
tid);
131 static void twdShutdown(
void *arg)
144 static void twdInitOnce(
void *arg)
162 cantProceed(
"Failed to spawn task watchdog thread\n");
185 pt = &allocNode()->
t;
202 ellAdd(&tList, (
void *)pt);
220 if (tid == pt->
tid) {
241 errlogPrintf(
"taskwdRemove: Thread %s (%p) not registered!\n",
252 if (funcs ==
NULL)
return;
256 pm = &allocNode()->
m;
261 ellAdd(&mList, (
void *)pm);
269 if (funcs ==
NULL)
return;
276 if (pm->
funcs == funcs && pm->
usr == usr) {
310 if (callback == NULL)
return;
314 pa = &allocNode()->
a;
319 pm = &allocNode()->
m;
320 pm->
funcs = &anyFuncs;
324 ellAdd(&mList, (
void *)pm);
338 if (pm->
funcs == &anyFuncs) {
340 if (pa->
key == key) {
352 errlogPrintf(
"taskwdAnyRemove: Unregistered key %p\n", key);
361 int mCount, fCount, tCount;
374 printf(
"%d monitors, %d threads registered, %d free nodes\n",
375 mCount, tCount, fCount);
377 printf(
"%16.16s %9s %12s %12s %12s\n",
378 "THREAD NAME",
"STATE",
"EPICS TID",
"epicsCallback",
"USR ARG");
382 printf(
"%16.16s %9s %12p %12p %12p\n",
383 tName, pt->
suspended ?
"Suspended" :
"Ok ",
394 static union twdNode *newNode(
void)
405 pn = calloc(1,
sizeof(
union twdNode));
411 static union twdNode *allocNode(
void)
415 errlogPrintf(
"Thread taskwd suspending: out of memory\n");
422 static void freeNode(
union twdNode *pn)
427 ellAdd(&fList, (
void *)pn);
void taskwdInsert(epicsThreadId tid, TASKWDFUNC callback, void *usr)
void taskwdAnyInsert(void *key, TASKWDANYFUNC callback, void *usr)
void(* insert)(void *usr, epicsThreadId tid)
#define ellCount(PLIST)
Report the number of nodes in a list.
#define epicsEventWait(ID)
ELLNODE * ellGet(ELLLIST *pList)
Deletes and returns the first node from a list.
#define epicsMutexMustCreate()
Create an epicsMutex semaphore for use from C code.
void(* notify)(void *usr, epicsThreadId tid, int suspended)
LIBCOM_API epicsEventStatus epicsEventWaitWithTimeout(epicsEventId id, double timeOut)
Wait an the event or until the specified timeout period is over.
#define ELLLIST_INIT
Value of an empty list.
LIBCOM_API epicsEventId epicsEventMustCreate(epicsEventInitialState initialState)
Create an epicsEvent for use from C code.
void epicsStdCall epicsMutexUnlock(epicsMutexId pmutexNode)
Release the semaphore.
Miscellaneous macro definitions.
LIBCOM_API unsigned int epicsStdCall epicsThreadGetStackSize(epicsThreadStackSizeClass size)
void taskwdMonitorAdd(const taskwdMonitor *funcs, void *usr)
epicsThreadId epicsStdCall epicsThreadCreate(const char *name, unsigned int priority, unsigned int stackSize, EPICSTHREADFUNC funptr, void *parm)
const taskwdMonitor * funcs
#define VALGRIND_CREATE_MEMPOOL(pool, rzB, is_zeroed)
A doubly-linked list library.
void ellAdd(ELLLIST *pList, ELLNODE *pNode)
Adds a node to the end of a list.
#define ellNext(PNODE)
Find the next node in list.
#define EPICS_THREAD_ONCE_INIT
LIBCOM_API void epicsStdCall epicsThreadSuspendSelf(void)
#define epicsEventSignal(ID)
A synonym for epicsEventTrigger().
#define VALGRIND_DESTROY_MEMPOOL(pool)
void taskwdMonitorDel(const taskwdMonitor *funcs, void *usr)
APIs for the epicsMutex mutual exclusion semaphore.
LIBCOM_API void epicsStdCall epicsThreadOnce(epicsThreadOnceId *id, EPICSTHREADFUNC, void *arg)
void(* remove)(void *usr, epicsThreadId tid)
#define epicsThreadPriorityLow
Extended replacement for the Posix exit and atexit routines.
LIBCOM_API void epicsStdCall epicsThreadGetName(epicsThreadId id, char *name, size_t size)
#define VALGRIND_MEMPOOL_ALLOC(pool, addr, size)
int errlogPrintf(const char *pFormat,...)
APIs for the epicsEvent binary semaphore.
void taskwdRemove(epicsThreadId tid)
#define ellInit(PLIST)
Initialize a list type.
void taskwdAnyRemove(void *key)
LIBCOM_API void cantProceed(const char *msg,...)
void(* TASKWDANYFUNC)(void *usr, epicsThreadId tid)
LIBCOM_API int epicsStdCall epicsThreadIsSuspended(epicsThreadId id)
Routines for code that can't continue or return after an error.
void(* TASKWDFUNC)(void *usr)
#define VALGRIND_MEMPOOL_FREE(pool, addr)
#define epicsAtExit(F, A)
Convenience macro to register a function and context value to be run when the process exits...
C++ and C descriptions for a thread.
#define epicsMutexMustLock(ID)
Claim a semaphore (see epicsMutexLock()).
void ellDelete(ELLLIST *pList, ELLNODE *pNode)
Deletes a node from a list.
LIBCOM_API void taskwdShow(int level)
#define ellFirst(PLIST)
Find the first node in list.
LIBCOM_API epicsThreadId epicsStdCall epicsThreadGetIdSelf(void)