2 * Copyright © 2011 Keith Packard <keithp@keithp.com>
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; either version 2 of the License, or
7 * (at your option) any later version.
9 * This program is distributed in the hope that it will be useful, but
10 * WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * General Public License for more details.
14 * You should have received a copy of the GNU General Public License along
15 * with this program; if not, write to the Free Software Foundation, Inc.,
16 * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
21 volatile __xdata struct ao_fifo ao_button_fifo;
23 static __code struct {
28 { BUTTON_1_MASK, BUTTON_1_REG },
31 { BUTTON_2_MASK, BUTTON_2_REG },
34 { BUTTON_3_MASK, BUTTON_3_REG },
38 #define NUM_BUTTONS ((sizeof ao_buttons) / sizeof (ao_buttons[0]))
40 static __xdata uint16_t ao_button_tick[NUM_BUTTONS];
43 ao_button_insert(char n)
45 uint16_t now = ao_time();
46 if ((now - ao_button_tick[n]) > 20) {
47 ao_button_tick[n] = now;
48 ao_fifo_insert(ao_button_fifo, n);
49 ao_wakeup(&ao_button_fifo);
54 ao_button_isr(uint8_t flag, uint8_t reg)
58 for (b = 0; b < NUM_BUTTONS; b++)
59 if (ao_buttons[b].reg == reg && (ao_buttons[b].mask & flag))
60 ao_button_insert(b + 1);
64 ao_button_mask(uint8_t reg)
69 for (b = 0; b < NUM_BUTTONS; b++)
70 if (ao_buttons[b].reg == reg)
71 mask |= ao_buttons[b].mask;
76 ao_button_get(uint16_t timeout) __critical
80 while (ao_fifo_empty(ao_button_fifo))
81 if (ao_sleep_for(&ao_button_fifo, timeout))
83 ao_fifo_remove(ao_button_fifo, b);
88 ao_button_clear(void) __critical
92 while (!ao_fifo_empty(ao_button_fifo))
93 ao_fifo_remove(ao_button_fifo, b);
97 ao_p0_isr(void) ao_arch_interrupt(13)
100 ao_button_isr(P0IFG, 0);
105 ao_p1_isr(void) ao_arch_interrupt(15)
108 ao_button_isr(P1IFG, 1);
112 /* Shared with USB */
116 ao_button_isr(P2IFG, 2);
125 /* Pins are configured as inputs with pull-up by default */
127 /* Enable interrupts for P0 inputs */
128 mask = ao_button_mask(0);
131 PICTL |= PICTL_P0IENL;
133 PICTL |= PICTL_P0IENH;
137 PICTL |= PICTL_P0ICON;
140 /* Enable interrupts for P1 inputs */
141 mask = ao_button_mask(1);
147 PICTL |= PICTL_P1ICON;
150 /* Enable interrupts for P2 inputs */
151 mask = ao_button_mask(2);
153 PICTL |= PICTL_P2IEN;
157 PICTL |= PICTL_P2ICON;