BLE_API wrapper library for STMicroelectronics' BlueNRG Bluetooth Low Energy expansion board shield (Component)

Dependents:   Nucleo_Zumo_BLE_IDB04A1 contest_IOT5 contest_IOT6 contest_IOT_10 ... more

Fork of X_NUCLEO_IDB0XA1 by ST Expansion SW Team

Arduino Connector Compatibility Warning

X-NUCLEO-IDB04A1 and X-NUCLEO-IDB05A1 are Arduino compatible with an exception: instead of using pin D13 for the SPI clock, they use pin D3. The default configuration for this library is having the SPI clock on pin D3.

To be fully Arduino compatible, X-NUCLEO-IDB04A1 and X-NUCLEO-IDB05A1 need a small HW patch.

For X-NUCLEO-IDB04A1 this patch consists in removing zero resistor R10 and instead soldering zero resistor R11. For X-NUCLEO-IDB05A1 this patch consists in removing zero resistor R4 and instead soldering zero resistor R6.

In case you patch your board, then you also have to configure this library to use pin D13 to drive the SPI clock (see macro IDB0XA1_D13_PATCH in file x_nucleo_idb0xa1_targets.h).

If you use pin D13 for the SPI clock, please be aware that on STM32 Nucleo boards you may not drive the LED, otherwise you will get a conflict: the LED on STM32 Nucleo boards is connected to pin D13.

Referring to the current list of tested platforms (see X-NUCLEO-IDB04A1 and X-NUCLEO-IDB05A1 pages), the patch is required by ST-Nucleo-F103RB; ST-Nucleo-F302R8; ST-Nucleo-F411RE; and ST-Nucleo-F446RE.

Committer:
Andrea Palmieri
Date:
Mon May 16 17:22:03 2016 +0200
Revision:
229:9981f62cdb1a
Parent:
216:7aa807180321
Child:
242:058b2e731adc
Child:
245:6830f71c197c
Fix issues and add features

- Fix handles management
- Fix UUIDs management
- Implement API to read random address
- Fix clearing/setting of ADV payload
- Fix scanning behaviour
- Fix scanning while a connection is ongoing
- Implement Char Descriptor discovery
- Implement scanning/advertising filter policy (White List partial management)
- Update underlying BlueNRG stack
- Cosmetics

Signed-off-by: Andrea Palmieri <andrea.palmieri@st.com>

Who changed what in which revision?

UserRevisionLine numberNew contents of line
Wolfgang Betz 130:770ce14d3d15 1 /* mbed Microcontroller Library
Wolfgang Betz 130:770ce14d3d15 2 * Copyright (c) 2006-2013 ARM Limited
Wolfgang Betz 130:770ce14d3d15 3 *
Wolfgang Betz 130:770ce14d3d15 4 * Licensed under the Apache License, Version 2.0 (the "License");
Wolfgang Betz 130:770ce14d3d15 5 * you may not use this file except in compliance with the License.
Wolfgang Betz 130:770ce14d3d15 6 * You may obtain a copy of the License at
Wolfgang Betz 130:770ce14d3d15 7 *
Wolfgang Betz 130:770ce14d3d15 8 * http://www.apache.org/licenses/LICENSE-2.0
Wolfgang Betz 130:770ce14d3d15 9 *
Wolfgang Betz 130:770ce14d3d15 10 * Unless required by applicable law or agreed to in writing, software
Wolfgang Betz 130:770ce14d3d15 11 * distributed under the License is distributed on an "AS IS" BASIS,
Wolfgang Betz 130:770ce14d3d15 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
Wolfgang Betz 130:770ce14d3d15 13 * See the License for the specific language governing permissions and
Wolfgang Betz 130:770ce14d3d15 14 * limitations under the License.
Wolfgang Betz 130:770ce14d3d15 15 */
Wolfgang Betz 130:770ce14d3d15 16
Wolfgang Betz 130:770ce14d3d15 17 /**
Wolfgang Betz 130:770ce14d3d15 18 ******************************************************************************
Wolfgang Betz 130:770ce14d3d15 19 * @file BlueNRGDevice.cpp
Wolfgang Betz 130:770ce14d3d15 20 * @author STMicroelectronics
Wolfgang Betz 130:770ce14d3d15 21 * @brief Implementation of BLEDeviceInstanceBase
Wolfgang Betz 130:770ce14d3d15 22 ******************************************************************************
Wolfgang Betz 130:770ce14d3d15 23 * @copy
Wolfgang Betz 130:770ce14d3d15 24 *
Wolfgang Betz 130:770ce14d3d15 25 * THE PRESENT FIRMWARE WHICH IS FOR GUIDANCE ONLY AIMS AT PROVIDING CUSTOMERS
Wolfgang Betz 130:770ce14d3d15 26 * WITH CODING INFORMATION REGARDING THEIR PRODUCTS IN ORDER FOR THEM TO SAVE
Wolfgang Betz 130:770ce14d3d15 27 * TIME. AS A RESULT, STMICROELECTRONICS SHALL NOT BE HELD LIABLE FOR ANY
Wolfgang Betz 130:770ce14d3d15 28 * DIRECT, INDIRECT OR CONSEQUENTIAL DAMAGES WITH RESPECT TO ANY CLAIMS ARISING
Wolfgang Betz 130:770ce14d3d15 29 * FROM THE CONTENT OF SUCH FIRMWARE AND/OR THE USE MADE BY CUSTOMERS OF THE
Wolfgang Betz 130:770ce14d3d15 30 * CODING INFORMATION CONTAINED HEREIN IN CONNECTION WITH THEIR PRODUCTS.
Wolfgang Betz 130:770ce14d3d15 31 *
Wolfgang Betz 130:770ce14d3d15 32 * <h2><center>&copy; COPYRIGHT 2013 STMicroelectronics</center></h2>
Wolfgang Betz 130:770ce14d3d15 33 */
Wolfgang Betz 130:770ce14d3d15 34
Wolfgang Betz 130:770ce14d3d15 35 /** @defgroup BlueNRGDevice
Wolfgang Betz 130:770ce14d3d15 36 * @brief BlueNRG BLE_API Device Adaptation
Wolfgang Betz 130:770ce14d3d15 37 * @{
Wolfgang Betz 130:770ce14d3d15 38 */
Wolfgang Betz 130:770ce14d3d15 39
Wolfgang Betz 144:bdf5e8432131 40 #include "mbed-drivers/mbed.h"
Wolfgang Betz 130:770ce14d3d15 41 #include "BlueNRGDevice.h"
Wolfgang Betz 130:770ce14d3d15 42 #include "BlueNRGGap.h"
Wolfgang Betz 130:770ce14d3d15 43 #include "BlueNRGGattServer.h"
Wolfgang Betz 130:770ce14d3d15 44
Wolfgang Betz 130:770ce14d3d15 45 #include "btle.h"
Wolfgang Betz 130:770ce14d3d15 46 #include "Utils.h"
Wolfgang Betz 130:770ce14d3d15 47 #include "osal.h"
Wolfgang Betz 130:770ce14d3d15 48
Wolfgang Betz 130:770ce14d3d15 49 #include "debug.h"
Wolfgang Betz 130:770ce14d3d15 50 #include "stm32_bluenrg_ble.h"
Wolfgang Betz 130:770ce14d3d15 51
Wolfgang Betz 130:770ce14d3d15 52 extern "C" {
Wolfgang Betz 130:770ce14d3d15 53 #include "hci.h"
Wolfgang Betz 130:770ce14d3d15 54 }
Wolfgang Betz 130:770ce14d3d15 55
Wolfgang Betz 130:770ce14d3d15 56 #define HEADER_SIZE 5
Wolfgang Betz 130:770ce14d3d15 57 #define MAX_BUFFER_SIZE 255
Wolfgang Betz 130:770ce14d3d15 58
Wolfgang Betz 130:770ce14d3d15 59 /**
Wolfgang Betz 130:770ce14d3d15 60 * The singleton which represents the BlueNRG transport for the BLEDevice.
Wolfgang Betz 130:770ce14d3d15 61 *
Wolfgang Betz 130:770ce14d3d15 62 * See file 'x_nucleo_idb0xa1_targets.h' for details regarding the peripheral pins used!
Wolfgang Betz 130:770ce14d3d15 63 */
Wolfgang Betz 130:770ce14d3d15 64 #include "x_nucleo_idb0xa1_targets.h"
Wolfgang Betz 130:770ce14d3d15 65
Wolfgang Betz 130:770ce14d3d15 66 BlueNRGDevice bluenrgDeviceInstance(IDB0XA1_PIN_SPI_MOSI,
Wolfgang Betz 130:770ce14d3d15 67 IDB0XA1_PIN_SPI_MISO,
Wolfgang Betz 130:770ce14d3d15 68 IDB0XA1_PIN_SPI_SCK,
Wolfgang Betz 130:770ce14d3d15 69 IDB0XA1_PIN_SPI_nCS,
Wolfgang Betz 130:770ce14d3d15 70 IDB0XA1_PIN_SPI_RESET,
Wolfgang Betz 130:770ce14d3d15 71 IDB0XA1_PIN_SPI_IRQ);
Wolfgang Betz 130:770ce14d3d15 72
Wolfgang Betz 130:770ce14d3d15 73 /**
Wolfgang Betz 130:770ce14d3d15 74 * BLE-API requires an implementation of the following function in order to
Wolfgang Betz 130:770ce14d3d15 75 * obtain its transport handle.
Wolfgang Betz 130:770ce14d3d15 76 */
Wolfgang Betz 130:770ce14d3d15 77 BLEInstanceBase *
Wolfgang Betz 130:770ce14d3d15 78 createBLEInstance(void)
Wolfgang Betz 130:770ce14d3d15 79 {
Wolfgang Betz 130:770ce14d3d15 80 return (&bluenrgDeviceInstance);
Wolfgang Betz 130:770ce14d3d15 81 }
Wolfgang Betz 130:770ce14d3d15 82
Wolfgang Betz 130:770ce14d3d15 83 /**************************************************************************/
Wolfgang Betz 130:770ce14d3d15 84 /**
Wolfgang Betz 130:770ce14d3d15 85 @brief Constructor
Wolfgang Betz 130:770ce14d3d15 86 * @param mosi mbed pin to use for MOSI line of SPI interface
Wolfgang Betz 130:770ce14d3d15 87 * @param miso mbed pin to use for MISO line of SPI interface
Wolfgang Betz 130:770ce14d3d15 88 * @param sck mbed pin to use for SCK line of SPI interface
Wolfgang Betz 130:770ce14d3d15 89 * @param cs mbed pin to use for not chip select line of SPI interface
Wolfgang Betz 130:770ce14d3d15 90 * @param rst mbed pin to use for BlueNRG reset
Wolfgang Betz 130:770ce14d3d15 91 * @param irq mbed pin for BlueNRG IRQ
Wolfgang Betz 130:770ce14d3d15 92 */
Wolfgang Betz 130:770ce14d3d15 93 /**************************************************************************/
Wolfgang Betz 130:770ce14d3d15 94 BlueNRGDevice::BlueNRGDevice(PinName mosi,
Wolfgang Betz 130:770ce14d3d15 95 PinName miso,
Wolfgang Betz 130:770ce14d3d15 96 PinName sck,
Wolfgang Betz 130:770ce14d3d15 97 PinName cs,
Wolfgang Betz 130:770ce14d3d15 98 PinName rst,
Wolfgang Betz 168:ad1dff5dca1f 99 PinName irq) :
Wolfgang Betz 168:ad1dff5dca1f 100 isInitialized(false), spi_(mosi, miso, sck), nCS_(cs), rst_(rst), irq_(irq)
Wolfgang Betz 130:770ce14d3d15 101 {
Wolfgang Betz 130:770ce14d3d15 102 // Setup the spi for 8 bit data, low clock polarity,
Wolfgang Betz 130:770ce14d3d15 103 // 1-edge phase, with an 8MHz clock rate
Wolfgang Betz 130:770ce14d3d15 104 spi_.format(8, 0);
Wolfgang Betz 130:770ce14d3d15 105 spi_.frequency(8000000);
Wolfgang Betz 130:770ce14d3d15 106
Wolfgang Betz 130:770ce14d3d15 107 // Deselect the BlueNRG chip by keeping its nCS signal high
Wolfgang Betz 130:770ce14d3d15 108 nCS_ = 1;
Wolfgang Betz 130:770ce14d3d15 109
Wolfgang Betz 130:770ce14d3d15 110 wait_us(500);
Wolfgang Betz 130:770ce14d3d15 111 }
Wolfgang Betz 130:770ce14d3d15 112
Wolfgang Betz 130:770ce14d3d15 113 /**************************************************************************/
Wolfgang Betz 130:770ce14d3d15 114 /**
Wolfgang Betz 130:770ce14d3d15 115 @brief Destructor
Wolfgang Betz 130:770ce14d3d15 116 */
Wolfgang Betz 130:770ce14d3d15 117 /**************************************************************************/
Wolfgang Betz 130:770ce14d3d15 118 BlueNRGDevice::~BlueNRGDevice(void)
Wolfgang Betz 130:770ce14d3d15 119 {
Wolfgang Betz 130:770ce14d3d15 120 }
Wolfgang Betz 130:770ce14d3d15 121
Wolfgang Betz 130:770ce14d3d15 122
Wolfgang Betz 130:770ce14d3d15 123 /**
Wolfgang Betz 130:770ce14d3d15 124 @brief Initialises anything required to start using BLE
Wolfgang Betz 130:770ce14d3d15 125 @param[in] void
Wolfgang Betz 130:770ce14d3d15 126 @returns ble_error_t
Wolfgang Betz 130:770ce14d3d15 127 */
Andrea Palmieri 167:abc42e7158a6 128 ble_error_t BlueNRGDevice::init(BLE::InstanceID_t instanceID, FunctionPointerWithContext<BLE::InitializationCompleteCallbackContext *> callback)
Wolfgang Betz 130:770ce14d3d15 129 {
Andrea Palmieri 167:abc42e7158a6 130 if (isInitialized) {
Andrea Palmieri 167:abc42e7158a6 131 BLE::InitializationCompleteCallbackContext context = {
Andrea Palmieri 167:abc42e7158a6 132 BLE::Instance(instanceID),
Andrea Palmieri 167:abc42e7158a6 133 BLE_ERROR_ALREADY_INITIALIZED
Andrea Palmieri 167:abc42e7158a6 134 };
Andrea Palmieri 167:abc42e7158a6 135 callback.call(&context);
Andrea Palmieri 167:abc42e7158a6 136 return BLE_ERROR_ALREADY_INITIALIZED;
Andrea Palmieri 167:abc42e7158a6 137 }
Andrea Palmieri 167:abc42e7158a6 138
Wolfgang Betz 130:770ce14d3d15 139 // Set the interrupt handler for the device
Wolfgang Betz 169:485bbcddf0c3 140 irq_.mode(PullDown); // betzw: set irq mode
Wolfgang Betz 130:770ce14d3d15 141 irq_.rise(&HCI_Isr);
Wolfgang Betz 173:821942ac7d5a 142
Wolfgang Betz 130:770ce14d3d15 143 /* ToDo: Clear memory contents, reset the SD, etc. */
Wolfgang Betz 132:51056160fa4a 144 // By default, we set the device GAP role to PERIPHERAL
Andrea Palmieri 216:7aa807180321 145 btleInit(BlueNRGGap::getInstance().getIsSetAddress(), GAP_PERIPHERAL_ROLE_IDB04A1);
Wolfgang Betz 130:770ce14d3d15 146
Wolfgang Betz 130:770ce14d3d15 147 isInitialized = true;
Andrea Palmieri 167:abc42e7158a6 148 BLE::InitializationCompleteCallbackContext context = {
Andrea Palmieri 167:abc42e7158a6 149 BLE::Instance(instanceID),
Andrea Palmieri 167:abc42e7158a6 150 BLE_ERROR_NONE
Andrea Palmieri 167:abc42e7158a6 151 };
Andrea Palmieri 167:abc42e7158a6 152 callback.call(&context);
Wolfgang Betz 130:770ce14d3d15 153
Wolfgang Betz 130:770ce14d3d15 154 return BLE_ERROR_NONE;
Wolfgang Betz 130:770ce14d3d15 155 }
Wolfgang Betz 130:770ce14d3d15 156
Wolfgang Betz 130:770ce14d3d15 157
Wolfgang Betz 130:770ce14d3d15 158 /**
Wolfgang Betz 130:770ce14d3d15 159 @brief Resets the BLE HW, removing any existing services and
Wolfgang Betz 130:770ce14d3d15 160 characteristics
Wolfgang Betz 130:770ce14d3d15 161 @param[in] void
Andrea Palmieri 229:9981f62cdb1a 162 @returns void
Wolfgang Betz 130:770ce14d3d15 163 */
Andrea Palmieri 229:9981f62cdb1a 164 void BlueNRGDevice::reset(void)
Wolfgang Betz 130:770ce14d3d15 165 {
Wolfgang Betz 130:770ce14d3d15 166 wait_us(500);
Wolfgang Betz 130:770ce14d3d15 167
Wolfgang Betz 130:770ce14d3d15 168 /* Reset BlueNRG SPI interface */
Wolfgang Betz 130:770ce14d3d15 169 rst_ = 0;
Wolfgang Betz 130:770ce14d3d15 170 wait_us(5);
Wolfgang Betz 130:770ce14d3d15 171 rst_ = 1;
Wolfgang Betz 130:770ce14d3d15 172 wait_us(5);
Wolfgang Betz 130:770ce14d3d15 173
Wolfgang Betz 130:770ce14d3d15 174 /* Wait for the radio to come back up */
Wolfgang Betz 130:770ce14d3d15 175 wait_us(500);
Wolfgang Betz 130:770ce14d3d15 176
Wolfgang Betz 130:770ce14d3d15 177 }
Wolfgang Betz 130:770ce14d3d15 178
Wolfgang Betz 130:770ce14d3d15 179 /*!
Wolfgang Betz 130:770ce14d3d15 180 @brief Wait for any BLE Event like BLE Connection, Read Request etc.
Wolfgang Betz 130:770ce14d3d15 181 @param[in] void
Wolfgang Betz 130:770ce14d3d15 182 @returns char *
Wolfgang Betz 130:770ce14d3d15 183 */
Wolfgang Betz 130:770ce14d3d15 184 void BlueNRGDevice::waitForEvent(void)
Wolfgang Betz 130:770ce14d3d15 185 {
Wolfgang Betz 130:770ce14d3d15 186 bool must_return = false;
Wolfgang Betz 130:770ce14d3d15 187
Wolfgang Betz 130:770ce14d3d15 188 do {
Wolfgang Betz 130:770ce14d3d15 189 BlueNRGGap::getInstance().Process();
Wolfgang Betz 130:770ce14d3d15 190
Wolfgang Betz 130:770ce14d3d15 191 HCI_Process();
Wolfgang Betz 130:770ce14d3d15 192
Wolfgang Betz 130:770ce14d3d15 193 if(must_return) return;
Wolfgang Betz 130:770ce14d3d15 194
Wolfgang Betz 130:770ce14d3d15 195 __WFE(); /* it is recommended that SEVONPEND in the
Wolfgang Betz 130:770ce14d3d15 196 System Control Register is NOT set */
Wolfgang Betz 130:770ce14d3d15 197 must_return = true; /* after returning from WFE we must guarantee
Wolfgang Betz 130:770ce14d3d15 198 that conrol is given back to main loop before next WFE */
Wolfgang Betz 130:770ce14d3d15 199 } while(true);
Wolfgang Betz 130:770ce14d3d15 200
Wolfgang Betz 139:3a75965fd389 201 }
Wolfgang Betz 130:770ce14d3d15 202
Wolfgang Betz 130:770ce14d3d15 203 /*!
Wolfgang Betz 130:770ce14d3d15 204 @brief get GAP version
Andrea Palmieri 216:7aa807180321 205 @brief Get the BLE stack version information
Wolfgang Betz 130:770ce14d3d15 206 @param[in] void
Wolfgang Betz 130:770ce14d3d15 207 @returns char *
Andrea Palmieri 216:7aa807180321 208 @returns char *
Wolfgang Betz 130:770ce14d3d15 209 */
Wolfgang Betz 130:770ce14d3d15 210 const char *BlueNRGDevice::getVersion(void)
Wolfgang Betz 130:770ce14d3d15 211 {
Andrea Palmieri 216:7aa807180321 212 return getVersionString();
Wolfgang Betz 130:770ce14d3d15 213 }
Wolfgang Betz 130:770ce14d3d15 214
Wolfgang Betz 130:770ce14d3d15 215 /**************************************************************************/
Wolfgang Betz 130:770ce14d3d15 216 /*!
Wolfgang Betz 130:770ce14d3d15 217 @brief get reference to GAP object
Wolfgang Betz 130:770ce14d3d15 218 @param[in] void
Wolfgang Betz 130:770ce14d3d15 219 @returns Gap&
Wolfgang Betz 130:770ce14d3d15 220 */
Wolfgang Betz 130:770ce14d3d15 221 /**************************************************************************/
Wolfgang Betz 130:770ce14d3d15 222 Gap &BlueNRGDevice::getGap()
Wolfgang Betz 130:770ce14d3d15 223 {
Wolfgang Betz 130:770ce14d3d15 224 return BlueNRGGap::getInstance();
Wolfgang Betz 130:770ce14d3d15 225 }
Wolfgang Betz 130:770ce14d3d15 226
Wolfgang Betz 130:770ce14d3d15 227 const Gap &BlueNRGDevice::getGap() const
Wolfgang Betz 130:770ce14d3d15 228 {
Wolfgang Betz 130:770ce14d3d15 229 return BlueNRGGap::getInstance();
Wolfgang Betz 130:770ce14d3d15 230 }
Wolfgang Betz 130:770ce14d3d15 231
Wolfgang Betz 130:770ce14d3d15 232 /**************************************************************************/
Wolfgang Betz 130:770ce14d3d15 233 /*!
Wolfgang Betz 130:770ce14d3d15 234 @brief get reference to GATT server object
Wolfgang Betz 130:770ce14d3d15 235 @param[in] void
Wolfgang Betz 130:770ce14d3d15 236 @returns GattServer&
Wolfgang Betz 130:770ce14d3d15 237 */
Wolfgang Betz 130:770ce14d3d15 238 /**************************************************************************/
Wolfgang Betz 130:770ce14d3d15 239 GattServer &BlueNRGDevice::getGattServer()
Wolfgang Betz 130:770ce14d3d15 240 {
Wolfgang Betz 130:770ce14d3d15 241 return BlueNRGGattServer::getInstance();
Wolfgang Betz 130:770ce14d3d15 242 }
Wolfgang Betz 130:770ce14d3d15 243
Wolfgang Betz 130:770ce14d3d15 244 const GattServer &BlueNRGDevice::getGattServer() const
Wolfgang Betz 130:770ce14d3d15 245 {
Wolfgang Betz 130:770ce14d3d15 246 return BlueNRGGattServer::getInstance();
Wolfgang Betz 130:770ce14d3d15 247 }
Wolfgang Betz 130:770ce14d3d15 248
Wolfgang Betz 130:770ce14d3d15 249 /**************************************************************************/
Wolfgang Betz 130:770ce14d3d15 250 /*!
Andrea Palmieri 216:7aa807180321 251 @brief shut down the BLE device
Wolfgang Betz 130:770ce14d3d15 252 @param[out] error if any
Wolfgang Betz 130:770ce14d3d15 253 */
Wolfgang Betz 130:770ce14d3d15 254 /**************************************************************************/
Wolfgang Betz 130:770ce14d3d15 255 ble_error_t BlueNRGDevice::shutdown(void) {
Andrea Palmieri 216:7aa807180321 256 if (!isInitialized) {
Andrea Palmieri 216:7aa807180321 257 return BLE_ERROR_INITIALIZATION_INCOMPLETE;
Andrea Palmieri 216:7aa807180321 258 }
Andrea Palmieri 216:7aa807180321 259
Andrea Palmieri 229:9981f62cdb1a 260 /* Reset the BlueNRG device first */
Andrea Palmieri 229:9981f62cdb1a 261 reset();
Andrea Palmieri 229:9981f62cdb1a 262
Andrea Palmieri 229:9981f62cdb1a 263 /* Shutdown the BLE API and BlueNRG glue code */
Andrea Palmieri 229:9981f62cdb1a 264 ble_error_t error;
Andrea Palmieri 229:9981f62cdb1a 265
Andrea Palmieri 229:9981f62cdb1a 266 /* GattServer instance */
Andrea Palmieri 229:9981f62cdb1a 267 error = BlueNRGGattServer::getInstance().reset();
Andrea Palmieri 229:9981f62cdb1a 268 if (error != BLE_ERROR_NONE) {
Andrea Palmieri 229:9981f62cdb1a 269 return error;
Andrea Palmieri 229:9981f62cdb1a 270 }
Andrea Palmieri 229:9981f62cdb1a 271
Andrea Palmieri 229:9981f62cdb1a 272 /* GattClient instance */
Andrea Palmieri 229:9981f62cdb1a 273 error = BlueNRGGattClient::getInstance().reset();
Andrea Palmieri 229:9981f62cdb1a 274 if (error != BLE_ERROR_NONE) {
Andrea Palmieri 229:9981f62cdb1a 275 return error;
Andrea Palmieri 229:9981f62cdb1a 276 }
Andrea Palmieri 229:9981f62cdb1a 277
Andrea Palmieri 229:9981f62cdb1a 278 /* Gap instance */
Andrea Palmieri 229:9981f62cdb1a 279 error = BlueNRGGap::getInstance().reset();
Andrea Palmieri 229:9981f62cdb1a 280 if (error != BLE_ERROR_NONE) {
Andrea Palmieri 229:9981f62cdb1a 281 return error;
Andrea Palmieri 229:9981f62cdb1a 282 }
Andrea Palmieri 229:9981f62cdb1a 283
Andrea Palmieri 229:9981f62cdb1a 284 isInitialized = false;
Andrea Palmieri 229:9981f62cdb1a 285
Andrea Palmieri 229:9981f62cdb1a 286 return BLE_ERROR_NONE;
Andrea Palmieri 229:9981f62cdb1a 287
Wolfgang Betz 130:770ce14d3d15 288 }
Wolfgang Betz 130:770ce14d3d15 289
Wolfgang Betz 130:770ce14d3d15 290 /**
Wolfgang Betz 130:770ce14d3d15 291 * @brief Reads from BlueNRG SPI buffer and store data into local buffer.
Wolfgang Betz 130:770ce14d3d15 292 * @param buffer : Buffer where data from SPI are stored
Wolfgang Betz 130:770ce14d3d15 293 * @param buff_size: Buffer size
Wolfgang Betz 130:770ce14d3d15 294 * @retval int32_t : Number of read bytes
Wolfgang Betz 130:770ce14d3d15 295 */
Wolfgang Betz 130:770ce14d3d15 296 int32_t BlueNRGDevice::spiRead(uint8_t *buffer, uint8_t buff_size)
Wolfgang Betz 130:770ce14d3d15 297 {
Wolfgang Betz 130:770ce14d3d15 298 uint16_t byte_count;
Wolfgang Betz 130:770ce14d3d15 299 uint8_t len = 0;
Wolfgang Betz 130:770ce14d3d15 300 uint8_t char_ff = 0xff;
Wolfgang Betz 130:770ce14d3d15 301 volatile uint8_t read_char;
Wolfgang Betz 130:770ce14d3d15 302
Wolfgang Betz 130:770ce14d3d15 303 uint8_t i = 0;
Wolfgang Betz 130:770ce14d3d15 304 volatile uint8_t tmpreg;
Wolfgang Betz 130:770ce14d3d15 305
Wolfgang Betz 130:770ce14d3d15 306 uint8_t header_master[HEADER_SIZE] = {0x0b, 0x00, 0x00, 0x00, 0x00};
Wolfgang Betz 130:770ce14d3d15 307 uint8_t header_slave[HEADER_SIZE];
Wolfgang Betz 130:770ce14d3d15 308
Wolfgang Betz 130:770ce14d3d15 309 /* Select the chip */
Wolfgang Betz 130:770ce14d3d15 310 nCS_ = 0;
Wolfgang Betz 130:770ce14d3d15 311
Wolfgang Betz 130:770ce14d3d15 312 /* Read the header */
Wolfgang Betz 130:770ce14d3d15 313 for (i = 0; i < 5; i++)
Wolfgang Betz 130:770ce14d3d15 314 {
Wolfgang Betz 130:770ce14d3d15 315 tmpreg = spi_.write(header_master[i]);
Wolfgang Betz 130:770ce14d3d15 316 header_slave[i] = (uint8_t)(tmpreg);
Wolfgang Betz 130:770ce14d3d15 317 }
Wolfgang Betz 130:770ce14d3d15 318
Wolfgang Betz 130:770ce14d3d15 319 if (header_slave[0] == 0x02) {
Wolfgang Betz 130:770ce14d3d15 320 /* device is ready */
Wolfgang Betz 130:770ce14d3d15 321 byte_count = (header_slave[4]<<8)|header_slave[3];
Wolfgang Betz 130:770ce14d3d15 322
Wolfgang Betz 130:770ce14d3d15 323 if (byte_count > 0) {
Wolfgang Betz 130:770ce14d3d15 324
Wolfgang Betz 130:770ce14d3d15 325 /* avoid to read more data that size of the buffer */
Wolfgang Betz 130:770ce14d3d15 326 if (byte_count > buff_size){
Wolfgang Betz 130:770ce14d3d15 327 byte_count = buff_size;
Wolfgang Betz 130:770ce14d3d15 328 }
Wolfgang Betz 130:770ce14d3d15 329
Wolfgang Betz 130:770ce14d3d15 330 for (len = 0; len < byte_count; len++){
Wolfgang Betz 130:770ce14d3d15 331 read_char = spi_.write(char_ff);
Wolfgang Betz 130:770ce14d3d15 332 buffer[len] = read_char;
Wolfgang Betz 130:770ce14d3d15 333 }
Wolfgang Betz 130:770ce14d3d15 334 }
Wolfgang Betz 130:770ce14d3d15 335 }
Wolfgang Betz 130:770ce14d3d15 336 /* Release CS line to deselect the chip */
Wolfgang Betz 130:770ce14d3d15 337 nCS_ = 1;
Wolfgang Betz 130:770ce14d3d15 338
Wolfgang Betz 130:770ce14d3d15 339 // Add a small delay to give time to the BlueNRG to set the IRQ pin low
Wolfgang Betz 130:770ce14d3d15 340 // to avoid a useless SPI read at the end of the transaction
Wolfgang Betz 130:770ce14d3d15 341 for(volatile int i = 0; i < 2; i++)__NOP();
Wolfgang Betz 130:770ce14d3d15 342
Wolfgang Betz 130:770ce14d3d15 343 #ifdef PRINT_CSV_FORMAT
Wolfgang Betz 130:770ce14d3d15 344 if (len > 0) {
Wolfgang Betz 130:770ce14d3d15 345 print_csv_time();
Wolfgang Betz 130:770ce14d3d15 346 for (int i=0; i<len; i++) {
Wolfgang Betz 130:770ce14d3d15 347 PRINT_CSV(" %02x", buffer[i]);
Wolfgang Betz 130:770ce14d3d15 348 }
Wolfgang Betz 130:770ce14d3d15 349 PRINT_CSV("\n");
Wolfgang Betz 130:770ce14d3d15 350 }
Wolfgang Betz 130:770ce14d3d15 351 #endif
Wolfgang Betz 130:770ce14d3d15 352
Wolfgang Betz 130:770ce14d3d15 353 return len;
Wolfgang Betz 130:770ce14d3d15 354 }
Wolfgang Betz 130:770ce14d3d15 355
Wolfgang Betz 130:770ce14d3d15 356 /**
Wolfgang Betz 130:770ce14d3d15 357 * @brief Writes data from local buffer to SPI.
Wolfgang Betz 130:770ce14d3d15 358 * @param data1 : First data buffer to be written
Wolfgang Betz 130:770ce14d3d15 359 * @param data2 : Second data buffer to be written
Wolfgang Betz 130:770ce14d3d15 360 * @param Nb_bytes1: Size of first data buffer to be written
Wolfgang Betz 130:770ce14d3d15 361 * @param Nb_bytes2: Size of second data buffer to be written
Wolfgang Betz 130:770ce14d3d15 362 * @retval Number of read bytes
Wolfgang Betz 130:770ce14d3d15 363 */
Wolfgang Betz 130:770ce14d3d15 364 int32_t BlueNRGDevice::spiWrite(uint8_t* data1,
Wolfgang Betz 130:770ce14d3d15 365 uint8_t* data2, uint8_t Nb_bytes1, uint8_t Nb_bytes2)
Wolfgang Betz 130:770ce14d3d15 366 {
Wolfgang Betz 130:770ce14d3d15 367 int32_t result = 0;
Wolfgang Betz 130:770ce14d3d15 368 uint32_t i;
Wolfgang Betz 130:770ce14d3d15 369 volatile uint8_t tmpreg;
Wolfgang Betz 130:770ce14d3d15 370
Wolfgang Betz 130:770ce14d3d15 371 unsigned char header_master[HEADER_SIZE] = {0x0a, 0x00, 0x00, 0x00, 0x00};
Wolfgang Betz 130:770ce14d3d15 372 unsigned char header_slave[HEADER_SIZE] = {0xaa, 0x00, 0x00, 0x00, 0x00};
Wolfgang Betz 130:770ce14d3d15 373
Wolfgang Betz 130:770ce14d3d15 374 disable_irq();
Wolfgang Betz 130:770ce14d3d15 375
Wolfgang Betz 130:770ce14d3d15 376 /* CS reset */
Wolfgang Betz 130:770ce14d3d15 377 nCS_ = 0;
Wolfgang Betz 130:770ce14d3d15 378
Wolfgang Betz 130:770ce14d3d15 379 /* Exchange header */
Wolfgang Betz 130:770ce14d3d15 380 for (i = 0; i < 5; i++)
Wolfgang Betz 130:770ce14d3d15 381 {
Wolfgang Betz 130:770ce14d3d15 382 tmpreg = spi_.write(header_master[i]);
Wolfgang Betz 130:770ce14d3d15 383 header_slave[i] = tmpreg;
Wolfgang Betz 130:770ce14d3d15 384 }
Wolfgang Betz 130:770ce14d3d15 385
Wolfgang Betz 130:770ce14d3d15 386 if (header_slave[0] == 0x02) {
Wolfgang Betz 130:770ce14d3d15 387 /* SPI is ready */
Wolfgang Betz 130:770ce14d3d15 388 if (header_slave[1] >= (Nb_bytes1+Nb_bytes2)) {
Wolfgang Betz 130:770ce14d3d15 389
Wolfgang Betz 130:770ce14d3d15 390 /* Buffer is big enough */
Wolfgang Betz 130:770ce14d3d15 391 for (i = 0; i < Nb_bytes1; i++) {
Wolfgang Betz 130:770ce14d3d15 392 spi_.write(*(data1 + i));
Wolfgang Betz 130:770ce14d3d15 393 }
Wolfgang Betz 130:770ce14d3d15 394 for (i = 0; i < Nb_bytes2; i++) {
Wolfgang Betz 130:770ce14d3d15 395 spi_.write(*(data2 + i));
Wolfgang Betz 130:770ce14d3d15 396 }
Wolfgang Betz 130:770ce14d3d15 397 } else {
Wolfgang Betz 130:770ce14d3d15 398 /* Buffer is too small */
Wolfgang Betz 130:770ce14d3d15 399 result = -2;
Wolfgang Betz 130:770ce14d3d15 400 }
Wolfgang Betz 130:770ce14d3d15 401 } else {
Wolfgang Betz 130:770ce14d3d15 402 /* SPI is not ready */
Wolfgang Betz 130:770ce14d3d15 403 result = -1;
Wolfgang Betz 130:770ce14d3d15 404 }
Wolfgang Betz 130:770ce14d3d15 405
Wolfgang Betz 130:770ce14d3d15 406 /* Release CS line */
Wolfgang Betz 130:770ce14d3d15 407 //HAL_GPIO_WritePin(BNRG_SPI_CS_PORT, BNRG_SPI_CS_PIN, GPIO_PIN_SET);
Wolfgang Betz 130:770ce14d3d15 408 nCS_ = 1;
Wolfgang Betz 130:770ce14d3d15 409
Wolfgang Betz 130:770ce14d3d15 410 enable_irq();
Wolfgang Betz 130:770ce14d3d15 411
Wolfgang Betz 130:770ce14d3d15 412 return result;
Wolfgang Betz 130:770ce14d3d15 413 }
Wolfgang Betz 130:770ce14d3d15 414
Wolfgang Betz 130:770ce14d3d15 415 bool BlueNRGDevice::dataPresent()
Wolfgang Betz 130:770ce14d3d15 416 {
Wolfgang Betz 130:770ce14d3d15 417 return (irq_ == 1);
Wolfgang Betz 130:770ce14d3d15 418 }
Wolfgang Betz 130:770ce14d3d15 419
Wolfgang Betz 130:770ce14d3d15 420 void BlueNRGDevice::disable_irq()
Wolfgang Betz 130:770ce14d3d15 421 {
Wolfgang Betz 130:770ce14d3d15 422 irq_.disable_irq();
Wolfgang Betz 130:770ce14d3d15 423 }
Wolfgang Betz 130:770ce14d3d15 424
Wolfgang Betz 130:770ce14d3d15 425 void BlueNRGDevice::enable_irq()
Wolfgang Betz 130:770ce14d3d15 426 {
Wolfgang Betz 130:770ce14d3d15 427 irq_.enable_irq();
Wolfgang Betz 130:770ce14d3d15 428 }