From 780c7e34b795122b843c2d92ffb422a35058f63b Mon Sep 17 00:00:00 2001 From: Zhenyu Wang Date: Fri, 5 Dec 2008 14:05:19 +0800 Subject: [PATCH] SDVO: use attached display flags for output setup SDVO encoder will return all supported display types in capability flag, which can't be used to determine what current display type is, and possible to cause conflict. This one trys to use GET_ATTACHED_DISPLAYS command to setup output according with current config. --- src/i830_sdvo.c | 57 +++++++++++++++++++++++++++++++++++++++++++----------- 1 files changed, 45 insertions(+), 12 deletions(-) diff --git a/src/i830_sdvo.c b/src/i830_sdvo.c index 256d16d..f22c12c 100644 --- a/src/i830_sdvo.c +++ b/src/i830_sdvo.c @@ -1450,6 +1450,16 @@ i830_sdvo_dump(ScrnInfoPtr pScrn) } } +static uint8_t +i830_sdvo_get_attached_display (xf86OutputPtr output, uint16_t* response) +{ + uint8_t status; + + i830_sdvo_write_cmd(output, SDVO_CMD_GET_ATTACHED_DISPLAYS, NULL, 0); + status = i830_sdvo_read_response(output, response, 2); + return status; +} + /** * Asks the SDVO device if any displays are currently connected. * @@ -1462,16 +1472,15 @@ i830_sdvo_dump(ScrnInfoPtr pScrn) static xf86OutputStatus i830_sdvo_detect(xf86OutputPtr output) { - uint8_t response[2]; + uint16_t response; uint8_t status; - i830_sdvo_write_cmd(output, SDVO_CMD_GET_ATTACHED_DISPLAYS, NULL, 0); - status = i830_sdvo_read_response(output, &response, 2); + status = i830_sdvo_get_attached_display(output, &response); if (status != SDVO_CMD_STATUS_SUCCESS) return XF86OutputStatusUnknown; - if (response[0] != 0 || response[1] != 0) + if (response != 0) return XF86OutputStatusConnected; else return XF86OutputStatusDisconnected; @@ -1753,6 +1762,7 @@ i830_sdvo_get_digital_encoding_mode(xf86OutputPtr output) Bool i830_sdvo_init(ScrnInfoPtr pScrn, int output_device) { + I830Ptr pI830 = I830PTR(pScrn); xf86OutputPtr output; I830OutputPrivatePtr intel_output; struct i830_sdvo_priv *dev_priv; @@ -1762,6 +1772,8 @@ i830_sdvo_init(ScrnInfoPtr pScrn, int output_device) char name[60]; char *name_prefix; char *name_suffix; + uint8_t status; + uint16_t attached; output = xf86OutputCreate (pScrn, &i830_sdvo_output_funcs,NULL); if (!output) @@ -1866,11 +1878,32 @@ i830_sdvo_init(ScrnInfoPtr pScrn, int output_device) intel_output->pDDCBus = ddcbus; intel_output->dev_priv = dev_priv; - i830_sdvo_get_capabilities(output, &dev_priv->caps); + if (i830_sdvo_get_capabilities(output, &dev_priv->caps) == FALSE || + dev_priv->caps.output_flags == 0) + { + xf86DrvMsg(intel_output->pI2CBus->scrnIndex, X_WARNING, + "SDVO can't get encoder capability\n"); + xf86OutputDestroy (output); + return FALSE; + } + + status = i830_sdvo_get_attached_display (output, &attached); + if (status != SDVO_CMD_STATUS_SUCCESS) { + xf86DrvMsg(intel_output->pI2CBus->scrnIndex, X_WARNING, + "SDVO can't get attached displays\n"); + xf86OutputDestroy (output); + return FALSE; + } else { + if (pI830->debug_modes) + xf86DrvMsg(intel_output->pI2CBus->scrnIndex, X_INFO, + "SDVO%c attached display 0x%x\n", + output_device == SDVOB ? 'B' : 'C', + attached); + } - if (dev_priv->caps.output_flags & (SDVO_OUTPUT_TMDS0 | SDVO_OUTPUT_TMDS1)) + if (attached & (SDVO_OUTPUT_TMDS0 | SDVO_OUTPUT_TMDS1)) { - if (dev_priv->caps.output_flags & SDVO_OUTPUT_TMDS0) + if (attached & SDVO_OUTPUT_TMDS0) dev_priv->controlled_output = SDVO_OUTPUT_TMDS0; else dev_priv->controlled_output = SDVO_OUTPUT_TMDS1; @@ -1886,7 +1919,7 @@ i830_sdvo_init(ScrnInfoPtr pScrn, int output_device) name_prefix = "HDMI"; } } - else if (dev_priv->caps.output_flags & SDVO_OUTPUT_SVID0) + else if (attached & SDVO_OUTPUT_SVID0) { dev_priv->controlled_output = SDVO_OUTPUT_SVID0; output->subpixel_order = SubPixelHorizontalRGB; /* XXX */ @@ -1894,13 +1927,13 @@ i830_sdvo_init(ScrnInfoPtr pScrn, int output_device) dev_priv->is_tv = TRUE; intel_output->needs_tv_clock = TRUE; } - else if (dev_priv->caps.output_flags & SDVO_OUTPUT_RGB0) + else if (attached & SDVO_OUTPUT_RGB0) { dev_priv->controlled_output = SDVO_OUTPUT_RGB0; output->subpixel_order = SubPixelHorizontalRGB; name_prefix="VGA"; } - else if (dev_priv->caps.output_flags & SDVO_OUTPUT_RGB1) + else if (attached & SDVO_OUTPUT_RGB1) { dev_priv->controlled_output = SDVO_OUTPUT_RGB1; output->subpixel_order = SubPixelHorizontalRGB; @@ -1911,7 +1944,7 @@ i830_sdvo_init(ScrnInfoPtr pScrn, int output_device) unsigned char bytes[2]; dev_priv->controlled_output = 0; - memcpy (bytes, &dev_priv->caps.output_flags, 2); + memcpy (bytes, &attached, 2); xf86DrvMsg(intel_output->pI2CBus->scrnIndex, X_WARNING, "%s: Unknown SDVO output type (0x%02x%02x)\n", SDVO_NAME(dev_priv), @@ -1950,7 +1983,7 @@ i830_sdvo_init(ScrnInfoPtr pScrn, int output_device) dev_priv->caps.sdvo_input_count >= 2 ? "s" : ""); #define REPORT_OUTPUT_FLAG(flag, name) do { \ - if (dev_priv->caps.output_flags & flag) { \ + if (attached & flag) { \ xf86DrvMsg(pScrn->scrnIndex, X_INFO, "%s: %s output reported\n", \ SDVO_NAME(dev_priv), name); \ } \ -- 1.5.6.5