From a8f81837c506aba186b42f0c67633e85851395b1 Mon Sep 17 00:00:00 2001 From: Ben Skeggs Date: Fri, 20 Apr 2012 11:01:46 +1000 Subject: [PATCH] drm/nv50/disp: fixup error paths in crtc object creation Reported-by: Marcin Slusarz Signed-off-by: Ben Skeggs --- drivers/gpu/drm/nouveau/nv50_crtc.c | 52 +++++++++++--------------- drivers/gpu/drm/nouveau/nv50_display.c | 7 +++- 2 files changed, 26 insertions(+), 33 deletions(-) diff --git a/drivers/gpu/drm/nouveau/nv50_crtc.c b/drivers/gpu/drm/nouveau/nv50_crtc.c index 7eb3aa3b099e..97a477b3d52d 100644 --- a/drivers/gpu/drm/nouveau/nv50_crtc.c +++ b/drivers/gpu/drm/nouveau/nv50_crtc.c @@ -383,23 +383,15 @@ nv50_crtc_set_clock(struct drm_device *dev, int head, int pclk) static void nv50_crtc_destroy(struct drm_crtc *crtc) { - struct drm_device *dev; - struct nouveau_crtc *nv_crtc; - - if (!crtc) - return; - - dev = crtc->dev; - nv_crtc = nouveau_crtc(crtc); - - NV_DEBUG_KMS(dev, "\n"); + struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc); - drm_crtc_cleanup(&nv_crtc->base); + NV_DEBUG_KMS(crtc->dev, "\n"); nouveau_bo_unmap(nv_crtc->lut.nvbo); nouveau_bo_ref(NULL, &nv_crtc->lut.nvbo); nouveau_bo_unmap(nv_crtc->cursor.nvbo); nouveau_bo_ref(NULL, &nv_crtc->cursor.nvbo); + drm_crtc_cleanup(&nv_crtc->base); kfree(nv_crtc); } @@ -755,18 +747,22 @@ nv50_crtc_create(struct drm_device *dev, int index) if (!nv_crtc) return -ENOMEM; + nv_crtc->index = index; + nv_crtc->set_dither = nv50_crtc_set_dither; + nv_crtc->set_scale = nv50_crtc_set_scale; + nv_crtc->set_color_vibrance = nv50_crtc_set_color_vibrance; nv_crtc->color_vibrance = 50; nv_crtc->vibrant_hue = 0; - - /* Default CLUT parameters, will be activated on the hw upon - * first mode set. - */ + nv_crtc->lut.depth = 0; for (i = 0; i < 256; i++) { nv_crtc->lut.r[i] = i << 8; nv_crtc->lut.g[i] = i << 8; nv_crtc->lut.b[i] = i << 8; } - nv_crtc->lut.depth = 0; + + drm_crtc_init(dev, &nv_crtc->base, &nv50_crtc_funcs); + drm_crtc_helper_add(&nv_crtc->base, &nv50_crtc_helper_funcs); + drm_mode_crtc_set_gamma_size(&nv_crtc->base, 256); ret = nouveau_bo_new(dev, 4096, 0x100, TTM_PL_FLAG_VRAM, 0, 0x0000, NULL, &nv_crtc->lut.nvbo); @@ -778,21 +774,9 @@ nv50_crtc_create(struct drm_device *dev, int index) nouveau_bo_ref(NULL, &nv_crtc->lut.nvbo); } - if (ret) { - kfree(nv_crtc); - return ret; - } - - nv_crtc->index = index; + if (ret) + goto out; - /* set function pointers */ - nv_crtc->set_dither = nv50_crtc_set_dither; - nv_crtc->set_scale = nv50_crtc_set_scale; - nv_crtc->set_color_vibrance = nv50_crtc_set_color_vibrance; - - drm_crtc_init(dev, &nv_crtc->base, &nv50_crtc_funcs); - drm_crtc_helper_add(&nv_crtc->base, &nv50_crtc_helper_funcs); - drm_mode_crtc_set_gamma_size(&nv_crtc->base, 256); ret = nouveau_bo_new(dev, 64*64*4, 0x100, TTM_PL_FLAG_VRAM, 0, 0x0000, NULL, &nv_crtc->cursor.nvbo); @@ -804,6 +788,12 @@ nv50_crtc_create(struct drm_device *dev, int index) nouveau_bo_ref(NULL, &nv_crtc->cursor.nvbo); } + if (ret) + goto out; + nv50_cursor_init(nv_crtc); - return 0; +out: + if (ret) + nv50_crtc_destroy(&nv_crtc->base); + return ret; } diff --git a/drivers/gpu/drm/nouveau/nv50_display.c b/drivers/gpu/drm/nouveau/nv50_display.c index 211e5e9565ce..b526e3f61c17 100644 --- a/drivers/gpu/drm/nouveau/nv50_display.c +++ b/drivers/gpu/drm/nouveau/nv50_display.c @@ -358,8 +358,11 @@ nv50_display_create(struct drm_device *dev) dev_priv->engine.display.priv = priv; /* Create CRTC objects */ - for (i = 0; i < 2; i++) - nv50_crtc_create(dev, i); + for (i = 0; i < 2; i++) { + ret = nv50_crtc_create(dev, i); + if (ret) + return ret; + } /* We setup the encoders from the BIOS table */ for (i = 0 ; i < dcb->entries; i++) { -- 2.20.1