Skip to content

Commit 3fc2502

Browse files
committed
Reflecting review comments on SwitchBootstraps.
1 parent 5e663d7 commit 3fc2502

File tree

1 file changed

+30
-46
lines changed

1 file changed

+30
-46
lines changed

src/java.base/share/classes/java/lang/runtime/SwitchBootstraps.java

Lines changed: 30 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -58,26 +58,18 @@ private SwitchBootstraps() {}
5858

5959
private static final MethodHandles.Lookup LOOKUP = MethodHandles.lookup();
6060

61-
//typeSwitch implementation:
62-
private static final MethodHandle TYPE_INIT_HOOK;
63-
private static final MethodHandle TYPE_SWITCH_METHOD;
61+
private static final MethodHandle DO_SWITCH;
6462

6563
static {
6664
try {
67-
TYPE_INIT_HOOK = LOOKUP.findStatic(SwitchBootstraps.class, "typeInitHook",
68-
MethodType.methodType(MethodHandle.class, CallSite.class));
69-
TYPE_SWITCH_METHOD = LOOKUP.findVirtual(TypeSwitchCallSite.class, "doSwitch",
70-
MethodType.methodType(int.class, Object.class, int.class));
65+
DO_SWITCH = LOOKUP.findStatic(SwitchBootstraps.class, "doSwitch",
66+
MethodType.methodType(int.class, Object.class, int.class, Object[].class));
7167
}
7268
catch (ReflectiveOperationException e) {
7369
throw new ExceptionInInitializerError(e);
7470
}
7571
}
7672

77-
private static<T extends CallSite> MethodHandle typeInitHook(T receiver) {
78-
return TYPE_SWITCH_METHOD.bindTo(receiver);
79-
}
80-
8173
/**
8274
* Bootstrap method for linking an {@code invokedynamic} call site that
8375
* implements a {@code switch} on a reference-typed target. The static
@@ -124,56 +116,48 @@ public static CallSite typeSwitch(MethodHandles.Lookup lookup,
124116
labels = labels.clone();
125117
Stream.of(labels).forEach(SwitchBootstraps::verifyLabel);
126118

127-
return new TypeSwitchCallSite(invocationType, labels);
119+
MethodHandle target = MethodHandles.insertArguments(DO_SWITCH, 2, (Object) labels);
120+
return new ConstantCallSite(target);
128121
}
129122

130123
private static void verifyLabel(Object label) {
131-
if (Objects.isNull(label)) {
124+
if (label == null) {
132125
throw new IllegalArgumentException("null label found");
133126
}
134-
if (label.getClass() != Class.class &&
135-
label.getClass() != String.class &&
136-
label.getClass() != Integer.class) {
127+
Class<?> labelClass = label.getClass();
128+
if (labelClass != Class.class &&
129+
labelClass != String.class &&
130+
labelClass != Integer.class) {
137131
throw new IllegalArgumentException("label with illegal type found: " + label.getClass());
138132
}
139133
}
140134

141-
static class TypeSwitchCallSite extends ConstantCallSite {
142-
private final Object[] labels;
143-
144-
TypeSwitchCallSite(MethodType targetType,
145-
Object[] labels) throws Throwable {
146-
super(targetType, TYPE_INIT_HOOK);
147-
this.labels = labels;
148-
}
149-
150-
int doSwitch(Object target, int startIndex) {
151-
if (target == null)
152-
return -1;
153-
154-
// Dumbest possible strategy
155-
Class<?> targetClass = target.getClass();
156-
for (int i = startIndex; i < labels.length; i++) {
157-
if (labels[i] instanceof Class<?>) {
158-
Class<?> c = (Class<?>) labels[i];
159-
if (c.isAssignableFrom(targetClass))
135+
private static int doSwitch(Object target, int startIndex, Object[] labels) {
136+
if (target == null)
137+
return -1;
138+
139+
// Dumbest possible strategy
140+
Class<?> targetClass = target.getClass();
141+
for (int i = startIndex; i < labels.length; i++) {
142+
Object label = labels[i];
143+
if (label instanceof Class<?> c) {
144+
if (c.isAssignableFrom(targetClass))
145+
return i;
146+
} else {
147+
if (label instanceof Integer constant) {
148+
if (target instanceof Number input && constant.intValue() == input.intValue()) {
160149
return i;
161-
} else {
162-
if (labels[i] instanceof Integer constant) {
163-
if (target instanceof Number input && constant.intValue() == input.intValue()) {
164-
return i;
165-
}
166-
if (target instanceof Character input && constant.intValue() == input.charValue()) {
167-
return i;
168-
}
169-
} else if (labels[i].equals(target)) {
150+
}
151+
if (target instanceof Character input && constant.intValue() == input.charValue()) {
170152
return i;
171153
}
154+
} else if (label.equals(target)) {
155+
return i;
172156
}
173157
}
174-
175-
return labels.length;
176158
}
159+
160+
return labels.length;
177161
}
178162

179163
}

0 commit comments

Comments
 (0)