Wallbot_CaaS
Dependencies: MPU6050 mbed PID
Fork of BLE_MPU6050_test6_challenge_sb by
nRF51GattServer.cpp
00001 /* mbed Microcontroller Library 00002 * Copyright (c) 2006-2013 ARM Limited 00003 * 00004 * Licensed under the Apache License, Version 2.0 (the "License"); 00005 * you may not use this file except in compliance with the License. 00006 * You may obtain a copy of the License at 00007 * 00008 * http://www.apache.org/licenses/LICENSE-2.0 00009 * 00010 * Unless required by applicable law or agreed to in writing, software 00011 * distributed under the License is distributed on an "AS IS" BASIS, 00012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00013 * See the License for the specific language governing permissions and 00014 * limitations under the License. 00015 */ 00016 00017 #include "nRF51GattServer.h" 00018 #include "mbed.h" 00019 00020 #include "common/common.h " 00021 #include "btle/custom/custom_helper.h" 00022 00023 #include "nRF51Gap.h" 00024 00025 /**************************************************************************/ 00026 /*! 00027 @brief Adds a new service to the GATT table on the peripheral 00028 00029 @returns ble_error_t 00030 00031 @retval BLE_ERROR_NONE 00032 Everything executed properly 00033 00034 @section EXAMPLE 00035 00036 @code 00037 00038 @endcode 00039 */ 00040 /**************************************************************************/ 00041 ble_error_t nRF51GattServer::addService(GattService &service) 00042 { 00043 /* ToDo: Make sure we don't overflow the array, etc. */ 00044 /* ToDo: Make sure this service UUID doesn't already exist (?) */ 00045 /* ToDo: Basic validation */ 00046 00047 /* Add the service to the nRF51 */ 00048 ble_uuid_t nordicUUID; 00049 nordicUUID = custom_convert_to_nordic_uuid(service.getUUID()); 00050 00051 uint16_t serviceHandle; 00052 ASSERT( ERROR_NONE == 00053 sd_ble_gatts_service_add(BLE_GATTS_SRVC_TYPE_PRIMARY, 00054 &nordicUUID, 00055 &serviceHandle), 00056 BLE_ERROR_PARAM_OUT_OF_RANGE ); 00057 service.setHandle(serviceHandle); 00058 00059 /* Add characteristics to the service */ 00060 for (uint8_t i = 0; i < service.getCharacteristicCount(); i++) { 00061 GattCharacteristic *p_char = service.getCharacteristic(i); 00062 00063 /* Skip any incompletely defined, read-only characteristics. */ 00064 if ((p_char->getValueAttribute().getValuePtr() == NULL) && 00065 (p_char->getValueAttribute().getInitialLength() == 0) && 00066 (p_char->getProperties() == GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_READ)) { 00067 continue; 00068 } 00069 00070 nordicUUID = custom_convert_to_nordic_uuid(p_char->getValueAttribute().getUUID()); 00071 00072 ASSERT ( ERROR_NONE == 00073 custom_add_in_characteristic(BLE_GATT_HANDLE_INVALID, 00074 &nordicUUID, 00075 p_char->getProperties(), 00076 p_char->getValueAttribute().getValuePtr(), 00077 p_char->getValueAttribute().getInitialLength(), 00078 p_char->getValueAttribute().getMaxLength(), 00079 &nrfCharacteristicHandles[characteristicCount]), 00080 BLE_ERROR_PARAM_OUT_OF_RANGE ); 00081 00082 /* Update the characteristic handle */ 00083 uint16_t charHandle = characteristicCount; 00084 p_characteristics[characteristicCount++] = p_char; 00085 00086 p_char->getValueAttribute().setHandle(charHandle); 00087 00088 /* Add optional descriptors if any */ 00089 /* ToDo: Make sure we don't overflow the array */ 00090 for (uint8_t j = 0; j < p_char->getDescriptorCount(); j++) { 00091 GattAttribute *p_desc = p_char->getDescriptor(j); 00092 00093 nordicUUID = custom_convert_to_nordic_uuid(p_desc->getUUID()); 00094 00095 ASSERT ( ERROR_NONE == 00096 custom_add_in_descriptor(BLE_GATT_HANDLE_INVALID, 00097 &nordicUUID, 00098 p_desc->getValuePtr(), 00099 p_desc->getInitialLength(), 00100 p_desc->getMaxLength(), 00101 &nrfDescriptorHandles[descriptorCount]), 00102 BLE_ERROR_PARAM_OUT_OF_RANGE ); 00103 00104 uint16_t descHandle = descriptorCount; 00105 p_descriptors[descriptorCount++] = p_desc; 00106 p_desc->setHandle(descHandle); 00107 } 00108 } 00109 00110 serviceCount++; 00111 00112 return BLE_ERROR_NONE; 00113 } 00114 00115 /**************************************************************************/ 00116 /*! 00117 @brief Reads the value of a characteristic, based on the service 00118 and characteristic index fields 00119 00120 @param[in] charHandle 00121 The handle of the GattCharacteristic to read from 00122 @param[in] buffer 00123 Buffer to hold the the characteristic's value 00124 (raw byte array in LSB format) 00125 @param[in] len 00126 The number of bytes read into the buffer 00127 00128 @returns ble_error_t 00129 00130 @retval BLE_ERROR_NONE 00131 Everything executed properly 00132 00133 @section EXAMPLE 00134 00135 @code 00136 00137 @endcode 00138 */ 00139 /**************************************************************************/ 00140 ble_error_t nRF51GattServer::readValue(uint16_t charHandle, uint8_t buffer[], uint16_t *const lengthP) 00141 { 00142 ASSERT( ERROR_NONE == 00143 sd_ble_gatts_value_get(nrfCharacteristicHandles[charHandle].value_handle, 0, lengthP, buffer), 00144 BLE_ERROR_PARAM_OUT_OF_RANGE); 00145 00146 return BLE_ERROR_NONE; 00147 } 00148 00149 /**************************************************************************/ 00150 /*! 00151 @brief Updates the value of a characteristic, based on the service 00152 and characteristic index fields 00153 00154 @param[in] charHandle 00155 The handle of the GattCharacteristic to write to 00156 @param[in] buffer 00157 Data to use when updating the characteristic's value 00158 (raw byte array in LSB format) 00159 @param[in] len 00160 The number of bytes in buffer 00161 00162 @returns ble_error_t 00163 00164 @retval BLE_ERROR_NONE 00165 Everything executed properly 00166 00167 @section EXAMPLE 00168 00169 @code 00170 00171 @endcode 00172 */ 00173 /**************************************************************************/ 00174 ble_error_t nRF51GattServer::updateValue(uint16_t charHandle, uint8_t buffer[], uint16_t len, bool localOnly) 00175 { 00176 uint16_t gapConnectionHandle = nRF51Gap::getInstance().getConnectionHandle(); 00177 00178 if (localOnly) { 00179 /* Only update locally regardless of notify/indicate */ 00180 ASSERT_INT( ERROR_NONE, 00181 sd_ble_gatts_value_set(nrfCharacteristicHandles[charHandle].value_handle, 0, &len, buffer), 00182 BLE_ERROR_PARAM_OUT_OF_RANGE ); 00183 return BLE_ERROR_NONE; 00184 } 00185 00186 if ((p_characteristics[charHandle]->getProperties() & 00187 (GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_INDICATE | 00188 GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_NOTIFY)) && 00189 (gapConnectionHandle != BLE_CONN_HANDLE_INVALID)) { 00190 /* HVX update for the characteristic value */ 00191 ble_gatts_hvx_params_t hvx_params; 00192 00193 hvx_params.handle = nrfCharacteristicHandles[charHandle].value_handle; 00194 hvx_params.type = 00195 (p_characteristics[charHandle]->getProperties() & 00196 GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_NOTIFY) ? 00197 BLE_GATT_HVX_NOTIFICATION : BLE_GATT_HVX_INDICATION; 00198 hvx_params.offset = 0; 00199 hvx_params.p_data = buffer; 00200 hvx_params.p_len = &len; 00201 00202 error_t error = (error_t) sd_ble_gatts_hvx(gapConnectionHandle, &hvx_params); 00203 00204 /* ERROR_INVALID_STATE, ERROR_BUSY, ERROR_GATTS_SYS_ATTR_MISSING and 00205 *ERROR_NO_TX_BUFFERS the ATT table has been updated. */ 00206 if ((error != ERROR_NONE) && (error != ERROR_INVALID_STATE) && 00207 (error != ERROR_BLE_NO_TX_BUFFERS) && (error != ERROR_BUSY) && 00208 (error != ERROR_BLEGATTS_SYS_ATTR_MISSING)) { 00209 ASSERT_INT( ERROR_NONE, 00210 sd_ble_gatts_value_set(nrfCharacteristicHandles[charHandle].value_handle, 0, &len, buffer), 00211 BLE_ERROR_PARAM_OUT_OF_RANGE ); 00212 } 00213 } else { 00214 ASSERT_INT( ERROR_NONE, 00215 sd_ble_gatts_value_set(nrfCharacteristicHandles[charHandle].value_handle, 0, &len, buffer), 00216 BLE_ERROR_PARAM_OUT_OF_RANGE ); 00217 } 00218 00219 return BLE_ERROR_NONE; 00220 } 00221 00222 /**************************************************************************/ 00223 /*! 00224 @brief Callback handler for events getting pushed up from the SD 00225 */ 00226 /**************************************************************************/ 00227 void nRF51GattServer::hwCallback(ble_evt_t *p_ble_evt) 00228 { 00229 uint16_t handle_value; 00230 GattServerEvents::gattEvent_t eventType; 00231 const ble_gatts_evt_t *gattsEventP = &p_ble_evt->evt.gatts_evt; 00232 00233 switch (p_ble_evt->header.evt_id) { 00234 case BLE_GATTS_EVT_WRITE: 00235 /* There are 2 use case here: Values being updated & CCCD (indicate/notify) enabled */ 00236 00237 /* 1.) Handle CCCD changes */ 00238 handle_value = gattsEventP->params.write.handle; 00239 for (uint8_t i = 0; i<characteristicCount; i++) { 00240 if ((p_characteristics[i]->getProperties() & (GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_INDICATE | GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_NOTIFY)) && 00241 (nrfCharacteristicHandles[i].cccd_handle == handle_value)) { 00242 uint16_t cccd_value = 00243 (gattsEventP->params.write.data[1] << 8) | 00244 gattsEventP->params.write.data[0]; /* Little Endian but M0 may be mis-aligned */ 00245 00246 if (((p_characteristics[i]->getProperties() & GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_INDICATE) && (cccd_value & BLE_GATT_HVX_INDICATION)) || 00247 ((p_characteristics[i]->getProperties() & GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_NOTIFY) && (cccd_value & BLE_GATT_HVX_NOTIFICATION))) { 00248 eventType = GattServerEvents::GATT_EVENT_UPDATES_ENABLED; 00249 } else { 00250 eventType = GattServerEvents::GATT_EVENT_UPDATES_DISABLED; 00251 } 00252 00253 handleEvent(eventType, i); 00254 return; 00255 } 00256 } 00257 00258 /* 2.) Changes to the characteristic value will be handled with other events below */ 00259 eventType = GattServerEvents::GATT_EVENT_DATA_WRITTEN; 00260 break; 00261 00262 case BLE_GATTS_EVT_HVC: 00263 /* Indication confirmation received */ 00264 eventType = GattServerEvents::GATT_EVENT_CONFIRMATION_RECEIVED; 00265 handle_value = gattsEventP->params.hvc.handle; 00266 break; 00267 00268 case BLE_EVT_TX_COMPLETE: { 00269 handleDataSentEvent(p_ble_evt->evt.common_evt.params.tx_complete.count); 00270 return; 00271 } 00272 00273 case BLE_GATTS_EVT_SYS_ATTR_MISSING: 00274 sd_ble_gatts_sys_attr_set(gattsEventP->conn_handle, NULL, 0); 00275 return; 00276 00277 default: 00278 return; 00279 } 00280 00281 /* Find index (charHandle) in the pool */ 00282 for (uint8_t i = 0; i<characteristicCount; i++) { 00283 if (nrfCharacteristicHandles[i].value_handle == handle_value) { 00284 switch (eventType) { 00285 case GattServerEvents::GATT_EVENT_DATA_WRITTEN: { 00286 GattCharacteristicWriteCBParams cbParams = { 00287 .charHandle = i, 00288 .op = static_cast<GattCharacteristicWriteCBParams::Type>(gattsEventP->params.write.op), 00289 .offset = gattsEventP->params.write.offset, 00290 .len = gattsEventP->params.write.len, 00291 .data = gattsEventP->params.write.data 00292 }; 00293 handleDataWrittenEvent(&cbParams); 00294 break; 00295 } 00296 default: 00297 handleEvent(eventType, i); 00298 break; 00299 } 00300 } 00301 } 00302 } 00303 00304 ble_error_t 00305 nRF51GattServer::initializeGATTDatabase(void) 00306 { 00307 /* Empty. Services are populated in the GattDatabase through addService(). */ 00308 return BLE_ERROR_NONE; 00309 }
Generated on Tue Jul 12 2022 18:33:09 by 1.7.2