110448Snilay@cs.wisc.edu/* Copyright (c) 2012 Massachusetts Institute of Technology 210448Snilay@cs.wisc.edu * 310448Snilay@cs.wisc.edu * Permission is hereby granted, free of charge, to any person obtaining a copy 410448Snilay@cs.wisc.edu * of this software and associated documentation files (the "Software"), to deal 510448Snilay@cs.wisc.edu * in the Software without restriction, including without limitation the rights 610448Snilay@cs.wisc.edu * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 710448Snilay@cs.wisc.edu * copies of the Software, and to permit persons to whom the Software is 810448Snilay@cs.wisc.edu * furnished to do so, subject to the following conditions: 910448Snilay@cs.wisc.edu * 1010448Snilay@cs.wisc.edu * The above copyright notice and this permission notice shall be included in 1110448Snilay@cs.wisc.edu * all copies or substantial portions of the Software. 1210448Snilay@cs.wisc.edu * 1310448Snilay@cs.wisc.edu * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 1410448Snilay@cs.wisc.edu * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 1510448Snilay@cs.wisc.edu * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 1610448Snilay@cs.wisc.edu * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 1710448Snilay@cs.wisc.edu * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 1810448Snilay@cs.wisc.edu * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 1910448Snilay@cs.wisc.edu * THE SOFTWARE. 2010448Snilay@cs.wisc.edu */ 2110448Snilay@cs.wisc.edu 2210447Snilay@cs.wisc.edu#include "model/electrical/RepeatedLink.h" 2310447Snilay@cs.wisc.edu 2410447Snilay@cs.wisc.edu#include "model/PortInfo.h" 2510447Snilay@cs.wisc.edu#include "model/EventInfo.h" 2610447Snilay@cs.wisc.edu#include "model/TransitionInfo.h" 2710447Snilay@cs.wisc.edu#include "model/std_cells/StdCellLib.h" 2810447Snilay@cs.wisc.edu#include "model/std_cells/StdCell.h" 2910447Snilay@cs.wisc.edu#include "model/timing_graph/ElectricalTimingTree.h" 3010447Snilay@cs.wisc.edu#include "model/timing_graph/ElectricalTimingNode.h" 3110447Snilay@cs.wisc.edu#include "model/timing_graph/ElectricalNet.h" 3210447Snilay@cs.wisc.edu#include "model/timing_graph/ElectricalDriver.h" 3310447Snilay@cs.wisc.edu#include "model/timing_graph/ElectricalDelay.h" 3410447Snilay@cs.wisc.edu#include "model/timing_graph/ElectricalLoad.h" 3510447Snilay@cs.wisc.edu 3610447Snilay@cs.wisc.edunamespace DSENT 3710447Snilay@cs.wisc.edu{ 3810447Snilay@cs.wisc.edu RepeatedLink::RepeatedLink(const String& instance_name_, const TechModel* tech_model_) 3910447Snilay@cs.wisc.edu : ElectricalModel(instance_name_, tech_model_) 4010447Snilay@cs.wisc.edu { 4110447Snilay@cs.wisc.edu m_repeater_ = NULL; 4210447Snilay@cs.wisc.edu m_repeater_load_ = NULL; 4310447Snilay@cs.wisc.edu m_timing_tree_ = NULL; 4410447Snilay@cs.wisc.edu 4510447Snilay@cs.wisc.edu initParameters(); 4610447Snilay@cs.wisc.edu initProperties(); 4710447Snilay@cs.wisc.edu } 4810447Snilay@cs.wisc.edu 4910447Snilay@cs.wisc.edu RepeatedLink::~RepeatedLink() 5010447Snilay@cs.wisc.edu { 5110447Snilay@cs.wisc.edu delete m_repeater_; 5210447Snilay@cs.wisc.edu delete m_repeater_load_; 5310447Snilay@cs.wisc.edu delete m_timing_tree_; 5410447Snilay@cs.wisc.edu } 5510447Snilay@cs.wisc.edu 5610447Snilay@cs.wisc.edu void RepeatedLink::initParameters() 5710447Snilay@cs.wisc.edu { 5810447Snilay@cs.wisc.edu addParameterName("NumberBits"); 5910447Snilay@cs.wisc.edu addParameterName("WireLayer"); 6010447Snilay@cs.wisc.edu addParameterName("WireWidthMultiplier", 1.0); 6110447Snilay@cs.wisc.edu addParameterName("WireSpacingMultiplier", 1.0); 6210447Snilay@cs.wisc.edu return; 6310447Snilay@cs.wisc.edu } 6410447Snilay@cs.wisc.edu 6510447Snilay@cs.wisc.edu void RepeatedLink::initProperties() 6610447Snilay@cs.wisc.edu { 6710447Snilay@cs.wisc.edu addPropertyName("WireLength"); 6810447Snilay@cs.wisc.edu addPropertyName("Delay"); 6910447Snilay@cs.wisc.edu addPropertyName("IsKeepParity", "TRUE"); 7010447Snilay@cs.wisc.edu return; 7110447Snilay@cs.wisc.edu } 7210447Snilay@cs.wisc.edu 7310447Snilay@cs.wisc.edu RepeatedLink* RepeatedLink::clone() const 7410447Snilay@cs.wisc.edu { 7510447Snilay@cs.wisc.edu // TODO 7610447Snilay@cs.wisc.edu return NULL; 7710447Snilay@cs.wisc.edu } 7810447Snilay@cs.wisc.edu 7910447Snilay@cs.wisc.edu void RepeatedLink::constructModel() 8010447Snilay@cs.wisc.edu { 8110447Snilay@cs.wisc.edu // Get parameters 8210447Snilay@cs.wisc.edu unsigned int number_bits = getParameter("NumberBits").toUInt(); 8310447Snilay@cs.wisc.edu const String& wire_layer = getParameter("WireLayer"); 8410447Snilay@cs.wisc.edu double wire_width_multiplier = getParameter("WireWidthMultiplier").toDouble(); 8510447Snilay@cs.wisc.edu double wire_spacing_multiplier = getParameter("WireSpacingMultiplier").toDouble(); 8610447Snilay@cs.wisc.edu 8710447Snilay@cs.wisc.edu ASSERT(number_bits > 0, "[Error] " + getInstanceName() + 8810447Snilay@cs.wisc.edu " -> Number of bits must be > 0!"); 8910447Snilay@cs.wisc.edu ASSERT(getTechModel()->isWireLayerExist(wire_layer), "[Error] " + getInstanceName() + 9010447Snilay@cs.wisc.edu " -> Wire layer does not exist!"); 9110447Snilay@cs.wisc.edu ASSERT(wire_width_multiplier >= 1.0, "[Error] " + getInstanceName() + 9210447Snilay@cs.wisc.edu " -> Wire width multiplier must be >= 1.0!"); 9310447Snilay@cs.wisc.edu ASSERT(wire_spacing_multiplier >= 1.0, "[Error] " + getInstanceName() + 9410447Snilay@cs.wisc.edu " -> Wire spacing multiplier must be >= 1.0!"); 9510447Snilay@cs.wisc.edu 9610447Snilay@cs.wisc.edu double wire_min_width = getTechModel()->get("Wire->" + wire_layer + "->MinWidth").toDouble(); 9710447Snilay@cs.wisc.edu double wire_min_spacing = getTechModel()->get("Wire->" + wire_layer + "->MinSpacing").toDouble(); 9810447Snilay@cs.wisc.edu 9910447Snilay@cs.wisc.edu double wire_width = wire_min_width * wire_width_multiplier; 10010447Snilay@cs.wisc.edu double wire_spacing = wire_min_spacing * wire_spacing_multiplier; 10110447Snilay@cs.wisc.edu 10210447Snilay@cs.wisc.edu double wire_cap_per_len = getTechModel()->calculateWireCapacitance(wire_layer, wire_width, wire_spacing, 1.0); 10310447Snilay@cs.wisc.edu double wire_res_per_len = getTechModel()->calculateWireResistance(wire_layer, wire_width, 1.0); 10410447Snilay@cs.wisc.edu 10510447Snilay@cs.wisc.edu getGenProperties()->set("WireWidth", wire_width); 10610447Snilay@cs.wisc.edu getGenProperties()->set("WireSpacing", wire_spacing); 10710447Snilay@cs.wisc.edu getGenProperties()->set("WireCapacitancePerLength", wire_cap_per_len); 10810447Snilay@cs.wisc.edu getGenProperties()->set("WireResistancePerLength", wire_res_per_len); 10910447Snilay@cs.wisc.edu 11010447Snilay@cs.wisc.edu // Create ports 11110447Snilay@cs.wisc.edu createInputPort("In", makeNetIndex(0, number_bits-1)); 11210447Snilay@cs.wisc.edu createOutputPort("Out", makeNetIndex(0, number_bits-1)); 11310447Snilay@cs.wisc.edu 11410447Snilay@cs.wisc.edu // Create area, power, and event results 11510447Snilay@cs.wisc.edu createElectricalAtomicResults(); 11610447Snilay@cs.wisc.edu createElectricalEventAtomicResult("Send"); 11710447Snilay@cs.wisc.edu 11810447Snilay@cs.wisc.edu // Create connections 11910447Snilay@cs.wisc.edu // Since the length is not set yet, we only to virtual fan-in and virtual fan-out 12010447Snilay@cs.wisc.edu createNet("InTmp"); 12110447Snilay@cs.wisc.edu createNet("OutTmp"); 12210447Snilay@cs.wisc.edu assignVirtualFanin("InTmp", "In"); 12310447Snilay@cs.wisc.edu assignVirtualFanout("Out", "OutTmp"); 12410447Snilay@cs.wisc.edu 12510447Snilay@cs.wisc.edu // Build Electrical Connectivity 12610447Snilay@cs.wisc.edu createLoad("In_Cap"); 12710447Snilay@cs.wisc.edu createDelay("In_to_Out_delay"); 12810447Snilay@cs.wisc.edu createDriver("Out_Ron", false); // Indicate this driver is not sizable 12910447Snilay@cs.wisc.edu 13010447Snilay@cs.wisc.edu ElectricalLoad* in_cap = getLoad("In_Cap"); 13110447Snilay@cs.wisc.edu ElectricalDelay* in_to_out_delay = getDelay("In_to_Out_delay"); 13210447Snilay@cs.wisc.edu ElectricalDriver* out_ron = getDriver("Out_Ron"); 13310447Snilay@cs.wisc.edu 13410447Snilay@cs.wisc.edu getNet("InTmp")->addDownstreamNode(in_cap); 13510447Snilay@cs.wisc.edu in_cap->addDownstreamNode(in_to_out_delay); 13610447Snilay@cs.wisc.edu in_to_out_delay->addDownstreamNode(out_ron); 13710447Snilay@cs.wisc.edu out_ron->addDownstreamNode(getNet("OutTmp")); 13810447Snilay@cs.wisc.edu 13910447Snilay@cs.wisc.edu // Init a repeater and a load to mimic a segment of a repeated link 14010447Snilay@cs.wisc.edu m_repeater_ = getTechModel()->getStdCellLib()->createStdCell("INV", "Repeater"); 14110447Snilay@cs.wisc.edu m_repeater_->construct(); 14210447Snilay@cs.wisc.edu m_repeater_load_ = new ElectricalLoad("RepeaterIn_Cap", this); 14310447Snilay@cs.wisc.edu // Make path repeater_ -> repeater_load_ 14410447Snilay@cs.wisc.edu // to catch the repeater's input/output cap and ensure only one inverter delay 14510447Snilay@cs.wisc.edu // is added 14610447Snilay@cs.wisc.edu m_repeater_->getNet("Y")->addDownstreamNode(m_repeater_load_); 14710447Snilay@cs.wisc.edu // Init a timing object to calculate delay 14810447Snilay@cs.wisc.edu m_timing_tree_ = new ElectricalTimingTree("RepeatedLink", this); 14910447Snilay@cs.wisc.edu m_timing_tree_->performCritPathExtract(m_repeater_->getNet("A")); 15010447Snilay@cs.wisc.edu return; 15110447Snilay@cs.wisc.edu } 15210447Snilay@cs.wisc.edu 15310447Snilay@cs.wisc.edu void RepeatedLink::updateModel() 15410447Snilay@cs.wisc.edu { 15510447Snilay@cs.wisc.edu unsigned int number_bits = getParameter("NumberBits").toUInt(); 15610447Snilay@cs.wisc.edu 15710447Snilay@cs.wisc.edu // Get properties 15810447Snilay@cs.wisc.edu double wire_length = getProperty("WireLength").toDouble(); 15910447Snilay@cs.wisc.edu double required_delay = getProperty("Delay").toDouble(); 16010447Snilay@cs.wisc.edu bool isKeepParity = getProperty("IsKeepParity").toBool(); 16110447Snilay@cs.wisc.edu 16210447Snilay@cs.wisc.edu ASSERT(wire_length >= 0, "[Error] " + getInstanceName() + 16310447Snilay@cs.wisc.edu " -> Wire length must be >= 0!"); 16410447Snilay@cs.wisc.edu ASSERT(required_delay >= 0, "[Error] " + getInstanceName() + 16510447Snilay@cs.wisc.edu " -> Required delay must be >= 0!"); 16610447Snilay@cs.wisc.edu 16710447Snilay@cs.wisc.edu const String& wire_layer = getParameter("WireLayer"); 16810447Snilay@cs.wisc.edu double wire_width = getGenProperties()->get("WireWidth").toDouble(); 16910447Snilay@cs.wisc.edu double wire_spacing = getGenProperties()->get("WireSpacing").toDouble(); 17010447Snilay@cs.wisc.edu 17110447Snilay@cs.wisc.edu // Calculate the total wire cap and total wire res 17210447Snilay@cs.wisc.edu double wire_cap_per_len = getGenProperties()->get("WireCapacitancePerLength").toDouble(); 17310447Snilay@cs.wisc.edu double wire_res_per_len = getGenProperties()->get("WireResistancePerLength").toDouble(); 17410447Snilay@cs.wisc.edu double total_wire_cap = wire_cap_per_len * wire_length; 17510447Snilay@cs.wisc.edu double total_wire_res = wire_res_per_len * wire_length; 17610447Snilay@cs.wisc.edu 17710447Snilay@cs.wisc.edu m_repeater_->update(); 17810447Snilay@cs.wisc.edu 17910447Snilay@cs.wisc.edu unsigned int increment_segments = (isKeepParity)? 2:1; 18010447Snilay@cs.wisc.edu unsigned int number_segments = increment_segments; 18110447Snilay@cs.wisc.edu double delay; 18210447Snilay@cs.wisc.edu m_repeater_->setMinDrivingStrength(); 18310447Snilay@cs.wisc.edu m_repeater_->getNet("Y")->setDistributedCap(total_wire_cap / number_segments); 18410447Snilay@cs.wisc.edu m_repeater_->getNet("Y")->setDistributedRes(total_wire_res / number_segments); 18510447Snilay@cs.wisc.edu m_repeater_load_->setLoadCap(m_repeater_->getNet("A")->getTotalDownstreamCap()); 18610447Snilay@cs.wisc.edu m_timing_tree_->performCritPathExtract(m_repeater_->getNet("A")); 18710447Snilay@cs.wisc.edu delay = m_timing_tree_->calculateCritPathDelay(m_repeater_->getNet("A")) * number_segments; 18810447Snilay@cs.wisc.edu 18910447Snilay@cs.wisc.edu // If everything is 0, use number_segments min-sized repeater 19010447Snilay@cs.wisc.edu if(wire_length != 0) 19110447Snilay@cs.wisc.edu { 19210447Snilay@cs.wisc.edu // Set the initial number of segments based on isKeepParity 19310447Snilay@cs.wisc.edu double last_min_size_delay = 0; 19410447Snilay@cs.wisc.edu unsigned int iteration = 0; 19510447Snilay@cs.wisc.edu 19610447Snilay@cs.wisc.edu // First set the repeater to the minimum driving strength 19710447Snilay@cs.wisc.edu last_min_size_delay = delay; 19810447Snilay@cs.wisc.edu 19910447Snilay@cs.wisc.edu Log::printLine(getInstanceName() + " -> Beginning Repeater Insertion"); 20010447Snilay@cs.wisc.edu 20110447Snilay@cs.wisc.edu while(required_delay < delay) 20210447Snilay@cs.wisc.edu { 20310447Snilay@cs.wisc.edu Log::printLine(getInstanceName() + " -> Repeater Insertion Iteration " + (String)iteration + 20410447Snilay@cs.wisc.edu ": Required delay = " + (String)required_delay + 20510447Snilay@cs.wisc.edu ", Delay = " + (String)delay + 20610447Snilay@cs.wisc.edu ", Slack = " + (String)(required_delay - delay) + 20710447Snilay@cs.wisc.edu ", Number of repeaters = " + (String)number_segments); 20810447Snilay@cs.wisc.edu 20910447Snilay@cs.wisc.edu // Size up if timing is not met 21010447Snilay@cs.wisc.edu while(required_delay < delay) 21110447Snilay@cs.wisc.edu { 21210447Snilay@cs.wisc.edu if(m_repeater_->hasMaxDrivingStrength()) 21310447Snilay@cs.wisc.edu { 21410447Snilay@cs.wisc.edu break; 21510447Snilay@cs.wisc.edu } 21610447Snilay@cs.wisc.edu m_repeater_->increaseDrivingStrength(); 21710447Snilay@cs.wisc.edu m_repeater_load_->setLoadCap(m_repeater_->getNet("A")->getTotalDownstreamCap()); 21810447Snilay@cs.wisc.edu m_timing_tree_->performCritPathExtract(m_repeater_->getNet("A")); 21910447Snilay@cs.wisc.edu delay = m_timing_tree_->calculateCritPathDelay(m_repeater_->getNet("A")) * number_segments; 22010447Snilay@cs.wisc.edu 22110447Snilay@cs.wisc.edu iteration++; 22210447Snilay@cs.wisc.edu Log::printLine(getInstanceName() + " -> Slack: " + (String)(required_delay - delay)); 22310447Snilay@cs.wisc.edu } 22410447Snilay@cs.wisc.edu // Increase number of segments if timing is not met 22510447Snilay@cs.wisc.edu if(required_delay < delay) 22610447Snilay@cs.wisc.edu { 22710447Snilay@cs.wisc.edu number_segments += increment_segments; 22810447Snilay@cs.wisc.edu m_repeater_->setMinDrivingStrength(); 22910447Snilay@cs.wisc.edu m_repeater_->getNet("Y")->setDistributedCap(total_wire_cap / number_segments); 23010447Snilay@cs.wisc.edu m_repeater_->getNet("Y")->setDistributedRes(total_wire_res / number_segments); 23110447Snilay@cs.wisc.edu m_repeater_load_->setLoadCap(m_repeater_->getNet("A")->getTotalDownstreamCap()); 23210447Snilay@cs.wisc.edu m_timing_tree_->performCritPathExtract(m_repeater_->getNet("A")); 23310447Snilay@cs.wisc.edu delay = m_timing_tree_->calculateCritPathDelay(m_repeater_->getNet("A")) * number_segments; 23410447Snilay@cs.wisc.edu 23510447Snilay@cs.wisc.edu // Abort if adding more min sized repeaters does not decrease the delay 23610447Snilay@cs.wisc.edu if(delay > last_min_size_delay) 23710447Snilay@cs.wisc.edu { 23810447Snilay@cs.wisc.edu break; 23910447Snilay@cs.wisc.edu } 24010447Snilay@cs.wisc.edu last_min_size_delay = delay; 24110447Snilay@cs.wisc.edu } 24210447Snilay@cs.wisc.edu } 24310447Snilay@cs.wisc.edu Log::printLine(getInstanceName() + " -> Repeater Insertion Ended after Iteration: " + (String)iteration + 24410447Snilay@cs.wisc.edu ": Required delay = " + (String)required_delay + 24510447Snilay@cs.wisc.edu ", Delay = " + (String)delay + 24610447Snilay@cs.wisc.edu ", Slack = " + (String)(required_delay - delay) + 24710447Snilay@cs.wisc.edu ", Number of repeaters = " + (String)number_segments); 24810447Snilay@cs.wisc.edu 24910447Snilay@cs.wisc.edu // Print a warning if the timing is not met 25010447Snilay@cs.wisc.edu if(required_delay < delay) 25110447Snilay@cs.wisc.edu { 25210447Snilay@cs.wisc.edu const String& warning_msg = "[Warning] " + getInstanceName() + " -> Timing not met" + 25310447Snilay@cs.wisc.edu ": Required delay = " + (String)required_delay + 25410447Snilay@cs.wisc.edu ", Delay = " + (String)delay + 25510447Snilay@cs.wisc.edu ", Slack = " + (String)(required_delay - delay) + 25610447Snilay@cs.wisc.edu ", Number of repeaters = " + (String)number_segments; 25710447Snilay@cs.wisc.edu Log::printLine(std::cerr, warning_msg); 25810447Snilay@cs.wisc.edu } 25910447Snilay@cs.wisc.edu } 26010447Snilay@cs.wisc.edu 26110447Snilay@cs.wisc.edu // Update electrical interfaces 26210447Snilay@cs.wisc.edu getLoad("In_Cap")->setLoadCap(m_repeater_->getNet("A")->getTotalDownstreamCap()); 26310447Snilay@cs.wisc.edu getDelay("In_to_Out_delay")->setDelay(delay); 26410447Snilay@cs.wisc.edu getDriver("Out_Ron")->setOutputRes(m_repeater_->getDriver("Y_Ron")->getOutputRes() + (total_wire_res / number_segments)); 26510447Snilay@cs.wisc.edu 26610447Snilay@cs.wisc.edu getGenProperties()->set("NumberSegments", number_segments); 26710447Snilay@cs.wisc.edu 26810447Snilay@cs.wisc.edu // Update area, power results 26910447Snilay@cs.wisc.edu resetElectricalAtomicResults(); 27010447Snilay@cs.wisc.edu addElecticalAtomicResultValues(m_repeater_, number_segments * number_bits); 27110447Snilay@cs.wisc.edu double wire_area = wire_length * (wire_width + wire_spacing) * number_bits; 27210447Snilay@cs.wisc.edu addElecticalWireAtomicResultValue(wire_layer, wire_area); 27310447Snilay@cs.wisc.edu 27410447Snilay@cs.wisc.edu return; 27510447Snilay@cs.wisc.edu } 27610447Snilay@cs.wisc.edu 27710447Snilay@cs.wisc.edu void RepeatedLink::useModel() 27810447Snilay@cs.wisc.edu { 27910447Snilay@cs.wisc.edu // Update the transition information for the modeled repeater 28010447Snilay@cs.wisc.edu // Since we only modeled one repeater. So the transition information for 0->0 and 1->1 28110447Snilay@cs.wisc.edu // is averaged out 28210447Snilay@cs.wisc.edu const TransitionInfo& trans_In = getInputPort("In")->getTransitionInfo(); 28310447Snilay@cs.wisc.edu double average_static_transition = (trans_In.getNumberTransitions00() + trans_In.getNumberTransitions11()) / 2.0; 28410447Snilay@cs.wisc.edu TransitionInfo mod_trans_In(average_static_transition, trans_In.getNumberTransitions01(), average_static_transition); 28510447Snilay@cs.wisc.edu m_repeater_->getInputPort("A")->setTransitionInfo(mod_trans_In); 28610447Snilay@cs.wisc.edu m_repeater_->use(); 28710447Snilay@cs.wisc.edu 28810447Snilay@cs.wisc.edu // Get parameters 28910447Snilay@cs.wisc.edu unsigned int number_bits = getParameter("NumberBits").toUInt(); 29010447Snilay@cs.wisc.edu unsigned int number_segments = getGenProperties()->get("NumberSegments").toUInt(); 29110447Snilay@cs.wisc.edu 29210447Snilay@cs.wisc.edu // Propagate the transition information 29310447Snilay@cs.wisc.edu propagateTransitionInfo(); 29410447Snilay@cs.wisc.edu 29510447Snilay@cs.wisc.edu // Update leakage power 29610447Snilay@cs.wisc.edu double power = 0.0; 29710447Snilay@cs.wisc.edu power += m_repeater_->getNddPowerResult("Leakage")->calculateSum() * number_segments * number_bits; 29810447Snilay@cs.wisc.edu getNddPowerResult("Leakage")->setValue(power); 29910447Snilay@cs.wisc.edu 30010447Snilay@cs.wisc.edu // Update event result 30110447Snilay@cs.wisc.edu double energy = 0.0; 30210447Snilay@cs.wisc.edu energy += m_repeater_->getEventResult("INV")->calculateSum() * number_segments * number_bits; 30310447Snilay@cs.wisc.edu getEventResult("Send")->setValue(energy); 30410447Snilay@cs.wisc.edu 30510447Snilay@cs.wisc.edu return; 30610447Snilay@cs.wisc.edu } 30710447Snilay@cs.wisc.edu 30810447Snilay@cs.wisc.edu void RepeatedLink::propagateTransitionInfo() 30910447Snilay@cs.wisc.edu { 31010447Snilay@cs.wisc.edu unsigned int number_segments = getGenProperties()->get("NumberSegments"); 31110447Snilay@cs.wisc.edu 31210447Snilay@cs.wisc.edu if((number_segments % 2) == 0) 31310447Snilay@cs.wisc.edu { 31410447Snilay@cs.wisc.edu propagatePortTransitionInfo("Out", "In"); 31510447Snilay@cs.wisc.edu } 31610447Snilay@cs.wisc.edu else 31710447Snilay@cs.wisc.edu { 31810447Snilay@cs.wisc.edu const TransitionInfo& trans_In = getInputPort("In")->getTransitionInfo(); 31910447Snilay@cs.wisc.edu TransitionInfo trans_Out(trans_In.getNumberTransitions11(), trans_In.getNumberTransitions01(), trans_In.getNumberTransitions00()); 32010447Snilay@cs.wisc.edu getOutputPort("Out")->setTransitionInfo(trans_Out); 32110447Snilay@cs.wisc.edu } 32210447Snilay@cs.wisc.edu return; 32310447Snilay@cs.wisc.edu } 32410447Snilay@cs.wisc.edu 32510447Snilay@cs.wisc.edu} // namespace DSENT 32610447Snilay@cs.wisc.edu 327