Lancaster University's fork of the mbed BLE API. Lives on github, https://github.com/lancaster-university/BLE_API
Dependents: microbit-dal microbit-dal microbit-ble-open microbit-dal ... more
Fork of BLE_API by
Revision 1131:73c11a85c6d6, committed 2016-04-06
- Comitter:
- LancasterUniversity
- Date:
- Wed Apr 06 18:40:26 2016 +0100
- Parent:
- 1130:ff83f0020480
- Child:
- 1132:be7a1281777f
- Commit message:
- Synchronized with git rev 13bf70b6
Author: Rohit Grover
Release 2.1.5
=============
A minor release to separate the concept of minlen and len in
GattCharacteristic. Also contains some improvements to documentation.
Changed in this revision
--- a/DOXYGEN_FRONTPAGE.md Tue Jan 12 19:47:52 2016 +0000 +++ b/DOXYGEN_FRONTPAGE.md Wed Apr 06 18:40:26 2016 +0100 @@ -4,7 +4,8 @@ Bluetooth Low Energy on multiple platforms. This documentation describes the internal structure of the mbed -[BLE API](https://github.com/armmbed/ble). +[BLE API](https://github.com/armmbed/ble). It was automatically generated from +specially formatted comment blocks in BLE API's source code using Doxygen (see http://www.stack.nl/~dimitri/doxygen/ for more information on Doxygen). For getting started with BLE on mbed, check our [introduction page](https://docs.mbed.com/docs/ble-intros/en/latest/).
--- a/ble.doxyfile Tue Jan 12 19:47:52 2016 +0000 +++ b/ble.doxyfile Wed Apr 06 18:40:26 2016 +0100 @@ -131,7 +131,7 @@ # path before files name in the file list and in the header files. If set # to NO the shortest path that makes the file name unique will be used. -FULL_PATH_NAMES = YES +FULL_PATH_NAMES = NO # If the FULL_PATH_NAMES tag is set to YES then the STRIP_FROM_PATH tag # can be used to strip a user-defined part of the path. Stripping is @@ -165,7 +165,7 @@ # comments will behave just like regular Qt-style comments # (thus requiring an explicit @brief command for a brief description.) -JAVADOC_AUTOBRIEF = NO +JAVADOC_AUTOBRIEF = YES # If the QT_AUTOBRIEF tag is set to YES then Doxygen will # interpret the first line (until the first dot) of a Qt-style @@ -245,21 +245,15 @@ # Doxygen selects the parser to use depending on the extension of the files it # parses. With this tag you can assign which parser to use for a given # extension. Doxygen has a built-in mapping, but you can override or extend it -# using this tag. The format is ext=language, where ext is a file extension, and -# language is one of the parsers supported by doxygen: IDL, Java, Javascript, -# C#, C, C++, D, PHP, Objective-C, Python, Fortran (fixed format Fortran: -# FortranFixed, free formatted Fortran: FortranFree, unknown formatted Fortran: -# Fortran. In the later case the parser tries to guess whether the code is fixed -# or free formatted code, this is the default for Fortran type files), VHDL. For -# instance to make doxygen treat .inc files as Fortran files (default is PHP), -# and .f files as C (default is Fortran), use: inc=Fortran f=C. -# -# Note: For files without extension you can use no_extension as a placeholder. -# -# Note that for custom extensions you also need to set FILE_PATTERNS otherwise -# the files are not read by doxygen. +# using this tag. The format is ext=language, where ext is a file extension, +# and language is one of the parsers supported by doxygen: IDL, Java, +# Javascript, CSharp, C, C++, D, PHP, Objective-C, Python, Fortran, VHDL, C, +# C++. For instance to make doxygen treat .inc files as Fortran files (default +# is PHP), and .f files as C (default is Fortran), use: inc=Fortran f=C. Note +# that for custom extensions you also need to set FILE_PATTERNS otherwise the +# files are not read by doxygen. -EXTENSION_MAPPING = h=C++ +EXTENSION_MAPPING = # If MARKDOWN_SUPPORT is enabled (the default) then doxygen pre-processes all # comments according to the Markdown format, which allows for more readable @@ -367,12 +361,12 @@ # Private class members and static file members will be hidden unless # the EXTRACT_PRIVATE respectively EXTRACT_STATIC tags are set to YES -EXTRACT_ALL = NO +EXTRACT_ALL = YES # If the EXTRACT_PRIVATE tag is set to YES all private members of a class # will be included in the documentation. -EXTRACT_PRIVATE = NO +EXTRACT_PRIVATE = YES # If the EXTRACT_PACKAGE tag is set to YES all members with package or internal # scope will be included in the documentation. @@ -382,7 +376,7 @@ # If the EXTRACT_STATIC tag is set to YES all static members of a file # will be included in the documentation. -EXTRACT_STATIC = NO +EXTRACT_STATIC = YES # If the EXTRACT_LOCAL_CLASSES tag is set to YES classes (and structs) # defined locally in source files will be included in the documentation. @@ -395,7 +389,7 @@ # the interface are included in the documentation. # If set to NO (the default) only methods in the interface are included. -EXTRACT_LOCAL_METHODS = NO +EXTRACT_LOCAL_METHODS = YES # If this flag is set to YES, the members of anonymous namespaces will be # extracted and appear in the documentation as a namespace called @@ -494,7 +488,7 @@ # This tag will be ignored for brief docs if SORT_BRIEF_DOCS is set to NO # and ignored for detailed docs if SORT_MEMBER_DOCS is set to NO. -SORT_MEMBERS_CTORS_1ST = YES +SORT_MEMBERS_CTORS_1ST = NO # If the SORT_GROUP_NAMES tag is set to YES then doxygen will sort the # hierarchy of group names into alphabetical order. If set to NO (the default) @@ -644,7 +638,7 @@ # wrong or incomplete parameter documentation, but not about the absence of # documentation. -WARN_NO_PARAMDOC = YES +WARN_NO_PARAMDOC = NO # The WARN_FORMAT tag determines the format of the warning messages that # doxygen can produce. The string should contain the $file, $line, and $text @@ -659,10 +653,10 @@ # and error messages should be written. If left blank the output is written # to stderr. -WARN_LOGFILE = doxygen_warn.log +WARN_LOGFILE = #--------------------------------------------------------------------------- -# Configuration options related to the input files +# configuration options related to the input files #--------------------------------------------------------------------------- # The INPUT tag can be used to specify the files and/or directories that contain @@ -737,7 +731,7 @@ # and *.h) to filter out the source-files in the directories. If left # blank all files are included. -EXAMPLE_PATTERNS = +EXAMPLE_PATTERNS = * # If the EXAMPLE_RECURSIVE tag is set to YES then subdirectories will be # searched for input files to be used with the \include or \dontinclude @@ -839,16 +833,6 @@ REFERENCES_LINK_SOURCE = YES -# If SOURCE_TOOLTIPS is enabled (the default) then hovering a hyperlink in the -# source code will show a tooltip with additional information such as prototype, -# brief description and links to the definition and documentation. Since this -# will make the HTML file larger and loading of large files a bit slower, you -# can opt to disable this feature. -# The default value is: YES. -# This tag requires that the tag SOURCE_BROWSER is set to YES. - -SOURCE_TOOLTIPS = YES - # If the USE_HTAGS tag is set to YES then the references to source code # will point to the HTML generated by the htags(1) tool instead of doxygen # built-in source browser. The htags tool is part of GNU's global source @@ -871,7 +855,7 @@ # of all compounds will be generated. Enable this if the project # contains a lot of classes, structs, unions or interfaces. -ALPHABETICAL_INDEX = YES +ALPHABETICAL_INDEX = NO # If the alphabetical index is enabled (see ALPHABETICAL_INDEX) then # the COLS_IN_ALPHA_INDEX tag can be used to specify the number of columns @@ -887,7 +871,7 @@ IGNORE_PREFIX = #--------------------------------------------------------------------------- -# Configuration options related to the HTML output +# configuration options related to the HTML output #--------------------------------------------------------------------------- # If the GENERATE_HTML tag is set to YES (the default) Doxygen will @@ -1147,11 +1131,9 @@ GENERATE_ECLIPSEHELP = NO -# A unique identifier for the Eclipse help plugin. When installing the plugin -# the directory name containing the HTML and XML files should also have this -# name. Each documentation set should have its own identifier. -# The default value is: org.doxygen.Project. -# This tag requires that the tag GENERATE_ECLIPSEHELP is set to YES. +# A unique identifier for the eclipse help plugin. When installing the plugin +# the directory name containing the HTML and XML files should also have +# this name. ECLIPSE_DOC_ID = org.doxygen.Project @@ -1255,7 +1237,7 @@ # typically be disabled. For large projects the javascript based search engine # can be slow, then enabling SERVER_BASED_SEARCH may provide a better solution. -SEARCHENGINE = YES +SEARCHENGINE = NO # When the SERVER_BASED_SEARCH tag is enabled the search engine will be # implemented using a web server instead of a web client using Javascript. @@ -1291,11 +1273,10 @@ SEARCHDATA_FILE = searchdata.xml -# When SERVER_BASED_SEARCH and EXTERNAL_SEARCH are both enabled the +# When SERVER_BASED_SEARCH AND EXTERNAL_SEARCH are both enabled the # EXTERNAL_SEARCH_ID tag can be used as an identifier for the project. This is # useful in combination with EXTRA_SEARCH_MAPPINGS to search through multiple # projects and redirect the results back to the right project. -# This tag requires that the tag SEARCHENGINE is set to YES. EXTERNAL_SEARCH_ID = @@ -1309,7 +1290,7 @@ EXTRA_SEARCH_MAPPINGS = #--------------------------------------------------------------------------- -# Configuration options related to the LaTeX output +# configuration options related to the LaTeX output #--------------------------------------------------------------------------- # If the GENERATE_LATEX tag is set to YES (the default) Doxygen will @@ -1415,7 +1396,7 @@ LATEX_BIB_STYLE = plain #--------------------------------------------------------------------------- -# Configuration options related to the RTF output +# configuration options related to the RTF output #--------------------------------------------------------------------------- # If the GENERATE_RTF tag is set to YES Doxygen will generate RTF output @@ -1704,7 +1685,7 @@ # this option also works with HAVE_DOT disabled, but it is recommended to # install and use dot, since it yields more powerful graphs. -CLASS_DIAGRAMS = YES +CLASS_DIAGRAMS = NO # You can define message sequence charts within doxygen comments using the \msc # command. Doxygen will then run the mscgen tool (see
--- a/ble/BLE.h Tue Jan 12 19:47:52 2016 +0000 +++ b/ble/BLE.h Wed Apr 06 18:40:26 2016 +0100 @@ -196,7 +196,7 @@ * directly, as it returns references to singletons. * * @param[in] id - * Instance-ID. This should be less than NUM_INSTANCES + * Instance-ID. This should be less than NUM_INSTANCES * for the returned BLE singleton to be useful. * * @return a reference to a single object. @@ -239,7 +239,7 @@ * ble.setAddress(...) should be replaced with * ble.gap().setAddress(...). */ - ble_error_t setAddress(BLEProtocol::AddressType_t type, const BLEProtocol::AddressBytes_t address) { + ble_error_t setAddress(Gap::AddressType_t type, const Gap::Address_t address) { return gap().setAddress(type, address); } @@ -252,7 +252,7 @@ * ble.getAddress(...) should be replaced with * ble.gap().getAddress(...). */ - ble_error_t getAddress(BLEProtocol::AddressType_t *typeP, BLEProtocol::AddressBytes_t address) { + ble_error_t getAddress(Gap::AddressType_t *typeP, Gap::Address_t address) { return gap().getAddress(typeP, address); } @@ -752,10 +752,10 @@ * ble.connect(...) should be replaced with * ble.gap().connect(...). */ - ble_error_t connect(const BLEProtocol::AddressBytes_t peerAddr, - BLEProtocol::AddressType_t peerAddrType = BLEProtocol::AddressType::RANDOM_STATIC, - const Gap::ConnectionParams_t *connectionParams = NULL, - const GapScanningParams *scanParams = NULL) { + ble_error_t connect(const Gap::Address_t peerAddr, + Gap::AddressType_t peerAddrType = Gap::ADDR_TYPE_RANDOM_STATIC, + const Gap::ConnectionParams_t *connectionParams = NULL, + const GapScanningParams *scanParams = NULL) { return gap().connect(peerAddr, peerAddrType, connectionParams, scanParams); } @@ -773,7 +773,7 @@ } /** - * This call initiates the disconnection procedure, and its completion + * This call initiates the disconnection procedure, and its completion * is communicated to the application with an invocation of the * onDisconnection callback. * @@ -1407,7 +1407,7 @@ /** * Set up a callback for when the passkey needs to be displayed on a * peripheral with DISPLAY capability. This happens when security is - * configured to prevent Man-In-The-Middle attacks, and the peers need to exchange + * configured to prevent Man-In-The-Middle attacks, and the peers need to exchange * a passkey (or PIN) to authenticate the connection * attempt. *
--- a/ble/BLEProtocol.h Tue Jan 12 19:47:52 2016 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,69 +0,0 @@ -/* mbed Microcontroller Library - * Copyright (c) 2006-2013 ARM Limited - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef __BLE_PROTOCOL_H__ -#define __BLE_PROTOCOL_H__ - -#include <stddef.h> -#include <stdint.h> -#include <algorithm> - -/** - * A common namespace for types and constants used everywhere in BLE API. - */ -namespace BLEProtocol { - /**< - * A simple container for the enumeration of address-types for Protocol addresses. - * - * Adding a struct to encapsulate the contained enumeration prevents - * polluting the BLEProtocol namespace with the enumerated values. It also - * allows type-aliases for the enumeration while retaining the enumerated - * values. i.e. doing: - * typedef AddressType AliasedType; - * - * would allow the use of AliasedType::PUBLIC in code. - */ - struct AddressType { - /**< Address-types for Protocol addresses. */ - enum Type { - PUBLIC = 0, - RANDOM_STATIC, - RANDOM_PRIVATE_RESOLVABLE, - RANDOM_PRIVATE_NON_RESOLVABLE - }; - }; - typedef AddressType::Type AddressType_t; /**< Alias for AddressType::Type */ - - static const size_t ADDR_LEN = 6; /**< Length (in octets) of the BLE MAC address. */ - typedef uint8_t AddressBytes_t[ADDR_LEN]; /**< 48-bit address, in LSB format. */ - - /** - * BLE address. It contains an address-type (@ref AddressType_t) and bytes (@ref AddressBytes_t). - */ - struct Address_t { - AddressType_t type; /**< @ref AddressType_t */ - AddressBytes_t address; /**< @ref AddressBytes_t */ - - Address_t(AddressType_t typeIn, const AddressBytes_t& addressIn) : type(typeIn) { - std::copy(addressIn, addressIn + ADDR_LEN, address); - } - - Address_t() : type(), address() { - } - }; -}; - -#endif /* __BLE_PROTOCOL_H__ */ \ No newline at end of file
--- a/ble/CharacteristicDescriptorDiscovery.h Tue Jan 12 19:47:52 2016 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,99 +0,0 @@ -/* mbed Microcontroller Library - * Copyright (c) 2006-2015 ARM Limited - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef __CHARACTERISTIC_DESCRIPTOR_DISCOVERY_H__ -#define __CHARACTERISTIC_DESCRIPTOR_DISCOVERY_H__ - -#include "FunctionPointerWithContext.h" - -class DiscoveredCharacteristic; // forward declaration -class DiscoveredCharacteristicDescriptor; // forward declaration - -/** - * @brief Contain all definitions of callbacks and callbacks parameters types - * related to characteristic descriptor discovery. - * - * @details This class act like a namespace for characteristic descriptor discovery - * types. It act like ServiceDiscovery by providing callbacks and callbacks - * parameters types related to the characteristic descriptor discovery process but - * contrary to ServiceDiscovery class, it does not force the porter to use a - * specific interface for the characteristic descriptor discovery process. - */ -class CharacteristicDescriptorDiscovery { -public: - /** - * @brief Parameter type of CharacteristicDescriptorDiscovery::DiscoveryCallback_t. - * @detail Every time a characteristic descriptor has been discovered, the callback - * registered for the discovery operation through GattClient::discoverCharacteristicDescriptors - * or DiscoveredCharacteristic::discoverDescriptors will be called with this parameter. - * - */ - struct DiscoveryCallbackParams_t { - /** - * The characteristic owning the DiscoveredCharacteristicDescriptor - */ - const DiscoveredCharacteristic& characteristic; - - /** - * The characteristic descriptor discovered - */ - const DiscoveredCharacteristicDescriptor& descriptor; - }; - - /** - * @brief Parameter type of CharacteristicDescriptorDiscovery::TerminationCallback_t. - * @details Once a characteristic descriptor discovery process terminate, the termination - * callback registered for the discovery operation through - * GattClient::discoverCharacteristicDescriptors or DiscoveredCharacteristic::discoverDescriptors - * will be called with this parameter. - */ - struct TerminationCallbackParams_t { - /** - * The characteristic for which the descriptors has been discovered - */ - const DiscoveredCharacteristic& characteristic; - - /** - * status of the discovery operation - */ - ble_error_t status; - }; - - /** - * @brief Callback type for when a matching characteristic descriptor is found during - * characteristic descriptor discovery. - * - * @param param A pointer to a DiscoveryCallbackParams_t object which will remain - * valid for the lifetime of the callback. Memory for this object is owned by - * the BLE_API eventing framework. The application can safely make a persistent - * shallow-copy of this object in order to work with the service beyond the - * callback. - */ - typedef FunctionPointerWithContext<const DiscoveryCallbackParams_t*> DiscoveryCallback_t; - - /** - * @brief Callback type for when characteristic descriptor discovery terminates. - * - * @param param A pointer to a TerminationCallbackParams_t object which will remain - * valid for the lifetime of the callback. Memory for this object is owned by - * the BLE_API eventing framework. The application can safely make a persistent - * shallow-copy of this object in order to work with the service beyond the - * callback. - */ - typedef FunctionPointerWithContext<const TerminationCallbackParams_t*> TerminationCallback_t; -}; - -#endif // ifndef __CHARACTERISTIC_DESCRIPTOR_DISCOVERY_H__ \ No newline at end of file
--- a/ble/DiscoveredCharacteristic.h Tue Jan 12 19:47:52 2016 +0000 +++ b/ble/DiscoveredCharacteristic.h Wed Apr 06 18:40:26 2016 +0100 @@ -21,24 +21,10 @@ #include "Gap.h" #include "GattAttribute.h" #include "GattClient.h" -#include "CharacteristicDescriptorDiscovery.h" -#include "ble/DiscoveredCharacteristicDescriptor.h" /** - * @brief Representation of a characteristic discovered during a GattClient - * discovery procedure (see GattClient::launchServiceDiscovery ). - * - * @detail Provide detailed informations about a discovered characteristic like: - * - Its UUID (see #getUUID). - * - The most important handles of the characteristic definition - * (see #getDeclHandle, #getValueHandle, #getLastHandle ) - * - Its properties (see #getProperties). - * This class also provide functions to operate on the characteristic: - * - Read the characteristic value (see #read) - * - Writing a characteristic value (see #write or #writeWoResponse) - * - Discover descriptors inside the characteristic definition. These descriptors - * extends the characteristic. More information about descriptor usage is - * available in DiscoveredCharacteristicDescriptor class. + * Structure for holding information about the service and the characteristics + * found during the discovery process. */ class DiscoveredCharacteristic { public: @@ -47,7 +33,7 @@ uint8_t _read :1; /**< Reading the value permitted. */ uint8_t _writeWoResp :1; /**< Writing the value with Write Command permitted. */ uint8_t _write :1; /**< Writing the value with Write Request permitted. */ - uint8_t _notify :1; /**< Notifications of the value permitted. */ + uint8_t _notify :1; /**< Notications of the value permitted. */ uint8_t _indicate :1; /**< Indications of the value permitted. */ uint8_t _authSignedWrite :1; /**< Writing the value with Signed Write Command permitted. */ @@ -60,50 +46,36 @@ bool indicate(void) const {return _indicate; } bool authSignedWrite(void) const {return _authSignedWrite;} - /** - * @brief "Equal to" operator for DiscoveredCharacteristic::Properties_t - * - * @param lhs[in] The left hand side of the equality expression - * @param rhs[in] The right hand side of the equality expression - * - * @return true if operands are equals, false otherwise. - */ - friend bool operator==(Properties_t lhs, Properties_t rhs) { - return lhs._broadcast == rhs._broadcast && - lhs._read == rhs._read && - lhs._writeWoResp == rhs._writeWoResp && - lhs._write == rhs._write && - lhs._notify == rhs._notify && - lhs._indicate == rhs._indicate && - lhs._authSignedWrite == rhs._authSignedWrite; - } - - /** - * @brief "Not equal to" operator for DiscoveredCharacteristic::Properties_t - * - * @param lhs The right hand side of the expression - * @param rhs The left hand side of the expression - * - * @return true if operands are not equals, false otherwise. - */ - friend bool operator!=(Properties_t lhs, Properties_t rhs) { - return !(lhs == rhs); - } - private: operator uint8_t() const; /* Disallow implicit conversion into an integer. */ operator unsigned() const; /* Disallow implicit conversion into an integer. */ }; /** + * Structure for holding information about the service and the characteristics + * found during the discovery process. + */ + struct DiscoveredDescriptor { + GattAttribute::Handle_t handle; /**< Descriptor Handle. */ + UUID uuid; /**< Descriptor UUID. */ + }; + + /** + * Callback type for when a characteristic descriptor is found during descriptor- + * discovery. The receiving function is passed in a pointer to a + * DiscoveredDescriptor object which will remain valid for the lifetime + * of the callback. Memory for this object is owned by the BLE_API eventing + * framework. The application can safely make a persistent shallow-copy of + * this object in order to work with the characteristic beyond the callback. + */ + typedef void (*DescriptorCallback_t)(const DiscoveredDescriptor *); + + /** * Initiate (or continue) a read for the value attribute, optionally at a * given offset. If the characteristic or descriptor to be read is longer * than ATT_MTU - 1, this function must be called multiple times with * appropriate offset to read the complete value. * - * @param offset[in] The position - in the characteristic value bytes stream - where - * the read operation begin. - * * @return BLE_ERROR_NONE if a read has been initiated, or * BLE_ERROR_INVALID_STATE if some internal state about the connection is invalid, or * BLE_STACK_BUSY if some client procedure is already in progress, or @@ -111,22 +83,14 @@ */ ble_error_t read(uint16_t offset = 0) const; - /** - * @brief Same as #read(uint16_t) const but allow the user to register a callback - * which will be fired once the read is done. - * - * @param offset[in] The position - in the characteristic value bytes stream - where - * the read operation begin. - * @param onRead[in] Continuation of the read operation - */ ble_error_t read(uint16_t offset, const GattClient::ReadCallback_t& onRead) const; /** * Perform a write without response procedure. * - * @param[in] length + * @param length * The amount of data being written. - * @param[in] value + * @param value * The bytes being written. * * @note It is important to note that a write without response will generate @@ -146,20 +110,20 @@ /** * Initiate a GATT Characteristic Descriptor Discovery procedure for descriptors within this characteristic. * - * @param[in] onDescriptorDiscovered This callback will be called every time a descriptor is discovered - * @param[in] onTermination This callback will be called when the discovery process is over. + * @param callback + * @param matchingUUID + * Filter for descriptors. Defaults to wildcard which will discover all descriptors. * - * @return BLE_ERROR_NONE if descriptor discovery is launched successfully; else an appropriate error. + * @return BLE_ERROR_NONE if descriptor discovery is launched successfully; else an appropriate error. */ - ble_error_t discoverDescriptors(const CharacteristicDescriptorDiscovery::DiscoveryCallback_t& onDescriptorDiscovered, - const CharacteristicDescriptorDiscovery::TerminationCallback_t& onTermination) const; + ble_error_t discoverDescriptors(DescriptorCallback_t callback, const UUID &matchingUUID = UUID::ShortUUIDBytes_t(BLE_UUID_UNKNOWN)) const; /** * Perform a write procedure. * - * @param[in] length + * @param length * The amount of data being written. - * @param[in] value + * @param value * The bytes being written. * * @note It is important to note that a write will generate @@ -173,143 +137,37 @@ */ ble_error_t write(uint16_t length, const uint8_t *value) const; - /** - * Same as #write(uint16_t, const uint8_t *) const but register a callback - * which will be called once the data has been written. - * - * @param[in] length The amount of bytes to write. - * @param[in] value The bytes to write. - * @param[in] onRead Continuation callback for the write operation + /** + * Same as above but register the callback wich will be called once the data has been written */ - ble_error_t write(uint16_t length, const uint8_t *value, const GattClient::WriteCallback_t& onWrite) const; + ble_error_t write(uint16_t length, const uint8_t *value, const GattClient::WriteCallback_t& onRead) const; - void setupLongUUID(UUID::LongUUIDBytes_t longUUID, UUID::ByteOrder_t order = UUID::MSB) { - uuid.setupLong(longUUID, order); + void setupLongUUID(UUID::LongUUIDBytes_t longUUID) { + uuid.setupLong(longUUID); } public: - /** - * @brief Get the UUID of the discovered characteristic - * @return the UUID of this characteristic - */ const UUID& getUUID(void) const { return uuid; } - /** - * @brief Get the properties of this characteristic - * @return the set of properties of this characteristic - */ const Properties_t& getProperties(void) const { return props; } - /** - * @brief Get the declaration handle of this characteristic. - * @detail The declaration handle is the first handle of a characteristic - * definition. The value accessible at this handle contains the following - * informations: - * - The characteristics properties (see Properties_t). This value can - * be accessed by using #getProperties . - * - The characteristic value attribute handle. This field can be accessed - * by using #getValueHandle . - * - The characteristic UUID, this value can be accessed by using the - * function #getUUID . - * @return the declaration handle of this characteristic. - */ - GattAttribute::Handle_t getDeclHandle(void) const { + const GattAttribute::Handle_t& getDeclHandle(void) const { return declHandle; } - - /** - * @brief Return the handle used to access the value of this characteristic. - * @details This handle is the one provided in the characteristic declaration - * value. Usually, it is equal to #getDeclHandle() + 1. But it is not always - * the case. Anyway, users are allowed to use #getDeclHandle() + 1 to access - * the value of a characteristic. - * @return The handle to access the value of this characteristic. - */ - GattAttribute::Handle_t getValueHandle(void) const { + const GattAttribute::Handle_t& getValueHandle(void) const { return valueHandle; } - /** - * @brief Return the last handle of the characteristic definition. - * @details A Characteristic definition can contain a lot of handles: - * - one for the declaration (see #getDeclHandle) - * - one for the value (see #getValueHandle) - * - zero of more for the characteristic descriptors. - * This handle is the last handle of the characteristic definition. - * @return The last handle of this characteristic definition. - */ - GattAttribute::Handle_t getLastHandle(void) const { - return lastHandle; - } - - /** - * @brief Return the GattClient which can operate on this characteristic. - * @return The GattClient which can operate on this characteristic. - */ - GattClient* getGattClient() { - return gattc; - } - - /** - * @brief Return the GattClient which can operate on this characteristic. - * @return The GattClient which can operate on this characteristic. - */ - const GattClient* getGattClient() const { - return gattc; - } - - /** - * @brief Return the connection handle to the GattServer which contain - * this characteristic. - * @return the connection handle to the GattServer which contain - * this characteristic. - */ - Gap::Handle_t getConnectionHandle() const { - return connHandle; - } - - /** - * @brief "Equal to" operator for DiscoveredCharacteristic - * - * @param lhs[in] The left hand side of the equality expression - * @param rhs[in] The right hand side of the equality expression - * - * @return true if operands are equals, false otherwise. - */ - friend bool operator==(const DiscoveredCharacteristic& lhs, const DiscoveredCharacteristic& rhs) { - return lhs.gattc == rhs.gattc && - lhs.uuid == rhs.uuid && - lhs.props == rhs.props && - lhs.declHandle == rhs.declHandle && - lhs.valueHandle == rhs.valueHandle && - lhs.lastHandle == rhs.lastHandle && - lhs.connHandle == rhs.connHandle; - } - - /** - * @brief "Not equal to" operator for DiscoveredCharacteristic - * - * @param lhs[in] The right hand side of the expression - * @param rhs[in] The left hand side of the expression - * - * @return true if operands are not equals, false otherwise. - */ - friend bool operator !=(const DiscoveredCharacteristic& lhs, const DiscoveredCharacteristic& rhs) { - return !(lhs == rhs); - } - public: DiscoveredCharacteristic() : gattc(NULL), uuid(UUID::ShortUUIDBytes_t(0)), props(), declHandle(GattAttribute::INVALID_HANDLE), - valueHandle(GattAttribute::INVALID_HANDLE), - lastHandle(GattAttribute::INVALID_HANDLE), - connHandle() { + valueHandle(GattAttribute::INVALID_HANDLE) { /* empty */ } @@ -321,7 +179,6 @@ Properties_t props; GattAttribute::Handle_t declHandle; GattAttribute::Handle_t valueHandle; - GattAttribute::Handle_t lastHandle; Gap::Handle_t connHandle; };
--- a/ble/DiscoveredCharacteristicDescriptor.h Tue Jan 12 19:47:52 2016 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,111 +0,0 @@ -/* mbed Microcontroller Library - * Copyright (c) 2006-2013 ARM Limited - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef __DISCOVERED_CHARACTERISTIC_DESCRIPTOR_H__ -#define __DISCOVERED_CHARACTERISTIC_DESCRIPTOR_H__ - -#include "UUID.h" -#include "Gap.h" -#include "GattAttribute.h" -#include "GattClient.h" -#include "CharacteristicDescriptorDiscovery.h" - -/** - * @brief Representation of a descriptor discovered during a GattClient - * discovery procedure (see GattClient::discoverCharacteristicDescriptors or - * DiscoveredCharacteristic::discoverDescriptors ). - * - * @detail Provide detailed informations about a discovered characteristic descriptor - * like: - * - Its UUID (see #getUUID). - * - Its handle (see #getAttributeHandle) - * Basic read (see GattClient::read) and write (see GattClient::write) procedure from - * GattClient can be used access the value of the descriptor. - * - * @todo read member function - * @todo write member function - * @todo enumeration of standard descriptors - */ -class DiscoveredCharacteristicDescriptor { - -public: - - /** - * @brief construct a new instance of a DiscoveredCharacteristicDescriptor - * - * @param client The client from where the descriptor has been discovered - * @param connectionHandle The connection handle on which the descriptor has - * been discovered - * @param attributeHandle The handle of the attribute containing this descriptor - * @param uuid The UUID of the descriptor - */ - DiscoveredCharacteristicDescriptor( - GattClient* client, Gap::Handle_t connectionHandle, GattAttribute::Handle_t attributeHandle, const UUID& uuid) : - _client(client), _connectionHandle(connectionHandle), _uuid(uuid), _gattHandle(attributeHandle) { - - } - - /** - * @brief Return the GattClient which can operate on this descriptor. - * @return The GattClient which can operate on this descriptor. - */ - GattClient* getGattClient() { - return _client; - } - - /** - * @brief Return the GattClient which can operate on this descriptor. - * @return The GattClient which can operate on this descriptor. - */ - const GattClient* getGattClient() const { - return _client; - } - - /** - * @brief Return the connection handle to the GattServer which contain - * this descriptor. - * @return the connection handle to the GattServer which contain - * this descriptor. - */ - Gap::Handle_t getConnectionHandle() const { - return _connectionHandle; - } - - /** - * @brief Return the UUID of this descriptor - * @return the UUID of this descriptor - */ - const UUID& getUUID(void) const { - return _uuid; - } - - /** - * @brief Return the attribute handle to use to access to this descriptor - * on the gatt server. - * @return The attribute handle of the descriptor - */ - GattAttribute::Handle_t getAttributeHandle() const { - return _gattHandle; - } - -private: - GattClient *_client; - Gap::Handle_t _connectionHandle; - UUID _uuid; - GattAttribute::Handle_t _gattHandle; -}; - -#endif /*__DISCOVERED_CHARACTERISTIC_DESCRIPTOR_H__*/ \ No newline at end of file
--- a/ble/DiscoveredService.h Tue Jan 12 19:47:52 2016 +0000 +++ b/ble/DiscoveredService.h Wed Apr 06 18:40:26 2016 +0100 @@ -36,8 +36,8 @@ endHandle = endHandleIn; } - void setupLongUUID(UUID::LongUUIDBytes_t longUUID, UUID::ByteOrder_t order = UUID::MSB) { - uuid.setupLong(longUUID, order); + void setupLongUUID(UUID::LongUUIDBytes_t longUUID) { + uuid.setupLong(longUUID); } public:
--- a/ble/Gap.h Tue Jan 12 19:47:52 2016 +0000 +++ b/ble/Gap.h Wed Apr 06 18:40:26 2016 +0100 @@ -17,14 +17,12 @@ #ifndef __GAP_H__ #define __GAP_H__ -#include "ble/BLEProtocol.h" #include "GapAdvertisingData.h" #include "GapAdvertisingParams.h" #include "GapScanningParams.h" #include "GapEvents.h" #include "CallChainOfFunctionPointersWithContext.h" #include "FunctionPointerWithContext.h" -#include "deprecate.h" /* Forward declarations for classes that will only be used for pointers or references in the following. */ class GapAdvertisingParams; @@ -32,44 +30,19 @@ class GapAdvertisingData; class Gap { - /* - * DEPRECATION ALERT: all of the APIs in this `public` block are deprecated. - * They have been relocated to the class BLEProtocol. - */ public: - /** - * Address-type for BLEProtocol addresses. - * - * @note: deprecated. Use BLEProtocol::AddressType_t instead. - */ - typedef BLEProtocol::AddressType_t AddressType_t; - - /** - * Address-type for BLEProtocol addresses. - * @note: deprecated. Use BLEProtocol::AddressType_t instead. - */ - typedef BLEProtocol::AddressType_t addr_type_t; + enum AddressType_t { + ADDR_TYPE_PUBLIC = 0, + ADDR_TYPE_RANDOM_STATIC, + ADDR_TYPE_RANDOM_PRIVATE_RESOLVABLE, + ADDR_TYPE_RANDOM_PRIVATE_NON_RESOLVABLE + }; + typedef enum AddressType_t addr_type_t; /* @Note: Deprecated. Use AddressType_t instead. */ - /** - * Address-type for BLEProtocol addresses. - * \deprecated: Use BLEProtocol::AddressType_t instead. - * - * DEPRECATION ALERT: The following constants have been left in their - * deprecated state to transparenly support existing applications which may - * have used Gap::ADDR_TYPE_*. - */ - enum DeprecatedAddressType_t { - ADDR_TYPE_PUBLIC = BLEProtocol::AddressType::PUBLIC, - ADDR_TYPE_RANDOM_STATIC = BLEProtocol::AddressType::RANDOM_STATIC, - ADDR_TYPE_RANDOM_PRIVATE_RESOLVABLE = BLEProtocol::AddressType::RANDOM_PRIVATE_RESOLVABLE, - ADDR_TYPE_RANDOM_PRIVATE_NON_RESOLVABLE = BLEProtocol::AddressType::RANDOM_PRIVATE_NON_RESOLVABLE - }; + static const unsigned ADDR_LEN = 6; + typedef uint8_t Address_t[ADDR_LEN]; /* 48-bit address, LSB format. */ + typedef Address_t address_t; /* @Note: Deprecated. Use Address_t instead. */ - static const unsigned ADDR_LEN = BLEProtocol::ADDR_LEN; /**< Length (in octets) of the BLE MAC address. */ - typedef BLEProtocol::AddressBytes_t Address_t; /**< 48-bit address, LSB format. @Note: Deprecated. Use BLEProtocol::AddressBytes_t instead. */ - typedef BLEProtocol::AddressBytes_t address_t; /**< 48-bit address, LSB format. @Note: Deprecated. Use BLEProtocol::AddressBytes_t instead. */ - -public: enum TimeoutSource_t { TIMEOUT_SRC_ADVERTISING = 0x00, /**< Advertising timeout. */ TIMEOUT_SRC_SECURITY_REQUEST = 0x01, /**< Security request timeout. */ @@ -93,56 +66,6 @@ CONN_INTERVAL_UNACCEPTABLE = 0x3B, }; - /** - * Enumeration for whitelist advertising policy filter modes. The possible - * filter modes were obtained from the Bluetooth Core Specification - * 4.2 (Vol. 6), Part B, Section 4.3.2. - * - * @experimental - */ - enum AdvertisingPolicyMode_t { - ADV_POLICY_IGNORE_WHITELIST = 0, - ADV_POLICY_FILTER_SCAN_REQS = 1, - ADV_POLICY_FILTER_CONN_REQS = 2, - ADV_POLICY_FILTER_ALL_REQS = 3, - }; - - /** - * Enumeration for whitelist scanning policy filter modes. The possible - * filter modes were obtained from the Bluetooth Core Specification - * 4.2 (Vol. 6), Part B, Section 4.3.3. - * - * @experimental - */ - enum ScanningPolicyMode_t { - SCAN_POLICY_IGNORE_WHITELIST = 0, - SCAN_POLICY_FILTER_ALL_ADV = 1, - }; - - /** - * Enumeration for the whitelist initiator policy fiter modes. The possible - * filter modes were obtained from the Bluetooth Core Specification - * 4.2 (vol. 6), Part B, Section 4.4.4. - * - * @experimental - */ - enum InitiatorPolicyMode_t { - INIT_POLICY_IGNORE_WHITELIST = 0, - INIT_POLICY_FILTER_ALL_ADV = 1, - }; - - /** - * Representation of a Bluetooth Low Enery Whitelist containing addresses. - * - * @experimental - */ - struct Whitelist_t { - BLEProtocol::Address_t *addresses; - uint8_t size; - uint8_t capacity; - }; - - /* Describes the current state of the device (more than one bit can be set). */ struct GapState_t { unsigned advertising : 1; /**< Peripheral is currently advertising. */ @@ -152,9 +75,9 @@ typedef uint16_t Handle_t; /* Type for connection handle. */ typedef struct { - uint16_t minConnectionInterval; /**< Minimum Connection Interval in 1.25 ms units, see @ref BLE_GAP_CP_LIMITS.*/ - uint16_t maxConnectionInterval; /**< Maximum Connection Interval in 1.25 ms units, see @ref BLE_GAP_CP_LIMITS.*/ - uint16_t slaveLatency; /**< Slave Latency in number of connection events, see @ref BLE_GAP_CP_LIMITS.*/ + uint16_t minConnectionInterval; /**< Minimum Connection Interval in 1.25 ms units, see @ref BLE_GAP_CP_LIMITS.*/ + uint16_t maxConnectionInterval; /**< Maximum Connection Interval in 1.25 ms units, see @ref BLE_GAP_CP_LIMITS.*/ + uint16_t slaveLatency; /**< Slave Latency in number of connection events, see @ref BLE_GAP_CP_LIMITS.*/ uint16_t connectionSupervisionTimeout; /**< Connection Supervision Timeout in 10 ms units, see @ref BLE_GAP_CP_LIMITS.*/ } ConnectionParams_t; @@ -164,31 +87,31 @@ }; struct AdvertisementCallbackParams_t { - BLEProtocol::AddressBytes_t peerAddr; - int8_t rssi; - bool isScanResponse; - GapAdvertisingParams::AdvertisingType_t type; - uint8_t advertisingDataLen; - const uint8_t *advertisingData; + Address_t peerAddr; + int8_t rssi; + bool isScanResponse; + GapAdvertisingParams::AdvertisingType_t type; + uint8_t advertisingDataLen; + const uint8_t *advertisingData; }; typedef FunctionPointerWithContext<const AdvertisementCallbackParams_t *> AdvertisementReportCallback_t; struct ConnectionCallbackParams_t { - Handle_t handle; - Role_t role; - BLEProtocol::AddressType_t peerAddrType; - BLEProtocol::AddressBytes_t peerAddr; - BLEProtocol::AddressType_t ownAddrType; - BLEProtocol::AddressBytes_t ownAddr; - const ConnectionParams_t *connectionParams; + Handle_t handle; + Role_t role; + AddressType_t peerAddrType; + Address_t peerAddr; + AddressType_t ownAddrType; + Address_t ownAddr; + const ConnectionParams_t *connectionParams; - ConnectionCallbackParams_t(Handle_t handleIn, - Role_t roleIn, - BLEProtocol::AddressType_t peerAddrTypeIn, - const uint8_t *peerAddrIn, - BLEProtocol::AddressType_t ownAddrTypeIn, - const uint8_t *ownAddrIn, - const ConnectionParams_t *connectionParamsIn) : + ConnectionCallbackParams_t(Handle_t handleIn, + Role_t roleIn, + AddressType_t peerAddrTypeIn, + const uint8_t *peerAddrIn, + AddressType_t ownAddrTypeIn, + const uint8_t *ownAddrIn, + const ConnectionParams_t *connectionParamsIn) : handle(handleIn), role(roleIn), peerAddrType(peerAddrTypeIn), @@ -224,24 +147,21 @@ typedef CallChainOfFunctionPointersWithContext<const ConnectionCallbackParams_t *> ConnectionEventCallbackChain_t; typedef FunctionPointerWithContext<const DisconnectionCallbackParams_t*> DisconnectionEventCallback_t; - typedef CallChainOfFunctionPointersWithContext<const DisconnectionCallbackParams_t*> DisconnectionEventCallbackChain_t; + typedef CallChainOfFunctionPointersWithContext<const DisconnectionCallbackParams_t*> DisconnectionEventCallbackChain_t; typedef FunctionPointerWithContext<bool> RadioNotificationEventCallback_t; - typedef FunctionPointerWithContext<const Gap *> GapShutdownCallback_t; - typedef CallChainOfFunctionPointersWithContext<const Gap *> GapShutdownCallbackChain_t; - /* * The following functions are meant to be overridden in the platform-specific sub-class. */ public: /** * Set the BTLE MAC address and type. Please note that the address format is - * least significant byte first (LSB). Please refer to BLEProtocol::AddressBytes_t. + * least significant byte first (LSB). Please refer to Address_t. * * @return BLE_ERROR_NONE on success. */ - virtual ble_error_t setAddress(BLEProtocol::AddressType_t type, const BLEProtocol::AddressBytes_t address) { + virtual ble_error_t setAddress(AddressType_t type, const Address_t address) { /* avoid compiler warnings about unused variables */ (void)type; (void)address; @@ -254,7 +174,7 @@ * * @return BLE_ERROR_NONE on success. */ - virtual ble_error_t getAddress(BLEProtocol::AddressType_t *typeP, BLEProtocol::AddressBytes_t address) { + virtual ble_error_t getAddress(AddressType_t *typeP, Address_t address) { /* Avoid compiler warnings about unused variables. */ (void)typeP; (void)address; @@ -263,16 +183,14 @@ } /** - * @return Minimum Advertising interval in milliseconds for connectable - * undirected and connectable directed event types. + * @return Minimum Advertising interval in milliseconds. */ virtual uint16_t getMinAdvertisingInterval(void) const { return 0; /* Requesting action from porter(s): override this API if this capability is supported. */ } /** - * @return Minimum Advertising interval in milliseconds for scannable - * undirected and non-connectable undirected event types. + * @return Minimum Advertising interval in milliseconds for non-connectible mode. */ virtual uint16_t getMinNonConnectableAdvertisingInterval(void) const { return 0; /* Requesting action from porter(s): override this API if this capability is supported. */ @@ -313,10 +231,10 @@ * successfully. The connectionCallChain (if set) will be invoked upon * a connection event. */ - virtual ble_error_t connect(const BLEProtocol::AddressBytes_t peerAddr, - BLEProtocol::AddressType_t peerAddrType, - const ConnectionParams_t *connectionParams, - const GapScanningParams *scanParams) { + virtual ble_error_t connect(const Address_t peerAddr, + Gap::AddressType_t peerAddrType, + const ConnectionParams_t *connectionParams, + const GapScanningParams *scanParams) { /* Avoid compiler warnings about unused variables. */ (void)peerAddr; (void)peerAddrType; @@ -327,23 +245,6 @@ } /** - * Create a connection (GAP Link Establishment). - * - * \deprecated: This funtion overloads Gap::connect(const BLEProtocol::Address_t peerAddr, - BLEProtocol::AddressType_t peerAddrType, - const ConnectionParams_t *connectionParams, - const GapScanningParams *scanParams) - * to maintain backward compatibility for change from Gap::AddressType_t to BLEProtocol::AddressType_t - */ - ble_error_t connect(const BLEProtocol::AddressBytes_t peerAddr, - DeprecatedAddressType_t peerAddrType, - const ConnectionParams_t *connectionParams, - const GapScanningParams *scanParams) - __deprecated_message("Gap::DeprecatedAddressType_t is deprecated, use BLEProtocol::AddressType_t instead") { - return connect(peerAddr, (BLEProtocol::AddressType_t) peerAddrType, connectionParams, scanParams); - } - - /** * This call initiates the disconnection procedure, and its completion will * be communicated to the application with an invocation of the * disconnectionCallback. @@ -522,156 +423,6 @@ *countP = 0; /* Requesting action from porter(s): override this API if this capability is supported. */ } - /** - * @return Maximum size of the whitelist. - * - * @experimental - */ - virtual uint8_t getMaxWhitelistSize(void) const - { - return 0; - } - - /** - * Get the internal whitelist to be used by the Link Layer when scanning, - * advertising or initiating a connection depending on the filter policies. - * - * @param[in/out] whitelist - * (on input) whitelist.capacity contains the maximum number - * of addresses to be returned. - * (on output) The populated whitelist with copies of the - * addresses in the implementation's whitelist. - * - * @return BLE_ERROR_NONE if the implementation's whitelist was successfully - * copied into the supplied reference. - * - * @experimental - */ - virtual ble_error_t getWhitelist(Whitelist_t &whitelist) const - { - (void) whitelist; - return BLE_ERROR_NOT_IMPLEMENTED; - } - - /** - * Set the internal whitelist to be used by the Link Layer when scanning, - * advertising or initiating a connection depending on the filter policies. - * - * @param[in] whitelist - * A reference to a whitelist containing the addresses to - * be added to the internal whitelist. - * - * @return BLE_ERROR_NONE if the implementation's whitelist was successfully - * populated with the addresses in the given whitelist. - * - * @note The whitelist must not contain addresses of type @ref - * BLEProtocol::AddressType_t::RANDOM_PRIVATE_NON_RESOLVABLE, this - * this will result in a @ref BLE_ERROR_INVALID_PARAM since the - * remote peer might change its private address at any time and it - * is not possible to resolve it. - * @note If the input whitelist is larger than @ref getMaxWhitelistSize() - * the @ref BLE_ERROR_PARAM_OUT_OF_RANGE is returned. - * - * @experimental - */ - virtual ble_error_t setWhitelist(const Whitelist_t &whitelist) - { - (void) whitelist; - return BLE_ERROR_NOT_IMPLEMENTED; - } - - /** - * Set the advertising policy filter mode to be used in the next call - * to startAdvertising(). - * - * @param[in] mode - * The new advertising policy filter mode. - * - * @return BLE_ERROR_NONE if the specified policy filter mode was set - * successfully. - * - * @experimental - */ - virtual ble_error_t setAdvertisingPolicyMode(AdvertisingPolicyMode_t mode) - { - (void) mode; - return BLE_ERROR_NOT_IMPLEMENTED; - } - - /** - * Set the scan policy filter mode to be used in the next call - * to startScan(). - * - * @param[in] mode - * The new scan policy filter mode. - * - * @return BLE_ERROR_NONE if the specified policy filter mode was set - * successfully. - * - * @experimental - */ - virtual ble_error_t setScanningPolicyMode(ScanningPolicyMode_t mode) - { - (void) mode; - return BLE_ERROR_NOT_IMPLEMENTED; - } - - /** - * Set the initiator policy filter mode to be used. - * - * @param[in] mode - * The new initiator policy filter mode. - * - * @return BLE_ERROR_NONE if the specified policy filter mode was set - * successfully. - * - * @experimental - */ - virtual ble_error_t setInitiatorPolicyMode(InitiatorPolicyMode_t mode) - { - (void) mode; - return BLE_ERROR_NOT_IMPLEMENTED; - } - - /** - * Get the advertising policy filter mode that will be used in the next - * call to startAdvertising(). - * - * @return The set advertising policy filter mode. - * - * @experimental - */ - virtual AdvertisingPolicyMode_t getAdvertisingPolicyMode(void) const - { - return ADV_POLICY_IGNORE_WHITELIST; - } - - /** - * Get the scan policy filter mode that will be used in the next - * call to startScan(). - * - * @return The set scan policy filter mode. - * - * @experimental - */ - virtual ScanningPolicyMode_t getScanningPolicyMode(void) const - { - return SCAN_POLICY_IGNORE_WHITELIST; - } - - /** - * Get the initiator policy filter mode that will be used. - * - * @return The set scan policy filter mode. - * - * @experimental - */ - virtual InitiatorPolicyMode_t getInitiatorPolicyMode(void) const - { - return INIT_POLICY_IGNORE_WHITELIST; - } - - protected: /* Override the following in the underlying adaptation layer to provide the functionality of scanning. */ virtual ble_error_t startRadioScan(const GapScanningParams &scanningParams) { @@ -713,6 +464,11 @@ * peripheral faster, at the expense of more power being used by the radio * due to the higher data transmit rate. * + * @note: This API is now *deprecated* and will be dropped in the future. + * You should use the parallel API from Gap directly. A former call to + * ble.setAdvertisingInterval(...) should now be achieved using + * ble.gap().setAdvertisingInterval(...). + * * @Note: [WARNING] This API previously used 0.625ms as the unit for its * 'interval' argument. That required an explicit conversion from * milliseconds using Gap::MSEC_TO_GAP_DURATION_UNITS(). This conversion is @@ -822,16 +578,6 @@ * @param type The type describing the variable length data. * @param data Data bytes. * @param len Length of data. - * - * @return BLE_ERROR_NONE if the advertisement payload was updated based on - * matching AD type; otherwise, an appropriate error. - * - * @note When the specified AD type is INCOMPLETE_LIST_16BIT_SERVICE_IDS, - * COMPLETE_LIST_16BIT_SERVICE_IDS, INCOMPLETE_LIST_32BIT_SERVICE_IDS, - * COMPLETE_LIST_32BIT_SERVICE_IDS, INCOMPLETE_LIST_128BIT_SERVICE_IDS, - * COMPLETE_LIST_128BIT_SERVICE_IDS or LIST_128BIT_SOLICITATION_IDS the - * supplied value is appended to the values previously added to the - * payload. */ ble_error_t accumulateAdvertisingPayload(GapAdvertisingData::DataType type, const uint8_t *data, uint8_t len) { if (type == GapAdvertisingData::COMPLETE_LOCAL_NAME) { @@ -848,7 +594,8 @@ /** * Update a particular ADV field in the advertising payload (based on - * matching type). + * matching type and length). Note: the length of the new data must be the + * same as the old one. * * @param[in] type The ADV type field describing the variable length data. * @param[in] data Data bytes. @@ -857,7 +604,7 @@ * @note: If advertisements are enabled, then the update will take effect immediately. * * @return BLE_ERROR_NONE if the advertisement payload was updated based on - * matching AD type; otherwise, an appropriate error. + * a <type, len> match; otherwise, an appropriate error. */ ble_error_t updateAdvertisingPayload(GapAdvertisingData::DataType type, const uint8_t *data, uint8_t len) { if (type == GapAdvertisingData::COMPLETE_LOCAL_NAME) { @@ -1159,7 +906,7 @@ /** * @brief provide access to the callchain of timeout event callbacks * It is possible to register callbacks using onTimeout().add(callback); - * It is possible to unregister callbacks using onTimeout().detach(callback) + * It is possible to unregister callbacks using onTimeout().detach(callback) * @return The timeout event callbacks chain */ TimeoutEventCallbackChain_t& onTimeout() { @@ -1178,10 +925,10 @@ /** * @brief provide access to the callchain of connection event callbacks * It is possible to register callbacks using onConnection().add(callback); - * It is possible to unregister callbacks using onConnection().detach(callback) + * It is possible to unregister callbacks using onConnection().detach(callback) * @return The connection event callbacks chain */ - ConnectionEventCallbackChain_t& onConnection() { + ConnectionEventCallbackChain_t& onconnection() { return connectionCallChain; } @@ -1197,7 +944,7 @@ /** * @brief provide access to the callchain of disconnection event callbacks * It is possible to register callbacks using onDisconnection().add(callback); - * It is possible to unregister callbacks using onDisconnection().detach(callback) + * It is possible to unregister callbacks using onDisconnection().detach(callback) * @return The disconnection event callbacks chain */ DisconnectionEventCallbackChain_t& onDisconnection() { @@ -1239,80 +986,6 @@ radioNotificationCallback.attach(tptr, mptr); } - /** - * Setup a callback to be invoked to notify the user application that the - * Gap instance is about to shutdown (possibly as a result of a call - * to BLE::shutdown()). - * - * @Note: It is possible to chain together multiple onShutdown callbacks - * (potentially from different modules of an application) to be notified - * before the Gap instance is shutdown. - * - * @Note: It is also possible to set up a callback into a member function of - * some object. - * - * @Note It is possible to unregister a callback using onShutdown().detach(callback) - */ - void onShutdown(const GapShutdownCallback_t& callback) { - shutdownCallChain.add(callback); - } - template <typename T> - void onShutdown(T *objPtr, void (T::*memberPtr)(void)) { - shutdownCallChain.add(objPtr, memberPtr); - } - - /** - * @brief provide access to the callchain of shutdown event callbacks - * It is possible to register callbacks using onShutdown().add(callback); - * It is possible to unregister callbacks using onShutdown().detach(callback) - * @return The shutdown event callbacks chain - */ - GapShutdownCallbackChain_t& onShutdown() { - return shutdownCallChain; - } - -public: - /** - * Notify all registered onShutdown callbacks that the Gap instance is - * about to be shutdown and clear all Gap state of the - * associated object. - * - * This function is meant to be overridden in the platform-specific - * sub-class. Nevertheless, the sub-class is only expected to reset its - * state and not the data held in Gap members. This shall be achieved by a - * call to Gap::reset() from the sub-class' reset() implementation. - * - * @return BLE_ERROR_NONE on success. - * - * @note: Currently a call to reset() does not reset the advertising and - * scan parameters to default values. - */ - virtual ble_error_t reset(void) { - /* Notify that the instance is about to shutdown */ - shutdownCallChain.call(this); - shutdownCallChain.clear(); - - /* Clear Gap state */ - state.advertising = 0; - state.connected = 0; - - /* Clear scanning state */ - scanningActive = false; - - /* Clear advertising and scanning data */ - _advPayload.clear(); - _scanResponse.clear(); - - /* Clear callbacks */ - timeoutCallbackChain.clear(); - connectionCallChain.clear(); - disconnectionCallChain.clear(); - radioNotificationCallback = NULL; - onAdvertisementReport = NULL; - - return BLE_ERROR_NONE; - } - protected: Gap() : _advParams(), @@ -1332,13 +1005,13 @@ /* Entry points for the underlying stack to report events back to the user. */ public: - void processConnectionEvent(Handle_t handle, - Role_t role, - BLEProtocol::AddressType_t peerAddrType, - const BLEProtocol::AddressBytes_t peerAddr, - BLEProtocol::AddressType_t ownAddrType, - const BLEProtocol::AddressBytes_t ownAddr, - const ConnectionParams_t *connectionParams) { + void processConnectionEvent(Handle_t handle, + Role_t role, + AddressType_t peerAddrType, + const Address_t peerAddr, + AddressType_t ownAddrType, + const Address_t ownAddr, + const ConnectionParams_t *connectionParams) { state.connected = 1; ConnectionCallbackParams_t callbackParams(handle, role, peerAddrType, peerAddr, ownAddrType, ownAddr, connectionParams); connectionCallChain.call(&callbackParams); @@ -1350,12 +1023,12 @@ disconnectionCallChain.call(&callbackParams); } - void processAdvertisementReport(const BLEProtocol::AddressBytes_t peerAddr, - int8_t rssi, - bool isScanResponse, + void processAdvertisementReport(const Address_t peerAddr, + int8_t rssi, + bool isScanResponse, GapAdvertisingParams::AdvertisingType_t type, - uint8_t advertisingDataLen, - const uint8_t *advertisingData) { + uint8_t advertisingDataLen, + const uint8_t *advertisingData) { AdvertisementCallbackParams_t params; memcpy(params.peerAddr, peerAddr, ADDR_LEN); params.rssi = rssi; @@ -1389,9 +1062,6 @@ DisconnectionEventCallbackChain_t disconnectionCallChain; private: - GapShutdownCallbackChain_t shutdownCallChain; - -private: /* Disallow copy and assignment. */ Gap(const Gap &); Gap& operator=(const Gap &);
--- a/ble/GapAdvertisingData.h Tue Jan 12 19:47:52 2016 +0000 +++ b/ble/GapAdvertisingData.h Wed Apr 06 18:40:26 2016 +0100 @@ -187,7 +187,6 @@ PULSE_OXIMETER_GENERIC = 3136, /**< Generic Pulse Oximeter. */ PULSE_OXIMETER_FINGERTIP = 3137, /**< Fingertip Pulse Oximeter. */ PULSE_OXIMETER_WRIST_WORN = 3138, /**< Wrist Worn Pulse Oximeter. */ - GENERIC_WEIGHT_SCALE = 3200, /**< Generic Weight Scale. */ OUTDOOR_GENERIC = 5184, /**< Generic Outdoor. */ OUTDOOR_LOCATION_DISPLAY_DEVICE = 5185, /**< Outdoor Location Display Device. */ OUTDOOR_LOCATION_AND_NAVIGATION_DISPLAY_DEVICE = 5186, /**< Outdoor Location and Navigation Display Device. */ @@ -202,63 +201,149 @@ /** * Adds advertising data based on the specified AD type (see DataType). - * If the supplied AD type is already present in the advertising - * payload, then the value is updated. + * + * @param advDataType The Advertising 'DataType' to add. + * @param payload Pointer to the payload contents. + * @param len Size of the payload in bytes. + * + * @return BLE_ERROR_BUFFER_OVERFLOW if the specified data would cause the + * advertising buffer to overflow, else BLE_ERROR_NONE. + */ + ble_error_t addData(DataType advDataType, const uint8_t *payload, uint8_t len) + { + ble_error_t result = BLE_ERROR_BUFFER_OVERFLOW; + + // find field + uint8_t* field = findField(advDataType); + + // Field type already exist, either add to field or replace + if (field) { + switch(advDataType) { + // These fields will be overwritten with the new value + case FLAGS: + case SHORTENED_LOCAL_NAME: + case COMPLETE_LOCAL_NAME: + case TX_POWER_LEVEL: + case DEVICE_ID: + case SLAVE_CONNECTION_INTERVAL_RANGE: + case SERVICE_DATA: + case APPEARANCE: + case ADVERTISING_INTERVAL: + case MANUFACTURER_SPECIFIC_DATA: { + // current field length, with the type subtracted + uint8_t dataLength = field[0] - 1; + + // new data has same length, do in-order replacement + if (len == dataLength) { + for (uint8_t idx = 0; idx < dataLength; idx++) { + field[2 + idx] = payload[idx]; + } + } else { + // check if data fits + if ((_payloadLen - dataLength + len) <= GAP_ADVERTISING_DATA_MAX_PAYLOAD) { + + // remove old field + while ((field + dataLength + 2) < &_payload[_payloadLen]) { + *field = field[dataLength + 2]; + field++; + } + + // reduce length + _payloadLen -= dataLength + 2; + + // add new field + result = appendField(advDataType, payload, len); + } + } + + break; + } + // These fields will have the new data appended if there is sufficient space + case INCOMPLETE_LIST_16BIT_SERVICE_IDS: + case COMPLETE_LIST_16BIT_SERVICE_IDS: + case INCOMPLETE_LIST_32BIT_SERVICE_IDS: + case COMPLETE_LIST_32BIT_SERVICE_IDS: + case INCOMPLETE_LIST_128BIT_SERVICE_IDS: + case COMPLETE_LIST_128BIT_SERVICE_IDS: + case LIST_128BIT_SOLICITATION_IDS: { + // check if data fits + if ((_payloadLen + len) <= GAP_ADVERTISING_DATA_MAX_PAYLOAD) { + // make room for new field by moving the remainder of the + // advertisement payload "to the right" starting after the + // TYPE field. + uint8_t* end = &_payload[_payloadLen]; + + while (&field[1] < end) { + end[len] = *end; + end--; + } + + // insert new data + for (uint8_t idx = 0; idx < len; idx++) { + field[2 + idx] = payload[idx]; + } + + // increment lengths + field[0] += len; + _payloadLen += len; + + result = BLE_ERROR_NONE; + } + + break; + } + // Field exists but updating it is not supported. Abort operation. + default: + result = BLE_ERROR_NOT_IMPLEMENTED; + break; + } + } else { + // field doesn't exists, insert new + result = appendField(advDataType, payload, len); + } + + return result; + } + + /** + * Update a particular ADV field in the advertising payload (based on + * matching type and length). Note: the length of the new data must be the + * same as the old one. * * @param[in] advDataType The Advertising 'DataType' to add. * @param[in] payload Pointer to the payload contents. * @param[in] len Size of the payload in bytes. * - * @return BLE_ERROR_BUFFER_OVERFLOW if the new value causes the - * advertising buffer to overflow. BLE_ERROR_NONE is returned - * on success. - * - * @note When the specified AD type is INCOMPLETE_LIST_16BIT_SERVICE_IDS, - * COMPLETE_LIST_16BIT_SERVICE_IDS, INCOMPLETE_LIST_32BIT_SERVICE_IDS, - * COMPLETE_LIST_32BIT_SERVICE_IDS, INCOMPLETE_LIST_128BIT_SERVICE_IDS, - * COMPLETE_LIST_128BIT_SERVICE_IDS or LIST_128BIT_SOLICITATION_IDS the - * supplied value is appended to the values previously added to the - * payload. - */ - ble_error_t addData(DataType_t advDataType, const uint8_t *payload, uint8_t len) - { - // find field - uint8_t* field = findField(advDataType); - - if (field) { - // Field type already exist, either add to field or replace - return addField(advDataType, payload, len, field); - } else { - // field doesn't exists, insert new - return appendField(advDataType, payload, len); - } - } - - /** - * Update a particular ADV field in the advertising payload (based on - * matching type). - * - * @param[in] advDataType The Advertising 'DataType' to add. - * @param[in] payload Pointer to the payload contents. - * @param[in] len Size of the payload in bytes. - * - * @return BLE_ERROR_UNSPECIFIED if the specified field is not found, - * BLE_ERROR_BUFFER_OVERFLOW if the new value causes the - * advertising buffer to overflow. BLE_ERROR_NONE is returned - * on success. + * @return BLE_ERROR_UNSPECIFIED if the specified field is not found, else + * BLE_ERROR_NONE. */ ble_error_t updateData(DataType_t advDataType, const uint8_t *payload, uint8_t len) { - // find field - uint8_t* field = findField(advDataType); + if ((payload == NULL) || (len == 0)) { + return BLE_ERROR_INVALID_PARAM; + } + + /* A local struct to describe an ADV field. This definition comes from the Bluetooth Core Spec. (v4.2) Part C, Section 11. */ + struct ADVField_t { + uint8_t len; /* Describes the length (in bytes) of the following type and bytes. */ + uint8_t type; /* Should have the same representation of DataType_t (above). */ + uint8_t bytes[0]; /* A placeholder for variable length data. */ + }; - if (field) { - // Field type already exist, replace field contents - return updateField(advDataType, payload, len, field); - } else { - // field doesn't exists, return an error - return BLE_ERROR_UNSPECIFIED; + /* Iterate over the adv fields looking for the first match. */ + uint8_t byteIndex = 0; + while (byteIndex < _payloadLen) { + ADVField_t *currentADV = (ADVField_t *)&_payload[byteIndex]; + if ((currentADV->len == (len + 1)) && /* Incoming len only describes the payload, whereas ADV->len describes [type + payload]. */ + (currentADV->type == advDataType)) { + memcpy(currentADV->bytes, payload, len); + return BLE_ERROR_NONE; + } + + byteIndex += (currentADV->len + 1); /* Advance by len+1; '+1' is needed to span the len field itself. */ } + + return BLE_ERROR_UNSPECIFIED; } /** @@ -389,107 +474,6 @@ return NULL; } - /** - * Given the a pointer to a field in the advertising payload it replaces - * the existing data in the field with the supplied data. - * - * When the specified AD type is INCOMPLETE_LIST_16BIT_SERVICE_IDS, - * COMPLETE_LIST_16BIT_SERVICE_IDS, INCOMPLETE_LIST_32BIT_SERVICE_IDS, - * COMPLETE_LIST_32BIT_SERVICE_IDS, INCOMPLETE_LIST_128BIT_SERVICE_IDS, - * COMPLETE_LIST_128BIT_SERVICE_IDS or LIST_128BIT_SOLICITATION_IDS the - * supplied value is appended to the values previously added to the - * payload. - * - * Returns BLE_ERROR_NONE on success. - */ - ble_error_t addField(DataType_t advDataType, const uint8_t *payload, uint8_t len, uint8_t* field) - { - ble_error_t result = BLE_ERROR_BUFFER_OVERFLOW; - - switch(advDataType) { - // These fields will have the new data appended if there is sufficient space - case INCOMPLETE_LIST_16BIT_SERVICE_IDS: - case COMPLETE_LIST_16BIT_SERVICE_IDS: - case INCOMPLETE_LIST_32BIT_SERVICE_IDS: - case COMPLETE_LIST_32BIT_SERVICE_IDS: - case INCOMPLETE_LIST_128BIT_SERVICE_IDS: - case COMPLETE_LIST_128BIT_SERVICE_IDS: - case LIST_128BIT_SOLICITATION_IDS: { - // check if data fits - if ((_payloadLen + len) <= GAP_ADVERTISING_DATA_MAX_PAYLOAD) { - // make room for new field by moving the remainder of the - // advertisement payload "to the right" starting after the - // TYPE field. - uint8_t* end = &_payload[_payloadLen]; - - while (&field[1] < end) { - end[len] = *end; - end--; - } - - // insert new data - for (uint8_t idx = 0; idx < len; idx++) { - field[2 + idx] = payload[idx]; - } - - // increment lengths - field[0] += len; - _payloadLen += len; - - result = BLE_ERROR_NONE; - } - - break; - } - // These fields will be overwritten with the new value - default: { - result = updateField(advDataType, payload, len, field); - - break; - } - } - - return result; - } - - /** - * Given the a pointer to a field in the advertising payload it replaces - * the existing data in the field with the supplied data. - * Returns BLE_ERROR_NONE on success. - */ - ble_error_t updateField(DataType_t advDataType, const uint8_t *payload, uint8_t len, uint8_t* field) - { - ble_error_t result = BLE_ERROR_BUFFER_OVERFLOW; - uint8_t dataLength = field[0] - 1; - - // new data has same length, do in-order replacement - if (len == dataLength) { - for (uint8_t idx = 0; idx < dataLength; idx++) { - field[2 + idx] = payload[idx]; - } - - result = BLE_ERROR_NONE; - } else { - // check if data fits - if ((_payloadLen - dataLength + len) <= GAP_ADVERTISING_DATA_MAX_PAYLOAD) { - - // remove old field - while ((field + dataLength + 2) < &_payload[_payloadLen]) { - *field = field[dataLength + 2]; - field++; - } - - // reduce length - _payloadLen -= dataLength + 2; - - // add new field - result = appendField(advDataType, payload, len); - } - } - - return result; - } - uint8_t _payload[GAP_ADVERTISING_DATA_MAX_PAYLOAD]; uint8_t _payloadLen; uint16_t _appearance;
--- a/ble/GattAttribute.h Tue Jan 12 19:47:52 2016 +0000 +++ b/ble/GattAttribute.h Wed Apr 06 18:40:26 2016 +0100 @@ -37,8 +37,6 @@ * The length in bytes of this attribute's value. * @param[in] maxLen * The max length in bytes of this attribute's value. - * @param[in] hasVariableLen - * Whether the attribute's value length changes overtime. * * @section EXAMPLE * @@ -49,27 +47,25 @@ * * @endcode */ - GattAttribute(const UUID &uuid, uint8_t *valuePtr = NULL, uint16_t len = 0, uint16_t maxLen = 0, bool hasVariableLen = true) : - _uuid(uuid), _valuePtr(valuePtr), _lenMax(maxLen), _len(len), _hasVariableLen(hasVariableLen), _handle() { + GattAttribute(const UUID &uuid, uint8_t *valuePtr = NULL, uint16_t len = 0, uint16_t maxLen = 0) : + _uuid(uuid), _valuePtr(valuePtr), _lenMax(maxLen), _len(len), _handle() { /* Empty */ } public: - Handle_t getHandle(void) const {return _handle; } - const UUID &getUUID(void) const {return _uuid; } - uint16_t getLength(void) const {return _len; } - uint16_t getMaxLength(void) const {return _lenMax; } - uint16_t *getLengthPtr(void) {return &_len; } - void setHandle(Handle_t id) {_handle = id; } - uint8_t *getValuePtr(void) {return _valuePtr; } - bool hasVariableLength(void) const {return _hasVariableLen;} + Handle_t getHandle(void) const {return _handle; } + const UUID &getUUID(void) const {return _uuid; } + uint16_t getLength(void) const {return _len; } + uint16_t getMaxLength(void) const {return _lenMax; } + uint16_t *getLengthPtr(void) {return &_len; } + void setHandle(Handle_t id) {_handle = id; } + uint8_t *getValuePtr(void) {return _valuePtr; } private: - UUID _uuid; /* Characteristic UUID. */ + UUID _uuid; /* Characteristic UUID. */ uint8_t *_valuePtr; - uint16_t _lenMax; /* Maximum length of the value. */ - uint16_t _len; /* Current length of the value. */ - bool _hasVariableLen; + uint16_t _lenMax; /* Maximum length of the value. */ + uint16_t _len; /* Current length of the value. */ Handle_t _handle; private:
--- a/ble/GattCharacteristic.h Tue Jan 12 19:47:52 2016 +0000 +++ b/ble/GattCharacteristic.h Wed Apr 06 18:40:26 2016 +0100 @@ -311,8 +311,6 @@ * The length in bytes of this characteristic's value. * @param[in] maxLen * The max length in bytes of this characteristic's value. - * @param[in] hasVariableLen - * Whether the attribute's value length changes over time. * @param[in] props * The 8-bit field containing the characteristic's properties. * @param[in] descriptors @@ -334,9 +332,8 @@ uint16_t maxLen = 0, uint8_t props = BLE_GATT_CHAR_PROPERTIES_NONE, GattAttribute *descriptors[] = NULL, - unsigned numDescriptors = 0, - bool hasVariableLen = true) : - _valueAttribute(uuid, valuePtr, len, maxLen, hasVariableLen), + unsigned numDescriptors = 0) : + _valueAttribute(uuid, valuePtr, len, maxLen), _properties(props), _requiredSecurity(SecurityManager::SECURITY_MODE_ENCRYPTION_OPEN_LINK), _descriptors(descriptors), @@ -469,7 +466,7 @@ GattAttribute *descriptors[] = NULL, unsigned numDescriptors = 0) : GattCharacteristic(uuid, reinterpret_cast<uint8_t *>(valuePtr), sizeof(T), sizeof(T), - BLE_GATT_CHAR_PROPERTIES_READ | additionalProperties, descriptors, numDescriptors, false) { + BLE_GATT_CHAR_PROPERTIES_READ | additionalProperties, descriptors, numDescriptors) { /* empty */ } }; @@ -525,7 +522,7 @@ GattAttribute *descriptors[] = NULL, unsigned numDescriptors = 0) : GattCharacteristic(uuid, reinterpret_cast<uint8_t *>(valuePtr), sizeof(T) * NUM_ELEMENTS, sizeof(T) * NUM_ELEMENTS, - BLE_GATT_CHAR_PROPERTIES_READ | additionalProperties, descriptors, numDescriptors, false) { + BLE_GATT_CHAR_PROPERTIES_READ | additionalProperties, descriptors, numDescriptors) { /* empty */ } };
--- a/ble/GattClient.h Tue Jan 12 19:47:52 2016 +0000 +++ b/ble/GattClient.h Wed Apr 06 18:40:26 2016 +0100 @@ -20,7 +20,6 @@ #include "Gap.h" #include "GattAttribute.h" #include "ServiceDiscovery.h" -#include "CharacteristicDescriptorDiscovery.h" #include "GattCallbackParamTypes.h" @@ -42,9 +41,6 @@ typedef FunctionPointerWithContext<const GattHVXCallbackParams*> HVXCallback_t; typedef CallChainOfFunctionPointersWithContext<const GattHVXCallbackParams*> HVXCallbackChain_t; - typedef FunctionPointerWithContext<const GattClient *> GattClientShutdownCallback_t; - typedef CallChainOfFunctionPointersWithContext<const GattClient *> GattClientShutdownCallbackChain_t; - /* * The following functions are meant to be overridden in the platform-specific sub-class. */ @@ -220,8 +216,8 @@ * Initiate a GATT Client write procedure. * * @param[in] cmd - * Command can be either a write-request (which generates a - * matching response from the peripheral), or a write-command + * Command can be either a write-request (which generates a + * matching response from the peripheral), or a write-command * (which doesn't require the connected peer to respond). * @param[in] connHandle * Connection handle. @@ -250,8 +246,8 @@ /* Event callback handlers. */ public: /** - * Set up a callback for read response events. - * It is possible to remove registered callbacks using + * Set up a callback for read response events. + * It is possible to remove registered callbacks using * onDataRead().detach(callbackToRemove) */ void onDataRead(ReadCallback_t callback) { @@ -261,7 +257,7 @@ /** * @brief provide access to the callchain of read callbacks * It is possible to register callbacks using onDataRead().add(callback); - * It is possible to unregister callbacks using onDataRead().detach(callback) + * It is possible to unregister callbacks using onDataRead().detach(callback) * @return The read callbacks chain */ ReadCallbackChain_t& onDataRead() { @@ -270,7 +266,7 @@ /** * Set up a callback for write response events. - * It is possible to remove registered callbacks using + * It is possible to remove registered callbacks using * onDataWritten().detach(callbackToRemove). * @Note: Write commands (issued using writeWoResponse) don't generate a response. */ @@ -281,10 +277,10 @@ /** * @brief provide access to the callchain of data written callbacks * It is possible to register callbacks using onDataWritten().add(callback); - * It is possible to unregister callbacks using onDataWritten().detach(callback) + * It is possible to unregister callbacks using onDataWritten().detach(callback) * @return The data written callbacks chain */ - WriteCallbackChain_t& onDataWritten() { + WriteCallbackChain_t& onDataWritten() { return onDataWriteCallbackChain; } @@ -309,59 +305,6 @@ } /** - * @brief launch discovery of descriptors for a given characteristic - * @details This function will discover all descriptors available for a - * specific characteristic. - * - * @param characteristic[in] The characteristic targeted by this discovery - * procedure - * @param discoveryCallback[in] User function called each time a descriptor - * is found during the procedure. - * @param terminationCallback[in] User provided function which will be called - * once the discovery procedure is terminating. This will get called when all - * the descriptors have been discovered or if an error occur during the discovery - * procedure. - * - * @return - * BLE_ERROR_NONE if characteristic descriptor discovery is launched - * successfully; else an appropriate error. - */ - virtual ble_error_t discoverCharacteristicDescriptors( - const DiscoveredCharacteristic& characteristic, - const CharacteristicDescriptorDiscovery::DiscoveryCallback_t& discoveryCallback, - const CharacteristicDescriptorDiscovery::TerminationCallback_t& terminationCallback) { - (void) characteristic; - (void) discoveryCallback; - (void) terminationCallback; - /* Requesting action from porter(s): override this API if this capability is supported. */ - return BLE_ERROR_NOT_IMPLEMENTED; - } - - /** - * @brief Indicate if the discovery of characteristic descriptors is active for a given characteristic - * or not. - * @param characteristic[in] The characteristic concerned by the descriptors discovery. - * @return true if a descriptors discovery is active for the characteristic in input; otherwise false. - */ - virtual bool isCharacteristicDescriptorDiscoveryActive(const DiscoveredCharacteristic& characteristic) const - { - (void) characteristic; - return false; /* Requesting action from porter(s): override this API if this capability is supported. */ - } - - /** - * @brief Terminate an ongoing characteristic descriptor discovery. - * @detail This should result in an invocation of the TerminationCallback if - * the characteristic descriptor discovery is active. - * @param characteristic[in] The characteristic on which the running descriptors - * discovery should be stopped. - */ - virtual void terminateCharacteristicDescriptorDiscovery(const DiscoveredCharacteristic& characteristic) { - /* Requesting action from porter(s): override this API if this capability is supported. */ - (void) characteristic; - } - - /** * Set up a callback for when the GATT client receives an update event * corresponding to a change in the value of a characteristic on the remote * GATT server. @@ -371,74 +314,17 @@ onHVXCallbackChain.add(callback); } - /** - * Setup a callback to be invoked to notify the user application that the - * GattClient instance is about to shutdown (possibly as a result of a call - * to BLE::shutdown()). - * - * @Note: It is possible to chain together multiple onShutdown callbacks - * (potentially from different modules of an application) to be notified - * before the GattClient is shutdown. - * - * @Note: It is also possible to set up a callback into a member function of - * some object. - * - * @Note It is possible to unregister a callback using onShutdown().detach(callback) - */ - void onShutdown(const GattClientShutdownCallback_t& callback) { - shutdownCallChain.add(callback); - } - template <typename T> - void onShutdown(T *objPtr, void (T::*memberPtr)(void)) { - shutdownCallChain.add(objPtr, memberPtr); - } - - /** - * @brief provide access to the callchain of shutdown event callbacks - * It is possible to register callbacks using onShutdown().add(callback); - * It is possible to unregister callbacks using onShutdown().detach(callback) - * @return The shutdown event callbacks chain - */ - GattClientShutdownCallbackChain_t& onShutdown() { - return shutdownCallChain; - } /** * @brief provide access to the callchain of HVX callbacks * It is possible to register callbacks using onHVX().add(callback); - * It is possible to unregister callbacks using onHVX().detach(callback) + * It is possible to unregister callbacks using onHVX().detach(callback) * @return The HVX callbacks chain */ - HVXCallbackChain_t& onHVX() { + HVXCallbackChain_t& onHVX() { return onHVXCallbackChain; } -public: - /** - * Notify all registered onShutdown callbacks that the GattClient is - * about to be shutdown and clear all GattClient state of the - * associated object. - * - * This function is meant to be overridden in the platform-specific - * sub-class. Nevertheless, the sub-class is only expected to reset its - * state and not the data held in GattClient members. This shall be achieved - * by a call to GattClient::reset() from the sub-class' reset() - * implementation. - * - * @return BLE_ERROR_NONE on success. - */ - virtual ble_error_t reset(void) { - /* Notify that the instance is about to shutdown */ - shutdownCallChain.call(this); - shutdownCallChain.clear(); - - onDataReadCallbackChain.clear(); - onDataWriteCallbackChain.clear(); - onHVXCallbackChain.clear(); - - return BLE_ERROR_NONE; - } - protected: GattClient() { /* Empty */ @@ -461,10 +347,9 @@ } protected: - ReadCallbackChain_t onDataReadCallbackChain; - WriteCallbackChain_t onDataWriteCallbackChain; - HVXCallbackChain_t onHVXCallbackChain; - GattClientShutdownCallbackChain_t shutdownCallChain; + ReadCallbackChain_t onDataReadCallbackChain; + WriteCallbackChain_t onDataWriteCallbackChain; + HVXCallbackChain_t onHVXCallbackChain; private: /* Disallow copy and assignment. */
--- a/ble/GattServer.h Tue Jan 12 19:47:52 2016 +0000 +++ b/ble/GattServer.h Wed Apr 06 18:40:26 2016 +0100 @@ -26,19 +26,17 @@ class GattServer { public: + /* Event callback handlers. */ typedef FunctionPointerWithContext<unsigned> DataSentCallback_t; typedef CallChainOfFunctionPointersWithContext<unsigned> DataSentCallbackChain_t; typedef FunctionPointerWithContext<const GattWriteCallbackParams*> DataWrittenCallback_t; - typedef CallChainOfFunctionPointersWithContext<const GattWriteCallbackParams*> DataWrittenCallbackChain_t; + typedef CallChainOfFunctionPointersWithContext<const GattWriteCallbackParams*> DataWrittenCallbackChain_t; typedef FunctionPointerWithContext<const GattReadCallbackParams*> DataReadCallback_t; typedef CallChainOfFunctionPointersWithContext<const GattReadCallbackParams *> DataReadCallbackChain_t; - typedef FunctionPointerWithContext<const GattServer *> GattServerShutdownCallback_t; - typedef CallChainOfFunctionPointersWithContext<const GattServer *> GattServerShutdownCallbackChain_t; - typedef FunctionPointerWithContext<GattAttribute::Handle_t> EventCallback_t; protected: @@ -256,9 +254,9 @@ } /** - * @brief get the callback chain called when the event DATA_EVENT is triggered. + * @brief get the callback chain called when the event DATA_EVENT is triggered. */ - DataSentCallbackChain_t& onDataSent() { + DataSentCallbackChain_t& onDataSent() { return dataSentCallChain; } @@ -276,7 +274,7 @@ * * @Note: It is also possible to set up a callback into a member function of * some object. - * + * * @Note It is possible to unregister a callback using onDataWritten().detach(callback) */ void onDataWritten(const DataWrittenCallback_t& callback) {dataWrittenCallChain.add(callback);} @@ -288,9 +286,9 @@ /** * @brief provide access to the callchain of data written event callbacks * It is possible to register callbacks using onDataWritten().add(callback); - * It is possible to unregister callbacks using onDataWritten().detach(callback) + * It is possible to unregister callbacks using onDataWritten().detach(callback) * @return The data written event callbacks chain - */ + */ DataWrittenCallbackChain_t& onDataWritten() { return dataWrittenCallChain; } @@ -337,7 +335,7 @@ /** * @brief provide access to the callchain of data read event callbacks * It is possible to register callbacks using onDataRead().add(callback); - * It is possible to unregister callbacks using onDataRead().detach(callback) + * It is possible to unregister callbacks using onDataRead().detach(callback) * @return The data read event callbacks chain */ DataReadCallbackChain_t& onDataRead() { @@ -345,38 +343,6 @@ } /** - * Setup a callback to be invoked to notify the user application that the - * GattServer instance is about to shutdown (possibly as a result of a call - * to BLE::shutdown()). - * - * @Note: It is possible to chain together multiple onShutdown callbacks - * (potentially from different modules of an application) to be notified - * before the GattServer is shutdown. - * - * @Note: It is also possible to set up a callback into a member function of - * some object. - * - * @Note It is possible to unregister a callback using onShutdown().detach(callback) - */ - void onShutdown(const GattServerShutdownCallback_t& callback) { - shutdownCallChain.add(callback); - } - template <typename T> - void onShutdown(T *objPtr, void (T::*memberPtr)(void)) { - shutdownCallChain.add(objPtr, memberPtr); - } - - /** - * @brief provide access to the callchain of shutdown event callbacks - * It is possible to register callbacks using onShutdown().add(callback); - * It is possible to unregister callbacks using onShutdown().detach(callback) - * @return The shutdown event callbacks chain - */ - GattServerShutdownCallbackChain_t& onShutdown() { - return shutdownCallChain; - } - - /** * Set up a callback for when notifications or indications are enabled for a * characteristic on the local GATT server. */ @@ -430,50 +396,17 @@ dataSentCallChain.call(count); } -public: - /** - * Notify all registered onShutdown callbacks that the GattServer is - * about to be shutdown and clear all GattServer state of the - * associated object. - * - * This function is meant to be overridden in the platform-specific - * sub-class. Nevertheless, the sub-class is only expected to reset its - * state and not the data held in GattServer members. This shall be achieved - * by a call to GattServer::reset() from the sub-class' reset() - * implementation. - * - * @return BLE_ERROR_NONE on success. - */ - virtual ble_error_t reset(void) { - /* Notify that the instance is about to shutdown */ - shutdownCallChain.call(this); - shutdownCallChain.clear(); - - serviceCount = 0; - characteristicCount = 0; - - dataSentCallChain.clear(); - dataWrittenCallChain.clear(); - dataReadCallChain.clear(); - updatesEnabledCallback = NULL; - updatesDisabledCallback = NULL; - confirmationReceivedCallback = NULL; - - return BLE_ERROR_NONE; - } - protected: uint8_t serviceCount; uint8_t characteristicCount; private: - DataSentCallbackChain_t dataSentCallChain; - DataWrittenCallbackChain_t dataWrittenCallChain; - DataReadCallbackChain_t dataReadCallChain; - GattServerShutdownCallbackChain_t shutdownCallChain; - EventCallback_t updatesEnabledCallback; - EventCallback_t updatesDisabledCallback; - EventCallback_t confirmationReceivedCallback; + DataSentCallbackChain_t dataSentCallChain; + DataWrittenCallbackChain_t dataWrittenCallChain; + DataReadCallbackChain_t dataReadCallChain; + EventCallback_t updatesEnabledCallback; + EventCallback_t updatesDisabledCallback; + EventCallback_t confirmationReceivedCallback; private: /* Disallow copy and assignment. */
--- a/ble/SecurityManager.h Tue Jan 12 19:47:52 2016 +0000 +++ b/ble/SecurityManager.h Wed Apr 06 18:40:26 2016 +0100 @@ -1,331 +1,225 @@ -/* mbed Microcontroller Library - * Copyright (c) 2006-2015 ARM Limited - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef __SECURITY_MANAGER_H__ -#define __SECURITY_MANAGER_H__ - -#include <stdint.h> - -#include "Gap.h" -#include "CallChainOfFunctionPointersWithContext.h" - -class SecurityManager { -public: - enum SecurityMode_t { - SECURITY_MODE_NO_ACCESS, - SECURITY_MODE_ENCRYPTION_OPEN_LINK, /**< Require no protection, open link. */ - SECURITY_MODE_ENCRYPTION_NO_MITM, /**< Require encryption, but no MITM protection. */ - SECURITY_MODE_ENCRYPTION_WITH_MITM, /**< Require encryption and MITM protection. */ - SECURITY_MODE_SIGNED_NO_MITM, /**< Require signing or encryption, but no MITM protection. */ - SECURITY_MODE_SIGNED_WITH_MITM, /**< Require signing or encryption, and MITM protection. */ - }; - - /** - * @brief Defines possible security status or states. - * - * @details Defines possible security status or states of a link when requested by getLinkSecurity(). - */ - enum LinkSecurityStatus_t { - NOT_ENCRYPTED, /**< The link is not secured. */ - ENCRYPTION_IN_PROGRESS, /**< Link security is being established.*/ - ENCRYPTED /**< The link is secure.*/ - }; - - enum SecurityIOCapabilities_t { - IO_CAPS_DISPLAY_ONLY = 0x00, /**< Display only. */ - IO_CAPS_DISPLAY_YESNO = 0x01, /**< Display and yes/no entry. */ - IO_CAPS_KEYBOARD_ONLY = 0x02, /**< Keyboard only. */ - IO_CAPS_NONE = 0x03, /**< No I/O capabilities. */ - IO_CAPS_KEYBOARD_DISPLAY = 0x04, /**< Keyboard and display. */ - }; - - enum SecurityCompletionStatus_t { - SEC_STATUS_SUCCESS = 0x00, /**< Procedure completed with success. */ - SEC_STATUS_TIMEOUT = 0x01, /**< Procedure timed out. */ - SEC_STATUS_PDU_INVALID = 0x02, /**< Invalid PDU received. */ - SEC_STATUS_PASSKEY_ENTRY_FAILED = 0x81, /**< Passkey entry failed (user canceled or other). */ - SEC_STATUS_OOB_NOT_AVAILABLE = 0x82, /**< Out of Band Key not available. */ - SEC_STATUS_AUTH_REQ = 0x83, /**< Authentication requirements not met. */ - SEC_STATUS_CONFIRM_VALUE = 0x84, /**< Confirm value failed. */ - SEC_STATUS_PAIRING_NOT_SUPP = 0x85, /**< Pairing not supported. */ - SEC_STATUS_ENC_KEY_SIZE = 0x86, /**< Encryption key size. */ - SEC_STATUS_SMP_CMD_UNSUPPORTED = 0x87, /**< Unsupported SMP command. */ - SEC_STATUS_UNSPECIFIED = 0x88, /**< Unspecified reason. */ - SEC_STATUS_REPEATED_ATTEMPTS = 0x89, /**< Too little time elapsed since last attempt. */ - SEC_STATUS_INVALID_PARAMS = 0x8A, /**< Invalid parameters. */ - }; - - /** - * Declaration of type containing a passkey to be used during pairing. This - * is passed into initializeSecurity() to specify a pre-programmed passkey - * for authentication instead of generating a random one. - */ - static const unsigned PASSKEY_LEN = 6; - typedef uint8_t Passkey_t[PASSKEY_LEN]; /**< 6-digit passkey in ASCII ('0'-'9' digits only). */ - -public: - typedef void (*HandleSpecificEvent_t)(Gap::Handle_t handle); - typedef void (*SecuritySetupInitiatedCallback_t)(Gap::Handle_t, bool allowBonding, bool requireMITM, SecurityIOCapabilities_t iocaps); - typedef void (*SecuritySetupCompletedCallback_t)(Gap::Handle_t, SecurityCompletionStatus_t status); - typedef void (*LinkSecuredCallback_t)(Gap::Handle_t handle, SecurityMode_t securityMode); - typedef void (*PasskeyDisplayCallback_t)(Gap::Handle_t handle, const Passkey_t passkey); - - typedef FunctionPointerWithContext<const SecurityManager *> SecurityManagerShutdownCallback_t; - typedef CallChainOfFunctionPointersWithContext<const SecurityManager *> SecurityManagerShutdownCallbackChain_t; - - /* - * The following functions are meant to be overridden in the platform-specific sub-class. - */ -public: - /** - * Enable the BLE stack's Security Manager. The Security Manager implements - * the actual cryptographic algorithms and protocol exchanges that allow two - * devices to securely exchange data and privately detect each other. - * Calling this API is a prerequisite for encryption and pairing (bonding). - * - * @param[in] enableBonding Allow for bonding. - * @param[in] requireMITM Require protection for man-in-the-middle attacks. - * @param[in] iocaps To specify the I/O capabilities of this peripheral, - * such as availability of a display or keyboard, to - * support out-of-band exchanges of security data. - * @param[in] passkey To specify a static passkey. - * - * @return BLE_ERROR_NONE on success. - */ - virtual ble_error_t init(bool enableBonding = true, - bool requireMITM = true, - SecurityIOCapabilities_t iocaps = IO_CAPS_NONE, - const Passkey_t passkey = NULL) { - /* Avoid compiler warnings about unused variables. */ - (void)enableBonding; - (void)requireMITM; - (void)iocaps; - (void)passkey; - - return BLE_ERROR_NOT_IMPLEMENTED; /* Requesting action from porters: override this API if security is supported. */ - } - - /** - * Get the security status of a connection. - * - * @param[in] connectionHandle Handle to identify the connection. - * @param[out] securityStatusP Security status. - * - * @return BLE_ERROR_NONE or appropriate error code indicating the failure reason. - */ - virtual ble_error_t getLinkSecurity(Gap::Handle_t connectionHandle, LinkSecurityStatus_t *securityStatusP) { - /* Avoid compiler warnings about unused variables. */ - (void)connectionHandle; - (void)securityStatusP; - - return BLE_ERROR_NOT_IMPLEMENTED; /* Requesting action from porters: override this API if security is supported. */ - } - - /** - * Set the security mode on a connection. Useful for elevating the security mode - * once certain conditions are met, e.g., a particular service is found. - * - * @param[in] connectionHandle Handle to identify the connection. - * @param[in] securityMode Requested security mode. - * - * @return BLE_ERROR_NONE or appropriate error code indicating the failure reason. - */ - virtual ble_error_t setLinkSecurity(Gap::Handle_t connectionHandle, SecurityMode_t securityMode) { - /* Avoid compiler warnings about unused variables. */ - (void)connectionHandle; - (void)securityMode; - - return BLE_ERROR_NOT_IMPLEMENTED; - } - - /** - * Delete all peer device context and all related bonding information from - * the database within the security manager. - * - * @retval BLE_ERROR_NONE On success, else an error code indicating reason for failure. - * @retval BLE_ERROR_INVALID_STATE If the API is called without module initialization or - * application registration. - */ - virtual ble_error_t purgeAllBondingState(void) { - return BLE_ERROR_NOT_IMPLEMENTED; /* Requesting action from porters: override this API if security is supported. */ - } - - /** - * Get a list of addresses from all peers in the bond table. - * - * @param[in/out] addresses - * (on input) addresses.capacity contains the maximum - * number of addresses to be returned. - * (on output) The populated table with copies of the - * addresses in the implementation's whitelist. - * - * @retval BLE_ERROR_NONE On success, else an error code indicating reason for failure. - * @retval BLE_ERROR_INVALID_STATE If the API is called without module initialization or - * application registration. - * - * @experimental - */ - virtual ble_error_t getAddressesFromBondTable(Gap::Whitelist_t &addresses) const { - /* Avoid compiler warnings about unused variables */ - (void) addresses; - - return BLE_ERROR_NOT_IMPLEMENTED; /* Requesting action from porters: override this API if security is supported. */ - } - - /* Event callback handlers. */ -public: - /** - * Setup a callback to be invoked to notify the user application that the - * SecurityManager instance is about to shutdown (possibly as a result of a call - * to BLE::shutdown()). - * - * @Note: It is possible to chain together multiple onShutdown callbacks - * (potentially from different modules of an application) to be notified - * before the SecurityManager is shutdown. - * - * @Note: It is also possible to set up a callback into a member function of - * some object. - * - * @Note It is possible to unregister a callback using onShutdown().detach(callback) - */ - void onShutdown(const SecurityManagerShutdownCallback_t& callback) { - shutdownCallChain.add(callback); - } - template <typename T> - void onShutdown(T *objPtr, void (T::*memberPtr)(void)) { - shutdownCallChain.add(objPtr, memberPtr); - } - - /** - * @brief provide access to the callchain of shutdown event callbacks - * It is possible to register callbacks using onShutdown().add(callback); - * It is possible to unregister callbacks using onShutdown().detach(callback) - * @return The shutdown event callbacks chain - */ - SecurityManagerShutdownCallbackChain_t& onShutdown() { - return shutdownCallChain; - } - - /** - * To indicate that a security procedure for the link has started. - */ - virtual void onSecuritySetupInitiated(SecuritySetupInitiatedCallback_t callback) {securitySetupInitiatedCallback = callback;} - - /** - * To indicate that the security procedure for the link has completed. - */ - virtual void onSecuritySetupCompleted(SecuritySetupCompletedCallback_t callback) {securitySetupCompletedCallback = callback;} - - /** - * To indicate that the link with the peer is secured. For bonded devices, - * subsequent reconnections with a bonded peer will result only in this callback - * when the link is secured; setup procedures will not occur (unless the - * bonding information is either lost or deleted on either or both sides). - */ - virtual void onLinkSecured(LinkSecuredCallback_t callback) {linkSecuredCallback = callback;} - - /** - * To indicate that device context is stored persistently. - */ - virtual void onSecurityContextStored(HandleSpecificEvent_t callback) {securityContextStoredCallback = callback;} - - /** - * To set the callback for when the passkey needs to be displayed on a peripheral with DISPLAY capability. - */ - virtual void onPasskeyDisplay(PasskeyDisplayCallback_t callback) {passkeyDisplayCallback = callback;} - - /* Entry points for the underlying stack to report events back to the user. */ -public: - void processSecuritySetupInitiatedEvent(Gap::Handle_t handle, bool allowBonding, bool requireMITM, SecurityIOCapabilities_t iocaps) { - if (securitySetupInitiatedCallback) { - securitySetupInitiatedCallback(handle, allowBonding, requireMITM, iocaps); - } - } - - void processSecuritySetupCompletedEvent(Gap::Handle_t handle, SecurityCompletionStatus_t status) { - if (securitySetupCompletedCallback) { - securitySetupCompletedCallback(handle, status); - } - } - - void processLinkSecuredEvent(Gap::Handle_t handle, SecurityMode_t securityMode) { - if (linkSecuredCallback) { - linkSecuredCallback(handle, securityMode); - } - } - - void processSecurityContextStoredEvent(Gap::Handle_t handle) { - if (securityContextStoredCallback) { - securityContextStoredCallback(handle); - } - } - - void processPasskeyDisplayEvent(Gap::Handle_t handle, const Passkey_t passkey) { - if (passkeyDisplayCallback) { - passkeyDisplayCallback(handle, passkey); - } - } - -protected: - SecurityManager() : - securitySetupInitiatedCallback(), - securitySetupCompletedCallback(), - linkSecuredCallback(), - securityContextStoredCallback(), - passkeyDisplayCallback() { - /* empty */ - } - -public: - /** - * Notify all registered onShutdown callbacks that the SecurityManager is - * about to be shutdown and clear all SecurityManager state of the - * associated object. - * - * This function is meant to be overridden in the platform-specific - * sub-class. Nevertheless, the sub-class is only expected to reset its - * state and not the data held in SecurityManager members. This shall be - * achieved by a call to SecurityManager::reset() from the sub-class' - * reset() implementation. - * - * @return BLE_ERROR_NONE on success. - */ - virtual ble_error_t reset(void) { - /* Notify that the instance is about to shutdown */ - shutdownCallChain.call(this); - shutdownCallChain.clear(); - - securitySetupInitiatedCallback = NULL; - securitySetupCompletedCallback = NULL; - linkSecuredCallback = NULL; - securityContextStoredCallback = NULL; - passkeyDisplayCallback = NULL; - - return BLE_ERROR_NONE; - } - -protected: - SecuritySetupInitiatedCallback_t securitySetupInitiatedCallback; - SecuritySetupCompletedCallback_t securitySetupCompletedCallback; - LinkSecuredCallback_t linkSecuredCallback; - HandleSpecificEvent_t securityContextStoredCallback; - PasskeyDisplayCallback_t passkeyDisplayCallback; - -private: - SecurityManagerShutdownCallbackChain_t shutdownCallChain; -}; - +/* mbed Microcontroller Library + * Copyright (c) 2006-2015 ARM Limited + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef __SECURITY_MANAGER_H__ +#define __SECURITY_MANAGER_H__ + +#include <stdint.h> + +#include "Gap.h" + +class SecurityManager { +public: + enum SecurityMode_t { + SECURITY_MODE_NO_ACCESS, + SECURITY_MODE_ENCRYPTION_OPEN_LINK, /**< Require no protection, open link. */ + SECURITY_MODE_ENCRYPTION_NO_MITM, /**< Require encryption, but no MITM protection. */ + SECURITY_MODE_ENCRYPTION_WITH_MITM, /**< Require encryption and MITM protection. */ + SECURITY_MODE_SIGNED_NO_MITM, /**< Require signing or encryption, but no MITM protection. */ + SECURITY_MODE_SIGNED_WITH_MITM, /**< Require signing or encryption, and MITM protection. */ + }; + + /** + * @brief Defines possible security status or states. + * + * @details Defines possible security status or states of a link when requested by getLinkSecurity(). + */ + enum LinkSecurityStatus_t { + NOT_ENCRYPTED, /**< The link is not secured. */ + ENCRYPTION_IN_PROGRESS, /**< Link security is being established.*/ + ENCRYPTED /**< The link is secure.*/ + }; + + enum SecurityIOCapabilities_t { + IO_CAPS_DISPLAY_ONLY = 0x00, /**< Display only. */ + IO_CAPS_DISPLAY_YESNO = 0x01, /**< Display and yes/no entry. */ + IO_CAPS_KEYBOARD_ONLY = 0x02, /**< Keyboard only. */ + IO_CAPS_NONE = 0x03, /**< No I/O capabilities. */ + IO_CAPS_KEYBOARD_DISPLAY = 0x04, /**< Keyboard and display. */ + }; + + enum SecurityCompletionStatus_t { + SEC_STATUS_SUCCESS = 0x00, /**< Procedure completed with success. */ + SEC_STATUS_TIMEOUT = 0x01, /**< Procedure timed out. */ + SEC_STATUS_PDU_INVALID = 0x02, /**< Invalid PDU received. */ + SEC_STATUS_PASSKEY_ENTRY_FAILED = 0x81, /**< Passkey entry failed (user canceled or other). */ + SEC_STATUS_OOB_NOT_AVAILABLE = 0x82, /**< Out of Band Key not available. */ + SEC_STATUS_AUTH_REQ = 0x83, /**< Authentication requirements not met. */ + SEC_STATUS_CONFIRM_VALUE = 0x84, /**< Confirm value failed. */ + SEC_STATUS_PAIRING_NOT_SUPP = 0x85, /**< Pairing not supported. */ + SEC_STATUS_ENC_KEY_SIZE = 0x86, /**< Encryption key size. */ + SEC_STATUS_SMP_CMD_UNSUPPORTED = 0x87, /**< Unsupported SMP command. */ + SEC_STATUS_UNSPECIFIED = 0x88, /**< Unspecified reason. */ + SEC_STATUS_REPEATED_ATTEMPTS = 0x89, /**< Too little time elapsed since last attempt. */ + SEC_STATUS_INVALID_PARAMS = 0x8A, /**< Invalid parameters. */ + }; + + /** + * Declaration of type containing a passkey to be used during pairing. This + * is passed into initializeSecurity() to specify a pre-programmed passkey + * for authentication instead of generating a random one. + */ + static const unsigned PASSKEY_LEN = 6; + typedef uint8_t Passkey_t[PASSKEY_LEN]; /**< 6-digit passkey in ASCII ('0'-'9' digits only). */ + +public: + typedef void (*HandleSpecificEvent_t)(Gap::Handle_t handle); + typedef void (*SecuritySetupInitiatedCallback_t)(Gap::Handle_t, bool allowBonding, bool requireMITM, SecurityIOCapabilities_t iocaps); + typedef void (*SecuritySetupCompletedCallback_t)(Gap::Handle_t, SecurityCompletionStatus_t status); + typedef void (*LinkSecuredCallback_t)(Gap::Handle_t handle, SecurityMode_t securityMode); + typedef void (*PasskeyDisplayCallback_t)(Gap::Handle_t handle, const Passkey_t passkey); + + /* + * The following functions are meant to be overridden in the platform-specific sub-class. + */ +public: + /** + * Enable the BLE stack's Security Manager. The Security Manager implements + * the actual cryptographic algorithms and protocol exchanges that allow two + * devices to securely exchange data and privately detect each other. + * Calling this API is a prerequisite for encryption and pairing (bonding). + * + * @param[in] enableBonding Allow for bonding. + * @param[in] requireMITM Require protection for man-in-the-middle attacks. + * @param[in] iocaps To specify the I/O capabilities of this peripheral, + * such as availability of a display or keyboard, to + * support out-of-band exchanges of security data. + * @param[in] passkey To specify a static passkey. + * + * @return BLE_ERROR_NONE on success. + */ + virtual ble_error_t init(bool enableBonding = true, + bool requireMITM = true, + SecurityIOCapabilities_t iocaps = IO_CAPS_NONE, + const Passkey_t passkey = NULL) { + /* Avoid compiler warnings about unused variables. */ + (void)enableBonding; + (void)requireMITM; + (void)iocaps; + (void)passkey; + + return BLE_ERROR_NOT_IMPLEMENTED; /* Requesting action from porters: override this API if security is supported. */ + } + + /** + * Get the security status of a connection. + * + * @param[in] connectionHandle Handle to identify the connection. + * @param[out] securityStatusP Security status. + * + * @return BLE_SUCCESS or appropriate error code indicating the failure reason. + */ + virtual ble_error_t getLinkSecurity(Gap::Handle_t connectionHandle, LinkSecurityStatus_t *securityStatusP) { + /* Avoid compiler warnings about unused variables. */ + (void)connectionHandle; + (void)securityStatusP; + + return BLE_ERROR_NOT_IMPLEMENTED; /* Requesting action from porters: override this API if security is supported. */ + } + + /** + * Delete all peer device context and all related bonding information from + * the database within the security manager. + * + * @retval BLE_ERROR_NONE On success, else an error code indicating reason for failure. + * @retval BLE_ERROR_INVALID_STATE If the API is called without module initialization or + * application registration. + */ + virtual ble_error_t purgeAllBondingState(void) { + return BLE_ERROR_NOT_IMPLEMENTED; /* Requesting action from porters: override this API if security is supported. */ + } + + /* Event callback handlers. */ +public: + /** + * To indicate that a security procedure for the link has started. + */ + virtual void onSecuritySetupInitiated(SecuritySetupInitiatedCallback_t callback) {securitySetupInitiatedCallback = callback;} + + /** + * To indicate that the security procedure for the link has completed. + */ + virtual void onSecuritySetupCompleted(SecuritySetupCompletedCallback_t callback) {securitySetupCompletedCallback = callback;} + + /** + * To indicate that the link with the peer is secured. For bonded devices, + * subsequent reconnections with a bonded peer will result only in this callback + * when the link is secured; setup procedures will not occur (unless the + * bonding information is either lost or deleted on either or both sides). + */ + virtual void onLinkSecured(LinkSecuredCallback_t callback) {linkSecuredCallback = callback;} + + /** + * To indicate that device context is stored persistently. + */ + virtual void onSecurityContextStored(HandleSpecificEvent_t callback) {securityContextStoredCallback = callback;} + + /** + * To set the callback for when the passkey needs to be displayed on a peripheral with DISPLAY capability. + */ + virtual void onPasskeyDisplay(PasskeyDisplayCallback_t callback) {passkeyDisplayCallback = callback;} + + /* Entry points for the underlying stack to report events back to the user. */ +public: + void processSecuritySetupInitiatedEvent(Gap::Handle_t handle, bool allowBonding, bool requireMITM, SecurityIOCapabilities_t iocaps) { + if (securitySetupInitiatedCallback) { + securitySetupInitiatedCallback(handle, allowBonding, requireMITM, iocaps); + } + } + + void processSecuritySetupCompletedEvent(Gap::Handle_t handle, SecurityCompletionStatus_t status) { + if (securitySetupCompletedCallback) { + securitySetupCompletedCallback(handle, status); + } + } + + void processLinkSecuredEvent(Gap::Handle_t handle, SecurityMode_t securityMode) { + if (linkSecuredCallback) { + linkSecuredCallback(handle, securityMode); + } + } + + void processSecurityContextStoredEvent(Gap::Handle_t handle) { + if (securityContextStoredCallback) { + securityContextStoredCallback(handle); + } + } + + void processPasskeyDisplayEvent(Gap::Handle_t handle, const Passkey_t passkey) { + if (passkeyDisplayCallback) { + passkeyDisplayCallback(handle, passkey); + } + } + +protected: + SecurityManager() : + securitySetupInitiatedCallback(), + securitySetupCompletedCallback(), + linkSecuredCallback(), + securityContextStoredCallback(), + passkeyDisplayCallback() { + /* empty */ + } + +protected: + SecuritySetupInitiatedCallback_t securitySetupInitiatedCallback; + SecuritySetupCompletedCallback_t securitySetupCompletedCallback; + LinkSecuredCallback_t linkSecuredCallback; + HandleSpecificEvent_t securityContextStoredCallback; + PasskeyDisplayCallback_t passkeyDisplayCallback; +}; + #endif /*__SECURITY_MANAGER_H__*/ \ No newline at end of file
--- a/ble/ServiceDiscovery.h Tue Jan 12 19:47:52 2016 +0000 +++ b/ble/ServiceDiscovery.h Wed Apr 06 18:40:26 2016 +0100 @@ -132,27 +132,6 @@ */ virtual void onTermination(TerminationCallback_t callback) = 0; - /** - * Clear all ServiceDiscovery state of the associated object. - * - * This function is meant to be overridden in the platform-specific - * sub-class. Nevertheless, the sub-class is only expected to reset its - * state and not the data held in ServiceDiscovery members. This shall be - * achieved by a call to ServiceDiscovery::reset() from the sub-class' - * reset() implementation. - * - * @return BLE_ERROR_NONE on success. - */ - virtual ble_error_t reset(void) { - connHandle = 0; - matchingServiceUUID = UUID::ShortUUIDBytes_t(BLE_UUID_UNKNOWN); - serviceCallback = NULL; - matchingCharacteristicUUID = UUID::ShortUUIDBytes_t(BLE_UUID_UNKNOWN); - characteristicCallback = NULL; - - return BLE_ERROR_NONE; - } - protected: Gap::Handle_t connHandle; /**< Connection handle as provided by the SoftDevice. */ UUID matchingServiceUUID;
--- a/ble/UUID.h Tue Jan 12 19:47:52 2016 +0000 +++ b/ble/UUID.h Wed Apr 06 18:40:26 2016 +0100 @@ -19,27 +19,9 @@ #include <stdint.h> #include <string.h> -#include <algorithm> #include "blecommon.h" -/** - * A trivial converter for single hexadecimal character to unsigned-int. - * @param c hexadecimal character. - * @return the corresponding value as unsigned int. - */ -static uint8_t char2int(char c) { - if ((c >= '0') && (c <= '9')) { - return c - '0'; - } else if ((c >= 'a') && (c <= 'f')) { - return c - 'a' + 10; - } else if ((c >= 'A') && (c <= 'F')) { - return c - 'A' + 10; - } else { - return 0; - } -} - class UUID { public: enum UUID_Type_t { @@ -47,75 +29,12 @@ UUID_TYPE_LONG = 1 // Full 128-bit UUID. }; - /** - * An enumeration to specify byte ordering of the long version of the UUID. - */ - typedef enum { - MSB, /*!< Most-significant byte first (at the smallest address) */ - LSB /*!< least-significant byte first (at the smallest address) */ - } ByteOrder_t; - typedef uint16_t ShortUUIDBytes_t; static const unsigned LENGTH_OF_LONG_UUID = 16; typedef uint8_t LongUUIDBytes_t[LENGTH_OF_LONG_UUID]; - static const unsigned MAX_UUID_STRING_LENGTH = LENGTH_OF_LONG_UUID * 2 + 4; - public: - - /** - * Creates a new 128-bit UUID. - * - * @note The UUID is a unique 128-bit (16 byte) ID used to identify - * different service or characteristics on the BLE device. - * - * @param stringUUID - * The 128-bit (16-byte) UUID as a human readable const-string. - * Format: XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX - * Upper and lower case supported. Hyphens are optional, but only - * upto four of them. The UUID is stored internally as a 16 byte - * array, LSB (little endian), which is opposite from the string. - */ - UUID(const char* stringUUID) : type(UUID_TYPE_LONG), baseUUID(), shortUUID(0) { - bool nibble = false; - uint8_t byte = 0; - size_t baseIndex = 0; - uint8_t tempUUID[LENGTH_OF_LONG_UUID]; - - // Iterate through string, abort if NULL is encountered prematurely. - // Ignore upto four hyphens. - for (size_t index = 0; (index < MAX_UUID_STRING_LENGTH) && (baseIndex < LENGTH_OF_LONG_UUID); index++) { - if (stringUUID[index] == '\0') { - // error abort - break; - } else if (stringUUID[index] == '-') { - // ignore hyphen - continue; - } else if (nibble) { - // got second nibble - byte |= char2int(stringUUID[index]); - nibble = false; - - // store copy - tempUUID[baseIndex++] = byte; - } else { - // got first nibble - byte = char2int(stringUUID[index]) << 4; - nibble = true; - } - } - - // populate internal variables if string was successfully parsed - if (baseIndex == LENGTH_OF_LONG_UUID) { - setupLong(tempUUID, UUID::MSB); - } else { - const uint8_t sig[] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x00, - 0x80, 0x00, 0x00, 0x80, 0x5F, 0x9B, 0x34, 0xFB }; - setupLong(sig, UUID::MSB); - } - } - /** * Creates a new 128-bit UUID. * @@ -123,12 +42,10 @@ * different service or characteristics on the BLE device. * * @param longUUID - * The 128-bit (16-byte) UUID value. - * @param order - * The bit order of the UUID, MSB by default. + * The 128-bit (16-byte) UUID value, MSB first (big-endian). */ - UUID(const LongUUIDBytes_t longUUID, ByteOrder_t order = UUID::MSB) : type(UUID_TYPE_LONG), baseUUID(), shortUUID(0) { - setupLong(longUUID, order); + UUID(const LongUUIDBytes_t longUUID) : type(UUID_TYPE_LONG), baseUUID(), shortUUID(0) { + setupLong(longUUID); } /** @@ -152,7 +69,7 @@ * * @note Shortening is not available for UUIDs that are not derived from the * Bluetooth Base UUID. Such non-standard UUIDs are commonly called - * vendor-specific UUIDs. In these cases, you’ll need to use the full + * vendor-specific UUIDs. In these cases, you'll need to use the full * 128-bit UUID value at all times. * * @note We don't yet support 32-bit shortened UUIDs. @@ -174,15 +91,10 @@ /** * Fill in a 128-bit UUID; this is useful when the UUID isn't known at the time of the object construction. */ - void setupLong(const LongUUIDBytes_t longUUID, ByteOrder_t order = UUID::MSB) { + void setupLong(const LongUUIDBytes_t longUUID) { type = UUID_TYPE_LONG; - if (order == UUID::MSB) { - // Switch endian. Input is big-endian, internal representation is little endian. - std::reverse_copy(longUUID, longUUID + LENGTH_OF_LONG_UUID, baseUUID); - } else { - std::copy(longUUID, longUUID + LENGTH_OF_LONG_UUID, baseUUID); - } - shortUUID = (uint16_t)((baseUUID[13] << 8) | (baseUUID[12])); + memcpy(baseUUID, longUUID, LENGTH_OF_LONG_UUID); + shortUUID = (uint16_t)((longUUID[2] << 8) | (longUUID[3])); } public: @@ -220,8 +132,12 @@ private: UUID_Type_t type; // UUID_TYPE_SHORT or UUID_TYPE_LONG - LongUUIDBytes_t baseUUID; // The long UUID - ShortUUIDBytes_t shortUUID; // 16 bit UUID + LongUUIDBytes_t baseUUID; /* The base of the long UUID (if + * used). Note: bytes 12 and 13 (counting from LSB) + * are zeroed out to allow comparison with other long + * UUIDs, which differ only in the 16-bit relative + * part.*/ + ShortUUIDBytes_t shortUUID; // 16 bit UUID (byte 2-3 using with base). }; #endif // ifndef __UUID_H__ \ No newline at end of file
--- a/ble/blecommon.h Tue Jan 12 19:47:52 2016 +0000 +++ b/ble/blecommon.h Wed Apr 06 18:40:26 2016 +0100 @@ -49,6 +49,62 @@ BLE_UUID_GAP_CHARACTERISTIC_PPCP = 0x2A04, /**< Peripheral Preferred Connection Parameters Characteristic. */ }; +/*! Bluetooth appearance values. + * @note Retrieved from http://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.gap.appearance.xml + */ +enum { + BLE_APPEARANCE_UNKNOWN = 0, /**< Unknown. */ + BLE_APPEARANCE_GENERIC_PHONE = 64, /**< Generic Phone. */ + BLE_APPEARANCE_GENERIC_COMPUTER = 128, /**< Generic Computer. */ + BLE_APPEARANCE_GENERIC_WATCH = 192, /**< Generic Watch. */ + BLE_APPEARANCE_WATCH_SPORTS_WATCH = 193, /**< Watch: Sports Watch. */ + BLE_APPEARANCE_GENERIC_CLOCK = 256, /**< Generic Clock. */ + BLE_APPEARANCE_GENERIC_DISPLAY = 320, /**< Generic Display. */ + BLE_APPEARANCE_GENERIC_REMOTE_CONTROL = 384, /**< Generic Remote Control. */ + BLE_APPEARANCE_GENERIC_EYE_GLASSES = 448, /**< Generic Eye-glasses. */ + BLE_APPEARANCE_GENERIC_TAG = 512, /**< Generic Tag. */ + BLE_APPEARANCE_GENERIC_KEYRING = 576, /**< Generic Keyring. */ + BLE_APPEARANCE_GENERIC_MEDIA_PLAYER = 640, /**< Generic Media Player. */ + BLE_APPEARANCE_GENERIC_BARCODE_SCANNER = 704, /**< Generic Barcode Scanner. */ + BLE_APPEARANCE_GENERIC_THERMOMETER = 768, /**< Generic Thermometer. */ + BLE_APPEARANCE_THERMOMETER_EAR = 769, /**< Thermometer: Ear. */ + BLE_APPEARANCE_GENERIC_HEART_RATE_SENSOR = 832, /**< Generic Heart Rate Sensor. */ + BLE_APPEARANCE_HEART_RATE_SENSOR_HEART_RATE_BELT = 833, /**< Heart Rate Sensor: Heart Rate Belt. */ + BLE_APPEARANCE_GENERIC_BLOOD_PRESSURE = 896, /**< Generic Blood Pressure. */ + BLE_APPEARANCE_BLOOD_PRESSURE_ARM = 897, /**< Blood Pressure: Arm. */ + BLE_APPEARANCE_BLOOD_PRESSURE_WRIST = 898, /**< Blood Pressure: Wrist. */ + BLE_APPEARANCE_GENERIC_HID = 960, /**< Human Interface Device (HID). */ + BLE_APPEARANCE_HID_KEYBOARD = 961, /**< Keyboard (HID subtype). */ + BLE_APPEARANCE_HID_MOUSE = 962, /**< Mouse (HID subtype). */ + BLE_APPEARANCE_HID_JOYSTICK = 963, /**< Joystick (HID subtype). */ + BLE_APPEARANCE_HID_GAMEPAD = 964, /**< Gamepad (HID subtype). */ + BLE_APPEARANCE_HID_DIGITIZERSUBTYPE = 965, /**< Digitizer Tablet (HID subtype). */ + BLE_APPEARANCE_HID_CARD_READER = 966, /**< Card Reader (HID subtype). */ + BLE_APPEARANCE_HID_DIGITAL_PEN = 967, /**< Digital Pen (HID subtype). */ + BLE_APPEARANCE_HID_BARCODE = 968, /**< Barcode Scanner (HID subtype). */ + BLE_APPEARANCE_GENERIC_GLUCOSE_METER = 1024, /**< Generic Glucose Meter. */ + BLE_APPEARANCE_GENERIC_RUNNING_WALKING_SENSOR = 1088, /**< Generic Running Walking Sensor. */ + BLE_APPEARANCE_RUNNING_WALKING_SENSOR_IN_SHOE = 1089, /**< Running Walking Sensor: In-Shoe. */ + BLE_APPEARANCE_RUNNING_WALKING_SENSOR_ON_SHOE = 1090, /**< Running Walking Sensor: On-Shoe. */ + BLE_APPEARANCE_RUNNING_WALKING_SENSOR_ON_HIP = 1091, /**< Running Walking Sensor: On-Hip. */ + BLE_APPEARANCE_GENERIC_CYCLING = 1152, /**< Generic Cycling. */ + BLE_APPEARANCE_CYCLING_CYCLING_COMPUTER = 1153, /**< Cycling: Cycling Computer. */ + BLE_APPEARANCE_CYCLING_SPEED_SENSOR = 1154, /**< Cycling: Speed Sensor. */ + BLE_APPEARANCE_CYCLING_CADENCE_SENSOR = 1155, /**< Cycling: Cadence Sensor. */ + BLE_APPEARANCE_CYCLING_POWER_SENSOR = 1156, /**< Cycling: Power Sensor. */ + BLE_APPEARANCE_CYCLING_SPEED_CADENCE_SENSOR = 1157, /**< Cycling: Speed and Cadence Sensor. */ + BLE_APPEARANCE_GENERIC_PULSE_OXIMETER = 3136, /**< Generic Pulse Oximeter. */ + BLE_APPEARANCE_PULSE_OXIMETER_FINGERTIP = 3137, /**< Fingertip (Pulse Oximeter subtype). */ + BLE_APPEARANCE_PULSE_OXIMETER_WRIST_WORN = 3138, /**< Wrist Worn (Pulse Oximeter subtype). */ + BLE_APPEARANCE_GENERIC_WEIGHT_SCALE = 3200, /**< Generic Weight Scale. */ + BLE_APPEARANCE_GENERIC_OUTDOOR_SPORTS_ACT = 5184, /**< Generic Outdoor Sports Activity. */ + BLE_APPEARANCE_OUTDOOR_SPORTS_ACT_LOC_DISP = 5185, /**< Location Display Device (Outdoor Sports Activity subtype). */ + BLE_APPEARANCE_OUTDOOR_SPORTS_ACT_LOC_AND_NAV_DISP = 5186, /**< Location and Navigation Display Device (Outdoor Sports Activity subtype). */ + BLE_APPEARANCE_OUTDOOR_SPORTS_ACT_LOC_POD = 5187, /**< Location Pod (Outdoor Sports Activity subtype). */ + BLE_APPEARANCE_OUTDOOR_SPORTS_ACT_LOC_AND_NAV_POD = 5188, /**< Location and Navigation Pod (Outdoor Sports Activity subtype). */ +}; + + /*! @brief Error codes for the BLE API. */ enum ble_error_t { BLE_ERROR_NONE = 0, /**< No error. */ @@ -63,7 +119,6 @@ BLE_ERROR_INITIALIZATION_INCOMPLETE = 9, BLE_ERROR_ALREADY_INITIALIZED = 10, BLE_ERROR_UNSPECIFIED = 11, /**< Unknown error. */ - BLE_ERROR_INTERNAL_STACK_FAILURE = 12, /**< The platform-specific stack failed */ }; /** @brief Default MTU size. */
--- a/ble/deprecate.h Tue Jan 12 19:47:52 2016 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,26 +0,0 @@ -/* mbed Microcontroller Library - * Copyright (c) 2006-2013 ARM Limited - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef __DEPRECATE_H__ -#define __DEPRECATE_H__ - -#ifdef YOTTA_CFG_MBED_OS - #include "compiler-polyfill/attributes.h" -#else - #define __deprecated_message(msg) -#endif - -#endif \ No newline at end of file
--- a/ble/services/EnvironmentalService.h Tue Jan 12 19:47:52 2016 +0000 +++ b/ble/services/EnvironmentalService.h Wed Apr 06 18:40:26 2016 +0100 @@ -21,10 +21,10 @@ /** * @class EnvironmentalService -* @brief BLE Environmental Service. This service provides temperature, humidity and pressure measurement. -* Service: https://developer.bluetooth.org/gatt/services/Pages/ServiceViewer.aspx?u=org.bluetooth.service.environmental_sensing.xml -* Temperature: https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.temperature.xml -* Humidity: https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.humidity.xml +* @brief BLE Environmental Service. This service provides the location of the thermometer and the temperature. <br> +* Service: https://developer.bluetooth.org/gatt/services/Pages/ServiceViewer.aspx?u=org.bluetooth.service.environmental_sensing.xml <br> +* Temperature: https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.temperature.xml <br> +* Humidity: https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.humidity.xml <br> * Pressure: https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.pressure.xml */ class EnvironmentalService {
--- a/ble/services/HealthThermometerService.h Tue Jan 12 19:47:52 2016 +0000 +++ b/ble/services/HealthThermometerService.h Wed Apr 06 18:40:26 2016 +0100 @@ -21,34 +21,34 @@ /** * @class HealthThermometerService -* @brief BLE Health Thermometer Service. This service provides the location of the thermometer and the temperature. -* Service: https://developer.bluetooth.org/gatt/profiles/Pages/ProfileViewer.aspx?u=org.bluetooth.profile.health_thermometer.xml -* Temperature Measurement: https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.temperature_measurement.xml +* @brief BLE Health Thermometer Service. This service provides the location of the thermometer and the temperature. <br> +* Service: https://developer.bluetooth.org/gatt/profiles/Pages/ProfileViewer.aspx?u=org.bluetooth.profile.health_thermometer.xml <br> +* Temperature Measurement: https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.temperature_measurement.xml <br> * Temperature Type: https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.temperature_type.xml */ class HealthThermometerService { public: /** - * @enum Sensor Location. - * @brief Location of sensor on the body. + * @enum Sensor Location + * @brief Location of sensor on the body */ enum SensorLocation_t { - LOCATION_ARMPIT = 1, /*!< Armpit. */ - LOCATION_BODY, /*!< Body. */ - LOCATION_EAR, /*!< Ear. */ - LOCATION_FINGER, /*!< Finger. */ + LOCATION_ARMPIT = 1, /*!< armpit */ + LOCATION_BODY, /*!< body */ + LOCATION_EAR, /*!< ear */ + LOCATION_FINGER, /*!< finger */ LOCATION_GI_TRACT, /*!< GI tract */ - LOCATION_MOUTH, /*!< Mouth. */ - LOCATION_RECTUM, /*!< Rectum. */ - LOCATION_TOE, /*!< Toe. */ - LOCATION_EAR_DRUM, /*!< Eardrum. */ + LOCATION_MOUTH, /*!< mouth */ + LOCATION_RECTUM, /*!< rectum */ + LOCATION_TOE, /*!< toe */ + LOCATION_EAR_DRUM, /*!< ear drum */ }; public: /** - * @brief Add the Health Thermometer Service to an existing BLE object, initialize with temperature and location. - * @param[ref] _ble Reference to the BLE device. - * @param[in] initialTemp Initial value in celsius. + * @brief Add the Health Thermometer Service to an existing ble object, initialize with temperature and location. + * @param[ref] _ble reference to the BLE device + * @param[in] initialTemp initial value in celsius * @param[in] _location */ HealthThermometerService(BLE &_ble, float initialTemp, uint8_t _location) : @@ -64,10 +64,10 @@ } /** - * @brief Update the temperature being broadcast. + * @brief Update the temperature being broadcast * * @param[in] temperature - * Floating point value of the temperature. + * Floating point value of the temperature * */ void updateTemperature(float temperature) { @@ -80,14 +80,14 @@ /** * @brief Update the location. * @param loc - * New location value. + * new location value. */ void updateLocation(SensorLocation_t loc) { ble.gattServer().write(tempLocation.getValueHandle(), reinterpret_cast<uint8_t *>(&loc), sizeof(uint8_t)); } private: - /* Private internal representation for the bytes used to work with the vaulue of the temperature characteristic. */ + /* Private internal representation for the bytes used to work with the vaulue of the heart-rate characteristic. */ struct TemperatureValueBytes { static const unsigned OFFSET_OF_FLAGS = 0; static const unsigned OFFSET_OF_VALUE = OFFSET_OF_FLAGS + sizeof(uint8_t); @@ -101,7 +101,7 @@ static const uint8_t TEMPERATURE_UNITS_FAHRENHEIT = 1; TemperatureValueBytes(float initialTemperature) : bytes() { - /* Assumption: temperature values are expressed in celsius */ + /* assumption: temperature values are expressed in Celsius */ bytes[OFFSET_OF_FLAGS] = (TEMPERATURE_UNITS_CELSIUS << TEMPERATURE_UNITS_FLAG_POS) | (false << TIMESTAMP_FLAG_POS) | (false << TEMPERATURE_TYPE_FLAG_POS); @@ -128,15 +128,15 @@ * @return The temperature in 11073-20601 FLOAT-Type format. */ uint32_t quick_ieee11073_from_float(float temperature) { - uint8_t exponent = 0xFE; //Exponent is -2 + uint8_t exponent = 0xFE; //exponent is -2 uint32_t mantissa = (uint32_t)(temperature * 100); return (((uint32_t)exponent) << 24) | mantissa; } private: - /* First byte: 8-bit flags. Second field is a float holding the temperature value. */ - /* See https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.temperature_measurement.xml */ + /* First byte = 8-bit flags, Second field is a float holding the temperature value. */ + /* See --> https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.temperature_measurement.xml */ uint8_t bytes[SIZEOF_VALUE_BYTES]; };
--- a/ble/services/HeartRateService.h Tue Jan 12 19:47:52 2016 +0000 +++ b/ble/services/HeartRateService.h Wed Apr 06 18:40:26 2016 +0100 @@ -21,35 +21,35 @@ /** * @class HeartRateService -* @brief BLE Service for HeartRate. This BLE Service contains the location of the sensor and the heart rate in beats per minute. -* Service: https://developer.bluetooth.org/gatt/services/Pages/ServiceViewer.aspx?u=org.bluetooth.service.heart_rate.xml -* HRM Char: https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.heart_rate_measurement.xml +* @brief BLE Service for HeartRate. This BLE Service contains the location of the sensor, the heartrate in beats per minute. <br> +* Service: https://developer.bluetooth.org/gatt/services/Pages/ServiceViewer.aspx?u=org.bluetooth.service.heart_rate.xml <br> +* HRM Char: https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.heart_rate_measurement.xml <br> * Location: https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.body_sensor_location.xml */ class HeartRateService { public: /** * @enum SensorLocation - * @brief Location of the heart rate sensor on body. + * @brief Location of HeartRate sensor on body. */ enum { - LOCATION_OTHER = 0, /*!< Other location. */ - LOCATION_CHEST, /*!< Chest. */ - LOCATION_WRIST, /*!< Wrist. */ - LOCATION_FINGER, /*!< Finger. */ - LOCATION_HAND, /*!< Hand. */ - LOCATION_EAR_LOBE, /*!< Earlobe. */ - LOCATION_FOOT, /*!< Foot. */ + LOCATION_OTHER = 0, /*!< Other Location */ + LOCATION_CHEST, /*!< Chest */ + LOCATION_WRIST, /*!< Wrist */ + LOCATION_FINGER, /*!< Finger */ + LOCATION_HAND, /*!< Hand */ + LOCATION_EAR_LOBE, /*!< Earlobe */ + LOCATION_FOOT, /*!< Foot */ }; public: /** - * @brief Constructor with 8-bit HRM Counter value. + * @brief Constructor with 8bit HRM Counter value. * * @param[ref] _ble * Reference to the underlying BLE. * @param[in] hrmCounter (8-bit) - * Initial value for the HRM counter. + * initial value for the hrm counter. * @param[in] location * Sensor's location. */ @@ -70,7 +70,7 @@ * @param[in] _ble * Reference to the underlying BLE. * @param[in] hrmCounter (8-bit) - * Initial value for the HRM counter. + * initial value for the hrm counter. * @param[in] location * Sensor's location. */ @@ -86,10 +86,10 @@ } /** - * @brief Set a new 8-bit value for the heart rate. + * @brief Set a new 8-bit value for heart rate. * * @param[in] hrmCounter - * Heart rate in BPM. + * HeartRate in bpm. */ void updateHeartRate(uint8_t hrmCounter) { valueBytes.updateHeartRate(hrmCounter); @@ -97,10 +97,10 @@ } /** - * Set a new 16-bit value for the heart rate. + * Set a new 16-bit value for heart rate. * * @param[in] hrmCounter - * Heart rate in BPM. + * HeartRate in bpm. */ void updateHeartRate(uint16_t hrmCounter) { valueBytes.updateHeartRate(hrmCounter); @@ -108,8 +108,8 @@ } /** - * This callback allows the heart rate service to receive updates to the - * controlPoint characteristic. + * This callback allows the HeartRateService to receive updates to the + * controlPoint Characteristic. * * @param[in] params * Information about the characterisitc being updated. @@ -118,7 +118,7 @@ if (params->handle == controlPoint.getValueAttribute().getHandle()) { /* Do something here if the new value is 1; else you can override this method by * extending this class. - * @NOTE: If you are extending this class, be sure to also call + * @NOTE: if you are extending this class, be sure to also call * ble.onDataWritten(this, &ExtendedHRService::onDataWritten); in * your constructor. */ @@ -135,9 +135,9 @@ } protected: - /* Private internal representation for the bytes used to work with the value of the heart rate characteristic. */ + /* Private internal representation for the bytes used to work with the vaulue of the heart-rate characteristic. */ struct HeartRateValueBytes { - static const unsigned MAX_VALUE_BYTES = 3; /* Flags, and up to two bytes for heart rate. */ + static const unsigned MAX_VALUE_BYTES = 3; /* FLAGS + up to two bytes for heart-rate */ static const unsigned FLAGS_BYTE_INDEX = 0; static const unsigned VALUE_FORMAT_BITNUM = 0; @@ -175,8 +175,8 @@ } private: - /* First byte: 8-bit values, no extra info. Second byte: uint8_t HRM value */ - /* See https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.heart_rate_measurement.xml */ + /* First byte = 8-bit values, no extra info, Second byte = uint8_t HRM value */ + /* See --> https://developer.bluetooth.org/gatt/characteristics/Pages/CharacteristicViewer.aspx?u=org.bluetooth.characteristic.heart_rate_measurement.xml */ uint8_t valueBytes[MAX_VALUE_BYTES]; };
--- a/module.json Tue Jan 12 19:47:52 2016 +0000 +++ b/module.json Wed Apr 06 18:40:26 2016 +0100 @@ -1,42 +1,41 @@ -{ - "name": "ble", - "version": "2.5.0", - "description": "The BLE module offers a high level abstraction for using Bluetooth Low Energy on multiple platforms.", - "keywords": [ - "Bluetooth", - "BLE", - "mbed", - "mbed-official" - ], - "author": "Rohit Grover", - "repository": { - "url": "https://github.com/ARMmbed/ble.git", - "type": "git" - }, - "homepage": "https://developer.mbed.org/teams/Bluetooth-Low-Energy/", - "licenses": [ - { - "url": "https://spdx.org/licenses/Apache-2.0", - "type": "Apache-2.0" - } - ], - "dependencies": {}, - "targetDependencies": { - "st-ble-shield": { - "x-nucleo-idb0xa1": "^2.0.0" - }, - "nrf51822": { - "ble-nrf51822": "^2.2.8" - }, - "cordio": { - "ble-wicentric": "~0.0.4" - }, - "mbed-classic": { - "mbed-classic": "~0.0.1" - }, - "mbed-os": { - "mbed-drivers": "*", - "compiler-polyfill": "^1.2.1" - } - } +{ + "name": "ble", + "version": "2.1.5", + "description": "The BLE module offers a high level abstraction for using Bluetooth Low Energy on multiple platforms.", + "keywords": [ + "Bluetooth", + "BLE", + "mbed", + "mbed-official" + ], + "author": "Rohit Grover", + "repository": { + "url": "https://github.com/ARMmbed/ble.git", + "type": "git" + }, + "homepage": "https://developer.mbed.org/teams/Bluetooth-Low-Energy/", + "licenses": [ + { + "url": "https://spdx.org/licenses/Apache-2.0", + "type": "Apache-2.0" + } + ], + "dependencies": {}, + "targetDependencies": { + "st-ble-shield": { + "x-nucleo-idb0xa1": "ARMmbed/ble-x-nucleo-idb0xa1" + }, + "nrf51822": { + "ble-nrf51822": "^2.1.1" + }, + "cordio": { + "ble-wicentric": "~0.0.4" + }, + "mbed-classic": { + "mbed-classic": "~0.0.1" + }, + "mbed-os": { + "mbed-drivers": "*" + } + } } \ No newline at end of file
--- a/source/BLE.cpp Tue Jan 12 19:47:52 2016 +0000 +++ b/source/BLE.cpp Wed Apr 06 18:40:26 2016 +0100 @@ -131,6 +131,7 @@ ble_error_t BLE::shutdown(void) { + clearAdvertisingPayload(); if (!transport) { error("bad handle to underlying transport"); }
--- a/source/DiscoveredCharacteristic.cpp Tue Jan 12 19:47:52 2016 +0000 +++ b/source/DiscoveredCharacteristic.cpp Wed Apr 06 18:40:26 2016 +0100 @@ -31,29 +31,29 @@ return gattc->read(connHandle, valueHandle, offset); } -struct OneShotReadCallback { - static void launch(GattClient* client, Gap::Handle_t connHandle, - GattAttribute::Handle_t handle, const GattClient::ReadCallback_t& cb) { +struct OneShotReadCallback { + static void launch(GattClient* client, Gap::Handle_t connHandle, + GattAttribute::Handle_t handle, const GattClient::ReadCallback_t& cb) { OneShotReadCallback* oneShot = new OneShotReadCallback(client, connHandle, handle, cb); oneShot->attach(); // delete will be made when this callback is called } private: - OneShotReadCallback(GattClient* client, Gap::Handle_t connHandle, - GattAttribute::Handle_t handle, const GattClient::ReadCallback_t& cb) : + OneShotReadCallback(GattClient* client, Gap::Handle_t connHandle, + GattAttribute::Handle_t handle, const GattClient::ReadCallback_t& cb) : _client(client), _connHandle(connHandle), - _handle(handle), - _callback(cb) { } + _handle(handle), + _callback(cb) { } - void attach() { + void attach() { _client->onDataRead(makeFunctionPointer(this, &OneShotReadCallback::call)); } void call(const GattReadCallbackParams* params) { // verifiy that it is the right characteristic on the right connection - if (params->connHandle == _connHandle && params->handle == _handle) { + if (params->connHandle == _connHandle && params->handle == _handle) { _callback(params); _client->onDataRead().detach(makeFunctionPointer(this, &OneShotReadCallback::call)); delete this; @@ -68,7 +68,7 @@ ble_error_t DiscoveredCharacteristic::read(uint16_t offset, const GattClient::ReadCallback_t& onRead) const { ble_error_t error = read(offset); - if (error) { + if (error) { return error; } @@ -105,29 +105,29 @@ return gattc->write(GattClient::GATT_OP_WRITE_CMD, connHandle, valueHandle, length, value); } -struct OneShotWriteCallback { - static void launch(GattClient* client, Gap::Handle_t connHandle, - GattAttribute::Handle_t handle, const GattClient::WriteCallback_t& cb) { +struct OneShotWriteCallback { + static void launch(GattClient* client, Gap::Handle_t connHandle, + GattAttribute::Handle_t handle, const GattClient::WriteCallback_t& cb) { OneShotWriteCallback* oneShot = new OneShotWriteCallback(client, connHandle, handle, cb); oneShot->attach(); // delete will be made when this callback is called } private: - OneShotWriteCallback(GattClient* client, Gap::Handle_t connHandle, - GattAttribute::Handle_t handle, const GattClient::WriteCallback_t& cb) : + OneShotWriteCallback(GattClient* client, Gap::Handle_t connHandle, + GattAttribute::Handle_t handle, const GattClient::WriteCallback_t& cb) : _client(client), _connHandle(connHandle), - _handle(handle), - _callback(cb) { } + _handle(handle), + _callback(cb) { } - void attach() { + void attach() { _client->onDataWritten(makeFunctionPointer(this, &OneShotWriteCallback::call)); } void call(const GattWriteCallbackParams* params) { // verifiy that it is the right characteristic on the right connection - if (params->connHandle == _connHandle && params->handle == _handle) { + if (params->connHandle == _connHandle && params->handle == _handle) { _callback(params); _client->onDataWritten().detach(makeFunctionPointer(this, &OneShotWriteCallback::call)); delete this; @@ -142,7 +142,7 @@ ble_error_t DiscoveredCharacteristic::write(uint16_t length, const uint8_t *value, const GattClient::WriteCallback_t& onRead) const { ble_error_t error = write(length, value); - if (error) { + if (error) { return error; } @@ -151,17 +151,8 @@ return error; } -ble_error_t DiscoveredCharacteristic::discoverDescriptors( - const CharacteristicDescriptorDiscovery::DiscoveryCallback_t& onCharacteristicDiscovered, - const CharacteristicDescriptorDiscovery::TerminationCallback_t& onTermination) const { - - if(!gattc) { - return BLE_ERROR_INVALID_STATE; - } - - ble_error_t err = gattc->discoverCharacteristicDescriptors( - *this, onCharacteristicDiscovered, onTermination - ); - - return err; +ble_error_t +DiscoveredCharacteristic::discoverDescriptors(DescriptorCallback_t callback, const UUID &matchingUUID) const +{ + return BLE_ERROR_NOT_IMPLEMENTED; /* TODO: this needs to be filled in. */ } \ No newline at end of file