diff options
-rwxr-xr-x | Makefile | 2 | ||||
-rw-r--r-- | examples/arithmetic.bdl | 22 | ||||
-rwxr-xr-x | src/bootstrap/main.c | 93 |
3 files changed, 112 insertions, 5 deletions
@@ -15,7 +15,7 @@ BIN := $(BUILD_DIR)/$(TARGET) | |||
15 | 15 | ||
16 | # Compiler and linker configuration. | 16 | # Compiler and linker configuration. |
17 | CC := cc | 17 | CC := cc |
18 | CFLAGS := -Wall -Wextra -pedantic | 18 | CFLAGS := -Wall -Wextra -pedantic -DBIN_NAME=\"$(TARGET)\" |
19 | CFLAGS += $(INC_FLAGS) | 19 | CFLAGS += $(INC_FLAGS) |
20 | LDFLAGS := | 20 | LDFLAGS := |
21 | LDLIBS := | 21 | LDLIBS := |
diff --git a/examples/arithmetic.bdl b/examples/arithmetic.bdl new file mode 100644 index 0000000..5e102e9 --- /dev/null +++ b/examples/arithmetic.bdl | |||
@@ -0,0 +1,22 @@ | |||
1 | ; | ||
2 | ; Basic arithmetic operations | ||
3 | ; | ||
4 | |||
5 | ; Addition | ||
6 | (+ 10 100) | ||
7 | (+ 1 -2 3 4) | ||
8 | |||
9 | ; Substraction | ||
10 | (- 100 75) | ||
11 | (- 10 20 30) | ||
12 | |||
13 | ; Multiplication | ||
14 | (* 10 7) | ||
15 | (* -1 66) | ||
16 | |||
17 | ; Division | ||
18 | (/ 45 5) | ||
19 | (/ 10 5 2) | ||
20 | |||
21 | ; Nesting operations. | ||
22 | (* 20 (+ 100 (- 50 30) (/ 300 3)) 10) | ||
diff --git a/src/bootstrap/main.c b/src/bootstrap/main.c index 1494378..e0012eb 100755 --- a/src/bootstrap/main.c +++ b/src/bootstrap/main.c | |||
@@ -1,4 +1,5 @@ | |||
1 | #include <ctype.h> | 1 | #include <ctype.h> |
2 | #include <getopt.h> | ||
2 | #include <stdio.h> | 3 | #include <stdio.h> |
3 | #include <stdlib.h> | 4 | #include <stdlib.h> |
4 | #include <string.h> | 5 | #include <string.h> |
@@ -695,9 +696,16 @@ eval(Object *root) { | |||
695 | return NULL; | 696 | return NULL; |
696 | } | 697 | } |
697 | 698 | ||
698 | int | 699 | void |
699 | main(void) { | 700 | print_usage(void) { |
700 | init(); | 701 | printf("Usage: %s [options] <filename>\n", BIN_NAME); |
702 | printf("\n"); | ||
703 | printf("\t-i\tInteractive mode (REPL).\n"); | ||
704 | printf("\n"); | ||
705 | } | ||
706 | |||
707 | void | ||
708 | run_repl(void) { | ||
701 | printf("BDL REPL (Press Ctrl-C to exit)\n"); | 709 | printf("BDL REPL (Press Ctrl-C to exit)\n"); |
702 | while (true) { | 710 | while (true) { |
703 | printf(REPL_PROMPT); | 711 | printf(REPL_PROMPT); |
@@ -725,5 +733,82 @@ main(void) { | |||
725 | printf("\n"); | 733 | printf("\n"); |
726 | } | 734 | } |
727 | } | 735 | } |
728 | return 0; | 736 | } |
737 | |||
738 | void | ||
739 | run_file(char *file_name) { | ||
740 | #if DEBUG | ||
741 | printf("Executing file: %s\n", file_name); | ||
742 | #endif | ||
743 | |||
744 | // Load entire file into memory. | ||
745 | char * src = NULL; | ||
746 | FILE *fd = fopen(file_name, "r"); | ||
747 | if (!fd) { | ||
748 | fprintf(stderr, "couldn't open file: %s\n", file_name); | ||
749 | exit(-1); | ||
750 | } | ||
751 | fseek(fd, 0, SEEK_END); | ||
752 | size_t file_size = ftell(fd); | ||
753 | fseek(fd, 0, SEEK_SET); | ||
754 | src = malloc(file_size + 1); | ||
755 | fread(src, 1, file_size, fd); | ||
756 | src[file_size] = '\0'; | ||
757 | fclose(fd); | ||
758 | |||
759 | Tokens tokens = tokenize((StringView){.start = src, .n = file_size}); | ||
760 | #if DEBUG | ||
761 | printf("N_TOKENS: %ld\n", tokens.n); | ||
762 | for (size_t i = 0; i < tokens.n; i++) { | ||
763 | printf("\tTYPE: %3d ", tokens.start[i].type); | ||
764 | printf("N: %3ld ", tokens.start[i].value.n); | ||
765 | printf("VALUE: "); | ||
766 | sv_write(tokens.start[i].value); | ||
767 | printf("\n"); | ||
768 | } | ||
769 | #endif | ||
770 | while (tokens.n) { | ||
771 | Object *ast = parse(&tokens); | ||
772 | if (ast) { | ||
773 | #if DEBUG | ||
774 | printf("AST: "); | ||
775 | display(ast); | ||
776 | printf("\n"); | ||
777 | printf("EVAL: "); | ||
778 | #endif | ||
779 | display(eval(ast)); | ||
780 | printf("\n"); | ||
781 | } | ||
782 | } | ||
783 | |||
784 | free(src); | ||
785 | } | ||
786 | |||
787 | int | ||
788 | main(int argc, char *argv[]) { | ||
789 | init(); | ||
790 | |||
791 | int option; | ||
792 | while ((option = getopt(argc, argv, "i")) != -1) { | ||
793 | switch (option) { | ||
794 | case 'i': { | ||
795 | run_repl(); | ||
796 | return EXIT_SUCCESS; | ||
797 | } break; | ||
798 | default: { | ||
799 | print_usage(); | ||
800 | return EXIT_FAILURE; | ||
801 | } break; | ||
802 | } | ||
803 | } | ||
804 | |||
805 | if (optind != argc - 1) { | ||
806 | fprintf(stderr, "%s: No input file given.\n", BIN_NAME); | ||
807 | print_usage(); | ||
808 | return EXIT_FAILURE; | ||
809 | } | ||
810 | char *file_name = argv[optind]; | ||
811 | run_file(file_name); | ||
812 | |||
813 | return EXIT_SUCCESS; | ||
729 | } | 814 | } |