// Copyright 2019 The Chromium OS Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "cups_proxy/mhd_util.h"

#include <microhttpd.h>

#include "cups_proxy/mhd_http_request.h"

#include <base/check.h>

namespace cups_proxy {

namespace {

// Adds a HTTP header to the MHDHttpRequest.
//
// This is called for each header of the request.
// |cls| is the MHDHttpRequest argument passed from MHD_get_connection_values.
int AddHeader(void* cls,
              enum MHD_ValueKind kind,
              const char* key,
              const char* value) {
  DCHECK(kind == MHD_HEADER_KIND);
  auto* request = static_cast<MHDHttpRequest*>(cls);
  request->AddHeader(key, value);
  return MHD_YES;
}

// Handles incoming HTTP request.
//
// This function would be called multiple times by MHD with the same |con_cls|
// for a single HTTP request.
//
// For a POST request, the first call would have |con_cls| storing NULL, |url|,
// |method|, |version| from the HTTP header, and empty |upload_data|.
// Then POST data would be incrementally available by calling this function
// multiple times (with data in |upload_data| and a non-zero
// |*upload_data_size|).
// A final call with |*upload_data_size| zero indicates the end of the request.
int AccessHandler(void* cls,
                  struct MHD_Connection* connection,
                  const char* url,
                  const char* method,
                  const char* version,
                  const char* upload_data,
                  size_t* upload_data_size,
                  void** con_cls) {
  auto* request = static_cast<MHDHttpRequest*>(*con_cls);
  if (request == nullptr) {
    request = new MHDHttpRequest();
    request->SetStatusLine(method, url, version);
    MHD_get_connection_values(connection, MHD_HEADER_KIND, &AddHeader, request);
    *con_cls = request;
    return MHD_YES;
  }

  if (*upload_data_size != 0) {
    request->PushToBody(base::StringPiece(upload_data, *upload_data_size));
    *upload_data_size = 0;
    return MHD_YES;
  }

  request->Finalize();
  auto* mojo_handler = static_cast<MojoHandler*>(cls);
  IppResponse response = mojo_handler->ProxyRequestSync(*request);

  ScopedMHDResponse mhd_resp(MHD_create_response_from_buffer(
      response.body.size(), response.body.data(), MHD_RESPMEM_MUST_COPY));
  if (!mhd_resp) {
    return MHD_NO;
  }

  for (auto& header : response.headers) {
    int ret = MHD_add_response_header(mhd_resp.get(), header->key.c_str(),
                                      header->value.c_str());
    if (ret != MHD_YES) {
      return ret;
    }
  }

  int ret =
      MHD_queue_response(connection, response.http_status_code, mhd_resp.get());
  return ret;
}

// Cleanup the allocated MHDHttpRequest object.
//
// This function is called when the HTTP request is completed.
void CleanupRequest(void* cls,
                    struct MHD_Connection* connection,
                    void** con_cls,
                    enum MHD_RequestTerminationCode toe) {
  auto* request = static_cast<MHDHttpRequest*>(*con_cls);
  delete request;
}

}  // namespace

ScopedMHDDaemon StartMHDDaemon(base::ScopedFD fd, MojoHandler* mojo_handler) {
  const struct MHD_OptionItem kOps[] = {
      {MHD_OPTION_LISTEN_SOCKET, fd.release(), NULL},
      {MHD_OPTION_NOTIFY_COMPLETED, reinterpret_cast<intptr_t>(&CleanupRequest),
       NULL},
      {MHD_OPTION_END, 0, NULL}  // MUST stay last option
  };

  return ScopedMHDDaemon(
      MHD_start_daemon(MHD_USE_SELECT_INTERNALLY, 0, NULL, NULL, &AccessHandler,
                       mojo_handler, MHD_OPTION_ARRAY, kOps, MHD_OPTION_END));
}

}  // namespace cups_proxy
