' =============================================================================== ' NAME: Sockets Demonstration Program ' FILE NAME: Sockets.bas ' AUTHOR: Stephane Richard (MystikShadows) ' ------------------------------------------------------------------------------- ' DESCRIPTION: This little program uses the wsock32 library to connect to a ' website (in this example http://www.ascii-world.com) and ' retrieves some information about the website as wellas the ' contents of the index.html file and displays them on the screen. ' =============================================================================== OPTION EXPLICIT ' -------------------- ' Library Inclusions ' -------------------- '#Include "winsock.bi" <- Commented out for tutorial purposes, ' should be used instead in projects #INCLIB "wsock32" ' ------------------------------------------------------------------ ' Constants and defines extracted from winsock.bi for this example ' ------------------------------------------------------------------ CONST AF_Inet = 2 CONST Sock_Stream = 1 CONST IPProto_TCP = 6 CONST NewLine = CHR$(13)+CHR$(10) #DEFINE MAKEWORD(a,b) ((a) shl 8 or ((b) and &h000000FF)) #DEFINE WSADESCRIPTION_LEN 256 #DEFINE WSASYS_STATUS_LEN 128 ' --------------------------------------------------------------- ' User Defined Types extracted from winsock.bi for this example ' --------------------------------------------------------------- TYPE WSAData wVersion AS SHORT wHighVersion AS SHORT szDescription AS STRING * WSADESCRIPTION_LEN+1-1 szSystemStatus AS STRING * WSASYS_STATUS_LEN+1-1 wMaxSockets AS USHORT wMaxUDPDG AS USHORT dwVendorInfo AS BYTE PTR END TYPE TYPE HostEnt H_Name AS BYTE PTR H_Aliases AS BYTE PTR PTR H_AddrType AS SHORT H_Length AS SHORT H_Addr_List AS UINTEGER PTR PTR END TYPE TYPE S_Un_B_ S_B1 AS UBYTE S_B2 AS UBYTE S_B3 AS UBYTE S_B4 AS UBYTE END TYPE TYPE S_Un_W_ S_W1 AS USHORT S_W2 AS USHORT END TYPE UNION In_Addr S_Un_B AS S_Un_B_ S_Un_W AS S_Un_W_ S_Addr AS UINTEGER END UNION Type SockAddr_In Sin_Family AS SHORT Sin_Port AS USHORT Sin_Addr As In_Addr Sin_Zero(0 TO 7) AS BYTE End Type Type SockAddr SA_Family AS SHORT SA_Zero(0 TO 13) AS BYTE END TYPE ' ---------------------------------------------------------------------- ' API Function Declarations extracted from winsock.bi for this example ' ---------------------------------------------------------------------- DECLARE FUNCTION WSAStartup _ LIB "WSock32" _ ALIAS "WSAStartup" (BYVAL wVersionRequired AS SHORT, _ BYVAL lpWSAData AS WSAData PTR) AS LONG DECLARE FUNCTION WSAGetLastError _ LIB "WSock32" _ ALIAS "WSAGetLastError" () AS LONG DECLARE FUNCTION WSACleanup _ LIB "WSock32" _ ALIAS "WSACleanup" () AS LONG DECLARE FUNCTION Socket _ LIB "WSock32" _ ALIAS "socket" (BYVAL AF AS LONG, _ BYVAL S_Type AS LONG, _ BYVAL Protocol AS LONG) AS LONG DECLARE FUNCTION CloseSocket _ LIB "WSock32" _ ALIAS "closesocket" (BYVAL S AS LONG) AS LONG DECLARE FUNCTION Connect _ LIB "WSock32" _ ALIAS "connect" (BYVAL AS LONG, _ BYVAL AS SockAddr PTR, _ BYVAL AS LONG) AS LONG DECLARE FUNCTION HTons _ LIB "WSock32" _ ALIAS "htons" (BYVAL HostShort AS USHORT) AS USHORT DECLARE FUNCTION GetHostByName _ LIB "WSock32" _ ALIAS "gethostbyname" (BYVAL szHost AS STRING) AS HostEnt PTR DECLARE FUNCTION Send _ LIB "WSock32" _ ALIAS "send" (BYVAL SocketID AS LONG, _ BYVAL BufferPtr AS LONG, _ BYVAL BufLen AS LONG, _ BYVAL Flags AS LONG) AS LONG DECLARE FUNCTION Recv _ LIB "WSock32" _ ALIAS "recv" (BYVAL SocketID AS LONG, _ BYVAL BufferPtr AS LONG, _ BYVAL BufLen AS LONG, _ BYVAL Flags AS LONG) AS LONG '==================================================== ' StartSockets gets a WSAData structure ready to be ' used in the rest of the program. '==================================================== FUNCTION StartSockets() AS LONG DIM WSAInfo AS WSAData WSAStartup(MakeWord(1,1), @WSAInfo) END FUNCTION ' ==================================================== ' EndSockets clears resources used by StartSockets ' ==================================================== FUNCTION EndSockets() AS LONG WSACleanup() END FUNCTION ' ==================================================== ' NAME: ConnectToURL() ' PARAMETERS: BYVAL URL AS STRING ' RETURN VALUE: A LONG typed value ' ASSUMES: URL to be a valid website URL ' ---------------------------------------------------- ' DESCRIPTION: This function performs the actual ' work of this demonstration. it will ' connect to the URL passed as its ' parameter and retrieve and display ' some information about the URL. ' ==================================================== FUNCTION ConnectTOURL(BYVAL URL AS STRING) AS LONG ' ---------------- ' Work Variables ' ---------------- DIM URLHost AS HostEnt PTR DIM URLSocket AS SockAddr_In DIM URLSocketID AS UINTEGER DIM Connection AS LONG DIM Message AS STRING DIM Buffer AS STRING DIM BufferReceive AS ZSTRING *1001 DIM BytesReceived AS LONG ' --------------------- ' Retreive URL's host ' --------------------- URLHost = GetHostByName(URL) ' --------------------- ' Create URL's Socket ' --------------------- WITH URLSocket .Sin_Family = AF_Inet .Sin_Port = HTons(80) .Sin_Addr.S_Addr = **URLHost->H_Addr_List END WITH ' ------------------- ' Create The Socket ' ------------------- URLSocketID = Socket(AF_Inet, Sock_Stream, IPProto_TCP) ' -------------------- ' Connect To The URL ' -------------------- Connection = Connect(URLSocketID, @URLSocket, LEN(URLSocket)) ConnectURL = URLSocketID ' ------------------------------------------------------------- ' Prepare HTTP GET request and send it to throught the socket ' ------------------------------------------------------------- Message = "GET / HTTP/1.0" + NewLine _ + "Host: " + URL + NewLine _ + "User-Agent: MystikShadows" + NewLine + NewLine Send(URLSocketID, STRPTR(Message), LEN(Message), 0) ' --------------- ' Retrieve File ' --------------- BytesReceived = Recv(URLSocketID, STRPTR(BufferReceive), 1000, 0) WHILE BytesReceived > 0 Buffer = Buffer + LEFT$(BufferReceive, BytesReceived) BytesReceived = Recv(URLSocketID, STRPTR(BufferReceive), 1000, 0) WEND ' -------------------------------------------- ' Display received file and info to the user ' -------------------------------------------- PRINT Buffer END FUNCTION '========================== ' MAIN PART OF THE PROGRAM '========================== DIM Connection AS LONG StartSockets() Connection = ConnectToURL("www.ascii-world.com") EndSockets() SLEEP