Project

General

Profile

Patch #810 » dcmtk-3.6.2-SlimReaderWriterLock.patch

Patch - Marco Eichelberg, 2018-01-29 16:11

View differences:

dcmtk-for-dcmjp2k-3.6.2-unix.patched/dcmdata/apps/dcmconv.cc 2018-01-19 09:58:04.601534500 +0100
} else {
tagKey = dicent->getKey();
}
dcmDataDict.unlock();
dcmDataDict.rdunlock();
return tagKey;
} else /* tag name has format "gggg,eeee" */
{
dcmtk-for-dcmjp2k-3.6.2-unix.patched/dcmdata/apps/dcmdump.cc 2018-01-23 15:12:19.947386700 +0100
} else {
tagKey = dicent->getKey();
}
dcmDataDict.unlock();
dcmDataDict.rdunlock();
return tagKey;
} else /* tag name has format "gggg,eeee" */
{
......
const DcmDictEntry *dicent = globalDataDict.findEntry(tagName);
if (dicent == NULL) {
OFLOG_WARN(dcmdumpLogger, "unrecognized tag name: '" << tagName << "'");
dcmDataDict.unlock();
dcmDataDict.rdunlock();
return OFFalse;
} else {
/* note for later */
printTagKeys[printTagCount] = new DcmTagKey(dicent->getKey());
}
dcmDataDict.unlock();
dcmDataDict.rdunlock();
} else {
/* tag name has format xxxx,xxxx */
/* do not lookup in dictionary, tag could be private */
dcmtk-for-dcmjp2k-3.6.2-unix.patched/dcmdata/apps/mdfdsman.cc 2018-01-23 16:08:21.239644400 +0100
{
key = dicent->getKey();
}
dcmDataDict.unlock();
dcmDataDict.rdunlock();
return key;
}
......
const DcmDataDictionary& globalDataDict = dcmDataDict.rdlock();
const DcmDictEntry *dicent = globalDataDict.findEntry(search_key,NULL);
// successfull lookup in dictionary -> translate to tag and return
dcmDataDict.unlock();
dcmDataDict.rdunlock();
if (dicent)
return OFTrue;
else return OFFalse;
dcmtk-for-dcmjp2k-3.6.2-unix.patched/dcmdata/include/dcmtk/dcmdata/dcdict.h 2018-01-23 15:12:37.143696900 +0100
/** unlocks the read or write lock which must have been acquired previously.
*/
void unlock();
void rdunlock();
void wrunlock();
/** checks if a data dictionary has been loaded. This method acquires and
* releases a read lock. It must not be called with another lock on the
dcmtk-for-dcmjp2k-3.6.2-unix.patched/dcmdata/libsrc/dcdict.cc 2018-01-23 15:13:09.880569700 +0100
if (!dataDict)
dataDict = new DcmDataDictionary(OFTrue /*loadBuiltin*/, loadExternal);
#ifdef WITH_THREADS
dataDictLock.unlock();
dataDictLock.wrunlock();
#endif
}
......
{
/* dataDictLock must not be locked during createDataDict() */
#ifdef WITH_THREADS
dataDictLock.unlock();
dataDictLock.rdunlock();
#endif
createDataDict();
#ifdef WITH_THREADS
......
{
/* dataDictLock must not be locked during createDataDict() */
#ifdef WITH_THREADS
dataDictLock.unlock();
dataDictLock.wrunlock();
#endif
createDataDict();
#ifdef WITH_THREADS
......
return *dataDict;
}
void GlobalDcmDataDictionary::unlock()
// void GlobalDcmDataDictionary::unlock()
// {
// #ifdef WITH_THREADS
// dataDictLock.unlock();
// #endif
// }
void GlobalDcmDataDictionary::rdunlock()
{
#ifdef WITH_THREADS
dataDictLock.rdunlock();
#endif
}
void GlobalDcmDataDictionary::wrunlock()
{
#ifdef WITH_THREADS
dataDictLock.unlock();
dataDictLock.wrunlock();
#endif
}
OFBool GlobalDcmDataDictionary::isDictionaryLoaded()
{
OFBool result = rdlock().isDictionaryLoaded();
unlock();
rdunlock();
return result;
}
void GlobalDcmDataDictionary::clear()
{
wrlock().clear();
unlock();
wrunlock();
}
dcmtk-for-dcmjp2k-3.6.2-unix.patched/dcmdata/libsrc/dctag.cc 2018-01-23 15:13:32.029332900 +0100
vr = dictRef->getVR();
errorFlag = EC_Normal;
}
dcmDataDict.unlock();
dcmDataDict.rdunlock();
}
// ********************************
......
if (newTagName == NULL)
newTagName = DcmTag_ERROR_TagName;
updateTagName(newTagName);
dcmDataDict.unlock();
dcmDataDict.rdunlock();
if (tagName)
return tagName;
......
}
else
result = EC_TagNotFound;
dcmDataDict.unlock();
dcmDataDict.rdunlock();
}
}
return result;
dcmtk-for-dcmjp2k-3.6.2-unix.patched/dcmdata/tests/tnewdcme.cc 2018-01-23 15:13:38.470173500 +0100
{
DcmDataDictionary &dict = dcmDataDict.wrlock();
dict.addEntry(new DcmDictEntry(PRIVATE_ELEMENT_STRINGELEM, EVR_LO, "StringAttributeForTesting", 1, 1, "private", OFTrue, PRIVATE_CREATOR_NAME));
dcmDataDict.unlock();
dcmDataDict.wrunlock();
}
dcmtk-for-dcmjp2k-3.6.2-unix.patched/dcmiod/libsrc/iodutil.cc 2018-01-23 15:13:46.391194600 +0100
{
vr = dictRef->getVR();
}
dcmDataDict.unlock();
dcmDataDict.rdunlock();
if (vr.getEVR() == EVR_SQ)
return OFTrue;
return OFFalse;
dcmtk-for-dcmjp2k-3.6.2-unix.patched/dcmnet/apps/movescu.cc 2018-01-23 15:14:04.574071000 +0100
DcmTagKey key(0xffff,0xffff);
const DcmDataDictionary& globalDataDict = dcmDataDict.rdlock();
const DcmDictEntry *dicent = globalDataDict.findEntry(dicName.c_str());
dcmDataDict.unlock();
dcmDataDict.rdunlock();
if (dicent!=NULL) {
// found dictionary name, copy group and element number
key = dicent->getKey();
dcmtk-for-dcmjp2k-3.6.2-unix.patched/dcmpstat/apps/dcmpschk.cc 2018-01-23 15:15:19.179049600 +0100
if (dictRef && (t.getEVR() == EVR_up) && (t.getEVR() == dictRef->getEVR())) result = OFTrue;
dcmDataDict.unlock();
dcmDataDict.rdunlock();
return result;
}
......
} //end of if (isaStringVR(vr))
}
dcmDataDict.unlock();
dcmDataDict.rdunlock();
return 0;
}
dcmtk-for-dcmjp2k-3.6.2-unix.patched/dcmsign/apps/dcmsign.cc 2018-01-23 15:15:31.011522400 +0100
{
if (EC_Normal == tagList.putTagVal(dicent->getKey(), tagList.getVM())) result = OFTrue;
}
dcmDataDict.unlock();
dcmDataDict.rdunlock();
} else {
if (EC_Normal == tagList.putTagVal(DcmTagKey(group,elem), tagList.getVM())) result = OFTrue;
}
......
if (dicent)
{
key = dicent->getKey();
dcmDataDict.unlock();
dcmDataDict.rdunlock();
pos = lpos;
return 1; // tag key;
}
dcmDataDict.unlock();
dcmDataDict.rdunlock();
OFLOG_ERROR(dcmsignLogger, "attribute name '" << aString.c_str() << "' unknown.");
return 0; // parse error
}
dcmtk-for-dcmjp2k-3.6.2-unix.patched/ofstd/include/dcmtk/ofstd/ofthread.h 2018-01-23 15:16:11.185530700 +0100
* @return 0 upon success, an error code otherwise.
*/
int lock();
int rdlock();
int wrlock();
/** tries to lock the mutex object. If the mutex is already locked,
* returns OFMutex::busy.
......
* an error code otherwise.
*/
int trylock();
int tryrdlock();
int trywrlock();
/** releases the lock on the mutex object. The mutex must be locked and
* the calling thread must be the owner of the lock, otherwise the
......
* @return 0 upon success, an error code otherwise.
*/
int unlock();
int rdunlock();
int wrunlock();
/** converts any of the error codes returned by the methods of this class
* into a textual description, which is written into the string object.
......
* @return 0 upon success, an error code otherwise.
*/
int unlock();
int rdunlock();
int wrunlock();
/** converts any of the error codes returned by the methods of this class
* into a textual description, which is written into the string object.
dcmtk-for-dcmjp2k-3.6.2-unix.patched/ofstd/libsrc/ofthread.cc 2018-01-23 15:17:43.191052100 +0100
#ifdef USE_WIN32_CREATE_MUTEX
theMutex = OFstatic_cast(void *, CreateMutex(NULL, FALSE, NULL));
#else
CRITICAL_SECTION *critSec = new CRITICAL_SECTION;
InitializeCriticalSection(critSec);
theMutex = OFstatic_cast(void *, critSec);
//CRITICAL_SECTION *critSec = new CRITICAL_SECTION;
//InitializeCriticalSection(critSec);
//theMutex = OFstatic_cast(void *, critSec);
SRWLOCK* srwLock = new SRWLOCK;
InitializeSRWLock(srwLock);
theMutex = OFstatic_cast(void*, srwLock);
#endif
#elif defined(POSIX_INTERFACE)
pthread_mutex_t *mtx = new pthread_mutex_t;
......
#ifdef USE_WIN32_CREATE_MUTEX
CloseHandle(OFthread_cast(HANDLE, theMutex));
#else
CRITICAL_SECTION *critSec = OFthread_cast(CRITICAL_SECTION *, theMutex);
DeleteCriticalSection(critSec);
delete critSec;
// CRITICAL_SECTION *critSec = OFthread_cast(CRITICAL_SECTION *, theMutex);
// DeleteCriticalSection(critSec);
// delete critSec;
SRWLOCK* srwLock = OFthread_cast(SRWLOCK*, theMutex); // no explicit destruction is necessary
delete srwLock;
#endif
#elif defined(POSIX_INTERFACE)
if (theMutex) pthread_mutex_destroy(OFthread_cast(pthread_mutex_t *, theMutex));
......
if (WaitForSingleObject(OFthread_cast(HANDLE, theMutex), INFINITE) == WAIT_OBJECT_0) return 0;
else return OFstatic_cast(int, GetLastError());
#else
EnterCriticalSection(OFthread_cast(CRITICAL_SECTION *, theMutex));
//EnterCriticalSection(OFthread_cast(CRITICAL_SECTION *, theMutex));
AcquireSRWLockExclusive(OFthread_cast(SRWLOCK*, theMutex));
return 0;
#endif
#elif defined(POSIX_INTERFACE)
if (theMutex) return pthread_mutex_lock(OFthread_cast(pthread_mutex_t *, theMutex)); else return EINVAL;
#elif defined(SOLARIS_INTERFACE)
if (theMutex) return mutex_lock(OFthread_cast(mutex_t *, theMutex)); else return EINVAL;
#else
return -1;
#endif
}
int OFMutex::rdlock()
{
#ifdef WINDOWS_INTERFACE
#ifdef USE_WIN32_CREATE_MUTEX
if (WaitForSingleObject(OFthread_cast(HANDLE, theMutex), INFINITE) == WAIT_OBJECT_0) return 0;
else return OFstatic_cast(int, GetLastError());
#else
//EnterCriticalSection(OFthread_cast(CRITICAL_SECTION *, theMutex));
AcquireSRWLockShared(OFthread_cast(SRWLOCK*, theMutex));
return 0;
#endif
#elif defined(POSIX_INTERFACE)
if (theMutex) return pthread_mutex_lock(OFthread_cast(pthread_mutex_t *, theMutex)); else return EINVAL;
#elif defined(SOLARIS_INTERFACE)
if (theMutex) return mutex_lock(OFthread_cast(mutex_t *, theMutex)); else return EINVAL;
#else
return -1;
#endif
}
int OFMutex::wrlock()
{
#ifdef WINDOWS_INTERFACE
#ifdef USE_WIN32_CREATE_MUTEX
if (WaitForSingleObject(OFthread_cast(HANDLE, theMutex), INFINITE) == WAIT_OBJECT_0) return 0;
else return OFstatic_cast(int, GetLastError());
#else
//EnterCriticalSection(OFthread_cast(CRITICAL_SECTION *, theMutex));
AcquireSRWLockExclusive(OFthread_cast(SRWLOCK*, theMutex));
return 0;
#endif
#elif defined(POSIX_INTERFACE)
......
else if (result == WAIT_TIMEOUT) return OFMutex::busy;
else return OFstatic_cast(int, GetLastError());
#else
if (TryEnterCriticalSection(OFthread_cast(CRITICAL_SECTION *, theMutex))) return 0;
//if (TryEnterCriticalSection(OFthread_cast(CRITICAL_SECTION *, theMutex))) return 0;
if (TryAcquireSRWLockExclusive(OFthread_cast(SRWLOCK*, theMutex))) return 0;
else return OFMutex::busy;
#endif
#elif defined(POSIX_INTERFACE)
if (theMutex) return pthread_mutex_trylock(OFthread_cast(pthread_mutex_t *, theMutex)); else return EINVAL; // may return EBUSY.
#elif defined(SOLARIS_INTERFACE)
if (theMutex) return mutex_trylock(OFthread_cast(mutex_t *, theMutex)); else return EINVAL; // may return EBUSY.
#else
return -1;
#endif
}
int OFMutex::tryrdlock()
{
#ifdef WINDOWS_INTERFACE
#ifdef USE_WIN32_CREATE_MUTEX
DWORD result = WaitForSingleObject(OFthread_cast(HANDLE, theMutex), 0);
if (result == WAIT_OBJECT_0) return 0;
else if (result == WAIT_TIMEOUT) return OFMutex::busy;
else return OFstatic_cast(int, GetLastError());
#else
//if (TryEnterCriticalSection(OFthread_cast(CRITICAL_SECTION *, theMutex))) return 0;
if (TryAcquireSRWLockShared(OFthread_cast(SRWLOCK*, theMutex))) return 0;
else return OFMutex::busy;
#endif
#elif defined(POSIX_INTERFACE)
if (theMutex) return pthread_mutex_trylock(OFthread_cast(pthread_mutex_t *, theMutex)); else return EINVAL; // may return EBUSY.
#elif defined(SOLARIS_INTERFACE)
if (theMutex) return mutex_trylock(OFthread_cast(mutex_t *, theMutex)); else return EINVAL; // may return EBUSY.
#else
return -1;
#endif
}
int OFMutex::trywrlock()
{
#ifdef WINDOWS_INTERFACE
#ifdef USE_WIN32_CREATE_MUTEX
DWORD result = WaitForSingleObject(OFthread_cast(HANDLE, theMutex), 0);
if (result == WAIT_OBJECT_0) return 0;
else if (result == WAIT_TIMEOUT) return OFMutex::busy;
else return OFstatic_cast(int, GetLastError());
#else
//if (TryEnterCriticalSection(OFthread_cast(CRITICAL_SECTION *, theMutex))) return 0;
if (TryAcquireSRWLockExclusive(OFthread_cast(SRWLOCK*, theMutex))) return 0;
else return OFMutex::busy;
#endif
#elif defined(POSIX_INTERFACE)
......
#ifdef USE_WIN32_CREATE_MUTEX
if (ReleaseMutex(OFthread_cast(HANDLE, theMutex))) return 0; else return OFstatic_cast(int, GetLastError());
#else
LeaveCriticalSection(OFthread_cast(CRITICAL_SECTION *, theMutex));
//LeaveCriticalSection(OFthread_cast(CRITICAL_SECTION *, theMutex));
ReleaseSRWLockExclusive(OFthread_cast(SRWLOCK*, theMutex));
return 0;
#endif
#elif defined(POSIX_INTERFACE)
if (theMutex) return pthread_mutex_unlock(OFthread_cast(pthread_mutex_t *, theMutex)); else return EINVAL;
#elif defined(SOLARIS_INTERFACE)
if (theMutex) return mutex_unlock(OFthread_cast(mutex_t *, theMutex)); else return EINVAL;
#else
return -1;
#endif
}
int OFMutex::rdunlock()
{
#ifdef WINDOWS_INTERFACE
#ifdef USE_WIN32_CREATE_MUTEX
if (ReleaseMutex(OFthread_cast(HANDLE, theMutex))) return 0; else return OFstatic_cast(int, GetLastError());
#else
//LeaveCriticalSection(OFthread_cast(CRITICAL_SECTION *, theMutex));
ReleaseSRWLockShared(OFthread_cast(SRWLOCK*, theMutex));
return 0;
#endif
#elif defined(POSIX_INTERFACE)
if (theMutex) return pthread_mutex_unlock(OFthread_cast(pthread_mutex_t *, theMutex)); else return EINVAL;
#elif defined(SOLARIS_INTERFACE)
if (theMutex) return mutex_unlock(OFthread_cast(mutex_t *, theMutex)); else return EINVAL;
#else
return -1;
#endif
}
int OFMutex::wrunlock()
{
#ifdef WINDOWS_INTERFACE
#ifdef USE_WIN32_CREATE_MUTEX
if (ReleaseMutex(OFthread_cast(HANDLE, theMutex))) return 0; else return OFstatic_cast(int, GetLastError());
#else
//LeaveCriticalSection(OFthread_cast(CRITICAL_SECTION *, theMutex));
ReleaseSRWLockExclusive(OFthread_cast(SRWLOCK*, theMutex));
return 0;
#endif
#elif defined(POSIX_INTERFACE)
......
if (theLock)
{
OFReadWriteLockHelper *rwl = OFthread_cast(OFReadWriteLockHelper *, theLock);
int result =0;
while (1)
{
if (0 != (result = rwl->accessMutex.lock())) return result; // lock mutex
if (rwl->numReaders >= 0) // we can grant the read lock
{
if (rwl->numReaders == 0)
{
if (0 != (result = rwl->usageSemaphore.wait()))
{
rwl->accessMutex.unlock();
return result;
}
}
(rwl->numReaders)++;
return rwl->accessMutex.unlock();
}
// we cannot grant the read lock, block thread.
if (0 != (result = rwl->accessMutex.unlock())) return result;
if (0 != (result = rwl->usageSemaphore.wait())) return result;
if (0 != (result = rwl->usageSemaphore.post())) return result;
}
return rwl->accessMutex.rdlock();
} else return EINVAL;
#elif defined(POSIX_INTERFACE)
if (theLock) return pthread_rwlock_rdlock(OFthread_cast(pthread_rwlock_t *, theLock)); else return EINVAL;
......
if (theLock)
{
OFReadWriteLockHelper *rwl = OFthread_cast(OFReadWriteLockHelper *, theLock);
int result =0;
while (1)
{
if (0 != (result = rwl->accessMutex.lock())) return result; // lock mutex
if (rwl->numReaders == 0) // we can grant the write lock
{
if (0 != (result = rwl->usageSemaphore.wait()))
{
rwl->accessMutex.unlock();
return result;
}
rwl->numReaders = -1;
return rwl->accessMutex.unlock();
}
// we cannot grant the write lock, block thread.
if (0 != (result = rwl->accessMutex.unlock())) return result;
if (0 != (result = rwl->usageSemaphore.wait())) return result;
if (0 != (result = rwl->usageSemaphore.post())) return result;
}
return rwl->accessMutex.wrlock();
} else return EINVAL;
#elif defined(POSIX_INTERFACE)
if (theLock) return pthread_rwlock_wrlock(OFthread_cast(pthread_rwlock_t *, theLock)); else return EINVAL;
......
if (theLock)
{
OFReadWriteLockHelper *rwl = OFthread_cast(OFReadWriteLockHelper *, theLock);
int result =0;
if (0 != (result = rwl->accessMutex.lock())) return result; // lock mutex
if (rwl->numReaders >= 0) // we can grant the read lock
{
if (rwl->numReaders == 0)
{
if (0 != (result = rwl->usageSemaphore.wait()))
{
rwl->accessMutex.unlock();
return result;
}
}
(rwl->numReaders)++;
return rwl->accessMutex.unlock();
}
result = rwl->accessMutex.unlock();
if (result) return result; else return OFReadWriteLock::busy;
return rwl->accessMutex.tryrdlock();
} else return EINVAL;
#elif defined(POSIX_INTERFACE)
if (theLock) return pthread_rwlock_tryrdlock(OFthread_cast(pthread_rwlock_t *, theLock)); else return EINVAL; // may return EBUSY.
......
if (theLock)
{
OFReadWriteLockHelper *rwl = OFthread_cast(OFReadWriteLockHelper *, theLock);
int result =0;
if (0 != (result = rwl->accessMutex.lock())) return result; // lock mutex
if (rwl->numReaders == 0) // we can grant the write lock
{
if (0 != (result = rwl->usageSemaphore.wait()))
{
rwl->accessMutex.unlock();
return result;
}
rwl->numReaders = -1;
return rwl->accessMutex.unlock();
}
result = rwl->accessMutex.unlock();
if (result) return result; else return OFReadWriteLock::busy;
return rwl->accessMutex.trywrlock();
} else return EINVAL;
#elif defined(POSIX_INTERFACE)
if (theLock) return pthread_rwlock_trywrlock(OFthread_cast(pthread_rwlock_t *, theLock)); else return EINVAL; // may return EBUSY.
......
if (theLock)
{
OFReadWriteLockHelper *rwl = OFthread_cast(OFReadWriteLockHelper *, theLock);
int result =0;
if (0 != (result = rwl->accessMutex.lock())) return result; // lock mutex
if (rwl->numReaders == -1) rwl->numReaders = 0; else (rwl->numReaders)--;
if ((rwl->numReaders == 0) && (0 != (result = rwl->usageSemaphore.post())))
{
rwl->accessMutex.unlock();
return result;
}
return rwl->accessMutex.unlock();
} else return EINVAL;
#elif defined(POSIX_INTERFACE)
if (theLock) return pthread_rwlock_unlock(OFthread_cast(pthread_rwlock_t *, theLock)); else return EINVAL;
#elif defined(SOLARIS_INTERFACE)
if (theLock) return rw_unlock(OFthread_cast(rwlock_t *, theLock)); else return EINVAL;
#else
return -1;
#endif
}
int OFReadWriteLock::rdunlock()
{
#if defined(WINDOWS_INTERFACE) || defined(POSIX_INTERFACE_WITHOUT_RWLOCK)
if (theLock)
{
OFReadWriteLockHelper *rwl = OFthread_cast(OFReadWriteLockHelper *, theLock);
return rwl->accessMutex.rdunlock();
} else return EINVAL;
#elif defined(POSIX_INTERFACE)
if (theLock) return pthread_rwlock_unlock(OFthread_cast(pthread_rwlock_t *, theLock)); else return EINVAL;
#elif defined(SOLARIS_INTERFACE)
if (theLock) return rw_unlock(OFthread_cast(rwlock_t *, theLock)); else return EINVAL;
#else
return -1;
#endif
}
int OFReadWriteLock::wrunlock()
{
#if defined(WINDOWS_INTERFACE) || defined(POSIX_INTERFACE_WITHOUT_RWLOCK)
if (theLock)
{
OFReadWriteLockHelper *rwl = OFthread_cast(OFReadWriteLockHelper *, theLock);
return rwl->accessMutex.wrunlock();
} else return EINVAL;
#elif defined(POSIX_INTERFACE)
if (theLock) return pthread_rwlock_unlock(OFthread_cast(pthread_rwlock_t *, theLock)); else return EINVAL;
#elif defined(SOLARIS_INTERFACE)
if (theLock) return rw_unlock(OFthread_cast(rwlock_t *, theLock)); else return EINVAL;
#else
(1-1/2)