Andrew Haley wrote:
David Daney writes:
> Tom Tromey wrote:
> >>>>>> "David" == David Daney <[EMAIL PROTECTED]> writes:
> >
> > David> The call to _ZN4java4lang6ObjectC1Ev is being generated as non-pic,
> > David> even though that symbol is defined in libgcj.so. The assembler and
> > David> linker conspire to jump to address 0x00000000 for this call.
> >
> > Could also be the problem reported at the end of:
> >
> > http://gcc.gnu.org/bugzilla/show_bug.cgi?id=30606
> >
> > Tom
>
> I suspect it is the same problem. APH's patch would not have fixed it
> if it were.
OK. Does your patch work? If it does, I'm going to trace through jc1
to see if I can find the real origin of this regression.
I am testing a new patch that (I think) fixes the real problem. I am
not sure why it regressed as Richard added the code that was being made
to fail last March. The bad code was in class.c when green committed it
over 8 years ago. Several months ago Tromey removed it and then added
it back a few days later.
The problem is that in is_compiled_class() we were erroneously saying
that a candidate class was being emitted to the object file *if* it was
the current_class being parsed. This does not hold because many classes
are parsed that are not emitted so that jc1 can calculate the class
layout and load the symbol tables.
The real fix,I think, is the one I made to is_compiled_class(). I left
the change to layout_class_method() where we don't re-check for
DECL_EXTERNAL if it is already set as a micro-optimization. I tested
both with and without this and obtained correct results, so it is not
really needed.
I also wonder if your previous patch setting DECL_EXTERNAL is still
needed after this has been applied. I didn't check.
I am currently regression testing the attached patch on
x86_64-pc-linux-gnu, and will post it to gcc-patches@ if it passes.
David Daney.
Index: gcc/java/class.c
===================================================================
--- gcc/java/class.c (revision 121441)
+++ gcc/java/class.c (working copy)
@@ -2134,10 +2134,6 @@ is_compiled_class (tree class)
return 1;
if (TYPE_ARRAY_P (class))
return 0;
- /* We have to check this explicitly to avoid trying to load a class
- that we're currently parsing. */
- if (class == current_class)
- return 2;
seen_in_zip = (TYPE_JCF (class) && JCF_SEEN_IN_ZIP (TYPE_JCF (class)));
if (CLASS_FROM_CURRENTLY_COMPILED_P (class))
@@ -2147,7 +2143,7 @@ is_compiled_class (tree class)
been loaded already. Load it if necessary. This prevent
build_class_ref () from crashing. */
- if (seen_in_zip && !CLASS_LOADED_P (class))
+ if (seen_in_zip && !CLASS_LOADED_P (class) && (class != current_class))
load_class (class, 1);
/* We return 2 for class seen in ZIP and class from files
@@ -2161,7 +2157,7 @@ is_compiled_class (tree class)
{
if (CLASS_FROM_SOURCE_P (class))
safe_layout_class (class);
- else
+ else if (class != current_class)
load_class (class, 1);
}
return 1;
@@ -2510,10 +2506,12 @@ layout_class_method (tree this_class, tr
tree method_name = DECL_NAME (method_decl);
TREE_PUBLIC (method_decl) = 1;
+
/* Considered external unless it is being compiled into this object
- file. */
- DECL_EXTERNAL (method_decl) = ((is_compiled_class (this_class) != 2)
- || METHOD_NATIVE (method_decl));
+ file, or it was already flagged as external. */
+ if (!DECL_EXTERNAL (method_decl))
+ DECL_EXTERNAL (method_decl) = ((is_compiled_class (this_class) != 2)
+ || METHOD_NATIVE (method_decl));
if (ID_INIT_P (method_name))
{