// Copyright (c) 2011 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 <windows.h>
#include <winternl.h>

#include "base/base_switches.h"
#include "base/command_line.h"
#include "base/files/file_path.h"
#include "base/scoped_native_library.h"
#include "base/test/multiprocess_test.h"
#include "base/test/test_timeouts.h"
#include "base/win/scoped_handle.h"

#include "testing/gtest/include/gtest/gtest.h"
#include "testing/multiprocess_func_list.h"

namespace base {
namespace win {

namespace testing {
extern "C" bool __declspec(dllexport) RunTest();
}  // namespace testing

TEST(ScopedHandleTest, ScopedHandle) {
  // Any illegal error code will do. We just need to test that it is preserved
  // by ScopedHandle to avoid bug 528394.
  const DWORD magic_error = 0x12345678;

  HANDLE handle = ::CreateMutex(nullptr, false, nullptr);
  // Call SetLastError after creating the handle.
  ::SetLastError(magic_error);
  base::win::ScopedHandle handle_holder(handle);
  EXPECT_EQ(magic_error, ::GetLastError());

  // Create a new handle and then set LastError again.
  handle = ::CreateMutex(nullptr, false, nullptr);
  ::SetLastError(magic_error);
  handle_holder.Set(handle);
  EXPECT_EQ(magic_error, ::GetLastError());

  // Create a new handle and then set LastError again.
  handle = ::CreateMutex(nullptr, false, nullptr);
  base::win::ScopedHandle handle_source(handle);
  ::SetLastError(magic_error);
  handle_holder = std::move(handle_source);
  EXPECT_EQ(magic_error, ::GetLastError());
}

TEST(ScopedHandleTest, ActiveVerifierTrackedHasBeenClosed) {
  HANDLE handle = ::CreateMutex(nullptr, false, nullptr);
  ASSERT_NE(HANDLE(nullptr), handle);
  typedef NTSTATUS(WINAPI * NtCloseFunc)(HANDLE);
  NtCloseFunc ntclose = reinterpret_cast<NtCloseFunc>(
      GetProcAddress(GetModuleHandle(L"ntdll.dll"), "NtClose"));
  ASSERT_NE(nullptr, ntclose);

  ASSERT_DEATH({
    base::win::ScopedHandle handle_holder(handle);
    ntclose(handle);
    // Destructing a ScopedHandle with an illegally closed handle should fail.
  }, "");
}

TEST(ScopedHandleTest, ActiveVerifierDoubleTracking) {
  HANDLE handle = ::CreateMutex(nullptr, false, nullptr);
  ASSERT_NE(HANDLE(nullptr), handle);

  base::win::ScopedHandle handle_holder(handle);

  ASSERT_DEATH({
    base::win::ScopedHandle handle_holder2(handle);
  }, "");
}

TEST(ScopedHandleTest, ActiveVerifierWrongOwner) {
  HANDLE handle = ::CreateMutex(nullptr, false, nullptr);
  ASSERT_NE(HANDLE(nullptr), handle);

  base::win::ScopedHandle handle_holder(handle);
  ASSERT_DEATH({
    base::win::ScopedHandle handle_holder2;
    handle_holder2.handle_ = handle;
  }, "");
  ASSERT_TRUE(handle_holder.IsValid());
  handle_holder.Close();
}

TEST(ScopedHandleTest, ActiveVerifierUntrackedHandle) {
  HANDLE handle = ::CreateMutex(nullptr, false, nullptr);
  ASSERT_NE(HANDLE(nullptr), handle);

  ASSERT_DEATH({
    base::win::ScopedHandle handle_holder;
    handle_holder.handle_ = handle;
  }, "");

  ASSERT_TRUE(::CloseHandle(handle));
}

// Under ASan, the multi-process test crashes during process shutdown for
// unknown reasons. Disable it for now. http://crbug.com/685262
#if defined(ADDRESS_SANITIZER)
#define MAYBE_MultiProcess DISABLED_MultiProcess
#else
#define MAYBE_MultiProcess MultiProcess
#endif

TEST(ScopedHandleTest, MAYBE_MultiProcess) {
  // Initializing ICU in the child process causes a scoped handle to be created
  // before the test gets a chance to test the race condition, so disable ICU
  // for the child process here.
  CommandLine command_line(base::GetMultiProcessTestChildBaseCommandLine());
  command_line.AppendSwitch(switches::kTestDoNotInitializeIcu);

  base::Process test_child_process = base::SpawnMultiProcessTestChild(
      "ActiveVerifierChildProcess", command_line, LaunchOptions());

  int rv = -1;
  ASSERT_TRUE(test_child_process.WaitForExitWithTimeout(
      TestTimeouts::action_timeout(), &rv));
  EXPECT_EQ(0, rv);
}

MULTIPROCESS_TEST_MAIN(ActiveVerifierChildProcess) {
  ScopedNativeLibrary module(FilePath(L"scoped_handle_test_dll.dll"));

  if (!module.is_valid())
    return 1;
  auto run_test_function = reinterpret_cast<decltype(&testing::RunTest)>(
      module.GetFunctionPointer("RunTest"));
  if (!run_test_function)
    return 1;
  if (!run_test_function())
    return 1;

  return 0;
}

}  // namespace win
}  // namespace base
