|
|
1.1 root 1: /******************************************************************************
2: * Copyright (c) 2004, 2008 IBM Corporation
3: * All rights reserved.
4: * This program and the accompanying materials
5: * are made available under the terms of the BSD License
6: * which accompanies this distribution, and is available at
7: * http://www.opensource.org/licenses/bsd-license.php
8: *
9: * Contributors:
10: * IBM Corporation - initial implementation
11: *****************************************************************************/
12:
13:
14: #include <of.h>
15: #include <systemcall.h>
16: #include <stdarg.h>
17: #include <netdriver_int.h>
18: #include <string.h>
19: #include <fileio.h>
20:
21: //extern ihandle_t fd_array[32];
22: extern snk_module_t *get_module_by_type(int type);
23: extern int vsprintf(char *, const char *, va_list);
24: extern void _exit(int status);
25:
26: int printk(const char*, ...);
27:
28: static int
29: _syscall_open(const char* name, int flags)
30: {
31: int fd, i;
32:
33: /* search free file descriptor */
34: for(fd=0; fd<FILEIO_MAX; ++fd) {
35: if(fd_array[fd].type == FILEIO_TYPE_EMPTY) {
36: break;
37: }
38: }
39: if(fd == FILEIO_MAX) {
40: printk ("Can not open \"%s\" because file descriptor list is full\n", name);
41: /* there is no free file descriptor avaliable */
42: return -2;
43: }
44:
45: for(i=0; i<MODULES_MAX; ++i) {
46: if(!snk_modules[i] || !snk_modules[i]->open) {
47: continue;
48: }
49:
50: if(snk_modules[i]->running == 0) {
51: snk_modules[i]->init();
52: }
53:
54: if(snk_modules[i]->open(&fd_array[fd], name, flags) == 0)
55: break;
56: }
57:
58: if(i==MODULES_MAX) {
59: /* file not found */
60: return -1;
61: }
62:
63: return fd;
64: }
65:
66: static int
67: _syscall_socket(int domain, int type, int proto, char *mac_addr)
68: {
69: snk_module_t *net_module;
70:
71: net_module = get_module_by_type(MOD_TYPE_NETWORK);
72: if( !net_module || !net_module->init) {
73: printk("No net_init function available");
74: return -1;
75: }
76:
77: /* Init net device driver */
78: if(net_module->running == 0) {
79: net_module->init();
80: }
81:
82: if(net_module->running == 0)
83: return -2;
84:
85: memcpy(mac_addr, &net_module->mac_addr[0], 6);
86: return 0;
87: }
88:
89: static int
90: _syscall_close(int fd)
91: {
92: if(fd < 0 || fd >= FILEIO_MAX
93: || fd_array[fd].type == FILEIO_TYPE_EMPTY
94: || fd_array[fd].close == 0)
95: return -1;
96:
97: return fd_array[fd].close(&fd_array[fd]);
98: }
99:
100: static long
101: _syscall_read (int fd, char *buf, long len)
102: {
103: if(fd < 0 || fd >= FILEIO_MAX
104: || fd_array[fd].type == FILEIO_TYPE_EMPTY
105: || fd_array[fd].read == 0)
106: return -1;
107:
108: return fd_array[fd].read(&fd_array[fd], buf, len);
109: }
110:
111: static long
112: _syscall_write (int fd, char *buf, long len)
113: {
114: char dest_buf[512];
115: char *dest_buf_ptr;
116: int i;
117: if (fd == 1 || fd == 2)
118: {
119: dest_buf_ptr = &dest_buf[0];
120: for (i = 0; i < len && i < 256; i++)
121: {
122: *dest_buf_ptr++ = *buf++;
123: if (buf[-1] == '\n')
124: *dest_buf_ptr++ = '\r';
125: }
126: len = dest_buf_ptr - &dest_buf[0];
127: buf = &dest_buf[0];
128: }
129:
130: if(fd < 0 || fd >= FILEIO_MAX
131: || fd_array[fd].type == FILEIO_TYPE_EMPTY
132: || fd_array[fd].write == 0)
133: return -1;
134:
135: return fd_array[fd].write(&fd_array[fd], buf, len);
136: }
137:
138: static long
139: _syscall_lseek (int fd, long offset, int whence)
140: {
141: return 0; // this syscall is unused !!!
142: #if 0
143: if (whence != 0)
144: return -1;
145:
146: of_seek (fd_array[fd], (unsigned int) (offset>>32), (unsigned int) (offset & 0xffffffffULL));
147:
148: return offset;
149: #endif
150: }
151:
152: static int
153: _syscall_ioctl (int fd, int request, void* data)
154: {
155: if (fd < 0
156: || fd >= FILEIO_MAX
157: || fd_array[fd].type == FILEIO_TYPE_EMPTY)
158: return -1;
159: if (!fd_array[fd].ioctl) { /* for backwards compatibility with network modules */
160: snk_module_t *net_module;
161:
162: net_module = get_module_by_type(MOD_TYPE_NETWORK);
163: if ( !net_module || !net_module->ioctl ) {
164: printk("No net_ioctl function available");
165: return -1;
166: }
167:
168: return net_module->ioctl(request, data);
169: }
170:
171: return fd_array[fd].ioctl(&fd_array[fd], request, data);
172: }
173:
174: static long
175: _syscall_recv(int fd, void *packet, int packet_len, int flags)
176: {
177: snk_module_t *net_module;
178:
179: net_module = get_module_by_type(MOD_TYPE_NETWORK);
180: if( !net_module || !net_module->read ) {
181: printk("No net_receive function available");
182: return -1;
183: }
184:
185: return net_module->read(packet, packet_len);
186: }
187:
188: static long
189: _syscall_send(int fd, void *packet, int packet_len, int flags)
190: {
191: snk_module_t *net_module;
192:
193: net_module = get_module_by_type(MOD_TYPE_NETWORK);
194: if( !net_module || !net_module->write ) {
195: printk("No net_xmit function available");
196: return -1;
197: }
198:
199: return net_module->write(packet, packet_len);
200: }
201:
202: static long
203: _syscall_sendto(int fd, void *packet, int packet_len, int flags,
204: void *sock_addr, int sock_addr_len)
205: {
206: return _syscall_send(fd, packet, packet_len, flags);
207: }
208:
209:
210:
211:
212:
213:
214:
215:
216: long
217: _system_call(long arg0, long arg1, long arg2, long arg3,
218: long arg4, long arg5, long arg6, int nr)
219: {
220: long rc = -1;
221:
222: switch (nr)
223: {
224: case _open_sc_nr:
225: rc = _syscall_open ((void *) arg0, arg1);
226: break;
227: case _read_sc_nr:
228: rc = _syscall_read (arg0, (void *) arg1, arg2);
229: break;
230: case _close_sc_nr:
231: _syscall_close (arg0);
232: break;
233: case _lseek_sc_nr:
234: rc = _syscall_lseek (arg0, arg1, arg2);
235: break;
236: case _write_sc_nr:
237: rc = _syscall_write (arg0, (void *) arg1, arg2);
238: break;
239: case _ioctl_sc_nr:
240: rc = _syscall_ioctl (arg0, arg1, (void *) arg2);
241: break;
242: case _socket_sc_nr:
243: switch (arg0)
244: {
245: case _sock_sc_nr:
246: rc = _syscall_socket (arg1, arg2, arg3, (char*) arg4);
247: break;
248: case _recv_sc_nr:
249: rc = _syscall_recv (arg1, (void *) arg2, arg3, arg4);
250: break;
251: case _send_sc_nr:
252: rc = _syscall_send (arg1, (void *) arg2, arg3, arg4);
253: break;
254: case _sendto_sc_nr:
255: rc = _syscall_sendto (arg1, (void *) arg2, arg3, arg4, (void *) arg5, arg6);
256: break;
257: default:
258: break;
259: }
260: break;
261: default:
262: break;
263: }
264:
265: return rc;
266: }
267:
268: void
269: exit(int status)
270: {
271: _exit(status);
272: }
273:
274: int
275: printk(const char* fmt, ...)
276: {
277: int count;
278: va_list ap;
279: char buffer[256];
280: va_start (ap, fmt);
281: count=vsprintf(buffer, fmt, ap);
282: _syscall_write (1, buffer, count);
283: va_end (ap);
284: return count;
285: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.