static void print_annotation (FILE *stream, JCF *jcf, int level) { uint16 type_index = JCF_readu2 (jcf); uint16 npairs = JCF_readu2 (jcf); fprintf (stream, "\n"); indent (stream, level); fprintf (stream, "Annotation name: "); print_constant_terse_with_index (stream, jcf, type_index, CONSTANT_Utf8); if (npairs) { fprintf (stream, "\n"); while (npairs--) { uint16 name_index = JCF_readu2 (jcf); indent (stream, level + 1); fprintf (stream, "Name: "); print_constant_terse_with_index (stream, jcf, name_index, CONSTANT_Utf8); fprintf (stream, "\n"); print_element_value (stream, jcf, level + 2); } } }
static void print_exception_table (JCF *jcf, const unsigned char *entries, int count) { /* Print exception table. */ int i = count; if (i > 0) { const unsigned char *ptr = entries; fprintf (out, "Exceptions (count: %d):\n", i); for (; --i >= 0; ptr+= 8) { int start_pc = GET_u2 (ptr); int end_pc = GET_u2 (ptr+2); int handler_pc = GET_u2 (ptr+4); int catch_type = GET_u2 (ptr+6); fprintf (out, " start: %d, end: %d, handler: %d, type: ", start_pc, end_pc, handler_pc); if (catch_type == 0) fputs ("0 /* finally */", out); else print_constant_terse_with_index (out, jcf, catch_type, CONSTANT_Class); fputc ('\n', out); } } }
static void print_element_value (FILE *stream, JCF *jcf, int level) { uint8 tag = JCF_readu (jcf); indent (stream, level); switch (tag) { case 'B': case 'C': case 'S': case 'Z': case 'I': { uint16 cindex = JCF_readu2 (jcf); print_constant_terse_with_index (stream, jcf, cindex, CONSTANT_Integer); } break; case 'D': { uint16 cindex = JCF_readu2 (jcf); print_constant_terse_with_index (stream, jcf, cindex, CONSTANT_Double); } break; case 'F': { uint16 cindex = JCF_readu2 (jcf); print_constant_terse_with_index (stream, jcf, cindex, CONSTANT_Float); } break; case 'J': { uint16 cindex = JCF_readu2 (jcf); print_constant_terse_with_index (stream, jcf, cindex, CONSTANT_Long); } break; case 's': { uint16 cindex = JCF_readu2 (jcf); /* Despite what the JVM spec says, compilers generate a Utf8 constant here, not a String. */ print_constant_terse_with_index (stream, jcf, cindex, CONSTANT_Utf8); } break; case 'e': { uint16 type_name_index = JCF_readu2 (jcf); uint16 const_name_index = JCF_readu2 (jcf); fprintf (stream, "enum class: "); print_constant_terse_with_index (stream, jcf, type_name_index, CONSTANT_Utf8); fprintf (stream, "\n"); indent (stream, level); fprintf (stream, "Field: "); print_constant_terse_with_index (stream, jcf, const_name_index, CONSTANT_Utf8); } break; case 'c': { uint16 class_info_index = JCF_readu2 (jcf); print_constant_terse_with_index (stream, jcf, class_info_index, CONSTANT_Utf8); } break; case '@': { fprintf (stream, "Annotation:\n"); print_annotation (stream, jcf, level + 1); } break; case '[': { uint16 n_array_elts = JCF_readu2 (jcf); fprintf (stream, "array[%d]: [\n", (int) n_array_elts); while (n_array_elts--) print_element_value (stream, jcf, level + 1); indent (stream, level); fprintf (stream, "]"); } break; default: fprintf (stream, "Unexpected tag value: %d", (int) tag); break; } fputc ('\n', stream); }