シンプルなプロキシサーバーを実装しようとしていますが、これまでのところGETメソッドを正しく処理できましたが、今はキャッシングを実装する必要があります。その背後にある考え方は、私は次のコマンドを取得するときにということで:キャッシングシステムを使用したプロキシの実装
- GET www.google.com
- GET www.cplusplus.com
- GET www.google.com
2回目は私のキャッシュシステムからGoogleの情報を取得するよう求められます。私は考えてきました。これを行う最善の方法は、受信した情報をファイルに保存し、ファイルが存在する場合はいつでもそれを読み取るシンプルなファイリングシステムを実装することです。私が抱いている唯一の問題は、ファイルを作成できないということです。http://elf.cs.edu.ro/
ここに私のコードがありますので、私が何をしているのか分かります。
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <netinet/in.h>
#include <netdb.h>
#include <errno.h>
void error(char* msg) {
perror(msg);
exit(0);
}
int main(int argc,char* argv[]) {
int count = 0;
FILE *in;
FILE *out;
pid_t pid;
struct sockaddr_in addr_in,cli_addr,serv_addr;
struct hostent* host;
int sockfd,newsockfd;
if(argc<2)
error("./proxy <port_no>");
printf("\n*****WELCOME TO PROXY SERVER*****\n");
bzero((char*)&serv_addr,sizeof(serv_addr));
bzero((char*)&cli_addr, sizeof(cli_addr));
serv_addr.sin_family=AF_INET;
serv_addr.sin_port=htons(atoi(argv[1]));
serv_addr.sin_addr.s_addr=INADDR_ANY;
sockfd=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);
if(sockfd<0)
error("Problem in initializing socket");
if(bind(sockfd,(struct sockaddr*)&serv_addr,sizeof(serv_addr))<0)
error("Error on binding");
listen(sockfd,50);
int clilen=sizeof(cli_addr);
startpoint:
newsockfd=accept(sockfd,(struct sockaddr*)&cli_addr,&clilen);
if(newsockfd<0)
error("Problem in accepting connection");
pid=fork();
//printf("Pid is: %d\n", pid);
if(pid==0) {
sites saves[10];
int noOfSites = 0;
struct sockaddr_in host_addr;
int flag=0,newsockfd1,n,port=0,i,sockfd1;
char buffer[510],t1[300],t2[300],t3[10], aux[510];
char* temp=NULL;
bzero((char*)buffer,500);
recv(newsockfd,buffer,sizeof(buffer),0);
//printf("%s\n",buffer);
sscanf(buffer,"%s %s %s",t1,t2,t3);
//printf("%s\n",buffer);
if (((strncmp(t1,"GET",3)==0))&&((strncmp(t3,"HTTP/1.0",8)==0)||(strncmp(t3,"HTTP/1.0",8)==0))&&(strncmp(t2,"http://",7)==0)) {
strcpy(t1,t2);
int saved = 0;
flag=0;
for(i=7;i<strlen(t2);i++) {
if(t2[i]==':') {
flag=1;
break;
}
}
// printf("The site to GET is : %s\n",t2);
temp=strtok(t2,"//");
if (flag==0) {
port=80;
temp=strtok(NULL,"/");
}
else {
temp=strtok(NULL,":");
}
sprintf(t2,"%s",temp);
host=gethostbyname(t2);
int it;
for (it = 0; it < noOfSites; it++){
printf("Site saved is: %s\n", saves[it].site);
if (strcmp(saves[it].site,t2) == 0){
saved = 1;
out = fopen(t2, "r");
printf("We have cache!\n");
}
}
if(flag==1) {
temp=strtok(NULL,"/");
port=atoi(temp);
}
strcat(t1,"^]");
temp=strtok(t1,"//");
temp=strtok(NULL,"/");
if(temp!=NULL)
temp=strtok(NULL,"^]");
bzero((char*)&host_addr,sizeof(host_addr));
host_addr.sin_port=htons(port);
host_addr.sin_family=AF_INET;
bcopy((char*)host->h_addr,(char*)&host_addr.sin_addr.s_addr,host->h_length);
sockfd1=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);
newsockfd1=connect(sockfd1,(struct sockaddr*)&host_addr,sizeof(struct sockaddr));
sprintf(buffer,"\nConnected to %s IP - %s\n",t2,inet_ntoa(host_addr.sin_addr));
if(newsockfd1<0)
error("Error in connecting to remote server");
bzero((char*)buffer,sizeof(buffer));
if(temp!=NULL)
sprintf(buffer,"GET /%s %s\r\nHost: %s\r\nConnection: close\r\n\r\n",temp,t3,t2);
else
sprintf(buffer,"GET/%s\r\nHost: %s\r\nConnection: close\r\n\r\n",t3,t2);
if (saved == 1){
printf("Are we ever here\n");
n = send(sockfd1,buffer,strlen(buffer),0);
char * line = NULL;
size_t len = 0;
ssize_t read;
int count = 0;
if (n<0)
error("Error writing to socket");
else {
while ((read = getline(&line, &len, out)) != -1) {
//printf("Retrieved line of length %zu :\n", read);
if (count > 0)
write(newsockfd,line,read);
if (strcmp(line,"\r\n") == 0)
count++;
}
}
}
if (saved == 0){
//printf("We are only here\n");
strcpy(saves[noOfSites].site,t2);
noOfSites++;
printf("The new site file is: %d\n", noOfSites);
in = fopen(t2,"w");
n=send(sockfd1,buffer,strlen(buffer),0);
printf("I have opened for writing: %s\n\n\n\n\n\n",t2);
if(n<0)
error("Error writing to socket");
else {
do {
memset(buffer, 0, sizeof(buffer));
n=recv(sockfd1,buffer,sizeof(buffer),0);
fwrite(buffer, n, 1, stdout);
printf("\n");
fwrite(buffer, n, 1, in);
if(!(n<=0))
write(newsockfd,buffer,n);
} while(n>0);
}
}
}
else {
send(newsockfd,"400 : BAD REQUEST\nONLY HTTP REQUESTS ALLOWED",18,0);
}
close(sockfd1);
close(newsockfd);
close(sockfd);
fclose(in);
return 0;
}
else {
close(newsockfd);
goto startpoint;
}
return 0;
}
誰でも正しい方向に向けることができますか?私は誰かが私のためにそれをするのを望んでいない、ちょうどあなたがそれをやる方法についてのちょっとしたアイデアなので、チャンスがあるかもしれない。あなたの時間をありがとう!
デバッグヘルプ( "**なぜこのコードは機能していないのですか?**")は、質問自体に再現するために、必要な動作、特定の問題またはエラー、および**最短のコードが必要です。明確な問題文がない質問は、他の読者にとって有用ではありません。参照:[最小限で完全で検証可能な例の作成方法](/ help/mcve) –