aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBen Skeggs <bskeggs@redhat.com>2016-06-01 22:23:31 -0400
committerBen Skeggs <bskeggs@redhat.com>2016-06-01 23:53:44 -0400
commitf045f459d925138fe7d6193a8c86406bda7e49da (patch)
treef00acbaf667b587b9e0cbdcb00d16826cbc12429
parent383d0a419f8e63e3d65e706c3c515fa9505ce364 (diff)
drm/nouveau/fbcon: fix out-of-bounds memory accesses
Reported by KASAN. Signed-off-by: Ben Skeggs <bskeggs@redhat.com> Cc: stable@vger.kernel.org
-rw-r--r--drivers/gpu/drm/nouveau/nouveau_fbcon.c1
-rw-r--r--drivers/gpu/drm/nouveau/nv04_fbcon.c7
-rw-r--r--drivers/gpu/drm/nouveau/nv50_fbcon.c6
-rw-r--r--drivers/gpu/drm/nouveau/nvc0_fbcon.c6
4 files changed, 7 insertions, 13 deletions
diff --git a/drivers/gpu/drm/nouveau/nouveau_fbcon.c b/drivers/gpu/drm/nouveau/nouveau_fbcon.c
index 57aaf98a26f9..300ea03be8f0 100644
--- a/drivers/gpu/drm/nouveau/nouveau_fbcon.c
+++ b/drivers/gpu/drm/nouveau/nouveau_fbcon.c
@@ -552,6 +552,7 @@ nouveau_fbcon_init(struct drm_device *dev)
552 if (ret) 552 if (ret)
553 goto fini; 553 goto fini;
554 554
555 fbcon->helper.fbdev->pixmap.buf_align = 4;
555 return 0; 556 return 0;
556 557
557fini: 558fini:
diff --git a/drivers/gpu/drm/nouveau/nv04_fbcon.c b/drivers/gpu/drm/nouveau/nv04_fbcon.c
index 0f3e4bb411cc..7d9248b8c664 100644
--- a/drivers/gpu/drm/nouveau/nv04_fbcon.c
+++ b/drivers/gpu/drm/nouveau/nv04_fbcon.c
@@ -82,7 +82,6 @@ nv04_fbcon_imageblit(struct fb_info *info, const struct fb_image *image)
82 uint32_t fg; 82 uint32_t fg;
83 uint32_t bg; 83 uint32_t bg;
84 uint32_t dsize; 84 uint32_t dsize;
85 uint32_t width;
86 uint32_t *data = (uint32_t *)image->data; 85 uint32_t *data = (uint32_t *)image->data;
87 int ret; 86 int ret;
88 87
@@ -93,9 +92,6 @@ nv04_fbcon_imageblit(struct fb_info *info, const struct fb_image *image)
93 if (ret) 92 if (ret)
94 return ret; 93 return ret;
95 94
96 width = ALIGN(image->width, 8);
97 dsize = ALIGN(width * image->height, 32) >> 5;
98
99 if (info->fix.visual == FB_VISUAL_TRUECOLOR || 95 if (info->fix.visual == FB_VISUAL_TRUECOLOR ||
100 info->fix.visual == FB_VISUAL_DIRECTCOLOR) { 96 info->fix.visual == FB_VISUAL_DIRECTCOLOR) {
101 fg = ((uint32_t *) info->pseudo_palette)[image->fg_color]; 97 fg = ((uint32_t *) info->pseudo_palette)[image->fg_color];
@@ -111,10 +107,11 @@ nv04_fbcon_imageblit(struct fb_info *info, const struct fb_image *image)
111 ((image->dx + image->width) & 0xffff)); 107 ((image->dx + image->width) & 0xffff));
112 OUT_RING(chan, bg); 108 OUT_RING(chan, bg);
113 OUT_RING(chan, fg); 109 OUT_RING(chan, fg);
114 OUT_RING(chan, (image->height << 16) | width); 110 OUT_RING(chan, (image->height << 16) | image->width);
115 OUT_RING(chan, (image->height << 16) | image->width); 111 OUT_RING(chan, (image->height << 16) | image->width);
116 OUT_RING(chan, (image->dy << 16) | (image->dx & 0xffff)); 112 OUT_RING(chan, (image->dy << 16) | (image->dx & 0xffff));
117 113
114 dsize = ALIGN(image->width * image->height, 32) >> 5;
118 while (dsize) { 115 while (dsize) {
119 int iter_len = dsize > 128 ? 128 : dsize; 116 int iter_len = dsize > 128 ? 128 : dsize;
120 117
diff --git a/drivers/gpu/drm/nouveau/nv50_fbcon.c b/drivers/gpu/drm/nouveau/nv50_fbcon.c
index 33d9ee0fac40..1aeb698e9707 100644
--- a/drivers/gpu/drm/nouveau/nv50_fbcon.c
+++ b/drivers/gpu/drm/nouveau/nv50_fbcon.c
@@ -95,7 +95,7 @@ nv50_fbcon_imageblit(struct fb_info *info, const struct fb_image *image)
95 struct nouveau_fbdev *nfbdev = info->par; 95 struct nouveau_fbdev *nfbdev = info->par;
96 struct nouveau_drm *drm = nouveau_drm(nfbdev->dev); 96 struct nouveau_drm *drm = nouveau_drm(nfbdev->dev);
97 struct nouveau_channel *chan = drm->channel; 97 struct nouveau_channel *chan = drm->channel;
98 uint32_t width, dwords, *data = (uint32_t *)image->data; 98 uint32_t dwords, *data = (uint32_t *)image->data;
99 uint32_t mask = ~(~0 >> (32 - info->var.bits_per_pixel)); 99 uint32_t mask = ~(~0 >> (32 - info->var.bits_per_pixel));
100 uint32_t *palette = info->pseudo_palette; 100 uint32_t *palette = info->pseudo_palette;
101 int ret; 101 int ret;
@@ -107,9 +107,6 @@ nv50_fbcon_imageblit(struct fb_info *info, const struct fb_image *image)
107 if (ret) 107 if (ret)
108 return ret; 108 return ret;
109 109
110 width = ALIGN(image->width, 32);
111 dwords = (width * image->height) >> 5;
112
113 BEGIN_NV04(chan, NvSub2D, 0x0814, 2); 110 BEGIN_NV04(chan, NvSub2D, 0x0814, 2);
114 if (info->fix.visual == FB_VISUAL_TRUECOLOR || 111 if (info->fix.visual == FB_VISUAL_TRUECOLOR ||
115 info->fix.visual == FB_VISUAL_DIRECTCOLOR) { 112 info->fix.visual == FB_VISUAL_DIRECTCOLOR) {
@@ -128,6 +125,7 @@ nv50_fbcon_imageblit(struct fb_info *info, const struct fb_image *image)
128 OUT_RING(chan, 0); 125 OUT_RING(chan, 0);
129 OUT_RING(chan, image->dy); 126 OUT_RING(chan, image->dy);
130 127
128 dwords = ALIGN(image->width * image->height, 32) >> 5;
131 while (dwords) { 129 while (dwords) {
132 int push = dwords > 2047 ? 2047 : dwords; 130 int push = dwords > 2047 ? 2047 : dwords;
133 131
diff --git a/drivers/gpu/drm/nouveau/nvc0_fbcon.c b/drivers/gpu/drm/nouveau/nvc0_fbcon.c
index a0913359ac05..839f4c8c1805 100644
--- a/drivers/gpu/drm/nouveau/nvc0_fbcon.c
+++ b/drivers/gpu/drm/nouveau/nvc0_fbcon.c
@@ -95,7 +95,7 @@ nvc0_fbcon_imageblit(struct fb_info *info, const struct fb_image *image)
95 struct nouveau_fbdev *nfbdev = info->par; 95 struct nouveau_fbdev *nfbdev = info->par;
96 struct nouveau_drm *drm = nouveau_drm(nfbdev->dev); 96 struct nouveau_drm *drm = nouveau_drm(nfbdev->dev);
97 struct nouveau_channel *chan = drm->channel; 97 struct nouveau_channel *chan = drm->channel;
98 uint32_t width, dwords, *data = (uint32_t *)image->data; 98 uint32_t dwords, *data = (uint32_t *)image->data;
99 uint32_t mask = ~(~0 >> (32 - info->var.bits_per_pixel)); 99 uint32_t mask = ~(~0 >> (32 - info->var.bits_per_pixel));
100 uint32_t *palette = info->pseudo_palette; 100 uint32_t *palette = info->pseudo_palette;
101 int ret; 101 int ret;
@@ -107,9 +107,6 @@ nvc0_fbcon_imageblit(struct fb_info *info, const struct fb_image *image)
107 if (ret) 107 if (ret)
108 return ret; 108 return ret;
109 109
110 width = ALIGN(image->width, 32);
111 dwords = (width * image->height) >> 5;
112
113 BEGIN_NVC0(chan, NvSub2D, 0x0814, 2); 110 BEGIN_NVC0(chan, NvSub2D, 0x0814, 2);
114 if (info->fix.visual == FB_VISUAL_TRUECOLOR || 111 if (info->fix.visual == FB_VISUAL_TRUECOLOR ||
115 info->fix.visual == FB_VISUAL_DIRECTCOLOR) { 112 info->fix.visual == FB_VISUAL_DIRECTCOLOR) {
@@ -128,6 +125,7 @@ nvc0_fbcon_imageblit(struct fb_info *info, const struct fb_image *image)
128 OUT_RING (chan, 0); 125 OUT_RING (chan, 0);
129 OUT_RING (chan, image->dy); 126 OUT_RING (chan, image->dy);
130 127
128 dwords = ALIGN(image->width * image->height, 32) >> 5;
131 while (dwords) { 129 while (dwords) {
132 int push = dwords > 2047 ? 2047 : dwords; 130 int push = dwords > 2047 ? 2047 : dwords;
133 131