Skip to content

AArch64: MOV (to general): vess is not set #1452

@nkaretnikov

Description

@nkaretnikov

This is with Capstone (4.0.1) (Python bindings).

MOV (to general), an alias of UMOV, sets the vector element size specifier (vess) to ARM64_VESS_INVALID while the other UMOV variants set it properly.

Maybe it's intentional as the size can be determined based on the destination operand, but it'd be nice to have consistent behavior.

Code:

#!/usr/bin/env python3

from capstone import *
from capstone.arm64_const import *
from keystone import *
import struct

def parse_vess(vess):
  if vess == ARM64_VESS_INVALID:
    return "invalid"
  elif vess == ARM64_VESS_B:
    return "b"
  elif vess == ARM64_VESS_H:
    return "h"
  elif vess == ARM64_VESS_S:
    return "s"
  elif vess == ARM64_VESS_D:
    return "d"
  else:
    print(f"Unsupported vector element size specifier: '{vess}'")
    exit(1)

def disasm(code):
    c = Cs(CS_ARCH_ARM64, CS_MODE_ARM)
    c.detail = True
    for insn in c.disasm(code, 0):  # addr = 0
        assert len(insn.operands) == 2  # XXX: hardcoded
        op = insn.operands[1]
        print(f'vector_index: {op.vector_index}')
        print(f'vess: {parse_vess(op.vess)}')
        i = struct.unpack("<I", insn.bytes)[0]
        print(f"dis: {i:032b} {i:08x} {insn.mnemonic} {insn.op_str}")

def asm(code):
  k = Ks(KS_ARCH_ARM64, 0)
  enc, cnt = k.asm(code)
  i = struct.unpack("<I", bytes(enc))[0]
  print(f"asm: {i:032b} {i:08x} {code}")

def main():
    asm('umov w0, v1.s[1]')
    asm('mov  w0, v1.s[1]')
    disasm(b'\x20\x3c\x0c\x0e')
    print()

    asm('umov x0, v1.d[1]')
    asm('mov  x0, v1.d[1]')
    disasm(b'\x20\x3c\x18\x4e')
    print()

    asm('umov w0, v1.b[1]')
    disasm(b'\x20\x3c\x03\x0e')
    print()

    asm('umov w0, v1.h[1]')
    disasm(b'\x20\x3c\x06\x0e')
    print()

if __name__ == "__main__":
    main()

Output:

asm: 00001110000011000011110000100000 0e0c3c20 umov w0, v1.s[1]
asm: 00001110000011000011110000100000 0e0c3c20 mov  w0, v1.s[1]
vector_index: 1
vess: invalid
dis: 00001110000011000011110000100000 0e0c3c20 mov w0, v1.s[1]

asm: 01001110000110000011110000100000 4e183c20 umov x0, v1.d[1]
asm: 01001110000110000011110000100000 4e183c20 mov  x0, v1.d[1]
vector_index: 1
vess: invalid
dis: 01001110000110000011110000100000 4e183c20 mov x0, v1.d[1]

asm: 00001110000000110011110000100000 0e033c20 umov w0, v1.b[1]
vector_index: 1
vess: b
dis: 00001110000000110011110000100000 0e033c20 umov w0, v1.b[1]

asm: 00001110000001100011110000100000 0e063c20 umov w0, v1.h[1]
vector_index: 1
vess: h
dis: 00001110000001100011110000100000 0e063c20 umov w0, v1.h[1]

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions