~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~ [ freetext search ] ~ [ file search ] ~

Linux Cross Reference
cvs/emstar/devel/link/rnc/rnc_lower.c


  1 /*
  2  *
  3  * Copyright (c) 2003 The Regents of the University of California.  All 
  4  * rights reserved.
  5  *
  6  * Redistribution and use in source and binary forms, with or without
  7  * modification, are permitted provided that the following conditions
  8  * are met:
  9  *
 10  * - Redistributions of source code must retain the above copyright
 11  *   notice, this list of conditions and the following disclaimer.
 12  *
 13  * - Neither the name of the University nor the names of its
 14  *   contributors may be used to endorse or promote products derived
 15  *   from this software without specific prior written permission.
 16  *
 17  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS''
 18  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
 19  * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
 20  * PARTICULAR  PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR
 21  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
 22  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
 23  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 24  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
 25  * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
 26  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
 27  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 28  *
 29  */
 30  
 31 
 32 /*
 33  * rnc_lower.c: The "lower" half of rnc, i.e. handling the link
 34  * layer interfaces underneath the daemon that we use to send the
 35  * packets.
 36  *
 37  * $Id: rnc_lower.c,v 1.10 2003-07-11 22:29:54 cerpa Exp $
 38  */
 39 
 40 char rnc_lower_c_cvsid[] = "$Id: rnc_lower.c,v 1.10 2003-07-11 22:29:54 cerpa Exp $";
 41 
 42 #include <stdio.h>
 43 #include <stdlib.h>
 44 
 45 #include "link/link.h"
 46 #include "rnc_i.h"
 47 
 48 
 49 /*******************************************************************/
 50 
 51 
 52 /*
 53  * This callback is called whenever a packet arrives up from one of
 54  * the underlying datalink interfaces
 55  */
 56 static int rnc_receiver(link_pkt_t *link_pkt, ssize_t data_len, link_context_t *link)
 57 {
 58     rnc_state_t *f = (rnc_state_t *) link_opts(link)->data;
 59     rnc_pkt_t *rnc_pkt = (rnc_pkt_t *) link_pkt->data;
 60 
 61     // Make sure the packet has the right packet type. Since we
 62     // specified the desired packet type when we registered to receive
 63     // packets, this test should never fail.
 64     if (link_pkt->type != PKT_TYPE_RNC) {
 65         elog(LOG_WARNING, "got a packet not meant for us - filter failed!");
 66         goto done;
 67     }
 68 
 69     // Make sure the data portion of the packet is at least the size of
 70     // a rnc packet header
 71     if (data_len < sizeof(rnc_pkt_t)) {
 72         elog(LOG_ERR, "got a short rnc packet (%d bytes < %d)!", data_len,
 73              sizeof(rnc_pkt_t));
 74         goto done;
 75     }
 76 
 77     // We now know that the data pointed to by rnc_pkt is valid 
 78     switch( rnc_pkt->sub_type) {
 79     case RNC_DATA:
 80         elog(LOG_DEBUG(4), "got rnc data packet");
 81         rnc_handle_data_pkt(f, link_pkt, data_len);
 82         break;
 83     case RNC_ACK:
 84         elog(LOG_DEBUG(4), "got rnc ack packet");       
 85         rnc_handle_ack_pkt(f, link_pkt, data_len);
 86         break;
 87     default:
 88         elog(LOG_ERR, "got rnc packet with an unknown subtype %d", rnc_pkt->sub_type);  
 89     }
 90 
 91  done:
 92     free(link_pkt);
 93     return EVENT_RENEW;
 94 }
 95 
 96 
 97 /*
 98  * This function opens one of the underlying transport devices used by
 99  * the rnc daemon (e.g., a basic datalink such as motenic)
100  */
101 void rnc_open_link(rnc_state_t *f, int link_index)
102 {
103     rnc_iface_t *i;
104 
105     // make sure we don't have too many interfaces open
106     if (f->num_ifaces >= MAX_IFACES) {
107         elog(LOG_ERR, "can't open link interface: too many interfaces!");
108         exit(1);
109     }
110 
111     // get a pointer to the next available iface struct 
112     i = &(f->iface[f->num_ifaces]);
113 
114     // set options for this link 
115     memset(i, 0, sizeof(rnc_iface_t));
116     i->if_opts.link_index = link_index;
117     i->if_opts.pkt_type = PKT_TYPE_RNC;
118     // Make the queues large enough to handle retransmission storms
119     i->if_opts.q_opts.outq_len = 300;
120     i->if_opts.q_opts.inq_len = 300;
121     i->if_opts.receive = rnc_receiver;
122     i->if_opts.data = f;
123 
124     // try to open it
125     if (link_open(&i->if_opts, &i->if_context) < 0) {
126         elog(LOG_CRIT, "can't open %s: %m", link_name(&i->if_opts));
127         exit(1);
128     }
129 
130     // Open succeeded - increment interface count
131     f->num_ifaces++;
132     elog(LOG_NOTICE, "opened lower interface %d: %s", f->num_ifaces, link_name(&i->if_opts));
133 }
134 
135 
136 /*
137  * Send a link_pkt to all interfaces opened by the function above
138  */
139 void rnc_send_to_all(rnc_state_t *f, link_pkt_t *pkt, int data_len)
140 {
141     int i;
142     uint32_t seqnum;
143     rnc_pkt_t *p=(rnc_pkt_t *)(pkt->data);
144     rnc_data_pkt_t *d=(rnc_data_pkt_t *)(p->next_hdr);
145 
146     if (p->sub_type==RNC_DATA) {
147         seqnum=d->seq_num;
148         elog(LOG_NOTICE, "Source %d sending packet %d\n", 
149              my_node_id, seqnum);
150     } else {
151         elog(LOG_NOTICE, "Source %d sending ACK packet\n", my_node_id);
152     }
153         
154     elog(LOG_DEBUG(4), "sending; %d interfaces", f->num_ifaces);
155 
156     for (i = 0; i < f->num_ifaces; i++) {
157         elog(LOG_DEBUG(4), "sending to %s", 
158              link_name(link_opts(f->iface[i].if_context)));
159 
160         if (link_send(f->iface[i].if_context, pkt, data_len) < 0)
161             elog(LOG_WARNING, "sending to %s: %m", 
162                  link_name(&(f->iface[i].if_opts)));
163     }
164 }
165 

~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~ [ freetext search ] ~ [ file search ] ~

This page was automatically generated by the LXR engine.
Visit the LXR main site for more information.