Contiki 2.6
|
00001 /** 00002 * \addtogroup rimermh 00003 * @{ 00004 */ 00005 00006 /* 00007 * Copyright (c) 2007, Swedish Institute of Computer Science. 00008 * All rights reserved. 00009 * 00010 * Redistribution and use in source and binary forms, with or without 00011 * modification, are permitted provided that the following conditions 00012 * are met: 00013 * 1. Redistributions of source code must retain the above copyright 00014 * notice, this list of conditions and the following disclaimer. 00015 * 2. Redistributions in binary form must reproduce the above copyright 00016 * notice, this list of conditions and the following disclaimer in the 00017 * documentation and/or other materials provided with the distribution. 00018 * 3. Neither the name of the Institute nor the names of its contributors 00019 * may be used to endorse or promote products derived from this software 00020 * without specific prior written permission. 00021 * 00022 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 00023 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 00024 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 00025 * ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 00026 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 00027 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 00028 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 00029 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 00030 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 00031 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 00032 * SUCH DAMAGE. 00033 * 00034 * This file is part of the Contiki operating system. 00035 * 00036 * $Id: rmh.c,v 1.10 2009/11/08 19:40:17 adamdunkels Exp $ 00037 */ 00038 00039 /** 00040 * \file 00041 * Multihop forwarding 00042 * \author 00043 * Adam Dunkels <adam@sics.se> 00044 */ 00045 00046 #include "contiki.h" 00047 #include "net/rime.h" 00048 #include "net/rime/rmh.h" 00049 00050 struct data_hdr { 00051 rimeaddr_t dest; 00052 rimeaddr_t originator; 00053 uint8_t hops; 00054 uint8_t max_rexmits; 00055 }; 00056 00057 #define DEBUG 0 00058 #if DEBUG 00059 #include <stdio.h> 00060 #define PRINTF(...) printf(__VA_ARGS__) 00061 #else 00062 #define PRINTF(...) 00063 #endif 00064 00065 /*---------------------------------------------------------------------------*/ 00066 static void 00067 received(struct runicast_conn *uc, const rimeaddr_t *from, uint8_t seqno) 00068 { 00069 struct rmh_conn *c = (struct rmh_conn *)uc; 00070 struct data_hdr *msg = packetbuf_dataptr(); 00071 rimeaddr_t *nexthop; 00072 00073 PRINTF("data_packet_received from %d.%d towards %d.%d len %d\n", 00074 from->u8[0], from->u8[1], 00075 msg->dest.u8[0], msg->dest.u8[1], 00076 packetbuf_datalen()); 00077 00078 if(rimeaddr_cmp(&msg->dest, &rimeaddr_node_addr)) { 00079 PRINTF("for us!\n"); 00080 packetbuf_hdrreduce(sizeof(struct data_hdr)); 00081 if(c->cb->recv) { 00082 c->cb->recv(c, &msg->originator, msg->hops); 00083 } 00084 } else { 00085 nexthop = NULL; 00086 if(c->cb->forward) { 00087 nexthop = c->cb->forward(c, &msg->originator, 00088 &msg->dest, from, msg->hops); 00089 } 00090 if(nexthop) { 00091 PRINTF("forwarding to %d.%d\n", nexthop->u8[0], nexthop->u8[1]); 00092 msg->hops++; 00093 runicast_send(&c->c, nexthop, c->num_rexmit); 00094 } 00095 } 00096 } 00097 /*---------------------------------------------------------------------------*/ 00098 static void 00099 sent(struct runicast_conn *c, const rimeaddr_t *to, uint8_t retransmissions) 00100 { 00101 00102 } 00103 /*---------------------------------------------------------------------------*/ 00104 static void 00105 timedout(struct runicast_conn *c, const rimeaddr_t *to, uint8_t retransmissions) 00106 { 00107 00108 } 00109 /*---------------------------------------------------------------------------*/ 00110 static const struct runicast_callbacks data_callbacks = { received , 00111 sent, 00112 timedout}; 00113 /*---------------------------------------------------------------------------*/ 00114 void 00115 rmh_open(struct rmh_conn *c, uint16_t channel, 00116 const struct rmh_callbacks *callbacks) 00117 { 00118 runicast_open(&c->c, channel, &data_callbacks); 00119 c->cb = callbacks; 00120 } 00121 /*---------------------------------------------------------------------------*/ 00122 void 00123 rmh_close(struct rmh_conn *c) 00124 { 00125 runicast_close(&c->c); 00126 } 00127 /*---------------------------------------------------------------------------*/ 00128 int 00129 rmh_send(struct rmh_conn *c, rimeaddr_t *to, uint8_t num_rexmit, uint8_t max_hops) 00130 { 00131 rimeaddr_t *nexthop; 00132 struct data_hdr *hdr; 00133 00134 c->num_rexmit = num_rexmit; 00135 00136 if(c->cb->forward == NULL) { 00137 return 0; 00138 } 00139 00140 nexthop = c->cb->forward(c, &rimeaddr_node_addr, to, NULL, 0); 00141 if(nexthop == NULL) { 00142 PRINTF("rmh_send: no route\n"); 00143 return 0; 00144 } else { 00145 PRINTF("rmh_send: sending data\n"); 00146 00147 00148 if(packetbuf_hdralloc(sizeof(struct data_hdr))) { 00149 hdr = packetbuf_hdrptr(); 00150 rimeaddr_copy(&hdr->dest, to); 00151 rimeaddr_copy(&hdr->originator, &rimeaddr_node_addr); 00152 hdr->hops = 1; 00153 hdr->max_rexmits = num_rexmit; 00154 runicast_send(&c->c, nexthop, num_rexmit); 00155 } 00156 return 1; 00157 } 00158 } 00159 /*---------------------------------------------------------------------------*/ 00160 /** @} */