diff options
| author | Yousef Alhouseen <alhouseenyousef@gmail.com> | 2026-06-25 20:13:14 +0200 |
|---|---|---|
| committer | Wei Liu <wei.liu@kernel.org> | 2026-07-22 23:51:04 +0000 |
| commit | b496f042e0da26dd673806870c204adfe697f169 (patch) | |
| tree | 5c9719164b78d79f4cba2024bdcc443ee46ec774 | |
| parent | ab96bc97cdcf77c6f38634c73d00074c4f92c324 (diff) | |
mshv_vtl: clear hypercall output before copyout
mshv_vtl_hvcall_call() copies output_size bytes to userspace.
The output page is freshly allocated. Userspace chooses the copyout length.
If the hypercall writes less, the tail can contain stale page data.
Clear the copied range before issuing the hypercall.
Also check both bounce page allocations before either page is used.
Signed-off-by: Yousef Alhouseen <alhouseenyousef@gmail.com>
Reviewed-by: Michael Kelley <mhklinux@outlook.com>
Signed-off-by: Wei Liu <wei.liu@kernel.org>
| -rw-r--r-- | drivers/hv/mshv_vtl_main.c | 10 |
1 files changed, 10 insertions, 0 deletions
diff --git a/drivers/hv/mshv_vtl_main.c b/drivers/hv/mshv_vtl_main.c index 0d3d4161974f..dbf03b6676cd 100644 --- a/drivers/hv/mshv_vtl_main.c +++ b/drivers/hv/mshv_vtl_main.c @@ -1148,12 +1148,22 @@ static int mshv_vtl_hvcall_call(struct mshv_vtl_hvcall_fd *fd, */ in = (void *)__get_free_page(GFP_KERNEL); out = (void *)__get_free_page(GFP_KERNEL); + if (!in || !out) { + ret = -ENOMEM; + goto free_pages; + } if (copy_from_user(in, (void __user *)hvcall.input_ptr, hvcall.input_size)) { ret = -EFAULT; goto free_pages; } + /* + * The caller supplies output_size, so clear the range copied back to + * userspace in case the hypercall writes fewer bytes than requested. + */ + memset(out, 0, hvcall.output_size); + hvcall.status = hv_do_hypercall(hvcall.control, in, out); if (copy_to_user((void __user *)hvcall.output_ptr, out, hvcall.output_size)) { |
