示例#1
0
文件: LoadObj.py 项目: sofayam/m3
def load(filename, obj=None):
    parser = xml.sax.make_parser()
    nh = NodeHandler()
    parser.setContentHandler(nh)
    if not os.path.exists(filename):
        # try looking in the predefined library
        base = os.path.basename(filename)
        libfilename = string.join(
            [os.environ['M3_HOME'], 'lib', 'm3lib', base], os.sep)
        if not os.path.exists(libfilename):
            error("%s does not exist" % filename,
                  catastrophic=True,
                  obj=obj,
                  code="CAT001")
        else:
            #print "got library file %s" % libfilename
            filename = libfilename

    parser.parse(filename)
    tn = nh.topNode
    #    tn.resolveRefs()
    tn.visit(lambda x: x.restoreSlots())
    if os.path.exists(tn.source):
        sourcetime = os.stat(tn.source)[stat.ST_MTIME]
        objtime = os.stat(filename)[stat.ST_MTIME]
        if sourcetime > objtime:
            import LoadSrc
            print "Recompiling %s from %s" % (
                filename, relpath.relcwd(tn.source))  #OK
            tn = LoadSrc.load(fileName=tn.source)
    return tn
示例#2
0
    def generateC(self, saveOutput):
        if saveOutput:
            s = open(self.getCFileBaseName() + ".c", "w")
        else:
            s = FakeFile()
        s.write('#include "M3Predef.h"\n')
        exps = self.getExports()
        if exps != []:
            s.write('#include "%s.h"\n' % self.modname.idname)
        for imp in self.imports.kids:
            imp.genC(s)
        if not self.exportIds.isNULL():
            error("%s for explicit exports" % nocando, self)
        else:
            # Variables in interfaces need to be shifted down into the body (extern left in the header)
            if len(exps) == 1:
                expXML = m3.compile(fileName=exps[0] + "." +
                                    CompilationUnit.unitTypeNames["Interface"],
                                    saveOutput=saveOutput)
                expXML.generateCBody(s)

        self.block.genC(s, 0, module=True)
        if Options.options.mainProgram and saveOutput:
            mp = open(self.getCFileBaseName() + "__main.c", "w")
            myname = self.modname.idname
            mods = CompOrder.getCClosure(myname)
            mp.write("int main() { \n")
            for mod in mods:
                if mod != myname:
                    mp.write("   %s__elaboration();\n" % mod)
            mp.write("   %s__elaboration();\n};\n" % myname)
            mp.close()
示例#3
0
 def genCRecord(self, tipe):
     # start with a row of empty boxes
     fields = [None] * len(tipe.fields)
     # populate boxes with defaults
     for ctr, field in enumerate(tipe.fields):
         if field.default:
             fields[ctr] = field.defaultNode.genC()
     positional = True  # start processing constructor in positional mode
     for ctr, kid in enumerate(self.kidsNoSep()):
         if positional:
             if kid.__class__.__name__ == "ConsEltExprNode":
                 fields[ctr] = kid.genC()
             else:
                 positional = False
         if not positional:
             # place the named field into the right box
             fields[tipe.offsetForFieldName(
                 kid.id.idname)] = kid.expr.genC()
     for ctr, field in enumerate(fields):
         # catch incomplete case (box will still be empty)
         if field == None:
             error(
                 "C Code - incomplete constructor, missing value for field %s"
                 % tipe.fields[ctr].name)
             return ""
     # finally generate the completed aggregate
     return string.join(fields, ",")
示例#4
0
文件: LoadSrc.py 项目: sofayam/m3
def load(fileName=None, src=None, patchFileName=None):
    if not (fileName or src):
        raise "Catastrophic problem with load - neither a fileName nor a sourcefile"
    p = m3parser.Parser()
    p.verbose = int(Options.options.verbosity)
    if fileName:
        if not os.path.exists(fileName):
            error("File %s does not exist" % fileName)
            return
        f = open(fileName)
        txt = f.read()
    else:
        txt = src
    txt = compro.commentkiller(txt)
    txt = compro.umlautkiller(txt)
    if Options.options.errorTest:
        Errors.findDirective(txt)
    try:
        topNode = p(txt)
    except tpg.SyntacticError, e:
        error(e.msg,
              None,
              fileName or patchFileName,
              e.line,
              catastrophic=True,
              code="CAT002")
        raise
示例#5
0
 def check(actuals,obj):
     tipe1 = actuals[0]['tipe']
     tipe2 = actuals[1]['tipe']
     if not tipe1.fits(tipe2):
         error("Arguments to %s must be identical type" % functionName, obj, code="027")
     if not (tipe1.isOrdinal or tipe1.isReal):
         error("Arguments to %s must be ordinal or real" % functionName, obj, code="028")
     return tipe1
示例#6
0
def doVAL(actuals, obj):
    val = actuals[0]['tipe']
    if not val.isInteger:
        error("VAL called with first argument of non-integer type %s" % val, obj,code="019")
    tipe = actuals[1]['tipe']
    if not tipe.isOrdinal:
        error("VAL called with second argument of non-ordinal type %s" % tipe, obj,code="018")
    return tipe
示例#7
0
def doAPPEND(actuals, obj):
    listType = actuals[0]['tipe']
    if not listType.isList:
        error("APPEND called with non-list as first argument", obj)
    else:    
        eltType = actuals[1]['tipe']
        if eltType != listType.elementType:
            error("Attempted APPEND of type %s to LIST of type %s" % (eltType,listType), obj)
    return M3Types.M3ProcedureNullReturn    
示例#8
0
 def genC(self):
     tipe = self.tipe.getType()
     if tipe.isArray:
         return "{ %s }" % self.consEltList.genCArray(tipe.length())
     elif tipe.isRecord:
         return "{ %s }" % self.consEltList.genCRecord(tipe)
     else:
         error("%s constructor not supported for this type (yet)" % nocando,
               self)
示例#9
0
 def genCNEW(self, res):
     # only handle the first item in the selector list (LIMITATION)
     param = self.selectorList.kids[0].actualList.kids[0].expr.expr
     nodename = param.__class__.__name__
     if nodename == "RefNode":
         return "%s(%s)" % (res, param.tipe.genC())
     elif nodename == "TypeNameNode":
         return "%s(%s__REFERENT)" % (res, param.genC())
     else:
         error("%s NEW parameter too complex (%s)" % (nocando, nodename),
               self)
示例#10
0
文件: LUT.py 项目: sofayam/m3
 def enterOver(self, name, entry, obj):
     import Lexis
     if name in Lexis.reservedWords:
         error("%s is a reserved word" % name, obj, code="001")
     if name in self.table:
         if self.table[name].declarer != "TYPE":
             error("Procedure %s declared more than once" % name,
                   obj,
                   code="002")
         entry.spec = self.table[name]
         # TBD squirrel the spec away so you can check the match once everything is ready (but not yet)
     self.table[name] = entry
示例#11
0
def doNUMBER(actuals,obj):
    val = actuals[0]['val']
    tipe = actuals[0]['tipe']

    if tipe.isOrdinal and hasattr(val,"isType"):
        pass
    elif tipe.isList and not hasattr(val,"isType"):
        pass
    elif tipe.isArray:
        pass
    else:
        error("NUMBER can only be called on Ordinal and ARRAY types or ARRAY and LIST values", obj, code="023")
    return M3Types.M3IntegerBase                
示例#12
0
def getCCodeName(tipe, self):
    if hasattr(tipe, "CCodeName"):
        tipestr = tipe.CCodeName
    elif tipe.isBoolean:
        tipestr = "M3Predef__BOOLEAN"
    elif tipe.isInteger or tipe.isEnum:
        tipestr = "M3Predef__INTEGER"
    elif tipe.isReal:
        tipestr = "M3Predef__REAL"
    else:
        error("%s deriving C name for type '%s'" % (nocando, self.regen()),
              self)
        tipestr = "ERROR"
    return tipestr
示例#13
0
def doLimit(actuals, obj, name):
    val = actuals[0]['val']
    tipe = actuals[0]['tipe']
    if tipe.isArray:
        return tipe.indexType or M3Types.M3IntegerBase
    elif tipe.isList:
        if hasattr(val,"isType"):
           error("LAST not allowed on LIST types", obj)
        return M3Types.M3IntegerBase
    elif tipe.isOrdinal:
        return tipe
    else:
        error("Cannot use %s on type %s" % (name, tipe), obj, code="021")
        return tipe
示例#14
0
def doINDEX(actuals, obj):
    def checkElement(container,containerName, elementType):
        if not container.elementType.fits(elementType):
            error("2nd Argument of INDEX for this %s must be %s" % (containerName,container.elementType), obj)
    containerType = actuals[0]['tipe']
    elementType = actuals[1]['tipe']
    
    if containerType.isList:
        checkElement(containerType, "LIST", elementType)
        return M3Types.M3IntegerBase        
    elif containerType.isDict:
        checkElement(containerType, "DICT", elementType)        
        return containerType.indexType
    else:
        error("INDEX only allowed with LIST or DICT as 1st argument", obj)
    return M3Types.M3ProcedureNullReturn
示例#15
0
文件: LUT.py 项目: sofayam/m3
 def getTipe(self, root=None):
     #print "root", root
     if not self.finalTipe:
         if self.findingType:
             self.finalTipe = M3Types.M3ErrorType(
                 error("Recursive type definition (ask FJG for coaching)",
                       self.node))
         else:
             self.findingType = True  # detects recursive type definitions
             self.finalTipe = self.node.getType()
             self.findingType = False
     return self.finalTipe
示例#16
0
文件: LUT.py 项目: sofayam/m3
 def lookupEntry(self, name, obj=None, errorOnMissing=True):
     import Lexis
     import M3Reserved
     #print "looking up %s" % name
     res = None
     if name in Lexis.reservedWords:
         res = M3Reserved.getEntry(name, obj)
     elif name in self.table:
         res = self.table[name]
     else:
         enclut = self.getEnclosingLUT()
         if enclut:
             res = enclut.lookupEntry(name, obj, errorOnMissing)
     if not res and errorOnMissing:
         err = error("Unknown Identifier %s" % name, obj, code="005")
         res = LUTEntry(tipe=M3Types.M3ErrorType(err))
     return res
示例#17
0
def doDEL(actuals, obj):
    listType = actuals[0]['tipe']
    toDel = actuals[1]['tipe']
    if listType.isList:
        if not toDel.isInteger:
            error("2nd Argument of DEL for a LIST must be an INTEGER")
    elif listType.isDict:
        if not listType.indexType.fits(toDel):
            error("2nd Argument of DEL for a DICT should be %s and not %s" % (listType.indexType,toDel))
    else:
        error("DEL only allowed with LIST or DICT as 1st argument", obj)
    return M3Types.M3ProcedureNullReturn
示例#18
0
    def genC(self):
        myOp = self.token
        unchanged = ("+", "-", "*", "/", ">", "<", ">=", "<=")

        opDict = {
            "=": "==",
            "#": "!=",
            "AND": "&&",
            "OR": "||",
            "NOT": "!",
            "DIV": "/",
        }
        if myOp in unchanged:
            return myOp
        elif myOp in opDict:
            return opDict[myOp]
        else:
            return error("%s for operator %s" % (nocando, myOp), self)
示例#19
0
文件: LUT.py 项目: sofayam/m3
 def enter(self, name, entry, obj=None):
     import Lexis
     #print "Enter %s with entry %s" % (name, entry.image())
     if name in Lexis.reservedWords:
         error("%s is a reserved word" % name, obj, code="001")
     if name in Lexis.pythonReservedWords:
         error("%s is a python reserved word" % name, obj)
     if name in self.table:
         #self.dump()
         error("%s already declared" % name, obj, code="004")
     if entry.__class__.__name__ != "LUTEntry":
         raise "Only LUTEntries allowed"
     entry.name = name
     self.table[name] = entry
示例#20
0
def doSUBARRAY(actuals, obj):
    failed = False
    arrayBase = actuals[0]['tipe']
    start = actuals[1]['tipe']
    length = actuals[2]['tipe']
    if not arrayBase.isArray:
        error("SUBARRAY first parameter must be an array",obj, code="032")
        failed = True
    if not start.isInteger:
        error("SUBARRAY second parameter must be an integer",obj, code="033")        
        failed = True
    if not length.isInteger:
        error("SUBARRAY third parameter must be an integer",obj, code="034")
        failed = True
    if failed:
        return M3Types.M3ErrorType("Subarray Error")
    else:
        return M3Types.M3SubArrayType(arrayBase)
示例#21
0
def doISTYPE(actuals, obj):
    ref = actuals[0]['tipe']
    tipe = actuals[0]['tipe']
    if not ((ref.isRef or ref.isObject) and (tipe.isRef or tipe.isObject)):
        error("ISTYPE can only be called with references or objects", obj, code="030")
    return M3Types.M3Boolean
示例#22
0
def doKEYS(actuals, obj):
    dictType = actuals[0]['tipe']
    if not dictType.isDict:
        error("KEYS called with non-dict argument", obj)    
    return M3Types.M3ListType(dictType.indexType)
示例#23
0
def doNEW(actuals,obj):
    tipe = actuals[0]['tipe']
    
    if not (tipe.isRef or tipe.isObject):
        error("NEW called on non-reference/object type %s" % tipe,  obj, code="006")
    elif tipe.isObject:
        
        for actual in actuals[1:]:
            actname = actual['name']
            if not actname:
                error("Arguments to NEW for object must be named",obj, code="007")
                break
            #print "name is", name
            acttipe = actual['tipe']
            field = tipe.getFieldNewCheck(actname)
#            print field.name, field.tipe, field.default
            if acttipe.isProcedure:
                tipe.checkOverride(actname, acttipe, obj)
            else:
                if not field.tipe.fits(acttipe):
                    error("Type conflict for field '%s' in NEW : actual: %s, formal: %s" % (
                        actname, acttipe, field.tipe), obj, code="010")
    elif tipe.referent.isOpen:
        if len(actuals) <= 1:
            error("Length not supplied for open array", obj,code="011")
        level = tipe.referent
        for dim in actuals[1:]:
            if dim['name']:
                error("Arguments to NEW for array may not be named", obj,code="012")
            if not dim['tipe'].isInteger:
                error("Arguments to NEW for array must be INTEGERs", obj, code="013")
            if level.isOpen:
                level = level.elementType
            else:                
                error("Dimension of array is not open", obj, code="014")
    elif tipe.referent.isObject:
        error("Ref to object currently unsupported (you probably do not mean this anyway!)", obj,code="008")
    elif tipe.referent.isRecord:
        for field in actuals[1:]:
            if not field['name']:
                error("Arguments to NEW for record must be named", obj, code="015")
            if field['name'] not in tipe.referent.fieldnames:
                error("Record does not have field %s" % field['name'], obj, code="016")
            else:
                if not field['tipe'].fits(tipe.referent.fielddict[field['name']].tipe):
                    error("Type mismatch for field %s in allocator" % field['name'], obj, code="009")
    return tipe
示例#24
0
def doPOP(actuals, obj):
    listType = actuals[0]['tipe']
    if not listType.isList:
        error("POP called with non-list argument", obj)
    return listType.elementType
示例#25
0
def doDISPOSE(actuals, obj):
    ref = actuals[0]['tipe']
    if not (ref.isRef or ref.isObject):
        error("DISPOSE can only be called with references or objects", obj, code="031")
    return M3Types.M3ProcedureNullReturn
示例#26
0
def doTYPECODE(actuals, obj):
    tipe = actuals[0]['tipe']
    if not (tipe.isRef or tipe.isObject):
        error("TYPECODE can only be called with references or objects", obj, code="029")
    return M3Types.M3Cardinal
示例#27
0
 def checkElement(container,containerName, elementType):
     if not container.elementType.fits(elementType):
         error("2nd Argument of INDEX for this %s must be %s" % (containerName,container.elementType), obj)
示例#28
0
def doABS(actuals, obj):
    tipe = actuals[0]['tipe']
    if not tipe.isNumeric:
        error("ABS can only be called on numeric types", obj, code="026")
    return tipe
示例#29
0
def doORD(actuals, obj):
    ord = actuals[0]['tipe']
    if not ord.isOrdinal:
        error("ORD called on object of non-ordinal type %s" % ord, obj, code="017")
    return M3Types.M3IntegerBase        
示例#30
0
 def check (actuals, obj):
     tipe = actuals[0]['tipe']
     if not tipe.fits(M3Types.M3RealBase):
         error("%s can only be called on reals" % functionName, obj, code="025")
     return M3Types.M3IntegerBase