I'm trying to handle errors that occur in some of my timer functions (TimerFcn, StopFcn, ...). My problem is that I need to handle the errors outside of the actual callbacks. However, the following does not work:
callback = @(~, ~) error('Oops.');
try
t = timer('TimerFcn', callback);
start(t);
catch e
fprintf('Caught exception: %s\n', e.message);
end
The output is:
Error while evaluating TimerFcn for timer 'timer-5'
Oops.
I do understand why the above code does not work (after all, the idea of timers is to execute asynchronously). However I haven't found any other official way to achieve my goal (e.g. a global error handler that I could hook into).
The only workaround I've found so far is to shadow error:
oldError = @error;
errors = {};
error = @(varargin) assignin('base', 'errors', [evalin('base', 'errors'), {varargin}]);
callback = @(~, ~) error('Oops.');
t = timer('TimerFcn', callback);
start(t);
wait(t);
The error is now stored in errors. However, this approach has a lot of problems: when to restore the original error function? How to deal with errors raised by code other than the timer functions? ...
Hence: How can I handle errors in timer functions in a clean and reliable way?
You should probably use the ErrorFcn property of the timer object.
A simple example:
>> tcallback = @(~, ~) error('Oops.');
>> ecallback = @(~, ~) disp('Caught error');
>> t = timer('TimerFcn', tcallback, 'ErrorFcn', ecallback);
>> start(t)
Error while evaluating TimerFcn for timer 'timer-2'
Oops.
Caught error
You can obviously make your error handling more robust than that, but it takes care of the asynchronous nature of timer errors. The input arguments to the ErrorFcn (if you don't suppress them as in the above example) provide information about the error that was thrown, so you can handle them specifically.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With