コード例 #1
0
ファイル: httpclient.c プロジェクト: LeeThompson/replaypc
extern int hc_read_pieces(struct hc * hc,
                          void (*callback)(unsigned char *, size_t, void *),
                          void * v)
{
    char * te;
    int chunked = 0;
    int done = 0;
    char * buf;
    size_t len, len_read;
    
    te = hc_lookup_rsp_header(hc, "Transfer-Encoding");
    if (te && strcmp(te, "chunked") == 0) {
        chunked = 1;
    }

    while (!done) {
        if (chunked) {
            char lenstr[32];

            nc_read_line(hc->nc, lenstr, sizeof lenstr);
            len = strtoul(lenstr, NULL, 16);
        } else {
            len = 4096;
        }
        if (len) {
            buf = malloc(len+1);
            len_read = nc_read(hc->nc, buf, len);
            if (len_read < len)
                done = 1;
            buf[len_read] = '\0';
            callback(buf, len_read, v);
        } else {
            done = 1;
        }
        if (chunked) {
            char linebuf[80];
            /* if done, then any non-blank lines read here are
               supposed to be treated as HTTP header lines, but since
               we didn't say we could accept trailers, the server's
               only allowed to send them if it's happy with us
               discarding them. (2616 3.7b).  The Replay doesn't use
               trailers anyway */
            while (nc_read_line(hc->nc, linebuf, sizeof linebuf) > 0)
                ;
        }
    }
    return 0;
}
コード例 #2
0
extern int hc_read_pieces_len(struct hc * hc,
                              void (*callback)(unsigned char *, size_t, void *),
                              void * v, size_t len_to_read)
{
    char * te;
    int chunked = 0;
    int done = 0;
    char * buf;
    size_t len, len_read, octets_to_go;
    char * cl;

    // NOTE: len_to_read is not currently implemented for non-chunked content.
    // The ReplayTV only sends chunked content so this doesn't matter here.
    cl = hc_lookup_rsp_header(hc, "Content-Length");
    if (cl) {
        octets_to_go = strtoul(cl, NULL, 10);
    } else {
        octets_to_go = 0;
    }

    te = hc_lookup_rsp_header(hc, "Transfer-Encoding");
    if (te && strcmp(te, "chunked") == 0) {
        chunked = 1;
    }
    while (!done) {
        if (chunked) {
            char lenstr[32];

            if (!hc->curr_chunk_len) {
                nc_read_line(hc->nc, lenstr, sizeof lenstr);
                hc->curr_chunk_len = strtoul(lenstr, NULL, 16);
            }
            if (len_to_read > hc->curr_chunk_len) {
                len = hc->curr_chunk_len;
            } else {
                len = len_to_read;
            }
        } else {
            if (cl) {
                len = octets_to_go;
                if (len > MAX_CHUNK)
                    len = MAX_CHUNK;
            } else {
                len = MAX_CHUNK;
            }
        }
        if (len) {
            buf = malloc(len+1);
            len_read = nc_read(hc->nc, buf, len);
            if (len_read <= len)
                done = 1;
            buf[len_read] = '\0';
            callback(buf, len_read, v);
            if (cl) {
                octets_to_go -= len_read;
                if (octets_to_go == 0 && !chunked) {
                    done = 1;
                }
            }
            hc->curr_chunk_len -= len_read;
        } else {
            done = 1;
        }
        if (chunked && !hc->curr_chunk_len) {
            char linebuf[80];
            /* if done, then any non-blank lines read here are
               supposed to be treated as HTTP header lines, but since
               we didn't say we could accept trailers, the server's
               only allowed to send them if it's happy with us
               discarding them. (2616 3.7b).  The Replay doesn't use
               trailers anyway */
            while (nc_read_line(hc->nc, linebuf, sizeof linebuf) > 0)
                ;
        }
    }
    return 0;
}