Skip to content

wasm-ld crashes on static library + flto #18651

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
gl84 opened this issue Feb 2, 2023 · 3 comments
Open

wasm-ld crashes on static library + flto #18651

gl84 opened this issue Feb 2, 2023 · 3 comments

Comments

@gl84
Copy link
Contributor

gl84 commented Feb 2, 2023

Building a static library with two object files leads to a wasm-ld crash. The crash can be reproduced without any linking to boost libraries (using a >= 1.80 version). For boost <= 1.79 everything works.

Version of emscripten/emsdk:

> emcc --version
emcc (Emscripten gcc/clang-like replacement + linker emulating GNU ld) 3.1.32-git (36c194dfff84504434f8db4b8161071fa71f6c97)
Copyright (C) 2014 the Emscripten authors (see AUTHORS.txt)
This is free and open source software under the MIT license.
There is NO warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.

Here is a simple repro case:
reader.hpp:

struct reader {
    public:
        reader() {}
        ~reader();
};

reader.cpp:

#include "reader.hpp"
#include <boost/filesystem.hpp>
reader::~reader() {}

exported_api.cpp:

#include "emscripten.h"
#include <boost/filesystem.hpp>
#include "reader.hpp"
extern "C" {
    EMSCRIPTEN_KEEPALIVE void reader_destroy(reader* r) {
        delete r;
    }
}

Building the object files, using emar to combine them and finally producing a side module leads to a wasm-ld crash:
emcc -flto -O0 -o exported_api.cpp.o -c exported_api.cpp -I/home/user/boost_1.80_headers/
emcc -flto -O0 -o reader.cpp.o -c reader.cpp -I/home/user/boost_1.80_headers/
emar -rcs lib_combined.a reader.cpp.o exported_api.cpp.o
emcc -O3 -o lib.wasm lib_combined.a -sSIDE_MODULE=2 -sEXPORTED_FUNCTIONS=[_reader_destroy]

Rerunning the wasm-ld part with --verbose gives:

wasm-ld: Loading: lib_combined.a
wasm-ld: Processing: lib_combined.a
wasm-ld: Processing: lib_combined.a(exported_api.cpp.o)
wasm-ld: Processing: lib_combined.a(reader.cpp.o)
wasm-ld: -- createOutputSegments
wasm-ld: -- createSyntheticSections
wasm-ld: -- layoutMemory
wasm-ld: mem: global base = 0
wasm-ld: mem: .bss            offset=0        size=28       align=2
wasm-ld: mem: static data = 28
wasm-ld: mem: total pages = 1
wasm-ld: -- populateTargetFeatures
wasm-ld: Allowed feature: mutable-globals
wasm-ld: Allowed feature: sign-ext
wasm-ld: -- combineOutputSegments
wasm-ld: -- createSyntheticSectionsPostLayout
wasm-ld: -- populateProducers
wasm-ld: -- calculateImports
wasm-ld: -- scanRelocations
wasm-ld: -- finalizeIndirectFunctionTable
wasm-ld: -- createSyntheticInitFunctions
wasm-ld: -- assignIndexes
wasm-ld: -- calculateInitFunctions
wasm-ld: /b/s/w/ir/cache/builder/emscripten-releases/llvm-project/llvm/include/llvm/Support/Casting.h:579: decltype(auto) llvm::cast(From *) [To = lld::wasm::DefinedFunction, From = const lld::wasm::FunctionSymbol]: Assertion `isa<To>(Val) && "cast<Ty>() argument of incompatible type!"' failed.
PLEASE submit a bug report to https://github.com/llvm/llvm-project/issues/ and include the crash backtrace.
Stack dump:
0.      Program arguments: /home/user/emsdk_tot/emsdk/upstream/bin/wasm-ld --verbose -o lib.wasm lib_combined.a -L/home/user/emsdk_tot/emsdk/upstream/emscripten/cache/sysroot/lib/wasm32-emscripten/pic -mllvm -combiner-global-alias-analysis=false -mllvm -enable-emscripten-sjlj -mllvm -disable-lsr --import-undefined --import-memory --strip-debug --export-if-defined=reader_destroy --export-if-defined=__start_em_asm --export-if-defined=__stop_em_asm --export-if-defined=__start_em_lib_deps --export-if-defined=__stop_em_lib_deps --export-if-defined=__start_em_js --export-if-defined=__stop_em_js --export-if-defined=__wasm_apply_data_relocs --export=__wasm_call_ctors --experimental-pic -shared --no-export-dynamic
 #0 0x00007f6271acf788 llvm::sys::PrintStackTrace(llvm::raw_ostream&, int) (/home/user/emsdk_tot/emsdk/upstream/bin/../lib/libLLVM-17git.so+0x1b73788)
 #1 0x00007f6271acd62e llvm::sys::RunSignalHandlers() (/home/user/emsdk_tot/emsdk/upstream/bin/../lib/libLLVM-17git.so+0x1b7162e)
 #2 0x00007f6271acff3d SignalHandler(int) Signals.cpp:0:0
 #3 0x00007f626fb36520 (/lib/x86_64-linux-gnu/libc.so.6+0x42520)
 #4 0x00007f626fb8aa7c __pthread_kill_implementation ./nptl/pthread_kill.c:44:76
 #5 0x00007f626fb8aa7c __pthread_kill_internal ./nptl/pthread_kill.c:78:10
 #6 0x00007f626fb8aa7c pthread_kill ./nptl/pthread_kill.c:89:10
 #7 0x00007f626fb36476 gsignal ./signal/../sysdeps/posix/raise.c:27:6
 #8 0x00007f626fb1c7f3 abort ./stdlib/abort.c:81:7
 #9 0x00007f626fb1c71b _nl_load_domain ./intl/loadmsgcat.c:1177:9
#10 0x00007f626fb2de96 (/lib/x86_64-linux-gnu/libc.so.6+0x39e96)
#11 0x0000561084c02306 (/home/user/emsdk_tot/emsdk/upstream/bin/wasm-ld+0x4ce306)
#12 0x0000561084c0b4a8 lld::wasm::(anonymous namespace)::Writer::run() Writer.cpp:0:0
#13 0x0000561084c03926 lld::wasm::writeResult() (/home/user/emsdk_tot/emsdk/upstream/bin/wasm-ld+0x4cf926)
#14 0x0000561084be0e24 lld::wasm::(anonymous namespace)::LinkerDriver::linkerMain(llvm::ArrayRef<char const*>) Driver.cpp:0:0
#15 0x0000561084bdde05 lld::wasm::link(llvm::ArrayRef<char const*>, llvm::raw_ostream&, llvm::raw_ostream&, bool, bool) (/home/user/emsdk_tot/emsdk/upstream/bin/wasm-ld+0x4a9e05)
#16 0x00005610848d2577 lldMain(int, char const**, llvm::raw_ostream&, llvm::raw_ostream&, bool) lld.cpp:0:0
#17 0x00005610848d1d9c lld_main(int, char**) (/home/user/emsdk_tot/emsdk/upstream/bin/wasm-ld+0x19dd9c)
#18 0x00007f626fb1dd90 __libc_start_call_main ./csu/../sysdeps/nptl/libc_start_call_main.h:58:16
#19 0x00007f626fb1de40 call_init ./csu/../csu/libc-start.c:128:20
#20 0x00007f626fb1de40 __libc_start_main ./csu/../csu/libc-start.c:379:5
#21 0x00005610848d18aa _start (/home/user/emsdk_tot/emsdk/upstream/bin/wasm-ld+0x19d8aa)

Using the object files directly, removing flto or using boost < 1.80 works as expected.

@sbc100
Copy link
Collaborator

sbc100 commented Feb 2, 2023

Does this issue still happen if you build without -sSIDE_MODULE=2 ?

BTW, normally when building a side module (or code that gets dynamically linked) you would compiler the sources with -fPIC. Does doing that help in this case?

@gl84
Copy link
Contributor Author

gl84 commented Feb 2, 2023

fPIC doesn't make a difference, flto is needed to reproduce the crash.

The crash also occurs without -sSIDE_MODULE=2 (if I add a dummy main to exported_api.cpp)

@sbc100
Copy link
Collaborator

sbc100 commented Oct 3, 2023

I just updated our boost port to 1.80 and then 1.83 and I was not able to reproduce the issue. (See #20384).

Here is the script I used:

emcc -flto -O0 -o exported_api.cpp.o -c exported_api.cpp -sUSE_BOOST_HEADERS
emcc -flto -O0 -o reader.cpp.o -c reader.cpp -sUSE_BOOST_HEADERS 
emar -rcs  lib_combined.a reader.cpp.o exported_api.cpp.o
emcc -O3 -o lib.wasm lib_combined.a  -sSIDE_MODULE=2 -sEXPORTED_FUNCTIONS=_reader_destroy -sUSE_BOOST_HEADERS

I don't get a crash on linking.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants