Mika Vatanen
Mika Vatanen

Reputation: 4037

How to set the instruction size (16 bit or 32 bit) for a function on ARM thumb?

ARM has multiple instruction sets: A32 (32 bit long instructions) and mixed-length T32 (either 32 bit or 16 bit long instructions). T32 was called Thumb before ArmV8.

While 16 bit instructions reduce code size, 32 bit instructions can have higher performance.

According to https://developer.arm.com/documentation/dui0473/m/dom1359731139853 and https://developer.arm.com/architectures/instruction-sets, it would be possible to define the used instruction length separately for different sections of code, when using mixed length instructions.

Some instructions use the least significant bit of the address to determine whether the code being branched to is Thumb code or ARM code.

The T32 instruction set was introduced as a supplementary set of 16-bit instructions that supported improved code density for user code. Over time, T32 evolved into a 16-bit and 32-bit mixed-length instruction set. As a result, the compiler can balance performance and code size trade-off in a single instruction set.

As I understand, the default in Rust comes from the target (e.g. thumbv7m-none-eabi = T32), but how to force the used instruction length on per-function basis in Rust?

Here's an answer on how to enable it on C: https://stackoverflow.com/a/52692271/499839

Upvotes: 0

Views: 890

Answers (1)

Chayim Friedman
Chayim Friedman

Reputation: 71605

Since Rust 1.67.0, this can be done with the #[instruction_set] attribute.

#[instruction_set(arm::t32)]
pub unsafe fn t32() { ... }

#[instruction_set(arm::a32)]
pub unsafe fn a32() { ... }

Upvotes: 1

Related Questions