void retu_set_clear_reg_bits(int reg, u16 set, u16 clear) { unsigned long flags; u16 w; spin_lock_irqsave(&retu_lock, flags); w = retu_read_reg(reg); w &= ~clear; w |= set; retu_write_reg(reg, w); spin_unlock_irqrestore(&retu_lock, flags); }
/* * Disable given RETU interrupt */ void retu_disable_irq(int id) { unsigned long flags; u16 mask; spin_lock_irqsave(&retu_lock, flags); mask = retu_read_reg(RETU_REG_IMR); mask |= 1 << id; mask = retu_disable_bogus_irqs(mask); retu_write_reg(RETU_REG_IMR, mask); spin_unlock_irqrestore(&retu_lock, flags); }
static int retu_remove(struct device *dev) { #ifdef CONFIG_CBUS_RETU_USER retu_user_cleanup(); #endif /* Mask all RETU interrupts */ retu_write_reg(RETU_REG_IMR, 0xffff); free_irq(OMAP_GPIO_IRQ(retu_irq_pin), 0); omap_free_gpio(retu_irq_pin); tasklet_kill(&retu_tasklet); return 0; }
/* * Enable given RETU interrupt */ void retu_enable_irq(int id) { unsigned long flags; u16 mask; if (id == 3) { printk("Enabling Retu IRQ %d\n", id); dump_stack(); } spin_lock_irqsave(&retu_lock, flags); mask = retu_read_reg(RETU_REG_IMR); mask &= ~(1 << id); mask = retu_disable_bogus_irqs(mask); retu_write_reg(RETU_REG_IMR, mask); spin_unlock_irqrestore(&retu_lock, flags); }
int retu_read_adc(int channel) { unsigned long flags; int res; if (channel < 0 || channel > ADC_MAX_CHAN_NUMBER) return -EINVAL; spin_lock_irqsave(&retu_lock, flags); if ((channel == 8) && retu_is_vilma) { int scr = retu_read_reg(RETU_REG_ADCSCR); int ch = (retu_read_reg(RETU_REG_ADCR) >> 10) & 0xf; if (((scr & 0xff) != 0) && (ch != 8)) retu_write_reg (RETU_REG_ADCSCR, (scr & ~0xff)); }
int retu_read_adc(int channel) { unsigned long flags; int res; if (channel < 0 || channel > ADC_MAX_CHAN_NUMBER) return -EINVAL; spin_lock_irqsave(&retu_lock, flags); /* Select the channel and read result */ retu_write_reg(RETU_REG_ADCR, channel << 10); res = retu_read_reg(RETU_REG_ADCR) & 0x3ff; /* Unlock retu */ spin_unlock_irqrestore(&retu_lock, flags); return res; }
/** * retu_probe - Probe for Retu ASIC * @dev: the Retu device * * Probe for the Retu ASIC and allocate memory * for its device-struct if found */ static int __devinit retu_probe(struct device *dev) { const struct omap_em_asic_bb5_config * em_asic_config; int rev, ret; /* Prepare tasklet */ tasklet_init(&retu_tasklet, retu_tasklet_handler, 0); em_asic_config = omap_get_config(OMAP_TAG_EM_ASIC_BB5, struct omap_em_asic_bb5_config); if (em_asic_config == NULL) { printk(KERN_ERR PFX "Unable to retrieve config data\n"); return -ENODATA; } retu_irq_pin = em_asic_config->retu_irq_gpio; if ((ret = omap_request_gpio(retu_irq_pin)) < 0) { printk(KERN_ERR PFX "Unable to reserve IRQ GPIO\n"); return ret; } /* Set the pin as input */ omap_set_gpio_direction(retu_irq_pin, 1); /* Rising edge triggers the IRQ */ set_irq_type(OMAP_GPIO_IRQ(retu_irq_pin), IRQT_RISING); retu_initialized = 1; rev = retu_read_reg(RETU_REG_ASICR) & 0xff; if (rev & (1 << 7)) retu_is_vilma = 1; printk(KERN_INFO "%s v%d.%d found\n", retu_is_vilma ? "Vilma" : "Retu", (rev >> 4) & 0x07, rev & 0x0f); /* Mask all RETU interrupts */ retu_write_reg(RETU_REG_IMR, 0xffff); ret = request_irq(OMAP_GPIO_IRQ(retu_irq_pin), retu_irq_handler, 0, "retu", 0); if (ret < 0) { printk(KERN_ERR PFX "Unable to register IRQ handler\n"); omap_free_gpio(retu_irq_pin); return ret; } /* Register power off function */ pm_power_off = retu_power_off; #ifdef CONFIG_CBUS_RETU_USER /* Initialize user-space interface */ if (retu_user_init() < 0) { printk(KERN_ERR "Unable to initialize driver\n"); free_irq(OMAP_GPIO_IRQ(retu_irq_pin), 0); omap_free_gpio(retu_irq_pin); return ret; } #endif return 0; }
/* * Acknowledge given RETU interrupt */ void retu_ack_irq(int id) { retu_write_reg(RETU_REG_IDR, 1 << id); }