https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68759
Ulrich Weigand <uweigand at gcc dot gnu.org> changed: What |Removed |Added ---------------------------------------------------------------------------- Status|UNCONFIRMED |ASSIGNED Last reconfirmed| |2015-12-07 CC| |amodra at gcc dot gnu.org, | |dje.gcc at gmail dot com Assignee|unassigned at gcc dot gnu.org |uweigand at gcc dot gnu.org Ever confirmed|0 |1 --- Comment #4 from Ulrich Weigand <uweigand at gcc dot gnu.org> --- OK, with this .config I was able to recreate the problem. Thanks! The immediate cause for the ERROR (which is reported by the kernel's modpost tool) is that object files contain undefined references against symbols that are actually *defined* in the same object file as local symbols. This weird situation is the result of some very special object file magic performed by the perl script ./scripts/recordmcount.pl, which is apparently supposed to record all call sites to the _mcount routine into a special section, and uses rather complex logic to do so, which involves parsing the output of objdump. This objdump parsing in turn seems to get thrown out of sync if the object file's .text sections contain data blocks outside of functions (or at least, before the very first function). For the sparc64 target, there is special code in the recordmcount.pl script to handle this situation, but not for powerpc. This didn't matter so far since on powerpc, this could never happen. However, it turns out that kernel modules are built with -mcmodel=large for some reason, and therefore after my patch, we do indeed see a data block before the first function. Using the same trick as on sparc64 makes the build go through again: diff --git a/scripts/recordmcount.pl b/scripts/recordmcount.pl index 826470d..96e2486 100755 --- a/scripts/recordmcount.pl +++ b/scripts/recordmcount.pl @@ -263,7 +263,8 @@ if ($arch eq "x86_64") { } elsif ($arch eq "powerpc") { $local_regex = "^[0-9a-fA-F]+\\s+t\\s+(\\.?\\S+)"; - $function_regex = "^([0-9a-fA-F]+)\\s+<(\\.?.*?)>:"; + # See comment in the sparc64 section for why we use '\w'. + $function_regex = "^([0-9a-fA-F]+)\\s+<(\\.?\\w*?)>:"; $mcount_regex = "^\\s*([0-9a-fA-F]+):.*\\s\\.?_mcount\$"; if ($bits == 64) { Alan, have you seen this recordmcount.pl script before? Is there really no simpler way to achieve what this wants to do? B.t.w. given that kernel modules are build with -mcmodel=large, this probably means that we'll now have to teach the kernel module loader to handle the R_PPC64_ENTRY reloc. I guess we need to talk to the kernel folks.