Mercurial > hg > graal-jvmci-8
comparison src/share/vm/jvmci/jvmciCodeInstaller.cpp @ 22478:822922922f3c
Explicitly store slot kinds in DebugInfo.
author | Roland Schatz <roland.schatz@oracle.com> |
---|---|
date | Fri, 28 Aug 2015 13:18:24 +0200 |
parents | 76af33d4d504 |
children | da68ca58b271 |
comparison
equal
deleted
inserted
replaced
22477:c3ad14a83248 | 22478:822922922f3c |
---|---|
176 | 176 |
177 static void record_metadata_in_patch(Handle& constant, OopRecorder* oop_recorder) { | 177 static void record_metadata_in_patch(Handle& constant, OopRecorder* oop_recorder) { |
178 record_metadata_reference(HotSpotMetaspaceConstantImpl::metaspaceObject(constant), HotSpotMetaspaceConstantImpl::primitive(constant), HotSpotMetaspaceConstantImpl::compressed(constant), oop_recorder); | 178 record_metadata_reference(HotSpotMetaspaceConstantImpl::metaspaceObject(constant), HotSpotMetaspaceConstantImpl::primitive(constant), HotSpotMetaspaceConstantImpl::compressed(constant), oop_recorder); |
179 } | 179 } |
180 | 180 |
181 ScopeValue* CodeInstaller::get_scope_value(oop value, GrowableArray<ScopeValue*>* objects, ScopeValue* &second) { | 181 static Location::Type get_oop_type(oop value) { |
182 oop lirKind = AbstractValue::lirKind(value); | |
183 oop platformKind = LIRKind::platformKind(lirKind); | |
184 assert(LIRKind::referenceMask(lirKind) == 1, "unexpected referenceMask"); | |
185 | |
186 if (JVMCIRuntime::kindToBasicType(Kind::typeChar(platformKind)) == T_INT) { | |
187 return Location::narrowoop; | |
188 } else { | |
189 return Location::oop; | |
190 } | |
191 } | |
192 | |
193 ScopeValue* CodeInstaller::get_scope_value(oop value, BasicType type, GrowableArray<ScopeValue*>* objects, ScopeValue* &second) { | |
182 second = NULL; | 194 second = NULL; |
183 if (value == AbstractValue::ILLEGAL()) { | 195 if (value == AbstractValue::ILLEGAL()) { |
196 assert(type == T_ILLEGAL, "expected legal value"); | |
184 return _illegal_value; | 197 return _illegal_value; |
185 } | 198 } else if (value->is_a(RegisterValue::klass())) { |
186 | |
187 oop lirKind = AbstractValue::lirKind(value); | |
188 oop platformKind = LIRKind::platformKind(lirKind); | |
189 jint referenceMask = LIRKind::referenceMask(lirKind); | |
190 assert(referenceMask != -1, "derived pointers are not allowed"); | |
191 assert(referenceMask == 0 || referenceMask == 1, "unexpected referenceMask"); | |
192 bool reference = referenceMask == 1; | |
193 | |
194 BasicType type = JVMCIRuntime::kindToBasicType(Kind::typeChar(platformKind)); | |
195 | |
196 if (value->is_a(RegisterValue::klass())) { | |
197 oop reg = RegisterValue::reg(value); | 199 oop reg = RegisterValue::reg(value); |
198 jint number = code_Register::number(reg); | 200 jint number = code_Register::number(reg); |
199 VMReg hotspotRegister = get_hotspot_reg(number); | 201 VMReg hotspotRegister = get_hotspot_reg(number); |
200 if (is_general_purpose_reg(hotspotRegister)) { | 202 if (is_general_purpose_reg(hotspotRegister)) { |
201 Location::Type locationType; | 203 Location::Type locationType; |
202 if (type == T_INT) { | 204 if (type == T_OBJECT) { |
203 locationType = reference ? Location::narrowoop : Location::int_in_long; | 205 locationType = get_oop_type(value); |
204 } else if(type == T_SHORT || type == T_CHAR || type == T_BYTE || type == T_BOOLEAN) { | 206 } else if (type == T_LONG) { |
207 locationType = Location::lng; | |
208 } else { | |
209 assert(type == T_INT || type == T_FLOAT || type == T_SHORT || type == T_CHAR || type == T_BYTE || type == T_BOOLEAN, "unexpected type in cpu register"); | |
205 locationType = Location::int_in_long; | 210 locationType = Location::int_in_long; |
206 } else if (type == T_FLOAT) { | |
207 locationType = Location::int_in_long; | |
208 } else if (type == T_LONG) { | |
209 locationType = reference ? Location::oop : Location::lng; | |
210 } else { | |
211 assert(type == T_OBJECT && reference, "unexpected type in cpu register"); | |
212 locationType = Location::oop; | |
213 } | 211 } |
214 ScopeValue* value = new LocationValue(Location::new_reg_loc(locationType, hotspotRegister)); | 212 ScopeValue* value = new LocationValue(Location::new_reg_loc(locationType, hotspotRegister)); |
215 if (type == T_LONG && !reference) { | 213 if (type == T_LONG) { |
216 second = value; | 214 second = value; |
217 } | 215 } |
218 return value; | 216 return value; |
219 } else { | 217 } else { |
220 assert(type == T_FLOAT || type == T_DOUBLE, "only float and double expected in xmm register"); | 218 assert(type == T_FLOAT || type == T_DOUBLE, "only float and double expected in xmm register"); |
223 // this seems weird, but the same value is used in c1_LinearScan | 221 // this seems weird, but the same value is used in c1_LinearScan |
224 locationType = Location::normal; | 222 locationType = Location::normal; |
225 } else { | 223 } else { |
226 locationType = Location::dbl; | 224 locationType = Location::dbl; |
227 } | 225 } |
228 assert(!reference, "unexpected type in floating point register"); | |
229 ScopeValue* value = new LocationValue(Location::new_reg_loc(locationType, hotspotRegister)); | 226 ScopeValue* value = new LocationValue(Location::new_reg_loc(locationType, hotspotRegister)); |
230 if (type == T_DOUBLE) { | 227 if (type == T_DOUBLE) { |
231 second = value; | 228 second = value; |
232 } | 229 } |
233 return value; | 230 return value; |
237 if (StackSlot::addFrameSize(value)) { | 234 if (StackSlot::addFrameSize(value)) { |
238 offset += _total_frame_size; | 235 offset += _total_frame_size; |
239 } | 236 } |
240 | 237 |
241 Location::Type locationType; | 238 Location::Type locationType; |
242 if (type == T_LONG) { | 239 if (type == T_OBJECT) { |
243 locationType = reference ? Location::oop : Location::lng; | 240 locationType = get_oop_type(value); |
244 } else if (type == T_INT) { | 241 } else if (type == T_LONG) { |
245 locationType = reference ? Location::narrowoop : Location::normal; | 242 locationType = Location::lng; |
246 } else if(type == T_SHORT || type == T_CHAR || type == T_BYTE || type == T_BOOLEAN) { | |
247 locationType = Location::normal; | |
248 } else if (type == T_FLOAT) { | |
249 assert(!reference, "unexpected type in stack slot"); | |
250 locationType = Location::normal; | |
251 } else if (type == T_DOUBLE) { | 243 } else if (type == T_DOUBLE) { |
252 assert(!reference, "unexpected type in stack slot"); | |
253 locationType = Location::dbl; | 244 locationType = Location::dbl; |
254 } else { | 245 } else { |
255 assert(type == T_OBJECT && reference, "unexpected type in stack slot"); | 246 assert(type == T_INT || type == T_FLOAT || type == T_SHORT || type == T_CHAR || type == T_BYTE || type == T_BOOLEAN, "unexpected type in stack slot"); |
256 locationType = Location::oop; | 247 locationType = Location::normal; |
257 } | 248 } |
258 ScopeValue* value = new LocationValue(Location::new_stk_loc(locationType, offset)); | 249 ScopeValue* value = new LocationValue(Location::new_stk_loc(locationType, offset)); |
259 if (type == T_DOUBLE || (type == T_LONG && !reference)) { | 250 if (type == T_DOUBLE || type == T_LONG) { |
260 second = value; | 251 second = value; |
261 } | 252 } |
262 return value; | 253 return value; |
263 } else if (value->is_a(JavaConstant::klass())){ | 254 } else if (value->is_a(JavaConstant::klass())) { |
264 record_metadata_in_constant(value, _oop_recorder); | 255 record_metadata_in_constant(value, _oop_recorder); |
265 if (value->is_a(PrimitiveConstant::klass())) { | 256 if (value->is_a(PrimitiveConstant::klass())) { |
266 assert(!reference, "unexpected primitive constant type"); | 257 if (value->is_a(RawConstant::klass())) { |
267 if(value->is_a(RawConstant::klass())) { | |
268 jlong prim = PrimitiveConstant::primitive(value); | 258 jlong prim = PrimitiveConstant::primitive(value); |
269 return new ConstantLongValue(prim); | 259 return new ConstantLongValue(prim); |
270 } else if (type == T_INT || type == T_FLOAT) { | 260 } else { |
271 jint prim = (jint)PrimitiveConstant::primitive(value); | 261 assert(type == JVMCIRuntime::kindToBasicType(Kind::typeChar(PrimitiveConstant::kind(value))), "primitive constant type doesn't match"); |
272 switch (prim) { | 262 if (type == T_INT || type == T_FLOAT) { |
273 case -1: return _int_m1_scope_value; | 263 jint prim = (jint)PrimitiveConstant::primitive(value); |
274 case 0: return _int_0_scope_value; | 264 switch (prim) { |
275 case 1: return _int_1_scope_value; | 265 case -1: return _int_m1_scope_value; |
276 case 2: return _int_2_scope_value; | 266 case 0: return _int_0_scope_value; |
277 default: return new ConstantIntValue(prim); | 267 case 1: return _int_1_scope_value; |
268 case 2: return _int_2_scope_value; | |
269 default: return new ConstantIntValue(prim); | |
270 } | |
271 } else { | |
272 assert(type == T_LONG || type == T_DOUBLE, "unexpected primitive constant type"); | |
273 jlong prim = PrimitiveConstant::primitive(value); | |
274 second = _int_1_scope_value; | |
275 return new ConstantLongValue(prim); | |
278 } | 276 } |
279 } else { | |
280 assert(type == T_LONG || type == T_DOUBLE, "unexpected primitive constant type"); | |
281 jlong prim = PrimitiveConstant::primitive(value); | |
282 second = _int_1_scope_value; | |
283 return new ConstantLongValue(prim); | |
284 } | 277 } |
285 } else { | 278 } else { |
286 assert(reference, "unexpected object constant type"); | 279 assert(type == T_OBJECT, "unexpected object constant"); |
287 if (value->is_a(NullConstant::klass()) || value->is_a(HotSpotCompressedNullConstant::klass())) { | 280 if (value->is_a(NullConstant::klass()) || value->is_a(HotSpotCompressedNullConstant::klass())) { |
288 return _oop_null_scope_value; | 281 return _oop_null_scope_value; |
289 } else { | 282 } else { |
290 assert(value->is_a(HotSpotObjectConstantImpl::klass()), "unexpected constant type"); | 283 assert(value->is_a(HotSpotObjectConstantImpl::klass()), "unexpected constant type"); |
291 oop obj = HotSpotObjectConstantImpl::object(value); | 284 oop obj = HotSpotObjectConstantImpl::object(value); |
292 assert(obj != NULL, "null value must be in NullConstant"); | 285 assert(obj != NULL, "null value must be in NullConstant"); |
293 return new ConstantOopWriteValue(JNIHandles::make_local(obj)); | 286 return new ConstantOopWriteValue(JNIHandles::make_local(obj)); |
294 } | 287 } |
295 } | 288 } |
296 } else if (value->is_a(VirtualObject::klass())) { | 289 } else if (value->is_a(VirtualObject::klass())) { |
290 assert(type == T_OBJECT, "unexpected virtual object"); | |
297 int id = VirtualObject::id(value); | 291 int id = VirtualObject::id(value); |
298 ScopeValue* object = objects->at(id); | 292 ScopeValue* object = objects->at(id); |
299 assert(object != NULL, "missing value"); | 293 assert(object != NULL, "missing value"); |
300 return object; | 294 return object; |
301 } else { | 295 } else { |
312 oop javaMirror = HotSpotResolvedObjectTypeImpl::javaClass(type); | 306 oop javaMirror = HotSpotResolvedObjectTypeImpl::javaClass(type); |
313 Klass* klass = java_lang_Class::as_Klass(javaMirror); | 307 Klass* klass = java_lang_Class::as_Klass(javaMirror); |
314 bool isLongArray = klass == Universe::longArrayKlassObj(); | 308 bool isLongArray = klass == Universe::longArrayKlassObj(); |
315 | 309 |
316 objArrayOop values = VirtualObject::values(value); | 310 objArrayOop values = VirtualObject::values(value); |
311 objArrayOop slotKinds = VirtualObject::slotKinds(value); | |
317 for (jint i = 0; i < values->length(); i++) { | 312 for (jint i = 0; i < values->length(); i++) { |
318 ScopeValue* cur_second = NULL; | 313 ScopeValue* cur_second = NULL; |
319 oop object = values->obj_at(i); | 314 oop object = values->obj_at(i); |
320 ScopeValue* value = get_scope_value(object, objects, cur_second); | 315 oop kind = slotKinds->obj_at(i); |
316 BasicType type = JVMCIRuntime::kindToBasicType(Kind::typeChar(kind)); | |
317 ScopeValue* value = get_scope_value(object, type, objects, cur_second); | |
321 | 318 |
322 if (isLongArray && cur_second == NULL) { | 319 if (isLongArray && cur_second == NULL) { |
323 // we're trying to put ints into a long array... this isn't really valid, but it's used for some optimizations. | 320 // we're trying to put ints into a long array... this isn't really valid, but it's used for some optimizations. |
324 // add an int 0 constant | 321 // add an int 0 constant |
325 cur_second = _int_0_scope_value; | 322 cur_second = _int_0_scope_value; |
332 sv->field_values()->append(value); | 329 sv->field_values()->append(value); |
333 } | 330 } |
334 } | 331 } |
335 | 332 |
336 MonitorValue* CodeInstaller::get_monitor_value(oop value, GrowableArray<ScopeValue*>* objects) { | 333 MonitorValue* CodeInstaller::get_monitor_value(oop value, GrowableArray<ScopeValue*>* objects) { |
337 guarantee(value->is_a(StackLockValue::klass()), "Monitors must be of type MonitorValue"); | 334 guarantee(value->is_a(StackLockValue::klass()), "Monitors must be of type StackLockValue"); |
338 | 335 |
339 ScopeValue* second = NULL; | 336 ScopeValue* second = NULL; |
340 ScopeValue* owner_value = get_scope_value(StackLockValue::owner(value), objects, second); | 337 ScopeValue* owner_value = get_scope_value(StackLockValue::owner(value), T_OBJECT, objects, second); |
341 assert(second == NULL, "monitor cannot occupy two stack slots"); | 338 assert(second == NULL, "monitor cannot occupy two stack slots"); |
342 | 339 |
343 ScopeValue* lock_data_value = get_scope_value(StackLockValue::slot(value), objects, second); | 340 ScopeValue* lock_data_value = get_scope_value(StackLockValue::slot(value), T_LONG, objects, second); |
344 assert(second == lock_data_value, "monitor is LONG value that occupies two stack slots"); | 341 assert(second == lock_data_value, "monitor is LONG value that occupies two stack slots"); |
345 assert(lock_data_value->is_location(), "invalid monitor location"); | 342 assert(lock_data_value->is_location(), "invalid monitor location"); |
346 Location lock_data_loc = ((LocationValue*)lock_data_value)->location(); | 343 Location lock_data_loc = ((LocationValue*)lock_data_value)->location(); |
347 | 344 |
348 bool eliminated = false; | 345 bool eliminated = false; |
724 oop position = DebugInfo::bytecodePosition(debug_info); | 721 oop position = DebugInfo::bytecodePosition(debug_info); |
725 if (position == NULL) { | 722 if (position == NULL) { |
726 // Stubs do not record scope info, just oop maps | 723 // Stubs do not record scope info, just oop maps |
727 return; | 724 return; |
728 } | 725 } |
729 | 726 |
730 GrowableArray<ScopeValue*>* objectMapping = record_virtual_objects(debug_info); | 727 GrowableArray<ScopeValue*>* objectMapping = record_virtual_objects(debug_info); |
731 record_scope(pc_offset, position, objectMapping); | 728 record_scope(pc_offset, position, objectMapping); |
732 } | 729 } |
733 | 730 |
734 void CodeInstaller::record_scope(jint pc_offset, oop position, GrowableArray<ScopeValue*>* objects) { | 731 void CodeInstaller::record_scope(jint pc_offset, oop position, GrowableArray<ScopeValue*>* objects) { |
773 if (frame != NULL) { | 770 if (frame != NULL) { |
774 jint local_count = BytecodeFrame::numLocals(frame); | 771 jint local_count = BytecodeFrame::numLocals(frame); |
775 jint expression_count = BytecodeFrame::numStack(frame); | 772 jint expression_count = BytecodeFrame::numStack(frame); |
776 jint monitor_count = BytecodeFrame::numLocks(frame); | 773 jint monitor_count = BytecodeFrame::numLocks(frame); |
777 objArrayOop values = BytecodeFrame::values(frame); | 774 objArrayOop values = BytecodeFrame::values(frame); |
775 objArrayOop slotKinds = BytecodeFrame::slotKinds(frame); | |
778 | 776 |
779 assert(local_count + expression_count + monitor_count == values->length(), "unexpected values length"); | 777 assert(local_count + expression_count + monitor_count == values->length(), "unexpected values length"); |
778 assert(local_count + expression_count == slotKinds->length(), "unexpected slotKinds length"); | |
780 | 779 |
781 GrowableArray<ScopeValue*>* locals = local_count > 0 ? new GrowableArray<ScopeValue*> (local_count) : NULL; | 780 GrowableArray<ScopeValue*>* locals = local_count > 0 ? new GrowableArray<ScopeValue*> (local_count) : NULL; |
782 GrowableArray<ScopeValue*>* expressions = expression_count > 0 ? new GrowableArray<ScopeValue*> (expression_count) : NULL; | 781 GrowableArray<ScopeValue*>* expressions = expression_count > 0 ? new GrowableArray<ScopeValue*> (expression_count) : NULL; |
783 GrowableArray<MonitorValue*>* monitors = monitor_count > 0 ? new GrowableArray<MonitorValue*> (monitor_count) : NULL; | 782 GrowableArray<MonitorValue*>* monitors = monitor_count > 0 ? new GrowableArray<MonitorValue*> (monitor_count) : NULL; |
784 | 783 |
789 | 788 |
790 for (jint i = 0; i < values->length(); i++) { | 789 for (jint i = 0; i < values->length(); i++) { |
791 ScopeValue* second = NULL; | 790 ScopeValue* second = NULL; |
792 oop value = values->obj_at(i); | 791 oop value = values->obj_at(i); |
793 if (i < local_count) { | 792 if (i < local_count) { |
794 ScopeValue* first = get_scope_value(value, objects, second); | 793 oop kind = slotKinds->obj_at(i); |
794 BasicType type = JVMCIRuntime::kindToBasicType(Kind::typeChar(kind)); | |
795 ScopeValue* first = get_scope_value(value, type, objects, second); | |
795 if (second != NULL) { | 796 if (second != NULL) { |
796 locals->append(second); | 797 locals->append(second); |
797 } | 798 } |
798 locals->append(first); | 799 locals->append(first); |
799 } else if (i < local_count + expression_count) { | 800 } else if (i < local_count + expression_count) { |
800 ScopeValue* first = get_scope_value(value, objects, second); | 801 oop kind = slotKinds->obj_at(i); |
802 BasicType type = JVMCIRuntime::kindToBasicType(Kind::typeChar(kind)); | |
803 ScopeValue* first = get_scope_value(value, type, objects, second); | |
801 if (second != NULL) { | 804 if (second != NULL) { |
802 expressions->append(second); | 805 expressions->append(second); |
803 } | 806 } |
804 expressions->append(first); | 807 expressions->append(first); |
805 } else { | 808 } else { |