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:
Wed Aug 27 08:45:06 2014 +0100
Revision:
300:55638feb26a4
Parent:
270:e2babe29baf8
Child:
314:b682143dd337
Synchronized with git revision 90467175c04ad81c20cdf7b2ddb86c54f5f3dcbb

Full URL: https://github.com/mbedmicro/mbed/commit/90467175c04ad81c20cdf7b2ddb86c54f5f3dcbb/

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 uint8_t addrSet = 0;
mbed_official 85:e1a8e879a6a9 34
mbed_official 300:55638feb26a4 35 void i2c_interface_enable(i2c_t *obj)
mbed_official 300:55638feb26a4 36 {
mbed_official 85:e1a8e879a6a9 37 obj->i2c->ENABLE = (TWI_ENABLE_ENABLE_Enabled << TWI_ENABLE_ENABLE_Pos);
mbed_official 85:e1a8e879a6a9 38 }
mbed_official 85:e1a8e879a6a9 39
mbed_official 300:55638feb26a4 40 void twi_master_init(i2c_t *obj, PinName sda, PinName scl, int frequency)
mbed_official 300:55638feb26a4 41 {
mbed_official 300:55638feb26a4 42 NRF_GPIO->PIN_CNF[scl] = ((GPIO_PIN_CNF_DIR_Input << GPIO_PIN_CNF_DIR_Pos) |
mbed_official 300:55638feb26a4 43 (GPIO_PIN_CNF_INPUT_Connect << GPIO_PIN_CNF_INPUT_Pos) |
mbed_official 300:55638feb26a4 44 (GPIO_PIN_CNF_PULL_Disabled << GPIO_PIN_CNF_PULL_Pos) |
mbed_official 300:55638feb26a4 45 (GPIO_PIN_CNF_DRIVE_S0D1 << GPIO_PIN_CNF_DRIVE_Pos) |
mbed_official 300:55638feb26a4 46 (GPIO_PIN_CNF_SENSE_Disabled << GPIO_PIN_CNF_SENSE_Pos));
mbed_official 85:e1a8e879a6a9 47
mbed_official 300:55638feb26a4 48 NRF_GPIO->PIN_CNF[sda] = ((GPIO_PIN_CNF_DIR_Input << GPIO_PIN_CNF_DIR_Pos) |
mbed_official 300:55638feb26a4 49 (GPIO_PIN_CNF_INPUT_Connect << GPIO_PIN_CNF_INPUT_Pos) |
mbed_official 300:55638feb26a4 50 (GPIO_PIN_CNF_PULL_Disabled << GPIO_PIN_CNF_PULL_Pos) |
mbed_official 300:55638feb26a4 51 (GPIO_PIN_CNF_DRIVE_S0D1 << GPIO_PIN_CNF_DRIVE_Pos) |
mbed_official 300:55638feb26a4 52 (GPIO_PIN_CNF_SENSE_Disabled << GPIO_PIN_CNF_SENSE_Pos));
mbed_official 85:e1a8e879a6a9 53
mbed_official 300:55638feb26a4 54 obj->i2c->PSELSCL = scl;
mbed_official 300:55638feb26a4 55 obj->i2c->PSELSDA = sda;
mbed_official 85:e1a8e879a6a9 56 // set default frequency at 100k
mbed_official 85:e1a8e879a6a9 57 i2c_frequency(obj, frequency);
mbed_official 85:e1a8e879a6a9 58 i2c_interface_enable(obj);
mbed_official 85:e1a8e879a6a9 59 }
mbed_official 300:55638feb26a4 60
mbed_official 300:55638feb26a4 61 void i2c_init(i2c_t *obj, PinName sda, PinName scl)
mbed_official 300:55638feb26a4 62 {
mbed_official 85:e1a8e879a6a9 63 // determine the SPI to use
mbed_official 85:e1a8e879a6a9 64 I2CName i2c_sda = (I2CName)pinmap_peripheral(sda, PinMap_I2C_SDA);
mbed_official 85:e1a8e879a6a9 65 I2CName i2c_scl = (I2CName)pinmap_peripheral(scl, PinMap_I2C_SCL);
mbed_official 300:55638feb26a4 66 I2CName i2c = (I2CName)pinmap_merge(i2c_sda, i2c_scl);
mbed_official 300:55638feb26a4 67 obj->i2c = (NRF_TWI_Type *)i2c;
mbed_official 300:55638feb26a4 68
mbed_official 227:7bd0639b8911 69 MBED_ASSERT((int)obj->i2c != NC);
mbed_official 85:e1a8e879a6a9 70
mbed_official 300:55638feb26a4 71 obj->scl = scl;
mbed_official 300:55638feb26a4 72 obj->sda = sda;
mbed_official 85:e1a8e879a6a9 73 obj->i2c->EVENTS_ERROR = 0;
mbed_official 227:7bd0639b8911 74 obj->i2c->ENABLE = TWI_ENABLE_ENABLE_Disabled << TWI_ENABLE_ENABLE_Pos;
mbed_official 227:7bd0639b8911 75 obj->i2c->POWER = 0;
mbed_official 300:55638feb26a4 76
mbed_official 300:55638feb26a4 77 for (int i = 0; i<100; i++) {
mbed_official 85:e1a8e879a6a9 78 }
mbed_official 300:55638feb26a4 79
mbed_official 300:55638feb26a4 80 obj->i2c->POWER = 1;
mbed_official 300:55638feb26a4 81 twi_master_init(obj, sda, scl, 100000);
mbed_official 85:e1a8e879a6a9 82 }
mbed_official 300:55638feb26a4 83
mbed_official 300:55638feb26a4 84 void i2c_reset(i2c_t *obj)
mbed_official 300:55638feb26a4 85 {
mbed_official 85:e1a8e879a6a9 86 obj->i2c->EVENTS_ERROR = 0;
mbed_official 227:7bd0639b8911 87 obj->i2c->ENABLE = TWI_ENABLE_ENABLE_Disabled << TWI_ENABLE_ENABLE_Pos;
mbed_official 227:7bd0639b8911 88 obj->i2c->POWER = 0;
mbed_official 300:55638feb26a4 89 for (int i = 0; i<100; i++) {
mbed_official 85:e1a8e879a6a9 90 }
mbed_official 300:55638feb26a4 91
mbed_official 300:55638feb26a4 92 obj->i2c->POWER = 1;
mbed_official 300:55638feb26a4 93 twi_master_init(obj, obj->sda, obj->scl, obj->freq);
mbed_official 85:e1a8e879a6a9 94 }
mbed_official 85:e1a8e879a6a9 95
mbed_official 300:55638feb26a4 96 int i2c_start(i2c_t *obj)
mbed_official 300:55638feb26a4 97 {
mbed_official 85:e1a8e879a6a9 98 int status = 0;
mbed_official 85:e1a8e879a6a9 99 i2c_reset(obj);
mbed_official 300:55638feb26a4 100 addrSet = 0;
mbed_official 85:e1a8e879a6a9 101 return status;
mbed_official 85:e1a8e879a6a9 102 }
mbed_official 85:e1a8e879a6a9 103
mbed_official 300:55638feb26a4 104 int i2c_stop(i2c_t *obj)
mbed_official 300:55638feb26a4 105 {
mbed_official 85:e1a8e879a6a9 106 int timeOut = 100000;
mbed_official 85:e1a8e879a6a9 107 obj->i2c->EVENTS_STOPPED = 0;
mbed_official 85:e1a8e879a6a9 108 // write the stop bit
mbed_official 85:e1a8e879a6a9 109 obj->i2c->TASKS_STOP = 1;
mbed_official 300:55638feb26a4 110 while (!obj->i2c->EVENTS_STOPPED) {
mbed_official 85:e1a8e879a6a9 111 timeOut--;
mbed_official 300:55638feb26a4 112 if (timeOut<0) {
mbed_official 85:e1a8e879a6a9 113 return 1;
mbed_official 300:55638feb26a4 114 }
mbed_official 227:7bd0639b8911 115 }
mbed_official 85:e1a8e879a6a9 116 addrSet = 0;
mbed_official 85:e1a8e879a6a9 117 i2c_reset(obj);
mbed_official 85:e1a8e879a6a9 118 return 0;
mbed_official 85:e1a8e879a6a9 119 }
mbed_official 85:e1a8e879a6a9 120
mbed_official 300:55638feb26a4 121 int i2c_do_write(i2c_t *obj, int value)
mbed_official 300:55638feb26a4 122 {
mbed_official 85:e1a8e879a6a9 123 int timeOut = 100000;
mbed_official 85:e1a8e879a6a9 124 obj->i2c->TXD = value;
mbed_official 300:55638feb26a4 125 while (!obj->i2c->EVENTS_TXDSENT) {
mbed_official 85:e1a8e879a6a9 126 timeOut--;
mbed_official 300:55638feb26a4 127 if (timeOut<0) {
mbed_official 85:e1a8e879a6a9 128 return 1;
mbed_official 300:55638feb26a4 129 }
mbed_official 85:e1a8e879a6a9 130 }
mbed_official 227:7bd0639b8911 131 obj->i2c->EVENTS_TXDSENT = 0;
mbed_official 85:e1a8e879a6a9 132 return 0;
mbed_official 85:e1a8e879a6a9 133 }
mbed_official 85:e1a8e879a6a9 134
mbed_official 300:55638feb26a4 135 int i2c_do_read(i2c_t *obj, char *data, int last)
mbed_official 300:55638feb26a4 136 {
mbed_official 85:e1a8e879a6a9 137 int timeOut = 100000;
mbed_official 177:d57c40a064c8 138
mbed_official 300:55638feb26a4 139 if (last) {
mbed_official 177:d57c40a064c8 140 obj->i2c->TASKS_STOP = 1;
mbed_official 177:d57c40a064c8 141 }
mbed_official 300:55638feb26a4 142 while (!obj->i2c->EVENTS_RXDREADY) {
mbed_official 85:e1a8e879a6a9 143 timeOut--;
mbed_official 300:55638feb26a4 144 if (timeOut<0) {
mbed_official 85:e1a8e879a6a9 145 return 1;
mbed_official 300:55638feb26a4 146 }
mbed_official 85:e1a8e879a6a9 147 }
mbed_official 300:55638feb26a4 148 obj->i2c->EVENTS_RXDREADY = 0;
mbed_official 300:55638feb26a4 149
mbed_official 85:e1a8e879a6a9 150 *data = obj->i2c->RXD;
mbed_official 300:55638feb26a4 151
mbed_official 300:55638feb26a4 152 for (int i = 0; i<320; i++) {
mbed_official 85:e1a8e879a6a9 153 }
mbed_official 300:55638feb26a4 154
mbed_official 85:e1a8e879a6a9 155 obj->i2c->TASKS_RESUME = 1;
mbed_official 300:55638feb26a4 156
mbed_official 85:e1a8e879a6a9 157 return 0;
mbed_official 85:e1a8e879a6a9 158 }
mbed_official 85:e1a8e879a6a9 159
mbed_official 300:55638feb26a4 160 void i2c_frequency(i2c_t *obj, int hz)
mbed_official 300:55638feb26a4 161 {
mbed_official 300:55638feb26a4 162 if (hz<250000) {
mbed_official 85:e1a8e879a6a9 163 obj->freq = 100000;
mbed_official 85:e1a8e879a6a9 164 obj->i2c->FREQUENCY = (TWI_FREQUENCY_FREQUENCY_K100 << TWI_FREQUENCY_FREQUENCY_Pos);
mbed_official 300:55638feb26a4 165 } else if (hz<400000) {
mbed_official 85:e1a8e879a6a9 166 obj->freq = 250000;
mbed_official 85:e1a8e879a6a9 167 obj->i2c->FREQUENCY = (TWI_FREQUENCY_FREQUENCY_K250 << TWI_FREQUENCY_FREQUENCY_Pos);
mbed_official 300:55638feb26a4 168 } else {
mbed_official 85:e1a8e879a6a9 169 obj->freq = 400000;
mbed_official 85:e1a8e879a6a9 170 obj->i2c->FREQUENCY = (TWI_FREQUENCY_FREQUENCY_K400 << TWI_FREQUENCY_FREQUENCY_Pos);
mbed_official 85:e1a8e879a6a9 171 }
mbed_official 85:e1a8e879a6a9 172 }
mbed_official 85:e1a8e879a6a9 173
mbed_official 300:55638feb26a4 174 int checkError(i2c_t *obj)
mbed_official 300:55638feb26a4 175 {
mbed_official 300:55638feb26a4 176 if (obj->i2c->EVENTS_ERROR == 1) {
mbed_official 300:55638feb26a4 177 if (obj->i2c->ERRORSRC & TWI_ERRORSRC_ANACK_Msk) {
mbed_official 300:55638feb26a4 178 obj->i2c->EVENTS_ERROR = 0;
mbed_official 300:55638feb26a4 179 obj->i2c->TASKS_STOP = 1;
mbed_official 85:e1a8e879a6a9 180 return I2C_ERROR_BUS_BUSY;
mbed_official 85:e1a8e879a6a9 181 }
mbed_official 300:55638feb26a4 182
mbed_official 300:55638feb26a4 183 obj->i2c->EVENTS_ERROR = 0;
mbed_official 300:55638feb26a4 184 obj->i2c->TASKS_STOP = 1;
mbed_official 227:7bd0639b8911 185 return I2C_ERROR_NO_SLAVE;
mbed_official 227:7bd0639b8911 186 }
mbed_official 85:e1a8e879a6a9 187 return 0;
mbed_official 85:e1a8e879a6a9 188 }
mbed_official 85:e1a8e879a6a9 189
mbed_official 300:55638feb26a4 190 int i2c_read(i2c_t *obj, int address, char *data, int length, int stop)
mbed_official 300:55638feb26a4 191 {
mbed_official 300:55638feb26a4 192 int status, count, errorResult;
mbed_official 300:55638feb26a4 193 obj->i2c->ADDRESS = (address >> 1);
mbed_official 85:e1a8e879a6a9 194 obj->i2c->SHORTS = 0;
mbed_official 85:e1a8e879a6a9 195 obj->i2c->EVENTS_RXDREADY = 0;
mbed_official 85:e1a8e879a6a9 196 obj->i2c->TASKS_STARTRX = 1;
mbed_official 300:55638feb26a4 197
mbed_official 85:e1a8e879a6a9 198 // Read in all except last byte
mbed_official 85:e1a8e879a6a9 199 for (count = 0; count < (length - 1); count++) {
mbed_official 300:55638feb26a4 200 status = i2c_do_read(obj, &data[count], 0);
mbed_official 227:7bd0639b8911 201 if (status) {
mbed_official 85:e1a8e879a6a9 202 errorResult = checkError(obj);
mbed_official 85:e1a8e879a6a9 203 i2c_reset(obj);
mbed_official 300:55638feb26a4 204 if (errorResult<0) {
mbed_official 85:e1a8e879a6a9 205 return errorResult;
mbed_official 85:e1a8e879a6a9 206 }
mbed_official 85:e1a8e879a6a9 207 return count;
mbed_official 85:e1a8e879a6a9 208 }
mbed_official 85:e1a8e879a6a9 209 }
mbed_official 85:e1a8e879a6a9 210
mbed_official 85:e1a8e879a6a9 211 // read in last byte
mbed_official 300:55638feb26a4 212 status = i2c_do_read(obj, &data[length - 1], 1);
mbed_official 85:e1a8e879a6a9 213 if (status) {
mbed_official 85:e1a8e879a6a9 214 i2c_reset(obj);
mbed_official 85:e1a8e879a6a9 215 return length - 1;
mbed_official 85:e1a8e879a6a9 216 }
mbed_official 85:e1a8e879a6a9 217 // If not repeated start, send stop.
mbed_official 85:e1a8e879a6a9 218 if (stop) {
mbed_official 300:55638feb26a4 219 while (!obj->i2c->EVENTS_STOPPED) {
mbed_official 85:e1a8e879a6a9 220 }
mbed_official 85:e1a8e879a6a9 221 obj->i2c->EVENTS_STOPPED = 0;
mbed_official 227:7bd0639b8911 222 }
mbed_official 85:e1a8e879a6a9 223 return length;
mbed_official 85:e1a8e879a6a9 224 }
mbed_official 85:e1a8e879a6a9 225
mbed_official 300:55638feb26a4 226 int i2c_write(i2c_t *obj, int address, const char *data, int length, int stop)
mbed_official 300:55638feb26a4 227 {
mbed_official 85:e1a8e879a6a9 228 int status, errorResult;
mbed_official 300:55638feb26a4 229 obj->i2c->ADDRESS = (address >> 1);
mbed_official 85:e1a8e879a6a9 230 obj->i2c->SHORTS = 0;
mbed_official 227:7bd0639b8911 231 obj->i2c->TASKS_STARTTX = 1;
mbed_official 300:55638feb26a4 232
mbed_official 300:55638feb26a4 233 for (int i = 0; i<length; i++) {
mbed_official 85:e1a8e879a6a9 234 status = i2c_do_write(obj, data[i]);
mbed_official 300:55638feb26a4 235 if (status) {
mbed_official 85:e1a8e879a6a9 236 i2c_reset(obj);
mbed_official 85:e1a8e879a6a9 237 errorResult = checkError(obj);
mbed_official 300:55638feb26a4 238 if (errorResult<0) {
mbed_official 85:e1a8e879a6a9 239 return errorResult;
mbed_official 85:e1a8e879a6a9 240 }
mbed_official 85:e1a8e879a6a9 241 return i;
mbed_official 85:e1a8e879a6a9 242 }
mbed_official 85:e1a8e879a6a9 243 }
mbed_official 300:55638feb26a4 244
mbed_official 85:e1a8e879a6a9 245 // If not repeated start, send stop.
mbed_official 85:e1a8e879a6a9 246 if (stop) {
mbed_official 300:55638feb26a4 247 if (i2c_stop(obj)) {
mbed_official 85:e1a8e879a6a9 248 return I2C_ERROR_NO_SLAVE;
mbed_official 85:e1a8e879a6a9 249 }
mbed_official 85:e1a8e879a6a9 250 }
mbed_official 85:e1a8e879a6a9 251 return length;
mbed_official 85:e1a8e879a6a9 252 }
mbed_official 85:e1a8e879a6a9 253
mbed_official 300:55638feb26a4 254 int i2c_byte_read(i2c_t *obj, int last)
mbed_official 300:55638feb26a4 255 {
mbed_official 85:e1a8e879a6a9 256 char data;
mbed_official 85:e1a8e879a6a9 257 int status;
mbed_official 300:55638feb26a4 258
mbed_official 300:55638feb26a4 259 status = i2c_do_read(obj, &data, last);
mbed_official 85:e1a8e879a6a9 260 if (status) {
mbed_official 85:e1a8e879a6a9 261 i2c_reset(obj);
mbed_official 85:e1a8e879a6a9 262 }
mbed_official 85:e1a8e879a6a9 263 return data;
mbed_official 85:e1a8e879a6a9 264 }
mbed_official 85:e1a8e879a6a9 265
mbed_official 300:55638feb26a4 266 int i2c_byte_write(i2c_t *obj, int data)
mbed_official 300:55638feb26a4 267 {
mbed_official 85:e1a8e879a6a9 268 int status = 0;
mbed_official 300:55638feb26a4 269 if (!addrSet) {
mbed_official 300:55638feb26a4 270 addrSet = 1;
mbed_official 300:55638feb26a4 271 obj->i2c->ADDRESS = (data >> 1);
mbed_official 300:55638feb26a4 272
mbed_official 300:55638feb26a4 273 if (data & 1) {
mbed_official 85:e1a8e879a6a9 274 obj->i2c->EVENTS_RXDREADY = 0;
mbed_official 85:e1a8e879a6a9 275 obj->i2c->TASKS_STARTRX = 1;
mbed_official 300:55638feb26a4 276 } else {
mbed_official 300:55638feb26a4 277 obj->i2c->TASKS_STARTTX = 1;
mbed_official 85:e1a8e879a6a9 278 }
mbed_official 300:55638feb26a4 279 } else {
mbed_official 85:e1a8e879a6a9 280 status = i2c_do_write(obj, data);
mbed_official 300:55638feb26a4 281 if (status) {
mbed_official 85:e1a8e879a6a9 282 i2c_reset(obj);
mbed_official 85:e1a8e879a6a9 283 }
mbed_official 85:e1a8e879a6a9 284 }
mbed_official 300:55638feb26a4 285 return (1 - status);
mbed_official 85:e1a8e879a6a9 286 }