Hi

I've been having problems retrieving a webpage using HTTP GET in winsock. I used a packet sniffer to construct the header and the GET Request appears fine although I receive a "400 Bad Request Error". Thanks if you can help.

Ricky

My code:

int HTTP_GET()
{
		 WSADATA wsa;
		 struct hostent *remoteHost;

		 SOCKET sock;
		 struct sockaddr_in addr;
		 unsigned long win=0;
		 char Get_Request[523];//998576
		 char Response[8576]; //2018
		 int iResult;
		 DWORD dwError;
		 
		 //Initialise winsock

		 iResult = WSAStartup(MAKEWORD(2,2), &wsa);
		 if(iResult != 0)
		 {
			printf("WSAStartup failed with error: %d\n", iResult);
			WSACleanup();
			return 1;
		 }

		 char* HostURL = "www.alfred-hitchcock.com";

		 remoteHost = gethostbyname(HostURL);
		 if(remoteHost == NULL)
		 {
			 dwError = WSAGetLastError();
			 if (dwError != 0)
			 {
				 if(dwError == WSAHOST_NOT_FOUND) 
				 {
				     printf ("Host %s not found.\n", HostURL);
					 WSACleanup();
					 Sleep(10000);
					 return 2;
				 }
				 else if (dwError == WSANO_DATA) 
				 {
					 printf ("No data record found.\n");
					 Sleep(10000);
					 return 2;
				 }
				 else
				 {
					 printf("Function failed with error: %ld\n", dwError);
					 Sleep(10000);
					 return 2;
				 }
			 }
		 }
		 else
		 {
			 printf ("Successfully connected to host: %s.\n", HostURL);
			 Sleep(5000);
		 }

		 win = *(unsigned long*) remoteHost->h_addr;

		    // The sockaddr_in structure specifies the address family,
            // IP address, and port of the server to be connected to.

		 addr.sin_family=AF_INET;
		 addr.sin_port=htons(80);
		 addr.sin_addr.s_addr = win;

		 // Create a SOCKET for connecting to server
		 sock = socket(PF_INET, SOCK_STREAM,IPPROTO_TCP);
		 if( sock == INVALID_SOCKET)
		 {
			   printf("Server: Error at socket(), error code: %ld\n", WSAGetLastError());

          // Clean up
		  WSACleanup();
		  // and exit with error
		  return 2;
		 }

		 char * Dir = "/trivia.html";

		 //HTTP POST Get_Request, constructed using a packet sniffer
		 sprintf(Get_Request, "GET %s HTTP/1.1\r\n", Dir);
		 sprintf(Get_Request, "%sHost: %s\r\n", Get_Request, HostURL);
		 sprintf(Get_Request, "%sUser-Agent: Mozilla/5.0 (Windows; U; Windows NT 6.1; en-GB; rv:1.9.2.3) Gecko/20100401 Firefox/3.6.3\r\n",Get_Request);
		 sprintf(Get_Request, "%sAccept: text/html,application/xhtml+xml,application/xml;q=0.9,*//*;q=0.8\r\n",Get_Request);
		 sprintf(Get_Request, "%sAccept-Language: en-gb,en;q=0.5\r\n",Get_Request);
		 sprintf(Get_Request, "%sAccept-Encoding: gzip,deflate\r\n",Get_Request);
		 sprintf(Get_Request, "%sAccept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7\r\n",Get_Request);
		 sprintf(Get_Request, "%sKeep-Alive: 115\r\n",Get_Request);
		 sprintf(Get_Request, "%sConnection: keep-alive\r\n", Get_Request);
		 
		 cout << Get_Request ;
		 //Sleep(50000);
		 // Connect to server.
		 iResult = connect(sock, (SOCKADDR*)&addr, sizeof(addr));
		 if(iResult == SOCKET_ERROR)
		 {
			 printf("connect failed with error: %d\n", WSAGetLastError());
			 closesocket(sock);
			 WSACleanup();
			 return 2;
		 }

		 // Send buffer
	 	iResult = send(sock, Get_Request, strlen(Get_Request), 0);

		 if(iResult == SOCKET_ERROR) 
		 {
			 printf("send() failed with error: %d\n", WSAGetLastError());
			 closesocket(sock);
			 WSACleanup();
			 return 2;
		 }
		 else
		 {
			  printf("Bytes sent: %d\n", iResult);
		 }

		while (iResult > 0 )
		 {
			 iResult = recv(sock, Response, strlen(Response), 0);

			 if ( iResult > 0 )
			 {
				 printf("Bytes received: %d\n", iResult);
				printf("%s", Response);
				 Sleep(5000);
			 }
			 else if (iResult == 0)
			 {
				 printf("Connection closed\n");
				
				 	 Sleep(5000);
			 }
			 else
			 {
				 printf("recv failed with error: %d\n", WSAGetLastError());
				 	 Sleep(5000);
			 }
			//

		 }      

		 // cleanup

		 closesocket(sock);
		 WSACleanup();
		 //cout << win << endl;
		 cin.get();
		 return EXIT_SUCCESS;
	 }

HTTP headers must end with a CR/LF line, so you should add sprintf(Get_Request, "%s\r\n", Get_Request); at the end to get it working.

Also, when recv() -ing, you shouldn't use strlen(Response) as the length argument, since your buffer isn't initialized, so strlen will pretty much return random numbers. Instead, use sizeof(Response) - 1 and then add the terminating null character with Response[iResult] = '\0'; .

And a second thing, gethostbyname has been deprecated for a long time, you should consider using getaddrinfo .

HTTP headers must end with a CR/LF line, so you should add sprintf(Get_Request, "%s\r\n", Get_Request); at the end to get it working.

Also, when recv() -ing, you shouldn't use strlen(Response) as the length argument, since your buffer isn't initialized, so strlen will pretty much return random numbers. Instead, use sizeof(Response) - 1 and then add the terminating null character with Response[iResult] = '\0'; .

And a second thing, gethostbyname has been deprecated for a long time, you should consider using getaddrinfo .

Thank you so very much, can't believe I forgot the new line at the end! Thanks for the other advice too.

This article has been dead for over six months. Start a new discussion instead.