SimplifyC++ Article
x86-64 Machine Code Encoding: Little-endian Conversion Walkthroughs
x86-64 Machine Code Encoding: Little-endian Conversion Walkthroughs
The x86-64 architecture uses little-endian byte order for representing multi-byte values such as immediate constants, displacement fields, and memory contents. Understanding how to correctly convert multi-byte numerical values into little-endian format is essential for accurate machine code encoding and assembly programming.
This section walks through examples demonstrating the process of converting multi-byte integers (both immediate values and displacements) from their natural numeric form into the little-endian byte sequence used in x86-64 machine code.
1. What Is Little-endian?
In little-endian encoding, the least significant byte (LSB) is stored at the lowest memory address, and the most significant byte (MSB) is stored at the highest.
This contrasts with big-endian, where the MSB is stored first.
The x86-64 ISA follows little-endian convention universally for all multi-byte values in instructions and memory.
2. General Conversion Rules
Write the multi-byte integer in hexadecimal.
Split into bytes, grouping two hex digits per byte (one byte = 8 bits).
Reverse the order of these bytes, placing the least significant byte first.
3. Walkthrough Examples
Example 1: Immediate 32-bit value 0x12345678
Step-by-step conversion:
| Hexadecimal Value | Split Bytes | Little-endian Order |
|---|---|---|
0x12345678 | 12 34 56 78 | 78 56 34 12 |
Machine code bytes: 78 56 34 12
Example 2: Immediate 64-bit value 0x0123456789ABCDEF
Step-by-step conversion:
| Hexadecimal Value | Split Bytes | Little-endian Order |
|---|---|---|
0x0123456789ABCDEF | 01 23 45 67 89 AB CD EF | EF CD AB 89 67 45 23 01 |
Machine code bytes: EF CD AB 89 67 45 23 01
Example 3: 8-bit signed displacement -16 (decimal)
Decimal -16 corresponds to hex
0xF0(two's complement 8-bit)
Machine code byte: F0
Example 4: 32-bit signed displacement -256 (decimal)
Decimal -256 corresponds to hex
0xFFFFFF00(two's complement 32-bit)Bytes split:
FF FF FF 00Little-endian order:
00 FF FF FF
Machine code bytes: 00 FF FF FF
Example 5: Immediate 16-bit value 0xABCD
| Hexadecimal Value | Split Bytes | Little-endian Order |
|---|---|---|
0xABCD | AB CD | CD AB |
Machine code bytes: CD AB
4. Application to Instruction Encoding
When encoding instructions with immediate or displacement fields, the assembler converts numerical values to little-endian byte order before inserting them into the machine code stream.
Instruction Example: MOV EAX, 0x12345678
Opcode:
B8+ register code (for EAX register, justB8)Immediate:
0x12345678→ bytes78 56 34 12
Final Encoding: B8 78 56 34 12
Instruction Example: JMP with 32-bit relative displacement +0x10
Opcode:
E9Displacement:
0x10→ single byte10 00 00 00in little-endian
Final Encoding: E9 10 00 00 00
5. Common Pitfalls and Considerations
Always convert multi-byte values to little-endian, regardless of source format.
Negative numbers require two's complement representation before conversion.
The size of immediate or displacement fields must match the instruction’s expected operand size (e.g., 8, 16, 32, or 64 bits).
Misalignment in byte order results in incorrect instructions and runtime errors.
6. Summary
Little-endian conversion is a fundamental step in translating assembly language instructions into correct x86-64 machine code. Mastery of these conversions ensures the assembler produces accurate and functional binary instructions. The conversion procedure is straightforward: break the numeric values into bytes and reverse their order before encoding.