Windows: Use the "big" PE object format on amd64
ClosedPublic

Authored by bgamari on Mon, Nov 26, 6:04 PM.

Details

Summary

Otherwise we tend to blow through the 32k PE section limit. See Trac #15934.

Test Plan

Do full build on Windows.

Diff Detail

Repository
rGHC Glasgow Haskell Compiler
Lint
Automatic diff as part of commit; lint not applicable.
Unit
Automatic diff as part of commit; unit tests not applicable.
bgamari created this revision.Mon, Nov 26, 6:04 PM
Phyx added a comment.Tue, Nov 27, 2:02 AM

This is fine, I'm surprised the linker flag is needed though. Seems like an LD bug. Only question I have is about the 32 bit builds, I'm assuming non-prifiling builds don't have this issue but now gas will ignore -mbig-obj but ld will probably error out.

So I think the case needs to only apply to x86_64-w64-mingw32 for now so non-prifiling builds work.
For the 32 bit builds we should either force split-sections off for the profiling libs or fix binutils. The latter doesn't seem to be that difficult. Most of the code in the patch is generic bfd anyway.

Can you make a binutils PR for this? I'll try to do it this weekend.

AndreasK requested changes to this revision.Tue, Nov 27, 3:22 PM

There seems to be some sort of syntax error in your changes.

checking whether C compiler has an LLVM back end... no
checking Setting up CFLAGS, LDFLAGS, IGNORE_LINKER_LD_FLAGS and CPPFLAGS... ./configure: line 9512: syntax error near unexpected token `when'
./configure: line 9512: `    case $target when'
This revision now requires changes to proceed.Tue, Nov 27, 3:22 PM

There seems to be some sort of syntax error in your changes.

checking whether C compiler has an LLVM back end... no
checking Setting up CFLAGS, LDFLAGS, IGNORE_LINKER_LD_FLAGS and CPPFLAGS... ./configure: line 9512: syntax error near unexpected token `when'
./configure: line 9512: `    case $target when'

I could have sworn I pushed a new revision with this fixed.

bgamari updated this revision to Diff 18911.Tue, Nov 27, 4:30 PM

Really fix it

bgamari updated this revision to Diff 18912.Tue, Nov 27, 4:34 PM

Really fix it

Phyx added inline comments.Tue, Nov 27, 4:49 PM
aclocal.m4
699 ↗(On Diff #18912)

This is still wrong and will break the 32 bit builds in mysterious ways due to the --oformat,pe-bigobj-x86-64

bgamari updated this revision to Diff 18919.Wed, Nov 28, 9:43 AM

Fix it for good

AndreasK requested changes to this revision.Wed, Nov 28, 3:34 PM

CI doesn't lie I also get

/bin/sh: inplace/bin/ghc-cabal.exe: cannot execute binary file: Exec format error
This revision now requires changes to proceed.Wed, Nov 28, 3:34 PM
Phyx added a comment.Wed, Nov 28, 4:10 PM

Yes, because of --oformat,pe-bigobj-x86-64, --oformat is used to set the output format, but there isn't such a format for PE (the name in bfd is a bit misleading). The bigobj is as the name implies a COFF format, e.g. only for object files.
--oformat,pe-bigobj-* is only needed if you're doing pre-linking with -r. For the final PE binary, there's no way you should have no# sections anywhere near the limit of of the PE file anyway, as the linker would have merged the subsections again.

what exactly was the error that made you think this was needed @bgamari ?

what exactly was the error that made you think this was needed @bgamari ?

C://ghc//msys64//home//Andi//ghc_head//inplace//mingw//bin/as.exe: C:\\ghc\\msys64\\tmp\\ghc6664_0\\ghc_6.p_o: too many sections (32801)
C:\\ghc\\msys64\\tmp\\ghc6664_0\\ghc_1.s: Assembler messages:
C:\\ghc\\msys64\\tmp\\ghc6664_0\\ghc_1.s: Fatal error: can't write 4 bytes to section .rdata$c1w2b_str of C:\\ghc\\msys64\\tmp\\ghc6664_0\\ghc_6.p_o because: 'File too big'
C://ghc//msys64//home//Andi//ghc_head//inplace//mingw//bin/as.exe: C:\\ghc\\msys64\\tmp\\ghc6664_0\\ghc_6.p_o: too many sections (32801)
C:\\ghc\\msys64\\tmp\\ghc6664_0\\ghc_1.s: Fatal error: can't close C:\\ghc\\msys64\\tmp\\ghc6664_0\\ghc_6.p_o: File too big
`gcc.exe' failed in phase `Assembler'. (Exit code: 1)
make[1]: *** [libraries/template-haskell/ghc.mk:4: libraries/template-haskell/dist-install/build/Language/Haskell/TH/Syntax.p_o] Error 1
make[1]: *** Waiting for unfinished jobs....
make: *** [Makefile:128: all] Error 2
Phyx added a comment.Wed, Nov 28, 4:21 PM

what exactly was the error that made you think this was needed @bgamari ?

C://ghc//msys64//home//Andi//ghc_head//inplace//mingw//bin/as.exe: C:\\ghc\\msys64\\tmp\\ghc6664_0\\ghc_6.p_o: too many sections (32801)
C:\\ghc\\msys64\\tmp\\ghc6664_0\\ghc_1.s: Assembler messages:
C:\\ghc\\msys64\\tmp\\ghc6664_0\\ghc_1.s: Fatal error: can't write 4 bytes to section .rdata$c1w2b_str of C:\\ghc\\msys64\\tmp\\ghc6664_0\\ghc_6.p_o because: 'File too big'
C://ghc//msys64//home//Andi//ghc_head//inplace//mingw//bin/as.exe: C:\\ghc\\msys64\\tmp\\ghc6664_0\\ghc_6.p_o: too many sections (32801)
C:\\ghc\\msys64\\tmp\\ghc6664_0\\ghc_1.s: Fatal error: can't close C:\\ghc\\msys64\\tmp\\ghc6664_0\\ghc_6.p_o: File too big
`gcc.exe' failed in phase `Assembler'. (Exit code: 1)
make[1]: *** [libraries/template-haskell/ghc.mk:4: libraries/template-haskell/dist-install/build/Language/Haskell/TH/Syntax.p_o] Error 1
make[1]: *** Waiting for unfinished jobs....
make: *** [Makefile:128: all] Error 2

that's the assembler error, -Wa,-mbig-obj should have fixed that.

but on the ticket he says

However, things then fail at linking. I believe this will be fixed by passing --oformat pe-bigobj-x86-64 to the linker, although this hasn't been confirmed yet.

Which is a bit suspicious.. unless the link errors are coming from the ghci whole-object files we prelink, but that shouldn't be it since we provide a linker scripts to merge those sections during prelinking.

That's the assembler error, -Wa,-mbig-obj should have fixed that.

It did, I had assumed you asked about the initial error, my bad.

When setting the assembler flag we get a linker error that's essentially the same when passing the asm flag. But I haven't kept the log around for the exact wording.

I think for the file in question we also generate a C stub for stable pointers.
It might happen when combining the stub and haskell code into one object file?

Phyx added a comment.Wed, Nov 28, 4:39 PM

I think for the file in question we also generate a C stub for stable pointers.
It might happen when combining the stub and haskell code into one object file?

Hm that could be if it's combining two object files into one. In which case the control needs to be a tad more fine grained.

Setting LD_FLAGS here will have the unfortunate effect of also affecting the final link.

AndreasK added a comment.EditedWed, Nov 28, 5:24 PM
In D5383#148498, @Phyx wrote:

I think for the file in question we also generate a C stub for stable pointers.
It might happen when combining the stub and haskell code into one object file?

Hm that could be if it's combining two object files into one. In which case the control needs to be a tad more fine grained.

Setting LD_FLAGS here will have the unfortunate effect of also affecting the final link.

Given that the issue could just as well arise in user code outside of GHC maybe the proper fix would be to adjust the assembler/linker invocation ghc uses.

In D5383#148498, @Phyx wrote:

I think for the file in question we also generate a C stub for stable pointers.
It might happen when combining the stub and haskell code into one object file?

Hm that could be if it's combining two object files into one. In which case the control needs to be a tad more fine grained.

Setting LD_FLAGS here will have the unfortunate effect of also affecting the final link.

Ahh, yes, this sounds plausible. Patch coming.

bgamari updated this revision to Diff 18932.Thu, Nov 29, 10:08 AM

A new beginning

bgamari updated this revision to Diff 18934.Thu, Nov 29, 10:44 AM

Windows is not OSWindows

AndreasK added inline comments.Thu, Nov 29, 12:07 PM
compiler/main/DriverPipeline.hs
1342

Will this work on 32bit windows?

Phyx added inline comments.Thu, Nov 29, 12:22 PM
compiler/main/DriverPipeline.hs
1342

None of this will. Even if the assembler ignores the flag (which it may) the oformat,pe-bigobj-x86-64 is very wrong.

2204

Needs to be gated on 64 bit targets. This will force the 32 bit builds to produce a 64 bit object file.

bgamari updated this revision to Diff 18936.Thu, Nov 29, 1:54 PM

It finally works

bgamari updated this revision to Diff 18937.Thu, Nov 29, 1:58 PM

Guard on 64-bit target

bgamari marked 2 inline comments as done.Thu, Nov 29, 1:58 PM
bgamari updated this revision to Diff 18939.Thu, Nov 29, 6:45 PM

The last straw

AndreasK accepted this revision.Wed, Dec 5, 3:39 PM

@bgamari Reminder to put this also into 8.8

This revision is now accepted and ready to land.Wed, Dec 5, 3:39 PM
This revision was automatically updated to reflect the committed changes.