configure.ac | 62 +++++- man/radeon.man | 26 +- src/AtomBios/CD_Operations.c | 68 ++++-- src/AtomBios/Decoder.c | 115 ++++++----- src/AtomBios/hwserv_drv.c | 14 - src/AtomBios/includes/CD_Common_Types.h | 12 + src/AtomBios/includes/CD_Definitions.h | 3 src/AtomBios/includes/CD_Structs.h | 24 ++ src/AtomBios/includes/Decoder.h | 24 ++ src/AtomBios/includes/atombios.h | 62 ++++++ src/Makefile.am | 8 src/ati_pciids_gen.h | 6 src/atombios_crtc.c | 202 +++++++++++++++++-- src/atombios_output.c | 30 +- src/legacy_crtc.c | 289 +++++++++++++--------------- src/legacy_output.c | 11 - src/pcidb/ati_pciids.csv | 10 src/radeon.h | 43 +++- src/radeon_accel.c | 26 -- src/radeon_accelfuncs.c | 40 +++ src/radeon_atombios.c | 327 +++++++++++++++++--------------- src/radeon_atomwrapper.c | 1 src/radeon_bios.c | 115 +++++++---- src/radeon_chipinfo_gen.h | 10 src/radeon_chipset_gen.h | 6 src/radeon_commonfuncs.c | 14 - src/radeon_crtc.c | 163 +++++++++++---- src/radeon_cursor.c | 16 - src/radeon_dri.c | 36 ++- src/radeon_dri.h | 7 src/radeon_driver.c | 313 ++++++++++++++++++++++-------- src/radeon_exa.c | 8 src/radeon_exa_funcs.c | 25 ++ src/radeon_exa_render.c | 55 ++--- src/radeon_output.c | 63 +++++- src/radeon_pci_chipset_gen.h | 6 src/radeon_pci_device_match_gen.h | 6 src/radeon_probe.h | 3 src/radeon_reg.h | 71 +++++- src/radeon_textured_videofuncs.c | 45 +++- src/radeon_version.h | 7 src/radeon_video.c | 55 +++-- 42 files changed, 1680 insertions(+), 747 deletions(-)
New commits: commit 1f3eee3682f3598a303c9c3accfbe01b245cacf9 Author: Alex Deucher <[EMAIL PROTECTED]> Date: Tue Jul 29 20:29:32 2008 -0400 Change prim types for exa and textured video to help avoid tearing - r1xx - switch from tri fan to rect list - r2xx/r3xx/r4xx/r5xx - switch from tri fan to quad list diff --git a/src/radeon_exa_render.c b/src/radeon_exa_render.c index 4736e4f..5d28d80 100644 --- a/src/radeon_exa_render.c +++ b/src/radeon_exa_render.c @@ -1962,9 +1962,9 @@ static void FUNC_NAME(RadeonCompositeTile)(PixmapPtr pDst, #ifdef ACCEL_CP if (info->ChipFamily < CHIP_FAMILY_R200) { - BEGIN_RING(4 * vtx_count + 3); + BEGIN_RING(3 * vtx_count + 3); OUT_RING(CP_PACKET3(RADEON_CP_PACKET3_3D_DRAW_IMMD, - 4 * vtx_count + 1)); + 3 * vtx_count + 1)); if (has_mask) OUT_RING(RADEON_CP_VC_FRMT_XY | RADEON_CP_VC_FRMT_ST0 | @@ -1972,11 +1972,11 @@ static void FUNC_NAME(RadeonCompositeTile)(PixmapPtr pDst, else OUT_RING(RADEON_CP_VC_FRMT_XY | RADEON_CP_VC_FRMT_ST0); - OUT_RING(RADEON_CP_VC_CNTL_PRIM_TYPE_TRI_FAN | + OUT_RING(RADEON_CP_VC_CNTL_PRIM_TYPE_RECT_LIST | RADEON_CP_VC_CNTL_PRIM_WALK_RING | RADEON_CP_VC_CNTL_MAOS_ENABLE | RADEON_CP_VC_CNTL_VTX_FMT_RADEON_MODE | - (4 << RADEON_CP_VC_CNTL_NUM_SHIFT)); + (3 << RADEON_CP_VC_CNTL_NUM_SHIFT)); } else { if (IS_R300_3D || IS_R500_3D) BEGIN_RING(4 * vtx_count + 4); @@ -1985,7 +1985,7 @@ static void FUNC_NAME(RadeonCompositeTile)(PixmapPtr pDst, OUT_RING(CP_PACKET3(R200_CP_PACKET3_3D_DRAW_IMMD_2, 4 * vtx_count)); - OUT_RING(RADEON_CP_VC_CNTL_PRIM_TYPE_TRI_FAN | + OUT_RING(RADEON_CP_VC_CNTL_PRIM_TYPE_QUAD_LIST | RADEON_CP_VC_CNTL_PRIM_WALK_RING | (4 << RADEON_CP_VC_CNTL_NUM_SHIFT)); } @@ -1993,25 +1993,29 @@ static void FUNC_NAME(RadeonCompositeTile)(PixmapPtr pDst, #else /* ACCEL_CP */ if (IS_R300_3D || IS_R500_3D) BEGIN_ACCEL(2 + vtx_count * 4); + else if (info->ChipFamily < CHIP_FAMILY_R200) + BEGIN_ACCEL(1 + vtx_count * 3); else BEGIN_ACCEL(1 + vtx_count * 4); if (info->ChipFamily < CHIP_FAMILY_R200) { - OUT_ACCEL_REG(RADEON_SE_VF_CNTL, (RADEON_VF_PRIM_TYPE_TRIANGLE_FAN | + OUT_ACCEL_REG(RADEON_SE_VF_CNTL, (RADEON_VF_PRIM_TYPE_RECTANGLE_LIST | RADEON_VF_PRIM_WALK_DATA | RADEON_VF_RADEON_MODE | - 4 << RADEON_VF_NUM_VERTICES_SHIFT)); + (3 << RADEON_VF_NUM_VERTICES_SHIFT))); } else { OUT_ACCEL_REG(RADEON_SE_VF_CNTL, (RADEON_VF_PRIM_TYPE_QUAD_LIST | RADEON_VF_PRIM_WALK_DATA | - 4 << RADEON_VF_NUM_VERTICES_SHIFT)); + (4 << RADEON_VF_NUM_VERTICES_SHIFT))); } #endif if (has_mask) { - VTX_OUT_MASK((float)dstX, (float)dstY, - xFixedToFloat(srcTopLeft.x) / info->texW[0], xFixedToFloat(srcTopLeft.y) / info->texH[0], - xFixedToFloat(maskTopLeft.x) / info->texW[1], xFixedToFloat(maskTopLeft.y) / info->texH[1]); + if (info->ChipFamily >= CHIP_FAMILY_R200) { + VTX_OUT_MASK((float)dstX, (float)dstY, + xFixedToFloat(srcTopLeft.x) / info->texW[0], xFixedToFloat(srcTopLeft.y) / info->texH[0], + xFixedToFloat(maskTopLeft.x) / info->texW[1], xFixedToFloat(maskTopLeft.y) / info->texH[1]); + } VTX_OUT_MASK((float)dstX, (float)(dstY + h), xFixedToFloat(srcBottomLeft.x) / info->texW[0], xFixedToFloat(srcBottomLeft.y) / info->texH[0], xFixedToFloat(maskBottomLeft.x) / info->texW[1], xFixedToFloat(maskBottomLeft.y) / info->texH[1]); @@ -2022,8 +2026,10 @@ static void FUNC_NAME(RadeonCompositeTile)(PixmapPtr pDst, xFixedToFloat(srcTopRight.x) / info->texW[0], xFixedToFloat(srcTopRight.y) / info->texH[0], xFixedToFloat(maskTopRight.x) / info->texW[1], xFixedToFloat(maskTopRight.y) / info->texH[1]); } else { - VTX_OUT((float)dstX, (float)dstY, - xFixedToFloat(srcTopLeft.x) / info->texW[0], xFixedToFloat(srcTopLeft.y) / info->texH[0]); + if (info->ChipFamily >= CHIP_FAMILY_R200) { + VTX_OUT((float)dstX, (float)dstY, + xFixedToFloat(srcTopLeft.x) / info->texW[0], xFixedToFloat(srcTopLeft.y) / info->texH[0]); + } VTX_OUT((float)dstX, (float)(dstY + h), xFixedToFloat(srcBottomLeft.x) / info->texW[0], xFixedToFloat(srcBottomLeft.y) / info->texH[0]); VTX_OUT((float)(dstX + w), (float)(dstY + h), diff --git a/src/radeon_reg.h b/src/radeon_reg.h index 60f12fc..1d35236 100644 --- a/src/radeon_reg.h +++ b/src/radeon_reg.h @@ -3189,6 +3189,7 @@ #define RADEON_CP_VC_CNTL_PRIM_TYPE_RECT_LIST 0x00000008 #define RADEON_CP_VC_CNTL_PRIM_TYPE_3VRT_POINT_LIST 0x00000009 #define RADEON_CP_VC_CNTL_PRIM_TYPE_3VRT_LINE_LIST 0x0000000a +#define RADEON_CP_VC_CNTL_PRIM_TYPE_QUAD_LIST 0x0000000d #define RADEON_CP_VC_CNTL_PRIM_WALK_IND 0x00000010 #define RADEON_CP_VC_CNTL_PRIM_WALK_LIST 0x00000020 #define RADEON_CP_VC_CNTL_PRIM_WALK_RING 0x00000030 diff --git a/src/radeon_textured_videofuncs.c b/src/radeon_textured_videofuncs.c index 98dc9a4..d39f74d 100644 --- a/src/radeon_textured_videofuncs.c +++ b/src/radeon_textured_videofuncs.c @@ -587,16 +587,16 @@ FUNC_NAME(RADEONDisplayTexturedVideo)(ScrnInfoPtr pScrn, RADEONPortPrivPtr pPriv #ifdef ACCEL_CP if (info->ChipFamily < CHIP_FAMILY_R200) { - BEGIN_RING(4 * VTX_DWORD_COUNT + 3); + BEGIN_RING(3 * VTX_DWORD_COUNT + 3); OUT_RING(CP_PACKET3(RADEON_CP_PACKET3_3D_DRAW_IMMD, - 4 * VTX_DWORD_COUNT + 1)); + 3 * VTX_DWORD_COUNT + 1)); OUT_RING(RADEON_CP_VC_FRMT_XY | RADEON_CP_VC_FRMT_ST0); - OUT_RING(RADEON_CP_VC_CNTL_PRIM_TYPE_TRI_FAN | + OUT_RING(RADEON_CP_VC_CNTL_PRIM_TYPE_RECT_LIST | RADEON_CP_VC_CNTL_PRIM_WALK_RING | RADEON_CP_VC_CNTL_MAOS_ENABLE | RADEON_CP_VC_CNTL_VTX_FMT_RADEON_MODE | - (4 << RADEON_CP_VC_CNTL_NUM_SHIFT)); + (3 << RADEON_CP_VC_CNTL_NUM_SHIFT)); } else { if (IS_R300_3D || IS_R500_3D) BEGIN_RING(4 * VTX_DWORD_COUNT + 4); @@ -604,30 +604,33 @@ FUNC_NAME(RADEONDisplayTexturedVideo)(ScrnInfoPtr pScrn, RADEONPortPrivPtr pPriv BEGIN_RING(4 * VTX_DWORD_COUNT + 2); OUT_RING(CP_PACKET3(R200_CP_PACKET3_3D_DRAW_IMMD_2, 4 * VTX_DWORD_COUNT)); - OUT_RING(RADEON_CP_VC_CNTL_PRIM_TYPE_TRI_FAN | + OUT_RING(RADEON_CP_VC_CNTL_PRIM_TYPE_QUAD_LIST | RADEON_CP_VC_CNTL_PRIM_WALK_RING | (4 << RADEON_CP_VC_CNTL_NUM_SHIFT)); } #else /* ACCEL_CP */ if (IS_R300_3D || IS_R500_3D) BEGIN_VIDEO(2 + VTX_DWORD_COUNT * 4); + else if (info->ChipFamily < CHIP_FAMILY_R200) + BEGIN_VIDEO(1 + VTX_DWORD_COUNT * 3); else BEGIN_VIDEO(1 + VTX_DWORD_COUNT * 4); if (info->ChipFamily < CHIP_FAMILY_R200) { - OUT_VIDEO_REG(RADEON_SE_VF_CNTL, (RADEON_VF_PRIM_TYPE_TRIANGLE_FAN | + OUT_VIDEO_REG(RADEON_SE_VF_CNTL, (RADEON_VF_PRIM_TYPE_RECTANGLE_LIST | RADEON_VF_PRIM_WALK_DATA | RADEON_VF_RADEON_MODE | - 4 << RADEON_VF_NUM_VERTICES_SHIFT)); + (3 << RADEON_VF_NUM_VERTICES_SHIFT))); } else { OUT_VIDEO_REG(RADEON_SE_VF_CNTL, (RADEON_VF_PRIM_TYPE_QUAD_LIST | RADEON_VF_PRIM_WALK_DATA | - 4 << RADEON_VF_NUM_VERTICES_SHIFT)); + (4 << RADEON_VF_NUM_VERTICES_SHIFT))); } #endif - - VTX_OUT((float)dstX, (float)dstY, - xFixedToFloat(srcTopLeft.x) / info->texW[0], xFixedToFloat(srcTopLeft.y) / info->texH[0]); + if (info->ChipFamily >= CHIP_FAMILY_R200) { + VTX_OUT((float)dstX, (float)dstY, + xFixedToFloat(srcTopLeft.x) / info->texW[0], xFixedToFloat(srcTopLeft.y) / info->texH[0]); + } VTX_OUT((float)dstX, (float)(dstY + dsth), xFixedToFloat(srcBottomLeft.x) / info->texW[0], xFixedToFloat(srcBottomLeft.y) / info->texH[0]); VTX_OUT((float)(dstX + dstw), (float)(dstY + dsth), commit 5b5441f8cc119db0d1e03dd35bd06015a26270dd Author: Brice Goglin <[EMAIL PROTECTED]> Date: Tue Jul 29 23:31:14 2008 +0200 Increase default GART size to 32MB on >=R300 diff --git a/src/radeon_dri.h b/src/radeon_dri.h index b1c5bbf..6e3ad62 100644 --- a/src/radeon_dri.h +++ b/src/radeon_dri.h @@ -40,6 +40,7 @@ /* DRI Driver defaults */ #define RADEON_DEFAULT_GART_SIZE 8 /* MB (must be 2^n and > 4MB) */ +#define R300_DEFAULT_GART_SIZE 32 /* MB (for R300 and above) */ #define RADEON_DEFAULT_RING_SIZE 1 /* MB (must be page aligned) */ #define RADEON_DEFAULT_BUFFER_SIZE 2 /* MB (must be page aligned) */ #define RADEON_DEFAULT_GART_TEX_SIZE 1 /* MB (must be page aligned) */ diff --git a/src/radeon_driver.c b/src/radeon_driver.c index d55b906..010f1b9 100644 --- a/src/radeon_driver.c +++ b/src/radeon_driver.c @@ -2184,7 +2184,11 @@ static Bool RADEONPreInitDRI(ScrnInfoPtr pScrn) "Direct rendering experimental on RS400/Xpress 200 enabled\n"); } - info->gartSize = RADEON_DEFAULT_GART_SIZE; + if (info->ChipFamily >= CHIP_FAMILY_R300) + info->gartSize = R300_DEFAULT_GART_SIZE; + else + info->gartSize = RADEON_DEFAULT_GART_SIZE; + info->ringSize = RADEON_DEFAULT_RING_SIZE; info->bufSize = RADEON_DEFAULT_BUFFER_SIZE; info->gartTexSize = RADEON_DEFAULT_GART_TEX_SIZE; commit 0a505297f09aefb1b4432176a263bfdf6f256f77 Author: Alex Deucher <[EMAIL PROTECTED]> Date: Mon Jul 28 17:12:41 2008 -0400 Fix error in driver connector table for powerbook w/ vga diff --git a/src/radeon_output.c b/src/radeon_output.c index 77533cc..a835c0c 100644 --- a/src/radeon_output.c +++ b/src/radeon_output.c @@ -2318,7 +2318,7 @@ static Bool RADEONSetupAppleConnectors(ScrnInfoPtr pScrn) info->BiosConnector[0].ddc_i2c = legacy_setup_i2c_bus(RADEON_GPIO_DVI_DDC); info->BiosConnector[0].DACType = DAC_NONE; info->BiosConnector[0].TMDSType = TMDS_NONE; - info->BiosConnector[0].ConnectorType = CONNECTOR_VGA; + info->BiosConnector[0].ConnectorType = CONNECTOR_LVDS; info->BiosConnector[0].valid = TRUE; info->BiosConnector[1].ddc_i2c = legacy_setup_i2c_bus(RADEON_GPIO_VGA_DDC); commit d5799ac53c3e1b2ca1da97780b171a44060c3aad Author: Alex Deucher <[EMAIL PROTECTED]> Date: Mon Jul 28 11:09:10 2008 -0400 Add quirk for oem x300 card - debian bug 492457 diff --git a/src/radeon_bios.c b/src/radeon_bios.c index 35e6960..adedeb3 100644 --- a/src/radeon_bios.c +++ b/src/radeon_bios.c @@ -481,6 +481,16 @@ static void RADEONApplyLegacyQuirks(ScrnInfoPtr pScrn, int index) } } + /* X300 card with extra non-existent DVI port */ + if (info->Chipset == PCI_CHIP_RV370_5B60 && + PCI_SUB_VENDOR_ID(info->PciInfo) == 0x17af && + PCI_SUB_DEVICE_ID(info->PciInfo) == 0x201e && + index == 2) { + if (info->BiosConnector[index].ConnectorType == CONNECTOR_DVI_I) { + info->BiosConnector[index].valid = FALSE; + } + } + } static Bool RADEONGetLegacyConnectorInfoFromBIOS (ScrnInfoPtr pScrn) commit 64dbadddcf6d069c0472f37afeab89d3e31e937d Author: Owain Gordon Ainsworth <[EMAIL PROTECTED]> Date: Mon Jul 28 10:40:58 2008 +1000 radeon: don't call ioctl unless DRI is initialised diff --git a/src/legacy_crtc.c b/src/legacy_crtc.c index f7216f9..334194a 100644 --- a/src/legacy_crtc.c +++ b/src/legacy_crtc.c @@ -625,6 +625,9 @@ radeon_crtc_modeset_ioctl(xf86CrtcPtr crtc, Bool post) RADEONCrtcPrivatePtr radeon_crtc = crtc->driver_private; struct drm_modeset_ctl modeset; + if (!info->directRenderingEnabled) + return; + modeset.crtc = radeon_crtc->crtc_id; modeset.cmd = post ? _DRM_POST_MODESET : _DRM_PRE_MODESET; commit 1c5858484da4fb1c9bc3ac3b4d7a97863ab99730 Author: Alex Deucher <[EMAIL PROTECTED]> Date: Mon Jul 21 23:47:45 2008 -0400 First pass at InitDispBandwidth() for AVIVO chips - support for LB allocation - MC priority bumps for display1/2 on RV515 variants and RS690 If you are having display underflow problems (flickering on sides of screen in high res modes, etc.) on RV515 or RS690 boards, try setting: Option "DisplayPriority" "HIGH" in your config. - still no support for full display watermark programming yet Something similar might be useful in rhd as well. diff --git a/src/atombios_crtc.c b/src/atombios_crtc.c index 406e786..70650e1 100644 --- a/src/atombios_crtc.c +++ b/src/atombios_crtc.c @@ -514,6 +514,9 @@ atombios_crtc_mode_set(xf86CrtcPtr crtc, atombios_set_crtc_timing(info->atomBIOS, &crtc_timing); + if (info->DispPriority) + RADEONInitDispBandwidth(pScrn); + if (tilingChanged) { /* need to redraw front buffer, I guess this can be considered a hack ? */ /* if this is called during ScreenInit() we don't have pScrn->pScreen yet */ @@ -527,3 +530,126 @@ atombios_crtc_mode_set(xf86CrtcPtr crtc, } +/* Calculate display buffer watermark to prevent buffer underflow */ +void +RADEONInitDispBandwidthAVIVO(ScrnInfoPtr pScrn, + DisplayModePtr mode1, int pixel_bytes1, + DisplayModePtr mode2, int pixel_bytes2) +{ + RADEONInfoPtr info = RADEONPTR(pScrn); + RADEONEntPtr pRADEONEnt = RADEONEntPriv(pScrn); + unsigned char *RADEONMMIO = info->MMIO; + + uint32_t dc_lb_memory_split; + float mem_bw, peak_disp_bw; + float min_mem_eff = 0.8; /* XXX: taken from legacy method */ + float pix_clk, pix_clk2; /* in MHz */ + + /* + * Set display0/1 priority up in the memory controller for + * modes if the user specifies HIGH for displaypriority + * option. + */ + if (info->DispPriority == 2) { + uint32_t mc_init_misc_lat_timer = 0; + if (info->ChipFamily == CHIP_FAMILY_RV515) + mc_init_misc_lat_timer = INMC(pScrn, RV515_MC_INIT_MISC_LAT_TIMER); + else if (info->ChipFamily == CHIP_FAMILY_RS690) + mc_init_misc_lat_timer = INMC(pScrn, RS690_MC_INIT_MISC_LAT_TIMER); + + mc_init_misc_lat_timer &= ~(R300_MC_DISP1R_INIT_LAT_MASK << R300_MC_DISP1R_INIT_LAT_SHIFT); + mc_init_misc_lat_timer &= ~(R300_MC_DISP0R_INIT_LAT_MASK << R300_MC_DISP0R_INIT_LAT_SHIFT); + + if (pRADEONEnt->pCrtc[1]->enabled) + mc_init_misc_lat_timer |= (1 << R300_MC_DISP1R_INIT_LAT_SHIFT); /* display 1 */ + if (pRADEONEnt->pCrtc[0]->enabled) + mc_init_misc_lat_timer |= (1 << R300_MC_DISP0R_INIT_LAT_SHIFT); /* display 0 */ + + if (info->ChipFamily == CHIP_FAMILY_RV515) + OUTMC(pScrn, RV515_MC_INIT_MISC_LAT_TIMER, mc_init_misc_lat_timer); + else if (info->ChipFamily == CHIP_FAMILY_RS690) + OUTMC(pScrn, RS690_MC_INIT_MISC_LAT_TIMER, mc_init_misc_lat_timer); + } + + /* XXX: fix me for AVIVO + * Determine if there is enough bandwidth for current display mode + */ + mem_bw = info->mclk * (info->RamWidth / 8) * (info->IsDDR ? 2 : 1); + + pix_clk = 0; + pix_clk2 = 0; + peak_disp_bw = 0; + if (mode1) { + pix_clk = mode1->Clock/1000.0; + peak_disp_bw += (pix_clk * pixel_bytes1); + } + if (mode2) { + pix_clk2 = mode2->Clock/1000.0; + peak_disp_bw += (pix_clk2 * pixel_bytes2); + } + + if (peak_disp_bw >= mem_bw * min_mem_eff) { + xf86DrvMsg(pScrn->scrnIndex, X_WARNING, + "You may not have enough display bandwidth for current mode\n" + "If you have flickering problem, try to lower resolution, refresh rate, or color depth\n"); + } + + /* + * Line Buffer Setup + * There is a single line buffer shared by both display controllers. + * DC_LB_MEMORY_SPLIT controls how that line buffer is shared between the display + * controllers. The paritioning can either be done manually or via one of four + * preset allocations specified in bits 1:0: + * 0 - line buffer is divided in half and shared between each display controller + * 1 - D1 gets 3/4 of the line buffer, D2 gets 1/4 + * 2 - D1 gets the whole buffer + * 3 - D1 gets 1/4 of the line buffer, D2 gets 3/4 + * Setting bit 2 of DC_LB_MEMORY_SPLIT controls switches to manual allocation mode. + * In manual allocation mode, D1 always starts at 0, D1 end/2 is specified in bits + * 14:4; D2 allocation follows D1. + */ + + /* is auto or manual better ? */ + dc_lb_memory_split = INREG(AVIVO_DC_LB_MEMORY_SPLIT) & ~AVIVO_DC_LB_MEMORY_SPLIT_MASK; + dc_lb_memory_split &= ~AVIVO_DC_LB_MEMORY_SPLIT_SHIFT_MODE; +#if 1 + /* auto */ + if (mode1 && mode2) { + if (mode1->HDisplay > mode2->HDisplay) { + if (mode1->HDisplay > 2560) + dc_lb_memory_split |= AVIVO_DC_LB_MEMORY_SPLIT_D1_3Q_D2_1Q; + else + dc_lb_memory_split |= AVIVO_DC_LB_MEMORY_SPLIT_D1HALF_D2HALF; + } else if (mode2->HDisplay > mode1->HDisplay) { + if (mode2->HDisplay > 2560) + dc_lb_memory_split |= AVIVO_DC_LB_MEMORY_SPLIT_D1_1Q_D2_3Q; + else + dc_lb_memory_split |= AVIVO_DC_LB_MEMORY_SPLIT_D1HALF_D2HALF; + } else + dc_lb_memory_split |= AVIVO_DC_LB_MEMORY_SPLIT_D1HALF_D2HALF; + } else if (mode1) { + dc_lb_memory_split |= AVIVO_DC_LB_MEMORY_SPLIT_D1_ONLY; + } else if (mode2) { + dc_lb_memory_split |= AVIVO_DC_LB_MEMORY_SPLIT_D1_1Q_D2_3Q; + } +#else + /* manual */ + dc_lb_memory_split |= AVIVO_DC_LB_MEMORY_SPLIT_SHIFT_MODE; + dc_lb_memory_split &= ~(AVIVO_DC_LB_DISP1_END_ADR_MASK << AVIVO_DC_LB_DISP1_END_ADR_SHIFT); + if (mode1) { + dc_lb_memory_split |= ((((mode1->HDisplay / 2) + 64 /*???*/) & AVIVO_DC_LB_DISP1_END_ADR_MASK) + << AVIVO_DC_LB_DISP1_END_ADR_SHIFT); + } else if (mode2) { + dc_lb_memory_split |= (0 << AVIVO_DC_LB_DISP1_END_ADR_SHIFT); + } + OUTREG(AVIVO_DC_LB_MEMORY_SPLIT, dc_lb_memory_split); +#endif + + /* + * Watermark setup + * TODO... + * Unforunately, I haven't been able to dig up the avivo watermark programming + * guide yet. -AGD + */ + +} diff --git a/src/radeon_crtc.c b/src/radeon_crtc.c index 9e5f672..1316669 100644 --- a/src/radeon_crtc.c +++ b/src/radeon_crtc.c @@ -62,6 +62,10 @@ extern void RADEONInitDispBandwidthLegacy(ScrnInfoPtr pScrn, DisplayModePtr mode1, int pixel_bytes1, DisplayModePtr mode2, int pixel_bytes2); +extern void +RADEONInitDispBandwidthAVIVO(ScrnInfoPtr pScrn, + DisplayModePtr mode1, int pixel_bytes1, + DisplayModePtr mode2, int pixel_bytes2); void radeon_crtc_dpms(xf86CrtcPtr crtc, int mode) @@ -602,7 +606,10 @@ RADEONInitDispBandwidth(ScrnInfoPtr pScrn) return; } - RADEONInitDispBandwidthLegacy(pScrn, mode1, pixel_bytes1, mode2, pixel_bytes2); + if (IS_AVIVO_VARIANT) + RADEONInitDispBandwidthAVIVO(pScrn, mode1, pixel_bytes1, mode2, pixel_bytes2); + else + RADEONInitDispBandwidthLegacy(pScrn, mode1, pixel_bytes1, mode2, pixel_bytes2); } Bool RADEONAllocateControllers(ScrnInfoPtr pScrn, int mask) diff --git a/src/radeon_driver.c b/src/radeon_driver.c index 4de7bae..d55b906 100644 --- a/src/radeon_driver.c +++ b/src/radeon_driver.c @@ -4188,6 +4188,7 @@ avivo_save(ScrnInfoPtr pScrn, RADEONSavePtr save) state->crtc_master_en = INREG(AVIVO_DC_CRTC_MASTER_EN); state->crtc_tv_control = INREG(AVIVO_DC_CRTC_TV_CONTROL); + state->dc_lb_memory_split = INREG(AVIVO_DC_LB_MEMORY_SPLIT); state->pll1.ref_div_src = INREG(AVIVO_EXT1_PPLL_REF_DIV_SRC); state->pll1.ref_div = INREG(AVIVO_EXT1_PPLL_REF_DIV); @@ -4818,6 +4819,7 @@ avivo_restore(ScrnInfoPtr pScrn, RADEONSavePtr restore) /* Where should that go ? */ OUTREG(AVIVO_DC_CRTC_TV_CONTROL, state->crtc_tv_control); + OUTREG(AVIVO_DC_LB_MEMORY_SPLIT, state->dc_lb_memory_split); /* Need fixing too ? */ OUTREG(AVIVO_D1CRTC_BLANK_CONTROL, state->crtc1.blank_control); diff --git a/src/radeon_probe.h b/src/radeon_probe.h index 35d622d..944ab9f 100644 --- a/src/radeon_probe.h +++ b/src/radeon_probe.h @@ -328,6 +328,7 @@ struct avivo_state uint32_t crtc_master_en; uint32_t crtc_tv_control; + uint32_t dc_lb_memory_split; struct avivo_pll_state pll1; struct avivo_pll_state pll2; diff --git a/src/radeon_reg.h b/src/radeon_reg.h index b750303..60f12fc 100644 --- a/src/radeon_reg.h +++ b/src/radeon_reg.h @@ -3422,6 +3422,7 @@ #define RS690_MC_AGP_LOCATION 0x101 #define RS690_MC_AGP_BASE 0x102 #define RS690_MC_AGP_BASE_2 0x103 +#define RS690_MC_INIT_MISC_LAT_TIMER 0x104 #define RS690_MC_STATUS 0x90 #define RS690_MC_STATUS_IDLE (1 << 0) @@ -3440,6 +3441,7 @@ # define R520_MC_STATUS_IDLE (1 << 1) #define RV515_MC_STATUS 0x08 # define RV515_MC_STATUS_IDLE (1 << 4) +#define RV515_MC_INIT_MISC_LAT_TIMER 0x09 #define AVIVO_MC_DATA 0x0074 #define RV515_MC_FB_LOCATION 0x1 @@ -3602,6 +3604,17 @@ #define AVIVO_DC_LUTA_WHITE_OFFSET_GREEN 0x64d4 #define AVIVO_DC_LUTA_WHITE_OFFSET_RED 0x64d8 +#define AVIVO_DC_LB_MEMORY_SPLIT 0x6520 +# define AVIVO_DC_LB_MEMORY_SPLIT_MASK 0x3 +# define AVIVO_DC_LB_MEMORY_SPLIT_SHIFT 0 +# define AVIVO_DC_LB_MEMORY_SPLIT_D1HALF_D2HALF 0 +# define AVIVO_DC_LB_MEMORY_SPLIT_D1_3Q_D2_1Q 1 +# define AVIVO_DC_LB_MEMORY_SPLIT_D1_ONLY 2 +# define AVIVO_DC_LB_MEMORY_SPLIT_D1_1Q_D2_3Q 3 +# define AVIVO_DC_LB_MEMORY_SPLIT_SHIFT_MODE (1 << 2) +# define AVIVO_DC_LB_DISP1_END_ADR_SHIFT 4 +# define AVIVO_DC_LB_DISP1_END_ADR_MASK 0x7ff + #define AVIVO_D1MODE_DATA_FORMAT 0x6528 # define AVIVO_D1MODE_INTERLEAVE_EN (1 << 0) #define AVIVO_D1MODE_DESKTOP_HEIGHT 0x652c commit b0378bb145c8a915c943bef7d17f2cdecfccc891 Author: Alex Deucher <[EMAIL PROTECTED]> Date: Mon Jul 21 13:47:09 2008 -0400 Interlaced mode fixups for AVIVO chips diff --git a/src/atombios_crtc.c b/src/atombios_crtc.c index 12a20bb..406e786 100644 --- a/src/atombios_crtc.c +++ b/src/atombios_crtc.c @@ -502,6 +502,12 @@ atombios_crtc_mode_set(xf86CrtcPtr crtc, OUTREG(AVIVO_D1MODE_VIEWPORT_SIZE + radeon_crtc->crtc_offset, (mode->HDisplay << 16) | mode->VDisplay); + if (adjusted_mode->Flags & V_INTERLACE) + OUTREG(AVIVO_D1MODE_DATA_FORMAT + radeon_crtc->crtc_offset, + AVIVO_D1MODE_INTERLEAVE_EN); + else + OUTREG(AVIVO_D1MODE_DATA_FORMAT + radeon_crtc->crtc_offset, + 0); } atombios_crtc_set_pll(crtc, adjusted_mode, pll_flags); diff --git a/src/radeon_cursor.c b/src/radeon_cursor.c index d480416..13c2b9c 100644 --- a/src/radeon_cursor.c +++ b/src/radeon_cursor.c @@ -209,11 +209,6 @@ radeon_crtc_set_cursor_position (xf86CrtcPtr crtc, int x, int y) if (xorigin >= CURSOR_WIDTH) xorigin = CURSOR_WIDTH - 1; if (yorigin >= CURSOR_HEIGHT) yorigin = CURSOR_HEIGHT - 1; - if (mode->Flags & V_INTERLACE) - y /= 2; - else if (mode->Flags & V_DBLSCAN) - y *= 2; - if (IS_AVIVO_VARIANT) { /* avivo cursor spans the full fb width */ if (crtc->rotatedData == NULL) { @@ -226,6 +221,11 @@ radeon_crtc_set_cursor_position (xf86CrtcPtr crtc, int x, int y) OUTREG(AVIVO_D1CUR_HOT_SPOT + radeon_crtc->crtc_offset, (xorigin << 16) | yorigin); avivo_lock_cursor(crtc, FALSE); } else { + if (mode->Flags & V_INTERLACE) + y /= 2; + else if (mode->Flags & V_DBLSCAN) + y *= 2; + if (crtc_id == 0) { OUTREG(RADEON_CUR_HORZ_VERT_OFF, (RADEON_CUR_LOCK | (xorigin << 16) diff --git a/src/radeon_driver.c b/src/radeon_driver.c index 8d6edff..4de7bae 100644 --- a/src/radeon_driver.c +++ b/src/radeon_driver.c @@ -4246,6 +4246,7 @@ avivo_save(ScrnInfoPtr pScrn, RADEONSavePtr save) state->grph1.desktop_height = INREG(AVIVO_D1MODE_DESKTOP_HEIGHT); state->grph1.viewport_start = INREG(AVIVO_D1MODE_VIEWPORT_START); state->grph1.viewport_size = INREG(AVIVO_D1MODE_VIEWPORT_SIZE); + state->grph1.mode_data_format = INREG(AVIVO_D1MODE_DATA_FORMAT); state->crtc2.pll_source = INREG(AVIVO_PCLK_CRTC2_CNTL); @@ -4286,6 +4287,7 @@ avivo_save(ScrnInfoPtr pScrn, RADEONSavePtr save) state->grph2.desktop_height = INREG(AVIVO_D2MODE_DESKTOP_HEIGHT); state->grph2.viewport_start = INREG(AVIVO_D2MODE_VIEWPORT_START); state->grph2.viewport_size = INREG(AVIVO_D2MODE_VIEWPORT_SIZE); + state->grph2.mode_data_format = INREG(AVIVO_D2MODE_DATA_FORMAT); if (IS_DCE3_VARIANT) { /* save DVOA regs */ @@ -4543,12 +4545,14 @@ avivo_restore(ScrnInfoPtr pScrn, RADEONSavePtr restore) OUTREG(AVIVO_D1MODE_DESKTOP_HEIGHT, state->grph1.desktop_height); OUTREG(AVIVO_D1MODE_VIEWPORT_START, state->grph1.viewport_start); OUTREG(AVIVO_D1MODE_VIEWPORT_SIZE, state->grph1.viewport_size); + OUTREG(AVIVO_D1MODE_DATA_FORMAT, state->grph1.mode_data_format); OUTREG(AVIVO_D1SCL_UPDATE, 0); OUTREG(AVIVO_D2SCL_UPDATE, AVIVO_D1SCL_UPDATE_LOCK); OUTREG(AVIVO_D2MODE_DESKTOP_HEIGHT, state->grph2.desktop_height); OUTREG(AVIVO_D2MODE_VIEWPORT_START, state->grph2.viewport_start); OUTREG(AVIVO_D2MODE_VIEWPORT_SIZE, state->grph2.viewport_size); + OUTREG(AVIVO_D2MODE_DATA_FORMAT, state->grph2.mode_data_format); OUTREG(AVIVO_D2SCL_UPDATE, 0); /* Set the PLL */ diff --git a/src/radeon_output.c b/src/radeon_output.c index 64f14c2..77533cc 100644 --- a/src/radeon_output.c +++ b/src/radeon_output.c @@ -582,6 +582,13 @@ radeon_mode_fixup(xf86OutputPtr output, DisplayModePtr mode, } } + if (IS_AVIVO_VARIANT) { + /* hw bug */ + if ((mode->Flags & V_INTERLACE) + && (mode->CrtcVSyncStart < (mode->CrtcVDisplay + 2))) + adjusted_mode->CrtcVSyncStart = adjusted_mode->CrtcVDisplay + 2; + } + return TRUE; } diff --git a/src/radeon_probe.h b/src/radeon_probe.h index 2837671..35d622d 100644 --- a/src/radeon_probe.h +++ b/src/radeon_probe.h @@ -313,6 +313,7 @@ struct avivo_grph_state { uint32_t desktop_height; uint32_t viewport_start; uint32_t viewport_size; + uint32_t mode_data_format; }; struct avivo_state diff --git a/src/radeon_reg.h b/src/radeon_reg.h index 5c0e852..b750303 100644 --- a/src/radeon_reg.h +++ b/src/radeon_reg.h @@ -3602,6 +3602,8 @@ #define AVIVO_DC_LUTA_WHITE_OFFSET_GREEN 0x64d4 #define AVIVO_DC_LUTA_WHITE_OFFSET_RED 0x64d8 +#define AVIVO_D1MODE_DATA_FORMAT 0x6528 +# define AVIVO_D1MODE_INTERLEAVE_EN (1 << 0) #define AVIVO_D1MODE_DESKTOP_HEIGHT 0x652c #define AVIVO_D1MODE_VIEWPORT_START 0x6580 #define AVIVO_D1MODE_VIEWPORT_SIZE 0x6584 @@ -3654,6 +3656,7 @@ #define AVIVO_D2CUR_SIZE 0x6c10 #define AVIVO_D2CUR_POSITION 0x6c14 +#define AVIVO_D2MODE_DATA_FORMAT 0x6d28 #define AVIVO_D2MODE_DESKTOP_HEIGHT 0x6d2c #define AVIVO_D2MODE_VIEWPORT_START 0x6d80 #define AVIVO_D2MODE_VIEWPORT_SIZE 0x6d84 commit c18fad622a3c4f9572051120d83af68b625b5686 Author: Alex Deucher <[EMAIL PROTECTED]> Date: Mon Jul 21 10:36:48 2008 -0400 Clear display priority bits before resetting them diff --git a/src/legacy_crtc.c b/src/legacy_crtc.c index e5561e8..f7216f9 100644 --- a/src/legacy_crtc.c +++ b/src/legacy_crtc.c @@ -1369,6 +1369,8 @@ RADEONInitDispBandwidthLegacy(ScrnInfoPtr pScrn, */ if ((info->DispPriority == 2) && IS_R300_VARIANT) { uint32_t mc_init_misc_lat_timer = INREG(R300_MC_INIT_MISC_LAT_TIMER); + mc_init_misc_lat_timer &= ~(R300_MC_DISP1R_INIT_LAT_MASK << R300_MC_DISP1R_INIT_LAT_SHIFT); + mc_init_misc_lat_timer &= ~(R300_MC_DISP0R_INIT_LAT_MASK << R300_MC_DISP0R_INIT_LAT_SHIFT); if (pRADEONEnt->pCrtc[1]->enabled) mc_init_misc_lat_timer |= (1 << R300_MC_DISP1R_INIT_LAT_SHIFT); /* display 1 */ if (pRADEONEnt->pCrtc[0]->enabled) @@ -1376,7 +1378,6 @@ RADEONInitDispBandwidthLegacy(ScrnInfoPtr pScrn, OUTREG(R300_MC_INIT_MISC_LAT_TIMER, mc_init_misc_lat_timer); } - /* R420 and RV410 family not supported yet */ if (info->ChipFamily == CHIP_FAMILY_R420 || info->ChipFamily == CHIP_FAMILY_RV410) return; diff --git a/src/radeon_reg.h b/src/radeon_reg.h index b79dbd5..5c0e852 100644 --- a/src/radeon_reg.h +++ b/src/radeon_reg.h @@ -1033,7 +1033,9 @@ #define RADEON_NB_TOM 0x15c #define R300_MC_INIT_MISC_LAT_TIMER 0x180 # define R300_MC_DISP0R_INIT_LAT_SHIFT 8 +# define R300_MC_DISP0R_INIT_LAT_MASK 0xf # define R300_MC_DISP1R_INIT_LAT_SHIFT 12 +# define R300_MC_DISP1R_INIT_LAT_MASK 0xf #define RADEON_MCLK_CNTL 0x0012 /* PLL */ # define RADEON_FORCEON_MCLKA (1 << 16) # define RADEON_FORCEON_MCLKB (1 << 17) commit dc231ff8e063313d2bcf5acccad67a9f8a7e3314 Author: Alex Deucher <[EMAIL PROTECTED]> Date: Mon Jul 21 10:30:41 2008 -0400 Clean up legacy display watermark setup - makes crtc1 and crtc2 watermark setup independant. - fixes the case where only crtc2 is active diff --git a/src/legacy_crtc.c b/src/legacy_crtc.c index 3df61a7..e5561e8 100644 --- a/src/legacy_crtc.c +++ b/src/legacy_crtc.c @@ -1327,9 +1327,12 @@ radeon_update_tv_routing(ScrnInfoPtr pScrn, RADEONSavePtr restore) } /* Calculate display buffer watermark to prevent buffer underflow */ -static void -RADEONInitDispBandwidth2(ScrnInfoPtr pScrn, RADEONInfoPtr info, int pixel_bytes2, DisplayModePtr mode1, DisplayModePtr mode2) +void +RADEONInitDispBandwidthLegacy(ScrnInfoPtr pScrn, + DisplayModePtr mode1, int pixel_bytes1, + DisplayModePtr mode2, int pixel_bytes2) { + RADEONInfoPtr info = RADEONPTR(pScrn); RADEONEntPtr pRADEONEnt = RADEONEntPriv(pScrn); unsigned char *RADEONMMIO = info->MMIO; @@ -1352,10 +1355,10 @@ RADEONInitDispBandwidth2(ScrnInfoPtr pScrn, RADEONInfoPtr info, int pixel_bytes2 float min_mem_eff = 0.8; float sclk_eff, sclk_delay; float mc_latency_mclk, mc_latency_sclk, cur_latency_mclk, cur_latency_sclk; - float disp_latency, disp_latency_overhead, disp_drain_rate, disp_drain_rate2; + float disp_latency, disp_latency_overhead, disp_drain_rate = 0, disp_drain_rate2; float pix_clk, pix_clk2; /* in MHz */ int cur_size = 16; /* in octawords */ - int critical_point, critical_point2; + int critical_point = 0, critical_point2; int stop_req, max_stop_req; float read_return_rate, time_disp1_drop_priority; @@ -1366,11 +1369,10 @@ RADEONInitDispBandwidth2(ScrnInfoPtr pScrn, RADEONInfoPtr info, int pixel_bytes2 */ if ((info->DispPriority == 2) && IS_R300_VARIANT) { uint32_t mc_init_misc_lat_timer = INREG(R300_MC_INIT_MISC_LAT_TIMER); - if (pRADEONEnt->pCrtc[1]->enabled) { - mc_init_misc_lat_timer |= 0x1100; /* display 0 and 1 */ - } else { - mc_init_misc_lat_timer |= 0x0100; /* display 0 only */ - } + if (pRADEONEnt->pCrtc[1]->enabled) + mc_init_misc_lat_timer |= (1 << R300_MC_DISP1R_INIT_LAT_SHIFT); /* display 1 */ + if (pRADEONEnt->pCrtc[0]->enabled) + mc_init_misc_lat_timer |= (1 << R300_MC_DISP0R_INIT_LAT_SHIFT); /* display 0 */ OUTREG(R300_MC_INIT_MISC_LAT_TIMER, mc_init_misc_lat_timer); } @@ -1383,15 +1385,17 @@ RADEONInitDispBandwidth2(ScrnInfoPtr pScrn, RADEONInfoPtr info, int pixel_bytes2 */ mem_bw = info->mclk * (info->RamWidth / 8) * (info->IsDDR ? 2 : 1); - pix_clk = mode1->Clock/1000.0; - if (mode2) + pix_clk = 0; + pix_clk2 = 0; + peak_disp_bw = 0; + if (mode1) { + pix_clk = mode1->Clock/1000.0; + peak_disp_bw += (pix_clk * pixel_bytes1); + } + if (mode2) { pix_clk2 = mode2->Clock/1000.0; - else - pix_clk2 = 0; - - peak_disp_bw = (pix_clk * info->CurrentLayout.pixel_bytes); - if (pixel_bytes2) - peak_disp_bw += (pix_clk2 * pixel_bytes2); + peak_disp_bw += (pix_clk2 * pixel_bytes2); + } if (peak_disp_bw >= mem_bw * min_mem_eff) { xf86DrvMsg(pScrn->scrnIndex, X_WARNING, @@ -1399,20 +1403,6 @@ RADEONInitDispBandwidth2(ScrnInfoPtr pScrn, RADEONInfoPtr info, int pixel_bytes2 "If you have flickering problem, try to lower resolution, refresh rate, or color depth\n"); } - /* CRTC1 - Set GRPH_BUFFER_CNTL register using h/w defined optimal values. - GRPH_STOP_REQ <= MIN[ 0x7C, (CRTC_H_DISP + 1) * (bit depth) / 0x10 ] - */ - stop_req = mode1->HDisplay * info->CurrentLayout.pixel_bytes / 16; - - /* setup Max GRPH_STOP_REQ default value */ - if (IS_RV100_VARIANT) - max_stop_req = 0x5c; - else - max_stop_req = 0x7c; - if (stop_req > max_stop_req) - stop_req = max_stop_req; - /* Get values from the EXT_MEM_CNTL register...converting its contents. */ temp = INREG(RADEON_MEM_TIMING_CNTL); if ((info->ChipFamily == CHIP_FAMILY_RV100) || info->IsIGP) { /* RV100, M6, IGPs */ @@ -1435,9 +1425,8 @@ RADEONInitDispBandwidth2(ScrnInfoPtr pScrn, RADEONInfoPtr info, int pixel_bytes2 } if (IS_R300_VARIANT) { - /* on the R300, Tcas is included in Trbs. - */ + */ temp = INREG(RADEON_MEM_CNTL); data = (R300_MEM_NUM_CHANNELS_MASK & temp); if (data == 1) { @@ -1473,7 +1462,8 @@ RADEONInitDispBandwidth2(ScrnInfoPtr pScrn, RADEONInfoPtr info, int pixel_bytes2 sclk_eff = info->sclk; } - /* Find the memory controller latency for the display client. + /* + Find the memory controller latency for the display client. */ if (IS_R300_VARIANT) { /*not enough for R350 ???*/ @@ -1527,89 +1517,107 @@ RADEONInitDispBandwidth2(ScrnInfoPtr pScrn, RADEONInfoPtr info, int pixel_bytes2 mc_latency_sclk = mc_latency_sclk + disp_latency_overhead + cur_latency_sclk; disp_latency = MAX(mc_latency_mclk, mc_latency_sclk); - /* - Find the drain rate of the display buffer. - */ - disp_drain_rate = pix_clk / (16.0/info->CurrentLayout.pixel_bytes); - if (pixel_bytes2) - disp_drain_rate2 = pix_clk2 / (16.0/pixel_bytes2); + /* setup Max GRPH_STOP_REQ default value */ + if (IS_RV100_VARIANT) + max_stop_req = 0x5c; else - disp_drain_rate2 = 0; + max_stop_req = 0x7c; - /* - Find the critical point of the display buffer. - */ - critical_point= (uint32_t)(disp_drain_rate * disp_latency + 0.5); + if (mode1) { + /* CRTC1 + Set GRPH_BUFFER_CNTL register using h/w defined optimal values. + GRPH_STOP_REQ <= MIN[ 0x7C, (CRTC_H_DISP + 1) * (bit depth) / 0x10 ] + */ + stop_req = mode1->HDisplay * pixel_bytes1 / 16; - /* ???? */ - /* - temp = (info->SavedReg.grph_buffer_cntl & RADEON_GRPH_CRITICAL_POINT_MASK) >> RADEON_GRPH_CRITICAL_POINT_SHIFT; - if (critical_point < temp) critical_point = temp; - */ - if (info->DispPriority == 2) { - critical_point = 0; - } + if (stop_req > max_stop_req) + stop_req = max_stop_req; - /* - The critical point should never be above max_stop_req-4. Setting - GRPH_CRITICAL_CNTL = 0 will thus force high priority all the time. - */ - if (max_stop_req - critical_point < 4) critical_point = 0; + /* + Find the drain rate of the display buffer. + */ + disp_drain_rate = pix_clk / (16.0/pixel_bytes1); - if (critical_point == 0 && mode2 && info->ChipFamily == CHIP_FAMILY_R300) { - /* some R300 cards have problem with this set to 0, when CRTC2 is enabled.*/ - critical_point = 0x10; - } + /* + Find the critical point of the display buffer. + */ + critical_point= (uint32_t)(disp_drain_rate * disp_latency + 0.5); - temp = info->SavedReg->grph_buffer_cntl; - temp &= ~(RADEON_GRPH_STOP_REQ_MASK); - temp |= (stop_req << RADEON_GRPH_STOP_REQ_SHIFT); - temp &= ~(RADEON_GRPH_START_REQ_MASK); - if ((info->ChipFamily == CHIP_FAMILY_R350) && - (stop_req > 0x15)) { - stop_req -= 0x10; - } - temp |= (stop_req << RADEON_GRPH_START_REQ_SHIFT); + /* ???? */ + /* + temp = (info->SavedReg.grph_buffer_cntl & RADEON_GRPH_CRITICAL_POINT_MASK) >> RADEON_GRPH_CRITICAL_POINT_SHIFT; + if (critical_point < temp) critical_point = temp; + */ + if (info->DispPriority == 2) { + critical_point = 0; + } - temp |= RADEON_GRPH_BUFFER_SIZE; - temp &= ~(RADEON_GRPH_CRITICAL_CNTL | - RADEON_GRPH_CRITICAL_AT_SOF | - RADEON_GRPH_STOP_CNTL); - /* - Write the result into the register. - */ - OUTREG(RADEON_GRPH_BUFFER_CNTL, ((temp & ~RADEON_GRPH_CRITICAL_POINT_MASK) | - (critical_point << RADEON_GRPH_CRITICAL_POINT_SHIFT))); + /* + The critical point should never be above max_stop_req-4. Setting + GRPH_CRITICAL_CNTL = 0 will thus force high priority all the time. + */ + if (max_stop_req - critical_point < 4) critical_point = 0; + + if (critical_point == 0 && mode2 && info->ChipFamily == CHIP_FAMILY_R300) { + /* some R300 cards have problem with this set to 0, when CRTC2 is enabled.*/ + critical_point = 0x10; + } + + temp = info->SavedReg->grph_buffer_cntl; + temp &= ~(RADEON_GRPH_STOP_REQ_MASK); + temp |= (stop_req << RADEON_GRPH_STOP_REQ_SHIFT); + temp &= ~(RADEON_GRPH_START_REQ_MASK); + if ((info->ChipFamily == CHIP_FAMILY_R350) && + (stop_req > 0x15)) { + stop_req -= 0x10; + } + temp |= (stop_req << RADEON_GRPH_START_REQ_SHIFT); + + temp |= RADEON_GRPH_BUFFER_SIZE; + temp &= ~(RADEON_GRPH_CRITICAL_CNTL | + RADEON_GRPH_CRITICAL_AT_SOF | + RADEON_GRPH_STOP_CNTL); + /* + Write the result into the register. + */ -- To UNSUBSCRIBE, email to [EMAIL PROTECTED] with a subject of "unsubscribe". Trouble? Contact [EMAIL PROTECTED]