Skip to content

Commit c8f2aae

Browse files
authored
Use little-endian byte ordering for internal conversions. (#343)
When implementing reinterpret-cast functions, use `python.struct`'s `<` (little-endian) instead of `!` (network byte order). This has no effective semantic change, because the conversions are just converting between i32/f32 and i64/f64 and are always done in pairs, so it's only required that the decoding match the encoding. However, using little-endian more clearly describes the behavior as corresponding to a Wasm store followed by a Wasm load, which would both be little-endian. In theory this could become significant in the future if we add SIMD values where endianness conversions are partitioned by SIMD lanes, or other complex types.
1 parent 444b0f4 commit c8f2aae

File tree

2 files changed

+8
-8
lines changed

2 files changed

+8
-8
lines changed

design/mvp/CanonicalABI.md

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -500,10 +500,10 @@ def decode_i64_as_float(i):
500500
return canonicalize_nan64(core_f64_reinterpret_i64(i))
501501

502502
def core_f32_reinterpret_i32(i):
503-
return struct.unpack('!f', struct.pack('!I', i))[0] # f32.reinterpret_i32
503+
return struct.unpack('<f', struct.pack('<I', i))[0] # f32.reinterpret_i32
504504

505505
def core_f64_reinterpret_i64(i):
506-
return struct.unpack('!d', struct.pack('!Q', i))[0] # f64.reinterpret_i64
506+
return struct.unpack('<d', struct.pack('<Q', i))[0] # f64.reinterpret_i64
507507
```
508508

509509
An `i32` is converted to a `char` (a [Unicode Scalar Value]) by dynamically
@@ -760,10 +760,10 @@ def encode_float_as_i64(f):
760760
return core_i64_reinterpret_f64(maybe_scramble_nan64(f))
761761

762762
def core_i32_reinterpret_f32(f):
763-
return struct.unpack('!I', struct.pack('!f', f))[0] # i32.reinterpret_f32
763+
return struct.unpack('<I', struct.pack('<f', f))[0] # i32.reinterpret_f32
764764

765765
def core_i64_reinterpret_f64(f):
766-
return struct.unpack('!Q', struct.pack('!d', f))[0] # i64.reinterpret_f64
766+
return struct.unpack('<Q', struct.pack('<d', f))[0] # i64.reinterpret_f64
767767
```
768768

769769
The integral value of a `char` (a [Unicode Scalar Value]) is a valid unsigned

design/mvp/canonical-abi/definitions.py

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -435,10 +435,10 @@ def decode_i64_as_float(i):
435435
return canonicalize_nan64(core_f64_reinterpret_i64(i))
436436

437437
def core_f32_reinterpret_i32(i):
438-
return struct.unpack('!f', struct.pack('!I', i))[0] # f32.reinterpret_i32
438+
return struct.unpack('<f', struct.pack('<I', i))[0] # f32.reinterpret_i32
439439

440440
def core_f64_reinterpret_i64(i):
441-
return struct.unpack('!d', struct.pack('!Q', i))[0] # f64.reinterpret_i64
441+
return struct.unpack('<d', struct.pack('<Q', i))[0] # f64.reinterpret_i64
442442

443443
def convert_i32_to_char(cx, i):
444444
trap_if(i >= 0x110000)
@@ -611,10 +611,10 @@ def encode_float_as_i64(f):
611611
return core_i64_reinterpret_f64(maybe_scramble_nan64(f))
612612

613613
def core_i32_reinterpret_f32(f):
614-
return struct.unpack('!I', struct.pack('!f', f))[0] # i32.reinterpret_f32
614+
return struct.unpack('<I', struct.pack('<f', f))[0] # i32.reinterpret_f32
615615

616616
def core_i64_reinterpret_f64(f):
617-
return struct.unpack('!Q', struct.pack('!d', f))[0] # i64.reinterpret_f64
617+
return struct.unpack('<Q', struct.pack('<d', f))[0] # i64.reinterpret_f64
618618

619619
def char_to_i32(c):
620620
i = ord(c)

0 commit comments

Comments
 (0)