aboutsummaryrefslogtreecommitdiff
path: root/compilador
diff options
context:
space:
mode:
authorIván Ávalos <avalos@disroot.org>2022-11-22 09:02:46 -0600
committerIván Ávalos <avalos@disroot.org>2022-11-22 09:02:46 -0600
commit032fe000cfc2b36dc9c1f00c734fada41133403e (patch)
treecc489901762fe26dbe1253f7a4f2dca55956f89a /compilador
parent86c099629fad439402a51f031e3cb5507bc92278 (diff)
downloadjavanol-032fe000cfc2b36dc9c1f00c734fada41133403e.tar.gz
javanol-032fe000cfc2b36dc9c1f00c734fada41133403e.tar.bz2
javanol-032fe000cfc2b36dc9c1f00c734fada41133403e.zip
Se implementa semáforo (fases de compilación)
Diffstat (limited to 'compilador')
-rw-r--r--compilador/lexer.py21
-rw-r--r--compilador/main.py49
-rw-r--r--compilador/parser.py10
-rw-r--r--compilador/tabla.py11
4 files changed, 66 insertions, 25 deletions
diff --git a/compilador/lexer.py b/compilador/lexer.py
index bc2b14a..8bb7c13 100644
--- a/compilador/lexer.py
+++ b/compilador/lexer.py
@@ -34,7 +34,7 @@ class Selector(Enum):
ENTERO = 5
class Lexer:
- def __init__(self, data, input_file):
+ def __init__(self, input_file: str):
self.tabla = TablaLex()
self.numlinea = 1
self.selector = Selector.NINGUNO
@@ -44,26 +44,23 @@ class Lexer:
self.recol_operador = ''
self.recol_ident = ''
self.recol_entero = ''
- self.data = data
- self.tabla_file = None
- if input_file:
- self.tabla_file = input_file + '.tab'
+ self.input_file = input_file
+ with open(input_file) as f:
+ self.data = f.read()
def inicio(self):
for l in self.data.splitlines():
for c in l + "\n":
r = self.procesar(c)
- if r == Control.ERROR: exit(1)
+ if r == Control.ERROR: return 1
while r != Control.SIGUIENTE:
r = self.procesar(c)
- if r == Control.ERROR: exit(1)
+ if r == Control.ERROR: return 1
self.numlinea += 1
- # Imprimir tabla de símbolos
- if self.tabla_file:
- self.tabla.exportar(self.tabla_file)
- Parser(self.tabla).inicio()
-
+ # Exportar tabla de símbolos
+ self.tabla.exportar(self.input_file + '.tab')
+ return 0
def procesar(self, c):
# if c != "\t" and c != "\n":
diff --git a/compilador/main.py b/compilador/main.py
index 186ca83..98e23c9 100644
--- a/compilador/main.py
+++ b/compilador/main.py
@@ -1,21 +1,30 @@
-import sys, getopt
+import sys, getopt, os, traceback
+from enum import Enum
from tkinter import *
from tkinter import ttk, filedialog
from lexer import *
+class Step(Enum):
+ LEXICO = 0
+ SINTACTICO = 1
+ SEMANTICO = 2
+
class Main:
input_file = None
output_file = None
output_table = False
+ step = None
def print_help (self, arg0):
print("Uso: % s -i entrada.es -o salida.es" % arg0)
- print(" % s -i entrada.es -o salida.es -t")
+ print(" % s -i entrada.es -o salida.es [-l|-p|-s] [-t]" % arg0)
print(" % s -h" % arg0)
def main(self, argv):
try:
- opts, args = getopt.getopt(argv[1:], "hi:o:t", ["input=", "output=", "table"])
+ opts, args = getopt.getopt(argv[1:], "hi:o:lpst", [
+ "input=", "output=", "lex", "parse", "semantic", "table"
+ ])
except getopt.GetoptError as err:
print(err)
print_help(argv[0]);
@@ -30,16 +39,40 @@ class Main:
self.output_file = a
elif o in ("-t", "--table"):
self.output_table = True
+ elif o in ("-l", "--lex"):
+ self.step = Step.LEXICO
+ elif o in ("-p", "--parse"):
+ self.step = Step.SINTACTICO
+ elif o in ("-s", "--semantic"):
+ self.step = Step.SEMANTICO
else:
assert False, "opción desconocida"
if self.input_file and self.output_file:
- with open(self.input_file) as f:
- data = f.read()
- if self.output_table:
- Lexer(data, self.input_file).inicio()
+ table_file = self.input_file + '.tab'
+ delete_tab = not self.step and not self.output_table and not os.path.exists(table_file)
+ try:
+ if self.step == Step.LEXICO:
+ sys.exit(Lexer(self.input_file).inicio())
+ elif self.step == Step.SINTACTICO:
+ sys.exit(Parser(self.input_file).inicio())
+ elif self.step == Step.SEMANTICO:
+ print("NOT IMPLEMENTED")
+ sys.exit(1)
else:
- Lexer(data, None).inicio()
+ if Lexer(self.input_file).inicio() != 0:
+ raise Exception("Error léxico")
+ if Parser(self.input_file).inicio() != 0:
+ raise Exception("Error sintáctico")
+ except Exception as e:
+ traceback.print_exception(type(e), e, e.__traceback__)
+ sys.exit(1)
+ # Borrar tabla de símbolos
+ if delete_tab:
+ os.remove(table_file)
+ else:
+ self.print_help(argv[0])
+ sys.exit(2)
if __name__ == "__main__":
Main().main(sys.argv)
diff --git a/compilador/parser.py b/compilador/parser.py
index 6c6d223..951b517 100644
--- a/compilador/parser.py
+++ b/compilador/parser.py
@@ -23,24 +23,26 @@ class Selector(Enum):
FUNCION = 7
class Parser:
- def __init__(self, tabla):
+ def __init__(self, input_file: str):
self.arbol = Arbol()
self.pila_selector = [
[Selector.NINGUNO, []] # selector, recolector
]
self.pila_arbol = [self.arbol.raiz]
self.expresion = None
- self.tabla = tabla
+ self.tabla = TablaLex()
+ self.tabla.importar(input_file + '.tab')
def inicio (self):
for t in self.tabla.tabla:
r = self.procesar(t)
- if r == Control.ERROR: exit(1)
+ if r == Control.ERROR: return 1
while r != Control.SIGUIENTE:
r = self.procesar(t)
- if r == Control.ERROR: exit(1)
+ if r == Control.ERROR: return 1
print(str(self.arbol))
+ return 0
def procesar (self, t: LexToken):
if len(self.pila_selector) == 0:
diff --git a/compilador/tabla.py b/compilador/tabla.py
index 637b9a6..ebe6225 100644
--- a/compilador/tabla.py
+++ b/compilador/tabla.py
@@ -70,7 +70,7 @@ class TablaLex:
data.append({
'tipo': t.tipo,
'nombre': t.nombre,
- 'valor': str(t.valor),
+ 'valor': t.valor,
'numlinea': t.numlinea
})
output = json.dumps(data)
@@ -80,6 +80,15 @@ class TablaLex:
f.truncate(0)
f.write(output)
+ def importar(self, input_file):
+ with open(input_file, 'r') as f:
+ data = json.loads(f.read())
+ for t in data:
+ self.insertar(LexToken(t['tipo'],
+ t['nombre'],
+ t['valor'],
+ t['numlinea']))
+
def __str__(self):
output = ""
for t in self.tabla: