* [PATCH] block/vhdx: Add alignment checks for region tables
@ 2026-11-11 16:14 Thomas Huth
2026-11-11 20:32 ` Eric Blake
0 siblings, 1 reply; 7+ messages in thread
From: Thomas Huth @ 2026-11-11 16:14 UTC (permalink / raw)
To: Kevin Wolf, qemu-devel; +Cc: Peter Maydell, Hanna Reitz, qemu-block
According to the VHDX specification:
"The FileOffset and Length fields specify the 64-bit byte offset and 32-bit
byte length of the object within the file. The values must be a multiple of
1 MB, and FileOffset must be at least 1 MB."
Thus let's add a sanity check to avoid that bad things could happen later.
Buglink: https://gitlab.com/qemu-project/qemu/-/work_items/3762
Reported-by: Daniel Wade <danjwade95@gmail.com>
Signed-off-by: Thomas Huth <thuth@redhat.com>
---
block/vhdx.c | 10 ++++++++++
1 file changed, 10 insertions(+)
diff --git a/block/vhdx.c b/block/vhdx.c
index 8013a90a1a4..f5beace56f5 100644
--- a/block/vhdx.c
+++ b/block/vhdx.c
@@ -566,6 +566,16 @@ vhdx_open_region_tables(BlockDriverState *bs, BDRVVHDXState *s)
vhdx_region_entry_le_import(&rt_entry);
+ /*
+ * According to the VHDX spec, offset and length must be multiple
+ * of 1 MiB and length must be at least 1 MiB.
+ */
+ if ((rt_entry.file_offset & (MiB - 1)) ||
+ (rt_entry.length & (MiB - 1)) || rt_entry.length < MiB) {
+ ret = -EINVAL;
+ goto fail;
+ }
+
/* check for region overlap between these entries, and any
* other memory regions in the file */
ret = vhdx_region_check(s, rt_entry.file_offset, rt_entry.length);
--
2.56.0
^ permalink raw reply related [flat|nested] 7+ messages in thread
* Re: [PATCH] block/vhdx: Add alignment checks for region tables
2026-11-11 16:14 Thomas Huth
@ 2026-11-11 20:32 ` Eric Blake
2026-11-12 9:11 ` Thomas Huth
0 siblings, 1 reply; 7+ messages in thread
From: Eric Blake @ 2026-11-11 20:32 UTC (permalink / raw)
To: Thomas Huth
Cc: Kevin Wolf, qemu-devel, Peter Maydell, Hanna Reitz, qemu-block
On Wed, Nov 11, 2026 at 05:14:42PM +0100, Thomas Huth wrote:
> According to the VHDX specification:
>
> "The FileOffset and Length fields specify the 64-bit byte offset and 32-bit
> byte length of the object within the file. The values must be a multiple of
> 1 MB, and FileOffset must be at least 1 MB."
>
> Thus let's add a sanity check to avoid that bad things could happen later.
>
> Buglink: https://gitlab.com/qemu-project/qemu/-/work_items/3762
> Reported-by: Daniel Wade <danjwade95@gmail.com>
> Signed-off-by: Thomas Huth <thuth@redhat.com>
> ---
> block/vhdx.c | 10 ++++++++++
> 1 file changed, 10 insertions(+)
>
> diff --git a/block/vhdx.c b/block/vhdx.c
> index 8013a90a1a4..f5beace56f5 100644
> --- a/block/vhdx.c
> +++ b/block/vhdx.c
> @@ -566,6 +566,16 @@ vhdx_open_region_tables(BlockDriverState *bs, BDRVVHDXState *s)
>
> vhdx_region_entry_le_import(&rt_entry);
>
> + /*
> + * According to the VHDX spec, offset and length must be multiple
> + * of 1 MiB and length must be at least 1 MiB.
> + */
> + if ((rt_entry.file_offset & (MiB - 1)) ||
> + (rt_entry.length & (MiB - 1)) || rt_entry.length < MiB) {
Would QEMU_IS_ALIGNED() be better than open-coding the math here?
Also, the 'rt_entry.length < MiB' clause could be simplified to
'rt_entry.length == 0', since all other values less than MiB fail the
earlier alignment clause.
--
Eric Blake, Principal Software Engineer
Red Hat, Inc.
Virtualization: qemu.org | libguestfs.org
^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: [PATCH] block/vhdx: Add alignment checks for region tables
2026-11-11 20:32 ` Eric Blake
@ 2026-11-12 9:11 ` Thomas Huth
0 siblings, 0 replies; 7+ messages in thread
From: Thomas Huth @ 2026-11-12 9:11 UTC (permalink / raw)
To: Eric Blake; +Cc: Kevin Wolf, qemu-devel, Peter Maydell, Hanna Reitz, qemu-block
Am 11.11.26 um 21:32 schrieb Eric Blake:
> On Wed, Nov 11, 2026 at 05:14:42PM +0100, Thomas Huth wrote:
>> According to the VHDX specification:
>>
>> "The FileOffset and Length fields specify the 64-bit byte offset and 32-bit
>> byte length of the object within the file. The values must be a multiple of
>> 1 MB, and FileOffset must be at least 1 MB."
>>
>> Thus let's add a sanity check to avoid that bad things could happen later.
>>
>> Buglink: https://gitlab.com/qemu-project/qemu/-/work_items/3762
>> Reported-by: Daniel Wade <danjwade95@gmail.com>
>> Signed-off-by: Thomas Huth <thuth@redhat.com>
>> ---
>> block/vhdx.c | 10 ++++++++++
>> 1 file changed, 10 insertions(+)
>>
>> diff --git a/block/vhdx.c b/block/vhdx.c
>> index 8013a90a1a4..f5beace56f5 100644
>> --- a/block/vhdx.c
>> +++ b/block/vhdx.c
>> @@ -566,6 +566,16 @@ vhdx_open_region_tables(BlockDriverState *bs, BDRVVHDXState *s)
>>
>> vhdx_region_entry_le_import(&rt_entry);
>>
>> + /*
>> + * According to the VHDX spec, offset and length must be multiple
>> + * of 1 MiB and length must be at least 1 MiB.
>> + */
>> + if ((rt_entry.file_offset & (MiB - 1)) ||
>> + (rt_entry.length & (MiB - 1)) || rt_entry.length < MiB) {
>
> Would QEMU_IS_ALIGNED() be better than open-coding the math here?
That looks nicer, indeed. I'll send a v2...
Thanks,
Thomas
^ permalink raw reply [flat|nested] 7+ messages in thread
* [PATCH] block/vhdx: Add alignment checks for region tables
@ 2026-11-12 9:22 Thomas Huth
2026-11-12 12:49 ` Kevin Wolf
0 siblings, 1 reply; 7+ messages in thread
From: Thomas Huth @ 2026-11-12 9:22 UTC (permalink / raw)
To: Kevin Wolf, qemu-devel; +Cc: Peter Maydell, Hanna Reitz, qemu-block, Eric Blake
According to the VHDX specification:
"The FileOffset and Length fields specify the 64-bit byte offset and 32-bit
byte length of the object within the file. The values must be a multiple of
1 MB, and FileOffset must be at least 1 MB."
Thus let's add a sanity check to avoid that bad things could happen later.
Buglink: https://gitlab.com/qemu-project/qemu/-/work_items/3762
Reported-by: Daniel Wade <danjwade95@gmail.com>
Signed-off-by: Thomas Huth <thuth@redhat.com>
---
v2: Use QEMU_IS_ALIGNED() as suggested by Eric
block/vhdx.c | 10 ++++++++++
1 file changed, 10 insertions(+)
diff --git a/block/vhdx.c b/block/vhdx.c
index 8013a90a1a4..21270988b5a 100644
--- a/block/vhdx.c
+++ b/block/vhdx.c
@@ -566,6 +566,16 @@ vhdx_open_region_tables(BlockDriverState *bs, BDRVVHDXState *s)
vhdx_region_entry_le_import(&rt_entry);
+ /*
+ * According to the VHDX spec, offset and length must be multiple
+ * of 1 MiB and length must be at least 1 MiB.
+ */
+ if (!QEMU_IS_ALIGNED(rt_entry.file_offset, MiB) ||
+ !QEMU_IS_ALIGNED(rt_entry.length, MiB) || !rt_entry.length) {
+ ret = -EINVAL;
+ goto fail;
+ }
+
/* check for region overlap between these entries, and any
* other memory regions in the file */
ret = vhdx_region_check(s, rt_entry.file_offset, rt_entry.length);
--
2.56.0
^ permalink raw reply related [flat|nested] 7+ messages in thread
* Re: [PATCH] block/vhdx: Add alignment checks for region tables
2026-11-12 9:22 [PATCH] block/vhdx: Add alignment checks for region tables Thomas Huth
@ 2026-11-12 12:49 ` Kevin Wolf
2026-11-12 14:48 ` Thomas Huth
0 siblings, 1 reply; 7+ messages in thread
From: Kevin Wolf @ 2026-11-12 12:49 UTC (permalink / raw)
To: Thomas Huth
Cc: qemu-devel, Peter Maydell, Hanna Reitz, qemu-block, Eric Blake
Am 12.11.2026 um 10:22 hat Thomas Huth geschrieben:
> According to the VHDX specification:
>
> "The FileOffset and Length fields specify the 64-bit byte offset and 32-bit
> byte length of the object within the file. The values must be a multiple of
> 1 MB, and FileOffset must be at least 1 MB."
This requires that the offset (not length) is at least 1 MB...
> Thus let's add a sanity check to avoid that bad things could happen later.
>
> Buglink: https://gitlab.com/qemu-project/qemu/-/work_items/3762
> Reported-by: Daniel Wade <danjwade95@gmail.com>
> Signed-off-by: Thomas Huth <thuth@redhat.com>
> ---
> v2: Use QEMU_IS_ALIGNED() as suggested by Eric
>
> block/vhdx.c | 10 ++++++++++
> 1 file changed, 10 insertions(+)
>
> diff --git a/block/vhdx.c b/block/vhdx.c
> index 8013a90a1a4..21270988b5a 100644
> --- a/block/vhdx.c
> +++ b/block/vhdx.c
> @@ -566,6 +566,16 @@ vhdx_open_region_tables(BlockDriverState *bs, BDRVVHDXState *s)
>
> vhdx_region_entry_le_import(&rt_entry);
>
> + /*
> + * According to the VHDX spec, offset and length must be multiple
> + * of 1 MiB and length must be at least 1 MiB.
> + */
> + if (!QEMU_IS_ALIGNED(rt_entry.file_offset, MiB) ||
> + !QEMU_IS_ALIGNED(rt_entry.length, MiB) || !rt_entry.length) {
...but the comment and code do the opposite and check only that the
length is at least 1 MB, leaving FileOffset (which was the actual
requirement) unchecked.
>
> + ret = -EINVAL;
> + goto fail;
> + }
> +
> /* check for region overlap between these entries, and any
> * other memory regions in the file */
> ret = vhdx_region_check(s, rt_entry.file_offset, rt_entry.length);
I'm also wondering if the check shouldn't be in vhdx_region_check()
instead, which we're already calling here.
Kevin
^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: [PATCH] block/vhdx: Add alignment checks for region tables
2026-11-12 12:49 ` Kevin Wolf
@ 2026-11-12 14:48 ` Thomas Huth
2026-11-12 16:19 ` Kevin Wolf
0 siblings, 1 reply; 7+ messages in thread
From: Thomas Huth @ 2026-11-12 14:48 UTC (permalink / raw)
To: Kevin Wolf; +Cc: qemu-devel, Peter Maydell, Hanna Reitz, qemu-block, Eric Blake
Am 12.11.26 um 13:49 schrieb Kevin Wolf:
> Am 12.11.2026 um 10:22 hat Thomas Huth geschrieben:
>> According to the VHDX specification:
>>
>> "The FileOffset and Length fields specify the 64-bit byte offset and 32-bit
>> byte length of the object within the file. The values must be a multiple of
>> 1 MB, and FileOffset must be at least 1 MB."
>
> This requires that the offset (not length) is at least 1 MB...
>
>> Thus let's add a sanity check to avoid that bad things could happen later.
>>
>> Buglink: https://gitlab.com/qemu-project/qemu/-/work_items/3762
>> Reported-by: Daniel Wade <danjwade95@gmail.com>
>> Signed-off-by: Thomas Huth <thuth@redhat.com>
>> ---
>> v2: Use QEMU_IS_ALIGNED() as suggested by Eric
>>
>> block/vhdx.c | 10 ++++++++++
>> 1 file changed, 10 insertions(+)
>>
>> diff --git a/block/vhdx.c b/block/vhdx.c
>> index 8013a90a1a4..21270988b5a 100644
>> --- a/block/vhdx.c
>> +++ b/block/vhdx.c
>> @@ -566,6 +566,16 @@ vhdx_open_region_tables(BlockDriverState *bs, BDRVVHDXState *s)
>>
>> vhdx_region_entry_le_import(&rt_entry);
>>
>> + /*
>> + * According to the VHDX spec, offset and length must be multiple
>> + * of 1 MiB and length must be at least 1 MiB.
>> + */
>> + if (!QEMU_IS_ALIGNED(rt_entry.file_offset, MiB) ||
>> + !QEMU_IS_ALIGNED(rt_entry.length, MiB) || !rt_entry.length) {
>
> ...but the comment and code do the opposite and check only that the
> length is at least 1 MB, leaving FileOffset (which was the actual
> requirement) unchecked.
D'oh, stupid me! I was apparently sloppy when reading the spec, sorry!
(though a zero length likely also does not make much sense...)
>>
>> + ret = -EINVAL;
>> + goto fail;
>> + }
>> +
>> /* check for region overlap between these entries, and any
>> * other memory regions in the file */
>> ret = vhdx_region_check(s, rt_entry.file_offset, rt_entry.length);
>
> I'm also wondering if the check shouldn't be in vhdx_region_check()
> instead, which we're already calling here.
I considered that, too, but finally decided against it since
vhdx_region_check() seemed rather about overlapping regions... but if you
prefer, I can also move it there.
Thomas
^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: [PATCH] block/vhdx: Add alignment checks for region tables
2026-11-12 14:48 ` Thomas Huth
@ 2026-11-12 16:19 ` Kevin Wolf
0 siblings, 0 replies; 7+ messages in thread
From: Kevin Wolf @ 2026-11-12 16:19 UTC (permalink / raw)
To: Thomas Huth
Cc: qemu-devel, Peter Maydell, Hanna Reitz, qemu-block, Eric Blake
Am 12.11.2026 um 15:48 hat Thomas Huth geschrieben:
> Am 12.11.26 um 13:49 schrieb Kevin Wolf:
> > Am 12.11.2026 um 10:22 hat Thomas Huth geschrieben:
> > > According to the VHDX specification:
> > >
> > > "The FileOffset and Length fields specify the 64-bit byte offset and 32-bit
> > > byte length of the object within the file. The values must be a multiple of
> > > 1 MB, and FileOffset must be at least 1 MB."
> >
> > This requires that the offset (not length) is at least 1 MB...
> >
> > > Thus let's add a sanity check to avoid that bad things could happen later.
> > >
> > > Buglink: https://gitlab.com/qemu-project/qemu/-/work_items/3762
> > > Reported-by: Daniel Wade <danjwade95@gmail.com>
> > > Signed-off-by: Thomas Huth <thuth@redhat.com>
> > > ---
> > > v2: Use QEMU_IS_ALIGNED() as suggested by Eric
> > >
> > > block/vhdx.c | 10 ++++++++++
> > > 1 file changed, 10 insertions(+)
> > >
> > > diff --git a/block/vhdx.c b/block/vhdx.c
> > > index 8013a90a1a4..21270988b5a 100644
> > > --- a/block/vhdx.c
> > > +++ b/block/vhdx.c
> > > @@ -566,6 +566,16 @@ vhdx_open_region_tables(BlockDriverState *bs, BDRVVHDXState *s)
> > > vhdx_region_entry_le_import(&rt_entry);
> > > + /*
> > > + * According to the VHDX spec, offset and length must be multiple
> > > + * of 1 MiB and length must be at least 1 MiB.
> > > + */
> > > + if (!QEMU_IS_ALIGNED(rt_entry.file_offset, MiB) ||
> > > + !QEMU_IS_ALIGNED(rt_entry.length, MiB) || !rt_entry.length) {
> >
> > ...but the comment and code do the opposite and check only that the
> > length is at least 1 MB, leaving FileOffset (which was the actual
> > requirement) unchecked.
>
> D'oh, stupid me! I was apparently sloppy when reading the spec, sorry!
> (though a zero length likely also does not make much sense...)
Yes, I wouldn't have complained about the extra check for length, but
checking the offset seems important.
> > >
> > > + ret = -EINVAL;
> > > + goto fail;
> > > + }
> > > +
> > > /* check for region overlap between these entries, and any
> > > * other memory regions in the file */
> > > ret = vhdx_region_check(s, rt_entry.file_offset, rt_entry.length);
> >
> > I'm also wondering if the check shouldn't be in vhdx_region_check()
> > instead, which we're already calling here.
>
> I considered that, too, but finally decided against it since
> vhdx_region_check() seemed rather about overlapping regions... but if you
> prefer, I can also move it there.
There's a comment at vhdx_region_check() that could use an update then,
but the name vhdx_region_check() feels generic enough to me.
But this is not a requirement from my side, just a thought I had. If we
both had it, maybe that means something, but you decide.
Kevin
^ permalink raw reply [flat|nested] 7+ messages in thread
end of thread, other threads:[~2026-11-12 16:19 UTC | newest]
Thread overview: 7+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-11-12 9:22 [PATCH] block/vhdx: Add alignment checks for region tables Thomas Huth
2026-11-12 12:49 ` Kevin Wolf
2026-11-12 14:48 ` Thomas Huth
2026-11-12 16:19 ` Kevin Wolf
-- strict thread matches above, loose matches on Subject: below --
2026-11-11 16:14 Thomas Huth
2026-11-11 20:32 ` Eric Blake
2026-11-12 9:11 ` Thomas Huth
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.