This commit is contained in:
Dmitry Samersoff 2015-12-04 18:40:03 +00:00
commit 4622d15a73
126 changed files with 822 additions and 2098 deletions

View File

@ -74,6 +74,9 @@ CFLAGS += $(VM_PICFLAG)
CFLAGS += -qnortti
CFLAGS += -qnoeh
# for compiler-level tls
CFLAGS += -qtls=default
CFLAGS += -D_REENTRANT
# no xlc counterpart for -fcheck-new
# CFLAGS += -fcheck-new

View File

@ -260,6 +260,9 @@ endif
OPT_CFLAGS = $(OPT_CFLAGS/$(OPT_CFLAGS_DEFAULT)) $(OPT_EXTRAS)
# Variable tracking size limit exceeded for VMStructs::init()
OPT_CFLAGS/vmStructs.o += -fno-var-tracking-assignments
# The gcc compiler segv's on ia64 when compiling bytecodeInterpreter.cpp
# if we use expensive-optimizations
ifeq ($(BUILDARCH), ia64)

View File

@ -41,6 +41,7 @@
#include "runtime/icache.hpp"
#include "runtime/interfaceSupport.hpp"
#include "runtime/sharedRuntime.hpp"
#include "runtime/thread.hpp"
#if INCLUDE_ALL_GCS
#include "gc/g1/g1CollectedHeap.inline.hpp"
@ -4653,3 +4654,23 @@ void MacroAssembler::encode_iso_array(Register src, Register dst,
BIND(DONE);
sub(result, result, len); // Return index where we stopped
}
// get_thread() can be called anywhere inside generated code so we
// need to save whatever non-callee save context might get clobbered
// by the call to JavaThread::aarch64_get_thread_helper() or, indeed,
// the call setup code.
//
// aarch64_get_thread_helper() clobbers only r0, r1, and flags.
//
void MacroAssembler::get_thread(Register dst) {
RegSet saved_regs = RegSet::range(r0, r1) + lr - dst;
push(saved_regs, sp);
mov(lr, CAST_FROM_FN_PTR(address, JavaThread::aarch64_get_thread_helper));
blrt(lr, 1, 0, 1);
if (dst != c_rarg0) {
mov(dst, c_rarg0);
}
pop(saved_regs, sp);
}

View File

@ -360,10 +360,10 @@ void MacroAssembler::leave() {
#ifdef ASSERT
// a hook for debugging
static Thread* reinitialize_thread() {
return ThreadLocalStorage::thread();
return Thread::current();
}
#else
#define reinitialize_thread ThreadLocalStorage::thread
#define reinitialize_thread Thread::current
#endif
#ifdef ASSERT
@ -393,7 +393,7 @@ void MacroAssembler::get_thread() {
}
static Thread* verify_thread_subroutine(Thread* gthread_value) {
Thread* correct_value = ThreadLocalStorage::thread();
Thread* correct_value = Thread::current();
guarantee(gthread_value == correct_value, "G2_thread value must be the thread");
return correct_value;
}

View File

@ -36,7 +36,7 @@ extern "C" {
address _flush_reg_windows(); // in .s file.
// Flush registers to stack. In case of error we will need to stack walk.
address bootstrap_flush_windows(void) {
Thread* thread = ThreadLocalStorage::get_thread_slow();
Thread* thread = Thread::current_or_null();
// Very early in process there is no thread.
if (thread != NULL) {
guarantee(thread->is_Java_thread(), "Not a Java thread.");

View File

@ -39,6 +39,7 @@
#include "runtime/os.hpp"
#include "runtime/sharedRuntime.hpp"
#include "runtime/stubRoutines.hpp"
#include "runtime/thread.hpp"
#include "utilities/macros.hpp"
#if INCLUDE_ALL_GCS
#include "gc/g1/g1CollectedHeap.inline.hpp"
@ -10834,3 +10835,43 @@ SkipIfEqual::SkipIfEqual(
SkipIfEqual::~SkipIfEqual() {
_masm->bind(_label);
}
// 32-bit Windows has its own fast-path implementation
// of get_thread
#if !defined(WIN32) || defined(_LP64)
// This is simply a call to Thread::current()
void MacroAssembler::get_thread(Register thread) {
if (thread != rax) {
push(rax);
}
LP64_ONLY(push(rdi);)
LP64_ONLY(push(rsi);)
push(rdx);
push(rcx);
#ifdef _LP64
push(r8);
push(r9);
push(r10);
push(r11);
#endif
MacroAssembler::call_VM_leaf_base(CAST_FROM_FN_PTR(address, Thread::current), 0);
#ifdef _LP64
pop(r11);
pop(r10);
pop(r9);
pop(r8);
#endif
pop(rcx);
pop(rdx);
LP64_ONLY(pop(rsi);)
LP64_ONLY(pop(rdi);)
if (thread != rax) {
mov(thread, rax);
pop(rax);
}
}
#endif

View File

@ -902,7 +902,7 @@ static void *java_start(Thread *thread) {
int pid = os::current_process_id();
alloca(((pid ^ counter++) & 7) * 128);
ThreadLocalStorage::set_thread(thread);
thread->initialize_thread_current();
OSThread* osthread = thread->osthread();
@ -1077,32 +1077,6 @@ void os::free_thread(OSThread* osthread) {
delete osthread;
}
//////////////////////////////////////////////////////////////////////////////
// thread local storage
int os::allocate_thread_local_storage() {
pthread_key_t key;
int rslt = pthread_key_create(&key, NULL);
assert(rslt == 0, "cannot allocate thread local storage");
return (int)key;
}
// Note: This is currently not used by VM, as we don't destroy TLS key
// on VM exit.
void os::free_thread_local_storage(int index) {
int rslt = pthread_key_delete((pthread_key_t)index);
assert(rslt == 0, "invalid index");
}
void os::thread_local_storage_at_put(int index, void* value) {
int rslt = pthread_setspecific((pthread_key_t)index, value);
assert(rslt == 0, "pthread_setspecific failed");
}
extern "C" Thread* get_thread() {
return ThreadLocalStorage::thread();
}
////////////////////////////////////////////////////////////////////////////////
// time support

View File

@ -36,10 +36,6 @@
#include <sys/ioctl.h>
#include <netdb.h>
inline void* os::thread_local_storage_at(int index) {
return pthread_getspecific((pthread_key_t)index);
}
// File names are case-sensitive on windows only.
inline int os::file_name_strcmp(const char* s1, const char* s2) {
return strcmp(s1, s2);

View File

@ -1,36 +0,0 @@
/*
* Copyright (c) 2002, 2013, Oracle and/or its affiliates. All rights reserved.
* Copyright 2012, 2013 SAP AG. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#ifndef OS_AIX_VM_THREAD_AIX_INLINE_HPP
#define OS_AIX_VM_THREAD_AIX_INLINE_HPP
#include "runtime/thread.hpp"
#include "runtime/threadLocalStorage.hpp"
// Contains inlined functions for class Thread and ThreadLocalStorage
inline void ThreadLocalStorage::pd_invalidate_all() {} // nothing to do
#endif // OS_AIX_VM_THREAD_AIX_INLINE_HPP

View File

@ -674,7 +674,7 @@ static void *java_start(Thread *thread) {
int pid = os::current_process_id();
alloca(((pid ^ counter++) & 7) * 128);
ThreadLocalStorage::set_thread(thread);
thread->initialize_thread_current();
OSThread* osthread = thread->osthread();
Monitor* sync = osthread->startThread_lock();
@ -882,44 +882,6 @@ void os::free_thread(OSThread* osthread) {
delete osthread;
}
//////////////////////////////////////////////////////////////////////////////
// thread local storage
// Restore the thread pointer if the destructor is called. This is in case
// someone from JNI code sets up a destructor with pthread_key_create to run
// detachCurrentThread on thread death. Unless we restore the thread pointer we
// will hang or crash. When detachCurrentThread is called the key will be set
// to null and we will not be called again. If detachCurrentThread is never
// called we could loop forever depending on the pthread implementation.
static void restore_thread_pointer(void* p) {
Thread* thread = (Thread*) p;
os::thread_local_storage_at_put(ThreadLocalStorage::thread_index(), thread);
}
int os::allocate_thread_local_storage() {
pthread_key_t key;
int rslt = pthread_key_create(&key, restore_thread_pointer);
assert(rslt == 0, "cannot allocate thread local storage");
return (int)key;
}
// Note: This is currently not used by VM, as we don't destroy TLS key
// on VM exit.
void os::free_thread_local_storage(int index) {
int rslt = pthread_key_delete((pthread_key_t)index);
assert(rslt == 0, "invalid index");
}
void os::thread_local_storage_at_put(int index, void* value) {
int rslt = pthread_setspecific((pthread_key_t)index, value);
assert(rslt == 0, "pthread_setspecific failed");
}
extern "C" Thread* get_thread() {
return ThreadLocalStorage::thread();
}
////////////////////////////////////////////////////////////////////////////////
// time support

View File

@ -1,5 +1,5 @@
/*
* Copyright (c) 1999, 2014, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1999, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -34,10 +34,6 @@
#include <sys/poll.h>
#include <netdb.h>
inline void* os::thread_local_storage_at(int index) {
return pthread_getspecific((pthread_key_t)index);
}
// File names are case-sensitive on windows only
inline int os::file_name_strcmp(const char* s1, const char* s2) {
return strcmp(s1, s2);

View File

@ -1,39 +0,0 @@
/*
* Copyright (c) 2002, 2011, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#ifndef OS_BSD_VM_THREAD_BSD_INLINE_HPP
#define OS_BSD_VM_THREAD_BSD_INLINE_HPP
#ifndef SHARE_VM_RUNTIME_THREAD_INLINE_HPP_SCOPE
#error "This file should only be included from thread.inline.hpp"
#endif
#include "runtime/thread.hpp"
#include "runtime/threadLocalStorage.hpp"
// Contains inlined functions for class Thread and ThreadLocalStorage
inline void ThreadLocalStorage::pd_invalidate_all() {} // nothing to do
#endif // OS_BSD_VM_THREAD_BSD_INLINE_HPP

View File

@ -646,7 +646,7 @@ static void *java_start(Thread *thread) {
int pid = os::current_process_id();
alloca(((pid ^ counter++) & 7) * 128);
ThreadLocalStorage::set_thread(thread);
thread->initialize_thread_current();
OSThread* osthread = thread->osthread();
Monitor* sync = osthread->startThread_lock();
@ -873,43 +873,6 @@ void os::free_thread(OSThread* osthread) {
delete osthread;
}
//////////////////////////////////////////////////////////////////////////////
// thread local storage
// Restore the thread pointer if the destructor is called. This is in case
// someone from JNI code sets up a destructor with pthread_key_create to run
// detachCurrentThread on thread death. Unless we restore the thread pointer we
// will hang or crash. When detachCurrentThread is called the key will be set
// to null and we will not be called again. If detachCurrentThread is never
// called we could loop forever depending on the pthread implementation.
static void restore_thread_pointer(void* p) {
Thread* thread = (Thread*) p;
os::thread_local_storage_at_put(ThreadLocalStorage::thread_index(), thread);
}
int os::allocate_thread_local_storage() {
pthread_key_t key;
int rslt = pthread_key_create(&key, restore_thread_pointer);
assert(rslt == 0, "cannot allocate thread local storage");
return (int)key;
}
// Note: This is currently not used by VM, as we don't destroy TLS key
// on VM exit.
void os::free_thread_local_storage(int index) {
int rslt = pthread_key_delete((pthread_key_t)index);
assert(rslt == 0, "invalid index");
}
void os::thread_local_storage_at_put(int index, void* value) {
int rslt = pthread_setspecific((pthread_key_t)index, value);
assert(rslt == 0, "pthread_setspecific failed");
}
extern "C" Thread* get_thread() {
return ThreadLocalStorage::thread();
}
//////////////////////////////////////////////////////////////////////////////
// initial thread

View File

@ -1,5 +1,5 @@
/*
* Copyright (c) 1999, 2014, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1999, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -34,10 +34,6 @@
#include <sys/poll.h>
#include <netdb.h>
inline void* os::thread_local_storage_at(int index) {
return pthread_getspecific((pthread_key_t)index);
}
// File names are case-sensitive on windows only
inline int os::file_name_strcmp(const char* s1, const char* s2) {
return strcmp(s1, s2);

View File

@ -1,39 +0,0 @@
/*
* Copyright (c) 2002, 2011, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#ifndef OS_LINUX_VM_THREAD_LINUX_INLINE_HPP
#define OS_LINUX_VM_THREAD_LINUX_INLINE_HPP
#ifndef SHARE_VM_RUNTIME_THREAD_INLINE_HPP_SCOPE
#error "This file should only be included from thread.inline.hpp"
#endif
#include "runtime/thread.hpp"
#include "runtime/threadLocalStorage.hpp"
// Contains inlined functions for class Thread and ThreadLocalStorage
inline void ThreadLocalStorage::pd_invalidate_all() {} // nothing to do
#endif // OS_LINUX_VM_THREAD_LINUX_INLINE_HPP

View File

@ -0,0 +1,68 @@
/*
* Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#include "runtime/threadLocalStorage.hpp"
#include <pthread.h>
static pthread_key_t _thread_key;
static bool _initialized = false;
// Restore the thread pointer if the destructor is called. This is in case
// someone from JNI code sets up a destructor with pthread_key_create to run
// detachCurrentThread on thread death. Unless we restore the thread pointer we
// will hang or crash. When detachCurrentThread is called the key will be set
// to null and we will not be called again. If detachCurrentThread is never
// called we could loop forever depending on the pthread implementation.
extern "C" void restore_thread_pointer(void* p) {
ThreadLocalStorage::set_thread((Thread*) p);
}
void ThreadLocalStorage::init() {
assert(!_initialized, "initializing TLS more than once!");
int rslt = pthread_key_create(&_thread_key, restore_thread_pointer);
// If this assert fails we will get a recursive assertion failure
// and not see the actual error message or get a hs_err file
assert_status(rslt == 0, rslt, "pthread_key_create");
_initialized = true;
}
bool ThreadLocalStorage::is_initialized() {
return _initialized;
}
Thread* ThreadLocalStorage::thread() {
// If this assert fails we will get a recursive assertion failure
// and not see the actual error message or get a hs_err file.
// Which most likely indicates we have taken an error path early in
// the initialization process, which is using Thread::current without
// checking TLS is initialized - see java.cpp vm_exit
assert(_initialized, "TLS not initialized yet!");
return (Thread*) pthread_getspecific(_thread_key); // may be NULL
}
void ThreadLocalStorage::set_thread(Thread* current) {
assert(_initialized, "TLS not initialized yet!");
int rslt = pthread_setspecific(_thread_key, current);
assert_status(rslt == 0, rslt, "pthread_setspecific");
}

View File

@ -728,6 +728,9 @@ extern "C" void* java_start(void* thread_addr) {
int prio;
Thread* thread = (Thread*)thread_addr;
thread->initialize_thread_current();
OSThread* osthr = thread->osthread();
osthr->set_lwp_id(_lwp_self()); // Store lwp in case we are bound
@ -5579,7 +5582,7 @@ int os::fork_and_exec(char* cmd) {
// fork is async-safe, fork1 is not so can't use in signal handler
pid_t pid;
Thread* t = ThreadLocalStorage::get_thread_slow();
Thread* t = Thread::current_or_null_safe();
if (t != NULL && t->is_inside_signal_handler()) {
pid = fork();
} else {

View File

@ -1,50 +0,0 @@
/*
* Copyright (c) 2002, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#ifndef OS_SOLARIS_VM_THREAD_SOLARIS_INLINE_HPP
#define OS_SOLARIS_VM_THREAD_SOLARIS_INLINE_HPP
#ifndef SHARE_VM_RUNTIME_THREAD_INLINE_HPP_SCOPE
#error "This file should only be included from thread.inline.hpp"
#endif
#include "runtime/thread.hpp"
#include "runtime/threadLocalStorage.hpp"
// Thread::current is "hot" it's called > 128K times in the 1st 500 msecs of
// startup.
// ThreadLocalStorage::thread is warm -- it's called > 16K times in the same
// period. Thread::current() now calls ThreadLocalStorage::thread() directly.
// For SPARC, to avoid excessive register window spill-fill faults,
// we aggressively inline these routines.
inline void ThreadLocalStorage::set_thread(Thread* thread) {
_thr_current = thread;
}
inline Thread* ThreadLocalStorage::thread() {
return _thr_current;
}
#endif // OS_SOLARIS_VM_THREAD_SOLARIS_INLINE_HPP

View File

@ -419,6 +419,8 @@ static unsigned __stdcall java_start(Thread* thread) {
int pid = os::current_process_id();
_alloca(((pid ^ counter++) & 7) * 128);
thread->initialize_thread_current();
OSThread* osthr = thread->osthread();
assert(osthr->get_state() == RUNNABLE, "invalid os thread state");
@ -2146,7 +2148,7 @@ int os::signal_wait() {
LONG Handle_Exception(struct _EXCEPTION_POINTERS* exceptionInfo,
address handler) {
JavaThread* thread = JavaThread::current();
JavaThread* thread = (JavaThread*) Thread::current_or_null();
// Save pc in thread
#ifdef _M_IA64
// Do not blow up if no thread info available.
@ -2384,7 +2386,7 @@ LONG WINAPI topLevelExceptionFilter(struct _EXCEPTION_POINTERS* exceptionInfo) {
address pc = (address) exceptionInfo->ContextRecord->Eip;
#endif
#endif
Thread* t = ThreadLocalStorage::get_thread_slow(); // slow & steady
Thread* t = Thread::current_or_null_safe();
// Handle SafeFetch32 and SafeFetchN exceptions.
if (StubRoutines::is_safefetch_fault(pc)) {
@ -4011,27 +4013,6 @@ bool os::message_box(const char* title, const char* message) {
return result == IDYES;
}
int os::allocate_thread_local_storage() {
return TlsAlloc();
}
void os::free_thread_local_storage(int index) {
TlsFree(index);
}
void os::thread_local_storage_at_put(int index, void* value) {
TlsSetValue(index, value);
assert(thread_local_storage_at(index) == value, "Just checking");
}
void* os::thread_local_storage_at(int index) {
return TlsGetValue(index);
}
#ifndef PRODUCT
#ifndef _WIN64
// Helpers to check whether NX protection is enabled
@ -4079,6 +4060,9 @@ void os::init(void) {
fatal("DuplicateHandle failed\n");
}
main_thread_id = (int) GetCurrentThreadId();
// initialize fast thread access - only used for 32-bit
win32::initialize_thread_ptr_offset();
}
// To install functions for atexit processing
@ -5177,9 +5161,7 @@ void Parker::park(bool isAbsolute, jlong time) {
}
}
JavaThread* thread = (JavaThread*)(Thread::current());
assert(thread->is_Java_thread(), "Must be JavaThread");
JavaThread *jt = (JavaThread *)thread;
JavaThread* thread = JavaThread::current();
// Don't wait if interrupted or already triggered
if (Thread::is_interrupted(thread, false) ||
@ -5187,16 +5169,16 @@ void Parker::park(bool isAbsolute, jlong time) {
ResetEvent(_ParkEvent);
return;
} else {
ThreadBlockInVM tbivm(jt);
ThreadBlockInVM tbivm(thread);
OSThreadWaitState osts(thread->osthread(), false /* not Object.wait() */);
jt->set_suspend_equivalent();
thread->set_suspend_equivalent();
WaitForSingleObject(_ParkEvent, time);
ResetEvent(_ParkEvent);
// If externally suspended while waiting, re-suspend
if (jt->handle_special_suspend_equivalent_condition()) {
jt->java_suspend_self();
if (thread->handle_special_suspend_equivalent_condition()) {
thread->java_suspend_self();
}
}
}
@ -5299,7 +5281,7 @@ LONG WINAPI os::win32::serialize_fault_filter(struct _EXCEPTION_POINTERS* e) {
DWORD exception_code = e->ExceptionRecord->ExceptionCode;
if (exception_code == EXCEPTION_ACCESS_VIOLATION) {
JavaThread* thread = (JavaThread*)ThreadLocalStorage::get_thread_slow();
JavaThread* thread = JavaThread::current();
PEXCEPTION_RECORD exceptionRecord = e->ExceptionRecord;
address addr = (address) exceptionRecord->ExceptionInformation[1];
@ -6066,3 +6048,15 @@ int os::get_signal_number(const char* name) {
return -1;
}
// Fast current thread access
int os::win32::_thread_ptr_offset = 0;
static void call_wrapper_dummy() {}
// We need to call the os_exception_wrapper once so that it sets
// up the offset from FS of the thread pointer.
void os::win32::initialize_thread_ptr_offset() {
os::os_exception_wrapper((java_call_t)call_wrapper_dummy,
NULL, NULL, NULL, NULL);
}

View File

@ -117,6 +117,17 @@ class win32 {
// filter function to ignore faults on serializations page
static LONG WINAPI serialize_fault_filter(struct _EXCEPTION_POINTERS* e);
// Fast access to current thread
protected:
static int _thread_ptr_offset;
private:
static void initialize_thread_ptr_offset();
public:
static inline void set_thread_ptr_offset(int offset) {
_thread_ptr_offset = offset;
}
static inline int get_thread_ptr_offset() { return _thread_ptr_offset; }
};
/*

View File

@ -0,0 +1,63 @@
/*
* Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#include "precompiled.hpp"
#include "runtime/threadLocalStorage.hpp"
#include <windows.h>
static DWORD _thread_key;
static bool _initialized = false;
void ThreadLocalStorage::init() {
assert(!_initialized, "initializing TLS more than once!");
_thread_key = TlsAlloc();
// If this assert fails we will get a recursive assertion failure
// and not see the actual error message or get a hs_err file
assert(_thread_key != TLS_OUT_OF_INDEXES, "TlsAlloc failed: out of indices");
_initialized = true;
}
bool ThreadLocalStorage::is_initialized() {
return _initialized;
}
Thread* ThreadLocalStorage::thread() {
// If this assert fails we will get a recursive assertion failure
// and not see the actual error message or get a hs_err file.
// Which most likely indicates we have taken an error path early in
// the initialization process, which is using Thread::current without
// checking TLS is initialized - see java.cpp vm_exit
assert(_initialized, "TLS not initialized yet!");
Thread* current = (Thread*) TlsGetValue(_thread_key);
assert(current != 0 || GetLastError() == ERROR_SUCCESS,
"TlsGetValue failed with error code: %lu", GetLastError());
return current;
}
void ThreadLocalStorage::set_thread(Thread* current) {
assert(_initialized, "TLS not initialized yet!");
BOOL res = TlsSetValue(_thread_key, current);
assert(res, "TlsSetValue failed with error code: %lu", GetLastError());
}

View File

@ -1,39 +0,0 @@
/*
* Copyright (c) 2002, 2010, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#ifndef OS_WINDOWS_VM_THREAD_WINDOWS_INLINE_HPP
#define OS_WINDOWS_VM_THREAD_WINDOWS_INLINE_HPP
#ifndef SHARE_VM_RUNTIME_THREAD_INLINE_HPP_SCOPE
#error "This file should only be included from thread.inline.hpp"
#endif
#include "runtime/thread.hpp"
#include "runtime/threadLocalStorage.hpp"
// Contains inlined functions for class Thread and ThreadLocalStorage
inline void ThreadLocalStorage::pd_invalidate_all() { return; }
#endif // OS_WINDOWS_VM_THREAD_WINDOWS_INLINE_HPP

View File

@ -167,7 +167,7 @@ JVM_handle_aix_signal(int sig, siginfo_t* info, void* ucVoid, int abort_if_unrec
ucontext_t* uc = (ucontext_t*) ucVoid;
Thread* t = ThreadLocalStorage::get_thread_slow(); // slow & steady
Thread* t = Thread::current_or_null_safe();
SignalHandlerMark shm(t);

View File

@ -1,40 +0,0 @@
/*
* Copyright (c) 1997, 2013, Oracle and/or its affiliates. All rights reserved.
* Copyright 2012, 2014 SAP AG. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#include "precompiled.hpp"
#include "runtime/threadLocalStorage.hpp"
#include "runtime/thread.hpp"
void ThreadLocalStorage::generate_code_for_get_thread() {
// Nothing we can do here for user-level thread.
}
void ThreadLocalStorage::pd_init() {
// Nothing to do.
}
void ThreadLocalStorage::pd_set_thread(Thread* thread) {
os::thread_local_storage_at_put(ThreadLocalStorage::thread_index(), thread);
}

View File

@ -1,36 +0,0 @@
/*
* Copyright (c) 2000, 2013, Oracle and/or its affiliates. All rights reserved.
* Copyright 2012, 2013 SAP AG. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#ifndef OS_CPU_AIX_PPC_VM_THREADLS_AIX_PPC_HPP
#define OS_CPU_AIX_PPC_VM_THREADLS_AIX_PPC_HPP
// Processor dependent parts of ThreadLocalStorage
public:
static Thread* thread() {
return (Thread *) os::thread_local_storage_at(thread_index());
}
#endif // OS_CPU_AIX_PPC_VM_THREADLS_AIX_PPC_HPP

View File

@ -1,5 +1,5 @@
/*
* Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1999, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -26,62 +26,7 @@
#include "asm/macroAssembler.hpp"
#include "asm/macroAssembler.inline.hpp"
#include "runtime/os.hpp"
#include "runtime/threadLocalStorage.hpp"
#ifndef _LP64
void MacroAssembler::int3() {
call(RuntimeAddress(CAST_FROM_FN_PTR(address, os::breakpoint)));
}
void MacroAssembler::get_thread(Register thread) {
movl(thread, rsp);
shrl(thread, PAGE_SHIFT);
ExternalAddress tls_base((address)ThreadLocalStorage::sp_map_addr());
Address index(noreg, thread, Address::times_4);
ArrayAddress tls(tls_base, index);
movptr(thread, tls);
}
#else
void MacroAssembler::int3() {
call(RuntimeAddress(CAST_FROM_FN_PTR(address, os::breakpoint)));
}
void MacroAssembler::get_thread(Register thread) {
// call pthread_getspecific
// void * pthread_getspecific(pthread_key_t key);
if (thread != rax) {
push(rax);
}
push(rdi);
push(rsi);
push(rdx);
push(rcx);
push(r8);
push(r9);
push(r10);
// XXX
mov(r10, rsp);
andq(rsp, -16);
push(r10);
push(r11);
movl(rdi, ThreadLocalStorage::thread_index());
call(RuntimeAddress(CAST_FROM_FN_PTR(address, pthread_getspecific)));
pop(r11);
pop(rsp);
pop(r10);
pop(r9);
pop(r8);
pop(rcx);
pop(rdx);
pop(rsi);
pop(rdi);
if (thread != rax) {
mov(thread, rax);
pop(rax);
}
}
#endif

View File

@ -405,7 +405,7 @@ JVM_handle_bsd_signal(int sig,
int abort_if_unrecognized) {
ucontext_t* uc = (ucontext_t*) ucVoid;
Thread* t = ThreadLocalStorage::get_thread_slow();
Thread* t = Thread::current_or_null_safe();
// Must do this before SignalHandlerMark, if crash protection installed we will longjmp away
// (no destructors can be run)

View File

@ -1,92 +0,0 @@
/*
* Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#include "precompiled.hpp"
#include "runtime/thread.inline.hpp"
#include "runtime/threadLocalStorage.hpp"
// Map stack pointer (%esp) to thread pointer for faster TLS access
//
// Here we use a flat table for better performance. Getting current thread
// is down to one memory access (read _sp_map[%esp>>12]) in generated code
// and two in runtime code (-fPIC code needs an extra load for _sp_map).
//
// This code assumes stack page is not shared by different threads. It works
// in 32-bit VM when page size is 4K (or a multiple of 4K, if that matters).
//
// Notice that _sp_map is allocated in the bss segment, which is ZFOD
// (zero-fill-on-demand). While it reserves 4M address space upfront,
// actual memory pages are committed on demand.
//
// If an application creates and destroys a lot of threads, usually the
// stack space freed by a thread will soon get reused by new thread
// (this is especially true in NPTL or BsdThreads in fixed-stack mode).
// No memory page in _sp_map is wasted.
//
// However, it's still possible that we might end up populating &
// committing a large fraction of the 4M table over time, but the actual
// amount of live data in the table could be quite small. The max wastage
// is less than 4M bytes. If it becomes an issue, we could use madvise()
// with MADV_DONTNEED to reclaim unused (i.e. all-zero) pages in _sp_map.
// MADV_DONTNEED on Bsd keeps the virtual memory mapping, but zaps the
// physical memory page (i.e. similar to MADV_FREE on Solaris).
#ifndef AMD64
Thread* ThreadLocalStorage::_sp_map[1UL << (SP_BITLENGTH - PAGE_SHIFT)];
#endif // !AMD64
void ThreadLocalStorage::generate_code_for_get_thread() {
// nothing we can do here for user-level thread
}
void ThreadLocalStorage::pd_init() {
#ifndef AMD64
assert(align_size_down(os::vm_page_size(), PAGE_SIZE) == os::vm_page_size(),
"page size must be multiple of PAGE_SIZE");
#endif // !AMD64
}
void ThreadLocalStorage::pd_set_thread(Thread* thread) {
os::thread_local_storage_at_put(ThreadLocalStorage::thread_index(), thread);
#ifndef AMD64
address stack_top = os::current_stack_base();
size_t stack_size = os::current_stack_size();
for (address p = stack_top - stack_size; p < stack_top; p += PAGE_SIZE) {
// pd_set_thread() is called with non-NULL value when a new thread is
// created/attached, or with NULL value when a thread is about to exit.
// If both "thread" and the corresponding _sp_map[] entry are non-NULL,
// they should have the same value. Otherwise it might indicate that the
// stack page is shared by multiple threads. However, a more likely cause
// for this assertion to fail is that an attached thread exited without
// detaching itself from VM, which is a program error and could cause VM
// to crash.
assert(thread == NULL || _sp_map[(uintptr_t)p >> PAGE_SHIFT] == NULL ||
thread == _sp_map[(uintptr_t)p >> PAGE_SHIFT],
"thread exited without detaching from VM??");
_sp_map[(uintptr_t)p >> PAGE_SHIFT] = thread;
}
#endif // !AMD64
}

View File

@ -1,56 +0,0 @@
/*
* Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#ifndef OS_CPU_BSD_X86_VM_THREADLS_BSD_X86_HPP
#define OS_CPU_BSD_X86_VM_THREADLS_BSD_X86_HPP
// Processor dependent parts of ThreadLocalStorage
#ifndef AMD64
// map stack pointer to thread pointer - see notes in threadLS_bsd_x86.cpp
#define SP_BITLENGTH 32
#ifndef PAGE_SHIFT
#define PAGE_SHIFT 12
#define PAGE_SIZE (1UL << PAGE_SHIFT)
#endif
static Thread* _sp_map[1UL << (SP_BITLENGTH - PAGE_SHIFT)];
#endif // !AMD64
public:
#ifndef AMD64
static Thread** sp_map_addr() { return _sp_map; }
#endif // !AMD64
static Thread* thread() {
#ifdef AMD64
return (Thread*) os::thread_local_storage_at(thread_index());
#else
uintptr_t sp;
__asm__ volatile ("movl %%esp, %0" : "=r" (sp));
return _sp_map[sp >> PAGE_SHIFT];
#endif // AMD64
}
#endif // OS_CPU_BSD_X86_VM_THREADLS_BSD_X86_HPP

View File

@ -1,5 +1,5 @@
/*
* Copyright (c) 1997, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1997, 2015, Oracle and/or its affiliates. All rights reserved.
* Copyright 2009 Red Hat, Inc.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
@ -23,10 +23,4 @@
*
*/
#include "precompiled.hpp"
#include "asm/assembler.hpp"
#include "assembler_zero.inline.hpp"
#include "runtime/os.hpp"
#include "runtime/threadLocalStorage.hpp"
// This file is intentionally empty

View File

@ -134,7 +134,7 @@ JVM_handle_bsd_signal(int sig,
int abort_if_unrecognized) {
ucontext_t* uc = (ucontext_t*) ucVoid;
Thread* t = ThreadLocalStorage::get_thread_slow();
Thread* t = Thread::current_or_null_safe();
SignalHandlerMark shm(t);

View File

@ -1,40 +0,0 @@
/*
* Copyright (c) 2003, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright 2007 Red Hat, Inc.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#include "precompiled.hpp"
#include "runtime/thread.inline.hpp"
#include "runtime/threadLocalStorage.hpp"
void ThreadLocalStorage::generate_code_for_get_thread() {
// nothing to do
}
void ThreadLocalStorage::pd_init() {
// nothing to do
}
void ThreadLocalStorage::pd_set_thread(Thread* thread) {
os::thread_local_storage_at_put(ThreadLocalStorage::thread_index(), thread);
}

View File

@ -1,35 +0,0 @@
/*
* Copyright (c) 2003, 2010, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#ifndef OS_CPU_BSD_ZERO_VM_THREADLS_BSD_ZERO_HPP
#define OS_CPU_BSD_ZERO_VM_THREADLS_BSD_ZERO_HPP
// Processor dependent parts of ThreadLocalStorage
public:
static Thread* thread() {
return (Thread*) os::thread_local_storage_at(thread_index());
}
#endif // OS_CPU_BSD_ZERO_VM_THREADLS_BSD_ZERO_HPP

View File

@ -1,5 +1,5 @@
/*
* Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1999, 2015, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2014, Red Hat Inc. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
@ -23,32 +23,6 @@
*
*/
#include "precompiled.hpp"
#include "asm/macroAssembler.hpp"
#include "asm/macroAssembler.inline.hpp"
#include "runtime/os.hpp"
#include "runtime/threadLocalStorage.hpp"
// nothing required here
// get_thread can be called anywhere inside generated code so we need
// to save whatever non-callee save context might get clobbered by the
// call to the C thread_local lookup call or, indeed, the call setup
// code. x86 appears to save C arg registers.
void MacroAssembler::get_thread(Register dst) {
// call pthread_getspecific
// void * pthread_getspecific(pthread_key_t key);
// Save all call-clobbered regs except dst, plus r19 and r20.
RegSet saved_regs = RegSet::range(r0, r20) + lr - dst;
push(saved_regs, sp);
mov(c_rarg0, ThreadLocalStorage::thread_index());
mov(r19, CAST_FROM_FN_PTR(address, pthread_getspecific));
blrt(r19, 1, 0, 1);
if (dst != c_rarg0) {
mov(dst, c_rarg0);
}
// restore pushed registers
pop(saved_regs, sp);
}

View File

@ -249,7 +249,7 @@ JVM_handle_linux_signal(int sig,
int abort_if_unrecognized) {
ucontext_t* uc = (ucontext_t*) ucVoid;
Thread* t = ThreadLocalStorage::get_thread_slow();
Thread* t = Thread::current_or_null_safe();
// Must do this before SignalHandlerMark, if crash protection installed we will longjmp away
// (no destructors can be run)

View File

@ -1,42 +0,0 @@
/*
* Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2014, Red Hat Inc. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#include "precompiled.hpp"
#include "runtime/threadLocalStorage.hpp"
#include "runtime/thread.inline.hpp"
void ThreadLocalStorage::generate_code_for_get_thread() {
// nothing we can do here for user-level thread
}
void ThreadLocalStorage::pd_init() {
}
__thread Thread *aarch64_currentThread;
void ThreadLocalStorage::pd_set_thread(Thread* thread) {
os::thread_local_storage_at_put(ThreadLocalStorage::thread_index(), thread);
aarch64_currentThread = thread;
}

View File

@ -1,37 +0,0 @@
/*
* Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2014, Red Hat Inc. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#ifndef OS_CPU_LINUX_AARCH64_VM_THREADLS_LINUX_AARCH64_HPP
#define OS_CPU_LINUX_AARCH64_VM_THREADLS_LINUX_AARCH64_HPP
// Processor dependent parts of ThreadLocalStorage
public:
static Thread *thread() {
return aarch64_currentThread;
}
#endif // OS_CPU_LINUX_AARCH64_VM_THREADLS_LINUX_AARCH64_HPP

View File

@ -0,0 +1,44 @@
// Copyright (c) 2015, Red Hat Inc. All rights reserved.
// DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
//
// This code is free software; you can redistribute it and/or modify it
// under the terms of the GNU General Public License version 2 only, as
// published by the Free Software Foundation.
//
// This code is distributed in the hope that it will be useful, but WITHOUT
// ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
// FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
// version 2 for more details (a copy is included in the LICENSE file that
// accompanied this code).
//
// You should have received a copy of the GNU General Public License version
// 2 along with this work; if not, write to the Free Software Foundation,
// Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
//
// Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
// or visit www.oracle.com if you need additional information or have any
// questions.
// JavaThread::aarch64_get_thread_helper()
//
// Return the current thread pointer in x0.
// Clobber x1, flags.
// All other registers are preserved,
.global _ZN10JavaThread25aarch64_get_thread_helperEv
.type _ZN10JavaThread25aarch64_get_thread_helperEv, %function
_ZN10JavaThread25aarch64_get_thread_helperEv:
stp x29, x30, [sp, -16]!
adrp x0, :tlsdesc:_ZN6Thread12_thr_currentE
ldr x1, [x0, #:tlsdesc_lo12:_ZN6Thread12_thr_currentE]
add x0, x0, :tlsdesc_lo12:_ZN6Thread12_thr_currentE
.tlsdesccall _ZN6Thread12_thr_currentE
blr x1
mrs x1, tpidr_el0
add x0, x1, x0
ldr x0, [x0]
ldp x29, x30, [sp], 16
ret
.size _ZN10JavaThread25aarch64_get_thread_helperEv, .-_ZN10JavaThread25aarch64_get_thread_helperEv

View File

@ -1,5 +1,5 @@
/*
* Copyright (c) 2000, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2014, Red Hat Inc. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
@ -77,6 +77,8 @@ private:
bool pd_get_top_frame(frame* fr_addr, void* ucontext, bool isInJava);
public:
static Thread *aarch64_get_thread_helper();
// These routines are only used on cpu architectures that
// have separate register stacks (Itanium).
static bool register_stack_overflow() { return false; }

View File

@ -182,7 +182,7 @@ JVM_handle_linux_signal(int sig,
int abort_if_unrecognized) {
ucontext_t* uc = (ucontext_t*) ucVoid;
Thread* t = ThreadLocalStorage::get_thread_slow();
Thread* t = Thread::current_or_null_safe();
SignalHandlerMark shm(t);

View File

@ -1,39 +0,0 @@
/*
* Copyright (c) 1997, 2013, Oracle and/or its affiliates. All rights reserved.
* Copyright 2012, 2013 SAP AG. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#include "precompiled.hpp"
#include "runtime/threadLocalStorage.hpp"
void ThreadLocalStorage::generate_code_for_get_thread() {
// nothing we can do here for user-level thread
}
void ThreadLocalStorage::pd_init() {
// Nothing to do
}
void ThreadLocalStorage::pd_set_thread(Thread* thread) {
os::thread_local_storage_at_put(ThreadLocalStorage::thread_index(), thread);
}

View File

@ -1,36 +0,0 @@
/*
* Copyright (c) 2000, 2013, Oracle and/or its affiliates. All rights reserved.
* Copyright 2012, 2013 SAP AG. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#ifndef OS_CPU_LINUX_PPC_VM_THREADLS_LINUX_PPC_HPP
#define OS_CPU_LINUX_PPC_VM_THREADLS_LINUX_PPC_HPP
// Processor dependent parts of ThreadLocalStorage
public:
static Thread* thread() {
return (Thread *) os::thread_local_storage_at(thread_index());
}
#endif // OS_CPU_LINUX_PPC_VM_THREADLS_LINUX_PPC_HPP

View File

@ -541,7 +541,7 @@ JVM_handle_linux_signal(int sig,
ucontext_t* ucFake = (ucontext_t*) ucVoid;
sigcontext* uc = (sigcontext*)ucVoid;
Thread* t = ThreadLocalStorage::get_thread_slow();
Thread* t = Thread::current_or_null_safe();
// Must do this before SignalHandlerMark, if crash protection installed we will longjmp away
// (no destructors can be run)

View File

@ -1,38 +0,0 @@
/*
* Copyright (c) 1998, 2010, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#include "precompiled.hpp"
#include "runtime/thread.inline.hpp"
#include "runtime/threadLocalStorage.hpp"
void ThreadLocalStorage::generate_code_for_get_thread() {
}
void ThreadLocalStorage::pd_init() {
// Nothing to do
}
void ThreadLocalStorage::pd_set_thread(Thread* thread) {
os::thread_local_storage_at_put(ThreadLocalStorage::thread_index(), thread);
}

View File

@ -1,33 +0,0 @@
/*
* Copyright (c) 1998, 2010, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#ifndef OS_CPU_LINUX_SPARC_VM_THREADLS_LINUX_SPARC_HPP
#define OS_CPU_LINUX_SPARC_VM_THREADLS_LINUX_SPARC_HPP
public:
static Thread* thread() {
return (Thread*) os::thread_local_storage_at(thread_index());
}
#endif // OS_CPU_LINUX_SPARC_VM_THREADLS_LINUX_SPARC_HPP

View File

@ -1,5 +1,5 @@
/*
* Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1999, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -26,85 +26,7 @@
#include "asm/macroAssembler.hpp"
#include "asm/macroAssembler.inline.hpp"
#include "runtime/os.hpp"
#include "runtime/threadLocalStorage.hpp"
#ifndef _LP64
void MacroAssembler::int3() {
call(RuntimeAddress(CAST_FROM_FN_PTR(address, os::breakpoint)));
}
#ifdef MINIMIZE_RAM_USAGE
void MacroAssembler::get_thread(Register thread) {
// call pthread_getspecific
// void * pthread_getspecific(pthread_key_t key);
if (thread != rax) push(rax);
push(rcx);
push(rdx);
push(ThreadLocalStorage::thread_index());
call(RuntimeAddress(CAST_FROM_FN_PTR(address, pthread_getspecific)));
increment(rsp, wordSize);
pop(rdx);
pop(rcx);
if (thread != rax) {
mov(thread, rax);
pop(rax);
}
}
#else
void MacroAssembler::get_thread(Register thread) {
movl(thread, rsp);
shrl(thread, PAGE_SHIFT);
ExternalAddress tls_base((address)ThreadLocalStorage::sp_map_addr());
Address index(noreg, thread, Address::times_4);
ArrayAddress tls(tls_base, index);
movptr(thread, tls);
}
#endif // MINIMIZE_RAM_USAGE
#else
void MacroAssembler::int3() {
call(RuntimeAddress(CAST_FROM_FN_PTR(address, os::breakpoint)));
}
void MacroAssembler::get_thread(Register thread) {
// call pthread_getspecific
// void * pthread_getspecific(pthread_key_t key);
if (thread != rax) {
push(rax);
}
push(rdi);
push(rsi);
push(rdx);
push(rcx);
push(r8);
push(r9);
push(r10);
// XXX
mov(r10, rsp);
andq(rsp, -16);
push(r10);
push(r11);
movl(rdi, ThreadLocalStorage::thread_index());
call(RuntimeAddress(CAST_FROM_FN_PTR(address, pthread_getspecific)));
pop(r11);
pop(rsp);
pop(r10);
pop(r9);
pop(r8);
pop(rcx);
pop(rdx);
pop(rsi);
pop(rdi);
if (thread != rax) {
mov(thread, rax);
pop(rax);
}
}
#endif

View File

@ -221,7 +221,7 @@ JVM_handle_linux_signal(int sig,
int abort_if_unrecognized) {
ucontext_t* uc = (ucontext_t*) ucVoid;
Thread* t = ThreadLocalStorage::get_thread_slow();
Thread* t = Thread::current_or_null_safe();
// Must do this before SignalHandlerMark, if crash protection installed we will longjmp away
// (no destructors can be run)

View File

@ -1,98 +0,0 @@
/*
* Copyright (c) 1999, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#include "precompiled.hpp"
#include "runtime/thread.inline.hpp"
#include "runtime/threadLocalStorage.hpp"
// Map stack pointer (%esp) to thread pointer for faster TLS access
//
// Here we use a flat table for better performance. Getting current thread
// is down to one memory access (read _sp_map[%esp>>12]) in generated code
// and two in runtime code (-fPIC code needs an extra load for _sp_map).
//
// This code assumes stack page is not shared by different threads. It works
// in 32-bit VM when page size is 4K (or a multiple of 4K, if that matters).
//
// Notice that _sp_map is allocated in the bss segment, which is ZFOD
// (zero-fill-on-demand). While it reserves 4M address space upfront,
// actual memory pages are committed on demand.
//
// If an application creates and destroys a lot of threads, usually the
// stack space freed by a thread will soon get reused by new thread.
// No memory page in _sp_map is wasted.
//
// However, it's still possible that we might end up populating &
// committing a large fraction of the 4M table over time, but the actual
// amount of live data in the table could be quite small. The max wastage
// is less than 4M bytes. If it becomes an issue, we could use madvise()
// with MADV_DONTNEED to reclaim unused (i.e. all-zero) pages in _sp_map.
// MADV_DONTNEED on Linux keeps the virtual memory mapping, but zaps the
// physical memory page (i.e. similar to MADV_FREE on Solaris).
#if !defined(AMD64) && !defined(MINIMIZE_RAM_USAGE)
Thread* ThreadLocalStorage::_sp_map[1UL << (SP_BITLENGTH - PAGE_SHIFT)];
void ThreadLocalStorage::generate_code_for_get_thread() {
// nothing we can do here for user-level thread
}
void ThreadLocalStorage::pd_init() {
assert(align_size_down(os::vm_page_size(), PAGE_SIZE) == os::vm_page_size(),
"page size must be multiple of PAGE_SIZE");
}
void ThreadLocalStorage::pd_set_thread(Thread* thread) {
os::thread_local_storage_at_put(ThreadLocalStorage::thread_index(), thread);
address stack_top = os::current_stack_base();
size_t stack_size = os::current_stack_size();
for (address p = stack_top - stack_size; p < stack_top; p += PAGE_SIZE) {
// pd_set_thread() is called with non-NULL value when a new thread is
// created/attached, or with NULL value when a thread is about to exit.
// If both "thread" and the corresponding _sp_map[] entry are non-NULL,
// they should have the same value. Otherwise it might indicate that the
// stack page is shared by multiple threads. However, a more likely cause
// for this assertion to fail is that an attached thread exited without
// detaching itself from VM, which is a program error and could cause VM
// to crash.
assert(thread == NULL || _sp_map[(uintptr_t)p >> PAGE_SHIFT] == NULL ||
thread == _sp_map[(uintptr_t)p >> PAGE_SHIFT],
"thread exited without detaching from VM??");
_sp_map[(uintptr_t)p >> PAGE_SHIFT] = thread;
}
}
#else
void ThreadLocalStorage::generate_code_for_get_thread() {
// nothing we can do here for user-level thread
}
void ThreadLocalStorage::pd_init() {
}
void ThreadLocalStorage::pd_set_thread(Thread* thread) {
os::thread_local_storage_at_put(ThreadLocalStorage::thread_index(), thread);
}
#endif // !AMD64 && !MINIMIZE_RAM_USAGE

View File

@ -1,58 +0,0 @@
/*
* Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#ifndef OS_CPU_LINUX_X86_VM_THREADLS_LINUX_X86_HPP
#define OS_CPU_LINUX_X86_VM_THREADLS_LINUX_X86_HPP
// Processor dependent parts of ThreadLocalStorage
#if !defined(AMD64) && !defined(MINIMIZE_RAM_USAGE)
// map stack pointer to thread pointer - see notes in threadLS_linux_x86.cpp
#define SP_BITLENGTH 32
#define PAGE_SHIFT 12
#define PAGE_SIZE (1UL << PAGE_SHIFT)
static Thread* _sp_map[1UL << (SP_BITLENGTH - PAGE_SHIFT)];
public:
static Thread** sp_map_addr() { return _sp_map; }
static Thread* thread() {
uintptr_t sp;
__asm__ volatile ("movl %%esp, %0" : "=r" (sp));
return _sp_map[sp >> PAGE_SHIFT];
}
#else
public:
static Thread* thread() {
return (Thread*) os::thread_local_storage_at(thread_index());
}
#endif // AMD64 || MINIMIZE_RAM_USAGE
#endif // OS_CPU_LINUX_X86_VM_THREADLS_LINUX_X86_HPP

View File

@ -1,5 +1,5 @@
/*
* Copyright (c) 1997, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1997, 2015, Oracle and/or its affiliates. All rights reserved.
* Copyright 2009 Red Hat, Inc.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
@ -23,10 +23,4 @@
*
*/
#include "precompiled.hpp"
#include "asm/assembler.hpp"
#include "assembler_zero.inline.hpp"
#include "runtime/os.hpp"
#include "runtime/threadLocalStorage.hpp"
// This file is intentionally empty

View File

@ -125,7 +125,7 @@ JVM_handle_linux_signal(int sig,
int abort_if_unrecognized) {
ucontext_t* uc = (ucontext_t*) ucVoid;
Thread* t = ThreadLocalStorage::get_thread_slow();
Thread* t = Thread::current_or_null_safe();
SignalHandlerMark shm(t);

View File

@ -1,40 +0,0 @@
/*
* Copyright (c) 2003, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright 2007 Red Hat, Inc.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#include "precompiled.hpp"
#include "runtime/thread.inline.hpp"
#include "runtime/threadLocalStorage.hpp"
void ThreadLocalStorage::generate_code_for_get_thread() {
// nothing to do
}
void ThreadLocalStorage::pd_init() {
// nothing to do
}
void ThreadLocalStorage::pd_set_thread(Thread* thread) {
os::thread_local_storage_at_put(ThreadLocalStorage::thread_index(), thread);
}

View File

@ -1,35 +0,0 @@
/*
* Copyright (c) 2003, 2010, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#ifndef OS_CPU_LINUX_ZERO_VM_THREADLS_LINUX_ZERO_HPP
#define OS_CPU_LINUX_ZERO_VM_THREADLS_LINUX_ZERO_HPP
// Processor dependent parts of ThreadLocalStorage
public:
static Thread* thread() {
return (Thread*) os::thread_local_storage_at(thread_index());
}
#endif // OS_CPU_LINUX_ZERO_VM_THREADLS_LINUX_ZERO_HPP

View File

@ -290,7 +290,7 @@ JVM_handle_solaris_signal(int sig, siginfo_t* info, void* ucVoid,
int abort_if_unrecognized) {
ucontext_t* uc = (ucontext_t*) ucVoid;
Thread* t = ThreadLocalStorage::get_thread_slow();
Thread* t = Thread::current_or_null_safe();
// Must do this before SignalHandlerMark, if crash protection installed we will longjmp away
// (no destructors can be run)

View File

@ -1,52 +0,0 @@
/*
* Copyright (c) 1998, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#include "precompiled.hpp"
#include "runtime/thread.inline.hpp"
#include "runtime/threadLocalStorage.hpp"
// True thread-local variable
__thread Thread * ThreadLocalStorage::_thr_current = NULL;
// Implementations needed to support the shared API
void ThreadLocalStorage::pd_invalidate_all() {} // nothing to do
bool ThreadLocalStorage::_initialized = false;
void ThreadLocalStorage::init() {
_initialized = true;
}
bool ThreadLocalStorage::is_initialized() {
return _initialized;
}
Thread* ThreadLocalStorage::get_thread_slow() {
return thread();
}
extern "C" Thread* get_thread() {
return ThreadLocalStorage::thread();
}

View File

@ -1,39 +0,0 @@
/*
* Copyright (c) 1998, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#ifndef OS_CPU_SOLARIS_SPARC_VM_THREADLS_SOLARIS_SPARC_HPP
#define OS_CPU_SOLARIS_SPARC_VM_THREADLS_SOLARIS_SPARC_HPP
// Solaris specific implementation involves simple, direct use
// of a compiler-based thread-local variable
private:
static __thread Thread * _thr_current;
static bool _initialized; // needed for shared API
public:
static inline Thread* thread();
#endif // OS_CPU_SOLARIS_SPARC_VM_THREADLS_SOLARIS_SPARC_HPP

View File

@ -25,8 +25,6 @@
#include "precompiled.hpp"
#include "asm/macroAssembler.inline.hpp"
#include "runtime/os.hpp"
#include "runtime/threadLocalStorage.hpp"
#include "runtime/thread.inline.hpp"
void MacroAssembler::int3() {
push(rax);
@ -37,33 +35,3 @@ void MacroAssembler::int3() {
pop(rdx);
pop(rax);
}
// This is simply a call to ThreadLocalStorage::thread()
void MacroAssembler::get_thread(Register thread) {
if (thread != rax) {
push(rax);
}
push(rdi);
push(rsi);
push(rdx);
push(rcx);
push(r8);
push(r9);
push(r10);
push(r11);
call(RuntimeAddress(CAST_FROM_FN_PTR(address, ThreadLocalStorage::thread)));
pop(r11);
pop(r10);
pop(r9);
pop(r8);
pop(rcx);
pop(rdx);
pop(rsi);
pop(rdi);
if (thread != rax) {
movl(thread, rax);
pop(rax);
}
}

View File

@ -346,7 +346,7 @@ JVM_handle_solaris_signal(int sig, siginfo_t* info, void* ucVoid,
}
#endif // !AMD64
Thread* t = ThreadLocalStorage::get_thread_slow(); // slow & steady
Thread* t = Thread::current_or_null_safe();
// Must do this before SignalHandlerMark, if crash protection installed we will longjmp away
// (no destructors can be run)

View File

@ -1,52 +0,0 @@
/*
* Copyright (c) 1998, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#include "precompiled.hpp"
#include "runtime/thread.inline.hpp"
#include "runtime/threadLocalStorage.hpp"
// True thread-local variable
__thread Thread * ThreadLocalStorage::_thr_current = NULL;
// Implementations needed to support the shared API
void ThreadLocalStorage::pd_invalidate_all() {} // nothing to do
bool ThreadLocalStorage::_initialized = false;
void ThreadLocalStorage::init() {
_initialized = true;
}
bool ThreadLocalStorage::is_initialized() {
return _initialized;
}
Thread* ThreadLocalStorage::get_thread_slow() {
return thread();
}
extern "C" Thread* get_thread() {
return ThreadLocalStorage::thread();
}

View File

@ -1,39 +0,0 @@
/*
* Copyright (c) 1998, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#ifndef OS_CPU_SOLARIS_X86_VM_THREADLS_SOLARIS_X86_HPP
#define OS_CPU_SOLARIS_X86_VM_THREADLS_SOLARIS_X86_HPP
// Solaris specific implementation involves simple, direct use
// of a compiler-based thread-local variable
private:
static __thread Thread * _thr_current;
static bool _initialized; // needed for shared API
public:
static inline Thread* thread();
#endif // OS_CPU_SOLARIS_X86_VM_THREADLS_SOLARIS_X86_HPP

View File

@ -1,5 +1,5 @@
/*
* Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1999, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -26,8 +26,6 @@
#include "asm/macroAssembler.hpp"
#include "asm/macroAssembler.inline.hpp"
#include "runtime/os.hpp"
#include "runtime/threadLocalStorage.hpp"
void MacroAssembler::int3() {
emit_int8((unsigned char)0xCC);
@ -58,44 +56,11 @@ void MacroAssembler::get_thread(Register thread) {
prefix(FS_segment);
movptr(thread, null);
assert(ThreadLocalStorage::get_thread_ptr_offset() != 0,
assert(os::win32::get_thread_ptr_offset() != 0,
"Thread Pointer Offset has not been initialized");
movl(thread, Address(thread, ThreadLocalStorage::get_thread_ptr_offset()));
movl(thread, Address(thread, os::win32::get_thread_ptr_offset()));
}
#else
// call (Thread*)TlsGetValue(thread_index());
void MacroAssembler::get_thread(Register thread) {
if (thread != rax) {
push(rax);
}
push(rdi);
push(rsi);
push(rdx);
push(rcx);
push(r8);
push(r9);
push(r10);
// XXX
mov(r10, rsp);
andq(rsp, -16);
push(r10);
push(r11);
movl(c_rarg0, ThreadLocalStorage::thread_index());
call(RuntimeAddress((address)TlsGetValue));
// #else - use shared x86 implementation in cpu/x86/vm/macroAssembler_x86.cpp
pop(r11);
pop(rsp);
pop(r10);
pop(r9);
pop(r8);
pop(rcx);
pop(rdx);
pop(rsi);
pop(rdi);
if (thread != rax) {
mov(thread, rax);
pop(rax);
}
}
#endif

View File

@ -85,14 +85,14 @@ void os::os_exception_wrapper(java_call_t f, JavaValue* value, const methodHandl
//
volatile Thread* wrapperthread = thread;
if ( ThreadLocalStorage::get_thread_ptr_offset() == 0 ) {
if (os::win32::get_thread_ptr_offset() == 0) {
int thread_ptr_offset;
__asm {
lea eax, dword ptr wrapperthread;
sub eax, dword ptr FS:[0H];
mov thread_ptr_offset, eax
};
ThreadLocalStorage::set_thread_ptr_offset(thread_ptr_offset);
os::win32::set_thread_ptr_offset(thread_ptr_offset);
}
#ifdef ASSERT
// Verify that the offset hasn't changed since we initally captured
@ -105,7 +105,7 @@ void os::os_exception_wrapper(java_call_t f, JavaValue* value, const methodHandl
sub eax, dword ptr FS:[0H];
mov test_thread_ptr_offset, eax
};
assert(test_thread_ptr_offset == ThreadLocalStorage::get_thread_ptr_offset(),
assert(test_thread_ptr_offset == os::win32::get_thread_ptr_offset(),
"thread pointer offset from SEH changed");
}
#endif // ASSERT

View File

@ -1,49 +0,0 @@
/*
* Copyright (c) 1998, 2010, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#include "precompiled.hpp"
#include "runtime/thread.inline.hpp"
#include "runtime/threadLocalStorage.hpp"
// Provides an entry point we can link against and
// a buffer we can emit code into. The buffer is
// filled by ThreadLocalStorage::generate_code_for_get_thread
// and called from ThreadLocalStorage::thread()
int ThreadLocalStorage::_thread_ptr_offset = 0;
static void call_wrapper_dummy() {}
// We need to call the os_exception_wrapper once so that it sets
// up the offset from FS of the thread pointer.
void ThreadLocalStorage::generate_code_for_get_thread() {
os::os_exception_wrapper( (java_call_t)call_wrapper_dummy,
NULL, NULL, NULL, NULL);
}
void ThreadLocalStorage::pd_init() { }
void ThreadLocalStorage::pd_set_thread(Thread* thread) {
os::thread_local_storage_at_put(ThreadLocalStorage::thread_index(), thread);
}

View File

@ -1,49 +0,0 @@
/*
* Copyright (c) 1998, 2010, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#ifndef OS_CPU_WINDOWS_X86_VM_THREADLS_WINDOWS_X86_HPP
#define OS_CPU_WINDOWS_X86_VM_THREADLS_WINDOWS_X86_HPP
// Processor dependent parts of ThreadLocalStorage
protected:
static int _thread_ptr_offset;
public:
// Java Thread
static inline Thread* thread() {
return (Thread*)TlsGetValue(thread_index());
}
static inline Thread* get_thread() {
return (Thread*)TlsGetValue(thread_index());
}
static inline void set_thread_ptr_offset( int offset ) { _thread_ptr_offset = offset; }
static inline int get_thread_ptr_offset() { return _thread_ptr_offset; }
#endif // OS_CPU_WINDOWS_X86_VM_THREADLS_WINDOWS_X86_HPP

View File

@ -48,6 +48,7 @@
#include "runtime/thread.hpp"
#include "services/threadService.hpp"
#include "utilities/bytes.hpp"
#include "logging/log.hpp"
#define NOFAILOVER_MAJOR_VERSION 51
#define NONZERO_PADDING_BYTES_IN_SWITCH_MAJOR_VERSION 51
@ -111,6 +112,18 @@ void Verifier::trace_class_resolution(Klass* resolve_class, InstanceKlass* verif
}
}
// Prints the end-verification message to the appropriate output.
void Verifier::log_end_verification(outputStream* st, const char* klassName, Symbol* exception_name, TRAPS) {
if (HAS_PENDING_EXCEPTION) {
st->print("Verification for %s has", klassName);
st->print_cr(" exception pending %s ",
PENDING_EXCEPTION->klass()->external_name());
} else if (exception_name != NULL) {
st->print_cr("Verification for %s failed", klassName);
}
st->print_cr("End class verification for: %s", klassName);
}
bool Verifier::verify(instanceKlassHandle klass, Verifier::Mode mode, bool should_verify_class, TRAPS) {
HandleMark hm;
ResourceMark rm(THREAD);
@ -155,9 +168,7 @@ bool Verifier::verify(instanceKlassHandle klass, Verifier::Mode mode, bool shoul
bool can_failover = FailOverToOldVerifier &&
klass->major_version() < NOFAILOVER_MAJOR_VERSION;
if (TraceClassInitialization) {
tty->print_cr("Start class verification for: %s", klassName);
}
log_info(classinit)("Start class verification for: %s", klassName);
if (klass->major_version() >= STACKMAP_ATTRIBUTE_MAJOR_VERSION) {
ClassVerifier split_verifier(klass, THREAD);
split_verifier.verify_class(THREAD);
@ -165,10 +176,10 @@ bool Verifier::verify(instanceKlassHandle klass, Verifier::Mode mode, bool shoul
if (can_failover && !HAS_PENDING_EXCEPTION &&
(exception_name == vmSymbols::java_lang_VerifyError() ||
exception_name == vmSymbols::java_lang_ClassFormatError())) {
if (TraceClassInitialization || VerboseVerification) {
tty->print_cr(
"Fail over class verification to old verifier for: %s", klassName);
if (VerboseVerification) {
tty->print_cr("Fail over class verification to old verifier for: %s", klassName);
}
log_info(classinit)("Fail over class verification to old verifier for: %s", klassName);
exception_name = inference_verify(
klass, message_buffer, message_buffer_len, THREAD);
}
@ -180,15 +191,11 @@ bool Verifier::verify(instanceKlassHandle klass, Verifier::Mode mode, bool shoul
klass, message_buffer, message_buffer_len, THREAD);
}
if (TraceClassInitialization || VerboseVerification) {
if (HAS_PENDING_EXCEPTION) {
tty->print("Verification for %s has", klassName);
tty->print_cr(" exception pending %s ",
PENDING_EXCEPTION->klass()->external_name());
} else if (exception_name != NULL) {
tty->print_cr("Verification for %s failed", klassName);
}
tty->print_cr("End class verification for: %s", klassName);
if (log_is_enabled(Info, classinit)){
log_end_verification(LogHandle(classinit)::info_stream(), klassName, exception_name, THREAD);
}
if (VerboseVerification){
log_end_verification(tty, klassName, exception_name, THREAD);
}
if (HAS_PENDING_EXCEPTION) {
@ -598,10 +605,13 @@ void ClassVerifier::verify_class(TRAPS) {
verify_method(methodHandle(THREAD, m), CHECK_VERIFY(this));
}
if (VerboseVerification || TraceClassInitialization) {
if (was_recursively_verified())
if (was_recursively_verified()){
if (VerboseVerification){
tty->print_cr("Recursive verification detected for: %s",
_klass->external_name());
_klass->external_name());
}
log_info(classinit)("Recursive verification detected for: %s",
_klass->external_name());
}
}

View File

@ -50,6 +50,7 @@ class Verifier : AllStatic {
* Otherwise, no exception is thrown and the return indicates the
* error.
*/
static void log_end_verification(outputStream* st, const char* klassName, Symbol* exception_name, TRAPS);
static bool verify(instanceKlassHandle klass, Mode mode, bool should_verify_class, TRAPS);
// Return false if the class is loaded by the bootstrap loader,

View File

@ -2609,7 +2609,7 @@ address nmethod::continuation_for_implicit_exception(address pc) {
int cont_offset = ImplicitExceptionTable(this).at( exception_offset );
#ifdef ASSERT
if (cont_offset == 0) {
Thread* thread = ThreadLocalStorage::get_thread_slow();
Thread* thread = Thread::current();
ResetNoHandleMark rnm; // Might be called from LEAF/QUICK ENTRY
HandleMark hm(thread);
ResourceMark rm(thread);

View File

@ -144,9 +144,6 @@ void ConcurrentMarkSweepThread::run() {
_cmst = NULL;
Terminator_lock->notify();
}
// Thread destructor usually does this..
ThreadLocalStorage::set_thread(NULL);
}
#ifndef PRODUCT

View File

@ -123,7 +123,7 @@ class G1HotCardCache: public CHeapObj<mtGC> {
// Resets the hot card cache and discards the entries.
void reset_hot_cache() {
assert(SafepointSynchronize::is_at_safepoint(), "Should be at a safepoint");
assert(Thread::current_noinline()->is_VM_thread(), "Current thread should be the VMthread");
assert(Thread::current()->is_VM_thread(), "Current thread should be the VMthread");
if (default_use_cache()) {
reset_hot_cache_internal();
}

View File

@ -33,9 +33,11 @@
#define G1_FLAGS(develop, develop_pd, product, product_pd, diagnostic, experimental, notproduct, manageable, product_rw, range, constraint) \
\
product(bool, G1UseAdaptiveIHOP, false, \
"Adaptively adjust InitiatingHeapOccupancyPercent from the " \
"initial value.") \
product(bool, G1UseAdaptiveIHOP, true, \
"Adaptively adjust the initiating heap occupancy from the " \
"initial value of InitiatingHeapOccupancyPercent. The policy " \
"attempts to start marking in time based on application " \
"behavior.") \
\
experimental(size_t, G1AdaptiveIHOPNumInitialSamples, 3, \
"How many completed time periods from initial mark to first " \

View File

@ -1,4 +1,3 @@
/*
* Copyright (c) 2002, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
@ -96,7 +95,6 @@ void GCTaskThread::print_task_time_stamps() {
void GCTaskThread::run() {
// Set up the thread for stack overflow support
this->record_stack_base_and_size();
this->initialize_thread_local_storage();
this->initialize_named_thread();
// Bind yourself to your processor.
if (processor_id() != GCTaskManager::sentinel_worker()) {

View File

@ -51,7 +51,6 @@ void ConcurrentGCThread::create_and_start() {
void ConcurrentGCThread::initialize_in_thread() {
this->record_stack_base_and_size();
this->initialize_thread_local_storage();
this->initialize_named_thread();
this->set_active_handles(JNIHandleBlock::allocate_block());
// From this time Thread::current() should be working.
@ -74,9 +73,6 @@ void ConcurrentGCThread::terminate() {
_has_terminated = true;
Terminator_lock->notify();
}
// Thread destructor usually does this..
ThreadLocalStorage::set_thread(NULL);
}
static void _sltLoop(JavaThread* thread, TRAPS) {

View File

@ -275,7 +275,6 @@ void AbstractGangWorker::run() {
}
void AbstractGangWorker::initialize() {
this->initialize_thread_local_storage();
this->record_stack_base_and_size();
this->initialize_named_thread();
assert(_gang != NULL, "No gang to run in");

View File

@ -31,6 +31,7 @@
// (The tags 'all', 'disable' and 'help' are special tags that can
// not be used in log calls, and should not be listed below.)
#define LOG_TAG_LIST \
LOG_TAG(classinit) \
LOG_TAG(defaultmethods) \
LOG_TAG(gc) \
LOG_TAG(logging) \

View File

@ -790,7 +790,7 @@ void Arena::free_malloced_objects(Chunk* chunk, char* hwm, char* max, char* hwm2
ReallocMark::ReallocMark() {
#ifdef ASSERT
Thread *thread = ThreadLocalStorage::get_thread_slow();
Thread *thread = Thread::current();
_nesting = thread->resource_area()->nesting();
#endif
}

View File

@ -1,5 +1,5 @@
/*
* Copyright (c) 1997, 2014, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1997, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -121,7 +121,7 @@ protected:
debug_only(_area->_nesting++;)
assert( _area->_nesting > 0, "must stack allocate RMs" );
#ifdef ASSERT
Thread* thread = ThreadLocalStorage::thread();
Thread* thread = Thread::current_or_null();
if (thread != NULL) {
_thread = thread;
_previous_resource_mark = thread->current_resource_mark();

View File

@ -63,6 +63,7 @@
#include "services/threadService.hpp"
#include "utilities/dtrace.hpp"
#include "utilities/macros.hpp"
#include "logging/log.hpp"
#ifdef COMPILER1
#include "c1/c1_Compiler.hpp"
#endif
@ -491,9 +492,9 @@ void InstanceKlass::eager_initialize_impl(instanceKlassHandle this_k) {
this_k->set_init_state (fully_initialized);
this_k->fence_and_clear_init_lock();
// trace
if (TraceClassInitialization) {
if (log_is_enabled(Info, classinit)) {
ResourceMark rm(THREAD);
tty->print_cr("[Initialized %s without side effects]", this_k->external_name());
log_info(classinit)("[Initialized %s without side effects]", this_k->external_name());
}
}
}
@ -1129,10 +1130,12 @@ void InstanceKlass::call_class_initializer_impl(instanceKlassHandle this_k, TRAP
methodHandle h_method(THREAD, this_k->class_initializer());
assert(!this_k->is_initialized(), "we cannot initialize twice");
if (TraceClassInitialization) {
tty->print("%d Initializing ", call_class_initializer_impl_counter++);
this_k->name()->print_value();
tty->print_cr("%s (" INTPTR_FORMAT ")", h_method() == NULL ? "(no method)" : "", p2i(this_k()));
if (log_is_enabled(Info, classinit)) {
ResourceMark rm;
outputStream* log = LogHandle(classinit)::info_stream();
log->print("%d Initializing ", call_class_initializer_impl_counter++);
this_k->name()->print_value_on(log);
log->print_cr("%s (" INTPTR_FORMAT ")", h_method() == NULL ? "(no method)" : "", p2i(this_k()));
}
if (h_method() != NULL) {
JavaCallArguments args; // No arguments

View File

@ -35,7 +35,7 @@ void oop::register_oop() {
assert (CheckUnhandledOops, "should only call when CheckUnhandledOops");
if (!Universe::is_fully_initialized()) return;
// This gets expensive, which is why checking unhandled oops is on a switch.
Thread* t = ThreadLocalStorage::thread();
Thread* t = Thread::current_or_null();
if (t != NULL && t->is_Java_thread()) {
frame fr = os::current_frame();
// This points to the oop creator, I guess current frame points to caller
@ -48,7 +48,7 @@ void oop::unregister_oop() {
assert (CheckUnhandledOops, "should only call when CheckUnhandledOops");
if (!Universe::is_fully_initialized()) return;
// This gets expensive, which is why checking unhandled oops is on a switch.
Thread* t = ThreadLocalStorage::thread();
Thread* t = Thread::current_or_null();
if (t != NULL && t->is_Java_thread()) {
t->unhandled_oops()->unregister_unhandled_oop(this);
}

View File

@ -203,7 +203,6 @@
# include "runtime/stubRoutines.hpp"
# include "runtime/synchronizer.hpp"
# include "runtime/thread.hpp"
# include "runtime/threadLocalStorage.hpp"
# include "runtime/timer.hpp"
# include "runtime/unhandledOops.hpp"
# include "runtime/vframe.hpp"

View File

@ -4175,7 +4175,7 @@ static jint attach_current_thread(JavaVM *vm, void **penv, void *_args, bool dae
}
*/
Thread* t = ThreadLocalStorage::get_thread_slow();
Thread* t = Thread::current_or_null();
if (t != NULL) {
// If the thread has been attached this operation is a no-op
*(JNIEnv**)penv = ((JavaThread*) t)->jni_environment();
@ -4190,10 +4190,8 @@ static jint attach_current_thread(JavaVM *vm, void **penv, void *_args, bool dae
// initializing the Java level thread object. Hence, the correct state must
// be set in order for the Safepoint code to deal with it correctly.
thread->set_thread_state(_thread_in_vm);
// Must do this before initialize_thread_local_storage
thread->record_stack_base_and_size();
thread->initialize_thread_local_storage();
thread->initialize_thread_current();
if (!os::create_attached_thread(thread)) {
delete thread;
@ -4300,8 +4298,8 @@ jint JNICALL jni_DetachCurrentThread(JavaVM *vm) {
JNIWrapper("DetachCurrentThread");
// If the thread has been deattacted the operations is a no-op
if (ThreadLocalStorage::thread() == NULL) {
// If the thread has already been detached the operation is a no-op
if (Thread::current_or_null() == NULL) {
HOTSPOT_JNI_DETACHCURRENTTHREAD_RETURN(JNI_OK);
return JNI_OK;
}
@ -4358,7 +4356,7 @@ jint JNICALL jni_GetEnv(JavaVM *vm, void **penv, jint version) {
#define JVMPI_VERSION_1_2 ((jint)0x10000003)
#endif // !JVMPI_VERSION_1
Thread* thread = ThreadLocalStorage::thread();
Thread* thread = Thread::current_or_null();
if (thread != NULL && thread->is_Java_thread()) {
if (Threads::is_supported_jni_version_including_1_1(version)) {
*(JNIEnv**)penv = ((JavaThread*) thread)->jni_environment();

View File

@ -87,9 +87,9 @@ static struct JNINativeInterface_ * unchecked_jni_NativeInterface;
#define JNI_ENTRY_CHECKED(result_type, header) \
extern "C" { \
result_type JNICALL header { \
JavaThread* thr = (JavaThread*)ThreadLocalStorage::get_thread_slow();\
JavaThread* thr = (JavaThread*) Thread::current_or_null(); \
if (thr == NULL || !thr->is_Java_thread()) { \
tty->print_cr("%s", fatal_using_jnienv_in_nonjava); \
tty->print_cr("%s", fatal_using_jnienv_in_nonjava); \
os::abort(true); \
} \
JNIEnv* xenv = thr->jni_environment(); \

View File

@ -494,7 +494,7 @@ static jvmtiError JNICALL
}</xsl:text>
<xsl:text>
Thread* this_thread = (Thread*)ThreadLocalStorage::thread(); </xsl:text>
Thread* this_thread = Thread::current_or_null(); </xsl:text>
<xsl:apply-templates select="." mode="transition"/>
</xsl:when>
@ -528,7 +528,7 @@ static jvmtiError JNICALL
</xsl:if>
<xsl:text> return JVMTI_ERROR_WRONG_PHASE;
}
Thread* this_thread = (Thread*)ThreadLocalStorage::thread(); </xsl:text>
Thread* this_thread = Thread::current_or_null(); </xsl:text>
<xsl:apply-templates select="." mode="transition"/>
</xsl:if>
</xsl:otherwise>
@ -558,7 +558,7 @@ static jvmtiError JNICALL
<xsl:choose>
<xsl:when test="count(@callbacksafe)=0 or not(contains(@callbacksafe,'safe'))">
<xsl:text> if (Threads::number_of_threads() != 0) {
Thread* this_thread = (Thread*)ThreadLocalStorage::thread();</xsl:text>
Thread* this_thread = Thread::current_or_null();</xsl:text>
</xsl:when>
<xsl:otherwise>
@ -567,7 +567,7 @@ static jvmtiError JNICALL
if (Threads::number_of_threads() == 0) {
transition = false;
} else {
this_thread = (Thread*)ThreadLocalStorage::thread();
this_thread = Thread::current_or_null();
transition = ((this_thread != NULL) &amp;&amp; !this_thread->is_VM_thread() &amp;&amp; !this_thread->is_ConcurrentGC_thread());
}
if (transition) {</xsl:text>

View File

@ -374,7 +374,7 @@ JvmtiExport::get_jvmti_interface(JavaVM *jvm, void **penv, jint version) {
}
if (JvmtiEnv::get_phase() == JVMTI_PHASE_LIVE) {
JavaThread* current_thread = (JavaThread*) ThreadLocalStorage::thread();
JavaThread* current_thread = JavaThread::current();
// transition code: native to VM
ThreadInVMfromNative __tiv(current_thread);
VM_ENTRY_BASE(jvmtiEnv*, JvmtiExport::get_jvmti_interface, current_thread)
@ -1901,7 +1901,7 @@ void JvmtiExport::post_dynamic_code_generated_while_holding_locks(const char* na
// Collect all the vm internally allocated objects which are visible to java world
void JvmtiExport::record_vm_internal_object_allocation(oop obj) {
Thread* thread = ThreadLocalStorage::thread();
Thread* thread = Thread::current_or_null();
if (thread != NULL && thread->is_Java_thread()) {
// Can not take safepoint here.
No_Safepoint_Verifier no_sfpt;
@ -2436,7 +2436,7 @@ NoJvmtiVMObjectAllocMark::NoJvmtiVMObjectAllocMark() : _collector(NULL) {
if (!JvmtiExport::should_post_vm_object_alloc()) {
return;
}
Thread* thread = ThreadLocalStorage::thread();
Thread* thread = Thread::current_or_null();
if (thread != NULL && thread->is_Java_thread()) {
JavaThread* current_thread = (JavaThread*)thread;
JvmtiThreadState *state = current_thread->jvmti_thread_state();

View File

@ -1,5 +1,5 @@
/*
* Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1999, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -79,7 +79,7 @@ class SafeResourceMark : public ResourceMark {
if (Threads::number_of_threads() == 0) {
return JvmtiUtil::single_threaded_resource_area();
}
thread = ThreadLocalStorage::thread();
thread = Thread::current_or_null();
if (thread == NULL) {
return JvmtiUtil::single_threaded_resource_area();
}

View File

@ -1449,9 +1449,6 @@ public:
develop(bool, TraceBytecodes, false, \
"Trace bytecode execution") \
\
develop(bool, TraceClassInitialization, false, \
"Trace class initialization") \
\
product(bool, TraceExceptions, false, \
"Trace exceptions") \
\

View File

@ -32,7 +32,6 @@
#include "runtime/interfaceSupport.hpp"
#include "runtime/orderAccess.inline.hpp"
#include "runtime/os.inline.hpp"
#include "runtime/threadLocalStorage.hpp"
#include "runtime/vframe.hpp"
#include "utilities/preserveException.hpp"

View File

@ -562,7 +562,7 @@ extern "C" { \
#define JVM_ENTRY_NO_ENV(result_type, header) \
extern "C" { \
result_type JNICALL header { \
JavaThread* thread = (JavaThread*)ThreadLocalStorage::thread(); \
JavaThread* thread = JavaThread::current(); \
ThreadInVMfromNative __tiv(thread); \
debug_only(VMNativeEntryWrapper __vew;) \
VM_ENTRY_BASE(result_type, header, thread)

View File

@ -512,10 +512,10 @@ void before_exit(JavaThread * thread) {
}
void vm_exit(int code) {
Thread* thread = ThreadLocalStorage::is_initialized() ?
ThreadLocalStorage::get_thread_slow() : NULL;
Thread* thread =
ThreadLocalStorage::is_initialized() ? Thread::current_or_null() : NULL;
if (thread == NULL) {
// we have serious problems -- just exit
// very early initialization failure -- just exit
vm_direct_exit(code);
}
@ -551,8 +551,7 @@ void vm_perform_shutdown_actions() {
// Calling 'exit_globals()' will disable thread-local-storage and cause all
// kinds of assertions to trigger in debug mode.
if (is_init_completed()) {
Thread* thread = ThreadLocalStorage::is_initialized() ?
ThreadLocalStorage::get_thread_slow() : NULL;
Thread* thread = Thread::current_or_null();
if (thread != NULL && thread->is_Java_thread()) {
// We are leaving the VM, set state to native (in case any OS exit
// handlers call back to the VM)
@ -606,7 +605,7 @@ void vm_exit_during_initialization(Handle exception) {
// If there are exceptions on this thread it must be cleared
// first and here. Any future calls to EXCEPTION_MARK requires
// that no pending exceptions exist.
Thread *THREAD = Thread::current();
Thread *THREAD = Thread::current(); // can't be NULL
if (HAS_PENDING_EXCEPTION) {
CLEAR_PENDING_EXCEPTION;
}

View File

@ -1,5 +1,5 @@
/*
* Copyright (c) 1998, 2014, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 1998, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -1035,10 +1035,10 @@ void Monitor::jvm_raw_lock() {
Exeunt:
assert(ILocked(), "invariant");
assert(_owner == NULL, "invariant");
// This can potentially be called by non-java Threads. Thus, the ThreadLocalStorage
// This can potentially be called by non-java Threads. Thus, the Thread::current_or_null()
// might return NULL. Don't call set_owner since it will break on an NULL owner
// Consider installing a non-null "ANON" distinguished value instead of just NULL.
_owner = ThreadLocalStorage::thread();
_owner = Thread::current_or_null();
return;
}

View File

@ -27,7 +27,6 @@
#include "runtime/os.inline.hpp"
#include "runtime/safepoint.hpp"
#include "runtime/thread.inline.hpp"
#include "runtime/threadLocalStorage.hpp"
#include "runtime/vmThread.hpp"
// Mutexes used in the VM (see comment in mutexLocker.hpp):

View File

@ -420,28 +420,6 @@ void* os::native_java_library() {
}
#endif
}
static jboolean onLoaded = JNI_FALSE;
if (onLoaded) {
// We may have to wait to fire OnLoad until TLS is initialized.
if (ThreadLocalStorage::is_initialized()) {
// The JNI_OnLoad handling is normally done by method load in
// java.lang.ClassLoader$NativeLibrary, but the VM loads the base library
// explicitly so we have to check for JNI_OnLoad as well
const char *onLoadSymbols[] = JNI_ONLOAD_SYMBOLS;
JNI_OnLoad_t JNI_OnLoad = CAST_TO_FN_PTR(
JNI_OnLoad_t, dll_lookup(_native_java_library, onLoadSymbols[0]));
if (JNI_OnLoad != NULL) {
JavaThread* thread = JavaThread::current();
ThreadToNativeFromVM ttn(thread);
HandleMark hm(thread);
jint ver = (*JNI_OnLoad)(&main_vm, NULL);
onLoaded = JNI_TRUE;
if (!Threads::is_supported_jni_version_including_1_1(ver)) {
vm_exit_during_initialization("Unsupported JNI version");
}
}
}
}
return _native_java_library;
}
@ -574,7 +552,7 @@ void* os::malloc(size_t size, MEMFLAGS memflags, const NativeCallStack& stack) {
// exists and has crash protection.
WatcherThread *wt = WatcherThread::watcher_thread();
if (wt != NULL && wt->has_crash_protection()) {
Thread* thread = ThreadLocalStorage::get_thread_slow();
Thread* thread = Thread::current_or_null();
if (thread == wt) {
assert(!wt->has_crash_protection(),
"Can't malloc with crash protection from WatcherThread");

View File

@ -670,12 +670,6 @@ class os: AllStatic {
static jlong current_file_offset(int fd);
static jlong seek_to_file_offset(int fd, jlong offset);
// Thread Local Storage
static int allocate_thread_local_storage();
static void thread_local_storage_at_put(int index, void* value);
static void* thread_local_storage_at(int index);
static void free_thread_local_storage(int index);
// Retrieve native stack frames.
// Parameter:
// stack: an array to storage stack pointers.

View File

@ -30,7 +30,6 @@
#include "interpreter/linkResolver.hpp"
#include "memory/allocation.hpp"
#include "memory/resourceArea.hpp"
#include "runtime/threadLocalStorage.hpp"
#include "utilities/hashtable.hpp"
#include "utilities/macros.hpp"

View File

@ -78,7 +78,6 @@
#include "runtime/task.hpp"
#include "runtime/thread.inline.hpp"
#include "runtime/threadCritical.hpp"
#include "runtime/threadLocalStorage.hpp"
#include "runtime/vframe.hpp"
#include "runtime/vframeArray.hpp"
#include "runtime/vframe_hp.hpp"
@ -142,6 +141,10 @@
#endif // ndef DTRACE_ENABLED
#ifndef USE_LIBRARY_BASED_TLS_ONLY
// Current thread is maintained as a thread-local variable
THREAD_LOCAL_DECL Thread* Thread::_thr_current = NULL;
#endif
// Class hierarchy
// - Thread
@ -281,22 +284,22 @@ Thread::Thread() {
#endif // ASSERT
}
// Non-inlined version to be used where thread.inline.hpp shouldn't be included.
Thread* Thread::current_noinline() {
return Thread::current();
void Thread::initialize_thread_current() {
#ifndef USE_LIBRARY_BASED_TLS_ONLY
assert(_thr_current == NULL, "Thread::current already initialized");
_thr_current = this;
#endif
assert(ThreadLocalStorage::thread() == NULL, "ThreadLocalStorage::thread already initialized");
ThreadLocalStorage::set_thread(this);
assert(Thread::current() == ThreadLocalStorage::thread(), "TLS mismatch!");
}
void Thread::initialize_thread_local_storage() {
// Note: Make sure this method only calls
// non-blocking operations. Otherwise, it might not work
// with the thread-startup/safepoint interaction.
// During Java thread startup, safepoint code should allow this
// method to complete because it may need to allocate memory to
// store information for the new thread.
// initialize structure dependent on thread local storage
ThreadLocalStorage::set_thread(this);
void Thread::clear_thread_current() {
assert(Thread::current() == ThreadLocalStorage::thread(), "TLS mismatch!");
#ifndef USE_LIBRARY_BASED_TLS_ONLY
_thr_current = NULL;
#endif
ThreadLocalStorage::set_thread(NULL);
}
void Thread::record_stack_base_and_size() {
@ -364,15 +367,12 @@ Thread::~Thread() {
delete _SR_lock;
// clear thread local storage if the Thread is deleting itself
// clear Thread::current if thread is deleting itself.
// Needed to ensure JNI correctly detects non-attached threads.
if (this == Thread::current()) {
ThreadLocalStorage::set_thread(NULL);
} else {
// In the case where we're not the current thread, invalidate all the
// caches in case some code tries to get the current thread or the
// thread that was destroyed, and gets stale information.
ThreadLocalStorage::invalidate_all();
clear_thread_current();
}
CHECK_UNHANDLED_OOPS_ONLY(if (CheckUnhandledOops) delete unhandled_oops();)
}
@ -1273,7 +1273,6 @@ void WatcherThread::run() {
assert(this == watcher_thread(), "just checking");
this->record_stack_base_and_size();
this->initialize_thread_local_storage();
this->set_native_thread_name(this->name());
this->set_active_handles(JNIHandleBlock::allocate_block());
while (true) {
@ -1326,9 +1325,6 @@ void WatcherThread::run() {
_watcher_thread = NULL;
Terminator_lock->notify();
}
// Thread destructor usually does this..
ThreadLocalStorage::set_thread(NULL);
}
void WatcherThread::start() {
@ -1663,9 +1659,6 @@ void JavaThread::run() {
// Record real stack base and size.
this->record_stack_base_and_size();
// Initialize thread local storage; set before calling MutexLocker
this->initialize_thread_local_storage();
this->create_stack_guard_pages();
this->cache_global_variables();
@ -1997,8 +1990,7 @@ void JavaThread::cleanup_failed_attach_current_thread() {
JavaThread* JavaThread::active() {
Thread* thread = ThreadLocalStorage::thread();
assert(thread != NULL, "just checking");
Thread* thread = Thread::current();
if (thread->is_Java_thread()) {
return (JavaThread*) thread;
} else {
@ -3407,7 +3399,7 @@ jint Threads::create_vm(JavaVMInitArgs* args, bool* canTryAgain) {
jint adjust_after_os_result = Arguments::adjust_after_os();
if (adjust_after_os_result != JNI_OK) return adjust_after_os_result;
// initialize TLS
// Initialize library-based TLS
ThreadLocalStorage::init();
// Initialize output stream logging
@ -3444,14 +3436,9 @@ jint Threads::create_vm(JavaVMInitArgs* args, bool* canTryAgain) {
// Attach the main thread to this os thread
JavaThread* main_thread = new JavaThread();
main_thread->set_thread_state(_thread_in_vm);
// must do this before set_active_handles and initialize_thread_local_storage
// Note: on solaris initialize_thread_local_storage() will (indirectly)
// change the stack size recorded here to one based on the java thread
// stacksize. This adjusted size is what is used to figure the placement
// of the guard pages.
main_thread->initialize_thread_current();
// must do this before set_active_handles
main_thread->record_stack_base_and_size();
main_thread->initialize_thread_local_storage();
main_thread->set_active_handles(JNIHandleBlock::allocate_block());
if (!main_thread->set_as_starting_thread()) {

View File

@ -102,6 +102,12 @@ class WorkerThread;
class Thread: public ThreadShadow {
friend class VMStructs;
private:
#ifndef USE_LIBRARY_BASED_TLS_ONLY
// Current thread is maintained as a thread-local variable
static THREAD_LOCAL_DECL Thread* _thr_current;
#endif
// Exception handling
// (Note: _pending_exception and friends are in ThreadShadow)
//oop _pending_exception; // pending exception for current thread
@ -260,7 +266,6 @@ class Thread: public ThreadShadow {
friend class No_Alloc_Verifier;
friend class No_Safepoint_Verifier;
friend class Pause_No_Safepoint_Verifier;
friend class ThreadLocalStorage;
friend class GC_locker;
ThreadLocalAllocBuffer _tlab; // Thread-local eden
@ -307,9 +312,12 @@ class Thread: public ThreadShadow {
Thread();
virtual ~Thread();
// initializtion
void initialize_thread_local_storage();
// Manage Thread::current()
void initialize_thread_current();
private:
void clear_thread_current(); // needed for detaching JNI threads
public:
// thread entry point
virtual void run();
@ -337,10 +345,13 @@ class Thread: public ThreadShadow {
virtual char* name() const { return (char*)"Unknown thread"; }
// Returns the current thread
// Returns the current thread (ASSERTS if NULL)
static inline Thread* current();
// ... without having to include thread.inline.hpp.
static Thread* current_noinline();
// Returns the current thread, or NULL if not attached
static inline Thread* current_or_null();
// Returns the current thread, or NULL if not attached, and is
// safe for use from signal-handlers
static inline Thread* current_or_null_safe();
// Common thread operations
static void set_priority(Thread* thread, ThreadPriority priority);
@ -649,25 +660,22 @@ protected:
};
// Inline implementation of Thread::current()
// Thread::current is "hot" it's called > 128K times in the 1st 500 msecs of
// startup.
// ThreadLocalStorage::thread is warm -- it's called > 16K times in the same
// period. This is inlined in thread_<os_family>.inline.hpp.
inline Thread* Thread::current() {
#ifdef ASSERT
// This function is very high traffic. Define PARANOID to enable expensive
// asserts.
#ifdef PARANOID
// Signal handler should call ThreadLocalStorage::get_thread_slow()
Thread* t = ThreadLocalStorage::get_thread_slow();
assert(t != NULL && !t->is_inside_signal_handler(),
"Don't use Thread::current() inside signal handler");
Thread* current = current_or_null();
assert(current != NULL, "Thread::current() called on detached thread");
return current;
}
inline Thread* Thread::current_or_null() {
#ifndef USE_LIBRARY_BASED_TLS_ONLY
return _thr_current;
#else
return ThreadLocalStorage::thread();
#endif
#endif
Thread* thread = ThreadLocalStorage::thread();
assert(thread != NULL, "just checking");
return thread;
}
inline Thread* Thread::current_or_null_safe() {
return ThreadLocalStorage::thread();
}
// Name support for threads. non-JavaThread subclasses with multiple
@ -1842,8 +1850,8 @@ class JavaThread: public Thread {
// Inline implementation of JavaThread::current
inline JavaThread* JavaThread::current() {
Thread* thread = ThreadLocalStorage::thread();
assert(thread != NULL && thread->is_Java_thread(), "just checking");
Thread* thread = Thread::current();
assert(thread->is_Java_thread(), "just checking");
return (JavaThread*)thread;
}

View File

@ -1,5 +1,5 @@
/*
* Copyright (c) 2012, 2014, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2012, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@ -30,21 +30,6 @@
#include "runtime/atomic.inline.hpp"
#include "runtime/os.inline.hpp"
#include "runtime/thread.hpp"
#ifdef TARGET_OS_FAMILY_linux
# include "thread_linux.inline.hpp"
#endif
#ifdef TARGET_OS_FAMILY_solaris
# include "thread_solaris.inline.hpp"
#endif
#ifdef TARGET_OS_FAMILY_windows
# include "thread_windows.inline.hpp"
#endif
#ifdef TARGET_OS_FAMILY_aix
# include "thread_aix.inline.hpp"
#endif
#ifdef TARGET_OS_FAMILY_bsd
# include "thread_bsd.inline.hpp"
#endif
#undef SHARE_VM_RUNTIME_THREAD_INLINE_HPP_SCOPE

View File

@ -1,63 +0,0 @@
/*
* Copyright (c) 1997, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*
*/
#include "precompiled.hpp"
#include "runtime/os.inline.hpp"
#include "runtime/thread.inline.hpp"
#include "runtime/threadLocalStorage.hpp"
// Solaris no longer has this kind of ThreadLocalStorage implementation.
// This will be removed from all platforms in the near future.
#ifndef SOLARIS
// static member initialization
int ThreadLocalStorage::_thread_index = -1;
Thread* ThreadLocalStorage::get_thread_slow() {
return (Thread*) os::thread_local_storage_at(ThreadLocalStorage::thread_index());
}
void ThreadLocalStorage::set_thread(Thread* thread) {
pd_set_thread(thread);
// The following ensure that any optimization tricks we have tried
// did not backfire on us:
guarantee(get_thread() == thread, "must be the same thread, quickly");
guarantee(get_thread_slow() == thread, "must be the same thread, slowly");
}
void ThreadLocalStorage::init() {
assert(!is_initialized(),
"More than one attempt to initialize threadLocalStorage");
pd_init();
set_thread_index(os::allocate_thread_local_storage());
generate_code_for_get_thread();
}
bool ThreadLocalStorage::is_initialized() {
return (thread_index() != -1);
}
#endif // SOLARIS

View File

@ -25,86 +25,26 @@
#ifndef SHARE_VM_RUNTIME_THREADLOCALSTORAGE_HPP
#define SHARE_VM_RUNTIME_THREADLOCALSTORAGE_HPP
#include "gc/shared/gcUtil.hpp"
#include "runtime/os.hpp"
#include "utilities/top.hpp"
// Interface for thread local storage
// forward-decl as we can't have an include cycle
class Thread;
// Fast variant of ThreadLocalStorage::get_thread_slow
extern "C" Thread* get_thread();
// Get raw thread id: e.g., %g7 on sparc, fs or gs on x86
extern "C" uintptr_t _raw_thread_id();
// Wrapper class for library-based (as opposed to compiler-based)
// thread-local storage (TLS). All platforms require this for
// signal-handler based TLS access (which while not strictly async-signal
// safe in theory, is and has-been for a long time, in practice).
// Platforms without compiler-based TLS (i.e. __thread storage-class modifier)
// will use this implementation for all TLS access - see thread.hpp/cpp
class ThreadLocalStorage : AllStatic {
// Exported API
public:
static void set_thread(Thread* thread);
static Thread* get_thread_slow();
static void invalidate_all() { pd_invalidate_all(); }
static Thread* thread(); // return current thread, if attached
static void set_thread(Thread* thread); // set current thread
static void init();
static bool is_initialized();
// Machine dependent stuff
#ifdef TARGET_OS_ARCH_linux_x86
# include "threadLS_linux_x86.hpp"
#endif
#ifdef TARGET_OS_ARCH_linux_sparc
# include "threadLS_linux_sparc.hpp"
#endif
#ifdef TARGET_OS_ARCH_linux_zero
# include "threadLS_linux_zero.hpp"
#endif
#ifdef TARGET_OS_ARCH_solaris_x86
# include "threadLS_solaris_x86.hpp"
#endif
#ifdef TARGET_OS_ARCH_solaris_sparc
# include "threadLS_solaris_sparc.hpp"
#endif
#ifdef TARGET_OS_ARCH_windows_x86
# include "threadLS_windows_x86.hpp"
#endif
#ifdef TARGET_OS_ARCH_linux_arm
# include "threadLS_linux_arm.hpp"
#endif
#ifdef TARGET_OS_ARCH_linux_ppc
# include "threadLS_linux_ppc.hpp"
#endif
#ifdef TARGET_OS_ARCH_linux_aarch64
# include "threadLS_linux_aarch64.hpp"
#endif
#ifdef TARGET_OS_ARCH_aix_ppc
# include "threadLS_aix_ppc.hpp"
#endif
#ifdef TARGET_OS_ARCH_bsd_x86
# include "threadLS_bsd_x86.hpp"
#endif
#ifdef TARGET_OS_ARCH_bsd_zero
# include "threadLS_bsd_zero.hpp"
#endif
#ifndef SOLARIS
public:
// Accessor
static inline int thread_index() { return _thread_index; }
static inline void set_thread_index(int index) { _thread_index = index; }
private:
static int _thread_index;
static void generate_code_for_get_thread();
// Processor dependent parts of set_thread and initialization
static void pd_set_thread(Thread* thread);
static void pd_init();
#endif // SOLARIS
// Invalidate any thread cacheing or optimization schemes.
static void pd_invalidate_all();
static bool is_initialized(); // can't use TLS prior to initialization
};
#endif // SHARE_VM_RUNTIME_THREADLOCALSTORAGE_HPP

View File

@ -240,7 +240,6 @@ void VMThread::destroy() {
void VMThread::run() {
assert(this == vm_thread(), "check");
this->initialize_thread_local_storage();
this->initialize_named_thread();
this->record_stack_base_and_size();
// Notify_lock wait checks on active_handles() to rewait in
@ -308,9 +307,6 @@ void VMThread::run() {
_terminate_lock->notify();
}
// Thread destructor usually does this.
ThreadLocalStorage::set_thread(NULL);
// Deletion must be done synchronously by the JNI DestroyJavaVM thread
// so that the VMThread deletion completes before the main thread frees
// up the CodeHeap.

View File

@ -378,7 +378,7 @@ Thread * VM_Exit::_shutdown_thread = NULL;
int VM_Exit::set_vm_exited() {
CodeCacheExtensions::complete_step(CodeCacheExtensionsSteps::LastStep);
Thread * thr_cur = ThreadLocalStorage::get_thread_slow();
Thread * thr_cur = Thread::current();
assert(SafepointSynchronize::is_at_safepoint(), "must be at safepoint already");
@ -400,7 +400,7 @@ int VM_Exit::wait_for_threads_in_native_to_block() {
// to wait for threads in _thread_in_native state to be quiescent.
assert(SafepointSynchronize::is_at_safepoint(), "must be at safepoint already");
Thread * thr_cur = ThreadLocalStorage::get_thread_slow();
Thread * thr_cur = Thread::current();
Monitor timer(Mutex::leaf, "VM_Exit timer", true,
Monitor::_safepoint_check_never);
@ -477,7 +477,7 @@ void VM_Exit::doit() {
void VM_Exit::wait_if_vm_exited() {
if (_vm_exited &&
ThreadLocalStorage::get_thread_slow() != _shutdown_thread) {
Thread::current_or_null() != _shutdown_thread) {
// _vm_exited is set at safepoint, and the Threads_lock is never released
// we will block here until the process dies
Threads_lock->lock_without_safepoint_check();

Some files were not shown because too many files have changed in this diff Show More