Login Register


[C]Brainfuck Interpreter filter_list
Author
Message
[C]Brainfuck Interpreter #1
Since i'm making the Brainfuck tutorial, i decided to make an interpreter for it:Smile:
Code:
#include <stdio.h> #include <stdlib.h> #include <string.h> #define MEMORY_SIZE 30000 int files = 0; char ** filelist = 0; FILE * file = 0; char * program = 0; char memory[MEMORY_SIZE]; void print_guide(char * runname); int file_is_alive(char * name); void add_file_tolist(char * name); int decent_character(char character); int load_program(char * name); int check_syntax(char * name); void run_program(char * name); void endfunction(); int main(int number_of_arguments, char **arguments) { int i; atexit(endfunction); if (number_of_arguments < 2) { print_guide(arguments[0]); return EXIT_FAILURE; } for (i = 1; i < number_of_arguments; ++i) { if (file_is_alive(arguments[i])) { add_file_tolist(arguments[i]); } else { printf("Error! File %s was not found or it's unable to open!\n", arguments[i]); print_guide(arguments[0]); return EXIT_FAILURE; } } for (i = 0; i < files; ++i) { if (load_program(filelist[i]) && check_syntax(filelist[i])) { run_program(filelist[i]); } } return EXIT_SUCCESS; } void print_guide(char * runname) { printf("Brainfuck-compiler 0.1\nAction: %s files\n", runname); } int file_is_alive(char * name) { file = fopen(name, "r"); if (!file) { return 0; } fclose(file); return 1; } void add_file_tolist(char * name) { /* Expand the list */ ++files; filelist = (char**)realloc(filelist, files * sizeof(char*)); if (!filelist) { printf("Program ran out of memory when creating the file list!\n"); exit(EXIT_FAILURE); } /* Allocate memory and put the file name into there */ filelist[files - 1] = (char*) malloc(strlen(name) + 1); if (!filelist[files - 1]) { printf("Program ran out of memory when creating the file list!\n"); exit(EXIT_FAILURE); } strcpy(filelist[files - 1], name); } int decent_character(char character) { if (character == '<') return 1; if (character == '>') return 1; if (character == '+') return 1; if (character == '-') return 1; if (character == '.') return 1; if (character == ',') return 1; if (character == '[') return 1; if (character == ']') return 1; return 0; } int load_program(char * name) { size_t size; int i, j; file = fopen(name, "r"); if (!file) { printf("Error! File '%s' couldn't be opened!\n", name); exit(EXIT_FAILURE); } /* Measure the file */ fseek(file, 0, SEEK_END); size = ftell(file); fseek(file, 0, SEEK_SET); /* Release the old code and allocate new */ if (program) { free(program); } program = (char*)malloc(size + 1); if (!program) { printf("Error! For the program in the file '%s' was not derived memory.", name); exit(EXIT_FAILURE); } /* Read the whole file */ if (fread(program, size, 1, file) != 1) { printf("Error! File '%s' couldn't be opened!\n", name); exit(EXIT_FAILURE); } program[size] = 0; /* Delete characters which are not part of the program */ for (i = j = 0; program[i] != 0; ++i) { if (decent_character(program[i])) { program[j] = program[i]; ++j; } } program[j] = 0; return 1; } int check_syntax(char * name) { int i, brackets; if (!program) { return 0; } /* Count that there are enough brackets for both ways */ for (i = brackets = 0; program[i] != 0; ++i) { if (program[i] == '[') { ++brackets; } else if (program[i] == ']') { --brackets; } } if (brackets != 0) { printf("There is error in the syntax of the file '%s'!\n", name); } return brackets == 0; } void run_program(char * name) { int position = 0, brackets; char *pointer = memory; if (!program) { return; } printf("Run '%s'\n", name); /* Reset the memory */ memset(memory, 0, MEMORY_SIZE); /* In the end of the text, there is 'zeromark', repeat until that */ while (program[position] != 0) { switch (program[position]) { case '>': ++pointer; break; case '<': --pointer; break; case '+': ++*pointer; break; case '-': --*pointer; break; case '.': putchar(*pointer); fflush(stdout); break; case ',': *pointer = getchar(); break; case '[': if (*pointer == 0) { /* Get equivalent closing bracket */ brackets = 1; while (brackets) { ++position; if (program[position] == '[') { ++brackets; } else if (program[position] == ']') { --brackets; } } } break; case ']': if (*pointer != 0) { /* Get equilevant starting bracket */ brackets = 1; while (brackets) { --position; if (program[position] == ']') { ++brackets; } else if (program[position] == '[') { --brackets; } } } break; } /* To the next character in the code */ ++position; } printf("\nThe end.\n"); } void endfunction() { int i; if (filelist) { for (i = 0; i < files; ++i) { if (filelist[i]) { free(filelist[i]); } } free(filelist); } if (program) { free(program); } if (file) { fclose(file); } }


Reply

RE: [C]Brainfuck Interpreter #2
If you coded this from scratch, well done.

This looks like a good job to me, you even freed the allocated space in the end, which is a good habit. This code only looks bad:

Code:
{ if (character == '<') return 1; if (character == '>') return 1; if (character == '+') return 1; if (character == '-') return 1; if (character == '.') return 1; if (character == ',') return 1; if (character == '[') return 1; if (character == ']') return 1; return 0; }

Why not an if-or-if statement? Or even making an array with all the chars, then iterating through it with an if statement, but this thing you did hurts my stomach.
My Bitcoin address: 1AtxVsSSG2Z8JfjNy9KNFDUN6haeKr7LiP
Give me money by visiting www.google.com here: http://coin-ads.com/6Ol83U

If you want a Bitcoin URL shortener/advertiser, please, use this referral: http://coin-ads.com/register.php?refid=noize

Reply

RE: [C]Brainfuck Interpreter #3
:Grin: i really don't know why i did that. Maybe i should change it.


Reply

RE: [C]Brainfuck Interpreter #4
(09-16-2013, 04:40 AM)Slarek Wrote: :Grin: i really don't know why i did that. Maybe i should change it.

Well, it's not erroneous, of course, but I wonder what ArkPhaze would say, lol.

With 8 commands, a Brainfuck interpreter is a nice and relatively simple thing to code, as you mainly have to work out the basis, and the add-commands part is far shorter.

More fun and less work.
My Bitcoin address: 1AtxVsSSG2Z8JfjNy9KNFDUN6haeKr7LiP
Give me money by visiting www.google.com here: http://coin-ads.com/6Ol83U

If you want a Bitcoin URL shortener/advertiser, please, use this referral: http://coin-ads.com/register.php?refid=noize

Reply

RE: [C]Brainfuck Interpreter #5
@noize
I think i'm going to change it.
I do not want to face the anger of ArkPhaze.


Reply







Users browsing this thread: 1 Guest(s)