void pm_do_poweroff(void) { unsigned long start, flags; PWER &= ~0x8000ffff; local_irq_save(flags); printk("Poweroff, Begin to wait BP_RDY signal.\n"); pm_send_all(PM_SUSPEND, (void *)3); start = OSCR; *(unsigned long *)(phys_to_virt(BPSIG_ADDR)) = NO_FLAG; do { if( !(GPLR(GPIO_BP_RDY) & GPIO_bit(GPIO_BP_RDY))){ printk(KERN_DEBUG"got BP_RDY signal.\n"); GPDR(GPIO_WDI_AP) |= GPIO_bit(GPIO_WDI_AP); GPCR(GPIO_WDI_AP) = GPIO_bit(GPIO_WDI_AP); while(1); } if ((OSCR - start) >= POWER_OFF_TIMEOUT) { printk(KERN_DEBUG "timeout when power down\n"); mdelay(1); GPDR(GPIO_WDI_AP) |= GPIO_bit(GPIO_WDI_AP); GPCR(GPIO_WDI_AP) = GPIO_bit(GPIO_WDI_AP); while(1); } } while(1); pm_do_useroff(); printk(KERN_DEBUG "resume from useroff\n"); pm_send_all(PM_SUSPEND, (void *)0); local_irq_restore(flags); }
int pxa_gpio_mode(int gpio_mode) { unsigned long flags; int gpio = gpio_mode & GPIO_MD_MASK_NR; int fn = (gpio_mode & GPIO_MD_MASK_FN) >> 8; int gafr; if (gpio > pxa_last_gpio) return -EINVAL; local_irq_save(flags); if (gpio_mode & GPIO_DFLT_LOW) GPCR(gpio) = GPIO_bit(gpio); else if (gpio_mode & GPIO_DFLT_HIGH) GPSR(gpio) = GPIO_bit(gpio); if (gpio_mode & GPIO_MD_MASK_DIR) GPDR(gpio) |= GPIO_bit(gpio); else GPDR(gpio) &= ~GPIO_bit(gpio); gafr = GAFR(gpio) & ~(0x3 << (((gpio) & 0xf)*2)); GAFR(gpio) = gafr | (fn << (((gpio) & 0xf)*2)); local_irq_restore(flags); return 0; }
static int pxa2xx_mfp_suspend(struct sys_device *d, pm_message_t state) { int i; /* set corresponding PGSR bit of those marked MFP_LPM_KEEP_OUTPUT */ for (i = 0; i < pxa_last_gpio; i++) { if ((gpio_desc[i].config & MFP_LPM_KEEP_OUTPUT) && (GPDR(i) & GPIO_bit(i))) { if (GPLR(i) & GPIO_bit(i)) PGSR(i) |= GPIO_bit(i); else PGSR(i) &= ~GPIO_bit(i); } } for (i = 0; i <= gpio_to_bank(pxa_last_gpio); i++) { saved_gafr[0][i] = GAFR_L(i); saved_gafr[1][i] = GAFR_U(i); saved_gpdr[i] = GPDR(i * 32); saved_pgsr[i] = PGSR(i); GPDR(i * 32) = gpdr_lpm[i]; } return 0; }
static int init_module(void) { /* u32 reg; */ int result=1; result = misc_register(&dsp_misc); printk("btpxa_dsp 2.0: dsp_init\n"); if (result) printk("btweb: can't register /dev/dsp (error %i)\n", result); /* reg = GPDR; */ /* printk("btweb: dsp_init reg=%x letto\n",reg); DAVEDE */ /* reg &= ~GPIO_GPIO(1); */ /* GPIO1 is input */ GPDR(1) &= ~GPIO_bit(1); /* TODO: Da mettere nel boot loader */ /* reg |= GPIO_GPIO(17) | GPIO_GPIO(19); */ /* 17 and 19 are output DAVEDE */ /* TODO: Da mettere nel boot loader */ GPDR(19) |= GPIO_bit(19); GPDR(17) |= GPIO_bit(17); GPDR(73) |= GPIO_bit(73); /* GPDR = reg; */ /* printk("btweb: dsp_init reg=%x scritto\n",reg); DAVEDE */ /* TODO: Da mettere nel boot loader */ MCIO0 = 0x00018103; MCIO1 = 0x00018103; MECR = 0x00000001; return result; }
void pxa_gpio_func(int gpio, int mode, int dir) { if (dir) GPDR(gpio) |= GPIO_BIT(gpio); else GPDR(gpio) &= ~GPIO_BIT(gpio); /* Set the alternate function register */ GAFR(gpio) = (GAFR(gpio) & ~GPIO_GAFR_MASK(gpio)) | GPIO_GAFR_MODE(mode, gpio); }
void pxa_gpio_mode(int gpio_mode) { unsigned long flags; int gpio = gpio_mode & GPIO_MD_MASK_NR; int fn = (gpio_mode & GPIO_MD_MASK_FN) >> 8; int gafr; local_irq_save(flags); if (gpio_mode & GPIO_MD_MASK_DIR) GPDR(gpio) |= GPIO_bit(gpio); else GPDR(gpio) &= ~GPIO_bit(gpio); gafr = GAFR(gpio) & ~(0x3 << (((gpio) & 0xf)*2)); GAFR(gpio) = gafr | (fn << (((gpio) & 0xf)*2)); local_irq_restore(flags); }
/** * i2c_init_board - reset i2c bus. When the board is powercycled during a * bus transfer it might hang; for details see doc/I2C_Edge_Conditions. * The Innokom board has GPIO70 connected to SCLK which can be toggled * until all chips think that their current cycles are finished. */ int i2c_init_board(void) { int i; /* set gpio pin low _before_ we change direction to output */ writel(GPIO_bit(70), GPCR(70)); /* now toggle between output=low and high-impedance */ for (i = 0; i < 20; i++) { writel(readl(GPDR(70)) | GPIO_bit(70), GPDR(70)); /* output */ udelay(10); writel(readl(GPDR(70)) & ~GPIO_bit(70), GPDR(70)); /* input */ udelay(10); } return 0; }
void set_GPIO_mode(int gpio_mode) { int gpio = gpio_mode & GPIO_MD_MASK_NR; int fn = (gpio_mode & GPIO_MD_MASK_FN) >> 8; int gafr; if (gpio_mode & GPIO_MD_MASK_DIR) { GPDR(gpio) |= GPIO_bit(gpio); } else { GPDR(gpio) &= ~GPIO_bit(gpio); } gafr = GAFR(gpio) & ~(0x3 << (((gpio) & 0xf)*2)); GAFR(gpio) = gafr | (fn << (((gpio) & 0xf)*2)); }
static void pxa2xx_mfp_resume(void) { int i; for (i = 0; i <= gpio_to_bank(pxa_last_gpio); i++) { GAFR_L(i) = saved_gafr[0][i]; GAFR_U(i) = saved_gafr[1][i]; GPDR(i * 32) = saved_gpdr[i]; PGSR(i) = saved_pgsr[i]; } PSSR = PSSR_RDH | PSSR_PH; }
static int pxa2xx_mfp_resume(struct sys_device *d) { int i; for (i = 0; i <= gpio_to_bank(pxa_last_gpio); i++) { GAFR_L(i) = saved_gafr[0][i]; GAFR_U(i) = saved_gafr[1][i]; GPDR(i * 32) = saved_gpdr[i]; PGSR(i) = saved_pgsr[i]; } PSSR = PSSR_RDH | PSSR_PH; return 0; }
void set_GPIO_mode(int gpio_mode) { int gpio = gpio_mode & GPIO_MD_MASK_NR; int fn = (gpio_mode & GPIO_MD_MASK_FN) >> 8; int val; /* This below changes direction setting of GPIO "gpio" */ val = readl(GPDR(gpio)); if (gpio_mode & GPIO_MD_MASK_DIR) val |= GPIO_bit(gpio); else val &= ~GPIO_bit(gpio); writel(val, GPDR(gpio)); /* This below updates only AF of GPIO "gpio" */ val = readl(GAFR(gpio)); val &= ~(0x3 << (((gpio) & 0xf) * 2)); val |= fn << (((gpio) & 0xf) * 2); writel(val, GAFR(gpio)); }
static int pxa2xx_mfp_suspend(void) { int i; /* set corresponding PGSR bit of those marked MFP_LPM_KEEP_OUTPUT */ for (i = 0; i < pxa_last_gpio; i++) { if ((gpio_desc[i].config & MFP_LPM_KEEP_OUTPUT) && (GPDR(i) & GPIO_bit(i))) { if (GPLR(i) & GPIO_bit(i)) PGSR(gpio_to_bank(i)) |= GPIO_bit(i); else PGSR(gpio_to_bank(i)) &= ~GPIO_bit(i); } } for (i = 0; i <= gpio_to_bank(pxa_last_gpio); i++) { saved_gafr[0][i] = GAFR_L(i); saved_gafr[1][i] = GAFR_U(i); saved_gpdr[i] = GPDR(i * 32); saved_gplr[i] = GPLR(i * 32); saved_pgsr[i] = PGSR(i); GPSR(i * 32) = PGSR(i); GPCR(i * 32) = ~PGSR(i); } /* set GPDR bits taking into account MFP_LPM_KEEP_OUTPUT */ for (i = 0; i < pxa_last_gpio; i++) { if ((gpdr_lpm[gpio_to_bank(i)] & GPIO_bit(i)) || ((gpio_desc[i].config & MFP_LPM_KEEP_OUTPUT) && (saved_gpdr[gpio_to_bank(i)] & GPIO_bit(i)))) GPDR(i) |= GPIO_bit(i); else GPDR(i) &= ~GPIO_bit(i); } return 0; }
static int __mfp_config_gpio(unsigned gpio, unsigned long c) { unsigned long gafr, mask = GPIO_bit(gpio); int fn; fn = MFP_AF(c); if (fn > 3) return -EINVAL; /* alternate function and direction */ gafr = GAFR(gpio) & ~(0x3 << ((gpio & 0xf) * 2)); GAFR(gpio) = gafr | (fn << ((gpio & 0xf) * 2)); if (c & MFP_DIR_OUT) GPDR(gpio) |= mask; else GPDR(gpio) &= ~mask; if (__mfp_config_lpm(gpio, c & MFP_LPM_STATE_MASK)) return -EINVAL; /* give early warning if MFP_LPM_CAN_WAKEUP is set on the * configurations of those pins not able to wakeup */ if ((c & MFP_LPM_CAN_WAKEUP) && !gpio_desc[gpio].can_wakeup) { pr_warning("%s: GPIO%d unable to wakeup\n", __func__, gpio); return -EINVAL; } if ((c & MFP_LPM_CAN_WAKEUP) && (c & MFP_DIR_OUT)) { pr_warning("%s: output GPIO%d unable to wakeup\n", __func__, gpio); return -EINVAL; } return 0; }
/** * i2c_init_board - reset i2c bus. When the board is powercycled during a * bus transfer it might hang; for details see doc/I2C_Edge_Conditions. * The Innokom board has GPIO70 connected to SCLK which can be toggled * until all chips think that their current cycles are finished. */ int i2c_init_board(void) { int i, icr; /* disable I2C controller first, otherwhise it thinks we want to */ /* talk to the slave port... */ icr = ICR; ICR &= ~(ICR_SCLE | ICR_IUE); /* set gpio pin low _before_ we change direction to output */ GPCR(70) = GPIO_bit(70); /* now toggle between output=low and high-impedance */ for (i = 0; i < 20; i++) { GPDR(70) |= GPIO_bit(70); /* output */ udelay(10); GPDR(70) &= ~GPIO_bit(70); /* input */ udelay(10); } ICR = icr; return 0; }
void pxa_gpio_mode(int gpio_mode) { unsigned long flags; int gpio = gpio_mode & GPIO_MD_MASK_NR; int fn = (gpio_mode & GPIO_MD_MASK_FN) >> 8; int gafr; local_irq_save(flags); #ifndef CONFIG_PXA3xx if (gpio_mode & GPIO_DFLT_LOW) GPCR(gpio) = GPIO_bit(gpio); else if (gpio_mode & GPIO_DFLT_HIGH) GPSR(gpio) = GPIO_bit(gpio); if (gpio_mode & GPIO_MD_MASK_DIR) GPDR(gpio) |= GPIO_bit(gpio); else GPDR(gpio) &= ~GPIO_bit(gpio); gafr = GAFR(gpio) & ~(0x3 << (((gpio) & 0xf)*2)); GAFR(gpio) = gafr | (fn << (((gpio) & 0xf)*2)); #else GCDR(gpio) &= (1 << (gpio & 0x1f)); #endif local_irq_restore(flags); }
int gpio_direction_input(unsigned gpio) { unsigned long flags; u32 mask; if (gpio > pxa_last_gpio) return -EINVAL; mask = GPIO_bit(gpio); local_irq_save(flags); GPDR(gpio) &= ~mask; local_irq_restore(flags); return 0; }
// open() 함수를 이용하여 디바이스 드라이버가 열린 경우 호출되는 함수 static int cis_open(struct inode *minode, struct file *mfile) { int res; GPDR(IRQ_TO_GPIO(IRQ_CMOS)) &= ~GPIO_bit(IRQ_TO_GPIO(IRQ_CMOS)); set_irq_type(IRQ_CMOS, IRQ_TYPE_EDGE_RISING); res = request_irq(IRQ_CMOS,cis_interrupt,IRQF_DISABLED,"FPGA CAMERA",NULL); if(res < 0) printk(KERN_ERR "%s: Request for IRQ %d failed\n",__FUNCTION__,IRQ_CMOS); *mode_select = 0x00; *sub_sampling = 0x00; return 0; }
int gpio_direction_output(unsigned gpio, int value) { unsigned long flags; u32 mask; if (gpio > pxa_last_gpio) return -EINVAL; mask = GPIO_bit(gpio); local_irq_save(flags); if (value) GPSR(gpio) = mask; else GPCR(gpio) = mask; GPDR(gpio) |= mask; local_irq_restore(flags); return 0; }
static int pxa_gpio_irq_type(unsigned int irq, unsigned int type) { int gpio, idx; gpio = IRQ_TO_GPIO(irq); idx = gpio >> 5; if (type == IRQT_PROBE) { /* Don't mess with enabled GPIOs using preconfigured edges or GPIOs set to alternate function or to output during probe */ if ((GPIO_IRQ_rising_edge[idx] | GPIO_IRQ_falling_edge[idx] | GPDR(gpio)) & GPIO_bit(gpio)) return 0; if (GAFR(gpio) & (0x3 << (((gpio) & 0xf)*2))) return 0; type = __IRQT_RISEDGE | __IRQT_FALEDGE; } /* printk(KERN_DEBUG "IRQ%d (GPIO%d): ", irq, gpio); */ pxa_gpio_mode(gpio | GPIO_IN); if (type & __IRQT_RISEDGE) { /* printk("rising "); */ __set_bit (gpio, GPIO_IRQ_rising_edge); } else __clear_bit (gpio, GPIO_IRQ_rising_edge); if (type & __IRQT_FALEDGE) { /* printk("falling "); */ __set_bit (gpio, GPIO_IRQ_falling_edge); } else __clear_bit (gpio, GPIO_IRQ_falling_edge); /* printk("edges\n"); */ GRER(gpio) = GPIO_IRQ_rising_edge[idx] & GPIO_IRQ_mask[idx]; GFER(gpio) = GPIO_IRQ_falling_edge[idx] & GPIO_IRQ_mask[idx]; return 0; }
static int __init pxa2xx_mfp_init(void) { int i; if (!cpu_is_pxa2xx()) return 0; if (cpu_is_pxa25x()) pxa25x_mfp_init(); if (cpu_is_pxa27x()) pxa27x_mfp_init(); /* clear RDH bit to enable GPIO receivers after reset/sleep exit */ PSSR = PSSR_RDH; /* initialize gafr_run[], pgsr_lpm[] from existing values */ for (i = 0; i <= gpio_to_bank(pxa_last_gpio); i++) gpdr_lpm[i] = GPDR(i * 32); return 0; }
static int __init pxa2xx_mfp_init(void) { int i; if (!cpu_is_pxa2xx()) return 0; if (cpu_is_pxa25x()) pxa25x_mfp_init(); if (cpu_is_pxa27x()) pxa27x_mfp_init(); PSSR = PSSR_RDH; for (i = 0; i <= gpio_to_bank(pxa_last_gpio); i++) gpdr_lpm[i] = GPDR(i * 32); return 0; }
static int __mfp_config_gpio(unsigned gpio, unsigned long c) { unsigned long gafr, mask = GPIO_bit(gpio); int bank = gpio_to_bank(gpio); int uorl = !!(gpio & 0x10); int shft = (gpio & 0xf) << 1; int fn = MFP_AF(c); int is_out = (c & MFP_DIR_OUT) ? 1 : 0; if (fn > 3) return -EINVAL; gafr = (uorl == 0) ? GAFR_L(bank) : GAFR_U(bank); gafr = (gafr & ~(0x3 << shft)) | (fn << shft); if (uorl == 0) GAFR_L(bank) = gafr; else GAFR_U(bank) = gafr; if (is_out ^ gpio_desc[gpio].dir_inverted) GPDR(gpio) |= mask; else GPDR(gpio) &= ~mask; switch (c & MFP_LPM_STATE_MASK) { case MFP_LPM_DRIVE_HIGH: PGSR(bank) |= mask; is_out = 1; break; case MFP_LPM_DRIVE_LOW: PGSR(bank) &= ~mask; is_out = 1; break; case MFP_LPM_INPUT: case MFP_LPM_DEFAULT: break; default: pr_warning("%s: GPIO%d: unsupported low power mode\n", __func__, gpio); break; } if (is_out ^ gpio_desc[gpio].dir_inverted) gpdr_lpm[bank] |= mask; else gpdr_lpm[bank] &= ~mask; if ((c & MFP_LPM_CAN_WAKEUP) && !gpio_desc[gpio].can_wakeup) { pr_warning("%s: GPIO%d unable to wakeup\n", __func__, gpio); return -EINVAL; } if ((c & MFP_LPM_CAN_WAKEUP) && is_out) { pr_warning("%s: output GPIO%d unable to wakeup\n", __func__, gpio); return -EINVAL; } return 0; }
static int __mfp_config_gpio(unsigned gpio, unsigned long c) { unsigned long gafr, mask = GPIO_bit(gpio); int bank = gpio_to_bank(gpio); int uorl = !!(gpio & 0x10); /* GAFRx_U or GAFRx_L ? */ int shft = (gpio & 0xf) << 1; int fn = MFP_AF(c); int is_out = (c & MFP_DIR_OUT) ? 1 : 0; if (fn > 3) return -EINVAL; /* alternate function and direction at run-time */ gafr = (uorl == 0) ? GAFR_L(bank) : GAFR_U(bank); gafr = (gafr & ~(0x3 << shft)) | (fn << shft); if (uorl == 0) GAFR_L(bank) = gafr; else GAFR_U(bank) = gafr; if (is_out ^ gpio_desc[gpio].dir_inverted) GPDR(gpio) |= mask; else GPDR(gpio) &= ~mask; /* alternate function and direction at low power mode */ switch (c & MFP_LPM_STATE_MASK) { case MFP_LPM_DRIVE_HIGH: PGSR(bank) |= mask; is_out = 1; break; case MFP_LPM_DRIVE_LOW: PGSR(bank) &= ~mask; is_out = 1; break; case MFP_LPM_INPUT: case MFP_LPM_DEFAULT: break; default: /* warning and fall through, treat as MFP_LPM_DEFAULT */ pr_warning("%s: GPIO%d: unsupported low power mode\n", __func__, gpio); break; } if (is_out ^ gpio_desc[gpio].dir_inverted) gpdr_lpm[bank] |= mask; else gpdr_lpm[bank] &= ~mask; /* give early warning if MFP_LPM_CAN_WAKEUP is set on the * configurations of those pins not able to wakeup */ if ((c & MFP_LPM_CAN_WAKEUP) && !gpio_desc[gpio].can_wakeup) { pr_warning("%s: GPIO%d unable to wakeup\n", __func__, gpio); return -EINVAL; } if ((c & MFP_LPM_CAN_WAKEUP) && is_out) { pr_warning("%s: output GPIO%d unable to wakeup\n", __func__, gpio); return -EINVAL; } return 0; }