This source file includes following definitions.
- move_addr_to_kernel
- move_addr_to_user
- get_fd
- toss_fd
- socki_lookup
- sockfd_lookup
- sock_alloc
- sock_release_peer
- sock_release
- sock_lseek
- sock_read
- sock_write
- sock_readdir
- sock_ioctl
- sock_select
- sock_close
- sock_awaitconn
- sock_socket
- sock_socketpair
- sock_bind
- sock_listen
- sock_accept
- sock_connect
- sock_getsockname
- sock_getpeername
- sock_send
- sock_sendto
- sock_recv
- sock_recvfrom
- sock_setsockopt
- sock_getsockopt
- sock_shutdown
- sock_fcntl
- sys_socketcall
- sock_register
- proto_init
- sock_init
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37 #include <linux/config.h>
38 #include <linux/signal.h>
39 #include <linux/errno.h>
40 #include <linux/sched.h>
41 #include <linux/kernel.h>
42 #include <linux/major.h>
43 #include <linux/stat.h>
44 #include <linux/socket.h>
45 #include <linux/fcntl.h>
46 #include <linux/net.h>
47 #include <linux/interrupt.h>
48 #include <linux/netdevice.h>
49
50 #include <asm/system.h>
51 #include <asm/segment.h>
52
53 static int sock_lseek(struct inode *inode, struct file *file, off_t offset,
54 int whence);
55 static int sock_read(struct inode *inode, struct file *file, char *buf,
56 int size);
57 static int sock_write(struct inode *inode, struct file *file, char *buf,
58 int size);
59 static int sock_readdir(struct inode *inode, struct file *file,
60 struct dirent *dirent, int count);
61 static void sock_close(struct inode *inode, struct file *file);
62 static int sock_select(struct inode *inode, struct file *file, int which, select_table *seltable);
63 static int sock_ioctl(struct inode *inode, struct file *file,
64 unsigned int cmd, unsigned long arg);
65
66
67
68
69
70
71
72 static struct file_operations socket_file_ops = {
73 sock_lseek,
74 sock_read,
75 sock_write,
76 sock_readdir,
77 sock_select,
78 sock_ioctl,
79 NULL,
80 NULL,
81 sock_close
82 };
83
84
85
86
87 static struct socket sockets[NSOCKETS];
88
89
90
91 static struct wait_queue *socket_wait_free = NULL;
92
93
94
95 static struct proto_ops *pops[NPROTO];
96
97 #define last_socket (sockets + NSOCKETS - 1)
98
99
100
101
102
103
104
105 #define MAX_SOCK_ADDR 128
106
107 static int move_addr_to_kernel(void *uaddr, int ulen, void *kaddr)
108 {
109 int err;
110 if(ulen<0||ulen>MAX_SOCK_ADDR)
111 return -EINVAL;
112 if(ulen==0)
113 return 0;
114 if((err=verify_area(VERIFY_READ,uaddr,ulen))<0)
115 return err;
116 memcpy_fromfs(kaddr,uaddr,ulen);
117 return 0;
118 }
119
120 static int move_addr_to_user(void *kaddr, int klen, void *uaddr, int *ulen)
121 {
122 int err;
123 int len;
124
125
126 if((err=verify_area(VERIFY_WRITE,ulen,sizeof(*ulen)))<0)
127 return err;
128 len=get_fs_long(ulen);
129 if(len>klen)
130 len=klen;
131 if(len<0 || len> MAX_SOCK_ADDR)
132 return -EINVAL;
133 if(len)
134 {
135 if((err=verify_area(VERIFY_WRITE,uaddr,len))<0)
136 return err;
137 memcpy_tofs(uaddr,kaddr,len);
138 }
139 put_fs_long(len,ulen);
140 return 0;
141 }
142
143
144
145
146
147 static int get_fd(struct inode *inode)
148 {
149 int fd;
150 struct file *file;
151
152
153
154
155
156 file = get_empty_filp();
157 if (!file)
158 return(-1);
159
160 for (fd = 0; fd < NR_OPEN; ++fd)
161 if (!current->files->fd[fd])
162 break;
163 if (fd == NR_OPEN)
164 {
165 file->f_count = 0;
166 return(-1);
167 }
168
169 FD_CLR(fd, ¤t->files->close_on_exec);
170 current->files->fd[fd] = file;
171 file->f_op = &socket_file_ops;
172 file->f_mode = 3;
173 file->f_flags = O_RDWR;
174 file->f_count = 1;
175 file->f_inode = inode;
176 if (inode)
177 inode->i_count++;
178 file->f_pos = 0;
179 return(fd);
180 }
181
182
183
184
185
186
187
188
189 static inline void toss_fd(int fd)
190 {
191 sys_close(fd);
192 }
193
194
195
196
197
198 struct socket *socki_lookup(struct inode *inode)
199 {
200 struct socket *sock;
201
202 if ((sock = inode->i_socket) != NULL)
203 {
204 if (sock->state != SS_FREE && SOCK_INODE(sock) == inode)
205 return sock;
206 printk("socket.c: uhhuh. stale inode->i_socket pointer\n");
207 }
208 for (sock = sockets; sock <= last_socket; ++sock)
209 if (sock->state != SS_FREE && SOCK_INODE(sock) == inode)
210 {
211 printk("socket.c: uhhuh. Found socket despite no inode->i_socket pointer\n");
212 return(sock);
213 }
214 return(NULL);
215 }
216
217
218
219
220
221 static inline struct socket *sockfd_lookup(int fd, struct file **pfile)
222 {
223 struct file *file;
224
225 if (fd < 0 || fd >= NR_OPEN || !(file = current->files->fd[fd]))
226 return(NULL);
227
228 if (pfile)
229 *pfile = file;
230
231 return(socki_lookup(file->f_inode));
232 }
233
234
235
236
237
238 static struct socket *sock_alloc(int wait)
239 {
240 struct socket *sock;
241
242 while (1)
243 {
244 cli();
245 for (sock = sockets; sock <= last_socket; ++sock)
246 {
247 if (sock->state == SS_FREE)
248 {
249
250
251
252 sock->state = SS_UNCONNECTED;
253 sti();
254 sock->flags = 0;
255 sock->ops = NULL;
256 sock->data = NULL;
257 sock->conn = NULL;
258 sock->iconn = NULL;
259
260
261
262
263
264
265
266 if (!(SOCK_INODE(sock) = get_empty_inode()))
267 {
268 printk("NET: sock_alloc: no more inodes\n");
269 sock->state = SS_FREE;
270 return(NULL);
271 }
272 SOCK_INODE(sock)->i_mode = S_IFSOCK;
273 SOCK_INODE(sock)->i_uid = current->euid;
274 SOCK_INODE(sock)->i_gid = current->egid;
275 SOCK_INODE(sock)->i_socket = sock;
276
277 sock->wait = &SOCK_INODE(sock)->i_wait;
278 return(sock);
279 }
280 }
281 sti();
282
283
284
285 if (!wait)
286 return(NULL);
287
288
289
290 interruptible_sleep_on(&socket_wait_free);
291
292
293
294 if (current->signal & ~current->blocked)
295 {
296 return(NULL);
297 }
298 }
299 }
300
301
302
303
304
305 static inline void sock_release_peer(struct socket *peer)
306 {
307 peer->state = SS_DISCONNECTING;
308 wake_up_interruptible(peer->wait);
309 }
310
311
312 static void sock_release(struct socket *sock)
313 {
314 int oldstate;
315 struct inode *inode;
316 struct socket *peersock, *nextsock;
317
318 if ((oldstate = sock->state) != SS_UNCONNECTED)
319 sock->state = SS_DISCONNECTING;
320
321
322
323
324
325 for (peersock = sock->iconn; peersock; peersock = nextsock)
326 {
327 nextsock = peersock->next;
328 sock_release_peer(peersock);
329 }
330
331
332
333
334
335
336 peersock = (oldstate == SS_CONNECTED) ? sock->conn : NULL;
337 if (sock->ops)
338 sock->ops->release(sock, peersock);
339 if (peersock)
340 sock_release_peer(peersock);
341 inode = SOCK_INODE(sock);
342 sock->state = SS_FREE;
343
344
345
346
347 wake_up_interruptible(&socket_wait_free);
348
349
350
351
352
353 iput(inode);
354 }
355
356
357
358
359
360 static int sock_lseek(struct inode *inode, struct file *file, off_t offset, int whence)
361 {
362 return(-ESPIPE);
363 }
364
365
366
367
368
369
370 static int sock_read(struct inode *inode, struct file *file, char *ubuf, int size)
371 {
372 struct socket *sock;
373 int err;
374
375 if (!(sock = socki_lookup(inode)))
376 {
377 printk("NET: sock_read: can't find socket for inode!\n");
378 return(-EBADF);
379 }
380 if (sock->flags & SO_ACCEPTCON)
381 return(-EINVAL);
382
383 if(size<0)
384 return -EINVAL;
385 if(size==0)
386 return 0;
387 if ((err=verify_area(VERIFY_WRITE,ubuf,size))<0)
388 return err;
389 return(sock->ops->read(sock, ubuf, size, (file->f_flags & O_NONBLOCK)));
390 }
391
392
393
394
395
396
397 static int sock_write(struct inode *inode, struct file *file, char *ubuf, int size)
398 {
399 struct socket *sock;
400 int err;
401
402 if (!(sock = socki_lookup(inode)))
403 {
404 printk("NET: sock_write: can't find socket for inode!\n");
405 return(-EBADF);
406 }
407
408 if (sock->flags & SO_ACCEPTCON)
409 return(-EINVAL);
410
411 if(size<0)
412 return -EINVAL;
413 if(size==0)
414 return 0;
415
416 if ((err=verify_area(VERIFY_READ,ubuf,size))<0)
417 return err;
418 return(sock->ops->write(sock, ubuf, size,(file->f_flags & O_NONBLOCK)));
419 }
420
421
422
423
424
425 static int sock_readdir(struct inode *inode, struct file *file, struct dirent *dirent,
426 int count)
427 {
428 return(-EBADF);
429 }
430
431
432
433
434
435
436 int sock_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
437 unsigned long arg)
438 {
439 struct socket *sock;
440
441 if (!(sock = socki_lookup(inode)))
442 {
443 printk("NET: sock_ioctl: can't find socket for inode!\n");
444 return(-EBADF);
445 }
446 return(sock->ops->ioctl(sock, cmd, arg));
447 }
448
449
450 static int sock_select(struct inode *inode, struct file *file, int sel_type, select_table * wait)
451 {
452 struct socket *sock;
453
454 if (!(sock = socki_lookup(inode)))
455 {
456 printk("NET: sock_select: can't find socket for inode!\n");
457 return(0);
458 }
459
460
461
462
463
464 if (sock->ops && sock->ops->select)
465 return(sock->ops->select(sock, sel_type, wait));
466 return(0);
467 }
468
469
470 void sock_close(struct inode *inode, struct file *file)
471 {
472 struct socket *sock;
473
474
475
476
477
478 if (!inode)
479 return;
480
481 if (!(sock = socki_lookup(inode)))
482 {
483 printk("NET: sock_close: can't find socket for inode!\n");
484 return;
485 }
486
487 sock_release(sock);
488 }
489
490
491
492
493
494 int sock_awaitconn(struct socket *mysock, struct socket *servsock)
495 {
496 struct socket *last;
497
498
499
500
501 if (!(servsock->flags & SO_ACCEPTCON))
502 {
503 return(-EINVAL);
504 }
505
506
507
508
509
510 mysock->next = NULL;
511 cli();
512 if (!(last = servsock->iconn))
513 servsock->iconn = mysock;
514 else
515 {
516 while (last->next)
517 last = last->next;
518 last->next = mysock;
519 }
520 mysock->state = SS_CONNECTING;
521 mysock->conn = servsock;
522 sti();
523
524
525
526
527
528 wake_up_interruptible(servsock->wait);
529 if (mysock->state != SS_CONNECTED)
530 {
531 interruptible_sleep_on(mysock->wait);
532 if (mysock->state != SS_CONNECTED &&
533 mysock->state != SS_DISCONNECTING)
534 {
535
536
537
538
539
540
541
542 if (mysock->conn == servsock)
543 {
544 cli();
545 if ((last = servsock->iconn) == mysock)
546 servsock->iconn = mysock->next;
547 else
548 {
549 while (last->next != mysock)
550 last = last->next;
551 last->next = mysock->next;
552 }
553 sti();
554 }
555 return(mysock->conn ? -EINTR : -EACCES);
556 }
557 }
558 return(0);
559 }
560
561
562
563
564
565
566
567 static int sock_socket(int family, int type, int protocol)
568 {
569 int i, fd;
570 struct socket *sock;
571 struct proto_ops *ops;
572
573
574 for (i = 0; i < NPROTO; ++i)
575 {
576 if (pops[i] == NULL) continue;
577 if (pops[i]->family == family)
578 break;
579 }
580
581 if (i == NPROTO)
582 {
583 return -EINVAL;
584 }
585
586 ops = pops[i];
587
588
589
590
591
592
593
594 if ((type != SOCK_STREAM && type != SOCK_DGRAM &&
595 type != SOCK_SEQPACKET && type != SOCK_RAW &&
596 type != SOCK_PACKET) || protocol < 0)
597 return(-EINVAL);
598
599
600
601
602
603
604
605 if (!(sock = sock_alloc(1)))
606 {
607 printk("sock_socket: no more sockets\n");
608 return(-EAGAIN);
609 }
610
611 sock->type = type;
612 sock->ops = ops;
613 if ((i = sock->ops->create(sock, protocol)) < 0)
614 {
615 sock_release(sock);
616 return(i);
617 }
618
619 if ((fd = get_fd(SOCK_INODE(sock))) < 0)
620 {
621 sock_release(sock);
622 return(-EINVAL);
623 }
624
625 return(fd);
626 }
627
628
629
630
631
632 static int sock_socketpair(int family, int type, int protocol, unsigned long usockvec[2])
633 {
634 int fd1, fd2, i;
635 struct socket *sock1, *sock2;
636 int er;
637
638
639
640
641
642
643 if ((fd1 = sock_socket(family, type, protocol)) < 0)
644 return(fd1);
645 sock1 = sockfd_lookup(fd1, NULL);
646 if (!sock1->ops->socketpair)
647 {
648 sys_close(fd1);
649 return(-EINVAL);
650 }
651
652
653
654
655
656 if ((fd2 = sock_socket(family, type, protocol)) < 0)
657 {
658 sys_close(fd1);
659 return(-EINVAL);
660 }
661
662 sock2 = sockfd_lookup(fd2, NULL);
663 if ((i = sock1->ops->socketpair(sock1, sock2)) < 0)
664 {
665 sys_close(fd1);
666 sys_close(fd2);
667 return(i);
668 }
669
670 sock1->conn = sock2;
671 sock2->conn = sock1;
672 sock1->state = SS_CONNECTED;
673 sock2->state = SS_CONNECTED;
674
675 er=verify_area(VERIFY_WRITE, usockvec, 2 * sizeof(int));
676 if(er)
677 return er;
678 put_fs_long(fd1, &usockvec[0]);
679 put_fs_long(fd2, &usockvec[1]);
680
681 return(0);
682 }
683
684
685
686
687
688
689
690
691
692
693 static int sock_bind(int fd, struct sockaddr *umyaddr, int addrlen)
694 {
695 struct socket *sock;
696 int i;
697 char address[MAX_SOCK_ADDR];
698 int err;
699
700 if (fd < 0 || fd >= NR_OPEN || current->files->fd[fd] == NULL)
701 return(-EBADF);
702
703 if (!(sock = sockfd_lookup(fd, NULL)))
704 return(-ENOTSOCK);
705
706 if((err=move_addr_to_kernel(umyaddr,addrlen,address))<0)
707 return err;
708
709 if ((i = sock->ops->bind(sock, (struct sockaddr *)address, addrlen)) < 0)
710 {
711 return(i);
712 }
713 return(0);
714 }
715
716
717
718
719
720
721
722
723 static int sock_listen(int fd, int backlog)
724 {
725 struct socket *sock;
726
727 if (fd < 0 || fd >= NR_OPEN || current->files->fd[fd] == NULL)
728 return(-EBADF);
729 if (!(sock = sockfd_lookup(fd, NULL)))
730 return(-ENOTSOCK);
731
732 if (sock->state != SS_UNCONNECTED)
733 {
734 return(-EINVAL);
735 }
736
737 if (sock->ops && sock->ops->listen)
738 sock->ops->listen(sock, backlog);
739 sock->flags |= SO_ACCEPTCON;
740 return(0);
741 }
742
743
744
745
746
747
748
749
750
751
752 static int sock_accept(int fd, struct sockaddr *upeer_sockaddr, int *upeer_addrlen)
753 {
754 struct file *file;
755 struct socket *sock, *newsock;
756 int i;
757 char address[MAX_SOCK_ADDR];
758 int len;
759
760 if (fd < 0 || fd >= NR_OPEN || ((file = current->files->fd[fd]) == NULL))
761 return(-EBADF);
762 if (!(sock = sockfd_lookup(fd, &file)))
763 return(-ENOTSOCK);
764 if (sock->state != SS_UNCONNECTED)
765 {
766 return(-EINVAL);
767 }
768 if (!(sock->flags & SO_ACCEPTCON))
769 {
770 return(-EINVAL);
771 }
772
773 if (!(newsock = sock_alloc(0)))
774 {
775 printk("NET: sock_accept: no more sockets\n");
776 return(-EAGAIN);
777 }
778 newsock->type = sock->type;
779 newsock->ops = sock->ops;
780 if ((i = sock->ops->dup(newsock, sock)) < 0)
781 {
782 sock_release(newsock);
783 return(i);
784 }
785
786 i = newsock->ops->accept(sock, newsock, file->f_flags);
787 if ( i < 0)
788 {
789 sock_release(newsock);
790 return(i);
791 }
792
793 if ((fd = get_fd(SOCK_INODE(newsock))) < 0)
794 {
795 sock_release(newsock);
796 return(-EINVAL);
797 }
798
799 if (upeer_sockaddr)
800 {
801 newsock->ops->getname(newsock, (struct sockaddr *)address, &len, 1);
802 move_addr_to_user(address,len, upeer_sockaddr, upeer_addrlen);
803 }
804 return(fd);
805 }
806
807
808
809
810
811
812
813 static int sock_connect(int fd, struct sockaddr *uservaddr, int addrlen)
814 {
815 struct socket *sock;
816 struct file *file;
817 int i;
818 char address[MAX_SOCK_ADDR];
819 int err;
820
821 if (fd < 0 || fd >= NR_OPEN || (file=current->files->fd[fd]) == NULL)
822 return(-EBADF);
823 if (!(sock = sockfd_lookup(fd, &file)))
824 return(-ENOTSOCK);
825
826 if((err=move_addr_to_kernel(uservaddr,addrlen,address))<0)
827 return err;
828
829 switch(sock->state)
830 {
831 case SS_UNCONNECTED:
832
833 break;
834 case SS_CONNECTED:
835
836 if(sock->type == SOCK_DGRAM)
837 break;
838 return -EISCONN;
839 case SS_CONNECTING:
840
841
842
843
844
845
846
847 return(sock->ops->connect(sock, uservaddr,
848 addrlen, file->f_flags));
849 default:
850 return(-EINVAL);
851 }
852 i = sock->ops->connect(sock, (struct sockaddr *)address, addrlen, file->f_flags);
853 if (i < 0)
854 {
855 return(i);
856 }
857 return(0);
858 }
859
860
861
862
863
864
865 static int sock_getsockname(int fd, struct sockaddr *usockaddr, int *usockaddr_len)
866 {
867 struct socket *sock;
868 char address[MAX_SOCK_ADDR];
869 int len;
870 int err;
871
872 if (fd < 0 || fd >= NR_OPEN || current->files->fd[fd] == NULL)
873 return(-EBADF);
874 if (!(sock = sockfd_lookup(fd, NULL)))
875 return(-ENOTSOCK);
876
877 err=sock->ops->getname(sock, (struct sockaddr *)address, &len, 0);
878 if(err)
879 return err;
880 if((err=move_addr_to_user(address,len, usockaddr, usockaddr_len))<0)
881 return err;
882 return 0;
883 }
884
885
886
887
888
889
890 static int sock_getpeername(int fd, struct sockaddr *usockaddr, int *usockaddr_len)
891 {
892 struct socket *sock;
893 char address[MAX_SOCK_ADDR];
894 int len;
895 int err;
896
897 if (fd < 0 || fd >= NR_OPEN || current->files->fd[fd] == NULL)
898 return(-EBADF);
899 if (!(sock = sockfd_lookup(fd, NULL)))
900 return(-ENOTSOCK);
901
902 err=sock->ops->getname(sock, (struct sockaddr *)address, &len, 1);
903 if(err)
904 return err;
905 if((err=move_addr_to_user(address,len, usockaddr, usockaddr_len))<0)
906 return err;
907 return 0;
908 }
909
910
911
912
913
914
915 static int sock_send(int fd, void * buff, int len, unsigned flags)
916 {
917 struct socket *sock;
918 struct file *file;
919 int err;
920
921 if (fd < 0 || fd >= NR_OPEN || ((file = current->files->fd[fd]) == NULL))
922 return(-EBADF);
923 if (!(sock = sockfd_lookup(fd, NULL)))
924 return(-ENOTSOCK);
925
926 if(len<0)
927 return -EINVAL;
928 err=verify_area(VERIFY_READ, buff, len);
929 if(err)
930 return err;
931 return(sock->ops->send(sock, buff, len, (file->f_flags & O_NONBLOCK), flags));
932 }
933
934
935
936
937
938
939
940 static int sock_sendto(int fd, void * buff, int len, unsigned flags,
941 struct sockaddr *addr, int addr_len)
942 {
943 struct socket *sock;
944 struct file *file;
945 char address[MAX_SOCK_ADDR];
946 int err;
947
948 if (fd < 0 || fd >= NR_OPEN || ((file = current->files->fd[fd]) == NULL))
949 return(-EBADF);
950 if (!(sock = sockfd_lookup(fd, NULL)))
951 return(-ENOTSOCK);
952
953 if(len<0)
954 return -EINVAL;
955 err=verify_area(VERIFY_READ,buff,len);
956 if(err)
957 return err;
958
959 if((err=move_addr_to_kernel(addr,addr_len,address))<0)
960 return err;
961
962 return(sock->ops->sendto(sock, buff, len, (file->f_flags & O_NONBLOCK),
963 flags, (struct sockaddr *)address, addr_len));
964 }
965
966
967
968
969
970
971
972
973
974
975 static int sock_recv(int fd, void * buff, int len, unsigned flags)
976 {
977 struct socket *sock;
978 struct file *file;
979 int err;
980
981 if (fd < 0 || fd >= NR_OPEN || ((file = current->files->fd[fd]) == NULL))
982 return(-EBADF);
983
984 if (!(sock = sockfd_lookup(fd, NULL)))
985 return(-ENOTSOCK);
986
987 if(len<0)
988 return -EINVAL;
989 if(len==0)
990 return 0;
991 err=verify_area(VERIFY_WRITE, buff, len);
992 if(err)
993 return err;
994
995 return(sock->ops->recv(sock, buff, len,(file->f_flags & O_NONBLOCK), flags));
996 }
997
998
999
1000
1001
1002
1003
1004 static int sock_recvfrom(int fd, void * buff, int len, unsigned flags,
1005 struct sockaddr *addr, int *addr_len)
1006 {
1007 struct socket *sock;
1008 struct file *file;
1009 char address[MAX_SOCK_ADDR];
1010 int err;
1011 int alen;
1012 if (fd < 0 || fd >= NR_OPEN || ((file = current->files->fd[fd]) == NULL))
1013 return(-EBADF);
1014 if (!(sock = sockfd_lookup(fd, NULL)))
1015 return(-ENOTSOCK);
1016 if(len<0)
1017 return -EINVAL;
1018 if(len==0)
1019 return 0;
1020
1021 err=verify_area(VERIFY_WRITE,buff,len);
1022 if(err)
1023 return err;
1024
1025 len=sock->ops->recvfrom(sock, buff, len, (file->f_flags & O_NONBLOCK),
1026 flags, (struct sockaddr *)address, &alen);
1027
1028 if(len<0)
1029 return len;
1030 if(addr!=NULL && (err=move_addr_to_user(address,alen, addr, addr_len))<0)
1031 return err;
1032
1033 return len;
1034 }
1035
1036
1037
1038
1039
1040
1041 static int sock_setsockopt(int fd, int level, int optname, char *optval, int optlen)
1042 {
1043 struct socket *sock;
1044 struct file *file;
1045
1046 if (fd < 0 || fd >= NR_OPEN || ((file = current->files->fd[fd]) == NULL))
1047 return(-EBADF);
1048 if (!(sock = sockfd_lookup(fd, NULL)))
1049 return(-ENOTSOCK);
1050
1051 return(sock->ops->setsockopt(sock, level, optname, optval, optlen));
1052 }
1053
1054
1055
1056
1057
1058
1059 static int sock_getsockopt(int fd, int level, int optname, char *optval, int *optlen)
1060 {
1061 struct socket *sock;
1062 struct file *file;
1063
1064 if (fd < 0 || fd >= NR_OPEN || ((file = current->files->fd[fd]) == NULL))
1065 return(-EBADF);
1066 if (!(sock = sockfd_lookup(fd, NULL)))
1067 return(-ENOTSOCK);
1068
1069 if (!sock->ops || !sock->ops->getsockopt)
1070 return(0);
1071 return(sock->ops->getsockopt(sock, level, optname, optval, optlen));
1072 }
1073
1074
1075
1076
1077
1078
1079 static int sock_shutdown(int fd, int how)
1080 {
1081 struct socket *sock;
1082 struct file *file;
1083
1084 if (fd < 0 || fd >= NR_OPEN || ((file = current->files->fd[fd]) == NULL))
1085 return(-EBADF);
1086 if (!(sock = sockfd_lookup(fd, NULL)))
1087 return(-ENOTSOCK);
1088
1089 return(sock->ops->shutdown(sock, how));
1090 }
1091
1092
1093
1094
1095
1096
1097 int sock_fcntl(struct file *filp, unsigned int cmd, unsigned long arg)
1098 {
1099 struct socket *sock;
1100
1101 sock = socki_lookup (filp->f_inode);
1102 if (sock != NULL && sock->ops != NULL && sock->ops->fcntl != NULL)
1103 return(sock->ops->fcntl(sock, cmd, arg));
1104 return(-EINVAL);
1105 }
1106
1107
1108
1109
1110
1111
1112
1113
1114
1115
1116
1117
1118 asmlinkage int sys_socketcall(int call, unsigned long *args)
1119 {
1120 int er;
1121 switch(call)
1122 {
1123 case SYS_SOCKET:
1124 er=verify_area(VERIFY_READ, args, 3 * sizeof(long));
1125 if(er)
1126 return er;
1127 return(sock_socket(get_fs_long(args+0),
1128 get_fs_long(args+1),
1129 get_fs_long(args+2)));
1130 case SYS_BIND:
1131 er=verify_area(VERIFY_READ, args, 3 * sizeof(long));
1132 if(er)
1133 return er;
1134 return(sock_bind(get_fs_long(args+0),
1135 (struct sockaddr *)get_fs_long(args+1),
1136 get_fs_long(args+2)));
1137 case SYS_CONNECT:
1138 er=verify_area(VERIFY_READ, args, 3 * sizeof(long));
1139 if(er)
1140 return er;
1141 return(sock_connect(get_fs_long(args+0),
1142 (struct sockaddr *)get_fs_long(args+1),
1143 get_fs_long(args+2)));
1144 case SYS_LISTEN:
1145 er=verify_area(VERIFY_READ, args, 2 * sizeof(long));
1146 if(er)
1147 return er;
1148 return(sock_listen(get_fs_long(args+0),
1149 get_fs_long(args+1)));
1150 case SYS_ACCEPT:
1151 er=verify_area(VERIFY_READ, args, 3 * sizeof(long));
1152 if(er)
1153 return er;
1154 return(sock_accept(get_fs_long(args+0),
1155 (struct sockaddr *)get_fs_long(args+1),
1156 (int *)get_fs_long(args+2)));
1157 case SYS_GETSOCKNAME:
1158 er=verify_area(VERIFY_READ, args, 3 * sizeof(long));
1159 if(er)
1160 return er;
1161 return(sock_getsockname(get_fs_long(args+0),
1162 (struct sockaddr *)get_fs_long(args+1),
1163 (int *)get_fs_long(args+2)));
1164 case SYS_GETPEERNAME:
1165 er=verify_area(VERIFY_READ, args, 3 * sizeof(long));
1166 if(er)
1167 return er;
1168 return(sock_getpeername(get_fs_long(args+0),
1169 (struct sockaddr *)get_fs_long(args+1),
1170 (int *)get_fs_long(args+2)));
1171 case SYS_SOCKETPAIR:
1172 er=verify_area(VERIFY_READ, args, 4 * sizeof(long));
1173 if(er)
1174 return er;
1175 return(sock_socketpair(get_fs_long(args+0),
1176 get_fs_long(args+1),
1177 get_fs_long(args+2),
1178 (unsigned long *)get_fs_long(args+3)));
1179 case SYS_SEND:
1180 er=verify_area(VERIFY_READ, args, 4 * sizeof(unsigned long));
1181 if(er)
1182 return er;
1183 return(sock_send(get_fs_long(args+0),
1184 (void *)get_fs_long(args+1),
1185 get_fs_long(args+2),
1186 get_fs_long(args+3)));
1187 case SYS_SENDTO:
1188 er=verify_area(VERIFY_READ, args, 6 * sizeof(unsigned long));
1189 if(er)
1190 return er;
1191 return(sock_sendto(get_fs_long(args+0),
1192 (void *)get_fs_long(args+1),
1193 get_fs_long(args+2),
1194 get_fs_long(args+3),
1195 (struct sockaddr *)get_fs_long(args+4),
1196 get_fs_long(args+5)));
1197 case SYS_RECV:
1198 er=verify_area(VERIFY_READ, args, 4 * sizeof(unsigned long));
1199 if(er)
1200 return er;
1201 return(sock_recv(get_fs_long(args+0),
1202 (void *)get_fs_long(args+1),
1203 get_fs_long(args+2),
1204 get_fs_long(args+3)));
1205 case SYS_RECVFROM:
1206 er=verify_area(VERIFY_READ, args, 6 * sizeof(unsigned long));
1207 if(er)
1208 return er;
1209 return(sock_recvfrom(get_fs_long(args+0),
1210 (void *)get_fs_long(args+1),
1211 get_fs_long(args+2),
1212 get_fs_long(args+3),
1213 (struct sockaddr *)get_fs_long(args+4),
1214 (int *)get_fs_long(args+5)));
1215 case SYS_SHUTDOWN:
1216 er=verify_area(VERIFY_READ, args, 2* sizeof(unsigned long));
1217 if(er)
1218 return er;
1219 return(sock_shutdown(get_fs_long(args+0),
1220 get_fs_long(args+1)));
1221 case SYS_SETSOCKOPT:
1222 er=verify_area(VERIFY_READ, args, 5*sizeof(unsigned long));
1223 if(er)
1224 return er;
1225 return(sock_setsockopt(get_fs_long(args+0),
1226 get_fs_long(args+1),
1227 get_fs_long(args+2),
1228 (char *)get_fs_long(args+3),
1229 get_fs_long(args+4)));
1230 case SYS_GETSOCKOPT:
1231 er=verify_area(VERIFY_READ, args, 5*sizeof(unsigned long));
1232 if(er)
1233 return er;
1234 return(sock_getsockopt(get_fs_long(args+0),
1235 get_fs_long(args+1),
1236 get_fs_long(args+2),
1237 (char *)get_fs_long(args+3),
1238 (int *)get_fs_long(args+4)));
1239 default:
1240 return(-EINVAL);
1241 }
1242 }
1243
1244
1245
1246
1247
1248
1249
1250 int sock_register(int family, struct proto_ops *ops)
1251 {
1252 int i;
1253
1254 cli();
1255 for(i = 0; i < NPROTO; i++)
1256 {
1257 if (pops[i] != NULL)
1258 continue;
1259 pops[i] = ops;
1260 pops[i]->family = family;
1261 sti();
1262 return(i);
1263 }
1264 sti();
1265 return(-ENOMEM);
1266 }
1267
1268 void proto_init(void)
1269 {
1270 extern struct net_proto protocols[];
1271 struct net_proto *pro;
1272
1273
1274 pro = protocols;
1275 while (pro->name != NULL)
1276 {
1277 (*pro->init_func)(pro);
1278 pro++;
1279 }
1280
1281 }
1282
1283
1284 void sock_init(void)
1285 {
1286 struct socket *sock;
1287 int i;
1288
1289 printk("Swansea University Computer Society NET3.016\n");
1290
1291
1292
1293
1294 for (sock = sockets; sock <= last_socket; ++sock)
1295 sock->state = SS_FREE;
1296
1297
1298
1299
1300
1301 for (i = 0; i < NPROTO; ++i) pops[i] = NULL;
1302
1303
1304
1305
1306
1307 proto_init();
1308
1309 #ifdef CONFIG_NET
1310
1311
1312
1313
1314 dev_init();
1315
1316
1317
1318
1319
1320 bh_base[NET_BH].routine= net_bh;
1321 #endif
1322
1323 }