Annotation of linux/net/tcp/packet.c, revision 1.1.1.1

1.1       root        1: /* packet.c - implements raw packet sockets. */
                      2: /*
                      3:     Copyright (C) 1992  Ross Biro
                      4: 
                      5:     This program is free software; you can redistribute it and/or modify
                      6:     it under the terms of the GNU General Public License as published by
                      7:     the Free Software Foundation; either version 2, or (at your option)
                      8:     any later version.
                      9: 
                     10:     This program is distributed in the hope that it will be useful,
                     11:     but WITHOUT ANY WARRANTY; without even the implied warranty of
                     12:     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
                     13:     GNU General Public License for more details.
                     14: 
                     15:     You should have received a copy of the GNU General Public License
                     16:     along with this program; if not, write to the Free Software
                     17:     Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 
                     18: 
                     19:     The Author may be reached as [email protected] or
                     20:     C/O Department of Mathematics; Stanford University; Stanford, CA 94305
                     21: */
                     22: 
                     23: #include <linux/types.h>
                     24: #include <linux/sched.h>
                     25: #include <linux/fcntl.h>
                     26: #include <linux/socket.h>
                     27: #include <netinet/in.h>
                     28: #include "timer.h"
                     29: #include "ip.h"
                     30: #include "tcp.h"
                     31: #include "sock.h"
                     32: #include <linux/errno.h>
                     33: #include <linux/timer.h>
                     34: #include <asm/system.h>
                     35: #include <asm/segment.h>
                     36: #include "../kern_sock.h" /* for PRINTK */
                     37: 
                     38: extern struct proto raw_prot;
                     39: 
                     40: static  unsigned long
                     41: min(unsigned long a, unsigned long b)
                     42: {
                     43:    if (a < b) return (a);
                     44:    return (b);
                     45: }
                     46: 
                     47: /* this should be the easiest of all, all we do is copy it into
                     48:    a buffer. */
                     49: int
                     50: packet_rcv (struct sk_buff *skb, struct device *dev,  struct packet_type *pt)
                     51: {
                     52:    volatile struct sock *sk;
                     53: 
                     54:    sk = pt->data;
                     55:    skb->dev = dev;
                     56:    skb->len += dev->hard_header_len;
                     57: 
                     58:    /* now see if we are in use. */
                     59:    cli();
                     60:    if (sk->inuse)
                     61:      {
                     62:        sti();
                     63:        /* drop any packets if we can't currently deal with them.
                     64:           Assume that the other end will retransmit if it was
                     65:           important. */
                     66:        skb->sk = NULL;
                     67:        free_skb (skb, FREE_READ);
                     68:        return (0);
                     69: 
                     70:      }
                     71:    sk->inuse = 1;
                     72:    sti ();
                     73: 
                     74:    skb->sk = sk;
                     75: 
                     76:    /* charge it too the socket. */
                     77:    if (sk->rmem_alloc + skb->mem_len >= SK_RMEM_MAX)
                     78:      {
                     79:        skb->sk = NULL;
                     80:        free_skb (skb, FREE_READ);
                     81:        return (0);
                     82:      }
                     83:             
                     84:    sk->rmem_alloc += skb->mem_len;
                     85: 
                     86:    /* now just put it onto the queue. */
                     87:    if (sk->rqueue == NULL)
                     88:      {
                     89:        sk->rqueue = skb;
                     90:        skb->next = skb;
                     91:        skb->prev = skb;
                     92:      }
                     93:    else
                     94:      {
                     95:        skb->next = sk->rqueue;
                     96:        skb->prev = sk->rqueue->prev;
                     97:        skb->prev->next = skb;
                     98:        skb->next->prev = skb;
                     99:      }
                    100:    wake_up (sk->sleep);
                    101:    release_sock (sk);
                    102:    return (0);
                    103: }
                    104: 
                    105: /* this will do terrible things if len + ipheader + devheader > dev->mtu */
                    106: static int
                    107: packet_sendto (volatile struct sock *sk, unsigned char *from, int len,
                    108:               int noblock,
                    109:               unsigned flags, struct sockaddr_in *usin, int addr_len)
                    110: {
                    111:    struct sk_buff *skb;
                    112:    struct device *dev;
                    113:    struct sockaddr saddr;
                    114: 
                    115:    /* check the flags. */
                    116:    if (flags) return (-EINVAL);
                    117:    if (len < 0) return (-EINVAL);
                    118: 
                    119:    /* get and verify the address. */
                    120:    if (usin)
                    121:      {
                    122:        if (addr_len < sizeof (saddr))
                    123:          return (-EINVAL);
                    124:        verify_area (usin, sizeof (saddr));
                    125:        memcpy_fromfs (&saddr, usin, sizeof(saddr));
                    126:      }
                    127:    else
                    128:      return (-EINVAL);
                    129: 
                    130:    skb = sk->prot->wmalloc (sk, len+sizeof (*skb) + sk->prot->max_header, 0);
                    131:    /* this shouldn't happen, but it could. */
                    132:    if (skb == NULL)
                    133:      {
                    134:        PRINTK ("packet_sendto: write buffer full?\n");
                    135:        print_sk (sk);
                    136:        return (-EAGAIN);
                    137:      }
                    138:    skb->mem_addr = skb;
                    139:    skb->mem_len = len + sizeof (*skb) +sk->prot->max_header;
                    140:    skb->sk = sk;
                    141:    skb->free = 1;
                    142:    saddr.sa_data[13] = 0;
                    143:    dev = get_dev (saddr.sa_data);
                    144:    if (dev == NULL)
                    145:      {
                    146:        sk->prot->wfree (sk, skb->mem_addr, skb->mem_len);
                    147:        return (-ENXIO);
                    148:      }
                    149:    verify_area (from, len);
                    150:    memcpy_fromfs (skb+1, from, len);
                    151:    skb->len = len;
                    152:    skb->next = NULL;
                    153:    if (dev->up)
                    154:      dev->queue_xmit (skb, dev, sk->priority);
                    155:    else
                    156:      free_skb (skb, FREE_WRITE);
                    157:    return (len);
                    158: }
                    159: 
                    160: static int
                    161: packet_write (volatile struct sock *sk, unsigned char *buff, 
                    162:              int len, int noblock,  unsigned flags)
                    163: {
                    164:    return (packet_sendto (sk, buff, len, noblock, flags, NULL, 0));
                    165: }
                    166: 
                    167: static void
                    168: packet_close (volatile struct sock *sk, int timeout)
                    169: {
                    170:    sk->inuse = 1;
                    171:    sk->state = TCP_CLOSE;
                    172:    dev_remove_pack ((struct packet_type *)sk->pair);
                    173:    free_s ((void *)sk->pair, sizeof (struct packet_type));
                    174:    release_sock (sk);
                    175: }
                    176: 
                    177: static int
                    178: packet_init (volatile struct sock *sk)
                    179: {
                    180:    struct packet_type *p;
                    181:    p = malloc (sizeof (*p));
                    182:    if (p == NULL) return (-ENOMEM);
                    183: 
                    184:    p->func = packet_rcv;
                    185:    p->type = sk->num;
                    186:    p->data = (void *)sk;
                    187:    dev_add_pack (p);
                    188:    
                    189:    /* we need to remember this somewhere. */
                    190:    sk->pair = (volatile struct sock *)p;
                    191: 
                    192:    return (0);
                    193: }
                    194: 
                    195: 
                    196: int
                    197: packet_recvfrom (volatile struct sock *sk, unsigned char *to, int len,
                    198:              int noblock,
                    199:              unsigned flags, struct sockaddr_in *sin, int *addr_len)
                    200: {
                    201:        /* this should be easy, if there is something there we
                    202:           return it, otherwise we block. */
                    203:        int copied=0;
                    204:        struct sk_buff *skb;
                    205:        struct sockaddr *saddr;
                    206:        saddr = (struct sockaddr *)sin;
                    207: 
                    208:        if (len == 0) return (0);
                    209:        if (len < 0) return (-EINVAL);
                    210:        if (addr_len)
                    211:          {
                    212:                  verify_area (addr_len, sizeof(*addr_len));
                    213:                  put_fs_long (sizeof (*saddr), addr_len);
                    214:          }
                    215: 
                    216:        sk->inuse = 1;
                    217:        while (sk->rqueue == NULL)
                    218:          {
                    219:             if (noblock)
                    220:               {
                    221:                  release_sock (sk);
                    222:                  return (-EAGAIN);
                    223:               }
                    224:             release_sock (sk);
                    225:             cli();
                    226:             if (sk->rqueue == NULL)
                    227:               {
                    228:                  interruptible_sleep_on (sk->sleep);
                    229:                  if (current->signal & ~current->blocked)
                    230:                    {
                    231:                       return (-ERESTARTSYS);
                    232:                    }
                    233:               }
                    234:             sti();
                    235:          }
                    236:        skb = sk->rqueue;
                    237: 
                    238:        if (!(flags & MSG_PEEK))
                    239:          {
                    240:                  if (skb->next == skb )
                    241:                    {
                    242:                            sk->rqueue = NULL;
                    243:                    }
                    244:                  else
                    245:                    {
                    246:                            sk->rqueue = sk->rqueue ->next;
                    247:                            skb->prev->next = skb->next;
                    248:                            skb->next->prev = skb->prev;
                    249:                    }
                    250:          }
                    251:        copied = min (len, skb->len);
                    252:        verify_area (to, copied);
                    253:        memcpy_tofs (to, skb+1,  copied);
                    254:        /* copy the address. */
                    255:        if (saddr)
                    256:          {
                    257:                  struct sockaddr addr;
                    258:                  addr.sa_family = skb->dev->type;
                    259:                  memcpy (addr.sa_data,skb->dev->name, 14);
                    260:                  verify_area (saddr, sizeof (*saddr));
                    261:                  memcpy_tofs(saddr, &addr, sizeof (*saddr));
                    262:          }
                    263: 
                    264:        if (!(flags & MSG_PEEK))
                    265:          {
                    266:             free_skb (skb, FREE_READ);
                    267:          }
                    268: 
                    269:        release_sock (sk);
                    270:        return (copied);
                    271: 
                    272: }
                    273: 
                    274: int
                    275: packet_read (volatile struct sock *sk, unsigned char *buff,
                    276:             int len, int noblock, unsigned flags)
                    277: {
                    278:        return (packet_recvfrom (sk, buff, len, noblock, flags, NULL, NULL));
                    279: }
                    280: 
                    281: 
                    282: int udp_connect (volatile struct sock *sk, struct sockaddr_in *usin,
                    283:                 int addr_len);
                    284: 
                    285: int udp_select (volatile struct sock *sk, int sel_type, select_table *wait);
                    286: 
                    287: 
                    288: struct proto packet_prot =
                    289: {
                    290:   sock_wmalloc,
                    291:   sock_rmalloc,
                    292:   sock_wfree,
                    293:   sock_rfree,
                    294:   sock_rspace,
                    295:   sock_wspace,
                    296:   packet_close,
                    297:   packet_read,
                    298:   packet_write,
                    299:   packet_sendto,
                    300:   packet_recvfrom,
                    301:   ip_build_header,
                    302:   udp_connect,
                    303:   NULL,
                    304:   ip_queue_xmit,
                    305:   ip_retransmit,
                    306:   NULL,
                    307:   NULL,
                    308:   NULL, 
                    309:   udp_select,
                    310:   NULL,
                    311:   packet_init,
                    312:   128,
                    313:   0,
                    314:   {NULL,}
                    315: };

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.