コード例 #1
0
ファイル: httpd.c プロジェクト: jrswanson91/HTTPServer
/**
 * The main function that handles an HTTP request.
 */
int main(int argc, const char *argv[])
{
    req_t *req;
    if (argc < 2) {
        return -1;
    }

    document_root = argv[1];

    req = read_request(0);

    if (!req && errno != 0) {
        // internal error
        perror("httpd");
        send_error(stdout, 500, "Internal Server Error",
                   "Internal server error: %s", strerror(errno));
        return 1;
    } else if (!req || !req_is_valid(req)) {
        send_error(stdout, 400, "Bad Request", "Incomplete or invalid request.");
        return 0;
    } else {
        if (handle_request(req, stdout) < 0) {
            return 1;
        } else {
            return 0;
        }
    }
}
コード例 #2
0
ファイル: rrw_server.c プロジェクト: isuvalov/fftsender_new
int srv_handle_req(srv_t *srv) {
  base_req_t *req = (base_req_t *)srv->req;

  if(!req_is_valid(req))
    return (srv->fn_rv = RRW_RV_BAD_REQ);

  switch(req->fn) {
  case RRW_FN_STATUS:
    srv->fn_rv = srv_handle_status_req(srv);
    break;

  case RRW_FN_MEAS_CTL:
    srv->fn_rv = srv_handle_meas_ctl_req(srv);    
    break;

  case RRW_FN_TEST:
    srv->fn_rv = srv_handle_test_req(srv);
    break;

  case RRW_FN_DATA:    
    srv->fn_rv = srv_handle_data_req(srv);
    break;

  default:
    srv->fn_rv = RRW_RV_BAD_REQ;
    break;
  }
    
  return srv->fn_rv;
}
コード例 #3
0
ファイル: rrw_server.c プロジェクト: halecky/fftsender_new
/**Handle request in dependence of its type*/
int srv_handle_req(srv_t *srv) {
  base_req_t *req = (base_req_t *)srv->req;

  //if request has no validity mark stop further processing
  if(!req_is_valid(req)) {
    #ifdef DBG_SRV
    logprintf("SERVER: invalid request!\n");
    #endif // DBG_SRV
    return (srv->fn_rv = RRW_RV_BAD_REQ);
  }
  //call appropriate handler and set request return value (srv->fn_rv)
  switch(req->fn) {
  case RRW_FN_STATUS:
    #ifdef DBG_SRV
    logprintf("SERVER: %d get status!\n",((base_req_t *)srv->req)->no);
    #endif
    srv->fn_rv = srv_handle_status_req(srv);
    break;

  case RRW_FN_MEAS_CTL:
    #ifdef DBG_SRV
    logprintf("SERVER: %d measurement control!\n",((base_req_t *)srv->req)->no);
    #endif
    srv->fn_rv = srv_handle_meas_ctl_req(srv);
    break;

  case RRW_FN_DATA_ALT:
    #ifdef DBG_SRV
    if(req->fn == RRW_FN_DATA)
      logprintf("SERVER: %d get data!\n",((base_req_t *)srv->req)->no);
    if(req->fn == RRW_FN_DATA_ALT)
      logprintf("SERVER: %d get data alt!\n",((base_req_t *)srv->req)->no);
    #endif
    srv->fn_rv = srv_handle_data_req(srv);
    break;
  case RRW_FN_SET_TH:
    #ifdef DBG_SRV
    logprintf("SERVER: %d set threshold!\n",((base_req_t *)srv->req)->no);
    #endif
    srv->fn_rv = srv_handle_setth_req(srv);
    break;
  case RRW_FN_GET_TH:
    #ifdef DBG_SRV
    logprintf("SERVER: %d get threshold!\n",((base_req_t *)srv->req)->no);
    #endif
    srv->fn_rv = srv_handle_getth_req(srv);
    break;
  default:
    #ifdef DBG_SRV
    logprintf("SERVER: %d incorrect function code!\n",((base_req_t *)srv->req)->no);
    #endif
    //if request contains incorrect function code process it as bad request
    srv->fn_rv = RRW_RV_BAD_REQ;
    break;
  }

  return srv->fn_rv;
}
コード例 #4
0
ファイル: httpd.c プロジェクト: jrswanson91/HTTPServer
/**
 * Handle an HTTP request and produce an appropriate response.
 *
 * @param req The parsed HTTP request.
 * @param stream The stream to which the response should be printed.
 */
static int handle_request(req_t *req, FILE *stream)
{
    g_return_val_if_fail(req != NULL, -1);
    g_return_val_if_fail(req_is_complete(req), -1);
    g_return_val_if_fail(req_is_valid(req), -1);
    g_return_val_if_fail(document_root != NULL, -1);

    const char *path = req_path(req);

    // check path validity
    if (strstr(path, "..")) {
        // oops, contains '..'
        send_error(stream, 400, "Bad Request", "Request path is invalid");
        return 0;
    } else if (*path != '/') {
        // oops, is not absolute (no leading '/')
        send_error(stream, 400, "Bad Request", "Request path is invalid");
        return 0;
    }

    int result = 0;
    // combine path with document root to get a UNIX file path
    char *filepath = g_build_filename(document_root, path, NULL);
    // now start examining it
    struct stat sb;
    if (stat(filepath, &sb) < 0) {
        // there is an error with the file
        switch (errno) {
            case ENOENT:
                send_error(stream, 404, "Not Found",
                           "The resource %s could not be found.", path);
                break;
            case EACCES:
                send_error(stream, 401, "Forbidden",
                           "The resource %s could not be read.", path);
                break;
            default:
                send_error(stream, 500, "Internal Server Error",
                           "%s: %s", path, strerror(errno));
                result = -1;
                break;
        }
    } else if (S_ISDIR(sb.st_mode)) {
        if (filepath[strlen(filepath) - 1] == '/') {
            // we have a directory with a proper path. check for index.html.
            char *ind_fp = g_build_filename(filepath, "index.html", NULL);
            if (stat(ind_fp, &sb) < 0) {
                // not found
                result = send_dir_index(stream, req, filepath);
            } else {
                // index.html exists
                result = send_file(stream, req, ind_fp, &sb);
            }
            g_free(ind_fp);
        } else {
            // no trailing '/', send a redirect
            fprintf(stream, "HTTP/1.0 301 Moved Permanently\r\n");
            const char *host = req_host(req);
            if (host) {
                fprintf(stream, "Location: http://%s%s/\r\n", req_host(req), path);
            } else {
                // not entirely conformant, but the best we can do
                fprintf(stderr, "warning: no host in request\n");
                fprintf(stream, "Location: %s/\r\n", path);
            }
            fprintf(stream, "\r\n");
        }
    } else if (S_ISREG(sb.st_mode)) {
        result = send_file(stream, req, filepath, &sb);
    } else {
        send_error(stream, 401, "Forbidden", "Access denied.");
    }

    g_free(filepath);

    return result;
}
コード例 #5
0
/**
 * The main function that handles an HTTP request.
 */
int main(int argc, char **argv)
{
	//obtain arguments
	int code;
	char *host = "::";
	char *port = "4080";
	char act_host[NI_MAXHOST];
	char act_port[NI_MAXSERV];
	//ssize_t result;
	//size_t bytes_done, req_len;
	struct sockaddr *addr;
	ssize_t addr_len;
	char **prog_args;
	FILE *handler;
	setup_signals();

	while((code = getopt(argc, argv, "h:p:"))>0) {
		switch(code){
			case 'h':
				host = optarg;
				break;
			case 'p':
				port = optarg;
				break;
			case '?':
			default:
				fprintf(stderr, "bad argument\n");
				exit(EX_USAGE);
		}
	}
	prog_args = malloc((argc - optind + 1) * sizeof(char*));
	for (int i = 0; i < argc - optind; i++) {
		prog_args[i] = argv[optind + i];
	}
	prog_args[argc-optind] = NULL;

	addr_len = lookup_address(host, port, &addr);
	if (addr_len < 0) {
		fprintf(stderr, "%s:%s: %s\n", host, port, gai_strerror(addr_len));
		exit(EXIT_FAILURE);
	}

	getnameinfo(addr, addr_len, act_host, NI_MAXHOST, act_port, NI_MAXSERV,
		NI_NUMERICHOST | NI_NUMERICSERV);
	fprintf(stderr, "listening on %s:%s\n", act_host, act_port);

	int sock = socket(AF_INET6, SOCK_STREAM, 0);
	if (sock < 0) {
		perror("socket");
		exit(EXIT_FAILURE);
	}

	code = bind(sock, addr, addr_len);
	if (code < 0) {
		perror("bind");
		exit(EXIT_FAILURE);
	}

	code = listen(sock, 5);
	if (code < 0) {
		perror("listen");
		exit(EXIT_FAILURE);
	}

	pid_t group = setpgrp();
//	fprintf(stderr, "process group %d\n", group);

//wait for connection and then process the request.
	while(keep_running){
		fprintf(stderr, "waiting for connection \n");
		struct sockaddr_in6 c_addr;
		socklen_t c_addr_len = sizeof(struct sockaddr_in6);
		int client = accept(sock, (void*) &c_addr, &c_addr_len);
		if(client < 0){
			if(errno == EINTR){
				continue;
			}else{
				perror("accept");
				exit(EXIT_FAILURE);
			}
		}
		pid_t child = fork();
		if(child < 0){
			perror("fork");
			exit(EX_OSERR);
		}else if(child){
			close(client);
		}else{
			//close(sock);
			req_t *req;
			document_root = argv[optind];

			req = read_request(client);
			handler = fdopen(client, "r+");
	
			if (!req && errno != 0) {
			// internal error
				perror("httpd");
				send_error(handler, 500, "Internal Server Error",
					   "Internal server error: %s", strerror(errno));
				return 1;
			} else if (!req || !req_is_valid(req)) {
				send_error(handler, 400, "Bad Request", "Incomplete or invalid request.");
				return 0;
			} else {
				//handler = fdopen(client, "r+");
				if (handle_request(req, handler) < 0) {
				    return 1;
				} else {
				    fclose(handler);
				    close(client);
				    free(addr);
				    return 0;
				}
			}
			close(sock);
			close(client);
			fclose(handler);
		}
	}
	close(sock);
	free(addr);
	return 0;
}