// Copyright 2016 The Chromium 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 <components/os_crypt/kwallet_dbus.h>

#include <algorithm>
#include <memory>

#include "base/logging.h"
#include "dbus/bus.h"
#include "dbus/message.h"
#include "dbus/object_proxy.h"

namespace {

// DBus service, path, and interface names for klauncher and kwalletd.
const char kKWalletDName[] = "kwalletd";
const char kKWalletD5Name[] = "kwalletd5";
const char kKWalletServiceName[] = "org.kde.kwalletd";
const char kKWallet5ServiceName[] = "org.kde.kwalletd5";
const char kKWalletPath[] = "/modules/kwalletd";
const char kKWallet5Path[] = "/modules/kwalletd5";
const char kKWalletInterface[] = "org.kde.KWallet";
const char kKLauncherServiceName[] = "org.kde.klauncher";
const char kKLauncherPath[] = "/KLauncher";
const char kKLauncherInterface[] = "org.kde.KLauncher";

}  // namespace

KWalletDBus::KWalletDBus(base::nix::DesktopEnvironment desktop_env)
    : session_bus_(nullptr), kwallet_proxy_(nullptr) {
  if (desktop_env == base::nix::DESKTOP_ENVIRONMENT_KDE5) {
    dbus_service_name_ = kKWallet5ServiceName;
    dbus_path_ = kKWallet5Path;
    kwalletd_name_ = kKWalletD5Name;
  } else {
    dbus_service_name_ = kKWalletServiceName;
    dbus_path_ = kKWalletPath;
    kwalletd_name_ = kKWalletDName;
  }
}

KWalletDBus::~KWalletDBus() = default;

dbus::Bus* KWalletDBus::GetSessionBus() {
  return session_bus_.get();
}

void KWalletDBus::SetSessionBus(scoped_refptr<dbus::Bus> session_bus) {
  session_bus_ = session_bus;
  kwallet_proxy_ = session_bus_->GetObjectProxy(dbus_service_name_,
                                                dbus::ObjectPath(dbus_path_));
}

bool KWalletDBus::StartKWalletd() {
  dbus::ObjectProxy* klauncher = session_bus_->GetObjectProxy(
      kKLauncherServiceName, dbus::ObjectPath(kKLauncherPath));

  dbus::MethodCall method_call(kKLauncherInterface,
                               "start_service_by_desktop_name");
  dbus::MessageWriter builder(&method_call);
  std::vector<std::string> empty;
  builder.AppendString(kwalletd_name_);  // serviceName
  builder.AppendArrayOfStrings(empty);   // urls
  builder.AppendArrayOfStrings(empty);   // envs
  builder.AppendString(std::string());   // startup_id
  builder.AppendBool(false);             // blind
  std::unique_ptr<dbus::Response> response(klauncher->CallMethodAndBlock(
      &method_call, dbus::ObjectProxy::TIMEOUT_USE_DEFAULT));
  if (!response) {
    LOG(ERROR) << "Error contacting klauncher to start " << kwalletd_name_;
    return false;
  }
  dbus::MessageReader reader(response.get());
  int32_t ret = -1;
  std::string dbus_name;
  std::string error;
  int32_t pid = -1;
  if (!reader.PopInt32(&ret) || !reader.PopString(&dbus_name) ||
      !reader.PopString(&error) || !reader.PopInt32(&pid)) {
    LOG(ERROR) << "Error reading response from klauncher to start "
               << kwalletd_name_ << ": " << response->ToString();
    return false;
  }
  if (!error.empty() || ret) {
    LOG(ERROR) << "Error launching " << kwalletd_name_ << ": error '" << error
               << "' (code " << ret << ")";
    return false;
  }

  return true;
}

KWalletDBus::Error KWalletDBus::IsEnabled(bool* enabled) {
  dbus::MethodCall method_call(kKWalletInterface, "isEnabled");
  std::unique_ptr<dbus::Response> response(kwallet_proxy_->CallMethodAndBlock(
      &method_call, dbus::ObjectProxy::TIMEOUT_USE_DEFAULT));
  if (!response) {
    LOG(ERROR) << "Error contacting " << kwalletd_name_ << " (isEnabled)";
    return CANNOT_CONTACT;
  }
  dbus::MessageReader reader(response.get());
  if (!reader.PopBool(enabled)) {
    LOG(ERROR) << "Error reading response from " << kwalletd_name_
               << " (isEnabled): " << response->ToString();
    return CANNOT_READ;
  }
  // Not enabled? Don't use KWallet. But also don't warn here.
  if (!enabled) {
    VLOG(1) << kwalletd_name_ << " reports that KWallet is not enabled.";
  }

  return SUCCESS;
}

KWalletDBus::Error KWalletDBus::NetworkWallet(std::string* wallet_name) {
  // Get the wallet name.
  dbus::MethodCall method_call(kKWalletInterface, "networkWallet");
  std::unique_ptr<dbus::Response> response(kwallet_proxy_->CallMethodAndBlock(
      &method_call, dbus::ObjectProxy::TIMEOUT_USE_DEFAULT));
  if (!response) {
    LOG(ERROR) << "Error contacting " << kwalletd_name_ << " (networkWallet)";
    return CANNOT_CONTACT;
  }
  dbus::MessageReader reader(response.get());
  if (!reader.PopString(wallet_name)) {
    LOG(ERROR) << "Error reading response from " << kwalletd_name_
               << " (networkWallet): " << response->ToString();
    return CANNOT_READ;
  }

  return SUCCESS;
}

KWalletDBus::Error KWalletDBus::Open(const std::string& wallet_name,
                                     const std::string& app_name,
                                     int* handle_ptr) {
  dbus::MethodCall method_call(kKWalletInterface, "open");
  dbus::MessageWriter builder(&method_call);
  builder.AppendString(wallet_name);  // wallet
  builder.AppendInt64(0);             // wid
  builder.AppendString(app_name);     // appid
  std::unique_ptr<dbus::Response> response(kwallet_proxy_->CallMethodAndBlock(
      &method_call, dbus::ObjectProxy::TIMEOUT_USE_DEFAULT));
  if (!response) {
    LOG(ERROR) << "Error contacting " << kwalletd_name_ << " (open)";
    return CANNOT_CONTACT;
  }
  dbus::MessageReader reader(response.get());
  if (!reader.PopInt32(handle_ptr)) {
    LOG(ERROR) << "Error reading response from " << kwalletd_name_
               << " (open): " << response->ToString();
    return CANNOT_READ;
  }
  return SUCCESS;
}

KWalletDBus::Error KWalletDBus::HasEntry(const int wallet_handle,
                                         const std::string& folder_name,
                                         const std::string& signon_realm,
                                         const std::string& app_name,
                                         bool* has_entry) {
  dbus::MethodCall method_call(kKWalletInterface, "hasEntry");
  dbus::MessageWriter builder(&method_call);
  builder.AppendInt32(wallet_handle);  // handle
  builder.AppendString(folder_name);   // folder
  builder.AppendString(signon_realm);  // key
  builder.AppendString(app_name);      // appid
  std::unique_ptr<dbus::Response> response(kwallet_proxy_->CallMethodAndBlock(
      &method_call, dbus::ObjectProxy::TIMEOUT_USE_DEFAULT));
  if (!response) {
    LOG(ERROR) << "Error contacting " << kwalletd_name_ << " (hasEntry)";
    return CANNOT_CONTACT;
  }
  dbus::MessageReader reader(response.get());
  if (!reader.PopBool(has_entry)) {
    LOG(ERROR) << "Error reading response from " << kwalletd_name_
               << " (hasEntry): " << response->ToString();
    return CANNOT_READ;
  }
  return SUCCESS;
}

KWalletDBus::Error KWalletDBus::ReadEntry(const int wallet_handle,
                                          const std::string& folder_name,
                                          const std::string& signon_realm,
                                          const std::string& app_name,
                                          std::vector<uint8_t>* bytes_ptr) {
  dbus::MethodCall method_call(kKWalletInterface, "readEntry");
  dbus::MessageWriter builder(&method_call);
  builder.AppendInt32(wallet_handle);  // handle
  builder.AppendString(folder_name);   // folder
  builder.AppendString(signon_realm);  // key
  builder.AppendString(app_name);      // appid
  std::unique_ptr<dbus::Response> response(kwallet_proxy_->CallMethodAndBlock(
      &method_call, dbus::ObjectProxy::TIMEOUT_USE_DEFAULT));
  if (!response) {
    LOG(ERROR) << "Error contacting " << kwalletd_name_ << " (readEntry)";
    return CANNOT_CONTACT;
  }
  size_t length = 0;
  const uint8_t* bytes_temp = nullptr;
  dbus::MessageReader reader(response.get());
  if (!reader.PopArrayOfBytes(&bytes_temp, &length)) {
    LOG(ERROR) << "Error reading response from " << kwalletd_name_
               << " (readEntry): " << response->ToString();
    return CANNOT_READ;
  }
  if (bytes_temp) {
    bytes_ptr->assign(bytes_temp, bytes_temp + length);
  } else {
    bytes_ptr->clear();
  }
  return SUCCESS;
}

KWalletDBus::Error KWalletDBus::EntryList(
    const int wallet_handle,
    const std::string& folder_name,
    const std::string& app_name,
    std::vector<std::string>* entry_list_ptr) {
  dbus::MethodCall method_call(kKWalletInterface, "entryList");
  dbus::MessageWriter builder(&method_call);
  builder.AppendInt32(wallet_handle);  // handle
  builder.AppendString(folder_name);   // folder
  builder.AppendString(app_name);      // appid
  std::unique_ptr<dbus::Response> response(kwallet_proxy_->CallMethodAndBlock(
      &method_call, dbus::ObjectProxy::TIMEOUT_USE_DEFAULT));
  if (!response) {
    LOG(ERROR) << "Error contacting " << kwalletd_name_ << " (entryList)";
    return CANNOT_CONTACT;
  }
  dbus::MessageReader reader(response.get());
  if (!reader.PopArrayOfStrings(entry_list_ptr)) {
    LOG(ERROR) << "Error reading response from " << kwalletd_name_
               << "(entryList): " << response->ToString();
    return CANNOT_READ;
  }
  return SUCCESS;
}

KWalletDBus::Error KWalletDBus::RemoveEntry(const int wallet_handle,
                                            const std::string& folder_name,
                                            const std::string& signon_realm,
                                            const std::string& app_name,
                                            int* return_code_ptr) {
  dbus::MethodCall method_call(kKWalletInterface, "removeEntry");
  dbus::MessageWriter builder(&method_call);
  builder.AppendInt32(wallet_handle);  // handle
  builder.AppendString(folder_name);   // folder
  builder.AppendString(signon_realm);  // key
  builder.AppendString(app_name);      // appid
  std::unique_ptr<dbus::Response> response(kwallet_proxy_->CallMethodAndBlock(
      &method_call, dbus::ObjectProxy::TIMEOUT_USE_DEFAULT));
  if (!response) {
    LOG(ERROR) << "Error contacting " << kwalletd_name_ << " (removeEntry)";
    return CANNOT_CONTACT;
  }
  dbus::MessageReader reader(response.get());
  if (!reader.PopInt32(return_code_ptr)) {
    LOG(ERROR) << "Error reading response from " << kwalletd_name_
               << " (removeEntry): " << response->ToString();
    return CANNOT_READ;
  }
  return SUCCESS;
}

KWalletDBus::Error KWalletDBus::WriteEntry(const int wallet_handle,
                                           const std::string& folder_name,
                                           const std::string& signon_realm,
                                           const std::string& app_name,
                                           const uint8_t* data,
                                           const size_t length,
                                           int* return_code_ptr) {
  dbus::MethodCall method_call(kKWalletInterface, "writeEntry");
  dbus::MessageWriter builder(&method_call);
  builder.AppendInt32(wallet_handle);        // handle
  builder.AppendString(folder_name);         // folder
  builder.AppendString(signon_realm);        // key
  builder.AppendArrayOfBytes(data, length);  // value
  builder.AppendString(app_name);            // appid
  std::unique_ptr<dbus::Response> response(kwallet_proxy_->CallMethodAndBlock(
      &method_call, dbus::ObjectProxy::TIMEOUT_USE_DEFAULT));
  if (!response) {
    LOG(ERROR) << "Error contacting " << kwalletd_name_ << " (writeEntry)";
    return CANNOT_CONTACT;
  }
  dbus::MessageReader reader(response.get());
  if (!reader.PopInt32(return_code_ptr)) {
    LOG(ERROR) << "Error reading response from " << kwalletd_name_
               << " (writeEntry): " << response->ToString();
    return CANNOT_READ;
  }
  return SUCCESS;
}

KWalletDBus::Error KWalletDBus::HasFolder(const int handle,
                                          const std::string& folder_name,
                                          const std::string& app_name,
                                          bool* has_folder_ptr) {
  dbus::MethodCall method_call(kKWalletInterface, "hasFolder");
  dbus::MessageWriter builder(&method_call);
  builder.AppendInt32(handle);        // handle
  builder.AppendString(folder_name);  // folder
  builder.AppendString(app_name);     // appid
  std::unique_ptr<dbus::Response> response(kwallet_proxy_->CallMethodAndBlock(
      &method_call, dbus::ObjectProxy::TIMEOUT_USE_DEFAULT));
  if (!response) {
    LOG(ERROR) << "Error contacting " << kwalletd_name_ << " (hasFolder)";
    return CANNOT_CONTACT;
  }
  dbus::MessageReader reader(response.get());
  if (!reader.PopBool(has_folder_ptr)) {
    LOG(ERROR) << "Error reading response from " << kwalletd_name_
               << " (hasFolder): " << response->ToString();
    return CANNOT_READ;
  }
  return SUCCESS;
}

KWalletDBus::Error KWalletDBus::CreateFolder(const int handle,
                                             const std::string& folder_name,
                                             const std::string& app_name,
                                             bool* success_ptr) {
  dbus::MethodCall method_call(kKWalletInterface, "createFolder");
  dbus::MessageWriter builder(&method_call);
  builder.AppendInt32(handle);        // handle
  builder.AppendString(folder_name);  // folder
  builder.AppendString(app_name);     // appid
  std::unique_ptr<dbus::Response> response(kwallet_proxy_->CallMethodAndBlock(
      &method_call, dbus::ObjectProxy::TIMEOUT_USE_DEFAULT));
  if (!response) {
    LOG(ERROR) << "Error contacting " << kwalletd_name_ << " (createFolder)";
    return CANNOT_CONTACT;
  }
  dbus::MessageReader reader(response.get());
  if (!reader.PopBool(success_ptr)) {
    LOG(ERROR) << "Error reading response from " << kwalletd_name_
               << " (createFolder): " << response->ToString();
    return CANNOT_READ;
  }
  return SUCCESS;
}

KWalletDBus::Error KWalletDBus::WritePassword(const int handle,
                                              const std::string& folder_name,
                                              const std::string& key,
                                              const std::string& password,
                                              const std::string& app_name,
                                              bool* const write_success_ptr) {
  dbus::MethodCall method_call(kKWalletInterface, "writePassword");
  dbus::MessageWriter builder(&method_call);
  builder.AppendInt32(handle);
  builder.AppendString(folder_name);
  builder.AppendString(key);
  builder.AppendString(password);
  builder.AppendString(app_name);
  std::unique_ptr<dbus::Response> response(kwallet_proxy_->CallMethodAndBlock(
      &method_call, dbus::ObjectProxy::TIMEOUT_USE_DEFAULT));
  if (!response) {
    LOG(ERROR) << "Error contacting " << kwalletd_name_ << " (writePassword)";
    return CANNOT_CONTACT;
  }
  dbus::MessageReader reader(response.get());
  int return_code;
  if (!reader.PopInt32(&return_code)) {
    LOG(ERROR) << "Error reading response from " << kwalletd_name_
               << " (writePassword): " << response->ToString();
    return CANNOT_READ;
  }
  *write_success_ptr = return_code == 0;
  return SUCCESS;
}

KWalletDBus::Error KWalletDBus::ReadPassword(const int handle,
                                             const std::string& folder_name,
                                             const std::string& key,
                                             const std::string& app_name,
                                             std::string* const password_ptr) {
  dbus::MethodCall method_call(kKWalletInterface, "readPassword");
  dbus::MessageWriter builder(&method_call);
  builder.AppendInt32(handle);
  builder.AppendString(folder_name);
  builder.AppendString(key);
  builder.AppendString(app_name);
  std::unique_ptr<dbus::Response> response(kwallet_proxy_->CallMethodAndBlock(
      &method_call, dbus::ObjectProxy::TIMEOUT_USE_DEFAULT));
  if (!response) {
    LOG(ERROR) << "Error contacting " << kwalletd_name_ << " (readPassword)";
    return CANNOT_CONTACT;
  }
  dbus::MessageReader reader(response.get());
  if (!reader.PopString(password_ptr)) {
    LOG(ERROR) << "Error reading response from " << kwalletd_name_
               << " (readPassword): " << response->ToString();
    return CANNOT_READ;
  }
  return SUCCESS;
}

KWalletDBus::Error KWalletDBus::Close(const int handle,
                                      const bool force,
                                      const std::string& app_name,
                                      bool* success_ptr) {
  dbus::MethodCall method_call(kKWalletInterface, "close");
  dbus::MessageWriter builder(&method_call);
  builder.AppendInt32(handle);
  builder.AppendBool(force);
  builder.AppendString(app_name);
  std::unique_ptr<dbus::Response> response(kwallet_proxy_->CallMethodAndBlock(
      &method_call, dbus::ObjectProxy::TIMEOUT_USE_DEFAULT));
  if (!response) {
    LOG(ERROR) << "Error contacting " << kwalletd_name_ << " (close)";
    return CANNOT_CONTACT;
  }
  dbus::MessageReader reader(response.get());
  int return_code = 1;
  if (!reader.PopInt32(&return_code)) {
    LOG(ERROR) << "Error reading response from " << kwalletd_name_
               << " (close): " << response->ToString();
    return CANNOT_READ;
  }
  *success_ptr = return_code == 0;
  return SUCCESS;
}
