What should it be? Wabt uses v128.const i32 0xXXXXXXXX 0xXXXXXXXX 0xXXXXXXXX 0xXXXXXXXX, LLVM (which currently does not try too hard to match the official text format) uses v128.const followed by 2 or 4 LLVM floating point constants or 2, 4, 8, or 16 integer constants. Binaryen is about to get a generalization of Wabt's format that accepts i32, f32, i64, or f64 as the lane type and 2, 4, 8, or 16 constants as appropriate unless we decide otherwise here.
I think preserving the "v128.const i32 0xXXXXXXXX 0xXXXXXXXX 0xXXXXXXXX 0xXXXXXXXX" format used by wabt makes sense. It makes sense for the text format to use i32 as a canonical form to display the v128.const bits.
Changing this will invalidate most of the handwritten tests that relies on the format recognized by wabt.
It makes sense to support different lane numbers.
But why not use the syntax i32x4.const etc instead? That would be more in line with the other SIMD instruction names.
I like this idea, but it might suggest to a reader that they have different opcodes.
Ah, that's a good point, I agree that would be very odd. I retract the idea. :)
We have the related discussion on this topic here, https://github.com/WebAssembly/wabt/issues/663
@tlively is this resolved? shall we close this issue?
I think we have consensus that v128.const i32 0xXXXXXXXX 0xXXXXXXXX 0xXXXXXXXX 0xXXXXXXXX is a good format and that it should be the canonical format for printing these instructions. But do we also want to allow tools to accept other formats for reading? This was mentioned in https://github.com/WebAssembly/wabt/issues/663 as being useful for writing tests, but the issue was not really resolved there. I think allowing for additional formats is extremely valuable for writing readable tests. It would be nice to standardize these additional formats so that tests for different tools are not unnecessarily different.
So we should probably add v128.const {i8,i16,i64,f32,f64} ....
Thinking about it some more, it seems like the only information that is really needed is i vs f. The size is determined by the number of literals.
I wonder if we can't get away with distinguishing int vs float solely from the literal syntax as well, i.e., float if they have a decimal point or exponent, int otherwise (like in C and other languages). It would be an error if there is a mix.
I slightly prefer keeping the lane type around because doing so would mean that all existing tests are still valid and because it means that parsers (and human readers) never have to disambiguate between floats and ints by looking at value literals themselves. I believe no other instruction currently requires such disambiguation.
True, I think I buy the explicitness argument. It feels a bit odd, though, to use a type annotation that is not really the type of the literal as a whole. I think it would be somewhat more consistent to fully spell out the lane type, i.e., (v128.const i32x4 0 0 0 0) instead of just (v128.const i32 0 0 0 0).
For existing tests this should be a trivial search+replace.
Revisiting this issue, I'm fine with @rossberg's suggestion above to use they full vector type as the annotation. I'll create a PR to add text about this to the spec proposal.
Sorry, but it's not clear what was decided in the end. Does the spec require the immediate to be expressed using one of i32x4, i64x2, f32x4 or f64x2? Or can we still use i8x16 and i16x8?
Basically, is this legal:
v128.const i16x8 0 0 0 0 0 0 0 0
@carlsmith https://github.com/WebAssembly/simd/blob/master/proposals/simd/TextSIMD.md has some documentation the text format for v128.const as well. (See Merged PR by tlively linked in this issue)
Thanks, @ngzhian. Much appreciated.