* [PATCH 1/1] PCI: Check pci_rebar_size_supported() input
@ 2025-11-24 15:37 Ilpo Järvinen
2025-11-24 23:39 ` Bjorn Helgaas
0 siblings, 1 reply; 2+ messages in thread
From: Ilpo Järvinen @ 2025-11-24 15:37 UTC (permalink / raw)
To: Bjorn Helgaas, Christian König, linux-pci, linux-kernel
Cc: Ilpo Järvinen, Dan Carpenter
According to Dan Carpenter, smatch detects issue with size parameter
given to pci_rebar_size_supported():
drivers/pci/rebar.c:142 pci_rebar_size_supported()
error: undefined (user controlled) shift '(((1))) << size'
The problem is this call tree:
__resource_resize_store() <- takes an unsigned long from the user
-> pci_resize_resource() <- truncates it to int
-> pci_rebar_size_supported()
The string input to __resource_resize_store() is to unsigned long and
then passed to pci_resize_resource(). There could be similar problems
also with the values coming from GPU drivers.
Add 'size' validation to pci_rebar_size_supported().
There seems to be no SZ_128T prior to this so add one to be able to
specify the largest size supported by the kernel (PCIe r7.0 spec
already defines sizes even beyond 128TB but kernel does not yet support
them).
The issue looks older than the introduction of
pci_rebar_size_supported() in the commit bb1fabd0d94e ("PCI: Add
pci_rebar_size_supported() helper").
It would be also nice to convert 'size' unsigned too everywhere, maybe
even u8 but that is left as further work.
Fixes: 8bb705e3e79d ("PCI: Add pci_resize_resource() for resizing BARs")
Reported-by: Dan Carpenter <dan.carpenter@linaro.org>
Signed-off-by: Ilpo Järvinen <ilpo.jarvinen@linux.intel.com>
---
As this is so close to the merge window, I assume this will be routed
through next but I suggest not folding it to the commit bb1fabd0d94e
("PCI: Add pci_rebar_size_supported() helper") as this should be
backported. It will fail backport immediately as pci_rebar_size_supported()
is only in pci/resource but I'll deal with it when the time comes and
create a backport for it to the older codebase.
---
drivers/pci/rebar.c | 3 +++
include/linux/sizes.h | 1 +
2 files changed, 4 insertions(+)
diff --git a/drivers/pci/rebar.c b/drivers/pci/rebar.c
index 8f7af3053cd8..a84165a196fa 100644
--- a/drivers/pci/rebar.c
+++ b/drivers/pci/rebar.c
@@ -139,6 +139,9 @@ bool pci_rebar_size_supported(struct pci_dev *pdev, int bar, int size)
{
u64 sizes = pci_rebar_get_possible_sizes(pdev, bar);
+ if (size < 0 || size > ilog2(SZ_128T) - ilog2(PCI_REBAR_MIN_SIZE))
+ return false;
+
return BIT(size) & sizes;
}
EXPORT_SYMBOL_GPL(pci_rebar_size_supported);
diff --git a/include/linux/sizes.h b/include/linux/sizes.h
index 49039494076f..f1f1a055b047 100644
--- a/include/linux/sizes.h
+++ b/include/linux/sizes.h
@@ -67,5 +67,6 @@
#define SZ_16T _AC(0x100000000000, ULL)
#define SZ_32T _AC(0x200000000000, ULL)
#define SZ_64T _AC(0x400000000000, ULL)
+#define SZ_128T _AC(0x800000000000, ULL)
#endif /* __LINUX_SIZES_H__ */
base-commit: bf0a90fc907e47344f88e5b9b241082184dbac27
--
2.39.5
^ permalink raw reply related [flat|nested] 2+ messages in thread
* Re: [PATCH 1/1] PCI: Check pci_rebar_size_supported() input
2025-11-24 15:37 [PATCH 1/1] PCI: Check pci_rebar_size_supported() input Ilpo Järvinen
@ 2025-11-24 23:39 ` Bjorn Helgaas
0 siblings, 0 replies; 2+ messages in thread
From: Bjorn Helgaas @ 2025-11-24 23:39 UTC (permalink / raw)
To: Ilpo Järvinen
Cc: Bjorn Helgaas, Christian König, linux-pci, linux-kernel,
Dan Carpenter
On Mon, Nov 24, 2025 at 05:37:40PM +0200, Ilpo Järvinen wrote:
> According to Dan Carpenter, smatch detects issue with size parameter
> given to pci_rebar_size_supported():
>
> drivers/pci/rebar.c:142 pci_rebar_size_supported()
> error: undefined (user controlled) shift '(((1))) << size'
>
> The problem is this call tree:
> __resource_resize_store() <- takes an unsigned long from the user
> -> pci_resize_resource() <- truncates it to int
> -> pci_rebar_size_supported()
>
> The string input to __resource_resize_store() is to unsigned long and
> then passed to pci_resize_resource(). There could be similar problems
> also with the values coming from GPU drivers.
>
> Add 'size' validation to pci_rebar_size_supported().
>
> There seems to be no SZ_128T prior to this so add one to be able to
> specify the largest size supported by the kernel (PCIe r7.0 spec
> already defines sizes even beyond 128TB but kernel does not yet support
> them).
>
> The issue looks older than the introduction of
> pci_rebar_size_supported() in the commit bb1fabd0d94e ("PCI: Add
> pci_rebar_size_supported() helper").
>
> It would be also nice to convert 'size' unsigned too everywhere, maybe
> even u8 but that is left as further work.
>
> Fixes: 8bb705e3e79d ("PCI: Add pci_resize_resource() for resizing BARs")
> Reported-by: Dan Carpenter <dan.carpenter@linaro.org>
> Signed-off-by: Ilpo Järvinen <ilpo.jarvinen@linux.intel.com>
Applied to pci/resource for v6.19, thanks!
> ---
>
> As this is so close to the merge window, I assume this will be routed
> through next but I suggest not folding it to the commit bb1fabd0d94e
> ("PCI: Add pci_rebar_size_supported() helper") as this should be
> backported. It will fail backport immediately as pci_rebar_size_supported()
> is only in pci/resource but I'll deal with it when the time comes and
> create a backport for it to the older codebase.
>
> ---
> drivers/pci/rebar.c | 3 +++
> include/linux/sizes.h | 1 +
> 2 files changed, 4 insertions(+)
>
> diff --git a/drivers/pci/rebar.c b/drivers/pci/rebar.c
> index 8f7af3053cd8..a84165a196fa 100644
> --- a/drivers/pci/rebar.c
> +++ b/drivers/pci/rebar.c
> @@ -139,6 +139,9 @@ bool pci_rebar_size_supported(struct pci_dev *pdev, int bar, int size)
> {
> u64 sizes = pci_rebar_get_possible_sizes(pdev, bar);
>
> + if (size < 0 || size > ilog2(SZ_128T) - ilog2(PCI_REBAR_MIN_SIZE))
> + return false;
> +
> return BIT(size) & sizes;
> }
> EXPORT_SYMBOL_GPL(pci_rebar_size_supported);
> diff --git a/include/linux/sizes.h b/include/linux/sizes.h
> index 49039494076f..f1f1a055b047 100644
> --- a/include/linux/sizes.h
> +++ b/include/linux/sizes.h
> @@ -67,5 +67,6 @@
> #define SZ_16T _AC(0x100000000000, ULL)
> #define SZ_32T _AC(0x200000000000, ULL)
> #define SZ_64T _AC(0x400000000000, ULL)
> +#define SZ_128T _AC(0x800000000000, ULL)
>
> #endif /* __LINUX_SIZES_H__ */
>
> base-commit: bf0a90fc907e47344f88e5b9b241082184dbac27
> --
> 2.39.5
>
^ permalink raw reply [flat|nested] 2+ messages in thread
end of thread, other threads:[~2025-11-24 23:39 UTC | newest]
Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2025-11-24 15:37 [PATCH 1/1] PCI: Check pci_rebar_size_supported() input Ilpo Järvinen
2025-11-24 23:39 ` Bjorn Helgaas
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox