test legalizer target x86_64 ; Test legalization for various forms of heap addresses. function %heap_addrs(i32, i64, i64 vmctx) { gv4 = vmctx gv0 = iadd_imm.i64 gv4, 64 gv1 = iadd_imm.i64 gv4, 72 gv2 = iadd_imm.i64 gv4, 80 gv3 = load.i32 notrap aligned gv4+88 heap0 = static gv0, min 0x1_0000, bound 0x1_0000_0000, guard 0x8000_0000, index_type i32 heap1 = static gv0, guard 0x1000, bound 0x1_0000, index_type i32 heap2 = static gv0, min 0x1_0000, bound 0x1_0000_0000, guard 0x8000_0000, index_type i64 heap3 = static gv0, guard 0x1000, bound 0x1_0000, index_type i64 heap4 = dynamic gv1, min 0x1_0000, bound gv3, guard 0x8000_0000, index_type i32 heap5 = dynamic gv1, bound gv3, guard 0x1000, index_type i32 heap6 = dynamic gv1, min 0x1_0000, bound gv2, guard 0x8000_0000, index_type i64 heap7 = dynamic gv1, bound gv2, guard 0x1000, index_type i64 ; check: heap0 = static gv0, min 0x0001_0000, bound 0x0001_0000_0000, guard 0x8000_0000, index_type i32 ; check: heap1 = static gv0, min 0, bound 0x0001_0000, guard 4096, index_type i32 ; check: heap2 = static gv0, min 0x0001_0000, bound 0x0001_0000_0000, guard 0x8000_0000, index_type i64 ; check: heap3 = static gv0, min 0, bound 0x0001_0000, guard 4096, index_type i64 ; check: heap4 = dynamic gv1, min 0x0001_0000, bound gv3, guard 0x8000_0000, index_type i32 ; check: heap5 = dynamic gv1, min 0, bound gv3, guard 4096, index_type i32 ; check: heap6 = dynamic gv1, min 0x0001_0000, bound gv2, guard 0x8000_0000, index_type i64 ; check: heap7 = dynamic gv1, min 0, bound gv2, guard 4096, index_type i64 ebb0(v0: i32, v1: i64, v3: i64): ; The fast-path; 32-bit index, static heap with a sufficient bound, no bounds check needed! v4 = heap_addr.i64 heap0, v0, 0 ; check: v12 = uextend.i64 v0 ; check: v13 = iadd_imm v3, 64 ; check: v4 = iadd v13, v12 v5 = heap_addr.i64 heap1, v0, 0 ; check: v14 = icmp_imm ugt v0, 0x0001_0000 ; check: brz v14, ebb1 ; check: trap heap_oob ; check: ebb1: ; check: v15 = uextend.i64 v0 ; check: v16 = iadd_imm.i64 v3, 64 ; check: v5 = iadd v16, v15 v6 = heap_addr.i64 heap2, v1, 0 ; check: v19 = iconst.i64 0x0001_0000_0000 ; check: v17 = icmp.i64 ugt v1, v19 ; check: brz v17, ebb2 ; check: trap heap_oob ; check: ebb2: ; check: v18 = iadd_imm.i64 v3, 64 ; check: v6 = iadd v18, v1 v7 = heap_addr.i64 heap3, v1, 0 ; check: v20 = icmp_imm.i64 ugt v1, 0x0001_0000 ; check: brz v20, ebb3 ; check: trap heap_oob ; check: ebb3: ; check: v21 = iadd_imm.i64 v3, 64 ; check: v7 = iadd v21, v1 v8 = heap_addr.i64 heap4, v0, 0 ; check: v22 = load.i32 notrap aligned v3+88 ; check: v23 = iadd_imm v22, 0 ; check: v24 = icmp.i32 ugt v0, v23 ; check: brz v24, ebb4 ; check: trap heap_oob ; check: ebb4: ; check: v25 = uextend.i64 v0 ; check: v26 = iadd_imm.i64 v3, 72 ; check: v8 = iadd v26, v25 v9 = heap_addr.i64 heap5, v0, 0 ; check: v27 = load.i32 notrap aligned v3+88 ; check: v28 = iadd_imm v27, 0 ; check: v29 = icmp.i32 ugt v0, v28 ; check: brz v29, ebb5 ; check: trap heap_oob ; check: ebb5: ; check: v30 = uextend.i64 v0 ; check: v31 = iadd_imm.i64 v3, 72 ; check: v9 = iadd v31, v30 v10 = heap_addr.i64 heap6, v1, 0 ; check: v32 = iadd_imm.i64 v3, 80 ; check: v33 = iadd_imm v32, 0 ; check: v34 = icmp.i64 ugt v1, v33 ; check: brz v34, ebb6 ; check: trap heap_oob ; check: ebb6: ; check: v35 = iadd_imm.i64 v3, 72 ; check: v10 = iadd v35, v1 v11 = heap_addr.i64 heap7, v1, 0 ; check: v36 = iadd_imm.i64 v3, 80 ; check: v37 = iadd_imm v36, 0 ; check: v38 = icmp.i64 ugt v1, v37 ; check: brz v38, ebb7 ; check: trap heap_oob ; check: ebb7: ; check: v39 = iadd_imm.i64 v3, 72 ; check: v11 = iadd v39, v1 return }