# HG changeset patch # User Sebastien Jodogne # Date 1410967388 -7200 # Node ID 3db41779d8f9374847ee04205de6930b4c0ff0f8 # Parent 80671157d051a83d7b83dfa16f9e9ae9f6c201c0 abstraction to allow/prevent transfer syntaxes on AET basis diff -r 80671157d051 -r 3db41779d8f9 OrthancServer/DicomProtocol/IApplicationEntityFilter.h --- a/OrthancServer/DicomProtocol/IApplicationEntityFilter.h Wed Sep 17 11:57:28 2014 +0200 +++ b/OrthancServer/DicomProtocol/IApplicationEntityFilter.h Wed Sep 17 17:23:08 2014 +0200 @@ -51,5 +51,8 @@ virtual bool IsAllowedRequest(const std::string& callingIp, const std::string& callingAet, DicomRequestType type) = 0; + + virtual bool IsAllowedTransferSyntax(const std::string& callingAet, + TransferSyntax syntax) = 0; }; } diff -r 80671157d051 -r 3db41779d8f9 OrthancServer/Internals/CommandDispatcher.cpp --- a/OrthancServer/Internals/CommandDispatcher.cpp Wed Sep 17 11:57:28 2014 +0200 +++ b/OrthancServer/Internals/CommandDispatcher.cpp Wed Sep 17 17:23:08 2014 +0200 @@ -459,7 +459,38 @@ return NULL; } - LOG(INFO) << "Association Received"; + // Retrieve the AET and the IP address of the remote modality + std::string callingAet; + std::string callingIP; + std::string calledAet; + + { + DIC_AE callingAet_C; + DIC_AE calledAet_C; + DIC_AE callingIP_C; + DIC_AE calledIP_C; + if (ASC_getAPTitles(assoc->params, callingAet_C, calledAet_C, NULL).bad() || + ASC_getPresentationAddresses(assoc->params, callingIP_C, calledIP_C).bad()) + { + T_ASC_RejectParameters rej = + { + ASC_RESULT_REJECTEDPERMANENT, + ASC_SOURCE_SERVICEUSER, + ASC_REASON_SU_NOREASON + }; + ASC_rejectAssociation(assoc, &rej); + AssociationCleanup(assoc); + return NULL; + } + + callingIP = std::string(/*OFSTRING_GUARD*/(callingIP_C)); + callingAet = std::string(/*OFSTRING_GUARD*/(callingAet_C)); + calledAet = (/*OFSTRING_GUARD*/(calledAet_C)); + } + + LOG(INFO) << "Association Received from AET " << callingAet + << " on IP " << callingIP; + std::vector transferSyntaxes; @@ -469,36 +500,72 @@ transferSyntaxes.push_back(UID_LittleEndianImplicitTransferSyntax); // New transfer syntaxes supported since Orthanc 0.7.2 - transferSyntaxes.push_back(UID_DeflatedExplicitVRLittleEndianTransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess1TransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess2_4TransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess3_5TransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess6_8TransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess7_9TransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess10_12TransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess11_13TransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess14TransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess15TransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess16_18TransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess17_19TransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess20_22TransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess21_23TransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess24_26TransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess25_27TransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess28TransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess29TransferSyntax); - transferSyntaxes.push_back(UID_JPEGProcess14SV1TransferSyntax); - transferSyntaxes.push_back(UID_JPEGLSLosslessTransferSyntax); - transferSyntaxes.push_back(UID_JPEGLSLossyTransferSyntax); - transferSyntaxes.push_back(UID_JPEG2000LosslessOnlyTransferSyntax); - transferSyntaxes.push_back(UID_JPEG2000TransferSyntax); - transferSyntaxes.push_back(UID_JPEG2000Part2MulticomponentImageCompressionLosslessOnlyTransferSyntax); - transferSyntaxes.push_back(UID_JPEG2000Part2MulticomponentImageCompressionTransferSyntax); - transferSyntaxes.push_back(UID_JPIPReferencedTransferSyntax); - transferSyntaxes.push_back(UID_JPIPReferencedDeflateTransferSyntax); - transferSyntaxes.push_back(UID_MPEG2MainProfileAtMainLevelTransferSyntax); - transferSyntaxes.push_back(UID_MPEG2MainProfileAtHighLevelTransferSyntax); - transferSyntaxes.push_back(UID_RLELosslessTransferSyntax); + if (!server.HasApplicationEntityFilter() || + server.GetApplicationEntityFilter().IsAllowedTransferSyntax(callingAet, TransferSyntax_Deflated)) + { + transferSyntaxes.push_back(UID_DeflatedExplicitVRLittleEndianTransferSyntax); + } + + if (!server.HasApplicationEntityFilter() || + server.GetApplicationEntityFilter().IsAllowedTransferSyntax(callingAet, TransferSyntax_Jpeg)) + { + transferSyntaxes.push_back(UID_JPEGProcess1TransferSyntax); + transferSyntaxes.push_back(UID_JPEGProcess2_4TransferSyntax); + transferSyntaxes.push_back(UID_JPEGProcess3_5TransferSyntax); + transferSyntaxes.push_back(UID_JPEGProcess6_8TransferSyntax); + transferSyntaxes.push_back(UID_JPEGProcess7_9TransferSyntax); + transferSyntaxes.push_back(UID_JPEGProcess10_12TransferSyntax); + transferSyntaxes.push_back(UID_JPEGProcess11_13TransferSyntax); + transferSyntaxes.push_back(UID_JPEGProcess14TransferSyntax); + transferSyntaxes.push_back(UID_JPEGProcess15TransferSyntax); + transferSyntaxes.push_back(UID_JPEGProcess16_18TransferSyntax); + transferSyntaxes.push_back(UID_JPEGProcess17_19TransferSyntax); + transferSyntaxes.push_back(UID_JPEGProcess20_22TransferSyntax); + transferSyntaxes.push_back(UID_JPEGProcess21_23TransferSyntax); + transferSyntaxes.push_back(UID_JPEGProcess24_26TransferSyntax); + transferSyntaxes.push_back(UID_JPEGProcess25_27TransferSyntax); + transferSyntaxes.push_back(UID_JPEGProcess28TransferSyntax); + transferSyntaxes.push_back(UID_JPEGProcess29TransferSyntax); + transferSyntaxes.push_back(UID_JPEGProcess14SV1TransferSyntax); + transferSyntaxes.push_back(UID_JPEGLSLosslessTransferSyntax); + transferSyntaxes.push_back(UID_JPEGLSLossyTransferSyntax); + } + + if (!server.HasApplicationEntityFilter() || + server.GetApplicationEntityFilter().IsAllowedTransferSyntax(callingAet, TransferSyntax_Jpeg2000)) + { + transferSyntaxes.push_back(UID_JPEG2000LosslessOnlyTransferSyntax); + transferSyntaxes.push_back(UID_JPEG2000TransferSyntax); + } + + if (!server.HasApplicationEntityFilter() || + server.GetApplicationEntityFilter().IsAllowedTransferSyntax(callingAet, TransferSyntax_JpegLossless)) + { + transferSyntaxes.push_back(UID_JPEG2000LosslessOnlyTransferSyntax); + transferSyntaxes.push_back(UID_JPEG2000TransferSyntax); + transferSyntaxes.push_back(UID_JPEG2000Part2MulticomponentImageCompressionLosslessOnlyTransferSyntax); + transferSyntaxes.push_back(UID_JPEG2000Part2MulticomponentImageCompressionTransferSyntax); + } + + if (!server.HasApplicationEntityFilter() || + server.GetApplicationEntityFilter().IsAllowedTransferSyntax(callingAet, TransferSyntax_Jpip)) + { + transferSyntaxes.push_back(UID_JPIPReferencedTransferSyntax); + transferSyntaxes.push_back(UID_JPIPReferencedDeflateTransferSyntax); + } + + if (!server.HasApplicationEntityFilter() || + server.GetApplicationEntityFilter().IsAllowedTransferSyntax(callingAet, TransferSyntax_Mpeg2)) + { + transferSyntaxes.push_back(UID_MPEG2MainProfileAtMainLevelTransferSyntax); + transferSyntaxes.push_back(UID_MPEG2MainProfileAtHighLevelTransferSyntax); + } + + if (!server.HasApplicationEntityFilter() || + server.GetApplicationEntityFilter().IsAllowedTransferSyntax(callingAet, TransferSyntax_Rle)) + { + transferSyntaxes.push_back(UID_RLELosslessTransferSyntax); + } /* accept the Verification SOP Class if presented */ cond = ASC_acceptContextsWithPreferredTransferSyntaxes(assoc->params, &knownAbstractSyntaxes[0], knownAbstractSyntaxes.size(), &transferSyntaxes[0], transferSyntaxes.size()); @@ -555,62 +622,38 @@ return NULL; } - std::string callingIP; - std::string callingTitle; - /* check the AETs */ + if (!server.IsMyAETitle(calledAet)) { - DIC_AE callingTitle_C; - DIC_AE calledTitle_C; - DIC_AE callingIP_C; - DIC_AE calledIP_C; - if (ASC_getAPTitles(assoc->params, callingTitle_C, calledTitle_C, NULL).bad() || - ASC_getPresentationAddresses(assoc->params, callingIP_C, calledIP_C).bad()) - { - T_ASC_RejectParameters rej = - { - ASC_RESULT_REJECTEDPERMANENT, - ASC_SOURCE_SERVICEUSER, - ASC_REASON_SU_NOREASON - }; - ASC_rejectAssociation(assoc, &rej); - AssociationCleanup(assoc); - return NULL; - } - - callingIP = std::string(/*OFSTRING_GUARD*/(callingIP_C)); - callingTitle = std::string(/*OFSTRING_GUARD*/(callingTitle_C)); - std::string calledTitle(/*OFSTRING_GUARD*/(calledTitle_C)); - - if (!server.IsMyAETitle(calledTitle)) - { - T_ASC_RejectParameters rej = - { - ASC_RESULT_REJECTEDPERMANENT, - ASC_SOURCE_SERVICEUSER, - ASC_REASON_SU_CALLEDAETITLENOTRECOGNIZED - }; - ASC_rejectAssociation(assoc, &rej); - AssociationCleanup(assoc); - return NULL; - } - - if (server.HasApplicationEntityFilter() && - !server.GetApplicationEntityFilter().IsAllowedConnection(callingIP, callingTitle)) - { - T_ASC_RejectParameters rej = - { - ASC_RESULT_REJECTEDPERMANENT, - ASC_SOURCE_SERVICEUSER, - ASC_REASON_SU_CALLINGAETITLENOTRECOGNIZED - }; - ASC_rejectAssociation(assoc, &rej); - AssociationCleanup(assoc); - return NULL; - } + LOG(WARNING) << "Rejected association, because of a bad called AET in the request (" << calledAet << ")"; + T_ASC_RejectParameters rej = + { + ASC_RESULT_REJECTEDPERMANENT, + ASC_SOURCE_SERVICEUSER, + ASC_REASON_SU_CALLEDAETITLENOTRECOGNIZED + }; + ASC_rejectAssociation(assoc, &rej); + AssociationCleanup(assoc); + return NULL; } - if (opt_rejectWithoutImplementationUID && strlen(assoc->params->theirImplementationClassUID) == 0) + if (server.HasApplicationEntityFilter() && + !server.GetApplicationEntityFilter().IsAllowedConnection(callingIP, callingAet)) + { + LOG(WARNING) << "Rejected association for remote AET " << callingAet << " on IP " << callingIP; + T_ASC_RejectParameters rej = + { + ASC_RESULT_REJECTEDPERMANENT, + ASC_SOURCE_SERVICEUSER, + ASC_REASON_SU_CALLINGAETITLENOTRECOGNIZED + }; + ASC_rejectAssociation(assoc, &rej); + AssociationCleanup(assoc); + return NULL; + } + + if (opt_rejectWithoutImplementationUID && + strlen(assoc->params->theirImplementationClassUID) == 0) { /* reject: the no implementation Class UID provided */ T_ASC_RejectParameters rej = @@ -644,7 +687,7 @@ } IApplicationEntityFilter* filter = server.HasApplicationEntityFilter() ? &server.GetApplicationEntityFilter() : NULL; - return new CommandDispatcher(server, assoc, callingIP, callingTitle, filter); + return new CommandDispatcher(server, assoc, callingIP, callingAet, filter); } bool CommandDispatcher::Step() diff -r 80671157d051 -r 3db41779d8f9 OrthancServer/ServerEnumerations.cpp --- a/OrthancServer/ServerEnumerations.cpp Wed Sep 17 11:57:28 2014 +0200 +++ b/OrthancServer/ServerEnumerations.cpp Wed Sep 17 17:23:08 2014 +0200 @@ -324,7 +324,6 @@ return "Store"; break; - default: throw OrthancException(ErrorCode_ParameterOutOfRange); } @@ -359,4 +358,36 @@ throw OrthancException(ErrorCode_ParameterOutOfRange); } } + + + const char* EnumerationToString(TransferSyntax syntax) + { + switch (syntax) + { + case TransferSyntax_Deflated: + return "Deflated"; + + case TransferSyntax_Jpeg: + return "JPEG"; + + case TransferSyntax_Jpeg2000: + return "JPEG2000"; + + case TransferSyntax_JpegLossless: + return "JPEG Lossless"; + + case TransferSyntax_Jpip: + return "JPIP"; + + case TransferSyntax_Mpeg2: + return "MPEG2"; + + case TransferSyntax_Rle: + return "RLE"; + + default: + throw OrthancException(ErrorCode_ParameterOutOfRange); + } + } + } diff -r 80671157d051 -r 3db41779d8f9 OrthancServer/ServerEnumerations.h --- a/OrthancServer/ServerEnumerations.h Wed Sep 17 11:57:28 2014 +0200 +++ b/OrthancServer/ServerEnumerations.h Wed Sep 17 17:23:08 2014 +0200 @@ -79,6 +79,17 @@ DicomReplaceMode_IgnoreIfAbsent }; + enum TransferSyntax + { + TransferSyntax_Deflated, + TransferSyntax_Jpeg, + TransferSyntax_Jpeg2000, + TransferSyntax_JpegLossless, + TransferSyntax_Jpip, + TransferSyntax_Mpeg2, + TransferSyntax_Rle + }; + /** * WARNING: Do not change the explicit values in the enumerations @@ -157,6 +168,8 @@ const char* EnumerationToString(DicomRequestType type); + const char* EnumerationToString(TransferSyntax syntax); + ModalityManufacturer StringToModalityManufacturer(const std::string& manufacturer); ResourceType GetParentResourceType(ResourceType type); diff -r 80671157d051 -r 3db41779d8f9 OrthancServer/main.cpp --- a/OrthancServer/main.cpp Wed Sep 17 11:57:28 2014 +0200 +++ b/OrthancServer/main.cpp Wed Sep 17 17:23:08 2014 +0200 @@ -177,6 +177,13 @@ return true; } } + + virtual bool IsAllowedTransferSyntax(const std::string& callingAet, + TransferSyntax syntax) + { + // TODO - https://trello.com/c/8GxcTR0n + return true; + } };