[CRIU] [PATCH 2/2] tcp: refresh a data about tcp connection after blocking it (v4)
Pavel Emelyanov
xemul at parallels.com
Fri Nov 16 06:02:22 EST 2012
On 11/15/2012 11:47 PM, Andrey Vagin wrote:
> We have a window between getting info about tcp connections
> and blocking them. States of tcp connections can be changes,
> so they should be refreshed after blocking.
>
> https://bugzilla.openvz.org/show_bug.cgi?id=2419
>
> v2: clean up
> v3: don't update lengthes of queues for listen sockets,
> they don't used.
> v4: check that a state of a tcp connection is ESTABLISHED or CLOSE
>
> Signed-off-by: Andrey Vagin <avagin at openvz.org>
> ---
> sk-tcp.c | 47 +++++++++++++++++++++++++++++++++++++++++++++++
> 1 file changed, 47 insertions(+)
>
> diff --git a/sk-tcp.c b/sk-tcp.c
> index cc1af80..ca14f47 100644
> --- a/sk-tcp.c
> +++ b/sk-tcp.c
> @@ -51,6 +51,38 @@ static int tcp_repair_on(int fd)
> return ret;
> }
>
> +static int refresh_inet_sk(int fd, struct inet_sk_desc *sk)
> +{
> + int size;
> + struct tcp_info info;
> +
> + if (sk->state == TCP_CLOSE)
> + return 0;
How can this be true?
> +
> + if (dump_opt(fd, SOL_TCP, TCP_INFO, &info)) {
> + pr_perror("Failt to obtain TCP_INFO");
> + return -1;
> + }
> +
> + sk->state = info.tcpi_state;
> +
> + if (ioctl(fd, SIOCOUTQ, &size) == -1) {
> + pr_perror("Unable to get size of snd queue");
> + return -1;
> + }
> +
> + sk->wqlen = size;
> +
> + if (ioctl(fd, SIOCINQ, &size) == -1) {
> + pr_perror("Unable to get size of recv queue");
> + return -1;
> + }
> +
> + sk->rqlen = size;
> +
> + return 0;
> +}
> +
> static int tcp_repair_establised(int fd, struct inet_sk_desc *sk)
> {
> int ret;
> @@ -298,6 +330,21 @@ int dump_one_tcp(int fd, struct inet_sk_desc *sk)
> ret = nf_lock_connection(sk);
> if (ret < 0)
> return -1;
> +
> + /* A state of a tcp connection could be changed */
> + ret = refresh_inet_sk(fd, sk);
> + if (ret < 0)
> + goto err;
> +
> + if (sk->state == TCP_CLOSE) {
Socket cant change state from established to closed w/o task's will.
> + nf_unlock_connection(sk);
> + return 0;
> + }
> +
> + if (sk->state != TCP_ESTABLISHED) {
> + pr_err("Unknown state %d\n", sk->state);
> + goto err;
> + }
> }
>
> pr_info("Dumping TCP connection\n");
>
More information about the CRIU
mailing list