@@ -117,9 +117,9 @@ bool frame::safe_for_sender(JavaThread *thread) {
117
117
return false ;
118
118
}
119
119
120
- common_abi* sender_abi = (common_abi*) fp;
120
+ volatile common_abi* sender_abi = (common_abi*) fp; // May get updated concurrently by deoptimization!
121
121
intptr_t * sender_sp = (intptr_t *) fp;
122
- address sender_pc = (address) sender_abi->lr ;;
122
+ address sender_pc = (address) sender_abi->lr ;
123
123
124
124
if (Continuation::is_return_barrier_entry (sender_pc)) {
125
125
// If our sender_pc is the return barrier, then our "real" sender is the continuation entry
@@ -134,9 +134,18 @@ bool frame::safe_for_sender(JavaThread *thread) {
134
134
return false ;
135
135
}
136
136
137
+ intptr_t * unextended_sender_sp = is_interpreted_frame () ? interpreter_frame_sender_sp () : sender_sp;
138
+
139
+ // If the sender is a deoptimized nmethod we need to check if the original pc is valid.
140
+ nmethod* sender_nm = sender_blob->as_nmethod_or_null ();
141
+ if (sender_nm != nullptr && sender_nm->is_deopt_pc (sender_pc)) {
142
+ address orig_pc = *(address*)((address)unextended_sender_sp + sender_nm->orig_pc_offset ());
143
+ if (!sender_nm->insts_contains_inclusive (orig_pc)) return false ;
144
+ }
145
+
137
146
// It should be safe to construct the sender though it might not be valid.
138
147
139
- frame sender (sender_sp, sender_pc, nullptr /* unextended_sp */ , nullptr /* fp */ , sender_blob);
148
+ frame sender (sender_sp, sender_pc, unextended_sender_sp , nullptr /* fp */ , sender_blob);
140
149
141
150
// Do we have a valid fp?
142
151
address sender_fp = (address) sender.fp ();
0 commit comments