4178 }
4179
4180 protected void genNewInstance(int cpi) {
4181 JavaType type = lookupType(cpi, NEW);
4182 genNewInstance(type);
4183 }
4184
4185 protected void genNewInstance(JavaType type) {
4186 if (typeIsResolved(type)) {
4187 genNewInstance((ResolvedJavaType) type);
4188 } else {
4189 handleUnresolvedNewInstance(type);
4190 }
4191 }
4192
4193 protected void genNewInstance(ResolvedJavaType resolvedType) {
4194 if (resolvedType.isAbstract() || resolvedType.isInterface()) {
4195 handleIllegalNewInstance(resolvedType);
4196 return;
4197 }
4198
4199 maybeEagerlyInitialize(resolvedType);
4200
4201 ClassInitializationPlugin classInitializationPlugin = graphBuilderConfig.getPlugins().getClassInitializationPlugin();
4202 if (!resolvedType.isInitialized() && classInitializationPlugin == null) {
4203 handleIllegalNewInstance(resolvedType);
4204 return;
4205 }
4206
4207 ResolvedJavaType[] skippedExceptionTypes = this.graphBuilderConfig.getSkippedExceptionTypes();
4208 if (skippedExceptionTypes != null) {
4209 for (ResolvedJavaType exceptionType : skippedExceptionTypes) {
4210 if (exceptionType.isAssignableFrom(resolvedType)) {
4211 append(new DeoptimizeNode(DeoptimizationAction.InvalidateRecompile, RuntimeConstraint));
4212 return;
4213 }
4214 }
4215 }
4216
4217 if (classInitializationPlugin != null) {
4218 classInitializationPlugin.apply(this, resolvedType, this::createCurrentFrameState);
4492 private void genGetStatic(JavaField field) {
4493 ResolvedJavaField resolvedField = resolveStaticFieldAccess(field, null);
4494 if (resolvedField == null) {
4495 return;
4496 }
4497
4498 if (!parsingIntrinsic() && GeneratePIC.getValue(getOptions())) {
4499 graph.recordField(resolvedField);
4500 }
4501
4502 /*
4503 * Javac does not allow use of "$assertionsDisabled" for a field name but Eclipse does, in
4504 * which case a suffix is added to the generated field.
4505 */
4506 if ((parsingIntrinsic() || graphBuilderConfig.omitAssertions()) && resolvedField.isSynthetic() && resolvedField.getName().startsWith("$assertionsDisabled")) {
4507 frameState.push(field.getJavaKind(), ConstantNode.forBoolean(true, graph));
4508 return;
4509 }
4510
4511 ResolvedJavaType holder = resolvedField.getDeclaringClass();
4512 maybeEagerlyInitialize(holder);
4513 ClassInitializationPlugin classInitializationPlugin = this.graphBuilderConfig.getPlugins().getClassInitializationPlugin();
4514 if (classInitializationPlugin != null) {
4515 classInitializationPlugin.apply(this, holder, this::createCurrentFrameState);
4516 }
4517
4518 for (NodePlugin plugin : graphBuilderConfig.getPlugins().getNodePlugins()) {
4519 if (plugin.handleLoadStaticField(this, resolvedField)) {
4520 return;
4521 }
4522 }
4523
4524 ValueNode fieldRead = append(genLoadField(null, resolvedField));
4525 JavaKind fieldKind = resolvedField.getJavaKind();
4526
4527 pushLoadField(resolvedField, fieldRead, fieldKind);
4528 }
4529
4530 /**
4531 * Pushes a loaded field onto the stack. If the loaded field is volatile, a
4532 * {@link StateSplitProxyNode} is appended so that deoptimization does not deoptimize to a point
4533 * before the field load.
4534 */
4535 private void pushLoadField(ResolvedJavaField resolvedField, ValueNode fieldRead, JavaKind fieldKind) {
4536 if (resolvedField.isVolatile() && fieldRead instanceof LoadFieldNode) {
4537 StateSplitProxyNode readProxy = append(genVolatileFieldReadProxy(fieldRead));
4538 frameState.push(fieldKind, readProxy);
4539 readProxy.setStateAfter(frameState.create(stream.nextBCI(), readProxy));
4540 } else {
4541 frameState.push(fieldKind, fieldRead);
4542 }
4543 }
4544
4545 private ResolvedJavaField resolveStaticFieldAccess(JavaField field, ValueNode value) {
4546 if (field instanceof ResolvedJavaField) {
4547 ResolvedJavaField resolvedField = (ResolvedJavaField) field;
4548 if (resolvedField.getDeclaringClass().isInitialized() || graphBuilderConfig.getPlugins().getClassInitializationPlugin() != null) {
4549 return resolvedField;
4550 }
4551 /*
4552 * Static fields have initialization semantics but may be safely accessed under certain
4553 * conditions while the class is being initialized. Executing in the clinit or init of
4554 * classes which are subtypes of the field holder are sure to be running in a context
4555 * where the access is safe.
4556 */
4557 if (resolvedField.getDeclaringClass().isAssignableFrom(method.getDeclaringClass())) {
4558 if (method.isClassInitializer() || method.isConstructor()) {
4559 return resolvedField;
4560 }
4561 }
4562 }
4563 if (value == null) {
4564 handleUnresolvedLoadField(field, null);
4565 } else {
4566 handleUnresolvedStoreField(field, value, null);
4567
4568 }
4569 return null;
4570 }
4571
4572 protected void genPutStatic(int cpi, int opcode) {
4573 JavaField field = lookupField(cpi, opcode);
4574 genPutStatic(field);
4575 }
4576
4577 protected void genPutStatic(JavaField field) {
4578 int stackSizeBefore = frameState.stackSize();
4579 ValueNode value = frameState.pop(field.getJavaKind());
4580 ResolvedJavaField resolvedField = resolveStaticFieldAccess(field, value);
4581 if (resolvedField == null) {
4582 return;
4583 }
4584
4585 if (!parsingIntrinsic() && GeneratePIC.getValue(getOptions())) {
4586 graph.recordField(resolvedField);
4587 }
4588
4589 ClassInitializationPlugin classInitializationPlugin = this.graphBuilderConfig.getPlugins().getClassInitializationPlugin();
4590 ResolvedJavaType holder = resolvedField.getDeclaringClass();
4591 maybeEagerlyInitialize(holder);
4592 if (classInitializationPlugin != null) {
4593 Supplier<FrameState> stateBefore = () -> {
4594 JavaKind[] pushedSlotKinds = {field.getJavaKind()};
4595 ValueNode[] pushedValues = {value};
4596 FrameState fs = frameState.create(bci(), getNonIntrinsicAncestor(), false, pushedSlotKinds, pushedValues);
4597 assert stackSizeBefore == fs.stackSize();
4598 return fs;
4599 };
4600 classInitializationPlugin.apply(this, holder, stateBefore);
4601 }
4602
4603 for (NodePlugin plugin : graphBuilderConfig.getPlugins().getNodePlugins()) {
4604 if (plugin.handleStoreStaticField(this, resolvedField, value)) {
4605 return;
4606 }
4607 }
4608
4609 genStoreField(null, resolvedField, value);
4610 }
4611
|
4178 }
4179
4180 protected void genNewInstance(int cpi) {
4181 JavaType type = lookupType(cpi, NEW);
4182 genNewInstance(type);
4183 }
4184
4185 protected void genNewInstance(JavaType type) {
4186 if (typeIsResolved(type)) {
4187 genNewInstance((ResolvedJavaType) type);
4188 } else {
4189 handleUnresolvedNewInstance(type);
4190 }
4191 }
4192
4193 protected void genNewInstance(ResolvedJavaType resolvedType) {
4194 if (resolvedType.isAbstract() || resolvedType.isInterface()) {
4195 handleIllegalNewInstance(resolvedType);
4196 return;
4197 }
4198 maybeEagerlyInitialize(resolvedType);
4199
4200 ClassInitializationPlugin classInitializationPlugin = graphBuilderConfig.getPlugins().getClassInitializationPlugin();
4201 if (!resolvedType.isInitialized() && classInitializationPlugin == null) {
4202 handleIllegalNewInstance(resolvedType);
4203 return;
4204 }
4205
4206 ResolvedJavaType[] skippedExceptionTypes = this.graphBuilderConfig.getSkippedExceptionTypes();
4207 if (skippedExceptionTypes != null) {
4208 for (ResolvedJavaType exceptionType : skippedExceptionTypes) {
4209 if (exceptionType.isAssignableFrom(resolvedType)) {
4210 append(new DeoptimizeNode(DeoptimizationAction.InvalidateRecompile, RuntimeConstraint));
4211 return;
4212 }
4213 }
4214 }
4215
4216 if (classInitializationPlugin != null) {
4217 classInitializationPlugin.apply(this, resolvedType, this::createCurrentFrameState);
4491 private void genGetStatic(JavaField field) {
4492 ResolvedJavaField resolvedField = resolveStaticFieldAccess(field, null);
4493 if (resolvedField == null) {
4494 return;
4495 }
4496
4497 if (!parsingIntrinsic() && GeneratePIC.getValue(getOptions())) {
4498 graph.recordField(resolvedField);
4499 }
4500
4501 /*
4502 * Javac does not allow use of "$assertionsDisabled" for a field name but Eclipse does, in
4503 * which case a suffix is added to the generated field.
4504 */
4505 if ((parsingIntrinsic() || graphBuilderConfig.omitAssertions()) && resolvedField.isSynthetic() && resolvedField.getName().startsWith("$assertionsDisabled")) {
4506 frameState.push(field.getJavaKind(), ConstantNode.forBoolean(true, graph));
4507 return;
4508 }
4509
4510 ResolvedJavaType holder = resolvedField.getDeclaringClass();
4511 ClassInitializationPlugin classInitializationPlugin = this.graphBuilderConfig.getPlugins().getClassInitializationPlugin();
4512 if (classInitializationPlugin != null) {
4513 classInitializationPlugin.apply(this, holder, this::createCurrentFrameState);
4514 }
4515
4516 for (NodePlugin plugin : graphBuilderConfig.getPlugins().getNodePlugins()) {
4517 if (plugin.handleLoadStaticField(this, resolvedField)) {
4518 return;
4519 }
4520 }
4521
4522 ValueNode fieldRead = append(genLoadField(null, resolvedField));
4523 JavaKind fieldKind = resolvedField.getJavaKind();
4524
4525 pushLoadField(resolvedField, fieldRead, fieldKind);
4526 }
4527
4528 /**
4529 * Pushes a loaded field onto the stack. If the loaded field is volatile, a
4530 * {@link StateSplitProxyNode} is appended so that deoptimization does not deoptimize to a point
4531 * before the field load.
4532 */
4533 private void pushLoadField(ResolvedJavaField resolvedField, ValueNode fieldRead, JavaKind fieldKind) {
4534 if (resolvedField.isVolatile() && fieldRead instanceof LoadFieldNode) {
4535 StateSplitProxyNode readProxy = append(genVolatileFieldReadProxy(fieldRead));
4536 frameState.push(fieldKind, readProxy);
4537 readProxy.setStateAfter(frameState.create(stream.nextBCI(), readProxy));
4538 } else {
4539 frameState.push(fieldKind, fieldRead);
4540 }
4541 }
4542
4543 private ResolvedJavaField resolveStaticFieldAccess(JavaField field, ValueNode value) {
4544 if (field instanceof ResolvedJavaField) {
4545 ResolvedJavaField resolvedField = (ResolvedJavaField) field;
4546 ResolvedJavaType resolvedType = resolvedField.getDeclaringClass();
4547 maybeEagerlyInitialize(resolvedType);
4548
4549 if (resolvedType.isInitialized() || graphBuilderConfig.getPlugins().getClassInitializationPlugin() != null) {
4550 return resolvedField;
4551 }
4552
4553 /*
4554 * Static fields have initialization semantics but may be safely accessed under certain
4555 * conditions while the class is being initialized. Executing in the clinit or init of
4556 * subclasses (but not implementers) of the field holder are sure to be running in a
4557 * context where the access is safe.
4558 */
4559 if (!resolvedType.isInterface() && resolvedType.isAssignableFrom(method.getDeclaringClass())) {
4560 if (method.isClassInitializer() || method.isConstructor()) {
4561 return resolvedField;
4562 }
4563 }
4564 }
4565 if (value == null) {
4566 handleUnresolvedLoadField(field, null);
4567 } else {
4568 handleUnresolvedStoreField(field, value, null);
4569
4570 }
4571 return null;
4572 }
4573
4574 protected void genPutStatic(int cpi, int opcode) {
4575 JavaField field = lookupField(cpi, opcode);
4576 genPutStatic(field);
4577 }
4578
4579 protected void genPutStatic(JavaField field) {
4580 int stackSizeBefore = frameState.stackSize();
4581 ValueNode value = frameState.pop(field.getJavaKind());
4582 ResolvedJavaField resolvedField = resolveStaticFieldAccess(field, value);
4583 if (resolvedField == null) {
4584 return;
4585 }
4586
4587 if (!parsingIntrinsic() && GeneratePIC.getValue(getOptions())) {
4588 graph.recordField(resolvedField);
4589 }
4590
4591 ClassInitializationPlugin classInitializationPlugin = this.graphBuilderConfig.getPlugins().getClassInitializationPlugin();
4592 ResolvedJavaType holder = resolvedField.getDeclaringClass();
4593 if (classInitializationPlugin != null) {
4594 Supplier<FrameState> stateBefore = () -> {
4595 JavaKind[] pushedSlotKinds = {field.getJavaKind()};
4596 ValueNode[] pushedValues = {value};
4597 FrameState fs = frameState.create(bci(), getNonIntrinsicAncestor(), false, pushedSlotKinds, pushedValues);
4598 assert stackSizeBefore == fs.stackSize();
4599 return fs;
4600 };
4601 classInitializationPlugin.apply(this, holder, stateBefore);
4602 }
4603
4604 for (NodePlugin plugin : graphBuilderConfig.getPlugins().getNodePlugins()) {
4605 if (plugin.handleStoreStaticField(this, resolvedField, value)) {
4606 return;
4607 }
4608 }
4609
4610 genStoreField(null, resolvedField, value);
4611 }
4612
|