summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorChia-I Wu <[email protected]>2010-10-23 02:52:14 +0800
committerChia-I Wu <[email protected]>2010-10-23 11:20:41 +0800
commite32ac5b8a963202dcdfb91354f77979765083000 (patch)
tree4814ea72fe3cda7306a88922f5ffe1810d4811b2
parent37213ceacc2d7b309de7641da501282f8f24c8c2 (diff)
egl: Fix _eglModeLookup.
Internally a mode belongs to a screen. But functions like eglGetModeAttribMESA treat a mode as a display resource: a mode can be looked up without a screen. Considering how KMS works, it is better to stick to the current implementation. To properly support looking up a mode without a screen, this commit assigns each mode (of all screens) a unique ID.
-rw-r--r--src/egl/main/eglmode.c58
-rw-r--r--src/egl/main/eglmode.h5
-rw-r--r--src/egl/main/eglscreen.c17
-rw-r--r--src/egl/main/eglscreen.h5
-rw-r--r--src/gallium/state_trackers/egl/common/egl_g3d.c22
5 files changed, 43 insertions, 64 deletions
diff --git a/src/egl/main/eglmode.c b/src/egl/main/eglmode.c
index ed107d5d7a7..29d7964386e 100644
--- a/src/egl/main/eglmode.c
+++ b/src/egl/main/eglmode.c
@@ -31,56 +31,24 @@ _eglLookupMode(EGLModeMESA mode, _EGLDisplay *disp)
/* loop over all screens on the display */
for (scrnum = 0; scrnum < disp->Screens->Size; scrnum++) {
const _EGLScreen *scrn = disp->Screens->Elements[scrnum];
- EGLint i;
- /* search list of modes for handle */
- for (i = 0; i < scrn->NumModes; i++) {
- if (scrn->Modes[i].Handle == mode) {
- return scrn->Modes + i;
- }
- }
- }
+ EGLint idx;
- return NULL;
-}
+ /*
+ * the mode ids of a screen ranges from scrn->Handle to scrn->Handle +
+ * scrn->NumModes
+ */
+ if (mode >= scrn->Handle &&
+ mode < scrn->Handle + _EGL_SCREEN_MAX_MODES) {
+ idx = mode - scrn->Handle;
+ assert(idx < scrn->NumModes && scrn->Modes[idx].Handle == mode);
-/**
- * Add a new mode with the given attributes (width, height, depth, refreshRate)
- * to the given screen.
- * Assign a new mode ID/handle to the mode as well.
- * \return pointer to the new _EGLMode
- */
-_EGLMode *
-_eglAddNewMode(_EGLScreen *screen, EGLint width, EGLint height,
- EGLint refreshRate, const char *name)
-{
- EGLint n;
- _EGLMode *newModes;
-
- assert(screen);
- assert(width > 0);
- assert(height > 0);
- assert(refreshRate > 0);
-
- n = screen->NumModes;
- newModes = (_EGLMode *) realloc(screen->Modes, (n+1) * sizeof(_EGLMode));
- if (newModes) {
- screen->Modes = newModes;
- screen->Modes[n].Handle = n + 1;
- screen->Modes[n].Width = width;
- screen->Modes[n].Height = height;
- screen->Modes[n].RefreshRate = refreshRate;
- screen->Modes[n].Optimal = EGL_FALSE;
- screen->Modes[n].Interlaced = EGL_FALSE;
- screen->Modes[n].Name = _eglstrdup(name);
- screen->NumModes++;
- return screen->Modes + n;
- }
- else {
- return NULL;
+ return &scrn->Modes[idx];
+ }
}
-}
+ return NULL;
+}
/**
diff --git a/src/egl/main/eglmode.h b/src/egl/main/eglmode.h
index 9167cbc4b9b..ed4eb2c34af 100644
--- a/src/egl/main/eglmode.h
+++ b/src/egl/main/eglmode.h
@@ -32,11 +32,6 @@ extern _EGLMode *
_eglLookupMode(EGLModeMESA mode, _EGLDisplay *dpy);
-PUBLIC _EGLMode *
-_eglAddNewMode(_EGLScreen *screen, EGLint width, EGLint height,
- EGLint refreshRate, const char *name);
-
-
extern EGLBoolean
_eglChooseModeMESA(_EGLDriver *drv, _EGLDisplay *dpy, _EGLScreen *scrn,
const EGLint *attrib_list, EGLModeMESA *modes,
diff --git a/src/egl/main/eglscreen.c b/src/egl/main/eglscreen.c
index 0bbead84769..fc3ab322ab0 100644
--- a/src/egl/main/eglscreen.c
+++ b/src/egl/main/eglscreen.c
@@ -42,7 +42,8 @@ _eglAllocScreenHandle(void)
EGLScreenMESA s;
_eglLockMutex(&_eglNextScreenHandleMutex);
- s = _eglNextScreenHandle++;
+ s = _eglNextScreenHandle;
+ _eglNextScreenHandle += _EGL_SCREEN_MAX_MODES;
_eglUnlockMutex(&_eglNextScreenHandleMutex);
return s;
@@ -53,12 +54,19 @@ _eglAllocScreenHandle(void)
* Initialize an _EGLScreen object to default values.
*/
void
-_eglInitScreen(_EGLScreen *screen, _EGLDisplay *dpy)
+_eglInitScreen(_EGLScreen *screen, _EGLDisplay *dpy, EGLint num_modes)
{
memset(screen, 0, sizeof(_EGLScreen));
+
screen->Display = dpy;
+ screen->NumModes = num_modes;
screen->StepX = 1;
screen->StepY = 1;
+
+ if (num_modes > _EGL_SCREEN_MAX_MODES)
+ num_modes = _EGL_SCREEN_MAX_MODES;
+ screen->Modes = (_EGLMode *) calloc(num_modes, sizeof(*screen->Modes));
+ screen->NumModes = (screen->Modes) ? num_modes : 0;
}
@@ -70,6 +78,7 @@ EGLScreenMESA
_eglLinkScreen(_EGLScreen *screen)
{
_EGLDisplay *display;
+ EGLint i;
assert(screen && screen->Display);
display = screen->Display;
@@ -79,7 +88,11 @@ _eglLinkScreen(_EGLScreen *screen)
if (!display->Screens)
return (EGLScreenMESA) 0;
}
+
screen->Handle = _eglAllocScreenHandle();
+ for (i = 0; i < screen->NumModes; i++)
+ screen->Modes[i].Handle = screen->Handle + i;
+
_eglAppendArray(display->Screens, (void *) screen);
return screen->Handle;
diff --git a/src/egl/main/eglscreen.h b/src/egl/main/eglscreen.h
index 44fe20da3be..2a99f23c50a 100644
--- a/src/egl/main/eglscreen.h
+++ b/src/egl/main/eglscreen.h
@@ -8,6 +8,9 @@
#ifdef EGL_MESA_screen_surface
+#define _EGL_SCREEN_MAX_MODES 16
+
+
/**
* Per-screen information.
* Note that an EGL screen doesn't have a size. A screen may be set to
@@ -35,7 +38,7 @@ struct _egl_screen
PUBLIC void
-_eglInitScreen(_EGLScreen *screen, _EGLDisplay *dpy);
+_eglInitScreen(_EGLScreen *screen, _EGLDisplay *dpy, EGLint num_modes);
PUBLIC EGLScreenMESA
diff --git a/src/gallium/state_trackers/egl/common/egl_g3d.c b/src/gallium/state_trackers/egl/common/egl_g3d.c
index 772c65daf50..30ddcd5bc14 100644
--- a/src/gallium/state_trackers/egl/common/egl_g3d.c
+++ b/src/gallium/state_trackers/egl/common/egl_g3d.c
@@ -126,18 +126,18 @@ egl_g3d_add_screens(_EGLDriver *drv, _EGLDisplay *dpy)
continue;
}
- _eglInitScreen(&gscr->base, dpy);
-
- for (j = 0; j < num_modes; j++) {
+ _eglInitScreen(&gscr->base, dpy, num_modes);
+ for (j = 0; j < gscr->base.NumModes; j++) {
const struct native_mode *nmode = native_modes[j];
- _EGLMode *mode;
-
- mode = _eglAddNewMode(&gscr->base, nmode->width, nmode->height,
- nmode->refresh_rate, nmode->desc);
- if (!mode)
- break;
- /* gscr->native_modes and gscr->base.Modes should be consistent */
- assert(mode == &gscr->base.Modes[j]);
+ _EGLMode *mode = &gscr->base.Modes[j];
+
+ mode->Width = nmode->width;
+ mode->Height = nmode->height;
+ mode->RefreshRate = nmode->refresh_rate;
+ mode->Optimal = EGL_FALSE;
+ mode->Interlaced = EGL_FALSE;
+ /* no need to strdup() */
+ mode->Name = nmode->desc;
}
gscr->native = nconn;