import testcheck # 大小端字节序专项: # · 标记 `bigend` 的槽位,在(默认的)小端目标上必须以**大端字节序列**存放; # · 标记 `littlend` 的槽位与目标序一致,按目标序存放; # · 无标记 = native,不参与任何交换。 # 因此本测试既校验「读写成对交换」的语义不变式(round-trip), # 又**直接检查内存里的字节序列** —— 只有后者能真正证明交换发生了 # (纯 round-trip 即使不交换也会通过,因为读写交换会互相抵消)。 def read_byte(p: rawptr, i: int) -> int: """读指针第 i 个字节;i8 按有符号解释,这里只取低 8 位。""" return int(p[i]) & 0xFF def test_big_endian_local() -> None: """大端局部变量:内存字节必须是 12 34 56 78(MSB 在前),读回值不变。""" testcheck.section("BigEndian local variable") x: bigend int32 = 0x12345678 px: rawptr = rawptr(&x) testcheck.check(read_byte(px, 0) == 0x12, "BigEndian memory byte[0] = 0x12 (MSB first)", "expect 0x12") testcheck.check(read_byte(px, 1) == 0x34, "BigEndian memory byte[1] = 0x34", "expect 0x34") testcheck.check(read_byte(px, 2) == 0x56, "BigEndian memory byte[2] = 0x56", "expect 0x56") testcheck.check(read_byte(px, 3) == 0x78, "BigEndian memory byte[3] = 0x78 (LSB last)", "expect 0x78") testcheck.check(x == 0x12345678, "BigEndian local round-trip", "expect 0x12345678") def test_little_endian_local() -> None: """小端局部变量:小端目标上与目标序一致,内存字节是 78 56 34 12(LSB 在前)。""" testcheck.section("LittleEndian local variable") y: littlend int32 = 0x12345678 py: rawptr = rawptr(&y) testcheck.check(read_byte(py, 0) == 0x78, "LittleEndian memory byte[0] = 0x78 (LSB first)", "expect 0x78") testcheck.check(read_byte(py, 3) == 0x12, "LittleEndian memory byte[3] = 0x12", "expect 0x12") testcheck.check(y == 0x12345678, "LittleEndian local round-trip", "expect 0x12345678") def test_be_le_differ() -> None: """同一值分别按大端/小端存放,内存字节序列必须互为反转。""" testcheck.section("BigEndian vs LittleEndian memory layout") a: bigend int32 = 0x22334455 b: littlend int32 = 0x22334455 pa: rawptr = rawptr(&a) pb: rawptr = rawptr(&b) testcheck.check(read_byte(pa, 0) == read_byte(pb, 3), "BE byte[0] == LE byte[3]", "expect reversed byte order") testcheck.check(read_byte(pa, 1) == read_byte(pb, 2), "BE byte[1] == LE byte[2]", "expect reversed byte order") testcheck.check(read_byte(pa, 0) == 0x22, "BigEndian starts with MSB (0x22)", "expect 0x22") class NetHeader: """经典用法:结构体成员带字节序标记(对齐 TransPyC 文档里的 NetHeader)。""" magic: bigend int32 length: littlend int16 body: int32 def test_struct_field_roundtrip() -> None: """结构体成员:带标记的字段读写必须相等(读写成对交换的语义不变式)。""" testcheck.section("Byte-order struct fields") h: NetHeader = NetHeader() h.magic = 0x11223344 h.length = 0x5566 h.body = 0x778899AA testcheck.check(h.magic == 0x11223344, "BigEndian field magic round-trip", "expect 0x11223344") testcheck.check(h.length == 0x5566, "BigEndian field length round-trip", "expect 0x5566") testcheck.check(h.body == 0x778899AA, "native field body round-trip", "expect 0x778899AA") # 赋值后再读第二次,确保交换是成对的、不会逐次累积 testcheck.check(h.magic == 0x11223344, "BigEndian field second read unchanged", "expect 0x11223344") def test_repeated_write() -> None: """反复写入不同值,读回始终正确(交换必须成对且不残留)。""" testcheck.section("Repeated writes") x: bigend int32 = 0 i: int = 0 ok: int = 1 for i in range(int(4)): v: int32 = int32(0x10000000 * (i + 1)) x = v if x != v: ok = 0 testcheck.check(ok == 1, "BigEndian repeated writes stay consistent", "expect all round-trips to match") def main() -> int: testcheck.begin("EndianTest: BigEndian / LittleEndian byte order") test_big_endian_local() test_little_endian_local() test_be_le_differ() test_struct_field_roundtrip() test_repeated_write() return testcheck.end()