1706f2543Smrg/*
2706f2543Smrg * Copyright � 2006 Intel Corporation
3706f2543Smrg *
4706f2543Smrg * Permission is hereby granted, free of charge, to any person obtaining a
5706f2543Smrg * copy of this software and associated documentation files (the "Software"),
6706f2543Smrg * to deal in the Software without restriction, including without limitation
7706f2543Smrg * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8706f2543Smrg * and/or sell copies of the Software, and to permit persons to whom the
9706f2543Smrg * Software is furnished to do so, subject to the following conditions:
10706f2543Smrg *
11706f2543Smrg * The above copyright notice and this permission notice (including the next
12706f2543Smrg * paragraph) shall be included in all copies or substantial portions of the
13706f2543Smrg * Software.
14706f2543Smrg *
15706f2543Smrg * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16706f2543Smrg * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17706f2543Smrg * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
18706f2543Smrg * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19706f2543Smrg * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20706f2543Smrg * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21706f2543Smrg * SOFTWARE.
22706f2543Smrg *
23706f2543Smrg * Authors:
24706f2543Smrg *    Eric Anholt <anholt@FreeBSD.org>
25706f2543Smrg *
26706f2543Smrg */
27706f2543Smrg
28706f2543Smrg#ifdef HAVE_CONFIG_H
29706f2543Smrg#include <xorg-config.h>
30706f2543Smrg#endif
31706f2543Smrg
32706f2543Smrg#include <string.h>
33706f2543Smrg
34706f2543Smrg#include "exa_priv.h"
35706f2543Smrg
36706f2543Smrg#include "xf86str.h"
37706f2543Smrg#include "xf86.h"
38706f2543Smrg
39706f2543Smrgtypedef struct _ExaXorgScreenPrivRec {
40706f2543Smrg    CloseScreenProcPtr 		 SavedCloseScreen;
41706f2543Smrg    EnableDisableFBAccessProcPtr SavedEnableDisableFBAccess;
42706f2543Smrg    OptionInfoPtr		 options;
43706f2543Smrg} ExaXorgScreenPrivRec, *ExaXorgScreenPrivPtr;
44706f2543Smrg
45706f2543Smrgstatic DevPrivateKeyRec exaXorgScreenPrivateKeyRec;
46706f2543Smrg#define exaXorgScreenPrivateKey (&exaXorgScreenPrivateKeyRec)
47706f2543Smrg
48706f2543Smrgtypedef enum {
49706f2543Smrg    EXAOPT_MIGRATION_HEURISTIC,
50706f2543Smrg    EXAOPT_NO_COMPOSITE,
51706f2543Smrg    EXAOPT_NO_UTS,
52706f2543Smrg    EXAOPT_NO_DFS,
53706f2543Smrg    EXAOPT_OPTIMIZE_MIGRATION
54706f2543Smrg} EXAOpts;
55706f2543Smrg
56706f2543Smrgstatic const OptionInfoRec EXAOptions[] = {
57706f2543Smrg    { EXAOPT_MIGRATION_HEURISTIC,	"MigrationHeuristic",
58706f2543Smrg				OPTV_ANYSTR,	{0}, FALSE },
59706f2543Smrg    { EXAOPT_NO_COMPOSITE,		"EXANoComposite",
60706f2543Smrg				OPTV_BOOLEAN,	{0}, FALSE },
61706f2543Smrg    { EXAOPT_NO_UTS,			"EXANoUploadToScreen",
62706f2543Smrg				OPTV_BOOLEAN,	{0}, FALSE },
63706f2543Smrg    { EXAOPT_NO_DFS,			"EXANoDownloadFromScreen",
64706f2543Smrg				OPTV_BOOLEAN,	{0}, FALSE },
65706f2543Smrg    { EXAOPT_OPTIMIZE_MIGRATION,	"EXAOptimizeMigration",
66706f2543Smrg				OPTV_BOOLEAN,	{0}, FALSE },
67706f2543Smrg    { -1,				NULL,
68706f2543Smrg				OPTV_NONE,	{0}, FALSE }
69706f2543Smrg};
70706f2543Smrg
71706f2543Smrgstatic Bool
72706f2543SmrgexaXorgCloseScreen (int i, ScreenPtr pScreen)
73706f2543Smrg{
74706f2543Smrg    ScrnInfoPtr pScrn = XF86SCRNINFO(pScreen);
75706f2543Smrg    ExaXorgScreenPrivPtr pScreenPriv = (ExaXorgScreenPrivPtr)
76706f2543Smrg	dixLookupPrivate(&pScreen->devPrivates, exaXorgScreenPrivateKey);
77706f2543Smrg
78706f2543Smrg    pScreen->CloseScreen = pScreenPriv->SavedCloseScreen;
79706f2543Smrg
80706f2543Smrg    pScrn->EnableDisableFBAccess = pScreenPriv->SavedEnableDisableFBAccess;
81706f2543Smrg
82706f2543Smrg    free(pScreenPriv->options);
83706f2543Smrg    free(pScreenPriv);
84706f2543Smrg
85706f2543Smrg    return pScreen->CloseScreen (i, pScreen);
86706f2543Smrg}
87706f2543Smrg
88706f2543Smrgstatic void
89706f2543SmrgexaXorgEnableDisableFBAccess (int index, Bool enable)
90706f2543Smrg{
91706f2543Smrg    ScreenPtr pScreen = screenInfo.screens[index];
92706f2543Smrg    ExaXorgScreenPrivPtr pScreenPriv = (ExaXorgScreenPrivPtr)
93706f2543Smrg	dixLookupPrivate(&pScreen->devPrivates, exaXorgScreenPrivateKey);
94706f2543Smrg
95706f2543Smrg    if (!enable)
96706f2543Smrg	exaEnableDisableFBAccess (index, enable);
97706f2543Smrg
98706f2543Smrg    if (pScreenPriv->SavedEnableDisableFBAccess)
99706f2543Smrg       pScreenPriv->SavedEnableDisableFBAccess (index, enable);
100706f2543Smrg
101706f2543Smrg    if (enable)
102706f2543Smrg	exaEnableDisableFBAccess (index, enable);
103706f2543Smrg}
104706f2543Smrg
105706f2543Smrg/**
106706f2543Smrg * This will be called during exaDriverInit, giving us the chance to set options
107706f2543Smrg * and hook in our EnableDisableFBAccess.
108706f2543Smrg */
109706f2543Smrgvoid
110706f2543SmrgexaDDXDriverInit(ScreenPtr pScreen)
111706f2543Smrg{
112706f2543Smrg    ExaScreenPriv(pScreen);
113706f2543Smrg    /* Do NOT use XF86SCRNINFO macro here!! */
114706f2543Smrg    ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
115706f2543Smrg    ExaXorgScreenPrivPtr pScreenPriv;
116706f2543Smrg
117706f2543Smrg    if (!dixRegisterPrivateKey(&exaXorgScreenPrivateKeyRec, PRIVATE_SCREEN, 0))
118706f2543Smrg	return;
119706f2543Smrg
120706f2543Smrg    pScreenPriv = calloc(1, sizeof(ExaXorgScreenPrivRec));
121706f2543Smrg    if (pScreenPriv == NULL)
122706f2543Smrg	return;
123706f2543Smrg
124706f2543Smrg    pScreenPriv->options = xnfalloc (sizeof(EXAOptions));
125706f2543Smrg    memcpy(pScreenPriv->options, EXAOptions, sizeof(EXAOptions));
126706f2543Smrg    xf86ProcessOptions (pScrn->scrnIndex, pScrn->options, pScreenPriv->options);
127706f2543Smrg
128706f2543Smrg    if (pExaScr->info->flags & EXA_OFFSCREEN_PIXMAPS) {
129706f2543Smrg	if (!(pExaScr->info->flags & EXA_HANDLES_PIXMAPS) &&
130706f2543Smrg	    pExaScr->info->offScreenBase < pExaScr->info->memorySize) {
131706f2543Smrg	    char *heuristicName;
132706f2543Smrg
133706f2543Smrg	    heuristicName = xf86GetOptValString (pScreenPriv->options,
134706f2543Smrg						 EXAOPT_MIGRATION_HEURISTIC);
135706f2543Smrg	    if (heuristicName != NULL) {
136706f2543Smrg		if (strcmp(heuristicName, "greedy") == 0)
137706f2543Smrg		    pExaScr->migration = ExaMigrationGreedy;
138706f2543Smrg		else if (strcmp(heuristicName, "always") == 0)
139706f2543Smrg		    pExaScr->migration = ExaMigrationAlways;
140706f2543Smrg		else if (strcmp(heuristicName, "smart") == 0)
141706f2543Smrg		    pExaScr->migration = ExaMigrationSmart;
142706f2543Smrg		else {
143706f2543Smrg		    xf86DrvMsg (pScreen->myNum, X_WARNING,
144706f2543Smrg				"EXA: unknown migration heuristic %s\n",
145706f2543Smrg				heuristicName);
146706f2543Smrg		}
147706f2543Smrg	    }
148706f2543Smrg	}
149706f2543Smrg
150706f2543Smrg	pExaScr->optimize_migration =
151706f2543Smrg	    xf86ReturnOptValBool(pScreenPriv->options,
152706f2543Smrg				 EXAOPT_OPTIMIZE_MIGRATION,
153706f2543Smrg				 TRUE);
154706f2543Smrg    }
155706f2543Smrg
156706f2543Smrg    if (xf86ReturnOptValBool(pScreenPriv->options,
157706f2543Smrg                             EXAOPT_NO_COMPOSITE, FALSE)) {
158706f2543Smrg	xf86DrvMsg(pScreen->myNum, X_CONFIG,
159706f2543Smrg		   "EXA: Disabling Composite operation "
160706f2543Smrg		   "(RENDER acceleration)\n");
161706f2543Smrg	pExaScr->info->CheckComposite = NULL;
162706f2543Smrg	pExaScr->info->PrepareComposite = NULL;
163706f2543Smrg    }
164706f2543Smrg
165706f2543Smrg    if (xf86ReturnOptValBool(pScreenPriv->options, EXAOPT_NO_UTS, FALSE)) {
166706f2543Smrg	xf86DrvMsg(pScreen->myNum, X_CONFIG,
167706f2543Smrg		   "EXA: Disabling UploadToScreen\n");
168706f2543Smrg	pExaScr->info->UploadToScreen = NULL;
169706f2543Smrg    }
170706f2543Smrg
171706f2543Smrg    if (xf86ReturnOptValBool(pScreenPriv->options, EXAOPT_NO_DFS, FALSE)) {
172706f2543Smrg	xf86DrvMsg(pScreen->myNum, X_CONFIG,
173706f2543Smrg		   "EXA: Disabling DownloadFromScreen\n");
174706f2543Smrg	pExaScr->info->DownloadFromScreen = NULL;
175706f2543Smrg    }
176706f2543Smrg
177706f2543Smrg    dixSetPrivate(&pScreen->devPrivates, exaXorgScreenPrivateKey, pScreenPriv);
178706f2543Smrg
179706f2543Smrg    pScreenPriv->SavedEnableDisableFBAccess = pScrn->EnableDisableFBAccess;
180706f2543Smrg    pScrn->EnableDisableFBAccess = exaXorgEnableDisableFBAccess;
181706f2543Smrg
182706f2543Smrg    pScreenPriv->SavedCloseScreen = pScreen->CloseScreen;
183706f2543Smrg    pScreen->CloseScreen = exaXorgCloseScreen;
184706f2543Smrg
185706f2543Smrg}
186706f2543Smrg
187706f2543Smrgstatic XF86ModuleVersionInfo exaVersRec =
188706f2543Smrg{
189706f2543Smrg	"exa",
190706f2543Smrg	MODULEVENDORSTRING,
191706f2543Smrg	MODINFOSTRING1,
192706f2543Smrg	MODINFOSTRING2,
193706f2543Smrg	XORG_VERSION_CURRENT,
194706f2543Smrg	EXA_VERSION_MAJOR, EXA_VERSION_MINOR, EXA_VERSION_RELEASE,
195706f2543Smrg	ABI_CLASS_VIDEODRV,		/* requires the video driver ABI */
196706f2543Smrg	ABI_VIDEODRV_VERSION,
197706f2543Smrg	MOD_CLASS_NONE,
198706f2543Smrg	{0,0,0,0}
199706f2543Smrg};
200706f2543Smrg
201706f2543Smrg_X_EXPORT XF86ModuleData exaModuleData = { &exaVersRec, NULL, NULL };
202