TTEthernet Model for INET Framework
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
TTEInput.cc
Go to the documentation of this file.
1 //
2 // This program is free software: you can redistribute it and/or modify
3 // it under the terms of the GNU Lesser General Public License as published by
4 // the Free Software Foundation, either version 3 of the License, or
5 // (at your option) any later version.
6 //
7 // This program is distributed in the hope that it will be useful,
8 // but WITHOUT ANY WARRANTY; without even the implied warranty of
9 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 // GNU Lesser General Public License for more details.
11 //
12 // You should have received a copy of the GNU Lesser General Public License
13 // along with this program. If not, see http://www.gnu.org/licenses/.
14 //
15 
16 #include "TTEInput.h"
17 #include "TTEScheduler.h"
18 
19 #include "Buffer.h"
20 
21 #include <iostream>
22 
23 using namespace TTEthernetModel;
24 
26 
27 simsignal_t TTEInput::ctDroppedSignal = SIMSIGNAL_NULL;
28 
30  hadError=false;
31 }
32 
34 {
35  ctDroppedSignal = registerSignal("ctDropped");
36 }
37 
38 //void TTEInput::addIncoming(uint16 ctID, Incoming *incoming)
39 //{
40 // incomings[ctID].push_back(incoming);
41 //}
42 
43 void TTEInput::handleMessage(cMessage *msg)
44 {
45  if (msg->arrivedOn("in"))
46  {
47  EtherFrame *frame = (EtherFrame*) msg;
48 
49  int i = msg->findPar("received");
50  cMsgPar* par;
51  if( i >=0 )
52  par = &msg->par(i);
53  else
54  par = &msg->addPar("received");
55  par->setLongValue(((TTEScheduler*)getParentModule()->getParentModule()->getSubmodule("tteScheduler"))->getTicks());
56 
57  i = msg->findPar("received_total");
58  if( i >=0 )
59  par = &msg->par(i);
60  else
61  par = &msg->addPar("received_total");
62  par->setLongValue(((TTEScheduler*)getParentModule()->getParentModule()->getSubmodule("tteScheduler"))->getTotalTicks());
63 
64 
65  i = msg->findPar("received_port");
66  if( i >=0 )
67  par = &msg->par(i);
68  else
69  par = &msg->addPar("received_port");
70  par->setLongValue(getParentModule()->getIndex());
71 
72  //Auf CTCs verteilen oder BE traffic
73  if (isCT(frame))
74  {
75  std::map<uint16_t, std::list<Incoming *> >::iterator incomingList = incomings.find(getCTID(frame));
76  if (incomingList != incomings.end())
77  {
78  //Send to all CTCs for the CT-ID
79  for (std::list<Incoming*>::iterator incoming = incomingList->second.begin(); incoming
80  != incomingList->second.end(); incoming++)
81  {
82  sendDirect(frame->dup(), (*incoming)->gate("in"));
83  }
84  delete frame;
85  }
86  else
87  {
88  emit(ctDroppedSignal, 1);
89  hadError=true;
90  if(ev.isGUI()){
91  bubble("No matching buffer configured");
92  getDisplayString().setTagArg("i2", 0, "status/excl3");
93  getDisplayString().setTagArg("tt", 0, "WARNING: Input configuration problem - No matching buffer configured");
94  getParentModule()->getDisplayString().setTagArg("i2", 0, "status/excl3");
95  getParentModule()->getDisplayString().setTagArg("tt", 0, "WARNING: Input configuration problem - No matching buffer configured");
96  getParentModule()->getParentModule()->getDisplayString().setTagArg("i2", 0, "status/excl3");
97  getParentModule()->getParentModule()->getDisplayString().setTagArg("tt", 0, "WARNING: Input configuration problem - No matching buffer configured");
98  }
99  delete frame;
100  }
101  }
102  //Sonst BE
103  else
104  {
105  if(promiscuous || frame->getDest().isMulticast()){
106  send(msg, "out");
107  }
108  else{
109  MACAddress address;
110  address.setAddress(frame->getArrivalGate()->getPathStartGate()->getOwnerModule()->par("address"));
111  if(frame->getDest().equals(address)){
112  send(msg, "out");
113  }
114  else{
115  delete msg;
116  }
117  }
118  }
119  }
120 }
121 
122 void TTEInput::handleParameterChange(const char* parname){
123  ctMask = (uint32_t)par("ct_mask").longValue();
124  ctMarker = (uint32_t)par("ct_marker").longValue();
125  promiscuous = par("promiscuous").boolValue();
126 
127  incomings.clear();
128 
129  std::string incomingsString = par("incomings").stdstringValue();
130  std::vector<std::string> incomingPaths;
131  split(incomingsString,',',incomingPaths);
132  for(std::vector<std::string>::iterator incomingPath = incomingPaths.begin();
133  incomingPath!=incomingPaths.end();incomingPath++){
134  cModule* module = simulation.getModuleByPath((*incomingPath).c_str());
135  if(module){
136  Incoming *incoming = dynamic_cast<Incoming*> (module);
137  if(incoming){
138  Buffer *buffer = dynamic_cast<Buffer*> (incoming->gate("out")->getPathEndGate()->getOwner());
139  if(buffer && buffer->hasPar("ct_id")){
140  incomings[buffer->par("ct_id").longValue()].push_back(incoming);
141  }
142  }
143  }
144  else{
145  if(ev.isGUI()){
146  ev<<"Configuration problem: Module "<<(*incomingPath)<<" could not be resolved or is no Incoming CTC Module, or module is not connected to a buffer!"<<endl;
147  getDisplayString().setTagArg("i2", 0, "status/excl3");
148  getDisplayString().setTagArg("tt", 0, "WARNING: Configuration Problem Input Buffers!");
149  }
150  }
151  }
152 }
153 
154 bool TTEInput::isCT(EtherFrame *frame)
155 {
156  unsigned char macBytes[6];
157  frame->getDest().getAddressBytes(macBytes);
158  //Check for ct
159  if ((((macBytes[0] << 24) | (macBytes[1] << 16) | (macBytes[2] << 8) | (macBytes[3])) & ctMask) == (ctMarker
160  & ctMask))
161  {
162  return true;
163  }
164  //TODO More checking ?
165  return false;
166 }
167 
168 uint16_t TTEInput::getCTID(EtherFrame *frame)
169 {
170  unsigned char macBytes[6];
171  frame->getDest().getAddressBytes(macBytes);
172  return (macBytes[4] << 8) | macBytes[5];
173 }