diff options
Diffstat (limited to 'bf.c')
| -rw-r--r-- | bf.c | 94 |
1 files changed, 94 insertions, 0 deletions
@@ -0,0 +1,94 @@ +#include <stdio.h> +#include <stdlib.h> +#include <stdint.h> + +int main(int argc, char **argv) +{ + if (argc != 2) { + fprintf(stderr, "Usage: %s file.bf\n", argv[0]); + exit(EXIT_FAILURE); + } + + FILE *fp = fopen(argv[1], "r"); + fseek(fp, 0, SEEK_END); + size_t program_size = ftell(fp); + fseek(fp, 0, SEEK_SET); + + char program[program_size + 1]; + program[program_size] = 0; + + fread(program, sizeof(uint8_t), program_size, fp); + + fclose(fp); + + size_t dp = 0; + size_t pc = 0; + uint8_t mem[3000] = { 0 }; + + while (pc < program_size) { + switch (program[pc]) { + case '>': { + dp++; + break; + } + case '<': { + dp--; + break; + } + case '+': { + mem[dp]++; + break; + } + case '-': { + mem[dp]--; + break; + } + case ',': { + mem[dp] = getchar(); + break; + } + case '.': { + putchar(mem[dp]); + break; + } + case '[': { + if (mem[dp] == 0) { + size_t l = 1; + while (l) { + switch (program[++pc]) { + case '[': { + l++; + break; + } + case ']': { + l--; + break; + } + } + } + } + break; + } + case ']': { + if (mem[dp] != 0) { + size_t l = 1; + while (l) { + switch (program[--pc]) { + case ']': { l++; + break; + } + case '[': { + l--; + break; + } + } + } + } + break; + } + } + pc++; + } + + return EXIT_SUCCESS; +} |
