From: "Philippe Mathieu-Daudé" <philmd@linaro.org>
To: Mark Cave-Ayland <mark.cave-ayland@ilande.co.uk>,
pbonzini@redhat.com, qemu-devel@nongnu.org
Cc: Markus Armbruster <armbru@redhat.com>
Subject: Re: [PATCH 3/3] softmmu/ioport.c: make MemoryRegionPortioList owner of portio_list MemoryRegions
Date: Thu, 11 May 2023 21:22:31 +0200 [thread overview]
Message-ID: <0f030dfa-9c3e-b44a-584a-22deca1680f7@linaro.org> (raw)
In-Reply-To: <20230419151652.362717-4-mark.cave-ayland@ilande.co.uk>
On 19/4/23 17:16, Mark Cave-Ayland wrote:
> Currently when portio_list MemoryRegions are freed using portio_list_destroy() the RCU
> thread segfaults generating a backtrace similar to that below:
>
> #0 0x5555599a34b6 in phys_section_destroy ../softmmu/physmem.c:996
> #1 0x5555599a37a3 in phys_sections_free ../softmmu/physmem.c:1011
> #2 0x5555599b24aa in address_space_dispatch_free ../softmmu/physmem.c:2430
> #3 0x55555996a283 in flatview_destroy ../softmmu/memory.c:292
> #4 0x55555a2cb9fb in call_rcu_thread ../util/rcu.c:284
> #5 0x55555a29b71d in qemu_thread_start ../util/qemu-thread-posix.c:541
> #6 0x7ffff4a0cea6 in start_thread nptl/pthread_create.c:477
> #7 0x7ffff492ca2e in __clone (/lib/x86_64-linux-gnu/libc.so.6+0xfca2e)
>
> The problem here is that portio_list_destroy() unparents the portio_list MemoryRegions
> causing them to be freed immediately, however the flatview still has a reference to the
> MemoryRegion and so causes a use-after-free segfault when the RCU thread next updates
> the flatview.
>
> Solve the lifetime issue by making MemoryRegionPortioList the owner of the portio_list
> MemoryRegions, and then reparenting them to the portio_list owner. This ensures that they
> can be accessed as QOM childen via the portio_list owner, yet the MemoryRegionPortioList
"children"
> owns the refcount.
>
> Update portio_list_destroy() to unparent the MemoryRegion from the portio_list owner and
> then add a finalize() method to MemoryRegionPortioList, so that the portio_list
> MemoryRegions remain allocated until flatview_destroy() removes the final refcount upon
> the next flatview update.
>
> Signed-off-by: Mark Cave-Ayland <mark.cave-ayland@ilande.co.uk>
> ---
> softmmu/ioport.c | 34 +++++++++++++++++++++++++++++++---
> 1 file changed, 31 insertions(+), 3 deletions(-)
> @@ -230,6 +230,8 @@ static void portio_list_add_1(PortioList *piolist,
> unsigned off_low, unsigned off_high)
> {
> MemoryRegionPortioList *mrpio;
> + Object *owner;
> + char *name;
> unsigned i;
>
> /* Copy the sub-list and null-terminate it. */
> @@ -246,8 +248,25 @@ static void portio_list_add_1(PortioList *piolist,
> mrpio->ports[i].base = start + off_low;
> }
>
> - memory_region_init_io(&mrpio->mr, piolist->owner, &portio_ops, mrpio,
> + /*
> + * The MemoryRegion owner is the MemoryRegionPortioList since that manages
> + * the lifecycle via the refcount
> + */
> + memory_region_init_io(&mrpio->mr, OBJECT(mrpio), &portio_ops, mrpio,
> piolist->name, off_high - off_low);
> +
> + /* Reparent the MemoryRegion to the piolist owner */
> + object_ref(&mrpio->mr);
> + object_unparent(OBJECT(&mrpio->mr));
Out of this patch scope, but could this part <...
> + if (!piolist->owner) {
> + owner = container_get(qdev_get_machine(), "/unattached");
> + } else {
> + owner = piolist->owner;
> + }
> + name = g_strdup_printf("%s[*]", piolist->name);
> + object_property_add_child(owner, name, OBJECT(&mrpio->mr));
> + g_free(name);
...> be extracted as qdev_add_child()? It seems to duplicate
code from device_set_realized().
> if (piolist->flush_coalesced_mmio) {
> memory_region_set_flush_coalesced(&mrpio->mr);
> }
> @@ -305,10 +324,19 @@ void portio_list_del(PortioList *piolist)
> }
> }
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
next prev parent reply other threads:[~2023-05-11 19:23 UTC|newest]
Thread overview: 16+ messages / expand[flat|nested] mbox.gz Atom feed top
2023-04-19 15:16 [PATCH 0/3] softmmu/ioport.c: fix use-after-free when calling portio_list_destroy() Mark Cave-Ayland
2023-04-19 15:16 ` [PATCH 1/3] softmmu/ioport.c: allocate MemoryRegionPortioList ports on the heap Mark Cave-Ayland
2023-04-20 8:37 ` Philippe Mathieu-Daudé
2023-04-19 15:16 ` [PATCH 2/3] softmmu/ioport.c: QOMify MemoryRegionPortioList Mark Cave-Ayland
2023-04-20 8:41 ` Philippe Mathieu-Daudé
2023-04-20 10:53 ` Mark Cave-Ayland
2023-05-11 13:46 ` Philippe Mathieu-Daudé
2023-05-11 14:43 ` Mark Cave-Ayland
2023-05-17 16:31 ` Paolo Bonzini
2023-05-11 13:50 ` Philippe Mathieu-Daudé
2023-05-11 14:52 ` Mark Cave-Ayland
2023-05-17 16:37 ` Paolo Bonzini
2023-04-19 15:16 ` [PATCH 3/3] softmmu/ioport.c: make MemoryRegionPortioList owner of portio_list MemoryRegions Mark Cave-Ayland
2023-05-11 19:22 ` Philippe Mathieu-Daudé [this message]
2023-05-12 6:56 ` Mark Cave-Ayland
2023-05-12 14:13 ` Philippe Mathieu-Daudé
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=0f030dfa-9c3e-b44a-584a-22deca1680f7@linaro.org \
--to=philmd@linaro.org \
--cc=armbru@redhat.com \
--cc=mark.cave-ayland@ilande.co.uk \
--cc=pbonzini@redhat.com \
--cc=qemu-devel@nongnu.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).