From: Artur Bergman Date: Wed, 1 May 2002 17:54:19 +0000 (+0000) Subject: Add semaphore.pm X-Git-Url: http://git.shadowcat.co.uk/gitweb/gitweb.cgi?a=commitdiff_plain;h=0b876b54c46ad609b64df8dfe0d6cc37987c3201;p=p5sagit%2Fp5-mst-13.2.git Add semaphore.pm p4raw-id: //depot/perl@16311 --- diff --git a/ext/threads/shared/semaphore.pm b/ext/threads/shared/semaphore.pm new file mode 100644 index 0000000..f8aa3e0 --- /dev/null +++ b/ext/threads/shared/semaphore.pm @@ -0,0 +1,90 @@ +package threads::shared::semaphore; + +use threads::shared; + +our $VERSION = '1.00'; + +=head1 NAME + +Thread::Semaphore - thread-safe semaphores + +=head1 SYNOPSIS + + use Thread::Semaphore; + my $s = new Thread::Semaphore; + $s->up; # Also known as the semaphore V -operation. + # The guarded section is here + $s->down; # Also known as the semaphore P -operation. + + # The default semaphore value is 1. + my $s = new Thread::Semaphore($initial_value); + $s->up($up_value); + $s->down($up_value); + +=head1 DESCRIPTION + +Semaphores provide a mechanism to regulate access to resources. Semaphores, +unlike locks, aren't tied to particular scalars, and so may be used to +control access to anything you care to use them for. + +Semaphores don't limit their values to zero or one, so they can be used to +control access to some resource that may have more than one of. (For +example, filehandles) Increment and decrement amounts aren't fixed at one +either, so threads can reserve or return multiple resources at once. + +=head1 FUNCTIONS AND METHODS + +=over 8 + +=item new + +=item new NUMBER + +C creates a new semaphore, and initializes its count to the passed +number. If no number is passed, the semaphore's count is set to one. + +=item down + +=item down NUMBER + +The C method decreases the semaphore's count by the specified number, +or one if no number has been specified. If the semaphore's count would drop +below zero, this method will block until such time that the semaphore's +count is equal to or larger than the amount you're Cing the +semaphore's count by. + +=item up + +=item up NUMBER + +The C method increases the semaphore's count by the number specified, +or one if no number's been specified. This will unblock any thread blocked +trying to C the semaphore if the C raises the semaphore count +above what the Cs are trying to decrement it by. + +=back + +=cut + +sub new { + my $class = shift; + my $val : shared = @_ ? shift : 1; + bless \$val, $class; +} + +sub down { + my $s = shift; + lock($s); + my $inc = @_ ? shift : 1; + cond_wait $s until $$s >= $inc; + $$s -= $inc; +} + +sub up { + my $s = shift; + lock($s); + my $inc = @_ ? shift : 1; + ($$s += $inc) > 0 and cond_broadcast $s; +} + +1;