Example #1
0
DateInterval::DateInterval(const String& date_interval,
                           bool date_string /*= false */) {
  if (date_string) {
    setDateString(date_interval);
  } else {
    setInterval(date_interval);
  }
}
Example #2
0
File: kweb.c Project: klueska/kweb
/* This is a wrapped version of the child web server thread */
static void __http_server(struct kqueue *q,
                          struct http_connection *c,
                          struct http_request *r)
{
    struct stat statbuf;
    int j, file_fd, buflen;
    long i = 0, ret = 0;
    char *fstr;
    char *request_line;
    char *saveptr;
    char now[RFC1123_TIME_LEN + 1];
    char mod[RFC1123_TIME_LEN + 1];

    /* Try and extract a request from the connection. */
    ret = extract_request(c, r);

    /* If there was an error, just destroy the connection, as there is
     * nothing more we can do with this connection anyway. */
    if(ret < 0) {
        logger(LOG, "Connection reset by peer.", "", c->conn.id);
        maybe_destroy_connection(q, c);
        return;
    }

    /* If there was no error, but we weren't able to extract a request, finish up
     * if we are the last one to look at the connection. */
    if(ret == 0) {
        maybe_destroy_connection(q, c);
        return;
    }

    /* Otherwise, just reenqueue the connection so another thread can grab the
     * next request and start processing it. */
    if (!c->should_close) {
        if(c->burst_length) {
            c->burst_length--;
            enqueue_connection_head(q, c);
        }
        else {
            c->burst_length = MAX_BURST;
            enqueue_connection_tail(q, c);
        }
    }

    /* Attempt to intercept the request and do something special with it. */
    struct intercept_buf ib;
    if (intercept_request(&ib, r)) {
        /* Send the necessary header info + a blank line */
        logger(LOG, "INTERCEPT URL", &request_line[4], c->conn.id);
        setDateString(NULL, now);
        setDateString(NULL, mod);
        sprintf(r->buf, page_data[OK_HEADER], VERSION,
                now, ib.mime_type, ib.size, mod);
        serialized_write(c, r->buf, strlen(r->buf));
        serialized_write(c, ib.buf, ib.size);
        free(ib.buf);
        maybe_destroy_connection(q, c);
        return;
    }

    /* If not intercepted, parse through the extracted request, grabbing only the
     * first line. */
    request_line = strtok_r(r->buf, "\r\n", &saveptr);
    if (!request_line) {
        logger(LOG, "Unterminated request buffer.", "", c->conn.id);
        maybe_destroy_connection(q, c);
        return;
    }

    /* Make sure it's a GET operation */
    if(strncmp(request_line, "GET ", 4) && strncmp(request_line, "get ", 4)) {
        logger(FORBIDDEN, "Only simple GET operation supported", request_line, c->socketfd);
        serialized_write(c, page_data[FORBIDDEN_PAGE], strlen(page_data[FORBIDDEN_PAGE]));
        maybe_destroy_connection(q, c);
        return;
    }
    logger(LOG, "Request", request_line, c->conn.id);

    /* Strip the version info from the request_line */
    for(i=4; i<strlen(request_line); i++) {
        /* String is "GET URL?<query_data> HTTP_VERSION" */
        if(request_line[i] == ' ') {
            request_line[i] = '\0';
            break;
        }
    }

    /* Strip all query data from the request_line */
    for(i=4; i<strlen(request_line); i++) {
        /* String is "GET URL?<query_data>" */
        if(request_line[i] == '?') {
            request_line[i] = '\0';
            break;
        }
    }

    /* Otherwise, check for illegal parent directory use .. */
    for(j=4; j<i-1; j++) {
        if(request_line[j] == '.' && request_line[j+1] == '.') {
            logger(FORBIDDEN, "Parent directory (..) path names not supported", request_line, c->socketfd);
            serialized_write(c, page_data[FORBIDDEN_PAGE], strlen(page_data[FORBIDDEN_PAGE]));
            maybe_destroy_connection(q, c);
            return;
        }
    }

    /* Convert no filename to index file */
    if(!strncmp(request_line, "GET /\0", 6) || !strncmp(request_line, "get /\0", 6))
        strcpy(request_line, "GET /index.html");

    /* Work out the file type and check we support it */
    buflen=strlen(request_line);
    fstr = 0;
    for(i=0; extensions[i].ext != 0; i++) {
        int len = strlen(extensions[i].ext);
        if(!strncmp(&request_line[buflen-len], extensions[i].ext, len)) {
            fstr =extensions[i].filetype;
            break;
        }
    }
    if(fstr == 0) {
        logger(FORBIDDEN, "File extension type not supported", request_line, c->socketfd);
        serialized_write(c, page_data[FORBIDDEN_PAGE], strlen(page_data[FORBIDDEN_PAGE]));
        maybe_destroy_connection(q, c);
        return;
    }

    /* Open the file for reading */
    if((file_fd = open(&request_line[5], O_RDONLY)) == -1) {
        logger(NOTFOUND, "Failed to open file", &request_line[5], c->socketfd);
        serialized_write(c, page_data[NOTFOUND_PAGE], strlen(page_data[NOTFOUND_PAGE]));
        maybe_destroy_connection(q, c);
        return;
    }

    /* Get the File Stats */
    fstat(file_fd, &statbuf);

    /* Prepopulate the request buf with the beginning of the requested file */
    ret = read(file_fd, r->buf, sizeof(r->buf));
    if (ret < 0) {
        logger(ERROR, "Failed to read file", "...", 0);
        close(file_fd);
        maybe_destroy_connection(q, c);
        return;
    }

    /* Prepare the header info + a blank line */
    setDateString(NULL, now);
    setDateString(&statbuf.st_mtime, mod);
    sprintf(r->rsp_header, page_data[OK_HEADER], VERSION, now,
            fstr, statbuf.st_size, mod);
    logger(LOG, "Header", r->rsp_header, c->conn.id);

    /* Start sending a response */
    logger(LOG, "SEND", &request_line[5], c->conn.id);
    tpool_inform_blocking(&tpool);
    mutex_lock(&c->writelock);
    tpool_inform_unblocked(&tpool);
    timed_write(c, r->rsp_header, strlen(r->rsp_header));
    /* Send the file itself in 8KB chunks - last block may be smaller */
    do {
        if(timed_write(c, r->buf, ret) < 0)
            logger(LOG, "Write error on socket.", "", c->socketfd);
    } while((ret = read(file_fd, r->buf, sizeof(r->buf))) > 0);
    mutex_unlock(&c->writelock);

    close(file_fd);
    maybe_destroy_connection(q, c);
}