⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 httpheader.c

📁 -
💻 C
📖 第 1 页 / 共 3 页
字号:
httpHeaderReset(HttpHeader * hdr){    http_hdr_owner_type ho = hdr->owner;    assert(hdr);    ho = hdr->owner;    httpHeaderClean(hdr);    httpHeaderInit(hdr, ho);    return 0;}inthttpHeaderParse(HttpHeader * hdr, const char *header_start, const char *header_end){    const char *field_start = header_start;    HttpHeaderEntry *e;    assert(hdr);    assert(header_start && header_end);    debug(55, 7) ("parsing hdr: (%p)\n%s\n", hdr, getStringPrefix(header_start, header_end));    HttpHeaderStats[hdr->owner].parsedCount++;    /* commonn format headers are "<name>:[ws]<value>" lines delimited by <CRLF> */    while (field_start < header_end) {	const char *field_end = field_start + strcspn(field_start, "\r\n");	if (!*field_end || field_end > header_end)	    return httpHeaderReset(hdr);	/* missing <CRLF> */	e = httpHeaderEntryParseCreate(field_start, field_end);	if (e != NULL)	    httpHeaderAddEntry(hdr, e);	else	    debug(55, 2) ("warning: ignoring unparseable http header field near '%s'\n",		getStringPrefix(field_start, field_end));	field_start = field_end;	/* skip CRLF */	if (*field_start == '\r')	    field_start++;	if (*field_start == '\n')	    field_start++;    }    return 1;			/* even if no fields where found, it is a valid header */}/* packs all the entries using supplied packer */voidhttpHeaderPackInto(const HttpHeader * hdr, Packer * p){    HttpHeaderPos pos = HttpHeaderInitPos;    const HttpHeaderEntry *e;    assert(hdr && p);    debug(55, 7) ("packing hdr: (%p)\n", hdr);    /* pack all entries one by one */    while ((e = httpHeaderGetEntry(hdr, &pos)))	httpHeaderEntryPackInto(e, p);}/* returns next valid entry */HttpHeaderEntry *httpHeaderGetEntry(const HttpHeader * hdr, HttpHeaderPos * pos){    assert(hdr && pos);    assert(*pos >= HttpHeaderInitPos && *pos < hdr->entries.count);    for ((*pos)++; *pos < hdr->entries.count; (*pos)++) {	if (hdr->entries.items[*pos])	    return hdr->entries.items[*pos];    }    return NULL;}/* * returns a pointer to a specified entry if any  * note that we return one entry so it does not make much sense to ask for * "list" headers */HttpHeaderEntry *httpHeaderFindEntry(const HttpHeader * hdr, http_hdr_type id){    HttpHeaderPos pos = HttpHeaderInitPos;    HttpHeaderEntry *e;    assert(hdr);    assert_eid(id);    assert(!CBIT_TEST(ListHeadersMask, id));    /* check mask first */    if (!CBIT_TEST(hdr->mask, id))	return NULL;    /* looks like we must have it, do linear search */    while ((e = httpHeaderGetEntry(hdr, &pos))) {	if (e->id == id)	    return e;    }    /* hm.. we thought it was there, but it was not found */    assert(0);    return NULL;		/* not reached */}/* * same as httpHeaderFindEntry */static HttpHeaderEntry *httpHeaderFindLastEntry(const HttpHeader * hdr, http_hdr_type id){    HttpHeaderPos pos = HttpHeaderInitPos;    HttpHeaderEntry *e;    HttpHeaderEntry *result = NULL;    assert(hdr);    assert_eid(id);    assert(!CBIT_TEST(ListHeadersMask, id));    /* check mask first */    if (!CBIT_TEST(hdr->mask, id))	return NULL;    /* looks like we must have it, do linear search */    while ((e = httpHeaderGetEntry(hdr, &pos))) {	if (e->id == id)	    result = e;    }    assert(result);		/* must be there! */    return result;}/* * deletes all fields with a given name if any, returns #fields deleted;  */inthttpHeaderDelByName(HttpHeader * hdr, const char *name){    int count = 0;    HttpHeaderPos pos = HttpHeaderInitPos;    HttpHeaderEntry *e;    httpHeaderMaskInit(&hdr->mask, 0);	/* temporal inconsistency */    debug(55, 7) ("deleting '%s' fields in hdr %p\n", name, hdr);    while ((e = httpHeaderGetEntry(hdr, &pos))) {	if (!strCaseCmp(e->name, name)) {	    httpHeaderDelAt(hdr, pos);	    count++;	} else	    CBIT_SET(hdr->mask, e->id);    }    return count;}/* deletes all entries with a given id, returns the #entries deleted */inthttpHeaderDelById(HttpHeader * hdr, http_hdr_type id){    int count = 0;    HttpHeaderPos pos = HttpHeaderInitPos;    HttpHeaderEntry *e;    debug(55, 8) ("%p del-by-id %d\n", hdr, id);    assert(hdr);    assert_eid(id);    assert_eid(id != HDR_OTHER);	/* does not make sense */    if (!CBIT_TEST(hdr->mask, id))	return 0;    while ((e = httpHeaderGetEntry(hdr, &pos))) {	if (e->id == id) {	    httpHeaderDelAt(hdr, pos);	    count++;	}    }    CBIT_CLR(hdr->mask, id);    assert(count);    return count;}/* * deletes an entry at pos and leaves a gap; leaving a gap makes it * possible to iterate(search) and delete fields at the same time */voidhttpHeaderDelAt(HttpHeader * hdr, HttpHeaderPos pos){    HttpHeaderEntry *e;    assert(pos >= HttpHeaderInitPos && pos < hdr->entries.count);    e = hdr->entries.items[pos];    hdr->entries.items[pos] = NULL;    /* decrement header length, allow for ": " and crlf */    hdr->len -= strLen(e->name) + 2 + strLen(e->value) + 2;    assert(hdr->len >= 0);    httpHeaderEntryDestroy(e);}/* appends an entry;  * does not call httpHeaderEntryClone() so one should not reuse "*e" */voidhttpHeaderAddEntry(HttpHeader * hdr, HttpHeaderEntry * e){    assert(hdr && e);    assert_eid(e->id);    debug(55, 7) ("%p adding entry: %d at %d\n",	hdr, e->id, hdr->entries.count);    if (CBIT_TEST(hdr->mask, e->id))	Headers[e->id].stat.repCount++;    else	CBIT_SET(hdr->mask, e->id);    arrayAppend(&hdr->entries, e);    /* increment header length, allow for ": " and crlf */    hdr->len += strLen(e->name) + 2 + strLen(e->value) + 2;}/* return a list of entries with the same id separated by ',' and ws */StringhttpHeaderGetList(const HttpHeader * hdr, http_hdr_type id){    String s = StringNull;    HttpHeaderEntry *e;    HttpHeaderPos pos = HttpHeaderInitPos;    debug(55, 6) ("%p: joining for id %d\n", hdr, id);    /* only fields from ListHeaders array can be "listed" */    assert(CBIT_TEST(ListHeadersMask, id));    if (!CBIT_TEST(hdr->mask, id))	return s;    while ((e = httpHeaderGetEntry(hdr, &pos))) {	if (e->id == id)	    strListAdd(&s, strBuf(e->value), ',');    }    /*     * note: we might get an empty (len==0) string if there was an "empty"     * header; we must not get a NULL string though.     */    assert(strBuf(s));    /* temporary warning: remove it! @?@ @?@ @?@ */    if (!strLen(s))	debug(55, 3) ("empty list header: %s (%d)\n", strBuf(Headers[id].name), id);    debug(55, 6) ("%p: joined for id %d: %s\n", hdr, id, strBuf(s));    return s;}/* test if a field is present */inthttpHeaderHas(const HttpHeader * hdr, http_hdr_type id){    assert(hdr);    assert_eid(id);    assert(id != HDR_OTHER);    debug(55, 7) ("%p lookup for %d\n", hdr, id);    return CBIT_TEST(hdr->mask, id);}voidhttpHeaderPutInt(HttpHeader * hdr, http_hdr_type id, int number){    assert_eid(id);    assert(Headers[id].type == ftInt);	/* must be of an appropriate type */    assert(number >= 0);    httpHeaderAddEntry(hdr, httpHeaderEntryCreate(id, NULL, xitoa(number)));}voidhttpHeaderPutTime(HttpHeader * hdr, http_hdr_type id, time_t time){    assert_eid(id);    assert(Headers[id].type == ftDate_1123);	/* must be of an appropriate type */    assert(time >= 0);    httpHeaderAddEntry(hdr, httpHeaderEntryCreate(id, NULL, mkrfc1123(time)));}voidhttpHeaderPutStr(HttpHeader * hdr, http_hdr_type id, const char *str){    assert_eid(id);    assert(Headers[id].type == ftStr);	/* must be of an appropriate type */    assert(str);    httpHeaderAddEntry(hdr, httpHeaderEntryCreate(id, NULL, str));}voidhttpHeaderPutAuth(HttpHeader * hdr, const char *authScheme, const char *realm){    assert(hdr && authScheme && realm);    httpHeaderPutStrf(hdr, HDR_WWW_AUTHENTICATE, "%s realm=\"%s\"", authScheme, realm);}voidhttpHeaderPutCc(HttpHeader * hdr, const HttpHdrCc * cc){    MemBuf mb;    Packer p;    assert(hdr && cc);    /* remove old directives if any */    httpHeaderDelById(hdr, HDR_CACHE_CONTROL);    /* pack into mb */    memBufDefInit(&mb);    packerToMemInit(&p, &mb);    httpHdrCcPackInto(cc, &p);    /* put */    httpHeaderAddEntry(hdr, httpHeaderEntryCreate(HDR_CACHE_CONTROL, NULL, mb.buf));    /* cleanup */    packerClean(&p);    memBufClean(&mb);}voidhttpHeaderPutContRange(HttpHeader * hdr, const HttpHdrContRange * cr){    MemBuf mb;    Packer p;    assert(hdr && cr);    /* remove old directives if any */    httpHeaderDelById(hdr, HDR_CONTENT_RANGE);    /* pack into mb */    memBufDefInit(&mb);    packerToMemInit(&p, &mb);    httpHdrContRangePackInto(cr, &p);    /* put */    httpHeaderAddEntry(hdr, httpHeaderEntryCreate(HDR_CONTENT_RANGE, NULL, mb.buf));    /* cleanup */    packerClean(&p);    memBufClean(&mb);}voidhttpHeaderPutRange(HttpHeader * hdr, const HttpHdrRange * range){    MemBuf mb;    Packer p;    assert(hdr && range);    /* remove old directives if any */    httpHeaderDelById(hdr, HDR_RANGE);    /* pack into mb */    memBufDefInit(&mb);    packerToMemInit(&p, &mb);    httpHdrRangePackInto(range, &p);    /* put */    httpHeaderAddEntry(hdr, httpHeaderEntryCreate(HDR_RANGE, NULL, mb.buf));    /* cleanup */    packerClean(&p);    memBufClean(&mb);}/* add extension header (these fields are not parsed/analyzed/joined, etc.) */voidhttpHeaderPutExt(HttpHeader * hdr, const char *name, const char *value){    assert(name && value);    debug(55, 8) ("%p adds ext entry '%s: %s'\n", hdr, name, value);    httpHeaderAddEntry(hdr, httpHeaderEntryCreate(HDR_OTHER, name, value));}inthttpHeaderGetInt(const HttpHeader * hdr, http_hdr_type id){    HttpHeaderEntry *e;    int value = -1;    int ok;    assert_eid(id);    assert(Headers[id].type == ftInt);	/* must be of an appropriate type */    if ((e = httpHeaderFindEntry(hdr, id))) {	ok = httpHeaderParseInt(strBuf(e->value), &value);	httpHeaderNoteParsedEntry(e->id, e->value, !ok);    }    return value;}time_thttpHeaderGetTime(const HttpHeader * hdr, http_hdr_type id){    HttpHeaderEntry *e;    time_t value = -1;    assert_eid(id);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -