Merge branch 'multiport' into supply_routing

This commit is contained in:
Matt Guthaus 2018-10-11 09:56:38 -07:00
commit a094db9077
23 changed files with 330 additions and 330 deletions

View File

@ -38,9 +38,9 @@ class bitcell(design.design):
def list_bitcell_pins(self, col, row): def list_bitcell_pins(self, col, row):
""" Creates a list of connections in the bitcell, indexed by column and row, for instance use in bitcell_array """ """ Creates a list of connections in the bitcell, indexed by column and row, for instance use in bitcell_array """
bitcell_pins = ["bl[{0}]".format(col), bitcell_pins = ["bl_{0}".format(col),
"br[{0}]".format(col), "br_{0}".format(col),
"wl[{0}]".format(row), "wl_{0}".format(row),
"vdd", "vdd",
"gnd"] "gnd"]
return bitcell_pins return bitcell_pins

View File

@ -1186,10 +1186,10 @@ class pbitcell(design.design):
""" Creates a list of connections in the bitcell, indexed by column and row, for instance use in bitcell_array """ """ Creates a list of connections in the bitcell, indexed by column and row, for instance use in bitcell_array """
bitcell_pins = [] bitcell_pins = []
for port in range(self.total_ports): for port in range(self.total_ports):
bitcell_pins.append("bl{0}[{1}]".format(port,col)) bitcell_pins.append("bl{0}_{1}".format(port,col))
bitcell_pins.append("br{0}[{1}]".format(port,col)) bitcell_pins.append("br{0}_{1}".format(port,col))
for port in range(self.total_ports): for port in range(self.total_ports):
bitcell_pins.append("wl{0}[{1}]".format(port,row)) bitcell_pins.append("wl{0}_{1}".format(port,row))
bitcell_pins.append("vdd") bitcell_pins.append("vdd")
bitcell_pins.append("gnd") bitcell_pins.append("gnd")
return bitcell_pins return bitcell_pins
@ -1242,4 +1242,4 @@ class pbitcell(design.design):
Q_bar_pos = self.inverter_pmos_left.get_pin("D").uc() Q_bar_pos = self.inverter_pmos_left.get_pin("D").uc()
vdd_pos = vector(Q_bar_pos.x, self.vdd_position.y) vdd_pos = vector(Q_bar_pos.x, self.vdd_position.y)
self.add_path("metal1", [Q_bar_pos, vdd_pos]) self.add_path("metal1", [Q_bar_pos, vdd_pos])

View File

@ -68,13 +68,13 @@ class bank(design.design):
""" Adding pins for Bank module""" """ Adding pins for Bank module"""
for port in range(self.total_read): for port in range(self.total_read):
for bit in range(self.word_size): for bit in range(self.word_size):
self.add_pin("dout{0}[{1}]".format(self.read_index[port],bit),"OUT") self.add_pin("dout{0}_{1}".format(self.read_index[port],bit),"OUT")
for port in range(self.total_write): for port in range(self.total_write):
for bit in range(self.word_size): for bit in range(self.word_size):
self.add_pin("din{0}[{1}]".format(port,bit),"IN") self.add_pin("din{0}_{1}".format(port,bit),"IN")
for port in range(self.total_ports): for port in range(self.total_ports):
for bit in range(self.addr_size): for bit in range(self.addr_size):
self.add_pin("addr{0}[{1}]".format(port,bit),"INPUT") self.add_pin("addr{0}_{1}".format(port,bit),"INPUT")
# For more than one bank, we have a bank select and name # For more than one bank, we have a bank select and name
# the signals gated_*. # the signals gated_*.
@ -285,10 +285,10 @@ class bank(design.design):
temp = [] temp = []
for col in range(self.num_cols): for col in range(self.num_cols):
for bitline in self.total_bitline_list: for bitline in self.total_bitline_list:
temp.append(bitline+"[{0}]".format(col)) temp.append(bitline+"_{0}".format(col))
for row in range(self.num_rows): for row in range(self.num_rows):
for wordline in self.total_wl_list: for wordline in self.total_wl_list:
temp.append(wordline+"[{0}]".format(row)) temp.append(wordline+"_{0}".format(row))
temp.append("vdd") temp.append("vdd")
temp.append("gnd") temp.append("gnd")
self.connect_inst(temp) self.connect_inst(temp)
@ -308,8 +308,8 @@ class bank(design.design):
mod=self.precharge_array[port])) mod=self.precharge_array[port]))
temp = [] temp = []
for i in range(self.num_cols): for i in range(self.num_cols):
temp.append(self.read_bl_list[port]+"[{0}]".format(i)) temp.append(self.read_bl_list[port]+"_{0}".format(i))
temp.append(self.read_br_list[port]+"[{0}]".format(i)) temp.append(self.read_br_list[port]+"_{0}".format(i))
temp.extend([self.prefix+"clk_buf_bar{0}".format(self.read_index[port]), "vdd"]) temp.extend([self.prefix+"clk_buf_bar{0}".format(self.read_index[port]), "vdd"])
self.connect_inst(temp) self.connect_inst(temp)
@ -337,13 +337,13 @@ class bank(design.design):
temp = [] temp = []
for col in range(self.num_cols): for col in range(self.num_cols):
temp.append(self.total_bl_list[port]+"[{0}]".format(col)) temp.append(self.total_bl_list[port]+"_{0}".format(col))
temp.append(self.total_br_list[port]+"[{0}]".format(col)) temp.append(self.total_br_list[port]+"_{0}".format(col))
for word in range(self.words_per_row): for word in range(self.words_per_row):
temp.append("sel{0}[{1}]".format(port,word)) temp.append("sel{0}_{1}".format(port,word))
for bit in range(self.word_size): for bit in range(self.word_size):
temp.append(self.total_bl_list[port]+"_out[{0}]".format(bit)) temp.append(self.total_bl_list[port]+"_out_{0}".format(bit))
temp.append(self.total_br_list[port]+"_out[{0}]".format(bit)) temp.append(self.total_br_list[port]+"_out_{0}".format(bit))
temp.append("gnd") temp.append("gnd")
self.connect_inst(temp) self.connect_inst(temp)
@ -371,13 +371,13 @@ class bank(design.design):
temp = [] temp = []
for bit in range(self.word_size): for bit in range(self.word_size):
temp.append("dout{0}[{1}]".format(self.read_index[port],bit)) temp.append("dout{0}_{1}".format(self.read_index[port],bit))
if self.words_per_row == 1: if self.words_per_row == 1:
temp.append(self.read_bl_list[port]+"[{0}]".format(bit)) temp.append(self.read_bl_list[port]+"_{0}".format(bit))
temp.append(self.read_br_list[port]+"[{0}]".format(bit)) temp.append(self.read_br_list[port]+"_{0}".format(bit))
else: else:
temp.append(self.read_bl_list[port]+"_out[{0}]".format(bit)) temp.append(self.read_bl_list[port]+"_out_{0}".format(bit))
temp.append(self.read_br_list[port]+"_out[{0}]".format(bit)) temp.append(self.read_br_list[port]+"_out_{0}".format(bit))
temp.extend([self.prefix+"s_en{}".format(self.read_index[port]), "vdd", "gnd"]) temp.extend([self.prefix+"s_en{}".format(self.read_index[port]), "vdd", "gnd"])
self.connect_inst(temp) self.connect_inst(temp)
@ -402,14 +402,14 @@ class bank(design.design):
temp = [] temp = []
for bit in range(self.word_size): for bit in range(self.word_size):
temp.append("din{0}[{1}]".format(port,bit)) temp.append("din{0}_{1}".format(port,bit))
for bit in range(self.word_size): for bit in range(self.word_size):
if (self.words_per_row == 1): if (self.words_per_row == 1):
temp.append(self.write_bl_list[port]+"[{0}]".format(bit)) temp.append(self.write_bl_list[port]+"_{0}".format(bit))
temp.append(self.write_br_list[port]+"[{0}]".format(bit)) temp.append(self.write_br_list[port]+"_{0}".format(bit))
else: else:
temp.append(self.write_bl_list[port]+"_out[{0}]".format(bit)) temp.append(self.write_bl_list[port]+"_out_{0}".format(bit))
temp.append(self.write_br_list[port]+"_out[{0}]".format(bit)) temp.append(self.write_br_list[port]+"_out_{0}".format(bit))
temp.extend([self.prefix+"w_en{0}".format(port), "vdd", "gnd"]) temp.extend([self.prefix+"w_en{0}".format(port), "vdd", "gnd"])
self.connect_inst(temp) self.connect_inst(temp)
@ -434,9 +434,9 @@ class bank(design.design):
temp = [] temp = []
for bit in range(self.row_addr_size): for bit in range(self.row_addr_size):
temp.append("addr{0}[{1}]".format(port,bit+self.col_addr_size)) temp.append("addr{0}_{1}".format(port,bit+self.col_addr_size))
for row in range(self.num_rows): for row in range(self.num_rows):
temp.append("dec_out{0}[{1}]".format(port,row)) temp.append("dec_out{0}_{1}".format(port,row))
temp.extend(["vdd", "gnd"]) temp.extend(["vdd", "gnd"])
self.connect_inst(temp) self.connect_inst(temp)
@ -466,9 +466,9 @@ class bank(design.design):
temp = [] temp = []
for row in range(self.num_rows): for row in range(self.num_rows):
temp.append("dec_out{0}[{1}]".format(port,row)) temp.append("dec_out{0}_{1}".format(port,row))
for row in range(self.num_rows): for row in range(self.num_rows):
temp.append(self.total_wl_list[port]+"[{0}]".format(row)) temp.append(self.total_wl_list[port]+"_{0}".format(row))
temp.append(self.prefix+"clk_buf{0}".format(port)) temp.append(self.prefix+"clk_buf{0}".format(port))
temp.append("vdd") temp.append("vdd")
temp.append("gnd") temp.append("gnd")
@ -510,9 +510,9 @@ class bank(design.design):
temp = [] temp = []
for bit in range(self.col_addr_size): for bit in range(self.col_addr_size):
temp.append("addr{0}[{1}]".format(port,bit)) temp.append("addr{0}_{1}".format(port,bit))
for bit in range(self.num_col_addr_lines): for bit in range(self.num_col_addr_lines):
temp.append("sel{0}[{1}]".format(port,bit)) temp.append("sel{0}_{1}".format(port,bit))
temp.extend(["vdd", "gnd"]) temp.extend(["vdd", "gnd"])
self.connect_inst(temp) self.connect_inst(temp)
@ -679,10 +679,10 @@ class bank(design.design):
# FIXME: Update for multiport # FIXME: Update for multiport
for port in range(self.total_read): for port in range(self.total_read):
for col in range(self.num_cols): for col in range(self.num_cols):
precharge_bl = self.precharge_array_inst[port].get_pin("bl[{}]".format(col)).bc() precharge_bl = self.precharge_array_inst[port].get_pin("bl_{}".format(col)).bc()
precharge_br = self.precharge_array_inst[port].get_pin("br[{}]".format(col)).bc() precharge_br = self.precharge_array_inst[port].get_pin("br_{}".format(col)).bc()
bitcell_bl = self.bitcell_array_inst.get_pin(self.read_bl_list[port]+"[{}]".format(col)).uc() bitcell_bl = self.bitcell_array_inst.get_pin(self.read_bl_list[port]+"_{}".format(col)).uc()
bitcell_br = self.bitcell_array_inst.get_pin(self.read_br_list[port]+"[{}]".format(col)).uc() bitcell_br = self.bitcell_array_inst.get_pin(self.read_br_list[port]+"_{}".format(col)).uc()
yoffset = 0.5*(precharge_bl.y+bitcell_bl.y) yoffset = 0.5*(precharge_bl.y+bitcell_bl.y)
self.add_path("metal2",[precharge_bl, vector(precharge_bl.x,yoffset), self.add_path("metal2",[precharge_bl, vector(precharge_bl.x,yoffset),
@ -701,10 +701,10 @@ class bank(design.design):
# FIXME: Update for multiport # FIXME: Update for multiport
for port in range(self.total_ports): for port in range(self.total_ports):
for col in range(self.num_cols): for col in range(self.num_cols):
col_mux_bl = self.col_mux_array_inst[port].get_pin("bl[{}]".format(col)).uc() col_mux_bl = self.col_mux_array_inst[port].get_pin("bl_{}".format(col)).uc()
col_mux_br = self.col_mux_array_inst[port].get_pin("br[{}]".format(col)).uc() col_mux_br = self.col_mux_array_inst[port].get_pin("br_{}".format(col)).uc()
bitcell_bl = self.bitcell_array_inst.get_pin(self.total_bl_list[port]+"[{}]".format(col)).bc() bitcell_bl = self.bitcell_array_inst.get_pin(self.total_bl_list[port]+"_{}".format(col)).bc()
bitcell_br = self.bitcell_array_inst.get_pin(self.total_br_list[port]+"[{}]".format(col)).bc() bitcell_br = self.bitcell_array_inst.get_pin(self.total_br_list[port]+"_{}".format(col)).bc()
yoffset = 0.5*(col_mux_bl.y+bitcell_bl.y) yoffset = 0.5*(col_mux_bl.y+bitcell_bl.y)
self.add_path("metal2",[col_mux_bl, vector(col_mux_bl.x,yoffset), self.add_path("metal2",[col_mux_bl, vector(col_mux_bl.x,yoffset),
@ -718,17 +718,17 @@ class bank(design.design):
for port in range(self.total_read): for port in range(self.total_read):
for bit in range(self.word_size): for bit in range(self.word_size):
sense_amp_bl = self.sense_amp_array_inst[port].get_pin("bl[{}]".format(bit)).uc() sense_amp_bl = self.sense_amp_array_inst[port].get_pin("bl_{}".format(bit)).uc()
sense_amp_br = self.sense_amp_array_inst[port].get_pin("br[{}]".format(bit)).uc() sense_amp_br = self.sense_amp_array_inst[port].get_pin("br_{}".format(bit)).uc()
if self.col_addr_size>0: if self.col_addr_size>0:
# Sense amp is connected to the col mux # Sense amp is connected to the col mux
connect_bl = self.col_mux_array_inst[port].get_pin("bl_out[{}]".format(bit)).bc() connect_bl = self.col_mux_array_inst[port].get_pin("bl_out_{}".format(bit)).bc()
connect_br = self.col_mux_array_inst[port].get_pin("br_out[{}]".format(bit)).bc() connect_br = self.col_mux_array_inst[port].get_pin("br_out_{}".format(bit)).bc()
else: else:
# Sense amp is directly connected to the bitcell array # Sense amp is directly connected to the bitcell array
connect_bl = self.bitcell_array_inst.get_pin(self.read_bl_list[port]+"[{}]".format(bit)).bc() connect_bl = self.bitcell_array_inst.get_pin(self.read_bl_list[port]+"_{}".format(bit)).bc()
connect_br = self.bitcell_array_inst.get_pin(self.read_br_list[port]+"[{}]".format(bit)).bc() connect_br = self.bitcell_array_inst.get_pin(self.read_br_list[port]+"_{}".format(bit)).bc()
yoffset = 0.5*(sense_amp_bl.y+connect_bl.y) yoffset = 0.5*(sense_amp_bl.y+connect_bl.y)
@ -744,8 +744,8 @@ class bank(design.design):
# FIXME: Update for multiport # FIXME: Update for multiport
for port in range(self.total_read): for port in range(self.total_read):
for bit in range(self.word_size): for bit in range(self.word_size):
data_pin = self.sense_amp_array_inst[port].get_pin("data[{}]".format(bit)) data_pin = self.sense_amp_array_inst[port].get_pin("data_{}".format(bit))
self.add_layout_pin_rect_center(text="dout{0}[{1}]".format(self.read_index[port],bit), self.add_layout_pin_rect_center(text="dout{0}_{1}".format(self.read_index[port],bit),
layer=data_pin.layer, layer=data_pin.layer,
offset=data_pin.center(), offset=data_pin.center(),
height=data_pin.height(), height=data_pin.height(),
@ -760,8 +760,8 @@ class bank(design.design):
for port in range(self.total_ports): for port in range(self.total_ports):
for row in range(self.row_addr_size): for row in range(self.row_addr_size):
addr_idx = row + self.col_addr_size addr_idx = row + self.col_addr_size
decoder_name = "addr[{}]".format(row) decoder_name = "addr_{}".format(row)
addr_name = "addr{0}[{1}]".format(port,addr_idx) addr_name = "addr{0}_{1}".format(port,addr_idx)
self.copy_layout_pin(self.row_decoder_inst[port], decoder_name, addr_name) self.copy_layout_pin(self.row_decoder_inst[port], decoder_name, addr_name)
@ -769,8 +769,8 @@ class bank(design.design):
""" Connecting write driver """ """ Connecting write driver """
for port in range(self.total_ports): for port in range(self.total_ports):
for row in range(self.word_size): for row in range(self.word_size):
data_name = "data[{}]".format(row) data_name = "data_{}".format(row)
din_name = "din{0}[{1}]".format(port,row) din_name = "din{0}_{1}".format(port,row)
self.copy_layout_pin(self.write_driver_array_inst[port], data_name, din_name) self.copy_layout_pin(self.write_driver_array_inst[port], data_name, din_name)
@ -779,15 +779,15 @@ class bank(design.design):
for port in range(self.total_ports): for port in range(self.total_ports):
for row in range(self.num_rows): for row in range(self.num_rows):
# The pre/post is to access the pin from "outside" the cell to avoid DRCs # The pre/post is to access the pin from "outside" the cell to avoid DRCs
decoder_out_pos = self.row_decoder_inst[port].get_pin("decode[{}]".format(row)).rc() decoder_out_pos = self.row_decoder_inst[port].get_pin("decode_{}".format(row)).rc()
driver_in_pos = self.wordline_driver_inst[port].get_pin("in[{}]".format(row)).lc() driver_in_pos = self.wordline_driver_inst[port].get_pin("in_{}".format(row)).lc()
mid1 = decoder_out_pos.scale(0.5,1)+driver_in_pos.scale(0.5,0) mid1 = decoder_out_pos.scale(0.5,1)+driver_in_pos.scale(0.5,0)
mid2 = decoder_out_pos.scale(0.5,0)+driver_in_pos.scale(0.5,1) mid2 = decoder_out_pos.scale(0.5,0)+driver_in_pos.scale(0.5,1)
self.add_path("metal1", [decoder_out_pos, mid1, mid2, driver_in_pos]) self.add_path("metal1", [decoder_out_pos, mid1, mid2, driver_in_pos])
# The mid guarantees we exit the input cell to the right. # The mid guarantees we exit the input cell to the right.
driver_wl_pos = self.wordline_driver_inst[port].get_pin("wl[{}]".format(row)).rc() driver_wl_pos = self.wordline_driver_inst[port].get_pin("wl_{}".format(row)).rc()
bitcell_wl_pos = self.bitcell_array_inst.get_pin(self.total_wl_list[port]+"[{}]".format(row)).lc() bitcell_wl_pos = self.bitcell_array_inst.get_pin(self.total_wl_list[port]+"_{}".format(row)).lc()
mid1 = driver_wl_pos.scale(0.5,1)+bitcell_wl_pos.scale(0.5,0) mid1 = driver_wl_pos.scale(0.5,1)+bitcell_wl_pos.scale(0.5,0)
mid2 = driver_wl_pos.scale(0.5,0)+bitcell_wl_pos.scale(0.5,1) mid2 = driver_wl_pos.scale(0.5,0)+bitcell_wl_pos.scale(0.5,1)
self.add_path("metal1", [driver_wl_pos, mid1, mid2, bitcell_wl_pos]) self.add_path("metal1", [driver_wl_pos, mid1, mid2, bitcell_wl_pos])
@ -805,25 +805,25 @@ class bank(design.design):
decode_names = ["Zb", "Z"] decode_names = ["Zb", "Z"]
# The Address LSB # The Address LSB
self.copy_layout_pin(self.col_decoder_inst[port], "A", "addr{}[0]".format(port)) self.copy_layout_pin(self.col_decoder_inst[port], "A", "addr{}_0".format(port))
elif self.col_addr_size > 1: elif self.col_addr_size > 1:
decode_names = [] decode_names = []
for i in range(self.num_col_addr_lines): for i in range(self.num_col_addr_lines):
decode_names.append("out[{}]".format(i)) decode_names.append("out_{}".format(i))
for i in range(self.col_addr_size): for i in range(self.col_addr_size):
decoder_name = "in[{}]".format(i) decoder_name = "in_{}".format(i)
addr_name = "addr{0}[{1}]".format(port,i) addr_name = "addr{0}_{1}".format(port,i)
self.copy_layout_pin(self.col_decoder_inst[port], decoder_name, addr_name) self.copy_layout_pin(self.col_decoder_inst[port], decoder_name, addr_name)
# This will do a quick "river route" on two layers. # This will do a quick "river route" on two layers.
# When above the top select line it will offset "inward" again to prevent conflicts. # When above the top select line it will offset "inward" again to prevent conflicts.
# This could be done on a single layer, but we follow preferred direction rules for later routing. # This could be done on a single layer, but we follow preferred direction rules for later routing.
top_y_offset = self.col_mux_array_inst[port].get_pin("sel[{}]".format(self.num_col_addr_lines-1)).cy() top_y_offset = self.col_mux_array_inst[port].get_pin("sel_{}".format(self.num_col_addr_lines-1)).cy()
for (decode_name,i) in zip(decode_names,range(self.num_col_addr_lines)): for (decode_name,i) in zip(decode_names,range(self.num_col_addr_lines)):
mux_name = "sel[{}]".format(i) mux_name = "sel_{}".format(i)
mux_addr_pos = self.col_mux_array_inst[port].get_pin(mux_name).lc() mux_addr_pos = self.col_mux_array_inst[port].get_pin(mux_name).lc()
decode_out_pos = self.col_decoder_inst[port].get_pin(decode_name).center() decode_out_pos = self.col_decoder_inst[port].get_pin(decode_name).center()
@ -846,7 +846,7 @@ class bank(design.design):
""" """
# Add the wordline names # Add the wordline names
for i in range(self.num_rows): for i in range(self.num_rows):
wl_name = "wl[{}]".format(i) wl_name = "wl_{}".format(i)
wl_pin = self.bitcell_array_inst.get_pin(wl_name) wl_pin = self.bitcell_array_inst.get_pin(wl_name)
self.add_label(text=wl_name, self.add_label(text=wl_name,
layer="metal1", layer="metal1",
@ -854,8 +854,8 @@ class bank(design.design):
# Add the bitline names # Add the bitline names
for i in range(self.num_cols): for i in range(self.num_cols):
bl_name = "bl[{}]".format(i) bl_name = "bl_{}".format(i)
br_name = "br[{}]".format(i) br_name = "br_{}".format(i)
bl_pin = self.bitcell_array_inst.get_pin(bl_name) bl_pin = self.bitcell_array_inst.get_pin(bl_name)
br_pin = self.bitcell_array_inst.get_pin(br_name) br_pin = self.bitcell_array_inst.get_pin(br_name)
self.add_label(text=bl_name, self.add_label(text=bl_name,
@ -867,16 +867,16 @@ class bank(design.design):
# # Add the data output names to the sense amp output # # Add the data output names to the sense amp output
# for i in range(self.word_size): # for i in range(self.word_size):
# data_name = "data[{}]".format(i) # data_name = "data_{}".format(i)
# data_pin = self.sense_amp_array_inst.get_pin(data_name) # data_pin = self.sense_amp_array_inst.get_pin(data_name)
# self.add_label(text="sa_out[{}]".format(i), # self.add_label(text="sa_out_{}".format(i),
# layer="metal2", # layer="metal2",
# offset=data_pin.center()) # offset=data_pin.center())
# Add labels on the decoder # Add labels on the decoder
for i in range(self.word_size): for i in range(self.word_size):
data_name = "dec_out[{}]".format(i) data_name = "dec_out_{}".format(i)
pin_name = "in[{}]".format(i) pin_name = "in_{}".format(i)
data_pin = self.wordline_driver_inst[0].get_pin(pin_name) data_pin = self.wordline_driver_inst[0].get_pin(pin_name)
self.add_label(text=data_name, self.add_label(text=data_name,
layer="metal1", layer="metal1",

View File

@ -69,10 +69,10 @@ class bitcell_array(design.design):
column_list = self.cell.list_all_bitline_names() column_list = self.cell.list_all_bitline_names()
for col in range(self.column_size): for col in range(self.column_size):
for cell_column in column_list: for cell_column in column_list:
self.add_pin(cell_column+"[{0}]".format(col)) self.add_pin(cell_column+"_{0}".format(col))
for row in range(self.row_size): for row in range(self.row_size):
for cell_row in row_list: for cell_row in row_list:
self.add_pin(cell_row+"[{0}]".format(row)) self.add_pin(cell_row+"_{0}".format(row))
self.add_pin("vdd") self.add_pin("vdd")
self.add_pin("gnd") self.add_pin("gnd")
@ -105,7 +105,7 @@ class bitcell_array(design.design):
for col in range(self.column_size): for col in range(self.column_size):
for cell_column in column_list: for cell_column in column_list:
bl_pin = self.cell_inst[0,col].get_pin(cell_column) bl_pin = self.cell_inst[0,col].get_pin(cell_column)
self.add_layout_pin(text=cell_column+"[{0}]".format(col), self.add_layout_pin(text=cell_column+"_{0}".format(col),
layer="metal2", layer="metal2",
offset=bl_pin.ll(), offset=bl_pin.ll(),
width=bl_pin.width(), width=bl_pin.width(),
@ -118,7 +118,7 @@ class bitcell_array(design.design):
for row in range(self.row_size): for row in range(self.row_size):
for cell_row in row_list: for cell_row in row_list:
wl_pin = self.cell_inst[row,0].get_pin(cell_row) wl_pin = self.cell_inst[row,0].get_pin(cell_row)
self.add_layout_pin(text=cell_row+"[{0}]".format(row), self.add_layout_pin(text=cell_row+"_{0}".format(row),
layer="metal1", layer="metal1",
offset=wl_pin.ll(), offset=wl_pin.ll(),
width=self.width, width=self.width,

View File

@ -299,7 +299,7 @@ class control_logic(design.design):
control_inputs = ["cs"] control_inputs = ["cs"]
else: else:
control_inputs = ["cs", "we"] control_inputs = ["cs", "we"]
dff_out_map = zip(["dout_bar[{}]".format(i) for i in range(2*self.num_control_signals - 1)], control_inputs) dff_out_map = zip(["dout_bar_{}".format(i) for i in range(2*self.num_control_signals - 1)], control_inputs)
self.connect_vertical_bus(dff_out_map, self.ctrl_dff_inst, self.rail_offsets) self.connect_vertical_bus(dff_out_map, self.ctrl_dff_inst, self.rail_offsets)
# Connect the clock rail to the other clock rail # Connect the clock rail to the other clock rail
@ -311,9 +311,9 @@ class control_logic(design.design):
offset=rail_pos, offset=rail_pos,
rotate=90) rotate=90)
self.copy_layout_pin(self.ctrl_dff_inst, "din[0]", "csb") self.copy_layout_pin(self.ctrl_dff_inst, "din_0", "csb")
if (self.port_type == "rw"): if (self.port_type == "rw"):
self.copy_layout_pin(self.ctrl_dff_inst, "din[1]", "web") self.copy_layout_pin(self.ctrl_dff_inst, "din_1", "web")
def create_dffs(self): def create_dffs(self):

View File

@ -83,21 +83,21 @@ class dff_array(design.design):
def get_din_name(self, row, col): def get_din_name(self, row, col):
if self.columns == 1: if self.columns == 1:
din_name = "din[{0}]".format(row) din_name = "din_{0}".format(row)
elif self.rows == 1: elif self.rows == 1:
din_name = "din[{0}]".format(col) din_name = "din_{0}".format(col)
else: else:
din_name = "din[{0}][{1}]".format(row,col) din_name = "din_{0}_{1}".format(row,col)
return din_name return din_name
def get_dout_name(self, row, col): def get_dout_name(self, row, col):
if self.columns == 1: if self.columns == 1:
dout_name = "dout[{0}]".format(row) dout_name = "dout_{0}".format(row)
elif self.rows == 1: elif self.rows == 1:
dout_name = "dout[{0}]".format(col) dout_name = "dout_{0}".format(col)
else: else:
dout_name = "dout[{0}][{1}]".format(row,col) dout_name = "dout_{0}_{1}".format(row,col)
return dout_name return dout_name

View File

@ -84,31 +84,31 @@ class dff_buf_array(design.design):
def get_din_name(self, row, col): def get_din_name(self, row, col):
if self.columns == 1: if self.columns == 1:
din_name = "din[{0}]".format(row) din_name = "din_{0}".format(row)
elif self.rows == 1: elif self.rows == 1:
din_name = "din[{0}]".format(col) din_name = "din_{0}".format(col)
else: else:
din_name = "din[{0}][{1}]".format(row,col) din_name = "din_{0}_{1}".format(row,col)
return din_name return din_name
def get_dout_name(self, row, col): def get_dout_name(self, row, col):
if self.columns == 1: if self.columns == 1:
dout_name = "dout[{0}]".format(row) dout_name = "dout_{0}".format(row)
elif self.rows == 1: elif self.rows == 1:
dout_name = "dout[{0}]".format(col) dout_name = "dout_{0}".format(col)
else: else:
dout_name = "dout[{0}][{1}]".format(row,col) dout_name = "dout_{0}_{1}".format(row,col)
return dout_name return dout_name
def get_dout_bar_name(self, row, col): def get_dout_bar_name(self, row, col):
if self.columns == 1: if self.columns == 1:
dout_bar_name = "dout_bar[{0}]".format(row) dout_bar_name = "dout_bar_{0}".format(row)
elif self.rows == 1: elif self.rows == 1:
dout_bar_name = "dout_bar[{0}]".format(col) dout_bar_name = "dout_bar_{0}".format(col)
else: else:
dout_bar_name = "dout_bar[{0}][{1}]".format(row,col) dout_bar_name = "dout_bar_{0}_{1}".format(row,col)
return dout_bar_name return dout_bar_name

View File

@ -84,31 +84,31 @@ class dff_inv_array(design.design):
def get_din_name(self, row, col): def get_din_name(self, row, col):
if self.columns == 1: if self.columns == 1:
din_name = "din[{0}]".format(row) din_name = "din_{0}".format(row)
elif self.rows == 1: elif self.rows == 1:
din_name = "din[{0}]".format(col) din_name = "din_{0}".format(col)
else: else:
din_name = "din[{0}][{1}]".format(row,col) din_name = "din_{0}_{1}".format(row,col)
return din_name return din_name
def get_dout_name(self, row, col): def get_dout_name(self, row, col):
if self.columns == 1: if self.columns == 1:
dout_name = "dout[{0}]".format(row) dout_name = "dout_{0}".format(row)
elif self.rows == 1: elif self.rows == 1:
dout_name = "dout[{0}]".format(col) dout_name = "dout_{0}".format(col)
else: else:
dout_name = "dout[{0}][{1}]".format(row,col) dout_name = "dout_{0}_{1}".format(row,col)
return dout_name return dout_name
def get_dout_bar_name(self, row, col): def get_dout_bar_name(self, row, col):
if self.columns == 1: if self.columns == 1:
dout_bar_name = "dout_bar[{0}]".format(row) dout_bar_name = "dout_bar_{0}".format(row)
elif self.rows == 1: elif self.rows == 1:
dout_bar_name = "dout_bar[{0}]".format(col) dout_bar_name = "dout_bar_{0}".format(col)
else: else:
dout_bar_name = "dout_bar[{0}][{1}]".format(row,col) dout_bar_name = "dout_bar_{0}_{1}".format(row,col)
return dout_bar_name return dout_bar_name

View File

@ -27,8 +27,8 @@ class hierarchical_decoder(design.design):
b = self.mod_bitcell() b = self.mod_bitcell()
self.bitcell_height = b.height self.bitcell_height = b.height
self.NAND_FORMAT = "DEC_NAND[{0}]" self.NAND_FORMAT = "DEC_NAND_{0}"
self.INV_FORMAT = "DEC_INV_[{0}]" self.INV_FORMAT = "DEC_INV_{0}"
self.pre2x4_inst = [] self.pre2x4_inst = []
self.pre3x8_inst = [] self.pre3x8_inst = []
@ -168,7 +168,7 @@ class hierarchical_decoder(design.design):
min_x = min(min_x, -self.pre3_8.width) min_x = min(min_x, -self.pre3_8.width)
input_offset=vector(min_x - self.input_routing_width,0) input_offset=vector(min_x - self.input_routing_width,0)
input_bus_names = ["addr[{0}]".format(i) for i in range(self.num_inputs)] input_bus_names = ["addr_{0}".format(i) for i in range(self.num_inputs)]
self.input_rails = self.create_vertical_pin_bus(layer="metal2", self.input_rails = self.create_vertical_pin_bus(layer="metal2",
pitch=self.m2_pitch, pitch=self.m2_pitch,
offset=input_offset, offset=input_offset,
@ -184,9 +184,9 @@ class hierarchical_decoder(design.design):
for i in range(2): for i in range(2):
index = pre_num * 2 + i index = pre_num * 2 + i
input_pos = self.input_rails["addr[{}]".format(index)] input_pos = self.input_rails["addr_{}".format(index)]
in_name = "in[{}]".format(i) in_name = "in_{}".format(i)
decoder_pin = self.pre2x4_inst[pre_num].get_pin(in_name) decoder_pin = self.pre2x4_inst[pre_num].get_pin(in_name)
# To prevent conflicts, we will offset each input connect so # To prevent conflicts, we will offset each input connect so
@ -201,9 +201,9 @@ class hierarchical_decoder(design.design):
for i in range(3): for i in range(3):
index = pre_num * 3 + i + self.no_of_pre2x4 * 2 index = pre_num * 3 + i + self.no_of_pre2x4 * 2
input_pos = self.input_rails["addr[{}]".format(index)] input_pos = self.input_rails["addr_{}".format(index)]
in_name = "in[{}]".format(i) in_name = "in_{}".format(i)
decoder_pin = self.pre3x8_inst[pre_num].get_pin(in_name) decoder_pin = self.pre3x8_inst[pre_num].get_pin(in_name)
# To prevent conflicts, we will offset each input connect so # To prevent conflicts, we will offset each input connect so
@ -230,10 +230,10 @@ class hierarchical_decoder(design.design):
""" Add the module pins """ """ Add the module pins """
for i in range(self.num_inputs): for i in range(self.num_inputs):
self.add_pin("addr[{0}]".format(i)) self.add_pin("addr_{0}".format(i))
for j in range(self.rows): for j in range(self.rows):
self.add_pin("decode[{0}]".format(j)) self.add_pin("decode_{0}".format(j))
self.add_pin("vdd") self.add_pin("vdd")
self.add_pin("gnd") self.add_pin("gnd")
@ -258,12 +258,12 @@ class hierarchical_decoder(design.design):
pins = [] pins = []
for input_index in range(2): for input_index in range(2):
pins.append("addr[{0}]".format(input_index + index_off1)) pins.append("addr_{0}".format(input_index + index_off1))
for output_index in range(4): for output_index in range(4):
pins.append("out[{0}]".format(output_index + index_off2)) pins.append("out_{0}".format(output_index + index_off2))
pins.extend(["vdd", "gnd"]) pins.extend(["vdd", "gnd"])
self.pre2x4_inst.append(self.add_inst(name="pre[{0}]".format(num), self.pre2x4_inst.append(self.add_inst(name="pre_{0}".format(num),
mod=self.pre2_4)) mod=self.pre2_4))
self.connect_inst(pins) self.connect_inst(pins)
@ -277,12 +277,12 @@ class hierarchical_decoder(design.design):
pins = [] pins = []
for input_index in range(3): for input_index in range(3):
pins.append("addr[{0}]".format(input_index + in_index_offset)) pins.append("addr_{0}".format(input_index + in_index_offset))
for output_index in range(8): for output_index in range(8):
pins.append("out[{0}]".format(output_index + out_index_offset)) pins.append("out_{0}".format(output_index + out_index_offset))
pins.extend(["vdd", "gnd"]) pins.extend(["vdd", "gnd"])
self.pre3x8_inst.append(self.add_inst(name="pre3x8[{0}]".format(num), self.pre3x8_inst.append(self.add_inst(name="pre3x8_{0}".format(num),
mod=self.pre3_8)) mod=self.pre3_8))
self.connect_inst(pins) self.connect_inst(pins)
@ -340,9 +340,9 @@ class hierarchical_decoder(design.design):
name = self.NAND_FORMAT.format(row) name = self.NAND_FORMAT.format(row)
self.nand_inst.append(self.add_inst(name=name, self.nand_inst.append(self.add_inst(name=name,
mod=self.nand2)) mod=self.nand2))
pins =["out[{0}]".format(i), pins =["out_{0}".format(i),
"out[{0}]".format(j + len(self.predec_groups[0])), "out_{0}".format(j + len(self.predec_groups[0])),
"Z[{0}]".format(row), "Z_{0}".format(row),
"vdd", "gnd"] "vdd", "gnd"]
self.connect_inst(pins) self.connect_inst(pins)
@ -359,10 +359,10 @@ class hierarchical_decoder(design.design):
self.nand_inst.append(self.add_inst(name=name, self.nand_inst.append(self.add_inst(name=name,
mod=self.nand3)) mod=self.nand3))
pins = ["out[{0}]".format(i), pins = ["out_{0}".format(i),
"out[{0}]".format(j + len(self.predec_groups[0])), "out_{0}".format(j + len(self.predec_groups[0])),
"out[{0}]".format(k + len(self.predec_groups[0]) + len(self.predec_groups[1])), "out_{0}".format(k + len(self.predec_groups[0]) + len(self.predec_groups[1])),
"Z[{0}]".format(row), "Z_{0}".format(row),
"vdd", "gnd"] "vdd", "gnd"]
self.connect_inst(pins) self.connect_inst(pins)
@ -377,8 +377,8 @@ class hierarchical_decoder(design.design):
name = self.INV_FORMAT.format(row) name = self.INV_FORMAT.format(row)
self.inv_inst.append(self.add_inst(name=name, self.inv_inst.append(self.add_inst(name=name,
mod=self.inv)) mod=self.inv))
self.connect_inst(args=["Z[{0}]".format(row), self.connect_inst(args=["Z_{0}".format(row),
"decode[{0}]".format(row), "decode_{0}".format(row),
"vdd", "gnd"]) "vdd", "gnd"])
@ -466,7 +466,7 @@ class hierarchical_decoder(design.design):
self.add_path("metal1", [zr_pos, mid1_pos, mid2_pos, al_pos]) self.add_path("metal1", [zr_pos, mid1_pos, mid2_pos, al_pos])
z_pin = self.inv_inst[row].get_pin("Z") z_pin = self.inv_inst[row].get_pin("Z")
self.add_layout_pin(text="decode[{0}]".format(row), self.add_layout_pin(text="decode_{0}".format(row),
layer="metal1", layer="metal1",
offset=z_pin.ll(), offset=z_pin.ll(),
width=z_pin.width(), width=z_pin.width(),
@ -480,7 +480,7 @@ class hierarchical_decoder(design.design):
# This is not needed for inputs <4 since they have no pre/decode stages. # This is not needed for inputs <4 since they have no pre/decode stages.
if (self.num_inputs >= 4): if (self.num_inputs >= 4):
input_offset = vector(0.5*self.m2_width,0) input_offset = vector(0.5*self.m2_width,0)
input_bus_names = ["predecode[{0}]".format(i) for i in range(self.total_number_of_predecoder_outputs)] input_bus_names = ["predecode_{0}".format(i) for i in range(self.total_number_of_predecoder_outputs)]
self.predecode_rails = self.create_vertical_pin_bus(layer="metal2", self.predecode_rails = self.create_vertical_pin_bus(layer="metal2",
pitch=self.m2_pitch, pitch=self.m2_pitch,
offset=input_offset, offset=input_offset,
@ -497,8 +497,8 @@ class hierarchical_decoder(design.design):
# FIXME: convert to connect_bus # FIXME: convert to connect_bus
for pre_num in range(self.no_of_pre2x4): for pre_num in range(self.no_of_pre2x4):
for i in range(4): for i in range(4):
predecode_name = "predecode[{}]".format(pre_num * 4 + i) predecode_name = "predecode_{}".format(pre_num * 4 + i)
out_name = "out[{}]".format(i) out_name = "out_{}".format(i)
pin = self.pre2x4_inst[pre_num].get_pin(out_name) pin = self.pre2x4_inst[pre_num].get_pin(out_name)
self.route_predecode_rail_m3(predecode_name, pin) self.route_predecode_rail_m3(predecode_name, pin)
@ -506,8 +506,8 @@ class hierarchical_decoder(design.design):
# FIXME: convert to connect_bus # FIXME: convert to connect_bus
for pre_num in range(self.no_of_pre3x8): for pre_num in range(self.no_of_pre3x8):
for i in range(8): for i in range(8):
predecode_name = "predecode[{}]".format(pre_num * 8 + i + self.no_of_pre2x4 * 4) predecode_name = "predecode_{}".format(pre_num * 8 + i + self.no_of_pre2x4 * 4)
out_name = "out[{}]".format(i) out_name = "out_{}".format(i)
pin = self.pre3x8_inst[pre_num].get_pin(out_name) pin = self.pre3x8_inst[pre_num].get_pin(out_name)
self.route_predecode_rail_m3(predecode_name, pin) self.route_predecode_rail_m3(predecode_name, pin)
@ -526,9 +526,9 @@ class hierarchical_decoder(design.design):
for index_A in self.predec_groups[0]: for index_A in self.predec_groups[0]:
for index_B in self.predec_groups[1]: for index_B in self.predec_groups[1]:
# FIXME: convert to connect_bus? # FIXME: convert to connect_bus?
predecode_name = "predecode[{}]".format(index_A) predecode_name = "predecode_{}".format(index_A)
self.route_predecode_rail(predecode_name, self.nand_inst[row_index].get_pin("A")) self.route_predecode_rail(predecode_name, self.nand_inst[row_index].get_pin("A"))
predecode_name = "predecode[{}]".format(index_B) predecode_name = "predecode_{}".format(index_B)
self.route_predecode_rail(predecode_name, self.nand_inst[row_index].get_pin("B")) self.route_predecode_rail(predecode_name, self.nand_inst[row_index].get_pin("B"))
row_index = row_index + 1 row_index = row_index + 1
@ -537,11 +537,11 @@ class hierarchical_decoder(design.design):
for index_B in self.predec_groups[1]: for index_B in self.predec_groups[1]:
for index_C in self.predec_groups[2]: for index_C in self.predec_groups[2]:
# FIXME: convert to connect_bus? # FIXME: convert to connect_bus?
predecode_name = "predecode[{}]".format(index_A) predecode_name = "predecode_{}".format(index_A)
self.route_predecode_rail(predecode_name, self.nand_inst[row_index].get_pin("A")) self.route_predecode_rail(predecode_name, self.nand_inst[row_index].get_pin("A"))
predecode_name = "predecode[{}]".format(index_B) predecode_name = "predecode_{}".format(index_B)
self.route_predecode_rail(predecode_name, self.nand_inst[row_index].get_pin("B")) self.route_predecode_rail(predecode_name, self.nand_inst[row_index].get_pin("B"))
predecode_name = "predecode[{}]".format(index_C) predecode_name = "predecode_{}".format(index_C)
self.route_predecode_rail(predecode_name, self.nand_inst[row_index].get_pin("C")) self.route_predecode_rail(predecode_name, self.nand_inst[row_index].get_pin("C"))
row_index = row_index + 1 row_index = row_index + 1

View File

@ -25,9 +25,9 @@ class hierarchical_predecode(design.design):
def add_pins(self): def add_pins(self):
for k in range(self.number_of_inputs): for k in range(self.number_of_inputs):
self.add_pin("in[{0}]".format(k)) self.add_pin("in_{0}".format(k))
for i in range(self.number_of_outputs): for i in range(self.number_of_outputs):
self.add_pin("out[{0}]".format(i)) self.add_pin("out_{0}".format(i))
self.add_pin("vdd") self.add_pin("vdd")
self.add_pin("gnd") self.add_pin("gnd")
@ -67,7 +67,7 @@ class hierarchical_predecode(design.design):
def route_rails(self): def route_rails(self):
""" Create all of the rails for the inputs and vdd/gnd/inputs_bar/inputs """ """ Create all of the rails for the inputs and vdd/gnd/inputs_bar/inputs """
input_names = ["in[{}]".format(x) for x in range(self.number_of_inputs)] input_names = ["in_{}".format(x) for x in range(self.number_of_inputs)]
offset = vector(0.5*self.m2_width,2*self.m1_width) offset = vector(0.5*self.m2_width,2*self.m1_width)
self.input_rails = self.create_vertical_pin_bus(layer="metal2", self.input_rails = self.create_vertical_pin_bus(layer="metal2",
pitch=self.m2_pitch, pitch=self.m2_pitch,
@ -75,8 +75,8 @@ class hierarchical_predecode(design.design):
names=input_names, names=input_names,
length=self.height - 2*self.m1_width) length=self.height - 2*self.m1_width)
invert_names = ["Abar[{}]".format(x) for x in range(self.number_of_inputs)] invert_names = ["Abar_{}".format(x) for x in range(self.number_of_inputs)]
non_invert_names = ["A[{}]".format(x) for x in range(self.number_of_inputs)] non_invert_names = ["A_{}".format(x) for x in range(self.number_of_inputs)]
decode_names = invert_names + non_invert_names decode_names = invert_names + non_invert_names
offset = vector(self.x_off_inv_1 + self.inv.width + 2*self.m2_pitch, 2*self.m1_width) offset = vector(self.x_off_inv_1 + self.inv.width + 2*self.m2_pitch, 2*self.m1_width)
self.decode_rails = self.create_vertical_bus(layer="metal2", self.decode_rails = self.create_vertical_bus(layer="metal2",
@ -90,11 +90,11 @@ class hierarchical_predecode(design.design):
""" Create the input inverters to invert input signals for the decode stage. """ """ Create the input inverters to invert input signals for the decode stage. """
self.in_inst = [] self.in_inst = []
for inv_num in range(self.number_of_inputs): for inv_num in range(self.number_of_inputs):
name = "Xpre_inv[{0}]".format(inv_num) name = "Xpre_inv_{0}".format(inv_num)
self.in_inst.append(self.add_inst(name=name, self.in_inst.append(self.add_inst(name=name,
mod=self.inv)) mod=self.inv))
self.connect_inst(["in[{0}]".format(inv_num), self.connect_inst(["in_{0}".format(inv_num),
"inbar[{0}]".format(inv_num), "inbar_{0}".format(inv_num),
"vdd", "gnd"]) "vdd", "gnd"])
def place_input_inverters(self): def place_input_inverters(self):
@ -114,11 +114,11 @@ class hierarchical_predecode(design.design):
""" Create inverters for the inverted output decode signals. """ """ Create inverters for the inverted output decode signals. """
self.inv_inst = [] self.inv_inst = []
for inv_num in range(self.number_of_outputs): for inv_num in range(self.number_of_outputs):
name = "Xpre_nand_inv[{}]".format(inv_num) name = "Xpre_nand_inv_{}".format(inv_num)
self.inv_inst.append(self.add_inst(name=name, self.inv_inst.append(self.add_inst(name=name,
mod=self.inv)) mod=self.inv))
self.connect_inst(["Z[{}]".format(inv_num), self.connect_inst(["Z_{}".format(inv_num),
"out[{}]".format(inv_num), "out_{}".format(inv_num),
"vdd", "gnd"]) "vdd", "gnd"])
@ -140,7 +140,7 @@ class hierarchical_predecode(design.design):
self.nand_inst = [] self.nand_inst = []
for nand_input in range(self.number_of_outputs): for nand_input in range(self.number_of_outputs):
inout = str(self.number_of_inputs)+"x"+str(self.number_of_outputs) inout = str(self.number_of_inputs)+"x"+str(self.number_of_outputs)
name = "Xpre{0}_nand[{1}]".format(inout,nand_input) name = "Xpre{0}_nand_{1}".format(inout,nand_input)
self.nand_inst.append(self.add_inst(name=name, self.nand_inst.append(self.add_inst(name=name,
mod=self.nand)) mod=self.nand))
self.connect_inst(connections[nand_input]) self.connect_inst(connections[nand_input])
@ -175,8 +175,8 @@ class hierarchical_predecode(design.design):
# typically where the p/n devices are and there are no # typically where the p/n devices are and there are no
# pins in the nand gates. # pins in the nand gates.
y_offset = (num+self.number_of_inputs) * self.inv.height + contact.m1m2.width + self.m1_space y_offset = (num+self.number_of_inputs) * self.inv.height + contact.m1m2.width + self.m1_space
in_pin = "in[{}]".format(num) in_pin = "in_{}".format(num)
a_pin = "A[{}]".format(num) a_pin = "A_{}".format(num)
in_pos = vector(self.input_rails[in_pin].x,y_offset) in_pos = vector(self.input_rails[in_pin].x,y_offset)
a_pos = vector(self.decode_rails[a_pin].x,y_offset) a_pos = vector(self.decode_rails[a_pin].x,y_offset)
self.add_path("metal1",[in_pos, a_pos]) self.add_path("metal1",[in_pos, a_pos])
@ -202,7 +202,7 @@ class hierarchical_predecode(design.design):
self.add_path("metal1", [zr_pos, mid1_pos, mid2_pos, al_pos]) self.add_path("metal1", [zr_pos, mid1_pos, mid2_pos, al_pos])
z_pin = self.inv_inst[num].get_pin("Z") z_pin = self.inv_inst[num].get_pin("Z")
self.add_layout_pin(text="out[{}]".format(num), self.add_layout_pin(text="out_{}".format(num),
layer="metal1", layer="metal1",
offset=z_pin.ll(), offset=z_pin.ll(),
height=z_pin.height(), height=z_pin.height(),
@ -214,8 +214,8 @@ class hierarchical_predecode(design.design):
Route all conections of the inputs inverters [Inputs, outputs, vdd, gnd] Route all conections of the inputs inverters [Inputs, outputs, vdd, gnd]
""" """
for inv_num in range(self.number_of_inputs): for inv_num in range(self.number_of_inputs):
out_pin = "Abar[{}]".format(inv_num) out_pin = "Abar_{}".format(inv_num)
in_pin = "in[{}]".format(inv_num) in_pin = "in_{}".format(inv_num)
#add output so that it is just below the vdd or gnd rail #add output so that it is just below the vdd or gnd rail
# since this is where the p/n devices are and there are no # since this is where the p/n devices are and there are no

View File

@ -21,10 +21,10 @@ class hierarchical_predecode2x4(hierarchical_predecode):
self.create_modules() self.create_modules()
self.create_input_inverters() self.create_input_inverters()
self.create_output_inverters() self.create_output_inverters()
connections =[["inbar[0]", "inbar[1]", "Z[0]", "vdd", "gnd"], connections =[["inbar_0", "inbar_1", "Z_0", "vdd", "gnd"],
["in[0]", "inbar[1]", "Z[1]", "vdd", "gnd"], ["in_0", "inbar_1", "Z_1", "vdd", "gnd"],
["inbar[0]", "in[1]", "Z[2]", "vdd", "gnd"], ["inbar_0", "in_1", "Z_2", "vdd", "gnd"],
["in[0]", "in[1]", "Z[3]", "vdd", "gnd"]] ["in_0", "in_1", "Z_3", "vdd", "gnd"]]
self.create_nand_array(connections) self.create_nand_array(connections)
def create_layout(self): def create_layout(self):
@ -44,10 +44,10 @@ class hierarchical_predecode2x4(hierarchical_predecode):
def get_nand_input_line_combination(self): def get_nand_input_line_combination(self):
""" These are the decoder connections of the NAND gates to the A,B pins """ """ These are the decoder connections of the NAND gates to the A,B pins """
combination = [["Abar[0]", "Abar[1]"], combination = [["Abar_0", "Abar_1"],
["A[0]", "Abar[1]"], ["A_0", "Abar_1"],
["Abar[0]", "A[1]"], ["Abar_0", "A_1"],
["A[0]", "A[1]"]] ["A_0", "A_1"]]
return combination return combination

View File

@ -21,14 +21,14 @@ class hierarchical_predecode3x8(hierarchical_predecode):
self.create_modules() self.create_modules()
self.create_input_inverters() self.create_input_inverters()
self.create_output_inverters() self.create_output_inverters()
connections=[["inbar[0]", "inbar[1]", "inbar[2]", "Z[0]", "vdd", "gnd"], connections=[["inbar_0", "inbar_1", "inbar_2", "Z_0", "vdd", "gnd"],
["in[0]", "inbar[1]", "inbar[2]", "Z[1]", "vdd", "gnd"], ["in_0", "inbar_1", "inbar_2", "Z_1", "vdd", "gnd"],
["inbar[0]", "in[1]", "inbar[2]", "Z[2]", "vdd", "gnd"], ["inbar_0", "in_1", "inbar_2", "Z_2", "vdd", "gnd"],
["in[0]", "in[1]", "inbar[2]", "Z[3]", "vdd", "gnd"], ["in_0", "in_1", "inbar_2", "Z_3", "vdd", "gnd"],
["inbar[0]", "inbar[1]", "in[2]", "Z[4]", "vdd", "gnd"], ["inbar_0", "inbar_1", "in_2", "Z_4", "vdd", "gnd"],
["in[0]", "inbar[1]", "in[2]", "Z[5]", "vdd", "gnd"], ["in_0", "inbar_1", "in_2", "Z_5", "vdd", "gnd"],
["inbar[0]", "in[1]", "in[2]", "Z[6]", "vdd", "gnd"], ["inbar_0", "in_1", "in_2", "Z_6", "vdd", "gnd"],
["in[0]", "in[1]", "in[2]", "Z[7]", "vdd", "gnd"]] ["in_0", "in_1", "in_2", "Z_7", "vdd", "gnd"]]
self.create_nand_array(connections) self.create_nand_array(connections)
def create_layout(self): def create_layout(self):
@ -49,14 +49,14 @@ class hierarchical_predecode3x8(hierarchical_predecode):
def get_nand_input_line_combination(self): def get_nand_input_line_combination(self):
""" These are the decoder connections of the NAND gates to the A,B,C pins """ """ These are the decoder connections of the NAND gates to the A,B,C pins """
combination = [["Abar[0]", "Abar[1]", "Abar[2]"], combination = [["Abar_0", "Abar_1", "Abar_2"],
["A[0]", "Abar[1]", "Abar[2]"], ["A_0", "Abar_1", "Abar_2"],
["Abar[0]", "A[1]", "Abar[2]"], ["Abar_0", "A_1", "Abar_2"],
["A[0]", "A[1]", "Abar[2]"], ["A_0", "A_1", "Abar_2"],
["Abar[0]", "Abar[1]", "A[2]"], ["Abar_0", "Abar_1", "A_2"],
["A[0]", "Abar[1]", "A[2]"], ["A_0", "Abar_1", "A_2"],
["Abar[0]", "A[1]", "A[2]"], ["Abar_0", "A_1", "A_2"],
["A[0]", "A[1]", "A[2]"]] ["A_0", "A_1", "A_2"]]
return combination return combination

View File

@ -75,11 +75,11 @@ class multibank(design.design):
def add_pins(self): def add_pins(self):
""" Adding pins for Bank module""" """ Adding pins for Bank module"""
for i in range(self.word_size): for i in range(self.word_size):
self.add_pin("DOUT[{0}]".format(i),"OUT") self.add_pin("DOUT_{0}".format(i),"OUT")
for i in range(self.word_size): for i in range(self.word_size):
self.add_pin("BANK_DIN[{0}]".format(i),"IN") self.add_pin("BANK_DIN_{0}".format(i),"IN")
for i in range(self.addr_size): for i in range(self.addr_size):
self.add_pin("A[{0}]".format(i),"INPUT") self.add_pin("A_{0}".format(i),"INPUT")
# For more than one bank, we have a bank select and name # For more than one bank, we have a bank select and name
# the signals gated_*. # the signals gated_*.
@ -227,10 +227,10 @@ class multibank(design.design):
offset=vector(0,0)) offset=vector(0,0))
temp = [] temp = []
for i in range(self.num_cols): for i in range(self.num_cols):
temp.append("bl[{0}]".format(i)) temp.append("bl_{0}".format(i))
temp.append("br[{0}]".format(i)) temp.append("br_{0}".format(i))
for j in range(self.num_rows): for j in range(self.num_rows):
temp.append("wl[{0}]".format(j)) temp.append("wl_{0}".format(j))
temp.extend(["vdd", "gnd"]) temp.extend(["vdd", "gnd"])
self.connect_inst(temp) self.connect_inst(temp)
@ -246,8 +246,8 @@ class multibank(design.design):
offset=vector(0,y_offset)) offset=vector(0,y_offset))
temp = [] temp = []
for i in range(self.num_cols): for i in range(self.num_cols):
temp.append("bl[{0}]".format(i)) temp.append("bl_{0}".format(i))
temp.append("br[{0}]".format(i)) temp.append("br_{0}".format(i))
temp.extend([self.prefix+"clk_buf_bar", "vdd"]) temp.extend([self.prefix+"clk_buf_bar", "vdd"])
self.connect_inst(temp) self.connect_inst(temp)
@ -265,13 +265,13 @@ class multibank(design.design):
offset=vector(0,y_offset).scale(-1,-1)) offset=vector(0,y_offset).scale(-1,-1))
temp = [] temp = []
for i in range(self.num_cols): for i in range(self.num_cols):
temp.append("bl[{0}]".format(i)) temp.append("bl_{0}".format(i))
temp.append("br[{0}]".format(i)) temp.append("br_{0}".format(i))
for k in range(self.words_per_row): for k in range(self.words_per_row):
temp.append("sel[{0}]".format(k)) temp.append("sel_{0}".format(k))
for j in range(self.word_size): for j in range(self.word_size):
temp.append("bl_out[{0}]".format(j)) temp.append("bl_out_{0}".format(j))
temp.append("br_out[{0}]".format(j)) temp.append("br_out_{0}".format(j))
temp.append("gnd") temp.append("gnd")
self.connect_inst(temp) self.connect_inst(temp)
@ -284,13 +284,13 @@ class multibank(design.design):
offset=vector(0,y_offset).scale(-1,-1)) offset=vector(0,y_offset).scale(-1,-1))
temp = [] temp = []
for i in range(self.word_size): for i in range(self.word_size):
temp.append("sa_out[{0}]".format(i)) temp.append("sa_out_{0}".format(i))
if self.words_per_row == 1: if self.words_per_row == 1:
temp.append("bl[{0}]".format(i)) temp.append("bl_{0}".format(i))
temp.append("br[{0}]".format(i)) temp.append("br_{0}".format(i))
else: else:
temp.append("bl_out[{0}]".format(i)) temp.append("bl_out_{0}".format(i))
temp.append("br_out[{0}]".format(i)) temp.append("br_out_{0}".format(i))
temp.extend([self.prefix+"s_en", "vdd", "gnd"]) temp.extend([self.prefix+"s_en", "vdd", "gnd"])
self.connect_inst(temp) self.connect_inst(temp)
@ -306,14 +306,14 @@ class multibank(design.design):
temp = [] temp = []
for i in range(self.word_size): for i in range(self.word_size):
temp.append("BANK_DIN[{0}]".format(i)) temp.append("BANK_DIN_{0}".format(i))
for i in range(self.word_size): for i in range(self.word_size):
if (self.words_per_row == 1): if (self.words_per_row == 1):
temp.append("bl[{0}]".format(i)) temp.append("bl_{0}".format(i))
temp.append("br[{0}]".format(i)) temp.append("br_{0}".format(i))
else: else:
temp.append("bl_out[{0}]".format(i)) temp.append("bl_out_{0}".format(i))
temp.append("br_out[{0}]".format(i)) temp.append("br_out_{0}".format(i))
temp.extend([self.prefix+"w_en", "vdd", "gnd"]) temp.extend([self.prefix+"w_en", "vdd", "gnd"])
self.connect_inst(temp) self.connect_inst(temp)
@ -327,9 +327,9 @@ class multibank(design.design):
temp = [] temp = []
for i in range(self.word_size): for i in range(self.word_size):
temp.append("sa_out[{0}]".format(i)) temp.append("sa_out_{0}".format(i))
for i in range(self.word_size): for i in range(self.word_size):
temp.append("DOUT[{0}]".format(i)) temp.append("DOUT_{0}".format(i))
temp.extend([self.prefix+"tri_en", self.prefix+"tri_en_bar", "vdd", "gnd"]) temp.extend([self.prefix+"tri_en", self.prefix+"tri_en_bar", "vdd", "gnd"])
self.connect_inst(temp) self.connect_inst(temp)
@ -350,9 +350,9 @@ class multibank(design.design):
temp = [] temp = []
for i in range(self.row_addr_size): for i in range(self.row_addr_size):
temp.append("A[{0}]".format(i+self.col_addr_size)) temp.append("A_{0}".format(i+self.col_addr_size))
for j in range(self.num_rows): for j in range(self.num_rows):
temp.append("dec_out[{0}]".format(j)) temp.append("dec_out_{0}".format(j))
temp.extend(["vdd", "gnd"]) temp.extend(["vdd", "gnd"])
self.connect_inst(temp) self.connect_inst(temp)
@ -367,9 +367,9 @@ class multibank(design.design):
temp = [] temp = []
for i in range(self.num_rows): for i in range(self.num_rows):
temp.append("dec_out[{0}]".format(i)) temp.append("dec_out_{0}".format(i))
for i in range(self.num_rows): for i in range(self.num_rows):
temp.append("wl[{0}]".format(i)) temp.append("wl_{0}".format(i))
temp.append(self.prefix+"clk_buf") temp.append(self.prefix+"clk_buf")
temp.append("vdd") temp.append("vdd")
temp.append("gnd") temp.append("gnd")
@ -389,9 +389,9 @@ class multibank(design.design):
temp = [] temp = []
for i in range(self.col_addr_size): for i in range(self.col_addr_size):
temp.append("A[{0}]".format(i)) temp.append("A_{0}".format(i))
for j in range(self.num_col_addr_lines): for j in range(self.num_col_addr_lines):
temp.append("sel[{0}]".format(j)) temp.append("sel_{0}".format(j))
temp.extend(["vdd", "gnd"]) temp.extend(["vdd", "gnd"])
self.connect_inst(temp) self.connect_inst(temp)
@ -528,10 +528,10 @@ class multibank(design.design):
""" Routing of BL and BR between pre-charge and bitcell array """ """ Routing of BL and BR between pre-charge and bitcell array """
for i in range(self.num_cols): for i in range(self.num_cols):
precharge_bl = self.precharge_array_inst.get_pin("bl[{}]".format(i)).bc() precharge_bl = self.precharge_array_inst.get_pin("bl_{}".format(i)).bc()
precharge_br = self.precharge_array_inst.get_pin("br[{}]".format(i)).bc() precharge_br = self.precharge_array_inst.get_pin("br_{}".format(i)).bc()
bitcell_bl = self.bitcell_array_inst.get_pin("bl[{}]".format(i)).uc() bitcell_bl = self.bitcell_array_inst.get_pin("bl_{}".format(i)).uc()
bitcell_br = self.bitcell_array_inst.get_pin("br[{}]".format(i)).uc() bitcell_br = self.bitcell_array_inst.get_pin("br_{}".format(i)).uc()
yoffset = 0.5*(precharge_bl.y+bitcell_bl.y) yoffset = 0.5*(precharge_bl.y+bitcell_bl.y)
self.add_path("metal2",[precharge_bl, vector(precharge_bl.x,yoffset), self.add_path("metal2",[precharge_bl, vector(precharge_bl.x,yoffset),
@ -548,10 +548,10 @@ class multibank(design.design):
return return
for i in range(self.num_cols): for i in range(self.num_cols):
col_mux_bl = self.col_mux_array_inst.get_pin("bl[{}]".format(i)).uc() col_mux_bl = self.col_mux_array_inst.get_pin("bl_{}".format(i)).uc()
col_mux_br = self.col_mux_array_inst.get_pin("br[{}]".format(i)).uc() col_mux_br = self.col_mux_array_inst.get_pin("br_{}".format(i)).uc()
bitcell_bl = self.bitcell_array_inst.get_pin("bl[{}]".format(i)).bc() bitcell_bl = self.bitcell_array_inst.get_pin("bl_{}".format(i)).bc()
bitcell_br = self.bitcell_array_inst.get_pin("br[{}]".format(i)).bc() bitcell_br = self.bitcell_array_inst.get_pin("br_{}".format(i)).bc()
yoffset = 0.5*(col_mux_bl.y+bitcell_bl.y) yoffset = 0.5*(col_mux_bl.y+bitcell_bl.y)
self.add_path("metal2",[col_mux_bl, vector(col_mux_bl.x,yoffset), self.add_path("metal2",[col_mux_bl, vector(col_mux_bl.x,yoffset),
@ -563,17 +563,17 @@ class multibank(design.design):
""" Routing of BL and BR between sense_amp and column mux or bitcell array """ """ Routing of BL and BR between sense_amp and column mux or bitcell array """
for i in range(self.word_size): for i in range(self.word_size):
sense_amp_bl = self.sense_amp_array_inst.get_pin("bl[{}]".format(i)).uc() sense_amp_bl = self.sense_amp_array_inst.get_pin("bl_{}".format(i)).uc()
sense_amp_br = self.sense_amp_array_inst.get_pin("br[{}]".format(i)).uc() sense_amp_br = self.sense_amp_array_inst.get_pin("br_{}".format(i)).uc()
if self.col_addr_size>0: if self.col_addr_size>0:
# Sense amp is connected to the col mux # Sense amp is connected to the col mux
connect_bl = self.col_mux_array_inst.get_pin("bl_out[{}]".format(i)).bc() connect_bl = self.col_mux_array_inst.get_pin("bl_out_{}".format(i)).bc()
connect_br = self.col_mux_array_inst.get_pin("br_out[{}]".format(i)).bc() connect_br = self.col_mux_array_inst.get_pin("br_out_{}".format(i)).bc()
else: else:
# Sense amp is directly connected to the bitcell array # Sense amp is directly connected to the bitcell array
connect_bl = self.bitcell_array_inst.get_pin("bl[{}]".format(i)).bc() connect_bl = self.bitcell_array_inst.get_pin("bl_{}".format(i)).bc()
connect_br = self.bitcell_array_inst.get_pin("br[{}]".format(i)).bc() connect_br = self.bitcell_array_inst.get_pin("br_{}".format(i)).bc()
yoffset = 0.5*(sense_amp_bl.y+connect_bl.y) yoffset = 0.5*(sense_amp_bl.y+connect_bl.y)
@ -587,8 +587,8 @@ class multibank(design.design):
for i in range(self.word_size): for i in range(self.word_size):
# Connection of data_out of sense amp to data_in # Connection of data_out of sense amp to data_in
tri_gate_in = self.tri_gate_array_inst.get_pin("in[{}]".format(i)).lc() tri_gate_in = self.tri_gate_array_inst.get_pin("in_{}".format(i)).lc()
sa_data_out = self.sense_amp_array_inst.get_pin("data[{}]".format(i)).bc() sa_data_out = self.sense_amp_array_inst.get_pin("data_{}".format(i)).bc()
self.add_via_center(layers=("metal2", "via2", "metal3"), self.add_via_center(layers=("metal2", "via2", "metal3"),
offset=tri_gate_in) offset=tri_gate_in)
@ -599,8 +599,8 @@ class multibank(design.design):
def route_sense_amp_out(self): def route_sense_amp_out(self):
""" Add pins for the sense amp output """ """ Add pins for the sense amp output """
for i in range(self.word_size): for i in range(self.word_size):
data_pin = self.sense_amp_array_inst.get_pin("data[{}]".format(i)) data_pin = self.sense_amp_array_inst.get_pin("data_{}".format(i))
self.add_layout_pin_rect_center(text="DOUT[{}]".format(i), self.add_layout_pin_rect_center(text="DOUT_{}".format(i),
layer=data_pin.layer, layer=data_pin.layer,
offset=data_pin.center(), offset=data_pin.center(),
height=data_pin.height(), height=data_pin.height(),
@ -609,8 +609,8 @@ class multibank(design.design):
def route_tri_gate_out(self): def route_tri_gate_out(self):
""" Metal 3 routing of tri_gate output data """ """ Metal 3 routing of tri_gate output data """
for i in range(self.word_size): for i in range(self.word_size):
data_pin = self.tri_gate_array_inst.get_pin("out[{}]".format(i)) data_pin = self.tri_gate_array_inst.get_pin("out_{}".format(i))
self.add_layout_pin_rect_center(text="DOUT[{}]".format(i), self.add_layout_pin_rect_center(text="DOUT_{}".format(i),
layer=data_pin.layer, layer=data_pin.layer,
offset=data_pin.center(), offset=data_pin.center(),
height=data_pin.height(), height=data_pin.height(),
@ -623,8 +623,8 @@ class multibank(design.design):
# Create inputs for the row address lines # Create inputs for the row address lines
for i in range(self.row_addr_size): for i in range(self.row_addr_size):
addr_idx = i + self.col_addr_size addr_idx = i + self.col_addr_size
decoder_name = "A[{}]".format(i) decoder_name = "A_{}".format(i)
addr_name = "A[{}]".format(addr_idx) addr_name = "A_{}".format(addr_idx)
self.copy_layout_pin(self.row_decoder_inst, decoder_name, addr_name) self.copy_layout_pin(self.row_decoder_inst, decoder_name, addr_name)
@ -632,8 +632,8 @@ class multibank(design.design):
""" Connecting write driver """ """ Connecting write driver """
for i in range(self.word_size): for i in range(self.word_size):
data_name = "data[{}]".format(i) data_name = "data_{}".format(i)
din_name = "BANK_DIN[{}]".format(i) din_name = "BANK_DIN_{}".format(i)
self.copy_layout_pin(self.write_driver_array_inst, data_name, din_name) self.copy_layout_pin(self.write_driver_array_inst, data_name, din_name)
@ -644,15 +644,15 @@ class multibank(design.design):
# we don't care about bends after connecting to the input pin, so let the path code decide. # we don't care about bends after connecting to the input pin, so let the path code decide.
for i in range(self.num_rows): for i in range(self.num_rows):
# The pre/post is to access the pin from "outside" the cell to avoid DRCs # The pre/post is to access the pin from "outside" the cell to avoid DRCs
decoder_out_pos = self.row_decoder_inst.get_pin("decode[{}]".format(i)).rc() decoder_out_pos = self.row_decoder_inst.get_pin("decode_{}".format(i)).rc()
driver_in_pos = self.wordline_driver_inst.get_pin("in[{}]".format(i)).lc() driver_in_pos = self.wordline_driver_inst.get_pin("in_{}".format(i)).lc()
mid1 = decoder_out_pos.scale(0.5,1)+driver_in_pos.scale(0.5,0) mid1 = decoder_out_pos.scale(0.5,1)+driver_in_pos.scale(0.5,0)
mid2 = decoder_out_pos.scale(0.5,0)+driver_in_pos.scale(0.5,1) mid2 = decoder_out_pos.scale(0.5,0)+driver_in_pos.scale(0.5,1)
self.add_path("metal1", [decoder_out_pos, mid1, mid2, driver_in_pos]) self.add_path("metal1", [decoder_out_pos, mid1, mid2, driver_in_pos])
# The mid guarantees we exit the input cell to the right. # The mid guarantees we exit the input cell to the right.
driver_wl_pos = self.wordline_driver_inst.get_pin("wl[{}]".format(i)).rc() driver_wl_pos = self.wordline_driver_inst.get_pin("wl_{}".format(i)).rc()
bitcell_wl_pos = self.bitcell_array_inst.get_pin("wl[{}]".format(i)).lc() bitcell_wl_pos = self.bitcell_array_inst.get_pin("wl_{}".format(i)).lc()
mid1 = driver_wl_pos.scale(0.5,1)+bitcell_wl_pos.scale(0.5,0) mid1 = driver_wl_pos.scale(0.5,1)+bitcell_wl_pos.scale(0.5,0)
mid2 = driver_wl_pos.scale(0.5,0)+bitcell_wl_pos.scale(0.5,1) mid2 = driver_wl_pos.scale(0.5,0)+bitcell_wl_pos.scale(0.5,1)
self.add_path("metal1", [driver_wl_pos, mid1, mid2, bitcell_wl_pos]) self.add_path("metal1", [driver_wl_pos, mid1, mid2, bitcell_wl_pos])
@ -677,20 +677,20 @@ class multibank(design.design):
elif self.col_addr_size > 1: elif self.col_addr_size > 1:
decode_names = [] decode_names = []
for i in range(self.num_col_addr_lines): for i in range(self.num_col_addr_lines):
decode_names.append("out[{}]".format(i)) decode_names.append("out_{}".format(i))
for i in range(self.col_addr_size): for i in range(self.col_addr_size):
decoder_name = "in[{}]".format(i) decoder_name = "in_{}".format(i)
addr_name = "A[{}]".format(i) addr_name = "A_{}".format(i)
self.copy_layout_pin(self.col_decoder_inst, decoder_name, addr_name) self.copy_layout_pin(self.col_decoder_inst, decoder_name, addr_name)
# This will do a quick "river route" on two layers. # This will do a quick "river route" on two layers.
# When above the top select line it will offset "inward" again to prevent conflicts. # When above the top select line it will offset "inward" again to prevent conflicts.
# This could be done on a single layer, but we follow preferred direction rules for later routing. # This could be done on a single layer, but we follow preferred direction rules for later routing.
top_y_offset = self.col_mux_array_inst.get_pin("sel[{}]".format(self.num_col_addr_lines-1)).cy() top_y_offset = self.col_mux_array_inst.get_pin("sel_{}".format(self.num_col_addr_lines-1)).cy()
for (decode_name,i) in zip(decode_names,range(self.num_col_addr_lines)): for (decode_name,i) in zip(decode_names,range(self.num_col_addr_lines)):
mux_name = "sel[{}]".format(i) mux_name = "sel_{}".format(i)
mux_addr_pos = self.col_mux_array_inst.get_pin(mux_name).lc() mux_addr_pos = self.col_mux_array_inst.get_pin(mux_name).lc()
decode_out_pos = self.col_decoder_inst.get_pin(decode_name).center() decode_out_pos = self.col_decoder_inst.get_pin(decode_name).center()
@ -716,7 +716,7 @@ class multibank(design.design):
""" """
# Add the wordline names # Add the wordline names
for i in range(self.num_rows): for i in range(self.num_rows):
wl_name = "wl[{}]".format(i) wl_name = "wl_{}".format(i)
wl_pin = self.bitcell_array_inst.get_pin(wl_name) wl_pin = self.bitcell_array_inst.get_pin(wl_name)
self.add_label(text=wl_name, self.add_label(text=wl_name,
layer="metal1", layer="metal1",
@ -724,8 +724,8 @@ class multibank(design.design):
# Add the bitline names # Add the bitline names
for i in range(self.num_cols): for i in range(self.num_cols):
bl_name = "bl[{}]".format(i) bl_name = "bl_{}".format(i)
br_name = "br[{}]".format(i) br_name = "br_{}".format(i)
bl_pin = self.bitcell_array_inst.get_pin(bl_name) bl_pin = self.bitcell_array_inst.get_pin(bl_name)
br_pin = self.bitcell_array_inst.get_pin(br_name) br_pin = self.bitcell_array_inst.get_pin(br_name)
self.add_label(text=bl_name, self.add_label(text=bl_name,
@ -737,16 +737,16 @@ class multibank(design.design):
# # Add the data output names to the sense amp output # # Add the data output names to the sense amp output
# for i in range(self.word_size): # for i in range(self.word_size):
# data_name = "data[{}]".format(i) # data_name = "data_{}".format(i)
# data_pin = self.sense_amp_array_inst.get_pin(data_name) # data_pin = self.sense_amp_array_inst.get_pin(data_name)
# self.add_label(text="sa_out[{}]".format(i), # self.add_label(text="sa_out_{}".format(i),
# layer="metal2", # layer="metal2",
# offset=data_pin.center()) # offset=data_pin.center())
# Add labels on the decoder # Add labels on the decoder
for i in range(self.word_size): for i in range(self.word_size):
data_name = "dec_out[{}]".format(i) data_name = "dec_out_{}".format(i)
pin_name = "in[{}]".format(i) pin_name = "in_{}".format(i)
data_pin = self.wordline_driver_inst.get_pin(pin_name) data_pin = self.wordline_driver_inst.get_pin(pin_name)
self.add_label(text=data_name, self.add_label(text=data_name,
layer="metal1", layer="metal1",

View File

@ -31,8 +31,8 @@ class precharge_array(design.design):
def add_pins(self): def add_pins(self):
"""Adds pins for spice file""" """Adds pins for spice file"""
for i in range(self.columns): for i in range(self.columns):
self.add_pin("bl[{0}]".format(i)) self.add_pin("bl_{0}".format(i))
self.add_pin("br[{0}]".format(i)) self.add_pin("br_{0}".format(i))
self.add_pin("en") self.add_pin("en")
self.add_pin("vdd") self.add_pin("vdd")
@ -71,13 +71,13 @@ class precharge_array(design.design):
for i in range(len(self.local_insts)): for i in range(len(self.local_insts)):
inst = self.local_insts[i] inst = self.local_insts[i]
bl_pin = inst.get_pin("bl") bl_pin = inst.get_pin("bl")
self.add_layout_pin(text="bl[{0}]".format(i), self.add_layout_pin(text="bl_{0}".format(i),
layer="metal2", layer="metal2",
offset=bl_pin.ll(), offset=bl_pin.ll(),
width=drc["minwidth_metal2"], width=drc["minwidth_metal2"],
height=bl_pin.height()) height=bl_pin.height())
br_pin = inst.get_pin("br") br_pin = inst.get_pin("br")
self.add_layout_pin(text="br[{0}]".format(i), self.add_layout_pin(text="br_{0}".format(i),
layer="metal2", layer="metal2",
offset=br_pin.ll(), offset=br_pin.ll(),
width=drc["minwidth_metal2"], width=drc["minwidth_metal2"],
@ -94,7 +94,7 @@ class precharge_array(design.design):
mod=self.pc_cell, mod=self.pc_cell,
offset=offset) offset=offset)
self.local_insts.append(inst) self.local_insts.append(inst)
self.connect_inst(["bl[{0}]".format(i), "br[{0}]".format(i), "en", "vdd"]) self.connect_inst(["bl_{0}".format(i), "br_{0}".format(i), "en", "vdd"])
def place_insts(self): def place_insts(self):

View File

@ -111,12 +111,12 @@ class replica_bitline(design.design):
# This is the threshold detect inverter on the output of the RBL # This is the threshold detect inverter on the output of the RBL
self.rbl_inv_inst=self.add_inst(name="rbl_inv", self.rbl_inv_inst=self.add_inst(name="rbl_inv",
mod=self.inv) mod=self.inv)
self.connect_inst(["bl0[0]", "out", "vdd", "gnd"]) self.connect_inst(["bl0_0", "out", "vdd", "gnd"])
self.tx_inst=self.add_inst(name="rbl_access_tx", self.tx_inst=self.add_inst(name="rbl_access_tx",
mod=self.access_tx) mod=self.access_tx)
# D, G, S, B # D, G, S, B
self.connect_inst(["vdd", "delayed_en", "bl0[0]", "vdd"]) self.connect_inst(["vdd", "delayed_en", "bl0_0", "vdd"])
# add the well and poly contact # add the well and poly contact
self.dc_inst=self.add_inst(name="delay_chain", self.dc_inst=self.add_inst(name="delay_chain",
@ -127,22 +127,22 @@ class replica_bitline(design.design):
mod=self.replica_bitcell) mod=self.replica_bitcell)
temp = [] temp = []
for port in range(self.total_ports): for port in range(self.total_ports):
temp.append("bl{}[0]".format(port)) temp.append("bl{}_0".format(port))
temp.append("br{}[0]".format(port)) temp.append("br{}_0".format(port))
for port in range(self.total_ports): for port in range(self.total_ports):
temp.append("delayed_en") temp.append("delayed_en")
temp.append("vdd") temp.append("vdd")
temp.append("gnd") temp.append("gnd")
self.connect_inst(temp) self.connect_inst(temp)
#self.connect_inst(["bl[0]", "br[0]", "delayed_en", "vdd", "gnd"]) #self.connect_inst(["bl_0", "br_0", "delayed_en", "vdd", "gnd"])
self.rbl_inst=self.add_inst(name="load", self.rbl_inst=self.add_inst(name="load",
mod=self.rbl) mod=self.rbl)
temp = [] temp = []
for port in range(self.total_ports): for port in range(self.total_ports):
temp.append("bl{}[0]".format(port)) temp.append("bl{}_0".format(port))
temp.append("br{}[0]".format(port)) temp.append("br{}_0".format(port))
for wl in range(self.bitcell_loads): for wl in range(self.bitcell_loads):
for port in range(self.total_ports): for port in range(self.total_ports):
temp.append("gnd") temp.append("gnd")
@ -180,7 +180,7 @@ class replica_bitline(design.design):
""" Connect the RBL word lines to gnd """ """ Connect the RBL word lines to gnd """
# Connect the WL and gnd pins directly to the center and right gnd rails # Connect the WL and gnd pins directly to the center and right gnd rails
for row in range(self.bitcell_loads): for row in range(self.bitcell_loads):
wl = self.wl_list[0]+"[{}]".format(row) wl = self.wl_list[0]+"_{}".format(row)
pin = self.rbl_inst.get_pin(wl) pin = self.rbl_inst.get_pin(wl)
# Route the connection to the right so that it doesn't interfere with the cells # Route the connection to the right so that it doesn't interfere with the cells
@ -199,7 +199,7 @@ class replica_bitline(design.design):
self.add_power_pin("gnd", pin_extension2) self.add_power_pin("gnd", pin_extension2)
# for multiport, need to short wordlines to each other so they all connect to gnd # for multiport, need to short wordlines to each other so they all connect to gnd
wl_last = self.wl_list[self.total_ports-1]+"[{}]".format(row) wl_last = self.wl_list[self.total_ports-1]+"_{}".format(row)
pin_last = self.rbl_inst.get_pin(wl_last) pin_last = self.rbl_inst.get_pin(wl_last)
correct = vector(0.5*drc["minwidth_metal1"], 0) correct = vector(0.5*drc["minwidth_metal1"], 0)
@ -414,7 +414,7 @@ class replica_bitline(design.design):
# Connect the WL and gnd pins directly to the center and right gnd rails # Connect the WL and gnd pins directly to the center and right gnd rails
for row in range(self.bitcell_loads): for row in range(self.bitcell_loads):
wl = self.wl_list[0]+"[{}]".format(row) wl = self.wl_list[0]+"_{}".format(row)
pin = self.rbl_inst.get_pin(wl) pin = self.rbl_inst.get_pin(wl)
if pin.layer != "metal1": if pin.layer != "metal1":
continue continue

View File

@ -43,9 +43,9 @@ class sense_amp_array(design.design):
def add_pins(self): def add_pins(self):
for i in range(0,self.word_size): for i in range(0,self.word_size):
self.add_pin("data[{0}]".format(i)) self.add_pin("data_{0}".format(i))
self.add_pin("bl[{0}]".format(i)) self.add_pin("bl_{0}".format(i))
self.add_pin("br[{0}]".format(i)) self.add_pin("br_{0}".format(i))
self.add_pin("en") self.add_pin("en")
self.add_pin("vdd") self.add_pin("vdd")
self.add_pin("gnd") self.add_pin("gnd")
@ -70,9 +70,9 @@ class sense_amp_array(design.design):
name = "sa_d{0}".format(i) name = "sa_d{0}".format(i)
self.local_insts.append(self.add_inst(name=name, self.local_insts.append(self.add_inst(name=name,
mod=self.amp)) mod=self.amp))
self.connect_inst(["bl[{0}]".format(i), self.connect_inst(["bl_{0}".format(i),
"br[{0}]".format(i), "br_{0}".format(i),
"data[{0}]".format(i), "data_{0}".format(i),
"en", "vdd", "gnd"]) "en", "vdd", "gnd"])
def place_sense_amp_array(self): def place_sense_amp_array(self):
@ -107,18 +107,18 @@ class sense_amp_array(design.design):
br_pin = inst.get_pin("br") br_pin = inst.get_pin("br")
dout_pin = inst.get_pin("dout") dout_pin = inst.get_pin("dout")
self.add_layout_pin(text="bl[{0}]".format(i), self.add_layout_pin(text="bl_{0}".format(i),
layer="metal2", layer="metal2",
offset=bl_pin.ll(), offset=bl_pin.ll(),
width=bl_pin.width(), width=bl_pin.width(),
height=bl_pin.height()) height=bl_pin.height())
self.add_layout_pin(text="br[{0}]".format(i), self.add_layout_pin(text="br_{0}".format(i),
layer="metal2", layer="metal2",
offset=br_pin.ll(), offset=br_pin.ll(),
width=br_pin.width(), width=br_pin.width(),
height=br_pin.height()) height=br_pin.height())
self.add_layout_pin(text="data[{0}]".format(i), self.add_layout_pin(text="data_{0}".format(i),
layer="metal2", layer="metal2",
offset=dout_pin.ll(), offset=dout_pin.ll(),
width=dout_pin.width(), width=dout_pin.width(),

View File

@ -50,13 +50,13 @@ class single_level_column_mux_array(design.design):
def add_pins(self): def add_pins(self):
for i in range(self.columns): for i in range(self.columns):
self.add_pin("bl[{}]".format(i)) self.add_pin("bl_{}".format(i))
self.add_pin("br[{}]".format(i)) self.add_pin("br_{}".format(i))
for i in range(self.words_per_row): for i in range(self.words_per_row):
self.add_pin("sel[{}]".format(i)) self.add_pin("sel_{}".format(i))
for i in range(self.word_size): for i in range(self.word_size):
self.add_pin("bl_out[{}]".format(i)) self.add_pin("bl_out_{}".format(i))
self.add_pin("br_out[{}]".format(i)) self.add_pin("br_out_{}".format(i))
self.add_pin("gnd") self.add_pin("gnd")
@ -83,11 +83,11 @@ class single_level_column_mux_array(design.design):
self.mux_inst.append(self.add_inst(name=name, self.mux_inst.append(self.add_inst(name=name,
mod=self.mux)) mod=self.mux))
self.connect_inst(["bl[{}]".format(col_num), self.connect_inst(["bl_{}".format(col_num),
"br[{}]".format(col_num), "br_{}".format(col_num),
"bl_out[{}]".format(int(col_num/self.words_per_row)), "bl_out_{}".format(int(col_num/self.words_per_row)),
"br_out[{}]".format(int(col_num/self.words_per_row)), "br_out_{}".format(int(col_num/self.words_per_row)),
"sel[{}]".format(col_num % self.words_per_row), "sel_{}".format(col_num % self.words_per_row),
"gnd"]) "gnd"])
def place_array(self): def place_array(self):
@ -104,13 +104,13 @@ class single_level_column_mux_array(design.design):
for col_num in range(self.columns): for col_num in range(self.columns):
mux_inst = self.mux_inst[col_num] mux_inst = self.mux_inst[col_num]
offset = mux_inst.get_pin("bl").ll() offset = mux_inst.get_pin("bl").ll()
self.add_layout_pin(text="bl[{}]".format(col_num), self.add_layout_pin(text="bl_{}".format(col_num),
layer="metal2", layer="metal2",
offset=offset, offset=offset,
height=self.height-offset.y) height=self.height-offset.y)
offset = mux_inst.get_pin("br").ll() offset = mux_inst.get_pin("br").ll()
self.add_layout_pin(text="br[{}]".format(col_num), self.add_layout_pin(text="br_{}".format(col_num),
layer="metal2", layer="metal2",
offset=offset, offset=offset,
height=self.height-offset.y) height=self.height-offset.y)
@ -128,7 +128,7 @@ class single_level_column_mux_array(design.design):
""" Create address input rails on M1 below the mux transistors """ """ Create address input rails on M1 below the mux transistors """
for j in range(self.words_per_row): for j in range(self.words_per_row):
offset = vector(0, self.route_height + (j-self.words_per_row)*self.m1_pitch) offset = vector(0, self.route_height + (j-self.words_per_row)*self.m1_pitch)
self.add_layout_pin(text="sel[{}]".format(j), self.add_layout_pin(text="sel_{}".format(j),
layer="metal1", layer="metal1",
offset=offset, offset=offset,
width=self.mux.width * self.columns, width=self.mux.width * self.columns,
@ -144,9 +144,9 @@ class single_level_column_mux_array(design.design):
# Add the column x offset to find the right select bit # Add the column x offset to find the right select bit
gate_offset = self.mux_inst[col].get_pin("sel").bc() gate_offset = self.mux_inst[col].get_pin("sel").bc()
# height to connect the gate to the correct horizontal row # height to connect the gate to the correct horizontal row
sel_height = self.get_pin("sel[{}]".format(sel_index)).by() sel_height = self.get_pin("sel_{}".format(sel_index)).by()
# use the y offset from the sel pin and the x offset from the gate # use the y offset from the sel pin and the x offset from the gate
offset = vector(gate_offset.x,self.get_pin("sel[{}]".format(sel_index)).cy()) offset = vector(gate_offset.x,self.get_pin("sel_{}".format(sel_index)).cy())
# Add the poly contact with a shift to account for the rotation # Add the poly contact with a shift to account for the rotation
self.add_via_center(layers=("metal1", "contact", "poly"), self.add_via_center(layers=("metal1", "contact", "poly"),
offset=offset, offset=offset,
@ -178,12 +178,12 @@ class single_level_column_mux_array(design.design):
# Extend the bitline output rails and gnd downward on the first bit of each n-way mux # Extend the bitline output rails and gnd downward on the first bit of each n-way mux
self.add_layout_pin(text="bl_out[{}]".format(int(j/self.words_per_row)), self.add_layout_pin(text="bl_out_{}".format(int(j/self.words_per_row)),
layer="metal2", layer="metal2",
offset=bl_out_offset.scale(1,0), offset=bl_out_offset.scale(1,0),
width=drc['minwidth_metal2'], width=drc['minwidth_metal2'],
height=self.route_height) height=self.route_height)
self.add_layout_pin(text="br_out[{}]".format(int(j/self.words_per_row)), self.add_layout_pin(text="br_out_{}".format(int(j/self.words_per_row)),
layer="metal2", layer="metal2",
offset=br_out_offset.scale(1,0), offset=br_out_offset.scale(1,0),
width=drc['minwidth_metal2'], width=drc['minwidth_metal2'],

View File

@ -45,9 +45,9 @@ class tri_gate_array(design.design):
def add_pins(self): def add_pins(self):
"""create the name of pins depend on the word size""" """create the name of pins depend on the word size"""
for i in range(self.word_size): for i in range(self.word_size):
self.add_pin("in[{0}]".format(i)) self.add_pin("in_{0}".format(i))
for i in range(self.word_size): for i in range(self.word_size):
self.add_pin("out[{0}]".format(i)) self.add_pin("out_{0}".format(i))
for pin in ["en", "en_bar", "vdd", "gnd"]: for pin in ["en", "en_bar", "vdd", "gnd"]:
self.add_pin(pin) self.add_pin(pin)
@ -59,8 +59,8 @@ class tri_gate_array(design.design):
self.tri_inst[i]=self.add_inst(name=name, self.tri_inst[i]=self.add_inst(name=name,
mod=self.tri) mod=self.tri)
index = int(i/self.words_per_row) index = int(i/self.words_per_row)
self.connect_inst(["in[{0}]".format(index), self.connect_inst(["in_{0}".format(index),
"out[{0}]".format(index), "out_{0}".format(index),
"en", "en_bar", "vdd", "gnd"]) "en", "en_bar", "vdd", "gnd"])
def place_array(self): def place_array(self):
@ -76,14 +76,14 @@ class tri_gate_array(design.design):
index = int(i/self.words_per_row) index = int(i/self.words_per_row)
in_pin = self.tri_inst[i].get_pin("in") in_pin = self.tri_inst[i].get_pin("in")
self.add_layout_pin(text="in[{0}]".format(index), self.add_layout_pin(text="in_{0}".format(index),
layer="metal2", layer="metal2",
offset=in_pin.ll(), offset=in_pin.ll(),
width=in_pin.width(), width=in_pin.width(),
height=in_pin.height()) height=in_pin.height())
out_pin = self.tri_inst[i].get_pin("out") out_pin = self.tri_inst[i].get_pin("out")
self.add_layout_pin(text="out[{0}]".format(index), self.add_layout_pin(text="out_{0}".format(index),
layer="metal2", layer="metal2",
offset=out_pin.ll(), offset=out_pin.ll(),
width=out_pin.width(), width=out_pin.width(),

View File

@ -40,10 +40,10 @@ class wordline_driver(design.design):
def add_pins(self): def add_pins(self):
# inputs to wordline_driver. # inputs to wordline_driver.
for i in range(self.rows): for i in range(self.rows):
self.add_pin("in[{0}]".format(i)) self.add_pin("in_{0}".format(i))
# Outputs from wordline_driver. # Outputs from wordline_driver.
for i in range(self.rows): for i in range(self.rows):
self.add_pin("wl[{0}]".format(i)) self.add_pin("wl_{0}".format(i))
self.add_pin("en") self.add_pin("en")
self.add_pin("vdd") self.add_pin("vdd")
self.add_pin("gnd") self.add_pin("gnd")
@ -107,20 +107,20 @@ class wordline_driver(design.design):
self.inv1_inst.append(self.add_inst(name=name_inv1, self.inv1_inst.append(self.add_inst(name=name_inv1,
mod=self.inv_no_output)) mod=self.inv_no_output))
self.connect_inst(["en", self.connect_inst(["en",
"en_bar[{0}]".format(row), "en_bar_{0}".format(row),
"vdd", "gnd"]) "vdd", "gnd"])
# add nand 2 # add nand 2
self.nand_inst.append(self.add_inst(name=name_nand, self.nand_inst.append(self.add_inst(name=name_nand,
mod=self.nand2)) mod=self.nand2))
self.connect_inst(["en_bar[{0}]".format(row), self.connect_inst(["en_bar_{0}".format(row),
"in[{0}]".format(row), "in_{0}".format(row),
"wl_bar[{0}]".format(row), "wl_bar_{0}".format(row),
"vdd", "gnd"]) "vdd", "gnd"])
# add inv2 # add inv2
self.inv2_inst.append(self.add_inst(name=name_inv2, self.inv2_inst.append(self.add_inst(name=name_inv2,
mod=self.inv)) mod=self.inv))
self.connect_inst(["wl_bar[{0}]".format(row), self.connect_inst(["wl_bar_{0}".format(row),
"wl[{0}]".format(row), "wl_{0}".format(row),
"vdd", "gnd"]) "vdd", "gnd"])
@ -205,7 +205,7 @@ class wordline_driver(design.design):
input_offset = vector(0,b_pos.y + up_or_down) input_offset = vector(0,b_pos.y + up_or_down)
mid_via_offset = vector(clk_offset.x,input_offset.y) + vector(0.5*self.m2_width+self.m2_space+0.5*contact.m1m2.width,0) mid_via_offset = vector(clk_offset.x,input_offset.y) + vector(0.5*self.m2_width+self.m2_space+0.5*contact.m1m2.width,0)
# must under the clk line in M1 # must under the clk line in M1
self.add_layout_pin_segment_center(text="in[{0}]".format(row), self.add_layout_pin_segment_center(text="in_{0}".format(row),
layer="metal1", layer="metal1",
start=input_offset, start=input_offset,
end=mid_via_offset) end=mid_via_offset)
@ -221,7 +221,7 @@ class wordline_driver(design.design):
# output each WL on the right # output each WL on the right
wl_offset = inv2_inst.get_pin("Z").rc() wl_offset = inv2_inst.get_pin("Z").rc()
self.add_layout_pin_segment_center(text="wl[{0}]".format(row), self.add_layout_pin_segment_center(text="wl_{0}".format(row),
layer="metal1", layer="metal1",
start=wl_offset, start=wl_offset,
end=wl_offset-vector(self.m1_width,0)) end=wl_offset-vector(self.m1_width,0))

View File

@ -44,10 +44,10 @@ class write_driver_array(design.design):
def add_pins(self): def add_pins(self):
for i in range(self.word_size): for i in range(self.word_size):
self.add_pin("data[{0}]".format(i)) self.add_pin("data_{0}".format(i))
for i in range(self.word_size): for i in range(self.word_size):
self.add_pin("bl[{0}]".format(i)) self.add_pin("bl_{0}".format(i))
self.add_pin("br[{0}]".format(i)) self.add_pin("br_{0}".format(i))
self.add_pin("en") self.add_pin("en")
self.add_pin("vdd") self.add_pin("vdd")
self.add_pin("gnd") self.add_pin("gnd")
@ -73,9 +73,9 @@ class write_driver_array(design.design):
self.driver_insts[index]=self.add_inst(name=name, self.driver_insts[index]=self.add_inst(name=name,
mod=self.driver) mod=self.driver)
self.connect_inst(["data[{0}]".format(index), self.connect_inst(["data_{0}".format(index),
"bl[{0}]".format(index), "bl_{0}".format(index),
"br[{0}]".format(index), "br_{0}".format(index),
"en", "vdd", "gnd"]) "en", "vdd", "gnd"])
@ -94,20 +94,20 @@ class write_driver_array(design.design):
def add_layout_pins(self): def add_layout_pins(self):
for i in range(self.word_size): for i in range(self.word_size):
din_pin = self.driver_insts[i].get_pin("din") din_pin = self.driver_insts[i].get_pin("din")
self.add_layout_pin(text="data[{0}]".format(i), self.add_layout_pin(text="data_{0}".format(i),
layer="metal2", layer="metal2",
offset=din_pin.ll(), offset=din_pin.ll(),
width=din_pin.width(), width=din_pin.width(),
height=din_pin.height()) height=din_pin.height())
bl_pin = self.driver_insts[i].get_pin("bl") bl_pin = self.driver_insts[i].get_pin("bl")
self.add_layout_pin(text="bl[{0}]".format(i), self.add_layout_pin(text="bl_{0}".format(i),
layer="metal2", layer="metal2",
offset=bl_pin.ll(), offset=bl_pin.ll(),
width=bl_pin.width(), width=bl_pin.width(),
height=bl_pin.height()) height=bl_pin.height())
br_pin = self.driver_insts[i].get_pin("br") br_pin = self.driver_insts[i].get_pin("br")
self.add_layout_pin(text="br[{0}]".format(i), self.add_layout_pin(text="br_{0}".format(i),
layer="metal2", layer="metal2",
offset=br_pin.ll(), offset=br_pin.ll(),
width=br_pin.width(), width=br_pin.width(),

View File

@ -100,17 +100,17 @@ class sram_1bank(sram_base):
self.copy_layout_pin(self.control_logic_inst[port], signal, signal+"{}".format(port)) self.copy_layout_pin(self.control_logic_inst[port], signal, signal+"{}".format(port))
for bit in range(self.word_size): for bit in range(self.word_size):
self.copy_layout_pin(self.bank_inst, "dout{0}[{1}]".format(port,bit), "DOUT{0}[{1}]".format(port,bit)) self.copy_layout_pin(self.bank_inst, "dout{0}_{1}".format(port,bit), "DOUT{0}[{1}]".format(port,bit))
# Lower address bits # Lower address bits
for bit in range(self.col_addr_size): for bit in range(self.col_addr_size):
self.copy_layout_pin(self.col_addr_dff_inst[port], "din[{}]".format(bit),"ADDR{0}[{1}]".format(port,bit)) self.copy_layout_pin(self.col_addr_dff_inst[port], "din_{}".format(bit),"ADDR{0}[{1}]".format(port,bit))
# Upper address bits # Upper address bits
for bit in range(self.row_addr_size): for bit in range(self.row_addr_size):
self.copy_layout_pin(self.row_addr_dff_inst[port], "din[{}]".format(bit),"ADDR{0}[{1}]".format(port,bit+self.col_addr_size)) self.copy_layout_pin(self.row_addr_dff_inst[port], "din_{}".format(bit),"ADDR{0}[{1}]".format(port,bit+self.col_addr_size))
for bit in range(self.word_size): for bit in range(self.word_size):
self.copy_layout_pin(self.data_dff_inst[port], "din[{}]".format(bit), "DIN{0}[{1}]".format(port,bit)) self.copy_layout_pin(self.data_dff_inst[port], "din_{}".format(bit), "DIN{0}[{1}]".format(port,bit))
def route(self): def route(self):
""" Route a single bank SRAM """ """ Route a single bank SRAM """
@ -186,8 +186,8 @@ class sram_1bank(sram_base):
""" Connect the output of the row flops to the bank pins """ """ Connect the output of the row flops to the bank pins """
for port in range(self.total_ports): for port in range(self.total_ports):
for bit in range(self.row_addr_size): for bit in range(self.row_addr_size):
flop_name = "dout[{}]".format(bit) flop_name = "dout_{}".format(bit)
bank_name = "addr{0}[{1}]".format(port,bit+self.col_addr_size) bank_name = "addr{0}_{1}".format(port,bit+self.col_addr_size)
flop_pin = self.row_addr_dff_inst[port].get_pin(flop_name) flop_pin = self.row_addr_dff_inst[port].get_pin(flop_name)
bank_pin = self.bank_inst.get_pin(bank_name) bank_pin = self.bank_inst.get_pin(bank_name)
flop_pos = flop_pin.center() flop_pos = flop_pin.center()
@ -201,18 +201,18 @@ class sram_1bank(sram_base):
def route_col_addr_dff(self): def route_col_addr_dff(self):
""" Connect the output of the row flops to the bank pins """ """ Connect the output of the row flops to the bank pins """
for port in range(self.total_ports): for port in range(self.total_ports):
bus_names = ["addr[{}]".format(x) for x in range(self.col_addr_size)] bus_names = ["addr_{}".format(x) for x in range(self.col_addr_size)]
col_addr_bus_offsets = self.create_horizontal_bus(layer="metal1", col_addr_bus_offsets = self.create_horizontal_bus(layer="metal1",
pitch=self.m1_pitch, pitch=self.m1_pitch,
offset=self.col_addr_dff_inst[port].ul() + vector(0, self.m1_pitch), offset=self.col_addr_dff_inst[port].ul() + vector(0, self.m1_pitch),
names=bus_names, names=bus_names,
length=self.col_addr_dff_inst[port].width) length=self.col_addr_dff_inst[port].width)
dff_names = ["dout[{}]".format(x) for x in range(self.col_addr_size)] dff_names = ["dout_{}".format(x) for x in range(self.col_addr_size)]
data_dff_map = zip(dff_names, bus_names) data_dff_map = zip(dff_names, bus_names)
self.connect_horizontal_bus(data_dff_map, self.col_addr_dff_inst[port], col_addr_bus_offsets) self.connect_horizontal_bus(data_dff_map, self.col_addr_dff_inst[port], col_addr_bus_offsets)
bank_names = ["addr{0}[{1}]".format(port,x) for x in range(self.col_addr_size)] bank_names = ["addr{0}_{1}".format(port,x) for x in range(self.col_addr_size)]
data_bank_map = zip(bank_names, bus_names) data_bank_map = zip(bank_names, bus_names)
self.connect_horizontal_bus(data_bank_map, self.bank_inst, col_addr_bus_offsets) self.connect_horizontal_bus(data_bank_map, self.bank_inst, col_addr_bus_offsets)
@ -223,8 +223,8 @@ class sram_1bank(sram_base):
for port in range(self.total_write): for port in range(self.total_write):
offset = self.data_dff_inst[port].ul() + vector(0, self.m1_pitch) offset = self.data_dff_inst[port].ul() + vector(0, self.m1_pitch)
dff_names = ["dout[{}]".format(x) for x in range(self.word_size)] dff_names = ["dout_{}".format(x) for x in range(self.word_size)]
bank_names = ["din{0}[{1}]".format(port,x) for x in range(self.word_size)] bank_names = ["din{0}_{1}".format(port,x) for x in range(self.word_size)]
route_map = list(zip(bank_names, dff_names)) route_map = list(zip(bank_names, dff_names))
dff_pins = {key: self.data_dff_inst[port].get_pin(key) for key in dff_names } dff_pins = {key: self.data_dff_inst[port].get_pin(key) for key in dff_names }

View File

@ -123,7 +123,7 @@ class sram_4bank(sram_base):
# connect the MSB flops to the address input bus # connect the MSB flops to the address input bus
for i in [0,1]: for i in [0,1]:
msb_pins = self.msb_address_inst.get_pins("din[{}]".format(i)) msb_pins = self.msb_address_inst.get_pins("din_{}".format(i))
for msb_pin in msb_pins: for msb_pin in msb_pins:
if msb_pin.layer == "metal3": if msb_pin.layer == "metal3":
msb_pin_pos = msb_pin.lc() msb_pin_pos = msb_pin.lc()
@ -141,7 +141,7 @@ class sram_4bank(sram_base):
# Connect bank decoder outputs to the bank select vertical bus wires # Connect bank decoder outputs to the bank select vertical bus wires
for i in range(self.num_banks): for i in range(self.num_banks):
msb_pin = self.msb_decoder_inst.get_pin("out[{}]".format(i)) msb_pin = self.msb_decoder_inst.get_pin("out_{}".format(i))
msb_pin_pos = msb_pin.lc() msb_pin_pos = msb_pin.lc()
rail_pos = vector(self.vert_control_bus_positions["bank_sel[{}]".format(i)].x,msb_pin_pos.y) rail_pos = vector(self.vert_control_bus_positions["bank_sel[{}]".format(i)].x,msb_pin_pos.y)
self.add_path("metal1",[msb_pin_pos,rail_pos]) self.add_path("metal1",[msb_pin_pos,rail_pos])

View File

@ -158,7 +158,7 @@ class sram_base(design):
length=self.addr_bus_height)) length=self.addr_bus_height))
self.bank_sel_bus_names = ["bank_sel{0}[{1}]".format(port,i) for i in range(self.num_banks)] self.bank_sel_bus_names = ["bank_sel{0}_{1}".format(port,i) for i in range(self.num_banks)]
self.vert_control_bus_positions.update(self.create_vertical_pin_bus(layer="metal2", self.vert_control_bus_positions.update(self.create_vertical_pin_bus(layer="metal2",
pitch=self.m2_pitch, pitch=self.m2_pitch,
offset=self.bank_sel_bus_offset, offset=self.bank_sel_bus_offset,