// Copyright (c) 2012 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 <cstring>  // memcpy

#include <base/stl_util.h>
#include <base/strings/string_number_conversions.h>

#include "brillo/secure_blob.h"

namespace brillo {

namespace {

bool ConvertHexToBytes(char c, uint8_t* v) {
  if (c >= '0' && c <='9')
    *v = c - '0';
  else if (c >= 'a' && c <= 'f')
    *v = c - 'a' + 10;
  else if (c >= 'A' && c <= 'F')
    *v = c - 'A' + 10;
  else
    return false;

  return true;
}

}  // namespace

std::string BlobToString(const Blob& blob) {
  return std::string(blob.begin(), blob.end());
}

Blob BlobFromString(const std::string& bytes) {
  return Blob(bytes.begin(), bytes.end());
}

Blob CombineBlobs(const std::initializer_list<Blob>& blobs) {
  size_t total_size = 0;
  for (const auto& blob : blobs)
    total_size += blob.size();
  Blob concatenation;
  concatenation.reserve(total_size);
  for (const auto& blob : blobs)
    concatenation.insert(concatenation.end(), blob.begin(), blob.end());
  return concatenation;
}

SecureBlob::SecureBlob(const Blob& blob)
    : SecureBlob(blob.begin(), blob.end()) {}

SecureBlob::SecureBlob(const std::string& data)
    : SecureBlob(data.begin(), data.end()) {}

SecureBlob::~SecureBlob() {
  SecureVector::clear();
}

void SecureBlob::resize(size_type count) {
  if (count < size()) {
    SecureMemset(data() + count, 0, capacity() - count);
  }
  SecureVector::resize(count);
}

void SecureBlob::resize(size_type count, const value_type& value) {
  if (count < size()) {
    SecureMemset(data() + count, 0, capacity() - count);
  }
  SecureVector::resize(count, value);
}

void SecureBlob::clear() {
  SecureVector::clear();
}

std::string SecureBlob::to_string() const {
  return std::string(data(), data() + size());
}

SecureBlob SecureBlob::Combine(const SecureBlob& blob1,
                               const SecureBlob& blob2) {
  SecureBlob result;
  result.reserve(blob1.size() + blob2.size());
  result.insert(result.end(), blob1.begin(), blob1.end());
  result.insert(result.end(), blob2.begin(), blob2.end());
  return result;
}

bool SecureBlob::HexStringToSecureBlob(const std::string& input,
                                       SecureBlob* output) {
  // TODO(jorgelo,crbug.com/728047): Consider not using an intermediate
  // std::vector here at all.
  std::vector<uint8_t> temp;
  if (!base::HexStringToBytes(input, &temp)) {
    output->clear();
    return false;
  }
  output->assign(temp.begin(), temp.end());
  SecureMemset(temp.data(), 0, temp.capacity());
  return true;
}

BRILLO_DISABLE_ASAN void* SecureMemset(void* v, int c, size_t n) {
  volatile uint8_t* p = reinterpret_cast<volatile uint8_t*>(v);
  while (n--)
    *p++ = c;
  return v;
}

int SecureMemcmp(const void* s1, const void* s2, size_t n) {
  const uint8_t* us1 = reinterpret_cast<const uint8_t*>(s1);
  const uint8_t* us2 = reinterpret_cast<const uint8_t*>(s2);
  int result = 0;

  if (0 == n)
    return 1;

  /* Code snippet without data-dependent branch due to
   * Nate Lawson (nate@root.org) of Root Labs. */
  while (n--)
    result |= *us1++ ^ *us2++;

  return result != 0;
}

// base::HexEncode and base::HexStringToBytes use strings, which may leak
// contents. These functions are alternatives that keep all contents
// within secured memory.
SecureBlob SecureBlobToSecureHex(const SecureBlob& blob) {
  std::string kHexChars("0123456789ABCDEF");
  SecureBlob hex(blob.size() * 2, 0);
  const char* blob_char_data = blob.char_data();

  // Each input byte creates two output hex characters.
  for (size_t i = 0; i < blob.size(); ++i) {
    hex[(i * 2)] = kHexChars[(blob_char_data[i] >> 4) & 0xf];
    hex[(i * 2) + 1] = kHexChars[blob_char_data[i] & 0xf];
  }
  return hex;
}

SecureBlob SecureHexToSecureBlob(const SecureBlob& hex) {
  SecureBlob blob(hex.size()/2, 0);

  if (hex.size() == 0 || hex.size() % 2)
    return SecureBlob();

  for (size_t i = 0; i < hex.size(); i++) {
    uint8_t v;
    // Check for invalid characters.
    if (!ConvertHexToBytes(hex[i], &v))
      return SecureBlob();

    blob[i/2] = (blob[i/2] << 4) | (v & 0xf);
  }

  return blob;
}

}  // namespace brillo
