Hello all, I have an question about my program implementation. (c++ ,TCP, unix/b
ID: 3833850 • Letter: H
Question
Hello all, I have an question about my program implementation. (c++ ,TCP, unix/bash)
I have written what i thought would work but I have no such luck. Thanks for the help!
Question Prompt:
TCP Programming with Sockets - Rudimentary HTTP Server Purpose To practice socket programming with TCP/IP, including the system calls that were learned previously, as well as bind, listen, and accept. Assignment Write a C++ program that implements a basic HTTP server
. If this is done properly, you should be able to connect to it through a web browser, but this will not be one of the criteria for grading. The program will essentially be a loop that goes on forever (until it is killed), waiting for a client to connect. When a client connects, it accepts that connection, calls fork to make a child process, and handles communication from that client in the child process. The parent process should continue to wait for more connections, accepting them and forking as necessary.
The program will accept two command line parameters: 1. the port number on which the server will be listening 2. the path to a directory that will serve as the root directory of the web server For example: % ./TCP 9001 www The requests received by the program will be of the form: GET path where the path is the path, relative to the directory specified as the second command line parameter, of the file that is being requested.
There are several rules on what can constitute a valid path, and they are as follows:
• it must begin with a “/”
• it may contain additional “/” path separators to access subdirectories
• a single “/” character refers to the directory specified in command line
• a trailing “/” in the pathname can be ignored if the path refers to a directory
• any data in the request beyond the path should be ignored
• it may not contain the substring “..”
If the path refers to a directory, then:
• if the file called “index.html” exists in that directory, send the contents of that file to the client
• if not, send a list of the files in the specified directory to the client (do not include files that start with “.”) If the path refers to a file, then the content of the file should be sent to the client.
Error Checking If the command line arguments are incomplete, or if the path to the web server’s root is invalid, print an error message to stderr and exit with an error code. If any of the system calls fail, the program should use perror to report what happened and exit with an error code. If the path in the GET request is invalid, or if a file or directory cannot be accessed, then an appropriate error message should be sent to the client to notify them. 1
Other Notes • This is a simple TCP server. If you need a tool to test it, you can use the telnet command to connect to your server at the specified port. Type your command and hit enter, and the client should display what the server returns.
SAMPLE OUTPUT:
% telnet localhost 9001 Connected to localhost. Escape character is '^]'. GET / fileOne.html fileTwo.html Connection closed by foreign host. % telnet localhost 9001 Connected to localhost. Escape character is '^]'. GET fileOne Error: fileOne not found Connection closed by foreign host. % telnet localhost 9001 Connected to localhost. Escape character is '^]'. GET fileOne.html ... contents of file ... Connection closed by foreign host.
• Make sure that the assignment is contained in a single file called “TCP.cxx” • Make sure that your program compiles, links, and runs properly
What I currently have:
#include <iostream>
using namespace std;
#include <string.h>
#define LISTEN_PORT 80
#define BACKLOG 5
#define PROTOCOL "HTTP/1.1"
void main(){
WSAData wsadata;
if(WSAStartup(MAKEWORD(2,2), &wsadata) != NO_ERROR){
cout<<"Error at WSAStartup ";
return;
}
SOCKET listenSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if(listenSocket == INVALID_SOCKET){
cout<<"Error opening socket: "<<WSAGetLastError()<<endl;
WSACleanup();
return;
}
sockaddr_in serverService;
serverService.sin_family = AF_INET;
serverService.sin_addr.s_addr = INADDR_ANY;
serverService.sin_port = htons(LISTEN_PORT);
if(bind(listenSocket, (SOCKADDR*)&serverService, sizeof(serverService)) == SOCKET_ERROR){
cout<<"Error at bind: "<<WSAGetLastError()<<endl;
closesocket(listenSocket);
WSACleanup();
return;
}
if(listen(listenSocket, BACKLOG) == SOCKET_ERROR){
cout<<"Error at listen: "<<WSAGetLastError()<<endl;
closesocket(listenSocket);
WSACleanup();
return;
}
cout<<"Server connected ";
while(true){
struct sockaddr_in from;
int fromLen = sizeof(from);
SOCKET msgSocket = accept(listenSocket, (struct sockaddr*)&from, &fromLen);
if(msgSocket == INVALID_SOCKET){
cout<<"Error at accept: "<<WSAGetLastError()<<endl;
closesocket(listenSocket);
WSACleanup();
return;
}
cout<<"Clinet: address "<<inet_ntoa(from.sin_addr)<<" port: "<<ntohs(from.sin_port)<<endl;
char HTML[] = "<HTML><TITLE></TITLE><BODY><H1>Hi!</H1></BODY></HTML>";
char sendBuff[1000];
char recvBuff[1000];
int bytesSent = 0;
int bytesRecv = 0;
//recieve from client
bytesRecv = recv(msgSocket, recvBuff, (int)strlen(recvBuff), 0);
if(bytesRecv == SOCKET_ERROR){
cout<<"Server, error at recv() "<<WSAGetLastError()<<endl;
closesocket(listenSocket);
WSACleanup();
return;
}
recvBuff[strlen(recvBuff)] = '';
//send response to client
cout<<"Server recieved message: "<<recvBuff<<" from Client address: "<<inet_ntoa(from.sin_addr)<<" port: "<<ntohs(from.sin_port)<<" bytes recv: "<<bytesRecv<<endl;
sprintf(sendBuff, "%s %d %s", PROTOCOL, 200, "OK");
send(msgSocket, sendBuff, (int)strlen(sendBuff), 0);
cout<<"Server sent message: "<<sendBuff<<endl;
//send content
send(msgSocket, HTML, (int)strlen(HTML), 0);
cout<<"Server sent message: "<<HTML<<endl;
closesocket(msgSocket);
}
closesocket(listenSocket);
WSACleanup();
return;
}
Please correct my mistakes/logic. Thanks!
Explanation / Answer
#include <iostream>
using namespace std;
#include <string.h>
#define LISTEN_PORT 80
#define BACKLOG 5
#define PROTOCOL "HTTP/1.1"
void main(){
WSAData wsadata;
if(WSAStartup(MAKEWORD(2,2), &wsadata) != NO_ERROR){
cout<<"Error at WSAStartup ";
return;
}
SOCKET listenSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if(listenSocket == INVALID_SOCKET){
cout<<"Error opening socket: "<<WSAGetLastError()<<endl;
WSACleanup();
return;
}
sockaddr_in serverService;
serverService.sin_family = AF_INET;
serverService.sin_addr.s_addr = INADDR_ANY;
serverService.sin_port = htons(LISTEN_PORT);
if(bind(listenSocket, (SOCKADDR*)&serverService, sizeof(serverService)) == SOCKET_ERROR){
cout<<"Error at bind: "<<WSAGetLastError()<<endl;
closesocket(listenSocket);
WSACleanup();
return;
}
if(listen(listenSocket, BACKLOG) == SOCKET_ERROR){
cout<<"Error at listen: "<<WSAGetLastError()<<endl;
closesocket(listenSocket);
WSACleanup();
return;
}
cout<<"Server connected ";
while(true){
struct sockaddr_in from;
int fromLen = sizeof(from);
SOCKET msgSocket = accept(listenSocket, (struct sockaddr*)&from, &fromLen);
if(msgSocket == INVALID_SOCKET){
cout<<"Error at accept: "<<WSAGetLastError()<<endl;
closesocket(listenSocket);
WSACleanup();
return;
}
cout<<"Clinet: address "<<inet_ntoa(from.sin_addr)<<" port: "<<ntohs(from.sin_port)<<endl;
char HTML[] = "<HTML><TITLE></TITLE><BODY><H1>Hi!</H1></BODY></HTML>";
char sendBuff[1000];
char recvBuff[1000];
int bytesSent = 0;
int bytesRecv = 0;
//recieve from client
bytesRecv = recv(msgSocket, recvBuff, (int)strlen(recvBuff), 0);
if(bytesRecv == SOCKET_ERROR){
cout<<"Server, error at recv() "<<WSAGetLastError()<<endl;
closesocket(listenSocket);
WSACleanup();
return;
}
recvBuff[strlen(recvBuff)] = '';
//send response to client
cout<<"Server recieved message: "<<recvBuff<<" from Client address: "<<inet_ntoa(from.sin_addr)<<" port: "<<ntohs(from.sin_port)<<" bytes recv: "<<bytesRecv<<endl;
sprintf(sendBuff, "%s %d %s", PROTOCOL, 200, "OK");
send(msgSocket, sendBuff, (int)strlen(sendBuff), 0);
cout<<"Server sent message: "<<sendBuff<<endl;
//send content
send(msgSocket, HTML, (int)strlen(HTML), 0);
cout<<"Server sent message: "<<HTML<<endl;
closesocket(msgSocket);
}
closesocket(listenSocket);
WSACleanup();
return;
}
Related Questions
drjack9650@gmail.com
Navigate
Integrity-first tutoring: explanations and feedback only — we do not complete graded work. Learn more.