Uh oh!
There was an error while loading. Please reload this page.
Validate invalid base type declarations in ILVerify - #129118
Conversation
Tagging subscribers to this area: @JulieLeeMSFT, @dotnet/jit-contrib |
pkuyo
commented
Jun 8, 2026
@dotnet-policy-service agree |
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
pkuyo
commented
Jun 17, 2026
Hi @jkotas, just checking in on this PR. I’ve addressed the feedback and made the requested updates. Please let me know if there’s anything else I should adjust. Thanks! |
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
pkuyo
commented
Jun 30, 2026
Thanks for the review. I updated the PR to address the latest feedback, The TypeSpec validation now follows the ECMA-335 augment behavior. Please let me know if there is anything else I should adjust. |
(Edited to fix issue number) I wonder if we should approach this from an angle that also allows to address #4945
|
pkuyo
commented
Jul 16, 2026
Thanks. I've initialized ErrorArguments for the BadTypeSpec verification results, |
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
Workflow state for the Holistic Review Orchestrator. {
"version": 5,
"last_dispatched_commit": "bcf96c9eb4e8c79be8c0ee96c8244238f1df7e84",
"last_dispatched_base_ref": "main",
"last_dispatched_base_sha": "916a8b78c41c5fd0b50a8e51f6b5563a5187d961",
"last_reviewed_commit": "bcf96c9eb4e8c79be8c0ee96c8244238f1df7e84",
"last_reviewed_base_ref": "main",
"last_reviewed_base_sha": "916a8b78c41c5fd0b50a8e51f6b5563a5187d961",
"last_recorded_worker_run_id": "29690871985",
"review_attempt_commit": "",
"review_attempt_base_ref": "",
"review_attempt_count": 0,
"max_review_attempts": 5,
"review_history_format": "holistic-review-disclosure-v1",
"review_history": [
{
"commit": "69a8cf8e74552c7bcf86fbe2f916240ad62c4386",
"review_id": 4730816951
},
{
"commit": "bcf96c9eb4e8c79be8c0ee96c8244238f1df7e84",
"review_id": 4730944291
}
]
} |
There was a problem hiding this comment.
Holistic Review
Motivation: The problem is real and well-scoped. Issue #119536 shows ILAsm emitting a class whose base type is encoded as an invalid TypeSpec (extends object) that CoreCLR then cannot load, while ILVerify silently accepted it. Per ECMA-335 the TypeSpecBlob grammar only permits (CLASS | VALUETYPE) TypeDefOrRef, so rejecting these encodings is spec-correct.
Approach: The direction agreed with the maintainer's guidance: reject malformed TypeSpecs centrally in the signature parser (EcmaSignatureParser.ParseTypeSpec), gated behind the ILVERIFICATION define via a partial hook so AOT/regular CoreCLR resolution is unaffected, plus a dedicated VerifyBaseType check for the base-type class/valuetype/interface rules. The wiring through VerifierException.Code into VerificationResult is reasonable and the spec augment doc was updated to match.
Summary: VerifyBaseType appears to misclassify enums: a type extends System.Enum resolves to a base whose IsValueType is true, so it would be reported as InvalidBaseType. Enums are legal and this path has no test coverage that would catch the regression. See the inline comment and findings below.
Detailed Findings
❌ Correctness — Enums with extends System.Enum will be falsely rejected
See the inline comment on TypeVerifier.cs. System.Enum derives from System.ValueType, so EcmaType.ComputeTypeFlags marks it TypeFlags.ValueType. In VerifyBaseType, a valid enum's resolvedBaseType is System.Enum (IsValueType == true), which triggers VerifierError.InvalidBaseType. The existing enum types in the test IL don't use the _ValidType_/_InvalidType_ naming convention, so TypeVerifier is never exercised against them and CI wouldn't flag this. A System.Enum base should be explicitly allowed, with a *_ValidType_Valid enum case added to BaseTypeTests.il.
⚠️ Robustness — Format(EntityHandle) silently swallows resolution failures
The new Format(EntityHandle) overload catches BadImageFormatException and TypeSystemException and falls back to a token/kind string. That is acceptable for building an error message about already-invalid metadata, but the empty catch blocks are worth a brief comment noting the intent (formatting must never throw while reporting another error), since a bare swallow reads like an accidental omission.
💡 Style — Trailing whitespace
Line 57 (return; ) and the blank line after TypeDesc resolvedBaseType = ... carry trailing whitespace. Minor; .editorconfig/format pass will catch it, but worth cleaning up.
✅ Spec + gating
The ECMA-335-Augments update correctly reverses the prior "TypeSpec modifiers permitted in practice" note to "invalid," matching the code. Gating the malformed-TypeSpec rejection behind ILVERIFICATION (partial ReportInvalidTypeSpec) correctly keeps the stricter behavior out of the shared AOT type-system path, addressing the maintainer's concern.
✅ Tests
BaseTypeTests.il and MalformedTypeSpecTests.il cover the original repro plus array/pointer/valuetype/generic-valuetype bases and modopt/return-signature TypeSpecs, and the pre-existing tests that relied on invalid TypeSpecs were corrected. The main gap is the missing enum (and arguably a plain valid class base already covered) positive case noted above.
Note
This review was generated by this repository's Holistic Review agentic workflow to complement the built-in Copilot review.
Generated by Holistic Review · 176.3 AIC · ⌖ 11.2 AIC · ⊞ 10K
Uh oh!
There was an error while loading. Please reload this page.
There was a problem hiding this comment.
Holistic Review
Motivation: Unchanged from the prior review. Issue #119536 shows ILAsm emitting a class whose base type is an invalid TypeSpec (extends object) that CoreCLR cannot load while ILVerify silently accepted it. Per ECMA-335 the TypeSpecBlob grammar only permits (CLASS | VALUETYPE) TypeDefOrRef, so rejecting these encodings is spec-correct.
Approach: Unchanged. Malformed TypeSpecs are rejected centrally in EcmaSignatureParser.ParseTypeSpec, gated behind ILVERIFICATION via a partial hook so AOT/regular CoreCLR resolution is unaffected, plus a dedicated VerifyBaseType check for base-type class/valuetype/interface rules, wired through VerifierException.Code into VerificationResult. The single new commit since the prior review (bcf96c9) adds an enum positive test, strips two trailing-whitespace artifacts, and documents the intent of the Format(EntityHandle) catch blocks.
Summary: return; / blank line, and the missing comment on Format(EntityHandle)'s empty catches). However, the primary enum finding is only half addressed: it adds the positive EnumBase_ValidType_Valid test but does not change VerifyBaseType, so that new test appears to assert a case the code still rejects. See the inline comment.
Assessment History
- review 4730816951 reviewed commit
69a8cf8with verdict⚠️ Needs Changes. Current verdict is also⚠️ Needs Changes — assessment unchanged in verdict/motivation/approach/risk. The new commit clears the two style/robustness findings but leaves the core enum correctness issue open, so the overall verdict does not change.
Detailed Findings
❌ Correctness — enum positive test added without the corresponding VerifyBaseType fix
See the inline comment on BaseTypeTests.il. System.Enum derives from the well-known System.ValueType, so EcmaType.ComputeTypeFlags tags it TypeFlags.ValueType and System.Enum.IsValueType == true. For a type extends System.Enum, resolvedBaseType.IsValueType in VerifyBaseType is true and VerifierError.InvalidBaseType is emitted, but TestValidTypes asserts Assert.Empty(results). The fix belongs in VerifyBaseType (special-case a System.Enum base), not solely in the test. Please confirm against an actual ILVerification test run before merging, since this worker cannot build or execute tests.
Scope correction to the inline comment
My inline note's parenthetical also mentioned extends [System.Runtime]System.ValueType and delegate bases. Those are handled correctly: System.ValueType's own base is System.Object, so it resolves to the Class category (IsValueType == false) and passes, as do System.Delegate/System.MulticastDelegate. The concrete failing case introduced by this commit is the enum one only.
✅ Resolved since prior review
- Trailing whitespace on
return;and the blank line inVerifyBaseTypeis removed. Format(EntityHandle)now carries a comment explaining the fall-back-on-resolution-failure intent, addressing the empty-catch readability note.
Note
This review was generated by this repository's Holistic Review agentic workflow to complement the built-in Copilot review.
Generated by Holistic Review · 188.7 AIC · ⌖ 10.9 AIC · ⊞ 10K
Uh oh!
There was an error while loading. Please reload this page.
pkuyo
commented
Aug 6, 2026
Hi @jkotas, I’ve addressed the remaining feedback and replied to the outstanding review threads. Could you take another look when you have a chance? |
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
Fixes#119536
This adds ILVerify validation for invalid class base type declarations.
The original issue reports a case where ILAsm accepts a type declared with
extends object, but the resulting type cannot be loaded by the runtime.ILVerify previously accepted that assembly without reporting an error.
This change reports
InvalidBaseTypefor invalid base type declarations ratherthan special-casing only the exact
extends objectspelling.Tests added in
BaseTypeTests.il:ObjectTypeSpecBase_InvalidType_InvalidBaseTypeextends object.InvalidBaseType.NilBaseInterface_ValidType_ValidGenericClassTypeSpecBase_ValidType_ValidValueTypeBase_InvalidType_InvalidBaseTypeGenericValueTypeSpecBase_InvalidType_InvalidBaseType