Fedora kernel-2.6.17-1.2142_FC4 patched with stable patch-2.6.17.4-vs2.0.2-rc26.diff
[linux-2.6.git] / net / wanrouter / af_wanpipe.c
index 4776ec1..b126518 100644 (file)
@@ -36,6 +36,7 @@
 #include <linux/types.h>
 #include <linux/sched.h>
 #include <linux/mm.h>
+#include <linux/capability.h>
 #include <linux/fcntl.h>
 #include <linux/socket.h>
 #include <linux/in.h>
 #include <asm/uaccess.h>
 #include <linux/module.h>
 #include <linux/init.h>
-#include <linux/wanpipe.h>
 #include <linux/if_wanpipe.h>
 #include <linux/pkt_sched.h>
-#include <linux/tcp.h>
+#include <linux/tcp_states.h>
 #include <linux/if_wanpipe_common.h>
-#include <linux/sdla_x25.h>
 
 #ifdef CONFIG_INET
 #include <net/inet_common.h>
@@ -158,7 +157,7 @@ static void dbg_kfree(void * v, int line) {
 
 /* List of all wanpipe sockets. */
 HLIST_HEAD(wanpipe_sklist);
-static rwlock_t wanpipe_sklist_lock = RW_LOCK_UNLOCKED;
+static DEFINE_RWLOCK(wanpipe_sklist_lock);
 
 atomic_t wanpipe_socks_nr;
 static unsigned long wanpipe_tx_critical;
@@ -181,7 +180,7 @@ struct wanpipe_opt
 #endif
 
 static int sk_count;
-extern struct proto_ops wanpipe_ops;
+extern const struct proto_ops wanpipe_ops;
 static unsigned long find_free_critical;
 
 static void wanpipe_unlink_driver(struct sock *sk);
@@ -394,7 +393,7 @@ static int wanpipe_listen_rcv (struct sk_buff *skb,  struct sock *sk)
        chan->lcn = mbox_ptr->cmd.lcn;
        card->u.x.svc_to_dev_map[(chan->lcn%MAX_X25_LCN)] = dev;
 
-       newsk->sk_zapped = 0;
+       sock_reset_flag(newsk, SOCK_ZAPPED);
        newwp->num = htons(X25_PROT);
 
        if (wanpipe_do_bind(newsk, dev, newwp->num)) {
@@ -468,13 +467,26 @@ static struct sock *wanpipe_make_new(struct sock *osk)
        wp_sk(sk)->num  = wp_sk(osk)->num;
        sk->sk_rcvbuf   = osk->sk_rcvbuf;
        sk->sk_sndbuf   = osk->sk_sndbuf;
-       sk->sk_debug    = osk->sk_debug;
        sk->sk_state    = WANSOCK_CONNECTING;
        sk->sk_sleep    = osk->sk_sleep;
 
+       if (sock_flag(osk, SOCK_DBG))
+               sock_set_flag(sk, SOCK_DBG);
+
        return sk;
 }
 
+/* 
+ * FIXME: wanpipe_opt has to include a sock in its definition and stop using
+ * sk_protinfo, but this code is not even compilable now, so lets leave it for
+ * later.
+ */
+static struct proto wanpipe_proto = {
+       .name     = "WANPIPE",
+       .owner    = THIS_MODULE,
+       .obj_size = sizeof(struct sock),
+};
+
 /*============================================================
  * wanpipe_make_new
  *
@@ -493,7 +505,7 @@ static struct sock *wanpipe_alloc_socket(void)
        struct sock *sk;
        struct wanpipe_opt *wan_opt;
 
-       if ((sk = sk_alloc(PF_WANPIPE, GFP_ATOMIC, 1, NULL)) == NULL)
+       if ((sk = sk_alloc(PF_WANPIPE, GFP_ATOMIC, &wanpipe_proto, 1)) == NULL)
                return NULL;
 
        if ((wan_opt = kmalloc(sizeof(struct wanpipe_opt), GFP_ATOMIC)) == NULL) {
@@ -546,7 +558,7 @@ static int wanpipe_sendmsg(struct kiocb *iocb, struct socket *sock,
        int ifindex, err, reserve = 0;
 
        
-       if (!sk->sk_zapped)
+       if (!sock_flag(sk, SOCK_ZAPPED))
                return -ENETDOWN;
 
        if (sk->sk_state != WANSOCK_CONNECTED)
@@ -672,7 +684,7 @@ static void wanpipe_delayed_transmit (unsigned long data)
                return;
        }
        
-       if (sk->sk_state != WANSOCK_CONNECTED || !sk->sk_zapped) {
+       if (sk->sk_state != WANSOCK_CONNECTED || !sock_flag(sk, SOCK_ZAPPED)) {
                clear_bit(0, &wp->timer);
                DBG_PRINTK(KERN_INFO "wansock: Tx Timer, State not CONNECTED\n");
                return;
@@ -865,7 +877,7 @@ static void wanpipe_unlink_driver (struct sock *sk)
        struct net_device *dev;
        wanpipe_common_t *chan=NULL;
 
-       sk->sk_zapped = 0;
+       sock_reset_flag(sk, SOCK_ZAPPED);
        sk->sk_state = WANSOCK_DISCONNECTED;
        wp_sk(sk)->dev = NULL;
 
@@ -914,7 +926,7 @@ static void wanpipe_link_driver(struct net_device *dev, struct sock *sk)
        chan->mbox = wp->mbox;
        chan->tx_timer = &wp->tx_timer;
        wp->dev = dev;
-       sk->sk_zapped = 1;
+       sock_set_flag(sk, SOCK_ZAPPED);
        clear_bit(0,&chan->common_critical);
 }
 
@@ -964,7 +976,7 @@ static int wanpipe_release(struct socket *sock)
         */
 
        if (wp->num == htons(X25_PROT) &&
-           sk->sk_state != WANSOCK_DISCONNECTED && sk->sk_zapped) {
+           sk->sk_state != WANSOCK_DISCONNECTED && sock_flag(sk, SOCK_ZAPPED)) {
                struct net_device *dev = dev_get_by_index(sk->sk_bound_dev_if);
                wanpipe_common_t *chan;
                if (dev){
@@ -1075,18 +1087,18 @@ static void release_driver(struct sock *sk)
                        }
                        kfree_skb(skb);
                }
-               if (sk->sk_zapped)
+               if (sock_flag(sk, SOCK_ZAPPED))
                        wanpipe_unlink_card(sk);
        }else{
-               if (sk->sk_zapped)
+               if (sock_flag(sk, SOCK_ZAPPED))
                        wanpipe_unlink_driver(sk);
        }
        sk->sk_state        = WANSOCK_DISCONNECTED;
        sk->sk_bound_dev_if = 0;
-       sk->sk_zapped       = 0;
+       sock_reset_flag(sk, SOCK_ZAPPED);
        wp = wp_sk(sk);
 
-       if (wp && wp->mbox) {
+       if (wp) {
                kfree(wp->mbox);
                wp->mbox = NULL;
        }
@@ -1173,10 +1185,8 @@ static void wanpipe_kill_sock_timer (unsigned long data)
                return;
        }
 
-       if (wp_sk(sk)) {
-               kfree(wp_sk(sk));
-               wp_sk(sk) = NULL;
-       }
+       kfree(wp_sk(sk));
+       wp_sk(sk) = NULL;
 
        if (atomic_read(&sk->sk_refcnt) != 1) {
                atomic_set(&sk->sk_refcnt, 1);
@@ -1206,10 +1216,8 @@ static void wanpipe_kill_sock_accept (struct sock *sk)
        sk->sk_socket = NULL;
 
 
-       if (wp_sk(sk)) {
-               kfree(wp_sk(sk));
-               wp_sk(sk) = NULL;
-       }
+       kfree(wp_sk(sk));
+       wp_sk(sk) = NULL;
 
        if (atomic_read(&sk->sk_refcnt) != 1) {
                atomic_set(&sk->sk_refcnt, 1);
@@ -1230,10 +1238,8 @@ static void wanpipe_kill_sock_irq (struct sock *sk)
 
        sk->sk_socket = NULL;
 
-       if (wp_sk(sk)) {
-               kfree(wp_sk(sk));
-               wp_sk(sk) = NULL;
-       }
+       kfree(wp_sk(sk));
+       wp_sk(sk) = NULL;
 
        if (atomic_read(&sk->sk_refcnt) != 1) {
                atomic_set(&sk->sk_refcnt, 1);
@@ -1261,7 +1267,7 @@ static int wanpipe_do_bind(struct sock *sk, struct net_device *dev,
        wanpipe_common_t *chan=NULL;
        int err=0;
 
-       if (sk->sk_zapped) {
+       if (sock_flag(sk, SOCK_ZAPPED)) {
                err = -EALREADY;
                goto bind_unlock_exit;
        }
@@ -1515,7 +1521,7 @@ static int wanpipe_create(struct socket *sock, int protocol)
        sock->ops = &wanpipe_ops;
        sock_init_data(sock,sk);
 
-       sk->sk_zapped       = 0;
+       sock_reset_flag(sk, SOCK_ZAPPED);
        sk->sk_family       = PF_WANPIPE;
        wp_sk(sk)->num      = protocol;
        sk->sk_state        = WANSOCK_DISCONNECTED;
@@ -1721,7 +1727,7 @@ static int wanpipe_notifier(struct notifier_block *this, unsigned long msg, void
                case NETDEV_UNREGISTER:
                        if (dev->ifindex == sk->sk_bound_dev_if) {
                                printk(KERN_INFO "wansock: Device down %s\n",dev->name);
-                               if (sk->sk_zapped) {
+                               if (sock_flag(sk, SOCK_ZAPPED)) {
                                        wanpipe_unlink_driver(sk);
                                        sk->sk_err = ENETDOWN;
                                        sk->sk_error_report(sk);
@@ -1737,7 +1743,7 @@ static int wanpipe_notifier(struct notifier_block *this, unsigned long msg, void
                        break;
                case NETDEV_UP:
                        if (dev->ifindex == sk->sk_bound_dev_if &&
-                           po->num && !sk->sk_zapped) {
+                           po->num && !sock_flag(sk, SOCK_ZAPPED)) {
                                printk(KERN_INFO "wansock: Registering Device: %s\n",
                                                dev->name);
                                wanpipe_link_driver(dev,sk);
@@ -1832,7 +1838,7 @@ static int wanpipe_ioctl(struct socket *sock, unsigned int cmd, unsigned long ar
 #endif
 
                default:
-                       return dev_ioctl(cmd,(void __user *) arg);
+                       return -ENOIOCTLCMD;
        }
        /*NOTREACHED*/
 }
@@ -2160,7 +2166,7 @@ static int wanpipe_link_card (struct sock *sk)
 
        card->sk=sk;
        card->func=wanpipe_listen_rcv;
-       sk->sk_zapped = 1;
+       sock_set_flag(sk, SOCK_ZAPPED);
  
        return 0;
 }
@@ -2423,7 +2429,6 @@ static int wanpipe_accept(struct socket *sock, struct socket *newsock, int flags
        write_unlock(&wanpipe_sklist_lock);
        clear_bit(1,&wanpipe_tx_critical);
 
-       newsk->sk_pair = NULL;
        newsk->sk_socket = newsock;
        newsk->sk_sleep = &newsock->wait;
 
@@ -2505,7 +2510,7 @@ static int wanpipe_connect(struct socket *sock, struct sockaddr *uaddr, int addr
 
        dev_put(dev);
        
-       if (!sk->sk_zapped) /* Must bind first - autobinding does not work */
+       if (!sock_flag(sk, SOCK_ZAPPED)) /* Must bind first - autobinding does not work */
                return -EINVAL;
 
        sock->state   = SS_CONNECTING;
@@ -2540,7 +2545,7 @@ static int wanpipe_connect(struct socket *sock, struct sockaddr *uaddr, int addr
        return 0;
 }
 
-struct proto_ops wanpipe_ops = {
+const struct proto_ops wanpipe_ops = {
        .family =       PF_WANPIPE,
        .owner =        THIS_MODULE,
        .release =      wanpipe_release,
@@ -2576,17 +2581,23 @@ void cleanup_module(void)
        printk(KERN_INFO "wansock: Cleaning up \n");
        unregister_netdevice_notifier(&wanpipe_netdev_notifier);
        sock_unregister(PF_WANPIPE);
-       return;
+       proto_unregister(&wanpipe_proto);
 }
 
-
 int init_module(void)
 {
+       int rc;
 
        printk(KERN_INFO "wansock: Registering Socket \n");
+
+       rc = proto_register(&wanpipe_proto, 0);
+       if (rc != 0)
+               goto out;
+
        sock_register(&wanpipe_family_ops);
        register_netdevice_notifier(&wanpipe_netdev_notifier);
-       return 0;
+out:
+       return rc;
 }
 #endif
 MODULE_LICENSE("GPL");