Home
Winsock: how to retrieve the protocol information corresponding to a protocol name
DO decl
IF InitWinsock ()
= DisplayProtInfo ("tcp" )
= DisplayProtInfo ("udp" )
= WSACleanup ()
ENDIF
* End of Main
PROCEDURE DisplayProtInfo (lcProtName)
LOCAL lnProtoentPtr
lnProtoentPtr = getprotobyname (lcProtName)
IF lnProtoentPtr = 0
* no protocol found with this name
? lcProtName
RETURN
ENDIF
*| struct protoent {
*| char FAR * p_name; 0 :4
*| char FAR * FAR * p_aliases; 4 :4
*| short p_proto; 8 :4
*| }; total bytes = 12
#DEFINE PROTOENT_SIZE 12
LOCAL lcBuffer, lcProt, lcAliases, lnProt
lcBuffer = Repli (Chr (0 ), PROTOENT_SIZE)
= Heap2Str (@ lcBuffer, lnProtoentPtr, PROTOENT_SIZE)
lcProt = GetMemStr (buf2dword (SUBSTR (lcBuffer, 1 ,4 )))
lcAliases = GetAliases (buf2dword (SUBSTR (lcBuffer, 5 ,4 )))
lnProt = buf2word (SUBSTR (lcBuffer, 9 ,2 ))
? PADR (lcProt,20 ), STR (lnProt,5 ), lcAliases
RETURN
FUNCTION GetAliases (lnArrayPtr)
* returns a string with alternate names for the protocol
* delimited with semicolons
IF lnArrayPtr = 0
EXIT
ENDIF
LOCAL lcResult, lnDataPtr, lcAlias
lcResult = ""
DO WHILE .T.
* each array element contains a pointer to data
lnDataPtr = buf2dword (GetMemBuf (lnArrayPtr, 4 ))
IF lnDataPtr <> 0
lcAlias = GetMemStr (lnDataPtr)
lcResult = lcResult +;
Iif (Empty (lcResult), "" ,";" ) + lcAlias
ELSE
* the last array element contains null
EXIT
ENDIF
lnArrayPtr = lnArrayPtr + 4 && next array element
ENDDO
RETURN lcResult
FUNCTION InitWinsock ()
* Initializing the Winsock service for the application
#DEFINE WSADATA_SIZE 398
#DEFINE WS_VERSION 0x0202
LOCAL lcWSADATA, lnInitResult
lcWSADATA = Repli (Chr (0 ), WSADATA_SIZE)
lnInitResult = WSAStartup (WS_VERSION, @ lcWSADATA)
RETURN (lnInitResult = 0 )
FUNCTION GetMemBuf (lnAddr, lnBufsize)
LOCAL lcBuffer
lcBuffer = Repli (Chr (0 ), lnBufsize)
= Heap2Str (@ lcBuffer, lnAddr, lnBufsize)
RETURN lcBuffer
FUNCTION GetMemStr (lnAddr)
* returning data from a memory block
* before the first occurence of a zero byte
LOCAL lcBuffer
lcBuffer = GetMemBuf (lnAddr, 250 )
RETURN SUBSTR (lcBuffer, 1 , AT (Chr (0 ),lcBuffer)-1 )
FUNCTION buf2word (lcBuffer)
RETURN Asc (SUBSTR (lcBuffer, 1 ,1 )) + ;
Asc (SUBSTR (lcBuffer, 2 ,1 )) * 256
FUNCTION buf2dword (lcBuffer)
RETURN Asc (SUBSTR (lcBuffer, 1 ,1 )) + ;
Asc (SUBSTR (lcBuffer, 2 ,1 )) * 256 +;
Asc (SUBSTR (lcBuffer, 3 ,1 )) * 65536 +;
Asc (SUBSTR (lcBuffer, 4 ,1 )) * 16777216
PROCEDURE decl
DECLARE INTEGER WSAStartup IN ws2_32 INTEGER wVerRq, STRING @ lpWSAData
DECLARE INTEGER WSACleanup IN ws2_32
DECLARE INTEGER getprotobyname IN ws2_32 STRING name
DECLARE RtlMoveMemory IN kernel32 As Heap2Str;
STRING @ Dest, INTEGER Src, INTEGER nLength
WSACleanup
WSAStartup
getprotobyname