crypto: af_alg - Forbid bind(2) when nokey child sockets are present
[pandora-kernel.git] / crypto / af_alg.c
index 2f8fd84..68ec1ac 100644 (file)
@@ -130,19 +130,16 @@ EXPORT_SYMBOL_GPL(af_alg_release);
 void af_alg_release_parent(struct sock *sk)
 {
        struct alg_sock *ask = alg_sk(sk);
-       bool last;
+       unsigned int nokey = ask->nokey_refcnt;
+       bool last = nokey && !ask->refcnt;
 
        sk = ask->parent;
-
-       if (ask->nokey_refcnt && !ask->refcnt) {
-               sock_put(sk);
-               return;
-       }
-
        ask = alg_sk(sk);
 
        lock_sock(sk);
-       last = !--ask->refcnt;
+       ask->nokey_refcnt -= nokey;
+       if (!last)
+               last = !--ask->refcnt;
        release_sock(sk);
 
        if (last)
@@ -185,7 +182,7 @@ static int alg_bind(struct socket *sock, struct sockaddr *uaddr, int addr_len)
 
        err = -EBUSY;
        lock_sock(sk);
-       if (ask->refcnt)
+       if (ask->refcnt | ask->nokey_refcnt)
                goto unlock;
 
        swap(ask->type, type);
@@ -296,6 +293,7 @@ int af_alg_accept(struct sock *sk, struct socket *newsock)
 
        if (nokey || !ask->refcnt++)
                sock_hold(sk);
+       ask->nokey_refcnt += nokey;
        alg_sk(sk2)->parent = sk;
        alg_sk(sk2)->type = type;
        alg_sk(sk2)->nokey_refcnt = nokey;