/*---------------------------------------------------------------------------*/ static uip_ds6_maddr_t * join_mcast_group() { uip_ipaddr_t addr; uip_ds6_maddr_t * rv; /* First, set our v6 global */ uip_ip6addr(&addr, 0xaaaa, 0, 0, 0, 0, 0, 0, 0); uip_ds6_set_addr_iid(&addr, &uip_lladdr); uip_ds6_addr_add(&addr, 0, ADDR_AUTOCONF); /* * IPHC will use stateless multicast compression for this destination * (M=1, DAC=0), with 32 inline bits (1E 89 AB CD) */ uip_ip6addr(&addr,0xFF1E,0,0,0,0,0,0x89,0xABCD); rv = uip_ds6_maddr_add(&addr); if(rv) { PRINTF("Joined multicast group "); PRINT6ADDR(&uip_ds6_maddr_lookup(&addr)->ipaddr); PRINTF("\n"); } return rv; }
/*---------------------------------------------------------------------------*/ uip_ds6_addr_t * uip_ds6_addr_add(uip_ipaddr_t *ipaddr, unsigned long vlifetime, uint8_t type) { if(uip_ds6_list_loop ((uip_ds6_element_t *)uip_ds6_if.addr_list, UIP_DS6_ADDR_NB, sizeof(uip_ds6_addr_t), ipaddr, 128, (uip_ds6_element_t **)&locaddr) == FREESPACE) { locaddr->isused = 1; uip_ipaddr_copy(&locaddr->ipaddr, ipaddr); locaddr->type = type; if(vlifetime == 0) { locaddr->isinfinite = 1; } else { locaddr->isinfinite = 0; stimer_set(&(locaddr->vlifetime), vlifetime); } #if UIP_ND6_DEF_MAXDADNS > 0 locaddr->state = ADDR_TENTATIVE; timer_set(&locaddr->dadtimer, random_rand() % (UIP_ND6_MAX_RTR_SOLICITATION_DELAY * CLOCK_SECOND)); locaddr->dadnscount = 0; #else /* UIP_ND6_DEF_MAXDADNS > 0 */ locaddr->state = ADDR_PREFERRED; #endif /* UIP_ND6_DEF_MAXDADNS > 0 */ uip_create_solicited_node(ipaddr, &loc_fipaddr); uip_ds6_maddr_add(&loc_fipaddr); return locaddr; } return NULL; }
/*---------------------------------------------------------------------------*/ uip_ds6_addr_t * uip_ds6_addr_add(uip_ipaddr_t * ipaddr, unsigned long vlifetime, u8_t type) { if(uip_ds6_list_loop ((uip_ds6_element_t *) uip_ds6_if.addr_list, UIP_DS6_ADDR_NB, sizeof(uip_ds6_addr_t), ipaddr, 128, (uip_ds6_element_t **) & locaddr) == FREESPACE) { locaddr->isused = 1; uip_ipaddr_copy(&locaddr->ipaddr, ipaddr); if (uip_is_addr_link_local(ipaddr)) { locaddr->state = ADDR_PREFERRED; } else { locaddr->state = ADDR_TENTATIVE; } locaddr->type = type; if(vlifetime == 0) { locaddr->isinfinite = 1; } else { locaddr->isinfinite = 0; stimer_set(&locaddr->vlifetime, vlifetime); } #if UIP_CONF_ROUTER /* * If 6LoWPAN-ND optimizations are implemented, hosts do not join the * Solicited-node multicast address. */ uip_create_solicited_node(ipaddr, &loc_fipaddr); uip_ds6_maddr_add(&loc_fipaddr); #endif /* UIP_CONF_ROUTER */ return locaddr; } return NULL; }
/*---------------------------------------------------------------------------*/ uip_ds6_addr_t * uip_ds6_addr_add(uip_ipaddr_t *ipaddr, unsigned long vlifetime, uint8_t type) { loc_loop_state = uip_ds6_list_loop ((uip_ds6_element_t *)uip_ds6_if.addr_list, UIP_DS6_ADDR_NB, sizeof(uip_ds6_addr_t), ipaddr, 128, (uip_ds6_element_t **)&locaddr); if(loc_loop_state == NOSPACE) { uip_ds6_addr_clean(); } if(loc_loop_state == FREESPACE) { locaddr->isused = 1; uip_ipaddr_copy(&locaddr->ipaddr, ipaddr); locaddr->type = type; if(vlifetime == 0) { locaddr->isinfinite = 1; } else { locaddr->isinfinite = 0; stimestamp_set(&(locaddr->vlifetime), vlifetime); } locaddr->state = ADDR_PREFERRED; uip_create_solicited_node(ipaddr, &loc_fipaddr); uip_ds6_maddr_add(&loc_fipaddr); return locaddr; } return NULL; }
/*---------------------------------------------------------------------------*/ void uip_ds6_init(void) { PRINTF("Init of IPv6 data structures"); memset(uip_ds6_nbr_cache, 0, sizeof(uip_ds6_nbr_cache)); memset(uip_ds6_defrt_list, 0, sizeof(uip_ds6_defrt_list)); memset(uip_ds6_prefix_list, 0, sizeof(uip_ds6_prefix_list)); memset(&uip_ds6_if, 0, sizeof(uip_ds6_if)); memset(uip_ds6_routing_table, 0, sizeof(uip_ds6_routing_table)); /* Set interface parameters */ uip_ds6_if.link_mtu = UIP_LINK_MTU; uip_ds6_if.cur_hop_limit = UIP_TTL; uip_ds6_if.base_reachable_time = UIP_ND6_REACHABLE_TIME; uip_ds6_if.reachable_time = uip_ds6_compute_reachable_time(); uip_ds6_if.retrans_timer = UIP_ND6_RETRANS_TIMER; uip_ds6_if.maxdadns = UIP_ND6_DEF_MAXDADNS; /* Create link local address, prefix, multicast addresses, anycast addresses */ uip_create_linklocal_prefix(&loc_fipaddr); #if UIP_CONF_ROUTER uip_ds6_prefix_add(&loc_fipaddr, UIP_DEFAULT_PREFIX_LEN, 0, 0, 0, 0); #else /* UIP_CONF_ROUTER */ uip_ds6_prefix_add(&loc_fipaddr, UIP_DEFAULT_PREFIX_LEN, 0); #endif /* UIP_CONF_ROUTER */ uip_ds6_set_addr_iid(&loc_fipaddr, &uip_lladdr); uip_ds6_addr_add(&loc_fipaddr, 0, ADDR_AUTOCONF); //uip_ds6_addr_add_preferred(&loc_fipaddr, 0, ADDR_AUTOCONF);// CHANGED ALE uip_create_linklocal_allnodes_mcast(&loc_fipaddr); uip_ds6_maddr_add(&loc_fipaddr); #if UIP_CONF_ROUTER uip_create_linklocal_allrouters_mcast(&loc_fipaddr); uip_ds6_maddr_add(&loc_fipaddr); #if UIP_ND6_SEND_RA stimer_set(&uip_ds6_timer_ra, 2); /* wait to have a link local IP address */ #endif /* UIP_ND6_SEND_RA */ #else /* UIP_CONF_ROUTER */ etimer_set(&uip_ds6_timer_rs, tcpip_process, random_rand() % (UIP_ND6_MAX_RTR_SOLICITATION_DELAY * CLOCK_SECOND)); #endif /* UIP_CONF_ROUTER */ etimer_set(&uip_ds6_timer_periodic, tcpip_process, UIP_DS6_PERIOD); return; }
/** * Add a multicast address to the list. */ ule6lo_status_t ule6loGI_addMulticastAddr(ule6lo_ip6addr_t* ipaddress) { ule6lo_status_t status = STATUS_NO_DEVICE; #if UIP_CONF_MLD if( uip_ds6_maddr_add((uip_ipaddr_t*)ipaddress)){ status = STATUS_SUCCESS; } #endif return status; }
void rpl_init(void) { uip_ipaddr_t rplmaddr; PRINTF("RPL started\n"); rpl_reset_periodic_timer(); neighbor_info_subscribe(rpl_link_neighbor_callback); /* add rpl multicast address */ uip_create_linklocal_rplnodes_mcast(&rplmaddr); uip_ds6_maddr_add(&rplmaddr); #if RPL_CONF_STATS memset(&rpl_stats, 0, sizeof(rpl_stats)); #endif }
/*---------------------------------------------------------------------------*/ void rpl_init(void) { uip_ipaddr_t rplmaddr; PRINTF("RPL started\n"); default_instance = NULL; rpl_dag_init(); rpl_reset_periodic_timer(); /* add rpl multicast address */ uip_create_linklocal_rplnodes_mcast(&rplmaddr); uip_ds6_maddr_add(&rplmaddr); #if RPL_CONF_STATS memset(&rpl_stats, 0, sizeof(rpl_stats)); #endif }
smcp_t smcp_plat_init(smcp_t self) { SMCP_EMBEDDED_SELF_HOOK; #if UIP_CONF_IPV6 { uip_ipaddr_t all_coap_nodes_addr; if(uiplib_ipaddrconv( COAP_MULTICAST_IP6_LL_ALLDEVICES, &all_coap_nodes_addr )) { uip_ds6_maddr_add(&all_coap_nodes_addr); } } #endif return self; }
/*---------------------------------------------------------------------------*/ PROCESS_THREAD(multicast_example_process, ev, data) { PROCESS_BEGIN(); /* Create a linkl-local multicast addresses. */ uip_ip6addr(&addr, 0xff02, 0, 0, 0, 0, 0, 0x1337, 0x0001); /* Join local group. */ if(uip_ds6_maddr_add(&addr) == NULL) { printf("Error: could not join local multicast group.\n"); } /* Register UDP socket callback */ udp_socket_register(&s, NULL, receiver); /* Bind UDP socket to local port */ udp_socket_bind(&s, PORT); /* Connect UDP socket to remote port */ udp_socket_connect(&s, NULL, PORT); while(1) { /* Set up two timers, one for keeping track of the send interval, which is periodic, and one for setting up a randomized send time within that interval. */ etimer_set(&periodic_timer, SEND_INTERVAL); etimer_set(&send_timer, (random_rand() % SEND_INTERVAL)); PROCESS_WAIT_UNTIL(etimer_expired(&send_timer)); printf("Sending multicast\n"); udp_socket_sendto(&s, "hello", 6, &addr, PORT); PROCESS_WAIT_UNTIL(etimer_expired(&periodic_timer)); } PROCESS_END(); }
/*---------------------------------------------------------------------------*/ PROCESS_THREAD(rest_server_example, ev, data) { uip_ipaddr_t server_ipaddr; uip_ds6_maddr_t *rv; PROCESS_BEGIN(); uip_ip6addr(&server_ipaddr, 0xff1e, 0, 0, 0, 0, 0, 0x89, 0xabcd); rv = uip_ds6_maddr_add(&server_ipaddr); if(rv) { PRINTF("Joined multicast group "); PRINT6ADDR(&uip_ds6_maddr_lookup(&server_ipaddr)->ipaddr); PRINTF("\n"); } print_local_addresses(); #ifdef WITH_DTLS dtls_set_log_level(LOG_DEBUG); set_dtls_handler(get_psk_key, NULL); #endif /* WITH_DTLS */ PRINTF("\r\nStarting Erbium Example Server\r\n"); /* Initialize the REST engine. */ rest_init_engine(); /** Creating an entry in routing table to able to answer to multicast request with the first message */ uip_ipaddr_t client_addr; uip_lladdr_t lladdr = {{0x04,0x0f,0x07,0xb2,0x00, 0x12,0x4b,0x00}}; uip_ip6addr(&client_addr, 0xfe80, 0, 0, 0, 0x060f, 0x07b2, 0x0012, 0x4b00); uip_ds6_nbr_add(&client_addr, &lladdr, 0, 1); #ifdef WITH_DTLS session_t session; /**< Creating a secure session */ uip_ipaddr_copy(&session.addr, &server_ipaddr); session.port = UIP_HTONS(COAP_DEFAULT_PORT+1); session.size = sizeof(session.addr) + sizeof(session.port); session.ifindex = 1; #ifdef WITH_MULTICAST secure_group_creation(&session); /**< Create a DTLS group in case of multicast communication */ #endif // WITH_MULTICAST #endif // WITH_DTLS /* Activate the application-specific resources. */ #if REST_RES_HELLO rest_activate_resource(&resource_helloworld); #endif #if REST_RES_BATTERY SENSORS_ACTIVATE(battery_sensor); rest_activate_resource(&resource_battery); #endif PROCESS_END(); }
struct net_context *net_context_get(enum ip_protocol ip_proto, const struct net_addr *remote_addr, uint16_t remote_port, struct net_addr *local_addr, uint16_t local_port) { #ifdef CONFIG_NETWORKING_WITH_IPV6 const struct in6_addr in6addr_any = IN6ADDR_ANY_INIT; const uip_ds6_addr_t *uip_addr; uip_ipaddr_t ipaddr; #endif int i; struct net_context *context = NULL; /* User must provide storage for the local address. */ if (!local_addr) { return NULL; } #ifdef CONFIG_NETWORKING_WITH_IPV6 if (memcmp(&local_addr->in6_addr, &in6addr_any, sizeof(in6addr_any)) == 0) { uip_addr = uip_ds6_get_global(-1); if (!uip_addr) { uip_addr = uip_ds6_get_link_local(-1); } if (!uip_addr) { return NULL; } memcpy(&local_addr->in6_addr, &uip_addr->ipaddr, sizeof(struct in6_addr)); } #else if (local_addr->in_addr.s_addr == INADDR_ANY) { uip_gethostaddr((uip_ipaddr_t *)&local_addr->in_addr); } #endif nano_sem_take(&contexts_lock, TICKS_UNLIMITED); if (local_port) { if (context_port_used(ip_proto, local_port, local_addr) < 0) { return NULL; } } else { do { local_port = random_rand() | 0x8000; } while (context_port_used(ip_proto, local_port, local_addr) == -EEXIST); } for (i = 0; i < NET_MAX_CONTEXT; i++) { if (!contexts[i].tuple.ip_proto) { contexts[i].tuple.ip_proto = ip_proto; contexts[i].tuple.remote_addr = (struct net_addr *)remote_addr; contexts[i].tuple.remote_port = remote_port; contexts[i].tuple.local_addr = (struct net_addr *)local_addr; contexts[i].tuple.local_port = local_port; context = &contexts[i]; break; } } context_sem_give(&contexts_lock); /* Set our local address */ #ifdef CONFIG_NETWORKING_WITH_IPV6 memcpy(&ipaddr.u8, local_addr->in6_addr.s6_addr, sizeof(ipaddr.u8)); if (uip_is_addr_mcast(&ipaddr)) { uip_ds6_maddr_add(&ipaddr); } else { uip_ds6_addr_add(&ipaddr, 0, ADDR_MANUAL); } #endif return context; }
/*---------------------------------------------------------------------------*/ void uip_ds6_init(void) { uip_ds6_neighbors_init(); uip_ds6_route_init(); PRINTF("Init of IPv6 data structures\n"); PRINTF("%u neighbors\n%u default routers\n%u prefixes\n%u routes\n%u unicast addresses\n%u multicast addresses\n%u anycast addresses\n", NBR_TABLE_MAX_NEIGHBORS, UIP_DS6_DEFRT_NB, UIP_DS6_PREFIX_NB, UIP_DS6_ROUTE_NB, UIP_DS6_ADDR_NB, UIP_DS6_MADDR_NB, UIP_DS6_AADDR_NB); memset(uip_ds6_prefix_list, 0, sizeof(uip_ds6_prefix_list)); memset(&uip_ds6_if, 0, sizeof(uip_ds6_if)); #if CONF_6LOWPAN_ND memset(uip_ds6_context_pref_list, 0, sizeof(uip_ds6_context_pref_list)); memset(uip_ds6_br_list, 0, sizeof(uip_ds6_br_list)); #if UIP_CONF_6LBR memset(uip_ds6_dup_addr_list, 0, sizeof(uip_ds6_dup_addr_list)); #endif /* UIP_CONF_6LBR */ #endif /* CONF_6LOWPAN_ND */ uip_ds6_addr_size = sizeof(struct uip_ds6_addr); uip_ds6_netif_addr_list_offset = offsetof(struct uip_ds6_netif, addr_list); /* Set interface parameters */ uip_ds6_if.link_mtu = UIP_LINK_MTU; uip_ds6_if.cur_hop_limit = UIP_TTL; uip_ds6_if.base_reachable_time = UIP_ND6_REACHABLE_TIME; uip_ds6_if.reachable_time = uip_ds6_compute_reachable_time(); uip_ds6_if.retrans_timer = UIP_ND6_RETRANS_TIMER; uip_ds6_if.maxdadns = UIP_ND6_DEF_MAXDADNS; /* Create link local address, prefix, multicast addresses, anycast addresses */ uip_create_linklocal_prefix(&loc_fipaddr); #if UIP_CONF_ROUTER uip_ds6_prefix_add(&loc_fipaddr, UIP_DEFAULT_PREFIX_LEN, 0, 0, 0, 0); #else /* UIP_CONF_ROUTER */ uip_ds6_prefix_add(&loc_fipaddr, UIP_DEFAULT_PREFIX_LEN, 0); #endif /* UIP_CONF_ROUTER */ uip_ds6_set_addr_iid(&loc_fipaddr, &uip_lladdr); uip_ds6_addr_add(&loc_fipaddr, 0, ADDR_AUTOCONF); uip_create_linklocal_allnodes_mcast(&loc_fipaddr); uip_ds6_maddr_add(&loc_fipaddr); #if UIP_CONF_ROUTER uip_create_linklocal_allrouters_mcast(&loc_fipaddr); uip_ds6_maddr_add(&loc_fipaddr); #if UIP_ND6_SEND_RA #if !CONF_6LOWPAN_ND || UIP_ND6_RA_PERIODIC PRINTF("Will Sending periodic RA\n"); stimer_set(&uip_ds6_timer_ra, 2); /* wait to have a link local IP address */ #endif /* #if !CONF_6LOWPAN_ND || UIP_ND6_RA_PERIODIC */ #endif /* UIP_ND6_SEND_RA */ #if UIP_CONF_6LR etimer_set(&uip_ds6_timer_rs, random_rand() % (UIP_ND6_MAX_RTR_SOLICITATION_DELAY * CLOCK_SECOND)); #endif /* UIP_CONF_6LR */ #else /* UIP_CONF_ROUTER */ etimer_set(&uip_ds6_timer_rs, random_rand() % (UIP_ND6_MAX_RTR_SOLICITATION_DELAY * CLOCK_SECOND)); #endif /* UIP_CONF_ROUTER */ etimer_set(&uip_ds6_timer_periodic, UIP_DS6_PERIOD); #if CONF_6LOWPAN_ND_OPTI_START && UIP_CONF_6L_ROUTER rpl_started = 0; #endif /* CONF_6LOWPAN_ND_OPTI_START && UIP_CONF_6L_ROUTER */ return; }