mbed library sources

Dependents:   Encrypted my_mbed lklk CyaSSL_DTLS_Cellular ... more

Superseded

This library was superseded by mbed-dev - https://os.mbed.com/users/mbed_official/code/mbed-dev/.

Development branch of the mbed library sources. This library is kept in synch with the latest changes from the mbed SDK and it is not guaranteed to work.

If you are looking for a stable and tested release, please import one of the official mbed library releases:

Import librarymbed

The official Mbed 2 C/C++ SDK provides the software platform and libraries to build your applications.

Committer:
mbed_official
Date:
Fri Oct 31 13:45:07 2014 +0000
Revision:
378:be043393235b
Parent:
314:b682143dd337
Child:
395:bfce16e86ea4
Synchronized with git revision e7e9dd54ebd366325b11c63276cf9e0e2191ad4d

Full URL: https://github.com/mbedmicro/mbed/commit/e7e9dd54ebd366325b11c63276cf9e0e2191ad4d/

Toolchain: NUCLEO_F334R8 - support for IAR

Who changed what in which revision?

UserRevisionLine numberNew contents of line
mbed_official 85:e1a8e879a6a9 1 /* mbed Microcontroller Library
mbed_official 104:a6a92e2e5a92 2 * Copyright (c) 2013 Nordic Semiconductor
mbed_official 85:e1a8e879a6a9 3 *
mbed_official 85:e1a8e879a6a9 4 * Licensed under the Apache License, Version 2.0 (the "License");
mbed_official 85:e1a8e879a6a9 5 * you may not use this file except in compliance with the License.
mbed_official 85:e1a8e879a6a9 6 * You may obtain a copy of the License at
mbed_official 85:e1a8e879a6a9 7 *
mbed_official 85:e1a8e879a6a9 8 * http://www.apache.org/licenses/LICENSE-2.0
mbed_official 85:e1a8e879a6a9 9 *
mbed_official 85:e1a8e879a6a9 10 * Unless required by applicable law or agreed to in writing, software
mbed_official 85:e1a8e879a6a9 11 * distributed under the License is distributed on an "AS IS" BASIS,
mbed_official 85:e1a8e879a6a9 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
mbed_official 85:e1a8e879a6a9 13 * See the License for the specific language governing permissions and
mbed_official 85:e1a8e879a6a9 14 * limitations under the License.
mbed_official 85:e1a8e879a6a9 15 */
mbed_official 227:7bd0639b8911 16 #include "mbed_assert.h"
mbed_official 85:e1a8e879a6a9 17 #include "i2c_api.h"
mbed_official 85:e1a8e879a6a9 18 #include "cmsis.h"
mbed_official 85:e1a8e879a6a9 19 #include "pinmap.h"
mbed_official 85:e1a8e879a6a9 20
mbed_official 85:e1a8e879a6a9 21 static const PinMap PinMap_I2C_SDA[] = {
mbed_official 85:e1a8e879a6a9 22 {p22, I2C_0, 1},
mbed_official 85:e1a8e879a6a9 23 {p13, I2C_1, 2},
mbed_official 300:55638feb26a4 24 {NC, NC, 0}
mbed_official 85:e1a8e879a6a9 25 };
mbed_official 85:e1a8e879a6a9 26
mbed_official 85:e1a8e879a6a9 27 static const PinMap PinMap_I2C_SCL[] = {
mbed_official 85:e1a8e879a6a9 28 {p20, I2C_0, 1},
mbed_official 85:e1a8e879a6a9 29 {p15, I2C_1, 2},
mbed_official 300:55638feb26a4 30 {NC, NC, 0}
mbed_official 85:e1a8e879a6a9 31 };
mbed_official 85:e1a8e879a6a9 32
mbed_official 300:55638feb26a4 33 void i2c_interface_enable(i2c_t *obj)
mbed_official 300:55638feb26a4 34 {
mbed_official 85:e1a8e879a6a9 35 obj->i2c->ENABLE = (TWI_ENABLE_ENABLE_Enabled << TWI_ENABLE_ENABLE_Pos);
mbed_official 85:e1a8e879a6a9 36 }
mbed_official 85:e1a8e879a6a9 37
mbed_official 300:55638feb26a4 38 void twi_master_init(i2c_t *obj, PinName sda, PinName scl, int frequency)
mbed_official 300:55638feb26a4 39 {
mbed_official 300:55638feb26a4 40 NRF_GPIO->PIN_CNF[scl] = ((GPIO_PIN_CNF_DIR_Input << GPIO_PIN_CNF_DIR_Pos) |
mbed_official 300:55638feb26a4 41 (GPIO_PIN_CNF_INPUT_Connect << GPIO_PIN_CNF_INPUT_Pos) |
mbed_official 300:55638feb26a4 42 (GPIO_PIN_CNF_PULL_Disabled << GPIO_PIN_CNF_PULL_Pos) |
mbed_official 300:55638feb26a4 43 (GPIO_PIN_CNF_DRIVE_S0D1 << GPIO_PIN_CNF_DRIVE_Pos) |
mbed_official 300:55638feb26a4 44 (GPIO_PIN_CNF_SENSE_Disabled << GPIO_PIN_CNF_SENSE_Pos));
mbed_official 85:e1a8e879a6a9 45
mbed_official 300:55638feb26a4 46 NRF_GPIO->PIN_CNF[sda] = ((GPIO_PIN_CNF_DIR_Input << GPIO_PIN_CNF_DIR_Pos) |
mbed_official 300:55638feb26a4 47 (GPIO_PIN_CNF_INPUT_Connect << GPIO_PIN_CNF_INPUT_Pos) |
mbed_official 300:55638feb26a4 48 (GPIO_PIN_CNF_PULL_Disabled << GPIO_PIN_CNF_PULL_Pos) |
mbed_official 300:55638feb26a4 49 (GPIO_PIN_CNF_DRIVE_S0D1 << GPIO_PIN_CNF_DRIVE_Pos) |
mbed_official 300:55638feb26a4 50 (GPIO_PIN_CNF_SENSE_Disabled << GPIO_PIN_CNF_SENSE_Pos));
mbed_official 85:e1a8e879a6a9 51
mbed_official 300:55638feb26a4 52 obj->i2c->PSELSCL = scl;
mbed_official 300:55638feb26a4 53 obj->i2c->PSELSDA = sda;
mbed_official 85:e1a8e879a6a9 54 // set default frequency at 100k
mbed_official 85:e1a8e879a6a9 55 i2c_frequency(obj, frequency);
mbed_official 85:e1a8e879a6a9 56 i2c_interface_enable(obj);
mbed_official 85:e1a8e879a6a9 57 }
mbed_official 300:55638feb26a4 58
mbed_official 300:55638feb26a4 59 void i2c_init(i2c_t *obj, PinName sda, PinName scl)
mbed_official 300:55638feb26a4 60 {
mbed_official 85:e1a8e879a6a9 61 // determine the SPI to use
mbed_official 85:e1a8e879a6a9 62 I2CName i2c_sda = (I2CName)pinmap_peripheral(sda, PinMap_I2C_SDA);
mbed_official 85:e1a8e879a6a9 63 I2CName i2c_scl = (I2CName)pinmap_peripheral(scl, PinMap_I2C_SCL);
mbed_official 300:55638feb26a4 64 I2CName i2c = (I2CName)pinmap_merge(i2c_sda, i2c_scl);
mbed_official 300:55638feb26a4 65 obj->i2c = (NRF_TWI_Type *)i2c;
mbed_official 300:55638feb26a4 66
mbed_official 227:7bd0639b8911 67 MBED_ASSERT((int)obj->i2c != NC);
mbed_official 85:e1a8e879a6a9 68
mbed_official 300:55638feb26a4 69 obj->scl = scl;
mbed_official 300:55638feb26a4 70 obj->sda = sda;
mbed_official 85:e1a8e879a6a9 71 obj->i2c->EVENTS_ERROR = 0;
mbed_official 227:7bd0639b8911 72 obj->i2c->ENABLE = TWI_ENABLE_ENABLE_Disabled << TWI_ENABLE_ENABLE_Pos;
mbed_official 227:7bd0639b8911 73 obj->i2c->POWER = 0;
mbed_official 300:55638feb26a4 74
mbed_official 300:55638feb26a4 75 for (int i = 0; i<100; i++) {
mbed_official 85:e1a8e879a6a9 76 }
mbed_official 300:55638feb26a4 77
mbed_official 300:55638feb26a4 78 obj->i2c->POWER = 1;
mbed_official 300:55638feb26a4 79 twi_master_init(obj, sda, scl, 100000);
mbed_official 85:e1a8e879a6a9 80 }
mbed_official 300:55638feb26a4 81
mbed_official 300:55638feb26a4 82 void i2c_reset(i2c_t *obj)
mbed_official 300:55638feb26a4 83 {
mbed_official 85:e1a8e879a6a9 84 obj->i2c->EVENTS_ERROR = 0;
mbed_official 227:7bd0639b8911 85 obj->i2c->ENABLE = TWI_ENABLE_ENABLE_Disabled << TWI_ENABLE_ENABLE_Pos;
mbed_official 227:7bd0639b8911 86 obj->i2c->POWER = 0;
mbed_official 300:55638feb26a4 87 for (int i = 0; i<100; i++) {
mbed_official 85:e1a8e879a6a9 88 }
mbed_official 300:55638feb26a4 89
mbed_official 300:55638feb26a4 90 obj->i2c->POWER = 1;
mbed_official 300:55638feb26a4 91 twi_master_init(obj, obj->sda, obj->scl, obj->freq);
mbed_official 85:e1a8e879a6a9 92 }
mbed_official 85:e1a8e879a6a9 93
mbed_official 300:55638feb26a4 94 int i2c_start(i2c_t *obj)
mbed_official 300:55638feb26a4 95 {
mbed_official 85:e1a8e879a6a9 96 int status = 0;
mbed_official 85:e1a8e879a6a9 97 i2c_reset(obj);
mbed_official 314:b682143dd337 98 obj->address_set = 0;
mbed_official 85:e1a8e879a6a9 99 return status;
mbed_official 85:e1a8e879a6a9 100 }
mbed_official 85:e1a8e879a6a9 101
mbed_official 300:55638feb26a4 102 int i2c_stop(i2c_t *obj)
mbed_official 300:55638feb26a4 103 {
mbed_official 85:e1a8e879a6a9 104 int timeOut = 100000;
mbed_official 85:e1a8e879a6a9 105 obj->i2c->EVENTS_STOPPED = 0;
mbed_official 85:e1a8e879a6a9 106 // write the stop bit
mbed_official 85:e1a8e879a6a9 107 obj->i2c->TASKS_STOP = 1;
mbed_official 300:55638feb26a4 108 while (!obj->i2c->EVENTS_STOPPED) {
mbed_official 85:e1a8e879a6a9 109 timeOut--;
mbed_official 300:55638feb26a4 110 if (timeOut<0) {
mbed_official 85:e1a8e879a6a9 111 return 1;
mbed_official 300:55638feb26a4 112 }
mbed_official 227:7bd0639b8911 113 }
mbed_official 314:b682143dd337 114 obj->address_set = 0;
mbed_official 85:e1a8e879a6a9 115 i2c_reset(obj);
mbed_official 85:e1a8e879a6a9 116 return 0;
mbed_official 85:e1a8e879a6a9 117 }
mbed_official 85:e1a8e879a6a9 118
mbed_official 300:55638feb26a4 119 int i2c_do_write(i2c_t *obj, int value)
mbed_official 300:55638feb26a4 120 {
mbed_official 85:e1a8e879a6a9 121 int timeOut = 100000;
mbed_official 85:e1a8e879a6a9 122 obj->i2c->TXD = value;
mbed_official 300:55638feb26a4 123 while (!obj->i2c->EVENTS_TXDSENT) {
mbed_official 85:e1a8e879a6a9 124 timeOut--;
mbed_official 300:55638feb26a4 125 if (timeOut<0) {
mbed_official 85:e1a8e879a6a9 126 return 1;
mbed_official 300:55638feb26a4 127 }
mbed_official 85:e1a8e879a6a9 128 }
mbed_official 227:7bd0639b8911 129 obj->i2c->EVENTS_TXDSENT = 0;
mbed_official 85:e1a8e879a6a9 130 return 0;
mbed_official 85:e1a8e879a6a9 131 }
mbed_official 85:e1a8e879a6a9 132
mbed_official 300:55638feb26a4 133 int i2c_do_read(i2c_t *obj, char *data, int last)
mbed_official 300:55638feb26a4 134 {
mbed_official 85:e1a8e879a6a9 135 int timeOut = 100000;
mbed_official 177:d57c40a064c8 136
mbed_official 300:55638feb26a4 137 if (last) {
mbed_official 314:b682143dd337 138 // To trigger stop task when a byte is received,
mbed_official 314:b682143dd337 139 // must be set before resume task.
mbed_official 314:b682143dd337 140 obj->i2c->SHORTS = 2;
mbed_official 177:d57c40a064c8 141 }
mbed_official 314:b682143dd337 142
mbed_official 314:b682143dd337 143 obj->i2c->TASKS_RESUME = 1;
mbed_official 314:b682143dd337 144
mbed_official 300:55638feb26a4 145 while (!obj->i2c->EVENTS_RXDREADY) {
mbed_official 85:e1a8e879a6a9 146 timeOut--;
mbed_official 300:55638feb26a4 147 if (timeOut<0) {
mbed_official 85:e1a8e879a6a9 148 return 1;
mbed_official 300:55638feb26a4 149 }
mbed_official 85:e1a8e879a6a9 150 }
mbed_official 300:55638feb26a4 151 obj->i2c->EVENTS_RXDREADY = 0;
mbed_official 85:e1a8e879a6a9 152 *data = obj->i2c->RXD;
mbed_official 300:55638feb26a4 153
mbed_official 85:e1a8e879a6a9 154 return 0;
mbed_official 85:e1a8e879a6a9 155 }
mbed_official 85:e1a8e879a6a9 156
mbed_official 300:55638feb26a4 157 void i2c_frequency(i2c_t *obj, int hz)
mbed_official 300:55638feb26a4 158 {
mbed_official 300:55638feb26a4 159 if (hz<250000) {
mbed_official 85:e1a8e879a6a9 160 obj->freq = 100000;
mbed_official 85:e1a8e879a6a9 161 obj->i2c->FREQUENCY = (TWI_FREQUENCY_FREQUENCY_K100 << TWI_FREQUENCY_FREQUENCY_Pos);
mbed_official 300:55638feb26a4 162 } else if (hz<400000) {
mbed_official 85:e1a8e879a6a9 163 obj->freq = 250000;
mbed_official 85:e1a8e879a6a9 164 obj->i2c->FREQUENCY = (TWI_FREQUENCY_FREQUENCY_K250 << TWI_FREQUENCY_FREQUENCY_Pos);
mbed_official 300:55638feb26a4 165 } else {
mbed_official 85:e1a8e879a6a9 166 obj->freq = 400000;
mbed_official 85:e1a8e879a6a9 167 obj->i2c->FREQUENCY = (TWI_FREQUENCY_FREQUENCY_K400 << TWI_FREQUENCY_FREQUENCY_Pos);
mbed_official 85:e1a8e879a6a9 168 }
mbed_official 85:e1a8e879a6a9 169 }
mbed_official 85:e1a8e879a6a9 170
mbed_official 300:55638feb26a4 171 int checkError(i2c_t *obj)
mbed_official 300:55638feb26a4 172 {
mbed_official 300:55638feb26a4 173 if (obj->i2c->EVENTS_ERROR == 1) {
mbed_official 300:55638feb26a4 174 if (obj->i2c->ERRORSRC & TWI_ERRORSRC_ANACK_Msk) {
mbed_official 300:55638feb26a4 175 obj->i2c->EVENTS_ERROR = 0;
mbed_official 300:55638feb26a4 176 obj->i2c->TASKS_STOP = 1;
mbed_official 85:e1a8e879a6a9 177 return I2C_ERROR_BUS_BUSY;
mbed_official 85:e1a8e879a6a9 178 }
mbed_official 300:55638feb26a4 179
mbed_official 300:55638feb26a4 180 obj->i2c->EVENTS_ERROR = 0;
mbed_official 300:55638feb26a4 181 obj->i2c->TASKS_STOP = 1;
mbed_official 227:7bd0639b8911 182 return I2C_ERROR_NO_SLAVE;
mbed_official 227:7bd0639b8911 183 }
mbed_official 85:e1a8e879a6a9 184 return 0;
mbed_official 85:e1a8e879a6a9 185 }
mbed_official 85:e1a8e879a6a9 186
mbed_official 300:55638feb26a4 187 int i2c_read(i2c_t *obj, int address, char *data, int length, int stop)
mbed_official 300:55638feb26a4 188 {
mbed_official 300:55638feb26a4 189 int status, count, errorResult;
mbed_official 300:55638feb26a4 190 obj->i2c->ADDRESS = (address >> 1);
mbed_official 314:b682143dd337 191 obj->i2c->SHORTS = 1; // to trigger suspend task when a byte is received
mbed_official 85:e1a8e879a6a9 192 obj->i2c->EVENTS_RXDREADY = 0;
mbed_official 85:e1a8e879a6a9 193 obj->i2c->TASKS_STARTRX = 1;
mbed_official 300:55638feb26a4 194
mbed_official 85:e1a8e879a6a9 195 // Read in all except last byte
mbed_official 85:e1a8e879a6a9 196 for (count = 0; count < (length - 1); count++) {
mbed_official 300:55638feb26a4 197 status = i2c_do_read(obj, &data[count], 0);
mbed_official 227:7bd0639b8911 198 if (status) {
mbed_official 85:e1a8e879a6a9 199 errorResult = checkError(obj);
mbed_official 85:e1a8e879a6a9 200 i2c_reset(obj);
mbed_official 300:55638feb26a4 201 if (errorResult<0) {
mbed_official 85:e1a8e879a6a9 202 return errorResult;
mbed_official 85:e1a8e879a6a9 203 }
mbed_official 85:e1a8e879a6a9 204 return count;
mbed_official 85:e1a8e879a6a9 205 }
mbed_official 85:e1a8e879a6a9 206 }
mbed_official 85:e1a8e879a6a9 207
mbed_official 85:e1a8e879a6a9 208 // read in last byte
mbed_official 300:55638feb26a4 209 status = i2c_do_read(obj, &data[length - 1], 1);
mbed_official 85:e1a8e879a6a9 210 if (status) {
mbed_official 85:e1a8e879a6a9 211 i2c_reset(obj);
mbed_official 85:e1a8e879a6a9 212 return length - 1;
mbed_official 85:e1a8e879a6a9 213 }
mbed_official 85:e1a8e879a6a9 214 // If not repeated start, send stop.
mbed_official 85:e1a8e879a6a9 215 if (stop) {
mbed_official 300:55638feb26a4 216 while (!obj->i2c->EVENTS_STOPPED) {
mbed_official 85:e1a8e879a6a9 217 }
mbed_official 85:e1a8e879a6a9 218 obj->i2c->EVENTS_STOPPED = 0;
mbed_official 227:7bd0639b8911 219 }
mbed_official 85:e1a8e879a6a9 220 return length;
mbed_official 85:e1a8e879a6a9 221 }
mbed_official 85:e1a8e879a6a9 222
mbed_official 300:55638feb26a4 223 int i2c_write(i2c_t *obj, int address, const char *data, int length, int stop)
mbed_official 300:55638feb26a4 224 {
mbed_official 85:e1a8e879a6a9 225 int status, errorResult;
mbed_official 300:55638feb26a4 226 obj->i2c->ADDRESS = (address >> 1);
mbed_official 85:e1a8e879a6a9 227 obj->i2c->SHORTS = 0;
mbed_official 227:7bd0639b8911 228 obj->i2c->TASKS_STARTTX = 1;
mbed_official 300:55638feb26a4 229
mbed_official 300:55638feb26a4 230 for (int i = 0; i<length; i++) {
mbed_official 85:e1a8e879a6a9 231 status = i2c_do_write(obj, data[i]);
mbed_official 300:55638feb26a4 232 if (status) {
mbed_official 85:e1a8e879a6a9 233 i2c_reset(obj);
mbed_official 85:e1a8e879a6a9 234 errorResult = checkError(obj);
mbed_official 300:55638feb26a4 235 if (errorResult<0) {
mbed_official 85:e1a8e879a6a9 236 return errorResult;
mbed_official 85:e1a8e879a6a9 237 }
mbed_official 85:e1a8e879a6a9 238 return i;
mbed_official 85:e1a8e879a6a9 239 }
mbed_official 85:e1a8e879a6a9 240 }
mbed_official 300:55638feb26a4 241
mbed_official 85:e1a8e879a6a9 242 // If not repeated start, send stop.
mbed_official 85:e1a8e879a6a9 243 if (stop) {
mbed_official 300:55638feb26a4 244 if (i2c_stop(obj)) {
mbed_official 85:e1a8e879a6a9 245 return I2C_ERROR_NO_SLAVE;
mbed_official 85:e1a8e879a6a9 246 }
mbed_official 85:e1a8e879a6a9 247 }
mbed_official 85:e1a8e879a6a9 248 return length;
mbed_official 85:e1a8e879a6a9 249 }
mbed_official 85:e1a8e879a6a9 250
mbed_official 300:55638feb26a4 251 int i2c_byte_read(i2c_t *obj, int last)
mbed_official 300:55638feb26a4 252 {
mbed_official 85:e1a8e879a6a9 253 char data;
mbed_official 85:e1a8e879a6a9 254 int status;
mbed_official 300:55638feb26a4 255
mbed_official 300:55638feb26a4 256 status = i2c_do_read(obj, &data, last);
mbed_official 85:e1a8e879a6a9 257 if (status) {
mbed_official 85:e1a8e879a6a9 258 i2c_reset(obj);
mbed_official 85:e1a8e879a6a9 259 }
mbed_official 85:e1a8e879a6a9 260 return data;
mbed_official 85:e1a8e879a6a9 261 }
mbed_official 85:e1a8e879a6a9 262
mbed_official 300:55638feb26a4 263 int i2c_byte_write(i2c_t *obj, int data)
mbed_official 300:55638feb26a4 264 {
mbed_official 85:e1a8e879a6a9 265 int status = 0;
mbed_official 314:b682143dd337 266 if (!obj->address_set) {
mbed_official 314:b682143dd337 267 obj->address_set = 1;
mbed_official 300:55638feb26a4 268 obj->i2c->ADDRESS = (data >> 1);
mbed_official 300:55638feb26a4 269
mbed_official 300:55638feb26a4 270 if (data & 1) {
mbed_official 85:e1a8e879a6a9 271 obj->i2c->EVENTS_RXDREADY = 0;
mbed_official 314:b682143dd337 272 obj->i2c->SHORTS = 1;
mbed_official 85:e1a8e879a6a9 273 obj->i2c->TASKS_STARTRX = 1;
mbed_official 300:55638feb26a4 274 } else {
mbed_official 314:b682143dd337 275 obj->i2c->SHORTS = 0;
mbed_official 300:55638feb26a4 276 obj->i2c->TASKS_STARTTX = 1;
mbed_official 85:e1a8e879a6a9 277 }
mbed_official 300:55638feb26a4 278 } else {
mbed_official 85:e1a8e879a6a9 279 status = i2c_do_write(obj, data);
mbed_official 300:55638feb26a4 280 if (status) {
mbed_official 85:e1a8e879a6a9 281 i2c_reset(obj);
mbed_official 85:e1a8e879a6a9 282 }
mbed_official 85:e1a8e879a6a9 283 }
mbed_official 300:55638feb26a4 284 return (1 - status);
mbed_official 85:e1a8e879a6a9 285 }