changeset 84:470aad460956 upgrade

upgrade
author Sebastien Jodogne <s.jodogne@gmail.com>
date Wed, 02 Dec 2015 15:00:59 +0100
parents 26e90f9b3dbf
children cd1c06f6f163
files Orthanc/Sdk-0.9.4/orthanc/OrthancCDatabasePlugin.h Orthanc/Sdk-0.9.4/orthanc/OrthancCPlugin.h Orthanc/Sdk-0.9.4/orthanc/OrthancCppDatabasePlugin.h Resources/SyncOrthancFolder.py
diffstat 4 files changed, 1694 insertions(+), 352 deletions(-) [+]
line wrap: on
line diff
--- a/Orthanc/Sdk-0.9.4/orthanc/OrthancCDatabasePlugin.h	Wed Dec 02 14:20:55 2015 +0100
+++ b/Orthanc/Sdk-0.9.4/orthanc/OrthancCDatabasePlugin.h	Wed Dec 02 15:00:59 2015 +0100
@@ -320,27 +320,27 @@
 
   typedef struct
   {
-    int32_t  (*addAttachment) (
+    OrthancPluginErrorCode  (*addAttachment) (
       /* inputs */
       void* payload,
       int64_t id,
       const OrthancPluginAttachment* attachment);
                              
-    int32_t  (*attachChild) (
+    OrthancPluginErrorCode  (*attachChild) (
       /* inputs */
       void* payload,
       int64_t parent,
       int64_t child);
                              
-    int32_t  (*clearChanges) (
+    OrthancPluginErrorCode  (*clearChanges) (
       /* inputs */
       void* payload);
                              
-    int32_t  (*clearExportedResources) (
+    OrthancPluginErrorCode  (*clearExportedResources) (
       /* inputs */
       void* payload);
 
-    int32_t  (*createResource) (
+    OrthancPluginErrorCode  (*createResource) (
       /* outputs */
       int64_t* id, 
       /* inputs */
@@ -348,25 +348,25 @@
       const char* publicId,
       OrthancPluginResourceType resourceType);           
                    
-    int32_t  (*deleteAttachment) (
+    OrthancPluginErrorCode  (*deleteAttachment) (
       /* inputs */
       void* payload,
       int64_t id,
       int32_t contentType);
    
-    int32_t  (*deleteMetadata) (
+    OrthancPluginErrorCode  (*deleteMetadata) (
       /* inputs */
       void* payload,
       int64_t id,
       int32_t metadataType);
    
-    int32_t  (*deleteResource) (
+    OrthancPluginErrorCode  (*deleteResource) (
       /* inputs */
       void* payload,
       int64_t id);    
 
     /* Output: Use OrthancPluginDatabaseAnswerString() */
-    int32_t  (*getAllPublicIds) (
+    OrthancPluginErrorCode  (*getAllPublicIds) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
@@ -375,7 +375,7 @@
 
     /* Output: Use OrthancPluginDatabaseAnswerChange() and
      * OrthancPluginDatabaseAnswerChangesDone() */
-    int32_t  (*getChanges) (
+    OrthancPluginErrorCode  (*getChanges) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
@@ -384,7 +384,7 @@
       uint32_t maxResult);
 
     /* Output: Use OrthancPluginDatabaseAnswerInt64() */
-    int32_t  (*getChildrenInternalId) (
+    OrthancPluginErrorCode  (*getChildrenInternalId) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
@@ -392,7 +392,7 @@
       int64_t id);
                    
     /* Output: Use OrthancPluginDatabaseAnswerString() */
-    int32_t  (*getChildrenPublicId) (
+    OrthancPluginErrorCode  (*getChildrenPublicId) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
@@ -401,7 +401,7 @@
 
     /* Output: Use OrthancPluginDatabaseAnswerExportedResource() and
      * OrthancPluginDatabaseAnswerExportedResourcesDone() */
-    int32_t  (*getExportedResources) (
+    OrthancPluginErrorCode  (*getExportedResources) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
@@ -410,21 +410,21 @@
       uint32_t  maxResult);
                    
     /* Output: Use OrthancPluginDatabaseAnswerChange() */
-    int32_t  (*getLastChange) (
+    OrthancPluginErrorCode  (*getLastChange) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
       void* payload);
 
     /* Output: Use OrthancPluginDatabaseAnswerExportedResource() */
-    int32_t  (*getLastExportedResource) (
+    OrthancPluginErrorCode  (*getLastExportedResource) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
       void* payload);
                    
     /* Output: Use OrthancPluginDatabaseAnswerDicomTag() */
-    int32_t  (*getMainDicomTags) (
+    OrthancPluginErrorCode  (*getMainDicomTags) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
@@ -432,47 +432,47 @@
       int64_t id);
                    
     /* Output: Use OrthancPluginDatabaseAnswerString() */
-    int32_t  (*getPublicId) (
+    OrthancPluginErrorCode  (*getPublicId) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
       void* payload,
       int64_t id);
 
-    int32_t  (*getResourceCount) (
+    OrthancPluginErrorCode  (*getResourceCount) (
       /* outputs */
       uint64_t* target,
       /* inputs */
       void* payload,
       OrthancPluginResourceType  resourceType);
                    
-    int32_t  (*getResourceType) (
+    OrthancPluginErrorCode  (*getResourceType) (
       /* outputs */
       OrthancPluginResourceType* resourceType,
       /* inputs */
       void* payload,
       int64_t id);
 
-    int32_t  (*getTotalCompressedSize) (
+    OrthancPluginErrorCode  (*getTotalCompressedSize) (
       /* outputs */
       uint64_t* target,
       /* inputs */
       void* payload);
                    
-    int32_t  (*getTotalUncompressedSize) (
+    OrthancPluginErrorCode  (*getTotalUncompressedSize) (
       /* outputs */
       uint64_t* target,
       /* inputs */
       void* payload);
                    
-    int32_t  (*isExistingResource) (
+    OrthancPluginErrorCode  (*isExistingResource) (
       /* outputs */
       int32_t* existing,
       /* inputs */
       void* payload,
       int64_t id);
 
-    int32_t  (*isProtectedPatient) (
+    OrthancPluginErrorCode  (*isProtectedPatient) (
       /* outputs */
       int32_t* isProtected,
       /* inputs */
@@ -480,7 +480,7 @@
       int64_t id);
 
     /* Output: Use OrthancPluginDatabaseAnswerInt32() */
-    int32_t  (*listAvailableMetadata) (
+    OrthancPluginErrorCode  (*listAvailableMetadata) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
@@ -488,25 +488,25 @@
       int64_t id);
                    
     /* Output: Use OrthancPluginDatabaseAnswerInt32() */
-    int32_t  (*listAvailableAttachments) (
+    OrthancPluginErrorCode  (*listAvailableAttachments) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
       void* payload,
       int64_t id);
 
-    int32_t  (*logChange) (
+    OrthancPluginErrorCode  (*logChange) (
       /* inputs */
       void* payload,
       const OrthancPluginChange* change);
                    
-    int32_t  (*logExportedResource) (
+    OrthancPluginErrorCode  (*logExportedResource) (
       /* inputs */
       void* payload,
       const OrthancPluginExportedResource* exported);
                    
     /* Output: Use OrthancPluginDatabaseAnswerAttachment() */
-    int32_t  (*lookupAttachment) (
+    OrthancPluginErrorCode  (*lookupAttachment) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
@@ -515,23 +515,26 @@
       int32_t contentType);
 
     /* Output: Use OrthancPluginDatabaseAnswerString() */
-    int32_t  (*lookupGlobalProperty) (
+    OrthancPluginErrorCode  (*lookupGlobalProperty) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
       void* payload,
       int32_t property);
 
-    /* Output: Use OrthancPluginDatabaseAnswerInt64() */
-    int32_t  (*lookupIdentifier) (
+    /* Use "OrthancPluginDatabaseExtensions::lookupIdentifier3" 
+       instead of this function as of Orthanc 0.9.5 (db v6), can be set to NULL.
+       Output: Use OrthancPluginDatabaseAnswerInt64() */
+    OrthancPluginErrorCode  (*lookupIdentifier) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
       void* payload,
       const OrthancPluginDicomTag* tag);
 
-    /* Output: Use OrthancPluginDatabaseAnswerInt64() */
-    int32_t  (*lookupIdentifier2) (
+    /* Unused starting with Orthanc 0.9.5 (db v6), can be set to NULL.
+       Output: Use OrthancPluginDatabaseAnswerInt64() */
+    OrthancPluginErrorCode  (*lookupIdentifier2) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
@@ -539,7 +542,7 @@
       const char* value);
 
     /* Output: Use OrthancPluginDatabaseAnswerString() */
-    int32_t  (*lookupMetadata) (
+    OrthancPluginErrorCode  (*lookupMetadata) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
@@ -548,7 +551,7 @@
       int32_t metadata);
 
     /* Output: Use OrthancPluginDatabaseAnswerInt64() */
-    int32_t  (*lookupParent) (
+    OrthancPluginErrorCode  (*lookupParent) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
@@ -556,7 +559,7 @@
       int64_t id);
 
     /* Output: Use OrthancPluginDatabaseAnswerResource() */
-    int32_t  (*lookupResource) (
+    OrthancPluginErrorCode  (*lookupResource) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
@@ -564,68 +567,68 @@
       const char* publicId);
 
     /* Output: Use OrthancPluginDatabaseAnswerInt64() */
-    int32_t  (*selectPatientToRecycle) (
+    OrthancPluginErrorCode  (*selectPatientToRecycle) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
       void* payload);
 
     /* Output: Use OrthancPluginDatabaseAnswerInt64() */
-    int32_t  (*selectPatientToRecycle2) (
+    OrthancPluginErrorCode  (*selectPatientToRecycle2) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
       void* payload,
       int64_t patientIdToAvoid);
 
-    int32_t  (*setGlobalProperty) (
+    OrthancPluginErrorCode  (*setGlobalProperty) (
       /* inputs */
       void* payload,
       int32_t property,
       const char* value);
 
-    int32_t  (*setMainDicomTag) (
+    OrthancPluginErrorCode  (*setMainDicomTag) (
       /* inputs */
       void* payload,
       int64_t id,
       const OrthancPluginDicomTag* tag);
 
-    int32_t  (*setIdentifierTag) (
+    OrthancPluginErrorCode  (*setIdentifierTag) (
       /* inputs */
       void* payload,
       int64_t id,
       const OrthancPluginDicomTag* tag);
 
-    int32_t  (*setMetadata) (
+    OrthancPluginErrorCode  (*setMetadata) (
       /* inputs */
       void* payload,
       int64_t id,
       int32_t metadata,
       const char* value);
 
-    int32_t  (*setProtectedPatient) (
+    OrthancPluginErrorCode  (*setProtectedPatient) (
       /* inputs */
       void* payload,
       int64_t id,
       int32_t isProtected);
 
-    int32_t (*startTransaction) (
+    OrthancPluginErrorCode  (*startTransaction) (
       /* inputs */
       void* payload);
 
-    int32_t (*rollbackTransaction) (
+    OrthancPluginErrorCode  (*rollbackTransaction) (
       /* inputs */
       void* payload);
 
-    int32_t (*commitTransaction) (
+    OrthancPluginErrorCode  (*commitTransaction) (
       /* inputs */
       void* payload);
 
-    int32_t (*open) (
+    OrthancPluginErrorCode  (*open) (
       /* inputs */
       void* payload);
 
-    int32_t (*close) (
+    OrthancPluginErrorCode  (*close) (
       /* inputs */
       void* payload);
 
@@ -635,7 +638,7 @@
   typedef struct
   {
     /* Output: Use OrthancPluginDatabaseAnswerString() */
-    int32_t  (*getAllPublicIdsWithLimit) (
+    OrthancPluginErrorCode  (*getAllPublicIdsWithLimit) (
       /* outputs */
       OrthancPluginDatabaseContext* context,
       /* inputs */
@@ -644,18 +647,41 @@
       uint64_t since,
       uint64_t limit);
 
-    int32_t  (*getDatabaseVersion) (
+    OrthancPluginErrorCode  (*getDatabaseVersion) (
       /* outputs */
       uint32_t* version,
       /* inputs */
       void* payload);
 
-    int32_t  (*upgradeDatabase) (
+    OrthancPluginErrorCode  (*upgradeDatabase) (
       /* inputs */
       void* payload,
       uint32_t targetVersion,
       OrthancPluginStorageArea* storageArea);
-  } OrthancPluginDatabaseExtensions;
+ 
+    OrthancPluginErrorCode  (*clearMainDicomTags) (
+      /* inputs */
+      void* payload,
+      int64_t id);
+
+    /* Output: Use OrthancPluginDatabaseAnswerInt64() */
+    OrthancPluginErrorCode  (*getAllInternalIds) (
+      /* outputs */
+      OrthancPluginDatabaseContext* context,
+      /* inputs */
+      void* payload,
+      OrthancPluginResourceType resourceType);
+
+    /* Output: Use OrthancPluginDatabaseAnswerInt64() */
+    OrthancPluginErrorCode  (*lookupIdentifier3) (
+      /* outputs */
+      OrthancPluginDatabaseContext* context,
+      /* inputs */
+      void* payload,
+      OrthancPluginResourceType resourceType,
+      const OrthancPluginDicomTag* tag,
+      OrthancPluginIdentifierConstraint constraint);
+   } OrthancPluginDatabaseExtensions;
 
 /*<! @endcond */
 
--- a/Orthanc/Sdk-0.9.4/orthanc/OrthancCPlugin.h	Wed Dec 02 14:20:55 2015 +0100
+++ b/Orthanc/Sdk-0.9.4/orthanc/OrthancCPlugin.h	Wed Dec 02 15:00:59 2015 +0100
@@ -18,6 +18,8 @@
  *    - Possibly register its callback for changes to the DICOM store using ::OrthancPluginRegisterOnChangeCallback().
  *    - Possibly register a custom storage area using ::OrthancPluginRegisterStorageArea().
  *    - Possibly register a custom database back-end area using OrthancPluginRegisterDatabaseBackendV2().
+ *    - Possibly register a handler for C-Find SCP against DICOM worklists using OrthancPluginRegisterWorklistCallback().
+ *    - Possibly register a custom decoder for DICOM images using OrthancPluginRegisterDecodeImageCallback().
  * -# <tt>void OrthancPluginFinalize()</tt>:
  *    This function is invoked by Orthanc during its shutdown. The plugin
  *    must free all its memory.
@@ -49,6 +51,9 @@
  * @defgroup Callbacks Callbacks
  * @brief Functions to register and manage callbacks by the plugins.
  *
+ * @defgroup Worklists Worklists
+ * @brief Functions to register and manage worklists.
+ *
  * @defgroup Orthanc Orthanc
  * @brief Functions to access the content of the Orthanc server.
  **/
@@ -109,7 +114,7 @@
 
 #define ORTHANC_PLUGINS_MINIMAL_MAJOR_NUMBER     0
 #define ORTHANC_PLUGINS_MINIMAL_MINOR_NUMBER     9
-#define ORTHANC_PLUGINS_MINIMAL_REVISION_NUMBER  4
+#define ORTHANC_PLUGINS_MINIMAL_REVISION_NUMBER  5
 
 
 
@@ -210,6 +215,10 @@
     OrthancPluginErrorCode_BadJson = 28    /*!< Cannot parse a JSON document */,
     OrthancPluginErrorCode_Unauthorized = 29    /*!< Bad credentials were provided to an HTTP request */,
     OrthancPluginErrorCode_BadFont = 30    /*!< Badly formatted font file */,
+    OrthancPluginErrorCode_DatabasePlugin = 31    /*!< The plugin implementing a custom database back-end does not fulfill the proper interface */,
+    OrthancPluginErrorCode_StorageAreaPlugin = 32    /*!< Error in the plugin implementing a custom storage area */,
+    OrthancPluginErrorCode_EmptyRequest = 33    /*!< The request is empty */,
+    OrthancPluginErrorCode_NotAcceptable = 34    /*!< Cannot send a response which is acceptable according to the Accept HTTP header */,
     OrthancPluginErrorCode_SQLiteNotOpened = 1000    /*!< SQLite: The database is not opened */,
     OrthancPluginErrorCode_SQLiteAlreadyOpened = 1001    /*!< SQLite: Connection is already open */,
     OrthancPluginErrorCode_SQLiteCannotOpen = 1002    /*!< SQLite: Unable to open the database */,
@@ -262,6 +271,12 @@
     OrthancPluginErrorCode_LuaBadOutput = 2033    /*!< The Lua function does not give the expected number of outputs */,
     OrthancPluginErrorCode_NotLuaPredicate = 2034    /*!< The Lua function is not a predicate (only true/false outputs allowed) */,
     OrthancPluginErrorCode_LuaReturnsNoString = 2035    /*!< The Lua function does not return a string */,
+    OrthancPluginErrorCode_StorageAreaAlreadyRegistered = 2036    /*!< Another plugin has already registered a custom storage area */,
+    OrthancPluginErrorCode_DatabaseBackendAlreadyRegistered = 2037    /*!< Another plugin has already registered a custom database back-end */,
+    OrthancPluginErrorCode_DatabaseNotInitialized = 2038    /*!< Plugin trying to call the database during its initialization */,
+    OrthancPluginErrorCode_SslDisabled = 2039    /*!< Orthanc has been built without SSL support */,
+    OrthancPluginErrorCode_CannotOrderSlices = 2040    /*!< Unable to order the slices of the series */,
+    OrthancPluginErrorCode_NoWorklistHandler = 2041    /*!< No request handler factory for DICOM C-Find Modality SCP */,
 
     _OrthancPluginErrorCode_INTERNAL = 0x7fffffff
   } OrthancPluginErrorCode;
@@ -378,6 +393,14 @@
     _OrthancPluginService_WriteFile = 16,
     _OrthancPluginService_GetErrorDescription = 17,
     _OrthancPluginService_CallHttpClient = 18,
+    _OrthancPluginService_RegisterErrorCode = 19,
+    _OrthancPluginService_RegisterDictionaryTag = 20,
+    _OrthancPluginService_DicomBufferToJson = 21,
+    _OrthancPluginService_DicomInstanceToJson = 22,
+    _OrthancPluginService_CreateDicom = 23,
+    _OrthancPluginService_ComputeMd5 = 24,
+    _OrthancPluginService_ComputeSha1 = 25,
+    _OrthancPluginService_LookupDictionary = 26,
 
     /* Registration of callbacks */
     _OrthancPluginService_RegisterRestCallback = 1000,
@@ -385,6 +408,8 @@
     _OrthancPluginService_RegisterStorageArea = 1002,
     _OrthancPluginService_RegisterOnChangeCallback = 1003,
     _OrthancPluginService_RegisterRestCallbackNoLock = 1004,
+    _OrthancPluginService_RegisterWorklistCallback = 1005,
+    _OrthancPluginService_RegisterDecodeImageCallback = 1006,
 
     /* Sending answers to REST calls */
     _OrthancPluginService_AnswerBuffer = 2000,
@@ -415,6 +440,8 @@
     _OrthancPluginService_RestApiPostAfterPlugins = 3011,
     _OrthancPluginService_RestApiDeleteAfterPlugins = 3012,
     _OrthancPluginService_RestApiPutAfterPlugins = 3013,
+    _OrthancPluginService_ReconstructMainDicomTags = 3014,
+    _OrthancPluginService_RestApiGet2 = 3015,
 
     /* Access to DICOM instances */
     _OrthancPluginService_GetInstanceRemoteAet = 4000,
@@ -424,6 +451,7 @@
     _OrthancPluginService_GetInstanceSimplifiedJson = 4004,
     _OrthancPluginService_HasInstanceMetadata = 4005,
     _OrthancPluginService_GetInstanceMetadata = 4006,
+    _OrthancPluginService_GetInstanceOrigin = 4007,
 
     /* Services for plugins implementing a database back-end */
     _OrthancPluginService_RegisterDatabaseBackend = 5000,
@@ -446,6 +474,15 @@
     _OrthancPluginService_GetFontsCount = 6009,
     _OrthancPluginService_GetFontInfo = 6010,
     _OrthancPluginService_DrawText = 6011,
+    _OrthancPluginService_CreateImage = 6012,
+    _OrthancPluginService_CreateImageAccessor = 6013,
+    _OrthancPluginService_DecodeDicomImage = 6014,
+
+    /* Primitives for handling worklists */
+    _OrthancPluginService_WorklistAddAnswer = 7000,
+    _OrthancPluginService_WorklistMarkIncomplete = 7001,
+    _OrthancPluginService_WorklistIsMatch = 7002,
+    _OrthancPluginService_WorklistGetDicomQuery = 7003,
 
     _OrthancPluginService_INTERNAL = 0x7fffffff
   } _OrthancPluginService;
@@ -538,6 +575,7 @@
     OrthancPluginResourceType_Study = 1,       /*!< Study */
     OrthancPluginResourceType_Series = 2,      /*!< Series */
     OrthancPluginResourceType_Instance = 3,    /*!< Instance */
+    OrthancPluginResourceType_None = 4,        /*!< Unavailable resource type */
 
     _OrthancPluginResourceType_INTERNAL = 0x7fffffff
   } OrthancPluginResourceType;
@@ -560,6 +598,10 @@
     OrthancPluginChangeType_StablePatient = 7,      /*!< Timeout: No new instance in this patient */
     OrthancPluginChangeType_StableSeries = 8,       /*!< Timeout: No new instance in this series */
     OrthancPluginChangeType_StableStudy = 9,        /*!< Timeout: No new instance in this study */
+    OrthancPluginChangeType_OrthancStarted = 10,    /*!< Orthanc has started */
+    OrthancPluginChangeType_OrthancStopped = 11,    /*!< Orthanc is stopping */
+    OrthancPluginChangeType_UpdatedAttachment = 12, /*!< Some user-defined attachment has changed for this resource */
+    OrthancPluginChangeType_UpdatedMetadata = 13,   /*!< Some user-defined metadata has changed for this resource */
 
     _OrthancPluginChangeType_INTERNAL = 0x7fffffff
   } OrthancPluginChangeType;
@@ -586,13 +628,128 @@
    **/
   typedef enum
   {
-    OrthancPluginImageFormat_Png = 0,   /*!< Image compressed using PNG */
-    OrthancPluginImageFormat_Jpeg = 1,  /*!< Image compressed using JPEG */
+    OrthancPluginImageFormat_Png = 0,    /*!< Image compressed using PNG */
+    OrthancPluginImageFormat_Jpeg = 1,   /*!< Image compressed using JPEG */
+    OrthancPluginImageFormat_Dicom = 2,  /*!< Image compressed using DICOM */
 
     _OrthancPluginImageFormat_INTERNAL = 0x7fffffff
   } OrthancPluginImageFormat;
 
 
+  /**
+   * The value representations present in the DICOM standard (version 2013).
+   * @ingroup Toolbox
+   **/
+  typedef enum
+  {
+    OrthancPluginValueRepresentation_AE = 1,   /*!< Application Entity */
+    OrthancPluginValueRepresentation_AS = 2,   /*!< Age String */
+    OrthancPluginValueRepresentation_AT = 3,   /*!< Attribute Tag */
+    OrthancPluginValueRepresentation_CS = 4,   /*!< Code String */
+    OrthancPluginValueRepresentation_DA = 5,   /*!< Date */
+    OrthancPluginValueRepresentation_DS = 6,   /*!< Decimal String */
+    OrthancPluginValueRepresentation_DT = 7,   /*!< Date Time */
+    OrthancPluginValueRepresentation_FD = 8,   /*!< Floating Point Double */
+    OrthancPluginValueRepresentation_FL = 9,   /*!< Floating Point Single */
+    OrthancPluginValueRepresentation_IS = 10,  /*!< Integer String */
+    OrthancPluginValueRepresentation_LO = 11,  /*!< Long String */
+    OrthancPluginValueRepresentation_LT = 12,  /*!< Long Text */
+    OrthancPluginValueRepresentation_OB = 13,  /*!< Other Byte String */
+    OrthancPluginValueRepresentation_OF = 14,  /*!< Other Float String */
+    OrthancPluginValueRepresentation_OW = 15,  /*!< Other Word String */
+    OrthancPluginValueRepresentation_PN = 16,  /*!< Person Name */
+    OrthancPluginValueRepresentation_SH = 17,  /*!< Short String */
+    OrthancPluginValueRepresentation_SL = 18,  /*!< Signed Long */
+    OrthancPluginValueRepresentation_SQ = 19,  /*!< Sequence of Items */
+    OrthancPluginValueRepresentation_SS = 20,  /*!< Signed Short */
+    OrthancPluginValueRepresentation_ST = 21,  /*!< Short Text */
+    OrthancPluginValueRepresentation_TM = 22,  /*!< Time */
+    OrthancPluginValueRepresentation_UI = 23,  /*!< Unique Identifier (UID) */
+    OrthancPluginValueRepresentation_UL = 24,  /*!< Unsigned Long */
+    OrthancPluginValueRepresentation_UN = 25,  /*!< Unknown */
+    OrthancPluginValueRepresentation_US = 26,  /*!< Unsigned Short */
+    OrthancPluginValueRepresentation_UT = 27,  /*!< Unlimited Text */
+
+    _OrthancPluginValueRepresentation_INTERNAL = 0x7fffffff
+  } OrthancPluginValueRepresentation;
+
+
+  /**
+   * The possible output formats for a DICOM-to-JSON conversion.
+   * @ingroup Toolbox
+   * @see OrthancPluginDicomToJson()
+   **/
+  typedef enum
+  {
+    OrthancPluginDicomToJsonFormat_Full = 1,    /*!< Full output, with most details */
+    OrthancPluginDicomToJsonFormat_Short = 2,   /*!< Tags output as hexadecimal numbers */
+    OrthancPluginDicomToJsonFormat_Human = 3,   /*!< Human-readable JSON */
+
+    _OrthancPluginDicomToJsonFormat_INTERNAL = 0x7fffffff
+  } OrthancPluginDicomToJsonFormat;
+
+
+  /**
+   * Flags to customize a DICOM-to-JSON conversion. By default, binary
+   * tags are formatted using Data URI scheme.
+   * @ingroup Toolbox
+   **/
+  typedef enum
+  {
+    OrthancPluginDicomToJsonFlags_IncludeBinary         = (1 << 0),  /*!< Include the binary tags */
+    OrthancPluginDicomToJsonFlags_IncludePrivateTags    = (1 << 1),  /*!< Include the private tags */
+    OrthancPluginDicomToJsonFlags_IncludeUnknownTags    = (1 << 2),  /*!< Include the tags unknown by the dictionary */
+    OrthancPluginDicomToJsonFlags_IncludePixelData      = (1 << 3),  /*!< Include the pixel data */
+    OrthancPluginDicomToJsonFlags_ConvertBinaryToAscii  = (1 << 4),  /*!< Output binary tags as-is, dropping non-ASCII */
+    OrthancPluginDicomToJsonFlags_ConvertBinaryToNull   = (1 << 5),  /*!< Signal binary tags as null values */
+
+    _OrthancPluginDicomToJsonFlags_INTERNAL = 0x7fffffff
+  } OrthancPluginDicomToJsonFlags;
+
+
+  /**
+   * Flags to the creation of a DICOM file.
+   * @ingroup Toolbox
+   * @see OrthancPluginCreateDicom()
+   **/
+  typedef enum
+  {
+    OrthancPluginCreateDicomFlags_DecodeDataUriScheme   = (1 << 0),  /*!< Decode fields encoded using data URI scheme */
+    OrthancPluginCreateDicomFlags_GenerateIdentifiers   = (1 << 1),  /*!< Automatically generate DICOM identifiers */
+
+    _OrthancPluginCreateDicomFlags_INTERNAL = 0x7fffffff
+  } OrthancPluginCreateDicomFlags;
+
+
+  /**
+   * The constraints on the DICOM identifiers that must be supported
+   * by the database plugins.
+   **/
+  typedef enum
+  {
+    OrthancPluginIdentifierConstraint_Equal = 1,           /*!< Equal */
+    OrthancPluginIdentifierConstraint_SmallerOrEqual = 2,  /*!< Less or equal */
+    OrthancPluginIdentifierConstraint_GreaterOrEqual = 3,  /*!< More or equal */
+    OrthancPluginIdentifierConstraint_Wildcard = 4,        /*!< Case-sensitive wildcard matching (with * and ?) */
+
+    _OrthancPluginIdentifierConstraint_INTERNAL = 0x7fffffff
+  } OrthancPluginIdentifierConstraint;
+
+
+  /**
+   * The origin of a DICOM instance that has been received by Orthanc.
+   **/
+  typedef enum
+  {
+    OrthancPluginInstanceOrigin_Unknown = 1,        /*!< Unknown origin */
+    OrthancPluginInstanceOrigin_DicomProtocol = 2,  /*!< Instance received through DICOM protocol */
+    OrthancPluginInstanceOrigin_RestApi = 3,        /*!< Instance received through REST API of Orthanc */
+    OrthancPluginInstanceOrigin_Plugin = 4,         /*!< Instance added to Orthanc by a plugin */
+    OrthancPluginInstanceOrigin_Lua = 5,            /*!< Instance added to Orthanc by a Lua script */
+
+    _OrthancPluginInstanceOrigin_INTERNAL = 0x7fffffff
+  } OrthancPluginInstanceOrigin;
+
 
   /**
    * @brief A memory buffer allocated by the core system of Orthanc.
@@ -649,10 +806,26 @@
 
 
   /**
+   * @brief Opaque structure to an object that represents a C-Find query.
+   * @ingroup Worklists
+   **/
+  typedef struct _OrthancPluginWorklistQuery_t OrthancPluginWorklistQuery;
+
+
+
+  /**
+   * @brief Opaque structure to an object that represents the answers to a C-Find query.
+   * @ingroup Worklists
+   **/
+  typedef struct _OrthancPluginWorklistAnswers_t OrthancPluginWorklistAnswers;
+
+
+
+  /**
    * @brief Signature of a callback function that answers to a REST request.
    * @ingroup Callbacks
    **/
-  typedef int32_t (*OrthancPluginRestCallback) (
+  typedef OrthancPluginErrorCode (*OrthancPluginRestCallback) (
     OrthancPluginRestOutput* output,
     const char* url,
     const OrthancPluginHttpRequest* request);
@@ -663,7 +836,7 @@
    * @brief Signature of a callback function that is triggered when Orthanc receives a DICOM instance.
    * @ingroup Callbacks
    **/
-  typedef int32_t (*OrthancPluginOnStoredInstanceCallback) (
+  typedef OrthancPluginErrorCode (*OrthancPluginOnStoredInstanceCallback) (
     OrthancPluginDicomInstance* instance,
     const char* instanceId);
 
@@ -673,7 +846,7 @@
    * @brief Signature of a callback function that is triggered when a change happens to some DICOM resource.
    * @ingroup Callbacks
    **/
-  typedef int32_t (*OrthancPluginOnChangeCallback) (
+  typedef OrthancPluginErrorCode (*OrthancPluginOnChangeCallback) (
     OrthancPluginChangeType changeType,
     OrthancPluginResourceType resourceType,
     const char* resourceId);
@@ -681,6 +854,18 @@
 
 
   /**
+   * @brief Signature of a callback function to decode a DICOM instance as an image.
+   * @ingroup Callbacks
+   **/
+  typedef OrthancPluginErrorCode (*OrthancPluginDecodeImageCallback) (
+    OrthancPluginImage** target,
+    const void* dicom,
+    const uint32_t size,
+    uint32_t frameIndex);
+
+
+
+  /**
    * @brief Signature of a function to free dynamic memory.
    **/
   typedef void (*OrthancPluginFree) (void* buffer);
@@ -699,7 +884,7 @@
    * @return 0 if success, other value if error.
    * @ingroup Callbacks
    **/
-  typedef int32_t (*OrthancPluginStorageCreate) (
+  typedef OrthancPluginErrorCode (*OrthancPluginStorageCreate) (
     const char* uuid,
     const void* content,
     int64_t size,
@@ -719,7 +904,7 @@
    * @return 0 if success, other value if error.
    * @ingroup Callbacks
    **/
-  typedef int32_t (*OrthancPluginStorageRead) (
+  typedef OrthancPluginErrorCode (*OrthancPluginStorageRead) (
     void** content,
     int64_t* size,
     const char* uuid,
@@ -737,13 +922,34 @@
    * @return 0 if success, other value if error.
    * @ingroup Callbacks
    **/
-  typedef int32_t (*OrthancPluginStorageRemove) (
+  typedef OrthancPluginErrorCode (*OrthancPluginStorageRemove) (
     const char* uuid,
     OrthancPluginContentType type);
 
 
 
   /**
+   * @brief Callback to handle the C-Find SCP requests received by Orthanc.
+   *
+   * Signature of a callback function that is triggered when Orthanc
+   * receives a C-Find SCP request against modality worklists.
+   *
+   * @param answers The target structure where answers must be stored.
+   * @param query The worklist query.
+   * @param remoteAet The Application Entity Title (AET) of the modality from which the request originates.
+   * @param calledAet The Application Entity Title (AET) of the modality that is called by the request.
+   * @return 0 if success, other value if error.
+   * @ingroup Worklists
+   **/
+  typedef OrthancPluginErrorCode (*OrthancPluginWorklistCallback) (
+    OrthancPluginWorklistAnswers*     answers,
+    const OrthancPluginWorklistQuery* query,
+    const char*                       remoteAet,
+    const char*                       calledAet);
+
+
+
+  /**
    * @brief Data structure that contains information about the Orthanc core.
    **/
   typedef struct _OrthancPluginContext_t
@@ -757,6 +963,20 @@
   } OrthancPluginContext;
 
 
+  
+  /**
+   * @brief An entry in the dictionary of DICOM tags.
+   **/
+  typedef struct
+  {
+    uint16_t                          group;            /*!< The group of the tag */
+    uint16_t                          element;          /*!< The element of the tag */
+    OrthancPluginValueRepresentation  vr;               /*!< The value representation of the tag */
+    uint32_t                          minMultiplicity;  /*!< The minimum multiplicity of the tag */
+    uint32_t                          maxMultiplicity;  /*!< The maximum multiplicity of the tag (0 means arbitrary) */
+  } OrthancPluginDictionaryEntry;
+
+
 
   /**
    * @brief Free a string.
@@ -804,7 +1024,13 @@
         sizeof(int32_t) != sizeof(OrthancPluginResourceType) ||
         sizeof(int32_t) != sizeof(OrthancPluginChangeType) ||
         sizeof(int32_t) != sizeof(OrthancPluginCompressionType) ||
-        sizeof(int32_t) != sizeof(OrthancPluginImageFormat))
+        sizeof(int32_t) != sizeof(OrthancPluginImageFormat) ||
+        sizeof(int32_t) != sizeof(OrthancPluginValueRepresentation) ||
+        sizeof(int32_t) != sizeof(OrthancPluginDicomToJsonFormat) ||
+        sizeof(int32_t) != sizeof(OrthancPluginDicomToJsonFlags) ||
+        sizeof(int32_t) != sizeof(OrthancPluginCreateDicomFlags) ||
+        sizeof(int32_t) != sizeof(OrthancPluginIdentifierConstraint) ||
+        sizeof(int32_t) != sizeof(OrthancPluginInstanceOrigin))
     {
       /* Mismatch in the size of the enumerations */
       return 0;
@@ -1139,7 +1365,7 @@
    * file is stored into a newly allocated memory buffer.
    * 
    * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
-   * @param target The target memory buffer.
+   * @param target The target memory buffer. It must be freed with OrthancPluginFreeMemoryBuffer().
    * @param instanceId The Orthanc identifier of the DICOM instance of interest.
    * @return 0 if success, or the error code if failure.
    * @ingroup Orthanc
@@ -1170,7 +1396,7 @@
    * the query is stored into a newly allocated memory buffer.
    * 
    * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
-   * @param target The target memory buffer.
+   * @param target The target memory buffer. It must be freed with OrthancPluginFreeMemoryBuffer().
    * @param uri The URI in the built-in Orthanc API.
    * @return 0 if success, or the error code if failure.
    * @see OrthancPluginRestApiGetAfterPlugins
@@ -1199,7 +1425,7 @@
    * query is stored into a newly allocated memory buffer.
    * 
    * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
-   * @param target The target memory buffer.
+   * @param target The target memory buffer. It must be freed with OrthancPluginFreeMemoryBuffer().
    * @param uri The URI in the built-in Orthanc API.
    * @return 0 if success, or the error code if failure.
    * @see OrthancPluginRestApiGet
@@ -1233,7 +1459,7 @@
    * the query is stored into a newly allocated memory buffer.
    * 
    * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
-   * @param target The target memory buffer.
+   * @param target The target memory buffer. It must be freed with OrthancPluginFreeMemoryBuffer().
    * @param uri The URI in the built-in Orthanc API.
    * @param body The body of the POST request.
    * @param bodySize The size of the body.
@@ -1267,7 +1493,7 @@
    * query is stored into a newly allocated memory buffer.
    * 
    * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
-   * @param target The target memory buffer.
+   * @param target The target memory buffer. It must be freed with OrthancPluginFreeMemoryBuffer().
    * @param uri The URI in the built-in Orthanc API.
    * @param body The body of the POST request.
    * @param bodySize The size of the body.
@@ -1341,7 +1567,7 @@
    * the query is stored into a newly allocated memory buffer.
    * 
    * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
-   * @param target The target memory buffer.
+   * @param target The target memory buffer. It must be freed with OrthancPluginFreeMemoryBuffer().
    * @param uri The URI in the built-in Orthanc API.
    * @param body The body of the PUT request.
    * @param bodySize The size of the body.
@@ -1376,7 +1602,7 @@
    * query is stored into a newly allocated memory buffer.
    * 
    * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
-   * @param target The target memory buffer.
+   * @param target The target memory buffer. It must be freed with OrthancPluginFreeMemoryBuffer().
    * @param uri The URI in the built-in Orthanc API.
    * @param body The body of the PUT request.
    * @param bodySize The size of the body.
@@ -1752,11 +1978,12 @@
 
   typedef struct
   {
-    char**                      resultStringToFree;
-    const char**                resultString;
-    int64_t*                    resultInt64;
-    const char*                 key;
-    OrthancPluginDicomInstance* instance;
+    char**                       resultStringToFree;
+    const char**                 resultString;
+    int64_t*                     resultInt64;
+    const char*                  key;
+    OrthancPluginDicomInstance*  instance;
+    OrthancPluginInstanceOrigin* resultOrigin;   /* New in Orthanc 0.9.5 SDK */
   } _OrthancPluginAccessDicomInstance;
 
 
@@ -2164,6 +2391,12 @@
    *
    * This function registers a callback function that is called
    * whenever a change happens to some DICOM resource.
+   *
+   * @warning If your change callback has to call the REST API of
+   * Orthanc, you should make these calls in a separate thread (with
+   * the events passing through a message queue). Otherwise, this
+   * could result in deadlocks in the presence of other plugins or Lua
+   * script.
    * 
    * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
    * @param callback The callback function.
@@ -2550,7 +2783,7 @@
    * version of the zlib library that is used by the Orthanc core.
    * 
    * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
-   * @param target The target memory buffer.
+   * @param target The target memory buffer. It must be freed with OrthancPluginFreeMemoryBuffer().
    * @param source The source buffer.
    * @param size The size in bytes of the source buffer.
    * @param compression The compression algorithm.
@@ -2592,7 +2825,7 @@
    * a newly allocated memory buffer.
    * 
    * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
-   * @param target The target memory buffer.
+   * @param target The target memory buffer. It must be freed with OrthancPluginFreeMemoryBuffer().
    * @param path The path of the file to be read.
    * @return 0 if success, or the error code if failure.
    **/
@@ -2733,7 +2966,7 @@
     const OrthancPluginImage*  image;
     uint32_t*                  resultUint32;
     OrthancPluginPixelFormat*  resultPixelFormat;
-    const void**               resultBuffer;
+    void**                     resultBuffer;
   } _OrthancPluginGetImageInfo;
 
 
@@ -2882,11 +3115,11 @@
    * @return The pointer.
    * @ingroup Images
    **/
-  ORTHANC_PLUGIN_INLINE const void*  OrthancPluginGetImageBuffer(
+  ORTHANC_PLUGIN_INLINE void*  OrthancPluginGetImageBuffer(
     OrthancPluginContext*      context,
     const OrthancPluginImage*  image)
   {
-    const void* target = NULL;
+    void* target = NULL;
 
     _OrthancPluginGetImageInfo params;
     memset(&params, 0, sizeof(params));
@@ -3150,7 +3383,7 @@
    * Orthanc instance that hosts this plugin.
    * 
    * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
-   * @param target The target memory buffer.
+   * @param target The target memory buffer. It must be freed with OrthancPluginFreeMemoryBuffer().
    * @param url The URL of interest.
    * @param username The username (can be <tt>NULL</tt> if no password protection).
    * @param password The password (can be <tt>NULL</tt> if no password protection).
@@ -3185,7 +3418,7 @@
    * the Orthanc instance that hosts this plugin.
    * 
    * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
-   * @param target The target memory buffer.
+   * @param target The target memory buffer. It must be freed with OrthancPluginFreeMemoryBuffer().
    * @param url The URL of interest.
    * @param body The content of the body of the request.
    * @param bodySize The size of the body of the request.
@@ -3226,7 +3459,7 @@
    * Orthanc instance that hosts this plugin.
    * 
    * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
-   * @param target The target memory buffer.
+   * @param target The target memory buffer. It must be freed with OrthancPluginFreeMemoryBuffer().
    * @param url The URL of interest.
    * @param body The content of the body of the request.
    * @param bodySize The size of the body of the request.
@@ -3587,7 +3820,6 @@
     OrthancPluginContentType    type;
   } _OrthancPluginStorageAreaRemove;
 
-
   /**
    * @brief Remove a file from the storage area.
    *
@@ -3617,6 +3849,834 @@
 
 
 
+  typedef struct
+  {
+    OrthancPluginErrorCode*  target;
+    int32_t                  code;
+    uint16_t                 httpStatus;
+    const char*              message;
+  } _OrthancPluginRegisterErrorCode;
+  
+  /**
+   * @brief Declare a custom error code for this plugin.
+   *
+   * This function declares a custom error code that can be generated
+   * by this plugin. This declaration is used to enrich the body of
+   * the HTTP answer in the case of an error, and to set the proper
+   * HTTP status code.
+   *
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param code The error code that is internal to this plugin.
+   * @param httpStatus The HTTP status corresponding to this error.
+   * @param message The description of the error.
+   * @return The error code that has been assigned inside the Orthanc core.
+   * @ingroup Toolbox
+   **/
+  ORTHANC_PLUGIN_INLINE OrthancPluginErrorCode  OrthancPluginRegisterErrorCode(
+    OrthancPluginContext*    context,
+    int32_t                  code,
+    uint16_t                 httpStatus,
+    const char*              message)
+  {
+    OrthancPluginErrorCode target;
+
+    _OrthancPluginRegisterErrorCode params;
+    params.target = &target;
+    params.code = code;
+    params.httpStatus = httpStatus;
+    params.message = message;
+
+    if (context->InvokeService(context, _OrthancPluginService_RegisterErrorCode, &params) == OrthancPluginErrorCode_Success)
+    {
+      return target;
+    }
+    else
+    {
+      /* There was an error while assigned the error. Use a generic code. */
+      return OrthancPluginErrorCode_Plugin;
+    }
+  }
+
+
+
+  typedef struct
+  {
+    uint16_t                          group;
+    uint16_t                          element;
+    OrthancPluginValueRepresentation  vr;
+    const char*                       name;
+    uint32_t                          minMultiplicity;
+    uint32_t                          maxMultiplicity;
+  } _OrthancPluginRegisterDictionaryTag;
+  
+  /**
+   * @brief Register a new tag into the DICOM dictionary.
+   *
+   * This function declares a new tag in the dictionary of DICOM tags
+   * that are known to Orthanc. This function should be used in the
+   * OrthancPluginInitialize() callback.
+   *
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param group The group of the tag.
+   * @param element The element of the tag.
+   * @param vr The value representation of the tag.
+   * @param name The nickname of the tag.
+   * @param minMultiplicity The minimum multiplicity of the tag (must be above 0).
+   * @param maxMultiplicity The maximum multiplicity of the tag. A value of 0 means
+   * an arbitrary multiplicity ("<tt>n</tt>").
+   * @return 0 if success, other value if error.
+   * @ingroup Toolbox
+   **/
+  ORTHANC_PLUGIN_INLINE OrthancPluginErrorCode  OrthancPluginRegisterDictionaryTag(
+    OrthancPluginContext*             context,
+    uint16_t                          group,
+    uint16_t                          element,
+    OrthancPluginValueRepresentation  vr,
+    const char*                       name,
+    uint32_t                          minMultiplicity,
+    uint32_t                          maxMultiplicity)
+  {
+    _OrthancPluginRegisterDictionaryTag params;
+    params.group = group;
+    params.element = element;
+    params.vr = vr;
+    params.name = name;
+    params.minMultiplicity = minMultiplicity;
+    params.maxMultiplicity = maxMultiplicity;
+
+    return context->InvokeService(context, _OrthancPluginService_RegisterDictionaryTag, &params);
+  }
+
+
+
+
+  typedef struct
+  {
+    OrthancPluginStorageArea*  storageArea;
+    OrthancPluginResourceType  level;
+  } _OrthancPluginReconstructMainDicomTags;
+
+  /**
+   * @brief Reconstruct the main DICOM tags.
+   *
+   * This function requests the Orthanc core to reconstruct the main
+   * DICOM tags of all the resources of the given type. This function
+   * can only be used as a part of the upgrade of a custom database
+   * back-end
+   * (cf. OrthancPlugins::IDatabaseBackend::UpgradeDatabase). A
+   * database transaction will be automatically setup.
+   *
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param storageArea The storage area.
+   * @param level The type of the resources of interest.
+   * @return 0 if success, other value if error.
+   * @ingroup Callbacks
+   **/
+  ORTHANC_PLUGIN_INLINE OrthancPluginErrorCode  OrthancPluginReconstructMainDicomTags(
+    OrthancPluginContext*      context,
+    OrthancPluginStorageArea*  storageArea,
+    OrthancPluginResourceType  level)
+  {
+    _OrthancPluginReconstructMainDicomTags params;
+    params.level = level;
+    params.storageArea = storageArea;
+
+    return context->InvokeService(context, _OrthancPluginService_ReconstructMainDicomTags, &params);
+  }
+
+
+  typedef struct
+  {
+    char**                          result;
+    const char*                     instanceId;
+    const char*                     buffer;
+    uint32_t                        size;
+    OrthancPluginDicomToJsonFormat  format;
+    OrthancPluginDicomToJsonFlags   flags;
+    uint32_t                        maxStringLength;
+  } _OrthancPluginDicomToJson;
+
+
+  /**
+   * @brief Format a DICOM memory buffer as a JSON string.
+   *
+   * This function takes as input a memory buffer containing a DICOM
+   * file, and outputs a JSON string representing the tags of this
+   * DICOM file.
+   *
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param buffer The memory buffer containing the DICOM file.
+   * @param size The size of the memory buffer.
+   * @param format The output format.
+   * @param flags Flags governing the output.
+   * @param maxStringLength The maximum length of a field. Too long fields will
+   * be output as "null". The 0 value means no maximum length.
+   * @return The NULL value if the case of an error, or the JSON
+   * string. This string must be freed by OrthancPluginFreeString().
+   * @ingroup Toolbox
+   * @see OrthancPluginDicomInstanceToJson
+   **/
+  ORTHANC_PLUGIN_INLINE char* OrthancPluginDicomBufferToJson(
+    OrthancPluginContext*           context,
+    const char*                     buffer,
+    uint32_t                        size,
+    OrthancPluginDicomToJsonFormat  format,
+    OrthancPluginDicomToJsonFlags   flags, 
+    uint32_t                        maxStringLength)
+  {
+    char* result;
+
+    _OrthancPluginDicomToJson params;
+    memset(&params, 0, sizeof(params));
+    params.result = &result;
+    params.buffer = buffer;
+    params.size = size;
+    params.format = format;
+    params.flags = flags;
+    params.maxStringLength = maxStringLength;
+
+    if (context->InvokeService(context, _OrthancPluginService_DicomBufferToJson, &params) != OrthancPluginErrorCode_Success)
+    {
+      /* Error */
+      return NULL;
+    }
+    else
+    {
+      return result;
+    }
+  }
+
+
+  /**
+   * @brief Format a DICOM instance as a JSON string.
+   *
+   * This function formats a DICOM instance that is stored in Orthanc,
+   * and outputs a JSON string representing the tags of this DICOM
+   * instance.
+   *
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param instanceId The Orthanc identifier of the instance.
+   * @param format The output format.
+   * @param flags Flags governing the output.
+   * @param maxStringLength The maximum length of a field. Too long fields will
+   * be output as "null". The 0 value means no maximum length.
+   * @return The NULL value if the case of an error, or the JSON
+   * string. This string must be freed by OrthancPluginFreeString().
+   * @ingroup Toolbox
+   * @see OrthancPluginDicomInstanceToJson
+   **/
+  ORTHANC_PLUGIN_INLINE char* OrthancPluginDicomInstanceToJson(
+    OrthancPluginContext*           context,
+    const char*                     instanceId,
+    OrthancPluginDicomToJsonFormat  format,
+    OrthancPluginDicomToJsonFlags   flags, 
+    uint32_t                        maxStringLength)
+  {
+    char* result;
+
+    _OrthancPluginDicomToJson params;
+    memset(&params, 0, sizeof(params));
+    params.result = &result;
+    params.instanceId = instanceId;
+    params.format = format;
+    params.flags = flags;
+    params.maxStringLength = maxStringLength;
+
+    if (context->InvokeService(context, _OrthancPluginService_DicomInstanceToJson, &params) != OrthancPluginErrorCode_Success)
+    {
+      /* Error */
+      return NULL;
+    }
+    else
+    {
+      return result;
+    }
+  }
+
+
+  typedef struct
+  {
+    OrthancPluginMemoryBuffer*  target;
+    const char*                 uri;
+    uint32_t                    headersCount;
+    const char* const*          headersKeys;
+    const char* const*          headersValues;
+    int32_t                     afterPlugins;
+  } _OrthancPluginRestApiGet2;
+
+  /**
+   * @brief Make a GET call to the Orthanc REST API, with custom HTTP headers.
+   * 
+   * Make a GET call to the Orthanc REST API with extended
+   * parameters. The result to the query is stored into a newly
+   * allocated memory buffer.
+   * 
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param target The target memory buffer. It must be freed with OrthancPluginFreeMemoryBuffer().
+   * @param uri The URI in the built-in Orthanc API.
+   * @param headersCount The number of HTTP headers.
+   * @param headersKeys Array containing the keys of the HTTP headers.
+   * @param headersValues Array containing the values of the HTTP headers.
+   * @param afterPlugins If 0, the built-in API of Orthanc is used.
+   * If 1, the API is tainted by the plugins.
+   * @return 0 if success, or the error code if failure.
+   * @see OrthancPluginRestApiGet, OrthancPluginRestApiGetAfterPlugins
+   * @ingroup Orthanc
+   **/
+  ORTHANC_PLUGIN_INLINE OrthancPluginErrorCode  OrthancPluginRestApiGet2(
+    OrthancPluginContext*       context,
+    OrthancPluginMemoryBuffer*  target,
+    const char*                 uri,
+    uint32_t                    headersCount,
+    const char* const*          headersKeys,
+    const char* const*          headersValues,
+    int32_t                     afterPlugins)
+  {
+    _OrthancPluginRestApiGet2 params;
+    params.target = target;
+    params.uri = uri;
+    params.headersCount = headersCount;
+    params.headersKeys = headersKeys;
+    params.headersValues = headersValues;
+    params.afterPlugins = afterPlugins;
+
+    return context->InvokeService(context, _OrthancPluginService_RestApiGet2, &params);
+  }
+
+
+
+  typedef struct
+  {
+    OrthancPluginWorklistCallback callback;
+  } _OrthancPluginWorklistCallback;
+
+  /**
+   * @brief Register a callback to handle modality worklists requests.
+   *
+   * This function registers a callback to handle C-Find SCP requests
+   * on modality worklists.
+   *
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param callback The callback.
+   * @return 0 if success, other value if error.
+   * @ingroup Worklists
+   **/
+  ORTHANC_PLUGIN_INLINE OrthancPluginErrorCode OrthancPluginRegisterWorklistCallback(
+    OrthancPluginContext*          context,
+    OrthancPluginWorklistCallback  callback)
+  {
+    _OrthancPluginWorklistCallback params;
+    params.callback = callback;
+
+    return context->InvokeService(context, _OrthancPluginService_RegisterWorklistCallback, &params);
+  }
+
+
+  
+  typedef struct
+  {
+    OrthancPluginWorklistAnswers*      answers;
+    const OrthancPluginWorklistQuery*  query;
+    const void*                        dicom;
+    uint32_t                           size;
+  } _OrthancPluginWorklistAnswersOperation;
+
+  /**
+   * @brief Add one answer to some modality worklist request.
+   *
+   * This function adds one worklist (encoded as a DICOM file) to the
+   * set of answers corresponding to some C-Find SCP request against
+   * modality worklists.
+   *
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param answers The set of answers.
+   * @param query The worklist query, as received by the callback.
+   * @param dicom The worklist to answer, encoded as a DICOM file.
+   * @param size The size of the DICOM file.
+   * @return 0 if success, other value if error.
+   * @ingroup Worklists
+   **/
+  ORTHANC_PLUGIN_INLINE OrthancPluginErrorCode  OrthancPluginWorklistAddAnswer(
+    OrthancPluginContext*             context,
+    OrthancPluginWorklistAnswers*     answers,
+    const OrthancPluginWorklistQuery* query,
+    const void*                       dicom,
+    uint32_t                          size)
+  {
+    _OrthancPluginWorklistAnswersOperation params;
+    params.answers = answers;
+    params.query = query;
+    params.dicom = dicom;
+    params.size = size;
+
+    return context->InvokeService(context, _OrthancPluginService_WorklistAddAnswer, &params);
+  }
+
+
+  /**
+   * @brief Mark the set of worklist answers as incomplete.
+   *
+   * This function marks as incomplete the set of answers
+   * corresponding to some C-Find SCP request against modality
+   * worklists. This must be used if canceling the handling of a
+   * request when too many answers are to be returned.
+   *
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param answers The set of answers.
+   * @return 0 if success, other value if error.
+   * @ingroup Worklists
+   **/
+  ORTHANC_PLUGIN_INLINE OrthancPluginErrorCode  OrthancPluginWorklistMarkIncomplete(
+    OrthancPluginContext*          context,
+    OrthancPluginWorklistAnswers*  answers)
+  {
+    _OrthancPluginWorklistAnswersOperation params;
+    params.answers = answers;
+    params.query = NULL;
+    params.dicom = NULL;
+    params.size = 0;
+
+    return context->InvokeService(context, _OrthancPluginService_WorklistMarkIncomplete, &params);
+  }
+
+
+  typedef struct
+  {
+    const OrthancPluginWorklistQuery*  query;
+    const void*                        dicom;
+    uint32_t                           size;
+    int32_t*                           isMatch;
+    OrthancPluginMemoryBuffer*         target;
+  } _OrthancPluginWorklistQueryOperation;
+
+  /**
+   * @brief Test whether a worklist matches the query.
+   *
+   * This function checks whether one worklist (encoded as a DICOM
+   * file) matches the C-Find SCP query against modality
+   * worklists. This function must be called before adding the
+   * worklist as an answer through OrthancPluginWorklistAddAnswer().
+   *
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param query The worklist query, as received by the callback.
+   * @param dicom The worklist to answer, encoded as a DICOM file.
+   * @param size The size of the DICOM file.
+   * @return 1 if the worklist matches the query, 0 otherwise.
+   * @ingroup Worklists
+   **/
+  ORTHANC_PLUGIN_INLINE int32_t  OrthancPluginWorklistIsMatch(
+    OrthancPluginContext*              context,
+    const OrthancPluginWorklistQuery*  query,
+    const void*                        dicom,
+    uint32_t                           size)
+  {
+    int32_t isMatch = 0;
+
+    _OrthancPluginWorklistQueryOperation params;
+    params.query = query;
+    params.dicom = dicom;
+    params.size = size;
+    params.isMatch = &isMatch;
+    params.target = NULL;
+
+    if (context->InvokeService(context, _OrthancPluginService_WorklistIsMatch, &params) == OrthancPluginErrorCode_Success)
+    {
+      return isMatch;
+    }
+    else
+    {
+      /* Error: Assume non-match */
+      return 0;
+    }
+  }
+
+
+  /**
+   * @brief Retrieve the worklist query as a DICOM file.
+   *
+   * This function retrieves the DICOM file that underlies a C-Find
+   * SCP query against modality worklists.
+   *
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param target Memory buffer where to store the DICOM file. It must be freed with OrthancPluginFreeMemoryBuffer().
+   * @param query The worklist query, as received by the callback.
+   * @return 0 if success, other value if error.
+   * @ingroup Worklists
+   **/
+  ORTHANC_PLUGIN_INLINE OrthancPluginErrorCode  OrthancPluginWorklistGetDicomQuery(
+    OrthancPluginContext*              context,
+    OrthancPluginMemoryBuffer*         target,
+    const OrthancPluginWorklistQuery*  query)
+  {
+    _OrthancPluginWorklistQueryOperation params;
+    params.query = query;
+    params.dicom = NULL;
+    params.size = 0;
+    params.isMatch = NULL;
+    params.target = target;
+
+    return context->InvokeService(context, _OrthancPluginService_WorklistGetDicomQuery, &params);
+  }
+
+
+  /**
+   * @brief Get the origin of a DICOM file.
+   *
+   * This function returns the origin of a DICOM instance that has been received by Orthanc.
+   * 
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param instance The instance of interest.
+   * @return The origin of the instance.
+   * @ingroup Callbacks
+   **/
+  ORTHANC_PLUGIN_INLINE OrthancPluginInstanceOrigin OrthancPluginGetInstanceOrigin(
+    OrthancPluginContext*       context,
+    OrthancPluginDicomInstance* instance)
+  {
+    OrthancPluginInstanceOrigin origin;
+
+    _OrthancPluginAccessDicomInstance params;
+    memset(&params, 0, sizeof(params));
+    params.resultOrigin = &origin;
+    params.instance = instance;
+
+    if (context->InvokeService(context, _OrthancPluginService_GetInstanceOrigin, &params) != OrthancPluginErrorCode_Success)
+    {
+      /* Error */
+      return OrthancPluginInstanceOrigin_Unknown;
+    }
+    else
+    {
+      return origin;
+    }
+  }
+
+
+  typedef struct
+  {
+    OrthancPluginMemoryBuffer*     target;
+    const char*                    json;
+    const OrthancPluginImage*      pixelData;
+    OrthancPluginCreateDicomFlags  flags;
+  } _OrthancPluginCreateDicom;
+
+  /**
+   * @brief Create a DICOM instance from a JSON string and an image.
+   *
+   * This function takes as input a string containing a JSON file
+   * describing the content of a DICOM instance. As an output, it
+   * writes the corresponding DICOM instance to a newly allocated
+   * memory buffer. Additionally, an image to be encoded within the
+   * DICOM instance can also be provided.
+   *
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param target The target memory buffer. It must be freed with OrthancPluginFreeMemoryBuffer().
+   * @param json The input JSON file.
+   * @param pixelData The image. Can be NULL, if the pixel data is encoded inside the JSON with the data URI scheme.
+   * @param flags Flags governing the output.
+   * @return 0 if success, other value if error.
+   * @ingroup Toolbox
+   * @see OrthancPluginDicomBufferToJson
+   **/
+  ORTHANC_PLUGIN_INLINE OrthancPluginErrorCode OrthancPluginCreateDicom(
+    OrthancPluginContext*          context,
+    OrthancPluginMemoryBuffer*     target,
+    const char*                    json,
+    const OrthancPluginImage*      pixelData,
+    OrthancPluginCreateDicomFlags  flags)
+  {
+    _OrthancPluginCreateDicom params;
+    params.target = target;
+    params.json = json;
+    params.pixelData = pixelData;
+    params.flags = flags;
+
+    return context->InvokeService(context, _OrthancPluginService_CreateDicom, &params);
+  }
+
+
+  typedef struct
+  {
+    OrthancPluginDecodeImageCallback callback;
+  } _OrthancPluginDecodeImageCallback;
+
+  /**
+   * @brief Register a callback to handle the decoding of DICOM images.
+   *
+   * This function registers a custom callback to the decoding of
+   * DICOM images, replacing the built-in decoder of Orthanc.
+   *
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param callback The callback.
+   * @return 0 if success, other value if error.
+   * @ingroup Callbacks
+   **/
+  ORTHANC_PLUGIN_INLINE OrthancPluginErrorCode OrthancPluginRegisterDecodeImageCallback(
+    OrthancPluginContext*             context,
+    OrthancPluginDecodeImageCallback  callback)
+  {
+    _OrthancPluginDecodeImageCallback params;
+    params.callback = callback;
+
+    return context->InvokeService(context, _OrthancPluginService_RegisterDecodeImageCallback, &params);
+  }
+  
+
+
+  typedef struct
+  {
+    OrthancPluginImage**       target;
+    OrthancPluginPixelFormat   format;
+    uint32_t                   width;
+    uint32_t                   height;
+    uint32_t                   pitch;
+    void*                      buffer;
+    const void*                constBuffer;
+    uint32_t                   bufferSize;
+    uint32_t                   frameIndex;
+  } _OrthancPluginCreateImage;
+
+
+  /**
+   * @brief Create an image.
+   *
+   * This function creates an image of given size and format.
+   *
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param format The format of the pixels.
+   * @param width The width of the image.
+   * @param height The height of the image.
+   * @return The newly allocated image. It must be freed with OrthancPluginFreeImage().
+   * @ingroup Images
+   **/
+  ORTHANC_PLUGIN_INLINE OrthancPluginImage* OrthancPluginCreateImage(
+    OrthancPluginContext*     context,
+    OrthancPluginPixelFormat  format,
+    uint32_t                  width,
+    uint32_t                  height)
+  {
+    OrthancPluginImage* target = NULL;
+
+    _OrthancPluginCreateImage params;
+    memset(&params, 0, sizeof(params));
+    params.target = &target;
+    params.format = format;
+    params.width = width;
+    params.height = height;
+
+    if (context->InvokeService(context, _OrthancPluginService_CreateImage, &params) != OrthancPluginErrorCode_Success)
+    {
+      return NULL;
+    }
+    else
+    {
+      return target;
+    }
+  }
+
+
+  /**
+   * @brief Create an image pointing to a memory buffer.
+   *
+   * This function creates an image whose content points to a memory
+   * buffer managed by the plugin. Note that the buffer is directly
+   * accessed, no memory is allocated and no data is copied.
+   *
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param format The format of the pixels.
+   * @param width The width of the image.
+   * @param height The height of the image.
+   * @param pitch The pitch of the image (i.e. the number of bytes
+   * between 2 successive lines of the image in the memory buffer).
+   * @param buffer The memory buffer.
+   * @return The newly allocated image. It must be freed with OrthancPluginFreeImage().
+   * @ingroup Images
+   **/
+  ORTHANC_PLUGIN_INLINE OrthancPluginImage* OrthancPluginCreateImageAccessor(
+    OrthancPluginContext*     context,
+    OrthancPluginPixelFormat  format,
+    uint32_t                  width,
+    uint32_t                  height,
+    uint32_t                  pitch,
+    void*                     buffer)
+  {
+    OrthancPluginImage* target = NULL;
+
+    _OrthancPluginCreateImage params;
+    memset(&params, 0, sizeof(params));
+    params.target = &target;
+    params.format = format;
+    params.width = width;
+    params.height = height;
+    params.pitch = pitch;
+    params.buffer = buffer;
+
+    if (context->InvokeService(context, _OrthancPluginService_CreateImageAccessor, &params) != OrthancPluginErrorCode_Success)
+    {
+      return NULL;
+    }
+    else
+    {
+      return target;
+    }
+  }
+
+
+
+  /**
+   * @brief Decode one frame from a DICOM instance.
+   *
+   * This function decodes one frame of a DICOM image that is stored
+   * in a memory buffer. This function will give the same result as
+   * OrthancPluginUncompressImage() for single-frame DICOM images.
+   *
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param buffer Pointer to a memory buffer containing the DICOM image.
+   * @param bufferSize Size of the memory buffer containing the DICOM image.
+   * @param frameIndex The index of the frame of interest in a multi-frame image.
+   * @return The uncompressed image. It must be freed with OrthancPluginFreeImage().
+   * @ingroup Images
+   **/
+  ORTHANC_PLUGIN_INLINE OrthancPluginImage* OrthancPluginDecodeDicomImage(
+    OrthancPluginContext*  context,
+    const void*            buffer,
+    uint32_t               bufferSize,
+    uint32_t               frameIndex)
+  {
+    OrthancPluginImage* target = NULL;
+
+    _OrthancPluginCreateImage params;
+    memset(&params, 0, sizeof(params));
+    params.target = &target;
+    params.constBuffer = buffer;
+    params.bufferSize = bufferSize;
+    params.frameIndex = frameIndex;
+
+    if (context->InvokeService(context, _OrthancPluginService_DecodeDicomImage, &params) != OrthancPluginErrorCode_Success)
+    {
+      return NULL;
+    }
+    else
+    {
+      return target;
+    }
+  }
+
+
+
+  typedef struct
+  {
+    char**       result;
+    const void*  buffer;
+    uint32_t     size;
+  } _OrthancPluginComputeHash;
+
+  /**
+   * @brief Compute an MD5 hash.
+   *
+   * This functions computes the MD5 cryptographic hash of the given memory buffer.
+   * 
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param buffer The source memory buffer.
+   * @param size The size in bytes of the source buffer.
+   * @return The NULL value in case of error, or a string containing the cryptographic hash.
+   * This string must be freed by OrthancPluginFreeString().
+   * @ingroup Toolbox
+   **/
+  ORTHANC_PLUGIN_INLINE char* OrthancPluginComputeMd5(
+    OrthancPluginContext*  context,
+    const void*            buffer,
+    uint32_t               size)
+  {
+    char* result;
+
+    _OrthancPluginComputeHash params;
+    params.result = &result;
+    params.buffer = buffer;
+    params.size = size;
+
+    if (context->InvokeService(context, _OrthancPluginService_ComputeMd5, &params) != OrthancPluginErrorCode_Success)
+    {
+      /* Error */
+      return NULL;
+    }
+    else
+    {
+      return result;
+    }
+  }
+
+
+  /**
+   * @brief Compute a SHA-1 hash.
+   *
+   * This functions computes the SHA-1 cryptographic hash of the given memory buffer.
+   * 
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param buffer The source memory buffer.
+   * @param size The size in bytes of the source buffer.
+   * @return The NULL value in case of error, or a string containing the cryptographic hash.
+   * This string must be freed by OrthancPluginFreeString().
+   * @ingroup Toolbox
+   **/
+  ORTHANC_PLUGIN_INLINE char* OrthancPluginComputeSha1(
+    OrthancPluginContext*  context,
+    const void*            buffer,
+    uint32_t               size)
+  {
+    char* result;
+
+    _OrthancPluginComputeHash params;
+    params.result = &result;
+    params.buffer = buffer;
+    params.size = size;
+
+    if (context->InvokeService(context, _OrthancPluginService_ComputeSha1, &params) != OrthancPluginErrorCode_Success)
+    {
+      /* Error */
+      return NULL;
+    }
+    else
+    {
+      return result;
+    }
+  }
+
+
+
+  typedef struct
+  {
+    OrthancPluginDictionaryEntry* target;
+    const char*                   name;
+  } _OrthancPluginLookupDictionary;
+
+  /**
+   * @brief Get information about the given DICOM tag.
+   *
+   * This functions makes a lookup in the dictionary of DICOM tags
+   * that are known to Orthanc, and returns information about this
+   * tag. The tag can be specified using its human-readable name
+   * (e.g. "PatientName") or a set of two hexadecimal numbers
+   * (e.g. "0010-0020").
+   * 
+   * @param context The Orthanc plugin context, as received by OrthancPluginInitialize().
+   * @param target Where to store the information about the tag.
+   * @param name The name of the DICOM tag.
+   * @return 0 if success, other value if error.
+   * @ingroup Toolbox
+   **/
+  ORTHANC_PLUGIN_INLINE OrthancPluginErrorCode  OrthancPluginLookupDictionary(
+    OrthancPluginContext*          context,
+    OrthancPluginDictionaryEntry*  target,
+    const char*                    name)
+  {
+    _OrthancPluginLookupDictionary params;
+    params.target = target;
+    params.name = name;
+    return context->InvokeService(context, _OrthancPluginService_LookupDictionary, &params);
+  }
+
+
 #ifdef  __cplusplus
 }
 #endif
--- a/Orthanc/Sdk-0.9.4/orthanc/OrthancCppDatabasePlugin.h	Wed Dec 02 14:20:55 2015 +0100
+++ b/Orthanc/Sdk-0.9.4/orthanc/OrthancCppDatabasePlugin.h	Wed Dec 02 15:00:59 2015 +0100
@@ -62,6 +62,29 @@
 //! @endcond
 
 
+  /**
+   * @ingroup Callbacks
+   **/
+  class DatabaseException
+  {
+  private:
+    OrthancPluginErrorCode  code_;
+
+  public:
+    DatabaseException() : code_(OrthancPluginErrorCode_DatabasePlugin)
+    {
+    }
+
+    DatabaseException(OrthancPluginErrorCode code) : code_(code)
+    {
+    }
+
+    OrthancPluginErrorCode  GetErrorCode() const
+    {
+      return code_;
+    }
+  };
+
 
   /**
    * @ingroup Callbacks
@@ -99,6 +122,11 @@
     {
     }
 
+    OrthancPluginContext* GetContext()
+    {
+      return context_;
+    }
+
     void LogError(const std::string& message)
     {
       OrthancPluginLogError(context_, message.c_str());
@@ -311,6 +339,9 @@
 
     virtual void DeleteResource(int64_t id) = 0;
 
+    virtual void GetAllInternalIds(std::list<int64_t>& target,
+                                   OrthancPluginResourceType resourceType) = 0;
+
     virtual void GetAllPublicIds(std::list<std::string>& target,
                                  OrthancPluginResourceType resourceType) = 0;
 
@@ -375,18 +406,11 @@
     virtual bool LookupGlobalProperty(std::string& target /*out*/,
                                       int32_t property) = 0;
 
-    /**
-     * "Identifiers" are necessarily one of the following tags:
-     * PatientID (0x0010, 0x0020), StudyInstanceUID (0x0020, 0x000d),
-     * SeriesInstanceUID (0x0020, 0x000e), SOPInstanceUID (0x0008,
-     * 0x0018) or AccessionNumber (0x0008, 0x0050).
-     **/
     virtual void LookupIdentifier(std::list<int64_t>& target /*out*/,
+                                  OrthancPluginResourceType resourceType,
                                   uint16_t group,
                                   uint16_t element,
-                                  const char* value) = 0;
-
-    virtual void LookupIdentifier(std::list<int64_t>& target /*out*/,
+                                  OrthancPluginIdentifierConstraint constraint,
                                   const char* value) = 0;
 
     virtual bool LookupMetadata(std::string& target /*out*/,
@@ -433,8 +457,15 @@
 
     virtual uint32_t GetDatabaseVersion() = 0;
 
+    /**
+     * Upgrade the database to the specified version of the database
+     * schema.  The upgrade script is allowed to make calls to
+     * OrthancPluginReconstructMainDicomTags().
+     **/
     virtual void UpgradeDatabase(uint32_t  targetVersion,
                                  OrthancPluginStorageArea* storageArea) = 0;
+
+    virtual void ClearMainDicomTags(int64_t internalId) = 0;
   };
 
 
@@ -463,9 +494,9 @@
     }
 
 
-    static int32_t  AddAttachment(void* payload,
-                                  int64_t id,
-                                  const OrthancPluginAttachment* attachment)
+    static OrthancPluginErrorCode  AddAttachment(void* payload,
+                                                 int64_t id,
+                                                 const OrthancPluginAttachment* attachment)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -473,19 +504,23 @@
       try
       {
         backend->AddAttachment(id, *attachment);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
                              
-    static int32_t  AttachChild(void* payload,
-                                int64_t parent,
-                                int64_t child)
+    static OrthancPluginErrorCode  AttachChild(void* payload,
+                                               int64_t parent,
+                                               int64_t child)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -493,17 +528,21 @@
       try
       {
         backend->AttachChild(parent, child);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
           
                    
-    static int32_t  ClearChanges(void* payload)
+    static OrthancPluginErrorCode  ClearChanges(void* payload)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -511,17 +550,21 @@
       try
       {
         backend->ClearChanges();
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
                              
 
-    static int32_t  ClearExportedResources(void* payload)
+    static OrthancPluginErrorCode  ClearExportedResources(void* payload)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -529,20 +572,24 @@
       try
       {
         backend->ClearExportedResources();
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  CreateResource(int64_t* id, 
-                                   void* payload,
-                                   const char* publicId,
-                                   OrthancPluginResourceType resourceType)
+    static OrthancPluginErrorCode  CreateResource(int64_t* id, 
+                                                  void* payload,
+                                                  const char* publicId,
+                                                  OrthancPluginResourceType resourceType)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -550,19 +597,23 @@
       try
       {
         *id = backend->CreateResource(publicId, resourceType);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
           
          
-    static int32_t  DeleteAttachment(void* payload,
-                                     int64_t id,
-                                     int32_t contentType)
+    static OrthancPluginErrorCode  DeleteAttachment(void* payload,
+                                                    int64_t id,
+                                                    int32_t contentType)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -570,19 +621,23 @@
       try
       {
         backend->DeleteAttachment(id, contentType);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
    
 
-    static int32_t  DeleteMetadata(void* payload,
-                                   int64_t id,
-                                   int32_t metadataType)
+    static OrthancPluginErrorCode  DeleteMetadata(void* payload,
+                                                  int64_t id,
+                                                  int32_t metadataType)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -590,18 +645,22 @@
       try
       {
         backend->DeleteMetadata(id, metadataType);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
    
 
-    static int32_t  DeleteResource(void* payload,
-                                   int64_t id)
+    static OrthancPluginErrorCode  DeleteResource(void* payload,
+                                                  int64_t id)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -609,19 +668,56 @@
       try
       {
         backend->DeleteResource(id);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  GetAllPublicIds(OrthancPluginDatabaseContext* context,
-                                    void* payload,
-                                    OrthancPluginResourceType resourceType)
+    static OrthancPluginErrorCode  GetAllInternalIds(OrthancPluginDatabaseContext* context,
+                                                     void* payload,
+                                                     OrthancPluginResourceType resourceType)
+    {
+      IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
+      backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
+
+      try
+      {
+        std::list<int64_t> target;
+        backend->GetAllInternalIds(target, resourceType);
+
+        for (std::list<int64_t>::const_iterator
+               it = target.begin(); it != target.end(); ++it)
+        {
+          OrthancPluginDatabaseAnswerInt64(backend->GetOutput().context_,
+                                           backend->GetOutput().database_, *it);
+        }
+
+        return OrthancPluginErrorCode_Success;
+      }
+      catch (std::runtime_error& e)
+      {
+        LogError(backend, e);
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
+      }
+    }
+
+
+    static OrthancPluginErrorCode  GetAllPublicIds(OrthancPluginDatabaseContext* context,
+                                                   void* payload,
+                                                   OrthancPluginResourceType resourceType)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -639,21 +735,25 @@
                                             it->c_str());
         }
 
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  GetAllPublicIdsWithLimit(OrthancPluginDatabaseContext* context,
-                                             void* payload,
-                                             OrthancPluginResourceType resourceType,
-                                             uint64_t since,
-                                             uint64_t limit)
+    static OrthancPluginErrorCode  GetAllPublicIdsWithLimit(OrthancPluginDatabaseContext* context,
+                                                            void* payload,
+                                                            OrthancPluginResourceType resourceType,
+                                                            uint64_t since,
+                                                            uint64_t limit)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -671,20 +771,24 @@
                                             it->c_str());
         }
 
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  GetChanges(OrthancPluginDatabaseContext* context,
-                               void* payload,
-                               int64_t since,
-                               uint32_t maxResult)
+    static OrthancPluginErrorCode  GetChanges(OrthancPluginDatabaseContext* context,
+                                              void* payload,
+                                              int64_t since,
+                                              uint32_t maxResult)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_Change);
@@ -700,19 +804,23 @@
                                                  backend->GetOutput().database_);
         }
 
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  GetChildrenInternalId(OrthancPluginDatabaseContext* context,
-                                          void* payload,
-                                          int64_t id)
+    static OrthancPluginErrorCode  GetChildrenInternalId(OrthancPluginDatabaseContext* context,
+                                                         void* payload,
+                                                         int64_t id)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -729,19 +837,23 @@
                                            backend->GetOutput().database_, *it);
         }
 
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
           
          
-    static int32_t  GetChildrenPublicId(OrthancPluginDatabaseContext* context,
-                                        void* payload,
-                                        int64_t id)
+    static OrthancPluginErrorCode  GetChildrenPublicId(OrthancPluginDatabaseContext* context,
+                                                       void* payload,
+                                                       int64_t id)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -759,20 +871,24 @@
                                             it->c_str());
         }
 
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  GetExportedResources(OrthancPluginDatabaseContext* context,
-                                         void* payload,
-                                         int64_t  since,
-                                         uint32_t  maxResult)
+    static OrthancPluginErrorCode  GetExportedResources(OrthancPluginDatabaseContext* context,
+                                                        void* payload,
+                                                        int64_t  since,
+                                                        uint32_t  maxResult)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_ExportedResource);
@@ -787,18 +903,22 @@
           OrthancPluginDatabaseAnswerExportedResourcesDone(backend->GetOutput().context_,
                                                            backend->GetOutput().database_);
         }
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
           
          
-    static int32_t  GetLastChange(OrthancPluginDatabaseContext* context,
-                                  void* payload)
+    static OrthancPluginErrorCode  GetLastChange(OrthancPluginDatabaseContext* context,
+                                                 void* payload)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_Change);
@@ -806,18 +926,22 @@
       try
       {
         backend->GetLastChange();
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  GetLastExportedResource(OrthancPluginDatabaseContext* context,
-                                            void* payload)
+    static OrthancPluginErrorCode  GetLastExportedResource(OrthancPluginDatabaseContext* context,
+                                                           void* payload)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_ExportedResource);
@@ -825,19 +949,23 @@
       try
       {
         backend->GetLastExportedResource();
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
     
                
-    static int32_t  GetMainDicomTags(OrthancPluginDatabaseContext* context,
-                                     void* payload,
-                                     int64_t id)
+    static OrthancPluginErrorCode  GetMainDicomTags(OrthancPluginDatabaseContext* context,
+                                                    void* payload,
+                                                    int64_t id)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_DicomTag);
@@ -845,19 +973,23 @@
       try
       {
         backend->GetMainDicomTags(id);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
           
          
-    static int32_t  GetPublicId(OrthancPluginDatabaseContext* context,
-                                void* payload,
-                                int64_t id)
+    static OrthancPluginErrorCode  GetPublicId(OrthancPluginDatabaseContext* context,
+                                               void* payload,
+                                               int64_t id)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -869,19 +1001,23 @@
                                           backend->GetOutput().database_,
                                           s.c_str());
 
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  GetResourceCount(uint64_t* target,
-                                     void* payload,
-                                     OrthancPluginResourceType  resourceType)
+    static OrthancPluginErrorCode  GetResourceCount(uint64_t* target,
+                                                    void* payload,
+                                                    OrthancPluginResourceType  resourceType)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -889,19 +1025,23 @@
       try
       {
         *target = backend->GetResourceCount(resourceType);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
                    
 
-    static int32_t  GetResourceType(OrthancPluginResourceType* resourceType,
-                                    void* payload,
-                                    int64_t id)
+    static OrthancPluginErrorCode  GetResourceType(OrthancPluginResourceType* resourceType,
+                                                   void* payload,
+                                                   int64_t id)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -909,18 +1049,22 @@
       try
       {
         *resourceType = backend->GetResourceType(id);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  GetTotalCompressedSize(uint64_t* target,
-                                           void* payload)
+    static OrthancPluginErrorCode  GetTotalCompressedSize(uint64_t* target,
+                                                          void* payload)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -928,18 +1072,22 @@
       try
       {
         *target = backend->GetTotalCompressedSize();
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
           
          
-    static int32_t  GetTotalUncompressedSize(uint64_t* target,
-                                             void* payload)
+    static OrthancPluginErrorCode  GetTotalUncompressedSize(uint64_t* target,
+                                                            void* payload)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -947,19 +1095,23 @@
       try
       {
         *target = backend->GetTotalUncompressedSize();
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
                    
 
-    static int32_t  IsExistingResource(int32_t* existing,
-                                       void* payload,
-                                       int64_t id)
+    static OrthancPluginErrorCode  IsExistingResource(int32_t* existing,
+                                                      void* payload,
+                                                      int64_t id)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -967,19 +1119,23 @@
       try
       {
         *existing = backend->IsExistingResource(id);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  IsProtectedPatient(int32_t* isProtected,
-                                       void* payload,
-                                       int64_t id)
+    static OrthancPluginErrorCode  IsProtectedPatient(int32_t* isProtected,
+                                                      void* payload,
+                                                      int64_t id)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -987,19 +1143,23 @@
       try
       {
         *isProtected = backend->IsProtectedPatient(id);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  ListAvailableMetadata(OrthancPluginDatabaseContext* context,
-                                          void* payload,
-                                          int64_t id)
+    static OrthancPluginErrorCode  ListAvailableMetadata(OrthancPluginDatabaseContext* context,
+                                                         void* payload,
+                                                         int64_t id)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1017,19 +1177,23 @@
                                            *it);
         }
 
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
           
          
-    static int32_t  ListAvailableAttachments(OrthancPluginDatabaseContext* context,
-                                             void* payload,
-                                             int64_t id)
+    static OrthancPluginErrorCode  ListAvailableAttachments(OrthancPluginDatabaseContext* context,
+                                                            void* payload,
+                                                            int64_t id)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1047,18 +1211,22 @@
                                            *it);
         }
 
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  LogChange(void* payload,
-                              const OrthancPluginChange* change)
+    static OrthancPluginErrorCode  LogChange(void* payload,
+                                             const OrthancPluginChange* change)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1066,18 +1234,22 @@
       try
       {
         backend->LogChange(*change);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
           
          
-    static int32_t  LogExportedResource(void* payload,
-                                        const OrthancPluginExportedResource* exported)
+    static OrthancPluginErrorCode  LogExportedResource(void* payload,
+                                                       const OrthancPluginExportedResource* exported)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1085,20 +1257,24 @@
       try
       {
         backend->LogExportedResource(*exported);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
           
          
-    static int32_t  LookupAttachment(OrthancPluginDatabaseContext* context,
-                                     void* payload,
-                                     int64_t id,
-                                     int32_t contentType)
+    static OrthancPluginErrorCode  LookupAttachment(OrthancPluginDatabaseContext* context,
+                                                    void* payload,
+                                                    int64_t id,
+                                                    int32_t contentType)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_Attachment);
@@ -1106,19 +1282,23 @@
       try
       {
         backend->LookupAttachment(id, contentType);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  LookupGlobalProperty(OrthancPluginDatabaseContext* context,
-                                         void* payload,
-                                         int32_t property)
+    static OrthancPluginErrorCode  LookupGlobalProperty(OrthancPluginDatabaseContext* context,
+                                                        void* payload,
+                                                        int32_t property)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1133,19 +1313,25 @@
                                             s.c_str());
         }
 
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  LookupIdentifier(OrthancPluginDatabaseContext* context,
-                                     void* payload,
-                                     const OrthancPluginDicomTag* tag)
+    static OrthancPluginErrorCode  LookupIdentifier3(OrthancPluginDatabaseContext* context,
+                                                     void* payload,
+                                                     OrthancPluginResourceType resourceType,
+                                                     const OrthancPluginDicomTag* tag,
+                                                     OrthancPluginIdentifierConstraint constraint)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1153,7 +1339,7 @@
       try
       {
         std::list<int64_t> target;
-        backend->LookupIdentifier(target, tag->group, tag->element, tag->value);
+        backend->LookupIdentifier(target, resourceType, tag->group, tag->element, constraint, tag->value);
 
         for (std::list<int64_t>::const_iterator
                it = target.begin(); it != target.end(); ++it)
@@ -1162,49 +1348,24 @@
                                            backend->GetOutput().database_, *it);
         }
 
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  LookupIdentifier2(OrthancPluginDatabaseContext* context,
-                                      void* payload,
-                                      const char* value)
-    {
-      IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
-      backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
-
-      try
-      {
-        std::list<int64_t> target;
-        backend->LookupIdentifier(target, value);
-
-        for (std::list<int64_t>::const_iterator
-               it = target.begin(); it != target.end(); ++it)
-        {
-          OrthancPluginDatabaseAnswerInt64(backend->GetOutput().context_,
-                                           backend->GetOutput().database_, *it);
-        }
-
-        return 0;
-      }
-      catch (std::runtime_error& e)
-      {
-        LogError(backend, e);
-        return -1;
-      }
-    }
-
-
-    static int32_t  LookupMetadata(OrthancPluginDatabaseContext* context,
-                                   void* payload,
-                                   int64_t id,
-                                   int32_t metadata)
+    static OrthancPluginErrorCode  LookupMetadata(OrthancPluginDatabaseContext* context,
+                                                  void* payload,
+                                                  int64_t id,
+                                                  int32_t metadata)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1218,19 +1379,23 @@
                                             backend->GetOutput().database_, s.c_str());
         }
 
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  LookupParent(OrthancPluginDatabaseContext* context,
-                                 void* payload,
-                                 int64_t id)
+    static OrthancPluginErrorCode  LookupParent(OrthancPluginDatabaseContext* context,
+                                                void* payload,
+                                                int64_t id)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1244,19 +1409,23 @@
                                            backend->GetOutput().database_, parent);
         }
 
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  LookupResource(OrthancPluginDatabaseContext* context,
-                                   void* payload,
-                                   const char* publicId)
+    static OrthancPluginErrorCode  LookupResource(OrthancPluginDatabaseContext* context,
+                                                  void* payload,
+                                                  const char* publicId)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1272,18 +1441,22 @@
                                               id, type);
         }
 
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  SelectPatientToRecycle(OrthancPluginDatabaseContext* context,
-                                           void* payload)
+    static OrthancPluginErrorCode  SelectPatientToRecycle(OrthancPluginDatabaseContext* context,
+                                                          void* payload)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1297,19 +1470,23 @@
                                            backend->GetOutput().database_, id);
         }
 
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  SelectPatientToRecycle2(OrthancPluginDatabaseContext* context,
-                                            void* payload,
-                                            int64_t patientIdToAvoid)
+    static OrthancPluginErrorCode  SelectPatientToRecycle2(OrthancPluginDatabaseContext* context,
+                                                           void* payload,
+                                                           int64_t patientIdToAvoid)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1323,19 +1500,23 @@
                                            backend->GetOutput().database_, id);
         }
 
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  SetGlobalProperty(void* payload,
-                                      int32_t property,
-                                      const char* value)
+    static OrthancPluginErrorCode  SetGlobalProperty(void* payload,
+                                                     int32_t property,
+                                                     const char* value)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1343,19 +1524,23 @@
       try
       {
         backend->SetGlobalProperty(property, value);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  SetMainDicomTag(void* payload,
-                                    int64_t id,
-                                    const OrthancPluginDicomTag* tag)
+    static OrthancPluginErrorCode  SetMainDicomTag(void* payload,
+                                                   int64_t id,
+                                                   const OrthancPluginDicomTag* tag)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1363,19 +1548,23 @@
       try
       {
         backend->SetMainDicomTag(id, tag->group, tag->element, tag->value);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  SetIdentifierTag(void* payload,
-                                    int64_t id,
-                                    const OrthancPluginDicomTag* tag)
+    static OrthancPluginErrorCode  SetIdentifierTag(void* payload,
+                                                    int64_t id,
+                                                    const OrthancPluginDicomTag* tag)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1383,20 +1572,24 @@
       try
       {
         backend->SetIdentifierTag(id, tag->group, tag->element, tag->value);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  SetMetadata(void* payload,
-                                int64_t id,
-                                int32_t metadata,
-                                const char* value)
+    static OrthancPluginErrorCode  SetMetadata(void* payload,
+                                               int64_t id,
+                                               int32_t metadata,
+                                               const char* value)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1404,19 +1597,23 @@
       try
       {
         backend->SetMetadata(id, metadata, value);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t  SetProtectedPatient(void* payload,
-                                        int64_t id,
-                                        int32_t isProtected)
+    static OrthancPluginErrorCode  SetProtectedPatient(void* payload,
+                                                       int64_t id,
+                                                       int32_t isProtected)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1424,17 +1621,21 @@
       try
       {
         backend->SetProtectedPatient(id, (isProtected != 0));
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t StartTransaction(void* payload)
+    static OrthancPluginErrorCode StartTransaction(void* payload)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1442,17 +1643,21 @@
       try
       {
         backend->StartTransaction();
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t RollbackTransaction(void* payload)
+    static OrthancPluginErrorCode RollbackTransaction(void* payload)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1460,17 +1665,21 @@
       try
       {
         backend->RollbackTransaction();
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t CommitTransaction(void* payload)
+    static OrthancPluginErrorCode CommitTransaction(void* payload)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1478,17 +1687,21 @@
       try
       {
         backend->CommitTransaction();
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t Open(void* payload)
+    static OrthancPluginErrorCode Open(void* payload)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1496,17 +1709,21 @@
       try
       {
         backend->Open();
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t Close(void* payload)
+    static OrthancPluginErrorCode Close(void* payload)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       backend->GetOutput().SetAllowedAnswers(DatabaseBackendOutput::AllowedAnswers_None);
@@ -1514,49 +1731,83 @@
       try
       {
         backend->Close();
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t GetDatabaseVersion(uint32_t* version,
-                                      void* payload)
+    static OrthancPluginErrorCode GetDatabaseVersion(uint32_t* version,
+                                                     void* payload)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       
       try
       {
         *version = backend->GetDatabaseVersion();
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
 
-    static int32_t UpgradeDatabase(void* payload,
-                                   uint32_t  targetVersion,
-                                   OrthancPluginStorageArea* storageArea)
+    static OrthancPluginErrorCode UpgradeDatabase(void* payload,
+                                                  uint32_t  targetVersion,
+                                                  OrthancPluginStorageArea* storageArea)
     {
       IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
       
       try
       {
         backend->UpgradeDatabase(targetVersion, storageArea);
-        return 0;
+        return OrthancPluginErrorCode_Success;
       }
       catch (std::runtime_error& e)
       {
         LogError(backend, e);
-        return -1;
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
+      }
+    }
+
+    
+    static OrthancPluginErrorCode ClearMainDicomTags(void* payload,
+                                                     int64_t internalId)
+    {
+      IDatabaseBackend* backend = reinterpret_cast<IDatabaseBackend*>(payload);
+      
+      try
+      {
+        backend->ClearMainDicomTags(internalId);
+        return OrthancPluginErrorCode_Success;
+      }
+      catch (std::runtime_error& e)
+      {
+        LogError(backend, e);
+        return OrthancPluginErrorCode_DatabasePlugin;
+      }
+      catch (DatabaseException& e)
+      {
+        return e.GetErrorCode();
       }
     }
 
@@ -1607,8 +1858,8 @@
       params.logExportedResource = LogExportedResource;
       params.lookupAttachment = LookupAttachment;
       params.lookupGlobalProperty = LookupGlobalProperty;
-      params.lookupIdentifier = LookupIdentifier;
-      params.lookupIdentifier2 = LookupIdentifier2;
+      params.lookupIdentifier = NULL;   // Unused starting with Orthanc 0.9.5 (db v6)
+      params.lookupIdentifier2 = NULL;   // Unused starting with Orthanc 0.9.5 (db v6)
       params.lookupMetadata = LookupMetadata;
       params.lookupParent = LookupParent;
       params.lookupResource = LookupResource;
@@ -1628,6 +1879,9 @@
       extensions.getAllPublicIdsWithLimit = GetAllPublicIdsWithLimit;
       extensions.getDatabaseVersion = GetDatabaseVersion;
       extensions.upgradeDatabase = UpgradeDatabase;
+      extensions.clearMainDicomTags = ClearMainDicomTags;
+      extensions.getAllInternalIds = GetAllInternalIds;   // New in Orthanc 0.9.5 (db v6)
+      extensions.lookupIdentifier3 = LookupIdentifier3;   // New in Orthanc 0.9.5 (db v6)
 
       OrthancPluginDatabaseContext* database = OrthancPluginRegisterDatabaseBackendV2(context, &params, &extensions, &backend);
       if (!context)
--- a/Resources/SyncOrthancFolder.py	Wed Dec 02 14:20:55 2015 +0100
+++ b/Resources/SyncOrthancFolder.py	Wed Dec 02 15:00:59 2015 +0100
@@ -65,9 +65,11 @@
     commands.append([ 'default', f, f ])
 
 for f in SDK:
-    commands.append([ 'Orthanc-%s' % PLUGIN_SDK_VERSION, 
-                      'Plugins/Include/%s' % f,
-                      'Sdk-%s/%s' % (PLUGIN_SDK_VERSION, f) ])
+    commands.append([
+        'default',
+        #'Orthanc-%s' % PLUGIN_SDK_VERSION, 
+        'Plugins/Include/%s' % f,
+        'Sdk-%s/%s' % (PLUGIN_SDK_VERSION, f) ])
 
 
 pool = multiprocessing.Pool(10)  # simultaneous downloads