From 4ca0e313a0f2adb995dccd95fdd885dfa7dacbd1 Mon Sep 17 00:00:00 2001 From: OpenUniProjects Date: Wed, 16 Mar 2022 22:17:36 +0200 Subject: [PATCH] more errors handling Signed-off-by: OpenUniProjects --- .github/workflows/CI.yml | 10 ++++++-- assembler.c | 7 ++++++ misc/definitions.h | 2 +- misc/parsers.c | 15 +++++++----- misc/utils.c | 53 +++++++++++++++++++++++++++++----------- misc/utils.h | 3 ++- passes/first_pass.c | 11 ++++++--- passes/pre_assembler.c | 4 +-- passes/second_pass.c | 2 +- ps4.as | 3 ++- ps7.as | 4 ++- 11 files changed, 82 insertions(+), 32 deletions(-) diff --git a/.github/workflows/CI.yml b/.github/workflows/CI.yml index 6976583..7ce2839 100644 --- a/.github/workflows/CI.yml +++ b/.github/workflows/CI.yml @@ -26,8 +26,14 @@ jobs: cmp tester/ps.ob tester/main_tester - uses: actions/upload-artifact@v3 with: - name: assembler - path: assembler + name: assembler.zip + path: | + misc + passes + tester + assembler + assembler.c + Makefile build_and_test_18_04: runs-on: ubuntu-18.04 diff --git a/assembler.c b/assembler.c index 84446ee..670e055 100644 --- a/assembler.c +++ b/assembler.c @@ -3,6 +3,11 @@ #include "passes/pre_assembler.h" #include "passes/first_pass.h" +/** + * main wrapper function that parses the user inputs and executes the runs + * @param argc + * @param argv + */ void mainRunner(int argc, char **argv) { int errors = 0; int inputFileCounter = 1; @@ -16,6 +21,7 @@ void mainRunner(int argc, char **argv) { printf("Received %d files, starting assembler process.\n\n", argc-1); while (inputFileCounter < argc) { /* iterate over files from argv .as */ errors = 0; + lineNum = 1; memset(line, '0', 4); if ((inp = inputFileInit(argv, inp, &inputFileCounter)) == NULL) { printError("file not found, skipping to next"); @@ -32,6 +38,7 @@ void mainRunner(int argc, char **argv) { printf("===>>>>>> Pre assembler finished: Errors: %d\n", errors); if (errors == 0) { fclose(inp); + lineNum = 1; firstPass(line, outP, &errors, outPutFileName); } else { fclose(outP); diff --git a/misc/definitions.h b/misc/definitions.h index 90f0c2d..7eff9a9 100644 --- a/misc/definitions.h +++ b/misc/definitions.h @@ -10,7 +10,7 @@ #define MAX_COMMANDS 8192 /** - * declare boolean type TRUE = 1 FLASE = 0 using enum + * declare boolean type TRUE = 1 FALSE = 0 using enum */ typedef int bool; diff --git a/misc/parsers.c b/misc/parsers.c index 77d1e52..bdccb20 100644 --- a/misc/parsers.c +++ b/misc/parsers.c @@ -1,6 +1,5 @@ #include "definitions.h" #include "utils.h" -#include "utils.h" /** * functions array with each func declaration @@ -107,7 +106,7 @@ int getOperandsCount(char *cmd, int *errors) { } } *errors += 1; - printf("--->Error: CMD: [ %s ] not found.\n", cmdName); + printf("%d --->Error: CMD: [ %s ] not found.\n", lineNum, cmdName); return -1; } @@ -170,13 +169,13 @@ char **chooseParser(char *input, int *errors) { } if (assertNumOfOperands(parsedLine, errors, numOfOperands) == FALSE) { swapLastCharIfNewLine(parsedLine[0]); - printf("--->Wrong number of operands for command: %s\n", parsedLine[0]); + printf("%d --->Wrong number of operands for command: %s\n", lineNum, parsedLine[0]); return NULL; } if (strtok(NULL, " ") != NULL) { swapLastCharIfNewLine(parsedLine[0]); *errors += 1; - printf("--->Wrong number of operands for command: %s\n", parsedLine[0]); + printf("%d --->Wrong number of operands for command: %s\n", lineNum, parsedLine[0]); return NULL; } return parsedLine; @@ -202,7 +201,7 @@ void parseCmd(char **parsedLine, int *errors, char *cmd, machineCode *mCode, lon } } if (found == FALSE) { - printf("--->Error: CMD: [ %s ] not found\n", cmd); + printf("%d --->Error: CMD: [ %s ] not found\n", lineNum, cmd); *errors += 1; } setCode(mCode, IC, &functions[i], parsedLine, labelName, errors); @@ -302,6 +301,10 @@ sortType getSortType(char *operand, int *errors) { if ((atoi(&operand[1]) >= 0 && atoi(&operand[1]) <= 9 && operand[2] == '\0') || (atoi(&operand[1]) >= 10 && atoi(&operand[1]) <= 15 && operand[3] == '\0')) { return sort3; + } else { + *errors += 1; + printf("%d --->reg: %s, wrong number\n", lineNum, operand); + return unsorted; } } /*direct sort*/ @@ -311,7 +314,7 @@ sortType getSortType(char *operand, int *errors) { /*did not find appropriate sort*/ else { *errors += 1; - printf("--->Operand: %s, did not find matching sort type\n", operand); + printf("%d --->Operand: %s, did not find matching sort type\n", lineNum, operand); return unsorted; } } diff --git a/misc/utils.c b/misc/utils.c index 8495639..2e3793d 100644 --- a/misc/utils.c +++ b/misc/utils.c @@ -1,6 +1,7 @@ #include "definitions.h" #include "parsers.h" +int lineNum = 1; /* utils */ /** * swap last char /n for /0 @@ -325,7 +326,7 @@ char *iterator(char *line, FILE *inp, const int *errors) { while ((fgets(line, MAX_LENGTH, inp)) != NULL) { /* read from .as file and save macro data to .am file */ if (strlen(line) > MAX_LENGTH) { errors += 1; - printf("--->line to long\n"); + printf("%d --->line to long\n", lineNum); continue; } if (line[0] == '\n') continue; @@ -341,7 +342,7 @@ char *iterator(char *line, FILE *inp, const int *errors) { * @param error */ void printError(char *error) { - printf("\n--->%s\n", error); + printf("\n-->%s\n", error); } /** @@ -403,14 +404,24 @@ void setAdditionalLines(machineCode *mCode, long *IC, sortType sort, int *L, cha * @param sort * @return */ -int regNumber(char *reg, sortType sort) { +int regNumber(char *reg, sortType sort, int *errors) { + int num; if (sort == sort2) { strtok(reg, "["); reg = strtok(NULL, ""); /* for regs in []*/ reg[strlen(reg) - 1] = '\0'; + ++reg; + num = atoi(reg); + if (num > 15 || num < 10) { + *errors += 1; + printf("%d --->expected regs between 10 and 15\n", lineNum); + return -1; + } + } else { + ++reg; + num = atoi(reg); } - ++reg; - return atoi(reg); + return num; } /** @@ -500,7 +511,7 @@ void setCode(machineCode *mCode, long *IC, func *f, char **parsedLine, char *lab mCode[*IC].word.code->destSort = destSort; if (destSort == sort3 || destSort == sort2) { - destReg = regNumber(parsedLine[1], destSort); + destReg = regNumber(parsedLine[1], destSort, errors); mCode[*IC].word.code->destReg = destReg; } setOperandLabel(destSort, sourceSort, labelName, mCode, parsedLine, IC, f->operands); @@ -515,11 +526,11 @@ void setCode(machineCode *mCode, long *IC, func *f, char **parsedLine, char *lab mCode[*IC].word.code->destSort = destSort; if (sourceSort == sort3 || sourceSort == sort2) { - sourceReg = regNumber(parsedLine[1], sourceSort); + sourceReg = regNumber(parsedLine[1], sourceSort, errors); mCode[*IC].word.code->sourceReg = sourceReg; } if (destSort == sort3 || destSort == sort2) { - destReg = regNumber(parsedLine[2], destSort); + destReg = regNumber(parsedLine[2], destSort, errors); mCode[*IC].word.code->destReg = destReg; } setOperandLabel(destSort, sourceSort, labelName, mCode, parsedLine, IC, f->operands); @@ -548,18 +559,32 @@ void errorHandler(int *errors, char *currLine) { checkMalloc(lineForErrorHandling); stringCopy(lineForErrorHandling, currLine); - while (lineForErrorHandling[i] != '\0'){ - if (lineForErrorHandling[i] == ','){ - if (isComma == TRUE){ + while (lineForErrorHandling[i] != '\0') { + if (lineForErrorHandling[i] == ',') { + if (isComma == TRUE) { *errors += 1; - printf("--->Too many commas in 1 line\n"); + printf("%d --->Too many commas in 1 line\n", lineNum); } isComma = TRUE; } i++; } - i = 0; - + if (strstr(lineForErrorHandling, ".string")) { + i = 0; + isComma = FALSE; + while (lineForErrorHandling[i] != '\0') { + if (lineForErrorHandling[i] == '"' && isComma == FALSE) { + isComma = TRUE; + i++; + continue; + } + if (isComma == TRUE && lineForErrorHandling[i] == '"'){ + return; + } + i++; + } + printf("%d --->String not declared properly\n", lineNum); + } } /** diff --git a/misc/utils.h b/misc/utils.h index aefb321..a3ce1e1 100644 --- a/misc/utils.h +++ b/misc/utils.h @@ -1,6 +1,7 @@ #ifndef _UTILS_ #define _UTILS_ +int lineNum; /* utils */ void swapLastCharIfNewLine(char *string); @@ -42,7 +43,7 @@ void setARE(int IC, machineCode *mCode, unsigned char A, unsigned char R, unsign void setAdditionalLines(machineCode *mCode, long *IC, sortType sort, int *L, char *operand); -int regNumber(char *reg, sortType sort); +int regNumber(char *reg, sortType sort, int *errors); void setOperandLabel(sortType destSort, sortType sourceSort, const char *labelName, machineCode *mCode, char **parsedLine, const long *IC, int operands); diff --git a/passes/first_pass.c b/passes/first_pass.c index 30d90a5..808e893 100644 --- a/passes/first_pass.c +++ b/passes/first_pass.c @@ -44,7 +44,7 @@ int codeDataOrString(char *line, machineCode *mCode, long *DC, bool withLabel, c strtok(tempLine, "”"); tempLine = strtok(NULL, ""); if (tempLine == NULL) { - printf("--->No characters after .string declaration\n"); + printf("%d --->No characters after .string declaration or string undeclared properly\n", lineNum-1); *errors += 1; return 0; } @@ -85,7 +85,7 @@ int codeDataOrString(char *line, machineCode *mCode, long *DC, bool withLabel, c tempLine = strtok(tempLine, ".data"); } if (tempLine == NULL) { - printf("--->No data after .data declaration\n"); + printf("%d --->No data after .data declaration\n", lineNum); *errors += 1; return 0; } @@ -163,7 +163,7 @@ bool labelAndDirectiveStep(char *line, symbol *head, long *IC, long *DC, if (assertLabelProperDeclaration(line) == FALSE) { *errors += 1; swapLastCharIfNewLine(line); - printf("--->Undefined label: %s\n", line); + printf("%d --->Undefined label: %s\n", lineNum, line); return FALSE; } } @@ -280,16 +280,19 @@ bool firstPass(char *line, FILE *inp, int *errors, char *outPutFileName) { if (is == TRUE) { stringCopy(line, iterator(line, inp, errors)); errorHandler(errors, line); + lineNum++; continue; } if (checkIfEntryOrExtern(line) == 2) { /*extern*/ externStep(line, head, errors, zero); stringCopy(line, iterator(line, inp, errors)); errorHandler(errors, line); + lineNum++; continue; } else if (checkIfEntryOrExtern(line) == 1) { stringCopy(line, iterator(line, inp, errors)); errorHandler(errors, line); + lineNum++; continue; } /*entry - doing nothing first pass*/ @@ -305,6 +308,7 @@ bool firstPass(char *line, FILE *inp, int *errors, char *outPutFileName) { if (parsedLine == NULL) { stringCopy(line, iterator(line, inp, errors)); errorHandler(errors, line); + lineNum++; continue; } parseCmd(parsedLine, errors, tempLine, mCode, &IC, labelName); @@ -314,6 +318,7 @@ bool firstPass(char *line, FILE *inp, int *errors, char *outPutFileName) { } stringCopy(line, iterator(line, inp, errors)); errorHandler(errors, line); + lineNum++; } printf("===>>>>>> First pass finished: Errors: %d\n", *errors); diff --git a/passes/pre_assembler.c b/passes/pre_assembler.c index 46904d5..365f45f 100644 --- a/passes/pre_assembler.c +++ b/passes/pre_assembler.c @@ -1,6 +1,5 @@ #include "../misc/definitions.h" #include "../misc/utils.h" -#include "../misc/parsers.h" /** * add macro to the macro's table during pre-assembler @@ -74,10 +73,11 @@ void preAssembler(char *line, int *errors, FILE *inp, FILE *outP, macroTable *ta stringCopy(macroName, strtok(NULL, ":")); if (macroName[strlen(macroName) - 1] == '\n') macroName[strlen(macroName) - 1] = '\0'; while ((fgets(line, 80, inp)) != NULL) { /* read from .as file and save macro data */ + lineNum++; if (*line == '\n') continue; if (strlen(line) > 80) { errors += 1; - printf("--->line to long\n"); + printf("%d --->line to long\n", lineNum); continue; } if (strstr(line, "endm")) { diff --git a/passes/second_pass.c b/passes/second_pass.c index 7ed7a8b..8203448 100644 --- a/passes/second_pass.c +++ b/passes/second_pass.c @@ -388,7 +388,7 @@ void assertLabelsDeclaration(int *errors, machineCode *mCode, const long *IC, sy found = checkLabel(mCode[i].labelUsageSource, tempNode, found, errors); if (*errors > err) { err = *errors; - printf("--->Usage of undeclared label found: %s, error\n", mCode[i].labelUsageSource); + printf("--->Usage of undeclared label found: %s, error\n" , mCode[i].labelUsageSource); } tempNode = head; found = checkLabel(mCode[i].labelUsageDest, tempNode, found, errors); diff --git a/ps4.as b/ps4.as index 9613570..b1b701f 100644 --- a/ps4.as +++ b/ps4.as @@ -5,4 +5,5 @@ jpr A ABC DCA mov #1, R23 clr 1 -clr REG \ No newline at end of file +clr REG +.string "aaaaaa \ No newline at end of file diff --git a/ps7.as b/ps7.as index 6a61e9e..225e8d0 100644 --- a/ps7.as +++ b/ps7.as @@ -4,4 +4,6 @@ clr A, , #$%#@$%@#$#@ r1 r2 MAIN: -jsr \ No newline at end of file +jsr +mov x[r9], r4 +mov #4, r32 \ No newline at end of file