@@ -81,7 +81,7 @@ static void ws_bootstrap_state_change(protocol_interface_info_entry_t *cur, icmp
81
81
static bool ws_bootstrap_state_discovery (struct protocol_interface_info_entry * cur );
82
82
static int8_t ws_bootsrap_event_trig (ws_bootsrap_event_type_e event_type , int8_t interface_id , arm_library_event_priority_e priority , void * event_data );
83
83
84
- static bool ws_bootstrap_neighbor_info_request (struct protocol_interface_info_entry * interface , const uint8_t * mac_64 , llc_neighbour_req_t * neighbor_buffer , bool request_new );
84
+ static bool ws_bootstrap_neighbor_info_request (struct protocol_interface_info_entry * interface , const uint8_t * mac_64 , llc_neighbour_req_t * neighbor_buffer , bool request_new , bool multicast );
85
85
static uint16_t ws_bootstrap_routing_cost_calculate (protocol_interface_info_entry_t * cur );
86
86
static uint16_t ws_bootstrap_rank_get (protocol_interface_info_entry_t * cur );
87
87
static uint16_t ws_bootstrap_min_rank_inc_get (protocol_interface_info_entry_t * cur );
@@ -104,6 +104,13 @@ typedef enum {
104
104
WS_EAPOL_PARENT_SYNCH , /**< Broadcast synch with EAPOL parent*/
105
105
} ws_parent_synch_e ;
106
106
107
+ static void ws_bootsrap_create_ll_address (uint8_t * ll_address , const uint8_t * mac64 )
108
+ {
109
+ memcpy (ll_address , ADDR_LINK_LOCAL_PREFIX , 8 );
110
+ memcpy (ll_address + 8 , mac64 , 8 );
111
+ ll_address [8 ] ^= 2 ;
112
+ }
113
+
107
114
mac_neighbor_table_entry_t * ws_bootstrap_mac_neighbor_add (struct protocol_interface_info_entry * interface , const uint8_t * src64 )
108
115
109
116
{
@@ -312,9 +319,7 @@ static bool ws_nud_message_build(protocol_interface_info_entry_t *cur, mac_neigh
312
319
{
313
320
//Send NS
314
321
uint8_t ll_target [16 ];
315
- memcpy (ll_target , ADDR_LINK_LOCAL_PREFIX , 8 );
316
- memcpy (ll_target + 8 , neighbor -> mac64 , 8 );
317
- ll_target [8 ] ^= 2 ;
322
+ ws_bootsrap_create_ll_address (ll_target , neighbor -> mac64 );
318
323
tr_info ("NUD generate NS %u" , neighbor -> index );
319
324
buffer_t * buffer = icmpv6_build_ns (cur , ll_target , NULL , true, false, NULL );
320
325
if (buffer ) {
@@ -923,7 +928,7 @@ static void ws_bootstrap_pan_advertisement_analyse(struct protocol_interface_inf
923
928
// Save route cost for all neighbours
924
929
llc_neighbour_req_t neighbor_info ;
925
930
neighbor_info .neighbor = NULL ;
926
- if (ws_bootstrap_neighbor_info_request (cur , data -> SrcAddr , & neighbor_info , false)) {
931
+ if (ws_bootstrap_neighbor_info_request (cur , data -> SrcAddr , & neighbor_info , false, false )) {
927
932
neighbor_info .ws_neighbor -> routing_cost = pan_information .routing_cost ;
928
933
}
929
934
@@ -1073,7 +1078,7 @@ static void ws_bootstrap_pan_config_analyse(struct protocol_interface_info_entry
1073
1078
return ;
1074
1079
}
1075
1080
llc_neighbour_req_t neighbor_info ;
1076
- if (!ws_bootstrap_neighbor_info_request (cur , data -> SrcAddr , & neighbor_info , true)) {
1081
+ if (!ws_bootstrap_neighbor_info_request (cur , data -> SrcAddr , & neighbor_info , true, true )) {
1077
1082
return ;
1078
1083
}
1079
1084
@@ -1156,7 +1161,7 @@ static void ws_bootstrap_pan_config_solicit_analyse(struct protocol_interface_in
1156
1161
*/
1157
1162
1158
1163
llc_neighbour_req_t neighbor_info ;
1159
- if (ws_bootstrap_neighbor_info_request (cur , data -> SrcAddr , & neighbor_info , false)) {
1164
+ if (ws_bootstrap_neighbor_info_request (cur , data -> SrcAddr , & neighbor_info , false, false )) {
1160
1165
etx_lqi_dbm_update (cur -> id , data -> mpduLinkQuality , data -> signal_dbm , neighbor_info .neighbor -> index );
1161
1166
ws_neighbor_class_neighbor_unicast_time_info_update (neighbor_info .ws_neighbor , ws_utt , data -> timestamp );
1162
1167
ws_neighbor_class_neighbor_unicast_schedule_set (neighbor_info .ws_neighbor , ws_us );
@@ -1347,7 +1352,7 @@ static void ws_bootstrap_neighbor_table_clean(struct protocol_interface_info_ent
1347
1352
memcpy (ll_target + 8 , cur -> mac64 , 8 );
1348
1353
ll_target [8 ] ^= 2 ;
1349
1354
1350
- if (rpl_control_is_dodag_parent (interface , ll_target )) {
1355
+ if (rpl_control_is_dodag_parent (interface , ll_target , true )) {
1351
1356
// Possible parent is limited to 3 by default?
1352
1357
continue ;
1353
1358
}
@@ -1365,7 +1370,7 @@ static void ws_bootstrap_neighbor_table_clean(struct protocol_interface_info_ent
1365
1370
link_min_timeout = WS_NEIGHBOR_NOT_TRUSTED_LINK_MIN_TIMEOUT ;
1366
1371
}
1367
1372
1368
- if (time_from_last_unicast_shedule > link_min_timeout ) {
1373
+ if (time_from_last_unicast_shedule > link_min_timeout || ! ws_neighbor -> unicast_data_rx ) {
1369
1374
//Accept only Enough Old Device
1370
1375
if (!neighbor_entry_ptr ) {
1371
1376
//Accept first compare
@@ -1386,7 +1391,7 @@ static void ws_bootstrap_neighbor_table_clean(struct protocol_interface_info_ent
1386
1391
1387
1392
}
1388
1393
1389
- static bool ws_bootstrap_neighbor_info_request (struct protocol_interface_info_entry * interface , const uint8_t * mac_64 , llc_neighbour_req_t * neighbor_buffer , bool request_new )
1394
+ static bool ws_bootstrap_neighbor_info_request (struct protocol_interface_info_entry * interface , const uint8_t * mac_64 , llc_neighbour_req_t * neighbor_buffer , bool request_new , bool multicast )
1390
1395
{
1391
1396
neighbor_buffer -> neighbor = mac_neighbor_table_address_discover (mac_neighbor_info (interface ), mac_64 , ADDR_802_15_4_LONG );
1392
1397
if (neighbor_buffer -> neighbor ) {
@@ -1399,15 +1404,34 @@ static bool ws_bootstrap_neighbor_info_request(struct protocol_interface_info_en
1399
1404
if (!request_new ) {
1400
1405
return false;
1401
1406
}
1402
- uint8_t ll_target [16 ];
1403
- memcpy (ll_target , ADDR_LINK_LOCAL_PREFIX , 8 );
1404
- memcpy (ll_target + 8 , mac_64 , 8 );
1405
- ll_target [8 ] ^= 2 ;
1406
1407
1408
+ if (!multicast ) {
1409
+ uint8_t ll_target [16 ];
1410
+ ws_bootsrap_create_ll_address (ll_target , mac_64 );
1407
1411
1408
- if (blacklist_reject (ll_target )) {
1409
- // Rejected by blacklist
1410
- return false;
1412
+ if (blacklist_reject (ll_target )) {
1413
+ // Rejected by blacklist
1414
+ return false;
1415
+ }
1416
+ } else {
1417
+
1418
+ if (interface -> bootsrap_mode == ARM_NWK_BOOTSRAP_MODE_6LoWPAN_BORDER_ROUTER ) {
1419
+ //Border router never allocate neighbors by multicast
1420
+ return false;
1421
+ }
1422
+
1423
+ uint16_t parent_candidate_size = rpl_control_parent_candidate_list_size (interface , false);
1424
+
1425
+ //if we have enough candidates at list do not accept new multicast neighbours
1426
+ if (parent_candidate_size >= 4 ) {
1427
+ return false;
1428
+ }
1429
+
1430
+ parent_candidate_size = rpl_control_parent_candidate_list_size (interface , true);
1431
+ //If we have already enough parent selected Candidates count is bigger tahn 4
1432
+ if (parent_candidate_size >= 2 ) {
1433
+ return false;
1434
+ }
1411
1435
}
1412
1436
1413
1437
ws_bootstrap_neighbor_table_clean (interface );
@@ -1483,6 +1507,21 @@ static bool ws_neighbor_entry_nud_notify(mac_neighbor_table_entry_t *entry_ptr,
1483
1507
//Accept quick Probe for init ETX
1484
1508
activate_nud = true;
1485
1509
} else {
1510
+ if (cur -> bootsrap_mode == ARM_NWK_BOOTSRAP_MODE_6LoWPAN_BORDER_ROUTER ) {
1511
+ if (etx_entry -> etx_samples || !ws_neighbor -> unicast_data_rx ) {
1512
+ //Border router just need 1 sample for ETX
1513
+ return false;
1514
+ }
1515
+ } else {
1516
+ uint8_t ll_address [16 ];
1517
+ ws_bootsrap_create_ll_address (ll_address , entry_ptr -> mac64 );
1518
+ if (!rpl_control_is_dodag_parent (cur , ll_address , false)) {
1519
+ if (etx_entry -> etx_samples || !ws_neighbor -> unicast_data_rx ) {
1520
+ return 0 ;
1521
+ }
1522
+ }
1523
+ }
1524
+
1486
1525
uint32_t probe_period = WS_PROBE_INIT_BASE_SECONDS << etx_entry -> etx_samples ;
1487
1526
uint32_t time_block = 1 << etx_entry -> etx_samples ;
1488
1527
if (time_from_start >= probe_period ) {
@@ -2471,7 +2510,7 @@ void ws_bootstrap_network_scan_process(protocol_interface_info_entry_t *cur)
2471
2510
2472
2511
// Add EAPOL neighbour
2473
2512
llc_neighbour_req_t neighbor_info ;
2474
- if (!ws_bootstrap_neighbor_info_request (cur , cur -> ws_info -> parent_info .addr , & neighbor_info , true)) {
2513
+ if (!ws_bootstrap_neighbor_info_request (cur , cur -> ws_info -> parent_info .addr , & neighbor_info , true, false )) {
2475
2514
return ;
2476
2515
}
2477
2516
@@ -2664,9 +2703,7 @@ void ws_primary_parent_update(protocol_interface_info_entry_t *interface, mac_ne
2664
2703
neighbor_info .ws_neighbor = ws_neighbor_class_entry_get (& interface -> ws_info -> neighbor_storage , neighbor -> index );
2665
2704
ws_bootstrap_primary_parent_set (interface , & neighbor_info , WS_PARENT_HARD_SYNCH );
2666
2705
uint8_t link_local_address [16 ];
2667
- memcpy (link_local_address , ADDR_LINK_LOCAL_PREFIX , 8 );
2668
- memcpy (link_local_address + 8 , neighbor -> mac64 , 8 );
2669
- link_local_address [8 ] ^= 2 ;
2706
+ ws_bootsrap_create_ll_address (link_local_address , neighbor -> mac64 );
2670
2707
dhcp_client_server_address_update (interface -> id , NULL , link_local_address );
2671
2708
2672
2709
ws_secondary_parent_update (interface );
0 commit comments