279 lines
3.7 KiB
ArmAsm
279 lines
3.7 KiB
ArmAsm
%define EXPANSION 1000000-1
|
|
|
|
global _start
|
|
[bits 32]
|
|
[section .text]
|
|
|
|
%include "utils.s"
|
|
|
|
_start:
|
|
|
|
; find line length
|
|
mov edi, file
|
|
mov ecx, file.over - file
|
|
mov al, 10 ; \n
|
|
repne scasb
|
|
mov eax, edi
|
|
sub eax, file
|
|
mov [line_len], eax
|
|
call print_dec
|
|
call newline
|
|
|
|
mov eax, -1
|
|
mov ecx, 512
|
|
mov edi, empty_rows
|
|
rep stosd
|
|
mov eax, -1
|
|
mov ecx, 512*2
|
|
mov edi, stars
|
|
rep stosd
|
|
|
|
; find empty rows
|
|
xor ebx, ebx
|
|
mov ebp, empty_rows
|
|
check_rows:
|
|
mov eax, [line_len]
|
|
mov ecx, eax
|
|
mul ebx
|
|
lea edi, [eax+file]
|
|
mov esi, edi
|
|
add esi, ecx
|
|
mov al, '.'
|
|
repe scasb
|
|
mov eax, esi
|
|
cmp edi, esi
|
|
jne .not_empty
|
|
.empty:
|
|
mov [ebp], ebx
|
|
add ebp, 4
|
|
.not_empty:
|
|
.cont:
|
|
inc ebx
|
|
cmp eax, file.over
|
|
jb check_rows
|
|
|
|
; find empty cols
|
|
xor ebx, ebx
|
|
mov ebp, empty_cols
|
|
check_cols:
|
|
lea edi, [file+ebx]
|
|
.l:
|
|
cmp edi, file.over
|
|
jae .empty
|
|
cmp byte [edi], '.'
|
|
jne .not_empty
|
|
add edi, [line_len]
|
|
jmp .l
|
|
.empty:
|
|
mov [ebp], ebx
|
|
add ebp, 4
|
|
.not_empty:
|
|
inc ebx
|
|
cmp ebx, [line_len]
|
|
jb check_cols
|
|
|
|
print_empty_rows:
|
|
mov esi, empty_str
|
|
mov ecx, 6
|
|
call print_string
|
|
mov esi, empty_rows
|
|
xor eax, eax
|
|
.l:
|
|
lodsd
|
|
cmp eax, -1
|
|
je .done
|
|
call space
|
|
call print_dec
|
|
jmp .l
|
|
.done:
|
|
call newline
|
|
|
|
print_empty_cols:
|
|
mov esi, empty_str
|
|
mov ecx, 6
|
|
call print_string
|
|
mov esi, empty_cols
|
|
xor eax, eax
|
|
.l:
|
|
lodsd
|
|
cmp eax, -1
|
|
je .done
|
|
call space
|
|
call print_dec
|
|
jmp .l
|
|
.done:
|
|
call newline
|
|
|
|
; find #s
|
|
xor ebx, ebx ; row
|
|
mov ebp, stars
|
|
find_stars:
|
|
mov eax, ebx
|
|
mul dword [line_len]
|
|
lea edi, [file+eax] ; row ptr
|
|
cmp edi, file.over
|
|
jae .done
|
|
xor ecx, ecx ; col
|
|
.for_cols:
|
|
cmp byte [edi+ecx], '#'
|
|
jne .for_cols_cont
|
|
mov eax, ebx
|
|
call print_dec
|
|
call space
|
|
mov [ebp], ebx ; row
|
|
mov eax, ecx
|
|
call print_dec
|
|
call newline
|
|
mov [ebp+4], ecx ; col
|
|
add ebp, 8
|
|
.for_cols_cont:
|
|
inc ecx
|
|
cmp ecx, [line_len]
|
|
jb .for_cols
|
|
inc ebx
|
|
jmp find_stars
|
|
.done:
|
|
call newline
|
|
|
|
; calc adjustments
|
|
calc_adj:
|
|
xor ecx, ecx
|
|
.fill:
|
|
mov [adj_rows+ecx*4], ecx
|
|
mov [adj_cols+ecx*4], ecx
|
|
inc ecx
|
|
cmp ecx, 256
|
|
jb .fill
|
|
; do rows
|
|
mov esi, empty_rows
|
|
.rows:
|
|
lodsd
|
|
cmp eax, -1
|
|
je .rows_done
|
|
inc eax
|
|
.add_to_rows:
|
|
add dword [adj_rows+eax*4], EXPANSION
|
|
inc eax
|
|
cmp eax, 256
|
|
jb .add_to_rows
|
|
jmp .rows
|
|
.rows_done:
|
|
; do cols
|
|
mov esi, empty_cols
|
|
.cols:
|
|
lodsd
|
|
cmp eax, -1
|
|
je .cols_done
|
|
inc eax
|
|
.add_to_cols:
|
|
add dword [adj_cols+eax*4], EXPANSION
|
|
inc eax
|
|
cmp eax, 256
|
|
jb .add_to_cols
|
|
jmp .cols
|
|
.cols_done:
|
|
|
|
; apply adjustments
|
|
apply_adj:
|
|
xor eax, eax
|
|
mov esi, stars
|
|
mov edi, stars
|
|
.l:
|
|
lodsd ; row
|
|
cmp eax, -1
|
|
je .done
|
|
mov eax, [adj_rows+eax*4]
|
|
stosd
|
|
lodsd ; col
|
|
mov eax, [adj_cols+eax*4]
|
|
stosd
|
|
jmp .l
|
|
.done:
|
|
|
|
; print stars
|
|
print_stars:
|
|
mov esi, stars
|
|
xor eax, eax
|
|
.l:
|
|
lodsd
|
|
cmp eax, -1
|
|
je .done
|
|
call print_dec
|
|
call space
|
|
lodsd
|
|
call print_dec
|
|
call newline
|
|
jmp .l
|
|
.done:
|
|
call newline
|
|
|
|
; calc distances
|
|
sub esp, 4
|
|
mov ebp, stars
|
|
calc_dist:
|
|
lea esi, [ebp+8]
|
|
mov ecx, [ebp] ; row
|
|
mov edx, [ebp+4] ; col
|
|
mov [esp], ebp
|
|
xor edi, edi ; running sum low
|
|
xor ebp, ebp ; running sum high
|
|
.to_next:
|
|
lodsd ; row
|
|
cmp eax, -1
|
|
je .all_added
|
|
sub eax, ecx
|
|
; abs (m := n>>31, n := (n+m)^m)
|
|
mov ebx, eax
|
|
sar ebx, 31
|
|
add eax, ebx
|
|
xor eax, ebx
|
|
; add to total
|
|
add edi, eax
|
|
adc ebp, 0
|
|
lodsd ; col
|
|
sub eax, edx
|
|
mov ebx, eax
|
|
sar ebx, 31
|
|
add eax, ebx
|
|
xor eax, ebx
|
|
; add to total
|
|
add edi, eax
|
|
adc ebp, 0
|
|
jmp .to_next
|
|
.all_added:
|
|
add dword [final_value], edi
|
|
adc dword [final_value_high], ebp
|
|
calc_dist_cont:
|
|
mov ebp, [esp]
|
|
add ebp, 8
|
|
cmp dword [ebp], -1
|
|
jne calc_dist
|
|
calc_dist_end:
|
|
add esp, 4
|
|
|
|
game_over:
|
|
; answer is penultimate + (ultimate * 2^32)
|
|
mov eax, [final_value]
|
|
call print_dec
|
|
call newline
|
|
mov eax, [final_value_high]
|
|
call print_dec
|
|
call newline
|
|
jmp exit
|
|
|
|
[section .data]
|
|
line_len: dd 0
|
|
final_value: dd 0
|
|
final_value_high: dd 0
|
|
file: incbin "input"
|
|
.over:
|
|
empty_str: db "Empty:"
|
|
not_empty_str: db "Not Empty:"
|
|
|
|
[section .bss]
|
|
empty_rows: resd 256
|
|
empty_cols: resd 256
|
|
adj_rows: resd 256
|
|
adj_cols: resd 256
|
|
stars: resd 512*2
|