-
Notifications
You must be signed in to change notification settings - Fork 1.9k
Rust: Fix context-based type inference explosion #21217
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
base: main
Are you sure you want to change the base?
Conversation
71ee1c9 to
38929dd
Compare
38929dd to
50ce393
Compare
| hasTypeConstraint(tt, constraint) and | ||
| t = getTypeAt(tt, path) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This conjunction has non-linear recursion, hence the magic'ed version of hasTypeConstraint.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Pull request overview
This PR fixes a type inference explosion issue in Rust queries by correcting two bugs in the type inference implementation:
- Path resolution bug: Changed
getASuccessor(_)togetAnAssocItem()to correctly resolve trait functions only from the trait itself, not from sub-traits - Context-based return type checking: Enhanced the logic to only use return type for disambiguation when all argument positions are trivially satisfied
Changes:
- Fixed trait function resolution to prevent matching sub-trait implementations
- Added logic to check return type matches calling context for polymorphic functions
- Refactored Input modules into a unified structure
- Added regression test for the
Default::default()andFrom::from()pattern
Reviewed changes
Copilot reviewed 6 out of 6 changed files in this pull request and generated no comments.
Show a summary per file
| File | Description |
|---|---|
| shared/typeinference/codeql/typeinference/internal/TypeInference.qll | Added helper predicate with pragma[nomagic] to optimize type constraint checking |
| rust/ql/lib/codeql/rust/internal/typeinference/TypeInference.qll | Fixed getASuccessor → getAnAssocItem bug, merged Input modules, fixed parameter ordering in context typing |
| rust/ql/lib/codeql/rust/internal/typeinference/FunctionOverloading.qll | Split predicate and added return type disambiguation logic |
| rust/ql/test/library-tests/type-inference/main.rs | Added regression test for from_default module |
| rust/ql/test/library-tests/type-inference/type-inference.expected | Updated expected test output |
| rust/ql/test/query-tests/security/CWE-312/CONSISTENCY/PathResolutionConsistency.expected | Removed spurious multiple resolution error |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
The following simple program would make our type inference implementation explode:
Firstly, because of a
getSuccessorvsgetAssocItembug,From::fromwould allow for any sub trait ofFrom, for example theInttrait, which meant thatxcould be inferred to have typebool. Secondly, since manyfromimplementations are polymorphic in their argument, we should really be checking that the return type matches the type of the calling context.This PR makes those two adjustments, and adds the regression test.
DCA looks good; we loose some call edges, but nothing too serious.