Brainfuck tools: a tiny interpreter (bf), a macro preprocessor (bfpp) that emits plain BF, and a tiny BASIC compiler (bfbasic) that emits bfpp macros.
usage: bf [-t] [-D] [input_file]
- -t : Trace execution to stdout
- -D : Dump final status of the machine to stdout
- input_file : parse input file instead of stdin
Reads input_file or stdin, processes only canonical BF chars (<>+-.,[]). Tape grows right; pointer underflow is an error.
Expands an extended BF dialect to plain BF.
usage: bfpp [-o output_file] [-I include_path] [-D name=value] [-v] [input_file]
- -o output_file : outputs BF code to given file instead of stdout
- -I include_path : add directory to search path for source and include files
- -D name=value : defines numeric macro to be used in the code
- input_file : parse input file instead of stdin
- -v : show memory usage statistics
>N/<N: absolute move to tape cellN(0-based).+N/-N: increment/decrement current cell byN.+(expr)/-(expr)/>(expr)/<(expr): evaluateexpr(identifiers/macros allowed).+'c': increment by ASCII of characterc.{ ... }: save/restore tape position (emits moves to return).#include "file": include file.#define NAME value: object-like macro.#define NAME(p,...) value: function-like macro.#undef NAME#if / #elsif / #else / #endif: conditional assembly on expressions.
- Allocation:
alloc_cellX(NAME),free_cellX(NAME). (X=8,16). - Cell ops:
clearX(a),setX(a, v),moveX(a, b),copyX(a, b). (X=8,16). - Logic:
notX(a),andX(a, b),orX(a, b),xorX(a, b),shrX(a, b),shlX(a, b). (X=8,16). - Arithmetic:
addX(a, b),subX(a, b),mulX(a, b),divX(a, b),modX(a, b),powX(a, b). (X=8,8s,16,16s).negX(a),signX(a),absX(a). (X=8,16). - Comparisons:
eqX(a, b),neX(a, b),ltX(a, b),leX(a, b),gtX(a, b),geX(a, b),minX(a, b),maxX(a, b). (X=8,8s,16,16s). - Control:
if(expr) ... else ... endif,while(expr) ... endwhile,repeat(count) ... endrepeat. - Arrays:
alloc_arrayX(NAME, size),free_arrayX(NAME),put_arrayX(NAME, idx_cell, source_cell),get_arrayX(NAME, idx_cell, target_cell). (X=8,16). - Strings: allocated with
alloc_array8, item 0 holds length, item 1 first character.set_string(STR, "string"),clear_string(STR),append_string(DST, SRC),left_string(DST, SRC, size),right_string(DST, SRC, size),mid_string(DST, SRC, start, size),cmp_string(STR1, STR2, result).format_cellX(DST, cell),string_valX(SRC, cell). (X=8,8s,16,16s). - Output:
print_char(value),print_char8(cell).
print_string("string"). string supports common C escape sequences:\n,\t,\r,\\,\",\',\0,\a,\b,\f,\v.print_string(STR),print_newline.print_cellX(cell). (X=8,8s,16,16s). - Input:
scan_spaces,scan_char8(cell),unscan_char8(cell).
scan_cellX(cell). (X=8,8s,16,16s).scan_word(STR).
Notes:
- Allocation reserves cells from 0 upward and zeroes them.
movezeroes the source;copypreserves it.- Division/modulo are integer; arithmetic wraps at 8-bit (or 16-bit for
xx16).
Compiles a tiny BASIC subset to Brainfuck (via bfpp codegen).
usage: bfbasic [-o output_file] input_file
- -o output_file : write output to the given file instead of stdout
- input_file : BASIC source file (reads stdin if omitted)
Supported statements (one per line; blank lines allowed):
[LET] var = expr- assign integer expression to a variable.DIM var(size) [, var(size)...]- allocates array,A(i)accesses element, 1 <= i <= size.INPUT var1 [, var2...]- read integers intovarN.PRINT [string|expr][,|;]...- print values of expressions and stringsIF expr THEN stmts [ELSE stmts]- single line if-else.IF expr THEN, ...,[ELSE, ...,]ENDIF- multi-line if-else.WHILE expr, ...,WEND- loops controled on an expression.FOR var = expr TO expr [STEP expr], ...,NEXT- counted loops.SUB name(param,param$,...) ... ENDSUB- define subroutine, called with[CALL name(arg1,arg2$,...).FUNCTION name[$](param,param$,...) ... ENDFUNCTION- define function that can be called inside expressions. Function must assign toname[$]the return value.- a colon (
:) can be used to separate statements in the same line. - a single
_followed by newline is considered white space and ignored.
Strings:
- Must be DIM-ensinoned to the maximum size -
DIM A$(10). - Can be assigned -
[LET] A$ = "hello". - Can be concatenated -
[LET] A$ = B$ & C$. - Can be printed and read -
PRINT A$,INPUT A$. - String functions in expressions -
LEFT$,MID$,RIGHT$,STR$,LEN,VAL,CHR$,ASC. - String comparison operators -
=,<>,<,<=,>,>=.
Expressions:
- variables and decimal integers
- binary arithmetic:
+ - * / \\ MOD ^ - relational:
= <> < <= > >=(results are 0/1) - boolean logic:
AND OR XOR(operates on 0/1)
Precedence and associativity (highest to lowest):
- unary (
+,-,NOT) - power (
^) - multiplicative (
*,/,\,MOD) - additive (
+,-) - shift (
SHL,SHR) - relational (
=,<>,<,<=,>,>=) - logical AND (
AND) - logical XOR (
XOR) - logical OR (
OR)
Parentheses (...) can be used to override precedence.
The compiler allocates variables automatically and emits bfpp code.
Makefile project targeting C++17. Typical flow:
git clone <repo_url>
cd <repo_dir>
make
make test
This produces bf, bfpp and bfbasic executables in the project directory. You can run them as described above.
Here's a simple example using bfpp to create a BF program that prints "Hello, World!":
./bf examples/hello.bf
./bfpp examples/hello.bfpp | ./bf
Here's a simple calculator written in bfpp and compiled to bf:
echo '2*3+7' | ./bf examples/calc.bf
This project is licensed under the Artistic License 2.0.