From ffc66ad59ee7cb0ce4079dbdffe570bfc525b3fa Mon Sep 17 00:00:00 2001 From: unknown Date: Fri, 28 May 2021 17:23:22 +0545 Subject: [PATCH] Improve error details --- README.md | 4 +++- src/Storm/error.py | 16 +++++++++++----- src/Storm/lexer.py | 26 ++++++++++---------------- src/Storm/position.py | 18 ++++++++++++++++++ 4 files changed, 42 insertions(+), 22 deletions(-) create mode 100644 src/Storm/position.py diff --git a/README.md b/README.md index b1b43b9..81f73be 100644 --- a/README.md +++ b/README.md @@ -1,2 +1,4 @@ # Storm -A Compiler made from scratch using Python + + +Storm is a basic programming language implemented with the help of Python. \ No newline at end of file diff --git a/src/Storm/error.py b/src/Storm/error.py index 8b91d2d..7f7b387 100644 --- a/src/Storm/error.py +++ b/src/Storm/error.py @@ -1,14 +1,20 @@ class Error: - def __init__(self, error_name, error_details = None) -> None: + def __init__(self, file_name, line_number, error_name, error_details = None) -> None: + self.file_name = file_name + self.line_number = line_number self.error_name = error_name self. error_details = error_details def __repr__(self) -> str: - if self.error_details != None: return f'{self.error_name} \n Details : {self.error_details}' - return f'{self.error_name}' + if self.file_name != None: + error_info = f'{self.error_name} in line {self.line_number} of {self.file_name}' + else: + error_info = f'{self.error_name} in line {self.line_number}' + if self.error_details != None: return f'{error_info}\n Details : {self.error_details}' + return f'{error_info}' class ErrorIllegalChar(Error): - def __init__(self, details) -> None: - super().__init__('Illegal Character Deteted', details) + def __init__(self,file_name, line_number, details) -> None: + super().__init__(file_name, line_number,'Illegal Character Detected', details) \ No newline at end of file diff --git a/src/Storm/lexer.py b/src/Storm/lexer.py index 702b2e6..e783a22 100644 --- a/src/Storm/lexer.py +++ b/src/Storm/lexer.py @@ -1,30 +1,28 @@ from Storm import token -from Storm.type import * +from Storm.type import get_number_type, get_type from Storm.token import Token from Storm.type import get_type -from Storm.error import * +from Storm.error import ErrorIllegalChar +from Storm.position import Position class Lexer: - def __init__(self, text) -> None: + def __init__(self, text, file_name = None) -> None: + self.file_name = file_name self.text = text - self.pos = -1 + self.pos = Position(-1, 1, -1, self.file_name, self.text) self.cur_char = None def __increment(self): - self.pos += 1 - self.cur_char = self.text[self.pos] if self.pos < len(self.text) else None - - def __decrement(self): - self.pos -= 1 - self.cur_char = self.text[self.pos] if self.pos < 0 else None + self.pos.increment(self.cur_char) + self.cur_char = self.text[self.pos.index] if self.pos.index < len(self.text) else None def make_tokens(self): list_tokens = [] self.__increment() while self.cur_char != None: - if self.cur_char in " \t": + if self.cur_char in " \t\n": self.__increment() else: token_type = get_type(self.cur_char) @@ -34,11 +32,8 @@ def make_tokens(self): elif token_type == 'DIGIT': token_type, value = self.make_numbers() list_tokens.append(Token(token_type, value)) - self.__increment() else: - return [], ErrorIllegalChar(self.cur_char) - - + return [], ErrorIllegalChar(self.file_name, self.pos.line_number, f'Invalid character \'{self.cur_char}\' found') return list_tokens, None def make_numbers(self): @@ -53,7 +48,6 @@ def make_numbers(self): elif char_type == "DIGIT": num_str += str(self.cur_char) else: - self.__decrement() break self.__increment() return get_number_type(num_str), num_str diff --git a/src/Storm/position.py b/src/Storm/position.py new file mode 100644 index 0000000..bd2a50c --- /dev/null +++ b/src/Storm/position.py @@ -0,0 +1,18 @@ +class Position: + def __init__(self, index, line_number, column, file_name, file_content) -> None: + self.index = index + self.line_number = line_number + self.column = column + self.file_name = file_name + self.file_content = file_content + + def increment(self, cur_char): + self.index += 1 + self.column += 1 + if cur_char == "\n": + self.line_number += 1 + self.column = 0 + return self + + def copy(self): + return Position(self.index, self.line_number, self.line_number, self.file_name, self.file_content)