Skip to content
Closed
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
Enable emulated TLS and add test.
  • Loading branch information
marsupial authored and Axel-Naumann committed Jul 6, 2017
commit eff7edf7bf358bf33171f41c45f5d9958d4adda7
3 changes: 3 additions & 0 deletions interpreter/cling/lib/Interpreter/IncrementalExecutor.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -97,6 +97,9 @@ IncrementalExecutor::IncrementalExecutor(clang::DiagnosticsEngine& diags,
m_AtExitFuncs.reserve(256);

std::unique_ptr<TargetMachine> TM(CreateHostTargetMachine(CI));

TM->Options.EmulatedTLS = 1;

m_BackendPasses.reset(new BackendPasses(CI.getCodeGenOpts(),
CI.getTargetOpts(),
CI.getLangOpts(),
Expand Down
1 change: 1 addition & 0 deletions interpreter/cling/lib/Utils/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ endif()
add_cling_library(clingUtils OBJECT
AST.cpp
Diagnostics.cpp
EmuTLS.cpp
ParserStateRAII.cpp
Output.cpp
Paths.cpp
Expand Down
17 changes: 14 additions & 3 deletions interpreter/cling/lib/Utils/EmuTLS.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5,15 +5,24 @@
* This file is dual licensed under the MIT and the University of Illinois Open
* Source Licenses. See LICENSE.TXT for details.
*
* Taken from compiler-rt/lib/builtins/emutls.c with additions for Windows
*
* ===----------------------------------------------------------------------===
*/

// When compiling with GCC, use its version of __emutls_get_address

#if defined(__clang__) || defined(_WIN32)

#include "cling/Utils/Casting.h"

#include <stdint.h>
#include <stdlib.h>
#include <string.h>

#include "int_lib.h"
#include "int_util.h"
#ifndef COMPILE_TIME_ASSERT
#define COMPILE_TIME_ASSERT(X) static_assert(X, "Error")
#endif

typedef struct emutls_address_array {
uintptr_t size; /* number of elements in the 'data' array */
Expand Down Expand Up @@ -340,10 +349,12 @@ emutls_get_address_array(uintptr_t index) {
return array;
}

void* __emutls_get_address(__emutls_control* control) {
extern "C" void* __emutls_get_address(__emutls_control* control) {
uintptr_t index = emutls_get_index(control);
emutls_address_array* array = emutls_get_address_array(index--);
if (array->data[index] == NULL)
array->data[index] = emutls_allocate_object(control);
return array->data[index];
}

#endif
54 changes: 54 additions & 0 deletions interpreter/cling/test/CodeGeneration/TLSVars.C
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
//------------------------------------------------------------------------------
// CLING - the C++ LLVM-based InterpreterG :)
//
// This file is dual-licensed: you can choose to license it under the University
// of Illinois Open Source License or the GNU Lesser General Public License. See
// LICENSE.TXT for details.
//------------------------------------------------------------------------------

// RUN: cat %s | %cling -Xclang -verify | FileCheck %s

// Test whether the TLS data is properly handled

#include <string>
#include <thread>
#include <mutex>
#include <stdio.h>
#include <stdlib.h>

thread_local unsigned int TLSCounter = 1;
std::mutex WriteMutex;

static void WriteValue(const char* Name, unsigned Val) {
std::lock_guard<std::mutex> Lock(WriteMutex);
printf("TLSCounter for '%s' : %u\n", Name, Val);
}

void TLSIncrement(const char* Name) {
++TLSCounter;
if (const int Incr = atoi(Name))
TLSCounter += Incr;
WriteValue(Name, TLSCounter);
}

static const char* Name[] = {
"A",
"B",
"10",
"5",
0,
};
for (unsigned i = 0; Name[i]; ++i) {
std::thread(TLSIncrement, Name[i]).join();
}
WriteValue("main", TLSCounter);


// CHECK: TLSCounter for 'A' : 2
// CHECK: TLSCounter for 'B' : 2
// CHECK: TLSCounter for '10' : 12
// CHECK: TLSCounter for '5' : 7
// CHECK: TLSCounter for 'main' : 1

// expected-no-diagnostics
.q