comparison Core/DicomNetworking/Internals/CommandDispatcher.cpp @ 3965:7f296ae25039

reviewed CommandDispatcher.cpp
author Sebastien Jodogne <s.jodogne@gmail.com>
date Fri, 22 May 2020 08:33:26 +0200
parents 821715370890
children b3f09bc9734b
comparison
equal deleted inserted replaced
3964:821715370890 3965:7f296ae25039
101 #include <dcmtk/dcmdata/dcuid.h> /* for variable dcmAllStorageSOPClassUIDs */ 101 #include <dcmtk/dcmdata/dcuid.h> /* for variable dcmAllStorageSOPClassUIDs */
102 #include <dcmtk/dcmnet/dcasccfg.h> /* for class DcmAssociationConfiguration */ 102 #include <dcmtk/dcmnet/dcasccfg.h> /* for class DcmAssociationConfiguration */
103 103
104 #include <boost/lexical_cast.hpp> 104 #include <boost/lexical_cast.hpp>
105 105
106 static OFBool opt_rejectWithoutImplementationUID = OFFalse; 106 static OFBool opt_rejectWithoutImplementationUID = OFFalse;
107 107
108 108
109 109
110 static DUL_PRESENTATIONCONTEXT * 110 static DUL_PRESENTATIONCONTEXT *
111 findPresentationContextID(LST_HEAD * head, 111 findPresentationContextID(LST_HEAD * head,
274 T_ASC_Association *assoc; 274 T_ASC_Association *assoc;
275 OFCondition cond; 275 OFCondition cond;
276 OFString sprofile; 276 OFString sprofile;
277 OFString temp_str; 277 OFString temp_str;
278 278
279
280
281 cond = ASC_receiveAssociation(net, &assoc, 279 cond = ASC_receiveAssociation(net, &assoc,
282 /*opt_maxPDU*/ ASC_DEFAULTMAXPDU, 280 /*opt_maxPDU*/ ASC_DEFAULTMAXPDU,
283 NULL, NULL, 281 NULL, NULL,
284 /*opt_secureConnection*/ OFFalse, 282 /*opt_secureConnection*/ OFFalse,
285 DUL_NOBLOCK, 1); 283 DUL_NOBLOCK, 1);
311 DIC_AE remoteIp_C; 309 DIC_AE remoteIp_C;
312 DIC_AE calledIP_C; 310 DIC_AE calledIP_C;
313 311
314 if ( 312 if (
315 #if DCMTK_VERSION_NUMBER >= 364 313 #if DCMTK_VERSION_NUMBER >= 364
316 ASC_getAPTitles(assoc->params, remoteAet_C, sizeof(remoteAet_C), calledAet_C, sizeof(calledAet_C), NULL, 0).bad() || 314 ASC_getAPTitles(assoc->params, remoteAet_C, sizeof(remoteAet_C), calledAet_C, sizeof(calledAet_C), NULL, 0).bad() ||
317 ASC_getPresentationAddresses(assoc->params, remoteIp_C, sizeof(remoteIp_C), calledIP_C, sizeof(calledIP_C)).bad() 315 ASC_getPresentationAddresses(assoc->params, remoteIp_C, sizeof(remoteIp_C), calledIP_C, sizeof(calledIP_C)).bad()
318 #else 316 #else
319 ASC_getAPTitles(assoc->params, remoteAet_C, calledAet_C, NULL).bad() || 317 ASC_getAPTitles(assoc->params, remoteAet_C, calledAet_C, NULL).bad() ||
320 ASC_getPresentationAddresses(assoc->params, remoteIp_C, calledIP_C).bad() 318 ASC_getPresentationAddresses(assoc->params, remoteIp_C, calledIP_C).bad()
321 #endif 319 #endif
322 ) 320 )
323 { 321 {
324 T_ASC_RejectParameters rej = 322 T_ASC_RejectParameters rej =
325 { 323 {
326 ASC_RESULT_REJECTEDPERMANENT, 324 ASC_RESULT_REJECTEDPERMANENT,
327 ASC_SOURCE_SERVICEUSER, 325 ASC_SOURCE_SERVICEUSER,
372 if (server.HasMoveRequestHandlerFactory()) 370 if (server.HasMoveRequestHandlerFactory())
373 { 371 {
374 knownAbstractSyntaxes.push_back(UID_MOVEStudyRootQueryRetrieveInformationModel); 372 knownAbstractSyntaxes.push_back(UID_MOVEStudyRootQueryRetrieveInformationModel);
375 knownAbstractSyntaxes.push_back(UID_MOVEPatientRootQueryRetrieveInformationModel); 373 knownAbstractSyntaxes.push_back(UID_MOVEPatientRootQueryRetrieveInformationModel);
376 } 374 }
377 375
378 // For C-GET 376 // For C-GET
379 if (server.HasGetRequestHandlerFactory()) 377 if (server.HasGetRequestHandlerFactory())
380 { 378 {
381 knownAbstractSyntaxes.push_back(UID_GETStudyRootQueryRetrieveInformationModel); 379 knownAbstractSyntaxes.push_back(UID_GETStudyRootQueryRetrieveInformationModel);
382 knownAbstractSyntaxes.push_back(UID_GETPatientRootQueryRetrieveInformationModel); 380 knownAbstractSyntaxes.push_back(UID_GETPatientRootQueryRetrieveInformationModel);
383 } 381 }
384
385 382
386 cond = ASC_acceptContextsWithPreferredTransferSyntaxes( 383 cond = ASC_acceptContextsWithPreferredTransferSyntaxes(
387 assoc->params, 384 assoc->params,
388 &knownAbstractSyntaxes[0], knownAbstractSyntaxes.size(), 385 &knownAbstractSyntaxes[0], knownAbstractSyntaxes.size(),
389 &genericTransferSyntaxes[0], genericTransferSyntaxes.size()); 386 &genericTransferSyntaxes[0], genericTransferSyntaxes.size());
520 // only published if DCMTK >= 3.6.2: 517 // only published if DCMTK >= 3.6.2:
521 // https://bitbucket.org/sjodogne/orthanc/issues/137 518 // https://bitbucket.org/sjodogne/orthanc/issues/137
522 assert(static_cast<int>(count) == numberOfDcmAllStorageSOPClassUIDs); 519 assert(static_cast<int>(count) == numberOfDcmAllStorageSOPClassUIDs);
523 #endif 520 #endif
524 521
525 // now that C-GET SCP is always enabled, the first branch of this if is useless 522 if (!server.HasGetRequestHandlerFactory()) // dcmqrsrv.cc line 828
526 // TO BE ANALYZED by SJ 523 {
527 if (!server.HasGetRequestHandlerFactory()) // dcmqrsrv.cc line 828 524 // This branch exactly corresponds to Orthanc <= 1.6.1 (in
528 { 525 // which C-GET SCP was not supported)
529 cond = ASC_acceptContextsWithPreferredTransferSyntaxes( 526 cond = ASC_acceptContextsWithPreferredTransferSyntaxes(
530 assoc->params, 527 assoc->params, dcmAllStorageSOPClassUIDs, count,
531 dcmAllStorageSOPClassUIDs, count, 528 &storageTransferSyntaxes[0], storageTransferSyntaxes.size());
532 &storageTransferSyntaxes[0], storageTransferSyntaxes.size()); 529 if (cond.bad())
533 if (cond.bad())
534 {
535 LOG(INFO) << cond.text();
536 AssociationCleanup(assoc);
537 return NULL;
538 }
539 }
540 else // see dcmqrsrv.cc lines 839 - 876
541 {
542 /* accept storage syntaxes with proposed role */
543 T_ASC_PresentationContext pc;
544 T_ASC_SC_ROLE role;
545 int npc = ASC_countPresentationContexts(assoc->params);
546 for (int i = 0; i < npc; i++)
547 {
548 ASC_getPresentationContext(assoc->params, i, &pc);
549 if (dcmIsaStorageSOPClassUID(pc.abstractSyntax))
550 { 530 {
551 /* 531 LOG(INFO) << cond.text();
552 ** We are prepared to accept whatever role the caller proposes. 532 AssociationCleanup(assoc);
553 ** Normally we can be the SCP of the Storage Service Class. 533 return NULL;
554 ** When processing the C-GET operation we can be the SCU of the Storage Service Class. 534 }
555 */ 535 }
556 role = pc.proposedRole; 536 else // see dcmqrsrv.cc lines 839 - 876
537 {
538 /* accept storage syntaxes with proposed role */
539 int npc = ASC_countPresentationContexts(assoc->params);
540 for (int i = 0; i < npc; i++)
541 {
542 T_ASC_PresentationContext pc;
543 ASC_getPresentationContext(assoc->params, i, &pc);
544 if (dcmIsaStorageSOPClassUID(pc.abstractSyntax))
545 {
546 /**
547 * We are prepared to accept whatever role the caller
548 * proposes. Normally we can be the SCP of the Storage
549 * Service Class. When processing the C-GET operation
550 * we can be the SCU of the Storage Service Class.
551 **/
552 const T_ASC_SC_ROLE role = pc.proposedRole;
557 553
558 /* 554 /**
559 ** Accept in the order "least wanted" to "most wanted" transfer 555 * Accept in the order "least wanted" to "most wanted"
560 ** syntax. Accepting a transfer syntax will override previously 556 * transfer syntax. Accepting a transfer syntax will
561 ** accepted transfer syntaxes. 557 * override previously accepted transfer syntaxes.
562 */ 558 **/
563 for (int k = (int) storageTransferSyntaxes.size() - 1; k >= 0; k--) 559 for (int k = static_cast<int>(storageTransferSyntaxes.size()) - 1; k >= 0; k--)
564 {
565 for (int j = 0; j < (int)pc.transferSyntaxCount; j++)
566 { 560 {
567 /* if the transfer syntax was proposed then we can accept it 561 for (int j = 0; j < static_cast<int>(pc.transferSyntaxCount); j++)
568 * appears in our supported list of transfer syntaxes
569 */
570 if (strcmp(pc.proposedTransferSyntaxes[j], storageTransferSyntaxes[k]) == 0)
571 { 562 {
572 cond = ASC_acceptPresentationContext( 563 /**
573 assoc->params, pc.presentationContextID, storageTransferSyntaxes[k], role); 564 * If the transfer syntax was proposed then we can accept it
574 if (cond.bad()) 565 * appears in our supported list of transfer syntaxes
566 **/
567 if (strcmp(pc.proposedTransferSyntaxes[j], storageTransferSyntaxes[k]) == 0)
575 { 568 {
576 LOG(INFO) << cond.text(); 569 cond = ASC_acceptPresentationContext(
577 AssociationCleanup(assoc); 570 assoc->params, pc.presentationContextID, storageTransferSyntaxes[k], role);
578 return NULL; 571 if (cond.bad())
572 {
573 LOG(INFO) << cond.text();
574 AssociationCleanup(assoc);
575 return NULL;
576 }
579 } 577 }
580 } 578 }
581 } 579 }
582 } 580 }
583 } 581 } /* for */
584 } /* for */ 582 }
585
586 }
587
588 583
589 if (!server.HasApplicationEntityFilter() || 584 if (!server.HasApplicationEntityFilter() ||
590 server.GetApplicationEntityFilter().IsUnknownSopClassAccepted(remoteIp, remoteAet, calledAet)) 585 server.GetApplicationEntityFilter().IsUnknownSopClassAccepted(remoteIp, remoteAet, calledAet))
591 { 586 {
592 /* 587 /*