Synchronized with git revision fdcc1e387426ce216bc17175b73bcd5f4aececff

master
bogdanm 2014-04-01 11:04:56 +01:00
parent 496a607f88
commit f1655e0b62
18 changed files with 357 additions and 765 deletions

View File

@ -34,6 +34,7 @@ GapAdvertisingData::GapAdvertisingData(void)
{
memset(_payload, 0, GAP_ADVERTISING_DATA_MAX_PAYLOAD);
_payloadLen = 0;
_appearance = GENERIC_TAG;
}
/**************************************************************************/
@ -119,6 +120,7 @@ ble_error_t GapAdvertisingData::addData(DataType advDataType, uint8_t * payload,
/**************************************************************************/
ble_error_t GapAdvertisingData::addAppearance(Appearance appearance)
{
_appearance = appearance;
return addData(GapAdvertisingData::APPEARANCE, (uint8_t*)&appearance, 2);
}
@ -210,7 +212,7 @@ void GapAdvertisingData::clear(void)
/**************************************************************************/
uint8_t * GapAdvertisingData::getPayload(void)
{
return _payload;
return (_payloadLen > 0) ? _payload : NULL;
}
/**************************************************************************/
@ -224,3 +226,15 @@ uint8_t GapAdvertisingData::getPayloadLen(void)
{
return _payloadLen;
}
/**************************************************************************/
/*!
\brief Returns the 16-bit appearance value for this device
\returns The 16-bit appearance value
*/
/**************************************************************************/
uint16_t GapAdvertisingData::getAppearance(void)
{
return (uint16_t)_appearance;
}

View File

@ -195,16 +195,18 @@ class GapAdvertisingData
virtual ~GapAdvertisingData(void);
ble_error_t addData(DataType, uint8_t *, uint8_t);
ble_error_t addAppearance(Appearance appearance = UNKNOWN);
ble_error_t addAppearance(Appearance appearance = GENERIC_TAG);
ble_error_t addFlags(Flags flag = LE_GENERAL_DISCOVERABLE);
ble_error_t addTxPower(int8_t txPower);
void clear(void);
uint8_t * getPayload(void);
uint8_t getPayloadLen(void);
uint16_t getAppearance(void);
private:
uint8_t _payload[GAP_ADVERTISING_DATA_MAX_PAYLOAD];
uint8_t _payloadLen;
uint8_t _payload[GAP_ADVERTISING_DATA_MAX_PAYLOAD];
uint8_t _payloadLen;
uint16_t _appearance;
};
#endif

View File

@ -52,7 +52,7 @@ GattCharacteristic::GattCharacteristic(uint16_t id, uint16_t minLen, uint16_t ma
memcpy(&properties, &props, 1);
lenMin = minLen;
lenMax = maxLen;
handle = 0;
// handle = 0;
}
/**************************************************************************/

View File

@ -21,6 +21,7 @@
#include "blecommon.h"
#include "UUID.h"
#include "ble_gatts.h"
/* ToDo: Update to use 16-bit or 128-bit UUIDs! */
/**************************************************************************/
@ -31,6 +32,78 @@
class GattCharacteristic
{
public:
enum
{
UUID_BATTERY_LEVEL_STATE_CHAR = 0x2A1B,
UUID_BATTERY_POWER_STATE_CHAR = 0x2A1A,
UUID_REMOVABLE_CHAR = 0x2A3A,
UUID_SERVICE_REQUIRED_CHAR = 0x2A3B,
UUID_ALERT_CATEGORY_ID_CHAR = 0x2A43,
UUID_ALERT_CATEGORY_ID_BIT_MASK_CHAR = 0x2A42,
UUID_ALERT_LEVEL_CHAR = 0x2A06,
UUID_ALERT_NOTIFICATION_CONTROL_POINT_CHAR = 0x2A44,
UUID_ALERT_STATUS_CHAR = 0x2A3F,
UUID_BATTERY_LEVEL_CHAR = 0x2A19,
UUID_BLOOD_PRESSURE_FEATURE_CHAR = 0x2A49,
UUID_BLOOD_PRESSURE_MEASUREMENT_CHAR = 0x2A35,
UUID_BODY_SENSOR_LOCATION_CHAR = 0x2A38,
UUID_BOOT_KEYBOARD_INPUT_REPORT_CHAR = 0x2A22,
UUID_BOOT_KEYBOARD_OUTPUT_REPORT_CHAR = 0x2A32,
UUID_BOOT_MOUSE_INPUT_REPORT_CHAR = 0x2A33,
UUID_CURRENT_TIME_CHAR = 0x2A2B,
UUID_DATE_TIME_CHAR = 0x2A08,
UUID_DAY_DATE_TIME_CHAR = 0x2A0A,
UUID_DAY_OF_WEEK_CHAR = 0x2A09,
UUID_DST_OFFSET_CHAR = 0x2A0D,
UUID_EXACT_TIME_256_CHAR = 0x2A0C,
UUID_FIRMWARE_REVISION_STRING_CHAR = 0x2A26,
UUID_GLUCOSE_FEATURE_CHAR = 0x2A51,
UUID_GLUCOSE_MEASUREMENT_CHAR = 0x2A18,
UUID_GLUCOSE_MEASUREMENT_CONTEXT_CHAR = 0x2A34,
UUID_HARDWARE_REVISION_STRING_CHAR = 0x2A27,
UUID_HEART_RATE_CONTROL_POINT_CHAR = 0x2A39,
UUID_HEART_RATE_MEASUREMENT_CHAR = 0x2A37,
UUID_HID_CONTROL_POINT_CHAR = 0x2A4C,
UUID_HID_INFORMATION_CHAR = 0x2A4A,
UUID_IEEE_REGULATORY_CERTIFICATION_DATA_LIST_CHAR = 0x2A2A,
UUID_INTERMEDIATE_CUFF_PRESSURE_CHAR = 0x2A36,
UUID_INTERMEDIATE_TEMPERATURE_CHAR = 0x2A1E,
UUID_LOCAL_TIME_INFORMATION_CHAR = 0x2A0F,
UUID_MANUFACTURER_NAME_STRING_CHAR = 0x2A29,
UUID_MEASUREMENT_INTERVAL_CHAR = 0x2A21,
UUID_MODEL_NUMBER_STRING_CHAR = 0x2A24,
UUID_UNREAD_ALERT_CHAR = 0x2A45,
UUID_NEW_ALERT_CHAR = 0x2A46,
UUID_PNP_ID_CHAR = 0x2A50,
UUID_PROTOCOL_MODE_CHAR = 0x2A4E,
UUID_RECORD_ACCESS_CONTROL_POINT_CHAR = 0x2A52,
UUID_REFERENCE_TIME_INFORMATION_CHAR = 0x2A14,
UUID_REPORT_CHAR = 0x2A4D,
UUID_REPORT_MAP_CHAR = 0x2A4B,
UUID_RINGER_CONTROL_POINT_CHAR = 0x2A40,
UUID_RINGER_SETTING_CHAR = 0x2A41,
UUID_SCAN_INTERVAL_WINDOW_CHAR = 0x2A4F,
UUID_SCAN_REFRESH_CHAR = 0x2A31,
UUID_SERIAL_NUMBER_STRING_CHAR = 0x2A25,
UUID_SOFTWARE_REVISION_STRING_CHAR = 0x2A28,
UUID_SUPPORTED_NEW_ALERT_CATEGORY_CHAR = 0x2A47,
UUID_SUPPORTED_UNREAD_ALERT_CATEGORY_CHAR = 0x2A48,
UUID_SYSTEM_ID_CHAR = 0x2A23,
UUID_TEMPERATURE_MEASUREMENT_CHAR = 0x2A1C,
UUID_TEMPERATURE_TYPE_CHAR = 0x2A1D,
UUID_TIME_ACCURACY_CHAR = 0x2A12,
UUID_TIME_SOURCE_CHAR = 0x2A13,
UUID_TIME_UPDATE_CONTROL_POINT_CHAR = 0x2A16,
UUID_TIME_UPDATE_STATE_CHAR = 0x2A17,
UUID_TIME_WITH_DST_CHAR = 0x2A11,
UUID_TIME_ZONE_CHAR = 0x2A0E,
UUID_TX_POWER_LEVEL_CHAR = 0x2A07,
UUID_CSC_FEATURE_CHAR = 0x2A5C,
UUID_CSC_MEASUREMENT_CHAR = 0x2A5B,
UUID_RSC_FEATURE_CHAR = 0x2A54,
UUID_RSC_MEASUREMENT_CHAR = 0x2A53,
};
/**************************************************************************/
/*!
\brief Standard GATT characteristic presentation format unit types.
@ -236,7 +309,7 @@ class GattCharacteristic
uint16_t uuid; /* Characteristic UUID */
uint16_t lenMin; /* Minimum length of the value */
uint16_t lenMax; /* Maximum length of the value */
uint8_t handle;
uint16_t handle;
uint8_t properties;
private:

View File

@ -104,7 +104,7 @@ ble_error_t GattService::addCharacteristic(GattCharacteristic & characteristic)
/* ToDo: Make sure this characteristic UUID doesn't already exist */
/* ToDo: Basic validation */
characteristics[characteristicCount] = characteristic;
characteristics[characteristicCount] = &characteristic;
characteristicCount++;
return BLE_ERROR_NONE;

View File

@ -40,10 +40,31 @@ class GattService
UUID primaryServiceID;
uint8_t characteristicCount;
GattCharacteristic characteristics[BLE_SERVICE_MAX_CHARACTERISTICS];
uint8_t handle;
GattCharacteristic* characteristics[BLE_SERVICE_MAX_CHARACTERISTICS];
uint16_t handle;
ble_error_t addCharacteristic(GattCharacteristic &);
enum {
UUID_ALERT_NOTIFICATION_SERVICE = 0x1811,
UUID_BATTERY_SERVICE = 0x180F,
UUID_BLOOD_PRESSURE_SERVICE = 0x1810,
UUID_CURRENT_TIME_SERVICE = 0x1805,
UUID_CYCLING_SPEED_AND_CADENCE = 0x1816,
UUID_DEVICE_INFORMATION_SERVICE = 0x180A,
UUID_GLUCOSE_SERVICE = 0x1808,
UUID_HEALTH_THERMOMETER_SERVICE = 0x1809,
UUID_HEART_RATE_SERVICE = 0x180D,
UUID_HUMAN_INTERFACE_DEVICE_SERVICE = 0x1812,
UUID_IMMEDIATE_ALERT_SERVICE = 0x1802,
UUID_LINK_LOSS_SERVICE = 0x1803,
UUID_NEXT_DST_CHANGE_SERVICE = 0x1807,
UUID_PHONE_ALERT_STATUS_SERVICE = 0x180E,
UUID_REFERENCE_TIME_UPDATE_SERVICE = 0x1806,
UUID_RUNNING_SPEED_AND_CADENCE = 0x1814,
UUID_SCAN_PARAMETERS_SERVICE = 0x1813,
UUID_TX_POWER_SERVICE = 0x1804
};
};
#endif

View File

@ -17,6 +17,11 @@
#ifndef __BLE_COMMON_H__
#define __BLE_COMMON_H__
#define NRF51
#define DEBUG_NRF_USER
#define BLE_STACK_SUPPORT_REQD
#define BOARD_PCA10001
#ifdef __cplusplus
extern "C" {
#endif

View File

@ -34,6 +34,7 @@ class BLEDevice
public:
virtual Gap& getGap() = 0;
virtual GattServer& getGattServer() = 0;
virtual ble_error_t init() = 0;
virtual ble_error_t reset(void) = 0;
};

View File

@ -21,6 +21,7 @@
#include "blecommon.h"
#include "GapAdvertisingData.h"
#include "GapAdvertisingParams.h"
#include "GapEvents.h"
/**************************************************************************/
/*!
@ -31,40 +32,45 @@
/**************************************************************************/
class Gap
{
protected:
FunctionPointer m_callback_event;
private:
GapEvents *m_pEventHandler;
public:
/******************************************************************/
/*!
\brief
Identifies GAP events generated by the radio HW when an event
callback occurs
*/
/******************************************************************/
typedef enum gap_event_e
{
GAP_EVENT_ADVERTISING_STARTED = 1,
GAP_EVENT_CONNECTED = 2,
GAP_EVENT_DISCONNECTED = 3
} gapEvent_t;
/* These functions must be defined in the sub-class */
virtual ble_error_t setAdvertisingData(GapAdvertisingData &, GapAdvertisingData &) = 0;
virtual ble_error_t startAdvertising(GapAdvertisingParams &) = 0;
virtual ble_error_t stopAdvertising(void) = 0;
virtual ble_error_t disconnect(void) = 0;
/* These functions must be defined in the sub-class */
virtual ble_error_t setAdvertising(GapAdvertisingParams &, GapAdvertisingData &, GapAdvertisingData &) = 0;
virtual ble_error_t startAdvertising(void) = 0;
virtual ble_error_t stopAdvertising(void) = 0;
/* Describes the current state of the device (more than one bit can be set) */
typedef struct GapState_s
{
unsigned advertising : 1; /**< The device is current advertising */
unsigned connected : 1; /**< The peripheral is connected to a central device */
} GapState_t;
uint16_t state; /* Initialising, Advertising, Scanning, Connected, etc. ... more than one bit can be set at a time! */
/* Event callback */
void attach(void (*function)(void)) {
m_callback_event.attach( function );
}
template<typename T>
void attach(T *object, void (T::*member)(void)) {
m_callback_event.attach( object, member );
}
/* Event callback handlers */
void setEventHandler(GapEvents *pEventHandler) {m_pEventHandler = pEventHandler;}
void handleEvent(GapEvents::gapEvent_e type) {
if (NULL == m_pEventHandler)
return;
switch(type) {
case GapEvents::GAP_EVENT_TIMEOUT:
state.advertising = 0;
m_pEventHandler->onTimeout();
break;
case GapEvents::GAP_EVENT_CONNECTED:
state.connected = 1;
m_pEventHandler->onConnected();
break;
case GapEvents::GAP_EVENT_DISCONNECTED:
state.connected = 0;
m_pEventHandler->onDisconnected();
break;
}
}
GapState_t state;
};
#endif

71
hw/GapEvents.h Normal file
View File

@ -0,0 +1,71 @@
/* 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 __GAP_EVENTS_H__
#define __GAP_EVENTS_H__
#include "blecommon.h"
#include "mbed.h"
/**************************************************************************/
/*!
\brief
The base class used to abstract away the callback events that can be
triggered with the GAP.
*/
/**************************************************************************/
class GapEvents {
public:
/******************************************************************/
/*!
\brief
Identifies GAP events generated by the radio HW when an event
callback occurs
*/
/******************************************************************/
typedef enum gapEvent_e
{
GAP_EVENT_TIMEOUT = 1, /**< Advertising timed out before a connection was established */
GAP_EVENT_CONNECTED = 2, /**< A connection was established with a central device */
GAP_EVENT_DISCONNECTED = 3 /**< A connection was closed or lost with a central device */
} gapEvent_t;
/******************************************************************/
/*!
\brief
Advertising timed out before a connection was established
*/
/******************************************************************/
virtual void onTimeout(void) {}
/******************************************************************/
/*!
\brief
A connection was established with a central device
*/
/******************************************************************/
virtual void onConnected(void) {}
/******************************************************************/
/*!
\brief
A connection was closed or lost with a central device
*/
/******************************************************************/
virtual void onDisconnected(void) {}
};
#endif

View File

@ -17,10 +17,10 @@
#ifndef __GATT_SERVER_H__
#define __GATT_SERVER_H__
#include "blecommon.h"
#include "UUID.h"
#include "GattService.h"
#include "mbed.h"
#include "blecommon.h"
#include "GattService.h"
#include "GattServerEvents.h"
/**************************************************************************/
/*!
@ -31,48 +31,46 @@
/**************************************************************************/
class GattServer
{
protected:
FunctionPointer m_callback_event;
private:
GattServerEvents *m_pEventHandler;
public:
/******************************************************************/
/*!
\brief
Identifies GATT events generated by the radio HW when an event
callback occurs
*/
/******************************************************************/
typedef enum gatt_event_e
{
GATT_EVENT_DATA_SENT = 1, /* Fired when a msg was successfully sent out */
GATT_EVENT_DATA_WRITTEN = 2, /* Client wrote data to Server (separate into char and descriptor writes?) */
GATT_EVENT_UPDATES_ENABLED = 3, /* Notify/Indicate Enabled in CCCD */
GATT_EVENT_UPDATES_DISABLED = 4, /* Notify/Indicate Disnabled in CCCD */
GATT_EVENT_CONFIRMATION_RECEIVED = 5 /* Response received from Indicate message */
} gattEvent_t;
/* These functions must be defined in the sub-class */
virtual ble_error_t addService(GattService &) = 0;
virtual ble_error_t readValue(uint8_t, uint8_t[], uint16_t) = 0;
virtual ble_error_t updateValue(uint8_t, uint8_t[], uint16_t) = 0;
virtual ble_error_t readValue(uint16_t, uint8_t[], uint16_t) = 0;
virtual ble_error_t updateValue(uint16_t, uint8_t[], uint16_t, bool localOnly = false) = 0;
// ToDo: For updateValue, check the CCCD to see if the value we are
// updating has the notify or indicate bits sent, and if BOTH are set
// be sure to call sd_ble_gatts_hvx() twice with notify then indicate!
// Strange use case, but valid and must be covered!
/* Event callback handlers */
void setEventHandler(GattServerEvents *pEventHandler) {m_pEventHandler = pEventHandler;}
void handleEvent(GattServerEvents::gattEvent_e type, uint16_t charHandle) {
if (NULL == m_pEventHandler)
return;
switch(type) {
case GattServerEvents::GATT_EVENT_DATA_SENT:
m_pEventHandler->onDataSent(charHandle);
break;
case GattServerEvents::GATT_EVENT_DATA_WRITTEN:
m_pEventHandler->onDataWritten(charHandle);
break;
case GattServerEvents::GATT_EVENT_UPDATES_ENABLED:
m_pEventHandler->onUpdatesEnabled(charHandle);
break;
case GattServerEvents::GATT_EVENT_UPDATES_DISABLED:
m_pEventHandler->onUpdatesDisabled(charHandle);
break;
case GattServerEvents::GATT_EVENT_CONFIRMATION_RECEIVED:
m_pEventHandler->onConfirmationReceived(charHandle);
break;
}
}
uint8_t serviceCount;
uint8_t characteristicCount;
/* Event callback */
void attach(void (*function)(void)) {
m_callback_event.attach( function );
}
template<typename T>
void attach(T *object, void (T::*member)(void)) {
m_callback_event.attach( object, member );
}
};
#endif

91
hw/GattServerEvents.h Normal file
View File

@ -0,0 +1,91 @@
/* 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 __GATT_SERVER_EVENTS_H__
#define __GATT_SERVER_EVENTS_H__
#include "blecommon.h"
#include "mbed.h"
/**************************************************************************/
/*!
\brief
The base class used to abstract away the callback events that can be
triggered with the GATT Server.
*/
/**************************************************************************/
class GattServerEvents {
public:
/******************************************************************/
/*!
\brief
Identifies GATT events generated by the radio HW when an event
callback occurs
*/
/******************************************************************/
typedef enum gattEvent_e
{
GATT_EVENT_DATA_SENT = 1, /**< Fired when a msg was successfully sent out (notify only?) */
GATT_EVENT_DATA_WRITTEN = 2, /**< Client wrote data to Server (separate into char and descriptor writes?) */
GATT_EVENT_UPDATES_ENABLED = 3, /**< Notify/Indicate Enabled in CCCD */
GATT_EVENT_UPDATES_DISABLED = 4, /**< Notify/Indicate Disabled in CCCD */
GATT_EVENT_CONFIRMATION_RECEIVED = 5 /**< Response received from Indicate message */
} gattEvent_t;
/******************************************************************/
/*!
\brief
A message was successfully transmitted
*/
/******************************************************************/
virtual void onDataSent(uint16_t charHandle) {}
/******************************************************************/
/*!
\brief
The GATT client (the phone, tablet, etc.) wrote data to a
characteristic or descriptor on the GATT Server (the peripheral
device).
*/
/******************************************************************/
virtual void onDataWritten(uint16_t charHandle) {}
/******************************************************************/
/*!
\brief
A Notify or Indicate flag was enabled in the CCCD
*/
/******************************************************************/
virtual void onUpdatesEnabled(uint16_t charHandle) {}
/******************************************************************/
/*!
\brief
A Notify or Indicate flag was disabled in the CCCD
*/
/******************************************************************/
virtual void onUpdatesDisabled(uint16_t charHandle) {}
/******************************************************************/
/*!
\brief
A confirmation response was received from an Indicate message
*/
/******************************************************************/
virtual void onConfirmationReceived(uint16_t charHandle) {}
};
#endif

View File

@ -1,91 +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.
*/
#include "mbed.h"
#include "nRF51822s.h"
/**************************************************************************/
/*!
@brief UART callback function
*/
/**************************************************************************/
void nRF51822s::uartCallback(void)
{
/* ToDo: Check responses and set a flag for success/error/etc. */
/* Read serial to clear the RX interrupt */
uart.getc();
}
/**************************************************************************/
/*!
@brief Constructor
*/
/**************************************************************************/
nRF51822s::nRF51822s(PinName tx, PinName rx, PinName rts, PinName cts) : uart(tx, rx), gap(uart), gattServer(uart)
{
/* Setup the nRF UART interface */
uart.baud(9600);
/* Echo data on the debug CDC port */
uart.attach(this, &nRF51822s::uartCallback);
/* Add flow control for UART (required by the nRF51822) */
uart.set_flow_control(RawSerial::RTSCTS, rts, cts);
}
/**************************************************************************/
/*!
@brief Destructor
*/
/**************************************************************************/
nRF51822s::~nRF51822s(void)
{
}
/**************************************************************************/
/*!
@brief Resets the BLE HW, removing any existing services and
characteristics
@returns ble_error_t
@retval BLE_ERROR_NONE
Everything executed properly
@section EXAMPLE
@code
@endcode
*/
/**************************************************************************/
ble_error_t nRF51822s::reset(void)
{
wait(0.5);
/* Command ID = 0x0005, No payload */
uart.printf("10 05 00 00\r\n");
/* Reset the service and characteristic counters */
//serviceCount = 0;
//characteristicCount = 0;
/* Wait for the radio to come back up */
wait(1);
return BLE_ERROR_NONE;
}

View File

@ -1,51 +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 __NRF51822_H__
#define __NRF51822_H__
#include "mbed.h"
#include "blecommon.h"
#include "hw/BLEDevice.h"
#include "hw/nRF51822s/nRF51Gap.h"
#include "hw/nRF51822s/nRF51GattServer.h"
/**************************************************************************/
/*!
\brief
*/
/**************************************************************************/
class nRF51822s : public BLEDevice
{
protected:
RawSerial uart;
nRF51Gap gap;
nRF51GattServer gattServer;
public:
nRF51822s(PinName, PinName, PinName, PinName);
virtual ~nRF51822s(void);
virtual Gap& getGap() { return gap; };
virtual GattServer& getGattServer() { return gattServer; };
virtual ble_error_t reset(void);
private:
void uartCallback(void);
};
#endif

View File

@ -1,255 +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.
*/
#include "nRF51Gap.h"
#include "mbed.h"
/**************************************************************************/
/*!
@brief Constructor
*/
/**************************************************************************/
nRF51Gap::nRF51Gap(RawSerial &serial) : Gap(), uart(serial)
{
/* ToDo: Reset the service and characteristic counters */
/* ToDo: Set state variable to an appropriate value */
}
/**************************************************************************/
/*!
@brief Destructor
*/
/**************************************************************************/
nRF51Gap::~nRF51Gap(void)
{
}
/**************************************************************************/
/*!
@brief Sets the advertising parameters and payload for the device
@param[in] params
Basic advertising details, including the advertising
delay, timeout and how the device should be advertised
@params[in] advData
The primary advertising data payload
@params[in] scanResponse
The optional Scan Response payload if the advertising
type is set to \ref GapAdvertisingParams::ADV_SCANNABLE_UNDIRECTED
in \ref GapAdveritinngParams
@returns \ref ble_error_t
@retval BLE_ERROR_NONE
Everything executed properly
@retval BLE_ERROR_BUFFER_OVERFLOW
The proposed action would cause a buffer overflow. All
advertising payloads must be <= 31 bytes, for example.
@retval BLE_ERROR_NOT_IMPLEMENTED
A feature was requested that is not yet supported in the
nRF51 firmware or hardware.
@retval BLE_ERROR_PARAM_OUT_OF_RANGE
One of the proposed values is outside the valid range.
@section EXAMPLE
@code
@endcode
*/
/**************************************************************************/
ble_error_t nRF51Gap::setAdvertising(GapAdvertisingParams & params, GapAdvertisingData & advData, GapAdvertisingData & scanResponse)
{
uint8_t len = 0;
uint8_t *buffer;
/* Make sure we support the advertising type */
if (params.getAdvertisingType() == GapAdvertisingParams::ADV_CONNECTABLE_DIRECTED)
{
/* ToDo: This requires a propery security implementation, etc. */
return BLE_ERROR_NOT_IMPLEMENTED;
}
/* Check interval range */
if (params.getAdvertisingType() == GapAdvertisingParams::ADV_NON_CONNECTABLE_UNDIRECTED)
{
/* Min delay is slightly longer for unconnectable devices */
if ((params.getInterval() < GAP_ADV_PARAMS_INTERVAL_MIN_NONCON) ||
(params.getInterval() > GAP_ADV_PARAMS_INTERVAL_MAX))
{
return BLE_ERROR_PARAM_OUT_OF_RANGE;
}
}
else
{
if ((params.getInterval() < GAP_ADV_PARAMS_INTERVAL_MIN) ||
(params.getInterval() > GAP_ADV_PARAMS_INTERVAL_MAX))
{
return BLE_ERROR_PARAM_OUT_OF_RANGE;
}
}
/* Check timeout is zero for Connectable Directed */
if ((params.getAdvertisingType() == GapAdvertisingParams::ADV_CONNECTABLE_DIRECTED) &&
(params.getTimeout() != 0))
{
/* Timeout must be 0 with this type, although we'll never get here */
/* since this isn't implemented yet anyway */
return BLE_ERROR_PARAM_OUT_OF_RANGE;
}
/* Check timeout for other advertising types */
if ((params.getAdvertisingType() != GapAdvertisingParams::ADV_CONNECTABLE_DIRECTED) &&
(params.getTimeout() > GAP_ADV_PARAMS_TIMEOUT_MAX))
{
return BLE_ERROR_PARAM_OUT_OF_RANGE;
}
/* Make sure we don't exceed the advertising payload length */
if (advData.getPayloadLen() > GAP_ADVERTISING_DATA_MAX_PAYLOAD)
{
return BLE_ERROR_BUFFER_OVERFLOW;
}
/* Check the scan response payload limits */
if ((params.getAdvertisingType() == GapAdvertisingParams::ADV_SCANNABLE_UNDIRECTED))
{
/* Check if we're within the upper limit */
if (advData.getPayloadLen() > GAP_ADVERTISING_DATA_MAX_PAYLOAD)
{
return BLE_ERROR_BUFFER_OVERFLOW;
}
/* Make sure we have a payload! */
if (advData.getPayloadLen() == 0)
{
return BLE_ERROR_PARAM_OUT_OF_RANGE;
}
}
/* ToDo: Perform some checks on the payload, for example the Scan Response can't */
/* contains a flags AD type, etc. */
/* ToDo: Refactor these actions into separate private functions */
/* 1.) Send advertising params, Command IDs = 0x000C, 0x000D, 0x000E */
/* A.) Command ID = 0x000C, Advertising Interval, uint16_t */
uart.printf("10 0C 00 02 %02X %02X\r\n", (uint8_t)(params.getInterval() & 0xFF),
(uint8_t)(params.getInterval() >> 8));
/* ToDo: Check response */
wait(0.5);
/* B.) Command ID = 0x000D, Advertising Timeout, uint16_t */
uart.printf("10 0D 00 02 %02X %02X\r\n", (uint8_t)(params.getTimeout() & 0xFF),
(uint8_t)(params.getTimeout() >> 8));
/* ToDo: Check response */
wait(0.5);
/* C.) Command ID = 0x000E, Advertising Type, uint8_t */
uart.printf("10 0E 00 01 %02X\r\n", (uint8_t)(params.getAdvertisingType()));
/* ToDo: Check response */
wait(0.5);
/* 2.) Send advertising data, Command ID = 0x000A */
len = advData.getPayloadLen();
buffer = advData.getPayload();
uart.printf("10 0A 00 %02X", len);
for (uint16_t i = 0; i < len; i++)
{
uart.printf(" %02X", buffer[i]);
}
uart.printf("\r\n");
/* ToDo: Check response */
wait(0.1);
/* 3.) Send scan response data, Command ID = 0x000B */
if ((params.getAdvertisingType() == GapAdvertisingParams::ADV_SCANNABLE_UNDIRECTED))
{
len = scanResponse.getPayloadLen();
buffer = scanResponse.getPayload();
uart.printf("10 0B 00 %02X", len);
for (uint16_t i = 0; i < len; i++)
{
uart.printf(" %02X", buffer[i]);
}
uart.printf("\r\n");
/* ToDo: Check response */
wait(0.1);
}
return BLE_ERROR_NONE;
}
/**************************************************************************/
/*!
@brief Starts the BLE HW, initialising any services that were
added before this function was called.
@note All services must be added before calling this function!
@returns ble_error_t
@retval BLE_ERROR_NONE
Everything executed properly
@section EXAMPLE
@code
@endcode
*/
/**************************************************************************/
ble_error_t nRF51Gap::startAdvertising(void)
{
/* Command ID = 0x0003, No payload */
uart.printf("10 03 00 00\r\n");
/* ToDo: Check response */
wait(0.5);
return BLE_ERROR_NONE;
}
/**************************************************************************/
/*!
@brief Stops the BLE HW and disconnects from any devices
@returns ble_error_t
@retval BLE_ERROR_NONE
Everything executed properly
@section EXAMPLE
@code
@endcode
*/
/**************************************************************************/
ble_error_t nRF51Gap::stopAdvertising(void)
{
/* Command ID = 0x0004, No payload */
uart.printf("10 04 00 00\r\n");
/* ToDo: Check response */
wait(0.1);
return BLE_ERROR_NONE;
}

View File

@ -1,47 +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 __NRF51822_GAP_H__
#define __NRF51822_GAP_H__
#include "mbed.h"
#include "blecommon.h"
#include "GapAdvertisingParams.h"
#include "GapAdvertisingData.h"
#include "hw/Gap.h"
/**************************************************************************/
/*!
\brief
*/
/**************************************************************************/
class nRF51Gap : public Gap
{
public:
nRF51Gap(RawSerial &);
virtual ~nRF51Gap(void);
/* Functions that must be implemented from Gap */
virtual ble_error_t setAdvertising(GapAdvertisingParams &, GapAdvertisingData &, GapAdvertisingData &);
virtual ble_error_t startAdvertising(void);
virtual ble_error_t stopAdvertising(void);
private:
RawSerial& uart;
};
#endif

View File

@ -1,197 +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.
*/
#include "nRF51GattServer.h"
#include "mbed.h"
/* ToDo: Convert to Singleton! */
/**************************************************************************/
/*!
@brief Constructor
*/
/**************************************************************************/
nRF51GattServer::nRF51GattServer(RawSerial &serial): GattServer(), uart(serial)
{
/* Reset the service and characteristic counters */
serviceCount = 0;
characteristicCount = 0;
}
/**************************************************************************/
/*!
@brief Destructor
*/
/**************************************************************************/
nRF51GattServer::~nRF51GattServer(void)
{
}
/**************************************************************************/
/*!
@brief Adds a new service to the GATT table on the peripheral
@returns ble_error_t
@retval BLE_ERROR_NONE
Everything executed properly
@section EXAMPLE
@code
@endcode
*/
/**************************************************************************/
ble_error_t nRF51GattServer::addService(GattService & service)
{
/* ToDo: Make sure we don't overflow the array, etc. */
/* ToDo: Make sure this service UUID doesn't already exist (?) */
/* ToDo: Basic validation */
/* Add the service to the nRF51 */
if (service.primaryServiceID.type == UUID::UUID_TYPE_SHORT)
{
/* 16-bit BLE UUID */
uart.printf("10 01 00 04 01 02 %02X %02X\r\n",
service.primaryServiceID.value & 0xFF,
service.primaryServiceID.value >> 8);
}
else
{
/* 128-bit Custom UUID */
uart.printf("10 01 00 12 01 10 %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X\r\n",
service.primaryServiceID.base[0],
service.primaryServiceID.base[1],
service.primaryServiceID.base[2],
service.primaryServiceID.base[3],
service.primaryServiceID.base[4],
service.primaryServiceID.base[5],
service.primaryServiceID.base[6],
service.primaryServiceID.base[7],
service.primaryServiceID.base[8],
service.primaryServiceID.base[9],
service.primaryServiceID.base[10],
service.primaryServiceID.base[11],
service.primaryServiceID.base[12],
service.primaryServiceID.base[13],
service.primaryServiceID.base[14],
service.primaryServiceID.base[15]);
}
/* ToDo: Check response */
wait(0.1);
/* Add characteristics to the service */
for (uint8_t i = 0; i < service.characteristicCount; i++)
{
/* Command ID = 0x0002 */
uart.printf("10 02 00 0F 01 02 %02X %02X 04 02 %02X %02X 05 02 %02X %02X 03 01 %02X\r\n",
service.characteristics[i].uuid & 0xFF,
service.characteristics[i].uuid >> 8,
service.characteristics[i].lenMin & 0xFF,
service.characteristics[i].lenMin >> 8,
service.characteristics[i].lenMax & 0xFF,
service.characteristics[i].lenMax >> 8,
service.characteristics[i].properties);
/* ToDo: Check response */
wait(0.1);
/* Update the characteristic handle */
service.characteristics[i].handle = characteristicCount;
characteristicCount++;
}
/* Update the service handle */
service.handle = serviceCount;
serviceCount++;
return BLE_ERROR_NONE;
}
/**************************************************************************/
/*!
@brief Reads the value of a characteristic, based on the service
and characteristic index fields
@param[in] charHandle
The handle of the GattCharacteristic to read from
@param[in] buffer
Buffer to hold the the characteristic's value
(raw byte array in LSB format)
@param[in] len
The number of bytes read into the buffer
@returns ble_error_t
@retval BLE_ERROR_NONE
Everything executed properly
@section EXAMPLE
@code
@endcode
*/
/**************************************************************************/
ble_error_t nRF51GattServer::readValue(uint8_t charHandle, uint8_t buffer[], uint16_t len)
{
/* ToDo */
return BLE_ERROR_NONE;
}
/**************************************************************************/
/*!
@brief Updates the value of a characteristic, based on the service
and characteristic index fields
@param[in] charHandle
The handle of the GattCharacteristic to write to
@param[in] buffer
Data to use when updating the characteristic's value
(raw byte array in LSB format)
@param[in] len
The number of bytes in buffer
@returns ble_error_t
@retval BLE_ERROR_NONE
Everything executed properly
@section EXAMPLE
@code
@endcode
*/
/**************************************************************************/
ble_error_t nRF51GattServer::updateValue(uint8_t charHandle, uint8_t buffer[], uint16_t len)
{
/* Command ID = 0x0006, Payload = Characteristic ID, Value */
uart.printf("10 06 00 %02X %02X", len + 1, charHandle);
for (uint16_t i = 0; i<len; i++)
{
uart.printf(" %02X", buffer[i]);
}
uart.printf("\r\n");
/* ToDo: Check response */
wait(0.1);
return BLE_ERROR_NONE;
}

View File

@ -1,49 +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 __NRF51822_GATT_SERVER_H__
#define __NRF51822_GATT_SERVER_H__
#include "mbed.h"
#include "blecommon.h"
#include "GattService.h"
#include "hw/GattServer.h"
/**************************************************************************/
/*!
\brief
*/
/**************************************************************************/
class nRF51GattServer : public GattServer
{
public:
nRF51GattServer(RawSerial &);
virtual ~nRF51GattServer(void);
/* Functions that must be implemented from GattServer */
virtual ble_error_t addService(GattService &);
virtual ble_error_t readValue(uint8_t, uint8_t[], uint16_t);
virtual ble_error_t updateValue(uint8_t, uint8_t[], uint16_t);
/* nRF51 Functions */
void uartCallback(void);
private:
RawSerial& uart;
};
#endif