![](/media/cache/profiles/profile2.jpg.50x50_q85.jpg)
This software setup a central node of a star topology network
Dependencies: MQTT target_st_bluenrg
Fork of ble-star-mbed by
source/BleSlaveService.cpp@2:1525f4848cf2, 2018-02-26 (annotated)
- Committer:
- lorevee
- Date:
- Mon Feb 26 12:29:03 2018 +0000
- Revision:
- 2:1525f4848cf2
- Parent:
- 1:110b5e896bc9
- Child:
- 3:3f35e80ed848
Ble Star release 1.0
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
lorevee | 0:1902469bdd2d | 1 | #include <BleSlaveService.h> |
lorevee | 0:1902469bdd2d | 2 | |
lorevee | 0:1902469bdd2d | 3 | |
lorevee | 0:1902469bdd2d | 4 | /* ----- Private variables ----- */ |
lorevee | 0:1902469bdd2d | 5 | /* Struct of slave dev */ |
lorevee | 0:1902469bdd2d | 6 | SlaveDevice_t slaveDev; |
lorevee | 0:1902469bdd2d | 7 | |
lorevee | 0:1902469bdd2d | 8 | |
lorevee | 0:1902469bdd2d | 9 | ChangeNotificationQueue notifyQ, *notifyP; |
lorevee | 0:1902469bdd2d | 10 | |
lorevee | 0:1902469bdd2d | 11 | |
lorevee | 0:1902469bdd2d | 12 | /* Struct of periph dev */ |
lorevee | 0:1902469bdd2d | 13 | extern PeripheralDevices_t perDevs; |
lorevee | 0:1902469bdd2d | 14 | |
lorevee | 0:1902469bdd2d | 15 | /* Notification frequency */ |
lorevee | 0:1902469bdd2d | 16 | uint8_t notification_freq = NOTIFICATION_FREQ_WIFI_OFF; |
lorevee | 0:1902469bdd2d | 17 | |
lorevee | 0:1902469bdd2d | 18 | |
lorevee | 0:1902469bdd2d | 19 | /* Star Service and Characteristic */ |
lorevee | 0:1902469bdd2d | 20 | uint8_t sUuid[16] = {0x00,0x00,0x00,0x00,0x00,0x01,0x11,0xe1,0x9a,0xb4,0x00,0x02,0xa5,0xd5,0xc5,0x1b}; |
lorevee | 0:1902469bdd2d | 21 | uint8_t dataUuid[16] = {0x00,0x08,0x00,0x00,0x00,0x01,0x11,0xe1,0xac,0x36,0x00,0x02,0xa5,0xd5,0xc5,0x1b}; |
lorevee | 0:1902469bdd2d | 22 | uint8_t confUuid[16] = {0x00,0x04,0x00,0x00,0x00,0x01,0x11,0xe1,0xac,0x36,0x00,0x02,0xa5,0xd5,0xc5,0x1b}; |
lorevee | 0:1902469bdd2d | 23 | |
lorevee | 0:1902469bdd2d | 24 | |
lorevee | 0:1902469bdd2d | 25 | /*---- Create the two characteristic ----*/ |
lorevee | 0:1902469bdd2d | 26 | /* Config char */ |
lorevee | 0:1902469bdd2d | 27 | GattCharacteristic configChar(confUuid, slaveDev.star_config_value, STAR_CHAR_MAX_VALUE_LEN, STAR_CHAR_MAX_VALUE_LEN, |
lorevee | 0:1902469bdd2d | 28 | GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_NOTIFY|GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_READ|GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_WRITE_WITHOUT_RESPONSE, |
lorevee | 0:1902469bdd2d | 29 | NULL, 0, true); |
lorevee | 0:1902469bdd2d | 30 | |
lorevee | 0:1902469bdd2d | 31 | |
lorevee | 0:1902469bdd2d | 32 | /* Data char */ |
lorevee | 0:1902469bdd2d | 33 | GattCharacteristic dataChar(dataUuid, slaveDev.notification_data.attribute_value, STAR_CHAR_MAX_VALUE_LEN, STAR_CHAR_MAX_VALUE_LEN, |
lorevee | 0:1902469bdd2d | 34 | GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_NOTIFY|GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_READ|GattCharacteristic::BLE_GATT_CHAR_PROPERTIES_WRITE_WITHOUT_RESPONSE, |
lorevee | 0:1902469bdd2d | 35 | NULL, 0, true); |
lorevee | 0:1902469bdd2d | 36 | |
lorevee | 0:1902469bdd2d | 37 | |
lorevee | 0:1902469bdd2d | 38 | /* MANUFACTURER_SPECIFIC_DATA */ |
lorevee | 0:1902469bdd2d | 39 | uint8_t manuf_data[6] = { |
lorevee | 0:1902469bdd2d | 40 | 0x01, /*SKD version */ |
lorevee | 0:1902469bdd2d | 41 | 0x81, /* NUCLEO-Board remote */ |
lorevee | 0:1902469bdd2d | 42 | 0x00, /* Led Prox+Lux */ //Unused |
lorevee | 0:1902469bdd2d | 43 | 0x0C, /* Star Config Char + Star Data Char */ //Unused |
lorevee | 0:1902469bdd2d | 44 | 0x00, /* SensorFusionShort */ //Unused |
lorevee | 0:1902469bdd2d | 45 | 0x00 /* SensorFusionFloat */ //Unused |
lorevee | 0:1902469bdd2d | 46 | }; |
lorevee | 0:1902469bdd2d | 47 | |
lorevee | 0:1902469bdd2d | 48 | |
lorevee | 0:1902469bdd2d | 49 | |
lorevee | 0:1902469bdd2d | 50 | |
lorevee | 0:1902469bdd2d | 51 | |
lorevee | 0:1902469bdd2d | 52 | /*----------------------------------------------------------------------------*/ |
lorevee | 0:1902469bdd2d | 53 | |
lorevee | 0:1902469bdd2d | 54 | |
lorevee | 0:1902469bdd2d | 55 | /* Set the device as a slave in discoverable mode */ |
lorevee | 0:1902469bdd2d | 56 | void setSlaveDiscoverable(void) { |
lorevee | 0:1902469bdd2d | 57 | //printf("\r\nsetSlaveDiscoverable\n");//DEBUG |
lorevee | 0:1902469bdd2d | 58 | BLE& ble = BLE::Instance(); |
lorevee | 0:1902469bdd2d | 59 | ble_error_t e2; |
lorevee | 0:1902469bdd2d | 60 | |
lorevee | 0:1902469bdd2d | 61 | |
lorevee | 0:1902469bdd2d | 62 | //if-MAIN - discovery/reading/writing ops completed |
lorevee | 0:1902469bdd2d | 63 | if ((discoveryCompleted == 1) /*&& (readCompleted == 1) && (writeDescriptorCompleted == 1)*/){ |
lorevee | 0:1902469bdd2d | 64 | |
lorevee | 0:1902469bdd2d | 65 | |
lorevee | 2:1525f4848cf2 | 66 | /* !! Solve advertising after master disconnection */ |
lorevee | 2:1525f4848cf2 | 67 | |
lorevee | 0:1902469bdd2d | 68 | /* Start advertisng */ |
lorevee | 0:1902469bdd2d | 69 | if ((!ble.gap().getState().advertising)){ |
lorevee | 0:1902469bdd2d | 70 | advEnds =0; |
lorevee | 0:1902469bdd2d | 71 | |
lorevee | 0:1902469bdd2d | 72 | printf("\r\nSet Discoverable Mode (%d)\n", perDevs.status); |
lorevee | 0:1902469bdd2d | 73 | e2 = ble.gap().startAdvertising(); |
lorevee | 0:1902469bdd2d | 74 | if ( e2 == BLE_ERROR_NONE ){ |
lorevee | 0:1902469bdd2d | 75 | /* Giving some time to connect */ |
lorevee | 0:1902469bdd2d | 76 | eventQ.call_in(7000, stopAdv);//N ms |
lorevee | 0:1902469bdd2d | 77 | }else{ |
lorevee | 0:1902469bdd2d | 78 | printf("\r\nError while starting advertising (err: %d - stat: %d)\n", e2, perDevs.status); |
lorevee | 0:1902469bdd2d | 79 | advEnds=1;//terminated because not started |
lorevee | 0:1902469bdd2d | 80 | } |
lorevee | 0:1902469bdd2d | 81 | |
lorevee | 0:1902469bdd2d | 82 | }//if-not-adv |
lorevee | 0:1902469bdd2d | 83 | }//if-MAIN |
lorevee | 0:1902469bdd2d | 84 | |
lorevee | 0:1902469bdd2d | 85 | |
lorevee | 0:1902469bdd2d | 86 | //Restart loop ops |
lorevee | 0:1902469bdd2d | 87 | perDevs.status = CONN_INIT; |
lorevee | 0:1902469bdd2d | 88 | perDevs.discovery_enabled = true; |
lorevee | 0:1902469bdd2d | 89 | //printf("\rstatus = CONN_INIT (%d)\n", perDevs.status);//DEBUG |
lorevee | 0:1902469bdd2d | 90 | |
lorevee | 0:1902469bdd2d | 91 | } |
lorevee | 0:1902469bdd2d | 92 | /*----------------------------------------------------------------------------*/ |
lorevee | 0:1902469bdd2d | 93 | |
lorevee | 0:1902469bdd2d | 94 | |
lorevee | 0:1902469bdd2d | 95 | |
lorevee | 0:1902469bdd2d | 96 | void stopAdv(){ |
lorevee | 0:1902469bdd2d | 97 | |
lorevee | 0:1902469bdd2d | 98 | if ((slaveDev.is_connected == false) && (discoveryCompleted == 1)){ |
lorevee | 0:1902469bdd2d | 99 | if (BLE::Instance().gap().getState().advertising){ |
lorevee | 0:1902469bdd2d | 100 | ble_error_t e = BLE::Instance().gap().stopAdvertising(); |
lorevee | 0:1902469bdd2d | 101 | if ( e != BLE_ERROR_NONE ) { |
lorevee | 0:1902469bdd2d | 102 | printf("\r\nError stopping ADV\n");//DEBUG |
lorevee | 0:1902469bdd2d | 103 | } |
lorevee | 0:1902469bdd2d | 104 | } |
lorevee | 0:1902469bdd2d | 105 | }//if |
lorevee | 0:1902469bdd2d | 106 | |
lorevee | 0:1902469bdd2d | 107 | advEnds = 1; |
lorevee | 0:1902469bdd2d | 108 | } |
lorevee | 0:1902469bdd2d | 109 | /*----------------------------------------------------------------------------*/ |
lorevee | 0:1902469bdd2d | 110 | |
lorevee | 0:1902469bdd2d | 111 | |
lorevee | 0:1902469bdd2d | 112 | |
lorevee | 0:1902469bdd2d | 113 | /** |
lorevee | 0:1902469bdd2d | 114 | * @brief This function sets some notification properties (e.g. the |
lorevee | 0:1902469bdd2d | 115 | * notification period) by sending a command according to the |
lorevee | 0:1902469bdd2d | 116 | * following format: |
lorevee | 0:1902469bdd2d | 117 | * FEATURE_MASK (4bytes) + Command (1byte) + Data (1byte) |
lorevee | 0:1902469bdd2d | 118 | * In case of the notification period the command is 255 while the allowed data are: |
lorevee | 0:1902469bdd2d | 119 | * 50 @5S, 10 @1S, 1 @100mS, 0 @50mS (default). |
lorevee | 0:1902469bdd2d | 120 | * @param connection handle |
lorevee | 0:1902469bdd2d | 121 | * @param peripheral device index |
lorevee | 0:1902469bdd2d | 122 | * @param feature mask |
lorevee | 0:1902469bdd2d | 123 | * @param command |
lorevee | 0:1902469bdd2d | 124 | * @param data |
lorevee | 0:1902469bdd2d | 125 | * @retval None |
lorevee | 0:1902469bdd2d | 126 | */ |
lorevee | 0:1902469bdd2d | 127 | void setNotificationProperty(uint16_t conn_handle, uint8_t i, uint32_t feature_mask, |
lorevee | 0:1902469bdd2d | 128 | uint8_t command, uint8_t data) { |
lorevee | 0:1902469bdd2d | 129 | //printf("\r\nsetNotificationProperty\n");//DEBUG |
lorevee | 0:1902469bdd2d | 130 | |
lorevee | 0:1902469bdd2d | 131 | uint16_t attr_handle; |
lorevee | 0:1902469bdd2d | 132 | uint8_t value_len; |
lorevee | 0:1902469bdd2d | 133 | uint8_t attr_value[6]; |
lorevee | 0:1902469bdd2d | 134 | |
lorevee | 0:1902469bdd2d | 135 | attr_handle = perDevs.cfg_char_handle[i] + 1; |
lorevee | 0:1902469bdd2d | 136 | attr_value[0] = (uint8_t)((feature_mask) >> 24); |
lorevee | 0:1902469bdd2d | 137 | attr_value[1] = (uint8_t)((feature_mask) >> 16); |
lorevee | 0:1902469bdd2d | 138 | attr_value[2] = (uint8_t)((feature_mask) >> 8); |
lorevee | 0:1902469bdd2d | 139 | attr_value[3] = (uint8_t)((feature_mask)); |
lorevee | 0:1902469bdd2d | 140 | attr_value[4] = command; |
lorevee | 0:1902469bdd2d | 141 | attr_value[5] = data; |
lorevee | 0:1902469bdd2d | 142 | value_len = 6; /* FEATURE_MASK len (4bytes) + Command len (1byte) + Data len (1byte) */ |
lorevee | 2:1525f4848cf2 | 143 | |
lorevee | 0:1902469bdd2d | 144 | /* The gatt write function above is w/out response, so we just wait for a short time before going on */ |
lorevee | 0:1902469bdd2d | 145 | writeCharacValueWithoutResp(conn_handle, attr_handle, value_len, attr_value); |
lorevee | 0:1902469bdd2d | 146 | HAL_Delay(2000);//N ms |
lorevee | 0:1902469bdd2d | 147 | } |
lorevee | 0:1902469bdd2d | 148 | /*----------------------------------------------------------------------------*/ |
lorevee | 0:1902469bdd2d | 149 | |
lorevee | 0:1902469bdd2d | 150 | |
lorevee | 0:1902469bdd2d | 151 | |
lorevee | 0:1902469bdd2d | 152 | |
lorevee | 0:1902469bdd2d | 153 | /* Forwards to master all notifications from peripherals */ |
lorevee | 0:1902469bdd2d | 154 | void notifyMaster(uint8_t data_length, uint8_t* attribute_value, uint16_t attribute_handle){ |
lorevee | 0:1902469bdd2d | 155 | //printf("\r\nnotifyMaster\n");//DEBUG |
lorevee | 0:1902469bdd2d | 156 | ble_error_t notifyError; |
lorevee | 0:1902469bdd2d | 157 | |
lorevee | 0:1902469bdd2d | 158 | |
lorevee | 0:1902469bdd2d | 159 | notifyError = BLE::Instance().gattServer().write(attribute_handle+1, attribute_value, data_length, false); |
lorevee | 0:1902469bdd2d | 160 | |
lorevee | 0:1902469bdd2d | 161 | if (notifyError != BLE_ERROR_NONE){ |
lorevee | 0:1902469bdd2d | 162 | printf("\r\n(notifyMaster) Error (%d) while updating characteristic\n", notifyError);//BLE_STACK_BUSY |
lorevee | 1:110b5e896bc9 | 163 | if (notifyError == BLE_STACK_BUSY){ |
lorevee | 1:110b5e896bc9 | 164 | stackBusy = 1; |
lorevee | 1:110b5e896bc9 | 165 | return; |
lorevee | 1:110b5e896bc9 | 166 | } |
lorevee | 1:110b5e896bc9 | 167 | }else { |
lorevee | 1:110b5e896bc9 | 168 | stackBusy = 0; |
lorevee | 1:110b5e896bc9 | 169 | return; |
lorevee | 0:1902469bdd2d | 170 | } |
lorevee | 1:110b5e896bc9 | 171 | |
lorevee | 0:1902469bdd2d | 172 | } |
lorevee | 0:1902469bdd2d | 173 | /*----------------------------------------------------------------------------*/ |
lorevee | 0:1902469bdd2d | 174 | |
lorevee | 0:1902469bdd2d | 175 | |
lorevee | 0:1902469bdd2d | 176 | /* Add all services using a vendor specific UUIDs */ |
lorevee | 0:1902469bdd2d | 177 | void addAllServices(void){ |
lorevee | 0:1902469bdd2d | 178 | |
lorevee | 0:1902469bdd2d | 179 | ble_error_t error; |
lorevee | 0:1902469bdd2d | 180 | notifyP = ¬ifyQ; |
lorevee | 0:1902469bdd2d | 181 | |
lorevee | 0:1902469bdd2d | 182 | |
lorevee | 0:1902469bdd2d | 183 | GattCharacteristic *charTable[] = {&configChar, &dataChar}; |
lorevee | 0:1902469bdd2d | 184 | |
lorevee | 0:1902469bdd2d | 185 | /*---- Create the hw service ----*/ |
lorevee | 0:1902469bdd2d | 186 | GattService starService(sUuid, charTable, sizeof(charTable) / sizeof(GattCharacteristic *)); |
lorevee | 0:1902469bdd2d | 187 | |
lorevee | 0:1902469bdd2d | 188 | /*---- Add the hw service ----*/ |
lorevee | 1:110b5e896bc9 | 189 | error = BLE::Instance().gattServer().addService(starService); |
lorevee | 0:1902469bdd2d | 190 | slaveDev.star_hw_serv_handle = starService.getHandle(); |
lorevee | 0:1902469bdd2d | 191 | slaveDev.star_config_char_handle = configChar.getValueHandle()-1; //-1 for decl handle |
lorevee | 0:1902469bdd2d | 192 | slaveDev.star_data_char_handle = dataChar.getValueHandle()-1; //-1 for decl handle |
lorevee | 0:1902469bdd2d | 193 | |
lorevee | 0:1902469bdd2d | 194 | |
lorevee | 0:1902469bdd2d | 195 | |
lorevee | 0:1902469bdd2d | 196 | if ( error != BLE_ERROR_NONE ){ |
lorevee | 0:1902469bdd2d | 197 | printf("\r\nError while creating starService(error: %d)\n", error); |
lorevee | 0:1902469bdd2d | 198 | |
lorevee | 0:1902469bdd2d | 199 | } else { |
lorevee | 0:1902469bdd2d | 200 | printf("\r\nStar HW Gatt Service added (handle 0x%004x)\n", slaveDev.star_hw_serv_handle); |
lorevee | 0:1902469bdd2d | 201 | printf("\rStar HW Config Char added (handle 0x%004x)\n", slaveDev.star_config_char_handle); |
lorevee | 0:1902469bdd2d | 202 | printf("\rStar HW Data Char added (handle 0x%004x)", slaveDev.star_data_char_handle); |
lorevee | 0:1902469bdd2d | 203 | printf("\r\n"); |
lorevee | 0:1902469bdd2d | 204 | } |
lorevee | 0:1902469bdd2d | 205 | |
lorevee | 0:1902469bdd2d | 206 | } |
lorevee | 0:1902469bdd2d | 207 | /*----------------------------------------------------------------------------*/ |
lorevee | 0:1902469bdd2d | 208 | |
lorevee | 0:1902469bdd2d | 209 | |
lorevee | 0:1902469bdd2d | 210 | /* Disable all notifications */ |
lorevee | 0:1902469bdd2d | 211 | void disableAllNotifications(void){ |
lorevee | 0:1902469bdd2d | 212 | //printf("\r\ndisableAllNotifications\n");//DEBUG |
lorevee | 0:1902469bdd2d | 213 | |
lorevee | 0:1902469bdd2d | 214 | |
lorevee | 0:1902469bdd2d | 215 | uint8_t j; |
lorevee | 0:1902469bdd2d | 216 | uint16_t attr_handle; |
lorevee | 0:1902469bdd2d | 217 | uint8_t value_len; |
lorevee | 0:1902469bdd2d | 218 | uint8_t attr_value[2]; |
lorevee | 0:1902469bdd2d | 219 | char* feat = NULL; |
lorevee | 0:1902469bdd2d | 220 | |
lorevee | 0:1902469bdd2d | 221 | for (j=0; j<(perDevs.connDevices+perDevs.discDevices); j++) { |
lorevee | 0:1902469bdd2d | 222 | |
lorevee | 0:1902469bdd2d | 223 | if ((perDevs.mic_event[j]) && (perDevs.mic_event_enabled)) { |
lorevee | 0:1902469bdd2d | 224 | feat = "MIC"; |
lorevee | 0:1902469bdd2d | 225 | perDevs.mic_event_enabled = 0; |
lorevee | 0:1902469bdd2d | 226 | perDevs.mic_event[j] = 0; |
lorevee | 0:1902469bdd2d | 227 | attr_handle = perDevs.mic_char_handle[j] + 2; |
lorevee | 0:1902469bdd2d | 228 | |
lorevee | 0:1902469bdd2d | 229 | } else if ((perDevs.prx_event[j]) && (perDevs.prx_event_enabled)) { |
lorevee | 0:1902469bdd2d | 230 | feat = "PRX"; |
lorevee | 0:1902469bdd2d | 231 | perDevs.prx_event_enabled = 0; |
lorevee | 0:1902469bdd2d | 232 | perDevs.prx_on[j] = 0; |
lorevee | 0:1902469bdd2d | 233 | attr_handle = perDevs.prx_char_handle[j] + 2; |
lorevee | 0:1902469bdd2d | 234 | |
lorevee | 0:1902469bdd2d | 235 | } else if ((perDevs.agm_event[j]) && (perDevs.agm_event_enabled)) { |
lorevee | 0:1902469bdd2d | 236 | feat = "AGM"; |
lorevee | 0:1902469bdd2d | 237 | perDevs.acc_event_enabled = 0; |
lorevee | 0:1902469bdd2d | 238 | perDevs.gyr_event_enabled = 0; |
lorevee | 0:1902469bdd2d | 239 | perDevs.mag_event_enabled = 0; |
lorevee | 0:1902469bdd2d | 240 | perDevs.agm_event_enabled = 0; |
lorevee | 0:1902469bdd2d | 241 | perDevs.agm_on[j] = 0; |
lorevee | 0:1902469bdd2d | 242 | attr_handle = perDevs.agm_char_handle[j] + 2; |
lorevee | 0:1902469bdd2d | 243 | |
lorevee | 0:1902469bdd2d | 244 | } else if ((perDevs.sfusion_event[j]) && (perDevs.sfusion_event_enabled)) { |
lorevee | 0:1902469bdd2d | 245 | feat = "SFUSION"; |
lorevee | 0:1902469bdd2d | 246 | perDevs.sfusion_event_enabled = 0; |
lorevee | 0:1902469bdd2d | 247 | perDevs.sfusion_on[j] = 0; |
lorevee | 0:1902469bdd2d | 248 | attr_handle = perDevs.sfusion_char_handle[j] + 2; |
lorevee | 0:1902469bdd2d | 249 | |
lorevee | 0:1902469bdd2d | 250 | } else { |
lorevee | 0:1902469bdd2d | 251 | continue; |
lorevee | 0:1902469bdd2d | 252 | } |
lorevee | 0:1902469bdd2d | 253 | |
lorevee | 0:1902469bdd2d | 254 | value_len = 2; |
lorevee | 0:1902469bdd2d | 255 | attr_value[0] = DISABLE; |
lorevee | 0:1902469bdd2d | 256 | |
lorevee | 0:1902469bdd2d | 257 | |
lorevee | 0:1902469bdd2d | 258 | writeDescriptorCompleted=0; |
lorevee | 0:1902469bdd2d | 259 | ble_error_t disableErr = writeCharacDescriptorWithError(perDevs.connection_handle[j], attr_handle, value_len, attr_value); |
lorevee | 0:1902469bdd2d | 260 | printf("\r\nSet OFF the %s notifications on node %d\n", feat, j); |
lorevee | 0:1902469bdd2d | 261 | |
lorevee | 0:1902469bdd2d | 262 | if (disableErr != BLE_ERROR_NONE){ |
lorevee | 1:110b5e896bc9 | 263 | printf("\r\n(disableAllNotifications) Write charac descriptor failed (err: %d, stat: %d)\n", disableErr, perDevs.status); |
lorevee | 0:1902469bdd2d | 264 | writeDescriptorCompleted=1; |
lorevee | 0:1902469bdd2d | 265 | }//if-error |
lorevee | 0:1902469bdd2d | 266 | }//for |
lorevee | 0:1902469bdd2d | 267 | } |
lorevee | 0:1902469bdd2d | 268 | /*----------------------------------------------------------------------------*/ |
lorevee | 0:1902469bdd2d | 269 | |
lorevee | 0:1902469bdd2d | 270 | |
lorevee | 0:1902469bdd2d | 271 | |
lorevee | 0:1902469bdd2d | 272 | /* This function enables or disables the new peripheral scanning */ |
lorevee | 0:1902469bdd2d | 273 | void setNewNodesScanning(uint8_t enabled){ |
lorevee | 0:1902469bdd2d | 274 | |
lorevee | 0:1902469bdd2d | 275 | STORE_LE_16(slaveDev.star_config_value,(HAL_GetTick()>>3)); /* Timestamp */ |
lorevee | 0:1902469bdd2d | 276 | |
lorevee | 0:1902469bdd2d | 277 | switch (enabled) { |
lorevee | 0:1902469bdd2d | 278 | case 0x01: |
lorevee | 0:1902469bdd2d | 279 | perDevs.discovery_enabled = true; |
lorevee | 0:1902469bdd2d | 280 | //printf("\r\nScanning enabled (%d)\n", enabled); |
lorevee | 0:1902469bdd2d | 281 | break; |
lorevee | 0:1902469bdd2d | 282 | |
lorevee | 0:1902469bdd2d | 283 | case 0x02: |
lorevee | 0:1902469bdd2d | 284 | perDevs.discovery_enabled = false; |
lorevee | 0:1902469bdd2d | 285 | //printf("\r\nScanning disabled (%d)\n", enabled); |
lorevee | 0:1902469bdd2d | 286 | break; |
lorevee | 0:1902469bdd2d | 287 | |
lorevee | 0:1902469bdd2d | 288 | default: |
lorevee | 0:1902469bdd2d | 289 | //printf("\r\nScanning set to unrecognized value (%d)\n", enabled); |
lorevee | 0:1902469bdd2d | 290 | break; |
lorevee | 0:1902469bdd2d | 291 | } |
lorevee | 0:1902469bdd2d | 292 | |
lorevee | 0:1902469bdd2d | 293 | slaveDev.star_config_value[2] = enabled; |
lorevee | 0:1902469bdd2d | 294 | slaveDev.star_config_value_len = 3; |
lorevee | 0:1902469bdd2d | 295 | //HAL_Delay(300); |
lorevee | 0:1902469bdd2d | 296 | |
lorevee | 0:1902469bdd2d | 297 | /* Notify master for scanning */ |
lorevee | 0:1902469bdd2d | 298 | |
lorevee | 2:1525f4848cf2 | 299 | /* Check the scan enable/disable */ |
lorevee | 0:1902469bdd2d | 300 | // notifyMaster(slaveDev.star_config_value_len, slaveDev.star_config_value, |
lorevee | 0:1902469bdd2d | 301 | // slaveDev.star_config_char_handle); |
lorevee | 0:1902469bdd2d | 302 | |
lorevee | 0:1902469bdd2d | 303 | } |
lorevee | 0:1902469bdd2d | 304 | /*----------------------------------------------------------------------------*/ |
lorevee | 0:1902469bdd2d | 305 | |
lorevee | 0:1902469bdd2d | 306 | |
lorevee | 0:1902469bdd2d | 307 | //NOT USED FOR NOW !! |
lorevee | 0:1902469bdd2d | 308 | /* This function forwards to the peripheral device the command coming from the Cloud */ |
lorevee | 0:1902469bdd2d | 309 | void Forward_Command_To_BlueNRG(uint8_t* data_ptr, uint8_t data_length){ |
lorevee | 0:1902469bdd2d | 310 | |
lorevee | 0:1902469bdd2d | 311 | uint16_t handle; |
lorevee | 0:1902469bdd2d | 312 | uint8_t buffer[4] = {0, 0, 0, 0}; |
lorevee | 0:1902469bdd2d | 313 | uint8_t num, even, odd; |
lorevee | 0:1902469bdd2d | 314 | uint8_t i; |
lorevee | 0:1902469bdd2d | 315 | uint8_t cmd_type; |
lorevee | 0:1902469bdd2d | 316 | |
lorevee | 0:1902469bdd2d | 317 | cmd_type = (data_ptr[0] - '0') << 4 | (data_ptr[1] - '0'); |
lorevee | 0:1902469bdd2d | 318 | //printf("\r\ncommand %d\n", cmd_type); |
lorevee | 0:1902469bdd2d | 319 | |
lorevee | 0:1902469bdd2d | 320 | switch (cmd_type) |
lorevee | 0:1902469bdd2d | 321 | { |
lorevee | 0:1902469bdd2d | 322 | case 0: |
lorevee | 0:1902469bdd2d | 323 | printf("\rScan cmd type (%d)\n", cmd_type); |
lorevee | 0:1902469bdd2d | 324 | handle = slaveDev.star_config_char_handle + 1; |
lorevee | 0:1902469bdd2d | 325 | break; |
lorevee | 0:1902469bdd2d | 326 | case 1: |
lorevee | 0:1902469bdd2d | 327 | printf("\rLED/MIC/PRX cmd type (%d)\n", cmd_type); |
lorevee | 0:1902469bdd2d | 328 | handle = slaveDev.star_data_char_handle + 1; |
lorevee | 0:1902469bdd2d | 329 | break; |
lorevee | 0:1902469bdd2d | 330 | default: |
lorevee | 0:1902469bdd2d | 331 | printf("\rUnknown cmd type (%d)\n", cmd_type); |
lorevee | 0:1902469bdd2d | 332 | return; |
lorevee | 0:1902469bdd2d | 333 | //break; |
lorevee | 0:1902469bdd2d | 334 | } |
lorevee | 0:1902469bdd2d | 335 | |
lorevee | 0:1902469bdd2d | 336 | /** |
lorevee | 0:1902469bdd2d | 337 | * For Scan cmd type: |
lorevee | 0:1902469bdd2d | 338 | * |Value | |
lorevee | 0:1902469bdd2d | 339 | * |1 byte | |
lorevee | 0:1902469bdd2d | 340 | * For LED/MIC/PRX cmd type: |
lorevee | 0:1902469bdd2d | 341 | * |Node ID | Type ID | Value | |
lorevee | 0:1902469bdd2d | 342 | * |2 bytes | 1 byte | x bytes | |
lorevee | 0:1902469bdd2d | 343 | */ |
lorevee | 0:1902469bdd2d | 344 | for (i=2; i<data_length; i++) { |
lorevee | 0:1902469bdd2d | 345 | switch (data_ptr[i]) |
lorevee | 0:1902469bdd2d | 346 | { |
lorevee | 0:1902469bdd2d | 347 | case 'A': |
lorevee | 0:1902469bdd2d | 348 | case 'a': |
lorevee | 0:1902469bdd2d | 349 | num = 10; |
lorevee | 0:1902469bdd2d | 350 | break; |
lorevee | 0:1902469bdd2d | 351 | case 'B': |
lorevee | 0:1902469bdd2d | 352 | case 'b': |
lorevee | 0:1902469bdd2d | 353 | num = 11; |
lorevee | 0:1902469bdd2d | 354 | break; |
lorevee | 0:1902469bdd2d | 355 | case 'C': |
lorevee | 0:1902469bdd2d | 356 | case 'c': |
lorevee | 0:1902469bdd2d | 357 | num = 12; |
lorevee | 0:1902469bdd2d | 358 | break; |
lorevee | 0:1902469bdd2d | 359 | case 'D': |
lorevee | 0:1902469bdd2d | 360 | case 'd': |
lorevee | 0:1902469bdd2d | 361 | num = 13; |
lorevee | 0:1902469bdd2d | 362 | break; |
lorevee | 0:1902469bdd2d | 363 | case 'E': |
lorevee | 0:1902469bdd2d | 364 | case 'e': |
lorevee | 0:1902469bdd2d | 365 | num = 14; |
lorevee | 0:1902469bdd2d | 366 | break; |
lorevee | 0:1902469bdd2d | 367 | case 'F': |
lorevee | 0:1902469bdd2d | 368 | case 'f': |
lorevee | 0:1902469bdd2d | 369 | num = 15; |
lorevee | 0:1902469bdd2d | 370 | break; |
lorevee | 0:1902469bdd2d | 371 | default: |
lorevee | 0:1902469bdd2d | 372 | num = data_ptr[i] - '0'; |
lorevee | 0:1902469bdd2d | 373 | break; |
lorevee | 0:1902469bdd2d | 374 | } |
lorevee | 0:1902469bdd2d | 375 | if (!(i%2)) { |
lorevee | 0:1902469bdd2d | 376 | even = num << 4; |
lorevee | 0:1902469bdd2d | 377 | } |
lorevee | 0:1902469bdd2d | 378 | else { |
lorevee | 0:1902469bdd2d | 379 | odd = num; |
lorevee | 0:1902469bdd2d | 380 | buffer[(i-2)/2] = even | odd; |
lorevee | 0:1902469bdd2d | 381 | } |
lorevee | 0:1902469bdd2d | 382 | } |
lorevee | 0:1902469bdd2d | 383 | |
lorevee | 0:1902469bdd2d | 384 | createAttribute_Modified_CB_Prototype(handle, (data_length-2)/2, buffer); |
lorevee | 0:1902469bdd2d | 385 | } |
lorevee | 0:1902469bdd2d | 386 | /*----------------------------------------------------------------------------*/ |
lorevee | 0:1902469bdd2d | 387 | |
lorevee | 0:1902469bdd2d | 388 | |
lorevee | 0:1902469bdd2d | 389 | /* Function used to call AttributeModified_CB outside the callback call */ |
lorevee | 0:1902469bdd2d | 390 | void createAttribute_Modified_CB_Prototype(uint16_t handle, uint8_t data_length, uint8_t *att_data){ |
lorevee | 0:1902469bdd2d | 391 | |
lorevee | 0:1902469bdd2d | 392 | GattWriteCallbackParams paramStruct, *pointerToParam; |
lorevee | 0:1902469bdd2d | 393 | pointerToParam = ¶mStruct; |
lorevee | 0:1902469bdd2d | 394 | |
lorevee | 0:1902469bdd2d | 395 | pointerToParam->handle = handle; |
lorevee | 0:1902469bdd2d | 396 | pointerToParam->len = data_length; |
lorevee | 0:1902469bdd2d | 397 | pointerToParam->data = att_data; |
lorevee | 0:1902469bdd2d | 398 | |
lorevee | 0:1902469bdd2d | 399 | AttributeModified_CB(pointerToParam); |
lorevee | 0:1902469bdd2d | 400 | } |
lorevee | 0:1902469bdd2d | 401 | /*----------------------------------------------------------------------------*/ |
lorevee | 0:1902469bdd2d | 402 | |
lorevee | 0:1902469bdd2d | 403 | |
lorevee | 0:1902469bdd2d | 404 | |
lorevee | 0:1902469bdd2d | 405 | |
lorevee | 0:1902469bdd2d | 406 | /* This function is called when a local attribute gets modified */ |
lorevee | 0:1902469bdd2d | 407 | void AttributeModified_CB(const GattWriteCallbackParams* param){ |
lorevee | 0:1902469bdd2d | 408 | // printf("\r\nAttributeModified_CB (%d)\n", perDevs.status);//DEBUG |
lorevee | 0:1902469bdd2d | 409 | |
lorevee | 0:1902469bdd2d | 410 | |
lorevee | 0:1902469bdd2d | 411 | /* Assign prototype vars */ |
lorevee | 0:1902469bdd2d | 412 | uint16_t handle = param->handle; |
lorevee | 0:1902469bdd2d | 413 | //uint8_t data_length = param->len; //not used |
lorevee | 0:1902469bdd2d | 414 | uint8_t *att_data = (uint8_t *)param->data; |
lorevee | 0:1902469bdd2d | 415 | |
lorevee | 0:1902469bdd2d | 416 | |
lorevee | 0:1902469bdd2d | 417 | uint8_t i; |
lorevee | 0:1902469bdd2d | 418 | uint16_t conn_handle; |
lorevee | 0:1902469bdd2d | 419 | uint16_t attr_handle; |
lorevee | 0:1902469bdd2d | 420 | uint8_t value_len; |
lorevee | 0:1902469bdd2d | 421 | uint8_t attr_value[6]; |
lorevee | 0:1902469bdd2d | 422 | char* mems; |
lorevee | 0:1902469bdd2d | 423 | |
lorevee | 0:1902469bdd2d | 424 | if (handle == slaveDev.star_config_char_handle + 1) { |
lorevee | 0:1902469bdd2d | 425 | |
lorevee | 0:1902469bdd2d | 426 | perDevs.status = ALL_DATA_READ; |
lorevee | 0:1902469bdd2d | 427 | if (att_data[0]==0x01) { |
lorevee | 0:1902469bdd2d | 428 | /* Disabling all previously enabled notifications */ |
lorevee | 0:1902469bdd2d | 429 | disableAllNotifications(); |
lorevee | 0:1902469bdd2d | 430 | }//if |
lorevee | 0:1902469bdd2d | 431 | setNewNodesScanning(att_data[0]); |
lorevee | 0:1902469bdd2d | 432 | |
lorevee | 0:1902469bdd2d | 433 | |
lorevee | 0:1902469bdd2d | 434 | } else if (handle == slaveDev.star_config_char_handle + 2) { |
lorevee | 0:1902469bdd2d | 435 | if (att_data[0]==0x01) { |
lorevee | 0:1902469bdd2d | 436 | //printf("\r\nEnable scanning notification\n"); |
lorevee | 0:1902469bdd2d | 437 | STORE_LE_16(slaveDev.star_config_value,(HAL_GetTick()>>3)); /* Timestamp */ |
lorevee | 0:1902469bdd2d | 438 | slaveDev.star_config_value[2] = perDevs.discovery_enabled; |
lorevee | 0:1902469bdd2d | 439 | slaveDev.star_config_value_len = 3; |
lorevee | 0:1902469bdd2d | 440 | |
lorevee | 0:1902469bdd2d | 441 | /* send the status of the scanning when notifications are enabled */ |
lorevee | 0:1902469bdd2d | 442 | notifyMaster(slaveDev.star_config_value_len, slaveDev.star_config_value, |
lorevee | 0:1902469bdd2d | 443 | slaveDev.star_config_char_handle); |
lorevee | 0:1902469bdd2d | 444 | |
lorevee | 0:1902469bdd2d | 445 | /* enable here the data notifications since sometimes the relative command gets lost (FIXME) */ |
lorevee | 0:1902469bdd2d | 446 | //printf("\r\nEnable data notification (0)\n"); |
lorevee | 0:1902469bdd2d | 447 | slaveDev.star_data_char_notify = 1; |
lorevee | 0:1902469bdd2d | 448 | |
lorevee | 0:1902469bdd2d | 449 | } else if (att_data[0]==0x00) { |
lorevee | 0:1902469bdd2d | 450 | //printf("\r\nDisable scanning notification\n"); |
lorevee | 0:1902469bdd2d | 451 | } |
lorevee | 0:1902469bdd2d | 452 | |
lorevee | 0:1902469bdd2d | 453 | } else if (handle == slaveDev.star_data_char_handle + 2) { |
lorevee | 0:1902469bdd2d | 454 | if (att_data[0]==0x01) { |
lorevee | 0:1902469bdd2d | 455 | //printf("\r\nEnable data notification (1)\n"); |
lorevee | 0:1902469bdd2d | 456 | slaveDev.star_data_char_notify = 1; |
lorevee | 0:1902469bdd2d | 457 | |
lorevee | 0:1902469bdd2d | 458 | |
lorevee | 0:1902469bdd2d | 459 | } else if (att_data[0]==0x00) { |
lorevee | 0:1902469bdd2d | 460 | //printf("\r\nDisable data notification\n"); |
lorevee | 0:1902469bdd2d | 461 | slaveDev.star_data_char_notify = 0; |
lorevee | 0:1902469bdd2d | 462 | |
lorevee | 0:1902469bdd2d | 463 | } |
lorevee | 0:1902469bdd2d | 464 | |
lorevee | 0:1902469bdd2d | 465 | } else if (handle == slaveDev.star_data_char_handle + 1) { |
lorevee | 0:1902469bdd2d | 466 | |
lorevee | 0:1902469bdd2d | 467 | /* |
lorevee | 0:1902469bdd2d | 468 | * Forward the command to the proper peripheral node. |
lorevee | 0:1902469bdd2d | 469 | * It can be: |
lorevee | 0:1902469bdd2d | 470 | * - the ON/OFF of a LED |
lorevee | 0:1902469bdd2d | 471 | * - the notification enabling/disabling for a MIC Level or a Proximity Sensor |
lorevee | 0:1902469bdd2d | 472 | * The coming data are received according to the following format: |
lorevee | 0:1902469bdd2d | 473 | * |Node ID | Type ID | value | |
lorevee | 0:1902469bdd2d | 474 | * |2 bytes | 1 byte | x bytes | |
lorevee | 0:1902469bdd2d | 475 | */ |
lorevee | 0:1902469bdd2d | 476 | |
lorevee | 0:1902469bdd2d | 477 | i = Get_Device_Index_From_Addr(att_data); |
lorevee | 0:1902469bdd2d | 478 | if ((i < MAX_NUM_OF_NODES) && (!perDevs.is_disconnected[i]) && (perDevs.cfg_char_handle[i] != 0)) { |
lorevee | 0:1902469bdd2d | 479 | conn_handle = perDevs.connection_handle[i]; |
lorevee | 0:1902469bdd2d | 480 | |
lorevee | 0:1902469bdd2d | 481 | switch (att_data[2]) { |
lorevee | 0:1902469bdd2d | 482 | |
lorevee | 0:1902469bdd2d | 483 | |
lorevee | 0:1902469bdd2d | 484 | //LED_TYPE_ID |
lorevee | 0:1902469bdd2d | 485 | case LED_TYPE_ID: |
lorevee | 0:1902469bdd2d | 486 | attr_handle = perDevs.cfg_char_handle[i] + 1; |
lorevee | 0:1902469bdd2d | 487 | value_len = 5; /* 4 bytes for the feature mask + 1 byte for the command (0=ON, 1=OFF) */ |
lorevee | 0:1902469bdd2d | 488 | attr_value[0] = (uint8_t)(((uint32_t)FEATURE_MASK_LED_EVENTS) >> 24); |
lorevee | 0:1902469bdd2d | 489 | attr_value[1] = (uint8_t)(((uint32_t)FEATURE_MASK_LED_EVENTS) >> 16); |
lorevee | 0:1902469bdd2d | 490 | attr_value[2] = (uint8_t)(((uint32_t)FEATURE_MASK_LED_EVENTS) >> 8); |
lorevee | 0:1902469bdd2d | 491 | attr_value[3] = (uint8_t)(((uint32_t)FEATURE_MASK_LED_EVENTS)); |
lorevee | 0:1902469bdd2d | 492 | attr_value[4] = att_data[3]; |
lorevee | 0:1902469bdd2d | 493 | |
lorevee | 0:1902469bdd2d | 494 | writeCharacValueWithoutResp(conn_handle, attr_handle, value_len, attr_value); |
lorevee | 0:1902469bdd2d | 495 | |
lorevee | 0:1902469bdd2d | 496 | perDevs.readDeviceIdx = i; |
lorevee | 0:1902469bdd2d | 497 | break; |
lorevee | 0:1902469bdd2d | 498 | |
lorevee | 0:1902469bdd2d | 499 | |
lorevee | 0:1902469bdd2d | 500 | |
lorevee | 0:1902469bdd2d | 501 | //MICLEVEL_TYPE_ID |
lorevee | 0:1902469bdd2d | 502 | case MICLEVEL_TYPE_ID: |
lorevee | 0:1902469bdd2d | 503 | |
lorevee | 0:1902469bdd2d | 504 | if (readCompleted == 0){ |
lorevee | 0:1902469bdd2d | 505 | notificationPending = 1; |
lorevee | 0:1902469bdd2d | 506 | |
lorevee | 0:1902469bdd2d | 507 | /* Fill the temp struct */ |
lorevee | 0:1902469bdd2d | 508 | notifyP->att_data = att_data; |
lorevee | 0:1902469bdd2d | 509 | notifyP->attr_value = attr_value; |
lorevee | 0:1902469bdd2d | 510 | notifyP->conn_handle = conn_handle; |
lorevee | 0:1902469bdd2d | 511 | notifyP->i = i; |
lorevee | 0:1902469bdd2d | 512 | notifyP->feature_mask = FEATURE_MASK_MIC; |
lorevee | 0:1902469bdd2d | 513 | notifyP->frequency = notification_freq; |
lorevee | 0:1902469bdd2d | 514 | |
lorevee | 0:1902469bdd2d | 515 | /* Then, call the Change_Notification_Status from the readCallback with these params */ |
lorevee | 0:1902469bdd2d | 516 | |
lorevee | 0:1902469bdd2d | 517 | }else if (readCompleted == 1) { |
lorevee | 1:110b5e896bc9 | 518 | //notificationPending = 0; |
lorevee | 0:1902469bdd2d | 519 | Change_Notification_Status(att_data, attr_value, conn_handle, i, FEATURE_MASK_MIC, notification_freq); |
lorevee | 0:1902469bdd2d | 520 | } |
lorevee | 0:1902469bdd2d | 521 | perDevs.prx_on[i] = attr_value[0]; |
lorevee | 0:1902469bdd2d | 522 | printf("\r\nMIC notifications [%d] %s (status %d, discovery %d)\n", i, (attr_value[0]==1 ? "ON" : "OFF"), perDevs.status, perDevs.discovery_enabled); |
lorevee | 0:1902469bdd2d | 523 | |
lorevee | 0:1902469bdd2d | 524 | #if SCAN_AFTER_NOTIFICATION |
lorevee | 0:1902469bdd2d | 525 | /* Restart peripheral discovery and notification*/ |
lorevee | 0:1902469bdd2d | 526 | if (attr_value[0]!=1){ |
lorevee | 0:1902469bdd2d | 527 | perDevs.discovery_enabled = 1; |
lorevee | 0:1902469bdd2d | 528 | setNewNodesScanning(0x01); |
lorevee | 0:1902469bdd2d | 529 | //HAL_Delay(300); |
lorevee | 0:1902469bdd2d | 530 | } |
lorevee | 0:1902469bdd2d | 531 | #endif |
lorevee | 0:1902469bdd2d | 532 | break; |
lorevee | 0:1902469bdd2d | 533 | |
lorevee | 0:1902469bdd2d | 534 | |
lorevee | 0:1902469bdd2d | 535 | |
lorevee | 0:1902469bdd2d | 536 | |
lorevee | 0:1902469bdd2d | 537 | |
lorevee | 0:1902469bdd2d | 538 | //PRX_TYPE_ID |
lorevee | 0:1902469bdd2d | 539 | case PRX_TYPE_ID: |
lorevee | 0:1902469bdd2d | 540 | |
lorevee | 0:1902469bdd2d | 541 | if (readCompleted == 0){ |
lorevee | 0:1902469bdd2d | 542 | notificationPending = 1; |
lorevee | 0:1902469bdd2d | 543 | |
lorevee | 0:1902469bdd2d | 544 | /* Fill the temp struct */ |
lorevee | 0:1902469bdd2d | 545 | notifyP->att_data = att_data; |
lorevee | 0:1902469bdd2d | 546 | notifyP->attr_value = attr_value; |
lorevee | 0:1902469bdd2d | 547 | notifyP->conn_handle = conn_handle; |
lorevee | 0:1902469bdd2d | 548 | notifyP->i = i; |
lorevee | 0:1902469bdd2d | 549 | notifyP->feature_mask = FEATURE_MASK_PROX; |
lorevee | 1:110b5e896bc9 | 550 | notifyP->frequency = notification_freq*SENDING_INTERVAL_100MS_MULTIPLE; |
lorevee | 0:1902469bdd2d | 551 | |
lorevee | 0:1902469bdd2d | 552 | /* Then, call the Change_Notification_Status from the readCallback with these params */ |
lorevee | 0:1902469bdd2d | 553 | |
lorevee | 0:1902469bdd2d | 554 | }else if (readCompleted == 1) { |
lorevee | 1:110b5e896bc9 | 555 | //notificationPending = 0; |
lorevee | 1:110b5e896bc9 | 556 | Change_Notification_Status(att_data, attr_value, conn_handle, i, FEATURE_MASK_PROX, notification_freq*SENDING_INTERVAL_100MS_MULTIPLE); |
lorevee | 0:1902469bdd2d | 557 | } |
lorevee | 0:1902469bdd2d | 558 | perDevs.prx_on[i] = attr_value[0]; |
lorevee | 0:1902469bdd2d | 559 | printf("\r\nPRX notifications [%d] %s (status %d)\n", i, (attr_value[0]==1 ? "ON" : "OFF"), perDevs.status); |
lorevee | 0:1902469bdd2d | 560 | |
lorevee | 0:1902469bdd2d | 561 | #if SCAN_AFTER_NOTIFICATION |
lorevee | 0:1902469bdd2d | 562 | /* Restart peripheral discovery and notification*/ |
lorevee | 0:1902469bdd2d | 563 | if (attr_value[0]!=1){ |
lorevee | 0:1902469bdd2d | 564 | perDevs.discovery_enabled = 1; |
lorevee | 0:1902469bdd2d | 565 | setNewNodesScanning(0x01); |
lorevee | 0:1902469bdd2d | 566 | //HAL_Delay(300); |
lorevee | 0:1902469bdd2d | 567 | } |
lorevee | 0:1902469bdd2d | 568 | #endif |
lorevee | 0:1902469bdd2d | 569 | break; |
lorevee | 0:1902469bdd2d | 570 | |
lorevee | 0:1902469bdd2d | 571 | |
lorevee | 0:1902469bdd2d | 572 | |
lorevee | 0:1902469bdd2d | 573 | //ACC_TYPE_ID |
lorevee | 0:1902469bdd2d | 574 | //GYR_TYPE_ID |
lorevee | 0:1902469bdd2d | 575 | //MAG_TYPE_ID |
lorevee | 0:1902469bdd2d | 576 | case ACC_TYPE_ID: |
lorevee | 0:1902469bdd2d | 577 | case GYR_TYPE_ID: |
lorevee | 0:1902469bdd2d | 578 | case MAG_TYPE_ID: |
lorevee | 0:1902469bdd2d | 579 | |
lorevee | 0:1902469bdd2d | 580 | if (readCompleted == 0){ |
lorevee | 0:1902469bdd2d | 581 | notificationPending = 1; |
lorevee | 0:1902469bdd2d | 582 | |
lorevee | 0:1902469bdd2d | 583 | /* Fill the temp struct */ |
lorevee | 0:1902469bdd2d | 584 | notifyP->att_data = att_data; |
lorevee | 0:1902469bdd2d | 585 | notifyP->attr_value = attr_value; |
lorevee | 0:1902469bdd2d | 586 | notifyP->conn_handle = conn_handle; |
lorevee | 0:1902469bdd2d | 587 | notifyP->i = i; |
lorevee | 0:1902469bdd2d | 588 | notifyP->feature_mask = FEATURE_MASK_ACC; |
lorevee | 2:1525f4848cf2 | 589 | notifyP->frequency = notification_freq*SENDING_INTERVAL_100MS_MULTIPLE; |
lorevee | 0:1902469bdd2d | 590 | |
lorevee | 0:1902469bdd2d | 591 | |
lorevee | 0:1902469bdd2d | 592 | /* Then, call the Change_Notification_Status from the readCallback with these params */ |
lorevee | 0:1902469bdd2d | 593 | |
lorevee | 0:1902469bdd2d | 594 | }else if (readCompleted == 1) { |
lorevee | 1:110b5e896bc9 | 595 | //notificationPending = 0; |
lorevee | 2:1525f4848cf2 | 596 | Change_Notification_Status(att_data, attr_value, conn_handle, i, FEATURE_MASK_ACC, notification_freq*SENDING_INTERVAL_100MS_MULTIPLE); |
lorevee | 0:1902469bdd2d | 597 | } |
lorevee | 0:1902469bdd2d | 598 | perDevs.agm_on[i] = attr_value[0]; |
lorevee | 0:1902469bdd2d | 599 | |
lorevee | 0:1902469bdd2d | 600 | if (att_data[2] == 0x09) { |
lorevee | 0:1902469bdd2d | 601 | perDevs.acc_event_enabled = attr_value[0]; |
lorevee | 0:1902469bdd2d | 602 | mems = "ACC"; |
lorevee | 0:1902469bdd2d | 603 | |
lorevee | 0:1902469bdd2d | 604 | } else if (att_data[2] == 0x0A) { |
lorevee | 0:1902469bdd2d | 605 | perDevs.gyr_event_enabled = attr_value[0]; |
lorevee | 0:1902469bdd2d | 606 | mems = "GYR"; |
lorevee | 0:1902469bdd2d | 607 | |
lorevee | 0:1902469bdd2d | 608 | } else if (att_data[2] == 0x0B) { |
lorevee | 0:1902469bdd2d | 609 | perDevs.mag_event_enabled = attr_value[0]; |
lorevee | 0:1902469bdd2d | 610 | mems = "MAG"; |
lorevee | 0:1902469bdd2d | 611 | } |
lorevee | 0:1902469bdd2d | 612 | |
lorevee | 0:1902469bdd2d | 613 | printf("\r\nAGM notifications [%d] %s (%s) (status %d)\n", i, (attr_value[0]==1 ? "ON" : "OFF"), mems, perDevs.status); |
lorevee | 0:1902469bdd2d | 614 | #if SCAN_AFTER_NOTIFICATION |
lorevee | 0:1902469bdd2d | 615 | /* Restart peripheral discovery and notification*/ |
lorevee | 0:1902469bdd2d | 616 | if (attr_value[0]!=1){ |
lorevee | 0:1902469bdd2d | 617 | perDevs.discovery_enabled = 1; |
lorevee | 0:1902469bdd2d | 618 | setNewNodesScanning(0x01); |
lorevee | 0:1902469bdd2d | 619 | //HAL_Delay(300); |
lorevee | 0:1902469bdd2d | 620 | } |
lorevee | 0:1902469bdd2d | 621 | #endif |
lorevee | 0:1902469bdd2d | 622 | break; |
lorevee | 0:1902469bdd2d | 623 | |
lorevee | 0:1902469bdd2d | 624 | |
lorevee | 0:1902469bdd2d | 625 | |
lorevee | 0:1902469bdd2d | 626 | //SFUSION_TYPE_ID |
lorevee | 0:1902469bdd2d | 627 | case SFUSION_TYPE_ID: |
lorevee | 0:1902469bdd2d | 628 | |
lorevee | 0:1902469bdd2d | 629 | if (readCompleted == 0){ |
lorevee | 0:1902469bdd2d | 630 | notificationPending = 1; |
lorevee | 0:1902469bdd2d | 631 | |
lorevee | 0:1902469bdd2d | 632 | /* Fill the temp struct */ |
lorevee | 0:1902469bdd2d | 633 | notifyP->att_data = att_data; |
lorevee | 0:1902469bdd2d | 634 | notifyP->attr_value = attr_value; |
lorevee | 0:1902469bdd2d | 635 | notifyP->conn_handle = conn_handle; |
lorevee | 0:1902469bdd2d | 636 | notifyP->i = i; |
lorevee | 0:1902469bdd2d | 637 | notifyP->feature_mask = FEATURE_MASK_SENSORFUSION; |
lorevee | 2:1525f4848cf2 | 638 | notifyP->frequency = notification_freq*SENDING_INTERVAL_100MS_MULTIPLE; |
lorevee | 0:1902469bdd2d | 639 | |
lorevee | 0:1902469bdd2d | 640 | /* Then, call the Change_Notification_Status from the readCallback with these params */ |
lorevee | 0:1902469bdd2d | 641 | |
lorevee | 0:1902469bdd2d | 642 | }else if (readCompleted == 1) { |
lorevee | 1:110b5e896bc9 | 643 | //notificationPending = 0; |
lorevee | 2:1525f4848cf2 | 644 | Change_Notification_Status(att_data, attr_value, conn_handle, i, FEATURE_MASK_SENSORFUSION, notification_freq*SENDING_INTERVAL_100MS_MULTIPLE); |
lorevee | 0:1902469bdd2d | 645 | } |
lorevee | 0:1902469bdd2d | 646 | |
lorevee | 0:1902469bdd2d | 647 | perDevs.sfusion_on[i] = attr_value[0]; |
lorevee | 0:1902469bdd2d | 648 | printf("\r\nSFUSION notifications [%d] %s (status %d)\n", i, (attr_value[0]==1 ? "ON" : "OFF"), perDevs.status); |
lorevee | 0:1902469bdd2d | 649 | |
lorevee | 0:1902469bdd2d | 650 | #if SCAN_AFTER_NOTIFICATION |
lorevee | 0:1902469bdd2d | 651 | /* Restart peripheral discovery and notification*/ |
lorevee | 0:1902469bdd2d | 652 | if (attr_value[0]!=1){ |
lorevee | 0:1902469bdd2d | 653 | perDevs.discovery_enabled = 1; |
lorevee | 0:1902469bdd2d | 654 | setNewNodesScanning(0x01); |
lorevee | 0:1902469bdd2d | 655 | //HAL_Delay(300); |
lorevee | 0:1902469bdd2d | 656 | |
lorevee | 0:1902469bdd2d | 657 | } |
lorevee | 0:1902469bdd2d | 658 | #endif |
lorevee | 0:1902469bdd2d | 659 | break; |
lorevee | 0:1902469bdd2d | 660 | } |
lorevee | 0:1902469bdd2d | 661 | }//if |
lorevee | 0:1902469bdd2d | 662 | }//if-main |
lorevee | 0:1902469bdd2d | 663 | |
lorevee | 0:1902469bdd2d | 664 | |
lorevee | 0:1902469bdd2d | 665 | } |
lorevee | 0:1902469bdd2d | 666 | /*----------------------------------------------------------------------------*/ |
lorevee | 0:1902469bdd2d | 667 | |
lorevee | 0:1902469bdd2d | 668 | |
lorevee | 0:1902469bdd2d | 669 | |
lorevee | 0:1902469bdd2d | 670 | |
lorevee | 0:1902469bdd2d | 671 | /* Retrieve the device index from the peripheral device address */ |
lorevee | 0:1902469bdd2d | 672 | uint8_t Get_Device_Index_From_Addr(uint8_t *addr){ |
lorevee | 0:1902469bdd2d | 673 | |
lorevee | 0:1902469bdd2d | 674 | uint8_t i; |
lorevee | 0:1902469bdd2d | 675 | |
lorevee | 0:1902469bdd2d | 676 | for (i=0; i<MAX_NUM_OF_NODES; i++) { |
lorevee | 0:1902469bdd2d | 677 | |
lorevee | 0:1902469bdd2d | 678 | if ((perDevs.devInfo[i].bdaddr[NODE_ID_B2] == addr[0]) && (perDevs.devInfo[i].bdaddr[NODE_ID_B1] == addr[1])) { |
lorevee | 0:1902469bdd2d | 679 | return i; |
lorevee | 0:1902469bdd2d | 680 | } |
lorevee | 0:1902469bdd2d | 681 | } |
lorevee | 0:1902469bdd2d | 682 | return MAX_NUM_OF_NODES; |
lorevee | 0:1902469bdd2d | 683 | } |
lorevee | 0:1902469bdd2d | 684 | /*----------------------------------------------------------------------------*/ |
lorevee | 0:1902469bdd2d | 685 | |
lorevee | 0:1902469bdd2d | 686 | |
lorevee | 0:1902469bdd2d | 687 | |
lorevee | 0:1902469bdd2d | 688 | |
lorevee | 0:1902469bdd2d | 689 | /** |
lorevee | 0:1902469bdd2d | 690 | * @brief This function is called to Enable/Disable MIC/PRX/AGM/SFusion notifications |
lorevee | 0:1902469bdd2d | 691 | * @param att_data : pointer to the modified attribute data |
lorevee | 0:1902469bdd2d | 692 | * @param connection handle |
lorevee | 0:1902469bdd2d | 693 | * @param peripheral device index |
lorevee | 0:1902469bdd2d | 694 | * @param feature mask |
lorevee | 0:1902469bdd2d | 695 | * @param notification frequency |
lorevee | 0:1902469bdd2d | 696 | * @retval None |
lorevee | 0:1902469bdd2d | 697 | */ |
lorevee | 0:1902469bdd2d | 698 | void Change_Notification_Status(uint8_t *att_data, uint8_t *attr_value, uint16_t conn_handle, uint8_t i, |
lorevee | 0:1902469bdd2d | 699 | uint32_t feature_mask, uint8_t frequency) { |
lorevee | 1:110b5e896bc9 | 700 | //printf("\r\nChange_Notification_Status (status: %d) (read: %s) (write: %s)\n", perDevs.status, (readCompleted == 1 ? "completed" : "pending"),(writeDescriptorCompleted == 1 ? "completed" : "pending"));//DEBUG |
lorevee | 1:110b5e896bc9 | 701 | |
lorevee | 0:1902469bdd2d | 702 | |
lorevee | 0:1902469bdd2d | 703 | uint8_t value_len; |
lorevee | 0:1902469bdd2d | 704 | uint16_t attr_handle; |
lorevee | 0:1902469bdd2d | 705 | |
lorevee | 0:1902469bdd2d | 706 | |
lorevee | 0:1902469bdd2d | 707 | if (att_data[3] == 1) { |
lorevee | 0:1902469bdd2d | 708 | |
lorevee | 0:1902469bdd2d | 709 | /* Setting notification frequency (wait of 2s for writing op)*/ |
lorevee | 0:1902469bdd2d | 710 | setNotificationProperty(conn_handle, i, feature_mask, NOTIFICATION_FREQ_CMD, frequency); |
lorevee | 0:1902469bdd2d | 711 | |
lorevee | 0:1902469bdd2d | 712 | /* Stopping the scanning for new peripheral nodes */ |
lorevee | 0:1902469bdd2d | 713 | if (perDevs.discovery_enabled) { |
lorevee | 0:1902469bdd2d | 714 | //Disable scanning when notification is enabled |
lorevee | 0:1902469bdd2d | 715 | setNewNodesScanning(0x02); |
lorevee | 0:1902469bdd2d | 716 | } |
lorevee | 0:1902469bdd2d | 717 | |
lorevee | 0:1902469bdd2d | 718 | /* Disabling all previously enabled notifications */ |
lorevee | 0:1902469bdd2d | 719 | disableAllNotifications(); |
lorevee | 0:1902469bdd2d | 720 | |
lorevee | 0:1902469bdd2d | 721 | }//if |
lorevee | 0:1902469bdd2d | 722 | |
lorevee | 0:1902469bdd2d | 723 | |
lorevee | 0:1902469bdd2d | 724 | |
lorevee | 0:1902469bdd2d | 725 | |
lorevee | 0:1902469bdd2d | 726 | /* Enabling/Disabling notifications */ |
lorevee | 0:1902469bdd2d | 727 | value_len = 2; |
lorevee | 0:1902469bdd2d | 728 | attr_value[0] = att_data[3]; |
lorevee | 0:1902469bdd2d | 729 | |
lorevee | 0:1902469bdd2d | 730 | if (feature_mask==FEATURE_MASK_MIC){ |
lorevee | 0:1902469bdd2d | 731 | attr_handle = perDevs.mic_char_handle[i] + 2; |
lorevee | 0:1902469bdd2d | 732 | perDevs.mic_event_enabled = attr_value[0]; |
lorevee | 0:1902469bdd2d | 733 | |
lorevee | 0:1902469bdd2d | 734 | } else if (feature_mask==FEATURE_MASK_PROX){ |
lorevee | 0:1902469bdd2d | 735 | attr_handle = perDevs.prx_char_handle[i] + 2; |
lorevee | 0:1902469bdd2d | 736 | perDevs.prx_event_enabled = attr_value[0]; |
lorevee | 0:1902469bdd2d | 737 | |
lorevee | 0:1902469bdd2d | 738 | } else if (feature_mask==FEATURE_MASK_ACC){ |
lorevee | 0:1902469bdd2d | 739 | attr_handle = perDevs.agm_char_handle[i] + 2; |
lorevee | 0:1902469bdd2d | 740 | perDevs.agm_event_enabled = attr_value[0]; |
lorevee | 0:1902469bdd2d | 741 | |
lorevee | 0:1902469bdd2d | 742 | } else if (feature_mask==FEATURE_MASK_SENSORFUSION){ |
lorevee | 0:1902469bdd2d | 743 | attr_handle = perDevs.sfusion_char_handle[i] + 2; |
lorevee | 0:1902469bdd2d | 744 | perDevs.sfusion_event_enabled = attr_value[0]; |
lorevee | 0:1902469bdd2d | 745 | } |
lorevee | 0:1902469bdd2d | 746 | |
lorevee | 0:1902469bdd2d | 747 | |
lorevee | 0:1902469bdd2d | 748 | // if ((discoveryCompleted == 1)){ |
lorevee | 0:1902469bdd2d | 749 | |
lorevee | 0:1902469bdd2d | 750 | ble_error_t err; |
lorevee | 0:1902469bdd2d | 751 | |
lorevee | 0:1902469bdd2d | 752 | writeDescriptorCompleted=0; |
lorevee | 0:1902469bdd2d | 753 | err = writeCharacDescriptorWithError(conn_handle, attr_handle, value_len, attr_value); |
lorevee | 0:1902469bdd2d | 754 | |
lorevee | 0:1902469bdd2d | 755 | if (err != BLE_ERROR_NONE){ |
lorevee | 0:1902469bdd2d | 756 | writeDescriptorCompleted=1; |
lorevee | 0:1902469bdd2d | 757 | printf("\r\nERROR Enabling/Disabling Notification (err: %d) (stat: %d)\n", err, perDevs.status); |
lorevee | 1:110b5e896bc9 | 758 | |
lorevee | 0:1902469bdd2d | 759 | } |
lorevee | 0:1902469bdd2d | 760 | |
lorevee | 0:1902469bdd2d | 761 | |
lorevee | 0:1902469bdd2d | 762 | |
lorevee | 0:1902469bdd2d | 763 | |
lorevee | 0:1902469bdd2d | 764 | |
lorevee | 0:1902469bdd2d | 765 | /* WUP notification enable/disable */ |
lorevee | 1:110b5e896bc9 | 766 | if(attr_value[0]==0x00){ |
lorevee | 2:1525f4848cf2 | 767 | for (uint8_t j=0; j<(perDevs.connDevices+perDevs.discDevices); j++) { |
lorevee | 2:1525f4848cf2 | 768 | if (!perDevs.wup_event[j] && perDevs.devInfo[j].dev_v == NODE_ME1 && perDevs.is_connected[j]) { |
lorevee | 2:1525f4848cf2 | 769 | attr_handle = perDevs.wup_char_handle[j] + 2; |
lorevee | 2:1525f4848cf2 | 770 | attr_value[0] = 0x01; |
lorevee | 2:1525f4848cf2 | 771 | |
lorevee | 2:1525f4848cf2 | 772 | setNotificationProperty(perDevs.connection_handle[j], j, FEATURE_MASK_WAKEUP_EVENTS, WAKEUP_NOTIFICATION_CMD, 1); |
lorevee | 2:1525f4848cf2 | 773 | |
lorevee | 2:1525f4848cf2 | 774 | if (discoveryCompleted == 1){ |
lorevee | 2:1525f4848cf2 | 775 | |
lorevee | 2:1525f4848cf2 | 776 | writeDescriptorCompleted=0; |
lorevee | 2:1525f4848cf2 | 777 | ble_error_t wupErrOn = writeCharacDescriptorWithError(perDevs.connection_handle[j], attr_handle, value_len, attr_value); |
lorevee | 2:1525f4848cf2 | 778 | |
lorevee | 2:1525f4848cf2 | 779 | if (wupErrOn == BLE_ERROR_NONE){ |
lorevee | 2:1525f4848cf2 | 780 | perDevs.wup_event_enabled = 1; |
lorevee | 2:1525f4848cf2 | 781 | perDevs.wup_event[j] = 1; |
lorevee | 2:1525f4848cf2 | 782 | printf("\r\nWUP notification on node [%d] ON\n", j); |
lorevee | 2:1525f4848cf2 | 783 | |
lorevee | 2:1525f4848cf2 | 784 | } else { |
lorevee | 2:1525f4848cf2 | 785 | printf("\r\nWrite WUP char descriptor failed! (%d)\n", wupErrOn); |
lorevee | 2:1525f4848cf2 | 786 | |
lorevee | 2:1525f4848cf2 | 787 | }//if-else |
lorevee | 2:1525f4848cf2 | 788 | writeDescriptorCompleted=1; |
lorevee | 2:1525f4848cf2 | 789 | |
lorevee | 2:1525f4848cf2 | 790 | }//if-else-discovery-completed |
lorevee | 2:1525f4848cf2 | 791 | }//if |
lorevee | 2:1525f4848cf2 | 792 | }//for |
lorevee | 2:1525f4848cf2 | 793 | |
lorevee | 2:1525f4848cf2 | 794 | |
lorevee | 2:1525f4848cf2 | 795 | if (perDevs.wup_event_enabled == 1) |
lorevee | 2:1525f4848cf2 | 796 | //printf("\r\nAll WUP notifications turned ON\n");//DEBUG |
lorevee | 2:1525f4848cf2 | 797 | perDevs.status = ALL_DATA_READ; |
lorevee | 1:110b5e896bc9 | 798 | |
lorevee | 1:110b5e896bc9 | 799 | |
lorevee | 1:110b5e896bc9 | 800 | } else{ |
lorevee | 1:110b5e896bc9 | 801 | for (uint8_t j=0; j<(perDevs.connDevices+perDevs.discDevices); j++) { |
lorevee | 1:110b5e896bc9 | 802 | if ((perDevs.wup_event[j]) && (perDevs.devInfo[j].dev_v == NODE_ME1) && (perDevs.is_connected[j])) { |
lorevee | 1:110b5e896bc9 | 803 | attr_handle = perDevs.wup_char_handle[j] + 2; |
lorevee | 1:110b5e896bc9 | 804 | attr_value[0] = 0x00; |
lorevee | 1:110b5e896bc9 | 805 | |
lorevee | 1:110b5e896bc9 | 806 | |
lorevee | 1:110b5e896bc9 | 807 | if (discoveryCompleted == 1){ |
lorevee | 1:110b5e896bc9 | 808 | |
lorevee | 1:110b5e896bc9 | 809 | writeDescriptorCompleted=0; |
lorevee | 1:110b5e896bc9 | 810 | ble_error_t wupErrOff = writeCharacDescriptorWithError(perDevs.connection_handle[j], attr_handle, value_len, attr_value); |
lorevee | 1:110b5e896bc9 | 811 | |
lorevee | 1:110b5e896bc9 | 812 | if (wupErrOff == BLE_ERROR_NONE){ |
lorevee | 1:110b5e896bc9 | 813 | perDevs.wup_event_enabled = 0; |
lorevee | 1:110b5e896bc9 | 814 | perDevs.wup_event[j] = 0; |
lorevee | 1:110b5e896bc9 | 815 | printf("\r\nWUP notification on node [%d] OFF\n", j); |
lorevee | 1:110b5e896bc9 | 816 | |
lorevee | 1:110b5e896bc9 | 817 | } else { |
lorevee | 1:110b5e896bc9 | 818 | printf("\r\nWrite WUP char descriptor failed! (%d)\n", wupErrOff); |
lorevee | 1:110b5e896bc9 | 819 | |
lorevee | 1:110b5e896bc9 | 820 | } |
lorevee | 1:110b5e896bc9 | 821 | writeDescriptorCompleted=1; |
lorevee | 1:110b5e896bc9 | 822 | |
lorevee | 1:110b5e896bc9 | 823 | }//if-discovery-completed |
lorevee | 1:110b5e896bc9 | 824 | }//if |
lorevee | 1:110b5e896bc9 | 825 | }//for |
lorevee | 1:110b5e896bc9 | 826 | |
lorevee | 1:110b5e896bc9 | 827 | perDevs.status = NOTIFICATIONS_DATA_READ; |
lorevee | 1:110b5e896bc9 | 828 | |
lorevee | 1:110b5e896bc9 | 829 | }//if-else-wup |
lorevee | 0:1902469bdd2d | 830 | |
lorevee | 0:1902469bdd2d | 831 | attr_value[0] = att_data[3]; |
lorevee | 0:1902469bdd2d | 832 | perDevs.readDeviceIdx = i; |
lorevee | 0:1902469bdd2d | 833 | |
lorevee | 0:1902469bdd2d | 834 | notificationPending = 0; |
lorevee | 0:1902469bdd2d | 835 | |
lorevee | 0:1902469bdd2d | 836 | //Return to connectionProcess |
lorevee | 0:1902469bdd2d | 837 | perDevs.status = CONN_INIT; |
lorevee | 0:1902469bdd2d | 838 | |
lorevee | 0:1902469bdd2d | 839 | |
lorevee | 0:1902469bdd2d | 840 | |
lorevee | 0:1902469bdd2d | 841 | |
lorevee | 0:1902469bdd2d | 842 | } |
lorevee | 0:1902469bdd2d | 843 | /*----------------------------------------------------------------------------*/ |