From 548e4ce55656c187946d7b99d4466bb0217f34fe Mon Sep 17 00:00:00 2001 From: adamdunkels Date: Wed, 14 Mar 2007 00:30:46 +0000 Subject: [PATCH] New rime module: best-effort network flooding (nf) --- core/net/rime/Makefile.rime | 3 +- core/net/rime/nf.c | 183 ++++++++++++++++++++++++++++++++++++ core/net/rime/nf.h | 71 ++++++++++++++ 3 files changed, 256 insertions(+), 1 deletion(-) create mode 100644 core/net/rime/nf.c create mode 100644 core/net/rime/nf.h diff --git a/core/net/rime/Makefile.rime b/core/net/rime/Makefile.rime index c3e1e08ff..ae231aa08 100644 --- a/core/net/rime/Makefile.rime +++ b/core/net/rime/Makefile.rime @@ -1,2 +1,3 @@ CONTIKI_SOURCEFILES += rimebuf.c queuebuf.c ctimer.c neighbor.c rime.c \ - ibc.c uc.c suc.c ruc.c sibc.c sabc.c ccsabc.c abc.c abc-udp.c + ibc.c uc.c suc.c ruc.c sibc.c sabc.c ccsabc.c abc.c abc-udp.c \ + nf.c diff --git a/core/net/rime/nf.c b/core/net/rime/nf.c new file mode 100644 index 000000000..5ef39ed8b --- /dev/null +++ b/core/net/rime/nf.c @@ -0,0 +1,183 @@ +/* + * Copyright (c) 2006, Swedish Institute of Computer Science. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of the Institute nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * This file is part of the Contiki operating system. + * + * $Id: nf.c,v 1.1 2007/03/14 00:30:46 adamdunkels Exp $ + */ + +/** + * \file + * Best-effort network flooding (nf) + * \author + * Adam Dunkels + */ + +#include "net/rime/nf.h" +#include "net/rime.h" +#include "lib/rand.h" +#include + +#define QUEUE_TIME ((CLOCK_SECOND / 16) * (rand() % 16)) + +#define HOPS_MAX 16 + +struct nf_hdr { + u8_t hops; + u8_t originator_seqno; + node_id_t originator_id; +}; + +static u8_t seqno; + +static void send(void *ptr); + +/*---------------------------------------------------------------------------*/ +static void +set_timer(struct nf_conn *c) +{ + ctimer_set(&c->t, QUEUE_TIME, send, c); +} +/*---------------------------------------------------------------------------*/ +static void +send(void *ptr) +{ + struct nf_conn *c = ptr; + + if(c->packets_received > 0) { + c->packets_received = 0; + set_timer(c); + } else { + /* DEBUGF(3, "nf: send()\n");*/ + queuebuf_to_rimebuf(c->buf); + queuebuf_free(c->buf); + c->buf = NULL; + ibc_send(&c->c); + if(c->u->sent != NULL) { + c->u->sent(c); + } + } +} +/*---------------------------------------------------------------------------*/ +static int +queue_for_send(struct nf_conn *c) +{ + if(c->buf == NULL) { + c->buf = queuebuf_new_from_rimebuf(); + } + if(c->buf == NULL) { + return 0; + } + c->packets_received = 0; + set_timer(c); + return 1; +} +/*---------------------------------------------------------------------------*/ +static void +recv_from_ibc(struct ibc_conn *ibc, node_id_t from_id) +{ + register struct nf_conn *c = (struct nf_conn *)ibc; + struct nf_hdr *hdr = rimebuf_dataptr(); + u8_t hops; + struct queuebuf *queuebuf; + + c->packets_received++; + + hops = hdr->hops; + + /* Remember packet if we need to forward it. */ + queuebuf = queuebuf_new_from_rimebuf(); + + rimebuf_hdrreduce(sizeof(struct nf_hdr)); + if(c->u->recv != NULL) { + if(!(hdr->originator_id == c->last_originator_id && + hdr->originator_seqno <= c->last_originator_seqno)) { + + if(c->u->recv(c, from_id, hdr->originator_id, hops)) { + + if(queuebuf != NULL) { + queuebuf_to_rimebuf(queuebuf); + queuebuf_free(queuebuf); + queuebuf = NULL; + hdr = rimebuf_dataptr(); + + /* Rebroadcast received packet. */ + if(hops < HOPS_MAX) { + /* printf("rebroadcasting %d/%d (%d/%d) hops %d\n", + hdr->originator_id, hdr->originator_seqno, + c->last_originator_id, c->last_originator_seqno, + hops);*/ + hdr->hops++; + queue_for_send(c); + c->last_originator_id = hdr->originator_id; + c->last_originator_seqno = hdr->originator_seqno; + } + } + } + } + } + if(queuebuf != NULL) { + queuebuf_free(queuebuf); + } +} +/*---------------------------------------------------------------------------*/ +static const struct ibc_ulayer nf = {recv_from_ibc}; +/*---------------------------------------------------------------------------*/ +void +nf_setup(struct nf_conn *c, u16_t channel, + const struct nf_ulayer *u) +{ + ibc_setup(&c->c, channel, &nf); + c->u = u; +} +/*---------------------------------------------------------------------------*/ +int +nf_send(struct nf_conn *c) +{ + if(c->buf != NULL) { + queuebuf_free(c->buf); + c->buf = NULL; + } + + if(rimebuf_hdrextend(sizeof(struct nf_hdr))) { + struct nf_hdr *hdr = rimebuf_hdrptr(); + + c->last_originator_id = hdr->originator_id = node_id; + c->last_originator_seqno = hdr->originator_seqno = ++seqno; + hdr->hops = 0; + return queue_for_send(c); + } + return 0; +} +/*---------------------------------------------------------------------------*/ +void +nf_cancel(struct nf_conn *c) +{ + ctimer_stop(&c->t); +} +/*---------------------------------------------------------------------------*/ diff --git a/core/net/rime/nf.h b/core/net/rime/nf.h new file mode 100644 index 000000000..1005c3a36 --- /dev/null +++ b/core/net/rime/nf.h @@ -0,0 +1,71 @@ +/* + * Copyright (c) 2006, Swedish Institute of Computer Science. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of the Institute nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * This file is part of the Contiki operating system. + * + * $Id: nf.h,v 1.1 2007/03/14 00:30:46 adamdunkels Exp $ + */ + +/** + * \file + * Header file for the best-effort network flooding (nf) + * \author + * Adam Dunkels + */ + +#ifndef __NF_H__ +#define __NF_H__ + +#include "net/rime/uc.h" +#include "net/rime/ctimer.h" +#include "net/rime/queuebuf.h" + +struct nf_conn; + +struct nf_ulayer { + int (* recv)(struct nf_conn *c, node_id_t from, + node_id_t originator, u8_t hops); + void (* sent)(struct nf_conn *c); +}; + +struct nf_conn { + struct ibc_conn c; + struct ctimer t; + struct queuebuf *buf; + u8_t packets_received; + u8_t last_originator_seqno; + node_id_t last_originator_id; + const struct nf_ulayer *u; +}; + +void nf_setup(struct nf_conn *c, u16_t channel, + const struct nf_ulayer *u); + +int nf_send(struct nf_conn *c); + +#endif /* __SIBC_H__ */