aboutsummaryrefslogtreecommitdiffstats
path: root/utils/unittest/googletest
diff options
context:
space:
mode:
authorBenjamin Kramer <benny.kra@googlemail.com>2010-06-02 22:01:25 +0000
committerBenjamin Kramer <benny.kra@googlemail.com>2010-06-02 22:01:25 +0000
commite4b9c93fc1b531fe0cfe25a042f6b81c1e7c15c0 (patch)
tree1656513dd240b9ed4690589b9934d0e5371694fb /utils/unittest/googletest
parent18f30e6f5e80787808fe1455742452a5210afe07 (diff)
downloadexternal_llvm-e4b9c93fc1b531fe0cfe25a042f6b81c1e7c15c0.zip
external_llvm-e4b9c93fc1b531fe0cfe25a042f6b81c1e7c15c0.tar.gz
external_llvm-e4b9c93fc1b531fe0cfe25a042f6b81c1e7c15c0.tar.bz2
Merge gtest-1.3.0.
OSX users: make sure that CrashReporter is disabled when running unit tests. Death tests are enabled now so you'll get a ton of message boxes. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@105352 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'utils/unittest/googletest')
-rw-r--r--utils/unittest/googletest/gtest-death-test.cc832
-rw-r--r--utils/unittest/googletest/gtest-filepath.cc62
-rw-r--r--utils/unittest/googletest/gtest-port.cc365
-rw-r--r--utils/unittest/googletest/gtest-test-part.cc4
-rw-r--r--utils/unittest/googletest/gtest-typed-test.cc3
-rw-r--r--utils/unittest/googletest/gtest.cc596
-rw-r--r--utils/unittest/googletest/include/gtest/gtest-death-test.h55
-rw-r--r--utils/unittest/googletest/include/gtest/gtest-message.h4
-rw-r--r--utils/unittest/googletest/include/gtest/gtest-param-test.h4
-rw-r--r--utils/unittest/googletest/include/gtest/gtest-typed-test.h4
-rw-r--r--utils/unittest/googletest/include/gtest/gtest.h122
-rw-r--r--utils/unittest/googletest/include/gtest/internal/gtest-death-test-internal.h54
-rw-r--r--utils/unittest/googletest/include/gtest/internal/gtest-filepath.h11
-rw-r--r--utils/unittest/googletest/include/gtest/internal/gtest-internal-inl.h187
-rw-r--r--utils/unittest/googletest/include/gtest/internal/gtest-internal.h24
-rw-r--r--utils/unittest/googletest/include/gtest/internal/gtest-param-util-generated.h4
-rw-r--r--utils/unittest/googletest/include/gtest/internal/gtest-param-util.h2
-rw-r--r--utils/unittest/googletest/include/gtest/internal/gtest-port.h220
-rw-r--r--utils/unittest/googletest/include/gtest/internal/gtest-string.h2
-rw-r--r--utils/unittest/googletest/include/gtest/internal/gtest-type-util.h2
20 files changed, 2089 insertions, 468 deletions
diff --git a/utils/unittest/googletest/gtest-death-test.cc b/utils/unittest/googletest/gtest-death-test.cc
index 617e301..149b8a6 100644
--- a/utils/unittest/googletest/gtest-death-test.cc
+++ b/utils/unittest/googletest/gtest-death-test.cc
@@ -27,17 +27,31 @@
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
//
-// Author: wan@google.com (Zhanyong Wan)
+// Author: wan@google.com (Zhanyong Wan), vladl@google.com (Vlad Losev)
//
// This file implements death tests.
#include <gtest/gtest-death-test.h>
#include <gtest/internal/gtest-port.h>
-#ifdef GTEST_HAS_DEATH_TEST
+#if GTEST_HAS_DEATH_TEST
+
+#if GTEST_OS_MAC
+#include <crt_externs.h>
+#endif // GTEST_OS_MAC
+
#include <errno.h>
+#include <fcntl.h>
#include <limits.h>
#include <stdarg.h>
+
+#if GTEST_OS_WINDOWS
+#include <windows.h>
+#else
+#include <sys/mman.h>
+#include <sys/wait.h>
+#endif // GTEST_OS_WINDOWS
+
#endif // GTEST_HAS_DEATH_TEST
#include <gtest/gtest-message.h>
@@ -48,9 +62,9 @@
// included, or there will be a compiler error. This trick is to
// prevent a user from accidentally including gtest-internal-inl.h in
// his code.
-#define GTEST_IMPLEMENTATION
+#define GTEST_IMPLEMENTATION_ 1
#include "gtest/internal/gtest-internal-inl.h"
-#undef GTEST_IMPLEMENTATION
+#undef GTEST_IMPLEMENTATION_
namespace testing {
@@ -68,6 +82,18 @@ GTEST_DEFINE_string_(
"\"fast\" (child process runs the death test immediately "
"after forking).");
+GTEST_DEFINE_bool_(
+ death_test_use_fork,
+ internal::BoolFromGTestEnv("death_test_use_fork", false),
+ "Instructs to use fork()/_exit() instead of clone() in death tests. "
+ "Ignored and always uses fork() on POSIX systems where clone() is not "
+ "implemented. Useful when running under valgrind or similar tools if "
+ "those do not support clone(). Valgrind 3.3.1 will just fail if "
+ "it sees an unsupported combination of clone() flags. "
+ "It is not recommended to use this flag w/o valgrind though it will "
+ "work in 99% of the cases. Once valgrind is fixed, this flag will "
+ "most likely be removed.");
+
namespace internal {
GTEST_DEFINE_string_(
internal_run_death_test, "",
@@ -79,7 +105,7 @@ GTEST_DEFINE_string_(
"death test. FOR INTERNAL USE ONLY.");
} // namespace internal
-#ifdef GTEST_HAS_DEATH_TEST
+#if GTEST_HAS_DEATH_TEST
// ExitedWithCode constructor.
ExitedWithCode::ExitedWithCode(int exit_code) : exit_code_(exit_code) {
@@ -87,9 +113,14 @@ ExitedWithCode::ExitedWithCode(int exit_code) : exit_code_(exit_code) {
// ExitedWithCode function-call operator.
bool ExitedWithCode::operator()(int exit_status) const {
+#if GTEST_OS_WINDOWS
+ return exit_status == exit_code_;
+#else
return WIFEXITED(exit_status) && WEXITSTATUS(exit_status) == exit_code_;
+#endif // GTEST_OS_WINDOWS
}
+#if !GTEST_OS_WINDOWS
// KilledBySignal constructor.
KilledBySignal::KilledBySignal(int signum) : signum_(signum) {
}
@@ -98,6 +129,7 @@ KilledBySignal::KilledBySignal(int signum) : signum_(signum) {
bool KilledBySignal::operator()(int exit_status) const {
return WIFSIGNALED(exit_status) && WTERMSIG(exit_status) == signum_;
}
+#endif // !GTEST_OS_WINDOWS
namespace internal {
@@ -107,6 +139,9 @@ namespace internal {
// specified by wait(2).
static String ExitSummary(int exit_code) {
Message m;
+#if GTEST_OS_WINDOWS
+ m << "Exited with exit status " << exit_code;
+#else
if (WIFEXITED(exit_code)) {
m << "Exited with exit status " << WEXITSTATUS(exit_code);
} else if (WIFSIGNALED(exit_code)) {
@@ -117,6 +152,7 @@ static String ExitSummary(int exit_code) {
m << " (core dumped)";
}
#endif
+#endif // GTEST_OS_WINDOWS
return m.GetString();
}
@@ -126,6 +162,7 @@ bool ExitedUnsuccessfully(int exit_status) {
return !ExitedWithCode(0)(exit_status);
}
+#if !GTEST_OS_WINDOWS
// Generates a textual failure message when a death test finds more than
// one thread running, or cannot determine the number of threads, prior
// to executing the given statement. It is the responsibility of the
@@ -133,17 +170,14 @@ bool ExitedUnsuccessfully(int exit_status) {
static String DeathTestThreadWarning(size_t thread_count) {
Message msg;
msg << "Death tests use fork(), which is unsafe particularly"
- << " in a threaded context. For this test, " << GTEST_NAME << " ";
+ << " in a threaded context. For this test, " << GTEST_NAME_ << " ";
if (thread_count == 0)
msg << "couldn't detect the number of threads.";
else
msg << "detected " << thread_count << " threads.";
return msg.GetString();
}
-
-// Static string containing a description of the outcome of the
-// last death test.
-static String last_death_test_message;
+#endif // !GTEST_OS_WINDOWS
// Flag characters for reporting a death test that did not die.
static const char kDeathTestLived = 'L';
@@ -159,29 +193,33 @@ static const char kDeathTestInternalError = 'I';
enum DeathTestOutcome { IN_PROGRESS, DIED, LIVED, RETURNED };
// Routine for aborting the program which is safe to call from an
-// exec-style death test child process, in which case the the error
+// exec-style death test child process, in which case the error
// message is propagated back to the parent process. Otherwise, the
// message is simply printed to stderr. In either case, the program
// then exits with status 1.
-void DeathTestAbort(const char* format, ...) {
- // This function may be called from a threadsafe-style death test
- // child process, which operates on a very small stack. Use the
- // heap for any additional non-miniscule memory requirements.
+void DeathTestAbort(const String& message) {
+ // On a POSIX system, this function may be called from a threadsafe-style
+ // death test child process, which operates on a very small stack. Use
+ // the heap for any additional non-minuscule memory requirements.
const InternalRunDeathTestFlag* const flag =
GetUnitTestImpl()->internal_run_death_test_flag();
- va_list args;
- va_start(args, format);
-
if (flag != NULL) {
- FILE* parent = fdopen(flag->status_fd, "w");
+// Suppress MSVC complaints about POSIX functions.
+#ifdef _MSC_VER
+#pragma warning(push)
+#pragma warning(disable: 4996)
+#endif // _MSC_VER
+ FILE* parent = fdopen(flag->status_fd(), "w");
+#ifdef _MSC_VER
+#pragma warning(pop)
+#endif // _MSC_VER
fputc(kDeathTestInternalError, parent);
- vfprintf(parent, format, args);
- fclose(parent);
- va_end(args);
+ fprintf(parent, "%s", message.c_str());
+ fflush(parent);
_exit(1);
} else {
- vfprintf(stderr, format, args);
- va_end(args);
+ fprintf(stderr, "%s", message.c_str());
+ fflush(stderr);
abort();
}
}
@@ -191,8 +229,9 @@ void DeathTestAbort(const char* format, ...) {
#define GTEST_DEATH_TEST_CHECK_(expression) \
do { \
if (!(expression)) { \
- DeathTestAbort("CHECK failed: File %s, line %d: %s", \
- __FILE__, __LINE__, #expression); \
+ DeathTestAbort(::testing::internal::String::Format(\
+ "CHECK failed: File %s, line %d: %s", \
+ __FILE__, __LINE__, #expression)); \
} \
} while (0)
@@ -205,16 +244,59 @@ void DeathTestAbort(const char* format, ...) {
// something other than EINTR, DeathTestAbort is called.
#define GTEST_DEATH_TEST_CHECK_SYSCALL_(expression) \
do { \
- int retval; \
+ int gtest_retval; \
do { \
- retval = (expression); \
- } while (retval == -1 && errno == EINTR); \
- if (retval == -1) { \
- DeathTestAbort("CHECK failed: File %s, line %d: %s != -1", \
- __FILE__, __LINE__, #expression); \
+ gtest_retval = (expression); \
+ } while (gtest_retval == -1 && errno == EINTR); \
+ if (gtest_retval == -1) { \
+ DeathTestAbort(::testing::internal::String::Format(\
+ "CHECK failed: File %s, line %d: %s != -1", \
+ __FILE__, __LINE__, #expression)); \
} \
} while (0)
+// Returns the message describing the last system error, regardless of the
+// platform.
+String GetLastSystemErrorMessage() {
+#if GTEST_OS_WINDOWS
+ const DWORD error_num = ::GetLastError();
+
+ if (error_num == NULL)
+ return String("");
+
+ char* message_ptr;
+
+ ::FormatMessageA(
+ // The caller does not provide a buffer. The function will allocate one.
+ FORMAT_MESSAGE_ALLOCATE_BUFFER |
+ // The function must look up an error message in its system error
+ // message table.
+ FORMAT_MESSAGE_FROM_SYSTEM |
+ // Do not expand insert sequences in the message definition.
+ FORMAT_MESSAGE_IGNORE_INSERTS,
+ NULL, // Message source. Ignored in this call.
+ error_num,
+ 0x0, // Use system-default language.
+ reinterpret_cast<LPSTR>(&message_ptr),
+ 0, // Buffer size. Ignored in this call.
+ NULL); // Message arguments. Ignored in this call.
+
+ const String message = message_ptr;
+ ::LocalFree(message_ptr);
+ return message;
+#else
+ return errno == 0 ? String("") : String(strerror(errno));
+#endif // GTEST_OS_WINDOWS
+}
+
+// TODO(vladl@google.com): Move the definition of FailFromInternalError
+// here.
+#if GTEST_OS_WINDOWS
+static void FailFromInternalError(HANDLE handle);
+#else
+static void FailFromInternalError(int fd);
+#endif // GTEST_OS_WINDOWS
+
// Death test constructor. Increments the running death test count
// for the current test.
DeathTest::DeathTest() {
@@ -234,61 +316,393 @@ bool DeathTest::Create(const char* statement, const RE* regex,
}
const char* DeathTest::LastMessage() {
- return last_death_test_message.c_str();
+ return last_death_test_message_.c_str();
}
+void DeathTest::set_last_death_test_message(const String& message) {
+ last_death_test_message_ = message;
+}
+
+String DeathTest::last_death_test_message_;
+
+// Provides cross platform implementation for some death functionality.
+// TODO(vladl@google.com): Merge this class with DeathTest in
+// gtest-death-test-internal.h.
+class DeathTestImpl : public DeathTest {
+ protected:
+ DeathTestImpl(const char* statement, const RE* regex)
+ : statement_(statement),
+ regex_(regex),
+ spawned_(false),
+ status_(-1),
+ outcome_(IN_PROGRESS) {}
+
+ virtual bool Passed(bool status_ok);
+
+ const char* statement() const { return statement_; }
+ const RE* regex() const { return regex_; }
+ bool spawned() const { return spawned_; }
+ void set_spawned(bool spawned) { spawned_ = spawned; }
+ int status() const { return status_; }
+ void set_status(int status) { status_ = status; }
+ DeathTestOutcome outcome() const { return outcome_; }
+ void set_outcome(DeathTestOutcome outcome) { outcome_ = outcome; }
+
+ private:
+ // The textual content of the code this object is testing. This class
+ // doesn't own this string and should not attempt to delete it.
+ const char* const statement_;
+ // The regular expression which test output must match. DeathTestImpl
+ // doesn't own this object and should not attempt to delete it.
+ const RE* const regex_;
+ // True if the death test child process has been successfully spawned.
+ bool spawned_;
+ // The exit status of the child process.
+ int status_;
+ // How the death test concluded.
+ DeathTestOutcome outcome_;
+};
+
+// TODO(vladl@google.com): Move definition of DeathTestImpl::Passed() here.
+
+#if GTEST_OS_WINDOWS
+// WindowsDeathTest implements death tests on Windows. Due to the
+// specifics of starting new processes on Windows, death tests there are
+// always threadsafe, and Google Test considers the
+// --gtest_death_test_style=fast setting to be equivalent to
+// --gtest_death_test_style=threadsafe there.
+//
+// A few implementation notes: Like the Linux version, the Windows
+// implementation uses pipes for child-to-parent communication. But due to
+// the specifics of pipes on Windows, some extra steps are required:
+//
+// 1. The parent creates a communication pipe and stores handles to both
+// ends of it.
+// 2. The parent starts the child and provides it with the information
+// necessary to acquire the handle to the write end of the pipe.
+// 3. The child acquires the write end of the pipe and signals the parent
+// using a Windows event.
+// 4. Now the parent can release the write end of the pipe on its side. If
+// this is done before step 3, the object's reference count goes down to
+// 0 and it is destroyed, preventing the child from acquiring it. The
+// parent now has to release it, or read operations on the read end of
+// the pipe will not return when the child terminates.
+// 5. The parent reads child's output through the pipe (outcome code and
+// any possible error messages) from the pipe, and its stderr and then
+// determines whether to fail the test.
+//
+// Note: to distinguish Win32 API calls from the local method and function
+// calls, the former are explicitly resolved in the global namespace.
+//
+class WindowsDeathTest : public DeathTestImpl {
+ public:
+ WindowsDeathTest(const char* statement,
+ const RE* regex,
+ const char* file,
+ int line)
+ : DeathTestImpl(statement, regex), file_(file), line_(line) {}
+
+ // All of these virtual functions are inherited from DeathTest.
+ virtual int Wait();
+ virtual void Abort(AbortReason reason);
+ virtual TestRole AssumeRole();
+
+ private:
+ // The name of the file in which the death test is located.
+ const char* const file_;
+ // The line number on which the death test is located.
+ const int line_;
+ // Handle to the read end of the pipe to the child process.
+ // The child keeps its write end of the pipe in the status_handle_
+ // field of its InternalRunDeathTestFlag class.
+ AutoHandle read_handle_;
+ // Handle to the write end of the pipe to the child process.
+ AutoHandle write_handle_;
+ // Child process handle.
+ AutoHandle child_handle_;
+ // Event the child process uses to signal the parent that it has
+ // acquired the handle to the write end of the pipe. After seeing this
+ // event the parent can release its own handles to make sure its
+ // ReadFile() calls return when the child terminates.
+ AutoHandle event_handle_;
+};
+
+// Waits for the child in a death test to exit, returning its exit
+// status, or 0 if no child process exists. As a side effect, sets the
+// outcome data member.
+// TODO(vladl@google.com): Outcome classification logic is common with
+// ForkingDeathTes::Wait(). Refactor it into a
+// common function.
+int WindowsDeathTest::Wait() {
+ if (!spawned())
+ return 0;
+
+ // Wait until the child either signals that it has acquired the write end
+ // of the pipe or it dies.
+ const HANDLE wait_handles[2] = { child_handle_.Get(), event_handle_.Get() };
+ switch (::WaitForMultipleObjects(2,
+ wait_handles,
+ FALSE, // Waits for any of the handles.
+ INFINITE)) {
+ case WAIT_OBJECT_0:
+ case WAIT_OBJECT_0 + 1:
+ break;
+ default:
+ GTEST_DEATH_TEST_CHECK_(false); // Should not get here.
+ }
+
+ // The child has acquired the write end of the pipe or exited.
+ // We release the handle on our side and continue.
+ write_handle_.Reset();
+ event_handle_.Reset();
+
+ // ReadFile() blocks until data is available (signifying the
+ // failure of the death test) or until the pipe is closed (signifying
+ // its success), so it's okay to call this in the parent before or
+ // after the child process has exited.
+ char flag;
+ DWORD bytes_read;
+ GTEST_DEATH_TEST_CHECK_(::ReadFile(read_handle_.Get(),
+ &flag,
+ 1,
+ &bytes_read,
+ NULL) ||
+ ::GetLastError() == ERROR_BROKEN_PIPE);
+
+ if (bytes_read == 0) {
+ set_outcome(DIED);
+ } else if (bytes_read == 1) {
+ switch (flag) {
+ case kDeathTestReturned:
+ set_outcome(RETURNED);
+ break;
+ case kDeathTestLived:
+ set_outcome(LIVED);
+ break;
+ case kDeathTestInternalError:
+ FailFromInternalError(read_handle_.Get()); // Does not return.
+ break;
+ default:
+ GTEST_LOG_(FATAL,
+ Message() << "Death test child process reported "
+ << " unexpected status byte ("
+ << static_cast<unsigned int>(flag) << ")");
+ }
+ } else {
+ GTEST_LOG_(FATAL,
+ Message() << "Read from death test child process failed: "
+ << GetLastSystemErrorMessage());
+ }
+ read_handle_.Reset(); // Done with reading.
+
+ // Waits for the child process to exit if it haven't already. This
+ // returns immediately if the child has already exited, regardless of
+ // whether previous calls to WaitForMultipleObjects synchronized on this
+ // handle or not.
+ GTEST_DEATH_TEST_CHECK_(
+ WAIT_OBJECT_0 == ::WaitForSingleObject(child_handle_.Get(),
+ INFINITE));
+ DWORD status;
+ GTEST_DEATH_TEST_CHECK_(::GetExitCodeProcess(child_handle_.Get(),
+ &status));
+ child_handle_.Reset();
+ set_status(static_cast<int>(status));
+ return this->status();
+}
+
+// TODO(vladl@google.com): define a cross-platform way to write to
+// status_fd to be used both here and in ForkingDeathTest::Abort().
+//
+// Signals that the death test did not die as expected. This is called
+// from the child process only.
+void WindowsDeathTest::Abort(AbortReason reason) {
+ const InternalRunDeathTestFlag* const internal_flag =
+ GetUnitTestImpl()->internal_run_death_test_flag();
+ // The parent process considers the death test to be a failure if
+ // it finds any data in our pipe. So, here we write a single flag byte
+ // to the pipe, then exit.
+ const char status_ch =
+ reason == TEST_DID_NOT_DIE ? kDeathTestLived : kDeathTestReturned;
+
+#ifdef _MSC_VER
+#pragma warning(push)
+#pragma warning(disable: 4996)
+#endif // _MSC_VER
+ GTEST_DEATH_TEST_CHECK_SYSCALL_(write(internal_flag->status_fd(),
+ &status_ch, 1));
+#ifdef _MSC_VER
+#pragma warning(pop)
+#endif // _MSC_VER
+
+ // The write handle will be closed when the child terminates in _exit().
+ _exit(1); // Exits w/o any normal exit hooks (we were supposed to crash)
+}
+
+// The AssumeRole process for a Windows death test. It creates a child
+// process with the same executable as the current process to run the
+// death test. The child process is given the --gtest_filter and
+// --gtest_internal_run_death_test flags such that it knows to run the
+// current death test only.
+DeathTest::TestRole WindowsDeathTest::AssumeRole() {
+ const UnitTestImpl* const impl = GetUnitTestImpl();
+ const InternalRunDeathTestFlag* const flag =
+ impl->internal_run_death_test_flag();
+ const TestInfo* const info = impl->current_test_info();
+ const int death_test_index = info->result()->death_test_count();
+
+ if (flag != NULL) {
+ // ParseInternalRunDeathTestFlag() has performed all the necessary
+ // processing.
+ return EXECUTE_TEST;
+ }
+
+ // WindowsDeathTest uses an anonymous pipe to communicate results of
+ // a death test.
+ SECURITY_ATTRIBUTES handles_are_inheritable = {
+ sizeof(SECURITY_ATTRIBUTES), NULL, TRUE };
+ HANDLE read_handle, write_handle;
+ GTEST_DEATH_TEST_CHECK_(::CreatePipe(&read_handle, &write_handle,
+ &handles_are_inheritable,
+ 0)); // Default buffer size.
+ read_handle_.Reset(read_handle);
+ write_handle_.Reset(write_handle);
+ event_handle_.Reset(::CreateEvent(
+ &handles_are_inheritable,
+ TRUE, // The event will automatically reset to non-signaled state.
+ FALSE, // The initial state is non-signalled.
+ NULL)); // The even is unnamed.
+ GTEST_DEATH_TEST_CHECK_(event_handle_.Get() != NULL);
+ const String filter_flag = String::Format("--%s%s=%s.%s",
+ GTEST_FLAG_PREFIX_, kFilterFlag,
+ info->test_case_name(),
+ info->name());
+ const String internal_flag = String::Format(
+ "--%s%s=%s|%d|%d|%u|%Iu|%Iu",
+ GTEST_FLAG_PREFIX_,
+ kInternalRunDeathTestFlag,
+ file_, line_,
+ death_test_index,
+ static_cast<unsigned int>(::GetCurrentProcessId()),
+ // size_t has the same with as pointers on both 32-bit and 64-bit
+ // Windows platforms.
+ // See http://msdn.microsoft.com/en-us/library/tcxf1dw6.aspx.
+ reinterpret_cast<size_t>(write_handle),
+ reinterpret_cast<size_t>(event_handle_.Get()));
+
+ char executable_path[_MAX_PATH + 1]; // NOLINT
+ GTEST_DEATH_TEST_CHECK_(
+ _MAX_PATH + 1 != ::GetModuleFileNameA(NULL,
+ executable_path,
+ _MAX_PATH));
+
+ String command_line = String::Format("%s %s \"%s\"",
+ ::GetCommandLineA(),
+ filter_flag.c_str(),
+ internal_flag.c_str());
+
+ DeathTest::set_last_death_test_message("");
+
+ CaptureStderr();
+ // Flush the log buffers since the log streams are shared with the child.
+ FlushInfoLog();
+
+ // The child process will share the standard handles with the parent.
+ STARTUPINFOA startup_info;
+ memset(&startup_info, 0, sizeof(STARTUPINFO));
+ startup_info.dwFlags = STARTF_USESTDHANDLES;
+ startup_info.hStdInput = ::GetStdHandle(STD_INPUT_HANDLE);
+ startup_info.hStdOutput = ::GetStdHandle(STD_OUTPUT_HANDLE);
+ startup_info.hStdError = ::GetStdHandle(STD_ERROR_HANDLE);
+
+ PROCESS_INFORMATION process_info;
+ GTEST_DEATH_TEST_CHECK_(::CreateProcessA(
+ executable_path,
+ const_cast<char*>(command_line.c_str()),
+ NULL, // Retuned process handle is not inheritable.
+ NULL, // Retuned thread handle is not inheritable.
+ TRUE, // Child inherits all inheritable handles (for write_handle_).
+ 0x0, // Default creation flags.
+ NULL, // Inherit the parent's environment.
+ UnitTest::GetInstance()->original_working_dir(),
+ &startup_info,
+ &process_info));
+ child_handle_.Reset(process_info.hProcess);
+ ::CloseHandle(process_info.hThread);
+ set_spawned(true);
+ return OVERSEE_TEST;
+}
+#else // We are not on Windows.
+
// ForkingDeathTest provides implementations for most of the abstract
// methods of the DeathTest interface. Only the AssumeRole method is
// left undefined.
-class ForkingDeathTest : public DeathTest {
+class ForkingDeathTest : public DeathTestImpl {
public:
ForkingDeathTest(const char* statement, const RE* regex);
// All of these virtual functions are inherited from DeathTest.
virtual int Wait();
- virtual bool Passed(bool status_ok);
virtual void Abort(AbortReason reason);
protected:
- void set_forked(bool forked) { forked_ = forked; }
void set_child_pid(pid_t child_pid) { child_pid_ = child_pid; }
void set_read_fd(int fd) { read_fd_ = fd; }
void set_write_fd(int fd) { write_fd_ = fd; }
private:
- // The textual content of the code this object is testing.
- const char* const statement_;
- // The regular expression which test output must match.
- const RE* const regex_;
- // True if the death test successfully forked.
- bool forked_;
// PID of child process during death test; 0 in the child process itself.
pid_t child_pid_;
// File descriptors for communicating the death test's status byte.
int read_fd_; // Always -1 in the child process.
int write_fd_; // Always -1 in the parent process.
- // The exit status of the child process.
- int status_;
- // How the death test concluded.
- DeathTestOutcome outcome_;
};
// Constructs a ForkingDeathTest.
ForkingDeathTest::ForkingDeathTest(const char* statement, const RE* regex)
- : DeathTest(),
- statement_(statement),
- regex_(regex),
- forked_(false),
+ : DeathTestImpl(statement, regex),
child_pid_(-1),
read_fd_(-1),
- write_fd_(-1),
- status_(-1),
- outcome_(IN_PROGRESS) {
+ write_fd_(-1) {
}
+#endif // GTEST_OS_WINDOWS
+
+// This is called from a death test parent process to read a failure
+// message from the death test child process and log it with the FATAL
+// severity. On Windows, the message is read from a pipe handle. On other
+// platforms, it is read from a file descriptor.
+// TODO(vladl@google.com): Re-factor the code to merge common parts after
+// the reading code is abstracted.
+#if GTEST_OS_WINDOWS
+static void FailFromInternalError(HANDLE handle) {
+ Message error;
+ char buffer[256];
-// Reads an internal failure message from a file descriptor, then calls
-// LOG(FATAL) with that message. Called from a death test parent process
-// to read a failure message from the death test child process.
+ bool read_succeeded = true;
+ DWORD bytes_read;
+ do {
+ // ERROR_BROKEN_PIPE arises when the other end of the pipe has been
+ // closed. This is a normal condition for us.
+ bytes_read = 0;
+ read_succeeded = ::ReadFile(handle,
+ buffer,
+ sizeof(buffer) - 1,
+ &bytes_read,
+ NULL) || ::GetLastError() == ERROR_BROKEN_PIPE;
+ buffer[bytes_read] = 0;
+ error << buffer;
+ } while (read_succeeded && bytes_read > 0);
+
+ if (read_succeeded) {
+ GTEST_LOG_(FATAL, error);
+ } else {
+ const DWORD last_error = ::GetLastError();
+ const String message = GetLastSystemErrorMessage();
+ GTEST_LOG_(FATAL,
+ Message() << "Error while reading death test internal: "
+ << message << " [" << last_error << "]");
+ }
+}
+#else
static void FailFromInternalError(int fd) {
Message error;
char buffer[256];
@@ -301,21 +715,24 @@ static void FailFromInternalError(int fd) {
}
} while (num_read == -1 && errno == EINTR);
- // TODO(smcafee): Maybe just FAIL the test instead?
if (num_read == 0) {
GTEST_LOG_(FATAL, error);
} else {
+ const int last_error = errno;
+ const String message = GetLastSystemErrorMessage();
GTEST_LOG_(FATAL,
Message() << "Error while reading death test internal: "
- << strerror(errno) << " [" << errno << "]");
+ << message << " [" << last_error << "]");
}
}
+#endif // GTEST_OS_WINDOWS
+#if !GTEST_OS_WINDOWS
// Waits for the child in a death test to exit, returning its exit
// status, or 0 if no child process exists. As a side effect, sets the
// outcome data member.
int ForkingDeathTest::Wait() {
- if (!forked_)
+ if (!spawned())
return 0;
// The read() here blocks until data is available (signifying the
@@ -330,14 +747,14 @@ int ForkingDeathTest::Wait() {
} while (bytes_read == -1 && errno == EINTR);
if (bytes_read == 0) {
- outcome_ = DIED;
+ set_outcome(DIED);
} else if (bytes_read == 1) {
switch (flag) {
case kDeathTestReturned:
- outcome_ = RETURNED;
+ set_outcome(RETURNED);
break;
case kDeathTestLived:
- outcome_ = LIVED;
+ set_outcome(LIVED);
break;
case kDeathTestInternalError:
FailFromInternalError(read_fd_); // Does not return.
@@ -349,28 +766,34 @@ int ForkingDeathTest::Wait() {
<< ")");
}
} else {
+ const String error_message = GetLastSystemErrorMessage();
GTEST_LOG_(FATAL,
Message() << "Read from death test child process failed: "
- << strerror(errno));
+ << error_message);
}
GTEST_DEATH_TEST_CHECK_SYSCALL_(close(read_fd_));
- GTEST_DEATH_TEST_CHECK_SYSCALL_(waitpid(child_pid_, &status_, 0));
- return status_;
+ int status;
+ GTEST_DEATH_TEST_CHECK_SYSCALL_(waitpid(child_pid_, &status, 0));
+ set_status(status);
+ return status;
}
+#endif // !GTEST_OS_WINDOWS
// Assesses the success or failure of a death test, using both private
// members which have previously been set, and one argument:
//
// Private data members:
-// outcome: an enumeration describing how the death test
+// outcome: An enumeration describing how the death test
// concluded: DIED, LIVED, or RETURNED. The death test fails
-// in the latter two cases
-// status: the exit status of the child process, in the format
-// specified by wait(2)
-// regex: a regular expression object to be applied to
+// in the latter two cases.
+// status: The exit status of the child process. On *nix, it is in the
+// in the format specified by wait(2). On Windows, this is the
+// value supplied to the ExitProcess() API or a numeric code
+// of the exception that terminated the program.
+// regex: A regular expression object to be applied to
// the test's captured standard error output; the death test
-// fails if it does not match
+// fails if it does not match.
//
// Argument:
// status_ok: true if exit_status is acceptable in the context of
@@ -378,9 +801,9 @@ int ForkingDeathTest::Wait() {
//
// 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
-// reported. Also sets the static variable last_death_test_message.
-bool ForkingDeathTest::Passed(bool status_ok) {
- if (!forked_)
+// reported. Also sets the last death test message string.
+bool DeathTestImpl::Passed(bool status_ok) {
+ if (!spawned())
return false;
#if GTEST_HAS_GLOBAL_STRING
@@ -392,8 +815,8 @@ bool ForkingDeathTest::Passed(bool status_ok) {
bool success = false;
Message buffer;
- buffer << "Death test: " << statement_ << "\n";
- switch (outcome_) {
+ buffer << "Death test: " << statement() << "\n";
+ switch (outcome()) {
case LIVED:
buffer << " Result: failed to die.\n"
<< " Error msg: " << error_message;
@@ -404,16 +827,16 @@ bool ForkingDeathTest::Passed(bool status_ok) {
break;
case DIED:
if (status_ok) {
- if (RE::PartialMatch(error_message, *regex_)) {
+ if (RE::PartialMatch(error_message, *regex())) {
success = true;
} else {
buffer << " Result: died but not with expected error.\n"
- << " Expected: " << regex_->pattern() << "\n"
+ << " Expected: " << regex()->pattern() << "\n"
<< "Actual msg: " << error_message;
}
} else {
buffer << " Result: died but not with expected exit code:\n"
- << " " << ExitSummary(status_) << "\n";
+ << " " << ExitSummary(status()) << "\n";
}
break;
case IN_PROGRESS:
@@ -422,13 +845,14 @@ bool ForkingDeathTest::Passed(bool status_ok) {
"DeathTest::Passed somehow called before conclusion of test");
}
- last_death_test_message = buffer.GetString();
+ DeathTest::set_last_death_test_message(buffer.GetString());
return success;
}
+#if !GTEST_OS_WINDOWS
// Signals that the death test code which should have exited, didn't.
// Should be called only in a death test child process.
-// Writes a status byte to the child's status file desriptor, then
+// Writes a status byte to the child's status file descriptor, then
// calls _exit(1).
void ForkingDeathTest::Abort(AbortReason reason) {
// The parent process considers the death test to be a failure if
@@ -461,7 +885,7 @@ DeathTest::TestRole NoExecDeathTest::AssumeRole() {
int pipe_fd[2];
GTEST_DEATH_TEST_CHECK_(pipe(pipe_fd) != -1);
- last_death_test_message = "";
+ DeathTest::set_last_death_test_message("");
CaptureStderr();
// When we fork the process below, the log file buffers are copied, but the
// file descriptors are shared. We flush all log files here so that closing
@@ -486,7 +910,7 @@ DeathTest::TestRole NoExecDeathTest::AssumeRole() {
} else {
GTEST_DEATH_TEST_CHECK_SYSCALL_(close(pipe_fd[1]));
set_read_fd(pipe_fd[0]);
- set_forked(true);
+ set_spawned(true);
return OVERSEE_TEST;
}
}
@@ -513,9 +937,9 @@ class Arguments {
Arguments() {
args_.push_back(NULL);
}
+
~Arguments() {
- for (std::vector<char*>::iterator i = args_.begin();
- i + 1 != args_.end();
+ for (std::vector<char*>::iterator i = args_.begin(); i != args_.end();
++i) {
free(*i);
}
@@ -546,6 +970,22 @@ 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
+extern "C" char** environ; // Some POSIX platforms expect you
+ // to declare environ. extern "C" makes
+ // it reside in the global namespace.
+inline char** GetEnviron() {
+ return environ;
+}
+#endif // GTEST_OS_MAC
+
// 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.
@@ -560,8 +1000,9 @@ static int ExecDeathTestChildMain(void* child_arg) {
UnitTest::GetInstance()->original_working_dir();
// We can safely call chdir() as it's a direct system call.
if (chdir(original_dir) != 0) {
- DeathTestAbort("chdir(\"%s\") failed: %s",
- original_dir, strerror(errno));
+ DeathTestAbort(String::Format("chdir(\"%s\") failed: %s",
+ original_dir,
+ GetLastSystemErrorMessage().c_str()));
return EXIT_FAILURE;
}
@@ -570,9 +1011,11 @@ static int ExecDeathTestChildMain(void* child_arg) {
// unsafe. Since execve() 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, environ);
- DeathTestAbort("execve(%s, ...) in %s failed: %s",
- args->argv[0], original_dir, strerror(errno));
+ execve(args->argv[0], args->argv, GetEnviron());
+ DeathTestAbort(String::Format("execve(%s, ...) in %s failed: %s",
+ args->argv[0],
+ original_dir,
+ GetLastSystemErrorMessage().c_str()));
return EXIT_FAILURE;
}
@@ -581,12 +1024,12 @@ static int ExecDeathTestChildMain(void* child_arg) {
// This could be accomplished more elegantly by a single recursive
// function, but we want to guard against the unlikely possibility of
// a smart compiler optimizing the recursion away.
-static bool StackLowerThanAddress(const void* ptr) {
+bool StackLowerThanAddress(const void* ptr) {
int dummy;
return &dummy < ptr;
}
-static bool StackGrowsDown() {
+bool StackGrowsDown() {
int dummy;
return StackLowerThanAddress(&dummy);
}
@@ -595,18 +1038,36 @@ static bool StackGrowsDown() {
// that uses clone(2). It dies with an error message if anything goes
// wrong.
static pid_t ExecDeathTestFork(char* const* argv, int close_fd) {
- static const bool stack_grows_down = StackGrowsDown();
- const size_t stack_size = getpagesize();
- void* const stack = mmap(NULL, stack_size, PROT_READ | PROT_WRITE,
- MAP_ANONYMOUS | MAP_PRIVATE, -1, 0);
- GTEST_DEATH_TEST_CHECK_(stack != MAP_FAILED);
- void* const stack_top =
- static_cast<char*>(stack) + (stack_grows_down ? stack_size : 0);
ExecDeathTestArgs args = { argv, close_fd };
- const pid_t child_pid = clone(&ExecDeathTestChildMain, stack_top,
- SIGCHLD, &args);
+ pid_t child_pid;
+
+#if GTEST_HAS_CLONE
+ const bool use_fork = GTEST_FLAG(death_test_use_fork);
+
+ if (!use_fork) {
+ static const bool stack_grows_down = StackGrowsDown();
+ const size_t stack_size = getpagesize();
+ // MMAP_ANONYMOUS is not defined on Mac, so we use MAP_ANON instead.
+ void* const stack = mmap(NULL, stack_size, PROT_READ | PROT_WRITE,
+ MAP_ANON | MAP_PRIVATE, -1, 0);
+ GTEST_DEATH_TEST_CHECK_(stack != MAP_FAILED);
+ void* const stack_top =
+ static_cast<char*>(stack) + (stack_grows_down ? stack_size : 0);
+
+ child_pid = clone(&ExecDeathTestChildMain, stack_top, SIGCHLD, &args);
+
+ GTEST_DEATH_TEST_CHECK_(munmap(stack, stack_size) != -1);
+ }
+#else
+ const bool use_fork = true;
+#endif // GTEST_HAS_CLONE
+
+ if (use_fork && (child_pid = fork()) == 0) {
+ ExecDeathTestChildMain(&args);
+ _exit(0);
+ }
+
GTEST_DEATH_TEST_CHECK_(child_pid != -1);
- GTEST_DEATH_TEST_CHECK_(munmap(stack, stack_size) != -1);
return child_pid;
}
@@ -622,7 +1083,7 @@ DeathTest::TestRole ExecDeathTest::AssumeRole() {
const int death_test_index = info->result()->death_test_count();
if (flag != NULL) {
- set_write_fd(flag->status_fd);
+ set_write_fd(flag->status_fd());
return EXECUTE_TEST;
}
@@ -634,19 +1095,18 @@ DeathTest::TestRole ExecDeathTest::AssumeRole() {
const String filter_flag =
String::Format("--%s%s=%s.%s",
- GTEST_FLAG_PREFIX, kFilterFlag,
+ GTEST_FLAG_PREFIX_, kFilterFlag,
info->test_case_name(), info->name());
const String internal_flag =
- String::Format("--%s%s=%s:%d:%d:%d",
- GTEST_FLAG_PREFIX, kInternalRunDeathTestFlag, file_, line_,
- death_test_index, pipe_fd[1]);
+ String::Format("--%s%s=%s|%d|%d|%d",
+ GTEST_FLAG_PREFIX_, kInternalRunDeathTestFlag,
+ file_, line_, death_test_index, pipe_fd[1]);
Arguments args;
args.AddArguments(GetArgvs());
- args.AddArgument("--logtostderr");
args.AddArgument(filter_flag.c_str());
args.AddArgument(internal_flag.c_str());
- last_death_test_message = "";
+ DeathTest::set_last_death_test_message("");
CaptureStderr();
// See the comment in NoExecDeathTest::AssumeRole for why the next line
@@ -657,10 +1117,12 @@ DeathTest::TestRole ExecDeathTest::AssumeRole() {
GTEST_DEATH_TEST_CHECK_SYSCALL_(close(pipe_fd[1]));
set_child_pid(child_pid);
set_read_fd(pipe_fd[0]);
- set_forked(true);
+ set_spawned(true);
return OVERSEE_TEST;
}
+#endif // !GTEST_OS_WINDOWS
+
// Creates a concrete DeathTest-derived class that depends on the
// --gtest_death_test_style flag, and sets the pointer pointed to
// by the "test" argument to its address. If the test should be
@@ -676,28 +1138,36 @@ bool DefaultDeathTestFactory::Create(const char* statement, const RE* regex,
->increment_death_test_count();
if (flag != NULL) {
- if (death_test_index > flag->index) {
- last_death_test_message = String::Format(
+ if (death_test_index > flag->index()) {
+ DeathTest::set_last_death_test_message(String::Format(
"Death test count (%d) somehow exceeded expected maximum (%d)",
- death_test_index, flag->index);
+ death_test_index, flag->index()));
return false;
}
- if (!(flag->file == file && flag->line == line &&
- flag->index == death_test_index)) {
+ if (!(flag->file() == file && flag->line() == line &&
+ flag->index() == death_test_index)) {
*test = NULL;
return true;
}
}
+#if GTEST_OS_WINDOWS
+ if (GTEST_FLAG(death_test_style) == "threadsafe" ||
+ GTEST_FLAG(death_test_style) == "fast") {
+ *test = new WindowsDeathTest(statement, regex, file, line);
+ }
+#else
if (GTEST_FLAG(death_test_style) == "threadsafe") {
*test = new ExecDeathTest(statement, regex, file, line);
} else if (GTEST_FLAG(death_test_style) == "fast") {
*test = new NoExecDeathTest(statement, regex);
- } else {
- last_death_test_message = String::Format(
+ }
+#endif // GTEST_OS_WINDOWS
+ else { // NOLINT - this is more readable than unbalanced brackets inside #if.
+ DeathTest::set_last_death_test_message(String::Format(
"Unknown death test style \"%s\" encountered",
- GTEST_FLAG(death_test_style).c_str());
+ GTEST_FLAG(death_test_style).c_str()));
return false;
}
@@ -707,6 +1177,8 @@ bool DefaultDeathTestFactory::Create(const char* statement, const RE* regex,
// Splits a given string on a given delimiter, populating a given
// vector with the fields. GTEST_HAS_DEATH_TEST implies that we have
// ::std::string, so we can use it here.
+// TODO(vladl@google.com): Get rid of std::vector to be able to build on
+// Visual C++ 7.1 with exceptions disabled.
static void SplitString(const ::std::string& str, char delimiter,
::std::vector< ::std::string>* dest) {
::std::vector< ::std::string> parsed;
@@ -724,25 +1196,72 @@ static void SplitString(const ::std::string& str, char delimiter,
dest->swap(parsed);
}
-// Attempts to parse a string into a positive integer. Returns true
-// if that is possible. GTEST_HAS_DEATH_TEST implies that we have
-// ::std::string, so we can use it here.
-static bool ParsePositiveInt(const ::std::string& str, int* number) {
- // Fail fast if the given string does not begin with a digit;
- // this bypasses strtol's "optional leading whitespace and plus
- // or minus sign" semantics, which are undesirable here.
- if (str.empty() || !isdigit(str[0])) {
- return false;
+#if GTEST_OS_WINDOWS
+// Recreates the pipe and event handles from the provided parameters,
+// signals the event, and returns a file descriptor wrapped around the pipe
+// handle. This function is called in the child process only.
+int GetStatusFileDescriptor(unsigned int parent_process_id,
+ size_t status_handle_as_size_t,
+ size_t event_handle_as_size_t) {
+ AutoHandle parent_process_handle(::OpenProcess(PROCESS_DUP_HANDLE,
+ FALSE, // Non-inheritable.
+ parent_process_id));
+ if (parent_process_handle.Get() == INVALID_HANDLE_VALUE) {
+ DeathTestAbort(String::Format("Unable to open parent process %u",
+ parent_process_id));
}
- char* endptr;
- const long parsed = strtol(str.c_str(), &endptr, 10); // NOLINT
- if (*endptr == '\0' && parsed <= INT_MAX) {
- *number = static_cast<int>(parsed);
- return true;
- } else {
- return false;
+
+ // TODO(vladl@google.com): Replace the following check with a
+ // compile-time assertion when available.
+ GTEST_CHECK_(sizeof(HANDLE) <= sizeof(size_t));
+
+ const HANDLE status_handle =
+ reinterpret_cast<HANDLE>(status_handle_as_size_t);
+ HANDLE dup_status_handle;
+
+ // The newly initialized handle is accessible only in in the parent
+ // process. To obtain one accessible within the child, we need to use
+ // DuplicateHandle.
+ if (!::DuplicateHandle(parent_process_handle.Get(), status_handle,
+ ::GetCurrentProcess(), &dup_status_handle,
+ 0x0, // Requested privileges ignored since
+ // DUPLICATE_SAME_ACCESS is used.
+ FALSE, // Request non-inheritable handler.
+ DUPLICATE_SAME_ACCESS)) {
+ DeathTestAbort(String::Format(
+ "Unable to duplicate the pipe handle %Iu from the parent process %u",
+ status_handle_as_size_t, parent_process_id));
}
+
+ const HANDLE event_handle = reinterpret_cast<HANDLE>(event_handle_as_size_t);
+ HANDLE dup_event_handle;
+
+ if (!::DuplicateHandle(parent_process_handle.Get(), event_handle,
+ ::GetCurrentProcess(), &dup_event_handle,
+ 0x0,
+ FALSE,
+ DUPLICATE_SAME_ACCESS)) {
+ DeathTestAbort(String::Format(
+ "Unable to duplicate the event handle %Iu from the parent process %u",
+ event_handle_as_size_t, parent_process_id));
+ }
+
+ const int status_fd =
+ ::_open_osfhandle(reinterpret_cast<intptr_t>(dup_status_handle),
+ O_APPEND | O_TEXT);
+ if (status_fd == -1) {
+ DeathTestAbort(String::Format(
+ "Unable to convert pipe handle %Iu to a file descriptor",
+ status_handle_as_size_t));
+ }
+
+ // Signals the parent that the write end of the pipe has been acquired
+ // so the parent can release its own write end.
+ ::SetEvent(dup_event_handle);
+
+ return status_fd;
}
+#endif // GTEST_OS_WINDOWS
// Returns a newly created InternalRunDeathTestFlag object with fields
// initialized from the GTEST_FLAG(internal_run_death_test) flag if
@@ -750,22 +1269,43 @@ static bool ParsePositiveInt(const ::std::string& str, int* number) {
InternalRunDeathTestFlag* ParseInternalRunDeathTestFlag() {
if (GTEST_FLAG(internal_run_death_test) == "") return NULL;
- InternalRunDeathTestFlag* const internal_run_death_test_flag =
- new InternalRunDeathTestFlag;
// GTEST_HAS_DEATH_TEST implies that we have ::std::string, so we
// can use it here.
+ int line = -1;
+ int index = -1;
::std::vector< ::std::string> fields;
- SplitString(GTEST_FLAG(internal_run_death_test).c_str(), ':', &fields);
+ SplitString(GTEST_FLAG(internal_run_death_test).c_str(), '|', &fields);
+ int status_fd = -1;
+
+#if GTEST_OS_WINDOWS
+ unsigned int parent_process_id = 0;
+ size_t status_handle_as_size_t = 0;
+ size_t event_handle_as_size_t = 0;
+
+ if (fields.size() != 6
+ || !ParseNaturalNumber(fields[1], &line)
+ || !ParseNaturalNumber(fields[2], &index)
+ || !ParseNaturalNumber(fields[3], &parent_process_id)
+ || !ParseNaturalNumber(fields[4], &status_handle_as_size_t)
+ || !ParseNaturalNumber(fields[5], &event_handle_as_size_t)) {
+ DeathTestAbort(String::Format(
+ "Bad --gtest_internal_run_death_test flag: %s",
+ GTEST_FLAG(internal_run_death_test).c_str()));
+ }
+ status_fd = GetStatusFileDescriptor(parent_process_id,
+ status_handle_as_size_t,
+ event_handle_as_size_t);
+#else
if (fields.size() != 4
- || !ParsePositiveInt(fields[1], &internal_run_death_test_flag->line)
- || !ParsePositiveInt(fields[2], &internal_run_death_test_flag->index)
- || !ParsePositiveInt(fields[3],
- &internal_run_death_test_flag->status_fd)) {
- DeathTestAbort("Bad --gtest_internal_run_death_test flag: %s",
- GTEST_FLAG(internal_run_death_test).c_str());
- }
- internal_run_death_test_flag->file = fields[0].c_str();
- return internal_run_death_test_flag;
+ || !ParseNaturalNumber(fields[1], &line)
+ || !ParseNaturalNumber(fields[2], &index)
+ || !ParseNaturalNumber(fields[3], &status_fd)) {
+ DeathTestAbort(String::Format(
+ "Bad --gtest_internal_run_death_test flag: %s",
+ GTEST_FLAG(internal_run_death_test).c_str()));
+ }
+#endif // GTEST_OS_WINDOWS
+ return new InternalRunDeathTestFlag(fields[0], line, index, status_fd);
}
} // namespace internal
diff --git a/utils/unittest/googletest/gtest-filepath.cc b/utils/unittest/googletest/gtest-filepath.cc
index 493ba0b..07f828c 100644
--- a/utils/unittest/googletest/gtest-filepath.cc
+++ b/utils/unittest/googletest/gtest-filepath.cc
@@ -36,21 +36,22 @@
#ifdef _WIN32_WCE
#include <windows.h>
-#elif defined(GTEST_OS_WINDOWS)
+#elif GTEST_OS_WINDOWS
#include <direct.h>
#include <io.h>
#include <sys/stat.h>
-#elif defined(GTEST_OS_SYMBIAN)
+#elif GTEST_OS_SYMBIAN
// Symbian OpenC has PATH_MAX in sys/syslimits.h
#include <sys/syslimits.h>
#include <unistd.h>
#else
#include <limits.h>
-#include <sys/stat.h>
-#include <unistd.h>
+#include <sys/stat.h> // NOLINT
+#include <unistd.h> // NOLINT
+#include <climits> // Some Linux distributions define PATH_MAX here.
#endif // _WIN32_WCE or _WIN32
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
#define GTEST_PATH_MAX_ _MAX_PATH
#elif defined(PATH_MAX)
#define GTEST_PATH_MAX_ PATH_MAX
@@ -65,7 +66,7 @@
namespace testing {
namespace internal {
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
const char kPathSeparator = '\\';
const char kPathSeparatorString[] = "\\";
#ifdef _WIN32_WCE
@@ -90,7 +91,7 @@ FilePath FilePath::GetCurrentDir() {
// Windows CE doesn't have a current directory, so we just return
// something reasonable.
return FilePath(kCurrentDirectoryString);
-#elif defined(GTEST_OS_WINDOWS)
+#elif GTEST_OS_WINDOWS
char cwd[GTEST_PATH_MAX_ + 1] = {};
return FilePath(_getcwd(cwd, sizeof(cwd)) == NULL ? "" : cwd);
#else
@@ -144,19 +145,28 @@ FilePath FilePath::MakeFileName(const FilePath& directory,
const FilePath& base_name,
int number,
const char* extension) {
- FilePath dir(directory.RemoveTrailingPathSeparator());
- if (number == 0) {
- return FilePath(String::Format("%s%c%s.%s", dir.c_str(), kPathSeparator,
- base_name.c_str(), extension));
- }
- return FilePath(String::Format("%s%c%s_%d.%s", dir.c_str(), kPathSeparator,
- base_name.c_str(), number, extension));
+ const FilePath file_name(
+ (number == 0) ?
+ String::Format("%s.%s", base_name.c_str(), extension) :
+ String::Format("%s_%d.%s", base_name.c_str(), number, extension));
+ return ConcatPaths(directory, file_name);
+}
+
+// Given directory = "dir", relative_path = "test.xml", returns "dir/test.xml".
+// On Windows, uses \ as the separator rather than /.
+FilePath FilePath::ConcatPaths(const FilePath& directory,
+ const FilePath& relative_path) {
+ if (directory.IsEmpty())
+ return relative_path;
+ const FilePath dir(directory.RemoveTrailingPathSeparator());
+ return FilePath(String::Format("%s%c%s", dir.c_str(), kPathSeparator,
+ relative_path.c_str()));
}
// Returns true if pathname describes something findable in the file-system,
// either a file, directory, or whatever.
bool FilePath::FileOrDirectoryExists() const {
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
#ifdef _WIN32_WCE
LPCWSTR unicode = String::AnsiToUtf16(pathname_.c_str());
const DWORD attributes = GetFileAttributes(unicode);
@@ -176,7 +186,7 @@ bool FilePath::FileOrDirectoryExists() const {
// that exists.
bool FilePath::DirectoryExists() const {
bool result = false;
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
// Don't strip off trailing separator if path is a root directory on
// Windows (like "C:\\").
const FilePath& path(IsRootDirectory() ? *this :
@@ -205,15 +215,27 @@ bool FilePath::DirectoryExists() const {
// Returns true if pathname describes a root directory. (Windows has one
// root directory per disk drive.)
bool FilePath::IsRootDirectory() const {
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
+ // TODO(wan@google.com): on Windows a network share like
+ // \\server\share can be a root directory, although it cannot be the
+ // current directory. Handle this properly.
+ return pathname_.GetLength() == 3 && IsAbsolutePath();
+#else
+ return pathname_ == kPathSeparatorString;
+#endif
+}
+
+// Returns true if pathname describes an absolute path.
+bool FilePath::IsAbsolutePath() const {
const char* const name = pathname_.c_str();
- return pathname_.GetLength() == 3 &&
+#if GTEST_OS_WINDOWS
+ return pathname_.GetLength() >= 3 &&
((name[0] >= 'a' && name[0] <= 'z') ||
(name[0] >= 'A' && name[0] <= 'Z')) &&
name[1] == ':' &&
name[2] == kPathSeparator;
#else
- return pathname_ == kPathSeparatorString;
+ return name[0] == kPathSeparator;
#endif
}
@@ -264,7 +286,7 @@ bool FilePath::CreateDirectoriesRecursively() const {
// directory for any reason, including if the parent directory does not
// exist. Not named "CreateDirectory" because that's a macro on Windows.
bool FilePath::CreateFolder() const {
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
#ifdef _WIN32_WCE
FilePath removed_sep(this->RemoveTrailingPathSeparator());
LPCWSTR unicode = String::AnsiToUtf16(removed_sep.c_str());
diff --git a/utils/unittest/googletest/gtest-port.cc b/utils/unittest/googletest/gtest-port.cc
index 9878cae..abc7149 100644
--- a/utils/unittest/googletest/gtest-port.cc
+++ b/utils/unittest/googletest/gtest-port.cc
@@ -35,9 +35,16 @@
#include <stdlib.h>
#include <stdio.h>
-#ifdef GTEST_HAS_DEATH_TEST
-#include <regex.h>
-#endif // GTEST_HAS_DEATH_TEST
+#if GTEST_OS_WINDOWS
+#include <io.h>
+#include <sys/stat.h>
+#else
+#include <unistd.h>
+#endif // GTEST_OS_WINDOWS
+
+#if GTEST_USES_SIMPLE_RE
+#include <string.h>
+#endif
#ifdef _WIN32_WCE
#include <windows.h> // For TerminateProcess()
@@ -47,11 +54,26 @@
#include <gtest/gtest-message.h>
#include <gtest/internal/gtest-string.h>
+// Indicates that this translation unit is part of Google Test's
+// implementation. It must come before gtest-internal-inl.h is
+// included, or there will be a compiler error. This trick is to
+// prevent a user from accidentally including gtest-internal-inl.h in
+// his code.
+#define GTEST_IMPLEMENTATION_ 1
+#include "gtest/internal/gtest-internal-inl.h"
+#undef GTEST_IMPLEMENTATION_
namespace testing {
namespace internal {
-#ifdef GTEST_HAS_DEATH_TEST
+#if GTEST_OS_WINDOWS
+// Microsoft does not provide a definition of STDERR_FILENO.
+const int kStdErrFileno = 2;
+#else
+const int kStdErrFileno = STDERR_FILENO;
+#endif // GTEST_OS_WINDOWS
+
+#if GTEST_USES_POSIX_RE
// Implements RE. Currently only needed for death tests.
@@ -93,7 +115,13 @@ void RE::Init(const char* regex) {
// previous expression returns false. Otherwise partial_regex_ may
// not be properly initialized can may cause trouble when it's
// freed.
- is_valid_ = (regcomp(&partial_regex_, regex, REG_EXTENDED) == 0) && is_valid_;
+ //
+ // Some implementation of POSIX regex (e.g. on at least some
+ // versions of Cygwin) doesn't accept the empty string as a valid
+ // regex. We change it to an equivalent form "()" to be safe.
+ const char* const partial_regex = (*regex == '\0') ? "()" : regex;
+ is_valid_ = (regcomp(&partial_regex_, partial_regex, REG_EXTENDED) == 0)
+ && is_valid_;
EXPECT_TRUE(is_valid_)
<< "Regular expression \"" << regex
<< "\" is not a valid POSIX Extended regular expression.";
@@ -101,7 +129,262 @@ void RE::Init(const char* regex) {
delete[] full_pattern;
}
-#endif // GTEST_HAS_DEATH_TEST
+#elif GTEST_USES_SIMPLE_RE
+
+// Returns true iff ch appears anywhere in str (excluding the
+// terminating '\0' character).
+bool IsInSet(char ch, const char* str) {
+ return ch != '\0' && strchr(str, ch) != NULL;
+}
+
+// Returns true iff ch belongs to the given classification. Unlike
+// similar functions in <ctype.h>, these aren't affected by the
+// current locale.
+bool IsDigit(char ch) { return '0' <= ch && ch <= '9'; }
+bool IsPunct(char ch) {
+ return IsInSet(ch, "^-!\"#$%&'()*+,./:;<=>?@[\\]_`{|}~");
+}
+bool IsRepeat(char ch) { return IsInSet(ch, "?*+"); }
+bool IsWhiteSpace(char ch) { return IsInSet(ch, " \f\n\r\t\v"); }
+bool IsWordChar(char ch) {
+ return ('a' <= ch && ch <= 'z') || ('A' <= ch && ch <= 'Z') ||
+ ('0' <= ch && ch <= '9') || ch == '_';
+}
+
+// Returns true iff "\\c" is a supported escape sequence.
+bool IsValidEscape(char c) {
+ return (IsPunct(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.
+bool AtomMatchesChar(bool escaped, char pattern_char, char ch) {
+ if (escaped) { // "\\p" where p is pattern_char.
+ switch (pattern_char) {
+ case 'd': return IsDigit(ch);
+ case 'D': return !IsDigit(ch);
+ case 'f': return ch == '\f';
+ case 'n': return ch == '\n';
+ case 'r': return ch == '\r';
+ case 's': return IsWhiteSpace(ch);
+ case 'S': return !IsWhiteSpace(ch);
+ case 't': return ch == '\t';
+ case 'v': return ch == '\v';
+ case 'w': return IsWordChar(ch);
+ case 'W': return !IsWordChar(ch);
+ }
+ return IsPunct(pattern_char) && pattern_char == ch;
+ }
+
+ return (pattern_char == '.' && ch != '\n') || pattern_char == ch;
+}
+
+// Helper function used by ValidateRegex() to format error messages.
+String FormatRegexSyntaxError(const char* regex, int index) {
+ return (Message() << "Syntax error at index " << index
+ << " in simple regular expression \"" << regex << "\": ").GetString();
+}
+
+// Generates non-fatal failures and returns false if regex is invalid;
+// otherwise returns true.
+bool ValidateRegex(const char* regex) {
+ if (regex == NULL) {
+ // TODO(wan@google.com): fix the source file location in the
+ // assertion failures to match where the regex is used in user
+ // code.
+ ADD_FAILURE() << "NULL is not a valid simple regular expression.";
+ return false;
+ }
+
+ bool is_valid = true;
+
+ // True iff ?, *, or + can follow the previous atom.
+ bool prev_repeatable = false;
+ for (int i = 0; regex[i]; i++) {
+ if (regex[i] == '\\') { // An escape sequence
+ i++;
+ if (regex[i] == '\0') {
+ ADD_FAILURE() << FormatRegexSyntaxError(regex, i - 1)
+ << "'\\' cannot appear at the end.";
+ return false;
+ }
+
+ if (!IsValidEscape(regex[i])) {
+ ADD_FAILURE() << FormatRegexSyntaxError(regex, i - 1)
+ << "invalid escape sequence \"\\" << regex[i] << "\".";
+ is_valid = false;
+ }
+ prev_repeatable = true;
+ } else { // Not an escape sequence.
+ const char ch = regex[i];
+
+ if (ch == '^' && i > 0) {
+ ADD_FAILURE() << FormatRegexSyntaxError(regex, i)
+ << "'^' can only appear at the beginning.";
+ is_valid = false;
+ } else if (ch == '$' && regex[i + 1] != '\0') {
+ ADD_FAILURE() << FormatRegexSyntaxError(regex, i)
+ << "'$' can only appear at the end.";
+ is_valid = false;
+ } else if (IsInSet(ch, "()[]{}|")) {
+ ADD_FAILURE() << FormatRegexSyntaxError(regex, i)
+ << "'" << ch << "' is unsupported.";
+ is_valid = false;
+ } else if (IsRepeat(ch) && !prev_repeatable) {
+ ADD_FAILURE() << FormatRegexSyntaxError(regex, i)
+ << "'" << ch << "' can only follow a repeatable token.";
+ is_valid = false;
+ }
+
+ prev_repeatable = !IsInSet(ch, "^$?*+");
+ }
+ }
+
+ return is_valid;
+}
+
+// Matches a repeated regex atom followed by a valid simple regular
+// expression. The regex atom is defined as c if escaped is false,
+// or \c otherwise. repeat is the repetition meta character (?, *,
+// or +). The behavior is undefined if str contains too many
+// characters to be indexable by size_t, in which case the test will
+// probably time out anyway. We are fine with this limitation as
+// std::string has it too.
+bool MatchRepetitionAndRegexAtHead(
+ bool escaped, char c, char repeat, const char* regex,
+ const char* str) {
+ const size_t min_count = (repeat == '+') ? 1 : 0;
+ const size_t max_count = (repeat == '?') ? 1 :
+ static_cast<size_t>(-1) - 1;
+ // We cannot call numeric_limits::max() as it conflicts with the
+ // max() macro on Windows.
+
+ for (size_t i = 0; i <= max_count; ++i) {
+ // We know that the atom matches each of the first i characters in str.
+ if (i >= min_count && MatchRegexAtHead(regex, str + i)) {
+ // We have enough matches at the head, and the tail matches too.
+ // Since we only care about *whether* the pattern matches str
+ // (as opposed to *how* it matches), there is no need to find a
+ // greedy match.
+ return true;
+ }
+ if (str[i] == '\0' || !AtomMatchesChar(escaped, c, str[i]))
+ return false;
+ }
+ 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
+// result is undefined.
+bool MatchRegexAtHead(const char* regex, const char* str) {
+ if (*regex == '\0') // An empty regex matches a prefix of anything.
+ return true;
+
+ // "$" only matches the end of a string. Note that regex being
+ // valid guarantees that there's nothing after "$" in it.
+ if (*regex == '$')
+ return *str == '\0';
+
+ // Is the first thing in regex an escape sequence?
+ const bool escaped = *regex == '\\';
+ if (escaped)
+ ++regex;
+ if (IsRepeat(regex[1])) {
+ // MatchRepetitionAndRegexAtHead() calls MatchRegexAtHead(), so
+ // here's an indirect recursion. It terminates as the regex gets
+ // shorter in each recursion.
+ return MatchRepetitionAndRegexAtHead(
+ escaped, regex[0], regex[1], regex + 2, str);
+ } else {
+ // regex isn't empty, isn't "$", and doesn't start with a
+ // repetition. We match the first atom of regex with the first
+ // character of str and recurse.
+ return (*str != '\0') && AtomMatchesChar(escaped, *regex, *str) &&
+ MatchRegexAtHead(regex + 1, str + 1);
+ }
+}
+
+// Returns true iff 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
+// stack space normally. In rare cases the time complexity can be
+// exponential with respect to the regex length + the string length,
+// but usually it's must faster (often close to linear).
+bool MatchRegexAnywhere(const char* regex, const char* str) {
+ if (regex == NULL || str == NULL)
+ return false;
+
+ if (*regex == '^')
+ return MatchRegexAtHead(regex + 1, str);
+
+ // A successful match can be anywhere in str.
+ do {
+ if (MatchRegexAtHead(regex, str))
+ return true;
+ } while (*str++ != '\0');
+ return false;
+}
+
+// Implements the RE class.
+
+RE::~RE() {
+ free(const_cast<char*>(pattern_));
+ free(const_cast<char*>(full_pattern_));
+}
+
+// Returns true iff 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).
+bool RE::PartialMatch(const char* str, const RE& re) {
+ return re.is_valid_ && MatchRegexAnywhere(re.pattern_, str);
+}
+
+// Initializes an RE from its string representation.
+void RE::Init(const char* regex) {
+ pattern_ = full_pattern_ = NULL;
+ if (regex != NULL) {
+#if GTEST_OS_WINDOWS
+ pattern_ = _strdup(regex);
+#else
+ pattern_ = strdup(regex);
+#endif
+ }
+
+ is_valid_ = ValidateRegex(regex);
+ if (!is_valid_) {
+ // No need to calculate the full pattern when the regex is invalid.
+ return;
+ }
+
+ const size_t len = strlen(regex);
+ // Reserves enough bytes to hold the regular expression used for a
+ // full match: we need space to prepend a '^', append a '$', and
+ // terminate the string with '\0'.
+ char* buffer = static_cast<char*>(malloc(len + 3));
+ full_pattern_ = buffer;
+
+ if (*regex != '^')
+ *buffer++ = '^'; // Makes sure full_pattern_ starts with '^'.
+
+ // We don't use snprintf or strncpy, as they trigger a warning when
+ // compiled with VC++ 8.0.
+ memcpy(buffer, regex, len);
+ buffer += len;
+
+ if (len == 0 || regex[len - 1] != '$')
+ *buffer++ = '$'; // Makes sure full_pattern_ ends with '$'.
+
+ *buffer = '\0';
+}
+
+#endif // GTEST_USES_POSIX_RE
// Logs a message at the given severity level.
void GTestLog(GTestLogSeverity severity, const char* file,
@@ -112,11 +395,19 @@ void GTestLog(GTestLogSeverity severity, const char* file,
severity == GTEST_ERROR ? "[ ERROR ]" : "[ FATAL ]";
fprintf(stderr, "\n%s %s:%d: %s\n", marker, file, line, msg);
if (severity == GTEST_FATAL) {
+ fflush(NULL); // abort() is not guaranteed to flush open file streams.
abort();
}
}
-#ifdef GTEST_HAS_DEATH_TEST
+#if GTEST_HAS_STD_STRING
+
+// Disable Microsoft deprecation warnings for POSIX functions called from
+// this class (creat, dup, dup2, and close)
+#ifdef _MSC_VER
+#pragma warning(push)
+#pragma warning(disable: 4996)
+#endif // _MSC_VER
// Defines the stderr capturer.
@@ -124,16 +415,26 @@ class CapturedStderr {
public:
// The ctor redirects stderr to a temporary file.
CapturedStderr() {
- uncaptured_fd_ = dup(STDERR_FILENO);
+ uncaptured_fd_ = dup(kStdErrFileno);
+#if GTEST_OS_WINDOWS
+ char temp_dir_path[MAX_PATH + 1] = { '\0' }; // NOLINT
+ char temp_file_path[MAX_PATH + 1] = { '\0' }; // NOLINT
+
+ ::GetTempPathA(sizeof(temp_dir_path), temp_dir_path);
+ ::GetTempFileNameA(temp_dir_path, "gtest_redir", 0, temp_file_path);
+ const int captured_fd = creat(temp_file_path, _S_IREAD | _S_IWRITE);
+ 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.
char name_template[] = "/tmp/captured_stderr.XXXXXX";
const int captured_fd = mkstemp(name_template);
filename_ = name_template;
+#endif // GTEST_OS_WINDOWS
fflush(NULL);
- dup2(captured_fd, STDERR_FILENO);
+ dup2(captured_fd, kStdErrFileno);
close(captured_fd);
}
@@ -145,7 +446,7 @@ class CapturedStderr {
void StopCapture() {
// Restores the original stream.
fflush(NULL);
- dup2(uncaptured_fd_, STDERR_FILENO);
+ dup2(uncaptured_fd_, kStdErrFileno);
close(uncaptured_fd_);
uncaptured_fd_ = -1;
}
@@ -160,6 +461,10 @@ class CapturedStderr {
::std::string filename_;
};
+#ifdef _MSC_VER
+#pragma warning(pop)
+#endif // _MSC_VER
+
static CapturedStderr* g_captured_stderr = NULL;
// Returns the size (in bytes) of a file.
@@ -169,8 +474,6 @@ static size_t GetFileSize(FILE * file) {
}
// Reads the entire content of a file as a string.
-// GTEST_HAS_DEATH_TEST implies that we have ::std::string, so we can
-// use it here.
static ::std::string ReadEntireFile(FILE * file) {
const size_t file_size = GetFileSize(file);
char* const buffer = new char[file_size];
@@ -206,9 +509,18 @@ void CaptureStderr() {
// use it here.
::std::string GetCapturedStderr() {
g_captured_stderr->StopCapture();
+
+// Disables Microsoft deprecation warning for fopen and fclose.
+#ifdef _MSC_VER
+#pragma warning(push)
+#pragma warning(disable: 4996)
+#endif // _MSC_VER
FILE* const file = fopen(g_captured_stderr->filename().c_str(), "r");
const ::std::string content = ReadEntireFile(file);
fclose(file);
+#ifdef _MSC_VER
+#pragma warning(pop)
+#endif // _MSC_VER
delete g_captured_stderr;
g_captured_stderr = NULL;
@@ -216,6 +528,10 @@ void CaptureStderr() {
return content;
}
+#endif // GTEST_HAS_STD_STRING
+
+#if GTEST_HAS_DEATH_TEST
+
// A copy of all command line arguments. Set by InitGoogleTest().
::std::vector<String> g_argvs;
@@ -235,7 +551,8 @@ void abort() {
// given flag. For example, FlagToEnvVar("foo") will return
// "GTEST_FOO" in the open-source version.
static String FlagToEnvVar(const char* flag) {
- const String full_flag = (Message() << GTEST_FLAG_PREFIX << flag).GetString();
+ const String full_flag =
+ (Message() << GTEST_FLAG_PREFIX_ << flag).GetString();
Message env_var;
for (int i = 0; i != full_flag.GetLength(); i++) {
@@ -245,17 +562,6 @@ static String FlagToEnvVar(const char* flag) {
return env_var.GetString();
}
-// 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".
-bool BoolFromGTestEnv(const char* flag, bool default_value) {
- const String env_var = FlagToEnvVar(flag);
- const char* const string_value = GetEnv(env_var.c_str());
- return string_value == NULL ?
- default_value : strcmp(string_value, "0") != 0;
-}
-
// 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.
@@ -297,6 +603,17 @@ bool ParseInt32(const Message& src_text, const char* str, Int32* value) {
return true;
}
+// 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".
+bool BoolFromGTestEnv(const char* flag, bool default_value) {
+ const String env_var = FlagToEnvVar(flag);
+ const char* const string_value = GetEnv(env_var.c_str());
+ return string_value == NULL ?
+ default_value : strcmp(string_value, "0") != 0;
+}
+
// 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.
diff --git a/utils/unittest/googletest/gtest-test-part.cc b/utils/unittest/googletest/gtest-test-part.cc
index 2e80f21..0f0116b 100644
--- a/utils/unittest/googletest/gtest-test-part.cc
+++ b/utils/unittest/googletest/gtest-test-part.cc
@@ -38,9 +38,9 @@
// included, or there will be a compiler error. This trick is to
// prevent a user from accidentally including gtest-internal-inl.h in
// his code.
-#define GTEST_IMPLEMENTATION
+#define GTEST_IMPLEMENTATION_ 1
#include "gtest/internal/gtest-internal-inl.h"
-#undef GTEST_IMPLEMENTATION
+#undef GTEST_IMPLEMENTATION_
namespace testing {
diff --git a/utils/unittest/googletest/gtest-typed-test.cc b/utils/unittest/googletest/gtest-typed-test.cc
index d42a159..e45e2ab 100644
--- a/utils/unittest/googletest/gtest-typed-test.cc
+++ b/utils/unittest/googletest/gtest-typed-test.cc
@@ -35,7 +35,7 @@
namespace testing {
namespace internal {
-#ifdef GTEST_HAS_TYPED_TEST_P
+#if GTEST_HAS_TYPED_TEST_P
// Verifies that registered_tests match the test names in
// defined_test_names_; returns registered_tests if successful, or
@@ -85,6 +85,7 @@ const char* TypedTestCasePState::VerifyRegisteredTestNames(
if (errors_str != "") {
fprintf(stderr, "%s %s", FormatFileLocation(file, line).c_str(),
errors_str.c_str());
+ fflush(stderr);
abort();
}
diff --git a/utils/unittest/googletest/gtest.cc b/utils/unittest/googletest/gtest.cc
index b5a654f..8f4252d 100644
--- a/utils/unittest/googletest/gtest.cc
+++ b/utils/unittest/googletest/gtest.cc
@@ -43,11 +43,11 @@
#include <wchar.h>
#include <wctype.h>
-#ifdef GTEST_OS_LINUX
+#if GTEST_OS_LINUX
// TODO(kenton@google.com): Use autoconf to detect availability of
// gettimeofday().
-#define GTEST_HAS_GETTIMEOFDAY
+#define GTEST_HAS_GETTIMEOFDAY_ 1
#include <fcntl.h>
#include <limits.h>
@@ -60,22 +60,22 @@
#include <string>
#include <vector>
-#elif defined(GTEST_OS_SYMBIAN)
-#define GTEST_HAS_GETTIMEOFDAY
+#elif GTEST_OS_SYMBIAN
+#define GTEST_HAS_GETTIMEOFDAY_ 1
#include <sys/time.h> // NOLINT
-#elif defined(GTEST_OS_ZOS)
-#define GTEST_HAS_GETTIMEOFDAY
+#elif GTEST_OS_ZOS
+#define GTEST_HAS_GETTIMEOFDAY_ 1
#include <sys/time.h> // NOLINT
// On z/OS we additionally need strings.h for strcasecmp.
-#include <strings.h>
+#include <strings.h> // NOLINT
#elif defined(_WIN32_WCE) // We are on Windows CE.
#include <windows.h> // NOLINT
-#elif defined(GTEST_OS_WINDOWS) // We are on Windows proper.
+#elif GTEST_OS_WINDOWS // We are on Windows proper.
#include <io.h> // NOLINT
#include <sys/timeb.h> // NOLINT
@@ -89,9 +89,9 @@
// TODO(kenton@google.com): There are other ways to get the time on
// Windows, like GetTickCount() or GetSystemTimeAsFileTime(). MinGW
// supports these. consider using them instead.
-#define GTEST_HAS_GETTIMEOFDAY
+#define GTEST_HAS_GETTIMEOFDAY_ 1
#include <sys/time.h> // NOLINT
-#endif
+#endif // defined(__MINGW__) || defined(__MINGW32__)
// cpplint thinks that the header is already included, so we want to
// silence it.
@@ -102,13 +102,17 @@
// Assume other platforms have gettimeofday().
// TODO(kenton@google.com): Use autoconf to detect availability of
// gettimeofday().
-#define GTEST_HAS_GETTIMEOFDAY
+#define GTEST_HAS_GETTIMEOFDAY_ 1
// cpplint thinks that the header is already included, so we want to
// silence it.
#include <sys/time.h> // NOLINT
#include <unistd.h> // NOLINT
+#endif // GTEST_OS_LINUX
+
+#if GTEST_HAS_EXCEPTIONS
+#include <stdexcept>
#endif
// Indicates that this translation unit is part of Google Test's
@@ -116,11 +120,11 @@
// included, or there will be a compiler error. This trick is to
// prevent a user from accidentally including gtest-internal-inl.h in
// his code.
-#define GTEST_IMPLEMENTATION
+#define GTEST_IMPLEMENTATION_ 1
#include "gtest/internal/gtest-internal-inl.h"
-#undef GTEST_IMPLEMENTATION
+#undef GTEST_IMPLEMENTATION_
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
#define fileno _fileno
#define isatty _isatty
#define vsnprintf _vsnprintf
@@ -145,6 +149,13 @@ static const char kUniversalFilter[] = "*";
// The default output file for XML output.
static const char kDefaultOutputFile[] = "test_detail.xml";
+// The environment variable name for the test shard index.
+static const char kTestShardIndex[] = "GTEST_SHARD_INDEX";
+// The environment variable name for the total number of test shards.
+static const char kTestTotalShards[] = "GTEST_TOTAL_SHARDS";
+// The environment variable name for the test shard status file.
+static const char kTestShardStatusFile[] = "GTEST_SHARD_STATUS_FILE";
+
namespace internal {
// The text used in failure messages to indicate the start of the
@@ -154,6 +165,11 @@ const char kStackTraceMarker[] = "\nStack trace:\n";
} // namespace internal
GTEST_DEFINE_bool_(
+ also_run_disabled_tests,
+ internal::BoolFromGTestEnv("also_run_disabled_tests", false),
+ "Run disabled tests too, in addition to the tests normally being run.");
+
+GTEST_DEFINE_bool_(
break_on_failure,
internal::BoolFromGTestEnv("break_on_failure", false),
"True iff a failed assertion should be a debugger break-point.");
@@ -161,7 +177,7 @@ GTEST_DEFINE_bool_(
GTEST_DEFINE_bool_(
catch_exceptions,
internal::BoolFromGTestEnv("catch_exceptions", false),
- "True iff " GTEST_NAME
+ "True iff " GTEST_NAME_
" should catch exceptions and treat them as test failures.");
GTEST_DEFINE_string_(
@@ -199,7 +215,7 @@ GTEST_DEFINE_string_(
GTEST_DEFINE_bool_(
print_time,
internal::BoolFromGTestEnv("print_time", false),
- "True iff " GTEST_NAME
+ "True iff " GTEST_NAME_
" should display elapsed time in text output.");
GTEST_DEFINE_int32_(
@@ -216,11 +232,22 @@ GTEST_DEFINE_int32_(
GTEST_DEFINE_bool_(
show_internal_stack_frames, false,
- "True iff " GTEST_NAME " should include internal stack frames when "
+ "True iff " GTEST_NAME_ " should include internal stack frames when "
"printing test failure stack traces.");
+GTEST_DEFINE_bool_(
+ throw_on_failure,
+ internal::BoolFromGTestEnv("throw_on_failure", false),
+ "When this flag is specified, a failed assertion will throw an exception "
+ "if exceptions are enabled or exit the program with a non-zero code "
+ "otherwise.");
+
namespace internal {
+// g_help_flag is true iff the --help flag or an equivalent form is
+// specified on the command line.
+static bool g_help_flag = false;
+
// GTestIsInitialized() returns true iff the user has initialized
// Google Test. Useful for catching the user mistake of not initializing
// Google Test before calling RUN_ALL_TESTS().
@@ -290,7 +317,7 @@ String g_executable_path;
FilePath GetCurrentExecutableName() {
FilePath result;
-#if defined(_WIN32_WCE) || defined(GTEST_OS_WINDOWS)
+#if defined(_WIN32_WCE) || GTEST_OS_WINDOWS
result.Set(FilePath(g_executable_path).RemoveExtension("exe"));
#else
result.Set(FilePath(g_executable_path));
@@ -314,16 +341,28 @@ String UnitTestOptions::GetOutputFormat() {
// Returns the name of the requested output file, or the default if none
// was explicitly specified.
-String UnitTestOptions::GetOutputFile() {
+String UnitTestOptions::GetAbsolutePathToOutputFile() {
const char* const gtest_output_flag = GTEST_FLAG(output).c_str();
if (gtest_output_flag == NULL)
return String("");
const char* const colon = strchr(gtest_output_flag, ':');
if (colon == NULL)
- return String(kDefaultOutputFile);
+ return String(internal::FilePath::ConcatPaths(
+ internal::FilePath(
+ UnitTest::GetInstance()->original_working_dir()),
+ internal::FilePath(kDefaultOutputFile)).ToString() );
internal::FilePath output_name(colon + 1);
+ if (!output_name.IsAbsolutePath())
+ // TODO(wan@google.com): on Windows \some\path is not an absolute
+ // path (as its meaning depends on the current drive), yet the
+ // following logic for turning it into an absolute path is wrong.
+ // Fix it.
+ output_name = internal::FilePath::ConcatPaths(
+ internal::FilePath(UnitTest::GetInstance()->original_working_dir()),
+ internal::FilePath(colon + 1));
+
if (!output_name.IsDirectory())
return output_name.ToString();
@@ -357,7 +396,7 @@ bool UnitTestOptions::PatternMatchesString(const char *pattern,
bool UnitTestOptions::MatchesFilter(const String& name, const char* filter) {
const char *cur_pattern = filter;
- while (true) {
+ for (;;) {
if (PatternMatchesString(cur_pattern, name.c_str())) {
return true;
}
@@ -409,7 +448,7 @@ bool UnitTestOptions::FilterMatchesTest(const String &test_case_name,
!MatchesFilter(full_name, negative.c_str()));
}
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
// Returns EXCEPTION_EXECUTE_HANDLER if Google Test should handle the
// given SEH exception, or EXCEPTION_CONTINUE_SEARCH otherwise.
// This function is useful as an __except condition.
@@ -719,7 +758,7 @@ static TimeInMillis GetTimeInMillis() {
return now_int64.QuadPart;
}
return 0;
-#elif defined(GTEST_OS_WINDOWS) && !defined(GTEST_HAS_GETTIMEOFDAY)
+#elif GTEST_OS_WINDOWS && !GTEST_HAS_GETTIMEOFDAY_
__timeb64 now;
#ifdef _MSC_VER
// MSVC 8 deprecates _ftime64(), so we want to suppress warning 4996
@@ -734,7 +773,7 @@ static TimeInMillis GetTimeInMillis() {
_ftime64(&now);
#endif // _MSC_VER
return static_cast<TimeInMillis>(now.time) * 1000 + now.millitm;
-#elif defined(GTEST_HAS_GETTIMEOFDAY)
+#elif GTEST_HAS_GETTIMEOFDAY_
struct timeval now;
gettimeofday(&now, NULL);
return static_cast<TimeInMillis>(now.tv_sec) * 1000 + now.tv_usec / 1000;
@@ -769,7 +808,7 @@ static char* CloneString(const char* str, size_t length) {
char* const clone = new char[length + 1];
// MSVC 8 deprecates strncpy(), so we want to suppress warning
// 4996 (deprecated function) there.
-#ifdef GTEST_OS_WINDOWS // We are on Windows.
+#if GTEST_OS_WINDOWS // We are on Windows.
#pragma warning(push) // Saves the current warning state.
#pragma warning(disable:4996) // Temporarily disables warning 4996.
strncpy(clone, str, length);
@@ -1290,7 +1329,7 @@ AssertionResult IsNotSubstring(
namespace internal {
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
namespace {
@@ -1418,14 +1457,14 @@ char* CodePointToUtf8(UInt32 code_point, char* str) {
// null-terminate the destination string.
// MSVC 8 deprecates strncpy(), so we want to suppress warning
// 4996 (deprecated function) there.
-#ifdef GTEST_OS_WINDOWS // We are on Windows.
+#if GTEST_OS_WINDOWS // We are on Windows.
#pragma warning(push) // Saves the current warning state.
#pragma warning(disable:4996) // Temporarily disables warning 4996.
#endif
strncpy(str, String::Format("(Invalid Unicode 0x%X)", code_point).c_str(),
32);
-#ifdef GTEST_OS_WINDOWS // We are on Windows.
-#pragma warning(pop) // Restores the warning state.
+#if GTEST_OS_WINDOWS // We are on Windows.
+#pragma warning(pop) // Restores the warning state.
#endif
str[31] = '\0'; // Makes sure no change in the format to strncpy leaves
// the result unterminated.
@@ -1441,23 +1480,19 @@ char* CodePointToUtf8(UInt32 code_point, char* str) {
// and thus should be combined into a single Unicode code point
// using CreateCodePointFromUtf16SurrogatePair.
inline bool IsUtf16SurrogatePair(wchar_t first, wchar_t second) {
- if (sizeof(wchar_t) == 2)
- return (first & 0xFC00) == 0xD800 && (second & 0xFC00) == 0xDC00;
- else
- return false;
+ return sizeof(wchar_t) == 2 &&
+ (first & 0xFC00) == 0xD800 && (second & 0xFC00) == 0xDC00;
}
// Creates a Unicode code point from UTF16 surrogate pair.
inline UInt32 CreateCodePointFromUtf16SurrogatePair(wchar_t first,
wchar_t second) {
- if (sizeof(wchar_t) == 2) {
- const UInt32 mask = (1 << 10) - 1;
- return (((first & mask) << 10) | (second & mask)) + 0x10000;
- } else {
- // This should not be called, but we provide a sensible default
- // in case it is.
- return static_cast<UInt32>(first);
- }
+ const UInt32 mask = (1 << 10) - 1;
+ return (sizeof(wchar_t) == 2) ?
+ (((first & mask) << 10) | (second & mask)) + 0x10000 :
+ // This function should not be called when the condition is
+ // false, but we provide a sensible default in case it is.
+ static_cast<UInt32>(first);
}
// Converts a wide string to a narrow string in UTF-8 encoding.
@@ -1572,7 +1607,7 @@ bool String::CaseInsensitiveCStringEquals(const char * lhs, const char * rhs) {
if ( rhs == NULL ) return false;
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
return _stricmp(lhs, rhs) == 0;
#else // GTEST_OS_WINDOWS
return strcasecmp(lhs, rhs) == 0;
@@ -1597,9 +1632,9 @@ bool String::CaseInsensitiveWideCStringEquals(const wchar_t* lhs,
if ( rhs == NULL ) return false;
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
return _wcsicmp(lhs, rhs) == 0;
-#elif defined(GTEST_OS_LINUX)
+#elif GTEST_OS_LINUX
return wcscasecmp(lhs, rhs) == 0;
#else
// Mac OS X and Cygwin don't define wcscasecmp. Other unknown OSes
@@ -1610,7 +1645,7 @@ bool String::CaseInsensitiveWideCStringEquals(const wchar_t* lhs,
right = towlower(*rhs++);
} while (left && left == right);
return left == right;
-#endif // OS selector
+#endif // OS selector
}
// Constructs a String by copying a given number of chars from a
@@ -1700,7 +1735,7 @@ String String::Format(const char * format, ...) {
char buffer[4096];
// MSVC 8 deprecates vsnprintf(), so we want to suppress warning
// 4996 (deprecated function) there.
-#ifdef GTEST_OS_WINDOWS // We are on Windows.
+#if GTEST_OS_WINDOWS // We are on Windows.
#pragma warning(push) // Saves the current warning state.
#pragma warning(disable:4996) // Temporarily disables warning 4996.
const int size =
@@ -1807,7 +1842,7 @@ bool TestResult::ValidateTestProperty(const TestProperty& test_property) {
<< "Reserved key used in RecordProperty(): "
<< key
<< " ('name', 'status', 'time', and 'classname' are reserved by "
- << GTEST_NAME << ")";
+ << GTEST_NAME_ << ")";
return false;
}
return true;
@@ -1897,7 +1932,7 @@ void Test::RecordProperty(const char* key, int value) {
RecordProperty(key, value_message.GetString().c_str());
}
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
// We are on Windows.
// Adds an "exception thrown" fatal failure to the current test.
@@ -1993,7 +2028,7 @@ void Test::Run() {
if (!HasSameFixtureClass()) return;
internal::UnitTestImpl* const impl = internal::GetUnitTestImpl();
-#if defined(GTEST_OS_WINDOWS) && !defined(__MINGW32__)
+#if GTEST_OS_WINDOWS && !defined(__MINGW32__)
// We are on Windows.
impl->os_stack_trace_getter()->UponLeavingGTest();
__try {
@@ -2102,7 +2137,7 @@ TestInfo* MakeAndRegisterTestInfo(
return test_info;
}
-#ifdef GTEST_HAS_PARAM_TEST
+#if GTEST_HAS_PARAM_TEST
void ReportInvalidTestCaseType(const char* test_case_name,
const char* file, int line) {
Message errors;
@@ -2201,7 +2236,7 @@ namespace internal {
// and INSTANTIATE_TEST_CASE_P into regular tests and registers those.
// This will be done just once during the program runtime.
void UnitTestImpl::RegisterParameterizedTests() {
-#ifdef GTEST_HAS_PARAM_TEST
+#if GTEST_HAS_PARAM_TEST
if (!parameterized_tests_registered_) {
parameterized_test_registry_.RegisterTests();
parameterized_tests_registered_ = true;
@@ -2227,7 +2262,7 @@ void TestInfoImpl::Run() {
const TimeInMillis start = GetTimeInMillis();
impl->os_stack_trace_getter()->UponLeavingGTest();
-#if defined(GTEST_OS_WINDOWS) && !defined(__MINGW32__)
+#if GTEST_OS_WINDOWS && !defined(__MINGW32__)
// We are on Windows.
Test* test = NULL;
@@ -2418,14 +2453,20 @@ static const char * TestPartResultTypeToString(TestPartResultType type) {
return "Unknown result type";
}
+// Prints a TestPartResult to a String.
+static internal::String PrintTestPartResultToString(
+ const TestPartResult& test_part_result) {
+ return (Message()
+ << internal::FormatFileLocation(test_part_result.file_name(),
+ test_part_result.line_number())
+ << " " << TestPartResultTypeToString(test_part_result.type())
+ << test_part_result.message()).GetString();
+}
+
// Prints a TestPartResult.
static void PrintTestPartResult(
- const TestPartResult & test_part_result) {
- printf("%s %s%s\n",
- internal::FormatFileLocation(test_part_result.file_name(),
- test_part_result.line_number()).c_str(),
- TestPartResultTypeToString(test_part_result.type()),
- test_part_result.message());
+ const TestPartResult& test_part_result) {
+ printf("%s\n", PrintTestPartResultToString(test_part_result).c_str());
fflush(stdout);
}
@@ -2434,12 +2475,13 @@ static void PrintTestPartResult(
namespace internal {
enum GTestColor {
+ COLOR_DEFAULT,
COLOR_RED,
COLOR_GREEN,
COLOR_YELLOW
};
-#if defined(GTEST_OS_WINDOWS) && !defined(_WIN32_WCE)
+#if GTEST_OS_WINDOWS && !defined(_WIN32_WCE)
// Returns the character attribute for the given color.
WORD GetColorAttribute(GTestColor color) {
@@ -2447,20 +2489,21 @@ WORD GetColorAttribute(GTestColor color) {
case COLOR_RED: return FOREGROUND_RED;
case COLOR_GREEN: return FOREGROUND_GREEN;
case COLOR_YELLOW: return FOREGROUND_RED | FOREGROUND_GREEN;
+ default: return 0;
}
- return 0;
}
#else
-// Returns the ANSI color code for the given color.
+// Returns the ANSI color code for the given color. COLOR_DEFAULT is
+// an invalid input.
const char* GetAnsiColorCode(GTestColor color) {
switch (color) {
case COLOR_RED: return "1";
case COLOR_GREEN: return "2";
case COLOR_YELLOW: return "3";
+ default: return NULL;
};
- return NULL;
}
#endif // GTEST_OS_WINDOWS && !_WIN32_WCE
@@ -2470,7 +2513,7 @@ bool ShouldUseColor(bool stdout_is_tty) {
const char* const gtest_color = GTEST_FLAG(color).c_str();
if (String::CaseInsensitiveCStringEquals(gtest_color, "auto")) {
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
// On Windows the TERM variable is usually not set, but the
// console there does support colors.
return stdout_is_tty;
@@ -2502,11 +2545,13 @@ void ColoredPrintf(GTestColor color, const char* fmt, ...) {
va_list args;
va_start(args, fmt);
-#if defined(_WIN32_WCE) || defined(GTEST_OS_SYMBIAN) || defined(GTEST_OS_ZOS)
- static const bool use_color = false;
+#if defined(_WIN32_WCE) || GTEST_OS_SYMBIAN || GTEST_OS_ZOS
+ const bool use_color = false;
#else
- static const bool use_color = ShouldUseColor(isatty(fileno(stdout)) != 0);
-#endif // !_WIN32_WCE
+ static const bool in_color_mode =
+ ShouldUseColor(isatty(fileno(stdout)) != 0);
+ const bool use_color = in_color_mode && (color != COLOR_DEFAULT);
+#endif // defined(_WIN32_WCE) || GTEST_OS_SYMBIAN || GTEST_OS_ZOS
// The '!= 0' comparison is necessary to satisfy MSVC 7.1.
if (!use_color) {
@@ -2515,7 +2560,7 @@ void ColoredPrintf(GTestColor color, const char* fmt, ...) {
return;
}
-#if defined(GTEST_OS_WINDOWS) && !defined(_WIN32_WCE)
+#if GTEST_OS_WINDOWS && !defined(_WIN32_WCE)
const HANDLE stdout_handle = GetStdHandle(STD_OUTPUT_HANDLE);
// Gets the current text color.
@@ -2533,13 +2578,14 @@ void ColoredPrintf(GTestColor color, const char* fmt, ...) {
printf("\033[0;3%sm", GetAnsiColorCode(color));
vprintf(fmt, args);
printf("\033[m"); // Resets the terminal to default.
-#endif // GTEST_OS_WINDOWS && !_WIN32_WCE
+#endif // GTEST_OS_WINDOWS && !defined(_WIN32_WCE)
va_end(args);
}
} // namespace internal
using internal::ColoredPrintf;
+using internal::COLOR_DEFAULT;
using internal::COLOR_RED;
using internal::COLOR_GREEN;
using internal::COLOR_YELLOW;
@@ -2579,7 +2625,14 @@ void PrettyUnitTestResultPrinter::OnUnitTestStart(
// tests may be skipped.
if (!internal::String::CStringEquals(filter, kUniversalFilter)) {
ColoredPrintf(COLOR_YELLOW,
- "Note: %s filter = %s\n", GTEST_NAME, filter);
+ "Note: %s filter = %s\n", GTEST_NAME_, filter);
+ }
+
+ if (internal::ShouldShard(kTestTotalShards, kTestShardIndex, false)) {
+ ColoredPrintf(COLOR_YELLOW,
+ "Note: This is test shard %s of %s.\n",
+ internal::GetEnv(kTestShardIndex),
+ internal::GetEnv(kTestTotalShards));
}
const internal::UnitTestImpl* const impl = unit_test->impl();
@@ -2736,7 +2789,7 @@ void PrettyUnitTestResultPrinter::OnUnitTestEnd(
}
int num_disabled = impl->disabled_test_count();
- if (num_disabled) {
+ if (num_disabled && !GTEST_FLAG(also_run_disabled_tests)) {
if (!num_failures) {
printf("\n"); // Add a spacer if no FAILURE banner is displayed.
}
@@ -2899,7 +2952,7 @@ void XmlUnitTestResultPrinter::OnUnitTestEnd(const UnitTest* unit_test) {
if (output_dir.CreateDirectoriesRecursively()) {
// MSVC 8 deprecates fopen(), so we want to suppress warning 4996
// (deprecated function) there.
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
// We are on Windows.
#pragma warning(push) // Saves the current warning state.
#pragma warning(disable:4996) // Temporarily disables warning 4996.
@@ -3164,7 +3217,7 @@ void OsStackTraceGetter::UponLeavingGTest() {
const char* const
OsStackTraceGetter::kElidedFramesMarker =
- "... " GTEST_NAME " internal frames ...";
+ "... " GTEST_NAME_ " internal frames ...";
} // namespace internal
@@ -3213,6 +3266,19 @@ Environment* UnitTest::AddEnvironment(Environment* env) {
return env;
}
+#if GTEST_HAS_EXCEPTIONS
+// A failed Google Test assertion will throw an exception of this type
+// when exceptions are enabled. We derive it from std::runtime_error,
+// which is for errors presumably detectable only at run time. Since
+// std::runtime_error inherits from std::exception, many testing
+// frameworks know how to extract and print the message inside it.
+class GoogleTestFailureException : public ::std::runtime_error {
+ public:
+ explicit GoogleTestFailureException(const TestPartResult& failure)
+ : runtime_error(PrintTestPartResultToString(failure).c_str()) {}
+};
+#endif
+
// Adds a TestPartResult to the current TestResult object. All Google Test
// assertion macros (e.g. ASSERT_TRUE, EXPECT_EQ, etc) eventually call
// this to report their results. The user code should use the
@@ -3228,7 +3294,7 @@ void UnitTest::AddTestPartResult(TestPartResultType result_type,
internal::MutexLock lock(&mutex_);
if (impl_->gtest_trace_stack()->size() > 0) {
- msg << "\n" << GTEST_NAME << " trace:";
+ msg << "\n" << GTEST_NAME_ << " trace:";
for (internal::ListNode<internal::TraceInfo>* node =
impl_->gtest_trace_stack()->Head();
@@ -3249,11 +3315,23 @@ void UnitTest::AddTestPartResult(TestPartResultType result_type,
impl_->GetTestPartResultReporterForCurrentThread()->
ReportTestPartResult(result);
- // If this is a failure and the user wants the debugger to break on
- // failures ...
- if (result_type != TPRT_SUCCESS && GTEST_FLAG(break_on_failure)) {
- // ... then we generate a seg fault.
- *static_cast<int*>(NULL) = 1;
+ if (result_type != TPRT_SUCCESS) {
+ // gunit_break_on_failure takes precedence over
+ // gunit_throw_on_failure. This allows a user to set the latter
+ // in the code (perhaps in order to use Google Test assertions
+ // with another testing framework) and specify the former on the
+ // command line for debugging.
+ if (GTEST_FLAG(break_on_failure)) {
+ *static_cast<int*>(NULL) = 1;
+ } else if (GTEST_FLAG(throw_on_failure)) {
+#if GTEST_HAS_EXCEPTIONS
+ throw GoogleTestFailureException(result);
+#else
+ // We cannot call abort() as it generates a pop-up in debug mode
+ // that cannot be suppressed in VC 7.1 or below.
+ exit(1);
+#endif
+ }
}
}
@@ -3271,19 +3349,48 @@ void UnitTest::RecordPropertyForCurrentTest(const char* key,
// We don't protect this under mutex_, as we only support calling it
// from the main thread.
int UnitTest::Run() {
-#if defined(GTEST_OS_WINDOWS) && !defined(__MINGW32__)
-
+#if GTEST_OS_WINDOWS && !defined(__MINGW32__)
+
+ const bool in_death_test_child_process =
+ internal::GTEST_FLAG(internal_run_death_test).GetLength() > 0;
+
+ // Either the user wants Google Test to catch exceptions thrown by the
+ // tests or this is executing in the context of death test child
+ // process. In either case the user does not want to see pop-up dialogs
+ // about crashes - they are expected..
+ if (GTEST_FLAG(catch_exceptions) || in_death_test_child_process) {
+ // process. In either case the user does not want to see pop-up dialogs
+ // about crashes - they are expected..
+ if (GTEST_FLAG(catch_exceptions) || in_death_test_child_process) {
#if !defined(_WIN32_WCE)
- // SetErrorMode doesn't exist on CE.
- if (GTEST_FLAG(catch_exceptions)) {
- // The user wants Google Test to catch exceptions thrown by the tests.
-
- // This lets fatal errors be handled by us, instead of causing pop-ups.
+ // SetErrorMode doesn't exist on CE.
SetErrorMode(SEM_FAILCRITICALERRORS | SEM_NOALIGNMENTFAULTEXCEPT |
SEM_NOGPFAULTERRORBOX | SEM_NOOPENFILEERRORBOX);
- }
#endif // _WIN32_WCE
+ // Death test children can be terminated with _abort(). On Windows,
+ // _abort() can show a dialog with a warning message. This forces the
+ // abort message to go to stderr instead.
+ _set_error_mode(_OUT_TO_STDERR);
+
+ // In the debug version, Visual Studio pops up a separate dialog
+ // offering a choice to debug the aborted program. We need to suppress
+ // this dialog or it will pop up for every EXPECT/ASSERT_DEATH statement
+ // executed. Google Test will notify the user of any unexpected
+ // failure via stderr.
+#if _MSC_VER >= 1400
+ // VC++ doesn't define _set_abort_behavior() prior to the version 8.0.
+ // Users of prior VC versions shall suffer the agony and pain of
+ // clicking through the countless debug dialogs.
+ // TODO(vladl@google.com): find a way to suppress the abort dialog() in the
+ // debug mode when compiled with VC 7.1 or lower.
+ if (!GTEST_FLAG(break_on_failure))
+ _set_abort_behavior(
+ 0x0, // Clear the following flags:
+ _WRITE_ABORT_MSG | _CALL_REPORTFAULT); // pop-up window, core dump.
+#endif // _MSC_VER >= 1400
+ }
+
__try {
return impl_->RunAllTests();
} __except(internal::UnitTestOptions::GTestShouldProcessSEH(
@@ -3322,7 +3429,7 @@ const TestInfo* UnitTest::current_test_info() const {
return impl_->current_test_info();
}
-#ifdef GTEST_HAS_PARAM_TEST
+#if GTEST_HAS_PARAM_TEST
// Returns ParameterizedTestCaseRegistry object used to keep track of
// value-parameterized tests and instantiate and register them.
// L < mutex_
@@ -3377,7 +3484,7 @@ UnitTestImpl::UnitTestImpl(UnitTest* parent)
per_thread_test_part_result_reporter_(
&default_per_thread_test_part_result_reporter_),
test_cases_(),
-#ifdef GTEST_HAS_PARAM_TEST
+#if GTEST_HAS_PARAM_TEST
parameterized_test_registry_(),
parameterized_tests_registered_(false),
#endif // GTEST_HAS_PARAM_TEST
@@ -3387,7 +3494,7 @@ UnitTestImpl::UnitTestImpl(UnitTest* parent)
ad_hoc_test_result_(),
result_printer_(NULL),
os_stack_trace_getter_(NULL),
-#ifdef GTEST_HAS_DEATH_TEST
+#if GTEST_HAS_DEATH_TEST
elapsed_time_(0),
internal_run_death_test_flag_(NULL),
death_test_factory_(new DefaultDeathTestFactory) {
@@ -3495,8 +3602,17 @@ int UnitTestImpl::RunAllTests() {
return 1;
}
+ // Do not run any test if the --help flag was specified.
+ if (g_help_flag)
+ return 0;
+
RegisterParameterizedTests();
+ // Even if sharding is not on, test runners may want to use the
+ // GTEST_SHARD_STATUS_FILE to query whether the test supports the sharding
+ // protocol.
+ internal::WriteToShardStatusFileIfNeeded();
+
// Lists all the tests and exits if the --gtest_list_tests
// flag was specified.
if (GTEST_FLAG(list_tests)) {
@@ -3508,16 +3624,22 @@ int UnitTestImpl::RunAllTests() {
// death test.
bool in_subprocess_for_death_test = false;
-#ifdef GTEST_HAS_DEATH_TEST
+#if GTEST_HAS_DEATH_TEST
internal_run_death_test_flag_.reset(ParseInternalRunDeathTestFlag());
in_subprocess_for_death_test = (internal_run_death_test_flag_.get() != NULL);
#endif // GTEST_HAS_DEATH_TEST
UnitTestEventListenerInterface * const printer = result_printer();
+ const bool should_shard = ShouldShard(kTestTotalShards, kTestShardIndex,
+ in_subprocess_for_death_test);
+
// Compares the full test names with the filter to decide which
// tests to run.
- const bool has_tests_to_run = FilterTests() > 0;
+ const bool has_tests_to_run = FilterTests(should_shard
+ ? HONOR_SHARDING_PROTOCOL
+ : IGNORE_SHARDING_PROTOCOL) > 0;
+
// True iff at least one test has failed.
bool failed = false;
@@ -3573,14 +3695,128 @@ int UnitTestImpl::RunAllTests() {
return failed ? 1 : 0;
}
+// Reads the GTEST_SHARD_STATUS_FILE environment variable, and creates the file
+// if the variable is present. If a file already exists at this location, this
+// function will write over it. If the variable is present, but the file cannot
+// be created, prints an error and exits.
+void WriteToShardStatusFileIfNeeded() {
+ const char* const test_shard_file = GetEnv(kTestShardStatusFile);
+ if (test_shard_file != NULL) {
+#ifdef _MSC_VER // MSVC 8 deprecates fopen().
+#pragma warning(push) // Saves the current warning state.
+#pragma warning(disable:4996) // Temporarily disables warning on
+ // deprecated functions.
+#endif
+ FILE* const file = fopen(test_shard_file, "w");
+#ifdef _MSC_VER
+#pragma warning(pop) // Restores the warning state.
+#endif
+ if (file == NULL) {
+ ColoredPrintf(COLOR_RED,
+ "Could not write to the test shard status file \"%s\" "
+ "specified by the %s environment variable.\n",
+ test_shard_file, kTestShardStatusFile);
+ fflush(stdout);
+ exit(EXIT_FAILURE);
+ }
+ fclose(file);
+ }
+}
+
+// Checks whether sharding is enabled by examining the relevant
+// environment variable values. If the variables are present,
+// but inconsistent (i.e., shard_index >= total_shards), prints
+// an error and exits. If in_subprocess_for_death_test, sharding is
+// disabled because it must only be applied to the original test
+// process. Otherwise, we could filter out death tests we intended to execute.
+bool ShouldShard(const char* total_shards_env,
+ const char* shard_index_env,
+ bool in_subprocess_for_death_test) {
+ if (in_subprocess_for_death_test) {
+ return false;
+ }
+
+ const Int32 total_shards = Int32FromEnvOrDie(total_shards_env, -1);
+ const Int32 shard_index = Int32FromEnvOrDie(shard_index_env, -1);
+
+ if (total_shards == -1 && shard_index == -1) {
+ return false;
+ } else if (total_shards == -1 && shard_index != -1) {
+ const Message msg = Message()
+ << "Invalid environment variables: you have "
+ << kTestShardIndex << " = " << shard_index
+ << ", but have left " << kTestTotalShards << " unset.\n";
+ ColoredPrintf(COLOR_RED, msg.GetString().c_str());
+ fflush(stdout);
+ exit(EXIT_FAILURE);
+ } else if (total_shards != -1 && shard_index == -1) {
+ const Message msg = Message()
+ << "Invalid environment variables: you have "
+ << kTestTotalShards << " = " << total_shards
+ << ", but have left " << kTestShardIndex << " unset.\n";
+ ColoredPrintf(COLOR_RED, msg.GetString().c_str());
+ fflush(stdout);
+ exit(EXIT_FAILURE);
+ } else if (shard_index < 0 || shard_index >= total_shards) {
+ const Message msg = Message()
+ << "Invalid environment variables: we require 0 <= "
+ << kTestShardIndex << " < " << kTestTotalShards
+ << ", but you have " << kTestShardIndex << "=" << shard_index
+ << ", " << kTestTotalShards << "=" << total_shards << ".\n";
+ ColoredPrintf(COLOR_RED, msg.GetString().c_str());
+ fflush(stdout);
+ exit(EXIT_FAILURE);
+ }
+
+ return total_shards > 1;
+}
+
+// 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 aborts.
+Int32 Int32FromEnvOrDie(const char* const var, Int32 default_val) {
+ const char* str_val = GetEnv(var);
+ if (str_val == NULL) {
+ return default_val;
+ }
+
+ Int32 result;
+ if (!ParseInt32(Message() << "The value of environment variable " << var,
+ str_val, &result)) {
+ exit(EXIT_FAILURE);
+ }
+ return result;
+}
+
+// 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
+// method. Assumes that 0 <= shard_index < total_shards.
+bool ShouldRunTestOnShard(int total_shards, int shard_index, int test_id) {
+ return (test_id % total_shards) == shard_index;
+}
+
// Compares the name of each test with the user-specified filter to
// decide whether the test should be run, then records the result in
// each TestCase and TestInfo object.
+// If shard_tests == true, further filters tests based on sharding
+// variables in the environment - see
+// http://code.google.com/p/googletest/wiki/GoogleTestAdvancedGuide.
// Returns the number of tests that should run.
-int UnitTestImpl::FilterTests() {
+int UnitTestImpl::FilterTests(ReactionToSharding shard_tests) {
+ const Int32 total_shards = shard_tests == HONOR_SHARDING_PROTOCOL ?
+ Int32FromEnvOrDie(kTestTotalShards, -1) : -1;
+ const Int32 shard_index = shard_tests == HONOR_SHARDING_PROTOCOL ?
+ Int32FromEnvOrDie(kTestShardIndex, -1) : -1;
+
+ // num_runnable_tests are the number of tests that will
+ // run across all shards (i.e., match filter and are not disabled).
+ // num_selected_tests are the number of tests to be run on
+ // this shard.
int num_runnable_tests = 0;
+ int num_selected_tests = 0;
for (const internal::ListNode<TestCase *> *test_case_node =
- test_cases_.Head();
+ test_cases_.Head();
test_case_node != NULL;
test_case_node = test_case_node->next()) {
TestCase * const test_case = test_case_node->element();
@@ -3588,7 +3824,7 @@ int UnitTestImpl::FilterTests() {
test_case->set_should_run(false);
for (const internal::ListNode<TestInfo *> *test_info_node =
- test_case->test_info_list().Head();
+ test_case->test_info_list().Head();
test_info_node != NULL;
test_info_node = test_info_node->next()) {
TestInfo * const test_info = test_info_node->element();
@@ -3596,23 +3832,30 @@ int UnitTestImpl::FilterTests() {
// A test is disabled if test case name or test name matches
// kDisableTestFilter.
const bool is_disabled =
- internal::UnitTestOptions::MatchesFilter(test_case_name,
- kDisableTestFilter) ||
- internal::UnitTestOptions::MatchesFilter(test_name,
- kDisableTestFilter);
+ internal::UnitTestOptions::MatchesFilter(test_case_name,
+ kDisableTestFilter) ||
+ internal::UnitTestOptions::MatchesFilter(test_name,
+ kDisableTestFilter);
test_info->impl()->set_is_disabled(is_disabled);
- const bool should_run = !is_disabled &&
+ const bool is_runnable =
+ (GTEST_FLAG(also_run_disabled_tests) || !is_disabled) &&
internal::UnitTestOptions::FilterMatchesTest(test_case_name,
test_name);
- test_info->impl()->set_should_run(should_run);
- test_case->set_should_run(test_case->should_run() || should_run);
- if (should_run) {
- num_runnable_tests++;
- }
+
+ const bool is_selected = is_runnable &&
+ (shard_tests == IGNORE_SHARDING_PROTOCOL ||
+ ShouldRunTestOnShard(total_shards, shard_index,
+ num_runnable_tests));
+
+ num_runnable_tests += is_runnable;
+ num_selected_tests += is_selected;
+
+ test_info->impl()->set_should_run(is_selected);
+ test_case->set_should_run(test_case->should_run() || is_selected);
}
}
- return num_runnable_tests;
+ return num_selected_tests;
}
// Lists all tests by name.
@@ -3658,7 +3901,7 @@ UnitTestEventListenerInterface* UnitTestImpl::result_printer() {
return result_printer_;
}
-#ifdef GTEST_HAS_DEATH_TEST
+#if GTEST_HAS_DEATH_TEST
if (internal_run_death_test_flag_.get() != NULL) {
result_printer_ = new NullUnitTestResultPrinter;
return result_printer_;
@@ -3669,7 +3912,7 @@ UnitTestEventListenerInterface* UnitTestImpl::result_printer() {
const String& output_format = internal::UnitTestOptions::GetOutputFormat();
if (output_format == "xml") {
repeater->AddListener(new XmlUnitTestResultPrinter(
- internal::UnitTestOptions::GetOutputFile().c_str()));
+ internal::UnitTestOptions::GetAbsolutePathToOutputFile().c_str()));
} else if (output_format != "") {
printf("WARNING: unrecognized output format \"%s\" ignored.\n",
output_format.c_str());
@@ -3757,6 +4000,22 @@ int GetFailedPartCount(const TestResult* result) {
return result->failed_part_count();
}
+// Used by the GTEST_HIDE_UNREACHABLE_CODE_ macro to suppress unreachable
+// code warnings.
+namespace {
+class ClassUniqueToAlwaysTrue {};
+}
+
+bool AlwaysTrue() {
+#if GTEST_HAS_EXCEPTIONS
+ // This condition is always false so AlwaysTrue() never actually throws,
+ // but it makes the compiler think that it may throw.
+ if (atoi("42") == 36) // NOLINT
+ throw ClassUniqueToAlwaysTrue();
+#endif // GTEST_HAS_EXCEPTIONS
+ return true;
+}
+
// Parses a string as a command line flag. The string should have
// the format "--flag=value". When def_optional is true, the "=value"
// part can be omitted.
@@ -3768,8 +4027,8 @@ const char* ParseFlagValue(const char* str,
// str and flag must not be NULL.
if (str == NULL || flag == NULL) return NULL;
- // The flag must start with "--" followed by GTEST_FLAG_PREFIX.
- const String flag_str = String::Format("--%s%s", GTEST_FLAG_PREFIX, flag);
+ // The flag must start with "--" followed by GTEST_FLAG_PREFIX_.
+ const String flag_str = String::Format("--%s%s", GTEST_FLAG_PREFIX_, flag);
const size_t flag_len = flag_str.GetLength();
if (strncmp(str, flag_str.c_str(), flag_len) != 0) return NULL;
@@ -3846,6 +4105,102 @@ bool ParseStringFlag(const char* str, const char* flag, String* value) {
return true;
}
+// Prints a string containing code-encoded text. The following escape
+// sequences can be used in the string to control the text color:
+//
+// @@ prints a single '@' character.
+// @R changes the color to red.
+// @G changes the color to green.
+// @Y changes the color to yellow.
+// @D changes to the default terminal text color.
+//
+// TODO(wan@google.com): Write tests for this once we add stdout
+// capturing to Google Test.
+static void PrintColorEncoded(const char* str) {
+ GTestColor color = COLOR_DEFAULT; // The current color.
+
+ // Conceptually, we split the string into segments divided by escape
+ // sequences. Then we print one segment at a time. At the end of
+ // each iteration, the str pointer advances to the beginning of the
+ // next segment.
+ for (;;) {
+ const char* p = strchr(str, '@');
+ if (p == NULL) {
+ ColoredPrintf(color, "%s", str);
+ return;
+ }
+
+ ColoredPrintf(color, "%s", String(str, p - str).c_str());
+
+ const char ch = p[1];
+ str = p + 2;
+ if (ch == '@') {
+ ColoredPrintf(color, "@");
+ } else if (ch == 'D') {
+ color = COLOR_DEFAULT;
+ } else if (ch == 'R') {
+ color = COLOR_RED;
+ } else if (ch == 'G') {
+ color = COLOR_GREEN;
+ } else if (ch == 'Y') {
+ color = COLOR_YELLOW;
+ } else {
+ --str;
+ }
+ }
+}
+
+static const char kColorEncodedHelpMessage[] =
+"This program contains tests written using " GTEST_NAME_ ". You can use the\n"
+"following command line flags to control its behavior:\n"
+"\n"
+"Test Selection:\n"
+" @G--" GTEST_FLAG_PREFIX_ "list_tests@D\n"
+" List the names of all tests instead of running them. The name of\n"
+" TEST(Foo, Bar) is \"Foo.Bar\".\n"
+" @G--" GTEST_FLAG_PREFIX_ "filter=@YPOSTIVE_PATTERNS"
+ "[@G-@YNEGATIVE_PATTERNS]@D\n"
+" Run only the tests whose name matches one of the positive patterns but\n"
+" none of the negative patterns. '?' matches any single character; '*'\n"
+" matches any substring; ':' separates two patterns.\n"
+" @G--" GTEST_FLAG_PREFIX_ "also_run_disabled_tests@D\n"
+" Run all disabled tests too.\n"
+" @G--" GTEST_FLAG_PREFIX_ "repeat=@Y[COUNT]@D\n"
+" Run the tests repeatedly; use a negative count to repeat forever.\n"
+"\n"
+"Test Output:\n"
+" @G--" GTEST_FLAG_PREFIX_ "color=@Y(@Gyes@Y|@Gno@Y|@Gauto@Y)@D\n"
+" Enable/disable colored output. The default is @Gauto@D.\n"
+" -@G-" GTEST_FLAG_PREFIX_ "print_time@D\n"
+" Print the elapsed time of each test.\n"
+" @G--" GTEST_FLAG_PREFIX_ "output=xml@Y[@G:@YDIRECTORY_PATH@G"
+ GTEST_PATH_SEP_ "@Y|@G:@YFILE_PATH]@D\n"
+" Generate an XML report in the given directory or with the given file\n"
+" name. @YFILE_PATH@D defaults to @Gtest_details.xml@D.\n"
+"\n"
+"Failure Behavior:\n"
+" @G--" GTEST_FLAG_PREFIX_ "break_on_failure@D\n"
+" Turn assertion failures into debugger break-points.\n"
+" @G--" GTEST_FLAG_PREFIX_ "throw_on_failure@D\n"
+" Turn assertion failures into C++ exceptions.\n"
+#if GTEST_OS_WINDOWS
+" @G--" GTEST_FLAG_PREFIX_ "catch_exceptions@D\n"
+" Suppress pop-ups caused by exceptions.\n"
+#endif // GTEST_OS_WINDOWS
+"\n"
+"Except for @G--" GTEST_FLAG_PREFIX_ "list_tests@D, you can alternatively set "
+ "the corresponding\n"
+"environment variable of a flag (all letters in upper-case). For example, to\n"
+"print the elapsed time, you can either specify @G--" GTEST_FLAG_PREFIX_
+ "print_time@D or set the\n"
+"@G" GTEST_FLAG_PREFIX_UPPER_ "PRINT_TIME@D environment variable to a "
+ "non-zero value.\n"
+"\n"
+"For more information, please read the " GTEST_NAME_ " documentation at\n"
+"@G" GTEST_PROJECT_URL_ "@D. If you find a bug in " GTEST_NAME_ "\n"
+"(not one in your own code or tests), please report it to\n"
+"@G<" GTEST_DEV_EMAIL_ ">@D.\n";
+
// Parses the command line for Google Test flags, without initializing
// other parts of Google Test. The type parameter CharType can be
// instantiated to either char or wchar_t.
@@ -3860,20 +4215,25 @@ void ParseGoogleTestFlagsOnlyImpl(int* argc, CharType** argv) {
using internal::ParseStringFlag;
// Do we see a Google Test flag?
- if (ParseBoolFlag(arg, kBreakOnFailureFlag,
+ if (ParseBoolFlag(arg, kAlsoRunDisabledTestsFlag,
+ &GTEST_FLAG(also_run_disabled_tests)) ||
+ ParseBoolFlag(arg, kBreakOnFailureFlag,
&GTEST_FLAG(break_on_failure)) ||
ParseBoolFlag(arg, kCatchExceptionsFlag,
&GTEST_FLAG(catch_exceptions)) ||
ParseStringFlag(arg, kColorFlag, &GTEST_FLAG(color)) ||
ParseStringFlag(arg, kDeathTestStyleFlag,
&GTEST_FLAG(death_test_style)) ||
+ ParseBoolFlag(arg, kDeathTestUseFork,
+ &GTEST_FLAG(death_test_use_fork)) ||
ParseStringFlag(arg, kFilterFlag, &GTEST_FLAG(filter)) ||
ParseStringFlag(arg, kInternalRunDeathTestFlag,
&GTEST_FLAG(internal_run_death_test)) ||
ParseBoolFlag(arg, kListTestsFlag, &GTEST_FLAG(list_tests)) ||
ParseStringFlag(arg, kOutputFlag, &GTEST_FLAG(output)) ||
ParseBoolFlag(arg, kPrintTimeFlag, &GTEST_FLAG(print_time)) ||
- ParseInt32Flag(arg, kRepeatFlag, &GTEST_FLAG(repeat))
+ ParseInt32Flag(arg, kRepeatFlag, &GTEST_FLAG(repeat)) ||
+ ParseBoolFlag(arg, kThrowOnFailureFlag, &GTEST_FLAG(throw_on_failure))
) {
// Yes. Shift the remainder of the argv list left by one. Note
// that argv has (*argc + 1) elements, the last one always being
@@ -3889,8 +4249,18 @@ void ParseGoogleTestFlagsOnlyImpl(int* argc, CharType** argv) {
// We also need to decrement the iterator as we just removed
// an element.
i--;
+ } else if (arg_string == "--help" || arg_string == "-h" ||
+ arg_string == "-?" || arg_string == "/?") {
+ g_help_flag = true;
}
}
+
+ if (g_help_flag) {
+ // We print the help here instead of in RUN_ALL_TESTS(), as the
+ // latter may not be called at all if the user is using Google
+ // Test with another testing framework.
+ PrintColorEncoded(kColorEncodedHelpMessage);
+ }
}
// Parses the command line for Google Test flags, without initializing
@@ -3917,7 +4287,7 @@ void InitGoogleTestImpl(int* argc, CharType** argv) {
internal::g_executable_path = internal::StreamableToString(argv[0]);
-#ifdef GTEST_HAS_DEATH_TEST
+#if GTEST_HAS_DEATH_TEST
g_argvs.clear();
for (int i = 0; i != *argc; i++) {
g_argvs.push_back(StreamableToString(argv[i]));
diff --git a/utils/unittest/googletest/include/gtest/gtest-death-test.h b/utils/unittest/googletest/include/gtest/gtest-death-test.h
index f0e109a..dcb2b66 100644
--- a/utils/unittest/googletest/include/gtest/gtest-death-test.h
+++ b/utils/unittest/googletest/include/gtest/gtest-death-test.h
@@ -49,7 +49,7 @@ namespace testing {
// after forking.
GTEST_DECLARE_string_(death_test_style);
-#ifdef GTEST_HAS_DEATH_TEST
+#if GTEST_HAS_DEATH_TEST
// The following macros are useful for writing death tests.
@@ -86,6 +86,57 @@ GTEST_DECLARE_string_(death_test_style);
//
// ASSERT_EXIT(client.HangUpServer(), KilledBySIGHUP, "Hanging up!");
//
+// On the regular expressions used in death tests:
+//
+// On POSIX-compliant systems (*nix), we use the <regex.h> library,
+// which uses the POSIX extended regex syntax.
+//
+// On other platforms (e.g. Windows), we only support a simple regex
+// syntax implemented as part of Google Test. This limited
+// implementation should be enough most of the time when writing
+// death tests; though it lacks many features you can find in PCRE
+// or POSIX extended regex syntax. For example, we don't support
+// union ("x|y"), grouping ("(xy)"), brackets ("[xy]"), and
+// repetition count ("x{5,7}"), among others.
+//
+// Below is the syntax that we do support. We chose it to be a
+// subset of both PCRE and POSIX extended regex, so it's easy to
+// learn wherever you come from. In the following: 'A' denotes a
+// literal character, period (.), or a single \\ escape sequence;
+// 'x' and 'y' denote regular expressions; 'm' and 'n' are for
+// natural numbers.
+//
+// c matches any literal character c
+// \\d matches any decimal digit
+// \\D matches any character that's not a decimal digit
+// \\f matches \f
+// \\n matches \n
+// \\r matches \r
+// \\s matches any ASCII whitespace, including \n
+// \\S matches any character that's not a whitespace
+// \\t matches \t
+// \\v matches \v
+// \\w matches any letter, _, or decimal digit
+// \\W matches any character that \\w doesn't match
+// \\c matches any literal character c, which must be a punctuation
+// . matches any single character except \n
+// A? matches 0 or 1 occurrences of A
+// A* matches 0 or many occurrences of A
+// A+ matches 1 or many occurrences of A
+// ^ matches the beginning of a string (not that of each line)
+// $ matches the end of a string (not that of each line)
+// xy matches x followed by y
+//
+// If you accidentally use PCRE or POSIX extended regex features
+// not implemented by us, you will get a run-time failure. In that
+// case, please try to rewrite your regular expression within the
+// above syntax.
+//
+// This implementation is *not* meant to be as highly tuned or robust
+// as a compiled regex library, but should perform well enough for a
+// death test, which already incurs significant overhead by launching
+// a child process.
+//
// Known caveats:
//
// A "threadsafe" style death test obtains the path to the test
@@ -133,6 +184,7 @@ class ExitedWithCode {
const int exit_code_;
};
+#if !GTEST_OS_WINDOWS
// Tests that an exit code describes an exit due to termination by a
// given signal.
class KilledBySignal {
@@ -142,6 +194,7 @@ class KilledBySignal {
private:
const int signum_;
};
+#endif // !GTEST_OS_WINDOWS
// EXPECT_DEBUG_DEATH asserts that the given statements die in debug mode.
// The death testing framework causes this to have interesting semantics,
diff --git a/utils/unittest/googletest/include/gtest/gtest-message.h b/utils/unittest/googletest/include/gtest/gtest-message.h
index 7effd08..99ae454 100644
--- a/utils/unittest/googletest/include/gtest/gtest-message.h
+++ b/utils/unittest/googletest/include/gtest/gtest-message.h
@@ -102,7 +102,7 @@ class Message {
}
~Message() { delete ss_; }
-#ifdef GTEST_OS_SYMBIAN
+#if GTEST_OS_SYMBIAN
// Streams a value (either a pointer or not) to this object.
template <typename T>
inline Message& operator <<(const T& value) {
@@ -187,7 +187,7 @@ class Message {
}
private:
-#ifdef GTEST_OS_SYMBIAN
+#if GTEST_OS_SYMBIAN
// These are needed as the Nokia Symbian Compiler cannot decide between
// const T& and const T* in a function template. The Nokia compiler _can_
// decide between class template specializations for T and T*, so a
diff --git a/utils/unittest/googletest/include/gtest/gtest-param-test.h b/utils/unittest/googletest/include/gtest/gtest-param-test.h
index 0cf05dc..c9d4f24 100644
--- a/utils/unittest/googletest/include/gtest/gtest-param-test.h
+++ b/utils/unittest/googletest/include/gtest/gtest-param-test.h
@@ -151,7 +151,7 @@ INSTANTIATE_TEST_CASE_P(AnotherInstantiationName, FooTest, ValuesIn(pets));
#include <gtest/internal/gtest-port.h>
-#ifdef GTEST_HAS_PARAM_TEST
+#if GTEST_HAS_PARAM_TEST
#include <gtest/internal/gtest-internal.h>
#include <gtest/internal/gtest-param-util.h>
@@ -1190,7 +1190,7 @@ inline internal::ParamGenerator<bool> Bool() {
return Values(false, true);
}
-#ifdef GTEST_HAS_COMBINE
+#if GTEST_HAS_COMBINE
// Combine() allows the user to combine two or more sequences to produce
// values of a Cartesian product of those sequences' elements.
//
diff --git a/utils/unittest/googletest/include/gtest/gtest-typed-test.h b/utils/unittest/googletest/include/gtest/gtest-typed-test.h
index dec42cf..519edfe 100644
--- a/utils/unittest/googletest/include/gtest/gtest-typed-test.h
+++ b/utils/unittest/googletest/include/gtest/gtest-typed-test.h
@@ -151,7 +151,7 @@ INSTANTIATE_TYPED_TEST_CASE_P(My, FooTest, MyTypes);
// Implements typed tests.
-#ifdef GTEST_HAS_TYPED_TEST
+#if GTEST_HAS_TYPED_TEST
// INTERNAL IMPLEMENTATION - DO NOT USE IN USER CODE.
//
@@ -186,7 +186,7 @@ INSTANTIATE_TYPED_TEST_CASE_P(My, FooTest, MyTypes);
// Implements type-parameterized tests.
-#ifdef GTEST_HAS_TYPED_TEST_P
+#if GTEST_HAS_TYPED_TEST_P
// INTERNAL IMPLEMENTATION - DO NOT USE IN USER CODE.
//
diff --git a/utils/unittest/googletest/include/gtest/gtest.h b/utils/unittest/googletest/include/gtest/gtest.h
index ebd3123..9b72b63 100644
--- a/utils/unittest/googletest/include/gtest/gtest.h
+++ b/utils/unittest/googletest/include/gtest/gtest.h
@@ -93,17 +93,59 @@
namespace testing {
-// The upper limit for valid stack trace depths.
-const int kMaxStackTraceDepth = 100;
+// Declares the flags.
-// This flag specifies the maximum number of stack frames to be
-// printed in a failure message.
-GTEST_DECLARE_int32_(stack_trace_depth);
+// This flag temporary enables the disabled tests.
+GTEST_DECLARE_bool_(also_run_disabled_tests);
+
+// This flag brings the debugger on an assertion failure.
+GTEST_DECLARE_bool_(break_on_failure);
+
+// This flag controls whether Google Test catches all test-thrown exceptions
+// and logs them as failures.
+GTEST_DECLARE_bool_(catch_exceptions);
+
+// This flag enables using colors in terminal output. Available values are
+// "yes" to enable colors, "no" (disable colors), or "auto" (the default)
+// to let Google Test decide.
+GTEST_DECLARE_string_(color);
+
+// This flag sets up the filter to select by name using a glob pattern
+// the tests to run. If the filter is not given all tests are executed.
+GTEST_DECLARE_string_(filter);
+
+// This flag causes the Google Test to list tests. None of the tests listed
+// are actually run if the flag is provided.
+GTEST_DECLARE_bool_(list_tests);
+
+// This flag controls whether Google Test emits a detailed XML report to a file
+// in addition to its normal textual output.
+GTEST_DECLARE_string_(output);
+
+// This flags control whether Google Test prints the elapsed time for each
+// test.
+GTEST_DECLARE_bool_(print_time);
+
+// This flag sets how many times the tests are repeated. The default value
+// is 1. If the value is -1 the tests are repeating forever.
+GTEST_DECLARE_int32_(repeat);
// This flag controls whether Google Test includes Google Test internal
// stack frames in failure stack traces.
GTEST_DECLARE_bool_(show_internal_stack_frames);
+// This flag specifies the maximum number of stack frames to be
+// printed in a failure message.
+GTEST_DECLARE_int32_(stack_trace_depth);
+
+// When this flag is specified, a failed assertion will throw an
+// exception if exceptions are enabled, or exit the program with a
+// non-zero code otherwise.
+GTEST_DECLARE_bool_(throw_on_failure);
+
+// The upper limit for valid stack trace depths.
+const int kMaxStackTraceDepth = 100;
+
namespace internal {
class GTestFlagSaver;
@@ -353,7 +395,7 @@ class TestInfo {
// Returns the result of the test.
const internal::TestResult* result() const;
private:
-#ifdef GTEST_HAS_DEATH_TEST
+#if GTEST_HAS_DEATH_TEST
friend class internal::DefaultDeathTestFactory;
#endif // GTEST_HAS_DEATH_TEST
friend class internal::TestInfoImpl;
@@ -484,7 +526,7 @@ class UnitTest {
// or NULL if no test is running.
const TestInfo* current_test_info() const;
-#ifdef GTEST_HAS_PARAM_TEST
+#if GTEST_HAS_PARAM_TEST
// Returns the ParameterizedTestCaseRegistry object used to keep track of
// value-parameterized tests and instantiate and register them.
internal::ParameterizedTestCaseRegistry& parameterized_test_registry();
@@ -614,10 +656,20 @@ AssertionResult CmpHelperEQ(const char* expected_expression,
const char* actual_expression,
const T1& expected,
const T2& actual) {
+#ifdef _MSC_VER
+#pragma warning(push) // Saves the current warning state.
+#pragma warning(disable:4389) // Temporarily disables warning on
+ // signed/unsigned mismatch.
+#endif
+
if (expected == actual) {
return AssertionSuccess();
}
+#ifdef _MSC_VER
+#pragma warning(pop) // Restores the warning state.
+#endif
+
return EqFailure(expected_expression,
actual_expression,
FormatForComparisonFailureMessage(expected, actual),
@@ -688,7 +740,7 @@ class EqHelper<true> {
template <typename T1, typename T2>
static AssertionResult Compare(const char* expected_expression,
const char* actual_expression,
- const T1& expected,
+ const T1& /* expected */,
T2* actual) {
// We already know that 'expected' is a null pointer.
return CmpHelperEQ(expected_expression, actual_expression,
@@ -893,7 +945,7 @@ class AssertHelper {
} // namespace internal
-#ifdef GTEST_HAS_PARAM_TEST
+#if GTEST_HAS_PARAM_TEST
// The abstract base class that all value-parameterized tests inherit from.
//
// This class adds support for accessing the test parameter value via
@@ -1187,7 +1239,7 @@ AssertionResult DoubleLE(const char* expr1, const char* expr2,
double val1, double val2);
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
// Macros that test for HRESULT failure and success, these are only useful
// on Windows, and rely on Windows SDK macros and APIs to compile.
@@ -1242,6 +1294,52 @@ AssertionResult DoubleLE(const char* expr1, const char* expr2,
::testing::internal::ScopedTrace GTEST_CONCAT_TOKEN_(gtest_trace_, __LINE__)(\
__FILE__, __LINE__, ::testing::Message() << (message))
+namespace internal {
+
+// This template is declared, but intentionally undefined.
+template <typename T1, typename T2>
+struct StaticAssertTypeEqHelper;
+
+template <typename T>
+struct StaticAssertTypeEqHelper<T, T> {};
+
+} // namespace internal
+
+// Compile-time assertion for type equality.
+// StaticAssertTypeEq<type1, type2>() compiles iff type1 and type2 are
+// the same type. The value it returns is not interesting.
+//
+// Instead of making StaticAssertTypeEq a class template, we make it a
+// function template that invokes a helper class template. This
+// prevents a user from misusing StaticAssertTypeEq<T1, T2> by
+// defining objects of that type.
+//
+// CAVEAT:
+//
+// When used inside a method of a class template,
+// StaticAssertTypeEq<T1, T2>() is effective ONLY IF the method is
+// instantiated. For example, given:
+//
+// template <typename T> class Foo {
+// public:
+// void Bar() { testing::StaticAssertTypeEq<int, T>(); }
+// };
+//
+// the code:
+//
+// void Test1() { Foo<bool> foo; }
+//
+// will NOT generate a compiler error, as Foo<bool>::Bar() is never
+// actually instantiated. Instead, you need:
+//
+// void Test2() { Foo<bool> foo; foo.Bar(); }
+//
+// to cause a compiler error.
+template <typename T1, typename T2>
+bool StaticAssertTypeEq() {
+ internal::StaticAssertTypeEqHelper<T1, T2>();
+ return true;
+}
// Defines a test.
//
@@ -1269,7 +1367,7 @@ AssertionResult DoubleLE(const char* expr1, const char* expr2,
// value, as it always calls GetTypeId<>() from the Google Test
// framework.
#define TEST(test_case_name, test_name)\
- GTEST_TEST_(test_case_name, test_name,\
+ GTEST_TEST_(test_case_name, test_name, \
::testing::Test, ::testing::internal::GetTestTypeId())
@@ -1300,7 +1398,7 @@ AssertionResult DoubleLE(const char* expr1, const char* expr2,
// }
#define TEST_F(test_fixture, test_name)\
- GTEST_TEST_(test_fixture, test_name, test_fixture,\
+ GTEST_TEST_(test_fixture, test_name, test_fixture, \
::testing::internal::GetTypeId<test_fixture>())
// Use this macro in main() to run all tests. It returns 0 if all
diff --git a/utils/unittest/googletest/include/gtest/internal/gtest-death-test-internal.h b/utils/unittest/googletest/include/gtest/internal/gtest-death-test-internal.h
index 0769fca..ff2e490 100644
--- a/utils/unittest/googletest/include/gtest/internal/gtest-death-test-internal.h
+++ b/utils/unittest/googletest/include/gtest/internal/gtest-death-test-internal.h
@@ -39,6 +39,10 @@
#include <gtest/internal/gtest-internal.h>
+#if GTEST_HAS_DEATH_TEST && GTEST_OS_WINDOWS
+#include <io.h>
+#endif // GTEST_HAS_DEATH_TEST && GTEST_OS_WINDOWS
+
namespace testing {
namespace internal {
@@ -46,9 +50,10 @@ GTEST_DECLARE_string_(internal_run_death_test);
// Names of the flags (needed for parsing Google Test flags).
const char kDeathTestStyleFlag[] = "death_test_style";
+const char kDeathTestUseFork[] = "death_test_use_fork";
const char kInternalRunDeathTestFlag[] = "internal_run_death_test";
-#ifdef GTEST_HAS_DEATH_TEST
+#if GTEST_HAS_DEATH_TEST
// DeathTest is a class that hides much of the complexity of the
// GTEST_DEATH_TEST_ macro. It is abstract; its static Create method
@@ -120,7 +125,12 @@ class DeathTest {
// the last death test.
static const char* LastMessage();
+ static void set_last_death_test_message(const String& message);
+
private:
+ // A string containing a description of the outcome of the last death test.
+ static String last_death_test_message_;
+
GTEST_DISALLOW_COPY_AND_ASSIGN_(DeathTest);
};
@@ -166,7 +176,7 @@ bool ExitedUnsuccessfully(int exit_status);
case ::testing::internal::DeathTest::EXECUTE_TEST: { \
::testing::internal::DeathTest::ReturnSentinel \
gtest_sentinel(gtest_dt); \
- { statement; } \
+ GTEST_HIDE_UNREACHABLE_CODE_(statement); \
gtest_dt->Abort(::testing::internal::DeathTest::TEST_DID_NOT_DIE); \
break; \
} \
@@ -178,14 +188,42 @@ bool ExitedUnsuccessfully(int exit_status);
// The symbol "fail" here expands to something into which a message
// can be streamed.
-// A struct representing the parsed contents of the
+// A class representing the parsed contents of the
// --gtest_internal_run_death_test flag, as it existed when
// RUN_ALL_TESTS was called.
-struct InternalRunDeathTestFlag {
- String file;
- int line;
- int index;
- int status_fd;
+class InternalRunDeathTestFlag {
+ public:
+ InternalRunDeathTestFlag(const String& file,
+ int line,
+ int index,
+ int status_fd)
+ : file_(file), line_(line), index_(index), status_fd_(status_fd) {}
+
+ ~InternalRunDeathTestFlag() {
+ if (status_fd_ >= 0)
+// Suppress MSVC complaints about POSIX functions.
+#ifdef _MSC_VER
+#pragma warning(push)
+#pragma warning(disable: 4996)
+#endif // _MSC_VER
+ close(status_fd_);
+#ifdef _MSC_VER
+#pragma warning(pop)
+#endif // _MSC_VER
+ }
+
+ String file() const { return file_; }
+ int line() const { return line_; }
+ int index() const { return index_; }
+ int status_fd() const { return status_fd_; }
+
+ private:
+ String file_;
+ int line_;
+ int index_;
+ int status_fd_;
+
+ GTEST_DISALLOW_COPY_AND_ASSIGN_(InternalRunDeathTestFlag);
};
// Returns a newly created InternalRunDeathTestFlag object with fields
diff --git a/utils/unittest/googletest/include/gtest/internal/gtest-filepath.h b/utils/unittest/googletest/include/gtest/internal/gtest-filepath.h
index 9a0682a..1b2f586 100644
--- a/utils/unittest/googletest/include/gtest/internal/gtest-filepath.h
+++ b/utils/unittest/googletest/include/gtest/internal/gtest-filepath.h
@@ -34,7 +34,7 @@
// This header file declares classes and functions used internally by
// Google Test. They are subject to change without notice.
//
-// This file is #included in testing/base/internal/gtest-internal.h
+// This file is #included in <gtest/internal/gtest-internal.h>.
// Do not include this header file separately!
#ifndef GTEST_INCLUDE_GTEST_INTERNAL_GTEST_FILEPATH_H_
@@ -93,6 +93,12 @@ class FilePath {
int number,
const char* extension);
+ // Given directory = "dir", relative_path = "test.xml",
+ // returns "dir/test.xml".
+ // On Windows, uses \ as the separator rather than /.
+ static FilePath ConcatPaths(const FilePath& directory,
+ const FilePath& relative_path);
+
// Returns a pathname for a file that does not currently exist. The pathname
// will be directory/base_name.extension or
// directory/base_name_<number>.extension if directory/base_name.extension
@@ -164,6 +170,9 @@ class FilePath {
// root directory per disk drive.)
bool IsRootDirectory() const;
+ // Returns true if pathname describes an absolute path.
+ bool IsAbsolutePath() const;
+
private:
// Replaces multiple consecutive separators with a single separator.
// For example, "bar///foo" becomes "bar/foo". Does not eliminate other
diff --git a/utils/unittest/googletest/include/gtest/internal/gtest-internal-inl.h b/utils/unittest/googletest/include/gtest/internal/gtest-internal-inl.h
index b8f67c1..d079a3e 100644
--- a/utils/unittest/googletest/include/gtest/internal/gtest-internal-inl.h
+++ b/utils/unittest/googletest/include/gtest/internal/gtest-internal-inl.h
@@ -37,20 +37,24 @@
#ifndef GTEST_SRC_GTEST_INTERNAL_INL_H_
#define GTEST_SRC_GTEST_INTERNAL_INL_H_
-// GTEST_IMPLEMENTATION is defined iff the current translation unit is
-// part of Google Test's implementation.
-#ifndef GTEST_IMPLEMENTATION
+// GTEST_IMPLEMENTATION_ is defined to 1 iff the current translation unit is
+// part of Google Test's implementation; otherwise it's undefined.
+#if !GTEST_IMPLEMENTATION_
// A user is trying to include this from his code - just say no.
#error "gtest-internal-inl.h is part of Google Test's internal implementation."
#error "It must not be included except by Google Test itself."
-#endif // GTEST_IMPLEMENTATION
+#endif // GTEST_IMPLEMENTATION_
+#include <errno.h>
#include <stddef.h>
+#include <stdlib.h> // For strtoll/_strtoul64.
+
+#include <string>
#include <gtest/internal/gtest-port.h>
-#ifdef GTEST_OS_WINDOWS
-#include <windows.h> // NOLINT
+#if GTEST_OS_WINDOWS
+#include <windows.h> // For DWORD.
#endif // GTEST_OS_WINDOWS
#include <gtest/gtest.h>
@@ -60,19 +64,10 @@ namespace testing {
// Declares the flags.
//
-// We don't want the users to modify these flags in the code, but want
-// Google Test's own unit tests to be able to access them. Therefore we
-// declare them here as opposed to in gtest.h.
-GTEST_DECLARE_bool_(break_on_failure);
-GTEST_DECLARE_bool_(catch_exceptions);
-GTEST_DECLARE_string_(color);
-GTEST_DECLARE_string_(filter);
-GTEST_DECLARE_bool_(list_tests);
-GTEST_DECLARE_string_(output);
-GTEST_DECLARE_bool_(print_time);
-GTEST_DECLARE_int32_(repeat);
-GTEST_DECLARE_int32_(stack_trace_depth);
-GTEST_DECLARE_bool_(show_internal_stack_frames);
+// We don't want the users to modify this flag in the code, but want
+// Google Test's own unit tests to be able to access it. Therefore we
+// declare it here as opposed to in gtest.h.
+GTEST_DECLARE_bool_(death_test_use_fork);
namespace internal {
@@ -81,6 +76,7 @@ namespace internal {
extern const TypeId kTestTypeIdInGoogleTest;
// Names of the flags (needed for parsing Google Test flags).
+const char kAlsoRunDisabledTestsFlag[] = "also_run_disabled_tests";
const char kBreakOnFailureFlag[] = "break_on_failure";
const char kCatchExceptionsFlag[] = "catch_exceptions";
const char kColorFlag[] = "color";
@@ -89,6 +85,7 @@ const char kListTestsFlag[] = "list_tests";
const char kOutputFlag[] = "output";
const char kPrintTimeFlag[] = "print_time";
const char kRepeatFlag[] = "repeat";
+const char kThrowOnFailureFlag[] = "throw_on_failure";
// This class saves the values of all Google Test flags in its c'tor, and
// restores them in its d'tor.
@@ -96,37 +93,45 @@ class GTestFlagSaver {
public:
// The c'tor.
GTestFlagSaver() {
+ also_run_disabled_tests_ = GTEST_FLAG(also_run_disabled_tests);
break_on_failure_ = GTEST_FLAG(break_on_failure);
catch_exceptions_ = GTEST_FLAG(catch_exceptions);
color_ = GTEST_FLAG(color);
death_test_style_ = GTEST_FLAG(death_test_style);
+ death_test_use_fork_ = GTEST_FLAG(death_test_use_fork);
filter_ = GTEST_FLAG(filter);
internal_run_death_test_ = GTEST_FLAG(internal_run_death_test);
list_tests_ = GTEST_FLAG(list_tests);
output_ = GTEST_FLAG(output);
print_time_ = GTEST_FLAG(print_time);
repeat_ = GTEST_FLAG(repeat);
+ throw_on_failure_ = GTEST_FLAG(throw_on_failure);
}
// The d'tor is not virtual. DO NOT INHERIT FROM THIS CLASS.
~GTestFlagSaver() {
+ GTEST_FLAG(also_run_disabled_tests) = also_run_disabled_tests_;
GTEST_FLAG(break_on_failure) = break_on_failure_;
GTEST_FLAG(catch_exceptions) = catch_exceptions_;
GTEST_FLAG(color) = color_;
GTEST_FLAG(death_test_style) = death_test_style_;
+ GTEST_FLAG(death_test_use_fork) = death_test_use_fork_;
GTEST_FLAG(filter) = filter_;
GTEST_FLAG(internal_run_death_test) = internal_run_death_test_;
GTEST_FLAG(list_tests) = list_tests_;
GTEST_FLAG(output) = output_;
GTEST_FLAG(print_time) = print_time_;
GTEST_FLAG(repeat) = repeat_;
+ GTEST_FLAG(throw_on_failure) = throw_on_failure_;
}
private:
// Fields for saving the original values of flags.
+ bool also_run_disabled_tests_;
bool break_on_failure_;
bool catch_exceptions_;
String color_;
String death_test_style_;
+ bool death_test_use_fork_;
String filter_;
String internal_run_death_test_;
bool list_tests_;
@@ -134,6 +139,7 @@ class GTestFlagSaver {
bool print_time_;
bool pretty_;
internal::Int32 repeat_;
+ bool throw_on_failure_;
} GTEST_ATTRIBUTE_UNUSED_;
// Converts a Unicode code point to a narrow string in UTF-8 encoding.
@@ -164,6 +170,32 @@ String WideStringToUtf8(const wchar_t* str, int num_chars);
// Returns the number of active threads, or 0 when there is an error.
size_t GetThreadCount();
+// Reads the GTEST_SHARD_STATUS_FILE environment variable, and creates the file
+// if the variable is present. If a file already exists at this location, this
+// function will write over it. If the variable is present, but the file cannot
+// be created, prints an error and exits.
+void WriteToShardStatusFileIfNeeded();
+
+// Checks whether sharding is enabled by examining the relevant
+// environment variable values. If the variables are present,
+// but inconsistent (e.g., shard_index >= total_shards), prints
+// an error and exits. If in_subprocess_for_death_test, sharding is
+// disabled because it must only be applied to the original test
+// process. Otherwise, we could filter out death tests we intended to execute.
+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
+// and aborts.
+Int32 Int32FromEnvOrDie(const char* env_var, Int32 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
+// method. Assumes that 0 <= shard_index < total_shards.
+bool ShouldRunTestOnShard(int total_shards, int shard_index, int test_id);
+
// List is a simple singly-linked list container.
//
// We cannot use std::list as Microsoft's implementation of STL has
@@ -790,9 +822,10 @@ class UnitTestOptions {
// Returns the output format, or "" for normal printed output.
static String GetOutputFormat();
- // Returns the name of the requested output file, or the default if none
- // was explicitly specified.
- static String GetOutputFile();
+ // Returns the absolute path of the requested output file, or the
+ // default (test_detail.xml in the original working directory) if
+ // none was explicitly specified.
+ static String GetAbsolutePathToOutputFile();
// Functions for processing the gtest_filter flag.
@@ -808,7 +841,7 @@ class UnitTestOptions {
static bool FilterMatchesTest(const String &test_case_name,
const String &test_name);
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
// Function for supporting the gtest_catch_exception flag.
// Returns EXCEPTION_EXECUTE_HANDLER if Google Test should handle the
@@ -891,6 +924,8 @@ class DefaultGlobalTestPartResultReporter
private:
UnitTestImpl* const unit_test_;
+
+ GTEST_DISALLOW_COPY_AND_ASSIGN_(DefaultGlobalTestPartResultReporter);
};
// This is the default per thread test part result reporter used in
@@ -905,6 +940,8 @@ class DefaultPerThreadTestPartResultReporter
private:
UnitTestImpl* const unit_test_;
+
+ GTEST_DISALLOW_COPY_AND_ASSIGN_(DefaultPerThreadTestPartResultReporter);
};
// The private implementation of the UnitTest class. We don't protect
@@ -1066,7 +1103,7 @@ class UnitTestImpl {
tear_down_tc)->AddTestInfo(test_info);
}
-#ifdef GTEST_HAS_PARAM_TEST
+#if GTEST_HAS_PARAM_TEST
// Returns ParameterizedTestCaseRegistry object used to keep track of
// value-parameterized tests and instantiate and register them.
internal::ParameterizedTestCaseRegistry& parameterized_test_registry() {
@@ -1108,11 +1145,18 @@ class UnitTestImpl {
ad_hoc_test_result_.Clear();
}
+ enum ReactionToSharding {
+ HONOR_SHARDING_PROTOCOL,
+ IGNORE_SHARDING_PROTOCOL
+ };
+
// Matches the full name of each test against the user-specified
// filter to decide whether the test should run, then records the
// result in each TestCase and TestInfo object.
+ // If shard_tests == HONOR_SHARDING_PROTOCOL, further filters tests
+ // based on sharding variables in the environment.
// Returns the number of tests that should run.
- int FilterTests();
+ int FilterTests(ReactionToSharding shard_tests);
// Lists all the tests by name.
void ListAllTests();
@@ -1139,7 +1183,7 @@ class UnitTestImpl {
return gtest_trace_stack_.pointer();
}
-#ifdef GTEST_HAS_DEATH_TEST
+#if GTEST_HAS_DEATH_TEST
// Returns a pointer to the parsed --gtest_internal_run_death_test
// flag, or NULL if that flag was not specified.
// This information is useful only in a death test child process.
@@ -1188,7 +1232,7 @@ class UnitTestImpl {
internal::List<TestCase*> test_cases_; // The list of TestCases.
-#ifdef GTEST_HAS_PARAM_TEST
+#if GTEST_HAS_PARAM_TEST
// ParameterizedTestRegistry object used to register value-parameterized
// tests.
internal::ParameterizedTestCaseRegistry parameterized_test_registry_;
@@ -1237,7 +1281,7 @@ class UnitTestImpl {
// How long the test took to run, in milliseconds.
TimeInMillis elapsed_time_;
-#ifdef GTEST_HAS_DEATH_TEST
+#if GTEST_HAS_DEATH_TEST
// The decomposed components of the gtest_internal_run_death_test flag,
// parsed when RUN_ALL_TESTS is called.
internal::scoped_ptr<InternalRunDeathTestFlag> internal_run_death_test_flag_;
@@ -1256,11 +1300,98 @@ inline UnitTestImpl* GetUnitTestImpl() {
return UnitTest::GetInstance()->impl();
}
+// Internal helper functions for implementing the simple regular
+// expression matcher.
+bool IsInSet(char ch, const char* str);
+bool IsDigit(char ch);
+bool IsPunct(char ch);
+bool IsRepeat(char ch);
+bool IsWhiteSpace(char ch);
+bool IsWordChar(char ch);
+bool IsValidEscape(char ch);
+bool AtomMatchesChar(bool escaped, char pattern, char ch);
+bool ValidateRegex(const char* regex);
+bool MatchRegexAtHead(const char* regex, const char* str);
+bool MatchRepetitionAndRegexAtHead(
+ bool escaped, char ch, char repeat, const char* regex, const char* str);
+bool MatchRegexAnywhere(const char* regex, const char* str);
+
// Parses the command line for Google Test flags, without initializing
// other parts of Google Test.
void ParseGoogleTestFlagsOnly(int* argc, char** argv);
void ParseGoogleTestFlagsOnly(int* argc, wchar_t** argv);
+#if GTEST_HAS_DEATH_TEST
+
+// Returns the message describing the last system error, regardless of the
+// platform.
+String GetLastSystemErrorMessage();
+
+#if GTEST_OS_WINDOWS
+// Provides leak-safe Windows kernel handle ownership.
+class AutoHandle {
+ public:
+ AutoHandle() : handle_(INVALID_HANDLE_VALUE) {}
+ explicit AutoHandle(HANDLE handle) : handle_(handle) {}
+
+ ~AutoHandle() { Reset(); }
+
+ HANDLE Get() const { return handle_; }
+ void Reset() { Reset(INVALID_HANDLE_VALUE); }
+ void Reset(HANDLE handle) {
+ if (handle != handle_) {
+ if (handle_ != INVALID_HANDLE_VALUE)
+ ::CloseHandle(handle_);
+ handle_ = handle;
+ }
+ }
+
+ private:
+ HANDLE handle_;
+
+ GTEST_DISALLOW_COPY_AND_ASSIGN_(AutoHandle);
+};
+#endif // GTEST_OS_WINDOWS
+
+// Attempts to parse a string into a positive integer pointed to by the
+// number parameter. Returns true if that is possible.
+// GTEST_HAS_DEATH_TEST implies that we have ::std::string, so we can use
+// it here.
+template <typename Integer>
+bool ParseNaturalNumber(const ::std::string& str, Integer* number) {
+ // Fail fast if the given string does not begin with a digit;
+ // this bypasses strtoXXX's "optional leading whitespace and plus
+ // or minus sign" semantics, which are undesirable here.
+ if (str.empty() || !isdigit(str[0])) {
+ return false;
+ }
+ errno = 0;
+
+ char* end;
+ // BiggestConvertible is the largest integer type that system-provided
+ // string-to-number conversion routines can return.
+#if GTEST_OS_WINDOWS
+ 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
+ const bool parse_success = *end == '\0' && errno == 0;
+
+ // TODO(vladl@google.com): Convert this to compile time assertion when it is
+ // available.
+ GTEST_CHECK_(sizeof(Integer) <= sizeof(parsed));
+
+ const Integer result = static_cast<Integer>(parsed);
+ if (parse_success && static_cast<BiggestConvertible>(result) == parsed) {
+ *number = result;
+ return true;
+ }
+ return false;
+}
+#endif // GTEST_HAS_DEATH_TEST
+
} // namespace internal
} // namespace testing
diff --git a/utils/unittest/googletest/include/gtest/internal/gtest-internal.h b/utils/unittest/googletest/include/gtest/internal/gtest-internal.h
index 242ffea..def4b59 100644
--- a/utils/unittest/googletest/include/gtest/internal/gtest-internal.h
+++ b/utils/unittest/googletest/include/gtest/internal/gtest-internal.h
@@ -39,7 +39,7 @@
#include <gtest/internal/gtest-port.h>
-#ifdef GTEST_OS_LINUX
+#if GTEST_OS_LINUX
#include <stdlib.h>
#include <sys/types.h>
#include <sys/wait.h>
@@ -566,7 +566,7 @@ class TestFactoryImpl : public TestFactoryBase {
virtual Test* CreateTest() { return new TestClass; }
};
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
// Predicate-formatters for implementing the HRESULT checking macros
// {ASSERT|EXPECT}_HRESULT_{SUCCEEDED|FAILED}
@@ -620,7 +620,7 @@ TestInfo* MakeAndRegisterTestInfo(
TearDownTestCaseFunc tear_down_tc,
TestFactoryBase* factory);
-#if defined(GTEST_HAS_TYPED_TEST) || defined(GTEST_HAS_TYPED_TEST_P)
+#if GTEST_HAS_TYPED_TEST || GTEST_HAS_TYPED_TEST_P
// State of the definition of a type-parameterized test case.
class TypedTestCasePState {
@@ -636,6 +636,7 @@ class TypedTestCasePState {
fprintf(stderr, "%s Test %s must be defined before "
"REGISTER_TYPED_TEST_CASE_P(%s, ...).\n",
FormatFileLocation(file, line).c_str(), test_name, case_name);
+ fflush(stderr);
abort();
}
defined_test_names_.insert(test_name);
@@ -768,6 +769,9 @@ String GetCurrentOsStackTraceExceptTop(UnitTest* unit_test, int skip_count);
// Returns the number of failed test parts in the given test result object.
int GetFailedPartCount(const TestResult* result);
+// A helper for suppressing warnings on unreachable code in some macros.
+bool AlwaysTrue();
+
} // namespace internal
} // namespace testing
@@ -784,12 +788,18 @@ int GetFailedPartCount(const TestResult* result);
#define GTEST_SUCCESS_(message) \
GTEST_MESSAGE_(message, ::testing::TPRT_SUCCESS)
+// Suppresses MSVC warnings 4072 (unreachable code) for the code following
+// statement if it returns or throws (or doesn't return or throw in some
+// situations).
+#define GTEST_HIDE_UNREACHABLE_CODE_(statement) \
+ if (::testing::internal::AlwaysTrue()) { statement; }
+
#define GTEST_TEST_THROW_(statement, expected_exception, fail) \
GTEST_AMBIGUOUS_ELSE_BLOCKER_ \
if (const char* gtest_msg = "") { \
bool gtest_caught_expected = false; \
try { \
- statement; \
+ GTEST_HIDE_UNREACHABLE_CODE_(statement); \
} \
catch (expected_exception const&) { \
gtest_caught_expected = true; \
@@ -813,7 +823,7 @@ int GetFailedPartCount(const TestResult* result);
GTEST_AMBIGUOUS_ELSE_BLOCKER_ \
if (const char* gtest_msg = "") { \
try { \
- statement; \
+ GTEST_HIDE_UNREACHABLE_CODE_(statement); \
} \
catch (...) { \
gtest_msg = "Expected: " #statement " doesn't throw an exception.\n" \
@@ -829,7 +839,7 @@ int GetFailedPartCount(const TestResult* result);
if (const char* gtest_msg = "") { \
bool gtest_caught_any = false; \
try { \
- statement; \
+ GTEST_HIDE_UNREACHABLE_CODE_(statement); \
} \
catch (...) { \
gtest_caught_any = true; \
@@ -855,7 +865,7 @@ int GetFailedPartCount(const TestResult* result);
GTEST_AMBIGUOUS_ELSE_BLOCKER_ \
if (const char* gtest_msg = "") { \
::testing::internal::HasNewFatalFailureHelper gtest_fatal_failure_checker; \
- { statement; } \
+ GTEST_HIDE_UNREACHABLE_CODE_(statement); \
if (gtest_fatal_failure_checker.has_new_fatal_failure()) { \
gtest_msg = "Expected: " #statement " doesn't generate new fatal " \
"failures in the current thread.\n" \
diff --git a/utils/unittest/googletest/include/gtest/internal/gtest-param-util-generated.h b/utils/unittest/googletest/include/gtest/internal/gtest-param-util-generated.h
index 17f3f7b..ad06e02 100644
--- a/utils/unittest/googletest/include/gtest/internal/gtest-param-util-generated.h
+++ b/utils/unittest/googletest/include/gtest/internal/gtest-param-util-generated.h
@@ -46,7 +46,7 @@
#include <gtest/internal/gtest-port.h>
-#ifdef GTEST_HAS_PARAM_TEST
+#if GTEST_HAS_PARAM_TEST
#include <gtest/internal/gtest-param-util.h>
@@ -2659,7 +2659,7 @@ class ValueArray50 {
const T50 v50_;
};
-#ifdef GTEST_HAS_COMBINE
+#if GTEST_HAS_COMBINE
// INTERNAL IMPLEMENTATION - DO NOT USE IN USER CODE.
//
// Generates values from the Cartesian product of values produced
diff --git a/utils/unittest/googletest/include/gtest/internal/gtest-param-util.h b/utils/unittest/googletest/include/gtest/internal/gtest-param-util.h
index 3bb07ec..5559ab4 100644
--- a/utils/unittest/googletest/include/gtest/internal/gtest-param-util.h
+++ b/utils/unittest/googletest/include/gtest/internal/gtest-param-util.h
@@ -40,7 +40,7 @@
#include <gtest/internal/gtest-port.h>
-#ifdef GTEST_HAS_PARAM_TEST
+#if GTEST_HAS_PARAM_TEST
#if GTEST_HAS_RTTI
#include <typeinfo>
diff --git a/utils/unittest/googletest/include/gtest/internal/gtest-port.h b/utils/unittest/googletest/include/gtest/internal/gtest-port.h
index 20a95c9..d949ec1 100644
--- a/utils/unittest/googletest/include/gtest/internal/gtest-port.h
+++ b/utils/unittest/googletest/include/gtest/internal/gtest-port.h
@@ -63,21 +63,15 @@
// This header defines the following utilities:
//
-// Macros indicating the name of the Google C++ Testing Framework project:
-// GTEST_NAME - a string literal of the project name.
-// GTEST_FLAG_PREFIX - a string literal of the prefix all Google
-// Test flag names share.
-// GTEST_FLAG_PREFIX_UPPER - a string literal of the prefix all Google
-// Test flag names share, in upper case.
-//
-// Macros indicating the current platform:
-// GTEST_OS_CYGWIN - defined iff compiled on Cygwin.
-// GTEST_OS_LINUX - defined iff compiled on Linux.
-// GTEST_OS_MAC - defined iff compiled on Mac OS X.
-// GTEST_OS_SOLARIS - defined iff compiled on Sun Solaris.
-// GTEST_OS_SYMBIAN - defined iff compiled for Symbian.
-// GTEST_OS_WINDOWS - defined iff compiled on Windows.
-// GTEST_OS_ZOS - defined iff compiled on IBM z/OS.
+// Macros indicating the current platform (defined to 1 if compiled on
+// the given platform; otherwise undefined):
+// GTEST_OS_CYGWIN - Cygwin
+// GTEST_OS_LINUX - Linux
+// GTEST_OS_MAC - Mac OS X
+// GTEST_OS_SOLARIS - Sun Solaris
+// GTEST_OS_SYMBIAN - Symbian
+// GTEST_OS_WINDOWS - Windows
+// GTEST_OS_ZOS - z/OS
//
// Among the platforms, Cygwin, Linux, Max OS X, and Windows have the
// most stable support. Since core members of the Google Test project
@@ -86,17 +80,19 @@
// googletestframework@googlegroups.com (patches for fixing them are
// even more welcome!).
//
-// Note that it is possible that none of the GTEST_OS_ macros are defined.
+// Note that it is possible that none of the GTEST_OS_* macros are defined.
//
-// Macros indicating available Google Test features:
-// GTEST_HAS_COMBINE - defined iff Combine construct is supported
-// in value-parameterized tests.
-// GTEST_HAS_DEATH_TEST - defined iff death tests are supported.
-// GTEST_HAS_PARAM_TEST - defined iff value-parameterized tests are
-// supported.
-// GTEST_HAS_TYPED_TEST - defined iff typed tests are supported.
-// GTEST_HAS_TYPED_TEST_P - defined iff type-parameterized tests are
-// supported.
+// Macros indicating available Google Test features (defined to 1 if
+// the corresponding feature is supported; otherwise undefined):
+// GTEST_HAS_COMBINE - the Combine() function (for value-parameterized
+// tests)
+// GTEST_HAS_DEATH_TEST - death tests
+// GTEST_HAS_PARAM_TEST - value-parameterized tests
+// GTEST_HAS_TYPED_TEST - typed tests
+// GTEST_HAS_TYPED_TEST_P - type-parameterized tests
+// GTEST_USES_POSIX_RE - enhanced POSIX regex is used.
+// GTEST_USES_SIMPLE_RE - our own simple regex is used;
+// the above two are mutually exclusive.
//
// Macros for basic C++ coding:
// GTEST_AMBIGUOUS_ELSE_BLOCKER_ - for disabling a gcc warning.
@@ -155,9 +151,11 @@
#include <stdio.h>
#include <iostream> // Used for GTEST_CHECK_
-#define GTEST_NAME "Google Test"
-#define GTEST_FLAG_PREFIX "gtest_"
-#define GTEST_FLAG_PREFIX_UPPER "GTEST_"
+#define GTEST_DEV_EMAIL_ "googletestframework@@googlegroups.com"
+#define GTEST_FLAG_PREFIX_ "gtest_"
+#define GTEST_FLAG_PREFIX_UPPER_ "GTEST_"
+#define GTEST_NAME_ "Google Test"
+#define GTEST_PROJECT_URL_ "http://code.google.com/p/googletest/"
// Determines the version of gcc that is used to compile this.
#ifdef __GNUC__
@@ -168,49 +166,76 @@
// Determines the platform on which Google Test is compiled.
#ifdef __CYGWIN__
-#define GTEST_OS_CYGWIN
+#define GTEST_OS_CYGWIN 1
#elif __SYMBIAN32__
-#define GTEST_OS_SYMBIAN
+#define GTEST_OS_SYMBIAN 1
#elif defined _MSC_VER
// TODO(kenton@google.com): GTEST_OS_WINDOWS is currently used to mean
// both "The OS is Windows" and "The compiler is MSVC". These
// meanings really should be separated in order to better support
// Windows compilers other than MSVC.
-#define GTEST_OS_WINDOWS
+#define GTEST_OS_WINDOWS 1
#elif defined __APPLE__
-#define GTEST_OS_MAC
+#define GTEST_OS_MAC 1
#elif defined __linux__
-#define GTEST_OS_LINUX
+#define GTEST_OS_LINUX 1
#elif defined __MVS__
-#define GTEST_OS_ZOS
+#define GTEST_OS_ZOS 1
#elif defined(__sun) && defined(__SVR4)
-#define GTEST_OS_SOLARIS
+#define GTEST_OS_SOLARIS 1
#elif defined(__HAIKU__)
#define GTEST_OS_HAIKU
#endif // _MSC_VER
-// Determines whether ::std::string and ::string are available.
+#if GTEST_OS_CYGWIN || GTEST_OS_LINUX || GTEST_OS_MAC
-#ifndef GTEST_HAS_STD_STRING
-// The user didn't tell us whether ::std::string is available, so we
-// need to figure it out.
+// On some platforms, <regex.h> needs someone to define size_t, and
+// won't compile otherwise. We can #include it here as we already
+// included <stdlib.h>, which is guaranteed to define size_t through
+// <stddef.h>.
+#include <regex.h> // NOLINT
+#define GTEST_USES_POSIX_RE 1
-#ifdef GTEST_OS_WINDOWS
+#else
+
+// <regex.h> may not be available on this platform. Use our own
+// simple regex implementation instead.
+#define GTEST_USES_SIMPLE_RE 1
+
+#endif // GTEST_OS_CYGWIN || GTEST_OS_LINUX || GTEST_OS_MAC
+
+// Defines GTEST_HAS_EXCEPTIONS to 1 if exceptions are enabled, or 0
+// otherwise.
+
+#ifdef _MSC_VER // Compiled by MSVC?
// Assumes that exceptions are enabled by default.
-#ifndef _HAS_EXCEPTIONS
+#ifndef _HAS_EXCEPTIONS // MSVC uses this macro to enable exceptions.
#define _HAS_EXCEPTIONS 1
#endif // _HAS_EXCEPTIONS
-// GTEST_HAS_EXCEPTIONS is non-zero iff exceptions are enabled. It is
-// always defined, while _HAS_EXCEPTIONS is defined only on Windows.
#define GTEST_HAS_EXCEPTIONS _HAS_EXCEPTIONS
-// On Windows, we can use ::std::string if the compiler version is VS
-// 2005 or above, or if exceptions are enabled.
-#define GTEST_HAS_STD_STRING ((_MSC_VER >= 1400) || GTEST_HAS_EXCEPTIONS)
-#else // We are on Linux or Mac OS.
+#else // The compiler is not MSVC.
+// gcc defines __EXCEPTIONS to 1 iff exceptions are enabled. For
+// other compilers, we assume exceptions are disabled to be
+// conservative.
+#if defined(__GNUC__) && __EXCEPTIONS
+#define GTEST_HAS_EXCEPTIONS 1
+#else
#define GTEST_HAS_EXCEPTIONS 0
-#define GTEST_HAS_STD_STRING 1
-#endif // GTEST_OS_WINDOWS
+#endif // defined(__GNUC__) && __EXCEPTIONS
+#endif // _MSC_VER
+// Determines whether ::std::string and ::string are available.
+
+#ifndef GTEST_HAS_STD_STRING
+// The user didn't tell us whether ::std::string is available, so we
+// need to figure it out. The only environment that we know
+// ::std::string is not available is MSVC 7.1 or lower with exceptions
+// disabled.
+#if defined(_MSC_VER) && (_MSC_VER < 1400) && !GTEST_HAS_EXCEPTIONS
+#define GTEST_HAS_STD_STRING 0
+#else
+#define GTEST_HAS_STD_STRING 1
+#endif
#endif // GTEST_HAS_STD_STRING
#ifndef GTEST_HAS_GLOBAL_STRING
@@ -227,21 +252,23 @@
// TODO(wan@google.com): uses autoconf to detect whether ::std::wstring
// is available.
-#if defined(GTEST_OS_CYGWIN) || defined(GTEST_OS_SOLARIS) || defined(GTEST_OS_HAIKU) || defined(_MINIX)
-// At least some versions of cygwin don't support ::std::wstring.
+#if GTEST_OS_CYGWIN || GTEST_OS_SOLARIS || GTEST_OS_HAIKU || defined(_MINIX)
+// Cygwin 1.5 and below doesn't support ::std::wstring.
+// Cygwin 1.7 might add wstring support; this should be updated when clear.
// Solaris' libc++ doesn't support it either.
// Minix currently doesn't support it either.
#define GTEST_HAS_STD_WSTRING 0
#else
#define GTEST_HAS_STD_WSTRING GTEST_HAS_STD_STRING
-#endif // defined(GTEST_OS_CYGWIN) || defined(GTEST_OS_SOLARIS)
+#endif // GTEST_OS_CYGWIN || GTEST_OS_SOLARIS
#endif // GTEST_HAS_STD_WSTRING
#ifndef GTEST_HAS_GLOBAL_WSTRING
// The user didn't tell us whether ::wstring is available, so we need
// to figure it out.
-#define GTEST_HAS_GLOBAL_WSTRING GTEST_HAS_GLOBAL_STRING
+#define GTEST_HAS_GLOBAL_WSTRING \
+ (GTEST_HAS_STD_WSTRING && GTEST_HAS_GLOBAL_STRING)
#endif // GTEST_HAS_GLOBAL_WSTRING
#if GTEST_HAS_STD_STRING || GTEST_HAS_GLOBAL_STRING || \
@@ -295,13 +322,7 @@
// Determines whether <pthread.h> is available.
#ifndef GTEST_HAS_PTHREAD
// The user didn't tell us, so we need to figure it out.
-
-#if defined(GTEST_OS_LINUX) || defined(GTEST_OS_MAC)
-#define GTEST_HAS_PTHREAD 1
-#else
-#define GTEST_HAS_PTHREAD 0
-#endif // GTEST_OS_LINUX || GTEST_OS_MAC
-
+#define GTEST_HAS_PTHREAD (GTEST_OS_LINUX || GTEST_OS_MAC)
#endif // GTEST_HAS_PTHREAD
// Determines whether tr1/tuple is available. If you have tr1/tuple
@@ -342,33 +363,36 @@
#ifndef GTEST_HAS_CLONE
// The user didn't tell us, so we need to figure it out.
-#if defined(GTEST_OS_LINUX) && !defined(__ia64__)
+#if GTEST_OS_LINUX && !defined(__ia64__)
#define GTEST_HAS_CLONE 1
#else
#define GTEST_HAS_CLONE 0
-#endif // defined(GTEST_OS_LINUX) && !defined(__ia64__)
+#endif // GTEST_OS_LINUX && !defined(__ia64__)
#endif // GTEST_HAS_CLONE
// Determines whether to support death tests.
-#if GTEST_HAS_STD_STRING && GTEST_HAS_CLONE
-#define GTEST_HAS_DEATH_TEST
-// On some platforms, <regex.h> needs someone to define size_t, and
-// won't compile otherwise. We can #include it here as we already
-// included <stdlib.h>, which is guaranteed to define size_t through
-// <stddef.h>.
-#include <regex.h>
+// Google Test does not support death tests for VC 7.1 and earlier for
+// these reasons:
+// 1. std::vector does not build in VC 7.1 when exceptions are disabled.
+// 2. std::string does not build in VC 7.1 when exceptions are disabled
+// (this is covered by GTEST_HAS_STD_STRING guard).
+// 3. abort() in a VC 7.1 application compiled as GUI in debug config
+// pops up a dialog window that cannot be suppressed programmatically.
+#if GTEST_HAS_STD_STRING && (GTEST_OS_LINUX || \
+ GTEST_OS_MAC || \
+ GTEST_OS_CYGWIN || \
+ (GTEST_OS_WINDOWS && _MSC_VER >= 1400))
+#define GTEST_HAS_DEATH_TEST 1
#include <vector>
-#include <fcntl.h>
-#include <sys/mman.h>
-#endif // GTEST_HAS_STD_STRING && GTEST_HAS_CLONE
+#endif
// Determines whether to support value-parameterized tests.
#if defined(__GNUC__) || (_MSC_VER >= 1400)
// TODO(vladl@google.com): get the implementation rid of vector and list
// to compile on MSVC 7.1.
-#define GTEST_HAS_PARAM_TEST
+#define GTEST_HAS_PARAM_TEST 1
#endif // defined(__GNUC__) || (_MSC_VER >= 1400)
// Determines whether to support type-driven tests.
@@ -376,21 +400,19 @@
// Typed tests need <typeinfo> and variadic macros, which gcc and VC
// 8.0+ support.
#if defined(__GNUC__) || (_MSC_VER >= 1400)
-#define GTEST_HAS_TYPED_TEST
-#define GTEST_HAS_TYPED_TEST_P
+#define GTEST_HAS_TYPED_TEST 1
+#define GTEST_HAS_TYPED_TEST_P 1
#endif // defined(__GNUC__) || (_MSC_VER >= 1400)
// Determines whether to support Combine(). This only makes sense when
// value-parameterized tests are enabled.
-#if defined(GTEST_HAS_PARAM_TEST) && GTEST_HAS_TR1_TUPLE
-#define GTEST_HAS_COMBINE
-#endif // defined(GTEST_HAS_PARAM_TEST) && GTEST_HAS_TR1_TUPLE
+#if GTEST_HAS_PARAM_TEST && GTEST_HAS_TR1_TUPLE
+#define GTEST_HAS_COMBINE 1
+#endif // GTEST_HAS_PARAM_TEST && GTEST_HAS_TR1_TUPLE
// Determines whether the system compiler uses UTF-16 for encoding wide strings.
-#if defined(GTEST_OS_WINDOWS) || defined(GTEST_OS_CYGWIN) || \
- defined(GTEST_OS_SYMBIAN)
-#define GTEST_WIDE_STRING_USES_UTF16_ 1
-#endif
+#define GTEST_WIDE_STRING_USES_UTF16_ \
+ (GTEST_OS_WINDOWS || GTEST_OS_CYGWIN || GTEST_OS_SYMBIAN)
// Defines some utility macros.
@@ -491,8 +513,6 @@ class scoped_ptr {
GTEST_DISALLOW_COPY_AND_ASSIGN_(scoped_ptr);
};
-#ifdef GTEST_HAS_DEATH_TEST
-
// Defines RE.
// A simple C++ wrapper for <regex.h>. It uses the POSIX Enxtended
@@ -550,12 +570,16 @@ class RE {
// String type here, in order to simplify dependencies between the
// files.
const char* pattern_;
+ bool is_valid_;
+#if GTEST_USES_POSIX_RE
regex_t full_regex_; // For FullMatch().
regex_t partial_regex_; // For PartialMatch().
- bool is_valid_;
-};
+#else // GTEST_USES_SIMPLE_RE
+ const char* full_pattern_; // For FullMatch();
+#endif
-#endif // GTEST_HAS_DEATH_TEST
+ GTEST_DISALLOW_COPY_AND_ASSIGN_(RE);
+};
// Defines logging utilities:
// GTEST_LOG_() - logs messages at the specified severity level.
@@ -584,14 +608,17 @@ inline void FlushInfoLog() { fflush(NULL); }
// CaptureStderr - starts capturing stderr.
// GetCapturedStderr - stops capturing stderr and returns the captured string.
-#ifdef GTEST_HAS_DEATH_TEST
+#if GTEST_HAS_STD_STRING
+void CaptureStderr();
+::std::string GetCapturedStderr();
+#endif // GTEST_HAS_STD_STRING
+
+#if GTEST_HAS_DEATH_TEST
// A copy of all command line arguments. Set by InitGoogleTest().
extern ::std::vector<String> g_argvs;
-void CaptureStderr();
// GTEST_HAS_DEATH_TEST implies we have ::std::string.
-::std::string GetCapturedStderr();
const ::std::vector<String>& GetArgvs();
#endif // GTEST_HAS_DEATH_TEST
@@ -675,10 +702,15 @@ struct is_pointer : public false_type {};
template <typename T>
struct is_pointer<T*> : public true_type {};
+#if GTEST_OS_WINDOWS
+#define GTEST_PATH_SEP_ "\\"
+#else
+#define GTEST_PATH_SEP_ "/"
+#endif // GTEST_OS_WINDOWS
+
// Defines BiggestInt as the biggest signed integer type the compiler
// supports.
-
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
typedef __int64 BiggestInt;
#else
typedef long long BiggestInt; // NOLINT
@@ -736,7 +768,7 @@ class TypeWithSize<4> {
template <>
class TypeWithSize<8> {
public:
-#ifdef GTEST_OS_WINDOWS
+#if GTEST_OS_WINDOWS
typedef __int64 Int;
typedef unsigned __int64 UInt;
#else
@@ -759,7 +791,7 @@ inline const char* GetEnv(const char* name) {
#ifdef _WIN32_WCE // We are on Windows CE.
// CE has no environment variables.
return NULL;
-#elif defined(GTEST_OS_WINDOWS) // We are on Windows proper.
+#elif GTEST_OS_WINDOWS // We are on Windows proper.
// MSVC 8 deprecates getenv(), so we want to suppress warning 4996
// (deprecated function) there.
#pragma warning(push) // Saves the current warning state.
diff --git a/utils/unittest/googletest/include/gtest/internal/gtest-string.h b/utils/unittest/googletest/include/gtest/internal/gtest-string.h
index 178f14e..566a6b5 100644
--- a/utils/unittest/googletest/include/gtest/internal/gtest-string.h
+++ b/utils/unittest/googletest/include/gtest/internal/gtest-string.h
@@ -35,7 +35,7 @@
// Google Test. They are subject to change without notice. They should not used
// by code external to Google Test.
//
-// This header file is #included by testing/base/internal/gtest-internal.h.
+// This header file is #included by <gtest/internal/gtest-internal.h>.
// It should not be #included by other files.
#ifndef GTEST_INCLUDE_GTEST_INTERNAL_GTEST_STRING_H_
diff --git a/utils/unittest/googletest/include/gtest/internal/gtest-type-util.h b/utils/unittest/googletest/include/gtest/internal/gtest-type-util.h
index 815da4b..1ea7d18 100644
--- a/utils/unittest/googletest/include/gtest/internal/gtest-type-util.h
+++ b/utils/unittest/googletest/include/gtest/internal/gtest-type-util.h
@@ -45,7 +45,7 @@
#include <gtest/internal/gtest-port.h>
#include <gtest/internal/gtest-string.h>
-#if defined(GTEST_HAS_TYPED_TEST) || defined(GTEST_HAS_TYPED_TEST_P)
+#if GTEST_HAS_TYPED_TEST || GTEST_HAS_TYPED_TEST_P
#ifdef __GNUC__
#include <cxxabi.h>