diff options
author | Francisco Jerez <currojerez@riseup.net> | 2010-10-14 22:32:54 +0200 |
---|---|---|
committer | Francisco Jerez <currojerez@riseup.net> | 2010-10-22 15:33:06 +0200 |
commit | 75daada678d03d2e162f8003a6f2edcbe0525f92 (patch) | |
tree | 9a6d88a2bf5979091bbbc474ce539387f468b8ef | |
parent | 70f0d2c886ceaa965ca4864788f4dd8e8f757a92 (diff) | |
download | xorg-driver-xf86-video-nouveau-75daada678d03d2e162f8003a6f2edcbe0525f92.tar.gz |
Restructure tiled pixmap allocation in a single place.
Signed-off-by: Francisco Jerez <currojerez@riseup.net>
-rw-r--r-- | src/drmmode_display.c | 56 | ||||
-rw-r--r-- | src/nouveau_exa.c | 55 | ||||
-rw-r--r-- | src/nv_accel_common.c | 67 | ||||
-rw-r--r-- | src/nv_driver.c | 34 | ||||
-rw-r--r-- | src/nv_proto.h | 3 | ||||
-rw-r--r-- | src/nv_type.h | 5 |
6 files changed, 104 insertions, 116 deletions
diff --git a/src/drmmode_display.c b/src/drmmode_display.c index 115398a..4220cf5 100644 --- a/src/drmmode_display.c +++ b/src/drmmode_display.c @@ -58,7 +58,7 @@ typedef struct { drmModeCrtcPtr mode_crtc; struct nouveau_bo *cursor; struct nouveau_bo *rotate_bo; - uint32_t rotate_pitch; + int rotate_pitch; PixmapPtr rotate_pixmap; uint32_t rotate_fb_id; Bool cursor_visible; @@ -430,28 +430,18 @@ drmmode_show_cursor (xf86CrtcPtr crtc) static void * drmmode_crtc_shadow_allocate(xf86CrtcPtr crtc, int width, int height) { + ScrnInfoPtr scrn = crtc->scrn; drmmode_crtc_private_ptr drmmode_crtc = crtc->driver_private; drmmode_ptr drmmode = drmmode_crtc->drmmode; - NVPtr pNv = NVPTR(crtc->scrn); - uint32_t tile_mode = 0, tile_flags = NOUVEAU_BO_TILE_SCANOUT; - int ah = height, ret, pitch; void *virtual; + int ret; - if (pNv->Architecture >= NV_ARCH_50 && pNv->tiled_scanout) { - tile_mode = 4; - tile_flags |= (drmmode->cpp == 2) ? 0x7000 : 0x7a00; - ah = NOUVEAU_ALIGN(height, 1 << (tile_mode + 2)); - pitch = NOUVEAU_ALIGN(width * drmmode->cpp, 64); - } else { - pitch = nv_pitch_align(pNv, width, crtc->scrn->depth); - pitch *= drmmode->cpp; - } - drmmode_crtc->rotate_pitch = pitch; - - ret = nouveau_bo_new_tile(pNv->dev, NOUVEAU_BO_VRAM | NOUVEAU_BO_MAP, 0, - drmmode_crtc->rotate_pitch * ah, tile_mode, - tile_flags, &drmmode_crtc->rotate_bo); - if (ret) { + ret = nouveau_allocate_surface(scrn, width, height, + scrn->bitsPerPixel, + NOUVEAU_CREATE_PIXMAP_SCANOUT, + &drmmode_crtc->rotate_pitch, + &drmmode_crtc->rotate_bo); + if (!ret) { xf86DrvMsg(crtc->scrn->scrnIndex, X_ERROR, "Couldn't allocate shadow memory for rotated CRTC\n"); return NULL; @@ -1026,27 +1016,16 @@ drmmode_xf86crtc_resize(ScrnInfoPtr scrn, int width, int height) drmmode_crtc_private_ptr drmmode_crtc = xf86_config->crtc[0]->driver_private; drmmode_ptr drmmode = drmmode_crtc->drmmode; - uint32_t pitch, old_width, old_height, old_pitch, old_fb_id; + uint32_t old_width, old_height, old_pitch, old_fb_id; struct nouveau_bo *old_bo = NULL; - uint32_t tile_mode = 0, tile_flags = NOUVEAU_BO_TILE_SCANOUT; + int ret, i, pitch; PixmapPtr ppix; - int ret, i, ah = height; ErrorF("resize called %d %d\n", width, height); if (scrn->virtualX == width && scrn->virtualY == height) return TRUE; - if (pNv->Architecture >= NV_ARCH_50 && pNv->tiled_scanout) { - tile_mode = 4; - tile_flags |= (scrn->bitsPerPixel == 16) ? 0x7000 : 0x7a00; - ah = NOUVEAU_ALIGN(height, 1 << (tile_mode + 2)); - pitch = NOUVEAU_ALIGN(width * (scrn->bitsPerPixel >> 3), 64); - } else { - pitch = nv_pitch_align(pNv, width, scrn->depth); - pitch *= (scrn->bitsPerPixel >> 3); - } - old_width = scrn->virtualX; old_height = scrn->virtualY; old_pitch = scrn->displayWidth; @@ -1054,16 +1033,17 @@ drmmode_xf86crtc_resize(ScrnInfoPtr scrn, int width, int height) nouveau_bo_ref(pNv->scanout, &old_bo); nouveau_bo_ref(NULL, &pNv->scanout); + ret = nouveau_allocate_surface(scrn, width, height, + scrn->bitsPerPixel, + NOUVEAU_CREATE_PIXMAP_SCANOUT, + &pitch, &pNv->scanout); + if (!ret) + goto fail; + scrn->virtualX = width; scrn->virtualY = height; scrn->displayWidth = pitch / (scrn->bitsPerPixel >> 3); - ret = nouveau_bo_new_tile(pNv->dev, NOUVEAU_BO_VRAM | NOUVEAU_BO_MAP, - 0, pitch * ah, tile_mode, tile_flags, - &pNv->scanout); - if (ret) - goto fail; - nouveau_bo_map(pNv->scanout, NOUVEAU_BO_RDWR); ret = drmModeAddFB(drmmode->fd, width, height, scrn->depth, diff --git a/src/nouveau_exa.c b/src/nouveau_exa.c index f3a2abd..4618994 100644 --- a/src/nouveau_exa.c +++ b/src/nouveau_exa.c @@ -312,10 +312,10 @@ static void * nouveau_exa_create_pixmap(ScreenPtr pScreen, int width, int height, int depth, int usage_hint, int bitsPerPixel, int *new_pitch) { - NVPtr pNv = NVPTR(xf86Screens[pScreen->myNum]); + ScrnInfoPtr scrn = xf86Screens[pScreen->myNum]; + NVPtr pNv = NVPTR(scrn); struct nouveau_pixmap *nvpix; - uint32_t flags = NOUVEAU_BO_MAP, tile_mode = 0, tile_flags = 0; - int ret, size, cpp = bitsPerPixel >> 3; + int ret; if (!width || !height) return calloc(1, sizeof(*nvpix)); @@ -328,52 +328,9 @@ nouveau_exa_create_pixmap(ScreenPtr pScreen, int width, int height, int depth, if (!nvpix) return NULL; - if (cpp) { - flags |= NOUVEAU_BO_VRAM; - *new_pitch = width * cpp; - - if (pNv->Architecture >= NV_ARCH_50) { - if (height > 32) tile_mode = 4; - else if (height > 16) tile_mode = 3; - else if (height > 8) tile_mode = 2; - else if (height > 4) tile_mode = 1; - else tile_mode = 0; - - if (usage_hint & NOUVEAU_CREATE_PIXMAP_ZETA) - tile_flags = 0x2800; - else - tile_flags = 0x7000; - - height = NOUVEAU_ALIGN(height, 1 << (tile_mode + 2)); - } else { - if (usage_hint & NOUVEAU_CREATE_PIXMAP_TILED) { - int pitch_align = max( - pNv->dev->chipset >= 0x40 ? 1024 : 256, - round_down_pow2(*new_pitch / 4)); - - *new_pitch = NOUVEAU_ALIGN(*new_pitch, - pitch_align); - tile_mode = *new_pitch; - - if (bitsPerPixel == 32) - tile_flags |= NOUVEAU_BO_TILE_32BPP; - else if (bitsPerPixel == 16) - tile_flags |= NOUVEAU_BO_TILE_16BPP; - - if (usage_hint & NOUVEAU_CREATE_PIXMAP_ZETA) - tile_flags |= NOUVEAU_BO_TILE_ZETA; - } - } - } else { - *new_pitch = (width * bitsPerPixel + 7) / 8; - } - - *new_pitch = NOUVEAU_ALIGN(*new_pitch, 64); - size = *new_pitch * height; - - ret = nouveau_bo_new_tile(pNv->dev, flags, 0, size, tile_mode, - tile_flags, &nvpix->bo); - if (ret) { + ret = nouveau_allocate_surface(scrn, width, height, bitsPerPixel, + usage_hint, new_pitch, &nvpix->bo); + if (!ret) { free(nvpix); return NULL; } diff --git a/src/nv_accel_common.c b/src/nv_accel_common.c index 891615c..3739c79 100644 --- a/src/nv_accel_common.c +++ b/src/nv_accel_common.c @@ -22,6 +22,73 @@ #include "nv_include.h" +Bool +nouveau_allocate_surface(ScrnInfoPtr scrn, int width, int height, int bpp, + int usage_hint, int *pitch, struct nouveau_bo **bo) +{ + NVPtr pNv = NVPTR(scrn); + Bool scanout = (usage_hint & NOUVEAU_CREATE_PIXMAP_SCANOUT); + Bool tiled = (usage_hint & NOUVEAU_CREATE_PIXMAP_TILED); + int tile_mode = 0, tile_flags = 0; + int flags = NOUVEAU_BO_MAP | (bpp >= 8 ? NOUVEAU_BO_VRAM : 0); + int ret; + + if ((scanout && pNv->tiled_scanout) || + (!scanout && pNv->Architecture >= NV_ARCH_50 && bpp >= 8)) + tiled = TRUE; + + *pitch = NOUVEAU_ALIGN(width * bpp, 512) / 8; + + if (tiled) { + if (pNv->Architecture >= NV_ARCH_50) { + if (height > 32) + tile_mode = 4; + else if (height > 16) + tile_mode = 3; + else if (height > 8) + tile_mode = 2; + else if (height > 4) + tile_mode = 1; + else + tile_mode = 0; + + if (usage_hint & NOUVEAU_CREATE_PIXMAP_ZETA) + tile_flags = 0x2800; + else if (usage_hint & NOUVEAU_CREATE_PIXMAP_SCANOUT) + tile_flags = (bpp == 16 ? 0x7000 : 0x7a00); + else + tile_flags = 0x7000; + + height = NOUVEAU_ALIGN(height, 1 << (tile_mode + 2)); + } else { + int pitch_align = max( + pNv->dev->chipset >= 0x40 ? 1024 : 256, + round_down_pow2(*pitch / 4)); + + tile_mode = *pitch = + NOUVEAU_ALIGN(*pitch, pitch_align); + } + } + + if (bpp == 32) + tile_flags |= NOUVEAU_BO_TILE_32BPP; + else if (bpp == 16) + tile_flags |= NOUVEAU_BO_TILE_16BPP; + + if (usage_hint & NOUVEAU_CREATE_PIXMAP_ZETA) + tile_flags |= NOUVEAU_BO_TILE_ZETA; + + if (usage_hint & NOUVEAU_CREATE_PIXMAP_SCANOUT) + tile_flags |= NOUVEAU_BO_TILE_SCANOUT; + + ret = nouveau_bo_new_tile(pNv->dev, flags, 0, *pitch * height, + tile_mode, tile_flags, bo); + if (ret) + return FALSE; + + return TRUE; +} + void NV11SyncToVBlank(PixmapPtr ppix, int x1, int y1, int x2, int y2) { diff --git a/src/nv_driver.c b/src/nv_driver.c index e07ce8c..e891cf3 100644 --- a/src/nv_driver.c +++ b/src/nv_driver.c @@ -815,16 +815,6 @@ NVPreInit(ScrnInfoPtr pScrn, int flags) if (!xf86SetGamma(pScrn, gammazeros)) NVPreInitFail("\n"); - if (pNv->Architecture >= NV_ARCH_50 && pNv->tiled_scanout) { - int cpp = pScrn->bitsPerPixel >> 3; - pScrn->displayWidth = pScrn->virtualX * cpp; - pScrn->displayWidth = NOUVEAU_ALIGN(pScrn->displayWidth, 64); - pScrn->displayWidth = pScrn->displayWidth / cpp; - } else { - pScrn->displayWidth = nv_pitch_align(pNv, pScrn->virtualX, - pScrn->depth); - } - /* No usable mode */ if (!pScrn->modes) return FALSE; @@ -866,29 +856,19 @@ NVMapMem(ScrnInfoPtr pScrn) { NVPtr pNv = NVPTR(pScrn); struct nouveau_device *dev = pNv->dev; - uint32_t tile_mode = 0, tile_flags = NOUVEAU_BO_TILE_SCANOUT; - int ret, size; - - size = pScrn->displayWidth * (pScrn->bitsPerPixel >> 3); - if (pNv->Architecture >= NV_ARCH_50 && pNv->tiled_scanout) { - tile_mode = 4; - tile_flags |= pScrn->bitsPerPixel == 16 ? 0x7000 : 0x7a00; - size *= NOUVEAU_ALIGN(pScrn->virtualY, (1 << (tile_mode + 2))); - } else { - size *= pScrn->virtualY; - } + int ret, pitch, size; - ret = nouveau_bo_new_tile(dev, NOUVEAU_BO_VRAM | NOUVEAU_BO_MAP, - 0, size, tile_mode, tile_flags, - &pNv->scanout); - if (ret) { + ret = nouveau_allocate_surface(pScrn, pScrn->virtualX, pScrn->virtualY, + pScrn->bitsPerPixel, + NOUVEAU_CREATE_PIXMAP_SCANOUT, + &pitch, &pNv->scanout); + if (!ret) { xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "Error allocating scanout buffer: %d\n", ret); return FALSE; } - nouveau_bo_map(pNv->scanout, NOUVEAU_BO_RDWR); - nouveau_bo_unmap(pNv->scanout); + pScrn->displayWidth = pitch / (pScrn->bitsPerPixel / 8); if (pNv->NoAccel) return TRUE; diff --git a/src/nv_proto.h b/src/nv_proto.h index 89411b2..ba234b3 100644 --- a/src/nv_proto.h +++ b/src/nv_proto.h @@ -17,6 +17,9 @@ Bool NVAccelGetCtxSurf2DFormatFromPicture(PicturePtr pPix, int *fmt_ret); PixmapPtr NVGetDrawablePixmap(DrawablePtr pDraw); void NVAccelFree(ScrnInfoPtr pScrn); void NV11SyncToVBlank(PixmapPtr ppix, int x1, int y1, int x2, int y2); +Bool nouveau_allocate_surface(ScrnInfoPtr scrn, int width, int height, + int bpp, int usage_hint, int *pitch, + struct nouveau_bo **bo); /* in nouveau_dri2.c */ void nouveau_dri2_vblank_handler(int fd, unsigned int frame, diff --git a/src/nv_type.h b/src/nv_type.h index 8290b09..a9c693f 100644 --- a/src/nv_type.h +++ b/src/nv_type.h @@ -151,8 +151,9 @@ typedef struct _NVPortPrivRec { #define TIMER_MASK (OFF_TIMER | FREE_TIMER) /* EXA driver-controlled pixmaps */ -#define NOUVEAU_CREATE_PIXMAP_ZETA 0x10000000 -#define NOUVEAU_CREATE_PIXMAP_TILED 0x20000000 +#define NOUVEAU_CREATE_PIXMAP_ZETA 0x10000000 +#define NOUVEAU_CREATE_PIXMAP_TILED 0x20000000 +#define NOUVEAU_CREATE_PIXMAP_SCANOUT 0x40000000 struct nouveau_pixmap { struct nouveau_bo *bo; |