diff options
author | James Jones <jajones@nvidia.com> | 2010-06-28 16:10:13 -0700 |
---|---|---|
committer | James Jones <jajones@nvidia.com> | 2010-12-06 19:15:26 -0800 |
commit | 1c4a0db2c6bf0320cb630b84ab87bcfd3801a53d (patch) | |
tree | 73a1fce58c7724a845ec024a04b1e50dfe872c9e | |
parent | af0f9f913398d34a885c3fb4e8d40c1a7e2b3ee9 (diff) |
Add fence sync driver interface
-Add fence sync objects
-Add fence sync devPrivates
-Add a X sync module screen private
-Add wrappable functions to create and destroy
fence sync objects
-Give fence sync objects wrappable functions to
trigger, test, and reset their 'triggered' value.
-Give fence sync objects wrappable functions to
notify driver when adding/removing triggers to/
from the sync object.
Signed-off-by: James Jones <jajones@nvidia.com>
Reviewed-by: Keith Packard <keithp@keithp.com>
-rw-r--r-- | Xext/sync.c | 6 | ||||
-rw-r--r-- | dix/privates.c | 1 | ||||
-rwxr-xr-x | hw/xfree86/loader/sdksyms.sh | 3 | ||||
-rw-r--r-- | include/privates.h | 1 | ||||
-rw-r--r-- | miext/sync/misync.c | 176 | ||||
-rw-r--r-- | miext/sync/misync.h | 46 | ||||
-rw-r--r-- | miext/sync/misyncstr.h | 13 |
7 files changed, 243 insertions, 3 deletions
diff --git a/Xext/sync.c b/Xext/sync.c index e5bc64f9a..2615c27eb 100644 --- a/Xext/sync.c +++ b/Xext/sync.c @@ -59,7 +59,7 @@ PERFORMANCE OF THIS SOFTWARE. #include <X11/X.h> #include <X11/Xproto.h> #include <X11/Xmd.h> -#include "misc.h" +#include "scrnintstr.h" #include "os.h" #include "extnsionst.h" #include "dixstruct.h" @@ -2199,6 +2199,10 @@ void SyncExtensionInit(void) { ExtensionEntry *extEntry; + int s; + + for (s = 0; s < screenInfo.numScreens; s++) + miSyncSetup(screenInfo.screens[s]); if (RTCounter == 0) { diff --git a/dix/privates.c b/dix/privates.c index 687fa7aa0..d651258f6 100644 --- a/dix/privates.c +++ b/dix/privates.c @@ -447,6 +447,7 @@ static const char *key_names[PRIVATE_LAST] = { [PRIVATE_GLYPH] = "GLYPH", [PRIVATE_GLYPHSET] = "GLYPHSET", [PRIVATE_PICTURE] = "PICTURE", + [PRIVATE_SYNC_FENCE] = "SYNC_FENCE", }; void diff --git a/hw/xfree86/loader/sdksyms.sh b/hw/xfree86/loader/sdksyms.sh index 4b3ed8694..21354303f 100755 --- a/hw/xfree86/loader/sdksyms.sh +++ b/hw/xfree86/loader/sdksyms.sh @@ -41,6 +41,9 @@ cat > sdksyms.c << EOF #include "damage.h" #include "damagestr.h" +/* miext/sync/Makefile.am */ +#include "misync.h" +#include "misyncstr.h" /* Xext/Makefile.am -- half is module, half is builtin */ /* diff --git a/include/privates.h b/include/privates.h index 9fb6ae84e..7ef2cb732 100644 --- a/include/privates.h +++ b/include/privates.h @@ -51,6 +51,7 @@ typedef enum { PRIVATE_GLYPH, PRIVATE_GLYPHSET, PRIVATE_PICTURE, + PRIVATE_SYNC_FENCE, /* last private type */ PRIVATE_LAST, diff --git a/miext/sync/misync.c b/miext/sync/misync.c index 344810f56..bcc68a2bb 100644 --- a/miext/sync/misync.c +++ b/miext/sync/misync.c @@ -21,5 +21,181 @@ * DEALINGS IN THE SOFTWARE. */ +#ifdef HAVE_DIX_CONFIG_H +#include <dix-config.h> +#endif + +#include "scrnintstr.h" #include "misync.h" #include "misyncstr.h" + +static DevPrivateKeyRec syncScreenPrivateKeyRec; +static DevPrivateKey syncScreenPrivateKey = &syncScreenPrivateKeyRec; + +#define SYNC_SCREEN_PRIV(pScreen) \ + (SyncScreenPrivPtr) dixLookupPrivate(&pScreen->devPrivates, \ + syncScreenPrivateKey) + +typedef struct _syncScreenPriv { + /* Wrappable sync-specific screen functions */ + SyncScreenFuncsRec funcs; + + /* Wrapped screen functions */ + CloseScreenProcPtr CloseScreen; +} SyncScreenPrivRec, *SyncScreenPrivPtr; + +/* Default implementations of the sync screen functions */ +void +miSyncScreenCreateFence(ScreenPtr pScreen, SyncFence* pFence, + Bool initially_triggered) +{ + (void)pScreen; + + pFence->triggered = initially_triggered; +} + +void miSyncScreenDestroyFence(ScreenPtr pScreen, SyncFence* pFence) +{ + (void)pScreen; + (void)pFence; +} + +/* Default implementations of the per-object functions */ +static void +miSyncFenceSetTriggered(SyncFence* pFence) +{ + pFence->triggered = TRUE; +} + +static void +miSyncFenceReset(SyncFence* pFence) +{ + pFence->triggered = FALSE; +} + +static Bool +miSyncFenceCheckTriggered(SyncFence* pFence) +{ + return pFence->triggered; +} + +static void +miSyncFenceAddTrigger(SyncTrigger* pTrigger) +{ + (void)pTrigger; + + return; +} + +static void +miSyncFenceDeleteTrigger(SyncTrigger* pTrigger) +{ + (void)pTrigger; + + return; +} + +/* Machine independent portion of the fence sync object implementation */ +void +miSyncInitFence(ScreenPtr pScreen, SyncFence* pFence, Bool initially_triggered) +{ + SyncScreenPrivPtr pScreenPriv = SYNC_SCREEN_PRIV(pScreen); + static const SyncFenceFuncsRec miSyncFenceFuncs = { + &miSyncFenceSetTriggered, + &miSyncFenceReset, + &miSyncFenceCheckTriggered, + &miSyncFenceAddTrigger, + &miSyncFenceDeleteTrigger + }; + + pFence->pScreen = pScreen; + pFence->funcs = miSyncFenceFuncs; + + pScreenPriv->funcs.CreateFence(pScreen, pFence, initially_triggered); +} + +void +miSyncDestroyFence(SyncFence* pFence) +{ + ScreenPtr pScreen = pFence->pScreen; + SyncScreenPrivPtr pScreenPriv = SYNC_SCREEN_PRIV(pScreen); + SyncTriggerList *ptl, *pNext; + + pFence->sync.beingDestroyed = TRUE; + /* tell all the fence's triggers that the counter has been destroyed */ + for (ptl = pFence->sync.pTriglist; ptl; ptl = pNext) + { + (*ptl->pTrigger->CounterDestroyed)(ptl->pTrigger); + pNext = ptl->next; + free(ptl); /* destroy the trigger list as we go */ + } + + pScreenPriv->funcs.DestroyFence(pScreen, pFence); + + dixFreeObjectWithPrivates(pFence, PRIVATE_SYNC_FENCE); +} + +void +miSyncTriggerFence(SyncFence* pFence) +{ + SyncTriggerList *ptl, *pNext; + CARD64 unused; + + pFence->funcs.SetTriggered(pFence); + + XSyncIntToValue(&unused, 0L); + + /* run through triggers to see if any fired */ + for (ptl = pFence->sync.pTriglist; ptl; ptl = pNext) + { + pNext = ptl->next; + if ((*ptl->pTrigger->CheckTrigger)(ptl->pTrigger, unused)) + (*ptl->pTrigger->TriggerFired)(ptl->pTrigger); + } +} + +SyncScreenFuncsPtr miSyncGetScreenFuncs(ScreenPtr pScreen) +{ + SyncScreenPrivPtr pScreenPriv = SYNC_SCREEN_PRIV(pScreen); + + return &pScreenPriv->funcs; +} + +static Bool +SyncCloseScreen (int i, ScreenPtr pScreen) +{ + SyncScreenPrivPtr pScreenPriv = SYNC_SCREEN_PRIV(pScreen); + + pScreen->CloseScreen = pScreenPriv->CloseScreen; + free(pScreenPriv); + + return (*pScreen->CloseScreen) (i, pScreen); +} + +Bool +miSyncSetup(ScreenPtr pScreen) +{ + SyncScreenPrivPtr pScreenPriv; + + static const SyncScreenFuncsRec miSyncScreenFuncs = { + &miSyncScreenCreateFence, + &miSyncScreenDestroyFence + }; + + if (dixPrivateKeyRegistered(syncScreenPrivateKey)) + return TRUE; + + if (!dixRegisterPrivateKey(syncScreenPrivateKey, PRIVATE_SCREEN, + sizeof(SyncScreenPrivRec))) + return FALSE; + + pScreenPriv = SYNC_SCREEN_PRIV(pScreen); + + pScreenPriv->funcs = miSyncScreenFuncs; + + /* Wrap CloseScreen to clean up */ + pScreenPriv->CloseScreen = pScreen->CloseScreen; + pScreen->CloseScreen = SyncCloseScreen; + + return TRUE; +} diff --git a/miext/sync/misync.h b/miext/sync/misync.h index c66be8d82..1c82ea516 100644 --- a/miext/sync/misync.h +++ b/miext/sync/misync.h @@ -28,4 +28,50 @@ #ifndef _MISYNC_H_ #define _MISYNC_H_ +typedef struct _SyncFence SyncFence; +typedef struct _SyncTrigger SyncTrigger; + +typedef void (*SyncScreenCreateFenceFunc) (ScreenPtr pScreen, + SyncFence* pFence, + Bool initially_triggered); +typedef void (*SyncScreenDestroyFenceFunc) (ScreenPtr pScreen, + SyncFence* pFence); + +typedef struct _syncScreenFuncs { + SyncScreenCreateFenceFunc CreateFence; + SyncScreenDestroyFenceFunc DestroyFence; +} SyncScreenFuncsRec, *SyncScreenFuncsPtr; + +extern _X_EXPORT void +miSyncScreenCreateFence(ScreenPtr pScreen, SyncFence* pFence, + Bool initially_triggered); +extern _X_EXPORT void +miSyncScreenDestroyFence(ScreenPtr pScreen, SyncFence* pFence); + +typedef void (*SyncFenceSetTriggeredFunc) (SyncFence* pFence); +typedef void (*SyncFenceResetFunc) (SyncFence* pFence); +typedef Bool (*SyncFenceCheckTriggeredFunc) (SyncFence* pFence); +typedef void (*SyncFenceAddTriggerFunc) (SyncTrigger* pTrigger); +typedef void (*SyncFenceDeleteTriggerFunc) (SyncTrigger* pTrigger); + +typedef struct _syncFenceFuncs { + SyncFenceSetTriggeredFunc SetTriggered; + SyncFenceResetFunc Reset; + SyncFenceCheckTriggeredFunc CheckTriggered; + SyncFenceAddTriggerFunc AddTrigger; + SyncFenceDeleteTriggerFunc DeleteTrigger; +} SyncFenceFuncsRec, *SyncFenceFuncsPtr; + +extern _X_EXPORT void +miSyncInitFence(ScreenPtr pScreen, SyncFence* pFence, Bool initially_triggered); +extern _X_EXPORT void +miSyncDestroyFence(SyncFence* pFence); +extern _X_EXPORT void +miSyncTriggerFence(SyncFence* pFence); + +extern _X_EXPORT SyncScreenFuncsPtr +miSyncGetScreenFuncs(ScreenPtr pScreen); +extern _X_EXPORT Bool +miSyncSetup(ScreenPtr pScreen); + #endif /* _MISYNC_H_ */ diff --git a/miext/sync/misyncstr.h b/miext/sync/misyncstr.h index eecf04f00..40a865c9c 100644 --- a/miext/sync/misyncstr.h +++ b/miext/sync/misyncstr.h @@ -35,6 +35,7 @@ /* Sync object types */ #define SYNC_COUNTER 0 +#define SYNC_FENCE 1 typedef struct _SyncObject { ClientPtr client; /* Owning client. 0 for system counters */ @@ -50,7 +51,15 @@ typedef struct _SyncCounter { struct _SysCounterInfo *pSysCounterInfo; /* NULL if not a system counter */ } SyncCounter; -typedef struct _SyncTrigger { +struct _SyncFence { + SyncObject sync; /* Common sync object data */ + ScreenPtr pScreen; /* Screen of this fence object */ + SyncFenceFuncsRec funcs; /* Funcs for performing ops on fence */ + Bool triggered; /* fence state */ + PrivateRec *devPrivates; /* driver-specific per-fence data */ +}; + +struct _SyncTrigger { SyncObject *pSync; CARD64 wait_value; /* wait value */ unsigned int value_type; /* Absolute or Relative */ @@ -66,7 +75,7 @@ typedef struct _SyncTrigger { void (*CounterDestroyed)( struct _SyncTrigger * /*pTrigger*/ ); -} SyncTrigger; +}; typedef struct _SyncTriggerList { SyncTrigger *pTrigger; |