콘텐츠로 이동
무료 평가 시작

PDComm.HsmsWorker

클래스

HsmsEndpoint를 전용 백그라운드 스레드에서 실행하고 비동기 메서드로 제공합니다.

public sealed class HsmsWorker : IAsyncDisposable

작업자 스레드가 끝점을 만들어 소유하며 모든 네이티브 호출을 수행합니다. HsmsWorkerOptions.PollIntervalMilliseconds마다, 또는 작업이 도착하면 더 일찍 끝점을 폴링하고, 큐에 들어간 명령을 순서대로 실행하며, HsmsWorker.ReadEventsAsync용으로 이벤트를 버퍼링합니다. 모든 멤버는 스레드로부터 안전합니다.

두 큐는 모두 크기가 제한됩니다. HsmsWorkerOptions.CommandCapacity 또는 HsmsWorkerOptions.MaxCommandBytes에 들어가지 않는 명령은 기다리지 않고 즉시 PdcommStatus.Backpressure로 실패합니다. 이벤트 버퍼가 가득 차면 작업자는 이벤트를 소비할 때까지 네이티브 이벤트 읽기를 멈추며, 그동안 메시지를 보내는 명령은 PdcommStatus.Backpressure로 실패합니다.

이벤트를 계속 읽고 각 이벤트를 해제해야 합니다. 정상적으로 종료하려면 HsmsWorker.StopAsync를 호출하고, HsmsWorker.ReadEventsAsync를 모두 읽고, HsmsWorker.Completion을 기다린 다음 작업자를 해제합니다.

await using HsmsWorker worker = await HsmsWorker.StartAsync(
    address, endpointOptions, workerOptions, deadline.Token);
HsmsToken request = default;
await using IAsyncEnumerator<HsmsEvent> events =
    worker.ReadEventsAsync(deadline.Token).GetAsyncEnumerator();
while (await events.MoveNextAsync())
{
    using HsmsEvent current = events.Current;
    HsmsEventInfo info = current.GetInfo();
    if (request == default && (await worker.GetStateAsync(deadline.Token)).State == HsmsConnectionState.Selected)
    {
        request = await worker.SubmitRequestAsync(1, 1, true, expectedBody, deadline.Token);
    }
    if (info.Kind == HsmsEventKind.Received && info.IsReply && info.Token == request)
    {
        break; // S1F2 received
    }
}
await worker.StopAsync(deadline.Token);
while (await events.MoveNextAsync())
{
    events.Current.Dispose();
}
await worker.Completion.WaitAsync(deadline.Token);

멤버

CancelAsync

메서드

작업자 스레드에서 열린 거래를 취소합니다.

public Task<bool> CancelAsync(HsmsToken token, CancellationToken cancellationToken = default)

명령은 작업자 스레드에서 실행됩니다. 명령 큐나 HsmsWorkerOptions.MaxCommandBytes가 가득 차면 PdcommException(PdcommStatus.Backpressure)으로, 작업자가 명령 수락을 멈춘 뒤에는 ObjectDisposedException으로, 그 밖에는 HsmsEndpoint.Cancel의 예외로 작업이 실패합니다. 명령이 실행되기 전에 cancellationToken이 취소되면 작업이 취소됩니다.

매개변수

이름설명
token거래를 시작할 때 반환된 토큰입니다.
cancellationToken아직 실행을 시작하지 않은 명령을 취소하는 토큰입니다.

반환값

거래가 열려 있었고 이제 취소되었으면 true를 결과로 갖는 작업입니다.

DeselectAsync

메서드

작업자 스레드에서 Deselect.req를 큐에 넣습니다.

public Task<HsmsToken> DeselectAsync(CancellationToken cancellationToken = default)

명령은 작업자 스레드에서 실행됩니다. 명령 큐나 HsmsWorkerOptions.MaxCommandBytes가 가득 찼거나 이벤트 출력이 막혀 있으면 PdcommException(PdcommStatus.Backpressure)으로, 작업자가 명령 수락을 멈춘 뒤에는 ObjectDisposedException으로, 그 밖에는 HsmsEndpoint.Deselect의 예외로 작업이 실패합니다. 명령이 실행되기 전에 cancellationToken이 취소되면 작업이 취소됩니다.

매개변수

이름설명
cancellationToken아직 실행을 시작하지 않은 명령을 취소하는 토큰입니다.

반환값

제어 거래의 토큰을 결과로 갖는 작업입니다.

DisposeAsync

메서드

작업자를 중지하고, 끝점을 닫고, 작업자 스레드가 종료될 때까지 기다립니다.

public ValueTask DisposeAsync()

새 명령은 ObjectDisposedException으로 거부되고, 큐의 명령은 실패하며, 읽지 않은 버퍼의 이벤트는 해제됩니다. 작업자는 그래도 연결을 중지하고 닫힐 때까지 최대 HsmsWorkerOptions.ShutdownTimeoutMilliseconds 동안 기다립니다.

작업자가 오류로 끝났으면(예: 연결이 제시간에 닫히지 않아 발생한 TimeoutException) 이 메서드는 스레드가 종료된 뒤 그 오류를 다시 throw합니다.

반환값

작업자 스레드가 종료되면 완료되는 작업입니다.

GetLocalAddressAsync

메서드

작업자 스레드에서 끝점의 로컬 소켓 주소를 읽습니다.

public Task<string> GetLocalAddressAsync(CancellationToken cancellationToken = default)

명령은 작업자 스레드에서 실행됩니다. 명령 큐나 HsmsWorkerOptions.MaxCommandBytes가 가득 차면 PdcommException(PdcommStatus.Backpressure)으로, 작업자가 명령 수락을 멈춘 뒤에는 ObjectDisposedException으로, 그 밖에는 HsmsEndpoint.GetLocalAddress의 예외로 작업이 실패합니다. 명령이 실행되기 전에 cancellationToken이 취소되면 작업이 취소됩니다.

매개변수

이름설명
cancellationToken아직 실행을 시작하지 않은 명령을 취소하는 토큰입니다.

반환값

숫자 로컬 소켓 주소를 결과로 갖는 작업입니다.

GetStateAsync

메서드

작업자 스레드에서 끝점의 연결 상태를 읽습니다.

public Task<HsmsState> GetStateAsync(CancellationToken cancellationToken = default)

명령은 작업자 스레드에서 실행됩니다. 명령 큐나 HsmsWorkerOptions.MaxCommandBytes가 가득 차면 PdcommException(PdcommStatus.Backpressure)으로, 작업자가 명령 수락을 멈춘 뒤에는 ObjectDisposedException으로, 그 밖에는 HsmsEndpoint.GetState의 예외로 작업이 실패합니다. 명령이 실행되기 전에 cancellationToken이 취소되면 작업이 취소됩니다.

매개변수

이름설명
cancellationToken아직 실행을 시작하지 않은 명령을 취소하는 토큰입니다.

반환값

끝점 상태의 스냅샷을 결과로 갖는 작업입니다.

IsPendingAsync

메서드

작업자 스레드에서 거래가 아직 열려 있는지 확인합니다.

public Task<bool> IsPendingAsync(HsmsToken token, CancellationToken cancellationToken = default)

명령은 작업자 스레드에서 실행됩니다. 명령 큐나 HsmsWorkerOptions.MaxCommandBytes가 가득 차면 PdcommException(PdcommStatus.Backpressure)으로, 작업자가 명령 수락을 멈춘 뒤에는 ObjectDisposedException으로, 그 밖에는 HsmsEndpoint.IsPending의 예외로 작업이 실패합니다. 명령이 실행되기 전에 cancellationToken이 취소되면 작업이 취소됩니다.

매개변수

이름설명
token거래를 시작할 때 반환된 토큰입니다.
cancellationToken아직 실행을 시작하지 않은 명령을 취소하는 토큰입니다.

반환값

거래가 아직 완료되지 않았으면 true를 결과로 갖는 작업입니다.

LinktestAsync

메서드

작업자 스레드에서 Linktest.req를 큐에 넣습니다.

public Task<HsmsToken> LinktestAsync(CancellationToken cancellationToken = default)

명령은 작업자 스레드에서 실행됩니다. 명령 큐나 HsmsWorkerOptions.MaxCommandBytes가 가득 찼거나 이벤트 출력이 막혀 있으면 PdcommException(PdcommStatus.Backpressure)으로, 작업자가 명령 수락을 멈춘 뒤에는 ObjectDisposedException으로, 그 밖에는 HsmsEndpoint.Linktest의 예외로 작업이 실패합니다. 명령이 실행되기 전에 cancellationToken이 취소되면 작업이 취소됩니다.

매개변수

이름설명
cancellationToken아직 실행을 시작하지 않은 명령을 취소하는 토큰입니다.

반환값

제어 거래의 토큰을 결과로 갖는 작업입니다.

ReadEventsAsync

메서드

끝점이 만든 이벤트를 순서대로 읽습니다.

public IAsyncEnumerable<HsmsEvent> ReadEventsAsync(CancellationToken cancellationToken = default)

여러 열거자를 동시에 실행할 수 있으며, 각 이벤트는 그중 하나에만 전달됩니다. 이벤트를 읽으면 이벤트 버퍼의 공간이 비워져 작업자가 폴링을 계속할 수 있습니다.

매개변수

이름설명
cancellationTokenOperationCanceledException으로 열거를 끝내는 토큰입니다.

반환값

이벤트의 비동기 시퀀스입니다. 호출자가 각 이벤트를 소유하며 해제해야 합니다. 시퀀스는 작업자가 종료되면 끝나며, 작업자가 실패했으면 작업자의 치명적 오류를 throw합니다.

ReplyAsync

메서드

작업자 스레드에서 수신 1차 메시지에 대한 응답을 큐에 넣습니다.

public Task ReplyAsync(HsmsEvent primary, byte stream, byte function, bool replyExpected, ReadOnlyMemory<byte> body, CancellationToken cancellationToken = default)

명령은 작업자 스레드에서 실행됩니다. 명령 큐나 HsmsWorkerOptions.MaxCommandBytes가 가득 찼거나 이벤트 출력이 막혀 있으면 PdcommException(PdcommStatus.Backpressure)으로, 작업자가 명령 수락을 멈춘 뒤에는 ObjectDisposedException으로, 그 밖에는 HsmsEndpoint.Reply의 예외로 작업이 실패합니다. 명령이 실행되기 전에 cancellationToken이 취소되면 작업이 취소됩니다. 그 사이에 primary를 해제하더라도 명령이 끝날 때까지 primary는 유효합니다.

매개변수

이름설명
primary응답을 기대하는 수신 1차 메시지 이벤트입니다.
stream응답의 스트림 번호이며, 보통 1차 메시지의 스트림입니다.
function응답의 펑션 번호이며, 보통 1차 메시지의 펑션에 1을 더한 값입니다. 중단하려면 0입니다.
replyExpected응답에 W 비트를 설정할지 여부입니다. 보통 false입니다.
body인코딩된 완전한 SECS-II 아이템 하나이거나, 헤더만 있는 응답이면 비워 둡니다. 복사됩니다.
cancellationToken아직 실행을 시작하지 않은 명령을 취소하는 토큰입니다.

반환값

응답이 끝점의 큐에 들어가면 완료되는 작업입니다.

참고

  • ArgumentNullException 예외: primary가 null입니다.
  • OperationCanceledException 예외: cancellationToken이 이미 취소되었습니다.
  • ObjectDisposedException 예외: primary가 해제되었습니다.
  • PdcommException 예외: body가 HsmsOptions.MaxFrameBytes에서 14를 뺀 값이나 SecsLimits.MessageBytes보다 큽니다(PdcommStatus.LimitExceeded).

SelectAsync

메서드

작업자 스레드에서 Select.req를 큐에 넣습니다.

public Task<HsmsToken> SelectAsync(CancellationToken cancellationToken = default)

명령은 작업자 스레드에서 실행됩니다. 명령 큐나 HsmsWorkerOptions.MaxCommandBytes가 가득 찼거나 이벤트 출력이 막혀 있으면 PdcommException(PdcommStatus.Backpressure)으로, 작업자가 명령 수락을 멈춘 뒤에는 ObjectDisposedException으로, 그 밖에는 HsmsEndpoint.Select의 예외로 작업이 실패합니다. 명령이 실행되기 전에 cancellationToken이 취소되면 작업이 취소됩니다.

매개변수

이름설명
cancellationToken아직 실행을 시작하지 않은 명령을 취소하는 토큰입니다.

반환값

제어 거래의 토큰을 결과로 갖는 작업입니다.

StartAsync

메서드

새 작업자 스레드에서 HSMS 끝점을 만들고 시작합니다.

public static Task<HsmsWorker> StartAsync(string address, HsmsOptions options, HsmsWorkerOptions workerOptions, CancellationToken cancellationToken = default)

비동기 메서드이므로 모든 예외는 반환된 작업을 통해 보고됩니다.

매개변수

이름설명
address연결할(액티브) 또는 수신 대기할(패시브) 숫자 소켓 주소입니다. HsmsEndpoint.Create를 참고합니다.
options끝점의 역할, 세션, 타이머, 한도입니다.
workerOptions작업자의 큐 용량과 타이밍입니다.
cancellationToken시작을 포기하는 토큰입니다. 이 경우 작업자는 해제됩니다.

반환값

실행 중인 작업자를 결과로 갖는 작업입니다. 호출자가 작업자를 소유하며 해제해야 합니다.

참고

  • ArgumentNullException 예외: address, options 또는 workerOptions가 null입니다.
  • ArgumentOutOfRangeException 예외: workerOptions의 용량이나 간격이 양수가 아니거나, 바이트 예산이 음수이거나, HsmsWorkerOptions.MaxEventBytes가 프레임 본문 하나보다 작습니다.
  • OperationCanceledException 예외: 시작 중에 cancellationToken이 취소되었습니다.
  • PdcommException 예외: 끝점을 만들거나 시작할 수 없었습니다. HsmsEndpoint.Create를 참고합니다.

StopAsync

메서드

연결과 작업자의 정상 종료를 시작합니다.

public Task StopAsync(CancellationToken cancellationToken = default)

중지 후 작업자는 연결이 닫히고, 네이티브 이벤트가 비워지고, 큐의 명령이 모두 실행될 때까지 폴링을 계속한 다음 종료하며 HsmsWorker.Completion을 완료합니다. 그동안 이벤트를 계속 읽어야 합니다. HsmsWorkerOptions.ShutdownTimeoutMilliseconds 안에 이 과정이 끝나지 않으면 HsmsWorker.Completion이 TimeoutException으로 실패합니다. 중지 후 이 메서드를 다시 호출해도 추가 효과가 없습니다.

매개변수

이름설명
cancellationToken아직 실행을 시작하지 않은 명령을 취소하는 토큰입니다.

반환값

연결이 닫혔을 때가 아니라 중지가 요청되었을 때 완료되는 작업입니다.

SubmitRequestAsync

메서드

작업자 스레드에서 1차 데이터 메시지를 큐에 넣습니다.

public Task<HsmsToken> SubmitRequestAsync(byte stream, byte function, bool replyExpected, ReadOnlyMemory<byte> body, CancellationToken cancellationToken = default)

명령은 작업자 스레드에서 실행됩니다. 명령 큐나 HsmsWorkerOptions.MaxCommandBytes가 가득 찼거나 이벤트 출력이 막혀 있으면 PdcommException(PdcommStatus.Backpressure)으로, 작업자가 명령 수락을 멈춘 뒤에는 ObjectDisposedException으로, 그 밖에는 HsmsEndpoint.Request의 예외로 작업이 실패합니다. 명령이 실행되기 전에 cancellationToken이 취소되면 작업이 취소됩니다.

매개변수

이름설명
streamSECS-II 스트림 번호(0~127)입니다.
functionSECS-II 펑션 번호입니다. 1차 메시지는 홀수를 사용합니다.
replyExpectedW 비트를 설정하고 T3 안에 응답을 기다릴지 여부입니다.
body인코딩된 완전한 SECS-II 아이템 하나이거나, 헤더만 있는 메시지이면 비워 둡니다. 복사됩니다.
cancellationToken아직 실행을 시작하지 않은 명령을 취소하는 토큰입니다.

반환값

거래의 토큰을 결과로 갖는 작업입니다. 응답이나 실패는 나중에 같은 토큰으로 HsmsWorker.ReadEventsAsync를 통해 도착합니다.

참고

  • PdcommException 예외: body가 HsmsOptions.MaxFrameBytes에서 14를 뺀 값이나 SecsLimits.MessageBytes보다 큽니다(PdcommStatus.LimitExceeded).

Completion

속성

작업자 스레드가 종료되고 끝점을 해제하면 완료되는 작업을 가져옵니다.

public Task Completion { get; }

중지로 연결이 닫히고, 네이티브 이벤트가 비워지고, 큐의 모든 명령이 실행된 뒤 작업이 성공적으로 완료됩니다. 작업자를 종료시킨 오류로 작업이 실패할 수 있습니다. 예를 들어 HsmsWorkerOptions.ShutdownTimeoutMilliseconds 안에 끝점을 닫을 수 없으면 TimeoutException입니다.

LocalAddress

속성

끝점이 수신 대기 중이거나 연결된 동안 로컬 소켓 주소를 가져오고, 그 밖에는 null을 가져옵니다.

public string? LocalAddress { get; }

패시브 작업자는 HsmsWorker.StartAsync가 완료되기 전에 수신 주소를 게시하므로, 포트 0에 대해 선택된 포트를 읽을 수 있습니다. 이 값은 폴링할 때마다 갱신됩니다.