|
degate 0.1.1
|
00001 /* -*-c++-*- 00002 00003 This file is part of the IC reverse engineering tool degate. 00004 00005 Copyright 2008, 2009, 2010 by Martin Schobert 00006 00007 Degate is free software: you can redistribute it and/or modify 00008 it under the terms of the GNU General Public License as published by 00009 the Free Software Foundation, either version 3 of the License, or 00010 any later version. 00011 00012 Degate is distributed in the hope that it will be useful, 00013 but WITHOUT ANY WARRANTY; without even the implied warranty of 00014 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00015 GNU General Public License for more details. 00016 00017 You should have received a copy of the GNU General Public License 00018 along with degate. If not, see <http://www.gnu.org/licenses/>. 00019 00020 */ 00021 00022 #include <ERCNet.h> 00023 00024 using namespace degate; 00025 00026 ERCNet::ERCNet() : 00027 RCBase("net", "Check for unusual net configs.", RC_ERROR) { 00028 } 00029 00030 void ERCNet::run(LogicModel_shptr lmodel) { 00031 clear_rc_violations(); 00032 00033 if(lmodel == NULL) return; 00034 00035 // iterate over nets 00036 for(LogicModel::net_collection::iterator net_iter = lmodel->nets_begin(); 00037 net_iter != lmodel->nets_end(); ++net_iter) { 00038 00039 check_net(lmodel, (*net_iter).second); 00040 } 00041 00042 } 00043 00044 void ERCNet::check_net(LogicModel_shptr lmodel, Net_shptr net) { 00045 00046 unsigned int 00047 in_ports = 0, 00048 out_ports = 0, 00049 inout_ports = 0; 00050 00051 // iterate over all objects from a net 00052 for(Net::connection_iterator c_iter = net->begin(); 00053 c_iter != net->end(); ++c_iter) { 00054 00055 object_id_t oid = *c_iter; 00056 00057 PlacedLogicModelObject_shptr plo = lmodel->get_object(oid); 00058 00059 if(GatePort_shptr gate_port = std::tr1::dynamic_pointer_cast<GatePort>(plo)) { 00060 00061 assert(gate_port->has_template_port() == true); // can't happen 00062 00063 if(gate_port->has_template_port()) { 00064 00065 GateTemplatePort_shptr tmpl_port = gate_port->get_template_port(); 00066 // Count in- and out-ports. Inout-ports must be counted first, because is_*port() will return true 00067 // for inout-ports. 00068 if(tmpl_port->is_inoutport()) inout_ports++; 00069 if(tmpl_port->is_inport()) in_ports++; 00070 else if(tmpl_port->is_outport()) out_ports++; 00071 else { 00072 boost::format f("For the corresponding gate template port of %1% the port " 00073 "direction is undefined."); 00074 f % gate_port->get_descriptive_identifier(); 00075 add_rc_violation(RCViolation_shptr(new RCViolation(gate_port, f.str(), 00076 "undef_port_dir"))); 00077 00078 } 00079 00080 } 00081 00082 } 00083 } 00084 00085 if((in_ports > 0 && out_ports == 0) || (out_ports > 1)) { 00086 00087 for(Net::connection_iterator c_iter = net->begin(); 00088 c_iter != net->end(); ++c_iter) { 00089 00090 object_id_t oid = *c_iter; 00091 PlacedLogicModelObject_shptr plo = lmodel->get_object(oid); 00092 if(GatePort_shptr gate_port = std::tr1::dynamic_pointer_cast<GatePort>(plo)) { 00093 00094 GateTemplatePort_shptr tmpl_port = gate_port->get_template_port(); 00095 std::string error_msg; 00096 std::string rc_class; 00097 00098 if(in_ports > 0 && out_ports == 0) { 00099 boost::format f("In-Port %1% is not feeded. It is only connected " 00100 "with %2% other in-ports."); 00101 f % gate_port->get_descriptive_identifier() % (in_ports - 1); 00102 error_msg = f.str(); 00103 rc_class = "net.not_feeded"; 00104 add_rc_violation(RCViolation_shptr(new RCViolation(gate_port, error_msg, rc_class))); 00105 } 00106 else if(out_ports > 1) { 00107 if(tmpl_port->is_outport()) { 00108 boost::format f("Out-Port %1% is connected with %2% other out-ports."); 00109 f % gate_port->get_descriptive_identifier() % (out_ports - 1); 00110 error_msg = f.str(); 00111 rc_class = "net.outputs_connected"; 00112 add_rc_violation(RCViolation_shptr(new RCViolation(gate_port, error_msg, rc_class))); 00113 } 00114 } 00115 00116 } 00117 } 00118 } 00119 }
1.7.4