Annotation of embedaddon/mrouted/ipip.c, revision 1.1.1.1

1.1       misho       1: /*
                      2:  * The mrouted program is covered by the license in the accompanying file
                      3:  * named "LICENSE".  Use of the mrouted program represents acceptance of
                      4:  * the terms and conditions listed in that file.
                      5:  *
                      6:  * The mrouted program is COPYRIGHT 1989 by The Board of Trustees of
                      7:  * Leland Stanford Junior University.
                      8:  */
                      9: 
                     10: #include "defs.h"
                     11: 
                     12: /*
                     13:  * Exported variables.
                     14:  */
                     15: #ifdef notyet
                     16: int            raw_socket;                 /* socket for raw network I/O  */
                     17: #endif
                     18: /*
                     19:  *XXX For now, we just use the IGMP socket to send packets.
                     20:  * This is legal in BSD, because the protocol # is not checked
                     21:  * on raw sockets.  The k_* interfaces need to gain a socket
                     22:  * argument so that we can call them on the raw_socket also.
                     23:  */
                     24: #define        raw_socket      igmp_socket
                     25: 
                     26: /*
                     27:  * Private variables.
                     28:  */
                     29: static int rawid = 0;
                     30: 
                     31: /*
                     32:  * Open and initialize the raw socket.
                     33:  */
                     34: void init_ipip(void)
                     35: {
                     36: #ifdef notyet
                     37:     if ((raw_socket = socket(AF_INET, SOCK_RAW, IPPROTO_RAW)) < 0)
                     38:        logit(LOG_ERR, errno, "Raw IP socket");
                     39: #endif
                     40: }
                     41: 
                     42: /*
                     43:  * Allocate and fill in static IP header for encapsulating on a tunnel.
                     44:  */
                     45: void init_ipip_on_vif(struct uvif *v)
                     46: {
                     47:     struct ip *ip;
                     48: 
                     49:     ip = v->uv_encap_hdr = (struct ip *)malloc(sizeof(struct ip));
                     50:     if (ip == NULL)
                     51:        logit(LOG_ERR, 0, "out of memory");
                     52:     memset(ip, 0, sizeof(struct ip));
                     53:     /*
                     54:      * Fields zeroed that aren't filled in later:
                     55:      * - IP ID (let the kernel fill it in)
                     56:      * - Offset (we don't send fragments)
                     57:      * - Checksum (let the kernel fill it in)
                     58:      */
                     59:     ip->ip_v   = IPVERSION;
                     60:     ip->ip_hl  = sizeof(struct ip) >> 2;
                     61:     ip->ip_tos = 0xc0;         /* Internet Control */
                     62:     ip->ip_ttl = MAXTTL;       /* applies to unicasts only */
                     63:     ip->ip_p   = IPPROTO_IPIP;
                     64:     ip->ip_src.s_addr = v->uv_lcl_addr;
                     65:     ip->ip_dst.s_addr = v->uv_rmt_addr;
                     66: }
                     67: 
                     68: /*
                     69:  * Call build_igmp() to build an IGMP message in the output packet buffer.
                     70:  * Then fill in the fields of the IP packet that build_igmp() left for the
                     71:  * kernel to fill in, and encapsulate the original packet with the
                     72:  * pre-created ip header for this vif.
                     73:  */
                     74: void send_ipip(u_int32 src, u_int32 dst, int type, int code, u_int32 group, int datalen, struct uvif *v)
                     75: {
                     76:     struct msghdr msg;
                     77:     struct iovec iov[2];
                     78:     struct sockaddr_in sdst;
                     79:     struct ip *ip;
                     80: 
                     81:     build_igmp(src, dst, type, code, group, datalen);
                     82:     ip = (struct ip *)send_buf;
                     83:     ip->ip_id = htons(rawid++);
                     84:     ip->ip_sum = 0;
                     85:     ip->ip_sum = inet_cksum((u_int16_t *)ip, ip->ip_hl << 2);
                     86: 
                     87:     ip = v->uv_encap_hdr;
                     88:     ip->ip_len = 2 * MIN_IP_HEADER_LEN + IGMP_MINLEN + datalen;
                     89:     ip->ip_len = htons(ip->ip_len);
                     90: 
                     91:     memset(&sdst, 0, sizeof(sdst));
                     92:     sdst.sin_family = AF_INET;
                     93: #ifdef HAVE_SA_LEN
                     94:     sdst.sin_len = sizeof(sdst);
                     95: #endif
                     96:     sdst.sin_addr = ip->ip_dst;
                     97: 
                     98:     iov[0].iov_base = (caddr_t)v->uv_encap_hdr;
                     99:     iov[0].iov_len = sizeof(struct ip);
                    100:     iov[1].iov_base = (caddr_t)send_buf;
                    101:     iov[1].iov_len = MIN_IP_HEADER_LEN + IGMP_MINLEN + datalen;
                    102: 
                    103:     memset(&msg, 0, sizeof(msg));
                    104:     msg.msg_name = (caddr_t)&sdst;
                    105:     msg.msg_namelen = sizeof(sdst);
                    106:     msg.msg_iov = iov;
                    107:     msg.msg_iovlen = 2;
                    108:     if (sendmsg(raw_socket, &msg, 0) < 0) {
                    109:        if (errno == ENETDOWN)
                    110:            check_vif_state();
                    111:        else
                    112:            logit(LOG_WARNING, errno,
                    113:                "sendmsg to %s on %s",
                    114:                inet_fmt(sdst.sin_addr.s_addr, s1, sizeof(s1)), inet_fmt(src, s2, sizeof(s2)));
                    115:     }
                    116: 
                    117:     IF_DEBUG(DEBUG_PKT|igmp_debug_kind(type, code))
                    118:     logit(LOG_DEBUG, 0, "SENT %s from %-15s to %s encaped to %s",
                    119:        igmp_packet_kind(type, code), src == INADDR_ANY ? "INADDR_ANY" :
                    120:                                 inet_fmt(src, s1, sizeof(s1)), inet_fmt(dst, s2, sizeof(s2)),
                    121:                                 inet_fmt(sdst.sin_addr.s_addr, s3, sizeof(s3)));
                    122: }
                    123: 
                    124: /**
                    125:  * Local Variables:
                    126:  *  version-control: t
                    127:  *  indent-tabs-mode: t
                    128:  *  c-file-style: "ellemtel"
                    129:  *  c-basic-offset: 4
                    130:  * End:
                    131:  */

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>