Fri, 27 Sep 2019 13:23:32 +0800
8227011: Starting a JFR recording in response to JVMTI VMInit and / or Java agent premain corrupts memory
Reviewed-by: egahlin, rwestberg
1.1 --- a/src/share/vm/jfr/recorder/jfrRecorder.cpp Fri Sep 27 10:27:29 2019 +0800 1.2 +++ b/src/share/vm/jfr/recorder/jfrRecorder.cpp Fri Sep 27 13:23:32 2019 +0800 1.3 @@ -189,9 +189,6 @@ 1.4 if (!validate_recording_options(thread)) { 1.5 return false; 1.6 } 1.7 - if (!JfrJavaEventWriter::initialize()) { 1.8 - return false; 1.9 - } 1.10 if (!JfrOptionSet::configure(thread)) { 1.11 return false; 1.12 } 1.13 @@ -235,6 +232,9 @@ 1.14 ResourceMark rm; 1.15 HandleMark hm; 1.16 1.17 + if (!create_java_event_writer()) { 1.18 + return false; 1.19 + } 1.20 if (!create_jvmti_agent()) { 1.21 return false; 1.22 } 1.23 @@ -276,6 +276,10 @@ 1.24 static JfrOSInterface* _os_interface = NULL; 1.25 static JfrThreadSampling* _thread_sampling = NULL; 1.26 1.27 +bool JfrRecorder::create_java_event_writer() { 1.28 + return JfrJavaEventWriter::initialize(); 1.29 +} 1.30 + 1.31 bool JfrRecorder::create_jvmti_agent() { 1.32 return JfrOptionSet::allow_retransforms() ? JfrJvmtiAgent::create() : true; 1.33 }
2.1 --- a/src/share/vm/jfr/recorder/jfrRecorder.hpp Fri Sep 27 10:27:29 2019 +0800 2.2 +++ b/src/share/vm/jfr/recorder/jfrRecorder.hpp Fri Sep 27 13:23:32 2019 +0800 2.3 @@ -42,6 +42,7 @@ 2.4 2.5 static bool create_checkpoint_manager(); 2.6 static bool create_chunk_repository(); 2.7 + static bool create_java_event_writer(); 2.8 static bool create_jvmti_agent(); 2.9 static bool create_os_interface(); 2.10 static bool create_post_box();
3.1 --- a/src/share/vm/jfr/writers/jfrJavaEventWriter.cpp Fri Sep 27 10:27:29 2019 +0800 3.2 +++ b/src/share/vm/jfr/writers/jfrJavaEventWriter.cpp Fri Sep 27 13:23:32 2019 +0800 3.3 @@ -142,8 +142,7 @@ 3.4 bool JfrJavaEventWriter::initialize() { 3.5 static bool initialized = false; 3.6 if (!initialized) { 3.7 - Thread* thread = Thread::current(); 3.8 - initialized = setup_event_writer_offsets(thread); 3.9 + initialized = setup_event_writer_offsets(Thread::current()); 3.10 } 3.11 return initialized; 3.12 } 3.13 @@ -162,6 +161,7 @@ 3.14 // large enough to accommodate the "requested size". 3.15 const bool is_valid = buffer->free_size() >= (size_t)(used + requested); 3.16 u1* const new_current_position = is_valid ? buffer->pos() + used : buffer->pos(); 3.17 + assert(start_pos_offset != invalid_offset, "invariant"); 3.18 w->long_field_put(start_pos_offset, (jlong)buffer->pos()); 3.19 w->long_field_put(current_pos_offset, (jlong)new_current_position); 3.20 // only update java writer if underlying memory changed
4.1 --- a/src/share/vm/jfr/writers/jfrJavaEventWriter.hpp Fri Sep 27 10:27:29 2019 +0800 4.2 +++ b/src/share/vm/jfr/writers/jfrJavaEventWriter.hpp Fri Sep 27 13:23:32 2019 +0800 4.3 @@ -33,14 +33,15 @@ 4.4 4.5 class JfrJavaEventWriter : AllStatic { 4.6 friend class JfrCheckpointThreadClosure; 4.7 + friend class JfrJavaEventWriterNotificationClosure; 4.8 friend class JfrJavaEventWriterNotifyOperation; 4.9 - friend class JfrJavaEventWriterNotificationClosure; 4.10 + friend class JfrRecorder; 4.11 private: 4.12 + static bool initialize(); 4.13 static void notify(JavaThread* jt); 4.14 4.15 public: 4.16 static bool has_required_classes(TRAPS); 4.17 - static bool initialize(); 4.18 static void notify(); 4.19 static jobject event_writer(Thread* t); 4.20 static jobject new_event_writer(TRAPS);