 /* @file privadata.h
  * 
  * @brief Holds definition for driver's private data and its manipulation functions. 
  * 
  * 
  * 
  */

/** @par LICENCE
 * 
 *  @verbatim
   Copyright (C) 2009  ADDI-DATA GmbH for the source code of this module.
        
   ADDI-DATA GmbH
   Airpark Business Center
   Airport Boulevard B210
   77836 Rheinm�nster
   Germany
   Tel: +49(0)7229/1847-0
   Fax: +49(0)7229/1847-200
   http://www.addi-data-com
   info@addi-data.com
 
 This library is free software; you can redistribute it and/or modify it under 
 the terms of the GNU Lesser General Public License as published by the 
 Free Software Foundation; either version 2.1 of the License, 
 or (at your option) any later version.
 
 This 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 Lesser General Public License for more details.
 
 You should have received a copy of the GNU Lesser General Public License 
 along with this library; if not, write to the Free Software Foundation, 
 Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
 
 
 You also shoud find the complete LGPL in the LGPL.txt file accompanying 
 this source code.
 
 @endverbatim
**/

#ifndef __APCIE1516_PRIVDATA_H_
#define __APCIE1516_PRIVDATA_H_

#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,26)		
	#include <asm/semaphore.h>
#else
	#include <linux/semaphore.h>
#endif


/* internal driver data */
struct apcie1516_str_BoardInformations
{
	struct semaphore sem; /**< semaphore protect the board data */

	unsigned char OutputMemoryStatus;	/**< Digital Output Memory Status (0: not active, 1: active) */     
	uint16_t RegisterDigitalOutput;		/**< Map the digital output register */	
	/* field used to implement linked list */
	struct pci_dev * previous; /**< previous in known-devices linked list */
	struct pci_dev * next; /**< next in known-devices linked list */
};

/** initialise board's private data - fill it when adding new members and ioctl handlers */
static __inline__ void apcie1516_init_priv_data(struct apcie1516_str_BoardInformations * data)
{
	/* Initialize the board structure */
	memset(data, 0, sizeof(struct apcie1516_str_BoardInformations));
	
	sema_init(&(data->sem), 1);	
}

/** typed cast (safer to use) */
static __inline__ struct apcie1516_str_BoardInformations * APCIE1516_PRIVDATA(struct pci_dev * pdev)
{	
	return (struct apcie1516_str_BoardInformations *) pci_get_drvdata(pdev);	
}

/** used to lock the board - 
 * may be interrupted : check return value 
 * like that:
 * if (APCIE1516_DOWN(pdev))
 * 	return -ERESTARTSYS;
 * 
 * */
static inline int APCIE1516_LOCK(struct pci_dev * pdev, unsigned long * flags)
{
	return down_interruptible(&(APCIE1516_PRIVDATA(pdev)->sem));
}

/** release the semaphore */
static inline void APCIE1516_UNLOCK(struct pci_dev * pdev, unsigned long flags)
{
	up(&(APCIE1516_PRIVDATA(pdev)->sem));
}


#endif // __APCIE1516_PRIVDATA_H_
