/*!
 * \file    LVC_RWLockManager.hpp
 * \author  IvanS
 * \brief   Reader-writer lock manager.
 */
/*

    ========== licence begin  GPL
    Copyright (c) 2002-2005 SAP AG

    This program is free software; you can redistribute it and/or
    modify it under the terms of the GNU General Public License
    as published by the Free Software Foundation; either version 2
    of the License, or (at your option) any later version.

    This program 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 General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with this program; if not, write to the Free Software
    Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
    ========== licence end


*/

#ifndef __LVC_RWLOCKMANAGER_HPP
#define __LVC_RWLOCKMANAGER_HPP

#include "RunTime/Synchronisation/RTESync_RWRegion.hpp"
#include "RunTime/Synchronisation/RTESync_Spinlock.hpp"

class RTESync_IRWRegion;
class SAPDBMem_IRawAllocator;

class LVC_RWLockManager {
public:
  LVC_RWLockManager(SAPDBMem_IRawAllocator &alloc, RTESync_SpinlockPool &spinlockPool);
  ~LVC_RWLockManager();

  /*!
   * \brief Get lock for given ID.
   *
   * \param id lock ID
   * \param createNew if true, create new lock if doesn't exist.
   * \return lock handle or null.
   */
  RTESync_IRWRegion *getLock(int id, bool createNew);
private:

  class Entry {
  public:
    /// Lock ID
    int                   m_id;
    /// Underlying lock
    RTESync_IRWRegion*    m_lock;
    /// Next entry in hash bucket
    Entry*                m_next;
  };

  /// Allocator for R/W locks.
  SAPDBMem_IRawAllocator  &m_alloc;
  /// Spinlock pool for R/W regions.
  RTESync_SpinlockPool    &m_spinlock_pool;
  /// Reader/writer locks for R/W regions.
  Entry** volatile        m_rw_locks;
  /// Current size of the hash table
  volatile int            m_hash_size;
  /// Limit for size.
  int                     m_limit;
  /// Count of items.
  int                     m_count;
  /// Lock on entries.
  RTESync_Spinlock        m_lock;
};

#endif  // __LVC_RWLOCKMANAGER_HPP
