mbed library sources. Supersedes mbed-src.

Dependents:   Nucleo_Hello_Encoder BLE_iBeaconScan AM1805_DEMO DISCO-F429ZI_ExportTemplate1 ... more

Committer:
<>
Date:
Tue Mar 14 16:40:56 2017 +0000
Revision:
160:d5399cc887bb
Parent:
159:612c381a210f
Child:
180:96ed750bd169
This updates the lib to the mbed lib v138

Who changed what in which revision?

UserRevisionLine numberNew contents of line
<> 144:ef7eb2e8f9f7 1 /* mbed Microcontroller Library
<> 144:ef7eb2e8f9f7 2 * Copyright (c) 2006-2013 ARM Limited
<> 144:ef7eb2e8f9f7 3 *
<> 144:ef7eb2e8f9f7 4 * Licensed under the Apache License, Version 2.0 (the "License");
<> 144:ef7eb2e8f9f7 5 * you may not use this file except in compliance with the License.
<> 144:ef7eb2e8f9f7 6 * You may obtain a copy of the License at
<> 144:ef7eb2e8f9f7 7 *
<> 144:ef7eb2e8f9f7 8 * http://www.apache.org/licenses/LICENSE-2.0
<> 144:ef7eb2e8f9f7 9 *
<> 144:ef7eb2e8f9f7 10 * Unless required by applicable law or agreed to in writing, software
<> 144:ef7eb2e8f9f7 11 * distributed under the License is distributed on an "AS IS" BASIS,
<> 144:ef7eb2e8f9f7 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
<> 144:ef7eb2e8f9f7 13 * See the License for the specific language governing permissions and
<> 144:ef7eb2e8f9f7 14 * limitations under the License.
<> 144:ef7eb2e8f9f7 15 */
<> 144:ef7eb2e8f9f7 16 #include <stddef.h>
<> 144:ef7eb2e8f9f7 17
<> 144:ef7eb2e8f9f7 18 #include "gpio_irq_api.h"
<> 144:ef7eb2e8f9f7 19 #include "intc_iodefine.h"
<> 144:ef7eb2e8f9f7 20 #include "pinmap.h"
<> 144:ef7eb2e8f9f7 21 #include "cmsis.h"
<> 144:ef7eb2e8f9f7 22 #include "gpio_addrdefine.h"
<> 144:ef7eb2e8f9f7 23
<> 144:ef7eb2e8f9f7 24 #define CHANNEL_NUM 8
<> 144:ef7eb2e8f9f7 25
<> 144:ef7eb2e8f9f7 26 static void gpio_irq0(void);
<> 144:ef7eb2e8f9f7 27 static void gpio_irq1(void);
<> 144:ef7eb2e8f9f7 28 static void gpio_irq2(void);
<> 144:ef7eb2e8f9f7 29 static void gpio_irq3(void);
<> 144:ef7eb2e8f9f7 30 static void gpio_irq4(void);
<> 144:ef7eb2e8f9f7 31 static void gpio_irq5(void);
<> 144:ef7eb2e8f9f7 32 static void gpio_irq6(void);
<> 144:ef7eb2e8f9f7 33 static void gpio_irq7(void);
<> 144:ef7eb2e8f9f7 34
<> 144:ef7eb2e8f9f7 35 static gpio_irq_t *channel_obj[CHANNEL_NUM] = {NULL};
<> 144:ef7eb2e8f9f7 36 static gpio_irq_handler irq_handler;
<> 144:ef7eb2e8f9f7 37 static const int nIRQn_h = 32;
<> 144:ef7eb2e8f9f7 38 extern PinName gpio_multi_guard;
<> 144:ef7eb2e8f9f7 39
<> 144:ef7eb2e8f9f7 40 enum {
<> 144:ef7eb2e8f9f7 41 IRQ0,IRQ1,
<> 144:ef7eb2e8f9f7 42 IRQ2,IRQ3,
<> 144:ef7eb2e8f9f7 43 IRQ4,IRQ5,
<> 144:ef7eb2e8f9f7 44 IRQ6,IRQ7,
<> 144:ef7eb2e8f9f7 45
<> 144:ef7eb2e8f9f7 46 } IRQNo;
<> 144:ef7eb2e8f9f7 47
<> 144:ef7eb2e8f9f7 48 static const IRQHandler irq_tbl[CHANNEL_NUM] = {
<> 144:ef7eb2e8f9f7 49 &gpio_irq0,
<> 144:ef7eb2e8f9f7 50 &gpio_irq1,
<> 144:ef7eb2e8f9f7 51 &gpio_irq2,
<> 144:ef7eb2e8f9f7 52 &gpio_irq3,
<> 144:ef7eb2e8f9f7 53 &gpio_irq4,
<> 144:ef7eb2e8f9f7 54 &gpio_irq5,
<> 144:ef7eb2e8f9f7 55 &gpio_irq6,
<> 144:ef7eb2e8f9f7 56 &gpio_irq7,
<> 144:ef7eb2e8f9f7 57 };
<> 144:ef7eb2e8f9f7 58
<> 144:ef7eb2e8f9f7 59 static const PinMap PinMap_IRQ[] = {
<> 144:ef7eb2e8f9f7 60 {P1_0, IRQ0, 4}, {P1_1, IRQ1, 4}, {P1_2, IRQ2, 4},
<> 144:ef7eb2e8f9f7 61 {P1_3, IRQ3, 4}, {P1_4, IRQ4, 4}, {P1_5, IRQ5, 4},
<> 144:ef7eb2e8f9f7 62 {P1_6, IRQ6, 4}, {P1_7, IRQ7, 4}, {P1_8, IRQ2, 3},
<> 144:ef7eb2e8f9f7 63 {P1_9, IRQ3, 3}, {P1_10, IRQ4, 3}, {P1_11, IRQ5, 3}, // 11
<> 144:ef7eb2e8f9f7 64 {P2_0, IRQ5, 6}, {P2_12, IRQ6, 6}, {P2_13, IRQ7, 8},
<> 144:ef7eb2e8f9f7 65 {P2_14, IRQ0, 8}, {P2_15, IRQ1, 8}, // 16
<> 144:ef7eb2e8f9f7 66 {P3_0, IRQ2, 3}, {P3_1, IRQ6, 3}, {P3_3, IRQ4, 3},
<> 144:ef7eb2e8f9f7 67 {P3_9, IRQ6, 8}, // 20
<> 144:ef7eb2e8f9f7 68 {P4_8, IRQ0, 8}, {P4_9, IRQ1, 8}, {P4_10, IRQ2, 8},
<> 144:ef7eb2e8f9f7 69 {P4_11, IRQ3, 8}, {P4_12, IRQ4, 8}, {P4_13, IRQ5, 8},
<> 144:ef7eb2e8f9f7 70 {P4_14, IRQ6, 8}, {P4_15, IRQ7, 8}, // 28
<> 144:ef7eb2e8f9f7 71 {P5_6, IRQ6, 6}, {P5_8, IRQ0, 2}, {P5_9, IRQ2, 4}, // 31
<> 144:ef7eb2e8f9f7 72 {P6_0, IRQ5, 6}, {P6_1, IRQ4, 4}, {P6_2, IRQ7, 4},
<> 144:ef7eb2e8f9f7 73 {P6_3, IRQ2, 4}, {P6_4, IRQ3, 4}, {P6_8, IRQ0, 8},
<> 144:ef7eb2e8f9f7 74 {P6_9, IRQ1, 8}, {P6_10, IRQ2, 8}, {P6_11, IRQ3, 8},
<> 144:ef7eb2e8f9f7 75 {P6_12, IRQ4, 8}, {P6_13, IRQ5, 8}, {P6_14, IRQ6, 8},
<> 144:ef7eb2e8f9f7 76 {P6_15, IRQ7, 8}, // 44
<> 144:ef7eb2e8f9f7 77 {P7_8, IRQ1, 8}, {P7_9, IRQ0, 8}, {P7_10, IRQ2, 8},
<> 144:ef7eb2e8f9f7 78 {P7_11, IRQ3, 8}, {P7_12, IRQ4, 8}, {P7_13, IRQ5, 8},
<> 144:ef7eb2e8f9f7 79 {P7_14, IRQ6, 8}, // 51
<> 144:ef7eb2e8f9f7 80 {P8_2, IRQ0, 5}, {P8_3, IRQ1, 6}, {P8_7, IRQ5, 4},
<> 144:ef7eb2e8f9f7 81 {P9_1, IRQ0, 4}, // 55
<> 144:ef7eb2e8f9f7 82 {P11_12,IRQ3, 3}, {P11_15,IRQ1, 3}, // 57
<> 144:ef7eb2e8f9f7 83
<> 144:ef7eb2e8f9f7 84 {NC, NC, 0}
<> 144:ef7eb2e8f9f7 85 };
<> 144:ef7eb2e8f9f7 86
<> 144:ef7eb2e8f9f7 87 static void handle_interrupt_in(int irq_num) {
<> 144:ef7eb2e8f9f7 88 uint16_t irqs;
<> 144:ef7eb2e8f9f7 89 uint16_t edge_req;
<> 144:ef7eb2e8f9f7 90 gpio_irq_t *obj;
<> 144:ef7eb2e8f9f7 91 gpio_irq_event irq_event;
<> 144:ef7eb2e8f9f7 92
<> 144:ef7eb2e8f9f7 93 irqs = INTCIRQRR;
<> 144:ef7eb2e8f9f7 94 if (irqs & (1 << irq_num)) {
<> 144:ef7eb2e8f9f7 95 obj = channel_obj[irq_num];
<> 144:ef7eb2e8f9f7 96 if (obj != NULL) {
<> 144:ef7eb2e8f9f7 97 edge_req = ((INTCICR1 >> (obj->ch * 2)) & 3);
<> 144:ef7eb2e8f9f7 98 if (edge_req == 1) {
<> 144:ef7eb2e8f9f7 99 irq_event = IRQ_FALL;
<> 144:ef7eb2e8f9f7 100 } else if (edge_req == 2) {
<> 144:ef7eb2e8f9f7 101 irq_event = IRQ_RISE;
<> 144:ef7eb2e8f9f7 102 } else {
<> 144:ef7eb2e8f9f7 103 uint32_t mask = (1 << (obj->pin & 0x0F));
<> 144:ef7eb2e8f9f7 104 __I uint32_t *reg_in = (volatile uint32_t *) PPR((int)PINGROUP(obj->pin));
<> 144:ef7eb2e8f9f7 105
<> 144:ef7eb2e8f9f7 106 if ((*reg_in & mask) == 0) {
<> 144:ef7eb2e8f9f7 107 irq_event = IRQ_FALL;
<> 144:ef7eb2e8f9f7 108 } else {
<> 144:ef7eb2e8f9f7 109 irq_event = IRQ_RISE;
<> 144:ef7eb2e8f9f7 110 }
<> 144:ef7eb2e8f9f7 111 }
<> 144:ef7eb2e8f9f7 112 irq_handler(obj->port, irq_event);
<> 144:ef7eb2e8f9f7 113 }
<> 144:ef7eb2e8f9f7 114 INTCIRQRR &= ~(1 << irq_num);
<> 144:ef7eb2e8f9f7 115 }
<> 144:ef7eb2e8f9f7 116 }
<> 144:ef7eb2e8f9f7 117
<> 144:ef7eb2e8f9f7 118 static void gpio_irq0(void) {
<> 144:ef7eb2e8f9f7 119 handle_interrupt_in(0);
<> 144:ef7eb2e8f9f7 120 }
<> 144:ef7eb2e8f9f7 121
<> 144:ef7eb2e8f9f7 122 static void gpio_irq1(void) {
<> 144:ef7eb2e8f9f7 123 handle_interrupt_in(1);
<> 144:ef7eb2e8f9f7 124 }
<> 144:ef7eb2e8f9f7 125
<> 144:ef7eb2e8f9f7 126 static void gpio_irq2(void) {
<> 144:ef7eb2e8f9f7 127 handle_interrupt_in(2);
<> 144:ef7eb2e8f9f7 128 }
<> 144:ef7eb2e8f9f7 129
<> 144:ef7eb2e8f9f7 130 static void gpio_irq3(void) {
<> 144:ef7eb2e8f9f7 131 handle_interrupt_in(3);
<> 144:ef7eb2e8f9f7 132 }
<> 144:ef7eb2e8f9f7 133
<> 144:ef7eb2e8f9f7 134 static void gpio_irq4(void) {
<> 144:ef7eb2e8f9f7 135 handle_interrupt_in(4);
<> 144:ef7eb2e8f9f7 136 }
<> 144:ef7eb2e8f9f7 137
<> 144:ef7eb2e8f9f7 138 static void gpio_irq5(void) {
<> 144:ef7eb2e8f9f7 139 handle_interrupt_in(5);
<> 144:ef7eb2e8f9f7 140 }
<> 144:ef7eb2e8f9f7 141
<> 144:ef7eb2e8f9f7 142 static void gpio_irq6(void) {
<> 144:ef7eb2e8f9f7 143 handle_interrupt_in(6);
<> 144:ef7eb2e8f9f7 144 }
<> 144:ef7eb2e8f9f7 145
<> 144:ef7eb2e8f9f7 146 static void gpio_irq7(void) {
<> 144:ef7eb2e8f9f7 147 handle_interrupt_in(7);
<> 144:ef7eb2e8f9f7 148 }
<> 144:ef7eb2e8f9f7 149
<> 144:ef7eb2e8f9f7 150 int gpio_irq_init(gpio_irq_t *obj, PinName pin, gpio_irq_handler handler, uint32_t id) {
<> 144:ef7eb2e8f9f7 151 int shift;
<> 144:ef7eb2e8f9f7 152 if (pin == NC) return -1;
<> 144:ef7eb2e8f9f7 153
<> 144:ef7eb2e8f9f7 154 obj->ch = pinmap_peripheral(pin, PinMap_IRQ);
<> 144:ef7eb2e8f9f7 155 obj->pin = (int)pin ;
<> 144:ef7eb2e8f9f7 156 obj->port = (int)id ;
<> 144:ef7eb2e8f9f7 157
<> 144:ef7eb2e8f9f7 158 shift = obj->ch*2;
<> 144:ef7eb2e8f9f7 159 channel_obj[obj->ch] = obj;
<> 144:ef7eb2e8f9f7 160 irq_handler = handler;
<> 144:ef7eb2e8f9f7 161
<> 144:ef7eb2e8f9f7 162 pinmap_pinout(pin, PinMap_IRQ);
<> 144:ef7eb2e8f9f7 163 gpio_multi_guard = pin; /* Set multi guard */
<> 144:ef7eb2e8f9f7 164
<> 144:ef7eb2e8f9f7 165 // INTC settings
<> 144:ef7eb2e8f9f7 166 InterruptHandlerRegister((IRQn_Type)(nIRQn_h+obj->ch), (void (*)(uint32_t))irq_tbl[obj->ch]);
<> 144:ef7eb2e8f9f7 167 INTCICR1 &= ~(0x3 << shift);
<> 144:ef7eb2e8f9f7 168 GIC_SetPriority((IRQn_Type)(nIRQn_h+obj->ch), 5);
<> 144:ef7eb2e8f9f7 169 obj->int_enable = 1;
<> 144:ef7eb2e8f9f7 170 __enable_irq();
<> 144:ef7eb2e8f9f7 171
<> 144:ef7eb2e8f9f7 172 return 0;
<> 144:ef7eb2e8f9f7 173 }
<> 144:ef7eb2e8f9f7 174
<> 144:ef7eb2e8f9f7 175 void gpio_irq_free(gpio_irq_t *obj) {
<> 144:ef7eb2e8f9f7 176 channel_obj[obj->ch] = NULL;
<> 144:ef7eb2e8f9f7 177 }
<> 144:ef7eb2e8f9f7 178
<> 144:ef7eb2e8f9f7 179 void gpio_irq_set(gpio_irq_t *obj, gpio_irq_event event, uint32_t enable) {
<> 144:ef7eb2e8f9f7 180 int shift = obj->ch*2;
<> 144:ef7eb2e8f9f7 181 uint16_t val = event == IRQ_RISE ? 2 :
<> 144:ef7eb2e8f9f7 182 event == IRQ_FALL ? 1 : 0;
<> 144:ef7eb2e8f9f7 183 uint16_t work_icr_val;
<> 144:ef7eb2e8f9f7 184
<> 144:ef7eb2e8f9f7 185 /* check edge interrupt setting */
<> 144:ef7eb2e8f9f7 186 work_icr_val = INTCICR1;
<> 144:ef7eb2e8f9f7 187 if (enable == 1) {
<> 144:ef7eb2e8f9f7 188 /* Set interrupt serect */
<> 144:ef7eb2e8f9f7 189 work_icr_val |= (val << shift);
<> 144:ef7eb2e8f9f7 190 } else {
<> 144:ef7eb2e8f9f7 191 /* Clear interrupt serect */
<> 144:ef7eb2e8f9f7 192 work_icr_val &= ~(val << shift);
<> 144:ef7eb2e8f9f7 193 }
<> 144:ef7eb2e8f9f7 194
<> 144:ef7eb2e8f9f7 195 if ((work_icr_val & (3 << shift)) == 0) {
<> 144:ef7eb2e8f9f7 196 /* No edge interrupt setting */
<> 144:ef7eb2e8f9f7 197 GIC_DisableIRQ((IRQn_Type)(nIRQn_h+obj->ch));
<> 144:ef7eb2e8f9f7 198 /* Clear Interrupt flags */
<> 144:ef7eb2e8f9f7 199 INTCIRQRR &= ~(1 << obj->ch);
<> 144:ef7eb2e8f9f7 200 INTCICR1 = work_icr_val;
<> 144:ef7eb2e8f9f7 201 } else if (obj->int_enable == 1) {
<> 144:ef7eb2e8f9f7 202 INTCICR1 = work_icr_val;
<> 144:ef7eb2e8f9f7 203 GIC_EnableIRQ((IRQn_Type)(nIRQn_h + obj->ch));
<> 144:ef7eb2e8f9f7 204 } else {
<> 144:ef7eb2e8f9f7 205 INTCICR1 = work_icr_val;
<> 144:ef7eb2e8f9f7 206 }
<> 144:ef7eb2e8f9f7 207 }
<> 144:ef7eb2e8f9f7 208
<> 144:ef7eb2e8f9f7 209 void gpio_irq_enable(gpio_irq_t *obj) {
<> 144:ef7eb2e8f9f7 210 int shift = obj->ch*2;
<> 144:ef7eb2e8f9f7 211 uint16_t work_icr_val = INTCICR1;
<> 144:ef7eb2e8f9f7 212
<> 144:ef7eb2e8f9f7 213 /* check edge interrupt setting */
<> 144:ef7eb2e8f9f7 214 if ((work_icr_val & (3 << shift)) != 0) {
<> 144:ef7eb2e8f9f7 215 GIC_EnableIRQ((IRQn_Type)(nIRQn_h + obj->ch));
<> 144:ef7eb2e8f9f7 216 }
<> 144:ef7eb2e8f9f7 217 obj->int_enable = 1;
<> 144:ef7eb2e8f9f7 218 }
<> 144:ef7eb2e8f9f7 219
<> 144:ef7eb2e8f9f7 220 void gpio_irq_disable(gpio_irq_t *obj) {
<> 144:ef7eb2e8f9f7 221 GIC_DisableIRQ((IRQn_Type)(nIRQn_h + obj->ch));
<> 144:ef7eb2e8f9f7 222 obj->int_enable = 0;
<> 144:ef7eb2e8f9f7 223 }
<> 144:ef7eb2e8f9f7 224