Add DoIt base design flow support. In full replacement of Makefiles.

This commit is contained in:
Jean-Paul Chaput 2022-12-31 15:01:37 +01:00
parent ae01be3c53
commit e590400ebb
73 changed files with 3646 additions and 7 deletions

View File

@ -32,3 +32,10 @@
PERMISSIONS OWNER_WRITE
OWNER_READ GROUP_READ WORLD_READ
OWNER_EXECUTE GROUP_EXECUTE WORLD_EXECUTE)
install(FILES crlenv.py
DESTINATION bin
RENAME crlenv
PERMISSIONS OWNER_WRITE
OWNER_READ GROUP_READ WORLD_READ
OWNER_EXECUTE GROUP_EXECUTE WORLD_EXECUTE)

269
bootstrap/crlenv.py Executable file
View File

@ -0,0 +1,269 @@
#!/usr/bin/env python3
import sys
import os
import os.path
from pathlib import Path
import socket
import subprocess
import re
import argparse
useDebug = False
reCoriolisPattern = re.compile( r".*coriolis.*" )
reReleaseSharedPattern = re.compile( r".*Release\.Shared.*" )
reReleaseStaticPattern = re.compile( r".*Release\.Static.*" )
reDebugSharedPattern = re.compile( r".*Debug\.Shared.*" )
reDebugStaticPattern = re.compile( r".*Debug\.Static.*" )
def scrubPath ( pathName ):
"""
Remove from the PATH like environment variable ``pathName`` any
previous path item referring to a Coriolis location.
"""
if not pathName in os.environ: return ''
value = os.environ[ pathName ]
elements = value.split( ':' )
scrubbed = []
for element in elements:
if element == '': continue
if reCoriolisPattern .match(element) \
or reReleaseSharedPattern.match(element) \
or reReleaseStaticPattern.match(element) \
or reDebugSharedPattern .match(element) \
or reDebugStaticPattern .match(element):
continue
scrubbed.append( element )
if len(scrubbed) == 0: return ''
return ':'.join( scrubbed )
def envWriteBack ( pathName, pathValue ):
"""
Add to the environment PATH like variable ``pathName`` the components
given in ``pathValue`` and export it back. To avoid having multiple
Coriolis in the path, it is scrubbed beforehand.
"""
if pathName in os.environ:
scrubbed = scrubPath( pathName )
if scrubbed != '':
pathValue += ':' + scrubbed
os.environ[ pathName ] = pathValue
return pathValue
def setupPaths ( verbose ):
"""
Guess and setup the main variables to use Coriolis:
* ``PATH``, to find the binaries.
* ``LD_LIBRARY_PATH``, to access the dynamic libraries.
* ``DYLD_LIBRARY_PATH``, same as above under MacOS.
* ``PYTHONPATH``, to access the various Python modules
provided by Coriolis.
"""
global useDebug
# Setup CORIOLIS_TOP.
osEL9 = re.compile (".*Linux.*el9.*x86_64.*")
osSlsoc7x_64 = re.compile (".*Linux.*el7.*x86_64.*")
osSlsoc6x_64 = re.compile (".*Linux.*el6.*x86_64.*")
osSlsoc6x = re.compile (".*Linux.*(el|slsoc)6.*")
osSLSoC5x_64 = re.compile (".*Linux.*el5.*x86_64.*")
osSLSoC5x = re.compile (".*Linux.*(el5|2.6.23.13.*SoC).*")
osFedora_64 = re.compile (".*Linux.*fc.*x86_64.*")
osFedora = re.compile (".*Linux.*fc.*")
osLinux_64 = re.compile (".*Linux.*x86_64.*")
osLinux = re.compile (".*Linux.*")
osDarwin = re.compile (".*Darwin.*")
osUbuntu1004 = re.compile (".*Linux.*ubuntu.*")
osUbuntu1004_64 = re.compile (".*Linux.*ubuntu.*x86_64.*")
osFreeBSD8x_amd64 = re.compile (".*FreeBSD 8.*amd64.*")
osFreeBSD8x_64 = re.compile (".*FreeBSD 8.*x86_64.*")
osFreeBSD8x = re.compile (".*FreeBSD 8.*")
osCygwinW7_64 = re.compile (".*CYGWIN_NT-6\.1.*x86_64.*")
osCygwinW7 = re.compile (".*CYGWIN_NT-6\.1.*i686.*")
osCygwinW8_64 = re.compile (".*CYGWIN_NT-6\.[2-3].*x86_64.*")
osCygwinW8 = re.compile (".*CYGWIN_NT-6\.[2-3].*i686.*")
osCygwinW10_64 = re.compile (".*CYGWIN_NT-10\.[0-3].*x86_64.*")
osCygwinW10 = re.compile (".*CYGWIN_NT-10\.[0-3].*i686.*")
uname = subprocess.Popen( ["uname", "-srm"], stdout=subprocess.PIPE )
lines = uname.stdout.readlines()
line = lines[0].decode( 'ascii' )
if osSlsoc7x_64 .match(line): osDir = "Linux.el7_64"
elif osEL9 .match(line): osDir = "Linux.el9"
elif osSlsoc6x_64 .match(line): osDir = "Linux.slsoc6x_64"
elif osSlsoc6x .match(line): osDir = "Linux.slsoc6x"
elif osSLSoC5x_64 .match(line): osDir = "Linux.SLSoC5x_64"
elif osSLSoC5x .match(line): osDir = "Linux.SLSoC5x"
elif osFedora_64 .match(line): osDir = "Linux.fc_64"
elif osFedora .match(line): osDir = "Linux.fc"
elif osUbuntu1004 .match(line): osDir = "Linux.Ubuntu1004"
elif osUbuntu1004_64 .match(line): osDir = "Linux.Ubuntu1004_64"
elif osLinux_64 .match(line): osDir = "Linux.x86_64"
elif osLinux .match(line): osDir = "Linux.i386"
elif osFreeBSD8x_64 .match(line): osDir = "FreeBSD.8x.x86_64"
elif osFreeBSD8x_amd64.match(line): osDir = "FreeBSD.8x.amd64"
elif osFreeBSD8x .match(line): osDir = "FreeBSD.8x.i386"
elif osDarwin .match(line): osDir = "Darwin"
elif osCygwinW7_64 .match(line): osDir = "Cygwin.W7_64"
elif osCygwinW7 .match(line): osDir = "Cygwin.W7"
elif osCygwinW8_64 .match(line): osDir = "Cygwin.W8_64"
elif osCygwinW8 .match(line): osDir = "Cygwin.W8"
elif osCygwinW10_64 .match(line): osDir = "Cygwin.W10_64"
elif osCygwinW10 .match(line): osDir = "Cygwin.W10"
else:
uname = subprocess.Popen( ["uname", "-sr"], stdout=subprocess.PIPE )
osDir = uname.stdout.readlines()[0][:-1]
print( '[WARNING] environment.setupPaths(): Unrecognized OS: "{}".'.format( line[:-1] ))
print( ' (using: "{}")'.format( osDir ))
osDir = Path( osDir )
homeDir = Path( os.environ['HOME'] )
buildType = Path( 'Release.Debug' if useDebug else 'Release.Shared' )
topDirs = []
if 'CORIOLIS_TOP' in os.environ:
topDirs += [ Path( os.environ['CORIOLIS_TOP'] ) ]
topDirs += [ homeDir / 'coriolis-2.x' / osDir / buildType / 'install'
, Path( '/soc/coriolis2' )
, Path( '/usr' )
]
if verbose:
print( ' o Self locating Coriolis:' )
coriolisTop = None
for topDir in topDirs:
if not coriolisTop:
if (topDir / 'bin' / 'cgt').is_file():
if verbose:
print( ' - {} *'.format(topDir) )
coriolisTop = topDir
else:
if verbose:
print( ' - {}'.format(topDir) )
if not coriolisTop:
print( '[ERROR] environment.setupPaths(): Unable to locate Coriolis.' )
return False
os.environ[ 'CORIOLIS_TOP' ] = coriolisTop.as_posix()
if coriolisTop == '/usr': sysconfDir = Path( 'etc', 'coriolis2' )
else: sysconfDir = coriolisTop / 'etc' / 'coriolis2'
# Setup PATH.
binPath = envWriteBack( 'PATH', (coriolisTop/'bin').as_posix() )
# Setup LD_LIBRARY_PATH.
libDirs = []
for lib in [ Path('lib'), Path('lib64') ]:
libDir = lib
absLibDir = coriolisTop / lib
if absLibDir.is_dir():
libDirs.append( absLibDir )
libDir = None
if not len(libDirs):
print( '[ERROR] environment.setupPaths(): Library directory not found.' )
return False
libraryPath = ''
ldPathName = 'LD_LIBRARY_PATH'
if osDir.as_posix().startswith( 'Darwin' ):
ldPathName = 'DYLD_LIBRARY_PATH'
for libDir in libDirs:
if len(libraryPath): libraryPath = libraryPath + ':'
libraryPath = libraryPath + libDir.as_posix()
libraryPath = envWriteBack( ldPathName, libraryPath )
# Setup PYTHONPATH.
v = sys.version_info
sitePackagesDir = None
for pyPackageDir in [ Path('python{}.{}'.format(v.major,v.minor)) / 'site-packages'
, Path('python{}.{}'.format(v.major,v.minor)) / 'dist-packages'
, Path('{}.{}'.format(v.major,v.minor)) / 'site-packages'
, Path('python{}'.format(v.major)) / 'site-packages'
, Path('python{}'.format(v.major)) / 'dist-packages'
, Path('{}'.format(v.major)) / 'site-packages'
]:
sitePackagesDir = libDirs[-1] / pyPackageDir
if sitePackagesDir.is_dir():
if verbose:
print( ' - {} *'.format(sitePackagesDir) )
break
if verbose:
print( ' - {}'.format(sitePackagesDir) )
sitePackagesDir = None
if sitePackagesDir is None:
print( '[ERROR] environment.setupPaths(): Python {site,dist}-packages directory not found.' )
return False
pythonPath = ''
for packageDir in [ sitePackagesDir
, sitePackagesDir / 'crlcore'
, sitePackagesDir / 'cumulus'
, sitePackagesDir / 'cumulus/plugins'
, sitePackagesDir / 'status'
, sysconfDir
]:
sys.path.append( str(packageDir) )
if len(pythonPath): pythonPath += ':'
pythonPath += str(packageDir)
pythonPath = envWriteBack( 'PYTHONPATH', pythonPath )
return True
def printVariable ( name ):
if not name in os.environ:
print( '{:<16}:'.format( name ))
print( '- variable_not_set' )
return
values = os.environ[ name ].split( ':' )
print( '{}:'.format( name ))
for value in values:
print( '- {}'.format( value ))
def printEnvironment ():
"""
Display the environment setup, using YAML formatting.
"""
print( '# crlenv.py: Alliance/Coriolis finder, guessed values.' )
print( '---' )
for name in ('CORIOLIS_TOP', 'PATH', 'DYLD_LIBRARY_PATH'
, 'LD_LIBRARY_PATH', 'PYTHONPATH'):
printVariable( name )
if __name__ == '__main__':
"""
Run any script in a environmnent set for Coriolis.
Example:
.. code:: bash
ego@home:~> crlenv.py -- doit clean_flow
b2v Run <blif2vst arlet6502 depends=[Arlet6502.blif]>.
cgt Run plain CGT (no loaded design)
clean_flow Clean all generated (targets) files.
gds Run <Alias "gds" for "pnr">.
pnr Run <pnr arlet6502_cts_r.gds depends=[arlet6502.vst,Arlet6502.spi]>.
yosys Run <yosys Arlet6502.v top=Arlet6502 blackboxes=[] flattens=[]>.
ego@home:~> crlenv.py -- bash
[ego@home]$ echo $CORIOLIS_TOP
/home/ego/coriolis-2.x/Linux.el9/Release.Shared/install
[ego@home]$ exit
ego@home:~>
"""
parser = argparse.ArgumentParser()
parser.add_argument( '-v', '--verbose', action='store_true', dest='verbose' )
parser.add_argument( '-d', '--debug' , action='store_true', dest='debug' )
parser.add_argument( 'command', nargs='*' )
args = parser.parse_args()
setupPaths( args.verbose )
if not len(args.command):
printEnvironment()
sys.exit( 0 )
state = subprocess.run( args.command )
sys.exit( state.returncode )

View File

@ -381,7 +381,7 @@ def staticInitialization ():
return
helpers.staticInitialization()
helpers.staticInitialization( quiet=True )
staticInitialization()
report = ReportLog( 'alliance' )

View File

@ -1,5 +1,30 @@
# -*- explicit-buffer-name: "CMakeLists.txt<cumulus/src>" -*-
set ( pyDesignFlow ${CMAKE_CURRENT_SOURCE_DIR}/designflow/task.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/copy.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/vasy.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/boom.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/boog.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/loon.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/genpat.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/asimut.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/flatph.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/cougar.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/s2r.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/lvx.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/druc.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/graal.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/dreal.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/yosys.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/blif2vst.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/pnr.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/clean.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/alias.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/technos.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/routecheck.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/pnrcheck.py
${CMAKE_CURRENT_SOURCE_DIR}/designflow/alliancesynth.py
)
set ( pySources ${CMAKE_CURRENT_SOURCE_DIR}/placeandroute.py
${CMAKE_CURRENT_SOURCE_DIR}/ref.py
${CMAKE_CURRENT_SOURCE_DIR}/Alliance.py
@ -90,6 +115,7 @@
${CMAKE_CURRENT_SOURCE_DIR}/plugins/alpha/harness/pads.py
)
install ( FILES ${pyDesignFlow} DESTINATION ${Python_CORIOLISLIB}/designflow )
install ( FILES ${pySources} DESTINATION ${Python_CORIOLISLIB}/cumulus )
install ( FILES ${pyPlugins} DESTINATION ${Python_CORIOLISLIB}/cumulus/plugins )
install ( FILES ${pyPluginCTS} DESTINATION ${Python_CORIOLISLIB}/cumulus/plugins/cts )

View File

View File

@ -0,0 +1,36 @@
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask
class BadAliasDepend ( Exception ): pass
class Alias ( FlowTask ):
@staticmethod
def mkRule ( rule, depends=[] ):
return Alias( rule, depends )
def __init__ ( self, rule, depends, ):
if len(depends) != 1:
raise BadAliasDepend( 'Alias.__init__(): There must be exactly *one* dependency ({})' \
.format( depends ))
if not isinstance(depends[0],FlowTask):
raise BadAliasDepend( 'Alias.__init__(): The dependency must be another *rule* ({})' \
.format( depends[0] ))
super().__init__( rule, [], depends )
def __repr__ ( self ):
return '<Alias "{}" for "{}">'.format( self.basename, self.depends[0].basename )
def doTask ( self ):
return True
def create_doit_tasks ( self ):
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : 'Run {}.'.format( self )
, 'targets' : self.targets
, 'file_dep' : self.file_dep
}

View File

@ -0,0 +1,43 @@
from pathlib import Path
from .vasy import Vasy
from .boom import Boom
from .boog import Boog
from .loon import Loon
from .clean import Clean
HasFsm = 0x00000001
def mkRuleSet ( callerGlobals, behFile, flags=0 ):
if not isinstance(behFile,Path):
behFile = Path( behFile )
ruleStem = behFile.stem
toolFlags = Vasy.AddPowerSupplies|Boom.LocalOptimization
if behFile.suffix in ('.vhdl', '.vhd', '.vlog', '.v'):
vasyTargets = [ Path(behFile.stem + '.vbe') ]
if flags & HasFsm:
vasyTargets = [ Path(behFile.stem+'_model.vbe')
, Path(behFile.stem+'.vst') ]
ruleVasy = Vasy.mkRule( 'vasy_'+ruleStem, vasyTargets
, behFile
, flags=toolFlags )
behFile = vasyTargets[0]
ruleBoom = Boom.mkRule( 'boom_'+ruleStem, behFile.stem + '_boom.vbe'
, behFile.stem + '.vbe'
, flags=toolFlags )
ruleBoog = Boog.mkRule( 'boog_'+ruleStem, behFile.stem + '_boog.vst'
, ruleBoom
, flags=toolFlags )
ruleLoon = Loon.mkRule( 'loon_'+ruleStem, behFile.stem + '.vst'
, ruleBoog
, flags=toolFlags )
for tag in [ 'Vasy', 'Boom', 'Boog', 'Loon' ]:
rule = 'rule' + tag
if rule in locals():
callerGlobals[ rule+'_'+ruleStem ] = locals()[ rule ]

View File

@ -0,0 +1,57 @@
import os
import subprocess
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask, ShellEnv
class MissingTarget ( Exception ): pass
class Asimut ( FlowTask ):
RootIsBehavioral = 0x0001
UseBdd = 0x0002
ZeroDelay = 0x0004
@staticmethod
def mkRule ( rule, targets, depends=[], flags=0 ):
return Asimut( rule, targets, depends, flags )
def __init__ ( self, rule, targets, depends, flags ):
super().__init__( rule, targets, depends )
self.vhdlFile = Path( self.file_depend(0) )
self.patFile = Path( self.file_depend(1) )
self.simFile = Path( self.targets[0] )
self.command = [ 'asimut' ]
if flags & Asimut.RootIsBehavioral: self.command.append( '-b' )
if flags & Asimut.UseBdd: self.command.append( '-bdd' )
if flags & Asimut.ZeroDelay: self.command.append( '-zerodelay' )
self.command += [ self.vhdlFile.stem, self.patFile.stem, self.simFile.stem ]
self.addClean( self.targets )
def __repr__ ( self ):
return '<{}>'.format( ' '.join(self.command) )
def doTask ( self ):
from CRL import AllianceFramework
from helpers.io import ErrorMessage
shellEnv = ShellEnv()
shellEnv[ 'MBK_IN_LO' ] = 'vst'
shellEnv.export()
state = subprocess.run( self.command )
if state.returncode:
e = ErrorMessage( 1, 'Asimut.doTask(): UNIX command failed ({}).' \
.format( state.returncode ))
return TaskFailed( e )
return self.checkTargets( 'Asimut.doTask' )
def create_doit_tasks ( self ):
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : 'Run {}.'.format( self )
, 'targets' : self.targets
, 'file_dep' : self.file_dep
}

View File

@ -0,0 +1,85 @@
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask
class TargetNotVst ( Exception ): pass
def renameNMigen( occurrence ):
masterCell = occurrence.getEntity().getMasterCell()
origName = masterCell.getName()
replName = origName.replace( '$$', '_unm' )
if not masterCell.isTerminalNetlist() and not replName.startswith('cmpt_'):
replName = 'cmpt_' + replName
#for letter in 'ABCDEFGHIJKLMNOPQRSTUVWXYZ':
# replName = replName.replace(letter, '{}u'.format(letter))
if origName != replName:
print( ' - "{}" => "{}"'.format(origName,replName) )
masterCell.setName( replName )
def renameNMigenUniquify ( topCell ):
for occurrence in topCell.getTerminalNetlistInstanceOccurrences():
renameNMigen(occurrence)
for occurrence in topCell.getNonTerminalNetlistInstanceOccurrences():
renameNMigen(occurrence)
return
class Blif2Vst ( FlowTask ):
@staticmethod
def mkRule ( rule, targets, depends=[], flags=0 ):
return Blif2Vst( rule, targets, depends, flags )
def __init__ ( self, rule, targets, depends, flags ):
super().__init__( rule, targets, depends )
self.flags = flags
if not self.targets[0].endswith('.vst'):
raise TargetNotVst( 'Blif2Vst.__init__(): First target *must* "{}" be a vst file.' \
.format( self.targets[0] ))
self.addClean( self.targets )
def __repr__ ( self ):
return '<blif2vst {} depends=[{}]>' \
.format( self.design, ','.join(self.file_dep) )
@property
def design ( self ):
if len(self.targets): return self.targets[0][:-4]
return None
def doTask ( self ):
from Hurricane import Cell
import CRL
import Viewer
from helpers.io import ErrorMessage
import plugins.rsave
print( 'Blif2Vst.doTask() on "{}"'.format( self.design ))
views = CRL.Catalog.State.Logical | self.flags
cell = CRL.Blif.load( self.file_depend() )
if cell.getName() == 'top':
print( ' o Renaming RTLIL anonymous top cell "top" into "{}".'.format(self.design) )
cell.setName( self.design )
renameNMigenUniquify( cell )
CRL.restoreNetsDirection( cell, Cell.Flags_TerminalNetlist )
kw = {}
kw['views'] = views
kw['cell' ] = cell
plugins.rsave.scriptMain( **kw )
return self.checkTargets( 'Blif2Vst.doTask' )
def create_doit_tasks ( self ):
if self.design: doc = 'Run {}.'.format( self )
else: doc = 'Run plain CGT (no loaded design)'
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : doc
, 'targets' : self.targets
, 'file_dep' : self.file_dep
}

View File

@ -0,0 +1,68 @@
import os
import subprocess
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask, ShellEnv
class UnsupportedVHdlSuffix ( Exception ): pass
class Boog ( FlowTask ):
FlagMask = 0x00110000
XschModeCritical = 0x00010000
XschModeAll = 0x00020000
OptimArea = 0x00040000
OptimAreaMostly = 0x00080000
OptimBalanced = 0x00100000
OptimDelaysMostly = 0x00200000
OptimDelays = 0x00400000
@staticmethod
def mkRule ( rule, targets, depends=[], flags=0 ):
return Boog( rule, targets, depends, flags )
def __init__ ( self, rule, targets, depends, flags ):
super().__init__( rule, targets, depends )
self.flags = flags
self.inputFile = Path( self.file_depend(0) )
self.outputFile = Path( self.targets[0] )
self.command = [ 'boog' ]
if flags & Boog.XschModeCritical: self.command += [ '-x', '0' ]
if flags & Boog.XschModeAll: self.command += [ '-x', '1' ]
if flags & Boog.OptimArea: self.command += [ '-m', '0' ]
if flags & Boog.OptimAreaMostly: self.command += [ '-m', '1' ]
if flags & Boog.OptimBalanced: self.command += [ '-m', '2' ]
if flags & Boog.OptimDelaysMostly: self.command += [ '-m', '3' ]
if flags & Boog.OptimDelays: self.command += [ '-m', '4' ]
self.command += [ self.inputFile.stem, self.outputFile.stem ]
self.targets.append( self.outputFile.stem + '.xsc' )
self.addClean( self.targets )
def __repr__ ( self ):
return '<{}>'.format( ' '.join(self.command) )
def doTask ( self ):
from CRL import AllianceFramework
from helpers.io import ErrorMessage
shellEnv = ShellEnv()
shellEnv[ 'MBK_OUT_LO' ] = self.outputFile.suffix[1:]
shellEnv.export()
print( ' -> Running "{}" ...'.format( ' '.join(self.command) ))
state = subprocess.run( self.command )
if state.returncode:
e = ErrorMessage( 1, 'Boog.doTask(): UNIX command failed ({}).' \
.format( state.returncode ))
return TaskFailed( e )
return self.checkTargets( 'Boog.doTask' )
def create_doit_tasks ( self ):
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : 'Run {}.'.format( self )
, 'targets' : self.targets
, 'file_dep' : self.file_dep
}

View File

@ -0,0 +1,60 @@
import os
import subprocess
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask, ShellEnv
class UnsupportedVHdlSuffix ( Exception ): pass
class Boom ( FlowTask ):
FlagMask = 0x00001100
Verbose = 0x00000100
TraceOn = 0x00000200
ReverseBdd = 0x00000400
LocalOptimization = 0x00000800
@staticmethod
def mkRule ( rule, targets, depends=[], flags=0 ):
return Boom( rule, targets, depends, flags )
def __init__ ( self, rule, targets, depends, flags ):
super().__init__( rule, targets, depends )
self.flags = flags
self.inputFile = Path( self.file_depend(0) )
self.outputFile = Path( self.targets[0] )
self.command = [ 'boom' ]
if flags & Boom.Verbose: self.command.append( '-V' )
if flags & Boom.TraceOn: self.command.append( '-T' )
if flags & Boom.ReverseBdd: self.command.append( '-O' )
if flags & Boom.LocalOptimization: self.command.append( '-A' )
self.command += [ self.inputFile.stem, self.outputFile.stem ]
self.addClean( self.targets )
def __repr__ ( self ):
return '<{}>'.format( ' '.join(self.command) )
def doTask ( self ):
from CRL import AllianceFramework
from helpers.io import ErrorMessage
shellEnv = ShellEnv()
shellEnv.export()
print( ' -> Running "{}" ...'.format( ' '.join(self.command) ))
state = subprocess.run( self.command )
if state.returncode:
e = ErrorMessage( 1, 'Boom.doTask(): UNIX command failed ({}).' \
.format( state.returncode ))
return TaskFailed( e )
return self.checkTargets( 'Boom.doTask' )
def create_doit_tasks ( self ):
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : 'Run {}.'.format( self )
, 'targets' : self.targets
, 'file_dep' : self.file_dep
}

View File

@ -0,0 +1,56 @@
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask
class MissingTarget ( Exception ): pass
class Clean ( FlowTask ):
@staticmethod
def mkRule ( extrasClean=[] ):
return Clean( extrasClean )
def __init__ ( self, extrasClean ):
super().__init__( 'clean_flow', [], [] )
self.extrasClean = extrasClean
def __repr__ ( self ):
return '<clean>'
def doTask ( self, doExtrasClean ):
print( ' Removing all target files' )
print( ' =========================' )
for fileName in FlowTask.cleanTargets:
filePath = Path( fileName )
if filePath.is_file():
print( ' - {:<40} [removed]'.format( filePath.as_posix() ))
filePath.unlink()
else:
print( ' - {}'.format( filePath.as_posix() ))
if doExtrasClean and len(self.extrasClean):
print( ' Removing extra clean files' )
print( ' ==========================' )
for fileName in self.extrasClean:
filePath = Path( fileName )
if filePath.is_file():
print( ' - {:<40} [removed]'.format( filePath.as_posix() ))
filePath.unlink()
else:
print( ' - {}'.format( filePath.as_posix() ))
return True
def create_doit_tasks ( self ):
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : 'Clean all generated (targets) files.'
, 'params' : [ { 'name' : 'doExtrasClean'
, 'long' : 'extras'
, 'type' : bool
, 'default' : False
} ]
, 'uptodate' : [ False ]
}

View File

@ -0,0 +1,44 @@
import os
import shutil
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask, ShellEnv
class MissingTarget ( Exception ): pass
class Copy ( FlowTask ):
@staticmethod
def mkRule ( rule, targets, depends=[] ):
return Copy( rule, targets, depends )
def __init__ ( self, rule, targets, depends ):
super().__init__( rule, targets, depends )
self.sourceFile = Path( self.file_depend(0) )
self.targetFile = Path( self.targets[0] )
self.addClean( self.targets )
def __repr__ ( self ):
return '<cp {} {}>'.format( self.sourceFile.as_posix(), self.targetFile.as_posix() )
def doTask ( self ):
from helpers.io import ErrorMessage
try:
shutil.copyfile( self.sourceFile, self.targetFile )
except Exception as e:
e = ErrorMessage( 1, [ 'Copy.doTask(): shutil.copyfile failed.'
, str(e) ] )
return TaskFailed( e )
return self.checkTargets( 'Copy.doTask' )
def create_doit_tasks ( self ):
return { 'basename' : 'copy_' + self.basename
, 'actions' : [ self.doTask ]
, 'doc' : 'Run {}.'.format( self )
, 'targets' : self.targets
, 'file_dep' : self.file_dep
}

View File

@ -0,0 +1,65 @@
import os
import subprocess
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask, ShellEnv
class MissingTarget ( Exception ): pass
class Cougar ( FlowTask ):
Transistor = 0x0001
Flatten = 0x0002
Verbose = 0x0004
Core = 0x0008
GroundCap = 0x0010
WireRC = 0x0020
@staticmethod
def mkRule ( rule, targets, depends=[], flags=0 ):
return Cougar( rule, targets, depends, flags )
def __init__ ( self, rule, targets, depends, flags ):
super().__init__( rule, targets, depends )
self.flags = flags
self.inputFile = Path( self.file_depend(0) )
self.outputFile = Path( self.targets[0] )
self.command = [ 'cougar' ]
if flags & Cougar.Transistor: self.command.append( '-t' )
if flags & Cougar.Flatten: self.command.append( '-f' )
if flags & Cougar.Verbose: self.command.append( '-v' )
if flags & Cougar.Core: self.command.append( '-c' )
if flags & Cougar.GroundCap: self.command.append( '-ac' )
if flags & Cougar.WireRC: self.command.append( '-ar' )
self.command += [ self.inputFile.stem, self.outputFile.stem ]
self.addClean( self.targets )
def __repr__ ( self ):
return '<{}>'.format( ' '.join(self.command) )
def doTask ( self ):
from CRL import AllianceFramework
from helpers.io import ErrorMessage
shellEnv = ShellEnv()
shellEnv[ 'MBK_OUT_LO' ] = self.outputFile.suffix[1:]
shellEnv[ 'MBK_IN_PH' ] = self.inputFile .suffix[1:]
shellEnv.export()
state = subprocess.run( self.command )
if state.returncode:
e = ErrorMessage( 1, 'Cougar.doTask(): UNIX command failed ({}).' \
.format( state.returncode ))
return TaskFailed( e )
return self.checkTargets( 'Cougar.doTask' )
def create_doit_tasks ( self ):
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : 'Run {}.'.format( self )
, 'targets' : self.targets
, 'file_dep' : self.file_dep
}

View File

@ -0,0 +1,56 @@
import os
import subprocess
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask, ShellEnv
class MissingTarget ( Exception ): pass
class Dreal ( FlowTask ):
Debug = 0x0001
Xor = 0x0002
Install = 0x0004
Force = 0x0008
@staticmethod
def mkRule ( rule, depends=[], flags=0 ):
return Dreal( rule, depends, flags )
def __init__ ( self, rule, depends, flags ):
super().__init__( rule, [], depends )
self.flags = flags
self.layoutFile = Path( self.file_depend(0) )
self.command = [ 'dreal', '-l', self.layoutFile.stem ]
if flags & Dreal.Debug: self.command.append( '-debug' )
if flags & Dreal.Xor: self.command.append( '-xor' )
if flags & Dreal.Install: self.command.append( '-install' )
if flags & Dreal.Force: self.command.append( '-force' )
def __repr__ ( self ):
return '<{}>'.format( ' '.join(self.command) )
def doTask ( self ):
from helpers.io import ErrorMessage
shellEnv = ShellEnv()
shellEnv[ 'RDS_IN' ] = self.layoutFile.suffix[1:]
shellEnv.export()
state = subprocess.run( self.command )
if state.returncode:
e = ErrorMessage( 1, 'Dreal.doTask(): UNIX command failed ({}).' \
.format( state.returncode ))
return TaskFailed( e )
return self.checkTargets( 'Dreal.doTask' )
def create_doit_tasks ( self ):
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : 'Run {}.'.format( self )
, 'file_dep' : self.file_dep
, 'uptodate' : [ False ]
}

View File

@ -0,0 +1,53 @@
import os
import subprocess
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask, ShellEnv
class MissingTarget ( Exception ): pass
class Druc ( FlowTask ):
Verbose = 0x0001
@staticmethod
def mkRule ( rule, depends=[], flags=0 ):
return Druc( rule, depends, flags )
def __init__ ( self, rule, depends, flags ):
super().__init__( rule, [], depends )
self.flags = flags
self.referenceFile = Path( self.file_depend(0) )
self.targets = [ self.referenceFile.stem + '.drc'
, self.referenceFile.stem + '_drc.gds'
, self.referenceFile.stem + '_rng.gds' ]
self.command = [ 'druc', self.referenceFile.stem ]
if flags & Druc.Verbose: self.command.append( '-v' )
self.addClean( self.targets )
def __repr__ ( self ):
return '<{}>'.format( ' '.join(self.command) )
def doTask ( self ):
from CRL import AllianceFramework
from helpers.io import ErrorMessage
shellEnv = ShellEnv()
shellEnv.export()
state = subprocess.run( self.command )
if state.returncode:
e = ErrorMessage( 1, 'Druc.doTask(): UNIX command failed ({}).' \
.format( state.returncode ))
return TaskFailed( e )
return self.checkTargets( 'Druc.doTask' )
def create_doit_tasks ( self ):
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : 'Run {}.'.format( self )
, 'file_dep' : self.file_dep
}

View File

@ -0,0 +1,61 @@
import os
import subprocess
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask, ShellEnv
class MissingTarget ( Exception ): pass
class Flatph ( FlowTask ):
Transistor = 0x0001
Catalog = 0x0002
@staticmethod
def mkRule ( rule, targets, depends=[], flags=0 ):
return Flatph( rule, targets, depends, flags )
def __init__ ( self, rule, targets, depends, flags ):
super().__init__( rule, targets, depends )
self.flags = flags
self.instFile = None
self.hierFile = Path( self.file_depend(0) )
self.flatFile = Path( self.targets[0] )
self.command = [ 'flatph' ]
if flags & Flatph.Transistor: self.command.append( '-t' )
if flags & Flatph.Catalog: self.command.append( '-r' )
self.command.append( self.hierFile.stem )
if len(self.targets) > 1:
self.instFile = Path( self.targets[1] )
self.command.append( self.instFile.stem )
self.command.append( self.flatFile.stem )
self.addClean( self.targets )
def __repr__ ( self ):
return '<{}>'.format( ' '.join(self.command) )
def doTask ( self ):
from helpers.io import ErrorMessage
shellEnv = ShellEnv()
shellEnv[ 'MBK_IN_PH' ] = self.hierFile.suffix[1:]
shellEnv[ 'MBK_IN_PH' ] = self.flatFile.suffix[1:]
shellEnv.export()
state = subprocess.run( self.command )
if state.returncode:
e = ErrorMessage( 1, 'Flatph.doTask(): UNIX command failed ({}).' \
.format( state.returncode ))
return TaskFailed( e )
return self.checkTargets( 'Flatph.doTask' )
def create_doit_tasks ( self ):
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : 'Run {}.'.format( self )
, 'targets' : self.targets
, 'file_dep' : self.file_dep
}

View File

@ -0,0 +1,48 @@
import os
import subprocess
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask, ShellEnv
class MissingTarget ( Exception ): pass
class Genpat ( FlowTask ):
@staticmethod
def mkRule ( rule, targets, depends=[], flags=0 ):
return Genpat( rule, targets, depends, flags )
def __init__ ( self, rule, targets, depends, flags ):
super().__init__( rule, targets, depends )
self.inputFile = Path( self.file_depend(0) )
self.outputFile = Path( self.targets[0] )
self.command = [ 'genpat' ]
self.command += [ self.inputFile.stem ]
self.addClean( self.targets )
def __repr__ ( self ):
return '<{}>'.format( ' '.join(self.command) )
def doTask ( self ):
from CRL import AllianceFramework
from helpers.io import ErrorMessage
shellEnv = ShellEnv()
shellEnv.export()
state = subprocess.run( self.command )
if state.returncode:
e = ErrorMessage( 1, 'Genpat.doTask(): UNIX command failed ({}).' \
.format( state.returncode ))
return TaskFailed( e )
return self.checkTargets( 'Genpat.doTask' )
def create_doit_tasks ( self ):
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : 'Run {}.'.format( self )
, 'targets' : self.targets
, 'file_dep' : self.file_dep
}

View File

@ -0,0 +1,56 @@
import os
import subprocess
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask, ShellEnv
class MissingTarget ( Exception ): pass
class Graal ( FlowTask ):
Debug = 0x0001
Xor = 0x0002
Install = 0x0004
Force = 0x0008
@staticmethod
def mkRule ( rule, depends=[], flags=0 ):
return Graal( rule, depends, flags )
def __init__ ( self, rule, depends, flags ):
super().__init__( rule, [], depends )
self.flags = flags
self.layoutFile = Path( self.file_depend(0) )
self.command = [ 'graal', '-l', self.layoutFile.stem ]
if flags & Graal.Debug: self.command.append( '-debug' )
if flags & Graal.Xor: self.command.append( '-xor' )
if flags & Graal.Install: self.command.append( '-install' )
if flags & Graal.Force: self.command.append( '-force' )
def __repr__ ( self ):
return '<{}>'.format( ' '.join(self.command) )
def doTask ( self ):
from helpers.io import ErrorMessage
shellEnv = ShellEnv()
shellEnv[ 'MBK_IN_PH' ] = self.layoutFile.suffix[1:]
shellEnv.export()
state = subprocess.run( self.command )
if state.returncode:
e = ErrorMessage( 1, 'Graal.doTask(): UNIX command failed ({}).' \
.format( state.returncode ))
return TaskFailed( e )
return self.checkTargets( 'Graal.doTask' )
def create_doit_tasks ( self ):
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : 'Run {}.'.format( self )
, 'file_dep' : self.file_dep
, 'uptodate' : [ False ]
}

View File

@ -0,0 +1,70 @@
import os
import subprocess
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask, ShellEnv
class UnsupportedVHdlSuffix ( Exception ): pass
class Loon ( FlowTask ):
FlagMask = 0x11000000
XschModeCritical = 0x01000000
XschModeAll = 0x02000000
OptimArea = 0x04000000
OptimAreaMostly = 0x08000000
OptimBalanced = 0x10000000
OptimDelaysMostly = 0x20000000
OptimDelays = 0x40000000
@staticmethod
def mkRule ( rule, targets, depends=[], flags=0 ):
return Loon( rule, targets, depends, flags )
def __init__ ( self, rule, targets, depends, flags ):
super().__init__( rule, targets, depends )
self.flags = flags
self.inputFile = Path( self.file_depend(0) )
self.outputFile = Path( self.targets[0] )
self.command = [ 'loon' ]
#print( 'flags=0x{:08x}'.format( flags ))
if flags & Loon.XschModeCritical: self.command += [ '-x', '0' ]
if flags & Loon.XschModeAll: self.command += [ '-x', '1' ]
if flags & Loon.OptimArea: self.command += [ '-m', '0' ]
if flags & Loon.OptimAreaMostly: self.command += [ '-m', '1' ]
if flags & Loon.OptimBalanced: self.command += [ '-m', '2' ]
if flags & Loon.OptimDelaysMostly: self.command += [ '-m', '3' ]
if flags & Loon.OptimDelays: self.command += [ '-m', '4' ]
self.command += [ self.inputFile.stem, self.outputFile.stem ]
self.targets.append( self.outputFile.stem + '.xsc' )
self.addClean( self.targets )
def __repr__ ( self ):
return '<{}>'.format( ' '.join(self.command) )
def doTask ( self ):
from CRL import AllianceFramework
from helpers.io import ErrorMessage
shellEnv = ShellEnv()
shellEnv[ 'MBK_OUT_LO' ] = self.outputFile.suffix[1:]
shellEnv[ 'MBK_IN_LO' ] = self.inputFile .suffix[1:]
shellEnv.export()
print( ' -> Running "{}" ...'.format( ' '.join(self.command) ))
state = subprocess.run( self.command )
if state.returncode:
e = ErrorMessage( 1, 'Loon.doTask(): UNIX command failed ({}).' \
.format( state.returncode ))
return TaskFailed( e )
return self.checkTargets( 'Loon.doTask' )
def create_doit_tasks ( self ):
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : 'Run {}.'.format( self )
, 'targets' : self.targets
, 'file_dep' : self.file_dep
}

View File

@ -0,0 +1,68 @@
import os
import subprocess
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask, ShellEnv
class MissingTarget ( Exception ): pass
class Lvx ( FlowTask ):
MergeSupply = 0x0001
SaveReorder = 0x0002
CheckUnassigned = 0x0004
Flatten = 0x0008
@staticmethod
def mkRule ( rule, depends=[], flags=0 ):
return Lvx( rule, depends, flags )
def __init__ ( self, rule, depends, flags ):
import CRL
super().__init__( rule, [], depends )
self.flags = flags
self.referenceFile = Path( self.file_depend(0) )
self.checkedFile = Path( self.file_depend(1) )
self.command = [ 'lvx'
, self.referenceFile.suffix[1:]
, self.checkedFile.suffix[1:]
, self.referenceFile.stem
, self.checkedFile.stem ]
if flags & Lvx.MergeSupply: self.command.append( '-a' )
if flags & Lvx.SaveReorder: self.command.append( '-o' )
if flags & Lvx.CheckUnassigned: self.command.append( '-u' )
if flags & Lvx.Flatten: self.command.append( '-f' )
if self.flags & Lvx.SaveReorder:
env = CRL.AllianceFramework.get().getEnvironment()
self.targets = [ self.checkedFile.stem + '.' + env.getOUT_LO() ]
self.addClean( self.targets )
def __repr__ ( self ):
return '<{}>'.format( ' '.join(self.command) )
def doTask ( self ):
from CRL import AllianceFramework
from helpers.io import ErrorMessage
shellEnv = ShellEnv()
shellEnv.export()
state = subprocess.run( self.command )
if state.returncode:
e = ErrorMessage( 1, 'Lvx.doTask(): UNIX command failed ({}).' \
.format( state.returncode ))
return TaskFailed( e )
return self.checkTargets( 'Lvx.doTask' )
def create_doit_tasks ( self ):
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : 'Run {}.'.format( self )
, 'targets' : self.targets
, 'file_dep' : self.file_dep
}

View File

@ -0,0 +1,114 @@
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask, ShellEnv
class MissingTarget ( Exception ): pass
class PnR ( FlowTask ):
"""
Rule to call a Coriolis ``scriptMain()`` script. If no script is provided,
just launch an empty graphical interface.
This class provides the expected ``doit`` function ``create_doit_tasks()``
so it is recognized as a task.
The action to be called by ``doit`` is provided by the ``doTask()`` function.
To create a new instance (task) of this rule, call the static method
``mkRule()``.
"""
textMode = True
@staticmethod
def mkRule ( rule, targets=[], depends=[], script=None ):
"""
Creates a new rule instance (``doit`` task).
:param rule: The name of the rule (``basename`` for ``doit``).
:param targets: A scalar or a list of either files or ``pathlib.Path`` instances.
:param depends: A scalar or a list of file, ``pathlib.Path`` or other rule
instances. In the later case all the *targets* of the rules are
considered as dependencies.
:param script: A callable, typically a ``scriptMain()`` function. The only
requirement is that it should accept one keyworded argument (``**kw``).
"""
return PnR( rule, targets, depends, script )
def __init__ ( self, rule, targets, depends, script ):
super().__init__( rule, targets, depends )
self.script = script
self.addClean( self.targets )
def __repr__ ( self ):
return '<pnr {} depends=[{}]>' \
.format( self.design, ','.join(self.file_dep) )
@property
def design ( self ):
if len(self.targets): return self.targets[0]
return None
def _setCgtBanner ( self, banner ):
banner.setName( 'cgt' )
banner.setPurpose( 'Coriolis Graphical Tool' )
return banner
def doTask ( self ):
from helpers.io import ErrorMessage
if self.design:
print( 'PnR.doTask() on "{}"'.format( self.design ))
else:
print( 'PnR.doTask() run in interactive CGT mode.' )
PnR.textMode = False
import Etesian
import Anabatic
import Katana
import Katabatic
import Kite
import Bora
import Tutorial
import Viewer
import Unicorn
ShellEnv().export()
if self.script and not callable(self.script):
e = ErrorMessage( 1, 'PnR.doTask(): "script" argument is *not* callable.' )
return TaskFailed( e )
if self.script:
self.script( **{} )
if not PnR.textMode:
# Run in graphic mode.
ha = Viewer.HApplication.create( [] )
Viewer.Graphics.enable()
unicorn = Unicorn.UnicornGui.create()
unicorn.setApplicationName ( 'cgt')
unicorn.registerTool ( Etesian.GraphicEtesianEngine.grab() )
unicorn.registerTool ( Kite.GraphicKiteEngine.grab() )
unicorn.registerTool ( Katana.GraphicKatanaEngine.grab() )
unicorn.registerTool ( Bora.GraphicBoraEngine.grab() )
unicorn.registerTool ( Tutorial.GraphicTutorialEngine.grab() )
#unicorn.setAnonNetSelectable(False)
unicorn.setLayerVisible ( "grid" , False );
unicorn.setLayerVisible ( "text.instance" , False );
unicorn.setLayerVisible ( "text.component", False );
self._setCgtBanner(unicorn.getBanner())
unicorn.show()
ha.qtExec()
return self.checkTargets( 'PnR.doTask' )
def create_doit_tasks ( self ):
if self.design: doc = 'Run {}.'.format( self )
else: doc = 'Run plain CGT (no loaded design)'
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : doc
, 'targets' : self.targets
, 'file_dep' : self.file_dep
}

View File

@ -0,0 +1,62 @@
from .copy import Copy
from .yosys import Yosys
from .blif2vst import Blif2Vst
from .cougar import Cougar
from .lvx import Lvx
from .druc import Druc
from .pnr import PnR
from .alias import Alias
from .clean import Clean
PnR.textMode = True
UseClockTree = 0x0001
NoSynthesis = 0x0002
IsChip = 0x0004
def mkRuleSet ( callerGlobals, vlogDesignName, flags=0, extraRtlDepends=[], extrasClean=[] ):
from doDesign import scriptMain
vhdlDesignName = vlogDesignName.lower()
if flags & IsChip:
routedName = 'chip'
else:
routedName = vhdlDesignName
if flags & UseClockTree:
routedName = vhdlDesignName + '_cts'
if not (flags & NoSynthesis):
ruleYosys = Yosys .mkRule( 'yosys', vlogDesignName+'.v' )
ruleB2V = Blif2Vst.mkRule( 'b2v' , [ vhdlDesignName+'.vst'
, vlogDesignName+'.spi' ]
, [ruleYosys]
, flags=0 )
rtlDepends = [ ruleB2V ]
pnrTargets = [ routedName+'_r.ap'
, routedName+'_r.vst'
, routedName+'_r.spi' ]
else:
rtlDepends = [ vhdlDesignName+'.vst' ]
pnrTargets = [ routedName+'_r.ap'
, routedName+'_r.vst'
, routedName+'_r.spi'
, routedName+'.vst'
, routedName+'.spi' ]
rtlDepends += extraRtlDepends
rulePnR = PnR .mkRule( 'pnr', pnrTargets, rtlDepends, scriptMain )
ruleCougar = Cougar.mkRule( 'cougar', routedName+'_r_ext.vst', [rulePnR], flags=Cougar.Verbose )
ruleLvx = Lvx .mkRule( 'lvx'
, [ rulePnR.file_target(1)
, ruleCougar.file_target(0) ]
, flags=Lvx.Flatten )
ruleDruc = Druc .mkRule( 'druc' , [rulePnR], flags=0 )
ruleLayout = Alias .mkRule( 'layout', [rulePnR] )
ruleCgt = PnR .mkRule( 'cgt' )
ruleClean = Clean .mkRule( extrasClean )
for tag in [ 'Yosys', 'B2V', 'PnR', 'Cougar', 'Lvx', 'Druc', 'Cgt', 'Layout', 'Clean' ]:
rule = 'rule' + tag
if rule in locals():
callerGlobals[ rule ] = locals()[ rule ]

View File

@ -0,0 +1,34 @@
from .copy import Copy
from .cougar import Cougar
from .lvx import Lvx
from .druc import Druc
from .pnr import PnR
from .alias import Alias
from .clean import Clean
PnR.textMode = True
def mkRuleSet ( callerGlobals, designName ):
from doDesign import scriptMain
rulePnR = PnR .mkRule( 'pnr', [ designName+'_r.ap'
, designName+'_r.vst'
, designName+'_r.spi'
]
, [ designName+'.vst'
, designName+'.ap'
]
, scriptMain )
ruleCougar = Cougar.mkRule( 'cougar', designName+'_r_ext.vst', [rulePnR], flags=Cougar.Verbose )
ruleLvx = Lvx .mkRule( 'lvx'
, [ rulePnR.file_target(1)
, ruleCougar.file_target(0) ]
, flags=Lvx.Flatten )
ruleDruc = Druc .mkRule( 'druc' , [rulePnR], flags=0 )
ruleLayout = Alias .mkRule( 'layout', [rulePnR] )
ruleCgt = PnR .mkRule( 'cgt' )
ruleClean = Clean .mkRule()
for tag in [ 'PnR', 'Cougar', 'Lvx', 'Druc', 'Cgt', 'Layout', 'Clean' ]:
rule = 'rule' + tag
callerGlobals[ rule ] = locals()[ rule ]

View File

@ -0,0 +1,63 @@
import os
import subprocess
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask, ShellEnv
class MissingTarget ( Exception ): pass
class S2R ( FlowTask ):
NoDenotch = 0x0001
DeleteNames = 0x0002
DoBlackboxes = 0x0004
NoReplaceBlackboxes = 0x0008
Verbose = 0x0010
@staticmethod
def mkRule ( rule, targets, depends=[], flags=0 ):
return S2R( rule, targets, depends, flags )
def __init__ ( self, rule, targets, depends, flags ):
super().__init__( rule, targets, depends )
self.flags = flags
self.inputFile = Path( self.file_depend(0) )
self.outputFile = Path( self.targets[0] )
self.command = [ 's2r' ]
if flags & S2R.NoDenotch: self.command.append( '-t' )
if flags & S2R.DeleteNames: self.command.append( '-c' )
if flags & S2R.DoBlackboxes: self.command.append( '-1' )
if flags & S2R.NoReplaceBlackboxes: self.command.append( '-r' )
if flags & S2R.Verbose: self.command.append( '-v' )
self.command += [ self.inputFile.stem, self.outputFile.stem ]
self.addClean( self.targets )
def __repr__ ( self ):
return '<{}>'.format( ' '.join(self.command) )
def doTask ( self ):
from CRL import AllianceFramework
from helpers.io import ErrorMessage
shellEnv = ShellEnv()
shellEnv[ 'RDS_OUT' ] = self.outputFile.suffix[1:]
shellEnv[ 'MBK_IN_PH' ] = self.inputFile .suffix[1:]
shellEnv.export()
state = subprocess.run( self.command )
if state.returncode:
e = ErrorMessage( 1, 'S2R.doTask(): UNIX command failed ({}).' \
.format( state.returncode ))
return TaskFailed( e )
return self.checkTargets( 'S2R.doTask' )
def create_doit_tasks ( self ):
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : 'Run {}.'.format( self )
, 'targets' : self.targets
, 'file_dep' : self.file_dep
}

View File

@ -0,0 +1,191 @@
import os
from pathlib import Path
from doit.exceptions import TaskFailed
class BadDependency ( Exception ): pass
class DuplicatedRule ( Exception ): pass
class ShellEnv ( object ):
"""
Manage and export to the sub-processes the legacy Alliance variables.
Environment variables stored at class level, should be set once and
for all at startup:
* ``ALLIANCE_TOP``, usually identical to ``CORIOLIS_TOP``.
* ``RDS_TECHNO_NAME``.
* ``CHECK_TOOLKIT``, where the ``alliance-check-toolkit`` is installed.
Mutable environment variables, could be changed in each instance.
Their initial values are extracted from the Coriolis Alliance Framework.
* ``MBK_CATA_LIB``.
* ``MBK_TARGET_LIB``.
* ``MBK_SCALE_X``.
* ``MBK_IN_LO``.
* ``MBK_OUT_LO``.
* ``MBK_IN_PH``.
* ``MBK_OUT_PH``.
* ``MBK_CATAL_NAME``.
* ``RDS_IN``.
* ``RDS_OUT``.
"""
ALLIANCE_TOP = None
RDS_TECHNO_NAME = None
CHECK_TOOLKIT = None
def __init__ ( self ):
self.shellEnv = {}
self.capture()
def __getitem__ ( self, key ):
return self.shellEnv[ key ]
def __setitem__ ( self, key, value ):
self.shellEnv[ key ] = str( value )
def capture ( self ):
"""
Get the default values of the environment variables from the
Coriolis configuration.
"""
import CRL
af = CRL.AllianceFramework.get()
env = af.getEnvironment()
if len(af.getAllianceLibraries()) > 1:
cataLib = [ lib.getPath() for lib in af.getAllianceLibraries()[1:] ]
self.shellEnv[ 'MBK_CATA_LIB' ] = ':'.join( cataLib )
self.shellEnv[ 'MBK_TARGET_LIB' ] = cataLib[0]
self.shellEnv[ 'MBK_SCALE_X' ] = str( env.getSCALE_X() )
self.shellEnv[ 'MBK_IN_LO' ] = env.getIN_LO()
self.shellEnv[ 'MBK_OUT_LO' ] = env.getOUT_LO()
self.shellEnv[ 'MBK_IN_PH' ] = env.getIN_PH()
self.shellEnv[ 'MBK_OUT_PH' ] = env.getOUT_PH()
self.shellEnv[ 'MBK_CATAL_NAME' ] = env.getCATALOG()
self.shellEnv[ 'RDS_IN' ] = 'gds'
self.shellEnv[ 'RDS_OUT' ] = 'gds'
self.shellEnv[ 'ALLIANCE_TOP' ] = ShellEnv.ALLIANCE_TOP
def export ( self ):
"""
Write back the variables into the environement for usage by the
sub-processes.
"""
for variable, value in self.shellEnv.items():
if value is None: continue
os.environ[ variable ] = value
if ShellEnv.RDS_TECHNO_NAME is not None:
os.environ[ 'RDS_TECHNO_NAME' ] = ShellEnv.RDS_TECHNO_NAME
if ShellEnv.CHECK_TOOLKIT is not None:
os.environ[ 'CHECK_TOOLKIT' ] = ShellEnv.CHECK_TOOLKIT
class FlowTask ( object ):
"""
Add extra features over a doit task. This class *do not* provides the
``create_doit_tasks()`` method. It alows task to be chained directly
between them instead of only through dependency/target files.
1. Targets management: targets are always file name, stored as strings.
2. Dependencies management: they can be plain files, pathlib.Path objects
or other tasks. In the later case, the dependencies are the *targets*
of said task, which sould be files, as stated on 1.
3. Perform an early check for homonymous tasks.
4. Keep track of all the targets of all the tasks to provide them for
the special ``clean_flow`` task.
"""
rules = {}
cleanTargets = []
def __init__ ( self, basename, targets, depends ):
"""
Promote ``targets`` and ``depends`` arguments to list if needed.
Check for duplicated rules, then register the rule name at class level.
"""
if FlowTask.hasRule(basename):
raise DuplicatedRule( 'FlowTask.__init__(): Duplicated rule "{}"'.format(basename) )
self.basename = basename
if depends is None: self.depends = []
elif not isinstance(depends,list): self.depends = [ depends ]
else: self.depends = depends
if targets is None: self.targets = []
elif not isinstance(targets,list): self.targets = [ targets ]
else: self.targets = targets
FlowTask.rules[ self.basename ] = self
@staticmethod
def hasRule ( name ):
if name in FlowTask.rules: return True
return False
@property
def file_dep ( self ):
"""
Build the list of dependencies to be passed on to doit (file_dep task dict).
Convert back pathlib.Path object to string. If the dependency is another
FlowTask, pass on it's own targets.
"""
files = []
for depend in self.depends:
if isinstance(depend,str):
files += [ depend ]
elif isinstance(depend,Path):
files += [ depend.as_posix() ]
elif isinstance(depend,FlowTask):
files += depend.targets
else:
raise BadDependency( 'FlowTask.file_dep(): Unsupported kind of dependency {}.'.format(depend) )
return files
def file_target ( self, tindex=0 ):
"""
Access a target, by default, the first one.
"""
if len(self.targets) > tindex:
return self.targets[ tindex ]
return None
def file_depend ( self, dindex=0, tindex=0 ):
"""
Access a dependency, by default the first one. It can be either a
string or a pathlib.Path object. If the dependency itself is a
FlowTask, then it's first *target* is returned. The dependency
can be selected by a ``dindex``, and a ``tindex`` in case of a
FlowTask.
"""
if len(self.depends) > dindex:
if isinstance(self.depends[dindex],FlowTask):
return self.depends[ dindex ].file_target( tindex )
return self.depends[ dindex ]
return None
def checkTargets ( self, methodName ):
"""
Checks that all the the target files have been generated, stop on
error. This is a helper for derived classes.
"""
from helpers.io import ErrorMessage
for target in self.targets:
path = Path( target )
if not path.is_file():
e = ErrorMessage( 1, '{}(): The rule "{}" did *not* generate target "{}".' \
.format( methodName, self.basename, target ))
return TaskFailed( e )
return True
def addClean ( self, targets ):
"""
Add the targets list to the global list. This is a helper method
that has to be explicitely called in derived classes.
"""
FlowTask.cleanTargets += targets

View File

@ -0,0 +1,308 @@
import sys
import os
import socket
from pathlib import Path
from .task import ShellEnv
__all__ = [ 'Where', 'setupCMOS', 'setupCMOS45' ]
class Where ( object ):
coriolisTop = None
allianceTop = None
cellsTop = None
checkToolkit = None
def __init__ ( self, checkToolkit=None ):
if 'CORIOLIS_TOP' in os.environ: Where.coriolisTop = Path( os.environ['CORIOLIS_TOP'] )
if 'ALLIANCE_TOP' in os.environ: Where.allianceTop = Path( os.environ['ALLIANCE_TOP'] )
if 'CELLS_TOP' in os.environ: Where.cellsTop = Path( os.environ['CELLS_TOP'] )
if Where.coriolisTop and not Where.allianceTop: Where.allianceTop = Where.coriolisTop
#print( Where.coriolisTop, Where.allianceTop )
if not Where.coriolisTop:
print( 'technos.Where.__init__(): Unable to locate Coriolis top.' )
if checkToolkit is None:
checkToolkit = Path.home() / 'coriolis-2.x' / 'src' / 'alliance-check-toolkit'
else:
if isinstance(checkToolkit,str):
checkToolkit = Path( checkToolkit )
if not Where.cellsTop:
Where.cellsTop = checkToolkit / 'cells'
Where.checkToolkit = checkToolkit
if not Where.cellsTop and Where.allianceTop:
Where.cellsTop = Where.allianceTop / 'cells'
ShellEnv.ALLIANCE_TOP = Where.allianceTop.as_posix()
def __repr__ ( self ):
if not Where.coriolisTop:
return '<Where coriolisTop=NOT_FOUND>'
return '<Where coriolisTop="{}">'.format( Where.coriolisTop.as_posix() )
def setupCMOS ():
import Cfg
import Viewer
import CRL
import symbolic.cmos
from helpers import overlay, l, u, n
from designflow.yosys import Yosys
Where()
with overlay.CfgCache(priority=Cfg.Parameter.Priority.UserFile) as cfg:
cfg.misc.catchCore = False
cfg.misc.info = False
cfg.misc.paranoid = False
cfg.misc.bug = False
cfg.misc.logMode = True
cfg.misc.verboseLevel1 = True
cfg.misc.verboseLevel2 = True
cfg.misc.minTraceLevel = 1900
cfg.misc.maxTraceLevel = 3000
cfg.katana.eventsLimit = 1000000
cfg.katana.termSatReservedLocal = 6
cfg.katana.termSatThreshold = 9
Viewer.Graphics.setStyle( 'Alliance.Classic [black]' )
af = CRL.AllianceFramework.get()
env = af.getEnvironment()
env.setCLOCK( '^ck$|m_clock|^clk$' )
Yosys.setLiberty( Where.cellsTop / 'sxlib' / 'sxlib.lib' )
ShellEnv.RDS_TECHNO_NAME = (Where.allianceTop / 'etc' / 'cmos.rds').as_posix()
path = None
for pathVar in [ 'PATH', 'path' ]:
if pathVar in os.environ:
path = os.environ[ pathVar ]
os.environ[ pathVar ] = path + ':' + (Where.allianceTop / 'bin').as_posix()
break
def setupCMOS45 ( useNsxlib=False, checkToolkit=None, cellsTop=None ):
import Cfg
import Viewer
import CRL
import symbolic.cmos45
from helpers import overlay, l, u, n
from designflow.yosys import Yosys
Where( checkToolkit )
if cellsTop is None:
cellsTop = Where.cellsTop
else:
if isinstance(cellsTop,str):
cellsTop = Path( cellsTop )
with overlay.CfgCache(priority=Cfg.Parameter.Priority.UserFile) as cfg:
cfg.misc.catchCore = False
cfg.misc.info = False
cfg.misc.paranoid = False
cfg.misc.bug = False
cfg.misc.logMode = True
cfg.misc.verboseLevel1 = True
cfg.misc.verboseLevel2 = True
cfg.misc.minTraceLevel = 1900
cfg.misc.maxTraceLevel = 3000
cfg.katana.eventsLimit = 1000000
cfg.etesian.graphics = 3
cfg.etesian.spaceMargin = 0.05
cfg.etesian.aspectRatio = 1.0
cfg.anabatic.edgeLenght = 24
cfg.anabatic.edgeWidth = 8
if useNsxlib:
cfg.anabatic.routingGauge = 'msxlib4'
cfg.anabatic.topRoutingLayer = 'METAL4'
cfg.katana.termSatReservedLocal = 6
cfg.katana.termSatThreshold = 9
Viewer.Graphics.setStyle( 'Alliance.Classic [black]' )
af = CRL.AllianceFramework.get()
env = af.getEnvironment()
env.setCLOCK( '^ck$|m_clock|^clk$' )
sxlib = cellsTop / 'nsxlib'
iolib = cellsTop / 'niolib'
liberty = sxlib / 'nsxlib.lib'
env.addSYSTEM_LIBRARY( library=iolib.as_posix(), mode=CRL.Environment.Prepend )
env.addSYSTEM_LIBRARY( library=sxlib.as_posix(), mode=CRL.Environment.Prepend )
if not sxlib.is_dir():
print( '[ERROR] technos.setupCMOS45(): sxlib directory do *not* exists:' )
print( ' "{}"'.format(sxlib.as_posix()) )
Yosys.setLiberty( liberty )
ShellEnv.RDS_TECHNO_NAME = (Where.checkToolkit / 'etc' / 'FreePDK45.rds').as_posix()
path = None
for pathVar in [ 'PATH', 'path' ]:
if pathVar in os.environ:
path = os.environ[ pathVar ]
os.environ[ pathVar ] = path + ':' + (Where.allianceTop / 'bin').as_posix()
break
def setupSky130_c4m ( checkToolkit=None, pdkMasterTop=None ):
import Cfg
import Viewer
import CRL
import helpers
from helpers import overlay, l, u, n
from designflow.yosys import Yosys
if isinstance(pdkMasterTop,str):
pdkMasterTop = Path( pdkMasterTop )
ndaDirectory = None
if pdkMasterTop:
ndaDirectory = pdkMasterTop / 'libs.tech' / 'coriolis' / 'techno'
elif not ndaDirectory:
hostname = socket.gethostname()
if hostname.startswith('lepka'):
ndaDirectory = Path( '/dsk/l1/jpc/crypted/soc/techno' )
if not ndaDirectory.is_dir():
print ('[ERROR] You forgot to mount the NDA encrypted directory, stupid!')
else:
ndaDirectory = Path( '/users/soft/techno/techno' )
pdkMasterTop = ndaDirectory
helpers.setNdaTopDir( ndaDirectory.as_posix() )
if not pdkMasterTop.is_dir():
print( '[ERROR] technos.setupSky130_c4m(): pdkMasterTop directory do *not* exists:' )
print( ' "{}"'.format(pdkMasterTop.as_posix()) )
Where( checkToolkit )
from node130.sky130 import techno, StdCellLib #, LibreSOCIO
techno.setup()
StdCellLib.setup()
#LibreSOCIO.setup()
cellsTop = pdkMasterTop / 'libs.ref'
liberty = cellsTop / 'StdCellLib' / 'liberty' / 'StdCellLib_nom.lib'
with overlay.CfgCache(priority=Cfg.Parameter.Priority.UserFile) as cfg:
cfg.misc.catchCore = False
cfg.misc.minTraceLevel = 12300
cfg.misc.maxTraceLevel = 12400
cfg.misc.info = False
cfg.misc.paranoid = False
cfg.misc.bug = False
cfg.misc.logMode = True
cfg.misc.verboseLevel1 = False
cfg.misc.verboseLevel2 = False
cfg.etesian.graphics = 2
cfg.anabatic.topRoutingLayer = 'm4'
cfg.katana.eventsLimit = 4000000
af = CRL.AllianceFramework.get()
lg5 = af.getRoutingGauge( 'StdCellLib' ).getLayerGauge( 5 )
lg5.setType( CRL.RoutingLayerGauge.PowerSupply )
env = af.getEnvironment()
env.setCLOCK( '^sys_clk$|^ck|^jtag_tck$' )
Yosys.setLiberty( liberty )
ShellEnv.CHECK_TOOLKIT = Where.checkToolkit.as_posix()
def setupFreePDK45_c4m ( checkToolkit=None, pdkMasterTop=None ):
import Cfg
import Viewer
import CRL
import helpers
from helpers import overlay, l, u, n
from designflow.yosys import Yosys
if isinstance(pdkMasterTop,str):
pdkMasterTop = Path( pdkMasterTop )
if not pdkMasterTop.is_dir():
print( '[ERROR] technos.setupFreePDK45_c4m(): pdkMasterTop directory do *not* exists:' )
print( ' "{}"'.format(pdkMasterTop.as_posix()) )
sys.path.append( (pdkMasterTop / 'coriolis' / 'techno' / 'etc' / 'coriolis2').resolve().as_posix() )
Where( checkToolkit )
from NDA.node45.freepdk45_c4m import techno, FlexLib, LibreSOCIO
techno.setup()
FlexLib.setup()
LibreSOCIO.setup()
liberty = pdkMasterTop / 'views' / 'FreePDK45' / 'FlexLib' / 'liberty' / 'FlexLib_nom.lib'
with overlay.CfgCache(priority=Cfg.Parameter.Priority.UserFile) as cfg:
cfg.misc.catchCore = False
cfg.misc.minTraceLevel = 12300
cfg.misc.maxTraceLevel = 12400
cfg.misc.info = False
cfg.misc.paranoid = False
cfg.misc.bug = False
cfg.misc.logMode = True
cfg.misc.verboseLevel1 = True
cfg.misc.verboseLevel2 = True
cfg.etesian.graphics = 3
cfg.etesian.spaceMargin = 0.10
cfg.anabatic.topRoutingLayer = 'metal6'
cfg.katana.eventsLimit = 4000000
af = CRL.AllianceFramework.get()
lg5 = af.getRoutingGauge('FlexLib').getLayerGauge( 5 )
lg5.setType( CRL.RoutingLayerGauge.PowerSupply )
env = af.getEnvironment()
env.setCLOCK( '^sys_clk$|^ck|^jtag_tck$' )
Yosys.setLiberty( liberty )
ShellEnv.CHECK_TOOLKIT = Where.checkToolkit.as_posix()
def setupTSMC_c180_c4m ( checkToolkit=None, ndaTop=None ):
import Cfg
import Viewer
import CRL
import helpers
from helpers import overlay, l, u, n
from designflow.yosys import Yosys
ndaDirectory = None
if ndaTop is not None:
if not isinstance(ndaTop,Path):
ndaDirectory = ndaTop
else:
ndaDirectory = Path( ndaTop )
if not ndaDirectory:
hostname = socket.gethostname()
if hostname.startswith('lepka'):
ndaDirectory = Path( '/dsk/l1/jpc/crypted/soc/techno' )
if not ndaDirectory.is_dir():
print( '[ERROR] You forgot to mount the NDA encrypted directory, stupid!' )
else:
ndaDirectory = '/users/soft/techno/techno'
helpers.setNdaTopDir( ndaDirectory )
Where( checkToolkit )
from NDA.node180.tsmc_c018 import techno, FlexLib, LibreSOCIO, LibreSOCMem #, pll
techno.setup()
FlexLib.setup()
LibreSOCIO.setup()
LibreSOCMem.setup()
#pll.setup()
liberty = ndaDirectory / 'etc' / 'coriolis2' / 'NDA' / 'node180' / 'tsmc_c018' / 'FlexLib.lib'
with overlay.CfgCache(priority=Cfg.Parameter.Priority.UserFile) as cfg:
cfg.misc.catchCore = False
cfg.misc.minTraceLevel = 10100
cfg.misc.maxTraceLevel = 10200
cfg.misc.info = False
cfg.misc.paranoid = False
cfg.misc.bug = False
cfg.misc.logMode = True
cfg.misc.verboseLevel1 = True
cfg.misc.verboseLevel2 = True
cfg.etesian.graphics = 3
cfg.etesian.uniformDensity = True
cfg.etesian.spaceMargin = 0.04
cfg.katana.eventsLimit = 4000000
af = CRL.AllianceFramework.get()
env = af.getEnvironment()
env.setCLOCK( '^clk|^reset' )
Yosys.setLiberty( liberty )
ShellEnv.CHECK_TOOLKIT = Where.checkToolkit.as_posix()

View File

@ -0,0 +1,71 @@
import os
import subprocess
from pathlib import Path
from doit.exceptions import TaskFailed
from .task import FlowTask, ShellEnv
class UnsupportedVHdlSuffix ( Exception ): pass
class Vasy ( FlowTask ):
FlagMask = 0x00000011
Verbose = 0x00000001
UseStdLogic = 0x00000002
AddPowerSupplies = 0x00000004
@staticmethod
def mkRule ( rule, targets, depends=[], flags=0 ):
return Vasy( rule, targets, depends, flags )
def __init__ ( self, rule, targets, depends, flags ):
super().__init__( rule, targets, depends )
self.flags = flags
self.vhdlFile = Path( self.file_depend(0) )
if len(self.targets) > 1:
self.outputFile = Path( self.targets[1].stem+'.vbe' )
else:
self.outputFile = Path( self.targets[0] )
self.command = [ 'vasy' ]
if flags & Vasy.Verbose: self.command.append( '-V' )
if flags & Vasy.UseStdLogic: self.command.append( '-S' )
if flags & Vasy.AddPowerSupplies: self.command.append( '-p' )
if self.outputFile.suffix in ('.v', '.vlog'):
self.command.append( '-v' )
elif self.outputFile.suffix in ('.vbe', '.vst'):
self.command.append( '-a' )
elif self.outputFile.suffix ('.vhd',):
self.command.append( '-s' )
if not (self.vhdlFile.suffix in ('.vbe', '.vst', '.vhd', '.vhdl')):
raise UnsupportedVHdlSuffix( 'Vasy.__init__(): File "{}" has unsupported VHDL suffix (not .vbe, .vst, .vhd, .vhdl).' )
self.command += [ '-I', self.vhdlFile.suffix[1:] ]
self.command += [ self.vhdlFile.stem, self.outputFile.stem ]
self.addClean( self.targets )
def __repr__ ( self ):
return '<{}>'.format( ' '.join(self.command) )
def doTask ( self ):
from CRL import AllianceFramework
from helpers.io import ErrorMessage
shellEnv = ShellEnv()
shellEnv.export()
print( ' -> Running "{}" ...'.format( ' '.join(self.command) ))
state = subprocess.run( self.command )
if state.returncode:
e = ErrorMessage( 1, 'Vasy.doTask(): UNIX command failed ({}).' \
.format( state.returncode ))
return TaskFailed( e )
return self.checkTargets( 'Vasy.doTask' )
def create_doit_tasks ( self ):
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : 'Run {}.'.format( self )
, 'targets' : self.targets
, 'file_dep' : self.file_dep
}

View File

@ -0,0 +1,118 @@
import os.path
from pathlib import Path
from pyosys import libyosys as yosys
from doit.exceptions import TaskFailed
from .task import FlowTask
class BadLiberty ( Exception ): pass
class Yosys ( FlowTask ):
_liberty = None
@staticmethod
def setLiberty ( liberty ):
if isinstance(liberty,Path): pass
elif isinstance(liberty,str): liberty = Path( liberty )
else:
raise BadLiberty( '[ERROR] Yosys.setLiberty(): Should be <str> or <Path> ({})' \
.format( liberty ))
if not liberty.is_file():
raise BadLiberty( '[ERROR] Yosys.setLiberty(): File not found "{}"' \
.format( liberty ))
Yosys._liberty = liberty
@staticmethod
def mkRule ( rule, depends, top=None, blackboxes=[], flattens=[] ):
return Yosys( rule, depends, top, blackboxes, flattens )
def __init__ ( self, rule, depends, top, blackboxes, flattens ):
super().__init__( rule, [], depends )
self.success = True
self.blackboxes = blackboxes
self.flattens = flattens
self.depends += blackboxes
if top is not None:
self.top = top
else:
if self.main.find('.') == -1:
self.top = self.main
else:
self.top = '.'.join( self.main.split('.')[0:-1] )
self.targets = [ self.top + '.blif' ]
self.addClean( self.targets )
def __repr__ ( self ):
return '<yosys {} top={} blackboxes=[{}] flattens=[{}]>' \
.format( self.main, self.top, ','.join(self.blackboxes), ','.join(self.flattens) )
@property
def liberty ( self ):
return Yosys._liberty
@property
def main ( self ):
return self.file_depend( 0 )
def _run_pass ( self, command ):
if self.success is not True: return
yosys.run_pass( command, self.tool )
def _loadDesign ( self, design ):
from helpers.io import ErrorMessage
if self.success is not True: return
if not os.path.isfile(design):
e = ErrorMessage( 1, 'Yosys._loadDesign(): Can\'t find design file "{}".'.format( design ))
self.success = TaskFailed( e )
return
if design.endswith('.v' ): self._run_pass( 'read_verilog {}'.format( design ))
elif design.endswith('.il'): self._run_pass( 'read_ilang {}'.format( design ))
else:
e = ErrorMessage( 1, 'Yosys._loadDesign(): Unsupported input format for "{}".'.format( design ))
self.success = TaskFailed( e )
return
def _loadBlackboxes ( self ):
if self.success is not True: return
for blackbox in self.blackboxes:
self._loadDesign( blackbox )
def _doFlattens ( self ):
if self.success is not True: return
flattens = ' '.join( self.flattens )
self._run_pass( 'flatten {}\n'.format( flattens ))
self._run_pass( 'hierarchy -top {}\n'.format( self.top ))
def doTask ( self ):
from helpers.io import ErrorMessage
if self.liberty is None:
e = ErrorMessage( 1, [ 'Yosys.doTask(): "liberty" has not been set' ] )
return TaskFailed( e )
if not self.liberty.is_file():
e = ErrorMessage( 1, [ 'Yosys.doTask(): File not found "{}"'
, '"{}"'.format( self.liberty.as_posix() ) ] )
return TaskFailed( e )
#print( 'Yosys.doTask() on "{}"'.format( self.design ))
self.tool = yosys.Design()
self._loadBlackboxes()
self._loadDesign( self.main )
self._run_pass( 'hierarchy -check -top {}'.format( self.top ))
self._run_pass( 'synth -top {}'.format( self.top ))
self._doFlattens()
self._run_pass( 'memory' )
self._run_pass( 'dfflibmap -liberty {}'.format( self.liberty.as_posix() ))
self._run_pass( 'abc -liberty {}'.format( self.liberty.as_posix() ))
self._run_pass( 'clean' )
self._run_pass( 'write_blif {}'.format( self.targets[0] ))
return self.success
def create_doit_tasks ( self ):
return { 'basename' : self.basename
, 'actions' : [ self.doTask ]
, 'doc' : 'Run {}.'.format( self )
, 'file_dep' : self.file_dep
, 'targets' : self.targets
}

View File

@ -54,6 +54,10 @@
content/pages/users-guide/ViewerTools.rst
content/pages/users-guide/ScriptsPlugins.rst )
set ( designFlowRst content/pages/design-flow/DesignFlow_HTML.rst
content/pages/design-flow/DesignFlow.rst
content/pages/design-flow/QuickStart.rst )
set ( rdsRst content/pages/rds/RDS_HTML.rst
content/pages/rds/RDSpage.rst )
@ -78,6 +82,7 @@
${usersGuideRst}
${pythonTutorialRst}
${pythonCppRst}
${designFlowRst}
${rdsRst}
${stratusRst}
)

View File

@ -0,0 +1,17 @@
.. -*- Mode: rst -*-
.. include:: ../../../etc/definitions.rst
=======================
Design Flow Quick Start
=======================
|pagestylefancy|
.. contents::
|newpage|
.. include:: QuickStart.rst

View File

@ -0,0 +1,37 @@
.. -*- Mode: rst -*-
===========
Design Flow
===========
:slug: design-flow
:date: 2022-12-31 01:00
:Authors: Jean-Paul Chaput
:Contact: <Jean-Paul.Chaput@lip6.fr>
:Version: December 31, 2022 (jpc)
:status: hidden
.. role:: raw-html(raw)
:format: html
.. URLs that changes between the various backends.
.. _Coriolis Tools Documentation: ../documentation.rst
.. _Here: {filename}/pdfs/DesignFlow.pdf
.. _DesignFlow: {filename}/pdfs/DesignFlow.pdf
Printable Version of this Document
==================================
`DesignFlow`_.
.. contents::
:depth: 2
.. include:: ../../../etc/definitions.rst
.. include:: QuickStart.rst

View File

@ -0,0 +1,312 @@
.. -*- Mode: rst -*-
1. Introduction
===============
The goal of the DesignFlow Python tool is to provide a replacement for
Makefiles, especially the complex system that has been developped for
alliance-check-toolkit. It is build upon |DoIt| (DoIt_).
1.1 Task vs. Rules
~~~~~~~~~~~~~~~~~~
Both as a tribute to |Makefile|, to avoid ambiguties with |DoIt| and to remember
that they are task *generators*, the classes defined to create tasks for the design
flow are called ``rules``.
1.2 A Warning About Determinism
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
There is a very important execution difference from a |Makefile|. In a
|Makefile| each rule command is executed in a a separated process, so
information is effectively passed through files which are written then read
from disk. But in |DoIt| we are running inside *one* |Python| process, so while
using Coriolis and the |Hurricane| database, all informations stays *in
memory*. Files are driven, but *not re-read* as the database will use the datas
already present in memory.
This is not whitout consequences about determism. Let's look at two different
scenarii.
1. We run straight from the RTL to the layout, using the rule/task sequence: ::
Yosys => design.blif => blif2vst => design.vst => PnR => design.gds
In this case, while ``design.vst`` is written on disk, the ``PnR`` stage
will not re-read the ``vst`` file and directly access the data in memory.
2. Run in two separated steps, first we create the ``vst`` file: ::
Yosys => design.blif => blif2vst => design.vst
Then, we perform the ``PnR``: ::
design.vst => PnR => design.gds
In this case, as the |DoIt| processess has been restarted between the two
tasks, the ``PnR`` stage *will* read the ``vst`` file.
The determism in |Coriolis| is ensured through the unique identifiers of the
objects, attributed in creation order. So between thoses two scenarii, the
identifiers will change and so the algorithm results. The differences should
be minor as the identifiers are used as a *last ditch* test to sort between
two objects which cost functions are exactly equal, nevertheless, it will
occur.
.. note:: |Coriolis| is deterministic, meaning that each scenario will always
give the same result. The difference is truly *between* scenarii.
2. Using The Design Flow
========================
2.1 Locating the Various Parts
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
One of the most tricky part of setting up the design flow is to locate where
the various components are. The script needs to be able to find:
1. Coriolis, binaries & libraries. This depends widely of your kind of
installation and system. The helper script ``crlenv.py`` supplied
both in |alliance-check-toolkit| and |Coriolis| may help you there.
It looks in all the standard locations (that it is aware of) to try
to find it.
.. note:: Usually, |Alliance| is installed in the same tree as
|Coriolis|, so it's setup can be deduced from it.
2. The configurations files for the technology to be used. Here again,
the ``designflow.technos`` module provides you with a set of
pre-defined configurations for open sources technologie shipped
with |Coriolis|. For unsupported ones, you may write your own,
it should perform the whole initialization of the |Coriolis| and
|Hurricane| database.
3. Optionnaly the |alliance-check-toolkit|.
2.2 Basic Example of |dodo| File
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
This example can be found in |alliance-check-toolkit|, under ``benchs/arlet6502/sky130_c4m``.
.. code:: Python
from designflow.technos import setupSky130_c4m
setupSky130_c4m( checkToolkit='../../..'
, pdkMasterTop='../../../pdkmaster/C4M.Sky130' )
DOIT_CONFIG = { 'verbosity' : 2 }
from designflow.pnr import PnR
from designflow.yosys import Yosys
from designflow.blif2vst import Blif2Vst
from designflow.alias import Alias
from designflow.clean import Clean
PnR.textMode = True
from doDesign import scriptMain
ruleYosys = Yosys .mkRule( 'yosys', 'Arlet6502.v' )
ruleB2V = Blif2Vst.mkRule( 'b2v' , [ 'arlet6502.vst'
, 'Arlet6502.spi' ]
, [ruleYosys]
, flags=0 )
rulePnR = PnR .mkRule( 'pnr' , [ 'arlet6502_cts_r.gds'
, 'arlet6502_cts_r.spi'
, 'arlet6502_cts_r.vst' ]
, [ruleB2V]
, scriptMain )
ruleCgt = PnR .mkRule( 'cgt' )
ruleGds = Alias .mkRule( 'gds', [rulePnR] )
ruleClean = Clean .mkRule()
You can run it with:
.. code:: bash
ego@home:sky130_c4m> ../../../bin/crlenv.py -- doit list
b2v Run <blif2vst arlet6502 depends=[Arlet6502.blif]>.
cgt Run plain CGT (no loaded design)
clean_flow Clean all generated (targets) files.
gds Run <Alias "gds" for "pnr">.
pnr Run <pnr arlet6502_cts_r.gds depends=[arlet6502.vst,Arlet6502.spi]>.
yosys Run <yosys Arlet6502.v top=Arlet6502 blackboxes=[] flattens=[]>.
ego@home:sky130_c4m> ../../../bin/crlenv.py -- doit pnr
ego@home:sky130_c4m> ../../../bin/crlenv.py -- doit clean_flow
Let's have a detailed look on the various parts of the script.
A. **Choosing the technology** Here, we load the predefined configuration for
SkyWater 130nm. We also have to give the location of the
|alliance-check-toolkit|, it may be relative or absolute.
If you want to use another one, it up to you to configure |Coriolis| at
this point by any means you see fit.
.. code:: Python
from designflow.technos import setupSky130_c4m
setupSky130_c4m( checkToolkit='../../..'
, pdkMasterTop='../../../pdkmaster/C4M.Sky130' )
B. **Loading the various task/rule generators that we will use**, from the
``designflow`` namespace. The rules are named from the tool they
encapsulate.
.. code:: Python
from designflow.pnr import PnR
from designflow.yosys import Yosys
from designflow.blif2vst import Blif2Vst
from designflow.alias import Alias
from designflow.clean import Clean
PnR.textMode = True
C. **Creating the rule set.** Each rule generator as a static method ``mkRule()``
to create a new task. The three first parameters are always:
1. The name of the task (the ``basename`` for |DoIt|).
2. A target or list of targets, must be files or ``pathlib.Path`` objects.
3. A dependency or list of dependencies, they can be files, ``pathlib.Path``
objects, or other tasks. We can see that the ``Blif2Vst`` rule uses
directly the ``Yosys`` one (the input file will be the *first* target
of the ``Yosys`` rule).
4. Any extra parameters. A set of flag for ``Blif2Vst``. The ``PnR`` rule takes
an optional callable argument, *any* callable. In this case we import the
``scriptMain()`` function from ``doDesign()``.
There are two more special rules:
* ``Alias``, to rename a rule. It this case ``gds`` is defined as an alias to
``PnR`` (because it generate the |gds| file).
* ``Clean`` to create a rule that will remove all the generated targets.
.. note:: The clean rule is named ``clean_flow`` because |DoIt| already have
a ``clean`` arguments which would shadow it.
.. code:: Python
PnR.textMode = True
from doDesign import scriptMain
ruleYosys = Yosys .mkRule( 'yosys', 'Arlet6502.v' )
ruleB2V = Blif2Vst.mkRule( 'b2v' , [ 'arlet6502.vst'
, 'Arlet6502.spi' ]
, [ruleYosys]
, flags=0 )
rulePnR = PnR .mkRule( 'pnr' , [ 'arlet6502_cts_r.gds'
, 'arlet6502_cts_r.spi'
, 'arlet6502_cts_r.vst' ]
, [ruleB2V]
, scriptMain )
ruleCgt = PnR .mkRule( 'cgt' )
ruleGds = Alias .mkRule( 'gds', [rulePnR] )
ruleClean = Clean .mkRule()
3. Rules's Catalog
==================
3.1 Alliance Legacy Tools
~~~~~~~~~~~~~~~~~~~~~~~~~
Support for the |Alliance| legacy tools. They are run through sub-processes.
For more detailed documentation about those tools, refer to their |man| pages.
#. ``Asimut``, |VHDL| simulator.
#. ``Boog``, logical synthesys. Map a |VHDL| behavioral description to a standard
cell library (works with ``boom`` & ``loon``).
#. ``Boom``, behavioral description optimizer (works with ``boog`` & ``loon``).
#. ``Cougar``, symbolic layout extractor.
#. ``Dreal``, real layout (|GDS|, |CIF|) editor.
#. ``Druc``, symbolic layout |DRC|.
#. ``Flatph``, flatten a layout, fully or in part.
#. ``Genpat``, pattern generator (for use with ``Asimut``).
#. ``Graal``, symbolic layout editor.
#. ``Loon``, netlist optimizer for surface and/or delay (works with ``boom`` & ``boog``).
#. ``Lvx``, netlist comparator (*Layout* *Versus* *Extracted*).
#. ``S2R``, symbolic to real translator (to |GDS| or |CIF|).
#. ``Vasy``, Alliance |VHDL| subset translator towards standard |VHDL| or |Verilog|.
3.2 Current Tools
~~~~~~~~~~~~~~~~~
#. ``Blif2Vst``, translate a |blif| netlist (|Yosys| output) into the |Alliance|
netlist format |vst|. This is a |Python| script calling |Coriolis| directly
integrated inside the task.
#. ``PnR``, maybe a bit of a misnomer. This is a caller to function that the user have
to write to perform the P&R as he sees fit for it's particular design.
#. ``Yosys``, call the |Yosys| logical synthesyser. Provide an off the shelf subset
of functionalities to perform classic use cases.
3.3 Utility Rules
~~~~~~~~~~~~~~~~~
#. ``Alias``, create a name alias for a rule.
#. ``Clean``, remove all the generated targets of all the rules. The name of the
rule is ``clean_flow` to not interfer with the |DoIt| clean arguments.
Files not part of any rules targets can be added to be removeds. Then,
to actually remove them, add the ``--extras`` flag to the command line.
.. code:: bash
ego@home:sky130_c4m> ../../../bin/crlenv.py -- doit clean_flow --extras
#. ``Copy``, copy a file into the current directory.
3.4 Rule Sets
~~~~~~~~~~~~~
For commonly used sequences of rules, some predefined sets are defined.
#. ``alliancesynth``, to apply the logical |Alliance| logical synthesis
set of tools. From |VHDL| to optimized |vst|. The set is as follow: ::
x.vbe => boom => x_boom.vbe => boog => x_boog.vst => loon => x.vst
An additional rule using ``vasy`` is triggered if the input format
is standard |VHDL|.
#. ``pnrcheck``, complete flow from |Verilog| to symbolic layout, with
|DRC| and |LVX| checks. Uses |Yosys| for synthesis.
#. ``routecheck``, perform the routing, the |DRC| and |LVX| check on an
already placed design. Use symbolic layout.

View File

@ -51,6 +51,9 @@ Coriolis Documentation
`Coriolis User's Guide <{filename}/pages/users-guide/UsersGuide_HTML.rst>`_ |br|
Using the software
`Design Flow Quick Start <{filename}/pages/design-flow/DesignFlow_HTML.rst>`_ |br|
Tool to build your design
`Python Tutorial <{filename}/pages/python-tutorial/PythonTutorial_HTML.rst>`_ |br|
A Tutorial to use Coriolis through Python

View File

@ -4,7 +4,7 @@
2. Implementation
=================
We do not try to provides an iterface as sleek as ``pybind11`` that completely
We do not try to provides an interface as sleek as ``pybind11`` that completely
hides the Python/C API. Instead we keep mostly visible the classic structure of
the Python/C API but we provides templates to automate as much as possible the
boring tasks (and code duplication). This way, if we need a very specific

Binary file not shown.

Binary file not shown.

View File

@ -60,7 +60,6 @@
.. |Debian| replace:: :sc:`Debian`
.. |Ubuntu| replace:: :sc:`Ubuntu`
.. |MOSIS| replace:: :sc:`mosis`
.. |Blif| replace:: :sc:`blif`
.. |TSMC| replace:: :sc:`tsmc`
.. |AMS| replace:: :sc:`ams`
.. |XFAB| replace:: :sc:`xfab`
@ -139,6 +138,7 @@
.. |pdf| replace:: :sc:`pdf`
.. |UTF-8| replace:: :sc:`utf-8`
.. |Python| replace:: :sc:`Python`
.. |DoIt| replace:: :sc:`DoIt`
.. |TCL| replace:: :sc:`tcl`
.. |Linux| replace:: :sc:`Linux`
.. |MacPorts| replace:: :sc:`MacPorts`
@ -163,6 +163,8 @@
.. |flex| replace:: :cb:`flex`
.. |struct| replace:: :cb:`struct`
.. |Makefile| replace:: :cb:`Makefile`
.. |dodo| replace:: :cb:`dodo`
.. |man| replace:: :cb:`man`
.. |KeyUp| replace:: :fboxtt:`Up`
@ -210,6 +212,7 @@
.. _Yosys: http://www.clifford.at/yosys/
.. _GHDL: https://github.com/ghdl/ghdl
.. _Si2: http://www.si2.org/
.. _DoIt: https://pydoit.org/contents.html
.. _GPL: http://www.gnu.org/copyleft/gpl.txt
.. _LGPL: https://www.gnu.org/licenses/lgpl-3.0.html
@ -226,10 +229,14 @@
.. |layout| replace:: *layout*
.. |layouts| replace:: *layouts*
.. |VLSI| replace:: :sc:`vlsi`
.. |DRC| replace:: :sc:`drc`
.. |LVX| replace:: :sc:`lvx`
.. |CIF| replace:: :sc:`cif`
.. |GDS| replace:: :sc:`gds`
.. |GDSII| replace:: :sc:`gdsii`
.. |CMOS| replace:: :sc:`cmos`
.. |VHDL| replace:: :sc:`vhdl`
.. |Verilog| replace:: :sc:`Verilog`
.. |NWELL| replace:: :sc:`nwell`
.. |POWER| replace:: :sc:`power`
.. |GROUND| replace:: :sc:`ground`
@ -251,5 +258,6 @@
.. |Collections| replace:: *Collections*
.. |ap| replace:: :cb:`ap`
.. |vst| replace:: :cb:`vst`
.. |blif| replace:: :cb:`blif`
.. |kgr| replace:: :cb:`kgr`
.. |dot_conf| replace:: :cb:`.conf`

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="./pages/.html"></a></li>
<li><a class="dropdown-item " href="./pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="./pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="./pages/.html"></a></li>
<li><a class="dropdown-item " href="./pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="./pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="./pages/.html"></a></li>
<li><a class="dropdown-item " href="./pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="./pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="./pages/.html"></a></li>
<li><a class="dropdown-item " href="./pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="./pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="./pages/.html"></a></li>
<li><a class="dropdown-item " href="./pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="./pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="./pages/.html"></a></li>
<li><a class="dropdown-item " href="./pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="./pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="./pages/.html"></a></li>
<li><a class="dropdown-item " href="./pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="./pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="./pages/.html"></a></li>
<li><a class="dropdown-item " href="./pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="./pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>

View File

@ -0,0 +1,559 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1">
<meta name="description" content="1. Introduction The goal of the DesignFlow Python tool is to provide a replacement for Makefiles, especially the complex system that has been developped for alliance-check-toolkit. It is build...">
<meta name="keywords" content="">
<link rel="icon" href="../favicon.ico">
<title> - Coriolis VLSI CAD Tools [offline]</title>
<!-- Stylesheets -->
<link href="../theme/css/bootstrap.css" rel="stylesheet">
<link href="../theme/css/fonts.css" rel="stylesheet">
<link href="../theme/css/nest.css" rel="stylesheet">
<link href="../theme/css/pygment.css" rel="stylesheet">
<link href="../theme/css/coriolis.css" rel="stylesheet">
<!-- /Stylesheets -->
<script src="../theme/js/jquery.min.js"></script>
<script src="../theme/js/bootstrap.min.js"></script>
<!-- RSS Feeds -->
<!-- /RSS Feeds -->
<!-- HTML5 shim and Respond.js for IE8 support of HTML5 elements and media queries -->
<!--[if lt IE 9]>
<script src="https://oss.maxcdn.com/html5shiv/3.7.2/html5shiv.min.js"></script>
<script src="https://oss.maxcdn.com/respond/1.4.2/respond.min.js"></script>
<![endif]-->
</head>
<body>
<!-- Header -->
<div class="header-container" style="background: linear-gradient(rgba(0, 0, 0, 0.2), rgba(0, 0, 0, 0.2)), url('../images/common/layout-motif-faded-4.png'); background-position: center; ">
<!--
<div class="container">
<nav class="navbar navbar-default">
<div class="container-fluid">
<div class="navbar-header">
<a class="navbar-brand" href="../"><img class="mr20" src="../images/common/Coriolis-logo-white-4-small.png" alt="logo">Coriolis VLSI CAD Tools [offline]</a>
</div>
<ul class="nav navbar-nav">
<li><a href="../pages/gitlab.html">Git</a></li>
<li><a href="../pages/documentation.html">Documentation</a></li>
<li class="dropdown">
<button class="btn btn-default dropdown-toggle" type="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="true">
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item active" href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
</li>
</ul>
</div>
</nav>
</div> <!-- navbar container -->
-->
<!-- Static navbar -->
<div class="container">
<div class="header-nav">
<div class="header-logo">
<a class="pull-left" href="../"><img class="mr20" src="../images/common/Coriolis-logo-white-4-small.png" alt="logo">Coriolis VLSI CAD Tools [offline]</a>
</div>
<div class="nav pull-right">
<a href="../pages/gitlab.html">Git</a>
<a href="../pages/documentation.html">Documentation</a>
</div>
<div class="nav pull-right">
<div class="dropdown">
<button class="btn btn-default dropdown-toggle" type="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="true">
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item active" href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
</div>
</div>
</div>
</div>
<!-- /Static navbar -->
<!-- Header -->
<div class="container header-wrapper">
<div class="row">
<div class="col-lg-12">
<div class="header-content">
<a href="https://www.lip6.fr/"><img class="mr20" height="60px" src="../images/common/LogoLIP6Blanc.png" alt="LIP6"></a>
<a href="https://www.sorbonne-universite.fr/"><img class="mr20" height="60px" src="../images/common/logo-SU-blanc-700px.png" alt="Sorbonne Universite"></a>
<a href="https://www.cnrs.fr/"><img class="mr20" height="60px" src="../images/common/LOGO-cnrs-white-large.png" alt="CNRS"></a>
<h1 class="header-title text-uppercase"></h1>
<div class="header-underline"></div>
</div>
</div>
</div>
</div>
<!-- /Header -->
</div>
<!-- /Header -->
<!-- Content -->
<div class="container content">
<!-- -*- Mode: rst -*- -->
<div class="section" id="introduction">
<h2>1. Introduction</h2>
<p>The goal of the DesignFlow Python tool is to provide a replacement for
Makefiles, especially the complex system that has been developped for
alliance-check-toolkit. It is build upon <a href="#id1"><span class="problematic" id="id2">|DoIt|</span></a> (<a href="#id91"><span class="problematic" id="id92">DoIt_</span></a>).</p>
<div class="section" id="task-vs-rules">
<h3>1.1 Task vs. Rules</h3>
<p>Both as a tribute to <a href="#id3"><span class="problematic" id="id4">|Makefile|</span></a>, to avoid ambiguties with <a href="#id5"><span class="problematic" id="id6">|DoIt|</span></a> and to remember
that they are task <em>generators</em>, the classes defined to create tasks for the design
flow are called <tt class="docutils literal">rules</tt>.</p>
</div>
<div class="section" id="a-warning-about-determinism">
<h3>1.2 A Warning About Determinism</h3>
<p>There is a very important execution difference from a <a href="#id7"><span class="problematic" id="id8">|Makefile|</span></a>. In a
<a href="#id9"><span class="problematic" id="id10">|Makefile|</span></a> each rule command is executed in a a separated process, so
information is effectively passed through files which are written then read
from disk. But in <a href="#id11"><span class="problematic" id="id12">|DoIt|</span></a> we are running inside <em>one</em> <a href="#id13"><span class="problematic" id="id14">|Python|</span></a> process, so while
using Coriolis and the <a href="#id15"><span class="problematic" id="id16">|Hurricane|</span></a> database, all informations stays <em>in
memory</em>. Files are driven, but <em>not re-read</em> as the database will use the datas
already present in memory.</p>
<p>This is not whitout consequences about determism. Let's look at two different
scenarii.</p>
<ol class="arabic">
<li><p class="first">We run straight from the RTL to the layout, using the rule/task sequence:</p>
<pre class="literal-block">
Yosys =&gt; design.blif =&gt; blif2vst =&gt; design.vst =&gt; PnR =&gt; design.gds
</pre>
<p>In this case, while <tt class="docutils literal">design.vst</tt> is written on disk, the <tt class="docutils literal">PnR</tt> stage
will not re-read the <tt class="docutils literal">vst</tt> file and directly access the data in memory.</p>
</li>
<li><p class="first">Run in two separated steps, first we create the <tt class="docutils literal">vst</tt> file:</p>
<pre class="literal-block">
Yosys =&gt; design.blif =&gt; blif2vst =&gt; design.vst
</pre>
<p>Then, we perform the <tt class="docutils literal">PnR</tt>:</p>
<pre class="literal-block">
design.vst =&gt; PnR =&gt; design.gds
</pre>
<p>In this case, as the <a href="#id17"><span class="problematic" id="id18">|DoIt|</span></a> processess has been restarted between the two
tasks, the <tt class="docutils literal">PnR</tt> stage <em>will</em> read the <tt class="docutils literal">vst</tt> file.</p>
</li>
</ol>
<p>The determism in <a href="#id19"><span class="problematic" id="id20">|Coriolis|</span></a> is ensured through the unique identifiers of the
objects, attributed in creation order. So between thoses two scenarii, the
identifiers will change and so the algorithm results. The differences should
be minor as the identifiers are used as a <em>last ditch</em> test to sort between
two objects which cost functions are exactly equal, nevertheless, it will
occur.</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last"><a href="#id21"><span class="problematic" id="id22">|Coriolis|</span></a> is deterministic, meaning that each scenario will always
give the same result. The difference is truly <em>between</em> scenarii.</p>
</div>
</div>
</div>
<div class="section" id="using-the-design-flow">
<h2>2. Using The Design Flow</h2>
<div class="section" id="locating-the-various-parts">
<h3>2.1 Locating the Various Parts</h3>
<p>One of the most tricky part of setting up the design flow is to locate where
the various components are. The script needs to be able to find:</p>
<ol class="arabic">
<li><p class="first">Coriolis, binaries &amp; libraries. This depends widely of your kind of
installation and system. The helper script <tt class="docutils literal">crlenv.py</tt> supplied
both in <a href="#id23"><span class="problematic" id="id24">|alliance-check-toolkit|</span></a> and <a href="#id25"><span class="problematic" id="id26">|Coriolis|</span></a> may help you there.
It looks in all the standard locations (that it is aware of) to try
to find it.</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last">Usually, <a href="#id27"><span class="problematic" id="id28">|Alliance|</span></a> is installed in the same tree as
<a href="#id29"><span class="problematic" id="id30">|Coriolis|</span></a>, so it's setup can be deduced from it.</p>
</div>
</li>
<li><p class="first">The configurations files for the technology to be used. Here again,
the <tt class="docutils literal">designflow.technos</tt> module provides you with a set of
pre-defined configurations for open sources technologie shipped
with <a href="#id31"><span class="problematic" id="id32">|Coriolis|</span></a>. For unsupported ones, you may write your own,
it should perform the whole initialization of the <a href="#id33"><span class="problematic" id="id34">|Coriolis|</span></a> and
<a href="#id35"><span class="problematic" id="id36">|Hurricane|</span></a> database.</p>
</li>
<li><p class="first">Optionnaly the <a href="#id37"><span class="problematic" id="id38">|alliance-check-toolkit|</span></a>.</p>
</li>
</ol>
</div>
<div class="section" id="basic-example-of-dodo-file">
<h3>2.2 Basic Example of <a href="#id39"><span class="problematic" id="id40">|dodo|</span></a> File</h3>
<p>This example can be found in <a href="#id41"><span class="problematic" id="id42">|alliance-check-toolkit|</span></a>, under <tt class="docutils literal">benchs/arlet6502/sky130_c4m</tt>.</p>
<pre class="code Python literal-block">
<span class="kn">from</span> <span class="nn">designflow.technos</span> <span class="kn">import</span> <span class="n">setupSky130_c4m</span>
<span class="n">setupSky130_c4m</span><span class="p">(</span> <span class="n">checkToolkit</span><span class="o">=</span><span class="s1">'../../..'</span>
<span class="p">,</span> <span class="n">pdkMasterTop</span><span class="o">=</span><span class="s1">'../../../pdkmaster/C4M.Sky130'</span> <span class="p">)</span>
<span class="n">DOIT_CONFIG</span> <span class="o">=</span> <span class="p">{</span> <span class="s1">'verbosity'</span> <span class="p">:</span> <span class="mi">2</span> <span class="p">}</span>
<span class="kn">from</span> <span class="nn">designflow.pnr</span> <span class="kn">import</span> <span class="n">PnR</span>
<span class="kn">from</span> <span class="nn">designflow.yosys</span> <span class="kn">import</span> <span class="n">Yosys</span>
<span class="kn">from</span> <span class="nn">designflow.blif2vst</span> <span class="kn">import</span> <span class="n">Blif2Vst</span>
<span class="kn">from</span> <span class="nn">designflow.alias</span> <span class="kn">import</span> <span class="n">Alias</span>
<span class="kn">from</span> <span class="nn">designflow.clean</span> <span class="kn">import</span> <span class="n">Clean</span>
<span class="n">PnR</span><span class="o">.</span><span class="n">textMode</span> <span class="o">=</span> <span class="kc">True</span>
<span class="kn">from</span> <span class="nn">doDesign</span> <span class="kn">import</span> <span class="n">scriptMain</span>
<span class="n">ruleYosys</span> <span class="o">=</span> <span class="n">Yosys</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'yosys'</span><span class="p">,</span> <span class="s1">'Arlet6502.v'</span> <span class="p">)</span>
<span class="n">ruleB2V</span> <span class="o">=</span> <span class="n">Blif2Vst</span><span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'b2v'</span> <span class="p">,</span> <span class="p">[</span> <span class="s1">'arlet6502.vst'</span>
<span class="p">,</span> <span class="s1">'Arlet6502.spi'</span> <span class="p">]</span>
<span class="p">,</span> <span class="p">[</span><span class="n">ruleYosys</span><span class="p">]</span>
<span class="p">,</span> <span class="n">flags</span><span class="o">=</span><span class="mi">0</span> <span class="p">)</span>
<span class="n">rulePnR</span> <span class="o">=</span> <span class="n">PnR</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'pnr'</span> <span class="p">,</span> <span class="p">[</span> <span class="s1">'arlet6502_cts_r.gds'</span>
<span class="p">,</span> <span class="s1">'arlet6502_cts_r.spi'</span>
<span class="p">,</span> <span class="s1">'arlet6502_cts_r.vst'</span> <span class="p">]</span>
<span class="p">,</span> <span class="p">[</span><span class="n">ruleB2V</span><span class="p">]</span>
<span class="p">,</span> <span class="n">scriptMain</span> <span class="p">)</span>
<span class="n">ruleCgt</span> <span class="o">=</span> <span class="n">PnR</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'cgt'</span> <span class="p">)</span>
<span class="n">ruleGds</span> <span class="o">=</span> <span class="n">Alias</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'gds'</span><span class="p">,</span> <span class="p">[</span><span class="n">rulePnR</span><span class="p">]</span> <span class="p">)</span>
<span class="n">ruleClean</span> <span class="o">=</span> <span class="n">Clean</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">()</span>
</pre>
<p>You can run it with:</p>
<pre class="code bash literal-block">
ego&#64;home:sky130_c4m&gt; ../../../bin/crlenv.py -- doit list
b2v Run &lt;blif2vst arlet6502 <span class="nv">depends</span><span class="o">=[</span>Arlet6502.blif<span class="o">]</span>&gt;.
cgt Run plain CGT <span class="o">(</span>no loaded design<span class="o">)</span>
clean_flow Clean all generated <span class="o">(</span>targets<span class="o">)</span> files.
gds Run &lt;Alias <span class="s2">&quot;gds&quot;</span> <span class="k">for</span> <span class="s2">&quot;pnr&quot;</span>&gt;.
pnr Run &lt;pnr arlet6502_cts_r.gds <span class="nv">depends</span><span class="o">=[</span>arlet6502.vst,Arlet6502.spi<span class="o">]</span>&gt;.
yosys Run &lt;yosys Arlet6502.v <span class="nv">top</span><span class="o">=</span>Arlet6502 <span class="nv">blackboxes</span><span class="o">=[]</span> <span class="nv">flattens</span><span class="o">=[]</span>&gt;.
ego&#64;home:sky130_c4m&gt; ../../../bin/crlenv.py -- doit pnr
ego&#64;home:sky130_c4m&gt; ../../../bin/crlenv.py -- doit clean_flow
</pre>
<p>Let's have a detailed look on the various parts of the script.</p>
<ol class="upperalpha">
<li><p class="first"><strong>Choosing the technology</strong> Here, we load the predefined configuration for
SkyWater 130nm. We also have to give the location of the
<a href="#id43"><span class="problematic" id="id44">|alliance-check-toolkit|</span></a>, it may be relative or absolute.</p>
<p>If you want to use another one, it up to you to configure <a href="#id45"><span class="problematic" id="id46">|Coriolis|</span></a> at
this point by any means you see fit.</p>
<pre class="code Python literal-block">
<span class="kn">from</span> <span class="nn">designflow.technos</span> <span class="kn">import</span> <span class="n">setupSky130_c4m</span>
<span class="n">setupSky130_c4m</span><span class="p">(</span> <span class="n">checkToolkit</span><span class="o">=</span><span class="s1">'../../..'</span>
<span class="p">,</span> <span class="n">pdkMasterTop</span><span class="o">=</span><span class="s1">'../../../pdkmaster/C4M.Sky130'</span> <span class="p">)</span>
</pre>
</li>
<li><p class="first"><strong>Loading the various task/rule generators that we will use</strong>, from the
<tt class="docutils literal">designflow</tt> namespace. The rules are named from the tool they
encapsulate.</p>
<pre class="code Python literal-block">
<span class="kn">from</span> <span class="nn">designflow.pnr</span> <span class="kn">import</span> <span class="n">PnR</span>
<span class="kn">from</span> <span class="nn">designflow.yosys</span> <span class="kn">import</span> <span class="n">Yosys</span>
<span class="kn">from</span> <span class="nn">designflow.blif2vst</span> <span class="kn">import</span> <span class="n">Blif2Vst</span>
<span class="kn">from</span> <span class="nn">designflow.alias</span> <span class="kn">import</span> <span class="n">Alias</span>
<span class="kn">from</span> <span class="nn">designflow.clean</span> <span class="kn">import</span> <span class="n">Clean</span>
<span class="n">PnR</span><span class="o">.</span><span class="n">textMode</span> <span class="o">=</span> <span class="kc">True</span>
</pre>
</li>
<li><p class="first"><strong>Creating the rule set.</strong> Each rule generator as a static method <tt class="docutils literal">mkRule()</tt>
to create a new task. The three first parameters are always:</p>
<ol class="arabic simple">
<li>The name of the task (the <tt class="docutils literal">basename</tt> for <a href="#id47"><span class="problematic" id="id48">|DoIt|</span></a>).</li>
<li>A target or list of targets, must be files or <tt class="docutils literal">pathlib.Path</tt> objects.</li>
<li>A dependency or list of dependencies, they can be files, <tt class="docutils literal">pathlib.Path</tt>
objects, or other tasks. We can see that the <tt class="docutils literal">Blif2Vst</tt> rule uses
directly the <tt class="docutils literal">Yosys</tt> one (the input file will be the <em>first</em> target
of the <tt class="docutils literal">Yosys</tt> rule).</li>
<li>Any extra parameters. A set of flag for <tt class="docutils literal">Blif2Vst</tt>. The <tt class="docutils literal">PnR</tt> rule takes
an optional callable argument, <em>any</em> callable. In this case we import the
<tt class="docutils literal">scriptMain()</tt> function from <tt class="docutils literal">doDesign()</tt>.</li>
</ol>
<p>There are two more special rules:</p>
<ul>
<li><p class="first"><tt class="docutils literal">Alias</tt>, to rename a rule. It this case <tt class="docutils literal">gds</tt> is defined as an alias to
<tt class="docutils literal">PnR</tt> (because it generate the <a href="#id49"><span class="problematic" id="id50">|gds|</span></a> file).</p>
</li>
<li><p class="first"><tt class="docutils literal">Clean</tt> to create a rule that will remove all the generated targets.</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last">The clean rule is named <tt class="docutils literal">clean_flow</tt> because <a href="#id51"><span class="problematic" id="id52">|DoIt|</span></a> already have
a <tt class="docutils literal">clean</tt> arguments which would shadow it.</p>
</div>
</li>
</ul>
<pre class="code Python literal-block">
<span class="n">PnR</span><span class="o">.</span><span class="n">textMode</span> <span class="o">=</span> <span class="kc">True</span>
<span class="kn">from</span> <span class="nn">doDesign</span> <span class="kn">import</span> <span class="n">scriptMain</span>
<span class="n">ruleYosys</span> <span class="o">=</span> <span class="n">Yosys</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'yosys'</span><span class="p">,</span> <span class="s1">'Arlet6502.v'</span> <span class="p">)</span>
<span class="n">ruleB2V</span> <span class="o">=</span> <span class="n">Blif2Vst</span><span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'b2v'</span> <span class="p">,</span> <span class="p">[</span> <span class="s1">'arlet6502.vst'</span>
<span class="p">,</span> <span class="s1">'Arlet6502.spi'</span> <span class="p">]</span>
<span class="p">,</span> <span class="p">[</span><span class="n">ruleYosys</span><span class="p">]</span>
<span class="p">,</span> <span class="n">flags</span><span class="o">=</span><span class="mi">0</span> <span class="p">)</span>
<span class="n">rulePnR</span> <span class="o">=</span> <span class="n">PnR</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'pnr'</span> <span class="p">,</span> <span class="p">[</span> <span class="s1">'arlet6502_cts_r.gds'</span>
<span class="p">,</span> <span class="s1">'arlet6502_cts_r.spi'</span>
<span class="p">,</span> <span class="s1">'arlet6502_cts_r.vst'</span> <span class="p">]</span>
<span class="p">,</span> <span class="p">[</span><span class="n">ruleB2V</span><span class="p">]</span>
<span class="p">,</span> <span class="n">scriptMain</span> <span class="p">)</span>
<span class="n">ruleCgt</span> <span class="o">=</span> <span class="n">PnR</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'cgt'</span> <span class="p">)</span>
<span class="n">ruleGds</span> <span class="o">=</span> <span class="n">Alias</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'gds'</span><span class="p">,</span> <span class="p">[</span><span class="n">rulePnR</span><span class="p">]</span> <span class="p">)</span>
<span class="n">ruleClean</span> <span class="o">=</span> <span class="n">Clean</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">()</span>
</pre>
</li>
</ol>
</div>
</div>
<div class="section" id="rules-s-catalog">
<h2>3. Rules's Catalog</h2>
<div class="section" id="alliance-legacy-tools">
<h3>3.1 Alliance Legacy Tools</h3>
<p>Support for the <a href="#id53"><span class="problematic" id="id54">|Alliance|</span></a> legacy tools. They are run through sub-processes.
For more detailed documentation about those tools, refer to their <a href="#id55"><span class="problematic" id="id56">|man|</span></a> pages.</p>
<ol class="arabic simple">
<li><tt class="docutils literal">Asimut</tt>, <a href="#id57"><span class="problematic" id="id58">|VHDL|</span></a> simulator.</li>
<li><tt class="docutils literal">Boog</tt>, logical synthesys. Map a <a href="#id59"><span class="problematic" id="id60">|VHDL|</span></a> behavioral description to a standard
cell library (works with <tt class="docutils literal">boom</tt> &amp; <tt class="docutils literal">loon</tt>).</li>
<li><tt class="docutils literal">Boom</tt>, behavioral description optimizer (works with <tt class="docutils literal">boog</tt> &amp; <tt class="docutils literal">loon</tt>).</li>
<li><tt class="docutils literal">Cougar</tt>, symbolic layout extractor.</li>
<li><tt class="docutils literal">Dreal</tt>, real layout (<a href="#id61"><span class="problematic" id="id62">|GDS|</span></a>, <a href="#id63"><span class="problematic" id="id64">|CIF|</span></a>) editor.</li>
<li><tt class="docutils literal">Druc</tt>, symbolic layout <a href="#id65"><span class="problematic" id="id66">|DRC|</span></a>.</li>
<li><tt class="docutils literal">Flatph</tt>, flatten a layout, fully or in part.</li>
<li><tt class="docutils literal">Genpat</tt>, pattern generator (for use with <tt class="docutils literal">Asimut</tt>).</li>
<li><tt class="docutils literal">Graal</tt>, symbolic layout editor.</li>
<li><tt class="docutils literal">Loon</tt>, netlist optimizer for surface and/or delay (works with <tt class="docutils literal">boom</tt> &amp; <tt class="docutils literal">boog</tt>).</li>
<li><tt class="docutils literal">Lvx</tt>, netlist comparator (<em>Layout</em> <em>Versus</em> <em>Extracted</em>).</li>
<li><tt class="docutils literal">S2R</tt>, symbolic to real translator (to <a href="#id67"><span class="problematic" id="id68">|GDS|</span></a> or <a href="#id69"><span class="problematic" id="id70">|CIF|</span></a>).</li>
<li><tt class="docutils literal">Vasy</tt>, Alliance <a href="#id71"><span class="problematic" id="id72">|VHDL|</span></a> subset translator towards standard <a href="#id73"><span class="problematic" id="id74">|VHDL|</span></a> or <a href="#id75"><span class="problematic" id="id76">|Verilog|</span></a>.</li>
</ol>
</div>
<div class="section" id="current-tools">
<h3>3.2 Current Tools</h3>
<ol class="arabic simple">
<li><tt class="docutils literal">Blif2Vst</tt>, translate a <a href="#id77"><span class="problematic" id="id78">|blif|</span></a> netlist (<a href="#id79"><span class="problematic" id="id80">|Yosys|</span></a> output) into the <a href="#id81"><span class="problematic" id="id82">|Alliance|</span></a>
netlist format <a href="#id83"><span class="problematic" id="id84">|vst|</span></a>. This is a <a href="#id85"><span class="problematic" id="id86">|Python|</span></a> script calling <a href="#id87"><span class="problematic" id="id88">|Coriolis|</span></a> directly
integrated inside the task.</li>
<li><tt class="docutils literal">PnR</tt>, maybe a bit of a misnomer. This is a caller to function that the user have
to write to perform the P&amp;R as he sees fit for it's particular design.</li>
<li><tt class="docutils literal">Yosys</tt>, call the <a href="#id89"><span class="problematic" id="id90">|Yosys|</span></a> logical synthesyser. Provide an off the shelf subset
of functionalities to perform classic use cases.</li>
</ol>
</div>
<div class="section" id="utility-rules">
<h3>3.3 Utility Rules</h3>
<ol class="arabic">
<li><p class="first"><tt class="docutils literal">Alias</tt>, create a name alias for a rule.</p>
</li>
<li><p class="first"><tt class="docutils literal">Clean</tt>, remove all the generated targets of all the rules. The name of the
rule is <tt class="docutils literal">clean_flow` to not interfer with the |DoIt| clean arguments.
Files not part of any rules targets can be added to be removeds. Then,
to actually remove them, add the <span class="pre">``--extras</span></tt> flag to the command line.</p>
<pre class="code bash literal-block">
ego&#64;home:sky130_c4m&gt; ../../../bin/crlenv.py -- doit clean_flow --extras
</pre>
</li>
<li><p class="first"><tt class="docutils literal">Copy</tt>, copy a file into the current directory.</p>
</li>
</ol>
</div>
<div class="section" id="rule-sets">
<h3>3.4 Rule Sets</h3>
<ol class="arabic simple">
<li>alliancesynth</li>
<li>pnrcheck</li>
<li>routecheck</li>
</ol>
</div>
</div>
<div class="system-messages section">
<h2>Docutils System Messages</h2>
<div class="system-message" id="id1">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 7); <em><a href="#id2">backlink</a></em></p>
Undefined substitution referenced: &quot;DoIt&quot;.</div>
<div class="system-message" id="id3">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 15); <em><a href="#id4">backlink</a></em></p>
Undefined substitution referenced: &quot;Makefile&quot;.</div>
<div class="system-message" id="id5">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 15); <em><a href="#id6">backlink</a></em></p>
Undefined substitution referenced: &quot;DoIt&quot;.</div>
<div class="system-message" id="id7">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 24); <em><a href="#id8">backlink</a></em></p>
Undefined substitution referenced: &quot;Makefile&quot;.</div>
<div class="system-message" id="id9">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 24); <em><a href="#id10">backlink</a></em></p>
Undefined substitution referenced: &quot;Makefile&quot;.</div>
<div class="system-message" id="id11">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 24); <em><a href="#id12">backlink</a></em></p>
Undefined substitution referenced: &quot;DoIt&quot;.</div>
<div class="system-message" id="id13">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 24); <em><a href="#id14">backlink</a></em></p>
Undefined substitution referenced: &quot;Python&quot;.</div>
<div class="system-message" id="id15">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 24); <em><a href="#id16">backlink</a></em></p>
Undefined substitution referenced: &quot;Hurricane&quot;.</div>
<div class="system-message" id="id17">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 50); <em><a href="#id18">backlink</a></em></p>
Undefined substitution referenced: &quot;DoIt&quot;.</div>
<div class="system-message" id="id19">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 53); <em><a href="#id20">backlink</a></em></p>
Undefined substitution referenced: &quot;Coriolis&quot;.</div>
<div class="system-message" id="id21">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 60); <em><a href="#id22">backlink</a></em></p>
Undefined substitution referenced: &quot;Coriolis&quot;.</div>
<div class="system-message" id="id23">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 74); <em><a href="#id24">backlink</a></em></p>
Undefined substitution referenced: &quot;alliance-check-toolkit&quot;.</div>
<div class="system-message" id="id25">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 74); <em><a href="#id26">backlink</a></em></p>
Undefined substitution referenced: &quot;Coriolis&quot;.</div>
<div class="system-message" id="id27">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 80); <em><a href="#id28">backlink</a></em></p>
Undefined substitution referenced: &quot;Alliance&quot;.</div>
<div class="system-message" id="id29">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 80); <em><a href="#id30">backlink</a></em></p>
Undefined substitution referenced: &quot;Coriolis&quot;.</div>
<div class="system-message" id="id31">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 83); <em><a href="#id32">backlink</a></em></p>
Undefined substitution referenced: &quot;Coriolis&quot;.</div>
<div class="system-message" id="id33">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 83); <em><a href="#id34">backlink</a></em></p>
Undefined substitution referenced: &quot;Coriolis&quot;.</div>
<div class="system-message" id="id35">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 83); <em><a href="#id36">backlink</a></em></p>
Undefined substitution referenced: &quot;Hurricane&quot;.</div>
<div class="system-message" id="id37">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 90); <em><a href="#id38">backlink</a></em></p>
Undefined substitution referenced: &quot;alliance-check-toolkit&quot;.</div>
<div class="system-message" id="id39">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 94); <em><a href="#id40">backlink</a></em></p>
Undefined substitution referenced: &quot;dodo&quot;.</div>
<div class="system-message" id="id41">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 96); <em><a href="#id42">backlink</a></em></p>
Undefined substitution referenced: &quot;alliance-check-toolkit&quot;.</div>
<div class="system-message" id="id43">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 148); <em><a href="#id44">backlink</a></em></p>
Undefined substitution referenced: &quot;alliance-check-toolkit&quot;.</div>
<div class="system-message" id="id45">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 152); <em><a href="#id46">backlink</a></em></p>
Undefined substitution referenced: &quot;Coriolis&quot;.</div>
<div class="system-message" id="id47">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 180); <em><a href="#id48">backlink</a></em></p>
Undefined substitution referenced: &quot;DoIt&quot;.</div>
<div class="system-message" id="id49">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 195); <em><a href="#id50">backlink</a></em></p>
Undefined substitution referenced: &quot;gds&quot;.</div>
<div class="system-message" id="id51">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 200); <em><a href="#id52">backlink</a></em></p>
Undefined substitution referenced: &quot;DoIt&quot;.</div>
<div class="system-message" id="id53">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 231); <em><a href="#id54">backlink</a></em></p>
Undefined substitution referenced: &quot;Alliance&quot;.</div>
<div class="system-message" id="id55">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 231); <em><a href="#id56">backlink</a></em></p>
Undefined substitution referenced: &quot;man&quot;.</div>
<div class="system-message" id="id57">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 234); <em><a href="#id58">backlink</a></em></p>
Undefined substitution referenced: &quot;VHDL&quot;.</div>
<div class="system-message" id="id59">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 236); <em><a href="#id60">backlink</a></em></p>
Undefined substitution referenced: &quot;VHDL&quot;.</div>
<div class="system-message" id="id61">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 243); <em><a href="#id62">backlink</a></em></p>
Undefined substitution referenced: &quot;GDS&quot;.</div>
<div class="system-message" id="id63">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 243); <em><a href="#id64">backlink</a></em></p>
Undefined substitution referenced: &quot;CIF&quot;.</div>
<div class="system-message" id="id65">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 245); <em><a href="#id66">backlink</a></em></p>
Undefined substitution referenced: &quot;DRC&quot;.</div>
<div class="system-message" id="id67">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 257); <em><a href="#id68">backlink</a></em></p>
Undefined substitution referenced: &quot;GDS&quot;.</div>
<div class="system-message" id="id69">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 257); <em><a href="#id70">backlink</a></em></p>
Undefined substitution referenced: &quot;CIF&quot;.</div>
<div class="system-message" id="id71">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 259); <em><a href="#id72">backlink</a></em></p>
Undefined substitution referenced: &quot;VHDL&quot;.</div>
<div class="system-message" id="id73">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 259); <em><a href="#id74">backlink</a></em></p>
Undefined substitution referenced: &quot;VHDL&quot;.</div>
<div class="system-message" id="id75">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 259); <em><a href="#id76">backlink</a></em></p>
Undefined substitution referenced: &quot;Verilog&quot;.</div>
<div class="system-message" id="id77">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 265); <em><a href="#id78">backlink</a></em></p>
Undefined substitution referenced: &quot;blif&quot;.</div>
<div class="system-message" id="id79">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 265); <em><a href="#id80">backlink</a></em></p>
Undefined substitution referenced: &quot;Yosys&quot;.</div>
<div class="system-message" id="id81">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 265); <em><a href="#id82">backlink</a></em></p>
Undefined substitution referenced: &quot;Alliance&quot;.</div>
<div class="system-message" id="id83">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 265); <em><a href="#id84">backlink</a></em></p>
Undefined substitution referenced: &quot;vst&quot;.</div>
<div class="system-message" id="id85">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 265); <em><a href="#id86">backlink</a></em></p>
Undefined substitution referenced: &quot;Python&quot;.</div>
<div class="system-message" id="id87">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 265); <em><a href="#id88">backlink</a></em></p>
Undefined substitution referenced: &quot;Coriolis&quot;.</div>
<div class="system-message" id="id89">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 272); <em><a href="#id90">backlink</a></em></p>
Undefined substitution referenced: &quot;Yosys&quot;.</div>
<div class="system-message" id="id91">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">/dsk/l1/jpc/coriolis-2.x/src/coriolis/documentation/content/pages/design-flow/QuickStart.rst</tt>, line 7); <em><a href="#id92">backlink</a></em></p>
Unknown target name: &quot;doit&quot;.</div>
</div>
</div>
<!-- /Content -->
<!-- Footer -->
<div class="footer gradient-2">
<div class="container footer-container ">
<div class="row">
<div class="col-xs-4 col-sm-3 col-md-3 col-lg-3">
<div class="footer-title">Social</div>
<ul class="list-unstyled">
</ul>
</div>
<div class="col-xs-4 col-sm-3 col-md-3 col-lg-2">
</div>
<div class="col-xs-4 col-sm-3 col-md-3 col-lg-3">
<div class="footer-title">Links</div>
<ul class="list-unstyled">
<li><a href="https://coriolis.lip6.fr/" target="_blank">Alliance/Coriolis</a></li>
<li><a href="https://www-soc.lip6.fr/" target="_blank">CIAN Team Website</a></li>
<li><a href="https://f-si.org" target="_blank">Free Silicon Foundation</a></li>
</ul>
</div>
<div class="col-xs-12 col-sm-3 col-md-3 col-lg-4">
<p class="pull-right text-right">
<small><em>Proudly powered by <a href="http://docs.getpelican.com/" target="_blank">pelican</a></em></small><br/>
<small><em><span class="sc">NEST</span> theme by <a href="https://github.com/molivier" target="_blank">molivier</a></em></small><br/>
<small>Copyright © 2020-2020 Sorbonne Universite</small>
</p>
</div>
</div>
</div>
</div>
<!-- /Footer -->
</body>
</html>

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -143,6 +145,15 @@
<!-- Hurricane Concepts. -->
<!-- -*- Mode: rst -*- -->
<!-- Acronyms & Names -->
<div class="system-message">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">content/pages/check-toolkit/README.rst</tt>, line 4)</p>
Duplicate substitution definition name: &quot;Verilog&quot;.</div>
<div class="system-message">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">content/pages/check-toolkit/README.rst</tt>, line 9)</p>
Duplicate substitution definition name: &quot;DRC&quot;.</div>
<div class="system-message">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">content/pages/check-toolkit/README.rst</tt>, line 78)</p>
Duplicate substitution definition name: &quot;blif&quot;.</div>
</div>
<div class="section" id="toolkit-purpose">
<h2><a class="toc-backref" href="#id4">Toolkit Purpose</a></h2>

View File

@ -0,0 +1,454 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1">
<meta name="description" content="Printable Version of this Document DesignFlow. Contents Printable Version of this Document 1. Introduction 1.1 Task vs. Rules 1.2 A Warning About Determinism 2. Using The Design Flow 2.1 Locating...">
<meta name="keywords" content="">
<link rel="icon" href="../favicon.ico">
<title>Design Flow - Coriolis VLSI CAD Tools [offline]</title>
<!-- Stylesheets -->
<link href="../theme/css/bootstrap.css" rel="stylesheet">
<link href="../theme/css/fonts.css" rel="stylesheet">
<link href="../theme/css/nest.css" rel="stylesheet">
<link href="../theme/css/pygment.css" rel="stylesheet">
<link href="../theme/css/coriolis.css" rel="stylesheet">
<!-- /Stylesheets -->
<script src="../theme/js/jquery.min.js"></script>
<script src="../theme/js/bootstrap.min.js"></script>
<!-- RSS Feeds -->
<!-- /RSS Feeds -->
<!-- HTML5 shim and Respond.js for IE8 support of HTML5 elements and media queries -->
<!--[if lt IE 9]>
<script src="https://oss.maxcdn.com/html5shiv/3.7.2/html5shiv.min.js"></script>
<script src="https://oss.maxcdn.com/respond/1.4.2/respond.min.js"></script>
<![endif]-->
</head>
<body>
<!-- Header -->
<div class="header-container" style="background: linear-gradient(rgba(0, 0, 0, 0.2), rgba(0, 0, 0, 0.2)), url('../images/common/layout-motif-faded-4.png'); background-position: center; ">
<!--
<div class="container">
<nav class="navbar navbar-default">
<div class="container-fluid">
<div class="navbar-header">
<a class="navbar-brand" href="../"><img class="mr20" src="../images/common/Coriolis-logo-white-4-small.png" alt="logo">Coriolis VLSI CAD Tools [offline]</a>
</div>
<ul class="nav navbar-nav">
<li><a href="../pages/gitlab.html">Git</a></li>
<li><a href="../pages/documentation.html">Documentation</a></li>
<li class="dropdown">
<button class="btn btn-default dropdown-toggle" type="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="true">
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
</li>
</ul>
</div>
</nav>
</div> <!-- navbar container -->
-->
<!-- Static navbar -->
<div class="container">
<div class="header-nav">
<div class="header-logo">
<a class="pull-left" href="../"><img class="mr20" src="../images/common/Coriolis-logo-white-4-small.png" alt="logo">Coriolis VLSI CAD Tools [offline]</a>
</div>
<div class="nav pull-right">
<a href="../pages/gitlab.html">Git</a>
<a href="../pages/documentation.html">Documentation</a>
</div>
<div class="nav pull-right">
<div class="dropdown">
<button class="btn btn-default dropdown-toggle" type="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="true">
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
</div>
</div>
</div>
</div>
<!-- /Static navbar -->
<!-- Header -->
<div class="container header-wrapper">
<div class="row">
<div class="col-lg-12">
<div class="header-content">
<a href="https://www.lip6.fr/"><img class="mr20" height="60px" src="../images/common/LogoLIP6Blanc.png" alt="LIP6"></a>
<a href="https://www.sorbonne-universite.fr/"><img class="mr20" height="60px" src="../images/common/logo-SU-blanc-700px.png" alt="Sorbonne Universite"></a>
<a href="https://www.cnrs.fr/"><img class="mr20" height="60px" src="../images/common/LOGO-cnrs-white-large.png" alt="CNRS"></a>
<h1 class="header-title text-uppercase">Design Flow</h1>
<div class="header-underline"></div>
</div>
</div>
</div>
</div>
<!-- /Header -->
</div>
<!-- /Header -->
<!-- Content -->
<div class="container content">
<!-- -*- Mode: rst -*- -->
<!-- URLs that changes between the various backends. -->
<div class="section" id="printable-version-of-this-document">
<h2><a class="toc-backref" href="#id2">Printable Version of this Document</a></h2>
<p><a class="reference external" href="../pdfs/DesignFlow.pdf">DesignFlow</a>.</p>
<div class="contents topic" id="contents">
<p class="topic-title">Contents</p>
<ul class="simple">
<li><a class="reference internal" href="#printable-version-of-this-document" id="id2">Printable Version of this Document</a></li>
<li><a class="reference internal" href="#introduction" id="id3">1. Introduction</a><ul>
<li><a class="reference internal" href="#task-vs-rules" id="id4">1.1 Task vs. Rules</a></li>
<li><a class="reference internal" href="#a-warning-about-determinism" id="id5">1.2 A Warning About Determinism</a></li>
</ul>
</li>
<li><a class="reference internal" href="#using-the-design-flow" id="id6">2. Using The Design Flow</a><ul>
<li><a class="reference internal" href="#locating-the-various-parts" id="id7">2.1 Locating the Various Parts</a></li>
<li><a class="reference internal" href="#basic-example-of-dodo-file" id="id8">2.2 Basic Example of <span class="cb">dodo</span> File</a></li>
</ul>
</li>
<li><a class="reference internal" href="#rules-s-catalog" id="id9">3. Rules's Catalog</a><ul>
<li><a class="reference internal" href="#alliance-legacy-tools" id="id10">3.1 Alliance Legacy Tools</a></li>
<li><a class="reference internal" href="#current-tools" id="id11">3.2 Current Tools</a></li>
<li><a class="reference internal" href="#utility-rules" id="id12">3.3 Utility Rules</a></li>
<li><a class="reference internal" href="#rule-sets" id="id13">3.4 Rule Sets</a></li>
</ul>
</li>
</ul>
</div>
<!-- -*- Mode: rst; explicit-buffer-name: "definition.rst<documentation/etc>" -*- -->
<!-- HTML/LaTeX backends mixed macros. -->
<!-- Acronyms & names. -->
<!-- URLs -->
<!-- Standard CAO/VLSI Concepts. -->
<!-- Alliance & MBK Concepts -->
<!-- Hurricane Concepts. -->
<!-- -*- Mode: rst -*- -->
</div>
<div class="section" id="introduction">
<h2><a class="toc-backref" href="#id3">1. Introduction</a></h2>
<p>The goal of the DesignFlow Python tool is to provide a replacement for
Makefiles, especially the complex system that has been developped for
alliance-check-toolkit. It is build upon <span class="sc">DoIt</span> (<a class="reference external" href="https://pydoit.org/contents.html">DoIt</a>).</p>
<div class="section" id="task-vs-rules">
<h3><a class="toc-backref" href="#id4">1.1 Task vs. Rules</a></h3>
<p>Both as a tribute to <span class="cb">Makefile</span>, to avoid ambiguties with <span class="sc">DoIt</span> and to remember
that they are task <em>generators</em>, the classes defined to create tasks for the design
flow are called <tt class="docutils literal">rules</tt>.</p>
</div>
<div class="section" id="a-warning-about-determinism">
<h3><a class="toc-backref" href="#id5">1.2 A Warning About Determinism</a></h3>
<p>There is a very important execution difference from a <span class="cb">Makefile</span>. In a
<span class="cb">Makefile</span> each rule command is executed in a a separated process, so
information is effectively passed through files which are written then read
from disk. But in <span class="sc">DoIt</span> we are running inside <em>one</em> <span class="sc">Python</span> process, so while
using Coriolis and the <span class="sc">Hurricane</span> database, all informations stays <em>in
memory</em>. Files are driven, but <em>not re-read</em> as the database will use the datas
already present in memory.</p>
<p>This is not whitout consequences about determism. Let's look at two different
scenarii.</p>
<ol class="arabic">
<li><p class="first">We run straight from the RTL to the layout, using the rule/task sequence:</p>
<pre class="literal-block">
Yosys =&gt; design.blif =&gt; blif2vst =&gt; design.vst =&gt; PnR =&gt; design.gds
</pre>
<p>In this case, while <tt class="docutils literal">design.vst</tt> is written on disk, the <tt class="docutils literal">PnR</tt> stage
will not re-read the <tt class="docutils literal">vst</tt> file and directly access the data in memory.</p>
</li>
<li><p class="first">Run in two separated steps, first we create the <tt class="docutils literal">vst</tt> file:</p>
<pre class="literal-block">
Yosys =&gt; design.blif =&gt; blif2vst =&gt; design.vst
</pre>
<p>Then, we perform the <tt class="docutils literal">PnR</tt>:</p>
<pre class="literal-block">
design.vst =&gt; PnR =&gt; design.gds
</pre>
<p>In this case, as the <span class="sc">DoIt</span> processess has been restarted between the two
tasks, the <tt class="docutils literal">PnR</tt> stage <em>will</em> read the <tt class="docutils literal">vst</tt> file.</p>
</li>
</ol>
<p>The determism in <span class="sc">Coriolis</span> is ensured through the unique identifiers of the
objects, attributed in creation order. So between thoses two scenarii, the
identifiers will change and so the algorithm results. The differences should
be minor as the identifiers are used as a <em>last ditch</em> test to sort between
two objects which cost functions are exactly equal, nevertheless, it will
occur.</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last"><span class="sc">Coriolis</span> is deterministic, meaning that each scenario will always
give the same result. The difference is truly <em>between</em> scenarii.</p>
</div>
</div>
</div>
<div class="section" id="using-the-design-flow">
<h2><a class="toc-backref" href="#id6">2. Using The Design Flow</a></h2>
<div class="section" id="locating-the-various-parts">
<h3><a class="toc-backref" href="#id7">2.1 Locating the Various Parts</a></h3>
<p>One of the most tricky part of setting up the design flow is to locate where
the various components are. The script needs to be able to find:</p>
<ol class="arabic">
<li><p class="first">Coriolis, binaries &amp; libraries. This depends widely of your kind of
installation and system. The helper script <tt class="docutils literal">crlenv.py</tt> supplied
both in <tt class="docutils literal"><span class="pre">alliance-check-toolkit</span></tt> and <span class="sc">Coriolis</span> may help you there.
It looks in all the standard locations (that it is aware of) to try
to find it.</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last">Usually, <span class="sc">Alliance</span> is installed in the same tree as
<span class="sc">Coriolis</span>, so it's setup can be deduced from it.</p>
</div>
</li>
<li><p class="first">The configurations files for the technology to be used. Here again,
the <tt class="docutils literal">designflow.technos</tt> module provides you with a set of
pre-defined configurations for open sources technologie shipped
with <span class="sc">Coriolis</span>. For unsupported ones, you may write your own,
it should perform the whole initialization of the <span class="sc">Coriolis</span> and
<span class="sc">Hurricane</span> database.</p>
</li>
<li><p class="first">Optionnaly the <tt class="docutils literal"><span class="pre">alliance-check-toolkit</span></tt>.</p>
</li>
</ol>
</div>
<div class="section" id="basic-example-of-dodo-file">
<h3><a class="toc-backref" href="#id8">2.2 Basic Example of <span class="cb">dodo</span> File</a></h3>
<p>This example can be found in <tt class="docutils literal"><span class="pre">alliance-check-toolkit</span></tt>, under <tt class="docutils literal">benchs/arlet6502/sky130_c4m</tt>.</p>
<pre class="code Python literal-block">
<span class="kn">from</span> <span class="nn">designflow.technos</span> <span class="kn">import</span> <span class="n">setupSky130_c4m</span>
<span class="n">setupSky130_c4m</span><span class="p">(</span> <span class="n">checkToolkit</span><span class="o">=</span><span class="s1">'../../..'</span>
<span class="p">,</span> <span class="n">pdkMasterTop</span><span class="o">=</span><span class="s1">'../../../pdkmaster/C4M.Sky130'</span> <span class="p">)</span>
<span class="n">DOIT_CONFIG</span> <span class="o">=</span> <span class="p">{</span> <span class="s1">'verbosity'</span> <span class="p">:</span> <span class="mi">2</span> <span class="p">}</span>
<span class="kn">from</span> <span class="nn">designflow.pnr</span> <span class="kn">import</span> <span class="n">PnR</span>
<span class="kn">from</span> <span class="nn">designflow.yosys</span> <span class="kn">import</span> <span class="n">Yosys</span>
<span class="kn">from</span> <span class="nn">designflow.blif2vst</span> <span class="kn">import</span> <span class="n">Blif2Vst</span>
<span class="kn">from</span> <span class="nn">designflow.alias</span> <span class="kn">import</span> <span class="n">Alias</span>
<span class="kn">from</span> <span class="nn">designflow.clean</span> <span class="kn">import</span> <span class="n">Clean</span>
<span class="n">PnR</span><span class="o">.</span><span class="n">textMode</span> <span class="o">=</span> <span class="kc">True</span>
<span class="kn">from</span> <span class="nn">doDesign</span> <span class="kn">import</span> <span class="n">scriptMain</span>
<span class="n">ruleYosys</span> <span class="o">=</span> <span class="n">Yosys</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'yosys'</span><span class="p">,</span> <span class="s1">'Arlet6502.v'</span> <span class="p">)</span>
<span class="n">ruleB2V</span> <span class="o">=</span> <span class="n">Blif2Vst</span><span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'b2v'</span> <span class="p">,</span> <span class="p">[</span> <span class="s1">'arlet6502.vst'</span>
<span class="p">,</span> <span class="s1">'Arlet6502.spi'</span> <span class="p">]</span>
<span class="p">,</span> <span class="p">[</span><span class="n">ruleYosys</span><span class="p">]</span>
<span class="p">,</span> <span class="n">flags</span><span class="o">=</span><span class="mi">0</span> <span class="p">)</span>
<span class="n">rulePnR</span> <span class="o">=</span> <span class="n">PnR</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'pnr'</span> <span class="p">,</span> <span class="p">[</span> <span class="s1">'arlet6502_cts_r.gds'</span>
<span class="p">,</span> <span class="s1">'arlet6502_cts_r.spi'</span>
<span class="p">,</span> <span class="s1">'arlet6502_cts_r.vst'</span> <span class="p">]</span>
<span class="p">,</span> <span class="p">[</span><span class="n">ruleB2V</span><span class="p">]</span>
<span class="p">,</span> <span class="n">scriptMain</span> <span class="p">)</span>
<span class="n">ruleCgt</span> <span class="o">=</span> <span class="n">PnR</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'cgt'</span> <span class="p">)</span>
<span class="n">ruleGds</span> <span class="o">=</span> <span class="n">Alias</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'gds'</span><span class="p">,</span> <span class="p">[</span><span class="n">rulePnR</span><span class="p">]</span> <span class="p">)</span>
<span class="n">ruleClean</span> <span class="o">=</span> <span class="n">Clean</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">()</span>
</pre>
<p>You can run it with:</p>
<pre class="code bash literal-block">
ego&#64;home:sky130_c4m&gt; ../../../bin/crlenv.py -- doit list
b2v Run &lt;blif2vst arlet6502 <span class="nv">depends</span><span class="o">=[</span>Arlet6502.blif<span class="o">]</span>&gt;.
cgt Run plain CGT <span class="o">(</span>no loaded design<span class="o">)</span>
clean_flow Clean all generated <span class="o">(</span>targets<span class="o">)</span> files.
gds Run &lt;Alias <span class="s2">&quot;gds&quot;</span> <span class="k">for</span> <span class="s2">&quot;pnr&quot;</span>&gt;.
pnr Run &lt;pnr arlet6502_cts_r.gds <span class="nv">depends</span><span class="o">=[</span>arlet6502.vst,Arlet6502.spi<span class="o">]</span>&gt;.
yosys Run &lt;yosys Arlet6502.v <span class="nv">top</span><span class="o">=</span>Arlet6502 <span class="nv">blackboxes</span><span class="o">=[]</span> <span class="nv">flattens</span><span class="o">=[]</span>&gt;.
ego&#64;home:sky130_c4m&gt; ../../../bin/crlenv.py -- doit pnr
ego&#64;home:sky130_c4m&gt; ../../../bin/crlenv.py -- doit clean_flow
</pre>
<p>Let's have a detailed look on the various parts of the script.</p>
<ol class="upperalpha">
<li><p class="first"><strong>Choosing the technology</strong> Here, we load the predefined configuration for
SkyWater 130nm. We also have to give the location of the
<tt class="docutils literal"><span class="pre">alliance-check-toolkit</span></tt>, it may be relative or absolute.</p>
<p>If you want to use another one, it up to you to configure <span class="sc">Coriolis</span> at
this point by any means you see fit.</p>
<pre class="code Python literal-block">
<span class="kn">from</span> <span class="nn">designflow.technos</span> <span class="kn">import</span> <span class="n">setupSky130_c4m</span>
<span class="n">setupSky130_c4m</span><span class="p">(</span> <span class="n">checkToolkit</span><span class="o">=</span><span class="s1">'../../..'</span>
<span class="p">,</span> <span class="n">pdkMasterTop</span><span class="o">=</span><span class="s1">'../../../pdkmaster/C4M.Sky130'</span> <span class="p">)</span>
</pre>
</li>
<li><p class="first"><strong>Loading the various task/rule generators that we will use</strong>, from the
<tt class="docutils literal">designflow</tt> namespace. The rules are named from the tool they
encapsulate.</p>
<pre class="code Python literal-block">
<span class="kn">from</span> <span class="nn">designflow.pnr</span> <span class="kn">import</span> <span class="n">PnR</span>
<span class="kn">from</span> <span class="nn">designflow.yosys</span> <span class="kn">import</span> <span class="n">Yosys</span>
<span class="kn">from</span> <span class="nn">designflow.blif2vst</span> <span class="kn">import</span> <span class="n">Blif2Vst</span>
<span class="kn">from</span> <span class="nn">designflow.alias</span> <span class="kn">import</span> <span class="n">Alias</span>
<span class="kn">from</span> <span class="nn">designflow.clean</span> <span class="kn">import</span> <span class="n">Clean</span>
<span class="n">PnR</span><span class="o">.</span><span class="n">textMode</span> <span class="o">=</span> <span class="kc">True</span>
</pre>
</li>
<li><p class="first"><strong>Creating the rule set.</strong> Each rule generator as a static method <tt class="docutils literal">mkRule()</tt>
to create a new task. The three first parameters are always:</p>
<ol class="arabic simple">
<li>The name of the task (the <tt class="docutils literal">basename</tt> for <span class="sc">DoIt</span>).</li>
<li>A target or list of targets, must be files or <tt class="docutils literal">pathlib.Path</tt> objects.</li>
<li>A dependency or list of dependencies, they can be files, <tt class="docutils literal">pathlib.Path</tt>
objects, or other tasks. We can see that the <tt class="docutils literal">Blif2Vst</tt> rule uses
directly the <tt class="docutils literal">Yosys</tt> one (the input file will be the <em>first</em> target
of the <tt class="docutils literal">Yosys</tt> rule).</li>
<li>Any extra parameters. A set of flag for <tt class="docutils literal">Blif2Vst</tt>. The <tt class="docutils literal">PnR</tt> rule takes
an optional callable argument, <em>any</em> callable. In this case we import the
<tt class="docutils literal">scriptMain()</tt> function from <tt class="docutils literal">doDesign()</tt>.</li>
</ol>
<p>There are two more special rules:</p>
<ul>
<li><p class="first"><tt class="docutils literal">Alias</tt>, to rename a rule. It this case <tt class="docutils literal">gds</tt> is defined as an alias to
<tt class="docutils literal">PnR</tt> (because it generate the <span class="sc">gds</span> file).</p>
</li>
<li><p class="first"><tt class="docutils literal">Clean</tt> to create a rule that will remove all the generated targets.</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last">The clean rule is named <tt class="docutils literal">clean_flow</tt> because <span class="sc">DoIt</span> already have
a <tt class="docutils literal">clean</tt> arguments which would shadow it.</p>
</div>
</li>
</ul>
<pre class="code Python literal-block">
<span class="n">PnR</span><span class="o">.</span><span class="n">textMode</span> <span class="o">=</span> <span class="kc">True</span>
<span class="kn">from</span> <span class="nn">doDesign</span> <span class="kn">import</span> <span class="n">scriptMain</span>
<span class="n">ruleYosys</span> <span class="o">=</span> <span class="n">Yosys</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'yosys'</span><span class="p">,</span> <span class="s1">'Arlet6502.v'</span> <span class="p">)</span>
<span class="n">ruleB2V</span> <span class="o">=</span> <span class="n">Blif2Vst</span><span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'b2v'</span> <span class="p">,</span> <span class="p">[</span> <span class="s1">'arlet6502.vst'</span>
<span class="p">,</span> <span class="s1">'Arlet6502.spi'</span> <span class="p">]</span>
<span class="p">,</span> <span class="p">[</span><span class="n">ruleYosys</span><span class="p">]</span>
<span class="p">,</span> <span class="n">flags</span><span class="o">=</span><span class="mi">0</span> <span class="p">)</span>
<span class="n">rulePnR</span> <span class="o">=</span> <span class="n">PnR</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'pnr'</span> <span class="p">,</span> <span class="p">[</span> <span class="s1">'arlet6502_cts_r.gds'</span>
<span class="p">,</span> <span class="s1">'arlet6502_cts_r.spi'</span>
<span class="p">,</span> <span class="s1">'arlet6502_cts_r.vst'</span> <span class="p">]</span>
<span class="p">,</span> <span class="p">[</span><span class="n">ruleB2V</span><span class="p">]</span>
<span class="p">,</span> <span class="n">scriptMain</span> <span class="p">)</span>
<span class="n">ruleCgt</span> <span class="o">=</span> <span class="n">PnR</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'cgt'</span> <span class="p">)</span>
<span class="n">ruleGds</span> <span class="o">=</span> <span class="n">Alias</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">(</span> <span class="s1">'gds'</span><span class="p">,</span> <span class="p">[</span><span class="n">rulePnR</span><span class="p">]</span> <span class="p">)</span>
<span class="n">ruleClean</span> <span class="o">=</span> <span class="n">Clean</span> <span class="o">.</span><span class="n">mkRule</span><span class="p">()</span>
</pre>
</li>
</ol>
</div>
</div>
<div class="section" id="rules-s-catalog">
<h2><a class="toc-backref" href="#id9">3. Rules's Catalog</a></h2>
<div class="section" id="alliance-legacy-tools">
<h3><a class="toc-backref" href="#id10">3.1 Alliance Legacy Tools</a></h3>
<p>Support for the <span class="sc">Alliance</span> legacy tools. They are run through sub-processes.
For more detailed documentation about those tools, refer to their <span class="cb">man</span> pages.</p>
<ol class="arabic simple">
<li><tt class="docutils literal">Asimut</tt>, <span class="sc">vhdl</span> simulator.</li>
<li><tt class="docutils literal">Boog</tt>, logical synthesys. Map a <span class="sc">vhdl</span> behavioral description to a standard
cell library (works with <tt class="docutils literal">boom</tt> &amp; <tt class="docutils literal">loon</tt>).</li>
<li><tt class="docutils literal">Boom</tt>, behavioral description optimizer (works with <tt class="docutils literal">boog</tt> &amp; <tt class="docutils literal">loon</tt>).</li>
<li><tt class="docutils literal">Cougar</tt>, symbolic layout extractor.</li>
<li><tt class="docutils literal">Dreal</tt>, real layout (<span class="sc">gds</span>, <span class="sc">cif</span>) editor.</li>
<li><tt class="docutils literal">Druc</tt>, symbolic layout <span class="sc">DRC</span>.</li>
<li><tt class="docutils literal">Flatph</tt>, flatten a layout, fully or in part.</li>
<li><tt class="docutils literal">Genpat</tt>, pattern generator (for use with <tt class="docutils literal">Asimut</tt>).</li>
<li><tt class="docutils literal">Graal</tt>, symbolic layout editor.</li>
<li><tt class="docutils literal">Loon</tt>, netlist optimizer for surface and/or delay (works with <tt class="docutils literal">boom</tt> &amp; <tt class="docutils literal">boog</tt>).</li>
<li><tt class="docutils literal">Lvx</tt>, netlist comparator (<em>Layout</em> <em>Versus</em> <em>Extracted</em>).</li>
<li><tt class="docutils literal">S2R</tt>, symbolic to real translator (to <span class="sc">gds</span> or <span class="sc">cif</span>).</li>
<li><tt class="docutils literal">Vasy</tt>, Alliance <span class="sc">vhdl</span> subset translator towards standard <span class="sc">vhdl</span> or <span class="sc">Verilog</span>.</li>
</ol>
</div>
<div class="section" id="current-tools">
<h3><a class="toc-backref" href="#id11">3.2 Current Tools</a></h3>
<ol class="arabic simple">
<li><tt class="docutils literal">Blif2Vst</tt>, translate a <span class="cb">blif</span> netlist (<span class="sc">Yosys</span> output) into the <span class="sc">Alliance</span>
netlist format <span class="cb">vst</span>. This is a <span class="sc">Python</span> script calling <span class="sc">Coriolis</span> directly
integrated inside the task.</li>
<li><tt class="docutils literal">PnR</tt>, maybe a bit of a misnomer. This is a caller to function that the user have
to write to perform the P&amp;R as he sees fit for it's particular design.</li>
<li><tt class="docutils literal">Yosys</tt>, call the <span class="sc">Yosys</span> logical synthesyser. Provide an off the shelf subset
of functionalities to perform classic use cases.</li>
</ol>
</div>
<div class="section" id="utility-rules">
<h3><a class="toc-backref" href="#id12">3.3 Utility Rules</a></h3>
<ol class="arabic">
<li><p class="first"><tt class="docutils literal">Alias</tt>, create a name alias for a rule.</p>
</li>
<li><p class="first"><tt class="docutils literal">Clean</tt>, remove all the generated targets of all the rules. The name of the
rule is <tt class="docutils literal">clean_flow` to not interfer with the |DoIt| clean arguments.
Files not part of any rules targets can be added to be removeds. Then,
to actually remove them, add the <span class="pre">``--extras</span></tt> flag to the command line.</p>
<pre class="code bash literal-block">
ego&#64;home:sky130_c4m&gt; ../../../bin/crlenv.py -- doit clean_flow --extras
</pre>
</li>
<li><p class="first"><tt class="docutils literal">Copy</tt>, copy a file into the current directory.</p>
</li>
</ol>
</div>
<div class="section" id="rule-sets">
<h3><a class="toc-backref" href="#id13">3.4 Rule Sets</a></h3>
<ol class="arabic simple">
<li>alliancesynth</li>
<li>pnrcheck</li>
<li>routecheck</li>
</ol>
</div>
</div>
</div>
<!-- /Content -->
<!-- Footer -->
<div class="footer gradient-2">
<div class="container footer-container ">
<div class="row">
<div class="col-xs-4 col-sm-3 col-md-3 col-lg-3">
<div class="footer-title">Social</div>
<ul class="list-unstyled">
</ul>
</div>
<div class="col-xs-4 col-sm-3 col-md-3 col-lg-2">
</div>
<div class="col-xs-4 col-sm-3 col-md-3 col-lg-3">
<div class="footer-title">Links</div>
<ul class="list-unstyled">
<li><a href="https://coriolis.lip6.fr/" target="_blank">Alliance/Coriolis</a></li>
<li><a href="https://www-soc.lip6.fr/" target="_blank">CIAN Team Website</a></li>
<li><a href="https://f-si.org" target="_blank">Free Silicon Foundation</a></li>
</ul>
</div>
<div class="col-xs-12 col-sm-3 col-md-3 col-lg-4">
<p class="pull-right text-right">
<small><em>Proudly powered by <a href="http://docs.getpelican.com/" target="_blank">pelican</a></em></small><br/>
<small><em><span class="sc">NEST</span> theme by <a href="https://github.com/molivier" target="_blank">molivier</a></em></small><br/>
<small>Copyright © 2020-2020 Sorbonne Universite</small>
</p>
</div>
</div>
</div>
</div>
<!-- /Footer -->
</body>
</html>

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -138,6 +140,8 @@ Regression tests &amp; examples</div>
<div class="col-md-5 col-md-offset-1">
<p><a class="reference external" href="../pages/users-guide.html">Coriolis User's Guide</a> <span class="raw-html"><br/></span>
Using the software</p>
<p><a class="reference external" href="../pages/design-flow.html">Design Flow Quick Start</a> <span class="raw-html"><br/></span>
Tool to build your design</p>
<p><a class="reference external" href="../pages/python-tutorial.html">Python Tutorial</a> <span class="raw-html"><br/></span>
A Tutorial to use Coriolis through Python</p>
<p><a class="reference external" href="../pages/python-cpp.html">Python/C++ Tutorial</a> <span class="raw-html"><br/></span>

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item active" href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item active" href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -213,7 +215,7 @@ and the double compilation pass.</p>
</div>
<div class="section" id="implementation">
<h2><a class="toc-backref" href="#id5">2. Implementation</a></h2>
<p>We do not try to provides an iterface as sleek as <tt class="docutils literal">pybind11</tt> that completely
<p>We do not try to provides an interface as sleek as <tt class="docutils literal">pybind11</tt> that completely
hides the Python/C API. Instead we keep mostly visible the classic structure of
the Python/C API but we provides templates to automate as much as possible the
boring tasks (and code duplication). This way, if we need a very specific

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -1397,11 +1399,11 @@ for any discrepencies.</p>
</div>
</div>
<div class="section" id="loading-a-blif-file-yosys">
<h3>7.2 Loading a <span class="sc">blif</span> file -- <span class="sc">Yosys</span></h3>
<p>The <span class="sc">blif</span> format is generated by the <a class="reference external" href="http://www.clifford.at/yosys/">Yosys</a> logic synthetizer. Here again, it is
<h3>7.2 Loading a <span class="cb">blif</span> file -- <span class="sc">Yosys</span></h3>
<p>The <span class="cb">blif</span> format is generated by the <a class="reference external" href="http://www.clifford.at/yosys/">Yosys</a> logic synthetizer. Here again, it is
pretty straightforward: call the static function <tt class="docutils literal">Blif.load()</tt>. If you made
your synthesis on a cell library not managed by <a class="reference external" href="../../crlcore/classCRL_1_1AllianceFramework.html">AllianceFramework</a>, for example
the one of the FreePDK45, you must load it prior to calling the <span class="sc">blif</span> loader.</p>
the one of the FreePDK45, you must load it prior to calling the <span class="cb">blif</span> loader.</p>
<div class="highlight"><pre><span></span><span class="n">cell</span> <span class="o">=</span> <span class="n">Blif</span><span class="o">.</span><span class="n">load</span><span class="p">(</span> <span class="s1">&#39;snx&#39;</span> <span class="p">)</span> <span class="c1"># load &quot;snx.blif&quot; in the working directory.</span>
</pre></div>
<!-- -*- Mode: rst -*- -->

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -146,6 +148,9 @@
<!-- -*- Mode: rst -*- -->
<!-- Tools -->
<!-- RDS file syntax. -->
<div class="system-message">
<p class="system-message-title">System Message: ERROR/3 (<tt class="docutils">content/pages/rds/RDSpage.rst</tt>, line 23)</p>
Duplicate substitution definition name: &quot;DRC&quot;.</div>
<p></p>
</div>
<div class="section" id="symbolic-layout">

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item active" href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item active" href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="../pages/.html"></a></li>
<li><a class="dropdown-item " href="../pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="../pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>

Binary file not shown.

Binary file not shown.

View File

@ -54,6 +54,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="./pages/.html"></a></li>
<li><a class="dropdown-item " href="./pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="./pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>
@ -80,6 +81,7 @@
<span class="caret"></span>Topics
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item " href="./pages/.html"></a></li>
<li><a class="dropdown-item " href="./pages/homepage.html">Coriolis <span class="sc">vlsi</span> Backend Tools</a></li>
<li><a class="dropdown-item " href="./pages/symbolic-layout.html">Symbolic Layout</a></li>
</ul>

View File

@ -31,6 +31,7 @@ STATIC_PATHS = [ 'pages/users-guide'
, 'pages/python-cpp'
, 'pages/stratus'
, 'pages/check-toolkit'
, 'pages/design-flow'
, 'pages/rds'
, 'scripts'
, 'images'