/*
**  Licensed to the Apache Software Foundation (ASF) under one or more
** contributor license agreements.  See the NOTICE file distributed with
** this work for additional information regarding copyright ownership.
** The ASF licenses this file to You 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 "httpd.h"
#include "http_config.h"
#include "http_log.h"
#include "util_filter.h"
#include "apr_tables.h"
#include "apr_buckets.h"
#include "http_request.h"
#include "apr_strings.h"

#include "apreq_module_apache2.h"
#include "apreq_private_apache2.h"
#include "apreq_error.h"


APR_INLINE
static ap_filter_t *get_apreq_filter(apreq_handle_t *handle)
{
    struct apache2_handle *req = (struct apache2_handle *)handle;

    if (req->f == NULL) {
        req->f = ap_add_input_filter(APREQ_FILTER_NAME, NULL,
                                     req->r,
                                     req->r->connection);
        /* ap_add_input_filter does not guarantee cfg->f == r->input_filters,
         * so we reposition the new filter there as necessary.
         */
        apreq_filter_relocate(req->f);
    }

    return req->f;
}


static apr_status_t apache2_jar(apreq_handle_t *handle, const apr_table_t **t)
{
    struct apache2_handle *req = (struct apache2_handle*)handle;
    request_rec *r = req->r;

    if (req->jar_status == APR_EINIT) {
        const char *cookies = apr_table_get(r->headers_in, "Cookie");
        if (cookies != NULL) {
            req->jar = apr_table_make(handle->pool, APREQ_DEFAULT_NELTS);
            req->jar_status =
                apreq_parse_cookie_header(handle->pool, req->jar, cookies);
        }
        else
            req->jar_status = APREQ_ERROR_NODATA;
    }

    *t = req->jar;
    return req->jar_status;
}

static apr_status_t apache2_args(apreq_handle_t *handle, const apr_table_t **t)
{
    struct apache2_handle *req = (struct apache2_handle*)handle;
    request_rec *r = req->r;

    if (req->args_status == APR_EINIT) {
        if (r->args != NULL) {
            req->args = apr_table_make(handle->pool, APREQ_DEFAULT_NELTS);
            req->args_status =
                apreq_parse_query_string(handle->pool, req->args, r->args);
        }
        else
            req->args_status = APREQ_ERROR_NODATA;
    }

    *t = req->args;
    return req->args_status;
}




static apreq_cookie_t *apache2_jar_get(apreq_handle_t *handle, const char *name)
{
    struct apache2_handle *req = (struct apache2_handle *)handle;
    const apr_table_t *t;
    const char *val;

    if (req->jar_status == APR_EINIT)
        apache2_jar(handle, &t);
    else
        t = req->jar;

    if (t == NULL)
        return NULL;

    val = apr_table_get(t, name);
    if (val == NULL)
        return NULL;

    return apreq_value_to_cookie(val);
}

static apreq_param_t *apache2_args_get(apreq_handle_t *handle, const char *name)
{
    struct apache2_handle *req = (struct apache2_handle *)handle;
    const apr_table_t *t;
    const char *val;

    if (req->args_status == APR_EINIT)
        apache2_args(handle, &t);
    else
        t = req->args;

    if (t == NULL)
        return NULL;

    val = apr_table_get(t, name);
    if (val == NULL)
        return NULL;

    return apreq_value_to_param(val);
}


static apr_status_t apache2_body(apreq_handle_t *handle, const apr_table_t **t)
{
    ap_filter_t *f = get_apreq_filter(handle);
    struct filter_ctx *ctx;

    if (f->ctx == NULL)
        apreq_filter_make_context(f);

    ctx = f->ctx;

    switch (ctx->body_status) {

    case APR_EINIT:
        apreq_filter_init_context(f);
        if (ctx->body_status != APR_INCOMPLETE)
            break;

    case APR_INCOMPLETE:
        while (apreq_filter_prefetch(f, APREQ_DEFAULT_READ_BLOCK_SIZE) == APR_INCOMPLETE)
            ;   /*loop*/
    }

    *t = ctx->body;
    return ctx->body_status;
}

static apreq_param_t *apache2_body_get(apreq_handle_t *handle, const char *name)
{
    ap_filter_t *f = get_apreq_filter(handle);
    struct filter_ctx *ctx;
    const char *val;
    apreq_hook_t *h;
    apreq_hook_find_param_ctx_t *hook_ctx;

    if (f->ctx == NULL)
        apreq_filter_make_context(f);

    ctx = f->ctx;

    switch (ctx->body_status) {

    case APR_SUCCESS:

        val = apr_table_get(ctx->body, name);
        if (val != NULL)
            return apreq_value_to_param(val);
        return NULL;


    case APR_EINIT:

        apreq_filter_init_context(f);
        if (ctx->body_status != APR_INCOMPLETE)
            return NULL;
        apreq_filter_prefetch(f, APREQ_DEFAULT_READ_BLOCK_SIZE);


    case APR_INCOMPLETE:

        val = apr_table_get(ctx->body, name);
        if (val != NULL)
            return apreq_value_to_param(val);

        /* Not seen yet, so we need to scan for
           param while prefetching the body */
        hook_ctx = apr_palloc(handle->pool, sizeof *hook_ctx);

        if (ctx->find_param == NULL)
            ctx->find_param = apreq_hook_make(handle->pool,
                                              apreq_hook_find_param,
                                              NULL, NULL);
        h = ctx->find_param;
        h->next = ctx->parser->hook;
        h->ctx = hook_ctx;
        ctx->parser->hook = h;
        hook_ctx->name = name;
        hook_ctx->param = NULL;
        hook_ctx->prev = ctx->parser->hook;

        do {
            apreq_filter_prefetch(f, APREQ_DEFAULT_READ_BLOCK_SIZE);
            if (hook_ctx->param != NULL)
                return hook_ctx->param;
        } while (ctx->body_status == APR_INCOMPLETE);

        ctx->parser->hook = h->next;
        return NULL;


    default:

        if (ctx->body == NULL)
            return NULL;

        val = apr_table_get(ctx->body, name);
        if (val != NULL)
            return apreq_value_to_param(val);
        return NULL;

    }

    /* not reached */
    return NULL;
}

static
apr_status_t apache2_parser_get(apreq_handle_t *handle,
                                  const apreq_parser_t **parser)
{
    ap_filter_t *f = get_apreq_filter(handle);
    struct filter_ctx *ctx = f->ctx;

    if (ctx == NULL) {
        *parser = NULL;
        return APR_EINIT;
    }
    *parser = ctx->parser;
    return APR_SUCCESS;
}

static
apr_status_t apache2_parser_set(apreq_handle_t *handle,
                                apreq_parser_t *parser)
{
    ap_filter_t *f = get_apreq_filter(handle);
    struct filter_ctx *ctx;

    if (f->ctx == NULL)
        apreq_filter_make_context(f);

    ctx = f->ctx;

    if (ctx->parser == NULL) {
        ctx->parser = parser;
        return APR_SUCCESS;
    }
    else
        return APREQ_ERROR_NOTEMPTY;
}



static
apr_status_t apache2_hook_add(apreq_handle_t *handle,
                              apreq_hook_t *hook)
{
    ap_filter_t *f = get_apreq_filter(handle);
    struct filter_ctx *ctx;

    if (f->ctx == NULL)
        apreq_filter_make_context(f);

    ctx = f->ctx;

    if (ctx->parser != NULL) {
        return apreq_parser_add_hook(ctx->parser, hook);
    }
    else if (ctx->hook_queue != NULL) {
        apreq_hook_t *h = ctx->hook_queue;
        while (h->next != NULL)
            h = h->next;
        h->next = hook;
    }
    else {
        ctx->hook_queue = hook;
    }
    return APR_SUCCESS;

}

static
apr_status_t apache2_brigade_limit_set(apreq_handle_t *handle,
                                       apr_size_t bytes)
{
    ap_filter_t *f = get_apreq_filter(handle);
    struct filter_ctx *ctx;

    if (f->ctx == NULL)
        apreq_filter_make_context(f);

    ctx = f->ctx;

    if (ctx->body_status == APR_EINIT || ctx->brigade_limit > bytes) {
        ctx->brigade_limit = bytes;
        return APR_SUCCESS;
    }

    return APREQ_ERROR_MISMATCH;
}

static
apr_status_t apache2_brigade_limit_get(apreq_handle_t *handle,
                                       apr_size_t *bytes)
{
    ap_filter_t *f = get_apreq_filter(handle);
    struct filter_ctx *ctx;

    if (f->ctx == NULL)
        apreq_filter_make_context(f);

    ctx = f->ctx;
    *bytes = ctx->brigade_limit;
    return APR_SUCCESS;
}

static
apr_status_t apache2_read_limit_set(apreq_handle_t *handle,
                                    apr_uint64_t bytes)
{
    ap_filter_t *f = get_apreq_filter(handle);
    struct filter_ctx *ctx;

    if (f->ctx == NULL)
        apreq_filter_make_context(f);

    ctx = f->ctx;

    if (ctx->read_limit > bytes && ctx->bytes_read < bytes) {
        ctx->read_limit = bytes;
        return APR_SUCCESS;
    }

    return APREQ_ERROR_MISMATCH;
}

static
apr_status_t apache2_read_limit_get(apreq_handle_t *handle,
                                    apr_uint64_t *bytes)
{
    ap_filter_t *f = get_apreq_filter(handle);
    struct filter_ctx *ctx;

    if (f->ctx == NULL)
        apreq_filter_make_context(f);

    ctx = f->ctx;
    *bytes = ctx->read_limit;
    return APR_SUCCESS;
}

static
apr_status_t apache2_temp_dir_set(apreq_handle_t *handle,
                                  const char *path)
{
    ap_filter_t *f = get_apreq_filter(handle);
    struct filter_ctx *ctx;

    if (f->ctx == NULL)
        apreq_filter_make_context(f);

    ctx = f->ctx;
    /* init vs incomplete state? */
    if (ctx->temp_dir == NULL && ctx->bytes_read == 0) {
        if (path != NULL)
            ctx->temp_dir = apr_pstrdup(handle->pool, path);
        return APR_SUCCESS;
    }

    return APREQ_ERROR_NOTEMPTY;
}

static
apr_status_t apache2_temp_dir_get(apreq_handle_t *handle,
                                  const char **path)
{
    ap_filter_t *f = get_apreq_filter(handle);
    struct filter_ctx *ctx;

    if (f->ctx == NULL)
        apreq_filter_make_context(f);

    ctx = f->ctx;
    *path = ctx->parser ? ctx->parser->temp_dir : ctx->temp_dir;
    return APR_SUCCESS;
}

static APREQ_MODULE(apache2, APREQ_APACHE2_MMN);

APREQ_DECLARE(apreq_handle_t *) apreq_handle_apache2(request_rec *r)
{
    struct apache2_handle *req =
        ap_get_module_config(r->request_config, &apreq_module);

    if (req != NULL) {
        get_apreq_filter(&req->handle);
        return &req->handle;
    }

    req = apr_palloc(r->pool, sizeof *req);
    ap_set_module_config(r->request_config, &apreq_module, req);

    req->handle.module = &apache2_module;
    req->handle.pool = r->pool;
    req->handle.bucket_alloc = r->connection->bucket_alloc;
    req->r = r;

    req->args_status = req->jar_status = APR_EINIT;
    req->args = req->jar = NULL;

    req->f = NULL;

    get_apreq_filter(&req->handle);
    return &req->handle;

}
