Skip to content

build: preserve main package identity for test builds - #2370

Open
visualfc wants to merge 1 commit into
xgo-dev:mainfrom
visualfc:fortest
Open

build: preserve main package identity for test builds#2370
visualfc wants to merge 1 commit into
xgo-dev:mainfrom
visualfc:fortest

Conversation

@visualfc

@visualfc visualfc commented Aug 20, 2026

Copy link
Copy Markdown
Collaborator

Summary

  • Preserve the main package identity during test builds instead of renaming it to main.test.
  • Add an internal @fortest marker to distinguish test-main packages when resolving ABI paths.
  • Keep c-shared test exports pointed at main.init and main.main.
  • Add linkname coverage for same-package, external-test, and main-package references.
  • Update the stdlib build-mode test runner for test binaries that retain the main package identity.
  • Keep generated test library names package-specific, such as libtar.test.
  • Link runners against main.init and main.main rather than package-path-derived test symbols.

Testing

  • go test ./test/linkname
  • LLGO=./dev/llgo.sh dev/test_std_buildmodes.sh ./test/std/archive/tar

@github-actions

github-actions Bot commented Aug 20, 2026

Copy link
Copy Markdown

LLGo baseline benchmarks

6348e54e0e57 | workflow run | long-term charts

Program measurements

Platform Workload File size vs base Build vs base Run vs base
Linux cprintf 19288 B 0 B / +0.0% 338.411 ms -8.723 ms / -2.5% (better) 1.420 ms +53.45 us / +3.9% (worse)
Linux fmtprintf 1860168 B 0 B / +0.0% 2.716 s -148.9 ms / -5.2% (better) 3.561 ms -84.89 us / -2.3% (better)
Linux println 68776 B 0 B / +0.0% 338.392 ms -17.98 ms / -5.0% (better) 1.728 ms +41 us / +2.4% (worse)
macOS cprintf 84672 B 0 B / +0.0% 445.286 ms +92.45 ms / +26.2% (worse) 3.151 ms +908.5 us / +40.5% (worse)
macOS fmtprintf 1892720 B 0 B / +0.0% 2.975 s +349.5 ms / +13.3% (worse) 15.315 ms +4.028 ms / +35.7% (worse)
macOS println 121360 B 0 B / +0.0% 355.779 ms +5.88 ms / +1.7% (worse) 3.464 ms +189.5 us / +5.8% (worse)
Core language and compiler benchmarks
Platform Benchmark ns/op vs base
Linux BenchmarkLookupPCRandom 12.250 ns/op -0.01 ns/op / -0.1% (better)
Linux BenchmarkMergeCompilerFlags 144 ns/op -3.5 ns/op / -2.4% (better)
Linux BenchmarkMergeLinkerFlags 93.790 ns/op -1.51 ns/op / -1.6% (better)
Linux BenchmarkChannelBuffered 36.330 ns/op -0.09 ns/op / -0.2% (better)
Linux BenchmarkChannelHandoff 24506 ns/op +369 ns/op / +1.5% (worse)
Linux BenchmarkDefer 45.960 ns/op -0.44 ns/op / -0.9% (better)
Linux BenchmarkDirectCall 1.758 ns/op +0.001 ns/op / +0.1% (worse)
Linux BenchmarkGlobalRead 1.758 ns/op 0 ns/op / +0.0%
Linux BenchmarkGlobalWrite 2.805 ns/op 0 ns/op / +0.0%
Linux BenchmarkGoroutine 30571 ns/op +285 ns/op / +0.9% (worse)
Linux BenchmarkInterfaceCall 8.450 ns/op +0.004 ns/op / +0.04736% (worse)
Linux BenchmarkRuntimeGetG 2.112 ns/op -0.001 ns/op / -0.04733% (better)
macOS BenchmarkLookupPCRandom 11.840 ns/op -0.2 ns/op / -1.7% (better)
macOS BenchmarkMergeCompilerFlags 167.600 ns/op +43.8 ns/op / +35.4% (worse)
macOS BenchmarkMergeLinkerFlags 82.870 ns/op +14.57 ns/op / +21.3% (worse)
macOS BenchmarkChannelBuffered 21.360 ns/op +0.86 ns/op / +4.2% (worse)
macOS BenchmarkChannelHandoff 6574 ns/op +849 ns/op / +14.8% (worse)
macOS BenchmarkDefer 28.780 ns/op +2.04 ns/op / +7.6% (worse)
macOS BenchmarkDirectCall 0.981 ns/op +0.0387 ns/op / +4.1% (worse)
macOS BenchmarkGlobalRead 0.994 ns/op +0.0177 ns/op / +1.8% (worse)
macOS BenchmarkGlobalWrite 0.986 ns/op +0.0441 ns/op / +4.7% (worse)
macOS BenchmarkGoroutine 48831 ns/op +25189 ns/op / +106.5% (worse)
macOS BenchmarkInterfaceCall 4.511 ns/op +0.419 ns/op / +10.2% (worse)
macOS BenchmarkRuntimeGetG 1.961 ns/op -0.251 ns/op / -11.3% (better)

Compared with 0314faeba69d measured in the same runner job.

@fennoai fennoai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Review Summary

This PR reworks how //go:linkname resolves into test-compiled main packages. It replaces the previous approach (renaming the package to "main.test", which mutated the real package name) with a scope sentinel: an @ForTest marker constant is inserted into the package scope when a main package is built for test, and ssa/abi/abi.go PathOf() consults that marker to return the real import path instead of collapsing to "main".

The approach is sound and a genuine improvement over mutating Types.Name():

  • The @ prefix is deliberately un-spellable as a Go identifier, so the sentinel cannot collide with, or be spoofed by, user code. No security issue.
  • The added Scope().Lookup in PathOf is O(1) and guarded by Name() == "main" short-circuit, so it only runs for main packages. No performance concern.
  • Removing the obsolete main.test rename (and its test) is correct hygiene; the surviving .test suffix checks operate on pkg.ID/pkg.PkgPath, not the removed rename, so they are unaffected.

Findings below are maintainability/robustness improvements, not blockers. The new test/linkname/ regression tests are a good addition.

Comment thread internal/build/build.go Outdated
Comment thread ssa/abi/abi.go Outdated
Comment thread internal/build/build.go Outdated
@codecov

codecov Bot commented Aug 20, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 81.81818% with 2 lines in your changes missing coverage. Please review.

Files with missing lines Patch % Lines
internal/build/build.go 85.71% 0 Missing and 1 partial ⚠️
test/linkname/main.go 66.66% 1 Missing ⚠️

📢 Thoughts on this report? Let us know!

@visualfc
visualfc force-pushed the fortest branch 2 times, most recently from 6cddd43 to df97f44 Compare August 20, 2026 04:02
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

Successfully merging this pull request may close these issues.

1 participant