@@ -95,6 +95,7 @@ ATTClass::ATTClass() :
95
95
memset (_peers[i].address , 0x00 , sizeof (_peers[i].address ));
96
96
_peers[i].mtu = 23 ;
97
97
_peers[i].device = NULL ;
98
+ _peers[i].encryption = 0x0 ;
98
99
}
99
100
100
101
memset (_eventHandlers, 0x00 , sizeof (_eventHandlers));
@@ -267,12 +268,22 @@ void ATTClass::handleData(uint16_t connectionHandle, uint8_t dlen, uint8_t data[
267
268
268
269
uint16_t mtu = this ->mtu (connectionHandle);
269
270
271
+ #ifdef _BLE_TRACE_
272
+ Serial.print (" data opcode: 0x" );
273
+ Serial.println (opcode, HEX);
274
+ #endif
270
275
switch (opcode) {
271
276
case ATT_OP_ERROR:
277
+ #ifdef _BLE_TRACE_
278
+ Serial.println (" [Info] data error" );
279
+ #endif
272
280
error (connectionHandle, dlen, data);
273
281
break ;
274
282
275
283
case ATT_OP_MTU_REQ:
284
+ #ifdef _BLE_TRACE_
285
+ Serial.println (" MTU" );
286
+ #endif
276
287
mtuReq (connectionHandle, dlen, data);
277
288
break ;
278
289
@@ -281,6 +292,9 @@ void ATTClass::handleData(uint16_t connectionHandle, uint8_t dlen, uint8_t data[
281
292
break ;
282
293
283
294
case ATT_OP_FIND_INFO_REQ:
295
+ #ifdef _BLE_TRACE_
296
+ Serial.println (" Find info" );
297
+ #endif
284
298
findInfoReq (connectionHandle, mtu, dlen, data);
285
299
break ;
286
300
@@ -293,6 +307,9 @@ void ATTClass::handleData(uint16_t connectionHandle, uint8_t dlen, uint8_t data[
293
307
break ;
294
308
295
309
case ATT_OP_READ_BY_TYPE_REQ:
310
+ #ifdef _BLE_TRACE_
311
+ Serial.println (" By type" );
312
+ #endif
296
313
readByTypeReq (connectionHandle, mtu, dlen, data);
297
314
break ;
298
315
@@ -319,6 +336,9 @@ void ATTClass::handleData(uint16_t connectionHandle, uint8_t dlen, uint8_t data[
319
336
320
337
case ATT_OP_WRITE_REQ:
321
338
case ATT_OP_WRITE_CMD:
339
+ #ifdef _BLE_TRACE_
340
+ Serial.println (" Write req" );
341
+ #endif
322
342
writeReqOrCmd (connectionHandle, mtu, opcode, dlen, data);
323
343
break ;
324
344
@@ -346,6 +366,9 @@ void ATTClass::handleData(uint16_t connectionHandle, uint8_t dlen, uint8_t data[
346
366
case ATT_OP_READ_MULTI_REQ:
347
367
case ATT_OP_SIGNED_WRITE_CMD:
348
368
default :
369
+ #ifdef _BLE_TRACE_
370
+ Serial.println (" [Info] Unhandled dara" );
371
+ #endif
349
372
sendError (connectionHandle, opcode, 0x00 , ATT_ECODE_REQ_NOT_SUPP);
350
373
break ;
351
374
}
@@ -398,6 +421,10 @@ void ATTClass::removeConnection(uint16_t handle, uint8_t /*reason*/)
398
421
_peers[peerIndex].addressType = 0x00 ;
399
422
memset (_peers[peerIndex].address , 0x00 , sizeof (_peers[peerIndex].address ));
400
423
_peers[peerIndex].mtu = 23 ;
424
+ _peers[peerIndex].encryption = PEER_ENCRYPTION::NO_ENCRYPTION;
425
+ _peers[peerIndex].IOCap [0 ] = 0 ;
426
+ _peers[peerIndex].IOCap [1 ] = 0 ;
427
+ _peers[peerIndex].IOCap [2 ] = 0 ;
401
428
402
429
if (_peers[peerIndex].device ) {
403
430
delete _peers[peerIndex].device ;
@@ -808,6 +835,14 @@ void ATTClass::readByGroupReq(uint16_t connectionHandle, uint16_t mtu, uint8_t d
808
835
uint16_t endHandle;
809
836
uint16_t uuid;
810
837
} *readByGroupReq = (ReadByGroupReq*)data;
838
+ #ifdef _BLE_TRACE_
839
+ Serial.print (" readByGroupReq: start: 0x" );
840
+ Serial.println (readByGroupReq->startHandle ,HEX);
841
+ Serial.print (" readByGroupReq: end: 0x" );
842
+ Serial.println (readByGroupReq->endHandle ,HEX);
843
+ Serial.print (" readByGroupReq: UUID: 0x" );
844
+ Serial.println (readByGroupReq->uuid ,HEX);
845
+ #endif
811
846
812
847
if (dlen != sizeof (ReadByGroupReq) || (readByGroupReq->uuid != BLETypeService && readByGroupReq->uuid != 0x2801 )) {
813
848
sendError (connectionHandle, ATT_OP_READ_BY_GROUP_REQ, readByGroupReq->startHandle , ATT_ECODE_UNSUPP_GRP_TYPE);
@@ -820,7 +855,10 @@ void ATTClass::readByGroupReq(uint16_t connectionHandle, uint16_t mtu, uint8_t d
820
855
response[0 ] = ATT_OP_READ_BY_GROUP_RESP;
821
856
response[1 ] = 0x00 ;
822
857
responseLength = 2 ;
823
-
858
+ #ifdef _BLE_TRACE_
859
+ Serial.print (" readByGroupReq: attrcount: " );
860
+ Serial.println (GATT.attributeCount ());
861
+ #endif
824
862
for (uint16_t i = (readByGroupReq->startHandle - 1 ); i < GATT.attributeCount () && i <= (readByGroupReq->endHandle - 1 ); i++) {
825
863
BLELocalAttribute* attribute = GATT.attribute (i);
826
864
@@ -907,6 +945,8 @@ void ATTClass::readOrReadBlobReq(uint16_t connectionHandle, uint16_t mtu, uint8_
907
945
return ;
908
946
}
909
947
}
948
+ // / if auth error, hold the response in a buffer.
949
+ bool holdResponse = false ;
910
950
911
951
uint16_t handle = *(uint16_t *)data;
912
952
uint16_t offset = (opcode == ATT_OP_READ_REQ) ? 0 : *(uint16_t *)&data[sizeof (handle)];
@@ -963,6 +1003,11 @@ void ATTClass::readOrReadBlobReq(uint16_t connectionHandle, uint16_t mtu, uint8_
963
1003
sendError (connectionHandle, opcode, handle, ATT_ECODE_READ_NOT_PERM);
964
1004
return ;
965
1005
}
1006
+ // If characteristic requires encryption send error & hold response until encrypted
1007
+ if ((characteristic->properties () & BLEAuth) > 0 && (getPeerEncryption (connectionHandle) & PEER_ENCRYPTION::ENCRYPTED_AES)==0 ) {
1008
+ holdResponse = true ;
1009
+ sendError (connectionHandle, opcode, handle, ATT_ECODE_INSUFF_ENC);
1010
+ }
966
1011
967
1012
uint16_t valueLength = characteristic->valueLength ();
968
1013
@@ -995,8 +1040,12 @@ void ATTClass::readOrReadBlobReq(uint16_t connectionHandle, uint16_t mtu, uint8_
995
1040
memcpy (&response[responseLength], descriptor->value () + offset, valueLength);
996
1041
responseLength += valueLength;
997
1042
}
998
-
999
- HCI.sendAclPkt (connectionHandle, ATT_CID, responseLength, response);
1043
+ if (holdResponse){
1044
+ memcpy (holdBuffer, response, responseLength);
1045
+ holdBufferSize = responseLength;
1046
+ }else {
1047
+ HCI.sendAclPkt (connectionHandle, ATT_CID, responseLength, response);
1048
+ }
1000
1049
}
1001
1050
1002
1051
void ATTClass::readResp (uint16_t connectionHandle, uint8_t dlen, uint8_t data[])
@@ -1688,7 +1737,85 @@ void ATTClass::writeCmd(uint16_t connectionHandle, uint16_t handle, const uint8_
1688
1737
sendReq (connectionHandle, &writeReq, 3 + dataLen, NULL );
1689
1738
}
1690
1739
1740
+ // Set encryption state for a peer
1741
+ int ATTClass::setPeerEncryption (uint16_t connectionHandle, uint8_t encryption){
1742
+ for (int i=0 ; i<ATT_MAX_PEERS; i++){
1743
+ if (_peers[i].connectionHandle != connectionHandle){
1744
+ continue ;
1745
+ }
1746
+ _peers[i].encryption = encryption;
1747
+ return 1 ;
1748
+ }
1749
+ return 0 ;
1750
+ }
1751
+ // Set the IO capabilities for a peer
1752
+ int ATTClass::setPeerIOCap (uint16_t connectionHandle, uint8_t IOCap[3 ]){
1753
+ for (int i=0 ; i<ATT_MAX_PEERS; i++){
1754
+ if (_peers[i].connectionHandle != connectionHandle){
1755
+ continue ;
1756
+ }
1757
+ memcpy (_peers[i].IOCap , IOCap, 3 );
1758
+ return 1 ;
1759
+ }
1760
+ return 0 ;
1761
+ }
1762
+ // Return the connection handle for the first peer that is requesting encryption
1763
+ uint16_t ATTClass::getPeerEncrptingConnectionHandle (){
1764
+ for (int i=0 ; i<ATT_MAX_PEERS; i++){
1765
+ if (_peers[i].encryption & PEER_ENCRYPTION::REQUESTED_ENCRYPTION > 0 ){
1766
+ return _peers[i].connectionHandle ;
1767
+ }
1768
+ }
1769
+ return ATT_MAX_PEERS + 1 ;
1770
+ }
1771
+ // Get the encryption state for a particular peer / connection handle
1772
+ uint8_t ATTClass::getPeerEncryption (uint16_t connectionHandle) {
1773
+ for (int i=0 ; i<ATT_MAX_PEERS; i++){
1774
+ if (_peers[i].connectionHandle != connectionHandle){continue ;}
1775
+ return _peers[i].encryption ;
1776
+ }
1777
+ return 0 ;
1778
+ }
1779
+ // Get the IOCapabilities for a peer
1780
+ int ATTClass::getPeerIOCap (uint16_t connectionHandle, uint8_t IOCap[3 ]) {
1781
+ for (int i=0 ; i<ATT_MAX_PEERS; i++){
1782
+ if (_peers[i].connectionHandle != connectionHandle){continue ;}
1783
+ // return _peers[i].encryption;
1784
+ memcpy (IOCap, _peers[i].IOCap , 3 );
1785
+ }
1786
+ return 0 ;
1787
+ }
1788
+ // Get the BD_ADDR for a peer
1789
+ int ATTClass::getPeerAddr (uint16_t connectionHandle, uint8_t peerAddr[])
1790
+ {
1791
+ for (int i=0 ; i<ATT_MAX_PEERS; i++)
1792
+ {
1793
+ if (_peers[i].connectionHandle != connectionHandle){continue ;}
1794
+ memcpy (peerAddr, _peers[i].address ,6 );
1795
+ return 1 ;
1796
+ }
1797
+ return 0 ;
1798
+ }
1799
+ // Get the BD_ADDR for a peer in the format needed by f6 for pairing.
1800
+ int ATTClass::getPeerAddrWithType (uint16_t connectionHandle, uint8_t peerAddr[])
1801
+ {
1802
+ for (int i=0 ; i<ATT_MAX_PEERS; i++)
1803
+ {
1804
+ if (_peers[i].connectionHandle != connectionHandle){continue ;}
1805
+ for (int k=0 ; k<6 ; k++){
1806
+ peerAddr[6 -k] = _peers[i].address [k];
1807
+ }
1808
+ if (_peers[i].addressType ){
1809
+ peerAddr[0 ] = 0x01 ;
1810
+ }else {
1811
+ peerAddr[0 ] = 0x00 ;
1812
+ }
1813
+ return 1 ;
1814
+ }
1815
+ return 0 ;
1816
+ }
1817
+
1691
1818
#if !defined(FAKE_ATT)
1692
1819
ATTClass ATTObj;
1693
1820
ATTClass& ATT = ATTObj;
1694
- #endif
1821
+ #endif
0 commit comments