summary refs log tree commit diff homepage
path: root/day01.asm
blob: fd31fce089eb8abb24b543a1e201a9f0fb092cb7 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
%include "sys.asm"
%include "lib.asm"

%define rPosX r8
%define rPosY r9
%define rDirX r10
%define rDirY r11

global _start
_start:
  sub rsp, 4096
  syscall SYS_READ, FD_STDIN, rsp, 4096
  mov rdi, rax ;; Length.
  xor rcx, rcx ;; Index.

  xor rPosX, rPosX
  xor rPosY, rPosY
  xor rDirX, rDirX
  mov rDirY, -1 ;; North.

  .loopTurn:
    cmp byte [rsp + rcx], 'L'
    jne .right
    .left: ;; L(dx, dy) = (dy, -dx)
      neg rDirX
      jmp .swap
    .right: ;; R(dx, dy) = (-dy, dx)
      neg rDirY
    .swap:
    xchg rDirX, rDirY

    xor rax, rax
    .loopDigit:
      inc rcx
      movzx rdx, byte [rsp + rcx]
      cmp dl, '0'
      jb .breakDigit

      ;; rax = rax * 10 + rdx - '0'
      shl rax, 1
      lea rax, [rax + rax * 4 - '0']
      add rax, rdx
    jmp .loopDigit
    .breakDigit:
    add rcx, 2 ;; Discard comma and space.

    mov rdx, rax
    imul rdx, rDirX
    add rPosX, rdx

    mov rdx, rax
    imul rdx, rDirY
    add rPosY, rdx

  cmp rcx, rdi
  jb .loopTurn

  ;; abs(x) = (x ^ (x >> 63)) - (x >> 63)
  mov rax, rPosX
  sar rax, 63
  xor rPosX, rax
  sub rPosX, rax

  mov rax, rPosY
  sar rax, 63
  xor rPosY, rax
  sub rPosY, rax

  lea rdi, [rPosX + rPosY]
  call hex32
  push rax
  syscall SYS_WRITE, FD_STDOUT, rsp, 8

  xor rax, rax
syscall SYS_EXIT, rax