11099013bSjsg /*
21099013bSjsg * Copyright 2007-8 Advanced Micro Devices, Inc.
31099013bSjsg * Copyright 2008 Red Hat Inc.
41099013bSjsg *
51099013bSjsg * Permission is hereby granted, free of charge, to any person obtaining a
61099013bSjsg * copy of this software and associated documentation files (the "Software"),
71099013bSjsg * to deal in the Software without restriction, including without limitation
81099013bSjsg * the rights to use, copy, modify, merge, publish, distribute, sublicense,
91099013bSjsg * and/or sell copies of the Software, and to permit persons to whom the
101099013bSjsg * Software is furnished to do so, subject to the following conditions:
111099013bSjsg *
121099013bSjsg * The above copyright notice and this permission notice shall be included in
131099013bSjsg * all copies or substantial portions of the Software.
141099013bSjsg *
151099013bSjsg * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
161099013bSjsg * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
171099013bSjsg * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
181099013bSjsg * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR
191099013bSjsg * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
201099013bSjsg * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
211099013bSjsg * OTHER DEALINGS IN THE SOFTWARE.
221099013bSjsg *
231099013bSjsg * Authors: Dave Airlie
241099013bSjsg * Alex Deucher
251099013bSjsg */
26c349dbc7Sjsg
27c349dbc7Sjsg #include <linux/backlight.h>
28c349dbc7Sjsg #include <linux/pci.h>
29c349dbc7Sjsg
30c349dbc7Sjsg #include <drm/drm_device.h>
31c349dbc7Sjsg #include <drm/drm_file.h>
32*f005ef32Sjsg #include <drm/drm_modeset_helper_vtables.h>
33c349dbc7Sjsg #include <drm/drm_util.h>
347f4dd379Sjsg #include <drm/radeon_drm.h>
35c349dbc7Sjsg
361bb76ff1Sjsg #include <acpi/video.h>
371bb76ff1Sjsg
381099013bSjsg #include "radeon.h"
397f4dd379Sjsg #include "radeon_asic.h"
405ca02815Sjsg #include "radeon_legacy_encoders.h"
411099013bSjsg #include "atom.h"
427ccd5a2cSjsg #ifdef CONFIG_PMAC_BACKLIGHT
437ccd5a2cSjsg #include <asm/backlight.h>
447ccd5a2cSjsg #endif
451099013bSjsg
radeon_legacy_encoder_disable(struct drm_encoder * encoder)461099013bSjsg static void radeon_legacy_encoder_disable(struct drm_encoder *encoder)
471099013bSjsg {
481099013bSjsg struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
493253c27bSkettenis const struct drm_encoder_helper_funcs *encoder_funcs;
501099013bSjsg
511099013bSjsg encoder_funcs = encoder->helper_private;
521099013bSjsg encoder_funcs->dpms(encoder, DRM_MODE_DPMS_OFF);
531099013bSjsg radeon_encoder->active_device = 0;
541099013bSjsg }
551099013bSjsg
radeon_legacy_lvds_update(struct drm_encoder * encoder,int mode)561099013bSjsg static void radeon_legacy_lvds_update(struct drm_encoder *encoder, int mode)
571099013bSjsg {
581099013bSjsg struct drm_device *dev = encoder->dev;
591099013bSjsg struct radeon_device *rdev = dev->dev_private;
601099013bSjsg struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
611099013bSjsg uint32_t lvds_gen_cntl, lvds_pll_cntl, pixclks_cntl, disp_pwr_man;
621099013bSjsg int panel_pwr_delay = 2000;
631099013bSjsg bool is_mac = false;
641099013bSjsg uint8_t backlight_level;
651099013bSjsg DRM_DEBUG_KMS("\n");
661099013bSjsg
671099013bSjsg lvds_gen_cntl = RREG32(RADEON_LVDS_GEN_CNTL);
681099013bSjsg backlight_level = (lvds_gen_cntl >> RADEON_LVDS_BL_MOD_LEVEL_SHIFT) & 0xff;
691099013bSjsg
701099013bSjsg if (radeon_encoder->enc_priv) {
711099013bSjsg if (rdev->is_atom_bios) {
721099013bSjsg struct radeon_encoder_atom_dig *lvds = radeon_encoder->enc_priv;
731099013bSjsg panel_pwr_delay = lvds->panel_pwr_delay;
741099013bSjsg if (lvds->bl_dev)
751099013bSjsg backlight_level = lvds->backlight_level;
761099013bSjsg } else {
771099013bSjsg struct radeon_encoder_lvds *lvds = radeon_encoder->enc_priv;
781099013bSjsg panel_pwr_delay = lvds->panel_pwr_delay;
791099013bSjsg if (lvds->bl_dev)
801099013bSjsg backlight_level = lvds->backlight_level;
811099013bSjsg }
821099013bSjsg }
831099013bSjsg
841099013bSjsg /* macs (and possibly some x86 oem systems?) wire up LVDS strangely
851099013bSjsg * Taken from radeonfb.
861099013bSjsg */
871099013bSjsg if ((rdev->mode_info.connector_table == CT_IBOOK) ||
881099013bSjsg (rdev->mode_info.connector_table == CT_POWERBOOK_EXTERNAL) ||
891099013bSjsg (rdev->mode_info.connector_table == CT_POWERBOOK_INTERNAL) ||
901099013bSjsg (rdev->mode_info.connector_table == CT_POWERBOOK_VGA))
911099013bSjsg is_mac = true;
921099013bSjsg
931099013bSjsg switch (mode) {
941099013bSjsg case DRM_MODE_DPMS_ON:
951099013bSjsg disp_pwr_man = RREG32(RADEON_DISP_PWR_MAN);
961099013bSjsg disp_pwr_man |= RADEON_AUTO_PWRUP_EN;
971099013bSjsg WREG32(RADEON_DISP_PWR_MAN, disp_pwr_man);
981099013bSjsg lvds_pll_cntl = RREG32(RADEON_LVDS_PLL_CNTL);
991099013bSjsg lvds_pll_cntl |= RADEON_LVDS_PLL_EN;
1001099013bSjsg WREG32(RADEON_LVDS_PLL_CNTL, lvds_pll_cntl);
1011099013bSjsg mdelay(1);
1021099013bSjsg
1031099013bSjsg lvds_pll_cntl = RREG32(RADEON_LVDS_PLL_CNTL);
1041099013bSjsg lvds_pll_cntl &= ~RADEON_LVDS_PLL_RESET;
1051099013bSjsg WREG32(RADEON_LVDS_PLL_CNTL, lvds_pll_cntl);
1061099013bSjsg
1071099013bSjsg lvds_gen_cntl &= ~(RADEON_LVDS_DISPLAY_DIS |
1081099013bSjsg RADEON_LVDS_BL_MOD_LEVEL_MASK);
1091099013bSjsg lvds_gen_cntl |= (RADEON_LVDS_ON | RADEON_LVDS_EN |
1101099013bSjsg RADEON_LVDS_DIGON | RADEON_LVDS_BLON |
1111099013bSjsg (backlight_level << RADEON_LVDS_BL_MOD_LEVEL_SHIFT));
1121099013bSjsg if (is_mac)
1131099013bSjsg lvds_gen_cntl |= RADEON_LVDS_BL_MOD_EN;
1141099013bSjsg mdelay(panel_pwr_delay);
1151099013bSjsg WREG32(RADEON_LVDS_GEN_CNTL, lvds_gen_cntl);
1161099013bSjsg break;
1171099013bSjsg case DRM_MODE_DPMS_STANDBY:
1181099013bSjsg case DRM_MODE_DPMS_SUSPEND:
1191099013bSjsg case DRM_MODE_DPMS_OFF:
1201099013bSjsg pixclks_cntl = RREG32_PLL(RADEON_PIXCLKS_CNTL);
1211099013bSjsg WREG32_PLL_P(RADEON_PIXCLKS_CNTL, 0, ~RADEON_PIXCLK_LVDS_ALWAYS_ONb);
1221099013bSjsg lvds_gen_cntl |= RADEON_LVDS_DISPLAY_DIS;
1231099013bSjsg if (is_mac) {
1241099013bSjsg lvds_gen_cntl &= ~RADEON_LVDS_BL_MOD_EN;
1251099013bSjsg WREG32(RADEON_LVDS_GEN_CNTL, lvds_gen_cntl);
1261099013bSjsg lvds_gen_cntl &= ~(RADEON_LVDS_ON | RADEON_LVDS_EN);
1271099013bSjsg } else {
1281099013bSjsg WREG32(RADEON_LVDS_GEN_CNTL, lvds_gen_cntl);
1291099013bSjsg lvds_gen_cntl &= ~(RADEON_LVDS_ON | RADEON_LVDS_BLON | RADEON_LVDS_EN | RADEON_LVDS_DIGON);
1301099013bSjsg }
1311099013bSjsg mdelay(panel_pwr_delay);
1321099013bSjsg WREG32(RADEON_LVDS_GEN_CNTL, lvds_gen_cntl);
1331099013bSjsg WREG32_PLL(RADEON_PIXCLKS_CNTL, pixclks_cntl);
1341099013bSjsg mdelay(panel_pwr_delay);
1351099013bSjsg break;
1361099013bSjsg }
1371099013bSjsg
1381099013bSjsg if (rdev->is_atom_bios)
1391099013bSjsg radeon_atombios_encoder_dpms_scratch_regs(encoder, (mode == DRM_MODE_DPMS_ON) ? true : false);
1401099013bSjsg else
1411099013bSjsg radeon_combios_encoder_dpms_scratch_regs(encoder, (mode == DRM_MODE_DPMS_ON) ? true : false);
1421099013bSjsg
1431099013bSjsg }
1441099013bSjsg
radeon_legacy_lvds_dpms(struct drm_encoder * encoder,int mode)1451099013bSjsg static void radeon_legacy_lvds_dpms(struct drm_encoder *encoder, int mode)
1461099013bSjsg {
1471099013bSjsg struct radeon_device *rdev = encoder->dev->dev_private;
1481099013bSjsg struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
1491099013bSjsg DRM_DEBUG("\n");
1501099013bSjsg
1511099013bSjsg if (radeon_encoder->enc_priv) {
1521099013bSjsg if (rdev->is_atom_bios) {
1531099013bSjsg struct radeon_encoder_atom_dig *lvds = radeon_encoder->enc_priv;
1541099013bSjsg lvds->dpms_mode = mode;
1551099013bSjsg } else {
1561099013bSjsg struct radeon_encoder_lvds *lvds = radeon_encoder->enc_priv;
1571099013bSjsg lvds->dpms_mode = mode;
1581099013bSjsg }
1591099013bSjsg }
1601099013bSjsg
1611099013bSjsg radeon_legacy_lvds_update(encoder, mode);
1621099013bSjsg }
1631099013bSjsg
radeon_legacy_lvds_prepare(struct drm_encoder * encoder)1641099013bSjsg static void radeon_legacy_lvds_prepare(struct drm_encoder *encoder)
1651099013bSjsg {
1661099013bSjsg struct radeon_device *rdev = encoder->dev->dev_private;
1671099013bSjsg
1681099013bSjsg if (rdev->is_atom_bios)
1691099013bSjsg radeon_atom_output_lock(encoder, true);
1701099013bSjsg else
1711099013bSjsg radeon_combios_output_lock(encoder, true);
1721099013bSjsg radeon_legacy_lvds_dpms(encoder, DRM_MODE_DPMS_OFF);
1731099013bSjsg }
1741099013bSjsg
radeon_legacy_lvds_commit(struct drm_encoder * encoder)1751099013bSjsg static void radeon_legacy_lvds_commit(struct drm_encoder *encoder)
1761099013bSjsg {
1771099013bSjsg struct radeon_device *rdev = encoder->dev->dev_private;
1781099013bSjsg
1791099013bSjsg radeon_legacy_lvds_dpms(encoder, DRM_MODE_DPMS_ON);
1801099013bSjsg if (rdev->is_atom_bios)
1811099013bSjsg radeon_atom_output_lock(encoder, false);
1821099013bSjsg else
1831099013bSjsg radeon_combios_output_lock(encoder, false);
1841099013bSjsg }
1851099013bSjsg
radeon_legacy_lvds_mode_set(struct drm_encoder * encoder,struct drm_display_mode * mode,struct drm_display_mode * adjusted_mode)1861099013bSjsg static void radeon_legacy_lvds_mode_set(struct drm_encoder *encoder,
1871099013bSjsg struct drm_display_mode *mode,
1881099013bSjsg struct drm_display_mode *adjusted_mode)
1891099013bSjsg {
1901099013bSjsg struct drm_device *dev = encoder->dev;
1911099013bSjsg struct radeon_device *rdev = dev->dev_private;
1921099013bSjsg struct radeon_crtc *radeon_crtc = to_radeon_crtc(encoder->crtc);
1931099013bSjsg struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
1941099013bSjsg uint32_t lvds_pll_cntl, lvds_gen_cntl, lvds_ss_gen_cntl;
1951099013bSjsg
1961099013bSjsg DRM_DEBUG_KMS("\n");
1971099013bSjsg
1981099013bSjsg lvds_pll_cntl = RREG32(RADEON_LVDS_PLL_CNTL);
1991099013bSjsg lvds_pll_cntl &= ~RADEON_LVDS_PLL_EN;
2001099013bSjsg
2011099013bSjsg lvds_ss_gen_cntl = RREG32(RADEON_LVDS_SS_GEN_CNTL);
2021099013bSjsg if (rdev->is_atom_bios) {
2031099013bSjsg /* LVDS_GEN_CNTL parameters are computed in LVDSEncoderControl
2041099013bSjsg * need to call that on resume to set up the reg properly.
2051099013bSjsg */
2061099013bSjsg radeon_encoder->pixel_clock = adjusted_mode->clock;
2071099013bSjsg atombios_digital_setup(encoder, PANEL_ENCODER_ACTION_ENABLE);
2081099013bSjsg lvds_gen_cntl = RREG32(RADEON_LVDS_GEN_CNTL);
2091099013bSjsg } else {
2101099013bSjsg struct radeon_encoder_lvds *lvds = (struct radeon_encoder_lvds *)radeon_encoder->enc_priv;
2111099013bSjsg if (lvds) {
2121099013bSjsg DRM_DEBUG_KMS("bios LVDS_GEN_CNTL: 0x%x\n", lvds->lvds_gen_cntl);
2131099013bSjsg lvds_gen_cntl = lvds->lvds_gen_cntl;
2141099013bSjsg lvds_ss_gen_cntl &= ~((0xf << RADEON_LVDS_PWRSEQ_DELAY1_SHIFT) |
2151099013bSjsg (0xf << RADEON_LVDS_PWRSEQ_DELAY2_SHIFT));
2161099013bSjsg lvds_ss_gen_cntl |= ((lvds->panel_digon_delay << RADEON_LVDS_PWRSEQ_DELAY1_SHIFT) |
2171099013bSjsg (lvds->panel_blon_delay << RADEON_LVDS_PWRSEQ_DELAY2_SHIFT));
2181099013bSjsg } else
2191099013bSjsg lvds_gen_cntl = RREG32(RADEON_LVDS_GEN_CNTL);
2201099013bSjsg }
2211099013bSjsg lvds_gen_cntl |= RADEON_LVDS_DISPLAY_DIS;
2221099013bSjsg lvds_gen_cntl &= ~(RADEON_LVDS_ON |
2231099013bSjsg RADEON_LVDS_BLON |
2241099013bSjsg RADEON_LVDS_EN |
2251099013bSjsg RADEON_LVDS_RST_FM);
2261099013bSjsg
2271099013bSjsg if (ASIC_IS_R300(rdev))
2281099013bSjsg lvds_pll_cntl &= ~(R300_LVDS_SRC_SEL_MASK);
2291099013bSjsg
2301099013bSjsg if (radeon_crtc->crtc_id == 0) {
2311099013bSjsg if (ASIC_IS_R300(rdev)) {
2321099013bSjsg if (radeon_encoder->rmx_type != RMX_OFF)
2331099013bSjsg lvds_pll_cntl |= R300_LVDS_SRC_SEL_RMX;
2341099013bSjsg } else
2351099013bSjsg lvds_gen_cntl &= ~RADEON_LVDS_SEL_CRTC2;
2361099013bSjsg } else {
2371099013bSjsg if (ASIC_IS_R300(rdev))
2381099013bSjsg lvds_pll_cntl |= R300_LVDS_SRC_SEL_CRTC2;
2391099013bSjsg else
2401099013bSjsg lvds_gen_cntl |= RADEON_LVDS_SEL_CRTC2;
2411099013bSjsg }
2421099013bSjsg
2431099013bSjsg WREG32(RADEON_LVDS_GEN_CNTL, lvds_gen_cntl);
2441099013bSjsg WREG32(RADEON_LVDS_PLL_CNTL, lvds_pll_cntl);
2451099013bSjsg WREG32(RADEON_LVDS_SS_GEN_CNTL, lvds_ss_gen_cntl);
2461099013bSjsg
2471099013bSjsg if (rdev->family == CHIP_RV410)
2481099013bSjsg WREG32(RADEON_CLOCK_CNTL_INDEX, 0);
2491099013bSjsg
2501099013bSjsg if (rdev->is_atom_bios)
2511099013bSjsg radeon_atombios_encoder_crtc_scratch_regs(encoder, radeon_crtc->crtc_id);
2521099013bSjsg else
2531099013bSjsg radeon_combios_encoder_crtc_scratch_regs(encoder, radeon_crtc->crtc_id);
2541099013bSjsg }
2551099013bSjsg
radeon_legacy_mode_fixup(struct drm_encoder * encoder,const struct drm_display_mode * mode,struct drm_display_mode * adjusted_mode)2561099013bSjsg static bool radeon_legacy_mode_fixup(struct drm_encoder *encoder,
2571099013bSjsg const struct drm_display_mode *mode,
2581099013bSjsg struct drm_display_mode *adjusted_mode)
2591099013bSjsg {
2601099013bSjsg struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
2611099013bSjsg
2621099013bSjsg /* set the active encoder to connector routing */
2631099013bSjsg radeon_encoder_set_active_device(encoder);
2641099013bSjsg drm_mode_set_crtcinfo(adjusted_mode, 0);
2651099013bSjsg
2661099013bSjsg /* get the native mode for LVDS */
2671099013bSjsg if (radeon_encoder->active_device & (ATOM_DEVICE_LCD_SUPPORT))
2681099013bSjsg radeon_panel_mode_fixup(encoder, adjusted_mode);
2691099013bSjsg
2701099013bSjsg return true;
2711099013bSjsg }
2721099013bSjsg
2731099013bSjsg static const struct drm_encoder_helper_funcs radeon_legacy_lvds_helper_funcs = {
2741099013bSjsg .dpms = radeon_legacy_lvds_dpms,
2751099013bSjsg .mode_fixup = radeon_legacy_mode_fixup,
2761099013bSjsg .prepare = radeon_legacy_lvds_prepare,
2771099013bSjsg .mode_set = radeon_legacy_lvds_mode_set,
2781099013bSjsg .commit = radeon_legacy_lvds_commit,
2791099013bSjsg .disable = radeon_legacy_encoder_disable,
2801099013bSjsg };
2811099013bSjsg
2821099013bSjsg u8
radeon_legacy_get_backlight_level(struct radeon_encoder * radeon_encoder)2831099013bSjsg radeon_legacy_get_backlight_level(struct radeon_encoder *radeon_encoder)
2841099013bSjsg {
2851099013bSjsg struct drm_device *dev = radeon_encoder->base.dev;
2861099013bSjsg struct radeon_device *rdev = dev->dev_private;
2871099013bSjsg u8 backlight_level;
2881099013bSjsg
2891099013bSjsg backlight_level = (RREG32(RADEON_LVDS_GEN_CNTL) >>
2901099013bSjsg RADEON_LVDS_BL_MOD_LEVEL_SHIFT) & 0xff;
2911099013bSjsg
2921099013bSjsg return backlight_level;
2931099013bSjsg }
2941099013bSjsg
2951099013bSjsg void
radeon_legacy_set_backlight_level(struct radeon_encoder * radeon_encoder,u8 level)2961099013bSjsg radeon_legacy_set_backlight_level(struct radeon_encoder *radeon_encoder, u8 level)
2971099013bSjsg {
2981099013bSjsg struct drm_device *dev = radeon_encoder->base.dev;
2991099013bSjsg struct radeon_device *rdev = dev->dev_private;
3001099013bSjsg int dpms_mode = DRM_MODE_DPMS_ON;
3011099013bSjsg
3021099013bSjsg if (radeon_encoder->enc_priv) {
3031099013bSjsg if (rdev->is_atom_bios) {
3041099013bSjsg struct radeon_encoder_atom_dig *lvds = radeon_encoder->enc_priv;
3051099013bSjsg if (lvds->backlight_level > 0)
3061099013bSjsg dpms_mode = lvds->dpms_mode;
3071099013bSjsg else
3081099013bSjsg dpms_mode = DRM_MODE_DPMS_OFF;
3091099013bSjsg lvds->backlight_level = level;
3101099013bSjsg } else {
3111099013bSjsg struct radeon_encoder_lvds *lvds = radeon_encoder->enc_priv;
3121099013bSjsg if (lvds->backlight_level > 0)
3131099013bSjsg dpms_mode = lvds->dpms_mode;
3141099013bSjsg else
3151099013bSjsg dpms_mode = DRM_MODE_DPMS_OFF;
3161099013bSjsg lvds->backlight_level = level;
3171099013bSjsg }
3181099013bSjsg }
3191099013bSjsg
3201099013bSjsg radeon_legacy_lvds_update(&radeon_encoder->base, dpms_mode);
3211099013bSjsg }
3221099013bSjsg
radeon_legacy_lvds_level(struct backlight_device * bd)3231099013bSjsg static uint8_t radeon_legacy_lvds_level(struct backlight_device *bd)
3241099013bSjsg {
3251099013bSjsg struct radeon_backlight_privdata *pdata = bl_get_data(bd);
3261099013bSjsg uint8_t level;
3271099013bSjsg
3281099013bSjsg /* Convert brightness to hardware level */
3291099013bSjsg if (bd->props.brightness < 0)
3301099013bSjsg level = 0;
3311099013bSjsg else if (bd->props.brightness > RADEON_MAX_BL_LEVEL)
3321099013bSjsg level = RADEON_MAX_BL_LEVEL;
3331099013bSjsg else
3341099013bSjsg level = bd->props.brightness;
3351099013bSjsg
3361099013bSjsg if (pdata->negative)
3371099013bSjsg level = RADEON_MAX_BL_LEVEL - level;
3381099013bSjsg
3391099013bSjsg return level;
3401099013bSjsg }
3411099013bSjsg
radeon_legacy_backlight_update_status(struct backlight_device * bd)3421099013bSjsg static int radeon_legacy_backlight_update_status(struct backlight_device *bd)
3431099013bSjsg {
3441099013bSjsg struct radeon_backlight_privdata *pdata = bl_get_data(bd);
3451099013bSjsg struct radeon_encoder *radeon_encoder = pdata->encoder;
3461099013bSjsg
3471099013bSjsg radeon_legacy_set_backlight_level(radeon_encoder,
3481099013bSjsg radeon_legacy_lvds_level(bd));
3491099013bSjsg
3501099013bSjsg return 0;
3511099013bSjsg }
3521099013bSjsg
radeon_legacy_backlight_get_brightness(struct backlight_device * bd)3531099013bSjsg static int radeon_legacy_backlight_get_brightness(struct backlight_device *bd)
3541099013bSjsg {
3551099013bSjsg struct radeon_backlight_privdata *pdata = bl_get_data(bd);
3561099013bSjsg struct radeon_encoder *radeon_encoder = pdata->encoder;
3571099013bSjsg struct drm_device *dev = radeon_encoder->base.dev;
3581099013bSjsg struct radeon_device *rdev = dev->dev_private;
3591099013bSjsg uint8_t backlight_level;
3601099013bSjsg
3611099013bSjsg backlight_level = (RREG32(RADEON_LVDS_GEN_CNTL) >>
3621099013bSjsg RADEON_LVDS_BL_MOD_LEVEL_SHIFT) & 0xff;
3631099013bSjsg
3641099013bSjsg return pdata->negative ? RADEON_MAX_BL_LEVEL - backlight_level : backlight_level;
3651099013bSjsg }
3661099013bSjsg
3671099013bSjsg static const struct backlight_ops radeon_backlight_ops = {
3681099013bSjsg .get_brightness = radeon_legacy_backlight_get_brightness,
3691099013bSjsg .update_status = radeon_legacy_backlight_update_status,
3701099013bSjsg };
3711099013bSjsg
radeon_legacy_backlight_init(struct radeon_encoder * radeon_encoder,struct drm_connector * drm_connector)3721099013bSjsg void radeon_legacy_backlight_init(struct radeon_encoder *radeon_encoder,
3731099013bSjsg struct drm_connector *drm_connector)
3741099013bSjsg {
3751099013bSjsg struct drm_device *dev = radeon_encoder->base.dev;
3761099013bSjsg struct radeon_device *rdev = dev->dev_private;
3771099013bSjsg struct backlight_device *bd;
3781099013bSjsg struct backlight_properties props;
3791099013bSjsg struct radeon_backlight_privdata *pdata;
3801099013bSjsg uint8_t backlight_level;
3811099013bSjsg char bl_name[16];
3821099013bSjsg
3831099013bSjsg if (!radeon_encoder->enc_priv)
3841099013bSjsg return;
3851099013bSjsg
3861099013bSjsg #ifdef CONFIG_PMAC_BACKLIGHT
3871099013bSjsg if (!pmac_has_backlight_type("ati") &&
3881099013bSjsg !pmac_has_backlight_type("mnca"))
3891099013bSjsg return;
3901099013bSjsg #endif
3911099013bSjsg
3921bb76ff1Sjsg if (!acpi_video_backlight_use_native()) {
3931bb76ff1Sjsg drm_info(dev, "Skipping radeon legacy LVDS backlight registration\n");
3941bb76ff1Sjsg return;
3951bb76ff1Sjsg }
3961bb76ff1Sjsg
397de5631a0Sjsg pdata = kmalloc(sizeof(struct radeon_backlight_privdata), GFP_KERNEL);
3981099013bSjsg if (!pdata) {
3991099013bSjsg DRM_ERROR("Memory allocation failed\n");
4001099013bSjsg goto error;
4011099013bSjsg }
4021099013bSjsg
4031099013bSjsg memset(&props, 0, sizeof(props));
4041099013bSjsg props.max_brightness = RADEON_MAX_BL_LEVEL;
4051099013bSjsg props.type = BACKLIGHT_RAW;
4061099013bSjsg snprintf(bl_name, sizeof(bl_name),
4071099013bSjsg "radeon_bl%d", dev->primary->index);
4087ccd5a2cSjsg bd = backlight_device_register(bl_name, drm_connector->kdev,
4091099013bSjsg pdata, &radeon_backlight_ops, &props);
4101099013bSjsg if (IS_ERR(bd)) {
4111099013bSjsg DRM_ERROR("Backlight registration failed\n");
4121099013bSjsg goto error;
4131099013bSjsg }
4141099013bSjsg
4151099013bSjsg pdata->encoder = radeon_encoder;
4161099013bSjsg
4171099013bSjsg backlight_level = (RREG32(RADEON_LVDS_GEN_CNTL) >>
4181099013bSjsg RADEON_LVDS_BL_MOD_LEVEL_SHIFT) & 0xff;
4191099013bSjsg
4201099013bSjsg /* First, try to detect backlight level sense based on the assumption
4211099013bSjsg * that firmware set it up at full brightness
4221099013bSjsg */
4231099013bSjsg if (backlight_level == 0)
4241099013bSjsg pdata->negative = true;
4251099013bSjsg else if (backlight_level == 0xff)
4261099013bSjsg pdata->negative = false;
4271099013bSjsg else {
4281099013bSjsg /* XXX hack... maybe some day we can figure out in what direction
4291099013bSjsg * backlight should work on a given panel?
4301099013bSjsg */
4311099013bSjsg pdata->negative = (rdev->family != CHIP_RV200 &&
4321099013bSjsg rdev->family != CHIP_RV250 &&
4331099013bSjsg rdev->family != CHIP_RV280 &&
4341099013bSjsg rdev->family != CHIP_RV350);
4351099013bSjsg
4361099013bSjsg #ifdef CONFIG_PMAC_BACKLIGHT
4371099013bSjsg pdata->negative = (pdata->negative ||
4381099013bSjsg of_machine_is_compatible("PowerBook4,3") ||
4391099013bSjsg of_machine_is_compatible("PowerBook6,3") ||
4401099013bSjsg of_machine_is_compatible("PowerBook6,5"));
4411099013bSjsg #endif
4421099013bSjsg }
4431099013bSjsg
4441099013bSjsg if (rdev->is_atom_bios) {
4451099013bSjsg struct radeon_encoder_atom_dig *lvds = radeon_encoder->enc_priv;
4461099013bSjsg lvds->bl_dev = bd;
4471099013bSjsg } else {
4481099013bSjsg struct radeon_encoder_lvds *lvds = radeon_encoder->enc_priv;
4491099013bSjsg lvds->bl_dev = bd;
4501099013bSjsg }
4511099013bSjsg
4521099013bSjsg bd->props.brightness = radeon_legacy_backlight_get_brightness(bd);
4531099013bSjsg bd->props.power = FB_BLANK_UNBLANK;
4541099013bSjsg backlight_update_status(bd);
4551099013bSjsg
4561099013bSjsg DRM_INFO("radeon legacy LVDS backlight initialized\n");
4577ccd5a2cSjsg rdev->mode_info.bl_encoder = radeon_encoder;
4581099013bSjsg
4591099013bSjsg return;
4601099013bSjsg
4611099013bSjsg error:
462de5631a0Sjsg kfree(pdata);
4631099013bSjsg return;
4641099013bSjsg }
4651099013bSjsg
radeon_legacy_backlight_exit(struct radeon_encoder * radeon_encoder)4661099013bSjsg static void radeon_legacy_backlight_exit(struct radeon_encoder *radeon_encoder)
4671099013bSjsg {
4681099013bSjsg struct drm_device *dev = radeon_encoder->base.dev;
4691099013bSjsg struct radeon_device *rdev = dev->dev_private;
4701099013bSjsg struct backlight_device *bd = NULL;
4711099013bSjsg
4721099013bSjsg if (!radeon_encoder->enc_priv)
4731099013bSjsg return;
4741099013bSjsg
4751099013bSjsg if (rdev->is_atom_bios) {
4761099013bSjsg struct radeon_encoder_atom_dig *lvds = radeon_encoder->enc_priv;
4771099013bSjsg bd = lvds->bl_dev;
4781099013bSjsg lvds->bl_dev = NULL;
4791099013bSjsg } else {
4801099013bSjsg struct radeon_encoder_lvds *lvds = radeon_encoder->enc_priv;
4811099013bSjsg bd = lvds->bl_dev;
4821099013bSjsg lvds->bl_dev = NULL;
4831099013bSjsg }
4841099013bSjsg
4851099013bSjsg if (bd) {
4861099013bSjsg struct radeon_backlight_privdata *pdata;
4871099013bSjsg
4881099013bSjsg pdata = bl_get_data(bd);
4891099013bSjsg backlight_device_unregister(bd);
490de5631a0Sjsg kfree(pdata);
4911099013bSjsg
4921099013bSjsg DRM_INFO("radeon legacy LVDS backlight unloaded\n");
4931099013bSjsg }
4941099013bSjsg }
4951099013bSjsg
radeon_lvds_enc_destroy(struct drm_encoder * encoder)4961099013bSjsg static void radeon_lvds_enc_destroy(struct drm_encoder *encoder)
4971099013bSjsg {
4981099013bSjsg struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
4991099013bSjsg
5001099013bSjsg if (radeon_encoder->enc_priv) {
5011099013bSjsg radeon_legacy_backlight_exit(radeon_encoder);
502de5631a0Sjsg kfree(radeon_encoder->enc_priv);
5031099013bSjsg }
5041099013bSjsg drm_encoder_cleanup(encoder);
505de5631a0Sjsg kfree(radeon_encoder);
5061099013bSjsg }
5071099013bSjsg
5081099013bSjsg static const struct drm_encoder_funcs radeon_legacy_lvds_enc_funcs = {
5091099013bSjsg .destroy = radeon_lvds_enc_destroy,
5101099013bSjsg };
5111099013bSjsg
radeon_legacy_primary_dac_dpms(struct drm_encoder * encoder,int mode)5121099013bSjsg static void radeon_legacy_primary_dac_dpms(struct drm_encoder *encoder, int mode)
5131099013bSjsg {
5141099013bSjsg struct drm_device *dev = encoder->dev;
5151099013bSjsg struct radeon_device *rdev = dev->dev_private;
5161099013bSjsg uint32_t crtc_ext_cntl = RREG32(RADEON_CRTC_EXT_CNTL);
5171099013bSjsg uint32_t dac_cntl = RREG32(RADEON_DAC_CNTL);
5181099013bSjsg uint32_t dac_macro_cntl = RREG32(RADEON_DAC_MACRO_CNTL);
5191099013bSjsg
5201099013bSjsg DRM_DEBUG_KMS("\n");
5211099013bSjsg
5221099013bSjsg switch (mode) {
5231099013bSjsg case DRM_MODE_DPMS_ON:
5241099013bSjsg crtc_ext_cntl |= RADEON_CRTC_CRT_ON;
5251099013bSjsg dac_cntl &= ~RADEON_DAC_PDWN;
5261099013bSjsg dac_macro_cntl &= ~(RADEON_DAC_PDWN_R |
5271099013bSjsg RADEON_DAC_PDWN_G |
5281099013bSjsg RADEON_DAC_PDWN_B);
5291099013bSjsg break;
5301099013bSjsg case DRM_MODE_DPMS_STANDBY:
5311099013bSjsg case DRM_MODE_DPMS_SUSPEND:
5321099013bSjsg case DRM_MODE_DPMS_OFF:
5331099013bSjsg crtc_ext_cntl &= ~RADEON_CRTC_CRT_ON;
5341099013bSjsg dac_cntl |= RADEON_DAC_PDWN;
5351099013bSjsg dac_macro_cntl |= (RADEON_DAC_PDWN_R |
5361099013bSjsg RADEON_DAC_PDWN_G |
5371099013bSjsg RADEON_DAC_PDWN_B);
5381099013bSjsg break;
5391099013bSjsg }
5401099013bSjsg
5411099013bSjsg /* handled in radeon_crtc_dpms() */
5421099013bSjsg if (!(rdev->flags & RADEON_SINGLE_CRTC))
5431099013bSjsg WREG32(RADEON_CRTC_EXT_CNTL, crtc_ext_cntl);
5441099013bSjsg WREG32(RADEON_DAC_CNTL, dac_cntl);
5451099013bSjsg WREG32(RADEON_DAC_MACRO_CNTL, dac_macro_cntl);
5461099013bSjsg
5471099013bSjsg if (rdev->is_atom_bios)
5481099013bSjsg radeon_atombios_encoder_dpms_scratch_regs(encoder, (mode == DRM_MODE_DPMS_ON) ? true : false);
5491099013bSjsg else
5501099013bSjsg radeon_combios_encoder_dpms_scratch_regs(encoder, (mode == DRM_MODE_DPMS_ON) ? true : false);
5511099013bSjsg
5521099013bSjsg }
5531099013bSjsg
radeon_legacy_primary_dac_prepare(struct drm_encoder * encoder)5541099013bSjsg static void radeon_legacy_primary_dac_prepare(struct drm_encoder *encoder)
5551099013bSjsg {
5561099013bSjsg struct radeon_device *rdev = encoder->dev->dev_private;
5571099013bSjsg
5581099013bSjsg if (rdev->is_atom_bios)
5591099013bSjsg radeon_atom_output_lock(encoder, true);
5601099013bSjsg else
5611099013bSjsg radeon_combios_output_lock(encoder, true);
5621099013bSjsg radeon_legacy_primary_dac_dpms(encoder, DRM_MODE_DPMS_OFF);
5631099013bSjsg }
5641099013bSjsg
radeon_legacy_primary_dac_commit(struct drm_encoder * encoder)5651099013bSjsg static void radeon_legacy_primary_dac_commit(struct drm_encoder *encoder)
5661099013bSjsg {
5671099013bSjsg struct radeon_device *rdev = encoder->dev->dev_private;
5681099013bSjsg
5691099013bSjsg radeon_legacy_primary_dac_dpms(encoder, DRM_MODE_DPMS_ON);
5701099013bSjsg
5711099013bSjsg if (rdev->is_atom_bios)
5721099013bSjsg radeon_atom_output_lock(encoder, false);
5731099013bSjsg else
5741099013bSjsg radeon_combios_output_lock(encoder, false);
5751099013bSjsg }
5761099013bSjsg
radeon_legacy_primary_dac_mode_set(struct drm_encoder * encoder,struct drm_display_mode * mode,struct drm_display_mode * adjusted_mode)5771099013bSjsg static void radeon_legacy_primary_dac_mode_set(struct drm_encoder *encoder,
5781099013bSjsg struct drm_display_mode *mode,
5791099013bSjsg struct drm_display_mode *adjusted_mode)
5801099013bSjsg {
5811099013bSjsg struct drm_device *dev = encoder->dev;
5821099013bSjsg struct radeon_device *rdev = dev->dev_private;
5831099013bSjsg struct radeon_crtc *radeon_crtc = to_radeon_crtc(encoder->crtc);
5841099013bSjsg struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
5851099013bSjsg uint32_t disp_output_cntl, dac_cntl, dac2_cntl, dac_macro_cntl;
5861099013bSjsg
5871099013bSjsg DRM_DEBUG_KMS("\n");
5881099013bSjsg
5891099013bSjsg if (radeon_crtc->crtc_id == 0) {
5901099013bSjsg if (rdev->family == CHIP_R200 || ASIC_IS_R300(rdev)) {
5911099013bSjsg disp_output_cntl = RREG32(RADEON_DISP_OUTPUT_CNTL) &
5921099013bSjsg ~(RADEON_DISP_DAC_SOURCE_MASK);
5931099013bSjsg WREG32(RADEON_DISP_OUTPUT_CNTL, disp_output_cntl);
5941099013bSjsg } else {
5951099013bSjsg dac2_cntl = RREG32(RADEON_DAC_CNTL2) & ~(RADEON_DAC2_DAC_CLK_SEL);
5961099013bSjsg WREG32(RADEON_DAC_CNTL2, dac2_cntl);
5971099013bSjsg }
5981099013bSjsg } else {
5991099013bSjsg if (rdev->family == CHIP_R200 || ASIC_IS_R300(rdev)) {
6001099013bSjsg disp_output_cntl = RREG32(RADEON_DISP_OUTPUT_CNTL) &
6011099013bSjsg ~(RADEON_DISP_DAC_SOURCE_MASK);
6021099013bSjsg disp_output_cntl |= RADEON_DISP_DAC_SOURCE_CRTC2;
6031099013bSjsg WREG32(RADEON_DISP_OUTPUT_CNTL, disp_output_cntl);
6041099013bSjsg } else {
6051099013bSjsg dac2_cntl = RREG32(RADEON_DAC_CNTL2) | RADEON_DAC2_DAC_CLK_SEL;
6061099013bSjsg WREG32(RADEON_DAC_CNTL2, dac2_cntl);
6071099013bSjsg }
6081099013bSjsg }
6091099013bSjsg
6101099013bSjsg dac_cntl = (RADEON_DAC_MASK_ALL |
6111099013bSjsg RADEON_DAC_VGA_ADR_EN |
6121099013bSjsg /* TODO 6-bits */
6131099013bSjsg RADEON_DAC_8BIT_EN);
6141099013bSjsg
6151099013bSjsg WREG32_P(RADEON_DAC_CNTL,
6161099013bSjsg dac_cntl,
6171099013bSjsg RADEON_DAC_RANGE_CNTL |
6181099013bSjsg RADEON_DAC_BLANKING);
6191099013bSjsg
6201099013bSjsg if (radeon_encoder->enc_priv) {
6211099013bSjsg struct radeon_encoder_primary_dac *p_dac = (struct radeon_encoder_primary_dac *)radeon_encoder->enc_priv;
6221099013bSjsg dac_macro_cntl = p_dac->ps2_pdac_adj;
6231099013bSjsg } else
6241099013bSjsg dac_macro_cntl = RREG32(RADEON_DAC_MACRO_CNTL);
6251099013bSjsg dac_macro_cntl |= RADEON_DAC_PDWN_R | RADEON_DAC_PDWN_G | RADEON_DAC_PDWN_B;
6261099013bSjsg WREG32(RADEON_DAC_MACRO_CNTL, dac_macro_cntl);
6271099013bSjsg
6281099013bSjsg if (rdev->is_atom_bios)
6291099013bSjsg radeon_atombios_encoder_crtc_scratch_regs(encoder, radeon_crtc->crtc_id);
6301099013bSjsg else
6311099013bSjsg radeon_combios_encoder_crtc_scratch_regs(encoder, radeon_crtc->crtc_id);
6321099013bSjsg }
6331099013bSjsg
radeon_legacy_primary_dac_detect(struct drm_encoder * encoder,struct drm_connector * connector)6341099013bSjsg static enum drm_connector_status radeon_legacy_primary_dac_detect(struct drm_encoder *encoder,
6351099013bSjsg struct drm_connector *connector)
6361099013bSjsg {
6371099013bSjsg struct drm_device *dev = encoder->dev;
6381099013bSjsg struct radeon_device *rdev = dev->dev_private;
6391099013bSjsg uint32_t vclk_ecp_cntl, crtc_ext_cntl;
6401099013bSjsg uint32_t dac_ext_cntl, dac_cntl, dac_macro_cntl, tmp;
6411099013bSjsg enum drm_connector_status found = connector_status_disconnected;
6421099013bSjsg bool color = true;
6431099013bSjsg
6441099013bSjsg /* just don't bother on RN50 those chip are often connected to remoting
6451099013bSjsg * console hw and often we get failure to load detect those. So to make
6461099013bSjsg * everyone happy report the encoder as always connected.
6471099013bSjsg */
6481099013bSjsg if (ASIC_IS_RN50(rdev)) {
6491099013bSjsg return connector_status_connected;
6501099013bSjsg }
6511099013bSjsg
6521099013bSjsg /* save the regs we need */
6531099013bSjsg vclk_ecp_cntl = RREG32_PLL(RADEON_VCLK_ECP_CNTL);
6541099013bSjsg crtc_ext_cntl = RREG32(RADEON_CRTC_EXT_CNTL);
6551099013bSjsg dac_ext_cntl = RREG32(RADEON_DAC_EXT_CNTL);
6561099013bSjsg dac_cntl = RREG32(RADEON_DAC_CNTL);
6571099013bSjsg dac_macro_cntl = RREG32(RADEON_DAC_MACRO_CNTL);
6581099013bSjsg
6591099013bSjsg tmp = vclk_ecp_cntl &
6601099013bSjsg ~(RADEON_PIXCLK_ALWAYS_ONb | RADEON_PIXCLK_DAC_ALWAYS_ONb);
6611099013bSjsg WREG32_PLL(RADEON_VCLK_ECP_CNTL, tmp);
6621099013bSjsg
6631099013bSjsg tmp = crtc_ext_cntl | RADEON_CRTC_CRT_ON;
6641099013bSjsg WREG32(RADEON_CRTC_EXT_CNTL, tmp);
6651099013bSjsg
6661099013bSjsg tmp = RADEON_DAC_FORCE_BLANK_OFF_EN |
6671099013bSjsg RADEON_DAC_FORCE_DATA_EN;
6681099013bSjsg
6691099013bSjsg if (color)
6701099013bSjsg tmp |= RADEON_DAC_FORCE_DATA_SEL_RGB;
6711099013bSjsg else
6721099013bSjsg tmp |= RADEON_DAC_FORCE_DATA_SEL_G;
6731099013bSjsg
6741099013bSjsg if (ASIC_IS_R300(rdev))
6751099013bSjsg tmp |= (0x1b6 << RADEON_DAC_FORCE_DATA_SHIFT);
6761099013bSjsg else if (ASIC_IS_RV100(rdev))
6771099013bSjsg tmp |= (0x1ac << RADEON_DAC_FORCE_DATA_SHIFT);
6781099013bSjsg else
6791099013bSjsg tmp |= (0x180 << RADEON_DAC_FORCE_DATA_SHIFT);
6801099013bSjsg
6811099013bSjsg WREG32(RADEON_DAC_EXT_CNTL, tmp);
6821099013bSjsg
6831099013bSjsg tmp = dac_cntl & ~(RADEON_DAC_RANGE_CNTL_MASK | RADEON_DAC_PDWN);
6841099013bSjsg tmp |= RADEON_DAC_RANGE_CNTL_PS2 | RADEON_DAC_CMP_EN;
6851099013bSjsg WREG32(RADEON_DAC_CNTL, tmp);
6861099013bSjsg
6871099013bSjsg tmp = dac_macro_cntl;
6881099013bSjsg tmp &= ~(RADEON_DAC_PDWN_R |
6891099013bSjsg RADEON_DAC_PDWN_G |
6901099013bSjsg RADEON_DAC_PDWN_B);
6911099013bSjsg
6921099013bSjsg WREG32(RADEON_DAC_MACRO_CNTL, tmp);
6931099013bSjsg
6941099013bSjsg mdelay(2);
6951099013bSjsg
6961099013bSjsg if (RREG32(RADEON_DAC_CNTL) & RADEON_DAC_CMP_OUTPUT)
6971099013bSjsg found = connector_status_connected;
6981099013bSjsg
6991099013bSjsg /* restore the regs we used */
7001099013bSjsg WREG32(RADEON_DAC_CNTL, dac_cntl);
7011099013bSjsg WREG32(RADEON_DAC_MACRO_CNTL, dac_macro_cntl);
7021099013bSjsg WREG32(RADEON_DAC_EXT_CNTL, dac_ext_cntl);
7031099013bSjsg WREG32(RADEON_CRTC_EXT_CNTL, crtc_ext_cntl);
7041099013bSjsg WREG32_PLL(RADEON_VCLK_ECP_CNTL, vclk_ecp_cntl);
7051099013bSjsg
7061099013bSjsg return found;
7071099013bSjsg }
7081099013bSjsg
7091099013bSjsg static const struct drm_encoder_helper_funcs radeon_legacy_primary_dac_helper_funcs = {
7101099013bSjsg .dpms = radeon_legacy_primary_dac_dpms,
7111099013bSjsg .mode_fixup = radeon_legacy_mode_fixup,
7121099013bSjsg .prepare = radeon_legacy_primary_dac_prepare,
7131099013bSjsg .mode_set = radeon_legacy_primary_dac_mode_set,
7141099013bSjsg .commit = radeon_legacy_primary_dac_commit,
7151099013bSjsg .detect = radeon_legacy_primary_dac_detect,
7161099013bSjsg .disable = radeon_legacy_encoder_disable,
7171099013bSjsg };
7181099013bSjsg
7191099013bSjsg
7201099013bSjsg static const struct drm_encoder_funcs radeon_legacy_primary_dac_enc_funcs = {
7211099013bSjsg .destroy = radeon_enc_destroy,
7221099013bSjsg };
7231099013bSjsg
radeon_legacy_tmds_int_dpms(struct drm_encoder * encoder,int mode)7241099013bSjsg static void radeon_legacy_tmds_int_dpms(struct drm_encoder *encoder, int mode)
7251099013bSjsg {
7261099013bSjsg struct drm_device *dev = encoder->dev;
7271099013bSjsg struct radeon_device *rdev = dev->dev_private;
7281099013bSjsg uint32_t fp_gen_cntl = RREG32(RADEON_FP_GEN_CNTL);
7291099013bSjsg DRM_DEBUG_KMS("\n");
7301099013bSjsg
7311099013bSjsg switch (mode) {
7321099013bSjsg case DRM_MODE_DPMS_ON:
7331099013bSjsg fp_gen_cntl |= (RADEON_FP_FPON | RADEON_FP_TMDS_EN);
7341099013bSjsg break;
7351099013bSjsg case DRM_MODE_DPMS_STANDBY:
7361099013bSjsg case DRM_MODE_DPMS_SUSPEND:
7371099013bSjsg case DRM_MODE_DPMS_OFF:
7381099013bSjsg fp_gen_cntl &= ~(RADEON_FP_FPON | RADEON_FP_TMDS_EN);
7391099013bSjsg break;
7401099013bSjsg }
7411099013bSjsg
7421099013bSjsg WREG32(RADEON_FP_GEN_CNTL, fp_gen_cntl);
7431099013bSjsg
7441099013bSjsg if (rdev->is_atom_bios)
7451099013bSjsg radeon_atombios_encoder_dpms_scratch_regs(encoder, (mode == DRM_MODE_DPMS_ON) ? true : false);
7461099013bSjsg else
7471099013bSjsg radeon_combios_encoder_dpms_scratch_regs(encoder, (mode == DRM_MODE_DPMS_ON) ? true : false);
7481099013bSjsg
7491099013bSjsg }
7501099013bSjsg
radeon_legacy_tmds_int_prepare(struct drm_encoder * encoder)7511099013bSjsg static void radeon_legacy_tmds_int_prepare(struct drm_encoder *encoder)
7521099013bSjsg {
7531099013bSjsg struct radeon_device *rdev = encoder->dev->dev_private;
7541099013bSjsg
7551099013bSjsg if (rdev->is_atom_bios)
7561099013bSjsg radeon_atom_output_lock(encoder, true);
7571099013bSjsg else
7581099013bSjsg radeon_combios_output_lock(encoder, true);
7591099013bSjsg radeon_legacy_tmds_int_dpms(encoder, DRM_MODE_DPMS_OFF);
7601099013bSjsg }
7611099013bSjsg
radeon_legacy_tmds_int_commit(struct drm_encoder * encoder)7621099013bSjsg static void radeon_legacy_tmds_int_commit(struct drm_encoder *encoder)
7631099013bSjsg {
7641099013bSjsg struct radeon_device *rdev = encoder->dev->dev_private;
7651099013bSjsg
7661099013bSjsg radeon_legacy_tmds_int_dpms(encoder, DRM_MODE_DPMS_ON);
7671099013bSjsg
7681099013bSjsg if (rdev->is_atom_bios)
7691099013bSjsg radeon_atom_output_lock(encoder, true);
7701099013bSjsg else
7711099013bSjsg radeon_combios_output_lock(encoder, true);
7721099013bSjsg }
7731099013bSjsg
radeon_legacy_tmds_int_mode_set(struct drm_encoder * encoder,struct drm_display_mode * mode,struct drm_display_mode * adjusted_mode)7741099013bSjsg static void radeon_legacy_tmds_int_mode_set(struct drm_encoder *encoder,
7751099013bSjsg struct drm_display_mode *mode,
7761099013bSjsg struct drm_display_mode *adjusted_mode)
7771099013bSjsg {
7781099013bSjsg struct drm_device *dev = encoder->dev;
7791099013bSjsg struct radeon_device *rdev = dev->dev_private;
7801099013bSjsg struct radeon_crtc *radeon_crtc = to_radeon_crtc(encoder->crtc);
7811099013bSjsg struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
7821099013bSjsg uint32_t tmp, tmds_pll_cntl, tmds_transmitter_cntl, fp_gen_cntl;
7831099013bSjsg int i;
7841099013bSjsg
7851099013bSjsg DRM_DEBUG_KMS("\n");
7861099013bSjsg
7871099013bSjsg tmp = tmds_pll_cntl = RREG32(RADEON_TMDS_PLL_CNTL);
7881099013bSjsg tmp &= 0xfffff;
7891099013bSjsg if (rdev->family == CHIP_RV280) {
7901099013bSjsg /* bit 22 of TMDS_PLL_CNTL is read-back inverted */
7911099013bSjsg tmp ^= (1 << 22);
7921099013bSjsg tmds_pll_cntl ^= (1 << 22);
7931099013bSjsg }
7941099013bSjsg
7951099013bSjsg if (radeon_encoder->enc_priv) {
7961099013bSjsg struct radeon_encoder_int_tmds *tmds = (struct radeon_encoder_int_tmds *)radeon_encoder->enc_priv;
7971099013bSjsg
7981099013bSjsg for (i = 0; i < 4; i++) {
7991099013bSjsg if (tmds->tmds_pll[i].freq == 0)
8001099013bSjsg break;
8011099013bSjsg if ((uint32_t)(mode->clock / 10) < tmds->tmds_pll[i].freq) {
8021099013bSjsg tmp = tmds->tmds_pll[i].value ;
8031099013bSjsg break;
8041099013bSjsg }
8051099013bSjsg }
8061099013bSjsg }
8071099013bSjsg
8081099013bSjsg if (ASIC_IS_R300(rdev) || (rdev->family == CHIP_RV280)) {
8091099013bSjsg if (tmp & 0xfff00000)
8101099013bSjsg tmds_pll_cntl = tmp;
8111099013bSjsg else {
8121099013bSjsg tmds_pll_cntl &= 0xfff00000;
8131099013bSjsg tmds_pll_cntl |= tmp;
8141099013bSjsg }
8151099013bSjsg } else
8161099013bSjsg tmds_pll_cntl = tmp;
8171099013bSjsg
8181099013bSjsg tmds_transmitter_cntl = RREG32(RADEON_TMDS_TRANSMITTER_CNTL) &
8191099013bSjsg ~(RADEON_TMDS_TRANSMITTER_PLLRST);
8201099013bSjsg
8211099013bSjsg if (rdev->family == CHIP_R200 ||
8221099013bSjsg rdev->family == CHIP_R100 ||
8231099013bSjsg ASIC_IS_R300(rdev))
8241099013bSjsg tmds_transmitter_cntl &= ~(RADEON_TMDS_TRANSMITTER_PLLEN);
8251099013bSjsg else /* RV chips got this bit reversed */
8261099013bSjsg tmds_transmitter_cntl |= RADEON_TMDS_TRANSMITTER_PLLEN;
8271099013bSjsg
8281099013bSjsg fp_gen_cntl = (RREG32(RADEON_FP_GEN_CNTL) |
8291099013bSjsg (RADEON_FP_CRTC_DONT_SHADOW_VPAR |
8301099013bSjsg RADEON_FP_CRTC_DONT_SHADOW_HEND));
8311099013bSjsg
8321099013bSjsg fp_gen_cntl &= ~(RADEON_FP_FPON | RADEON_FP_TMDS_EN);
8331099013bSjsg
8341099013bSjsg fp_gen_cntl &= ~(RADEON_FP_RMX_HVSYNC_CONTROL_EN |
8351099013bSjsg RADEON_FP_DFP_SYNC_SEL |
8361099013bSjsg RADEON_FP_CRT_SYNC_SEL |
8371099013bSjsg RADEON_FP_CRTC_LOCK_8DOT |
8381099013bSjsg RADEON_FP_USE_SHADOW_EN |
8391099013bSjsg RADEON_FP_CRTC_USE_SHADOW_VEND |
8401099013bSjsg RADEON_FP_CRT_SYNC_ALT);
8411099013bSjsg
8421099013bSjsg if (1) /* FIXME rgbBits == 8 */
8431099013bSjsg fp_gen_cntl |= RADEON_FP_PANEL_FORMAT; /* 24 bit format */
8441099013bSjsg else
8451099013bSjsg fp_gen_cntl &= ~RADEON_FP_PANEL_FORMAT;/* 18 bit format */
8461099013bSjsg
8471099013bSjsg if (radeon_crtc->crtc_id == 0) {
8481099013bSjsg if (ASIC_IS_R300(rdev) || rdev->family == CHIP_R200) {
8491099013bSjsg fp_gen_cntl &= ~R200_FP_SOURCE_SEL_MASK;
8501099013bSjsg if (radeon_encoder->rmx_type != RMX_OFF)
8511099013bSjsg fp_gen_cntl |= R200_FP_SOURCE_SEL_RMX;
8521099013bSjsg else
8531099013bSjsg fp_gen_cntl |= R200_FP_SOURCE_SEL_CRTC1;
8541099013bSjsg } else
8551099013bSjsg fp_gen_cntl &= ~RADEON_FP_SEL_CRTC2;
8561099013bSjsg } else {
8571099013bSjsg if (ASIC_IS_R300(rdev) || rdev->family == CHIP_R200) {
8581099013bSjsg fp_gen_cntl &= ~R200_FP_SOURCE_SEL_MASK;
8591099013bSjsg fp_gen_cntl |= R200_FP_SOURCE_SEL_CRTC2;
8601099013bSjsg } else
8611099013bSjsg fp_gen_cntl |= RADEON_FP_SEL_CRTC2;
8621099013bSjsg }
8631099013bSjsg
8641099013bSjsg WREG32(RADEON_TMDS_PLL_CNTL, tmds_pll_cntl);
8651099013bSjsg WREG32(RADEON_TMDS_TRANSMITTER_CNTL, tmds_transmitter_cntl);
8661099013bSjsg WREG32(RADEON_FP_GEN_CNTL, fp_gen_cntl);
8671099013bSjsg
8681099013bSjsg if (rdev->is_atom_bios)
8691099013bSjsg radeon_atombios_encoder_crtc_scratch_regs(encoder, radeon_crtc->crtc_id);
8701099013bSjsg else
8711099013bSjsg radeon_combios_encoder_crtc_scratch_regs(encoder, radeon_crtc->crtc_id);
8721099013bSjsg }
8731099013bSjsg
8741099013bSjsg static const struct drm_encoder_helper_funcs radeon_legacy_tmds_int_helper_funcs = {
8751099013bSjsg .dpms = radeon_legacy_tmds_int_dpms,
8761099013bSjsg .mode_fixup = radeon_legacy_mode_fixup,
8771099013bSjsg .prepare = radeon_legacy_tmds_int_prepare,
8781099013bSjsg .mode_set = radeon_legacy_tmds_int_mode_set,
8791099013bSjsg .commit = radeon_legacy_tmds_int_commit,
8801099013bSjsg .disable = radeon_legacy_encoder_disable,
8811099013bSjsg };
8821099013bSjsg
8831099013bSjsg
8841099013bSjsg static const struct drm_encoder_funcs radeon_legacy_tmds_int_enc_funcs = {
8851099013bSjsg .destroy = radeon_enc_destroy,
8861099013bSjsg };
8871099013bSjsg
radeon_legacy_tmds_ext_dpms(struct drm_encoder * encoder,int mode)8881099013bSjsg static void radeon_legacy_tmds_ext_dpms(struct drm_encoder *encoder, int mode)
8891099013bSjsg {
8901099013bSjsg struct drm_device *dev = encoder->dev;
8911099013bSjsg struct radeon_device *rdev = dev->dev_private;
8921099013bSjsg uint32_t fp2_gen_cntl = RREG32(RADEON_FP2_GEN_CNTL);
8931099013bSjsg DRM_DEBUG_KMS("\n");
8941099013bSjsg
8951099013bSjsg switch (mode) {
8961099013bSjsg case DRM_MODE_DPMS_ON:
8971099013bSjsg fp2_gen_cntl &= ~RADEON_FP2_BLANK_EN;
8981099013bSjsg fp2_gen_cntl |= (RADEON_FP2_ON | RADEON_FP2_DVO_EN);
8991099013bSjsg break;
9001099013bSjsg case DRM_MODE_DPMS_STANDBY:
9011099013bSjsg case DRM_MODE_DPMS_SUSPEND:
9021099013bSjsg case DRM_MODE_DPMS_OFF:
9031099013bSjsg fp2_gen_cntl |= RADEON_FP2_BLANK_EN;
9041099013bSjsg fp2_gen_cntl &= ~(RADEON_FP2_ON | RADEON_FP2_DVO_EN);
9051099013bSjsg break;
9061099013bSjsg }
9071099013bSjsg
9081099013bSjsg WREG32(RADEON_FP2_GEN_CNTL, fp2_gen_cntl);
9091099013bSjsg
9101099013bSjsg if (rdev->is_atom_bios)
9111099013bSjsg radeon_atombios_encoder_dpms_scratch_regs(encoder, (mode == DRM_MODE_DPMS_ON) ? true : false);
9121099013bSjsg else
9131099013bSjsg radeon_combios_encoder_dpms_scratch_regs(encoder, (mode == DRM_MODE_DPMS_ON) ? true : false);
9141099013bSjsg
9151099013bSjsg }
9161099013bSjsg
radeon_legacy_tmds_ext_prepare(struct drm_encoder * encoder)9171099013bSjsg static void radeon_legacy_tmds_ext_prepare(struct drm_encoder *encoder)
9181099013bSjsg {
9191099013bSjsg struct radeon_device *rdev = encoder->dev->dev_private;
9201099013bSjsg
9211099013bSjsg if (rdev->is_atom_bios)
9221099013bSjsg radeon_atom_output_lock(encoder, true);
9231099013bSjsg else
9241099013bSjsg radeon_combios_output_lock(encoder, true);
9251099013bSjsg radeon_legacy_tmds_ext_dpms(encoder, DRM_MODE_DPMS_OFF);
9261099013bSjsg }
9271099013bSjsg
radeon_legacy_tmds_ext_commit(struct drm_encoder * encoder)9281099013bSjsg static void radeon_legacy_tmds_ext_commit(struct drm_encoder *encoder)
9291099013bSjsg {
9301099013bSjsg struct radeon_device *rdev = encoder->dev->dev_private;
9311099013bSjsg radeon_legacy_tmds_ext_dpms(encoder, DRM_MODE_DPMS_ON);
9321099013bSjsg
9331099013bSjsg if (rdev->is_atom_bios)
9341099013bSjsg radeon_atom_output_lock(encoder, false);
9351099013bSjsg else
9361099013bSjsg radeon_combios_output_lock(encoder, false);
9371099013bSjsg }
9381099013bSjsg
radeon_legacy_tmds_ext_mode_set(struct drm_encoder * encoder,struct drm_display_mode * mode,struct drm_display_mode * adjusted_mode)9391099013bSjsg static void radeon_legacy_tmds_ext_mode_set(struct drm_encoder *encoder,
9401099013bSjsg struct drm_display_mode *mode,
9411099013bSjsg struct drm_display_mode *adjusted_mode)
9421099013bSjsg {
9431099013bSjsg struct drm_device *dev = encoder->dev;
9441099013bSjsg struct radeon_device *rdev = dev->dev_private;
9451099013bSjsg struct radeon_crtc *radeon_crtc = to_radeon_crtc(encoder->crtc);
9461099013bSjsg struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
9471099013bSjsg uint32_t fp2_gen_cntl;
9481099013bSjsg
9491099013bSjsg DRM_DEBUG_KMS("\n");
9501099013bSjsg
9511099013bSjsg if (rdev->is_atom_bios) {
9521099013bSjsg radeon_encoder->pixel_clock = adjusted_mode->clock;
9531099013bSjsg atombios_dvo_setup(encoder, ATOM_ENABLE);
9541099013bSjsg fp2_gen_cntl = RREG32(RADEON_FP2_GEN_CNTL);
9551099013bSjsg } else {
9561099013bSjsg fp2_gen_cntl = RREG32(RADEON_FP2_GEN_CNTL);
9571099013bSjsg
9581099013bSjsg if (1) /* FIXME rgbBits == 8 */
9591099013bSjsg fp2_gen_cntl |= RADEON_FP2_PANEL_FORMAT; /* 24 bit format, */
9601099013bSjsg else
9611099013bSjsg fp2_gen_cntl &= ~RADEON_FP2_PANEL_FORMAT;/* 18 bit format, */
9621099013bSjsg
9631099013bSjsg fp2_gen_cntl &= ~(RADEON_FP2_ON |
9641099013bSjsg RADEON_FP2_DVO_EN |
9651099013bSjsg RADEON_FP2_DVO_RATE_SEL_SDR);
9661099013bSjsg
9671099013bSjsg /* XXX: these are oem specific */
9681099013bSjsg if (ASIC_IS_R300(rdev)) {
9695ca02815Sjsg if ((rdev->pdev->device == 0x4850) &&
9705ca02815Sjsg (rdev->pdev->subsystem_vendor == 0x1028) &&
9715ca02815Sjsg (rdev->pdev->subsystem_device == 0x2001)) /* Dell Inspiron 8600 */
9721099013bSjsg fp2_gen_cntl |= R300_FP2_DVO_CLOCK_MODE_SINGLE;
9731099013bSjsg else
9741099013bSjsg fp2_gen_cntl |= RADEON_FP2_PAD_FLOP_EN | R300_FP2_DVO_CLOCK_MODE_SINGLE;
9751099013bSjsg
9761099013bSjsg /*if (mode->clock > 165000)
9771099013bSjsg fp2_gen_cntl |= R300_FP2_DVO_DUAL_CHANNEL_EN;*/
9781099013bSjsg }
9791099013bSjsg if (!radeon_combios_external_tmds_setup(encoder))
9801099013bSjsg radeon_external_tmds_setup(encoder);
9811099013bSjsg }
9821099013bSjsg
9831099013bSjsg if (radeon_crtc->crtc_id == 0) {
9841099013bSjsg if ((rdev->family == CHIP_R200) || ASIC_IS_R300(rdev)) {
9851099013bSjsg fp2_gen_cntl &= ~R200_FP2_SOURCE_SEL_MASK;
9861099013bSjsg if (radeon_encoder->rmx_type != RMX_OFF)
9871099013bSjsg fp2_gen_cntl |= R200_FP2_SOURCE_SEL_RMX;
9881099013bSjsg else
9891099013bSjsg fp2_gen_cntl |= R200_FP2_SOURCE_SEL_CRTC1;
9901099013bSjsg } else
9911099013bSjsg fp2_gen_cntl &= ~RADEON_FP2_SRC_SEL_CRTC2;
9921099013bSjsg } else {
9931099013bSjsg if ((rdev->family == CHIP_R200) || ASIC_IS_R300(rdev)) {
9941099013bSjsg fp2_gen_cntl &= ~R200_FP2_SOURCE_SEL_MASK;
9951099013bSjsg fp2_gen_cntl |= R200_FP2_SOURCE_SEL_CRTC2;
9961099013bSjsg } else
9971099013bSjsg fp2_gen_cntl |= RADEON_FP2_SRC_SEL_CRTC2;
9981099013bSjsg }
9991099013bSjsg
10001099013bSjsg WREG32(RADEON_FP2_GEN_CNTL, fp2_gen_cntl);
10011099013bSjsg
10021099013bSjsg if (rdev->is_atom_bios)
10031099013bSjsg radeon_atombios_encoder_crtc_scratch_regs(encoder, radeon_crtc->crtc_id);
10041099013bSjsg else
10051099013bSjsg radeon_combios_encoder_crtc_scratch_regs(encoder, radeon_crtc->crtc_id);
10061099013bSjsg }
10071099013bSjsg
radeon_ext_tmds_enc_destroy(struct drm_encoder * encoder)10081099013bSjsg static void radeon_ext_tmds_enc_destroy(struct drm_encoder *encoder)
10091099013bSjsg {
10101099013bSjsg struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
10111099013bSjsg /* don't destroy the i2c bus record here, this will be done in radeon_i2c_fini */
1012de5631a0Sjsg kfree(radeon_encoder->enc_priv);
10131099013bSjsg drm_encoder_cleanup(encoder);
1014de5631a0Sjsg kfree(radeon_encoder);
10151099013bSjsg }
10161099013bSjsg
10171099013bSjsg static const struct drm_encoder_helper_funcs radeon_legacy_tmds_ext_helper_funcs = {
10181099013bSjsg .dpms = radeon_legacy_tmds_ext_dpms,
10191099013bSjsg .mode_fixup = radeon_legacy_mode_fixup,
10201099013bSjsg .prepare = radeon_legacy_tmds_ext_prepare,
10211099013bSjsg .mode_set = radeon_legacy_tmds_ext_mode_set,
10221099013bSjsg .commit = radeon_legacy_tmds_ext_commit,
10231099013bSjsg .disable = radeon_legacy_encoder_disable,
10241099013bSjsg };
10251099013bSjsg
10261099013bSjsg
10271099013bSjsg static const struct drm_encoder_funcs radeon_legacy_tmds_ext_enc_funcs = {
10281099013bSjsg .destroy = radeon_ext_tmds_enc_destroy,
10291099013bSjsg };
10301099013bSjsg
radeon_legacy_tv_dac_dpms(struct drm_encoder * encoder,int mode)10311099013bSjsg static void radeon_legacy_tv_dac_dpms(struct drm_encoder *encoder, int mode)
10321099013bSjsg {
10331099013bSjsg struct drm_device *dev = encoder->dev;
10341099013bSjsg struct radeon_device *rdev = dev->dev_private;
10351099013bSjsg struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
10361099013bSjsg uint32_t fp2_gen_cntl = 0, crtc2_gen_cntl = 0, tv_dac_cntl = 0;
10371099013bSjsg uint32_t tv_master_cntl = 0;
10381099013bSjsg bool is_tv;
10391099013bSjsg DRM_DEBUG_KMS("\n");
10401099013bSjsg
10411099013bSjsg is_tv = radeon_encoder->active_device & ATOM_DEVICE_TV_SUPPORT ? true : false;
10421099013bSjsg
10431099013bSjsg if (rdev->family == CHIP_R200)
10441099013bSjsg fp2_gen_cntl = RREG32(RADEON_FP2_GEN_CNTL);
10451099013bSjsg else {
10461099013bSjsg if (is_tv)
10471099013bSjsg tv_master_cntl = RREG32(RADEON_TV_MASTER_CNTL);
10481099013bSjsg else
10491099013bSjsg crtc2_gen_cntl = RREG32(RADEON_CRTC2_GEN_CNTL);
10501099013bSjsg tv_dac_cntl = RREG32(RADEON_TV_DAC_CNTL);
10511099013bSjsg }
10521099013bSjsg
10531099013bSjsg switch (mode) {
10541099013bSjsg case DRM_MODE_DPMS_ON:
10551099013bSjsg if (rdev->family == CHIP_R200) {
10561099013bSjsg fp2_gen_cntl |= (RADEON_FP2_ON | RADEON_FP2_DVO_EN);
10571099013bSjsg } else {
10581099013bSjsg if (is_tv)
10591099013bSjsg tv_master_cntl |= RADEON_TV_ON;
10601099013bSjsg else
10611099013bSjsg crtc2_gen_cntl |= RADEON_CRTC2_CRT2_ON;
10621099013bSjsg
10631099013bSjsg if (rdev->family == CHIP_R420 ||
10641099013bSjsg rdev->family == CHIP_R423 ||
10651099013bSjsg rdev->family == CHIP_RV410)
10661099013bSjsg tv_dac_cntl &= ~(R420_TV_DAC_RDACPD |
10671099013bSjsg R420_TV_DAC_GDACPD |
10681099013bSjsg R420_TV_DAC_BDACPD |
10691099013bSjsg RADEON_TV_DAC_BGSLEEP);
10701099013bSjsg else
10711099013bSjsg tv_dac_cntl &= ~(RADEON_TV_DAC_RDACPD |
10721099013bSjsg RADEON_TV_DAC_GDACPD |
10731099013bSjsg RADEON_TV_DAC_BDACPD |
10741099013bSjsg RADEON_TV_DAC_BGSLEEP);
10751099013bSjsg }
10761099013bSjsg break;
10771099013bSjsg case DRM_MODE_DPMS_STANDBY:
10781099013bSjsg case DRM_MODE_DPMS_SUSPEND:
10791099013bSjsg case DRM_MODE_DPMS_OFF:
10801099013bSjsg if (rdev->family == CHIP_R200)
10811099013bSjsg fp2_gen_cntl &= ~(RADEON_FP2_ON | RADEON_FP2_DVO_EN);
10821099013bSjsg else {
10831099013bSjsg if (is_tv)
10841099013bSjsg tv_master_cntl &= ~RADEON_TV_ON;
10851099013bSjsg else
10861099013bSjsg crtc2_gen_cntl &= ~RADEON_CRTC2_CRT2_ON;
10871099013bSjsg
10881099013bSjsg if (rdev->family == CHIP_R420 ||
10891099013bSjsg rdev->family == CHIP_R423 ||
10901099013bSjsg rdev->family == CHIP_RV410)
10911099013bSjsg tv_dac_cntl |= (R420_TV_DAC_RDACPD |
10921099013bSjsg R420_TV_DAC_GDACPD |
10931099013bSjsg R420_TV_DAC_BDACPD |
10941099013bSjsg RADEON_TV_DAC_BGSLEEP);
10951099013bSjsg else
10961099013bSjsg tv_dac_cntl |= (RADEON_TV_DAC_RDACPD |
10971099013bSjsg RADEON_TV_DAC_GDACPD |
10981099013bSjsg RADEON_TV_DAC_BDACPD |
10991099013bSjsg RADEON_TV_DAC_BGSLEEP);
11001099013bSjsg }
11011099013bSjsg break;
11021099013bSjsg }
11031099013bSjsg
11041099013bSjsg if (rdev->family == CHIP_R200) {
11051099013bSjsg WREG32(RADEON_FP2_GEN_CNTL, fp2_gen_cntl);
11061099013bSjsg } else {
11071099013bSjsg if (is_tv)
11081099013bSjsg WREG32(RADEON_TV_MASTER_CNTL, tv_master_cntl);
11091099013bSjsg /* handled in radeon_crtc_dpms() */
11101099013bSjsg else if (!(rdev->flags & RADEON_SINGLE_CRTC))
11111099013bSjsg WREG32(RADEON_CRTC2_GEN_CNTL, crtc2_gen_cntl);
11121099013bSjsg WREG32(RADEON_TV_DAC_CNTL, tv_dac_cntl);
11131099013bSjsg }
11141099013bSjsg
11151099013bSjsg if (rdev->is_atom_bios)
11161099013bSjsg radeon_atombios_encoder_dpms_scratch_regs(encoder, (mode == DRM_MODE_DPMS_ON) ? true : false);
11171099013bSjsg else
11181099013bSjsg radeon_combios_encoder_dpms_scratch_regs(encoder, (mode == DRM_MODE_DPMS_ON) ? true : false);
11191099013bSjsg
11201099013bSjsg }
11211099013bSjsg
radeon_legacy_tv_dac_prepare(struct drm_encoder * encoder)11221099013bSjsg static void radeon_legacy_tv_dac_prepare(struct drm_encoder *encoder)
11231099013bSjsg {
11241099013bSjsg struct radeon_device *rdev = encoder->dev->dev_private;
11251099013bSjsg
11261099013bSjsg if (rdev->is_atom_bios)
11271099013bSjsg radeon_atom_output_lock(encoder, true);
11281099013bSjsg else
11291099013bSjsg radeon_combios_output_lock(encoder, true);
11301099013bSjsg radeon_legacy_tv_dac_dpms(encoder, DRM_MODE_DPMS_OFF);
11311099013bSjsg }
11321099013bSjsg
radeon_legacy_tv_dac_commit(struct drm_encoder * encoder)11331099013bSjsg static void radeon_legacy_tv_dac_commit(struct drm_encoder *encoder)
11341099013bSjsg {
11351099013bSjsg struct radeon_device *rdev = encoder->dev->dev_private;
11361099013bSjsg
11371099013bSjsg radeon_legacy_tv_dac_dpms(encoder, DRM_MODE_DPMS_ON);
11381099013bSjsg
11391099013bSjsg if (rdev->is_atom_bios)
11401099013bSjsg radeon_atom_output_lock(encoder, true);
11411099013bSjsg else
11421099013bSjsg radeon_combios_output_lock(encoder, true);
11431099013bSjsg }
11441099013bSjsg
radeon_legacy_tv_dac_mode_set(struct drm_encoder * encoder,struct drm_display_mode * mode,struct drm_display_mode * adjusted_mode)11451099013bSjsg static void radeon_legacy_tv_dac_mode_set(struct drm_encoder *encoder,
11461099013bSjsg struct drm_display_mode *mode,
11471099013bSjsg struct drm_display_mode *adjusted_mode)
11481099013bSjsg {
11491099013bSjsg struct drm_device *dev = encoder->dev;
11501099013bSjsg struct radeon_device *rdev = dev->dev_private;
11511099013bSjsg struct radeon_crtc *radeon_crtc = to_radeon_crtc(encoder->crtc);
11521099013bSjsg struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
11531099013bSjsg struct radeon_encoder_tv_dac *tv_dac = radeon_encoder->enc_priv;
11541099013bSjsg uint32_t tv_dac_cntl, gpiopad_a = 0, dac2_cntl, disp_output_cntl = 0;
11551099013bSjsg uint32_t disp_hw_debug = 0, fp2_gen_cntl = 0, disp_tv_out_cntl = 0;
11561099013bSjsg bool is_tv = false;
11571099013bSjsg
11581099013bSjsg DRM_DEBUG_KMS("\n");
11591099013bSjsg
11601099013bSjsg is_tv = radeon_encoder->active_device & ATOM_DEVICE_TV_SUPPORT ? true : false;
11611099013bSjsg
11621099013bSjsg if (rdev->family != CHIP_R200) {
11631099013bSjsg tv_dac_cntl = RREG32(RADEON_TV_DAC_CNTL);
11641099013bSjsg if (rdev->family == CHIP_R420 ||
11651099013bSjsg rdev->family == CHIP_R423 ||
11661099013bSjsg rdev->family == CHIP_RV410) {
11671099013bSjsg tv_dac_cntl &= ~(RADEON_TV_DAC_STD_MASK |
11681099013bSjsg RADEON_TV_DAC_BGADJ_MASK |
11691099013bSjsg R420_TV_DAC_DACADJ_MASK |
11701099013bSjsg R420_TV_DAC_RDACPD |
11711099013bSjsg R420_TV_DAC_GDACPD |
11721099013bSjsg R420_TV_DAC_BDACPD |
11731099013bSjsg R420_TV_DAC_TVENABLE);
11741099013bSjsg } else {
11751099013bSjsg tv_dac_cntl &= ~(RADEON_TV_DAC_STD_MASK |
11761099013bSjsg RADEON_TV_DAC_BGADJ_MASK |
11771099013bSjsg RADEON_TV_DAC_DACADJ_MASK |
11781099013bSjsg RADEON_TV_DAC_RDACPD |
11791099013bSjsg RADEON_TV_DAC_GDACPD |
11801099013bSjsg RADEON_TV_DAC_BDACPD);
11811099013bSjsg }
11821099013bSjsg
11831099013bSjsg tv_dac_cntl |= RADEON_TV_DAC_NBLANK | RADEON_TV_DAC_NHOLD;
11841099013bSjsg
11851099013bSjsg if (is_tv) {
11861099013bSjsg if (tv_dac->tv_std == TV_STD_NTSC ||
11871099013bSjsg tv_dac->tv_std == TV_STD_NTSC_J ||
11881099013bSjsg tv_dac->tv_std == TV_STD_PAL_M ||
11891099013bSjsg tv_dac->tv_std == TV_STD_PAL_60)
11901099013bSjsg tv_dac_cntl |= tv_dac->ntsc_tvdac_adj;
11911099013bSjsg else
11921099013bSjsg tv_dac_cntl |= tv_dac->pal_tvdac_adj;
11931099013bSjsg
11941099013bSjsg if (tv_dac->tv_std == TV_STD_NTSC ||
11951099013bSjsg tv_dac->tv_std == TV_STD_NTSC_J)
11961099013bSjsg tv_dac_cntl |= RADEON_TV_DAC_STD_NTSC;
11971099013bSjsg else
11981099013bSjsg tv_dac_cntl |= RADEON_TV_DAC_STD_PAL;
11991099013bSjsg } else
12001099013bSjsg tv_dac_cntl |= (RADEON_TV_DAC_STD_PS2 |
12011099013bSjsg tv_dac->ps2_tvdac_adj);
12021099013bSjsg
12031099013bSjsg WREG32(RADEON_TV_DAC_CNTL, tv_dac_cntl);
12041099013bSjsg }
12051099013bSjsg
12061099013bSjsg if (ASIC_IS_R300(rdev)) {
12071099013bSjsg gpiopad_a = RREG32(RADEON_GPIOPAD_A) | 1;
12081099013bSjsg disp_output_cntl = RREG32(RADEON_DISP_OUTPUT_CNTL);
12091099013bSjsg } else if (rdev->family != CHIP_R200)
12101099013bSjsg disp_hw_debug = RREG32(RADEON_DISP_HW_DEBUG);
12111099013bSjsg else if (rdev->family == CHIP_R200)
12121099013bSjsg fp2_gen_cntl = RREG32(RADEON_FP2_GEN_CNTL);
12131099013bSjsg
12141099013bSjsg if (rdev->family >= CHIP_R200)
12151099013bSjsg disp_tv_out_cntl = RREG32(RADEON_DISP_TV_OUT_CNTL);
12161099013bSjsg
12171099013bSjsg if (is_tv) {
12181099013bSjsg uint32_t dac_cntl;
12191099013bSjsg
12201099013bSjsg dac_cntl = RREG32(RADEON_DAC_CNTL);
12211099013bSjsg dac_cntl &= ~RADEON_DAC_TVO_EN;
12221099013bSjsg WREG32(RADEON_DAC_CNTL, dac_cntl);
12231099013bSjsg
12241099013bSjsg if (ASIC_IS_R300(rdev))
12251099013bSjsg gpiopad_a = RREG32(RADEON_GPIOPAD_A) & ~1;
12261099013bSjsg
12271099013bSjsg dac2_cntl = RREG32(RADEON_DAC_CNTL2) & ~RADEON_DAC2_DAC2_CLK_SEL;
12281099013bSjsg if (radeon_crtc->crtc_id == 0) {
12291099013bSjsg if (ASIC_IS_R300(rdev)) {
12301099013bSjsg disp_output_cntl &= ~RADEON_DISP_TVDAC_SOURCE_MASK;
12311099013bSjsg disp_output_cntl |= (RADEON_DISP_TVDAC_SOURCE_CRTC |
12321099013bSjsg RADEON_DISP_TV_SOURCE_CRTC);
12331099013bSjsg }
12341099013bSjsg if (rdev->family >= CHIP_R200) {
12351099013bSjsg disp_tv_out_cntl &= ~RADEON_DISP_TV_PATH_SRC_CRTC2;
12361099013bSjsg } else {
12371099013bSjsg disp_hw_debug |= RADEON_CRT2_DISP1_SEL;
12381099013bSjsg }
12391099013bSjsg } else {
12401099013bSjsg if (ASIC_IS_R300(rdev)) {
12411099013bSjsg disp_output_cntl &= ~RADEON_DISP_TVDAC_SOURCE_MASK;
12421099013bSjsg disp_output_cntl |= RADEON_DISP_TV_SOURCE_CRTC;
12431099013bSjsg }
12441099013bSjsg if (rdev->family >= CHIP_R200) {
12451099013bSjsg disp_tv_out_cntl |= RADEON_DISP_TV_PATH_SRC_CRTC2;
12461099013bSjsg } else {
12471099013bSjsg disp_hw_debug &= ~RADEON_CRT2_DISP1_SEL;
12481099013bSjsg }
12491099013bSjsg }
12501099013bSjsg WREG32(RADEON_DAC_CNTL2, dac2_cntl);
12511099013bSjsg } else {
12521099013bSjsg
12531099013bSjsg dac2_cntl = RREG32(RADEON_DAC_CNTL2) | RADEON_DAC2_DAC2_CLK_SEL;
12541099013bSjsg
12551099013bSjsg if (radeon_crtc->crtc_id == 0) {
12561099013bSjsg if (ASIC_IS_R300(rdev)) {
12571099013bSjsg disp_output_cntl &= ~RADEON_DISP_TVDAC_SOURCE_MASK;
12581099013bSjsg disp_output_cntl |= RADEON_DISP_TVDAC_SOURCE_CRTC;
12591099013bSjsg } else if (rdev->family == CHIP_R200) {
12601099013bSjsg fp2_gen_cntl &= ~(R200_FP2_SOURCE_SEL_MASK |
12611099013bSjsg RADEON_FP2_DVO_RATE_SEL_SDR);
12621099013bSjsg } else
12631099013bSjsg disp_hw_debug |= RADEON_CRT2_DISP1_SEL;
12641099013bSjsg } else {
12651099013bSjsg if (ASIC_IS_R300(rdev)) {
12661099013bSjsg disp_output_cntl &= ~RADEON_DISP_TVDAC_SOURCE_MASK;
12671099013bSjsg disp_output_cntl |= RADEON_DISP_TVDAC_SOURCE_CRTC2;
12681099013bSjsg } else if (rdev->family == CHIP_R200) {
12691099013bSjsg fp2_gen_cntl &= ~(R200_FP2_SOURCE_SEL_MASK |
12701099013bSjsg RADEON_FP2_DVO_RATE_SEL_SDR);
12711099013bSjsg fp2_gen_cntl |= R200_FP2_SOURCE_SEL_CRTC2;
12721099013bSjsg } else
12731099013bSjsg disp_hw_debug &= ~RADEON_CRT2_DISP1_SEL;
12741099013bSjsg }
12751099013bSjsg WREG32(RADEON_DAC_CNTL2, dac2_cntl);
12761099013bSjsg }
12771099013bSjsg
12781099013bSjsg if (ASIC_IS_R300(rdev)) {
12791099013bSjsg WREG32_P(RADEON_GPIOPAD_A, gpiopad_a, ~1);
12801099013bSjsg WREG32(RADEON_DISP_OUTPUT_CNTL, disp_output_cntl);
12811099013bSjsg } else if (rdev->family != CHIP_R200)
12821099013bSjsg WREG32(RADEON_DISP_HW_DEBUG, disp_hw_debug);
12831099013bSjsg else if (rdev->family == CHIP_R200)
12841099013bSjsg WREG32(RADEON_FP2_GEN_CNTL, fp2_gen_cntl);
12851099013bSjsg
12861099013bSjsg if (rdev->family >= CHIP_R200)
12871099013bSjsg WREG32(RADEON_DISP_TV_OUT_CNTL, disp_tv_out_cntl);
12881099013bSjsg
12891099013bSjsg if (is_tv)
12901099013bSjsg radeon_legacy_tv_mode_set(encoder, mode, adjusted_mode);
12911099013bSjsg
12921099013bSjsg if (rdev->is_atom_bios)
12931099013bSjsg radeon_atombios_encoder_crtc_scratch_regs(encoder, radeon_crtc->crtc_id);
12941099013bSjsg else
12951099013bSjsg radeon_combios_encoder_crtc_scratch_regs(encoder, radeon_crtc->crtc_id);
12961099013bSjsg
12971099013bSjsg }
12981099013bSjsg
r300_legacy_tv_detect(struct drm_encoder * encoder,struct drm_connector * connector)12991099013bSjsg static bool r300_legacy_tv_detect(struct drm_encoder *encoder,
13001099013bSjsg struct drm_connector *connector)
13011099013bSjsg {
13021099013bSjsg struct drm_device *dev = encoder->dev;
13031099013bSjsg struct radeon_device *rdev = dev->dev_private;
13041099013bSjsg uint32_t crtc2_gen_cntl, tv_dac_cntl, dac_cntl2, dac_ext_cntl;
13051099013bSjsg uint32_t disp_output_cntl, gpiopad_a, tmp;
13061099013bSjsg bool found = false;
13071099013bSjsg
13081099013bSjsg /* save regs needed */
13091099013bSjsg gpiopad_a = RREG32(RADEON_GPIOPAD_A);
13101099013bSjsg dac_cntl2 = RREG32(RADEON_DAC_CNTL2);
13111099013bSjsg crtc2_gen_cntl = RREG32(RADEON_CRTC2_GEN_CNTL);
13121099013bSjsg dac_ext_cntl = RREG32(RADEON_DAC_EXT_CNTL);
13131099013bSjsg tv_dac_cntl = RREG32(RADEON_TV_DAC_CNTL);
13141099013bSjsg disp_output_cntl = RREG32(RADEON_DISP_OUTPUT_CNTL);
13151099013bSjsg
13161099013bSjsg WREG32_P(RADEON_GPIOPAD_A, 0, ~1);
13171099013bSjsg
13181099013bSjsg WREG32(RADEON_DAC_CNTL2, RADEON_DAC2_DAC2_CLK_SEL);
13191099013bSjsg
13201099013bSjsg WREG32(RADEON_CRTC2_GEN_CNTL,
13211099013bSjsg RADEON_CRTC2_CRT2_ON | RADEON_CRTC2_VSYNC_TRISTAT);
13221099013bSjsg
13231099013bSjsg tmp = disp_output_cntl & ~RADEON_DISP_TVDAC_SOURCE_MASK;
13241099013bSjsg tmp |= RADEON_DISP_TVDAC_SOURCE_CRTC2;
13251099013bSjsg WREG32(RADEON_DISP_OUTPUT_CNTL, tmp);
13261099013bSjsg
13271099013bSjsg WREG32(RADEON_DAC_EXT_CNTL,
13281099013bSjsg RADEON_DAC2_FORCE_BLANK_OFF_EN |
13291099013bSjsg RADEON_DAC2_FORCE_DATA_EN |
13301099013bSjsg RADEON_DAC_FORCE_DATA_SEL_RGB |
13311099013bSjsg (0xec << RADEON_DAC_FORCE_DATA_SHIFT));
13321099013bSjsg
13331099013bSjsg WREG32(RADEON_TV_DAC_CNTL,
13341099013bSjsg RADEON_TV_DAC_STD_NTSC |
13351099013bSjsg (8 << RADEON_TV_DAC_BGADJ_SHIFT) |
13361099013bSjsg (6 << RADEON_TV_DAC_DACADJ_SHIFT));
13371099013bSjsg
13381099013bSjsg RREG32(RADEON_TV_DAC_CNTL);
13391099013bSjsg mdelay(4);
13401099013bSjsg
13411099013bSjsg WREG32(RADEON_TV_DAC_CNTL,
13421099013bSjsg RADEON_TV_DAC_NBLANK |
13431099013bSjsg RADEON_TV_DAC_NHOLD |
13441099013bSjsg RADEON_TV_MONITOR_DETECT_EN |
13451099013bSjsg RADEON_TV_DAC_STD_NTSC |
13461099013bSjsg (8 << RADEON_TV_DAC_BGADJ_SHIFT) |
13471099013bSjsg (6 << RADEON_TV_DAC_DACADJ_SHIFT));
13481099013bSjsg
13491099013bSjsg RREG32(RADEON_TV_DAC_CNTL);
13501099013bSjsg mdelay(6);
13511099013bSjsg
13521099013bSjsg tmp = RREG32(RADEON_TV_DAC_CNTL);
13531099013bSjsg if ((tmp & RADEON_TV_DAC_GDACDET) != 0) {
13541099013bSjsg found = true;
13551099013bSjsg DRM_DEBUG_KMS("S-video TV connection detected\n");
13561099013bSjsg } else if ((tmp & RADEON_TV_DAC_BDACDET) != 0) {
13571099013bSjsg found = true;
13581099013bSjsg DRM_DEBUG_KMS("Composite TV connection detected\n");
13591099013bSjsg }
13601099013bSjsg
13611099013bSjsg WREG32(RADEON_TV_DAC_CNTL, tv_dac_cntl);
13621099013bSjsg WREG32(RADEON_DAC_EXT_CNTL, dac_ext_cntl);
13631099013bSjsg WREG32(RADEON_CRTC2_GEN_CNTL, crtc2_gen_cntl);
13641099013bSjsg WREG32(RADEON_DISP_OUTPUT_CNTL, disp_output_cntl);
13651099013bSjsg WREG32(RADEON_DAC_CNTL2, dac_cntl2);
13661099013bSjsg WREG32_P(RADEON_GPIOPAD_A, gpiopad_a, ~1);
13671099013bSjsg return found;
13681099013bSjsg }
13691099013bSjsg
radeon_legacy_tv_detect(struct drm_encoder * encoder,struct drm_connector * connector)13701099013bSjsg static bool radeon_legacy_tv_detect(struct drm_encoder *encoder,
13711099013bSjsg struct drm_connector *connector)
13721099013bSjsg {
13731099013bSjsg struct drm_device *dev = encoder->dev;
13741099013bSjsg struct radeon_device *rdev = dev->dev_private;
13751099013bSjsg uint32_t tv_dac_cntl, dac_cntl2;
13761099013bSjsg uint32_t config_cntl, tv_pre_dac_mux_cntl, tv_master_cntl, tmp;
13771099013bSjsg bool found = false;
13781099013bSjsg
13791099013bSjsg if (ASIC_IS_R300(rdev))
13801099013bSjsg return r300_legacy_tv_detect(encoder, connector);
13811099013bSjsg
13821099013bSjsg dac_cntl2 = RREG32(RADEON_DAC_CNTL2);
13831099013bSjsg tv_master_cntl = RREG32(RADEON_TV_MASTER_CNTL);
13841099013bSjsg tv_dac_cntl = RREG32(RADEON_TV_DAC_CNTL);
13851099013bSjsg config_cntl = RREG32(RADEON_CONFIG_CNTL);
13861099013bSjsg tv_pre_dac_mux_cntl = RREG32(RADEON_TV_PRE_DAC_MUX_CNTL);
13871099013bSjsg
13881099013bSjsg tmp = dac_cntl2 & ~RADEON_DAC2_DAC2_CLK_SEL;
13891099013bSjsg WREG32(RADEON_DAC_CNTL2, tmp);
13901099013bSjsg
13911099013bSjsg tmp = tv_master_cntl | RADEON_TV_ON;
13921099013bSjsg tmp &= ~(RADEON_TV_ASYNC_RST |
13931099013bSjsg RADEON_RESTART_PHASE_FIX |
13941099013bSjsg RADEON_CRT_FIFO_CE_EN |
13951099013bSjsg RADEON_TV_FIFO_CE_EN |
13961099013bSjsg RADEON_RE_SYNC_NOW_SEL_MASK);
13971099013bSjsg tmp |= RADEON_TV_FIFO_ASYNC_RST | RADEON_CRT_ASYNC_RST;
13981099013bSjsg WREG32(RADEON_TV_MASTER_CNTL, tmp);
13991099013bSjsg
14001099013bSjsg tmp = RADEON_TV_DAC_NBLANK | RADEON_TV_DAC_NHOLD |
14011099013bSjsg RADEON_TV_MONITOR_DETECT_EN | RADEON_TV_DAC_STD_NTSC |
14021099013bSjsg (8 << RADEON_TV_DAC_BGADJ_SHIFT);
14031099013bSjsg
14041099013bSjsg if (config_cntl & RADEON_CFG_ATI_REV_ID_MASK)
14051099013bSjsg tmp |= (4 << RADEON_TV_DAC_DACADJ_SHIFT);
14061099013bSjsg else
14071099013bSjsg tmp |= (8 << RADEON_TV_DAC_DACADJ_SHIFT);
14081099013bSjsg WREG32(RADEON_TV_DAC_CNTL, tmp);
14091099013bSjsg
14101099013bSjsg tmp = RADEON_C_GRN_EN | RADEON_CMP_BLU_EN |
14111099013bSjsg RADEON_RED_MX_FORCE_DAC_DATA |
14121099013bSjsg RADEON_GRN_MX_FORCE_DAC_DATA |
14131099013bSjsg RADEON_BLU_MX_FORCE_DAC_DATA |
14141099013bSjsg (0x109 << RADEON_TV_FORCE_DAC_DATA_SHIFT);
14151099013bSjsg WREG32(RADEON_TV_PRE_DAC_MUX_CNTL, tmp);
14161099013bSjsg
14171099013bSjsg mdelay(3);
14181099013bSjsg tmp = RREG32(RADEON_TV_DAC_CNTL);
14191099013bSjsg if (tmp & RADEON_TV_DAC_GDACDET) {
14201099013bSjsg found = true;
14211099013bSjsg DRM_DEBUG_KMS("S-video TV connection detected\n");
14221099013bSjsg } else if ((tmp & RADEON_TV_DAC_BDACDET) != 0) {
14231099013bSjsg found = true;
14241099013bSjsg DRM_DEBUG_KMS("Composite TV connection detected\n");
14251099013bSjsg }
14261099013bSjsg
14271099013bSjsg WREG32(RADEON_TV_PRE_DAC_MUX_CNTL, tv_pre_dac_mux_cntl);
14281099013bSjsg WREG32(RADEON_TV_DAC_CNTL, tv_dac_cntl);
14291099013bSjsg WREG32(RADEON_TV_MASTER_CNTL, tv_master_cntl);
14301099013bSjsg WREG32(RADEON_DAC_CNTL2, dac_cntl2);
14311099013bSjsg return found;
14321099013bSjsg }
14331099013bSjsg
radeon_legacy_ext_dac_detect(struct drm_encoder * encoder,struct drm_connector * connector)14341099013bSjsg static bool radeon_legacy_ext_dac_detect(struct drm_encoder *encoder,
14351099013bSjsg struct drm_connector *connector)
14361099013bSjsg {
14371099013bSjsg struct drm_device *dev = encoder->dev;
14381099013bSjsg struct radeon_device *rdev = dev->dev_private;
14391099013bSjsg uint32_t gpio_monid, fp2_gen_cntl, disp_output_cntl, crtc2_gen_cntl;
14401099013bSjsg uint32_t disp_lin_trans_grph_a, disp_lin_trans_grph_b, disp_lin_trans_grph_c;
14411099013bSjsg uint32_t disp_lin_trans_grph_d, disp_lin_trans_grph_e, disp_lin_trans_grph_f;
14421099013bSjsg uint32_t tmp, crtc2_h_total_disp, crtc2_v_total_disp;
14431099013bSjsg uint32_t crtc2_h_sync_strt_wid, crtc2_v_sync_strt_wid;
14441099013bSjsg bool found = false;
14451099013bSjsg int i;
14461099013bSjsg
14471099013bSjsg /* save the regs we need */
14481099013bSjsg gpio_monid = RREG32(RADEON_GPIO_MONID);
14491099013bSjsg fp2_gen_cntl = RREG32(RADEON_FP2_GEN_CNTL);
14501099013bSjsg disp_output_cntl = RREG32(RADEON_DISP_OUTPUT_CNTL);
14511099013bSjsg crtc2_gen_cntl = RREG32(RADEON_CRTC2_GEN_CNTL);
14521099013bSjsg disp_lin_trans_grph_a = RREG32(RADEON_DISP_LIN_TRANS_GRPH_A);
14531099013bSjsg disp_lin_trans_grph_b = RREG32(RADEON_DISP_LIN_TRANS_GRPH_B);
14541099013bSjsg disp_lin_trans_grph_c = RREG32(RADEON_DISP_LIN_TRANS_GRPH_C);
14551099013bSjsg disp_lin_trans_grph_d = RREG32(RADEON_DISP_LIN_TRANS_GRPH_D);
14561099013bSjsg disp_lin_trans_grph_e = RREG32(RADEON_DISP_LIN_TRANS_GRPH_E);
14571099013bSjsg disp_lin_trans_grph_f = RREG32(RADEON_DISP_LIN_TRANS_GRPH_F);
14581099013bSjsg crtc2_h_total_disp = RREG32(RADEON_CRTC2_H_TOTAL_DISP);
14591099013bSjsg crtc2_v_total_disp = RREG32(RADEON_CRTC2_V_TOTAL_DISP);
14601099013bSjsg crtc2_h_sync_strt_wid = RREG32(RADEON_CRTC2_H_SYNC_STRT_WID);
14611099013bSjsg crtc2_v_sync_strt_wid = RREG32(RADEON_CRTC2_V_SYNC_STRT_WID);
14621099013bSjsg
14631099013bSjsg tmp = RREG32(RADEON_GPIO_MONID);
14641099013bSjsg tmp &= ~RADEON_GPIO_A_0;
14651099013bSjsg WREG32(RADEON_GPIO_MONID, tmp);
14661099013bSjsg
14671099013bSjsg WREG32(RADEON_FP2_GEN_CNTL, (RADEON_FP2_ON |
14681099013bSjsg RADEON_FP2_PANEL_FORMAT |
14691099013bSjsg R200_FP2_SOURCE_SEL_TRANS_UNIT |
14701099013bSjsg RADEON_FP2_DVO_EN |
14711099013bSjsg R200_FP2_DVO_RATE_SEL_SDR));
14721099013bSjsg
14731099013bSjsg WREG32(RADEON_DISP_OUTPUT_CNTL, (RADEON_DISP_DAC_SOURCE_RMX |
14741099013bSjsg RADEON_DISP_TRANS_MATRIX_GRAPHICS));
14751099013bSjsg
14761099013bSjsg WREG32(RADEON_CRTC2_GEN_CNTL, (RADEON_CRTC2_EN |
14771099013bSjsg RADEON_CRTC2_DISP_REQ_EN_B));
14781099013bSjsg
14791099013bSjsg WREG32(RADEON_DISP_LIN_TRANS_GRPH_A, 0x00000000);
14801099013bSjsg WREG32(RADEON_DISP_LIN_TRANS_GRPH_B, 0x000003f0);
14811099013bSjsg WREG32(RADEON_DISP_LIN_TRANS_GRPH_C, 0x00000000);
14821099013bSjsg WREG32(RADEON_DISP_LIN_TRANS_GRPH_D, 0x000003f0);
14831099013bSjsg WREG32(RADEON_DISP_LIN_TRANS_GRPH_E, 0x00000000);
14841099013bSjsg WREG32(RADEON_DISP_LIN_TRANS_GRPH_F, 0x000003f0);
14851099013bSjsg
14861099013bSjsg WREG32(RADEON_CRTC2_H_TOTAL_DISP, 0x01000008);
14871099013bSjsg WREG32(RADEON_CRTC2_H_SYNC_STRT_WID, 0x00000800);
14881099013bSjsg WREG32(RADEON_CRTC2_V_TOTAL_DISP, 0x00080001);
14891099013bSjsg WREG32(RADEON_CRTC2_V_SYNC_STRT_WID, 0x00000080);
14901099013bSjsg
14911099013bSjsg for (i = 0; i < 200; i++) {
14921099013bSjsg tmp = RREG32(RADEON_GPIO_MONID);
14931099013bSjsg if (tmp & RADEON_GPIO_Y_0)
14941099013bSjsg found = true;
14951099013bSjsg
14961099013bSjsg if (found)
14971099013bSjsg break;
14981099013bSjsg
14991099013bSjsg if (!drm_can_sleep())
15001099013bSjsg mdelay(1);
15011099013bSjsg else
1502e1001332Skettenis drm_msleep(1);
15031099013bSjsg }
15041099013bSjsg
15051099013bSjsg /* restore the regs we used */
15061099013bSjsg WREG32(RADEON_DISP_LIN_TRANS_GRPH_A, disp_lin_trans_grph_a);
15071099013bSjsg WREG32(RADEON_DISP_LIN_TRANS_GRPH_B, disp_lin_trans_grph_b);
15081099013bSjsg WREG32(RADEON_DISP_LIN_TRANS_GRPH_C, disp_lin_trans_grph_c);
15091099013bSjsg WREG32(RADEON_DISP_LIN_TRANS_GRPH_D, disp_lin_trans_grph_d);
15101099013bSjsg WREG32(RADEON_DISP_LIN_TRANS_GRPH_E, disp_lin_trans_grph_e);
15111099013bSjsg WREG32(RADEON_DISP_LIN_TRANS_GRPH_F, disp_lin_trans_grph_f);
15121099013bSjsg WREG32(RADEON_CRTC2_H_TOTAL_DISP, crtc2_h_total_disp);
15131099013bSjsg WREG32(RADEON_CRTC2_V_TOTAL_DISP, crtc2_v_total_disp);
15141099013bSjsg WREG32(RADEON_CRTC2_H_SYNC_STRT_WID, crtc2_h_sync_strt_wid);
15151099013bSjsg WREG32(RADEON_CRTC2_V_SYNC_STRT_WID, crtc2_v_sync_strt_wid);
15161099013bSjsg WREG32(RADEON_CRTC2_GEN_CNTL, crtc2_gen_cntl);
15171099013bSjsg WREG32(RADEON_DISP_OUTPUT_CNTL, disp_output_cntl);
15181099013bSjsg WREG32(RADEON_FP2_GEN_CNTL, fp2_gen_cntl);
15191099013bSjsg WREG32(RADEON_GPIO_MONID, gpio_monid);
15201099013bSjsg
15211099013bSjsg return found;
15221099013bSjsg }
15231099013bSjsg
radeon_legacy_tv_dac_detect(struct drm_encoder * encoder,struct drm_connector * connector)15241099013bSjsg static enum drm_connector_status radeon_legacy_tv_dac_detect(struct drm_encoder *encoder,
15251099013bSjsg struct drm_connector *connector)
15261099013bSjsg {
15271099013bSjsg struct drm_device *dev = encoder->dev;
15281099013bSjsg struct radeon_device *rdev = dev->dev_private;
15291099013bSjsg uint32_t crtc2_gen_cntl = 0, tv_dac_cntl, dac_cntl2, dac_ext_cntl;
15301099013bSjsg uint32_t gpiopad_a = 0, pixclks_cntl, tmp;
15311099013bSjsg uint32_t disp_output_cntl = 0, disp_hw_debug = 0, crtc_ext_cntl = 0;
15321099013bSjsg enum drm_connector_status found = connector_status_disconnected;
15331099013bSjsg struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder);
15341099013bSjsg struct radeon_encoder_tv_dac *tv_dac = radeon_encoder->enc_priv;
15351099013bSjsg bool color = true;
15361099013bSjsg struct drm_crtc *crtc;
15371099013bSjsg
15381099013bSjsg /* find out if crtc2 is in use or if this encoder is using it */
15391099013bSjsg list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
15401099013bSjsg struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc);
15411099013bSjsg if ((radeon_crtc->crtc_id == 1) && crtc->enabled) {
15421099013bSjsg if (encoder->crtc != crtc) {
15431099013bSjsg return connector_status_disconnected;
15441099013bSjsg }
15451099013bSjsg }
15461099013bSjsg }
15471099013bSjsg
15481099013bSjsg if (connector->connector_type == DRM_MODE_CONNECTOR_SVIDEO ||
15491099013bSjsg connector->connector_type == DRM_MODE_CONNECTOR_Composite ||
15501099013bSjsg connector->connector_type == DRM_MODE_CONNECTOR_9PinDIN) {
15511099013bSjsg bool tv_detect;
15521099013bSjsg
15531099013bSjsg if (radeon_encoder->active_device && !(radeon_encoder->active_device & ATOM_DEVICE_TV_SUPPORT))
15541099013bSjsg return connector_status_disconnected;
15551099013bSjsg
15561099013bSjsg tv_detect = radeon_legacy_tv_detect(encoder, connector);
15571099013bSjsg if (tv_detect && tv_dac)
15581099013bSjsg found = connector_status_connected;
15591099013bSjsg return found;
15601099013bSjsg }
15611099013bSjsg
15621099013bSjsg /* don't probe if the encoder is being used for something else not CRT related */
15631099013bSjsg if (radeon_encoder->active_device && !(radeon_encoder->active_device & ATOM_DEVICE_CRT_SUPPORT)) {
15641099013bSjsg DRM_INFO("not detecting due to %08x\n", radeon_encoder->active_device);
15651099013bSjsg return connector_status_disconnected;
15661099013bSjsg }
15671099013bSjsg
15681099013bSjsg /* R200 uses an external DAC for secondary DAC */
15691099013bSjsg if (rdev->family == CHIP_R200) {
15701099013bSjsg if (radeon_legacy_ext_dac_detect(encoder, connector))
15711099013bSjsg found = connector_status_connected;
15721099013bSjsg return found;
15731099013bSjsg }
15741099013bSjsg
15751099013bSjsg /* save the regs we need */
15761099013bSjsg pixclks_cntl = RREG32_PLL(RADEON_PIXCLKS_CNTL);
15771099013bSjsg
15781099013bSjsg if (rdev->flags & RADEON_SINGLE_CRTC) {
15791099013bSjsg crtc_ext_cntl = RREG32(RADEON_CRTC_EXT_CNTL);
15801099013bSjsg } else {
15811099013bSjsg if (ASIC_IS_R300(rdev)) {
15821099013bSjsg gpiopad_a = RREG32(RADEON_GPIOPAD_A);
15831099013bSjsg disp_output_cntl = RREG32(RADEON_DISP_OUTPUT_CNTL);
15841099013bSjsg } else {
15851099013bSjsg disp_hw_debug = RREG32(RADEON_DISP_HW_DEBUG);
15861099013bSjsg }
15871099013bSjsg crtc2_gen_cntl = RREG32(RADEON_CRTC2_GEN_CNTL);
15881099013bSjsg }
15891099013bSjsg tv_dac_cntl = RREG32(RADEON_TV_DAC_CNTL);
15901099013bSjsg dac_ext_cntl = RREG32(RADEON_DAC_EXT_CNTL);
15911099013bSjsg dac_cntl2 = RREG32(RADEON_DAC_CNTL2);
15921099013bSjsg
15931099013bSjsg tmp = pixclks_cntl & ~(RADEON_PIX2CLK_ALWAYS_ONb
15941099013bSjsg | RADEON_PIX2CLK_DAC_ALWAYS_ONb);
15951099013bSjsg WREG32_PLL(RADEON_PIXCLKS_CNTL, tmp);
15961099013bSjsg
15971099013bSjsg if (rdev->flags & RADEON_SINGLE_CRTC) {
15981099013bSjsg tmp = crtc_ext_cntl | RADEON_CRTC_CRT_ON;
15991099013bSjsg WREG32(RADEON_CRTC_EXT_CNTL, tmp);
16001099013bSjsg } else {
16011099013bSjsg tmp = crtc2_gen_cntl & ~RADEON_CRTC2_PIX_WIDTH_MASK;
16021099013bSjsg tmp |= RADEON_CRTC2_CRT2_ON |
16031099013bSjsg (2 << RADEON_CRTC2_PIX_WIDTH_SHIFT);
16041099013bSjsg WREG32(RADEON_CRTC2_GEN_CNTL, tmp);
16051099013bSjsg
16061099013bSjsg if (ASIC_IS_R300(rdev)) {
16071099013bSjsg WREG32_P(RADEON_GPIOPAD_A, 1, ~1);
16081099013bSjsg tmp = disp_output_cntl & ~RADEON_DISP_TVDAC_SOURCE_MASK;
16091099013bSjsg tmp |= RADEON_DISP_TVDAC_SOURCE_CRTC2;
16101099013bSjsg WREG32(RADEON_DISP_OUTPUT_CNTL, tmp);
16111099013bSjsg } else {
16121099013bSjsg tmp = disp_hw_debug & ~RADEON_CRT2_DISP1_SEL;
16131099013bSjsg WREG32(RADEON_DISP_HW_DEBUG, tmp);
16141099013bSjsg }
16151099013bSjsg }
16161099013bSjsg
16171099013bSjsg tmp = RADEON_TV_DAC_NBLANK |
16181099013bSjsg RADEON_TV_DAC_NHOLD |
16191099013bSjsg RADEON_TV_MONITOR_DETECT_EN |
16201099013bSjsg RADEON_TV_DAC_STD_PS2;
16211099013bSjsg
16221099013bSjsg WREG32(RADEON_TV_DAC_CNTL, tmp);
16231099013bSjsg
16241099013bSjsg tmp = RADEON_DAC2_FORCE_BLANK_OFF_EN |
16251099013bSjsg RADEON_DAC2_FORCE_DATA_EN;
16261099013bSjsg
16271099013bSjsg if (color)
16281099013bSjsg tmp |= RADEON_DAC_FORCE_DATA_SEL_RGB;
16291099013bSjsg else
16301099013bSjsg tmp |= RADEON_DAC_FORCE_DATA_SEL_G;
16311099013bSjsg
16321099013bSjsg if (ASIC_IS_R300(rdev))
16331099013bSjsg tmp |= (0x1b6 << RADEON_DAC_FORCE_DATA_SHIFT);
16341099013bSjsg else
16351099013bSjsg tmp |= (0x180 << RADEON_DAC_FORCE_DATA_SHIFT);
16361099013bSjsg
16371099013bSjsg WREG32(RADEON_DAC_EXT_CNTL, tmp);
16381099013bSjsg
16391099013bSjsg tmp = dac_cntl2 | RADEON_DAC2_DAC2_CLK_SEL | RADEON_DAC2_CMP_EN;
16401099013bSjsg WREG32(RADEON_DAC_CNTL2, tmp);
16411099013bSjsg
16421099013bSjsg mdelay(10);
16431099013bSjsg
16441099013bSjsg if (ASIC_IS_R300(rdev)) {
16451099013bSjsg if (RREG32(RADEON_DAC_CNTL2) & RADEON_DAC2_CMP_OUT_B)
16461099013bSjsg found = connector_status_connected;
16471099013bSjsg } else {
16481099013bSjsg if (RREG32(RADEON_DAC_CNTL2) & RADEON_DAC2_CMP_OUTPUT)
16491099013bSjsg found = connector_status_connected;
16501099013bSjsg }
16511099013bSjsg
16521099013bSjsg /* restore regs we used */
16531099013bSjsg WREG32(RADEON_DAC_CNTL2, dac_cntl2);
16541099013bSjsg WREG32(RADEON_DAC_EXT_CNTL, dac_ext_cntl);
16551099013bSjsg WREG32(RADEON_TV_DAC_CNTL, tv_dac_cntl);
16561099013bSjsg
16571099013bSjsg if (rdev->flags & RADEON_SINGLE_CRTC) {
16581099013bSjsg WREG32(RADEON_CRTC_EXT_CNTL, crtc_ext_cntl);
16591099013bSjsg } else {
16601099013bSjsg WREG32(RADEON_CRTC2_GEN_CNTL, crtc2_gen_cntl);
16611099013bSjsg if (ASIC_IS_R300(rdev)) {
16621099013bSjsg WREG32(RADEON_DISP_OUTPUT_CNTL, disp_output_cntl);
16631099013bSjsg WREG32_P(RADEON_GPIOPAD_A, gpiopad_a, ~1);
16641099013bSjsg } else {
16651099013bSjsg WREG32(RADEON_DISP_HW_DEBUG, disp_hw_debug);
16661099013bSjsg }
16671099013bSjsg }
16681099013bSjsg
16691099013bSjsg WREG32_PLL(RADEON_PIXCLKS_CNTL, pixclks_cntl);
16701099013bSjsg
16711099013bSjsg return found;
16721099013bSjsg
16731099013bSjsg }
16741099013bSjsg
16751099013bSjsg static const struct drm_encoder_helper_funcs radeon_legacy_tv_dac_helper_funcs = {
16761099013bSjsg .dpms = radeon_legacy_tv_dac_dpms,
16771099013bSjsg .mode_fixup = radeon_legacy_mode_fixup,
16781099013bSjsg .prepare = radeon_legacy_tv_dac_prepare,
16791099013bSjsg .mode_set = radeon_legacy_tv_dac_mode_set,
16801099013bSjsg .commit = radeon_legacy_tv_dac_commit,
16811099013bSjsg .detect = radeon_legacy_tv_dac_detect,
16821099013bSjsg .disable = radeon_legacy_encoder_disable,
16831099013bSjsg };
16841099013bSjsg
16851099013bSjsg
16861099013bSjsg static const struct drm_encoder_funcs radeon_legacy_tv_dac_enc_funcs = {
16871099013bSjsg .destroy = radeon_enc_destroy,
16881099013bSjsg };
16891099013bSjsg
16901099013bSjsg
radeon_legacy_get_tmds_info(struct radeon_encoder * encoder)16911099013bSjsg static struct radeon_encoder_int_tmds *radeon_legacy_get_tmds_info(struct radeon_encoder *encoder)
16921099013bSjsg {
16931099013bSjsg struct drm_device *dev = encoder->base.dev;
16941099013bSjsg struct radeon_device *rdev = dev->dev_private;
1695*f005ef32Sjsg struct radeon_encoder_int_tmds *tmds;
16961099013bSjsg bool ret;
16971099013bSjsg
1698de5631a0Sjsg tmds = kzalloc(sizeof(struct radeon_encoder_int_tmds), GFP_KERNEL);
16991099013bSjsg
17001099013bSjsg if (!tmds)
17011099013bSjsg return NULL;
17021099013bSjsg
17031099013bSjsg if (rdev->is_atom_bios)
17041099013bSjsg ret = radeon_atombios_get_tmds_info(encoder, tmds);
17051099013bSjsg else
17061099013bSjsg ret = radeon_legacy_get_tmds_info_from_combios(encoder, tmds);
17071099013bSjsg
1708c349dbc7Sjsg if (!ret)
17091099013bSjsg radeon_legacy_get_tmds_info_from_table(encoder, tmds);
17101099013bSjsg
17111099013bSjsg return tmds;
17121099013bSjsg }
17131099013bSjsg
radeon_legacy_get_ext_tmds_info(struct radeon_encoder * encoder)17141099013bSjsg static struct radeon_encoder_ext_tmds *radeon_legacy_get_ext_tmds_info(struct radeon_encoder *encoder)
17151099013bSjsg {
17161099013bSjsg struct drm_device *dev = encoder->base.dev;
17171099013bSjsg struct radeon_device *rdev = dev->dev_private;
1718*f005ef32Sjsg struct radeon_encoder_ext_tmds *tmds;
17191099013bSjsg bool ret;
17201099013bSjsg
17211099013bSjsg if (rdev->is_atom_bios)
17221099013bSjsg return NULL;
17231099013bSjsg
1724de5631a0Sjsg tmds = kzalloc(sizeof(struct radeon_encoder_ext_tmds), GFP_KERNEL);
17251099013bSjsg
17261099013bSjsg if (!tmds)
17271099013bSjsg return NULL;
17281099013bSjsg
17291099013bSjsg ret = radeon_legacy_get_ext_tmds_info_from_combios(encoder, tmds);
17301099013bSjsg
1731c349dbc7Sjsg if (!ret)
17321099013bSjsg radeon_legacy_get_ext_tmds_info_from_table(encoder, tmds);
17331099013bSjsg
17341099013bSjsg return tmds;
17351099013bSjsg }
17361099013bSjsg
17371099013bSjsg void
radeon_add_legacy_encoder(struct drm_device * dev,uint32_t encoder_enum,uint32_t supported_device)17381099013bSjsg radeon_add_legacy_encoder(struct drm_device *dev, uint32_t encoder_enum, uint32_t supported_device)
17391099013bSjsg {
17401099013bSjsg struct radeon_device *rdev = dev->dev_private;
17411099013bSjsg struct drm_encoder *encoder;
17421099013bSjsg struct radeon_encoder *radeon_encoder;
17431099013bSjsg
17441099013bSjsg /* see if we already added it */
17451099013bSjsg list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
17461099013bSjsg radeon_encoder = to_radeon_encoder(encoder);
17471099013bSjsg if (radeon_encoder->encoder_enum == encoder_enum) {
17481099013bSjsg radeon_encoder->devices |= supported_device;
17491099013bSjsg return;
17501099013bSjsg }
17511099013bSjsg
17521099013bSjsg }
17531099013bSjsg
17541099013bSjsg /* add a new one */
1755de5631a0Sjsg radeon_encoder = kzalloc(sizeof(struct radeon_encoder), GFP_KERNEL);
17561099013bSjsg if (!radeon_encoder)
17571099013bSjsg return;
17581099013bSjsg
17591099013bSjsg encoder = &radeon_encoder->base;
17601099013bSjsg if (rdev->flags & RADEON_SINGLE_CRTC)
17611099013bSjsg encoder->possible_crtcs = 0x1;
17621099013bSjsg else
17631099013bSjsg encoder->possible_crtcs = 0x3;
17641099013bSjsg
17651099013bSjsg radeon_encoder->enc_priv = NULL;
17661099013bSjsg
17671099013bSjsg radeon_encoder->encoder_enum = encoder_enum;
17681099013bSjsg radeon_encoder->encoder_id = (encoder_enum & OBJECT_ID_MASK) >> OBJECT_ID_SHIFT;
17691099013bSjsg radeon_encoder->devices = supported_device;
17701099013bSjsg radeon_encoder->rmx_type = RMX_OFF;
17711099013bSjsg
17721099013bSjsg switch (radeon_encoder->encoder_id) {
17731099013bSjsg case ENCODER_OBJECT_ID_INTERNAL_LVDS:
17741099013bSjsg encoder->possible_crtcs = 0x1;
17757f4dd379Sjsg drm_encoder_init(dev, encoder, &radeon_legacy_lvds_enc_funcs,
17767f4dd379Sjsg DRM_MODE_ENCODER_LVDS, NULL);
17771099013bSjsg drm_encoder_helper_add(encoder, &radeon_legacy_lvds_helper_funcs);
17781099013bSjsg if (rdev->is_atom_bios)
17791099013bSjsg radeon_encoder->enc_priv = radeon_atombios_get_lvds_info(radeon_encoder);
17801099013bSjsg else
17811099013bSjsg radeon_encoder->enc_priv = radeon_combios_get_lvds_info(radeon_encoder);
17821099013bSjsg radeon_encoder->rmx_type = RMX_FULL;
17831099013bSjsg break;
17841099013bSjsg case ENCODER_OBJECT_ID_INTERNAL_TMDS1:
17857f4dd379Sjsg drm_encoder_init(dev, encoder, &radeon_legacy_tmds_int_enc_funcs,
17867f4dd379Sjsg DRM_MODE_ENCODER_TMDS, NULL);
17871099013bSjsg drm_encoder_helper_add(encoder, &radeon_legacy_tmds_int_helper_funcs);
17881099013bSjsg radeon_encoder->enc_priv = radeon_legacy_get_tmds_info(radeon_encoder);
17891099013bSjsg break;
17901099013bSjsg case ENCODER_OBJECT_ID_INTERNAL_DAC1:
17917f4dd379Sjsg drm_encoder_init(dev, encoder, &radeon_legacy_primary_dac_enc_funcs,
17927f4dd379Sjsg DRM_MODE_ENCODER_DAC, NULL);
17931099013bSjsg drm_encoder_helper_add(encoder, &radeon_legacy_primary_dac_helper_funcs);
17941099013bSjsg if (rdev->is_atom_bios)
17951099013bSjsg radeon_encoder->enc_priv = radeon_atombios_get_primary_dac_info(radeon_encoder);
17961099013bSjsg else
17971099013bSjsg radeon_encoder->enc_priv = radeon_combios_get_primary_dac_info(radeon_encoder);
17981099013bSjsg break;
17991099013bSjsg case ENCODER_OBJECT_ID_INTERNAL_DAC2:
18007f4dd379Sjsg drm_encoder_init(dev, encoder, &radeon_legacy_tv_dac_enc_funcs,
18017f4dd379Sjsg DRM_MODE_ENCODER_TVDAC, NULL);
18021099013bSjsg drm_encoder_helper_add(encoder, &radeon_legacy_tv_dac_helper_funcs);
18031099013bSjsg if (rdev->is_atom_bios)
18041099013bSjsg radeon_encoder->enc_priv = radeon_atombios_get_tv_dac_info(radeon_encoder);
18051099013bSjsg else
18061099013bSjsg radeon_encoder->enc_priv = radeon_combios_get_tv_dac_info(radeon_encoder);
18071099013bSjsg break;
18081099013bSjsg case ENCODER_OBJECT_ID_INTERNAL_DVO1:
18097f4dd379Sjsg drm_encoder_init(dev, encoder, &radeon_legacy_tmds_ext_enc_funcs,
18107f4dd379Sjsg DRM_MODE_ENCODER_TMDS, NULL);
18111099013bSjsg drm_encoder_helper_add(encoder, &radeon_legacy_tmds_ext_helper_funcs);
18121099013bSjsg if (!rdev->is_atom_bios)
18131099013bSjsg radeon_encoder->enc_priv = radeon_legacy_get_ext_tmds_info(radeon_encoder);
18141099013bSjsg break;
18151099013bSjsg }
18161099013bSjsg }
1817