Skip to content

Instantly share code, notes, and snippets.

@lifthrasiir
Created September 25, 2010 09:36
Show Gist options
  • Star 117 You must be signed in to star a gist
  • Fork 8 You must be signed in to fork a gist
  • Save lifthrasiir/596667 to your computer and use it in GitHub Desktop.
Save lifthrasiir/596667 to your computer and use it in GitHub Desktop.
/* The world's smallest Brainfuck interpreter in C, by Kang Seonghoon
* http://j.mearie.org/post/1181041789/brainfuck-interpreter-in-2-lines-of-c */
s[99],*r=s,*d,c;main(a,b){char*v=1[d=b];for(;c=*v++%93;)for(b=c&2,b=c%7?a&&(c&17
?c&1?(*r+=b-1):(r+=b-1):syscall(4-!b,b,r,1),0):v;b&&c|a**r;v=d)main(!c,&a);d=v;}
@dtomvan
Copy link

dtomvan commented Feb 15, 2023

using gcc to compile results in a binary that segfaults on any input

Same here, it does compile, but it always segfaults.

$ /bin/gcc --version | head -n1
gcc (GCC) 12.2.1 20230201

$ expac '%v' gcc
12.2.1-2

$ expac -Ss '%r-%v' '^gcc$'
core-12.2.1-2

Still nice idea, but for some reason just doesn't work.

@locnnil
Copy link

locnnil commented Mar 28, 2023

My compiled binary with gcc also gets segfaults for any input! Anyone have a tip!?

My GCC: gcc (Ubuntu 12.1.0-2ubuntu1~22.04) 12.1.0

@carter-canedy
Copy link

carter-canedy commented Mar 28, 2023

See below

@lifthrasiir
Copy link
Author

lifthrasiir commented Mar 29, 2023

you'll need to refactor the bf compiler so that it's not implicitly typing all untyped variables as ints, this only works as-is on platforms where the int width is the same as a char (1 octet/8 bits), which is the case on the pdp11. To run this as-is, your best bet is to see if you can find an emulator for the pdp11, if it exists.

No it isn't. It does assume that int has the same size as a pointer, which no longer holds in modern 64-bit architectures, but I'm pretty sure that you can still compile and run this code in 32-bit architectures by, for example, using -m32 in GCC to force it. (As you can imagine, because I wrote that code. But I'm on a road and I cannot readily test that, so YMMV.)

@kwmu4k
Copy link

kwmu4k commented Apr 20, 2023

How does this work? :O

@carter-canedy
Copy link

To any newcomers:

Compile using gcc with the flag "-m32"

You may need to install the gcc-multilib package in order to target an x86 binary

After you have the right libraries installed, you should be able to compile like this:

gcc -m32 -o bf bf.c

@f3nai
Copy link

f3nai commented Oct 20, 2023

good stuff.

@adamsir
Copy link

adamsir commented Nov 6, 2023

Here is the clarified version. I used gpt-4 to reconstruct the code, meaning I just wanted to share the clarified version for learning purposes. I don't know C language, but I was curious.

#include <unistd.h>
#include <stdlib.h>
#include <stdio.h>

#define TAPE_SIZE 30000

// Declare an array to act as the tape for Brainfuck. Initialize all to zero.
unsigned char s[TAPE_SIZE] = {0};

// This will be the data pointer used in Brainfuck
unsigned char* ptr = s;

// Forward declaration of the main function to make it recursive
int main(int argc, char *argv[]);

int main(int argc, char *argv[]) {
  char* v;

  // Ensure that a Brainfuck program is provided as an argument
  if (argc != 2) {
    fprintf(stderr, "Usage: %s 'brainfuck_code'\n", argv[0]);
    return 1;
  }

  v = argv[1];

  while (*v) {
    switch (*v) {
      case '>':
        ptr++;
        // Boundary check to prevent going beyond the tape
        if (ptr >= s + TAPE_SIZE) {
          fprintf(stderr, "Error: Pointer out of bounds\n");
          return 1;
        }
        break;
      case '<':
        // Boundary check to prevent going before the tape
        if (ptr <= s) {
          fprintf(stderr, "Error: Pointer out of bounds\n");
          return 1;
        }
        ptr--;
        break;
      case '+':
        (*ptr)++;
        break;
      case '-':
        (*ptr)--;
        break;
      case '.':
        putchar(*ptr);
        break;
      case ',':
        *ptr = (unsigned char)getchar();
        break;
      case '[':
        if (!*ptr) {
          int loop = 1;
          while (loop > 0) {
            v++;
            if (*v == '[') loop++;
            if (*v == ']') loop--;
          }
        }
        break;
      case ']':
        if (*ptr) {
          int loop = 1;
          while (loop > 0) {
            v--;
            if (*v == '[') loop--;
            if (*v == ']') loop++;
          }
        }
        break;
    }
    v++;
  }

  return 0;
}

How to compile?

gcc brainfuck.c

How to run?

./a.out "++++++++++[>+++++++>++++++++++>+++>+<<<<-]>++.>+.+++++++..+++.>++.<<+++++++++++++++.>.+++.------.--------.>+.>.
"

This should dispay

Hello world

@neonfuz
Copy link

neonfuz commented Mar 5, 2024

Here is the clarified version. I used gpt-4 to reconstruct the code, meaning I just wanted to share the clarified version for learning purposes. I don't know C language, but I was curious.

Honestly looks like chat gpt just spat out a generic bf interpreter, it doesn't share many characteristics with the minimal interpreter.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment