[PATCH] [glx] Use goto-style error handling in __glXDRIscreenProbe()
Ian Romanick
idr at freedesktop.org
Thu Dec 17 10:45:52 PST 2009
-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1
Tomas Carnecky wrote:
> This fixes a 'Result of operation is garbage or undefined' bug found
> by clang. 'framebuffer.base' was read before being initialized.
If the problem is that framebuffer.base is not initialized, I think it
would be better to just initialize it to NULL at the top. Having
multiple goto labels opens the possibility for someone to add / modify
code and use the wrong one.
> Signed-off-by: Tomas Carnecky <tom at dbservice.com>
> ---
>
> This patch slightly reorders the cleanup. In the original code DRICloseConnection()
> would go before dlclose(screen->driver). But since we open the dri connection before
> dlopen'ing the driver, I thought it would make sense to dlclose the driver before
> closing the dri connection. I don't know if that can be a problem, so someone
> familiar with the code please review.
The order of these two operations shouldn't matter.
> glx/glxdri.c | 45 +++++++++++++++++++++++----------------------
> 1 files changed, 23 insertions(+), 22 deletions(-)
>
> diff --git a/glx/glxdri.c b/glx/glxdri.c
> index 6122653..cbbf240 100644
> --- a/glx/glxdri.c
> +++ b/glx/glxdri.c
> @@ -996,7 +996,7 @@ __glXDRIscreenProbe(ScreenPtr pScreen)
>
> if (!DRIOpenConnection(pScreen, &hSAREA, &BusID)) {
> LogMessage(X_ERROR, "AIGLX error: DRIOpenConnection failed\n");
> - goto handle_error;
> + goto err_free;
> }
>
> fd = drmOpenOnce(NULL, BusID, &newlyopened);
> @@ -1004,12 +1004,12 @@ __glXDRIscreenProbe(ScreenPtr pScreen)
> if (fd < 0) {
> LogMessage(X_ERROR, "AIGLX error: drmOpenOnce failed (%s)\n",
> strerror(-fd));
> - goto handle_error;
> + goto err_close_dri;
> }
>
> if (drmGetMagic(fd, &magic)) {
> LogMessage(X_ERROR, "AIGLX error: drmGetMagic failed\n");
> - goto handle_error;
> + goto err_close_drm;
> }
>
> version = drmGetVersion(fd);
> @@ -1027,7 +1027,7 @@ __glXDRIscreenProbe(ScreenPtr pScreen)
>
> if (newlyopened && !DRIAuthConnection(pScreen, magic)) {
> LogMessage(X_ERROR, "AIGLX error: DRIAuthConnection failed\n");
> - goto handle_error;
> + goto err_close_drm;
> }
>
> /* Get device name (like "tdfx") and the ddx version numbers.
> @@ -1039,7 +1039,7 @@ __glXDRIscreenProbe(ScreenPtr pScreen)
> &ddx_version.patch,
> &driverName)) {
> LogMessage(X_ERROR, "AIGLX error: DRIGetClientDriverName failed\n");
> - goto handle_error;
> + goto err_close_drm;
> }
>
> snprintf(filename, sizeof filename, "%s/%s_dri.so",
> @@ -1049,14 +1049,14 @@ __glXDRIscreenProbe(ScreenPtr pScreen)
> if (screen->driver == NULL) {
> LogMessage(X_ERROR, "AIGLX error: dlopen of %s failed (%s)\n",
> filename, dlerror());
> - goto handle_error;
> + goto err_close_drm;
> }
>
> extensions = dlsym(screen->driver, __DRI_DRIVER_EXTENSIONS);
> if (extensions == NULL) {
> LogMessage(X_ERROR, "AIGLX error: %s exports no extensions (%s)\n",
> driverName, dlerror());
> - goto handle_error;
> + goto err_dlclose;
> }
>
> for (i = 0; extensions[i]; i++) {
> @@ -1075,7 +1075,7 @@ __glXDRIscreenProbe(ScreenPtr pScreen)
> LogMessage(X_ERROR,
> "AIGLX error: %s does not export required DRI extension\n",
> driverName);
> - goto handle_error;
> + goto err_dlclose;
> }
>
> /*
> @@ -1088,7 +1088,7 @@ __glXDRIscreenProbe(ScreenPtr pScreen)
> &framebuffer.size, &framebuffer.stride,
> &framebuffer.dev_priv_size, &framebuffer.dev_priv)) {
> LogMessage(X_ERROR, "AIGLX error: XF86DRIGetDeviceInfo failed\n");
> - goto handle_error;
> + goto err_dlclose;
> }
>
> framebuffer.width = pScreen->width;
> @@ -1100,7 +1100,7 @@ __glXDRIscreenProbe(ScreenPtr pScreen)
> if (status != 0) {
> LogMessage(X_ERROR, "AIGLX error: drmMap of framebuffer failed (%s)\n",
> strerror(-status));
> - goto handle_error;
> + goto err_dlclose;
> }
>
> /* Map the SAREA region. Further mmap regions may be setup in
> @@ -1110,7 +1110,7 @@ __glXDRIscreenProbe(ScreenPtr pScreen)
> if (status != 0) {
> LogMessage(X_ERROR, "AIGLX error: drmMap of SAREA failed (%s)\n",
> strerror(-status));
> - goto handle_error;
> + goto err_unmap_fb;
> }
>
> screen->driScreen =
> @@ -1128,7 +1128,7 @@ __glXDRIscreenProbe(ScreenPtr pScreen)
> if (screen->driScreen == NULL) {
> LogMessage(X_ERROR,
> "AIGLX error: Calling driver entry point failed\n");
> - goto handle_error;
> + goto err_unmap_sarea;
> }
>
> screen->base.fbconfigs = glxConvertConfigs(screen->core, driConfigs);
> @@ -1167,21 +1167,22 @@ __glXDRIscreenProbe(ScreenPtr pScreen)
>
> return &screen->base;
>
> - handle_error:
> - if (pSAREA != NULL)
> - drmUnmap(pSAREA, SAREA_MAX);
> +err_unmap_sarea:
> + drmUnmap(pSAREA, SAREA_MAX);
>
> - if (framebuffer.base != NULL)
> - drmUnmap((drmAddress)framebuffer.base, framebuffer.size);
> +err_unmap_fb:
> + drmUnmap((drmAddress)framebuffer.base, framebuffer.size);
>
> - if (fd >= 0)
> - drmCloseOnce(fd);
> +err_dlclose:
> + dlclose(screen->driver);
>
> - DRICloseConnection(pScreen);
> +err_close_drm:
> + drmCloseOnce(fd);
>
> - if (screen->driver)
> - dlclose(screen->driver);
> +err_close_dri:
> + DRICloseConnection(pScreen);
>
> +err_free:
> xfree(screen);
>
> LogMessage(X_ERROR, "AIGLX: reverting to software rendering\n");
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.10 (GNU/Linux)
Comment: Using GnuPG with Mozilla - http://enigmail.mozdev.org/
iEYEARECAAYFAksqfF0ACgkQX1gOwKyEAw8+/gCgh04mi2G0Y3R3ZGh+LTyP7EC+
W98AnRwTlwPxvRSTutekoCrk087qthjB
=oO8i
-----END PGP SIGNATURE-----
More information about the xorg-devel
mailing list