#include <lib6lowpan.h>
#include <6lowpan.h>
#include <ip_malloc.h>
+#include <Statistics.h>
#include "in_cksum.h"
#include "PrintfUART.h"
#include "ICMP.h"
icmp_statistics_t stats;
uint32_t solicitation_period;
uint32_t advertisement_period;
+ uint16_t nd_seqno = 0;
uint16_t ping_seq, ping_n, ping_rcv, ping_ident;
struct in6_addr ping_dest;
}
command void ICMP.sendAdvertisements() {
+
+
uint16_t jitter = (call Random.rand16()) % TRICKLE_JITTER;
CHECK_NODE_ID;
if (call Advertisement.isRunning()) return;
msg->hdr.nxt_hdr = IANA_ICMP;
- i_hdr->cksum = call ICMP.cksum(msg, IANA_ICMP);
+ i_hdr->cksum = htons(call ICMP.cksum(msg, IANA_ICMP));
call IP.send(msg);
if (ipmsg == NULL) return;
dbg("ICMPResponder", "Solicitation\n");
- //stats.sol_tx++;
+ //BLIP_STATS_INCR(stats.sol_tx);
msg->type = ICMP_TYPE_ROUTER_SOL;
msg->code = 0;
call IPAddress.getLLAddr(&ipmsg->hdr.ip6_src);
- inet_pton6("ff02::2", &ipmsg->hdr.ip6_dst);
+ ip_memclr((uint8_t *)&ipmsg->hdr.ip6_dst, 16);
+ ipmsg->hdr.ip6_dst.s6_addr16[0] = htons(0xff02);
+ ipmsg->hdr.ip6_dst.s6_addr16[7] = htons(2);
msg->cksum = call ICMP.cksum(ipmsg, IANA_ICMP);
radv_t *r = (radv_t *)payload;
pfx_t *pfx = (pfx_t *)(r->options);
- uint16_t cost = 0;
rqual_t *beacon = (rqual_t *)(pfx + 1);
if (len > sizeof(radv_t) + sizeof(pfx_t) &&
beacon->type == ICMP_EXT_TYPE_BEACON) {
- cost = beacon->metric;
+
+ if (beacon->seqno > nd_seqno || (nd_seqno > 0 && beacon->seqno == 0)) {
+ call IPRouting.reset();
+ }
+
+ nd_seqno = beacon->seqno;
+ call IPRouting.reportAdvertisement(meta->sender, r->hlim,
+ meta->lqi, beacon->metric);
+
+
+
dbg("ICMPResponder", " * beacon cost: 0x%x\n", cost);
- } else
+ } else {
dbg("ICMPResponder", " * no beacon cost\n");
-
- call IPRouting.reportAdvertisement(meta->sender, r->hlim,
- meta->lqi, cost);
+ }
if (pfx->type != ICMP_EXT_TYPE_PREFIX) return;
if (globalPrefix) {
len += sizeof(pfx_t);
p->type = ICMP_EXT_TYPE_PREFIX;
- p->length = 8;
+ p->length = sizeof(pfx_t) >> 3;
+ p->pfx_len = 64;
memcpy(p->prefix, call IPAddress.getPublicAddr(), 8);
}
len += sizeof(rqual_t);
q->type = ICMP_EXT_TYPE_BEACON;
- q->length = 2;
+ q->length = sizeof(rqual_t) >> 3;;
q->metric = call IPRouting.getQuality();
call IPAddress.getLLAddr(&ipmsg->hdr.ip6_src);
- inet_pton6("ff02::1", &ipmsg->hdr.ip6_dst);
+ ip_memclr((uint8_t *)&ipmsg->hdr.ip6_dst, 16);
+ ipmsg->hdr.ip6_dst.s6_addr16[0] = htons(0xff02);
+ ipmsg->hdr.ip6_dst.s6_addr16[7] = htons(1);
//dbg("ICMPResponder", "My Address: [0x%x] [0x%x] [0x%x] [0x%x]\n", ipmsg->hdr.src_addr[12], ipmsg->hdr.src_addr[13], ipmsg->hdr.src_addr[14], ipmsg->hdr.src_addr[15]);
dbg("ICMPResponder", "adv hop limit: 0x%x\n", r->hlim);
struct ip_metadata *meta) {
icmp_echo_hdr_t *req = (icmp_echo_hdr_t *)payload;
uint16_t len = ntohs(iph->plen);
- stats.rx++;
+ BLIP_STATS_INCR(stats.rx);
// for checksum calculation
printfUART ("icmp type: 0x%x code: 0x%x cksum: 0x%x ident: 0x%x seqno: 0x%x len: 0x%x\n",
switch (req->type) {
case ICMP_TYPE_ROUTER_ADV:
handleRouterAdv(payload, len, meta);
- //stats.adv_rx++;
+ //BLIP_STATS_INCR(stats.adv_rx);
break;
case ICMP_TYPE_ROUTER_SOL:
// only reply to solicitations if we have established a default route.
nx_uint32_t *sendTime = (nx_uint32_t *)(req + 1);
struct icmp_stats p_stat;
p_stat.seq = req->seqno;
- p_stat.ttl = 0;// buf->hdr.hlim;
+ p_stat.ttl = iph->hlim;
p_stat.rtt = (call LocalTime.get()) - (*sendTime);
signal ICMPPing.pingReply[req->ident](&iph->ip6_src, &p_stat);
ping_rcv++;