This is the mail archive of the java-patches@gcc.gnu.org mailing list for the Java project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[gcjx] Patch: FYI: compute correct max_locals


I'm checking this in on the gcjx branch.

This is actually a fix to the previous patch.  When an interrupted
'return' expression has 'long' type we failed to allocate two local
variable slots.  This actually occurs in libgcj.

With this change, I can run the libgcj.jar generated by gcjx through
the current gcj with the new verifier enabled [1].  To me this says
that we generate verifiable bytecode in many situations.

Tom

[1] There is actually one complaint, but that is a bug in the
verifier.  The bug is that the verifier on the trunk does not know
that Object.<init> is a special case for checking whether 'this' is
initialized.  This bug is fixed in the verifier on the gcjx branch.
It didn't seem important enough to warrant fixing on the trunk.


Index: ChangeLog
from  Tom Tromey  <tromey@redhat.com>

	* bytecode/generate.cc (visit_method): Updated.
	(visit_return): Use request().
	* bytecode/locals.cc (request(bool)): New method.
	(request(model_variable_decl*)): Use it.
	(request()): New method.
	* bytecode/locals.hh (locals::request): Declare.

Index: bytecode/generate.cc
===================================================================
RCS file: /cvs/gcc/gcc/gcjx/bytecode/Attic/generate.cc,v
retrieving revision 1.1.2.12
diff -u -r1.1.2.12 generate.cc
--- bytecode/generate.cc 18 May 2005 00:17:22 -0000 1.1.2.12
+++ bytecode/generate.cc 18 May 2005 00:17:45 -0000
@@ -399,7 +399,7 @@
 
   if (! meth->static_p ())
     {
-      this_index = vars.request (NULL);
+      this_index = vars.request ((model_variable_decl *) NULL);
       // This must always be true.
       assert (! this_index);
     }
@@ -899,7 +899,7 @@
       // assign to it, then reload it before the return.
       if (! finally_stack.empty ())
 	{
-	  tmpvar = vars.request (NULL);
+	  tmpvar = vars.request ();
 	  emit_store (expr->type (), tmpvar);
 	}
     }
Index: bytecode/locals.cc
===================================================================
RCS file: /cvs/gcc/gcc/gcjx/bytecode/Attic/locals.cc,v
retrieving revision 1.1.2.7
diff -u -r1.1.2.7 locals.cc
--- bytecode/locals.cc 20 Apr 2005 16:05:01 -0000 1.1.2.7
+++ bytecode/locals.cc 18 May 2005 00:17:45 -0000
@@ -35,17 +35,14 @@
 }
 
 int
-locals::request (model_variable_decl *decl)
+locals::request (bool is_wide)
 {
-  assert (decl == NULL || vars.find (decl) == vars.end ());
-  int n;
-  int delta = 0;
-  if (wide_p (decl ? decl->type () : NULL))
-    delta = 1;
+  int delta = is_wide ? 1 : 0;
 
   // This loop is written a little strangely so that it will always
   // terminate with N == MAX if we didn't find a large enough empty
   // space.
+  int n;
   for (n = 0; n < max; ++n)
     {
       if (! used[n] && (n + delta < max && ! used[n + delta]))
@@ -60,6 +57,15 @@
   used[n] = true;
   used[n + delta] = true;
 
+  return n;
+}
+
+int
+locals::request (model_variable_decl *decl)
+{
+  assert (decl == NULL || vars.find (decl) == vars.end ());
+  int n = request (decl ? wide_p (decl->type ()) : false);
+
   if (decl)
     {
       debug_info info;
@@ -74,6 +80,12 @@
 }
 
 int
+locals::request ()
+{
+  return request (true);
+}
+
+int
 locals::get_index (model_variable_decl *decl)
 {
   // It would be way easier to have a field on the variable.
Index: bytecode/locals.hh
===================================================================
RCS file: /cvs/gcc/gcc/gcjx/bytecode/Attic/locals.hh,v
retrieving revision 1.1.2.5
diff -u -r1.1.2.5 locals.hh
--- bytecode/locals.hh 20 Apr 2005 16:05:01 -0000 1.1.2.5
+++ bytecode/locals.hh 18 May 2005 00:17:45 -0000
@@ -69,6 +69,8 @@
   // Number of variables that survived updating.
   int valid;
 
+  int request (bool);
+
 public:
 
   locals (bytecode_generator *g)
@@ -91,6 +93,12 @@
   // managed more explicitly.
   int request (model_variable_decl *);
 
+  // Request a new slot for a wide variable.  The variable is assumed
+  // to be synthetic and must be explicitly managed.  That is, removal
+  // must be handled via the special remove() method for synthetic
+  // variables.
+  int request ();
+
   // Find the index of an existing local.
   int get_index (model_variable_decl *);
 


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]