mirror of
https://github.com/VLSIDA/OpenRAM.git
synced 2026-09-08 03:43:44 +02:00
Merge remote-tracking branch 'origin/dev' into rbl_revamp
This commit is contained in:
@@ -34,7 +34,6 @@ class sram():
|
||||
start_time = datetime.datetime.now()
|
||||
|
||||
self.name = name
|
||||
|
||||
|
||||
if self.num_banks == 1:
|
||||
from sram_1bank import sram_1bank as sram
|
||||
@@ -84,8 +83,6 @@ class sram():
|
||||
self.gds_write(gdsname)
|
||||
print_time("GDS", datetime.datetime.now(), start_time)
|
||||
|
||||
|
||||
|
||||
# Save the spice file
|
||||
start_time = datetime.datetime.now()
|
||||
spname = OPTS.output_path + self.s.name + ".sp"
|
||||
@@ -133,4 +130,4 @@ class sram():
|
||||
vname = OPTS.output_path + self.s.name + ".v"
|
||||
debug.print_raw("Verilog: Writing to {0}".format(vname))
|
||||
self.verilog_write(vname)
|
||||
print_time("Verilog", datetime.datetime.now(), start_time)
|
||||
print_time("Verilog", datetime.datetime.now(), start_time)
|
||||
@@ -46,6 +46,9 @@ class sram_1bank(sram_base):
|
||||
|
||||
self.data_dff_insts = self.create_data_dff()
|
||||
|
||||
if (self.write_size != self.word_size):
|
||||
self.wmask_dff_insts = self.create_wmask_dff()
|
||||
|
||||
|
||||
def place_instances(self):
|
||||
"""
|
||||
@@ -65,6 +68,7 @@ class sram_1bank(sram_base):
|
||||
row_addr_pos = [None]*len(self.all_ports)
|
||||
col_addr_pos = [None]*len(self.all_ports)
|
||||
data_pos = [None]*len(self.all_ports)
|
||||
wmask_pos = [None]*len(self.all_ports)
|
||||
|
||||
# This is M2 pitch even though it is on M1 to help stem via spacings on the trunk
|
||||
# The M1 pitch is for supply rail spacings
|
||||
@@ -105,6 +109,29 @@ class sram_1bank(sram_base):
|
||||
row_addr_pos[port] = vector(x_offset, y_offset)
|
||||
self.row_addr_dff_insts[port].place(row_addr_pos[port])
|
||||
|
||||
# Add the col address flops below the bank to the left of the lower-left of bank array
|
||||
if self.col_addr_dff:
|
||||
col_addr_pos[port] = vector(self.bank.bank_array_ll.x - self.col_addr_dff_insts[port].width - self.bank.m2_gap,
|
||||
-max_gap_size - self.col_addr_dff_insts[port].height)
|
||||
self.col_addr_dff_insts[port].place(col_addr_pos[port])
|
||||
|
||||
# Add the data flops below the bank to the right of the lower-left of bank array
|
||||
# This relies on the lower-left of the array of the bank
|
||||
# decoder in upper left, bank in upper right, sensing in lower right.
|
||||
# These flops go below the sensing and leave a gap to channel route to the
|
||||
# sense amps.
|
||||
if port in self.write_ports:
|
||||
data_pos[port] = vector(self.bank.bank_array_ll.x,
|
||||
-max_gap_size - self.data_dff_insts[port].height)
|
||||
self.data_dff_insts[port].place(data_pos[port])
|
||||
|
||||
# Add the write mask flops to the left of the din flops.
|
||||
if (self.write_size != self.word_size):
|
||||
if port in self.write_ports:
|
||||
wmask_pos[port] = vector(self.bank.bank_array_ur.x - self.data_dff_insts[port].width,
|
||||
self.bank.height + max_gap_size + self.data_dff_insts[port].height)
|
||||
self.wmask_dff_insts[port].place(wmask_pos[port], mirror="MX")
|
||||
|
||||
|
||||
if len(self.all_ports)>1:
|
||||
# Port 1
|
||||
@@ -119,6 +146,13 @@ class sram_1bank(sram_base):
|
||||
data_pos[port] = vector(self.bank.bank_array_ur.x - self.data_dff_insts[port].width,
|
||||
self.bank.height + max_gap_size + self.dff.height)
|
||||
self.data_dff_insts[port].place(data_pos[port], mirror="MX")
|
||||
|
||||
# Add the write mask flops to the left of the din flops.
|
||||
if (self.write_size != self.word_size):
|
||||
if port in self.write_ports:
|
||||
wmask_pos[port] = vector(self.bank.bank_array_ur.x - self.data_dff_insts[port].width,
|
||||
self.bank.height + max_gap_size + self.data_dff_insts[port].height)
|
||||
self.wmask_dff_insts[port].place(wmask_pos[port], mirror="MX")
|
||||
else:
|
||||
data_pos[port] = self.bank_inst.ur()
|
||||
|
||||
@@ -143,7 +177,7 @@ class sram_1bank(sram_base):
|
||||
self.row_addr_dff_insts[port].place(row_addr_pos[port], mirror="XY")
|
||||
|
||||
|
||||
|
||||
|
||||
def add_layout_pins(self):
|
||||
"""
|
||||
Add the top-level pins for a single bank SRAM with control.
|
||||
@@ -326,10 +360,13 @@ class sram_1bank(sram_base):
|
||||
offset=pin.center())
|
||||
|
||||
def graph_exclude_data_dff(self):
|
||||
"""Removes data dff from search graph. """
|
||||
#Data dffs are only for writing so are not useful for evaluating read delay.
|
||||
"""Removes data dff and wmask dff (if applicable) from search graph. """
|
||||
#Data dffs and wmask dffs are only for writing so are not useful for evaluating read delay.
|
||||
for inst in self.data_dff_insts:
|
||||
self.graph_inst_exclude.add(inst)
|
||||
if (self.write_size != self.word_size):
|
||||
for inst in self.wmask_dff_insts:
|
||||
self.graph_inst_exclude.add(inst)
|
||||
|
||||
def graph_exclude_addr_dff(self):
|
||||
"""Removes data dff from search graph. """
|
||||
|
||||
@@ -68,7 +68,10 @@ class sram_base(design, verilog, lef):
|
||||
self.add_pin("web{}".format(port),"INPUT")
|
||||
for port in self.all_ports:
|
||||
self.add_pin("clk{}".format(port),"INPUT")
|
||||
|
||||
# add the optional write mask pins
|
||||
if self.word_size != self.write_size:
|
||||
for port in self.write_ports:
|
||||
self.add_pin("wmask{}".format(port),"INPUT")
|
||||
for port in self.read_ports:
|
||||
for bit in range(self.word_size):
|
||||
self.add_pin("DOUT{0}[{1}]".format(port,bit),"OUTPUT")
|
||||
@@ -150,9 +153,6 @@ class sram_base(design, verilog, lef):
|
||||
rtr.route()
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
def compute_bus_sizes(self):
|
||||
""" Compute the independent bus widths shared between two and four bank SRAMs """
|
||||
|
||||
@@ -278,7 +278,9 @@ class sram_base(design, verilog, lef):
|
||||
self.data_dff = dff_array(name="data_dff", rows=1, columns=self.word_size)
|
||||
self.add_mod(self.data_dff)
|
||||
|
||||
|
||||
self.wmask_dff = dff_array(name="wmask_dff", rows=1, columns=int(self.word_size/self.write_size))
|
||||
self.add_mod(self.wmask_dff)
|
||||
|
||||
|
||||
# Create the bank module (up to four are instantiated)
|
||||
from bank import bank
|
||||
@@ -303,6 +305,7 @@ class sram_base(design, verilog, lef):
|
||||
self.control_logic_rw = self.mod_control_logic(num_rows=self.num_rows,
|
||||
words_per_row=self.words_per_row,
|
||||
word_size=self.word_size,
|
||||
write_size = self.write_size,
|
||||
sram=self,
|
||||
port_type="rw")
|
||||
self.add_mod(self.control_logic_rw)
|
||||
@@ -310,6 +313,7 @@ class sram_base(design, verilog, lef):
|
||||
self.control_logic_w = self.mod_control_logic(num_rows=self.num_rows,
|
||||
words_per_row=self.words_per_row,
|
||||
word_size=self.word_size,
|
||||
write_size=self.write_size,
|
||||
sram=self,
|
||||
port_type="w")
|
||||
self.add_mod(self.control_logic_w)
|
||||
@@ -317,7 +321,8 @@ class sram_base(design, verilog, lef):
|
||||
self.control_logic_r = self.mod_control_logic(num_rows=self.num_rows,
|
||||
words_per_row=self.words_per_row,
|
||||
word_size=self.word_size,
|
||||
sram=self,
|
||||
write_size=self.write_size,
|
||||
sram=self,
|
||||
port_type="r")
|
||||
self.add_mod(self.control_logic_r)
|
||||
|
||||
@@ -448,6 +453,29 @@ class sram_base(design, verilog, lef):
|
||||
|
||||
return insts
|
||||
|
||||
def create_wmask_dff(self):
|
||||
""" Add and place all wmask flops """
|
||||
num_wmask = int(self.word_size/self.write_size)
|
||||
insts = []
|
||||
for port in self.all_ports:
|
||||
if port in self.write_ports:
|
||||
insts.append(self.add_inst(name="wmask_dff{}".format(port),
|
||||
mod=self.wmask_dff))
|
||||
else:
|
||||
insts.append(None)
|
||||
continue
|
||||
|
||||
# inputs, outputs/output/bar
|
||||
inputs = []
|
||||
outputs = []
|
||||
for bit in range(num_wmask):
|
||||
inputs.append("wmask{}[{}]".format(port, bit))
|
||||
outputs.append("BANK_WMASK{}[{}]".format(port, bit))
|
||||
|
||||
self.connect_inst(inputs + outputs + ["clk_buf{}".format(port), "vdd", "gnd"])
|
||||
|
||||
return insts
|
||||
|
||||
|
||||
def create_control_logic(self):
|
||||
""" Add control logic instances """
|
||||
|
||||
@@ -14,16 +14,20 @@ from sram_factory import factory
|
||||
class sram_config:
|
||||
""" This is a structure that is used to hold the SRAM configuration options. """
|
||||
|
||||
def __init__(self, word_size, num_words, num_banks=1, words_per_row=None):
|
||||
def __init__(self, word_size, num_words, write_size = None, num_banks=1, words_per_row=None):
|
||||
self.word_size = word_size
|
||||
self.num_words = num_words
|
||||
self.write_size = write_size
|
||||
self.num_banks = num_banks
|
||||
|
||||
# This will get over-written when we determine the organization
|
||||
self.words_per_row = words_per_row
|
||||
|
||||
if self.write_size == None:
|
||||
self.write_size = self.word_size
|
||||
|
||||
self.compute_sizes()
|
||||
|
||||
|
||||
|
||||
def set_local_config(self, module):
|
||||
""" Copy all of the member variables to the given module for convenience """
|
||||
|
||||
Reference in New Issue
Block a user