rk610 hdmi fix some problem
authoryzq <yzq@rock-chip.com>
Wed, 2 May 2012 08:03:56 +0000 (01:03 -0700)
committeryzq <yzq@rock-chip.com>
Thu, 3 May 2012 08:47:17 +0000 (01:47 -0700)
drivers/video/hdmi/chips/rk610/rk610_hdmi.c
drivers/video/hdmi/chips/rk610/rk610_hdmi_hw.c
drivers/video/hdmi/chips/rk610/rk610_hdmi_hw.h
drivers/video/hdmi/hdmi-codec.c
drivers/video/rk29_fb.c
include/linux/rk_screen.h

index 72b29189e941d97f2378cfdec12b015a616b4973..d9c6fcaa5006895202e125aa87dbaf6ad3d723fd 100644 (file)
@@ -64,6 +64,7 @@ static int rk610_hdmi_insert(struct hdmi *hdmi)
     RK610_DBG(&rk610_hdmi->client->dev,"%s \n",__FUNCTION__);\r
        if(rk610_hdmi->init == 1)\r
                return -1;\r
+       Rk610_hdmi_plug(rk610_hdmi->client);
        rk610_hdmi_param_chg(rk610_hdmi);\r
     hdmi_set_spk(HDMI_DISABLE);\r
     printk("rk610_hdmi_insert hdmi->display_on=%d\n",hdmi->display_on);\r
@@ -78,6 +79,7 @@ static int rk610_hdmi_remove(struct hdmi *hdmi)
                return -1;\r
        hdmi_set_spk(HDMI_ENABLE);\r
        hdmi_switch_fb(hdmi, HDMI_DISABLE);\r
+       Rk610_hdmi_unplug(rk610_hdmi->client);
        printk("rk610_hdmi_remove hdmi->display_on=%d\n",hdmi->display_on);\r
        return 0;\r
 }\r
index ac8c3984c47df72c74dc5550f0c103d5c09423f6..d3c72aca9e0962dee3f60fb1e2000743b47afd87 100644 (file)
@@ -9,8 +9,8 @@ static struct edid_result Rk610_edid_result;
 byte DoEdidRead (struct i2c_client *client);\r
 static int RK610_hdmi_soft_reset(struct i2c_client *client);\r
 static int Rk610_hdmi_Display_switch(struct i2c_client *client);\r
-static void Rk610_hdmi_plug(struct i2c_client *client);\r
-static void Rk610_hdmi_unplug(struct i2c_client *client);\r
+static int Rk610_hdmi_sys_power_up(struct i2c_client *client);\r
+static int Rk610_hdmi_sys_power_down(struct i2c_client *client);\r
 \r
 static int Rk610_hdmi_i2c_read_p0_reg(struct i2c_client *client, char reg, char *val)\r
 {\r
@@ -20,25 +20,42 @@ static int Rk610_hdmi_i2c_write_p0_reg(struct i2c_client *client, char reg, char
 {\r
        return i2c_master_reg8_send(client, reg, val, 1, 100*1000) > 0? 0: -EINVAL;\r
 }\r
-\r
+static int RK610_hdmi_audio_mute(struct i2c_client *client,bool enable)\r
+{\r
+       char c;\r
+       int ret=0;\r
+    c = ((~enable)&1)<<1;\r
+       ret =Rk610_hdmi_i2c_write_p0_reg(client, 0x05, &c);\r
+}\r
 static int Rk610_hdmi_pwr_mode(struct i2c_client *client, int mode)\r
 {\r
     char c;\r
     int ret=0;\r
+       RK610_DBG(&client->dev,"%s \n",__FUNCTION__);\r
     switch(mode){\r
      case NORMAL:\r
+               Rk610_hdmi_sys_power_down(client);\r
+               c=0x82;\r
+           ret =Rk610_hdmi_i2c_write_p0_reg(client, 0xe3, &c);\r
+               c=0x00;\r
+           ret =Rk610_hdmi_i2c_write_p0_reg(client, 0xe5, &c);\r
         c=0x00;\r
            ret =Rk610_hdmi_i2c_write_p0_reg(client, 0xe4, &c);\r
            c=0x00;\r
            ret =Rk610_hdmi_i2c_write_p0_reg(client, 0xe7, &c);\r
         c=0x8e;\r
-           ret =Rk610_hdmi_i2c_write_p0_reg(client, 0xe1, &c);\r
-           c=0x00;\r
-           ret =Rk610_hdmi_i2c_write_p0_reg(client, 0xe5, &c);\r
-               c=0x82;\r
-           ret =Rk610_hdmi_i2c_write_p0_reg(client, 0xe3, &c);   \r
-           break;\r
+               ret =Rk610_hdmi_i2c_write_p0_reg(client, 0xe1, &c);\r
+               c=0x00;\r
+               ret =Rk610_hdmi_i2c_write_p0_reg(client, 0xce, &c);\r
+               c=0x01;\r
+               ret =Rk610_hdmi_i2c_write_p0_reg(client, 0xce, &c);\r
+               RK610_hdmi_audio_mute(client,1);\r
+               Rk610_hdmi_sys_power_up(client);\r
+               g_hw_inf.analog_sync = 1;\r
+               break;\r
        case LOWER_PWR:\r
+               RK610_hdmi_audio_mute(client,0);\r
+               Rk610_hdmi_sys_power_down(client);\r
                c=0x02;\r
            ret =Rk610_hdmi_i2c_write_p0_reg(client, 0xe3, &c);\r
            c=0x1c;\r
@@ -49,7 +66,7 @@ static int Rk610_hdmi_pwr_mode(struct i2c_client *client, int mode)
            ret =Rk610_hdmi_i2c_write_p0_reg(client, 0xe7, &c);\r
            c=0x03;\r
            ret =Rk610_hdmi_i2c_write_p0_reg(client, 0xe4, &c);\r
-           break;\r
+               break;\r
        default:\r
            RK610_ERR(&client->dev,"unkown rk610 hdmi pwr mode %d\n",mode);\r
     }\r
@@ -84,21 +101,21 @@ int Rk610_hdmi_resume(struct i2c_client *client)
        return ret;\r
 }\r
 #endif\r
-static int Rk610_hdmi_sys_power_down(struct i2c_client *client)\r
+static int Rk610_hdmi_sys_power_up(struct i2c_client *client)\r
 {\r
     char c = 0;\r
     int ret = 0;\r
     RK610_DBG(&client->dev,"%s \n",__FUNCTION__);\r
-    c= RK610_SYS_CLK<<2 |RK610_SYS_PWR_OFF<<1 |RK610_INT_POL;\r
+    c= RK610_SYS_CLK<<2 |RK610_SYS_PWR_ON<<1 |RK610_INT_POL;\r
        ret =Rk610_hdmi_i2c_write_p0_reg(client, 0x00, &c);\r
        return ret;\r
 }\r
-static int Rk610_hdmi_sys_power_up(struct i2c_client *client)\r
+static int Rk610_hdmi_sys_power_down(struct i2c_client *client)\r
 {\r
     char c = 0;\r
     int ret = 0;\r
     RK610_DBG(&client->dev,"%s \n",__FUNCTION__);\r
-    c= RK610_SYS_CLK<<2 |RK610_SYS_PWR_ON<<1 |RK610_INT_POL;\r
+    c= RK610_SYS_CLK<<2 |RK610_SYS_PWR_OFF<<1 |RK610_INT_POL;\r
        ret =Rk610_hdmi_i2c_write_p0_reg(client, 0x00, &c);\r
        return ret;\r
 }\r
@@ -1106,15 +1123,14 @@ static int RK610_hdmi_PLL_mode(struct i2c_client *client)
        ret = Rk610_hdmi_i2c_write_p0_reg(client, 0xe5, &c);\r
        return 0;\r
 }\r
-static void Rk610_hdmi_plug(struct i2c_client *client)\r
+void Rk610_hdmi_plug(struct i2c_client *client)\r
 {\r
     RK610_DBG(&client->dev,">>> hdmi plug \n");\r
        DoEdidRead(client);\r
        Rk610_hdmi_Display_switch(client);\r
-       Rk610_hdmi_pwr_mode(client,LOWER_PWR);\r
        Rk610_hdmi_pwr_mode(client,NORMAL);\r
 }\r
-static void Rk610_hdmi_unplug(struct i2c_client *client)\r
+void Rk610_hdmi_unplug(struct i2c_client *client)\r
 {\r
     RK610_DBG(&client->dev,">>> hdmi unplug \n");\r
        g_edid.edidDataValid = FALSE;\r
@@ -1138,11 +1154,11 @@ void Rk610_hdmi_event_work(struct i2c_client *client, bool *hpd)
            ret =Rk610_hdmi_i2c_write_p0_reg(client, 0xc1, &c);\r
            ret =Rk610_hdmi_i2c_read_p0_reg(client, 0xc8, &c);\r
                if(c & RK610_HPD_PLUG ){\r
-            Rk610_hdmi_plug(client);\r
+        //    Rk610_hdmi_plug(client);\r
                        g_hw_inf.hpd=1;\r
                }\r
                else{\r
-            Rk610_hdmi_unplug(client);\r
+          //  Rk610_hdmi_unplug(client);\r
                        g_hw_inf.hpd=0;\r
                }\r
 \r
@@ -1162,7 +1178,7 @@ int Rk610_hdmi_Config_Done(struct i2c_client *client)
     int ret=0;\r
     RK610_DBG(&client->dev,"%s \n",__FUNCTION__);\r
 \r
-    ret =Rk610_hdmi_sys_power_up(client);\r
+    ret =Rk610_hdmi_sys_power_down(client);\r
 \r
     if(g_hw_inf.config_param != 0){\r
        c=0x08;\r
@@ -1178,9 +1194,16 @@ int Rk610_hdmi_Config_Done(struct i2c_client *client)
         g_hw_inf.config_param &= (~AUDIO_CHANGE); \r
        }\r
     }\r
-    ret =Rk610_hdmi_sys_power_down(client);\r
     ret =Rk610_hdmi_sys_power_up(client);\r
     ret =Rk610_hdmi_sys_power_down(client);\r
+    ret =Rk610_hdmi_sys_power_up(client);\r
+       if(g_hw_inf.analog_sync){\r
+               c=0x00;\r
+               ret =Rk610_hdmi_i2c_write_p0_reg(client, 0xce, &c);\r
+               c=0x01;\r
+               ret =Rk610_hdmi_i2c_write_p0_reg(client, 0xce, &c);\r
+               g_hw_inf.analog_sync = 0;\r
+       }\r
 \r
     return ret;\r
 }\r
@@ -1220,7 +1243,7 @@ static void Rk610_hdmi_Variable_Initial(void)
     g_hw_inf.config_param = AUDIO_CHANGE | VIDEO_CHANGE;\r
     g_hw_inf.hpd = 0;\r
     g_hw_inf.suspend_flag = 0;\r
-\r
+       g_hw_inf.analog_sync = 0;\r
 }\r
 int Rk610_hdmi_init(struct i2c_client *client)\r
 {\r
@@ -1233,14 +1256,13 @@ int Rk610_hdmi_init(struct i2c_client *client)
        Rk610_hdmi_Set_Video(g_hw_inf.video_format);\r
        Rk610_hdmi_Set_Audio(g_hw_inf.audio_fs);\r
     Rk610_hdmi_Config_Done(client);\r
-    \r
     Rk610_hdmi_i2c_read_p0_reg(client, 0xc8, &c);\r
-    if(c & RK610_HPD_PLUG ){\r
+       if(c & RK610_HPD_PLUG ){\r
         Rk610_hdmi_plug(client);\r
-           g_hw_inf.hpd=1;\r
+               g_hw_inf.hpd=1;\r
        }else{\r
-        Rk610_hdmi_unplug(client);\r
-           g_hw_inf.hpd=0;\r
+               Rk610_hdmi_unplug(client);\r
+               g_hw_inf.hpd=0;\r
        }\r
        return 0;\r
 }\r
index e14e19ada6a67dfe2de6d8fdd317a3eddb39298c..bc84f151fa30e84f66c7313e82d2f815c8bf08d5 100644 (file)
@@ -100,8 +100,8 @@ enum{
 \r
 //0x00\r
 #define RK610_INT_POL       1\r
-#define RK610_SYS_PWR_ON    1\r
-#define RK610_SYS_PWR_OFF   0\r
+#define RK610_SYS_PWR_ON    0\r
+#define RK610_SYS_PWR_OFF   1\r
 #define RK610_PHY_CLK       0\r
 #define RK610_SYS_CLK       1\r
 \r
@@ -239,13 +239,16 @@ struct rk610_hdmi_hw_inf{
     u8 audio_fs;\r
     u8 config_param;\r
     bool suspend_flag;\r
-    bool hpd;\r
+    bool hpd;
+       bool analog_sync;
 };\r
 \r
 #ifdef CONFIG_HAS_EARLYSUSPEND\r
 extern int Rk610_hdmi_suspend(struct i2c_client *client);\r
 extern int Rk610_hdmi_resume(struct i2c_client *client);\r
 #endif\r
+extern void Rk610_hdmi_plug(struct i2c_client *client);
+extern void Rk610_hdmi_unplug(struct i2c_client *client);
 extern int Rk610_hdmi_Set_Video(u8 video_format);\r
 extern int Rk610_hdmi_Set_Audio(u8 audio_fs);\r
 extern int Rk610_hdmi_Config_Done(struct i2c_client *client);\r
index e0360ceb7fd6a025acc72b5037a7d6178411cd59..a42b0228442f271411993ceb85984589ac16c60d 100755 (executable)
@@ -1,5 +1,5 @@
 #include <linux/hdmi.h>
-#if defined CONFIG_SND_SOC_WM8900 || defined CONFIG_SND_SOC_RT5631 || defined CONFIG_SND_SOC_RT5621
+#if defined CONFIG_SND_SOC_WM8900 || defined CONFIG_SND_SOC_RT5631 || defined CONFIG_SND_SOC_RT5621 || defined CONFIG_SND_RK29_SOC_RK610
 /* sound/soc/codecs/wm8900.c */
 extern void codec_set_spk(bool on);
 #else
index 1d39f93a7bb70b75b95319e5807cb9b923c29dd5..c1d1981e871e5e8204b207f33fc6ed8fcabd2fa9 100644 (file)
@@ -2935,8 +2935,14 @@ int FB_Switch_Screen( struct rk29fb_screen *screen, u32 enable )
     if(inf->cur_screen->standby)    inf->cur_screen->standby(1);
     // operate the display_on pin to power down the lcd
 #ifdef CONFIG_HDMI_DUAL_DISP
-    inf->panel1_info.sscreen_get(&inf->panel1_info,inf->panel2_info.hdmi_resolution);
-    inf->panel1_info.sscreen_set(&inf->panel1_info,enable);
+       if(inf->panel1_info.sscreen_get!=NULL)
+       inf->panel1_info.sscreen_get(&inf->panel1_info,inf->panel2_info.hdmi_resolution);
+       else
+               printk("warnig : LCD driver do not support dual display");
+       if(inf->panel1_info.sscreen_set!=NULL)
+       inf->panel1_info.sscreen_set(&inf->panel1_info,enable);
+       else
+               printk("warnig : LCD driver do not support dual display");
 #else
     if(enable && mach_info->io_disable)mach_info->io_disable();  //close lcd out
     else if (mach_info->io_enable)mach_info->io_enable();       //open lcd out
index ef404c6097523628a17db96be3211650f8dadb3e..2409ddc0938eb4e1797dc32d928702b354254fa8 100644 (file)
@@ -25,18 +25,24 @@ enum{
         
 enum{
     SCALE_PLL(148500000,    66000000,   16, 9,  4),
-    SCALE_PLL(148500000,    54000000,   16, 11, 4),
+    SCALE_PLL(148500000,    57375000,   17, 11, 4),
+    SCALE_PLL(148500000,    54000000,   16, 11, 4),    
     SCALE_PLL(148500000,    33000000,   16, 9,  8),
     SCALE_PLL(148500000,    30375000,   18, 11, 8),
     SCALE_PLL(148500000,    29700000,   16, 10, 8),
     SCALE_PLL(148500000,    25312500,   15, 11, 8),
 
     SCALE_PLL(74250000,     66000000,   32, 9,  4),
+    SCALE_PLL(74250000,     57375000,   34, 11, 4),
     SCALE_PLL(74250000,     54000000,   32, 11, 4),
     SCALE_PLL(74250000,     33000000,   32, 9,  8),
     SCALE_PLL(74250000,     30375000,   36, 11, 8),
     SCALE_PLL(74250000,     25312500,   30, 11, 8),
 
+    SCALE_PLL(27000000,     75000000,   100, 9,  4),
+    SCALE_PLL(27000000,     72000000,   32, 3,  4),
+    SCALE_PLL(27000000,     63281250,   75, 4,  8),
+    SCALE_PLL(27000000,     54375000,   145, 9,  8),
     SCALE_PLL(27000000,     31500000,   28, 3,  8),
     SCALE_PLL(27000000,     30000000,   80, 9,  8),
 };
@@ -125,6 +131,9 @@ typedef struct rk29fb_screen {
        u16 s_vsync_len; 
        u16 s_hsync_st;
        u16 s_vsync_st;
+       bool s_den_inv;
+       bool s_hv_sync_inv;
+       bool s_clk_inv;
 #endif
        u8 hdmi_resolution;
            /* mcu need */