def test_slewNotifiesDependents(self): mockTime = self.mockTime mockTime.timeNow = 5020.8 b = SysClock() c = TunableClock(b, tickRate=1000, ticks=5) cc = TunableClock(c, tickRate=100) d1 = MockDependent() d2 = MockDependent() d3 = MockDependent() b.bind(d1) c.bind(d2) cc.bind(d3) d1.assertNotNotified() d2.assertNotNotified() d3.assertNotNotified() c.slew = 100 d1.assertNotNotified() d2.assertNotificationsEqual([c]) d3.assertNotificationsEqual([cc])
def setUp(self): self.root = SysClock( ) # init before installing mock, so it can do its precision measurement while time still flows self.mockTime = MockTime() self.mockTime.install() self.parent = CorrelatedClock(parentClock=self.root, tickRate=1000) self.altParent = CorrelatedClock(parentClock=self.root, tickRate=50)
def createCSSClientObjects(cmdParser): """\ Create the client objects needed to engage in the CSS-WC and CSS-TS protocols. :param cmdParser the command line parser object """ args = cmdParser.args sysclock=SysClock() wallClock=TunableClock(sysclock,tickRate=1000000000) # nanos # measure precision of wall clock empirically wcPrecisionNanos = measurePrecision(wallClock) * 1000000000 algorithm = LowestDispersionCandidate(wallClock,repeatSecs=0.3,timeoutSecs=0.3) wcClient=WallClockClient(cmdParser.wcBind, args.wcUrl[0], wallClock, algorithm) timelineClock = CorrelatedClock(wallClock, args.timelineClockFrequency) # start recording dispersion of the wall clock dispRecorder=DispersionRecorder(algorithm) dispRecorder.start() print "Connecting, requesting timeline for:" print " Any contentId beginning with:", args.contentIdStem print " and using timeline selector: ", args.timelineSelector print ts = TSClientClockController(args.tsUrl[0], args.contentIdStem, args.timelineSelector, timelineClock, correlationChangeThresholdSecs=0.0) return (ts, timelineClock, args.timelineClockFrequency, wcClient, wallClock, wcPrecisionNanos, dispRecorder)
def test_rangeConversion(self): mockTime=MockTime() mockTime.install() mockTime.timeNow = 0.0 b = SysClock(tickRate=1000) c = RangeCorrelatedClock(b, 1000, correlation1=(100,1000), correlation2=(200,1110)) mockTime.timeNow = b.calcWhen(100) self.assertEqual(c.ticks, 1000) mockTime.timeNow = b.calcWhen(200) self.assertEqual(c.ticks, 1110) mockTime.timeNow = b.calcWhen(150) self.assertEqual(c.ticks, 1055)
def test_changeSpeedeNotifies(self): """Check a change to the correlation propagates notifications to dependents of this clock""" b = SysClock() c = CorrelatedClock(b, 1000, correlation=(0,300)) cc = CorrelatedClock(c, 50) d1 = MockDependent() d2 = MockDependent() d3 = MockDependent() b.bind(d1) c.bind(d2) cc.bind(d3) c.speed = 0.5 d1.assertNotNotified() d2.assertNotificationsEqual([c]) d3.assertNotificationsEqual([cc])
def test_speedChangePropagates(self): mockTime = self.mockTime mockTime.timeNow = 5 a = SysClock(tickRate=1000) a1 = CorrelatedClock(a, tickRate=1000, correlation=(50,0)) a2 = CorrelatedClock(a1, tickRate=100, correlation=(28,999)) a3 = CorrelatedClock(a2, tickRate=50, correlation=(5,1003)) a4 = CorrelatedClock(a3, tickRate=25, correlation=(1000,9)) b3 = CorrelatedClock(a2, tickRate=1000, correlation=(500,20)) b4 = CorrelatedClock(b3, tickRate=2000, correlation=(15,90)) at1, a1t1, a2t1, a3t1, a4t1, b3t1, b4t1 = [x.ticks for x in [a,a1,a2,a3,a4,b3,b4]] a3.speed = 0.5 a4.speed = 0.2 self.assertEquals(1.0, a.getEffectiveSpeed()) self.assertEquals(1.0, a1.getEffectiveSpeed()) self.assertEquals(1.0, a2.getEffectiveSpeed()) self.assertEquals(0.5, a3.getEffectiveSpeed()) self.assertEquals(0.1, a4.getEffectiveSpeed()) a3.speed = 0 a4.speed = 1.0 self.assertEquals(1.0, a.getEffectiveSpeed()) self.assertEquals(1.0, a1.getEffectiveSpeed()) self.assertEquals(1.0, a2.getEffectiveSpeed()) self.assertEquals(0.0, a3.getEffectiveSpeed()) self.assertEquals(0.0, a4.getEffectiveSpeed()) mockTime.timeNow = 6 # advance time 1 second at2, a1t2, a2t2, a3t2, a4t2, b3t2, b4t2 = [x.ticks for x in [a,a1,a2,a3,a4,b3,b4]] self.assertEquals(at2, at1 + 1000) # a still advances self.assertEquals(a1t2, a1t1 + 1000) # a1 still advances self.assertEquals(a2t2, a2t1 + 100) # a2 still advances self.assertEquals(a3t2, 1003) # a3 is speed zero, is now at the correlation point self.assertEquals(a4t2, 10.5) # a4 is speed zero, a3.ticks is 3 ticks from correlation point for a4, translating to 1.5 ticks from a4 correlation point at its tickRate self.assertEquals(b3t2, b3t1 + 1000) # b3 still advances self.assertEquals(b4t2, b4t1 + 2000) # b4 is paused
def test_noCommonAncestor(self): a = SysClock() b = SysClock() a1 = CorrelatedClock(a, tickRate=1000, correlation=(0,0)) b1 = CorrelatedClock(b, tickRate=1000, correlation=(0,0)) a2 = CorrelatedClock(a1, tickRate=1000, correlation=(0,0)) b2 = CorrelatedClock(b1, tickRate=1000, correlation=(0,0)) self.assertRaises(NoCommonClock, lambda:a.toOtherClockTicks(b, 5)) self.assertRaises(NoCommonClock, lambda:a.toOtherClockTicks(b1, 5)) self.assertRaises(NoCommonClock, lambda:a.toOtherClockTicks(b2, 5)) self.assertRaises(NoCommonClock, lambda:a1.toOtherClockTicks(b, 5)) self.assertRaises(NoCommonClock, lambda:a1.toOtherClockTicks(b1, 5)) self.assertRaises(NoCommonClock, lambda:a1.toOtherClockTicks(b2, 5)) self.assertRaises(NoCommonClock, lambda:a2.toOtherClockTicks(b, 5)) self.assertRaises(NoCommonClock, lambda:a2.toOtherClockTicks(b1, 5)) self.assertRaises(NoCommonClock, lambda:a2.toOtherClockTicks(b2, 5)) self.assertRaises(NoCommonClock, lambda:b.toOtherClockTicks(a, 5)) self.assertRaises(NoCommonClock, lambda:b.toOtherClockTicks(a1, 5)) self.assertRaises(NoCommonClock, lambda:b.toOtherClockTicks(a2, 5)) self.assertRaises(NoCommonClock, lambda:b1.toOtherClockTicks(a, 5)) self.assertRaises(NoCommonClock, lambda:b1.toOtherClockTicks(a1, 5)) self.assertRaises(NoCommonClock, lambda:b1.toOtherClockTicks(a2, 5)) self.assertRaises(NoCommonClock, lambda:b2.toOtherClockTicks(a, 5)) self.assertRaises(NoCommonClock, lambda:b2.toOtherClockTicks(a1, 5)) self.assertRaises(NoCommonClock, lambda:b2.toOtherClockTicks(a2, 5))
def test_changeFreqNotifies(self): mockTime = self.mockTime mockTime.timeNow = 5020.8 b = SysClock() c = CorrelatedClock(b, 1000, correlation=(50,300)) cc = CorrelatedClock(c, 50) d1 = MockDependent() d2 = MockDependent() d3 = MockDependent() b.bind(d1) c.bind(d2) cc.bind(d3) c.tickRate = 500 d1.assertNotNotified() d2.assertNotificationsEqual([c]) d3.assertNotificationsEqual([cc])
# (pydvbcss>=0.5.0 functionality) # otherwise, set it to the specified value and prevent the CII server from rewriting it. if args.advertise_addr is None: ADVERTISE_HOST = "{{host}}" CII_REWRITE_PROPS = ['wcUrl', 'tsUrl'] else: ADVERTISE_HOST = args.advertise_addr[0] CII_REWRITE_PROPS = [] WebSocketPlugin(cherrypy.engine).subscribe() cherrypy.config.update({"server.socket_host": HOST}) cherrypy.config.update({"server.socket_port": WS_PORT}) cherrypy.config.update({"engine.autoreload.on": False}) wallClock = SysClock(tickRate=1000000000) precision = measurePrecision( wallClock, 20 ) # reduced iterations because on Windows the normal clock is low precision maxFreqError = 500 wcServer = WallClockServer(wallClock, precision, maxFreqError, bindaddr=HOST, bindport=WC_PORT) wcWsServer = WebSocketWallClock_ServerEndpoint(wallClock, precision, maxFreqError) ciiServer = BlockableCIIServer(maxConnectionsAllowed=-1, enabled=False, rewriteHostPort=CII_REWRITE_PROPS)
"--fr", "--followup-replies", dest="followup", action="store_true", default=False, help="Configure server to send follow-up responses (default=not)") args = parser.parse_args() if args.quiet: logging.disable(logging.CRITICAL) else: logging.basicConfig(level=args.loglevel[0]) if not args.quiet: print "----" print "CSS-WC endpoint bound to host %s on port %d" % (args.wc_addr, args.wc_port) print "----" clock = SysClock(maxFreqErrorPpm=args.maxFreqError) wc_server = WallClockServer(clock, None, None, args.wc_addr, args.wc_port, followup=args.followup) wc_server.start() while True: time.sleep(1)
logging.getLogger("cherrypy.error").setLevel(logging.CRITICAL) if not args.quiet: print "----" print "CSS-CII endpoint URL: ws://%s:%d/cii" % (args.ws_addr, args.ws_port) print "CSS-TS endpoint URL: ws://%s:%d/ts" % (args.ws_addr, args.ws_port) print "CSS-WC endpoint bound to host %s on port %d" % (args.wc_addr, args.wc_port) print "Content ID:", CONTENT_ID print "----" WebSocketPlugin(cherrypy.engine).subscribe() systemClock = SysClock(tickRate=1000000000, maxFreqErrorPpm=500) wallClock = CorrelatedClock(parentClock=systemClock, tickRate=1000000000, correlation=Correlation(0, 0)) cherrypy.config.update({"server.socket_host": args.ws_addr}) cherrypy.config.update({"server.socket_port": args.ws_port}) cherrypy.config.update({"engine.autoreload.on": False}) wcServer = WallClockServer(wallClock, None, None, bindaddr=args.wc_addr, bindport=args.wc_port) ciiServer = CIIServer(maxConnectionsAllowed=5,
tsUrl = args.tsUrl[0] wc_dest=args.wcUrl[0] wc_bind=(args.wc_bindaddr, args.wc_bindport) contentIdStem = args.contentIdStem[0] timelineSelector= args.timelineSelector[0] timelineFreq = args.timelineFreq[0] if args.quiet: logging.disable(logging.CRITICAL) else: logging.basicConfig(level=args.loglevel[0]) logging.getLogger("dvbcss.protocol.client.wc").setLevel(args.wcloglevel[0]) sysclock=SysClock() wallClock=CorrelatedClock(sysclock,tickRate=1000000000) # nanos algorithm = LowestDispersionCandidate(wallClock,repeatSecs=1,timeoutSecs=0.5) wc_client=WallClockClient(wc_bind, wc_dest, wallClock, algorithm) wc_client.start() timelineClock = CorrelatedClock(wallClock, timelineFreq) timelineClock.setAvailability(False) print "Connecting, requesting timeline for:" print " Any contentId beginning with:",contentIdStem print " and using timeline selector: ",timelineSelector print
nargs="?", help="Port number to bind to (default=" + str(DEFAULT_BIND[1]) + ")", default=DEFAULT_BIND[1]) args = parser.parse_args() dest = (args.addr, args.port) bind = (args.bindaddr, args.bindport) if args.quiet: logging.disable(logging.CRITICAL) else: logging.basicConfig(level=args.loglevel[0]) #first we'll create a clock to represent the wall clock sysclock = SysClock(tickRate=1000000000) wallClock = CorrelatedClock(sysclock, tickRate=1000000000) # we'll also create the algorithm object that adjusts the clock and controls # how often requests are made to the server. algorithm = LowestDispersionCandidate(wallClock, repeatSecs=1, timeoutSecs=0.5) # finally we create the client and start it. wc_client = WallClockClient(bind, dest, wallClock, algorithm) wc_client.start() n = 0 while True: time.sleep(0.2)
def test_fromParentTicks(self): sysClock = SysClock() self.assertRaises(StopIteration, lambda : sysClock.fromParentTicks(10))
def test_calcWhen(self): sysClock = SysClock() self.assertAlmostEqual(sysClock.calcWhen(91248752), 91248752/1000000.0, places=5)
def newSysClock(self, *args, **kwargs): self.mockTime.enableAutoIncrementBy(0.000001, numReadsBetweenIncrements=1) sysClock = SysClock(*args, **kwargs) self.mockTime.disableAutoIncrement() return sysClock
def setupWallClockMaster(maxFreqError, addr, port): wallClock = SysClock(tickRate=1000000000) precisionSecs = measurePrecision(wallClock) wcServer = WallClockServer(wallClock, precisionSecs, maxFreqError, addr, port) return (wcServer, wallClock, precisionSecs)
def test_getParent(self): sysClock = SysClock() self.assertEqual(sysClock.getParent(), None)