Skip to content

Bytecode

Jon Feldman edited this page Jun 6, 2016 · 10 revisions

Instructions are one byte and have a variable number of bytes afterwards.

Note that this file describes the instruction set AS THE VM INTERPRETS IT, e.g. not as you'd write it for the assembler. Notable, the size operand is normally automatically calculated when it refers to data afterwards.

Any integers of greater than one byte are not re-ordered to fit endianness. If you specify 0001 as a value, the vm will read this as: uint16_t val = *((uint16_t*){0x00, 0x01}) Be aware of this.

Unless otherwise noted, if an instruction doesn't succeed, it will abort the VM. When booting up, it'll noisily throw an error. In loader, it will trigger svcBreak.

nop

  • 1 byte
  • Opcode 0x00 Does nothing. Not actually treated as an instruction, rather just skipped over. This is mainly just for compatibility.

rel mode

  • 2 bytes
  • Opcode 0x01
  • Chooses memory/patch relativity.
  • mode : The location and size to operate in.
    • Boot only:
      • 0x0: NATIVE_FIRM (whole size)
      • 0x1: AGB_FIRM (whole size)
      • 0x2: TWL_FIRM (whole size)
      • 0x3: Native Proc9 ExeFS (Default during boot)
      • 0x4: AGB Proc9 ExeFS
      • 0x5: TWL Proc9 ExeFS
      • 0x6: Native Section 0
      • 0x7: Native Section 1
      • 0x8: Native Section 2
      • 0x9: Native Section 3
      • 0xA: AGB Section 0
      • 0xB: AGB Section 1
      • 0xC: AGB Section 2
      • 0xD: AGB Section 3
      • 0xE: TWL Section 0
      • 0xF: TWL Section 1
      • 0x10: TWL Section 2
      • 0x11: TWL Section 3
    • Loader only:
      • 0x12: ExeFs .text segment (Default with loader)
      • 0x13: ExeFs .data segment
      • 0x14: ExeFs .ro segment

find size pattern...

  • 2 + size bytes
  • opcode 0x02
  • Finds a pattern in memory. On success, operations will be performed relative to the beginning of the found pattern.
  • size
    • 1 byte
    • How many bytes the pattern is.
  • pattern
    • size bytes
    • The data to find

back count

  • 2 bytes
  • opcode 0x03
  • Moves back count bytes from current position.
  • count
    • 1 byte
    • How many bytes to rewind.

fwd

  • 2 bytes
  • opcode 0x04
  • Moves forward count bytes from current position.
  • count
    • 1 byte
    • How many bytes to rewind.

set size data...

  • 2 + size bytes
  • opcode 0x05
  • Copies the bytes in to the current location pointed to, and increments the current location by bytes copied.
  • size
    • 1 byte
    • How many bytes to copy.
  • data
    • size bytes
    • Data to copy.

test size data...

  • 2 + size bytes
  • opcode 0x06
  • Tests if the current location's data is equivalent to data, and sets flags accordingly.
  • size
    • 1 byte
    • Size of data to test against.
  • data
    • size bytes
    • Pattern to test.

jmp offset

  • 3 bytes
  • opcode 0x07
  • Unconditionally jumps to absolute offset instruction within the bytecode, and resumes execution from there. Note that the assembler should be passed the number of instruction, not the offset, and will automatically calculate the offset needed.
  • offset
    • 2 bytes
    • Offset to jump to.

rewind

  • 1 byte
  • opcode 0x08
  • Resets the location to the beginning of the space we're working off.

and size data...

  • 2 + size bytes
  • opcode 0x09
  • Performs an AND operation bitwise using data as a mask.
  • size
    • 1 byte
    • Size of data
  • data
    • size bytes
    • Data to bitwise and with relative data.

or size data...

  • 2 + size bytes
  • opcode 0x0A
  • Performs an OR operation bitwise using data as a mask.
  • size
    • 1 byte
    • Size of data
  • data
    • size bytes
    • Data to bitwise or with relative data.

xor size data...

  • 2 + size bytes
  • opcode 0x0B
  • Performs an XOR operation bitwise using data as a mask.
  • size
    • 1 byte
    • Size of data
  • data
    • size bytes
    • Data to bitwise xor with relative data.

not size

  • 2 bytes
  • opcode 0x0C
  • Performs an NOT operation on data of size bytes.
  • size
    • 1 byte
    • Size to perform bitwise not on

ver version

  • 3 bytes
  • opcode 0x0D
  • Acts like test - compares the uint16_t version of a software title against input version. Sets flags accordingly.
  • version
    • 2 bytes
    • uint16_t to test version against

clf

  • 1 byte
  • opcode 0x0E
  • Clears flags set by test/ver.

jmpeq offset

  • 3 bytes
  • opcode 0x17
  • Jumps if equal flag is set to an absolute offset within the bytecode, and resumes execution from there. Note that the assembler should be passed the number of instruction, not the offset, and will automatically calculate the offset needed.
  • offset
    • 2 bytes
    • Offset to jump to.

jmpne offset

  • 3 bytes
  • opcode 0x27
  • Jumps if equal flag is not set to an absolute offset within the bytecode, and resumes execution from there. Note that the assembler should be passed the number of instruction, not the offset, and will automatically calculate the offset needed.
  • offset
    • 2 bytes
    • Offset to jump to.

jmplt offset

  • 3 bytes
  • opcode 0x37
  • Jumps if less than flag is set to an absolute offset within the bytecode, and resumes execution from there. Note that the assembler should be passed the number of instruction, not the offset, and will automatically calculate the offset needed.
  • offset
    • 2 bytes
    • Offset to jump to.

jmpgt offset

  • 3 bytes
  • opcode 0x47
  • Jumps if greater than flag is set to an absolute offset within the bytecode, and resumes execution from there. Note that the assembler should be passed the number of instruction, not the offset, and will automatically calculate the offset needed.
  • offset
    • 2 bytes
    • Offset to jump to.

jmple offset

  • 3 bytes
  • opcode 0x57
  • Jumps if less than or equal flag is set, to an absolute offset within the bytecode, and resumes execution from there. Note that the assembler should be passed the number of instruction, not the offset, and will automatically calculate the offset needed.
  • offset
    • 2 bytes
    • Offset to jump to.

jmpge offset

  • 3 bytes
  • opcode 0x67
  • Jumps if greater than or equal flag is set, to an absolute offset within the bytecode, and resumes execution from there. Note that the assembler should be passed the number of instruction, not the offset, and will automatically calculate the offset needed.
  • offset
    • 2 bytes
    • Offset to jump to.

next

  • 1 byte
  • Opcode 0xFF
  • Resets state to default, and changes the base of code to the next instruction. This opcode is not meant to be used directly - it's emitted when generating caches.

Clone this wiki locally