DEV Community

Gealber Morales
Gealber Morales

Posted on • Originally published at gealber.com

Challenge RE #13

Let's do another re challenge, if you've been reading my recent posts you know that I'm solving the challenges from challenges.re. This time, I'm going to analyze the short but not less interesting #13. Let's start.

Analysis

This time we don't have a binary file, instead we have a quite short assembly code. Using 128-bit registers, xmm0 and xmm1. For this program we have three arguments, rsi, rdx and rdi. The first two contains unsigned integers, given the way we are accessing them we can infer they are being passed on 2 arrays.

Here is the code

f:
    xor rax, rax
.L4:
    movdqu  xmm0, XMMWORD PTR [rsi+rax]
    movdqu  xmm1, XMMWORD PTR [rdx+rax]
    pmaxub  xmm0, xmm1 ;; returns maximum of both
    movdqu  XMMWORD PTR [rdi+rax], xmm0
    add rax, 16
    cmp rax, 1024
    jne .L4
    rep ret
Enter fullscreen mode Exit fullscreen mode

Immediately we can notice that we have a loop, and that the iteration will end when rax will be 1024. On each iteration we increase rax by 16, so we will iterate 64 times. Now what's done on these iterations?

Actually quite simple, we are comparing each elements of the array, the one in rsi and rdx, and selecting the maximum value between the two to be saved in rdi. Given that rdi it's a 64 bit register and we iterate exactly 64 times, we will fill rdi with these maximum elements.

With this, we can already give our formal description of the program:

Formal description

Given two arrays, a and b, with unsigned integers, we return and array arr where for each i = 0, ..., 64, we have arr[i] = max(a[i], b[i]).

That's it!!

Top comments (0)