Mercurial > hg > orthanc
changeset 5175:48005e522bd6
start fixing thread safety issues with DicomMap
author | Sebastien Jodogne <s.jodogne@gmail.com> |
---|---|
date | Fri, 24 Mar 2023 19:00:33 +0100 |
parents | d75af1cde602 |
children | 6d8647122ef3 |
files | OrthancFramework/Sources/DicomFormat/DicomMap.cpp OrthancFramework/Sources/DicomFormat/DicomMap.h OrthancFramework/UnitTestsSources/DicomMapTests.cpp OrthancServer/Sources/Database/StatelessDatabaseOperations.cpp OrthancServer/Sources/ServerJobs/ResourceModificationJob.cpp |
diffstat | 5 files changed, 70 insertions(+), 60 deletions(-) [+] |
line wrap: on
line diff
--- a/OrthancFramework/Sources/DicomFormat/DicomMap.cpp Wed Mar 22 08:26:41 2023 +0100 +++ b/OrthancFramework/Sources/DicomFormat/DicomMap.cpp Fri Mar 24 19:00:33 2023 +0100 @@ -139,8 +139,6 @@ class DicomMap::MainDicomTagsConfiguration { private: - friend DicomMap; - std::set<DicomTag> patientsMainDicomTagsByLevel_; std::set<DicomTag> studiesMainDicomTagsByLevel_; std::set<DicomTag> seriesMainDicomTagsByLevel_; @@ -156,27 +154,6 @@ ResetDefaultMainDicomTags(); } - void ResetDefaultMainDicomTags() - { - patientsMainDicomTagsByLevel_.clear(); - studiesMainDicomTagsByLevel_.clear(); - seriesMainDicomTagsByLevel_.clear(); - instancesMainDicomTagsByLevel_.clear(); - - allMainDicomTags_.clear(); - - // by default, initialize with the previous static list (up to 1.10.0) - LoadDefaultMainDicomTags(ResourceType_Patient); - LoadDefaultMainDicomTags(ResourceType_Study); - LoadDefaultMainDicomTags(ResourceType_Series); - LoadDefaultMainDicomTags(ResourceType_Instance); - - defaultSignatures_[ResourceType_Patient] = signatures_[ResourceType_Patient]; - defaultSignatures_[ResourceType_Study] = signatures_[ResourceType_Study]; - defaultSignatures_[ResourceType_Series] = signatures_[ResourceType_Series]; - defaultSignatures_[ResourceType_Instance] = signatures_[ResourceType_Instance]; - } - std::string ComputeSignature(const std::set<DicomTag>& tags) { // std::set are sorted by default (which is important for us !) @@ -229,29 +206,6 @@ { AddMainDicomTag(tags[i], level); } - - } - - - std::set<DicomTag>& GetMainDicomTagsByLevel(ResourceType level) - { - switch (level) - { - case ResourceType_Patient: - return patientsMainDicomTagsByLevel_; - - case ResourceType_Study: - return studiesMainDicomTagsByLevel_; - - case ResourceType_Series: - return seriesMainDicomTagsByLevel_; - - case ResourceType_Instance: - return instancesMainDicomTagsByLevel_; - - default: - throw OrthancException(ErrorCode_InternalError); - } } public: @@ -262,6 +216,27 @@ return parameters; } + void ResetDefaultMainDicomTags() + { + patientsMainDicomTagsByLevel_.clear(); + studiesMainDicomTagsByLevel_.clear(); + seriesMainDicomTagsByLevel_.clear(); + instancesMainDicomTagsByLevel_.clear(); + + allMainDicomTags_.clear(); + + // by default, initialize with the previous static list (up to 1.10.0) + LoadDefaultMainDicomTags(ResourceType_Patient); + LoadDefaultMainDicomTags(ResourceType_Study); + LoadDefaultMainDicomTags(ResourceType_Series); + LoadDefaultMainDicomTags(ResourceType_Instance); + + defaultSignatures_[ResourceType_Patient] = signatures_[ResourceType_Patient]; + defaultSignatures_[ResourceType_Study] = signatures_[ResourceType_Study]; + defaultSignatures_[ResourceType_Series] = signatures_[ResourceType_Series]; + defaultSignatures_[ResourceType_Instance] = signatures_[ResourceType_Instance]; + } + void AddMainDicomTag(const DicomTag& tag, ResourceType level) { const std::set<DicomTag>& existingLevelTags = GetMainDicomTagsByLevel(level); @@ -296,6 +271,26 @@ return defaultSignatures_[level]; } + std::set<DicomTag>& GetMainDicomTagsByLevel(ResourceType level) + { + switch (level) + { + case ResourceType_Patient: + return patientsMainDicomTagsByLevel_; + + case ResourceType_Study: + return studiesMainDicomTagsByLevel_; + + case ResourceType_Series: + return seriesMainDicomTagsByLevel_; + + case ResourceType_Instance: + return instancesMainDicomTagsByLevel_; + + default: + throw OrthancException(ErrorCode_InternalError); + } + } }; @@ -706,9 +701,10 @@ } - const std::set<DicomTag>& DicomMap::GetMainDicomTags(ResourceType level) + void DicomMap::GetMainDicomTags(std::set<DicomTag>& target, + ResourceType level) { - return DicomMap::MainDicomTagsConfiguration::GetInstance().GetMainDicomTagsByLevel(level); + target = DicomMap::MainDicomTagsConfiguration::GetInstance().GetMainDicomTagsByLevel(level); } const std::set<DicomTag>& DicomMap::GetAllMainDicomTags()
--- a/OrthancFramework/Sources/DicomFormat/DicomMap.h Wed Mar 22 08:26:41 2023 +0100 +++ b/OrthancFramework/Sources/DicomFormat/DicomMap.h Fri Mar 24 19:00:33 2023 +0100 @@ -154,7 +154,8 @@ static bool HasComputedTags(const std::set<DicomTag>& tags); - static const std::set<DicomTag>& GetMainDicomTags(ResourceType level); + static void GetMainDicomTags(std::set<DicomTag>& target, + ResourceType level); // returns a string uniquely identifying the list of main dicom tags for a level static const std::string& GetMainDicomTagsSignature(ResourceType level);
--- a/OrthancFramework/UnitTestsSources/DicomMapTests.cpp Wed Mar 22 08:26:41 2023 +0100 +++ b/OrthancFramework/UnitTestsSources/DicomMapTests.cpp Fri Mar 24 19:00:33 2023 +0100 @@ -90,26 +90,30 @@ } { - const std::set<DicomTag>& s = DicomMap::GetMainDicomTags(ResourceType_Patient); + std::set<DicomTag> s; + DicomMap::GetMainDicomTags(s, ResourceType_Patient); ASSERT_TRUE(s.end() != s.find(DICOM_TAG_PATIENT_ID)); ASSERT_TRUE(s.end() == s.find(DICOM_TAG_STUDY_INSTANCE_UID)); } { - const std::set<DicomTag>& s = DicomMap::GetMainDicomTags(ResourceType_Study); + std::set<DicomTag> s; + DicomMap::GetMainDicomTags(s, ResourceType_Study); ASSERT_TRUE(s.end() != s.find(DICOM_TAG_STUDY_INSTANCE_UID)); ASSERT_TRUE(s.end() != s.find(DICOM_TAG_ACCESSION_NUMBER)); ASSERT_TRUE(s.end() == s.find(DICOM_TAG_PATIENT_ID)); } { - const std::set<DicomTag>& s = DicomMap::GetMainDicomTags(ResourceType_Series); + std::set<DicomTag> s; + DicomMap::GetMainDicomTags(s, ResourceType_Series); ASSERT_TRUE(s.end() != s.find(DICOM_TAG_SERIES_INSTANCE_UID)); ASSERT_TRUE(s.end() == s.find(DICOM_TAG_PATIENT_ID)); } { - const std::set<DicomTag>& s = DicomMap::GetMainDicomTags(ResourceType_Instance); + std::set<DicomTag> s; + DicomMap::GetMainDicomTags(s, ResourceType_Instance); ASSERT_TRUE(s.end() != s.find(DICOM_TAG_SOP_INSTANCE_UID)); ASSERT_TRUE(s.end() == s.find(DICOM_TAG_PATIENT_ID)); } @@ -120,12 +124,14 @@ DicomMap::AddMainDicomTag(DICOM_TAG_BITS_ALLOCATED, ResourceType_Instance); { - const std::set<DicomTag>& s = DicomMap::GetMainDicomTags(ResourceType_Instance); + std::set<DicomTag> s; + DicomMap::GetMainDicomTags(s, ResourceType_Instance); ASSERT_TRUE(s.end() != s.find(DICOM_TAG_BITS_ALLOCATED)); ASSERT_TRUE(s.end() != s.find(DICOM_TAG_SOP_INSTANCE_UID)); } { - const std::set<DicomTag>& s = DicomMap::GetMainDicomTags(ResourceType_Series); + std::set<DicomTag> s; + DicomMap::GetMainDicomTags(s, ResourceType_Series); ASSERT_TRUE(s.end() == s.find(DICOM_TAG_BITS_ALLOCATED)); } @@ -242,8 +248,10 @@ // REFERENCE: DICOM PS3.3 2015c - Information Object Definitions // http://dicom.nema.org/medical/dicom/current/output/html/part03.html + std::set<DicomTag> main; + DicomMap::GetMainDicomTags(main, level); + std::set<DicomTag> moduleTags; - const std::set<DicomTag>& main = DicomMap::GetMainDicomTags(level); DicomTag::AddTagsForModule(moduleTags, module); // The main dicom tags are a subset of the module @@ -918,7 +926,8 @@ { ResourceType level = static_cast<ResourceType>(i); - const std::set<DicomTag>& tags = DicomMap::GetMainDicomTags(level); + std::set<DicomTag> tags; + DicomMap::GetMainDicomTags(tags, level); for (std::set<DicomTag>::const_iterator it = tags.begin(); it != tags.end(); ++it) {
--- a/OrthancServer/Sources/Database/StatelessDatabaseOperations.cpp Wed Mar 22 08:26:41 2023 +0100 +++ b/OrthancServer/Sources/Database/StatelessDatabaseOperations.cpp Fri Mar 24 19:00:33 2023 +0100 @@ -362,7 +362,8 @@ } { - const std::set<DicomTag>& tags = DicomMap::GetMainDicomTags(level); + std::set<DicomTag> tags; + DicomMap::GetMainDicomTags(tags, level); for (std::set<DicomTag>::const_iterator tag = tags.begin(); tag != tags.end(); ++tag)
--- a/OrthancServer/Sources/ServerJobs/ResourceModificationJob.cpp Wed Mar 22 08:26:41 2023 +0100 +++ b/OrthancServer/Sources/ServerJobs/ResourceModificationJob.cpp Fri Mar 24 19:00:33 2023 +0100 @@ -749,8 +749,11 @@ DicomMap targetPatientTags; targetPatient.tags_.ExtractPatientInformation(targetPatientTags); - for (std::set<DicomTag>::const_iterator mainPatientTag = DicomMap::GetMainDicomTags(ResourceType_Patient).begin(); - mainPatientTag != DicomMap::GetMainDicomTags(ResourceType_Patient).end(); ++mainPatientTag) + std::set<DicomTag> mainPatientTags; + DicomMap::GetMainDicomTags(mainPatientTags, ResourceType_Patient); + + for (std::set<DicomTag>::const_iterator mainPatientTag = mainPatientTags.begin(); + mainPatientTag != mainPatientTags.end(); ++mainPatientTag) { if (targetPatientTags.HasTag(*mainPatientTag) && (!modification_->IsReplaced(*mainPatientTag)