RINASim  October 2016
Documentation of framework for OMNeT++
SimpleTORForwarding.cc
Go to the documentation of this file.
1 // The MIT License (MIT)
2 //
3 // Copyright (c) 2014-2016 Brno University of Technology, PRISTINE project
4 //
5 // Permission is hereby granted, free of charge, to any person obtaining a copy
6 // of this software and associated documentation files (the "Software"), to deal
7 // in the Software without restriction, including without limitation the rights
8 // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 // copies of the Software, and to permit persons to whom the Software is
10 // furnished to do so, subject to the following conditions:
11 //
12 // The above copyright notice and this permission notice shall be included in
13 // all copies or substantial portions of the Software.
14 //
15 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21 // THE SOFTWARE.
22 
23 #include "SimpleTORForwarding.h"
24 #include <sstream>
25 #include "Utils.h"
26 
27 namespace NSPSimpleDC {
28 
29  Register_Class(SimpleTORForwarding);
30 
31  using namespace std;
32 
33  tFWDEntry::tFWDEntry() : entryType(false), inverseStorage(false) {}
34 
35 
37  upCount = par("upCount").longValue();
38  if(upCount < 0) { upCount = 0; }
39  portsArray = new Port[upCount];
40  for(int i = 0; i<upCount; i++) { portsArray[i] = nullptr; }
41  }
42 
43  vector<Port> SimpleTORForwarding::search(const DCAddr & n_addr) {
44  if(Im == n_addr) { return vector<Port>(); }
45  if(n_addr.type < 0 || n_addr.type > 3) {
46  cerr << "Invalid dst addr ("<<n_addr<< ")" << endl;
47  return vector<Port>();
48  }
49 
50  auto r = table.find(n_addr);
51  if(r != table.end()) {
52  auto & e = r->second;
53  if(!e.entryType) { return vector<Port>(); }
54 
55  vector<Port> ret;
56  for(int i = 0; i<upCount; i++) {
57  Port p = portsArray[i];
58  if(e.inverseStorage == (e.ports.find(p) == e.ports.end()) ) {
59  ret.push_back(p);
60  }
61  }
62  return ret;
63  }
64 
65  switch(n_addr.type) {
66  case 1:
67  case 3:
68  if(n_addr.b < upCount && portsArray[n_addr.b]!= nullptr) {
69  vector<Port> ret;
70  ret.push_back(portsArray[n_addr.b]);
71  return ret;
72  } else { cerr << "!!!" << endl;}
73  break;
74  case 2:
75  if(n_addr.a < upCount && portsArray[n_addr.a]!= nullptr) {
76  vector<Port> ret;
77  ret.push_back(portsArray[n_addr.a]);
78  return ret;
79  } else { cerr << "!!!" << endl;}
80  break;
81  }
82  return upV;
83  }
84 
85 
86  bool SimpleTORForwarding::setNeigh(const DCAddr & n_addr, Port port) {
87  if(n_addr.type != 1 || Im.a != n_addr.a || n_addr.b >= upCount) {
88  cerr << "Invalid neighbour ("<<n_addr<< ") found for TOR " << Im<<endl;
89  return false;
90  }
91 
92  Port t = portsArray[n_addr.b];
93  if(portsArray[n_addr.b] == port) { return true; }
94  portsArray[n_addr.b] = port;
95 
96 
97  upV.clear();
98  for(int i = 0; i<upCount; i++) {
99  if(portsArray[i]!= nullptr) {
100  upV.push_back(portsArray[i]);
101  }
102  }
103 
104 
105  for(auto & e : table) {
106  if(e.second.ports.find(t) != e.second.ports.end()) {
107  e.second.ports.erase(t);
108  if(port != nullptr) {
109  e.second.ports.insert(port);
110  }
111  }
112  }
113  refreshCache (t, port);
114  return true;
115  }
116 
117  void SimpleTORForwarding::setDst(const DCAddr & n_addr, const set<DCAddr> & next) {
118  if(n_addr == Im) { return; }
119 
120  if(n_addr.type < 0 || n_addr.type > 3) {
121  cerr << "Invalid dst addr ("<<n_addr<< ")" << endl;
122  return;
123  }
124 
125  int S = next.size();
126 
127  if(S == 0) {
128  table[n_addr] = tFWDEntry();
129  return;
130  }
131 
132  set<int> pIds;
133  for(const auto & n : next) {
134  pIds.insert(n.b);
135  }
136 
137  switch(n_addr.type) {
138  case 0:
139  if(S == upCount) {
140  table.erase(n_addr);
141  refreshCache (n_addr);
142  return;
143  } break;
144  case 1:
145  case 3:
146  if(S == 1 && pIds.find(n_addr.b) != pIds.end() ){
147  table.erase(n_addr);
148  refreshCache (n_addr);
149  return;
150  }
151  break;
152  case 2:
153  if(S == 1 && pIds.find(n_addr.a) != pIds.end() ){
154  table.erase(n_addr);
155  refreshCache (n_addr);
156  return;
157  }
158  break;
159  }
160 
161  table[n_addr] = getFWDEntry(pIds);
162 
163  refreshCache (n_addr);
164  }
165 
167  tFWDEntry ret;
168  ret.entryType = true;
169  ret.inverseStorage = ((int)pIds.size()*2 > upCount);
170 
171  for(int i = 0; i< upCount; i++) {
172  if(ret.inverseStorage == (pIds.find(i) == pIds.end())) {
173  ret.ports.insert(portsArray[i]);
174  }
175  }
176  return ret;
177  }
178 
180  if(par("printAtEnd").boolValue()) {
181  cout << "-----------------------" << endl;
182  cout << "SimpleTORForwarding at "<< endl;
183  cout << " " << getFullPath() << endl;
184 
185  cout << "I'm TOR "<< Im << endl;
186  if(upCount > 0) {
187  cout << "\tUp neighbours:" << endl;
188  for(int i = 0; i < upCount; i++) {
189  cout << "\t\t1."<<Im.a<<"."<<i<<" -> Status "<< (portsArray[i]!=nullptr? "ON":"OFF") << endl;
190  }
191  }
192  if(table.empty()) {
193  cout << "\tNo entries stored" << endl;
194  } else {
195  cout << "Stored entries " << table.size() << endl;
196  for(auto & e : table) {
197  cout <<"\t\t"<< e.first << " -- ";
198  if(e.second.entryType == false) {
199  cout << "Unreachable";
200  } else {
201  if(e.second.inverseStorage) {
202  cout << "(inverse) ";
203  }
204  cout << e.second.ports.size() << " stored ports:";
205  }
206  cout << endl;
207  for(auto &k : e.second.ports) {
208  cout << "\t\t\t" << k->getFullPath() << endl;
209  }
210  }
211  }
212  }
213 
214  delete portsArray;
215  }
216 
217 }
bool entryType
Register_Class(SimpleDCGenerator)
void setDst(const DCAddr &n_addr, const set< DCAddr > &next)
virtual void refreshCache(Port oldP, Port newP)
tFWDEntry getFWDEntry(const set< int > &pIds)
tFWDEntry()
map< DCAddr, tFWDEntry > table
vector< Port > search(const DCAddr &n_addr)
bool inverseStorage
set< Port > ports
bool setNeigh(const DCAddr &n_addr, Port port)