
/*
  CoreLinux++ 
  Copyright (C) 1999,2000 CoreLinux Consortium
  
   The CoreLinux++ Library is free software; you can redistribute it and/or
   modify it under the terms of the GNU Library General Public License as
   published by the Free Software Foundation; either version 2 of the
   License, or (at your option) any later version.

   The CoreLinux++ Library Library is distributed in the hope that it will 
   be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
   Library General Public License for more details.

   You should have received a copy of the GNU Library General Public
   License along with the GNU C Library; see the file COPYING.LIB.  If not,
   write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
   Boston, MA 02111-1307, USA.  
*/

#if   !defined(__COMMON_HPP)
#include <Common.hpp>
#endif

#if   !defined(__SEMAPHORE_HPP)
#include <Semaphore.hpp>
#endif

extern "C"
{
   #include <sys/sem.h>
}

static   SemaphoreIdentifier  dummy(-1);

namespace corelinux
{
   //
   // Default constructor not allowed
   //

   Semaphore::Semaphore( void ) throw(Assertion)
      :
      AbstractSemaphore( NULLPTR, dummy ),
      theOwningThread(-1),
      theRecursionQueueLength(0)
   {
      NEVER_GET_HERE;
   }

   //
   // Copy constructor not allowed
   //

   Semaphore::Semaphore( SemaphoreCref ) throw(Assertion)
      :
      AbstractSemaphore( NULLPTR, dummy ),
      theOwningThread(-1),
      theRecursionQueueLength(0)
   {
      NEVER_GET_HERE;
   }

   //
   // Default constructor to use
   //

   Semaphore::Semaphore
      ( 
         SemaphoreGroupPtr       aGroup,
         SemaphoreIdentifierRef  aIdentifier,
         bool                    aRecursionFlag,
         bool                    aBalkingFlag
      ) throw ( NullPointerException )
      :
      AbstractSemaphore(aGroup,aIdentifier),
      theOwningThread(0),
      theRecursionQueueLength(0),
      theRecursiveMode( aRecursionFlag ),
      theBalkingMode( aBalkingFlag )
   {
      ;  // do nothing
   }

   //
   // Virtual Destructor
   //

   Semaphore::~Semaphore( void )
   {
      theOwningThread = (-1);
      theRecursionQueueLength = 0;
   }

   //
   // Equality operator
   //

   bool  Semaphore::operator==( SemaphoreCref aSemaphore ) const
   {
      return ( getIdentifier() == aSemaphore.getIdentifier() &&
               aSemaphore.getGroupIdentifier() == getGroupIdentifier() );
   }

   //
   // Assignment operator
   //

   SemaphoreRef   Semaphore::operator=( SemaphoreCref ) throw( Assertion )
   {
      NEVER_GET_HERE;
      return ( *this );
   }

   // Increment operator

   CounterCref Semaphore::operator++( void )
   {
      return (++theRecursionQueueLength);
   }

   // Decrement operator

   CounterCref Semaphore::operator--( void )
   {
      return (--theRecursionQueueLength);
   }

   // Returns true if balking enabled

   bool  Semaphore::isBalkingEnabled( void ) const
   {
      return theBalkingMode;
   }

   // Returns true if recursion allowed

   bool  Semaphore::isRecursionEnabled( void ) const
   {
      return theRecursiveMode;
   }

   // Return the current thread owner

   ThreadIdentifierCref Semaphore::getOwningThreadIdentifier( void ) const
   {
      return theOwningThread;
   }

   // Return the queue length for recursion

   CounterCref Semaphore::getRecursionQueueLength( void ) const
   {
      return theRecursionQueueLength;
   }

   // Protected method for retrieving thread identifier

   ThreadIdentifierRef  Semaphore::getOwnerId( void )
   {
      return theOwningThread;
   }

   // Protected method for setting thread identifier

   void  Semaphore::setOwnerId( void )
   {
      theOwningThread = Thread::getThreadIdentifier();
   }

   // Protected method for setting queue length

   void  Semaphore::setRecursionQueueLength( Counter aCount )
   {
      theRecursionQueueLength = aCount;
   }

   // Protected method for setting the thread identifier to non

   void  Semaphore::resetOwnerId( void )
   {
      theOwningThread = (0);
      theRecursionQueueLength = (0);
   }

}

/*
   Common rcs information do not modify
   $Author: frankc $
   $Revision: 1.5 $
   $Date: 2000/06/02 11:51:52 $
   $Locker:  $
*/



