Bug ID: 77997
           Summary: Miscompilation due to LTO on aarch64
           Product: gcc
           Version: 6.2.1
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: lto
          Assignee: unassigned at gcc dot
          Reporter: yyc1992 at gmail dot com
  Target Milestone: ---

I'm seeing a miscompilation of LLVM's tablegen on AArch64 by gcc 6.2.1 when LTO
is enabled. I've tried very hard to reduce it but unfortunately it wasn't very
successful this time and the current repro is still 8000 lines of code.

Attached are the source and resulting binaries. (Edit: the tarball is too big
(3M) so I uploaded to gist instead. Please find it here

The `code/` directory has a simple cmake projects reduced from the LLVM one (I
can turn that into a makefile or a shell script on request but the current form
should be pretty simple already). To reproduce make a `build/` directory in
`code/` and run `CFLAGS='-flto -O3' CXXFLAGS='-flto -O3' LDFLAGS='-O3 -flto'
cmake .. -DCMAKE_BUILD_TYPE=Release; make llvm-tblgen; bin/llvm-tblgen`. Remove
the `-flto` should get rid of the error in the last command.

Changes in seemingly unrelated lines can also make the error go away. (If
there's anything I learnt from reducing it, the error seems to appear only when
the code is complex....). One of such changes is commenting out
`SCTrans.PredTerm = Preds;` close to the end of `CodeGenSchedule.cpp` (used to
generate the `good/` version included). In fact, removing almost any lines in
this file can make the error go away even though not a single line of code
there should be executed.

The `bad/` and the `good/` directories conatins compilation results using the
flags mentioned above with the unmodified code and the code with the one line
commented out. They have all the object files, binary files and the disassemble
of the resulting executable/the bad function. The asm's are disassembled from
the final binary since I don't know how to get it directly when compiling with

The direct error seems to be in `CodeGenRegister::computeSubRegs` in the branch
before the `printf("5\n")`. The `DenseMap::insert` method (which is called
twice in this function and nowhere else) is inlined but returns corrupted
iterator sometimes when the inserted key already exists in the map causing the
check to fail. The difference of asm of this function is in the toplevel of the

Original repro is compiling LLVM with LTO on on AArch64. The compilation should
fail when generating target information for AArch64.

GCC version is GCC binary package from ArchLinux ARM repo. `gcc --version`
gives `gcc (GCC) 6.2.1 20160830`

Reply via email to