/* 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 "mod_ftp.h"
#include "ftp_internal.h"

/* In httpd 2.4, we want to log by module */
#if AP_MODULE_MAGIC_AT_LEAST(20111130,0)
APLOG_USE_MODULE(ftp);
#endif

#ifndef apr_time_from_sec
#define apr_time_from_sec(sec) ((apr_time_t)(sec) * APR_USEC_PER_SEC)
#endif

/*
 * ftp_process_request: Called after the request is read.  This function
 *                      will process the request, and call the correct
 *                      command handler, send the response and log the
 *                      transaction.
 *
 * Arguments: r - The request to be processed.
 *            fc - The ftp connection record associated with this request.
 *
 * Returns: Nothing.
 */
void ftp_process_request(request_rec *r)
{
    ftp_connection *fc = ftp_get_module_config(r->connection->conn_config);
    ftp_server_config *fsc = ftp_get_module_config(r->server->module_config);
    int res;

    fc->traffic += r->read_length;
    fc->response_notes = "";

    apr_table_setn(r->subprocess_env, "ftp_transfer_ok", "1");
    res = ftp_run_cmd(r, r->method);

    /* If the passive connection has been open too long, close it */
    if ((fc->passive_created != -1) && fc->csock
        && (res != FTP_REPLY_DATA_CLOSE)
        && (res != FTP_REPLY_CONTROL_CLOSE)
        && (apr_time_now() - fc->passive_created
            > apr_time_from_sec(fsc->timeout_data))) {
        ap_log_error(APLOG_MARK, APLOG_WARNING, 0, r->server,
          "Timeout waiting to use passive port (closing data connection).");
        ftp_reset_dataconn(fc);
    }

    ftp_send_response(r, res);

    ap_run_log_transaction(r);
}

apr_status_t ftp_protocol_filter(ap_filter_t *f, apr_bucket_brigade *b,
                                ap_input_mode_t mode, apr_read_type_e block,
                                              apr_off_t readbytes)
{
    apr_bucket *eos;

    eos = apr_bucket_eos_create(b->bucket_alloc);
    APR_BRIGADE_INSERT_HEAD(b, eos);

    return APR_SUCCESS;
}
