tcp: cookie transactions setsockopt memory leak
authorDmitry Popov <dp@highloadlab.com>
Thu, 29 Jul 2010 01:59:36 +0000 (01:59 +0000)
committerDavid S. Miller <davem@davemloft.net>
Sat, 31 Jul 2010 06:04:07 +0000 (23:04 -0700)
There is a bug in do_tcp_setsockopt(net/ipv4/tcp.c),
TCP_COOKIE_TRANSACTIONS case.
In some cases (when tp->cookie_values == NULL) new tcp_cookie_values
structure can be allocated (at cvp), but not bound to
tp->cookie_values. So a memory leak occurs.

Signed-off-by: Dmitry Popov <dp@highloadlab.com>
Signed-off-by: David S. Miller <davem@davemloft.net>

net/ipv4/tcp.c

index 65afeae..c259714 100644 (file)
@@ -2176,6 +2176,8 @@ static int do_tcp_setsockopt(struct sock *sk, int level,
                                      GFP_KERNEL);
                        if (cvp == NULL)
                                return -ENOMEM;
+
+                       kref_init(&cvp->kref);
                }
                lock_sock(sk);
                tp->rx_opt.cookie_in_always =
@@ -2190,12 +2192,11 @@ static int do_tcp_setsockopt(struct sock *sk, int level,
                                 */
                                kref_put(&tp->cookie_values->kref,
                                         tcp_cookie_values_release);
-                               kref_init(&cvp->kref);
-                               tp->cookie_values = cvp;
                        } else {
                                cvp = tp->cookie_values;
                        }
                }
+
                if (cvp != NULL) {
                        cvp->cookie_desired = ctd.tcpct_cookie_desired;
 
@@ -2209,6 +2210,8 @@ static int do_tcp_setsockopt(struct sock *sk, int level,
                                cvp->s_data_desired = ctd.tcpct_s_data_desired;
                                cvp->s_data_constant = 0; /* false */
                        }
+
+                       tp->cookie_values = cvp;
                }
                release_sock(sk);
                return err;