|
|
|
@ -5,11 +5,36 @@ org 0x100
|
|
|
|
|
|
|
|
|
|
section .code |
|
|
|
|
|
|
|
|
|
seed equ 20220224 |
|
|
|
|
|
|
|
|
|
; Seed the rng |
|
|
|
|
mov ax, seed & 0xffff |
|
|
|
|
mov dx, seed >> 16 |
|
|
|
|
mov bp, rng_seed |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
select_target: |
|
|
|
|
; TODO: Implement target word selection |
|
|
|
|
; https://github.com/lynn/hello-wordl/blob/7da40c1f067eb1ec157d4c5b7a9bd8257ed39342/src/util.ts#L14 |
|
|
|
|
mov si, 1397 |
|
|
|
|
; Call rng to get a number |
|
|
|
|
call rng |
|
|
|
|
mov bp, rng_output |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; Multiply rng output by number of targer words |
|
|
|
|
xor si, si |
|
|
|
|
xor dx, dx |
|
|
|
|
xor ax, ax |
|
|
|
|
mov cx, targets_len |
|
|
|
|
.multiply_loop: |
|
|
|
|
add ax, [rng_output + 0] |
|
|
|
|
adc dx, [rng_output + 2] |
|
|
|
|
adc si, 0 |
|
|
|
|
loop .multiply_loop |
|
|
|
|
|
|
|
|
|
mov ax, si |
|
|
|
|
call hexprint16 |
|
|
|
|
call newline |
|
|
|
|
|
|
|
|
|
load_target: |
|
|
|
|
shl si, 1 |
|
|
|
|
shl si, 1 |
|
|
|
|
add si, targets |
|
|
|
@ -18,6 +43,11 @@ select_target:
|
|
|
|
|
|
|
|
|
|
call unpack_target |
|
|
|
|
|
|
|
|
|
; Figure out whether this is a removed word |
|
|
|
|
; If so, reroll target word |
|
|
|
|
cmp byte [target], '{' |
|
|
|
|
je select_target |
|
|
|
|
|
|
|
|
|
read_guess: |
|
|
|
|
; Number of thus far guessed letters stored in bx |
|
|
|
|
xor bx, bx |
|
|
|
@ -428,6 +458,237 @@ unpack_target:
|
|
|
|
|
|
|
|
|
|
ret |
|
|
|
|
|
|
|
|
|
; out: |
|
|
|
|
; dx:ax = result |
|
|
|
|
rng: |
|
|
|
|
; https://github.com/lynn/hello-wordl/blob/7da40c1f067eb1ec157d4c5b7a9bd8257ed39342/src/util.ts#L14 |
|
|
|
|
|
|
|
|
|
; rng_t = rng_seed += rng_seed + 0x6d2b79f5 |
|
|
|
|
mov bp, rng_seed |
|
|
|
|
call load32 |
|
|
|
|
add ax, 0x79f5 |
|
|
|
|
adc dx, 0x6d2b |
|
|
|
|
call store32 |
|
|
|
|
mov bp, rng_t |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; xorl32 = rng_t |
|
|
|
|
mov bp, xorl32 |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; xorr32 = rng_t >> 15 |
|
|
|
|
mov cx, 15 |
|
|
|
|
call rshift32 |
|
|
|
|
mov bp, xorr32 |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; mull32 = xorl32 ^ xorr32 = rng_t ^ (rng_t >> 15) |
|
|
|
|
call xor32 |
|
|
|
|
mov bp, mull32 |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; mulr32 = rng_t | 1 |
|
|
|
|
mov bp, rng_t |
|
|
|
|
call load32 |
|
|
|
|
or ax, 1 |
|
|
|
|
mov bp, mulr32 |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; rng_t = mull32 * mulr32 = (rng_t ^ (rng_t >> 15)) * (rng_t | 1) |
|
|
|
|
call mul32 |
|
|
|
|
mov bp, rng_t |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; xorl32 = rng_t |
|
|
|
|
mov bp, xorl32 |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; xorr32 = rng_t >> 7 |
|
|
|
|
mov cx, 7 |
|
|
|
|
call rshift32 |
|
|
|
|
mov bp, xorr32 |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; mull32 = xorl32 ^ xorr32 = rng_t ^ (rng_t >> 7) |
|
|
|
|
call xor32 |
|
|
|
|
mov bp, mull32 |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; mulr32 = rng_t | 61 |
|
|
|
|
mov bp, rng_t |
|
|
|
|
call load32 |
|
|
|
|
or ax, 61 |
|
|
|
|
mov bp, mulr32 |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; addl32 = rng_t |
|
|
|
|
mov bp, rng_t |
|
|
|
|
call load32 |
|
|
|
|
mov bp, addl32 |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; addr32 = mull32 * mulr32 = (rng_t ^ (rng_t >> 7)) * (rng_t | 61) |
|
|
|
|
call mul32 |
|
|
|
|
mov bp, addr32 |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; xorl32 = rng_t |
|
|
|
|
mov bp, rng_t |
|
|
|
|
call load32 |
|
|
|
|
mov bp, xorl32 |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; xorr32 = addl32 + addr32 = rng_t + (rng_t ^ (rng_t >> 7)) * (rng_t | 61) |
|
|
|
|
call add32 |
|
|
|
|
mov bp, xorr32 |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; rng_t = xorl32 ^ xorr32 = rng_t ^ (rng_t + (rng_t ^ (rng_t >> 7)) * (rng_t | 61)) |
|
|
|
|
call xor32 |
|
|
|
|
mov bp, rng_t |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; xorl32 = rng_t |
|
|
|
|
mov bp, xorl32 |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; xorr32 = rng_t >> 14 |
|
|
|
|
mov cx, 14 |
|
|
|
|
call rshift32 |
|
|
|
|
mov bp, xorr32 |
|
|
|
|
call store32 |
|
|
|
|
|
|
|
|
|
; result = xorl32 ^ xorr32 = rng_t ^ (rng_t >> 14) |
|
|
|
|
call xor32 |
|
|
|
|
|
|
|
|
|
ret |
|
|
|
|
|
|
|
|
|
; in: |
|
|
|
|
; bp = address of uint32 |
|
|
|
|
; out: |
|
|
|
|
; dx = high 16 bits |
|
|
|
|
; ax = low 16 bits |
|
|
|
|
load32: |
|
|
|
|
mov ax, [bp + 0] |
|
|
|
|
mov dx, [bp + 2] |
|
|
|
|
ret |
|
|
|
|
|
|
|
|
|
; in: |
|
|
|
|
; bp = address of uint32 |
|
|
|
|
; dx = high 16 bits |
|
|
|
|
; ax = low 16 bits |
|
|
|
|
store32: |
|
|
|
|
mov [bp + 0], ax |
|
|
|
|
mov [bp + 2], dx |
|
|
|
|
ret |
|
|
|
|
|
|
|
|
|
; in: |
|
|
|
|
; dx:ax = uint32 to be shifted |
|
|
|
|
; cx = shift amount (must not be 0) |
|
|
|
|
; out: |
|
|
|
|
; dx:ax = result |
|
|
|
|
rshift32: |
|
|
|
|
push cx |
|
|
|
|
.loop: |
|
|
|
|
shr dx, 1 |
|
|
|
|
rcr ax, 1 |
|
|
|
|
loop .loop |
|
|
|
|
pop cx |
|
|
|
|
ret |
|
|
|
|
|
|
|
|
|
; in: |
|
|
|
|
; [xorl32], [xorr32] = operands |
|
|
|
|
; out: |
|
|
|
|
; dx:ax = result |
|
|
|
|
xor32: |
|
|
|
|
mov ax, [xorl32 + 0] |
|
|
|
|
xor ax, [xorr32 + 0] |
|
|
|
|
mov dx, [xorl32 + 2] |
|
|
|
|
xor dx, [xorr32 + 2] |
|
|
|
|
ret |
|
|
|
|
|
|
|
|
|
; in: |
|
|
|
|
; [mull32], [mulr32] = operands |
|
|
|
|
; out: |
|
|
|
|
; dx:ax = result |
|
|
|
|
mul32: |
|
|
|
|
push bx |
|
|
|
|
push cx |
|
|
|
|
; c = 1<<16 |
|
|
|
|
; l = l₁<<16 + l₀ |
|
|
|
|
; r = r₁<<16 + r₀ |
|
|
|
|
; l·r = (l₁<<16 + l₀)·(r₁<<16 + r₀) |
|
|
|
|
; = l₁<<16·r₁<<16 + l₁<<16·r₀ + l₀·r₁<<16 + l₀·r₀ |
|
|
|
|
; = l₁·r₁<<32 + l₁·r₀<<16 + l₀·r₁<<16 + l₀·r₀ ||1<<32 = 0 (mod 1<<32) |
|
|
|
|
; = l₁·r₀<<16 + l₀·r₁<<16 + l₀·r₀ |
|
|
|
|
|
|
|
|
|
; l₀·r₀ |
|
|
|
|
mov ax, [mull32 + 0] |
|
|
|
|
mul word [mulr32 + 0] |
|
|
|
|
mov bx, ax |
|
|
|
|
mov cx, dx |
|
|
|
|
|
|
|
|
|
; l₀·r₁<<16 |
|
|
|
|
mov ax, [mull32 + 0] |
|
|
|
|
mul word [mulr32 + 2] |
|
|
|
|
add cx, ax |
|
|
|
|
|
|
|
|
|
; l₁·r₀<<16 |
|
|
|
|
mov ax, [mull32 + 2] |
|
|
|
|
mul word [mulr32 + 0] |
|
|
|
|
add cx, ax |
|
|
|
|
|
|
|
|
|
mov dx, cx |
|
|
|
|
mov ax, bx |
|
|
|
|
|
|
|
|
|
pop cx |
|
|
|
|
pop bx |
|
|
|
|
|
|
|
|
|
ret |
|
|
|
|
|
|
|
|
|
; in: |
|
|
|
|
; [addl32], [addr32] = operands |
|
|
|
|
; out: |
|
|
|
|
; dx:ax = result |
|
|
|
|
add32: |
|
|
|
|
mov ax, [addl32 + 0] |
|
|
|
|
mov dx, [addl32 + 2] |
|
|
|
|
add ax, [addr32 + 0] |
|
|
|
|
adc dx, [addr32 + 2] |
|
|
|
|
ret |
|
|
|
|
|
|
|
|
|
hexprint32: |
|
|
|
|
xchg ax, dx |
|
|
|
|
call hexprint16 |
|
|
|
|
xchg ax, dx |
|
|
|
|
hexprint16: |
|
|
|
|
xchg ah, al |
|
|
|
|
call hexprint8 |
|
|
|
|
xchg ah, al |
|
|
|
|
hexprint8: |
|
|
|
|
%rep 4 |
|
|
|
|
rol al, 1 |
|
|
|
|
%endrep |
|
|
|
|
call hexprint4 |
|
|
|
|
%rep 4 |
|
|
|
|
rol al, 1 |
|
|
|
|
%endrep |
|
|
|
|
hexprint4: |
|
|
|
|
push ax |
|
|
|
|
and al, 0xf |
|
|
|
|
cmp al, 10 |
|
|
|
|
jb .digit09 |
|
|
|
|
|
|
|
|
|
add al, 'a' - 10 - '0' |
|
|
|
|
|
|
|
|
|
.digit09: |
|
|
|
|
add al, '0' |
|
|
|
|
mov ah, 0xe |
|
|
|
|
int 0x10 |
|
|
|
|
|
|
|
|
|
pop ax |
|
|
|
|
ret |
|
|
|
|
|
|
|
|
|
section .data |
|
|
|
|
target times 5 db 0 |
|
|
|
|
guess times 5 db 0 |
|
|
|
@ -439,6 +700,18 @@ guesses db 0
|
|
|
|
|
|
|
|
|
|
dictionary_entry times 5 db 0 |
|
|
|
|
|
|
|
|
|
rng_seed dd 0 |
|
|
|
|
rng_t dd 0 |
|
|
|
|
|
|
|
|
|
rng_output dd 0 |
|
|
|
|
|
|
|
|
|
xorl32 dd 0 |
|
|
|
|
xorr32 dd 0 |
|
|
|
|
mull32 dd 0 |
|
|
|
|
mulr32 dd 0 |
|
|
|
|
addl32 dd 0 |
|
|
|
|
addr32 dd 0 |
|
|
|
|
|
|
|
|
|
section .rodata |
|
|
|
|
|
|
|
|
|
not_found_str db ' - word not found$' |
|
|
|
|