Merge remote-tracking branch 'bkoppelmann/bit-sym' into dev

This commit is contained in:
Matt Guthaus 2020-01-29 11:24:09 -08:00
commit 3147b99ce0
13 changed files with 315 additions and 208 deletions

View File

@ -0,0 +1,131 @@
# See LICENSE for licensing information.
#
# Copyright (c) 2016-2019 Regents of the University of California and The Board
# of Regents for the Oklahoma Agricultural and Mechanical College
# (acting for and on behalf of Oklahoma State University)
# All rights reserved.
#
import debug
import design
from tech import cell_properties
class bitcell_base_array(design.design):
"""
Abstract base class for bitcell-arrays -- bitcell, dummy
"""
def __init__(self, cols, rows, name, column_offset):
design.design.__init__(self, name)
debug.info(1, "Creating {0} {1} x {2}".format(self.name, rows, cols))
self.add_comment("rows: {0} cols: {1}".format(rows, cols))
self.column_size = cols
self.row_size = rows
self.column_offset = column_offset
def add_pins(self):
row_list = self.cell.get_all_wl_names()
column_list = self.cell.get_all_bitline_names()
for col in range(self.column_size):
for cell_column in column_list:
self.add_pin(cell_column+"_{0}".format(col), "INOUT")
for row in range(self.row_size):
for cell_row in row_list:
self.add_pin(cell_row+"_{0}".format(row), "INPUT")
self.add_pin("vdd", "POWER")
self.add_pin("gnd", "GROUND")
def get_bitcell_pins(self, col, row):
""" Creates a list of connections in the bitcell,
indexed by column and row, for instance use in bitcell_array """
bitcell_pins = []
pin_names = self.cell.get_all_bitline_names()
for pin in pin_names:
bitcell_pins.append(pin+"_{0}".format(col))
pin_names = self.cell.get_all_wl_names()
for pin in pin_names:
bitcell_pins.append(pin+"_{0}".format(row))
bitcell_pins.append("vdd")
bitcell_pins.append("gnd")
return bitcell_pins
def add_layout_pins(self):
""" Add the layout pins """
row_list = self.cell.get_all_wl_names()
column_list = self.cell.get_all_bitline_names()
for col in range(self.column_size):
for cell_column in column_list:
bl_pin = self.cell_inst[0,col].get_pin(cell_column)
self.add_layout_pin(text=cell_column+"_{0}".format(col),
layer=bl_pin.layer,
offset=bl_pin.ll().scale(1,0),
width=bl_pin.width(),
height=self.height)
for row in range(self.row_size):
for cell_row in row_list:
wl_pin = self.cell_inst[row,0].get_pin(cell_row)
self.add_layout_pin(text=cell_row+"_{0}".format(row),
layer=wl_pin.layer,
offset=wl_pin.ll().scale(0,1),
width=self.width,
height=wl_pin.height())
# For every second row and column, add a via for gnd and vdd
for row in range(self.row_size):
for col in range(self.column_size):
inst = self.cell_inst[row,col]
for pin_name in ["vdd", "gnd"]:
for pin in inst.get_pins(pin_name):
self.add_power_pin(name=pin_name, loc=pin.center(), vertical=True, start_layer=pin.layer)
def _adjust_x_offset(self, xoffset, col, col_offset):
tempx = xoffset
dir_y = False
# If we mirror the current cell on the y axis adjust the x position
if cell_properties.bitcell.mirror.y and (col + col_offset) % 2:
tempx = xoffset + self.cell.width
dir_y = True
return (tempx, dir_y)
def _adjust_y_offset(self, yoffset, row, row_offset):
tempy = yoffset
dir_x = False
# If we mirror the current cell on the x axis adjust the y position
if cell_properties.bitcell.mirror.x and (row + row_offset) % 2:
tempy = yoffset + self.cell.height
dir_x = True
return (tempy, dir_x)
def place_array(self, name_template, row_offset=0):
# We increase it by a well enclosure so the precharges don't overlap our wells
self.height = self.row_size*self.cell.height
self.width = self.column_size*self.cell.width
xoffset = 0.0
for col in range(self.column_size):
yoffset = 0.0
tempx, dir_y = self._adjust_x_offset(xoffset, col, self.column_offset)
for row in range(self.row_size):
name = name_template.format(row, col)
tempy, dir_x = self._adjust_y_offset(yoffset, row, row_offset)
if dir_x and dir_y:
dir_key = "XY"
elif dir_x:
dir_key = "MX"
elif dir_y:
dir_key = "MY"
else:
dir_key = ""
self.cell_inst[row,col].place(offset=[tempx, tempy],
mirror=dir_key)
yoffset += self.cell.height
xoffset += self.cell.width

View File

@ -7,25 +7,21 @@
#
import debug
import design
from base_array import bitcell_base_array
from tech import drc, spice
from vector import vector
from globals import OPTS
from sram_factory import factory
import logical_effort
class bitcell_array(design.design):
class bitcell_array(bitcell_base_array):
"""
Creates a rows x cols array of memory cells. Assumes bit-lines
and word line is connected by abutment.
Connects the word lines and bit lines.
"""
def __init__(self, cols, rows, name):
design.design.__init__(self, name)
debug.info(1, "Creating {0} {1} x {2}".format(self.name, rows, cols))
self.add_comment("rows: {0} cols: {1}".format(rows, cols))
self.column_size = cols
self.row_size = rows
def __init__(self, cols, rows, name, column_offset=0):
super().__init__(cols, rows, name, column_offset)
self.create_netlist()
if not OPTS.netlist_only:
@ -44,27 +40,7 @@ class bitcell_array(design.design):
def create_layout(self):
# We increase it by a well enclosure so the precharges don't overlap our wells
self.height = self.row_size*self.cell.height
self.width = self.column_size*self.cell.width
xoffset = 0.0
for col in range(self.column_size):
yoffset = 0.0
for row in range(self.row_size):
name = "bit_r{0}_c{1}".format(row, col)
if row % 2:
tempy = yoffset + self.cell.height
dir_key = "MX"
else:
tempy = yoffset
dir_key = ""
self.cell_inst[row,col].place(offset=[xoffset, tempy],
mirror=dir_key)
yoffset += self.cell.height
xoffset += self.cell.width
self.place_array("bit_r{0}_c{1}")
self.add_layout_pins()
@ -72,41 +48,13 @@ class bitcell_array(design.design):
self.DRC_LVS()
def add_pins(self):
row_list = self.cell.get_all_wl_names()
column_list = self.cell.get_all_bitline_names()
for col in range(self.column_size):
for cell_column in column_list:
self.add_pin(cell_column+"_{0}".format(col), "INOUT")
for row in range(self.row_size):
for cell_row in row_list:
self.add_pin(cell_row+"_{0}".format(row), "INPUT")
self.add_pin("vdd", "POWER")
self.add_pin("gnd", "GROUND")
def add_modules(self):
""" Add the modules used in this design """
self.cell = factory.create(module_type="bitcell")
self.add_mod(self.cell)
def get_bitcell_pins(self, col, row):
""" Creates a list of connections in the bitcell,
indexed by column and row, for instance use in bitcell_array """
bitcell_pins = []
pin_names = self.cell.get_all_bitline_names()
for pin in pin_names:
bitcell_pins.append(pin+"_{0}".format(col))
pin_names = self.cell.get_all_wl_names()
for pin in pin_names:
bitcell_pins.append(pin+"_{0}".format(row))
bitcell_pins.append("vdd")
bitcell_pins.append("gnd")
return bitcell_pins
def create_instances(self):
""" Create the module instances used in this design """
self.cell_inst = {}
@ -117,37 +65,6 @@ class bitcell_array(design.design):
mod=self.cell)
self.connect_inst(self.get_bitcell_pins(col, row))
def add_layout_pins(self):
""" Add the layout pins """
row_list = self.cell.get_all_wl_names()
column_list = self.cell.get_all_bitline_names()
for col in range(self.column_size):
for cell_column in column_list:
bl_pin = self.cell_inst[0,col].get_pin(cell_column)
self.add_layout_pin(text=cell_column+"_{0}".format(col),
layer=bl_pin.layer,
offset=bl_pin.ll().scale(1,0),
width=bl_pin.width(),
height=self.height)
for row in range(self.row_size):
for cell_row in row_list:
wl_pin = self.cell_inst[row,0].get_pin(cell_row)
self.add_layout_pin(text=cell_row+"_{0}".format(row),
layer=wl_pin.layer,
offset=wl_pin.ll().scale(0,1),
width=self.width,
height=wl_pin.height())
# For every second row and column, add a via for gnd and vdd
for row in range(self.row_size):
for col in range(self.column_size):
inst = self.cell_inst[row,col]
for pin_name in ["vdd", "gnd"]:
for pin in inst.get_pins(pin_name):
self.add_power_pin(name=pin_name, loc=pin.center(), vertical=True, start_layer=pin.layer)
def analytical_power(self, corner, load):
"""Power of Bitcell array and bitline in nW."""

View File

@ -0,0 +1,28 @@
# See LICENSE for licensing information.
#
# Copyright (c) 2016-2020 Regents of the University of California and The Board
# of Regents for the Oklahoma Agricultural and Mechanical College
# (acting for and on behalf of Oklahoma State University)
# All rights reserved.
#
class _MirrorAxis:
def __init__(self, x, y):
self.x = x
self.y = y
class _Bitcell:
def __init__(self, mirror):
self.mirror = mirror
class CellProperties():
"""
TODO
"""
def __init__(self):
self.names = {}
self._bitcell = _Bitcell(_MirrorAxis(True, False))
@property
def bitcell(self):
return self._bitcell

View File

@ -5,23 +5,19 @@
#
import debug
import design
from base_array import bitcell_base_array
from tech import drc
import contact
from sram_factory import factory
from vector import vector
from globals import OPTS
class dummy_array(design.design):
class dummy_array(bitcell_base_array):
"""
Generate a dummy row/column for the replica array.
"""
def __init__(self, cols, rows, mirror=0, name=""):
design.design.__init__(self, name)
debug.info(1, "Creating {0} {1} x {2}".format(self.name, rows, cols))
self.add_comment("rows: {0} cols: {1}".format(rows, cols))
self.column_size = cols
self.row_size = rows
def __init__(self, cols, rows, column_offset=0, mirror=0, name=""):
super().__init__(cols, rows, name, column_offset)
self.mirror = mirror
self.create_netlist()
@ -37,27 +33,7 @@ class dummy_array(design.design):
def create_layout(self):
# We increase it by a well enclosure so the precharges don't overlap our wells
self.height = self.row_size*self.dummy_cell.height
self.width = self.column_size*self.dummy_cell.width
xoffset = 0.0
for col in range(self.column_size):
yoffset = 0.0
for row in range(self.row_size):
name = "dummy_r{0}_c{1}".format(row, col)
if (row+self.mirror) % 2:
tempy = yoffset + self.dummy_cell.height
dir_key = "MX"
else:
tempy = yoffset
dir_key = ""
self.cell_inst[row,col].place(offset=[xoffset, tempy],
mirror=dir_key)
yoffset += self.dummy_cell.height
xoffset += self.dummy_cell.width
self.place_array("dummy_r{0}_c{1}", self.mirror)
self.add_layout_pins()
@ -65,18 +41,6 @@ class dummy_array(design.design):
self.DRC_LVS()
def add_pins(self):
row_list = self.cell.get_all_wl_names()
column_list = self.cell.get_all_bitline_names()
for col in range(self.column_size):
for cell_column in column_list:
self.add_pin(cell_column+"_{0}".format(col), "INOUT")
for row in range(self.row_size):
for cell_row in row_list:
self.add_pin(cell_row+"_{0}".format(row), "INPUT")
self.add_pin("vdd", "POWER")
self.add_pin("gnd", "GROUND")
def add_modules(self):
""" Add the modules used in this design """
self.dummy_cell = factory.create(module_type="dummy_bitcell")
@ -84,23 +48,6 @@ class dummy_array(design.design):
self.cell = factory.create(module_type="bitcell")
def get_bitcell_pins(self, col, row):
""" Creates a list of connections in the bitcell,
indexed by column and row, for instance use in bitcell_array """
bitcell_pins = []
pin_names = self.cell.get_all_bitline_names()
for pin in pin_names:
bitcell_pins.append(pin+"_{0}".format(col))
pin_names = self.cell.get_all_wl_names()
for pin in pin_names:
bitcell_pins.append(pin+"_{0}".format(row))
bitcell_pins.append("vdd")
bitcell_pins.append("gnd")
return bitcell_pins
def create_instances(self):
""" Create the module instances used in this design """
@ -111,39 +58,6 @@ class dummy_array(design.design):
self.cell_inst[row,col]=self.add_inst(name=name,
mod=self.dummy_cell)
self.connect_inst(self.get_bitcell_pins(col, row))
def add_layout_pins(self):
""" Add the layout pins """
row_list = self.cell.get_all_wl_names()
column_list = self.cell.get_all_bitline_names()
for col in range(self.column_size):
for cell_column in column_list:
bl_pin = self.cell_inst[0,col].get_pin(cell_column)
self.add_layout_pin(text=cell_column+"_{0}".format(col),
layer="m2",
offset=bl_pin.ll(),
width=bl_pin.width(),
height=self.height)
for row in range(self.row_size):
for cell_row in row_list:
wl_pin = self.cell_inst[row,0].get_pin(cell_row)
self.add_layout_pin(text=cell_row+"_{0}".format(row),
layer="m1",
offset=wl_pin.ll(),
width=self.width,
height=wl_pin.height())
# For every second row and column, add a via for gnd and vdd
for row in range(self.row_size):
for col in range(self.column_size):
inst = self.cell_inst[row,col]
for pin_name in ["vdd", "gnd"]:
for pin in inst.get_pins(pin_name):
self.add_power_pin(name=pin_name, loc=pin.center(), vertical=True, start_layer=pin.layer)
def input_load(self):
wl_wire = self.gen_wl_wire()

View File

@ -107,9 +107,19 @@ class precharge_array(design.design):
def place_insts(self):
""" Places precharge array by horizontally tiling the precharge cell"""
from tech import cell_properties
xoffset = 0
for i in range(self.columns):
offset = vector(self.pc_cell.width * i, 0)
self.local_insts[i].place(offset)
tempx = xoffset
if cell_properties.bitcell.mirror.y and (i + 1) % 2:
mirror = "MY"
tempx = tempx + self.pc_cell.width
else:
mirror = ""
offset = vector(tempx, 0)
self.local_insts[i].place(offset=offset, mirror=mirror)
xoffset = xoffset + self.pc_cell.width
def get_en_cin(self):
"""Get the relative capacitance of all the clk connections in the precharge array"""

View File

@ -86,6 +86,7 @@ class replica_bitcell_array(design.design):
# Bitcell array
self.bitcell_array = factory.create(module_type="bitcell_array",
column_offset=1 + self.left_rbl,
cols=self.column_size,
rows=self.row_size)
self.add_mod(self.bitcell_array)
@ -95,12 +96,17 @@ class replica_bitcell_array(design.design):
for bit in range(self.left_rbl+self.right_rbl):
if bit<self.left_rbl:
replica_bit = bit+1
# dummy column
column_offset = 1
else:
replica_bit = bit+self.row_size+1
# dummy column + replica column + bitcell colums
column_offset = 3 + self.row_size
self.replica_columns[bit] = factory.create(module_type="replica_column",
rows=self.row_size,
left_rbl=self.left_rbl,
right_rbl=self.right_rbl,
column_offset=column_offset,
replica_bit=replica_bit)
self.add_mod(self.replica_columns[bit])
@ -108,16 +114,30 @@ class replica_bitcell_array(design.design):
self.dummy_row = factory.create(module_type="dummy_array",
cols=self.column_size,
rows=1,
# dummy column + left replica column
column_offset=1 + self.left_rbl,
mirror=0)
self.add_mod(self.dummy_row)
# Dummy col (mirror starting at first if odd replica+dummy rows)
self.dummy_col = factory.create(module_type="dummy_array",
cols=1,
rows=self.row_size + self.extra_rows,
mirror=(self.left_rbl+1)%2)
self.add_mod(self.dummy_col)
self.dummy_col_left = factory.create(module_type="dummy_array",
cols=1,
column_offset=0,
rows=self.row_size + self.extra_rows,
mirror=(self.left_rbl+1)%2)
self.add_mod(self.dummy_col_left)
self.dummy_col_right = factory.create(module_type="dummy_array",
cols=1,
# dummy column
# + left replica column
# + bitcell columns
# + right replica column
column_offset=1 + self.left_rbl + self.column_size + self.right_rbl,
rows=self.row_size + self.extra_rows,
mirror=(self.left_rbl+1)%2)
self.add_mod(self.dummy_col_right)
def add_pins(self):
@ -236,10 +256,10 @@ class replica_bitcell_array(design.design):
# Left/right Dummy columns
self.dummy_col_left_inst=self.add_inst(name="dummy_col_left",
mod=self.dummy_col)
mod=self.dummy_col_left)
self.connect_inst([x+"_left" for x in self.dummy_cell_bl_names] + self.dummy_col_wl_names + supplies)
self.dummy_col_right_inst=self.add_inst(name="dummy_col_right",
mod=self.dummy_col)
mod=self.dummy_col_right)
self.connect_inst([x+"_right" for x in self.dummy_cell_bl_names] + self.dummy_col_wl_names + supplies)

View File

@ -20,7 +20,8 @@ class replica_column(design.design):
replica cell.
"""
def __init__(self, name, rows, left_rbl, right_rbl, replica_bit):
def __init__(self, name, rows, left_rbl, right_rbl, replica_bit,
column_offset=0):
design.design.__init__(self, name)
self.rows = rows
@ -29,6 +30,7 @@ class replica_column(design.design):
self.replica_bit = replica_bit
# left, right, regular rows plus top/bottom dummy cells
self.total_size = self.left_rbl+rows+self.right_rbl+2
self.column_offset = column_offset
debug.check(replica_bit!=0 and replica_bit!=rows,"Replica bit cannot be the dummy row.")
debug.check(replica_bit<=left_rbl or replica_bit>=self.total_size-right_rbl-1,
@ -92,18 +94,35 @@ class replica_column(design.design):
self.connect_inst(self.get_bitcell_pins(0, row))
def place_instances(self):
from tech import cell_properties
# Flip the mirrors if we have an odd number of replica+dummy rows at the bottom
# so that we will start with mirroring rather than not mirroring
rbl_offset = (self.left_rbl+1)%2
# if our bitcells are mirrored on the y axis, check if we are in global
# column that needs to be flipped.
dir_y = False
xoffset = 0
if cell_properties.bitcell.mirror.y and self.column_offset % 2:
dir_y = True
xoffset = self.replica_cell.width
for row in range(self.total_size):
dir_x = False
name = "bit_r{0}_{1}".format(row,"rbl")
offset = vector(0,self.cell.height*(row+(row+rbl_offset)%2))
if (row+rbl_offset)%2:
if cell_properties.bitcell.mirror.x and (row+rbl_offset)%2:
dir_x = True
offset = vector(xoffset,self.cell.height*(row+(row+rbl_offset)%2))
if dir_x and dir_y:
dir_key = "XY"
elif dir_x:
dir_key = "MX"
elif dir_y:
dir_key = "MY"
else:
dir_key = "R0"
dir_key = ""
self.cell_inst[row].place(offset=offset,
mirror=dir_key)

View File

@ -84,14 +84,27 @@ class sense_amp_array(design.design):
"en", "vdd", "gnd"])
def place_sense_amp_array(self):
from tech import cell_properties
if self.bitcell.width > self.amp.width:
amp_spacing = self.bitcell.width * self.words_per_row
else:
amp_spacing = self.amp.width * self.words_per_row
for i in range(0,self.word_size):
amp_position = vector(amp_spacing * i, 0)
self.local_insts[i].place(amp_position)
xoffset = amp_spacing * i
# align the xoffset to the grid of bitcells. This way we
# know when to do the mirroring.
grid_x = int(xoffset / self.amp.width)
if cell_properties.bitcell.mirror.y and grid_x % 2:
mirror = "MY"
xoffset = xoffset + self.amp.width
else:
mirror = ""
amp_position = vector(xoffset, 0)
self.local_insts[i].place(offset=amp_position,mirror=mirror)
def add_layout_pins(self):

View File

@ -99,11 +99,19 @@ class single_level_column_mux_array(design.design):
"gnd"])
def place_array(self):
from tech import cell_properties
# For every column, add a pass gate
for col_num in range(self.columns):
xoffset = col_num * self.mux.width
if cell_properties.bitcell.mirror.y and col_num % 2:
mirror = "MY"
xoffset = xoffset + self.mux.width
else:
mirror = ""
name = "XMUX{0}".format(col_num)
x_off = vector(col_num * self.mux.width, self.route_height)
self.mux_inst[col_num].place(x_off)
offset = vector(xoffset, self.route_height)
self.mux_inst[col_num].place(offset=offset, mirror=mirror)
def add_layout_pins(self):
@ -161,6 +169,7 @@ class single_level_column_mux_array(design.design):
def route_bitlines(self):
""" Connect the output bit-lines to form the appropriate width mux """
from tech import cell_properties
for j in range(self.columns):
bl_offset = self.mux_inst[j].get_pin("bl_out").bc()
br_offset = self.mux_inst[j].get_pin("br_out").bc()
@ -171,23 +180,38 @@ class single_level_column_mux_array(design.design):
bl_out_offset_end = bl_out_offset + vector(0,self.route_height)
br_out_offset_end = br_out_offset + vector(0,self.route_height)
if cell_properties.bitcell.mirror.y and j % 2:
tmp_bl_out_end = br_out_offset_end
tmp_br_out_end = bl_out_offset_end
else:
tmp_bl_out_end = bl_out_offset_end
tmp_br_out_end = br_out_offset_end
if (j % self.words_per_row) == 0:
# Create the metal1 to connect the n-way mux output from the pass gate
# These will be located below the select lines. Yes, these are M2 width
# to ensure vias are enclosed and M1 min width rules.
width = self.m2_width + self.mux.width * (self.words_per_row - 1)
self.add_path("m1", [bl_out_offset, bl_out_offset+vector(width,0)])
self.add_path("m1", [br_out_offset, br_out_offset+vector(width,0)])
if cell_properties.bitcell.mirror.y and (j % 2) == 0:
bl = self.mux.get_pin("bl")
br = self.mux.get_pin("br")
dist = abs(bl.ll().x - br.ll().x)
else:
dist = 0
self.add_path("m1", [bl_out_offset, bl_out_offset+vector(width+dist,0)])
self.add_path("m1", [br_out_offset, br_out_offset+vector(width-dist,0)])
# Extend the bitline output rails and gnd downward on the first bit of each n-way mux
self.add_layout_pin_segment_center(text="bl_out_{}".format(int(j/self.words_per_row)),
layer="m2",
start=bl_out_offset,
end=bl_out_offset_end)
end=tmp_bl_out_end)
self.add_layout_pin_segment_center(text="br_out_{}".format(int(j/self.words_per_row)),
layer="m2",
start=br_out_offset,
end=br_out_offset_end)
end=tmp_br_out_end)
# This via is on the right of the wire
@ -200,8 +224,8 @@ class single_level_column_mux_array(design.design):
else:
self.add_path("m2", [ bl_out_offset, bl_out_offset_end])
self.add_path("m2", [ br_out_offset, br_out_offset_end])
self.add_path("m2", [ bl_out_offset, tmp_bl_out_end])
self.add_path("m2", [ br_out_offset, tmp_br_out_end])
# This via is on the right of the wire
self.add_via_center(layers=self.m1_stack,

View File

@ -106,14 +106,23 @@ class write_driver_array(design.design):
def place_write_array(self):
from tech import cell_properties
if self.bitcell.width > self.driver.width:
self.driver_spacing = self.bitcell.width
else:
self.driver_spacing = self.driver.width
for i in range(0,self.columns,self.words_per_row):
index = int(i/self.words_per_row)
base = vector(i * self.driver_spacing, 0)
self.driver_insts[index].place(base)
xoffset = i * self.driver_spacing
if cell_properties.bitcell.mirror.y and i % 2:
mirror = "MY"
xoffset = xoffset + self.driver.width
else:
mirror = ""
base = vector(xoffset, 0)
self.driver_insts[index].place(offset=base, mirror=mirror)
def add_layout_pins(self):

View File

@ -8,6 +8,7 @@
import os
from design_rules import *
from module_type import *
from custom_cell_properties import CellProperties
"""
File containing the process technology parameters for FreePDK 45nm.
@ -24,6 +25,12 @@ File containing the process technology parameters for FreePDK 45nm.
# For example: tech_modules['contact'] = 'contact_freepdk45'
tech_modules = ModuleType()
###################################################
# Custom cell properties
###################################################
cell_properties = CellProperties()
cell_properties.bitcell.mirror.x = True
cell_properties.bitcell.mirror.y = False
###################################################
# GDS file info

View File

@ -1,6 +1,7 @@
import os
from design_rules import *
from module_type import *
from custom_cell_properties import CellProperties
"""
File containing the process technology parameters for SCMOS 3me, subm, 180nm.
@ -12,6 +13,13 @@ File containing the process technology parameters for SCMOS 3me, subm, 180nm.
# For example: tech_modules['contact'] = 'contact_scn3me'
tech_modules = ModuleType()
###################################################
# Custom cell properties
###################################################
cell_properties = CellProperties()
cell_properties.bitcell.mirror.x = True
cell_properties.bitcell.mirror.y = False
#GDS file info
GDS={}
# gds units

View File

@ -8,6 +8,7 @@
import os
from design_rules import *
from module_type import *
from custom_cell_properties import CellProperties
"""
File containing the process technology parameters for SCMOS 4m, 0.35um
@ -24,6 +25,12 @@ File containing the process technology parameters for SCMOS 4m, 0.35um
# For example: tech_modules['contact'] = 'contact_scn4m'
tech_modules = ModuleType()
###################################################
# Custom cell properties
###################################################
cell_properties = CellProperties()
cell_properties.bitcell.mirror.x = True
cell_properties.bitcell.mirror.y = False
###################################################
# GDS file info