diff options
| author | Mustafa Quraish <[email protected]> | 2022-02-07 03:02:39 -0500 |
|---|---|---|
| committer | Mustafa Quraish <[email protected]> | 2022-02-07 03:18:08 -0500 |
| commit | 3817688851fae07b1d6a13ba2ce1906fc9811f8f (patch) | |
| tree | bb936b224cada39dc7ede856d9f15a4000950526 /compiler/main.cup | |
| parent | Add missing files to self-hosted directory (diff) | |
| download | cup-3817688851fae07b1d6a13ba2ce1906fc9811f8f.tar.xz cup-3817688851fae07b1d6a13ba2ce1906fc9811f8f.zip | |
[cup] Self-hosting is now possible! Make some tweaks to match C output
A bit of a chonky commit, but this ports over the remaining (well,
almost) everything from the C implementation to the self-hosted
compiler.
The only things that really remain right now are (1) defer support
and (2) support for constants in local scopes. There were used barely
enough so for now their uses have been removed, but I'll implement
them back later. Not sure how useful (2) is though.
Diffstat (limited to 'compiler/main.cup')
| -rw-r--r-- | compiler/main.cup | 81 |
1 files changed, 69 insertions, 12 deletions
diff --git a/compiler/main.cup b/compiler/main.cup index fa7db31..7a4ae0c 100644 --- a/compiler/main.cup +++ b/compiler/main.cup @@ -5,23 +5,80 @@ import "compiler/builtins.cup" import "compiler/parser.cup" import "compiler/codegen.cup" +fn print_usage_and_exit(name: char*, status: int) { + puts("Usage: "); puts(name); putsln(" [options] <file>"); + putsln("Options:"); + putsln(" -c <code> Code to compile"); + putsln(" -h Show this help"); + putsln(" -o <file> Output file"); + putsln(" -d Dump AST to stdout"); + putsln("Output file will be named 'build/host.nasm' by default"); + exit(status); +} + +// FIXME: Allow variables functions to be static to a file? +// we can avoid the prefixes then. +const MAX_STDIN_SOURCE_LEN = 4096; +let m_filename: char*; +let m_outut_filename = "build/host.nasm"; +let m_source: char*; +let m_source_len = 0; +let m_dump_ast = false; + +fn parse_cli_args(argc: int, argv: char**) { + for (let i = 1; i < argc; ++i) { + if (streq(argv[i], "-c")) { + m_source_len = strlen(argv[i+1]); + m_source = argv[i+1]; + ++i; + m_filename = "CLI"; + } else if (streq(argv[i], "-h")) { + print_usage_and_exit(argv[0], 0); + } else if (streq(argv[i], "-d")) { + m_dump_ast = true; + } else if (streq(argv[i], "-o")) { + ++i; + m_outut_filename = argv[i]; + } else if (m_filename == null) { + if (streq(argv[i], "-")) { + m_filename = "stdin"; + m_source = malloc(MAX_STDIN_SOURCE_LEN); + m_source_len = read(0, m_source, MAX_STDIN_SOURCE_LEN); + m_source[m_source_len] = 0; + if (m_source_len == MAX_STDIN_SOURCE_LEN) { + putsln("Source too long to use through stdin"); + exit(1); + } + } else { + m_filename = argv[i]; + let file = fopen(m_filename, 'r'); + m_source = fread_to_string(file, &m_source_len); + fclose(file); + } + } else { + print_usage_and_exit(argv[0], 1); + } + } + if (m_filename == null) { + print_usage_and_exit(argv[0], 1); + } +} + fn main(argc: int, argv: char **): int { - if (argc != 2) - die("Usage: cupcc <input_file>"); + parse_cli_args(argc, argv); - let lexer = lexer_new_open_file(argv[1]); + let lexer = lexer_new(m_filename, m_source, m_source_len); let ast = parse_program(lexer); - dump_ast(ast, 0); - - let out_file = fopen("build/host.nasm", 'w'); - defer fclose(out_file); + if (m_dump_ast) + dump_ast(ast, 0); + let out_file = fopen(m_outut_filename, 'w'); generate_program(ast, out_file); + fclose(out_file); // TODO: Defer on self-host - puts("---------------------------\n"); - - puts("Total amount of memory used by malloc: "); - putu(__malloc_buf_pos); - putsln("\nDone."); + // puts("---------------------------\n"); + // puts("Total amount of memory used by malloc: "); + // putu(__malloc_buf_pos); + // putsln("\nDone."); }
\ No newline at end of file |