mirror of
https://github.com/openjdk/jdk.git
synced 2025-09-18 18:14:38 +02:00
8206003: SafepointSynchronize with TLH: StoreStore barriers should be moved out of the loop
Reviewed-by: eosterlund, rehn, dholmes
This commit is contained in:
parent
e02646e05b
commit
4f2abf069a
6 changed files with 24 additions and 5 deletions
|
@ -297,12 +297,12 @@ HandshakeState::HandshakeState() : _operation(NULL), _semaphore(1), _thread_in_p
|
||||||
|
|
||||||
void HandshakeState::set_operation(JavaThread* target, HandshakeOperation* op) {
|
void HandshakeState::set_operation(JavaThread* target, HandshakeOperation* op) {
|
||||||
_operation = op;
|
_operation = op;
|
||||||
SafepointMechanism::arm_local_poll(target);
|
SafepointMechanism::arm_local_poll_release(target);
|
||||||
}
|
}
|
||||||
|
|
||||||
void HandshakeState::clear_handshake(JavaThread* target) {
|
void HandshakeState::clear_handshake(JavaThread* target) {
|
||||||
_operation = NULL;
|
_operation = NULL;
|
||||||
SafepointMechanism::disarm_local_poll(target);
|
SafepointMechanism::disarm_local_poll_release(target);
|
||||||
}
|
}
|
||||||
|
|
||||||
void HandshakeState::process_self_inner(JavaThread* thread) {
|
void HandshakeState::process_self_inner(JavaThread* thread) {
|
||||||
|
|
|
@ -243,9 +243,10 @@ void SafepointSynchronize::begin() {
|
||||||
if (SafepointMechanism::uses_thread_local_poll()) {
|
if (SafepointMechanism::uses_thread_local_poll()) {
|
||||||
// Arming the per thread poll while having _state != _not_synchronized means safepointing
|
// Arming the per thread poll while having _state != _not_synchronized means safepointing
|
||||||
log_trace(safepoint)("Setting thread local yield flag for threads");
|
log_trace(safepoint)("Setting thread local yield flag for threads");
|
||||||
|
OrderAccess::storestore(); // storestore, global state -> local state
|
||||||
for (JavaThreadIteratorWithHandle jtiwh; JavaThread *cur = jtiwh.next(); ) {
|
for (JavaThreadIteratorWithHandle jtiwh; JavaThread *cur = jtiwh.next(); ) {
|
||||||
// Make sure the threads start polling, it is time to yield.
|
// Make sure the threads start polling, it is time to yield.
|
||||||
SafepointMechanism::arm_local_poll(cur); // release store, global state -> local state
|
SafepointMechanism::arm_local_poll(cur);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
OrderAccess::fence(); // storestore|storeload, global state -> local state
|
OrderAccess::fence(); // storestore|storeload, global state -> local state
|
||||||
|
@ -546,7 +547,7 @@ void SafepointSynchronize::end() {
|
||||||
for (; JavaThread *current = jtiwh.next(); ) {
|
for (; JavaThread *current = jtiwh.next(); ) {
|
||||||
ThreadSafepointState* cur_state = current->safepoint_state();
|
ThreadSafepointState* cur_state = current->safepoint_state();
|
||||||
cur_state->restart(); // TSS _running
|
cur_state->restart(); // TSS _running
|
||||||
SafepointMechanism::disarm_local_poll(current); // release store, local state -> polling page
|
SafepointMechanism::disarm_local_poll(current);
|
||||||
}
|
}
|
||||||
log_info(safepoint)("Leaving safepoint region");
|
log_info(safepoint)("Leaving safepoint region");
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -79,9 +79,13 @@ public:
|
||||||
// Blocks a thread until safepoint is completed
|
// Blocks a thread until safepoint is completed
|
||||||
static inline void block_if_requested(JavaThread* thread);
|
static inline void block_if_requested(JavaThread* thread);
|
||||||
|
|
||||||
|
// Caller is responsible for using a memory barrier if needed.
|
||||||
static inline void arm_local_poll(JavaThread* thread);
|
static inline void arm_local_poll(JavaThread* thread);
|
||||||
static inline void disarm_local_poll(JavaThread* thread);
|
static inline void disarm_local_poll(JavaThread* thread);
|
||||||
|
|
||||||
|
static inline void arm_local_poll_release(JavaThread* thread);
|
||||||
|
static inline void disarm_local_poll_release(JavaThread* thread);
|
||||||
|
|
||||||
// Setup the selected safepoint mechanism
|
// Setup the selected safepoint mechanism
|
||||||
static void initialize();
|
static void initialize();
|
||||||
static void initialize_header(JavaThread* thread);
|
static void initialize_header(JavaThread* thread);
|
||||||
|
|
|
@ -87,4 +87,12 @@ void SafepointMechanism::disarm_local_poll(JavaThread* thread) {
|
||||||
thread->set_polling_page(poll_disarmed_value());
|
thread->set_polling_page(poll_disarmed_value());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void SafepointMechanism::arm_local_poll_release(JavaThread* thread) {
|
||||||
|
thread->set_polling_page_release(poll_armed_value());
|
||||||
|
}
|
||||||
|
|
||||||
|
void SafepointMechanism::disarm_local_poll_release(JavaThread* thread) {
|
||||||
|
thread->set_polling_page_release(poll_disarmed_value());
|
||||||
|
}
|
||||||
|
|
||||||
#endif // SHARE_VM_RUNTIME_SAFEPOINTMECHANISM_INLINE_HPP
|
#endif // SHARE_VM_RUNTIME_SAFEPOINTMECHANISM_INLINE_HPP
|
||||||
|
|
|
@ -1207,6 +1207,7 @@ class JavaThread: public Thread {
|
||||||
bool do_not_unlock_if_synchronized() { return _do_not_unlock_if_synchronized; }
|
bool do_not_unlock_if_synchronized() { return _do_not_unlock_if_synchronized; }
|
||||||
void set_do_not_unlock_if_synchronized(bool val) { _do_not_unlock_if_synchronized = val; }
|
void set_do_not_unlock_if_synchronized(bool val) { _do_not_unlock_if_synchronized = val; }
|
||||||
|
|
||||||
|
inline void set_polling_page_release(void* poll_value);
|
||||||
inline void set_polling_page(void* poll_value);
|
inline void set_polling_page(void* poll_value);
|
||||||
inline volatile void* get_polling_page();
|
inline volatile void* get_polling_page();
|
||||||
|
|
||||||
|
|
|
@ -170,10 +170,15 @@ inline bool JavaThread::stack_guards_enabled() {
|
||||||
|
|
||||||
// The release make sure this store is done after storing the handshake
|
// The release make sure this store is done after storing the handshake
|
||||||
// operation or global state
|
// operation or global state
|
||||||
inline void JavaThread::set_polling_page(void* poll_value) {
|
inline void JavaThread::set_polling_page_release(void* poll_value) {
|
||||||
OrderAccess::release_store(polling_page_addr(), poll_value);
|
OrderAccess::release_store(polling_page_addr(), poll_value);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Caller is responsible for using a memory barrier if needed.
|
||||||
|
inline void JavaThread::set_polling_page(void* poll_value) {
|
||||||
|
*polling_page_addr() = poll_value;
|
||||||
|
}
|
||||||
|
|
||||||
// The aqcquire make sure reading of polling page is done before
|
// The aqcquire make sure reading of polling page is done before
|
||||||
// the reading the handshake operation or the global state
|
// the reading the handshake operation or the global state
|
||||||
inline volatile void* JavaThread::get_polling_page() {
|
inline volatile void* JavaThread::get_polling_page() {
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue