From 1beff241c359fb8c98c98a661142e5b614eceb64 Mon Sep 17 00:00:00 2001
From: Manoj Gupta <manojgupta@google.com>
Date: Tue, 17 Oct 2017 11:01:39 -0700
Subject: [PATCH] googletest: Add GTEST_API_ attribute to ThreadLocal class.

ThreadLocal class needs to be have default visibility.
Root cause is gtest uses typeinfo for the ThreadLocal class.
The problem manifests When gtest/gmock are built as a shared library
with libc++. When a class is used in typeinfo, it must have default
visibility.

There is an explanation about typeinfo and visibility here:
https://developer.apple.com/library/content/documentation/DeveloperTools/Conceptual/CppRuntimeEnv/Articles/SymbolVisibility.html

When libc++ is used with gtest in shared library mode, any tests
that are compiled with -fvisibility=hidden and exercise the
macro EXPECT_CALL, it results in an abort like:
[ FATAL ] /usr/include/gtest/internal/gtest-port.h:1394::
Condition typeid(*base) == typeid(Derived) failed.
This is because the typeinfo for ThreadLocal class is not visible.
Therefore, linker failed to match it to the shared library symbol, creating a
new symbol instead.

This fixes https://github.com/google/googletest/issues/1207.
---
 googletest/include/gtest/internal/gtest-port.h | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/googletest/include/gtest/internal/gtest-port.h b/googletest/include/gtest/internal/gtest-port.h
index 5529ba544..5e1315987 100644
--- a/googletest/include/gtest/internal/gtest-port.h
+++ b/googletest/include/gtest/internal/gtest-port.h
@@ -2061,7 +2061,7 @@ extern "C" inline void DeleteThreadLocalValue(void* value_holder) {
 
 // Implements thread-local storage on pthreads-based systems.
 template <typename T>
-class ThreadLocal {
+class GTEST_API_ ThreadLocal {
  public:
   ThreadLocal()
       : key_(CreateKey()), default_factory_(new DefaultValueHolderFactory()) {}
@@ -2193,7 +2193,7 @@ class GTestMutexLock {
 typedef GTestMutexLock MutexLock;
 
 template <typename T>
-class ThreadLocal {
+class GTEST_API_ ThreadLocal {
  public:
   ThreadLocal() : value_() {}
   explicit ThreadLocal(const T& value) : value_(value) {}