Categories:
Audio (13)
Biotech (29)
Bytecode (36)
Database (77)
Framework (7)
Game (7)
General (507)
Graphics (53)
I/O (35)
IDE (2)
JAR Tools (101)
JavaBeans (21)
JDBC (121)
JDK (426)
JSP (20)
Logging (108)
Mail (58)
Messaging (8)
Network (84)
PDF (97)
Report (7)
Scripting (84)
Security (32)
Server (121)
Servlet (26)
SOAP (24)
Testing (54)
Web (15)
XML (309)
Collections:
Other Resources:
JRE 8 rt.jar - java.* Package Source Code
JRE 8 rt.jar is the JAR file for JRE 8 RT (Runtime) libraries. JRE (Java Runtime) 8 is the runtime environment included in JDK 8. JRE 8 rt.jar libraries are divided into 6 packages:
com.* - Internal Oracle and Sun Microsystems libraries java.* - Standard Java API libraries. javax.* - Extended Java API libraries. jdk.* - JDK supporting libraries. org.* - Third party libraries. sun.* - Old libraries developed by Sun Microsystems.
JAR File Information:
Directory of C:\fyicenter\jdk-1.8.0_191\jre\lib 63,596,151 rt.jar
Here is the list of Java classes of the java.* package in JRE 1.8.0_191 rt.jar. Java source codes are also provided.
✍: FYIcenter
⏎ java/lang/invoke/BoundMethodHandle.java
/* * Copyright (c) 2008, 2013, Oracle and/or its affiliates. All rights reserved. * ORACLE PROPRIETARY/CONFIDENTIAL. Use is subject to license terms. * * * * * * * * * * * * * * * * * * * * */ package java.lang.invoke; import static jdk.internal.org.objectweb.asm.Opcodes.*; import static java.lang.invoke.LambdaForm.*; import static java.lang.invoke.LambdaForm.BasicType.*; import static java.lang.invoke.MethodHandleStatics.*; import java.lang.invoke.LambdaForm.NamedFunction; import java.lang.invoke.MethodHandles.Lookup; import java.lang.reflect.Field; import java.util.Arrays; import java.util.function.Function; import java.util.concurrent.ConcurrentMap; import java.util.concurrent.ConcurrentHashMap; import jdk.internal.org.objectweb.asm.FieldVisitor; import sun.invoke.util.ValueConversions; import sun.invoke.util.Wrapper; import jdk.internal.org.objectweb.asm.ClassWriter; import jdk.internal.org.objectweb.asm.MethodVisitor; /** * The flavor of method handle which emulates an invoke instruction * on a predetermined argument. The JVM dispatches to the correct method * when the handle is created, not when it is invoked. * * All bound arguments are encapsulated in dedicated species. */ /*non-public*/ abstract class BoundMethodHandle extends MethodHandle { /*non-public*/ BoundMethodHandle(MethodType type, LambdaForm form) { super(type, form); assert(speciesData() == speciesData(form)); } // // BMH API and internals // static BoundMethodHandle bindSingle(MethodType type, LambdaForm form, BasicType xtype, Object x) { // for some type signatures, there exist pre-defined concrete BMH classes try { switch (xtype) { case L_TYPE: return bindSingle(type, form, x); // Use known fast path. case I_TYPE: return (BoundMethodHandle) SpeciesData.EMPTY.extendWith(I_TYPE).constructor().invokeBasic(type, form, ValueConversions.widenSubword(x)); case J_TYPE: return (BoundMethodHandle) SpeciesData.EMPTY.extendWith(J_TYPE).constructor().invokeBasic(type, form, (long) x); case F_TYPE: return (BoundMethodHandle) SpeciesData.EMPTY.extendWith(F_TYPE).constructor().invokeBasic(type, form, (float) x); case D_TYPE: return (BoundMethodHandle) SpeciesData.EMPTY.extendWith(D_TYPE).constructor().invokeBasic(type, form, (double) x); default : throw newInternalError("unexpected xtype: " + xtype); } } catch (Throwable t) { throw newInternalError(t); } } /*non-public*/ LambdaFormEditor editor() { return form.editor(); } static BoundMethodHandle bindSingle(MethodType type, LambdaForm form, Object x) { return Species_L.make(type, form, x); } @Override // there is a default binder in the super class, for 'L' types only /*non-public*/ BoundMethodHandle bindArgumentL(int pos, Object value) { return editor().bindArgumentL(this, pos, value); } /*non-public*/ BoundMethodHandle bindArgumentI(int pos, int value) { return editor().bindArgumentI(this, pos, value); } /*non-public*/ BoundMethodHandle bindArgumentJ(int pos, long value) { return editor().bindArgumentJ(this, pos, value); } /*non-public*/ BoundMethodHandle bindArgumentF(int pos, float value) { return editor().bindArgumentF(this, pos, value); } /*non-public*/ BoundMethodHandle bindArgumentD(int pos, double value) { return editor().bindArgumentD(this, pos, value); } @Override BoundMethodHandle rebind() { if (!tooComplex()) { return this; } return makeReinvoker(this); } private boolean tooComplex() { return (fieldCount() > FIELD_COUNT_THRESHOLD || form.expressionCount() > FORM_EXPRESSION_THRESHOLD); } private static final int FIELD_COUNT_THRESHOLD = 12; // largest convenient BMH field count private static final int FORM_EXPRESSION_THRESHOLD = 24; // largest convenient BMH expression count /** * A reinvoker MH has this form: * {@code lambda (bmh, arg*) { thismh = bmh[0]; invokeBasic(thismh, arg*) }} */ static BoundMethodHandle makeReinvoker(MethodHandle target) { LambdaForm form = DelegatingMethodHandle.makeReinvokerForm( target, MethodTypeForm.LF_REBIND, Species_L.SPECIES_DATA, Species_L.SPECIES_DATA.getterFunction(0)); return Species_L.make(target.type(), form, target); } /** * Return the {@link SpeciesData} instance representing this BMH species. All subclasses must provide a * static field containing this value, and they must accordingly implement this method. */ /*non-public*/ abstract SpeciesData speciesData(); /*non-public*/ static SpeciesData speciesData(LambdaForm form) { Object c = form.names[0].constraint; if (c instanceof SpeciesData) return (SpeciesData) c; // if there is no BMH constraint, then use the null constraint return SpeciesData.EMPTY; } /** * Return the number of fields in this BMH. Equivalent to speciesData().fieldCount(). */ /*non-public*/ abstract int fieldCount(); @Override Object internalProperties() { return "\n& BMH="+internalValues(); } @Override final Object internalValues() { Object[] boundValues = new Object[speciesData().fieldCount()]; for (int i = 0; i < boundValues.length; ++i) { boundValues[i] = arg(i); } return Arrays.asList(boundValues); } /*non-public*/ final Object arg(int i) { try { switch (speciesData().fieldType(i)) { case L_TYPE: return speciesData().getters[i].invokeBasic(this); case I_TYPE: return (int) speciesData().getters[i].invokeBasic(this); case J_TYPE: return (long) speciesData().getters[i].invokeBasic(this); case F_TYPE: return (float) speciesData().getters[i].invokeBasic(this); case D_TYPE: return (double) speciesData().getters[i].invokeBasic(this); } } catch (Throwable ex) { throw newInternalError(ex); } throw new InternalError("unexpected type: " + speciesData().typeChars+"."+i); } // // cloning API // /*non-public*/ abstract BoundMethodHandle copyWith(MethodType mt, LambdaForm lf); /*non-public*/ abstract BoundMethodHandle copyWithExtendL(MethodType mt, LambdaForm lf, Object narg); /*non-public*/ abstract BoundMethodHandle copyWithExtendI(MethodType mt, LambdaForm lf, int narg); /*non-public*/ abstract BoundMethodHandle copyWithExtendJ(MethodType mt, LambdaForm lf, long narg); /*non-public*/ abstract BoundMethodHandle copyWithExtendF(MethodType mt, LambdaForm lf, float narg); /*non-public*/ abstract BoundMethodHandle copyWithExtendD(MethodType mt, LambdaForm lf, double narg); // // concrete BMH classes required to close bootstrap loops // private // make it private to force users to access the enclosing class first static final class Species_L extends BoundMethodHandle { final Object argL0; private Species_L(MethodType mt, LambdaForm lf, Object argL0) { super(mt, lf); this.argL0 = argL0; } @Override /*non-public*/ SpeciesData speciesData() { return SPECIES_DATA; } @Override /*non-public*/ int fieldCount() { return 1; } /*non-public*/ static final SpeciesData SPECIES_DATA = new SpeciesData("L", Species_L.class); /*non-public*/ static BoundMethodHandle make(MethodType mt, LambdaForm lf, Object argL0) { return new Species_L(mt, lf, argL0); } @Override /*non-public*/ final BoundMethodHandle copyWith(MethodType mt, LambdaForm lf) { return new Species_L(mt, lf, argL0); } @Override /*non-public*/ final BoundMethodHandle copyWithExtendL(MethodType mt, LambdaForm lf, Object narg) { try { return (BoundMethodHandle) SPECIES_DATA.extendWith(L_TYPE).constructor().invokeBasic(mt, lf, argL0, narg); } catch (Throwable ex) { throw uncaughtException(ex); } } @Override /*non-public*/ final BoundMethodHandle copyWithExtendI(MethodType mt, LambdaForm lf, int narg) { try { return (BoundMethodHandle) SPECIES_DATA.extendWith(I_TYPE).constructor().invokeBasic(mt, lf, argL0, narg); } catch (Throwable ex) { throw uncaughtException(ex); } } @Override /*non-public*/ final BoundMethodHandle copyWithExtendJ(MethodType mt, LambdaForm lf, long narg) { try { return (BoundMethodHandle) SPECIES_DATA.extendWith(J_TYPE).constructor().invokeBasic(mt, lf, argL0, narg); } catch (Throwable ex) { throw uncaughtException(ex); } } @Override /*non-public*/ final BoundMethodHandle copyWithExtendF(MethodType mt, LambdaForm lf, float narg) { try { return (BoundMethodHandle) SPECIES_DATA.extendWith(F_TYPE).constructor().invokeBasic(mt, lf, argL0, narg); } catch (Throwable ex) { throw uncaughtException(ex); } } @Override /*non-public*/ final BoundMethodHandle copyWithExtendD(MethodType mt, LambdaForm lf, double narg) { try { return (BoundMethodHandle) SPECIES_DATA.extendWith(D_TYPE).constructor().invokeBasic(mt, lf, argL0, narg); } catch (Throwable ex) { throw uncaughtException(ex); } } } // // BMH species meta-data // /** * Meta-data wrapper for concrete BMH types. * Each BMH type corresponds to a given sequence of basic field types (LIJFD). * The fields are immutable; their values are fully specified at object construction. * Each BMH type supplies an array of getter functions which may be used in lambda forms. * A BMH is constructed by cloning a shorter BMH and adding one or more new field values. * The shortest possible BMH has zero fields; its class is SimpleMethodHandle. * BMH species are not interrelated by subtyping, even though it would appear that * a shorter BMH could serve as a supertype of a longer one which extends it. */ static class SpeciesData { private final String typeChars; private final BasicType[] typeCodes; private final Class<? extends BoundMethodHandle> clazz; // Bootstrapping requires circular relations MH -> BMH -> SpeciesData -> MH // Therefore, we need a non-final link in the chain. Use array elements. @Stable private final MethodHandle[] constructor; @Stable private final MethodHandle[] getters; @Stable private final NamedFunction[] nominalGetters; @Stable private final SpeciesData[] extensions; /*non-public*/ int fieldCount() { return typeCodes.length; } /*non-public*/ BasicType fieldType(int i) { return typeCodes[i]; } /*non-public*/ char fieldTypeChar(int i) { return typeChars.charAt(i); } Object fieldSignature() { return typeChars; } public Class<? extends BoundMethodHandle> fieldHolder() { return clazz; } public String toString() { return "SpeciesData<"+fieldSignature()+">"; } /** * Return a {@link LambdaForm.Name} containing a {@link LambdaForm.NamedFunction} that * represents a MH bound to a generic invoker, which in turn forwards to the corresponding * getter. */ NamedFunction getterFunction(int i) { NamedFunction nf = nominalGetters[i]; assert(nf.memberDeclaringClassOrNull() == fieldHolder()); assert(nf.returnType() == fieldType(i)); return nf; } NamedFunction[] getterFunctions() { return nominalGetters; } MethodHandle[] getterHandles() { return getters; } MethodHandle constructor() { return constructor[0]; } static final SpeciesData EMPTY = new SpeciesData("", BoundMethodHandle.class); SpeciesData(String types, Class<? extends BoundMethodHandle> clazz) { this.typeChars = types; this.typeCodes = basicTypes(types); this.clazz = clazz; if (!INIT_DONE) { this.constructor = new MethodHandle[1]; // only one ctor this.getters = new MethodHandle[types.length()]; this.nominalGetters = new NamedFunction[types.length()]; } else { this.constructor = Factory.makeCtors(clazz, types, null); this.getters = Factory.makeGetters(clazz, types, null); this.nominalGetters = Factory.makeNominalGetters(types, null, this.getters); } this.extensions = new SpeciesData[ARG_TYPE_LIMIT]; } private void initForBootstrap() { assert(!INIT_DONE); if (constructor() == null) { String types = typeChars; CACHE.put(types, this); Factory.makeCtors(clazz, types, this.constructor); Factory.makeGetters(clazz, types, this.getters); Factory.makeNominalGetters(types, this.nominalGetters, this.getters); } } private static final ConcurrentMap<String, SpeciesData> CACHE = new ConcurrentHashMap<>(); private static final boolean INIT_DONE; // set after <clinit> finishes... SpeciesData extendWith(byte type) { return extendWith(BasicType.basicType(type)); } SpeciesData extendWith(BasicType type) { int ord = type.ordinal(); SpeciesData d = extensions[ord]; if (d != null) return d; extensions[ord] = d = get(typeChars+type.basicTypeChar()); return d; } private static SpeciesData get(String types) { return CACHE.computeIfAbsent(types, new Function<String, SpeciesData>() { @Override public SpeciesData apply(String types) { Class<? extends BoundMethodHandle> bmhcl = Factory.getConcreteBMHClass(types); // SpeciesData instantiation may throw VirtualMachineError because of // code cache overflow... SpeciesData speciesData = new SpeciesData(types, bmhcl); // CHM.computeIfAbsent ensures only one SpeciesData will be set // successfully on the concrete BMH class if ever Factory.setSpeciesDataToConcreteBMHClass(bmhcl, speciesData); // the concrete BMH class is published via SpeciesData instance // returned here only after it's SPECIES_DATA field is set return speciesData; } }); } /** * This is to be called when assertions are enabled. It checks whether SpeciesData for all of the statically * defined species subclasses of BoundMethodHandle has been added to the SpeciesData cache. See below in the * static initializer for */ static boolean speciesDataCachePopulated() { Class<BoundMethodHandle> rootCls = BoundMethodHandle.class; try { for (Class<?> c : rootCls.getDeclaredClasses()) { if (rootCls.isAssignableFrom(c)) { final Class<? extends BoundMethodHandle> cbmh = c.asSubclass(BoundMethodHandle.class); SpeciesData d = Factory.getSpeciesDataFromConcreteBMHClass(cbmh); assert(d != null) : cbmh.getName(); assert(d.clazz == cbmh); assert(CACHE.get(d.typeChars) == d); } } } catch (Throwable e) { throw newInternalError(e); } return true; } static { // Pre-fill the BMH species-data cache with EMPTY and all BMH's inner subclasses. EMPTY.initForBootstrap(); Species_L.SPECIES_DATA.initForBootstrap(); // check that all static SpeciesData instances have been initialized assert speciesDataCachePopulated(); // Note: Do not simplify this, because INIT_DONE must not be // a compile-time constant during bootstrapping. INIT_DONE = Boolean.TRUE; } } static SpeciesData getSpeciesData(String types) { return SpeciesData.get(types); } /** * Generation of concrete BMH classes. * * A concrete BMH species is fit for binding a number of values adhering to a * given type pattern. Reference types are erased. * * BMH species are cached by type pattern. * * A BMH species has a number of fields with the concrete (possibly erased) types of * bound values. Setters are provided as an API in BMH. Getters are exposed as MHs, * which can be included as names in lambda forms. */ static class Factory { static final String JLO_SIG = "Ljava/lang/Object;"; static final String JLS_SIG = "Ljava/lang/String;"; static final String JLC_SIG = "Ljava/lang/Class;"; static final String MH = "java/lang/invoke/MethodHandle"; static final String MH_SIG = "L"+MH+";"; static final String BMH = "java/lang/invoke/BoundMethodHandle"; static final String BMH_SIG = "L"+BMH+";"; static final String SPECIES_DATA = "java/lang/invoke/BoundMethodHandle$SpeciesData"; static final String SPECIES_DATA_SIG = "L"+SPECIES_DATA+";"; static final String STABLE_SIG = "Ljava/lang/invoke/Stable;"; static final String SPECIES_PREFIX_NAME = "Species_"; static final String SPECIES_PREFIX_PATH = BMH + "$" + SPECIES_PREFIX_NAME; static final String BMHSPECIES_DATA_EWI_SIG = "(B)" + SPECIES_DATA_SIG; static final String BMHSPECIES_DATA_GFC_SIG = "(" + JLS_SIG + JLC_SIG + ")" + SPECIES_DATA_SIG; static final String MYSPECIES_DATA_SIG = "()" + SPECIES_DATA_SIG; static final String VOID_SIG = "()V"; static final String INT_SIG = "()I"; static final String SIG_INCIPIT = "(Ljava/lang/invoke/MethodType;Ljava/lang/invoke/LambdaForm;"; static final String[] E_THROWABLE = new String[] { "java/lang/Throwable" }; static final ConcurrentMap<String, Class<? extends BoundMethodHandle>> CLASS_CACHE = new ConcurrentHashMap<>(); /** * Get a concrete subclass of BMH for a given combination of bound types. * * @param types the type signature, wherein reference types are erased to 'L' * @return the concrete BMH class */ static Class<? extends BoundMethodHandle> getConcreteBMHClass(String types) { // CHM.computeIfAbsent ensures generateConcreteBMHClass is called // only once per key. return CLASS_CACHE.computeIfAbsent( types, new Function<String, Class<? extends BoundMethodHandle>>() { @Override public Class<? extends BoundMethodHandle> apply(String types) { return generateConcreteBMHClass(types); } }); } /** * Generate a concrete subclass of BMH for a given combination of bound types. * * A concrete BMH species adheres to the following schema: * * <pre> * class Species_[[types]] extends BoundMethodHandle { * [[fields]] * final SpeciesData speciesData() { return SpeciesData.get("[[types]]"); } * } * </pre> * * The {@code [[types]]} signature is precisely the string that is passed to this * method. * * The {@code [[fields]]} section consists of one field definition per character in * the type signature, adhering to the naming schema described in the definition of * {@link #makeFieldName}. * * For example, a concrete BMH species for two reference and one integral bound values * would have the following shape: * * <pre> * class BoundMethodHandle { ... private static * final class Species_LLI extends BoundMethodHandle { * final Object argL0; * final Object argL1; * final int argI2; * private Species_LLI(MethodType mt, LambdaForm lf, Object argL0, Object argL1, int argI2) { * super(mt, lf); * this.argL0 = argL0; * this.argL1 = argL1; * this.argI2 = argI2; * } * final SpeciesData speciesData() { return SPECIES_DATA; } * final int fieldCount() { return 3; } * @Stable static SpeciesData SPECIES_DATA; // injected afterwards * static BoundMethodHandle make(MethodType mt, LambdaForm lf, Object argL0, Object argL1, int argI2) { * return new Species_LLI(mt, lf, argL0, argL1, argI2); * } * final BoundMethodHandle copyWith(MethodType mt, LambdaForm lf) { * return new Species_LLI(mt, lf, argL0, argL1, argI2); * } * final BoundMethodHandle copyWithExtendL(MethodType mt, LambdaForm lf, Object narg) { * return SPECIES_DATA.extendWith(L_TYPE).constructor().invokeBasic(mt, lf, argL0, argL1, argI2, narg); * } * final BoundMethodHandle copyWithExtendI(MethodType mt, LambdaForm lf, int narg) { * return SPECIES_DATA.extendWith(I_TYPE).constructor().invokeBasic(mt, lf, argL0, argL1, argI2, narg); * } * final BoundMethodHandle copyWithExtendJ(MethodType mt, LambdaForm lf, long narg) { * return SPECIES_DATA.extendWith(J_TYPE).constructor().invokeBasic(mt, lf, argL0, argL1, argI2, narg); * } * final BoundMethodHandle copyWithExtendF(MethodType mt, LambdaForm lf, float narg) { * return SPECIES_DATA.extendWith(F_TYPE).constructor().invokeBasic(mt, lf, argL0, argL1, argI2, narg); * } * public final BoundMethodHandle copyWithExtendD(MethodType mt, LambdaForm lf, double narg) { * return SPECIES_DATA.extendWith(D_TYPE).constructor().invokeBasic(mt, lf, argL0, argL1, argI2, narg); * } * } * </pre> * * @param types the type signature, wherein reference types are erased to 'L' * @return the generated concrete BMH class */ static Class<? extends BoundMethodHandle> generateConcreteBMHClass(String types) { final ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS + ClassWriter.COMPUTE_FRAMES); String shortTypes = LambdaForm.shortenSignature(types); final String className = SPECIES_PREFIX_PATH + shortTypes; final String sourceFile = SPECIES_PREFIX_NAME + shortTypes; final int NOT_ACC_PUBLIC = 0; // not ACC_PUBLIC cw.visit(V1_6, NOT_ACC_PUBLIC + ACC_FINAL + ACC_SUPER, className, null, BMH, null); cw.visitSource(sourceFile, null); // emit static types and SPECIES_DATA fields FieldVisitor fw = cw.visitField(NOT_ACC_PUBLIC + ACC_STATIC, "SPECIES_DATA", SPECIES_DATA_SIG, null, null); fw.visitAnnotation(STABLE_SIG, true); fw.visitEnd(); // emit bound argument fields for (int i = 0; i < types.length(); ++i) { final char t = types.charAt(i); final String fieldName = makeFieldName(types, i); final String fieldDesc = t == 'L' ? JLO_SIG : String.valueOf(t); cw.visitField(ACC_FINAL, fieldName, fieldDesc, null, null).visitEnd(); } MethodVisitor mv; // emit constructor mv = cw.visitMethod(ACC_PRIVATE, "<init>", makeSignature(types, true), null, null); mv.visitCode(); mv.visitVarInsn(ALOAD, 0); // this mv.visitVarInsn(ALOAD, 1); // type mv.visitVarInsn(ALOAD, 2); // form mv.visitMethodInsn(INVOKESPECIAL, BMH, "<init>", makeSignature("", true), false); for (int i = 0, j = 0; i < types.length(); ++i, ++j) { // i counts the arguments, j counts corresponding argument slots char t = types.charAt(i); mv.visitVarInsn(ALOAD, 0); mv.visitVarInsn(typeLoadOp(t), j + 3); // parameters start at 3 mv.visitFieldInsn(PUTFIELD, className, makeFieldName(types, i), typeSig(t)); if (t == 'J' || t == 'D') { ++j; // adjust argument register access } } mv.visitInsn(RETURN); mv.visitMaxs(0, 0); mv.visitEnd(); // emit implementation of speciesData() mv = cw.visitMethod(NOT_ACC_PUBLIC + ACC_FINAL, "speciesData", MYSPECIES_DATA_SIG, null, null); mv.visitCode(); mv.visitFieldInsn(GETSTATIC, className, "SPECIES_DATA", SPECIES_DATA_SIG); mv.visitInsn(ARETURN); mv.visitMaxs(0, 0); mv.visitEnd(); // emit implementation of fieldCount() mv = cw.visitMethod(NOT_ACC_PUBLIC + ACC_FINAL, "fieldCount", INT_SIG, null, null); mv.visitCode(); int fc = types.length(); if (fc <= (ICONST_5 - ICONST_0)) { mv.visitInsn(ICONST_0 + fc); } else { mv.visitIntInsn(SIPUSH, fc); } mv.visitInsn(IRETURN); mv.visitMaxs(0, 0); mv.visitEnd(); // emit make() ...factory method wrapping constructor mv = cw.visitMethod(NOT_ACC_PUBLIC + ACC_STATIC, "make", makeSignature(types, false), null, null); mv.visitCode(); // make instance mv.visitTypeInsn(NEW, className); mv.visitInsn(DUP); // load mt, lf mv.visitVarInsn(ALOAD, 0); // type mv.visitVarInsn(ALOAD, 1); // form // load factory method arguments for (int i = 0, j = 0; i < types.length(); ++i, ++j) { // i counts the arguments, j counts corresponding argument slots char t = types.charAt(i); mv.visitVarInsn(typeLoadOp(t), j + 2); // parameters start at 3 if (t == 'J' || t == 'D') { ++j; // adjust argument register access } } // finally, invoke the constructor and return mv.visitMethodInsn(INVOKESPECIAL, className, "<init>", makeSignature(types, true), false); mv.visitInsn(ARETURN); mv.visitMaxs(0, 0); mv.visitEnd(); // emit copyWith() mv = cw.visitMethod(NOT_ACC_PUBLIC + ACC_FINAL, "copyWith", makeSignature("", false), null, null); mv.visitCode(); // make instance mv.visitTypeInsn(NEW, className); mv.visitInsn(DUP); // load mt, lf mv.visitVarInsn(ALOAD, 1); mv.visitVarInsn(ALOAD, 2); // put fields on the stack emitPushFields(types, className, mv); // finally, invoke the constructor and return mv.visitMethodInsn(INVOKESPECIAL, className, "<init>", makeSignature(types, true), false); mv.visitInsn(ARETURN); mv.visitMaxs(0, 0); mv.visitEnd(); // for each type, emit copyWithExtendT() for (BasicType type : BasicType.ARG_TYPES) { int ord = type.ordinal(); char btChar = type.basicTypeChar(); mv = cw.visitMethod(NOT_ACC_PUBLIC + ACC_FINAL, "copyWithExtend" + btChar, makeSignature(String.valueOf(btChar), false), null, E_THROWABLE); mv.visitCode(); // return SPECIES_DATA.extendWith(t).constructor().invokeBasic(mt, lf, argL0, ..., narg) // obtain constructor mv.visitFieldInsn(GETSTATIC, className, "SPECIES_DATA", SPECIES_DATA_SIG); int iconstInsn = ICONST_0 + ord; assert(iconstInsn <= ICONST_5); mv.visitInsn(iconstInsn); mv.visitMethodInsn(INVOKEVIRTUAL, SPECIES_DATA, "extendWith", BMHSPECIES_DATA_EWI_SIG, false); mv.visitMethodInsn(INVOKEVIRTUAL, SPECIES_DATA, "constructor", "()" + MH_SIG, false); // load mt, lf mv.visitVarInsn(ALOAD, 1); mv.visitVarInsn(ALOAD, 2); // put fields on the stack emitPushFields(types, className, mv); // put narg on stack mv.visitVarInsn(typeLoadOp(btChar), 3); // finally, invoke the constructor and return mv.visitMethodInsn(INVOKEVIRTUAL, MH, "invokeBasic", makeSignature(types + btChar, false), false); mv.visitInsn(ARETURN); mv.visitMaxs(0, 0); mv.visitEnd(); } cw.visitEnd(); // load class final byte[] classFile = cw.toByteArray(); InvokerBytecodeGenerator.maybeDump(className, classFile); Class<? extends BoundMethodHandle> bmhClass = //UNSAFE.defineAnonymousClass(BoundMethodHandle.class, classFile, null).asSubclass(BoundMethodHandle.class); UNSAFE.defineClass(className, classFile, 0, classFile.length, BoundMethodHandle.class.getClassLoader(), null) .asSubclass(BoundMethodHandle.class); return bmhClass; } private static int typeLoadOp(char t) { switch (t) { case 'L': return ALOAD; case 'I': return ILOAD; case 'J': return LLOAD; case 'F': return FLOAD; case 'D': return DLOAD; default : throw newInternalError("unrecognized type " + t); } } private static void emitPushFields(String types, String className, MethodVisitor mv) { for (int i = 0; i < types.length(); ++i) { char tc = types.charAt(i); mv.visitVarInsn(ALOAD, 0); mv.visitFieldInsn(GETFIELD, className, makeFieldName(types, i), typeSig(tc)); } } static String typeSig(char t) { return t == 'L' ? JLO_SIG : String.valueOf(t); } // // Getter MH generation. // private static MethodHandle makeGetter(Class<?> cbmhClass, String types, int index) { String fieldName = makeFieldName(types, index); Class<?> fieldType = Wrapper.forBasicType(types.charAt(index)).primitiveType(); try { return LOOKUP.findGetter(cbmhClass, fieldName, fieldType); } catch (NoSuchFieldException | IllegalAccessException e) { throw newInternalError(e); } } static MethodHandle[] makeGetters(Class<?> cbmhClass, String types, MethodHandle[] mhs) { if (mhs == null) mhs = new MethodHandle[types.length()]; for (int i = 0; i < mhs.length; ++i) { mhs[i] = makeGetter(cbmhClass, types, i); assert(mhs[i].internalMemberName().getDeclaringClass() == cbmhClass); } return mhs; } static MethodHandle[] makeCtors(Class<? extends BoundMethodHandle> cbmh, String types, MethodHandle mhs[]) { if (mhs == null) mhs = new MethodHandle[1]; if (types.equals("")) return mhs; // hack for empty BMH species mhs[0] = makeCbmhCtor(cbmh, types); return mhs; } static NamedFunction[] makeNominalGetters(String types, NamedFunction[] nfs, MethodHandle[] getters) { if (nfs == null) nfs = new NamedFunction[types.length()]; for (int i = 0; i < nfs.length; ++i) { nfs[i] = new NamedFunction(getters[i]); } return nfs; } // // Auxiliary methods. // static SpeciesData getSpeciesDataFromConcreteBMHClass(Class<? extends BoundMethodHandle> cbmh) { try { Field F_SPECIES_DATA = cbmh.getDeclaredField("SPECIES_DATA"); return (SpeciesData) F_SPECIES_DATA.get(null); } catch (ReflectiveOperationException ex) { throw newInternalError(ex); } } static void setSpeciesDataToConcreteBMHClass(Class<? extends BoundMethodHandle> cbmh, SpeciesData speciesData) { try { Field F_SPECIES_DATA = cbmh.getDeclaredField("SPECIES_DATA"); assert F_SPECIES_DATA.getDeclaredAnnotation(Stable.class) != null; F_SPECIES_DATA.set(null, speciesData); } catch (ReflectiveOperationException ex) { throw newInternalError(ex); } } /** * Field names in concrete BMHs adhere to this pattern: * arg + type + index * where type is a single character (L, I, J, F, D). */ private static String makeFieldName(String types, int index) { assert index >= 0 && index < types.length(); return "arg" + types.charAt(index) + index; } private static String makeSignature(String types, boolean ctor) { StringBuilder buf = new StringBuilder(SIG_INCIPIT); for (char c : types.toCharArray()) { buf.append(typeSig(c)); } return buf.append(')').append(ctor ? "V" : BMH_SIG).toString(); } static MethodHandle makeCbmhCtor(Class<? extends BoundMethodHandle> cbmh, String types) { try { return LOOKUP.findStatic(cbmh, "make", MethodType.fromMethodDescriptorString(makeSignature(types, false), null)); } catch (NoSuchMethodException | IllegalAccessException | IllegalArgumentException | TypeNotPresentException e) { throw newInternalError(e); } } } private static final Lookup LOOKUP = Lookup.IMPL_LOOKUP; /** * All subclasses must provide such a value describing their type signature. */ static final SpeciesData SPECIES_DATA = SpeciesData.EMPTY; private static final SpeciesData[] SPECIES_DATA_CACHE = new SpeciesData[5]; private static SpeciesData checkCache(int size, String types) { int idx = size - 1; SpeciesData data = SPECIES_DATA_CACHE[idx]; if (data != null) return data; SPECIES_DATA_CACHE[idx] = data = getSpeciesData(types); return data; } static SpeciesData speciesData_L() { return checkCache(1, "L"); } static SpeciesData speciesData_LL() { return checkCache(2, "LL"); } static SpeciesData speciesData_LLL() { return checkCache(3, "LLL"); } static SpeciesData speciesData_LLLL() { return checkCache(4, "LLLL"); } static SpeciesData speciesData_LLLLL() { return checkCache(5, "LLLLL"); } }
⏎ java/lang/invoke/BoundMethodHandle.java
Or download all of them as a single archive file:
File name: jre-rt-java-1.8.0_191-src.zip File size: 6664831 bytes Release date: 2018-10-28 Download
⇒ JRE 8 rt.jar - javax.* Package Source Code
2023-08-23, 248204👍, 4💬
Popular Posts:
JDK 17 java.desktop.jmod is the JMOD file for JDK 17 Desktop module. JDK 17 Desktop module compiled ...
The Bouncy Castle Crypto package is a Java implementation of cryptographic algorithms, it was develo...
The Jakarta-ORO Java classes are a set of text-processing Java classes that provide Perl5 compatible...
JDK 11 jdk.jdi.jmod is the JMOD file for JDK 11 JDI (Java Debug Interface) tool. JDK 11 JDI tool com...
How to download and install JDK (Java Development Kit) 7? If you want to write Java applications, yo...