changeset 431:906efffc68fd

integration OrthancDicomWeb-1.1->mainline
author Sebastien Jodogne <s.jodogne@gmail.com>
date Mon, 25 May 2020 14:15:16 +0200
parents 641b21848ed5 (diff) 4b1de0813852 (current diff)
children ad671caa2dcf
files CMakeLists.txt Resources/Orthanc/DownloadOrthancFramework.cmake Resources/Orthanc/LinuxStandardBaseToolchain.cmake
diffstat 12 files changed, 359 insertions(+), 71 deletions(-) [+]
line wrap: on
line diff
--- a/CMakeLists.txt	Mon May 25 13:01:52 2020 +0200
+++ b/CMakeLists.txt	Mon May 25 14:15:16 2020 +0200
@@ -21,10 +21,11 @@
 
 project(OrthancDicomWeb)
 
-set(ORTHANC_DICOM_WEB_VERSION "1.1")
+set(ORTHANC_DICOM_WEB_VERSION "mainline")
 
 if (ORTHANC_DICOM_WEB_VERSION STREQUAL "mainline")
-  set(ORTHANC_FRAMEWORK_DEFAULT_VERSION "mainline")
+  # TODO - Switch to "mainline" after "transcoding" is made the new "default"
+  set(ORTHANC_FRAMEWORK_DEFAULT_VERSION "1.6.1")
   set(ORTHANC_FRAMEWORK_DEFAULT_SOURCE "hg")
 else()
   set(ORTHANC_FRAMEWORK_DEFAULT_VERSION "1.6.1")
--- a/NEWS	Mon May 25 13:01:52 2020 +0200
+++ b/NEWS	Mon May 25 14:15:16 2020 +0200
@@ -2,6 +2,12 @@
 ===============================
 
 
+Maintenance
+-----------
+
+* "QidoCaseSensitive" defaults to "CaseSensitivePN" of Orthanc configuration (instead of "true")
+
+
 Version 1.1 (2020-03-04)
 ========================
 
--- a/Plugin/Configuration.cpp	Mon May 25 13:01:52 2020 +0200
+++ b/Plugin/Configuration.cpp	Mon May 25 14:15:16 2020 +0200
@@ -334,6 +334,14 @@
     }
 
 
+    bool LookupBooleanValue(bool& target,
+                            const std::string& key)
+    {
+      assert(configuration_.get() != NULL);
+      return configuration_->LookupBooleanValue(target, key);
+    }
+
+
     unsigned int GetUnsignedIntegerValue(const std::string& key,
                                          unsigned int defaultValue)
     {
--- a/Plugin/Configuration.h	Mon May 25 13:01:52 2020 +0200
+++ b/Plugin/Configuration.h	Mon May 25 14:15:16 2020 +0200
@@ -92,12 +92,14 @@
   {
     void Initialize();
 
-    std::string GetStringValue(const std::string& key,
-                               const std::string& defaultValue);
-
+    bool HasKey(const std::string& key);
+    
     bool GetBooleanValue(const std::string& key,
                          bool defaultValue);
 
+    bool LookupBooleanValue(bool& target,
+                            const std::string& key);
+
     unsigned int GetUnsignedIntegerValue(const std::string& key,
                                          unsigned int defaultValue);
 
--- a/Plugin/GdcmParsedDicomFile.cpp	Mon May 25 13:01:52 2020 +0200
+++ b/Plugin/GdcmParsedDicomFile.cpp	Mon May 25 14:15:16 2020 +0200
@@ -433,3 +433,6 @@
     return OrthancPlugins::GetWadoUrl(base, GetDataSet());
   }
 }
+
+
+#include "./GdcmParsedDicomFile_TransferSyntaxes.impl.h"
--- a/Plugin/GdcmParsedDicomFile.h	Mon May 25 13:01:52 2020 +0200
+++ b/Plugin/GdcmParsedDicomFile.h	Mon May 25 14:15:16 2020 +0200
@@ -85,5 +85,14 @@
                        const gdcm::Tag& tag) const;
 
     std::string GetWadoUrl(const OrthancPluginHttpRequest* request) const;
+
+    Orthanc::DicomTransferSyntax GetTransferSyntax() const
+    {
+      return GetOrthancTransferSyntax(GetFile().GetHeader().GetDataSetTransferSyntax());
+    }
+    
+    static gdcm::TransferSyntax GetGdcmTransferSyntax(Orthanc::DicomTransferSyntax syntax);
+    
+    static Orthanc::DicomTransferSyntax GetOrthancTransferSyntax(gdcm::TransferSyntax syntax);
   };
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/Plugin/GdcmParsedDicomFile_TransferSyntaxes.impl.h	Mon May 25 14:15:16 2020 +0200
@@ -0,0 +1,121 @@
+/**
+ * Orthanc - A Lightweight, RESTful DICOM Store
+ * Copyright (C) 2012-2016 Sebastien Jodogne, Medical Physics
+ * Department, University Hospital of Liege, Belgium
+ * Copyright (C) 2017-2020 Osimis S.A., Belgium
+ *
+ * This program is free software: you can redistribute it and/or
+ * modify it under the terms of the GNU Affero General Public License
+ * as published by the Free Software Foundation, either version 3 of
+ * the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Affero General Public License for more details.
+ * 
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ **/
+
+// This file is autogenerated by "../Resources/GenerateTransferSyntaxes.py"
+
+namespace OrthancPlugins
+{
+  gdcm::TransferSyntax GdcmParsedDicomFile::GetGdcmTransferSyntax(Orthanc::DicomTransferSyntax syntax)
+  {
+    switch (syntax)
+    {
+      case Orthanc::DicomTransferSyntax_LittleEndianImplicit:
+        return gdcm::TransferSyntax::ImplicitVRLittleEndian;
+
+      case Orthanc::DicomTransferSyntax_LittleEndianExplicit:
+        return gdcm::TransferSyntax::ExplicitVRLittleEndian;
+
+      case Orthanc::DicomTransferSyntax_JPEGProcess1:
+        return gdcm::TransferSyntax::JPEGBaselineProcess1;
+
+      case Orthanc::DicomTransferSyntax_JPEGProcess2_4:
+        return gdcm::TransferSyntax::JPEGExtendedProcess2_4;
+
+      case Orthanc::DicomTransferSyntax_JPEGProcess14:
+        return gdcm::TransferSyntax::JPEGLosslessProcess14;
+
+      case Orthanc::DicomTransferSyntax_JPEGProcess14SV1:
+        return gdcm::TransferSyntax::JPEGLosslessProcess14_1;
+
+      case Orthanc::DicomTransferSyntax_JPEGLSLossless:
+        return gdcm::TransferSyntax::JPEGLSLossless;
+
+      case Orthanc::DicomTransferSyntax_JPEGLSLossy:
+        return gdcm::TransferSyntax::JPEGLSNearLossless;
+
+      case Orthanc::DicomTransferSyntax_JPEG2000LosslessOnly:
+        return gdcm::TransferSyntax::JPEG2000Lossless;
+
+      case Orthanc::DicomTransferSyntax_JPEG2000:
+        return gdcm::TransferSyntax::JPEG2000;
+
+      case Orthanc::DicomTransferSyntax_JPEG2000MulticomponentLosslessOnly:
+        return gdcm::TransferSyntax::JPEG2000Part2Lossless;
+
+      case Orthanc::DicomTransferSyntax_JPEG2000Multicomponent:
+        return gdcm::TransferSyntax::JPEG2000Part2;
+
+      case Orthanc::DicomTransferSyntax_RLELossless:
+        return gdcm::TransferSyntax::RLELossless;
+
+      default:
+        throw Orthanc::OrthancException(Orthanc::ErrorCode_ParameterOutOfRange);
+    }
+  }
+
+
+  Orthanc::DicomTransferSyntax GdcmParsedDicomFile::GetOrthancTransferSyntax(gdcm::TransferSyntax syntax)
+  {
+    switch (syntax)
+    {
+      case gdcm::TransferSyntax::ImplicitVRLittleEndian:
+        return Orthanc::DicomTransferSyntax_LittleEndianImplicit;
+
+      case gdcm::TransferSyntax::ExplicitVRLittleEndian:
+        return Orthanc::DicomTransferSyntax_LittleEndianExplicit;
+
+      case gdcm::TransferSyntax::JPEGBaselineProcess1:
+        return Orthanc::DicomTransferSyntax_JPEGProcess1;
+
+      case gdcm::TransferSyntax::JPEGExtendedProcess2_4:
+        return Orthanc::DicomTransferSyntax_JPEGProcess2_4;
+
+      case gdcm::TransferSyntax::JPEGLosslessProcess14:
+        return Orthanc::DicomTransferSyntax_JPEGProcess14;
+
+      case gdcm::TransferSyntax::JPEGLosslessProcess14_1:
+        return Orthanc::DicomTransferSyntax_JPEGProcess14SV1;
+
+      case gdcm::TransferSyntax::JPEGLSLossless:
+        return Orthanc::DicomTransferSyntax_JPEGLSLossless;
+
+      case gdcm::TransferSyntax::JPEGLSNearLossless:
+        return Orthanc::DicomTransferSyntax_JPEGLSLossy;
+
+      case gdcm::TransferSyntax::JPEG2000Lossless:
+        return Orthanc::DicomTransferSyntax_JPEG2000LosslessOnly;
+
+      case gdcm::TransferSyntax::JPEG2000:
+        return Orthanc::DicomTransferSyntax_JPEG2000;
+
+      case gdcm::TransferSyntax::JPEG2000Part2Lossless:
+        return Orthanc::DicomTransferSyntax_JPEG2000MulticomponentLosslessOnly;
+
+      case gdcm::TransferSyntax::JPEG2000Part2:
+        return Orthanc::DicomTransferSyntax_JPEG2000Multicomponent;
+
+      case gdcm::TransferSyntax::RLELossless:
+        return Orthanc::DicomTransferSyntax_RLELossless;
+
+      default:
+        throw Orthanc::OrthancException(Orthanc::ErrorCode_ParameterOutOfRange);
+    }
+  }
+}
--- a/Plugin/QidoRs.cpp	Mon May 25 13:01:52 2020 +0200
+++ b/Plugin/QidoRs.cpp	Mon May 25 14:15:16 2020 +0200
@@ -265,8 +265,13 @@
           throw Orthanc::OrthancException(Orthanc::ErrorCode_InternalError);
       }
 
+      bool caseSensitive;
+      if (OrthancPlugins::Configuration::LookupBooleanValue(caseSensitive, "QidoCaseSensitive"))
+      {
+        result["CaseSensitive"] = caseSensitive;
+      }
+
       result["Expand"] = false;
-      result["CaseSensitive"] = OrthancPlugins::Configuration::GetBooleanValue("QidoCaseSensitive", true);
       result["Query"] = Json::objectValue;
       result["Limit"] = limit_;
       result["Since"] = offset_;
@@ -483,6 +488,8 @@
   Json::Value find;
   matcher.ConvertToOrthanc(find, level);
 
+  LOG(INFO) << "Body of the call from QIDO-RS to /tools/find: " << find.toStyledString();
+  
   std::string body;
 
   {
--- a/Plugin/WadoRsRetrieveFrames.cpp	Mon May 25 13:01:52 2020 +0200
+++ b/Plugin/WadoRsRetrieveFrames.cpp	Mon May 25 14:15:16 2020 +0200
@@ -35,7 +35,6 @@
 #include <boost/lexical_cast.hpp>
 
 
-
 static void TokenizeAndNormalize(std::vector<std::string>& tokens,
                                  const std::string& source,
                                  char separator)
@@ -62,8 +61,8 @@
 
 
 
-static gdcm::TransferSyntax ParseTransferSyntax(const OrthancPluginHttpRequest* request,
-                                                gdcm::TransferSyntax sourceTransferSyntax)
+static Orthanc::DicomTransferSyntax ParseTransferSyntax(const OrthancPluginHttpRequest* request,
+                                                        Orthanc::DicomTransferSyntax sourceTransferSyntax)
 {
   for (uint32_t i = 0; i < request->headersCount; i++)
   {
@@ -78,7 +77,7 @@
       if (tokens.size() == 0 ||
           tokens[0] == "*/*")
       {
-        return gdcm::TransferSyntax::ExplicitVRLittleEndian;
+        return Orthanc::DicomTransferSyntax_LittleEndianExplicit;
       }
 
       if (tokens[0] != "multipart/related")
@@ -116,7 +115,7 @@
       {
         if (transferSyntax.empty())
         {
-          return gdcm::TransferSyntax(gdcm::TransferSyntax::ExplicitVRLittleEndian);
+          return Orthanc::DicomTransferSyntax(Orthanc::DicomTransferSyntax_LittleEndianExplicit);
         }
         else if (transferSyntax == "*")
         {
@@ -140,51 +139,51 @@
         if (type == "image/jpeg" && (transferSyntax.empty() ||  // Default
                                      transferSyntax == "1.2.840.10008.1.2.4.70"))
         {
-          return gdcm::TransferSyntax::JPEGLosslessProcess14_1;
+          return Orthanc::DicomTransferSyntax_JPEGProcess14SV1;
         }
         else if (type == "image/jpeg" && transferSyntax == "1.2.840.10008.1.2.4.50")
         {
-          return gdcm::TransferSyntax::JPEGBaselineProcess1;
+          return Orthanc::DicomTransferSyntax_JPEGProcess1;
         }
         else if (type == "image/jpeg" && transferSyntax == "1.2.840.10008.1.2.4.51")
         {
-          return gdcm::TransferSyntax::JPEGExtendedProcess2_4;
+          return Orthanc::DicomTransferSyntax_JPEGProcess2_4;
         }
         else if (type == "image/jpeg" && transferSyntax == "1.2.840.10008.1.2.4.57")
         {
-          return gdcm::TransferSyntax::JPEGLosslessProcess14;
+          return Orthanc::DicomTransferSyntax_JPEGProcess14;
         }
         else if (type == "image/x-dicom-rle" && (transferSyntax.empty() ||  // Default
                                                  transferSyntax == "1.2.840.10008.1.2.5"))
         {
-          return gdcm::TransferSyntax::RLELossless;
+          return Orthanc::DicomTransferSyntax_RLELossless;
         }
         else if (type == "image/x-jls" && (transferSyntax.empty() ||  // Default
                                            transferSyntax == "1.2.840.10008.1.2.4.80"))
         {
-          return gdcm::TransferSyntax::JPEGLSLossless;
+          return Orthanc::DicomTransferSyntax_JPEGLSLossless;
         }
         else if (type == "image/x-jls" && transferSyntax == "1.2.840.10008.1.2.4.81")
         {
-          return gdcm::TransferSyntax::JPEGLSNearLossless;
+          return Orthanc::DicomTransferSyntax_JPEGLSLossy;
         }
         else if (type == "image/jp2" && (transferSyntax.empty() ||  // Default
                                          transferSyntax == "1.2.840.10008.1.2.4.90"))
         {
-          return gdcm::TransferSyntax::JPEG2000Lossless;
+          return Orthanc::DicomTransferSyntax_JPEG2000LosslessOnly;
         }
         else if (type == "image/jp2" && transferSyntax == "1.2.840.10008.1.2.4.91")
         {
-          return gdcm::TransferSyntax::JPEG2000;
+          return Orthanc::DicomTransferSyntax_JPEG2000;
         }
         else if (type == "image/jpx" && (transferSyntax.empty() ||  // Default
                                          transferSyntax == "1.2.840.10008.1.2.4.92"))
         {
-          return gdcm::TransferSyntax::JPEG2000Part2Lossless;
+          return Orthanc::DicomTransferSyntax_JPEG2000MulticomponentLosslessOnly;
         }
         else if (type == "image/jpx" && transferSyntax == "1.2.840.10008.1.2.4.93")
         {
-          return gdcm::TransferSyntax::JPEG2000Part2;
+          return Orthanc::DicomTransferSyntax_JPEG2000Multicomponent;
         }
 
 
@@ -194,52 +193,52 @@
          **/
         if (type == "image/dicom+jpeg" && transferSyntax == "1.2.840.10008.1.2.4.50")
         {
-          return gdcm::TransferSyntax::JPEGBaselineProcess1;
+          return Orthanc::DicomTransferSyntax_JPEGProcess1;
         }
         else if (type == "image/dicom+jpeg" && transferSyntax == "1.2.840.10008.1.2.4.51")
         {
-          return gdcm::TransferSyntax::JPEGExtendedProcess2_4;
+          return Orthanc::DicomTransferSyntax_JPEGProcess2_4;
         }
         else if (type == "image/dicom+jpeg" && transferSyntax == "1.2.840.10008.1.2.4.57")
         {
-          return gdcm::TransferSyntax::JPEGLosslessProcess14;
+          return Orthanc::DicomTransferSyntax_JPEGProcess14;
         }
         else if (type == "image/dicom+jpeg" && (transferSyntax.empty() ||
                                                 transferSyntax == "1.2.840.10008.1.2.4.70"))
         {
-          return gdcm::TransferSyntax::JPEGLosslessProcess14_1;
+          return Orthanc::DicomTransferSyntax_JPEGProcess14SV1;
         }
         else if (type == "image/dicom+rle" && (transferSyntax.empty() ||
                                                transferSyntax == "1.2.840.10008.1.2.5"))
         {
-          return gdcm::TransferSyntax::RLELossless;
+          return Orthanc::DicomTransferSyntax_RLELossless;
         }
         else if (type == "image/dicom+jpeg-ls" && (transferSyntax.empty() ||
                                                    transferSyntax == "1.2.840.10008.1.2.4.80"))
         {
-          return gdcm::TransferSyntax::JPEGLSLossless;
+          return Orthanc::DicomTransferSyntax_JPEGLSLossless;
         }
         else if (type == "image/dicom+jpeg-ls" && transferSyntax == "1.2.840.10008.1.2.4.81")
         {
-          return gdcm::TransferSyntax::JPEGLSNearLossless;
+          return Orthanc::DicomTransferSyntax_JPEGLSLossy;
         }
         else if (type == "image/dicom+jp2" && (transferSyntax.empty() ||
                                                transferSyntax == "1.2.840.10008.1.2.4.90"))
         {
-          return gdcm::TransferSyntax::JPEG2000Lossless;
+          return Orthanc::DicomTransferSyntax_JPEG2000LosslessOnly;
         }
         else if (type == "image/dicom+jp2" && transferSyntax == "1.2.840.10008.1.2.4.91")
         {
-          return gdcm::TransferSyntax::JPEG2000;
+          return Orthanc::DicomTransferSyntax_JPEG2000;
         }
         else if (type == "image/dicom+jpx" && (transferSyntax.empty() ||
                                                transferSyntax == "1.2.840.10008.1.2.4.92"))
         {
-          return gdcm::TransferSyntax::JPEG2000Part2Lossless;
+          return Orthanc::DicomTransferSyntax_JPEG2000MulticomponentLosslessOnly;
         }
         else if (type == "image/dicom+jpx" && transferSyntax == "1.2.840.10008.1.2.4.93")
         {
-          return gdcm::TransferSyntax::JPEG2000Part2;
+          return Orthanc::DicomTransferSyntax_JPEG2000Multicomponent;
         }
 
         throw Orthanc::OrthancException(
@@ -251,7 +250,7 @@
   }
 
   // By default, DICOMweb expectes Little Endian uncompressed pixel data
-  return gdcm::TransferSyntax::ExplicitVRLittleEndian;
+  return Orthanc::DicomTransferSyntax_LittleEndianExplicit;
 }
 
 
@@ -288,51 +287,51 @@
 
 
 
-static const char* GetMimeType(const gdcm::TransferSyntax& syntax)
+static const char* GetMimeType(const Orthanc::DicomTransferSyntax& syntax)
 {
   // http://dicom.nema.org/medical/dicom/current/output/html/part18.html#table_6.1.1.8-3b
   // http://dicom.nema.org/MEDICAL/dicom/2019a/output/chtml/part18/chapter_6.html#table_6.1.1.8-3b
 
   switch (syntax)
   {
-    case gdcm::TransferSyntax::ImplicitVRLittleEndian:
+    case Orthanc::DicomTransferSyntax_LittleEndianImplicit:
       // The "transfer-syntax" info was added in version 1.1 of the plugin
       return "application/octet-stream; transfer-syntax=1.2.840.10008.1.2";
 
-    case gdcm::TransferSyntax::ExplicitVRLittleEndian:
+    case Orthanc::DicomTransferSyntax_LittleEndianExplicit:
       return "application/octet-stream; transfer-syntax=1.2.840.10008.1.2.1";
 
-    case gdcm::TransferSyntax::JPEGBaselineProcess1:
+    case Orthanc::DicomTransferSyntax_JPEGProcess1:
       return "image/jpeg; transfer-syntax=1.2.840.10008.1.2.4.50";
 
-    case gdcm::TransferSyntax::JPEGExtendedProcess2_4:
+    case Orthanc::DicomTransferSyntax_JPEGProcess2_4:
       return "image/jpeg; transfer-syntax=1.2.840.10008.1.2.4.51";
     
-    case gdcm::TransferSyntax::JPEGLosslessProcess14:
+    case Orthanc::DicomTransferSyntax_JPEGProcess14:
       return "image/jpeg; transfer-syntax=1.2.840.10008.1.2.4.57";
 
-    case gdcm::TransferSyntax::JPEGLosslessProcess14_1:
-      return "image/jpeg; transferSyntax=1.2.840.10008.1.2.4.70";
+    case Orthanc::DicomTransferSyntax_JPEGProcess14SV1:
+      return "image/jpeg; transfer-syntax=1.2.840.10008.1.2.4.70";
     
-    case gdcm::TransferSyntax::RLELossless:
-      return "image/x-dicom-rle; transferSyntax=1.2.840.10008.1.2.5";
+    case Orthanc::DicomTransferSyntax_RLELossless:
+      return "image/x-dicom-rle; transfer-syntax=1.2.840.10008.1.2.5";
 
-    case gdcm::TransferSyntax::JPEGLSLossless:
-      return "image/x-jls; transferSyntax=1.2.840.10008.1.2.4.80";
+    case Orthanc::DicomTransferSyntax_JPEGLSLossless:
+      return "image/x-jls; transfer-syntax=1.2.840.10008.1.2.4.80";
 
-    case gdcm::TransferSyntax::JPEGLSNearLossless:
+    case Orthanc::DicomTransferSyntax_JPEGLSLossy:
       return "image/x-jls; transfer-syntax=1.2.840.10008.1.2.4.81";
 
-    case gdcm::TransferSyntax::JPEG2000Lossless:
-      return "image/jp2; transferSyntax=1.2.840.10008.1.2.4.90";
+    case Orthanc::DicomTransferSyntax_JPEG2000LosslessOnly:
+      return "image/jp2; transfer-syntax=1.2.840.10008.1.2.4.90";
 
-    case gdcm::TransferSyntax::JPEG2000:
+    case Orthanc::DicomTransferSyntax_JPEG2000:
       return "image/jp2; transfer-syntax=1.2.840.10008.1.2.4.91";
 
-    case gdcm::TransferSyntax::JPEG2000Part2Lossless:
-      return "image/jpx; transferSyntax=1.2.840.10008.1.2.4.92";
+    case Orthanc::DicomTransferSyntax_JPEG2000MulticomponentLosslessOnly:
+      return "image/jpx; transfer-syntax=1.2.840.10008.1.2.4.92";
 
-    case gdcm::TransferSyntax::JPEG2000Part2:
+    case Orthanc::DicomTransferSyntax_JPEG2000Multicomponent:
       return "image/jpx; transfer-syntax=1.2.840.10008.1.2.4.93";
 
     default:
@@ -442,7 +441,7 @@
 static bool AnswerFrames(OrthancPluginRestOutput* output,
                          const OrthancPluginHttpRequest* request,
                          const OrthancPlugins::GdcmParsedDicomFile& dicom,
-                         const gdcm::TransferSyntax& syntax,
+                         const Orthanc::DicomTransferSyntax& syntax,
                          std::list<unsigned int>& frames)
 {
   static const gdcm::Tag DICOM_TAG_BITS_ALLOCATED(0x0028, 0x0100);
@@ -479,7 +478,11 @@
     std::string photometric;
     if (samplesPerPixel == 3 &&
         dicom.GetStringTag(photometric, DICOM_TAG_PHOTOMETRIC_INTERPRETATION, true) &&
-        photometric == "YBR_FULL")
+        photometric == "YBR_FULL" &&
+        // Only applicable to uncompressed transfer syntaxes
+        (syntax == Orthanc::DicomTransferSyntax_LittleEndianImplicit ||
+         syntax == Orthanc::DicomTransferSyntax_LittleEndianExplicit ||
+         syntax == Orthanc::DicomTransferSyntax_BigEndianExplicit))
     {
       convertYbr = true;
     }
@@ -520,8 +523,8 @@
     
     if (pixelData.GetByteValue()->GetLength() % frameSize != 0 &&
         (/* allow one padding byte to be present */
-         pixelData.GetByteValue()->GetLength() % 2 == 0 &&
-         pixelData.GetByteValue()->GetLength() % frameSize != 1))
+          pixelData.GetByteValue()->GetLength() % 2 == 0 &&
+          pixelData.GetByteValue()->GetLength() % frameSize != 1))
     {
       throw Orthanc::OrthancException(Orthanc::ErrorCode_InternalError);      
     }
@@ -625,21 +628,26 @@
     }
 
     std::auto_ptr<OrthancPlugins::GdcmParsedDicomFile> source;
-
-    gdcm::TransferSyntax sourceSyntax;
+    
+    Orthanc::DicomTransferSyntax sourceSyntax;
 
     if (header.type() == Json::objectValue &&
         header.isMember("TransferSyntaxUID"))
     {
-      sourceSyntax = gdcm::TransferSyntax::GetTSType(header["TransferSyntaxUID"].asCString());
+      std::string uid = header["TransferSyntaxUID"].asString();
+      if (!Orthanc::LookupTransferSyntax(sourceSyntax, uid))
+      {
+        throw Orthanc::OrthancException(Orthanc::ErrorCode_ParameterOutOfRange,
+                                        "Unknown transfer syntax: " + uid);
+      }
     }
     else
     {
       source.reset(new OrthancPlugins::GdcmParsedDicomFile(content));
-      sourceSyntax = source->GetFile().GetHeader().GetDataSetTransferSyntax();
+      sourceSyntax = source->GetTransferSyntax();
     }
 
-    gdcm::TransferSyntax targetSyntax(ParseTransferSyntax(request, sourceSyntax));
+    Orthanc::DicomTransferSyntax targetSyntax = ParseTransferSyntax(request, sourceSyntax);
 
     if (sourceSyntax == targetSyntax)
     {
@@ -654,16 +662,13 @@
     }
     else
     {
-      // Need to convert the transfer syntax
-
-      {
-        OrthancPlugins::LogInfo("DICOMweb RetrieveFrames: Transcoding instance " + orthancId + 
-                                " from transfer syntax " + std::string(sourceSyntax.GetString()) + 
-                                " to " + std::string(targetSyntax.GetString()));
-      }
+      // Need to convert the transfer syntax (transcoding)
+      OrthancPlugins::LogInfo("DICOMweb RetrieveFrames: Transcoding instance " + orthancId + 
+                              " from transfer syntax " + Orthanc::GetTransferSyntaxUid(sourceSyntax) +
+                              " to " + Orthanc::GetTransferSyntaxUid(targetSyntax));
 
       gdcm::ImageChangeTransferSyntax change;
-      change.SetTransferSyntax(targetSyntax);
+      change.SetTransferSyntax(OrthancPlugins::GdcmParsedDicomFile::GetGdcmTransferSyntax(targetSyntax));
 
       // TODO Avoid this unnecessary memcpy by defining a stream over the MemoryBuffer
       std::string dicom(content.GetData(), content.GetData() + content.GetSize());
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/Resources/GenerateTransferSyntaxes.mustache	Mon May 25 14:15:16 2020 +0200
@@ -0,0 +1,57 @@
+/**
+ * Orthanc - A Lightweight, RESTful DICOM Store
+ * Copyright (C) 2012-2016 Sebastien Jodogne, Medical Physics
+ * Department, University Hospital of Liege, Belgium
+ * Copyright (C) 2017-2020 Osimis S.A., Belgium
+ *
+ * This program is free software: you can redistribute it and/or
+ * modify it under the terms of the GNU Affero General Public License
+ * as published by the Free Software Foundation, either version 3 of
+ * the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Affero General Public License for more details.
+ * 
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ **/
+
+// This file is autogenerated by "../Resources/GenerateTransferSyntaxes.py"
+
+namespace OrthancPlugins
+{
+  gdcm::TransferSyntax GdcmParsedDicomFile::GetGdcmTransferSyntax(Orthanc::DicomTransferSyntax syntax)
+  {
+    switch (syntax)
+    {
+      {{#Syntaxes}}
+      {{#GDCM}}
+      case Orthanc::DicomTransferSyntax_{{Value}}:
+        return {{GDCM}};
+
+      {{/GDCM}}
+      {{/Syntaxes}}
+      default:
+        throw Orthanc::OrthancException(Orthanc::ErrorCode_ParameterOutOfRange);
+    }
+  }
+
+
+  Orthanc::DicomTransferSyntax GdcmParsedDicomFile::GetOrthancTransferSyntax(gdcm::TransferSyntax syntax)
+  {
+    switch (syntax)
+    {
+      {{#Syntaxes}}
+      {{#GDCM}}
+      case {{GDCM}}:
+        return Orthanc::DicomTransferSyntax_{{Value}};
+
+      {{/GDCM}}
+      {{/Syntaxes}}
+      default:
+        throw Orthanc::OrthancException(Orthanc::ErrorCode_ParameterOutOfRange);
+    }
+  }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/Resources/GenerateTransferSyntaxes.py	Mon May 25 14:15:16 2020 +0200
@@ -0,0 +1,50 @@
+#!/usr/bin/python
+
+# Orthanc - A Lightweight, RESTful DICOM Store
+# Copyright (C) 2012-2016 Sebastien Jodogne, Medical Physics
+# Department, University Hospital of Liege, Belgium
+# Copyright (C) 2017-2020 Osimis S.A., Belgium
+#
+# This program is free software: you can redistribute it and/or
+# modify it under the terms of the GNU General Public License as
+# published by the Free Software Foundation, either version 3 of the
+# License, or (at your option) any later version.
+#
+# In addition, as a special exception, the copyright holders of this
+# program give permission to link the code of its release with the
+# OpenSSL project's "OpenSSL" library (or with modified versions of it
+# that use the same license as the "OpenSSL" library), and distribute
+# the linked executables. You must obey the GNU General Public License
+# in all respects for all of the code used other than "OpenSSL". If you
+# modify file(s) with this exception, you may extend this exception to
+# your version of the file(s), but you are not obligated to do so. If
+# you do not wish to do so, delete this exception statement from your
+# version. If you delete this exception statement from all source files
+# in the program, then also delete it here.
+# 
+# This program is distributed in the hope that it will be useful, but
+# WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+# General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see <http://www.gnu.org/licenses/>.
+
+
+import json
+import os
+import pystache
+
+ORTHANC_ROOT = '/home/jodogne/Subversion/orthanc/'
+BASE = os.path.abspath(os.path.join(os.path.dirname(__file__), '..'))
+
+
+with open(os.path.join(ORTHANC_ROOT, 'Resources', 'DicomTransferSyntaxes.json'), 'r') as f:
+    SYNTAXES = json.loads(f.read())
+
+
+with open(os.path.join(BASE, 'Plugin', 'GdcmParsedDicomFile_TransferSyntaxes.impl.h'), 'w') as b:
+    with open(os.path.join(BASE, 'Resources', 'GenerateTransferSyntaxes.mustache'), 'r') as a:
+        b.write(pystache.render(a.read(), {
+            'Syntaxes' : SYNTAXES
+        }))
--- a/Status.txt	Mon May 25 13:01:52 2020 +0200
+++ b/Status.txt	Mon May 25 14:15:16 2020 +0200
@@ -1,5 +1,9 @@
 Reference: http://dicom.nema.org/MEDICAL/dicom/2019a/output/html/part18.html
 
+If you need some missing feature as an industrial player, please
+consider hiring the development team from Osimis by filling the
+dedicated form on the Orthanc Web site:
+https://www.orthanc-server.com/orthanc-pro.php
 
 
 =======================================
@@ -103,7 +107,6 @@
 * GIF output
 * The following "Retrieve Rendered Query Parameters" (table 6.5.8-2):
   annotation, charset, iccprofile
-* URI "/studies/.../rendered" (only available for series, instances and frames)
 
 
 
@@ -148,6 +151,22 @@
 
 
 
+===================
+6.8 RS Capabilities
+===================
+
+Not supported.
+
+
+
+===================
+6.9 UPS-RS Worklist
+===================
+
+Not supported.
+
+
+
 ==========================================================
 CP 1509 - Refactor media type description for web services
 ==========================================================