4073 Commits

Author SHA1 Message Date
Andrea Gussoni 57f7e577fe DetectABI: name outlined stubs after symbols 2026-06-19 15:35:18 +02:00
Andrea Gussoni f6d2a71466 DetectABI: add post-inline IR dump flag
Add `--detect-abi-after-inline-ir-dir=<dir>` which writes one
`<fn>.ll` file per outlined stub immediately after the helper inlinining
has taken place.
2026-06-19 15:35:18 +02:00
Andrea Gussoni 6a56557177 DetectABI: inline helpers
Inline `revng_inline` helper calls into each outlined stub which is
consumed by `analyzeABI`, so the analysis can observe the reads and
writes the helper performs on the floating point registers.

The helper module is linked only once at the beginning of the pass, to
avoid double linking issues.
2026-06-19 15:35:18 +02:00
Andrea Gussoni 06733a9f3a InlineHelpers: split into link / inline / delete
Split the `InlineHelpers` pass into the three phases:

- `link-helpers-to-inline` links the missing `revng_inline` helper
  bodies from the `libtcg-helpers-to-inline-arch` module.
- `inline-helpers` inlines, in every function except those tagged
  `Root` or `Helper`, the calls to `revng_inline` helpers whose
  critical arguments on the call site are constant.
- `delete-helper-bodies` drops from the module the body of every
  `revng_inline` function, leaving only the declaration.

The three passes live in a dedicated `revngInlineHelpers` library
(`lib/InlineHelpers/` + `include/revng/InlineHelpers/`), so that
libraries which do not depend on `revngFunctionIsolation` can use them
without creating cyclic dependencies.
2026-06-19 15:35:18 +02:00
Pietro Fezzardi a7aa3a0e1a ExitSSA: fix detection of incompatible PHINodes
The previous logic for detection of incompatible PHINodes was broken in
various different ways.
1. `return true` and `return false` were flipped, so it effectively did
   the opposite of what it was expected to do
2. `std::numeri_limits<Value *>::max()` yielded 0, breaking the lookup.

This commit fixes the condition for incompatible PHINodes and adds a lot
of logging.
2026-06-19 11:07:44 +02:00
Pietro Fezzardi a7d4a73d2d ExitSSA: don't exclude PHINodes with non-phi Users
Before this commit, the code never put in the same group two PHINodes if
one of them had a non-phi User. This condition was wrong and was
unnecessarily preventing valig PHINodes to be put in the same group.
This caused the generation of a lot more local variables than necessary.
2026-06-19 11:07:44 +02:00
Pietro Fezzardi 422319f4d8 ExitSSA: fix insertion of undefs
Before this commit we were replacing all uses of a PHI that were not
used by other PHIs with llvm::UndefValue. That was wrong. The
replacement is valid only if the use is used by a PHINode that is in the
same group. This commit fixes the condition for such a replacement to
take place.
2026-06-19 11:07:44 +02:00
Alessandro Di Federico 12b9a44ace Ban dynamic-size allocas, use ArrayType instead 2026-06-19 09:18:16 +02:00
Alessandro Di Federico 903617e79e IRHelpers: turn some functions into IRBuilder::* 2026-06-19 09:18:16 +02:00
Alessandro Di Federico 63734b7ca0 Canonicalize: ban pointers
In order to ensure there are no `alloca`s containing pointers, we change
the passes that emit them to emit instead integer scalars of the same
type.
2026-06-19 09:18:16 +02:00
Alessandro Di Federico 3e31edf817 Introduce FixPointerSize
This commit introduces `FixPointerSize`, a pipe changing the
`DataLayout` of module in order to have a pointer size identical to the
one of `targetABI()`.

The pipe also performs safety checks to ensure this does not corrupt
semantics.
2026-06-19 09:18:16 +02:00
Alessandro Di Federico 64fa538051 Introduce DropRedundantPtrIntCasts 2026-06-19 09:18:15 +02:00
Alessandro Di Federico ffaf735219 sqlite: open read-only when appropriate 2026-06-19 09:18:15 +02:00
Alessandro Di Federico b5e3ccba9e Do not allocate const objects 2026-06-18 16:44:15 +02:00
Alessandro Di Federico a35da01bdd Minor changes 2026-06-18 16:44:15 +02:00
Ivan Krysak 1609bbe745 Restore the separate enum declaration node 2026-06-16 18:43:45 +02:00
Ivan Krysak 42a045a2b5 CliftEmitC: fix the header filtering direction 2026-06-15 17:32:35 +02:00
Ivan Krysak e5113a8c1d ImportFromC: add a logger printing clang inputs 2026-06-15 17:32:33 +02:00
Ivan Krysak 42e9973ab1 ImportFromC: drop a pointless logger
It was only outputting errors that were already printed anyway.
2026-06-15 17:32:30 +02:00
Pietro Fezzardi 6a3ab92a9d Mark to-be-dropped pipeline names as legacy
Several components in both pipeline YAMLs are slated for removal.
Prepend a legacy prefix to their names, and to the matching c++ code, so
they are clearly distinguished from the new Clift-based pipeline until
they are dropped.
2026-06-15 17:28:22 +02:00
Ivan Krysak 81aceca45d CliftContainer: use llvm::StringRef overload
Because of how `StringAttr` comparison works, two attributes with
the same name can be added to one module. Forcing `StringAttr`
recreation from a raw string prevents that.
2026-06-15 17:28:22 +02:00
Alessandro Di Federico ffd8710492 isolate: keep CSVs used by helpers
We used not to put CSVs in `declarations-only`, since `lift` is able to
create them. However, this led to have less CSVs than those we get
post-inlining (some are only used in helpers). This represents a problem
since sometimes we ignore non-existing registers.
2026-06-15 17:28:22 +02:00
Alessandro Di Federico 1660b44cfe promote-csvs: improve logging 2026-06-15 17:28:22 +02:00
Pietro Fezzardi 4b125fc6c8 CliftEmitC: emit trailing struct padding
The type emitter printed inter-field padding but never the padding
between the end of the last field and the declared size of the
struct.
Since every struct is emitted packed annotation, any struct with
trailing padding had a wrong sizeof in C.

This commit fixes the problem by always printing trailing padding in
structs, unless user have explicitly opted out setting `ExplicitPadding`
to off.
2026-06-15 17:28:22 +02:00
Lauri Vasama 15c5da73f2 Fix VoidType serialization 2026-06-15 17:28:22 +02:00
Pietro Fezzardi ec5af3d5cb CliftImportModel: import symbol descriptive info
When importing descriptive info for a single function, the body walk
now intercepts clift::UseOp operations and follows the symbol
reference to find the target FunctionOp or GlobalVariableOp.

Before this commit, the per-function overload of importDescriptiveInfo
recorded the rename only for the current function (plus helpers and
globals at module level, but not via UseOp).

The deduplication logic makes it cheap and safe for a single FunctionOp
or GlobalVariableOp to be used in many UseOps without importing
descriptive info twice. The same holds if the FunctionOp is also visited
at module level and not just via UseOp, as is the case for
self-recursive functions.
2026-06-15 17:28:22 +02:00
Pietro Fezzardi 8fc5ff2c94 CliftImportModel: deduplicate recorded targets
This commit adds a set of module-level ops whose descriptive info has
already been recorded to SymbolRenamer, and short-circuit
recordFunctionOpName / recordGlobalVariableOpName when the same op
shows up again.

The set lives on SymbolRenamer (and not on the Importer) because a
single importDescriptiveInfo invocation may construct several Importer
instances: the per-function overload visits the current function with
one Importer, then each helper/global at module level with a fresh one,
and any callee reached through a clift::UseOp would similarly create
another. The deduplication logic must be shared across all of them so
that the same target is not recorded twice.

Behavior is unchanged for the current call sites (each module-level op
is visited at most once today); the deduplication logic prepares for
when the body walk will also reache sibling declarations through
clift::UseOp, which is necessary for importing descriptive info
properly.
2026-06-15 17:28:22 +02:00
Pietro Fezzardi 7aad574196 CliftImportModel: refactor visitGlobalVariableOp
Split visitFunctionOp into two parts:
1. a new recordGlobalVariableOpName helper, which records the name for
any GlobalVariableOp;
2 the existing visitGlobalVariableOp, that now delegates to the helper.

The helper exists so that, like recordFunctionOpName, it can be invoked
from contexts other than the top-level module walk, in particular, when
a clift::UseOp in a function body refers to a GlobalVariableOp.

Pure refactor: behavior is unchanged.
2026-06-15 17:28:22 +02:00
Pietro Fezzardi 98b0dd9380 CliftImportModel: refactor visitFunctionOp
Split visitFunctionOp into two parts:
1. a new recordFunctionOpName helper, which records the name for any
FunctionOp without touching the Importer's CurrentFunction state;
2. the existing visitFunctionOp, which keeps the CurrentFunction
lifecycle and now delegates the recording to the new helper.

This makes the recording reusable from contexts where mutating
CurrentFunction is not appropriate e.g. when reaching a callee
declaration from a body walk via a clift::UseOp, which will need in a
later commit.

Pure refactor: behavior is unchanged.
2026-06-15 17:28:22 +02:00
Lauri Vasama aa48a01400 Fix overwriting of names in Clift type import 2026-06-15 17:28:22 +02:00
Ivan Krysak 2a2854c020 CliftEmitC: always emit opaque types in headers 2026-06-15 17:28:22 +02:00
Ivan Krysak 6d86e8ca71 CliftAttributes: improve mutation error message 2026-06-15 17:28:22 +02:00
Ivan Krysak ce9918a0c6 Clifter: do not load dialect in the pipe
Container already takes care of that.
2026-06-15 17:28:22 +02:00
Ivan Krysak f8e13b8c96 TypeDependencyGraph: skip opaque types 2026-06-15 17:28:22 +02:00
Ivan Krysak a83521d337 Ensure no duplicate opaque types in headers 2026-06-15 17:28:22 +02:00
Ivan Krysak 5cd3556765 emit-single-type-definition: add a TODO 2026-06-15 17:28:22 +02:00
Ivan Krysak 3a6ed1e7eb CliftContainer: accept owning module references 2026-06-15 17:28:22 +02:00
Ivan Krysak a8056e8cee UnconfiguredNB: ensure binary lives long enough 2026-06-15 17:28:22 +02:00
Ivan Krysak 77affee259 importType: provide a error-less overload 2026-06-15 17:28:22 +02:00
Ivan Krysak 686dc0877a hasModuleAttr -> isCliftModule 2026-06-15 17:28:22 +02:00
Ivan Krysak ffc367f584 Pipebox: reorder containers and pipes 2026-06-15 17:28:22 +02:00
Ivan Krysak b0bc3eb2d8 Pipebox: streamline registration
Having manual indexing leads to having to touch all the following
entries when one is removed. It also makes adding new ones to
the middle of the list really awkward.

Instead of manual indexing, use a simple macro to come up with
the instance name on the fly.
2026-06-15 17:28:22 +02:00
Ivan Krysak 93e9b41769 EnforceABI: drop an unused class declaration 2026-06-15 17:28:22 +02:00
Ivan Krysak 53b868e48f PTML: drop unused interfaces 2026-06-15 17:28:22 +02:00
Ivan Krysak 81190634df ABI: drop unused interfaces 2026-06-15 17:28:22 +02:00
Ivan Krysak 0c9d83dd4d CliftImportModel: import artificial field comments 2026-06-15 17:28:22 +02:00
Ivan Krysak c03d582ba4 ArtificialStruct name: use name builder helper 2026-06-15 17:28:22 +02:00
Ivan Krysak 771d01f107 CliftEmitC: mark typedefs as commentable 2026-06-15 17:28:22 +02:00
Ivan Krysak c01a553d23 CliftEmitC: mark segments as commentable 2026-06-15 17:28:22 +02:00
Ivan Krysak ff53337edb CEmitter: fix sub-comment commands
Before this fix, triggering "comment" action *between* other parts,
for example, between arguments, would trigger it on the function
itself.

That behavior was confusing, so comment action is not allowed there
anymore.
2026-06-15 17:28:22 +02:00