1 /* 2 * Copyright (C) 2021 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16 /** 17 * @file att_send.c 18 * 19 * @brief implement send function to be called. 20 * 21 */ 22 23 #include "att_common.h" 24 #include "att_receive.h" 25 26 #include <memory.h> 27 28 #include "buffer.h" 29 #include "list.h" 30 #include "packet.h" 31 32 #include "log.h" 33 34 #include "gap_if.h" 35 #include "gap_le_if.h" 36 37 #include "platform/include/allocator.h" 38 39 static AttServerSendDataCallback g_attServerSendDataCB; 40 41 static void AttAssignMTU(uint16_t *mtu, AttConnectInfo *connect); 42 static void AttFindInformationResDataAssign( 43 uint8_t format, uint16_t *inforDataLenPtr, uint16_t *dataLenPtr, uint16_t pairNum); 44 45 static void AttErrorResponseAsync(const void *context); 46 static void AttErrorResponseAsyncDestroy(const void *context); 47 static void AttExchangeMTUResponseAsync(const void *context); 48 static void AttExchangeMTUResponseAsyncDestroy(const void *context); 49 static void AttFindInformationResponseAsync(const void *context); 50 static void AttFindInformationResponseAsyncDestroy(const void *context); 51 static void AttFindByTypeValueResponseAsync(const void *context); 52 static void AttFindByTypeValueResponseAsyncDestroy(const void *context); 53 static void AttReadByTypeResponseAsync(const void *context); 54 static void AttReadByTypeResponseAsyncDestroy(const void *context); 55 static void AttReadResponseAsync(const void *context); 56 static void AttReadResponseAsyncDestroy(const void *context); 57 static void AttReadBlobResponseAsync(const void *context); 58 static void AttReadBlobResponseAsyncDestroy(const void *context); 59 static void AttReadMultipleResponseAsync(const void *context); 60 static void AttReadMultipleResponseAsyncDestroy(const void *context); 61 static void AttReadByGroupTypeResponseAsync(const void *context); 62 static void AttReadByGroupTypeResponseAsyncDestroy(const void *context); 63 static void AttWriteResponseAsync(const void *context); 64 static void AttWriteResponseAsyncDestroy(const void *context); 65 static void AttPrepareWriteResponseAsync(const void *context); 66 static void AttPrepareWriteResponseAsyncDestroy(const void *context); 67 static void AttExecuteWriteResponseAsync(const void *context); 68 static void AttExecuteWriteResponseAsyncDestroy(const void *context); 69 static void AttHandleValueNotificationAsync(const void *context); 70 static void AttHandleValueNotificationAsyncDestroy(const void *context); 71 static void AttHandleValueIndicationAsync(const void *context); 72 static void AttHandleValueIndicationAsyncDestroy(const void *context); 73 74 static void AttReadByTypeResponseFree(ReadByTypeResponseAsync *readByTypeResAsyncPtr); 75 static void AttFindInformationResponsePacketDataAssign( 76 uint8_t *data, FindInformationResponseAsync *findInforPtr, uint16_t dataLen); 77 static void AttReadByGroupTypeResponseAsyncFree( 78 ReadByGroupTypeResponseAsync *attReadByGroupResponseAsyncPtr, uint16_t num); 79 80 static void AttServerSendDataRegisterAsync(const void *context); 81 static void AttServerSendDataRegisterAsyncDestroy(const void *context); 82 static void AttServerSendDataDeRegisterAsync(const void *context); 83 static void AttServerSendDataDeRegisterAsyncDestroy(const void *context); 84 85 /** 86 * @brief Assign to mtu. 87 * 88 * @param1 mtu Indicates the pointer to mtu. 89 * @param2 connect Indicates the pointer to AttConnectInfo. 90 */ AttAssignMTU(uint16_t * mtu,AttConnectInfo * connect)91 void AttAssignMTU(uint16_t *mtu, AttConnectInfo *connect) 92 { 93 LOG_INFO("%{public}s enter", __FUNCTION__); 94 95 if (connect == NULL) { 96 LOG_INFO("%{public}s connect == NULL", __FUNCTION__); 97 return; 98 } 99 100 if (connect->mtuFlag) { 101 connect->mtuFlag = false; 102 if (connect->transportType == BT_TRANSPORT_BR_EDR) { 103 *mtu = DEFAULTBREDRMTU; 104 } 105 if (connect->transportType == BT_TRANSPORT_LE) { 106 *mtu = DEFAULTLEATTMTU; 107 } 108 } else { 109 *mtu = connect->mtu; 110 } 111 112 return; 113 } 114 115 /** 116 * @brief error response in self thread.. 117 * 118 * @param context Indicates the pointer to context. 119 */ AttErrorResponseAsync(const void * context)120 static void AttErrorResponseAsync(const void *context) 121 { 122 LOG_INFO("%{public}s enter", __FUNCTION__); 123 124 uint16_t index = 0; 125 int ret; 126 uint8_t *data = NULL; 127 Packet *packet = NULL; 128 AttConnectInfo *connect = NULL; 129 ErrorResponseAsync *errorResAsyncPtr = NULL; 130 131 errorResAsyncPtr = (ErrorResponseAsync *)context; 132 133 AttGetConnectInfoIndexByConnectHandle(errorResAsyncPtr->connectHandle, &index, &connect); 134 135 if (connect == NULL) { 136 LOG_INFO("%{public}s connect == NULL, and goto ATT_ERRORRESPONSE_END", __FUNCTION__); 137 goto ATT_ERRORRESPONSE_END; 138 } 139 140 packet = PacketMalloc(0, 0, sizeof(uint8_t) + STEP_FOUR); 141 if (packet == NULL) { 142 LOG_ERROR("point to NULL"); 143 return; 144 } 145 data = BufferPtr(PacketContinuousPayload(packet)); 146 data[0] = ERROR_RESPONSE; 147 data[1] = errorResAsyncPtr->ATTErrorPtr->reqOpcode; 148 ((uint16_t *)(data + STEP_TWO))[0] = errorResAsyncPtr->ATTErrorPtr->attHandleInError; 149 data[STEP_FOUR] = errorResAsyncPtr->ATTErrorPtr->errorCode; 150 151 ret = AttResponseSendData(connect, packet); 152 ServerCallbackReturnValue(ret, connect); 153 PacketFree(packet); 154 155 ATT_ERRORRESPONSE_END: 156 MEM_MALLOC.free(errorResAsyncPtr->ATTErrorPtr); 157 MEM_MALLOC.free(errorResAsyncPtr); 158 return; 159 } 160 161 /** 162 * @brief destroy error response in self thread.. 163 * 164 * @param context Indicates the pointer to context. 165 */ AttErrorResponseAsyncDestroy(const void * context)166 static void AttErrorResponseAsyncDestroy(const void *context) 167 { 168 LOG_INFO("%{public}s enter", __FUNCTION__); 169 170 ErrorResponseAsync *errorResAsyncPtr = (ErrorResponseAsync *)context; 171 172 MEM_MALLOC.free(errorResAsyncPtr->ATTErrorPtr); 173 MEM_MALLOC.free(errorResAsyncPtr); 174 175 return; 176 } 177 178 /** 179 * @brief gatt send error response to att. 180 * 181 * @param1 connectHandle Indicates the connect handle. 182 * @param2 attErrorPtr Indicates the pointer to const error response parameter. 183 * @return Returns <b>0</b> if the operation is successful; returns <b>!0</b> if the operation fails. 184 */ ATT_ErrorResponse(uint16_t connectHandle,const AttError * attErrorPtr)185 void ATT_ErrorResponse(uint16_t connectHandle, const AttError *attErrorPtr) 186 { 187 LOG_INFO("%{public}s enter, connectHandle = %hu, reqOpcode = %{public}d, " 188 "attHandleInError = %{public}d, errorCode = %{public}d", 189 __FUNCTION__, 190 connectHandle, 191 attErrorPtr->reqOpcode, 192 attErrorPtr->attHandleInError, 193 attErrorPtr->errorCode); 194 195 AttError *attErrorAsyncPtr = NULL; 196 ErrorResponseAsync *errorResAsyncPtr = NULL; 197 198 attErrorAsyncPtr = MEM_MALLOC.alloc(sizeof(AttError)); 199 if (attErrorAsyncPtr == NULL) { 200 LOG_ERROR("point to NULL"); 201 return; 202 } 203 attErrorAsyncPtr->reqOpcode = attErrorPtr->reqOpcode; 204 attErrorAsyncPtr->attHandleInError = attErrorPtr->attHandleInError; 205 attErrorAsyncPtr->errorCode = attErrorPtr->errorCode; 206 207 errorResAsyncPtr = MEM_MALLOC.alloc(sizeof(ErrorResponseAsync)); 208 if (errorResAsyncPtr == NULL) { 209 LOG_ERROR("point to NULL"); 210 return; 211 } 212 errorResAsyncPtr->connectHandle = connectHandle; 213 errorResAsyncPtr->ATTErrorPtr = attErrorAsyncPtr; 214 215 AttAsyncProcess(AttErrorResponseAsync, AttErrorResponseAsyncDestroy, errorResAsyncPtr); 216 217 return; 218 } 219 220 /** 221 * @brief exchange mtu response in self thread.. 222 * 223 * @param context Indicates the pointer to context. 224 */ AttExchangeMTUResponseAsync(const void * context)225 static void AttExchangeMTUResponseAsync(const void *context) 226 { 227 LOG_INFO("%{public}s enter", __FUNCTION__); 228 229 int ret; 230 uint16_t index = 0; 231 ExchangeMTUAsync *exchangeMtuResPtr = (ExchangeMTUAsync *)context; 232 AttConnectInfo *connect = NULL; 233 Packet *packet = NULL; 234 uint8_t *data = NULL; 235 236 AttGetConnectInfoIndexByConnectHandle(exchangeMtuResPtr->connectHandle, &index, &connect); 237 238 if (connect == NULL) { 239 LOG_INFO("%{public}s connect == NULL and goto ATTEXCHANGEMTURESPONSE_END", __FUNCTION__); 240 goto ATTEXCHANGEMTURESPONSE_END; 241 } 242 243 packet = PacketMalloc(0, 0, sizeof(uint8_t) + sizeof(exchangeMtuResPtr->mtu)); 244 if (packet == NULL) { 245 LOG_ERROR("point to NULL"); 246 return; 247 } 248 data = BufferPtr(PacketContinuousPayload(packet)); 249 data[0] = EXCHANGE_MTU_RESPONSE; 250 ((uint16_t *)(data + 1))[0] = exchangeMtuResPtr->mtu; 251 connect->mtu = Min(connect->receiveMtu, exchangeMtuResPtr->mtu); 252 253 ret = AttResponseSendData(connect, packet); 254 ServerCallbackReturnValue(ret, connect); 255 256 PacketFree(packet); 257 258 ATTEXCHANGEMTURESPONSE_END: 259 MEM_MALLOC.free(exchangeMtuResPtr); 260 return; 261 } 262 263 /** 264 * @brief destroy exchange mtu response in self thread.. 265 * 266 * @param context Indicates the pointer to context. 267 */ AttExchangeMTUResponseAsyncDestroy(const void * context)268 static void AttExchangeMTUResponseAsyncDestroy(const void *context) 269 { 270 LOG_INFO("%{public}s enter", __FUNCTION__); 271 272 ExchangeMTUAsync *exchangeMtuResPtr = (ExchangeMTUAsync *)context; 273 274 MEM_MALLOC.free(exchangeMtuResPtr); 275 276 return; 277 } 278 279 /** 280 * @brief gatt send exchangeMTU response to att. 281 * 282 * @param1 connectHandle Indicates the connect handle. 283 * @param2 serverRxMTU Indicates the attribute server receive MTU size. 284 * @return Returns <b>0</b> if the operation is successful; returns <b>!0</b> if the operation fails. 285 */ ATT_ExchangeMTUResponse(uint16_t connectHandle,uint16_t serverRxMTU)286 void ATT_ExchangeMTUResponse(uint16_t connectHandle, uint16_t serverRxMTU) 287 { 288 LOG_INFO("%{public}s enter, connectHandle = %hu, serverRxMTU = %hu", __FUNCTION__, connectHandle, serverRxMTU); 289 290 ExchangeMTUAsync *exchangeMtuResPtr = MEM_MALLOC.alloc(sizeof(ExchangeMTUAsync)); 291 if (exchangeMtuResPtr == NULL) { 292 if (g_attServerSendDataCB.attSendDataCB != NULL) { 293 g_attServerSendDataCB.attSendDataCB(connectHandle, BT_NO_MEMORY, g_attServerSendDataCB.context); 294 } 295 return; 296 } 297 exchangeMtuResPtr->connectHandle = connectHandle; 298 exchangeMtuResPtr->mtu = serverRxMTU; 299 AttAsyncProcess(AttExchangeMTUResponseAsync, AttExchangeMTUResponseAsyncDestroy, exchangeMtuResPtr); 300 301 return; 302 } 303 304 /** 305 * @brief find information response data assign. 306 * 307 * @param1 inforDataLenPtr Indicates the pointer of uint16_t. 308 * @param2 dataLenPtr Indicates the pointer of uint16_t. 309 */ AttFindInformationResDataAssign(uint8_t format,uint16_t * inforDataLenPtr,uint16_t * dataLenPtr,uint16_t pairNum)310 void AttFindInformationResDataAssign(uint8_t format, uint16_t *inforDataLenPtr, uint16_t *dataLenPtr, uint16_t pairNum) 311 { 312 LOG_INFO("%{public}s enter", __FUNCTION__); 313 314 if (format == HANDLEAND16BITBLUETOOTHUUID) { 315 *inforDataLenPtr = FINDINFORRESINFOR16BITLEN * pairNum; 316 *dataLenPtr = FINDINFORRESINFOR16BITLEN; 317 } else if (format == HANDLEAND128BITUUID) { 318 *inforDataLenPtr = FINDINFORRESINFOR128BITLEN * pairNum; 319 *dataLenPtr = FINDINFORRESINFOR128BITLEN; 320 } 321 322 return; 323 } 324 AttFindInformationResponsePacketDataAssign(uint8_t * data,FindInformationResponseAsync * findInforPtr,uint16_t dataLen)325 void AttFindInformationResponsePacketDataAssign( 326 uint8_t *data, FindInformationResponseAsync *findInforPtr, uint16_t dataLen) 327 { 328 LOG_INFO("%{public}s enter", __FUNCTION__); 329 330 uint16_t index; 331 332 data[0] = FIND_INFORMATION_RESPONSE; 333 data[1] = findInforPtr->attFindInformationResContext.format; 334 data += STEP_TWO; 335 for (index = 0; index < findInforPtr->attFindInformationResContext.pairNum; ++index) { 336 ((uint16_t *)(data))[0] = findInforPtr->attFindInformationResContext.handleUuidPairs[index].attHandle; 337 if (findInforPtr->attFindInformationResContext.format == HANDLEAND16BITBLUETOOTHUUID) { 338 ((uint16_t *)(data + STEP_TWO))[0] = 339 findInforPtr->attFindInformationResContext.handleUuidPairs[index].uuid.uuid16; 340 } else if (findInforPtr->attFindInformationResContext.format == HANDLEAND128BITUUID) { 341 if (memcpy_s(data + STEP_TWO, 342 UUID128BITTYPELEN, 343 findInforPtr->attFindInformationResContext.handleUuidPairs[index].uuid.uuid128, 344 UUID128BITTYPELEN) != EOK) { 345 LOG_ERROR("%{public}s memcpy_s fail", __FUNCTION__); 346 return; 347 } 348 } 349 data += dataLen; 350 } 351 352 return; 353 } 354 355 /** 356 * @brief find information response in self thread.. 357 * 358 * @param context Indicates the pointer to context. 359 */ AttFindInformationResponseAsync(const void * context)360 static void AttFindInformationResponseAsync(const void *context) 361 { 362 LOG_INFO("%{public}s enter", __FUNCTION__); 363 364 uint16_t index = 0; 365 int ret; 366 FindInformationResponseAsync *findInforPtr = (FindInformationResponseAsync *)context; 367 Packet *packet = NULL; 368 uint8_t *data = NULL; 369 uint16_t mtu = 0; 370 uint16_t inforDataLen = 0; 371 AttConnectInfo *connect = NULL; 372 uint16_t dataLen = 0; 373 374 AttGetConnectInfoIndexByConnectHandle(findInforPtr->connectHandle, &index, &connect); 375 if (connect == NULL) { 376 LOG_INFO("%{public}s connect == NULL and goto ATTFINDINFORMATIONRESPONSE_END", __FUNCTION__); 377 goto ATTFINDINFORMATIONRESPONSE_END; 378 } 379 AttAssignMTU(&mtu, connect); 380 AttFindInformationResDataAssign(findInforPtr->attFindInformationResContext.format, 381 &inforDataLen, 382 &dataLen, 383 findInforPtr->attFindInformationResContext.pairNum); 384 385 if (inforDataLen > (mtu - STEP_TWO)) { 386 LOG_INFO("%{public}s inforDataLen > (mtu - 2)", __FUNCTION__); 387 ServerCallbackBTBADPARAM(connect); 388 goto ATTFINDINFORMATIONRESPONSE_END; 389 } 390 391 packet = PacketMalloc(0, 0, sizeof(uint8_t) + sizeof(uint8_t) + inforDataLen); 392 if (packet == NULL) { 393 LOG_ERROR("point to NULL"); 394 return; 395 } 396 data = BufferPtr(PacketContinuousPayload(packet)); 397 AttFindInformationResponsePacketDataAssign(data, findInforPtr, dataLen); 398 399 ret = AttResponseSendData(connect, packet); 400 ServerCallbackReturnValue(ret, connect); 401 PacketFree(packet); 402 403 ATTFINDINFORMATIONRESPONSE_END: 404 MEM_MALLOC.free(findInforPtr->attFindInformationResContext.handleUuidPairs); 405 MEM_MALLOC.free(findInforPtr); 406 return; 407 } 408 409 /** 410 * @brief find information response in self thread.. 411 * 412 * @param context Indicates the pointer to context. 413 */ AttFindInformationResponseAsyncDestroy(const void * context)414 static void AttFindInformationResponseAsyncDestroy(const void *context) 415 { 416 LOG_INFO("%{public}s enter", __FUNCTION__); 417 418 FindInformationResponseAsync *findInforPtr = (FindInformationResponseAsync *)context; 419 420 MEM_MALLOC.free(findInforPtr->attFindInformationResContext.handleUuidPairs); 421 MEM_MALLOC.free(findInforPtr); 422 423 return; 424 } 425 426 /** 427 * @brief gatt send findInformation response to att. 428 * 429 * @param1 connectHandle Indicates the connect handle. 430 * @param2 format Indicates the format of the information data. 431 * @param3 handleUUIDPairs Indicates the pointer to const information data whose format is determined by the Format 432 * field. 433 * @param4 pairNum Indicates the paris number of the Information Data. 434 * @return Returns <b>0</b> if the operation is successful; returns <b>!0</b> if the operation fails. 435 */ ATT_FindInformationResponse(uint16_t connectHandle,uint8_t format,AttHandleUuid * handleUUIDPairs,uint16_t pairNum)436 void ATT_FindInformationResponse( 437 uint16_t connectHandle, uint8_t format, AttHandleUuid *handleUUIDPairs, uint16_t pairNum) 438 { 439 LOG_INFO("%{public}s enter, connectHandle = %hu, format=%hhu, pairNum=%hu", 440 __FUNCTION__, connectHandle, format, pairNum); 441 442 uint16_t index; 443 444 AttHandleUuid *attHandleUuidPtr = MEM_MALLOC.alloc(sizeof(AttHandleUuid) * pairNum); 445 if (attHandleUuidPtr == NULL) { 446 LOG_WARN("attHandleUuidPtr is null"); 447 return; 448 } 449 450 for (index = 0; index < pairNum; ++index) { 451 attHandleUuidPtr[index].attHandle = handleUUIDPairs[index].attHandle; 452 if (format == HANDLEAND16BITBLUETOOTHUUID) { 453 attHandleUuidPtr[index].uuid.uuid16 = handleUUIDPairs[index].uuid.uuid16; 454 } else if (format == HANDLEAND128BITUUID) { 455 (void)memcpy_s(attHandleUuidPtr[index].uuid.uuid128, 456 UUID128BITTYPELEN, 457 handleUUIDPairs[index].uuid.uuid128, 458 UUID128BITTYPELEN); 459 } 460 } 461 FindInformationResponseAsync *findInfor = MEM_MALLOC.alloc(sizeof(FindInformationResponseAsync)); 462 if (findInfor == NULL) { 463 LOG_ERROR("point to NULL"); 464 return; 465 } 466 findInfor->connectHandle = connectHandle; 467 findInfor->attFindInformationResContext.format = format; 468 findInfor->attFindInformationResContext.pairNum = pairNum; 469 findInfor->attFindInformationResContext.handleUuidPairs = attHandleUuidPtr; 470 471 AttAsyncProcess(AttFindInformationResponseAsync, AttFindInformationResponseAsyncDestroy, findInfor); 472 473 return; 474 } 475 476 /** 477 * @brief find by type value response in self thread.. 478 * 479 * @param context Indicates the pointer to context. 480 */ AttFindByTypeValueResponseAsync(const void * context)481 static void AttFindByTypeValueResponseAsync(const void *context) 482 { 483 LOG_INFO("%{public}s enter", __FUNCTION__); 484 485 uint16_t index = 0; 486 uint16_t mtu = 0; 487 AttConnectInfo *connect = NULL; 488 FindByTypeValueResponseAsync *findByTypeResAsyncPtr = (FindByTypeValueResponseAsync *)context; 489 uint16_t handleInfoListLen = (findByTypeResAsyncPtr->attFindByTypeResContext.listNum) * sizeof(AttHandleInfo); 490 int ret; 491 492 AttGetConnectInfoIndexByConnectHandle(findByTypeResAsyncPtr->connectHandle, &index, &connect); 493 494 if (connect == NULL) { 495 LOG_INFO("%{public}s connect == NULL and goto ATTFINDBYTYPEVALUERESPONSE_END", __FUNCTION__); 496 goto ATTFINDBYTYPEVALUERESPONSE_END; 497 } 498 499 AttAssignMTU(&mtu, connect); 500 501 if (handleInfoListLen > (mtu - 1)) { 502 ServerCallbackBTBADPARAM(connect); 503 goto ATTFINDBYTYPEVALUERESPONSE_END; 504 } 505 506 uint16_t handlesInforLen = sizeof(AttHandleInfo) * (findByTypeResAsyncPtr->attFindByTypeResContext.listNum); 507 Packet *packet = PacketMalloc(0, 0, sizeof(uint8_t) + handlesInforLen); 508 if (packet == NULL) { 509 LOG_ERROR("point to NULL"); 510 return; 511 } 512 uint8_t *data = BufferPtr(PacketContinuousPayload(packet)); 513 data[0] = FIND_BY_TYPE_VALUE_RESPONSE; 514 (void)memcpy_s( 515 data + 1, handleInfoListLen, findByTypeResAsyncPtr->attFindByTypeResContext.handleInfoList, handleInfoListLen); 516 517 ret = AttResponseSendData(connect, packet); 518 ServerCallbackReturnValue(ret, connect); 519 PacketFree(packet); 520 521 ATTFINDBYTYPEVALUERESPONSE_END: 522 MEM_MALLOC.free(findByTypeResAsyncPtr->attFindByTypeResContext.handleInfoList); 523 MEM_MALLOC.free(findByTypeResAsyncPtr); 524 return; 525 } 526 527 /** 528 * @brief destroy find by type value response in self thread.. 529 * 530 * @param context Indicates the pointer to context. 531 */ AttFindByTypeValueResponseAsyncDestroy(const void * context)532 static void AttFindByTypeValueResponseAsyncDestroy(const void *context) 533 { 534 LOG_INFO("%{public}s enter", __FUNCTION__); 535 536 FindByTypeValueResponseAsync *findByTypeResAsyncDesPtr = (FindByTypeValueResponseAsync *)context; 537 538 MEM_MALLOC.free(findByTypeResAsyncDesPtr->attFindByTypeResContext.handleInfoList); 539 MEM_MALLOC.free(findByTypeResAsyncDesPtr); 540 541 return; 542 } 543 544 /** 545 * @brief gatt send findbytypevalue response to att. 546 * 547 * @param1 connectHandle Indicates the connect handle. 548 * @param2 handleInfoList Indicates the pointer to const a list of 1 or more Handle Informations. 549 * @param3 listNum Indicates the number of handles information list. 550 * @return Returns <b>0</b> if the operation is successful; returns <b>!0</b> if the operation fails. 551 */ ATT_FindByTypeValueResponse(uint16_t connectHandle,const AttHandleInfo * handleInfoList,uint16_t listNum)552 void ATT_FindByTypeValueResponse(uint16_t connectHandle, const AttHandleInfo *handleInfoList, uint16_t listNum) 553 { 554 LOG_INFO("%{public}s enter,connectHandle = %hu,listNum=%hu", __FUNCTION__, connectHandle, listNum); 555 556 AttHandleInfo *attHandleInfoPtr = MEM_MALLOC.alloc(sizeof(AttHandleInfo) * listNum); 557 if (attHandleInfoPtr == NULL) { 558 LOG_ERROR("point to NULL"); 559 return; 560 } 561 (void)memcpy_s(attHandleInfoPtr, sizeof(AttHandleInfo) * listNum, handleInfoList, sizeof(AttHandleInfo) * listNum); 562 FindByTypeValueResponseAsync *findByTypeResAsyncPtr = MEM_MALLOC.alloc(sizeof(FindByTypeValueResponseAsync)); 563 if (findByTypeResAsyncPtr == NULL) { 564 LOG_ERROR("point to NULL"); 565 return; 566 } 567 findByTypeResAsyncPtr->connectHandle = connectHandle; 568 findByTypeResAsyncPtr->attFindByTypeResContext.listNum = listNum; 569 findByTypeResAsyncPtr->attFindByTypeResContext.handleInfoList = attHandleInfoPtr; 570 571 AttAsyncProcess(AttFindByTypeValueResponseAsync, AttFindByTypeValueResponseAsyncDestroy, findByTypeResAsyncPtr); 572 573 return; 574 } 575 AttReadByTypeResponseFree(ReadByTypeResponseAsync * readByTypeResAsyncPtr)576 static void AttReadByTypeResponseFree(ReadByTypeResponseAsync *readByTypeResAsyncPtr) 577 { 578 LOG_INFO("%{public}s enter", __FUNCTION__); 579 580 uint16_t index = 0; 581 582 for (; index < readByTypeResAsyncPtr->attReadByTypeRspContext.valueNum; ++index) { 583 MEM_MALLOC.free(readByTypeResAsyncPtr->attReadByTypeRspContext.valueList[index].attributeValue); 584 } 585 MEM_MALLOC.free(readByTypeResAsyncPtr->attReadByTypeRspContext.valueList); 586 MEM_MALLOC.free(readByTypeResAsyncPtr); 587 588 return; 589 } 590 591 /** 592 * @brief read by type response in self thread.. 593 * 594 * @param context Indicates the pointer to context. 595 */ AttReadByTypeResponseAsync(const void * context)596 static void AttReadByTypeResponseAsync(const void *context) 597 { 598 LOG_INFO("%{public}s enter", __FUNCTION__); 599 600 uint16_t index = 0; 601 uint16_t mtu = 0; 602 603 ReadByTypeResponseAsync *readByTypeResAsyncPtr = (ReadByTypeResponseAsync *)context; 604 Buffer *bufferPtr = NULL; 605 AttConnectInfo *connect = NULL; 606 607 uint8_t len = readByTypeResAsyncPtr->attReadByTypeRspContext.len; 608 uint16_t num = readByTypeResAsyncPtr->attReadByTypeRspContext.valueNum; 609 AttGetConnectInfoIndexByConnectHandle(readByTypeResAsyncPtr->connectHandle, &index, &connect); 610 611 if (connect == NULL) { 612 LOG_INFO("%{public}s connect == NULL and goto ATT_READBYTYPERESPONSE_END", __FUNCTION__); 613 goto ATT_READBYTYPERESPONSE_END; 614 } 615 616 AttAssignMTU(&mtu, connect); 617 618 if ((len * num) > (mtu - STEP_TWO)) { 619 ServerCallbackBTBADPARAM(connect); 620 goto ATT_READBYTYPERESPONSE_END; 621 } 622 if (((len - STEP_TWO) > (mtu - STEP_FOUR)) || ((len - STEP_TWO) > MAXREADBYTYPERESLEN)) { 623 len = Min(mtu - STEP_FOUR, MAXREADBYTYPERESLEN); 624 } 625 626 Packet *packet = PacketMalloc(0, 0, sizeof(uint8_t) + sizeof(len)); 627 if (packet == NULL) { 628 LOG_ERROR("point to NULL"); 629 return; 630 } 631 *(uint8_t *)BufferPtr(PacketContinuousPayload(packet)) = READ_BY_TYPE_RESPONSE; 632 *((uint8_t *)BufferPtr(PacketContinuousPayload(packet)) + 1) = len; 633 634 for (index = 0; index < num; index++) { 635 bufferPtr = BufferMalloc(len); 636 (void)memcpy_s(BufferPtr(bufferPtr), 637 BufferGetSize(bufferPtr), 638 &(readByTypeResAsyncPtr->attReadByTypeRspContext.valueList[index]), 639 STEP_TWO); 640 (void)memcpy_s((uint8_t *)BufferPtr(bufferPtr) + STEP_TWO, 641 BufferGetSize(bufferPtr) - STEP_TWO, 642 readByTypeResAsyncPtr->attReadByTypeRspContext.valueList[index].attributeValue, 643 len - STEP_TWO); 644 PacketPayloadAddLast(packet, bufferPtr); 645 BufferFree(bufferPtr); 646 } 647 648 int ret = AttResponseSendData(connect, packet); 649 ServerCallbackReturnValue(ret, connect); 650 PacketFree(packet); 651 652 ATT_READBYTYPERESPONSE_END: 653 AttReadByTypeResponseFree(readByTypeResAsyncPtr); 654 return; 655 } 656 657 /** 658 * @brief destroy read by type response in self thread.. 659 * 660 * @param context Indicates the pointer to context. 661 */ AttReadByTypeResponseAsyncDestroy(const void * context)662 static void AttReadByTypeResponseAsyncDestroy(const void *context) 663 { 664 LOG_INFO("%{public}s enter", __FUNCTION__); 665 666 ReadByTypeResponseAsync *readByTypeResAsyncPtr = (ReadByTypeResponseAsync *)context; 667 668 AttReadByTypeResponseFree(readByTypeResAsyncPtr); 669 670 return; 671 } 672 673 /** 674 * @brief gatt send readbytype response to att. 675 * 676 * @param1 connectHandle Indicates the connect handle. 677 * @param2 length Indicates the size of each attribute handlevalue pair. 678 * @param3 valueList Indicates the pointer to const a list of attribute data. 679 * @param4 attrValueNum Indicates the value of attribute value number. 680 * @return Returns <b>0</b> if the operation is successful; returns <b>!0</b> if the operation fails. 681 */ ATT_ReadByTypeResponse(uint16_t connectHandle,uint8_t length,const AttReadByTypeRspDataList * valueList,uint16_t attrValueNum)682 void ATT_ReadByTypeResponse( 683 uint16_t connectHandle, uint8_t length, const AttReadByTypeRspDataList *valueList, uint16_t attrValueNum) 684 { 685 LOG_INFO("%{public}s enter, connectHandle = %hu, length=%hhu, attrValueNum = %hu", 686 __FUNCTION__, 687 connectHandle, 688 length, 689 attrValueNum); 690 691 uint16_t index = 0; 692 AttReadByTypeRspDataList *attReadByTypeDataPtr = MEM_MALLOC.alloc(sizeof(AttReadByTypeRspDataList) * attrValueNum); 693 if (attReadByTypeDataPtr == NULL) { 694 LOG_ERROR("point to NULL"); 695 return; 696 } 697 698 for (; index < attrValueNum; ++index) { 699 attReadByTypeDataPtr[index].attHandle = valueList[index].attHandle; 700 attReadByTypeDataPtr[index].attributeValue = MEM_MALLOC.alloc(length - STEP_TWO); 701 if (attReadByTypeDataPtr[index].attributeValue == NULL) { 702 LOG_WARN("point is null"); 703 return; 704 } 705 706 (void)memcpy_s(attReadByTypeDataPtr[index].attributeValue, 707 length - STEP_TWO, 708 valueList[index].attributeValue, 709 length - STEP_TWO); 710 } 711 712 ReadByTypeResponseAsync *readByTypeResAsyncPtr = MEM_MALLOC.alloc(sizeof(ReadByTypeResponseAsync)); 713 readByTypeResAsyncPtr->connectHandle = connectHandle; 714 readByTypeResAsyncPtr->attReadByTypeRspContext.len = length; 715 readByTypeResAsyncPtr->attReadByTypeRspContext.valueNum = attrValueNum; 716 readByTypeResAsyncPtr->attReadByTypeRspContext.valueList = attReadByTypeDataPtr; 717 718 AttAsyncProcess(AttReadByTypeResponseAsync, AttReadByTypeResponseAsyncDestroy, readByTypeResAsyncPtr); 719 720 return; 721 } 722 723 /** 724 * @brief read response in self thread.. 725 * 726 * @param context Indicates the pointer to context. 727 */ AttReadResponseAsync(const void * context)728 static void AttReadResponseAsync(const void *context) 729 { 730 LOG_INFO("%{public}s enter", __FUNCTION__); 731 732 uint16_t index = 0; 733 uint16_t mtu = 0; 734 int ret; 735 uint16_t bufferSize; 736 ReadResponseAsync *readResAsyncPtr = (ReadResponseAsync *)context; 737 Packet *packet = NULL; 738 Buffer *bufferNew = NULL; 739 AttConnectInfo *connect = NULL; 740 uint8_t *data = NULL; 741 742 AttGetConnectInfoIndexByConnectHandle(readResAsyncPtr->connectHandle, &index, &connect); 743 744 if (connect == NULL) { 745 LOG_INFO("%{public}s connect == NULL and goto ATT_READRESPONSE_END", __FUNCTION__); 746 goto ATT_READRESPONSE_END; 747 } 748 749 AttAssignMTU(&mtu, connect); 750 751 bufferSize = BufferGetSize(readResAsyncPtr->attValue); 752 packet = PacketMalloc(0, 0, sizeof(uint8_t)); 753 if (packet == NULL) { 754 LOG_ERROR("point to NULL"); 755 return; 756 } 757 data = BufferPtr(PacketContinuousPayload(packet)); 758 data[0] = READ_RESPONSE; 759 760 if (bufferSize > (mtu - 1)) { 761 bufferNew = BufferSliceMalloc(readResAsyncPtr->attValue, 0, mtu - 1); 762 PacketPayloadAddLast(packet, bufferNew); 763 BufferFree(bufferNew); 764 } else if ((bufferSize <= (mtu - 1)) && (bufferSize > 0)) { 765 PacketPayloadAddLast(packet, readResAsyncPtr->attValue); 766 } 767 768 ret = AttResponseSendData(connect, packet); 769 ServerCallbackReturnValue(ret, connect); 770 PacketFree(packet); 771 772 ATT_READRESPONSE_END: 773 BufferFree(readResAsyncPtr->attValue); 774 MEM_MALLOC.free(readResAsyncPtr); 775 return; 776 } 777 778 /** 779 * @brief destroy read response in self thread.. 780 * 781 * @param context Indicates the pointer to context. 782 */ AttReadResponseAsyncDestroy(const void * context)783 static void AttReadResponseAsyncDestroy(const void *context) 784 { 785 LOG_INFO("%{public}s enter", __FUNCTION__); 786 787 ReadResponseAsync *readResAsyncPtr = (ReadResponseAsync *)context; 788 789 BufferFree(readResAsyncPtr->attValue); 790 MEM_MALLOC.free(readResAsyncPtr); 791 792 return; 793 } 794 795 /** 796 * @brief gatt send read response to att. 797 * 798 * @param1 connectHandle Indicates the connect handle. 799 * @param2 attValue Indicates the pointer to the value of the attribute with the handle given. 800 * @return Returns <b>0</b> if the operation is successful; returns <b>!0</b> if the operation fails. 801 */ ATT_ReadResponse(uint16_t connectHandle,const Buffer * attValue)802 void ATT_ReadResponse(uint16_t connectHandle, const Buffer *attValue) 803 { 804 LOG_INFO("%{public}s enter,connectHandle = %hu", __FUNCTION__, connectHandle); 805 806 Buffer *bufferPtr = NULL; 807 ReadResponseAsync *readResAsyncPtr = NULL; 808 809 bufferPtr = BufferRefMalloc(attValue); 810 readResAsyncPtr = MEM_MALLOC.alloc(sizeof(ReadResponseAsync)); 811 if (readResAsyncPtr == NULL) { 812 LOG_ERROR("point to NULL"); 813 return; 814 } 815 readResAsyncPtr->connectHandle = connectHandle; 816 readResAsyncPtr->attValue = bufferPtr; 817 818 AttAsyncProcess(AttReadResponseAsync, AttReadResponseAsyncDestroy, readResAsyncPtr); 819 820 return; 821 } 822 823 /** 824 * @brief read blob response in self thread.. 825 * 826 * @param context Indicates the pointer to context. 827 */ AttReadBlobResponseAsync(const void * context)828 static void AttReadBlobResponseAsync(const void *context) 829 { 830 LOG_INFO("%{public}s enter", __FUNCTION__); 831 832 uint16_t index = 0; 833 int ret; 834 uint16_t mtu = 0; 835 uint8_t *data = NULL; 836 ReadResponseAsync *readBlobResAsyncPtr = NULL; 837 AttConnectInfo *connect = NULL; 838 uint16_t bufferSize; 839 Packet *packet = NULL; 840 Buffer *bufferNew = NULL; 841 842 readBlobResAsyncPtr = (ReadResponseAsync *)context; 843 AttGetConnectInfoIndexByConnectHandle(readBlobResAsyncPtr->connectHandle, &index, &connect); 844 845 if (connect == NULL) { 846 LOG_INFO("%{public}s connect == NULL and goto ATT_READBLOBRESPONSE_END", __FUNCTION__); 847 goto ATT_READBLOBRESPONSE_END; 848 } 849 850 AttAssignMTU(&mtu, connect); 851 852 bufferSize = BufferGetSize(readBlobResAsyncPtr->attValue); 853 packet = PacketMalloc(0, 0, sizeof(uint8_t)); 854 if (packet == NULL) { 855 LOG_ERROR("point to NULL"); 856 return; 857 } 858 data = BufferPtr(PacketContinuousPayload(packet)); 859 data[0] = READ_BLOB_RESPONSE; 860 861 if (bufferSize > (mtu - 1)) { 862 bufferNew = BufferSliceMalloc(readBlobResAsyncPtr->attValue, 0, mtu - 1); 863 PacketPayloadAddLast(packet, bufferNew); 864 BufferFree(bufferNew); 865 } else if ((bufferSize <= (mtu - 1)) && (bufferSize > 0)) { 866 PacketPayloadAddLast(packet, readBlobResAsyncPtr->attValue); 867 } 868 869 ret = AttResponseSendData(connect, packet); 870 ServerCallbackReturnValue(ret, connect); 871 PacketFree(packet); 872 873 ATT_READBLOBRESPONSE_END: 874 BufferFree(readBlobResAsyncPtr->attValue); 875 MEM_MALLOC.free(readBlobResAsyncPtr); 876 return; 877 } 878 879 /** 880 * @brief destroy read blob response in self thread.. 881 * 882 * @param context Indicates the pointer to context. 883 */ AttReadBlobResponseAsyncDestroy(const void * context)884 static void AttReadBlobResponseAsyncDestroy(const void *context) 885 { 886 LOG_INFO("%{public}s enter", __FUNCTION__); 887 888 ReadResponseAsync *readBlobResAsyncPtr = (ReadResponseAsync *)context; 889 890 BufferFree(readBlobResAsyncPtr->attValue); 891 MEM_MALLOC.free(readBlobResAsyncPtr); 892 893 return; 894 } 895 896 /** 897 * @brief gatt send readblob response to att. 898 * 899 * @param1 connectHandle Indicates the connect handle. 900 * @param2 attReadBlobResObj Indicates the pointer to part of the value of the attribute with the handle given. 901 * @return Returns <b>0</b> if the operation is successful; returns <b>!0</b> if the operation fails. 902 */ ATT_ReadBlobResponse(uint16_t connectHandle,const Buffer * attReadBlobResObj)903 void ATT_ReadBlobResponse(uint16_t connectHandle, const Buffer *attReadBlobResObj) 904 { 905 LOG_INFO("%{public}s enter,connectHandle = %hu", __FUNCTION__, connectHandle); 906 907 Buffer *bufferPtr = NULL; 908 ReadResponseAsync *readBlobResAsyncPtr = NULL; 909 910 bufferPtr = BufferRefMalloc(attReadBlobResObj); 911 readBlobResAsyncPtr = MEM_MALLOC.alloc(sizeof(ReadResponseAsync)); 912 if (readBlobResAsyncPtr == NULL) { 913 LOG_ERROR("point to NULL"); 914 return; 915 } 916 readBlobResAsyncPtr->connectHandle = connectHandle; 917 readBlobResAsyncPtr->attValue = bufferPtr; 918 919 AttAsyncProcess(AttReadBlobResponseAsync, AttReadBlobResponseAsyncDestroy, readBlobResAsyncPtr); 920 921 return; 922 } 923 924 /** 925 * @brief read multiple response in self thread.. 926 * 927 * @param context Indicates the pointer to context. 928 */ AttReadMultipleResponseAsync(const void * context)929 static void AttReadMultipleResponseAsync(const void *context) 930 { 931 LOG_INFO("%{public}s enter", __FUNCTION__); 932 933 uint16_t index = 0; 934 int ret; 935 uint16_t bufferSize; 936 Packet *packet = NULL; 937 uint16_t mtu = 0; 938 ReadResponseAsync *readMultipleResponseAsyncPtr = NULL; 939 uint8_t *data = NULL; 940 Buffer *bufferNew = NULL; 941 AttConnectInfo *connect = NULL; 942 943 readMultipleResponseAsyncPtr = (ReadResponseAsync *)context; 944 945 AttGetConnectInfoIndexByConnectHandle(readMultipleResponseAsyncPtr->connectHandle, &index, &connect); 946 947 if (connect == NULL) { 948 LOG_INFO("%{public}s connect == NULL and goto ATT_READMULTIPLERESPONSE_END", __FUNCTION__); 949 goto ATT_READMULTIPLERESPONSE_END; 950 } 951 952 AttAssignMTU(&mtu, connect); 953 954 bufferSize = BufferGetSize(readMultipleResponseAsyncPtr->attValue); 955 packet = PacketMalloc(0, 0, sizeof(uint8_t)); 956 if (packet == NULL) { 957 LOG_ERROR("point to NULL"); 958 return; 959 } 960 data = BufferPtr(PacketContinuousPayload(packet)); 961 data[0] = READ_MULTIPLE_RESPONSE; 962 963 if (bufferSize > (mtu - 1)) { 964 bufferNew = BufferSliceMalloc(readMultipleResponseAsyncPtr->attValue, 0, mtu - 1); 965 PacketPayloadAddLast(packet, bufferNew); 966 BufferFree(bufferNew); 967 } else if ((bufferSize <= (mtu - 1)) && (bufferSize > 0)) { 968 PacketPayloadAddLast(packet, readMultipleResponseAsyncPtr->attValue); 969 } 970 971 ret = AttResponseSendData(connect, packet); 972 ServerCallbackReturnValue(ret, connect); 973 PacketFree(packet); 974 975 ATT_READMULTIPLERESPONSE_END: 976 BufferFree(readMultipleResponseAsyncPtr->attValue); 977 MEM_MALLOC.free(readMultipleResponseAsyncPtr); 978 return; 979 } 980 981 /** 982 * @brief destroy read multiple response in self thread.. 983 * 984 * @param context Indicates the pointer to context. 985 */ AttReadMultipleResponseAsyncDestroy(const void * context)986 static void AttReadMultipleResponseAsyncDestroy(const void *context) 987 { 988 LOG_INFO("%{public}s enter", __FUNCTION__); 989 990 ReadResponseAsync *readMultipleResponseAsyncPtr = (ReadResponseAsync *)context; 991 992 BufferFree(readMultipleResponseAsyncPtr->attValue); 993 MEM_MALLOC.free(readMultipleResponseAsyncPtr); 994 995 return; 996 } 997 998 /** 999 * @brief gatt send readmultiple response to att. 1000 * 1001 * @param1 connectHandle Indicates the connect handle. 1002 * @param2 valueList Indicates the pointer to a set of two or more values. 1003 * @return Returns <b>0</b> if the operation is successful; returns <b>!0</b> if the operation fails. 1004 */ ATT_ReadMultipleResponse(uint16_t connectHandle,const Buffer * valueList)1005 void ATT_ReadMultipleResponse(uint16_t connectHandle, const Buffer *valueList) 1006 { 1007 LOG_INFO("%{public}s enter,connectHandle = %hu", __FUNCTION__, connectHandle); 1008 1009 Buffer *bufferPtr = NULL; 1010 ReadResponseAsync *readMultipleResAsyncPtr = NULL; 1011 1012 bufferPtr = BufferRefMalloc(valueList); 1013 readMultipleResAsyncPtr = MEM_MALLOC.alloc(sizeof(ReadResponseAsync)); 1014 if (readMultipleResAsyncPtr == NULL) { 1015 LOG_ERROR("point to NULL"); 1016 return; 1017 } 1018 readMultipleResAsyncPtr->connectHandle = connectHandle; 1019 readMultipleResAsyncPtr->attValue = bufferPtr; 1020 1021 AttAsyncProcess(AttReadMultipleResponseAsync, AttReadMultipleResponseAsyncDestroy, readMultipleResAsyncPtr); 1022 1023 return; 1024 } 1025 AttReadByGroupTypeResponseAsyncFree(ReadByGroupTypeResponseAsync * attReadByGroupResponseAsyncPtr,uint16_t num)1026 void AttReadByGroupTypeResponseAsyncFree(ReadByGroupTypeResponseAsync *attReadByGroupResponseAsyncPtr, uint16_t num) 1027 { 1028 LOG_INFO("%{public}s enter", __FUNCTION__); 1029 1030 uint16_t index; 1031 1032 for (index = 0; index < num; index++) { 1033 MEM_MALLOC.free(attReadByGroupResponseAsyncPtr->attReadGroupResContext.attributeData[index].attributeValue); 1034 } 1035 MEM_MALLOC.free(attReadByGroupResponseAsyncPtr->attReadGroupResContext.attributeData); 1036 MEM_MALLOC.free(attReadByGroupResponseAsyncPtr); 1037 1038 return; 1039 } 1040 1041 /** 1042 * @brief read by group type response in self thread.. 1043 * 1044 * @param context Indicates the pointer to context. 1045 */ AttReadByGroupTypeResponseAsync(const void * context)1046 static void AttReadByGroupTypeResponseAsync(const void *context) 1047 { 1048 LOG_INFO("%{public}s enter", __FUNCTION__); 1049 1050 uint16_t index = 0; 1051 AttConnectInfo *connect = NULL; 1052 uint16_t mtu = 0; 1053 1054 ReadByGroupTypeResponseAsync *attReadByGroupResponseAsyncPtr = (ReadByGroupTypeResponseAsync *)context; 1055 1056 uint8_t len = attReadByGroupResponseAsyncPtr->attReadGroupResContext.length; 1057 uint16_t num = attReadByGroupResponseAsyncPtr->attReadGroupResContext.num; 1058 AttGetConnectInfoIndexByConnectHandle(attReadByGroupResponseAsyncPtr->connectHandle, &index, &connect); 1059 1060 if (connect == NULL) { 1061 LOG_INFO("%{public}s connect == NULL and goto ATTREADBYGROUPTYPERESONSE_END", __FUNCTION__); 1062 goto ATTREADBYGROUPTYPERESONSE_END; 1063 } 1064 1065 AttAssignMTU(&mtu, connect); 1066 1067 if ((len * num) > (mtu - STEP_TWO)) { 1068 ServerCallbackBTBADPARAM(connect); 1069 goto ATTREADBYGROUPTYPERESONSE_END; 1070 } 1071 if (((len - STEP_FOUR) > (mtu - STEP_SIX)) || ((len - STEP_FOUR) > MAXREADBYGROUPRESLEN)) { 1072 len = Min(mtu - STEP_SIX, MAXREADBYGROUPRESLEN); 1073 } 1074 1075 Packet *packet = PacketMalloc(0, 0, sizeof(uint8_t) + sizeof(len)); 1076 if (packet == NULL) { 1077 LOG_ERROR("point to NULL"); 1078 return; 1079 } 1080 *(uint8_t *)BufferPtr(PacketContinuousPayload(packet)) = READ_BY_GROUP_TYPE_RESPONSE; 1081 *((uint8_t *)BufferPtr(PacketContinuousPayload(packet)) + 1) = len; 1082 1083 for (index = 0; index < num; index++) { 1084 Buffer *bufferNew = BufferMalloc(len); 1085 (void)memcpy_s(BufferPtr(bufferNew), 1086 BufferGetSize(bufferNew), 1087 &(attReadByGroupResponseAsyncPtr->attReadGroupResContext.attributeData[index]), 1088 STEP_FOUR); 1089 (void)memcpy_s(((uint8_t *)BufferPtr(bufferNew) + STEP_FOUR), 1090 BufferGetSize(bufferNew) - STEP_FOUR, 1091 attReadByGroupResponseAsyncPtr->attReadGroupResContext.attributeData[index].attributeValue, 1092 len - STEP_FOUR); 1093 PacketPayloadAddLast(packet, bufferNew); 1094 BufferFree(bufferNew); 1095 } 1096 1097 int ret = AttResponseSendData(connect, packet); 1098 ServerCallbackReturnValue(ret, connect); 1099 PacketFree(packet); 1100 1101 ATTREADBYGROUPTYPERESONSE_END: 1102 AttReadByGroupTypeResponseAsyncFree(attReadByGroupResponseAsyncPtr, num); 1103 return; 1104 } 1105 1106 /** 1107 * @brief destroy read by group type response in self thread.. 1108 * 1109 * @param context Indicates the pointer to context. 1110 */ AttReadByGroupTypeResponseAsyncDestroy(const void * context)1111 static void AttReadByGroupTypeResponseAsyncDestroy(const void *context) 1112 { 1113 LOG_INFO("%{public}s enter", __FUNCTION__); 1114 1115 uint16_t num = 0; 1116 1117 ReadByGroupTypeResponseAsync *attReadByGroupResponseAsyncPtr = NULL; 1118 1119 attReadByGroupResponseAsyncPtr = (ReadByGroupTypeResponseAsync *)context; 1120 num = attReadByGroupResponseAsyncPtr->attReadGroupResContext.num; 1121 1122 AttReadByGroupTypeResponseAsyncFree(attReadByGroupResponseAsyncPtr, num); 1123 1124 return; 1125 } 1126 1127 /** 1128 * @brief gatt send readbygrouptype response to att. 1129 * 1130 * @param1 connectHandle Indicates the connect handle. 1131 * @param2 length Indicates the size of each attribute data. 1132 * @param3 serviceList Indicates the pointer to const a list of attribute data. 1133 * @param4 serviceNum Indicates the number of attribute data. 1134 * @return Returns <b>0</b> if the operation is successful; returns <b>!0</b> if the operation fails. 1135 */ ATT_ReadByGroupTypeResponse(uint16_t connectHandle,uint8_t length,const AttReadGoupAttributeData * serviceList,uint16_t serviceNum)1136 void ATT_ReadByGroupTypeResponse( 1137 uint16_t connectHandle, uint8_t length, const AttReadGoupAttributeData *serviceList, uint16_t serviceNum) 1138 { 1139 LOG_INFO("%{public}s enter, connectHandle = %hu,length = %{public}d,serviceNum = %{public}d", 1140 __FUNCTION__, connectHandle, length, serviceNum); 1141 1142 uint16_t index = 0; 1143 AttReadGoupAttributeData *attReadGroupAttrDataPtr = NULL; 1144 ReadByGroupTypeResponseAsync *attReadByGroupResAsyncPtr = NULL; 1145 1146 attReadGroupAttrDataPtr = MEM_MALLOC.alloc(sizeof(AttReadGoupAttributeData) * serviceNum); 1147 if (attReadGroupAttrDataPtr == NULL) { 1148 LOG_ERROR("point to NULL"); 1149 return; 1150 } 1151 for (; index < serviceNum; ++index) { 1152 attReadGroupAttrDataPtr[index].attributeValue = MEM_MALLOC.alloc(length - STEP_FOUR); 1153 attReadGroupAttrDataPtr[index].attHandle = serviceList[index].attHandle; 1154 attReadGroupAttrDataPtr[index].groupEndHandle = serviceList[index].groupEndHandle; 1155 (void)memcpy_s(attReadGroupAttrDataPtr[index].attributeValue, 1156 length - STEP_FOUR, 1157 serviceList[index].attributeValue, 1158 length - STEP_FOUR); 1159 } 1160 1161 attReadByGroupResAsyncPtr = MEM_MALLOC.alloc(sizeof(ReadByGroupTypeResponseAsync)); 1162 attReadByGroupResAsyncPtr->connectHandle = connectHandle; 1163 attReadByGroupResAsyncPtr->attReadGroupResContext.length = length; 1164 attReadByGroupResAsyncPtr->attReadGroupResContext.num = serviceNum; 1165 attReadByGroupResAsyncPtr->attReadGroupResContext.attributeData = attReadGroupAttrDataPtr; 1166 1167 AttAsyncProcess(AttReadByGroupTypeResponseAsync, AttReadByGroupTypeResponseAsyncDestroy, attReadByGroupResAsyncPtr); 1168 1169 return; 1170 } 1171 1172 /** 1173 * @brief write response in self thread.. 1174 * 1175 * @param context Indicates the pointer to context. 1176 */ AttWriteResponseAsync(const void * context)1177 static void AttWriteResponseAsync(const void *context) 1178 { 1179 LOG_INFO("%{public}s enter", __FUNCTION__); 1180 1181 uint16_t index = 0; 1182 int ret; 1183 Packet *packet = NULL; 1184 WriteResponseAsync *writeResponseAsyncPtr = NULL; 1185 uint8_t *data = NULL; 1186 uint16_t mtu = 0; 1187 AttConnectInfo *connect = NULL; 1188 1189 writeResponseAsyncPtr = (WriteResponseAsync *)context; 1190 1191 AttGetConnectInfoIndexByConnectHandle(writeResponseAsyncPtr->connectHandle, &index, &connect); 1192 1193 if (connect == NULL) { 1194 LOG_INFO("%{public}s connect == NULL and goto ATTWRITERESPONSE_END", __FUNCTION__); 1195 goto ATTWRITERESPONSE_END; 1196 } 1197 1198 AttAssignMTU(&mtu, connect); 1199 1200 packet = PacketMalloc(0, 0, sizeof(uint8_t)); 1201 if (packet == NULL) { 1202 LOG_ERROR("point to NULL"); 1203 return; 1204 } 1205 data = BufferPtr(PacketContinuousPayload(packet)); 1206 data[0] = WRITE_RESPONSE; 1207 1208 ret = AttResponseSendData(connect, packet); 1209 ServerCallbackReturnValue(ret, connect); 1210 PacketFree(packet); 1211 1212 ATTWRITERESPONSE_END: 1213 MEM_MALLOC.free(writeResponseAsyncPtr); 1214 return; 1215 } 1216 1217 /** 1218 * @brief destroy write response in self thread.. 1219 * 1220 * @param context Indicates the pointer to context. 1221 */ AttWriteResponseAsyncDestroy(const void * context)1222 static void AttWriteResponseAsyncDestroy(const void *context) 1223 { 1224 LOG_INFO("%{public}s enter", __FUNCTION__); 1225 1226 WriteResponseAsync *writeResponseAsyncPtr = (WriteResponseAsync *)context; 1227 1228 MEM_MALLOC.free(writeResponseAsyncPtr); 1229 1230 return; 1231 } 1232 1233 /** 1234 * @brief gatt send write response to att. 1235 * 1236 * @param connectHandle Indicates the connect handle. 1237 * @return Returns <b>0</b> if the operation is successful; returns <b>!0</b> if the operation fails. 1238 */ ATT_WriteResponse(uint16_t connectHandle)1239 void ATT_WriteResponse(uint16_t connectHandle) 1240 { 1241 LOG_INFO("%{public}s enter, connectHandle = %hu", __FUNCTION__, connectHandle); 1242 1243 WriteResponseAsync *writeResAsyncPtr = MEM_MALLOC.alloc(sizeof(WriteResponseAsync)); 1244 if (writeResAsyncPtr == NULL) { 1245 LOG_ERROR("point to NULL"); 1246 return; 1247 } 1248 writeResAsyncPtr->connectHandle = connectHandle; 1249 1250 AttAsyncProcess(AttWriteResponseAsync, AttWriteResponseAsyncDestroy, writeResAsyncPtr); 1251 1252 return; 1253 } 1254 1255 /** 1256 * @brief prepare write response in self thread.. 1257 * 1258 * @param context Indicates the pointer to context. 1259 */ AttPrepareWriteResponseAsync(const void * context)1260 static void AttPrepareWriteResponseAsync(const void *context) 1261 { 1262 LOG_INFO("%{public}s enter", __FUNCTION__); 1263 1264 uint16_t index = 0; 1265 int ret; 1266 uint16_t bufferSize; 1267 Packet *packet = NULL; 1268 uint8_t *data = NULL; 1269 uint16_t mtu = 0; 1270 AttConnectInfo *connect = NULL; 1271 PrepareWriteAsync *prepareWriteResAsyncPtr = NULL; 1272 1273 prepareWriteResAsyncPtr = (PrepareWriteAsync *)context; 1274 bufferSize = BufferGetSize(prepareWriteResAsyncPtr->attValue); 1275 1276 AttGetConnectInfoIndexByConnectHandle(prepareWriteResAsyncPtr->connectHandle, &index, &connect); 1277 1278 if (connect == NULL) { 1279 LOG_INFO("%{public}s connect == NULL and goto ATTPREPAREWRITERESPONSE_END", __FUNCTION__); 1280 goto ATTPREPAREWRITERESPONSE_END; 1281 } 1282 1283 AttAssignMTU(&mtu, connect); 1284 1285 if (bufferSize > (mtu - STEP_FIVE)) { 1286 LOG_INFO("%{public}s bufferSize > (mtu - 5)", __FUNCTION__); 1287 ServerCallbackBTBADPARAM(connect); 1288 goto ATTPREPAREWRITERESPONSE_END; 1289 } 1290 1291 packet = PacketMalloc(0, 0, sizeof(uint8_t) + sizeof(prepareWriteResAsyncPtr->attReadBlobObj)); 1292 if (packet == NULL) { 1293 LOG_ERROR("point to NULL"); 1294 return; 1295 } 1296 data = BufferPtr(PacketContinuousPayload(packet)); 1297 data[0] = PREPARE_WRITE_RESPONSE; 1298 ((uint16_t *)(data + 1))[0] = prepareWriteResAsyncPtr->attReadBlobObj.attHandle; 1299 ((uint16_t *)(data + STEP_THREE))[0] = prepareWriteResAsyncPtr->attReadBlobObj.offset; 1300 1301 if ((bufferSize < (mtu - STEP_FIVE)) && (bufferSize > 0)) { 1302 PacketPayloadAddLast(packet, prepareWriteResAsyncPtr->attValue); 1303 } 1304 1305 ret = AttResponseSendData(connect, packet); 1306 ServerCallbackReturnValue(ret, connect); 1307 PacketFree(packet); 1308 1309 ATTPREPAREWRITERESPONSE_END: 1310 BufferFree(prepareWriteResAsyncPtr->attValue); 1311 MEM_MALLOC.free(prepareWriteResAsyncPtr); 1312 return; 1313 } 1314 1315 /** 1316 * @brief destroy prepare write response in self thread.. 1317 * 1318 * @param context Indicates the pointer to context. 1319 */ AttPrepareWriteResponseAsyncDestroy(const void * context)1320 static void AttPrepareWriteResponseAsyncDestroy(const void *context) 1321 { 1322 LOG_INFO("%{public}s enter", __FUNCTION__); 1323 1324 PrepareWriteAsync *prepareWriteResAsyncPtr = (PrepareWriteAsync *)context; 1325 1326 BufferFree(prepareWriteResAsyncPtr->attValue); 1327 MEM_MALLOC.free(prepareWriteResAsyncPtr); 1328 1329 return; 1330 } 1331 1332 /** 1333 * @brief gatt send preparewrite response to att. 1334 * 1335 * @param1 connectHandle Indicates the connect handle. 1336 * @param2 attReadBlobObj Indicates the value of the struct AttReadBlobReqPrepareWriteValue. 1337 * @param3 attValue Indicates the pointer to the value of the attribute to be written. 1338 * @return Returns <b>0</b> if the operation is successful; returns <b>!0</b> if the operation fails. 1339 */ ATT_PrepareWriteResponse(uint16_t connectHandle,AttReadBlobReqPrepareWriteValue attReadBlobObj,const Buffer * attValue)1340 void ATT_PrepareWriteResponse( 1341 uint16_t connectHandle, AttReadBlobReqPrepareWriteValue attReadBlobObj, const Buffer *attValue) 1342 { 1343 LOG_INFO("%{public}s enter, connectHandle = %hu, attHandle = %{public}d, offset = %{public}d", 1344 __FUNCTION__, 1345 connectHandle, 1346 attReadBlobObj.attHandle, 1347 attReadBlobObj.offset); 1348 1349 Buffer *bufferPtr = NULL; 1350 PrepareWriteAsync *prepareWriteResAsyncPtr = NULL; 1351 1352 bufferPtr = BufferRefMalloc(attValue); 1353 prepareWriteResAsyncPtr = MEM_MALLOC.alloc(sizeof(PrepareWriteAsync)); 1354 if (prepareWriteResAsyncPtr == NULL) { 1355 LOG_ERROR("point to NULL"); 1356 return; 1357 } 1358 prepareWriteResAsyncPtr->connectHandle = connectHandle; 1359 prepareWriteResAsyncPtr->attReadBlobObj.attHandle = attReadBlobObj.attHandle; 1360 prepareWriteResAsyncPtr->attReadBlobObj.offset = attReadBlobObj.offset; 1361 prepareWriteResAsyncPtr->attValue = bufferPtr; 1362 1363 AttAsyncProcess(AttPrepareWriteResponseAsync, AttPrepareWriteResponseAsyncDestroy, prepareWriteResAsyncPtr); 1364 1365 return; 1366 } 1367 1368 /** 1369 * @brief execute write response in self thread.. 1370 * 1371 * @param context Indicates the pointer to context. 1372 */ AttExecuteWriteResponseAsync(const void * context)1373 static void AttExecuteWriteResponseAsync(const void *context) 1374 { 1375 LOG_INFO("%{public}s enter", __FUNCTION__); 1376 1377 uint16_t index = 0; 1378 int ret; 1379 Packet *packet = NULL; 1380 uint8_t *data = NULL; 1381 uint16_t mtu = 0; 1382 AttConnectInfo *connect = NULL; 1383 WriteResponseAsync *executeWriteResAsyncPtr = (WriteResponseAsync *)context; 1384 1385 AttGetConnectInfoIndexByConnectHandle(executeWriteResAsyncPtr->connectHandle, &index, &connect); 1386 1387 if (connect == NULL) { 1388 LOG_INFO("%{public}s connect == NULL and goto ATTEXECUTEWRITERESPONSE_END", __FUNCTION__); 1389 goto ATTEXECUTEWRITERESPONSE_END; 1390 } 1391 1392 AttAssignMTU(&mtu, connect); 1393 1394 packet = PacketMalloc(0, 0, sizeof(uint8_t)); 1395 if (packet == NULL) { 1396 LOG_ERROR("point to NULL"); 1397 return; 1398 } 1399 data = BufferPtr(PacketContinuousPayload(packet)); 1400 data[0] = EXECUTE_WRITE_RESPONSE; 1401 1402 ret = AttResponseSendData(connect, packet); 1403 ServerCallbackReturnValue(ret, connect); 1404 PacketFree(packet); 1405 1406 ATTEXECUTEWRITERESPONSE_END: 1407 MEM_MALLOC.free(executeWriteResAsyncPtr); 1408 return; 1409 } 1410 1411 /** 1412 * @brief destroy execute write response in self thread.. 1413 * 1414 * @param context Indicates the pointer to context. 1415 */ AttExecuteWriteResponseAsyncDestroy(const void * context)1416 static void AttExecuteWriteResponseAsyncDestroy(const void *context) 1417 { 1418 LOG_INFO("%{public}s enter", __FUNCTION__); 1419 1420 WriteResponseAsync *executeWriteResAsyncPtr = (WriteResponseAsync *)context; 1421 1422 MEM_MALLOC.free(executeWriteResAsyncPtr); 1423 1424 return; 1425 } 1426 1427 /** 1428 * @brief gatt send executewrite response to att. 1429 * 1430 * @param connectHandle Indicates the connect handle. 1431 * @return Returns <b>0</b> if the operation is successful; returns <b>!0</b> if the operation fails. 1432 */ ATT_ExecuteWriteResponse(uint16_t connectHandle)1433 void ATT_ExecuteWriteResponse(uint16_t connectHandle) 1434 { 1435 LOG_INFO("%{public}s enter,connectHandle = %hu", __FUNCTION__, connectHandle); 1436 1437 WriteResponseAsync *executeWriteResAsyncPtr = MEM_MALLOC.alloc(sizeof(WriteResponseAsync)); 1438 if (executeWriteResAsyncPtr == NULL) { 1439 LOG_ERROR("point to NULL"); 1440 return; 1441 } 1442 executeWriteResAsyncPtr->connectHandle = connectHandle; 1443 1444 AttAsyncProcess(AttExecuteWriteResponseAsync, AttExecuteWriteResponseAsyncDestroy, executeWriteResAsyncPtr); 1445 1446 return; 1447 } 1448 1449 /** 1450 * @brief handle value notification in self thread.. 1451 * 1452 * @param context Indicates the pointer to context. 1453 */ AttHandleValueNotificationAsync(const void * context)1454 static void AttHandleValueNotificationAsync(const void *context) 1455 { 1456 LOG_INFO("%{public}s enter", __FUNCTION__); 1457 1458 uint16_t index = 0; 1459 int ret; 1460 Packet *packet = NULL; 1461 Buffer *bufferNew = NULL; 1462 AttConnectInfo *connect = NULL; 1463 WriteAsync *handleNotificationAsyncPtr = NULL; 1464 uint16_t bufferSizenoti; 1465 uint8_t *data = NULL; 1466 1467 handleNotificationAsyncPtr = (WriteAsync *)context; 1468 1469 AttGetConnectInfoIndexByConnectHandle(handleNotificationAsyncPtr->connectHandle, &index, &connect); 1470 1471 if (connect == NULL) { 1472 LOG_INFO("%{public}s connect == NULL and goto ATT_HANDLEVALUENOTIFICATION_END", __FUNCTION__); 1473 goto ATT_HANDLEVALUENOTIFICATION_END; 1474 } 1475 1476 bufferSizenoti = BufferGetSize(handleNotificationAsyncPtr->attValue); 1477 packet = PacketMalloc(0, 0, sizeof(uint8_t) + sizeof(uint16_t)); 1478 if (packet == NULL) { 1479 LOG_ERROR("point to NULL"); 1480 return; 1481 } 1482 data = BufferPtr(PacketContinuousPayload(packet)); 1483 data[0] = HANDLE_VALUE_NOTIFICATION; 1484 ((uint16_t *)(data + 1))[0] = handleNotificationAsyncPtr->attHandle; 1485 1486 if ((bufferSizenoti > 0) && (bufferSizenoti <= (connect->mtu - STEP_THREE))) { 1487 PacketPayloadAddLast(packet, handleNotificationAsyncPtr->attValue); 1488 } else if (bufferSizenoti > (connect->mtu - STEP_THREE)) { 1489 uint16_t len = connect->mtu - STEP_THREE; 1490 bufferNew = BufferSliceMalloc(handleNotificationAsyncPtr->attValue, 0, len); 1491 PacketPayloadAddLast(packet, bufferNew); 1492 BufferFree(bufferNew); 1493 } 1494 1495 ret = AttResponseSendData(connect, packet); 1496 ServerCallbackReturnValue(ret, connect); 1497 PacketFree(packet); 1498 1499 ATT_HANDLEVALUENOTIFICATION_END: 1500 BufferFree(handleNotificationAsyncPtr->attValue); 1501 MEM_MALLOC.free(handleNotificationAsyncPtr); 1502 return; 1503 } 1504 1505 /** 1506 * @brief destroy handle value notification in self thread.. 1507 * 1508 * @param context Indicates the pointer to context. 1509 */ AttHandleValueNotificationAsyncDestroy(const void * context)1510 static void AttHandleValueNotificationAsyncDestroy(const void *context) 1511 { 1512 LOG_INFO("%{public}s enter", __FUNCTION__); 1513 1514 WriteAsync *handleNotificationAsyncPtr = (WriteAsync *)context; 1515 1516 BufferFree(handleNotificationAsyncPtr->attValue); 1517 MEM_MALLOC.free(handleNotificationAsyncPtr); 1518 1519 return; 1520 } 1521 1522 /** 1523 * @brief gatt send handlevalue notification to att. 1524 * 1525 * @param1 connectHandle Indicates the connect handle. 1526 * @param2 attHandle Indicates the handle of the attribute. 1527 * @param3 attValue Indicates the pointer to the current value of the attribute. 1528 * @return Returns <b>0</b> if the operation is successful; returns <b>!0</b> if the operation fails. 1529 */ ATT_HandleValueNotification(uint16_t connectHandle,uint16_t attHandle,const Buffer * attValue)1530 void ATT_HandleValueNotification(uint16_t connectHandle, uint16_t attHandle, const Buffer *attValue) 1531 { 1532 LOG_INFO("%{public}s enter, connectHandle = %hu, attHandle=%{public}d", __FUNCTION__, connectHandle, attHandle); 1533 1534 Buffer *bufferPtr = NULL; 1535 WriteAsync *handleNotificationAsyncPtr = NULL; 1536 1537 bufferPtr = BufferRefMalloc(attValue); 1538 handleNotificationAsyncPtr = MEM_MALLOC.alloc(sizeof(WriteAsync)); 1539 if (handleNotificationAsyncPtr == NULL) { 1540 LOG_ERROR("point to NULL"); 1541 return; 1542 } 1543 handleNotificationAsyncPtr->connectHandle = connectHandle; 1544 handleNotificationAsyncPtr->attHandle = attHandle; 1545 handleNotificationAsyncPtr->attValue = bufferPtr; 1546 1547 AttAsyncProcess( 1548 AttHandleValueNotificationAsync, AttHandleValueNotificationAsyncDestroy, handleNotificationAsyncPtr); 1549 1550 return; 1551 } 1552 1553 /** 1554 * @brief handle value indication in self thread.. 1555 * 1556 * @param context Indicates the pointer to context. 1557 */ AttHandleValueIndicationAsync(const void * context)1558 static void AttHandleValueIndicationAsync(const void *context) 1559 { 1560 LOG_INFO("%{public}s enter", __FUNCTION__); 1561 1562 uint16_t index = 0; 1563 int ret; 1564 uint16_t bufferSize; 1565 Packet *packet = NULL; 1566 uint8_t *data = NULL; 1567 Buffer *bufferNew = NULL; 1568 WriteAsync *handleIndicationAsyncPtr = NULL; 1569 uint16_t len; 1570 AttConnectInfo *connect = NULL; 1571 1572 handleIndicationAsyncPtr = (WriteAsync *)context; 1573 1574 AttGetConnectInfoIndexByConnectHandle(handleIndicationAsyncPtr->connectHandle, &index, &connect); 1575 1576 if (connect == NULL) { 1577 LOG_INFO("%{public}s connect == NULL and goto ATTHANDLEVALUEINDICATION_END", __FUNCTION__); 1578 goto ATTHANDLEVALUEINDICATION_END; 1579 } 1580 1581 connect->serverSendFlag = true; 1582 bufferSize = BufferGetSize(handleIndicationAsyncPtr->attValue); 1583 packet = PacketMalloc(0, 0, sizeof(uint8_t) + sizeof(handleIndicationAsyncPtr->attHandle)); 1584 if (packet == NULL) { 1585 LOG_ERROR("point to NULL"); 1586 return; 1587 } 1588 data = BufferPtr(PacketContinuousPayload(packet)); 1589 data[0] = HANDLE_VALUE_INDICATION; 1590 ((uint16_t *)(data + 1))[0] = handleIndicationAsyncPtr->attHandle; 1591 if ((bufferSize > 0) && (bufferSize <= (connect->mtu - STEP_THREE))) { 1592 PacketPayloadAddLast(packet, handleIndicationAsyncPtr->attValue); 1593 } else if (bufferSize > (connect->mtu - STEP_THREE)) { 1594 len = connect->mtu - STEP_THREE; 1595 bufferNew = BufferSliceMalloc(handleIndicationAsyncPtr->attValue, 0, len); 1596 PacketPayloadAddLast(packet, bufferNew); 1597 BufferFree(bufferNew); 1598 } 1599 1600 ret = AttResponseSendData(connect, packet); 1601 ServerCallbackReturnValue(ret, connect); 1602 PacketFree(packet); 1603 1604 ATTHANDLEVALUEINDICATION_END: 1605 BufferFree(handleIndicationAsyncPtr->attValue); 1606 MEM_MALLOC.free(handleIndicationAsyncPtr); 1607 return; 1608 } 1609 1610 /** 1611 * @brief destroy handle value indication in self thread.. 1612 * 1613 * @param context Indicates the pointer to context. 1614 */ AttHandleValueIndicationAsyncDestroy(const void * context)1615 static void AttHandleValueIndicationAsyncDestroy(const void *context) 1616 { 1617 LOG_INFO("%{public}s enter", __FUNCTION__); 1618 1619 WriteAsync *handleIndicationAsyncPtr = (WriteAsync *)context; 1620 1621 BufferFree(handleIndicationAsyncPtr->attValue); 1622 MEM_MALLOC.free(handleIndicationAsyncPtr); 1623 1624 return; 1625 } 1626 1627 /** 1628 * @brief gatt send handlevalue indication to att. 1629 * 1630 * @param1 connectHandle Indicates the connect handle. 1631 * @param2 attHandle Indicates the handle of the attribute. 1632 * @param3 attValue Indicates the pointer to the current value of the attribute. 1633 * @return Returns <b>0</b> if the operation is successful; returns <b>!0</b> if the operation fails. 1634 */ ATT_HandleValueIndication(uint16_t connectHandle,uint16_t attHandle,const Buffer * attValue)1635 void ATT_HandleValueIndication(uint16_t connectHandle, uint16_t attHandle, const Buffer *attValue) 1636 { 1637 LOG_INFO("%{public}s enter, connectHandle = %hu, attHandle=%{public}d", __FUNCTION__, connectHandle, attHandle); 1638 1639 Buffer *bufferPtr = NULL; 1640 WriteAsync *handleIndicationAsyncPtr = NULL; 1641 1642 bufferPtr = BufferRefMalloc(attValue); 1643 handleIndicationAsyncPtr = MEM_MALLOC.alloc(sizeof(WriteAsync)); 1644 if (handleIndicationAsyncPtr == NULL) { 1645 LOG_ERROR("point to NULL"); 1646 return; 1647 } 1648 handleIndicationAsyncPtr->connectHandle = connectHandle; 1649 handleIndicationAsyncPtr->attHandle = attHandle; 1650 handleIndicationAsyncPtr->attValue = bufferPtr; 1651 1652 AttAsyncProcess(AttHandleValueIndicationAsync, AttHandleValueIndicationAsyncDestroy, handleIndicationAsyncPtr); 1653 1654 return; 1655 } 1656 1657 /** 1658 * @brief server send data register.. 1659 * 1660 * @param context Indicates the pointer to context. 1661 */ AttServerSendDataRegisterAsync(const void * context)1662 void AttServerSendDataRegisterAsync(const void *context) 1663 { 1664 LOG_INFO("%{public}s enter", __FUNCTION__); 1665 1666 AttServerSendDataCallback *attServerSendDataCallbackPtr = (AttServerSendDataCallback *)context; 1667 1668 g_attServerSendDataCB.attSendDataCB = attServerSendDataCallbackPtr->attSendDataCB; 1669 g_attServerSendDataCB.context = attServerSendDataCallbackPtr->context; 1670 1671 AttServerCallBackCopyToCommon(attServerSendDataCallbackPtr->attSendDataCB, attServerSendDataCallbackPtr->context); 1672 1673 MEM_MALLOC.free(attServerSendDataCallbackPtr); 1674 1675 return; 1676 } 1677 1678 /** 1679 * @brief server send data register.destroy. 1680 * 1681 * @param context Indicates the pointer to context. 1682 */ AttServerSendDataRegisterAsyncDestroy(const void * context)1683 void AttServerSendDataRegisterAsyncDestroy(const void *context) 1684 { 1685 LOG_INFO("%{public}s enter", __FUNCTION__); 1686 1687 AttServerSendDataCallback *attServerSendDataCallbackPtr = (AttServerSendDataCallback *)context; 1688 1689 MEM_MALLOC.free(attServerSendDataCallbackPtr); 1690 1691 return; 1692 } 1693 1694 /** 1695 * @brief server gatt send data register. 1696 * 1697 * @param1 attSendDataCB Indicates the pointer of attSendDataCallback. 1698 * @param2 context Indicates the pointer of context. 1699 */ ATT_ServerSendDataRegister(attSendDataCallback attSendDataCB,void * context)1700 void ATT_ServerSendDataRegister(attSendDataCallback attSendDataCB, void *context) 1701 { 1702 LOG_INFO("%{public}s enter", __FUNCTION__); 1703 1704 AttServerSendDataCallback *attServerSendDataCallbackPtr = MEM_MALLOC.alloc(sizeof(AttServerSendDataCallback)); 1705 if (attServerSendDataCallbackPtr == NULL) { 1706 LOG_ERROR("point to NULL"); 1707 return; 1708 } 1709 attServerSendDataCallbackPtr->attSendDataCB = attSendDataCB; 1710 attServerSendDataCallbackPtr->context = context; 1711 1712 AttAsyncProcess( 1713 AttServerSendDataRegisterAsync, AttServerSendDataRegisterAsyncDestroy, attServerSendDataCallbackPtr); 1714 1715 return; 1716 } 1717 1718 /** 1719 * @brief server send data deregister. 1720 * 1721 * @param context Indicates the pointer to context. 1722 */ AttServerSendDataDeRegisterAsync(const void * context)1723 void AttServerSendDataDeRegisterAsync(const void *context) 1724 { 1725 LOG_INFO("%{public}s enter", __FUNCTION__); 1726 1727 g_attServerSendDataCB.attSendDataCB = NULL; 1728 g_attServerSendDataCB.context = NULL; 1729 1730 AttCallBackDelectCopyToCommon(); 1731 1732 return; 1733 } 1734 1735 /** 1736 * @brief server send data deregister.destroy. 1737 * 1738 * @param context Indicates the pointer to context. 1739 */ AttServerSendDataDeRegisterAsyncDestroy(const void * context)1740 void AttServerSendDataDeRegisterAsyncDestroy(const void *context) 1741 { 1742 LOG_INFO("%{public}s enter", __FUNCTION__); 1743 1744 return; 1745 } 1746 1747 /** 1748 * @brief server gatt send data deregister. 1749 * 1750 */ ATT_ServerSendDataDeRegister()1751 void ATT_ServerSendDataDeRegister() 1752 { 1753 LOG_INFO("%{public}s enter", __FUNCTION__); 1754 1755 AttAsyncProcess(AttServerSendDataDeRegisterAsync, AttServerSendDataDeRegisterAsyncDestroy, NULL); 1756 1757 return; 1758 } 1759