diff options
Diffstat (limited to 'src/mem/ruby/network/orion/power_crossbar.cc')
-rw-r--r-- | src/mem/ruby/network/orion/power_crossbar.cc | 365 |
1 files changed, 0 insertions, 365 deletions
diff --git a/src/mem/ruby/network/orion/power_crossbar.cc b/src/mem/ruby/network/orion/power_crossbar.cc deleted file mode 100644 index a9f3e2e39..000000000 --- a/src/mem/ruby/network/orion/power_crossbar.cc +++ /dev/null @@ -1,365 +0,0 @@ -/* - * Copyright (c) 1999-2008 Mark D. Hill and David A. Wood - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions are - * met: redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer; - * redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution; - * neither the name of the copyright holders nor the names of its - * contributors may be used to endorse or promote products derived from - * this software without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS - * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT - * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR - * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT - * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, - * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT - * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, - * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY - * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT - * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE - * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - */ - -#include <stdio.h> -#include <math.h> - -#include "mem/ruby/network/orion/power_ll.hh" -#include "mem/ruby/network/orion/power_crossbar.hh" -#include "mem/ruby/network/orion/parm_technology.hh" -#include "mem/ruby/network/orion/SIM_port.hh" -#include "mem/ruby/network/orion/power_static.hh" -#include "mem/ruby/network/orion/power_utils.hh" - -/*-------------------- CROSSBAR power model -------------------*/ - -static double crossbar_in_cap(double wire_cap, unsigned n_out, int connect_type, int trans_type, double *Nsize) -{ - double Ctotal = 0, Ctrans = 0, psize, nsize, Cdriver = 0; - - /* part 1: wire cap */ - Ctotal += wire_cap; - //printf("CROSSBAR_INTERNAL: input wire cap = %g\n", wire_cap); - - /* part 2: drain cap of transmission gate or gate cap of tri-state gate */ - if (connect_type == TRANS_GATE) { - /* FIXME: resizing strategy */ - nsize = Nsize ? *Nsize : Wmemcellr; - psize = nsize * Wdecinvp / Wdecinvn; - Ctrans = SIM_power_draincap(nsize, NCH, 1); - if (trans_type == NP_GATE) - Ctrans += SIM_power_draincap(psize, PCH, 1); - } - else if (connect_type == TRISTATE_GATE) { - Ctrans = SIM_power_gatecap(Woutdrvnandn + Woutdrvnandp, 0) + - SIM_power_gatecap(Woutdrvnorn + Woutdrvnorp, 0); - } - else {/* some error handler */} - - //printf("CROSSBAR_INTERNAL: input connector cap = %g\n", (n_out * Ctrans)); - Ctotal += n_out * Ctrans; - - /* part 3: input driver */ - /* FIXME: how to specify timing? */ - psize = SIM_power_driver_size(Ctotal, Period / 3); - nsize = psize * Wdecinvn / Wdecinvp; - Cdriver = SIM_power_draincap(nsize, NCH, 1) + SIM_power_draincap(psize, PCH, 1) + - SIM_power_gatecap(nsize + psize, 0); - - //printf("CROSSBAR_INTERNAL: input driver cap = %g\n", Cdriver); - - Ctotal += Cdriver; - - return Ctotal / 2; -} - - -static double crossbar_out_cap(double length, unsigned n_in, int connect_type, int trans_type, double *Nsize) -{ - double Ctotal = 0, Cwire = 0, Ctrans = 0, Cdriver = 0, psize, nsize; - - /* part 1: wire cap */ - Cwire += CC3metal * length; - //printf("CROSSBAR_INTERNAL: output wire cap = %g\n", Cwire); - - Ctotal += Cwire; - - /* part 2: drain cap of transmission gate or tri-state gate */ - if (connect_type == TRANS_GATE) { - /* FIXME: resizing strategy */ - if (Nsize) { - /* FIXME: how to specify timing? */ - psize = SIM_power_driver_size(Ctotal, Period / 3); - *Nsize = nsize = psize * Wdecinvn / Wdecinvp; - } - else { - nsize = Wmemcellr; - psize = nsize * Wdecinvp / Wdecinvn; - } - Ctrans = SIM_power_draincap(nsize, NCH, 1); - if (trans_type == NP_GATE) - Ctrans += SIM_power_draincap(psize, PCH, 1); - } - else if (connect_type == TRISTATE_GATE) { - Ctrans = SIM_power_draincap(Woutdrivern, NCH, 1) + SIM_power_draincap(Woutdriverp, PCH, 1); - } - else {/* some error handler */} - - //printf("CROSSBAR_INTERNAL: output connector cap = %g\n", (n_in * Ctrans)); - Ctotal += n_in * Ctrans; - - /* part 3: output driver */ - Cdriver += SIM_power_draincap(Woutdrivern, NCH, 1) + SIM_power_draincap(Woutdriverp, PCH, 1) + - SIM_power_gatecap(Woutdrivern + Woutdriverp, 0); - - //printf("CROSSBAR_INTERNAL: output driver cap = %g\n", Cdriver); - - Ctotal += Cdriver; - - return Ctotal / 2; -} - - -/* cut-through crossbar only supports 4x4 now */ -static double crossbar_io_cap(double length) -{ - double Ctotal = 0, psize, nsize; - - /* part 1: wire cap */ - Ctotal += CC3metal * length; - - /* part 2: gate cap of tri-state gate */ - Ctotal += 2 * (SIM_power_gatecap(Woutdrvnandn + Woutdrvnandp, 0) + - SIM_power_gatecap(Woutdrvnorn + Woutdrvnorp, 0)); - - /* part 3: drain cap of tri-state gate */ - Ctotal += 2 * (SIM_power_draincap(Woutdrivern, NCH, 1) + SIM_power_draincap(Woutdriverp, PCH, 1)); - - /* part 4: input driver */ - /* FIXME: how to specify timing? */ - psize = SIM_power_driver_size(Ctotal, Period * 0.8); - nsize = psize * Wdecinvn / Wdecinvp; - Ctotal += SIM_power_draincap(nsize, NCH, 1) + SIM_power_draincap(psize, PCH, 1) + - SIM_power_gatecap(nsize + psize, 0); - - /* part 5: output driver */ - Ctotal += SIM_power_draincap(Woutdrivern, NCH, 1) + SIM_power_draincap(Woutdriverp, PCH, 1) + - SIM_power_gatecap(Woutdrivern + Woutdriverp, 0); - - /* HACK HACK HACK */ - /* this HACK is to count a 1:4 mux and a 4:1 mux, so we have a 5x5 crossbar */ - return Ctotal / 2 * 1.32; -} - - -static double crossbar_int_cap(unsigned degree, int connect_type, int trans_type) -{ - double Ctotal = 0, Ctrans; - - if (connect_type == TRANS_GATE) { - /* part 1: drain cap of transmission gate */ - /* FIXME: Wmemcellr and resize */ - Ctrans = SIM_power_draincap(Wmemcellr, NCH, 1); - if (trans_type == NP_GATE) - Ctrans += SIM_power_draincap(Wmemcellr * Wdecinvp / Wdecinvn, PCH, 1); - Ctotal += (degree + 1) * Ctrans; - } - else if (connect_type == TRISTATE_GATE) { - /* part 1: drain cap of tri-state gate */ - Ctotal += degree * (SIM_power_draincap(Woutdrivern, NCH, 1) + SIM_power_draincap(Woutdriverp, PCH, 1)); - - /* part 2: gate cap of tri-state gate */ - Ctotal += SIM_power_gatecap(Woutdrvnandn + Woutdrvnandp, 0) + - SIM_power_gatecap(Woutdrvnorn + Woutdrvnorp, 0); - } - else {/* some error handler */} - - return Ctotal / 2; -} - - -/* FIXME: segment control signals are not handled yet */ -static double crossbar_ctr_cap(double length, unsigned data_width, int prev_ctr, int next_ctr, unsigned degree, int connect_type, int trans_type) -{ - double Ctotal = 0, Cgate; - - /* part 1: wire cap */ - Ctotal = Cmetal * length; - - /* part 2: gate cap of transmission gate or tri-state gate */ - if (connect_type == TRANS_GATE) { - /* FIXME: Wmemcellr and resize */ - Cgate = SIM_power_gatecap(Wmemcellr, 0); - if (trans_type == NP_GATE) - Cgate += SIM_power_gatecap(Wmemcellr * Wdecinvp / Wdecinvn, 0); - } - else if (connect_type == TRISTATE_GATE) { - Cgate = SIM_power_gatecap(Woutdrvnandn + Woutdrvnandp, 0) + - SIM_power_gatecap(Woutdrvnorn + Woutdrvnorp, 0); - } - else {/* some error handler */} - - Ctotal += data_width * Cgate; - - /* part 3: inverter */ - if (!(connect_type == TRANS_GATE && trans_type == N_GATE && !prev_ctr)) - /* FIXME: need accurate size, use minimal size for now */ - Ctotal += SIM_power_draincap(Wdecinvn, NCH, 1) + SIM_power_draincap(Wdecinvp, PCH, 1) + - SIM_power_gatecap(Wdecinvn + Wdecinvp, 0); - - /* part 4: drain cap of previous level control signal */ - if (prev_ctr) - /* FIXME: need actual size, use decoder data for now */ - Ctotal += degree * SIM_power_draincap(WdecNORn, NCH, 1) + SIM_power_draincap(WdecNORp, PCH, degree); - - /* part 5: gate cap of next level control signal */ - if (next_ctr) - /* FIXME: need actual size, use decoder data for now */ - Ctotal += SIM_power_gatecap(WdecNORn + WdecNORp, degree * 40 + 20); - - return Ctotal; -} - - -int power_crossbar_init(power_crossbar *crsbar, int model, unsigned n_in, unsigned n_out, unsigned data_width, unsigned degree, int connect_type, int trans_type, double in_len, double out_len, double *req_len) -{ - double in_length, out_length, ctr_length, Nsize, in_wire_cap, i_leakage; - - if ((crsbar->model = model) && model < CROSSBAR_MAX_MODEL) { - crsbar->n_in = n_in; - crsbar->n_out = n_out; - crsbar->data_width = data_width; - crsbar->degree = degree; - crsbar->connect_type = connect_type; - crsbar->trans_type = trans_type; - /* redundant field */ - crsbar->mask = HAMM_MASK(data_width); - - crsbar->n_chg_in = crsbar->n_chg_int = crsbar->n_chg_out = crsbar->n_chg_ctr = 0; - - switch (model) { - case MATRIX_CROSSBAR: - - /* FIXME: need accurate spacing */ - in_length = n_out * data_width * CrsbarCellWidth; - out_length = n_in * data_width * CrsbarCellHeight; - if (in_length < in_len) in_length = in_len; - if (out_length < out_len) out_length = out_len; - ctr_length = in_length / 2; - if (req_len) *req_len = in_length; - - in_wire_cap = in_length * CC3metal; - - crsbar->e_chg_out = crossbar_out_cap(out_length, n_in, connect_type, trans_type, &Nsize) * EnergyFactor; - crsbar->e_chg_in = crossbar_in_cap(in_wire_cap, n_out, connect_type, trans_type, &Nsize) * EnergyFactor; - /* FIXME: wire length estimation, really reset? */ - /* control signal should reset after transmission is done, so no 1/2 */ - crsbar->e_chg_ctr = crossbar_ctr_cap(ctr_length, data_width, 0, 0, 0, connect_type, trans_type) * EnergyFactor; - crsbar->e_chg_int = 0; - - /* static power */ - i_leakage = 0; - /* tri-state buffers */ - i_leakage += ((Woutdrvnandp * (NAND2_TAB[0] + NAND2_TAB[1] + NAND2_TAB[2]) + Woutdrvnandn * NAND2_TAB[3]) / 4 + - (Woutdrvnorp * NOR2_TAB[0] + Woutdrvnorn * (NOR2_TAB[1] + NOR2_TAB[2] + NOR2_TAB[3])) / 4 + - Woutdrivern * NMOS_TAB[0] + Woutdriverp * PMOS_TAB[0]) * n_in * n_out * data_width; - /* input driver */ - i_leakage += (Wdecinvn * NMOS_TAB[0] + Wdecinvp * PMOS_TAB[0]) * n_in * data_width; - /* output driver */ - i_leakage += (Woutdrivern * NMOS_TAB[0] + Woutdriverp * PMOS_TAB[0]) * n_out * data_width; - /* control signal inverter */ - i_leakage += (Wdecinvn * NMOS_TAB[0] + Wdecinvp * PMOS_TAB[0]) * n_in * n_out; - crsbar->i_leakage = i_leakage / PARM_TECH_POINT * 100; - break; - - case MULTREE_CROSSBAR: - /* input wire horizontal segment length */ - in_length = n_in * data_width * CrsbarCellWidth * (n_out / 2); - in_wire_cap = in_length * CCmetal; - /* input wire vertical segment length */ - in_length = n_in * data_width * (5 * Lamda) * (n_out / 2); - in_wire_cap += in_length * CC3metal; - - ctr_length = n_in * data_width * CrsbarCellWidth * (n_out / 2) / 2; - - crsbar->e_chg_out = crossbar_out_cap(0, degree, connect_type, trans_type, NULL) * EnergyFactor; - crsbar->e_chg_in = crossbar_in_cap(in_wire_cap, n_out, connect_type, trans_type, NULL) * EnergyFactor; - crsbar->e_chg_int = crossbar_int_cap(degree, connect_type, trans_type) * EnergyFactor; - - /* redundant field */ - crsbar->depth = (unsigned)ceil(log(n_in) / log(degree)); - - /* control signal should reset after transmission is done, so no 1/2 */ - if (crsbar->depth == 1) - /* only one level of control signal */ - crsbar->e_chg_ctr = crossbar_ctr_cap(ctr_length, data_width, 0, 0, degree, connect_type, trans_type) * EnergyFactor; - else { - /* first level and last level control signals */ - crsbar->e_chg_ctr = crossbar_ctr_cap(ctr_length, data_width, 0, 1, degree, connect_type, trans_type) * EnergyFactor + - crossbar_ctr_cap(0, data_width, 1, 0, degree, connect_type, trans_type) * EnergyFactor; - /* intermediate control signals */ - if (crsbar->depth > 2) - crsbar->e_chg_ctr += (crsbar->depth - 2) * crossbar_ctr_cap(0, data_width, 1, 1, degree, connect_type, trans_type) * EnergyFactor; - } - - /* static power */ - i_leakage = 0; - /* input driver */ - i_leakage += (Wdecinvn * NMOS_TAB[0] + Wdecinvp * PMOS_TAB[0]) * n_in * data_width; - /* output driver */ - i_leakage += (Woutdrivern * NMOS_TAB[0] + Woutdriverp * PMOS_TAB[0]) * n_out * data_width; - /* mux */ - i_leakage += (WdecNORp * NOR2_TAB[0] + WdecNORn * (NOR2_TAB[1] + NOR2_TAB[2] + NOR2_TAB[3])) / 4 * (2 * n_in - 1) * n_out * data_width; - /* control signal inverter */ - i_leakage += (Wdecinvn * NMOS_TAB[0] + Wdecinvp * PMOS_TAB[0]) * n_in * n_out; - crsbar->i_leakage = i_leakage / PARM_TECH_POINT * 100; - break; - - default: break;/* some error handler */ - } - - return 0; - } - else - return -1; -} - - -/* FIXME: MULTREE_CROSSBAR record missing */ -int crossbar_record(power_crossbar *xb, int io, unsigned long int new_data, unsigned long int old_data, unsigned new_port, unsigned old_port) -{ - switch (xb->model) { - case MATRIX_CROSSBAR: - if (io) /* input port */ - xb->n_chg_in += SIM_power_Hamming(new_data, old_data, xb->mask); - else { /* output port */ - xb->n_chg_out += SIM_power_Hamming(new_data, old_data, xb->mask); - xb->n_chg_ctr += new_port != old_port; - } - break; - - case MULTREE_CROSSBAR: - break; - - default: break;/* some error handler */ - } - - return 0; -} - - -double crossbar_report(power_crossbar *crsbar) -{ - return (crsbar->n_chg_in * crsbar->e_chg_in + crsbar->n_chg_out * crsbar->e_chg_out + - crsbar->n_chg_int * crsbar->e_chg_int + crsbar->n_chg_ctr * crsbar->e_chg_ctr); -} - -/* ---------- crossbar model ---------- */ - - - |