From 2d69721ae87f8c317faee09d1374d6c6ecaedd1d Mon Sep 17 00:00:00 2001 From: Dave Airlie Date: Oct 23 2008 07:12:07 +0000 Subject: - limit VRAM usage in driver - not perfect but a good start --- diff --git a/radeon-modeset.patch b/radeon-modeset.patch index 12d033b..c25993d 100644 --- a/radeon-modeset.patch +++ b/radeon-modeset.patch @@ -1,3 +1,15 @@ +commit 3a29ac76d724c9a0ed6f4c2b832178594db94a0a +Author: Dave Airlie +Date: Thu Oct 23 17:05:12 2008 +1000 + + radeon: really rough effort at vram limit setting + +commit dddb524ded5b4b3b663cf332a97899b24134974e +Author: Dave Airlie +Date: Thu Oct 23 17:04:51 2008 +1000 + + radeon: this shouldn't fail but it did once while debugging so patch up + commit fe706004af67894eb7cf661ebd42305a754f3381 Author: Dave Airlie Date: Thu Oct 23 10:43:09 2008 +1000 @@ -577,7 +589,7 @@ index d65a3e4..ff54329 100644 + radeon_dri_bufmgr.h diff --git a/src/drmmode_display.c b/src/drmmode_display.c new file mode 100644 -index 0000000..1d04ddb +index 0000000..7ac30f8 --- /dev/null +++ b/src/drmmode_display.c @@ -0,0 +1,771 @@ @@ -748,7 +760,7 @@ index 0000000..1d04ddb + + dest_fb = drmModeGetFB(drmmode->fd, dest_id); + src_fb = drmModeGetFB(drmmode->fd, src_id); -+ if (src_fb == NULL) { ++ if (src_fb == NULL || dest_fb == NULL) { + ErrorF("failed to get old fb, id %d\n", src_id); + return; + } @@ -2356,10 +2368,10 @@ index 0000000..0d79b58 +#endif diff --git a/src/radeon_bufmgr_gem.c b/src/radeon_bufmgr_gem.c new file mode 100644 -index 0000000..3a82645 +index 0000000..48f941d --- /dev/null +++ b/src/radeon_bufmgr_gem.c -@@ -0,0 +1,426 @@ +@@ -0,0 +1,474 @@ +/************************************************************************** + * + * Copyright © 2007-2008 Red Hat Inc. @@ -2435,7 +2447,10 @@ index 0000000..3a82645 + struct _dri_bo_gem *next; + struct _dri_bo_gem *reloc_next; + int in_vram; /* have we migrated this bo to VRAM ever */ ++ int pinned; + int touched; ++ int space_accounted; ++ +} dri_bo_gem; + +typedef struct _dri_bufmgr_gem { @@ -2443,6 +2458,10 @@ index 0000000..3a82645 + struct radeon_bufmgr radeon_bufmgr; + int fd; + struct _dri_bo_gem *reloc_head; ++ uint32_t vram_limit; ++ uint32_t vram_write_used, gart_write_used; ++ uint32_t read_used; ++ +} dri_bufmgr_gem; + +static dri_bo * @@ -2603,6 +2622,7 @@ index 0000000..3a82645 + bo_gem->bo.bufmgr = bufmgr; + bo_gem->name = 0; + bo_gem->refcount = 1; ++ bo_gem->pinned = 1; + bo_gem->gem_handle = handle; + + return &bo_gem->bo; @@ -2691,7 +2711,8 @@ index 0000000..3a82645 + ret = ioctl(bufmgr_gem->fd, DRM_IOCTL_RADEON_GEM_PIN, &pin); + if (ret != 0) + return -1; -+ ++ ++ gem_bo->pinned = 1; + return 0; +} + @@ -2704,6 +2725,7 @@ index 0000000..3a82645 + + unpin.handle = gem_bo->gem_handle; + ioctl(bufmgr_gem->fd, DRM_IOCTL_RADEON_GEM_UNPIN, &unpin); ++ gem_bo->pinned = 0; +} + + @@ -2714,6 +2736,33 @@ index 0000000..3a82645 + return gem_bo->gem_handle; +} + ++static int radeon_gem_bufmgr_check_aperture_space(dri_bo *buf, uint32_t read_domains, uint32_t write_domain) ++{ ++ dri_bufmgr_gem *bufmgr_gem = (dri_bufmgr_gem *)buf->bufmgr; ++ dri_bo_gem *gem_bo = (dri_bo_gem *)buf; ++ ++ if (gem_bo->pinned) ++ return 0; ++ ++ if (gem_bo->space_accounted == 1) ++ return 0; ++ ++ if (write_domain == RADEON_GEM_DOMAIN_VRAM) { ++ bufmgr_gem->vram_write_used += buf->size; ++ } else { ++ bufmgr_gem->read_used += buf->size; ++ } ++ ++ if (bufmgr_gem->vram_write_used > bufmgr_gem->vram_limit) { ++ bufmgr_gem->vram_write_used = 0; ++ return -1; ++ } ++ ++ gem_bo->space_accounted = 1; ++ ++ return 0; ++} ++ +/** + * Initializes the GEM buffer manager, which is just a thin wrapper + * around the GEM allocator. @@ -2743,6 +2792,7 @@ index 0000000..3a82645 + //bufmgr_gem->bufmgr.bo_wait_rendering = radeon_bufmgr_gem_wait_rendering; + bufmgr_gem->radeon_bufmgr.emit_reloc = radeon_bufmgr_gem_emit_reloc; + bufmgr_gem->bufmgr.get_handle = radeon_gem_bufmgr_get_handle; ++ bufmgr_gem->bufmgr.check_aperture_space = radeon_gem_bufmgr_check_aperture_space; + bufmgr_gem->bufmgr.debug = 0; + return &bufmgr_gem->bufmgr; +} @@ -2752,7 +2802,6 @@ index 0000000..3a82645 +{ + dri_bufmgr_gem *bufmgr_gem = (dri_bufmgr_gem *)bufmgr; + struct _dri_bo_gem *trav, *prev; -+ + if (!bufmgr_gem->reloc_head) + return; + @@ -2763,10 +2812,13 @@ index 0000000..3a82645 + + prev->reloc_count = 0; + prev->reloc_next = NULL; ++ prev->space_accounted = 0; + dri_bo_unreference(&prev->bo); + } + bufmgr_gem->reloc_head = NULL; -+ ++ bufmgr_gem->read_used = 0; ++ bufmgr_gem->vram_write_used = 0; ++ +} + + @@ -2786,12 +2838,20 @@ index 0000000..3a82645 + + return gem_bo->touched; +} ++ ++void radeon_bufmgr_gem_set_vram_limit(dri_bufmgr *bufmgr, uint32_t vram_limit) ++{ ++ dri_bufmgr_gem *bufmgr_gem = (dri_bufmgr_gem *)bufmgr; ++ ++ ErrorF("setting vram limit to %d\n", vram_limit); ++ bufmgr_gem->vram_limit = vram_limit; ++} diff --git a/src/radeon_bufmgr_gem.h b/src/radeon_bufmgr_gem.h new file mode 100644 -index 0000000..f7fc757 +index 0000000..93ed653 --- /dev/null +++ b/src/radeon_bufmgr_gem.h -@@ -0,0 +1,14 @@ +@@ -0,0 +1,15 @@ +#ifndef RADEON_BUFMGR_GEM_H +#define RADEON_BUFMGR_GEM_H + @@ -2805,6 +2865,7 @@ index 0000000..f7fc757 +void radeon_bufmgr_unpin(dri_bo *buf); +uint32_t radeon_bufmgr_get_handle(dri_bo *buf); +int radeon_bufmgr_gem_has_references(dri_bo *buf); ++void radeon_bufmgr_gem_set_vram_limit(dri_bufmgr *bufmgr, uint32_t vram_limit); +#endif diff --git a/src/radeon_commonfuncs.c b/src/radeon_commonfuncs.c index dba197e..10d146e 100644 @@ -3631,7 +3692,7 @@ index 5542d2b..a4e8dea 100644 +} diff --git a/src/radeon_dri_bufmgr.c b/src/radeon_dri_bufmgr.c new file mode 100644 -index 0000000..2ba2951 +index 0000000..12263c3 --- /dev/null +++ b/src/radeon_dri_bufmgr.c @@ -0,0 +1,174 @@ @@ -3790,9 +3851,9 @@ index 0000000..2ba2951 +} + +int -+dri_bufmgr_check_aperture_space(dri_bo *bo) ++dri_bufmgr_check_aperture_space(dri_bo *bo, uint32_t read_domains, uint32_t write_domain) +{ -+ return bo->bufmgr->check_aperture_space(bo); ++ return bo->bufmgr->check_aperture_space(bo, read_domains, write_domain); +} + +int dri_bo_pin(dri_bo *bo, int domain) @@ -3811,7 +3872,7 @@ index 0000000..2ba2951 +} diff --git a/src/radeon_dri_bufmgr.h b/src/radeon_dri_bufmgr.h new file mode 100644 -index 0000000..a2b8a4f +index 0000000..dd61237 --- /dev/null +++ b/src/radeon_dri_bufmgr.h @@ -0,0 +1,270 @@ @@ -3993,7 +4054,7 @@ index 0000000..a2b8a4f + + void (*post_submit)(dri_bo *batch_buf, dri_fence **fence); + -+ int (*check_aperture_space)(dri_bo *bo); ++ int (*check_aperture_space)(dri_bo *bo, uint32_t read_domains, uint32_t write_domain); + + int (*pin)(dri_bo *bo, int domain); + void (*unpin)(dri_bo *bo); @@ -4039,7 +4100,7 @@ index 0000000..a2b8a4f +void *dri_process_relocs(dri_bo *batch_buf, uint32_t *count); +void dri_post_process_relocs(dri_bo *batch_buf); +void dri_post_submit(dri_bo *batch_buf, dri_fence **last_fence); -+int dri_bufmgr_check_aperture_space(dri_bo *bo); ++int dri_bufmgr_check_aperture_space(dri_bo *bo, uint32_t read_domains, uint32_t write_domain); + +int dri_bo_pin(dri_bo *bo, int domain); +void dri_bo_unpin(dri_bo *bo); @@ -6141,10 +6202,10 @@ index 0f86fdd..77a15c9 100644 } #endif diff --git a/src/radeon_exa_funcs.c b/src/radeon_exa_funcs.c -index 62224d0..5200fa3 100644 +index 62224d0..4c97c35 100644 --- a/src/radeon_exa_funcs.c +++ b/src/radeon_exa_funcs.c -@@ -74,21 +74,69 @@ FUNC_NAME(RADEONSync)(ScreenPtr pScreen, int marker) +@@ -74,21 +74,71 @@ FUNC_NAME(RADEONSync)(ScreenPtr pScreen, int marker) ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum]; RADEONInfoPtr info = RADEONPTR(pScrn); @@ -6212,10 +6273,12 @@ index 62224d0..5200fa3 100644 RINFO_FROM_SCREEN(pPix->drawable.pScreen); uint32_t datatype, dst_pitch_offset; + struct radeon_exa_pixmap_priv *driver_priv; ++ int ret; ++ int retry_count = 0; ACCEL_PREAMBLE(); TRACE; -@@ -97,25 +145,35 @@ FUNC_NAME(RADEONPrepareSolid)(PixmapPtr pPix, int alu, Pixel pm, Pixel fg) +@@ -97,25 +147,49 @@ FUNC_NAME(RADEONPrepareSolid)(PixmapPtr pPix, int alu, Pixel pm, Pixel fg) RADEON_FALLBACK(("24bpp unsupported\n")); if (!RADEONGetDatatypeBpp(pPix->drawable.bitsPerPixel, &datatype)) RADEON_FALLBACK(("RADEONGetDatatypeBpp failed\n")); @@ -6223,6 +6286,20 @@ index 62224d0..5200fa3 100644 if (!RADEONGetPixmapOffsetPitch(pPix, &dst_pitch_offset)) - RADEON_FALLBACK(("RADEONGetPixmapOffsetPitch failed\n")); + RADEON_FALLBACK(("RADEONGetPixmapOffsetPitch failed\n")); ++ ++ ++ if (info->new_cs) { ++ retry: ++ driver_priv = exaGetPixmapDriverPrivate(pPix); ++ ret = dri_bufmgr_check_aperture_space(driver_priv->bo, 0, RADEON_GEM_DOMAIN_VRAM); ++ if (ret) { ++ RADEONCPFlushIndirect(pScrn, 1); ++ retry_count++; ++ if (retry_count == 2) ++ RADEON_FALLBACK(("Not enough Video RAM\n")); ++ goto retry; ++ } ++ } RADEON_SWITCH_TO_2D(); @@ -6266,7 +6343,7 @@ index 62224d0..5200fa3 100644 return TRUE; } -@@ -148,8 +206,10 @@ FUNC_NAME(RADEONDoneSolid)(PixmapPtr pPix) +@@ -148,8 +222,10 @@ FUNC_NAME(RADEONDoneSolid)(PixmapPtr pPix) OUT_ACCEL_REG(RADEON_WAIT_UNTIL, RADEON_WAIT_2D_IDLECLEAN | RADEON_WAIT_DMA_GUI_IDLE); FINISH_ACCEL(); @@ -6277,7 +6354,7 @@ index 62224d0..5200fa3 100644 void FUNC_NAME(RADEONDoPrepareCopy)(ScrnInfoPtr pScrn, uint32_t src_pitch_offset, uint32_t dst_pitch_offset, uint32_t datatype, int rop, -@@ -160,23 +220,28 @@ FUNC_NAME(RADEONDoPrepareCopy)(ScrnInfoPtr pScrn, uint32_t src_pitch_offset, +@@ -160,23 +236,28 @@ FUNC_NAME(RADEONDoPrepareCopy)(ScrnInfoPtr pScrn, uint32_t src_pitch_offset, RADEON_SWITCH_TO_2D(); @@ -6323,16 +6400,18 @@ index 62224d0..5200fa3 100644 } static Bool -@@ -187,7 +252,7 @@ FUNC_NAME(RADEONPrepareCopy)(PixmapPtr pSrc, PixmapPtr pDst, +@@ -187,7 +268,9 @@ FUNC_NAME(RADEONPrepareCopy)(PixmapPtr pSrc, PixmapPtr pDst, { RINFO_FROM_SCREEN(pDst->drawable.pScreen); uint32_t datatype, src_pitch_offset, dst_pitch_offset; - + struct radeon_exa_pixmap_priv *driver_priv; ++ int ret; ++ int retry_count = 0; TRACE; info->accel_state->xdir = xdir; -@@ -197,10 +262,19 @@ FUNC_NAME(RADEONPrepareCopy)(PixmapPtr pSrc, PixmapPtr pDst, +@@ -197,10 +280,40 @@ FUNC_NAME(RADEONPrepareCopy)(PixmapPtr pSrc, PixmapPtr pDst, RADEON_FALLBACK(("24bpp unsupported")); if (!RADEONGetDatatypeBpp(pDst->drawable.bitsPerPixel, &datatype)) RADEON_FALLBACK(("RADEONGetDatatypeBpp failed\n")); @@ -6344,17 +6423,38 @@ index 62224d0..5200fa3 100644 - RADEON_FALLBACK(("RADEONGetPixmapOffsetPitch dest failed\n")); + RADEON_FALLBACK(("RADEONGetPixmapOffsetPitch dest failed\n")); + -+ driver_priv = exaGetPixmapDriverPrivate(pSrc); -+ if (driver_priv) -+ info->state_2d.src_bo = driver_priv->bo; ++ retry: ++ if (info->new_cs) { ++ driver_priv = exaGetPixmapDriverPrivate(pSrc); ++ if (driver_priv) { ++ ret = dri_bufmgr_check_aperture_space(driver_priv->bo, RADEON_GEM_DOMAIN_GTT | RADEON_GEM_DOMAIN_VRAM, 0); ++ if (ret) { ++ RADEONCPFlushIndirect(pScrn, 1); ++ retry_count++; ++ if (retry_count == 2) ++ RADEON_FALLBACK(("Not enough Video RAM\n")); ++ goto retry; ++ } ++ info->state_2d.src_bo = driver_priv->bo; + -+ driver_priv = exaGetPixmapDriverPrivate(pDst); -+ if (driver_priv) -+ info->state_2d.dst_bo = driver_priv->bo; ++ driver_priv = exaGetPixmapDriverPrivate(pDst); ++ if (driver_priv) { ++ ret = dri_bufmgr_check_aperture_space(driver_priv->bo, 0, RADEON_GEM_DOMAIN_VRAM); ++ if (ret) { ++ RADEONCPFlushIndirect(pScrn, 1); ++ retry_count++; ++ if (retry_count == 2) ++ RADEON_FALLBACK(("Not enough Video RAM\n")); ++ goto retry; ++ } ++ info->state_2d.dst_bo = driver_priv->bo; ++ } ++ } ++ } FUNC_NAME(RADEONDoPrepareCopy)(pScrn, src_pitch_offset, dst_pitch_offset, datatype, rop, planemask); -@@ -250,6 +324,8 @@ FUNC_NAME(RADEONDoneCopy)(PixmapPtr pDst) +@@ -250,6 +363,8 @@ FUNC_NAME(RADEONDoneCopy)(PixmapPtr pDst) OUT_ACCEL_REG(RADEON_WAIT_UNTIL, RADEON_WAIT_2D_IDLECLEAN | RADEON_WAIT_DMA_GUI_IDLE); FINISH_ACCEL(); @@ -6363,7 +6463,7 @@ index 62224d0..5200fa3 100644 } static Bool -@@ -260,6 +336,8 @@ FUNC_NAME(RADEONUploadToScreen)(PixmapPtr pDst, int x, int y, int w, int h, +@@ -260,6 +375,8 @@ FUNC_NAME(RADEONUploadToScreen)(PixmapPtr pDst, int x, int y, int w, int h, uint8_t *dst = info->FB + exaGetPixmapOffset(pDst); unsigned int dst_pitch = exaGetPixmapPitch(pDst); unsigned int bpp = pDst->drawable.bitsPerPixel; @@ -6372,7 +6472,7 @@ index 62224d0..5200fa3 100644 #ifdef ACCEL_CP unsigned int hpass; uint32_t buf_pitch, dst_pitch_off; -@@ -276,10 +354,45 @@ FUNC_NAME(RADEONUploadToScreen)(PixmapPtr pDst, int x, int y, int w, int h, +@@ -276,10 +393,45 @@ FUNC_NAME(RADEONUploadToScreen)(PixmapPtr pDst, int x, int y, int w, int h, if (bpp < 8) return FALSE; @@ -6421,7 +6521,7 @@ index 62224d0..5200fa3 100644 int cpp = bpp / 8; ACCEL_PREAMBLE(); -@@ -294,9 +407,10 @@ FUNC_NAME(RADEONUploadToScreen)(PixmapPtr pDst, int x, int y, int w, int h, +@@ -294,9 +446,10 @@ FUNC_NAME(RADEONUploadToScreen)(PixmapPtr pDst, int x, int y, int w, int h, exaMarkSync(pDst->drawable.pScreen); return TRUE; @@ -6434,7 +6534,7 @@ index 62224d0..5200fa3 100644 /* Do we need that sync here ? probably not .... */ exaWaitSync(pDst->drawable.pScreen); -@@ -335,14 +449,20 @@ FUNC_NAME(RADEONUploadToScreen)(PixmapPtr pDst, int x, int y, int w, int h, +@@ -335,14 +488,20 @@ FUNC_NAME(RADEONUploadToScreen)(PixmapPtr pDst, int x, int y, int w, int h, #ifdef ACCEL_CP /* Emit blit with arbitrary source and destination offsets and pitches */ static void @@ -6457,7 +6557,7 @@ index 62224d0..5200fa3 100644 OUT_ACCEL_REG(RADEON_DP_GUI_MASTER_CNTL, RADEON_GMC_DST_PITCH_OFFSET_CNTL | RADEON_GMC_SRC_PITCH_OFFSET_CNTL | -@@ -353,8 +473,14 @@ RADEONBlitChunk(ScrnInfoPtr pScrn, uint32_t datatype, uint32_t src_pitch_offset, +@@ -353,8 +512,14 @@ RADEONBlitChunk(ScrnInfoPtr pScrn, uint32_t datatype, uint32_t src_pitch_offset, RADEON_DP_SRC_SOURCE_MEMORY | RADEON_GMC_CLR_CMP_CNTL_DIS | RADEON_GMC_WR_MSK_DIS); @@ -6472,7 +6572,7 @@ index 62224d0..5200fa3 100644 OUT_ACCEL_REG(RADEON_SRC_Y_X, (srcY << 16) | srcX); OUT_ACCEL_REG(RADEON_DST_Y_X, (dstY << 16) | dstX); OUT_ACCEL_REG(RADEON_DST_HEIGHT_WIDTH, (h << 16) | w); -@@ -365,6 +491,104 @@ RADEONBlitChunk(ScrnInfoPtr pScrn, uint32_t datatype, uint32_t src_pitch_offset, +@@ -365,6 +530,104 @@ RADEONBlitChunk(ScrnInfoPtr pScrn, uint32_t datatype, uint32_t src_pitch_offset, RADEON_WAIT_2D_IDLECLEAN | RADEON_WAIT_DMA_GUI_IDLE); FINISH_ACCEL(); } @@ -6577,7 +6677,7 @@ index 62224d0..5200fa3 100644 #endif static Bool -@@ -389,12 +613,16 @@ FUNC_NAME(RADEONDownloadFromScreen)(PixmapPtr pSrc, int x, int y, int w, int h, +@@ -389,12 +652,16 @@ FUNC_NAME(RADEONDownloadFromScreen)(PixmapPtr pSrc, int x, int y, int w, int h, TRACE; #ifdef ACCEL_CP @@ -6595,7 +6695,7 @@ index 62224d0..5200fa3 100644 RADEONGetPixmapOffsetPitch(pSrc, &src_pitch_offset) && (scratch = RADEONCPGetBuffer(pScrn))) { -@@ -409,7 +637,8 @@ FUNC_NAME(RADEONDownloadFromScreen)(PixmapPtr pSrc, int x, int y, int w, int h, +@@ -409,7 +676,8 @@ FUNC_NAME(RADEONDownloadFromScreen)(PixmapPtr pSrc, int x, int y, int w, int h, RADEON_SWITCH_TO_2D(); /* Kick the first blit as early as possible */ @@ -6605,7 +6705,7 @@ index 62224d0..5200fa3 100644 x, y, 0, 0, w, hpass); FLUSH_RING(); -@@ -436,7 +665,8 @@ FUNC_NAME(RADEONDownloadFromScreen)(PixmapPtr pSrc, int x, int y, int w, int h, +@@ -436,7 +704,8 @@ FUNC_NAME(RADEONDownloadFromScreen)(PixmapPtr pSrc, int x, int y, int w, int h, /* Prepare next blit if anything's left */ if (hpass) { scratch_off = scratch->total/2 - scratch_off; @@ -6615,7 +6715,7 @@ index 62224d0..5200fa3 100644 x, y, 0, 0, w, hpass); } -@@ -543,14 +773,17 @@ Bool FUNC_NAME(RADEONDrawInit)(ScreenPtr pScreen) +@@ -543,14 +812,17 @@ Bool FUNC_NAME(RADEONDrawInit)(ScreenPtr pScreen) info->accel_state->exa->UploadToScreen = FUNC_NAME(RADEONUploadToScreen); info->accel_state->exa->DownloadFromScreen = FUNC_NAME(RADEONDownloadFromScreen); @@ -6636,7 +6736,7 @@ index 62224d0..5200fa3 100644 #ifdef RENDER if (info->RenderAccel) { -@@ -560,7 +793,7 @@ Bool FUNC_NAME(RADEONDrawInit)(ScreenPtr pScreen) +@@ -560,7 +832,7 @@ Bool FUNC_NAME(RADEONDrawInit)(ScreenPtr pScreen) else if (IS_R300_3D || IS_R500_3D) { if ((info->ChipFamily < CHIP_FAMILY_RS400) #ifdef XF86DRI @@ -6645,7 +6745,7 @@ index 62224d0..5200fa3 100644 #endif ) { xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Render acceleration " -@@ -595,6 +828,16 @@ Bool FUNC_NAME(RADEONDrawInit)(ScreenPtr pScreen) +@@ -595,6 +867,16 @@ Bool FUNC_NAME(RADEONDrawInit)(ScreenPtr pScreen) } #endif @@ -6663,7 +6763,7 @@ index 62224d0..5200fa3 100644 xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Setting EXA maxPitchBytes\n"); diff --git a/src/radeon_exa_render.c b/src/radeon_exa_render.c -index 97199ae..863d213 100644 +index 97199ae..72c095c 100644 --- a/src/radeon_exa_render.c +++ b/src/radeon_exa_render.c @@ -355,12 +355,14 @@ static Bool FUNC_NAME(R100TextureSetup)(PicturePtr pPict, PixmapPtr pPix, @@ -6949,16 +7049,68 @@ index 97199ae..863d213 100644 if (!pPict->repeat) OUT_ACCEL_REG(R300_TX_BORDER_COLOR_0 + (unit * 4), 0); FINISH_ACCEL(); -@@ -1184,6 +1267,8 @@ static Bool FUNC_NAME(R300PrepareComposite)(int op, PicturePtr pSrcPicture, +@@ -1173,6 +1256,7 @@ static Bool R300CheckComposite(int op, PicturePtr pSrcPicture, PicturePtr pMaskP + return TRUE; + + } ++ + #endif /* ONLY_ONCE */ + + static Bool FUNC_NAME(R300PrepareComposite)(int op, PicturePtr pSrcPicture, +@@ -1184,10 +1268,52 @@ static Bool FUNC_NAME(R300PrepareComposite)(int op, PicturePtr pSrcPicture, uint32_t txenable, colorpitch; uint32_t blendcntl; int pixel_shift; -+ int qwords; ++ int qwords, ret; ++ int retry_count = 0; + struct radeon_exa_pixmap_priv *driver_priv; ACCEL_PREAMBLE(); TRACE; -@@ -1201,7 +1286,7 @@ static Bool FUNC_NAME(R300PrepareComposite)(int op, PicturePtr pSrcPicture, + ++ retry: ++ if (info->new_cs) { ++ driver_priv = exaGetPixmapDriverPrivate(pSrc); ++ ret = dri_bufmgr_check_aperture_space(driver_priv->bo, RADEON_GEM_DOMAIN_GTT | RADEON_GEM_DOMAIN_VRAM, 0); ++ if (ret) { ++ RADEONCPFlushIndirect(pScrn, 1); ++ retry_count++; ++ if (retry_count == 2) ++ RADEON_FALLBACK(("Not enough Video RAM\n")); ++ goto retry; ++ } ++ ++ if (pMask) { ++ driver_priv = exaGetPixmapDriverPrivate(pMask); ++ ret = dri_bufmgr_check_aperture_space(driver_priv->bo, RADEON_GEM_DOMAIN_GTT | RADEON_GEM_DOMAIN_VRAM, 0); ++ if (ret) { ++ RADEONCPFlushIndirect(pScrn, 1); ++ retry_count++; ++ if (retry_count == 2) ++ RADEON_FALLBACK(("Not enough Video RAM\n")); ++ goto retry; ++ } ++ } ++ ++ driver_priv = exaGetPixmapDriverPrivate(pDst); ++ if (driver_priv) { ++ ret = dri_bufmgr_check_aperture_space(driver_priv->bo, 0, RADEON_GEM_DOMAIN_VRAM); ++ if (ret) { ++ RADEONCPFlushIndirect(pScrn, 1); ++ retry_count++; ++ if (retry_count == 2) ++ RADEON_FALLBACK(("Not enough Video RAM\n")); ++ goto retry; ++ } ++ } ++ } ++ ++ ++ + if (!info->accel_state->XInited3D) + RADEONInit3DEngine(pScrn); + +@@ -1201,7 +1327,7 @@ static Bool FUNC_NAME(R300PrepareComposite)(int op, PicturePtr pSrcPicture, pixel_shift = pDst->drawable.bitsPerPixel >> 4; @@ -6967,7 +7119,7 @@ index 97199ae..863d213 100644 dst_pitch = exaGetPixmapPitch(pDst); colorpitch = dst_pitch >> pixel_shift; -@@ -1210,7 +1295,7 @@ static Bool FUNC_NAME(R300PrepareComposite)(int op, PicturePtr pSrcPicture, +@@ -1210,7 +1336,7 @@ static Bool FUNC_NAME(R300PrepareComposite)(int op, PicturePtr pSrcPicture, colorpitch |= dst_format; @@ -6976,7 +7128,7 @@ index 97199ae..863d213 100644 RADEON_FALLBACK(("Bad destination offset 0x%x\n", (int)dst_offset)); if (((dst_pitch >> pixel_shift) & 0x7) != 0) RADEON_FALLBACK(("Bad destination pitch 0x%x\n", (int)dst_pitch)); -@@ -1829,9 +1914,18 @@ static Bool FUNC_NAME(R300PrepareComposite)(int op, PicturePtr pSrcPicture, +@@ -1829,9 +1955,18 @@ static Bool FUNC_NAME(R300PrepareComposite)(int op, PicturePtr pSrcPicture, FINISH_ACCEL(); } @@ -7035,16 +7187,17 @@ index 2a9ee94..0423571 100644 ExaOffscreenArea *area = mem_struct; diff --git a/src/radeon_memory.c b/src/radeon_memory.c new file mode 100644 -index 0000000..c2915b6 +index 0000000..94ff656 --- /dev/null +++ b/src/radeon_memory.c -@@ -0,0 +1,405 @@ +@@ -0,0 +1,407 @@ + +#include +#include +#include +#include "radeon.h" +#include "radeon_drm.h" ++#include "radeon_bufmgr_gem.h" + +Bool +radeon_bind_memory(ScrnInfoPtr pScrn, struct radeon_memory *mem) @@ -7405,6 +7558,7 @@ index 0000000..c2915b6 + if (info->drm_mode_setting) { + drmmode_set_fb(pScrn, &info->drmmode, pScrn->virtualX, RADEON_ALIGN(pScrn->virtualY, 16), stride, info->mm.front_buffer->kernel_bo_handle); + } ++ radeon_bufmgr_gem_set_vram_limit(info->bufmgr, remain_size_bytes / 2); + return TRUE; +} + diff --git a/xorg-x11-drv-ati.spec b/xorg-x11-drv-ati.spec index c889024..60f03d7 100644 --- a/xorg-x11-drv-ati.spec +++ b/xorg-x11-drv-ati.spec @@ -5,7 +5,7 @@ Summary: Xorg X11 ati video driver Name: xorg-x11-drv-ati Version: 6.9.0 -Release: 30%{?dist} +Release: 31%{?dist} URL: http://www.x.org License: MIT Group: User Interface/X Hardware Support @@ -72,6 +72,9 @@ rm -rf $RPM_BUILD_ROOT %{_mandir}/man4/radeon.4* %changelog +* Thu Oct 23 2008 Dave Airlie 6.9.0-31 +- limit VRAM usage in driver - not perfect but a good start + * Thu Oct 23 2008 Dave Airlie 6.9.0-30 - fix some bad memory allocations