stable.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
To: linux-kernel@vger.kernel.org
Cc: Greg Kroah-Hartman <gregkh@linuxfoundation.org>,
	stable@vger.kernel.org, Helge Deller <deller@gmx.de>,
	Geert Uytterhoeven <geert@linux-m68k.org>,
	Sven Schnelle <svens@stackframe.org>,
	Daniel Vetter <daniel.vetter@ffwll.ch>
Subject: [PATCH 5.16 039/126] Revert "fbdev: Garbage collect fbdev scrolling acceleration, part 1 (from TODO list)"
Date: Mon,  7 Feb 2022 12:06:10 +0100	[thread overview]
Message-ID: <20220207103805.481274163@linuxfoundation.org> (raw)
In-Reply-To: <20220207103804.053675072@linuxfoundation.org>

From: Helge Deller <deller@gmx.de>

commit 1148836fd3226c20de841084aba24184d4fbbe77 upstream.

This reverts commit b3ec8cdf457e5e63d396fe1346cc788cf7c1b578.

Revert the second (of 2) commits which disabled scrolling acceleration
in fbcon/fbdev.  It introduced a regression for fbdev-supported graphic
cards because of the performance penalty by doing screen scrolling by
software instead of using the existing graphic card 2D hardware
acceleration.

Console scrolling acceleration was disabled by dropping code which
checked at runtime the driver hardware capabilities for the
BINFO_HWACCEL_COPYAREA or FBINFO_HWACCEL_FILLRECT flags and if set, it
enabled scrollmode SCROLL_MOVE which uses hardware acceleration to move
screen contents.  After dropping those checks scrollmode was hard-wired
to SCROLL_REDRAW instead, which forces all graphic cards to redraw every
character at the new screen position when scrolling.

This change effectively disabled all hardware-based scrolling acceleration for
ALL drivers, because now all kind of 2D hardware acceleration (bitblt,
fillrect) in the drivers isn't used any longer.

The original commit message mentions that only 3 DRM drivers (nouveau, omapdrm
and gma500) used hardware acceleration in the past and thus code for checking
and using scrolling acceleration is obsolete.

This statement is NOT TRUE, because beside the DRM drivers there are around 35
other fbdev drivers which depend on fbdev/fbcon and still provide hardware
acceleration for fbdev/fbcon.

The original commit message also states that syzbot found lots of bugs in fbcon
and thus it's "often the solution to just delete code and remove features".
This is true, and the bugs - which actually affected all users of fbcon,
including DRM - were fixed, or code was dropped like e.g. the support for
software scrollback in vgacon (commit 973c096f6a85).

So to further analyze which bugs were found by syzbot, I've looked through all
patches in drivers/video which were tagged with syzbot or syzkaller back to
year 2005. The vast majority fixed the reported issues on a higher level, e.g.
when screen is to be resized, or when font size is to be changed. The few ones
which touched driver code fixed a real driver bug, e.g. by adding a check.

But NONE of those patches touched code of either the SCROLL_MOVE or the
SCROLL_REDRAW case.

That means, there was no real reason why SCROLL_MOVE had to be ripped-out and
just SCROLL_REDRAW had to be used instead. The only reason I can imagine so far
was that SCROLL_MOVE wasn't used by DRM and as such it was assumed that it
could go away. That argument completely missed the fact that SCROLL_MOVE is
still heavily used by fbdev (non-DRM) drivers.

Some people mention that using memcpy() instead of the hardware acceleration is
pretty much the same speed. But that's not true, at least not for older graphic
cards and machines where we see speed decreases by factor 10 and more and thus
this change leads to console responsiveness way worse than before.

That's why the original commit is to be reverted. By reverting we
reintroduce hardware-based scrolling acceleration and fix the
performance regression for fbdev drivers.

There isn't any impact on DRM when reverting those patches.

Signed-off-by: Helge Deller <deller@gmx.de>
Acked-by: Geert Uytterhoeven <geert@linux-m68k.org>
Acked-by: Sven Schnelle <svens@stackframe.org>
Cc: stable@vger.kernel.org # v5.16+
Signed-off-by: Helge Deller <deller@gmx.de>
Signed-off-by: Daniel Vetter <daniel.vetter@ffwll.ch>
Link: https://patchwork.freedesktop.org/patch/msgid/20220202135531.92183-2-deller@gmx.de
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
---
 Documentation/gpu/todo.rst              |   13 
 drivers/video/fbdev/core/bitblit.c      |   16 +
 drivers/video/fbdev/core/fbcon.c        |  509 ++++++++++++++++++++++++++++++--
 drivers/video/fbdev/core/fbcon.h        |   59 +++
 drivers/video/fbdev/core/fbcon_ccw.c    |   28 +
 drivers/video/fbdev/core/fbcon_cw.c     |   28 +
 drivers/video/fbdev/core/fbcon_rotate.h |    9 
 drivers/video/fbdev/core/fbcon_ud.c     |   37 +-
 drivers/video/fbdev/core/tileblit.c     |   16 +
 drivers/video/fbdev/skeletonfb.c        |   12 
 include/linux/fb.h                      |    2 
 11 files changed, 678 insertions(+), 51 deletions(-)

--- a/Documentation/gpu/todo.rst
+++ b/Documentation/gpu/todo.rst
@@ -314,19 +314,16 @@ Level: Advanced
 Garbage collect fbdev scrolling acceleration
 --------------------------------------------
 
-Scroll acceleration has been disabled in fbcon. Now it works as the old
-SCROLL_REDRAW mode. A ton of code was removed in fbcon.c and the hook bmove was
-removed from fbcon_ops.
-Remaining tasks:
+Scroll acceleration is disabled in fbcon by hard-wiring p->scrollmode =
+SCROLL_REDRAW. There's a ton of code this will allow us to remove:
 
-- a bunch of the hooks in fbcon_ops could be removed or simplified by calling
+- lots of code in fbcon.c
+
+- a bunch of the hooks in fbcon_ops, maybe the remaining hooks could be called
   directly instead of the function table (with a switch on p->rotate)
 
 - fb_copyarea is unused after this, and can be deleted from all drivers
 
-- after that, fb_copyarea can be deleted from fb_ops in include/linux/fb.h as
-  well as cfb_copyarea
-
 Note that not all acceleration code can be deleted, since clearing and cursor
 support is still accelerated, which might be good candidates for further
 deletion projects.
--- a/drivers/video/fbdev/core/bitblit.c
+++ b/drivers/video/fbdev/core/bitblit.c
@@ -43,6 +43,21 @@ static void update_attr(u8 *dst, u8 *src
 	}
 }
 
+static void bit_bmove(struct vc_data *vc, struct fb_info *info, int sy,
+		      int sx, int dy, int dx, int height, int width)
+{
+	struct fb_copyarea area;
+
+	area.sx = sx * vc->vc_font.width;
+	area.sy = sy * vc->vc_font.height;
+	area.dx = dx * vc->vc_font.width;
+	area.dy = dy * vc->vc_font.height;
+	area.height = height * vc->vc_font.height;
+	area.width = width * vc->vc_font.width;
+
+	info->fbops->fb_copyarea(info, &area);
+}
+
 static void bit_clear(struct vc_data *vc, struct fb_info *info, int sy,
 		      int sx, int height, int width)
 {
@@ -378,6 +393,7 @@ static int bit_update_start(struct fb_in
 
 void fbcon_set_bitops(struct fbcon_ops *ops)
 {
+	ops->bmove = bit_bmove;
 	ops->clear = bit_clear;
 	ops->putcs = bit_putcs;
 	ops->clear_margins = bit_clear_margins;
--- a/drivers/video/fbdev/core/fbcon.c
+++ b/drivers/video/fbdev/core/fbcon.c
@@ -173,6 +173,8 @@ static void fbcon_putcs(struct vc_data *
 			int count, int ypos, int xpos);
 static void fbcon_clear_margins(struct vc_data *vc, int bottom_only);
 static void fbcon_cursor(struct vc_data *vc, int mode);
+static void fbcon_bmove(struct vc_data *vc, int sy, int sx, int dy, int dx,
+			int height, int width);
 static int fbcon_switch(struct vc_data *vc);
 static int fbcon_blank(struct vc_data *vc, int blank, int mode_switch);
 static void fbcon_set_palette(struct vc_data *vc, const unsigned char *table);
@@ -180,8 +182,16 @@ static void fbcon_set_palette(struct vc_
 /*
  *  Internal routines
  */
+static __inline__ void ywrap_up(struct vc_data *vc, int count);
+static __inline__ void ywrap_down(struct vc_data *vc, int count);
+static __inline__ void ypan_up(struct vc_data *vc, int count);
+static __inline__ void ypan_down(struct vc_data *vc, int count);
+static void fbcon_bmove_rec(struct vc_data *vc, struct fbcon_display *p, int sy, int sx,
+			    int dy, int dx, int height, int width, u_int y_break);
 static void fbcon_set_disp(struct fb_info *info, struct fb_var_screeninfo *var,
 			   int unit);
+static void fbcon_redraw_move(struct vc_data *vc, struct fbcon_display *p,
+			      int line, int count, int dy);
 static void fbcon_modechanged(struct fb_info *info);
 static void fbcon_set_all_vcs(struct fb_info *info);
 static void fbcon_start(void);
@@ -1126,6 +1136,14 @@ static void fbcon_init(struct vc_data *v
 	ops->graphics = 0;
 
 	/*
+	 * No more hw acceleration for fbcon.
+	 *
+	 * FIXME: Garbage collect all the now dead code after sufficient time
+	 * has passed.
+	 */
+	p->scrollmode = SCROLL_REDRAW;
+
+	/*
 	 *  ++guenther: console.c:vc_allocate() relies on initializing
 	 *  vc_{cols,rows}, but we must not set those if we are only
 	 *  resizing the console.
@@ -1211,13 +1229,14 @@ finished:
  *  This system is now divided into two levels because of complications
  *  caused by hardware scrolling. Top level functions:
  *
- *	fbcon_clear(), fbcon_putc(), fbcon_clear_margins()
+ *	fbcon_bmove(), fbcon_clear(), fbcon_putc(), fbcon_clear_margins()
  *
  *  handles y values in range [0, scr_height-1] that correspond to real
  *  screen positions. y_wrap shift means that first line of bitmap may be
  *  anywhere on this display. These functions convert lineoffsets to
  *  bitmap offsets and deal with the wrap-around case by splitting blits.
  *
+ *	fbcon_bmove_physical_8()    -- These functions fast implementations
  *	fbcon_clear_physical_8()    -- of original fbcon_XXX fns.
  *	fbcon_putc_physical_8()	    -- (font width != 8) may be added later
  *
@@ -1390,6 +1409,224 @@ static void fbcon_set_disp(struct fb_inf
 	}
 }
 
+static __inline__ void ywrap_up(struct vc_data *vc, int count)
+{
+	struct fb_info *info = registered_fb[con2fb_map[vc->vc_num]];
+	struct fbcon_ops *ops = info->fbcon_par;
+	struct fbcon_display *p = &fb_display[vc->vc_num];
+
+	p->yscroll += count;
+	if (p->yscroll >= p->vrows)	/* Deal with wrap */
+		p->yscroll -= p->vrows;
+	ops->var.xoffset = 0;
+	ops->var.yoffset = p->yscroll * vc->vc_font.height;
+	ops->var.vmode |= FB_VMODE_YWRAP;
+	ops->update_start(info);
+	scrollback_max += count;
+	if (scrollback_max > scrollback_phys_max)
+		scrollback_max = scrollback_phys_max;
+	scrollback_current = 0;
+}
+
+static __inline__ void ywrap_down(struct vc_data *vc, int count)
+{
+	struct fb_info *info = registered_fb[con2fb_map[vc->vc_num]];
+	struct fbcon_ops *ops = info->fbcon_par;
+	struct fbcon_display *p = &fb_display[vc->vc_num];
+
+	p->yscroll -= count;
+	if (p->yscroll < 0)	/* Deal with wrap */
+		p->yscroll += p->vrows;
+	ops->var.xoffset = 0;
+	ops->var.yoffset = p->yscroll * vc->vc_font.height;
+	ops->var.vmode |= FB_VMODE_YWRAP;
+	ops->update_start(info);
+	scrollback_max -= count;
+	if (scrollback_max < 0)
+		scrollback_max = 0;
+	scrollback_current = 0;
+}
+
+static __inline__ void ypan_up(struct vc_data *vc, int count)
+{
+	struct fb_info *info = registered_fb[con2fb_map[vc->vc_num]];
+	struct fbcon_display *p = &fb_display[vc->vc_num];
+	struct fbcon_ops *ops = info->fbcon_par;
+
+	p->yscroll += count;
+	if (p->yscroll > p->vrows - vc->vc_rows) {
+		ops->bmove(vc, info, p->vrows - vc->vc_rows,
+			    0, 0, 0, vc->vc_rows, vc->vc_cols);
+		p->yscroll -= p->vrows - vc->vc_rows;
+	}
+
+	ops->var.xoffset = 0;
+	ops->var.yoffset = p->yscroll * vc->vc_font.height;
+	ops->var.vmode &= ~FB_VMODE_YWRAP;
+	ops->update_start(info);
+	fbcon_clear_margins(vc, 1);
+	scrollback_max += count;
+	if (scrollback_max > scrollback_phys_max)
+		scrollback_max = scrollback_phys_max;
+	scrollback_current = 0;
+}
+
+static __inline__ void ypan_up_redraw(struct vc_data *vc, int t, int count)
+{
+	struct fb_info *info = registered_fb[con2fb_map[vc->vc_num]];
+	struct fbcon_ops *ops = info->fbcon_par;
+	struct fbcon_display *p = &fb_display[vc->vc_num];
+
+	p->yscroll += count;
+
+	if (p->yscroll > p->vrows - vc->vc_rows) {
+		p->yscroll -= p->vrows - vc->vc_rows;
+		fbcon_redraw_move(vc, p, t + count, vc->vc_rows - count, t);
+	}
+
+	ops->var.xoffset = 0;
+	ops->var.yoffset = p->yscroll * vc->vc_font.height;
+	ops->var.vmode &= ~FB_VMODE_YWRAP;
+	ops->update_start(info);
+	fbcon_clear_margins(vc, 1);
+	scrollback_max += count;
+	if (scrollback_max > scrollback_phys_max)
+		scrollback_max = scrollback_phys_max;
+	scrollback_current = 0;
+}
+
+static __inline__ void ypan_down(struct vc_data *vc, int count)
+{
+	struct fb_info *info = registered_fb[con2fb_map[vc->vc_num]];
+	struct fbcon_display *p = &fb_display[vc->vc_num];
+	struct fbcon_ops *ops = info->fbcon_par;
+
+	p->yscroll -= count;
+	if (p->yscroll < 0) {
+		ops->bmove(vc, info, 0, 0, p->vrows - vc->vc_rows,
+			    0, vc->vc_rows, vc->vc_cols);
+		p->yscroll += p->vrows - vc->vc_rows;
+	}
+
+	ops->var.xoffset = 0;
+	ops->var.yoffset = p->yscroll * vc->vc_font.height;
+	ops->var.vmode &= ~FB_VMODE_YWRAP;
+	ops->update_start(info);
+	fbcon_clear_margins(vc, 1);
+	scrollback_max -= count;
+	if (scrollback_max < 0)
+		scrollback_max = 0;
+	scrollback_current = 0;
+}
+
+static __inline__ void ypan_down_redraw(struct vc_data *vc, int t, int count)
+{
+	struct fb_info *info = registered_fb[con2fb_map[vc->vc_num]];
+	struct fbcon_ops *ops = info->fbcon_par;
+	struct fbcon_display *p = &fb_display[vc->vc_num];
+
+	p->yscroll -= count;
+
+	if (p->yscroll < 0) {
+		p->yscroll += p->vrows - vc->vc_rows;
+		fbcon_redraw_move(vc, p, t, vc->vc_rows - count, t + count);
+	}
+
+	ops->var.xoffset = 0;
+	ops->var.yoffset = p->yscroll * vc->vc_font.height;
+	ops->var.vmode &= ~FB_VMODE_YWRAP;
+	ops->update_start(info);
+	fbcon_clear_margins(vc, 1);
+	scrollback_max -= count;
+	if (scrollback_max < 0)
+		scrollback_max = 0;
+	scrollback_current = 0;
+}
+
+static void fbcon_redraw_move(struct vc_data *vc, struct fbcon_display *p,
+			      int line, int count, int dy)
+{
+	unsigned short *s = (unsigned short *)
+		(vc->vc_origin + vc->vc_size_row * line);
+
+	while (count--) {
+		unsigned short *start = s;
+		unsigned short *le = advance_row(s, 1);
+		unsigned short c;
+		int x = 0;
+		unsigned short attr = 1;
+
+		do {
+			c = scr_readw(s);
+			if (attr != (c & 0xff00)) {
+				attr = c & 0xff00;
+				if (s > start) {
+					fbcon_putcs(vc, start, s - start,
+						    dy, x);
+					x += s - start;
+					start = s;
+				}
+			}
+			console_conditional_schedule();
+			s++;
+		} while (s < le);
+		if (s > start)
+			fbcon_putcs(vc, start, s - start, dy, x);
+		console_conditional_schedule();
+		dy++;
+	}
+}
+
+static void fbcon_redraw_blit(struct vc_data *vc, struct fb_info *info,
+			struct fbcon_display *p, int line, int count, int ycount)
+{
+	int offset = ycount * vc->vc_cols;
+	unsigned short *d = (unsigned short *)
+	    (vc->vc_origin + vc->vc_size_row * line);
+	unsigned short *s = d + offset;
+	struct fbcon_ops *ops = info->fbcon_par;
+
+	while (count--) {
+		unsigned short *start = s;
+		unsigned short *le = advance_row(s, 1);
+		unsigned short c;
+		int x = 0;
+
+		do {
+			c = scr_readw(s);
+
+			if (c == scr_readw(d)) {
+				if (s > start) {
+					ops->bmove(vc, info, line + ycount, x,
+						   line, x, 1, s-start);
+					x += s - start + 1;
+					start = s + 1;
+				} else {
+					x++;
+					start++;
+				}
+			}
+
+			scr_writew(c, d);
+			console_conditional_schedule();
+			s++;
+			d++;
+		} while (s < le);
+		if (s > start)
+			ops->bmove(vc, info, line + ycount, x, line, x, 1,
+				   s-start);
+		console_conditional_schedule();
+		if (ycount > 0)
+			line++;
+		else {
+			line--;
+			/* NOTE: We subtract two lines from these pointers */
+			s -= vc->vc_size_row;
+			d -= vc->vc_size_row;
+		}
+	}
+}
+
 static void fbcon_redraw(struct vc_data *vc, struct fbcon_display *p,
 			 int line, int count, int offset)
 {
@@ -1450,6 +1687,7 @@ static bool fbcon_scroll(struct vc_data
 {
 	struct fb_info *info = registered_fb[con2fb_map[vc->vc_num]];
 	struct fbcon_display *p = &fb_display[vc->vc_num];
+	int scroll_partial = info->flags & FBINFO_PARTIAL_PAN_OK;
 
 	if (fbcon_is_inactive(vc, info))
 		return true;
@@ -1466,32 +1704,249 @@ static bool fbcon_scroll(struct vc_data
 	case SM_UP:
 		if (count > vc->vc_rows)	/* Maximum realistic size */
 			count = vc->vc_rows;
-		fbcon_redraw(vc, p, t, b - t - count,
-			     count * vc->vc_cols);
-		fbcon_clear(vc, b - count, 0, count, vc->vc_cols);
-		scr_memsetw((unsigned short *) (vc->vc_origin +
-						vc->vc_size_row *
-						(b - count)),
-			    vc->vc_video_erase_char,
-			    vc->vc_size_row * count);
-		return true;
+		if (logo_shown >= 0)
+			goto redraw_up;
+		switch (p->scrollmode) {
+		case SCROLL_MOVE:
+			fbcon_redraw_blit(vc, info, p, t, b - t - count,
+				     count);
+			fbcon_clear(vc, b - count, 0, count, vc->vc_cols);
+			scr_memsetw((unsigned short *) (vc->vc_origin +
+							vc->vc_size_row *
+							(b - count)),
+				    vc->vc_video_erase_char,
+				    vc->vc_size_row * count);
+			return true;
+
+		case SCROLL_WRAP_MOVE:
+			if (b - t - count > 3 * vc->vc_rows >> 2) {
+				if (t > 0)
+					fbcon_bmove(vc, 0, 0, count, 0, t,
+						    vc->vc_cols);
+				ywrap_up(vc, count);
+				if (vc->vc_rows - b > 0)
+					fbcon_bmove(vc, b - count, 0, b, 0,
+						    vc->vc_rows - b,
+						    vc->vc_cols);
+			} else if (info->flags & FBINFO_READS_FAST)
+				fbcon_bmove(vc, t + count, 0, t, 0,
+					    b - t - count, vc->vc_cols);
+			else
+				goto redraw_up;
+			fbcon_clear(vc, b - count, 0, count, vc->vc_cols);
+			break;
+
+		case SCROLL_PAN_REDRAW:
+			if ((p->yscroll + count <=
+			     2 * (p->vrows - vc->vc_rows))
+			    && ((!scroll_partial && (b - t == vc->vc_rows))
+				|| (scroll_partial
+				    && (b - t - count >
+					3 * vc->vc_rows >> 2)))) {
+				if (t > 0)
+					fbcon_redraw_move(vc, p, 0, t, count);
+				ypan_up_redraw(vc, t, count);
+				if (vc->vc_rows - b > 0)
+					fbcon_redraw_move(vc, p, b,
+							  vc->vc_rows - b, b);
+			} else
+				fbcon_redraw_move(vc, p, t + count, b - t - count, t);
+			fbcon_clear(vc, b - count, 0, count, vc->vc_cols);
+			break;
+
+		case SCROLL_PAN_MOVE:
+			if ((p->yscroll + count <=
+			     2 * (p->vrows - vc->vc_rows))
+			    && ((!scroll_partial && (b - t == vc->vc_rows))
+				|| (scroll_partial
+				    && (b - t - count >
+					3 * vc->vc_rows >> 2)))) {
+				if (t > 0)
+					fbcon_bmove(vc, 0, 0, count, 0, t,
+						    vc->vc_cols);
+				ypan_up(vc, count);
+				if (vc->vc_rows - b > 0)
+					fbcon_bmove(vc, b - count, 0, b, 0,
+						    vc->vc_rows - b,
+						    vc->vc_cols);
+			} else if (info->flags & FBINFO_READS_FAST)
+				fbcon_bmove(vc, t + count, 0, t, 0,
+					    b - t - count, vc->vc_cols);
+			else
+				goto redraw_up;
+			fbcon_clear(vc, b - count, 0, count, vc->vc_cols);
+			break;
+
+		case SCROLL_REDRAW:
+		      redraw_up:
+			fbcon_redraw(vc, p, t, b - t - count,
+				     count * vc->vc_cols);
+			fbcon_clear(vc, b - count, 0, count, vc->vc_cols);
+			scr_memsetw((unsigned short *) (vc->vc_origin +
+							vc->vc_size_row *
+							(b - count)),
+				    vc->vc_video_erase_char,
+				    vc->vc_size_row * count);
+			return true;
+		}
+		break;
 
 	case SM_DOWN:
 		if (count > vc->vc_rows)	/* Maximum realistic size */
 			count = vc->vc_rows;
-		fbcon_redraw(vc, p, b - 1, b - t - count,
-			     -count * vc->vc_cols);
-		fbcon_clear(vc, t, 0, count, vc->vc_cols);
-		scr_memsetw((unsigned short *) (vc->vc_origin +
-						vc->vc_size_row *
-						t),
-			    vc->vc_video_erase_char,
-			    vc->vc_size_row * count);
-		return true;
+		if (logo_shown >= 0)
+			goto redraw_down;
+		switch (p->scrollmode) {
+		case SCROLL_MOVE:
+			fbcon_redraw_blit(vc, info, p, b - 1, b - t - count,
+				     -count);
+			fbcon_clear(vc, t, 0, count, vc->vc_cols);
+			scr_memsetw((unsigned short *) (vc->vc_origin +
+							vc->vc_size_row *
+							t),
+				    vc->vc_video_erase_char,
+				    vc->vc_size_row * count);
+			return true;
+
+		case SCROLL_WRAP_MOVE:
+			if (b - t - count > 3 * vc->vc_rows >> 2) {
+				if (vc->vc_rows - b > 0)
+					fbcon_bmove(vc, b, 0, b - count, 0,
+						    vc->vc_rows - b,
+						    vc->vc_cols);
+				ywrap_down(vc, count);
+				if (t > 0)
+					fbcon_bmove(vc, count, 0, 0, 0, t,
+						    vc->vc_cols);
+			} else if (info->flags & FBINFO_READS_FAST)
+				fbcon_bmove(vc, t, 0, t + count, 0,
+					    b - t - count, vc->vc_cols);
+			else
+				goto redraw_down;
+			fbcon_clear(vc, t, 0, count, vc->vc_cols);
+			break;
+
+		case SCROLL_PAN_MOVE:
+			if ((count - p->yscroll <= p->vrows - vc->vc_rows)
+			    && ((!scroll_partial && (b - t == vc->vc_rows))
+				|| (scroll_partial
+				    && (b - t - count >
+					3 * vc->vc_rows >> 2)))) {
+				if (vc->vc_rows - b > 0)
+					fbcon_bmove(vc, b, 0, b - count, 0,
+						    vc->vc_rows - b,
+						    vc->vc_cols);
+				ypan_down(vc, count);
+				if (t > 0)
+					fbcon_bmove(vc, count, 0, 0, 0, t,
+						    vc->vc_cols);
+			} else if (info->flags & FBINFO_READS_FAST)
+				fbcon_bmove(vc, t, 0, t + count, 0,
+					    b - t - count, vc->vc_cols);
+			else
+				goto redraw_down;
+			fbcon_clear(vc, t, 0, count, vc->vc_cols);
+			break;
+
+		case SCROLL_PAN_REDRAW:
+			if ((count - p->yscroll <= p->vrows - vc->vc_rows)
+			    && ((!scroll_partial && (b - t == vc->vc_rows))
+				|| (scroll_partial
+				    && (b - t - count >
+					3 * vc->vc_rows >> 2)))) {
+				if (vc->vc_rows - b > 0)
+					fbcon_redraw_move(vc, p, b, vc->vc_rows - b,
+							  b - count);
+				ypan_down_redraw(vc, t, count);
+				if (t > 0)
+					fbcon_redraw_move(vc, p, count, t, 0);
+			} else
+				fbcon_redraw_move(vc, p, t, b - t - count, t + count);
+			fbcon_clear(vc, t, 0, count, vc->vc_cols);
+			break;
+
+		case SCROLL_REDRAW:
+		      redraw_down:
+			fbcon_redraw(vc, p, b - 1, b - t - count,
+				     -count * vc->vc_cols);
+			fbcon_clear(vc, t, 0, count, vc->vc_cols);
+			scr_memsetw((unsigned short *) (vc->vc_origin +
+							vc->vc_size_row *
+							t),
+				    vc->vc_video_erase_char,
+				    vc->vc_size_row * count);
+			return true;
+		}
 	}
 	return false;
 }
 
+
+static void fbcon_bmove(struct vc_data *vc, int sy, int sx, int dy, int dx,
+			int height, int width)
+{
+	struct fb_info *info = registered_fb[con2fb_map[vc->vc_num]];
+	struct fbcon_display *p = &fb_display[vc->vc_num];
+
+	if (fbcon_is_inactive(vc, info))
+		return;
+
+	if (!width || !height)
+		return;
+
+	/*  Split blits that cross physical y_wrap case.
+	 *  Pathological case involves 4 blits, better to use recursive
+	 *  code rather than unrolled case
+	 *
+	 *  Recursive invocations don't need to erase the cursor over and
+	 *  over again, so we use fbcon_bmove_rec()
+	 */
+	fbcon_bmove_rec(vc, p, sy, sx, dy, dx, height, width,
+			p->vrows - p->yscroll);
+}
+
+static void fbcon_bmove_rec(struct vc_data *vc, struct fbcon_display *p, int sy, int sx,
+			    int dy, int dx, int height, int width, u_int y_break)
+{
+	struct fb_info *info = registered_fb[con2fb_map[vc->vc_num]];
+	struct fbcon_ops *ops = info->fbcon_par;
+	u_int b;
+
+	if (sy < y_break && sy + height > y_break) {
+		b = y_break - sy;
+		if (dy < sy) {	/* Avoid trashing self */
+			fbcon_bmove_rec(vc, p, sy, sx, dy, dx, b, width,
+					y_break);
+			fbcon_bmove_rec(vc, p, sy + b, sx, dy + b, dx,
+					height - b, width, y_break);
+		} else {
+			fbcon_bmove_rec(vc, p, sy + b, sx, dy + b, dx,
+					height - b, width, y_break);
+			fbcon_bmove_rec(vc, p, sy, sx, dy, dx, b, width,
+					y_break);
+		}
+		return;
+	}
+
+	if (dy < y_break && dy + height > y_break) {
+		b = y_break - dy;
+		if (dy < sy) {	/* Avoid trashing self */
+			fbcon_bmove_rec(vc, p, sy, sx, dy, dx, b, width,
+					y_break);
+			fbcon_bmove_rec(vc, p, sy + b, sx, dy + b, dx,
+					height - b, width, y_break);
+		} else {
+			fbcon_bmove_rec(vc, p, sy + b, sx, dy + b, dx,
+					height - b, width, y_break);
+			fbcon_bmove_rec(vc, p, sy, sx, dy, dx, b, width,
+					y_break);
+		}
+		return;
+	}
+	ops->bmove(vc, info, real_y(p, sy), sx, real_y(p, dy), dx,
+		   height, width);
+}
+
 static void updatescrollmode(struct fbcon_display *p,
 					struct fb_info *info,
 					struct vc_data *vc)
@@ -1664,7 +2119,21 @@ static int fbcon_switch(struct vc_data *
 
 	updatescrollmode(p, info, vc);
 
-	scrollback_phys_max = 0;
+	switch (p->scrollmode) {
+	case SCROLL_WRAP_MOVE:
+		scrollback_phys_max = p->vrows - vc->vc_rows;
+		break;
+	case SCROLL_PAN_MOVE:
+	case SCROLL_PAN_REDRAW:
+		scrollback_phys_max = p->vrows - 2 * vc->vc_rows;
+		if (scrollback_phys_max < 0)
+			scrollback_phys_max = 0;
+		break;
+	default:
+		scrollback_phys_max = 0;
+		break;
+	}
+
 	scrollback_max = 0;
 	scrollback_current = 0;
 
--- a/drivers/video/fbdev/core/fbcon.h
+++ b/drivers/video/fbdev/core/fbcon.h
@@ -29,6 +29,7 @@ struct fbcon_display {
     /* Filled in by the low-level console driver */
     const u_char *fontdata;
     int userfont;                   /* != 0 if fontdata kmalloc()ed */
+    u_short scrollmode;             /* Scroll Method */
     u_short inverse;                /* != 0 text black on white as default */
     short yscroll;                  /* Hardware scrolling */
     int vrows;                      /* number of virtual rows */
@@ -51,6 +52,8 @@ struct fbcon_display {
 };
 
 struct fbcon_ops {
+	void (*bmove)(struct vc_data *vc, struct fb_info *info, int sy,
+		      int sx, int dy, int dx, int height, int width);
 	void (*clear)(struct vc_data *vc, struct fb_info *info, int sy,
 		      int sx, int height, int width);
 	void (*putcs)(struct vc_data *vc, struct fb_info *info,
@@ -149,6 +152,62 @@ static inline int attr_col_ec(int shift,
 #define attr_bgcol_ec(bgshift, vc, info) attr_col_ec(bgshift, vc, info, 0)
 #define attr_fgcol_ec(fgshift, vc, info) attr_col_ec(fgshift, vc, info, 1)
 
+    /*
+     *  Scroll Method
+     */
+
+/* There are several methods fbcon can use to move text around the screen:
+ *
+ *                     Operation   Pan    Wrap
+ *---------------------------------------------
+ * SCROLL_MOVE         copyarea    No     No
+ * SCROLL_PAN_MOVE     copyarea    Yes    No
+ * SCROLL_WRAP_MOVE    copyarea    No     Yes
+ * SCROLL_REDRAW       imageblit   No     No
+ * SCROLL_PAN_REDRAW   imageblit   Yes    No
+ * SCROLL_WRAP_REDRAW  imageblit   No     Yes
+ *
+ * (SCROLL_WRAP_REDRAW is not implemented yet)
+ *
+ * In general, fbcon will choose the best scrolling
+ * method based on the rule below:
+ *
+ * Pan/Wrap > accel imageblit > accel copyarea >
+ * soft imageblit > (soft copyarea)
+ *
+ * Exception to the rule: Pan + accel copyarea is
+ * preferred over Pan + accel imageblit.
+ *
+ * The above is typical for PCI/AGP cards. Unless
+ * overridden, fbcon will never use soft copyarea.
+ *
+ * If you need to override the above rule, set the
+ * appropriate flags in fb_info->flags.  For example,
+ * to prefer copyarea over imageblit, set
+ * FBINFO_READS_FAST.
+ *
+ * Other notes:
+ * + use the hardware engine to move the text
+ *    (hw-accelerated copyarea() and fillrect())
+ * + use hardware-supported panning on a large virtual screen
+ * + amifb can not only pan, but also wrap the display by N lines
+ *    (i.e. visible line i = physical line (i+N) % yres).
+ * + read what's already rendered on the screen and
+ *     write it in a different place (this is cfb_copyarea())
+ * + re-render the text to the screen
+ *
+ * Whether to use wrapping or panning can only be figured out at
+ * runtime (when we know whether our font height is a multiple
+ * of the pan/wrap step)
+ *
+ */
+
+#define SCROLL_MOVE	   0x001
+#define SCROLL_PAN_MOVE	   0x002
+#define SCROLL_WRAP_MOVE   0x003
+#define SCROLL_REDRAW	   0x004
+#define SCROLL_PAN_REDRAW  0x005
+
 #ifdef CONFIG_FB_TILEBLITTING
 extern void fbcon_set_tileops(struct vc_data *vc, struct fb_info *info);
 #endif
--- a/drivers/video/fbdev/core/fbcon_ccw.c
+++ b/drivers/video/fbdev/core/fbcon_ccw.c
@@ -59,12 +59,31 @@ static void ccw_update_attr(u8 *dst, u8
 	}
 }
 
+
+static void ccw_bmove(struct vc_data *vc, struct fb_info *info, int sy,
+		     int sx, int dy, int dx, int height, int width)
+{
+	struct fbcon_ops *ops = info->fbcon_par;
+	struct fb_copyarea area;
+	u32 vyres = GETVYRES(ops->p->scrollmode, info);
+
+	area.sx = sy * vc->vc_font.height;
+	area.sy = vyres - ((sx + width) * vc->vc_font.width);
+	area.dx = dy * vc->vc_font.height;
+	area.dy = vyres - ((dx + width) * vc->vc_font.width);
+	area.width = height * vc->vc_font.height;
+	area.height  = width * vc->vc_font.width;
+
+	info->fbops->fb_copyarea(info, &area);
+}
+
 static void ccw_clear(struct vc_data *vc, struct fb_info *info, int sy,
 		     int sx, int height, int width)
 {
+	struct fbcon_ops *ops = info->fbcon_par;
 	struct fb_fillrect region;
 	int bgshift = (vc->vc_hi_font_mask) ? 13 : 12;
-	u32 vyres = info->var.yres;
+	u32 vyres = GETVYRES(ops->p->scrollmode, info);
 
 	region.color = attr_bgcol_ec(bgshift,vc,info);
 	region.dx = sy * vc->vc_font.height;
@@ -121,7 +140,7 @@ static void ccw_putcs(struct vc_data *vc
 	u32 cnt, pitch, size;
 	u32 attribute = get_attribute(info, scr_readw(s));
 	u8 *dst, *buf = NULL;
-	u32 vyres = info->var.yres;
+	u32 vyres = GETVYRES(ops->p->scrollmode, info);
 
 	if (!ops->fontbuffer)
 		return;
@@ -210,7 +229,7 @@ static void ccw_cursor(struct vc_data *v
 	int attribute, use_sw = vc->vc_cursor_type & CUR_SW;
 	int err = 1, dx, dy;
 	char *src;
-	u32 vyres = info->var.yres;
+	u32 vyres = GETVYRES(ops->p->scrollmode, info);
 
 	if (!ops->fontbuffer)
 		return;
@@ -368,7 +387,7 @@ static int ccw_update_start(struct fb_in
 {
 	struct fbcon_ops *ops = info->fbcon_par;
 	u32 yoffset;
-	u32 vyres = info->var.yres;
+	u32 vyres = GETVYRES(ops->p->scrollmode, info);
 	int err;
 
 	yoffset = (vyres - info->var.yres) - ops->var.xoffset;
@@ -383,6 +402,7 @@ static int ccw_update_start(struct fb_in
 
 void fbcon_rotate_ccw(struct fbcon_ops *ops)
 {
+	ops->bmove = ccw_bmove;
 	ops->clear = ccw_clear;
 	ops->putcs = ccw_putcs;
 	ops->clear_margins = ccw_clear_margins;
--- a/drivers/video/fbdev/core/fbcon_cw.c
+++ b/drivers/video/fbdev/core/fbcon_cw.c
@@ -44,12 +44,31 @@ static void cw_update_attr(u8 *dst, u8 *
 	}
 }
 
+
+static void cw_bmove(struct vc_data *vc, struct fb_info *info, int sy,
+		     int sx, int dy, int dx, int height, int width)
+{
+	struct fbcon_ops *ops = info->fbcon_par;
+	struct fb_copyarea area;
+	u32 vxres = GETVXRES(ops->p->scrollmode, info);
+
+	area.sx = vxres - ((sy + height) * vc->vc_font.height);
+	area.sy = sx * vc->vc_font.width;
+	area.dx = vxres - ((dy + height) * vc->vc_font.height);
+	area.dy = dx * vc->vc_font.width;
+	area.width = height * vc->vc_font.height;
+	area.height  = width * vc->vc_font.width;
+
+	info->fbops->fb_copyarea(info, &area);
+}
+
 static void cw_clear(struct vc_data *vc, struct fb_info *info, int sy,
 		     int sx, int height, int width)
 {
+	struct fbcon_ops *ops = info->fbcon_par;
 	struct fb_fillrect region;
 	int bgshift = (vc->vc_hi_font_mask) ? 13 : 12;
-	u32 vxres = info->var.xres;
+	u32 vxres = GETVXRES(ops->p->scrollmode, info);
 
 	region.color = attr_bgcol_ec(bgshift,vc,info);
 	region.dx = vxres - ((sy + height) * vc->vc_font.height);
@@ -106,7 +125,7 @@ static void cw_putcs(struct vc_data *vc,
 	u32 cnt, pitch, size;
 	u32 attribute = get_attribute(info, scr_readw(s));
 	u8 *dst, *buf = NULL;
-	u32 vxres = info->var.xres;
+	u32 vxres = GETVXRES(ops->p->scrollmode, info);
 
 	if (!ops->fontbuffer)
 		return;
@@ -193,7 +212,7 @@ static void cw_cursor(struct vc_data *vc
 	int attribute, use_sw = vc->vc_cursor_type & CUR_SW;
 	int err = 1, dx, dy;
 	char *src;
-	u32 vxres = info->var.xres;
+	u32 vxres = GETVXRES(ops->p->scrollmode, info);
 
 	if (!ops->fontbuffer)
 		return;
@@ -350,7 +369,7 @@ static void cw_cursor(struct vc_data *vc
 static int cw_update_start(struct fb_info *info)
 {
 	struct fbcon_ops *ops = info->fbcon_par;
-	u32 vxres = info->var.xres;
+	u32 vxres = GETVXRES(ops->p->scrollmode, info);
 	u32 xoffset;
 	int err;
 
@@ -366,6 +385,7 @@ static int cw_update_start(struct fb_inf
 
 void fbcon_rotate_cw(struct fbcon_ops *ops)
 {
+	ops->bmove = cw_bmove;
 	ops->clear = cw_clear;
 	ops->putcs = cw_putcs;
 	ops->clear_margins = cw_clear_margins;
--- a/drivers/video/fbdev/core/fbcon_rotate.h
+++ b/drivers/video/fbdev/core/fbcon_rotate.h
@@ -11,6 +11,15 @@
 #ifndef _FBCON_ROTATE_H
 #define _FBCON_ROTATE_H
 
+#define GETVYRES(s,i) ({                           \
+        (s == SCROLL_REDRAW || s == SCROLL_MOVE) ? \
+        (i)->var.yres : (i)->var.yres_virtual; })
+
+#define GETVXRES(s,i) ({                           \
+        (s == SCROLL_REDRAW || s == SCROLL_MOVE || !(i)->fix.xpanstep) ? \
+        (i)->var.xres : (i)->var.xres_virtual; })
+
+
 static inline int pattern_test_bit(u32 x, u32 y, u32 pitch, const char *pat)
 {
 	u32 tmp = (y * pitch) + x, index = tmp / 8,  bit = tmp % 8;
--- a/drivers/video/fbdev/core/fbcon_ud.c
+++ b/drivers/video/fbdev/core/fbcon_ud.c
@@ -44,13 +44,33 @@ static void ud_update_attr(u8 *dst, u8 *
 	}
 }
 
+
+static void ud_bmove(struct vc_data *vc, struct fb_info *info, int sy,
+		     int sx, int dy, int dx, int height, int width)
+{
+	struct fbcon_ops *ops = info->fbcon_par;
+	struct fb_copyarea area;
+	u32 vyres = GETVYRES(ops->p->scrollmode, info);
+	u32 vxres = GETVXRES(ops->p->scrollmode, info);
+
+	area.sy = vyres - ((sy + height) * vc->vc_font.height);
+	area.sx = vxres - ((sx + width) * vc->vc_font.width);
+	area.dy = vyres - ((dy + height) * vc->vc_font.height);
+	area.dx = vxres - ((dx + width) * vc->vc_font.width);
+	area.height = height * vc->vc_font.height;
+	area.width  = width * vc->vc_font.width;
+
+	info->fbops->fb_copyarea(info, &area);
+}
+
 static void ud_clear(struct vc_data *vc, struct fb_info *info, int sy,
 		     int sx, int height, int width)
 {
+	struct fbcon_ops *ops = info->fbcon_par;
 	struct fb_fillrect region;
 	int bgshift = (vc->vc_hi_font_mask) ? 13 : 12;
-	u32 vyres = info->var.yres;
-	u32 vxres = info->var.xres;
+	u32 vyres = GETVYRES(ops->p->scrollmode, info);
+	u32 vxres = GETVXRES(ops->p->scrollmode, info);
 
 	region.color = attr_bgcol_ec(bgshift,vc,info);
 	region.dy = vyres - ((sy + height) * vc->vc_font.height);
@@ -142,8 +162,8 @@ static void ud_putcs(struct vc_data *vc,
 	u32 mod = vc->vc_font.width % 8, cnt, pitch, size;
 	u32 attribute = get_attribute(info, scr_readw(s));
 	u8 *dst, *buf = NULL;
-	u32 vyres = info->var.yres;
-	u32 vxres = info->var.xres;
+	u32 vyres = GETVYRES(ops->p->scrollmode, info);
+	u32 vxres = GETVXRES(ops->p->scrollmode, info);
 
 	if (!ops->fontbuffer)
 		return;
@@ -239,8 +259,8 @@ static void ud_cursor(struct vc_data *vc
 	int attribute, use_sw = vc->vc_cursor_type & CUR_SW;
 	int err = 1, dx, dy;
 	char *src;
-	u32 vyres = info->var.yres;
-	u32 vxres = info->var.xres;
+	u32 vyres = GETVYRES(ops->p->scrollmode, info);
+	u32 vxres = GETVXRES(ops->p->scrollmode, info);
 
 	if (!ops->fontbuffer)
 		return;
@@ -390,8 +410,8 @@ static int ud_update_start(struct fb_inf
 {
 	struct fbcon_ops *ops = info->fbcon_par;
 	int xoffset, yoffset;
-	u32 vyres = info->var.yres;
-	u32 vxres = info->var.xres;
+	u32 vyres = GETVYRES(ops->p->scrollmode, info);
+	u32 vxres = GETVXRES(ops->p->scrollmode, info);
 	int err;
 
 	xoffset = vxres - info->var.xres - ops->var.xoffset;
@@ -409,6 +429,7 @@ static int ud_update_start(struct fb_inf
 
 void fbcon_rotate_ud(struct fbcon_ops *ops)
 {
+	ops->bmove = ud_bmove;
 	ops->clear = ud_clear;
 	ops->putcs = ud_putcs;
 	ops->clear_margins = ud_clear_margins;
--- a/drivers/video/fbdev/core/tileblit.c
+++ b/drivers/video/fbdev/core/tileblit.c
@@ -16,6 +16,21 @@
 #include <asm/types.h>
 #include "fbcon.h"
 
+static void tile_bmove(struct vc_data *vc, struct fb_info *info, int sy,
+		       int sx, int dy, int dx, int height, int width)
+{
+	struct fb_tilearea area;
+
+	area.sx = sx;
+	area.sy = sy;
+	area.dx = dx;
+	area.dy = dy;
+	area.height = height;
+	area.width = width;
+
+	info->tileops->fb_tilecopy(info, &area);
+}
+
 static void tile_clear(struct vc_data *vc, struct fb_info *info, int sy,
 		       int sx, int height, int width)
 {
@@ -118,6 +133,7 @@ void fbcon_set_tileops(struct vc_data *v
 	struct fb_tilemap map;
 	struct fbcon_ops *ops = info->fbcon_par;
 
+	ops->bmove = tile_bmove;
 	ops->clear = tile_clear;
 	ops->putcs = tile_putcs;
 	ops->clear_margins = tile_clear_margins;
--- a/drivers/video/fbdev/skeletonfb.c
+++ b/drivers/video/fbdev/skeletonfb.c
@@ -505,15 +505,15 @@ void xxxfb_fillrect(struct fb_info *p, c
 }
 
 /**
- *      xxxfb_copyarea - OBSOLETE function.
+ *      xxxfb_copyarea - REQUIRED function. Can use generic routines if
+ *                       non acclerated hardware and packed pixel based.
  *                       Copies one area of the screen to another area.
- *                       Will be deleted in a future version
  *
  *      @info: frame buffer structure that represents a single frame buffer
  *      @area: Structure providing the data to copy the framebuffer contents
  *	       from one region to another.
  *
- *      This drawing operation copied a rectangular area from one area of the
+ *      This drawing operation copies a rectangular area from one area of the
  *	screen to another area.
  */
 void xxxfb_copyarea(struct fb_info *p, const struct fb_copyarea *area) 
@@ -645,9 +645,9 @@ static const struct fb_ops xxxfb_ops = {
 	.fb_setcolreg	= xxxfb_setcolreg,
 	.fb_blank	= xxxfb_blank,
 	.fb_pan_display	= xxxfb_pan_display,
-	.fb_fillrect	= xxxfb_fillrect,	/* Needed !!!   */
-	.fb_copyarea	= xxxfb_copyarea,	/* Obsolete     */
-	.fb_imageblit	= xxxfb_imageblit,	/* Needed !!!   */
+	.fb_fillrect	= xxxfb_fillrect, 	/* Needed !!! */
+	.fb_copyarea	= xxxfb_copyarea,	/* Needed !!! */
+	.fb_imageblit	= xxxfb_imageblit,	/* Needed !!! */
 	.fb_cursor	= xxxfb_cursor,		/* Optional !!! */
 	.fb_sync	= xxxfb_sync,
 	.fb_ioctl	= xxxfb_ioctl,
--- a/include/linux/fb.h
+++ b/include/linux/fb.h
@@ -262,7 +262,7 @@ struct fb_ops {
 
 	/* Draws a rectangle */
 	void (*fb_fillrect) (struct fb_info *info, const struct fb_fillrect *rect);
-	/* Copy data from area to another. Obsolete. */
+	/* Copy data from area to another */
 	void (*fb_copyarea) (struct fb_info *info, const struct fb_copyarea *region);
 	/* Draws a image to the display */
 	void (*fb_imageblit) (struct fb_info *info, const struct fb_image *image);



  parent reply	other threads:[~2022-02-07 11:46 UTC|newest]

Thread overview: 130+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2022-02-07 11:05 [PATCH 5.16 000/126] 5.16.8-rc1 review Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 001/126] drm/i915: Disable DSB usage for now Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 002/126] selinux: fix double free of cond_list on error paths Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 003/126] audit: improve audit queue handling when "audit=1" on cmdline Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 004/126] ipc/sem: do not sleep with a spin lock held Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 005/126] spi: stm32-qspi: Update spi registering Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 006/126] ASoC: hdmi-codec: Fix OOB memory accesses Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 007/126] ASoC: ops: Reject out of bounds values in snd_soc_put_volsw() Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 008/126] ASoC: ops: Reject out of bounds values in snd_soc_put_volsw_sx() Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 009/126] ASoC: ops: Reject out of bounds values in snd_soc_put_xr_sx() Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 010/126] ALSA: usb-audio: Correct quirk for VF0770 Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 011/126] ALSA: hda: Fix UAF of leds class devs at unbinding Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 012/126] ALSA: hda: realtek: Fix race at concurrent COEF updates Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 013/126] ALSA: hda/realtek: Add quirk for ASUS GU603 Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 014/126] ALSA: hda/realtek: Add missing fixup-model entry for Gigabyte X570 ALC1220 quirks Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 015/126] ALSA: hda/realtek: Fix silent output on Gigabyte X570S Aorus Master (newer chipset) Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 016/126] ALSA: hda/realtek: Fix silent output on Gigabyte X570 Aorus Xtreme after reboot from Windows Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 017/126] ata: libata-core: Introduce ATA_HORKAGE_NO_LOG_DIR horkage Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 018/126] btrfs: dont start transaction for scrub if the fs is mounted read-only Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 019/126] btrfs: fix deadlock between quota disable and qgroup rescan worker Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 020/126] btrfs: fix use-after-free after failure to create a snapshot Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 021/126] Revert "fs/9p: search open fids first" Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 022/126] drm/nouveau: fix off by one in BIOS boundary checking Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 023/126] drm/i915/adlp: Fix TypeC PHY-ready status readout Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 024/126] drm/amdgpu: fix a potential GPU hang on cyan skillfish Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 025/126] drm/amd/pm: correct the MGpuFanBoost support for Beige Goby Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 026/126] drm/amd/display: Update watermark values for DCN301 Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 027/126] drm/amd/display: watermark latencies is not enough on DCN31 Greg Kroah-Hartman
2022-02-07 11:05 ` [PATCH 5.16 028/126] drm/amd/display: Force link_rate as LINK_RATE_RBR2 for 2018 15" Apple Retina panels Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 029/126] nvme-fabrics: fix state check in nvmf_ctlr_matches_baseopts() Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 030/126] mm/debug_vm_pgtable: remove pte entry from the page table Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 031/126] mm/pgtable: define pte_index so that preprocessor could recognize it Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 032/126] mm/kmemleak: avoid scanning potential huge holes Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 033/126] block: bio-integrity: Advance seed correctly for larger interval sizes Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 034/126] cifs: fix workstation_name for multiuser mounts Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 035/126] dma-buf: heaps: Fix potential spectre v1 gadget Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 036/126] IB/hfi1: Fix panic with larger ipoib send_queue_size Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 037/126] IB/hfi1: Fix alloc failure with larger txqueuelen Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 038/126] IB/hfi1: Fix AIP early init panic Greg Kroah-Hartman
2022-02-07 11:06 ` Greg Kroah-Hartman [this message]
2022-02-07 11:06 ` [PATCH 5.16 040/126] Revert "fbcon: Disable accelerated scrolling" Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 041/126] fbcon: Add option to enable legacy hardware acceleration Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 042/126] mptcp: fix msk traversal in mptcp_nl_cmd_set_flags() Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 043/126] [PATCH] Revert "ASoC: mediatek: Check for error clk pointer" Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 044/126] RISC-V: KVM: make CY, TM, and IR counters accessible in VU mode Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 045/126] KVM: arm64: Avoid consuming a stale esr value when SError occur Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 046/126] KVM: arm64: Stop handle_exit() from handling HVC twice when an SError occurs Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 047/126] arm64: Add Cortex-A510 CPU part definition Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 048/126] RDMA/cma: Use correct address when leaving multicast group Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 049/126] RDMA/ucma: Protect mc during concurrent multicast leaves Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 050/126] RDMA/siw: Fix refcounting leak in siw_create_qp() Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 051/126] IB/rdmavt: Validate remote_addr during loopback atomic tests Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 052/126] RDMA/siw: Fix broken RDMA Read Fence/Resume logic Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 053/126] RDMA/mlx4: Dont continue event handler after memory allocation failure Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 054/126] ALSA: usb-audio: initialize variables that could ignore errors Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 055/126] ALSA: hda: Fix signedness of sscanf() arguments Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 056/126] ALSA: hda: Skip codec shutdown in case the codec is not registered Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 057/126] iommu/vt-d: Fix potential memory leak in intel_setup_irq_remapping() Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 058/126] iommu/amd: Fix loop timeout issue in iommu_ga_log_enable() Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 059/126] spi: bcm-qspi: check for valid cs before applying chip select Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 060/126] spi: mediatek: Avoid NULL pointer crash in interrupt Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 061/126] spi: meson-spicc: add IRQ check in meson_spicc_probe Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 062/126] spi: uniphier: fix reference count leak in uniphier_spi_probe() Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 063/126] IB/hfi1: Fix tstats alloc and dealloc Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 064/126] IB/cm: Release previously acquired reference counter in the cm_id_priv Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 065/126] net: ieee802154: hwsim: Ensure proper channel selection at probe time Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 066/126] net: ieee802154: mcr20a: Fix lifs/sifs periods Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 067/126] net: ieee802154: ca8210: Stop leaking skbs Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 068/126] netfilter: nft_reject_bridge: Fix for missing reply from prerouting Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 069/126] net: ieee802154: Return meaningful error codes from the netlink helpers Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 070/126] net/smc: Forward wakeup to smc socket waitqueue after fallback Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 071/126] net: stmmac: dwmac-visconti: No change to ETHER_CLOCK_SEL for unexpected speed request Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 072/126] net: stmmac: properly handle with runtime pm in stmmac_dvr_remove() Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 073/126] net: macsec: Fix offload support for NETDEV_UNREGISTER event Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 074/126] net: macsec: Verify that send_sci is on when setting Tx sci explicitly Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 075/126] net: stmmac: dump gmac4 DMA registers correctly Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 076/126] net, neigh: Do not trigger immediate probes on NUD_FAILED from neigh_managed_work Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 077/126] net: stmmac: ensure PTP time register reads are consistent Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 078/126] drm: mxsfb: Fix NULL pointer dereference Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 079/126] drm/kmb: Fix for build errors with Warray-bounds Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 080/126] drm/i915/overlay: Prevent divide by zero bugs in scaling Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 081/126] drm/i915: Lock timeline mutex directly in error path of eb_pin_timeline Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 082/126] drm/amd: avoid suspend on dGPUs w/ s2idle support when runtime PM enabled Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 083/126] ASoC: rt5682: Fix deadlock on resume Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 084/126] ASoC: fsl: Add missing error handling in pcm030_fabric_probe Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 085/126] ASoC: xilinx: xlnx_formatter_pcm: Make buffer bytes multiple of period bytes Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 086/126] ASoC: simple-card: fix probe failure on platform component Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 087/126] ASoC: cpcap: Check for NULL pointer after calling of_get_child_by_name Greg Kroah-Hartman
2022-02-07 11:06 ` [PATCH 5.16 088/126] ASoC: max9759: fix underflow in speaker_gain_control_put() Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 089/126] ASoC: codecs: wcd938x: fix incorrect used of portid Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 090/126] ASoC: codecs: lpass-rx-macro: fix sidetone register offsets Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 091/126] ASoC: codecs: wcd938x: fix return value of mixer put function Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 092/126] ASoC: qdsp6: q6apm-dai: only stop graphs that are started Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 093/126] pinctrl: sunxi: Fix H616 I2S3 pin data Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 094/126] pinctrl: intel: Fix a glitch when updating IRQ flags on a preconfigured line Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 095/126] pinctrl: intel: fix unexpected interrupt Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 096/126] pinctrl: bcm2835: Fix a few error paths Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 097/126] btrfs: fix use of uninitialized variable at rm device ioctl Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 098/126] scsi: bnx2fc: Make bnx2fc_recv_frame() mp safe Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 099/126] nfsd: nfsd4_setclientid_confirm mistakenly expires confirmed client Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 100/126] gve: fix the wrong AdminQ buffer queue index check Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 101/126] bpf: Use VM_MAP instead of VM_ALLOC for ringbuf Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 102/126] selftests/exec: Remove pipe from TEST_GEN_FILES Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 103/126] selftests: futex: Use variable MAKE instead of make Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 104/126] tools/resolve_btfids: Do not print any commands when building silently Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 105/126] e1000e: Separate ADP board type from TGP Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 106/126] rtc: cmos: Evaluate century appropriate Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 107/126] objtool: Fix truncated string warning Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 108/126] kvm/arm64: rework guest entry logic Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 109/126] perf: Copy perf_event_attr::sig_data on modification Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 110/126] perf stat: Fix display of grouped aliased events Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 111/126] perf/x86/intel/pt: Fix crash with stop filters in single-range mode Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 112/126] x86/perf: Default set FREEZE_ON_SMI for all Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 113/126] EDAC/altera: Fix deferred probing Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 114/126] EDAC/xgene: " Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 115/126] ext4: prevent used blocks from being allocated during fast commit replay Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 116/126] ext4: modify the logic of ext4_mb_new_blocks_simple Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 117/126] ext4: fix error handling in ext4_restore_inline_data() Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 118/126] ext4: fix error handling in ext4_fc_record_modified_inode() Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 119/126] ext4: fix incorrect type issue during replay_del_range Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 120/126] net: dsa: mt7530: make NET_DSA_MT7530 select MEDIATEK_GE_PHY Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 121/126] cgroup/cpuset: Fix "suspicious RCU usage" lockdep warning Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 122/126] tools include UAPI: Sync sound/asound.h copy with the kernel sources Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 123/126] gpio: idt3243x: Fix an ignored error return from platform_get_irq() Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 124/126] gpio: mpc8xxx: " Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 125/126] selftests: nft_concat_range: add test for reload with no element add/del Greg Kroah-Hartman
2022-02-07 11:07 ` [PATCH 5.16 126/126] selftests: netfilter: check stateless nat udp checksum fixup Greg Kroah-Hartman
2022-02-07 12:19 ` [PATCH 5.16 000/126] 5.16.8-rc1 review Naresh Kamboju
2022-02-07 12:22   ` Nicolas Saenz Julienne
2022-02-07 13:38     ` Greg Kroah-Hartman

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20220207103805.481274163@linuxfoundation.org \
    --to=gregkh@linuxfoundation.org \
    --cc=daniel.vetter@ffwll.ch \
    --cc=deller@gmx.de \
    --cc=geert@linux-m68k.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=stable@vger.kernel.org \
    --cc=svens@stackframe.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).