%define BUFF_LIM 32768 ;%define GRID_X 10 ;%define GRID_Y 10 %define GRID_X 140 %define GRID_Y 140 global _start [bits 32] [section .text] %include "utils.s" _start: mov ebx, filename call open_file mov ecx, read_buff mov edx, BUFF_LIM call read_file add eax, read_buff mov [file_lim], eax ; 1. read file into array, ; padding edges by 1 read_to_array: mov esi, read_buff ; first line padded by . mov edi, array mov ecx, (GRID_X+2) mov al, '.' rep stosb mov ecx, GRID_Y ; line count .read_lines: ; 1 char pad before line mov al, '.' stosb push ecx .read_chars: mov ecx, GRID_X ; line len (discluding newline) rep movsb ; copy line inc esi ; skip newline mov al, '.' stosb ; pad with . pop ecx loop .read_lines ; fill last line with . mov ecx, (GRID_X+2) mov al, '.' rep stosb ; 2. find numbers, putting indexes ; into numbers array in the index array find_numbers: push 1 ; current number index xor ecx, ecx ; index .find_next: ; check for end of array cmp ecx, (GRID_X+2)*(GRID_Y*2) jge .done lea esi, [ecx+array] ; current char mov edi, esi ; number start if num call dec_parse jnc .has_num ; no number inc ecx jmp .find_next .has_num: sub esi, edi ; get number char length add esi, ecx ; add to index dec esi ; write to index and to numbers pop ebx ; cur num idx mov [numbers+ebx*4], eax ; save number value .write_idx: mov [index+ecx*2], bx ; overwrite digits with . mov byte [array+ecx], '.' inc ecx cmp ecx, esi jl .write_idx inc ecx ; push new cur num idx inc ebx push ebx jmp .find_next .done: add esp, 4 ; no more cur num idx ; 3. go through array, checking the neighbors of ; numbers for symbols, skip *last added index*, ; adding numbers with sym neighbors to final_value check_neighbors: xor ecx, ecx ; index dec ecx ; gets incremented immediately xor ebx, ebx ; last added idx mov esi, array mov edi, index .check_next_number: ; check for end of array inc ecx cmp ecx, (GRID_X+2)*(GRID_Y*2) jge .done ; check if num movzx eax, word [index+ecx*2] test eax, eax jz .check_next_number .found_num: ; check if last added idx cmp eax, ebx je .check_next_number ; is last added idx, skip .check_symbols: lea edx, [ecx+array] ; current char ; right cmp byte [edx+1], '.' je .r_nsym jmp .has_sym_neighbor .r_nsym: ; left cmp byte [edx-1], '.' je .l_nsym jmp .has_sym_neighbor .l_nsym: ; top cmp byte [edx-(GRID_X+2)], '.' je .t_nsym jmp .has_sym_neighbor .t_nsym: ; bottom cmp byte [edx+(GRID_X+2)], '.' je .b_nsym jmp .has_sym_neighbor .b_nsym: ; top left cmp byte [edx-((GRID_X+2)+1)], '.' je .tl_nsym jmp .has_sym_neighbor .tl_nsym: ; top right cmp byte [edx-((GRID_X+2)-1)], '.' je .tr_nsym jmp .has_sym_neighbor .tr_nsym: ; bottom left cmp byte [edx+((GRID_X+2)-1)], '.' je .bl_nsym jmp .has_sym_neighbor .bl_nsym: ; bottom right cmp byte [edx+((GRID_X+2)+1)], '.' je .br_nsym jmp .has_sym_neighbor .br_nsym: ; there's no symbol neighbor ; get next number jmp .check_next_number .has_sym_neighbor: ; we have a symbol neighbor! ; add to final value mov edx, [numbers+eax*4] add [final_value], edx ; set last added idx mov ebx, eax ; get next number jmp .check_next_number .done: ; we can print final value mov eax, [final_value] call print_dec jmp exit [section .data] file_lim: dd 0 final_value: dd 0 filename: db "input",0 [section .bss] numbers: resd 2048 array: resb (GRID_X+2)*(GRID_Y*2) index: resw (GRID_X+2)*(GRID_Y*2) read_buff: resb BUFF_LIM