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/OpticalModel.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/optical_graph/OpticalWaveguide.h" 2710447Snilay@cs.wisc.edu#include "model/optical_graph/OpticalNode.h" 2810447Snilay@cs.wisc.edu#include "model/optical_graph/OpticalLaser.h" 2910447Snilay@cs.wisc.edu#include "model/optical_graph/OpticalModulator.h" 3010447Snilay@cs.wisc.edu#include "model/optical_graph/OpticalFilter.h" 3110447Snilay@cs.wisc.edu#include "model/optical_graph/OpticalDetector.h" 3210447Snilay@cs.wisc.edu#include "model/optical_graph/OpticalWavelength.h" 3310447Snilay@cs.wisc.edu 3410447Snilay@cs.wisc.edunamespace DSENT 3510447Snilay@cs.wisc.edu{ 3610447Snilay@cs.wisc.edu OpticalModel::OpticalModel(const String& instance_name_, const TechModel* tech_model_) 3710447Snilay@cs.wisc.edu : ElectricalModel(instance_name_, tech_model_) 3810447Snilay@cs.wisc.edu { 3910447Snilay@cs.wisc.edu m_optical_input_ports_ = new Map<PortInfo*>; 4010447Snilay@cs.wisc.edu m_optical_output_ports_ = new Map<PortInfo*>; 4110447Snilay@cs.wisc.edu 4210447Snilay@cs.wisc.edu m_waveguides_ = new Map<OpticalWaveguide*>; 4310447Snilay@cs.wisc.edu m_lasers_ = new Map<OpticalLaser*>; 4410447Snilay@cs.wisc.edu m_modulators_ = new Map<OpticalModulator*>; 4510447Snilay@cs.wisc.edu m_filters_ = new Map<OpticalFilter*>; 4610447Snilay@cs.wisc.edu m_detectors_ = new Map<OpticalDetector*>; 4710447Snilay@cs.wisc.edu } 4810447Snilay@cs.wisc.edu 4910447Snilay@cs.wisc.edu OpticalModel::~OpticalModel() 5010447Snilay@cs.wisc.edu { 5110447Snilay@cs.wisc.edu delete m_optical_input_ports_; 5210447Snilay@cs.wisc.edu delete m_optical_output_ports_; 5310447Snilay@cs.wisc.edu deletePtrMap<OpticalWaveguide>(m_waveguides_); 5410447Snilay@cs.wisc.edu deletePtrMap<OpticalLaser>(m_lasers_); 5510447Snilay@cs.wisc.edu deletePtrMap<OpticalModulator>(m_modulators_); 5610447Snilay@cs.wisc.edu deletePtrMap<OpticalFilter>(m_filters_); 5710447Snilay@cs.wisc.edu deletePtrMap<OpticalDetector>(m_detectors_); 5810447Snilay@cs.wisc.edu m_optical_input_ports_ = NULL; 5910447Snilay@cs.wisc.edu m_optical_output_ports_ = NULL; 6010447Snilay@cs.wisc.edu m_waveguides_ = NULL; 6110447Snilay@cs.wisc.edu m_lasers_ = NULL; 6210447Snilay@cs.wisc.edu m_modulators_ = NULL; 6310447Snilay@cs.wisc.edu m_filters_ = NULL; 6410447Snilay@cs.wisc.edu m_detectors_ = NULL; 6510447Snilay@cs.wisc.edu } 6610447Snilay@cs.wisc.edu 6710447Snilay@cs.wisc.edu // Connect an optical port (input or output) to some OpticalWaveguide 6810447Snilay@cs.wisc.edu void OpticalModel::opticalPortConnect(OpticalModel* connect_model_, const String& port_name_, const String& waveguide_name_) 6910447Snilay@cs.wisc.edu { 7010447Snilay@cs.wisc.edu // Check that the connecting waveguide exists 7110447Snilay@cs.wisc.edu ASSERT(m_waveguides_->keyExist(waveguide_name_), "[Error] " + getInstanceName() + 7210447Snilay@cs.wisc.edu " -> Waveguide '" + waveguide_name_ + "' does not exist!"); 7310447Snilay@cs.wisc.edu 7410447Snilay@cs.wisc.edu // Check whether the port name is an input or output, assertion error if neither 7510447Snilay@cs.wisc.edu bool is_input = connect_model_->getOpticalInputs()->keyExist(port_name_); 7610447Snilay@cs.wisc.edu bool is_output = connect_model_->getOpticalOutputs()->keyExist(port_name_); 7710447Snilay@cs.wisc.edu ASSERT(is_input || is_output, "[Error] " + getInstanceName() + " -> Model '" + connect_model_->getInstanceName() + 7810447Snilay@cs.wisc.edu "' does not have a port named '" + port_name_ + "'!"); 7910447Snilay@cs.wisc.edu 8010447Snilay@cs.wisc.edu // Get the two waveguides 8110447Snilay@cs.wisc.edu OpticalWaveguide* port_waveguide = connect_model_->getWaveguide(port_name_); 8210447Snilay@cs.wisc.edu OpticalWaveguide* connect_waveguide = getWaveguide(waveguide_name_); 8310447Snilay@cs.wisc.edu 8410447Snilay@cs.wisc.edu // Check that the two waveguides expect the same wavelengths 8510447Snilay@cs.wisc.edu ASSERT((port_waveguide->getWavelengths().first == connect_waveguide->getWavelengths().first) && 8610447Snilay@cs.wisc.edu (port_waveguide->getWavelengths().second == connect_waveguide->getWavelengths().second), 8710447Snilay@cs.wisc.edu "[Error] " + getInstanceName() + " -> Optical port expects different wavelengths for Model '" + 8810447Snilay@cs.wisc.edu connect_model_->getInstanceName() + "." + port_name_ + "' and waveguide '" + waveguide_name_ + "'!"); 8910447Snilay@cs.wisc.edu 9010447Snilay@cs.wisc.edu if(is_input) 9110447Snilay@cs.wisc.edu { 9210447Snilay@cs.wisc.edu connect_waveguide->addDownstreamNode(port_waveguide); 9310447Snilay@cs.wisc.edu } 9410447Snilay@cs.wisc.edu else if(is_output) 9510447Snilay@cs.wisc.edu { 9610447Snilay@cs.wisc.edu port_waveguide->addDownstreamNode(connect_waveguide); 9710447Snilay@cs.wisc.edu } 9810447Snilay@cs.wisc.edu } 9910447Snilay@cs.wisc.edu 10010447Snilay@cs.wisc.edu //Get Waveguides 10110447Snilay@cs.wisc.edu const Map<OpticalWaveguide*>* OpticalModel::getWaveguides() const 10210447Snilay@cs.wisc.edu { 10310447Snilay@cs.wisc.edu return m_waveguides_; 10410447Snilay@cs.wisc.edu } 10510447Snilay@cs.wisc.edu 10610447Snilay@cs.wisc.edu OpticalWaveguide* OpticalModel::getWaveguide(const String& name_) 10710447Snilay@cs.wisc.edu { 10810447Snilay@cs.wisc.edu return m_waveguides_->get(name_); 10910447Snilay@cs.wisc.edu } 11010447Snilay@cs.wisc.edu 11110447Snilay@cs.wisc.edu //Get Lasers 11210447Snilay@cs.wisc.edu const Map<OpticalLaser*>* OpticalModel::getLasers() const 11310447Snilay@cs.wisc.edu { 11410447Snilay@cs.wisc.edu return m_lasers_; 11510447Snilay@cs.wisc.edu } 11610447Snilay@cs.wisc.edu 11710447Snilay@cs.wisc.edu OpticalLaser* OpticalModel::getLaser(const String& name_) 11810447Snilay@cs.wisc.edu { 11910447Snilay@cs.wisc.edu return m_lasers_->get(name_); 12010447Snilay@cs.wisc.edu } 12110447Snilay@cs.wisc.edu 12210447Snilay@cs.wisc.edu //Get Modulators 12310447Snilay@cs.wisc.edu const Map<OpticalModulator*>* OpticalModel::getModulators() const 12410447Snilay@cs.wisc.edu { 12510447Snilay@cs.wisc.edu return m_modulators_; 12610447Snilay@cs.wisc.edu } 12710447Snilay@cs.wisc.edu 12810447Snilay@cs.wisc.edu OpticalModulator* OpticalModel::getModulator(const String& name_) 12910447Snilay@cs.wisc.edu { 13010447Snilay@cs.wisc.edu return m_modulators_->get(name_); 13110447Snilay@cs.wisc.edu } 13210447Snilay@cs.wisc.edu 13310447Snilay@cs.wisc.edu //Get Filters 13410447Snilay@cs.wisc.edu const Map<OpticalFilter*>* OpticalModel::getFilters() const 13510447Snilay@cs.wisc.edu { 13610447Snilay@cs.wisc.edu return m_filters_; 13710447Snilay@cs.wisc.edu } 13810447Snilay@cs.wisc.edu 13910447Snilay@cs.wisc.edu OpticalFilter* OpticalModel::getFilter(const String& name_) 14010447Snilay@cs.wisc.edu { 14110447Snilay@cs.wisc.edu return m_filters_->get(name_); 14210447Snilay@cs.wisc.edu } 14310447Snilay@cs.wisc.edu 14410447Snilay@cs.wisc.edu //Get Detectors 14510447Snilay@cs.wisc.edu const Map<OpticalDetector*>* OpticalModel::getDetectors() const 14610447Snilay@cs.wisc.edu { 14710447Snilay@cs.wisc.edu return m_detectors_; 14810447Snilay@cs.wisc.edu } 14910447Snilay@cs.wisc.edu 15010447Snilay@cs.wisc.edu OpticalDetector* OpticalModel::getDetector(const String& name_) 15110447Snilay@cs.wisc.edu { 15210447Snilay@cs.wisc.edu return m_detectors_->get(name_); 15310447Snilay@cs.wisc.edu } 15410447Snilay@cs.wisc.edu 15510447Snilay@cs.wisc.edu //Get Inputs 15610447Snilay@cs.wisc.edu const Map<PortInfo*>* OpticalModel::getOpticalInputs() const 15710447Snilay@cs.wisc.edu { 15810447Snilay@cs.wisc.edu return m_optical_input_ports_; 15910447Snilay@cs.wisc.edu } 16010447Snilay@cs.wisc.edu 16110447Snilay@cs.wisc.edu PortInfo* OpticalModel::getOpticalInputPort(const String& name_) 16210447Snilay@cs.wisc.edu { 16310447Snilay@cs.wisc.edu ASSERT(m_optical_input_ports_->keyExist(name_), "[Error] " + getInstanceName() + 16410447Snilay@cs.wisc.edu " -> Input port (" + name_ + ") does not exist"); 16510447Snilay@cs.wisc.edu 16610447Snilay@cs.wisc.edu return m_optical_input_ports_->get(name_); 16710447Snilay@cs.wisc.edu } 16810447Snilay@cs.wisc.edu 16910447Snilay@cs.wisc.edu const PortInfo* OpticalModel::getOpticalInputPort(const String& name_) const 17010447Snilay@cs.wisc.edu { 17110447Snilay@cs.wisc.edu ASSERT(m_optical_input_ports_->keyExist(name_), "[Error] " + getInstanceName() + 17210447Snilay@cs.wisc.edu " -> Input port (" + name_ + ") does not exist"); 17310447Snilay@cs.wisc.edu 17410447Snilay@cs.wisc.edu return m_optical_input_ports_->get(name_); 17510447Snilay@cs.wisc.edu } 17610447Snilay@cs.wisc.edu 17710447Snilay@cs.wisc.edu //Get Outputs 17810447Snilay@cs.wisc.edu const Map<PortInfo*>* OpticalModel::getOpticalOutputs() const 17910447Snilay@cs.wisc.edu { 18010447Snilay@cs.wisc.edu return m_optical_output_ports_; 18110447Snilay@cs.wisc.edu } 18210447Snilay@cs.wisc.edu 18310447Snilay@cs.wisc.edu PortInfo* OpticalModel::getOpticalOutputPort(const String& name_) 18410447Snilay@cs.wisc.edu { 18510447Snilay@cs.wisc.edu ASSERT(m_optical_output_ports_->keyExist(name_), "[Error] " + getInstanceName() + 18610447Snilay@cs.wisc.edu " -> Input port (" + name_ + ") does not exist"); 18710447Snilay@cs.wisc.edu 18810447Snilay@cs.wisc.edu return m_optical_output_ports_->get(name_); 18910447Snilay@cs.wisc.edu } 19010447Snilay@cs.wisc.edu 19110447Snilay@cs.wisc.edu const PortInfo* OpticalModel::getOpticalOutputPort(const String& name_) const 19210447Snilay@cs.wisc.edu { 19310447Snilay@cs.wisc.edu ASSERT(m_optical_output_ports_->keyExist(name_), "[Error] " + getInstanceName() + 19410447Snilay@cs.wisc.edu " -> Input port (" + name_ + ") does not exist"); 19510447Snilay@cs.wisc.edu 19610447Snilay@cs.wisc.edu return m_optical_output_ports_->get(name_); 19710447Snilay@cs.wisc.edu } 19810447Snilay@cs.wisc.edu 19910447Snilay@cs.wisc.edu //------------------------------------------------------------------------- 20010447Snilay@cs.wisc.edu // Optical Connectivity Creation Functions 20110447Snilay@cs.wisc.edu //------------------------------------------------------------------------- 20210447Snilay@cs.wisc.edu void OpticalModel::createOpticalInputPort(const String& name_, const WavelengthGroup& wavelength_group_) 20310447Snilay@cs.wisc.edu { 20410447Snilay@cs.wisc.edu // Create the new waveguides 20510447Snilay@cs.wisc.edu // This should already check that it has not been previously declared 20610447Snilay@cs.wisc.edu createWaveguide(name_, wavelength_group_); 20710447Snilay@cs.wisc.edu // Add the waveguide name to list of input ports 20810447Snilay@cs.wisc.edu m_optical_input_ports_->set(name_, new PortInfo(name_, wavelength_group_)); 20910447Snilay@cs.wisc.edu return; 21010447Snilay@cs.wisc.edu } 21110447Snilay@cs.wisc.edu 21210447Snilay@cs.wisc.edu void OpticalModel::createOpticalOutputPort(const String& name_, const WavelengthGroup& wavelength_group_) 21310447Snilay@cs.wisc.edu { 21410447Snilay@cs.wisc.edu // Create the new waveguides (including its waveguide reference) 21510447Snilay@cs.wisc.edu // This should already check that it has not been previously declared 21610447Snilay@cs.wisc.edu createWaveguide(name_, wavelength_group_); 21710447Snilay@cs.wisc.edu // Add the waveguide name to list of output ports 21810447Snilay@cs.wisc.edu m_optical_output_ports_->set(name_, new PortInfo(name_, wavelength_group_)); 21910447Snilay@cs.wisc.edu return; 22010447Snilay@cs.wisc.edu } 22110447Snilay@cs.wisc.edu 22210447Snilay@cs.wisc.edu // Waveguide creation 22310447Snilay@cs.wisc.edu void OpticalModel::createWaveguide(const String& name_, const WavelengthGroup& wavelengths_) 22410447Snilay@cs.wisc.edu { 22510447Snilay@cs.wisc.edu // Check that the waveguide hasn't been previously declared 22610447Snilay@cs.wisc.edu ASSERT( !m_waveguides_->keyExist(name_), "[Error] " + getInstanceName() + 22710447Snilay@cs.wisc.edu " -> Redeclaration of waveguide " + name_); 22810447Snilay@cs.wisc.edu m_waveguides_->set(name_, new OpticalWaveguide(name_, this, wavelengths_)); 22910447Snilay@cs.wisc.edu return; 23010447Snilay@cs.wisc.edu } 23110447Snilay@cs.wisc.edu 23210447Snilay@cs.wisc.edu // Laser creation 23310447Snilay@cs.wisc.edu void OpticalModel::createLaser(const String& name_, const WavelengthGroup& wavelengths_) 23410447Snilay@cs.wisc.edu { 23510447Snilay@cs.wisc.edu // Check that the laser hasn't been previously declared 23610447Snilay@cs.wisc.edu ASSERT( !m_lasers_->keyExist(name_), "[Error] " + getInstanceName() + 23710447Snilay@cs.wisc.edu " -> Redeclaration of laser " + name_); 23810447Snilay@cs.wisc.edu m_lasers_->set(name_, new OpticalLaser(name_, this, wavelengths_)); 23910447Snilay@cs.wisc.edu return; 24010447Snilay@cs.wisc.edu } 24110447Snilay@cs.wisc.edu 24210447Snilay@cs.wisc.edu // Modulator creation 24310447Snilay@cs.wisc.edu void OpticalModel::createModulator(const String& name_, const WavelengthGroup& wavelengths_, bool opt_loss_, OpticalTransmitter* transmitter_) 24410447Snilay@cs.wisc.edu { 24510447Snilay@cs.wisc.edu // Check that the modulator hasn't been previously declared 24610447Snilay@cs.wisc.edu ASSERT( !m_modulators_->keyExist(name_), "[Error] " + getInstanceName() + 24710447Snilay@cs.wisc.edu " -> Redeclaration of modulator " + name_); 24810447Snilay@cs.wisc.edu m_modulators_->set(name_, new OpticalModulator(name_, this, wavelengths_, opt_loss_, transmitter_)); 24910447Snilay@cs.wisc.edu return; 25010447Snilay@cs.wisc.edu } 25110447Snilay@cs.wisc.edu 25210447Snilay@cs.wisc.edu // Modulator Multiplier creation 25310447Snilay@cs.wisc.edu void OpticalModel::createFilter(const String& name_, const WavelengthGroup& wavelengths_, bool drop_all_, const WavelengthGroup& drop_wavelengths_) 25410447Snilay@cs.wisc.edu { 25510447Snilay@cs.wisc.edu // Check that the filter hasn't been previously declared 25610447Snilay@cs.wisc.edu ASSERT( !m_filters_->keyExist(name_), "[Error] " + getInstanceName() + 25710447Snilay@cs.wisc.edu " -> Redeclaration of filter " + name_); 25810447Snilay@cs.wisc.edu m_filters_->set(name_, new OpticalFilter(name_, this, wavelengths_, drop_all_, drop_wavelengths_)); 25910447Snilay@cs.wisc.edu return; 26010447Snilay@cs.wisc.edu } 26110447Snilay@cs.wisc.edu 26210447Snilay@cs.wisc.edu // Detector creation 26310447Snilay@cs.wisc.edu void OpticalModel::createDetector(const String& name_, const WavelengthGroup& wavelengths_, OpticalReceiver* receiver_) 26410447Snilay@cs.wisc.edu { 26510447Snilay@cs.wisc.edu // Check that the detector hasn't been previously declared 26610447Snilay@cs.wisc.edu ASSERT( !m_detectors_->keyExist(name_), "[Error] " + getInstanceName() + 26710447Snilay@cs.wisc.edu " -> Redeclaration of detector " + name_); 26810447Snilay@cs.wisc.edu m_detectors_->set(name_, new OpticalDetector(name_, this, wavelengths_, receiver_)); 26910447Snilay@cs.wisc.edu return; 27010447Snilay@cs.wisc.edu } 27110447Snilay@cs.wisc.edu 27210447Snilay@cs.wisc.edu //------------------------------------------------------------------------- 27310447Snilay@cs.wisc.edu 27410447Snilay@cs.wisc.edu // Assign a waveguide to be downstream from another waveguide 27510447Snilay@cs.wisc.edu // assign downtream_waveguide_name_ = upstream_waveguide_name_ 27610447Snilay@cs.wisc.edu void OpticalModel::opticalAssign(const String& downstream_waveguide_name_, const String& upstream_waveguide_name_) 27710447Snilay@cs.wisc.edu { 27810447Snilay@cs.wisc.edu ASSERT(getWaveguides()->keyExist(downstream_waveguide_name_), "[Error] " + getInstanceName() + " -> Waveguide '" + 27910447Snilay@cs.wisc.edu downstream_waveguide_name_ + "' does not exist!"); 28010447Snilay@cs.wisc.edu 28110447Snilay@cs.wisc.edu ASSERT(getWaveguides()->keyExist(upstream_waveguide_name_), "[Error] " + getInstanceName() + " -> Waveguide '" + 28210447Snilay@cs.wisc.edu upstream_waveguide_name_ + "' does not exist!"); 28310447Snilay@cs.wisc.edu 28410447Snilay@cs.wisc.edu // Get the two waveguides 28510447Snilay@cs.wisc.edu OpticalWaveguide* upstream_waveguide = getWaveguide(upstream_waveguide_name_); 28610447Snilay@cs.wisc.edu OpticalWaveguide* downstream_waveguide = getWaveguide(downstream_waveguide_name_); 28710447Snilay@cs.wisc.edu 28810447Snilay@cs.wisc.edu // Check that the two waveguides expect the same wavelengths 28910447Snilay@cs.wisc.edu ASSERT((upstream_waveguide->getWavelengths().first == downstream_waveguide->getWavelengths().first) && 29010447Snilay@cs.wisc.edu (upstream_waveguide->getWavelengths().second == downstream_waveguide->getWavelengths().second), 29110447Snilay@cs.wisc.edu "[Error] " + getInstanceName() + " -> Assignment expects different wavelengths for waveguide '" + 29210447Snilay@cs.wisc.edu upstream_waveguide_name_ + "' and waveguide '" + downstream_waveguide_name_ + "'!"); 29310447Snilay@cs.wisc.edu 29410447Snilay@cs.wisc.edu // Connect the downstream waveguide and the upstream waveguide 29510447Snilay@cs.wisc.edu upstream_waveguide->addDownstreamNode(downstream_waveguide); 29610447Snilay@cs.wisc.edu return; 29710447Snilay@cs.wisc.edu } 29810447Snilay@cs.wisc.edu} // namespace DSENT 299