示例#1
0
    def editIcon(self, actComp=None):
        '''edit svg file'''
        if self.type == 'symbolView':
            block = actComp
            libname = actComp.libname
            blockname = actComp.blockname
        else:
            libname = self.libraries.currentItem().text()
            blockname = self.cells.currentItem().text()
            block = getBlock(libname, blockname)

        svgiconname = block.icon  #  = svgfilepath
        if svgiconname is None:
            svgiconname = libraries.blockpath(libname,
                                              blockname).rstrip('.py') + '.svg'

        # temp file
        fo = tempfile.NamedTemporaryFile(suffix='.svg', delete=False)
        svgtempfilename = fo.name

        if os.path.isfile(svgiconname):
            with open(svgiconname) as fi:
                t = fi.read()

            #copy to a tempfile
            fo.write(t)
            fo.close()

        updateSvg(block, svgtempfilename)

        timestamp0 = os.stat(svgtempfilename).st_mtime

        try:
            subprocess.call('inkscape {}'.format(svgtempfilename).split())
            timestamp1 = os.stat(svgtempfilename).st_mtime

            if timestamp0 and timestamp0 < timestamp1:  # newer => copy and update
                print('scrubbing', svgtempfilename)
                updateSvg(block, svgtempfilename, makeports=False)
                if not svgiconname.lower().endswith('.svg'):  # old-style icon
                    svgiconname = libraries.blockpath(
                        block.libname, block.blockname).rstrip('.py') + '.svg'
                shutil.move(svgtempfilename, svgiconname)
                print('mv to', svgiconname)
                block.setIcon(svgiconname)
                # register niew view
                blockdir = os.path.dirname(
                    libraries.blockpath(block.libname, block.blockname))
                relpath = os.path.relpath(svgiconname, blockdir)
                block.setView('icon', relpath)

            # creanup tempfile
            if os.path.exists(svgtempfilename):
                os.remove(svgtempfilename)

        except OSError:
            raise Exception('Inkscape is not installed')
示例#2
0
def updateOnDisk(libname, blockname, dd=dict(), writeback=True):
    '''replace assignments with new values for variable names in dd
    and write back to disk'''
    fname = libraries.blockpath(libname, blockname)
    src = []
    with open(fname) as f:
        lines = f.readlines()
        ix = 0
        while ix < len(lines):
            line = lines[ix]
            s = line.replace('=', ' = ').split()
            if len(s) > 2 and line.startswith(
                    s[0]) and s[0] in dd and s[1] == '=':
                # assignment without leading whitespace
                key = s[0]
                while line.endswith('\\\n') or line.strip().endswith(','):
                    ix += 1
                    line = lines[ix]
                # get comment if present
                line, _, cmt = line.partition('#')
                if cmt:
                    cmt = ' # ' + cmt.strip()
                line = '{} = {}\n'.format(key, dd[key], cmt)

            src.append(line)
            ix += 1

    src = ''.join(src)
    if writeback:
        with open(fname, 'wb') as f:
            f.write(src)

    getBlockModule(libname, blockname)  # update module
    return src
示例#3
0
def getBlockModule(libname, blockname, errors=[]):
    '''read python module of block from disk'''
    fpath = libraries.blockpath(libname, blockname)
    blk = import_module_from_source_file(fpath, errors)
    if errors:
        print(errors)
    block_modules[libname + '/' + blockname] = blk
    if blk:
        _addBlockModuleDefaults(libname, blockname)
    return blk
示例#4
0
def instToMyhdl(inst):
    '''returns tuple (text, isimport'''
    libname, blkname = inst['libname'], inst['blockname']
    name = inst['label']['text']  # instance name in diagram

    args = inst['conn']
    # store properties
    if 'properties' in inst:
        args.update(inst['properties'])

    parameters = inst['parameters'] if 'parameters' in inst else dict(
    )  # pcell

    instance_netlist = ''

    # find inst module
    k = libname + '/' + blkname
    try:
        blkMod = blkModuleCache[k]
    except KeyError:
        fname = libraries.blockpath(libname, blkname)
        blkMod = import_module_from_source_file(fname)
        blkModuleCache[k] = blkMod

    # try module.toMyhdlInstance()
    try:
        instance_netlist = blkMod.toMyhdlInstance(name, args, parameters)
        return instance_netlist, False

    except AttributeError:
        if parameters:  # parametrized cell should have netlist function
            message = 'error while netlisting parametrized block {}.{}\n'.format(libname, blkname) + \
                      'function toMyhdlInstance is not present.'
            raise Exception(message)

    if not instance_netlist:  # normal cell netlist
        #instance_netlist = defaultMyHdlInstance(name, libname, blkname, args)
        conns = []
        for pinname, netname in list(args.items()):
            if isinstance(netname, (list, tuple)):
                netname = netname[0]
            conns.append('{} = {}'.format(pinname, netname))
        jj = ',\n' + ' ' * 12
        c = jj.join(conns)
        return '    u_{} = {}{}.{}({})\n'.format(name, libraries.libprefix,
                                                 libname, blkname, c), True
示例#5
0
def _addBlockModuleDefaults(libname, blockname):
    '''add default settings to a loaded block_module'''
    blk = block_modules[libname + '/' + blockname]
    blk.name = blockname
    blk.libname = libname
    blk.textSource = libraries.blockpath(libname, blockname)
    try:
        if not 'icon' in blk.views:
            blk.views['icon'] = None
        if not hasattr(blk, 'bbox'):
            blk.bbox = None
        for pp in ['properties', 'parameters']:
            if not hasattr(blk, pp):
                setattr(blk, pp, dict())
    except Exception as e:
        raise Exception('Block {}.{} raised error {}'.format(
            libname, blockname, str(e)))

    p = libraries.libpath(libname)
    for viewname, (ed, ext) in viewTypes.items():
        fn = os.path.join(p, blockname + ext)
        if os.path.isfile(fn):
            blk.views[viewname] = fn
示例#6
0
    def convertSymAct(self):
        selection = self.scene.items(self.scene.selectionArea())
        if selection and self.scene.selectedItems():
            # blocks, connections, nodes, comments
            blocks = []
            connections = []
            nodes = []
            comments = []

            inp = []
            outp = []
            inout = []
            for item in selection:
                if isinstance(item, Block):
                    blocks.append(str(item.toData()))
                elif isConnection(item):
                    connections.append(str(item.toData()))
                elif isNode(item):
                    nodes.append(str(item.toData()))
                elif isPort(item, 'pin'):
                    item.pinToPort(inp, outp, inout)
                elif isComment(item):
                    comments.append(str(item.toData()))

            dialog = convertSymDialog()
            ret = dialog.getRet()

            if ret:

                name = ret['name']
                icon = ret['icon']

                if self.library.type == 'symbolView':
                    libname = self.library.tabs.tabText(
                        self.library.tabs.currentIndex())
                else:
                    libname = self.library.libraries.currentItem().text()

                ed, ext = viewTypes['diagram']
                views = dict(
                    diagram=os.path.join(libraries.libprefix + libname, name +
                                         ext))
                if icon:
                    views['icon'] = icon
                parameters = dict()
                properties = ret['properties']

                data = templates['block'].format(name=name,
                                                 libname=libname,
                                                 inp=inp,
                                                 outp=outp,
                                                 io=inout,
                                                 bbox=None,
                                                 properties=properties,
                                                 parameters=parameters,
                                                 views=views)

                # save block
                fname = libraries.blockpath(libname, name)
                with open(fname, 'w+') as f:
                    f.write(str(data))

                # save diagram
                ed, ext = viewTypes['diagram']
                fname = strip_ext(fname, '.py') + ext
                self.saveDiagramAs(fname, selection)

                for item in self.scene.selectedItems():
                    try:
                        item.remove()
                    except:
                        pass

#                with open(self.path + '/libraries/library_' + libname + '/' + name + '_diagram.py','w+') as f:
#                    f.write("blocks = [" + ",\n          ".join(blocks) + "]\n\n" +
#                            "connections = [" + ",\n               ".join(connections) + "]\n\n" +
#                            "nodes = [" + ",\n         ".join(nodes) + "]\n\n" +
#                            "comments = [" + ",\n         ".join(comments) + "]")

                center = self.scene.getCenter()
                item = getBlock(libname, name, None, self.scene)
                item.setPos(center[0], center[1])

                if self.library.type == 'symbolView':
                    ix = self.library.tabs.currentIndex()
                    self.library.symbolView()
                    self.library.tabs.setCurrentIndex(ix)
                else:
                    self.library.listView()
                    self.library.libraries.setCurrentItem(
                        self.library.libraries.findItems(
                            'symbols', QtCore.Qt.MatchExactly)[0])
        else:
            error('Select what you want to convert')
示例#7
0
def resolve_connectivity(filename, properties=dict()):

    #import file
    dgm = import_module_from_source_file(filename)

    #==============================================================================
    #   read blocks
    #==============================================================================
    blocks = dict()
    for inst in dgm.blocks:
        inst_name = inst['label']['text']
        blocks[inst_name] = inst

        blockname, libname = inst['blockname'], inst['libname']
        fname = libraries.blockpath(libname, blockname)
        k = blockname + '/' + libname
        if not k in blkModuleCache:
            blkModuleCache[k] = import_module_from_source_file(fname)
        blkMod = blkModuleCache[k]

        if 'parameters' in inst:
            param = inst['parameters']
            if hasattr(blkMod, 'ports'):
                inp, outp, inout = blkMod.ports(param)
            else:
                inp = param['inp'] if 'inp' in param else []
                outp = param['outp'] if 'outp' in param else []
                inout = param['inout'] if 'inout' in param else []
        else:
            inp, outp, inout = blkMod.inp, blkMod.outp, []

        # first initialize the connection to each pin to None
        inst['conn'] = OrderedDict()
        #        inst['signalType'] = OrderedDict()
        if isinstance(inp, int):
            for ix in range(inp):
                inst['conn']['.i_{}'.format(ix)] = None
        else:
            for pname, px, py in inp:
                inst['conn'][pname] = None

        inst['outp'] = set(
        )  # used to set unnamed nets that are connected to an output
        if isinstance(outp, int):
            for ix in range(outp):
                pname = '.o_{}'.format(ix)
                inst['conn'][pname] = None
                inst['outp'].add(pname)
        else:
            for pname, px, py in outp:
                inst['conn'][pname] = None
                inst['outp'].add(pname)

        if isinstance(inout, int):
            for ix in range(inout):
                inst['conn']['.io_{}'.format(ix)] = None
        else:
            for pname, px, py in inout:
                inst['conn'][pname] = None
        # copy keys, to signalTypes
#        inst['signalType'].update(inst['conn'])

# find pins because they are external nets
    pinnames = set()
    nodes = dict()
    for n in dgm.nodes:
        xy = n['x'], n['y']
        nodes[xy] = NetObj(n)
        if 'label' in n and n['porttype'] != 'node':
            pinnames.add(n['label']['text'])

    resolved = dict(
    )  # resolved connections resolved[netname] == set(connections and nodes)
    unresolved = set()  # unresolved connections

    for c in dgm.connections:
        conn = NetObj(c)
        for xy in [(c['x0'], c['y0']), (c['x1'], c['y1'])]:
            if xy in nodes:
                conn.stamp(nodes[xy])
                nodes[xy].stamp(conn)
        if conn.netname:
            if conn.netname not in resolved:
                resolved[conn.netname] = set()
            resolved[conn.netname].add(conn)
        else:
            unresolved.add(conn)
#==============================================================================
# propagate names nets
#==============================================================================
    for netname in resolved.keys():
        for conn in set(resolved[netname]):
            propagateNets(conn, unresolved, resolved)

#==============================================================================
#  propagate anonymous nets
#==============================================================================
# build a set of driven nets
    driven_connections = set()
    for conn in unresolved:
        if 'p0' in conn.d:
            driven_connections.add(conn)

    n_nets = 0  # used to number anonymous nets
    while unresolved:

        # check if there are driven conncetions
        if driven_connections:  # name after driving instance
            conn = driven_connections.pop()
            unresolved.discard(conn)
            instname, portname = conn.d['p0']
            inst = blocks[instname]

            netname = 'w_{}'.format(instname.lower())  #instance_name
            if portname in inst['outp']:
                netname = 'w_{}'.format(instname.lower())  #instance_name
                if len(inst['outp']) > 1:  # not the only output
                    netname += '_{}'.format(
                        portname.lstrip('.').lower())  # + port_name
            else:
                print(inst)
                raise Exception(
                    '{}: connection to {} pin {} is not an output of {}.{}'.
                    format(filename, instname, portname, inst['libname'],
                           inst['blockname']))

        else:  # choose arbitrary name
            conn = unresolved.pop()
            if debug:
                print('anonymous net in ', filename)
                print('   p0 = {}, {}'.format(conn.d['x0'], conn.d['y0']))
                print('   p1 = {}, {}'.format(conn.d['x1'], conn.d['y1']))
            n_nets += 1
            netname = 'net{}'.format(n_nets)

        conn.netname = netname
        if conn.netname not in resolved:
            resolved[conn.netname] = set()
        resolved[conn.netname].add(conn)
        propagateNets(conn, unresolved, resolved)

#==============================================================================
# resolve connection to blocks
#==============================================================================

    for netname, conns in resolved.items():
        for conn in conns:
            for p in ['p0', 'p1']:
                if p in conn.d:
                    blkname, pname = conn.d[p]
                    inst = blocks[blkname]
                    inst['conn'][pname] = (conn.netname, conn.type)

    # check that all block ports are connected
    for instname, inst in blocks.items():
        for pin, net in inst['conn'].items():
            if net is None:
                if debug:
                    print('debug', inst['conn'])
                raise Exception(
                    'file {}: instance {}, pin {} is not Connected'.format(
                        filename, instname, pin))


#                print('file {}: instance {}, pin {} is not Connected'.format(filename, instname, pin))

    internal_nets = dict()
    external_nets = dict()
    for netname in resolved:
        # signal_type
        st = None
        for item in resolved[netname]:
            if item.type:
                if st is None:
                    st = item.type
                elif st != item.type:
                    raise Exception('Type conflict: {}, {}\non {}'.format(\
                                    st, item.type, item))
        prop = dict(signalType=st)
        for c in resolved[netname]:
            if 'properties' in c.d:
                prop.update(c.d['properties'])

        if netname in pinnames:
            external_nets[netname] = prop
        else:
            internal_nets[netname] = prop

    return blocks, internal_nets, external_nets
示例#8
0
def resolve_dgm_connectivity(filename, properties=dict()):
    '''work out the connections in a diagram'''
    #import file
    dgm = import_module_from_source_file(filename)

    #==============================================================================
    #   read blocks
    #==============================================================================
    blocks = dict()
    for inst in dgm.blocks:
        inst_name = inst['label']['text']
        blocks[inst_name] = inst

        blockname, libname = inst['blockname'], inst['libname']
        fname = libraries.blockpath(libname, blockname)
        k = blockname + '/' + libname
        if not k in blkModuleCache:
            blkModuleCache[k] = import_module_from_source_file(fname)
        blkMod = blkModuleCache[k]

        if 'parameters' in inst:
            param = inst['parameters']
            if hasattr(blkMod, 'ports'):
                inp, outp, inout = blkMod.ports(param)
            else:
                inp = param['inp'] if 'inp' in param else []
                outp = param['outp'] if 'outp' in param else []
                inout = param['inout'] if 'inout' in param else []
        else:
            inp, outp, inout = blkMod.inp, blkMod.outp, []

        # first initialize the connection to each pin to None
        inst['conn'] = OrderedDict()
        #        inst['signalType'] = OrderedDict()
        if isinstance(inp, int):
            for ix in range(inp):
                inst['conn']['.i_{}'.format(ix)] = None
        else:
            for pname, px, py in inp:
                inst['conn'][pname] = None

#        inst['outp'] = set() # used to set unnamed nets that are connected to an output
        if isinstance(outp, int):
            for ix in range(outp):
                pname = '.o_{}'.format(ix)
                inst['conn'][pname] = None
#                inst['outp'].add(pname)
        else:
            for pname, px, py in outp:
                inst['conn'][pname] = None
#                inst['outp'].add(pname)

        if isinstance(inout, int):
            for ix in range(inout):
                inst['conn']['.io_{}'.format(ix)] = None
        else:
            for pname, px, py in inout:
                inst['conn'][pname] = None
        # copy keys, to signalTypes
#        inst['signalType'].update(inst['conn'])

#==============================================================================
#   Build connectivity network
#==============================================================================
    dgm_nets = Nets()  # dgm_nets hold all different nets
    for node in dgm.nodes:
        dgm_nets.addNode(node)
    for conn in dgm.connections:
        dgm_nets.addConnection(conn)
    dgm_nets.name_all_nets(blocks)

    #==============================================================================
    # check that all block ports are connected
    #==============================================================================
    for instname, inst in list(blocks.items()):
        for pin, net in list(inst['conn'].items()):
            if net is None:
                if debug:
                    print('debug', inst['conn'])
                raise Exception(
                    'file {}: instance {}, pin {} is floating'.format(
                        filename, instname, pin))


#==============================================================================
# spit internal and external nets
#==============================================================================
    internal_nets, external_nets = dgm_nets.split_nets()

    if debug:
        for netname, net in list(dgm_nets.named.items()):
            print('Net:', netname)
            net.pprint()

    return blocks, internal_nets, external_nets