BLE_API for nRF51

Fork of BLE_API by Bluetooth Low Energy

Committer:
rgrover1
Date:
Fri Aug 07 15:55:21 2015 +0100
Revision:
769:2d236d9afa9e
Parent:
765:4cd91998cd48
Child:
895:a43c4a9bde02
Synchronized with git rev 24a98921
Author: Rohit Grover
fix #64: GapAdvertisingData::getPayload() should return the payload pointer regardless of len.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
rgrover1 710:b2e1a2660ec2 1 /* mbed Microcontroller Library
rgrover1 710:b2e1a2660ec2 2 * Copyright (c) 2006-2013 ARM Limited
rgrover1 710:b2e1a2660ec2 3 *
rgrover1 710:b2e1a2660ec2 4 * Licensed under the Apache License, Version 2.0 (the "License");
rgrover1 710:b2e1a2660ec2 5 * you may not use this file except in compliance with the License.
rgrover1 710:b2e1a2660ec2 6 * You may obtain a copy of the License at
rgrover1 710:b2e1a2660ec2 7 *
rgrover1 710:b2e1a2660ec2 8 * http://www.apache.org/licenses/LICENSE-2.0
rgrover1 710:b2e1a2660ec2 9 *
rgrover1 710:b2e1a2660ec2 10 * Unless required by applicable law or agreed to in writing, software
rgrover1 710:b2e1a2660ec2 11 * distributed under the License is distributed on an "AS IS" BASIS,
rgrover1 710:b2e1a2660ec2 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
rgrover1 710:b2e1a2660ec2 13 * See the License for the specific language governing permissions and
rgrover1 710:b2e1a2660ec2 14 * limitations under the License.
rgrover1 710:b2e1a2660ec2 15 */
rgrover1 710:b2e1a2660ec2 16
rgrover1 710:b2e1a2660ec2 17 #ifndef __GAP_ADVERTISING_DATA_H__
rgrover1 710:b2e1a2660ec2 18 #define __GAP_ADVERTISING_DATA_H__
rgrover1 710:b2e1a2660ec2 19
rgrover1 710:b2e1a2660ec2 20 #include <stdint.h>
rgrover1 710:b2e1a2660ec2 21 #include <string.h>
rgrover1 710:b2e1a2660ec2 22
rgrover1 710:b2e1a2660ec2 23 #include "blecommon.h"
rgrover1 710:b2e1a2660ec2 24
rgrover1 710:b2e1a2660ec2 25 #define GAP_ADVERTISING_DATA_MAX_PAYLOAD (31)
rgrover1 710:b2e1a2660ec2 26
rgrover1 710:b2e1a2660ec2 27 /**************************************************************************/
rgrover1 710:b2e1a2660ec2 28 /*!
rgrover1 710:b2e1a2660ec2 29 \brief
rgrover1 710:b2e1a2660ec2 30 This class provides several helper functions to generate properly
rgrover1 710:b2e1a2660ec2 31 formatted GAP Advertising and Scan Response data payloads
rgrover1 710:b2e1a2660ec2 32
rgrover1 710:b2e1a2660ec2 33 \note
rgrover1 710:b2e1a2660ec2 34 See Bluetooth Specification 4.0 (Vol. 3), Part C, Section 11 and 18
rgrover1 710:b2e1a2660ec2 35 for further information on Advertising and Scan Response data.
rgrover1 710:b2e1a2660ec2 36
rgrover1 710:b2e1a2660ec2 37 \par Advertising and Scan Response Payloads
rgrover1 710:b2e1a2660ec2 38 Advertising data and Scan Response data are organized around a set of
rgrover1 710:b2e1a2660ec2 39 data types called 'AD types' in Bluetooth 4.0 (see the Bluetooth Core
rgrover1 710:b2e1a2660ec2 40 Specification v4.0, Vol. 3, Part C, Sections 11 and 18).
rgrover1 710:b2e1a2660ec2 41
rgrover1 710:b2e1a2660ec2 42 \par
rgrover1 710:b2e1a2660ec2 43 Each AD type has it's own standardized 'assigned number', as defined
rgrover1 710:b2e1a2660ec2 44 by the Bluetooth SIG:
rgrover1 710:b2e1a2660ec2 45 https://www.bluetooth.org/en-us/specification/assigned-numbers/generic-access-profile
rgrover1 710:b2e1a2660ec2 46
rgrover1 710:b2e1a2660ec2 47 \par
rgrover1 710:b2e1a2660ec2 48 For convenience sake, all appropriate AD types have been encapsulated
rgrover1 710:b2e1a2660ec2 49 into GapAdvertisingData::DataType.
rgrover1 710:b2e1a2660ec2 50
rgrover1 710:b2e1a2660ec2 51 \par
rgrover1 710:b2e1a2660ec2 52 Before the AD Types and their payload (if any) can be inserted into
rgrover1 710:b2e1a2660ec2 53 the Advertising or Scan Response frames, they need to be formatted as
rgrover1 710:b2e1a2660ec2 54 follows:
rgrover1 710:b2e1a2660ec2 55
rgrover1 710:b2e1a2660ec2 56 \li \c Record length (1 byte)
rgrover1 710:b2e1a2660ec2 57 \li \c AD Type (1 byte)
rgrover1 710:b2e1a2660ec2 58 \li \c AD payload (optional, only present if record length > 1)
rgrover1 710:b2e1a2660ec2 59
rgrover1 710:b2e1a2660ec2 60 \par
rgrover1 710:b2e1a2660ec2 61 This class takes care of properly formatting the payload, performs
rgrover1 710:b2e1a2660ec2 62 some basic checks on the payload length, and tries to avoid common
rgrover1 710:b2e1a2660ec2 63 errors like adding an exclusive AD field twice in the Advertising
rgrover1 710:b2e1a2660ec2 64 or Scan Response payload.
rgrover1 710:b2e1a2660ec2 65
rgrover1 710:b2e1a2660ec2 66 \par EXAMPLE
rgrover1 710:b2e1a2660ec2 67
rgrover1 710:b2e1a2660ec2 68 \code
rgrover1 710:b2e1a2660ec2 69
rgrover1 710:b2e1a2660ec2 70 // ToDo
rgrover1 710:b2e1a2660ec2 71
rgrover1 710:b2e1a2660ec2 72 \endcode
rgrover1 710:b2e1a2660ec2 73 */
rgrover1 710:b2e1a2660ec2 74 /**************************************************************************/
rgrover1 710:b2e1a2660ec2 75 class GapAdvertisingData
rgrover1 710:b2e1a2660ec2 76 {
rgrover1 710:b2e1a2660ec2 77 public:
rgrover1 710:b2e1a2660ec2 78 /**********************************************************************/
rgrover1 710:b2e1a2660ec2 79 /*!
rgrover1 710:b2e1a2660ec2 80 \brief
rgrover1 710:b2e1a2660ec2 81 A list of Advertising Data types commonly used by peripherals.
rgrover1 710:b2e1a2660ec2 82 These AD types are used to describe the capabilities of the
rgrover1 710:b2e1a2660ec2 83 peripheral, and get inserted inside the advertising or scan
rgrover1 710:b2e1a2660ec2 84 response payloads.
rgrover1 710:b2e1a2660ec2 85
rgrover1 710:b2e1a2660ec2 86 \par Source
rgrover1 710:b2e1a2660ec2 87 \li \c Bluetooth Core Specification 4.0 (Vol. 3), Part C, Section 11, 18
rgrover1 710:b2e1a2660ec2 88 \li \c https://www.bluetooth.org/en-us/specification/assigned-numbers/generic-access-profile
rgrover1 710:b2e1a2660ec2 89 */
rgrover1 710:b2e1a2660ec2 90 /**********************************************************************/
rgrover1 756:503c4bd89a3d 91 enum DataType_t {
rgrover1 710:b2e1a2660ec2 92 FLAGS = 0x01, /**< \ref *Flags */
rgrover1 710:b2e1a2660ec2 93 INCOMPLETE_LIST_16BIT_SERVICE_IDS = 0x02, /**< Incomplete list of 16-bit Service IDs */
rgrover1 710:b2e1a2660ec2 94 COMPLETE_LIST_16BIT_SERVICE_IDS = 0x03, /**< Complete list of 16-bit Service IDs */
rgrover1 710:b2e1a2660ec2 95 INCOMPLETE_LIST_32BIT_SERVICE_IDS = 0x04, /**< Incomplete list of 32-bit Service IDs (not relevant for Bluetooth 4.0) */
rgrover1 710:b2e1a2660ec2 96 COMPLETE_LIST_32BIT_SERVICE_IDS = 0x05, /**< Complete list of 32-bit Service IDs (not relevant for Bluetooth 4.0) */
rgrover1 710:b2e1a2660ec2 97 INCOMPLETE_LIST_128BIT_SERVICE_IDS = 0x06, /**< Incomplete list of 128-bit Service IDs */
rgrover1 710:b2e1a2660ec2 98 COMPLETE_LIST_128BIT_SERVICE_IDS = 0x07, /**< Complete list of 128-bit Service IDs */
rgrover1 710:b2e1a2660ec2 99 SHORTENED_LOCAL_NAME = 0x08, /**< Shortened Local Name */
rgrover1 710:b2e1a2660ec2 100 COMPLETE_LOCAL_NAME = 0x09, /**< Complete Local Name */
rgrover1 710:b2e1a2660ec2 101 TX_POWER_LEVEL = 0x0A, /**< TX Power Level (in dBm) */
rgrover1 710:b2e1a2660ec2 102 DEVICE_ID = 0x10, /**< Device ID */
rgrover1 710:b2e1a2660ec2 103 SLAVE_CONNECTION_INTERVAL_RANGE = 0x12, /**< Slave Connection Interval Range */
rgrover1 710:b2e1a2660ec2 104 SERVICE_DATA = 0x16, /**< Service Data */
rgrover1 710:b2e1a2660ec2 105 APPEARANCE = 0x19, /**< \ref Appearance */
rgrover1 710:b2e1a2660ec2 106 ADVERTISING_INTERVAL = 0x1A, /**< Advertising Interval */
rgrover1 710:b2e1a2660ec2 107 MANUFACTURER_SPECIFIC_DATA = 0xFF /**< Manufacturer Specific Data */
rgrover1 710:b2e1a2660ec2 108 };
rgrover1 756:503c4bd89a3d 109 typedef enum DataType_t DataType; /* Deprecated type alias. This may be dropped in a future release. */
rgrover1 710:b2e1a2660ec2 110
rgrover1 710:b2e1a2660ec2 111 /**********************************************************************/
rgrover1 710:b2e1a2660ec2 112 /*!
rgrover1 710:b2e1a2660ec2 113 \brief
rgrover1 710:b2e1a2660ec2 114 A list of values for the FLAGS AD Type
rgrover1 710:b2e1a2660ec2 115
rgrover1 710:b2e1a2660ec2 116 \note
rgrover1 710:b2e1a2660ec2 117 You can use more than one value in the FLAGS AD Type (ex.
rgrover1 710:b2e1a2660ec2 118 LE_GENERAL_DISCOVERABLE and BREDR_NOT_SUPPORTED).
rgrover1 710:b2e1a2660ec2 119
rgrover1 710:b2e1a2660ec2 120 \par Source
rgrover1 710:b2e1a2660ec2 121 \li \c Bluetooth Core Specification 4.0 (Vol. 3), Part C, Section 18.1
rgrover1 710:b2e1a2660ec2 122 */
rgrover1 710:b2e1a2660ec2 123 /**********************************************************************/
rgrover1 756:503c4bd89a3d 124 enum Flags_t {
rgrover1 710:b2e1a2660ec2 125 LE_LIMITED_DISCOVERABLE = 0x01, /**< *Peripheral device is discoverable for a limited period of time */
rgrover1 710:b2e1a2660ec2 126 LE_GENERAL_DISCOVERABLE = 0x02, /**< Peripheral device is discoverable at any moment */
rgrover1 710:b2e1a2660ec2 127 BREDR_NOT_SUPPORTED = 0x04, /**< Peripheral device is LE only */
rgrover1 710:b2e1a2660ec2 128 SIMULTANEOUS_LE_BREDR_C = 0x08, /**< Not relevant - central mode only */
rgrover1 710:b2e1a2660ec2 129 SIMULTANEOUS_LE_BREDR_H = 0x10 /**< Not relevant - central mode only */
rgrover1 710:b2e1a2660ec2 130 };
rgrover1 756:503c4bd89a3d 131 typedef enum Flags_t Flags; /* Deprecated type alias. This may be dropped in a future release. */
rgrover1 710:b2e1a2660ec2 132
rgrover1 710:b2e1a2660ec2 133 /**********************************************************************/
rgrover1 710:b2e1a2660ec2 134 /*!
rgrover1 710:b2e1a2660ec2 135 \brief
rgrover1 710:b2e1a2660ec2 136 A list of values for the APPEARANCE AD Type, which describes the
rgrover1 710:b2e1a2660ec2 137 physical shape or appearance of the device
rgrover1 710:b2e1a2660ec2 138
rgrover1 710:b2e1a2660ec2 139 \par Source
rgrover1 710:b2e1a2660ec2 140 \li \c Bluetooth Core Specification Supplement, Part A, Section 1.12
rgrover1 710:b2e1a2660ec2 141 \li \c Bluetooth Core Specification 4.0 (Vol. 3), Part C, Section 12.2
rgrover1 710:b2e1a2660ec2 142 \li \c https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.gap.appearance.xml
rgrover1 710:b2e1a2660ec2 143 */
rgrover1 710:b2e1a2660ec2 144 /**********************************************************************/
rgrover1 756:503c4bd89a3d 145 enum Appearance_t {
rgrover1 710:b2e1a2660ec2 146 UNKNOWN = 0, /**< Unknown of unspecified appearance type */
rgrover1 710:b2e1a2660ec2 147 GENERIC_PHONE = 64, /**< Generic Phone */
rgrover1 710:b2e1a2660ec2 148 GENERIC_COMPUTER = 128, /**< Generic Computer */
rgrover1 710:b2e1a2660ec2 149 GENERIC_WATCH = 192, /**< Generic Watch */
rgrover1 710:b2e1a2660ec2 150 WATCH_SPORTS_WATCH = 193, /**< Sports Watch */
rgrover1 710:b2e1a2660ec2 151 GENERIC_CLOCK = 256, /**< Generic Clock */
rgrover1 710:b2e1a2660ec2 152 GENERIC_DISPLAY = 320, /**< Generic Display */
rgrover1 710:b2e1a2660ec2 153 GENERIC_REMOTE_CONTROL = 384, /**< Generic Remote Control */
rgrover1 710:b2e1a2660ec2 154 GENERIC_EYE_GLASSES = 448, /**< Generic Eye Glasses */
rgrover1 710:b2e1a2660ec2 155 GENERIC_TAG = 512, /**< Generic Tag */
rgrover1 710:b2e1a2660ec2 156 GENERIC_KEYRING = 576, /**< Generic Keyring */
rgrover1 710:b2e1a2660ec2 157 GENERIC_MEDIA_PLAYER = 640, /**< Generic Media Player */
rgrover1 710:b2e1a2660ec2 158 GENERIC_BARCODE_SCANNER = 704, /**< Generic Barcode Scanner */
rgrover1 710:b2e1a2660ec2 159 GENERIC_THERMOMETER = 768, /**< Generic Thermometer */
rgrover1 710:b2e1a2660ec2 160 THERMOMETER_EAR = 769, /**< Ear Thermometer */
rgrover1 710:b2e1a2660ec2 161 GENERIC_HEART_RATE_SENSOR = 832, /**< Generic Heart Rate Sensor */
rgrover1 710:b2e1a2660ec2 162 HEART_RATE_SENSOR_HEART_RATE_BELT = 833, /**< Belt Heart Rate Sensor */
rgrover1 710:b2e1a2660ec2 163 GENERIC_BLOOD_PRESSURE = 896, /**< Generic Blood Pressure */
rgrover1 710:b2e1a2660ec2 164 BLOOD_PRESSURE_ARM = 897, /**< Arm Blood Pressure */
rgrover1 710:b2e1a2660ec2 165 BLOOD_PRESSURE_WRIST = 898, /**< Wrist Blood Pressure */
rgrover1 710:b2e1a2660ec2 166 HUMAN_INTERFACE_DEVICE_HID = 960, /**< Human Interface Device (HID) */
rgrover1 710:b2e1a2660ec2 167 KEYBOARD = 961, /**< Keyboard */
rgrover1 710:b2e1a2660ec2 168 MOUSE = 962, /**< Mouse */
rgrover1 710:b2e1a2660ec2 169 JOYSTICK = 963, /**< Joystick */
rgrover1 710:b2e1a2660ec2 170 GAMEPAD = 964, /**< Gamepad */
rgrover1 710:b2e1a2660ec2 171 DIGITIZER_TABLET = 965, /**< Digitizer Tablet */
rgrover1 710:b2e1a2660ec2 172 CARD_READER = 966, /**< Card Read */
rgrover1 710:b2e1a2660ec2 173 DIGITAL_PEN = 967, /**< Digital Pen */
rgrover1 710:b2e1a2660ec2 174 BARCODE_SCANNER = 968, /**< Barcode Scanner */
rgrover1 710:b2e1a2660ec2 175 GENERIC_GLUCOSE_METER = 1024, /**< Generic Glucose Meter */
rgrover1 710:b2e1a2660ec2 176 GENERIC_RUNNING_WALKING_SENSOR = 1088, /**< Generic Running/Walking Sensor */
rgrover1 710:b2e1a2660ec2 177 RUNNING_WALKING_SENSOR_IN_SHOE = 1089, /**< In Shoe Running/Walking Sensor */
rgrover1 710:b2e1a2660ec2 178 RUNNING_WALKING_SENSOR_ON_SHOE = 1090, /**< On Shoe Running/Walking Sensor */
rgrover1 710:b2e1a2660ec2 179 RUNNING_WALKING_SENSOR_ON_HIP = 1091, /**< On Hip Running/Walking Sensor */
rgrover1 710:b2e1a2660ec2 180 GENERIC_CYCLING = 1152, /**< Generic Cycling */
rgrover1 710:b2e1a2660ec2 181 CYCLING_CYCLING_COMPUTER = 1153, /**< Cycling Computer */
rgrover1 710:b2e1a2660ec2 182 CYCLING_SPEED_SENSOR = 1154, /**< Cycling Speed Senspr */
rgrover1 710:b2e1a2660ec2 183 CYCLING_CADENCE_SENSOR = 1155, /**< Cycling Cadence Sensor */
rgrover1 710:b2e1a2660ec2 184 CYCLING_POWER_SENSOR = 1156, /**< Cycling Power Sensor */
rgrover1 710:b2e1a2660ec2 185 CYCLING_SPEED_AND_CADENCE_SENSOR = 1157, /**< Cycling Speed and Cadence Sensor */
rgrover1 710:b2e1a2660ec2 186 PULSE_OXIMETER_GENERIC = 3136, /**< Generic Pulse Oximeter */
rgrover1 710:b2e1a2660ec2 187 PULSE_OXIMETER_FINGERTIP = 3137, /**< Fingertip Pulse Oximeter */
rgrover1 710:b2e1a2660ec2 188 PULSE_OXIMETER_WRIST_WORN = 3138, /**< Wrist Worn Pulse Oximeter */
rgrover1 710:b2e1a2660ec2 189 OUTDOOR_GENERIC = 5184, /**< Generic Outdoor */
rgrover1 710:b2e1a2660ec2 190 OUTDOOR_LOCATION_DISPLAY_DEVICE = 5185, /**< Outdoor Location Display Device */
rgrover1 710:b2e1a2660ec2 191 OUTDOOR_LOCATION_AND_NAVIGATION_DISPLAY_DEVICE = 5186, /**< Outdoor Location and Navigation Display Device */
rgrover1 710:b2e1a2660ec2 192 OUTDOOR_LOCATION_POD = 5187, /**< Outdoor Location Pod */
rgrover1 710:b2e1a2660ec2 193 OUTDOOR_LOCATION_AND_NAVIGATION_POD = 5188 /**< Outdoor Location and Navigation Pod */
rgrover1 710:b2e1a2660ec2 194 };
rgrover1 756:503c4bd89a3d 195 typedef enum Appearance_t Appearance; /* Deprecated type alias. This may be dropped in a future release. */
rgrover1 710:b2e1a2660ec2 196
rgrover1 710:b2e1a2660ec2 197 GapAdvertisingData(void) : _payload(), _payloadLen(0), _appearance(GENERIC_TAG) {
rgrover1 710:b2e1a2660ec2 198 /* empty */
rgrover1 710:b2e1a2660ec2 199 }
rgrover1 710:b2e1a2660ec2 200
rgrover1 710:b2e1a2660ec2 201 /**
rgrover1 710:b2e1a2660ec2 202 * Adds advertising data based on the specified AD type (see DataType)
rgrover1 710:b2e1a2660ec2 203 *
rgrover1 710:b2e1a2660ec2 204 * @param advDataType The Advertising 'DataType' to add
rgrover1 710:b2e1a2660ec2 205 * @param payload Pointer to the payload contents
rgrover1 710:b2e1a2660ec2 206 * @param len Size of the payload in bytes
rgrover1 710:b2e1a2660ec2 207 *
rgrover1 710:b2e1a2660ec2 208 * @return BLE_ERROR_BUFFER_OVERFLOW if the specified data would cause the
rgrover1 710:b2e1a2660ec2 209 * advertising buffer to overflow, else BLE_ERROR_NONE.
rgrover1 710:b2e1a2660ec2 210 */
rgrover1 710:b2e1a2660ec2 211 ble_error_t addData(DataType advDataType, const uint8_t *payload, uint8_t len)
rgrover1 765:4cd91998cd48 212 {
rgrover1 710:b2e1a2660ec2 213 /* ToDo: Check if an AD type already exists and if the existing */
rgrover1 710:b2e1a2660ec2 214 /* value is exclusive or not (flags, etc.) */
rgrover1 710:b2e1a2660ec2 215
rgrover1 710:b2e1a2660ec2 216 /* Make sure we don't exceed the 31 byte payload limit */
rgrover1 710:b2e1a2660ec2 217 if (_payloadLen + len + 2 > GAP_ADVERTISING_DATA_MAX_PAYLOAD) {
rgrover1 710:b2e1a2660ec2 218 return BLE_ERROR_BUFFER_OVERFLOW;
rgrover1 710:b2e1a2660ec2 219 }
rgrover1 710:b2e1a2660ec2 220
rgrover1 710:b2e1a2660ec2 221 /* Field length */
rgrover1 710:b2e1a2660ec2 222 memset(&_payload[_payloadLen], len + 1, 1);
rgrover1 710:b2e1a2660ec2 223 _payloadLen++;
rgrover1 710:b2e1a2660ec2 224
rgrover1 710:b2e1a2660ec2 225 /* Field ID */
rgrover1 710:b2e1a2660ec2 226 memset(&_payload[_payloadLen], (uint8_t)advDataType, 1);
rgrover1 710:b2e1a2660ec2 227 _payloadLen++;
rgrover1 710:b2e1a2660ec2 228
rgrover1 710:b2e1a2660ec2 229 /* Payload */
rgrover1 710:b2e1a2660ec2 230 memcpy(&_payload[_payloadLen], payload, len);
rgrover1 710:b2e1a2660ec2 231 _payloadLen += len;
rgrover1 710:b2e1a2660ec2 232
rgrover1 710:b2e1a2660ec2 233 return BLE_ERROR_NONE;
rgrover1 710:b2e1a2660ec2 234 }
rgrover1 710:b2e1a2660ec2 235
rgrover1 710:b2e1a2660ec2 236 /**
rgrover1 765:4cd91998cd48 237 * Update a particular ADV field in the advertising payload (based on
rgrover1 765:4cd91998cd48 238 * matching type and length). Note: the length of the new data must be the
rgrover1 765:4cd91998cd48 239 * same as the old one.
rgrover1 763:36c3e2b1f1ae 240 *
rgrover1 765:4cd91998cd48 241 * @param[in] advDataType The Advertising 'DataType' to add.
rgrover1 765:4cd91998cd48 242 * @param[in] payload Pointer to the payload contents.
rgrover1 765:4cd91998cd48 243 * @param[in] len Size of the payload in bytes.
rgrover1 763:36c3e2b1f1ae 244 *
rgrover1 763:36c3e2b1f1ae 245 * @return BLE_ERROR_UNSPECIFIED if the specified field is not found, else
rgrover1 763:36c3e2b1f1ae 246 * BLE_ERROR_NONE.
rgrover1 763:36c3e2b1f1ae 247 */
rgrover1 765:4cd91998cd48 248 ble_error_t updateData(DataType_t advDataType, const uint8_t *payload, uint8_t len)
rgrover1 765:4cd91998cd48 249 {
rgrover1 765:4cd91998cd48 250 if ((payload == NULL) || (len == 0)) {
rgrover1 765:4cd91998cd48 251 return BLE_ERROR_INVALID_PARAM;
rgrover1 765:4cd91998cd48 252 }
rgrover1 765:4cd91998cd48 253
rgrover1 765:4cd91998cd48 254 /* A local struct to describe an ADV field. This definition comes from the Bluetooth Core Spec. (v4.2) Part C, Section 11. */
rgrover1 765:4cd91998cd48 255 struct ADVField_t {
rgrover1 765:4cd91998cd48 256 uint8_t len; /* Describes the length (in bytes) of the following 'type' and 'bytes'. */
rgrover1 765:4cd91998cd48 257 uint8_t type; /* Should have the same representation of DataType_t (above). */
rgrover1 765:4cd91998cd48 258 uint8_t bytes[0]; /* A placeholder for variable length data. */
rgrover1 765:4cd91998cd48 259 };
rgrover1 765:4cd91998cd48 260
rgrover1 765:4cd91998cd48 261 /* Iterate over the adv fields looking for the first match. */
rgrover1 763:36c3e2b1f1ae 262 uint8_t byteIndex = 0;
rgrover1 763:36c3e2b1f1ae 263 while (byteIndex < _payloadLen) {
rgrover1 765:4cd91998cd48 264 ADVField_t *currentADV = (ADVField_t *)&_payload[byteIndex];
rgrover1 765:4cd91998cd48 265 if ((currentADV->len == (len + 1)) && /* incoming 'len' only describes the payload, whereas ADV->len describes 'type + payload' */
rgrover1 765:4cd91998cd48 266 (currentADV->type == advDataType)) {
rgrover1 765:4cd91998cd48 267 memcpy(currentADV->bytes, payload, len);
rgrover1 763:36c3e2b1f1ae 268 return BLE_ERROR_NONE;
rgrover1 763:36c3e2b1f1ae 269 }
rgrover1 765:4cd91998cd48 270
rgrover1 765:4cd91998cd48 271 byteIndex += (currentADV->len + 1); /* advance by len+1; '+1' is needed to span the len field itself. */
rgrover1 763:36c3e2b1f1ae 272 }
rgrover1 763:36c3e2b1f1ae 273
rgrover1 763:36c3e2b1f1ae 274 return BLE_ERROR_UNSPECIFIED;
rgrover1 763:36c3e2b1f1ae 275 }
rgrover1 763:36c3e2b1f1ae 276
rgrover1 763:36c3e2b1f1ae 277 /**
rgrover1 710:b2e1a2660ec2 278 * Helper function to add APPEARANCE data to the advertising payload
rgrover1 710:b2e1a2660ec2 279 *
rgrover1 710:b2e1a2660ec2 280 * @param appearance
rgrover1 710:b2e1a2660ec2 281 * The APPEARANCE value to add
rgrover1 710:b2e1a2660ec2 282 *
rgrover1 710:b2e1a2660ec2 283 * @return BLE_ERROR_BUFFER_OVERFLOW if the specified data would cause the
rgrover1 710:b2e1a2660ec2 284 * advertising buffer to overflow, else BLE_ERROR_NONE.
rgrover1 710:b2e1a2660ec2 285 */
rgrover1 710:b2e1a2660ec2 286 ble_error_t addAppearance(Appearance appearance = GENERIC_TAG) {
rgrover1 710:b2e1a2660ec2 287 _appearance = appearance;
rgrover1 710:b2e1a2660ec2 288 return addData(GapAdvertisingData::APPEARANCE, (uint8_t *)&appearance, 2);
rgrover1 710:b2e1a2660ec2 289 }
rgrover1 710:b2e1a2660ec2 290
rgrover1 710:b2e1a2660ec2 291 /**
rgrover1 710:b2e1a2660ec2 292 * Helper function to add FLAGS data to the advertising payload.
rgrover1 710:b2e1a2660ec2 293 * @param flags
rgrover1 710:b2e1a2660ec2 294 * LE_LIMITED_DISCOVERABLE
rgrover1 710:b2e1a2660ec2 295 * The peripheral is discoverable for a limited period of time.
rgrover1 710:b2e1a2660ec2 296 * LE_GENERAL_DISCOVERABLE
rgrover1 710:b2e1a2660ec2 297 * The peripheral is permanently discoverable.
rgrover1 710:b2e1a2660ec2 298 * BREDR_NOT_SUPPORTED
rgrover1 710:b2e1a2660ec2 299 * This peripheral is a Bluetooth Low Energy only device (no EDR support).
rgrover1 710:b2e1a2660ec2 300 *
rgrover1 710:b2e1a2660ec2 301 * @return BLE_ERROR_BUFFER_OVERFLOW if the specified data would cause the
rgrover1 710:b2e1a2660ec2 302 * advertising buffer to overflow, else BLE_ERROR_NONE.
rgrover1 710:b2e1a2660ec2 303 */
rgrover1 710:b2e1a2660ec2 304 ble_error_t addFlags(uint8_t flags = LE_GENERAL_DISCOVERABLE) {
rgrover1 710:b2e1a2660ec2 305 return addData(GapAdvertisingData::FLAGS, &flags, 1);
rgrover1 710:b2e1a2660ec2 306 }
rgrover1 710:b2e1a2660ec2 307
rgrover1 710:b2e1a2660ec2 308 /**
rgrover1 710:b2e1a2660ec2 309 * Helper function to add TX_POWER_LEVEL data to the advertising payload
rgrover1 710:b2e1a2660ec2 310 *
rgrover1 710:b2e1a2660ec2 311 * @return BLE_ERROR_BUFFER_OVERFLOW if the specified data would cause the
rgrover1 710:b2e1a2660ec2 312 * advertising buffer to overflow, else BLE_ERROR_NONE.
rgrover1 710:b2e1a2660ec2 313 */
rgrover1 710:b2e1a2660ec2 314 ble_error_t addTxPower(int8_t txPower) {
rgrover1 710:b2e1a2660ec2 315 /* ToDo: Basic error checking to make sure txPower is in range */
rgrover1 710:b2e1a2660ec2 316 return addData(GapAdvertisingData::TX_POWER_LEVEL, (uint8_t *)&txPower, 1);
rgrover1 710:b2e1a2660ec2 317 }
rgrover1 710:b2e1a2660ec2 318
rgrover1 710:b2e1a2660ec2 319 /**
rgrover1 710:b2e1a2660ec2 320 * Clears the payload and resets the payload length counter
rgrover1 710:b2e1a2660ec2 321 */
rgrover1 710:b2e1a2660ec2 322 void clear(void) {
rgrover1 710:b2e1a2660ec2 323 memset(&_payload, 0, GAP_ADVERTISING_DATA_MAX_PAYLOAD);
rgrover1 710:b2e1a2660ec2 324 _payloadLen = 0;
rgrover1 710:b2e1a2660ec2 325 }
rgrover1 710:b2e1a2660ec2 326
rgrover1 710:b2e1a2660ec2 327 /**
rgrover1 710:b2e1a2660ec2 328 * Returns a pointer to the the current payload
rgrover1 710:b2e1a2660ec2 329 */
rgrover1 710:b2e1a2660ec2 330 const uint8_t *getPayload(void) const {
rgrover1 769:2d236d9afa9e 331 return _payload;
rgrover1 710:b2e1a2660ec2 332 }
rgrover1 710:b2e1a2660ec2 333
rgrover1 710:b2e1a2660ec2 334 /**
rgrover1 710:b2e1a2660ec2 335 * Returns the current payload length (0..31 bytes)
rgrover1 710:b2e1a2660ec2 336 */
rgrover1 710:b2e1a2660ec2 337 uint8_t getPayloadLen(void) const {
rgrover1 710:b2e1a2660ec2 338 return _payloadLen;
rgrover1 710:b2e1a2660ec2 339 }
rgrover1 710:b2e1a2660ec2 340
rgrover1 710:b2e1a2660ec2 341 /**
rgrover1 710:b2e1a2660ec2 342 * Returns the 16-bit appearance value for this device
rgrover1 710:b2e1a2660ec2 343 */
rgrover1 710:b2e1a2660ec2 344 uint16_t getAppearance(void) const {
rgrover1 710:b2e1a2660ec2 345 return (uint16_t)_appearance;
rgrover1 710:b2e1a2660ec2 346 }
rgrover1 710:b2e1a2660ec2 347
rgrover1 710:b2e1a2660ec2 348 private:
rgrover1 710:b2e1a2660ec2 349 uint8_t _payload[GAP_ADVERTISING_DATA_MAX_PAYLOAD];
rgrover1 710:b2e1a2660ec2 350 uint8_t _payloadLen;
rgrover1 710:b2e1a2660ec2 351 uint16_t _appearance;
rgrover1 710:b2e1a2660ec2 352 };
rgrover1 710:b2e1a2660ec2 353
rgrover1 710:b2e1a2660ec2 354 #endif // ifndef __GAP_ADVERTISING_DATA_H__