예제 #1
0
int main(void) {

    char req[] = "Post /test?name=value&name2=value2 HTTP/1.1\r\n"
                 "Content-Length: 12345\r\n"
                 "Host:   www.example.com  \r\n"
                 "Pragma: no-cache\r\n"
                 "Accept-Encoding: text/plain\r\n"
                 "\r\nTHIS_IS_THE_BODY";
    int len = strlen(req);

    printf("Body: %s\n", http_parse_body(req, len));
    printf("Method: %d (%s)\n", http_parse_method(req), http_method_str[http_parse_method(req)]);
    printf("URI: '%s' (path is '%s')\n", http_parse_uri(req), http_parse_path(http_parse_uri(req)));
    printf("Pragma: '%s'\n", http_parse_header_field(req, len, "Pragma"));
    printf("Content-length: '%s'\n", http_parse_header_field(req, len, "Content-length"));
    printf("Accept-Encoding: '%s'\n", http_parse_header_field(req, len, "Accept-Encoding"));
    printf("Host: '%s'\n", http_parse_header_field(req, len, "Host"));

    printf("Body: %s\n", http_parse_body(req, len));
    printf("Method: %d (%s)\n", http_parse_method(req), http_method_str[http_parse_method(req)]);
    printf("URI: '%s' (path is '%s')\n", http_parse_uri(req), http_parse_path(http_parse_uri(req)));
    printf("Pragma: '%s'\n", http_parse_header_field(req, len, "Pragma"));
    printf("Content-length: '%s'\n", http_parse_header_field(req, len, "Content-length"));
    printf("Accept-Encoding: '%s'\n", http_parse_header_field(req, len, "Accept-Encoding"));
    printf("Host: '%s'\n", http_parse_header_field(req, len, "Host"));

    return 0;
}
예제 #2
0
int do_http_parse_test(http_t *p_http, char *buf , int len)
{
	local_t* local = http_get_local_t(p_http);
	int head_len = 0,ret = 0;
	if (local->state == 4){
		ret=http_parse_body(buf,len,p_http);
	}
	head_len = s_http_parse(buf,len,p_http);
	if (local->state < 4) {
		DBGH("state is < 4 ,header is not end\n");
		return -1;
	} else if (local->state == 4) {
		ret = http_parse_head(buf,head_len,0,p_http,0);
		ret = http_parse_body(buf+head_len,len-head_len,p_http);
	} else {
		DBGH("state = %d error \n", local->state);
	}
	
		
//	ret=http_parse_body(buf+head_len,1,p_http);
//        http_dump_logic(p_http);
//	http_dump_int(p_http);
//	http_dump_str(p_http);
	//http_dump_arg(p_http);

	return 0;
}
예제 #3
0
/*
 * If the HTTP header found in the first 'length' bytes of 'request'
 * is a complete HTTP header (i.e. contains an empty line indicating
 * end of header), returns the size of this header (in
 * bytes). Otherwise, returns -1. This function supports both requests
 * with LF only and with CR-LF. This function is only expected to be
 * called during the request retrieval process, and should not be used
 * after a parse function has been called, since parse functions
 * change the request in a way that changes the behaviour of this
 * function.
 */
int http_header_complete(const char *request, int length) {
    
    const char *body = http_parse_body(request, length);
    if (body && !memchr(request, '\0', body - request))
        return body - request;
    else
        return -1;
}
예제 #4
0
파일: service.c 프로젝트: czhu12/cs317
void init_req_header(req_header * req, char * header){
	int len = strlen(header);
	req->body = http_parse_body(header, len);
	req->method = http_parse_method((char *) header);
	req->uri = http_parse_uri(header);
	req->path = http_parse_path(http_parse_uri(header));
	cookie * cookies = parse_cookies(header);
	req->cookies = cookies;
	req->connection = http_parse_header_field(header, len, "Connection");
}
예제 #5
0
파일: service.c 프로젝트: czhu12/cs317
void init_req_header(req_header * req, char * header){
	char * cookie_header = malloc(strlen(header));
	strcpy(cookie_header, header);
	int len = strlen(header);
	req->body = http_parse_body(header, len);
	req->method = http_parse_method((char *) header);
	req->uri = http_parse_uri(header);
	req->path = http_parse_path(http_parse_uri(header));
	req->connection = http_parse_header_field( header, len, "Connection");
	req->cache_control = http_parse_header_field(header, len, "Cache-Control");

	cookie * cookies = parse_cookies(cookie_header, &(req->num_cookies));
	req->cookies = cookies;
}
예제 #6
0
void handle_client(int socket) {
  node *cookie, *param;
  service cmd;
  http_method method;
  http_response resp;
  int bytes, s, expected_len, header_len;
  char req[BUFFER_SIZE], buf[BUFFER_SIZE];
  const char *path;
  char *connection, *req_body_len;
  time_t since_time;

  /* TODO Loop receiving requests and sending appropriate responses,
   *      until one of the conditions to close the connection is
   *      met.
   */
  cookie = param = resp.expire = resp.cookie = NULL;

  do {
    // New request
    free_list(resp.cookie);
    free_list(resp.expire);
    if (cookie) free_list(cookie);
    if (param) free_list(param);
    cookie = param = NULL;
    memset(&resp, 0, sizeof(http_response));
    memset(req, 0, BUFFER_SIZE);
    bytes = 0;

    // Wait for HTTP header to complete
    do {
      bytes += recv(socket, req + bytes, BUFFER_SIZE, 0);
      header_len = http_header_complete(req, bytes);
    } while (header_len == -1);
    
    // Receive body if there is content length
    if (strstr(req, HDR_CONTENT_LEN)) {
      strcpy(buf, req);
      req_body_len = get_header_value_from_req(buf, HDR_CONTENT_LEN);
      expected_len = atoi(req_body_len) + header_len;
      while (bytes < expected_len) {
         bytes += recv(socket, req + bytes, BUFFER_SIZE, 0);
      }
    }
    // printf("recv %i bytes\n", bytes);

    // Get HTTP method
    method = http_parse_method(req);

    // Get path
    strcpy(buf, req);
    path = http_parse_path(http_parse_uri(buf));
    // printf("Request: %s\n", path);

    // Parse cookies 
    if (strstr(req, HDR_COOKIE)) {
      strcpy(buf, req);
      cookie = get_cookies_from_header(get_header_value_from_req(buf, HDR_COOKIE));
    } else {
      cookie = NULL;
    }

    // Match service command
    cmd = SERV_UNKNOWN;
    for (s= 0; s < SERV_UNKNOWN; s++) {
      if (strncasecmp(path, service_str[s], strlen(service_str[s])) == 0) {
        cmd = s;
        break;
      }
    }

    // Handle command
    switch(cmd) {
      case SERV_KNOCK:
      case SERV_LOGIN:
      case SERV_LOGOUT:
      case SERV_GETFILE:
      case SERV_ADDCART:
      case SERV_DELCART:
      case SERV_CHECKOUT:
        if (method == METHOD_GET) {
          param = get_params_from_query(get_query_str_from_path(path));
          if (cmd == SERV_KNOCK) {
            knock_handler(&resp, cookie);
          } else if (cmd == SERV_LOGIN) {
            login_handler(&resp, param);
          } else if (cmd == SERV_LOGOUT) {
            logout_handler(&resp, cookie);
          } else if (cmd == SERV_GETFILE) {
            since_time = 0;
            strcpy(buf, req);
            if (strstr(buf, HDR_IF_MOD_SINCE)) {
              if (!RFC_822_to_time(strstr(buf, HDR_IF_MOD_SINCE) + 
                    strlen(HDR_IF_MOD_SINCE), &since_time)) {
                since_time = 0;
              }
            }
            getfile_handler(&resp, param, since_time);
          } else if (cmd == SERV_ADDCART) {
            addcart_handler(&resp, param, cookie);
          } else if (cmd == SERV_DELCART) {
            delcart_handler(&resp, param, cookie);
          } else if (cmd == SERV_CHECKOUT) {
            checkout_handler(&resp, cookie);
          } else {
            resp.status = NOT_FOUND;
          }
        } else {
          resp.allow = METHOD_GET;
          resp.status = METHOD_NOT_ALLOWED;
        }
        break;
      case SERV_PUTFILE:
        if (method == METHOD_POST) {
          strcpy(buf, req);
          param = get_params_from_query((char*) http_parse_body(buf, bytes));
          putfile_handler(&resp, cookie, param);
        } else {
          resp.allow = METHOD_POST;
          resp.status = METHOD_NOT_ALLOWED;
        }
        break;
      default:
        resp.status = NOT_FOUND;
        break;
    }

    // Check if status not ok or 
    // client wants to close connection after completing request
    if (resp.status != OK) {
      resp.connection = CLOSE;
    } else if (strstr(req, "Connection:")) {
      connection = http_parse_header_field(buf, bytes, "Connection");
      if (strcmp(connection, "close") == 0) {
        resp.connection = CLOSE;
      }
    }

    send_response(socket, &resp);  
  } while (resp.connection != CLOSE);
}
예제 #7
0
파일: http.c 프로젝트: n8ohu/whitebox
int http_parse(int fd, struct http_request *r)
{
    int recvd;
    static char command[HTTP_BUFFER_LEN + 1];
    char *i;
    int newline_machine = 0;
    char *linestart;
    char *bodystart;
    static char linebuf[HTTP_LINE_LEN + 1];
    int linenum;

    if ((recvd = read(fd, (void*)command, HTTP_BUFFER_LEN)) < 0) {
        if (errno == EAGAIN) {
            printf("Eagain\n");
            return recvd;
        }
        perror("recvfrom");
        exit(1);
    }

    if ((recvd == 1 && *((char*)command) == '\0') || (recvd == 0)) {
        return 0;
    }

    command[HTTP_BUFFER_LEN] = '\0';

    linenum = 0;
    linestart = command;
    for (i = command; *i; ++i) {
        switch (newline_machine) {
            case 0: case 2: {
                if (*i == '\r') newline_machine++;
                else newline_machine = 0;
            } break;
            case 1: {
                if (*i == '\n') newline_machine++;
                else newline_machine = 0;
            } break;
            case 3: {
                if (*i == '\n') newline_machine++;
                else newline_machine = 0;
            } break;
            default: {
                newline_machine = 0;
            }
        }
        if (newline_machine == 2) {
            int linelength = i - linestart;
            linelength = linelength < HTTP_LINE_LEN ? linelength : HTTP_LINE_LEN;
            strncpy(linebuf, linestart, i - linestart);
            linebuf[HTTP_LINE_LEN] = '\0';
            if (linenum == 0) {
                if (http_parse_status(r, linebuf) < 0) {
                    printf("Estatus\n");
                    return -1;
                }
            } else {
                if (http_parse_header(r, linebuf) < 0) {
                    printf("Eheader\n");
                    return -1;
                }
            }

            linestart = i + 1;
            linenum++;
        }
        if (newline_machine == 4) {
            bodystart = i + 1;
            if (http_parse_body(r, bodystart) < 0) {
                printf("Ebody\n");
                return -1;
            }
            linenum++;
            break;
        }
    }

    return 0;
}