- def __init__(self, xid, name, maxrate, maxexemptrate, bytes, exemptbytes):
- self.xid = xid
- self.name = name
- self.reset(maxrate, maxexemptrate, bytes, exemptbytes)
-
- def __repr__(self):
- return self.name
-
- def reset(self, maxrate, maxexemptrate, bytes, exemptbytes):
- """
- Begin a new recording period. Remove caps by restoring limits
- to their default values.
- """
-
- # Reset baseline time
- self.time = time.time()
-
- # Reset baseline byte coutns
- self.bytes = bytes
- self.exemptbytes = exemptbytes
-
- # Query Node Manager for max rate overrides
- (new_maxrate, new_maxexemptrate) = nm.query(self.name, [('nm_net_max_rate', -1), ('nm_net_max_exempt_rate', -1)])
- if new_maxrate != -1:
- new_maxrate *= 1000
- else:
- new_maxrate = default_maxrate
- if new_maxexemptrate != -1:
- new_maxexemptrate *= 1000
- else:
- new_maxexemptrate = default_maxexemptrate
-
- if new_maxrate != maxrate or new_maxexemptrate != maxexemptrate:
- print "%s reset to %s/%s" % \
- (self.name,
- bwlimit.format_tc_rate(new_maxrate),
- bwlimit.format_tc_rate(new_maxexemptrate))
- bwlimit.set(xid = self.xid, maxrate = new_maxrate, maxexemptrate = new_maxexemptrate)
-
- def update(self, maxrate, maxexemptrate, bytes, exemptbytes):
- """
- Update byte counts and check if average rates have been
- exceeded. In the worst case (instantaneous usage of the entire
- average daily byte limit at the beginning of the recording
- period), the slice will be immediately capped and will get to
- send twice the average daily byte limit. In the common case,
- it will get to send slightly more than the average daily byte
- limit.
- """
-
- # Query Node Manager for max average rate overrides
- (self.avgrate, self.avgexemptrate) = nm.query(self.name, [('nm_net_avg_rate', -1), ('nm_net_avg_exempt_rate', -1)])
- if self.avgrate == -1:
- self.avgrate = default_avgrate
- if self.avgexemptrate == -1:
- self.avgexemptrate = default_avgexemptrate
-
- # Prepare message parameters from the template
- message = ""
- params = {'slice': self.name, 'hostname': socket.gethostname(),
- 'since': time.asctime(time.gmtime(self.time)) + " GMT",
- 'until': time.asctime(time.gmtime(self.time + period)) + " GMT",
- 'date': time.asctime(time.gmtime()) + " GMT",
- 'period': format_period(period)}
-
- bytelimit = self.avgrate * period / bits_per_byte
- if bytes >= (self.bytes + bytelimit) and \
- maxrate > self.avgrate:
- new_maxrate = self.avgrate
- else:
- new_maxrate = maxrate
-
- # Format template parameters for low bandwidth message
- params['class'] = "low bandwidth"
- params['bytes'] = format_bytes(bytes - self.bytes)
- params['maxrate'] = bwlimit.format_tc_rate(maxrate)
- params['limit'] = format_bytes(bytelimit)
- params['avgrate'] = bwlimit.format_tc_rate(self.avgrate)
-
- if verbose:
- print "%(slice)s %(class)s " \
- "%(bytes)s/%(limit)s (%(maxrate)s/%(avgrate)s)" % \
- params
-
- # Cap low bandwidth burst rate
- if new_maxrate != maxrate:
- message += template % params
- print "%(slice)s %(class)s capped at %(avgrate)s (%(bytes)s/%(limit)s)" % params
-
- exemptbytelimit = self.avgexemptrate * period / bits_per_byte
- if exemptbytes >= (self.exemptbytes + exemptbytelimit) and \
- maxexemptrate > self.avgexemptrate:
- new_maxexemptrate = self.avgexemptrate
- else:
- new_maxexemptrate = maxexemptrate
-
- # Format template parameters for high bandwidth message
- params['class'] = "high bandwidth"
- params['bytes'] = format_bytes(exemptbytes - self.exemptbytes)
- params['maxrate'] = bwlimit.format_tc_rate(maxexemptrate)
- params['limit'] = format_bytes(exemptbytelimit)
- params['avgrate'] = bwlimit.format_tc_rate(self.avgexemptrate)
-
- if verbose:
- print "%(slice)s %(class)s " \
- "%(bytes)s/%(limit)s (%(maxrate)s/%(avgrate)s)" % \
- params
-
- # Cap high bandwidth burst rate
- if new_maxexemptrate != maxexemptrate:
- message += template % params
- print "%(slice)s %(class)s capped at %(avgrate)s (%(bytes)s/%(limit)s)" % params
-
- # Apply parameters
- if new_maxrate != maxrate or new_maxexemptrate != maxexemptrate:
- bwlimit.set(xid = self.xid, maxrate = new_maxrate, maxexemptrate = new_maxexemptrate)
-
- # Notify slice
- if message:
- subject = "pl_mom capped bandwidth of slice %(slice)s on %(hostname)s" % params
- if debug:
- print subject
- print message + (footer % params)
- else:
- slicemail(self.name, subject, message + (footer % params))
+ def __init__(self, xid, name, maxrate, maxexemptrate, bytes, exemptbytes):
+ self.xid = xid
+ self.name = name
+ self.time = 0
+ self.bytes = 0
+ self.exemptbytes = 0
+ self.ByteMax = default_ByteMax
+ self.ByteThresh = default_ByteThresh
+ self.ExemptByteMax = default_ExemptByteMax
+ self.ExemptByteThresh = default_ExemptByteThresh
+ self.maxrate = default_maxrate
+ self.maxexemptrate = default_maxexemptrate
+
+ # Get real values where applicable
+ self.reset(maxrate, maxexemptrate, bytes, exemptbytes)
+
+ def __repr__(self):
+ return self.name
+
+ def updateSliceAttributes(self):
+ # Query Node Manager for max rate overrides
+ try:
+ vals = nm.query(self.name,
+ [('nm_net_max_rate', self.maxrate),
+ ('nm_net_max_exempt_rate', self.maxexemptrate),
+ ("nm_net_max_byte", self.ByteMax),
+ ("nm_net_max_exempt_byte", self.ExemptByteMax),
+ ("nm_net_max_thresh_byte", int( .8 * self.ByteMax)),
+ ("nm_net_max_thresh_exempt_byte", int(.8 * self.ExemptByteMax)),
+ ("nm_net_avg_rate", 0),
+ ("nm_net_avg_exempt_rate", 0)])
+
+ (self.maxrate,
+ self.maxexemptrate,
+ self.ByteMax,
+ self.ExemptByteMax,
+ self.ByteThresh,
+ self.ExemptByteThresh,
+ avgrate,
+ avgexemptrate) = vals
+
+ if (avgrate != 0) or (avgexemptrate != 0):
+ self.ByteMax = avgrate * period
+ self.ByteThresh = int(self.ByteMax * .8)
+ self.ExemptByteMax = avgexemptrate * period
+ self.ExemptByteThresh = int(self.ExemptByteMax * .8)
+
+ except Exception, err:
+ print "Warning: Exception received while querying NM:", err
+
+ def reset(self, maxrate, maxexemptrate, bytes, exemptbytes):
+ """
+ Begin a new recording period. Remove caps by restoring limits
+ to their default values.
+ """
+
+ # Query Node Manager for max rate overrides
+ self.updateSliceAttributes()
+
+ # Reset baseline time
+ self.time = time.time()
+
+ # Reset baseline byte coutns
+ self.bytes = bytes
+ self.exemptbytes = exemptbytes
+
+ if (self.maxrate != maxrate) or (self.maxexemptrate != maxexemptrate):
+ print "%s reset to %s/%s" % \
+ (self.name,
+ bwlimit.format_tc_rate(self.maxrate),
+ bwlimit.format_tc_rate(self.maxexemptrate))
+ bwlimit.set(xid = self.xid, maxrate = self.maxrate, maxexemptrate = self.maxexemptrate)
+
+ def update(self, maxrate, maxexemptrate, bytes, exemptbytes):
+ """
+ Update byte counts and check if byte limits have been
+ exceeded.
+ """
+
+ # Query Node Manager for max rate overrides
+ self.updateSliceAttributes()
+
+ # Prepare message parameters from the template
+ message = ""
+ params = {'slice': self.name, 'hostname': socket.gethostname(),
+ 'since': time.asctime(time.gmtime(self.time)) + " GMT",
+ 'until': time.asctime(time.gmtime(self.time + period)) + " GMT",
+ 'date': time.asctime(time.gmtime()) + " GMT",
+ 'period': format_period(period)}
+
+ if bytes >= (self.bytes + (self.ByteThresh * 1024)):
+ new_maxrate = \
+ int(((self.ByteMax * 1024) - self.bytes + bytes)/(period - time.time() - self.time))
+ else:
+ new_maxrate = maxrate
+
+ # Format template parameters for low bandwidth message
+ params['class'] = "low bandwidth"
+ params['bytes'] = format_bytes(bytes - self.bytes)
+ params['maxrate'] = bwlimit.format_tc_rate(maxrate)
+ params['limit'] = format_bytes(int(self.ByteMax * 1024))
+ params['new_maxrate'] = bwlimit.format_tc_rate(new_maxrate)
+
+ if verbose:
+ print "%(slice)s %(class)s " \
+ "%(bytes)s of %(limit)s (%(new_maxrate)s maxrate)" % \
+ params
+
+ # Cap low bandwidth burst rate
+ if new_maxrate != maxrate:
+ message += template % params
+ print "%(slice)s %(class)s capped at %(new_maxrate)s " % params
+
+ if exemptbytes >= (self.exemptbytes + (self.ExemptByteThresh * 1024)):
+ new_maxexemptrate = \
+ int(((self.ExemptByteMax * 1024) - (self.bytes + bytes))/(period - (time.time() - self.time)))
+ else:
+ new_maxexemptrate = maxexemptrate
+
+ # Format template parameters for high bandwidth message
+ params['class'] = "high bandwidth"
+ params['bytes'] = format_bytes(exemptbytes - self.exemptbytes)
+ params['maxrate'] = bwlimit.format_tc_rate(maxexemptrate)
+ params['limit'] = format_bytes(self.ExemptByteMax * 1024)
+ params['new_maxrate'] = bwlimit.format_tc_rate(new_maxexemptrate)
+
+ if verbose:
+ print "%(slice)s %(class)s " \
+ "%(bytes)s of %(limit)s (%(new_maxrate)s maxrate)" % params
+
+ # Cap high bandwidth burst rate
+ if new_maxexemptrate != maxexemptrate:
+ message += template % params
+ print "%(slice)s %(class)s capped at %(new_maxexemptrate)s" % params
+
+ # Apply parameters
+ if new_maxrate != maxrate or new_maxexemptrate != maxexemptrate:
+ bwlimit.set(xid = self.xid, maxrate = new_maxrate, maxexemptrate = new_maxexemptrate)
+
+ # Notify slice
+ #if message:
+ # subject = "pl_mom capped bandwidth of slice %(slice)s on %(hostname)s" % params
+ # if debug:
+ # print subject
+ # print message + (footer % params)
+ # else:
+ # slicemail(self.name, subject, message + (footer % params))
+
+