CS 352 Lecture 27 – If * 3
Dear students,
Let’s do another Program This:
Translate the following code to ARM assembly:if n >= 0 && n <= 9 print 'digit'
A straightforward implementation might take this approach:
mov r1, #0 mov r2, #0 // Let's assume n is in r0. cmp r0, #0 movgt r1, #1 cmp r0, #9 movlt r2, #1 and r3, r1, r2 cmp r3, #1 bne after then: ldr r0, =message bl printf after: ...
We put conditional predicates on the mov
instructions. If both r1
and r2
get set, then we print.
The problem with this is that we have violated the short-circuiting semantics of the &&
operator. If the first clause is false, we don’t even consider the second. Short-circuiting is important, and a lot of code relies on it. Like this snippet:
str.length() > 0 && str.charAt(0) == '<'
We should not touch any part of the second clause unless we know the first is true. We can implement this like so:
cmp r0, #0 blt after cmp r9, #9 bgt after then: ldr r0, =message bl printf after: ...
One interesting takeaway from this example is that the &&
operation from our high-level language does not actually translate into an and
instruction. Many high-level constructs become something completely different at the low-level, defying one’s intuition!
If we have time, we’ll do a comparison between conditional branching and simpler predicated instructions. Here’s a program that generates a bunch of random numbers and then branches to an odd or even count instruction:
.text .global main main: push {lr} mov r0, #133 bl srand mov r4, #0 // i mov r7, #0 // count of odds mov r8, #0 // count of evens b check loop: bl rand and r0, r0, #1 cmp r0, #1 beq odd even: add r8, r8, #1 b after odd: add r7, r7, #1 after: add r4, r4, #1 check: ldr r6, =n ldr r6, [r6] cmp r4, r6 bne loop mov r0, r5 pop {lr} mov pc, lr .data n: .word 100000000
We’ll rewrite this without the branches and time both versions using perf
from the linux-tools
package:
perf_4.4 stat --repeat=2 -e cpu-clock ./myprogram
We’ll close with one or two array processing examples:
- sum up an array of numbers
echo
See you next class!
P.S. It’s Haiku Friday!
pc
pinpoints code
Pounces cat-like, like popcorn
Propels computing
P.P.S. Here’s the code we wrote together…
in_range.c
int n = 17; void in_range() { if (n >= 0 && n <= 9) { printf("in range"); } }
sum.s
.text .global main main: push {lr} ldr r0, =numbers // r0 = &numbers mov r1, #0 // r1 = 0 b check loop: add r1, r1, r2 // r1 += r2 add r0, r0, #4 // r0 += 4 check: ldr r2, [r0] // r2 = *r0 cmp r2, #0 bne loop ldr r0, =message bl printf pop {lr} mov pc, lr .data numbers: .word 1, 2, 3, 4, 5, 6, 7, 8, 9, 0 message: .asciz "The sum is %d!\n"