/*
**  Copyright 2003-2005  The Apache Software Foundation
**
**  Licensed under the Apache License, Version 2.0 (the "License");
**  you may not use this file except in compliance with the License.
**  You may obtain a copy of the License at
**
**      http://www.apache.org/licenses/LICENSE-2.0
**
**  Unless required by applicable law or agreed to in writing, software
**  distributed under the License is distributed on an "AS IS" BASIS,
**  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
**  See the License for the specific language governing permissions and
**  limitations under the License.
*/

#include "apreq_util.h"
#include "apreq_error.h"
#include "apr_time.h"
#include "apr_strings.h"
#include "apr_lib.h"
#include <assert.h>
#define MIN(a,b) ( (a) < (b) ? (a) : (b) )
#define MAX(a,b) ( (a) > (b) ? (a) : (b) )

/* used for specifying file sizes */

APREQ_DECLARE(apr_int64_t) apreq_atoi64f(const char *s)
{
    apr_int64_t n = 0;
    char *p;
    if (s == NULL)
        return 0;

    n = apr_strtoi64(s, &p, 0);

    if (p == NULL)
        return n;
    while (apr_isspace(*p))
        ++p;

    switch (*p) {
      case 'G': /* fall thru */
      case 'g': return n * 1024*1024*1024;
      case 'M': /* fall thru */
      case 'm': return n * 1024*1024;
      case 'K': /* fall thru */
      case 'k': return n * 1024;
    }

    return n;
}


/* converts date offsets (e.g. "+3M") to seconds */

APREQ_DECLARE(apr_int64_t) apreq_atoi64t(const char *s) 
{
    apr_int64_t n = 0;
    char *p;
    if (s == NULL)
        return 0;
    n = apr_strtoi64(s, &p, 0); /* XXX: what about overflow? */

    if (p == NULL)
        return n;
    while (apr_isspace(*p))
        ++p;

    switch (*p) {
      case 'Y': /* fall thru */
      case 'y': return n * 60*60*24*365;
      case 'M': return n * 60*60*24*30;
      case 'D': /* fall thru */
      case 'd': return n * 60*60*24;
      case 'H': /* fall thru */
      case 'h': return n * 60*60;
      case 'm': return n * 60;
      case 's': /* fall thru */
      default:
          return n;
    }
    /* should never get here */
    return -1;
}


APREQ_DECLARE(apr_ssize_t ) apreq_index(const char* hay, apr_size_t hlen, 
                                        const char* ndl, apr_size_t nlen, 
                                        const apreq_match_t type)
{
    apr_size_t len = hlen;
    const char *end = hay + hlen;
    const char *begin = hay;

    while ( (hay = memchr(hay, ndl[0], len)) ) {
	len = end - hay;

	/* done if matches up to capacity of buffer */
	if ( memcmp(hay, ndl, MIN(nlen, len)) == 0 ) {
            if (type == APREQ_MATCH_FULL && len < nlen)
                hay = NULL;     /* insufficient room for match */
	    break;
        }
        --len;
        ++hay;
    }

    return hay ? hay - begin : -1;
}


static const char c2x_table[] = "0123456789ABCDEF";
static APR_INLINE unsigned char hex2_to_char(const char *what)
{
    register unsigned char digit;

#if !APR_CHARSET_EBCDIC
    digit  = (what[0] >= 'A' ? ((what[0] & 0xdf) - 'A') + 10 : (what[0] - '0'));
    digit *= 16;
    digit += (what[1] >= 'A' ? ((what[1] & 0xdf) - 'A') + 10 : (what[1] - '0'));
#else /*APR_CHARSET_EBCDIC*/
    char xstr[5];
    xstr[0]='0';
    xstr[1]='x';
    xstr[2]=what[0];
    xstr[3]=what[1];
    xstr[4]='\0';
    digit = apr_xlate_conv_byte(ap_hdrs_from_ascii, 0xFF & strtol(xstr, NULL, 16));
#endif /*APR_CHARSET_EBCDIC*/
    return (digit);
}


/* Unicode notes: "bmp" refers to the 16-bit 
 * Unicode Basic Multilingual Plane. Here we're 
 * restricting our unicode internals to 16-bit 
 * codepoints, to keep the code as simple as possible.
 * This should be sufficient for apreq itself, since
 * we really only need to validate RFC3986-encoded utf8.
 */

/* Converts Windows cp1252 to Unicode. */

static APR_INLINE
apr_uint16_t cp1252_to_bmp(unsigned char c)
{
    /* We only need to deal with iso-8859-1 control chars
     * in the 0x80 - 0x9F range.
     */
    if ((c & 0xE0) != 0x80)
        return c;

    switch (c) {
    case 0x80: return 0x20AC;
    case 0x82: return 0x201A;
    case 0x83: return 0x192;
    case 0x84: return 0x201E;
    case 0x85: return 0x2026;
    case 0x86: return 0x2020;
    case 0x87: return 0x2021;
    case 0x88: return 0x2C6;
    case 0x89: return 0x2030;
    case 0x8A: return 0x160;
    case 0x8B: return 0x2039;
    case 0x8C: return 0x152;
    case 0x8E: return 0x17D;
    case 0x91: return 0x2018;
    case 0x92: return 0x2019;
    case 0x93: return 0x201C;
    case 0x94: return 0x201D;
    case 0x95: return 0x2022;
    case 0x96: return 0x2013;
    case 0x97: return 0x2014;
    case 0x98: return 0x2DC;
    case 0x99: return 0x2122;
    case 0x9A: return 0x161;
    case 0x9B: return 0x203A;
    case 0x9C: return 0x153;
    case 0x9E: return 0x17E;
    case 0x9F: return 0x178;
    }
    return c;
}

/* converts cp1252 to utf8 */
APREQ_DECLARE(apr_size_t) apreq_cp1252_to_utf8(char *dest,
                                               const char *src, apr_size_t slen)
{
    const unsigned char *s = (unsigned const char *)src;
    const unsigned char *end = s + slen;
    unsigned char *d = (unsigned char *)dest;
    apr_uint16_t c;

    while (s < end) {
        c = cp1252_to_bmp(*s++);
        
        if (c < 0x80) {
            *d++ = c;
        }
        else if (c < 0x800) {
            *d++ = 0xC0 | (c >> 6);
            *d++ = 0x80 | (c & 0x3F);
        }
        else {
            *d++ = 0xE0 | (c >> 12);
            *d++ = 0x80 | ((c >> 6) & 0x3F);
            *d++ = 0x80 | (c & 0x3F);
        }
    }
    *d = 0;
    return d - (unsigned char *)dest;
}


/**
 * Valid utf8 bit patterns:
 *
 * 0xxxxxxx
 * 110xxxxx 10xxxxxx 
 * 1110xxxx 10xxxxxx 10xxxxxx
 * 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx
 * 111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
 * 1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
 */

static APR_INLINE unsigned is_89AB(const char c)
{

    switch(c) {
    case '8':
    case '9':
    case 'A':
    case 'B':
    case 'a':
    case 'b':
        return 1;
    }
    return 0;
}

static APR_INLINE unsigned is_enc8(const char *word, unsigned char wlen)
{

    while (wlen-- > 0) {
        if (word[0] == '%' && is_89AB(word[1]) && apr_isxdigit(word[2]))
            word += 3;
        else
            return 0;
    }
    return 1;
}

static APR_INLINE apreq_charset_t fragment_charset(const char *word,
                                                   const char *end)
{
    unsigned char flen = end - word;
    unsigned char wlen = flen / 3;
    if (!is_enc8(word, wlen))
        return APREQ_CHARSET_LATIN1;

    switch (flen % 3) {
    case 2:
        if (!is_89AB(*--end))
            return APREQ_CHARSET_LATIN1;
    case 1:
        if (*--end != '%')
            return APREQ_CHARSET_LATIN1;
    }
    return APREQ_CHARSET_UTF8;
}



static APR_INLINE apr_uint16_t hex4_to_bmp(const char *what) {
    register apr_uint16_t digit = 0;

#if !APR_CHARSET_EBCDIC
    digit  = (what[0] >= 'A' ? ((what[0] & 0xDF)-'A') + 10 : (what[0]-'0'));
    digit *= 16;
    digit += (what[1] >= 'A' ? ((what[1] & 0xDF)-'A') + 10 : (what[1]-'0'));
    digit *= 16;
    digit += (what[2] >= 'A' ? ((what[2] & 0xDF)-'A') + 10 : (what[2]-'0'));
    digit *= 16;
    digit += (what[3] >= 'A' ? ((what[3] & 0xDF)-'A') + 10 : (what[3]-'0'));

#else /*APR_CHARSET_EBCDIC*/
    char xstr[7];
    xstr[0]='0';
    xstr[1]='x';
    xstr[2]=what[0];
    xstr[3]=what[1];
    xstr[4]=what[2];
    xstr[5]=what[3];
    xstr[6]='\0';
    digit = apr_xlate_conv_byte(ap_hdrs_from_ascii, 0xFFFF & strtol(xstr, NULL, 16));
#endif /*APR_CHARSET_EBCDIC*/
    return (digit);
}


/*
 * Charset divination heuristics:
 * 1) presume ascii; if not, then
 * 2) presume utf8; if not, then
 * 3) presume latin1; unless there are control chars, in which case
 * 4) punt to cp1252.
 *
 * Note: in downgrading from 2 to 3, we should to be careful
 * about earlier control characters presumed to be valid utf8.
 * However, we aren't being that careful with the current implementation.
 */


static apr_status_t url_decode(char *dest, apr_size_t *dlen,
                               apreq_charset_t *charset,
                               const char *src, apr_size_t *slen)
{
    register const char *s = src;
    unsigned char *start = (unsigned char *)dest;
    register unsigned char *d = (unsigned char *)dest;
    const char *end = src + *slen;

    for (; s < end; ++d, ++s) {
        switch (*s) {

        case '+':
            *d = ' ';
            break;

        case '%':
	    if (s + 2 < end && apr_isxdigit(s[1]) && apr_isxdigit(s[2]))
            {
                unsigned char c;
		c = hex2_to_char(s + 1);
                s += 2;
                if (c < 0x80 || *charset == APREQ_CHARSET_CP1252)
                {
                    *d = c;
                }
                else if (c < 0xA0) {
                    /* these are ctrl chars in latin1 */
                    *charset = APREQ_CHARSET_CP1252;
                    *d = c;
                }
                else if (c < 0xC0) {
                    *charset = APREQ_CHARSET_LATIN1;
                    *d = c;
                }
                else if (*charset == APREQ_CHARSET_LATIN1) {
                    *d = c;
                }

                /* utf8 cases */

                else if (c < 0xE0) {
                    /* 2-byte utf8 */
                    if (s + 3 >= end) {
                        *charset = fragment_charset(s+1, end);
                        if (*charset == APREQ_CHARSET_UTF8) {
                            s -= 2;
                            *dlen = d - start;
                            *slen = s - src;
                            memmove(d, s, end - s);
                            d[end - s] = 0;
                            return APR_INCOMPLETE;
                        }
                        *d = c;
                    }
                    else if (is_enc8(s+1, 1)) {
                        *charset = APREQ_CHARSET_UTF8;
                        *d++ = c;
                        *d   = hex2_to_char(s+2);
                        s += 3;
                    }
                    else {
                        *charset = APREQ_CHARSET_LATIN1;
                        *d = c;
                    }
                }
                else if (c < 0xF0) {
                    /* 3-byte utf8 */
                    if (s + 6 >= end) {
                        *charset = fragment_charset(s+1, end);
                        if (*charset == APREQ_CHARSET_UTF8) {
                            s -= 2;
                            *dlen = d - start;
                            *slen = s - src;
                            memmove(d, s, end - s);
                            d[end - s] = 0;
                            return APR_INCOMPLETE;
                        }
                        *d = c;
                    }
                    else if (is_enc8(s+1, 2)) {
                        *charset = APREQ_CHARSET_UTF8;
                        *d++ = c;
                        *d++ = hex2_to_char(s+2);
                        *d   = hex2_to_char(s+5);
                        s += 6;
                    }
                    else {
                        *charset = APREQ_CHARSET_LATIN1;
                        *d = c;
                    }

                }
                else if (c < 0xF8) {
                    /* 4-byte utf8 */
                    if (s + 9 >= end) {
                        *charset = fragment_charset(s+1, end);
                        if (*charset == APREQ_CHARSET_UTF8) {
                            s -= 2;
                            *dlen = d - start;
                            *slen = s - src;
                            memmove(d, s, end - s);
                            d[end - s] = 0;
                            return APR_INCOMPLETE;
                        }
                        *d = c;
                    }
                    else if (is_enc8(s+1, 3)) {
                        *charset = APREQ_CHARSET_UTF8;
                        *d++ = c;
                        *d++ = hex2_to_char(s+2);
                        *d++ = hex2_to_char(s+5);
                        *d   = hex2_to_char(s+8);
                        s += 9;
                    }
                    else {
                        *charset = APREQ_CHARSET_LATIN1;
                        *d = c;
                    }

                }
                else if (c < 0xFC) {
                    /* 5-byte utf8 */
                    if (s + 12 >= end) {
                        *charset = fragment_charset(s+1, end);
                         if (*charset == APREQ_CHARSET_UTF8) {
                             s -= 2;
                             *dlen = d - start;
                             *slen = s - src;
                             memmove(d, s, end - s);
                             d[end - s] = 0;
                             return APR_INCOMPLETE;
                         }
                         *d = c;
                    }
                    else if (is_enc8(s+1, 4)) {
                        *charset = APREQ_CHARSET_UTF8;
                        *d++ = c;
                        *d++ = hex2_to_char(s+2);
                        *d++ = hex2_to_char(s+5);
                        *d++ = hex2_to_char(s+8);
                        *d   = hex2_to_char(s+11);
                        s += 12;
                    }
                    else {
                        *charset = APREQ_CHARSET_LATIN1;
                        *d = c;
                    }

                }
                else if (c < 0xFE) {
                    /* 6-byte utf8 */
                    if (s + 15 >= end) {
                        *charset = fragment_charset(s+1, end);
                        if (*charset == APREQ_CHARSET_UTF8) {
                            s -= 2;
                            *dlen = d - start;
                            *slen = s - src;
                            memmove(d, s, end - s);
                            d[end - s] = 0;
                            return APR_INCOMPLETE;
                        }
                        *d = c;
                    }
                    else if (is_enc8(s+1, 5)) {
                        *charset = APREQ_CHARSET_UTF8;
                        *d++ = c;
                        *d++ = hex2_to_char(s+2);
                        *d++ = hex2_to_char(s+5);
                        *d++ = hex2_to_char(s+8);
                        *d++ = hex2_to_char(s+11);
                        *d   = hex2_to_char(s+14);
                        s += 15;
                    }
                    else {
                        *charset = APREQ_CHARSET_LATIN1;
                        *d = c;
                    }
                }
                else {
                    /* (skipped) utf8 byte-order mark */
                    *charset = APREQ_CHARSET_UTF8;
                }
	    }
            else if (s + 5 < end && (s[1] == 'u' || s[1] == 'U') &&
                     apr_isxdigit(s[2]) && apr_isxdigit(s[3]) && 
                     apr_isxdigit(s[4]) && apr_isxdigit(s[5]))
            {
                apr_uint16_t c = hex4_to_bmp(s+2);

                switch (*charset) {
                case APREQ_CHARSET_ASCII:
                    *charset = APREQ_CHARSET_UTF8;
                case APREQ_CHARSET_UTF8:
                    break;

                default:
                    *dlen = d - start;
                    *slen = s - src;
                    *d = 0;
                    return APREQ_ERROR_BADSEQ;
                }


                if (c < 0x80) {
                    *d = c;
                }
                else if (c < 0x800) {
                    *d++ = 0xC0 | (c >> 6);
                    *d   = 0x80 | (c & 0x3F);
                }
                else {
                    *d++ = 0xE0 | (c >> 12);
                    *d++ = 0x80 | ((c >> 6) & 0x3F);
                    *d   = 0x80 | (c & 0x3F);
                }
                s += 5;
            }
	    else {
                *dlen = d - start;
                *slen = s - src;
                if (s + 5 < end 
                    || (s + 2 < end && !apr_isxdigit(s[2]))
                    || (s + 1 < end && !apr_isxdigit(s[1])
                        && s[1] != 'u' && s[1] != 'U'))
                {
                    *d = 0;
                    return APREQ_ERROR_BADSEQ;
                }

                memmove(d, s, end - s);
                d[end - s] = 0;
                return APR_INCOMPLETE;
	    }
            break;

        default:
            if (s > 0) {
                *d = *s;
            }
            else {
                *d = 0;
                *dlen = d - start;
                *slen = s - src;
                return APREQ_ERROR_BADCHAR;
            }
        }
    }

    *d = 0;
    *dlen = d - start;
    *slen = s - src;
    return APR_SUCCESS;
}


APREQ_DECLARE(apr_status_t) apreq_decode(char *d, apr_size_t *dlen,
                                         const char *s, apr_size_t slen)
{
    apr_size_t len = 0;
    const char *end = s + slen;
    apr_status_t rv;
    apreq_charset_t c = APREQ_CHARSET_ASCII;

    if (s == (const char *)d) {     /* optimize for src = dest case */
        for ( ; d < end; ++d) {
            if (*d == '%' || *d == '+')
                break;
            else if (*d == 0) {
                *dlen = (const char *)d - s;
                return APREQ_ERROR_BADCHAR;
            }
        }
        len = (const char *)d - s;
        s = (const char *)d;
        slen -= len;
    }

    rv = url_decode(d, dlen, &c, s, &slen);
    *dlen += len;

    return rv + c;
}

APREQ_DECLARE(apr_status_t) apreq_decodev(char *d, apr_size_t *dlen,
                                          struct iovec *v, int nelts)
{
    apr_status_t status = APR_SUCCESS;
    apreq_charset_t c = APREQ_CHARSET_ASCII;
    int n = 0;

    *dlen = 0;

    while (n < nelts) {
        apr_size_t slen, len;

        slen = v[n].iov_len;
        switch (status = url_decode(d,&len, &c, v[n].iov_base, &slen)) {

        case APR_SUCCESS:
            d += len;
            *dlen += len;
            ++n;
            continue;

        case APR_INCOMPLETE:
            d += len;
            *dlen += len;

            if (++n == nelts)
                return APR_INCOMPLETE + c;

            len = v[n-1].iov_len - slen;
            memcpy(d + len, v[n].iov_base, v[n].iov_len);
            v[n].iov_len += len;
            v[n].iov_base = d;
            continue;

        default:
            *dlen += len;
            return status;
        }
    }
    return APR_SUCCESS + c;
}


APREQ_DECLARE(apr_size_t) apreq_encode(char *dest, const char *src, 
                                       const apr_size_t slen) 
{
    char *d = dest;
    const unsigned char *s = (const unsigned char *)src;
    unsigned c;

    for ( ; s < (const unsigned char *)src + slen; ++s) {
        c = *s;
        if ( apr_isalnum(c) || c == '-' || c == '.' || c == '_' || c == '~' )
            *d++ = c;

        else if ( c == ' ' )
            *d++ = '+';

        else {
#if APR_CHARSET_EBCDIC
            c = apr_xlate_conv_byte(ap_hdrs_to_ascii, (unsigned char)c);
#endif
            *d++ = '%';
            *d++ = c2x_table[c >> 4];
            *d++ = c2x_table[c & 0xf];
        }
    }
    *d = 0;

    return d - dest;
}

APREQ_DECLARE(apr_size_t) apreq_quote_once(char *dest, const char *src, 
                                           const apr_size_t slen) 
{
    if (slen > 1 && src[0] == '"' && src[slen-1] == '"') {
        /* looks like src is already quoted */        
        memcpy(dest, src, slen);
        return slen;
    }
    else
        return apreq_quote(dest, src, slen);
}

APREQ_DECLARE(apr_size_t) apreq_quote(char *dest, const char *src, 
                                      const apr_size_t slen) 
{
    char *d = dest;
    const char *s = src;
    const char *const last = src + slen - 1;

    if (slen == 0) {
        *d = 0;
        return 0;
    }

    *d++ = '"';

    while (s <= last) {

        switch (*s) {

        case '\\': 
            if (s < last) {
                *d++ = *s++;
                break;
            }
            /* else fall through */

        case '"':
            *d++ = '\\';
        }

        *d++ = *s++;
    }

    *d++ = '"';
    *d = 0;

    return d - dest;
}

APREQ_DECLARE(char *) apreq_join(apr_pool_t *p, 
                                 const char *sep, 
                                 const apr_array_header_t *arr,
                                 apreq_join_t mode)
{
    apr_ssize_t len, slen;
    char *rv;
    const apreq_value_t **a = (const apreq_value_t **)arr->elts;
    char *d;
    const int n = arr->nelts;
    int j;

    slen = sep ? strlen(sep) : 0;

    if (n == 0)
        return apr_pstrdup(p, "");

    for (j=0, len=0; j < n; ++j)
        len += a[j]->dlen + slen + 1;

    /* Allocated the required space */

    switch (mode) {
    case APREQ_JOIN_ENCODE:
        len += 2 * len;
        break;
    case APREQ_JOIN_QUOTE:
        len = 2 * (len + n);
        break;
    default:
        /* nothing special required, just here to keep noisy compilers happy */
        break;
    }

    rv = apr_palloc(p, len);

    /* Pass two --- copy the argument strings into the result space */

    d = rv;

    switch (mode) {

    case APREQ_JOIN_ENCODE:
        d += apreq_encode(d, a[0]->data, a[0]->dlen);

        for (j = 1; j < n; ++j) {
                memcpy(d, sep, slen);
                d += slen;
                d += apreq_encode(d, a[j]->data, a[j]->dlen);
        }
        break;

    case APREQ_JOIN_DECODE:
        if (apreq_decode(d, &len, a[0]->data, a[0]->dlen))
            return NULL;
        else
            d += len;

        for (j = 1; j < n; ++j) {
            memcpy(d, sep, slen);
            d += slen;

            if (apreq_decode(d, &len, a[j]->data, a[j]->dlen))
                return NULL;
            else
                d += len;
        }
        break;


    case APREQ_JOIN_QUOTE:
        d += apreq_quote_once(d, a[0]->data, a[0]->dlen);

        for (j = 1; j < n; ++j) {
            memcpy(d, sep, slen);
            d += slen;
            d += apreq_quote_once(d, a[j]->data, a[j]->dlen);
        }
        break;


    case APREQ_JOIN_AS_IS:
        memcpy(d,a[0]->data, a[0]->dlen);
        d += a[0]->dlen;

        for (j = 1; j < n ; ++j) {
            memcpy(d, sep, slen);
            d += slen;
            memcpy(d, a[j]->data, a[j]->dlen);
            d += a[j]->dlen;
        }
        break;

    default:
        break;
    }

    *d = 0;
    return rv;
}

APR_INLINE
static apr_status_t apreq_fwritev(apr_file_t *f, struct iovec *v, 
                                  int *nelts, apr_size_t *bytes_written)
{
    apr_size_t len;
    int n;
    apr_status_t s;

    *bytes_written = 0;

    while (1) {
        /* try to write */
        s = apr_file_writev(f, v, *nelts, &len);

        *bytes_written += len;

        if (s != APR_SUCCESS)
            return s;

        /* see how far we've come */
        n = 0;
        while (n < *nelts && len >= v[n].iov_len)
            len -= v[n++].iov_len;

        if (n == *nelts) {
            /* nothing left to write, report success */
            *nelts = 0;
            return APR_SUCCESS;
        }

        /* incomplete write: must shift v */
        v[n].iov_len -= len;
        v[n].iov_base = (char *)(v[n].iov_base) + len;

        if (n > 0) {
            /* we're satisfied for now if we can remove one iovec from
               the "v" array */
            (*nelts) -= n;
            memmove(v, v + n, sizeof(*v) * *nelts);

            return APR_SUCCESS;
        }

        /* we're still in the first iovec - check for endless loop,
           and then try again */
        if (len == 0)
            return APREQ_ERROR_GENERAL;
    }
}


APREQ_DECLARE(apr_status_t) apreq_brigade_fwrite(apr_file_t *f, 
                                                 apr_off_t *wlen,
                                                 apr_bucket_brigade *bb)
{
    struct iovec v[APREQ_DEFAULT_NELTS];
    apr_status_t s;
    apr_bucket *e;
    int n = 0;
    *wlen = 0;

    for (e = APR_BRIGADE_FIRST(bb); e != APR_BRIGADE_SENTINEL(bb);
         e = APR_BUCKET_NEXT(e)) 
    {
        apr_size_t len;
        if (n == APREQ_DEFAULT_NELTS) {
            s = apreq_fwritev(f, v, &n, &len);
            if (s != APR_SUCCESS)
                return s;
            *wlen += len;
        }
        s = apr_bucket_read(e, (const char **)&(v[n].iov_base), 
                            &len, APR_BLOCK_READ);
        if (s != APR_SUCCESS)
            return s;

        v[n++].iov_len = len;
    }

    while (n > 0) {
        apr_size_t len;
        s = apreq_fwritev(f, v, &n, &len);
        if (s != APR_SUCCESS)
            return s;
        *wlen += len;
    }
    return APR_SUCCESS;
}


struct cleanup_data {
    const char *fname;
    apr_pool_t *pool;
};

static apr_status_t apreq_file_cleanup(void *d)
{
    struct cleanup_data *data = d;
    return apr_file_remove(data->fname, data->pool);
}

/*
 * The reason we need the above cleanup is because on Windows, APR_DELONCLOSE
 * forces applications to open the file with FILE_SHARED_DELETE
 * set, which is, unfortunately, a property that is preserved 
 * across NTFS "hard" links.  This breaks apps that link() the temp 
 * file to a permanent location, and subsequently expect to open it 
 * before the original tempfile is closed+deleted. In fact, even
 * Apache::Upload does this, so it is a common enough event that the
 * apreq_file_cleanup workaround is necessary.
 */

APREQ_DECLARE(apr_status_t) apreq_file_mktemp(apr_file_t **fp, 
                                              apr_pool_t *pool,
                                              const char *path)
{
    apr_status_t rc;
    char *tmpl;
    struct cleanup_data *data;

    if (path == NULL) {
        rc = apr_temp_dir_get(&path, pool);
        if (rc != APR_SUCCESS)
            return rc;
    }
    rc = apr_filepath_merge(&tmpl, path, "apreqXXXXXX",
                            APR_FILEPATH_NOTRELATIVE, pool);

    if (rc != APR_SUCCESS)
        return rc;
    
    data = apr_palloc(pool, sizeof *data);
    /* cleanups are LIFO, so this one will run just after 
       the cleanup set by mktemp */
    apr_pool_cleanup_register(pool, data, 
                              apreq_file_cleanup, apreq_file_cleanup);

    rc = apr_file_mktemp(fp, tmpl, /* NO APR_DELONCLOSE! see comment above */
                           APR_CREATE | APR_READ | APR_WRITE
                           | APR_EXCL | APR_BINARY, pool);

    if (rc == APR_SUCCESS) {
        apr_file_name_get(&data->fname, *fp);
        data->pool = pool;
    }
    else {
        apr_pool_cleanup_kill(pool, data, apreq_file_cleanup);
    }

    return rc;
}


/*
 * is_2616_token() is the verbatim definition from section 2.2
 * in the rfc itself.  We try to optimize it around the
 * expectation that the argument is not a token, which 
 * should be the typical usage.
 */

static APR_INLINE
unsigned is_2616_token(const char c) {
    switch (c) {
    case ' ': case ';': case ',': case '"': case '\t':
        /* The chars we are expecting are listed above;
           the chars below are just for completeness. */
    case '?': case '=': case '@': case ':': case '\\': case '/':
    case '(': case ')':
    case '<': case '>':
    case '{': case '}':
    case '[': case ']':
        return 0;
    default:
        if (apr_iscntrl(c))
            return 0;
    }
    return 1;
}

APREQ_DECLARE(apr_status_t)
    apreq_header_attribute(const char *hdr,
                           const char *name, const apr_size_t nlen,
                           const char **val, apr_size_t *vlen)
{
    const char *key, *v;

    /* Must ensure first char isn't '=', so we can safely backstep. */
    while (*hdr == '=')
        ++hdr;

    while ((key = strchr(hdr, '=')) != NULL) {

        v = key + 1;
        --key;

        while (apr_isspace(*key) && key > hdr + nlen)
            --key;

        key -= nlen - 1;

        while (apr_isspace(*v))
            ++v;

        if (*v == '"') {
            ++v;
            *val = v;

        look_for_end_quote:
            switch (*v) {
            case '"':
                break;
            case 0:
                return APREQ_ERROR_BADSEQ;
            case '\\':
                if (v[1] != 0)
                    ++v;
            default:
                ++v;
                goto look_for_end_quote;
            }
        }
        else {
            *val = v; 

        look_for_terminator:
            switch (*v) {
            case 0:
            case ' ':
            case ';':
            case ',':
            case '\t':
            case '\r':
            case '\n':
                break;
            default:
                ++v;
                goto look_for_terminator;
            }
        }

        if (strncasecmp(key, name, nlen) == 0) {
            *vlen = v - *val;
            if (key == hdr || ! is_2616_token(key[-1]))
                return APR_SUCCESS;
        }
        hdr = v;
    }

    return APREQ_ERROR_NOATTR;
}



#define BUCKET_IS_SPOOL(e) ((e)->type == &spool_bucket_type)
#define FILE_BUCKET_LIMIT      ((apr_size_t)-1 - 1)

static
void spool_bucket_destroy(void *data)
{
    apr_bucket_type_file.destroy(data);
}

static
apr_status_t spool_bucket_read(apr_bucket *e, const char **str,
                                   apr_size_t *len, apr_read_type_e block)
{
    return apr_bucket_type_file.read(e, str, len, block);
}

static
apr_status_t spool_bucket_setaside(apr_bucket *data, apr_pool_t *reqpool)
{
    return apr_bucket_type_file.setaside(data, reqpool);
}

static
apr_status_t spool_bucket_split(apr_bucket *a, apr_size_t point)
{
    apr_status_t rv = apr_bucket_shared_split(a, point);
    a->type = &apr_bucket_type_file;
    return rv;
}

static
apr_status_t spool_bucket_copy(apr_bucket *e, apr_bucket **c)
{
    apr_status_t rv = apr_bucket_shared_copy(e, c);
    (*c)->type = &apr_bucket_type_file;
    return rv;
}

static const apr_bucket_type_t spool_bucket_type = {
    "APREQ_SPOOL", 5, APR_BUCKET_DATA,
    spool_bucket_destroy,
    spool_bucket_read,
    spool_bucket_setaside,
    spool_bucket_split,
    spool_bucket_copy,
};

APREQ_DECLARE(apr_file_t *)apreq_brigade_spoolfile(apr_bucket_brigade *bb)
{
    apr_bucket *last;

    last = APR_BRIGADE_LAST(bb);
    if (BUCKET_IS_SPOOL(last))
        return ((apr_bucket_file *)last->data)->fd;

    return NULL;
}

APREQ_DECLARE(apr_status_t) apreq_brigade_concat(apr_pool_t *pool,
                                                 const char *temp_dir,
                                                 apr_size_t heap_limit,
                                                 apr_bucket_brigade *out, 
                                                 apr_bucket_brigade *in)
{
    apr_status_t s;
    apr_bucket_file *f;
    apr_off_t wlen;
    apr_file_t *file;
    apr_off_t in_len, out_len;
    apr_bucket *last_in, *last_out;

    last_out = APR_BRIGADE_LAST(out);

    if (APR_BUCKET_IS_EOS(last_out))
        return APR_EOF;

    s = apr_brigade_length(out, 0, &out_len);
    if (s != APR_SUCCESS)
        return s;

    /* This cast, when out_len = -1, is intentional */
    if ((apr_uint64_t)out_len < heap_limit) {

        s = apr_brigade_length(in, 0, &in_len);
        if (s != APR_SUCCESS)
            return s;

        /* This cast, when in_len = -1, is intentional */
        if ((apr_uint64_t)in_len < heap_limit - out_len) {
            APR_BRIGADE_CONCAT(out, in);
            return APR_SUCCESS;
        }
    }
    
    if (!BUCKET_IS_SPOOL(last_out)) {

        s = apreq_file_mktemp(&file, pool, temp_dir);
        if (s != APR_SUCCESS)
            return s;

        s = apreq_brigade_fwrite(file, &wlen, out);

        if (s != APR_SUCCESS)
            return s;

        last_out = apr_bucket_file_create(file, wlen, 0, 
                                          out->p, out->bucket_alloc);
        last_out->type = &spool_bucket_type;
        APR_BRIGADE_INSERT_TAIL(out, last_out);
        f = last_out->data;
    }
    else {
        f = last_out->data;
        /* Need to seek here, just in case our spool bucket 
         * was read from between apreq_brigade_concat calls. 
         */
        wlen = last_out->start + last_out->length;
        s = apr_file_seek(f->fd, APR_SET, &wlen);
        if (s != APR_SUCCESS)
            return s;
    }

    if (in == out)
        return APR_SUCCESS;

    last_in = APR_BRIGADE_LAST(in);

    if (APR_BUCKET_IS_EOS(last_in))
        APR_BUCKET_REMOVE(last_in);

    s = apreq_brigade_fwrite(f->fd, &wlen, in);

    if (s == APR_SUCCESS) {

        /* We have to deal with the possibility that the new 
         * data may be too large to be represented by a single
         * temp_file bucket.
         */

        while ((apr_uint64_t)wlen > FILE_BUCKET_LIMIT - last_out->length) {
            apr_bucket *e;

            apr_bucket_copy(last_out, &e);
            e->length = 0;
            e->start = last_out->start + FILE_BUCKET_LIMIT;
            wlen -= FILE_BUCKET_LIMIT - last_out->length;
            last_out->length = FILE_BUCKET_LIMIT;
            last_out->type = &apr_bucket_type_file;

            APR_BRIGADE_INSERT_TAIL(out, e);
            last_out = e;
        }

        last_out->length += wlen;

        if (APR_BUCKET_IS_EOS(last_in))
            APR_BRIGADE_INSERT_TAIL(out, last_in);

    }
    else if (APR_BUCKET_IS_EOS(last_in))
        APR_BRIGADE_INSERT_TAIL(in, last_in);

    apr_brigade_cleanup(in);
    return s;
}

