treewide: drop executable file attrib for non-executable files
[oweals/u-boot_mod.git] / u-boot / httpd / tapdev.c
1 /*
2  * Copyright (c) 2001, Swedish Institute of Computer Science.
3  * All rights reserved. 
4  *
5  * Redistribution and use in source and binary forms, with or without 
6  * modification, are permitted provided that the following conditions 
7  * are met: 
8  *
9  * 1. Redistributions of source code must retain the above copyright 
10  *    notice, this list of conditions and the following disclaimer. 
11  *
12  * 2. Redistributions in binary form must reproduce the above copyright 
13  *    notice, this list of conditions and the following disclaimer in the 
14  *    documentation and/or other materials provided with the distribution. 
15  *
16  * 3. Neither the name of the Institute nor the names of its contributors 
17  *    may be used to endorse or promote products derived from this software 
18  *    without specific prior written permission. 
19  *
20  * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 
21  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
22  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
23  * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 
24  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 
25  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 
26  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 
27  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
28  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 
29  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
30  * SUCH DAMAGE. 
31  *
32  * Author: Adam Dunkels <adam@sics.se>
33  *
34  * $Id: tapdev.c,v 1.7.2.1 2003/10/07 13:23:19 adam Exp $
35  */
36
37
38 #include <fcntl.h>
39 #include <stdlib.h>
40 #include <stdio.h>
41 #include <unistd.h>
42 #include <string.h>
43 #include <sys/ioctl.h>
44 #include <sys/socket.h>
45 #include <sys/types.h>
46 #include <sys/time.h>
47 #include <sys/uio.h>
48 #include <sys/socket.h>
49
50 #ifdef linux
51 #include <sys/ioctl.h>
52 #include <linux/if.h>
53 #include <linux/if_tun.h>
54 #define DEVTAP "/dev/net/tun"
55 #else  /* linux */
56 #define DEVTAP "/dev/tap0"
57 #endif /* linux */
58
59 #include "uip.h"
60
61 static int fd;
62
63 static unsigned long lasttime;
64 static struct timezone tz;
65
66 /*-----------------------------------------------------------------------------------*/
67 void
68 tapdev_init(void)
69 {
70   char buf[1024];
71   
72   fd = open(DEVTAP, O_RDWR);
73   if(fd == -1) {
74     perror("tapdev: tapdev_init: open");
75     exit(1);
76   }
77
78 #ifdef linux
79   {
80     struct ifreq ifr;
81     memset(&ifr, 0, sizeof(ifr));
82     ifr.ifr_flags = IFF_TAP|IFF_NO_PI;
83     if (ioctl(fd, TUNSETIFF, (void *) &ifr) < 0) {
84       perror(buf);
85       exit(1);
86     }
87   }
88 #endif /* Linux */
89
90   snprintf(buf, sizeof(buf), "ifconfig tap0 inet %d.%d.%d.%d",
91            UIP_DRIPADDR0, UIP_DRIPADDR1, UIP_DRIPADDR2, UIP_DRIPADDR3);
92   system(buf);
93
94   lasttime = 0;
95 }
96
97 void dump_mem(int type, int len)
98 {
99 #if DUMP == 1
100         int i;
101         for(i = 0; i < len; i++)
102                 printf("%c", uip_buf[i]);
103         if(type)
104         {
105                 printf("\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01");
106                 printf("\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01\01");
107         } else {
108                 printf("\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02");
109                 printf("\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02\02");
110         }
111         fflush(stdout);
112 #endif
113 }
114
115 /*-----------------------------------------------------------------------------------*/
116 unsigned int
117 tapdev_read(void)
118 {
119   fd_set fdset;
120   struct timeval tv, now;
121   int ret;
122   
123   if(lasttime >= 500000) {
124     lasttime = 0;
125     return 0;
126   }
127   
128   tv.tv_sec = 0;
129   tv.tv_usec = 500000 - lasttime;
130
131
132   FD_ZERO(&fdset);
133   FD_SET(fd, &fdset);
134
135   gettimeofday(&now, &tz);  
136   ret = select(fd + 1, &fdset, NULL, NULL, &tv);
137   if(ret == 0) {
138     lasttime = 0;    
139     return 0;
140   } 
141   ret = read(fd, uip_buf, UIP_BUFSIZE);  
142   if(ret == -1) {
143     perror("tap_dev: tapdev_read: read");
144   }
145   gettimeofday(&tv, &tz);
146   lasttime += (tv.tv_sec - now.tv_sec) * 1000000 + (tv.tv_usec - now.tv_usec);
147   dump_mem(0, ret);
148   return ret;
149 }
150 /*-----------------------------------------------------------------------------------*/
151 void
152 tapdev_send(void)
153 {
154   int ret;
155   struct iovec iov[2];
156   
157 #ifdef linux
158   {
159     char tmpbuf[UIP_BUFSIZE];
160     int i;
161
162     for(i = 0; i < 40 + UIP_LLH_LEN; i++) {
163       tmpbuf[i] = uip_buf[i];
164     }
165     
166     for(; i < uip_len; i++) {
167       tmpbuf[i] = uip_appdata[i - 40 - UIP_LLH_LEN];
168     }
169     
170     ret = write(fd, tmpbuf, uip_len);
171   }  
172 #else 
173
174   if(uip_len < 40 + UIP_LLH_LEN) {
175     ret = write(fd, uip_buf, uip_len + UIP_LLH_LEN);
176   } else {
177     iov[0].iov_base = uip_buf;
178     iov[0].iov_len = 40 + UIP_LLH_LEN;
179     iov[1].iov_base = (char *)uip_appdata;
180     iov[1].iov_len = uip_len - (40 + UIP_LLH_LEN);  
181     
182     ret = writev(fd, iov, 2);
183   }
184 #endif
185   dump_mem(1, ret);
186
187   if(ret == -1) {
188     perror("tap_dev: tapdev_send: writev");
189     exit(1);
190   }
191 }  
192 /*-----------------------------------------------------------------------------------*/