Skip to content

feat(slang): emit every contract in a source unit#460

Draft
hedgar2017 wants to merge 1 commit into
mainfrom
feat-slang-multi-contract
Draft

feat(slang): emit every contract in a source unit#460
hedgar2017 wants to merge 1 commit into
mainfrom
feat-slang-multi-contract

Conversation

@hedgar2017
Copy link
Copy Markdown
Contributor

The Slang frontend was processing only the first contract per source unit, silently dropping the rest of the file. Tests targeting a non-first contract failed with selector not found because the contract was never registered, and any future cross-contract lowering would have nothing to point at on the right-hand side of new B() or B(addr).method().

AstEmitter::emit now takes a single ContractDefinition and is invoked once per concrete contract in the source unit, with a fresh solx_mlir::Context per contract. Each contract gets its own deploy + runtime MLIR module pair through the existing finalize_module path and lands in output.contracts[file_id][contract_name] independently. Abstract contracts are skipped — their unimplemented members would crash the emitter, and derived concrete contracts continue to emit on their own.

Test delta on tests/solidity/simple -O M3B3 is zero (1903 passed, 4 failed, 305 invalid both with and without this change). Every multi-contract test in that suite also depends on contract creation, external calls, or inheritance — none of which are wired in the Slang pipeline yet. This change is a prerequisite for those: without it, the second contract's MLIR is never produced, so even after lowering new B() and b.method() the call sites would have nothing to bind to. solx-solidity semantic tests are unaffected — they exercise the solc-based frontend, not Slang.

Direct verification with a synthetic two-contract source confirms both contracts now appear in output.contracts[file_id] where previously only the first did.

@hedgar2017 hedgar2017 added the ci:slang Trigger slang unit tests on PR label May 28, 2026
The Slang frontend was processing only the first contract per source
unit, silently dropping the rest of the file. Tests targeting a
non-first contract failed with `selector not found` because the
contract was never registered, and any future cross-contract lowering
would have nothing to point at on the right-hand side of `new B()` or
`B(addr).method()`.

`AstEmitter::emit` now takes a single `ContractDefinition` and is
invoked once per concrete contract, with a fresh `solx_mlir::Context`
per contract. Each contract gets its own deploy + runtime MLIR module
pair through the existing `finalize_module` path and lands in
`output.contracts[file_id][contract_name]` independently. Abstract
contracts are skipped — their unimplemented members would crash the
emitter, and derived concrete contracts continue to emit on their own.
@hedgar2017 hedgar2017 force-pushed the feat-slang-multi-contract branch from 5a6eff0 to 7fe873f Compare May 28, 2026 15:45
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

ci:slang Trigger slang unit tests on PR

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant