28 inline void insert1(
const string & dst,
const T & m){ op1.insert(dst); m1 = m;}
29 inline void insert2(
const string & dst,
const T & m){ op2.insert(dst); m2 = m;}
30 inline void erase1(
const string & dst){ op1.erase(dst);}
31 inline void erase2(
const string & dst){ op2.erase(dst);}
34 inline void swap() {T tm = m1; m1 = m2; m2 = tm; set<string> td = op1; op1 = op2; op2 = td; }
36 unsigned char addEntry(
const string & dst,
const T &m) {
39 insert1(dst, m);
return CHBOTH;
40 }
else if(op2.empty()){
41 if(op1.find(dst) != op1.end()){
45 insert1(dst, m);
return CHBOTH;
52 erase1(dst); swap(); insert1(dst, m);
return CHBOTH;
55 erase1(dst); insert2(dst, m);
return (op1.size() > 2)?
CH1OPT :
CHBOTH;
63 swap(); insert1(dst, m);
return CHBOTH;
66 insert2(dst, m);
return (op1.size() > 1)?
NOCH :
CHMET;
68 insert1(dst, m);
return CH1OPT;
71 }
else if(op1.find(dst) != op1.end()){
77 erase1(dst); insert1(dst, m);
return CHBOTH;
80 clear1(); swap(); insert1(dst, m);
return CHBOTH;
88 erase1(dst); clear2(); swap(); insert1(dst, m);
return CHBOTH;
93 erase1(dst); clear2(); insert2(dst, m);
return (op1.size() > 2)?
CH1OPT :
CHBOTH;
96 erase1(dst); insert2(dst, m);
return (op1.size() > 2)?
CH1OPT :
CHBOTH;
102 }
else if(op2.find(dst) != op2.end()){
103 if(op2.size() == 1) {
107 }
else if( m == m1) {
109 clear2(); insert1(dst, m);
return (op1.size() > 2)?
CH1OPT :
CHBOTH;
110 }
else if( m != m2) {
112 insert2(dst, m);
return (op1.size() > 1)?
NOCH :
CHMET;
119 clear2(); swap(); insert1(dst, m);
return CHBOTH;
120 }
else if( m == m1) {
122 erase2(dst); insert1(dst, m);
return (op1.size() > 2)?
CH1OPT :
CHBOTH;
125 clear2(); insert2(dst, m);
return (op1.size() > 1)?
NOCH :
CHMET;
126 }
else if( m == m2) {
130 erase2(dst);
return NOCH;
136 clear2(); swap(); insert1(dst, m);
return CHBOTH;
137 }
else if( m == m1) {
139 insert1(dst, m);
return (op1.size() > 2)?
CH1OPT :
CHBOTH;
142 clear2(); insert2(dst, m);
return (op1.size() > 1)?
NOCH :
CHMET;
143 }
else if( m == m2) {
145 insert2(dst, m);
return NOCH;
154 if(op1.find(dst) != op1.end()){
155 if(op1.size() == 1) {
156 clear1(); swap();
return CHBOTH;
160 }
else if(op2.find(dst) != op2.end()){
161 erase2(dst);
return (op1.size() > 1)?
NOCH :
CHMET;
208 virtual void addFlow(
const Address &_nAddr,
const string &_addr,
const T &_metric){
210 if(oldM == _metric) {
return; }
214 unsigned char result = table[_addr].addEntry(_addr, _metric);
215 if(result &
CH1OPT) { changed.insert(_addr); }
217 rtEntry * oldE = &neiState[_addr];
219 T Dm = _metric - oldM;
220 for(
auto & entry : oldE->
entries){
222 unsigned char eResult = table[entry.first].addEntry(_addr, entry.second);
223 if(eResult & CH1OPT) { changed.insert(entry.first); }
233 unsigned char result = table[_addr].removeEntry(_addr);
234 if(result &
CH1OPT) { changed.insert(_addr); }
236 rtEntry oldE = neiState[_addr];
238 for(
const auto & entry : oldE.
entries){
239 unsigned char eResult = table[entry.first].removeEntry(_addr);
240 if(eResult & CH1OPT) { changed.insert(entry.first); }
244 neiState.erase(_addr);
250 if(
DV_Update * up = dynamic_cast<DV_Update*>(update)) {
258 rtEntry oldE = neiState[up->src];
259 if(oldE.
sId >= up->entries.sId) {
return false; }
261 unsigned char result = 0;
263 for(
const auto & entry : up->entries.entries){
266 unsigned char eResult = table[entry.first].addEntry(up->src, entry.second);
267 if(eResult &
CH1OPT) { changed.insert(entry.first); }
272 for(
const auto & entry : oldE.
entries){
273 if(up->entries.entries.find(entry.first) == up->entries.entries.end()){
274 unsigned char eResult = table[entry.first].removeEntry(up->src);
275 if(eResult &
CH1OPT) { changed.insert(entry.first); }
281 neiState[up->src] = up->
entries;
299 for(
const auto & en : table){
300 if(neig.first == en.first) {
continue; }
303 if(en.second.op1.size() >= 2 ) {
306 }
else if(en.second.op1.size() == 1) {
307 if(en.second.op1.find(neig.first) == en.second.op1.end()){
310 }
else if(!en.second.op2.empty()) {
317 entry.
entries[en.first] = cMet + linkM;
335 map<string, nhLMetric<T> > ret;
336 for(
const auto & dst : changed) {
337 Entry * e = &table[dst];
344 virtual map<string, nhLMetric<T> >
getAll() {
345 map<string, nhLMetric<T> > ret;
346 for(
const auto & e : table) {
355 EV <<
"Print nextHops : "<< endl;
356 for(
const auto & e : table) {
357 if(e.second.op1.empty()) {
continue; }
358 EV << e.first <<endl;
359 EV <<
"\t (" << e.second.m1 <<
") ::";
360 for (
string d : e.second.op1) {
361 EV <<
" <" << d <<
">";
364 if(e.second.op2.empty()) {
continue; }
365 EV <<
"\t (" << e.second.m2 <<
") ::";
366 for (
string d : e.second.op2) {
367 EV <<
" <" << d <<
">";
virtual void addFlow(const Address &_nAddr, const string &_addr, const T &_metric)
virtual void sendUpdate()
unsigned char removeEntry(const string &dst)
map< string, Entry > table
virtual map< string, nhLMetric< T > > getChanges()
virtual void addSynonym(const string syn)
virtual void addSynonym(const string syn)
void erase2(const string &dst)
unsigned char addEntry(const string &dst, const T &m)
virtual void removeSynonym(const string syn)
void erase1(const string &dst)
virtual void removeSynonym(const string syn)
virtual void removeFlow(const Address &_nAddr, const string &_addr)
void insert2(const string &dst, const T &m)
map< string, rtEntry > neiState
DV_Module(Routing_Module *p, const Address &_nAddr, const string &_addr, T inf)
DV_Update(const string &s, rtEntry &ent)
virtual void removeFlow(const Address &_nAddr, const string &_addr)
virtual bool processUpdate(Routing_Update *update)
Address class holds IPC Process identification.
virtual map< string, nhLMetric< T > > getAll()
virtual void sendUpdate()
virtual void addFlow(const Address &_nAddr, const string &_addr, const T &_metric)
void insert1(const string &dst, const T &m)