VPS-Plugin: initial checkin
[enigma2-plugins.git] / vps / src_py / Vps.py
1 # -*- coding: utf-8 -*-
2
3 from enigma import eTimer, eConsoleAppContainer, getBestPlayableServiceReference, eServiceReference, eEPGCache
4 from time import time, strftime, localtime
5 from Components.config import config
6 from timer import TimerEntry
7 from Tools import Notifications
8 from Screens.MessageBox import MessageBox
9 from os import access, chmod, X_OK
10 from RecordTimer import RecordTimerEntry, parseEvent
11 from ServiceReference import ServiceReference
12 import NavigationInstance
13
14 vps_exe = "/usr/lib/enigma2/python/Plugins/SystemPlugins/vps/vps"
15 if not access(vps_exe, X_OK):
16         chmod(vps_exe, 493)
17
18 class vps_timer:
19         def __init__(self, timer, session):
20                 self.timer = timer
21                 self.session = session
22                 self.program = eConsoleAppContainer()
23                 self.program.dataAvail.append(self.program_dataAvail)
24                 self.program.appClosed.append(self.program_closed)
25                 self.program_running = False
26                 self.program_try_search_running = False
27                 self.last_overwrite_enabled = False
28                 self.activated_auto_increase = False
29                 self.simulate_recordService = None
30                 self.demux = -1
31                 self.rec_ref = None
32                 self.found_pdc = False
33                 self.dont_restart_program = False
34                 self.org_timer_end = 0
35                 self.org_timer_begin = 0
36                 
37                 self.program_seek_vps_multiple = eConsoleAppContainer()
38                 self.program_seek_vps_multiple.dataAvail.append(self.program_seek_vps_multiple_dataAvail)
39                 self.program_seek_vps_multiple.appClosed.append(self.program_seek_vps_multiple_closed)
40                 self.program_seek_vps_multiple_started = 0
41         
42         def program_closed(self, retval):
43                 #print "[VPS-Plugin] Programm hat sich beendet"
44                 self.timer.log(0, "[VPS] stop monitoring (process terminated)")
45                 if self.program_running or self.program_try_search_running:
46                         self.program_running = False
47                         self.program_try_search_running = False
48                         self.stop_simulation()
49         
50         def program_dataAvail(self, str):
51                 #print "[VPS-Plugin] received: "+ str
52                 #try:
53                 if self.timer is None or self.timer.state == TimerEntry.StateEnded or self.timer.cancelled:
54                         self.program_abort()
55                         self.stop_simulation()
56                         return
57                 if self.timer.vpsplugin_enabled == False or config.plugins.vps.enabled.value == False:
58                         if self.activated_auto_increase:
59                                 self.timer.autoincrease = False
60                         self.program_abort()
61                         self.stop_simulation()
62                         return
63                 
64                 lines = str.split("\n")
65                 for line in lines:
66                         data = line.split()
67                         if len(data) < 2:
68                                 continue
69                         
70                         self.timer.log(0, "[VPS] "+ " ".join(data))
71                         
72                         if data[1] == "RUNNING_STATUS":
73                                 if data[2] == "1": # not running
74                                         # Wenn der Eintrag im Following (Section_Number = 1) ist, dann nicht beenden (Sendung begann noch gar nicht)
75                                         if data[3] == "FOLLOWING":
76                                                 if not self.activated_auto_increase and self.timer.state == TimerEntry.StateRunning:
77                                                         self.activate_autoincrease()
78                                         else:
79                                                 if self.timer.state == TimerEntry.StateRunning:
80                                                         self.activated_auto_increase = False
81                                                         self.timer.autoincrease = False
82                                                         
83                                                         if self.timer.vpsplugin_overwrite:
84                                                                 # sofortiger Stopp
85                                                                 self.timer.abort()
86                                                                 self.session.nav.RecordTimer.doActivate(self.timer)
87                                                                 self.stop_simulation()
88                                                         
89                                                         self.dont_restart_program = True
90                                                         self.program_abort()
91                                 
92                                 elif data[2] == "2": # starts in a few seconds
93                                         if self.timer.state == TimerEntry.StateWaiting:
94                                                 self.session.nav.RecordTimer.doActivate(self.timer)
95                                 
96                                 elif data[2] == "3": # pausing
97                                         if self.timer.state == TimerEntry.StateRunning:
98                                                 if not self.activated_auto_increase:
99                                                         self.activate_autoincrease()
100                                 
101                                 elif data[2] == "4": # running
102                                         if self.timer.state == TimerEntry.StateRunning:
103                                                 if not self.activated_auto_increase:
104                                                         self.activate_autoincrease()
105                                         
106                                         elif self.timer.state == TimerEntry.StateWaiting or self.timer.state == TimerEntry.StatePrepared:
107                                                 # setze Startzeit auf jetzt
108                                                 self.timer.begin = int(time())
109                                                 self.session.nav.RecordTimer.timeChanged(self.timer)
110                                                 
111                                                 if self.timer.vpsplugin_overwrite:
112                                                         self.activate_autoincrease()
113                                                         self.program_abort()
114                                                         self.stop_simulation()
115                                                         vps_timers.checksoon(2000) # Programm neu starten
116                                                 else:
117                                                         self.program_abort()
118                                                         self.stop_simulation()
119                         
120                         elif data[1] == "EVENT_ENDED":
121                                 if self.timer.state == TimerEntry.StateRunning:
122                                         self.activated_auto_increase = False
123                                         self.timer.autoincrease = False
124                                         
125                                         if self.timer.vpsplugin_overwrite:
126                                                 # sofortiger Stopp
127                                                 self.timer.abort()
128                                                 self.session.nav.RecordTimer.doActivate(self.timer)
129                                                 self.stop_simulation()
130
131                                                 
132                                 self.program_abort()
133                                 self.stop_simulation()
134                         
135                         elif data[1] == "OTHER_TS_RUNNING_STATUS":
136                                 if self.timer.state == TimerEntry.StateWaiting:
137                                         self.timer.start_prepare = int(time())
138                                         #self.session.nav.RecordTimer.calcNextActivation()
139                                         self.session.nav.RecordTimer.doActivate(self.timer)
140                                 
141                                 self.program_abort()
142                                 self.stop_simulation()
143                                 #self.check()
144                                 vps_timers.checksoon(2000)
145                         
146                         # PDC
147                         elif data[1] == "PDC_FOUND_EVENT_ID":
148                                 self.found_pdc = True
149                                 self.timer.eit = int(data[2])
150                                 epgcache = eEPGCache.getInstance()
151                                 evt = epgcache.lookupEventId(self.rec_ref, self.timer.eit)
152                                 if evt:
153                                         self.timer.name = evt.getEventName()
154                                         self.timer.description = evt.getShortDescription()
155                                 self.program_abort()
156                                 vps_timers.checksoon(500)
157                         
158                         # Fehler
159                         elif data[1] == "DMX_ERROR_TIMEOUT" or data[1] == "DMX_SET_FILTER_ERROR":
160                                 self.program_abort()
161                                 
162
163                 #except:
164                 #       pass
165         
166         def activate_autoincrease(self):
167                 self.activated_auto_increase = True
168                 self.timer.autoincrease = True
169                 self.timer.autoincreasetime = 60
170                 if self.org_timer_end == 0:
171                         self.org_timer_end = self.timer.end
172                 self.timer.log(0, "[VPS] enable autoincrease")
173         
174         def program_abort(self):
175                 if self.program_running or self.program_try_search_running:
176                         #self.program.sendCtrlC()
177                         self.program.kill()
178                         self.program_running = False
179                         self.program_try_search_running = False
180                         self.timer.log(0, "[VPS] stop monitoring")
181         
182         def stop_simulation(self):
183                 if self.simulate_recordService:
184                         NavigationInstance.instance.stopRecordService(self.simulate_recordService)
185                         self.simulate_recordService = None
186                         self.timer.log(0, "[VPS] stop RecordService (simulation)")
187         
188         
189         def program_seek_vps_multiple_closed(self, retval):
190                 self.program_seek_vps_multiple_started = -1
191         
192         def program_seek_vps_multiple_dataAvail(self, str):
193                 lines = str.split("\n")
194                 for line in lines:
195                         data = line.split()
196                         if len(data) < 2:
197                                 continue
198                         
199                         self.timer.log(0, "[VPS] "+ " ".join(data))
200                         
201                         if data[1] == "PDC_MULTIPLE_FOUND_EVENT":
202                                 neweventid = int(data[2])
203                                 epgcache = eEPGCache.getInstance()
204                                 evt = epgcache.lookupEventId(self.rec_ref, neweventid)
205                                 
206                                 if evt:
207                                         evt_begin = evt.getBeginTime() + 60
208                                         evt_end = evt.getBeginTime() + evt.getDuration() - 60
209                                         
210                                         # überprüfen, ob es den Timer nicht schon gibt
211                                         canbeadded = True
212                                         for checktimer in self.session.nav.RecordTimer.timer_list:
213                                                 if checktimer == self.timer:
214                                                         continue
215                                                 
216                                                 if checktimer.service_ref.ref.toCompareString() == self.timer.service_ref.ref.toCompareString() or checktimer.service_ref.ref.toCompareString() == self.rec_ref.toCompareString():      
217                                                         if checktimer.eit == neweventid:
218                                                                 canbeadded = False
219                                                         elif checktimer.begin <= evt_begin and checktimer.end >= evt_end:
220                                                                 canbeadded = False
221                                                                 if checktimer.vpsplugin_enabled and checktimer.vpsplugin_time is not None:
222                                                                         checktimer.eit = neweventid
223                                                                         checktimer.name = evt.getEventName()
224                                                                         checktimer.description = evt.getShortDescription()
225                                                                         checktimer.vpsplugin_time = None
226                                                                         checktimer.log(0, "[VPS] changed timer (found same PDC-Time as in other VPS-recording)")
227                                                                         
228                                         if canbeadded:
229                                                 newevent_data = parseEvent(evt)
230                                                 newEntry = RecordTimerEntry(ServiceReference(self.rec_ref), *newevent_data)
231                                                 newEntry.vpsplugin_enabled = True
232                                                 newEntry.vpsplugin_overwrite = True
233                                                 newEntry.log(0, "[VPS] added this timer (found same PDC-Time as in other VPS-recording)")
234                                                 
235                                                 NavigationInstance.instance.RecordTimer.record(newEntry)
236         
237         # Suche nach weiteren Events mit selber VPS-Zeit
238         def program_seek_vps_multiple_start(self):
239                 if self.program_seek_vps_multiple_started == 0:
240                         self.program_seek_vps_multiple_started = time()
241                         
242                         sid = self.rec_ref.getData(1)
243                         tsid = self.rec_ref.getData(2)
244                         onid = self.rec_ref.getData(3)
245                         demux = "/dev/dvb/adapter0/demux" + str(self.demux)
246                         
247                         day = strftime("%d", localtime(self.timer.vpsplugin_time))
248                         month = strftime("%m", localtime(self.timer.vpsplugin_time))
249                         hour = strftime("%H", localtime(self.timer.vpsplugin_time))
250                         minute = strftime("%M", localtime(self.timer.vpsplugin_time))
251                         cmd = vps_exe + " "+ demux +" 4 "+ str(onid) +" "+ str(tsid) +" "+ str(sid) +" "+ str(self.timer.eit) +" 0 "+ day +" "+ month +" "+ hour +" "+ minute
252                         
253                         self.program_seek_vps_multiple.execute(cmd)
254                         
255                         self.timer.log(0, "[VPS] seek another events with same PDC-Time")
256         
257         def program_seek_vps_multiple_abort(self):
258                 if self.program_seek_vps_multiple_started > 0:
259                         self.program_seek_vps_multiple.kill()
260                         self.program_seek_vps_multiple_started = -1
261                         self.timer.log(0, "[VPS] abort seeking other pdc-events")
262         
263         # startet den Hintergrundprozess
264         def program_do_start(self, mode):
265                 if self.program_running or self.program_try_search_running:
266                         self.program_abort()
267                 
268                 if mode == 1:
269                         self.demux = 0
270                         self.program_try_search_running = True
271                         self.program_running = False
272                         mode_program = 1
273                 else:
274                         self.program_try_search_running = False
275                         self.program_running = True
276                         mode_program = 0
277                 
278                 sid = self.rec_ref.getData(1)
279                 tsid = self.rec_ref.getData(2)
280                 onid = self.rec_ref.getData(3)
281                 demux = "/dev/dvb/adapter0/demux" + str(self.demux)
282                 
283                 #print "[VPS-Plugin] starte Hintergrundprozess"
284                 
285                 # PDC-Zeit?
286                 if self.timer.name == "" and self.timer.vpsplugin_time is not None and not self.found_pdc:
287                         mode_program += 2
288                         day = strftime("%d", localtime(self.timer.vpsplugin_time))
289                         month = strftime("%m", localtime(self.timer.vpsplugin_time))
290                         hour = strftime("%H", localtime(self.timer.vpsplugin_time))
291                         minute = strftime("%M", localtime(self.timer.vpsplugin_time))
292                         cmd = vps_exe + " "+ demux +" "+ str(mode_program) +" "+ str(onid) +" "+ str(tsid) +" "+ str(sid) +" 0 0 "+ day +" "+ month +" "+ hour +" "+ minute
293                         #print "[VPS-Plugin] "+ cmd
294                         self.timer.log(0, "[VPS] seek PDC-Time")
295                         self.program.execute(cmd)
296                         return
297                 
298                 cmd = vps_exe + " "+ demux +" "+ str(mode_program) +" "+ str(onid) +" "+ str(tsid) +" "+ str(sid) +" "+ str(self.timer.eit) +" 0"
299                 #print "[VPS-Plugin] "+ cmd
300                 self.timer.log(0, "[VPS] start monitoring running-status")
301                 self.program.execute(cmd)
302         
303         
304         def program_start(self):
305                 self.demux = -1
306                 
307                 if self.dont_restart_program:
308                         return
309                 
310                 self.rec_ref = self.timer.service_ref and self.timer.service_ref.ref
311                 if self.rec_ref and self.rec_ref.flags & eServiceReference.isGroup:
312                         self.rec_ref = getBestPlayableServiceReference(self.rec_ref, eServiceReference())
313                 
314                 # recordService (Simulation) ggf. starten
315                 if self.timer.state == TimerEntry.StateWaiting:
316                         if self.simulate_recordService is None:
317                                 if self.rec_ref:
318                                         self.simulate_recordService = NavigationInstance.instance.recordService(self.rec_ref, True)
319                                         if self.simulate_recordService:
320                                                 res = self.simulate_recordService.start()
321                                                 #print "[VPS-Plugin] starte Simulation, res: "+ str(res)
322                                                 self.timer.log(0, "[VPS] start recordService (simulation)")
323                                                 if res != 0 and res != -1:
324                                                         # Fehler aufgetreten (kein Tuner frei?)
325                                                         NavigationInstance.instance.stopRecordService(self.simulate_recordService)
326                                                         self.simulate_recordService = None
327                                                         
328                                                         # in einer Minute ggf. nochmal versuchen
329                                                         if 60 < self.nextExecution:
330                                                                 self.nextExecution = 60
331                                                         
332                                                         # Bei Overwrite versuchen ohne Fragen auf Sender zu schalten
333                                                         if self.timer.vpsplugin_overwrite == True:
334                                                                 cur_ref = NavigationInstance.instance.getCurrentlyPlayingServiceReference()
335                                                                 if cur_ref and not cur_ref.getPath():
336                                                                         self.timer.log(9, "[VPS-Plugin] zap without asking (simulation)")
337                                                                         Notifications.AddNotification(MessageBox, _("In order to record a timer, the TV was switched to the recording service!\n"), type=MessageBox.TYPE_INFO, timeout=20)
338                                                                         NavigationInstance.instance.playService(self.rec_ref)
339                                                                         if 3 < self.nextExecution:
340                                                                                 self.nextExecution = 3
341                                                         else:
342                                                                 # ansonsten versuchen auf dem aktuellen Transponder/Kanal nach Infos zu suchen
343                                                                 if not self.program_try_search_running:
344                                                                         self.program_do_start(1)
345                                                 else: # Simulation hat geklappt
346                                                         if 1 < self.nextExecution:
347                                                                 self.nextExecution = 1
348                         else: # Simulation läuft schon
349                                 # hole Demux
350                                 stream = self.simulate_recordService.stream()
351                                 if stream:
352                                         streamdata = stream.getStreamingData()
353                                         if (streamdata and ('demux' in streamdata)):
354                                                 self.demux = streamdata['demux']
355                                 
356                                 if self.demux == -1:
357                                         # ist noch nicht soweit(?), in einer Sekunde erneut versuchen
358                                         if 1 < self.nextExecution:
359                                                 self.nextExecution = 1
360                                 else:
361                                         self.program_do_start(0)
362                                         
363                 
364                 elif self.timer.state == TimerEntry.StatePrepared or self.timer.state == TimerEntry.StateRunning:
365                         stream = self.timer.record_service.stream()
366                         if stream:
367                                 streamdata = stream.getStreamingData()
368                                 if (streamdata and ('demux' in streamdata)):
369                                         self.demux = streamdata['demux']
370                         if self.demux != -1:
371                                 self.program_do_start(0)
372         
373         
374         # überprüft, ob etwas zu tun ist und gibt die Sekunden zurück, bis die Funktion
375         # spätestens wieder aufgerufen werden sollte
376         # oder -1, um vps_timer löschen zu lassen
377         def check(self):
378                 # Simulation ggf. stoppen
379                 if self.timer.state > TimerEntry.StateWaiting and self.simulate_recordService and self.timer.vpsplugin_overwrite == False:
380                         self.stop_simulation()
381                 
382                 # VPS wurde wieder deaktiviert oder Timer wurde beendet
383                 if self.timer is None or self.timer.state == TimerEntry.StateEnded or self.timer.cancelled:
384                         self.program_abort()
385                         self.stop_simulation()
386                         #print "[VPS-Plugin] Timer wurde beendet"
387                         return -1
388                 
389                 if self.timer.vpsplugin_enabled == False or config.plugins.vps.enabled.value == False:
390                         if self.activated_auto_increase:
391                                 self.timer.autoincrease = False
392                         self.program_abort()
393                         self.stop_simulation()
394                         #print "[VPS-Plugin] VPS wurde bei Timer wieder deaktiviert"
395                         return -1
396                 
397                 self.nextExecution = 180
398                 
399                 if self.timer.vpsplugin_overwrite == True:
400                         if config.plugins.vps.allow_overwrite.value == True:
401                                 self.nextExecution = 60
402                                 if self.timer.state == TimerEntry.StateWaiting or self.timer.state == TimerEntry.StatePrepared:
403                                         # Startzeit verschieben
404                                         if (self.timer.begin - 60) < time():
405                                                 if self.org_timer_begin == 0:
406                                                         self.org_timer_begin = self.timer.begin
407                                                 elif (self.org_timer_begin + (5*3600)) < time():
408                                                         # Sendung begann immer noch nicht -> abbrechen
409                                                         self.timer.abort()
410                                                         self.session.nav.RecordTimer.doActivate(self.timer)
411                                                         self.program_abort()
412                                                         self.stop_simulation()
413                                                         self.timer.log(0, "[VPS] abort timer, waited hours to find Event-ID")
414                                                         return -1
415                                                 
416                                                 self.timer.begin += 60
417                                                 if (self.timer.end - self.timer.begin) < 300:
418                                                         self.timer.end += 60
419                                                 self.timer.timeChanged()
420                                                 #print "[VPS-Plugin] verschiebe Startzeit des Timers (overwrite)"
421                                         
422                                         if 30 < self.nextExecution:
423                                                 self.nextExecution = 30
424                                 
425                                 if self.last_overwrite_enabled == False:
426                                         self.last_overwrite_enabled = True
427                                 
428                                 # Programm wird auch bei laufendem Timer gestartet
429                                 # mind. 2 Minuten Vorlaufzeit bekommen die VPS-Timer hier
430                                 if self.program_running == False and (config.plugins.vps.initial_time.value < 2 or self.timer.state == TimerEntry.StateRunning):
431                                         if (self.timer.begin - 120) <= time():
432                                                 self.program_start()
433                                         else:
434                                                 n = self.timer.begin - 120 - time()
435                                                 if n < self.nextExecution:
436                                                         self.nextExecution = n
437                         else:
438                                 self.timer.vpsplugin_overwrite = False
439                 
440                 # Wurde Overwrite deaktiviert?
441                 if self.timer.vpsplugin_overwrite == False and self.last_overwrite_enabled == True:
442                         self.last_overwrite_enabled = False
443                         # Wenn der Timer eh schon kurz vor Ende ist, dann Programm nicht beenden.
444                         #if self.program_running == True and (self.timer.end - 180) > time():
445                         self.program_abort()
446                 
447                 # Vorlaufzeit zur Prüfung
448                 if (self.timer.state == TimerEntry.StateWaiting or self.timer.state == TimerEntry.StatePrepared) and self.program_running == False and config.plugins.vps.initial_time.value > 0:
449                         if (self.timer.begin - (config.plugins.vps.initial_time.value * 60)) <= time():
450                                 self.program_start()
451                         else:
452                                 n = self.timer.begin - (config.plugins.vps.initial_time.value * 60) - time()
453                                 if n < self.nextExecution:
454                                         self.nextExecution = n
455                 
456                 # kurz vor (eigentlichem) Ende der Aufnahme Programm starten
457                 if self.timer.state == TimerEntry.StateRunning:
458                         if self.program_running == False:
459                                 if (self.timer.end - 120) <= time():
460                                         self.program_start()
461                                 else:
462                                         n = self.timer.end - 120 - time()
463                                         if n < self.nextExecution:
464                                                 self.nextExecution = n
465                         elif self.program_running == True and (self.timer.end - 120) > time() and self.timer.vpsplugin_overwrite == False:
466                                 self.program_abort()
467                         
468                         if self.activated_auto_increase and self.org_timer_end != 0 and (self.org_timer_end + (4*3600)) < time():
469                                 # Aufnahme läuft seit 4 Stunden im Autoincrease -> abbrechen
470                                 self.timer.autoincrease = False
471                                 self.activated_auto_increase = False
472                                 self.dont_restart_program = True
473                                 self.program_abort()
474                                 self.stop_simulation()
475                                 self.timer.log(0, "[VPS] stop recording, too much autoincrease")
476                 
477                 # suche nach weiteren Sendungen mit der VPS-Zeit
478                 if self.found_pdc == True:
479                         if self.program_seek_vps_multiple_started == 0 and self.timer.vpsplugin_overwrite == True:
480                                 self.program_seek_vps_multiple_start()
481                         elif self.program_seek_vps_multiple_started > 0 and ((time() - self.program_seek_vps_multiple_started) >= 60):
482                                 self.program_seek_vps_multiple_abort()
483                 
484                 return self.nextExecution
485
486 class vps:
487         def __init__(self):
488                 self.timer = eTimer()
489                 self.timer.callback.append(self.checkTimer)
490
491                 self.vpstimers = [ ]
492                 self.current_timers_list = [ ]
493                 self.max_activation = 900
494         
495         def checkTimer(self):
496                 nextExecution = self.max_activation
497                 
498                 # nach den Timern schauen und ggf. zur Liste hinzufügen
499                 if config.plugins.vps.enabled.value == True:
500                         now = time()
501                         try:
502                                 for timer in self.session.nav.RecordTimer.timer_list:
503                                         n = timer.begin - now - (config.plugins.vps.initial_time.value * 60) - 120
504                                         if n <= self.max_activation:
505                                                 if timer.vpsplugin_enabled == True and timer not in self.current_timers_list and not timer.justplay and not timer.repeated and not timer.disabled:
506                                                         self.addTimerToList(timer)
507                                                         #print "[VPS-Plugin] neuen VPS-Timer gefunden"
508                                         else:
509                                                 break
510                         except AttributeError:
511                                 print "[VPS-Plugin] AttributeError in Vps.py"
512                                 return
513                 else:
514                         nextExecution = 14400
515                 
516                 # eigene Timer-Liste durchgehen
517                 for o_timer in self.vpstimers[:]:
518                         newtime = int(o_timer.check())
519                         if newtime == -1:
520                                 self.current_timers_list.remove(o_timer.timer)
521                                 self.vpstimers.remove(o_timer)
522                         elif newtime < nextExecution:
523                                 nextExecution = newtime
524                 
525                 if nextExecution <= 0:
526                         nextExecution = 1
527                 
528                 self.timer.startLongTimer(nextExecution)
529                 print "[VPS-Plugin] next execution in "+ str(nextExecution) +" sec" 
530         
531         def addTimerToList(self, timer):
532                 self.vpstimers.append(vps_timer(timer, self.session))
533                 self.current_timers_list.append(timer)
534         
535         def checksoon(self, newstart = 3000):
536                 self.timer.start(newstart, True)
537         
538         def shutdown(self):
539                 for o_timer in self.vpstimers:
540                         o_timer.program_abort()
541                         o_timer.stop_simulation()
542                         o_timer.program_seek_vps_multiple_abort()
543         
544         def NextWakeup(self):
545                 if config.plugins.vps.enabled.value == False or config.plugins.vps.allow_wakeup.value == False:
546                         return -1
547                 
548                 try:
549                         for timer in self.session.nav.RecordTimer.timer_list:
550                                 if timer.vpsplugin_enabled == True and timer.state == TimerEntry.StateWaiting and not timer.justplay and not timer.repeated and not timer.disabled:
551                                         if config.plugins.vps.initial_time.value < 2 and timer.vpsplugin_overwrite:
552                                                 return (timer.begin - 180)
553                                         
554                                         return (timer.begin - (config.plugins.vps.initial_time.value * 60) - 60)
555                 except:
556                         pass
557                 
558                 return -1
559
560 vps_timers = vps()