Rework the video memory allocation.

The previous allocator worked in multiple passes, with (at least) one of
setting up allocations, another to attempt to adjust those for tiling, and
then a pass to set up the offsets and fix them in memory.

The new allocator is simpler, allocating memory immediately if possible,
setting up tiling up front, and choosing offsets immediately.  AGP memory
is only allocated to back actual memory used, saving some memory that would
have been allocated for padding previous. It will also allow dynamic freeing
and reallocation of memory, which will be useful for framebuffer resizing.
This commit is contained in:
Eric Anholt 2007-02-22 10:41:09 -08:00
parent a61a6b1db6
commit d3ac440e12
12 changed files with 1208 additions and 1797 deletions

View File

@ -488,6 +488,8 @@ SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
#define I915G_FENCE_SIZE_32M 0x00000500
#define I915G_FENCE_SIZE_64M 0x00000600
#define I915G_FENCE_SIZE_128M 0x00000700
#define I965_FENCE_X_MAJOR 0x00000000
#define I965_FENCE_Y_MAJOR 0x00000002
#define FENCE_PITCH_1 0x00000000
#define FENCE_PITCH_2 0x00000010
#define FENCE_PITCH_4 0x00000020

View File

@ -113,40 +113,58 @@ typedef CARD8(*I830ReadIndexedByteFunc)(I830Ptr pI830, IOADDRESS addr,
typedef void (*I830WriteByteFunc)(I830Ptr pI830, IOADDRESS addr, CARD8 value);
typedef CARD8(*I830ReadByteFunc)(I830Ptr pI830, IOADDRESS addr);
/* Linear region allocated in framebuffer. */
typedef struct _I830MemPool *I830MemPoolPtr;
typedef struct _I830MemRange *I830MemRangePtr;
typedef struct _I830MemRange {
long Start;
long End;
long Size;
unsigned long Physical;
unsigned long Offset; /* Offset of AGP-allocated portion */
unsigned long Alignment;
int Key;
I830MemPoolPtr Pool;
} I830MemRange;
/** Record of a linear allocation in the aperture. */
typedef struct _i830_memory i830_memory;
struct _i830_memory {
/** Offset of the allocation in card VM */
unsigned long offset;
/** End of the allocation in card VM */
unsigned long end;
/**
* Requested size of the allocation: doesn't count padding.
*
* Any bound memory will cover offset to (offset + size).
*/
unsigned long size;
/**
* Physical (or more properly, bus) address of the allocation.
* Only set if requested during allocation.
*/
unsigned long bus_addr;
/** AGP memory handle */
int key;
/**
* Whether or not the AGP memory (if any) is currently bound.
*/
Bool bound;
/**
* Offset that the AGP-allocated memory (if any) is to be bound to.
*
* This is either @offset or pI830->stolen_size
*/
unsigned long agp_offset;
typedef struct _I830MemPool {
I830MemRange Total;
I830MemRange Free;
I830MemRange Fixed;
I830MemRange Allocated;
} I830MemPool;
/** Description of the allocation, for logging */
char *name;
/** @{
* Memory allocator linked list pointers
*/
i830_memory *next;
i830_memory *prev;
/** @} */
};
typedef struct {
int tail_mask;
I830MemRange mem;
i830_memory *mem;
unsigned char *virtual_start;
int head;
int tail;
int space;
} I830RingBuffer;
typedef struct {
unsigned int Fence[FENCE_NEW_NR * 2];
} I830RegRec, *I830RegPtr;
typedef struct {
int lastInstance;
int refCount;
@ -206,8 +224,8 @@ typedef struct _I830CrtcPrivateRec {
ExaOffscreenArea *rotate_mem_exa;
#endif
I830MemRange cursor_mem;
I830MemRange cursor_mem_argb;
i830_memory *cursor_mem;
i830_memory *cursor_mem_argb;
} I830CrtcPrivateRec, *I830CrtcPrivatePtr;
#define I830CrtcPrivate(c) ((I830CrtcPrivatePtr) (c)->driver_private)
@ -249,36 +267,26 @@ typedef struct _I830Rec {
/* These are set in PreInit and never changed. */
long FbMapSize;
long TotalVideoRam;
I830MemRange StolenMemory; /* pre-allocated memory */
/* These change according to what has been allocated. */
long FreeMemory;
I830MemRange MemoryAperture;
I830MemPool StolenPool;
long allocatedMemory;
i830_memory *memory_list; /**< Linked list of video memory allocations */
long stolen_size; /**< bytes of pre-bound stolen memory */
int gtt_acquired; /**< whether we currently own the AGP */
/* Regions allocated either from the above pools, or from agpgart. */
/* for single and dual head configurations */
I830MemRange FrontBuffer;
I830MemRange FrontBuffer2;
I830MemRange Scratch;
I830MemRange Scratch2;
i830_memory *front_buffer;
i830_memory *front_buffer_2;
i830_memory *xaa_scratch;
i830_memory *xaa_scratch_2;
#ifdef I830_USE_EXA
I830MemRange Offscreen;
I830MemRange EXAStateMem; /* specific exa state for G965 */
i830_memory *exa_offscreen;
i830_memory *exa_965_state;
#endif
/* Regions allocated either from the above pools, or from agpgart. */
I830RingBuffer *LpRing;
#if REMAP_RESERVED
I830MemRange Dummy;
#endif
#ifdef I830_XV
/* For Xvideo */
I830MemRange *OverlayMem;
I830MemRange LinearMem;
i830_memory *overlay_regs;
i830_memory *xaa_linear;
#endif
unsigned long LinearAlloc;
XF86ModReqInfo shadowReq; /* to test for later libshadow */
@ -288,11 +296,13 @@ typedef struct _I830Rec {
CreateScreenResourcesProcPtr CreateScreenResources;
int *used3D;
I830MemRange ContextMem;
i830_memory *logical_context;
#ifdef XF86DRI
I830MemRange BackBuffer;
I830MemRange DepthBuffer;
I830MemRange TexMem;
i830_memory *back_buffer;
i830_memory *depth_buffer;
i830_memory *textures; /**< Compatibility texture memory */
i830_memory *memory_manager; /**< DRI memory manager aperture */
int TexGranularity;
int drmMinor;
Bool have3DWindows;
@ -330,13 +340,21 @@ typedef struct _I830Rec {
unsigned int BR[20];
int GttBound;
unsigned char **ScanlineColorExpandBuffers;
int NumScanlineColorExpandBuffers;
int nextColorExpandBuf;
I830RegRec ModeReg;
/**
* Values to be programmed into the fence registers.
*
* Pre-965, this is a list of FENCE_NR (8) CARD32 registers that
* contain their start, size, and pitch. On the 965, it is a list of
* FENCE_NEW_NR CARD32s for the start and pitch fields (low 32 bits) of
* the fence registers followed by FENCE_NEW_NR CARD32s for the end fields
* (high 32 bits) of the fence registers.
*/
unsigned int fence[FENCE_NEW_NR * 2];
unsigned int next_fence;
Bool useEXA;
Bool noAccel;
@ -407,7 +425,6 @@ typedef struct _I830Rec {
/* Broken-out options. */
OptionInfoPtr Options;
/* Stolen memory support */
Bool StolenOnly;
Bool swfSaved;
@ -499,7 +516,6 @@ typedef struct _I830Rec {
} I830Rec;
#define I830PTR(p) ((I830Ptr)((p)->driverPrivate))
#define I830REGPTR(p) (&(I830PTR(p)->ModeReg))
#define I830_SELECT_FRONT 0
#define I830_SELECT_BACK 1
@ -528,9 +544,6 @@ extern void i830_crtc_dpms_video(xf86CrtcPtr crtc, Bool on);
#ifdef XF86DRI
extern Bool I830Allocate3DMemory(ScrnInfoPtr pScrn, const int flags);
extern Bool I830AllocateBackBuffer(ScrnInfoPtr pScrn, const int flags);
extern Bool I830AllocateDepthBuffer(ScrnInfoPtr pScrn, const int flags);
extern Bool I830AllocateTextureMemory(ScrnInfoPtr pScrn, const int flags);
extern void I830SetupMemoryTiling(ScrnInfoPtr pScrn);
extern Bool I830DRIScreenInit(ScreenPtr pScreen);
extern Bool I830CheckDRIAvailable(ScrnInfoPtr pScrn);
@ -561,26 +574,17 @@ extern void I830SetupForSolidFill(ScrnInfoPtr pScrn, int color, int rop,
extern void I830SubsequentSolidFillRect(ScrnInfoPtr pScrn, int x, int y,
int w, int h);
extern void I830ResetAllocations(ScrnInfoPtr pScrn, const int flags);
Bool i830_allocator_init(ScrnInfoPtr pScrn, unsigned long offset,
unsigned long size);
void i830_describe_allocations(ScrnInfoPtr pScrn, int verbosity,
const char *prefix);
void i830_reset_allocations(ScrnInfoPtr pScrn);
extern long I830CheckAvailableMemory(ScrnInfoPtr pScrn);
extern long I830GetExcessMemoryAllocations(ScrnInfoPtr pScrn);
extern Bool I830Allocate2DMemory(ScrnInfoPtr pScrn, const int flags);
extern Bool I830DoPoolAllocation(ScrnInfoPtr pScrn, I830MemPool *pool);
extern Bool I830FixupOffsets(ScrnInfoPtr pScrn);
extern Bool I830BindAGPMemory(ScrnInfoPtr pScrn);
extern Bool I830UnbindAGPMemory(ScrnInfoPtr pScrn);
extern unsigned long I830AllocVidMem(ScrnInfoPtr pScrn, I830MemRange *result,
I830MemPool *pool, long size,
unsigned long alignment, int flags);
extern void I830FreeVidMem(ScrnInfoPtr pScrn, I830MemRange *range);
Bool i830_allocate_2d_memory(ScrnInfoPtr pScrn, const int flags);
Bool i830_allocate_3d_memory(ScrnInfoPtr pScrn, const int flags);
extern void I830PrintAllRegisters(I830RegPtr i830Reg);
extern void I830ReadAllRegisters(I830Ptr pI830, I830RegPtr i830Reg);
extern void I830ChangeFrontbuffer(ScrnInfoPtr pScrn,int buffer);
extern Bool I830IsPrimary(ScrnInfoPtr pScrn);
extern Bool I830FixOffset(ScrnInfoPtr pScrn, I830MemRange *mem);
extern Bool I830I2CInit(ScrnInfoPtr pScrn, I2CBusPtr *bus_ptr, int i2c_reg,
char *name);
@ -607,6 +611,9 @@ extern void i830MarkSync(ScrnInfoPtr pScrn);
extern void i830WaitSync(ScrnInfoPtr pScrn);
/* i830_memory.c */
Bool i830_bind_all_memory(ScrnInfoPtr pScrn);
Bool i830_unbind_all_memory(ScrnInfoPtr pScrn);
Bool I830BindAGPMemory(ScrnInfoPtr pScrn);
Bool I830UnbindAGPMemory(ScrnInfoPtr pScrn);
#ifdef I830_USE_XAA
@ -656,18 +663,8 @@ extern const int I830PatternROP[16];
extern const int I830CopyROP[16];
/* Flags for memory allocation function */
#define FROM_ANYWHERE 0x00000000
#define FROM_POOL_ONLY 0x00000001
#define FROM_NEW_ONLY 0x00000002
#define FROM_MASK 0x0000000f
#define ALLOCATE_AT_TOP 0x00000010
#define ALLOCATE_AT_BOTTOM 0x00000020
#define FORCE_GAPS 0x00000040
#define NEED_PHYSICAL_ADDR 0x00000100
#define ALIGN_BOTH_ENDS 0x00000200
#define FORCE_LOW 0x00000400
#define NEED_PHYSICAL_ADDR 0x00000001
#define ALIGN_BOTH_ENDS 0x00000002
#define ALLOC_NO_TILING 0x00001000
#define ALLOC_INITIAL 0x00002000

View File

@ -117,7 +117,7 @@ I830WaitLpRing(ScrnInfoPtr pScrn, int n, int timeout_millis)
ring->space = ring->head - (ring->tail + 8);
if (ring->space < 0)
ring->space += ring->mem.Size;
ring->space += ring->mem->size;
iters++;
now = GetTimeInMillis();
@ -195,9 +195,9 @@ I830Sync(ScrnInfoPtr pScrn)
ADVANCE_LP_RING();
}
I830WaitLpRing(pScrn, pI830->LpRing->mem.Size - 8, 0);
I830WaitLpRing(pScrn, pI830->LpRing->mem->size - 8, 0);
pI830->LpRing->space = pI830->LpRing->mem.Size - 8;
pI830->LpRing->space = pI830->LpRing->mem->size - 8;
pI830->nextColorExpandBuf = 0;
}
@ -226,10 +226,10 @@ I830SelectBuffer(ScrnInfoPtr pScrn, int buffer)
switch (buffer) {
#ifdef XF86DRI
case I830_SELECT_BACK:
pI830->bufferOffset = pI830->BackBuffer.Start;
pI830->bufferOffset = pI830->back_buffer->offset;
break;
case I830_SELECT_DEPTH:
pI830->bufferOffset = pI830->DepthBuffer.Start;
pI830->bufferOffset = pI830->depth_buffer->offset;
break;
#endif
default:
@ -252,7 +252,7 @@ I830RefreshRing(ScrnInfoPtr pScrn)
pI830->LpRing->tail = INREG(LP_RING + RING_TAIL);
pI830->LpRing->space = pI830->LpRing->head - (pI830->LpRing->tail + 8);
if (pI830->LpRing->space < 0)
pI830->LpRing->space += pI830->LpRing->mem.Size;
pI830->LpRing->space += pI830->LpRing->mem->size;
i830MarkSync(pScrn);
}

View File

@ -88,20 +88,20 @@ I830SetPipeCursorBase (xf86CrtcPtr crtc)
I830Ptr pI830 = I830PTR(pScrn);
xf86CrtcConfigPtr xf86_config = XF86_CRTC_CONFIG_PTR(pScrn);
int cursor_base = (pipe == 0 ? CURSOR_A_BASE : CURSOR_B_BASE);
I830MemRange *cursor_mem;
i830_memory *cursor_mem;
if (pipe >= xf86_config->num_crtc)
FatalError("Bad pipe number for cursor base setting\n");
if (pI830->CursorIsARGB)
cursor_mem = &intel_crtc->cursor_mem_argb;
cursor_mem = intel_crtc->cursor_mem_argb;
else
cursor_mem = &intel_crtc->cursor_mem;
cursor_mem = intel_crtc->cursor_mem;
if (pI830->CursorNeedsPhysical) {
OUTREG(cursor_base, cursor_mem->Physical);
OUTREG(cursor_base, cursor_mem->bus_addr);
} else {
OUTREG(cursor_base, cursor_mem->Start);
OUTREG(cursor_base, cursor_mem->offset);
}
}
@ -281,7 +281,7 @@ I830CRTCLoadCursorImage(xf86CrtcPtr crtc, unsigned char *src)
ScrnInfoPtr pScrn = crtc->scrn;
I830Ptr pI830 = I830PTR(pScrn);
I830CrtcPrivatePtr intel_crtc = crtc->driver_private;
CARD8 *pcurs = (CARD8 *) (pI830->FbBase + intel_crtc->cursor_mem.Start);
CARD8 *pcurs = (CARD8 *) (pI830->FbBase + intel_crtc->cursor_mem->offset);
int x, y;
DPRINTF(PFX, "I830LoadCursorImage\n");
@ -372,7 +372,7 @@ static Bool I830UseHWCursorARGB (ScreenPtr pScreen, CursorPtr pCurs)
for (i = 0; i < xf86_config->num_crtc; i++) {
I830CrtcPrivatePtr intel_crtc = xf86_config->crtc[i]->driver_private;
if (!intel_crtc->cursor_mem_argb.Start)
if (!intel_crtc->cursor_mem_argb->offset)
return FALSE;
}
@ -389,7 +389,8 @@ static void I830CRTCLoadCursorARGB (xf86CrtcPtr crtc, CursorPtr pCurs)
{
I830Ptr pI830 = I830PTR(crtc->scrn);
I830CrtcPrivatePtr intel_crtc = crtc->driver_private;
CARD32 *dst = (CARD32 *) (pI830->FbBase + intel_crtc->cursor_mem_argb.Start);
CARD32 *dst = (CARD32 *) (pI830->FbBase +
intel_crtc->cursor_mem_argb->offset);
CARD32 *image = (CARD32 *)pCurs->bits->argb;
int x, y, w, h;

View File

@ -345,10 +345,10 @@ i830PipeSetBase(xf86CrtcPtr crtc, int x, int y)
if (crtc->rotatedData != NULL) {
Start = (char *)crtc->rotatedData - (char *)pI830->FbBase;
} else if (I830IsPrimary(pScrn)) {
Start = pI830->FrontBuffer.Start;
Start = pI830->front_buffer->offset;
} else {
I830Ptr pI8301 = I830PTR(pI830->entityPrivate->pScrn_1);
Start = pI8301->FrontBuffer2.Start;
Start = pI8301->front_buffer_2->offset;
}
if (IS_I965G(pI830)) {
@ -1012,7 +1012,7 @@ i830_crtc_shadow_allocate (xf86CrtcPtr crtc, int width, int height)
"Couldn't allocate shadow memory for rotated CRTC\n");
return NULL;
}
rotate_offset = pI830->FrontBuffer.Start +
rotate_offset = pI830->front_buffer->offset +
intel_crtc->rotate_mem_xaa->offset * pI830->cpp;
}
#endif /* I830_USE_XAA */

View File

@ -145,17 +145,17 @@ I830InitDma(ScrnInfoPtr pScrn)
memset(&info, 0, sizeof(drmI830Init));
info.func = I830_INIT_DMA;
info.ring_start = ring->mem.Start + pI830->LinearAddr;
info.ring_end = ring->mem.End + pI830->LinearAddr;
info.ring_size = ring->mem.Size;
info.ring_start = ring->mem->offset + pI830->LinearAddr;
info.ring_end = ring->mem->end + pI830->LinearAddr;
info.ring_size = ring->mem->size;
info.mmio_offset = (unsigned int)pI830DRI->regs;
info.sarea_priv_offset = sizeof(XF86DRISAREARec);
info.front_offset = pI830->FrontBuffer.Start;
info.back_offset = pI830->BackBuffer.Start;
info.depth_offset = pI830->DepthBuffer.Start;
info.front_offset = pI830->front_buffer->offset;
info.back_offset = pI830->back_buffer->offset;
info.depth_offset = pI830->depth_buffer->offset;
info.w = pScrn->virtualX;
info.h = pScrn->virtualY;
info.pitch = pI830->displayWidth;
@ -509,7 +509,7 @@ I830DRIScreenInit(ScreenPtr pScreen)
pDRIInfo->ddxDriverPatchVersion = I830_PATCHLEVEL;
#if 1 /* Remove this soon - see bug 5714 */
pDRIInfo->frameBufferPhysicalAddress = (char *) pI830->LinearAddr +
pI830->FrontBuffer.Start;
pI830->front_buffer->offset;
pDRIInfo->frameBufferSize = ROUND_TO_PAGE(pScrn->displayWidth *
pScrn->virtualY * pI830->cpp);
#else
@ -829,8 +829,8 @@ I830DRIDoMappings(ScreenPtr pScreen)
(int)pI830DRI->regs);
if (drmAddMap(pI830->drmSubFD,
(drm_handle_t)pI830->LpRing->mem.Start + pI830->LinearAddr,
pI830->LpRing->mem.Size, DRM_AGP, 0,
(drm_handle_t)pI830->LpRing->mem->offset + pI830->LinearAddr,
pI830->LpRing->mem->size, DRM_AGP, 0,
(drmAddress) &pI830->ring_map) < 0) {
xf86DrvMsg(pScreen->myNum, X_ERROR,
"[drm] drmAddMap(ring_map) failed. Disabling DRI\n");
@ -1325,10 +1325,10 @@ I830DRIShadowUpdate (ScreenPtr pScreen, shadowBufPtr pBuf)
OUT_RING(br13);
OUT_RING((pbox->y1 << 16) | pbox->x1);
OUT_RING((pbox->y2 << 16) | pbox->x2);
OUT_RING(pI830->BackBuffer.Start);
OUT_RING(pI830->back_buffer->offset);
OUT_RING((pbox->y1 << 16) | pbox->x1);
OUT_RING(br13 & 0xffff);
OUT_RING(pI830->FrontBuffer.Start);
OUT_RING(pI830->front_buffer->offset);
ADVANCE_LP_RING();
}
}
@ -1360,10 +1360,10 @@ I830EnablePageFlip(ScreenPtr pScreen)
OUT_RING(br13);
OUT_RING(0);
OUT_RING((pScrn->virtualY << 16) | pScrn->virtualX);
OUT_RING(pI830->BackBuffer.Start);
OUT_RING(pI830->back_buffer->offset);
OUT_RING(0);
OUT_RING(br13 & 0xffff);
OUT_RING(pI830->FrontBuffer.Start);
OUT_RING(pI830->front_buffer->offset);
ADVANCE_LP_RING();
pSAREAPriv->pf_active = 1;
@ -1448,8 +1448,8 @@ I830UpdateDRIBuffers(ScrnInfoPtr pScrn, drmI830Sarea *sarea)
sarea->depth_tiled = pI830->depth_tiled;
sarea->rotated_tiled = FALSE;
sarea->front_offset = pI830->FrontBuffer.Start;
/* Don't use FrontBuffer.Size here as it includes the pixmap cache area
sarea->front_offset = pI830->front_buffer->offset;
/* Don't use front_buffer->size here as it includes the pixmap cache area
* Instead, calculate the entire framebuffer.
*/
sarea->front_size = pI830->displayWidth * pScrn->virtualY * pI830->cpp;
@ -1460,12 +1460,12 @@ I830UpdateDRIBuffers(ScrnInfoPtr pScrn, drmI830Sarea *sarea)
sarea->width = pScreen->width;
sarea->height = pScreen->height;
sarea->back_offset = pI830->BackBuffer.Start;
sarea->back_size = pI830->BackBuffer.Size;
sarea->depth_offset = pI830->DepthBuffer.Start;
sarea->depth_size = pI830->DepthBuffer.Size;
sarea->tex_offset = pI830->TexMem.Start;
sarea->tex_size = pI830->TexMem.Size;
sarea->back_offset = pI830->back_buffer->offset;
sarea->back_size = pI830->back_buffer->size;
sarea->depth_offset = pI830->depth_buffer->offset;
sarea->depth_size = pI830->depth_buffer->size;
sarea->tex_offset = pI830->textures->offset;
sarea->tex_size = pI830->textures->size;
sarea->log_tex_granularity = pI830->TexGranularity;
sarea->pitch = pScrn->displayWidth;
sarea->virtualX = pScrn->virtualX;

View File

@ -534,7 +534,7 @@ I830MapMem(ScrnInfoPtr pScrn)
return FALSE;
if (I830IsPrimary(pScrn))
pI830->LpRing->virtual_start = pI830->FbBase + pI830->LpRing->mem.Start;
pI830->LpRing->virtual_start = pI830->FbBase + pI830->LpRing->mem->offset;
return TRUE;
}
@ -755,9 +755,6 @@ PreInitCleanup(ScrnInfoPtr pScrn)
if (pI830->LpRing)
xfree(pI830->LpRing);
pI830->LpRing = NULL;
if (pI830->OverlayMem)
xfree(pI830->OverlayMem);
pI830->OverlayMem = NULL;
if (pI830->overlayOn)
xfree(pI830->overlayOn);
pI830->overlayOn = NULL;
@ -836,6 +833,13 @@ I830ReduceMMSize(ScrnInfoPtr pScrn, unsigned long newSize,
}
#endif
/**
* This is called per zaphod head (so usually just once) to do initialization
* before the Screen is created.
*
* This code generally covers probing, module loading, option handling,
* initial memory layout measurement, card mapping, and RandR setup.
*/
static Bool
I830PreInit(ScrnInfoPtr pScrn, int flags)
{
@ -846,12 +850,12 @@ I830PreInit(ScrnInfoPtr pScrn, int flags)
rgb defaultWeight = { 0, 0, 0 };
EntityInfoPtr pEnt;
I830EntPtr pI830Ent = NULL;
int mem;
int sys_mem;
int flags24;
int i;
char *s;
pointer pVBEModule = NULL;
Bool enable;
Bool enable, allocation_done;
const char *chipname;
int num_pipe;
int max_width, max_height;
@ -1187,41 +1191,6 @@ I830PreInit(ScrnInfoPtr pScrn, int flags)
xf86DrvMsg(pScrn->scrnIndex, X_INFO, "%d display pipe%s available.\n",
num_pipe, num_pipe > 1 ? "s" : "");
/*
* Get the pre-allocated (stolen) memory size.
*/
pI830->StolenMemory.Size = I830DetectMemory(pScrn);
pI830->StolenMemory.Start = 0;
pI830->StolenMemory.End = pI830->StolenMemory.Size;
/* Find the maximum amount of agpgart memory available. */
if (I830IsPrimary(pScrn)) {
mem = I830CheckAvailableMemory(pScrn);
pI830->StolenOnly = FALSE;
} else {
/* videoRam isn't used on the second head, but faked */
mem = pI830->entityPrivate->pScrn_1->videoRam;
pI830->StolenOnly = TRUE;
}
if (mem <= 0) {
if (pI830->StolenMemory.Size <= 0) {
/* Shouldn't happen. */
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"/dev/agpgart is either not available, or no memory "
"is available\nfor allocation, "
"and no pre-allocated memory is available.\n");
PreInitCleanup(pScrn);
return FALSE;
}
xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
"/dev/agpgart is either not available, or no memory "
"is available\nfor allocation. "
"Using pre-allocated memory only.\n");
mem = 0;
pI830->StolenOnly = TRUE;
}
if (xf86ReturnOptValBool(pI830->Options, OPTION_NOACCEL, FALSE)) {
pI830->noAccel = TRUE;
}
@ -1358,8 +1327,6 @@ I830PreInit(ScrnInfoPtr pScrn, int flags)
}
RestoreHWState(pScrn);
pScrn->displayWidth = (pScrn->virtualX + 63) & ~63;
/* XXX This should go away, replaced by xf86Crtc.c support for it */
pI830->rotation = RR_Rotate_0;
@ -1384,12 +1351,21 @@ I830PreInit(ScrnInfoPtr pScrn, int flags)
} else
pI830->checkDevices = FALSE;
pScrn->displayWidth = (pScrn->virtualX + 63) & ~63;
pI830->stolen_size = I830DetectMemory(pScrn);
/*
* The "VideoRam" config file parameter specifies the maximum amount of
* memory that will be used/allocated. When not present, we allow the
* driver to allocate as much memory as it wishes to satisfy its
* allocations, but if agpgart support isn't available (StolenOnly == TRUE),
* it gets limited to the amount of pre-allocated ("stolen") memory.
* allocations, but if agpgart support isn't available, it gets limited
* to the amount of pre-allocated ("stolen") memory.
*
* Note that in using this value for allocator initialization, we're
* limiting aperture allocation to the VideoRam option, rather than limiting
* actual memory allocation, so alignment and things will cause less than
* VideoRam to be actually used.
*/
if (!pI830->pEnt->device->videoRam) {
from = X_DEFAULT;
@ -1399,6 +1375,40 @@ I830PreInit(ScrnInfoPtr pScrn, int flags)
pScrn->videoRam = pI830->pEnt->device->videoRam;
}
sys_mem = I830CheckAvailableMemory(pScrn);
if (sys_mem == -1) {
if (pScrn->videoRam > pI830->stolen_size / KB(1)) {
xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
"/dev/agpgart is either not available, or no memory "
"is available\nfor allocation. "
"Using pre-allocated memory only.\n");
pScrn->videoRam = pI830->stolen_size / KB(1);
}
pI830->StolenOnly = TRUE;
} else {
if (sys_mem + (pI830->stolen_size / 1024) < pScrn->videoRam) {
pScrn->videoRam = sys_mem + (pI830->stolen_size / 1024);
from = X_PROBED;
if (sys_mem + (pI830->stolen_size / 1024) <
pI830->pEnt->device->videoRam)
{
xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
"VideoRAM reduced to %d kByte "
"(limited to available sysmem)\n", pScrn->videoRam);
}
}
}
if (pScrn->videoRam > pI830->FbMapSize / 1024) {
pScrn->videoRam = pI830->FbMapSize / 1024;
if (pI830->FbMapSize / 1024 < pI830->pEnt->device->videoRam) {
xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
"VideoRam reduced to %d kByte (limited to aperture "
"size)\n",
pScrn->videoRam);
}
}
/* Make sure it's on a page boundary */
if (pScrn->videoRam & 3) {
xf86DrvMsg(pScrn->scrnIndex, X_WARNING, "VideoRam reduced to %d KB "
@ -1407,46 +1417,16 @@ I830PreInit(ScrnInfoPtr pScrn, int flags)
pScrn->videoRam &= ~3;
}
DPRINTF(PFX,
"Available memory: %dk\n"
"Requested memory: %dk\n", mem, pScrn->videoRam);
if (mem + (pI830->StolenMemory.Size / 1024) < pScrn->videoRam) {
pScrn->videoRam = mem + (pI830->StolenMemory.Size / 1024);
from = X_PROBED;
if (mem + (pI830->StolenMemory.Size / 1024) <
pI830->pEnt->device->videoRam) {
xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
"VideoRAM reduced to %d kByte "
"(limited to available sysmem)\n", pScrn->videoRam);
}
if (!i830_allocator_init(pScrn, 0, pScrn->videoRam * KB(1))) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"Couldn't initialize video memory allocator\n");
PreInitCleanup(pScrn);
return FALSE;
}
if (pScrn->videoRam > pI830->FbMapSize / 1024) {
pScrn->videoRam = pI830->FbMapSize / 1024;
if (pI830->FbMapSize / 1024 < pI830->pEnt->device->videoRam)
xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
"VideoRam reduced to %d kByte (limited to aperture size)\n",
pScrn->videoRam);
}
xf86DrvMsg(pScrn->scrnIndex, X_PROBED,
"Pre-allocated VideoRam: %ld kByte\n",
pI830->StolenMemory.Size / 1024);
xf86DrvMsg(pScrn->scrnIndex, from, "Potential VideoRam: %d kByte\n",
pScrn->videoRam);
pI830->TotalVideoRam = KB(pScrn->videoRam);
/*
* If the requested videoRam amount is less than the stolen memory size,
* reduce the stolen memory size accordingly.
*/
if (pI830->StolenMemory.Size > pI830->TotalVideoRam) {
pI830->StolenMemory.Size = pI830->TotalVideoRam;
pI830->StolenMemory.End = pI830->TotalVideoRam;
}
xf86DrvMsg(pScrn->scrnIndex,
pI830->pEnt->device->videoRam ? X_CONFIG : X_DEFAULT,
"VideoRam: %d KB\n", pScrn->videoRam);
if (xf86GetOptValInteger(pI830->Options, OPTION_CACHE_LINES,
&(pI830->CacheLines))) {
@ -1502,12 +1482,10 @@ I830PreInit(ScrnInfoPtr pScrn, int flags)
/* Alloc our pointers for the primary head */
if (I830IsPrimary(pScrn)) {
pI830->LpRing = xalloc(sizeof(I830RingBuffer));
pI830->OverlayMem = xalloc(sizeof(I830MemRange));
pI830->LpRing = xcalloc(1, sizeof(I830RingBuffer));
pI830->overlayOn = xalloc(sizeof(Bool));
pI830->used3D = xalloc(sizeof(int));
if (!pI830->LpRing ||
!pI830->OverlayMem || !pI830->overlayOn || !pI830->used3D) {
if (!pI830->LpRing || !pI830->overlayOn || !pI830->used3D) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"Could not allocate primary data structures.\n");
PreInitCleanup(pScrn);
@ -1527,9 +1505,6 @@ I830PreInit(ScrnInfoPtr pScrn, int flags)
if (IS_I965G(pI830))
pI830->CursorNeedsPhysical = FALSE;
/* Force ring buffer to be in low memory for all chipsets */
pI830->NeedRingBufferLow = TRUE;
/*
* XXX If we knew the pre-initialised GTT format for certain, we could
* probably figure out the physical address even in the StolenOnly case.
@ -1548,21 +1523,6 @@ I830PreInit(ScrnInfoPtr pScrn, int flags)
pI830->SWCursor = TRUE;
}
/*
* Reduce the maximum videoram available for video modes by the ring buffer,
* minimum scratch space and HW cursor amounts.
*/
if (!pI830->SWCursor) {
pScrn->videoRam -= (HWCURSOR_SIZE / 1024);
pScrn->videoRam -= (HWCURSOR_SIZE_ARGB / 1024);
}
if (!pI830->XvDisabled)
pScrn->videoRam -= (OVERLAY_SIZE / 1024);
if (!pI830->noAccel) {
pScrn->videoRam -= (PRIMARY_RINGBUFFER_SIZE / 1024);
pScrn->videoRam -= (MIN_SCRATCH_BUFFER_SIZE / 1024);
}
if (!xf86RandR12PreInit (pScrn))
{
xf86DrvMsg(pScrn->scrnIndex, X_ERROR, "RandR initialization failure\n");
@ -1579,23 +1539,19 @@ I830PreInit(ScrnInfoPtr pScrn, int flags)
pI830->disableTiling = FALSE;
#if defined(XF86DRI)
/*
* If DRI is potentially usable, check if there is enough memory available
* for it, and if there's also enough to allow tiling to be enabled.
*/
#if defined(XF86DRI)
if (!I830CheckDRIAvailable(pScrn)) {
pI830->directRenderingDisabled = TRUE;
pI830->mmSize = 0;
} else if (pScrn->videoRam > pI830->FbMapSize / 1024 - pI830->mmSize) {
I830ReduceMMSize(pScrn, pI830->FbMapSize - KB(pScrn->videoRam),
"to make room for video memory");
}
if (I830IsPrimary(pScrn) && !pI830->directRenderingDisabled) {
int savedDisplayWidth = pScrn->displayWidth;
int memNeeded = 0;
Bool tiled = FALSE;
#ifdef I830_XV
@ -1612,12 +1568,14 @@ I830PreInit(ScrnInfoPtr pScrn, int flags)
~(tile_pixels - 1);
tiled = TRUE;
} else {
/* Good pitches to allow tiling. Don't care about pitches < 1024. */
/* Good pitches to allow tiling. Don't care about pitches < 1024
* pixels.
*/
static const int pitches[] = {
KB(1),
KB(2),
KB(4),
KB(8),
1024,
2048,
4096,
8192,
0
};
@ -1630,120 +1588,72 @@ I830PreInit(ScrnInfoPtr pScrn, int flags)
}
}
allocation_done = FALSE;
/*
* If the displayWidth is a tilable pitch, test if there's enough
* memory available to enable tiling.
*/
savedMMSize = pI830->mmSize;
if (tiled) {
retry_dryrun:
I830ResetAllocations(pScrn, 0);
if (I830Allocate2DMemory(pScrn, ALLOCATE_DRY_RUN | ALLOC_INITIAL) &&
I830Allocate3DMemory(pScrn, ALLOCATE_DRY_RUN)) {
memNeeded = I830GetExcessMemoryAllocations(pScrn);
if (memNeeded > 0 || pI830->MemoryAperture.Size < 0) {
if (memNeeded > 0) {
xf86DrvMsg(pScrn->scrnIndex, X_INFO,
"%d kBytes additional video memory is "
"required to\n\tenable tiling mode for DRI.\n",
(memNeeded + 1023) / 1024);
}
if (pI830->MemoryAperture.Size < 0) {
if (KB(pI830->mmSize) > I830_MM_MINPAGES * GTT_PAGE_SIZE) {
I830ReduceMMSize(pScrn, I830_MM_MINPAGES * GTT_PAGE_SIZE,
"to make room in AGP aperture for tiling.");
goto retry_dryrun;
}
/* XXX */
xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
"Allocation with DRI tiling enabled would "
"exceed the\n"
"\tmemory aperture size (%ld kB) by %ld kB.\n"
"\tReduce VideoRam amount to avoid this!\n",
pI830->FbMapSize / 1024,
-pI830->MemoryAperture.Size / 1024);
}
pScrn->displayWidth = savedDisplayWidth;
pI830->allowPageFlip = FALSE;
} else if (pScrn->displayWidth != savedDisplayWidth) {
xf86DrvMsg(pScrn->scrnIndex, X_INFO,
"Increasing the scanline pitch to allow tiling mode "
"(%d -> %d).\n",
savedDisplayWidth, pScrn->displayWidth);
retry_dryrun:
i830_reset_allocations(pScrn);
if (!i830_allocate_2d_memory(pScrn,
ALLOCATE_DRY_RUN | ALLOC_INITIAL) ||
!i830_allocate_3d_memory(pScrn, ALLOCATE_DRY_RUN))
{
/* Failure to set up allocations, so try reducing the DRI memory
* manager's size if we haven't yet.
*/
if (KB(pI830->mmSize) > I830_MM_MINPAGES * GTT_PAGE_SIZE) {
I830ReduceMMSize(pScrn, I830_MM_MINPAGES * GTT_PAGE_SIZE,
"to make room for tiling.");
goto retry_dryrun;
}
} else {
memNeeded = 0;
xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
"Unexpected dry run allocation failure (1).\n");
/* Otherwise, disable tiling. */
pScrn->displayWidth = savedDisplayWidth;
pI830->allowPageFlip = FALSE;
} else if (pScrn->displayWidth != savedDisplayWidth) {
xf86DrvMsg(pScrn->scrnIndex, X_INFO,
"Increasing the scanline pitch to allow tiling mode "
"(%d -> %d).\n",
savedDisplayWidth, pScrn->displayWidth);
allocation_done = TRUE;
}
}
if (memNeeded > 0 || pI830->MemoryAperture.Size < 0) {
if (!allocation_done) {
/*
* Tiling can't be enabled. Check if there's enough memory for DRI
* without tiling.
*/
pI830->mmSize = savedMMSize;
pI830->disableTiling = TRUE;
retry_dryrun2:
I830ResetAllocations(pScrn, 0);
if (I830Allocate2DMemory(pScrn, ALLOCATE_DRY_RUN | ALLOC_INITIAL) &&
I830Allocate3DMemory(pScrn, ALLOCATE_DRY_RUN | ALLOC_NO_TILING)) {
memNeeded = I830GetExcessMemoryAllocations(pScrn);
if (memNeeded > 0 || pI830->MemoryAperture.Size < 0) {
if (memNeeded > 0) {
xf86DrvMsg(pScrn->scrnIndex, X_INFO,
"%d kBytes additional video memory is required "
"to enable DRI.\n",
(memNeeded + 1023) / 1024);
}
if (pI830->MemoryAperture.Size < 0) {
if (KB(pI830->mmSize) > I830_MM_MINPAGES * GTT_PAGE_SIZE) {
I830ReduceMMSize(pScrn, I830_MM_MINPAGES * GTT_PAGE_SIZE,
"to save AGP aperture space for video memory.");
goto retry_dryrun2;
}
xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
"Allocation with DRI enabled would "
"exceed the\n"
"\tmemory aperture size (%ld kB) by %ld kB.\n"
"\tReduce VideoRam amount to avoid this!\n",
pI830->FbMapSize / 1024,
-pI830->MemoryAperture.Size / 1024);
}
pI830->mmSize = 0;
pI830->directRenderingDisabled = TRUE;
xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Disabling DRI.\n");
retry_dryrun2:
i830_reset_allocations(pScrn);
if (!i830_allocate_2d_memory(pScrn,
ALLOCATE_DRY_RUN | ALLOC_INITIAL) ||
!i830_allocate_3d_memory(pScrn, ALLOCATE_DRY_RUN))
{
/* Failure to set up allocations, so try reducing the DRI memory
* manager's size if we haven't yet.
*/
if (KB(pI830->mmSize) > I830_MM_MINPAGES * GTT_PAGE_SIZE) {
I830ReduceMMSize(pScrn, I830_MM_MINPAGES * GTT_PAGE_SIZE,
"to save AGP aperture space for video "
"memory.");
goto retry_dryrun2;
}
} else {
xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
"Unexpected dry run allocation failure (2).\n");
"Not enough video memory. Disabling DRI.");
pI830->mmSize = 0;
pI830->directRenderingDisabled = TRUE;
} else {
allocation_done = TRUE;
}
}
} else
#endif
pI830->disableTiling = TRUE; /* no DRI - so disableTiling */
if (pI830->pEnt->device->videoRam == 0) {
int default_videoram;
/* Now that we've sized the allocations, reduce our default VideoRam
* allocation from the aperture size to just what we need to cover our
* allocations. Only, put in some slop for alignment and such.
*/
default_videoram = pI830->StolenPool.Total.Size + pI830->allocatedMemory;
default_videoram += KB(512); /* slop */
/* align to 1MB increments */
default_videoram = (default_videoram + MB(1) - 1) / MB(1) * MB(1);
if (default_videoram < KB(pScrn->videoRam)) {
pScrn->videoRam = default_videoram / KB(1);
pI830->TotalVideoRam = KB(pScrn->videoRam);
}
}
xf86DrvMsg(pScrn->scrnIndex,
pI830->pEnt->device->videoRam ? X_CONFIG : X_DEFAULT,
"VideoRam: %d KB\n", pScrn->videoRam);
if (!IS_I965G(pI830) && pScrn->displayWidth > 2048) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"Cannot support DRI with frame buffer width > 2048.\n");
@ -1934,18 +1844,18 @@ SetFenceRegs(ScrnInfoPtr pScrn)
if (IS_I965G(pI830)) {
for (i = 0; i < FENCE_NEW_NR; i++) {
OUTREG(FENCE_NEW + i * 8, pI830->ModeReg.Fence[i]);
OUTREG(FENCE_NEW + 4 + i * 8, pI830->ModeReg.Fence[i+FENCE_NEW_NR]);
OUTREG(FENCE_NEW + i * 8, pI830->fence[i]);
OUTREG(FENCE_NEW + 4 + i * 8, pI830->fence[i+FENCE_NEW_NR]);
if (I810_DEBUG & DEBUG_VERBOSE_VGA) {
ErrorF("Fence Start Register : %x\n", pI830->ModeReg.Fence[i]);
ErrorF("Fence End Register : %x\n", pI830->ModeReg.Fence[i+FENCE_NEW_NR]);
ErrorF("Fence Start Register : %x\n", pI830->fence[i]);
ErrorF("Fence End Register : %x\n", pI830->fence[i+FENCE_NEW_NR]);
}
}
} else {
for (i = 0; i < FENCE_NR; i++) {
OUTREG(FENCE + i * 4, pI830->ModeReg.Fence[i]);
OUTREG(FENCE + i * 4, pI830->fence[i]);
if (I810_DEBUG & DEBUG_VERBOSE_VGA)
ErrorF("Fence Register : %x\n", pI830->ModeReg.Fence[i]);
ErrorF("Fence Register : %x\n", pI830->fence[i]);
}
}
}
@ -1970,25 +1880,22 @@ SetRingRegs(ScrnInfoPtr pScrn)
OUTREG(LP_RING + RING_TAIL, 0);
OUTREG(LP_RING + RING_HEAD, 0);
if ((long)(pI830->LpRing->mem.Start & I830_RING_START_MASK) !=
pI830->LpRing->mem.Start) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"I830SetRingRegs: Ring buffer start (%lx) violates its "
"mask (%x)\n", pI830->LpRing->mem.Start, I830_RING_START_MASK);
}
assert((pI830->LpRing->mem->offset & I830_RING_START_MASK) ==
pI830->LpRing->mem->offset);
/* Don't care about the old value. Reserved bits must be zero anyway. */
itemp = pI830->LpRing->mem.Start & I830_RING_START_MASK;
itemp = pI830->LpRing->mem->offset;
OUTREG(LP_RING + RING_START, itemp);
if (((pI830->LpRing->mem.Size - 4096) & I830_RING_NR_PAGES) !=
pI830->LpRing->mem.Size - 4096) {
if (((pI830->LpRing->mem->size - 4096) & I830_RING_NR_PAGES) !=
pI830->LpRing->mem->size - 4096) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"I830SetRingRegs: Ring buffer size - 4096 (%lx) violates its "
"mask (%x)\n", pI830->LpRing->mem.Size - 4096,
"mask (%x)\n", pI830->LpRing->mem->size - 4096,
I830_RING_NR_PAGES);
}
/* Don't care about the old value. Reserved bits must be zero anyway. */
itemp = (pI830->LpRing->mem.Size - 4096) & I830_RING_NR_PAGES;
itemp = (pI830->LpRing->mem->size - 4096) & I830_RING_NR_PAGES;
itemp |= (RING_NO_REPORT | RING_VALID);
OUTREG(LP_RING + RING_LEN, itemp);
I830RefreshRing(pScrn);
@ -2246,13 +2153,12 @@ static void
InitRegisterRec(ScrnInfoPtr pScrn)
{
I830Ptr pI830 = I830PTR(pScrn);
I830RegPtr i830Reg = &pI830->ModeReg;
int i;
if (!I830IsPrimary(pScrn)) return;
for (i = 0; i < 8; i++)
i830Reg->Fence[i] = 0;
pI830->fence[i] = 0;
}
static void
@ -2361,14 +2267,12 @@ IntelEmitInvarientState(ScrnInfoPtr pScrn)
}
#endif
ctx_addr = pI830->ContextMem.Start;
/* Align to a 2k boundry */
ctx_addr = ((ctx_addr + 2048 - 1) / 2048) * 2048;
ctx_addr = pI830->logical_context->offset;
assert((pI830->logical_context->offset & 2047) == 0);
{
BEGIN_LP_RING(2);
OUT_RING(MI_SET_CONTEXT);
OUT_RING(ctx_addr |
OUT_RING(pI830->logical_context->offset |
CTXT_NO_RESTORE |
CTXT_PALETTE_SAVE_DISABLE | CTXT_PALETTE_RESTORE_DISABLE);
ADVANCE_LP_RING();
@ -2525,14 +2429,11 @@ I830ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
if (I830IsPrimary(pScrn)) {
if (!pI830->LpRing)
pI830->LpRing = xalloc(sizeof(I830RingBuffer));
if (!pI830->OverlayMem)
pI830->OverlayMem = xalloc(sizeof(I830MemRange));
if (!pI830->overlayOn)
pI830->overlayOn = xalloc(sizeof(Bool));
if (!pI830->used3D)
pI830->used3D = xalloc(sizeof(int));
if (!pI830->LpRing ||
!pI830->OverlayMem || !pI830->overlayOn || !pI830->used3D) {
if (!pI830->LpRing || !pI830->overlayOn || !pI830->used3D) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"Could not allocate primary data structures.\n");
return FALSE;
@ -2546,7 +2447,7 @@ I830ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
if (!I830IsPrimary(pScrn)) {
pI8301 = I830PTR(pI830->entityPrivate->pScrn_1);
pI830->LpRing = pI8301->LpRing;
pI830->OverlayMem = pI8301->OverlayMem;
pI830->overlay_regs = pI8301->overlay_regs;
pI830->overlayOn = pI8301->overlayOn;
pI830->used3D = pI8301->used3D;
}
@ -2579,14 +2480,14 @@ I830ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
#endif
if (I830IsPrimary(pScrn)) {
I830ResetAllocations(pScrn, 0);
i830_reset_allocations(pScrn);
if (!I830Allocate2DMemory(pScrn, ALLOC_INITIAL))
if (!i830_allocate_2d_memory(pScrn, ALLOC_INITIAL))
return FALSE;
}
if (!pI830->noAccel) {
if (pI830->LpRing->mem.Size == 0) {
if (pI830->LpRing->mem->size == 0) {
xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
"Disabling acceleration because the ring buffer "
"allocation failed.\n");
@ -2601,7 +2502,7 @@ I830ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
"needs 2D acceleration.\n");
pI830->XvEnabled = FALSE;
}
if (pI830->OverlayMem->Physical == 0) {
if (pI830->overlay_regs == NULL) {
xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
"Disabling Xv because the overlay register buffer "
"allocation failed.\n");
@ -2639,8 +2540,8 @@ I830ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
if (pI830->directRenderingEnabled) {
pI830->directRenderingEnabled =
I830Allocate3DMemory(pScrn,
pI830->disableTiling ? ALLOC_NO_TILING : 0);
i830_allocate_3d_memory(pScrn,
pI830->disableTiling ? ALLOC_NO_TILING : 0);
if (!pI830->directRenderingEnabled)
I830DRICloseScreen(pScreen);
}
@ -2649,27 +2550,18 @@ I830ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
pI830->directRenderingEnabled = FALSE;
#endif
/*
/* XXX:
* After the 3D allocations have been done, see if there's any free space
* that can be added to the framebuffer allocation.
*/
if (I830IsPrimary(pScrn)) {
I830Allocate2DMemory(pScrn, 0);
DPRINTF(PFX, "assert(if(!I830DoPoolAllocation(pScrn, pI830->StolenPool)))\n");
if (!I830DoPoolAllocation(pScrn, &(pI830->StolenPool)))
return FALSE;
DPRINTF(PFX, "assert( if(!I830FixupOffsets(pScrn)) )\n");
if (!I830FixupOffsets(pScrn))
return FALSE;
i830_allocate_2d_memory(pScrn, 0);
}
i830_describe_allocations(pScrn, 1, "");
#ifdef XF86DRI
if (pI830->directRenderingEnabled) {
I830SetupMemoryTiling(pScrn);
if (pI830->directRenderingEnabled)
pI830->directRenderingEnabled = I830DRIDoMappings(pScreen);
}
#endif
DPRINTF(PFX, "assert( if(!I830MapMem(pScrn)) )\n");
@ -2679,9 +2571,9 @@ I830ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
pScrn->memPhysBase = (unsigned long)pI830->FbBase;
if (I830IsPrimary(pScrn)) {
pScrn->fbOffset = pI830->FrontBuffer.Start;
pScrn->fbOffset = pI830->front_buffer->offset;
} else {
pScrn->fbOffset = pI8301->FrontBuffer2.Start;
pScrn->fbOffset = pI8301->front_buffer_2->offset;
}
pI830->xoffset = (pScrn->fbOffset / pI830->cpp) % pScrn->displayWidth;
@ -2704,13 +2596,13 @@ I830ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
if (pI830->LinearAlloc &&
xf86InitFBManagerLinear(pScreen,
pI830->LinearMem.Offset / pI830->cpp,
pI830->LinearMem.Size / pI830->cpp))
pI830->xaa_linear->offset / pI830->cpp,
pI830->xaa_linear->size / pI830->cpp))
{
xf86DrvMsg(scrnIndex, X_INFO,
"Using %ld bytes of offscreen memory for linear "
"(offset=0x%lx)\n", pI830->LinearMem.Size,
pI830->LinearMem.Offset);
"(offset=0x%lx)\n", pI830->xaa_linear->size,
pI830->xaa_linear->offset);
}
} else {
if (!I830InitFBManager(pScreen, &(pI8301->FbMemBox2))) {
@ -2877,27 +2769,24 @@ I830ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
pI830->suspended = FALSE;
#ifdef XF86DRI_MM
if (pI830->directRenderingEnabled && (pI830->mmModeFlags & I830_KERNEL_MM)) {
unsigned long aperEnd = ROUND_DOWN_TO(pI830->FbMapSize, GTT_PAGE_SIZE)
/ GTT_PAGE_SIZE;
unsigned long aperStart = ROUND_TO(pI830->FbMapSize - KB(pI830->mmSize), GTT_PAGE_SIZE)
/ GTT_PAGE_SIZE;
if (aperEnd < aperStart || aperEnd - aperStart < I830_MM_MINPAGES) {
if (pI830->directRenderingEnabled && (pI830->mmModeFlags & I830_KERNEL_MM))
{
if (pI830->memory_manager == NULL) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"Too little AGP aperture space for DRM memory manager.\n"
"\tPlease increase AGP aperture size from BIOS configuration screen\n"
"\tor decrease the amount of video RAM using option \"VideoRam\".\n"
"\tPlease increase AGP aperture size from BIOS configuration screen.\n"
"\tDisabling DRI.\n");
pI830->directRenderingOpen = FALSE;
I830DRICloseScreen(pScreen);
pI830->directRenderingEnabled = FALSE;
} else {
#ifndef XSERVER_LIBDRM_MM
if (I830DrmMMInit(pI830->drmSubFD, aperStart, aperEnd - aperStart,
if (I830DrmMMInit(pI830->drmSubFD, pI830->memory_manager->offset,
pI830->memory_manager->size,
DRM_BO_MEM_TT)) {
#else
if (drmMMInit(pI830->drmSubFD, aperStart, aperEnd - aperStart,
if (drmMMInit(pI830->drmSubFD, pI830->memory_manager->offset,
pI830->memory_manager->size,
DRM_BO_MEM_TT)) {
#endif
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
@ -2906,12 +2795,6 @@ I830ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
pI830->directRenderingOpen = FALSE;
I830DRICloseScreen(pScreen);
pI830->directRenderingEnabled = FALSE;
} else {
xf86DrvMsg(pScrn->scrnIndex, X_INFO,
"Initialized DRM memory manager, %ld AGP pages\n"
"\tat AGP offset 0x%lx\n",
aperEnd - aperStart,
aperStart);
}
}
}
@ -2968,7 +2851,7 @@ I830LeaveVT(int scrnIndex, int flags)
if (!I830IsPrimary(pScrn)) {
I830Ptr pI8301 = I830PTR(pI830->entityPrivate->pScrn_1);
if (!pI8301->GttBound) {
if (!pI8301->gtt_acquired) {
return;
}
}
@ -3002,7 +2885,7 @@ I830LeaveVT(int scrnIndex, int flags)
i830DumpRegs (pScrn);
if (I830IsPrimary(pScrn))
I830UnbindAGPMemory(pScrn);
i830_unbind_all_memory(pScrn);
if (pI830->AccelInfoRec)
pI830->AccelInfoRec->NeedToSync = FALSE;
}
@ -3038,7 +2921,7 @@ I830EnterVT(int scrnIndex, int flags)
#endif
if (I830IsPrimary(pScrn))
if (!I830BindAGPMemory(pScrn))
if (!i830_bind_all_memory(pScrn))
return FALSE;
if (i830_check_error_state(pScrn)) {
@ -3223,8 +3106,6 @@ I830CloseScreen(int scrnIndex, ScreenPtr pScreen)
xfree(pI830->LpRing);
pI830->LpRing = NULL;
xfree(pI830->OverlayMem);
pI830->OverlayMem = NULL;
xfree(pI830->overlayOn);
pI830->overlayOn = NULL;
xfree(pI830->used3D);

View File

@ -318,8 +318,9 @@ I830EXAInit(ScreenPtr pScreen)
pI830->EXADriverPtr->exa_major = 2;
pI830->EXADriverPtr->exa_minor = 1;
pI830->EXADriverPtr->memoryBase = pI830->FbBase;
pI830->EXADriverPtr->offScreenBase = pI830->Offscreen.Start;
pI830->EXADriverPtr->memorySize = pI830->Offscreen.End;
pI830->EXADriverPtr->offScreenBase = pI830->exa_offscreen->offset;
pI830->EXADriverPtr->memorySize = pI830->exa_offscreen->offset +
pI830->exa_offscreen->size;
DPRINTF(PFX, "EXA Mem: memoryBase 0x%x, end 0x%x, offscreen base 0x%x, memorySize 0x%x\n",
pI830->EXADriverPtr->memoryBase,

File diff suppressed because it is too large Load Diff

View File

@ -184,9 +184,9 @@ void exaMoveInPixmap (PixmapPtr pPixmap);
OUT_RING(MI_OVERLAY_FLIP | MI_OVERLAY_FLIP_CONTINUE); \
} \
if (IS_I965G(pI830)) \
OUT_RING(pI830->OverlayMem->Start | OFC_UPDATE); \
OUT_RING(pI830->overlay_regs->offset | OFC_UPDATE); \
else \
OUT_RING(pI830->OverlayMem->Physical | OFC_UPDATE); \
OUT_RING(pI830->overlay_regs->bus_addr | OFC_UPDATE); \
OUT_RING(MI_WAIT_FOR_EVENT | MI_WAIT_FOR_OVERLAY_FLIP); \
OUT_RING(MI_NOOP); \
ADVANCE_LP_RING(); \
@ -202,9 +202,9 @@ void exaMoveInPixmap (PixmapPtr pPixmap);
OUT_RING(MI_NOOP); \
OUT_RING(MI_OVERLAY_FLIP | MI_OVERLAY_FLIP_OFF); \
if (IS_I965G(pI830)) \
OUT_RING(pI830->OverlayMem->Start | OFC_UPDATE); \
OUT_RING(pI830->overlay_regs->offset | OFC_UPDATE); \
else \
OUT_RING(pI830->OverlayMem->Physical | OFC_UPDATE); \
OUT_RING(pI830->overlay_regs->bus_addr | OFC_UPDATE); \
OUT_RING(MI_WAIT_FOR_EVENT | MI_WAIT_FOR_OVERLAY_FLIP); \
OUT_RING(MI_NOOP); \
ADVANCE_LP_RING(); \
@ -496,10 +496,10 @@ I830ResetVideo(ScrnInfoPtr pScrn)
I830Ptr pI830 = I830PTR(pScrn);
I830PortPrivPtr pPriv = pI830->adaptor->pPortPrivates[0].ptr;
I830OverlayRegPtr overlay =
(I830OverlayRegPtr) (pI830->FbBase + pI830->OverlayMem->Start);
(I830OverlayRegPtr) (pI830->FbBase + pI830->overlay_regs->offset);
OVERLAY_DEBUG("I830ResetVideo: base: %p, offset: 0x%lx, obase: %p\n",
pI830->FbBase, pI830->OverlayMem->Start, overlay);
pI830->FbBase, pI830->overlay_regs->offset, overlay);
/*
* Default to maximum image size in YV12
*/
@ -926,7 +926,7 @@ I830SetPortAttribute(ScrnInfoPtr pScrn,
I830PortPrivPtr pPriv = (I830PortPrivPtr) data;
I830Ptr pI830 = I830PTR(pScrn);
I830OverlayRegPtr overlay =
(I830OverlayRegPtr) (pI830->FbBase + pI830->OverlayMem->Start);
(I830OverlayRegPtr) (pI830->FbBase + pI830->overlay_regs->offset);
if (pPriv->textured) {
/* XXX: Currently the brightness/saturation attributes aren't hooked up.
@ -1553,7 +1553,7 @@ I830DisplayVideo(ScrnInfoPtr pScrn, int id, short width, short height,
I830Ptr pI830 = I830PTR(pScrn);
I830PortPrivPtr pPriv = pI830->adaptor->pPortPrivates[0].ptr;
I830OverlayRegPtr overlay =
(I830OverlayRegPtr) (pI830->FbBase + pI830->OverlayMem->Start);
(I830OverlayRegPtr) (pI830->FbBase + pI830->overlay_regs->offset);
unsigned int swidth;
unsigned int mask, shift, offsety, offsetu;
int tmp;
@ -2076,7 +2076,8 @@ I830AllocateMemory(ScrnInfoPtr pScrn, struct linear_alloc *linear, int size,
/* Converts an offset from XAA's linear allocator to an offset from the
* start of fb.
*/
#define XAA_OFFSET_TO_OFFSET(x) (pI830->FrontBuffer.Start + (x * pI830->cpp))
#define XAA_OFFSET_TO_OFFSET(x) \
(pI830->front_buffer->offset + (x * pI830->cpp))
/* The XFree86 linear allocator operates in units of screen pixels,
* sadly.
@ -2160,7 +2161,7 @@ I830PutImage(ScrnInfoPtr pScrn,
I830PortPrivPtr pPriv = (I830PortPrivPtr) data;
ScreenPtr pScreen = screenInfo.screens[pScrn->scrnIndex];
I830OverlayRegPtr overlay =
(I830OverlayRegPtr) (pI830->FbBase + pI830->OverlayMem->Start);
(I830OverlayRegPtr) (pI830->FbBase + pI830->overlay_regs->offset);
PixmapPtr pPixmap;
INT32 x1, x2, y1, y2;
int srcPitch, srcPitch2 = 0, dstPitch, destId;
@ -2700,7 +2701,7 @@ I830DisplaySurface(XF86SurfacePtr surface,
I830Ptr pI830 = I830PTR(pScrn);
I830PortPrivPtr pI830Priv = GET_PORT_PRIVATE(pScrn);
I830OverlayRegPtr overlay =
(I830OverlayRegPtr) (pI830->FbBase + pI830->OverlayMem->Start);
(I830OverlayRegPtr) (pI830->FbBase + pI830->overlay_regs->offset);
INT32 x1, y1, x2, y2;
INT32 loops = 0;
BoxRec dstBox;

View File

@ -162,20 +162,20 @@ I830XAAInit(ScreenPtr pScreen)
/* On the primary screen */
if (pI830->init == 0) {
if (pI830->Scratch.Size != 0) {
if (pI830->xaa_scratch->size != 0) {
width = ((pScrn->displayWidth + 31) & ~31) / 8;
nr_buffers = pI830->Scratch.Size / width;
ptr = pI830->FbBase + pI830->Scratch.Start;
nr_buffers = pI830->xaa_scratch->size / width;
ptr = pI830->FbBase + pI830->xaa_scratch->offset;
}
} else {
/* On the secondary screen */
I830Ptr pI8301 = I830PTR(pI830->entityPrivate->pScrn_1);
if (pI8301->Scratch2.Size != 0) {
if (pI8301->xaa_scratch_2->size != 0) {
width = ((pScrn->displayWidth + 31) & ~31) / 8;
nr_buffers = pI8301->Scratch2.Size / width;
nr_buffers = pI8301->xaa_scratch_2->size / width;
/* We have to use the primary screen's FbBase, as that's where
* we allocated Scratch2, so we get the correct pointer */
ptr = pI8301->FbBase + pI8301->Scratch2.Start;
* we allocated xaa_scratch_2, so we get the correct pointer */
ptr = pI8301->FbBase + pI8301->xaa_scratch_2->offset;
}
}
@ -279,11 +279,15 @@ CheckTiling(ScrnInfoPtr pScrn)
if (IS_I965G(pI830)) {
if (pI830->bufferOffset == pScrn->fbOffset && pI830->front_tiled == FENCE_XMAJOR)
tiled = 1;
if (pI830->bufferOffset == pI830->BackBuffer.Start && pI830->back_tiled == FENCE_XMAJOR)
if (pI830->bufferOffset == pI830->back_buffer->offset &&
pI830->back_tiled == FENCE_XMAJOR) {
tiled = 1;
}
/* not really supported as it's always YMajor tiled */
if (pI830->bufferOffset == pI830->DepthBuffer.Start && pI830->depth_tiled == FENCE_XMAJOR)
if (pI830->bufferOffset == pI830->depth_buffer->offset &&
pI830->depth_tiled == FENCE_XMAJOR) {
tiled = 1;
}
}
return tiled;
@ -600,7 +604,7 @@ I830SubsequentColorExpandScanline(ScrnInfoPtr pScrn, int bufno)
I830Ptr pI8301 = I830PTR(pI830->entityPrivate->pScrn_1);
/* We have to use the primary screen's FbBase, as that's where
* we allocated Scratch2, so we get the correct pointer */
* we allocated xaa_scratch_2, so we get the correct pointer */
pI830->BR[12] = (pI830->AccelInfoRec->ScanlineColorExpandBuffers[0] -
pI8301->FbBase);
}
@ -700,7 +704,7 @@ I830SubsequentImageWriteScanline(ScrnInfoPtr pScrn, int bufno)
I830Ptr pI8301 = I830PTR(pI830->entityPrivate->pScrn_1);
/* We have to use the primary screen's FbBase, as that's where
* we allocated Scratch2, so we get the correct pointer */
* we allocated xaa_scratch_2, so we get the correct pointer */
pI830->BR[12] = (pI830->AccelInfoRec->ScanlineColorExpandBuffers[0] -
pI8301->FbBase);
}

View File

@ -501,9 +501,9 @@ i965_prepare_composite(int op, PicturePtr pSrcPicture,
next_offset = default_color_offset + sizeof(*default_color_state);
total_state_size = next_offset;
assert(total_state_size < EXA_LINEAR_EXTRA);
assert(total_state_size < pI830->exa_965_state->size);
state_base_offset = pI830->EXAStateMem.Start;
state_base_offset = pI830->exa_965_state->offset;
state_base_offset = ALIGN(state_base_offset, 64);
state_base = (char *)(pI830->FbBase + state_base_offset);