mirror of
https://github.com/intrepidcs/libicsneo.git
synced 2026-08-05 17:38:35 +02:00
ThirdParty: Update included gtest
This commit is contained in:
@@ -32,6 +32,7 @@
|
||||
|
||||
#include "gtest/gtest-death-test.h"
|
||||
|
||||
#include <functional>
|
||||
#include <utility>
|
||||
|
||||
#include "gtest/internal/gtest-port.h"
|
||||
@@ -68,6 +69,7 @@
|
||||
# include <lib/fdio/fd.h>
|
||||
# include <lib/fdio/io.h>
|
||||
# include <lib/fdio/spawn.h>
|
||||
# include <lib/zx/channel.h>
|
||||
# include <lib/zx/port.h>
|
||||
# include <lib/zx/process.h>
|
||||
# include <lib/zx/socket.h>
|
||||
@@ -121,8 +123,8 @@ GTEST_DEFINE_string_(
|
||||
"Indicates the file, line number, temporal index of "
|
||||
"the single death test to run, and a file descriptor to "
|
||||
"which a success code may be sent, all separated by "
|
||||
"the '|' characters. This flag is specified if and only if the current "
|
||||
"process is a sub-process launched for running a thread-safe "
|
||||
"the '|' characters. This flag is specified if and only if the "
|
||||
"current process is a sub-process launched for running a thread-safe "
|
||||
"death test. FOR INTERNAL USE ONLY.");
|
||||
} // namespace internal
|
||||
|
||||
@@ -246,7 +248,7 @@ static std::string DeathTestThreadWarning(size_t thread_count) {
|
||||
msg << "detected " << thread_count << " threads.";
|
||||
}
|
||||
msg << " See "
|
||||
"https://github.com/google/googletest/blob/master/googletest/docs/"
|
||||
"https://github.com/google/googletest/blob/master/docs/"
|
||||
"advanced.md#death-tests-and-threads"
|
||||
<< " for more explanation and suggested solutions, especially if"
|
||||
<< " this is the last message you see before your test times out.";
|
||||
@@ -562,8 +564,8 @@ static ::std::string FormatDeathTestOutput(const ::std::string& output) {
|
||||
// status_ok: true if exit_status is acceptable in the context of
|
||||
// this particular death test, which fails if it is false
|
||||
//
|
||||
// Returns true iff all of the above conditions are met. Otherwise, the
|
||||
// first failing condition, in the order given above, is the one that is
|
||||
// Returns true if and only if all of the above conditions are met. Otherwise,
|
||||
// the first failing condition, in the order given above, is the one that is
|
||||
// reported. Also sets the last death test message string.
|
||||
bool DeathTestImpl::Passed(bool status_ok) {
|
||||
if (!spawned())
|
||||
@@ -831,7 +833,7 @@ class FuchsiaDeathTest : public DeathTestImpl {
|
||||
std::string captured_stderr_;
|
||||
|
||||
zx::process child_process_;
|
||||
zx::port port_;
|
||||
zx::channel exception_channel_;
|
||||
zx::socket stderr_socket_;
|
||||
};
|
||||
|
||||
@@ -863,7 +865,7 @@ class Arguments {
|
||||
}
|
||||
|
||||
int size() {
|
||||
return args_.size() - 1;
|
||||
return static_cast<int>(args_.size()) - 1;
|
||||
}
|
||||
|
||||
private:
|
||||
@@ -876,41 +878,50 @@ class Arguments {
|
||||
int FuchsiaDeathTest::Wait() {
|
||||
const int kProcessKey = 0;
|
||||
const int kSocketKey = 1;
|
||||
const int kExceptionKey = 2;
|
||||
|
||||
if (!spawned())
|
||||
return 0;
|
||||
|
||||
// Register to wait for the child process to terminate.
|
||||
// Create a port to wait for socket/task/exception events.
|
||||
zx_status_t status_zx;
|
||||
status_zx = child_process_.wait_async(
|
||||
port_, kProcessKey, ZX_PROCESS_TERMINATED, ZX_WAIT_ASYNC_ONCE);
|
||||
zx::port port;
|
||||
status_zx = zx::port::create(0, &port);
|
||||
GTEST_DEATH_TEST_CHECK_(status_zx == ZX_OK);
|
||||
|
||||
// Register to wait for the child process to terminate.
|
||||
status_zx = child_process_.wait_async(
|
||||
port, kProcessKey, ZX_PROCESS_TERMINATED, 0);
|
||||
GTEST_DEATH_TEST_CHECK_(status_zx == ZX_OK);
|
||||
|
||||
// Register to wait for the socket to be readable or closed.
|
||||
status_zx = stderr_socket_.wait_async(
|
||||
port_, kSocketKey, ZX_SOCKET_READABLE | ZX_SOCKET_PEER_CLOSED,
|
||||
ZX_WAIT_ASYNC_ONCE);
|
||||
port, kSocketKey, ZX_SOCKET_READABLE | ZX_SOCKET_PEER_CLOSED, 0);
|
||||
GTEST_DEATH_TEST_CHECK_(status_zx == ZX_OK);
|
||||
|
||||
// Register to wait for an exception.
|
||||
status_zx = exception_channel_.wait_async(
|
||||
port, kExceptionKey, ZX_CHANNEL_READABLE, 0);
|
||||
GTEST_DEATH_TEST_CHECK_(status_zx == ZX_OK);
|
||||
|
||||
bool process_terminated = false;
|
||||
bool socket_closed = false;
|
||||
do {
|
||||
zx_port_packet_t packet = {};
|
||||
status_zx = port_.wait(zx::time::infinite(), &packet);
|
||||
status_zx = port.wait(zx::time::infinite(), &packet);
|
||||
GTEST_DEATH_TEST_CHECK_(status_zx == ZX_OK);
|
||||
|
||||
if (packet.key == kProcessKey) {
|
||||
if (ZX_PKT_IS_EXCEPTION(packet.type)) {
|
||||
// Process encountered an exception. Kill it directly rather than
|
||||
// letting other handlers process the event. We will get a second
|
||||
// kProcessKey event when the process actually terminates.
|
||||
status_zx = child_process_.kill();
|
||||
GTEST_DEATH_TEST_CHECK_(status_zx == ZX_OK);
|
||||
} else {
|
||||
// Process terminated.
|
||||
GTEST_DEATH_TEST_CHECK_(ZX_PKT_IS_SIGNAL_ONE(packet.type));
|
||||
GTEST_DEATH_TEST_CHECK_(packet.signal.observed & ZX_PROCESS_TERMINATED);
|
||||
process_terminated = true;
|
||||
}
|
||||
if (packet.key == kExceptionKey) {
|
||||
// Process encountered an exception. Kill it directly rather than
|
||||
// letting other handlers process the event. We will get a kProcessKey
|
||||
// event when the process actually terminates.
|
||||
status_zx = child_process_.kill();
|
||||
GTEST_DEATH_TEST_CHECK_(status_zx == ZX_OK);
|
||||
} else if (packet.key == kProcessKey) {
|
||||
// Process terminated.
|
||||
GTEST_DEATH_TEST_CHECK_(ZX_PKT_IS_SIGNAL_ONE(packet.type));
|
||||
GTEST_DEATH_TEST_CHECK_(packet.signal.observed & ZX_PROCESS_TERMINATED);
|
||||
process_terminated = true;
|
||||
} else if (packet.key == kSocketKey) {
|
||||
GTEST_DEATH_TEST_CHECK_(ZX_PKT_IS_SIGNAL_ONE(packet.type));
|
||||
if (packet.signal.observed & ZX_SOCKET_READABLE) {
|
||||
@@ -930,8 +941,7 @@ int FuchsiaDeathTest::Wait() {
|
||||
} else {
|
||||
GTEST_DEATH_TEST_CHECK_(status_zx == ZX_ERR_SHOULD_WAIT);
|
||||
status_zx = stderr_socket_.wait_async(
|
||||
port_, kSocketKey, ZX_SOCKET_READABLE | ZX_SOCKET_PEER_CLOSED,
|
||||
ZX_WAIT_ASYNC_ONCE);
|
||||
port, kSocketKey, ZX_SOCKET_READABLE | ZX_SOCKET_PEER_CLOSED, 0);
|
||||
GTEST_DEATH_TEST_CHECK_(status_zx == ZX_OK);
|
||||
}
|
||||
} else {
|
||||
@@ -944,12 +954,12 @@ int FuchsiaDeathTest::Wait() {
|
||||
ReadAndInterpretStatusByte();
|
||||
|
||||
zx_info_process_t buffer;
|
||||
status_zx = child_process_.get_info(
|
||||
ZX_INFO_PROCESS, &buffer, sizeof(buffer), nullptr, nullptr);
|
||||
status_zx = child_process_.get_info(ZX_INFO_PROCESS, &buffer, sizeof(buffer),
|
||||
nullptr, nullptr);
|
||||
GTEST_DEATH_TEST_CHECK_(status_zx == ZX_OK);
|
||||
|
||||
GTEST_DEATH_TEST_CHECK_(buffer.exited);
|
||||
set_status(buffer.return_code);
|
||||
GTEST_DEATH_TEST_CHECK_(buffer.flags & ZX_INFO_PROCESS_FLAG_EXITED);
|
||||
set_status(static_cast<int>(buffer.return_code));
|
||||
return status();
|
||||
}
|
||||
|
||||
@@ -1033,12 +1043,11 @@ DeathTest::TestRole FuchsiaDeathTest::AssumeRole() {
|
||||
child_job, ZX_JOB_POL_RELATIVE, ZX_JOB_POL_BASIC, &policy, 1);
|
||||
GTEST_DEATH_TEST_CHECK_(status == ZX_OK);
|
||||
|
||||
// Create an exception port and attach it to the |child_job|, to allow
|
||||
// Create an exception channel attached to the |child_job|, to allow
|
||||
// us to suppress the system default exception handler from firing.
|
||||
status = zx::port::create(0, &port_);
|
||||
GTEST_DEATH_TEST_CHECK_(status == ZX_OK);
|
||||
status = zx_task_bind_exception_port(
|
||||
child_job, port_.get(), 0 /* key */, 0 /*options */);
|
||||
status =
|
||||
zx_task_create_exception_channel(
|
||||
child_job, 0, exception_channel_.reset_and_get_address());
|
||||
GTEST_DEATH_TEST_CHECK_(status == ZX_OK);
|
||||
|
||||
// Spawn the child process.
|
||||
@@ -1215,21 +1224,9 @@ struct ExecDeathTestArgs {
|
||||
int close_fd; // File descriptor to close; the read end of a pipe
|
||||
};
|
||||
|
||||
# if GTEST_OS_MAC
|
||||
inline char** GetEnviron() {
|
||||
// When Google Test is built as a framework on MacOS X, the environ variable
|
||||
// is unavailable. Apple's documentation (man environ) recommends using
|
||||
// _NSGetEnviron() instead.
|
||||
return *_NSGetEnviron();
|
||||
}
|
||||
# else
|
||||
// Some POSIX platforms expect you to declare environ. extern "C" makes
|
||||
// it reside in the global namespace.
|
||||
# if GTEST_OS_QNX
|
||||
extern "C" char** environ;
|
||||
inline char** GetEnviron() { return environ; }
|
||||
# endif // GTEST_OS_MAC
|
||||
|
||||
# if !GTEST_OS_QNX
|
||||
# else // GTEST_OS_QNX
|
||||
// The main function for a threadsafe-style death test child process.
|
||||
// This function is called in a clone()-ed process and thus must avoid
|
||||
// any potentially unsafe operations like malloc or libc functions.
|
||||
@@ -1249,18 +1246,18 @@ static int ExecDeathTestChildMain(void* child_arg) {
|
||||
return EXIT_FAILURE;
|
||||
}
|
||||
|
||||
// We can safely call execve() as it's a direct system call. We
|
||||
// We can safely call execv() as it's almost a direct system call. We
|
||||
// cannot use execvp() as it's a libc function and thus potentially
|
||||
// unsafe. Since execve() doesn't search the PATH, the user must
|
||||
// unsafe. Since execv() doesn't search the PATH, the user must
|
||||
// invoke the test program via a valid path that contains at least
|
||||
// one path separator.
|
||||
execve(args->argv[0], args->argv, GetEnviron());
|
||||
DeathTestAbort(std::string("execve(") + args->argv[0] + ", ...) in " +
|
||||
execv(args->argv[0], args->argv);
|
||||
DeathTestAbort(std::string("execv(") + args->argv[0] + ", ...) in " +
|
||||
original_dir + " failed: " +
|
||||
GetLastErrnoDescription());
|
||||
return EXIT_FAILURE;
|
||||
}
|
||||
# endif // !GTEST_OS_QNX
|
||||
# endif // GTEST_OS_QNX
|
||||
|
||||
# if GTEST_HAS_CLONE
|
||||
// Two utility routines that together determine the direction the stack
|
||||
@@ -1274,19 +1271,24 @@ static int ExecDeathTestChildMain(void* child_arg) {
|
||||
// correct answer.
|
||||
static void StackLowerThanAddress(const void* ptr,
|
||||
bool* result) GTEST_NO_INLINE_;
|
||||
// Make sure sanitizers do not tamper with the stack here.
|
||||
// Ideally, we want to use `__builtin_frame_address` instead of a local variable
|
||||
// address with sanitizer disabled, but it does not work when the
|
||||
// compiler optimizes the stack frame out, which happens on PowerPC targets.
|
||||
// HWAddressSanitizer add a random tag to the MSB of the local variable address,
|
||||
// making comparison result unpredictable.
|
||||
GTEST_ATTRIBUTE_NO_SANITIZE_ADDRESS_
|
||||
GTEST_ATTRIBUTE_NO_SANITIZE_HWADDRESS_
|
||||
static void StackLowerThanAddress(const void* ptr, bool* result) {
|
||||
int dummy;
|
||||
*result = (&dummy < ptr);
|
||||
int dummy = 0;
|
||||
*result = std::less<const void*>()(&dummy, ptr);
|
||||
}
|
||||
|
||||
// Make sure AddressSanitizer does not tamper with the stack here.
|
||||
GTEST_ATTRIBUTE_NO_SANITIZE_ADDRESS_
|
||||
GTEST_ATTRIBUTE_NO_SANITIZE_HWADDRESS_
|
||||
static bool StackGrowsDown() {
|
||||
int dummy;
|
||||
int dummy = 0;
|
||||
bool result;
|
||||
StackLowerThanAddress(&dummy, &result);
|
||||
return result;
|
||||
@@ -1329,8 +1331,7 @@ static pid_t ExecDeathTestSpawnChild(char* const* argv, int close_fd) {
|
||||
fd_flags | FD_CLOEXEC));
|
||||
struct inheritance inherit = {0};
|
||||
// spawn is a system call.
|
||||
child_pid =
|
||||
spawn(args.argv[0], 0, nullptr, &inherit, args.argv, GetEnviron());
|
||||
child_pid = spawn(args.argv[0], 0, nullptr, &inherit, args.argv, environ);
|
||||
// Restores the current working directory.
|
||||
GTEST_DEATH_TEST_CHECK_(fchdir(cwd_fd) != -1);
|
||||
GTEST_DEATH_TEST_CHECK_SYSCALL_(close(cwd_fd));
|
||||
@@ -1354,7 +1355,7 @@ static pid_t ExecDeathTestSpawnChild(char* const* argv, int close_fd) {
|
||||
|
||||
if (!use_fork) {
|
||||
static const bool stack_grows_down = StackGrowsDown();
|
||||
const auto stack_size = static_cast<size_t>(getpagesize());
|
||||
const auto stack_size = static_cast<size_t>(getpagesize() * 2);
|
||||
// MMAP_ANONYMOUS is not defined on Mac, so we use MAP_ANON instead.
|
||||
void* const stack = mmap(nullptr, stack_size, PROT_READ | PROT_WRITE,
|
||||
MAP_ANON | MAP_PRIVATE, -1, 0);
|
||||
|
||||
+18
-28
@@ -92,9 +92,10 @@ static bool IsPathSeparator(char c) {
|
||||
|
||||
// Returns the current working directory, or "" if unsuccessful.
|
||||
FilePath FilePath::GetCurrentDir() {
|
||||
#if GTEST_OS_WINDOWS_MOBILE || GTEST_OS_WINDOWS_PHONE || \
|
||||
GTEST_OS_WINDOWS_RT || ARDUINO
|
||||
// Windows CE and Arduino don't have a current directory, so we just return
|
||||
#if GTEST_OS_WINDOWS_MOBILE || GTEST_OS_WINDOWS_PHONE || \
|
||||
GTEST_OS_WINDOWS_RT || GTEST_OS_ESP8266 || GTEST_OS_ESP32 || \
|
||||
GTEST_OS_XTENSA
|
||||
// These platforms do not have a current directory, so we just return
|
||||
// something reasonable.
|
||||
return FilePath(kCurrentDirectoryString);
|
||||
#elif GTEST_OS_WINDOWS
|
||||
@@ -209,7 +210,7 @@ bool FilePath::FileOrDirectoryExists() const {
|
||||
delete [] unicode;
|
||||
return attributes != kInvalidFileAttributes;
|
||||
#else
|
||||
posix::StatStruct file_stat;
|
||||
posix::StatStruct file_stat{};
|
||||
return posix::Stat(pathname_.c_str(), &file_stat) == 0;
|
||||
#endif // GTEST_OS_WINDOWS_MOBILE
|
||||
}
|
||||
@@ -236,7 +237,7 @@ bool FilePath::DirectoryExists() const {
|
||||
result = true;
|
||||
}
|
||||
#else
|
||||
posix::StatStruct file_stat;
|
||||
posix::StatStruct file_stat{};
|
||||
result = posix::Stat(path.c_str(), &file_stat) == 0 &&
|
||||
posix::IsDir(file_stat);
|
||||
#endif // GTEST_OS_WINDOWS_MOBILE
|
||||
@@ -323,6 +324,9 @@ bool FilePath::CreateFolder() const {
|
||||
delete [] unicode;
|
||||
#elif GTEST_OS_WINDOWS
|
||||
int result = _mkdir(pathname_.c_str());
|
||||
#elif GTEST_OS_ESP8266 || GTEST_OS_XTENSA
|
||||
// do nothing
|
||||
int result = 0;
|
||||
#else
|
||||
int result = mkdir(pathname_.c_str(), 0777);
|
||||
#endif // GTEST_OS_WINDOWS_MOBILE
|
||||
@@ -346,33 +350,19 @@ FilePath FilePath::RemoveTrailingPathSeparator() const {
|
||||
// For example, "bar///foo" becomes "bar/foo". Does not eliminate other
|
||||
// redundancies that might be in a pathname involving "." or "..".
|
||||
void FilePath::Normalize() {
|
||||
if (pathname_.c_str() == nullptr) {
|
||||
pathname_ = "";
|
||||
return;
|
||||
}
|
||||
const char* src = pathname_.c_str();
|
||||
char* const dest = new char[pathname_.length() + 1];
|
||||
char* dest_ptr = dest;
|
||||
memset(dest_ptr, 0, pathname_.length() + 1);
|
||||
auto out = pathname_.begin();
|
||||
|
||||
while (*src != '\0') {
|
||||
*dest_ptr = *src;
|
||||
if (!IsPathSeparator(*src)) {
|
||||
src++;
|
||||
for (const char character : pathname_) {
|
||||
if (!IsPathSeparator(character)) {
|
||||
*(out++) = character;
|
||||
} else if (out == pathname_.begin() || *std::prev(out) != kPathSeparator) {
|
||||
*(out++) = kPathSeparator;
|
||||
} else {
|
||||
#if GTEST_HAS_ALT_PATH_SEP_
|
||||
if (*dest_ptr == kAlternatePathSeparator) {
|
||||
*dest_ptr = kPathSeparator;
|
||||
}
|
||||
#endif
|
||||
while (IsPathSeparator(*src))
|
||||
src++;
|
||||
continue;
|
||||
}
|
||||
dest_ptr++;
|
||||
}
|
||||
*dest_ptr = '\0';
|
||||
pathname_ = dest;
|
||||
delete[] dest;
|
||||
|
||||
pathname_.erase(out, pathname_.end());
|
||||
}
|
||||
|
||||
} // namespace internal
|
||||
|
||||
@@ -31,8 +31,8 @@
|
||||
// This file contains purely Google Test's internal implementation. Please
|
||||
// DO NOT #INCLUDE IT IN A USER PROGRAM.
|
||||
|
||||
#ifndef GTEST_SRC_GTEST_INTERNAL_INL_H_
|
||||
#define GTEST_SRC_GTEST_INTERNAL_INL_H_
|
||||
#ifndef GOOGLETEST_SRC_GTEST_INTERNAL_INL_H_
|
||||
#define GOOGLETEST_SRC_GTEST_INTERNAL_INL_H_
|
||||
|
||||
#ifndef _WIN32_WCE
|
||||
# include <errno.h>
|
||||
@@ -42,6 +42,7 @@
|
||||
#include <string.h> // For memmove.
|
||||
|
||||
#include <algorithm>
|
||||
#include <cstdint>
|
||||
#include <memory>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
@@ -83,9 +84,11 @@ const char kAlsoRunDisabledTestsFlag[] = "also_run_disabled_tests";
|
||||
const char kBreakOnFailureFlag[] = "break_on_failure";
|
||||
const char kCatchExceptionsFlag[] = "catch_exceptions";
|
||||
const char kColorFlag[] = "color";
|
||||
const char kFailFast[] = "fail_fast";
|
||||
const char kFilterFlag[] = "filter";
|
||||
const char kListTestsFlag[] = "list_tests";
|
||||
const char kOutputFlag[] = "output";
|
||||
const char kBriefFlag[] = "brief";
|
||||
const char kPrintTimeFlag[] = "print_time";
|
||||
const char kPrintUTF8Flag[] = "print_utf8";
|
||||
const char kRandomSeedFlag[] = "random_seed";
|
||||
@@ -99,14 +102,14 @@ const char kFlagfileFlag[] = "flagfile";
|
||||
// A valid random seed must be in [1, kMaxRandomSeed].
|
||||
const int kMaxRandomSeed = 99999;
|
||||
|
||||
// g_help_flag is true iff the --help flag or an equivalent form is
|
||||
// specified on the command line.
|
||||
// g_help_flag is true if and only if the --help flag or an equivalent form
|
||||
// is specified on the command line.
|
||||
GTEST_API_ extern bool g_help_flag;
|
||||
|
||||
// Returns the current time in milliseconds.
|
||||
GTEST_API_ TimeInMillis GetTimeInMillis();
|
||||
|
||||
// Returns true iff Google Test should use colors in the output.
|
||||
// Returns true if and only if Google Test should use colors in the output.
|
||||
GTEST_API_ bool ShouldUseColor(bool stdout_is_tty);
|
||||
|
||||
// Formats the given time in milliseconds as seconds.
|
||||
@@ -123,11 +126,11 @@ GTEST_API_ std::string FormatEpochTimeInMillisAsIso8601(TimeInMillis ms);
|
||||
// On success, stores the value of the flag in *value, and returns
|
||||
// true. On failure, returns false without changing *value.
|
||||
GTEST_API_ bool ParseInt32Flag(
|
||||
const char* str, const char* flag, Int32* value);
|
||||
const char* str, const char* flag, int32_t* value);
|
||||
|
||||
// Returns a random seed in range [1, kMaxRandomSeed] based on the
|
||||
// given --gtest_random_seed flag value.
|
||||
inline int GetRandomSeedFromFlag(Int32 random_seed_flag) {
|
||||
inline int GetRandomSeedFromFlag(int32_t random_seed_flag) {
|
||||
const unsigned int raw_seed = (random_seed_flag == 0) ?
|
||||
static_cast<unsigned int>(GetTimeInMillis()) :
|
||||
static_cast<unsigned int>(random_seed_flag);
|
||||
@@ -163,10 +166,12 @@ class GTestFlagSaver {
|
||||
color_ = GTEST_FLAG(color);
|
||||
death_test_style_ = GTEST_FLAG(death_test_style);
|
||||
death_test_use_fork_ = GTEST_FLAG(death_test_use_fork);
|
||||
fail_fast_ = GTEST_FLAG(fail_fast);
|
||||
filter_ = GTEST_FLAG(filter);
|
||||
internal_run_death_test_ = GTEST_FLAG(internal_run_death_test);
|
||||
list_tests_ = GTEST_FLAG(list_tests);
|
||||
output_ = GTEST_FLAG(output);
|
||||
brief_ = GTEST_FLAG(brief);
|
||||
print_time_ = GTEST_FLAG(print_time);
|
||||
print_utf8_ = GTEST_FLAG(print_utf8);
|
||||
random_seed_ = GTEST_FLAG(random_seed);
|
||||
@@ -186,9 +191,11 @@ class GTestFlagSaver {
|
||||
GTEST_FLAG(death_test_style) = death_test_style_;
|
||||
GTEST_FLAG(death_test_use_fork) = death_test_use_fork_;
|
||||
GTEST_FLAG(filter) = filter_;
|
||||
GTEST_FLAG(fail_fast) = fail_fast_;
|
||||
GTEST_FLAG(internal_run_death_test) = internal_run_death_test_;
|
||||
GTEST_FLAG(list_tests) = list_tests_;
|
||||
GTEST_FLAG(output) = output_;
|
||||
GTEST_FLAG(brief) = brief_;
|
||||
GTEST_FLAG(print_time) = print_time_;
|
||||
GTEST_FLAG(print_utf8) = print_utf8_;
|
||||
GTEST_FLAG(random_seed) = random_seed_;
|
||||
@@ -207,16 +214,18 @@ class GTestFlagSaver {
|
||||
std::string color_;
|
||||
std::string death_test_style_;
|
||||
bool death_test_use_fork_;
|
||||
bool fail_fast_;
|
||||
std::string filter_;
|
||||
std::string internal_run_death_test_;
|
||||
bool list_tests_;
|
||||
std::string output_;
|
||||
bool brief_;
|
||||
bool print_time_;
|
||||
bool print_utf8_;
|
||||
internal::Int32 random_seed_;
|
||||
internal::Int32 repeat_;
|
||||
int32_t random_seed_;
|
||||
int32_t repeat_;
|
||||
bool shuffle_;
|
||||
internal::Int32 stack_trace_depth_;
|
||||
int32_t stack_trace_depth_;
|
||||
std::string stream_result_to_;
|
||||
bool throw_on_failure_;
|
||||
} GTEST_ATTRIBUTE_UNUSED_;
|
||||
@@ -227,7 +236,7 @@ class GTestFlagSaver {
|
||||
// If the code_point is not a valid Unicode code point
|
||||
// (i.e. outside of Unicode range U+0 to U+10FFFF) it will be converted
|
||||
// to "(Invalid Unicode 0xXXXXXXXX)".
|
||||
GTEST_API_ std::string CodePointToUtf8(UInt32 code_point);
|
||||
GTEST_API_ std::string CodePointToUtf8(uint32_t code_point);
|
||||
|
||||
// Converts a wide string to a narrow string in UTF-8 encoding.
|
||||
// The wide string is assumed to have the following encoding:
|
||||
@@ -260,14 +269,14 @@ GTEST_API_ bool ShouldShard(const char* total_shards_str,
|
||||
const char* shard_index_str,
|
||||
bool in_subprocess_for_death_test);
|
||||
|
||||
// Parses the environment variable var as an Int32. If it is unset,
|
||||
// returns default_val. If it is not an Int32, prints an error and
|
||||
// Parses the environment variable var as a 32-bit integer. If it is unset,
|
||||
// returns default_val. If it is not a 32-bit integer, prints an error and
|
||||
// and aborts.
|
||||
GTEST_API_ Int32 Int32FromEnvOrDie(const char* env_var, Int32 default_val);
|
||||
GTEST_API_ int32_t Int32FromEnvOrDie(const char* env_var, int32_t default_val);
|
||||
|
||||
// Given the total number of shards, the shard index, and the test id,
|
||||
// returns true iff the test should be run on this shard. The test id is
|
||||
// some arbitrary but unique non-negative integer assigned to each test
|
||||
// returns true if and only if the test should be run on this shard. The test id
|
||||
// is some arbitrary but unique non-negative integer assigned to each test
|
||||
// method. Assumes that 0 <= shard_index < total_shards.
|
||||
GTEST_API_ bool ShouldRunTestOnShard(
|
||||
int total_shards, int shard_index, int test_id);
|
||||
@@ -323,7 +332,7 @@ void ShuffleRange(internal::Random* random, int begin, int end,
|
||||
const int last_in_range = begin + range_width - 1;
|
||||
const int selected =
|
||||
begin +
|
||||
static_cast<int>(random->Generate(static_cast<UInt32>(range_width)));
|
||||
static_cast<int>(random->Generate(static_cast<uint32_t>(range_width)));
|
||||
std::swap((*v)[static_cast<size_t>(selected)],
|
||||
(*v)[static_cast<size_t>(last_in_range)]);
|
||||
}
|
||||
@@ -352,7 +361,7 @@ class TestPropertyKeyIs {
|
||||
// TestPropertyKeyIs has NO default constructor.
|
||||
explicit TestPropertyKeyIs(const std::string& key) : key_(key) {}
|
||||
|
||||
// Returns true iff the test name of test property matches on key_.
|
||||
// Returns true if and only if the test name of test property matches on key_.
|
||||
bool operator()(const TestProperty& test_property) const {
|
||||
return test_property.key() == key_;
|
||||
}
|
||||
@@ -385,15 +394,8 @@ class GTEST_API_ UnitTestOptions {
|
||||
|
||||
// Functions for processing the gtest_filter flag.
|
||||
|
||||
// Returns true iff the wildcard pattern matches the string. The
|
||||
// first ':' or '\0' character in pattern marks the end of it.
|
||||
//
|
||||
// This recursive algorithm isn't very efficient, but is clear and
|
||||
// works well enough for matching test names, which are short.
|
||||
static bool PatternMatchesString(const char *pattern, const char *str);
|
||||
|
||||
// Returns true iff the user-specified filter matches the test suite
|
||||
// name and the test name.
|
||||
// Returns true if and only if the user-specified filter matches the test
|
||||
// suite name and the test name.
|
||||
static bool FilterMatchesTest(const std::string& test_suite_name,
|
||||
const std::string& test_name);
|
||||
|
||||
@@ -577,11 +579,12 @@ class GTEST_API_ UnitTestImpl {
|
||||
// Gets the elapsed time, in milliseconds.
|
||||
TimeInMillis elapsed_time() const { return elapsed_time_; }
|
||||
|
||||
// Returns true iff the unit test passed (i.e. all test suites passed).
|
||||
// Returns true if and only if the unit test passed (i.e. all test suites
|
||||
// passed).
|
||||
bool Passed() const { return !Failed(); }
|
||||
|
||||
// Returns true iff the unit test failed (i.e. some test suite failed
|
||||
// or something outside of all tests failed).
|
||||
// Returns true if and only if the unit test failed (i.e. some test suite
|
||||
// failed or something outside of all tests failed).
|
||||
bool Failed() const {
|
||||
return failed_test_suite_count() > 0 || ad_hoc_test_result()->Failed();
|
||||
}
|
||||
@@ -645,10 +648,10 @@ class GTEST_API_ UnitTestImpl {
|
||||
// Arguments:
|
||||
//
|
||||
// test_suite_name: name of the test suite
|
||||
// type_param: the name of the test's type parameter, or NULL if
|
||||
// this is not a typed or a type-parameterized test.
|
||||
// set_up_tc: pointer to the function that sets up the test suite
|
||||
// tear_down_tc: pointer to the function that tears down the test suite
|
||||
// type_param: the name of the test's type parameter, or NULL if
|
||||
// this is not a typed or a type-parameterized test.
|
||||
// set_up_tc: pointer to the function that sets up the test suite
|
||||
// tear_down_tc: pointer to the function that tears down the test suite
|
||||
TestSuite* GetTestSuite(const char* test_suite_name, const char* type_param,
|
||||
internal::SetUpTestSuiteFunc set_up_tc,
|
||||
internal::TearDownTestSuiteFunc tear_down_tc);
|
||||
@@ -672,6 +675,7 @@ class GTEST_API_ UnitTestImpl {
|
||||
void AddTestInfo(internal::SetUpTestSuiteFunc set_up_tc,
|
||||
internal::TearDownTestSuiteFunc tear_down_tc,
|
||||
TestInfo* test_info) {
|
||||
#if GTEST_HAS_DEATH_TEST
|
||||
// In order to support thread-safe death tests, we need to
|
||||
// remember the original working directory when the test program
|
||||
// was first invoked. We cannot do this in RUN_ALL_TESTS(), as
|
||||
@@ -684,6 +688,7 @@ class GTEST_API_ UnitTestImpl {
|
||||
GTEST_CHECK_(!original_working_dir_.IsEmpty())
|
||||
<< "Failed to get the current working directory.";
|
||||
}
|
||||
#endif // GTEST_HAS_DEATH_TEST
|
||||
|
||||
GetTestSuite(test_info->test_suite_name(), test_info->type_param(),
|
||||
set_up_tc, tear_down_tc)
|
||||
@@ -696,6 +701,17 @@ class GTEST_API_ UnitTestImpl {
|
||||
return parameterized_test_registry_;
|
||||
}
|
||||
|
||||
std::set<std::string>* ignored_parameterized_test_suites() {
|
||||
return &ignored_parameterized_test_suites_;
|
||||
}
|
||||
|
||||
// Returns TypeParameterizedTestSuiteRegistry object used to keep track of
|
||||
// type-parameterized tests and instantiations of them.
|
||||
internal::TypeParameterizedTestSuiteRegistry&
|
||||
type_parameterized_test_registry() {
|
||||
return type_parameterized_test_registry_;
|
||||
}
|
||||
|
||||
// Sets the TestSuite object for the test that's currently running.
|
||||
void set_current_test_suite(TestSuite* a_current_test_suite) {
|
||||
current_test_suite_ = a_current_test_suite;
|
||||
@@ -872,6 +888,12 @@ class GTEST_API_ UnitTestImpl {
|
||||
// ParameterizedTestRegistry object used to register value-parameterized
|
||||
// tests.
|
||||
internal::ParameterizedTestSuiteRegistry parameterized_test_registry_;
|
||||
internal::TypeParameterizedTestSuiteRegistry
|
||||
type_parameterized_test_registry_;
|
||||
|
||||
// The set holding the name of parameterized
|
||||
// test suites that may go uninstantiated.
|
||||
std::set<std::string> ignored_parameterized_test_suites_;
|
||||
|
||||
// Indicates whether RegisterParameterizedTests() has been called already.
|
||||
bool parameterized_tests_registered_;
|
||||
@@ -911,7 +933,7 @@ class GTEST_API_ UnitTestImpl {
|
||||
// desired.
|
||||
OsStackTraceGetterInterface* os_stack_trace_getter_;
|
||||
|
||||
// True iff PostFlagParsingInit() has been called.
|
||||
// True if and only if PostFlagParsingInit() has been called.
|
||||
bool post_flag_parse_init_performed_;
|
||||
|
||||
// The random number seed used at the beginning of the test run.
|
||||
@@ -998,20 +1020,9 @@ bool ParseNaturalNumber(const ::std::string& str, Integer* number) {
|
||||
char* end;
|
||||
// BiggestConvertible is the largest integer type that system-provided
|
||||
// string-to-number conversion routines can return.
|
||||
using BiggestConvertible = unsigned long long; // NOLINT
|
||||
|
||||
# if GTEST_OS_WINDOWS && !defined(__GNUC__)
|
||||
|
||||
// MSVC and C++ Builder define __int64 instead of the standard long long.
|
||||
typedef unsigned __int64 BiggestConvertible;
|
||||
const BiggestConvertible parsed = _strtoui64(str.c_str(), &end, 10);
|
||||
|
||||
# else
|
||||
|
||||
typedef unsigned long long BiggestConvertible; // NOLINT
|
||||
const BiggestConvertible parsed = strtoull(str.c_str(), &end, 10);
|
||||
|
||||
# endif // GTEST_OS_WINDOWS && !defined(__GNUC__)
|
||||
|
||||
const BiggestConvertible parsed = strtoull(str.c_str(), &end, 10); // NOLINT
|
||||
const bool parse_success = *end == '\0' && errno == 0;
|
||||
|
||||
GTEST_CHECK_(sizeof(Integer) <= sizeof(parsed));
|
||||
@@ -1153,13 +1164,13 @@ class StreamingListener : public EmptyTestEventListener {
|
||||
}
|
||||
|
||||
// Note that "event=TestCaseStart" is a wire format and has to remain
|
||||
// "case" for compatibilty
|
||||
// "case" for compatibility
|
||||
void OnTestCaseStart(const TestCase& test_case) override {
|
||||
SendLn(std::string("event=TestCaseStart&name=") + test_case.name());
|
||||
}
|
||||
|
||||
// Note that "event=TestCaseEnd" is a wire format and has to remain
|
||||
// "case" for compatibilty
|
||||
// "case" for compatibility
|
||||
void OnTestCaseEnd(const TestCase& test_case) override {
|
||||
SendLn("event=TestCaseEnd&passed=" + FormatBool(test_case.Passed()) +
|
||||
"&elapsed_time=" + StreamableToString(test_case.elapsed_time()) +
|
||||
@@ -1207,4 +1218,4 @@ class StreamingListener : public EmptyTestEventListener {
|
||||
|
||||
GTEST_DISABLE_MSC_WARNINGS_POP_() // 4251
|
||||
|
||||
#endif // GTEST_SRC_GTEST_INTERNAL_INL_H_
|
||||
#endif // GOOGLETEST_SRC_GTEST_INTERNAL_INL_H_
|
||||
|
||||
+14
-14
@@ -58,40 +58,40 @@ Matcher<std::string>::Matcher(const std::string& s) { *this = Eq(s); }
|
||||
// s.
|
||||
Matcher<std::string>::Matcher(const char* s) { *this = Eq(std::string(s)); }
|
||||
|
||||
#if GTEST_HAS_ABSL
|
||||
// Constructs a matcher that matches a const absl::string_view& whose value is
|
||||
#if GTEST_INTERNAL_HAS_STRING_VIEW
|
||||
// Constructs a matcher that matches a const StringView& whose value is
|
||||
// equal to s.
|
||||
Matcher<const absl::string_view&>::Matcher(const std::string& s) {
|
||||
Matcher<const internal::StringView&>::Matcher(const std::string& s) {
|
||||
*this = Eq(s);
|
||||
}
|
||||
|
||||
// Constructs a matcher that matches a const absl::string_view& whose value is
|
||||
// Constructs a matcher that matches a const StringView& whose value is
|
||||
// equal to s.
|
||||
Matcher<const absl::string_view&>::Matcher(const char* s) {
|
||||
Matcher<const internal::StringView&>::Matcher(const char* s) {
|
||||
*this = Eq(std::string(s));
|
||||
}
|
||||
|
||||
// Constructs a matcher that matches a const absl::string_view& whose value is
|
||||
// Constructs a matcher that matches a const StringView& whose value is
|
||||
// equal to s.
|
||||
Matcher<const absl::string_view&>::Matcher(absl::string_view s) {
|
||||
Matcher<const internal::StringView&>::Matcher(internal::StringView s) {
|
||||
*this = Eq(std::string(s));
|
||||
}
|
||||
|
||||
// Constructs a matcher that matches a absl::string_view whose value is equal to
|
||||
// Constructs a matcher that matches a StringView whose value is equal to
|
||||
// s.
|
||||
Matcher<absl::string_view>::Matcher(const std::string& s) { *this = Eq(s); }
|
||||
Matcher<internal::StringView>::Matcher(const std::string& s) { *this = Eq(s); }
|
||||
|
||||
// Constructs a matcher that matches a absl::string_view whose value is equal to
|
||||
// Constructs a matcher that matches a StringView whose value is equal to
|
||||
// s.
|
||||
Matcher<absl::string_view>::Matcher(const char* s) {
|
||||
Matcher<internal::StringView>::Matcher(const char* s) {
|
||||
*this = Eq(std::string(s));
|
||||
}
|
||||
|
||||
// Constructs a matcher that matches a absl::string_view whose value is equal to
|
||||
// Constructs a matcher that matches a StringView whose value is equal to
|
||||
// s.
|
||||
Matcher<absl::string_view>::Matcher(absl::string_view s) {
|
||||
Matcher<internal::StringView>::Matcher(internal::StringView s) {
|
||||
*this = Eq(std::string(s));
|
||||
}
|
||||
#endif // GTEST_HAS_ABSL
|
||||
#endif // GTEST_INTERNAL_HAS_STRING_VIEW
|
||||
|
||||
} // namespace testing
|
||||
|
||||
+74
-43
@@ -34,6 +34,7 @@
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <cstdint>
|
||||
#include <fstream>
|
||||
#include <memory>
|
||||
|
||||
@@ -197,7 +198,8 @@ size_t GetThreadCount() {
|
||||
if (sysctl(mib, miblen, NULL, &size, NULL, 0)) {
|
||||
return 0;
|
||||
}
|
||||
mib[5] = size / mib[4];
|
||||
|
||||
mib[5] = static_cast<int>(size / static_cast<size_t>(mib[4]));
|
||||
|
||||
// populate array of structs
|
||||
struct kinfo_proc info[mib[5]];
|
||||
@@ -206,8 +208,8 @@ size_t GetThreadCount() {
|
||||
}
|
||||
|
||||
// exclude empty members
|
||||
int nthreads = 0;
|
||||
for (int i = 0; i < size / mib[4]; i++) {
|
||||
size_t nthreads = 0;
|
||||
for (size_t i = 0; i < size / static_cast<size_t>(mib[4]); i++) {
|
||||
if (info[i].p_tid != -1)
|
||||
nthreads++;
|
||||
}
|
||||
@@ -536,6 +538,9 @@ class ThreadLocalRegistryImpl {
|
||||
// Returns a value that can be used to identify the thread from other threads.
|
||||
static ThreadLocalValueHolderBase* GetValueOnCurrentThread(
|
||||
const ThreadLocalBase* thread_local_instance) {
|
||||
#ifdef _MSC_VER
|
||||
MemoryIsNotDeallocated memory_is_not_deallocated;
|
||||
#endif // _MSC_VER
|
||||
DWORD current_thread = ::GetCurrentThreadId();
|
||||
MutexLock lock(&mutex_);
|
||||
ThreadIdToThreadLocals* const thread_to_thread_locals =
|
||||
@@ -683,8 +688,8 @@ class ThreadLocalRegistryImpl {
|
||||
static Mutex thread_map_mutex_;
|
||||
};
|
||||
|
||||
Mutex ThreadLocalRegistryImpl::mutex_(Mutex::kStaticMutex);
|
||||
Mutex ThreadLocalRegistryImpl::thread_map_mutex_(Mutex::kStaticMutex);
|
||||
Mutex ThreadLocalRegistryImpl::mutex_(Mutex::kStaticMutex); // NOLINT
|
||||
Mutex ThreadLocalRegistryImpl::thread_map_mutex_(Mutex::kStaticMutex); // NOLINT
|
||||
|
||||
ThreadLocalValueHolderBase* ThreadLocalRegistry::GetValueOnCurrentThread(
|
||||
const ThreadLocalBase* thread_local_instance) {
|
||||
@@ -715,7 +720,7 @@ RE::~RE() {
|
||||
free(const_cast<char*>(pattern_));
|
||||
}
|
||||
|
||||
// Returns true iff regular expression re matches the entire str.
|
||||
// Returns true if and only if regular expression re matches the entire str.
|
||||
bool RE::FullMatch(const char* str, const RE& re) {
|
||||
if (!re.is_valid_) return false;
|
||||
|
||||
@@ -723,8 +728,8 @@ bool RE::FullMatch(const char* str, const RE& re) {
|
||||
return regexec(&re.full_regex_, str, 1, &match, 0) == 0;
|
||||
}
|
||||
|
||||
// Returns true iff regular expression re matches a substring of str
|
||||
// (including str itself).
|
||||
// Returns true if and only if regular expression re matches a substring of
|
||||
// str (including str itself).
|
||||
bool RE::PartialMatch(const char* str, const RE& re) {
|
||||
if (!re.is_valid_) return false;
|
||||
|
||||
@@ -764,14 +769,14 @@ void RE::Init(const char* regex) {
|
||||
|
||||
#elif GTEST_USES_SIMPLE_RE
|
||||
|
||||
// Returns true iff ch appears anywhere in str (excluding the
|
||||
// Returns true if and only if ch appears anywhere in str (excluding the
|
||||
// terminating '\0' character).
|
||||
bool IsInSet(char ch, const char* str) {
|
||||
return ch != '\0' && strchr(str, ch) != nullptr;
|
||||
}
|
||||
|
||||
// Returns true iff ch belongs to the given classification. Unlike
|
||||
// similar functions in <ctype.h>, these aren't affected by the
|
||||
// Returns true if and only if ch belongs to the given classification.
|
||||
// Unlike similar functions in <ctype.h>, these aren't affected by the
|
||||
// current locale.
|
||||
bool IsAsciiDigit(char ch) { return '0' <= ch && ch <= '9'; }
|
||||
bool IsAsciiPunct(char ch) {
|
||||
@@ -784,13 +789,13 @@ bool IsAsciiWordChar(char ch) {
|
||||
('0' <= ch && ch <= '9') || ch == '_';
|
||||
}
|
||||
|
||||
// Returns true iff "\\c" is a supported escape sequence.
|
||||
// Returns true if and only if "\\c" is a supported escape sequence.
|
||||
bool IsValidEscape(char c) {
|
||||
return (IsAsciiPunct(c) || IsInSet(c, "dDfnrsStvwW"));
|
||||
}
|
||||
|
||||
// Returns true iff the given atom (specified by escaped and pattern)
|
||||
// matches ch. The result is undefined if the atom is invalid.
|
||||
// Returns true if and only if the given atom (specified by escaped and
|
||||
// pattern) matches ch. The result is undefined if the atom is invalid.
|
||||
bool AtomMatchesChar(bool escaped, char pattern_char, char ch) {
|
||||
if (escaped) { // "\\p" where p is pattern_char.
|
||||
switch (pattern_char) {
|
||||
@@ -828,7 +833,7 @@ bool ValidateRegex(const char* regex) {
|
||||
|
||||
bool is_valid = true;
|
||||
|
||||
// True iff ?, *, or + can follow the previous atom.
|
||||
// True if and only if ?, *, or + can follow the previous atom.
|
||||
bool prev_repeatable = false;
|
||||
for (int i = 0; regex[i]; i++) {
|
||||
if (regex[i] == '\\') { // An escape sequence
|
||||
@@ -904,8 +909,8 @@ bool MatchRepetitionAndRegexAtHead(
|
||||
return false;
|
||||
}
|
||||
|
||||
// Returns true iff regex matches a prefix of str. regex must be a
|
||||
// valid simple regular expression and not start with "^", or the
|
||||
// Returns true if and only if regex matches a prefix of str. regex must
|
||||
// be a valid simple regular expression and not start with "^", or the
|
||||
// result is undefined.
|
||||
bool MatchRegexAtHead(const char* regex, const char* str) {
|
||||
if (*regex == '\0') // An empty regex matches a prefix of anything.
|
||||
@@ -935,8 +940,8 @@ bool MatchRegexAtHead(const char* regex, const char* str) {
|
||||
}
|
||||
}
|
||||
|
||||
// Returns true iff regex matches any substring of str. regex must be
|
||||
// a valid simple regular expression, or the result is undefined.
|
||||
// Returns true if and only if regex matches any substring of str. regex must
|
||||
// be a valid simple regular expression, or the result is undefined.
|
||||
//
|
||||
// The algorithm is recursive, but the recursion depth doesn't exceed
|
||||
// the regex length, so we won't need to worry about running out of
|
||||
@@ -964,13 +969,13 @@ RE::~RE() {
|
||||
free(const_cast<char*>(full_pattern_));
|
||||
}
|
||||
|
||||
// Returns true iff regular expression re matches the entire str.
|
||||
// Returns true if and only if regular expression re matches the entire str.
|
||||
bool RE::FullMatch(const char* str, const RE& re) {
|
||||
return re.is_valid_ && MatchRegexAnywhere(re.full_pattern_, str);
|
||||
}
|
||||
|
||||
// Returns true iff regular expression re matches a substring of str
|
||||
// (including str itself).
|
||||
// Returns true if and only if regular expression re matches a substring of
|
||||
// str (including str itself).
|
||||
bool RE::PartialMatch(const char* str, const RE& re) {
|
||||
return re.is_valid_ && MatchRegexAnywhere(re.pattern_, str);
|
||||
}
|
||||
@@ -1090,9 +1095,9 @@ class CapturedStream {
|
||||
filename_ = temp_file_path;
|
||||
# else
|
||||
// There's no guarantee that a test has write access to the current
|
||||
// directory, so we create the temporary file in the /tmp directory
|
||||
// instead. We use /tmp on most systems, and /sdcard on Android.
|
||||
// That's because Android doesn't have /tmp.
|
||||
// directory, so we create the temporary file in a temporary directory.
|
||||
std::string name_template;
|
||||
|
||||
# if GTEST_OS_LINUX_ANDROID
|
||||
// Note: Android applications are expected to call the framework's
|
||||
// Context.getExternalStorageDirectory() method through JNI to get
|
||||
@@ -1102,23 +1107,49 @@ class CapturedStream {
|
||||
// code as part of a regular standalone executable, which doesn't
|
||||
// run in a Dalvik process (e.g. when running it through 'adb shell').
|
||||
//
|
||||
// The location /sdcard is directly accessible from native code
|
||||
// and is the only location (unofficially) supported by the Android
|
||||
// team. It's generally a symlink to the real SD Card mount point
|
||||
// which can be /mnt/sdcard, /mnt/sdcard0, /system/media/sdcard, or
|
||||
// other OEM-customized locations. Never rely on these, and always
|
||||
// use /sdcard.
|
||||
char name_template[] = "/sdcard/gtest_captured_stream.XXXXXX";
|
||||
// The location /data/local/tmp is directly accessible from native code.
|
||||
// '/sdcard' and other variants cannot be relied on, as they are not
|
||||
// guaranteed to be mounted, or may have a delay in mounting.
|
||||
name_template = "/data/local/tmp/";
|
||||
# elif GTEST_OS_IOS
|
||||
char user_temp_dir[PATH_MAX + 1];
|
||||
|
||||
// Documented alternative to NSTemporaryDirectory() (for obtaining creating
|
||||
// a temporary directory) at
|
||||
// https://developer.apple.com/library/archive/documentation/Security/Conceptual/SecureCodingGuide/Articles/RaceConditions.html#//apple_ref/doc/uid/TP40002585-SW10
|
||||
//
|
||||
// _CS_DARWIN_USER_TEMP_DIR (as well as _CS_DARWIN_USER_CACHE_DIR) is not
|
||||
// documented in the confstr() man page at
|
||||
// https://developer.apple.com/library/archive/documentation/System/Conceptual/ManPages_iPhoneOS/man3/confstr.3.html#//apple_ref/doc/man/3/confstr
|
||||
// but are still available, according to the WebKit patches at
|
||||
// https://trac.webkit.org/changeset/262004/webkit
|
||||
// https://trac.webkit.org/changeset/263705/webkit
|
||||
//
|
||||
// The confstr() implementation falls back to getenv("TMPDIR"). See
|
||||
// https://opensource.apple.com/source/Libc/Libc-1439.100.3/gen/confstr.c.auto.html
|
||||
::confstr(_CS_DARWIN_USER_TEMP_DIR, user_temp_dir, sizeof(user_temp_dir));
|
||||
|
||||
name_template = user_temp_dir;
|
||||
if (name_template.back() != GTEST_PATH_SEP_[0])
|
||||
name_template.push_back(GTEST_PATH_SEP_[0]);
|
||||
# else
|
||||
char name_template[] = "/tmp/captured_stream.XXXXXX";
|
||||
# endif // GTEST_OS_LINUX_ANDROID
|
||||
const int captured_fd = mkstemp(name_template);
|
||||
name_template = "/tmp/";
|
||||
# endif
|
||||
name_template.append("gtest_captured_stream.XXXXXX");
|
||||
|
||||
// mkstemp() modifies the string bytes in place, and does not go beyond the
|
||||
// string's length. This results in well-defined behavior in C++17.
|
||||
//
|
||||
// The const_cast is needed below C++17. The constraints on std::string
|
||||
// implementations in C++11 and above make assumption behind the const_cast
|
||||
// fairly safe.
|
||||
const int captured_fd = ::mkstemp(const_cast<char*>(name_template.data()));
|
||||
if (captured_fd == -1) {
|
||||
GTEST_LOG_(WARNING)
|
||||
<< "Failed to create tmp file " << name_template
|
||||
<< " for test; does the test have access to the /tmp directory?";
|
||||
}
|
||||
filename_ = name_template;
|
||||
filename_ = std::move(name_template);
|
||||
# endif // GTEST_OS_WINDOWS
|
||||
fflush(nullptr);
|
||||
dup2(captured_fd, fd_);
|
||||
@@ -1289,7 +1320,7 @@ static std::string FlagToEnvVar(const char* flag) {
|
||||
// Parses 'str' for a 32-bit signed integer. If successful, writes
|
||||
// the result to *value and returns true; otherwise leaves *value
|
||||
// unchanged and returns false.
|
||||
bool ParseInt32(const Message& src_text, const char* str, Int32* value) {
|
||||
bool ParseInt32(const Message& src_text, const char* str, int32_t* value) {
|
||||
// Parses the environment variable as a decimal integer.
|
||||
char* end = nullptr;
|
||||
const long long_value = strtol(str, &end, 10); // NOLINT
|
||||
@@ -1306,13 +1337,13 @@ bool ParseInt32(const Message& src_text, const char* str, Int32* value) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Is the parsed value in the range of an Int32?
|
||||
const Int32 result = static_cast<Int32>(long_value);
|
||||
// Is the parsed value in the range of an int32_t?
|
||||
const auto result = static_cast<int32_t>(long_value);
|
||||
if (long_value == LONG_MAX || long_value == LONG_MIN ||
|
||||
// The parsed value overflows as a long. (strtol() returns
|
||||
// LONG_MAX or LONG_MIN when the input overflows.)
|
||||
result != long_value
|
||||
// The parsed value overflows as an Int32.
|
||||
// The parsed value overflows as an int32_t.
|
||||
) {
|
||||
Message msg;
|
||||
msg << "WARNING: " << src_text
|
||||
@@ -1330,7 +1361,7 @@ bool ParseInt32(const Message& src_text, const char* str, Int32* value) {
|
||||
// Reads and returns the Boolean environment variable corresponding to
|
||||
// the given flag; if it's not set, returns default_value.
|
||||
//
|
||||
// The value is considered true iff it's not "0".
|
||||
// The value is considered true if and only if it's not "0".
|
||||
bool BoolFromGTestEnv(const char* flag, bool default_value) {
|
||||
#if defined(GTEST_GET_BOOL_FROM_ENV_)
|
||||
return GTEST_GET_BOOL_FROM_ENV_(flag, default_value);
|
||||
@@ -1345,7 +1376,7 @@ bool BoolFromGTestEnv(const char* flag, bool default_value) {
|
||||
// Reads and returns a 32-bit integer stored in the environment
|
||||
// variable corresponding to the given flag; if it isn't set or
|
||||
// doesn't represent a valid 32-bit integer, returns default_value.
|
||||
Int32 Int32FromGTestEnv(const char* flag, Int32 default_value) {
|
||||
int32_t Int32FromGTestEnv(const char* flag, int32_t default_value) {
|
||||
#if defined(GTEST_GET_INT32_FROM_ENV_)
|
||||
return GTEST_GET_INT32_FROM_ENV_(flag, default_value);
|
||||
#else
|
||||
@@ -1356,7 +1387,7 @@ Int32 Int32FromGTestEnv(const char* flag, Int32 default_value) {
|
||||
return default_value;
|
||||
}
|
||||
|
||||
Int32 result = default_value;
|
||||
int32_t result = default_value;
|
||||
if (!ParseInt32(Message() << "Environment variable " << env_var,
|
||||
string_value, &result)) {
|
||||
printf("The default value %s is used.\n",
|
||||
|
||||
+144
-53
@@ -42,11 +42,16 @@
|
||||
// defines Foo.
|
||||
|
||||
#include "gtest/gtest-printers.h"
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
#include <cctype>
|
||||
#include <cstdint>
|
||||
#include <cwchar>
|
||||
#include <ostream> // NOLINT
|
||||
#include <string>
|
||||
#include <type_traits>
|
||||
|
||||
#include "gtest/internal/gtest-port.h"
|
||||
#include "src/gtest-internal-inl.h"
|
||||
|
||||
@@ -102,9 +107,19 @@ void PrintBytesInObjectToImpl(const unsigned char* obj_bytes, size_t count,
|
||||
*os << ">";
|
||||
}
|
||||
|
||||
// Helpers for widening a character to char32_t. Since the standard does not
|
||||
// specify if char / wchar_t is signed or unsigned, it is important to first
|
||||
// convert it to the unsigned type of the same width before widening it to
|
||||
// char32_t.
|
||||
template <typename CharType>
|
||||
char32_t ToChar32(CharType in) {
|
||||
return static_cast<char32_t>(
|
||||
static_cast<typename std::make_unsigned<CharType>::type>(in));
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
namespace internal2 {
|
||||
namespace internal {
|
||||
|
||||
// Delegates to PrintBytesInObjectToImpl() to print the bytes in the
|
||||
// given object. The delegation simplifies the implementation, which
|
||||
@@ -116,10 +131,6 @@ void PrintBytesInObjectTo(const unsigned char* obj_bytes, size_t count,
|
||||
PrintBytesInObjectToImpl(obj_bytes, count, os);
|
||||
}
|
||||
|
||||
} // namespace internal2
|
||||
|
||||
namespace internal {
|
||||
|
||||
// Depending on the value of a char (or wchar_t), we print it in one
|
||||
// of three formats:
|
||||
// - as is if it's a printable ASCII (e.g. 'a', '2', ' '),
|
||||
@@ -134,18 +145,15 @@ enum CharFormat {
|
||||
// Returns true if c is a printable ASCII character. We test the
|
||||
// value of c directly instead of calling isprint(), which is buggy on
|
||||
// Windows Mobile.
|
||||
inline bool IsPrintableAscii(wchar_t c) {
|
||||
return 0x20 <= c && c <= 0x7E;
|
||||
}
|
||||
inline bool IsPrintableAscii(char32_t c) { return 0x20 <= c && c <= 0x7E; }
|
||||
|
||||
// Prints a wide or narrow char c as a character literal without the
|
||||
// quotes, escaping it when necessary; returns how c was formatted.
|
||||
// The template argument UnsignedChar is the unsigned version of Char,
|
||||
// which is the type of c.
|
||||
template <typename UnsignedChar, typename Char>
|
||||
// Prints c (of type char, char8_t, char16_t, char32_t, or wchar_t) as a
|
||||
// character literal without the quotes, escaping it when necessary; returns how
|
||||
// c was formatted.
|
||||
template <typename Char>
|
||||
static CharFormat PrintAsCharLiteralTo(Char c, ostream* os) {
|
||||
wchar_t w_c = static_cast<wchar_t>(c);
|
||||
switch (w_c) {
|
||||
const char32_t u_c = ToChar32(c);
|
||||
switch (u_c) {
|
||||
case L'\0':
|
||||
*os << "\\0";
|
||||
break;
|
||||
@@ -177,13 +185,12 @@ static CharFormat PrintAsCharLiteralTo(Char c, ostream* os) {
|
||||
*os << "\\v";
|
||||
break;
|
||||
default:
|
||||
if (IsPrintableAscii(w_c)) {
|
||||
if (IsPrintableAscii(u_c)) {
|
||||
*os << static_cast<char>(c);
|
||||
return kAsIs;
|
||||
} else {
|
||||
ostream::fmtflags flags = os->flags();
|
||||
*os << "\\x" << std::hex << std::uppercase
|
||||
<< static_cast<int>(static_cast<UnsignedChar>(c));
|
||||
*os << "\\x" << std::hex << std::uppercase << static_cast<int>(u_c);
|
||||
os->flags(flags);
|
||||
return kHexEscape;
|
||||
}
|
||||
@@ -191,9 +198,9 @@ static CharFormat PrintAsCharLiteralTo(Char c, ostream* os) {
|
||||
return kSpecialEscape;
|
||||
}
|
||||
|
||||
// Prints a wchar_t c as if it's part of a string literal, escaping it when
|
||||
// Prints a char32_t c as if it's part of a string literal, escaping it when
|
||||
// necessary; returns how c was formatted.
|
||||
static CharFormat PrintAsStringLiteralTo(wchar_t c, ostream* os) {
|
||||
static CharFormat PrintAsStringLiteralTo(char32_t c, ostream* os) {
|
||||
switch (c) {
|
||||
case L'\'':
|
||||
*os << "'";
|
||||
@@ -202,26 +209,68 @@ static CharFormat PrintAsStringLiteralTo(wchar_t c, ostream* os) {
|
||||
*os << "\\\"";
|
||||
return kSpecialEscape;
|
||||
default:
|
||||
return PrintAsCharLiteralTo<wchar_t>(c, os);
|
||||
return PrintAsCharLiteralTo(c, os);
|
||||
}
|
||||
}
|
||||
|
||||
static const char* GetCharWidthPrefix(char) {
|
||||
return "";
|
||||
}
|
||||
|
||||
static const char* GetCharWidthPrefix(signed char) {
|
||||
return "";
|
||||
}
|
||||
|
||||
static const char* GetCharWidthPrefix(unsigned char) {
|
||||
return "";
|
||||
}
|
||||
|
||||
#ifdef __cpp_char8_t
|
||||
static const char* GetCharWidthPrefix(char8_t) {
|
||||
return "u8";
|
||||
}
|
||||
#endif
|
||||
|
||||
static const char* GetCharWidthPrefix(char16_t) {
|
||||
return "u";
|
||||
}
|
||||
|
||||
static const char* GetCharWidthPrefix(char32_t) {
|
||||
return "U";
|
||||
}
|
||||
|
||||
static const char* GetCharWidthPrefix(wchar_t) {
|
||||
return "L";
|
||||
}
|
||||
|
||||
// Prints a char c as if it's part of a string literal, escaping it when
|
||||
// necessary; returns how c was formatted.
|
||||
static CharFormat PrintAsStringLiteralTo(char c, ostream* os) {
|
||||
return PrintAsStringLiteralTo(
|
||||
static_cast<wchar_t>(static_cast<unsigned char>(c)), os);
|
||||
return PrintAsStringLiteralTo(ToChar32(c), os);
|
||||
}
|
||||
|
||||
// Prints a wide or narrow character c and its code. '\0' is printed
|
||||
// as "'\\0'", other unprintable characters are also properly escaped
|
||||
// using the standard C++ escape sequence. The template argument
|
||||
// UnsignedChar is the unsigned version of Char, which is the type of c.
|
||||
template <typename UnsignedChar, typename Char>
|
||||
#ifdef __cpp_char8_t
|
||||
static CharFormat PrintAsStringLiteralTo(char8_t c, ostream* os) {
|
||||
return PrintAsStringLiteralTo(ToChar32(c), os);
|
||||
}
|
||||
#endif
|
||||
|
||||
static CharFormat PrintAsStringLiteralTo(char16_t c, ostream* os) {
|
||||
return PrintAsStringLiteralTo(ToChar32(c), os);
|
||||
}
|
||||
|
||||
static CharFormat PrintAsStringLiteralTo(wchar_t c, ostream* os) {
|
||||
return PrintAsStringLiteralTo(ToChar32(c), os);
|
||||
}
|
||||
|
||||
// Prints a character c (of type char, char8_t, char16_t, char32_t, or wchar_t)
|
||||
// and its code. '\0' is printed as "'\\0'", other unprintable characters are
|
||||
// also properly escaped using the standard C++ escape sequence.
|
||||
template <typename Char>
|
||||
void PrintCharAndCodeTo(Char c, ostream* os) {
|
||||
// First, print c as a literal in the most readable form we can find.
|
||||
*os << ((sizeof(c) > 1) ? "L'" : "'");
|
||||
const CharFormat format = PrintAsCharLiteralTo<UnsignedChar>(c, os);
|
||||
*os << GetCharWidthPrefix(c) << "'";
|
||||
const CharFormat format = PrintAsCharLiteralTo(c, os);
|
||||
*os << "'";
|
||||
|
||||
// To aid user debugging, we also print c's code in decimal, unless
|
||||
@@ -242,21 +291,21 @@ void PrintCharAndCodeTo(Char c, ostream* os) {
|
||||
*os << ")";
|
||||
}
|
||||
|
||||
void PrintTo(unsigned char c, ::std::ostream* os) {
|
||||
PrintCharAndCodeTo<unsigned char>(c, os);
|
||||
}
|
||||
void PrintTo(signed char c, ::std::ostream* os) {
|
||||
PrintCharAndCodeTo<unsigned char>(c, os);
|
||||
}
|
||||
void PrintTo(unsigned char c, ::std::ostream* os) { PrintCharAndCodeTo(c, os); }
|
||||
void PrintTo(signed char c, ::std::ostream* os) { PrintCharAndCodeTo(c, os); }
|
||||
|
||||
// Prints a wchar_t as a symbol if it is printable or as its internal
|
||||
// code otherwise and also as its code. L'\0' is printed as "L'\\0'".
|
||||
void PrintTo(wchar_t wc, ostream* os) {
|
||||
PrintCharAndCodeTo<wchar_t>(wc, os);
|
||||
void PrintTo(wchar_t wc, ostream* os) { PrintCharAndCodeTo(wc, os); }
|
||||
|
||||
// TODO(dcheng): Consider making this delegate to PrintCharAndCodeTo() as well.
|
||||
void PrintTo(char32_t c, ::std::ostream* os) {
|
||||
*os << std::hex << "U+" << std::uppercase << std::setfill('0') << std::setw(4)
|
||||
<< static_cast<uint32_t>(c);
|
||||
}
|
||||
|
||||
// Prints the given array of characters to the ostream. CharType must be either
|
||||
// char or wchar_t.
|
||||
// char, char8_t, char16_t, char32_t, or wchar_t.
|
||||
// The array starts at begin, the length is len, it may include '\0' characters
|
||||
// and may not be NUL-terminated.
|
||||
template <typename CharType>
|
||||
@@ -266,8 +315,8 @@ GTEST_ATTRIBUTE_NO_SANITIZE_HWADDRESS_
|
||||
GTEST_ATTRIBUTE_NO_SANITIZE_THREAD_
|
||||
static CharFormat PrintCharsAsStringTo(
|
||||
const CharType* begin, size_t len, ostream* os) {
|
||||
const char* const kQuoteBegin = sizeof(CharType) == 1 ? "\"" : "L\"";
|
||||
*os << kQuoteBegin;
|
||||
const char* const quote_prefix = GetCharWidthPrefix(*begin);
|
||||
*os << quote_prefix << "\"";
|
||||
bool is_previous_hex = false;
|
||||
CharFormat print_format = kAsIs;
|
||||
for (size_t index = 0; index < len; ++index) {
|
||||
@@ -276,7 +325,7 @@ static CharFormat PrintCharsAsStringTo(
|
||||
// Previous character is of '\x..' form and this character can be
|
||||
// interpreted as another hexadecimal digit in its number. Break string to
|
||||
// disambiguate.
|
||||
*os << "\" " << kQuoteBegin;
|
||||
*os << "\" " << quote_prefix << "\"";
|
||||
}
|
||||
is_previous_hex = PrintAsStringLiteralTo(cur, os) == kHexEscape;
|
||||
// Remember if any characters required hex escaping.
|
||||
@@ -322,22 +371,57 @@ void UniversalPrintArray(const char* begin, size_t len, ostream* os) {
|
||||
UniversalPrintCharArray(begin, len, os);
|
||||
}
|
||||
|
||||
#ifdef __cpp_char8_t
|
||||
// Prints a (const) char8_t array of 'len' elements, starting at address
|
||||
// 'begin'.
|
||||
void UniversalPrintArray(const char8_t* begin, size_t len, ostream* os) {
|
||||
UniversalPrintCharArray(begin, len, os);
|
||||
}
|
||||
#endif
|
||||
|
||||
// Prints a (const) char16_t array of 'len' elements, starting at address
|
||||
// 'begin'.
|
||||
void UniversalPrintArray(const char16_t* begin, size_t len, ostream* os) {
|
||||
UniversalPrintCharArray(begin, len, os);
|
||||
}
|
||||
|
||||
// Prints a (const) char32_t array of 'len' elements, starting at address
|
||||
// 'begin'.
|
||||
void UniversalPrintArray(const char32_t* begin, size_t len, ostream* os) {
|
||||
UniversalPrintCharArray(begin, len, os);
|
||||
}
|
||||
|
||||
// Prints a (const) wchar_t array of 'len' elements, starting at address
|
||||
// 'begin'.
|
||||
void UniversalPrintArray(const wchar_t* begin, size_t len, ostream* os) {
|
||||
UniversalPrintCharArray(begin, len, os);
|
||||
}
|
||||
|
||||
// Prints the given C string to the ostream.
|
||||
void PrintTo(const char* s, ostream* os) {
|
||||
namespace {
|
||||
|
||||
// Prints a null-terminated C-style string to the ostream.
|
||||
template <typename Char>
|
||||
void PrintCStringTo(const Char* s, ostream* os) {
|
||||
if (s == nullptr) {
|
||||
*os << "NULL";
|
||||
} else {
|
||||
*os << ImplicitCast_<const void*>(s) << " pointing to ";
|
||||
PrintCharsAsStringTo(s, strlen(s), os);
|
||||
PrintCharsAsStringTo(s, std::char_traits<Char>::length(s), os);
|
||||
}
|
||||
}
|
||||
|
||||
} // anonymous namespace
|
||||
|
||||
void PrintTo(const char* s, ostream* os) { PrintCStringTo(s, os); }
|
||||
|
||||
#ifdef __cpp_char8_t
|
||||
void PrintTo(const char8_t* s, ostream* os) { PrintCStringTo(s, os); }
|
||||
#endif
|
||||
|
||||
void PrintTo(const char16_t* s, ostream* os) { PrintCStringTo(s, os); }
|
||||
|
||||
void PrintTo(const char32_t* s, ostream* os) { PrintCStringTo(s, os); }
|
||||
|
||||
// MSVC compiler can be configured to define whar_t as a typedef
|
||||
// of unsigned short. Defining an overload for const wchar_t* in that case
|
||||
// would cause pointers to unsigned shorts be printed as wide strings,
|
||||
@@ -346,14 +430,7 @@ void PrintTo(const char* s, ostream* os) {
|
||||
// wchar_t is implemented as a native type.
|
||||
#if !defined(_MSC_VER) || defined(_NATIVE_WCHAR_T_DEFINED)
|
||||
// Prints the given wide C string to the ostream.
|
||||
void PrintTo(const wchar_t* s, ostream* os) {
|
||||
if (s == nullptr) {
|
||||
*os << "NULL";
|
||||
} else {
|
||||
*os << ImplicitCast_<const void*>(s) << " pointing to ";
|
||||
PrintCharsAsStringTo(s, wcslen(s), os);
|
||||
}
|
||||
}
|
||||
void PrintTo(const wchar_t* s, ostream* os) { PrintCStringTo(s, os); }
|
||||
#endif // wchar_t is native
|
||||
|
||||
namespace {
|
||||
@@ -431,6 +508,20 @@ void PrintStringTo(const ::std::string& s, ostream* os) {
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef __cpp_char8_t
|
||||
void PrintU8StringTo(const ::std::u8string& s, ostream* os) {
|
||||
PrintCharsAsStringTo(s.data(), s.size(), os);
|
||||
}
|
||||
#endif
|
||||
|
||||
void PrintU16StringTo(const ::std::u16string& s, ostream* os) {
|
||||
PrintCharsAsStringTo(s.data(), s.size(), os);
|
||||
}
|
||||
|
||||
void PrintU32StringTo(const ::std::u32string& s, ostream* os) {
|
||||
PrintCharsAsStringTo(s.data(), s.size(), os);
|
||||
}
|
||||
|
||||
#if GTEST_HAS_STD_WSTRING
|
||||
void PrintWideStringTo(const ::std::wstring& s, ostream* os) {
|
||||
PrintCharsAsStringTo(s.data(), s.size(), os);
|
||||
|
||||
@@ -31,6 +31,8 @@
|
||||
// The Google C++ Testing and Mocking Framework (Google Test)
|
||||
|
||||
#include "gtest/gtest-test-part.h"
|
||||
|
||||
#include "gtest/internal/gtest-port.h"
|
||||
#include "src/gtest-internal-inl.h"
|
||||
|
||||
namespace testing {
|
||||
@@ -46,7 +48,9 @@ std::string TestPartResult::ExtractSummary(const char* message) {
|
||||
|
||||
// Prints a TestPartResult object.
|
||||
std::ostream& operator<<(std::ostream& os, const TestPartResult& result) {
|
||||
return os << result.file_name() << ":" << result.line_number() << ": "
|
||||
return os << internal::FormatFileLocation(result.file_name(),
|
||||
result.line_number())
|
||||
<< " "
|
||||
<< (result.type() == TestPartResult::kSuccess
|
||||
? "Success"
|
||||
: result.type() == TestPartResult::kSkip
|
||||
|
||||
@@ -35,8 +35,6 @@
|
||||
namespace testing {
|
||||
namespace internal {
|
||||
|
||||
#if GTEST_HAS_TYPED_TEST_P
|
||||
|
||||
// Skips to the first non-space char in str. Returns an empty string if str
|
||||
// contains only whitespace characters.
|
||||
static const char* SkipSpaces(const char* str) {
|
||||
@@ -58,7 +56,10 @@ static std::vector<std::string> SplitIntoTestNames(const char* src) {
|
||||
// registered_tests_; returns registered_tests if successful, or
|
||||
// aborts the program otherwise.
|
||||
const char* TypedTestSuitePState::VerifyRegisteredTestNames(
|
||||
const char* file, int line, const char* registered_tests) {
|
||||
const char* test_suite_name, const char* file, int line,
|
||||
const char* registered_tests) {
|
||||
RegisterTypeParameterizedTestSuite(test_suite_name, CodeLocation(file, line));
|
||||
|
||||
typedef RegisteredTestsMap::const_iterator RegisteredTestIter;
|
||||
registered_ = true;
|
||||
|
||||
@@ -75,17 +76,7 @@ const char* TypedTestSuitePState::VerifyRegisteredTestNames(
|
||||
continue;
|
||||
}
|
||||
|
||||
bool found = false;
|
||||
for (RegisteredTestIter it = registered_tests_.begin();
|
||||
it != registered_tests_.end();
|
||||
++it) {
|
||||
if (name == it->first) {
|
||||
found = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (found) {
|
||||
if (registered_tests_.count(name) != 0) {
|
||||
tests.insert(name);
|
||||
} else {
|
||||
errors << "No test named " << name
|
||||
@@ -112,7 +103,5 @@ const char* TypedTestSuitePState::VerifyRegisteredTestNames(
|
||||
return registered_tests;
|
||||
}
|
||||
|
||||
#endif // GTEST_HAS_TYPED_TEST_P
|
||||
|
||||
} // namespace internal
|
||||
} // namespace testing
|
||||
|
||||
+1059
-437
File diff suppressed because it is too large
Load Diff
@@ -30,13 +30,20 @@
|
||||
#include <cstdio>
|
||||
#include "gtest/gtest.h"
|
||||
|
||||
#ifdef ARDUINO
|
||||
#if GTEST_OS_ESP8266 || GTEST_OS_ESP32
|
||||
#if GTEST_OS_ESP8266
|
||||
extern "C" {
|
||||
#endif
|
||||
void setup() {
|
||||
testing::InitGoogleTest();
|
||||
}
|
||||
|
||||
void loop() { RUN_ALL_TESTS(); }
|
||||
|
||||
#if GTEST_OS_ESP8266
|
||||
}
|
||||
#endif
|
||||
|
||||
#else
|
||||
|
||||
GTEST_API_ int main(int argc, char **argv) {
|
||||
|
||||
Reference in New Issue
Block a user