# HG changeset patch # User Laurent Bessard # Date 1351958426 -3600 # Node ID a8952b79caec2c861f3e78451113a7058470acea # Parent 8b24e9312f1836a98ae17b3a6c720c92dcd5f823 Fix bug in Debug refresh lock that, with too much data to debug, flooded GUI and blocked it diff -r 8b24e9312f18 -r a8952b79caec Beremiz.py --- a/Beremiz.py Wed Oct 31 12:05:44 2012 +0100 +++ b/Beremiz.py Sat Nov 03 17:00:26 2012 +0100 @@ -211,9 +211,16 @@ if current_time - self.LastRefreshTime > REFRESH_PERIOD and self.RefreshLock.acquire(False): self._should_write() else: - self.LastRefreshTimer = Timer(REFRESH_PERIOD, self._should_write) + self.LastRefreshTimer = Timer(REFRESH_PERIOD, self._timer_expired) self.LastRefreshTimer.start() + def _timer_expired(self): + if self.RefreshLock.acquire(False): + self._should_write() + else: + self.LastRefreshTimer = Timer(REFRESH_PERIOD, self._timer_expired) + self.LastRefreshTimer.start() + def _should_write(self): wx.CallAfter(self._write) if MainThread == currentThread().ident: @@ -225,7 +232,7 @@ def _write(self): if self.output : - self.output.Freeze(); + self.output.Freeze() self.lock.acquire() for s, style in self.stack: if style is None : style=self.black_white @@ -247,7 +254,7 @@ if newtime - self.rising_timer > 1: self.risecall() self.rising_timer = newtime - + def write_warning(self, s): self.write(s,self.red_white) diff -r 8b24e9312f18 -r a8952b79caec graphics/GraphicCommons.py --- a/graphics/GraphicCommons.py Wed Oct 31 12:05:44 2012 +0100 +++ b/graphics/GraphicCommons.py Sat Nov 03 17:00:26 2012 +0100 @@ -27,7 +27,7 @@ from math import * from types import * import datetime -from threading import Semaphore +from threading import Lock,Timer #------------------------------------------------------------------------------- # Common constants @@ -293,6 +293,7 @@ #------------------------------------------------------------------------------- REFRESH_PERIOD = 0.1 +DEBUG_REFRESH_LOCK = Lock() class DebugViewer: @@ -305,10 +306,10 @@ self.DataConsumers = {} self.LastRefreshTime = gettime() - self.RefreshLock = Semaphore() + self.HasAcquiredLock = False + self.AccessLock = Lock() - self.RefreshTimer = wx.Timer(self, -1) - self.Bind(wx.EVT_TIMER, self.OnRefreshTimer, self.RefreshTimer) + self.LastRefreshTimer = None self.SetDataProducer(producer) @@ -366,15 +367,26 @@ self.DataProducer.UnsubscribeDebugIECVariable(iec_path, consumer) self.DataConsumers = {} - def OnRefreshTimer(self, event): - self.RefreshNewData() - event.Skip() + def ShouldRefresh(self): + if DEBUG_REFRESH_LOCK.acquire(False): + self.AccessLock.acquire() + self.HasAcquiredLock = True + self.AccessLock.release() + self.RefreshNewData() + else: + self.LastRefreshTimer = Timer(REFRESH_PERIOD, self.ShouldRefresh) + self.LastRefreshTimer.start() def NewDataAvailable(self, *args, **kwargs): - self.RefreshTimer.Stop() + if self.LastRefreshTimer is not None: + self.LastRefreshTimer.cancel() + self.LastRefreshTimer=None if not self.Inhibited: current_time = gettime() - if current_time - self.LastRefreshTime > REFRESH_PERIOD and self.RefreshLock.acquire(False): + if current_time - self.LastRefreshTime > REFRESH_PERIOD and DEBUG_REFRESH_LOCK.acquire(False): + self.AccessLock.acquire() + self.HasAcquiredLock = True + self.AccessLock.release() self.LastRefreshTime = gettime() self.Inhibit(True) wx.CallAfter(self.RefreshViewOnNewData, *args, **kwargs) @@ -382,12 +394,17 @@ def RefreshViewOnNewData(self, *args, **kwargs): if self: self.RefreshNewData(*args, **kwargs) - self.RefreshTimer.Start(int(REFRESH_PERIOD * 1000), oneShot=True) + self.LastRefreshTimer = Timer(REFRESH_PERIOD, self.ShouldRefresh) + self.LastRefreshTimer.start() def RefreshNewData(self, *args, **kwargs): self.Inhibit(False) - self.RefreshLock.release() - + self.AccessLock.acquire() + if self.HasAcquiredLock: + DEBUG_REFRESH_LOCK.release() + self.HasAcquiredLock = False + self.AccessLock.release() + #------------------------------------------------------------------------------- # Viewer Rubberband #-------------------------------------------------------------------------------