[Lldb-commits] [PATCH] D129455: [lldb] Reduce the stack alignment requirements for the Windows x86_64 ABI

Martin Storsjö via Phabricator via lldb-commits lldb-commits at lists.llvm.org
Mon Jul 11 03:38:47 PDT 2022


mstorsjo added a comment.

In D129455#3641967 <https://reviews.llvm.org/D129455#3641967>, @labath wrote:

> You say that the issue is the lack of symtab in the "msvc" mode. What makes this test work then?

When invoked via the `%build` python script (lldb/test/Shell/helper/build.py), clang is invoked with extra options (`/Z7`) that generate codeview debug info, and then later the linker is invoked with extra options (`/DEBUG:FULL` and `'/PDB:' + self._pdb_file_name())`) to write that codeview debug info into a separate standalone PDB file.

In the MSVC ecosystem, executables/DLLs never have embedded debug info - it's always in a separate PDB file. Contrary to the GCC-compatible ecosystem, debug info is opt-in here, not opt-out (e.g. if linking with a unix linker, you get the symbol table and debug info included automatically unless you pass `-Wl,-s` or strip things separately afterwards). In the MSVC ecosystem, the only way to have a symbol table (without actual dwarf debug info) is with a PDB file.

In the mingw ecosystem, things behave as on unix - you get any embedded DWARF debug info included in the executable by default, and a symbol table - both which can be stripped out afterwards.

> Do some of the assembler directives (`.def`?) produce some sort of debug info entries?

Those just set the symbol type to "function" - it could be omitted from this test for clarity.

> What determines the modes that clang is operating in? Is it the default target triple?

Exactly.

Additionally, there's a couple more tooling differences that makes things a bit more complicated:

In the MSVC ecosystem, you normally would execute cl.exe (the MSVC compiler) or clang-cl (the cl.exe compatible clang frontend) - which has got an option syntax that is distinct and mostly incompatible from the gcc-compatible normal `clang` interface.

Despite this, you can also build code in MSVC mode with the regular gcc-compatible clang interface (either by passing e.g. `--target=x86_64-windows-msvc` or if such a triple is the deafult target triple). You can do most things in this setup too, but some MSVC-isms are tricky to achieve. This is what the `%clang_host` lit test macro does. Regular compiling, e.g. `%clang_host input.c -o executable -luser32` works fine for both MSVC and mingw mode.

In the MSVC ecosystem, you very rarely use the compiler driver to run linking - you'd normally execute `link.exe` or `lld-link` directly. If linking via the gcc-compatible clang interface, options passed to the linked with `-Wl,` need to be link.exe/lld-link options, which a unix-style linker obviously doesn't recognize.

> What does `-Wl,-debug:symtab` actually produce?

It produces an executable embedded symbol table, like in mingw mode. This is a lld specific option, MS's upstream link.exe doesn't support this option (it supports other parameters to `-debug:` but `symtab` is lld's invention). LLDB happily picks up and uses that (for mingw built executables it's the default case anyway).

> Would it make sense to make it a part of the `%clang_host` substitution (only for the msvc mode) to make the output of %clang_host more uniform? Or maybe achieve equivalence in some other way (add `-g1`, or similar, to the cmd line)?

I think that might be a sensible path forward in general! But as noted, I'd rather not hold up this trivial patch with that. (Also I'm a bit more short on time at the moment than usual, but I'm trying to get low hanging fruit merged before the llvm 15 branch deadline.)

> as I think it would be very useful if we could figure out a way to make this test (and others) cross-platform, so we don't have to have two versions of all of them.

A bunch of tests might be doable crossplatform that way, but any tests that involve assembly might be tricky. On i386, arm and aarch64, Windows has got mostly the same calling conventions as other OSes, but on x86_64, it's radically different - arguments are passed in different registers than on x86_64 unix. Additionally, the caller is required to allocate shadow space on the stack for all arguments passed in registers (the extra `subq $32, %rsp`) so that the callee can dump them there if wanted. And finally, this particular testcase generates SEH unwind instructions with the `.seh_*` directives. (I didn't test whether the testcase would work without the SEH unwind instructions or not - I made it to look mostly like what a regular Windows function would look like.)


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D129455/new/

https://reviews.llvm.org/D129455



More information about the lldb-commits mailing list