diff mbox series

[v2,2/2] tty/vt: Avoid passing struct console_font_op to con_font_copy()

Message ID 72c954371ed9b1d050901b2d498a979017de8a3c.1604306433.git.yepeilin.cs@gmail.com (mailing list archive)
State Superseded, archived
Headers show
Series [v2,1/2] console: Remove dummy con_font_op() callback implementations | expand

Commit Message

Peilin Ye Nov. 2, 2020, 9:37 a.m. UTC
con_font_op() is passing an entire `struct console_font_op *` to
con_font_copy(), but con_font_copy() only uses `op->height`. Additionally,
con_font_copy() is silently assigning the unsigned `op->height` to the
signed `con`, then pass it to fbcon_copy_font().

Let con_font_copy() and fbcon_copy_font() pass an unsigned int directly.
Also, add a comment in con_font_op() for less confusion, since ideally
`op->height` should not be used as a console index, as the field name
suggests.

This patch depends on patch "console: Remove dummy con_font_op() callback
implementations".

Suggested-by: Daniel Vetter <daniel@ffwll.ch>
Signed-off-by: Peilin Ye <yepeilin.cs@gmail.com>
---
con_font_set(), con_font_get() and con_font_default() also pass an entire
`console_font_op`.

con_font_get() and con_font_default() actually update the structure (later
copied to userspace), so let them be.

con_font_set() does not update the structure, but it uses all fields of it
except `op`. Avoiding passing `console_font_op` to con_font_set() will
thus make its signature pretty long (6 parameters).

Changes in v2:
  - Remove redundant `con < 0` check in con_font_copy() (kernel test robot
    <lkp@intel.com>)
  - Remove unnecessary range check in fbcon_copy_font(). con_font_copy()
    calls vc_cons_allocated(), which does the check
  - Do not Cc: stable
  - Rewrite the title and commit message accordingly

 drivers/tty/vt/vt.c              | 8 ++++----
 drivers/video/fbdev/core/fbcon.c | 2 +-
 include/linux/console.h          | 2 +-
 3 files changed, 6 insertions(+), 6 deletions(-)

Comments

Daniel Vetter Nov. 2, 2020, 10:10 a.m. UTC | #1
On Mon, Nov 02, 2020 at 04:37:55AM -0500, Peilin Ye wrote:
> con_font_op() is passing an entire `struct console_font_op *` to
> con_font_copy(), but con_font_copy() only uses `op->height`. Additionally,
> con_font_copy() is silently assigning the unsigned `op->height` to the
> signed `con`, then pass it to fbcon_copy_font().
> 
> Let con_font_copy() and fbcon_copy_font() pass an unsigned int directly.
> Also, add a comment in con_font_op() for less confusion, since ideally
> `op->height` should not be used as a console index, as the field name
> suggests.
> 
> This patch depends on patch "console: Remove dummy con_font_op() callback
> implementations".
> 
> Suggested-by: Daniel Vetter <daniel@ffwll.ch>
> Signed-off-by: Peilin Ye <yepeilin.cs@gmail.com>
> ---
> con_font_set(), con_font_get() and con_font_default() also pass an entire
> `console_font_op`.
> 
> con_font_get() and con_font_default() actually update the structure (later
> copied to userspace), so let them be.
> 
> con_font_set() does not update the structure, but it uses all fields of it
> except `op`. Avoiding passing `console_font_op` to con_font_set() will
> thus make its signature pretty long (6 parameters).
> 
> Changes in v2:
>   - Remove redundant `con < 0` check in con_font_copy() (kernel test robot
>     <lkp@intel.com>)
>   - Remove unnecessary range check in fbcon_copy_font(). con_font_copy()
>     calls vc_cons_allocated(), which does the check
>   - Do not Cc: stable
>   - Rewrite the title and commit message accordingly
> 
>  drivers/tty/vt/vt.c              | 8 ++++----
>  drivers/video/fbdev/core/fbcon.c | 2 +-
>  include/linux/console.h          | 2 +-
>  3 files changed, 6 insertions(+), 6 deletions(-)

I'm not sure switching from int to unsigned just here makes much sense.
All the console code is still using int con to index all the various
arrays (I just checked fbcon.c code), and using int to index arrays is
pretty standard. As long as we have the con < 0 check to catch evil
userspace.

There's still the switch from op to int for con_font_copy, but I think
that's better done as part of the larger cleanup we already discussed. And
then maybe also include patch 1 from this series in that rework.
-Daniel

> 
> diff --git a/drivers/tty/vt/vt.c b/drivers/tty/vt/vt.c
> index 9506a76f3ab6..27821ef97b13 100644
> --- a/drivers/tty/vt/vt.c
> +++ b/drivers/tty/vt/vt.c
> @@ -4704,9 +4704,8 @@ static int con_font_default(struct vc_data *vc, struct console_font_op *op)
>  	return rc;
>  }
>  
> -static int con_font_copy(struct vc_data *vc, struct console_font_op *op)
> +static int con_font_copy(struct vc_data *vc, unsigned int con)
>  {
> -	int con = op->height;
>  	int rc;
>  
>  
> @@ -4715,7 +4714,7 @@ static int con_font_copy(struct vc_data *vc, struct console_font_op *op)
>  		rc = -EINVAL;
>  	else if (!vc->vc_sw->con_font_copy)
>  		rc = -ENOSYS;
> -	else if (con < 0 || !vc_cons_allocated(con))
> +	else if (!vc_cons_allocated(con))
>  		rc = -ENOTTY;
>  	else if (con == vc->vc_num)	/* nothing to do */
>  		rc = 0;
> @@ -4735,7 +4734,8 @@ int con_font_op(struct vc_data *vc, struct console_font_op *op)
>  	case KD_FONT_OP_SET_DEFAULT:
>  		return con_font_default(vc, op);
>  	case KD_FONT_OP_COPY:
> -		return con_font_copy(vc, op);
> +		/* uses op->height as a console index */
> +		return con_font_copy(vc, op->height);
>  	}
>  	return -ENOSYS;
>  }
> diff --git a/drivers/video/fbdev/core/fbcon.c b/drivers/video/fbdev/core/fbcon.c
> index cef437817b0d..cb5b5705ea71 100644
> --- a/drivers/video/fbdev/core/fbcon.c
> +++ b/drivers/video/fbdev/core/fbcon.c
> @@ -2451,7 +2451,7 @@ static int fbcon_do_set_font(struct vc_data *vc, int w, int h,
>  	return 0;
>  }
>  
> -static int fbcon_copy_font(struct vc_data *vc, int con)
> +static int fbcon_copy_font(struct vc_data *vc, unsigned int con)
>  {
>  	struct fbcon_display *od = &fb_display[con];
>  	struct console_font *f = &vc->vc_font;
> diff --git a/include/linux/console.h b/include/linux/console.h
> index 4b1e26c4cb42..34855d3f2afd 100644
> --- a/include/linux/console.h
> +++ b/include/linux/console.h
> @@ -62,7 +62,7 @@ struct consw {
>  	int	(*con_font_get)(struct vc_data *vc, struct console_font *font);
>  	int	(*con_font_default)(struct vc_data *vc,
>  			struct console_font *font, char *name);
> -	int	(*con_font_copy)(struct vc_data *vc, int con);
> +	int	(*con_font_copy)(struct vc_data *vc, unsigned int con);
>  	int     (*con_resize)(struct vc_data *vc, unsigned int width,
>  			unsigned int height, unsigned int user);
>  	void	(*con_set_palette)(struct vc_data *vc,
> -- 
> 2.25.1
>
Peilin Ye Nov. 2, 2020, 11:12 a.m. UTC | #2
On Mon, Nov 02, 2020 at 11:10:44AM +0100, Daniel Vetter wrote:
> I'm not sure switching from int to unsigned just here makes much sense.
> All the console code is still using int con to index all the various
> arrays (I just checked fbcon.c code), and using int to index arrays is
> pretty standard. As long as we have the con < 0 check to catch evil
> userspace.
> 
> There's still the switch from op to int for con_font_copy, but I think
> that's better done as part of the larger cleanup we already discussed. And
> then maybe also include patch 1 from this series in that rework.

I see. I think at the moment there's not much we can do for
con_font_get/set/default(). _get() and _default() use *op, and _set()
uses all except one field of *op. Maybe we can change the type of *op
from console_font_op to font_desc, after cleaning up everything else?

Peilin
Daniel Vetter Nov. 2, 2020, 11:30 a.m. UTC | #3
On Mon, Nov 2, 2020 at 12:12 PM Peilin Ye <yepeilin.cs@gmail.com> wrote:
>
> On Mon, Nov 02, 2020 at 11:10:44AM +0100, Daniel Vetter wrote:
> > I'm not sure switching from int to unsigned just here makes much sense.
> > All the console code is still using int con to index all the various
> > arrays (I just checked fbcon.c code), and using int to index arrays is
> > pretty standard. As long as we have the con < 0 check to catch evil
> > userspace.
> >
> > There's still the switch from op to int for con_font_copy, but I think
> > that's better done as part of the larger cleanup we already discussed. And
> > then maybe also include patch 1 from this series in that rework.
>
> I see. I think at the moment there's not much we can do for
> con_font_get/set/default(). _get() and _default() use *op, and _set()
> uses all except one field of *op. Maybe we can change the type of *op
> from console_font_op to font_desc, after cleaning up everything else?

Yeah, for these one of the arguments should be the new font_desc, so
that we can remove the op stuff properly. Opening up all the arguments
without the font_desc doesn't make sense imo.
-Daniel
diff mbox series

Patch

diff --git a/drivers/tty/vt/vt.c b/drivers/tty/vt/vt.c
index 9506a76f3ab6..27821ef97b13 100644
--- a/drivers/tty/vt/vt.c
+++ b/drivers/tty/vt/vt.c
@@ -4704,9 +4704,8 @@  static int con_font_default(struct vc_data *vc, struct console_font_op *op)
 	return rc;
 }
 
-static int con_font_copy(struct vc_data *vc, struct console_font_op *op)
+static int con_font_copy(struct vc_data *vc, unsigned int con)
 {
-	int con = op->height;
 	int rc;
 
 
@@ -4715,7 +4714,7 @@  static int con_font_copy(struct vc_data *vc, struct console_font_op *op)
 		rc = -EINVAL;
 	else if (!vc->vc_sw->con_font_copy)
 		rc = -ENOSYS;
-	else if (con < 0 || !vc_cons_allocated(con))
+	else if (!vc_cons_allocated(con))
 		rc = -ENOTTY;
 	else if (con == vc->vc_num)	/* nothing to do */
 		rc = 0;
@@ -4735,7 +4734,8 @@  int con_font_op(struct vc_data *vc, struct console_font_op *op)
 	case KD_FONT_OP_SET_DEFAULT:
 		return con_font_default(vc, op);
 	case KD_FONT_OP_COPY:
-		return con_font_copy(vc, op);
+		/* uses op->height as a console index */
+		return con_font_copy(vc, op->height);
 	}
 	return -ENOSYS;
 }
diff --git a/drivers/video/fbdev/core/fbcon.c b/drivers/video/fbdev/core/fbcon.c
index cef437817b0d..cb5b5705ea71 100644
--- a/drivers/video/fbdev/core/fbcon.c
+++ b/drivers/video/fbdev/core/fbcon.c
@@ -2451,7 +2451,7 @@  static int fbcon_do_set_font(struct vc_data *vc, int w, int h,
 	return 0;
 }
 
-static int fbcon_copy_font(struct vc_data *vc, int con)
+static int fbcon_copy_font(struct vc_data *vc, unsigned int con)
 {
 	struct fbcon_display *od = &fb_display[con];
 	struct console_font *f = &vc->vc_font;
diff --git a/include/linux/console.h b/include/linux/console.h
index 4b1e26c4cb42..34855d3f2afd 100644
--- a/include/linux/console.h
+++ b/include/linux/console.h
@@ -62,7 +62,7 @@  struct consw {
 	int	(*con_font_get)(struct vc_data *vc, struct console_font *font);
 	int	(*con_font_default)(struct vc_data *vc,
 			struct console_font *font, char *name);
-	int	(*con_font_copy)(struct vc_data *vc, int con);
+	int	(*con_font_copy)(struct vc_data *vc, unsigned int con);
 	int     (*con_resize)(struct vc_data *vc, unsigned int width,
 			unsigned int height, unsigned int user);
 	void	(*con_set_palette)(struct vc_data *vc,