aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm/nouveau/nouveau_bios.c
diff options
context:
space:
mode:
authorBenjamin Herrenschmidt <benh@kernel.crashing.org>2012-04-01 23:38:19 -0400
committerDave Airlie <airlied@redhat.com>2012-04-02 06:06:33 -0400
commitd06221c0617ab6d0bc41c4980cefdd9c8cc9a1c1 (patch)
tree5ec7d22876848e194036c019aaea9f6a14e63c2a /drivers/gpu/drm/nouveau/nouveau_bios.c
parentea71f98d680c9ac768a7849d26d7ce4744064510 (diff)
nouveau/bios: Fix tracking of BIOS image data
The code tries various methods for retreiving the BIOS data. However it doesn't clear the bios->data pointer between the iterations. In some cases, the shadow() method will fail and not update bios->data at all, which will cause us to "score" the old data and incorrectly attribute that score to the new method. This can cause double frees later when disposing of the unused data. Additionally, we were not freeing the data for methods that fail the score test (we only freed when a "best" is superseeded, not when the new method has a lower score than the exising "best"). Fix that as well. Signed-off-by: Benjamin Herrenschmidt <benh@kernel.crashing.org> Acked-by: Ben Skeggs <bskeggs@redhat.com> Signed-off-by: Dave Airlie <airlied@redhat.com>
Diffstat (limited to 'drivers/gpu/drm/nouveau/nouveau_bios.c')
-rw-r--r--drivers/gpu/drm/nouveau/nouveau_bios.c4
1 files changed, 3 insertions, 1 deletions
diff --git a/drivers/gpu/drm/nouveau/nouveau_bios.c b/drivers/gpu/drm/nouveau/nouveau_bios.c
index 80963d05b54a..1947d6139a38 100644
--- a/drivers/gpu/drm/nouveau/nouveau_bios.c
+++ b/drivers/gpu/drm/nouveau/nouveau_bios.c
@@ -273,6 +273,7 @@ bios_shadow(struct drm_device *dev)
273 mthd->score = score_vbios(bios, mthd->rw); 273 mthd->score = score_vbios(bios, mthd->rw);
274 mthd->size = bios->length; 274 mthd->size = bios->length;
275 mthd->data = bios->data; 275 mthd->data = bios->data;
276 bios->data = NULL;
276 } while (mthd->score != 3 && (++mthd)->shadow); 277 } while (mthd->score != 3 && (++mthd)->shadow);
277 278
278 mthd = shadow_methods; 279 mthd = shadow_methods;
@@ -281,7 +282,8 @@ bios_shadow(struct drm_device *dev)
281 if (mthd->score > best->score) { 282 if (mthd->score > best->score) {
282 kfree(best->data); 283 kfree(best->data);
283 best = mthd; 284 best = mthd;
284 } 285 } else
286 kfree(mthd->data);
285 } while ((++mthd)->shadow); 287 } while ((++mthd)->shadow);
286 288
287 if (best->score) { 289 if (best->score) {