# How does the BRGE instruction work in assembly? Why is this code not functioning properly?

.cseg
ldi r16, 0x01
ldi r17, 0x01

add r16,r17
cpi r16,0xFF
brge greater
jmp less

greater:inc r1
jmp done

less:   jmp done

done: jmp done


I'm writing some assembly code in AVR studio 4, and I'm not sure how the branch works. When I compare r16 (which should have the value 2) with the value 255 in hex, the branch brge (greater than or equal to) jumps to the "greater" label, which then increments r1 to indicate that the value was greater than 255. This doesn't make sense as 2 is not greater than 255. What am I doing wrong?

• BRGE is a signed instruction, 0xFF is actually -1 Commented Jan 25, 2016 at 23:43
• I see. So what would the signed hex value of 255 be? Commented Jan 25, 2016 at 23:44
• It does not have one as it does not fit in an 8 bit character, since it requires 9 bits to represent, HOWEVER the equivalent unsigned instruction is brsh - see also wiki on two's compliment Commented Jan 25, 2016 at 23:47
• Thanks for your help! I'm just starting out and this is quite confusing to me. Commented Jan 25, 2016 at 23:48

## 1 Answer

BRGE is a signed branch instruction, meaning it interprets the arguments as signed numbers represented in Two's Complement format. For 8 bit numbers the values of twos complement range from -128 (1000 0000) to +127 (0111 1111)

In order for your code to work as intended with hex literals you need to use the unsigned branch comparison operator BRSH, which does an unsigned comparison.

For all available branch instructions you can peruse this list on the atmel website.

Most branch instruction will work by checking a status flag that is set by a previous operations, BRGE and BRSH check the signed flag and carry flag respectively. The convenience of two's complement signed numbers (that the architecture exploits) is that arithmetic operations are performed identically to unsigned numbers - so it only comes down to how you interpret the operands and results. The cpi command is agnostic to signed or unsigned numbers and will set both flags for the compare. The branch instruction will then check one or the other