#define __MACH_GPIO_H
#include <mach/irqs.h>
+
+typedef enum eGPIOPinLevel
+{
+ GPIO_LOW=0,
+ GPIO_HIGH
+}eGPIOPinLevel_t;
+
+typedef enum eGPIOPinDirection
+{
+ GPIO_IN=0,
+ GPIO_OUT
+}eGPIOPinDirection_t;
+
+typedef enum GPIOPullType {
+ PullDisable = 0,
+ PullEnable,
+ GPIONormal, //PullEnable, please do not use it
+ GPIOPullUp, //PullEnable, please do not use it
+ GPIOPullDown,//PullEnable, please do not use it
+ GPIONOInit,//PullEnable, please do not use it
+}eGPIOPullType_t;
+
+typedef enum GPIOIntType {
+ GPIOLevelLow=0,
+ GPIOLevelHigh,
+ GPIOEdgelFalling,
+ GPIOEdgelRising
+}eGPIOIntType_t;
+
+//¶¨ÒåGPIOÏà¹Ø¼Ä´æÆ÷Æ«ÒƵØÖ·
+#define GPIO_SWPORT_DR 0x00
+#define GPIO_SWPORT_DDR 0x04
+#define GPIO_INTEN 0x30
+#define GPIO_INTMASK 0x34
+#define GPIO_INTTYPE_LEVEL 0x38
+#define GPIO_INT_POLARITY 0x3c
+#define GPIO_INT_STATUS 0x40
+#define GPIO_INT_RAWSTATUS 0x44
+#define GPIO_DEBOUNCE 0x48
+#define GPIO_PORTS_EOI 0x4c
+#define GPIO_EXT_PORT 0x50
+#define GPIO_LS_SYNC 0x60
+
+#define RK30_ID_GPIO0 0
+#define RK30_ID_GPIO1 1
+#define RK30_ID_GPIO2 2
+#define RK30_ID_GPIO3 3
+#define RK30_ID_GPIO4 4
+#define RK30_ID_GPIO5 5
+
+#define NUM_GROUP 32
+#define MAX_BANK 7
+
+#define PIN_BASE NR_GIC_IRQS
+
+#define RK30_TOTOL_GPIO_NUM (NUM_GROUP*MAX_BANK)
+
+#define SPI_FPGA_EXPANDER_BASE (PIN_BASE+RK30_TOTOL_GPIO_NUM)
+
+#if defined (CONFIG_SPI_FPGA_GPIO)
+#define GPIO_EXPANDER_BASE (PIN_BASE+RK30_TOTOL_GPIO_NUM+CONFIG_SPI_FPGA_GPIO_NUM)
+#else
+#define GPIO_EXPANDER_BASE (PIN_BASE+RK30_TOTOL_GPIO_NUM)
+#endif
+
+#if defined(CONFIG_IOEXTEND_TCA6424)
+#define TCA6424_TOTOL_GPIO_NUM 24
+#define TCA6424_TOTOL_GPIO_IRQ_NUM 24
+#define TCA6424_GPIO_EXPANDER_BASE GPIO_EXPANDER_BASE
+#else
+#define TCA6424_TOTOL_GPIO_NUM 0
+#define TCA6424_TOTOL_GPIO_IRQ_NUM 0
+#endif
+
+#if defined(CONFIG_GPIO_WM831X)
+#define WM831X_TOTOL_GPIO_NUM 12
+#define WM831X_GPIO_EXPANDER_BASE (GPIO_EXPANDER_BASE+TCA6424_TOTOL_GPIO_NUM)
+#else
+#define WM831X_TOTOL_GPIO_NUM 0
+#define WM831X_GPIO_EXPANDER_BASE (GPIO_EXPANDER_BASE+TCA6424_TOTOL_GPIO_NUM)
+#endif
+
+#if defined (CONFIG_GPIO_WM8994)
+#define CONFIG_GPIO_WM8994_NUM 11
+#define WM8994_GPIO_EXPANDER_BASE (GPIO_EXPANDER_BASE+WM831X_TOTOL_GPIO_NUM)
+#else
+#define CONFIG_GPIO_WM8994_NUM 0
+#endif
+
+//¶¨ÒåGPIOµÄPIN¿Ú×î´óÊýÄ¿¡£CONFIG_SPI_FPGA_GPIO_NUM±íʾFPGAµÄPIN½ÅÊý¡£
+#define ARCH_NR_GPIOS (PIN_BASE + RK30_TOTOL_GPIO_NUM + TCA6424_TOTOL_GPIO_NUM + WM831X_TOTOL_GPIO_NUM + CONFIG_SPI_FPGA_GPIO_NUM+CONFIG_GPIO_WM8994_NUM)
+
+
+#define RK30_PIN0_PA0 (0*NUM_GROUP + PIN_BASE + 0)
+#define RK30_PIN0_PA1 (0*NUM_GROUP + PIN_BASE + 1)
+#define RK30_PIN0_PA2 (0*NUM_GROUP + PIN_BASE + 2)
+#define RK30_PIN0_PA3 (0*NUM_GROUP + PIN_BASE + 3)
+#define RK30_PIN0_PA4 (0*NUM_GROUP + PIN_BASE + 4)
+#define RK30_PIN0_PA5 (0*NUM_GROUP + PIN_BASE + 5)
+#define RK30_PIN0_PA6 (0*NUM_GROUP + PIN_BASE + 6)
+#define RK30_PIN0_PA7 (0*NUM_GROUP + PIN_BASE + 7)
+#define RK30_PIN0_PB0 (0*NUM_GROUP + PIN_BASE + 8)
+#define RK30_PIN0_PB1 (0*NUM_GROUP + PIN_BASE + 9)
+#define RK30_PIN0_PB2 (0*NUM_GROUP + PIN_BASE + 10)
+#define RK30_PIN0_PB3 (0*NUM_GROUP + PIN_BASE + 11)
+#define RK30_PIN0_PB4 (0*NUM_GROUP + PIN_BASE + 12)
+#define RK30_PIN0_PB5 (0*NUM_GROUP + PIN_BASE + 13)
+#define RK30_PIN0_PB6 (0*NUM_GROUP + PIN_BASE + 14)
+#define RK30_PIN0_PB7 (0*NUM_GROUP + PIN_BASE + 15)
+#define RK30_PIN0_PC0 (0*NUM_GROUP + PIN_BASE + 16)
+#define RK30_PIN0_PC1 (0*NUM_GROUP + PIN_BASE + 17)
+#define RK30_PIN0_PC2 (0*NUM_GROUP + PIN_BASE + 18)
+#define RK30_PIN0_PC3 (0*NUM_GROUP + PIN_BASE + 19)
+#define RK30_PIN0_PC4 (0*NUM_GROUP + PIN_BASE + 20)
+#define RK30_PIN0_PC5 (0*NUM_GROUP + PIN_BASE + 21)
+#define RK30_PIN0_PC6 (0*NUM_GROUP + PIN_BASE + 22)
+#define RK30_PIN0_PC7 (0*NUM_GROUP + PIN_BASE + 23)
+#define RK30_PIN0_PD0 (0*NUM_GROUP + PIN_BASE + 24)
+#define RK30_PIN0_PD1 (0*NUM_GROUP + PIN_BASE + 25)
+#define RK30_PIN0_PD2 (0*NUM_GROUP + PIN_BASE + 26)
+#define RK30_PIN0_PD3 (0*NUM_GROUP + PIN_BASE + 27)
+#define RK30_PIN0_PD4 (0*NUM_GROUP + PIN_BASE + 28)
+#define RK30_PIN0_PD5 (0*NUM_GROUP + PIN_BASE + 29)
+#define RK30_PIN0_PD6 (0*NUM_GROUP + PIN_BASE + 30)
+#define RK30_PIN0_PD7 (0*NUM_GROUP + PIN_BASE + 31)
+
+#define RK30_PIN1_PA0 (1*NUM_GROUP + PIN_BASE + 0)
+#define RK30_PIN1_PA1 (1*NUM_GROUP + PIN_BASE + 1)
+#define RK30_PIN1_PA2 (1*NUM_GROUP + PIN_BASE + 2)
+#define RK30_PIN1_PA3 (1*NUM_GROUP + PIN_BASE + 3)
+#define RK30_PIN1_PA4 (1*NUM_GROUP + PIN_BASE + 4)
+#define RK30_PIN1_PA5 (1*NUM_GROUP + PIN_BASE + 5)
+#define RK30_PIN1_PA6 (1*NUM_GROUP + PIN_BASE + 6)
+#define RK30_PIN1_PA7 (1*NUM_GROUP + PIN_BASE + 7)
+#define RK30_PIN1_PB0 (1*NUM_GROUP + PIN_BASE + 8)
+#define RK30_PIN1_PB1 (1*NUM_GROUP + PIN_BASE + 9)
+#define RK30_PIN1_PB2 (1*NUM_GROUP + PIN_BASE + 10)
+#define RK30_PIN1_PB3 (1*NUM_GROUP + PIN_BASE + 11)
+#define RK30_PIN1_PB4 (1*NUM_GROUP + PIN_BASE + 12)
+#define RK30_PIN1_PB5 (1*NUM_GROUP + PIN_BASE + 13)
+#define RK30_PIN1_PB6 (1*NUM_GROUP + PIN_BASE + 14)
+#define RK30_PIN1_PB7 (1*NUM_GROUP + PIN_BASE + 15)
+#define RK30_PIN1_PC0 (1*NUM_GROUP + PIN_BASE + 16)
+#define RK30_PIN1_PC1 (1*NUM_GROUP + PIN_BASE + 17)
+#define RK30_PIN1_PC2 (1*NUM_GROUP + PIN_BASE + 18)
+#define RK30_PIN1_PC3 (1*NUM_GROUP + PIN_BASE + 19)
+#define RK30_PIN1_PC4 (1*NUM_GROUP + PIN_BASE + 20)
+#define RK30_PIN1_PC5 (1*NUM_GROUP + PIN_BASE + 21)
+#define RK30_PIN1_PC6 (1*NUM_GROUP + PIN_BASE + 22)
+#define RK30_PIN1_PC7 (1*NUM_GROUP + PIN_BASE + 23)
+#define RK30_PIN1_PD0 (1*NUM_GROUP + PIN_BASE + 24)
+#define RK30_PIN1_PD1 (1*NUM_GROUP + PIN_BASE + 25)
+#define RK30_PIN1_PD2 (1*NUM_GROUP + PIN_BASE + 26)
+#define RK30_PIN1_PD3 (1*NUM_GROUP + PIN_BASE + 27)
+#define RK30_PIN1_PD4 (1*NUM_GROUP + PIN_BASE + 28)
+#define RK30_PIN1_PD5 (1*NUM_GROUP + PIN_BASE + 29)
+#define RK30_PIN1_PD6 (1*NUM_GROUP + PIN_BASE + 30)
+#define RK30_PIN1_PD7 (1*NUM_GROUP + PIN_BASE + 31)
+
+#define RK30_PIN2_PA0 (2*NUM_GROUP + PIN_BASE + 0)
+#define RK30_PIN2_PA1 (2*NUM_GROUP + PIN_BASE + 1)
+#define RK30_PIN2_PA2 (2*NUM_GROUP + PIN_BASE + 2)
+#define RK30_PIN2_PA3 (2*NUM_GROUP + PIN_BASE + 3)
+#define RK30_PIN2_PA4 (2*NUM_GROUP + PIN_BASE + 4)
+#define RK30_PIN2_PA5 (2*NUM_GROUP + PIN_BASE + 5)
+#define RK30_PIN2_PA6 (2*NUM_GROUP + PIN_BASE + 6)
+#define RK30_PIN2_PA7 (2*NUM_GROUP + PIN_BASE + 7)
+#define RK30_PIN2_PB0 (2*NUM_GROUP + PIN_BASE + 8)
+#define RK30_PIN2_PB1 (2*NUM_GROUP + PIN_BASE + 9)
+#define RK30_PIN2_PB2 (2*NUM_GROUP + PIN_BASE + 10)
+#define RK30_PIN2_PB3 (2*NUM_GROUP + PIN_BASE + 11)
+#define RK30_PIN2_PB4 (2*NUM_GROUP + PIN_BASE + 12)
+#define RK30_PIN2_PB5 (2*NUM_GROUP + PIN_BASE + 13)
+#define RK30_PIN2_PB6 (2*NUM_GROUP + PIN_BASE + 14)
+#define RK30_PIN2_PB7 (2*NUM_GROUP + PIN_BASE + 15)
+#define RK30_PIN2_PC0 (2*NUM_GROUP + PIN_BASE + 16)
+#define RK30_PIN2_PC1 (2*NUM_GROUP + PIN_BASE + 17)
+#define RK30_PIN2_PC2 (2*NUM_GROUP + PIN_BASE + 18)
+#define RK30_PIN2_PC3 (2*NUM_GROUP + PIN_BASE + 19)
+#define RK30_PIN2_PC4 (2*NUM_GROUP + PIN_BASE + 20)
+#define RK30_PIN2_PC5 (2*NUM_GROUP + PIN_BASE + 21)
+#define RK30_PIN2_PC6 (2*NUM_GROUP + PIN_BASE + 22)
+#define RK30_PIN2_PC7 (2*NUM_GROUP + PIN_BASE + 23)
+#define RK30_PIN2_PD0 (2*NUM_GROUP + PIN_BASE + 24)
+#define RK30_PIN2_PD1 (2*NUM_GROUP + PIN_BASE + 25)
+#define RK30_PIN2_PD2 (2*NUM_GROUP + PIN_BASE + 26)
+#define RK30_PIN2_PD3 (2*NUM_GROUP + PIN_BASE + 27)
+#define RK30_PIN2_PD4 (2*NUM_GROUP + PIN_BASE + 28)
+#define RK30_PIN2_PD5 (2*NUM_GROUP + PIN_BASE + 29)
+#define RK30_PIN2_PD6 (2*NUM_GROUP + PIN_BASE + 30)
+#define RK30_PIN2_PD7 (2*NUM_GROUP + PIN_BASE + 31)
+
+#define RK30_PIN3_PA0 (3*NUM_GROUP + PIN_BASE + 0)
+#define RK30_PIN3_PA1 (3*NUM_GROUP + PIN_BASE + 1)
+#define RK30_PIN3_PA2 (3*NUM_GROUP + PIN_BASE + 2)
+#define RK30_PIN3_PA3 (3*NUM_GROUP + PIN_BASE + 3)
+#define RK30_PIN3_PA4 (3*NUM_GROUP + PIN_BASE + 4)
+#define RK30_PIN3_PA5 (3*NUM_GROUP + PIN_BASE + 5)
+#define RK30_PIN3_PA6 (3*NUM_GROUP + PIN_BASE + 6)
+#define RK30_PIN3_PA7 (3*NUM_GROUP + PIN_BASE + 7)
+#define RK30_PIN3_PB0 (3*NUM_GROUP + PIN_BASE + 8)
+#define RK30_PIN3_PB1 (3*NUM_GROUP + PIN_BASE + 9)
+#define RK30_PIN3_PB2 (3*NUM_GROUP + PIN_BASE + 10)
+#define RK30_PIN3_PB3 (3*NUM_GROUP + PIN_BASE + 11)
+#define RK30_PIN3_PB4 (3*NUM_GROUP + PIN_BASE + 12)
+#define RK30_PIN3_PB5 (3*NUM_GROUP + PIN_BASE + 13)
+#define RK30_PIN3_PB6 (3*NUM_GROUP + PIN_BASE + 14)
+#define RK30_PIN3_PB7 (3*NUM_GROUP + PIN_BASE + 15)
+#define RK30_PIN3_PC0 (3*NUM_GROUP + PIN_BASE + 16)
+#define RK30_PIN3_PC1 (3*NUM_GROUP + PIN_BASE + 17)
+#define RK30_PIN3_PC2 (3*NUM_GROUP + PIN_BASE + 18)
+#define RK30_PIN3_PC3 (3*NUM_GROUP + PIN_BASE + 19)
+#define RK30_PIN3_PC4 (3*NUM_GROUP + PIN_BASE + 20)
+#define RK30_PIN3_PC5 (3*NUM_GROUP + PIN_BASE + 21)
+#define RK30_PIN3_PC6 (3*NUM_GROUP + PIN_BASE + 22)
+#define RK30_PIN3_PC7 (3*NUM_GROUP + PIN_BASE + 23)
+#define RK30_PIN3_PD0 (3*NUM_GROUP + PIN_BASE + 24)
+#define RK30_PIN3_PD1 (3*NUM_GROUP + PIN_BASE + 25)
+#define RK30_PIN3_PD2 (3*NUM_GROUP + PIN_BASE + 26)
+#define RK30_PIN3_PD3 (3*NUM_GROUP + PIN_BASE + 27)
+#define RK30_PIN3_PD4 (3*NUM_GROUP + PIN_BASE + 28)
+#define RK30_PIN3_PD5 (3*NUM_GROUP + PIN_BASE + 29)
+#define RK30_PIN3_PD6 (3*NUM_GROUP + PIN_BASE + 30)
+#define RK30_PIN3_PD7 (3*NUM_GROUP + PIN_BASE + 31)
+
+#define RK30_PIN4_PA0 (4*NUM_GROUP + PIN_BASE + 0)
+#define RK30_PIN4_PA1 (4*NUM_GROUP + PIN_BASE + 1)
+#define RK30_PIN4_PA2 (4*NUM_GROUP + PIN_BASE + 2)
+#define RK30_PIN4_PA3 (4*NUM_GROUP + PIN_BASE + 3)
+#define RK30_PIN4_PA4 (4*NUM_GROUP + PIN_BASE + 4)
+#define RK30_PIN4_PA5 (4*NUM_GROUP + PIN_BASE + 5)
+#define RK30_PIN4_PA6 (4*NUM_GROUP + PIN_BASE + 6)
+#define RK30_PIN4_PA7 (4*NUM_GROUP + PIN_BASE + 7)
+#define RK30_PIN4_PB0 (4*NUM_GROUP + PIN_BASE + 8)
+#define RK30_PIN4_PB1 (4*NUM_GROUP + PIN_BASE + 9)
+#define RK30_PIN4_PB2 (4*NUM_GROUP + PIN_BASE + 10)
+#define RK30_PIN4_PB3 (4*NUM_GROUP + PIN_BASE + 11)
+#define RK30_PIN4_PB4 (4*NUM_GROUP + PIN_BASE + 12)
+#define RK30_PIN4_PB5 (4*NUM_GROUP + PIN_BASE + 13)
+#define RK30_PIN4_PB6 (4*NUM_GROUP + PIN_BASE + 14)
+#define RK30_PIN4_PB7 (4*NUM_GROUP + PIN_BASE + 15)
+#define RK30_PIN4_PC0 (4*NUM_GROUP + PIN_BASE + 16)
+#define RK30_PIN4_PC1 (4*NUM_GROUP + PIN_BASE + 17)
+#define RK30_PIN4_PC2 (4*NUM_GROUP + PIN_BASE + 18)
+#define RK30_PIN4_PC3 (4*NUM_GROUP + PIN_BASE + 19)
+#define RK30_PIN4_PC4 (4*NUM_GROUP + PIN_BASE + 20)
+#define RK30_PIN4_PC5 (4*NUM_GROUP + PIN_BASE + 21)
+#define RK30_PIN4_PC6 (4*NUM_GROUP + PIN_BASE + 22)
+#define RK30_PIN4_PC7 (4*NUM_GROUP + PIN_BASE + 23)
+#define RK30_PIN4_PD0 (4*NUM_GROUP + PIN_BASE + 24)
+#define RK30_PIN4_PD1 (4*NUM_GROUP + PIN_BASE + 25)
+#define RK30_PIN4_PD2 (4*NUM_GROUP + PIN_BASE + 26)
+#define RK30_PIN4_PD3 (4*NUM_GROUP + PIN_BASE + 27)
+#define RK30_PIN4_PD4 (4*NUM_GROUP + PIN_BASE + 28)
+#define RK30_PIN4_PD5 (4*NUM_GROUP + PIN_BASE + 29)
+#define RK30_PIN4_PD6 (4*NUM_GROUP + PIN_BASE + 30)
+#define RK30_PIN4_PD7 (4*NUM_GROUP + PIN_BASE + 31)
+
+#define RK30_PIN6_PD7 (6*NUM_GROUP + PIN_BASE + 31)
+
+#if defined(CONFIG_SPI_FPGA_GPIO)
+#define FPGA_PIO0_00 (SPI_FPGA_EXPANDER_BASE + 0*NUM_GROUP + 0)
+#define FPGA_PIO0_01 (SPI_FPGA_EXPANDER_BASE + 0*NUM_GROUP + 1)
+#define FPGA_PIO0_02 (SPI_FPGA_EXPANDER_BASE + 0*NUM_GROUP + 2)
+#define FPGA_PIO0_03 (SPI_FPGA_EXPANDER_BASE + 0*NUM_GROUP + 3)
+#define FPGA_PIO0_04 (SPI_FPGA_EXPANDER_BASE + 0*NUM_GROUP + 4)
+#define FPGA_PIO0_05 (SPI_FPGA_EXPANDER_BASE + 0*NUM_GROUP + 5)
+#define FPGA_PIO0_06 (SPI_FPGA_EXPANDER_BASE + 0*NUM_GROUP + 6)
+#define FPGA_PIO0_07 (SPI_FPGA_EXPANDER_BASE + 0*NUM_GROUP + 7)
+
+#define FPGA_PIO0_08 (SPI_FPGA_EXPANDER_BASE + 1*NUM_GROUP + 0)
+#define FPGA_PIO0_09 (SPI_FPGA_EXPANDER_BASE + 1*NUM_GROUP + 1)
+#define FPGA_PIO0_10 (SPI_FPGA_EXPANDER_BASE + 1*NUM_GROUP + 2)
+#define FPGA_PIO0_11 (SPI_FPGA_EXPANDER_BASE + 1*NUM_GROUP + 3)
+#define FPGA_PIO0_12 (SPI_FPGA_EXPANDER_BASE + 1*NUM_GROUP + 4)
+#define FPGA_PIO0_13 (SPI_FPGA_EXPANDER_BASE + 1*NUM_GROUP + 5)
+#define FPGA_PIO0_14 (SPI_FPGA_EXPANDER_BASE + 1*NUM_GROUP + 6)
+#define FPGA_PIO0_15 (SPI_FPGA_EXPANDER_BASE + 1*NUM_GROUP + 7)
+
+#define FPGA_PIO1_00 (SPI_FPGA_EXPANDER_BASE + 2*NUM_GROUP + 0)
+#define FPGA_PIO1_01 (SPI_FPGA_EXPANDER_BASE + 2*NUM_GROUP + 1)
+#define FPGA_PIO1_02 (SPI_FPGA_EXPANDER_BASE + 2*NUM_GROUP + 2)
+#define FPGA_PIO1_03 (SPI_FPGA_EXPANDER_BASE + 2*NUM_GROUP + 3)
+#define FPGA_PIO1_04 (SPI_FPGA_EXPANDER_BASE + 2*NUM_GROUP + 4)
+#define FPGA_PIO1_05 (SPI_FPGA_EXPANDER_BASE + 2*NUM_GROUP + 5)
+#define FPGA_PIO1_06 (SPI_FPGA_EXPANDER_BASE + 2*NUM_GROUP + 6)
+#define FPGA_PIO1_07 (SPI_FPGA_EXPANDER_BASE + 2*NUM_GROUP + 7)
+
+#define FPGA_PIO1_08 (SPI_FPGA_EXPANDER_BASE + 3*NUM_GROUP + 0)
+#define FPGA_PIO1_09 (SPI_FPGA_EXPANDER_BASE + 3*NUM_GROUP + 1)
+#define FPGA_PIO1_10 (SPI_FPGA_EXPANDER_BASE + 3*NUM_GROUP + 2)
+#define FPGA_PIO1_11 (SPI_FPGA_EXPANDER_BASE + 3*NUM_GROUP + 3)
+#define FPGA_PIO1_12 (SPI_FPGA_EXPANDER_BASE + 3*NUM_GROUP + 4)
+#define FPGA_PIO1_13 (SPI_FPGA_EXPANDER_BASE + 3*NUM_GROUP + 5)
+#define FPGA_PIO1_14 (SPI_FPGA_EXPANDER_BASE + 3*NUM_GROUP + 6)
+#define FPGA_PIO1_15 (SPI_FPGA_EXPANDER_BASE + 3*NUM_GROUP + 7)
+
+#define FPGA_PIO2_00 (SPI_FPGA_EXPANDER_BASE + 4*NUM_GROUP + 0)
+#define FPGA_PIO2_01 (SPI_FPGA_EXPANDER_BASE + 4*NUM_GROUP + 1)
+#define FPGA_PIO2_02 (SPI_FPGA_EXPANDER_BASE + 4*NUM_GROUP + 2)
+#define FPGA_PIO2_03 (SPI_FPGA_EXPANDER_BASE + 4*NUM_GROUP + 3)
+#define FPGA_PIO2_04 (SPI_FPGA_EXPANDER_BASE + 4*NUM_GROUP + 4)
+#define FPGA_PIO2_05 (SPI_FPGA_EXPANDER_BASE + 4*NUM_GROUP + 5)
+#define FPGA_PIO2_06 (SPI_FPGA_EXPANDER_BASE + 4*NUM_GROUP + 6)
+#define FPGA_PIO2_07 (SPI_FPGA_EXPANDER_BASE + 4*NUM_GROUP + 7)
+
+#define FPGA_PIO2_08 (SPI_FPGA_EXPANDER_BASE + 5*NUM_GROUP + 0)
+#define FPGA_PIO2_09 (SPI_FPGA_EXPANDER_BASE + 5*NUM_GROUP + 1)
+#define FPGA_PIO2_10 (SPI_FPGA_EXPANDER_BASE + 5*NUM_GROUP + 2)
+#define FPGA_PIO2_11 (SPI_FPGA_EXPANDER_BASE + 5*NUM_GROUP + 3)
+#define FPGA_PIO2_12 (SPI_FPGA_EXPANDER_BASE + 5*NUM_GROUP + 4)
+#define FPGA_PIO2_13 (SPI_FPGA_EXPANDER_BASE + 5*NUM_GROUP + 5)
+#define FPGA_PIO2_14 (SPI_FPGA_EXPANDER_BASE + 5*NUM_GROUP + 6)
+#define FPGA_PIO2_15 (SPI_FPGA_EXPANDER_BASE + 5*NUM_GROUP + 7)
+
+#define FPGA_PIO3_00 (SPI_FPGA_EXPANDER_BASE + 6*NUM_GROUP + 0)
+#define FPGA_PIO3_01 (SPI_FPGA_EXPANDER_BASE + 6*NUM_GROUP + 1)
+#define FPGA_PIO3_02 (SPI_FPGA_EXPANDER_BASE + 6*NUM_GROUP + 2)
+#define FPGA_PIO3_03 (SPI_FPGA_EXPANDER_BASE + 6*NUM_GROUP + 3)
+#define FPGA_PIO3_04 (SPI_FPGA_EXPANDER_BASE + 6*NUM_GROUP + 4)
+#define FPGA_PIO3_05 (SPI_FPGA_EXPANDER_BASE + 6*NUM_GROUP + 5)
+#define FPGA_PIO3_06 (SPI_FPGA_EXPANDER_BASE + 6*NUM_GROUP + 6)
+#define FPGA_PIO3_07 (SPI_FPGA_EXPANDER_BASE + 6*NUM_GROUP + 7)
+
+#define FPGA_PIO3_08 (SPI_FPGA_EXPANDER_BASE + 7*NUM_GROUP + 0)
+#define FPGA_PIO3_09 (SPI_FPGA_EXPANDER_BASE + 7*NUM_GROUP + 1)
+#define FPGA_PIO3_10 (SPI_FPGA_EXPANDER_BASE + 7*NUM_GROUP + 2)
+#define FPGA_PIO3_11 (SPI_FPGA_EXPANDER_BASE + 7*NUM_GROUP + 3)
+#define FPGA_PIO3_12 (SPI_FPGA_EXPANDER_BASE + 7*NUM_GROUP + 4)
+#define FPGA_PIO3_13 (SPI_FPGA_EXPANDER_BASE + 7*NUM_GROUP + 5)
+#define FPGA_PIO3_14 (SPI_FPGA_EXPANDER_BASE + 7*NUM_GROUP + 6)
+#define FPGA_PIO3_15 (SPI_FPGA_EXPANDER_BASE + 7*NUM_GROUP + 7)
+
+#define FPGA_PIO4_00 (SPI_FPGA_EXPANDER_BASE + 8*NUM_GROUP + 0)
+#define FPGA_PIO4_01 (SPI_FPGA_EXPANDER_BASE + 8*NUM_GROUP + 1)
+#define FPGA_PIO4_02 (SPI_FPGA_EXPANDER_BASE + 8*NUM_GROUP + 2)
+#define FPGA_PIO4_03 (SPI_FPGA_EXPANDER_BASE + 8*NUM_GROUP + 3)
+#define FPGA_PIO4_04 (SPI_FPGA_EXPANDER_BASE + 8*NUM_GROUP + 4)
+#define FPGA_PIO4_05 (SPI_FPGA_EXPANDER_BASE + 8*NUM_GROUP + 5)
+#define FPGA_PIO4_06 (SPI_FPGA_EXPANDER_BASE + 8*NUM_GROUP + 6)
+#define FPGA_PIO4_07 (SPI_FPGA_EXPANDER_BASE + 8*NUM_GROUP + 7)
+
+#define FPGA_PIO4_08 (SPI_FPGA_EXPANDER_BASE + 9*NUM_GROUP + 0)
+#define FPGA_PIO4_09 (SPI_FPGA_EXPANDER_BASE + 9*NUM_GROUP + 1)
+#define FPGA_PIO4_10 (SPI_FPGA_EXPANDER_BASE + 9*NUM_GROUP + 2)
+#define FPGA_PIO4_11 (SPI_FPGA_EXPANDER_BASE + 9*NUM_GROUP + 3)
+#define FPGA_PIO4_12 (SPI_FPGA_EXPANDER_BASE + 9*NUM_GROUP + 4)
+#define FPGA_PIO4_13 (SPI_FPGA_EXPANDER_BASE + 9*NUM_GROUP + 5)
+#define FPGA_PIO4_14 (SPI_FPGA_EXPANDER_BASE + 9*NUM_GROUP + 6)
+#define FPGA_PIO4_15 (SPI_FPGA_EXPANDER_BASE + 9*NUM_GROUP + 7)
+
+#define FPGA_PIO5_00 (SPI_FPGA_EXPANDER_BASE + 10*NUM_GROUP + 0)
+#define FPGA_PIO5_01 (SPI_FPGA_EXPANDER_BASE + 10*NUM_GROUP + 1)
+#define FPGA_PIO5_02 (SPI_FPGA_EXPANDER_BASE + 10*NUM_GROUP + 2)
+#define FPGA_PIO5_03 (SPI_FPGA_EXPANDER_BASE + 10*NUM_GROUP + 3)
+#define FPGA_PIO5_04 (SPI_FPGA_EXPANDER_BASE + 10*NUM_GROUP + 4)
+#define FPGA_PIO5_05 (SPI_FPGA_EXPANDER_BASE + 10*NUM_GROUP + 5)
+#define FPGA_PIO5_06 (SPI_FPGA_EXPANDER_BASE + 10*NUM_GROUP + 6)
+#define FPGA_PIO5_07 (SPI_FPGA_EXPANDER_BASE + 10*NUM_GROUP + 7)
+
+#define FPGA_PIO5_08 (SPI_FPGA_EXPANDER_BASE + 11*NUM_GROUP + 0)
+#define FPGA_PIO5_09 (SPI_FPGA_EXPANDER_BASE + 11*NUM_GROUP + 1)
+#define FPGA_PIO5_10 (SPI_FPGA_EXPANDER_BASE + 11*NUM_GROUP + 2)
+#define FPGA_PIO5_11 (SPI_FPGA_EXPANDER_BASE + 11*NUM_GROUP + 3)
+#define FPGA_PIO5_12 (SPI_FPGA_EXPANDER_BASE + 11*NUM_GROUP + 4)
+#define FPGA_PIO5_13 (SPI_FPGA_EXPANDER_BASE + 11*NUM_GROUP + 5)
+#define FPGA_PIO5_14 (SPI_FPGA_EXPANDER_BASE + 11*NUM_GROUP + 6)
+#define FPGA_PIO5_15 (SPI_FPGA_EXPANDER_BASE + 11*NUM_GROUP + 7)
+
+#endif
+
+#if defined(CONFIG_IOEXTEND_TCA6424)
+#define TCA6424_P00 (TCA6424_GPIO_EXPANDER_BASE + 0*NUM_GROUP + 0)
+#define TCA6424_P01 (TCA6424_GPIO_EXPANDER_BASE + 0*NUM_GROUP + 1)
+#define TCA6424_P02 (TCA6424_GPIO_EXPANDER_BASE + 0*NUM_GROUP + 2)
+#define TCA6424_P03 (TCA6424_GPIO_EXPANDER_BASE + 0*NUM_GROUP + 3)
+#define TCA6424_P04 (TCA6424_GPIO_EXPANDER_BASE + 0*NUM_GROUP + 4)
+#define TCA6424_P05 (TCA6424_GPIO_EXPANDER_BASE + 0*NUM_GROUP + 5)
+#define TCA6424_P06 (TCA6424_GPIO_EXPANDER_BASE + 0*NUM_GROUP + 6)
+#define TCA6424_P07 (TCA6424_GPIO_EXPANDER_BASE + 0*NUM_GROUP + 7)
+
+#define TCA6424_P10 (TCA6424_GPIO_EXPANDER_BASE + 1*NUM_GROUP + 0)
+#define TCA6424_P11 (TCA6424_GPIO_EXPANDER_BASE + 1*NUM_GROUP + 1)
+#define TCA6424_P12 (TCA6424_GPIO_EXPANDER_BASE + 1*NUM_GROUP + 2)
+#define TCA6424_P13 (TCA6424_GPIO_EXPANDER_BASE + 1*NUM_GROUP + 3)
+#define TCA6424_P14 (TCA6424_GPIO_EXPANDER_BASE + 1*NUM_GROUP + 4)
+#define TCA6424_P15 (TCA6424_GPIO_EXPANDER_BASE + 1*NUM_GROUP + 5)
+#define TCA6424_P16 (TCA6424_GPIO_EXPANDER_BASE + 1*NUM_GROUP + 6)
+#define TCA6424_P17 (TCA6424_GPIO_EXPANDER_BASE + 1*NUM_GROUP + 7)
+
+#define TCA6424_P20 (TCA6424_GPIO_EXPANDER_BASE + 2*NUM_GROUP + 0)
+#define TCA6424_P21 (TCA6424_GPIO_EXPANDER_BASE + 2*NUM_GROUP + 1)
+#define TCA6424_P22 (TCA6424_GPIO_EXPANDER_BASE + 2*NUM_GROUP + 2)
+#define TCA6424_P23 (TCA6424_GPIO_EXPANDER_BASE + 2*NUM_GROUP + 3)
+#define TCA6424_P24 (TCA6424_GPIO_EXPANDER_BASE + 2*NUM_GROUP + 4)
+#define TCA6424_P25 (TCA6424_GPIO_EXPANDER_BASE + 2*NUM_GROUP + 5)
+#define TCA6424_P26 (TCA6424_GPIO_EXPANDER_BASE + 2*NUM_GROUP + 6)
+#define TCA6424_P27 (TCA6424_GPIO_EXPANDER_BASE + 2*NUM_GROUP + 7)
+#endif
+
+#if defined(CONFIG_GPIO_WM831X)
+#define WM831X_P01 (WM831X_GPIO_EXPANDER_BASE + 0*NUM_GROUP + 0)
+#define WM831X_P02 (WM831X_GPIO_EXPANDER_BASE + 0*NUM_GROUP + 1)
+#define WM831X_P03 (WM831X_GPIO_EXPANDER_BASE + 0*NUM_GROUP + 2)
+#define WM831X_P04 (WM831X_GPIO_EXPANDER_BASE + 0*NUM_GROUP + 3)
+#define WM831X_P05 (WM831X_GPIO_EXPANDER_BASE + 0*NUM_GROUP + 4)
+#define WM831X_P06 (WM831X_GPIO_EXPANDER_BASE + 0*NUM_GROUP + 5)
+#define WM831X_P07 (WM831X_GPIO_EXPANDER_BASE + 0*NUM_GROUP + 6)
+#define WM831X_P08 (WM831X_GPIO_EXPANDER_BASE + 0*NUM_GROUP + 7)
+
+#define WM831X_P09 (WM831X_GPIO_EXPANDER_BASE + 1*NUM_GROUP + 0)
+#define WM831X_P10 (WM831X_GPIO_EXPANDER_BASE + 1*NUM_GROUP + 1)
+#define WM831X_P11 (WM831X_GPIO_EXPANDER_BASE + 1*NUM_GROUP + 2)
+#define WM831X_P12 (WM831X_GPIO_EXPANDER_BASE + 1*NUM_GROUP + 3)
+#endif
+
+extern void __init rk30_gpio_init(void);
+/*-------------------------------------------------------------------------*/
-#define ARCH_NR_GPIOS NR_GPIO_IRQS
-#define PIN_BASE NR_GIC_IRQS
+/* wrappers for "new style" GPIO calls. the old RK2818-specfic ones should
+ * eventually be removed (along with this errno.h inclusion), and the
+ * gpio request/free calls should probably be implemented.
+ */
#include <asm/errno.h>
#include <asm-generic/gpio.h> /* cansleep wrappers */
--- /dev/null
+/* arch/arm/mach-rk29/gpio.c
+ *
+ * Copyright (C) 2010 ROCKCHIP, Inc.
+ *
+ * This software is licensed under the terms of the GNU General Public
+ * License version 2, as published by the Free Software Foundation, and
+ * may be copied, distributed, and modified under those terms.
+ *
+ * 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.
+ *
+ */
+
+#include <linux/clk.h>
+#include <linux/errno.h>
+#include <linux/interrupt.h>
+#include <linux/irq.h>
+#include <linux/debugfs.h>
+#include <linux/seq_file.h>
+#include <linux/kernel.h>
+#include <linux/list.h>
+#include <linux/module.h>
+#include <linux/io.h>
+#include <linux/syscore_ops.h>
+
+#include <mach/hardware.h>
+#include <mach/gpio.h>
+#include <mach/io.h>
+#include <mach/iomux.h>
+#include <asm/gpio.h>
+#include <asm/mach/irq.h>
+
+#define MAX_PIN RK30_PIN6_PD7
+
+#define to_rk30_gpio_bank(c) container_of(c, struct rk30_gpio_bank, chip)
+
+struct rk30_gpio_bank {
+ struct gpio_chip chip;
+ unsigned short id;
+ short irq;
+ void __iomem *regbase; /* Base of register bank */
+ struct clk *clk;
+ u32 suspend_wakeup;
+ u32 saved_wakeup;
+ spinlock_t lock;
+};
+
+static struct lock_class_key gpio_lock_class;
+
+static void rk30_gpiolib_dbg_show(struct seq_file *s, struct gpio_chip *chip);
+static void rk30_gpiolib_set(struct gpio_chip *chip, unsigned offset, int val);
+static int rk30_gpiolib_get(struct gpio_chip *chip, unsigned offset);
+static int rk30_gpiolib_direction_output(struct gpio_chip *chip,unsigned offset, int val);
+static int rk30_gpiolib_direction_input(struct gpio_chip *chip,unsigned offset);
+static int rk30_gpiolib_pull_updown(struct gpio_chip *chip, unsigned offset, unsigned enable);
+static int rk30_gpiolib_to_irq(struct gpio_chip *chip,unsigned offset);
+
+#define RK30_GPIO_BANK(ID) \
+ { \
+ .chip = { \
+ .label = "gpio" #ID, \
+ .direction_input = rk30_gpiolib_direction_input, \
+ .direction_output = rk30_gpiolib_direction_output, \
+ .get = rk30_gpiolib_get, \
+ .set = rk30_gpiolib_set, \
+ .pull_updown = rk30_gpiolib_pull_updown, \
+ .dbg_show = rk30_gpiolib_dbg_show, \
+ .to_irq = rk30_gpiolib_to_irq, \
+ .base = PIN_BASE + ID*NUM_GROUP, \
+ .ngpio = NUM_GROUP, \
+ }, \
+ .id = ID, \
+ .irq = IRQ_GPIO##ID, \
+ .regbase = (unsigned char __iomem *) RK30_GPIO##ID##_BASE, \
+ }
+
+static struct rk30_gpio_bank rk30_gpio_banks[] = {
+ RK30_GPIO_BANK(0),
+ RK30_GPIO_BANK(1),
+ RK30_GPIO_BANK(2),
+ RK30_GPIO_BANK(3),
+ RK30_GPIO_BANK(4),
+ RK30_GPIO_BANK(6),
+};
+
+static inline void rk30_gpio_bit_op(void __iomem *regbase, unsigned int offset, u32 bit, unsigned char flag)
+{
+ u32 val = __raw_readl(regbase + offset);
+ if (flag)
+ val |= bit;
+ else
+ val &= ~bit;
+ __raw_writel(val, regbase + offset);
+}
+
+static inline struct gpio_chip *pin_to_gpio_chip(unsigned pin)
+{
+ if (pin < PIN_BASE || pin > MAX_PIN)
+ return NULL;
+
+ pin -= PIN_BASE;
+ pin /= NUM_GROUP;
+ if (likely(pin < ARRAY_SIZE(rk30_gpio_banks)))
+ return &(rk30_gpio_banks[pin].chip);
+ return NULL;
+}
+
+static inline unsigned gpio_to_bit(unsigned gpio)
+{
+ gpio -= PIN_BASE;
+ return 1u << (gpio % NUM_GROUP);
+}
+
+static inline unsigned offset_to_bit(unsigned offset)
+{
+ return 1u << offset;
+}
+
+static void GPIOSetPinLevel(void __iomem *regbase, unsigned int bit, eGPIOPinLevel_t level)
+{
+ rk30_gpio_bit_op(regbase, GPIO_SWPORT_DDR, bit, 1);
+ rk30_gpio_bit_op(regbase, GPIO_SWPORT_DR, bit, level);
+}
+
+static int GPIOGetPinLevel(void __iomem *regbase, unsigned int bit)
+{
+ return ((__raw_readl(regbase + GPIO_EXT_PORT) & bit) != 0);
+}
+
+static void GPIOSetPinDirection(void __iomem *regbase, unsigned int bit, eGPIOPinDirection_t direction)
+{
+ rk30_gpio_bit_op(regbase, GPIO_SWPORT_DDR, bit, direction);
+ /* Enable debounce may halt cpu on wfi, disable it by default */
+ //rk30_gpio_bit_op(regbase, GPIO_DEBOUNCE, bit, 1);
+}
+
+static void GPIOEnableIntr(void __iomem *regbase, unsigned int bit)
+{
+ rk30_gpio_bit_op(regbase, GPIO_INTEN, bit, 1);
+}
+
+static void GPIODisableIntr(void __iomem *regbase, unsigned int bit)
+{
+ rk30_gpio_bit_op(regbase, GPIO_INTEN, bit, 0);
+}
+
+static void GPIOAckIntr(void __iomem *regbase, unsigned int bit)
+{
+ rk30_gpio_bit_op(regbase, GPIO_PORTS_EOI, bit, 1);
+}
+
+static void GPIOSetIntrType(void __iomem *regbase, unsigned int bit, eGPIOIntType_t type)
+{
+ switch (type) {
+ case GPIOLevelLow:
+ rk30_gpio_bit_op(regbase, GPIO_INT_POLARITY, bit, 0);
+ rk30_gpio_bit_op(regbase, GPIO_INTTYPE_LEVEL, bit, 0);
+ break;
+ case GPIOLevelHigh:
+ rk30_gpio_bit_op(regbase, GPIO_INTTYPE_LEVEL, bit, 0);
+ rk30_gpio_bit_op(regbase, GPIO_INT_POLARITY, bit, 1);
+ break;
+ case GPIOEdgelFalling:
+ rk30_gpio_bit_op(regbase, GPIO_INTTYPE_LEVEL, bit, 1);
+ rk30_gpio_bit_op(regbase, GPIO_INT_POLARITY, bit, 0);
+ break;
+ case GPIOEdgelRising:
+ rk30_gpio_bit_op(regbase, GPIO_INTTYPE_LEVEL, bit, 1);
+ rk30_gpio_bit_op(regbase, GPIO_INT_POLARITY, bit, 1);
+ break;
+ }
+}
+
+static int rk30_gpio_irq_set_type(struct irq_data *d, unsigned int type)
+{
+ struct rk30_gpio_bank *bank = irq_data_get_irq_chip_data(d);
+ u32 bit = gpio_to_bit(irq_to_gpio(d->irq));
+ eGPIOIntType_t int_type;
+ unsigned long flags;
+
+ switch (type) {
+ case IRQ_TYPE_EDGE_RISING:
+ int_type = GPIOEdgelRising;
+ break;
+ case IRQ_TYPE_EDGE_FALLING:
+ int_type = GPIOEdgelFalling;
+ break;
+ case IRQ_TYPE_LEVEL_HIGH:
+ int_type = GPIOLevelHigh;
+ break;
+ case IRQ_TYPE_LEVEL_LOW:
+ int_type = GPIOLevelLow;
+ break;
+ default:
+ return -EINVAL;
+ }
+
+ spin_lock_irqsave(&bank->lock, flags);
+ //ÉèÖÃΪÖжÏ֮ǰ£¬±ØÐëÏÈÉèÖÃΪÊäÈë״̬
+ GPIOSetPinDirection(bank->regbase, bit, GPIO_IN);
+ GPIOSetIntrType(bank->regbase, bit, int_type);
+ spin_unlock_irqrestore(&bank->lock, flags);
+
+ if (type & (IRQ_TYPE_LEVEL_LOW | IRQ_TYPE_LEVEL_HIGH))
+ __irq_set_handler_locked(d->irq, handle_level_irq);
+ else if (type & (IRQ_TYPE_EDGE_FALLING | IRQ_TYPE_EDGE_RISING))
+ __irq_set_handler_locked(d->irq, handle_edge_irq);
+
+ return 0;
+}
+
+static int rk30_gpio_irq_set_wake(struct irq_data *d, unsigned int on)
+{
+ struct rk30_gpio_bank *bank = irq_data_get_irq_chip_data(d);
+ u32 bit = gpio_to_bit(irq_to_gpio(d->irq));
+ unsigned long flags;
+
+ spin_lock_irqsave(&bank->lock, flags);
+ if (on)
+ bank->suspend_wakeup |= bit;
+ else
+ bank->suspend_wakeup &= ~bit;
+ spin_unlock_irqrestore(&bank->lock, flags);
+
+ return 0;
+}
+
+static void rk30_gpio_irq_unmask(struct irq_data *d)
+{
+ struct rk30_gpio_bank *bank = irq_data_get_irq_chip_data(d);
+ u32 bit = gpio_to_bit(irq_to_gpio(d->irq));
+ unsigned long flags;
+
+ spin_lock_irqsave(&bank->lock, flags);
+ GPIOEnableIntr(bank->regbase, bit);
+ spin_unlock_irqrestore(&bank->lock, flags);
+}
+
+static void rk30_gpio_irq_mask(struct irq_data *d)
+{
+ struct rk30_gpio_bank *bank = irq_data_get_irq_chip_data(d);
+ u32 bit = gpio_to_bit(irq_to_gpio(d->irq));
+ unsigned long flags;
+
+ spin_lock_irqsave(&bank->lock, flags);
+ GPIODisableIntr(bank->regbase, bit);
+ spin_unlock_irqrestore(&bank->lock, flags);
+}
+
+static void rk30_gpio_irq_ack(struct irq_data *d)
+{
+ struct rk30_gpio_bank *bank = irq_data_get_irq_chip_data(d);
+ u32 bit = gpio_to_bit(irq_to_gpio(d->irq));
+
+ GPIOAckIntr(bank->regbase, bit);
+}
+
+static int rk30_gpiolib_direction_output(struct gpio_chip *chip, unsigned offset, int val)
+{
+ struct rk30_gpio_bank *bank = to_rk30_gpio_bank(chip);
+ u32 bit = offset_to_bit(offset);
+ unsigned long flags;
+
+ spin_lock_irqsave(&bank->lock, flags);
+ GPIOSetPinDirection(bank->regbase, bit, GPIO_OUT);
+ GPIOSetPinLevel(bank->regbase, bit, val);
+ spin_unlock_irqrestore(&bank->lock, flags);
+ return 0;
+}
+
+static int rk30_gpiolib_direction_input(struct gpio_chip *chip,unsigned offset)
+{
+ struct rk30_gpio_bank *bank = to_rk30_gpio_bank(chip);
+ unsigned long flags;
+
+ spin_lock_irqsave(&bank->lock, flags);
+ GPIOSetPinDirection(bank->regbase, offset_to_bit(offset), GPIO_IN);
+ spin_unlock_irqrestore(&bank->lock, flags);
+ return 0;
+}
+
+
+static int rk30_gpiolib_get(struct gpio_chip *chip, unsigned offset)
+{
+ return GPIOGetPinLevel(to_rk30_gpio_bank(chip)->regbase, offset_to_bit(offset));
+}
+
+static void rk30_gpiolib_set(struct gpio_chip *chip, unsigned offset, int val)
+{
+ struct rk30_gpio_bank *bank = to_rk30_gpio_bank(chip);
+ unsigned long flags;
+
+ spin_lock_irqsave(&bank->lock, flags);
+ GPIOSetPinLevel(bank->regbase, offset_to_bit(offset), val);
+ spin_unlock_irqrestore(&bank->lock, flags);
+}
+
+static int rk30_gpiolib_pull_updown(struct gpio_chip *chip, unsigned offset, unsigned enable)
+{
+ struct rk30_gpio_bank *bank = to_rk30_gpio_bank(chip);
+ unsigned long flags;
+
+ spin_lock_irqsave(&bank->lock, flags);
+ rk30_gpio_bit_op((void *__iomem) RK30_GRF_BASE, 0x78 + bank->id * 4, offset_to_bit(offset), !enable);
+ spin_unlock_irqrestore(&bank->lock, flags);
+
+ return 0;
+}
+
+static int rk30_gpiolib_to_irq(struct gpio_chip *chip, unsigned offset)
+{
+ return chip->base + offset;
+}
+
+static void rk30_gpiolib_dbg_show(struct seq_file *s, struct gpio_chip *chip)
+{
+#if 0
+ int i;
+
+ for (i = 0; i < chip->ngpio; i++) {
+ unsigned pin = chip->base + i;
+ struct gpio_chip *chip = pin_to_gpioChip(pin);
+ u32 bit = pin_to_bit(pin);
+ const char *gpio_label;
+
+ if(!chip ||!bit)
+ return;
+
+ gpio_label = gpiochip_is_requested(chip, i);
+ if (gpio_label) {
+ seq_printf(s, "[%s] GPIO%s%d: ",
+ gpio_label, chip->label, i);
+
+ if (!chip || !bit)
+ {
+ seq_printf(s, "!chip || !bit\t");
+ return;
+ }
+
+ GPIOSetPinDirection(chip,bit,GPIO_IN);
+ seq_printf(s, "pin=%d,level=%d\t", pin,GPIOGetPinLevel(chip,bit));
+ seq_printf(s, "\t");
+ }
+ }
+#endif
+}
+
+static void rk30_gpio_irq_handler(unsigned int irq, struct irq_desc *desc)
+{
+ struct rk30_gpio_bank *bank = irq_get_handler_data(irq);
+ struct irq_chip *chip = irq_desc_get_chip(desc);
+ unsigned gpio_irq;
+ u32 isr, ilr;
+ unsigned pin;
+ unsigned unmasked = 0;
+
+ chained_irq_enter(chip, desc);
+
+ isr = __raw_readl(bank->regbase + GPIO_INT_STATUS);
+ ilr = __raw_readl(bank->regbase + GPIO_INTTYPE_LEVEL);
+
+ gpio_irq = gpio_to_irq(bank->chip.base);
+
+ while (isr) {
+ pin = fls(isr) - 1;
+ /* if gpio is edge triggered, clear condition
+ * before executing the hander so that we don't
+ * miss edges
+ */
+ if (ilr & (1 << pin)) {
+ unmasked = 1;
+ chained_irq_exit(chip, desc);
+ }
+
+ generic_handle_irq(gpio_irq + pin);
+ isr &= ~(1 << pin);
+ }
+
+ if (!unmasked)
+ chained_irq_exit(chip, desc);
+}
+
+static struct irq_chip rk30_gpio_irq_chip = {
+ .name = "GPIO",
+ .irq_ack = rk30_gpio_irq_ack,
+ .irq_disable = rk30_gpio_irq_mask,
+ .irq_mask = rk30_gpio_irq_mask,
+ .irq_unmask = rk30_gpio_irq_unmask,
+ .irq_set_type = rk30_gpio_irq_set_type,
+ .irq_set_wake = rk30_gpio_irq_set_wake,
+};
+
+void __init rk30_gpio_init(void)
+{
+ unsigned int i, j, pin;
+ struct rk30_gpio_bank *bank;
+
+ bank = rk30_gpio_banks;
+ pin = PIN_BASE;
+
+ for (i = 0; i < ARRAY_SIZE(rk30_gpio_banks); i++, bank++, pin += 32) {
+ spin_lock_init(&bank->lock);
+ bank->clk = clk_get(NULL, bank->chip.label);
+ clk_enable(bank->clk);
+ gpiochip_add(&bank->chip);
+
+ __raw_writel(0, bank->regbase + GPIO_INTEN);
+ for (j = 0; j < 32; j++) {
+ unsigned int irq = gpio_to_irq(pin + j);
+ irq_set_lockdep_class(irq, &gpio_lock_class);
+ irq_set_chip_data(irq, bank);
+ irq_set_chip_and_handler(irq, &rk30_gpio_irq_chip, handle_level_irq);
+ set_irq_flags(irq, IRQF_VALID);
+ }
+
+ irq_set_handler_data(bank->irq, bank);
+ irq_set_chained_handler(bank->irq, rk30_gpio_irq_handler);
+ }
+ printk("%s: %d gpio irqs in %d banks\n", __func__, pin - PIN_BASE, ARRAY_SIZE(rk30_gpio_banks));
+}
+
+#ifdef CONFIG_PM
+__weak void rk30_setgpio_suspend_board(void)
+{
+}
+
+__weak void rk30_setgpio_resume_board(void)
+{
+}
+
+static int rk30_gpio_suspend(void)
+{
+ unsigned i;
+
+ rk30_setgpio_suspend_board();
+
+ for (i = 0; i < ARRAY_SIZE(rk30_gpio_banks); i++) {
+ struct rk30_gpio_bank *bank = &rk30_gpio_banks[i];
+
+ bank->saved_wakeup = __raw_readl(bank->regbase + GPIO_INTEN);
+ __raw_writel(bank->suspend_wakeup, bank->regbase + GPIO_INTEN);
+
+ if (!bank->suspend_wakeup)
+ clk_disable(bank->clk);
+ }
+
+ return 0;
+}
+
+static void rk30_gpio_resume(void)
+{
+ unsigned i;
+
+ for (i = 0; i < ARRAY_SIZE(rk30_gpio_banks); i++) {
+ struct rk30_gpio_bank *bank = &rk30_gpio_banks[i];
+ u32 isr;
+
+ if (!bank->suspend_wakeup)
+ clk_enable(bank->clk);
+
+ /* keep enable for resume irq */
+ isr = __raw_readl(bank->regbase + GPIO_INT_STATUS);
+ __raw_writel(bank->saved_wakeup | (bank->suspend_wakeup & isr), bank->regbase + GPIO_INTEN);
+ }
+
+ rk30_setgpio_resume_board();
+}
+
+static struct syscore_ops rk30_gpio_syscore_ops = {
+ .suspend = rk30_gpio_suspend,
+ .resume = rk30_gpio_resume,
+};
+
+static int __init rk30_gpio_sysinit(void)
+{
+ register_syscore_ops(&rk30_gpio_syscore_ops);
+ return 0;
+}
+
+arch_initcall(rk30_gpio_sysinit);
+#endif