diff options
author | Jakob Bornecrantz <jakob@vmware.com> | 2010-02-11 22:04:53 +0100 |
---|---|---|
committer | Jakob Bornecrantz <jakob@vmware.com> | 2010-02-11 22:14:14 +0100 |
commit | c4f5bf8ea45b80c2ac4a5eec65ff58f148fb2807 (patch) | |
tree | ff65550002c3e21d0e1d403ac8ae58b59448e108 /src/vmwaremodule.c | |
parent | 0d9d1724dbe113dcc02736a8ca80ab540057cb5e (diff) |
Add a chain loading module to load new vmwgfx driver if kernel module is loaded
Diffstat (limited to 'src/vmwaremodule.c')
-rw-r--r-- | src/vmwaremodule.c | 142 |
1 files changed, 142 insertions, 0 deletions
diff --git a/src/vmwaremodule.c b/src/vmwaremodule.c new file mode 100644 index 0000000..826310b --- /dev/null +++ b/src/vmwaremodule.c @@ -0,0 +1,142 @@ +/********************************************************** + * Copyright 2010 VMware, Inc. All rights reserved. + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without + * restriction, including without limitation the rights to use, copy, + * modify, merge, publish, distribute, sublicense, and/or sell copies + * of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS + * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN + * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * + **********************************************************/ + +#include <xorg-server.h> +#include <xf86.h> +#include <xf86drm.h> + + +/* + * Defines and exported module info. + */ + +#define VMWARE_DRIVER_NAME "vmware" +#define VMWGFX_DRIVER_NAME "vmwgfx" +#define VMWLEGACY_DRIVER_NAME "vmwlegacy" + +#define VMWARE_VERSION_MAJOR 10 +#define VMWARE_VERSION_MINOR 16 +#define VMWARE_VERSION_PATCH 9 + +static XF86ModuleVersionInfo vmware_version; +static MODULESETUPPROTO(vmware_setup); + +_X_EXPORT XF86ModuleData vmwareModuleData = { + &vmware_version, + vmware_setup, + NULL +}; + + +/* + * Chain loading functions + */ + +static Bool +vmware_check_kernel_module() +{ + /* Super simple way of knowing if the kernel driver is loaded */ + int ret = drmOpen("vmwgfx", NULL); + if (ret < 0) + return FALSE; + + drmClose(ret); + + return TRUE; +} + +static Bool +vmware_chain_module(pointer opts) +{ + int vmwlegacy_devices; + int vmwgfx_devices; + int vmware_devices; + int matched; + char *driver_name; + GDevPtr *gdevs; + GDevPtr gdev; + int i; + + vmware_devices = xf86MatchDevice(VMWARE_DRIVER_NAME, &gdevs); + vmwgfx_devices = xf86MatchDevice(VMWGFX_DRIVER_NAME, NULL); + vmwlegacy_devices = xf86MatchDevice(VMWLEGACY_DRIVER_NAME, NULL); + + if (vmware_check_kernel_module()) { + driver_name = VMWGFX_DRIVER_NAME; + matched = vmwgfx_devices; + } else { + driver_name = VMWLEGACY_DRIVER_NAME; + matched = vmwlegacy_devices; + } + + for (i = 0; i < vmware_devices; i++) { + gdev = gdevs[i]; + gdev->driver = driver_name; + } + + xfree(gdevs); + + if (!matched) + xf86LoadOneModule(driver_name, opts); +} + + +/* + * Module info + */ + +static XF86ModuleVersionInfo vmware_version = { + VMWARE_DRIVER_NAME, + MODULEVENDORSTRING, + MODINFOSTRING1, + MODINFOSTRING2, + XORG_VERSION_CURRENT, + VMWARE_VERSION_MAJOR, VMWARE_VERSION_MINOR, VMWARE_VERSION_PATCH, + ABI_CLASS_VIDEODRV, + ABI_VIDEODRV_VERSION, + MOD_CLASS_VIDEODRV, + {0, 0, 0, 0} +}; + +static pointer +vmware_setup(pointer module, pointer opts, int *errmaj, int *errmin) +{ + static Bool setupDone = 0; + int ret; + + /* This module should be loaded only once, but check to be sure. */ + if (!setupDone) { + setupDone = 1; + + /* Chain load the real driver */ + vmware_chain_module(opts); + + return (pointer) 1; + } else { + if (errmaj) + *errmaj = LDR_ONCEONLY; + return NULL; + } +} |