Returns the size of the method_info JVMS structure generated by this MethodWriter. Also add the names of the attributes of this method in the constant pool. @return the size in bytes of the method_info JVMS structure.
()
| 2048 | * @return the size in bytes of the method_info JVMS structure. |
| 2049 | */ |
| 2050 | int computeMethodInfoSize() { |
| 2051 | // If this method_info must be copied from an existing one, the size computation is trivial. |
| 2052 | if (sourceOffset != 0) { |
| 2053 | // sourceLength excludes the first 6 bytes for access_flags, name_index and descriptor_index. |
| 2054 | return 6 + sourceLength; |
| 2055 | } |
| 2056 | // 2 bytes each for access_flags, name_index, descriptor_index and attributes_count. |
| 2057 | int size = 8; |
| 2058 | // For ease of reference, we use here the same attribute order as in Section 4.7 of the JVMS. |
| 2059 | if (code.length > 0) { |
| 2060 | if (code.length > 65535) { |
| 2061 | throw new IndexOutOfBoundsException("Method code too large!"); |
| 2062 | } |
| 2063 | symbolTable.addConstantUtf8(Constants.CODE); |
| 2064 | // The Code attribute has 6 header bytes, plus 2, 2, 4 and 2 bytes respectively for max_stack, |
| 2065 | // max_locals, code_length and attributes_count, plus the bytecode and the exception table. |
| 2066 | size += 16 + code.length + Handler.getExceptionTableSize(firstHandler); |
| 2067 | if (stackMapTableEntries != null) { |
| 2068 | boolean useStackMapTable = symbolTable.getMajorVersion() >= Opcodes.V1_6; |
| 2069 | symbolTable.addConstantUtf8(useStackMapTable ? Constants.STACK_MAP_TABLE : "StackMap"); |
| 2070 | // 6 header bytes and 2 bytes for number_of_entries. |
| 2071 | size += 8 + stackMapTableEntries.length; |
| 2072 | } |
| 2073 | if (lineNumberTable != null) { |
| 2074 | symbolTable.addConstantUtf8(Constants.LINE_NUMBER_TABLE); |
| 2075 | // 6 header bytes and 2 bytes for line_number_table_length. |
| 2076 | size += 8 + lineNumberTable.length; |
| 2077 | } |
| 2078 | if (localVariableTable != null) { |
| 2079 | symbolTable.addConstantUtf8(Constants.LOCAL_VARIABLE_TABLE); |
| 2080 | // 6 header bytes and 2 bytes for local_variable_table_length. |
| 2081 | size += 8 + localVariableTable.length; |
| 2082 | } |
| 2083 | if (localVariableTypeTable != null) { |
| 2084 | symbolTable.addConstantUtf8(Constants.LOCAL_VARIABLE_TYPE_TABLE); |
| 2085 | // 6 header bytes and 2 bytes for local_variable_type_table_length. |
| 2086 | size += 8 + localVariableTypeTable.length; |
| 2087 | } |
| 2088 | if (lastCodeRuntimeVisibleTypeAnnotation != null) { |
| 2089 | size += |
| 2090 | lastCodeRuntimeVisibleTypeAnnotation.computeAnnotationsSize( |
| 2091 | Constants.RUNTIME_VISIBLE_TYPE_ANNOTATIONS); |
| 2092 | } |
| 2093 | if (lastCodeRuntimeInvisibleTypeAnnotation != null) { |
| 2094 | size += |
| 2095 | lastCodeRuntimeInvisibleTypeAnnotation.computeAnnotationsSize( |
| 2096 | Constants.RUNTIME_INVISIBLE_TYPE_ANNOTATIONS); |
| 2097 | } |
| 2098 | if (firstCodeAttribute != null) { |
| 2099 | size += |
| 2100 | firstCodeAttribute.computeAttributesSize( |
| 2101 | symbolTable, code.data, code.length, maxStack, maxLocals); |
| 2102 | } |
| 2103 | } |
| 2104 | if (numberOfExceptions > 0) { |
| 2105 | symbolTable.addConstantUtf8(Constants.EXCEPTIONS); |
| 2106 | size += 8 + 2 * numberOfExceptions; |
| 2107 | } |
no test coverage detected