
//  SAMSUNG ELECTRONICS
//  Copyright(C) 2006
//  ALL RIGHTS RESERVED
//
//  This program is proprietary to Samsung Electronics,and is protected under International
//  Copyright Act as an unpublished work.Its use and disclosure is limited by the terms and
//  conditions of a license agreement. It may not be copied or otherwise reproduced or
//  disclosed to persons outside the licensee's organization except in accordance with
//  the terms and conditions of such an agreement.All copies and reproductions shall be
//  the property of Samsung Electronics and must bear this notice in its entirety.


//  File name: sgip_GpioPrimitives.h
//
//  Descriptions: this file contains the Samsung General purpose IO port Primitives (SGIP).
//              Bit Encoding information and Primitive macros to handle the GPIO
//
//  History :
//          Oct 18 2006 : First generated by jlpark
//          Mar 06 2007 : Modified for S3C6400 by jlpark
//          Jul 17 2009 : Modified for S5PV210 by JOHNLAY
//          Apr 12 2010 : Modified for S5PV210 by jungchul2.park

#ifndef __SGIP_GPIOPRIMITIVE_H__
#define __SGIP_GPIOPRIMITIVE_H__

#define USE_SGIPMETHOD   1

// Basic Constants
#define MASK_1  0x1
#define MASK_2  0x3
#define MASK_3  0x7
#define MASK_4  0xf
#define MASK_8  0xff

#define BIT_InitDat     31
#define BIT_InitPU      29
#define BIT_FMux4       26
#define BIT_FCon2       25
#define BIT_FPin8       24
#define BIT_PinIdx      20
#define BIT_ConVal      16
#define BIT_MuxNum      12
#define BIT_ConNum      8
#define BIT_Offset      0

#define SGIP_DatRegNum  1
#define SGIP_PuMuxNum   1   // 2-1
#define SGIP_PuMask     MASK_2

// Primitive methods
// Encoding Method __________________________//
#define spEnc_Offset(val)   ((0xff & (val)) << BIT_Offset)
#define spEnc_ConNum(val)   (( 0xf & (val)) << BIT_ConNum)
#define spEnc_MuxNum(val)   (( 0xf & (val)) << BIT_MuxNum)
#define spEnc_ConVal(val)   (( 0xf & (val)) << BIT_ConVal)
#define spEnc_PinIdx(val)   (( 0xf & (val)) << BIT_PinIdx)
#define spEnc_BitIdx8(val)  (( 0x1 & (val)) << BIT_FPin8)
#define spEnc_ConNum2(val)  (( 0x1 & (val)) << BIT_FCon2)
#define spEnc_MuxNum4(val)  (( 0x1 & (val)) << BIT_FMux4)
#define spEnc_InitPU(val)   (( 0x3 & (val)) << BIT_InitPU)
#define spEnc_InitDat(val)  (( 0x1 & (val)) << BIT_InitDat)

#define sp_GroupEncoder(Mux, Con, Off)  (spEnc_MuxNum(Mux)|spEnc_ConNum(Con)|spEnc_Offset(Off))
#define sp_PinEncoder(GroupInfo, fIdx8, DatIdx, ConVal) (GroupInfo|spEnc_BitIdx8(fIdx8)|spEnc_PinIdx(DatIdx)|spEnc_ConVal(ConVal))

// Retrieve Macro ___________________________//
#define sgipGetDatVal(Attribute)    ((Attribute & 0x80000000) >> BIT_InitDat)
#define sgipGetPuPdVal(Attribute)   ((Attribute & 0x60000000) >> BIT_InitPU)
// [26:28] are reserved.
#define sgipGetFlag2(Attribute)     ((Attribute & 0x04000000) >> BIT_FMux4) // Is the Mux 4?
#define sgipGetFlag1(Attribute)     ((Attribute & 0x02000000) >> BIT_FCon2) // Is the Con. Reg Number 2? & Mux 4
#define sgipGetFlag0(Attribute)     ((Attribute & 0x01000000) >> BIT_FPin8) // Is the Bit Position more than 8 & Mux 4?

#define sgipGetPinIdx(Attribute)    ((Attribute & 0x00f00000) >> BIT_PinIdx)
#define sgipGetConVal(Attribute)    ((Attribute & 0x000f0000) >> BIT_ConVal)
#define sgipGetMuxNum(Attribute)    ((Attribute & 0x0000f000) >> BIT_MuxNum)
#define sgipGetConRegNum(Attribute) ((Attribute & 0x00000f00) >> BIT_ConNum)
#define sgipGetGroupOFs(Attribute)  ((Attribute & 0x000000ff) >> BIT_Offset)

// Mux == 4, Control register == 2, PinIdx >= 8
#define sgipIsSpecialPin(Attribute) ((sgipGetFlag0(Attribute))&(sgipGetFlag1(Attribute))&(sgipGetFlag2(Attribute)))
#define sgipDatOffset(Attribute)    (((sgipGetGroupOFs(Attribute)) << 2) + (sgipGetFlag1(Attribute)) + 1)

#define sgipConMask(Attribute)      (MASK_2|(MASK_2 << ((sgipGetFlag2(Attribute)) << 1))) // Mux 4 : 0xf, Mux 2 : 0x3
#define sgipConOffset(Attribute)    (((sgipGetGroupOFs(Attribute)) << 2) + (sgipIsSpecialPin(Attribute)))
#define sgipConIdx(Attribute)       (sgipGetMuxNum(Attribute) * (sgipGetPinIdx(Attribute) - ((sgipIsSpecialPin(Attribute)) << 3)))

// Con : 0x00, Dat : 0x04, Pud : 0x08, Drv : 0x0c, ConPdn : 0x10, PuPdn : 0x14
#define sgipConRegAddr(BaseAddr, Attribute)     (*(volatile unsigned long * const)((unsigned long *)(BaseAddr) + (sgipConOffset(Attribute))))
#define sgipDatRegAddr(BaseAddr, Attribute)     (*(volatile unsigned long * const)((unsigned long *)(BaseAddr) + (sgipDatOffset(Attribute))))
#define sgipPuRegAddr(BaseAddr, Attribute)      (*(volatile unsigned long * const)((unsigned long *)(BaseAddr) + (sgipDatOffset(Attribute)) + SGIP_DatRegNum))
#define sgipDrvRegAddr(BaseAddr, Attribute)     (*(volatile unsigned long * const)((unsigned long *)(BaseAddr) + (sgipDatOffset(Attribute)) + 2))
#define sgipConPDRegAddr(BaseAddr, Attribute)   (*(volatile unsigned long * const)((unsigned long *)(BaseAddr) + (sgipDatOffset(Attribute)) + 3))
#define sgipPuPDRegAddr(BaseAddr, Attribute)    (*(volatile unsigned long * const)((unsigned long *)(BaseAddr) + (sgipDatOffset(Attribute)) + 4))

#define sgipGetPuPinIdx(Attribute)  ((sgipGetPinIdx(Attribute)) << SGIP_PuMuxNum)


// WKUP INT __________________________________________________________//
// WEINT CON
#define BIT_CONADDR     28
#define BIT_FLTADDR      16
#define BIT_PNDADDR       8
#define BIT_IDXADDR        0

// Only defined in S5PV210
#define BASEADDR_EXT_CON               0xE00
#define BASEADDR_EXT_FLTCON        0xE80
#define BASEADDR_EXT_MASK            0xF00
#define BASEADDR_EXT_PEND            0xF40

#define spEnc_EINTCONADDR(val)   ((MASK_4 & (val)) << BIT_CONADDR)
#define spEnc_EINTFLTADDR(val)   ((MASK_8  & (val)) << BIT_FLTADDR)
#define spEnc_EINTPNDADDR(val)   ((MASK_4  & (val)) << BIT_PNDADDR)
#define spEnc_EINTMSKADDR(val)   spEnc_EINTPNDADDR(val)
#define spEnc_EINTIDXADDR(val)    ((MASK_4  & (val)) << BIT_IDXADDR)

#define sgipEINTCONReg(Symbol)   (((Symbol & ((MASK_4)<<(BIT_CONADDR))) >> BIT_CONADDR) & (MASK_4))
#define sgipEINTFLTReg(Symbol)    (((Symbol & ((MASK_8)<<(BIT_FLTADDR))) >> BIT_FLTADDR) & (MASK_8))
#define sgipEINTPNDReg(Symbol)   (((Symbol & ((MASK_4)<<(BIT_PNDADDR))) >> BIT_PNDADDR) & (MASK_4))
#define sgipEINTMSKReg(Symbol)   sgipEINTPNDReg(Symbol)
#define sgipEINTIDXReg(Symbol)    (((Symbol & ((MASK_4)<<(BIT_IDXADDR))) >> BIT_IDXADDR) & (MASK_4))

#define sgipEINTConRegAddr(BaseAddr, Attribute)     (*(volatile unsigned long * const)((unsigned long)(BaseAddr) + (BASEADDR_EXT_CON)+(sgipEINTCONReg(Attribute))))
#define sgipEINTFLTRegAddr(BaseAddr, Attribute)     (*(volatile unsigned long * const)((unsigned long)(BaseAddr) + (BASEADDR_EXT_FLTCON)+(sgipEINTFLTReg(Attribute))))
#define sgipEINTMSKRegAddr(BaseAddr, Attribute)     (*(volatile unsigned long * const)((unsigned long)(BaseAddr) + (BASEADDR_EXT_MASK)+(sgipEINTPNDReg(Attribute))))
#define sgipEINTPNDRegAddr(BaseAddr, Attribute)     (*(volatile unsigned long * const)((unsigned long)(BaseAddr) + (BASEADDR_EXT_PEND)+(sgipEINTPNDReg(Attribute))))

#define sgipEINTCONOFT(Symbol)   (sgipEINTIDXReg(Symbol)<<2)
#define sgipEINTFLTOFT(Symbol)    ((sgipEINTIDXReg(Symbol)&0x3)<<3)
#define sgipEINTPNDOFT(Symbol)    sgipEINTIDXReg(Symbol)
#define sgipEINTMSKOFT(Symbol)    sgipEINTIDXReg(Symbol)
#define sgipEINTIDXOFT(Symbol)     sgipEINTIDXReg(Symbol)

#define spEINTEncoder(vCON,vFLT,vPND,vIDX)    ((spEnc_EINTCONADDR(vCON))|(spEnc_EINTFLTADDR(vFLT))|(spEnc_EINTPNDADDR(vPND))|(spEnc_EINTIDXADDR(vIDX)))

#endif  //__SGIP_GPIOPRIMITIVE_H__

