I need to reverse an YUV image with each byte in LSB instead of MSB. I have read Best Algorithm for Bit Reversal ( from MSB->LSB to LSB->MSB) in C but I would like to do something that is ARM-optimized.
int8 *image;
for(i = 0; i < size; i++) {
image[i] = reversebit8(image[i]); //Use the lookup mechanism
}
As I control the image format (two-byte YUYV or any permutation), I would be OK to reverse 16 bits:
int16 *image;
for(i = 0; i < size / 2; i++) {
image[i] = reversebit16(image[i]);
}
Image goes from YUYV LSB to UYVY MSB. Or even in 32 bits:
int32 *image;
for(i = 0; i < size / 4; i++) {
image[i] = reversebit32(image[i]);
}
Image goes from YUYV LSB to VYUY MSB.
Question: How can I do that in an optimized way for ARM? Neon is good too.
I think that those instructions http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.kui0100a/armasm_cihjgdid.htm could be useful.
The ARM RBIT
instruction does what you want. Write a loop that calls this on every aligned 4-byte value.
A8.6.134 RBIT
Reverse Bits reverses the bit order in a 32-bit register. Encoding T1 ARMv6T2, ARMv7
RBIT<c> <Rd>,<Rm>
if ConditionPassed() then
EncodingSpecificOperations(); bits(32) result;
for i = 0 to 31 do
result<31-i> = R[m]<i>;
R[d] = result;
As I mentioned it in my question, those ARM instructions (http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.kui0100a/armasm_cihjgdid.htm) can do the trick:
int32 *image;
for (i = 0; i < size / 4; h++) {
asm("rbit %1,%0" : "=r" (image[i]) : "r" (image[i]));
asm("rev %1,%0" : "=r" (image[i]) : "r" (image[i]));
}
rbit reverses the 32 bits, bit by bit. rev reverses the 32 bits, byte by byte. In fine, each byte is reversed independently. I'm still wondering if there is a better syntax or a better way to do this.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With