summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorJakob Bornecrantz <[email protected]>2010-02-06 01:21:36 +0100
committerJakob Bornecrantz <[email protected]>2010-02-06 03:36:47 +0100
commit6ffb6318a05f0e6405645a155cd32e5cfbdbc2ff (patch)
treef5cc6f1acf8b0a442bb44daace1eb7b5e4f3f75f /src
parenta9d61c286d27733d347f81ac7cfae3665accae92 (diff)
vmware/core: Handle new scanout field
Diffstat (limited to 'src')
-rw-r--r--src/gallium/winsys/drm/vmware/core/vmw_screen.c5
-rw-r--r--src/gallium/winsys/drm/vmware/core/vmw_screen.h4
-rw-r--r--src/gallium/winsys/drm/vmware/core/vmw_screen_dri.c12
-rw-r--r--src/gallium/winsys/drm/vmware/core/vmw_screen_ioctl.c18
4 files changed, 35 insertions, 4 deletions
diff --git a/src/gallium/winsys/drm/vmware/core/vmw_screen.c b/src/gallium/winsys/drm/vmware/core/vmw_screen.c
index 911eec5e254..6cc9b382932 100644
--- a/src/gallium/winsys/drm/vmware/core/vmw_screen.c
+++ b/src/gallium/winsys/drm/vmware/core/vmw_screen.c
@@ -37,13 +37,16 @@
* module.
*/
struct vmw_winsys_screen *
-vmw_winsys_create( int fd )
+vmw_winsys_create( int fd, boolean use_old_scanout_flag )
{
struct vmw_winsys_screen *vws = CALLOC_STRUCT(vmw_winsys_screen);
if (!vws)
goto out_no_vws;
vws->ioctl.drm_fd = fd;
+ vws->use_old_scanout_flag = use_old_scanout_flag;
+ debug_printf("%s: use_old_scanout_flag == %s\n", __FUNCTION__,
+ use_old_scanout_flag ? "true" : "false");
if (!vmw_ioctl_init(vws))
goto out_no_ioctl;
diff --git a/src/gallium/winsys/drm/vmware/core/vmw_screen.h b/src/gallium/winsys/drm/vmware/core/vmw_screen.h
index f1d69865e77..d3f2c2c7f56 100644
--- a/src/gallium/winsys/drm/vmware/core/vmw_screen.h
+++ b/src/gallium/winsys/drm/vmware/core/vmw_screen.h
@@ -52,6 +52,8 @@ struct vmw_winsys_screen
{
struct svga_winsys_screen base;
+ boolean use_old_scanout_flag;
+
struct {
volatile uint32_t *fifo_map;
uint64_t last_fence;
@@ -131,7 +133,7 @@ boolean vmw_winsys_screen_init_svga(struct vmw_winsys_screen *vws);
void vmw_ioctl_cleanup(struct vmw_winsys_screen *vws);
void vmw_pools_cleanup(struct vmw_winsys_screen *vws);
-struct vmw_winsys_screen *vmw_winsys_create(int fd);
+struct vmw_winsys_screen *vmw_winsys_create(int fd, boolean use_old_scanout_flag);
void vmw_winsys_destroy(struct vmw_winsys_screen *sws);
diff --git a/src/gallium/winsys/drm/vmware/core/vmw_screen_dri.c b/src/gallium/winsys/drm/vmware/core/vmw_screen_dri.c
index 917b49f1c12..b7c02f67177 100644
--- a/src/gallium/winsys/drm/vmware/core/vmw_screen_dri.c
+++ b/src/gallium/winsys/drm/vmware/core/vmw_screen_dri.c
@@ -51,6 +51,7 @@ static struct dri1_api_version dri_required = { 4, 0, 0 };
static struct dri1_api_version dri_compat = { 4, 0, 0 };
static struct dri1_api_version drm_required = { 0, 1, 0 };
static struct dri1_api_version drm_compat = { 0, 0, 0 };
+static struct dri1_api_version drm_scanout = { 0, 9, 0 };
static boolean
vmw_dri1_check_version(const struct dri1_api_version *cur,
@@ -85,6 +86,7 @@ vmw_drm_create_screen(struct drm_api *drm_api,
struct vmw_winsys_screen *vws;
struct pipe_screen *screen;
struct dri1_create_screen_arg *dri1;
+ boolean use_old_scanout_flag = FALSE;
if (!arg || arg->mode == DRM_CREATE_NORMAL) {
struct dri1_api_version drm_ver;
@@ -96,11 +98,16 @@ vmw_drm_create_screen(struct drm_api *drm_api,
drm_ver.major = ver->version_major;
drm_ver.minor = ver->version_minor;
+ drm_ver.patch_level = 0; /* ??? */
drmFreeVersion(ver);
if (!vmw_dri1_check_version(&drm_ver, &drm_required,
&drm_compat, "vmwgfx drm driver"))
return NULL;
+
+ if (!vmw_dri1_check_version(&drm_ver, &drm_scanout,
+ &drm_compat, "use old scanout field (not a error)"))
+ use_old_scanout_flag = TRUE;
}
if (arg != NULL) {
@@ -118,6 +125,9 @@ vmw_drm_create_screen(struct drm_api *drm_api,
if (!vmw_dri1_check_version(&dri1->drm_version, &drm_required,
&drm_compat, "vmwgfx drm driver"))
return NULL;
+ if (!vmw_dri1_check_version(&dri1->drm_version, &drm_scanout,
+ &drm_compat, "use old scanout field (not a error)"))
+ use_old_scanout_flag = TRUE;
dri1->api = &dri1_api_hooks;
break;
default:
@@ -125,7 +135,7 @@ vmw_drm_create_screen(struct drm_api *drm_api,
}
}
- vws = vmw_winsys_create( fd );
+ vws = vmw_winsys_create( fd, use_old_scanout_flag );
if (!vws)
goto out_no_vws;
diff --git a/src/gallium/winsys/drm/vmware/core/vmw_screen_ioctl.c b/src/gallium/winsys/drm/vmware/core/vmw_screen_ioctl.c
index ccd0b418a16..f2de2c333ff 100644
--- a/src/gallium/winsys/drm/vmware/core/vmw_screen_ioctl.c
+++ b/src/gallium/winsys/drm/vmware/core/vmw_screen_ioctl.c
@@ -57,6 +57,12 @@ struct vmw_region
uint32_t size;
};
+/* XXX: This isn't a real hardware flag, but just a hack for kernel to
+ * know about primary surfaces. In newer versions of the kernel
+ * interface the driver uses a special field.
+ */
+#define SVGA3D_SURFACE_HINT_SCANOUT (1 << 9)
+
static void
vmw_check_last_cmd(struct vmw_winsys_screen *vws)
{
@@ -169,7 +175,17 @@ vmw_ioctl_surface_create(struct vmw_winsys_screen *vws,
vmw_printf("%s flags %d format %d\n", __FUNCTION__, flags, format);
memset(&s_arg, 0, sizeof(s_arg));
- req->flags = (uint32_t) flags;
+ if (vws->use_old_scanout_flag &&
+ (req->flags & SVGA3D_SURFACE_HINT_SCANOUT)) {
+ req->flags = (uint32_t) (flags & ~SVGA3D_SURFACE_HINT_SCANOUT);
+ req->scanout = false;
+ } else if (req->flags & SVGA3D_SURFACE_HINT_SCANOUT) {
+ req->flags = (uint32_t) (flags & ~SVGA3D_SURFACE_HINT_SCANOUT);
+ req->scanout = false;
+ } else {
+ req->flags = (uint32_t) flags;
+ req->scanout = false;
+ }
req->format = (uint32_t) format;
req->shareable = 1;