Exemplo n.º 1
0
    def runTest(self):

        x = Argument(uint32_t)
        y = Argument(uint32_t)

        with Function("integer_sum", (x, y), uint32_t) as function:
            r_x = GeneralPurposeRegister32()
            r_y = GeneralPurposeRegister32()
            LOAD.ARGUMENT(r_x, x)
            LOAD.ARGUMENT(r_y, y)

            ADD(r_x, r_y)
            MOV(eax, r_x)
            RETURN()

        code = function.format()
        ref_code = """
uint32_t integer_sum(uint32_t x, uint32_t y)
    LOAD.ARGUMENT gp32-vreg<1>, uint32_t x
    LOAD.ARGUMENT gp32-vreg<2>, uint32_t y
    ADD gp32-vreg<1>, gp32-vreg<2>
    MOV eax, gp32-vreg<1>
    RETURN
"""
        assert equal_codes(code,
                           ref_code), "Unexpected Peach-Py code:\n" + code
Exemplo n.º 2
0
    def runTest(self):

        x_arg = Argument(uint32_t)
        y_arg = Argument(uint32_t)

        with Function("integer_sum", (x_arg, y_arg), uint32_t) as function:
            x = ecx
            LOAD.ARGUMENT(x, x_arg)
            y = r8d
            LOAD.ARGUMENT(y, y_arg)

            ADD(x, y)

            STORE.RESULT(x)
            RETURN()

        code = function.finalize(abi.goasm_amd64_abi).format("go")
        ref_code = """
// func integer_sum(x uint32, y uint32) uint32
TEXT \xc2\xB7integer_sum(SB),4,$0-12
    MOVL x+0(FP), CX
    MOVL y+4(FP), R8
    ADDL R8, CX
    MOVL CX, ret+8(FP)
    RET
"""
        assert equal_codes(code, ref_code), "Unexpected Golang code:\n" + code
Exemplo n.º 3
0
    def runTest(self):

        x = Argument(uint32_t)
        y = Argument(uint32_t)

        with Function("integer_sum", (x, y), uint32_t) as function:
            r_x = GeneralPurposeRegister32()
            r_x_temp = GeneralPurposeRegister32()
            r_y = GeneralPurposeRegister32()
            buffer = LocalVariable(4)

            LOAD.ARGUMENT(r_x, x)
            LOAD.ARGUMENT(r_y, y)

            MOV(buffer, r_x)
            MOV(r_x_temp, buffer)

            ADD(r_x_temp, r_y)
            MOV(eax, r_x_temp)
            RETURN()

        code = function.format()
        ref_code = """
uint32_t integer_sum(uint32_t x, uint32_t y)
    LOAD.ARGUMENT gp32-vreg<1>, uint32_t x
    LOAD.ARGUMENT gp32-vreg<3>, uint32_t y
    MOV dword [rsp], gp32-vreg<1>
    MOV gp32-vreg<2>, dword [rsp]
    ADD gp32-vreg<2>, gp32-vreg<3>
    MOV eax, gp32-vreg<2>
    RETURN
"""
        assert equal_codes(code, ref_code), "Unexpected PeachPy code:\n" + code
Exemplo n.º 4
0
    def runTest(self):

        x = Argument(uint32_t)
        y = Argument(uint32_t)

        with Function("integer_sum", (x, y), uint32_t) as function:
            r_x = GeneralPurposeRegister32()
            r_y = GeneralPurposeRegister32()
            LOAD.ARGUMENT(r_x, x)
            LOAD.ARGUMENT(r_y, y)

            ADD(r_x, r_y)
            MOV(eax, r_x)
            RETURN()

        code = function.format()
        ref_code = """
uint32_t integer_sum(uint32_t x, uint32_t y)
    LOAD.ARGUMENT gp32-vreg<1>, uint32_t x
    LOAD.ARGUMENT gp32-vreg<2>, uint32_t y
    ADD gp32-vreg<1>, gp32-vreg<2>
    MOV eax, gp32-vreg<1>
    RETURN
"""
        assert equal_codes(code, ref_code), "Unexpected Peach-Py code:\n" + code
Exemplo n.º 5
0
    def runTest(self):

        with Function("empty", tuple()) as function:
            RETURN()

        code = function.format()
        ref_code = """
void empty()
    RETURN
"""
        assert equal_codes(code, ref_code), "Unexpected PeachPy code:\n" + code
Exemplo n.º 6
0
    def runTest(self):

        with Function("empty", tuple()) as function:
            RETURN()

        code = function.format()
        ref_code = """
void empty()
    RETURN
"""
        assert equal_codes(code, ref_code), "Unexpected Peach-Py code:\n" + code
Exemplo n.º 7
0
    def runTest(self):

        with Function("empty", tuple()) as function:
            RETURN()

        code = function.finalize(abi.goasm_amd64_abi).format("go")
        ref_code = """
// func empty()
TEXT \xc2\xB7empty(SB),4,$0
    RET
"""
        assert equal_codes(code, ref_code), "Unexpected Golang code:\n" + code
Exemplo n.º 8
0
    def runTest(self):
        with Function("duplicate_autonamed_labels", tuple()) as function:
            # One "skip" label
            skip = Label()
            JMP(skip)
            INT(3)
            LABEL(skip)

            # Another "skip" label
            skip = Label()
            JMP(skip)
            NOP()
            LABEL(skip)

            RETURN()

        code = function.format()
        ref_code0 = """
void duplicate_autonamed_labels()
    JMP skip0
    INT 3
skip0:
    JMP skip1
    NOP
skip1:
    RETURN
"""
        ref_code1 = """
void duplicate_autonamed_labels()
    JMP skip1
    INT 3
skip1:
    JMP skip0
    NOP
skip0:
    RETURN
"""
        assert equal_codes(code, ref_code0) or equal_codes(code, ref_code1), \
            "Unexpected PeachPy code:\n" + code
Exemplo n.º 9
0
    def runTest(self):
        with Function("duplicate_autonamed_labels", tuple()) as function:
            # One "skip" label
            skip = Label()
            JMP(skip)
            INT(3)
            LABEL(skip)

            # Another "skip" label
            skip = Label()
            JMP(skip)
            NOP()
            LABEL(skip)

            RETURN()

        code = function.format()
        ref_code0 = """
void duplicate_autonamed_labels()
    JMP skip0
    INT 3
skip0:
    JMP skip1
    NOP
skip1:
    RETURN
"""
        ref_code1 = """
void duplicate_autonamed_labels()
    JMP skip1
    INT 3
skip1:
    JMP skip0
    NOP
skip0:
    RETURN
"""
        assert equal_codes(code, ref_code0) or equal_codes(code, ref_code1), \
            "Unexpected Peach-Py code:\n" + code
Exemplo n.º 10
0
    def runTest(self):
        x = Argument(uint32_t)
        y = Argument(uint32_t)

        with Function("integer_sum", (x, y), uint32_t) as function:
            reg_x = GeneralPurposeRegister32()
            reg_y = GeneralPurposeRegister32()
            LOAD.ARGUMENT(reg_x, x)
            LOAD.ARGUMENT(reg_y, y)

            ADD(reg_x, reg_y)
            MOV(eax, reg_x)
            RETURN()

        listing = function.format_instructions()
        ref_listing = """
LOAD.ARGUMENT gp32-vreg<1>, uint32_t x
    In regs:
    Out regs:   gp64-vreg<1>
    Live regs:
    Avail regs:

LOAD.ARGUMENT gp32-vreg<2>, uint32_t y
    In regs:
    Out regs:   gp64-vreg<2>
    Live regs:  gp32-vreg<1>
    Avail regs: gp64-vreg<1>

ADD gp32-vreg<1>, gp32-vreg<2>
    In regs:    gp32-vreg<1>, gp32-vreg<2>
    Out regs:   gp64-vreg<1>
    Live regs:  gp32-vreg<1>, gp32-vreg<2>
    Avail regs: gp64-vreg<1>, gp64-vreg<2>

MOV eax, gp32-vreg<1>
    In regs:    gp32-vreg<1>
    Out regs:   rax
    Live regs:  gp32-vreg<1>
    Avail regs: gp64-vreg<1>, gp64-vreg<2>

RETURN
    In regs:
    Out regs:
    Live regs:
    Avail regs: gp64-vreg<1>, gp64-vreg<2>, rax
"""
        assert equal_codes(
            listing, ref_listing), "Unexpected PeachPy listing:\n" + listing
Exemplo n.º 11
0
    def runTest(self):
        with Function("crash", (), int64_t) as function:
            r = GeneralPurposeRegister64()
            MOV(r, 999)
            RETURN(rax)

        listing = function.finalize(abi.goasm_amd64_abi).format("go")
        ref_listing = """
// func crash() int64
TEXT \xc2\xB7crash(SB),4,$0-8
	MOVQ $999, BX
	MOVQ AX, ret+0(FP)
	RET
"""
        assert equal_codes(
            listing, ref_listing), "Unexpected PeachPy listing:\n" + listing
Exemplo n.º 12
0
    def runTest(self):
        x = Argument(uint32_t)
        y = Argument(uint32_t)

        with Function("integer_sum", (x, y), uint32_t) as function:
            reg_x = GeneralPurposeRegister32()
            reg_y = GeneralPurposeRegister32()
            LOAD.ARGUMENT(reg_x, x)
            LOAD.ARGUMENT(reg_y, y)

            ADD(reg_x, reg_y)
            MOV(eax, reg_x)
            RETURN()

        listing = function.format_instructions()
        ref_listing = """
LOAD.ARGUMENT gp32-vreg<1>, uint32_t x
    In regs:
    Out regs:   gp64-vreg<1>
    Live regs:
    Avail regs:

LOAD.ARGUMENT gp32-vreg<2>, uint32_t y
    In regs:
    Out regs:   gp64-vreg<2>
    Live regs:  gp32-vreg<1>
    Avail regs: gp64-vreg<1>

ADD gp32-vreg<1>, gp32-vreg<2>
    In regs:    gp32-vreg<1>, gp32-vreg<2>
    Out regs:   gp64-vreg<1>
    Live regs:  gp32-vreg<1>, gp32-vreg<2>
    Avail regs: gp64-vreg<1>, gp64-vreg<2>

MOV eax, gp32-vreg<1>
    In regs:    gp32-vreg<1>
    Out regs:   rax
    Live regs:  gp32-vreg<1>
    Avail regs: gp64-vreg<1>, gp64-vreg<2>

RETURN
    In regs:
    Out regs:
    Live regs:
    Avail regs: gp64-vreg<1>, gp64-vreg<2>, rax
"""
        assert equal_codes(listing, ref_listing), "Unexpected Peach-Py listing:\n" + listing
Exemplo n.º 13
0
    def runTest(self):
        with Function("autonamed_label", tuple()) as function:
            skip_nop = Label()
            JMP(skip_nop)
            NOP()
            LABEL(skip_nop)
            RETURN()

        code = function.format()
        ref_code = """
void autonamed_label()
    JMP skip_nop
    NOP
skip_nop:
    RETURN
"""
        assert equal_codes(code, ref_code), "Unexpected PeachPy code:\n" + code
Exemplo n.º 14
0
    def runTest(self):
        with Function("autonamed_label", tuple()) as function:
            skip_nop = Label()
            JMP(skip_nop)
            NOP()
            LABEL(skip_nop)
            RETURN()

        code = function.format()
        ref_code = """
void autonamed_label()
    JMP skip_nop
    NOP
skip_nop:
    RETURN
"""
        assert equal_codes(code, ref_code), "Unexpected Peach-Py code:\n" + code
Exemplo n.º 15
0
    def runTest(self):
        with Function("unreferenced_labels", tuple()) as function:
            used_label = Label("used")
            unused_label = Label("unused")
            LABEL(unused_label)
            JMP(used_label)
            LABEL(used_label)
            RETURN()

        code = function.format()
        ref_code = """
void unreferenced_labels()
    JMP used
used:
    RETURN
"""
        assert equal_codes(code, ref_code), "Unexpected PeachPy code:\n" + code
Exemplo n.º 16
0
    def runTest(self):
        with Function("unreferenced_labels", tuple()) as function:
            used_label = Label("used")
            unused_label = Label("unused")
            LABEL(unused_label)
            JMP(used_label)
            LABEL(used_label)
            RETURN()

        code = function.format()
        ref_code = """
void unreferenced_labels()
    JMP used
used:
    RETURN
"""
        assert equal_codes(code, ref_code), "Unexpected Peach-Py code:\n" + code
Exemplo n.º 17
0
    def runTest(self):
        x = Argument(double_)

        with Function("return_float_arg", (x, ), double_) as function:
            xmm_x = XMMRegister()
            LOAD.ARGUMENT(xmm_x, x)

            MOVSD(xmm0, xmm_x)
            RETURN()

        code = function.format()
        ref_code = """
double return_float_arg(double x)
    LOAD.ARGUMENT xmm-vreg<1>, double x
    MOVSD xmm0, xmm-vreg<1>
    RETURN
"""
        assert equal_codes(code, ref_code), "Unexpected PeachPy code:\n" + code
Exemplo n.º 18
0
    def runTest(self):
        x = Argument(m128)

        with Function("return_m128_arg", (x, ), m128) as function:
            xmm_x = XMMRegister()
            LOAD.ARGUMENT(xmm_x, x)

            MOVAPS(xmm0, xmm_x)
            RETURN()

        code = function.format()
        ref_code = """
__m128 return_m128_arg(__m128 x)
    LOAD.ARGUMENT xmm-vreg<1>, __m128 x
    MOVAPS xmm0, xmm-vreg<1>
    RETURN
"""
        assert equal_codes(code, ref_code), "Unexpected PeachPy code:\n" + code
Exemplo n.º 19
0
    def runTest(self):
        with Function("implicit_reg", (), uint64_t) as function:
            reg_tmp = GeneralPurposeRegister64()
            MOV(reg_tmp, 42)
            CPUID()
            RETURN(reg_tmp)

        listing = function.finalize(abi.goasm_amd64_abi).format("go")
        ref_listing = """
// func implicit_reg() uint64
TEXT \xc2\xB7implicit_reg(SB),4,$0-8
	MOVQ $42, DI
	CPUID
	MOVQ DI, ret+0(FP)
	RET
"""
        assert equal_codes(
            listing, ref_listing), "Unexpected PeachPy listing:\n" + listing
Exemplo n.º 20
0
    def runTest(self):
        with Function("explicit_reg_input", (), uint64_t) as function:
            reg_tmp = GeneralPurposeRegister64()
            MOV(reg_tmp, 42)
            MOV([reg_tmp], rax)
            RETURN(reg_tmp)

        listing = function.finalize(abi.goasm_amd64_abi).format("go")
        ref_listing = """
// func explicit_reg_input() uint64
TEXT \xc2\xB7explicit_reg_input(SB),4,$0-8
   	MOVQ $42, BX
   	MOVQ AX, 0(BX)
   	MOVQ BX, ret+0(FP)
   	RET
"""
        assert equal_codes(
            listing, ref_listing), "Unexpected PeachPy listing:\n" + listing
Exemplo n.º 21
0
    def runTest(self):
        x = Argument(m128)

        with Function("return_m128_arg", (x,), m128) as function:
            xmm_x = XMMRegister()
            LOAD.ARGUMENT(xmm_x, x)

            MOVAPS(xmm0, xmm_x)
            RETURN()

        code = function.format()
        ref_code = """
__m128 return_m128_arg(__m128 x)
    LOAD.ARGUMENT xmm-vreg<1>, __m128 x
    MOVAPS xmm0, xmm-vreg<1>
    RETURN
"""
        assert equal_codes(code, ref_code), "Unexpected Peach-Py code:\n" + code
Exemplo n.º 22
0
    def runTest(self):
        x = Argument(double_)

        with Function("return_float_arg", (x,), double_) as function:
            xmm_x = XMMRegister()
            LOAD.ARGUMENT(xmm_x, x)

            MOVSD(xmm0, xmm_x)
            RETURN()

        code = function.format()
        ref_code = """
double return_float_arg(double x)
    LOAD.ARGUMENT xmm-vreg<1>, double x
    MOVSD xmm0, xmm-vreg<1>
    RETURN
"""
        assert equal_codes(code, ref_code), "Unexpected Peach-Py code:\n" + code
Exemplo n.º 23
0
    def runTest(self):

        n = Argument(uint32_t)

        with Function("return_int_arg", (n, ), uint32_t) as function:
            r_n = GeneralPurposeRegister32()
            LOAD.ARGUMENT(r_n, n)

            MOV(eax, r_n)
            RETURN()

        code = function.format()
        ref_code = """
uint32_t return_int_arg(uint32_t n)
    LOAD.ARGUMENT gp32-vreg<1>, uint32_t n
    MOV eax, gp32-vreg<1>
    RETURN
"""
        assert equal_codes(code, ref_code), "Unexpected PeachPy code:\n" + code
Exemplo n.º 24
0
    def runTest(self):

        n = Argument(uint32_t)

        with Function("return_int_arg", (n,), uint32_t) as function:
            r_n = GeneralPurposeRegister32()
            LOAD.ARGUMENT(r_n, n)

            MOV(eax, r_n)
            RETURN()

        code = function.format()
        ref_code = """
uint32_t return_int_arg(uint32_t n)
    LOAD.ARGUMENT gp32-vreg<1>, uint32_t n
    MOV eax, gp32-vreg<1>
    RETURN
"""
        assert equal_codes(code, ref_code), "Unexpected Peach-Py code:\n" + code
Exemplo n.º 25
0
    def runTest(self):

        n_arg = Argument(uint32_t)

        with Function("return_int_arg", (n_arg,), uint32_t) as function:
            n = ebx
            LOAD.ARGUMENT(n, n_arg)

            STORE.RESULT(n)
            RETURN()

        code = function.finalize(abi.goasm_amd64_abi).format("go")
        ref_code = """
// func return_int_arg(n uint32) uint32
TEXT \xc2\xB7return_int_arg(SB),4,$0-8
    MOVL n+0(FP), BX
    MOVL BX, ret+4(FP)
    RET
"""
        assert equal_codes(code, ref_code), "Unexpected Golang code:\n" + code
Exemplo n.º 26
0
    def runTest(self):
        x = Argument(ptr(const_float_))
        y = Argument(ptr(float_))
        length = Argument(size_t)

        with Function("square", (x, y, length)) as function:
            r_x = GeneralPurposeRegister64()
            r_y = GeneralPurposeRegister64()
            r_length = GeneralPurposeRegister64()
            LOAD.ARGUMENT(r_x, x)
            LOAD.ARGUMENT(r_y, y)
            LOAD.ARGUMENT(r_length, length)

            with Loop() as loop:
                xmm_value = XMMRegister()
                MOVSS(xmm_value, [r_x])
                MULSS(xmm_value, xmm_value)
                MOVSS([r_y], xmm_value)

                SUB(r_length, 1)
                JNZ(loop.begin)

            RETURN()

        code = function.format()
        ref_code = """
void square(float const* x, float* y, size_t length)
    LOAD.ARGUMENT gp64-vreg<1>, float const* x
    LOAD.ARGUMENT gp64-vreg<2>, float* y
    LOAD.ARGUMENT gp64-vreg<3>, size_t length
loop.begin:
    MOVSS xmm-vreg<1>, [gp64-vreg<1>]
    MULSS xmm-vreg<1>, xmm-vreg<1>
    MOVSS [gp64-vreg<2>], xmm-vreg<1>
    SUB gp64-vreg<3>, 1
    JNZ loop.begin
    RETURN
"""
        assert equal_codes(code,
                           ref_code), "Unexpected Peach-Py code:\n" + code
Exemplo n.º 27
0
    def runTest(self):
        x = Argument(ptr(const_float_))
        y = Argument(ptr(float_))
        length = Argument(size_t)

        with Function("square", (x, y, length)) as function:
            r_x = GeneralPurposeRegister64()
            r_y = GeneralPurposeRegister64()
            r_length = GeneralPurposeRegister64()
            LOAD.ARGUMENT(r_x, x)
            LOAD.ARGUMENT(r_y, y)
            LOAD.ARGUMENT(r_length, length)

            with Loop() as loop:
                xmm_value = XMMRegister()
                MOVSS(xmm_value, [r_x])
                MULSS(xmm_value, xmm_value)
                MOVSS([r_y], xmm_value)

                SUB(r_length, 1)
                JNZ(loop.begin)

            RETURN()

        code = function.format()
        ref_code = """
void square(float const* x, float* y, size_t length)
    LOAD.ARGUMENT gp64-vreg<1>, float const* x
    LOAD.ARGUMENT gp64-vreg<2>, float* y
    LOAD.ARGUMENT gp64-vreg<3>, size_t length
loop.begin:
    MOVSS xmm-vreg<1>, [gp64-vreg<1>]
    MULSS xmm-vreg<1>, xmm-vreg<1>
    MOVSS [gp64-vreg<2>], xmm-vreg<1>
    SUB gp64-vreg<3>, 1
    JNZ loop.begin
    RETURN
"""
        assert equal_codes(code, ref_code), "Unexpected Peach-Py code:\n" + code
Exemplo n.º 28
0
    def runTest(self):
        with Function("explicit_reg_input_2", ()) as function:
            g1 = GeneralPurposeRegister64()
            g2 = GeneralPurposeRegister64()
            MOV(g1, 0)
            MOV(g2, 0)
            MOV(rax, 0)
            MOV([g1], 0)
            MOV([g2], 0)
            RET()

        listing = function.finalize(abi.goasm_amd64_abi).format("go")
        ref_listing = """
// func explicit_reg_input_2()
TEXT \xc2\xB7explicit_reg_input_2(SB),4,$0
        MOVQ $0, BX
        MOVQ $0, CX
        MOVQ $0, AX
        MOVB $0, 0(BX)
        MOVB $0, 0(CX)
        RET
"""
        assert equal_codes(
            listing, ref_listing), "Unexpected PeachPy listing:\n" + listing
Exemplo n.º 29
0
    def runTest(self):
        x = Argument(ptr(const_float_))
        y = Argument(ptr(float_))
        length = Argument(size_t)

        with Function("square", (x, y, length)) as function:
            r_x = GeneralPurposeRegister64()
            r_y = GeneralPurposeRegister64()
            r_length = GeneralPurposeRegister64()
            LOAD.ARGUMENT(r_x, x)
            LOAD.ARGUMENT(r_y, y)
            LOAD.ARGUMENT(r_length, length)

            with Loop() as loop:
                xmm_value = XMMRegister()
                MOVSS(xmm_value, [r_x])
                MULSS(xmm_value, xmm_value)
                MOVSS([r_y], xmm_value)

                SUB(r_length, 1)
                JNZ(loop.begin)

            RETURN()

        listing = function.format_instructions()
        ref_listing = """
LOAD.ARGUMENT gp64-vreg<1>, float const* x
    In regs:
    Out regs:   gp64-vreg<1>
    Live regs:
    Avail regs:

LOAD.ARGUMENT gp64-vreg<2>, float* y
    In regs:
    Out regs:   gp64-vreg<2>
    Live regs:  gp64-vreg<1>
    Avail regs: gp64-vreg<1>

LOAD.ARGUMENT gp64-vreg<3>, size_t length
    In regs:
    Out regs:   gp64-vreg<3>
    Live regs:  gp64-vreg<1>, gp64-vreg<2>
    Avail regs: gp64-vreg<1>, gp64-vreg<2>

loop.begin:

MOVSS xmm-vreg<1>, [gp64-vreg<1>]
    In regs:    gp64-vreg<1>
    Out regs:   xmm-vreg<1>
    Live regs:  gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>
    Avail regs: gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, xmm-vreg<1>

MULSS xmm-vreg<1>, xmm-vreg<1>
    In regs:    xmm-vreg<1>
    Out regs:   xmm-vreg<1>
    Live regs:  gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, xmm-vreg<1>
    Avail regs: gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, xmm-vreg<1>

MOVSS [gp64-vreg<2>], xmm-vreg<1>
    In regs:    gp64-vreg<2>, xmm-vreg<1>
    Out regs:
    Live regs:  gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, xmm-vreg<1>
    Avail regs: gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, xmm-vreg<1>

SUB gp64-vreg<3>, 1
    In regs:    gp64-vreg<3>
    Out regs:   gp64-vreg<3>
    Live regs:  gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>
    Avail regs: gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, xmm-vreg<1>

JNZ loop.begin
    In regs:
    Out regs:
    Live regs:  gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>
    Avail regs: gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, xmm-vreg<1>

RETURN
    In regs:
    Out regs:
    Live regs:
    Avail regs: gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, xmm-vreg<1>
"""
        assert equal_codes(listing, ref_listing), "Unexpected Peach-Py code:\n" + listing
Exemplo n.º 30
0
    def runTest(self):
        vertex_edges = Argument(ptr(const_uint32_t))
        neighbors = Argument(ptr(const_uint32_t))
        input_queue = Argument(ptr(const_uint32_t))
        input_vertices = Argument(uint32_t)
        output_queue = Argument(ptr(uint32_t))
        levels = Argument(ptr(uint32_t))
        current_level = Argument(uint32_t)

        with Function("bfs",
                      (vertex_edges, neighbors, input_queue, input_vertices,
                       output_queue, levels, current_level)) as function:
            reg_vertex_edges = GeneralPurposeRegister64()
            LOAD.ARGUMENT(reg_vertex_edges, vertex_edges)

            reg_neighbors = GeneralPurposeRegister64()
            LOAD.ARGUMENT(reg_neighbors, neighbors)

            reg_input_queue = GeneralPurposeRegister64()
            LOAD.ARGUMENT(reg_input_queue, input_queue)

            reg_input_vertices = GeneralPurposeRegister64()
            LOAD.ARGUMENT(reg_input_vertices, input_vertices)

            reg_output_queue = GeneralPurposeRegister64()
            LOAD.ARGUMENT(reg_output_queue, output_queue)

            reg_levels = GeneralPurposeRegister64()
            LOAD.ARGUMENT(reg_levels, levels)

            reg_current_level = GeneralPurposeRegister32()
            LOAD.ARGUMENT(reg_current_level, current_level)

            reg_output_queue_start = GeneralPurposeRegister64()
            MOV(reg_output_queue_start, reg_output_queue)

            skip_neighbor = Label("skip_neighbor")
            per_edge_loop = Loop("per_edge_loop")

            with Loop() as per_vertex_loop:
                reg_current_vertex = GeneralPurposeRegister64()
                MOV(reg_current_vertex.as_dword, [reg_input_queue])
                ADD(reg_input_queue, 4)

                reg_start_edge = GeneralPurposeRegister64()
                MOV(reg_start_edge.as_dword, [reg_vertex_edges + reg_current_vertex * 4])

                reg_end_edge = GeneralPurposeRegister64()
                MOV(reg_end_edge.as_dword, [reg_vertex_edges + reg_current_vertex * 4 + 4])

                CMP(reg_start_edge, reg_end_edge)
                JE(per_edge_loop.end)

                reg_current_neighbor_pointer = GeneralPurposeRegister64()
                LEA(reg_current_neighbor_pointer, [reg_neighbors + reg_start_edge * 4])

                reg_end_neighbor_pointer = GeneralPurposeRegister64()
                LEA(reg_end_neighbor_pointer, [reg_neighbors + reg_end_edge * 4])

                with per_edge_loop:
                    reg_neighbor_vertex = GeneralPurposeRegister64()
                    MOV(reg_neighbor_vertex.as_dword, [reg_current_neighbor_pointer])
                    ADD(reg_current_neighbor_pointer, 4)

                    reg_neighbor_level = GeneralPurposeRegister32()
                    MOV(reg_neighbor_level, [reg_levels + reg_neighbor_vertex * 4])

                    CMP(reg_neighbor_level, reg_current_level)
                    JBE(skip_neighbor)

                    MOV([reg_output_queue], reg_neighbor_vertex.as_dword)
                    ADD(reg_output_queue, 4)

                    MOV([reg_levels + reg_neighbor_vertex * 4], reg_current_level)

                    LABEL(skip_neighbor)

                    CMP(reg_current_neighbor_pointer, reg_end_neighbor_pointer)
                    JNE(per_edge_loop.begin)

                SUB(reg_input_vertices, 1)
                JNE(per_vertex_loop.begin)

            SUB(reg_output_queue, reg_output_queue_start)
            SHR(reg_output_queue, 2)
            MOV(rax, reg_output_queue)

            RETURN()

        listing = function.format_instructions()
        ref_listing = """
LOAD.ARGUMENT gp64-vreg<1>, uint32_t const* vertex_edges
    In regs:
    Out regs:   gp64-vreg<1>
    Live regs:
    Avail regs:

LOAD.ARGUMENT gp64-vreg<2>, uint32_t const* neighbors
    In regs:
    Out regs:   gp64-vreg<2>
    Live regs:  gp64-vreg<1>
    Avail regs: gp64-vreg<1>

LOAD.ARGUMENT gp64-vreg<3>, uint32_t const* input_queue
    In regs:
    Out regs:   gp64-vreg<3>
    Live regs:  gp64-vreg<1>, gp64-vreg<2>
    Avail regs: gp64-vreg<1>, gp64-vreg<2>

LOAD.ARGUMENT gp64-vreg<4>, uint32_t input_vertices
    In regs:
    Out regs:   gp64-vreg<4>
    Live regs:  gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>
    Avail regs: gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>

LOAD.ARGUMENT gp64-vreg<5>, uint32_t* output_queue
    In regs:
    Out regs:   gp64-vreg<5>
    Live regs:  gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>
    Avail regs: gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>

LOAD.ARGUMENT gp64-vreg<6>, uint32_t* levels
    In regs:
    Out regs:   gp64-vreg<6>
    Live regs:  gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>
    Avail regs: gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>

LOAD.ARGUMENT gp32-vreg<7>, uint32_t current_level
    In regs:
    Out regs:   gp64-vreg<7>
    Live regs:  gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>
    Avail regs: gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>

MOV gp64-vreg<8>, gp64-vreg<5>
    In regs:    gp64-vreg<5>
    Out regs:   gp64-vreg<8>
    Live regs:  gp32-vreg<7>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>
    Avail regs: gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>

per_vertex_loop.begin:

MOV gp32-vreg<9>, [gp64-vreg<3>]
    In regs:    gp64-vreg<3>
    Out regs:   gp64-vreg<9>
    Live regs:  gp32-vreg<7>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

ADD gp64-vreg<3>, 4
    In regs:    gp64-vreg<3>
    Out regs:   gp64-vreg<3>
    Live regs:  gp32-vreg<7>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>, gp64-vreg<9>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

MOV gp32-vreg<10>, [gp64-vreg<1> + gp64-vreg<9>*4]
    In regs:    gp64-vreg<1>, gp64-vreg<9>
    Out regs:   gp64-vreg<10>
    Live regs:  gp32-vreg<7>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>, gp64-vreg<9>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

MOV gp32-vreg<11>, [gp64-vreg<1> + gp64-vreg<9>*4 + 4]
    In regs:    gp64-vreg<1>, gp64-vreg<9>
    Out regs:   gp64-vreg<11>
    Live regs:  gp32-vreg<7>, gp64-vreg<10>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>, gp64-vreg<9>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

CMP gp64-vreg<10>, gp64-vreg<11>
    In regs:    gp64-vreg<10>, gp64-vreg<11>
    Out regs:
    Live regs:  gp32-vreg<7>, gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

JE per_edge_loop.end
    In regs:
    Out regs:
    Live regs:  gp32-vreg<7>, gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

LEA gp64-vreg<12>, [gp64-vreg<2> + gp64-vreg<10>*4]
    In regs:    gp64-vreg<10>, gp64-vreg<2>
    Out regs:   gp64-vreg<12>
    Live regs:  gp32-vreg<7>, gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

LEA gp64-vreg<13>, [gp64-vreg<2> + gp64-vreg<11>*4]
    In regs:    gp64-vreg<11>, gp64-vreg<2>
    Out regs:   gp64-vreg<13>
    Live regs:  gp32-vreg<7>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

per_edge_loop.begin:

MOV gp32-vreg<14>, [gp64-vreg<12>]
    In regs:    gp64-vreg<12>
    Out regs:   gp64-vreg<14>
    Live regs:  gp32-vreg<7>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

ADD gp64-vreg<12>, 4
    In regs:    gp64-vreg<12>
    Out regs:   gp64-vreg<12>
    Live regs:  gp32-vreg<7>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

MOV gp32-vreg<15>, [gp64-vreg<6> + gp64-vreg<14>*4]
    In regs:    gp64-vreg<14>, gp64-vreg<6>
    Out regs:   gp64-vreg<15>
    Live regs:  gp32-vreg<7>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

CMP gp32-vreg<15>, gp32-vreg<7>
    In regs:    gp32-vreg<15>, gp32-vreg<7>
    Out regs:
    Live regs:  gp32-vreg<15>, gp32-vreg<7>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

JBE skip_neighbor
    In regs:
    Out regs:
    Live regs:  gp32-vreg<7>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

MOV [gp64-vreg<5>], gp32-vreg<14>
    In regs:    gp32-vreg<14>, gp64-vreg<5>
    Out regs:
    Live regs:  gp32-vreg<7>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

ADD gp64-vreg<5>, 4
    In regs:    gp64-vreg<5>
    Out regs:   gp64-vreg<5>
    Live regs:  gp32-vreg<7>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

MOV [gp64-vreg<6> + gp64-vreg<14>*4], gp32-vreg<7>
    In regs:    gp32-vreg<7>, gp64-vreg<14>, gp64-vreg<6>
    Out regs:
    Live regs:  gp32-vreg<7>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

skip_neighbor:

CMP gp64-vreg<12>, gp64-vreg<13>
    In regs:    gp64-vreg<12>, gp64-vreg<13>
    Out regs:
    Live regs:  gp32-vreg<7>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

JNE per_edge_loop.begin
    In regs:
    Out regs:
    Live regs:  gp32-vreg<7>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

per_edge_loop.end:

SUB gp64-vreg<4>, 1
    In regs:    gp64-vreg<4>
    Out regs:   gp64-vreg<4>
    Live regs:  gp32-vreg<7>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

JNE per_vertex_loop.begin
    In regs:
    Out regs:
    Live regs:  gp32-vreg<7>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

SUB gp64-vreg<5>, gp64-vreg<8>
    In regs:    gp64-vreg<5>, gp64-vreg<8>
    Out regs:   gp64-vreg<5>
    Live regs:  gp64-vreg<5>, gp64-vreg<8>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

SHR gp64-vreg<5>, 2
    In regs:    gp64-vreg<5>
    Out regs:   gp64-vreg<5>
    Live regs:  gp64-vreg<5>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

MOV rax, gp64-vreg<5>
    In regs:    gp64-vreg<5>
    Out regs:   rax
    Live regs:  gp64-vreg<5>
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>

RETURN
    In regs:
    Out regs:
    Live regs:
    Avail regs: gp64-vreg<10>, gp64-vreg<11>, gp64-vreg<12>, gp64-vreg<13>, gp64-vreg<14>, gp64-vreg<15>, gp64-vreg<1>, gp64-vreg<2>, gp64-vreg<3>, gp64-vreg<4>, gp64-vreg<5>, gp64-vreg<6>, gp64-vreg<7>, gp64-vreg<8>, gp64-vreg<9>, rax
"""
        assert equal_codes(listing, ref_listing), "Unexpected Peach-Py code:\n" + listing