Mbed SDK for XRange SX1272 LoRa module

Dependents:   XRangePingPong XRange-LoRaWAN-lmic-app lora-transceiver

SX1272 LoRa RF module

https://www.netblocks.eu/xrange-sx1272-lora-datasheet/

Committer:
netblocks
Date:
Thu Jan 07 13:01:25 2016 +0000
Revision:
339:ac6f3fd999f3
Parent:
336:1e18a06a987b
HSE_VALUE set for XTAL 16Mhz

Who changed what in which revision?

UserRevisionLine numberNew contents of line
dudmuck 336:1e18a06a987b 1 /* mbed Microcontroller Library
dudmuck 336:1e18a06a987b 2 *******************************************************************************
dudmuck 336:1e18a06a987b 3 * Copyright (c) 2014, STMicroelectronics
dudmuck 336:1e18a06a987b 4 * All rights reserved.
dudmuck 336:1e18a06a987b 5 *
dudmuck 336:1e18a06a987b 6 * Redistribution and use in source and binary forms, with or without
dudmuck 336:1e18a06a987b 7 * modification, are permitted provided that the following conditions are met:
dudmuck 336:1e18a06a987b 8 *
dudmuck 336:1e18a06a987b 9 * 1. Redistributions of source code must retain the above copyright notice,
dudmuck 336:1e18a06a987b 10 * this list of conditions and the following disclaimer.
dudmuck 336:1e18a06a987b 11 * 2. Redistributions in binary form must reproduce the above copyright notice,
dudmuck 336:1e18a06a987b 12 * this list of conditions and the following disclaimer in the documentation
dudmuck 336:1e18a06a987b 13 * and/or other materials provided with the distribution.
dudmuck 336:1e18a06a987b 14 * 3. Neither the name of STMicroelectronics nor the names of its contributors
dudmuck 336:1e18a06a987b 15 * may be used to endorse or promote products derived from this software
dudmuck 336:1e18a06a987b 16 * without specific prior written permission.
dudmuck 336:1e18a06a987b 17 *
dudmuck 336:1e18a06a987b 18 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
dudmuck 336:1e18a06a987b 19 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
dudmuck 336:1e18a06a987b 20 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
dudmuck 336:1e18a06a987b 21 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
dudmuck 336:1e18a06a987b 22 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
dudmuck 336:1e18a06a987b 23 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
dudmuck 336:1e18a06a987b 24 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
dudmuck 336:1e18a06a987b 25 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
dudmuck 336:1e18a06a987b 26 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
dudmuck 336:1e18a06a987b 27 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
dudmuck 336:1e18a06a987b 28 *******************************************************************************
dudmuck 336:1e18a06a987b 29 */
dudmuck 336:1e18a06a987b 30 #include "mbed_assert.h"
dudmuck 336:1e18a06a987b 31 #include "i2c_api.h"
dudmuck 336:1e18a06a987b 32
dudmuck 336:1e18a06a987b 33 #if DEVICE_I2C
dudmuck 336:1e18a06a987b 34
dudmuck 336:1e18a06a987b 35 #include "cmsis.h"
dudmuck 336:1e18a06a987b 36 #include "pinmap.h"
dudmuck 336:1e18a06a987b 37 #include "PeripheralPins.h"
dudmuck 336:1e18a06a987b 38
dudmuck 336:1e18a06a987b 39 /* Timeout values for flags and events waiting loops. These timeouts are
dudmuck 336:1e18a06a987b 40 not based on accurate values, they just guarantee that the application will
dudmuck 336:1e18a06a987b 41 not remain stuck if the I2C communication is corrupted. */
dudmuck 336:1e18a06a987b 42 #define FLAG_TIMEOUT ((int)0x1000)
dudmuck 336:1e18a06a987b 43 #define LONG_TIMEOUT ((int)0x8000)
dudmuck 336:1e18a06a987b 44
dudmuck 336:1e18a06a987b 45 I2C_HandleTypeDef I2cHandle;
dudmuck 336:1e18a06a987b 46
dudmuck 336:1e18a06a987b 47 int i2c1_inited = 0;
dudmuck 336:1e18a06a987b 48 int i2c2_inited = 0;
dudmuck 336:1e18a06a987b 49
dudmuck 336:1e18a06a987b 50 void i2c_init(i2c_t *obj, PinName sda, PinName scl)
dudmuck 336:1e18a06a987b 51 {
dudmuck 336:1e18a06a987b 52 // Determine the I2C to use
dudmuck 336:1e18a06a987b 53 I2CName i2c_sda = (I2CName)pinmap_peripheral(sda, PinMap_I2C_SDA);
dudmuck 336:1e18a06a987b 54 I2CName i2c_scl = (I2CName)pinmap_peripheral(scl, PinMap_I2C_SCL);
dudmuck 336:1e18a06a987b 55
dudmuck 336:1e18a06a987b 56 obj->i2c = (I2CName)pinmap_merge(i2c_sda, i2c_scl);
dudmuck 336:1e18a06a987b 57 MBED_ASSERT(obj->i2c != (I2CName)NC);
dudmuck 336:1e18a06a987b 58
dudmuck 336:1e18a06a987b 59 // Enable I2C1 clock and pinout if not done
dudmuck 336:1e18a06a987b 60 if ((obj->i2c == I2C_1) && !i2c1_inited) {
dudmuck 336:1e18a06a987b 61 i2c1_inited = 1;
dudmuck 336:1e18a06a987b 62 __I2C1_CLK_ENABLE();
dudmuck 336:1e18a06a987b 63 // Configure I2C pins
dudmuck 336:1e18a06a987b 64 pinmap_pinout(sda, PinMap_I2C_SDA);
dudmuck 336:1e18a06a987b 65 pinmap_pinout(scl, PinMap_I2C_SCL);
dudmuck 336:1e18a06a987b 66 pin_mode(sda, OpenDrain);
dudmuck 336:1e18a06a987b 67 pin_mode(scl, OpenDrain);
dudmuck 336:1e18a06a987b 68 }
dudmuck 336:1e18a06a987b 69 // Enable I2C2 clock and pinout if not done
dudmuck 336:1e18a06a987b 70 if ((obj->i2c == I2C_2) && !i2c2_inited) {
dudmuck 336:1e18a06a987b 71 i2c2_inited = 1;
dudmuck 336:1e18a06a987b 72 __I2C2_CLK_ENABLE();
dudmuck 336:1e18a06a987b 73 // Configure I2C pins
dudmuck 336:1e18a06a987b 74 pinmap_pinout(sda, PinMap_I2C_SDA);
dudmuck 336:1e18a06a987b 75 pinmap_pinout(scl, PinMap_I2C_SCL);
dudmuck 336:1e18a06a987b 76 pin_mode(sda, OpenDrain);
dudmuck 336:1e18a06a987b 77 pin_mode(scl, OpenDrain);
dudmuck 336:1e18a06a987b 78 }
dudmuck 336:1e18a06a987b 79
dudmuck 336:1e18a06a987b 80 // Reset to clear pending flags if any
dudmuck 336:1e18a06a987b 81 i2c_reset(obj);
dudmuck 336:1e18a06a987b 82
dudmuck 336:1e18a06a987b 83 // I2C configuration
dudmuck 336:1e18a06a987b 84 i2c_frequency(obj, 100000); // 100 kHz per default
dudmuck 336:1e18a06a987b 85
dudmuck 336:1e18a06a987b 86 // I2C master by default
dudmuck 336:1e18a06a987b 87 obj->slave = 0;
dudmuck 336:1e18a06a987b 88 }
dudmuck 336:1e18a06a987b 89
dudmuck 336:1e18a06a987b 90 void i2c_frequency(i2c_t *obj, int hz)
dudmuck 336:1e18a06a987b 91 {
dudmuck 336:1e18a06a987b 92 MBED_ASSERT((hz != 0) && (hz <= 400000));
dudmuck 336:1e18a06a987b 93 I2cHandle.Instance = (I2C_TypeDef *)(obj->i2c);
dudmuck 336:1e18a06a987b 94 int timeout;
dudmuck 336:1e18a06a987b 95
dudmuck 336:1e18a06a987b 96 // wait before init
dudmuck 336:1e18a06a987b 97 timeout = LONG_TIMEOUT;
dudmuck 336:1e18a06a987b 98 while ((__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_BUSY)) && (timeout-- != 0));
dudmuck 336:1e18a06a987b 99
dudmuck 336:1e18a06a987b 100 // I2C configuration
dudmuck 336:1e18a06a987b 101 I2cHandle.Init.AddressingMode = I2C_ADDRESSINGMODE_7BIT;
dudmuck 336:1e18a06a987b 102 I2cHandle.Init.ClockSpeed = hz;
dudmuck 336:1e18a06a987b 103 I2cHandle.Init.DualAddressMode = I2C_DUALADDRESS_DISABLED;
dudmuck 336:1e18a06a987b 104 I2cHandle.Init.DutyCycle = I2C_DUTYCYCLE_2;
dudmuck 336:1e18a06a987b 105 I2cHandle.Init.GeneralCallMode = I2C_GENERALCALL_DISABLED;
dudmuck 336:1e18a06a987b 106 I2cHandle.Init.NoStretchMode = I2C_NOSTRETCH_DISABLED;
dudmuck 336:1e18a06a987b 107 I2cHandle.Init.OwnAddress1 = 0;
dudmuck 336:1e18a06a987b 108 I2cHandle.Init.OwnAddress2 = 0;
dudmuck 336:1e18a06a987b 109 HAL_I2C_Init(&I2cHandle);
dudmuck 336:1e18a06a987b 110 if (obj->slave) {
dudmuck 336:1e18a06a987b 111 /* Enable Address Acknowledge */
dudmuck 336:1e18a06a987b 112 I2cHandle.Instance->CR1 |= I2C_CR1_ACK;
dudmuck 336:1e18a06a987b 113 }
dudmuck 336:1e18a06a987b 114
dudmuck 336:1e18a06a987b 115 }
dudmuck 336:1e18a06a987b 116
dudmuck 336:1e18a06a987b 117 inline int i2c_start(i2c_t *obj)
dudmuck 336:1e18a06a987b 118 {
dudmuck 336:1e18a06a987b 119 I2C_TypeDef *i2c = (I2C_TypeDef *)(obj->i2c);
dudmuck 336:1e18a06a987b 120 int timeout;
dudmuck 336:1e18a06a987b 121
dudmuck 336:1e18a06a987b 122 I2cHandle.Instance = (I2C_TypeDef *)(obj->i2c);
dudmuck 336:1e18a06a987b 123
dudmuck 336:1e18a06a987b 124 // Clear Acknowledge failure flag
dudmuck 336:1e18a06a987b 125 __HAL_I2C_CLEAR_FLAG(&I2cHandle, I2C_FLAG_AF);
dudmuck 336:1e18a06a987b 126
dudmuck 336:1e18a06a987b 127 // Generate the START condition
dudmuck 336:1e18a06a987b 128 i2c->CR1 |= I2C_CR1_START;
dudmuck 336:1e18a06a987b 129
dudmuck 336:1e18a06a987b 130 // Wait the START condition has been correctly sent
dudmuck 336:1e18a06a987b 131 timeout = FLAG_TIMEOUT;
dudmuck 336:1e18a06a987b 132 while (__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_SB) == RESET) {
dudmuck 336:1e18a06a987b 133 if ((timeout--) == 0) {
dudmuck 336:1e18a06a987b 134 return 1;
dudmuck 336:1e18a06a987b 135 }
dudmuck 336:1e18a06a987b 136 }
dudmuck 336:1e18a06a987b 137
dudmuck 336:1e18a06a987b 138 return 0;
dudmuck 336:1e18a06a987b 139 }
dudmuck 336:1e18a06a987b 140
dudmuck 336:1e18a06a987b 141 inline int i2c_stop(i2c_t *obj)
dudmuck 336:1e18a06a987b 142 {
dudmuck 336:1e18a06a987b 143 I2C_TypeDef *i2c = (I2C_TypeDef *)(obj->i2c);
dudmuck 336:1e18a06a987b 144
dudmuck 336:1e18a06a987b 145 // Generate the STOP condition
dudmuck 336:1e18a06a987b 146 i2c->CR1 |= I2C_CR1_STOP;
dudmuck 336:1e18a06a987b 147
dudmuck 336:1e18a06a987b 148 return 0;
dudmuck 336:1e18a06a987b 149 }
dudmuck 336:1e18a06a987b 150
dudmuck 336:1e18a06a987b 151 int i2c_read(i2c_t *obj, int address, char *data, int length, int stop)
dudmuck 336:1e18a06a987b 152 {
dudmuck 336:1e18a06a987b 153 I2C_TypeDef *i2c = (I2C_TypeDef *)(obj->i2c);
dudmuck 336:1e18a06a987b 154 I2cHandle.Instance = (I2C_TypeDef *)(obj->i2c);
dudmuck 336:1e18a06a987b 155 int timeout;
dudmuck 336:1e18a06a987b 156 int count;
dudmuck 336:1e18a06a987b 157 int value;
dudmuck 336:1e18a06a987b 158
dudmuck 336:1e18a06a987b 159 i2c_start(obj);
dudmuck 336:1e18a06a987b 160
dudmuck 336:1e18a06a987b 161 // Wait until SB flag is set
dudmuck 336:1e18a06a987b 162 timeout = FLAG_TIMEOUT;
dudmuck 336:1e18a06a987b 163 while (__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_SB) == RESET) {
dudmuck 336:1e18a06a987b 164 timeout--;
dudmuck 336:1e18a06a987b 165 if (timeout == 0) {
dudmuck 336:1e18a06a987b 166 return -1;
dudmuck 336:1e18a06a987b 167 }
dudmuck 336:1e18a06a987b 168 }
dudmuck 336:1e18a06a987b 169
dudmuck 336:1e18a06a987b 170 i2c->DR = I2C_7BIT_ADD_READ(address);
dudmuck 336:1e18a06a987b 171
dudmuck 336:1e18a06a987b 172
dudmuck 336:1e18a06a987b 173 // Wait address is acknowledged
dudmuck 336:1e18a06a987b 174 timeout = FLAG_TIMEOUT;
dudmuck 336:1e18a06a987b 175 while (__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_ADDR) == RESET) {
dudmuck 336:1e18a06a987b 176 timeout--;
dudmuck 336:1e18a06a987b 177 if (timeout == 0) {
dudmuck 336:1e18a06a987b 178 return -1;
dudmuck 336:1e18a06a987b 179 }
dudmuck 336:1e18a06a987b 180 }
dudmuck 336:1e18a06a987b 181 __HAL_I2C_CLEAR_ADDRFLAG(&I2cHandle);
dudmuck 336:1e18a06a987b 182
dudmuck 336:1e18a06a987b 183 // Read all bytes except last one
dudmuck 336:1e18a06a987b 184 for (count = 0; count < (length - 1); count++) {
dudmuck 336:1e18a06a987b 185 value = i2c_byte_read(obj, 0);
dudmuck 336:1e18a06a987b 186 data[count] = (char)value;
dudmuck 336:1e18a06a987b 187 }
dudmuck 336:1e18a06a987b 188
dudmuck 336:1e18a06a987b 189 // If not repeated start, send stop.
dudmuck 336:1e18a06a987b 190 // Warning: must be done BEFORE the data is read.
dudmuck 336:1e18a06a987b 191 if (stop) {
dudmuck 336:1e18a06a987b 192 i2c_stop(obj);
dudmuck 336:1e18a06a987b 193 }
dudmuck 336:1e18a06a987b 194
dudmuck 336:1e18a06a987b 195 // Read the last byte
dudmuck 336:1e18a06a987b 196 value = i2c_byte_read(obj, 1);
dudmuck 336:1e18a06a987b 197 data[count] = (char)value;
dudmuck 336:1e18a06a987b 198
dudmuck 336:1e18a06a987b 199 return length;
dudmuck 336:1e18a06a987b 200 }
dudmuck 336:1e18a06a987b 201
dudmuck 336:1e18a06a987b 202 int i2c_write(i2c_t *obj, int address, const char *data, int length, int stop)
dudmuck 336:1e18a06a987b 203 {
dudmuck 336:1e18a06a987b 204 I2C_TypeDef *i2c = (I2C_TypeDef *)(obj->i2c);
dudmuck 336:1e18a06a987b 205 I2cHandle.Instance = (I2C_TypeDef *)(obj->i2c);
dudmuck 336:1e18a06a987b 206 int timeout;
dudmuck 336:1e18a06a987b 207 int count;
dudmuck 336:1e18a06a987b 208
dudmuck 336:1e18a06a987b 209 i2c_start(obj);
dudmuck 336:1e18a06a987b 210
dudmuck 336:1e18a06a987b 211 // Wait until SB flag is set
dudmuck 336:1e18a06a987b 212 timeout = FLAG_TIMEOUT;
dudmuck 336:1e18a06a987b 213 while (__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_SB) == RESET) {
dudmuck 336:1e18a06a987b 214 timeout--;
dudmuck 336:1e18a06a987b 215 if (timeout == 0) {
dudmuck 336:1e18a06a987b 216 return -1;
dudmuck 336:1e18a06a987b 217 }
dudmuck 336:1e18a06a987b 218 }
dudmuck 336:1e18a06a987b 219
dudmuck 336:1e18a06a987b 220 i2c->DR = I2C_7BIT_ADD_WRITE(address);
dudmuck 336:1e18a06a987b 221
dudmuck 336:1e18a06a987b 222
dudmuck 336:1e18a06a987b 223 // Wait address is acknowledged
dudmuck 336:1e18a06a987b 224 timeout = FLAG_TIMEOUT;
dudmuck 336:1e18a06a987b 225 while (__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_ADDR) == RESET) {
dudmuck 336:1e18a06a987b 226 timeout--;
dudmuck 336:1e18a06a987b 227 if (timeout == 0) {
dudmuck 336:1e18a06a987b 228 return -1;
dudmuck 336:1e18a06a987b 229 }
dudmuck 336:1e18a06a987b 230 }
dudmuck 336:1e18a06a987b 231 __HAL_I2C_CLEAR_ADDRFLAG(&I2cHandle);
dudmuck 336:1e18a06a987b 232
dudmuck 336:1e18a06a987b 233 for (count = 0; count < length; count++) {
dudmuck 336:1e18a06a987b 234 if (i2c_byte_write(obj, data[count]) != 1) {
dudmuck 336:1e18a06a987b 235 i2c_stop(obj);
dudmuck 336:1e18a06a987b 236 return -1;
dudmuck 336:1e18a06a987b 237 }
dudmuck 336:1e18a06a987b 238 }
dudmuck 336:1e18a06a987b 239
dudmuck 336:1e18a06a987b 240 // If not repeated start, send stop.
dudmuck 336:1e18a06a987b 241 if (stop) {
dudmuck 336:1e18a06a987b 242 i2c_stop(obj);
dudmuck 336:1e18a06a987b 243 }
dudmuck 336:1e18a06a987b 244
dudmuck 336:1e18a06a987b 245 return count;
dudmuck 336:1e18a06a987b 246 }
dudmuck 336:1e18a06a987b 247
dudmuck 336:1e18a06a987b 248 int i2c_byte_read(i2c_t *obj, int last)
dudmuck 336:1e18a06a987b 249 {
dudmuck 336:1e18a06a987b 250 I2C_TypeDef *i2c = (I2C_TypeDef *)(obj->i2c);
dudmuck 336:1e18a06a987b 251 int timeout;
dudmuck 336:1e18a06a987b 252
dudmuck 336:1e18a06a987b 253 if (last) {
dudmuck 336:1e18a06a987b 254 // Don't acknowledge the last byte
dudmuck 336:1e18a06a987b 255 i2c->CR1 &= ~I2C_CR1_ACK;
dudmuck 336:1e18a06a987b 256 } else {
dudmuck 336:1e18a06a987b 257 // Acknowledge the byte
dudmuck 336:1e18a06a987b 258 i2c->CR1 |= I2C_CR1_ACK;
dudmuck 336:1e18a06a987b 259 }
dudmuck 336:1e18a06a987b 260
dudmuck 336:1e18a06a987b 261 // Wait until the byte is received
dudmuck 336:1e18a06a987b 262 timeout = FLAG_TIMEOUT;
dudmuck 336:1e18a06a987b 263 while (__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_RXNE) == RESET) {
dudmuck 336:1e18a06a987b 264 if ((timeout--) == 0) {
dudmuck 336:1e18a06a987b 265 return -1;
dudmuck 336:1e18a06a987b 266 }
dudmuck 336:1e18a06a987b 267 }
dudmuck 336:1e18a06a987b 268
dudmuck 336:1e18a06a987b 269 return (int)i2c->DR;
dudmuck 336:1e18a06a987b 270 }
dudmuck 336:1e18a06a987b 271
dudmuck 336:1e18a06a987b 272 int i2c_byte_write(i2c_t *obj, int data)
dudmuck 336:1e18a06a987b 273 {
dudmuck 336:1e18a06a987b 274 I2C_TypeDef *i2c = (I2C_TypeDef *)(obj->i2c);
dudmuck 336:1e18a06a987b 275 int timeout;
dudmuck 336:1e18a06a987b 276
dudmuck 336:1e18a06a987b 277 i2c->DR = (uint8_t)data;
dudmuck 336:1e18a06a987b 278
dudmuck 336:1e18a06a987b 279 // Wait until the byte is transmitted
dudmuck 336:1e18a06a987b 280 timeout = FLAG_TIMEOUT;
dudmuck 336:1e18a06a987b 281 while ((__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_TXE) == RESET) &&
dudmuck 336:1e18a06a987b 282 (__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_BTF) == RESET)) {
dudmuck 336:1e18a06a987b 283 if ((timeout--) == 0) {
dudmuck 336:1e18a06a987b 284 return 0;
dudmuck 336:1e18a06a987b 285 }
dudmuck 336:1e18a06a987b 286 }
dudmuck 336:1e18a06a987b 287
dudmuck 336:1e18a06a987b 288 return 1;
dudmuck 336:1e18a06a987b 289 }
dudmuck 336:1e18a06a987b 290
dudmuck 336:1e18a06a987b 291 void i2c_reset(i2c_t *obj)
dudmuck 336:1e18a06a987b 292 {
dudmuck 336:1e18a06a987b 293 int timeout;
dudmuck 336:1e18a06a987b 294
dudmuck 336:1e18a06a987b 295 // wait before reset
dudmuck 336:1e18a06a987b 296 timeout = LONG_TIMEOUT;
dudmuck 336:1e18a06a987b 297 while ((__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_BUSY)) && (timeout-- != 0));
dudmuck 336:1e18a06a987b 298
dudmuck 336:1e18a06a987b 299 if (obj->i2c == I2C_1) {
dudmuck 336:1e18a06a987b 300 __I2C1_FORCE_RESET();
dudmuck 336:1e18a06a987b 301 __I2C1_RELEASE_RESET();
dudmuck 336:1e18a06a987b 302 }
dudmuck 336:1e18a06a987b 303 if (obj->i2c == I2C_2) {
dudmuck 336:1e18a06a987b 304 __I2C2_FORCE_RESET();
dudmuck 336:1e18a06a987b 305 __I2C2_RELEASE_RESET();
dudmuck 336:1e18a06a987b 306 }
dudmuck 336:1e18a06a987b 307 }
dudmuck 336:1e18a06a987b 308
dudmuck 336:1e18a06a987b 309 #if DEVICE_I2CSLAVE
dudmuck 336:1e18a06a987b 310
dudmuck 336:1e18a06a987b 311 void i2c_slave_address(i2c_t *obj, int idx, uint32_t address, uint32_t mask)
dudmuck 336:1e18a06a987b 312 {
dudmuck 336:1e18a06a987b 313 I2C_TypeDef *i2c = (I2C_TypeDef *)(obj->i2c);
dudmuck 336:1e18a06a987b 314 uint16_t tmpreg = 0;
dudmuck 336:1e18a06a987b 315
dudmuck 336:1e18a06a987b 316 // Get the old register value
dudmuck 336:1e18a06a987b 317 tmpreg = i2c->OAR1;
dudmuck 336:1e18a06a987b 318 // Reset address bits
dudmuck 336:1e18a06a987b 319 tmpreg &= 0xFC00;
dudmuck 336:1e18a06a987b 320 // Set new address
dudmuck 336:1e18a06a987b 321 tmpreg |= (uint16_t)((uint16_t)address & (uint16_t)0x00FE); // 7-bits
dudmuck 336:1e18a06a987b 322 // Store the new register value
dudmuck 336:1e18a06a987b 323 i2c->OAR1 = tmpreg;
dudmuck 336:1e18a06a987b 324 }
dudmuck 336:1e18a06a987b 325
dudmuck 336:1e18a06a987b 326 void i2c_slave_mode(i2c_t *obj, int enable_slave)
dudmuck 336:1e18a06a987b 327 {
dudmuck 336:1e18a06a987b 328 I2cHandle.Instance = (I2C_TypeDef *)(obj->i2c);
dudmuck 336:1e18a06a987b 329 if (enable_slave) {
dudmuck 336:1e18a06a987b 330 obj->slave = 1;
dudmuck 336:1e18a06a987b 331 /* Enable Address Acknowledge */
dudmuck 336:1e18a06a987b 332 I2cHandle.Instance->CR1 |= I2C_CR1_ACK;
dudmuck 336:1e18a06a987b 333 }
dudmuck 336:1e18a06a987b 334 }
dudmuck 336:1e18a06a987b 335
dudmuck 336:1e18a06a987b 336 // See I2CSlave.h
dudmuck 336:1e18a06a987b 337 #define NoData 0 // the slave has not been addressed
dudmuck 336:1e18a06a987b 338 #define ReadAddressed 1 // the master has requested a read from this slave (slave = transmitter)
dudmuck 336:1e18a06a987b 339 #define WriteGeneral 2 // the master is writing to all slave
dudmuck 336:1e18a06a987b 340 #define WriteAddressed 3 // the master is writing to this slave (slave = receiver)
dudmuck 336:1e18a06a987b 341
dudmuck 336:1e18a06a987b 342 int i2c_slave_receive(i2c_t *obj)
dudmuck 336:1e18a06a987b 343 {
dudmuck 336:1e18a06a987b 344 int retValue = NoData;
dudmuck 336:1e18a06a987b 345
dudmuck 336:1e18a06a987b 346 if (__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_BUSY) == 1) {
dudmuck 336:1e18a06a987b 347 if (__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_ADDR) == 1) {
dudmuck 336:1e18a06a987b 348 if (__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_TRA) == 1)
dudmuck 336:1e18a06a987b 349 retValue = ReadAddressed;
dudmuck 336:1e18a06a987b 350 else
dudmuck 336:1e18a06a987b 351 retValue = WriteAddressed;
dudmuck 336:1e18a06a987b 352
dudmuck 336:1e18a06a987b 353 __HAL_I2C_CLEAR_FLAG(&I2cHandle, I2C_FLAG_ADDR);
dudmuck 336:1e18a06a987b 354 }
dudmuck 336:1e18a06a987b 355 }
dudmuck 336:1e18a06a987b 356
dudmuck 336:1e18a06a987b 357 return (retValue);
dudmuck 336:1e18a06a987b 358 }
dudmuck 336:1e18a06a987b 359
dudmuck 336:1e18a06a987b 360 int i2c_slave_read(i2c_t *obj, char *data, int length)
dudmuck 336:1e18a06a987b 361 {
dudmuck 336:1e18a06a987b 362 uint32_t Timeout;
dudmuck 336:1e18a06a987b 363 int size = 0;
dudmuck 336:1e18a06a987b 364
dudmuck 336:1e18a06a987b 365 I2cHandle.Instance = (I2C_TypeDef *)(obj->i2c);
dudmuck 336:1e18a06a987b 366
dudmuck 336:1e18a06a987b 367 while (length > 0) {
dudmuck 336:1e18a06a987b 368 /* Wait until RXNE flag is set */
dudmuck 336:1e18a06a987b 369 // Wait until the byte is received
dudmuck 336:1e18a06a987b 370 Timeout = FLAG_TIMEOUT;
dudmuck 336:1e18a06a987b 371 while (__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_RXNE) == RESET) {
dudmuck 336:1e18a06a987b 372 Timeout--;
dudmuck 336:1e18a06a987b 373 if (Timeout == 0) {
dudmuck 336:1e18a06a987b 374 return -1;
dudmuck 336:1e18a06a987b 375 }
dudmuck 336:1e18a06a987b 376 }
dudmuck 336:1e18a06a987b 377
dudmuck 336:1e18a06a987b 378 /* Read data from DR */
dudmuck 336:1e18a06a987b 379 (*data++) = I2cHandle.Instance->DR;
dudmuck 336:1e18a06a987b 380 length--;
dudmuck 336:1e18a06a987b 381 size++;
dudmuck 336:1e18a06a987b 382
dudmuck 336:1e18a06a987b 383 if ((__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_BTF) == SET) && (length != 0)) {
dudmuck 336:1e18a06a987b 384 /* Read data from DR */
dudmuck 336:1e18a06a987b 385 (*data++) = I2cHandle.Instance->DR;
dudmuck 336:1e18a06a987b 386 length--;
dudmuck 336:1e18a06a987b 387 size++;
dudmuck 336:1e18a06a987b 388 }
dudmuck 336:1e18a06a987b 389 }
dudmuck 336:1e18a06a987b 390
dudmuck 336:1e18a06a987b 391 /* Wait until STOP flag is set */
dudmuck 336:1e18a06a987b 392 Timeout = FLAG_TIMEOUT;
dudmuck 336:1e18a06a987b 393 while (__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_STOPF) == RESET) {
dudmuck 336:1e18a06a987b 394 Timeout--;
dudmuck 336:1e18a06a987b 395 if (Timeout == 0) {
dudmuck 336:1e18a06a987b 396 return -1;
dudmuck 336:1e18a06a987b 397 }
dudmuck 336:1e18a06a987b 398 }
dudmuck 336:1e18a06a987b 399
dudmuck 336:1e18a06a987b 400 /* Clear STOP flag */
dudmuck 336:1e18a06a987b 401 __HAL_I2C_CLEAR_STOPFLAG(&I2cHandle);
dudmuck 336:1e18a06a987b 402
dudmuck 336:1e18a06a987b 403 /* Wait until BUSY flag is reset */
dudmuck 336:1e18a06a987b 404 Timeout = FLAG_TIMEOUT;
dudmuck 336:1e18a06a987b 405 while (__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_BUSY) == SET) {
dudmuck 336:1e18a06a987b 406 Timeout--;
dudmuck 336:1e18a06a987b 407 if (Timeout == 0) {
dudmuck 336:1e18a06a987b 408 return -1;
dudmuck 336:1e18a06a987b 409 }
dudmuck 336:1e18a06a987b 410 }
dudmuck 336:1e18a06a987b 411
dudmuck 336:1e18a06a987b 412 return size;
dudmuck 336:1e18a06a987b 413 }
dudmuck 336:1e18a06a987b 414
dudmuck 336:1e18a06a987b 415 int i2c_slave_write(i2c_t *obj, const char *data, int length)
dudmuck 336:1e18a06a987b 416 {
dudmuck 336:1e18a06a987b 417 uint32_t Timeout;
dudmuck 336:1e18a06a987b 418 int size = 0;
dudmuck 336:1e18a06a987b 419
dudmuck 336:1e18a06a987b 420 I2cHandle.Instance = (I2C_TypeDef *)(obj->i2c);
dudmuck 336:1e18a06a987b 421
dudmuck 336:1e18a06a987b 422 while (length > 0) {
dudmuck 336:1e18a06a987b 423 /* Wait until TXE flag is set */
dudmuck 336:1e18a06a987b 424 Timeout = FLAG_TIMEOUT;
dudmuck 336:1e18a06a987b 425 while (__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_TXE) == RESET) {
dudmuck 336:1e18a06a987b 426 Timeout--;
dudmuck 336:1e18a06a987b 427 if (Timeout == 0) {
dudmuck 336:1e18a06a987b 428 return -1;
dudmuck 336:1e18a06a987b 429 }
dudmuck 336:1e18a06a987b 430 }
dudmuck 336:1e18a06a987b 431
dudmuck 336:1e18a06a987b 432
dudmuck 336:1e18a06a987b 433 /* Write data to DR */
dudmuck 336:1e18a06a987b 434 I2cHandle.Instance->DR = (*data++);
dudmuck 336:1e18a06a987b 435 length--;
dudmuck 336:1e18a06a987b 436 size++;
dudmuck 336:1e18a06a987b 437
dudmuck 336:1e18a06a987b 438 if ((__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_BTF) == SET) && (length != 0)) {
dudmuck 336:1e18a06a987b 439 /* Write data to DR */
dudmuck 336:1e18a06a987b 440 I2cHandle.Instance->DR = (*data++);
dudmuck 336:1e18a06a987b 441 length--;
dudmuck 336:1e18a06a987b 442 size++;
dudmuck 336:1e18a06a987b 443 }
dudmuck 336:1e18a06a987b 444 }
dudmuck 336:1e18a06a987b 445
dudmuck 336:1e18a06a987b 446 /* Wait until AF flag is set */
dudmuck 336:1e18a06a987b 447 Timeout = FLAG_TIMEOUT;
dudmuck 336:1e18a06a987b 448 while (__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_AF) == RESET) {
dudmuck 336:1e18a06a987b 449 Timeout--;
dudmuck 336:1e18a06a987b 450 if (Timeout == 0) {
dudmuck 336:1e18a06a987b 451 return -1;
dudmuck 336:1e18a06a987b 452 }
dudmuck 336:1e18a06a987b 453 }
dudmuck 336:1e18a06a987b 454
dudmuck 336:1e18a06a987b 455
dudmuck 336:1e18a06a987b 456 /* Clear AF flag */
dudmuck 336:1e18a06a987b 457 __HAL_I2C_CLEAR_FLAG(&I2cHandle, I2C_FLAG_AF);
dudmuck 336:1e18a06a987b 458
dudmuck 336:1e18a06a987b 459
dudmuck 336:1e18a06a987b 460 /* Wait until BUSY flag is reset */
dudmuck 336:1e18a06a987b 461 Timeout = FLAG_TIMEOUT;
dudmuck 336:1e18a06a987b 462 while (__HAL_I2C_GET_FLAG(&I2cHandle, I2C_FLAG_BUSY) == SET) {
dudmuck 336:1e18a06a987b 463 Timeout--;
dudmuck 336:1e18a06a987b 464 if (Timeout == 0) {
dudmuck 336:1e18a06a987b 465 return -1;
dudmuck 336:1e18a06a987b 466 }
dudmuck 336:1e18a06a987b 467 }
dudmuck 336:1e18a06a987b 468
dudmuck 336:1e18a06a987b 469 I2cHandle.State = HAL_I2C_STATE_READY;
dudmuck 336:1e18a06a987b 470
dudmuck 336:1e18a06a987b 471 /* Process Unlocked */
dudmuck 336:1e18a06a987b 472 __HAL_UNLOCK(&I2cHandle);
dudmuck 336:1e18a06a987b 473
dudmuck 336:1e18a06a987b 474 return size;
dudmuck 336:1e18a06a987b 475 }
dudmuck 336:1e18a06a987b 476
dudmuck 336:1e18a06a987b 477
dudmuck 336:1e18a06a987b 478 #endif // DEVICE_I2CSLAVE
dudmuck 336:1e18a06a987b 479
dudmuck 336:1e18a06a987b 480 #endif // DEVICE_I2C