JIT: propagate vector constants through assertion prop#127124
JIT: propagate vector constants through assertion prop#127124
Conversation
There was a problem hiding this comment.
Pull request overview
This PR extends CoreCLR JIT assertion propagation to recognize and propagate SIMD (vector) constants across equality/inequality guards, enabling more constant folding in common “guard then use” patterns for Vector64/128/256/512 integral vectors.
Changes:
- Added a new assertion operand kind
O2K_CONST_VECbacked by an arena-allocatedsimd_t, including equality/printing/factory support. - Taught
optAssertionGenJtrue/ assertion creation to recognizeVector*_op_Equality/op_Inequalitypatterns againstGT_CNS_VECand produce usable assertions (excluding FP base types). - Implemented SIMD constant materialization during propagation (including VN-based propagation into SIMD-typed loads such as byref ABI patterns).
Reviewed changes
Copilot reviewed 2 out of 2 changed files in this pull request and generated 3 comments.
| File | Description |
|---|---|
| src/coreclr/jit/compiler.h | Adds O2K_CONST_VEC plumbing to assertion descriptors, including storage, equality, and factory helpers; extends propagation eligibility for VN-based SIMD constants. |
| src/coreclr/jit/assertionprop.cpp | Recognizes SIMD compare patterns when generating assertions and propagates vector constants (including VN-based propagation for SIMD loads). |
This comment has been minimized.
This comment has been minimized.
🤖 Copilot Code Review — PR #127124Note This review was generated by Copilot and reflects analysis from multiple AI models (Claude Opus 4.6, Claude Sonnet 4.5, GPT-5.3-Codex). Holistic AssessmentMotivation: Well-motivated. Propagating vector constants through assertion prop enables further downstream optimizations (e.g., constant folding in HW intrinsic consumers). The pattern Approach: Follows existing assertion prop patterns for int/double constants, extending them cleanly to vector constants. Correctly handles IEEE floating-point semantics by restricting JTRUE-based assertions to integral SIMD base types. Summary: Detailed Findings
|
Agent-Logs-Url: https://github.com/dotnet/runtime/sessions/e8f6f2ee-359c-4b32-b822-877ec029ddc6 Co-authored-by: EgorBo <523221+EgorBo@users.noreply.github.com>
| if (op1->IsCnsIntOrI() && !op2->IsCnsIntOrI()) | ||
| { | ||
| std::swap(op1, op2); | ||
| } |
There was a problem hiding this comment.
Is this likely to be needed?
We tend to push constants to the right fairly early and consistently across phases (import, VN, morph, etc), but then we still have a lot of checks in other phases, like this one, which presume they might still not have been fixed yet.
-- Not a big deal, mostly just a thought on how much potential throughput we might be wasting across the whole JIT with these repeated checks/handling.
|
|
||
| // SIMD floating-point equality is not bitwise equality (+0 == -0, NaN != NaN), | ||
| // Only enable for integral SIMD base types. | ||
| if (varTypeIsIntegral(hwi->GetSimdBaseType()) && (hwi->GetOperandCount() == 2)) |
There was a problem hiding this comment.
The operand count check seems a bit superfluous and could probably be an assert. We should never encounter an equality node without 2 operands.
| { | ||
| op1 = hwi->Op(1); | ||
| op2 = hwi->Op(2); | ||
| if (op1->OperIs(GT_CNS_VEC)) |
There was a problem hiding this comment.
And same for the others
| if (op1->OperIs(GT_CNS_VEC)) | |
| if (op1->IsCnsVec()) |
| return NO_ASSERTION_INDEX; | ||
| } | ||
|
|
||
| if (!op1->TypeIs(TYP_SIMD8, TYP_SIMD12, TYP_SIMD16) || (op1->TypeGet() != op2->TypeGet())) |
There was a problem hiding this comment.
This also seems a bit superfluous and could be an assert. We should never be encountering IR where we a HWIntrinsic equality node where the operands aren't SIMD or are of different types.
It's the type of thing where something else has gone horribly wrong by that point.
Add a new kind of an assertion -
O2K_CONST_VEC.Diffs