Document Wasm SIMD arithmetic instructions#43583
Document Wasm SIMD arithmetic instructions#43583chrisdavidmills wants to merge 24 commits intomdn:mainfrom
Conversation
ge_s, ge_u, gt_s, gt_u, le_s, le_u, lt_s, lt_u all showed f32/f64 prefixes in the example column (e.g. `f32.ge_s`) which don't exist.
108 and 109 are both < 128 so they encode as single LEB128 bytes. The examples incorrectly showed a trailing 0x01 byte.
f32.div and f64.div showed 0x92/0xa0 (the add opcodes). f64x2.div showed 0xf0 0x01 (f64x2.add). Correct values are 0x95, 0xa3, and 0xf3 0x01 respectively.
i32.const and i64.const had spurious extra bytes; 2 and 1 are single LEB128 bytes so no extra byte is needed. f32.const 2.5 had an extra trailing 0x40 byte; 2.5 in f32 little-endian is 4 bytes. Also align the SIMD description example to use i32x4 consistently with the binary table.
The Wasm code uses i16x8 but the prose described it as i8x16.
The prose described the lane type as i8x16 but the code uses i16x8. Also switched to extract_lane_u since the page demonstrates unsigned shift-right.
ceil and floor only apply to f32x4 and f64x2. Using i32x4 with float literal values was incorrect.
The original described it as operating on "each byte" and "bit 7", which is only accurate for i8x16. Updated to say "each lane" and clarified the threshold values for wider types in the note.
The spec defines ixN.all_true as checking that each lane is non-zero, not each bit. A lane value of 1 passes (non-zero lane) even though most bits within it are 0.
Those pages don't exist yet; plain text avoids publishing dead links.
| - `output` | ||
| - : The output value. | ||
|
|
||
| For a non-SIMD `abs`, the `input` and `output` will be basic numeric values such as `-3.5` or `3.5`. |
There was a problem hiding this comment.
This reads as though the output can be -3.5.
There was a problem hiding this comment.
Fair point. I've removed the negative value in my next commit.
|
|
||
| #### JavaScript | ||
|
|
||
| In our script, we grab a reference to a {{htmlelement("p")}} element that we will output our result to, then define an object for import into Wasm containing a single function that writes a value to the output `<p>`. We then compile and instantiate our Wasm module using the [`WebAssembly.instantiateStreaming()`](/en-US/docs/WebAssembly/Reference/JavaScript_interface/instantiateStreaming_static) method, importing the object in the process. |
There was a problem hiding this comment.
Any reason you chose "in our" rather than "in the following", "in the", or "in this"? Feels inconsistent/odd.
There was a problem hiding this comment.
No reason at all. I don't think this is a big enough issue to worry about. It feels slightly more conversational than usual, but otherwise OK.
|
|
||
| For a non-SIMD `abs`, the `input` and `output` will be basic numeric values such as `-3.5` or `3.5`. | ||
|
|
||
| For a [SIMD](/en-US/docs/WebAssembly/Reference/SIMD) `abs`, the `input` and `output` will be [`v128`](/en-US/docs/WebAssembly/Reference/Types/v128) value interpretations, for example `i32x4 4 -8 12 -16`. |
There was a problem hiding this comment.
Ditto. So for a SIMD all the values will be made absolute after the instruction?
There was a problem hiding this comment.
Yes. I changed this one to all positive values too.
|
|
||
| For a non-SIMD `add`, these will be basic numeric values such as `3` or `3.5`. | ||
|
|
||
| For a [SIMD](/en-US/docs/WebAssembly/Reference/SIMD) `add`, these will be [`v128`](/en-US/docs/WebAssembly/Reference/Types/v128) value interpretations, for example `f32x4 0x9 0xa 0xb 0xc`. |
There was a problem hiding this comment.
I think you need to say what numbers are added in the SIMD case since there are multiple lanes in the input and the description is "is used for adding up two numbers".
Also in this case, where does the value "go"? Is it written into the v128 value or onto the stack?
There was a problem hiding this comment.
Ah, this is answered by the example. I think it is "For SIMD this adds two v128 values of the same interpretation type, returning another v128 on the stack where each lane is the addition of the corresponding lanes in the original blah blha.
It isn't clear if they have to be the same type of data, though I would assume so.
We should capture all this here.
There was a problem hiding this comment.
And similar for all the other instructions
There was a problem hiding this comment.
Some of this is a bit too obvious for the target audience. For example, if the "Type" section shows an output, you know that a value is pushed onto the stack as a result.
However, I think it is useful to explicitly describe the nature of each output in the case of SIMD versions of the instructions. I've gone through and added a descriptive sentence for each one, for example:
For a SIMD
add, these will bev128value interpretations, for examplef32x4 0x9 0xa 0xb 0xc. Each lane of the output pushed to the stack is the addition of the corresponding lanes in the input values.
|
|
||
| For a non-SIMD `and`, these will be basic numeric values such as `14` or `3`. | ||
|
|
||
| For a [SIMD](/en-US/docs/WebAssembly/Reference/SIMD) `and`, these will be [`v128`](/en-US/docs/WebAssembly/Reference/Types/v128) value interpretations, for example `i32x4 9 4 -16 100`. |
There was a problem hiding this comment.
As above https://github.com/mdn/content/pull/43583/changes#r3061408253 we need to make it clear if the types are the same and that the comparison is by corresponding lane, returning a new value to the stack of the same type.
There was a problem hiding this comment.
I've added an explanation, as per above. The types will always be the same in Wasm.
There was a problem hiding this comment.
YOu changed this in all the other cases to instruction/is
There was a problem hiding this comment.
Good catch; changed.
hamishwillee
left a comment
There was a problem hiding this comment.
It is all very consistent. I haven't got the energy or time to review every case, so I have read a few carefully and added a few points for discussion.
| - `input2` | ||
| - : The second input value. | ||
| - `output` | ||
| - : The output value. A new `v128` of the same type as the inputs, with each lane set to the greater of that lane index's value on the two inputs. |
There was a problem hiding this comment.
| - : The output value. A new `v128` of the same type as the inputs, with each lane set to the greater of that lane index's value on the two inputs. | |
| - : The output value. A new `v128` of the same type as the inputs, with each lane set to the lower of that lane index's value on the two inputs. |
There was a problem hiding this comment.
This was a claude check ^^^
Here is the rest of the comments:
- simd/bitwise/index.md — wrong URL for any_true
any_true links to the andnot page. Should be .../bitwise/any_true.
Grammar errors
- simd/index.md — "This instructions"
▎ "This instructions in this section are SIMD-specific."
Should be: "The instructions in this section are SIMD-specific."
- simd/bitwise/any_true/index.md — article before v128
▎ "tests whether an v128 input value contains any non-zero bits."
Should be: "tests whether a v128 input value..." (v is a consonant sound).
- simd/bitwise/all_true/index.md — type section says input1 but signature has [input]
### Type
[input] -> [output]
- `input1`
- : The input `v128` value interpretation.
The parameter name is input1 but the type signature uses input. Should be consistent — either input1/input2 pattern
(if that's the convention, but all_true only takes one input) or just input. This is the same pattern issue as
bitmask.
- simd/bitwise/bitmask/index.md — same input1 vs [input] inconsistency
The type signature shows [input] -> [output] but the parameter description uses input1.
Spelling errors
- simd/bitwise/bitmask/index.md — "equivent"
▎ "The example's output value is 4096, which is the decimal equivent of the above binary pattern."
Should be: "equivalent"
- simd/bitwise/bitmask/index.md — duplicate word "means means"
▎ "while an MSB of 0 means means the value is less than 128."
Should be: "while an MSB of 0 means the value is less than 128."
Wrong section heading (content accuracy)
- simd/arithmetic/index.md — ## Comparison heading is misleading
The section under ## Comparison lists max_s, max_u, min_s, min_u — these are arithmetic min/max instructions, not comparison instructions (comparisons return booleans). A heading like ## Min/Max would be more accurate.
There was a problem hiding this comment.
OK, cool, I've corrected all the ones that were not already fixed by @eqrion's PR.
SIMD arithmetic fixes
|
This pull request has merge conflicts that must be resolved before it can be merged. |
|
Just commenting that I did a quick technical review of this as well. It's a lot so I didn't look at everything. I added some commits that Chris merged on to his branch. |
Description
This PR adds reference docs for WebAssembly SIMD arithmetic instructions (and possibly some more bitwise ones too).
Note: I've updated the general
shlpage to cover SIMD and non-SIMD values. I've also deleted the previously published SIMD-specificshlpage and redirected it to the general one.Motivation
Additional details
Related issues and pull requests