public final class Indexer
extends java.lang.Object
The Indexer operates on input streams that point to class file data. Input streams do not need to be buffered, as the indexer already does this. There is also no limit to the number of class file streams the indexer can process, other than available memory.
The Indexer attempts to minimize the final memory state of the index, but to do this it must maintain additional in-process state (intern tables etc) until the index is complete.
Numerous optimizations are taken during indexing to attempt to minimize the CPU and I/O cost, however, the Java class file format was not designed for partial searching, which ultimately limits the efficiency of processing them.
Thread-Safety This class is not thread-safe can not be shared between threads. The index it produces however is thread-safe.
| Modifier and Type | Class and Description |
|---|---|
private static class |
Indexer.BooleanHolder |
private static class |
Indexer.InnerClassInfo |
private static class |
Indexer.IntegerHolder |
private static class |
Indexer.NameAndType |
private static class |
Indexer.PathElement |
private static class |
Indexer.PathElementStack |
private static class |
Indexer.TypeAnnotationState |
| Modifier and Type | Field and Description |
|---|---|
private java.util.HashMap<DotName,java.util.List<AnnotationInstance>> |
classAnnotations |
private java.util.Map<DotName,ClassInfo> |
classes |
private static int |
CONSTANT_CLASS |
private static int |
CONSTANT_DOUBLE |
private static int |
CONSTANT_FIELDREF |
private static int |
CONSTANT_FLOAT |
private static int |
CONSTANT_INTEGER |
private static int |
CONSTANT_INTERFACEMETHODREF |
private static int |
CONSTANT_INVOKEDYNAMIC |
private static int |
CONSTANT_LONG |
private static int |
CONSTANT_METHODHANDLE |
private static int |
CONSTANT_METHODREF |
private static int |
CONSTANT_METHODTYPE |
private static int |
CONSTANT_NAMEANDTYPE |
private static int |
CONSTANT_STRING |
private static int |
CONSTANT_UTF8 |
private byte[] |
constantPool |
private byte[] |
constantPoolAnnoAttrributes |
private int[] |
constantPoolOffsets |
private ClassInfo |
currentClass |
private java.util.ArrayList<AnnotationInstance> |
elementAnnotations |
private static byte[] |
ENCLOSING_METHOD |
private static int |
ENCLOSING_METHOD_LEN |
private static byte[] |
EXCEPTIONS |
private static int |
EXCEPTIONS_LEN |
private java.util.List<FieldInfo> |
fields |
private static int |
HAS_ENCLOSING_METHOD |
private static int |
HAS_EXCEPTIONS |
private static int |
HAS_INNER_CLASSES |
private static int |
HAS_RUNTIME_ANNOTATION |
private static int |
HAS_RUNTIME_PARAM_ANNOTATION |
private static int |
HAS_RUNTIME_TYPE_ANNOTATION |
private static int |
HAS_SIGNATURE |
private java.util.Map<DotName,java.util.List<ClassInfo>> |
implementors |
private static byte[] |
INIT_METHOD_NAME |
private static byte[] |
INNER_CLASSES |
private static int |
INNER_CLASSES_LEN |
private java.util.Map<DotName,Indexer.InnerClassInfo> |
innerClasses |
private java.util.Map<DotName,java.util.List<AnnotationInstance>> |
masterAnnotations |
private java.util.List<MethodInfo> |
methods |
private NameTable |
names |
private static byte[] |
RUNTIME_ANNOTATIONS |
private static int |
RUNTIME_ANNOTATIONS_LEN |
private static byte[] |
RUNTIME_PARAM_ANNOTATIONS |
private static int |
RUNTIME_PARAM_ANNOTATIONS_LEN |
private static byte[] |
RUNTIME_TYPE_ANNOTATIONS |
private static int |
RUNTIME_TYPE_ANNOTATIONS_LEN |
private static byte[] |
SIGNATURE |
private static int |
SIGNATURE_LEN |
private GenericSignatureParser |
signatureParser |
private java.util.IdentityHashMap<AnnotationTarget,java.lang.Object> |
signaturePresent |
private java.util.List<java.lang.Object> |
signatures |
private java.util.Map<DotName,java.util.List<ClassInfo>> |
subclasses |
private java.util.IdentityHashMap<AnnotationTarget,java.util.List<Indexer.TypeAnnotationState>> |
typeAnnotations |
| Constructor and Description |
|---|
Indexer() |
| Modifier and Type | Method and Description |
|---|---|
private void |
addImplementor(DotName interfaceName,
ClassInfo currentClass) |
private void |
addSubclass(DotName superName,
ClassInfo currentClass) |
private void |
applySignatures() |
private int |
bitsToInt(byte[] pool,
int pos) |
private long |
bitsToLong(byte[] pool,
int pos) |
private java.util.ArrayDeque<Indexer.InnerClassInfo> |
buildClassesQueue(DotName name) |
private java.util.Map<DotName,Type> |
buildOwnerMap(Type type) |
Index |
complete()
Completes, finalizes, and returns the index after zero or more calls to
index.
|
private static java.lang.String |
convertClassFieldDescriptor(java.lang.String descriptor) |
private ParameterizedType |
convertParameterized(Type oType) |
private static Type[] |
copyTypeParameters(AnnotationTarget target) |
private DotName |
decodeClassEntry(int classInfoIndex) |
private double |
decodeDoubleEntry(int index) |
private float |
decodeFloatEntry(int index) |
private int |
decodeIntegerEntry(int index) |
private long |
decodeLongEntry(int index) |
private Indexer.NameAndType |
decodeNameAndTypeEntry(int index) |
private java.lang.String |
decodeUtf8Entry(int index) |
private byte[] |
decodeUtf8EntryAsBytes(int index) |
private static Type[] |
getTypeParameters(AnnotationTarget target) |
ClassInfo |
index(java.io.InputStream stream)
Analyze and index the class file data present in the passed input stream.
|
private void |
initClassFields() |
private void |
initIndexMaps() |
private byte[] |
intern(byte[] bytes) |
private java.lang.String |
intern(java.lang.String string) |
private Type |
intern(Type type) |
private Type[] |
intern(Type[] type) |
private boolean |
isJDK11OrNewer(java.io.DataInputStream stream) |
private static boolean |
match(byte[] target,
int offset,
byte[] expected) |
private void |
parseClassSignature(java.lang.String signature,
ClassInfo clazz) |
private void |
parseFieldSignature(java.lang.String signature,
FieldInfo field) |
private Type[] |
parseMethodArgs(java.lang.String descriptor,
Indexer.IntegerHolder pos) |
private void |
parseMethodSignature(java.lang.String signature,
MethodInfo method) |
private Type |
parseType(java.lang.String descriptor) |
private Type |
parseType(java.lang.String descriptor,
Indexer.IntegerHolder pos) |
private int |
popNestedDepth(Indexer.PathElementStack elements) |
private AnnotationInstance |
processAnnotation(java.io.DataInputStream data,
AnnotationTarget target) |
private AnnotationValue |
processAnnotationElementValue(java.lang.String name,
java.io.DataInputStream data) |
private void |
processAnnotations(java.io.DataInputStream data,
AnnotationTarget target) |
private void |
processAttributes(java.io.DataInputStream data,
AnnotationTarget target) |
private void |
processClassInfo(java.io.DataInputStream data) |
private boolean |
processConstantPool(java.io.DataInputStream stream) |
private void |
processEnclosingMethod(java.io.DataInputStream data,
ClassInfo target) |
private void |
processExceptions(java.io.DataInputStream data,
MethodInfo target) |
private void |
processFieldInfo(java.io.DataInputStream data) |
private void |
processInnerClasses(java.io.DataInputStream data,
ClassInfo target) |
private void |
processMethodInfo(java.io.DataInputStream data) |
private void |
processSignature(java.io.DataInputStream data,
AnnotationTarget target) |
private java.util.ArrayList<Indexer.PathElement> |
processTargetPath(java.io.DataInputStream data,
Indexer.BooleanHolder genericsRequired) |
private Indexer.TypeAnnotationState |
processTypeAnnotation(java.io.DataInputStream data,
AnnotationTarget target) |
private void |
processTypeAnnotations(java.io.DataInputStream data,
AnnotationTarget target) |
private Type |
rebuildNestedType(Type type,
int depth,
Indexer.TypeAnnotationState typeAnnotationState) |
private void |
recordAnnotation(java.util.Map<DotName,java.util.List<AnnotationInstance>> classAnnotations,
DotName annotation,
AnnotationInstance instance) |
private void |
resolveTypeAnnotation(AnnotationTarget target,
Indexer.TypeAnnotationState typeAnnotationState) |
private void |
resolveTypeAnnotations() |
private Type |
resolveTypePath(Type type,
Indexer.TypeAnnotationState typeAnnotationState) |
private Type |
searchNestedType(Type type,
int depth,
Indexer.TypeAnnotationState typeAnnotationState) |
private Type |
searchTypePath(Type type,
Indexer.TypeAnnotationState typeAnnotationState) |
private void |
setTypeParameters(AnnotationTarget target,
Type[] typeParameters) |
private static byte[] |
sizeToFit(byte[] buf,
int needed,
int offset,
int remainingEntries) |
private static void |
skipFully(java.io.InputStream s,
long n) |
private void |
updateTypeTarget(AnnotationTarget enclosingTarget,
Indexer.TypeAnnotationState typeAnnotationState) |
private void |
updateTypeTargets() |
private void |
verifyMagic(java.io.DataInputStream stream) |
private static final int CONSTANT_CLASS
private static final int CONSTANT_FIELDREF
private static final int CONSTANT_METHODREF
private static final int CONSTANT_INTERFACEMETHODREF
private static final int CONSTANT_STRING
private static final int CONSTANT_INTEGER
private static final int CONSTANT_FLOAT
private static final int CONSTANT_LONG
private static final int CONSTANT_DOUBLE
private static final int CONSTANT_NAMEANDTYPE
private static final int CONSTANT_UTF8
private static final int CONSTANT_INVOKEDYNAMIC
private static final int CONSTANT_METHODHANDLE
private static final int CONSTANT_METHODTYPE
private static final byte[] RUNTIME_ANNOTATIONS
private static final byte[] RUNTIME_PARAM_ANNOTATIONS
private static final byte[] RUNTIME_TYPE_ANNOTATIONS
private static final byte[] SIGNATURE
private static final byte[] EXCEPTIONS
private static final byte[] INNER_CLASSES
private static final byte[] ENCLOSING_METHOD
private static final int RUNTIME_ANNOTATIONS_LEN
private static final int RUNTIME_PARAM_ANNOTATIONS_LEN
private static final int RUNTIME_TYPE_ANNOTATIONS_LEN
private static final int SIGNATURE_LEN
private static final int EXCEPTIONS_LEN
private static final int INNER_CLASSES_LEN
private static final int ENCLOSING_METHOD_LEN
private static final int HAS_RUNTIME_ANNOTATION
private static final int HAS_RUNTIME_PARAM_ANNOTATION
private static final int HAS_RUNTIME_TYPE_ANNOTATION
private static final int HAS_SIGNATURE
private static final int HAS_EXCEPTIONS
private static final int HAS_INNER_CLASSES
private static final int HAS_ENCLOSING_METHOD
private static final byte[] INIT_METHOD_NAME
private java.util.IdentityHashMap<AnnotationTarget,java.lang.Object> signaturePresent
private byte[] constantPool
private int[] constantPoolOffsets
private byte[] constantPoolAnnoAttrributes
private ClassInfo currentClass
private java.util.HashMap<DotName,java.util.List<AnnotationInstance>> classAnnotations
private java.util.ArrayList<AnnotationInstance> elementAnnotations
private java.util.List<java.lang.Object> signatures
private java.util.Map<DotName,Indexer.InnerClassInfo> innerClasses
private java.util.IdentityHashMap<AnnotationTarget,java.util.List<Indexer.TypeAnnotationState>> typeAnnotations
private java.util.List<MethodInfo> methods
private java.util.List<FieldInfo> fields
private java.util.Map<DotName,java.util.List<AnnotationInstance>> masterAnnotations
private NameTable names
private GenericSignatureParser signatureParser
private static boolean match(byte[] target,
int offset,
byte[] expected)
private static byte[] sizeToFit(byte[] buf,
int needed,
int offset,
int remainingEntries)
private static void skipFully(java.io.InputStream s,
long n)
throws java.io.IOException
java.io.IOExceptionprivate void initIndexMaps()
private void initClassFields()
private void processMethodInfo(java.io.DataInputStream data)
throws java.io.IOException
java.io.IOExceptionprivate void processFieldInfo(java.io.DataInputStream data)
throws java.io.IOException
java.io.IOExceptionprivate void processAttributes(java.io.DataInputStream data,
AnnotationTarget target)
throws java.io.IOException
java.io.IOExceptionprivate void processAnnotations(java.io.DataInputStream data,
AnnotationTarget target)
throws java.io.IOException
java.io.IOExceptionprivate void processInnerClasses(java.io.DataInputStream data,
ClassInfo target)
throws java.io.IOException
java.io.IOExceptionprivate void processEnclosingMethod(java.io.DataInputStream data,
ClassInfo target)
throws java.io.IOException
java.io.IOExceptionprivate void processTypeAnnotations(java.io.DataInputStream data,
AnnotationTarget target)
throws java.io.IOException
java.io.IOExceptionprivate Indexer.TypeAnnotationState processTypeAnnotation(java.io.DataInputStream data, AnnotationTarget target) throws java.io.IOException
java.io.IOExceptionprivate void resolveTypeAnnotations()
private void updateTypeTargets()
private static Type[] getTypeParameters(AnnotationTarget target)
private static Type[] copyTypeParameters(AnnotationTarget target)
private void setTypeParameters(AnnotationTarget target, Type[] typeParameters)
private void resolveTypeAnnotation(AnnotationTarget target, Indexer.TypeAnnotationState typeAnnotationState)
private Type resolveTypePath(Type type, Indexer.TypeAnnotationState typeAnnotationState)
private int popNestedDepth(Indexer.PathElementStack elements)
private void updateTypeTarget(AnnotationTarget enclosingTarget, Indexer.TypeAnnotationState typeAnnotationState)
private Type searchTypePath(Type type, Indexer.TypeAnnotationState typeAnnotationState)
private Type rebuildNestedType(Type type, int depth, Indexer.TypeAnnotationState typeAnnotationState)
private ParameterizedType convertParameterized(Type oType)
private Type searchNestedType(Type type, int depth, Indexer.TypeAnnotationState typeAnnotationState)
private java.util.ArrayDeque<Indexer.InnerClassInfo> buildClassesQueue(DotName name)
private java.util.ArrayList<Indexer.PathElement> processTargetPath(java.io.DataInputStream data, Indexer.BooleanHolder genericsRequired) throws java.io.IOException
java.io.IOExceptionprivate void processExceptions(java.io.DataInputStream data,
MethodInfo target)
throws java.io.IOException
java.io.IOExceptionprivate void processSignature(java.io.DataInputStream data,
AnnotationTarget target)
throws java.io.IOException
java.io.IOExceptionprivate void parseClassSignature(java.lang.String signature,
ClassInfo clazz)
private void applySignatures()
private void parseFieldSignature(java.lang.String signature,
FieldInfo field)
private void parseMethodSignature(java.lang.String signature,
MethodInfo method)
private AnnotationInstance processAnnotation(java.io.DataInputStream data, AnnotationTarget target) throws java.io.IOException
java.io.IOExceptionprivate void recordAnnotation(java.util.Map<DotName,java.util.List<AnnotationInstance>> classAnnotations, DotName annotation, AnnotationInstance instance)
private java.lang.String intern(java.lang.String string)
private byte[] intern(byte[] bytes)
private AnnotationValue processAnnotationElementValue(java.lang.String name, java.io.DataInputStream data) throws java.io.IOException
java.io.IOExceptionprivate void processClassInfo(java.io.DataInputStream data)
throws java.io.IOException
java.io.IOExceptionprivate boolean isJDK11OrNewer(java.io.DataInputStream stream)
throws java.io.IOException
java.io.IOExceptionprivate void verifyMagic(java.io.DataInputStream stream)
throws java.io.IOException
java.io.IOExceptionprivate DotName decodeClassEntry(int classInfoIndex)
private java.lang.String decodeUtf8Entry(int index)
private byte[] decodeUtf8EntryAsBytes(int index)
private Indexer.NameAndType decodeNameAndTypeEntry(int index)
private int bitsToInt(byte[] pool,
int pos)
private long bitsToLong(byte[] pool,
int pos)
private int decodeIntegerEntry(int index)
private long decodeLongEntry(int index)
private float decodeFloatEntry(int index)
private double decodeDoubleEntry(int index)
private static java.lang.String convertClassFieldDescriptor(java.lang.String descriptor)
private Type[] parseMethodArgs(java.lang.String descriptor, Indexer.IntegerHolder pos)
private Type parseType(java.lang.String descriptor)
private Type parseType(java.lang.String descriptor, Indexer.IntegerHolder pos)
private boolean processConstantPool(java.io.DataInputStream stream)
throws java.io.IOException
java.io.IOExceptionpublic ClassInfo index(java.io.InputStream stream) throws java.io.IOException
stream - a stream pointing to class file datajava.io.IOException - if the class file data is corrupt or the underlying stream failspublic Index complete()