Пример #1
0
int ara_key_enable(const struct ara_board_info *info,
                   int (*longpress_callback)(void *priv), bool enable)
{
    if (enable) {
        if (!info->ara_key_configured) {
            dbg_error("%s: no ara key gpio defined\n", __func__);
            return -EINVAL;
        }

        the_ara_key.longpress_callback = longpress_callback;
        the_ara_key.db.gpio = info->ara_key_gpio;
	the_ara_key.db.ms = ARA_KEY_DEBOUNCE_TIME_MS;
        the_ara_key.db.isr = ara_key_irqhandler;
        the_ara_key.db.db_state = DB_ST_INVALID;
        the_ara_key.rising_edge = info->ara_key_rising_edge;

        gpio_activate(info->ara_key_gpio);
        gpio_direction_in(info->ara_key_gpio);
        gpio_irq_mask(info->ara_key_gpio);
        gpio_irq_settriggering(info->ara_key_gpio, IRQ_TYPE_EDGE_BOTH);
        gpio_irq_attach(info->ara_key_gpio, ara_key_irqhandler);
    } else {
        gpio_irq_mask(info->ara_key_gpio);
        gpio_deactivate(info->ara_key_gpio);
    }

    return OK;
}
Пример #2
0
static void gpio_irq_handler(unsigned irq, struct irq_desc *desc)
{
	unsigned	pin;
	struct irq_desc	*gpio;
	struct at91_gpio_bank *bank;
	void __iomem	*pio;
	u32		isr;

	bank = get_irq_chip_data(irq);
	pio = bank->regbase;

	/* temporarily mask (level sensitive) parent IRQ */
	desc->chip->ack(irq);
	for (;;) {
		/* Reading ISR acks pending (edge triggered) GPIO interrupts.
		 * When there none are pending, we're finished unless we need
		 * to process multiple banks (like ID_PIOCDE on sam9263).
		 */
		isr = __raw_readl(pio + PIO_ISR) & __raw_readl(pio + PIO_IMR);
		if (!isr) {
			if (!bank->next)
				break;
			bank = bank->next;
			pio = bank->regbase;
			continue;
		}

		pin = bank->chipbase;
		gpio = &irq_desc[pin];

		while (isr) {
			if (isr & 1) {
				if (unlikely(gpio->depth)) {
					/*
					 * The core ARM interrupt handler lazily disables IRQs so
					 * another IRQ must be generated before it actually gets
					 * here to be disabled on the GPIO controller.
					 */
					gpio_irq_mask(pin);
				}
				else
					desc_handle_irq(pin, gpio);
			}
			pin++;
			gpio++;
			isr >>= 1;
		}
	}
	desc->chip->unmask(irq);
	/* now it may re-trigger */
}
Пример #3
0
static void fh_gpio_interrupt(int irq, void *param)
{
    rt_uint32_t irq_status;
    int gpio_num, gpio;
    rt_uint32_t base;
//   struct fh_gpio_obj *gpio_obj = (struct fh_gpio_obj *)param;

    // rt_kprintf("fh_gpio_interrupt start\n");

    // fixme: spin lock???
    base = (irq == 40) ? GPIO0_REG_BASE : GPIO1_REG_BASE;

    irq_status = GET_REG(base + REG_GPIO_INTSTATUS);

    if (irq_status == 0)
    {
        rt_kprintf("gpio irq status is zero.\n");
        return;
    }

    /* temporarily mask (level sensitive) parent IRQ */
    gpio_irq_mask(irq);

    gpio_num = __rt_ffs(irq_status) - 1;

    SET_REG(base + REG_GPIO_PORTA_EOI, BIT(gpio_num));

    gpio = gpio_num + ((irq == 40) ? 0 : 32);

    // generic_handle_irq(gpio_to_irq(gpio));
    if (irq_desc[gpio_to_irq(gpio)].handler)
        irq_desc[gpio_to_irq(gpio)].handler(gpio_to_irq(gpio),
                                            irq_desc[gpio_to_irq(gpio)].param);

    gpio_irq_mask(irq);
    /* now it may re-trigger */
}
Пример #4
0
static void gpio_irq_handler(unsigned irq, struct irq_desc *desc)
{
	unsigned	pin;
	struct irq_desc	*gpio;
	void __iomem	*pio;
	u32		isr;

	pio = get_irq_chip_data(irq);

	/* temporarily mask (level sensitive) parent IRQ */
	desc->chip->ack(irq);
	for (;;) {
		/* reading ISR acks the pending (edge triggered) GPIO interrupt */
		isr = __raw_readl(pio + PIO_ISR) & __raw_readl(pio + PIO_IMR);
		if (!isr)
			break;

		pin = (unsigned) get_irq_data(irq);
		gpio = &irq_desc[pin];

		while (isr) {
			if (isr & 1) {
				if (unlikely(gpio->depth)) {
					/*
					 * The core ARM interrupt handler lazily disables IRQs so
					 * another IRQ must be generated before it actually gets
					 * here to be disabled on the GPIO controller.
					 */
					gpio_irq_mask(pin);
				}
				else
					desc_handle_irq(pin, gpio);
			}
			pin++;
			gpio++;
			isr >>= 1;
		}
	}
	desc->chip->unmask(irq);
	/* now it may re-trigger */
}