* [PATCH v2 1/4] fb: Add dev_of_fbinfo() helper for optional sysfs support
From: Chintan Patel @ 2025-12-19 5:43 UTC (permalink / raw)
To: linux-fbdev, linux-staging, linux-omap
Cc: linux-kernel, dri-devel, tzimmermann, andy, deller, gregkh,
Chintan Patel
In-Reply-To: <20251219054320.447281-1-chintanlike@gmail.com>
Add dev_of_fbinfo() to return the framebuffer struct device when
CONFIG_FB_DEVICE is enabled, or NULL otherwise.
This allows fbdev drivers to use sysfs interfaces via runtime checks
instead of CONFIG_FB_DEVICE ifdefs, keeping the code clean while
remaining fully buildable.
Suggested-by: Helge Deller <deller@gmx.de>
Signed-off-by: Chintan Patel <chintanlike@gmail.com>
---
include/linux/fb.h | 9 +++++++++
1 file changed, 9 insertions(+)
diff --git a/include/linux/fb.h b/include/linux/fb.h
index 05cc251035da..dad3fb61a06a 100644
--- a/include/linux/fb.h
+++ b/include/linux/fb.h
@@ -628,6 +628,15 @@ static inline void unlock_fb_info(struct fb_info *info)
mutex_unlock(&info->lock);
}
+static inline struct device *dev_of_fbinfo(const struct fb_info *info)
+{
+#ifdef CONFIG_FB_DEVICE
+ return info->dev;
+#else
+ return NULL;
+#endif
+}
+
static inline void __fb_pad_aligned_buffer(u8 *dst, u32 d_pitch,
u8 *src, u32 s_pitch, u32 height)
{
--
2.43.0
^ permalink raw reply related
* [PATCH v2 0/4] fbdev: Make CONFIG_FB_DEVICE optional for drivers
From: Chintan Patel @ 2025-12-19 5:43 UTC (permalink / raw)
To: linux-fbdev, linux-staging, linux-omap
Cc: linux-kernel, dri-devel, tzimmermann, andy, deller, gregkh,
Chintan Patel
This series makes CONFIG_FB_DEVICE optional for fbdev drivers that use
it only for sysfs interfaces, addressing Thomas Zimmermann’s TODO to
remove hard FB_DEVICE dependencies.
The series introduces a small helper, dev_of_fbinfo(), which returns
NULL when CONFIG_FB_DEVICE=n. This allows sysfs code paths to be skipped
via runtime checks, avoids #ifdef CONFIG_FB_DEVICE clutter, and keeps
full compile-time syntax checking.
Changes in v2:
Add dev_of_fbinfo() helper (suggested by Geert Uytterhoeven)
Replace #ifdef CONFIG_FB_DEVICE blocks with runtime NULL checks
Switch to fb_dbg() / fb_info() logging (suggested by Thomas Zimmermann)
Chintan Patel (4):
fb: Add dev_of_fbinfo() helper for optional sysfs support
staging: fbtft: Make FB_DEVICE dependency optional
fbdev: omapfb: Make FB_DEVICE dependency optional
fbdev: sh_mobile_lcdc: Make FB_DEVICE dependency optional
drivers/staging/fbtft/Kconfig | 5 ++++-
drivers/staging/fbtft/fbtft-sysfs.c | 18 ++++++++++++++----
drivers/video/fbdev/omap2/omapfb/Kconfig | 3 ++-
.../video/fbdev/omap2/omapfb/omapfb-sysfs.c | 16 ++++++++++++----
drivers/video/fbdev/sh_mobile_lcdcfb.c | 9 +++++++++
include/linux/fb.h | 9 +++++++++
6 files changed, 50 insertions(+), 10 deletions(-)
--
2.43.0
^ permalink raw reply
* Re: [PATCH v2 14/19] video/vga: Add VGA_IS0_R
From: Ville Syrjälä @ 2025-12-18 16:56 UTC (permalink / raw)
To: Jani Nikula; +Cc: intel-gfx, intel-xe, Helge Deller, linux-fbdev, dri-devel
In-Reply-To: <7f70f53e34433e3056bf16195b009d14fb60b745@intel.com>
On Tue, Dec 09, 2025 at 12:55:49PM +0200, Jani Nikula wrote:
> On Tue, 09 Dec 2025, Ville Syrjala <ville.syrjala@linux.intel.com> wrote:
> > From: Ville Syrjälä <ville.syrjala@linux.intel.com>
> >
> > Add a proper name for the "Input status register 0" IO address.
> > Currently we have some code that does read addressed using the
> > aliasing VGA_MSR_W define, making it unclear what register we're
> > actually reading.
> >
> > v2: Remove stray '?'
> >
> > Cc: Helge Deller <deller@gmx.de>
Helge, can you toss me an ack to merge this via drm-intel please?
> > Cc: linux-fbdev@vger.kernel.org
> > Cc: dri-devel@lists.freedesktop.org
> > Signed-off-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
>
> Reviewed-by: Jani Nikula <jani.nikula@intel.com>
>
> > ---
> > include/video/vga.h | 1 +
> > 1 file changed, 1 insertion(+)
> >
> > diff --git a/include/video/vga.h b/include/video/vga.h
> > index 468764d6727a..2f13c371800b 100644
> > --- a/include/video/vga.h
> > +++ b/include/video/vga.h
> > @@ -46,6 +46,7 @@
> > #define VGA_MIS_R 0x3CC /* Misc Output Read Register */
> > #define VGA_MIS_W 0x3C2 /* Misc Output Write Register */
> > #define VGA_FTC_R 0x3CA /* Feature Control Read Register */
> > +#define VGA_IS0_R 0x3C2 /* Input Status Register 0 */
> > #define VGA_IS1_RC 0x3DA /* Input Status Register 1 - color emulation */
> > #define VGA_IS1_RM 0x3BA /* Input Status Register 1 - mono emulation */
> > #define VGA_PEL_D 0x3C9 /* PEL Data Register */
>
> --
> Jani Nikula, Intel
--
Ville Syrjälä
Intel
^ permalink raw reply
* Re: [PATCH] staging: fbtft: fix spacing before close parenthesis
From: Greg KH @ 2025-12-18 6:20 UTC (permalink / raw)
To: Arjun Changla; +Cc: andy, dri-devel, linux-fbdev, linux-staging, linux-kernel
In-Reply-To: <20251218061406.8043-1-arjunchangla7@gmail.com>
On Thu, Dec 18, 2025 at 06:14:06AM +0000, Arjun Changla wrote:
> Fix checkpatch error "space prohibited before that close parenthesis"
> on line 65 by removing the extra space.
>
> Signed-off-by: Arjun Changla <arjunchangla7@gmail.com>
> ---
> drivers/staging/fbtft/fbtft-bus.c | 2 +-
> 1 file changed, 1 insertion(+), 1 deletion(-)
>
> diff --git a/drivers/staging/fbtft/fbtft-bus.c b/drivers/staging/fbtft/fbtft-bus.c
> index 30e436ff19e4..2f7c891177fb 100644
> --- a/drivers/staging/fbtft/fbtft-bus.c
> +++ b/drivers/staging/fbtft/fbtft-bus.c
> @@ -62,7 +62,7 @@ out: \
> } \
> EXPORT_SYMBOL(func);
>
> -define_fbtft_write_reg(fbtft_write_reg8_bus8, u8, u8, )
> +define_fbtft_write_reg(fbtft_write_reg8_bus8, u8, u8)
But you just changed the function definition, does this still work now?
If so, how?
confused,
greg k-h
^ permalink raw reply
* [PATCH] staging: fbtft: fix spacing before close parenthesis
From: Arjun Changla @ 2025-12-18 6:14 UTC (permalink / raw)
To: andy, gregkh
Cc: dri-devel, linux-fbdev, linux-staging, linux-kernel,
Arjun Changla
Fix checkpatch error "space prohibited before that close parenthesis"
on line 65 by removing the extra space.
Signed-off-by: Arjun Changla <arjunchangla7@gmail.com>
---
drivers/staging/fbtft/fbtft-bus.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/staging/fbtft/fbtft-bus.c b/drivers/staging/fbtft/fbtft-bus.c
index 30e436ff19e4..2f7c891177fb 100644
--- a/drivers/staging/fbtft/fbtft-bus.c
+++ b/drivers/staging/fbtft/fbtft-bus.c
@@ -62,7 +62,7 @@ out: \
} \
EXPORT_SYMBOL(func);
-define_fbtft_write_reg(fbtft_write_reg8_bus8, u8, u8, )
+define_fbtft_write_reg(fbtft_write_reg8_bus8, u8, u8)
define_fbtft_write_reg(fbtft_write_reg16_bus8, __be16, u16, cpu_to_be16)
define_fbtft_write_reg(fbtft_write_reg16_bus16, u16, u16, )
--
2.43.0
^ permalink raw reply related
* Re: [PATCH] riva/fbdev: fix divide error in nv3_arb()
From: Guangshuo Li @ 2025-12-17 13:31 UTC (permalink / raw)
To: Helge Deller
Cc: Antonino Daplas, linux-fbdev, dri-devel, linux-kernel, stable
In-Reply-To: <dc2a9d7b-0495-4365-8353-b51dc0526b74@gmx.de>
Hi Helge,
thanks for your comments.
mclk_khz is derived from the PRAMDAC MCLK PLL and then passed into the
NV3 arbitration code. In nv3_arb() it is used as a divisor, so a zero
value will always be fatal.
For this fix I tried to keep it small and safe for stable. Putting the
guard in nv3_arb() makes sure we never hit a divide-by-zero no matter
how we got there. It also keeps the change local to the code that
actually needs the invariant mclk_khz != 0.
Adding checks in rivafb_set_par() (or other callers in the trace)
would either duplicate validation in places that do not compute
mclk_khz, or require pushing error handling through several layers.
About initializing mclk_khz to some default: I would rather not guess
a clock. A made-up value can lead to wrong FIFO arbitration settings.
If arbitration cannot be computed, bailing out and using the existing
conservative fallback is safer.
I agree it could be worth adding earlier validation of the PLL-derived
clock as a follow-up. For the stable fix, I prefer the minimal guard
at the division site.
Best regards,
Guangshuo
Helge Deller <deller@gmx.de> 于2025年12月9日周二 06:02写道:
>
> On 12/7/25 08:25, Guangshuo Li wrote:
> > A userspace program can trigger the RIVA NV3 arbitration code by
> > calling the FBIOPUT_VSCREENINFO ioctl on /dev/fb*. When doing so,
> > the driver recomputes FIFO arbitration parameters in nv3_arb(), using
> > state->mclk_khz (derived from the PRAMDAC MCLK PLL) as a divisor
> > without validating it first.
> >
> > In a normal setup, state->mclk_khz is provided by the real hardware
> > and is non-zero. However, an attacker can construct a malicious or
> > misconfigured device (e.g. a crafted/emulated PCI device) that exposes
> > a bogus PLL configuration, causing state->mclk_khz to become zero.
> > Once nv3_get_param() calls nv3_arb(), the division by state->mclk_khz in
> > the gns calculation causes a divide error and crashes the kernel.
> >
> > Fix this by checking whether state->mclk_khz is zero and bailing out before doing the division.
> >
> > The following log reveals it:
> >
> > rivafb: setting virtual Y resolution to 2184
> > divide error: 0000 [#1] PREEMPT SMP KASAN PTI
> > CPU: 0 PID: 2187 Comm: syz-executor.0 Not tainted 5.18.0-rc1+ #1
> > Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS rel-1.12.0-59-gc9ba5276e321-prebuilt.qemu.org 04/01/2014
> > RIP: 0010:nv3_arb drivers/video/fbdev/riva/riva_hw.c:439 [inline]
> > RIP: 0010:nv3_get_param+0x3ab/0x13b0 drivers/video/fbdev/riva/riva_hw.c:546
> > Code: c1 e8 03 42 0f b6 14 38 48 89 f8 83 e0 07 83 c0 03 38 d0 7c 08 84 d2 0f 85 b7 0e 00 00 41 8b 46 18 01 d8 69 c0 40 42 0f 00 99 <41> f7 fc 48 63 c8 4c 89 e8 48 c1 e8 03 42 0f b6 14 38 4c 89 e8 83
> > RSP: 0018:ffff888013b2f318 EFLAGS: 00010206
> > RAX: 0000000001d905c0 RBX: 0000000000000016 RCX: 0000000000040000
> > RDX: 0000000000000000 RSI: 0000000000000080 RDI: ffff888013b2f6f0
> > RBP: 0000000000000002 R08: ffffffff82226288 R09: 0000000000000001
> > R10: 0000000000000000 R11: 0000000000000001 R12: 0000000000000000
> > R13: ffff888013b2f4d8 R14: ffff888013b2f6d8 R15: dffffc0000000000
> > Call Trace:
> > nv3CalcArbitration.constprop.0+0x255/0x460 drivers/video/fbdev/riva/riva_hw.c:603
> > nv3UpdateArbitrationSettings drivers/video/fbdev/riva/riva_hw.c:637 [inline]
> > CalcStateExt+0x447/0x1b90 drivers/video/fbdev/riva/riva_hw.c:1246
> > riva_load_video_mode+0x8a9/0xea0 drivers/video/fbdev/riva/fbdev.c:779
> > rivafb_set_par+0xc0/0x5f0 drivers/video/fbdev/riva/fbdev.c:1196
>
> Doesn't it make sense to check mclk_khz (or the various variables which
> lead to mclk_khz) in rivafb_set_par() or any of the other functions mentioned
> in this trace?
> If in doubt, mclk_khz could be initialized to a sane value?
>
> Helge
>
>
> > fb_set_var+0x604/0xeb0 drivers/video/fbdev/core/fbmem.c:1033
> > do_fb_ioctl+0x234/0x670 drivers/video/fbdev/core/fbmem.c:1109
> > fb_ioctl+0xdd/0x130 drivers/video/fbdev/core/fbmem.c:1188
> > __x64_sys_ioctl+0x122/0x190 fs/ioctl.c:856
> >
> > Fixes: 1da177e4c3f4 ("Linux-2.6.12-rc2")
> > Cc: stable@vger.kernel.org
> > Signed-off-by: Guangshuo Li <lgs201920130244@gmail.com>
> > ---
> > drivers/video/fbdev/riva/riva_hw.c | 3 +++
> > 1 file changed, 3 insertions(+)
> >
> > diff --git a/drivers/video/fbdev/riva/riva_hw.c b/drivers/video/fbdev/riva/riva_hw.c
> > index 8b829b720064..d70c6c4d28e8 100644
> > --- a/drivers/video/fbdev/riva/riva_hw.c
> > +++ b/drivers/video/fbdev/riva/riva_hw.c
> > @@ -436,6 +436,9 @@ static char nv3_arb(nv3_fifo_info * res_info, nv3_sim_state * state, nv3_arb_in
> > vmisses = 2;
> > eburst_size = state->memory_width * 1;
> > mburst_size = 32;
> > + if (!state->mclk_khz)
> > + return (0);
> > +
> > gns = 1000000 * (gmisses*state->mem_page_miss + state->mem_latency)/state->mclk_khz;
> > ainfo->by_gfacc = gns*ainfo->gdrain_rate/1000000;
> > ainfo->wcmocc = 0;
>
^ permalink raw reply
* Re: [PATCH] staging: sm750fb: Fix alignment in sm750_hw_cursor_set_size call
From: Greg KH @ 2025-12-17 13:02 UTC (permalink / raw)
To: Karthikeya
Cc: sudipm.mukherjee, teddy.wang, linux-fbdev, linux-staging,
linux-kernel
In-Reply-To: <20251204150127.10844-1-garagakarthikeya2007@gmail.com>
On Thu, Dec 04, 2025 at 08:31:26PM +0530, Karthikeya wrote:
> Align the arguments of the sm750_hw_cursor_set_size function call
> with the opening parenthesis.
>
> This fixes a checkpatch.pl CHECK warning:
> 'Alignment should match open parenthesis'
>
> Signed-off-by: Karthikeya <garagakarthikeya2007@gmail.com>
> ---
> drivers/staging/sm750fb/sm750.c | 4 ++--
> 1 file changed, 2 insertions(+), 2 deletions(-)
>
> diff --git a/drivers/staging/sm750fb/sm750.c b/drivers/staging/sm750fb/sm750.c
> index 3659af7e5..9740f2705 100644
> --- a/drivers/staging/sm750fb/sm750.c
> +++ b/drivers/staging/sm750fb/sm750.c
> @@ -121,8 +121,8 @@ static int lynxfb_ops_cursor(struct fb_info *info, struct fb_cursor *fbcursor)
> sm750_hw_cursor_disable(cursor);
> if (fbcursor->set & FB_CUR_SETSIZE)
> sm750_hw_cursor_set_size(cursor,
> - fbcursor->image.width,
> - fbcursor->image.height);
> + fbcursor->image.width,
> + fbcursor->image.height);
>
> if (fbcursor->set & FB_CUR_SETPOS)
> sm750_hw_cursor_set_pos(cursor,
> --
> 2.52.0
>
Does not apply at all to the latest kernel tree :(
^ permalink raw reply
* Re: [PATCH v2,stable/linux-6.6.y] fbdev: Fix out-of-bounds issue in sys_fillrect()
From: Greg Kroah-Hartman @ 2025-12-17 9:34 UTC (permalink / raw)
To: Gu Bowen
Cc: Daniel Vetter, Helge Deller, linux-fbdev, dri-devel, stable,
Lu Jialin
In-Reply-To: <20251217094530.1685998-1-gubowen5@huawei.com>
On Wed, Dec 17, 2025 at 05:45:30PM +0800, Gu Bowen wrote:
> This issue has already been fixed by commit eabb03293087 ("fbdev:
> Refactoring the fbcon packed pixel drawing routines") on v6.15-rc1, but it
> still exists in the stable version.
Why not take the refactoring changes instead? That is almost always the
proper thing to do, one-off changes are almost always wrong and cause
extra work in the long-term.
Please try backporting those changes instead please.
thanks,
greg k-h
^ permalink raw reply
* [PATCH v2,stable/linux-6.6.y] fbdev: Fix out-of-bounds issue in sys_fillrect()
From: Gu Bowen @ 2025-12-17 9:45 UTC (permalink / raw)
To: Daniel Vetter, Helge Deller, Greg Kroah-Hartman
Cc: linux-fbdev, dri-devel, stable, Lu Jialin, Gu Bowen
There was an out-of-bounds issue found by syzkaller test on v6.6.
BUG: unable to handle page fault for address: ffffc90000c3f000
PGD 100000067 P4D 100000067 PUD 100c80067 PMD 10ac1c067 PTE 0
Oops: 0002 [#1] PREEMPT SMP KASAN PTI
CPU: 3 PID: 6521 Comm: syz.3.1365 Not tainted 6.6.0+ #82
Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS rel-1.14.0-0-g155821a1990b-prebuilt.qemu.org 04/01/2014
RIP: 0010:memset64 arch/x86/include/asm/string_64.h:58 [inline]
RIP: 0010:memset_l include/linux/string.h:168 [inline]
RIP: 0010:bitfill_aligned drivers/video/fbdev/core/sysfillrect.c:53 [inline]
RIP: 0010:bitfill_aligned+0x144/0x1c0 drivers/video/fbdev/core/sysfillrect.c:25
Code: 23 04 24 48 31 d0 49 89 46 f8 44 89 e0 44 29 f8 29 c3 e8 9f 39 49 fe 89 d8 31 d2 4c 89 f7 41 f7 f4 48 89 c3 48 89 c1 48 89 e8 <f3> 48 ab 31 ff 4c 89 ee e8 df 2f 49 fe 4d 85 ed 0f 84 6b ff ff ff
RSP: 0018:ffff888119ce7418 EFLAGS: 00010246
RAX: 0000000000000000 RBX: 0000000000000180 RCX: 0000000000000180
RDX: 0000000000000000 RSI: ffffc90003873000 RDI: ffffc90000c3f000
RBP: 0000000000000000 R08: 0000000000006000 R09: 0000000000000040
R10: 0000000000000000 R11: 0000000000000001 R12: 0000000000000040
R13: 0000000000000000 R14: ffffc90000c3f000 R15: 0000000000000000
FS: 00007f1704b926c0(0000) GS:ffff8881f5980000(0000) knlGS:0000000000000000
CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033
CR2: ffffc90000c3f000 CR3: 00000001230d0002 CR4: 0000000000770ee0
DR0: 0000000000000000 DR1: 000000000000e000 DR2: 0000000000000000
DR3: 0000000000000000 DR6: 00000000ffff0ff0 DR7: 0000000000000400
PKRU: 80000000
Call Trace:
<TASK>
sys_fillrect+0x429/0x830 drivers/video/fbdev/core/sysfillrect.c:281
drm_fbdev_generic_defio_fillrect+0x27/0x140 drivers/gpu/drm/drm_fbdev_generic.c:37
bit_clear+0x183/0x220 drivers/video/fbdev/core/bitblit.c:73
__fbcon_clear+0x5ea/0x670 drivers/video/fbdev/core/fbcon.c:1281
fbcon_scroll+0x41e/0x560 drivers/video/fbdev/core/fbcon.c:1847
con_scroll+0x464/0x6a0 drivers/tty/vt/vt.c:577
lf+0x274/0x2d0 drivers/tty/vt/vt.c:1461
do_con_trol+0x5ea/0x3d80 drivers/tty/vt/vt.c:2149
do_con_write+0x780/0x10c0 drivers/tty/vt/vt.c:2905
con_write+0x28/0xc0 drivers/tty/vt/vt.c:3245
do_output_char+0x5de/0x850 drivers/tty/n_tty.c:433
process_output drivers/tty/n_tty.c:500 [inline]
n_tty_write+0x442/0xb00 drivers/tty/n_tty.c:2406
iterate_tty_write+0x2b5/0x630 drivers/tty/tty_io.c:1017
file_tty_write.constprop.0+0x20c/0x3b0 drivers/tty/tty_io.c:1088
call_write_iter include/linux/fs.h:2085 [inline]
do_iter_readv_writev+0x210/0x3c0 fs/read_write.c:737
do_iter_write+0x181/0x4e0 fs/read_write.c:862
vfs_writev+0x15b/0x4d0 fs/read_write.c:935
do_writev+0x136/0x370 fs/read_write.c:978
do_syscall_x64 arch/x86/entry/common.c:51 [inline]
do_syscall_64+0x59/0x110 arch/x86/entry/common.c:81
entry_SYSCALL_64_after_hwframe+0x78/0xe2
When the virtual console is rotated in the backend state, it can lead to
inconsistencies between the size of the virtual console's size and its
hook functions. In such cases, clearing the screen may result in
out-of-bounds issue.
This issue has already been fixed by commit eabb03293087 ("fbdev:
Refactoring the fbcon packed pixel drawing routines") on v6.15-rc1, but it
still exists in the stable version.
It was unclear if there were other scenarios for this issue, and I tried
to add pr_err in sys_fillrect. But as Helge pointed out[1], sys_fillrect
is on the console printing code path and adding printing here might cause
infinite loop. So let's just fix the known scenario.
Fix it by moving set_blitting_type() to the visible area of the VC.
Link: https://lore.kernel.org/all/aef7d5fd-2926-4c58-b720-4af58aa380d3@gmx.de/ [1]
CC: stable@vger.kernel.org # for stable-6.6, fbdev had been refactored on 6.15-rc1
Fixes: 68648ed1f58d ("fbdev: add drawing functions for framebuffers in system RAM")
Signed-off-by: Gu Bowen <gubowen5@huawei.com>
---
drivers/video/fbdev/core/fbcon.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/video/fbdev/core/fbcon.c b/drivers/video/fbdev/core/fbcon.c
index 78a5b22c8d15..8139ac8a666f 100644
--- a/drivers/video/fbdev/core/fbcon.c
+++ b/drivers/video/fbdev/core/fbcon.c
@@ -2702,9 +2702,9 @@ static void fbcon_modechanged(struct fb_info *info)
return;
p = &fb_display[vc->vc_num];
- set_blitting_type(vc, info);
if (con_is_visible(vc)) {
+ set_blitting_type(vc, info);
var_to_display(p, &info->var, info);
cols = FBCON_SWAP(ops->rotate, info->var.xres, info->var.yres);
rows = FBCON_SWAP(ops->rotate, info->var.yres, info->var.xres);
--
2.43.0
^ permalink raw reply related
* [PATCH] fbcon: Add check for return value
From: Ваторопин Андрей @ 2025-12-17 9:11 UTC (permalink / raw)
To: Simona Vetter
Cc: Ваторопин Андрей,
Helge Deller, Thomas Zimmermann, Ville Syrjälä,
Sam Ravnborg, Shixiong Ou, Kees Cook, Zsolt Kajtar, Andrew Morton,
Antonino A. Daplas, linux-fbdev@vger.kernel.org,
dri-devel@lists.freedesktop.org, linux-kernel@vger.kernel.org,
lvc-project@linuxtesting.org, stable@vger.kernel.org
From: Andrey Vatoropin <a.vatoropin@crpt.ru>
If fbcon_open() fails when called from con2fb_acquire_newinfo() then
info->fbcon_par pointer remains NULL which is later dereferenced.
Add check for return value of the function con2fb_acquire_newinfo() to
avoid it.
Found by Linux Verification Center (linuxtesting.org) with SVACE.
Fixes: d1baa4ffa677 ("fbcon: set_con2fb_map fixes")
Cc: stable@vger.kernel.org
Signed-off-by: Andrey Vatoropin <a.vatoropin@crpt.ru>
---
drivers/video/fbdev/core/fbcon.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/drivers/video/fbdev/core/fbcon.c b/drivers/video/fbdev/core/fbcon.c
index e7e07eb2142e..7453377f3433 100644
--- a/drivers/video/fbdev/core/fbcon.c
+++ b/drivers/video/fbdev/core/fbcon.c
@@ -1047,7 +1047,8 @@ static void fbcon_init(struct vc_data *vc, bool init)
return;
if (!info->fbcon_par)
- con2fb_acquire_newinfo(vc, info, vc->vc_num);
+ if (con2fb_acquire_newinfo(vc, info, vc->vc_num))
+ return;
/* If we are not the first console on this
fb, copy the font from that console */
--
2.43.0
^ permalink raw reply related
* Re: [PATCH v3 7/9] efi: Refactor init_primary_display() helpers
From: Ard Biesheuvel @ 2025-12-16 13:40 UTC (permalink / raw)
To: Thomas Zimmermann
Cc: javierm, arnd, richard.lyu, helgaas, x86, linux-arm-kernel,
linux-kernel, linux-efi, loongarch, linux-riscv, dri-devel,
linux-hyperv, linux-pci, linux-fbdev
In-Reply-To: <20251126160854.553077-8-tzimmermann@suse.de>
On Wed, 26 Nov 2025 at 17:09, Thomas Zimmermann <tzimmermann@suse.de> wrote:
>
> Rework the kernel's init_primary_display() helpers to allow for later
> support of additional config-table entries and EDID information. No
> functional changes.
>
> Signed-off-by: Thomas Zimmermann <tzimmermann@suse.de>
> ---
> arch/loongarch/kernel/efi.c | 22 +++++++++++-----------
> drivers/firmware/efi/efi-init.c | 19 ++++++++++---------
> 2 files changed, 21 insertions(+), 20 deletions(-)
>
This patch seems unnecessary now that we've replace one table with another.
I've dropped it for now - let me know if you really want to keep it.
> diff --git a/arch/loongarch/kernel/efi.c b/arch/loongarch/kernel/efi.c
> index 638a392d2cd2..1ef38036e8ae 100644
> --- a/arch/loongarch/kernel/efi.c
> +++ b/arch/loongarch/kernel/efi.c
> @@ -81,19 +81,19 @@ EXPORT_SYMBOL_GPL(sysfb_primary_display);
>
> static void __init init_primary_display(void)
> {
> - struct screen_info *si;
> -
> - if (screen_info_table == EFI_INVALID_TABLE_ADDR)
> - return;
> -
> - si = early_memremap(screen_info_table, sizeof(*si));
> - if (!si) {
> - pr_err("Could not map screen_info config table\n");
> + if (screen_info_table == EFI_INVALID_TABLE_ADDR) {
> + struct screen_info *si = early_memremap(screen_info_table, sizeof(*si));
> +
> + if (!si) {
> + pr_err("Could not map screen_info config table\n");
> + return;
> + }
> + sysfb_primary_display.screen = *si;
> + memset(si, 0, sizeof(*si));
> + early_memunmap(si, sizeof(*si));
> + } else {
> return;
> }
> - sysfb_primary_display.screen = *si;
> - memset(si, 0, sizeof(*si));
> - early_memunmap(si, sizeof(*si));
>
> memblock_reserve(__screen_info_lfb_base(&sysfb_primary_display.screen),
> sysfb_primary_display.screen.lfb_size);
> diff --git a/drivers/firmware/efi/efi-init.c b/drivers/firmware/efi/efi-init.c
> index d1d418a34407..ca697d485116 100644
> --- a/drivers/firmware/efi/efi-init.c
> +++ b/drivers/firmware/efi/efi-init.c
> @@ -67,10 +67,9 @@ EXPORT_SYMBOL_GPL(sysfb_primary_display);
>
> static void __init init_primary_display(void)
> {
> - struct screen_info *si;
> -
> if (screen_info_table != EFI_INVALID_TABLE_ADDR) {
> - si = early_memremap(screen_info_table, sizeof(*si));
> + struct screen_info *si = early_memremap(screen_info_table, sizeof(*si));
> +
> if (!si) {
> pr_err("Could not map screen_info config table\n");
> return;
> @@ -78,14 +77,16 @@ static void __init init_primary_display(void)
> sysfb_primary_display.screen = *si;
> memset(si, 0, sizeof(*si));
> early_memunmap(si, sizeof(*si));
> + } else {
> + return;
> + }
>
> - if (memblock_is_map_memory(sysfb_primary_display.screen.lfb_base))
> - memblock_mark_nomap(sysfb_primary_display.screen.lfb_base,
> - sysfb_primary_display.screen.lfb_size);
> + if (memblock_is_map_memory(sysfb_primary_display.screen.lfb_base))
> + memblock_mark_nomap(sysfb_primary_display.screen.lfb_base,
> + sysfb_primary_display.screen.lfb_size);
>
> - if (IS_ENABLED(CONFIG_EFI_EARLYCON))
> - efi_earlycon_reprobe();
> - }
> + if (IS_ENABLED(CONFIG_EFI_EARLYCON))
> + efi_earlycon_reprobe();
> }
>
> static int __init uefi_init(u64 efi_system_table)
> --
> 2.51.1
>
^ permalink raw reply
* Re: [PATCH v3 9/9] efi: libstub: Simplify interfaces for primary_display
From: Ard Biesheuvel @ 2025-12-16 13:23 UTC (permalink / raw)
To: Thomas Zimmermann
Cc: javierm, arnd, richard.lyu, helgaas, x86, linux-arm-kernel,
linux-kernel, linux-efi, loongarch, linux-riscv, dri-devel,
linux-hyperv, linux-pci, linux-fbdev
In-Reply-To: <20251126160854.553077-10-tzimmermann@suse.de>
Hi Thomas
On Wed, 26 Nov 2025 at 17:09, Thomas Zimmermann <tzimmermann@suse.de> wrote:
>
> Rename alloc_primary_display() and __alloc_primary_display(), clarify
> free semantics to make interfaces easier to understand.
>
> Rename alloc_primary_display() to lookup_primary_display() as it
> does not necessarily allocate. Then rename __alloc_primary_display()
> to the new alloc_primary_display(). The helper belongs to
> free_primary_display), so it should be named without underscores.
>
> The lookup helper does not necessarily allocate, so the output
> parameter needs_free to indicate when free should be called.
I don't understand why we need this. Whether or not the helper
allocates is a compile time decision, and in builds where it doesn't,
the free helper doesn't do anything.
I'm all for making things simpler, but I don't think this patch
achieves that tbh.
I've queued up this series now up until this patch - once we converge
on the simplification, I'm happy to apply it on top.
Thanks,
> Pass
> an argument through the calls to track this state. Put the free
> handling into release_primary_display() for simplificy.
>
> Also move the comment fro primary_display.c to efi-stub-entry.c,
> where it now describes lookup_primary_display().
>
> Signed-off-by: Thomas Zimmermann <tzimmermann@suse.de>
> ---
> drivers/firmware/efi/libstub/efi-stub-entry.c | 23 +++++++++++++++++--
> drivers/firmware/efi/libstub/efi-stub.c | 22 ++++++++++++------
> drivers/firmware/efi/libstub/efistub.h | 2 +-
> .../firmware/efi/libstub/primary_display.c | 17 +-------------
> drivers/firmware/efi/libstub/zboot.c | 6 +++--
> 5 files changed, 42 insertions(+), 28 deletions(-)
>
> diff --git a/drivers/firmware/efi/libstub/efi-stub-entry.c b/drivers/firmware/efi/libstub/efi-stub-entry.c
> index aa85e910fe59..3077b51fe0b2 100644
> --- a/drivers/firmware/efi/libstub/efi-stub-entry.c
> +++ b/drivers/firmware/efi/libstub/efi-stub-entry.c
> @@ -14,10 +14,29 @@ static void *kernel_image_addr(void *addr)
> return addr + kernel_image_offset;
> }
>
> -struct sysfb_display_info *alloc_primary_display(void)
> +/*
> + * There are two ways of populating the core kernel's sysfb_primary_display
> + * via the stub:
> + *
> + * - using a configuration table, which relies on the EFI init code to
> + * locate the table and copy the contents; or
> + *
> + * - by linking directly to the core kernel's copy of the global symbol.
> + *
> + * The latter is preferred because it makes the EFIFB earlycon available very
> + * early, but it only works if the EFI stub is part of the core kernel image
> + * itself. The zboot decompressor can only use the configuration table
> + * approach.
> + */
> +
> +struct sysfb_display_info *lookup_primary_display(bool *needs_free)
> {
> + *needs_free = true;
> +
> if (IS_ENABLED(CONFIG_ARM))
> - return __alloc_primary_display();
> + return alloc_primary_display();
> +
> + *needs_free = false;
>
> if (IS_ENABLED(CONFIG_X86) ||
> IS_ENABLED(CONFIG_EFI_EARLYCON) ||
> diff --git a/drivers/firmware/efi/libstub/efi-stub.c b/drivers/firmware/efi/libstub/efi-stub.c
> index 42d6073bcd06..dc545f62c62b 100644
> --- a/drivers/firmware/efi/libstub/efi-stub.c
> +++ b/drivers/firmware/efi/libstub/efi-stub.c
> @@ -51,14 +51,14 @@ static bool flat_va_mapping = (EFI_RT_VIRTUAL_OFFSET != 0);
> void __weak free_primary_display(struct sysfb_display_info *dpy)
> { }
>
> -static struct sysfb_display_info *setup_primary_display(void)
> +static struct sysfb_display_info *setup_primary_display(bool *dpy_needs_free)
> {
> struct sysfb_display_info *dpy;
> struct screen_info *screen = NULL;
> struct edid_info *edid = NULL;
> efi_status_t status;
>
> - dpy = alloc_primary_display();
> + dpy = lookup_primary_display(dpy_needs_free);
> if (!dpy)
> return NULL;
> screen = &dpy->screen;
> @@ -68,15 +68,22 @@ static struct sysfb_display_info *setup_primary_display(void)
>
> status = efi_setup_graphics(screen, edid);
> if (status != EFI_SUCCESS)
> - goto err_free_primary_display;
> + goto err___free_primary_display;
>
> return dpy;
>
> -err_free_primary_display:
> - free_primary_display(dpy);
> +err___free_primary_display:
> + if (*dpy_needs_free)
> + free_primary_display(dpy);
> return NULL;
> }
>
> +static void release_primary_display(struct sysfb_display_info *dpy, bool dpy_needs_free)
> +{
> + if (dpy && dpy_needs_free)
> + free_primary_display(dpy);
> +}
> +
> static void install_memreserve_table(void)
> {
> struct linux_efi_memreserve *rsv;
> @@ -156,13 +163,14 @@ efi_status_t efi_stub_common(efi_handle_t handle,
> char *cmdline_ptr)
> {
> struct sysfb_display_info *dpy;
> + bool dpy_needs_free;
> efi_status_t status;
>
> status = check_platform_features();
> if (status != EFI_SUCCESS)
> return status;
>
> - dpy = setup_primary_display();
> + dpy = setup_primary_display(&dpy_needs_free);
>
> efi_retrieve_eventlog();
>
> @@ -182,7 +190,7 @@ efi_status_t efi_stub_common(efi_handle_t handle,
>
> status = efi_boot_kernel(handle, image, image_addr, cmdline_ptr);
>
> - free_primary_display(dpy);
> + release_primary_display(dpy, dpy_needs_free);
>
> return status;
> }
> diff --git a/drivers/firmware/efi/libstub/efistub.h b/drivers/firmware/efi/libstub/efistub.h
> index 979a21818cc1..1503ffb82903 100644
> --- a/drivers/firmware/efi/libstub/efistub.h
> +++ b/drivers/firmware/efi/libstub/efistub.h
> @@ -1176,8 +1176,8 @@ efi_enable_reset_attack_mitigation(void) { }
>
> void efi_retrieve_eventlog(void);
>
> +struct sysfb_display_info *lookup_primary_display(bool *needs_free);
> struct sysfb_display_info *alloc_primary_display(void);
> -struct sysfb_display_info *__alloc_primary_display(void);
> void free_primary_display(struct sysfb_display_info *dpy);
>
> void efi_cache_sync_image(unsigned long image_base,
> diff --git a/drivers/firmware/efi/libstub/primary_display.c b/drivers/firmware/efi/libstub/primary_display.c
> index cdaebab26514..34c54ac1e02a 100644
> --- a/drivers/firmware/efi/libstub/primary_display.c
> +++ b/drivers/firmware/efi/libstub/primary_display.c
> @@ -7,24 +7,9 @@
>
> #include "efistub.h"
>
> -/*
> - * There are two ways of populating the core kernel's sysfb_primary_display
> - * via the stub:
> - *
> - * - using a configuration table, which relies on the EFI init code to
> - * locate the table and copy the contents; or
> - *
> - * - by linking directly to the core kernel's copy of the global symbol.
> - *
> - * The latter is preferred because it makes the EFIFB earlycon available very
> - * early, but it only works if the EFI stub is part of the core kernel image
> - * itself. The zboot decompressor can only use the configuration table
> - * approach.
> - */
> -
> static efi_guid_t primary_display_guid = LINUX_EFI_PRIMARY_DISPLAY_TABLE_GUID;
>
> -struct sysfb_display_info *__alloc_primary_display(void)
> +struct sysfb_display_info *alloc_primary_display(void)
> {
> struct sysfb_display_info *dpy;
> efi_status_t status;
> diff --git a/drivers/firmware/efi/libstub/zboot.c b/drivers/firmware/efi/libstub/zboot.c
> index 4b76f74c56da..c1fd1fdbcb08 100644
> --- a/drivers/firmware/efi/libstub/zboot.c
> +++ b/drivers/firmware/efi/libstub/zboot.c
> @@ -26,9 +26,11 @@ void __weak efi_cache_sync_image(unsigned long image_base,
> // executable code loaded into memory to be safe for execution.
> }
>
> -struct sysfb_display_info *alloc_primary_display(void)
> +struct sysfb_display_info *lookup_primary_display(bool *needs_free)
> {
> - return __alloc_primary_display();
> + *needs_free = true;
> +
> + return alloc_primary_display();
> }
>
> asmlinkage efi_status_t __efiapi
> --
> 2.51.1
>
^ permalink raw reply
* Re: [PATCH v6 1/4] dt-bindings: backlight: Add max25014 support
From: Maud Spierings @ 2025-12-16 8:19 UTC (permalink / raw)
To: Rob Herring
Cc: Frank Li, Lee Jones, Daniel Thompson, Jingoo Han, Pavel Machek,
Krzysztof Kozlowski, Conor Dooley, Helge Deller, Shawn Guo,
Sascha Hauer, Pengutronix Kernel Team, Fabio Estevam,
Liam Girdwood, Mark Brown, dri-devel, linux-leds, devicetree,
linux-kernel, linux-fbdev, imx, linux-arm-kernel
In-Reply-To: <20251209190722.GA945742-robh@kernel.org>
On 12/9/25 20:07, Rob Herring wrote:
> On Mon, Dec 08, 2025 at 02:56:50PM +0100, Maud Spierings wrote:
>> On 12/2/25 15:53, Frank Li wrote:
>>> On Tue, Dec 02, 2025 at 08:46:21AM +0100, Maud Spierings wrote:
>>>> On 12/1/25 17:52, Frank Li wrote:
>>>>> On Mon, Dec 01, 2025 at 12:53:20PM +0100, Maud Spierings via B4 Relay wrote:
>>>>>> From: Maud Spierings <maudspierings@gocontroll.com>
>>>>>>
>>>>>> The Maxim MAX25014 is a 4-channel automotive grade backlight driver IC
>>>>>> with integrated boost controller.
>>>>>>
>>>>>> Signed-off-by: Maud Spierings <maudspierings@gocontroll.com>
>>>>>>
>>>>>> ---
>>>>>>
>>>>>> In the current implementation the control registers for channel 1,
>>>>>> control all channels. So only one led subnode with led-sources is
>>>>>> supported right now. If at some point the driver functionality is
>>>>>> expanded the bindings can be easily extended with it.
>>>>>> ---
>>>>>> .../bindings/leds/backlight/maxim,max25014.yaml | 107 +++++++++++++++++++++
>>>>>> MAINTAINERS | 5 +
>>>>>> 2 files changed, 112 insertions(+)
>>>>>>
>>>>>> diff --git a/Documentation/devicetree/bindings/leds/backlight/maxim,max25014.yaml b/Documentation/devicetree/bindings/leds/backlight/maxim,max25014.yaml
>>>>>> new file mode 100644
>>>>>> index 000000000000..e83723224b07
>>>>>> --- /dev/null
>>>>>> +++ b/Documentation/devicetree/bindings/leds/backlight/maxim,max25014.yaml
>>>>>> @@ -0,0 +1,107 @@
>>>>>> +# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause)
>>>>>> +%YAML 1.2
>>>>>> +---
>>>>>> +$id: http://devicetree.org/schemas/leds/backlight/maxim,max25014.yaml#
>>>>>> +$schema: http://devicetree.org/meta-schemas/core.yaml#
>>>>>> +
>>>>>> +title: Maxim max25014 backlight controller
>>>>>> +
>>>>>> +maintainers:
>>>>>> + - Maud Spierings <maudspierings@gocontroll.com>
>>>>>> +
>>>>>> +properties:
>>>>>> + compatible:
>>>>>> + enum:
>>>>>> + - maxim,max25014
>>>>>> +
>>>>>> + reg:
>>>>>> + maxItems: 1
>>>>>> +
>>>>>> + "#address-cells":
>>>>>> + const: 1
>>>>>> +
>>>>>> + "#size-cells":
>>>>>> + const: 0
>>>>>> +
>>>>>> + enable-gpios:
>>>>>> + maxItems: 1
>>>>>> +
>>>>>> + interrupts:
>>>>>> + maxItems: 1
>>>>>> +
>>>>>> + power-supply:
>>>>>> + description: Regulator which controls the boost converter input rail.
>>>>>> +
>>>>>> + pwms:
>>>>>> + maxItems: 1
>>>>>> +
>>>>>> + maxim,iset:
>>>>>> + $ref: /schemas/types.yaml#/definitions/uint32
>>>>>> + maximum: 15
>>>>>> + default: 11
>>>>>> + description:
>>>>>> + Value of the ISET field in the ISET register. This controls the current
>>>>>> + scale of the outputs, a higher number means more current.
>>>>>> +
>>>>>> + led@0:
>>>>>
>>>>> define whole binding, allow 0-3. binding is not related with driver's
>>>>> implement.
>>>>>
>>>>> it'd better put unders leds.
>>>>>
>>>>
>>>> so like:
>>>>
>>>> backlight: backlight@6f {
>>>> compatible = "maxim,max25014";
>>>> reg = <0x6f>;
>>>> enable-gpios = <&gpio1 4 GPIO_ACTIVE_HIGH>;
>>>> pinctrl-names = "default";
>>>> pinctrl-0 = <&pinctrl_backlight>;
>>>> maxim,iset = <7>;
>>>>
>>>> leds {
>>>> #address-cells = <1>;
>>>> #size-cells = <0>;
>>>>
>>>> led@0 {
>>>> reg = <0>;
>>>> led-sources = <0 1 2>;
>>>> default-brightness = <50>;
>>>> };
>>>>
>>>> optional led@#....
>>>> };
>>>> };
>>>>
>>>> right?
>>>
>>> yes.
>>>
>>
>> I am feeling a bit weird about these led sub nodes, because it is not
>> programmed as a led driver, it is programmed as a backlight. I am trying to
>> figure out how this would be used later when the led strings are
>> individually controllable.
>>
>> it isn't possible to link the seperate strings to different displays because
>> it is only one backlight device, so I don't seen any reason why it would
>> ever be used in another way than what it is now, were all strings are
>> programmed by one register.
>>
>> The only way I can make sense of it is if instead I program this device as a
>> led driver and then use the led_bl driver as the actual backlight.
>>
>> Thats a pretty big step in a different direction, but then the led subnodes
>> at least can be properly used I feel.
>
> If you don't have any use for anything other than driving a single
> backlight, then I'd just drop the led nodes completely.
Theoretically with how the registers are laid out, it should be able to
control 4 led strings individually. But as I said when I configure led
string 1 it will also affect all the others seemingly. I am not sure if
with some other configuration you can indeed do individual control.
Before I start converting stuff back to how it was several versions ago.
Frank, do you agree with removing the led nodes in this case? I don't
want to get stuck between two different paths.
Kind regards,
Maud
^ permalink raw reply
* [syzbot] Monthly fbdev report (Dec 2025)
From: syzbot @ 2025-12-16 1:32 UTC (permalink / raw)
To: deller, dri-devel, linux-fbdev, linux-kernel, syzkaller-bugs
Hello fbdev maintainers/developers,
This is a 31-day syzbot report for the fbdev subsystem.
All related reports/information can be found at:
https://syzkaller.appspot.com/upstream/s/fbdev
During the period, 0 new issues were detected and 0 were fixed.
In total, 6 issues are still open and 29 have already been fixed.
Some of the still happening issues:
Ref Crashes Repro Title
<1> 920 Yes KASAN: slab-out-of-bounds Read in fbcon_prepare_logo
https://syzkaller.appspot.com/bug?extid=0c815b25cdb3678e7083
<2> 381 Yes KASAN: vmalloc-out-of-bounds Write in imageblit (6)
https://syzkaller.appspot.com/bug?extid=5a40432dfe8f86ee657a
<3> 134 No KASAN: vmalloc-out-of-bounds Write in fillrect
https://syzkaller.appspot.com/bug?extid=7a63ce155648954e749b
<4> 7 No KASAN: slab-out-of-bounds Read in soft_cursor (2)
https://syzkaller.appspot.com/bug?extid=ae44b38396335bd847cd
---
This report is generated by a bot. It may contain errors.
See https://goo.gl/tpsmEJ for more information about syzbot.
syzbot engineers can be reached at syzkaller@googlegroups.com.
To disable reminders for individual bugs, reply with the following command:
#syz set <Ref> no-reminders
To change bug's subsystems, reply with:
#syz set <Ref> subsystems: new-subsystem
You may send multiple commands in a single email message.
^ permalink raw reply
* [PATCH] fbdev: xilinxfb: request memory region before mapping framebuffer
From: patdiviyam @ 2025-12-15 22:53 UTC (permalink / raw)
To: dri-devel; +Cc: tzimmermann, deller, linux-fbdev, DiviyamPathak
From: DiviyamPathak <patdiviyam@gmail.com>
The xilinxfb driver maps a physical framebuffer address with ioremap()
without first reserving the memory region. This can conflict with other
drivers accessing the same resource.
Request the memory region with devm_request_mem_region() before mapping
the framebuffer and use managed mappings for proper lifetime handling.
This addresses the fbdev TODO about requesting memory regions and avoids
potential resource conflicts.
Signed-off-by: DiviyamPathak <patdiviyam@gmail.com>
---
drivers/video/fbdev/xilinxfb.c | 30 +++++++++++++++++-------------
1 file changed, 17 insertions(+), 13 deletions(-)
diff --git a/drivers/video/fbdev/xilinxfb.c b/drivers/video/fbdev/xilinxfb.c
index 0a6e05cd155a..f18437490de8 100644
--- a/drivers/video/fbdev/xilinxfb.c
+++ b/drivers/video/fbdev/xilinxfb.c
@@ -280,19 +280,27 @@ static int xilinxfb_assign(struct platform_device *pdev,
/* Allocate the framebuffer memory */
if (pdata->fb_phys) {
drvdata->fb_phys = pdata->fb_phys;
- drvdata->fb_virt = ioremap(pdata->fb_phys, fbsize);
+ /* Request the memory region before mapping */
+ if (!devm_request_mem_region(dev, pdata->fb_phys, fbsize,
+ DRIVER_NAME)) {
+ dev_err(dev, "Cannot request framebuffer memory region\n");
+ return -EBUSY;
+ }
+ drvdata->fb_virt = devm_ioremap(dev, pdata->fb_phys, fbsize);
+ if (!drvdata->fb_virt) {
+ dev_err(dev, "Could not map framebuffer memory\n");
+ return -ENOMEM;
+ }
} else {
drvdata->fb_alloced = 1;
drvdata->fb_virt = dma_alloc_coherent(dev, PAGE_ALIGN(fbsize),
- &drvdata->fb_phys,
- GFP_KERNEL);
- }
-
- if (!drvdata->fb_virt) {
- dev_err(dev, "Could not allocate frame buffer memory\n");
- return -ENOMEM;
+ &drvdata->fb_phys,
+ GFP_KERNEL);
+ if (!drvdata->fb_virt) {
+ dev_err(dev, "Could not allocate frame buffer memory\n");
+ return -ENOMEM;
+ }
}
-
/* Clear (turn to black) the framebuffer */
memset_io((void __iomem *)drvdata->fb_virt, 0, fbsize);
@@ -362,8 +370,6 @@ static int xilinxfb_assign(struct platform_device *pdev,
if (drvdata->fb_alloced)
dma_free_coherent(dev, PAGE_ALIGN(fbsize), drvdata->fb_virt,
drvdata->fb_phys);
- else
- iounmap(drvdata->fb_virt);
/* Turn off the display */
xilinx_fb_out32(drvdata, REG_CTRL, 0);
@@ -386,8 +392,6 @@ static void xilinxfb_release(struct device *dev)
if (drvdata->fb_alloced)
dma_free_coherent(dev, PAGE_ALIGN(drvdata->info.fix.smem_len),
drvdata->fb_virt, drvdata->fb_phys);
- else
- iounmap(drvdata->fb_virt);
/* Turn off the display */
xilinx_fb_out32(drvdata, REG_CTRL, 0);
--
2.43.0
^ permalink raw reply related
* Re: [PATCH v2] fbdev: arkfb: Request legacy VGA I/O region
From: Swaraj Gaikwad @ 2025-12-14 11:19 UTC (permalink / raw)
To: sam
Cc: Frank.Li, akpm, david.hunter.linux, deller, donettom, dri-devel,
hverkuil+cisco, kees, konrad.dybcio, linux-fbdev, linux-kernel,
nicolas.dufresne, rongqianfeng, skhan, swarajgaikwad1925,
vivek.kasireddy, ydirson, ziy
In-Reply-To: <20251213223850.GA419250@ravnborg.org>
Hi Sam,
Thanks for the review.
You are right that the cast to (void __iomem *) makes it look like memory,
but the resource is explicitly initialized as I/O ports a few lines earlier:
vga_res.flags = IORESOURCE_IO;
Since the resource flag is IORESOURCE_IO (targeting the legacy VGA ports),
I used devm_request_region() instead of devm_request_mem_region().
Best regards,
Swaraj
^ permalink raw reply
* Re: [PATCH 2/8] Add Advantech EIO GPIO driver
From: Bartosz Golaszewski @ 2025-12-14 0:54 UTC (permalink / raw)
To: Ramiro Oliveira
Cc: linux-kernel, linux-gpio, linux-hwmon, linux-i2c, dri-devel,
linux-fbdev, linux-watchdog, linux-pm, Wenkai Chung,
Francisco Aragon-Trivino, Hongzhi Wang, Mikhail Tsukerman,
Thomas Kastner, Lee Jones, Linus Walleij, Bartosz Golaszewski,
Guenter Roeck, Andi Shyti, Daniel Thompson, Jingoo Han,
Helge Deller, Wim Van Sebroeck, Rafael J. Wysocki, Daniel Lezcano,
Zhang Rui, Lukasz Luba
In-Reply-To: <20251212-upstream-v1-v1-2-d50d40ec8d8a@advantech.com>
On Fri, 12 Dec 2025 17:40:53 +0100, Ramiro Oliveira
<ramiro.oliveira@advantech.com> said:
> This driver controls the GPIO component of the Advantech EIO chip.
>
> Signed-off-by: Ramiro Oliveira <ramiro.oliveira@advantech.com>
> ---
> MAINTAINERS | 1 +
> drivers/gpio/Kconfig | 6 ++
> drivers/gpio/Makefile | 1 +
> drivers/gpio/gpio-eio.c | 273 ++++++++++++++++++++++++++++++++++++++++++++++++
> 4 files changed, 281 insertions(+)
>
> diff --git a/MAINTAINERS b/MAINTAINERS
> index bd9279796c2f..359d4a13f212 100644
> --- a/MAINTAINERS
> +++ b/MAINTAINERS
> @@ -619,6 +619,7 @@ F: drivers/platform/x86/adv_swbutton.c
> ADVANTECH EIO DRIVER
> M: Ramiro Oliveira <ramiro.oliveira@advantech.com>
> S: Maintained
> +F: drivers/gpio/gpio-eio.c
Instead of churning MAINTAINERS in every patch of the series, I suggest you
add a separate patch adding the full entry at the end.
> F: drivers/mfd/eio_core.c
> F: include/linux/mfd/eio.h
>
> diff --git a/drivers/gpio/Kconfig b/drivers/gpio/Kconfig
> index bd185482a7fd..628a914842bd 100644
> --- a/drivers/gpio/Kconfig
> +++ b/drivers/gpio/Kconfig
> @@ -277,6 +277,12 @@ config GPIO_DWAPB
> Say Y or M here to build support for the Synopsys DesignWare APB
> GPIO block.
>
> +config GPIO_EIO
> + tristate "Advantech EIO GPIO"
> + depends on MFD_EIO
> + help
> + Say Y or M to build support for Advantech EIO GPIO block.
> +
> config GPIO_EIC_SPRD
> tristate "Spreadtrum EIC support"
> depends on ARCH_SPRD || COMPILE_TEST
> diff --git a/drivers/gpio/Makefile b/drivers/gpio/Makefile
> index 2421a8fd3733..ba3883d5e4a0 100644
> --- a/drivers/gpio/Makefile
> +++ b/drivers/gpio/Makefile
> @@ -64,6 +64,7 @@ obj-$(CONFIG_GPIO_DLN2) += gpio-dln2.o
> obj-$(CONFIG_GPIO_DS4520) += gpio-ds4520.o
> obj-$(CONFIG_GPIO_DWAPB) += gpio-dwapb.o
> obj-$(CONFIG_GPIO_EIC_SPRD) += gpio-eic-sprd.o
> +obj-$(CONFIG_GPIO_EIO) += gpio-eio.o
> obj-$(CONFIG_GPIO_ELKHARTLAKE) += gpio-elkhartlake.o
> obj-$(CONFIG_GPIO_EM) += gpio-em.o
> obj-$(CONFIG_GPIO_EN7523) += gpio-en7523.o
> diff --git a/drivers/gpio/gpio-eio.c b/drivers/gpio/gpio-eio.c
> new file mode 100644
> index 000000000000..50f66a325e8f
> --- /dev/null
> +++ b/drivers/gpio/gpio-eio.c
> @@ -0,0 +1,273 @@
> +// SPDX-License-Identifier: GPL-2.0-only
> +/*
> + * GPIO driver for Advantech EIO Embedded controller.
> + *
> + * Copyright (C) 2025 Advantech Corporation. All rights reserved.
> + */
> +
> +#include <linux/errno.h>
> +#include <linux/gpio.h>
Don't include this, it's a legacy header as per one of the first lines in this
file.
> +#include <linux/gpio/driver.h>
> +#include <linux/mfd/core.h>
> +#include <linux/mfd/eio.h>
> +#include <linux/module.h>
> +
> +#define GPIO_MAX_PINS 48
> +#define GPIO_WRITE 0x18
> +#define GPIO_READ 0x19
> +
> +struct eio_gpio_dev {
> + u64 avail;
> + int max;
> + struct gpio_chip chip;
> + struct device *dev;
> +};
> +
> +struct {
> + int size;
> + bool write;
> +} ctrl_para[] = {
> + { 0x01, false }, { 0x00, false }, { 0x00, false }, { 0x02, false },
> + { 0x01, false }, { 0x00, false }, { 0x00, false }, { 0x00, false },
> + { 0x00, false }, { 0x00, false }, { 0x00, false }, { 0x00, false },
> + { 0x00, false }, { 0x00, false }, { 0x00, false }, { 0x00, false },
> + { 0x01, true }, { 0x01, true }, { 0x02, true }, { 0x02, true },
> + { 0x02, false }, { 0x10, false }
> +};
This should be static.
> +
> +enum {
> + GPIO_STATUS = 0,
> + GPIO_GROUP_AVAIL = 3,
> + GPIO_ERROR = 0x04,
> + GPIO_PIN_DIR = 0x10,
> + GPIO_PIN_LEVEL = 0x11,
> + GPIO_GROUP_DIR = 0x12,
> + GPIO_GROUP_LEVEL = 0x13,
> + GPIO_MAPPING = 0x14,
> + GPIO_NAME = 0x15
> +} gpio_ctrl;
Do enum gpio_ctrl {. But also use a common prefix for all symbols in
this driver.
> +
> +struct {
> + int group;
> + int port;
> +} group_map[] = {
> + { 0, 0 }, { 0, 1 },
> + { 1, 0 }, { 1, 1 },
> + { 2, 0 }, { 2, 1 },
> + { 3, 0 }, { 3, 1 },
> + { 3, 2 }, { 3, 3 },
> + { 3, 4 }, { 3, 5 },
> + { 3, 6 }, { 3, 7 }
> +};
> +
> +static int timeout;
> +module_param(timeout, int, 0444);
> +MODULE_PARM_DESC(timeout, "Set PMC command timeout value.\n");
> +
> +static int pmc_write(struct device *mfd_dev, u8 ctrl, u8 dev_id, void *data)
> +{
> + struct pmc_op op = {
> + .cmd = GPIO_WRITE,
> + .control = ctrl,
> + .device_id = dev_id,
> + .payload = (u8 *)data,
> + .timeout = timeout,
> + };
> +
> + if (ctrl > ARRAY_SIZE(ctrl_para))
> + return -ENOMEM;
> +
> + if (!ctrl_para[ctrl].write)
> + return -EINVAL;
> +
> + op.size = ctrl_para[ctrl].size;
> +
> + return eio_core_pmc_operation(mfd_dev, &op);
> +}
> +
> +static int pmc_read(struct device *mfd_dev, u8 ctrl, u8 dev_id, void *data)
> +{
> + struct pmc_op op = {
> + .cmd = GPIO_READ,
> + .control = ctrl,
> + .device_id = dev_id,
> + .payload = (u8 *)data,
> + .timeout = timeout,
> + };
> +
> + if (ctrl > ARRAY_SIZE(ctrl_para))
> + return -ENOMEM;
> +
> + op.size = ctrl_para[ctrl].size;
> +
> + return eio_core_pmc_operation(mfd_dev, &op);
> +}
> +
> +static int get_dir(struct gpio_chip *chip, unsigned int offset)
> +{
> + u8 dir;
> + int ret;
> +
> + ret = pmc_read(chip->parent, GPIO_PIN_DIR, offset, &dir);
> + if (ret)
> + return ret;
> +
> + return dir ? 0 : 1;
> +}
> +
> +static int dir_input(struct gpio_chip *chip, unsigned int offset)
> +{
> + u8 dir = 0;
> +
> + return pmc_write(chip->parent, GPIO_PIN_DIR, offset, &dir);
> +}
> +
> +static int dir_output(struct gpio_chip *chip, unsigned int offset, int value)
> +{
> + u8 dir = 1;
> + u8 val = value;
> +
> + pmc_write(chip->parent, GPIO_PIN_DIR, offset, &dir);
> +
> + return pmc_write(chip->parent, GPIO_PIN_LEVEL, offset, &val);
> +}
> +
> +static int gpio_get(struct gpio_chip *chip, unsigned int offset)
> +{
> + u8 level;
> + int ret;
> +
> + ret = pmc_read(chip->parent, GPIO_PIN_LEVEL, offset, &level);
> + if (ret)
> + return ret;
> +
> + return level;
> +}
> +
> +static int gpio_set(struct gpio_chip *chip, unsigned int offset, int value)
> +{
> + u8 val = value;
> +
> + pmc_write(chip->parent, GPIO_PIN_LEVEL, offset, &val);
> +
> + return 0;
> +}
> +
> +static int check_support(struct device *dev)
> +{
> + u8 data;
> + int ret;
> +
> + ret = pmc_read(dev, GPIO_STATUS, 0, &data);
> + if (!ret)
> + return ret;
> +
> + if ((data & 0x01) == 0)
> + return -EOPNOTSUPP;
> +
> + return 0;
> +}
> +
> +static int check_pin(struct device *dev, int pin)
> +{
> + int ret;
> + int group, bit;
> + u16 data;
> +
> + /* Get pin mapping */
> + ret = pmc_read(dev, GPIO_MAPPING, pin, &data);
> + if (ret)
> + return ret;
> +
> + if ((data & 0xFF) > ARRAY_SIZE(group_map))
> + return -EINVAL;
> +
> + group = group_map[data & 0xFF].group;
> + bit = data >> 8;
> +
> + /* Check mapped pin */
> + ret = pmc_read(dev, GPIO_GROUP_AVAIL, group, &data);
> + if (ret)
> + return ret;
> +
> + return data & BIT(bit) ? 0 : -EOPNOTSUPP;
> +}
> +
> +static int gpio_init(struct device *mfd, struct eio_gpio_dev *eio_gpio)
> +{
> + int ret;
> + int i;
Keep these on the same line.
> + char str[GPIO_MAX_PINS + 1];
> +
> + memset(str, 0x30, sizeof(str));
> +
> + ret = check_support(mfd);
> + if (ret) {
> + dev_err(eio_gpio->dev, "GPIO not supported (%d)\n", ret);
return dev_err_probe()
> + return ret;
> + }
> +
> + eio_gpio->avail = 0;
> +
> + for (i = 0 ; i < GPIO_MAX_PINS ; i++) {
> + ret = check_pin(mfd, i);
> + if (ret)
> + continue;
> +
> + eio_gpio->avail |= BIT(i);
> + eio_gpio->max = i + 1;
> + str[GPIO_MAX_PINS - i] = '1';
> + }
> +
> + dev_info(eio_gpio->dev, "GPIO pins=%s\n", str);
> +
No need to print anything here.
> + return eio_gpio->max ? 0 : -EOPNOTSUPP;
> +}
> +
> +static const struct gpio_chip eio_gpio_chip = {
> + .label = KBUILD_MODNAME,
> + .owner = THIS_MODULE,
> + .direction_input = dir_input,
> + .get = gpio_get,
> + .direction_output = dir_output,
> + .set = gpio_set,
> + .get_direction = get_dir,
> + .base = -1,
> + .can_sleep = true,
> +};
Instead of having an unnecessary copy of the chip in .rodata, just use compound
literals when initiating it in probe().
> +
> +static int gpio_probe(struct platform_device *pdev)
> +{
> + struct device *dev = &pdev->dev;
> + struct eio_gpio_dev *eio_gpio;
> + struct eio_dev *eio_dev = dev_get_drvdata(dev->parent);
> +
> + if (!eio_dev) {
> + dev_err(dev, "Error contact eio_core\n");
> + return -ENODEV;
> + }
return dev_err_probe()
> +
> + eio_gpio = devm_kzalloc(dev, sizeof(*eio_gpio), GFP_KERNEL);
This can fail, please check the return value.
> + eio_gpio->dev = dev;
> +
> + if (gpio_init(dev->parent, eio_gpio))
> + return -EIO;
> +
> + eio_gpio->chip = eio_gpio_chip;
Don't use tabs like that please. Just stick to single spaces.
> + eio_gpio->chip.parent = dev->parent;
> + eio_gpio->chip.ngpio = eio_gpio->max;
> +
> + return devm_gpiochip_add_data(dev, &eio_gpio->chip, eio_gpio);
> +}
> +
> +static struct platform_driver gpio_driver = {
> + .probe = gpio_probe,
> + .driver = { .name = KBUILD_MODNAME, },
> +};
> +
> +module_platform_driver(gpio_driver);
> +
> +MODULE_AUTHOR("Wenkai Chung <wenkai.chung@advantech.com.tw>");
> +MODULE_AUTHOR("Ramiro Oliveira <ramiro.oliveira@advantech.com>");
> +MODULE_DESCRIPTION("GPIO driver for Advantech EIO embedded controller");
> +MODULE_LICENSE("GPL");
>
> --
> 2.43.0
>
>
^ permalink raw reply
* Re: [PATCH v2] fbdev: arkfb: Request legacy VGA I/O region
From: Sam Ravnborg @ 2025-12-13 22:38 UTC (permalink / raw)
To: Swaraj Gaikwad
Cc: Helge Deller, Andrew Morton, Hans Verkuil, Nicolas Dufresne,
Frank Li, Zi Yan, Donet Tom, Yann Dirson, Konrad Dybcio,
Vivek Kasireddy, Qianfeng Rong, Kees Cook,
open list:FRAMEBUFFER LAYER, open list:FRAMEBUFFER LAYER,
open list, skhan, david.hunter.linux
In-Reply-To: <20251213202239.8772-1-swarajgaikwad1925@gmail.com>
Hi Swaraj,
On Sat, Dec 13, 2025 at 08:22:34PM +0000, Swaraj Gaikwad wrote:
> The arkfb driver uses the legacy VGA I/O range (0x3c0+) but does not
> request it. This can cause conflicts with other drivers that try to
> reserve these ports.
>
> Fix this by using devm_request_region() during the probe function.
> This ensures the region is properly reserved and automatically released
> on driver detach.
>
> v1: https://lore.kernel.org/lkml/20251213154937.104301-1-swarajgaikwad1925@gmail.com/
> Signed-off-by: Swaraj Gaikwad <swarajgaikwad1925@gmail.com>
> ---
> v2:
> - Use resource_size(&vga_res) instead of hardcoded 64 * 1024.
> - (Feedback from Kees Cook)
>
> Compile-tested only on x86_64.
>
> drivers/video/fbdev/arkfb.c | 6 ++++++
> 1 file changed, 6 insertions(+)
>
> diff --git a/drivers/video/fbdev/arkfb.c b/drivers/video/fbdev/arkfb.c
> index ec084323115f..24e4c20d1a32 100644
> --- a/drivers/video/fbdev/arkfb.c
> +++ b/drivers/video/fbdev/arkfb.c
> @@ -1018,6 +1018,12 @@ static int ark_pci_probe(struct pci_dev *dev, const struct pci_device_id *id)
>
> pcibios_bus_to_resource(dev->bus, &vga_res, &bus_reg);
>
> + if (!devm_request_region(&dev->dev, vga_res.start, resource_size(&vga_res), "arkfb-vga")) {
> + dev_err(info->device, "cannot reserve legacy VGA ports\n");
> + rc = -EBUSY;
> + goto err_find_mode;
> + }
> +
> par->state.vgabase = (void __iomem *) (unsigned long) vga_res.start;
Any explanation why devm_request_region() is the right choice here?
As per the line above vga_res.start is iomem, and I had expected to see
devm_request_mem_region() used.
I looked only briefly, so I may be wrong.
Sam
^ permalink raw reply
* [PATCH] fbdev: geode: lxfb: Use devm_request_mem_region
From: Swaraj Gaikwad @ 2025-12-14 1:20 UTC (permalink / raw)
To: Andres Salomon, Helge Deller,
moderated list:AMD GEODE PROCESSOR/CHIPSET SUPPORT,
open list:FRAMEBUFFER LAYER, open list:FRAMEBUFFER LAYER,
open list
Cc: skhan, david.hunter.linux, Swaraj Gaikwad
The lxfb driver currently uses pci_request_region() for memory
reservation, which requires manual error handling and cleanup using
pci_release_region().
Simplify the driver by migrating to the managed helper
devm_request_mem_region(). This ensures that resources are automatically
released on driver detach, allowing the removal of explicit cleanup code
in the probe error path and the remove function.
This addresses the TODO item "Request memory regions in all fbdev
drivers" in Documentation/gpu/todo.rst.
Signed-off-by: Swaraj Gaikwad <swarajgaikwad1925@gmail.com>
---
Compile-tested only on x86_64.
drivers/video/fbdev/geode/lxfb_core.c | 36 +++++++++------------------
1 file changed, 12 insertions(+), 24 deletions(-)
diff --git a/drivers/video/fbdev/geode/lxfb_core.c b/drivers/video/fbdev/geode/lxfb_core.c
index cad99f5b7fe8..8189d6a13c5d 100644
--- a/drivers/video/fbdev/geode/lxfb_core.c
+++ b/drivers/video/fbdev/geode/lxfb_core.c
@@ -335,25 +335,21 @@ static int lxfb_map_video_memory(struct fb_info *info, struct pci_dev *dev)
if (ret)
return ret;
- ret = pci_request_region(dev, 0, "lxfb-framebuffer");
+ if (!devm_request_mem_region(&dev->dev, pci_resource_start(dev, 0),
+ pci_resource_len(dev, 0), "lxfb-framebuffer"))
+ return -EBUSY;
- if (ret)
- return ret;
-
- ret = pci_request_region(dev, 1, "lxfb-gp");
-
- if (ret)
- return ret;
+ if (!devm_request_mem_region(&dev->dev, pci_resource_start(dev, 1),
+ pci_resource_len(dev, 1), "lxfb-gp"))
+ return -EBUSY;
- ret = pci_request_region(dev, 2, "lxfb-vg");
+ if (!devm_request_mem_region(&dev->dev, pci_resource_start(dev, 2),
+ pci_resource_len(dev, 2), "lxfb-vg"))
+ return -EBUSY;
- if (ret)
- return ret;
-
- ret = pci_request_region(dev, 3, "lxfb-vp");
-
- if (ret)
- return ret;
+ if (!devm_request_mem_region(&dev->dev, pci_resource_start(dev, 3),
+ pci_resource_len(dev, 3), "lxfb-vp"))
+ return -EBUSY;
info->fix.smem_start = pci_resource_start(dev, 0);
info->fix.smem_len = vram ? vram : lx_framebuffer_size();
@@ -546,19 +542,15 @@ static int lxfb_probe(struct pci_dev *pdev, const struct pci_device_id *id)
err:
if (info->screen_base) {
iounmap(info->screen_base);
- pci_release_region(pdev, 0);
}
if (par->gp_regs) {
iounmap(par->gp_regs);
- pci_release_region(pdev, 1);
}
if (par->dc_regs) {
iounmap(par->dc_regs);
- pci_release_region(pdev, 2);
}
if (par->vp_regs) {
iounmap(par->vp_regs);
- pci_release_region(pdev, 3);
}
fb_dealloc_cmap(&info->cmap);
@@ -575,16 +567,12 @@ static void lxfb_remove(struct pci_dev *pdev)
unregister_framebuffer(info);
iounmap(info->screen_base);
- pci_release_region(pdev, 0);
iounmap(par->gp_regs);
- pci_release_region(pdev, 1);
iounmap(par->dc_regs);
- pci_release_region(pdev, 2);
iounmap(par->vp_regs);
- pci_release_region(pdev, 3);
fb_dealloc_cmap(&info->cmap);
framebuffer_release(info);
base-commit: a859eca0e4cc96f63ff125dbe5388d961558b0e9
--
2.52.0
^ permalink raw reply related
* [PATCH] fbdev: geode: gxfb: Use devm_request_mem_region
From: Swaraj Gaikwad @ 2025-12-14 1:13 UTC (permalink / raw)
To: Andres Salomon, Helge Deller,
moderated list:AMD GEODE PROCESSOR/CHIPSET SUPPORT,
open list:FRAMEBUFFER LAYER, open list:FRAMEBUFFER LAYER,
open list
Cc: skhan, david.hunter.linux, Swaraj Gaikwad
The gxfb driver currently uses pci_request_region() for memory
reservation, which requires manual error handling and cleanup using
pci_release_region().
Simplify the driver by migrating to the managed helper
devm_request_mem_region(). This ensures that resources are automatically
released on driver detach, allowing the removal of explicit cleanup code
in the probe error path and the remove function.
This addresses the TODO item "Request memory regions in all fbdev
drivers" in Documentation/gpu/todo.rst.
Signed-off-by: Swaraj Gaikwad <swarajgaikwad1925@gmail.com>
---
Compile-tested only on x86_64.
drivers/video/fbdev/geode/gxfb_core.c | 36 +++++++++++----------------
1 file changed, 15 insertions(+), 21 deletions(-)
diff --git a/drivers/video/fbdev/geode/gxfb_core.c b/drivers/video/fbdev/geode/gxfb_core.c
index 8d69be7c9d31..05af546c8c92 100644
--- a/drivers/video/fbdev/geode/gxfb_core.c
+++ b/drivers/video/fbdev/geode/gxfb_core.c
@@ -223,31 +223,33 @@ static int gxfb_map_video_memory(struct fb_info *info, struct pci_dev *dev)
if (ret < 0)
return ret;
- ret = pci_request_region(dev, 3, "gxfb (video processor)");
- if (ret < 0)
- return ret;
+ if (!devm_request_mem_region(&dev->dev, pci_resource_start(dev, 3),
+ pci_resource_len(dev, 3), "gxfb (video processor)"))
+ return -EBUSY;
+
par->vid_regs = pci_ioremap_bar(dev, 3);
if (!par->vid_regs)
return -ENOMEM;
- ret = pci_request_region(dev, 2, "gxfb (display controller)");
- if (ret < 0)
- return ret;
+ if (!devm_request_mem_region(&dev->dev, pci_resource_start(dev, 2),
+ pci_resource_len(dev, 2), "gxfb (display controller)"))
+ return -EBUSY;
+
par->dc_regs = pci_ioremap_bar(dev, 2);
if (!par->dc_regs)
return -ENOMEM;
- ret = pci_request_region(dev, 1, "gxfb (graphics processor)");
- if (ret < 0)
- return ret;
- par->gp_regs = pci_ioremap_bar(dev, 1);
+ if (!devm_request_mem_region(&dev->dev, pci_resource_start(dev, 1),
+ pci_resource_len(dev, 1), "gxfb (graphics processor)"))
+ return -EBUSY;
+ par->gp_regs = pci_ioremap_bar(dev, 1);
if (!par->gp_regs)
return -ENOMEM;
- ret = pci_request_region(dev, 0, "gxfb (framebuffer)");
- if (ret < 0)
- return ret;
+ if (!devm_request_mem_region(&dev->dev, pci_resource_start(dev, 0),
+ pci_resource_len(dev, 0), "gxfb (framebuffer)"))
+ return -EBUSY;
info->fix.smem_start = pci_resource_start(dev, 0);
info->fix.smem_len = vram ? vram : gx_frame_buffer_size();
@@ -414,19 +416,15 @@ static int gxfb_probe(struct pci_dev *pdev, const struct pci_device_id *id)
err:
if (info->screen_base) {
iounmap(info->screen_base);
- pci_release_region(pdev, 0);
}
if (par->vid_regs) {
iounmap(par->vid_regs);
- pci_release_region(pdev, 3);
}
if (par->dc_regs) {
iounmap(par->dc_regs);
- pci_release_region(pdev, 2);
}
if (par->gp_regs) {
iounmap(par->gp_regs);
- pci_release_region(pdev, 1);
}
fb_dealloc_cmap(&info->cmap);
@@ -442,16 +440,12 @@ static void gxfb_remove(struct pci_dev *pdev)
unregister_framebuffer(info);
iounmap((void __iomem *)info->screen_base);
- pci_release_region(pdev, 0);
iounmap(par->vid_regs);
- pci_release_region(pdev, 3);
iounmap(par->dc_regs);
- pci_release_region(pdev, 2);
iounmap(par->gp_regs);
- pci_release_region(pdev, 1);
fb_dealloc_cmap(&info->cmap);
base-commit: a859eca0e4cc96f63ff125dbe5388d961558b0e9
--
2.52.0
^ permalink raw reply related
* Re: [PATCH 8/8] Add Advantech EIO Fan driver
From: kernel test robot @ 2025-12-13 17:33 UTC (permalink / raw)
To: Ramiro Oliveira, Lee Jones, Linus Walleij, Bartosz Golaszewski,
Guenter Roeck, Andi Shyti, Daniel Thompson, Jingoo Han,
Helge Deller, Wim Van Sebroeck, Rafael J. Wysocki, Daniel Lezcano,
Zhang Rui, Lukasz Luba
Cc: oe-kbuild-all, linux-kernel, linux-gpio, linux-hwmon, linux-i2c,
dri-devel, linux-fbdev, linux-watchdog, linux-pm, Wenkai Chung,
Francisco Aragon-Trivino, Hongzhi Wang, Mikhail Tsukerman,
Thomas Kastner, Ramiro Oliveira
In-Reply-To: <20251212-upstream-v1-v1-8-d50d40ec8d8a@advantech.com>
Hi Ramiro,
kernel test robot noticed the following build warnings:
[auto build test WARNING on d9771d0dbe18dd643760431870a6abf9b0866bb0]
url: https://github.com/intel-lab-lkp/linux/commits/Ramiro-Oliveira/Add-Advantech-EIO-MFD-driver/20251213-004905
base: d9771d0dbe18dd643760431870a6abf9b0866bb0
patch link: https://lore.kernel.org/r/20251212-upstream-v1-v1-8-d50d40ec8d8a%40advantech.com
patch subject: [PATCH 8/8] Add Advantech EIO Fan driver
config: nios2-allmodconfig (https://download.01.org/0day-ci/archive/20251214/202512140153.dNgpAKJt-lkp@intel.com/config)
compiler: nios2-linux-gcc (GCC) 11.5.0
reproduce (this is a W=1 build): (https://download.01.org/0day-ci/archive/20251214/202512140153.dNgpAKJt-lkp@intel.com/reproduce)
If you fix the issue in a separate patch/commit (i.e. not just a new version of
the same patch/commit), kindly add following tags
| Reported-by: kernel test robot <lkp@intel.com>
| Closes: https://lore.kernel.org/oe-kbuild-all/202512140153.dNgpAKJt-lkp@intel.com/
All warnings (new ones prefixed by >>):
drivers/thermal/eio_fan.c: In function 'eio_fan_probe':
>> drivers/thermal/eio_fan.c:391:21: warning: variable 'temps_mc' set but not used [-Wunused-but-set-variable]
391 | int temps_mc[TRIP_NUM];
| ^~~~~~~~
vim +/temps_mc +391 drivers/thermal/eio_fan.c
375
376 static int eio_fan_probe(struct platform_device *pdev)
377 {
378 struct device *dev = &pdev->dev;
379 unsigned int fan_id;
380 int ret;
381
382 if (!dev_get_drvdata(dev->parent)) {
383 dev_err(dev, "eio_core not present\n");
384 return -ENODEV;
385 }
386
387 for (fan_id = 0; fan_id < FAN_MAX; fan_id++) {
388 u8 state = 0, name = 0;
389 int trip_hi = 0, trip_lo = 0, trip_stop = 0;
390 int pwm_hi = 0, pwm_lo = 0;
> 391 int temps_mc[TRIP_NUM];
392 struct eio_fan_dev *fan;
393 struct thermal_zone_device *tzd;
394 struct thermal_cooling_device *cdev;
395
396 if (pmc_read(dev->parent, CTRL_STATE, fan_id, &state) ||
397 pmc_read(dev->parent, CTRL_TYPE, fan_id, &name) ||
398 pmc_read(dev->parent, CTRL_THERM_HIGH, fan_id, &trip_hi) ||
399 pmc_read(dev->parent, CTRL_THERM_LOW, fan_id, &trip_lo) ||
400 pmc_read(dev->parent, CTRL_THERM_STOP, fan_id, &trip_stop) ||
401 pmc_read(dev->parent, CTRL_PWM_HIGH, fan_id, &pwm_hi) ||
402 pmc_read(dev->parent, CTRL_PWM_LOW, fan_id, &pwm_lo)) {
403 dev_info(dev, "fan%u: pmc read error, skipping\n", fan_id);
404 continue;
405 }
406
407 if (!(state & 0x1)) {
408 dev_info(dev, "fan%u: firmware reports disabled\n", fan_id);
409 continue;
410 }
411
412 if (!fan_name[name][0]) {
413 dev_info(dev, "fan%u: unknown name index %u\n", fan_id, name);
414 continue;
415 }
416
417 temps_mc[TRIP_HIGH] = DECI_KELVIN_TO_MILLI_CELSIUS(trip_hi);
418 temps_mc[TRIP_LOW] = DECI_KELVIN_TO_MILLI_CELSIUS(trip_lo);
419 temps_mc[TRIP_STOP] = DECI_KELVIN_TO_MILLI_CELSIUS(trip_stop);
420
421 fan = devm_kzalloc(dev, sizeof(*fan), GFP_KERNEL);
422 if (!fan)
423 return -ENOMEM;
424
425 fan->mfd = dev->parent;
426 fan->id = (u8)fan_id;
427
428 fan->trip_priv[TRIP_HIGH].trip_ctl = CTRL_THERM_HIGH;
429 fan->trip_priv[TRIP_LOW].trip_ctl = CTRL_THERM_LOW;
430 fan->trip_priv[TRIP_STOP].trip_ctl = CTRL_THERM_STOP;
431
432 struct thermal_trip trips[TRIP_NUM] = {
433 [TRIP_HIGH] = {
434 .type = THERMAL_TRIP_ACTIVE,
435 .temperature = DECI_KELVIN_TO_MILLI_CELSIUS(trip_hi),
436 .flags = THERMAL_TRIP_FLAG_RW_TEMP,
437 .priv = &fan->trip_priv[TRIP_HIGH],
438 },
439 [TRIP_LOW] = {
440 .type = THERMAL_TRIP_ACTIVE,
441 .temperature = DECI_KELVIN_TO_MILLI_CELSIUS(trip_lo),
442 .flags = THERMAL_TRIP_FLAG_RW_TEMP,
443 .priv = &fan->trip_priv[TRIP_LOW],
444 },
445 [TRIP_STOP] = {
446 .type = THERMAL_TRIP_ACTIVE,
447 .temperature = DECI_KELVIN_TO_MILLI_CELSIUS(trip_stop),
448 .flags = THERMAL_TRIP_FLAG_RW_TEMP,
449 .priv = &fan->trip_priv[TRIP_STOP],
450 },
451 };
452
453 tzd = thermal_zone_device_register_with_trips(fan_name[name],
454 trips, TRIP_NUM,
455 fan,
456 &zone_ops,
457 NULL,
458 0, 0);
459 if (IS_ERR(tzd))
460 return PTR_ERR(tzd);
461
462 cdev = thermal_cooling_device_register(fan_name[name], fan, &cooling_ops);
463 if (IS_ERR(cdev)) {
464 thermal_zone_device_unregister(tzd);
465 dev_err(dev, "fan%u: cdev register failed: %ld\n",
466 fan_id, PTR_ERR(cdev));
467 return PTR_ERR(cdev);
468 }
469
470 dev_set_drvdata(thermal_zone_device(tzd), tzd);
471 ret = device_create_file(thermal_zone_device(tzd), &dev_attr_fan_mode);
472 if (ret)
473 dev_warn(dev, "Error create thermal zone fan_mode sysfs\n");
474 }
475 return 0;
476 }
477
--
0-DAY CI Kernel Test Service
https://github.com/intel/lkp-tests/wiki
^ permalink raw reply
* Re: [PATCH 1/8] Add Advantech EIO MFD driver
From: kernel test robot @ 2025-12-13 15:19 UTC (permalink / raw)
To: Ramiro Oliveira, Lee Jones, Linus Walleij, Bartosz Golaszewski,
Guenter Roeck, Andi Shyti, Daniel Thompson, Jingoo Han,
Helge Deller, Wim Van Sebroeck, Rafael J. Wysocki, Daniel Lezcano,
Zhang Rui, Lukasz Luba
Cc: oe-kbuild-all, linux-kernel, linux-gpio, linux-hwmon, linux-i2c,
dri-devel, linux-fbdev, linux-watchdog, linux-pm, Wenkai Chung,
Francisco Aragon-Trivino, Hongzhi Wang, Mikhail Tsukerman,
Thomas Kastner, Ramiro Oliveira
In-Reply-To: <20251212-upstream-v1-v1-1-d50d40ec8d8a@advantech.com>
Hi Ramiro,
kernel test robot noticed the following build warnings:
[auto build test WARNING on d9771d0dbe18dd643760431870a6abf9b0866bb0]
url: https://github.com/intel-lab-lkp/linux/commits/Ramiro-Oliveira/Add-Advantech-EIO-MFD-driver/20251213-004905
base: d9771d0dbe18dd643760431870a6abf9b0866bb0
patch link: https://lore.kernel.org/r/20251212-upstream-v1-v1-1-d50d40ec8d8a%40advantech.com
patch subject: [PATCH 1/8] Add Advantech EIO MFD driver
config: nios2-allmodconfig (https://download.01.org/0day-ci/archive/20251213/202512132239.HrAPSw6z-lkp@intel.com/config)
compiler: nios2-linux-gcc (GCC) 11.5.0
reproduce (this is a W=1 build): (https://download.01.org/0day-ci/archive/20251213/202512132239.HrAPSw6z-lkp@intel.com/reproduce)
If you fix the issue in a separate patch/commit (i.e. not just a new version of
the same patch/commit), kindly add following tags
| Reported-by: kernel test robot <lkp@intel.com>
| Closes: https://lore.kernel.org/oe-kbuild-all/202512132239.HrAPSw6z-lkp@intel.com/
All warnings (new ones prefixed by >>):
>> Warning: drivers/mfd/eio_core.c:37 cannot understand function prototype: 'uint timeout = DEFAULT_TIMEOUT;'
--
0-DAY CI Kernel Test Service
https://github.com/intel/lkp-tests/wiki
^ permalink raw reply
* [PATCH v2] fbdev: arkfb: Request legacy VGA I/O region
From: Swaraj Gaikwad @ 2025-12-13 20:22 UTC (permalink / raw)
To: Helge Deller, Andrew Morton, Hans Verkuil, Nicolas Dufresne,
Frank Li, Zi Yan, Donet Tom, Yann Dirson, Konrad Dybcio,
Vivek Kasireddy, Qianfeng Rong, Kees Cook,
open list:FRAMEBUFFER LAYER, open list:FRAMEBUFFER LAYER,
open list
Cc: skhan, david.hunter.linux, Swaraj Gaikwad
The arkfb driver uses the legacy VGA I/O range (0x3c0+) but does not
request it. This can cause conflicts with other drivers that try to
reserve these ports.
Fix this by using devm_request_region() during the probe function.
This ensures the region is properly reserved and automatically released
on driver detach.
v1: https://lore.kernel.org/lkml/20251213154937.104301-1-swarajgaikwad1925@gmail.com/
Signed-off-by: Swaraj Gaikwad <swarajgaikwad1925@gmail.com>
---
v2:
- Use resource_size(&vga_res) instead of hardcoded 64 * 1024.
- (Feedback from Kees Cook)
Compile-tested only on x86_64.
drivers/video/fbdev/arkfb.c | 6 ++++++
1 file changed, 6 insertions(+)
diff --git a/drivers/video/fbdev/arkfb.c b/drivers/video/fbdev/arkfb.c
index ec084323115f..24e4c20d1a32 100644
--- a/drivers/video/fbdev/arkfb.c
+++ b/drivers/video/fbdev/arkfb.c
@@ -1018,6 +1018,12 @@ static int ark_pci_probe(struct pci_dev *dev, const struct pci_device_id *id)
pcibios_bus_to_resource(dev->bus, &vga_res, &bus_reg);
+ if (!devm_request_region(&dev->dev, vga_res.start, resource_size(&vga_res), "arkfb-vga")) {
+ dev_err(info->device, "cannot reserve legacy VGA ports\n");
+ rc = -EBUSY;
+ goto err_find_mode;
+ }
+
par->state.vgabase = (void __iomem *) (unsigned long) vga_res.start;
/* FIXME get memsize */
base-commit: a859eca0e4cc96f63ff125dbe5388d961558b0e9
--
2.52.0
^ permalink raw reply related
* Re: [PATCH] fbdev: arkfb: Request legacy VGA I/O region
From: Kees Cook @ 2025-12-13 14:22 UTC (permalink / raw)
To: Swaraj Gaikwad
Cc: Helge Deller, Andrew Morton, Hans Verkuil, Zi Yan, Frank Li,
Bjorn Andersson, Laurent Pinchart, Qianfeng Rong, Vivek Kasireddy,
Konrad Dybcio, Bartosz Golaszewski, open list:FRAMEBUFFER LAYER,
open list:FRAMEBUFFER LAYER, open list, skhan, david.hunter.linux
In-Reply-To: <20251213154937.104301-1-swarajgaikwad1925@gmail.com>
On Sat, Dec 13, 2025 at 03:49:32PM +0000, Swaraj Gaikwad wrote:
> The arkfb driver uses the legacy VGA I/O range (0x3c0+) but does not
> request it. This can cause conflicts with other drivers that try to
> reserve these ports.
Eek, nice catch!
>
> Fix this by using devm_request_region() during the probe function.
> This ensures the region is properly reserved and automatically released
> on driver detach.
>
> Signed-off-by: Swaraj Gaikwad <swarajgaikwad1925@gmail.com>
> ---
> Compile-tested only on x86_64.
>
> drivers/video/fbdev/arkfb.c | 6 ++++++
> 1 file changed, 6 insertions(+)
>
> diff --git a/drivers/video/fbdev/arkfb.c b/drivers/video/fbdev/arkfb.c
> index ec084323115f..24e4c20d1a32 100644
> --- a/drivers/video/fbdev/arkfb.c
> +++ b/drivers/video/fbdev/arkfb.c
> @@ -1018,6 +1018,12 @@ static int ark_pci_probe(struct pci_dev *dev, const struct pci_device_id *id)
>
> pcibios_bus_to_resource(dev->bus, &vga_res, &bus_reg);
>
> + if (!devm_request_region(&dev->dev, vga_res.start, 64 * 1024, "arkfb-vga")) {
I was expecting to see vga_res.end as the third argument instead of
repeating the open-coded value.
-Kees
> + dev_err(info->device, "cannot reserve legacy VGA ports\n");
> + rc = -EBUSY;
> + goto err_find_mode;
> + }
> +
> par->state.vgabase = (void __iomem *) (unsigned long) vga_res.start;
>
> /* FIXME get memsize */
>
> base-commit: a859eca0e4cc96f63ff125dbe5388d961558b0e9
> --
> 2.52.0
>
--
Kees Cook
^ permalink raw reply
* [PATCH] fbdev: arkfb: Request legacy VGA I/O region
From: Swaraj Gaikwad @ 2025-12-13 15:49 UTC (permalink / raw)
To: Helge Deller, Andrew Morton, Hans Verkuil, Zi Yan, Frank Li,
Bjorn Andersson, Laurent Pinchart, Qianfeng Rong, Vivek Kasireddy,
Konrad Dybcio, Bartosz Golaszewski, Kees Cook,
open list:FRAMEBUFFER LAYER, open list:FRAMEBUFFER LAYER,
open list
Cc: skhan, david.hunter.linux, Swaraj Gaikwad
The arkfb driver uses the legacy VGA I/O range (0x3c0+) but does not
request it. This can cause conflicts with other drivers that try to
reserve these ports.
Fix this by using devm_request_region() during the probe function.
This ensures the region is properly reserved and automatically released
on driver detach.
Signed-off-by: Swaraj Gaikwad <swarajgaikwad1925@gmail.com>
---
Compile-tested only on x86_64.
drivers/video/fbdev/arkfb.c | 6 ++++++
1 file changed, 6 insertions(+)
diff --git a/drivers/video/fbdev/arkfb.c b/drivers/video/fbdev/arkfb.c
index ec084323115f..24e4c20d1a32 100644
--- a/drivers/video/fbdev/arkfb.c
+++ b/drivers/video/fbdev/arkfb.c
@@ -1018,6 +1018,12 @@ static int ark_pci_probe(struct pci_dev *dev, const struct pci_device_id *id)
pcibios_bus_to_resource(dev->bus, &vga_res, &bus_reg);
+ if (!devm_request_region(&dev->dev, vga_res.start, 64 * 1024, "arkfb-vga")) {
+ dev_err(info->device, "cannot reserve legacy VGA ports\n");
+ rc = -EBUSY;
+ goto err_find_mode;
+ }
+
par->state.vgabase = (void __iomem *) (unsigned long) vga_res.start;
/* FIXME get memsize */
base-commit: a859eca0e4cc96f63ff125dbe5388d961558b0e9
--
2.52.0
^ permalink raw reply related
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox