Statistics
| Branch: | Revision:

mobicen / varie / util / Node.py @ 9110387b

History | View | Annotate | Download (5.17 KB)

1
from prettytable import PrettyTable
2
import os
3
import EventScheduler
4
import MyUtil
5
import code
6

    
7

    
8
class Node(object):
9

    
10
    def __init__(self, name, outFolder):
11
        self.name = name
12
        # RoutingTable {destName:{'distance':float, 'NHs':[lista dei next-hop equivalenti]}}
13
        self.RT = {}
14
        self.RT[name] = {'distance': 0.0, 'NHs': [name]}
15
        self.neighs = {}  # key: neigh_name, linkCost: attributes of neigh eg{'weight':float}
16
        self.bufferedDV = {}
17

    
18
    def set_Neighbours(self, neighs):
19
        self.neighs.update(neighs)
20

    
21
    def getLinkCost(self, v):
22
        if (v in self.neighs):
23
            try:
24
                return float(self.neighs[v]['weight'])
25
            except KeyError:
26
                return 1.0
27
        return 1000.0
28

    
29

    
30
class PopNode(Node):
31

    
32
    def __init__(self, name, outFolder):
33
        Node.__init__(self, name, outFolder)
34
        # DestinationTable {destName: {'contribs':{neigh: contrib}, 'Load':load of dest}}
35
        self.DT = {name: {'contribs': {}, 'Load': 0.0}}
36

    
37
    def printNode(self):
38
        print "PopNode: "+self.name + " - Load: "+str(self.computeCentrality())
39
        t = PrettyTable(['DEST', 'NHs', 'CONTRs', 'Load'])
40
        for d in self.RT:
41
            contr_string = ""
42
            try:
43
                contributors = self.DT[d]['contribs']
44
                contr_string = str(contributors)
45
            except:
46
                contr_string = "[//]"
47
                pass
48
            t.add_row([str(d), self.RT[d]['NHs'],
49
                       contr_string, str(self.DT[d]['Load'])])
50
        print t
51

    
52
    # send DV to all neighbours and schedule next sending
53
    def sendDV(self):
54
        # update centrality
55
        myCentr = self.computeCentrality()
56
        # prepare DV as dict {dest_name:(distance,CentrInfo=(NHs,contribute,Load))}
57
        toSend = {}
58

    
59
        for dest in self.RT:
60
            dist = self.RT[dest]['distance']
61
            NHs = self.RT[dest]['NHs']
62
            Load = -1.0
63
            try:
64
                Load = self.DT[dest]['Load']
65
            except:
66
                pass
67
            mycontr = 1.0  # my contributes for any dest is at least 1, counting for me
68
            try:
69
                contributors = self.DT[dest]['contribs']
70
                mycontr = 1.0 + sum(self.DT[dest]['contribs'].values())
71
            except KeyError:
72
                # if I know dest but I do not have any contributes for it
73
                pass
74
            # Split contributes before sending them
75
            splitcontr = mycontr / len(NHs)
76
            # CentrInfo = (creator, creator_dist, splitcontr, load)
77
            toSend[dest] = (dist, (self.name, dist, splitcontr, Load))
78

    
79
        return toSend
80

    
81
    def processRecInfo(self, time, senderName, DV):
82

    
83
        myCentr = self.computeCentrality()
84
        lc = self.getLinkCost(senderName)
85

    
86
        for dest in DV:
87
            '''if (dest==self.name):
88
                continue'''
89
            adv_dist = DV[dest][0]
90
            # Bellman-Ford (multi  NHs)
91
            if dest not in self.RT:
92
                self.RT[dest] = {
93
                    'distance': adv_dist + lc, 'NHs': [senderName]}
94
                self.DT[dest] = {'contribs': {}, 'Load': 0.0}
95
            else:
96
                cdist = self.RT[dest]['distance']
97
                if (adv_dist + lc <= cdist):
98
                    if (adv_dist + lc < cdist):
99
                        self.RT[dest]['distance'] = adv_dist + lc
100
                        self.RT[dest]['NHs'] = [senderName]
101
                    elif (adv_dist + lc == cdist):
102
                        if (senderName not in self.RT[dest]['NHs']):
103
                            self.RT[dest]['NHs'].append(senderName)
104

    
105
        # END Bellman-Ford, now RT is up-to-date
106

    
107
        # Guerrieri + contributions intercepting
108
        for dest in DV:
109
            try:
110
                CentrInfo = DV[dest][1]
111
            except IndexError as e:
112
                # No CentrInfo
113
                pass
114
            else:
115
                creator = CentrInfo[0]
116
                rdist = CentrInfo[1]
117
                splitcontr = CentrInfo[2]
118
                Load = CentrInfo[3]
119

    
120
                cdist = self.RT[dest]['distance']
121
                try:
122
                    rcost = self.RT[creator]['distance']
123
                except:
124
                    rcost = 1000000.0
125

    
126
                if (cdist < rdist and (rdist >= cdist + rcost)):
127
                    # self.updateContributors(senderName, dest, splitcontr + tutor_addend) #con tutoring vicini Legacy
128
                    # senza tutoring vicini Legacy
129
                    self.updateContributors(senderName, dest, splitcontr)
130
                else:
131
                    self.removeContr(senderName, dest)
132

    
133
                if (rdist < cdist):
134
                    self.DT[dest]['Load'] = Load
135

    
136
    def computeCentrality(self):
137
        tot = 0.0
138
        for d in self.DT:
139
            if (d != self.name):
140
                part = sum(self.DT[d]['contribs'].values())
141
                tot += part
142
        self.DT[self.name]['Load'] = float(tot)
143
        return float(tot)
144

    
145
    def updateContributors(self, neighName, dest, contr):
146
        self.DT[dest]['contribs'][neighName] = contr
147

    
148
    def removeContr(self, neighName, dest):
149
        if neighName in self.DT[dest]['contribs']:
150
            self.DT[dest]['contribs'].pop(neighName)