lkml.org 
[lkml]   [2021]   [Nov]   [25]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    From
    Subject[PATCH AUTOSEL 5.10 07/28] net/smc: Transfer remaining wait queue entries during fallback
    Date
    From: Wen Gu <guwen@linux.alibaba.com>

    [ Upstream commit 2153bd1e3d3dbf6a3403572084ef6ed31c53c5f0 ]

    The SMC fallback is incomplete currently. There may be some
    wait queue entries remaining in smc socket->wq, which should
    be removed to clcsocket->wq during the fallback.

    For example, in nginx/wrk benchmark, this issue causes an
    all-zeros test result:

    server: nginx -g 'daemon off;'
    client: smc_run wrk -c 1 -t 1 -d 5 http://11.200.15.93/index.html

    Running 5s test @ http://11.200.15.93/index.html
    1 threads and 1 connections
    Thread Stats Avg Stdev Max ± Stdev
    Latency 0.00us 0.00us 0.00us -nan%
    Req/Sec 0.00 0.00 0.00 -nan%
    0 requests in 5.00s, 0.00B read
    Requests/sec: 0.00
    Transfer/sec: 0.00B

    The reason for this all-zeros result is that when wrk used SMC
    to replace TCP, it added an eppoll_entry into smc socket->wq
    and expected to be notified if epoll events like EPOLL_IN/
    EPOLL_OUT occurred on the smc socket.

    However, once a fallback occurred, wrk switches to use clcsocket.
    Now it is clcsocket->wq instead of smc socket->wq which will
    be woken up. The eppoll_entry remaining in smc socket->wq does
    not work anymore and wrk stops the test.

    This patch fixes this issue by removing remaining wait queue
    entries from smc socket->wq to clcsocket->wq during the fallback.

    Link: https://www.spinics.net/lists/netdev/msg779769.html
    Signed-off-by: Wen Gu <guwen@linux.alibaba.com>
    Reviewed-by: Tony Lu <tonylu@linux.alibaba.com>
    Signed-off-by: David S. Miller <davem@davemloft.net>
    Signed-off-by: Sasha Levin <sashal@kernel.org>
    ---
    net/smc/af_smc.c | 14 ++++++++++++++
    1 file changed, 14 insertions(+)

    diff --git a/net/smc/af_smc.c b/net/smc/af_smc.c
    index cfb5b9be0569d..9714c779adf0a 100644
    --- a/net/smc/af_smc.c
    +++ b/net/smc/af_smc.c
    @@ -513,12 +513,26 @@ static void smc_link_save_peer_info(struct smc_link *link,

    static void smc_switch_to_fallback(struct smc_sock *smc)
    {
    + wait_queue_head_t *smc_wait = sk_sleep(&smc->sk);
    + wait_queue_head_t *clc_wait = sk_sleep(smc->clcsock->sk);
    + unsigned long flags;
    +
    smc->use_fallback = true;
    if (smc->sk.sk_socket && smc->sk.sk_socket->file) {
    smc->clcsock->file = smc->sk.sk_socket->file;
    smc->clcsock->file->private_data = smc->clcsock;
    smc->clcsock->wq.fasync_list =
    smc->sk.sk_socket->wq.fasync_list;
    +
    + /* There may be some entries remaining in
    + * smc socket->wq, which should be removed
    + * to clcsocket->wq during the fallback.
    + */
    + spin_lock_irqsave(&smc_wait->lock, flags);
    + spin_lock(&clc_wait->lock);
    + list_splice_init(&smc_wait->head, &clc_wait->head);
    + spin_unlock(&clc_wait->lock);
    + spin_unlock_irqrestore(&smc_wait->lock, flags);
    }
    }

    --
    2.33.0
    \
     
     \ /
      Last update: 2021-11-26 03:39    [W:4.131 / U:0.048 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site