Module: Itimer

Defined in:
lib/itimer.rb

Defined Under Namespace

Classes: Timeout

Class Method Summary collapse

Class Method Details

.timeout(seconds, klass = Timeout) ⇒ Object



7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
# File 'lib/itimer.rb', line 7

def self.timeout(seconds, klass=Timeout)
  @counter ||= 0
  @counter += 1

  catch_name = "itimer_#{@counter}"

  prev_handler = Signal.trap 'ALRM' do
    throw catch_name
  end

  prev = get(:real)
  start = Time.now
  if prev > 0
    seconds = [prev, seconds].min
  end

  timed_out = true
  ret = nil

  catch catch_name do
    set(:real, seconds)
    begin
      ret = yield
      timed_out = false
    ensure
      if prev > 0
        set(:real, [prev - (Time.now-start), 0.01].max)
      else
        set(:real, 0)
      end

      Signal.trap('ALRM', prev_handler)
    end
  end

  if timed_out
    raise klass
  end

  return ret
end