+++ /dev/null
-From bc80d7e1d1e199f1f758528182c999d4b879b915 Mon Sep 17 00:00:00 2001
-From: Sasha Levin <sashal@kernel.org>
-Date: Tue, 5 Apr 2022 23:03:27 +0200
-Subject: fbcon: Extract fbcon_open/release helpers
-
-From: Daniel Vetter <daniel.vetter@ffwll.ch>
-
-[ Upstream commit bd6026a8c4e6b7edf4bafcb71da885b284b8f4fd ]
-
-There's two minor behaviour changes in here:
-- in error paths we now consistently call fb_ops->fb_release
-- fb_release really can't fail (fbmem.c ignores it too) and there's no
- reasonable cleanup we can do anyway.
-
-Note that everything in fbcon.c is protected by the big console_lock()
-lock (especially all the global variables), so the minor changes in
-ordering of setup/cleanup do not matter.
-
-v2: Explain a bit better why this is all correct (Sam)
-
-Acked-by: Sam Ravnborg <sam@ravnborg.org>
-Signed-off-by: Daniel Vetter <daniel.vetter@intel.com>
-Cc: Daniel Vetter <daniel@ffwll.ch>
-Cc: Claudio Suarez <cssk@net-c.es>
-Cc: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
-Cc: Tetsuo Handa <penguin-kernel@I-love.SAKURA.ne.jp>
-Cc: Du Cheng <ducheng2@gmail.com>
-Link: https://patchwork.freedesktop.org/patch/msgid/20220405210335.3434130-10-daniel.vetter@ffwll.ch
-Stable-dep-of: 17186f1f90d3 ("fbdev: Fix do_register_framebuffer to prevent null-ptr-deref in fb_videomode_to_var")
-Signed-off-by: Sasha Levin <sashal@kernel.org>
----
- drivers/video/fbdev/core/fbcon.c | 107 +++++++++++++++----------------
- 1 file changed, 53 insertions(+), 54 deletions(-)
-
-diff --git a/drivers/video/fbdev/core/fbcon.c b/drivers/video/fbdev/core/fbcon.c
-index abea89d101626..2a230a6335a81 100644
---- a/drivers/video/fbdev/core/fbcon.c
-+++ b/drivers/video/fbdev/core/fbcon.c
-@@ -691,19 +691,37 @@ static int fbcon_invalid_charcount(struct fb_info *info, unsigned charcount)
-
- #endif /* CONFIG_MISC_TILEBLITTING */
-
-+static int fbcon_open(struct fb_info *info)
-+{
-+ if (!try_module_get(info->fbops->owner))
-+ return -ENODEV;
-+
-+ if (info->fbops->fb_open &&
-+ info->fbops->fb_open(info, 0)) {
-+ module_put(info->fbops->owner);
-+ return -ENODEV;
-+ }
-+
-+ return 0;
-+}
-+
-+static void fbcon_release(struct fb_info *info)
-+{
-+ if (info->fbops->fb_release)
-+ info->fbops->fb_release(info, 0);
-+
-+ module_put(info->fbops->owner);
-+}
-
- static int con2fb_acquire_newinfo(struct vc_data *vc, struct fb_info *info,
- int unit, int oldidx)
- {
- struct fbcon_ops *ops = NULL;
-- int err = 0;
--
-- if (!try_module_get(info->fbops->owner))
-- err = -ENODEV;
-+ int err;
-
-- if (!err && info->fbops->fb_open &&
-- info->fbops->fb_open(info, 0))
-- err = -ENODEV;
-+ err = fbcon_open(info);
-+ if (err)
-+ return err;
-
- if (!err) {
- ops = kzalloc(sizeof(struct fbcon_ops), GFP_KERNEL);
-@@ -724,7 +742,7 @@ static int con2fb_acquire_newinfo(struct vc_data *vc, struct fb_info *info,
-
- if (err) {
- con2fb_map[unit] = oldidx;
-- module_put(info->fbops->owner);
-+ fbcon_release(info);
- }
-
- return err;
-@@ -735,45 +753,34 @@ static int con2fb_release_oldinfo(struct vc_data *vc, struct fb_info *oldinfo,
- int oldidx, int found)
- {
- struct fbcon_ops *ops = oldinfo->fbcon_par;
-- int err = 0, ret;
-+ int ret;
-
-- if (oldinfo->fbops->fb_release &&
-- oldinfo->fbops->fb_release(oldinfo, 0)) {
-- con2fb_map[unit] = oldidx;
-- if (!found && newinfo->fbops->fb_release)
-- newinfo->fbops->fb_release(newinfo, 0);
-- if (!found)
-- module_put(newinfo->fbops->owner);
-- err = -ENODEV;
-- }
-+ fbcon_release(oldinfo);
-
-- if (!err) {
-- fbcon_del_cursor_work(oldinfo);
-- kfree(ops->cursor_state.mask);
-- kfree(ops->cursor_data);
-- kfree(ops->cursor_src);
-- kfree(ops->fontbuffer);
-- kfree(oldinfo->fbcon_par);
-- oldinfo->fbcon_par = NULL;
-- module_put(oldinfo->fbops->owner);
-- /*
-- If oldinfo and newinfo are driving the same hardware,
-- the fb_release() method of oldinfo may attempt to
-- restore the hardware state. This will leave the
-- newinfo in an undefined state. Thus, a call to
-- fb_set_par() may be needed for the newinfo.
-- */
-- if (newinfo && newinfo->fbops->fb_set_par) {
-- ret = newinfo->fbops->fb_set_par(newinfo);
-+ fbcon_del_cursor_work(oldinfo);
-+ kfree(ops->cursor_state.mask);
-+ kfree(ops->cursor_data);
-+ kfree(ops->cursor_src);
-+ kfree(ops->fontbuffer);
-+ kfree(oldinfo->fbcon_par);
-+ oldinfo->fbcon_par = NULL;
-+ /*
-+ If oldinfo and newinfo are driving the same hardware,
-+ the fb_release() method of oldinfo may attempt to
-+ restore the hardware state. This will leave the
-+ newinfo in an undefined state. Thus, a call to
-+ fb_set_par() may be needed for the newinfo.
-+ */
-+ if (newinfo && newinfo->fbops->fb_set_par) {
-+ ret = newinfo->fbops->fb_set_par(newinfo);
-
-- if (ret)
-- printk(KERN_ERR "con2fb_release_oldinfo: "
-- "detected unhandled fb_set_par error, "
-- "error code %d\n", ret);
-- }
-+ if (ret)
-+ printk(KERN_ERR "con2fb_release_oldinfo: "
-+ "detected unhandled fb_set_par error, "
-+ "error code %d\n", ret);
- }
-
-- return err;
-+ return 0;
- }
-
- static void con2fb_init_display(struct vc_data *vc, struct fb_info *info,
-@@ -928,7 +935,6 @@ static const char *fbcon_startup(void)
- struct fbcon_display *p = &fb_display[fg_console];
- struct vc_data *vc = vc_cons[fg_console].d;
- const struct font_desc *font = NULL;
-- struct module *owner;
- struct fb_info *info = NULL;
- struct fbcon_ops *ops;
- int rows, cols;
-@@ -947,17 +953,12 @@ static const char *fbcon_startup(void)
- if (!info)
- return NULL;
-
-- owner = info->fbops->owner;
-- if (!try_module_get(owner))
-+ if (fbcon_open(info))
- return NULL;
-- if (info->fbops->fb_open && info->fbops->fb_open(info, 0)) {
-- module_put(owner);
-- return NULL;
-- }
-
- ops = kzalloc(sizeof(struct fbcon_ops), GFP_KERNEL);
- if (!ops) {
-- module_put(owner);
-+ fbcon_release(info);
- return NULL;
- }
-
-@@ -3387,10 +3388,6 @@ static void fbcon_exit(void)
- }
-
- if (mapped) {
-- if (info->fbops->fb_release)
-- info->fbops->fb_release(info, 0);
-- module_put(info->fbops->owner);
--
- if (info->fbcon_par) {
- struct fbcon_ops *ops = info->fbcon_par;
-
-@@ -3400,6 +3397,8 @@ static void fbcon_exit(void)
- kfree(info->fbcon_par);
- info->fbcon_par = NULL;
- }
-+
-+ fbcon_release(info);
- }
- }
- }
---
-2.39.5
-
+++ /dev/null
-From 1f6a3677cb84e9a94f803e4e847b3ecad77a3ed2 Mon Sep 17 00:00:00 2001
-From: Sasha Levin <sashal@kernel.org>
-Date: Tue, 5 Apr 2022 23:03:32 +0200
-Subject: fbcon: Move console_lock for register/unlink/unregister
-
-From: Daniel Vetter <daniel.vetter@ffwll.ch>
-
-[ Upstream commit 6e7da3af008b72520f5318507f455f344b27f022 ]
-
-Ideally console_lock becomes an implementation detail of fbcon.c and
-doesn't show up anywhere in fbmem.c. We're still pretty far from that,
-but at least the register/unregister code is there now.
-
-With this the do_fb_ioctl() handler is the only code in fbmem.c still
-calling console_lock().
-
-Acked-by: Sam Ravnborg <sam@ravnborg.org>
-Signed-off-by: Daniel Vetter <daniel.vetter@intel.com>
-Cc: Daniel Vetter <daniel@ffwll.ch>
-Cc: Thomas Zimmermann <tzimmermann@suse.de>
-Cc: Du Cheng <ducheng2@gmail.com>
-Cc: Claudio Suarez <cssk@net-c.es>
-Cc: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
-Cc: Tetsuo Handa <penguin-kernel@I-love.SAKURA.ne.jp>
-Cc: Matthew Wilcox <willy@infradead.org>
-Cc: Sam Ravnborg <sam@ravnborg.org>
-Cc: Zheyu Ma <zheyuma97@gmail.com>
-Cc: Guenter Roeck <linux@roeck-us.net>
-Cc: Alex Deucher <alexander.deucher@amd.com>
-Cc: Zhen Lei <thunder.leizhen@huawei.com>
-Cc: Xiyu Yang <xiyuyang19@fudan.edu.cn>
-Link: https://patchwork.freedesktop.org/patch/msgid/20220405210335.3434130-15-daniel.vetter@ffwll.ch
-Stable-dep-of: 17186f1f90d3 ("fbdev: Fix do_register_framebuffer to prevent null-ptr-deref in fb_videomode_to_var")
-Signed-off-by: Sasha Levin <sashal@kernel.org>
----
- drivers/video/fbdev/core/fbcon.c | 33 ++++++++++++++++++++++++++------
- drivers/video/fbdev/core/fbmem.c | 23 ++--------------------
- 2 files changed, 29 insertions(+), 27 deletions(-)
-
-diff --git a/drivers/video/fbdev/core/fbcon.c b/drivers/video/fbdev/core/fbcon.c
-index 072a264ae380b..a67f982fe2ec0 100644
---- a/drivers/video/fbdev/core/fbcon.c
-+++ b/drivers/video/fbdev/core/fbcon.c
-@@ -2823,10 +2823,12 @@ void fbcon_fb_unbind(struct fb_info *info)
- int i, new_idx = -1, ret = 0;
- int idx = info->node;
-
-- WARN_CONSOLE_UNLOCKED();
-+ console_lock();
-
-- if (!fbcon_has_console_bind)
-+ if (!fbcon_has_console_bind) {
-+ console_unlock();
- return;
-+ }
-
- for (i = first_fb_vc; i <= last_fb_vc; i++) {
- if (con2fb_map[i] != idx &&
-@@ -2866,6 +2868,8 @@ void fbcon_fb_unbind(struct fb_info *info)
- }
- fbcon_unbind();
- }
-+
-+ console_unlock();
- }
-
- /* called with console_lock held */
-@@ -2873,10 +2877,12 @@ void fbcon_fb_unregistered(struct fb_info *info)
- {
- int i, idx;
-
-- WARN_CONSOLE_UNLOCKED();
-+ console_lock();
-
-- if (deferred_takeover)
-+ if (deferred_takeover) {
-+ console_unlock();
- return;
-+ }
-
- idx = info->node;
- for (i = first_fb_vc; i <= last_fb_vc; i++) {
-@@ -2905,6 +2911,7 @@ void fbcon_fb_unregistered(struct fb_info *info)
-
- if (!num_registered_fb)
- do_unregister_con_driver(&fb_con);
-+ console_unlock();
- }
-
- void fbcon_remap_all(struct fb_info *info)
-@@ -2962,19 +2969,27 @@ static inline void fbcon_select_primary(struct fb_info *info)
- }
- #endif /* CONFIG_FRAMEBUFFER_DETECT_PRIMARY */
-
-+static bool lockless_register_fb;
-+module_param_named_unsafe(lockless_register_fb, lockless_register_fb, bool, 0400);
-+MODULE_PARM_DESC(lockless_register_fb,
-+ "Lockless framebuffer registration for debugging [default=off]");
-+
- /* called with console_lock held */
- int fbcon_fb_registered(struct fb_info *info)
- {
- int ret = 0, i, idx;
-
-- WARN_CONSOLE_UNLOCKED();
-+ if (!lockless_register_fb)
-+ console_lock();
-+ else
-+ atomic_inc(&ignore_console_lock_warning);
-
- idx = info->node;
- fbcon_select_primary(info);
-
- if (deferred_takeover) {
- pr_info("fbcon: Deferring console take-over\n");
-- return 0;
-+ goto out;
- }
-
- if (info_idx == -1) {
-@@ -2994,6 +3009,12 @@ int fbcon_fb_registered(struct fb_info *info)
- }
- }
-
-+out:
-+ if (!lockless_register_fb)
-+ console_unlock();
-+ else
-+ atomic_dec(&ignore_console_lock_warning);
-+
- return ret;
- }
-
-diff --git a/drivers/video/fbdev/core/fbmem.c b/drivers/video/fbdev/core/fbmem.c
-index f4253ec8a6409..5e8ee360f6ba2 100644
---- a/drivers/video/fbdev/core/fbmem.c
-+++ b/drivers/video/fbdev/core/fbmem.c
-@@ -1620,14 +1620,9 @@ static void do_remove_conflicting_framebuffers(struct apertures_struct *a,
- }
- }
-
--static bool lockless_register_fb;
--module_param_named_unsafe(lockless_register_fb, lockless_register_fb, bool, 0400);
--MODULE_PARM_DESC(lockless_register_fb,
-- "Lockless framebuffer registration for debugging [default=off]");
--
- static int do_register_framebuffer(struct fb_info *fb_info)
- {
-- int i, ret;
-+ int i;
- struct fb_videomode mode;
-
- if (fb_check_foreignness(fb_info))
-@@ -1696,17 +1691,7 @@ static int do_register_framebuffer(struct fb_info *fb_info)
- }
- #endif
-
-- if (!lockless_register_fb)
-- console_lock();
-- else
-- atomic_inc(&ignore_console_lock_warning);
-- ret = fbcon_fb_registered(fb_info);
--
-- if (!lockless_register_fb)
-- console_unlock();
-- else
-- atomic_dec(&ignore_console_lock_warning);
-- return ret;
-+ return fbcon_fb_registered(fb_info);
- }
-
- static void unbind_console(struct fb_info *fb_info)
-@@ -1716,9 +1701,7 @@ static void unbind_console(struct fb_info *fb_info)
- if (WARN_ON(i < 0 || i >= FB_MAX || registered_fb[i] != fb_info))
- return;
-
-- console_lock();
- fbcon_fb_unbind(fb_info);
-- console_unlock();
- }
-
- static void unlink_framebuffer(struct fb_info *fb_info)
-@@ -1758,9 +1741,7 @@ static void do_unregister_framebuffer(struct fb_info *fb_info)
- fb_notifier_call_chain(FB_EVENT_FB_UNREGISTERED, &event);
- }
- #endif
-- console_lock();
- fbcon_fb_unregistered(fb_info);
-- console_unlock();
-
- /* this may free fb info */
- put_fb_info(fb_info);
---
-2.39.5
-
+++ /dev/null
-From bbeee6fbede2e3a3967af4884b2c2c8b31c26507 Mon Sep 17 00:00:00 2001
-From: Sasha Levin <sashal@kernel.org>
-Date: Tue, 5 Apr 2022 23:03:29 +0200
-Subject: fbcon: move more common code into fb_open()
-
-From: Daniel Vetter <daniel.vetter@ffwll.ch>
-
-[ Upstream commit d443d93864726ad68c0a741d1e7b03934a9af143 ]
-
-No idea why con2fb_acquire_newinfo() initializes much less than
-fbcon_startup(), but so be it. From a quick look most of the
-un-initialized stuff should be fairly harmless, but who knows.
-
-Note that the error handling for the con2fb_acquire_newinfo() failure
-case was very strange: Callers updated con2fb_map to the new value
-before calling this function, but upon error con2fb_acquire_newinfo
-reset it to the old value. Since I removed the call to fbcon_release
-anyway that strange error path was sticking out like a sore thumb,
-hence I removed it. Which also allows us to remove the oldidx
-parameter from that function.
-
-v2: Explain what's going on with oldidx and error paths (Sam)
-
-v3: Drop unused variable (0day)
-
-v4: Rebased over bisect fix in previous patch, unchagend end result.
-
-Acked-by: Sam Ravnborg <sam@ravnborg.org> (v2)
-Acked-by: Thomas Zimmermann <tzimmermann@suse.de>
-Cc: kernel test robot <lkp@intel.com>
-Signed-off-by: Daniel Vetter <daniel.vetter@intel.com>
-Cc: Daniel Vetter <daniel@ffwll.ch>
-Cc: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
-Cc: Tetsuo Handa <penguin-kernel@I-love.SAKURA.ne.jp>
-Cc: Thomas Zimmermann <tzimmermann@suse.de>
-Cc: Claudio Suarez <cssk@net-c.es>
-Cc: Du Cheng <ducheng2@gmail.com>
-Link: https://patchwork.freedesktop.org/patch/msgid/20220405210335.3434130-12-daniel.vetter@ffwll.ch
-Stable-dep-of: 17186f1f90d3 ("fbdev: Fix do_register_framebuffer to prevent null-ptr-deref in fb_videomode_to_var")
-Signed-off-by: Sasha Levin <sashal@kernel.org>
----
- drivers/video/fbdev/core/fbcon.c | 75 +++++++++++++-------------------
- 1 file changed, 30 insertions(+), 45 deletions(-)
-
-diff --git a/drivers/video/fbdev/core/fbcon.c b/drivers/video/fbdev/core/fbcon.c
-index 2a230a6335a81..734b8f3f81b24 100644
---- a/drivers/video/fbdev/core/fbcon.c
-+++ b/drivers/video/fbdev/core/fbcon.c
-@@ -691,8 +691,18 @@ static int fbcon_invalid_charcount(struct fb_info *info, unsigned charcount)
-
- #endif /* CONFIG_MISC_TILEBLITTING */
-
-+static void fbcon_release(struct fb_info *info)
-+{
-+ if (info->fbops->fb_release)
-+ info->fbops->fb_release(info, 0);
-+
-+ module_put(info->fbops->owner);
-+}
-+
- static int fbcon_open(struct fb_info *info)
- {
-+ struct fbcon_ops *ops;
-+
- if (!try_module_get(info->fbops->owner))
- return -ENODEV;
-
-@@ -702,48 +712,31 @@ static int fbcon_open(struct fb_info *info)
- return -ENODEV;
- }
-
-- return 0;
--}
-+ ops = kzalloc(sizeof(struct fbcon_ops), GFP_KERNEL);
-+ if (!ops) {
-+ fbcon_release(info);
-+ return -ENOMEM;
-+ }
-
--static void fbcon_release(struct fb_info *info)
--{
-- if (info->fbops->fb_release)
-- info->fbops->fb_release(info, 0);
-+ INIT_DELAYED_WORK(&ops->cursor_work, fb_flashcursor);
-+ ops->info = info;
-+ info->fbcon_par = ops;
-+ ops->cur_blink_jiffies = HZ / 5;
-
-- module_put(info->fbops->owner);
-+ return 0;
- }
-
- static int con2fb_acquire_newinfo(struct vc_data *vc, struct fb_info *info,
-- int unit, int oldidx)
-+ int unit)
- {
-- struct fbcon_ops *ops = NULL;
- int err;
-
- err = fbcon_open(info);
- if (err)
- return err;
-
-- if (!err) {
-- ops = kzalloc(sizeof(struct fbcon_ops), GFP_KERNEL);
-- if (!ops)
-- err = -ENOMEM;
-- }
--
-- if (!err) {
-- INIT_DELAYED_WORK(&ops->cursor_work, fb_flashcursor);
--
-- ops->cur_blink_jiffies = HZ / 5;
-- ops->info = info;
-- info->fbcon_par = ops;
--
-- if (vc)
-- set_blitting_type(vc, info);
-- }
--
-- if (err) {
-- con2fb_map[unit] = oldidx;
-- fbcon_release(info);
-- }
-+ if (vc)
-+ set_blitting_type(vc, info);
-
- return err;
- }
-@@ -854,9 +847,11 @@ static int set_con2fb_map(int unit, int newidx, int user)
-
- found = search_fb_in_map(newidx);
-
-- con2fb_map[unit] = newidx;
-- if (!err && !found)
-- err = con2fb_acquire_newinfo(vc, info, unit, oldidx);
-+ if (!err && !found) {
-+ err = con2fb_acquire_newinfo(vc, info, unit);
-+ if (!err)
-+ con2fb_map[unit] = newidx;
-+ }
-
- /*
- * If old fb is not mapped to any of the consoles,
-@@ -956,20 +951,10 @@ static const char *fbcon_startup(void)
- if (fbcon_open(info))
- return NULL;
-
-- ops = kzalloc(sizeof(struct fbcon_ops), GFP_KERNEL);
-- if (!ops) {
-- fbcon_release(info);
-- return NULL;
-- }
--
-- INIT_DELAYED_WORK(&ops->cursor_work, fb_flashcursor);
--
-+ ops = info->fbcon_par;
- ops->currcon = -1;
- ops->graphics = 1;
- ops->cur_rotate = -1;
-- ops->cur_blink_jiffies = HZ / 5;
-- ops->info = info;
-- info->fbcon_par = ops;
-
- p->con_rotate = initial_rotation;
- if (p->con_rotate == -1)
-@@ -1037,7 +1022,7 @@ static void fbcon_init(struct vc_data *vc, int init)
- return;
-
- if (!info->fbcon_par)
-- con2fb_acquire_newinfo(vc, info, vc->vc_num, -1);
-+ con2fb_acquire_newinfo(vc, info, vc->vc_num);
-
- /* If we are not the first console on this
- fb, copy the font from that console */
---
-2.39.5
-
+++ /dev/null
-From 5d4b0d384bdfa97b0e09d8f5bc550bcc29d5ca07 Mon Sep 17 00:00:00 2001
-From: Sasha Levin <sashal@kernel.org>
-Date: Tue, 5 Apr 2022 23:03:24 +0200
-Subject: fbcon: Use delayed work for cursor
-
-From: Daniel Vetter <daniel.vetter@ffwll.ch>
-
-[ Upstream commit 3b0fb6ab25dda03f6077bf8fce9407bb0d4db6ea ]
-
-Allows us to delete a bunch of hand-rolled stuff using a timer plus a
-separate work). Also to simplify the code we initialize the
-cursor_work completely when we allocate the fbcon_ops structure,
-instead of trying to cope with console re-initialization.
-
-The motiviation here is that fbcon code stops using the fb_info.queue,
-which helps with locking issues around cleanup and all that in a later
-patch.
-
-Also note that this allows us to ditch the hand-rolled work cleanup in
-fbcon_exit - we already call fbcon_del_cursor_timer, which takes care
-of everything. Plus this was racy anyway.
-
-v2:
-- Only INIT_DELAYED_WORK when kzalloc succeeded (Tetsuo)
-- Explain that we replace both the timer and a work with the combined
- delayed_work (Javier)
-
-Reviewed-by: Javier Martinez Canillas <javierm@redhat.com>
-Acked-by: Thomas Zimmermann <tzimmermann@suse.de>
-Signed-off-by: Daniel Vetter <daniel.vetter@intel.com>
-Cc: Daniel Vetter <daniel@ffwll.ch>
-Cc: Claudio Suarez <cssk@net-c.es>
-Cc: Du Cheng <ducheng2@gmail.com>
-Cc: Thomas Zimmermann <tzimmermann@suse.de>
-Cc: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
-Cc: Tetsuo Handa <penguin-kernel@I-love.SAKURA.ne.jp>
-Link: https://patchwork.freedesktop.org/patch/msgid/20220405210335.3434130-7-daniel.vetter@ffwll.ch
-Stable-dep-of: 17186f1f90d3 ("fbdev: Fix do_register_framebuffer to prevent null-ptr-deref in fb_videomode_to_var")
-Signed-off-by: Sasha Levin <sashal@kernel.org>
----
- drivers/video/fbdev/core/fbcon.c | 85 +++++++++++++-------------------
- drivers/video/fbdev/core/fbcon.h | 4 +-
- 2 files changed, 35 insertions(+), 54 deletions(-)
-
-diff --git a/drivers/video/fbdev/core/fbcon.c b/drivers/video/fbdev/core/fbcon.c
-index 805a4745abd86..abea89d101626 100644
---- a/drivers/video/fbdev/core/fbcon.c
-+++ b/drivers/video/fbdev/core/fbcon.c
-@@ -357,8 +357,8 @@ static int get_color(struct vc_data *vc, struct fb_info *info,
-
- static void fb_flashcursor(struct work_struct *work)
- {
-- struct fb_info *info = container_of(work, struct fb_info, queue);
-- struct fbcon_ops *ops = info->fbcon_par;
-+ struct fbcon_ops *ops = container_of(work, struct fbcon_ops, cursor_work.work);
-+ struct fb_info *info;
- struct vc_data *vc = NULL;
- int c;
- int mode;
-@@ -371,7 +371,10 @@ static void fb_flashcursor(struct work_struct *work)
- if (ret == 0)
- return;
-
-- if (ops && ops->currcon != -1)
-+ /* protected by console_lock */
-+ info = ops->info;
-+
-+ if (ops->currcon != -1)
- vc = vc_cons[ops->currcon].d;
-
- if (!vc || !con_is_visible(vc) ||
-@@ -387,42 +390,25 @@ static void fb_flashcursor(struct work_struct *work)
- ops->cursor(vc, info, mode, get_color(vc, info, c, 1),
- get_color(vc, info, c, 0));
- console_unlock();
--}
-
--static void cursor_timer_handler(struct timer_list *t)
--{
-- struct fbcon_ops *ops = from_timer(ops, t, cursor_timer);
-- struct fb_info *info = ops->info;
--
-- queue_work(system_power_efficient_wq, &info->queue);
-- mod_timer(&ops->cursor_timer, jiffies + ops->cur_blink_jiffies);
-+ queue_delayed_work(system_power_efficient_wq, &ops->cursor_work,
-+ ops->cur_blink_jiffies);
- }
-
--static void fbcon_add_cursor_timer(struct fb_info *info)
-+static void fbcon_add_cursor_work(struct fb_info *info)
- {
- struct fbcon_ops *ops = info->fbcon_par;
-
-- if ((!info->queue.func || info->queue.func == fb_flashcursor) &&
-- !(ops->flags & FBCON_FLAGS_CURSOR_TIMER) &&
-- !fbcon_cursor_noblink) {
-- if (!info->queue.func)
-- INIT_WORK(&info->queue, fb_flashcursor);
--
-- timer_setup(&ops->cursor_timer, cursor_timer_handler, 0);
-- mod_timer(&ops->cursor_timer, jiffies + ops->cur_blink_jiffies);
-- ops->flags |= FBCON_FLAGS_CURSOR_TIMER;
-- }
-+ if (!fbcon_cursor_noblink)
-+ queue_delayed_work(system_power_efficient_wq, &ops->cursor_work,
-+ ops->cur_blink_jiffies);
- }
-
--static void fbcon_del_cursor_timer(struct fb_info *info)
-+static void fbcon_del_cursor_work(struct fb_info *info)
- {
- struct fbcon_ops *ops = info->fbcon_par;
-
-- if (info->queue.func == fb_flashcursor &&
-- ops->flags & FBCON_FLAGS_CURSOR_TIMER) {
-- del_timer_sync(&ops->cursor_timer);
-- ops->flags &= ~FBCON_FLAGS_CURSOR_TIMER;
-- }
-+ cancel_delayed_work_sync(&ops->cursor_work);
- }
-
- #ifndef MODULE
-@@ -726,6 +712,8 @@ static int con2fb_acquire_newinfo(struct vc_data *vc, struct fb_info *info,
- }
-
- if (!err) {
-+ INIT_DELAYED_WORK(&ops->cursor_work, fb_flashcursor);
-+
- ops->cur_blink_jiffies = HZ / 5;
- ops->info = info;
- info->fbcon_par = ops;
-@@ -760,7 +748,7 @@ static int con2fb_release_oldinfo(struct vc_data *vc, struct fb_info *oldinfo,
- }
-
- if (!err) {
-- fbcon_del_cursor_timer(oldinfo);
-+ fbcon_del_cursor_work(oldinfo);
- kfree(ops->cursor_state.mask);
- kfree(ops->cursor_data);
- kfree(ops->cursor_src);
-@@ -876,7 +864,7 @@ static int set_con2fb_map(int unit, int newidx, int user)
- logo_shown != FBCON_LOGO_DONTSHOW);
-
- if (!found)
-- fbcon_add_cursor_timer(info);
-+ fbcon_add_cursor_work(info);
- con2fb_map_boot[unit] = newidx;
- con2fb_init_display(vc, info, unit, show_logo);
- }
-@@ -973,6 +961,8 @@ static const char *fbcon_startup(void)
- return NULL;
- }
-
-+ INIT_DELAYED_WORK(&ops->cursor_work, fb_flashcursor);
-+
- ops->currcon = -1;
- ops->graphics = 1;
- ops->cur_rotate = -1;
-@@ -1013,7 +1003,7 @@ static const char *fbcon_startup(void)
- info->var.yres,
- info->var.bits_per_pixel);
-
-- fbcon_add_cursor_timer(info);
-+ fbcon_add_cursor_work(info);
- return display_desc;
- }
-
-@@ -1199,7 +1189,7 @@ static void fbcon_deinit(struct vc_data *vc)
- goto finished;
-
- if (con_is_visible(vc))
-- fbcon_del_cursor_timer(info);
-+ fbcon_del_cursor_work(info);
-
- ops->flags &= ~FBCON_FLAGS_INIT;
- finished:
-@@ -1326,9 +1316,9 @@ static void fbcon_cursor(struct vc_data *vc, int mode)
- return;
-
- if (vc->vc_cursor_type & CUR_SW)
-- fbcon_del_cursor_timer(info);
-+ fbcon_del_cursor_work(info);
- else
-- fbcon_add_cursor_timer(info);
-+ fbcon_add_cursor_work(info);
-
- ops->cursor_flash = (mode == CM_ERASE) ? 0 : 1;
-
-@@ -2134,14 +2124,14 @@ static int fbcon_switch(struct vc_data *vc)
- }
-
- if (old_info != info)
-- fbcon_del_cursor_timer(old_info);
-+ fbcon_del_cursor_work(old_info);
- }
-
- if (fbcon_is_inactive(vc, info) ||
- ops->blank_state != FB_BLANK_UNBLANK)
-- fbcon_del_cursor_timer(info);
-+ fbcon_del_cursor_work(info);
- else
-- fbcon_add_cursor_timer(info);
-+ fbcon_add_cursor_work(info);
-
- set_blitting_type(vc, info);
- ops->cursor_reset = 1;
-@@ -2249,9 +2239,9 @@ static int fbcon_blank(struct vc_data *vc, int blank, int mode_switch)
-
- if (mode_switch || fbcon_is_inactive(vc, info) ||
- ops->blank_state != FB_BLANK_UNBLANK)
-- fbcon_del_cursor_timer(info);
-+ fbcon_del_cursor_work(info);
- else
-- fbcon_add_cursor_timer(info);
-+ fbcon_add_cursor_work(info);
-
- return 0;
- }
-@@ -3241,7 +3231,7 @@ static ssize_t show_cursor_blink(struct device *device,
- if (!ops)
- goto err;
-
-- blink = (ops->flags & FBCON_FLAGS_CURSOR_TIMER) ? 1 : 0;
-+ blink = delayed_work_pending(&ops->cursor_work);
- err:
- console_unlock();
- return snprintf(buf, PAGE_SIZE, "%d\n", blink);
-@@ -3270,10 +3260,10 @@ static ssize_t store_cursor_blink(struct device *device,
-
- if (blink) {
- fbcon_cursor_noblink = 0;
-- fbcon_add_cursor_timer(info);
-+ fbcon_add_cursor_work(info);
- } else {
- fbcon_cursor_noblink = 1;
-- fbcon_del_cursor_timer(info);
-+ fbcon_del_cursor_work(info);
- }
-
- err:
-@@ -3386,15 +3376,9 @@ static void fbcon_exit(void)
- #endif
-
- for_each_registered_fb(i) {
-- int pending = 0;
--
- mapped = 0;
- info = registered_fb[i];
-
-- if (info->queue.func)
-- pending = cancel_work_sync(&info->queue);
-- pr_debug("fbcon: %s pending work\n", (pending ? "canceled" : "no"));
--
- for (j = first_fb_vc; j <= last_fb_vc; j++) {
- if (con2fb_map[j] == i) {
- mapped = 1;
-@@ -3410,15 +3394,12 @@ static void fbcon_exit(void)
- if (info->fbcon_par) {
- struct fbcon_ops *ops = info->fbcon_par;
-
-- fbcon_del_cursor_timer(info);
-+ fbcon_del_cursor_work(info);
- kfree(ops->cursor_src);
- kfree(ops->cursor_state.mask);
- kfree(info->fbcon_par);
- info->fbcon_par = NULL;
- }
--
-- if (info->queue.func == fb_flashcursor)
-- info->queue.func = NULL;
- }
- }
- }
-diff --git a/drivers/video/fbdev/core/fbcon.h b/drivers/video/fbdev/core/fbcon.h
-index 3e1ec454b8aa3..a709e5796ef7e 100644
---- a/drivers/video/fbdev/core/fbcon.h
-+++ b/drivers/video/fbdev/core/fbcon.h
-@@ -14,11 +14,11 @@
- #include <linux/types.h>
- #include <linux/vt_buffer.h>
- #include <linux/vt_kern.h>
-+#include <linux/workqueue.h>
-
- #include <asm/io.h>
-
- #define FBCON_FLAGS_INIT 1
--#define FBCON_FLAGS_CURSOR_TIMER 2
-
- /*
- * This is the interface between the low-level console driver and the
-@@ -68,7 +68,7 @@ struct fbcon_ops {
- int (*update_start)(struct fb_info *info);
- int (*rotate_font)(struct fb_info *info, struct vc_data *vc);
- struct fb_var_screeninfo var; /* copy of the current fb_var_screeninfo */
-- struct timer_list cursor_timer; /* Cursor timer */
-+ struct delayed_work cursor_work; /* Cursor timer */
- struct fb_cursor cursor_state;
- struct fbcon_display *p;
- struct fb_info *info;
---
-2.39.5
-
+++ /dev/null
-From aad0fd8c1c0ea7e5b79ea269223efddf5c73720a Mon Sep 17 00:00:00 2001
-From: Sasha Levin <sashal@kernel.org>
-Date: Tue, 5 Apr 2022 23:03:30 +0200
-Subject: fbcon: use lock_fb_info in fbcon_open/release
-
-From: Daniel Vetter <daniel.vetter@ffwll.ch>
-
-[ Upstream commit 04933a294dacca3aaa480889d53e6195778d4578 ]
-
-Now we get to the real motiviation, because fbmem.c insists that
-that's the right lock for these.
-
-Ofc fbcon.c has a lot more places where it probably should call
-lock_fb_info(). But looking at fbmem.c at least most of these seem to
-be protected by console_lock() too, which is probably what papers over
-any issues.
-
-Note that this means we're shuffling around a bit the locking sections
-for some of the console takeover and unbind paths, but not all:
-- console binding/unbinding from the console layer never with
-lock_fb_info
-- unbind (as opposed to unlink) never bother with lock_fb_info
-
-Also the real serialization against set_par and set_pan are still
-doing by wrapping the entire ioctl code in console_lock(). So this
-shuffling shouldn't be worse than what we had from a "can you trigger
-races?" pov, but it's at least clearer.
-
-Acked-by: Sam Ravnborg <sam@ravnborg.org>
-Signed-off-by: Daniel Vetter <daniel.vetter@intel.com>
-Cc: Daniel Vetter <daniel@ffwll.ch>
-Cc: Claudio Suarez <cssk@net-c.es>
-Cc: Tetsuo Handa <penguin-kernel@I-love.SAKURA.ne.jp>
-Cc: Thomas Zimmermann <tzimmermann@suse.de>
-Cc: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
-Cc: Du Cheng <ducheng2@gmail.com>
-Cc: Sam Ravnborg <sam@ravnborg.org>
-Cc: Matthew Wilcox <willy@infradead.org>
-Cc: William Kucharski <william.kucharski@oracle.com>
-Cc: Alex Deucher <alexander.deucher@amd.com>
-Cc: Zheyu Ma <zheyuma97@gmail.com>
-Cc: Zhen Lei <thunder.leizhen@huawei.com>
-Cc: Xiyu Yang <xiyuyang19@fudan.edu.cn>
-Link: https://patchwork.freedesktop.org/patch/msgid/20220405210335.3434130-13-daniel.vetter@ffwll.ch
-Stable-dep-of: 17186f1f90d3 ("fbdev: Fix do_register_framebuffer to prevent null-ptr-deref in fb_videomode_to_var")
-Signed-off-by: Sasha Levin <sashal@kernel.org>
----
- drivers/video/fbdev/core/fbcon.c | 5 +++++
- drivers/video/fbdev/core/fbmem.c | 4 ----
- 2 files changed, 5 insertions(+), 4 deletions(-)
-
-diff --git a/drivers/video/fbdev/core/fbcon.c b/drivers/video/fbdev/core/fbcon.c
-index 734b8f3f81b24..072a264ae380b 100644
---- a/drivers/video/fbdev/core/fbcon.c
-+++ b/drivers/video/fbdev/core/fbcon.c
-@@ -693,8 +693,10 @@ static int fbcon_invalid_charcount(struct fb_info *info, unsigned charcount)
-
- static void fbcon_release(struct fb_info *info)
- {
-+ lock_fb_info(info);
- if (info->fbops->fb_release)
- info->fbops->fb_release(info, 0);
-+ unlock_fb_info(info);
-
- module_put(info->fbops->owner);
- }
-@@ -706,11 +708,14 @@ static int fbcon_open(struct fb_info *info)
- if (!try_module_get(info->fbops->owner))
- return -ENODEV;
-
-+ lock_fb_info(info);
- if (info->fbops->fb_open &&
- info->fbops->fb_open(info, 0)) {
-+ unlock_fb_info(info);
- module_put(info->fbops->owner);
- return -ENODEV;
- }
-+ unlock_fb_info(info);
-
- ops = kzalloc(sizeof(struct fbcon_ops), GFP_KERNEL);
- if (!ops) {
-diff --git a/drivers/video/fbdev/core/fbmem.c b/drivers/video/fbdev/core/fbmem.c
-index d938c31e8f90a..f4253ec8a6409 100644
---- a/drivers/video/fbdev/core/fbmem.c
-+++ b/drivers/video/fbdev/core/fbmem.c
-@@ -1700,9 +1700,7 @@ static int do_register_framebuffer(struct fb_info *fb_info)
- console_lock();
- else
- atomic_inc(&ignore_console_lock_warning);
-- lock_fb_info(fb_info);
- ret = fbcon_fb_registered(fb_info);
-- unlock_fb_info(fb_info);
-
- if (!lockless_register_fb)
- console_unlock();
-@@ -1719,9 +1717,7 @@ static void unbind_console(struct fb_info *fb_info)
- return;
-
- console_lock();
-- lock_fb_info(fb_info);
- fbcon_fb_unbind(fb_info);
-- unlock_fb_info(fb_info);
- console_unlock();
- }
-
---
-2.39.5
-
+++ /dev/null
-From 717d77b6fe020171b16ba65269413b40ff77bec7 Mon Sep 17 00:00:00 2001
-From: Sasha Levin <sashal@kernel.org>
-Date: Mon, 28 Apr 2025 18:34:06 +0300
-Subject: fbdev: Fix do_register_framebuffer to prevent null-ptr-deref in
- fb_videomode_to_var
-
-From: Murad Masimov <m.masimov@mt-integration.ru>
-
-[ Upstream commit 17186f1f90d34fa701e4f14e6818305151637b9e ]
-
-If fb_add_videomode() in do_register_framebuffer() fails to allocate
-memory for fb_videomode, it will later lead to a null-ptr dereference in
-fb_videomode_to_var(), as the fb_info is registered while not having the
-mode in modelist that is expected to be there, i.e. the one that is
-described in fb_info->var.
-
-================================================================
-general protection fault, probably for non-canonical address 0xdffffc0000000001: 0000 [#1] PREEMPT SMP KASAN NOPTI
-KASAN: null-ptr-deref in range [0x0000000000000008-0x000000000000000f]
-CPU: 1 PID: 30371 Comm: syz-executor.1 Not tainted 5.10.226-syzkaller #0
-Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS 1.12.0-1 04/01/2014
-RIP: 0010:fb_videomode_to_var+0x24/0x610 drivers/video/fbdev/core/modedb.c:901
-Call Trace:
- display_to_var+0x3a/0x7c0 drivers/video/fbdev/core/fbcon.c:929
- fbcon_resize+0x3e2/0x8f0 drivers/video/fbdev/core/fbcon.c:2071
- resize_screen drivers/tty/vt/vt.c:1176 [inline]
- vc_do_resize+0x53a/0x1170 drivers/tty/vt/vt.c:1263
- fbcon_modechanged+0x3ac/0x6e0 drivers/video/fbdev/core/fbcon.c:2720
- fbcon_update_vcs+0x43/0x60 drivers/video/fbdev/core/fbcon.c:2776
- do_fb_ioctl+0x6d2/0x740 drivers/video/fbdev/core/fbmem.c:1128
- fb_ioctl+0xe7/0x150 drivers/video/fbdev/core/fbmem.c:1203
- vfs_ioctl fs/ioctl.c:48 [inline]
- __do_sys_ioctl fs/ioctl.c:753 [inline]
- __se_sys_ioctl fs/ioctl.c:739 [inline]
- __x64_sys_ioctl+0x19a/0x210 fs/ioctl.c:739
- do_syscall_64+0x33/0x40 arch/x86/entry/common.c:46
- entry_SYSCALL_64_after_hwframe+0x67/0xd1
-================================================================
-
-Even though fbcon_init() checks beforehand if fb_match_mode() in
-var_to_display() fails, it can not prevent the panic because fbcon_init()
-does not return error code. Considering this and the comment in the code
-about fb_match_mode() returning NULL - "This should not happen" - it is
-better to prevent registering the fb_info if its mode was not set
-successfully. Also move fb_add_videomode() closer to the beginning of
-do_register_framebuffer() to avoid having to do the cleanup on fail.
-
-Found by Linux Verification Center (linuxtesting.org) with Syzkaller.
-
-Fixes: 1da177e4c3f4 ("Linux-2.6.12-rc2")
-Cc: stable@vger.kernel.org
-Signed-off-by: Murad Masimov <m.masimov@mt-integration.ru>
-Signed-off-by: Helge Deller <deller@gmx.de>
-Signed-off-by: Sasha Levin <sashal@kernel.org>
----
- drivers/video/fbdev/core/fbmem.c | 18 +++++++++++-------
- 1 file changed, 11 insertions(+), 7 deletions(-)
-
-diff --git a/drivers/video/fbdev/core/fbmem.c b/drivers/video/fbdev/core/fbmem.c
-index 5e8ee360f6ba2..a8d6bd465ffe4 100644
---- a/drivers/video/fbdev/core/fbmem.c
-+++ b/drivers/video/fbdev/core/fbmem.c
-@@ -1622,7 +1622,7 @@ static void do_remove_conflicting_framebuffers(struct apertures_struct *a,
-
- static int do_register_framebuffer(struct fb_info *fb_info)
- {
-- int i;
-+ int i, err = 0;
- struct fb_videomode mode;
-
- if (fb_check_foreignness(fb_info))
-@@ -1635,10 +1635,18 @@ static int do_register_framebuffer(struct fb_info *fb_info)
- if (num_registered_fb == FB_MAX)
- return -ENXIO;
-
-- num_registered_fb++;
- for (i = 0 ; i < FB_MAX; i++)
- if (!registered_fb[i])
- break;
-+
-+ if (!fb_info->modelist.prev || !fb_info->modelist.next)
-+ INIT_LIST_HEAD(&fb_info->modelist);
-+
-+ fb_var_to_videomode(&mode, &fb_info->var);
-+ err = fb_add_videomode(&mode, &fb_info->modelist);
-+ if (err < 0)
-+ return err;
-+
- fb_info->node = i;
- refcount_set(&fb_info->count, 1);
- mutex_init(&fb_info->lock);
-@@ -1671,16 +1679,12 @@ static int do_register_framebuffer(struct fb_info *fb_info)
- if (!fb_info->pixmap.blit_y)
- fb_info->pixmap.blit_y = ~(u32)0;
-
-- if (!fb_info->modelist.prev || !fb_info->modelist.next)
-- INIT_LIST_HEAD(&fb_info->modelist);
--
- if (fb_info->skip_vt_switch)
- pm_vt_switch_required(fb_info->dev, false);
- else
- pm_vt_switch_required(fb_info->dev, true);
-
-- fb_var_to_videomode(&mode, &fb_info->var);
-- fb_add_videomode(&mode, &fb_info->modelist);
-+ num_registered_fb++;
- registered_fb[i] = fb_info;
-
- #ifdef CONFIG_GUMSTIX_AM200EPD
---
-2.39.5
-
asoc-codec-wcd9335-convert-to-gpio-descriptors.patch
asoc-codecs-wcd9335-fix-missing-free-of-regulator-su.patch
f2fs-don-t-over-report-free-space-or-inodes-in-statv.patch
-fbcon-use-delayed-work-for-cursor.patch
-fbcon-extract-fbcon_open-release-helpers.patch
-fbcon-move-more-common-code-into-fb_open.patch
-fbcon-use-lock_fb_info-in-fbcon_open-release.patch
-fbcon-move-console_lock-for-register-unlink-unregist.patch
-fbdev-fix-do_register_framebuffer-to-prevent-null-pt.patch
drivers-hv-rename-alloced-to-allocated.patch
drivers-hv-vmbus-add-utility-function-for-querying-r.patch
uio_hv_generic-query-the-ringbuffer-size-for-device.patch
Stable-dep-of: 03bcbbb3995b ("dummycon: Trigger redraw when switching consoles with deferred takeover")
Signed-off-by: Sasha Levin <sashal@kernel.org>
---
- drivers/tty/vt/vt.c | 2 +-
- drivers/video/console/dummycon.c | 4 ++--
- drivers/video/console/mdacon.c | 4 ++--
- drivers/video/console/newport_con.c | 4 ++--
- drivers/video/console/sticon.c | 4 ++--
- drivers/video/console/vgacon.c | 4 ++--
- drivers/video/fbdev/core/fbcon.c | 6 +++---
- include/linux/console.h | 4 +++-
+ drivers/tty/vt/vt.c | 2 +-
+ drivers/video/console/dummycon.c | 4 ++--
+ drivers/video/console/mdacon.c | 4 ++--
+ drivers/video/console/newport_con.c | 4 ++--
+ drivers/video/console/sticon.c | 4 ++--
+ drivers/video/console/vgacon.c | 4 ++--
+ drivers/video/fbdev/core/fbcon.c | 6 +++---
+ include/linux/console.h | 4 +++-
8 files changed, 17 insertions(+), 15 deletions(-)
-diff --git a/drivers/tty/vt/vt.c b/drivers/tty/vt/vt.c
-index 765db5a7d5f52..a6e0c803e96ec 100644
--- a/drivers/tty/vt/vt.c
+++ b/drivers/tty/vt/vt.c
-@@ -1014,7 +1014,7 @@ void redraw_screen(struct vc_data *vc, int is_switch)
+@@ -1014,7 +1014,7 @@ void redraw_screen(struct vc_data *vc, i
}
if (redraw) {
int old_was_color = vc->vc_can_do_color;
set_origin(vc);
-diff --git a/drivers/video/console/dummycon.c b/drivers/video/console/dummycon.c
-index 6918014b02408..d701f2b51f5b1 100644
--- a/drivers/video/console/dummycon.c
+++ b/drivers/video/console/dummycon.c
-@@ -119,9 +119,9 @@ static bool dummycon_scroll(struct vc_data *vc, unsigned int top,
+@@ -119,9 +119,9 @@ static bool dummycon_scroll(struct vc_da
return false;
}
}
/*
-diff --git a/drivers/video/console/mdacon.c b/drivers/video/console/mdacon.c
-index 1ddbb6cd5b0ca..26b41a8f36c87 100644
--- a/drivers/video/console/mdacon.c
+++ b/drivers/video/console/mdacon.c
-@@ -454,9 +454,9 @@ static void mdacon_clear(struct vc_data *c, unsigned int y, unsigned int x,
+@@ -454,9 +454,9 @@ static void mdacon_clear(struct vc_data
scr_memsetw(dest, eattr, width * 2);
}
}
static int mdacon_blank(struct vc_data *c, int blank, int mode_switch)
-diff --git a/drivers/video/console/newport_con.c b/drivers/video/console/newport_con.c
-index 5dac00c825946..1ebb18bf10983 100644
--- a/drivers/video/console/newport_con.c
+++ b/drivers/video/console/newport_con.c
-@@ -462,7 +462,7 @@ static void newport_cursor(struct vc_data *vc, int mode)
+@@ -462,7 +462,7 @@ static void newport_cursor(struct vc_dat
}
}
{
static int logo_drawn = 0;
-@@ -476,7 +476,7 @@ static int newport_switch(struct vc_data *vc)
+@@ -476,7 +476,7 @@ static int newport_switch(struct vc_data
}
}
}
static int newport_blank(struct vc_data *c, int blank, int mode_switch)
-diff --git a/drivers/video/console/sticon.c b/drivers/video/console/sticon.c
-index 58e983b18f1f4..6b82194a8ef36 100644
--- a/drivers/video/console/sticon.c
+++ b/drivers/video/console/sticon.c
-@@ -309,9 +309,9 @@ static void sticon_clear(struct vc_data *conp, unsigned int sy, unsigned int sx,
+@@ -309,9 +309,9 @@ static void sticon_clear(struct vc_data
conp->vc_video_erase_char, font_data[conp->vc_num]);
}
}
static int sticon_blank(struct vc_data *c, int blank, int mode_switch)
-diff --git a/drivers/video/console/vgacon.c b/drivers/video/console/vgacon.c
-index 54d79edbe85e1..448aede31b946 100644
--- a/drivers/video/console/vgacon.c
+++ b/drivers/video/console/vgacon.c
-@@ -616,7 +616,7 @@ static int vgacon_doresize(struct vc_data *c,
+@@ -616,7 +616,7 @@ static int vgacon_doresize(struct vc_dat
return 0;
}
{
int x = c->vc_cols * VGA_FONTWIDTH;
int y = c->vc_rows * c->vc_cell_height;
-@@ -645,7 +645,7 @@ static int vgacon_switch(struct vc_data *c)
+@@ -645,7 +645,7 @@ static int vgacon_switch(struct vc_data
vgacon_doresize(c, c->vc_cols, c->vc_rows);
}
}
static void vga_set_palette(struct vc_data *vc, const unsigned char *table)
-diff --git a/drivers/video/fbdev/core/fbcon.c b/drivers/video/fbdev/core/fbcon.c
-index 7467b7a27ce2f..1ce767de96c11 100644
--- a/drivers/video/fbdev/core/fbcon.c
+++ b/drivers/video/fbdev/core/fbcon.c
-@@ -2043,7 +2043,7 @@ static int fbcon_resize(struct vc_data *vc, unsigned int width,
+@@ -2062,7 +2062,7 @@ static int fbcon_resize(struct vc_data *
return 0;
}
{
struct fb_info *info, *old_info = NULL;
struct fbcon_ops *ops;
-@@ -2166,9 +2166,9 @@ static int fbcon_switch(struct vc_data *vc)
+@@ -2185,9 +2185,9 @@ static int fbcon_switch(struct vc_data *
vc->vc_origin + vc->vc_size_row * vc->vc_top,
vc->vc_size_row * (vc->vc_bottom -
vc->vc_top) / 2);
}
static void fbcon_generic_blank(struct vc_data *vc, struct fb_info *info,
-diff --git a/include/linux/console.h b/include/linux/console.h
-index bd7f3a6a64cd0..e2862542a162d 100644
--- a/include/linux/console.h
+++ b/include/linux/console.h
@@ -40,6 +40,8 @@ enum vc_intensity;
int (*con_blank)(struct vc_data *vc, int blank, int mode_switch);
int (*con_font_set)(struct vc_data *vc, struct console_font *font,
unsigned int flags);
---
-2.39.5
-
Stable-dep-of: 03bcbbb3995b ("dummycon: Trigger redraw when switching consoles with deferred takeover")
Signed-off-by: Sasha Levin <sashal@kernel.org>
---
- drivers/tty/vt/vt.c | 8 ++++----
- drivers/video/console/dummycon.c | 2 +-
- drivers/video/console/mdacon.c | 2 +-
- drivers/video/console/newport_con.c | 2 +-
- drivers/video/console/sticon.c | 2 +-
- drivers/video/console/vgacon.c | 4 ++--
- drivers/video/fbdev/core/fbcon.c | 2 +-
- include/linux/console.h | 4 +++-
+ drivers/tty/vt/vt.c | 8 ++++----
+ drivers/video/console/dummycon.c | 2 +-
+ drivers/video/console/mdacon.c | 2 +-
+ drivers/video/console/newport_con.c | 2 +-
+ drivers/video/console/sticon.c | 2 +-
+ drivers/video/console/vgacon.c | 4 ++--
+ drivers/video/fbdev/core/fbcon.c | 2 +-
+ include/linux/console.h | 4 +++-
8 files changed, 14 insertions(+), 12 deletions(-)
-diff --git a/drivers/tty/vt/vt.c b/drivers/tty/vt/vt.c
-index bd125ea5c51f4..0e3d7d8f5e75a 100644
--- a/drivers/tty/vt/vt.c
+++ b/drivers/tty/vt/vt.c
@@ -1050,7 +1050,7 @@ int vc_cons_allocated(unsigned int i)
{
/* ++Geert: vc->vc_sw->con_init determines console size */
if (vc->vc_sw)
-@@ -1134,7 +1134,7 @@ int vc_allocate(unsigned int currcons) /* return 0 on success */
+@@ -1134,7 +1134,7 @@ int vc_allocate(unsigned int currcons) /
vc->port.ops = &vc_port_ops;
INIT_WORK(&vc_cons[currcons].SAK_work, vc_SAK);
/* Assuming vc->vc_{cols,rows,screenbuf_size} are sane here. */
vc->vc_screenbuf = kzalloc(vc->vc_screenbuf_size, GFP_NOWAIT);
vc_init(vc, vc->vc_rows, vc->vc_cols,
-@@ -3692,7 +3692,7 @@ static int do_bind_con_driver(const struct consw *csw, int first, int last,
+@@ -3692,7 +3692,7 @@ static int do_bind_con_driver(const stru
old_was_color = vc->vc_can_do_color;
vc->vc_sw->con_deinit(vc);
vc->vc_origin = (unsigned long)vc->vc_screenbuf;
set_origin(vc);
update_attr(vc);
-diff --git a/drivers/video/console/dummycon.c b/drivers/video/console/dummycon.c
-index f1711b2f9ff05..9a19eb72a18b9 100644
--- a/drivers/video/console/dummycon.c
+++ b/drivers/video/console/dummycon.c
-@@ -97,7 +97,7 @@ static const char *dummycon_startup(void)
+@@ -97,7 +97,7 @@ static const char *dummycon_startup(void
return "dummy device";
}
{
vc->vc_can_do_color = 1;
if (init) {
-diff --git a/drivers/video/console/mdacon.c b/drivers/video/console/mdacon.c
-index ef29b321967f0..c5b255c968794 100644
--- a/drivers/video/console/mdacon.c
+++ b/drivers/video/console/mdacon.c
@@ -352,7 +352,7 @@ static const char *mdacon_startup(void)
{
c->vc_complement_mask = 0x0800; /* reverse video */
c->vc_display_fg = &mda_display_fg;
-diff --git a/drivers/video/console/newport_con.c b/drivers/video/console/newport_con.c
-index d9c682ae03926..4b7161a81b2f6 100644
--- a/drivers/video/console/newport_con.c
+++ b/drivers/video/console/newport_con.c
-@@ -324,7 +324,7 @@ static const char *newport_startup(void)
+@@ -324,7 +324,7 @@ out_unmap:
return NULL;
}
{
int cols, rows;
-diff --git a/drivers/video/console/sticon.c b/drivers/video/console/sticon.c
-index f304163e87e99..10302df885147 100644
--- a/drivers/video/console/sticon.c
+++ b/drivers/video/console/sticon.c
-@@ -272,7 +272,7 @@ static int sticon_font_set(struct vc_data *vc, struct console_font *font,
+@@ -272,7 +272,7 @@ static int sticon_font_set(struct vc_dat
return sticon_set_font(vc, font);
}
{
struct sti_struct *sti = sticon_sti;
int vc_cols, vc_rows;
-diff --git a/drivers/video/console/vgacon.c b/drivers/video/console/vgacon.c
-index 9bfe451050209..a9777fd38ad92 100644
--- a/drivers/video/console/vgacon.c
+++ b/drivers/video/console/vgacon.c
@@ -353,7 +353,7 @@ static const char *vgacon_startup(void)
{
struct uni_pagedict *p;
-@@ -370,7 +370,7 @@ static void vgacon_init(struct vc_data *c, int init)
+@@ -370,7 +370,7 @@ static void vgacon_init(struct vc_data *
c->vc_scan_lines = vga_scan_lines;
c->vc_font.height = c->vc_cell_height = vga_video_font_height;
if (init) {
c->vc_cols = vga_video_num_columns;
c->vc_rows = vga_video_num_lines;
-diff --git a/drivers/video/fbdev/core/fbcon.c b/drivers/video/fbdev/core/fbcon.c
-index a3af7aacfaf11..f47dbba972fbb 100644
--- a/drivers/video/fbdev/core/fbcon.c
+++ b/drivers/video/fbdev/core/fbcon.c
-@@ -983,7 +983,7 @@ static const char *fbcon_startup(void)
+@@ -1002,7 +1002,7 @@ static const char *fbcon_startup(void)
return display_desc;
}
{
struct fb_info *info;
struct fbcon_ops *ops;
-diff --git a/include/linux/console.h b/include/linux/console.h
-index a97f277cfdfa3..9258cb8e0841e 100644
--- a/include/linux/console.h
+++ b/include/linux/console.h
@@ -34,6 +34,8 @@ enum vc_intensity;
void (*con_deinit)(struct vc_data *vc);
void (*con_clear)(struct vc_data *vc, int sy, int sx, int height,
int width);
---
-2.39.5
-
Stable-dep-of: 03bcbbb3995b ("dummycon: Trigger redraw when switching consoles with deferred takeover")
Signed-off-by: Sasha Levin <sashal@kernel.org>
---
- drivers/tty/vt/vt.c | 2 +-
- drivers/video/console/dummycon.c | 4 ++--
- drivers/video/console/mdacon.c | 15 +++++---------
- drivers/video/console/newport_con.c | 6 +++---
- drivers/video/console/sticon.c | 8 ++++----
- drivers/video/console/vgacon.c | 4 ++--
- drivers/video/fbdev/core/fbcon.c | 32 +++++++++++++++++------------
- include/linux/console.h | 5 +++--
+ drivers/tty/vt/vt.c | 2 +-
+ drivers/video/console/dummycon.c | 4 ++--
+ drivers/video/console/mdacon.c | 15 +++++----------
+ drivers/video/console/newport_con.c | 6 +++---
+ drivers/video/console/sticon.c | 8 ++++----
+ drivers/video/console/vgacon.c | 4 ++--
+ drivers/video/fbdev/core/fbcon.c | 32 +++++++++++++++++++-------------
+ include/linux/console.h | 5 +++--
8 files changed, 39 insertions(+), 37 deletions(-)
-diff --git a/drivers/tty/vt/vt.c b/drivers/tty/vt/vt.c
-index 0e3d7d8f5e75a..765db5a7d5f52 100644
--- a/drivers/tty/vt/vt.c
+++ b/drivers/tty/vt/vt.c
-@@ -1628,7 +1628,7 @@ static void csi_X(struct vc_data *vc, unsigned int vpar)
+@@ -1628,7 +1628,7 @@ static void csi_X(struct vc_data *vc, un
vc_uniscr_clear_line(vc, vc->state.x, count);
scr_memsetw((unsigned short *)vc->vc_pos, vc->vc_video_erase_char, 2 * count);
if (con_should_update(vc))
vc->vc_need_wrap = 0;
}
-diff --git a/drivers/video/console/dummycon.c b/drivers/video/console/dummycon.c
-index 9a19eb72a18b9..6918014b02408 100644
--- a/drivers/video/console/dummycon.c
+++ b/drivers/video/console/dummycon.c
-@@ -108,8 +108,8 @@ static void dummycon_init(struct vc_data *vc, bool init)
+@@ -108,8 +108,8 @@ static void dummycon_init(struct vc_data
}
static void dummycon_deinit(struct vc_data *vc) { }
static void dummycon_cursor(struct vc_data *vc, int mode) { }
static bool dummycon_scroll(struct vc_data *vc, unsigned int top,
-diff --git a/drivers/video/console/mdacon.c b/drivers/video/console/mdacon.c
-index c5b255c968794..1ddbb6cd5b0ca 100644
--- a/drivers/video/console/mdacon.c
+++ b/drivers/video/console/mdacon.c
-@@ -442,23 +442,18 @@ static void mdacon_putcs(struct vc_data *c, const unsigned short *s,
+@@ -442,23 +442,18 @@ static void mdacon_putcs(struct vc_data
}
}
static int mdacon_switch(struct vc_data *c)
{
return 1; /* redrawing needed */
-diff --git a/drivers/video/console/newport_con.c b/drivers/video/console/newport_con.c
-index 4b7161a81b2f6..5dac00c825946 100644
--- a/drivers/video/console/newport_con.c
+++ b/drivers/video/console/newport_con.c
-@@ -346,12 +346,12 @@ static void newport_deinit(struct vc_data *c)
+@@ -346,12 +346,12 @@ static void newport_deinit(struct vc_dat
}
}
if (logo_active)
return;
-diff --git a/drivers/video/console/sticon.c b/drivers/video/console/sticon.c
-index 10302df885147..58e983b18f1f4 100644
--- a/drivers/video/console/sticon.c
+++ b/drivers/video/console/sticon.c
-@@ -299,13 +299,13 @@ static void sticon_deinit(struct vc_data *c)
+@@ -299,13 +299,13 @@ static void sticon_deinit(struct vc_data
sticon_set_def_font(i, NULL);
}
conp->vc_video_erase_char, font_data[conp->vc_num]);
}
-diff --git a/drivers/video/console/vgacon.c b/drivers/video/console/vgacon.c
-index a9777fd38ad92..54d79edbe85e1 100644
--- a/drivers/video/console/vgacon.c
+++ b/drivers/video/console/vgacon.c
-@@ -1187,8 +1187,8 @@ static bool vgacon_scroll(struct vc_data *c, unsigned int t, unsigned int b,
+@@ -1187,8 +1187,8 @@ static bool vgacon_scroll(struct vc_data
* The console `switch' structure for the VGA based console
*/
static void vgacon_putc(struct vc_data *vc, int c, int ypos, int xpos) { }
static void vgacon_putcs(struct vc_data *vc, const unsigned short *s,
int count, int ypos, int xpos) { }
-diff --git a/drivers/video/fbdev/core/fbcon.c b/drivers/video/fbdev/core/fbcon.c
-index f47dbba972fbb..7467b7a27ce2f 100644
--- a/drivers/video/fbdev/core/fbcon.c
+++ b/drivers/video/fbdev/core/fbcon.c
-@@ -1210,8 +1210,8 @@ static void fbcon_deinit(struct vc_data *vc)
+@@ -1229,8 +1229,8 @@ finished:
* restriction is simplicity & efficiency at the moment.
*/
{
struct fb_info *info = registered_fb[con2fb_map[vc->vc_num]];
struct fbcon_ops *ops = info->fbcon_par;
-@@ -1250,6 +1250,12 @@ static void fbcon_clear(struct vc_data *vc, int sy, int sx, int height,
+@@ -1269,6 +1269,12 @@ static void fbcon_clear(struct vc_data *
ops->clear(vc, info, real_y(p, sy), sx, height, width, fg, bg);
}
static void fbcon_putcs(struct vc_data *vc, const unsigned short *s,
int count, int ypos, int xpos)
{
-@@ -1673,7 +1679,7 @@ static bool fbcon_scroll(struct vc_data *vc, unsigned int t, unsigned int b,
+@@ -1692,7 +1698,7 @@ static bool fbcon_scroll(struct vc_data
case SCROLL_MOVE:
fbcon_redraw_blit(vc, info, p, t, b - t - count,
count);
scr_memsetw((unsigned short *) (vc->vc_origin +
vc->vc_size_row *
(b - count)),
-@@ -1696,7 +1702,7 @@ static bool fbcon_scroll(struct vc_data *vc, unsigned int t, unsigned int b,
+@@ -1715,7 +1721,7 @@ static bool fbcon_scroll(struct vc_data
b - t - count, vc->vc_cols);
else
goto redraw_up;
break;
case SCROLL_PAN_REDRAW:
-@@ -1714,7 +1720,7 @@ static bool fbcon_scroll(struct vc_data *vc, unsigned int t, unsigned int b,
+@@ -1733,7 +1739,7 @@ static bool fbcon_scroll(struct vc_data
vc->vc_rows - b, b);
} else
fbcon_redraw_move(vc, p, t + count, b - t - count, t);
break;
case SCROLL_PAN_MOVE:
-@@ -1737,14 +1743,14 @@ static bool fbcon_scroll(struct vc_data *vc, unsigned int t, unsigned int b,
+@@ -1756,14 +1762,14 @@ static bool fbcon_scroll(struct vc_data
b - t - count, vc->vc_cols);
else
goto redraw_up;
scr_memsetw((unsigned short *) (vc->vc_origin +
vc->vc_size_row *
(b - count)),
-@@ -1761,7 +1767,7 @@ static bool fbcon_scroll(struct vc_data *vc, unsigned int t, unsigned int b,
+@@ -1780,7 +1786,7 @@ static bool fbcon_scroll(struct vc_data
case SCROLL_MOVE:
fbcon_redraw_blit(vc, info, p, b - 1, b - t - count,
-count);
scr_memsetw((unsigned short *) (vc->vc_origin +
vc->vc_size_row *
t),
-@@ -1784,7 +1790,7 @@ static bool fbcon_scroll(struct vc_data *vc, unsigned int t, unsigned int b,
+@@ -1803,7 +1809,7 @@ static bool fbcon_scroll(struct vc_data
b - t - count, vc->vc_cols);
else
goto redraw_down;
break;
case SCROLL_PAN_MOVE:
-@@ -1806,7 +1812,7 @@ static bool fbcon_scroll(struct vc_data *vc, unsigned int t, unsigned int b,
+@@ -1825,7 +1831,7 @@ static bool fbcon_scroll(struct vc_data
b - t - count, vc->vc_cols);
else
goto redraw_down;
break;
case SCROLL_PAN_REDRAW:
-@@ -1823,14 +1829,14 @@ static bool fbcon_scroll(struct vc_data *vc, unsigned int t, unsigned int b,
+@@ -1842,14 +1848,14 @@ static bool fbcon_scroll(struct vc_data
fbcon_redraw_move(vc, p, count, t, 0);
} else
fbcon_redraw_move(vc, p, t, b - t - count, t + count);
scr_memsetw((unsigned short *) (vc->vc_origin +
vc->vc_size_row *
t),
-@@ -2175,7 +2181,7 @@ static void fbcon_generic_blank(struct vc_data *vc, struct fb_info *info,
+@@ -2194,7 +2200,7 @@ static void fbcon_generic_blank(struct v
oldc = vc->vc_video_erase_char;
vc->vc_video_erase_char &= charmask;
vc->vc_video_erase_char = oldc;
}
}
-diff --git a/include/linux/console.h b/include/linux/console.h
-index 9258cb8e0841e..bd7f3a6a64cd0 100644
--- a/include/linux/console.h
+++ b/include/linux/console.h
@@ -36,6 +36,7 @@ enum vc_intensity;
void (*con_putc)(struct vc_data *vc, int c, int ypos, int xpos);
void (*con_putcs)(struct vc_data *vc, const unsigned short *s,
int count, int ypos, int xpos);
---
-2.39.5
-