// Copyright 2014 The Crashpad Authors. All rights reserved.
//
// Licensed 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 "minidump/minidump_module_writer.h"

#include <stddef.h>
#include <string.h>

#include <utility>

#include "base/format_macros.h"
#include "base/stl_util.h"
#include "base/strings/stringprintf.h"
#include "base/strings/utf_string_conversions.h"
#include "gtest/gtest.h"
#include "minidump/minidump_file_writer.h"
#include "minidump/test/minidump_file_writer_test_util.h"
#include "minidump/test/minidump_string_writer_test_util.h"
#include "minidump/test/minidump_writable_test_util.h"
#include "snapshot/test/test_module_snapshot.h"
#include "test/gtest_death.h"
#include "util/file/string_file.h"
#include "util/misc/implicit_cast.h"
#include "util/misc/uuid.h"

namespace crashpad {
namespace test {
namespace {

void GetModuleListStream(const std::string& file_contents,
                         const MINIDUMP_MODULE_LIST** module_list) {
  constexpr size_t kDirectoryOffset = sizeof(MINIDUMP_HEADER);
  constexpr size_t kModuleListStreamOffset =
      kDirectoryOffset + sizeof(MINIDUMP_DIRECTORY);
  constexpr size_t kModulesOffset =
      kModuleListStreamOffset + sizeof(MINIDUMP_MODULE_LIST);

  ASSERT_GE(file_contents.size(), kModulesOffset);

  const MINIDUMP_DIRECTORY* directory;
  const MINIDUMP_HEADER* header =
      MinidumpHeaderAtStart(file_contents, &directory);
  ASSERT_NO_FATAL_FAILURE(VerifyMinidumpHeader(header, 1, 0));
  ASSERT_TRUE(directory);

  ASSERT_EQ(directory[0].StreamType, kMinidumpStreamTypeModuleList);
  EXPECT_EQ(directory[0].Location.Rva, kModuleListStreamOffset);

  *module_list = MinidumpWritableAtLocationDescriptor<MINIDUMP_MODULE_LIST>(
      file_contents, directory[0].Location);
  ASSERT_TRUE(module_list);
}

TEST(MinidumpModuleWriter, EmptyModuleList) {
  MinidumpFileWriter minidump_file_writer;
  auto module_list_writer = std::make_unique<MinidumpModuleListWriter>();

  ASSERT_TRUE(minidump_file_writer.AddStream(std::move(module_list_writer)));

  StringFile string_file;
  ASSERT_TRUE(minidump_file_writer.WriteEverything(&string_file));

  ASSERT_EQ(string_file.string().size(),
            sizeof(MINIDUMP_HEADER) + sizeof(MINIDUMP_DIRECTORY) +
                sizeof(MINIDUMP_MODULE_LIST));

  const MINIDUMP_MODULE_LIST* module_list = nullptr;
  ASSERT_NO_FATAL_FAILURE(
      GetModuleListStream(string_file.string(), &module_list));

  EXPECT_EQ(module_list->NumberOfModules, 0u);
}

// If |expected_pdb_name| is not nullptr, |codeview_record| is used to locate a
// CodeView record in |file_contents|, and its fields are compared against the
// |expected_pdb_*| values. If |expected_pdb_uuid| is supplied, the CodeView
// record must be a PDB 7.0 link, otherwise, it must be a PDB 2.0 link. If
// |expected_pdb_name| is nullptr, |codeview_record| must not point to anything.
void ExpectCodeViewRecord(const MINIDUMP_LOCATION_DESCRIPTOR* codeview_record,
                          const std::string& file_contents,
                          const char* expected_pdb_name,
                          const UUID* expected_pdb_uuid,
                          time_t expected_pdb_timestamp,
                          uint32_t expected_pdb_age) {
  if (expected_pdb_name) {
    EXPECT_NE(codeview_record->Rva, 0u);

    std::string observed_pdb_name;
    if (expected_pdb_uuid) {
      // The CodeView record should be a PDB 7.0 link.
      const CodeViewRecordPDB70* codeview_pdb70_record =
          MinidumpWritableAtLocationDescriptor<CodeViewRecordPDB70>(
              file_contents, *codeview_record);
      ASSERT_TRUE(codeview_pdb70_record);
      EXPECT_EQ(memcmp(expected_pdb_uuid,
                       &codeview_pdb70_record->uuid,
                       sizeof(codeview_pdb70_record->uuid)),
                0);
      EXPECT_EQ(codeview_pdb70_record->age, expected_pdb_age);

      observed_pdb_name.assign(
          reinterpret_cast<const char*>(&codeview_pdb70_record->pdb_name[0]),
          codeview_record->DataSize - offsetof(CodeViewRecordPDB70, pdb_name));
    } else {
      // The CodeView record should be a PDB 2.0 link.
      const CodeViewRecordPDB20* codeview_pdb20_record =
          MinidumpWritableAtLocationDescriptor<CodeViewRecordPDB20>(
              file_contents, *codeview_record);
      ASSERT_TRUE(codeview_pdb20_record);
      EXPECT_EQ(codeview_pdb20_record->timestamp,
                static_cast<uint32_t>(expected_pdb_timestamp));
      EXPECT_EQ(codeview_pdb20_record->age, expected_pdb_age);

      observed_pdb_name.assign(
          reinterpret_cast<const char*>(&codeview_pdb20_record->pdb_name[0]),
          codeview_record->DataSize - offsetof(CodeViewRecordPDB20, pdb_name));
    }

    // Check for, and then remove, the NUL terminator.
    EXPECT_EQ(observed_pdb_name[observed_pdb_name.size() - 1], '\0');
    observed_pdb_name.resize(observed_pdb_name.size() - 1);

    EXPECT_EQ(observed_pdb_name, expected_pdb_name);
  } else {
    // There should be no CodeView record.
    EXPECT_EQ(codeview_record->DataSize, 0u);
    EXPECT_EQ(codeview_record->Rva, 0u);
  }
}

// If |expected_debug_name| is not nullptr, |misc_record| is used to locate a
// miscellanous debugging record in |file_contents|, and its fields are compared
// against the the |expected_debug_*| values. If |expected_debug_name| is
// nullptr, |misc_record| must not point to anything.
void ExpectMiscellaneousDebugRecord(
    const MINIDUMP_LOCATION_DESCRIPTOR* misc_record,
    const std::string& file_contents,
    const char* expected_debug_name,
    uint32_t expected_debug_type,
    bool expected_debug_utf16) {
  if (expected_debug_name) {
    EXPECT_NE(misc_record->Rva, 0u);
    const IMAGE_DEBUG_MISC* misc_debug_record =
        MinidumpWritableAtLocationDescriptor<IMAGE_DEBUG_MISC>(file_contents,
                                                               *misc_record);
    ASSERT_TRUE(misc_debug_record);
    EXPECT_EQ(misc_debug_record->DataType, expected_debug_type);
    EXPECT_EQ(misc_debug_record->Unicode != 0, expected_debug_utf16);
    EXPECT_EQ(misc_debug_record->Reserved[0], 0u);
    EXPECT_EQ(misc_debug_record->Reserved[1], 0u);
    EXPECT_EQ(misc_debug_record->Reserved[2], 0u);

    // Check for the NUL terminator.
    size_t bytes_available =
        misc_debug_record->Length - offsetof(IMAGE_DEBUG_MISC, Data);
    EXPECT_EQ(misc_debug_record->Data[bytes_available - 1], '\0');
    std::string observed_data(
        reinterpret_cast<const char*>(misc_debug_record->Data));

    size_t bytes_used;
    if (misc_debug_record->Unicode) {
      std::u16string observed_data_utf16(
          reinterpret_cast<const char16_t*>(misc_debug_record->Data));
      bytes_used = (observed_data_utf16.size() + 1) * sizeof(char16_t);
      observed_data = base::UTF16ToUTF8(observed_data_utf16);
    } else {
      observed_data = reinterpret_cast<const char*>(misc_debug_record->Data);
      bytes_used = (observed_data.size() + 1) * sizeof(char);
    }
    EXPECT_LE(bytes_used, bytes_available);

    // Make sure that any padding bytes after the first NUL are also NUL.
    for (size_t index = bytes_used; index < bytes_available; ++index) {
      EXPECT_EQ(misc_debug_record->Data[index], '\0');
    }

    EXPECT_EQ(observed_data, expected_debug_name);
  } else {
    // There should be no miscellaneous debugging record.
    EXPECT_EQ(misc_record->DataSize, 0u);
    EXPECT_EQ(misc_record->Rva, 0u);
  }
}

// ExpectModule() verifies that |expected| matches |observed|. Fields that are
// supposed to contain constant magic numbers are verified against the expected
// constants instead of |expected|. Reserved fields are verified to be 0. RVA
// and MINIDUMP_LOCATION_DESCRIPTOR fields are not verified against |expected|.
// Instead, |ModuleNameRva| is used to locate the module name, which is compared
// against |expected_module_name|. ExpectCodeViewRecord() and
// ExpectMiscellaneousDebugRecord() are used to verify the |CvRecord| and
// |MiscRecord| fields against |expected_pdb_*| and |expected_debug_*|
// parameters, respectively.
void ExpectModule(const MINIDUMP_MODULE* expected,
                  const MINIDUMP_MODULE* observed,
                  const std::string& file_contents,
                  const std::string& expected_module_name,
                  const char* expected_pdb_name,
                  const UUID* expected_pdb_uuid,
                  time_t expected_pdb_timestamp,
                  uint32_t expected_pdb_age,
                  const char* expected_debug_name,
                  uint32_t expected_debug_type,
                  bool expected_debug_utf16) {
  MINIDUMP_MODULE expected_module, observed_module;
  memcpy(&expected_module, expected, sizeof(expected_module));
  memcpy(&observed_module, observed, sizeof(observed_module));

  EXPECT_EQ(observed_module.BaseOfImage, expected_module.BaseOfImage);
  EXPECT_EQ(observed_module.SizeOfImage, expected_module.SizeOfImage);
  EXPECT_EQ(observed_module.CheckSum, expected_module.CheckSum);
  EXPECT_EQ(observed_module.TimeDateStamp, expected_module.TimeDateStamp);
  EXPECT_EQ(observed_module.VersionInfo.dwSignature,
            implicit_cast<uint32_t>(VS_FFI_SIGNATURE));
  EXPECT_EQ(observed_module.VersionInfo.dwStrucVersion,
            implicit_cast<uint32_t>(VS_FFI_STRUCVERSION));
  EXPECT_EQ(observed_module.VersionInfo.dwFileVersionMS,
            expected_module.VersionInfo.dwFileVersionMS);
  EXPECT_EQ(observed_module.VersionInfo.dwFileVersionLS,
            expected_module.VersionInfo.dwFileVersionLS);
  EXPECT_EQ(observed_module.VersionInfo.dwProductVersionMS,
            expected_module.VersionInfo.dwProductVersionMS);
  EXPECT_EQ(observed_module.VersionInfo.dwProductVersionLS,
            expected_module.VersionInfo.dwProductVersionLS);
  EXPECT_EQ(observed_module.VersionInfo.dwFileFlagsMask,
            expected_module.VersionInfo.dwFileFlagsMask);
  EXPECT_EQ(observed_module.VersionInfo.dwFileFlags,
            expected_module.VersionInfo.dwFileFlags);
  EXPECT_EQ(observed_module.VersionInfo.dwFileOS,
            expected_module.VersionInfo.dwFileOS);
  EXPECT_EQ(observed_module.VersionInfo.dwFileType,
            expected_module.VersionInfo.dwFileType);
  EXPECT_EQ(observed_module.VersionInfo.dwFileSubtype,
            expected_module.VersionInfo.dwFileSubtype);
  EXPECT_EQ(observed_module.VersionInfo.dwFileDateMS,
            expected_module.VersionInfo.dwFileDateMS);
  EXPECT_EQ(observed_module.VersionInfo.dwFileDateLS,
            expected_module.VersionInfo.dwFileDateLS);

  uint64_t reserved0, reserved1;
  memcpy(&reserved0, &observed_module.Reserved0, sizeof(reserved0));
  memcpy(&reserved1, &observed_module.Reserved1, sizeof(reserved1));

  EXPECT_EQ(reserved0, 0u);
  EXPECT_EQ(reserved1, 0u);

  EXPECT_NE(observed_module.ModuleNameRva, 0u);
  std::u16string observed_module_name_utf16 =
      MinidumpStringAtRVAAsString(file_contents, observed_module.ModuleNameRva);
  std::u16string expected_module_name_utf16 =
      base::UTF8ToUTF16(expected_module_name);
  EXPECT_EQ(observed_module_name_utf16, expected_module_name_utf16);

  ASSERT_NO_FATAL_FAILURE(ExpectCodeViewRecord(&observed_module.CvRecord,
                                               file_contents,
                                               expected_pdb_name,
                                               expected_pdb_uuid,
                                               expected_pdb_timestamp,
                                               expected_pdb_age));

  ASSERT_NO_FATAL_FAILURE(
      ExpectMiscellaneousDebugRecord(&observed_module.MiscRecord,
                                     file_contents,
                                     expected_debug_name,
                                     expected_debug_type,
                                     expected_debug_utf16));
}

// ExpectModuleWithBuildIDCv() is like ExpectModule( but expects the module to
// have a BuildID CodeView Record.
void ExpectModuleWithBuildIDCv(const MINIDUMP_MODULE* expected,
                               const MINIDUMP_MODULE* observed,
                               const std::string& file_contents,
                               const std::string& expected_module_name,
                               const std::vector<uint8_t>& expected_build_id) {
  EXPECT_EQ(observed->BaseOfImage, expected->BaseOfImage);
  EXPECT_EQ(observed->SizeOfImage, expected->SizeOfImage);
  EXPECT_EQ(observed->CheckSum, expected->CheckSum);
  EXPECT_EQ(observed->TimeDateStamp, expected->TimeDateStamp);
  EXPECT_EQ(observed->VersionInfo.dwSignature,
            implicit_cast<uint32_t>(VS_FFI_SIGNATURE));
  EXPECT_EQ(observed->VersionInfo.dwStrucVersion,
            implicit_cast<uint32_t>(VS_FFI_STRUCVERSION));
  EXPECT_EQ(observed->VersionInfo.dwFileVersionMS,
            expected->VersionInfo.dwFileVersionMS);
  EXPECT_EQ(observed->VersionInfo.dwFileVersionLS,
            expected->VersionInfo.dwFileVersionLS);
  EXPECT_EQ(observed->VersionInfo.dwProductVersionMS,
            expected->VersionInfo.dwProductVersionMS);
  EXPECT_EQ(observed->VersionInfo.dwProductVersionLS,
            expected->VersionInfo.dwProductVersionLS);
  EXPECT_EQ(observed->VersionInfo.dwFileFlagsMask,
            expected->VersionInfo.dwFileFlagsMask);
  EXPECT_EQ(observed->VersionInfo.dwFileFlags,
            expected->VersionInfo.dwFileFlags);
  EXPECT_EQ(observed->VersionInfo.dwFileOS, expected->VersionInfo.dwFileOS);
  EXPECT_EQ(observed->VersionInfo.dwFileType, expected->VersionInfo.dwFileType);
  EXPECT_EQ(observed->VersionInfo.dwFileSubtype,
            expected->VersionInfo.dwFileSubtype);
  EXPECT_EQ(observed->VersionInfo.dwFileDateMS,
            expected->VersionInfo.dwFileDateMS);
  EXPECT_EQ(observed->VersionInfo.dwFileDateLS,
            expected->VersionInfo.dwFileDateLS);

  uint64_t reserved0, reserved1;
  memcpy(&reserved0, &observed->Reserved0, sizeof(reserved0));
  memcpy(&reserved1, &observed->Reserved1, sizeof(reserved1));

  EXPECT_EQ(reserved0, 0u);
  EXPECT_EQ(reserved1, 0u);

  EXPECT_NE(observed->ModuleNameRva, 0u);
  std::u16string observed_module_name_utf16 =
      MinidumpStringAtRVAAsString(file_contents, observed->ModuleNameRva);
  std::u16string expected_module_name_utf16 =
      base::UTF8ToUTF16(expected_module_name);
  EXPECT_EQ(observed_module_name_utf16, expected_module_name_utf16);

  const CodeViewRecordBuildID* codeview_build_id_record =
      MinidumpWritableAtLocationDescriptor<CodeViewRecordBuildID>(
          file_contents, observed->CvRecord);
  ASSERT_TRUE(codeview_build_id_record);
  EXPECT_EQ(memcmp(expected_build_id.data(),
                   &codeview_build_id_record->build_id,
                   expected_build_id.size()),
            0);
}

TEST(MinidumpModuleWriter, EmptyModule) {
  MinidumpFileWriter minidump_file_writer;
  auto module_list_writer = std::make_unique<MinidumpModuleListWriter>();

  static constexpr char kModuleName[] = "test_executable";

  auto module_writer = std::make_unique<MinidumpModuleWriter>();
  module_writer->SetName(kModuleName);

  module_list_writer->AddModule(std::move(module_writer));
  ASSERT_TRUE(minidump_file_writer.AddStream(std::move(module_list_writer)));

  StringFile string_file;
  ASSERT_TRUE(minidump_file_writer.WriteEverything(&string_file));

  ASSERT_GT(string_file.string().size(),
            sizeof(MINIDUMP_HEADER) + sizeof(MINIDUMP_DIRECTORY) +
                sizeof(MINIDUMP_MODULE_LIST) + 1 * sizeof(MINIDUMP_MODULE));

  const MINIDUMP_MODULE_LIST* module_list = nullptr;
  ASSERT_NO_FATAL_FAILURE(
      GetModuleListStream(string_file.string(), &module_list));

  EXPECT_EQ(module_list->NumberOfModules, 1u);

  MINIDUMP_MODULE expected = {};
  ASSERT_NO_FATAL_FAILURE(ExpectModule(&expected,
                                       &module_list->Modules[0],
                                       string_file.string(),
                                       kModuleName,
                                       nullptr,
                                       nullptr,
                                       0,
                                       0,
                                       nullptr,
                                       0,
                                       false));
}

TEST(MinidumpModuleWriter, OneModule) {
  MinidumpFileWriter minidump_file_writer;
  auto module_list_writer = std::make_unique<MinidumpModuleListWriter>();

  static constexpr char kModuleName[] = "statically_linked";
  constexpr uint64_t kModuleBase = 0x10da69000;
  constexpr uint32_t kModuleSize = 0x1000;
  constexpr uint32_t kChecksum = 0x76543210;
  constexpr time_t kTimestamp = 0x386d4380;
  constexpr uint32_t kFileVersionMS = 0x00010002;
  constexpr uint32_t kFileVersionLS = 0x00030004;
  constexpr uint32_t kProductVersionMS = 0x00050006;
  constexpr uint32_t kProductVersionLS = 0x00070008;
  constexpr uint32_t kFileFlagsMask = VS_FF_DEBUG | VS_FF_PRERELEASE |
                                      VS_FF_PATCHED | VS_FF_PRIVATEBUILD |
                                      VS_FF_INFOINFERRED | VS_FF_SPECIALBUILD;
  constexpr uint32_t kFileFlags = VS_FF_PRIVATEBUILD | VS_FF_SPECIALBUILD;
  constexpr uint32_t kFileOS = VOS_DOS;
  constexpr uint32_t kFileType = VFT_DRV;
  constexpr uint32_t kFileSubtype = VFT2_DRV_KEYBOARD;
  static constexpr char kPDBName[] = "statical.pdb";
  static constexpr uint8_t kPDBUUIDBytes[16] = {0xfe,
                                                0xdc,
                                                0xba,
                                                0x98,
                                                0x76,
                                                0x54,
                                                0x32,
                                                0x10,
                                                0x08,
                                                0x19,
                                                0x2a,
                                                0x3b,
                                                0x4c,
                                                0x5d,
                                                0x6e,
                                                0x7f};
  UUID pdb_uuid;
  pdb_uuid.InitializeFromBytes(kPDBUUIDBytes);
  constexpr uint32_t kPDBAge = 1;
  constexpr uint32_t kDebugType = IMAGE_DEBUG_MISC_EXENAME;
  static constexpr char kDebugName[] = "statical.dbg";
  constexpr bool kDebugUTF16 = false;

  auto module_writer = std::make_unique<MinidumpModuleWriter>();
  module_writer->SetName(kModuleName);
  module_writer->SetImageBaseAddress(kModuleBase);
  module_writer->SetImageSize(kModuleSize);
  module_writer->SetChecksum(kChecksum);
  module_writer->SetTimestamp(kTimestamp);
  module_writer->SetFileVersion(kFileVersionMS >> 16,
                                kFileVersionMS & 0xffff,
                                kFileVersionLS >> 16,
                                kFileVersionLS & 0xffff);
  module_writer->SetProductVersion(kProductVersionMS >> 16,
                                   kProductVersionMS & 0xffff,
                                   kProductVersionLS >> 16,
                                   kProductVersionLS & 0xffff);
  module_writer->SetFileFlagsAndMask(kFileFlags, kFileFlagsMask);
  module_writer->SetFileOS(kFileOS);
  module_writer->SetFileTypeAndSubtype(kFileType, kFileSubtype);

  auto codeview_pdb70_writer =
      std::make_unique<MinidumpModuleCodeViewRecordPDB70Writer>();
  codeview_pdb70_writer->SetPDBName(kPDBName);
  codeview_pdb70_writer->SetUUIDAndAge(pdb_uuid, kPDBAge);
  module_writer->SetCodeViewRecord(std::move(codeview_pdb70_writer));

  auto misc_debug_writer =
      std::make_unique<MinidumpModuleMiscDebugRecordWriter>();
  misc_debug_writer->SetDataType(kDebugType);
  misc_debug_writer->SetData(kDebugName, kDebugUTF16);
  module_writer->SetMiscDebugRecord(std::move(misc_debug_writer));

  module_list_writer->AddModule(std::move(module_writer));
  ASSERT_TRUE(minidump_file_writer.AddStream(std::move(module_list_writer)));

  StringFile string_file;
  ASSERT_TRUE(minidump_file_writer.WriteEverything(&string_file));

  ASSERT_GT(string_file.string().size(),
            sizeof(MINIDUMP_HEADER) + sizeof(MINIDUMP_DIRECTORY) +
                sizeof(MINIDUMP_MODULE_LIST) + 1 * sizeof(MINIDUMP_MODULE));

  const MINIDUMP_MODULE_LIST* module_list = nullptr;
  ASSERT_NO_FATAL_FAILURE(
      GetModuleListStream(string_file.string(), &module_list));

  EXPECT_EQ(module_list->NumberOfModules, 1u);

  MINIDUMP_MODULE expected = {};
  expected.BaseOfImage = kModuleBase;
  expected.SizeOfImage = kModuleSize;
  expected.CheckSum = kChecksum;
  expected.TimeDateStamp = kTimestamp;
  expected.VersionInfo.dwFileVersionMS = kFileVersionMS;
  expected.VersionInfo.dwFileVersionLS = kFileVersionLS;
  expected.VersionInfo.dwProductVersionMS = kProductVersionMS;
  expected.VersionInfo.dwProductVersionLS = kProductVersionLS;
  expected.VersionInfo.dwFileFlagsMask = kFileFlagsMask;
  expected.VersionInfo.dwFileFlags = kFileFlags;
  expected.VersionInfo.dwFileOS = kFileOS;
  expected.VersionInfo.dwFileType = kFileType;
  expected.VersionInfo.dwFileSubtype = kFileSubtype;

  ASSERT_NO_FATAL_FAILURE(ExpectModule(&expected,
                                       &module_list->Modules[0],
                                       string_file.string(),
                                       kModuleName,
                                       kPDBName,
                                       &pdb_uuid,
                                       0,
                                       kPDBAge,
                                       kDebugName,
                                       kDebugType,
                                       kDebugUTF16));
}

TEST(MinidumpModuleWriter, OneModule_CodeViewUsesPDB20_MiscUsesUTF16) {
  // MinidumpModuleWriter.OneModule tested with a PDB 7.0 link as the CodeView
  // record and an IMAGE_DEBUG_MISC record in UTF-8. This test exercises the
  // alternatives, a PDB 2.0 link as the CodeView record and an IMAGE_DEBUG_MISC
  // record with UTF-16 data.
  MinidumpFileWriter minidump_file_writer;
  auto module_list_writer = std::make_unique<MinidumpModuleListWriter>();

  static constexpr char kModuleName[] = "dinosaur";
  static constexpr char kPDBName[] = "d1n05.pdb";
  constexpr time_t kPDBTimestamp = 0x386d4380;
  constexpr uint32_t kPDBAge = 1;
  constexpr uint32_t kDebugType = IMAGE_DEBUG_MISC_EXENAME;
  static constexpr char kDebugName[] = "d1n05.dbg";
  constexpr bool kDebugUTF16 = true;

  auto module_writer = std::make_unique<MinidumpModuleWriter>();
  module_writer->SetName(kModuleName);

  auto codeview_pdb20_writer =
      std::make_unique<MinidumpModuleCodeViewRecordPDB20Writer>();
  codeview_pdb20_writer->SetPDBName(kPDBName);
  codeview_pdb20_writer->SetTimestampAndAge(kPDBTimestamp, kPDBAge);
  module_writer->SetCodeViewRecord(std::move(codeview_pdb20_writer));

  auto misc_debug_writer =
      std::make_unique<MinidumpModuleMiscDebugRecordWriter>();
  misc_debug_writer->SetDataType(kDebugType);
  misc_debug_writer->SetData(kDebugName, kDebugUTF16);
  module_writer->SetMiscDebugRecord(std::move(misc_debug_writer));

  module_list_writer->AddModule(std::move(module_writer));
  ASSERT_TRUE(minidump_file_writer.AddStream(std::move(module_list_writer)));

  StringFile string_file;
  ASSERT_TRUE(minidump_file_writer.WriteEverything(&string_file));

  ASSERT_GT(string_file.string().size(),
            sizeof(MINIDUMP_HEADER) + sizeof(MINIDUMP_DIRECTORY) +
                sizeof(MINIDUMP_MODULE_LIST) + 1 * sizeof(MINIDUMP_MODULE));

  const MINIDUMP_MODULE_LIST* module_list = nullptr;
  ASSERT_NO_FATAL_FAILURE(
      GetModuleListStream(string_file.string(), &module_list));

  EXPECT_EQ(module_list->NumberOfModules, 1u);

  MINIDUMP_MODULE expected = {};

  ASSERT_NO_FATAL_FAILURE(ExpectModule(&expected,
                                       &module_list->Modules[0],
                                       string_file.string(),
                                       kModuleName,
                                       kPDBName,
                                       nullptr,
                                       kPDBTimestamp,
                                       kPDBAge,
                                       kDebugName,
                                       kDebugType,
                                       kDebugUTF16));
}

TEST(MinidumpModuleWriter, OneModule_CodeViewBuildID) {
  // MinidumpModuleWriter.OneModule tested with a BuildID CodeView
  MinidumpFileWriter minidump_file_writer;
  auto module_list_writer = std::make_unique<MinidumpModuleListWriter>();

  static constexpr char kModuleName[] = "dinosaur";
  static constexpr char kBuildID[] =
      "averylonghashcodeormaybeitsjustrandomnumbershardtosay";

  std::vector<uint8_t> build_id_data(kBuildID, kBuildID + 53);

  auto module_writer = std::make_unique<MinidumpModuleWriter>();
  module_writer->SetName(kModuleName);

  auto codeview_build_id_writer =
      std::make_unique<MinidumpModuleCodeViewRecordBuildIDWriter>();
  codeview_build_id_writer->SetBuildID(build_id_data);
  module_writer->SetCodeViewRecord(std::move(codeview_build_id_writer));

  module_list_writer->AddModule(std::move(module_writer));
  ASSERT_TRUE(minidump_file_writer.AddStream(std::move(module_list_writer)));

  StringFile string_file;
  ASSERT_TRUE(minidump_file_writer.WriteEverything(&string_file));

  ASSERT_GT(string_file.string().size(),
            sizeof(MINIDUMP_HEADER) + sizeof(MINIDUMP_DIRECTORY) +
                sizeof(MINIDUMP_MODULE_LIST) + 1 * sizeof(MINIDUMP_MODULE));

  const MINIDUMP_MODULE_LIST* module_list = nullptr;
  ASSERT_NO_FATAL_FAILURE(
      GetModuleListStream(string_file.string(), &module_list));

  EXPECT_EQ(module_list->NumberOfModules, 1u);

  MINIDUMP_MODULE expected = {};

  ASSERT_NO_FATAL_FAILURE(ExpectModuleWithBuildIDCv(&expected,
                                                    &module_list->Modules[0],
                                                    string_file.string(),
                                                    kModuleName,
                                                    build_id_data));
}

TEST(MinidumpModuleWriter, ThreeModules) {
  // As good exercise, this test uses three modules, one with a PDB 7.0 link as
  // its CodeView record, one with no CodeView record, and one with a PDB 2.0
  // link as its CodeView record.
  MinidumpFileWriter minidump_file_writer;
  auto module_list_writer = std::make_unique<MinidumpModuleListWriter>();

  static constexpr char kModuleName0[] = "main";
  constexpr uint64_t kModuleBase0 = 0x100101000;
  constexpr uint32_t kModuleSize0 = 0xf000;
  static constexpr char kPDBName0[] = "main";
  static constexpr uint8_t kPDBUUIDBytes0[16] = {0xaa,
                                                 0xbb,
                                                 0xcc,
                                                 0xdd,
                                                 0xee,
                                                 0xff,
                                                 0x00,
                                                 0x11,
                                                 0x22,
                                                 0x33,
                                                 0x44,
                                                 0x55,
                                                 0x66,
                                                 0x77,
                                                 0x88,
                                                 0x99};
  UUID pdb_uuid_0;
  pdb_uuid_0.InitializeFromBytes(kPDBUUIDBytes0);
  constexpr uint32_t kPDBAge0 = 0;

  static constexpr char kModuleName1[] = "ld.so";
  constexpr uint64_t kModuleBase1 = 0x200202000;
  constexpr uint32_t kModuleSize1 = 0x1e000;

  static constexpr char kModuleName2[] = "libc.so";
  constexpr uint64_t kModuleBase2 = 0x300303000;
  constexpr uint32_t kModuleSize2 = 0x2d000;
  static constexpr char kPDBName2[] = "libc.so";
  constexpr time_t kPDBTimestamp2 = 0x386d4380;
  constexpr uint32_t kPDBAge2 = 2;

  auto module_writer_0 = std::make_unique<MinidumpModuleWriter>();
  module_writer_0->SetName(kModuleName0);
  module_writer_0->SetImageBaseAddress(kModuleBase0);
  module_writer_0->SetImageSize(kModuleSize0);

  auto codeview_pdb70_writer_0 =
      std::make_unique<MinidumpModuleCodeViewRecordPDB70Writer>();
  codeview_pdb70_writer_0->SetPDBName(kPDBName0);
  codeview_pdb70_writer_0->SetUUIDAndAge(pdb_uuid_0, kPDBAge0);
  module_writer_0->SetCodeViewRecord(std::move(codeview_pdb70_writer_0));

  module_list_writer->AddModule(std::move(module_writer_0));

  auto module_writer_1 = std::make_unique<MinidumpModuleWriter>();
  module_writer_1->SetName(kModuleName1);
  module_writer_1->SetImageBaseAddress(kModuleBase1);
  module_writer_1->SetImageSize(kModuleSize1);

  module_list_writer->AddModule(std::move(module_writer_1));

  auto module_writer_2 = std::make_unique<MinidumpModuleWriter>();
  module_writer_2->SetName(kModuleName2);
  module_writer_2->SetImageBaseAddress(kModuleBase2);
  module_writer_2->SetImageSize(kModuleSize2);

  auto codeview_pdb70_writer_2 =
      std::make_unique<MinidumpModuleCodeViewRecordPDB20Writer>();
  codeview_pdb70_writer_2->SetPDBName(kPDBName2);
  codeview_pdb70_writer_2->SetTimestampAndAge(kPDBTimestamp2, kPDBAge2);
  module_writer_2->SetCodeViewRecord(std::move(codeview_pdb70_writer_2));

  module_list_writer->AddModule(std::move(module_writer_2));

  ASSERT_TRUE(minidump_file_writer.AddStream(std::move(module_list_writer)));

  StringFile string_file;
  ASSERT_TRUE(minidump_file_writer.WriteEverything(&string_file));

  ASSERT_GT(string_file.string().size(),
            sizeof(MINIDUMP_HEADER) + sizeof(MINIDUMP_DIRECTORY) +
                sizeof(MINIDUMP_MODULE_LIST) + 1 * sizeof(MINIDUMP_MODULE));

  const MINIDUMP_MODULE_LIST* module_list = nullptr;
  ASSERT_NO_FATAL_FAILURE(
      GetModuleListStream(string_file.string(), &module_list));

  EXPECT_EQ(module_list->NumberOfModules, 3u);

  MINIDUMP_MODULE expected = {};

  {
    SCOPED_TRACE("module 0");

    expected.BaseOfImage = kModuleBase0;
    expected.SizeOfImage = kModuleSize0;

    ASSERT_NO_FATAL_FAILURE(ExpectModule(&expected,
                                         &module_list->Modules[0],
                                         string_file.string(),
                                         kModuleName0,
                                         kPDBName0,
                                         &pdb_uuid_0,
                                         0,
                                         kPDBAge0,
                                         nullptr,
                                         0,
                                         false));
  }

  {
    SCOPED_TRACE("module 1");

    expected.BaseOfImage = kModuleBase1;
    expected.SizeOfImage = kModuleSize1;

    ASSERT_NO_FATAL_FAILURE(ExpectModule(&expected,
                                         &module_list->Modules[1],
                                         string_file.string(),
                                         kModuleName1,
                                         nullptr,
                                         nullptr,
                                         0,
                                         0,
                                         nullptr,
                                         0,
                                         false));
  }

  {
    SCOPED_TRACE("module 2");

    expected.BaseOfImage = kModuleBase2;
    expected.SizeOfImage = kModuleSize2;

    ASSERT_NO_FATAL_FAILURE(ExpectModule(&expected,
                                         &module_list->Modules[2],
                                         string_file.string(),
                                         kModuleName2,
                                         kPDBName2,
                                         nullptr,
                                         kPDBTimestamp2,
                                         kPDBAge2,
                                         nullptr,
                                         0,
                                         false));
  }
}

void InitializeTestModuleSnapshotFromMinidumpModule(
    TestModuleSnapshot* module_snapshot,
    const MINIDUMP_MODULE& minidump_module,
    const std::string& name,
    const std::string& pdb_name,
    const crashpad::UUID& uuid,
    uint32_t age) {
  module_snapshot->SetName(name);

  module_snapshot->SetAddressAndSize(minidump_module.BaseOfImage,
                                     minidump_module.SizeOfImage);
  module_snapshot->SetTimestamp(minidump_module.TimeDateStamp);
  module_snapshot->SetFileVersion(
      minidump_module.VersionInfo.dwFileVersionMS >> 16,
      minidump_module.VersionInfo.dwFileVersionMS & 0xffff,
      minidump_module.VersionInfo.dwFileVersionLS >> 16,
      minidump_module.VersionInfo.dwFileVersionLS & 0xffff);
  module_snapshot->SetSourceVersion(
      minidump_module.VersionInfo.dwProductVersionMS >> 16,
      minidump_module.VersionInfo.dwProductVersionMS & 0xffff,
      minidump_module.VersionInfo.dwProductVersionLS >> 16,
      minidump_module.VersionInfo.dwProductVersionLS & 0xffff);

  ModuleSnapshot::ModuleType module_type;
  switch (minidump_module.VersionInfo.dwFileType) {
    case VFT_APP:
      module_type = ModuleSnapshot::kModuleTypeExecutable;
      break;
    case VFT_DLL:
      module_type = ModuleSnapshot::kModuleTypeSharedLibrary;
      break;
    default:
      module_type = ModuleSnapshot::kModuleTypeUnknown;
      break;
  }
  module_snapshot->SetModuleType(module_type);

  module_snapshot->SetUUIDAndAge(uuid, age);
  module_snapshot->SetDebugFileName(pdb_name);
}

TEST(MinidumpModuleWriter, InitializeFromSnapshot) {
  MINIDUMP_MODULE expect_modules[3] = {};
  const char* module_paths[base::size(expect_modules)] = {};
  const char* module_pdbs[base::size(expect_modules)] = {};
  UUID uuids[base::size(expect_modules)] = {};
  uint32_t ages[base::size(expect_modules)] = {};

  expect_modules[0].BaseOfImage = 0x100101000;
  expect_modules[0].SizeOfImage = 0xf000;
  expect_modules[0].TimeDateStamp = 0x01234567;
  expect_modules[0].VersionInfo.dwFileVersionMS = 0x00010002;
  expect_modules[0].VersionInfo.dwFileVersionLS = 0x00030004;
  expect_modules[0].VersionInfo.dwProductVersionMS = 0x00050006;
  expect_modules[0].VersionInfo.dwProductVersionLS = 0x00070008;
  expect_modules[0].VersionInfo.dwFileType = VFT_APP;
  module_paths[0] = "/usr/bin/true";
  module_pdbs[0] = "true";
  static constexpr uint8_t kUUIDBytes0[16] = {0x00,
                                              0x11,
                                              0x22,
                                              0x33,
                                              0x44,
                                              0x55,
                                              0x66,
                                              0x77,
                                              0x88,
                                              0x99,
                                              0xaa,
                                              0xbb,
                                              0xcc,
                                              0xdd,
                                              0xee,
                                              0xff};
  uuids[0].InitializeFromBytes(kUUIDBytes0);
  ages[0] = 10;

  expect_modules[1].BaseOfImage = 0x200202000;
  expect_modules[1].SizeOfImage = 0x1e1000;
  expect_modules[1].TimeDateStamp = 0x89abcdef;
  expect_modules[1].VersionInfo.dwFileVersionMS = 0x0009000a;
  expect_modules[1].VersionInfo.dwFileVersionLS = 0x000b000c;
  expect_modules[1].VersionInfo.dwProductVersionMS = 0x000d000e;
  expect_modules[1].VersionInfo.dwProductVersionLS = 0x000f0000;
  expect_modules[1].VersionInfo.dwFileType = VFT_DLL;
  module_paths[1] = "/usr/lib/libSystem.B.dylib";
  module_pdbs[1] = "libSystem.B.dylib.pdb";
  static constexpr uint8_t kUUIDBytes1[16] = {0x00,
                                              0x01,
                                              0x02,
                                              0x03,
                                              0x04,
                                              0x05,
                                              0x06,
                                              0x07,
                                              0x08,
                                              0x09,
                                              0x0a,
                                              0x0b,
                                              0x0c,
                                              0x0d,
                                              0x0e,
                                              0x0f};
  uuids[1].InitializeFromBytes(kUUIDBytes1);
  ages[1] = 20;

  expect_modules[2].BaseOfImage = 0x300303000;
  expect_modules[2].SizeOfImage = 0x2d000;
  expect_modules[2].TimeDateStamp = 0x76543210;
  expect_modules[2].VersionInfo.dwFileVersionMS = 0x11112222;
  expect_modules[2].VersionInfo.dwFileVersionLS = 0x33334444;
  expect_modules[2].VersionInfo.dwProductVersionMS = 0x9999aaaa;
  expect_modules[2].VersionInfo.dwProductVersionLS = 0xbbbbcccc;
  expect_modules[2].VersionInfo.dwFileType = VFT_UNKNOWN;
  module_paths[2] = "/usr/lib/dyld";
  module_pdbs[2] = "/usr/lib/dyld.pdb";
  static constexpr uint8_t kUUIDBytes2[16] = {0xff,
                                              0xfe,
                                              0xfd,
                                              0xfc,
                                              0xfb,
                                              0xfa,
                                              0xf9,
                                              0xf8,
                                              0xf7,
                                              0xf6,
                                              0xf5,
                                              0xf4,
                                              0xf3,
                                              0xf2,
                                              0xf1,
                                              0xf0};
  uuids[2].InitializeFromBytes(kUUIDBytes2);
  ages[2] = 30;

  std::vector<std::unique_ptr<TestModuleSnapshot>> module_snapshots_owner;
  std::vector<const ModuleSnapshot*> module_snapshots;
  for (size_t index = 0; index < base::size(expect_modules); ++index) {
    module_snapshots_owner.push_back(std::make_unique<TestModuleSnapshot>());
    TestModuleSnapshot* module_snapshot = module_snapshots_owner.back().get();
    InitializeTestModuleSnapshotFromMinidumpModule(module_snapshot,
                                                   expect_modules[index],
                                                   module_paths[index],
                                                   module_pdbs[index],
                                                   uuids[index],
                                                   ages[index]);
    module_snapshots.push_back(module_snapshot);
  }

  auto module_list_writer = std::make_unique<MinidumpModuleListWriter>();
  module_list_writer->InitializeFromSnapshot(module_snapshots);

  MinidumpFileWriter minidump_file_writer;
  ASSERT_TRUE(minidump_file_writer.AddStream(std::move(module_list_writer)));

  StringFile string_file;
  ASSERT_TRUE(minidump_file_writer.WriteEverything(&string_file));

  const MINIDUMP_MODULE_LIST* module_list = nullptr;
  ASSERT_NO_FATAL_FAILURE(
      GetModuleListStream(string_file.string(), &module_list));

  ASSERT_EQ(module_list->NumberOfModules, 3u);

  for (size_t index = 0; index < module_list->NumberOfModules; ++index) {
    SCOPED_TRACE(base::StringPrintf("index %" PRIuS, index));
    ASSERT_NO_FATAL_FAILURE(ExpectModule(&expect_modules[index],
                                         &module_list->Modules[index],
                                         string_file.string(),
                                         module_paths[index],
                                         module_pdbs[index],
                                         &uuids[index],
                                         0,
                                         ages[index],
                                         nullptr,
                                         0,
                                         false));
  }
}

TEST(MinidumpModuleWriterDeathTest, NoModuleName) {
  MinidumpFileWriter minidump_file_writer;
  auto module_list_writer = std::make_unique<MinidumpModuleListWriter>();
  auto module_writer = std::make_unique<MinidumpModuleWriter>();
  module_list_writer->AddModule(std::move(module_writer));
  ASSERT_TRUE(minidump_file_writer.AddStream(std::move(module_list_writer)));

  StringFile string_file;
  ASSERT_DEATH_CHECK(minidump_file_writer.WriteEverything(&string_file),
                     "name_");
}

}  // namespace
}  // namespace test
}  // namespace crashpad
