Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 162b3a08 authored by Haavard Skinnemoen's avatar Haavard Skinnemoen Committed by Linus Torvalds
Browse files

atmel_lcdfb: validate display timings



Setting a display timing parameter too high or too low may cause it to
wrap around and thus become completely wrong. Validate the timings in
atmel_lcdfb_check_var() and saturate to the highest or lowest possible
value if necessary.

Signed-off-by: default avatarHaavard Skinnemoen <hskinnemoen@atmel.com>
Cc: "Antonino A. Daplas" <adaplas@pol.net>
Signed-off-by: default avatarAndrew Morton <akpm@linux-foundation.org>
Signed-off-by: default avatarLinus Torvalds <torvalds@linux-foundation.org>
parent 529e55b6
Loading
Loading
Loading
Loading
+20 −0
Original line number Diff line number Diff line
@@ -203,6 +203,26 @@ static int atmel_lcdfb_check_var(struct fb_var_screeninfo *var,
	var->transp.offset = var->transp.length = 0;
	var->xoffset = var->yoffset = 0;

	/* Saturate vertical and horizontal timings at maximum values */
	var->vsync_len = min_t(u32, var->vsync_len,
			(ATMEL_LCDC_VPW >> ATMEL_LCDC_VPW_OFFSET) + 1);
	var->upper_margin = min_t(u32, var->upper_margin,
			ATMEL_LCDC_VBP >> ATMEL_LCDC_VBP_OFFSET);
	var->lower_margin = min_t(u32, var->lower_margin,
			ATMEL_LCDC_VFP);
	var->right_margin = min_t(u32, var->right_margin,
			(ATMEL_LCDC_HFP >> ATMEL_LCDC_HFP_OFFSET) + 1);
	var->hsync_len = min_t(u32, var->hsync_len,
			(ATMEL_LCDC_HPW >> ATMEL_LCDC_HPW_OFFSET) + 1);
	var->left_margin = min_t(u32, var->left_margin,
			ATMEL_LCDC_HBP + 1);

	/* Some parameters can't be zero */
	var->vsync_len = max_t(u32, var->vsync_len, 1);
	var->right_margin = max_t(u32, var->right_margin, 1);
	var->hsync_len = max_t(u32, var->hsync_len, 1);
	var->left_margin = max_t(u32, var->left_margin, 1);

	switch (var->bits_per_pixel) {
	case 1:
	case 2:
+7 −7
Original line number Diff line number Diff line
@@ -115,20 +115,20 @@ struct atmel_lcdfb_info {
#define		ATMEL_LCDC_MEMOR_LITTLE		(1 << 31)

#define ATMEL_LCDC_TIM1		0x0808
#define	ATMEL_LCDC_VFP		(0xff <<  0)
#define	ATMEL_LCDC_VFP		(0xffU <<  0)
#define	ATMEL_LCDC_VBP_OFFSET		8
#define	ATMEL_LCDC_VBP		(0xff <<  ATMEL_LCDC_VBP_OFFSET)
#define	ATMEL_LCDC_VBP		(0xffU <<  ATMEL_LCDC_VBP_OFFSET)
#define	ATMEL_LCDC_VPW_OFFSET		16
#define	ATMEL_LCDC_VPW		(0x3f << ATMEL_LCDC_VPW_OFFSET)
#define	ATMEL_LCDC_VPW		(0x3fU << ATMEL_LCDC_VPW_OFFSET)
#define	ATMEL_LCDC_VHDLY_OFFSET		24
#define	ATMEL_LCDC_VHDLY	(0xf  << ATMEL_LCDC_VHDLY_OFFSET)
#define	ATMEL_LCDC_VHDLY	(0xfU  << ATMEL_LCDC_VHDLY_OFFSET)

#define ATMEL_LCDC_TIM2		0x080c
#define	ATMEL_LCDC_HBP		(0xff  <<  0)
#define	ATMEL_LCDC_HBP		(0xffU  <<  0)
#define	ATMEL_LCDC_HPW_OFFSET		8
#define	ATMEL_LCDC_HPW		(0x3f  <<  ATMEL_LCDC_HPW_OFFSET)
#define	ATMEL_LCDC_HPW		(0x3fU  <<  ATMEL_LCDC_HPW_OFFSET)
#define	ATMEL_LCDC_HFP_OFFSET		21
#define	ATMEL_LCDC_HFP		(0x7ff << ATMEL_LCDC_HFP_OFFSET)
#define	ATMEL_LCDC_HFP		(0x7ffU << ATMEL_LCDC_HFP_OFFSET)

#define ATMEL_LCDC_LCDFRMCFG	0x0810
#define	ATMEL_LCDC_LINEVAL	(0x7ff <<  0)