• 大小: 7KB
    文件类型: .c
    金币: 1
    下载: 0 次
    发布日期: 2021-06-01
  • 语言: 其他
  • 标签: ics  的proxy  lab  

资源简介

ics的proxy lab,实现一个代理服务器,已经经过测试,能够通过,绝对正确。

资源截图

代码片段和文件信息

/*
 * proxy.c - CS:APP Web proxy
 *
 * 
 * IMPORTANT: Give a high level description of your code here. You
 * must also provide a header comment at the beginning of each
 * function that describes what that function does.
 */ 

#include “csapp.h“

struct arg
{
    int fd;
    struct sockaddr_in sock;
};

FILE *log_file;
sem_t sem_log;
sem_t sem_dns;

/*
 * Function prototypes
 */
int parse_uri(char *uri char *target_addr char *path int  *port);
void format_log_entry(char *logstring struct sockaddr_in *sockaddr char *uri int size);
void *proxy(void *);
void Rio_writen_w(int fd void *usrbuf size_t n);
ssize_t Rio_readlineb_w(rio_t *rp void *usrbuf size_t maxlen);
int Open_clientfd_w(char *hostname int port);

/* 
 * main - Main routine for the proxy program 
 */
int main(int argc char **argv)
{
    Signal(SIGPIPE SIG_IGN);

    int port = atoi(argv[1]);

    sem_init(&sem_log 0 1);
    sem_init(&sem_dns 0 1);
 
    log_file = fopen(“./proxy.log“ “a“);

    int connfd;
    int listenfd = Open_listenfd(port);
    struct sockaddr_in clientaddr;
    int clientlen;
    pthread_t tid;
    struct arg g;

    while (1)
    {
        clientlen= sizeof(clientaddr);
        struct arg *g = (struct arg *)malloc(sizeof(struct arg));
        connfd = Accept(listenfd (SA *)(&(g->sock)) &clientlen);
        g->fd = connfd;
        Pthread_create(&tid NULL proxy (void *)g);
    }

    exit(0);
}

/*
 * Thread
 */
void *proxy(void *ptr)
{
    Pthread_detach(pthread_self());

    struct arg *g = (struct arg *)ptr;
    int connfd = g->fd;
    struct sockaddr_in sock;
    memcpy(&sock &(g->sock) sizeof(struct sockaddr_in));
    free(g);

    char buf[MAXLINE] method[MAXLINE] uri[MAXLINE] version[MAXLINE]
hostname[MAXLINE] pathname[MAXLINE] content[MAXLINE];
    int port server_fd content_len;
    rio_t rio_client rio_server;

    Rio_readinitb(&rio_client connfd);
    Rio_readlineb_w(&rio_client content MAXLINE);

    sscanf(content “%s %s %s“ method uri version);

    parse_uri(uri hostname pathname &port);

    //send content to server
    int retval = 0;
    server_fd = Open_clientfd_w(hostname port);
    if (server_fd==0) return;
    Rio_readinitb(&rio_server server_fd);  
    Rio_writen_w(server_fd content strlen(content));
    while (Rio_readlineb_w(&rio_client content MAXLINE)>2)
    {
        if (strstr(content “Proxy-Connection“))
            strcpy(content “Proxy-Connection: close\r\n“);
        else if (strstr(content “Connection“))
            strcpy(content “Connection: close\r\n“); 
        Rio_writen_w(server_fd content strlen(content));
    }
    Rio_writen_w(server_fd “\r\n“ 2);

    // receive content from server
    int found = 0;
    while (Rio_readlineb_w(&rio_server buf MAXLINE)>2) {
        char *index = strstr(buf “Content-Length“);
        if (index) {
            found = 1;
            content_len = atoi(index+16);
        }
        
        Rio_writen_w(connfd buf strlen(buf));
 

评论

共有 条评论