Hello, I'm trying to write a quick/dirty echoserver in Delphi, but I
notice that GetAcceptExSockaddrs seems to be writing to only the first 4
bytes of the structure I pass it.
USES SysUtils;
TYPE
BOOL = LongBool;
DWORD = Cardinal;
LPDWORD = ^DWORD;
short = SmallInt;
ushort = Word;
uint16 = Word;
uint = Cardinal;
ulong = Cardinal;
SOCKET = uint;
PVOID = Pointer;
_HANDLE = DWORD;
_in_addr = packed record
s_addr : ulong;
end;
_sockaddr_in = packed record
sin_family : short;
sin_port : uint16;
sin_addr : _in_addr;
sin_zero : array[0..7] of Char;
end;
P_sockaddr_in = ^_sockaddr_in;
_Overlapped = packed record
Internal : Int64;
Offset : Int64;
hEvent : _HANDLE;
end;
LP_Overlapped = ^_Overlapped;
IMPORTS
function _AcceptEx (sListenSocket, sAcceptSocket : SOCKET; lpOutputBuffer : PVOID; dwReceiveDataLength, dwLocalAddressLength, dwRemoteAddressLength : DWORD; lpdwBytesReceived : LPDWORD; lpOverlapped : LP_OVERLAPPED) : BOOL; stdcall; external MSWinsock name 'AcceptEx';
procedure _GetAcceptExSockaddrs (lpOutputBuffer : PVOID; dwReceiveDataLength, dwLocalAddressLength, dwRemoteAddressLength : DWORD; LocalSockaddr : P_Sockaddr_in; LocalSockaddrLength : LPINT; RemoteSockaddr : P_Sockaddr_in; RemoteSockaddrLength : LPINT); stdcall; external MSWinsock name 'GetAcceptExSockaddrs';
CONST
BufDataSize = 8192;
BufAddrSize = SizeOf (_sockaddr_in) + 16;
VAR
ListenSock, AcceptSock : SOCKET;
Addr, LocalAddr, RemoteAddr : _sockaddr_in;
LocalAddrSize, RemoteAddrSize : INT;
Buf : array[1..BufDataSize + BufAddrSize * 2] of Byte;
BytesReceived : DWORD;
Ov : _Overlapped;
BEGIN
//WSAStartup, create listen socket, bind to port 1066 on any interface, listen
//Create event for overlapped (autoreset, initally not signalled)
//Create accept socket
if _AcceptEx (ListenSock, AcceptSock, @Buf, BufDataSize, BufAddrSize, BufAddrSize, @BytesReceived, @Ov) then
WinCheck ('SetEvent', _SetEvent (Ov.hEvent))
else
if GetLastError <> ERROR_IO_PENDING then
WinCheck ('AcceptEx', GetLastError);
{do WaitForMultipleObjects}
_GetAcceptExSockaddrs (@Buf, BufDataSize, BufAddrSize, BufAddrSize, @LocalAddr, @LocalAddrSize, @RemoteAddr, @RemoteAddrSize);
So if I run this, connect to it with Telnet (on same computer,
connecting to localhost) and then type a key, WaitForMultipleObjects
will unblock and GetAcceptExSockaddrs will run.
But the result is garbage!
RemoteAddr.sin_family = -13894
RemoteAddr.sin_port = 64
and the rest is zeroes.
What gives?
Thanks in advance!