Class: ProcessShared::BinarySemaphore

Inherits:
Semaphore show all
Defined in:
lib/process_shared/binary_semaphore.rb

Overview

BinarySemaphore is identical to Semaphore except that its value is not permitted to rise above one (it may be either zero or one). When the value is at the maximum, calls to #post will raise an exception.

This is identical to a Semaphore but with extra error checking.

Instance Method Summary collapse

Methods inherited from Semaphore

#close, open, #try_wait, #value, #wait

Methods inherited from AbstractSemaphore

gen_name, make_finalizer, #synchronize

Methods included from PSem

psem_error_check

Methods included from DefineSingletonMethod

#define_singleton_method

Methods included from WithSelf

#with_self

Constructor Details

#initialize(value = 1, name = nil) ⇒ BinarySemaphore

Create a new semaphore with initial value value. After Kernel#fork, the semaphore will be shared across two (or more) processes. The semaphore must be closed with Semaphore#close in each process that no longer needs the semaphore.

(An object finalizer is registered that will close the semaphore to avoid memory leaks, but this should be considered a last resort).

Parameters:

  • value (Integer) (defaults to: 1)

    the initial semaphore value

  • name (String) (defaults to: nil)

    not currently supported



24
25
26
27
# File 'lib/process_shared/binary_semaphore.rb', line 24

def initialize(value = 1, name = nil)
  raise ArgumentErrror 'value must be 0 or 1' if (value < 0 or value > 1)
  super(value, name)
end

Instance Method Details

#postObject

Increment from zero to one.

First, attempt to decrement. If this fails with EAGAIN, the semaphore was at zero, so continue with the post. If this succeeds, the semaphore was not at zero, so increment back to one and raise ProcesError (multiple workers may have acquired the semaphore at this point).



36
37
38
39
40
41
42
43
44
45
46
# File 'lib/process_shared/binary_semaphore.rb', line 36

def post
  begin
    try_wait
    # oops, value was not zero...
    psem_post(sem, err)
    raise ProcessError, 'post would raise value over bound'
  rescue Errno::EAGAIN
    # ok, value was zero
    psem_post(sem, err)
  end
end