コード例 #1
0
		public DicomResponse(DicomMessage request, DicomStatus status) : base() {
			Type = (DicomCommandField)(0x8000 | (int)request.Type);
			SOPClassUID = request.SOPClassUID;
			RequestMessageID = request.MessageID;
			Status = status;
			abstractSyntaxUID = request.abstractSyntaxUID;
		}
コード例 #2
0
ファイル: DicomResponse.cs プロジェクト: vdrm/fo-dicom
 public DicomResponse(DicomMessage request, DicomStatus status)
     : base()
 {
     Type = (DicomCommandField)(0x8000 | (int)request.Type);
     AffectedSOPClassUID = request.AffectedSOPClassUID;
     RequestMessageID = request.MessageID;
     Status = status;
 }
コード例 #3
0
ファイル: DicomResponse.cs プロジェクト: dremerdt/fo-dicom
		public DicomResponse(DicomMessage request, DicomStatus status) : base() {

            PresentationContext = request.PresentationContext;

			Type = (DicomCommandField)(0x8000 | (int)request.Type);
			SOPClassUID = request.SOPClassUID;
			RequestMessageID = request.MessageID;
			Status = status;
		}
コード例 #4
0
ファイル: DicomService.cs プロジェクト: gustavosaita/fo-dicom
 private void SendMessage(DicomMessage message)
 {
     lock (_lock) _msgQueue.Enqueue(message);
     SendNextMessage();
 }
コード例 #5
0
ファイル: DicomService.cs プロジェクト: gustavosaita/fo-dicom
        private void PerformDimse(DicomMessage dimse)
        {
            try
            {
                Logger.Info("{logId} <- {dicomMessage}", LogID, dimse.ToString(Options.LogDimseDatasets));

                if (!DicomMessage.IsRequest(dimse.Type))
                {
                    var rsp = dimse as DicomResponse;
                    lock (_lock)
                    {
                        var req = _pending.FirstOrDefault(x => x.MessageID == rsp.RequestMessageID);
                        if (req != null)
                        {
                            rsp.UserState = req.UserState;
                            req.PostResponse(this, rsp);
                            if (rsp.Status.State != DicomState.Pending) _pending.Remove(req);
                        }
                    }
                    return;
                }

                if (dimse.Type == DicomCommandField.CStoreRequest)
                {
                    if (this is IDicomCStoreProvider)
                    {
                        var response = (this as IDicomCStoreProvider).OnCStoreRequest(dimse as DicomCStoreRequest);
                        SendResponse(response);
                        return;
                    }
                    else throw new DicomNetworkException("C-Store SCP not implemented");
                }

                if (dimse.Type == DicomCommandField.CFindRequest)
                {
                    if (this is IDicomCFindProvider)
                    {
                        var responses = (this as IDicomCFindProvider).OnCFindRequest(dimse as DicomCFindRequest);
                        foreach (var response in responses) SendResponse(response);
                        return;
                    }
                    else throw new DicomNetworkException("C-Find SCP not implemented");
                }

                if (dimse.Type == DicomCommandField.CMoveRequest)
                {
                    if (this is IDicomCMoveProvider)
                    {
                        var responses = (this as IDicomCMoveProvider).OnCMoveRequest(dimse as DicomCMoveRequest);
                        foreach (var response in responses) SendResponse(response);
                        return;
                    }
                    else throw new DicomNetworkException("C-Move SCP not implemented");
                }

                if (dimse.Type == DicomCommandField.CEchoRequest)
                {
                    if (this is IDicomCEchoProvider)
                    {
                        var response = (this as IDicomCEchoProvider).OnCEchoRequest(dimse as DicomCEchoRequest);
                        SendResponse(response);
                        return;
                    }
                    else throw new DicomNetworkException("C-Echo SCP not implemented");
                }

                if (dimse.Type == DicomCommandField.NActionRequest || dimse.Type == DicomCommandField.NCreateRequest
                    || dimse.Type == DicomCommandField.NDeleteRequest
                    || dimse.Type == DicomCommandField.NEventReportRequest
                    || dimse.Type == DicomCommandField.NGetRequest || dimse.Type == DicomCommandField.NSetRequest)
                {
                    if (!(this is IDicomNServiceProvider)) throw new DicomNetworkException("N-Service SCP not implemented");

                    DicomResponse response = null;
                    if (dimse.Type == DicomCommandField.NActionRequest) response = (this as IDicomNServiceProvider).OnNActionRequest(dimse as DicomNActionRequest);
                    else if (dimse.Type == DicomCommandField.NCreateRequest) response = (this as IDicomNServiceProvider).OnNCreateRequest(dimse as DicomNCreateRequest);
                    else if (dimse.Type == DicomCommandField.NDeleteRequest)
                        response =
                            (this as IDicomNServiceProvider).OnNDeleteRequest(dimse as DicomNDeleteRequest);
                    else if (dimse.Type == DicomCommandField.NEventReportRequest)
                        response =
                            (this as IDicomNServiceProvider).OnNEventReportRequest(
                                dimse as DicomNEventReportRequest);
                    else if (dimse.Type == DicomCommandField.NGetRequest)
                        response =
                            (this as IDicomNServiceProvider).OnNGetRequest(dimse as DicomNGetRequest);
                    else if (dimse.Type == DicomCommandField.NSetRequest)
                        response =
                            (this as IDicomNServiceProvider).OnNSetRequest(
                                dimse as DicomNSetRequest);

                    SendResponse(response);
                    return;
                }

                throw new DicomNetworkException("Operation not implemented");
            }
            finally
            {
                SendNextMessage();
            }
        }
コード例 #6
0
ファイル: DicomService.cs プロジェクト: gustavosaita/fo-dicom
        /// <summary>
        /// Process P-DATA-TF PDUs.
        /// </summary>
        /// <param name="pdu">PDU to process.</param>
        private async Task ProcessPDataTFAsync(PDataTF pdu)
        {
            try
            {
                foreach (var pdv in pdu.PDVs)
                {
                    if (_dimse == null)
                    {
                        // create stream for receiving command
                        if (_dimseStream == null)
                        {
                            _dimseStream = new MemoryStream();
                            _dimseStreamFile = null;
                        }
                    }
                    else
                    {
                        // create stream for receiving dataset
                        if (_dimseStream == null)
                        {
                            if (_dimse.Type == DicomCommandField.CStoreRequest)
                            {
                                var pc = Association.PresentationContexts.FirstOrDefault(x => x.ID == pdv.PCID);

                                var file = new DicomFile();
                                file.FileMetaInfo.MediaStorageSOPClassUID = pc.AbstractSyntax;
                                file.FileMetaInfo.MediaStorageSOPInstanceUID =
                                    _dimse.Command.Get<DicomUID>(DicomTag.AffectedSOPInstanceUID);
                                file.FileMetaInfo.TransferSyntax = pc.AcceptedTransferSyntax;
                                file.FileMetaInfo.ImplementationClassUID = Association.RemoteImplemetationClassUID;
                                file.FileMetaInfo.ImplementationVersionName = Association.RemoteImplementationVersion;
                                file.FileMetaInfo.SourceApplicationEntityTitle = Association.CallingAE;

                                CreateCStoreReceiveStream(file);
                            }
                            else
                            {
                                _dimseStream = new MemoryStream();
                                _dimseStreamFile = null;
                            }
                        }
                    }

                    await this._dimseStream.WriteAsync(pdv.Value, 0, pdv.Value.Length).ConfigureAwait(false);

                    if (pdv.IsLastFragment)
                    {
                        if (pdv.IsCommand)
                        {
                            _dimseStream.Seek(0, SeekOrigin.Begin);

                            var command = new DicomDataset();

                            var reader = new DicomReader();
                            reader.IsExplicitVR = false;
                            reader.Read(new StreamByteSource(_dimseStream), new DicomDatasetReaderObserver(command));

                            _dimseStream = null;
                            _dimseStreamFile = null;

                            var type = command.Get<DicomCommandField>(DicomTag.CommandField);
                            switch (type)
                            {
                                case DicomCommandField.CStoreRequest:
                                    _dimse = new DicomCStoreRequest(command);
                                    break;
                                case DicomCommandField.CStoreResponse:
                                    _dimse = new DicomCStoreResponse(command);
                                    break;
                                case DicomCommandField.CFindRequest:
                                    _dimse = new DicomCFindRequest(command);
                                    break;
                                case DicomCommandField.CFindResponse:
                                    _dimse = new DicomCFindResponse(command);
                                    break;
                                case DicomCommandField.CMoveRequest:
                                    _dimse = new DicomCMoveRequest(command);
                                    break;
                                case DicomCommandField.CMoveResponse:
                                    _dimse = new DicomCMoveResponse(command);
                                    break;
                                case DicomCommandField.CEchoRequest:
                                    _dimse = new DicomCEchoRequest(command);
                                    break;
                                case DicomCommandField.CEchoResponse:
                                    _dimse = new DicomCEchoResponse(command);
                                    break;
                                case DicomCommandField.NActionRequest:
                                    _dimse = new DicomNActionRequest(command);
                                    break;
                                case DicomCommandField.NActionResponse:
                                    _dimse = new DicomNActionResponse(command);
                                    break;
                                case DicomCommandField.NCreateRequest:
                                    _dimse = new DicomNCreateRequest(command);
                                    break;
                                case DicomCommandField.NCreateResponse:
                                    _dimse = new DicomNCreateResponse(command);
                                    break;
                                case DicomCommandField.NDeleteRequest:
                                    _dimse = new DicomNDeleteRequest(command);
                                    break;
                                case DicomCommandField.NDeleteResponse:
                                    _dimse = new DicomNDeleteResponse(command);
                                    break;
                                case DicomCommandField.NEventReportRequest:
                                    _dimse = new DicomNEventReportRequest(command);
                                    break;
                                case DicomCommandField.NEventReportResponse:
                                    _dimse = new DicomNEventReportResponse(command);
                                    break;
                                case DicomCommandField.NGetRequest:
                                    _dimse = new DicomNGetRequest(command);
                                    break;
                                case DicomCommandField.NGetResponse:
                                    _dimse = new DicomNGetResponse(command);
                                    break;
                                case DicomCommandField.NSetRequest:
                                    _dimse = new DicomNSetRequest(command);
                                    break;
                                case DicomCommandField.NSetResponse:
                                    _dimse = new DicomNSetResponse(command);
                                    break;
                                default:
                                    _dimse = new DicomMessage(command);
                                    break;
                            }
                            _dimse.PresentationContext =
                                Association.PresentationContexts.FirstOrDefault(x => x.ID == pdv.PCID);
                            if (!_dimse.HasDataset)
                            {
                                this.PerformDimse(this._dimse);
                                _dimse = null;
                                return;
                            }
                        }
                        else
                        {
                            if (_dimse.Type != DicomCommandField.CStoreRequest)
                            {
                                _dimseStream.Seek(0, SeekOrigin.Begin);

                                var pc = Association.PresentationContexts.FirstOrDefault(x => x.ID == pdv.PCID);

                                _dimse.Dataset = new DicomDataset();
                                _dimse.Dataset.InternalTransferSyntax = pc.AcceptedTransferSyntax;

                                var source = new StreamByteSource(_dimseStream);
                                source.Endian = pc.AcceptedTransferSyntax.Endian;

                                var reader = new DicomReader();
                                reader.IsExplicitVR = pc.AcceptedTransferSyntax.IsExplicitVR;
                                reader.Read(source, new DicomDatasetReaderObserver(_dimse.Dataset));

                                _dimseStream = null;
                                _dimseStreamFile = null;
                            }
                            else
                            {
                                var request = _dimse as DicomCStoreRequest;

                                try
                                {
                                    var dicomFile = GetCStoreDicomFile();
                                    _dimseStream = null;
                                    _dimseStreamFile = null;

                                    // NOTE: dicomFile will be valid with the default implementation of CreateCStoreReceiveStream() and
                                    // GetCStoreDicomFile(), but can be null if a child class overrides either method and changes behavior.
                                    // See documentation on CreateCStoreReceiveStream() and GetCStoreDicomFile() for information about why
                                    // this might be desired.
                                    request.File = dicomFile;
                                    if (request.File != null)
                                    {
                                        request.Dataset = request.File.Dataset;
                                    }
                                }
                                catch (Exception e)
                                {
                                    // failed to parse received DICOM file; send error response instead of aborting connection
                                    SendResponse(
                                        new DicomCStoreResponse(
                                            request,
                                            new DicomStatus(DicomStatus.ProcessingFailure, e.Message)));
                                    Logger.Error("Error parsing C-Store dataset: {@error}", e);
                                    (this as IDicomCStoreProvider).OnCStoreRequestException(
                                        _dimseStreamFile != null ? _dimseStreamFile.Name : null, e);
                                    return;
                                }
                            }

                            this.PerformDimse(this._dimse);
                            _dimse = null;
                        }
                    }
                }
            }
            catch (Exception e)
            {
                SendAbort(DicomAbortSource.ServiceUser, DicomAbortReason.NotSpecified);
                Logger.Error("Exception processing P-Data-TF PDU: {@error}", e);
            }
            finally
            {
                SendNextMessage();
            }
        }
コード例 #7
0
ファイル: DicomService.cs プロジェクト: jinyda/fo-dicom
		private void ProcessPDataTF(object state) {
			var pdu = (PDataTF)state;
			try {
				foreach (var pdv in pdu.PDVs) {
					if (_dimse == null) {
						// create stream for receiving command
						if (_dimseStream == null)
							_dimseStream = new MemoryStream();
					} else {
						// create stream for receiving dataset
						if (_dimseStream == null) {
							if (_dimse.Type == DicomCommandField.CStoreRequest) {
								var pc = Association.PresentationContexts.FirstOrDefault(x => x.ID == pdv.PCID);

								var file = new DicomFile();
								file.FileMetaInfo.MediaStorageSOPClassUID = pc.AbstractSyntax;
								file.FileMetaInfo.MediaStorageSOPInstanceUID = _dimse.Command.Get<DicomUID>(DicomTag.AffectedSOPInstanceUID);
								file.FileMetaInfo.TransferSyntax = pc.AcceptedTransferSyntax;
								file.FileMetaInfo.ImplementationClassUID = Association.RemoteImplemetationClassUID;
								file.FileMetaInfo.ImplementationVersionName = Association.RemoteImplementationVersion;
								file.FileMetaInfo.SourceApplicationEntityTitle = Association.CallingAE;

								var fileName = TemporaryFile.Create();

								file.Save(fileName);

								_dimseStream = File.OpenWrite(fileName);
								_dimseStream.Seek(0, SeekOrigin.End);
							} else {
								_dimseStream = new MemoryStream();
							}
						}
					}

					_dimseStream.Write(pdv.Value, 0, pdv.Value.Length);

					if (pdv.IsLastFragment) {
						if (pdv.IsCommand) {
							_dimseStream.Seek(0, SeekOrigin.Begin);

							var command = new DicomDataset();

							var reader = new DicomReader();
							reader.IsExplicitVR = false;
							reader.Read(new StreamByteSource(_dimseStream), new DicomDatasetReaderObserver(command));

							_dimseStream = null;

							var type = command.Get<DicomCommandField>(DicomTag.CommandField);
							switch (type) {
							case DicomCommandField.CStoreRequest:
								_dimse = new DicomCStoreRequest(command);
								break;
							case DicomCommandField.CStoreResponse:
								_dimse = new DicomCStoreResponse(command);
								break;
							case DicomCommandField.CFindRequest:
								_dimse = new DicomCFindRequest(command);
								break;
							case DicomCommandField.CFindResponse:
								_dimse = new DicomCFindResponse(command);
								break;
							case DicomCommandField.CMoveRequest:
								_dimse = new DicomCMoveRequest(command);
								break;
							case DicomCommandField.CMoveResponse:
								_dimse = new DicomCMoveResponse(command);
								break;
							case DicomCommandField.CEchoRequest:
								_dimse = new DicomCEchoRequest(command);
								break;
							case DicomCommandField.CEchoResponse:
								_dimse = new DicomCEchoResponse(command);
								break;
							case DicomCommandField.NActionRequest:
								_dimse = new DicomNActionRequest(command);
								break;
							case DicomCommandField.NActionResponse:
								_dimse = new DicomNActionResponse(command);
								break;
							case DicomCommandField.NCreateRequest:
								_dimse = new DicomNCreateRequest(command);
								break;
							case DicomCommandField.NCreateResponse:
								_dimse = new DicomNCreateResponse(command);
								break;
							case DicomCommandField.NDeleteRequest:
								_dimse = new DicomNDeleteRequest(command);
								break;
							case DicomCommandField.NDeleteResponse:
								_dimse = new DicomNDeleteResponse(command);
								break;
							case DicomCommandField.NEventReportRequest:
								_dimse = new DicomNEventReportRequest(command);
								break;
							case DicomCommandField.NEventReportResponse:
								_dimse = new DicomNEventReportResponse(command);
								break;
							case DicomCommandField.NGetRequest:
								_dimse = new DicomNGetRequest(command);
								break;
							case DicomCommandField.NGetResponse:
								_dimse = new DicomNGetResponse(command);
								break;
							case DicomCommandField.NSetRequest:
								_dimse = new DicomNSetRequest(command);
								break;
							case DicomCommandField.NSetResponse:
								_dimse = new DicomNSetResponse(command);
								break;
							default:
								_dimse = new DicomMessage(command);
								break;
							}

							if (!_dimse.HasDataset) {
								if (DicomMessage.IsRequest(_dimse.Type))
									ThreadPool.QueueUserWorkItem(PerformDimseCallback, _dimse);
								else
									_processQueue.Queue((_dimse as DicomResponse).RequestMessageID, PerformDimseCallback, _dimse);
								_dimse = null;
								return;
							}
						} else {
							if (_dimse.Type != DicomCommandField.CStoreRequest) {
								_dimseStream.Seek(0, SeekOrigin.Begin);

								var pc = Association.PresentationContexts.FirstOrDefault(x => x.ID == pdv.PCID);

								_dimse.Dataset = new DicomDataset();
								_dimse.Dataset.InternalTransferSyntax = pc.AcceptedTransferSyntax;

								var source = new StreamByteSource(_dimseStream);
								source.Endian = pc.AcceptedTransferSyntax.Endian;

								var reader = new DicomReader();
								reader.IsExplicitVR = pc.AcceptedTransferSyntax.IsExplicitVR;
								reader.Read(source, new DicomDatasetReaderObserver(_dimse.Dataset));

								_dimseStream = null;
							} else {
								var fileName = (_dimseStream as FileStream).Name;
								_dimseStream.Close();
								_dimseStream = null;

								var request = _dimse as DicomCStoreRequest;

								try {
									request.File = DicomFile.Open(fileName);
								} catch (Exception e) {
									// failed to parse received DICOM file; send error response instead of aborting connection
									SendResponse(new DicomCStoreResponse(request, new DicomStatus(DicomStatus.ProcessingFailure, e.Message)));
									Logger.Error("Error parsing C-Store dataset: " + e.ToString());
									(this as IDicomCStoreProvider).OnCStoreRequestException(fileName, e);
									return;
								}

								request.File.File.IsTempFile = true;
								request.Dataset = request.File.Dataset;
							}

							if (DicomMessage.IsRequest(_dimse.Type))
								ThreadPool.QueueUserWorkItem(PerformDimseCallback, _dimse);
							else
								_processQueue.Queue((_dimse as DicomResponse).RequestMessageID, PerformDimseCallback, _dimse);
							_dimse = null;
						}
					}
				}
			} catch (Exception e) {
				SendAbort(DicomAbortSource.ServiceUser, DicomAbortReason.NotSpecified);
				Logger.Error("Exception processing P-Data-TF PDU: " + e.ToString());
			} finally {
				SendNextMessage();
			}
		}
コード例 #8
0
ファイル: DicomService.cs プロジェクト: zhan2016/fo-dicom
 private void SendMessage(DicomMessage message)
 {
     lock (_lock)
         _msgQueue.Enqueue(message);
     SendNextMessage();
 }
コード例 #9
0
ファイル: DicomService.cs プロジェクト: zhan2016/fo-dicom
        private void PerformDimseCallback(object state)
        {
            var dimse = state as DicomMessage;

            try {
                Logger.Info("{logId} <- {dicomMessage}", LogID, dimse.ToString(Options.LogDimseDatasets));

                if (!DicomMessage.IsRequest(dimse.Type))
                {
                    var rsp = dimse as DicomResponse;
                    lock (_lock) {
                        var req = _pending.FirstOrDefault(x => x.MessageID == rsp.RequestMessageID);
                        if (req != null)
                        {
                            rsp.UserState = req.UserState;
                            (req as DicomRequest).PostResponse(this, rsp);
                            if (rsp.Status.State != DicomState.Pending)
                            {
                                _pending.Remove(req);
                            }
                        }
                    }
                    return;
                }

                if (dimse.Type == DicomCommandField.CStoreRequest)
                {
                    if (this is IDicomCStoreProvider)
                    {
                        var response = (this as IDicomCStoreProvider).OnCStoreRequest(dimse as DicomCStoreRequest);
                        SendResponse(response);
                        return;
                    }
                    else
                    {
                        throw new DicomNetworkException("C-Store SCP not implemented");
                    }
                }

                if (dimse.Type == DicomCommandField.CFindRequest)
                {
                    if (this is IDicomCFindProvider)
                    {
                        var responses = (this as IDicomCFindProvider).OnCFindRequest(dimse as DicomCFindRequest);
                        foreach (var response in responses)
                        {
                            SendResponse(response);
                        }
                        return;
                    }
                    else
                    {
                        throw new DicomNetworkException("C-Find SCP not implemented");
                    }
                }

                if (dimse.Type == DicomCommandField.CMoveRequest)
                {
                    if (this is IDicomCMoveProvider)
                    {
                        var responses = (this as IDicomCMoveProvider).OnCMoveRequest(dimse as DicomCMoveRequest);
                        foreach (var response in responses)
                        {
                            SendResponse(response);
                        }
                        return;
                    }
                    else
                    {
                        throw new DicomNetworkException("C-Move SCP not implemented");
                    }
                }

                if (dimse.Type == DicomCommandField.CEchoRequest)
                {
                    if (this is IDicomCEchoProvider)
                    {
                        var response = (this as IDicomCEchoProvider).OnCEchoRequest(dimse as DicomCEchoRequest);
                        SendResponse(response);
                        return;
                    }
                    else
                    {
                        throw new DicomNetworkException("C-Echo SCP not implemented");
                    }
                }

                if (dimse.Type == DicomCommandField.NActionRequest || dimse.Type == DicomCommandField.NCreateRequest ||
                    dimse.Type == DicomCommandField.NDeleteRequest || dimse.Type == DicomCommandField.NEventReportRequest ||
                    dimse.Type == DicomCommandField.NGetRequest || dimse.Type == DicomCommandField.NSetRequest)
                {
                    if (!(this is IDicomNServiceProvider))
                    {
                        throw new DicomNetworkException("N-Service SCP not implemented");
                    }

                    DicomResponse response = null;
                    if (dimse.Type == DicomCommandField.NActionRequest)
                    {
                        response = (this as IDicomNServiceProvider).OnNActionRequest(dimse as DicomNActionRequest);
                    }
                    else if (dimse.Type == DicomCommandField.NCreateRequest)
                    {
                        response = (this as IDicomNServiceProvider).OnNCreateRequest(dimse as DicomNCreateRequest);
                    }
                    else if (dimse.Type == DicomCommandField.NDeleteRequest)
                    {
                        response = (this as IDicomNServiceProvider).OnNDeleteRequest(dimse as DicomNDeleteRequest);
                    }
                    else if (dimse.Type == DicomCommandField.NEventReportRequest)
                    {
                        response = (this as IDicomNServiceProvider).OnNEventReportRequest(dimse as DicomNEventReportRequest);
                    }
                    else if (dimse.Type == DicomCommandField.NGetRequest)
                    {
                        response = (this as IDicomNServiceProvider).OnNGetRequest(dimse as DicomNGetRequest);
                    }
                    else if (dimse.Type == DicomCommandField.NSetRequest)
                    {
                        response = (this as IDicomNServiceProvider).OnNSetRequest(dimse as DicomNSetRequest);
                    }

                    SendResponse(response);
                    return;
                }

                throw new DicomNetworkException("Operation not implemented");
            } finally {
                SendNextMessage();
            }
        }
コード例 #10
0
ファイル: DicomService.cs プロジェクト: zhan2016/fo-dicom
        private void ProcessPDataTF(object state)
        {
            var pdu = (PDataTF)state;

            try {
                foreach (var pdv in pdu.PDVs)
                {
                    if (_dimse == null)
                    {
                        // create stream for receiving command
                        if (_dimseStream == null)
                        {
                            _dimseStream = new MemoryStream();
                        }
                    }
                    else
                    {
                        // create stream for receiving dataset
                        if (_dimseStream == null)
                        {
                            if (_dimse.Type == DicomCommandField.CStoreRequest)
                            {
                                var pc = Association.PresentationContexts.FirstOrDefault(x => x.ID == pdv.PCID);

                                var file = new DicomFile();
                                file.FileMetaInfo.MediaStorageSOPClassUID      = pc.AbstractSyntax;
                                file.FileMetaInfo.MediaStorageSOPInstanceUID   = _dimse.Command.Get <DicomUID>(DicomTag.AffectedSOPInstanceUID);
                                file.FileMetaInfo.TransferSyntax               = pc.AcceptedTransferSyntax;
                                file.FileMetaInfo.ImplementationClassUID       = Association.RemoteImplemetationClassUID;
                                file.FileMetaInfo.ImplementationVersionName    = Association.RemoteImplementationVersion;
                                file.FileMetaInfo.SourceApplicationEntityTitle = Association.CallingAE;

                                _dimseStream = CreateCStoreReceiveStream(file);
                            }
                            else
                            {
                                _dimseStream = new MemoryStream();
                            }
                        }
                    }

                    _dimseStream.Write(pdv.Value, 0, pdv.Value.Length);

                    if (pdv.IsLastFragment)
                    {
                        if (pdv.IsCommand)
                        {
                            _dimseStream.Seek(0, SeekOrigin.Begin);

                            var command = new DicomDataset();

                            var reader = new DicomReader();
                            reader.IsExplicitVR = false;
                            reader.Read(new StreamByteSource(_dimseStream), new DicomDatasetReaderObserver(command));

                            _dimseStream = null;

                            var type = command.Get <DicomCommandField>(DicomTag.CommandField);
                            switch (type)
                            {
                            case DicomCommandField.CStoreRequest:
                                _dimse = new DicomCStoreRequest(command);
                                break;

                            case DicomCommandField.CStoreResponse:
                                _dimse = new DicomCStoreResponse(command);
                                break;

                            case DicomCommandField.CFindRequest:
                                _dimse = new DicomCFindRequest(command);
                                break;

                            case DicomCommandField.CFindResponse:
                                _dimse = new DicomCFindResponse(command);
                                break;

                            case DicomCommandField.CMoveRequest:
                                _dimse = new DicomCMoveRequest(command);
                                break;

                            case DicomCommandField.CMoveResponse:
                                _dimse = new DicomCMoveResponse(command);
                                break;

                            case DicomCommandField.CEchoRequest:
                                _dimse = new DicomCEchoRequest(command);
                                break;

                            case DicomCommandField.CEchoResponse:
                                _dimse = new DicomCEchoResponse(command);
                                break;

                            case DicomCommandField.NActionRequest:
                                _dimse = new DicomNActionRequest(command);
                                break;

                            case DicomCommandField.NActionResponse:
                                _dimse = new DicomNActionResponse(command);
                                break;

                            case DicomCommandField.NCreateRequest:
                                _dimse = new DicomNCreateRequest(command);
                                break;

                            case DicomCommandField.NCreateResponse:
                                _dimse = new DicomNCreateResponse(command);
                                break;

                            case DicomCommandField.NDeleteRequest:
                                _dimse = new DicomNDeleteRequest(command);
                                break;

                            case DicomCommandField.NDeleteResponse:
                                _dimse = new DicomNDeleteResponse(command);
                                break;

                            case DicomCommandField.NEventReportRequest:
                                _dimse = new DicomNEventReportRequest(command);
                                break;

                            case DicomCommandField.NEventReportResponse:
                                _dimse = new DicomNEventReportResponse(command);
                                break;

                            case DicomCommandField.NGetRequest:
                                _dimse = new DicomNGetRequest(command);
                                break;

                            case DicomCommandField.NGetResponse:
                                _dimse = new DicomNGetResponse(command);
                                break;

                            case DicomCommandField.NSetRequest:
                                _dimse = new DicomNSetRequest(command);
                                break;

                            case DicomCommandField.NSetResponse:
                                _dimse = new DicomNSetResponse(command);
                                break;

                            default:
                                _dimse = new DicomMessage(command);
                                break;
                            }
                            _dimse.PresentationContext = Association.PresentationContexts.FirstOrDefault(x => x.ID == pdv.PCID);
                            if (!_dimse.HasDataset)
                            {
                                if (DicomMessage.IsRequest(_dimse.Type))
                                {
                                    ThreadPool.QueueUserWorkItem(PerformDimseCallback, _dimse);
                                }
                                else
                                {
                                    _processQueue.Queue((_dimse as DicomResponse).RequestMessageID, PerformDimseCallback, _dimse);
                                }
                                _dimse = null;
                                return;
                            }
                        }
                        else
                        {
                            if (_dimse.Type != DicomCommandField.CStoreRequest)
                            {
                                _dimseStream.Seek(0, SeekOrigin.Begin);

                                var pc = Association.PresentationContexts.FirstOrDefault(x => x.ID == pdv.PCID);

                                _dimse.Dataset = new DicomDataset();
                                _dimse.Dataset.InternalTransferSyntax = pc.AcceptedTransferSyntax;

                                var source = new StreamByteSource(_dimseStream);
                                source.Endian = pc.AcceptedTransferSyntax.Endian;

                                var reader = new DicomReader();
                                reader.IsExplicitVR = pc.AcceptedTransferSyntax.IsExplicitVR;
                                reader.Read(source, new DicomDatasetReaderObserver(_dimse.Dataset));

                                _dimseStream = null;
                            }
                            else
                            {
                                var request = _dimse as DicomCStoreRequest;

                                try
                                {
                                    var dicomFile = GetCStoreDicomFile();
                                    _dimseStream = null;
                                    _isTempFile  = false;

                                    // NOTE: dicomFile will be valid with the default implementation of CreateCStoreReceiveStream() and
                                    // GetCStoreDicomFile(), but can be null if a child class overrides either method and changes behavior.
                                    // See documentation on CreateCStoreReceiveStream() and GetCStoreDicomFile() for information about why
                                    // this might be desired.
                                    request.File = dicomFile;
                                    if (request.File != null)
                                    {
                                        request.Dataset = request.File.Dataset;
                                    }
                                }
                                catch (Exception e)
                                {
                                    var fileName = "";
                                    if (_dimseStream is FileStream)
                                    {
                                        fileName = (_dimseStream as FileStream).Name;
                                    }
                                    // failed to parse received DICOM file; send error response instead of aborting connection
                                    SendResponse(new DicomCStoreResponse(request, new DicomStatus(DicomStatus.ProcessingFailure, e.Message)));
                                    Logger.Error("Error parsing C-Store dataset: {@error}", e);
                                    (this as IDicomCStoreProvider).OnCStoreRequestException(fileName, e);
                                    return;
                                }
                            }

                            if (DicomMessage.IsRequest(_dimse.Type))
                            {
                                ThreadPool.QueueUserWorkItem(PerformDimseCallback, _dimse);
                            }
                            else
                            {
                                _processQueue.Queue((_dimse as DicomResponse).RequestMessageID, PerformDimseCallback, _dimse);
                            }
                            _dimse = null;
                        }
                    }
                }
            } catch (Exception e) {
                SendAbort(DicomAbortSource.ServiceUser, DicomAbortReason.NotSpecified);
                Logger.Error("Exception processing P-Data-TF PDU: {@error}", e);
            } finally {
                SendNextMessage();
            }
        }
コード例 #11
0
ファイル: DicomService.cs プロジェクト: aerik/fo-dicom
        private void SendMessage(DicomMessage message)
        {
            lock (_lock)
            {
                _msgQueue.Enqueue(message);

                if (_sending)
                {
                    return;
                }

            }

            SendNextMessage();
        }