0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013 #include <linux/linkage.h>
0014 #include <linux/platform_data/ams-delta-fiq.h>
0015 #include <linux/platform_data/gpio-omap.h>
0016 #include <linux/soc/ti/omap1-io.h>
0017
0018 #include <asm/assembler.h>
0019 #include <asm/irq.h>
0020
0021 #include "hardware.h"
0022 #include "ams-delta-fiq.h"
0023 #include "board-ams-delta.h"
0024 #include "iomap.h"
0025
0026
0027
0028
0029
0030 #define OMAP1510_GPIO_BASE 0xFFFCE000
0031
0032
0033 #define KEYBRD_DATA_MASK (0x1 << AMS_DELTA_GPIO_PIN_KEYBRD_DATA)
0034 #define KEYBRD_CLK_MASK (0x1 << AMS_DELTA_GPIO_PIN_KEYBRD_CLK)
0035 #define MODEM_IRQ_MASK (0x1 << AMS_DELTA_GPIO_PIN_MODEM_IRQ)
0036 #define HOOK_SWITCH_MASK (0x1 << AMS_DELTA_GPIO_PIN_HOOK_SWITCH)
0037 #define OTHERS_MASK (MODEM_IRQ_MASK | HOOK_SWITCH_MASK)
0038
0039
0040 #define DEFERRED_FIQ_MASK OMAP_IRQ_BIT(INT_DEFERRED_FIQ)
0041 #define GPIO_BANK1_MASK OMAP_IRQ_BIT(INT_GPIO_BANK1)
0042
0043
0044 #define BUF_MASK (FIQ_MASK * 4)
0045 #define BUF_STATE (FIQ_STATE * 4)
0046 #define BUF_KEYS_CNT (FIQ_KEYS_CNT * 4)
0047 #define BUF_TAIL_OFFSET (FIQ_TAIL_OFFSET * 4)
0048 #define BUF_HEAD_OFFSET (FIQ_HEAD_OFFSET * 4)
0049 #define BUF_BUF_LEN (FIQ_BUF_LEN * 4)
0050 #define BUF_KEY (FIQ_KEY * 4)
0051 #define BUF_MISSED_KEYS (FIQ_MISSED_KEYS * 4)
0052 #define BUF_BUFFER_START (FIQ_BUFFER_START * 4)
0053 #define BUF_GPIO_INT_MASK (FIQ_GPIO_INT_MASK * 4)
0054 #define BUF_KEYS_HICNT (FIQ_KEYS_HICNT * 4)
0055 #define BUF_IRQ_PEND (FIQ_IRQ_PEND * 4)
0056 #define BUF_SIR_CODE_L1 (FIQ_SIR_CODE_L1 * 4)
0057 #define BUF_SIR_CODE_L2 (IRQ_SIR_CODE_L2 * 4)
0058 #define BUF_CNT_INT_00 (FIQ_CNT_INT_00 * 4)
0059 #define BUF_CNT_INT_KEY (FIQ_CNT_INT_KEY * 4)
0060 #define BUF_CNT_INT_MDM (FIQ_CNT_INT_MDM * 4)
0061 #define BUF_CNT_INT_03 (FIQ_CNT_INT_03 * 4)
0062 #define BUF_CNT_INT_HSW (FIQ_CNT_INT_HSW * 4)
0063 #define BUF_CNT_INT_05 (FIQ_CNT_INT_05 * 4)
0064 #define BUF_CNT_INT_06 (FIQ_CNT_INT_06 * 4)
0065 #define BUF_CNT_INT_07 (FIQ_CNT_INT_07 * 4)
0066 #define BUF_CNT_INT_08 (FIQ_CNT_INT_08 * 4)
0067 #define BUF_CNT_INT_09 (FIQ_CNT_INT_09 * 4)
0068 #define BUF_CNT_INT_10 (FIQ_CNT_INT_10 * 4)
0069 #define BUF_CNT_INT_11 (FIQ_CNT_INT_11 * 4)
0070 #define BUF_CNT_INT_12 (FIQ_CNT_INT_12 * 4)
0071 #define BUF_CNT_INT_13 (FIQ_CNT_INT_13 * 4)
0072 #define BUF_CNT_INT_14 (FIQ_CNT_INT_14 * 4)
0073 #define BUF_CNT_INT_15 (FIQ_CNT_INT_15 * 4)
0074 #define BUF_CIRC_BUFF (FIQ_CIRC_BUFF * 4)
0075
0076
0077
0078
0079
0080
0081
0082
0083
0084
0085
0086
0087 .text
0088
0089 .global qwerty_fiqin_end
0090
0091 ENTRY(qwerty_fiqin_start)
0092 @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
0093 @ FIQ intrrupt handler
0094 ldr r12, omap_ih1_base @ set pointer to level1 handler
0095
0096 ldr r11, [r12, #IRQ_MIR_REG_OFFSET] @ fetch interrupts mask
0097
0098 ldr r13, [r12, #IRQ_ITR_REG_OFFSET] @ fetch interrupts status
0099 bics r13, r13, r11 @ clear masked - any left?
0100 beq exit @ none - spurious FIQ? exit
0101
0102 ldr r10, [r12, #IRQ_SIR_FIQ_REG_OFFSET] @ get requested interrupt number
0103
0104 mov r8, #2 @ reset FIQ agreement
0105 str r8, [r12, #IRQ_CONTROL_REG_OFFSET]
0106
0107 cmp r10, #(INT_GPIO_BANK1 - NR_IRQS_LEGACY) @ is it GPIO interrupt?
0108 beq gpio @ yes - process it
0109
0110 mov r8, #1
0111 orr r8, r11, r8, lsl r10 @ mask spurious interrupt
0112 str r8, [r12, #IRQ_MIR_REG_OFFSET]
0113 exit:
0114 subs pc, lr, #4 @ return from FIQ
0115 @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
0116
0117
0118 @@@@@@@@@@@@@@@@@@@@@@@@@@@
0119 gpio: @ GPIO bank interrupt handler
0120 ldr r12, omap1510_gpio_base @ set base pointer to GPIO bank
0121
0122 ldr r11, [r12, #OMAP1510_GPIO_INT_MASK] @ fetch GPIO interrupts mask
0123 restart:
0124 ldr r13, [r12, #OMAP1510_GPIO_INT_STATUS] @ fetch status bits
0125 bics r13, r13, r11 @ clear masked - any left?
0126 beq exit @ no - spurious interrupt? exit
0127
0128 orr r11, r11, r13 @ mask all requested interrupts
0129 str r11, [r12, #OMAP1510_GPIO_INT_MASK]
0130
0131 str r13, [r12, #OMAP1510_GPIO_INT_STATUS] @ ack all requested interrupts
0132
0133 ands r10, r13, #KEYBRD_CLK_MASK @ extract keyboard status - set?
0134 beq hksw @ no - try next source
0135
0136
0137 @@@@@@@@@@@@@@@@@@@@@@
0138 @ Keyboard clock FIQ mode interrupt handler
0139 @ r10 now contains KEYBRD_CLK_MASK, use it
0140 bic r11, r11, r10 @ unmask it
0141 str r11, [r12, #OMAP1510_GPIO_INT_MASK]
0142
0143 @ Process keyboard data
0144 ldr r8, [r12, #OMAP1510_GPIO_DATA_INPUT] @ fetch GPIO input
0145
0146 ldr r10, [r9, #BUF_STATE] @ fetch kbd interface state
0147 cmp r10, #0 @ are we expecting start bit?
0148 bne data @ no - go to data processing
0149
0150 ands r8, r8, #KEYBRD_DATA_MASK @ check start bit - detected?
0151 beq hksw @ no - try next source
0152
0153 @ r8 contains KEYBRD_DATA_MASK, use it
0154 str r8, [r9, #BUF_STATE] @ enter data processing state
0155 @ r10 already contains 0, reuse it
0156 str r10, [r9, #BUF_KEY] @ clear keycode
0157 mov r10, #2 @ reset input bit mask
0158 str r10, [r9, #BUF_MASK]
0159
0160 @ Mask other GPIO line interrupts till key done
0161 str r11, [r9, #BUF_GPIO_INT_MASK] @ save mask for later restore
0162 mvn r11, #KEYBRD_CLK_MASK @ prepare all except kbd mask
0163 str r11, [r12, #OMAP1510_GPIO_INT_MASK] @ store into the mask register
0164
0165 b restart @ restart
0166
0167 data: ldr r10, [r9, #BUF_MASK] @ fetch current input bit mask
0168
0169 @ r8 still contains GPIO input bits
0170 ands r8, r8, #KEYBRD_DATA_MASK @ is keyboard data line low?
0171 ldreq r8, [r9, #BUF_KEY] @ yes - fetch collected so far,
0172 orreq r8, r8, r10 @ set 1 at current mask position
0173 streq r8, [r9, #BUF_KEY] @ and save back
0174
0175 mov r10, r10, lsl #1 @ shift mask left
0176 bics r10, r10, #0x800 @ have we got all the bits?
0177 strne r10, [r9, #BUF_MASK] @ not yet - store the mask
0178 bne restart @ and restart
0179
0180 @ r10 already contains 0, reuse it
0181 str r10, [r9, #BUF_STATE] @ reset state to start
0182
0183 @ Key done - restore interrupt mask
0184 ldr r10, [r9, #BUF_GPIO_INT_MASK] @ fetch saved mask
0185 and r11, r11, r10 @ unmask all saved as unmasked
0186 str r11, [r12, #OMAP1510_GPIO_INT_MASK] @ restore into the mask register
0187
0188 @ Try appending the keycode to the circular buffer
0189 ldr r10, [r9, #BUF_KEYS_CNT] @ get saved keystrokes count
0190 ldr r8, [r9, #BUF_BUF_LEN] @ get buffer size
0191 cmp r10, r8 @ is buffer full?
0192 beq hksw @ yes - key lost, next source
0193
0194 add r10, r10, #1 @ incremet keystrokes counter
0195 str r10, [r9, #BUF_KEYS_CNT]
0196
0197 ldr r10, [r9, #BUF_TAIL_OFFSET] @ get buffer tail offset
0198 @ r8 already contains buffer size
0199 cmp r10, r8 @ end of buffer?
0200 moveq r10, #0 @ yes - rewind to buffer start
0201
0202 ldr r12, [r9, #BUF_BUFFER_START] @ get buffer start address
0203 add r12, r12, r10, LSL #2 @ calculate buffer tail address
0204 ldr r8, [r9, #BUF_KEY] @ get last keycode
0205 str r8, [r12] @ append it to the buffer tail
0206
0207 add r10, r10, #1 @ increment buffer tail offset
0208 str r10, [r9, #BUF_TAIL_OFFSET]
0209
0210 ldr r10, [r9, #BUF_CNT_INT_KEY] @ increment interrupts counter
0211 add r10, r10, #1
0212 str r10, [r9, #BUF_CNT_INT_KEY]
0213 @@@@@@@@@@@@@@@@@@@@@@@@
0214
0215
0216 hksw: @Is hook switch interrupt requested?
0217 tst r13, #HOOK_SWITCH_MASK @ is hook switch status bit set?
0218 beq mdm @ no - try next source
0219
0220
0221 @@@@@@@@@@@@@@@@@@@@@@@@
0222 @ Hook switch interrupt FIQ mode simple handler
0223
0224 @ Don't toggle active edge, the switch always bounces
0225
0226 @ Increment hook switch interrupt counter
0227 ldr r10, [r9, #BUF_CNT_INT_HSW]
0228 add r10, r10, #1
0229 str r10, [r9, #BUF_CNT_INT_HSW]
0230 @@@@@@@@@@@@@@@@@@@@@@@@
0231
0232
0233 mdm: @Is it a modem interrupt?
0234 tst r13, #MODEM_IRQ_MASK @ is modem status bit set?
0235 beq irq @ no - check for next interrupt
0236
0237
0238 @@@@@@@@@@@@@@@@@@@@@@@@
0239 @ Modem FIQ mode interrupt handler stub
0240
0241 @ Increment modem interrupt counter
0242 ldr r10, [r9, #BUF_CNT_INT_MDM]
0243 add r10, r10, #1
0244 str r10, [r9, #BUF_CNT_INT_MDM]
0245 @@@@@@@@@@@@@@@@@@@@@@@@
0246
0247
0248 irq: @ Place deferred_fiq interrupt request
0249 ldr r12, deferred_fiq_ih_base @ set pointer to IRQ handler
0250 mov r10, #DEFERRED_FIQ_MASK @ set deferred_fiq bit
0251 str r10, [r12, #IRQ_ISR_REG_OFFSET] @ place it in the ISR register
0252
0253 ldr r12, omap1510_gpio_base @ set pointer back to GPIO bank
0254 b restart @ check for next GPIO interrupt
0255 @@@@@@@@@@@@@@@@@@@@@@@@@@@
0256
0257
0258
0259
0260
0261 omap_ih1_base:
0262 .word OMAP1_IO_ADDRESS(OMAP_IH1_BASE)
0263 deferred_fiq_ih_base:
0264 .word OMAP1_IO_ADDRESS(DEFERRED_FIQ_IH_BASE)
0265 omap1510_gpio_base:
0266 .word OMAP1_IO_ADDRESS(OMAP1510_GPIO_BASE)
0267 qwerty_fiqin_end:
0268
0269
0270
0271
0272
0273 .if (qwerty_fiqin_end - qwerty_fiqin_start) > (0x200 - 0x1c)
0274 .err
0275 .endif