; *argvshould be
; argv, since you are not yet dereferencing the pointer.
cmpinstruction, you should prefer
jz, since it is nicer to the human reader.
Oh, the old times, where you had to tell the assembler to
jmp shortbecause it couldn’t figure it out on its own. 🙂
run the BF programsection, I would have changed
ediso that the
sregister points to the source code and the
dregister points to the data. But that is just for fun.
bfprogram_memory_inc, you can just say
inc byte [esi]. The
incinstruction has an
r/m8encoding that allows incrementing a value in memory directly, without needing the indirection.
safe to dooptimization is nice.
Since you rely on the ASCII encoding anyway, you should define
'['instead of 91, if possible. Not every reader knows the ASCII codes by heart.
Does NASM support local labels? That would make the label names in
bfprogram_jump_past_loopa little shorter and thereby easier to read.
Instead of calling
stderra linker-visible symbol so that you can access it directly?
Since your error messages don’t contain percent characters, you should call
The error messages should include a trailing newline.
(Or are they missing because Windows adds this newline anyway? If so, then it’s ok, since it is not necessary to write strictly conforming ANSI C code when you target a specific platform.)
bfprogram_jump_tableis very large. You can probably make it smaller by encoding the jump target relative to a known location, which should only take a single byte per entry.
times 43 db 0, db bfprogram_memory_inc - run_program_loop_end, ....
format_intseems to be unused.
STDERRshould be called
STDERR_FILENO(although that name comes from POSIX, not from Windows, it is still widely known).
0xFFis a valid instruction in a Brainfuck program, using it as the EOF marker is not a good idea. When loading the code from the file, you could replace every character above 93 or below 43 with 44. This change would also allow you to make the jump table smaller.
Overall, it’s a nice little program and the code does the obvious thing. It’s a pleasure to read.
Jump instructions are slow and should be minimized. One jump instruction in the interpreter loop can be removed as follows:
dec edi ; on first pass, compensate for inc edi run_program_loop: ; jump here after executing an opcode run_program_loop_end: ; old label for reference inc edi movzx eax, byte [edi] jmp [bfprogram_jump_table + 4*eax] ; addresses are dword, ASCII is translated to byte offsets