Added some simple symbol handling to the Parser.

This commit is contained in:
2022-05-06 18:55:22 +00:00
parent fc47bf2143
commit fbef044905
5 changed files with 90 additions and 57 deletions
+3 -5
View File
@@ -1,12 +1,10 @@
#ifndef PARSER_H #ifndef PARSER_H
#define PARSER_H #define PARSER_H
#include <stdio.h>
#include <stdlib.h>
#include "list.h" #include "list.h"
#include "token.h"
typedef struct {
char* name;
int address;
} Symbol;
void ParseTokens(List*); void ParseTokens(List*);
+1
View File
@@ -1,5 +1,6 @@
.org 0x100 .org 0x100
.db msg "Hello, world!", 0 .db msg "Hello, world!", 0
.db more_stuff "And yet another string!", 0
copy r1, msg copy r1, msg
copy r2, 0 copy r2, 0
+8 -8
View File
@@ -7,8 +7,6 @@
#include "../includes/futil.h" #include "../includes/futil.h"
#include "../includes/scanner.h" #include "../includes/scanner.h"
List* get_strings(const char*);
int main(int argc, char* args[]) { int main(int argc, char* args[]) {
if (argc == 1) { if (argc == 1) {
printf("Usage: assm <file1.asm>\n"); printf("Usage: assm <file1.asm>\n");
@@ -22,13 +20,15 @@ int main(int argc, char* args[]) {
List* list = GenerateTokenList(source_code); List* list = GenerateTokenList(source_code);
for(int i = 0; i < list->size; i++) { // for(int i = 0; i < list->size; i++) {
Token* t = (Token*) list->content[i]; // Token* t = (Token*) list->content[i];
printf("[%i] '%s'", t->type, t->lexeme); // printf("[%i] '%s'", t->type, t->lexeme);
if (t->type == NUMBER || t->type == HEX) printf(" NUM: %ld", *((long *) t->value)); // if (t->type == LABEL) printf("*");
printf("\n"); // printf("\n");
} // }
ParseTokens(list);
free(source_code); free(source_code);
} }
+73 -39
View File
@@ -1,55 +1,89 @@
#include "../includes/parser.h" #include "../includes/parser.h"
#include "../includes/token.h"
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h>
//static List* SymbolsTable; typedef struct {
//static unsigned int program_counter = 0; Token* token;
void ProcessDirective(List*); int address;
void ProcessVariableDeclaration(List*); } Symbol;
Symbol* CreateSymbol(Token*, int);
void AddSymbol(Token*);
void PrintSymbols(void);
Token* GetSymbol(char*);
List* SymbolsTable;
unsigned int ProgramCounter = 0;
void ParseTokens(List* tokens) { void ParseTokens(List* tokens) {
// for(int i = 0; i < tokens->size; i++) { SymbolsTable = CreateList();
// if (((Token *) tokens->content[i])->type == TK_Directive){
// ProcessDirective(tokens);
// }
// }
}
void ProcessDirective(List* tokens) { for(int i = 0; i < tokens->size; i++){
if (tokens->size < 2) { Token* t = tokens->content[i];
printf("Directives failed\n");
return;
}
Token* directive = (Token *) tokens->content[0]; switch(t->type) {
case IDENTIFIER:
if (strcmp(".org", directive->value) == 0) { case LABEL:
Token* address_start = (Token*) tokens->content[1]; AddSymbol(t);
if (address_start->type == NUMBER) { break;
long address = strtol(address_start->value, NULL, 10); case STRING:
printf("Address starting at '%ld'\n", address); ProgramCounter += strlen(t->lexeme);
} break;
else if (address_start->type == HEX) { case NUMBER:
long address = strtol(address_start->value, NULL, 16); case HEX:
printf("Setting address to '%ld'\n", address); if ((long) t->value < 256) ProgramCounter += 1;
else ProgramCounter += 2;
break;
default:
if (t->type > ORG) ProgramCounter += 1;
break;
} }
} }
if (strcmp(".db", directive->value) == 0) { PrintSymbols();
ProcessVariableDeclaration(tokens); DestroyList(SymbolsTable);
} printf("Program Counter: %d\n", ProgramCounter);
} }
void ProcessVariableDeclaration(List* tokens) { void PrintSymbols(void) {
if (tokens->size < 3) { printf("-----SYMBOLS-----\n");
printf("Invalid variable delcaration\n"); for(int i = 0; i < SymbolsTable->size; i++) {
return; Symbol* symbol = SymbolsTable->content[i];
printf("[%#08X] %s\n", symbol->address, symbol->token->lexeme);
} }
printf("-----SYMBOLS-----\n");
Token* symbol_token = (Token*) tokens->content[1]; }
Token* string_literal = (Token*) tokens->content[2];
printf("Found string literal.\n"); void AddSymbol(Token* token) {
printf("Name '%s' value: '%s'\n", symbol_token->lexeme, string_literal->lexeme); if (!token) return;
if (token->type != IDENTIFIER && token->type != LABEL) return;
for(int i = 0; i < SymbolsTable->size; i++) {
Symbol* s = SymbolsTable->content[i];
if (strcmp(s->token->lexeme, token->lexeme) == 0) return;
}
Symbol* symbol = CreateSymbol(token, ProgramCounter);
AddListItem(symbol, sizeof(Symbol), SymbolsTable);
}
Token* GetSymbol(char* name) {
if (!name) return NULL;
return NULL;
}
Symbol* CreateSymbol(Token* token, int offset) {
Symbol* symbol = calloc(1, sizeof(Symbol));
if (!symbol) {
return NULL;
}
symbol->token = token;
symbol->address = offset;
return symbol;
} }
+5 -5
View File
@@ -149,7 +149,6 @@ Token* ParseDirective(void) {
free(directive); free(directive);
//Ignore the line
IgnoreLine(); IgnoreLine();
return NULL; return NULL;
@@ -164,9 +163,7 @@ Token* ParseString(void) {
int start = Position; int start = Position;
while(!ScannerAtEnd() && PeekScanner() != '"') { while(!ScannerAtEnd() && PeekScanner() != '"') AdvanceScanner();
AdvanceScanner();
}
int length = Position - start; int length = Position - start;
@@ -211,7 +208,10 @@ Token* ParseIdentifier(void) {
if (IsOpcode(lexeme, &type)) return CreateToken(lexeme, lexeme, Line, type); if (IsOpcode(lexeme, &type)) return CreateToken(lexeme, lexeme, Line, type);
if (IsRegister(lexeme, &type)) return CreateToken(lexeme, lexeme, Line, type); if (IsRegister(lexeme, &type)) return CreateToken(lexeme, lexeme, Line, type);
if (lexeme[length - 1] == ':') return CreateToken(lexeme, lexeme, Line, LABEL); if (lexeme[length - 1] == ':') {
lexeme[length - 1] = '\0'; //Bit hacky, but this makes the parser's job a bit easier.
return CreateToken(lexeme, lexeme, Line, LABEL);
}
return CreateToken(lexeme, lexeme, Line, IDENTIFIER); return CreateToken(lexeme, lexeme, Line, IDENTIFIER);
} }