Search code examples
assemblyarmbit-fields

How to split a 32-bit integer to two 16-bit half-words


How can I divide a 32-bit hexadecimal to two 16-bit hexadecimals and store them so the lower one is inside the first register and higher one is inside the second register.

For example I have a data such as 0xB0B0A0A0 and I want to extract 0xA0A0 to R0 and 0xB0B0 to R1 in my code.


Solution

  • On sufficiently modern ARM chips, you can use the uxth (unsigned extend halfword) instruction for this purpose:

    @ assuming R2 = 0xb0b0a0a0
    uxth r0, r2, ror #0    @ r0 = 0x0000a0a0
    uxth r1, r2, ror #16   @ r1 = 0x0000b0b0
    

    Refer to the ARMv7-M ARM Architecture Reference Manual for details.

    If programming for ARMv6-M targets or if optimising for code-size on Thumb, the second instruction can be replaced with an lsrs to reduce code size:

    lsrs r1, r2, #16       @ r1 = 0x0000b0b0
    

    But note that this causes NZCV to be modified.