반응형
procedure SendToSocket(Sock : TSocket; Data : PaData; Len : Integer);
var
Overlap : OVERLAPPED;
BytesWritten : DWord;
BytesSend : Integer;
begin
{ create overlapped structure with controlling event }
FillChar(OverLap, SizeOf(OVERLAPPED), 0);
OverLap.hEvent := CreateEvent(nil, True, False, '');
if OverLap.hEvent = 0 then
{ event is not created }
RaiseLastWin32Error;
try
BytesSend := 0;
while BytesSend < Len do begin
if not WriteFile(Sock, Data^[BytesSend], Len - BytesSend, BytesWritten, @Overlap) then begin
if GetLastError <> ERROR_IO_PENDING then
{ non-recoverable WriteFile error }
RaiseLastWin32Error;
{ wait for 10 seconds for our write to complete }
case WaitForSingleObject(Overlap.hEvent, 10000) of
WAIT_OBJECT_0:
if not GetOverlappedResult(Sock, OverLap, BytesWritten, False) then
{ GetOverlappedResult failed }
RaiseLastWin32Error;
WAIT_TIMEOUT:
raise Exception.Create('Timed out waiting for our write to complete');
else
RaiseLastWin32Error;
end;
end;
if BytesWritten = 0 then
{ peer must have terminated connection }
raise Exception.Create('Connection is closed before sent has completed');
Inc(BytesSend, BytesWritten);
end;
finally
CloseHandle(Overlap.hEvent);
end;
end;
반응형