From: Laurent Mazet Date: Wed, 20 Dec 2023 16:10:52 +0000 (+0100) Subject: correct jump management X-Git-Url: https://secure.softndesign.org/git/?p=brainfuck.git;a=commitdiff_plain;h=3d8520e3c555b4568b42f241f3ee13e974999871 correct jump management --- diff --git a/bf.c b/bf.c index be9c11f..c71b467 100644 --- a/bf.c +++ b/bf.c @@ -14,7 +14,8 @@ /* macros */ #define BUFSIZE 256 -#define MEMSIZE 8 +#define MAXJUMP 4 +#define MEMSIZE 10 /* type definition */ @@ -23,6 +24,8 @@ char *progname = NULL; int p = 0; char mem[MEMSIZE] = {0}; +int j = 0; +int jump[MAXJUMP] = {0}; /* help function */ @@ -44,9 +47,13 @@ int usage (int ret) int process (char *buffer, int nb, FILE *out) { int i; - for (i = 0; (i < nb) && (buffer[i] != 0); i++) { + for (i = 0; i < nb; i++) { + if (buffer[i] == 0) { + break; + } + + VERBOSE (DEBUG, fprintf (stderr, "%s: p=%d, buffer='%s', memory=[ ", progname, p, buffer + i); int _i; for (_i = 0; _i < MEMSIZE; _i++) fprintf (stderr," %d", mem[_i]); fprintf (stderr," ]\n")); - VERBOSE (DEBUG, fprintf (stderr, "%s: read '%c' (%u)\n", progname, buffer[i], buffer[i])); switch (buffer[i]) { case '>': /* increase pointer */ p++; @@ -88,6 +95,10 @@ int process (char *buffer, int nb, FILE *out) { } break; case '[': /* jump to right bracket if pointer is set to 0 */ + if ((p < 0) || (p >= MEMSIZE)) { + VERBOSE (ERROR, fprintf (stderr, "%s: invalid address (%d)\n", progname, p)); + return 1; + } if (mem[p] == 0) { int bracket = 1; while ((++i < nb) && (bracket > 0)) { @@ -97,14 +108,21 @@ int process (char *buffer, int nb, FILE *out) { VERBOSE (ERROR, fprintf (stderr, "%s: brace not closed\n", progname)); return 1; } + i--; } else { - return process (buffer + i + 1, nb - i - 1, out); + if (j >= MAXJUMP) { + VERBOSE (ERROR, fprintf (stderr, "%s: too many jump\n", progname)); + return 1; + } + jump[j++] = i; } break; case ']': /* jump to left bracket if pointer is different to 0 */ - if (mem[p] != 0) { - i = -1; + if (j <= 0) { + VERBOSE (ERROR, fprintf (stderr, "%s: can't jump back\n", progname)); + return 1; } + i = jump[--j] - 1; break; case ' ': case '\t': @@ -217,7 +235,9 @@ int main (int argc, char *argv[]) } /* close input file */ - fclose (fid); + if (fid != stdin) { + fclose (fid); + } VERBOSE (DEBUG, fprintf (stderr, "%s: read %d bytes\n", progname, size + n - BUFSIZE)); } else { VERBOSE (DEBUG, fprintf (stderr, "%s: prog %d bytes\n", progname, size -1)); @@ -236,10 +256,13 @@ int main (int argc, char *argv[]) /* main process */ int rc = process (buffer, size, fid); - VERBOSE (INFO, fprintf (stdout, "\nmemory:"); int _i; for (_i = 0; _i < MEMSIZE; _i++) fprintf (stdout," %d", mem[_i]); fprintf (stdout,"\n")); /* close output file */ - fclose (fid); + if (fid != stdout) { + fclose (fid); + } + + VERBOSE (INFO, fprintf (stdout, "\nmemory:"); int _i; for (_i = 0; _i < MEMSIZE; _i++) fprintf (stdout," %d", mem[_i]); fprintf (stdout,"\n")); return rc; } @@ -252,12 +275,13 @@ int main (int argc, char *argv[]) // test: echo ">>." | bf.exe -o error/error.b 2>&1 | grep "can't open" | grep -q "writing" // test: echo '+++>++>>-<--' | bf.exe -v2 | grep -q "memory: 3 2 -2 -1 0" // test: bf.exe -e '+++>++>>-<--' -v2 | grep -q "memory: 3 2 -2 -1 0" +// test: bf.exe -m "51 50 49" -e '.>.>.' |grep -q "321" // test: echo '++++++++++[>+++++++>++++++++++>+++>+<<<<-]>++.>+.+++++++..+++.>++.<<+++++++++++++++.>.+++.------.--------.>+.>.' | bf.exe -v1 | grep -q "Hello World!" // test: echo '++++++++++[>+>+++>+++++++>++++++++++<<<<-]>>>++++++++++++++.>+++++++++++++++++.<<++.>+++++++++++++.>--.<<.>+++.+.--.>----.++++++.+.<++.>----.++.<<.>>+.-------.<<.>>++.<.>+++++.<<.>-.+.<.>---.>---.<-.++++++++.>----.<---.>+++++++.<---.++++++++.' | bf.exe -v1 | grep -q "Tu as decouvert un peu de brainfuck" // test: echo -e "123\0" | bf.exe -e ',[>,]' -v2 | grep -q "memory: 49 50 51 0" -// test: echo -e "43\0" | bf.exe -e ',>++++++[<-------->-],[<+>-]<.' -v1 | grep -q 7 - -// test: echo -e "32\0" | bf.exe -e ',>,>>++++++++++++++++[-<+++<---<--->>>]<<[<[>>+>+<<<-]>>>[<<<+>>>-]<<-]>.' -v1 | grep -q 6 -// test: echo -e "32\0" | bf.exe -e ',>,[->>+<<]+<[->>>[>>>>>+<<<<<->+<<]<[>]>>>>>[-<<->>>>>>>]<[>]<<<<<<]>[>>>>->]<<<<<<[-]>[-]>>[-]>.' -v1 | grep -q 3 +// test: echo -e "4+3\0" | bf.exe -e ',>++++++[<-------->-],,[<+>-]<.' -v1 | grep -q 7 +// test: echo -e "1+7\0" | bf.exe -e ',>++++++[<-------->-],,[<+>-]<.' -v1 | grep -q 8 +// test: echo -e "3*2\0" | bf.exe -e ',>,,>++++++++[<------<------>>-]<<[>[>+>+<<-]>>[<<+>>-]<<<-]>>>++++++[<++++++++>-]<.' -v1 | grep -q 6 +// test: echo -e "1*7\0" | bf.exe -e ',>,,>++++++++[<------<------>>-]<<[>[>+>+<<-]>>[<<+>>-]<<<-]>>>++++++[<++++++++>-]<.' -v1 | grep -q 7 /* vim: set ts=4 sw=4 et: */