mbed library sources

Fork of mbed-src by mbed official

Committer:
mbed_official
Date:
Fri Aug 01 14:45:06 2014 +0100
Revision:
270:e2babe29baf8
Parent:
targets/hal/TARGET_NORDIC/TARGET_NRF51822/i2c_api.c@227:7bd0639b8911
Child:
300:55638feb26a4
Synchronized with git revision 988c22d5984ba5565d9e83305cc1eb6431a683ee

Full URL: https://github.com/mbedmicro/mbed/commit/988c22d5984ba5565d9e83305cc1eb6431a683ee/

Fixed L6235E link error for NRF51822 variants

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