Пример #1
0
 def enterFinal_method_expression(self, ctx:VYPParser.Final_method_expressionContext):
     lastExpression = self.expressionStack.pop()
     if not isinstance(lastExpression.dataType, ClassSymbol):
         raise SemanticGeneralError(f"Cannot invoke method on non-object data type '{lastExpression.dataType}'")
     symbol = lastExpression.dataType.getMethod(ctx.function_call().ID().getText())
     if symbol is None:
         raise SemanticGeneralError(f"Method '{ctx.function_call().ID().getText()}' is not defined in class '{lastExpression.dataType.id}'")
     expression = VariableExpression(symbol.dataType, symbol.id)
     self.expressionStack.append(lastExpression)
     self.nestedObjectStack[-1].append(lastExpression)
Пример #2
0
 def getObjectFromReference(self, reference):
     if reference == 'this':
         if self.currentClass is None:
             raise SemanticGeneralError("Cannot access 'this' reference outside of class definition")
         self.codeGenerator.generateVariableExpression(self.currentFunction, reference)
         return self.currentClass
     if reference == 'super':
         if self.currentClass is None:
             raise SemanticGeneralError("Cannot access 'super' reference outside of class definition")
         self.codeGenerator.generateVariableExpression(self.currentFunction, 'this')
         return self.currentClass.parent
     symbol = self.localSymbolTable.getSymbol(reference)
     self.codeGenerator.generateVariableExpression(self.currentFunction, symbol.codeName)
     return symbol.dataType
Пример #3
0
 def enterFinal_field_expression(self, ctx:VYPParser.Final_field_expressionContext):
     lastExpression = self.expressionStack.pop()
     if lastExpression.id == 'super':
         raise SemanticGeneralError(f"Cannot invoke variable on 'super' reference")
     if not isinstance(lastExpression.dataType, ClassSymbol):
         raise SemanticGeneralError(f"Cannot invoke variable on non-object data type '{lastExpression.dataType}'")
     symbol = lastExpression.dataType.getField(ctx.ID().getText())
     if symbol is None:
         raise SemanticGeneralError(f"Field '{ctx.ID().getText()}' is not defined in class '{lastExpression.dataType.id}'")
     expression = VariableExpression(symbol.dataType, symbol.id)
     if not isinstance(ctx.parentCtx.parentCtx.parentCtx, VYPParser.Instance_assignmentContext):
         self.codeGenerator.generateFieldExpression(self.currentFunction, self.nestedObjectStack[-1][-1].dataType, symbol.id, 0)
         pass
     self.expressionStack.append(expression)
     self.nestedObjectStack[-1].append(expression)
Пример #4
0
    def exitReturn_statement(self, ctx: VYPParser.Return_statementContext):
        if self.currentClass == None:
            currentFunction = self.functionTable.getSymbol(self.currentFunctionId)
        else:
            currentFunction = self.currentClass.methodTable.getSymbol(self.currentFunctionId)
        if ctx.expression() is None:
            if currentFunction.dataType != 'void':
                raise SemanticGeneralError(f"Return statement must contain expression for non-void functions")
            self.codeGenerator.generateReturnValue(self.currentFunction, False)
            return
        if currentFunction.dataType == 'void':
            raise SemanticGeneralError(f"Void functions cannot return expression")

        returnExpression = self.expressionStack.pop()
        self.semanticsChecker.checkVariableAssignment(currentFunction.dataType, returnExpression.dataType)
        self.currentFunctionReturn = True
        setReturnValue = currentFunction.dataType != 'void'
        self.codeGenerator.generateReturnValue(self.currentFunction, setReturnValue)
 def updateFuntionTypesHelper(self, functionList):
     for function in functionList:
         if function.ownerClass == function.id:
             if function.dataType != 'void' or len(
                     function.parameterList) != 0:
                 raise SemanticGeneralError("Wrong constructor definition")
         if function.dataType not in ['int', 'void', 'string']:
             classSymbol = self.classTable.getSymbol(function.dataType)
             function.dataType = classSymbol
         self.updateFunctionParameterList(function.parameterList)
 def enterMultiple_variable_definition(
         self, ctx: VYPParser.Multiple_variable_definitionContext):
     definitionSymbol = GeneralSymbol(
         ctx.ID().getText(), SymbolType.VARIABLE,
         ctx.parentCtx.variable_type().getText(), ctx.start.line,
         ctx.start.column)
     self.localSymbolTable.addSymbol(ctx.ID().getText(), definitionSymbol)
     if self.functionTable.isSymbolDefined(
             ctx.ID().getText()) or self.classTable.isSymbolDefined(
                 ctx.ID().getText()):
         raise SemanticGeneralError(
             f"Symbol with id: {ctx.ID().getText()} is already defined")
     self.codeGenerator.defineVariable(definitionSymbol.codeName,
                                       self.currentFunction,
                                       definitionSymbol.dataType)
 def enterVariable_definition(self,
                              ctx: VYPParser.Variable_definitionContext):
     variableType = ctx.variable_type().getText() if ctx.variable_type(
     ).getText() in ['int', 'string'] else self.classTable.getSymbol(
         ctx.variable_type().getText())
     definitionSymbol = GeneralSymbol(ctx.ID().getText(),
                                      SymbolType.VARIABLE, variableType,
                                      ctx.start.line, ctx.start.column)
     self.localSymbolTable.addSymbol(ctx.ID().getText(), definitionSymbol)
     if self.functionTable.isSymbolDefined(
             ctx.ID().getText()) or self.classTable.isSymbolDefined(
                 ctx.ID().getText()):
         raise SemanticGeneralError(
             f"Symbol with id: {ctx.ID().getText()} is already defined")
     self.codeGenerator.defineVariable(definitionSymbol.codeName,
                                       self.currentFunction, variableType)
Пример #8
0
 def defineField(self, variableSymbol: GeneralSymbol):
     if self.getField(variableSymbol.id):
         raise SemanticGeneralError(
             f"Redefinition of field \'{variableSymbol.id}\' in class \'{self.id}\'"
         )
     self.fieldTable.addSymbol(variableSymbol.id, variableSymbol)
 def exitProgram(self, ctx):
     mainSymbol = self.functionTable.getSymbol('main')
     if mainSymbol.dataType != 'void' or len(mainSymbol.parameterList) != 0:
         raise SemanticGeneralError("Wrong definition of 'main' function")
     self.updateFunctionTypes()
 def enterMultiple_field_definition(
         self, ctx: VYPParser.Multiple_field_definitionContext):
     if self.currentClass.methodTable.isSymbolDefined(ctx.ID().getText()):
         raise SemanticGeneralError(
             f"There is already method with id: {ctx.ID().getText()} defined"
         )