NetworkStream の上に作成された GZipStream からデータを読み取るために使用している AsyncCallback を次に示します。
void ReadCompressedDataCallback(IAsyncResult ar)
{
var state = ar.AsyncState as ReadCompressedDataState;
try
{
switch (state.State)
{
case EReadCompressedDataState.BeginRead:
state.State = EReadCompressedDataState.EndRead;
state.InputStream.BeginRead(state.Buf, 0, state.Buf.Length, ReadCompressedDataCallback, state);
break;
case EReadCompressedDataState.EndRead:
var read = state.InputStream.EndRead(ar);
if (read==0)
{
state.OnCompleted();
return;
}
state.Result.Write(state.Buf,0,read);
state.State = EReadCompressedDataState.BeginRead;
ReadCompressedDataCallback(ar);
break;
default:
throw new ArgumentOutOfRangeException();
}
}
catch (Exception e)
{
state.LastException = e;
state.OnCompleted();
}
}
state.InputStream
new GZipStream(NetworkStream) のようなものです。
私の問題は、初めて呼び出すとread = state.InputStream.EndRead(ar);
、read
常に 0 になり、読み取りが停止することです。デバッガーで再度読み取りを開始すると、一部のデータが読み取られます。
私が読んだドキュメントによると、 NetworkStream は、読み取るバイトがもうない場合にのみ読み取り時に 0 バイトを返しますが、ここでは 0 バイトが返され、次の読み取りではいくつかのデータが続きます。
アプリが「デッドロック」して到着しないデータを待つリスクを冒さずに、gzip されたすべてのデータを正しく読み取るにはどうすればよいですか?