/*[]=====================================================================[]*/ /*[] LeadTools Run Time Library - Version 11 []*/ /*[] []*/ /*[] []*/ /*[] Copyright (c) 1991-2000 LEAD Technologies, Inc. []*/ /*[] All Rights Reserved. []*/ /*[] []*/ /*[] commun.c []*/ /*[]=====================================================================[]*/ #include "commun.h" #include "utils.h" #include "extern.h" //#include "globals.h" #include "draw.h" #include "process.h" CODETEXT CommandGlobal[] = { { COMMAND_C_STORE | COMMAND_REQUEST, "C-STORE-RQ" }, { COMMAND_C_FIND | COMMAND_REQUEST, "C-FIND-RQ" }, { COMMAND_C_GET | COMMAND_REQUEST, "C-GET-RQ" }, { COMMAND_C_MOVE | COMMAND_REQUEST, "C-MOVE-RQ" }, { COMMAND_C_CANCEL | COMMAND_REQUEST, "C-CANCEL-RQ" }, { COMMAND_C_ECHO | COMMAND_REQUEST, "C-ECHO-RQ" }, { COMMAND_N_REPORT | COMMAND_REQUEST, "N-REPORT-RQ" }, { COMMAND_N_GET | COMMAND_REQUEST, "N-GET-RQ" }, { COMMAND_N_SET | COMMAND_REQUEST, "N-SET-RQ" }, { COMMAND_N_ACTION | COMMAND_REQUEST, "N-ACTION-RQ" }, { COMMAND_N_CREATE | COMMAND_REQUEST, "N-CREATE-RQ" }, { COMMAND_N_DELETE | COMMAND_REQUEST, "N-DELETE-RQ" }, { COMMAND_C_STORE | COMMAND_RESPONSE, "C-STORE-RSP" }, { COMMAND_C_FIND | COMMAND_RESPONSE, "C-FIND-RSP" }, { COMMAND_C_GET | COMMAND_RESPONSE, "C-GET-RSP" }, { COMMAND_C_MOVE | COMMAND_RESPONSE, "C-MOVE-RSP" }, { COMMAND_C_CANCEL | COMMAND_RESPONSE, "C-CANCEL-RSP" }, { COMMAND_C_ECHO | COMMAND_RESPONSE, "C-ECHO-RSP" }, { COMMAND_N_REPORT | COMMAND_RESPONSE, "N-REPORT-RSP" }, { COMMAND_N_GET | COMMAND_RESPONSE, "N-GET-RSP" }, { COMMAND_N_SET | COMMAND_RESPONSE, "N-SET-RSP" }, { COMMAND_N_ACTION | COMMAND_RESPONSE, "N-ACTION-RSP" }, { COMMAND_N_CREATE | COMMAND_RESPONSE, "N-CREATE-RSP" }, { COMMAND_N_DELETE | COMMAND_RESPONSE, "N-DELETE-RSP" }, }; //hParent --TreeView parent to place item //i --Presentation Number (1,2,3,4 ...) //hAssociate --Associate request or associate accept object //bRequest --TRUE if associate request object, FALSE if associate accept object L_VOID DisplayAssociatePresentation(HTREEITEM hParent, L_INT i, HDICOMPDU hAssociate, L_BOOL bRequest) { L_CHAR szTmp[MAX_STRING_LEN]; L_UCHAR nID; L_UCHAR uResult; L_CHAR *szAbstract; L_CHAR *szResult; L_CHAR *szTransferSyntax; L_UCHAR *szExtended; pDICOMUID pUID; L_INT j; HTREEITEM hChildRoot; L_INT iTransferCount; //ID nID = L_DicomGetPresentation(hAssociate, i); wsprintf(szTmp, "Presentation Context %d: ", nID); //Result szResult = ""; if (bRequest== FALSE) //if an associate accept object { uResult = L_DicomGetResult(hAssociate, nID); switch (uResult) { case PDU_ACCEPT_RESULT_SUCCESS: szResult = "Accept"; break; case PDU_ACCEPT_RESULT_USER_REJECT: szResult = "Reject(User)"; break; case PDU_ACCEPT_RESULT_PROVIDER_REJECT: szResult = "Reject(Provider)"; break; case PDU_ACCEPT_RESULT_ABSTRACT_SYNTAX: szResult = "No Support(Abstract Syntax)"; break; case PDU_ACCEPT_RESULT_TRANSFER_SYNTAX: szResult = "No Support(TransferSyntax)"; break; } } hChildRoot = LogMessageChild(hParent, szTmp, szResult); //Abstract Syntax szAbstract = L_DicomGetAbstract(hAssociate, nID); if (szAbstract != NULL) { pUID = L_DicomFindUID(szAbstract); if (pUID != NULL) wsprintf(szTmp, "Abstract Syntax: %s[%s]", pUID->pszName, szAbstract); else wsprintf(szTmp, "Abstract Syntax: [%s]", szAbstract); } else wsprintf(szTmp, "Unknown"); LogMessageChild(hChildRoot, szTmp, ""); //Transfer Syntax(s) iTransferCount = L_DicomGetTransferCount(hAssociate, nID); for (i=0; ipszName, szTransferSyntax); else wsprintf(szTmp,"Transfer Syntax: %s", szTransferSyntax); } LogMessageChild(hChildRoot, szTmp, ""); } if (L_DicomIsRoleSelect(hAssociate, nID)) { switch (L_DicomGetUserRole(hAssociate, nID)) { case PDU_ROLE_NON_SUPPORT: wsprintf(szTmp, "User Role: Non Support, "); break; case PDU_ROLE_SUPPORT: wsprintf(szTmp, "User Role: Support, "); break; default: wsprintf(szTmp, "User Role: Unknown, "); break; } switch (L_DicomGetProviderRole(hAssociate, nID)) { case PDU_ROLE_NON_SUPPORT: lstrcat(szTmp, "Provider Role: Non Support"); break; case PDU_ROLE_SUPPORT: lstrcat(szTmp, "Provider Role: Support"); break; default: lstrcat(szTmp, "Provider Role: Unknown"); break; } LogMessageChild(hChildRoot, szTmp, ""); } if (L_DicomGetLengthExtended(hAssociate, nID) != 0) { szExtended = L_DicomGetExtended(hAssociate, nID); if (szExtended != NULL) { L_CHAR szExtendedAll[MAX_STRING_LEN]; L_CHAR szTmp[MAX_STRING_LEN]; strcpy(szExtendedAll, ""); for (j = 0; j < (INT)L_DicomGetLengthExtended(hAssociate, nID); j++) { wsprintf(szTmp, "%X ", szExtendedAll[j]); lstrcat(szExtendedAll, szTmp); } LogMessageChild(hChildRoot, "Extended:", szExtendedAll); } } } //Displays associate accept info in the LogMessage TreeView L_VOID DisplayAssociate(L_UINT uMsgType, L_CHAR *szMsg, HDICOMNET hNet, HDICOMPDU hAssociate, L_BOOL bRequest) { L_INT i; L_BOOL bRet; L_CHAR szTmp[MAX_STRING_LEN]; HTREEITEM hItemRoot; hItemRoot = LogMessage(uMsgType, szMsg); wsprintf(szTmp, "hNet[%x]", hNet); LogMessageChild(hItemRoot, szTmp, ""); LogMessageChild(hItemRoot, "Called: ", L_DicomGetCalled(hAssociate)); LogMessageChild(hItemRoot, "Calling: ", L_DicomGetCalling(hAssociate)); wsprintf(szTmp, "Version: %d", L_DicomGetVersion(hAssociate) ); LogMessageChild(hItemRoot, szTmp, ""); wsprintf(szTmp, "%s", L_DicomGetApplication(hAssociate) ); LogMessageChild(hItemRoot, "Application Context: ", szTmp); bRet = L_DicomIsMaxLength(hAssociate); if (bRet) { wsprintf(szTmp, "Max Length: %d", L_DicomGetMaxLength(hAssociate) ); LogMessageChild(hItemRoot, szTmp, ""); } bRet = L_DicomIsImplementClass(hAssociate); if (bRet) LogMessageChild(hItemRoot, "Implement Class: ", L_DicomGetImplementClass(hAssociate)); bRet = L_DicomIsImplementVersion(hAssociate); if (bRet) LogMessageChild(hItemRoot, "Implement Version: ", L_DicomGetImplementVersion(hAssociate)); bRet = L_DicomIsAsyncOperations(hAssociate); if (bRet) { wsprintf(szTmp, "%d", L_DicomGetInvokedOperations(hAssociate) ); LogMessageChild(hItemRoot, "Invoked Operations: ", szTmp); wsprintf(szTmp, "%d", L_DicomGetPerformedOperations(hAssociate) ); LogMessageChild(hItemRoot, "Performed Operations: ", szTmp); } for (i = 0; i < L_DicomGetPresentationCount(hAssociate); i++) { DisplayAssociatePresentation(hItemRoot, i, hAssociate, bRequest); } } L_VOID DisplayDataSet(HDICOMDS hDS) { pDICOMELEMENT pElement; pDICOMTAG pTag; L_CHAR szMsg[MAX_STRING_LEN], szTmp[MAX_STRING_LEN]; L_CHAR *szDebug; if (hDS == NULL) return; lstrcpy(szMsg, "DEBUG--hDS\n"); //Get root element of tree pElement = L_DicomGetFirstElement(hDS, NULL, TRUE, FALSE); while (pElement != 0) { //add the node to the tree pTag = L_DicomFindTag(pElement->nTag); if (pTag == NULL) lstrcat(szMsg, "Item"); else lstrcat(szMsg, pTag->pszName); strcpy(szTmp, ""); wsprintf(szTmp, "[%x]: ", pElement->nVR); lstrcat(szMsg, szTmp); switch(pElement->nVR) { case VR_CS: case VR_LO: szDebug = L_DicomGetStringValue(hDS, pElement, 0, 1); if (szDebug != NULL) lstrcat(szMsg,szDebug ); else lstrcat(szMsg, "*******"); break; } lstrcat(szMsg, "\n"); pElement = L_DicomGetNextElement(hDS, pElement, TRUE, FALSE); } LogMessage(MSG_ERROR, szMsg); } L_VOID DisplayCommandSet(HDICOMNET hNet, HDICOMDS hCS) { pDICOMELEMENT pElement; pDICOMTAG pTag; L_CHAR szMsg[MAX_STRING_LEN], szTmp[MAX_STRING_LEN]; L_UINT16 *pCommand,nCommand; L_INT i; L_UINT uLogMessageType; if (hCS == NULL) return; //Get the Command strcpy(szMsg, ""); pElement = L_DicomFindFirstElement(hCS, NULL, TAG_COMMAND_FIELD, TRUE); pCommand = L_DicomGetShortValue(hCS, pElement, 0, 1); if (pCommand != NULL) { nCommand = *pCommand; //Get the text of the command wsprintf(szMsg, "Unknown %u\n", nCommand); uLogMessageType = MSG_NONE; for (i=0; i< sizeof(CommandGlobal)/sizeof(CommandGlobal[0]); i++) { if (nCommand == (L_UINT16)CommandGlobal[i].nCode) { if ((nCommand & COMMAND_REQUEST) != 0) uLogMessageType = MSG_SEND; else uLogMessageType = MSG_RECEIVE; wsprintf(szMsg, "%s\n", CommandGlobal[i].pszText); break; } } } //Get root element of tree pElement = L_DicomGetFirstElement(hCS, NULL, TRUE, FALSE); while (pElement != 0) { //add the node to the tree pTag = L_DicomFindTag(pElement->nTag); if (pTag == NULL) lstrcat(szMsg, "Item"); else lstrcat(szMsg, pTag->pszName); //get the values and display them strcpy(szTmp, ""); L_DicomGetConvertValue(hCS, pElement, szTmp); lstrcat(szMsg, ": "); lstrcat(szMsg, szTmp); lstrcat(szMsg, "\n"); //move to next node in same level (if one) pElement = L_DicomGetNextElement(hCS, pElement, TRUE, FALSE); } LogMessage(uLogMessageType, szMsg); } L_VOID DisplayTree(HWND hTreeView, HDICOMDS hDS, HTREEITEM hParentTree, pDICOMELEMENT pParentElement, L_UINT16 nFlags) { pDICOMELEMENT pElement; pDICOMELEMENT pChild; pDICOMELEMENT pTemp; HTREEITEM hItem; L_CHAR szText[MAX_STRING_LEN]; L_CHAR *pszText; L_CHAR szValue[MAX_STRING_LEN]; pDICOMTAG pTag; L_UINT32 nLength; TV_INSERTSTRUCT tv; if ((pParentElement != NULL) && (L_DicomExistsElement(hDS, pParentElement) == FALSE)) { return; } if (nFlags & DISPLAY_TREE_DIRECTORY) { pElement = (pParentElement == NULL) ? L_DicomGetFirstKey(hDS, NULL, TRUE) : L_DicomGetChildKey(hDS, pParentElement); } else { pElement = (pParentElement == NULL) ? L_DicomGetFirstElement(hDS, NULL, TRUE, FALSE) : L_DicomGetChildElement(hDS, pParentElement, FALSE); } while (pElement != NULL) { if (nFlags & DISPLAY_TREE_DIRECTORY) { pszText = L_DicomGetValueKey(hDS, pElement); strcpy(szText, (pszText != NULL) ? pszText : "UNKNOWN: "); lstrcat(szText, ": "); pChild = L_DicomGetChildElement(hDS, pElement, TRUE); if ((pChild != NULL) && (pszText != NULL)) { if (lstrcmp(pszText, "PATIENT") == 0) { pTemp = L_DicomFindFirstElement(hDS, pChild, TAG_PATIENT_ID, TRUE); if (pTemp != NULL) { pszText = L_DicomGetStringValue(hDS, pTemp, 0, 1); if (pszText != NULL) { lstrcat(szText, pszText); lstrcat(szText, " "); } } pTemp = L_DicomFindFirstElement(hDS, pChild, TAG_PATIENT_NAME, TRUE); if (pTemp != NULL) { pszText = L_DicomGetStringValue(hDS, pTemp, 0, 1); if (pszText != NULL) { lstrcat(szText, pszText); } } } else if (lstrcmp(pszText, "STUDY") == 0) { pTemp = L_DicomFindFirstElement(hDS, pChild, TAG_STUDY_ID, TRUE); if (pTemp != NULL) { pszText = L_DicomGetStringValue(hDS, pTemp, 0, 1); if (pszText != NULL) { lstrcat(szText, pszText); lstrcat(szText, " "); } } pTemp = L_DicomFindFirstElement(hDS, pChild, TAG_PATIENT_NAME, TRUE); if (pTemp != NULL) { pszText = L_DicomGetStringValue(hDS, pTemp, 0, 1); if (pszText != NULL) { lstrcat(szText, pszText); } } } else if (lstrcmp(pszText, "SERIES") == 0) { pTemp = L_DicomFindFirstElement(hDS, pChild, TAG_SERIES_NUMBER, TRUE); if (pTemp != NULL) { L_DicomGetConvertValue(hDS, pTemp, szValue); lstrcat(szText, szValue); lstrcat(szText, " "); } } else if (strcmp(pszText, "INSTANCE") == 0) { pTemp = L_DicomFindFirstElement(hDS, pChild, TAG_INSTANCE_NUMBER, TRUE); if (pTemp != NULL) { L_DicomGetConvertValue(hDS, pTemp, szValue); lstrcat(szText, szValue); } } } } else { pTag = L_DicomFindTag(pElement->nTag); wsprintf(szText, "%04X:%04X - %s", GETGROUP(pElement->nTag), GETELEMENT(pElement->nTag), (pTag != NULL) ? pTag->pszName : "Unknown"); } if ((nFlags & DISPLAY_TREE_VALUES) && (pElement->nLength != 0) && (pElement->nLength != ELEMENT_LENGTH_MAX)) { nLength = L_DicomGetConvertValue(hDS, pElement, NULL); if (nLength < sizeof(szValue)) { L_DicomGetConvertValue(hDS, pElement, szValue); lstrcat(szText, ": "); lstrcat(szText, szValue); } } //add items to tree view tv.hInsertAfter= TVI_LAST; tv.item.mask = TVIF_TEXT | TVIF_IMAGE | TVIF_SELECTEDIMAGE | TVIF_PARAM; tv.hParent = hParentTree; tv.item.pszText = szText; tv.item.iImage = 0; tv.item.iSelectedImage = 0; tv.item.lParam = (DWORD)pElement; hItem = TreeView_InsertItem(hTreeView, &tv); if (nFlags & DISPLAY_TREE_DIRECTORY) { TV_SetItemState(hTreeView, hItem, TVIS_BOLD, TVIS_BOLD); } if (nFlags & DISPLAY_TREE_EXPANDED) { TV_SetItemState(hTreeView, hItem, TVIS_EXPANDED, TVIS_EXPANDED); } if (nFlags & DISPLAY_TREE_DIRECTORY) { if (L_DicomGetChildKey(hDS, pElement) != NULL) { DisplayTree(hTreeView, hDS, hItem, pElement, nFlags); } } else { if (L_DicomGetChildElement(hDS, pElement, FALSE) != NULL) { L_UINT16 uTempFlags; uTempFlags = nFlags & (~DISPLAY_TREE_DIRECTORY); DisplayTree(hTreeView, hDS, hItem, pElement, uTempFlags); } } if (nFlags & DISPLAY_TREE_DIRECTORY) { pElement = L_DicomGetNextKey(hDS, pElement, TRUE); } else { pElement = L_DicomGetNextElement(hDS, pElement, nFlags & (~DISPLAY_TREE_VALUES), TRUE); } } } L_VOID DeleteEmpty(HDICOMDS hDS, pDICOMELEMENT pParent) { pDICOMELEMENT pElement; pDICOMELEMENT pTemp; pElement = (pParent == NULL) ? L_DicomGetFirstElement(hDS, NULL, TRUE, FALSE) : L_DicomGetChildElement(hDS, pParent, FALSE); while (pElement != NULL) { if (L_DicomGetChildElement(hDS, pElement, FALSE) != NULL) { DeleteEmpty(hDS, pElement); } pTemp = L_DicomGetParentElement(hDS, pElement); if ((pElement->nTag == TAG_DIRECTORY_RECORD_SEQUENCE) || ((pElement->nTag == TAG_ITEM) && (pTemp != NULL) && (pTemp->nTag == TAG_DIRECTORY_RECORD_SEQUENCE)) || ((pElement->nLength != 0) && (pElement->nLength != ELEMENT_LENGTH_MAX)) || ((pElement->nLength == ELEMENT_LENGTH_MAX) && (L_DicomGetChildElement(hDS, pElement, FALSE) != NULL))) { pElement = L_DicomGetNextElement(hDS, pElement, TRUE, FALSE); } else { pTemp = pElement; pElement = L_DicomGetNextElement(hDS, pElement, TRUE, FALSE); L_DicomDeleteElement(hDS, pTemp); } } } // Unsupported Abstract and Transfer Syntaxes L_CHAR* UnsupportedUIDs[] = { // Abstract Syntaxes UID_BASIC_STUDY_NOTIFICATION_CLASS UID_APPLICATION_CONTEXT_NAME UID_MODALITY_PERFORMED_CLASS UID_MODALITY_PERFORMED_RETRIEVE_CLASS UID_MODALITY_PERFORMED_NOTIFICATION_CLASS UID_BASIC_FILM_SESSION_CLASS UID_BASIC_FILM_BOX_CLASS UID_BASIC_GRAYSCALE_IMAGE_BOX_CLASS UID_BASIC_COLOR_IMAGE_BOX_CLASS UID_REFERENCED_IMAGE_BOX_CLASS_RETIRED UID_BASIC_GRAYSCALE_PRINT_META_CLASS UID_REFERENCED_GRAYSCALE_PRINT_META_CLASS_RETIRED UID_PRINT_JOB_CLASS UID_BASIC_ANNOTATION_BOX_CLASS UID_PRINTER_CLASS UID_PRINTER_CONFIGURATION_RETRIEVAL_CLASS UID_PRINTER_INSTANCE UID_PRINTER_CONFIGURATION_RETRIEVAL_INSTANCE UID_BASIC_COLOR_PRINT_META_CLASS UID_REFERENCED_COLOR_PRINT_META_CLASS_RETIRED UID_VOI_LUT_BOX_CLASS_RETIRED UID_PRESENTATION_LUT_CLASS UID_IMAGE_OVERLAY_BOX_CLASS_RETIRED UID_BASIC_PRINT_IMAGE_OVERLAY_BOX_CLASS UID_PRINT_QUEUE_INSTANCE UID_PRINT_QUEUE_CLASS UID_PULL_PRINT_REQUEST_CLASS UID_PULL_STORED_PRINT_META_CLASS UID_PATIENT_ROOT_QUERY_FIND UID_PATIENT_ROOT_QUERY_MOVE UID_PATIENT_ROOT_QUERY_GET UID_STUDY_ROOT_QUERY_FIND UID_STUDY_ROOT_QUERY_MOVE UID_STUDY_ROOT_QUERY_GET UID_PATIENT_STUDY_QUERY_FIND UID_PATIENT_STUDY_QUERY_MOVE UID_PATIENT_STUDY_QUERY_GET UID_MODALITY_WORKLIST_FIND UID_PAPYRUS_3_IMPLICIT_VR_LITTLE_ENDIAN // Transfer Syntaxes UID_JPEG_EXTENDED_3_5, UID_JPEG_SPECTRAL_NONHIER_6_8, UID_JPEG_SPECTRAL_NONHIER_7_9, UID_JPEG_FULL_NONHIER_10_12, UID_JPEG_FULL_NONHIER_11_13, UID_JPEG_LOSSLESS_NONHIER_15, UID_JPEG_EXTENDED_HIER_16_18, UID_JPEG_EXTENDED_HIER_17_19, UID_JPEG_SPECTRAL_HIER_20_22, UID_JPEG_SPECTRAL_HIER_21_23, UID_JPEG_FULL_HIER_24_26, UID_JPEG_FULL_HIER_25_27, UID_JPEG_LOSSLESS_HIER_PROCESS_28, UID_JPEG_LOSSLESS_HIER_PROCESS_29, UID_JPEG_LS_LOSSLESS, UID_JPEG_LS_LOSSY }; L_BOOL IsSupported(L_CHAR* pszUID) { int iCount, i; iCount = sizeof(UnsupportedUIDs) / sizeof(UnsupportedUIDs[0]); for (i = 0; i < iCount; i++) if (lstrcmp(pszUID, UnsupportedUIDs[i]) == 0) return FALSE; if (L_DicomFindUID(pszUID) == NULL) return FALSE; return TRUE; } HTREEITEM FindDirectoryRecord(HTREEITEM hDirItem, L_UINT32 uTag, const L_CHAR* pszIdentifier) { pDICOMELEMENT pElement, pDR; HTREEITEM hCurrentItem; hCurrentItem = hDirItem; while (hCurrentItem) { pDR = (pDICOMELEMENT) TV_GetItemData(hTreeDir, hCurrentItem); if (pDR != NULL && L_DicomExistsElement(hDSGlobal, pDR)) { pElement = L_DicomGetChildElement(hDSGlobal, pDR, TRUE); if (pElement) { pElement = L_DicomFindFirstElement(hDSGlobal, pElement, uTag, TRUE); if (pElement) { if (lstrcmp(L_DicomGetStringValue(hDSGlobal, pElement, 0, 1), pszIdentifier) == 0) { L_DicomFreeValue(hDSGlobal, pElement); return hCurrentItem; } } } } hCurrentItem = TreeView_GetNextItem(hTreeDir, hCurrentItem, TVGN_NEXT); } return NULL; } L_VOID FillDirectoryRecord(HDICOMDS hSrcDS, pDICOMELEMENT pDR) { pDICOMELEMENT pElement, pDRElement, pModuleElement; pDICOMMODULE pModule; L_UINT32 uModule, uLength, i; L_CHAR* pszDRType, * pszValue; if (pDR == NULL) return; pDRElement = L_DicomGetChildElement(hDSGlobal, pDR, TRUE); if (pDRElement == NULL) return; pszDRType = L_DicomGetValueKey(hDSGlobal, pDR); if (lstrcmpi("PATIENT", pszDRType) == 0) { uModule = MODULE_PATIENT; } else if (lstrcmpi("STUDY", pszDRType) == 0) { uModule = MODULE_GENERAL_STUDY; } else if (lstrcmpi("SERIES", pszDRType) == 0) { uModule = MODULE_GENERAL_SERIES; } else if (lstrcmpi("IMAGE", pszDRType) == 0) { uModule = MODULE_GENERAL_IMAGE; } else { return; } pModule = L_DicomFindModule(hSrcDS, uModule); if (pModule == NULL) return; for (i = 0; i < pModule->nCount; i++) { pModuleElement = pModule->pElement[i]; if (pModuleElement->nLength != 0 && pModuleElement->nLength != ELEMENT_LENGTH_MAX) { uLength = L_DicomGetConvertValue(hSrcDS, pModuleElement, NULL); if (uLength > 0) { pszValue = (L_CHAR*) malloc(uLength); if (pszValue) { L_DicomGetConvertValue(hSrcDS, pModuleElement, pszValue); pElement = L_DicomFindFirstElement(hDSGlobal, pDRElement, pModuleElement->nTag, TRUE); if (pElement == NULL) { pElement = L_DicomInsertElement(hDSGlobal, pDRElement, FALSE, pModuleElement->nTag, pModuleElement->nVR, FALSE, 0); } if (pElement) { L_DicomSetConvertValue(hDSGlobal, pElement, pszValue, 1); } free(pszValue); } L_DicomFreeValue(hSrcDS, pModuleElement); } } } if (uModule == MODULE_GENERAL_IMAGE) { pElement = L_DicomFindFirstElement(hDSGlobal, pDRElement, TAG_SOP_INSTANCE_UID, TRUE); if (pElement == NULL) { pElement = L_DicomInsertElement(hDSGlobal, pDRElement, FALSE, TAG_SOP_INSTANCE_UID, VR_UI, FALSE, 0); } if (pElement) { pDRElement = pElement; pElement = L_DicomFindFirstElement(hSrcDS, NULL, TAG_SOP_INSTANCE_UID, FALSE); if (pElement) { pszValue = L_DicomGetStringValue(hSrcDS, pElement, 0, 1); if (pszValue) { L_DicomSetStringValue(hDSGlobal, pDRElement, pszValue, 1); L_DicomFreeValue(hSrcDS, pElement); } } } } } HTREEITEM InsertDirTreeDR(HTREEITEM hParentItem, pDICOMELEMENT pDR) { pDICOMELEMENT pElement, pDRElement; L_CHAR szItemText[MAX_STRING_LEN], * pszDRType, * pszValue; TV_INSERTSTRUCT is; L_UINT32 uLength; if (pDR == NULL) return NULL; pszDRType = L_DicomGetValueKey(hDSGlobal, pDR); if (pszDRType == NULL) return NULL; wsprintf(szItemText, "%s: ", pszDRType); pDRElement = L_DicomGetChildElement(hDSGlobal, pDR, TRUE); if (pDRElement) { if (lstrcmpi("PATIENT", pszDRType) == 0) { pElement = L_DicomFindFirstElement(hDSGlobal, pDRElement, TAG_PATIENT_ID, TRUE); if (pElement) { pszValue = L_DicomGetStringValue(hDSGlobal, pElement, 0, 1); if (pszValue) { lstrcat(szItemText, pszValue); lstrcat(szItemText, " "); } L_DicomFreeValue(hDSGlobal, pElement); } pElement = L_DicomFindFirstElement(hDSGlobal, pDRElement, TAG_PATIENT_NAME, TRUE); if (pElement) { pszValue = L_DicomGetStringValue(hDSGlobal, pElement, 0, 1); if (pszValue) { lstrcat(szItemText, pszValue); } L_DicomFreeValue(hDSGlobal, pElement); } } else if (lstrcmpi("STUDY", pszDRType) == 0) { pElement = L_DicomFindFirstElement(hDSGlobal, pDRElement, TAG_STUDY_ID, TRUE); if (pElement) { pszValue = L_DicomGetStringValue(hDSGlobal, pElement, 0, 1); if (pszValue) { lstrcat(szItemText, pszValue); } L_DicomFreeValue(hDSGlobal, pElement); } } else if (lstrcmpi("SERIES", pszDRType) == 0) { pElement = L_DicomFindFirstElement(hDSGlobal, pDRElement, TAG_SERIES_NUMBER, TRUE); if (pElement) { uLength = L_DicomGetConvertValue(hDSGlobal, pElement, NULL); if (uLength > 0) { pszValue = (L_CHAR*) malloc(uLength); if (pszValue) { L_DicomGetConvertValue(hDSGlobal, pElement, pszValue); lstrcat(szItemText, pszValue); free(pszValue); } } L_DicomFreeValue(hDSGlobal, pElement); } } else if (lstrcmpi("IMAGE", pszDRType) == 0) { pElement = L_DicomFindFirstElement(hDSGlobal, pDRElement, TAG_INSTANCE_NUMBER, TRUE); if (pElement) { uLength = L_DicomGetConvertValue(hDSGlobal, pElement, NULL); if (uLength > 0) { pszValue = (L_CHAR*) malloc(uLength); if (pszValue) { L_DicomGetConvertValue(hDSGlobal, pElement, pszValue); lstrcat(szItemText, pszValue); free(pszValue); } } L_DicomFreeValue(hDSGlobal, pElement); } } } is.hParent = hParentItem; is.hInsertAfter = TVI_LAST; is.item.mask = TVIF_TEXT | TVIF_IMAGE | TVIF_SELECTEDIMAGE | TVIF_PARAM; is.item.pszText = szItemText; is.item.iImage = 0; is.item.iSelectedImage = 0; is.item.lParam = (LPARAM) pDR; return TreeView_InsertItem(hTreeDir, &is); } L_VOID SetIconImage(pDICOMELEMENT pImageDR, HDICOMDS hSrcDS) { pDICOMELEMENT pElement; DICOMIMAGE ImageInfo; L_INT32 nDestPhotometric= IMAGE_PHOTOMETRIC_MONOCHROME2; if (pImageDR == NULL || L_DicomExistsElement(hDSGlobal, pImageDR) == FALSE) return; pElement = L_DicomFindFirstElement(hSrcDS, NULL, TAG_PIXEL_DATA, FALSE); if (pElement == NULL) return; if (L_DicomGetInfoImage(hSrcDS, pElement, &ImageInfo, 0) != DICOM_SUCCESS) return; if (L_DicomGetImage( hSrcDS, pElement, &DicomBitmap, sizeof(BITMAPHANDLE), 0, 0, ORDER_BGRORGRAY, DICOM_GETIMAGE_AUTO_APPLY_MODALITY_LUT| DICOM_GETIMAGE_AUTO_APPLY_VOI_LUT| DICOM_GETIMAGE_ALLOW_RANGE_EXPANSION, NULL, NULL) != DICOM_SUCCESS) return; switch(ImageInfo.nPhotometric) { case IMAGE_PHOTOMETRIC_MONOCHROME1: case IMAGE_PHOTOMETRIC_MONOCHROME2: nDestPhotometric= IMAGE_PHOTOMETRIC_MONOCHROME2; break; case IMAGE_PHOTOMETRIC_PALETTE_COLOR: nDestPhotometric= IMAGE_PHOTOMETRIC_PALETTE_COLOR; break; case IMAGE_PHOTOMETRIC_RGB: case IMAGE_PHOTOMETRIC_ARGB: case IMAGE_PHOTOMETRIC_CMYK: case IMAGE_PHOTOMETRIC_YBR_FULL_422: case IMAGE_PHOTOMETRIC_YBR_FULL: nDestPhotometric= IMAGE_PHOTOMETRIC_RGB; break; } pElement = L_DicomInsertElement(hDSGlobal, pImageDR, TRUE, TAG_ICON_IMAGE_SEQUENCE, VR_SQ, TRUE, 0); if (pElement) { pElement = L_DicomInsertElement(hDSGlobal, pElement, TRUE, TAG_ITEM, VR_OB, TRUE, 0); if (pElement) { pElement = L_DicomInsertElement(hDSGlobal, pElement, TRUE, TAG_PIXEL_DATA, VR_OW, FALSE, 0); if (pElement) { L_DicomSetImage( hDSGlobal, pElement, &DicomBitmap, sizeof(BITMAPHANDLE), IMAGE_COMPRESSION_NONE, nDestPhotometric, 0, 0, NULL, NULL); } } } } L_VOID ConnectToServer(pCONNECTION pConnection) { L_CHAR szMsg[MAX_STRING_LEN]; L_INT nRet; L_INT j; switch (uSecureMode) { case DICOM_SECURE_NONE: wsprintf(szMsg,"Send Connect\nhNet[%x]", hNetGlobal); LogMessage(MSG_SEND, szMsg); StartProcess(PROCESS_CONNECT, 0); nRet = L_DicomConnect( hNetGlobal, pConnection->szClientIP, 0, //first available port pConnection->szServerIP, pConnection->uServerPort ); break; case DICOM_SECURE_ISCL: nRet = MessageBox(NULL, "Warning, trying to connect to a non-ISCL Secure Server may cause problems.\nDo you wish to continue?", "Warning", MB_YESNO); if(nRet==IDNO) return; wsprintf(szMsg,"Send Connect\nhNet[%x]", hNetGlobalISCL); LogMessage(MSG_SEND, szMsg); L_DicomSetMutualAuthAlgISCL(hNetGlobalISCL, uISCLAuthAlg); for (j = 0; j < 8; j++) { if (uISCLAuthKeys[j] != 0) { L_DicomSetMutualAuthKeyISCL(hNetGlobalISCL, j+1, uISCLAuthKeys[j]); } } L_DicomSetIndexForMutualAuthISCL(hNetGlobalISCL, uISCLAuthCurrentKey+1); L_DicomSetDefaultEncryptionISCL(hNetGlobalISCL, uISCLEncAlg); L_DicomSetDefaultSigningISCL(hNetGlobalISCL, uISCLEncSign); for (j = 0; j < 8; j++) { if (uISCLEncKeys[j] != 0) { L_DicomSetEncryptKeyISCL(hNetGlobalISCL, j+1, uISCLEncKeys[j]); } } L_DicomSetIndexForEncryptISCL(hNetGlobalISCL, uISCLEncCurrentKey+1); L_DicomSetMaxMessageLengthISCL(hNetGlobalISCL, 1024000); L_DicomSetMaxCommBlockLengthISCL(hNetGlobalISCL, 8160); L_DicomSetAuthDataISCL(hNetGlobalISCL,"client Ana are mere", 20); L_DicomSetDefaultEncryptionISCL(hNetGlobalISCL, DICOM_ISCL_ENCRYPT_DESCBC); L_DicomSetDefaultSigningISCL(hNetGlobalISCL, DICOM_ISCL_MAC_MD5); StartProcess(PROCESS_CONNECT, 0); nRet = L_DicomConnect( hNetGlobalISCL, pConnection->szClientIP, 0, //first available port pConnection->szServerIP, pConnection->uServerPort ); break; case DICOM_SECURE_TLS: nRet = MessageBox(NULL, "Warning, trying to connect to a non-TLS Secure Server may cause problems.\nDo you wish to continue?", "Warning", MB_YESNO); if(nRet==IDNO) return; L_DicomSetCipherToIndexTLS(hNetGlobalTLS, 0, TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA); // L_DicomSetClientCertificateTLS(hNetGlobalTLS, CLIENT_CERT_FILE, L_TLS_FILETYPE_PEM, NULL); { L_INT ret; char szpath[_MAX_PATH]; char szdrive[_MAX_PATH]; char szdir[_MAX_PATH]; char szPEMPath[_MAX_PATH]; GetModuleFileName(NULL, szpath, _MAX_PATH); _splitpath(szpath, szdrive, szdir, NULL, NULL ); wsprintf(szPEMPath, "%s%s%s",szdrive,szdir,CLIENT_CERT_NAME); ret = L_DicomSetClientCertificateTLS(hNetGlobalTLS, szPEMPath, L_TLS_FILETYPE_PEM, NULL); if(ret!=DICOM_SUCCESS) { // reset the password so reprompted next secure connect bValidPrivateKeyPassword = FALSE; strcpy(szPrivateKeyPassword, ""); MessageBox(NULL, "Error Setting TLS Certificate - Non-Secure", "Error", MB_OK|MB_ICONERROR); } else { bValidPrivateKeyPassword = TRUE; } } nRet = L_DicomConnect(hNetGlobalTLS, pConnection->szClientIP, 0, //first available port pConnection->szServerIP, pConnection->uServerPort ); break; } if (nRet != DICOM_SUCCESS) { FinishProcess(PROCESS_CONNECT); LogMessage(MSG_ERROR, "Connect Failed"); } bConnectedGlobal = (nRet == DICOM_SUCCESS); //Set called AE, calling AE in hAssociateRequest //The associate request gets sent if OnConnect message is successful L_DicomSetCalled(hAssociateRequest, pConnection->szCalledAE); L_DicomSetCalling(hAssociateRequest, pConnection->szCallingAE); } L_VOID CEchoRequest() { L_UCHAR nPresentationID; L_CHAR szMsg[MAX_STRING_LEN]; L_CHAR szTmp[MAX_STRING_LEN]; L_CHAR *lpszUID = UID_VERIFICATION_CLASS; L_INT nResult; strcpy(szMsg, "C-ECHO-RQ\n"); nPresentationID = L_DicomFindAbstract(hAssociateAccept, UID_VERIFICATION_CLASS); if ( (nPresentationID == 0) || (L_DicomGetResult(hAssociateAccept, nPresentationID) != PDU_ACCEPT_RESULT_SUCCESS) ) { wsprintf(szTmp, "Abstract Syntax[%s] Not Included in the Association", UID_VERIFICATION_CLASS); lstrcat(szMsg, szTmp); LogMessage1(MSG_ERROR, DICOM_ERROR_PDU_ID, szMsg); return; } StartProcess(PROCESS_C_ECHO, nPresentationID); switch (uSecureMode) { case DICOM_SECURE_NONE: nResult = L_DicomSendCEchoRequest( hNetGlobal, nPresentationID, uUniqueMessageID++, UID_VERIFICATION_CLASS); break; case DICOM_SECURE_ISCL: nResult = L_DicomSendCEchoRequest( hNetGlobalISCL, nPresentationID, uUniqueMessageID++, UID_VERIFICATION_CLASS); break; case DICOM_SECURE_TLS: nResult = L_DicomSendCEchoRequest( hNetGlobalTLS, nPresentationID, uUniqueMessageID++, UID_VERIFICATION_CLASS); break; } if (nResult != DICOM_SUCCESS) LogMessage1(MSG_ERROR, nResult, szMsg); else { LogMessage(MSG_SEND, szMsg); } } L_VOID L_EXPORT exOnSecureLinkReady(HDICOMNET hNet, L_UINT32 nError, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; L_CHAR szTmp[MAX_STRING_LEN]; L_INT nRet; char PeerId[128]; int nPeerLength = sizeof(PeerId); if(nError == DICOM_SUCCESS) { if(uSecureMode == DICOM_SECURE_ISCL) { L_DicomGetPeerAuthDataISCL(hNet, PeerId, &nPeerLength); wsprintf(szMsg,"ISCLLink ready, peer identified by %s", PeerId); LogMessage(MSG_SEND, szMsg); } if(uSecureMode == DICOM_SECURE_TLS) { L_CIPHERSUITE tmp; tmp = L_DicomGetCiphersuiteTLS(hNet); if(tmp == TLS_DHE_RSA_WITH_DES_CBC_SHA) { LogMessage(MSG_SEND, "TLS ciphersuite is TLS_DHE_RSA_WITH_DES_CBC_SHA"); } else if(tmp == TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA) { LogMessage(MSG_SEND, "TLS ciphersuite is TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA"); } else { LogMessage(MSG_SEND, "Bad ciphersuite"); } } } FinishProcess(PROCESS_CONNECT); if (nError == DICOM_SUCCESS) { //Send associate request StartProcess(PROCESS_ASSOCIATE, 0); DisplayAssociate(MSG_SEND, "Send Associate Request", hNet, hAssociateRequest, TRUE); nRet = L_DicomSendAssociateRequest(hNet, hAssociateRequest); if (nRet != DICOM_SUCCESS) FinishProcess(PROCESS_ASSOCIATE); else StatusServer(connections.connection[iIndexConnectionGlobal].szName, TRUE); } else { wsprintf(szTmp, "%sError[%d]\n", szMsg, nError); lstrcpy(szMsg, szTmp); LogMessage(MSG_ERROR, szMsg); bConnectedGlobal = FALSE; L_DicomClose(hNet); } }; L_VOID L_EXPORT ConnectCallback(HDICOMNET hNet, L_INT nError, L_VOID *pUserData) { L_UINT lServerPort, lClientPort; L_CHAR szServerAddress[MAX_STRING_LEN]; L_CHAR szClientAddress[MAX_STRING_LEN]; L_CHAR szMsg[MAX_STRING_LEN]; L_CHAR szTmp[MAX_STRING_LEN]; wsprintf(szMsg, "Receive Connect\nhNet[%x]\n", hNet); if (nError == DICOM_SUCCESS) { L_DicomGetHostInfo(hNet, szClientAddress, &lClientPort); wsprintf(szTmp, "%sClientAddress[%s]\nClientPort[%d]\n", szMsg, szClientAddress, lClientPort); lstrcpy(szMsg, szTmp); L_DicomGetHostInfo(hNet, szClientAddress, &lClientPort); L_DicomGetPeerInfo(hNet, szServerAddress, &lServerPort); wsprintf(szTmp, "%sServerAddress[%s]\nServerPort[%d]\n", szMsg, szServerAddress, lServerPort); lstrcpy(szMsg, szTmp); LogMessage(MSG_RECEIVE, szMsg); } wsprintf(szMsg, "Receive Connect\nhNet[%x]\n", hNet); if(L_DicomGetSecureMode(hNet) == DICOM_SECURE_NONE) exOnSecureLinkReady(hNet, nError, NULL); } L_VOID L_EXPORT AcceptCallback(HDICOMNET hNet, L_INT nError, L_VOID *pUserData) { HDICOMNET hPeer; L_INT nRet; L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive Accept Request\nhNet[%x]\nnError[%d]", hNet, nError); LogMessage(MSG_RECEIVE, szMsg); nRet = L_DicomStartUp(); hPeer = L_DicomCreateNet(szTempFilesFolder, DICOM_SECURE_NONE); SetCallbacks(hPeer); wsprintf(szMsg, "Accepting Connection...\nhNet[%x]\nhPeer[%x]", hNet, hPeer); LogMessage(MSG_NONE, szMsg); nRet = L_DicomAccept(hNet, hPeer); } L_VOID L_EXPORT CloseCallback(HDICOMNET hNet, L_INT nError, HDICOMNET hPeer, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; switch (uSecureMode) { case DICOM_SECURE_NONE: if (hNet == hNetGlobal) { bConnectedGlobal = FALSE; wsprintf(szMsg, "Receive Close\nhNet[%x]\nhPeer[%x]\nnError[%d]", hNet, hPeer, nError ); } else //hNetListenGlobal--resulting Abort or CMove response { wsprintf(szMsg, "Receive Close (Server)\nhNet[%x]\nhPeer[%x]\nnError[%d]", hNet, hPeer, nError ); } break; case DICOM_SECURE_ISCL: if (hNet == hNetGlobalISCL) { bConnectedGlobal = FALSE; wsprintf(szMsg, "Receive Close\nhNet[%x]\nhPeer[%x]\nnError[%d]", hNet, hPeer, nError ); L_DicomCloseForced(hNet, TRUE); } else //hNetListenGlobal--resulting Abort or CMove response { wsprintf(szMsg, "Receive Close (Server)\nhNet[%x]\nhPeer[%x]\nnError[%d]", hNet, hPeer, nError ); } break; case DICOM_SECURE_TLS: if (hNet == hNetGlobalTLS) { bConnectedGlobal = FALSE; wsprintf(szMsg, "Receive Close\nhNet[%x]\nhPeer[%x]\nnError[%d]", hNet, hPeer, nError ); L_DicomCloseForced(hNet, TRUE); } else //hNetListenGlobal--resulting Abort or CMove response { wsprintf(szMsg, "Receive Close (Server)\nhNet[%x]\nhPeer[%x]\nnError[%d]", hNet, hPeer, nError ); } break; } LogMessage(MSG_RECEIVE, szMsg); FinishProcess(PROCESS_CLOSE); } L_VOID L_EXPORT ReceiveCallback(HDICOMNET hNet, L_INT nError, L_UCHAR nType, L_CHAR *pBuffer, L_UINT32 nBytes, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; if (nError != DICOM_SUCCESS) { wsprintf(szMsg, "Receive,Error: %d", nError); SendMessage(hStatusBarGlobal, SB_SETTEXT, (WPARAM)STATUS_INDEX_RECEIVE, (LPARAM)szMsg); L_DicomSendAbort(hNet, PDU_ABORT_SOURCE_USER, PDU_ABORT_REASON_UNKNOWN); return ; } if(nType == PDU_UNKNOWN) { L_DicomSendAbort(hNet, PDU_ABORT_SOURCE_USER, PDU_ABORT_REASON_UNKNOWN); wsprintf(szMsg, "SendAbort,Error: %d", nError); SendMessage(hStatusBarGlobal, SB_SETTEXT, (WPARAM)STATUS_INDEX_RECEIVE, (LPARAM)szMsg); return; } StatusReceive(nBytes); } L_VOID L_EXPORT SendCallback(HDICOMNET hNet, L_INT nError, L_UCHAR nType, L_UINT32 nBytes, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; if (nError != DICOM_SUCCESS) { wsprintf(szMsg, "Send,Error: %d", nError); SendMessage(hStatusBarGlobal, SB_SETTEXT, (WPARAM)STATUS_INDEX_RECEIVE, (LPARAM)szMsg); L_DicomSendAbort(hNet, PDU_ABORT_SOURCE_USER, PDU_ABORT_REASON_UNKNOWN); return ; } if(nType == PDU_UNKNOWN) { L_DicomSendAbort(hNet, PDU_ABORT_SOURCE_USER, PDU_ABORT_REASON_UNKNOWN); wsprintf(szMsg, "SendAbort,Error: %d", nError); SendMessage(hStatusBarGlobal, SB_SETTEXT, (WPARAM)STATUS_INDEX_RECEIVE, (LPARAM)szMsg); return; } StatusSend(nBytes); } L_VOID L_EXPORT ReceiveAssociateRequestCallback(HDICOMNET hNet, HDICOMPDU hPDU, L_VOID *pUserData) { HDICOMNET hServer; HDICOMPDU hAssociateResponse; L_INT nPresContCount, nTransSynCount; L_UCHAR nPresContID; L_CHAR* pszAbstractSynName; L_CHAR* pszTransSynName; int i, j; hServer = L_DicomGetServer(hNetListenGlobal); if (hServer != NULL) { //Here, the client can check to make sure that the server that sends an associate request //is the same server that the client connected to originally--make sure properties are same //This is not done in the demo //1. Server Called //2. Server IP address ; } DisplayAssociate(MSG_RECEIVE, "Receive Associate Request", hNet, hPDU, TRUE); /* Send the Associate response */ hAssociateResponse = L_DicomCreateAssociate(FALSE); L_DicomResetAssociate(hAssociateResponse, FALSE); // The Protocol Version L_DicomSetVersion(hAssociateResponse, 1); // Titles of the Called and Calling AEs L_DicomSetCalled(hAssociateResponse, L_DicomGetCalled(hPDU)); L_DicomSetCalling(hAssociateResponse, L_DicomGetCalling(hPDU)); // The Application Context Name L_DicomSetApplication(hAssociateResponse, UID_APPLICATION_CONTEXT_NAME); nPresContCount = L_DicomGetPresentationCount(hPDU); // Presentation Contexts for (i = 0; i < nPresContCount; i++) { nPresContID = L_DicomGetPresentation(hPDU, i); pszAbstractSynName = L_DicomGetAbstract(hPDU, nPresContID); L_DicomAddPresentation(hAssociateResponse, nPresContID, PDU_ACCEPT_RESULT_SUCCESS, pszAbstractSynName); // Do we support the Abstract Syntax of this Presentation Context? if (IsSupported(pszAbstractSynName)) { nTransSynCount = L_DicomGetTransferCount(hPDU, nPresContID); for (j = 0; j < nTransSynCount; j++) { pszTransSynName = L_DicomGetTransfer(hPDU, nPresContID, j); // Select this Transfer Syntax if we support it if (IsSupported(pszTransSynName)) { L_DicomAddTransfer(hAssociateResponse, nPresContID, pszTransSynName); break; } } // Reject this Presentation Context if we didn't find a suitable Transfer Syntax if (j >= nTransSynCount) { L_DicomSetResult(hAssociateResponse, nPresContID, PDU_ACCEPT_RESULT_TRANSFER_SYNTAX); } } else { // Reject this Presentation Context because we don't support the Abstract Syntax L_DicomSetResult(hAssociateResponse, nPresContID, PDU_ACCEPT_RESULT_ABSTRACT_SYNTAX); } } // Maximum Length Application PDU if(L_DicomIsMaxLength(hPDU)) { L_DicomSetMaxLength(hAssociateResponse, TRUE, L_DicomGetMaxLength(hPDU)); } else { L_DicomSetMaxLength(hAssociateResponse, TRUE, 16384); } // Implementation Class UID L_DicomSetImplementClass(hAssociateResponse, TRUE, IMPLEMENTATION_CLASS_UID); // Implementation Version Name L_DicomSetImplementVersion(hAssociateResponse, TRUE, IMPLEMENTATION_VERSION_NAME); // Send the response DisplayAssociate(MSG_SEND, "Send Associate Accept", hNet, hAssociateResponse, FALSE); L_DicomSendAssociateAccept(hNet, hAssociateResponse); L_DicomFreeAssociate(hAssociateResponse); } L_VOID L_EXPORT ReceiveAssociateAcceptCallback(HDICOMNET hNet, HDICOMPDU hPDU, L_VOID *pUserData) { FinishProcess(PROCESS_ASSOCIATE); hAssociateAccept = hPDU; DisplayAssociate(MSG_RECEIVE, "Receive Associate Accept", hNet, hAssociateAccept, FALSE); } L_VOID L_EXPORT ReceiveAssociateRejectCallback(HDICOMNET hNet, L_UCHAR nResult, L_UCHAR nSource, L_UCHAR nReason, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; FinishProcess(PROCESS_ASSOCIATE); wsprintf(szMsg, "Receive AssociateReject\nhNet[%x]\nnResult[%d]\nnSource[%d]\nnReason[%d]", hNet, nResult, nSource, nReason); LogMessage(MSG_RECEIVE, szMsg); } L_VOID L_EXPORT ReceiveDataCallback(HDICOMNET hNet, L_UCHAR nPresentationID, HDICOMDS hCS, HDICOMDS hDS, L_VOID *pUserData) { DisplayCommandSet(hNet, hCS); } L_VOID L_EXPORT ReceiveReleaseRequestCallback(HDICOMNET hNet, L_VOID *pUserData) { L_INT nResult; L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive Release Request\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); wsprintf(szMsg, "Send Release Response\nhNet[%x]", hNet); LogMessage(MSG_SEND, szMsg); nResult = L_DicomSendReleaseResponse(hNet); } L_VOID L_EXPORT ReceiveReleaseResponseCallback(HDICOMNET hNet, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; FinishProcess(PROCESS_RELEASE); wsprintf(szMsg, "Receive Release Response\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); wsprintf(szMsg, "Close\nhNet[%x]", hNet); LogMessage(MSG_NONE, szMsg); L_DicomCloseForced(hNet, TRUE); switch (uSecureMode) { case DICOM_SECURE_NONE: if (hNet = hNetGlobal) { bConnectedGlobal = FALSE; hAssociateAccept = NULL; StatusInit(TRUE); } break; case DICOM_SECURE_ISCL: if (hNet = hNetGlobalISCL) { bConnectedGlobal = FALSE; hAssociateAccept = NULL; StatusInit(TRUE); } break; case DICOM_SECURE_TLS: if (hNet = hNetGlobalTLS) { bConnectedGlobal = FALSE; hAssociateAccept = NULL; StatusInit(TRUE); } break; } } L_VOID L_EXPORT ReceiveAbortCallback(HDICOMNET hNet, L_UCHAR nSource, L_UCHAR nReason, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive Abort\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); //Disconnect hNetListenGlobal DisconnectFromServer(hNetListenGlobal); } L_VOID L_EXPORT ReceiveCStoreRequestCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_CHAR *pszInstance, L_UINT16 nPriority, L_CHAR *pszMoveAE, L_UINT16 nMoveMessageID, HDICOMDS hDS, L_VOID *pUserData) { pDICOMELEMENT pElement, pImageDR, pDR; L_CHAR* pszInstanceUID, * pszFile, * pszMessage, * pszPatientID, * pszSOPInstanceUID; L_CHAR* pszStudyInstanceUID, * pszSeriesInstanceUID, szMsg[MAX_STRING_LEN]; int iSize, iAbsent; L_UINT16 uRet; HTREEITEM hParentDirItem, hDirItem; if (hDS != NULL) { // Save the SOP Instance pElement = L_DicomFindFirstElement(hDS, NULL, TAG_SOP_INSTANCE_UID, FALSE); if (pElement) { pszInstanceUID = L_DicomGetStringValue(hDS, pElement, 0, 1); if (pszInstanceUID) { iSize = lstrlen(szStoreFolder) + lstrlen(pszInstanceUID) + 1; if (lstrlen(szExtension)) iSize += 1 + lstrlen(szExtension); pszFile = (L_CHAR*) malloc(iSize); if (pszFile) { wsprintf(pszFile, "%s%s", szStoreFolder, pszInstanceUID); if (lstrlen(szExtension)) wsprintf(pszFile, "%s.%s", pszFile, szExtension); uRet = L_DicomSaveDS(hDS, pszFile, DS_METAHEADER_PRESENT | DS_GROUP_LENGTHS); if (uRet == DICOM_SUCCESS) { iSize = lstrlen("SOP Instance was stored in \"\"") + lstrlen(pszFile) + 1; pszMessage = (L_CHAR*) malloc(iSize); if (pszMessage) { wsprintf(pszMessage, "SOP Instance was stored in \"%s\"", pszFile); LogMessage(MSG_NONE, pszMessage); free(pszMessage); } } free(pszFile); } } } pszPatientID = NULL; pszStudyInstanceUID = NULL; pszSeriesInstanceUID = NULL; pszSOPInstanceUID = NULL; if (nQueryMethodGlobal != QUERY_STUDY_ROOT) { pElement = L_DicomFindFirstElement(hDS, NULL, TAG_PATIENT_ID, FALSE); if (pElement) { pszPatientID = L_DicomGetStringValue(hDS, pElement, 0, 1); } } pElement = L_DicomFindFirstElement(hDS, NULL, TAG_STUDY_INSTANCE_UID, FALSE); if (pElement) { pszStudyInstanceUID = L_DicomGetStringValue(hDS, pElement, 0, 1); } if (nQueryMethodGlobal != QUERY_PATIENT_STUDY_ONLY) { pElement = L_DicomFindFirstElement(hDS, NULL, TAG_SERIES_INSTANCE_UID, FALSE); if (pElement) { pszSeriesInstanceUID = L_DicomGetStringValue(hDS, pElement, 0, 1); } pElement = L_DicomFindFirstElement(hDS, NULL, TAG_SOP_INSTANCE_UID, FALSE); if (pElement) { pszSOPInstanceUID = L_DicomGetStringValue(hDS, pElement, 0, 1); } } pImageDR = NULL; iAbsent = 0; // (Ptn: 1), (Std: 2), (Srs: 3), (Img: 4) hDirItem = TreeView_GetNextItem(hTreeDir, NULL, TVGN_CHILD); if (nQueryMethodGlobal != QUERY_STUDY_ROOT) { hDirItem = FindDirectoryRecord(hDirItem, TAG_PATIENT_ID, pszPatientID); } else { hDirItem = FindDirectoryRecord(hDirItem, TAG_STUDY_INSTANCE_UID, pszStudyInstanceUID); } if (hDirItem) { TV_SetItemState(hTreeDir, hDirItem, 0, TVIS_BOLD); hParentDirItem = hDirItem; hDirItem = TreeView_GetChild(hTreeDir, hDirItem); if (nQueryMethodGlobal != QUERY_STUDY_ROOT) { hDirItem = FindDirectoryRecord(hDirItem, TAG_STUDY_INSTANCE_UID, pszStudyInstanceUID); } else { hDirItem = FindDirectoryRecord(hDirItem, TAG_SERIES_INSTANCE_UID, pszSeriesInstanceUID); } if (hDirItem) { TV_SetItemState(hTreeDir, hDirItem, 0, TVIS_BOLD); if (nQueryMethodGlobal != QUERY_PATIENT_STUDY_ONLY) { hParentDirItem = hDirItem; hDirItem = TreeView_GetChild(hTreeDir, hDirItem); if (nQueryMethodGlobal != QUERY_STUDY_ROOT) { hDirItem = FindDirectoryRecord(hDirItem, TAG_SERIES_INSTANCE_UID, pszSeriesInstanceUID); } else { hDirItem = FindDirectoryRecord(hDirItem, TAG_SOP_INSTANCE_UID, pszSOPInstanceUID); } if (hDirItem) { TV_SetItemState(hTreeDir, hDirItem, 0, TVIS_BOLD); if (nQueryMethodGlobal != QUERY_STUDY_ROOT) { hParentDirItem = hDirItem; hDirItem = TreeView_GetChild(hTreeDir, hDirItem); hDirItem = FindDirectoryRecord(hDirItem, TAG_SOP_INSTANCE_UID, pszSOPInstanceUID); if (hDirItem) { TV_SetItemState(hTreeDir, hDirItem, 0, TVIS_BOLD); pImageDR = (pDICOMELEMENT) TV_GetItemData(hTreeDir, hDirItem); } else // New Image { iAbsent = 4; } } else { pImageDR = (pDICOMELEMENT) TV_GetItemData(hTreeDir, hDirItem); } } else // New Series or Image { iAbsent = (nQueryMethodGlobal != QUERY_STUDY_ROOT) ? 3 : 4; } } } else // New Study or Series { iAbsent = (nQueryMethodGlobal != QUERY_STUDY_ROOT) ? 2 : 3; } } else // New Patient or Study { iAbsent = (nQueryMethodGlobal != QUERY_STUDY_ROOT) ? 1 : 2; } if (iAbsent == 1) { pDR = L_DicomInsertKey(hDSGlobal, NULL, "PATIENT", FALSE); FillDirectoryRecord(hDS, pDR); if (pDR) DeleteEmpty(hDSGlobal, pDR); hParentDirItem = InsertDirTreeDR(NULL, pDR); } if (iAbsent == 2 && nQueryMethodGlobal == QUERY_STUDY_ROOT) { pDR = L_DicomInsertKey(hDSGlobal, NULL, "STUDY", FALSE); FillDirectoryRecord(hDS, pDR); if (pDR) DeleteEmpty(hDSGlobal, pDR); hParentDirItem = InsertDirTreeDR(NULL, pDR); } if ((iAbsent == 1 || iAbsent == 2) && nQueryMethodGlobal != QUERY_STUDY_ROOT && hParentDirItem != NULL) { pDR = (pDICOMELEMENT) TV_GetItemData(hTreeDir, hParentDirItem); pDR = L_DicomInsertKey(hDSGlobal, pDR, "STUDY", FALSE); FillDirectoryRecord(hDS, pDR); if (pDR) DeleteEmpty(hDSGlobal, pDR); hParentDirItem = InsertDirTreeDR(hParentDirItem, pDR); } if (nQueryMethodGlobal != QUERY_PATIENT_STUDY_ONLY) { if ((iAbsent == 1 || iAbsent == 2 || iAbsent == 3) && hParentDirItem != NULL) { pDR = (pDICOMELEMENT) TV_GetItemData(hTreeDir, hParentDirItem); pDR = L_DicomInsertKey(hDSGlobal, pDR, "SERIES", FALSE); FillDirectoryRecord(hDS, pDR); if (pDR) DeleteEmpty(hDSGlobal, pDR); hParentDirItem = InsertDirTreeDR(hParentDirItem, pDR); } if ((iAbsent == 1 || iAbsent == 2 || iAbsent == 3 || iAbsent == 4) && hParentDirItem != NULL) { pDR = (pDICOMELEMENT) TV_GetItemData(hTreeDir, hParentDirItem); pImageDR = L_DicomInsertKey(hDSGlobal, pDR, "IMAGE", FALSE); FillDirectoryRecord(hDS, pImageDR); if (pImageDR) DeleteEmpty(hDSGlobal, pImageDR); InsertDirTreeDR(hParentDirItem, pImageDR); } if (pImageDR) { SetIconImage(pImageDR, hDS); hDirItem = TreeView_GetSelection(hTreeDir); if (hDirItem && pImageDR == (pDICOMELEMENT) TV_GetItemData(hTreeDir, hDirItem)) { if (hPaletteGlobal) { DeleteObject(hPaletteGlobal); hPaletteGlobal = NULL; } TreeView_EnsureVisible(hTreeDir, hDirItem); ShowDicomImage(); } } } } wsprintf(szMsg, "Send C-STORE-RSP\nhNet[%x]", hNet); LogMessage(MSG_SEND, szMsg); L_DicomSendCStoreResponse(hNet, nPresentationID, nMessageID, pszClass, pszInstance, COMMAND_STATUS_SUCCESS); } L_VOID L_EXPORT ReceiveCStoreResponseCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_CHAR *pszInstance, L_UINT16 nStatus, L_VOID *pUserData) { FinishProcess(PROCESS_C_STORE); } L_VOID L_EXPORT ReceiveCFindRequestCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_UINT16 nPriority, HDICOMDS hDS, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive C-FIND-RQ\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); } L_VOID L_EXPORT ReceiveCFindResponseCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_UINT16 nStatus, HDICOMDS hDS, L_VOID *pUserData) { L_CHAR *szText; pDICOMELEMENT pElement; pDICOMELEMENT pParent; pDICOMELEMENT pTemp; if ((nStatus != COMMAND_STATUS_PENDING) && (nStatus != COMMAND_STATUS_PENDING_WARNING) ) FinishProcess(PROCESS_C_FIND); if (hItemGlobal == NULL) { pParent = NULL; } else { //Get lParam of hItem--this is pParent pParent = (pDICOMELEMENT) TV_GetItemData(hTreeDir, hItemGlobal); if ((pParent == NULL) && (L_DicomExistsElement(hDSGlobal, pParent) == FALSE)) return; } if (hDS != NULL) { L_UINT32 uCount, i; L_CHAR* pszAETitle, * pszCalledAETitle; HTREEITEM hItem; if (lstrlen(szRetrieveAEsMsg) == 0) { pElement = L_DicomFindFirstElement(hDS, NULL, TAG_RETRIEVE_AE_TITLE, FALSE); if (pElement) { uCount = L_DicomGetCountValue(hDS, pElement); if (uCount > 0) { pszCalledAETitle = L_DicomGetCalled(hAssociateAccept); wsprintf(szRetrieveAEsMsg, "The composite object instance(s) are not available from the \"%s\" " \ "AE we are connected to. They can be retrieved from the following " \ "DICOM AE(s):\n\n", pszCalledAETitle); for (i = 0; i < uCount; i++) { pszAETitle = L_DicomGetStringValue(hDS, pElement, i, 1); if (pszAETitle) { if (lstrcmpi(pszCalledAETitle, pszAETitle) == 0) { break; } lstrcat(szRetrieveAEsMsg, pszAETitle); if (i != uCount - 1) { lstrcat(szRetrieveAEsMsg, "\n"); } } } L_DicomFreeValue(hDS, pElement); if (i < uCount) { lstrcpy(szRetrieveAEsMsg, ""); } } } } switch (nQueryMethodGlobal) { case QUERY_PATIENT_ROOT: { if (hItemGlobal == NULL) szText = "PATIENT"; else if ((hItem = TreeView_GetParent(hTreeDir, hItemGlobal)) == NULL) szText = "STUDY"; else if (TreeView_GetParent(hTreeDir, hItem) == NULL) szText = "SERIES"; else szText = "IMAGE"; } break; case QUERY_STUDY_ROOT: { if (hItemGlobal == NULL) szText = "STUDY"; else if ((hItem = TreeView_GetParent(hTreeDir, hItemGlobal)) == NULL) szText = "SERIES"; else if (TreeView_GetParent(hTreeDir, hItem) == NULL) szText = "IMAGE"; else szText = "BITMAP"; } break; case QUERY_PATIENT_STUDY_ONLY: if (hItemGlobal == NULL) szText = "PATIENT"; else szText = "STUDY"; break; } pElement = L_DicomFindFirstElement(hDS, NULL, TAG_QUERY_RETRIEVE_LEVEL, TRUE); if (pElement != NULL) { L_DicomDeleteElement(hDS, pElement); } pElement = L_DicomGetFirstElement(hDS, NULL, TRUE, TRUE); while (pElement != NULL) { if ((GETGROUP(pElement->nTag) == 0x0000) || (GETGROUP(pElement->nTag) == 0x0002)) { pTemp = L_DicomGetNextElement(hDS, pElement, TRUE, TRUE); L_DicomDeleteElement(hDS, pElement); pElement = pTemp; } else { pElement = L_DicomGetNextElement(hDS, pElement, TRUE, TRUE); } } pElement = L_DicomInsertKey(hDSGlobal, pParent, szText, FALSE); L_DicomCopyDS(hDSGlobal, pElement, hDS, NULL); DeleteEmpty(hDSGlobal, pElement); } if (nStatus != COMMAND_STATUS_SUCCESS) return; if (hItemGlobal != NULL) { TV_SetItemState(hTreeDir, hItemGlobal, 0, TVIS_BOLD); TreeView_SelectItem(hTreeDir, hItemGlobal); } DisplayTree( hTreeDir, hDSGlobal, (hItemGlobal == NULL) ? TVI_ROOT : hItemGlobal, pParent, DISPLAY_TREE_DIRECTORY | DISPLAY_TREE_EXPANDED ); if (lstrlen(szRetrieveAEsMsg) > 0) { MessageBox(hWndMainGlobal, szRetrieveAEsMsg, "Demo", MB_OK | MB_ICONINFORMATION); SetFocus(hTreeDir); } } L_VOID L_EXPORT ReceiveCGetRequestCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_UINT16 nPriority, HDICOMDS hDS, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive C-GET-RQ\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); } L_VOID L_EXPORT ReceiveCGetResponseCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_UINT16 nStatus, L_UINT16 nRemaining, L_UINT16 nCompleted, L_UINT16 nFailed, L_UINT16 nWarning, HDICOMDS hDS, L_VOID *pUserData) { } L_VOID L_EXPORT ReceiveCMoveRequestCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_UINT16 nPriority, L_CHAR *pszMoveAE, HDICOMDS hDS, L_VOID *pUserData) { } L_VOID L_EXPORT ReceiveCMoveResponseCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_UINT16 nStatus, L_UINT16 nRemaining, L_UINT16 nCompleted, L_UINT16 nFailed, L_UINT16 nWarning, HDICOMDS hDS, L_VOID *pUserData) { if ((nStatus != COMMAND_STATUS_PENDING) && (nStatus != COMMAND_STATUS_PENDING_WARNING) ) { FinishProcess(PROCESS_C_MOVE); //Now client can quit listening for messages from server CloseConnection(hNetListenGlobal); } } L_VOID L_EXPORT ReceiveCCancelRequestCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive C-CANCEL-RQ\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); } L_VOID L_EXPORT ReceiveCEchoRequestCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive C-ECHO-RQ\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); L_DicomSendCEchoResponse(hNet, nPresentationID, nMessageID, pszClass, COMMAND_STATUS_SUCCESS); } L_VOID L_EXPORT ReceiveCEchoResponseCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_UINT16 nStatus, L_VOID *pUserData) { FinishProcess(PROCESS_C_ECHO); } L_VOID L_EXPORT ReceiveNReportRequestCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_CHAR *pszInstance, L_UINT16 nEvent, HDICOMDS hDS, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive N-REPORT-RQ\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); } L_VOID L_EXPORT ReceiveNReportResponseCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_CHAR *pszInstance, L_UINT16 nStatus, L_UINT16 nEvent, HDICOMDS hDS, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive C-REPORT-RSP\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); } L_VOID L_EXPORT ReceiveNGetRequestCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_CHAR *pszInstance, L_UINT32 *pnAttribute, L_UINT32 nCount, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive N-GET-RQ\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); } L_VOID L_EXPORT ReceiveNGetResponseCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_CHAR *pszInstance, L_UINT16 nStatus, HDICOMDS hDS, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive N-GET-RSP\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); } L_VOID L_EXPORT ReceiveNSetRequestCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_CHAR *pszInstance, HDICOMDS hDS, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive N-SET-RQ\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); } L_VOID L_EXPORT ReceiveNSetResponseCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_CHAR *pszInstance, L_UINT16 nStatus, HDICOMDS hDS, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive N-SET-RSP\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); } L_VOID L_EXPORT ReceiveNActionRequestCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_CHAR *pszInstance, L_UINT16 nAction, HDICOMDS hDS, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive N-ACTION-RQ\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); } L_VOID L_EXPORT ReceiveNActionResponseCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_CHAR *pszInstance, L_UINT16 nStatus, L_UINT16 nAction, HDICOMDS hDS, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive N-ACTION-RSP\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); } L_VOID L_EXPORT ReceiveNCreateRequestCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_CHAR *pszInstance, HDICOMDS hDS, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive N-CREATE-RQ\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); } L_VOID L_EXPORT ReceiveNCreateResponseCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_CHAR *pszInstance, L_UINT16 nStatus, HDICOMDS hDS, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive N-CREATE-RSP\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); } L_VOID L_EXPORT ReceiveNDeleteRequestCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_CHAR *pszInstance, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive N-DELETE-RQ\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); } L_VOID L_EXPORT ReceiveNDeleteResponseCallback(HDICOMNET hNet, L_UCHAR nPresentationID, L_UINT16 nMessageID, L_CHAR *pszClass, L_CHAR *pszInstance, L_UINT16 nStatus, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive N-DELETE-RSP\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); } L_VOID L_EXPORT ReceiveUnknownCallback(HDICOMNET hNet, L_UCHAR nPresentationID, HDICOMDS hCS, HDICOMDS hDS, L_VOID *pUserData) { L_CHAR szMsg[MAX_STRING_LEN]; wsprintf(szMsg, "Receive UNKNOWN\nhNet[%x]", hNet); LogMessage(MSG_RECEIVE, szMsg); } L_UINT32 L_EXPORT exGetChallengeISCL(HDICOMNET hNet, L_UINT64 *nChallenge, L_UINT64 nParameter, L_VOID *pUserData) { *nChallenge = 0x0123456789ABCDE1; return 0; }; L_UINT32 L_EXPORT exInternalAuthenticateISCL(HDICOMNET hNet, L_UINT64 nChallenge, L_UINT64 *nResponse, L_UINT64 nParameter, L_VOID *pUserData) { *nResponse = nChallenge + 1; return 0; }; L_UINT32 L_EXPORT exExternalAuthenticateISCL(HDICOMNET hNet, L_UINT64 nChallenge, L_UINT64 nResponse, L_UINT64 nParameter, L_VOID *pUserData) { if (nResponse == nChallenge + 1) return 0; else return 1; }; L_VOID L_EXPORT EXT_CALLBACK exOnReceivedISCLPacket(HDICOMNET hNet, L_INT nError, L_CHAR *pBuffer, L_UINT32 nBytes, L_VOID *pUserData) { L_UINT32 nMsgId, nOption, nPacketLoadLength; nMsgId = *((L_UINT32 *)&(pBuffer[4])); nPacketLoadLength = *((L_UINT32 *)&(pBuffer[8])); nOption = *((L_UINT32 *)&(pBuffer[12])); }; L_VOID SetCallbacks(HDICOMNET hNet) { DICOMNETCALLBACK cb; cb.pfnConnect = ConnectCallback; cb.pfnAccept = AcceptCallback; cb.pfnClose = CloseCallback; cb.pfnReceive = ReceiveCallback; cb.pfnSend = SendCallback; cb.pfnReceiveAssociateRequest = ReceiveAssociateRequestCallback; cb.pfnReceiveAssociateAccept = ReceiveAssociateAcceptCallback; cb.pfnReceiveAssociateReject = ReceiveAssociateRejectCallback; cb.pfnReceiveData = ReceiveDataCallback; cb.pfnReceiveReleaseRequest = ReceiveReleaseRequestCallback; cb.pfnReceiveReleaseResponse = ReceiveReleaseResponseCallback; cb.pfnReceiveAbort = ReceiveAbortCallback; cb.pfnReceiveCStoreRequest = ReceiveCStoreRequestCallback; cb.pfnReceiveCStoreResponse = ReceiveCStoreResponseCallback; cb.pfnReceiveCFindRequest = ReceiveCFindRequestCallback; cb.pfnReceiveCFindResponse = ReceiveCFindResponseCallback; cb.pfnReceiveCGetRequest = ReceiveCGetRequestCallback; cb.pfnReceiveCGetResponse = ReceiveCGetResponseCallback; cb.pfnReceiveCMoveRequest = ReceiveCMoveRequestCallback; cb.pfnReceiveCMoveResponse = ReceiveCMoveResponseCallback; cb.pfnReceiveCCancelRequest = ReceiveCCancelRequestCallback; cb.pfnReceiveCEchoRequest = ReceiveCEchoRequestCallback; cb.pfnReceiveCEchoResponse = ReceiveCEchoResponseCallback; cb.pfnReceiveNReportRequest = ReceiveNReportRequestCallback; cb.pfnReceiveNReportResponse = ReceiveNReportResponseCallback; cb.pfnReceiveNGetRequest = ReceiveNGetRequestCallback; cb.pfnReceiveNGetResponse = ReceiveNGetResponseCallback; cb.pfnReceiveNSetRequest = ReceiveNSetRequestCallback; cb.pfnReceiveNSetResponse = ReceiveNSetResponseCallback; cb.pfnReceiveNActionRequest = ReceiveNActionRequestCallback; cb.pfnReceiveNActionResponse = ReceiveNActionResponseCallback; cb.pfnReceiveNCreateRequest = ReceiveNCreateRequestCallback; cb.pfnReceiveNCreateResponse = ReceiveNCreateResponseCallback; cb.pfnReceiveNDeleteRequest = ReceiveNDeleteRequestCallback; cb.pfnReceiveNDeleteResponse = ReceiveNDeleteResponseCallback; cb.pfnReceiveUnknown = ReceiveUnknownCallback; cb.pUserData = NULL; cb.pfnOnSecureLinkReady = exOnSecureLinkReady; cb.pfnGetChallenge = exGetChallengeISCL; cb.pfnInternalAuthenticate = exInternalAuthenticateISCL; cb.pfnExternalAuthenticate = exExternalAuthenticateISCL; // debug only cb.pfnOnReceivedISCLPacket = exOnReceivedISCLPacket; L_DicomSetCallback(hNet, &cb); } LRESULT CALLBACK DlgPrivateKeyPassword (HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam) { static char *pszPrivateKeyPassword = NULL; switch(message) { case WM_INITDIALOG: { pszPrivateKeyPassword = (char *)lParam; SetDlgItemText(hDlg, IDC_PASSWORD, "test"); return TRUE; } case WM_COMMAND: switch (LOWORD(wParam)) { case IDCANCEL: EndDialog(hDlg, IDCANCEL); return TRUE; break; case IDOK: { GetDlgItemText(hDlg, IDC_PASSWORD, pszPrivateKeyPassword, 100); EndDialog(hDlg, IDOK); return TRUE; } break; } } return FALSE; } L_INT L_EXPORT EXT_CALLBACK exPrivateKeyPassword(HDICOMNET hNet, L_CHAR *pszPassword, L_INT nSize, L_INT rwFlag, L_VOID *pUserData) { int nLenPassword = 0; if ((strlen(szPrivateKeyPassword)==0) && (!bValidPrivateKeyPassword)) { INT_PTR nRet; nRet=DialogBoxParam( hInst, (LPCTSTR)IDD_PRIVATE_KEY_PASSWORD_DIALOG, hWndMainGlobal, (DLGPROC)DlgPrivateKeyPassword, (LPARAM)szPrivateKeyPassword ); if (nRet == IDOK) { // m_strPassword = dlg.m_strPassword; } else { DWORD dRet = GetLastError(); } } if (strlen(szPrivateKeyPassword)>0) { strncpy( pszPassword, szPrivateKeyPassword, nSize); nLenPassword = strlen(pszPassword); } return nLenPassword; } L_VOID SetCallbacksExt(HDICOMNET hNet) { DICOMNETCALLBACKEXT cb; memset(&cb, 0, sizeof(cb)); cb.uStructSize = sizeof(cb); //cb.pfnPreCreateCTX = NULL; //cb.pfnPreCreateCTX = NULL; cb.pfnPrivateKeyPassword = exPrivateKeyPassword; L_DicomSetCallbackExt(hNet, &cb); } L_VOID FindPatientRoot(pPATIENT pPatient) { L_INT nResult; pDICOMELEMENT pElement; HDICOMDS hDSLocal; L_UCHAR nPresentationID; nQueryMethodGlobal = QUERY_PATIENT_ROOT; L_DicomInitDS( hDSGlobal, CLASS_BASIC_DIRECTORY, DS_METAHEADER_PRESENT|DS_LITTLE_ENDIAN|DS_EXPLICIT_VR|DS_GROUP_LENGTHS ); TreeView_DeleteAllItems(hTreeDir); TreeView_DeleteAllItems(hTreeKey); hItemGlobal = NULL; /* if (m_pBitmap != NULL) { delete m_pBitmap; m_pBitmap = NULL; } */ nPresentationID = L_DicomFindAbstract(hAssociateAccept, UID_PATIENT_ROOT_QUERY_FIND); if ( (nPresentationID == 0) || (L_DicomGetResult(hAssociateAccept, nPresentationID) != PDU_ACCEPT_RESULT_SUCCESS) ) { LogMessage(MSG_ERROR, "Send C-Find Request\nPresentation ID not found"); return; } hDSLocal = L_DicomCreateDS(szTempFilesFolder); L_DicomInitDS( hDSLocal, CLASS_PATIENT_ROOT_QUERY_PATIENT, DS_METAHEADER_ABSENT|DS_LITTLE_ENDIAN|DS_EXPLICIT_VR ); pElement = L_DicomFindFirstElement( hDSLocal, NULL, TAG_QUERY_RETRIEVE_LEVEL, TRUE); if (pElement == NULL) { pElement = L_DicomInsertElement( hDSLocal, NULL, FALSE, TAG_QUERY_RETRIEVE_LEVEL, 0, FALSE, 0 ); } L_DicomSetStringValue(hDSLocal, pElement, "PATIENT", 1); pElement = L_DicomFindFirstElement(hDSLocal, NULL, TAG_PATIENT_NAME, TRUE); if (pElement == NULL) { pElement = L_DicomInsertElement(hDSLocal, NULL, FALSE, TAG_PATIENT_NAME, 0, FALSE, 0); } L_DicomSetStringValue(hDSLocal, pElement, pPatient->szPatientName, 1); pElement = L_DicomFindFirstElement(hDSLocal, NULL, TAG_PATIENT_ID, TRUE); if (pElement == NULL) { pElement = L_DicomInsertElement(hDSLocal, NULL, FALSE, TAG_PATIENT_ID, 0, FALSE, 0); } L_DicomSetStringValue(hDSLocal, pElement, pPatient->szPatientID, 1); lstrcpy(szRetrieveAEsMsg, ""); StartProcess(PROCESS_C_FIND, nPresentationID); switch (uSecureMode) { case DICOM_SECURE_NONE: nResult = L_DicomSendCFindRequest( hNetGlobal, nPresentationID, uUniqueMessageID++, UID_PATIENT_ROOT_QUERY_FIND, COMMAND_PRIORITY_MEDIUM, hDSLocal); break; case DICOM_SECURE_ISCL: nResult = L_DicomSendCFindRequest( hNetGlobalISCL, nPresentationID, uUniqueMessageID++, UID_PATIENT_ROOT_QUERY_FIND, COMMAND_PRIORITY_MEDIUM, hDSLocal); break; case DICOM_SECURE_TLS: nResult = L_DicomSendCFindRequest( hNetGlobalTLS, nPresentationID, uUniqueMessageID++, UID_PATIENT_ROOT_QUERY_FIND, COMMAND_PRIORITY_MEDIUM, hDSLocal); break; } LogMessage(MSG_SEND, "C-FIND-RQ"); if (nResult != DICOM_SUCCESS) FinishProcess(PROCESS_C_FIND); L_DicomFreeDS(hDSLocal); } L_VOID FindStudyRoot(pSTUDY pStudy) { L_INT nResult; pDICOMELEMENT pElement; HDICOMDS hDSLocal; L_UCHAR nPresentationID; nQueryMethodGlobal = QUERY_STUDY_ROOT; L_DicomInitDS( hDSGlobal, CLASS_BASIC_DIRECTORY, DS_METAHEADER_PRESENT|DS_LITTLE_ENDIAN|DS_EXPLICIT_VR|DS_GROUP_LENGTHS ); TreeView_DeleteAllItems(hTreeDir); TreeView_DeleteAllItems(hTreeKey); hItemGlobal = NULL; nPresentationID = L_DicomFindAbstract(hAssociateAccept, UID_STUDY_ROOT_QUERY_FIND); if ( (nPresentationID == 0) || (L_DicomGetResult(hAssociateAccept, nPresentationID) != PDU_ACCEPT_RESULT_SUCCESS) ) { LogMessage(MSG_ERROR, "Send C-FIND-RQ\nPresentation ID not found"); return; } hDSLocal = L_DicomCreateDS(szTempFilesFolder); L_DicomInitDS( hDSLocal, CLASS_STUDY_ROOT_QUERY_STUDY, DS_METAHEADER_ABSENT|DS_LITTLE_ENDIAN|DS_EXPLICIT_VR ); pElement = L_DicomFindFirstElement( hDSLocal, NULL, TAG_QUERY_RETRIEVE_LEVEL, TRUE); if (pElement == NULL) { pElement = L_DicomInsertElement( hDSLocal, NULL, FALSE, TAG_QUERY_RETRIEVE_LEVEL, 0, FALSE, 0 ); } L_DicomSetStringValue(hDSLocal, pElement, "STUDY", 1); pElement = L_DicomFindFirstElement(hDSLocal, NULL, TAG_STUDY_INSTANCE_UID, TRUE); if (pElement == NULL) { pElement = L_DicomInsertElement(hDSLocal, NULL, FALSE, TAG_STUDY_INSTANCE_UID, 0, FALSE, 0); } L_DicomSetStringValue(hDSLocal, pElement, pStudy->szStudyInstanceUID, 1); pElement = L_DicomFindFirstElement(hDSLocal, NULL, TAG_STUDY_ID, TRUE); if (pElement == NULL) { pElement = L_DicomInsertElement(hDSLocal, NULL, FALSE, TAG_STUDY_ID, 0, FALSE, 0); } L_DicomSetStringValue(hDSLocal, pElement, pStudy->szStudyID, 1); pElement = L_DicomFindFirstElement(hDSLocal, NULL, TAG_ACCESSION_NUMBER, TRUE); if (pElement == NULL) { pElement = L_DicomInsertElement(hDSLocal, NULL, FALSE, TAG_ACCESSION_NUMBER, 0, FALSE, 0); } L_DicomSetStringValue(hDSLocal, pElement, pStudy->szAccessionNumber, 1); pElement = L_DicomFindFirstElement(hDSLocal, NULL, TAG_PATIENT_NAME, TRUE); if (pElement == NULL) { pElement = L_DicomInsertElement(hDSLocal, NULL, FALSE, TAG_PATIENT_NAME, 0, FALSE, 0); } L_DicomSetStringValue(hDSLocal, pElement, pStudy->szPatientName, 1); pElement = L_DicomFindFirstElement(hDSLocal, NULL, TAG_PATIENT_ID, TRUE); if (pElement == NULL) { pElement = L_DicomInsertElement(hDSLocal, NULL, FALSE, TAG_PATIENT_ID, 0, FALSE, 0); } L_DicomSetStringValue(hDSLocal, pElement, pStudy->szPatientID, 1); lstrcpy(szRetrieveAEsMsg, ""); StartProcess(PROCESS_C_FIND, nPresentationID); switch (uSecureMode) { case DICOM_SECURE_NONE: nResult = L_DicomSendCFindRequest( hNetGlobal, nPresentationID, uUniqueMessageID++, UID_STUDY_ROOT_QUERY_FIND, COMMAND_PRIORITY_MEDIUM, hDSLocal); break; case DICOM_SECURE_ISCL: nResult = L_DicomSendCFindRequest( hNetGlobalISCL, nPresentationID, uUniqueMessageID++, UID_STUDY_ROOT_QUERY_FIND, COMMAND_PRIORITY_MEDIUM, hDSLocal); break; case DICOM_SECURE_TLS: nResult = L_DicomSendCFindRequest( hNetGlobalTLS, nPresentationID, uUniqueMessageID++, UID_STUDY_ROOT_QUERY_FIND, COMMAND_PRIORITY_MEDIUM, hDSLocal); break; } LogMessage(MSG_SEND, "C-FIND-RQ"); if (nResult != DICOM_SUCCESS) FinishProcess(PROCESS_C_FIND); L_DicomFreeDS(hDSLocal); } L_VOID FindPatientStudyOnly(pPATIENT pPatient) { L_INT nResult; pDICOMELEMENT pElement; HDICOMDS hDSLocal; L_UCHAR nPresentationID; nQueryMethodGlobal = QUERY_PATIENT_STUDY_ONLY; L_DicomInitDS( hDSGlobal, CLASS_BASIC_DIRECTORY, DS_METAHEADER_PRESENT|DS_LITTLE_ENDIAN|DS_EXPLICIT_VR|DS_GROUP_LENGTHS ); TreeView_DeleteAllItems(hTreeDir); TreeView_DeleteAllItems(hTreeKey); hItemGlobal = NULL; nPresentationID = L_DicomFindAbstract(hAssociateAccept, UID_PATIENT_STUDY_QUERY_FIND); if ( (nPresentationID == 0) || (L_DicomGetResult(hAssociateAccept, nPresentationID) != PDU_ACCEPT_RESULT_SUCCESS) ) { LogMessage(MSG_ERROR, "C-FIND_RQ\nPresentation ID not found"); return; } hDSLocal = L_DicomCreateDS(szTempFilesFolder); L_DicomInitDS( hDSLocal, CLASS_PATIENT_STUDY_QUERY_PATIENT, DS_METAHEADER_ABSENT|DS_LITTLE_ENDIAN|DS_EXPLICIT_VR ); pElement = L_DicomFindFirstElement( hDSLocal, NULL, TAG_QUERY_RETRIEVE_LEVEL, TRUE); if (pElement == NULL) { pElement = L_DicomInsertElement( hDSLocal, NULL, FALSE, TAG_QUERY_RETRIEVE_LEVEL, 0, FALSE, 0 ); } L_DicomSetStringValue(hDSLocal, pElement, "PATIENT", 1); pElement = L_DicomFindFirstElement(hDSLocal, NULL, TAG_PATIENT_NAME, TRUE); if (pElement == NULL) { pElement = L_DicomInsertElement(hDSLocal, NULL, FALSE, TAG_PATIENT_NAME, 0, FALSE, 0); } L_DicomSetStringValue(hDSLocal, pElement, pPatient->szPatientName, 1); pElement = L_DicomFindFirstElement(hDSLocal, NULL, TAG_PATIENT_ID, TRUE); if (pElement == NULL) { pElement = L_DicomInsertElement(hDSLocal, NULL, FALSE, TAG_PATIENT_ID, 0, FALSE, 0); } L_DicomSetStringValue(hDSLocal, pElement, pPatient->szPatientID, 1); lstrcpy(szRetrieveAEsMsg, ""); StartProcess(PROCESS_C_FIND, nPresentationID); switch (uSecureMode) { case DICOM_SECURE_NONE: nResult = L_DicomSendCFindRequest( hNetGlobal, nPresentationID, uUniqueMessageID++, UID_PATIENT_STUDY_QUERY_FIND, COMMAND_PRIORITY_MEDIUM, hDSLocal); break; case DICOM_SECURE_ISCL: nResult = L_DicomSendCFindRequest( hNetGlobalISCL, nPresentationID, uUniqueMessageID++, UID_PATIENT_STUDY_QUERY_FIND, COMMAND_PRIORITY_MEDIUM, hDSLocal); break; case DICOM_SECURE_TLS: nResult = L_DicomSendCFindRequest( hNetGlobalTLS, nPresentationID, uUniqueMessageID++, UID_PATIENT_STUDY_QUERY_FIND, COMMAND_PRIORITY_MEDIUM, hDSLocal); break; } LogMessage(MSG_SEND, "C-FIND-RQ"); if (nResult != DICOM_SUCCESS) FinishProcess(PROCESS_C_FIND); L_DicomFreeDS(hDSLocal); } L_VOID Retrieve() { HDICOMNET hNet; HTREEITEM hDirItem; HDICOMDS hIdentifier; pDICOMELEMENT pDR, pQRLevelElement; L_CHAR* pszDRType, * pszAbstractSyntax; L_UCHAR nPresentationID; L_INT nResult; hNet = NULL; switch (uSecureMode) { case DICOM_SECURE_NONE: hNet = hNetGlobal; break; case DICOM_SECURE_ISCL: hNet = hNetGlobalISCL; break; case DICOM_SECURE_TLS: hNet = hNetGlobalTLS; break; } hDirItem = TreeView_GetSelection(hTreeDir); if (hDirItem == NULL) { return; } pDR = (pDICOMELEMENT) TV_GetItemData(hTreeDir, hDirItem); if (pDR == NULL || L_DicomExistsElement(hDSGlobal, pDR) == FALSE || L_DicomIsAssociated(hNet) == FALSE || processGlobal.nStatus == PROCESS_STATUS_PENDING) { return; } hIdentifier = L_DicomCreateDS(szTempFilesFolder); L_DicomInitDS(hIdentifier, CLASS_UNKNOWN, DS_LITTLE_ENDIAN | DS_EXPLICIT_VR); pQRLevelElement = L_DicomFindFirstElement(hIdentifier, NULL, TAG_QUERY_RETRIEVE_LEVEL, FALSE); if (pQRLevelElement == NULL) { pQRLevelElement = L_DicomInsertElement(hIdentifier, NULL, FALSE, TAG_QUERY_RETRIEVE_LEVEL, VR_CS, FALSE, 0); if (pQRLevelElement == NULL) { L_DicomFreeDS(hIdentifier); return; } } pszDRType = L_DicomGetValueKey(hDSGlobal, pDR); if (lstrcmpi("PATIENT", pszDRType) == 0) { if (L_DicomSetStringValue(hIdentifier, pQRLevelElement, "PATIENT", 1) == FALSE) { L_DicomFreeDS(hIdentifier); return; } CopyTagKey(hDSGlobal, hIdentifier, pDR, "PATIENT", TAG_PATIENT_ID); } else if (lstrcmpi("STUDY", pszDRType) == 0) { if (L_DicomSetStringValue(hIdentifier, pQRLevelElement, "STUDY", 1) == FALSE) { L_DicomFreeDS(hIdentifier); return; } CopyTagKey(hDSGlobal, hIdentifier, pDR, "STUDY", TAG_STUDY_INSTANCE_UID); if (nQueryMethodGlobal != QUERY_STUDY_ROOT) { hDirItem = TreeView_GetParent(hTreeDir, hDirItem); if (hDirItem) { CopyTagKey(hDSGlobal, hIdentifier, (pDICOMELEMENT) TV_GetItemData(hTreeDir, hDirItem), "PATIENT", TAG_PATIENT_ID); } else { L_DicomFreeDS(hIdentifier); return; } } } else if (nQueryMethodGlobal != QUERY_PATIENT_STUDY_ONLY) { if (lstrcmpi("SERIES", pszDRType) == 0) { if (L_DicomSetStringValue(hIdentifier, pQRLevelElement, "SERIES", 1) == FALSE) { L_DicomFreeDS(hIdentifier); return; } CopyTagKey(hDSGlobal, hIdentifier, pDR, "SERIES", TAG_SERIES_INSTANCE_UID); hDirItem = TreeView_GetParent(hTreeDir, hDirItem); if (hDirItem) { CopyTagKey(hDSGlobal, hIdentifier, (pDICOMELEMENT) TV_GetItemData(hTreeDir, hDirItem), "STUDY", TAG_STUDY_INSTANCE_UID); } else { L_DicomFreeDS(hIdentifier); return; } if (nQueryMethodGlobal != QUERY_STUDY_ROOT) { hDirItem = TreeView_GetParent(hTreeDir, hDirItem); if (hDirItem) { CopyTagKey(hDSGlobal, hIdentifier, (pDICOMELEMENT) TV_GetItemData(hTreeDir, hDirItem), "PATIENT", TAG_PATIENT_ID); } else { L_DicomFreeDS(hIdentifier); return; } } } else if (lstrcmpi("IMAGE", pszDRType) == 0) { if (CheckAvailability(pDR) == FALSE) { L_DicomFreeDS(hIdentifier); return; } if (L_DicomSetStringValue(hIdentifier, pQRLevelElement, "IMAGE", 1) == FALSE) { L_DicomFreeDS(hIdentifier); return; } CopyTagKey(hDSGlobal, hIdentifier, pDR, "IMAGE", TAG_SOP_INSTANCE_UID); hDirItem = TreeView_GetParent(hTreeDir, hDirItem); if (hDirItem) { CopyTagKey(hDSGlobal, hIdentifier, (pDICOMELEMENT) TV_GetItemData(hTreeDir, hDirItem), "SERIES", TAG_SERIES_INSTANCE_UID); } else { L_DicomFreeDS(hIdentifier); return; } hDirItem = TreeView_GetParent(hTreeDir, hDirItem); if (hDirItem) { CopyTagKey(hDSGlobal, hIdentifier, (pDICOMELEMENT) TV_GetItemData(hTreeDir, hDirItem), "STUDY", TAG_STUDY_INSTANCE_UID); } else { L_DicomFreeDS(hIdentifier); return; } if (nQueryMethodGlobal != QUERY_STUDY_ROOT) { hDirItem = TreeView_GetParent(hTreeDir, hDirItem); if (hDirItem) { CopyTagKey(hDSGlobal, hIdentifier, (pDICOMELEMENT) TV_GetItemData(hTreeDir, hDirItem), "PATIENT", TAG_PATIENT_ID); } else { L_DicomFreeDS(hIdentifier); return; } } } else { L_DicomFreeDS(hIdentifier); return; } } else { L_DicomFreeDS(hIdentifier); return; } pszAbstractSyntax = NULL; switch (nQueryMethodGlobal) { case QUERY_PATIENT_ROOT: pszAbstractSyntax = UID_PATIENT_ROOT_QUERY_MOVE; break; case QUERY_STUDY_ROOT: pszAbstractSyntax = UID_STUDY_ROOT_QUERY_MOVE; break; case QUERY_PATIENT_STUDY_ONLY: pszAbstractSyntax = UID_PATIENT_STUDY_QUERY_MOVE; break; } nPresentationID = L_DicomFindAbstract(hAssociateAccept, pszAbstractSyntax); if (nPresentationID == 0 || L_DicomGetResult(hAssociateAccept, nPresentationID) != PDU_ACCEPT_RESULT_SUCCESS) { LogMessage(MSG_ERROR, "C-MOVE-RQ\nPresentation ID not found"); L_DicomFreeDS(hIdentifier); return; } // Start listening; the server will establish an Association with us to // move the SOP instances nResult = L_DicomListen(hNetListenGlobal, NULL, connections.connection[iIndexConnectionGlobal].uClientPort, 1); if (nResult != DICOM_SUCCESS) { L_DicomFreeDS(hIdentifier); return; } LogMessage(MSG_SEND, "C-MOVE-RQ"); StartProcess(PROCESS_C_MOVE, nPresentationID); nResult = L_DicomSendCMoveRequest(hNet, nPresentationID, uUniqueMessageID++, pszAbstractSyntax, COMMAND_PRIORITY_MEDIUM, L_DicomGetCalling(hAssociateAccept), hIdentifier); if (nResult != DICOM_SUCCESS) FinishProcess(PROCESS_C_MOVE); L_DicomFreeDS(hIdentifier); }