Skip to content

[wgsl-in] Report assignment and binary operator type mismatches in WGSL terms - #9970

Closed
emilk wants to merge 3 commits into
gfx-rs:trunkfrom
emilk:emilk/wgsl-assignment-type-mismatch-error
Closed

[wgsl-in] Report assignment and binary operator type mismatches in WGSL terms#9970
emilk wants to merge 3 commits into
gfx-rs:trunkfrom
emilk:emilk/wgsl-assignment-type-mismatch-error

Conversation

@emilk

@emilk emilk commented Jul 30, 2026

Copy link
Copy Markdown
Contributor

Connections

Depends on #9973. Fixes the rest of #7419.

Description

#9973 fixes the try_automatic_conversions choke point. Two spots don't go through it, and still reported type errors as IR handle indices:

  • Assignments — compare the value's type against the pointer's pointee type in StatementKind::Assign: The type of [13] doesn't match the type stored in [10]cannot assign a value of type `u32` to a memory location of type `array<u32, 16>` .
  • Binary operatorsproc::binary_op_accepts_operands, extracted from the validator so both share one set of typing rules: Operation Add can't work with [1] (of type Matrix { .. }) and [4] (of type Vector { .. })the `+` operator cannot be applied to `mat2x2<f32>` and `vec2<f32>` . Also covers &&/||, whose operands never form a Binary expression for the validator to inspect, and compound assignments like m += v.

Behavioral: return with a missing or unexpected value is now a parse error, and 1.0 < some_vec / 1.0 & some_vec are rejected at parse time (WGSL has no mixed scalar/vector overloads there and the validator already rejected them, so those shaders never compiled — only the error changed).

Testing

New check snapshots in wgsl_errors.rs; four check_validation! tests are now parse errors. Also parsed every .wgsl in the repo (nothing newly rejected), regenerated all Targets::IR snapshots (no diff), and validated a smoke shader covering mat*vec, vec*mat, mat*mat, scalar*mat, splats, shifts, bitwise ops, abstract mixes and compound assignments.

Squash or Rebase?

Rebase — each commit passes CI on its own. The bottom commit belongs to #9973.

Checklist

  • I self-reviewed and fully understand this PR.
  • WebGPU implementations built with wgpu may be affected behaviorally.
  • Validation and feature gates are in place to confine behavioral changes.
  • Tests demonstrate the validation and altered logic works.
  • CHANGELOG.md entries for the user-facing effects of this change are present.
  • The PR is minimal, and doesn't make sense to land as multiple PRs.
  • Commits are logically scoped and individually reviewable.
  • The PR description has enough context to understand the motivation and solution implemented.

🤖 Generated with Claude Code

@emilk
emilk marked this pull request as ready for review July 30, 2026 10:13
@emilk
emilk marked this pull request as draft July 30, 2026 10:16
@emilk emilk changed the title [wgsl-in] Report assignment type mismatches in WGSL terms [wgsl-in] Report type mismatches in WGSL terms, not IR handle indices Jul 30, 2026
`try_automatic_conversions` passed concrete values through untouched,
deliberately leaving the type error to the IR validator. But the
validator can only name operands by handle index, and prints handles from
different arenas identically, so a `return` mismatch read:

    The `return` expression Some([1]) does not match the declared return type Some([1])

where one `[1]` is an expression and the other a type. Function call
arguments were equally opaque, and a composite constructor with a
wrong-typed component became "Composing 0's component type is not
expected".

The reason for the punt was message quality: reporting a plain mismatch
as a failed automatic conversion would mislead. So report a type
mismatch instead. Every caller of `try_automatic_conversions` now gets a
diagnostic with spans and WGSL type names, and no future caller can
forget to check.

`var`/`let` initializers keep their existing wording by mapping the new
error, which also makes their follow-up `compare_types` check redundant.

Fixes gfx-rs#7419.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@emilk
emilk force-pushed the emilk/wgsl-assignment-type-mismatch-error branch from c2641a7 to 99a463c Compare July 30, 2026 10:53
@emilk emilk changed the title [wgsl-in] Report type mismatches in WGSL terms, not IR handle indices [wgsl-in] Report assignment and binary operator type mismatches in WGSL terms Jul 30, 2026
emilk and others added 2 commits July 30, 2026 14:11
An assignment whose value type does not match the assigned-to memory
location was previously only caught by the IR validator, which can only
refer to the operands by IR handle index, producing errors like:

    The type of [13] doesn't match the type stored in [10]

and sometimes with no source span at all. Check the store types during
WGSL lowering instead, so the error names the actual WGSL types and
points at both the target and the value.

Fixes gfx-rs#7419.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Extend the previous commit to the rest of the places where the WGSL front
end deferred a type error to the IR validator, which can only refer to
the operands by handle index — and, worse, prints handles from different
arenas identically, so that e.g. a `return` mismatch read

    The `return` expression Some([1]) does not match the declared return type Some([1])

`try_automatic_conversions` used to pass concrete values straight
through, on the grounds that reporting them as failed conversions would
be misleading. Instead it now reports a plain type mismatch, so every
caller — `var`/`let` initializers, `return`, call arguments and composite
constructors — gets a diagnostic with spans and WGSL type names, and no
future caller can forget to check.

Binary operators are checked with `proc::binary_op_accepts_operands`,
extracted from the validator so both share one set of typing rules. This
also covers the short-circuiting `&&`/`||`, whose operands never appear
in a `Binary` expression for the validator to inspect, and compound
assignments like `m += v`.

Two consequences worth noting:

- `return` with no value in a function that declares a return type, and
  `return` with a value in one that doesn't, are now parse errors.
- `1.0 < some_vec` and `1.0 & some_vec` are now rejected at parse time.
  WGSL has no mixed scalar/vector overloads for the comparison and
  bitwise operators, and the validator already rejected them, so such
  shaders never compiled — only the error changed.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@emilk
emilk force-pushed the emilk/wgsl-assignment-type-mismatch-error branch from 99a463c to a7dcfef Compare July 30, 2026 12:12
@emilk emilk closed this Jul 30, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant