From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from mail-lf1-x12d.google.com (mail-lf1-x12d.google.com [IPv6:2a00:1450:4864:20::12d]) by sourceware.org (Postfix) with ESMTPS id 5587A385842C for ; Sat, 29 Apr 2023 20:18:30 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.4.2 sourceware.org 5587A385842C Authentication-Results: sourceware.org; dmarc=pass (p=none dis=none) header.from=gmail.com Authentication-Results: sourceware.org; spf=pass smtp.mailfrom=gmail.com Received: by mail-lf1-x12d.google.com with SMTP id 2adb3069b0e04-4efe8991b8aso1527529e87.0 for ; Sat, 29 Apr 2023 13:18:30 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20221208; t=1682799508; x=1685391508; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=tl+Qb3hhp3REer9N3xEUKijLqLT0EO8S4fPJFv0cnCc=; b=QvMfNx+Keu3X1NZ1dqbntpLIeXAtmO3KxqwQJ2ys3u/RuNWUYzaYd0Luxi/wQfo7Z7 ZXJhNaObK9jyGAJk2s+Mqrl3isp0bZrzgFBfXakVsT1zUA84L0rSymH7FoxKYtYrFvwS iaKpVFcgRza7g/H5BBMzPNJlDxtQ2ucIK7fX8T0Ue5qZtGye6s+BDCEudrgrsLxmR45s RD/I8s4ol82Ypqoj1pSxQoNiE0RB17qdGgUgjNCdqWMSxWInueDbUgUDP0N5xOethrFS WdJsTTtY42vIB8shsbBo7p8UbhD+hz4ht//A/bnPJYh4dUPUL+rnTuPWgawADznZ4eTQ CDVg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20221208; t=1682799508; x=1685391508; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=tl+Qb3hhp3REer9N3xEUKijLqLT0EO8S4fPJFv0cnCc=; b=EHSBU+AGICDVK+vvtuoOytdUemigLh6eJ5drJvOT+HjXGBlSa7X6IExHJ93YiaVk1D QknstT0mYFIhe4tFecrrt+1PfLlQUKANnPzl8w2kt6xvcT8RQ+wCOaZLhnkamh6JZfg8 AFgO3MDWzKfnJORcw4+lmCDsCaWtokcByUe2gi9lY8VSvpWMIJF9K5ajRN+UCwBKG3id uBL2G8izzy2n2WE1OCJTWSbZkSiErEvCaSMfMspyifXkWb09gY3cYubvjKHjRkc2deqO euDeMaJ6DYbqF4pA31IROpp/XorUJYQTQ+ROtF/ZjanbjS0iwAsifrclV4sp5Dkd8X0u wyLA== X-Gm-Message-State: AC+VfDyS8f61luHdCfPgO9qbNpSEAcwttI1/dlqrGMGg6xpdzaTagnwn 97pGsswYC6Tn04KpL6/hhUbdc+Mnj4VVAg== X-Google-Smtp-Source: ACHHUZ7KZqDmhwWNp2c2iHyTEDLhZymKO1g1gT/biAMI/GRvjRQi8wpm0XJhWxV6qnum/nFw8edcfw== X-Received: by 2002:ac2:488e:0:b0:4e0:a426:6ddc with SMTP id x14-20020ac2488e000000b004e0a4266ddcmr2523095lfc.0.1682799507654; Sat, 29 Apr 2023 13:18:27 -0700 (PDT) Received: from surface-pro-6.. ([2a00:1370:818c:4a57:a7ac:6f45:1787:abcc]) by smtp.gmail.com with ESMTPSA id h25-20020ac250d9000000b004eb09820adbsm3905451lfm.105.2023.04.29.13.18.26 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Sat, 29 Apr 2023 13:18:27 -0700 (PDT) From: Sergey Bugaev To: libc-alpha@sourceware.org Cc: bug-hurd@gnu.org, Samuel Thibault Subject: [RFC PATCH v3 3/6] hurd: Replace reply port with a dead name on failed interruption Date: Sat, 29 Apr 2023 23:18:19 +0300 Message-Id: <20230429201822.2605207-4-bugaevc@gmail.com> X-Mailer: git-send-email 2.40.1 In-Reply-To: <20230429201822.2605207-1-bugaevc@gmail.com> References: <20230429201822.2605207-1-bugaevc@gmail.com> MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Spam-Status: No, score=-11.0 required=5.0 tests=BAYES_00,DKIM_SIGNED,DKIM_VALID,DKIM_VALID_AU,DKIM_VALID_EF,FREEMAIL_FROM,GIT_PATCH_0,RCVD_IN_DNSWL_NONE,SPF_HELO_NONE,SPF_PASS,TXREP,T_SCC_BODY_TEXT_LINE autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on server2.sourceware.org List-Id: If we're trying to interrupt an interruptible RPC, but the server fails to respond to our __interrupt_operation () call, we instead destroy the reply port we were expecting the reply to the RPC on. Instead of deallocating the name completely, replace it with a dead name, so the name won't get reused for some other right, and deallocate it in _hurd_intr_rpc_mach_msg once we return from the signal handler. Signed-off-by: Sergey Bugaev --- This is not required for x86_64, but probably a good idea anyway. I have checked that this does not fatally break things (this commit has been sitting in my tree, getting built along with the other changes, for quite some time without noticably breaking anything), but I have not run the full testsuite. Please do that on your end. hurd/hurdsig.c | 15 ++++++++++++--- hurd/intr-msg.c | 1 + sysdeps/mach/hurd/mig-reply.c | 25 +++++++------------------ 3 files changed, 20 insertions(+), 21 deletions(-) diff --git a/hurd/hurdsig.c b/hurd/hurdsig.c index b3808f9e..78ea59d9 100644 --- a/hurd/hurdsig.c +++ b/hurd/hurdsig.c @@ -477,9 +477,18 @@ _hurdsig_abort_rpcs (struct hurd_sigstate *ss, int signo, int sigthread, if (reply) { /* The interrupt didn't work. - Destroy the receive right the thread is blocked on. */ - __mach_port_destroy (__mach_task_self (), *reply); - *reply = MACH_PORT_NULL; + Destroy the receive right the thread is blocked on, and + replace it with a dead name to keep the name from reuse until + the therad is done with it. To do this atomically, first + insert a send right, and then destroy the receive right, + turning the send right into a dead name. */ + err = __mach_port_insert_right (__mach_task_self (), + *reply, *reply, + MACH_MSG_TYPE_MAKE_SEND); + assert_perror (err); + err = __mach_port_mod_refs (__mach_task_self (), *reply, + MACH_PORT_RIGHT_RECEIVE, -1); + assert_perror (err); } /* The system call return value register now contains diff --git a/hurd/intr-msg.c b/hurd/intr-msg.c index 1a086b51..716d87ab 100644 --- a/hurd/intr-msg.c +++ b/hurd/intr-msg.c @@ -305,6 +305,7 @@ _hurd_intr_rpc_mach_msg (mach_msg_header_t *msg, { /* Make sure we have a valid reply port. The one we were using may have been destroyed by interruption. */ + __mig_dealloc_reply_port (rcv_name); m->header.msgh_local_port = rcv_name = __mig_get_reply_port (); m->header.msgh_bits = msgh_bits; option = user_option; diff --git a/sysdeps/mach/hurd/mig-reply.c b/sysdeps/mach/hurd/mig-reply.c index 3fdee80e..7ea001df 100644 --- a/sysdeps/mach/hurd/mig-reply.c +++ b/sysdeps/mach/hurd/mig-reply.c @@ -69,29 +69,18 @@ __mig_dealloc_reply_port (mach_port_t arg) mach_port_t port = get_reply_port (); set_reply_port (MACH_PORT_NULL); /* So the mod_refs RPC won't use it. */ - - /* Normally, ARG should be the same as PORT that we store. However, if a - signal has interrupted the RPC, the stored PORT has been deallocated and - reset to MACH_PORT_NULL (or possibly MACH_PORT_DEAD). In this case the - MIG routine still has the old name, which it passes to us here. We must - not deallocate (or otherwise touch) it, since it may be already allocated - to another port right. Fortunately MIG itself doesn't do anything with - the reply port on errors either, other than immediately calling this - function. - - And so: - 1. Assert that things are sane, i.e. and PORT is either invalid or same - as ARG. - 2. Only deallocate the name if our stored PORT still names it. In that - case we're sure the right has not been deallocated / the name reused. - */ - + assert (port == arg); if (!MACH_PORT_VALID (port)) return; - assert (port == arg); err = __mach_port_mod_refs (__mach_task_self (), port, MACH_PORT_RIGHT_RECEIVE, -1); + if (err == KERN_INVALID_RIGHT) + /* It could be that during signal handling, the receive right had been + replaced with a dead name. */ + err = __mach_port_mod_refs (__mach_task_self (), port, + MACH_PORT_RIGHT_DEAD_NAME, -1); + assert_perror (err); } weak_alias (__mig_dealloc_reply_port, mig_dealloc_reply_port) -- 2.40.1