2 * This module implements the (SPP-derived) Sequenced Packet eXchange
3 * (SPX) protocol for Linux 2.1.X as specified in
4 * NetWare SPX Services Specification, Semantics and API
6 * Revision Date: February 9, 1993
9 * Jay Schulist <jschlst@samba.org>
10 * Jim Freeman <jfree@caldera.com>
13 * Alan Cox : Fixed an skb_unshare check for NULL
14 * that crashed it under load. Renamed and
15 * made static the ipx ops. Removed the hack
16 * ipx methods interface. Dropped AF_SPX - its
17 * the wrong abstraction.
18 * Eduardo Trapani : Added a check for the return value of
19 * ipx_if_offset that crashed sock_alloc_send_skb.
20 * Added spx_datagram_poll() so that select()
21 * works now on SPX sockets. Added updating
22 * of the alloc count to follow rmt_seq.
24 * This program is free software; you can redistribute it and/or
25 * modify it under the terms of the GNU General Public License
26 * as published by the Free Software Foundation; either version
27 * 2 of the License, or (at your option) any later version.
29 * None of the authors or maintainers or their employers admit
30 * liability nor provide warranty for any of this software.
31 * This material is provided "as is" and at no charge.
34 #include <linux/module.h>
38 #include <asm/byteorder.h>
39 #include <asm/uaccess.h>
40 #include <linux/uio.h>
41 #include <linux/unistd.h>
42 #include <linux/poll.h>
44 static struct proto_ops *ipx_operations;
45 static struct proto_ops spx_ops;
48 /* Functions needed for SPX connection start up */
49 static int spx_transmit(struct sock *sk,struct sk_buff *skb,int type,int len);
50 static void spx_retransmit(unsigned long data);
51 static void spx_watchdog(unsigned long data);
52 void spx_rcv(struct sock *sk, int bytes);
54 extern void ipx_remove_socket(struct sock *sk);
56 /* Datagram poll: the same code as datagram_poll() in net/core
57 but the right spx buffers are looked at and
58 there is no question on the type of the socket
60 static unsigned int spx_datagram_poll(struct file * file, struct socket *sock, poll_table *wait)
62 struct sock *sk = sock->sk;
63 struct spx_opt *pdata = &sk->tp_pinfo.af_spx;
66 poll_wait(file, sk->sleep, wait);
69 /* exceptional events? */
70 if (sk->err || !skb_queue_empty(&sk->error_queue))
72 if (sk->shutdown & RCV_SHUTDOWN)
76 if (!skb_queue_empty(&pdata->rcv_queue))
77 mask |= POLLIN | POLLRDNORM;
79 /* Need to check for termination and startup */
80 if (sk->state==TCP_CLOSE)
82 /* connection hasn't started yet? */
83 if (sk->state == TCP_SYN_SENT)
87 if (sock_writeable(sk))
88 mask |= POLLOUT | POLLWRNORM | POLLWRBAND;
90 set_bit(SOCK_ASYNC_NOSPACE,&sk->socket->flags);
95 /* Create the SPX specific data */
96 static int spx_sock_init(struct sock *sk)
98 struct spx_opt *pdata = &sk->tp_pinfo.af_spx;
100 pdata->state = SPX_CLOSED;
102 pdata->acknowledge = 0;
103 pdata->source_connid = htons(connids);
107 pdata->owner = (void *)sk;
108 pdata->sndbuf = sk->sndbuf;
110 pdata->watchdog.function = spx_watchdog;
111 pdata->watchdog.data = (unsigned long)sk;
112 pdata->wd_interval = VERIFY_TIMEOUT;
113 pdata->retransmit.function = spx_retransmit;
114 pdata->retransmit.data = (unsigned long)sk;
115 pdata->retransmits = 0;
117 pdata->max_retries = RETRY_COUNT;
119 skb_queue_head_init(&pdata->rcv_queue);
120 skb_queue_head_init(&pdata->transmit_queue);
121 skb_queue_head_init(&pdata->retransmit_queue);
126 static int spx_create(struct socket *sock, int protocol)
131 * Called on connection receive so cannot be GFP_KERNEL
134 sk = sk_alloc(PF_IPX, GFP_ATOMIC, 1);
141 sock->ops = &spx_ops;
145 return (-ESOCKTNOSUPPORT);
148 sock_init_data(sock, sk);
150 sk->data_ready = spx_rcv;
160 void spx_close_socket(struct sock *sk)
162 struct spx_opt *pdata = &sk->tp_pinfo.af_spx;
164 pdata->state = SPX_CLOSED;
165 sk->state = TCP_CLOSE;
166 del_timer(&pdata->retransmit);
167 del_timer(&pdata->watchdog);
170 void spx_destroy_socket(struct sock *sk)
172 struct spx_opt *pdata = &sk->tp_pinfo.af_spx;
175 ipx_remove_socket(sk);
176 while((skb = skb_dequeue(&sk->receive_queue)) != NULL)
178 while((skb = skb_dequeue(&pdata->transmit_queue)) != NULL)
180 while((skb = skb_dequeue(&pdata->retransmit_queue)) != NULL)
182 while((skb = skb_dequeue(&pdata->rcv_queue)) != NULL)
189 /* Release an SPX socket */
190 static int spx_release(struct socket *sock)
192 struct sock *sk = sock->sk;
193 struct spx_opt *pdata = &sk->tp_pinfo.af_spx;
198 sk->state_change(sk);
201 if(pdata->state != SPX_CLOSED)
203 spx_transmit(sk, NULL, DISCON, 0);
204 spx_close_socket(sk);
209 spx_destroy_socket(sk);
214 /* Move a socket into listening state. */
215 static int spx_listen(struct socket *sock, int backlog)
217 struct sock *sk = sock->sk;
219 if(sock->state != SS_UNCONNECTED)
221 if(sock->type != SOCK_SEQPACKET)
222 return (-EOPNOTSUPP);
226 sk->max_ack_backlog = backlog;
227 if(sk->state != TCP_LISTEN)
230 sk->state = TCP_LISTEN;
232 sk->socket->flags |= __SO_ACCEPTCON;
237 /* Accept a pending SPX connection */
238 static int spx_accept(struct socket *sock, struct socket *newsock, int flags)
249 if((sock->state != SS_UNCONNECTED) || !(sock->flags & __SO_ACCEPTCON))
251 if(sock->type != SOCK_SEQPACKET)
252 return (-EOPNOTSUPP);
253 if(sk->state != TCP_LISTEN)
258 skb = skb_dequeue(&sk->receive_queue);
261 if(flags & O_NONBLOCK)
264 return (-EWOULDBLOCK);
266 interruptible_sleep_on(sk->sleep);
267 if(signal_pending(current))
270 return (-ERESTARTSYS);
273 } while (skb == NULL);
279 err = spx_transmit(newsk, skb, CONACK, 0); /* Connection ACK */
283 /* Now attach up the new socket */
287 newsk->state = TCP_ESTABLISHED;
288 newsk->protinfo.af_ipx.dest_addr = newsk->tp_pinfo.af_spx.dest_addr;
293 /* Build a connection to an SPX socket */
294 static int spx_connect(struct socket *sock, struct sockaddr *uaddr,
295 int addr_len, int flags)
297 struct sock *sk = sock->sk;
298 struct spx_opt *pdata = &sk->tp_pinfo.af_spx;
299 struct sockaddr_ipx src;
304 err = ipx_operations->getname(sock, (struct sockaddr *)&src, &size, 0);
308 pdata->source_addr.net = src.sipx_network;
309 memcpy(pdata->source_addr.node, src.sipx_node, IPX_NODE_LEN);
310 pdata->source_addr.sock = (unsigned short)src.sipx_port;
312 err = ipx_operations->connect(sock, uaddr, addr_len, flags);
316 pdata->dest_addr = sk->protinfo.af_ipx.dest_addr;
317 pdata->state = SPX_CONNECTING;
318 sock->state = SS_CONNECTING;
319 sk->state = TCP_SYN_SENT;
321 /* Send Connection request */
322 err = spx_transmit(sk, NULL, CONREQ, 0);
328 skb = skb_dequeue(&sk->receive_queue);
331 if(flags & O_NONBLOCK)
334 return (-EWOULDBLOCK);
336 interruptible_sleep_on(sk->sleep);
337 if(signal_pending(current))
340 return (-ERESTARTSYS);
343 } while (skb == NULL);
345 if(pdata->state == SPX_CLOSED)
348 del_timer(&pdata->watchdog);
352 sock->state = SS_CONNECTED;
353 sk->state = TCP_ESTABLISHED;
361 * Calculate the timeout for a packet. Thankfully SPX has a large
362 * fudge factor (3/4 secs) and does not pay much attention to RTT.
363 * As we simply have a default retry time of 1*HZ and a max retry
364 * time of 5*HZ. Between those values we increase the timeout based
365 * on the number of retransmit tries.
367 * FixMe: This is quite fake, but will work for now. (JS)
369 static inline unsigned long spx_calc_rtt(int tries)
374 return (MAX_RETRY_DELAY);
378 static int spx_route_skb(struct spx_opt *pdata, struct sk_buff *skb, int type)
380 struct sk_buff *skb2;
383 skb = skb_unshare(skb, GFP_ATOMIC);
391 if(!skb_queue_empty(&pdata->retransmit_queue))
393 skb_queue_tail(&pdata->transmit_queue, skb);
398 pdata->retransmit.expires = jiffies + spx_calc_rtt(0);
399 add_timer(&pdata->retransmit);
401 skb2 = skb_clone(skb, GFP_NOIO);
404 skb_queue_tail(&pdata->retransmit_queue, skb2);
415 err = ipxrtr_route_skb(skb);
423 /* SPX packet transmit engine */
424 static int spx_transmit(struct sock *sk, struct sk_buff *skb, int type, int len)
426 struct spx_opt *pdata = &sk->tp_pinfo.af_spx;
427 struct ipxspxhdr *ipxh;
433 int offset = ipx_if_offset(pdata->dest_addr.net);
434 int size = offset + sizeof(struct ipxspxhdr);
436 if (offset < 0) /* ENETUNREACH */
437 return(-ENETUNREACH);
441 skb = sock_alloc_send_skb(sk, size, 0, &err);
443 restore_flags(flags);
446 skb_reserve(skb, offset);
447 skb->h.raw = skb->nh.raw = skb_put(skb,sizeof(struct ipxspxhdr));
448 restore_flags(flags);
452 ipxh = (struct ipxspxhdr *)skb->nh.raw;
453 ipxh->ipx.ipx_checksum = 0xFFFF;
454 ipxh->ipx.ipx_pktsize = htons(SPX_SYS_PKT_LEN);
455 ipxh->ipx.ipx_tctrl = 0;
456 ipxh->ipx.ipx_type = IPX_TYPE_SPX;
457 ipxh->ipx.ipx_dest = pdata->dest_addr;
458 ipxh->ipx.ipx_source = pdata->source_addr;
462 ipxh->spx.sequence = htons(pdata->sequence);
463 ipxh->spx.ackseq = htons(pdata->rmt_seq);
464 ipxh->spx.sconn = pdata->source_connid;
465 ipxh->spx.dconn = pdata->dest_connid;
466 ipxh->spx.allocseq = htons(pdata->alloc);
468 /* Reset/Set WD timer */
469 mod_timer(&pdata->watchdog, jiffies+VERIFY_TIMEOUT);
473 case (DATA): /* Data */
474 ipxh->ipx.ipx_pktsize = htons(SPX_SYS_PKT_LEN + len);
475 ipxh->spx.cctl = (CCTL_ACK | CCTL_EOM);
479 case (ACK): /* ACK */
481 case (WDACK): /* WD ACK */
482 case (CONACK): /* Connection ACK */
483 ipxh->spx.cctl = CCTL_SYS;
484 ipxh->spx.ackseq = htons(pdata->rmt_seq);
487 case (CONREQ): /* Connection Request */
488 del_timer(&pdata->watchdog);
489 case (WDREQ): /* WD Request */
490 pdata->source_connid = htons(connids++);
491 pdata->dest_connid = 0xFFFF;
492 pdata->alloc = 3 + pdata->rmt_seq;
493 ipxh->spx.cctl = (CCTL_ACK | CCTL_SYS);
494 ipxh->spx.sconn = pdata->source_connid;
495 ipxh->spx.dconn = pdata->dest_connid;
496 ipxh->spx.allocseq = htons(pdata->alloc);
499 case (DISCON): /* Informed Disconnect */
500 ipxh->spx.cctl = CCTL_ACK;
501 ipxh->spx.dtype = SPX_DTYPE_ECONN;
504 case (DISACK): /* Informed Disconnect ACK */
506 ipxh->spx.dtype = SPX_DTYPE_ECACK;
507 ipxh->spx.sequence = 0;
508 ipxh->spx.ackseq = htons(pdata->rmt_seq++);
512 return (-EOPNOTSUPP);
516 return (spx_route_skb(pdata, skb, type));
519 /* Check the state of the connection and send a WD request if needed. */
520 static void spx_watchdog(unsigned long data)
522 struct sock *sk = (struct sock*)data;
523 struct spx_opt *pdata = &sk->tp_pinfo.af_spx;
525 del_timer(&pdata->watchdog);
526 if(pdata->state == SPX_CLOSED)
528 if(pdata->retries > pdata->max_retries)
530 spx_close_socket(sk); /* Unilateral Abort */
534 /* Send WD request */
535 spx_transmit(sk, NULL, WDREQ, 0);
541 static void spx_retransmit(unsigned long data)
543 struct sock *sk = (struct sock*)data;
544 struct spx_opt *pdata = &sk->tp_pinfo.af_spx;
549 del_timer(&pdata->retransmit);
550 if(pdata->state == SPX_CLOSED)
552 if(pdata->retransmits > RETRY_COUNT)
554 spx_close_socket(sk); /* Unilateral Abort */
558 /* Need to leave skb on the queue, aye the fear */
561 skb = skb_peek(&pdata->retransmit_queue);
563 skb = skb_copy(skb, GFP_ATOMIC);
565 skb = skb_clone(skb, GFP_ATOMIC);
566 restore_flags(flags);
568 pdata->retransmit.expires = jiffies + spx_calc_rtt(pdata->retransmits);
569 add_timer(&pdata->retransmit);
571 err = spx_route_skb(pdata, skb, RETRAN);
572 pdata->retransmits++;
577 /* Check packet for retransmission, ConReqAck aware */
578 static int spx_retransmit_chk(struct spx_opt *pdata, int ackseq, int type)
580 struct ipxspxhdr *ipxh;
583 skb = skb_dequeue(&pdata->retransmit_queue);
587 /* Check Data/ACK seq */
590 case ACK: /* Check Sequence, Should == 1 */
591 ipxh = (struct ipxspxhdr *)skb->nh.raw;
592 if(!(ntohs(ipxh->spx.sequence) - htons(ackseq)))
596 del_timer(&pdata->retransmit);
597 pdata->retransmits = 0;
599 if(skb_queue_empty(&pdata->retransmit_queue))
601 skb = skb_dequeue(&pdata->transmit_queue);
603 spx_route_skb(pdata, skb, TQUEUE);
608 skb_queue_head(&pdata->retransmit_queue, skb);
612 /* SPX packet receive engine */
613 void spx_rcv(struct sock *sk, int bytes)
616 struct ipxspxhdr *ipxh;
617 struct spx_opt *pdata = &sk->tp_pinfo.af_spx;
619 skb = skb_dequeue(&sk->receive_queue);
622 ipxh = (struct ipxspxhdr *)skb->nh.raw;
624 /* Can't receive on a closed connection */
625 if((pdata->state == SPX_CLOSED) && (ipxh->spx.sequence != 0))
627 if(ntohs(ipxh->ipx.ipx_pktsize) < SPX_SYS_PKT_LEN)
629 if(ipxh->ipx.ipx_type != IPX_TYPE_SPX)
631 if(ntohs(ipxh->spx.ackseq) > pdata->sequence)
634 /* Reset WD timer on any received packet */
635 del_timer(&pdata->watchdog);
637 pdata->watchdog.expires = jiffies + ABORT_TIMEOUT;
638 add_timer(&pdata->watchdog);
640 switch(ipxh->spx.cctl)
642 case (CCTL_SYS | CCTL_ACK):
643 if((ipxh->spx.sequence == 0) /* ConReq */
644 && (ipxh->spx.ackseq == 0)
645 && (ipxh->spx.dconn == 0xFFFF))
647 pdata->state = SPX_CONNECTED;
648 pdata->dest_addr = ipxh->ipx.ipx_source;
649 pdata->source_addr = ipxh->ipx.ipx_dest;
650 pdata->dest_connid = ipxh->spx.sconn;
651 pdata->alloc = 3 + ntohs(ipxh->spx.sequence);
653 skb_queue_tail(&sk->receive_queue, skb);
654 wake_up_interruptible(sk->sleep);
656 else /* WD Request */
657 spx_transmit(sk, skb, WDACK, 0);
660 case CCTL_SYS: /* ACK */
661 if((ipxh->spx.dtype == 0) /* ConReq ACK */
662 && (ipxh->spx.sconn != 0xFFFF)
663 && (ipxh->spx.dconn != 0xFFFF)
664 && (ipxh->spx.sequence == 0)
665 && (ipxh->spx.ackseq == 0)
666 && (pdata->state != SPX_CONNECTED))
668 pdata->state = SPX_CONNECTED;
669 pdata->dest_connid = ipxh->spx.sconn;
671 if(spx_retransmit_chk(pdata, 0, CONACK) < 0)
674 skb_queue_tail(&sk->receive_queue, skb);
675 wake_up_interruptible(sk->sleep);
679 spx_retransmit_chk(pdata, ipxh->spx.ackseq, ACK);
683 /* Informed Disconnect */
684 if(ipxh->spx.dtype == SPX_DTYPE_ECONN)
687 spx_transmit(sk, skb, DISACK, 0);
688 spx_close_socket(sk);
694 if(ntohs(ipxh->spx.sequence) == pdata->rmt_seq)
696 pdata->rmt_seq = ntohs(ipxh->spx.sequence);
697 pdata->rmt_ack = ntohs(ipxh->spx.ackseq);
698 pdata->alloc = pdata->rmt_seq + 3;
699 if(pdata->rmt_ack > 0 || pdata->rmt_ack == 0)
700 spx_retransmit_chk(pdata,pdata->rmt_ack, ACK);
702 skb_queue_tail(&pdata->rcv_queue, skb);
703 wake_up_interruptible(sk->sleep);
704 if(ipxh->spx.cctl&CCTL_ACK)
705 spx_transmit(sk, NULL, ACK, 0);
709 if(ipxh->spx.dtype == SPX_DTYPE_ECACK)
711 if(pdata->state != SPX_CLOSED)
712 spx_close_socket(sk);
717 toss_skb: /* Catch All */
723 /* Get message/packet data from user-land */
724 static int spx_sendmsg(struct socket *sock, struct msghdr *msg, int len,
725 struct scm_cookie *scm)
727 struct sock *sk = sock->sk;
728 int flags = msg->msg_flags;
730 int err, offset, size;
735 return (-ENOTCONN); /* Socket not bound */
736 if(flags&~MSG_DONTWAIT)
739 offset = ipx_if_offset(sk->tp_pinfo.af_spx.dest_addr.net);
740 size = offset + sizeof(struct ipxspxhdr) + len;
743 skb = sock_alloc_send_skb(sk, size, flags&MSG_DONTWAIT, &err);
749 skb_reserve(skb, offset);
750 skb->h.raw = skb->nh.raw = skb_put(skb, sizeof(struct ipxspxhdr));
752 err = memcpy_fromiovec(skb_put(skb, len), msg->msg_iov, len);
759 err = spx_transmit(sk, skb, DATA, len);
766 /* Send message/packet data to user-land */
767 static int spx_recvmsg(struct socket *sock, struct msghdr *msg, int size,
768 int flags, struct scm_cookie *scm)
771 struct ipxspxhdr *ispxh;
772 struct sock *sk = sock->sk;
773 struct spx_opt *pdata = &sk->tp_pinfo.af_spx;
774 struct sockaddr_ipx *sipx = (struct sockaddr_ipx *)msg->msg_name;
778 return (-ENOTCONN); /* Socket not bound */
782 while(skb_queue_empty(&pdata->rcv_queue)) /* No data */
785 err = sock_error(sk);
789 /* Socket shut down? */
790 if(sk->shutdown & RCV_SHUTDOWN)
794 if(signal_pending(current))
795 return (-ERESTARTSYS);
797 /* User doesn't want to wait */
798 if(flags&MSG_DONTWAIT)
804 if(skb_peek(&pdata->rcv_queue) == NULL)
805 interruptible_sleep_on(sk->sleep);
806 restore_flags(flags);
810 skb = skb_dequeue(&pdata->rcv_queue);
814 ispxh = (struct ipxspxhdr *)skb->nh.raw;
815 copied = ntohs(ispxh->ipx.ipx_pktsize) - SPX_SYS_PKT_LEN;
819 msg->msg_flags |= MSG_TRUNC;
822 err = memcpy_toiovec(msg->msg_iov, skb->nh.raw+SPX_SYS_PKT_LEN, copied);
826 msg->msg_namelen = sizeof(*sipx);
829 sipx->sipx_family = AF_IPX;
830 sipx->sipx_port = ispxh->ipx.ipx_source.sock;
831 memcpy(sipx->sipx_node,ispxh->ipx.ipx_source.node,IPX_NODE_LEN);
832 sipx->sipx_network = ispxh->ipx.ipx_source.net;
833 sipx->sipx_type = ispxh->ipx.ipx_type;
842 * Functions which just wrap their IPX cousins
845 static int spx_bind(struct socket *sock, struct sockaddr *uaddr, int addr_len)
848 err = ipx_operations->bind(sock, uaddr, addr_len);
852 static int spx_getname (struct socket *sock, struct sockaddr *uaddr,
853 int *usockaddr_len, int peer)
856 err = ipx_operations->getname(sock, uaddr, usockaddr_len, peer);
860 static int spx_ioctl (struct socket *sock, unsigned int cmd,
864 err = ipx_operations->ioctl(sock, cmd, arg);
868 static int spx_setsockopt(struct socket *sock, int level, int optname,
869 char *optval, int optlen)
872 err = ipx_operations->setsockopt(sock, level, optname, optval, optlen);
876 static int spx_getsockopt(struct socket *sock, int level, int optname,
877 char *optval, int *optlen)
880 err = ipx_operations->getsockopt(sock, level, optname, optval, optlen);
884 static struct proto_ops SOCKOPS_WRAPPED(spx_ops) = {
887 release: spx_release,
889 connect: spx_connect,
890 socketpair: sock_no_socketpair,
892 getname: spx_getname,
893 poll: spx_datagram_poll,
896 shutdown: sock_no_shutdown,
897 setsockopt: spx_setsockopt,
898 getsockopt: spx_getsockopt,
899 sendmsg: spx_sendmsg,
900 recvmsg: spx_recvmsg,
902 sendpage: sock_no_sendpage,
905 #include <linux/smp_lock.h>
906 SOCKOPS_WRAP(spx, PF_IPX);
908 static struct net_proto_family spx_family_ops = {
913 static char banner[] __initdata = KERN_INFO "NET4: Sequenced Packet eXchange (SPX) 0.02 for Linux NET4.0\n";
915 static int __init spx_proto_init(void)
919 connids = (__u16)jiffies; /* initalize random */
921 error = ipx_register_spx(&ipx_operations, &spx_family_ops);
923 printk(KERN_ERR "SPX: unable to register with IPX.\n");
925 /* route socket(PF_IPX, SOCK_SEQPACKET) calls through spx_create() */
930 module_init(spx_proto_init);
932 static void __exit spx_proto_finito(void)
934 ipx_unregister_spx();
937 module_exit(spx_proto_finito);