Moved some of the grunt work to their own functions to clean the code up a bit.
This commit is contained in:
+72
-59
@@ -3,6 +3,10 @@
|
|||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
|
||||||
|
typedef enum {
|
||||||
|
NoOptions = 0, ForwardParser = 1, RemoveExpected = 2
|
||||||
|
} ExpectOptions;
|
||||||
|
|
||||||
List* TokensList;
|
List* TokensList;
|
||||||
int CurrentToken = 0;
|
int CurrentToken = 0;
|
||||||
|
|
||||||
@@ -18,7 +22,9 @@ int ParserAtEnd(void);
|
|||||||
int Expect(TokenClass class, void* value);
|
int Expect(TokenClass class, void* value);
|
||||||
IRState MachineState;
|
IRState MachineState;
|
||||||
|
|
||||||
//int ExpectPuncuation(TokenPunctuation punctuation);
|
void ExpectPuncuation(TokenPunctuation punctuation, ExpectOptions options);
|
||||||
|
void ExpectRegister(void);
|
||||||
|
Symbol* ExpectIdentifier(int resolved, ExpectOptions options);
|
||||||
//int ExpectIdentifier();
|
//int ExpectIdentifier();
|
||||||
|
|
||||||
int HeapSize = 0;
|
int HeapSize = 0;
|
||||||
@@ -35,7 +41,6 @@ IRState* ParseTokens(List* tokens) {
|
|||||||
while(!ParserAtEnd()) {
|
while(!ParserAtEnd()) {
|
||||||
Token* t = PeekToken();
|
Token* t = PeekToken();
|
||||||
if (!t || t->EndOfFile) break;
|
if (!t || t->EndOfFile) break;
|
||||||
int last = CurrentToken;
|
|
||||||
Symbol* tmp;
|
Symbol* tmp;
|
||||||
|
|
||||||
switch(t->Class) {
|
switch(t->Class) {
|
||||||
@@ -43,7 +48,7 @@ IRState* ParseTokens(List* tokens) {
|
|||||||
HandleAssemblerDirective();
|
HandleAssemblerDirective();
|
||||||
break;
|
break;
|
||||||
case MnemonicClass:
|
case MnemonicClass:
|
||||||
HandleOperation();
|
//HandleOperation();
|
||||||
break;
|
break;
|
||||||
case LabelClass:
|
case LabelClass:
|
||||||
{
|
{
|
||||||
@@ -87,31 +92,7 @@ void HandleAssemblerDirective() {
|
|||||||
{
|
{
|
||||||
RemoveCurrentToken();
|
RemoveCurrentToken();
|
||||||
|
|
||||||
Token* identifier = PeekToken();
|
Symbol* symbol = ExpectIdentifier(1, RemoveExpected);
|
||||||
|
|
||||||
if (identifier->Class != IdentifierClass) {
|
|
||||||
fprintf(stderr, "[Line %d] Expected Identifier '%c'\n", identifier->LineNumber, identifier->Value.Punctuation);
|
|
||||||
exit(30);
|
|
||||||
}
|
|
||||||
|
|
||||||
Symbol* symbol;
|
|
||||||
|
|
||||||
int found = TryGetSymbol(identifier->Lemexe, MachineState.SymbolsTable, &symbol);
|
|
||||||
|
|
||||||
if (found && symbol->Resolved) {
|
|
||||||
fprintf(stderr, "Redefinition of %s on line %d.\n", identifier->Lemexe, identifier->LineNumber);
|
|
||||||
exit(1);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (found) {
|
|
||||||
symbol->Address = HeapSize;
|
|
||||||
symbol->Resolved = 1;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
symbol = AddSymbolToTable(identifier->Lemexe, HeapSize, 1, MachineState.SymbolsTable);
|
|
||||||
}
|
|
||||||
|
|
||||||
RemoveCurrentToken(); //Remove the Idenifier name token.
|
|
||||||
|
|
||||||
Token* value = PeekToken();
|
Token* value = PeekToken();
|
||||||
|
|
||||||
@@ -121,11 +102,7 @@ void HandleAssemblerDirective() {
|
|||||||
RemoveCurrentToken(); //Remove the string declared by this DB command.
|
RemoveCurrentToken(); //Remove the string declared by this DB command.
|
||||||
|
|
||||||
if (PeekToken()->Class == PunctuationClass && PeekToken()->Value.Punctuation == Comma) {
|
if (PeekToken()->Class == PunctuationClass && PeekToken()->Value.Punctuation == Comma) {
|
||||||
if (PeekToken()->Value.Punctuation != Comma) {
|
ExpectPuncuation(Comma, RemoveExpected);
|
||||||
fprintf(stderr, "Syntax error line %d: Expected COMMA got %c.", PeekToken()->LineNumber, PeekToken()->Value.Punctuation);
|
|
||||||
exit(1);
|
|
||||||
}
|
|
||||||
RemoveCurrentToken(); //Remove COMMA
|
|
||||||
|
|
||||||
if (PeekToken()->Class != NumberClass) {
|
if (PeekToken()->Class != NumberClass) {
|
||||||
fprintf(stderr, "Syntax error line %d: Expected terminating byte.\n", PeekToken()->LineNumber);
|
fprintf(stderr, "Syntax error line %d: Expected terminating byte.\n", PeekToken()->LineNumber);
|
||||||
@@ -137,7 +114,7 @@ void HandleAssemblerDirective() {
|
|||||||
symbol->Length++;
|
symbol->Length++;
|
||||||
}
|
}
|
||||||
else if (PeekToken()->Class != PunctuationClass || PeekToken()->Value.Punctuation != NewLine) {
|
else if (PeekToken()->Class != PunctuationClass || PeekToken()->Value.Punctuation != NewLine) {
|
||||||
fprintf(stderr, "Syntax error line %d: Expected COMMA got %c.", PeekToken()->LineNumber, PeekToken()->Value.Punctuation);
|
fprintf(stderr, "Syntax error line %d: Expected COMMA.", PeekToken()->LineNumber);
|
||||||
exit(1);
|
exit(1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -165,19 +142,14 @@ void HandleAssemblerDirective() {
|
|||||||
if (reg->Class == RegisterClass) {
|
if (reg->Class == RegisterClass) {
|
||||||
AdvanceParser();
|
AdvanceParser();
|
||||||
|
|
||||||
if (PeekToken()->Class != PunctuationClass || PeekToken()->Value.Punctuation != Comma) {
|
ExpectPuncuation(Comma, ForwardParser);
|
||||||
|
|
||||||
exit(1);
|
if (PeekToken()->Class != IdentifierClass && PeekToken()->Class != NumberClass && PeekToken()->Class != RegisterClass) {
|
||||||
}
|
fprintf(stderr, "[Line %d] Syntax error, expected either a symbol, numeric literal or a register.\n", PeekToken()->LineNumber);
|
||||||
|
|
||||||
AdvanceParser(); //Save the comma
|
|
||||||
|
|
||||||
if (PeekToken()->Class != IdentifierClass && PeekToken()->Class != NumberClass && PeekToken()->Class != RegisterClass){
|
|
||||||
exit(2);
|
exit(2);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (PeekToken()->Class == NumberClass) {
|
if (PeekToken()->Class == NumberClass) {
|
||||||
printf("LODWI\n");
|
|
||||||
directive->Class = MnemonicClass;
|
directive->Class = MnemonicClass;
|
||||||
directive->Value.Mnemonic = LODWI;
|
directive->Value.Mnemonic = LODWI;
|
||||||
directive->Lemexe = "LODWI";
|
directive->Lemexe = "LODWI";
|
||||||
@@ -188,7 +160,6 @@ void HandleAssemblerDirective() {
|
|||||||
directive->Lemexe = "LODW";
|
directive->Lemexe = "LODW";
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
printf("LAA\n");
|
|
||||||
directive->Class = MnemonicClass;
|
directive->Class = MnemonicClass;
|
||||||
directive->Value.Mnemonic = LAA;
|
directive->Value.Mnemonic = LAA;
|
||||||
directive->Lemexe = "LAA";
|
directive->Lemexe = "LAA";
|
||||||
@@ -204,23 +175,11 @@ void HandleAssemblerDirective() {
|
|||||||
|
|
||||||
RemoveCurrentToken(); AdvanceParser(); //byte
|
RemoveCurrentToken(); AdvanceParser(); //byte
|
||||||
|
|
||||||
if (PeekToken()->Class != RegisterClass) {
|
ExpectRegister();
|
||||||
exit(3);
|
|
||||||
}
|
|
||||||
|
|
||||||
AdvanceParser(); //reg
|
ExpectPuncuation(Comma, ForwardParser);
|
||||||
|
|
||||||
if (PeekToken()->Class != PunctuationClass) {
|
ExpectRegister();
|
||||||
exit(7);
|
|
||||||
}
|
|
||||||
|
|
||||||
AdvanceParser(); //Comma
|
|
||||||
|
|
||||||
if (PeekToken()->Class != RegisterClass) {
|
|
||||||
exit(4);
|
|
||||||
}
|
|
||||||
|
|
||||||
AdvanceParser(); //Reg
|
|
||||||
|
|
||||||
directive->Class = MnemonicClass;
|
directive->Class = MnemonicClass;
|
||||||
directive->Value.Mnemonic = LODB;
|
directive->Value.Mnemonic = LODB;
|
||||||
@@ -230,6 +189,11 @@ void HandleAssemblerDirective() {
|
|||||||
AdvanceParser(); //Line end
|
AdvanceParser(); //Line end
|
||||||
}
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
case Store:
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
fprintf(stderr, "Synatx error on line %d, %s.\n", directive->LineNumber, directive->Lemexe);
|
fprintf(stderr, "Synatx error on line %d, %s.\n", directive->LineNumber, directive->Lemexe);
|
||||||
@@ -237,10 +201,59 @@ void HandleAssemblerDirective() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void HandleOperation(void) {
|
void ExpectPuncuation(TokenPunctuation punctuation, ExpectOptions options) {
|
||||||
|
Token* token = PeekToken();
|
||||||
|
|
||||||
|
if (token->Class != PunctuationClass || token->Value.Punctuation != punctuation) {
|
||||||
|
fprintf(stderr, "[Line %d] Syntac error, expected %c.\n", token->LineNumber, punctuation);
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (options & RemoveExpected) RemoveCurrentToken();
|
||||||
|
if (options & ForwardParser) AdvanceParser();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void ExpectRegister() {
|
||||||
|
Token* token = PeekToken();
|
||||||
|
|
||||||
|
if (token->Class != RegisterClass) {
|
||||||
|
fprintf(stderr, "[Line %d] Syntax error, expected Register.\n", token->LineNumber);
|
||||||
|
exit(2);
|
||||||
|
}
|
||||||
|
|
||||||
|
AdvanceParser();
|
||||||
|
}
|
||||||
|
|
||||||
|
Symbol* ExpectIdentifier(int resolved, ExpectOptions options) {
|
||||||
|
Token* token = PeekToken();
|
||||||
|
|
||||||
|
if (token->Class != IdentifierClass) {
|
||||||
|
fprintf(stderr, "[Line %d] Expected Identifier.\n", token->LineNumber);
|
||||||
|
exit(3);
|
||||||
|
}
|
||||||
|
|
||||||
|
Symbol* symbol;
|
||||||
|
|
||||||
|
int found = TryGetSymbol(token->Lemexe, MachineState.SymbolsTable, &symbol);
|
||||||
|
|
||||||
|
if (found && symbol->Resolved && resolved) {
|
||||||
|
fprintf(stderr, "[Line %d] Redefinition of symbol '%s'.\n", token->LineNumber, token->Lemexe);
|
||||||
|
exit(4);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (found) {
|
||||||
|
symbol->Address = HeapSize;
|
||||||
|
symbol->Resolved = resolved || symbol->Resolved;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
symbol = AddSymbolToTable(token->Lemexe, HeapSize, resolved, MachineState.SymbolsTable);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (options & RemoveExpected) RemoveCurrentToken();
|
||||||
|
if (options & ForwardParser) AdvanceParser();
|
||||||
|
|
||||||
|
return symbol;
|
||||||
|
}
|
||||||
|
|
||||||
void PrintSymbols(void) {
|
void PrintSymbols(void) {
|
||||||
//char mn[12];
|
//char mn[12];
|
||||||
|
|||||||
Reference in New Issue
Block a user