def gen_data(self, clk_times, sig_name, period, slew): """ Generates the PWL data inputs for a simulation timing test. """ # values for NOP, W1, W0, W1, R0, NOP, W1, W0, R1, NOP # we are asserting the opposite value on the other side of the tx gate during # the read to be "worst case". Otherwise, it can actually assist the read. values = [0, 1, 0, 1, 1, 1, 1, 0, 0, 0 ] stimuli.gen_pwl(self.sf, sig_name, clk_times, values, period, slew, 0.05)
def write_clock(self): """ Create the clock signal for setup/hold analysis. First period initializes the FF while the second is used for characterization.""" stimuli.gen_pwl(stim_file=self.sf, sig_name="clk", # initial clk edge is right after the 0 time to initialize a flop # without using .IC on an internal node. # Return input to value after one period. # The second pulse is the characterization one at 2*period clk_times=[0, 0.1*self.period,self.period,2*self.period], data_values=[0, 1, 0, 1], period=2*self.period, slew=self.constrained_input_slew, setup=0)
def gen_addr(self, clk_times, addr, period, slew): """ Generates the address inputs for a simulation timing test. This alternates between all 1's and all 0's for the address. """ zero_values = [0, 0, 0, 1, 0, 0, 0, 1, 0, 0 ] ones_values = [1, 1, 1, 0, 1, 0, 1, 0, 1, 1 ] for i in range(len(addr)): sig_name = "A[{0}]".format(i) if addr[i]=="1": stimuli.gen_pwl(self.sf, sig_name, clk_times, ones_values, period, slew, 0.05) else: stimuli.gen_pwl(self.sf, sig_name, clk_times, zero_values, period, slew, 0.05)
def write_data(self, mode, target_time, correct_value): """Create the data signals for setup/hold analysis. First period is to initialize it to the opposite polarity. Second period is used for characterization. """ self.sf.write("\n* Generation of the data and clk signals\n") incorrect_value = stimuli.get_inverse_value(correct_value) if mode=="HOLD": init_value = incorrect_value start_value = correct_value end_value = incorrect_value else: init_value = incorrect_value start_value = incorrect_value end_value = correct_value stimuli.gen_pwl(stim_file=self.sf, sig_name="data", clk_times=[0, self.period, target_time], data_values=[init_value, start_value, end_value], period=target_time, slew=self.constrained_input_slew, setup=0)
def gen_web(self, clk_times, period, slew): """ Generates the PWL WEb signal """ # values for NOP, W1, W0, W1, R0, NOP, W1, W0, R1, NOP # Keep WEb deasserted in NOP for measuring >1 period values = [1, 0, 0, 0, 1, 1, 0, 0, 1, 1] stimuli.gen_pwl(self.sf, "web", clk_times, values, period, slew, 0.05) # Keep acc_en deasserted in NOP for measuring >1 period values = [1, 0, 0, 0, 1, 1, 0, 0, 1, 1] stimuli.gen_pwl(self.sf, "acc_en", clk_times, values, period, slew, 0) values = [0, 1, 1, 1, 0, 0, 1, 1, 0, 0] stimuli.gen_pwl(self.sf, "acc_en_inv", clk_times, values, period, slew, 0)
def write_stimulus(self, feasible_period, target_period, data_value): """Creates a stimulus file for simulations to probe a certain bitcell, given an address and data-position of the data-word (probe-address form: '111010000' LSB=0, MSB=1) (probe_data form: number corresponding to the bit position of data-bus, begins with position 0) """ self.check_arguments() # obtains list of time-points for each rising clk edge self.obtain_cycle_times(slow_period=feasible_period, fast_period=target_period) # creates and opens stimulus file for writing temp_stim = "{0}/stim.sp".format(OPTS.openram_temp) self.sf = open(temp_stim, "w") self.sf.write( "* Stimulus data value of {0} for target period of {1}n\n".format( data_value, target_period)) self.sf.write("\n") # include files in stimulus file model_list = tech.spice["fet_models"] + [self.sram_sp_file] stimuli.write_include(stim_file=self.sf, models=model_list) self.sf.write("\n") # add vdd/gnd statements self.sf.write("* Global Power Supplies\n") stimuli.write_supply(stim_file=self.sf, vdd_name=tech.spice["vdd_name"], gnd_name=tech.spice["gnd_name"], vdd_voltage=tech.spice["supply_voltage"], gnd_voltage=tech.spice["gnd_voltage"]) self.sf.write("\n") # instantiate the sram self.sf.write("* Instantiation of the SRAM\n") stimuli.inst_sram(stim_file=self.sf, abits=self.addr_size, dbits=self.word_size, sram_name=self.name) self.sf.write("\n") # create a buffer and an inverter self.sf.write("* Buffers and inverter Initialization\n") # FIXME: We should replace the clock buffer with the same # 2x buffer for control signals. This needs the buffer to be # added to the control logic though. stimuli.create_buffer(stim_file=self.sf, buffer_name="clk1_buffer", size=[1, 4]) self.sf.write("\n") stimuli.create_buffer(stim_file=self.sf, buffer_name="clk2_buffer", size=[8, 16]) self.sf.write("\n") stimuli.create_buffer(stim_file=self.sf, buffer_name="buffer", size=[1, 2]) self.sf.write("\n") stimuli.create_inverter(stim_file=self.sf) self.sf.write("\n") # add a buffer for each signal and an inverter for WEb signal_list = [] for i in range(self.word_size): signal_list.append("D[{0}]".format(i)) for j in range(self.addr_size): signal_list.append("A[{0}]".format(j)) for k in tech.spice["control_signals"]: signal_list.append(k) self.sf.write("*Buffers for each generated signal and Inv for WEb\n") stimuli.add_buffer(stim_file=self.sf, buffer_name="buffer", signal_list=signal_list) stimuli.add_buffer(stim_file=self.sf, buffer_name="clk1_buffer", signal_list=["clk"]) stimuli.add_buffer(stim_file=self.sf, buffer_name="clk2_buffer", signal_list=["clk_buf"]) stimuli.add_buffer(stim_file=self.sf, buffer_name="buffer", signal_list=["WEb_trans"]) stimuli.add_inverter(stim_file=self.sf, signal_list=["WEb_trans"]) self.sf.write("\n") # add access transistors for data-bus self.sf.write("* Transmission Gates for data-bus\n") stimuli.add_accesstx(stim_file=self.sf, dbits=self.word_size) self.sf.write("\n") # generate data and addr signals self.sf.write("*Generation of data and address signals\n") if data_value == tech.spice["supply_voltage"]: v_val = tech.spice["gnd_voltage"] else: v_val = tech.spice["supply_voltage"] for i in range(self.word_size): if i == self.probe_data: stimuli.gen_data_pwl(stim_file=self.sf, key_times=self.cycle_times, sig_name="D[{0}]".format(i), data_value=data_value, feasible_period=feasible_period, target_period=target_period, t_rise=tech.spice["rise_time"], t_fall=tech.spice["fall_time"]) else: stimuli.gen_constant(stim_file=self.sf, sig_name="D[{0}]".format(i), v_ref=tech.spice["gnd_voltage"], v_val=v_val) stimuli.gen_addr_pwl(stim_file=self.sf, key_times=self.cycle_times, addr=self.probe_address, feasible_period=feasible_period, target_period=target_period, t_rise=tech.spice["rise_time"], t_fall=tech.spice["fall_time"]) self.sf.write("\n") # generate control signals self.sf.write("*Generation of control signals\n") # CSb (x_list, y_list) = stimuli.gen_csb_pwl(key_times=self.cycle_times, feasible_period=feasible_period, target_period=target_period, t_rise=tech.spice["rise_time"], t_fall=tech.spice["fall_time"]) stimuli.gen_pwl(stim_file=self.sf, sig_name="CSb", x_list=x_list, y_list=y_list) # WEb (x_list, y_list) = stimuli.gen_web_pwl(key_times=self.cycle_times, feasible_period=feasible_period, target_period=target_period, t_rise=tech.spice["rise_time"], t_fall=tech.spice["fall_time"]) stimuli.gen_pwl(stim_file=self.sf, sig_name="WEb", x_list=x_list, y_list=y_list) # OEb (x_list, y_list) = stimuli.gen_oeb_pwl(key_times=self.cycle_times, feasible_period=feasible_period, target_period=target_period, t_rise=tech.spice["rise_time"], t_fall=tech.spice["fall_time"]) stimuli.gen_pwl(stim_file=self.sf, sig_name="OEb", x_list=x_list, y_list=y_list) # WEb_transmission_gate (x_list, y_list) = stimuli.gen_web_trans_pwl(key_times=self.cycle_times, feasible_period=feasible_period, target_period=target_period, t_rise=tech.spice["rise_time"], t_fall=tech.spice["fall_time"]) stimuli.gen_pwl(stim_file=self.sf, sig_name="WEb_trans", x_list=x_list, y_list=y_list) self.sf.write("\n") self.write_clock() self.write_measures(data_value) self.write_control() self.sf.close()
def gen_oeb(self, clk_times, period, slew): """ Generates the PWL WEb signal """ # values for NOP, W1, W0, W1, R0, W1, W0, R1, NOP # Keep OEb asserted in NOP for measuring >1 period values = [1, 1, 1, 1, 0, 0, 1, 1, 0, 0] stimuli.gen_pwl(self.sf, "oeb", clk_times, values, period, slew, 0.05)