diff --git a/examples/rpl_udp/rpl.c b/examples/rpl_udp/rpl.c index 8411ca345a07a0f6e318d058b24320787fb8e7d3..9e2ebe077eddb166c97119a681c56c91fe77b237 100644 --- a/examples/rpl_udp/rpl.c +++ b/examples/rpl_udp/rpl.c @@ -96,42 +96,46 @@ void rpl_udp_init(int argc, char **argv) printf("Channel set to %" PRIi32 "\n", chan); + /* global address */ + ipv6_addr_t global_addr, global_prefix; + ipv6_addr_init(&global_prefix, 0xabcd, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0); + ipv6_addr_set_by_eui64(&global_addr, 0, &global_prefix); + if (command != 'h') { DEBUGF("Initializing RPL for interface 0\n"); - uint8_t state = rpl_init(0); - if (state != SIXLOWERROR_SUCCESS) { - printf("Error initializing RPL\n"); + uint8_t state; + if (command == 'n') { + /* + * no global address specified, we'll use auto address config + * initiated by the root node + */ + state = rpl_init(0, NULL); } - else { - puts("6LoWPAN and RPL initialized."); - } - - if (command == 'r') { - /* add global address */ - ipv6_addr_t tmp; - /* initialize prefix */ - ipv6_addr_init(&tmp, 0xabcd, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0); - + else if (command == 'r') { rpl_options_t rpl_opts = { .instance_id = 0, - .prefix = tmp, + .prefix = global_prefix, .prefix_len = 64, - .prefix_flags = RPL_PREFIX_INFO_AUTO_ADDR_CONF, /* autonomous address-configuration */ + .prefix_flags = RPL_PREFIX_INFO_AUTO_ADDR_CONF, + /* autonomous address-configuration */ }; - tmp.uint16[7] = HTONS(id); - /* set host suffix */ - ipv6_addr_set_by_eui64(&tmp, 0, &tmp); - ipv6_net_if_add_addr(0, &tmp, NDP_ADDR_STATE_PREFERRED, 0, 0, 0); - + /* use specific global address */ + state = rpl_init(0, &global_addr); rpl_init_root(&rpl_opts); - ipv6_iface_set_routing_provider(rpl_get_next_hop); is_root = 1; } + + if (state != SIXLOWERROR_SUCCESS) { + puts("Error initializing RPL"); + } else { - ipv6_iface_set_routing_provider(rpl_get_next_hop); + puts("6LoWPAN and RPL initialized."); } + + ipv6_iface_set_routing_provider(rpl_get_next_hop); + } else { puts("6LoWPAN initialized."); diff --git a/sys/net/include/rpl.h b/sys/net/include/rpl.h index a5fa816891abb8a44a5cdd3e843071c1c264b61b..d81b19bfd02a0bc53481c9e9527aeb2c047ba4c5 100644 --- a/sys/net/include/rpl.h +++ b/sys/net/include/rpl.h @@ -73,12 +73,13 @@ void rpl_send(ipv6_addr_t *destination, uint8_t *payload, uint16_t p_len, uint8_ * corresponding objective functions and sixlowpan (including own address). * * @param[in] if_id ID of the interface, which correspond to the network under RPL-control + * @param[in] address Global IPv6 address to use * * @return 1 if initialization was successful * @return 0 if initialization was not successful * */ -uint8_t rpl_init(int if_id); +uint8_t rpl_init(int if_id, ipv6_addr_t *address); /** * @brief Initialization of RPL-root. diff --git a/sys/net/routing/rpl/rpl.c b/sys/net/routing/rpl/rpl.c index 6d20c2f767565ab252b175c6ce953cea7d2e4e45..49b81896384cb0668228b39548809957d6c1fa8e 100644 --- a/sys/net/routing/rpl/rpl.c +++ b/sys/net/routing/rpl/rpl.c @@ -73,7 +73,7 @@ ipv6_addr_t my_address; /* IPv6 message buffer */ static ipv6_hdr_t *ipv6_buf; -uint8_t rpl_init(int if_id) +uint8_t rpl_init(int if_id, ipv6_addr_t *address) { rpl_if_id = if_id; rpl_instances_init(); @@ -89,12 +89,13 @@ uint8_t rpl_init(int if_id) rpl_process, NULL, "rpl_process"); sixlowpan_lowpan_init_interface(if_id); - /* need link local prefix to query _our_ corresponding address */ - ipv6_addr_t ll_address; - ipv6_addr_set_link_local_prefix(&ll_address); - ipv6_net_if_get_best_src_addr(&my_address, &ll_address); ipv6_register_rpl_handler(rpl_process_pid); + if (address) { + my_address = *address; + ipv6_net_if_add_addr(if_id, &my_address, NDP_ADDR_STATE_PREFERRED, 0, 0, 0); + } + /* add all-RPL-nodes address */ ipv6_addr_t all_rpl_nodes; ipv6_addr_set_all_rpl_nodes_addr(&all_rpl_nodes); diff --git a/sys/net/routing/rpl/rpl_control_messages.c b/sys/net/routing/rpl/rpl_control_messages.c index d42890468c1aeb2107c6a81672220e2c2e1d4dfb..32d6b858fad2593a4c14dd9503767b0cebc57339 100644 --- a/sys/net/routing/rpl/rpl_control_messages.c +++ b/sys/net/routing/rpl/rpl_control_messages.c @@ -426,7 +426,14 @@ void rpl_send_DAO(ipv6_addr_t *destination, uint8_t lifetime, bool default_lifet rpl_send_opt_target_buf->length = RPL_OPT_TARGET_LEN; rpl_send_opt_target_buf->flags = 0x00; rpl_send_opt_target_buf->prefix_length = RPL_DODAG_ID_LEN; - memcpy(&rpl_send_opt_target_buf->target, &my_address, sizeof(ipv6_addr_t)); + if (!ipv6_addr_is_unspecified(&my_dodag->prefix)) { + ipv6_addr_t tmp; + ipv6_addr_set_by_eui64(&tmp, rpl_if_id, &my_dodag->prefix); + memcpy(&rpl_send_opt_target_buf->target, &tmp, sizeof(ipv6_addr_t)); + } + else { + memcpy(&rpl_send_opt_target_buf->target, &my_address, sizeof(ipv6_addr_t)); + } opt_len += RPL_OPT_TARGET_LEN_WITH_OPT_LEN; rpl_send_opt_transit_buf = get_rpl_send_opt_transit_buf(DAO_BASE_LEN + opt_len);