ls

simple syscall based programming language from scratch
git clone git://git.kocotian.pl/ls.git
Log | Files | Refs | README

commit bcdbe9902d119248d090a75530d9a60b127bca2e
parent 97f96edafa117130485f16fbafee61556c831dd4
Author: kocotian <kocotian@kocotian.pl>
Date:   Fri, 26 Feb 2021 20:33:17 +0100

keywords, (void) in function

Diffstat:
Mgrammar.c | 28++++++++++++++++++++--------
Mlsc.c | 19+++++++++++++++++++
Mtokentypes | 1+
3 files changed, 40 insertions(+), 8 deletions(-)

diff --git a/grammar.c b/grammar.c @@ -1,8 +1,10 @@ #include <stdio.h> +#include <string.h> #include "grammar.h" extern char *contents; +extern char *output; static char * g_typetostr(TokenType type) @@ -33,13 +35,20 @@ g_statement(Token *tokens, size_t toksize) while (tokens[i].type != TokenClosingBrace && i < toksize) { g_statement(tokens + i, toksize - i); ++i; } - } else if (0) { /* conditional */ - } else if (0) { /* loop */ - } else if (0) { /* return */ - } else if (0) { /* variable */ - } else if (0) { /* constant */ - } else if (0) { /* expression */ - } else if (0) { /* noop */ + } else if (tokens[i].type == TokenKeyword) { + if (!strncmp(contents + tokens[i].off, "if", 2)) { /* conditional */ + } else if (!strncmp(contents + tokens[i].off, "while", 5)) { /* loop */ + } else if (!strncmp(contents + tokens[i].off, "return", 6)) { /* return */ + } else if (!strncmp(contents + tokens[i].off, "var", 3)) { /* variable */ + } else if (!strncmp(contents + tokens[i].off, "const", 5)) { /* constant */ + } else { + char buf[128]; + snprintf(buf, tokens[i].len + 1, "%s", contents + tokens[i].off); + errwarn("unexpected keyword: \033[1m%s\033[0m", 1, + tokens[i], buf); + } + } else if (!strncmp(contents + tokens[i].off, "void", 4)) { /* expression */ + } else if (tokens[i].type == TokenSemicolon) { /* noop */ } else { errwarn("unexpected token \033[1m%s\033[0m, in place of a statement", 1, tokens[i], g_typetostr(tokens[i].type)); @@ -56,7 +65,10 @@ g_function(Token *tokens, size_t toksize) fputs("parenthesis (opening)\n", stderr); g_expecttype(tokens[i], TokenOpeningParenthesis); fputs("loop:\n", stderr); - do { + if (tokens[i + 1].type == TokenKeyword + && !strncmp(contents + tokens[i + 1].off, "void", 4)) + i += 2; + else do { ++i; fputs("\tidentifier\n", stderr); g_expecttype(tokens[i++], TokenIdentifier); diff --git a/lsc.c b/lsc.c @@ -41,6 +41,8 @@ char *filename, *line; int fileline; char *contents; +char *output; +size_t outsiz; static int getsyscallbyname(char *name) @@ -109,6 +111,13 @@ parseline(char *input, size_t ilen, size_t off, Token **tokens, size_t *toksiz, (*tokens)[*tokiter].col = valstart - off + 1; (*tokens)[*tokiter].off = valstart; (*tokens)[*tokiter].len = j + (type == TokenString ? 1 : 0); + if (!strncmp(input + (valstart - off), "if", 2) + || !strncmp(input + (valstart - off), "while", 5) + || !strncmp(input + (valstart - off), "return", 6) + || !strncmp(input + (valstart - off), "var", 3) + || !strncmp(input + (valstart - off), "const", 5) + || !strncmp(input + (valstart - off), "void", 4)) + type = TokenKeyword; (*tokens)[(*tokiter)++].type = type; if (type != TokenString) --i; type = TokenNull; @@ -163,8 +172,18 @@ main(int argc, char *argv[]) write(1, "\n", 1); } + + output = malloc(outsiz = snprintf(buffer, BUFSIZ, "BITS 64\n" + "section .text\nglobal _start\n_start:\n\t" + "call main\n\tmov rax, 60\n\tmov rdi, 0\n\tsyscall\n") + 1); + + memcpy(output, buffer, outsiz); + memcpy(output + outsiz, "", 1); + g_main(tokens, tokiter); + write(1, output, outsiz); + free(output); free(tokens); free(contents); } diff --git a/tokentypes b/tokentypes @@ -5,6 +5,7 @@ TokenNull TokenNumber TokenIdentifier TokenString +TokenKeyword # "punctuation" TokenComma