📄 winsockbas.bas
字号:
Public Function WSAGetAsyncBufLen(ByVal lParam As Long) As Long
If (lParam And &HFFFF&) > &H7FFF Then
WSAGetAsyncBufLen = (lParam And &HFFFF&) - &H10000
Else
WSAGetAsyncBufLen = lParam And &HFFFF&
End If
End Function
Public Function WSAGetSelectEvent(ByVal lParam As Long) As Integer
If (lParam And &HFFFF&) > &H7FFF Then
WSAGetSelectEvent = (lParam And &HFFFF&) - &H10000
Else
WSAGetSelectEvent = lParam And &HFFFF&
End If
End Function
Public Function WSAGetAsyncError(ByVal lParam As Long) As Integer
WSAGetAsyncError = (lParam And &HFFFF0000) \ &H10000
End Function
'this function DOES work on 16 and 32 bit systems
Function AddrToIP(ByVal AddrOrIP$) As String
On Error Resume Next
AddrToIP$ = getascip(GetHostByNameAlias(AddrOrIP$))
If Err Then AddrToIP$ = "255.255.255.255"
End Function
'this function should work on 16 and 32 bit systems
#If Win16 Then
Function ConnectSock(ByVal Host$, ByVal Port%, retIpPort$, ByVal HWndToMsg%, ByVal Async%) As Integer
Dim s%, SelectOps%, dummy%
#ElseIf Win32 Then
Function ConnectSock(ByVal Host$, ByVal Port&, retIpPort$, ByVal HWndToMsg&, ByVal Async%) As Long
Dim s&, SelectOps&, dummy&
#End If
Dim sockin As sockaddr
SockReadBuffer$ = ""
sockin = saZero
sockin.sin_family = AF_INET
sockin.sin_port = htons(Port)
If sockin.sin_port = INVALID_SOCKET Then
ConnectSock = INVALID_SOCKET
Exit Function
End If
sockin.sin_addr = GetHostByNameAlias(Host$)
If sockin.sin_addr = INADDR_NONE Then
ConnectSock = INVALID_SOCKET
Exit Function
End If
retIpPort$ = getascip$(sockin.sin_addr) & ":" & ntohs(sockin.sin_port)
s = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP)
If s < 0 Then
ConnectSock = INVALID_SOCKET
Exit Function
End If
If SetSockLinger(s, 1, 0) = SOCKET_ERROR Then
If s > 0 Then
dummy = closesocket(s)
End If
ConnectSock = INVALID_SOCKET
Exit Function
End If
If Not Async Then
If connect(s, sockin, sockaddr_size) <> 0 Then
If s > 0 Then
dummy = closesocket(s)
End If
ConnectSock = INVALID_SOCKET
Exit Function
End If
SelectOps = FD_READ Or FD_WRITE Or FD_CONNECT Or FD_CLOSE
If WSAAsyncSelect(s, HWndToMsg, ByVal 1025, ByVal SelectOps) Then
If s > 0 Then
dummy = closesocket(s)
End If
ConnectSock = INVALID_SOCKET
Exit Function
End If
Else
SelectOps = FD_READ Or FD_WRITE Or FD_CONNECT Or FD_CLOSE
If WSAAsyncSelect(s, HWndToMsg, ByVal 1025, ByVal SelectOps) Then
If s > 0 Then
dummy = closesocket(s)
End If
ConnectSock = INVALID_SOCKET
Exit Function
End If
If connect(s, sockin, sockaddr_size) <> -1 Then
If s > 0 Then
dummy = closesocket(s)
End If
ConnectSock = INVALID_SOCKET
Exit Function
End If
End If
ConnectSock = s
End Function
#If Win32 Then
Public Function SetSockLinger(ByVal SockNum&, ByVal OnOff%, ByVal LingerTime%) As Long
#Else
Public Function SetSockLinger(ByVal SockNum%, ByVal OnOff%, ByVal LingerTime%) As Integer
#End If
Dim Linger As LingerType
Linger.l_onoff = OnOff
Linger.l_linger = LingerTime
If setsockopt(SockNum, SOL_SOCKET, SO_LINGER, Linger, 4) Then
Debug.Print "Error setting linger info: " & WSAGetLastError()
SetSockLinger = SOCKET_ERROR
Else
If getsockopt(SockNum, SOL_SOCKET, SO_LINGER, Linger, 4) Then
Debug.Print "Error getting linger info: " & WSAGetLastError()
SetSockLinger = SOCKET_ERROR
Else
Debug.Print "Linger is on if nonzero: "; Linger.l_onoff
Debug.Print "Linger time if linger is on: "; Linger.l_linger
End If
End If
End Function
'this function DOES work on 16 and 32 bit systems
Sub EndWinsock()
Dim ret&
If WSAIsBlocking() Then
ret = WSACancelBlockingCall()
End If
ret = WSACleanup()
WSAStartedUp = False
End Sub
'this function DOES work on 16 and 32 bit systems
Function getascip(ByVal inn As Long) As String
On Error Resume Next
Dim lpStr&
#If Win16 Then
Dim nStr%
#ElseIf Win32 Then
Dim nStr&
#End If
Dim retString$
retString = String(32, 0)
lpStr = inet_ntoa(inn)
If lpStr = 0 Then
getascip = "255.255.255.255"
Exit Function
End If
nStr = lstrlen(lpStr)
If nStr > 32 Then nStr = 32
MemCopy ByVal retString, ByVal lpStr, nStr
retString = Left(retString, nStr)
getascip = retString
If Err Then getascip = "255.255.255.255"
End Function
'this function DOES work on 32bit and 16 bit systems
Function GetHostByAddress(ByVal addr As Long) As String
On Error Resume Next
Dim phe&, ret&
Dim heDestHost As HostEnt
Dim hostname$
phe = gethostbyaddr(addr, 4, PF_INET)
Debug.Print phe
If phe <> 0 Then
MemCopy heDestHost, ByVal phe, hostent_size
Debug.Print heDestHost.h_name
Debug.Print heDestHost.h_aliases
Debug.Print heDestHost.h_addrtype
Debug.Print heDestHost.h_length
Debug.Print heDestHost.h_addr_list
hostname = String(256, 0)
MemCopy ByVal hostname, ByVal heDestHost.h_name, 256
GetHostByAddress = Left(hostname, InStr(hostname, Chr(0)) - 1)
Else
GetHostByAddress = WSA_NoName
End If
If Err Then GetHostByAddress = WSA_NoName
End Function
'this function DOES work on 16 and 32 bit systems
Function GetHostByNameAlias(ByVal hostname$) As Long
On Error Resume Next
'Return IP address as a long, in network byte order
Dim phe& ' pointer to host information entry
Dim heDestHost As HostEnt 'hostent structure
Dim addrList&
Dim retIP&
'first check to see if what we have been passed is a valid IP
retIP = inet_addr(hostname)
If retIP = INADDR_NONE Then
'it wasn't an IP, so do a DNS lookup
phe = gethostbyname(hostname)
If phe <> 0 Then
'Pointer is non-null, so copy in hostent structure
MemCopy heDestHost, ByVal phe, hostent_size
'Now get first pointer in address list
MemCopy addrList, ByVal heDestHost.h_addr_list, 4
MemCopy retIP, ByVal addrList, heDestHost.h_length
Else
'its not a valid address
retIP = INADDR_NONE
End If
End If
GetHostByNameAlias = retIP
If Err Then GetHostByNameAlias = INADDR_NONE
End Function
'this function DOES work on 16 and 32 bit systems
Function GetLocalHostName() As String
Dim dummy&
Dim LocalName$
Dim s$
On Error Resume Next
LocalName = String(256, 0)
LocalName = WSA_NoName
dummy = 1
s = String(256, 0)
dummy = gethostname(s, 256)
If dummy = 0 Then
s = Left(s, InStr(s, Chr(0)) - 1)
If Len(s) > 0 Then
LocalName = s
End If
End If
GetLocalHostName = LocalName
If Err Then GetLocalHostName = WSA_NoName
End Function
'this function DOES work on 16 and 32 bit systems
#If Win16 Then
Function GetPeerAddress(ByVal s%) As String
Dim addrlen%
Dim ret%
#ElseIf Win32 Then
Function GetPeerAddress(ByVal s&) As String
Dim addrlen&
Dim ret&
#End If
On Error Resume Next
Dim sa As sockaddr
addrlen = sockaddr_size
ret = getpeername(s, sa, addrlen)
If ret = 0 Then
GetPeerAddress = SockAddressToString(sa)
Else
GetPeerAddress = ""
End If
If Err Then GetPeerAddress = ""
End Function
'this function should work on 16 and 32 bit systems
#If Win16 Then
Function GetPortFromString(ByVal PortStr$) As Integer
#ElseIf Win32 Then
Function GetPortFromString(ByVal PortStr$) As Long
#End If
'sometimes users provide ports outside the range of a VB
'integer, so this function returns an integer for a string
'just to keep an error from happening, it converts the
'number to a negative if needed
On Error Resume Next
If Val(PortStr$) > 32767 Then
GetPortFromString = CInt(Val(PortStr$) - &H10000)
Else
GetPortFromString = Val(PortStr$)
End If
If Err Then GetPortFromString = 0
End Function
'this function should work on 16 and 32 bit systems
#If Win16 Then
Function GetProtocolByName(ByVal protocol$) As Integer
Dim tmpShort%
#ElseIf Win32 Then
Function GetProtocolByName(ByVal protocol$) As Long
Dim tmpShort&
#End If
On Error Resume Next
Dim ppe&
Dim peDestProt As protoent
ppe = getprotobyname(protocol)
If ppe = 0 Then
tmpShort = Val(protocol)
If tmpShort <> 0 Or protocol = "0" Or protocol = "" Then
GetProtocolByName = htons(tmpShort)
Else
GetProtocolByName = SOCKET_ERROR
End If
Else
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -