diff --git a/modules/libcom/src/error/errlog.c b/modules/libcom/src/error/errlog.c index f409accbb..3ed887d40 100644 --- a/modules/libcom/src/error/errlog.c +++ b/modules/libcom/src/error/errlog.c @@ -78,10 +78,10 @@ typedef struct { static struct { epicsMutexId bufSizeLock; - /* const after errlogInit() */ + /* guarded by bufSizeLock, allowing them to be resized after initialisation */ size_t maxMsgSize; - /* alloc size of both buffer_t::base */ size_t bufSize; + int errlogInitFailed; epicsMutexId listenerLock; @@ -754,6 +754,7 @@ void errlogFlush(void) static void errlogThread(void) { int wakeFlusher; + epicsMutexMustLock(pvt.bufSizeLock); epicsMutexMustLock(pvt.msgQueueLock); while (1) { pvt.flushSeq++; @@ -763,9 +764,17 @@ static void errlogThread(void) break; wakeFlusher = pvt.nFlushers!=0; epicsMutexUnlock(pvt.msgQueueLock); + // Allow the buffer size to be modified only at this point + epicsMutexUnlock(pvt.bufSizeLock); + if(wakeFlusher) epicsEventMustTrigger(pvt.waitForSeq); + epicsEventMustWait(pvt.waitForWork); + + // Block resizing the buffer size + epicsMutexMustLock(pvt.bufSizeLock); + epicsMutexMustLock(pvt.msgQueueLock); } else { @@ -783,6 +792,8 @@ static void errlogThread(void) } pvt.nLost = 0u; + // Note that we are intentionally still holding the buffer size lock + // here. The buffer can only be resized when this thread is idle. epicsMutexUnlock(pvt.msgQueueLock); while(pos < print->pos) { @@ -846,6 +857,7 @@ static void errlogThread(void) } wakeFlusher = pvt.nFlushers!=0; epicsMutexUnlock(pvt.msgQueueLock); + epicsMutexUnlock(pvt.bufSizeLock); if(wakeFlusher) epicsEventMustTrigger(pvt.waitForSeq); }