mirror of
https://github.com/tinygo-org/tinygo.git
synced 2026-07-26 06:38:42 +00:00
builder, runtime: fix duplicate symbol error with Go 1.26+ on Windows
Go 1.26 changed syscall.loadlibrary, syscall.loadsystemlibrary, and syscall.getprocaddress from declarations to definitions in syscall/dll_windows.go. TinyGo's runtime also defines these via //go:linkname, causing "symbol multiply defined!" during LLVM module linking. Resolve this by detecting duplicate function definitions before calling llvm.LinkModules and turning the incoming duplicate into a declaration, so the runtime's version wins. TinyGo's implementations must take precedence because Go 1.26's versions depend on //go:cgo_import_dynamic, which TinyGo does not support. Also fix the signature of syscall_loadsystemlibrary to match the standard library (remove unused absoluteFilepath parameter). Signed-off-by: deadprogram <ron@hybridgroup.com>
This commit is contained in:
@@ -546,6 +546,24 @@ func Build(pkgName, outpath, tmpdir string, config *compileopts.Config) (BuildRe
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to load bitcode file: %w", err)
|
||||
}
|
||||
// Resolve duplicate function definitions before linking.
|
||||
// This can happen when a newer Go version adds a function
|
||||
// body in a standard library package that was previously
|
||||
// just a declaration provided by //go:linkname from the
|
||||
// runtime. In that case, keep the existing (runtime)
|
||||
// definition and turn the new one into a declaration.
|
||||
for fn := pkgMod.FirstFunction(); !fn.IsNil(); fn = llvm.NextFunction(fn) {
|
||||
if fn.IsDeclaration() {
|
||||
continue
|
||||
}
|
||||
existing := mod.NamedFunction(fn.Name())
|
||||
if existing.IsNil() || existing.IsDeclaration() {
|
||||
continue
|
||||
}
|
||||
for _, bb := range fn.BasicBlocks() {
|
||||
bb.EraseFromParent()
|
||||
}
|
||||
}
|
||||
err = llvm.LinkModules(mod, pkgMod)
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to link module: %w", err)
|
||||
|
||||
Reference in New Issue
Block a user