// 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.
//
// Lockbox - class for storing tamper-evident data blobs.
#ifndef CRYPTOHOME_LOCKBOX_H_
#define CRYPTOHOME_LOCKBOX_H_

#include <openssl/sha.h>

#include <base/macros.h>
#include <base/memory/scoped_ptr.h>
#include <base/strings/string_util.h>
#include <chromeos/process.h>
#include <chromeos/secure_blob.h>

#include "cryptohome/platform.h"
#include "cryptohome/tpm.h"


namespace cryptohome {

struct LockboxContents;

// Lockbox stores a blob of data in a tamper-evident manner.
//
// This class provides system integration for supporting tamper-evident
// storage using the TPM NVRAM locking and restricted TPM ownership to
// ensure that a data blob stored on disk has not been tampered with to
// the degree that can be cryptographically assured.
//
// Lockbox is not thread-safe and should not be accessed in parallel.
//
// A normal usage flow for Lockbox would be something as follows:
//
// Initializing new data against a lockbox (except with error checking :)
//   Lockbox lockbox(tpm, kNvramSpace);
//   Lockbox::ErrorId error;
//   lockbox->Destroy(&error);
//   lockbox->Create(&error);
//   lockbox->Store(mah_locked_data, &error);
//
// Verifying data can be done along these lines:
//   Lockbox lockbox(tpm, kNvramSpace);
//   lockbox->Load(&error);
//   lockbox->Verify(mah_maybe_tampered_with_dat, &error);
// ...
class Lockbox {
 public:
  typedef enum {
    kErrorIdNone = 0,
    kErrorIdHashMismatch,  // Tampering or disk corruption.
    kErrorIdSizeMismatch,  // Tampering or disk corruption.
    kErrorIdInsufficientAuthorization,  // Bad call order or TPM state.
    kErrorIdNoNvramSpace,  // No space is defined. (legacy install)
    kErrorIdNoNvramData,  // Empty (unlocked) lockbox
    // All errors below indicate any number of system errors.
    kErrorIdNvramInvalid,
    kErrorIdNvramFailedToLock,
    kErrorIdTpmNotReady,
    kErrorIdTooLarge,
    kErrorIdTpmError,  // Transient or unknown TPM error.
  } ErrorId;

  // Populates the basic internal state of the Lockbox.
  //
  // Parameters
  // - tpm: a required pointer to a TPM object.
  // - nvram_index: the TPM NVRAM Index to use for this space.
  //
  // Lockbox requires a |tpm|.  If a NULL |tpm| is supplied, none of the
  // operations will succeed, but it should not crash or behave unexpectedly.
  // The |nvram_index| should be chosen carefully. See README.lockbox for info.
  Lockbox(Tpm* tpm, uint32_t nvram_index);
  virtual ~Lockbox();

  // Creates the backend state needed for this lockbox.
  //
  // Instantiates a new TPM NVRAM index lockable bWriteDefine to store
  // the hash and blob size of the data to lock away.
  //
  // Parameters
  // - error: will contain the ErrorId if false.
  // Returns
  // - true if a new space was instantiated or an old one could be used.
  // - false if the space cannot be created or claimed.
  virtual bool Create(ErrorId* error);

  // Destroys all backend state for this Lockbox.
  //
  // This call deletes the NVRAM space if defined.
  //
  // Parameters
  // - error: will contain the ErrorId if false.
  // Returns
  // - false if TPM Owner authorization is missing or the space cannot be
  //   destroyed.
  // - true if the space is already undefined or has been destroyed.
  virtual bool Destroy(ErrorId* error);

  // Loads the TPM NVRAM state date into memory
  //
  // Parameters
  // - error: ErrorId populated only on failure
  // Returns
  // - true if TPM NVRAM data is properly retrieved.
  // - false if the NVRAM data does not exist, is incorrect, or is unlocked.
  virtual bool Load(ErrorId* error);

  // Verifies the given blob against Load()d data.
  //
  // Parameters
  // - blob: data blob to verify.
  // - error: ErrorId populated only on failure
  // Returns
  // - true if verified
  // - false if the data could not be validated.
  virtual bool Verify(const chromeos::Blob& blob, ErrorId* error);

  // Hashes, salts, sizes, and stores metadata required for verifying |data|
  // in TPM NVRAM for later verification.
  //
  // Parameters
  // - data: blob to store.
  // - error: ErrorId populated only on failure
  // Returns
  // - true if written to disk and NVRAM (if there is a tpm).
  // - false if the data could not be persisted.
  virtual bool Store(const chromeos::Blob& data, ErrorId* error);

  // Replaces the tpm implementation.
  // Does NOT take ownership of the pointer.
  virtual void set_tpm(Tpm* tpm) { tpm_ = tpm; }

  // Replaces the process spawning implementation.
  // Does NOT take ownership of the pointer.
  virtual void set_process(chromeos::Process* p) { process_ = p; }

  // Replaces the Platform class (only used for mount-encrypted).
  // Does NOT take ownership of the pointer.
  virtual void set_platform(Platform* p) { platform_ = p; }

  // Return NVRAM index.
  virtual uint32_t nvram_index() const { return nvram_index_; }
  // Return NVRAM version.
  virtual uint32_t nvram_version() const { return nvram_version_; }
  // Replaces the default NVRAM structure version.
  virtual void set_nvram_version(uint32_t version) { nvram_version_ = version; }

  virtual Tpm* tpm() { return tpm_; }

  // Provide a simple means to access the expected NVRAM contents.
  virtual const LockboxContents* contents() const { return contents_.get(); }

  // NVRAM structure versions.
  static const uint32_t kNvramVersion1;
  static const uint32_t kNvramVersion2;
  static const uint32_t kNvramVersionDefault;
  // Space reserved for the blob data size.
  static const uint32_t kReservedSizeBytes;
  static const uint32_t kReservedFlagsBytes;
  static const uint32_t kReservedSaltBytesV1;
  static const uint32_t kReservedSaltBytesV2;
  static const uint32_t kReservedDigestBytes;
  // The sum of the above sizes, accounting for possible salts.
  static const uint32_t kReservedNvramBytesV1;
  static const uint32_t kReservedNvramBytesV2;

  // Literals for running mount-encrypted helper.
  static const char * const kMountEncrypted;
  static const char * const kMountEncryptedFinalize;

 protected:
  // Returns true if we have the authorization needed to create/destroy
  // NVRAM spaces.
  virtual bool HasAuthorization() const;

  // Returns true if the tpm is owned and connected.
  virtual bool TpmIsReady() const;

  // Serialize the size of data to a Blob.
  virtual bool GetSizeBlob(const chromeos::Blob& data,
                           chromeos::Blob* size_bytes) const;

  // Parse a serialized size from the front of |blob|.
  virtual bool ParseSizeBlob(const chromeos::Blob& blob, uint32_t* size) const;

  // Call out to the mount-encrypted helper to encrypt the key.
  virtual void FinalizeMountEncrypted(const chromeos::Blob &entropy) const;

 private:
  Tpm* tpm_;
  uint32_t nvram_index_;
  uint32_t nvram_version_;
  scoped_ptr<chromeos::Process> default_process_;
  chromeos::Process* process_;
  scoped_ptr<LockboxContents> contents_;
  scoped_ptr<Platform> default_platform_;
  Platform* platform_;

  DISALLOW_COPY_AND_ASSIGN(Lockbox);
};

// Defines the unmarshalled NVRAM contents.
#define CRYPTOHOME_LOCKBOX_SALT_LENGTH 32
struct LockboxContents {
  uint32_t size;
  uint8_t flags;
  uint8_t salt[CRYPTOHOME_LOCKBOX_SALT_LENGTH];
  uint8_t hash[SHA256_DIGEST_LENGTH];
  // Remaining variables are used internally and not stored to the NVRAM.
  uint32_t salt_size;
  bool loaded;
};

}  // namespace cryptohome

#endif  // CRYPTOHOME_LOCKBOX_H_
