jcf-reader.c (jcf_parse_one_method): Recognize HANDLE_END_METHOD.
authorTom Tromey <tromey@cygnus.com>
Sun, 13 Dec 1998 13:29:08 +0000 (13:29 +0000)
committerTom Tromey <tromey@gcc.gnu.org>
Sun, 13 Dec 1998 13:29:08 +0000 (13:29 +0000)
* jcf-reader.c (jcf_parse_one_method): Recognize
HANDLE_END_METHOD.
* gjavah.c (HANDLE_END_METHOD): New macro.
(HANDLE_CODE_ATTRIBUTE): New macro.
(decompile_method): New function.
(print_method_info): Don't print `;\n' at end of function decl.
Include java-opcodes.h.
(decompiled): New global.

From-SVN: r24295

gcc/java/ChangeLog
gcc/java/gjavah.c
gcc/java/jcf-reader.c

index ff6829b..adf8787 100644 (file)
@@ -1,3 +1,14 @@
+1998-12-13  Tom Tromey  <tromey@cygnus.com>
+
+       * jcf-reader.c (jcf_parse_one_method): Recognize
+       HANDLE_END_METHOD.
+       * gjavah.c (HANDLE_END_METHOD): New macro.
+       (HANDLE_CODE_ATTRIBUTE): New macro.
+       (decompile_method): New function.
+       (print_method_info): Don't print `;\n' at end of function decl.
+       Include java-opcodes.h.
+       (decompiled): New global.
+
 Sat Dec 12 20:13:19 1998  Per Bothner  <bothner@cygnus.com>
 
        * class.c (build_class_ref):  Handle PRIMTYPE.class if
index ed8e9e9..eec27b3 100644 (file)
@@ -33,6 +33,8 @@ The Free Software Foundation is independent of Sun Microsystems, Inc.  */
 
 #include <string.h>
 
+#include "java-opcodes.h"
+
 /* The output file.  */
 FILE *out = NULL;
 
@@ -99,6 +101,7 @@ static struct method_name *method_name_list;
 static void print_field_info PROTO ((FILE *, JCF*, int, int, JCF_u2));
 static void print_method_info PROTO ((FILE *, JCF*, int, int, JCF_u2));
 static void print_c_decl PROTO ((FILE*, JCF*, int, int, JCF_u2, int, char *));
+static void decompile_method PROTO ((FILE *, JCF *, int));
 
 JCF_u2 current_field_name;
 JCF_u2 current_field_value;
@@ -122,7 +125,16 @@ static int field_pass;
 #define HANDLE_CONSTANTVALUE(VALUEINDEX) current_field_value = (VALUEINDEX)
 
 #define HANDLE_METHOD(ACCESS_FLAGS, NAME, SIGNATURE, ATTRIBUTE_COUNT) \
-  if (out) print_method_info (out, jcf, NAME, SIGNATURE, ACCESS_FLAGS)
+  if (out) { decompiled = 0; \
+      print_method_info (out, jcf, NAME, SIGNATURE, ACCESS_FLAGS); \
+  }
+
+#define HANDLE_CODE_ATTRIBUTE(MAX_STACK, MAX_LOCALS, CODE_LENGTH) \
+  if (out) decompile_method (out, jcf, CODE_LENGTH);
+
+static int decompiled = 0;
+#define HANDLE_END_METHOD() \
+  if (out) fputs (decompiled ? "\n" : ";\n", out);
 
 #include "jcf-reader.c"
 
@@ -439,11 +451,37 @@ DEFUN(print_method_info, (stream, jcf, name_index, sig_index, flags),
        fputs ("virtual ", out);
     }
   print_c_decl (out, jcf, name_index, sig_index, flags, is_init, override);
+}
 
-  /* FIXME: it would be nice to decompile small methods here.  That
-     would allow for inlining.  */
-
-  fprintf(out, ";\n");
+/* Try to decompile a method body.  Right now we just try to handle a
+   simple case that we can do.  Expand as desired.  */
+static void
+decompile_method (out, jcf, code_len)
+     FILE *out;
+     JCF *jcf;
+     int code_len;
+{
+  unsigned char *codes = jcf->read_ptr;
+  int index;
+  uint16 name_and_type, name;
+
+  if (code_len == 5
+      && codes[0] == OPCODE_aload_0
+      && codes[1] == OPCODE_getfield
+      && codes[4] == OPCODE_areturn)
+    {
+      /* Found something useful to decompile.  */
+      fputs (" { return ", out);
+      index = (codes[2] << 8) | codes[3];
+      /* FIXME: ensure that tag is CONSTANT_Fieldref.  */
+      /* FIXME: ensure that the field's class is this class.  */
+      name_and_type = JPOOL_USHORT2 (jcf, index);
+      /* FIXME: ensure that tag is CONSTANT_NameAndType.  */
+      name = JPOOL_USHORT1 (jcf, name_and_type);
+      print_name (out, jcf, name);
+      fputs ("; }", out);
+      decompiled = 1;
+    }
 }
 
 /* Print one piece of a signature.  Returns pointer to next parseable
index 9816ce3..f3c860f 100644 (file)
@@ -308,6 +308,9 @@ DEFUN(jcf_parse_one_method, (jcf),
       if (code != 0)
        return code;
     }
+#ifdef HANDLE_END_METHOD
+  HANDLE_END_METHOD ();
+#endif
   return 0;
 }