Orange Pi5 kernel

Deprecated Linux kernel 5.10.110 for OrangePi 5/5B/5+ boards

3 Commits   0 Branches   0 Tags
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   1) // SPDX-License-Identifier: GPL-2.0-or-later
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   3)  * Copyright 1998-2008 VIA Technologies, Inc. All Rights Reserved.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   4)  * Copyright 2001-2008 S3 Graphics, Inc. All Rights Reserved.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   5) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   6)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   7) #include <linux/via-core.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   8) #include <linux/via_i2c.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   9) #include "global.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  10) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  11) #define viafb_compact_res(x, y) (((x)<<16)|(y))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  12) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  13) /* CLE266 Software Power Sequence */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  14) /* {Mask}, {Data}, {Delay} */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  15) static const int PowerSequenceOn[3][3] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  16) 	{0x10, 0x08, 0x06}, {0x10, 0x08, 0x06},	{0x19, 0x1FE, 0x01}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  17) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  18) static const int PowerSequenceOff[3][3] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  19) 	{0x06, 0x08, 0x10}, {0x00, 0x00, 0x00},	{0xD2, 0x19, 0x01}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  20) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  21) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  22) static struct _lcd_scaling_factor lcd_scaling_factor = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  23) 	/* LCD Horizontal Scaling Factor Register */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  24) 	{LCD_HOR_SCALING_FACTOR_REG_NUM,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  25) 	 {{CR9F, 0, 1}, {CR77, 0, 7}, {CR79, 4, 5} } },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  26) 	/* LCD Vertical Scaling Factor Register */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  27) 	{LCD_VER_SCALING_FACTOR_REG_NUM,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  28) 	 {{CR79, 3, 3}, {CR78, 0, 7}, {CR79, 6, 7} } }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  29) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  30) static struct _lcd_scaling_factor lcd_scaling_factor_CLE = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  31) 	/* LCD Horizontal Scaling Factor Register */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  32) 	{LCD_HOR_SCALING_FACTOR_REG_NUM_CLE, {{CR77, 0, 7}, {CR79, 4, 5} } },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  33) 	/* LCD Vertical Scaling Factor Register */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  34) 	{LCD_VER_SCALING_FACTOR_REG_NUM_CLE, {{CR78, 0, 7}, {CR79, 6, 7} } }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  35) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  36) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  37) static bool lvds_identify_integratedlvds(void);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  38) static void fp_id_to_vindex(int panel_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  39) static int lvds_register_read(int index);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  40) static void load_lcd_scaling(int set_hres, int set_vres, int panel_hres,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  41) 		      int panel_vres);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  42) static void lcd_patch_skew_dvp0(struct lvds_setting_information
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  43) 			 *plvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  44) 			 struct lvds_chip_information *plvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  45) static void lcd_patch_skew_dvp1(struct lvds_setting_information
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  46) 			 *plvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  47) 			 struct lvds_chip_information *plvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  48) static void lcd_patch_skew(struct lvds_setting_information
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  49) 	*plvds_setting_info, struct lvds_chip_information *plvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  50) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  51) static void integrated_lvds_disable(struct lvds_setting_information
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  52) 			     *plvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  53) 			     struct lvds_chip_information *plvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  54) static void integrated_lvds_enable(struct lvds_setting_information
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  55) 			    *plvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  56) 			    struct lvds_chip_information *plvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  57) static void lcd_powersequence_off(void);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  58) static void lcd_powersequence_on(void);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  59) static void fill_lcd_format(void);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  60) static void check_diport_of_integrated_lvds(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  61) 	struct lvds_chip_information *plvds_chip_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  62) 				     struct lvds_setting_information
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  63) 				     *plvds_setting_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  64) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  65) static inline bool check_lvds_chip(int device_id_subaddr, int device_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  66) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  67) 	return lvds_register_read(device_id_subaddr) == device_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  68) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  69) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  70) void viafb_init_lcd_size(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  71) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  72) 	DEBUG_MSG(KERN_INFO "viafb_init_lcd_size()\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  73) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  74) 	fp_id_to_vindex(viafb_lcd_panel_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  75) 	viaparinfo->lvds_setting_info2->lcd_panel_hres =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  76) 		viaparinfo->lvds_setting_info->lcd_panel_hres;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  77) 	viaparinfo->lvds_setting_info2->lcd_panel_vres =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  78) 		viaparinfo->lvds_setting_info->lcd_panel_vres;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  79) 	viaparinfo->lvds_setting_info2->device_lcd_dualedge =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  80) 	    viaparinfo->lvds_setting_info->device_lcd_dualedge;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  81) 	viaparinfo->lvds_setting_info2->LCDDithering =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  82) 		viaparinfo->lvds_setting_info->LCDDithering;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  83) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  84) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  85) static bool lvds_identify_integratedlvds(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  86) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  87) 	if (viafb_display_hardware_layout == HW_LAYOUT_LCD_EXTERNAL_LCD2) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  88) 		/* Two dual channel LCD (Internal LVDS + External LVDS): */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  89) 		/* If we have an external LVDS, such as VT1636, we should
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  90) 		   have its chip ID already. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  91) 		if (viaparinfo->chip_info->lvds_chip_info.lvds_chip_name) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  92) 			viaparinfo->chip_info->lvds_chip_info2.lvds_chip_name =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  93) 			    INTEGRATED_LVDS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  94) 			DEBUG_MSG(KERN_INFO "Support two dual channel LVDS! "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  95) 				  "(Internal LVDS + External LVDS)\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  96) 		} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  97) 			viaparinfo->chip_info->lvds_chip_info.lvds_chip_name =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  98) 			    INTEGRATED_LVDS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  99) 			DEBUG_MSG(KERN_INFO "Not found external LVDS, "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) 				  "so can't support two dual channel LVDS!\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) 	} else if (viafb_display_hardware_layout == HW_LAYOUT_LCD1_LCD2) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) 		/* Two single channel LCD (Internal LVDS + Internal LVDS): */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) 		viaparinfo->chip_info->lvds_chip_info.lvds_chip_name =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) 		INTEGRATED_LVDS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) 		viaparinfo->chip_info->lvds_chip_info2.lvds_chip_name =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) 			INTEGRATED_LVDS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) 		DEBUG_MSG(KERN_INFO "Support two single channel LVDS! "
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) 			  "(Internal LVDS + Internal LVDS)\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) 	} else if (viafb_display_hardware_layout != HW_LAYOUT_DVI_ONLY) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) 		/* If we have found external LVDS, just use it,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) 		   otherwise, we will use internal LVDS as default. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) 		if (!viaparinfo->chip_info->lvds_chip_info.lvds_chip_name) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) 			viaparinfo->chip_info->lvds_chip_info.lvds_chip_name =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) 			    INTEGRATED_LVDS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) 			DEBUG_MSG(KERN_INFO "Found Integrated LVDS!\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) 		viaparinfo->chip_info->lvds_chip_info.lvds_chip_name =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) 			NON_LVDS_TRANSMITTER;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) 		DEBUG_MSG(KERN_INFO "Do not support LVDS!\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) 		return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) 	return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) bool viafb_lvds_trasmitter_identify(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) 	if (viafb_lvds_identify_vt1636(VIA_PORT_31)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) 		viaparinfo->chip_info->lvds_chip_info.i2c_port = VIA_PORT_31;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) 		DEBUG_MSG(KERN_INFO
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) 			  "Found VIA VT1636 LVDS on port i2c 0x31\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) 		if (viafb_lvds_identify_vt1636(VIA_PORT_2C)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) 			viaparinfo->chip_info->lvds_chip_info.i2c_port =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) 				VIA_PORT_2C;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) 			DEBUG_MSG(KERN_INFO
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) 				  "Found VIA VT1636 LVDS on port gpio 0x2c\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) 	if (viaparinfo->chip_info->gfx_chip_name == UNICHROME_CX700)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) 		lvds_identify_integratedlvds();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) 	if (viaparinfo->chip_info->lvds_chip_info.lvds_chip_name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) 		return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) 	/* Check for VT1631: */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) 	viaparinfo->chip_info->lvds_chip_info.lvds_chip_name = VT1631_LVDS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) 	viaparinfo->chip_info->lvds_chip_info.lvds_chip_slave_addr =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) 		VT1631_LVDS_I2C_ADDR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) 	if (check_lvds_chip(VT1631_DEVICE_ID_REG, VT1631_DEVICE_ID)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) 		DEBUG_MSG(KERN_INFO "\n VT1631 LVDS ! \n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) 		DEBUG_MSG(KERN_INFO "\n %2d",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) 			  viaparinfo->chip_info->lvds_chip_info.lvds_chip_name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) 		DEBUG_MSG(KERN_INFO "\n %2d",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) 			  viaparinfo->chip_info->lvds_chip_info.lvds_chip_name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) 		return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) 	viaparinfo->chip_info->lvds_chip_info.lvds_chip_name =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) 		NON_LVDS_TRANSMITTER;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) 	viaparinfo->chip_info->lvds_chip_info.lvds_chip_slave_addr =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) 		VT1631_LVDS_I2C_ADDR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) 	return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) static void fp_id_to_vindex(int panel_id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) 	DEBUG_MSG(KERN_INFO "fp_get_panel_id()\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) 	if (panel_id > LCD_PANEL_ID_MAXIMUM)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) 		viafb_lcd_panel_id = panel_id =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) 		viafb_read_reg(VIACR, CR3F) & 0x0F;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) 	switch (panel_id) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) 	case 0x0:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 640;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 480;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) 		viaparinfo->lvds_setting_info->LCDDithering = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) 	case 0x1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 800;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 600;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) 		viaparinfo->lvds_setting_info->LCDDithering = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) 	case 0x2:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1024;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 768;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) 		viaparinfo->lvds_setting_info->LCDDithering = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) 	case 0x3:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1280;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 768;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) 		viaparinfo->lvds_setting_info->LCDDithering = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) 	case 0x4:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1280;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 1024;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) 		viaparinfo->lvds_setting_info->LCDDithering = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) 	case 0x5:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1400;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 1050;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) 		viaparinfo->lvds_setting_info->LCDDithering = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) 	case 0x6:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1600;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 1200;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) 		viaparinfo->lvds_setting_info->LCDDithering = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) 	case 0x8:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 800;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 480;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) 		viaparinfo->lvds_setting_info->LCDDithering = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) 	case 0x9:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1024;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 768;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) 		viaparinfo->lvds_setting_info->LCDDithering = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) 	case 0xA:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1024;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 768;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) 		viaparinfo->lvds_setting_info->LCDDithering = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) 	case 0xB:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1024;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 768;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) 		viaparinfo->lvds_setting_info->LCDDithering = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) 	case 0xC:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1280;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 768;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) 		viaparinfo->lvds_setting_info->LCDDithering = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) 	case 0xD:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1280;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 1024;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) 		viaparinfo->lvds_setting_info->LCDDithering = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) 	case 0xE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1400;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 1050;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) 		viaparinfo->lvds_setting_info->LCDDithering = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) 	case 0xF:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1600;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 1200;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) 		viaparinfo->lvds_setting_info->LCDDithering = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) 	case 0x10:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1366;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 768;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) 		viaparinfo->lvds_setting_info->LCDDithering = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) 	case 0x11:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1024;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 600;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) 		viaparinfo->lvds_setting_info->LCDDithering = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) 	case 0x12:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1280;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 768;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) 		viaparinfo->lvds_setting_info->LCDDithering = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) 	case 0x13:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1280;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 800;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) 		viaparinfo->lvds_setting_info->LCDDithering = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) 	case 0x14:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1360;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 768;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) 		viaparinfo->lvds_setting_info->LCDDithering = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) 	case 0x15:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1280;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 768;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) 		viaparinfo->lvds_setting_info->LCDDithering = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) 	case 0x16:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 480;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 640;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) 		viaparinfo->lvds_setting_info->LCDDithering = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) 	case 0x17:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) 		/* OLPC XO-1.5 panel */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 1200;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 900;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) 		viaparinfo->lvds_setting_info->LCDDithering = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) 	default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) 		viaparinfo->lvds_setting_info->lcd_panel_hres = 800;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) 		viaparinfo->lvds_setting_info->lcd_panel_vres = 600;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) 		viaparinfo->lvds_setting_info->device_lcd_dualedge = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) 		viaparinfo->lvds_setting_info->LCDDithering = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325) static int lvds_register_read(int index)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) 	u8 data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) 	viafb_i2c_readbyte(VIA_PORT_2C,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) 			(u8) viaparinfo->chip_info->lvds_chip_info.lvds_chip_slave_addr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) 			(u8) index, &data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) 	return data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) static void load_lcd_scaling(int set_hres, int set_vres, int panel_hres,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) 		      int panel_vres)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) 	int reg_value = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) 	int viafb_load_reg_num;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) 	struct io_register *reg = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) 	DEBUG_MSG(KERN_INFO "load_lcd_scaling()!!\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) 	/* LCD Scaling Enable */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) 	viafb_write_reg_mask(CR79, VIACR, 0x07, BIT0 + BIT1 + BIT2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) 	/* Check if expansion for horizontal */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) 	if (set_hres < panel_hres) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) 		/* Load Horizontal Scaling Factor */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) 		switch (viaparinfo->chip_info->gfx_chip_name) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) 		case UNICHROME_CLE266:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) 		case UNICHROME_K400:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) 			reg_value =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) 			    CLE266_LCD_HOR_SCF_FORMULA(set_hres, panel_hres);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) 			viafb_load_reg_num =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356) 			    lcd_scaling_factor_CLE.lcd_hor_scaling_factor.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) 			    reg_num;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358) 			reg = lcd_scaling_factor_CLE.lcd_hor_scaling_factor.reg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) 			viafb_load_reg(reg_value,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) 				viafb_load_reg_num, reg, VIACR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) 		case UNICHROME_K800:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) 		case UNICHROME_PM800:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) 		case UNICHROME_CN700:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) 		case UNICHROME_CX700:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) 		case UNICHROME_K8M890:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) 		case UNICHROME_P4M890:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) 		case UNICHROME_P4M900:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) 		case UNICHROME_CN750:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) 		case UNICHROME_VX800:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) 		case UNICHROME_VX855:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) 		case UNICHROME_VX900:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) 			reg_value =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) 			    K800_LCD_HOR_SCF_FORMULA(set_hres, panel_hres);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) 			/* Horizontal scaling enabled */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) 			viafb_write_reg_mask(CRA2, VIACR, 0xC0, BIT7 + BIT6);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) 			viafb_load_reg_num =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) 			    lcd_scaling_factor.lcd_hor_scaling_factor.reg_num;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) 			reg = lcd_scaling_factor.lcd_hor_scaling_factor.reg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) 			viafb_load_reg(reg_value,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) 				viafb_load_reg_num, reg, VIACR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) 		DEBUG_MSG(KERN_INFO "Horizontal Scaling value = %d", reg_value);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) 		/* Horizontal scaling disabled */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) 		viafb_write_reg_mask(CRA2, VIACR, 0x00, BIT7);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) 	/* Check if expansion for vertical */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) 	if (set_vres < panel_vres) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393) 		/* Load Vertical Scaling Factor */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) 		switch (viaparinfo->chip_info->gfx_chip_name) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) 		case UNICHROME_CLE266:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) 		case UNICHROME_K400:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) 			reg_value =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) 			    CLE266_LCD_VER_SCF_FORMULA(set_vres, panel_vres);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399) 			viafb_load_reg_num =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) 			    lcd_scaling_factor_CLE.lcd_ver_scaling_factor.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) 			    reg_num;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402) 			reg = lcd_scaling_factor_CLE.lcd_ver_scaling_factor.reg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) 			viafb_load_reg(reg_value,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) 				viafb_load_reg_num, reg, VIACR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) 		case UNICHROME_K800:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) 		case UNICHROME_PM800:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) 		case UNICHROME_CN700:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) 		case UNICHROME_CX700:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) 		case UNICHROME_K8M890:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411) 		case UNICHROME_P4M890:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) 		case UNICHROME_P4M900:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413) 		case UNICHROME_CN750:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) 		case UNICHROME_VX800:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) 		case UNICHROME_VX855:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416) 		case UNICHROME_VX900:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417) 			reg_value =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) 			    K800_LCD_VER_SCF_FORMULA(set_vres, panel_vres);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419) 			/* Vertical scaling enabled */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) 			viafb_write_reg_mask(CRA2, VIACR, 0x08, BIT3);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421) 			viafb_load_reg_num =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) 			    lcd_scaling_factor.lcd_ver_scaling_factor.reg_num;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423) 			reg = lcd_scaling_factor.lcd_ver_scaling_factor.reg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) 			viafb_load_reg(reg_value,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) 				viafb_load_reg_num, reg, VIACR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429) 		DEBUG_MSG(KERN_INFO "Vertical Scaling value = %d", reg_value);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) 		/* Vertical scaling disabled */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432) 		viafb_write_reg_mask(CRA2, VIACR, 0x00, BIT3);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) static void via_pitch_alignment_patch_lcd(int iga_path, int hres, int bpp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438) 	unsigned char cr13, cr35, cr65, cr66, cr67;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439) 	unsigned long dwScreenPitch = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440) 	unsigned long dwPitch;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442) 	dwPitch = hres * (bpp >> 3);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443) 	if (dwPitch & 0x1F) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444) 		dwScreenPitch = ((dwPitch + 31) & ~31) >> 3;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445) 		if (iga_path == IGA2) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446) 			if (bpp > 8) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447) 				cr66 = (unsigned char)(dwScreenPitch & 0xFF);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448) 				viafb_write_reg(CR66, VIACR, cr66);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449) 				cr67 = viafb_read_reg(VIACR, CR67) & 0xFC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450) 				cr67 |=
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451) 				    (unsigned
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452) 				     char)((dwScreenPitch & 0x300) >> 8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453) 				viafb_write_reg(CR67, VIACR, cr67);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454) 			}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) 			/* Fetch Count */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457) 			cr67 = viafb_read_reg(VIACR, CR67) & 0xF3;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458) 			cr67 |= (unsigned char)((dwScreenPitch & 0x600) >> 7);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459) 			viafb_write_reg(CR67, VIACR, cr67);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460) 			cr65 = (unsigned char)((dwScreenPitch >> 1) & 0xFF);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 461) 			cr65 += 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 462) 			viafb_write_reg(CR65, VIACR, cr65);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 463) 		} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 464) 			if (bpp > 8) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 465) 				cr13 = (unsigned char)(dwScreenPitch & 0xFF);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 466) 				viafb_write_reg(CR13, VIACR, cr13);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 467) 				cr35 = viafb_read_reg(VIACR, CR35) & 0x1F;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 468) 				cr35 |=
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 469) 				    (unsigned
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 470) 				     char)((dwScreenPitch & 0x700) >> 3);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 471) 				viafb_write_reg(CR35, VIACR, cr35);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 472) 			}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 473) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 474) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 475) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 476) static void lcd_patch_skew_dvp0(struct lvds_setting_information
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 477) 			 *plvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 478) 			 struct lvds_chip_information *plvds_chip_info)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 479) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 480) 	if (VT1636_LVDS == plvds_chip_info->lvds_chip_name) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 481) 		switch (viaparinfo->chip_info->gfx_chip_name) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 482) 		case UNICHROME_P4M900:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 483) 			viafb_vt1636_patch_skew_on_vt3364(plvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 484) 						    plvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 485) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 486) 		case UNICHROME_P4M890:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 487) 			viafb_vt1636_patch_skew_on_vt3327(plvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 488) 						    plvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 489) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 490) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 491) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 492) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 493) static void lcd_patch_skew_dvp1(struct lvds_setting_information
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 494) 			 *plvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 495) 			 struct lvds_chip_information *plvds_chip_info)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 496) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 497) 	if (VT1636_LVDS == plvds_chip_info->lvds_chip_name) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 498) 		switch (viaparinfo->chip_info->gfx_chip_name) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 499) 		case UNICHROME_CX700:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 500) 			viafb_vt1636_patch_skew_on_vt3324(plvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 501) 						    plvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 502) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 503) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 504) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 505) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 506) static void lcd_patch_skew(struct lvds_setting_information
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 507) 	*plvds_setting_info, struct lvds_chip_information *plvds_chip_info)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 508) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 509) 	DEBUG_MSG(KERN_INFO "lcd_patch_skew\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 510) 	switch (plvds_chip_info->output_interface) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 511) 	case INTERFACE_DVP0:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 512) 		lcd_patch_skew_dvp0(plvds_setting_info, plvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 513) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 514) 	case INTERFACE_DVP1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 515) 		lcd_patch_skew_dvp1(plvds_setting_info, plvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 516) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 517) 	case INTERFACE_DFP_LOW:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 518) 		if (UNICHROME_P4M900 == viaparinfo->chip_info->gfx_chip_name) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 519) 			viafb_write_reg_mask(CR99, VIACR, 0x08,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 520) 				       BIT0 + BIT1 + BIT2 + BIT3);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 521) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 522) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 523) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 524) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 525) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 526) /* LCD Set Mode */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 527) void viafb_lcd_set_mode(const struct fb_var_screeninfo *var, u16 cxres,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 528) 	u16 cyres, struct lvds_setting_information *plvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 529) 	struct lvds_chip_information *plvds_chip_info)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 530) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 531) 	int set_iga = plvds_setting_info->iga_path;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 532) 	int mode_bpp = var->bits_per_pixel;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 533) 	int set_hres = cxres ? cxres : var->xres;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 534) 	int set_vres = cyres ? cyres : var->yres;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 535) 	int panel_hres = plvds_setting_info->lcd_panel_hres;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 536) 	int panel_vres = plvds_setting_info->lcd_panel_vres;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 537) 	u32 clock;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 538) 	struct via_display_timing timing;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 539) 	struct fb_var_screeninfo panel_var;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 540) 	const struct fb_videomode *mode_crt_table, *panel_crt_table;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 541) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 542) 	DEBUG_MSG(KERN_INFO "viafb_lcd_set_mode!!\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 543) 	/* Get mode table */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 544) 	mode_crt_table = viafb_get_best_mode(set_hres, set_vres, 60);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 545) 	/* Get panel table Pointer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 546) 	panel_crt_table = viafb_get_best_mode(panel_hres, panel_vres, 60);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 547) 	viafb_fill_var_timing_info(&panel_var, panel_crt_table);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 548) 	DEBUG_MSG(KERN_INFO "bellow viafb_lcd_set_mode!!\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 549) 	if (VT1636_LVDS == plvds_chip_info->lvds_chip_name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 550) 		viafb_init_lvds_vt1636(plvds_setting_info, plvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 551) 	clock = PICOS2KHZ(panel_crt_table->pixclock) * 1000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 552) 	plvds_setting_info->vclk = clock;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 553) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 554) 	if (set_iga == IGA2 && (set_hres < panel_hres || set_vres < panel_vres)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 555) 		&& plvds_setting_info->display_method == LCD_EXPANDSION) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 556) 		timing = var_to_timing(&panel_var, panel_hres, panel_vres);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 557) 		load_lcd_scaling(set_hres, set_vres, panel_hres, panel_vres);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 558) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 559) 		timing = var_to_timing(&panel_var, set_hres, set_vres);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 560) 		if (set_iga == IGA2)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 561) 			/* disable scaling */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 562) 			via_write_reg_mask(VIACR, 0x79, 0x00,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 563) 				BIT0 + BIT1 + BIT2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 564) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 565) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 566) 	if (set_iga == IGA1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 567) 		via_set_primary_timing(&timing);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 568) 	else if (set_iga == IGA2)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 569) 		via_set_secondary_timing(&timing);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 570) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 571) 	/* Fetch count for IGA2 only */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 572) 	viafb_load_fetch_count_reg(set_hres, mode_bpp / 8, set_iga);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 573) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 574) 	if ((viaparinfo->chip_info->gfx_chip_name != UNICHROME_CLE266)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 575) 		&& (viaparinfo->chip_info->gfx_chip_name != UNICHROME_K400))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 576) 		viafb_load_FIFO_reg(set_iga, set_hres, set_vres);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 577) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 578) 	fill_lcd_format();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 579) 	viafb_set_vclock(clock, set_iga);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 580) 	lcd_patch_skew(plvds_setting_info, plvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 581) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 582) 	/* If K8M800, enable LCD Prefetch Mode. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 583) 	if ((viaparinfo->chip_info->gfx_chip_name == UNICHROME_K800)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 584) 	    || (UNICHROME_K8M890 == viaparinfo->chip_info->gfx_chip_name))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 585) 		viafb_write_reg_mask(CR6A, VIACR, 0x01, BIT0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 586) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 587) 	/* Patch for non 32bit alignment mode */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 588) 	via_pitch_alignment_patch_lcd(plvds_setting_info->iga_path, set_hres,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 589) 		var->bits_per_pixel);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 590) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 591) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 592) static void integrated_lvds_disable(struct lvds_setting_information
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 593) 			     *plvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 594) 			     struct lvds_chip_information *plvds_chip_info)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 595) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 596) 	bool turn_off_first_powersequence = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 597) 	bool turn_off_second_powersequence = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 598) 	if (INTERFACE_LVDS0LVDS1 == plvds_chip_info->output_interface)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 599) 		turn_off_first_powersequence = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 600) 	if (INTERFACE_LVDS0 == plvds_chip_info->output_interface)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 601) 		turn_off_first_powersequence = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 602) 	if (INTERFACE_LVDS1 == plvds_chip_info->output_interface)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 603) 		turn_off_second_powersequence = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 604) 	if (turn_off_second_powersequence) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 605) 		/* Use second power sequence control: */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 606) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 607) 		/* Turn off power sequence. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 608) 		viafb_write_reg_mask(CRD4, VIACR, 0, BIT1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 609) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 610) 		/* Turn off back light. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 611) 		viafb_write_reg_mask(CRD3, VIACR, 0xC0, BIT6 + BIT7);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 612) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 613) 	if (turn_off_first_powersequence) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 614) 		/* Use first power sequence control: */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 615) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 616) 		/* Turn off power sequence. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 617) 		viafb_write_reg_mask(CR6A, VIACR, 0, BIT3);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 618) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 619) 		/* Turn off back light. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 620) 		viafb_write_reg_mask(CR91, VIACR, 0xC0, BIT6 + BIT7);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 621) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 622) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 623) 	/* Power off LVDS channel. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 624) 	switch (plvds_chip_info->output_interface) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 625) 	case INTERFACE_LVDS0:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 626) 		{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 627) 			viafb_write_reg_mask(CRD2, VIACR, 0x80, BIT7);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 628) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 629) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 630) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 631) 	case INTERFACE_LVDS1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 632) 		{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 633) 			viafb_write_reg_mask(CRD2, VIACR, 0x40, BIT6);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 634) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 635) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 636) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 637) 	case INTERFACE_LVDS0LVDS1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 638) 		{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 639) 			viafb_write_reg_mask(CRD2, VIACR, 0xC0, BIT6 + BIT7);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 640) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 641) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 642) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 643) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 644) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 645) static void integrated_lvds_enable(struct lvds_setting_information
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 646) 			    *plvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 647) 			    struct lvds_chip_information *plvds_chip_info)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 648) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 649) 	DEBUG_MSG(KERN_INFO "integrated_lvds_enable, out_interface:%d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 650) 		  plvds_chip_info->output_interface);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 651) 	if (plvds_setting_info->lcd_mode == LCD_SPWG)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 652) 		viafb_write_reg_mask(CRD2, VIACR, 0x00, BIT0 + BIT1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 653) 	else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 654) 		viafb_write_reg_mask(CRD2, VIACR, 0x03, BIT0 + BIT1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 655) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 656) 	switch (plvds_chip_info->output_interface) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 657) 	case INTERFACE_LVDS0LVDS1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 658) 	case INTERFACE_LVDS0:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 659) 		/* Use first power sequence control: */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 660) 		/* Use hardware control power sequence. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 661) 		viafb_write_reg_mask(CR91, VIACR, 0, BIT0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 662) 		/* Turn on back light. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 663) 		viafb_write_reg_mask(CR91, VIACR, 0, BIT6 + BIT7);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 664) 		/* Turn on hardware power sequence. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 665) 		viafb_write_reg_mask(CR6A, VIACR, 0x08, BIT3);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 666) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 667) 	case INTERFACE_LVDS1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 668) 		/* Use second power sequence control: */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 669) 		/* Use hardware control power sequence. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 670) 		viafb_write_reg_mask(CRD3, VIACR, 0, BIT0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 671) 		/* Turn on back light. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 672) 		viafb_write_reg_mask(CRD3, VIACR, 0, BIT6 + BIT7);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 673) 		/* Turn on hardware power sequence. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 674) 		viafb_write_reg_mask(CRD4, VIACR, 0x02, BIT1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 675) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 676) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 677) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 678) 	/* Power on LVDS channel. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 679) 	switch (plvds_chip_info->output_interface) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 680) 	case INTERFACE_LVDS0:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 681) 		{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 682) 			viafb_write_reg_mask(CRD2, VIACR, 0, BIT7);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 683) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 684) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 685) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 686) 	case INTERFACE_LVDS1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 687) 		{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 688) 			viafb_write_reg_mask(CRD2, VIACR, 0, BIT6);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 689) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 690) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 691) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 692) 	case INTERFACE_LVDS0LVDS1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 693) 		{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 694) 			viafb_write_reg_mask(CRD2, VIACR, 0, BIT6 + BIT7);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 695) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 696) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 697) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 698) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 699) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 700) void viafb_lcd_disable(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 701) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 702) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 703) 	if (viaparinfo->chip_info->gfx_chip_name == UNICHROME_CLE266) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 704) 		lcd_powersequence_off();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 705) 		/* DI1 pad off */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 706) 		viafb_write_reg_mask(SR1E, VIASR, 0x00, 0x30);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 707) 	} else if (viaparinfo->chip_info->gfx_chip_name == UNICHROME_CX700) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 708) 		if (viafb_LCD2_ON
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 709) 		    && (INTEGRATED_LVDS ==
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 710) 			viaparinfo->chip_info->lvds_chip_info2.lvds_chip_name))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 711) 			integrated_lvds_disable(viaparinfo->lvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 712) 				&viaparinfo->chip_info->lvds_chip_info2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 713) 		if (INTEGRATED_LVDS ==
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 714) 			viaparinfo->chip_info->lvds_chip_info.lvds_chip_name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 715) 			integrated_lvds_disable(viaparinfo->lvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 716) 				&viaparinfo->chip_info->lvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 717) 		if (VT1636_LVDS == viaparinfo->chip_info->
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 718) 			lvds_chip_info.lvds_chip_name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 719) 			viafb_disable_lvds_vt1636(viaparinfo->lvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 720) 				&viaparinfo->chip_info->lvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 721) 	} else if (VT1636_LVDS ==
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 722) 	viaparinfo->chip_info->lvds_chip_info.lvds_chip_name) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 723) 		viafb_disable_lvds_vt1636(viaparinfo->lvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 724) 				    &viaparinfo->chip_info->lvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 725) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 726) 		/* Backlight off           */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 727) 		viafb_write_reg_mask(SR3D, VIASR, 0x00, 0x20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 728) 		/* 24 bit DI data paht off */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 729) 		viafb_write_reg_mask(CR91, VIACR, 0x80, 0x80);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 730) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 731) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 732) 	/* Disable expansion bit   */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 733) 	viafb_write_reg_mask(CR79, VIACR, 0x00, 0x01);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 734) 	/* Simultaneout disabled   */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 735) 	viafb_write_reg_mask(CR6B, VIACR, 0x00, 0x08);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 736) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 737) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 738) static void set_lcd_output_path(int set_iga, int output_interface)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 739) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 740) 	switch (output_interface) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 741) 	case INTERFACE_DFP:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 742) 		if ((UNICHROME_K8M890 == viaparinfo->chip_info->gfx_chip_name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 743) 		    || (UNICHROME_P4M890 ==
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 744) 		    viaparinfo->chip_info->gfx_chip_name))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 745) 			viafb_write_reg_mask(CR97, VIACR, 0x84,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 746) 				       BIT7 + BIT2 + BIT1 + BIT0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 747) 		fallthrough;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 748) 	case INTERFACE_DVP0:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 749) 	case INTERFACE_DVP1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 750) 	case INTERFACE_DFP_HIGH:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 751) 	case INTERFACE_DFP_LOW:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 752) 		if (set_iga == IGA2)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 753) 			viafb_write_reg(CR91, VIACR, 0x00);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 754) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 755) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 756) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 757) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 758) void viafb_lcd_enable(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 759) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 760) 	viafb_write_reg_mask(CR6B, VIACR, 0x00, BIT3);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 761) 	viafb_write_reg_mask(CR6A, VIACR, 0x08, BIT3);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 762) 	set_lcd_output_path(viaparinfo->lvds_setting_info->iga_path,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 763) 		viaparinfo->chip_info->lvds_chip_info.output_interface);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 764) 	if (viafb_LCD2_ON)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 765) 		set_lcd_output_path(viaparinfo->lvds_setting_info2->iga_path,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 766) 			viaparinfo->chip_info->
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 767) 			lvds_chip_info2.output_interface);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 768) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 769) 	if (viaparinfo->chip_info->gfx_chip_name == UNICHROME_CLE266) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 770) 		/* DI1 pad on */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 771) 		viafb_write_reg_mask(SR1E, VIASR, 0x30, 0x30);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 772) 		lcd_powersequence_on();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 773) 	} else if (viaparinfo->chip_info->gfx_chip_name == UNICHROME_CX700) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 774) 		if (viafb_LCD2_ON && (INTEGRATED_LVDS ==
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 775) 			viaparinfo->chip_info->lvds_chip_info2.lvds_chip_name))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 776) 			integrated_lvds_enable(viaparinfo->lvds_setting_info2, \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 777) 				&viaparinfo->chip_info->lvds_chip_info2);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 778) 		if (INTEGRATED_LVDS ==
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 779) 			viaparinfo->chip_info->lvds_chip_info.lvds_chip_name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 780) 			integrated_lvds_enable(viaparinfo->lvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 781) 				&viaparinfo->chip_info->lvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 782) 		if (VT1636_LVDS == viaparinfo->chip_info->
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 783) 			lvds_chip_info.lvds_chip_name)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 784) 			viafb_enable_lvds_vt1636(viaparinfo->
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 785) 			lvds_setting_info, &viaparinfo->chip_info->
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 786) 			lvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 787) 	} else if (VT1636_LVDS ==
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 788) 	viaparinfo->chip_info->lvds_chip_info.lvds_chip_name) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 789) 		viafb_enable_lvds_vt1636(viaparinfo->lvds_setting_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 790) 				   &viaparinfo->chip_info->lvds_chip_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 791) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 792) 		/* Backlight on            */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 793) 		viafb_write_reg_mask(SR3D, VIASR, 0x20, 0x20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 794) 		/* 24 bit DI data paht on  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 795) 		viafb_write_reg_mask(CR91, VIACR, 0x00, 0x80);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 796) 		/* LCD enabled             */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 797) 		viafb_write_reg_mask(CR6A, VIACR, 0x48, 0x48);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 798) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 799) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 800) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 801) static void lcd_powersequence_off(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 802) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 803) 	int i, mask, data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 804) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 805) 	/* Software control power sequence */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 806) 	viafb_write_reg_mask(CR91, VIACR, 0x11, 0x11);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 807) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 808) 	for (i = 0; i < 3; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 809) 		mask = PowerSequenceOff[0][i];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 810) 		data = PowerSequenceOff[1][i] & mask;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 811) 		viafb_write_reg_mask(CR91, VIACR, (u8) data, (u8) mask);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 812) 		udelay(PowerSequenceOff[2][i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 813) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 814) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 815) 	/* Disable LCD */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 816) 	viafb_write_reg_mask(CR6A, VIACR, 0x00, 0x08);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 817) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 818) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 819) static void lcd_powersequence_on(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 820) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 821) 	int i, mask, data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 822) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 823) 	/* Software control power sequence */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 824) 	viafb_write_reg_mask(CR91, VIACR, 0x11, 0x11);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 825) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 826) 	/* Enable LCD */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 827) 	viafb_write_reg_mask(CR6A, VIACR, 0x08, 0x08);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 828) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 829) 	for (i = 0; i < 3; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 830) 		mask = PowerSequenceOn[0][i];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 831) 		data = PowerSequenceOn[1][i] & mask;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 832) 		viafb_write_reg_mask(CR91, VIACR, (u8) data, (u8) mask);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 833) 		udelay(PowerSequenceOn[2][i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 834) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 835) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 836) 	udelay(1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 837) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 838) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 839) static void fill_lcd_format(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 840) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 841) 	u8 bdithering = 0, bdual = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 842) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 843) 	if (viaparinfo->lvds_setting_info->device_lcd_dualedge)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 844) 		bdual = BIT4;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 845) 	if (viaparinfo->lvds_setting_info->LCDDithering)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 846) 		bdithering = BIT0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 847) 	/* Dual & Dithering */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 848) 	viafb_write_reg_mask(CR88, VIACR, (bdithering | bdual), BIT4 + BIT0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 849) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 850) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 851) static void check_diport_of_integrated_lvds(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 852) 	struct lvds_chip_information *plvds_chip_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 853) 				     struct lvds_setting_information
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 854) 				     *plvds_setting_info)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 855) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 856) 	/* Determine LCD DI Port by hardware layout. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 857) 	switch (viafb_display_hardware_layout) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 858) 	case HW_LAYOUT_LCD_ONLY:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 859) 		{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 860) 			if (plvds_setting_info->device_lcd_dualedge) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 861) 				plvds_chip_info->output_interface =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 862) 				    INTERFACE_LVDS0LVDS1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 863) 			} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 864) 				plvds_chip_info->output_interface =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 865) 				    INTERFACE_LVDS0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 866) 			}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 867) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 868) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 869) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 870) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 871) 	case HW_LAYOUT_DVI_ONLY:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 872) 		{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 873) 			plvds_chip_info->output_interface = INTERFACE_NONE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 874) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 875) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 876) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 877) 	case HW_LAYOUT_LCD1_LCD2:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 878) 	case HW_LAYOUT_LCD_EXTERNAL_LCD2:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 879) 		{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 880) 			plvds_chip_info->output_interface =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 881) 			    INTERFACE_LVDS0LVDS1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 882) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 883) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 884) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 885) 	case HW_LAYOUT_LCD_DVI:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 886) 		{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 887) 			plvds_chip_info->output_interface = INTERFACE_LVDS1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 888) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 889) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 890) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 891) 	default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 892) 		{
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 893) 			plvds_chip_info->output_interface = INTERFACE_LVDS1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 894) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 895) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 896) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 897) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 898) 	DEBUG_MSG(KERN_INFO
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 899) 		  "Display Hardware Layout: 0x%x, LCD DI Port: 0x%x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 900) 		  viafb_display_hardware_layout,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 901) 		  plvds_chip_info->output_interface);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 902) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 903) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 904) void viafb_init_lvds_output_interface(struct lvds_chip_information
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 905) 				*plvds_chip_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 906) 				struct lvds_setting_information
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 907) 				*plvds_setting_info)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 908) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 909) 	if (INTERFACE_NONE != plvds_chip_info->output_interface) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 910) 		/*Do nothing, lcd port is specified by module parameter */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 911) 		return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 912) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 913) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 914) 	switch (plvds_chip_info->lvds_chip_name) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 915) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 916) 	case VT1636_LVDS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 917) 		switch (viaparinfo->chip_info->gfx_chip_name) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 918) 		case UNICHROME_CX700:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 919) 			plvds_chip_info->output_interface = INTERFACE_DVP1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 920) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 921) 		case UNICHROME_CN700:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 922) 			plvds_chip_info->output_interface = INTERFACE_DFP_LOW;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 923) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 924) 		default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 925) 			plvds_chip_info->output_interface = INTERFACE_DVP0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 926) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 927) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 928) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 929) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 930) 	case INTEGRATED_LVDS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 931) 		check_diport_of_integrated_lvds(plvds_chip_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 932) 						plvds_setting_info);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 933) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 934) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 935) 	default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 936) 		switch (viaparinfo->chip_info->gfx_chip_name) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 937) 		case UNICHROME_K8M890:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 938) 		case UNICHROME_P4M900:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 939) 		case UNICHROME_P4M890:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 940) 			plvds_chip_info->output_interface = INTERFACE_DFP_LOW;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 941) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 942) 		default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 943) 			plvds_chip_info->output_interface = INTERFACE_DFP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 944) 			break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 945) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 946) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 947) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 948) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 949) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 950) bool viafb_lcd_get_mobile_state(bool *mobile)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 951) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 952) 	unsigned char __iomem *romptr, *tableptr, *biosptr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 953) 	u8 core_base;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 954) 	/* Rom address */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 955) 	const u32 romaddr = 0x000C0000;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 956) 	u16 start_pattern;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 957) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 958) 	biosptr = ioremap(romaddr, 0x10000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 959) 	start_pattern = readw(biosptr);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 960) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 961) 	/* Compare pattern */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 962) 	if (start_pattern == 0xAA55) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 963) 		/* Get the start of Table */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 964) 		/* 0x1B means BIOS offset position */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 965) 		romptr = biosptr + 0x1B;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 966) 		tableptr = biosptr + readw(romptr);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 967) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 968) 		/* Get the start of biosver structure */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 969) 		/* 18 means BIOS version position. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 970) 		romptr = tableptr + 18;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 971) 		romptr = biosptr + readw(romptr);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 972) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 973) 		/* The offset should be 44, but the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 974) 		   actual image is less three char. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 975) 		/* pRom += 44; */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 976) 		romptr += 41;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 977) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 978) 		core_base = readb(romptr);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 979) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 980) 		if (core_base & 0x8)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 981) 			*mobile = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 982) 		else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 983) 			*mobile = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 984) 		/* release memory */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 985) 		iounmap(biosptr);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 986) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 987) 		return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 988) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 989) 		iounmap(biosptr);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 990) 		return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 991) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 992) }