@@ -1320,6 +1320,40 @@ uint8_t *icmpv6_write_mtu_option(uint32_t mtu, uint8_t *dptr)
1320
1320
return dptr ;
1321
1321
}
1322
1322
1323
+ void ack_receive_cb (struct buffer * buffer_ptr , uint8_t status )
1324
+ {
1325
+ /*icmpv6_na_handler functionality based on ACK*/
1326
+ ipv6_neighbour_t * neighbour_entry ;
1327
+ uint8_t ll_target [16 ];
1328
+
1329
+ if (status != SOCKET_TX_DONE ) {
1330
+ /*NS failed*/
1331
+ return ;
1332
+ }
1333
+
1334
+ if (buffer_ptr -> dst_sa .addr_type == ADDR_IPV6 ) {
1335
+ /*Full IPv6 address*/
1336
+ memcpy (ll_target , buffer_ptr -> dst_sa .address , 16 );
1337
+ } else if (buffer_ptr -> dst_sa .addr_type == ADDR_802_15_4_LONG ) {
1338
+ // Build link local address from long MAC address
1339
+ memcpy (ll_target , ADDR_LINK_LOCAL_PREFIX , 8 );
1340
+ memcpy (ll_target + 8 , & buffer_ptr -> dst_sa .address [2 ], 8 );
1341
+ ll_target [8 ] ^= 2 ;
1342
+ } else {
1343
+ tr_warn ("wrong address %d %s" , buffer_ptr -> dst_sa .addr_type , trace_array (buffer_ptr -> dst_sa .address , 16 ));
1344
+ return ;
1345
+ }
1346
+
1347
+ neighbour_entry = ipv6_neighbour_lookup (& buffer_ptr -> interface -> ipv6_neighbour_cache , ll_target );
1348
+ if (neighbour_entry ) {
1349
+ ipv6_neighbour_update_from_na (& buffer_ptr -> interface -> ipv6_neighbour_cache , neighbour_entry , NA_S , buffer_ptr -> dst_sa .addr_type , buffer_ptr -> dst_sa .address );
1350
+ }
1351
+
1352
+ if (ws_info (buffer_ptr -> interface )) {
1353
+ ws_common_neighbor_update (buffer_ptr -> interface , ll_target );
1354
+ }
1355
+ }
1356
+
1323
1357
buffer_t * icmpv6_build_ns (protocol_interface_info_entry_t * cur , const uint8_t target_addr [16 ], const uint8_t * prompting_src_addr , bool unicast , bool unspecified_source , const aro_t * aro )
1324
1358
{
1325
1359
if (!cur || addr_is_ipv6_multicast (target_addr )) {
@@ -1394,10 +1428,15 @@ buffer_t *icmpv6_build_ns(protocol_interface_info_entry_t *cur, const uint8_t ta
1394
1428
}
1395
1429
/* If ARO Success sending is omitted, MAC ACK is used instead */
1396
1430
/* Setting callback for receiving ACK from adaptation layer */
1397
- if (aro && cur -> ipv6_neighbour_cache .omit_aro_success ) {
1431
+ if (aro && cur -> ipv6_neighbour_cache .omit_na_aro_success ) {
1398
1432
buf -> ack_receive_cb = rpl_control_address_register_done ;
1399
1433
}
1400
1434
}
1435
+ if (!aro && cur -> ipv6_neighbour_cache .omit_na ) {
1436
+ /*MAC ACK is processed as success response*/
1437
+ buf -> ack_receive_cb = ack_receive_cb ;
1438
+ }
1439
+
1401
1440
buf -> src_sa .addr_type = ADDR_IPV6 ;
1402
1441
1403
1442
/* NS packets are implicitly on-link. If we ever find ourselves sending an
@@ -1530,11 +1569,16 @@ buffer_t *icmpv6_build_na(protocol_interface_info_entry_t *cur, bool solicited,
1530
1569
1531
1570
tr_debug ("Build NA" );
1532
1571
1533
- /* Check if ARO status == success, then sending can be omitted with flag */
1534
- if (aro && cur -> ipv6_neighbour_cache .omit_aro_success && aro -> status == ARO_SUCCESS ) {
1535
- tr_debug ("Omit success reply " );
1572
+ /* Check if ARO response and status == success, then sending can be omitted with flag */
1573
+ if (aro && cur -> ipv6_neighbour_cache .omit_na_aro_success && aro -> status == ARO_SUCCESS ) {
1574
+ tr_debug ("Omit NA ARO success " );
1536
1575
return NULL ;
1537
1576
}
1577
+ /* All other than ARO NA messages are omitted and MAC ACK is considered as success */
1578
+ if (!aro && cur -> ipv6_neighbour_cache .omit_na ) {
1579
+ return NULL ;
1580
+ }
1581
+
1538
1582
1539
1583
buffer_t * buf = buffer_get (8 + 16 + 16 + 16 ); /* fixed, target addr, target ll addr, aro */
1540
1584
if (!buf ) {
0 commit comments