b406710c75d87990ddfede5a96b918fd85d475b6
[profile/ivi/intel-emgd-kmod.git] / emgd / pal / ch7036 / ch7036_intf.c
1 /*-----------------------------------------------------------------------------
2 * Copyright (c) Chrontel Inc.
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a copy
5 * of this software and associated documentation files (the "Software"), to deal
6 * in the Software without restriction, including without limitation the rights
7 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8 * copies of the Software, and to permit persons to whom the Software is
9 * furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice shall be included in
12 * all copies or substantial portions of the Software.
13 *
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
20 * THE SOFTWARE.
21 *
22 *-----------------------------------------------------------------------------
23 * @file  ch7036_intf.c
24 * @version 1.2.5
25 *-----------------------------------------------------------------------------
26 */
27
28
29 #include "ch7036_intf.h"
30 #include "ch7036_attr.h"
31
32
33 #ifdef T_LINUX
34         #include "lvds/lvds.h"
35 #else
36         #include "lvds.h"
37 #endif
38
39
40 ch7036_status_t ch7036_get_hdmi_hpd(ch7036_device_context_t* p_ctx, uint8 *hpd);
41
42 unsigned long ch7036_invis_6x4_modes_table_size[3] = {2,3,5};
43 unsigned long ch7036_invis_8x6_7x4_table_size[3] = {3,5,6};
44
45 OUT_FMT hdmi_timing_table[OUT_HDMI_END] = {
46
47
48         {1,     25175,  1, {800,   640, 16,  96, 525,  480, 10,  2, 59, SCANTYPE_PROGRESSIVE} },
49     {1,     25250,  1, {800,   640, 16,  96, 525,  480, 10,  2, 60, SCANTYPE_PROGRESSIVE} },
50     {2,     27000,  1, {858,   720, 16,  62, 525,  480,  9,  6, 59, SCANTYPE_PROGRESSIVE} },
51     {2,     27027,  1, {858,   720, 16,  62, 525,  480,  9,  6, 60, SCANTYPE_PROGRESSIVE} },
52         {17,     27000,  1, {864,  720,  12,  64, 625,  576,  5,  5, 50, SCANTYPE_PROGRESSIVE} },
53
54     {4,     74176,  2, {1650, 1280, 110, 40, 750,  720,  5,  5, 59, SCANTYPE_PROGRESSIVE} },
55     {4,     74250,  2, {1650, 1280, 110, 40, 750,  720,  5,  5, 60, SCANTYPE_PROGRESSIVE} },
56     {5,     74176,  2, {2200, 1920, 88,  44, 1125, 1080, 2,  5, 59, SCANTYPE_INTERLACED} },
57     {5,     74250,  2, {2200, 1920, 88,  44, 1125, 1080, 2,  5, 60, SCANTYPE_INTERLACED} },
58         {16,    148350,  2, {2200, 1920, 88,  44, 1125, 1080, 4,  5, 59, SCANTYPE_PROGRESSIVE} },
59 //   {16,    148352,  2, {2200, 1920, 88,  44, 1125, 1080, 4,  5, 59, SCANTYPE_PROGRESSIVE} },
60    {16,    148500,  2, {2200, 1920, 88,  44, 1125, 1080, 4,  5, 60, SCANTYPE_PROGRESSIVE} },
61
62 //   {17,     27000,  1, {864,  720,  12,  64, 625,  576,  5,  5, 50, SCANTYPE_PROGRESSIVE} },
63    {19,     74250,  2, {1980, 1280, 440, 40, 750,  720,  5,  5, 50, SCANTYPE_PROGRESSIVE} },
64
65    {20,     74250,  2, {2640, 1920, 528, 44, 1125, 1080, 2, 5, 50, SCANTYPE_INTERLACED} },
66
67
68    {31,    148500,  2, {2640, 1920, 528, 44, 1125, 1080, 4,  5, 50, SCANTYPE_PROGRESSIVE} },
69    {32,     74175,  2, {2750, 1920, 638, 44, 1125, 1080, 4,  5, 23, SCANTYPE_PROGRESSIVE} },
70    {32,     74250,  2, {2750, 1920, 638, 44, 1125, 1080, 4,  5, 24, SCANTYPE_PROGRESSIVE} },
71    {33,     74250,  2, {2640, 1920, 528, 44, 1125, 1080, 4,  5, 25, SCANTYPE_PROGRESSIVE} },
72    {34,     74175,  2, {2200, 1920, 88,  44, 1125, 1080, 4,  5, 29, SCANTYPE_PROGRESSIVE} },
73    {34,     74250,  2, {2200, 1920, 88,  44, 1125, 1080, 4,  5, 30, SCANTYPE_PROGRESSIVE} },
74
75    {40,    148500,  2, {2640, 1920, 528, 44, 1124, 1080, 4, 10, 100, SCANTYPE_INTERLACED} },
76    {41,    148500,  2, {1980, 1280, 440, 40, 750,  720,  5,  5, 100, SCANTYPE_PROGRESSIVE} },
77    {42,     54000,  1, {864,   720, 12,  64, 625,  576,  5,  5, 100, SCANTYPE_PROGRESSIVE} },
78
79
80    {46,    148352,  2, {2200, 1920, 88,  44, 1124, 1080, 4, 10, 119, SCANTYPE_INTERLACED} },
81    {46,    148500,  2, {2200, 1920, 88,  44, 1124, 1080, 4, 10, 120, SCANTYPE_INTERLACED} },
82
83    {47,    148352,  2, {1650, 1280, 110, 40, 750,  720,  5,  5, 119, SCANTYPE_PROGRESSIVE} },
84    {47,    148500,  2, {1650, 1280, 110, 40, 750,  720,  5,  5, 120, SCANTYPE_PROGRESSIVE} },
85
86    {48,     54000,  1, {858,   720, 16,  62, 525,  480,  9,  6, 119, SCANTYPE_PROGRESSIVE} },
87    {48,     54054,  1, {858,   720, 16,  62, 525,  480,  9,  6, 120, SCANTYPE_PROGRESSIVE} },
88
89    {52,    108000,  1, {864,   720, 12,  64, 625,  576,  5,  5, 200, SCANTYPE_PROGRESSIVE} },
90
91    {56,    108000,  1, {858,   720, 16,  62, 525,  480,  9,  6, 239, SCANTYPE_PROGRESSIVE} },
92    {56,    108108,  1, {858,   720, 16,  62, 525,  480,  9,  6, 240, SCANTYPE_PROGRESSIVE} },
93
94 };
95
96 OUT_FMT dvi_timing_table[OUT_DVI_END] = {
97
98
99
100         {0,     25170,  0, { 800,  640, 16,  96, 525,  480, 10,  2,  60, SCANTYPE_PROGRESSIVE}  },
101         {0,     31500,  0, { 832,  640, 24,  40, 520,  480,  9,  3,  72, SCANTYPE_PROGRESSIVE}  },
102     {0,     31500,  0, { 800,  640, 16,  96, 525,  480, 11,  2,  75, SCANTYPE_PROGRESSIVE}      },
103
104         {0,     28322,  0, { 900,  720, 15, 108, 449,  400, 11,  2,  70, SCANTYPE_PROGRESSIVE}  },
105
106         {0,             38100,  0, {1088,  800, 32, 128, 619,  600,  1,  4,  56, SCANTYPE_PROGRESSIVE}  },
107
108
109         {0,             40000,  0, {1056,  800, 40, 128, 628,  600,  1,  4,  60, SCANTYPE_PROGRESSIVE}  },
110         {0,             50000,  0, {1040,  800, 56, 120, 666,  600, 37,  6,  72, SCANTYPE_PROGRESSIVE}  },
111         {0,             49500,  0, {1056,  800, 16,  80, 624,  600,  1,  2,  75, SCANTYPE_PROGRESSIVE}  },
112
113         {0,             65000,  0, {1344, 1024, 24,     136, 806,  768,  3,      6,  60, SCANTYPE_PROGRESSIVE}  },
114     {0,         75000,  0, {1328, 1024, 24,     136, 806,  768,  3,      6,  70, SCANTYPE_PROGRESSIVE}  },
115         {0,             78750,  0, {1312, 1024, 16,      96, 800,  768,  1,      3,  75, SCANTYPE_PROGRESSIVE}  },
116
117         {0,             81517,  0, {1688, 1152, 48,112,1066,  864,       1,      3,  60, SCANTYPE_PROGRESSIVE}  },
118
119         {0,             83460,  0, {1680, 1280, 64,     136, 828,  720,  1,      3,  60, SCANTYPE_PROGRESSIVE}  },
120
121         {0,             83865,  0, {1680, 1280, 64,     136, 828,  800,  1,      3,  60, SCANTYPE_PROGRESSIVE}  },
122
123         {0,             100638, 0, {1688, 1280, 48,     112, 1066, 960,  1,      3,  60, SCANTYPE_PROGRESSIVE}  },
124
125         {0,             108000, 0, {1688, 1280, 48,     112, 1066, 1024, 1,      3,  60, SCANTYPE_PROGRESSIVE}  },
126         {0,             135000, 0, {1688, 1280, 16,     144, 1066, 1024, 1,      3,  75, SCANTYPE_PROGRESSIVE}  },
127
128         {0,             85543,  0, {2256, 1360,104, 184, 1087, 768,  1,  3,  60, SCANTYPE_PROGRESSIVE}  },
129         {0,             85920,  0, {2256, 1366,104, 184, 1087, 768,  1,  3,  60, SCANTYPE_PROGRESSIVE}  },
130
131         {0,             121750, 0, {1864, 1400, 88,144,1089,  1050,      3,      4,  60, SCANTYPE_PROGRESSIVE}  },
132     {0,         156000, 0, {1896, 1400,104,144,1099,  1050,      3,      4,  75, SCANTYPE_PROGRESSIVE}  },
133
134
135         {0,             88750,  0, {1600, 1440, 48,     32,      926,  900,      3,      6,  60, SCANTYPE_PROGRESSIVE}  },
136         {0,             119000, 0, {1840, 1440, 48,     32,      1080, 1050, 3,  6,  60, SCANTYPE_PROGRESSIVE}  },
137
138         {0,             117936, 0, {2256, 1600,104,     184, 1250,  900, 1,      3,  60, SCANTYPE_PROGRESSIVE}  },
139         {0,             162000, 0, {2160, 1600, 64,     192, 1250, 1200, 1,      3,  60, SCANTYPE_PROGRESSIVE}  },
140
141         {0,             147130, 0, {2256, 1680,104,     184, 1087, 1050, 1,      3,  60, SCANTYPE_PROGRESSIVE}  },
142         {0,     148500, 0, {2200, 1920, 88,  44, 1125, 1080, 4,  5, 60, SCANTYPE_PROGRESSIVE} },
143         {0,             154000, 0, {2080, 1920, 48,      32, 1235, 1200, 3,      6,  60, SCANTYPE_PROGRESSIVE}  },
144
145 };
146
147
148
149
150 OUT_FMT ch7036_crt_timing_table[OUT_CRT_END] = {
151
152
153    {100,    31500,  1, {832,   640, 32,  64,  445,  400, 1,  3,  85, SCANTYPE_PROGRESSIVE}  },
154
155    {100,    25175,  1, {800,   640,  8,  96,  525,  480, 2,  2,  60, SCANTYPE_PROGRESSIVE}  },
156    {100,    31500,  1, {832,   640, 16,  40,  520,  480, 1,  3,  72, SCANTYPE_PROGRESSIVE}  },
157    {100,    31500,  1, {840,   640, 16,  64,  500,  480, 1,  3,  75, SCANTYPE_PROGRESSIVE}  },
158    {100,    36000,  1, {832,   640, 56,  56,  509,  480, 1,  3,  85, SCANTYPE_PROGRESSIVE}  },
159
160    {100,    35500,  1, {936,   720, 36,  72,  446,  400, 1,  3,  85, SCANTYPE_PROGRESSIVE}  },
161
162
163
164    {100,    36000,  1, {1024,  800, 24,  72,  625,  600, 1,  2,  56, SCANTYPE_PROGRESSIVE}  },
165
166
167    {100,    38250,  1, {1024,  800, 32,  80,  624,  600, 3,  4,  60, SCANTYPE_PROGRESSIVE}  },
168    {100,    50000,  1, {1040,  800, 56, 120,  666,  600, 37, 6,  72, SCANTYPE_PROGRESSIVE}  },
169    {100,    49000,  1, {1040,  800, 40,  80,  629,  600, 3,  4,  75, SCANTYPE_PROGRESSIVE}  },
170    {100,    56750,  1, {1056,  800, 48,  80,  633,  600, 3,  4,  85, SCANTYPE_PROGRESSIVE}  },
171
172
173    {100,    65000,  1, {1344, 1024, 24, 136,  806,  768, 3,  6,  60, SCANTYPE_PROGRESSIVE}  },
174    {100,    75000,  1, {1328, 1024, 24, 136,  806,  768, 3,  6,  70, SCANTYPE_PROGRESSIVE}  },
175    {100,    78750,  1, {1312, 1024, 16,  96,  800,  768, 1,  3,  75, SCANTYPE_PROGRESSIVE}  },
176
177    {100,    94500,  1, {1376, 1024, 48,  96,  808,  768, 1,  3,  85, SCANTYPE_PROGRESSIVE}  },
178
179
180    {100,   108000,  1, {1600, 1152, 64, 128,  900,  864, 1,  2,  75, SCANTYPE_PROGRESSIVE}  },
181
182
183    {100,    79500,  1, {1664, 1280, 64, 128,  798,  768, 3,  7,  60, SCANTYPE_PROGRESSIVE}  },
184    {100,   102250,  1, {1696, 1280, 80, 128,  805,  768, 3,  7,  75, SCANTYPE_PROGRESSIVE}  },
185    {100,   117500,  1, {1712, 1280, 80, 136,  809,  768, 3,  7,  85, SCANTYPE_PROGRESSIVE}  },
186
187
188    {100,   108000,  1, {1800, 1280, 96, 112, 1000,  960, 1,  3,  60, SCANTYPE_PROGRESSIVE}  },
189    {100,   148500,  1, {1728, 1280, 64, 160, 1011,  960, 1,  3,  85, SCANTYPE_PROGRESSIVE}  },
190
191
192    {100,   108000,  1, {1688, 1280, 48, 112, 1066, 1024, 1,  3,  60, SCANTYPE_PROGRESSIVE}  },
193    {100,   135000,  1, {1688, 1280, 16, 144, 1066, 1024, 1,  3,  75, SCANTYPE_PROGRESSIVE}  },
194    {100,   157500,  1, {1728, 1280, 64, 160, 1072, 1024, 1,  3,  85, SCANTYPE_PROGRESSIVE}  },
195
196
197    {100,    85500,      1, {1792, 1360, 64, 112,  795,  768, 3,  6,  60, SCANTYPE_PROGRESSIVE}  },
198
199
200    {100,   121750,      1, {1864, 1400, 88,144,1089,  1050,      3,      4,  60, SCANTYPE_PROGRESSIVE}  },
201    {100,   156000,      1, {1896, 1400,104,144,1099,  1050,      3,      4,  75, SCANTYPE_PROGRESSIVE}  },
202
203
204    {100,        88750,  1, {1600, 1440, 48,     32,      926,  900,      3,      6,  60, SCANTYPE_PROGRESSIVE}  },
205
206
207    {100,   119000,      1, {1840, 1440, 48,     32,      1080, 1050, 3,  6,  60, SCANTYPE_PROGRESSIVE}  },
208
209
210    {100,   117936,      1, {2256, 1600,104,     184, 1250,  900, 1,      3,  60, SCANTYPE_PROGRESSIVE}  },
211
212
213    {100,   162000,  1, {2160, 1600, 64, 192, 1250, 1200, 1,  3,  60, SCANTYPE_PROGRESSIVE}  },
214
215
216
217    {100,   148500, 1, {2200, 1920, 88,  44, 1125, 1080, 4,  5, 60, SCANTYPE_PROGRESSIVE} },
218
219
220
221 };
222
223
224
225
226
227 uint8 I2CRead(DEV_CONTEXT* pDevContext,uint8 index)
228 {
229
230         ch7036_device_context_t *p_ctx= pDevContext->pd_context;
231         pd_reg_t reg_list[2];
232
233         reg_list[0].reg = (i2c_reg_t)index;
234         reg_list[1].reg = PD_REG_LIST_END;
235
236         p_ctx->p_callback->read_regs(p_ctx->p_callback->callback_context, reg_list,PD_REG_DDC);
237
238         return (uint8)(reg_list[0].value);
239 }
240
241 void I2CWrite(DEV_CONTEXT* pDevContext,uint8 index, uint8 value)
242 {
243         ch7036_device_context_t *p_ctx= pDevContext->pd_context;
244         pd_reg_t reg_list[2];
245
246
247
248         reg_list[0].reg = (i2c_reg_t)index;
249         reg_list[0].value = (i2c_reg_t)value;
250
251         reg_list[1].reg = PD_REG_LIST_END;
252
253         p_ctx->p_callback->write_regs(p_ctx->p_callback->callback_context, reg_list,PD_REG_DDC);
254
255         return;
256 }
257
258
259 void I2CBlockWrite(DEV_CONTEXT* pDevContext,uint8 index, uint8* value, uint16 len)
260 {
261         ch7036_device_context_t *p_ctx= pDevContext->pd_context;
262         pd_reg_t reg_list[MAX_I2C_BLOCK_SIZE +1];
263         uint16 i=0;
264
265
266         for(i=0;i<len;i++) {
267                 reg_list[i].reg = (i2c_reg_t)index;
268                 reg_list[i].value = (i2c_reg_t)value[i];
269         }
270
271         reg_list[len].reg = PD_REG_LIST_END;
272
273         p_ctx->p_callback->write_regs(p_ctx->p_callback->callback_context, reg_list,PD_REG_DDC);
274
275         return;
276 }
277
278 ch7036_status_t ch7036_device_prepare(ch7036_device_context_t* p_ctx)
279 {
280         DEV_CONTEXT* p_ch_ctx = p_ctx->p_ch7xxx_context;
281         ch7036_status_t status = SS_SUCCESS;
282
283         PD_DEBUG("ch7036_intf: ch7036_device_prepare()\n");
284
285
286         if(!DevicePrepare(p_ch_ctx))
287         {
288                 p_ctx->last_emsg = GetLastErrorMessage();
289                 status = SS_UNSUCCESSFUL;
290         }
291
292         return status;
293 }
294
295 ch7036_status_t ch7036_device_config(ch7036_device_context_t* p_ctx)
296 {
297         DEV_CONTEXT* p_ch_ctx = p_ctx->p_ch7xxx_context;
298         ch7036_status_t status = SS_SUCCESS;
299
300         PD_DEBUG("ch7036_intf: ch7036_device_config()\n");
301
302
303         if(!DeviceConfig(p_ch_ctx))
304         {
305                 p_ctx->last_emsg = GetLastErrorMessage();
306                 status = SS_UNSUCCESSFUL;
307         }
308
309         return status;
310
311 }
312
313 ch7036_status_t ch7036_device_start(ch7036_device_context_t* p_ctx)
314 {
315
316         DEV_CONTEXT* p_ch_ctx = p_ctx->p_ch7xxx_context;
317         ch7036_status_t status = SS_SUCCESS;
318
319         PD_DEBUG("ch7036_intf: ch7036_device_start()\n");
320
321         if(!DeviceRunning(p_ch_ctx))
322         {
323                 p_ctx->last_emsg = GetLastErrorMessage();
324                 status = SS_UNSUCCESSFUL;
325         }
326
327         return status;
328
329 }
330
331 ch7036_status_t ch7036_device_set_power(ch7036_device_context_t* p_ctx, unsigned long channel)
332 {
333         DEV_CONTEXT* p_ch_ctx = p_ctx->p_ch7xxx_context;
334         ch7036_status_t status = SS_SUCCESS;
335
336         PD_DEBUG("ch7036_intf: ch7036_device_set_power()- channel [%x]\n", channel);
337
338         if(!DeviceSetPower(p_ch_ctx,channel))
339         {
340                 p_ctx->last_emsg = GetLastErrorMessage();
341                 status = SS_UNSUCCESSFUL;
342         }
343
344         return status;
345 }
346
347
348
349 ch7036_status_t ch7036_load_firmware(ch7036_device_context_t* p_ctx)
350 {
351
352         DEV_CONTEXT* p_ch_ctx = p_ctx->p_ch7xxx_context;
353
354         ch7036_status_t status = SS_UNSUCCESSFUL;
355
356         PD_DEBUG("ch7036: ch7036_load_firmware()\n");
357
358
359         if(LHFM_load_firmware(p_ch_ctx) == -1) {
360                 PD_DEBUG("ch7036_load_firmware: LHFM_load_firmware()- firmware loading FAILED...\n");
361
362         }
363         else  {
364                 PD_DEBUG("ch7036_load_firmware: LHFM_load_firmware()- firmware loading is a SUCCESS\n");
365                 status = SS_SUCCESS;
366         }
367
368
369         return status;
370
371 }
372
373
374
375
376
377
378 ch7036_status_t ch7036_get_hdvi_display_modes_supported(ch7036_device_context_t* p_ctx)
379 {
380         DEV_CONTEXT* p_ch7xxx_context = p_ctx->p_ch7xxx_context;
381         ch7036_status_t status;
382         ch7036_edid_blk_t* p_hedid = (ch7036_edid_blk_t *)p_ctx->hedid;
383
384
385         PD_DEBUG("ch7036_get_hdvi_display_modes_supported()- enter\n");
386
387         status = LHFM_get_hdmi_modeinfo(p_ch7xxx_context,p_hedid->supported_modes);
388
389         if (status == SS_SUCCESS) {
390
391                 PD_DEBUG("HDMI_Modes=%02X. Vesa_Modes=%02x\r\n", p_hedid->supported_modes[13], p_hedid->supported_modes[14]);
392
393
394         }
395         else {
396                 PD_DEBUG("ch7036_get_hdvi_display_modes_supported()-- failed!\r\n");
397                 PD_DEBUG("status: [%s]\n",status == SS_FIRMWARE_TIMEOUT?"timeout!":"firmware_error!");
398
399
400         }
401
402         return status;
403 }
404
405
406
407 ch7036_status_t ch7036_read_edid(ch7036_device_context_t* p_ctx, uint32 channel)
408 {
409
410         DEV_CONTEXT* p_ch7xxx_context = p_ctx->p_ch7xxx_context;
411         OUTPUT_INFO* pOutput_Info = p_ch7xxx_context->pOutput_Info;
412         ch7036_status_t status = SS_UNSUCCESSFUL;
413
414 \r#ifdef T_CH7036_EDID_DUMP
415         uint8 ebn;
416         int i;
417 #endif
418
419         ch7036_edid_blk_t* p_hedid = (ch7036_edid_blk_t *)p_ctx->hedid;
420         ch7036_edid_blk_t* p_cedid = (ch7036_edid_blk_t *)p_ctx->cedid;
421
422
423         unsigned char* hedidblk = p_hedid->edidblk;
424         unsigned char* cedidblk = p_cedid->edidblk;
425
426
427
428         switch (channel) {
429
430                 case CHANNEL_LVDS_HDMI:
431                 case CHANNEL_HDMI:
432
433
434                         status = LHFM_get_edid(p_ch7xxx_context,hedidblk, &(p_hedid->ebn), CH7036_HDMI_DDC);
435
436                         if(status == SS_SUCCESS) {
437
438                                 PD_DEBUG("ch7036_read_edid()-hdmi-dvi hpd status- attached, hdmi-dvi edid read is a SUCCESS\n");
439                                 PD_DEBUG("ch7036_read_edid()- number of blocks read [%x]\n", p_hedid->ebn);
440
441                                 p_hedid->is_edid = 1;
442                                 if(p_hedid->ebn == 1)
443                                         pOutput_Info->hdmi_fmt.is_dvi_mode =1;
444
445                                 else
446                                         pOutput_Info->hdmi_fmt.is_dvi_mode =0;
447
448
449
450 #ifdef T_CH7036_EDID_DUMP
451
452                                 if (p_hedid->ebn <= MAX_EDID_BLOCKS) {
453                                         for (i=0; i<p_hedid->ebn; i++)
454                                                 ch7036_dump("HDMI-DVI EDID Data", 128, &hedidblk[i*128]);
455
456                                 }
457
458 #endif
459
460                         }
461
462                         else {
463                                 p_hedid->is_edid = 0;
464
465                                 status = SS_UNSUCCESSFUL;
466
467                         }
468
469                         break;
470
471                 case CHANNEL_LVDS_VGA:
472                 case CHANNEL_VGA:
473
474                         I2CWrite(p_ch7xxx_context,0x03, 0x01);
475                         I2CWrite(p_ch7xxx_context,0x0F, I2CRead(p_ch7xxx_context,0x0F) & 0x7F);
476                         pd_usleep(200);
477
478                         status = LHFM_get_edid(p_ch7xxx_context,cedidblk, &(p_cedid->ebn), CH7036_VGA_DDC);
479                         if (status== SS_SUCCESS) {
480                                 p_cedid->is_edid =1;
481                                 PD_DEBUG("ch7036_read_edid()- crt hpd status- attached, crt edid read is a SUCCESS\n");
482                                 PD_DEBUG("ch7036_read_edid()- number of blocks read [%x]\n", p_cedid->ebn);
483
484 #ifdef T_CH7036_EDID_DUMP
485                                 if (p_cedid->ebn <= MAX_EDID_BLOCKS)
486                                         for (i=0; i<p_cedid->ebn; i++)
487                                                 ch7036_dump("VGA EDID Data", 128, &cedidblk[i*128]);
488
489
490 #endif
491
492                         }
493                         else {
494                                 p_cedid->is_edid =0;
495
496                                 status = SS_UNSUCCESSFUL;
497                         }
498
499
500                         break;
501
502                 default:
503                         break;
504
505
506         }
507
508
509         return status;
510 }
511
512 ch7036_status_t ch7036_get_hdmi_hpd(ch7036_device_context_t* p_ctx, uint8 *hpd)
513 {
514         DEV_CONTEXT* p_ch7xxx_context = p_ctx->p_ch7xxx_context;
515         ch7036_status_t status= SS_SUCCESS;
516         unsigned char reg, reg_hpdpw;
517
518         I2CWrite(p_ch7xxx_context,0x03, 0x03);
519         reg = I2CRead(p_ch7xxx_context,0x25);
520
521         I2CWrite(p_ch7xxx_context,0x03, 0x04);
522         reg_hpdpw = I2CRead(p_ch7xxx_context,0x51);
523
524 #ifdef T_CONFIG_PLB
525         if(!(reg & 0x10) && (reg_hpdpw & 0x80) ){
526                 reg= 0x10;
527         }
528 #endif
529
530         switch (reg & 0x10) {
531                 case 0x10:
532                         if(p_ctx->hpd & CH7036HPD_HDVI_ATTACHED)
533                                 *hpd = 0x01;
534                         else
535                                 *hpd = 0x81;
536                         break;
537                 case 0x00:
538                         if(p_ctx->hpd & CH7036HPD_HDVI_ATTACHED)
539                                 *hpd = 0x80;
540                         else
541                                 *hpd = 0x00;
542                         break;
543         }
544
545
546         PD_DEBUG("ch7036: ch7036_get_hdmi_hpd- exit...*hpd [0x%x]\n",*hpd);
547
548         return status;
549
550 }
551 ch7036_status_t ch7036_get_attached_device(ch7036_device_context_t* p_ctx)
552 {
553         DEV_CONTEXT* p_ch7xxx_context = p_ctx->p_ch7xxx_context;
554         OUTPUT_INFO* pOutput_Info = p_ch7xxx_context->pOutput_Info;
555         uint8 reg;
556         ch7036_status_t status = SS_SUCCESS;
557         ch7036_status_t status_hdmi, status_crt;
558
559         ch7036_edid_blk_t * p_hedid = (ch7036_edid_blk_t *)(p_ctx->hedid);
560
561         uint8 hpd = 0;
562
563
564
565         I2CWrite(p_ch7xxx_context,0x03, 0x04);
566         reg = I2CRead(p_ch7xxx_context,0x52);
567
568         reg = reg & 0xEF;
569         I2CWrite(p_ch7xxx_context,0x52, reg);
570
571
572         I2CWrite(p_ch7xxx_context,0x03, 0x0);
573         reg = I2CRead(p_ch7xxx_context,0x07);
574
575         reg = reg & 0x70;
576         I2CWrite(p_ch7xxx_context,0x07, reg);
577
578         I2CWrite(p_ch7xxx_context,0x03, 0x01);
579         reg = I2CRead(p_ch7xxx_context,0x0F);
580
581         reg = reg & 0x7F;
582         I2CWrite(p_ch7xxx_context,0x0F, reg);
583
584         I2CWrite(p_ch7xxx_context,0x0E, I2CRead(p_ch7xxx_context,0x0E) & 0x7F);
585
586         PD_DEBUG("ch7036_get_attached_device()- enter- p_ctx->hpd= [0x%x]\n", p_ctx->hpd);
587
588         status_hdmi = ch7036_get_hdmi_hpd(p_ctx,&hpd);
589         LHFM_enable_crt_hpd(p_ch7xxx_context);
590         status_crt = LHFM_get_crt_hpd(p_ch7xxx_context);
591
592         PD_DEBUG("ch7036_get_attached_device()- enter- pOutput_Info->channel = [0x%x]\n", pOutput_Info->channel);
593
594         if(p_ctx->man_sel_out==1) { //manual selection
595
596
597                 if( (status_crt == SS_SUCCESS) || ( (hpd & 0x01)== 1 ) ) {
598
599                         switch (pOutput_Info->channel) {
600                                 case CHANNEL_LVDS_DVI:
601                                 case CHANNEL_DVI:
602                                 case CHANNEL_LVDS_HDMI:
603                                 case CHANNEL_HDMI:
604
605
606                                         if( (status_crt == SS_SUCCESS) && ( (hpd & 0x01)== 0 ) ) {
607
608                                                 p_ctx->hpd = 0x16; //bit 4=1 to indicate SS_DISPLAY_CHOICE_NOT_ALLOWED,  check edid and parse it
609                                                 status = SS_DISPLAY_CHOICE_NOT_ALLOWED;
610
611                                         }
612                                         else {
613
614                                                 if (!p_ctx->init_done || ((p_ctx->prev_outchannel & pOutput_Info->channel) & 0x02) != 0x02 )
615                                                         p_ctx->hpd = 0x60;
616                                                 else
617                                                         p_ctx->hpd = ( ((p_ctx->prev_outchannel & pOutput_Info->channel) & 0x02) == 0x02)?0xA0:0x60;
618
619                                                 status = SS_SUCCESS;
620                                         }
621
622                                         break;
623
624                                 case CHANNEL_LVDS_VGA:
625                                 case CHANNEL_VGA:
626
627
628                                         if((status_crt != SS_SUCCESS) && ((hpd & 0x01)==1 ) ) {
629
630                                                 if(!p_ctx->init_done) {
631                                                         p_ctx->hpd = 0x06;
632                                                         status = SS_SUCCESS;
633
634                                                 }else {
635                                                         p_ctx->hpd = (hpd & 0x80)?0x70:0x30;
636                                                         status = SS_DISPLAY_CHOICE_NOT_ALLOWED;
637                                                 }
638
639                                         }
640                                         else {
641
642                                                 if ( (!p_ctx->init_done) || ((p_ctx->prev_outchannel & pOutput_Info->channel) & 0x04) != 0x04 )//at init, need to read edid, and parse it
643                                                         p_ctx->hpd = 0x06;
644                                                 else {
645                                                         p_ctx->hpd = ( ((p_ctx->prev_outchannel & pOutput_Info->channel) & 0x04) == 0x04)?0x0A:0x06;
646
647                                                 }
648
649                                                 status = SS_SUCCESS;
650                                         }
651
652                                         break;
653                         } //switch
654
655                         if(status == SS_DISPLAY_CHOICE_NOT_ALLOWED)
656                                 PD_DEBUG("ch7036_get_attached_device()- manual selection- display choice is not allowed...\n");
657
658                 }
659                 else {
660
661                         if (!p_ctx->init_done) {
662                                 p_ctx->hpd = 0x06;
663                                 status = SS_SUCCESS;
664
665                         }else {
666
667                                 PD_DEBUG("ch7036_get_attached_device()- manual selection- none is connected- not allowed...\n");
668
669                                 status = SS_DISPLAY_CHOICE_NOT_ALLOWED;
670                                 p_ctx->hpd = 0x50;
671
672                         }
673
674
675                 }
676
677                 PD_DEBUG("ch7036_get_attached_device()- manual selection- exit- p_ctx->hpd= [0x%x]\n", p_ctx->hpd);
678                 PD_DEBUG("ch7036_get_attached_device()- exit- pOutput_Info->channel = [0x%x]\n", pOutput_Info->channel);
679
680                 I2CWrite(p_ch7xxx_context,0x03, 0x03);
681                 reg = I2CRead(p_ch7xxx_context,0x25);
682
683                 PD_DEBUG("ch7036_get_attached_device()- manual selection- exit...HPD_MCU [0x%x]\n",reg);
684
685                 return status;
686         }
687
688         //auto detection
689
690         if(status_hdmi == SS_SUCCESS) {
691
692                         if( hpd == 0x81 ) {
693                                 if(p_ctx->hpd & CH7036HPD_HDVI_ATTACHED)  {
694
695                                         p_ctx->hpd = (p_ctx->hpd  & 0x9F) & ((~CH7036HPD_HDVI_STATUS_CHANGED) | CH7036HPD_HDVI_ATTACHED);
696
697                                         ch7036_get_hdvi_display_modes_supported(p_ctx);
698
699                                         if (
700                                                 ((pOutput_Info->hdmi_fmt.is_dvi_mode== 0) && (p_hedid->supported_modes[13] == 0) )||
701                                                 ((pOutput_Info->hdmi_fmt.is_dvi_mode== 1) && (p_hedid->supported_modes[13] > 0))
702                                         ) {
703
704                                                 p_ctx->hpd = (p_ctx->hpd  & 0x9F) | (CH7036HPD_HDVI_STATUS_CHANGED | CH7036HPD_HDVI_ATTACHED);
705                                                 PD_DEBUG("ch7036_get_attached_device()- hdvi HPD status changed [HDMI<->DVI] since last query and it's HIGH\n");
706
707                                         }
708                                         else
709                                                 PD_DEBUG("ch7036_get_attached_device()- hdvi HPD status has not changed since last query and it's HIGH\n");
710                                 }
711                                 else {
712
713
714                                         p_ctx->hpd = (p_ctx->hpd  & 0x9F) | (CH7036HPD_HDVI_STATUS_CHANGED | CH7036HPD_HDVI_ATTACHED);
715                                         PD_DEBUG("ch7036_get_attached_device()- hdvi HPD status changed since last query and it's HIGH\n");
716                                 }
717                         }
718                         else if (hpd ==0x80) {
719                                 if( (p_ctx->hpd & CH7036HPD_HDVI_ATTACHED) ==0 )  {
720
721                                         p_ctx->hpd = (p_ctx->hpd  & 0x9F) & ((~ CH7036HPD_HDVI_STATUS_CHANGED) & (~CH7036HPD_HDVI_ATTACHED)) ;
722                                         PD_DEBUG("ch7036_get_attached_device()- hdvi HPD status not changed since last query and it's LOW\n");
723                                 }
724                                 else {
725
726                                         p_ctx->hpd = (p_ctx->hpd  & 0x9F) | (CH7036HPD_HDVI_STATUS_CHANGED & (~CH7036HPD_HDVI_ATTACHED)) ;
727                                         PD_DEBUG("ch7036_get_attached_device()- hdvi HPD status changed since last query and it's LOW\n");
728                                 }
729
730                         }
731                         else if (hpd == 0x01) {
732
733                                 p_ctx->hpd = (p_ctx->hpd  & 0x9F) & ((~CH7036HPD_HDVI_STATUS_CHANGED) | CH7036HPD_HDVI_ATTACHED);
734                                 PD_DEBUG("ch7036_get_attached_device()- hdvi HPD status has not changed since last query and it's HIGH\n");
735                         }
736                         else {
737
738                                 p_ctx->hpd &= 0x9F;
739                                 PD_DEBUG("ch7036_get_attached_device()- hdvi HPD status has not changed since last query and it's LOW\n");
740                         }
741
742
743
744                         PD_DEBUG("ch7036: ch7036_get_attached_device()- SUCCESS- hdmi hpd [0x%x]\n", hpd);
745
746         }
747         else {
748
749
750                 if ( (!p_ctx->init_done) &&  (hpd == 0x86) )  {
751
752                         p_ctx->hpd |= CH7036HPD_HDVI_ATTACHED;
753
754                 }
755
756                 else {
757                         p_ctx->hpd &= ~CH7036HPD_HDVI_ATTACHED;
758
759                 }
760
761         }
762
763         if(status_crt == SS_SUCCESS) {
764
765                 if( (p_ctx->hpd & CH7036HPD_CRT_ATTACHED )== CH7036HPD_CRT_ATTACHED)
766                         p_ctx->hpd = (p_ctx->hpd  & 0xF9) & ((~CH7036HPD_CRT_STATUS_CHANGED)  | CH7036HPD_CRT_ATTACHED);
767
768                 else
769                         p_ctx->hpd = ((p_ctx->hpd  & 0xF9) | ( CH7036HPD_CRT_STATUS_CHANGED | CH7036HPD_CRT_ATTACHED));
770
771         }
772         else  {
773
774                 if( (p_ctx->hpd & CH7036HPD_CRT_ATTACHED ) == 0 ) {
775                         p_ctx->hpd &= 0xF9;
776
777                         if( (p_ctx->hpd & CH7036HPD_HDVI_ATTACHED)== 0  )
778                                 p_ctx->hpd |= 0x06;
779
780                 }
781                 else  {
782
783                         if ( (p_ctx->hpd & CH7036HPD_HDVI_ATTACHED) ==0 )
784                                 p_ctx->hpd &= 0xFB;
785                         else
786                                 p_ctx->hpd = (p_ctx->hpd & 0xF9) |  CH7036HPD_CRT_STATUS_CHANGED;
787                 }
788
789         }
790
791         PD_DEBUG("ch7036_get_attached_device()- auto detection - exit- p_ctx->hpd= [0x%x]\n", p_ctx->hpd);
792         return SS_SUCCESS;
793 }
794
795
796 void ch7036_reset(ch7036_device_context_t* p_ctx)
797 {
798         DEV_CONTEXT* p_ch_ctx = p_ctx->p_ch7xxx_context;
799
800         ch7036_reset_mcu(p_ch_ctx);
801         ch7036_reset_datapath(p_ch_ctx);
802
803         return;
804 }
805
806 void ch7036_reset_datapath(DEV_CONTEXT* p_ch_ctx)
807 {
808
809         PD_DEBUG("ch7036: ch7036_reset_datapath()-enter\n");
810     I2CWrite(p_ch_ctx,0x03, 0x04);
811         I2CWrite(p_ch_ctx,0x52, 0x2E);
812
813         pd_usleep(50);
814         I2CWrite(p_ch_ctx,0x52, 0x2F);
815
816         return;
817 }
818
819 void ch7036_reset_mcu(DEV_CONTEXT* p_ch_ctx)
820 {
821
822         PD_DEBUG("ch7036: ch7036_reset_mcu()-enter\n");
823
824     I2CWrite(p_ch_ctx,0x03, 0x04);
825         I2CWrite(p_ch_ctx,0x52, 0x2B);
826
827         pd_usleep(50);
828         I2CWrite(p_ch_ctx,0x52, 0x2F);
829
830
831         PD_DEBUG("ch7036: ch7036_reset_mcu()-exit-\n");
832         return;
833 }
834
835
836
837
838
839 void ch7036_set_input_timing_info(ch7036_device_context_t *p_ctx, INPUT_INFO* pInput_Info)
840 {
841         DEV_CONTEXT* p_ch7xxx_context = p_ctx->p_ch7xxx_context;
842         OUTPUT_INFO* pOutput_Info = p_ch7xxx_context->pOutput_Info;
843
844         pd_timing_t * p_current_mode = &(p_ctx->native_dtd);
845         uint8 audio_id = AUDIO_SPDIF;
846         PD_DEBUG("ch7036_intf: ch7036_set_input_timing_info()-\n");
847
848
849         if (p_ctx->init_done) {
850
851
852                 pInput_Info->timing.ht = p_current_mode->htotal+1;
853
854                 pInput_Info->timing.ha = p_current_mode->width;
855                 pInput_Info->timing.ho = p_current_mode->hsync_start - p_current_mode->hblank_start;
856                 pInput_Info->timing.hw = p_current_mode->hsync_end - p_current_mode->hsync_start;
857                 pInput_Info->timing.vt = p_current_mode->vtotal+1;
858
859                 pInput_Info->timing.va = p_current_mode->height;
860                 pInput_Info->timing.vo = p_current_mode->vsync_start - p_current_mode->vblank_start;
861                 pInput_Info->timing.vw = p_current_mode->vsync_end - p_current_mode->vsync_start;
862
863
864                 pInput_Info->rx_clk_khz = p_current_mode->dclk;
865
866
867                 pInput_Info->hs_pol = ((uint8)(((p_current_mode)->mode_info_flags & PD_HSYNC_HIGH) >> 24 ))?1:0;
868                 pInput_Info->vs_pol = ((uint8)(((p_current_mode)->mode_info_flags & PD_VSYNC_HIGH) >> 24))?1:0;
869
870         }
871
872
873
874
875
876         pInput_Info->pixel_fmt = ((lvds_context_t *)p_ctx->internal_lvds)->panel_depth == 18?PIXEL_FMT_18BIT:3;
877
878
879         pInput_Info->data_ch_pol = POL_NO_INV;
880
881
882         pInput_Info->data_ch_invert = POL_NO_INV;
883
884
885
886
887
888         pInput_Info->de_pol = POL_HIGH;
889
890
891
892
893
894         if(pOutput_Info->channel & CHANNEL_HDMI)
895                 ch7036_set_audio_type(pInput_Info, audio_id);
896
897 }
898
899 void ch7036_set_output_timing_info(ch7036_device_context_t *p_ctx, OUTPUT_INFO* pOutput_Info)
900 {
901
902
903         PD_DEBUG("ch7036: ch7036_set_output_timing_info()\n");
904
905
906         PD_DEBUG("ch7036_set_output_timing_info()- output channel from pd context[%u]\n",pOutput_Info->channel);
907
908
909         pOutput_Info->lvds_fmt.channel_swap = LVDS_CHANNEL_SWAP_DEF;
910         pOutput_Info->lvds_fmt.channel_pol = (POL_LOW << 4) | (POL_LOW << 3) | (POL_LOW << 2) | (POL_LOW << 1) | (POL_LOW << 0);
911         pOutput_Info->lvds_fmt.pixel_fmt = p_ctx->dither_select;
912
913
914
915         pOutput_Info->hdmi_fmt.channel_swap = 0;
916         pOutput_Info->hdmi_fmt.data_pol_invert = POL_NO_INV;
917         pOutput_Info->hdmi_fmt.protect_enable = 0;
918
919
920
921
922         if (pOutput_Info->channel & CHANNEL_HDMI)
923         {
924
925                 if(!(pOutput_Info->hdmi_fmt.is_dvi_mode))
926                 {
927                         PD_DEBUG("ch7036_set_output_timing_info- hdmi mode index is [0x%x]\n",p_ctx->hdmi_mode_index);
928                         pOutput_Info->hdmi_fmt.format_index = (uint8)hdmi_timing_table[p_ctx->hdmi_mode_index].fmt_index;
929                         pOutput_Info->hdmi_fmt.aspect_ratio = (uint8)hdmi_timing_table[p_ctx->hdmi_mode_index].aspect;
930
931                         pOutput_Info->timing.ht = hdmi_timing_table[p_ctx->hdmi_mode_index].timing.ht;
932                         pOutput_Info->timing.ha = hdmi_timing_table[p_ctx->hdmi_mode_index].timing.ha;
933                         pOutput_Info->timing.ho = hdmi_timing_table[p_ctx->hdmi_mode_index].timing.ho;
934                         pOutput_Info->timing.hw = hdmi_timing_table[p_ctx->hdmi_mode_index].timing.hw;
935                         pOutput_Info->timing.vt = hdmi_timing_table[p_ctx->hdmi_mode_index].timing.vt;
936                         pOutput_Info->timing.va = hdmi_timing_table[p_ctx->hdmi_mode_index].timing.va;
937                         pOutput_Info->timing.vo = hdmi_timing_table[p_ctx->hdmi_mode_index].timing.vo;
938                         pOutput_Info->timing.vw = hdmi_timing_table[p_ctx->hdmi_mode_index].timing.vw;
939                         pOutput_Info->uclk_khz = hdmi_timing_table[p_ctx->hdmi_mode_index].clk_freq;
940                 }
941                 else
942                 {
943                         pOutput_Info->hdmi_fmt.format_index = (uint8)dvi_timing_table[p_ctx->dvi_mode_index].fmt_index;
944                         pOutput_Info->hdmi_fmt.aspect_ratio = (uint8)dvi_timing_table[p_ctx->dvi_mode_index].aspect;
945
946                         pOutput_Info->timing.ht = dvi_timing_table[p_ctx->dvi_mode_index].timing.ht;
947                         pOutput_Info->timing.ha = dvi_timing_table[p_ctx->dvi_mode_index].timing.ha;
948                         pOutput_Info->timing.ho = dvi_timing_table[p_ctx->dvi_mode_index].timing.ho;
949                         pOutput_Info->timing.hw = dvi_timing_table[p_ctx->dvi_mode_index].timing.hw;
950                         pOutput_Info->timing.vt = dvi_timing_table[p_ctx->dvi_mode_index].timing.vt;
951                         pOutput_Info->timing.va = dvi_timing_table[p_ctx->dvi_mode_index].timing.va;
952                         pOutput_Info->timing.vo = dvi_timing_table[p_ctx->dvi_mode_index].timing.vo;
953                         pOutput_Info->timing.vw = dvi_timing_table[p_ctx->dvi_mode_index].timing.vw;
954                         pOutput_Info->uclk_khz = dvi_timing_table[p_ctx->dvi_mode_index].clk_freq;
955
956                 }
957
958
959
960         } else if((pOutput_Info->channel & CHANNEL_VGA) && ((pOutput_Info->channel & CHANNEL_HDMI)==0x00) )
961         {
962
963
964
965                 PD_DEBUG("ch7036_set_output_timing_info- crt mode index is [0x%x]\n",p_ctx->crt_mode_index);
966                 pOutput_Info->timing.ht = ch7036_crt_timing_table[p_ctx->crt_mode_index].timing.ht;
967                 pOutput_Info->timing.ha = ch7036_crt_timing_table[p_ctx->crt_mode_index].timing.ha;
968                 pOutput_Info->timing.ho = ch7036_crt_timing_table[p_ctx->crt_mode_index].timing.ho;
969                 pOutput_Info->timing.hw = ch7036_crt_timing_table[p_ctx->crt_mode_index].timing.hw;
970                 pOutput_Info->timing.vt = ch7036_crt_timing_table[p_ctx->crt_mode_index].timing.vt;
971                 pOutput_Info->timing.va = ch7036_crt_timing_table[p_ctx->crt_mode_index].timing.va;
972                 pOutput_Info->timing.vo = ch7036_crt_timing_table[p_ctx->crt_mode_index].timing.vo;
973                 pOutput_Info->timing.vw = ch7036_crt_timing_table[p_ctx->crt_mode_index].timing.vw;
974                 pOutput_Info->uclk_khz = ch7036_crt_timing_table[p_ctx->crt_mode_index].clk_freq;
975
976
977         } else
978                 ;
979
980
981         if(pOutput_Info->channel & CHANNEL_HDMI)
982                 ch7036_set_hdmi_sync_polarity(pOutput_Info);
983
984         if(pOutput_Info->channel & CHANNEL_HDMI || pOutput_Info->channel & CHANNEL_VGA) {
985
986                 ch7036_set_rotate (pOutput_Info);
987                 ch7036_set_hflip (pOutput_Info);
988                 ch7036_set_vflip (pOutput_Info);
989         }
990 }
991
992 void ch7036_set_prefer_timing_info(ch7036_device_context_t *p_ctx, PREFER_INFO* pPrefer_Info)
993 {
994
995
996
997
998         PD_DEBUG("ch7036_intf: ch7036_set_prefer_timing_info()\n");
999
1000
1001         if (!p_ctx->init_done) {
1002
1003         pPrefer_Info->mclk_khz = 166000;
1004         pPrefer_Info->uclkod_sel = 1;
1005         pPrefer_Info->dat16_32b = 0;
1006         pPrefer_Info->true24 = 0;
1007         pPrefer_Info->true_com = 0;
1008         pPrefer_Info->lvds_out_hs_tolerance = HS_TOLERANCE_LEVEL0;
1009         pPrefer_Info->lvds_out_reset_bit_sel = RST_BIT_VSYNC;
1010         pPrefer_Info->dither_filter_enable = DITHER_ENABLE;
1011
1012         pPrefer_Info->hscale_ratio_gate = 130;
1013         pPrefer_Info->reset=0;
1014         pPrefer_Info->vga_enable=0;
1015
1016         pPrefer_Info->text_enhancement = DEFAULT_TEXT_ENHANCE;
1017         pPrefer_Info->pll_ref_dly = DEF_PLL_REF_DLY;
1018         pPrefer_Info->pll_ref_fbdly = DEF_PLL_REF_FBDLY;
1019         pPrefer_Info->lvds_txdrv_ctrl = DEF_LVDS_TXDRV_CTRL;
1020
1021         pPrefer_Info->eye_bgtrim=0;
1022         pPrefer_Info->eye_dacg=0;
1023         pPrefer_Info->eye_dri_demp=0;
1024         pPrefer_Info->eye_dri_pll_cp=0;
1025         pPrefer_Info->eye_dri_damp=0;
1026         pPrefer_Info->eye_dri_pll_rlf=0;
1027         pPrefer_Info->eye_rdac=0;
1028
1029         }
1030
1031         pPrefer_Info->scale_line_adjust = 0;
1032
1033
1034
1035 }
1036
1037
1038 ch7036_status_t ch7036_parse_standard_edid(ch7036_device_context_t* p_ctx, uint32 channel)
1039 {
1040         uint8 i, index = 0;
1041
1042         ch7036_edid_blk_t* p_edid = (ch7036_edid_blk_t *)p_ctx->cedid;
1043         unsigned char* p_edidblk = p_edid->edidblk;
1044
1045
1046         OUT_FMT* p_table = ch7036_crt_timing_table;
1047         TIMING* p_timing;
1048
1049         unsigned char j=0;
1050
1051
1052
1053
1054
1055         established_timings_t *p_etiming_I = p_edid->etiming_I;
1056         established_timings_t *p_etiming_II = p_edid->etiming_II;
1057
1058
1059
1060         standard_timings_t      *stiming = p_edid->stiming;
1061         ch7036_attr_table_index_t* p_modes =  p_edid->modes;
1062
1063         unsigned long idx = 2;
1064
1065
1066         PD_DEBUG("ch7036_parse_stardard_edid() channel [0x%x] - enter...\n", channel);
1067
1068
1069         if(channel == CHANNEL_LVDS_HDMI) {
1070
1071                 p_edid = (ch7036_edid_blk_t *)p_ctx->hedid;
1072                 p_edidblk = p_edid->edidblk;
1073                 p_etiming_I = p_edid->etiming_I;
1074                 p_etiming_II = p_edid->etiming_II;
1075
1076                 stiming = p_edid->stiming;
1077                 p_modes =  p_edid->modes;
1078
1079
1080                 if (p_edid->ebn > 1) {
1081                         idx = 1;
1082                         p_table = hdmi_timing_table;
1083                 }
1084                 else {
1085                         idx = 0;
1086                         p_table = dvi_timing_table;
1087                         channel = 7;
1088                 }
1089
1090
1091         }
1092
1093
1094         while (index < MAX_ATTR_LIST_SIZE)
1095                 p_modes[index++] = FALSE;
1096
1097
1098         if (p_edidblk[EDID_EXTENSION_FLAG] == 0x00 ) {
1099
1100
1101                 ch7036_parse_standard_timing(p_edid,0);
1102
1103
1104                 ch7036_parse_established_timing(p_ctx, p_edid);
1105
1106
1107
1108                 ch7036_parse_detailed_descriptor_blocks(p_ctx, p_edid);
1109
1110
1111
1112                 for(i=0; i<8;i++) {
1113
1114
1115                         index=0;
1116                         while (index < MAX_ATTR_LIST_SIZE ) {
1117                                 if(p_modes[index]== TRUE) {
1118                                         index++;
1119                                         continue;
1120                                 }
1121                                 p_timing = &(p_table[index].timing);
1122
1123                                 if ( (p_edid->dtblk[j]).data_tag & 0x00FFFFFF ) {
1124                                         OUT_FMT* p_dtd = &((p_edid->dtblk[j]).dtiming);
1125
1126                                         if( (p_dtd->timing.ha == p_timing->ha) && (p_dtd->timing.va == p_timing->va) && (p_dtd->timing.hz >= p_timing->hz) ) {
1127                                                 p_modes[index] = TRUE;
1128                                                 j= j> 3?3:j+1;
1129
1130                                                 PD_DEBUG("ch7036_parse_standard_edid()- detailed timing mode supported- index [%d] name [%s]...\n",index,ch7036_get_mode_name(channel,index) );
1131
1132                                         }
1133
1134                                 }
1135
1136
1137                                 if( (stiming[i].ha == p_timing->ha) && (stiming[i].va == p_timing->va) && (stiming[i].refresh_rate >= p_timing->hz) ) {
1138                                         p_modes[index] = TRUE;
1139                                         PD_DEBUG("ch7036_parse_standard_edid()- std_timing mode supported- index [%d] name [%s]...\n",index,ch7036_get_mode_name(channel,index) );
1140                                 }
1141
1142                                 index++;
1143
1144                         }
1145
1146                 }
1147
1148
1149                 for(i=0;i<4;i++) {
1150                         if ( (p_edid->dtblk[i]).data_tag == 0xFA000000) {
1151                                 ;
1152                                 continue;
1153                         }
1154                 }
1155
1156
1157
1158                 for(i=0; i<8;i++) {
1159
1160
1161
1162                         if( (p_etiming_I[i].is_supported == TRUE) && (p_etiming_I[i].index[idx] != OUT_CRT_END) ) {
1163                                 p_modes[p_etiming_I[i].index[idx]] = TRUE;
1164                                 PD_DEBUG("ch7036_parse_standard_edid()- et1 mode supported- index [%d] name [%s]...\n",p_etiming_I[i].index[idx],p_etiming_I[i].mode_name);
1165                                 continue;
1166
1167                         }
1168
1169
1170                         if( (i==7) && (channel ==7) && (p_etiming_I[i].is_supported == TRUE) ) {
1171                                 p_modes[p_etiming_I[i].index[idx]] = TRUE;
1172                                 PD_DEBUG("ch7036_parse_standard_edid()- et1 mode supported- index [%d] name [%s]...\n",p_etiming_I[i].index[idx],p_etiming_I[i].mode_name);
1173                         }
1174
1175
1176                 }
1177
1178                 for(i=0; i<8;i++) {
1179
1180                         if( (p_etiming_II[i].is_supported == TRUE) && (p_etiming_II[i].index[idx] != OUT_CRT_END) ) {
1181                                 p_modes[p_etiming_II[i].index[idx]] = TRUE;
1182                                 PD_DEBUG("ch7036_parse_standard_edid()- et2 mode supported- index [%d] name [%s]...\n",p_etiming_II[i].index[idx],p_etiming_II[i].mode_name);
1183                                 continue;
1184
1185                         }
1186
1187                 }
1188
1189
1190
1191         }
1192         else {
1193                 PD_DEBUG("ch7036_parse_standard_edid()- vga/dvi has more than one 128 byte block\n");
1194         }
1195
1196
1197         PD_DEBUG("ch7036_parse_stardard_edid()-channel [0x%x] - exit...\n", channel);
1198
1199         return SS_SUCCESS;
1200
1201 }
1202
1203 void ch7036_parse_detailed_descriptor_blocks(ch7036_device_context_t* p_ctx, ch7036_edid_blk_t* p_edid)
1204 {
1205         unsigned long *monitor_descriptor;
1206         unsigned char* p_ebuf, *p_st;
1207         unsigned char* p_edidblk = p_edid->edidblk;
1208         unsigned char i;
1209         OUT_FMT* p_dt;
1210
1211
1212         p_ebuf = &(p_edidblk[EDID_DETAILED_TIMING_DESCRIPTION_1]);
1213
1214         PD_DEBUG("parse_detailed_descriptor_blocks()- enter...\n");
1215
1216         for(i=0;i<4;i++) {
1217
1218                 monitor_descriptor = (unsigned long *) p_ebuf;
1219
1220                 if((*monitor_descriptor) & 0x00FFFFFF ) {
1221
1222
1223                         p_dt = &(p_edid->dtblk[i].dtiming);
1224                         ch7036_parse_detailed_timing(p_dt, p_ebuf);
1225
1226                 }
1227
1228                 else {
1229
1230                         p_st = p_ebuf;
1231                         p_st +=5;
1232
1233                         switch (*monitor_descriptor) {
1234                                 case 0xFA000000:
1235                                         ch7036_parse_standard_timing(p_edid,p_st);
1236                                         break;
1237
1238                                 case 0xFD000000:
1239                                         (p_edid->rtiming).vrate_min = *p_st;
1240                                         (p_edid->rtiming).vrate_max = *(p_st+1);
1241                                         (p_edid->rtiming).hrate_min = *(p_st+2);
1242                                         (p_edid->rtiming).hrate_max = *(p_st+3);
1243                                         (p_edid->rtiming).pclk_max = (unsigned long)(*(p_st+4))*10000L;
1244
1245
1246                                         break;
1247
1248                                 case 0xFC000000:
1249                                 case 0xFF000000:
1250                                 default:
1251                                         break;
1252                         }
1253                 }
1254
1255                 (p_edid->dtblk[i]).data_tag = *monitor_descriptor;
1256
1257                 p_ebuf += 18;
1258         }
1259
1260         return;
1261 }
1262
1263 void ch7036_parse_detailed_timing(OUT_FMT *p_dt, unsigned char* p_ebuf)
1264 {
1265
1266         unsigned short blanking;
1267
1268         PD_DEBUG("ch7036_parse_detailed_descriptor_timing()- enter...\n");
1269
1270
1271         p_dt->clk_freq = ((uint32)(p_ebuf[1]<<8) | p_ebuf[0]) * 10;
1272
1273         p_dt->timing.ha = ((uint16)(p_ebuf[4] & 0xF0) << 4) | p_ebuf[2];
1274
1275         PD_DEBUG("ch7036_parse_detailed_timing() byte 3 [%x] byte 5 [%x]\n",p_ebuf[2],p_ebuf[4]);
1276
1277         blanking = ((uint16)(p_ebuf[4] & 0x0F) << 8) | p_ebuf[3];
1278         p_dt->timing.ht = p_dt->timing.ha + blanking;
1279
1280         p_dt->timing.va = ((uint16)(p_ebuf[7] & 0xF0) << 4) | p_ebuf[5];
1281
1282         PD_DEBUG("ch7036_parse_detailed_timing() byte 6 [%x] byte 8 [%x]\n",p_ebuf[5],p_ebuf[7]);
1283
1284         blanking = ((uint16)(p_ebuf[7] & 0x0F) << 8) | p_ebuf[6];
1285         p_dt->timing.vt = p_dt->timing.va + blanking;
1286
1287         PD_DEBUG("ch7036_parse_detailed_timing()- pclk [%d] Khz ha [%d] va [%d] ht [%d] vt [%d]\n",p_dt->clk_freq,p_dt->timing.ha,p_dt->timing.va,p_dt->timing.ht,p_dt->timing.vt);
1288
1289         p_dt->timing.hz =       (((p_dt->clk_freq / p_dt->timing.ht) + 1 ) * 1000) / p_dt->timing.vt;
1290
1291         p_dt->timing.stype = (p_ebuf[17] & 0x80)?0:1;
1292
1293         PD_DEBUG("ch7036_parse_detailed_timing()- refresh [%d] scantype [%d]\n",
1294                 p_dt->timing.hz,p_dt->timing.stype);
1295
1296         return;
1297 }
1298
1299
1300
1301 void ch7036_parse_standard_timing(ch7036_edid_blk_t* p_edid, unsigned char* p_addtional_st)
1302 {
1303         standard_timings_t *stiming = p_edid->stiming;
1304         unsigned char i, max=8;
1305
1306         unsigned char* p_edidblk = &(p_edid->edidblk[EDID_STANDARD_TIMINGS]);
1307
1308
1309         PD_DEBUG("ch7036_parse_standard_timing()- enter\n");
1310
1311         if(p_addtional_st) {
1312                 p_edidblk = p_addtional_st;
1313                 stiming = p_edid->stiming_x;
1314                 max = 6;
1315         }
1316
1317         for(i = 0; i < max; stiming++,i++) {
1318
1319
1320                 if( (*p_edidblk) == 0x01 &&  *(p_edidblk+1) == 0x01)
1321                         continue;
1322
1323                 stiming->ha = ((*p_edidblk) + 31) << 3 ;
1324
1325                 stiming->refresh_rate = (*(p_edidblk + 1) & 0x3F) + 60;
1326
1327                 switch(*(p_edidblk +1) >> 6) {
1328
1329                    case 0:
1330                            stiming->va =  (stiming->ha *10) >> 4;
1331                            break;
1332                    case 1:
1333                            stiming->va =  (stiming->ha *3) >> 2;
1334                            break;
1335                    case 2:
1336                            stiming->va =  (stiming->ha << 2) / 5;
1337                            break;
1338                    case 3:
1339                            stiming->va =  (stiming->ha* 9) >>4;
1340                            break;
1341                    default:
1342                            break;
1343                 }
1344
1345                 p_edidblk +=2;
1346
1347                 PD_DEBUG("ch7036_parse_standard_timing()- ha [%d] va [%d] refresh [%d]\n",stiming->ha,stiming->va,stiming->refresh_rate);
1348
1349         }
1350
1351         return;
1352 }
1353
1354
1355
1356
1357 void ch7036_parse_established_timing(ch7036_device_context_t* p_ctx, ch7036_edid_blk_t* p_edid)
1358 {
1359
1360         unsigned char* p_edidblk = p_edid->edidblk;
1361
1362
1363
1364         established_timings_t *p_etiming_I = p_edid->etiming_I;
1365         established_timings_t *p_etiming_II = p_edid->etiming_II;
1366         established_timings_t *p_etiming_man = p_edid->etiming_man;
1367
1368         unsigned char i=0;
1369         unsigned char et1, et2;
1370
1371         PD_DEBUG("ch7036_parse_established_timing()- enter...\n");
1372
1373         et1 = p_edidblk[EDID_ESTABLISHED_TIMINGS_1];
1374         et2 = p_edidblk[EDID_ESTABLISHED_TIMINGS_2];
1375
1376
1377
1378         for(i=0; i<8;i++) {
1379           p_etiming_I[i].is_supported = FALSE;
1380           p_etiming_II[i].is_supported = FALSE;
1381         }
1382
1383
1384
1385         p_etiming_man->is_supported = FALSE;
1386
1387
1388         for(i=0;i<8;i++) {
1389
1390
1391
1392                 if(et1 & 0x01) {
1393                         p_etiming_I[i].is_supported = TRUE;
1394
1395                 }
1396
1397
1398                 if(et2 & 0x01) {
1399                         p_etiming_II[i].is_supported = TRUE;
1400
1401                 }
1402
1403                 et1 >>=  1;
1404                 et2 >>=  1;
1405
1406         }
1407
1408
1409
1410         if (p_edidblk[EDID_MANUFACTURERS_RESERVED_TIMINGS] & 0x80) {
1411
1412                 p_etiming_man->is_supported = TRUE;
1413
1414         }
1415
1416
1417         return;
1418
1419 }
1420
1421
1422 ch7036_status_t ch7036_parse_cea_edid(ch7036_device_context_t* p_ctx)
1423 {
1424         uint8 tag, blk_size =0;
1425         uint8 index = 0;
1426
1427         uint16 count;
1428
1429         uint8*  p_buff;
1430
1431
1432         ch7036_edid_blk_t* p_hedid = (ch7036_edid_blk_t *)p_ctx->hedid;
1433
1434         unsigned char* p_edidblk = p_hedid->edidblk;
1435         ch7036_attr_table_index_t* p_modes =  p_hedid->modes;
1436
1437
1438         PD_DEBUG("ch7036_parse_cea_edid()- enter...\n");
1439
1440         while (index < MAX_ATTR_LIST_SIZE )
1441                 p_modes[index++] = FALSE;
1442
1443
1444         if(p_edidblk[EDID_CEA_DETAILED_TIMING_DATA_OFFSET] == 0 ||  p_edidblk[EDID_CEA_DETAILED_TIMING_DATA_OFFSET] > 124) {
1445                 PD_DEBUG("ch7036_parse_cea_edid()- invalid data block size [%d]\n", p_edidblk[EDID_CEA_DETAILED_TIMING_DATA_OFFSET]);
1446                 return SS_UNSUCCESSFUL;
1447         }
1448
1449
1450
1451         PD_DEBUG("ch7036_parse_cea_edid()- CEA revision [0x%x]...\n",p_edidblk[EDID_CEA_REVISION]);
1452
1453         if(p_edidblk[EDID_CEA_TAG] == 0x02 && p_edidblk[EDID_CEA_REVISION] == 0x03)
1454         {
1455
1456                 p_buff = &(p_edidblk[EDID_CEA_DATA_BLOCK]);
1457
1458
1459
1460                 count=4 ;
1461                 for(; count < p_edidblk[EDID_CEA_DETAILED_TIMING_DATA_OFFSET]; p_buff += blk_size) {
1462
1463                         blk_size = (*p_buff) & 0x1F;
1464                         tag = (*p_buff) & 0xE0;
1465
1466                         PD_DEBUG("ch7036_parse_cea_edid()- data type [0x%x] block_size [%d]\n", tag, blk_size);
1467
1468                         p_buff++;
1469                         switch (tag) {
1470
1471                                 case 0x20:
1472
1473                                         break;
1474
1475                                 case 0x40:
1476                                         ch7036_parse_cea_video_data_block(blk_size, p_buff, p_hedid);
1477                                         break;
1478
1479                                 case 0x60:
1480                                         break;
1481
1482                                 case 0x80:
1483                                         break;
1484
1485                                 default:
1486                                         break;
1487
1488                         }
1489
1490                         count += (blk_size + 1);
1491
1492
1493                 }
1494
1495         }
1496
1497
1498         PD_DEBUG("ch7036_parse_cea_edid()- exit...\n");
1499
1500         return SS_SUCCESS;
1501
1502
1503 }
1504
1505
1506 void ch7036_parse_cea_video_data_block(uint8 blk_size, uint8* p_buff, ch7036_edid_blk_t* p_edid)
1507 {
1508         uint8 i, index;
1509
1510         ch7036_attr_table_index_t* p_modes =  p_edid->modes;
1511
1512         for(i=1; i <= blk_size; i++, p_buff++ ) {
1513
1514                         index=0;
1515
1516                         PD_DEBUG("ch7036_parse_cea_video_data_block()- HDMI display video code [0x%x]\n",(*p_buff) & 0x7F);
1517
1518                         while (index < OUT_HDMI_END) {
1519
1520
1521                                 if( p_modes[index] == TRUE  ) {
1522                                         index++;
1523                                         continue;
1524                                 }
1525
1526
1527                                 if( ((*p_buff) & 0x7F) == hdmi_timing_table[index].fmt_index  ) {
1528
1529                                         p_modes[index] = TRUE;
1530                                         PD_DEBUG("ch7036_parse_cea_video_data_block()- mode supported: global table index [%d] name [%s]...\n",index, ch7036_get_mode_name(CHANNEL_LVDS_HDMI,index) );
1531
1532                                         if( hdmi_timing_table[index-1].fmt_index == hdmi_timing_table[index].fmt_index) {
1533
1534                                                 break;
1535                                         }
1536
1537                                 }
1538
1539                                 index++;
1540
1541                         }
1542         }
1543
1544         return;
1545 }
1546
1547
1548 ch7036_status_t ch7036_parse_edid(ch7036_device_context_t* p_ctx)
1549 {
1550
1551
1552         DEV_CONTEXT* p_ch7xxx_context = p_ctx->p_ch7xxx_context;
1553         OUTPUT_INFO* pOutput_Info = p_ch7xxx_context->pOutput_Info;
1554
1555         ch7036_edid_blk_t* p_hedid = (ch7036_edid_blk_t *)p_ctx->hedid;
1556         ch7036_edid_blk_t* p_cedid = (ch7036_edid_blk_t *)p_ctx->cedid;
1557
1558         unsigned char* p_edidblk=0;
1559         ch7036_attr_table_index_t* p_modes = 0;
1560         pd_attr_t  *p_attr = NULL ;
1561         int RESET =1;
1562
1563         PD_DEBUG("ch7036_parse_edid()- enter...\n");
1564
1565
1566         //hpd checking schemes
1567         if(p_ctx->hpd == 0)
1568                 return SS_SUCCESS;
1569
1570
1571         if (
1572                 ( (pOutput_Info->channel & 0x02) &&  (p_ctx->hpd & 0x80) )||
1573                 ( (pOutput_Info->channel & 0x04) &&  (p_ctx->hpd & 0x08) )
1574                 )
1575                 //parsing is already done
1576                 return SS_SUCCESS;
1577
1578
1579         switch (pOutput_Info->channel) {
1580                 case CHANNEL_LVDS_HDMI:
1581                 case CHANNEL_HDMI:
1582                         if(p_hedid->is_edid) {
1583                                 p_edidblk = p_hedid->edidblk;
1584
1585                                 p_hedid->is_preferred_timing = (p_edidblk[EDID_FEATURE_SUPPORT] >> 1) & 0x1;
1586
1587
1588                                 if(pOutput_Info->hdmi_fmt.is_dvi_mode == 0) {
1589                                         p_attr = pd_get_attr(p_ctx->p_ch7036_attr_table, p_ctx->ch7036_num_attrs, PD_ATTR_ID_HDMI_OUT_MODE, 0);
1590                                         ch7036_parse_cea_edid(p_ctx);
1591                                 }
1592                                 else {
1593                                         p_attr = pd_get_attr(p_ctx->p_ch7036_attr_table, p_ctx->ch7036_num_attrs, PD_ATTR_ID_DVI_OUT_MODE, 0);
1594                                         ch7036_parse_standard_edid(p_ctx, CHANNEL_LVDS_HDMI);
1595                                 }
1596
1597
1598
1599                                 p_ctx->hpd |= 0x80; //don't parse again next time
1600
1601                         }
1602                         else {
1603
1604                                 PD_DEBUG("ch7036_parse_edid()- hdmi edid read failed or never done...use default...\n");
1605                                 ch7036_set_edid_display_supported_attr( (void *)p_ctx->p_ch7036_attr_table, p_ctx->ch7036_num_attrs,p_ctx->downscaled,p_hedid->modes,RESET);
1606                                 p_ctx->hpd &= 0x7F; //allow to enter parsing block again
1607
1608                         }
1609
1610                         p_modes = p_hedid->modes;
1611
1612                         break;
1613
1614                 case CHANNEL_LVDS_VGA:
1615                 case CHANNEL_VGA:
1616                         if(p_cedid->is_edid) {
1617                                 p_edidblk = p_cedid->edidblk;
1618
1619                                 p_cedid->is_preferred_timing = (p_edidblk[EDID_FEATURE_SUPPORT] >> 1) & 0x1;
1620                                 p_attr = pd_get_attr(p_ctx->p_ch7036_attr_table, p_ctx->ch7036_num_attrs, PD_ATTR_ID_CRT_OUT_MODE, 0);
1621
1622                                 ch7036_parse_standard_edid(p_ctx, CHANNEL_LVDS_VGA);
1623                                 p_ctx->hpd |= 0x08;
1624                         }
1625                         else {
1626                                 PD_DEBUG("ch7036_parse_edid()- vga edid read failed or never done...use default...\n");
1627                                 ch7036_set_edid_display_supported_attr( (void *)p_ctx->p_ch7036_attr_table, p_ctx->ch7036_num_attrs,p_ctx->downscaled,p_cedid->modes,RESET);
1628                                 p_ctx->hpd &= 0x7F; //allow to enter parsing block again
1629                         }
1630                         p_modes = p_cedid->modes;
1631
1632                         break;
1633                 default:
1634                         //there is no separate DVI display channel, or LVDS edid reading at this time
1635                         //DVI display option should already be mapped to HDMI channel
1636                         p_edidblk = 0;
1637
1638         }
1639
1640         if(p_edidblk) {
1641
1642                 ch7036_set_edid_display_supported_attr( (void *)p_attr,0,p_ctx->downscaled,p_modes,0);
1643
1644         }
1645
1646         PD_DEBUG("ch7036_parse_edid()- exit...\n");
1647
1648         return SS_SUCCESS;
1649 }
1650
1651
1652 void ch7036_alter_display_table(int all, void *p_table,unsigned char* p_modes, void* val,unsigned long* p_invis,unsigned char is_invis,unsigned char is_6x4)
1653 {
1654         pd_attr_t  *p_attr;
1655         unsigned long i,j;
1656
1657
1658         PD_DEBUG("ch7036_alter_display_table()-enter...\n");
1659
1660         if(all) {
1661                 unsigned long* num_attrs = (unsigned long *)val;
1662                 for(i=0;i<3;i++) { //all 3 tables: hdmi, dvi, vga
1663
1664                         p_attr = pd_get_attr((pd_attr_t *)p_table, *num_attrs, PD_ATTR_ID_HDMI_OUT_MODE+i, 0);
1665                         if(is_6x4)
1666                                 p_attr++;
1667                         else
1668                                 p_attr= p_attr + ch7036_invis_6x4_modes_table_size[i] + 1; //1 is to skip header
1669
1670
1671                         for(j=0; j < *p_invis;j++) {
1672                                 if(is_invis)
1673                                         p_attr->flags  |= PD_ATTR_FLAG_USER_INVISIBLE;
1674                                 else
1675                                         p_attr->flags  &= ~PD_ATTR_FLAG_USER_INVISIBLE;
1676
1677
1678                                 p_attr++;
1679                         }
1680                         p_invis++; //now, grab dvi, then vga table size
1681
1682
1683                 }
1684
1685         }
1686         else {
1687                 unsigned long id= 0,k;
1688                 p_attr = (pd_attr_t *)p_table;
1689                 id = p_attr->id;
1690
1691                 if(is_6x4) {
1692                         p_attr++;
1693                         j=0;
1694                 }
1695                 else {
1696                         p_attr= p_attr + ch7036_invis_6x4_modes_table_size[id - PD_ATTR_ID_HDMI_OUT_MODE] + 1; //point to the first 7x4 entry
1697                         j= ch7036_invis_6x4_modes_table_size[id - PD_ATTR_ID_HDMI_OUT_MODE];
1698                 }
1699                 p_invis = p_invis + (id - PD_ATTR_ID_HDMI_OUT_MODE);
1700                 k= *p_invis + j;
1701
1702                 for(; j < k;j++) {
1703                         if(is_invis) {
1704                                 p_attr->flags  |= PD_ATTR_FLAG_USER_INVISIBLE;
1705                                 p_modes[j]=FALSE;
1706                         }
1707
1708                         p_attr++;
1709                 }
1710
1711         }
1712 }
1713
1714
1715 ch7036_status_t ch7036_set_edid_display_supported_attr(void *p_table, unsigned long num_attrs, unsigned char* p_downscaled, unsigned char* p_modes, int is_reset)
1716 {
1717
1718         pd_list_attr_t *p_hdr = (pd_list_attr_t *)p_table;
1719         pd_attr_t *p_entry = (pd_attr_t *)p_table;
1720
1721         uint8 i=0;
1722
1723 #ifdef T_SHOW_EDID_DISPLAY_ATTR
1724         pd_list_entry_attr_t *list_entry;
1725 #endif
1726
1727         PD_DEBUG("ch7036_set_edid_display_supported_attr()-enter... is_reset status = [%d]\n", is_reset);
1728
1729         if(is_reset) {
1730                 while (i < MAX_ATTR_LIST_SIZE ) {
1731                         p_modes[i++] = TRUE;
1732                 }
1733
1734
1735
1736                 //special handling for 1080i/p @ 59Hz
1737                 p_entry = pd_get_attr((pd_attr_t *)p_table, num_attrs, PD_ATTR_ID_HDMI_OUT_MODE, 0);
1738                 p_entry++;
1739                 p_entry = p_entry + OUT_HDMI_1920x1080I_59;
1740                 p_entry->flags  |= PD_ATTR_FLAG_USER_INVISIBLE;
1741                 p_entry += 2;
1742                 p_entry->flags  |= PD_ATTR_FLAG_USER_INVISIBLE;
1743
1744         }
1745         else {
1746
1747                 PD_DEBUG("ch7036_set_edid_display_supported_attr()-start to build edid display mode list...\n");
1748
1749                 p_entry++;
1750
1751                 for (i = 0; i < p_hdr->num_entries ; ++i,++p_entry) {
1752                         if(
1753                                 (p_modes[i] == FALSE) ||
1754                                 //1080 i/p @ 59 Hz
1755                                 ((p_hdr->id == PD_ATTR_ID_HDMI_OUT_MODE) && (i == OUT_HDMI_1920x1080I_59 || i== OUT_HDMI_1920x1080P_59) ) ){
1756
1757                                 p_entry->flags  |= PD_ATTR_FLAG_USER_INVISIBLE;
1758                                 continue;
1759                         }
1760
1761
1762                         p_entry->flags  &= ~PD_ATTR_FLAG_USER_INVISIBLE;
1763
1764                 }
1765
1766
1767         }
1768
1769         //special handling for 8x6,7x4,6x4-
1770         ch7036_alter_display_table(is_reset,p_table,p_modes,(void *)&num_attrs,ch7036_invis_6x4_modes_table_size,*p_downscaled,1);
1771         p_downscaled++;
1772         ch7036_alter_display_table(is_reset,p_table,p_modes,(void *)&num_attrs,ch7036_invis_8x6_7x4_table_size,*p_downscaled,0);
1773
1774 #ifdef T_SHOW_EDID_DISPLAY_ATTR
1775
1776         list_entry = (pd_list_entry_attr_t *)(p_table);
1777
1778         for (i = 0,++list_entry; i < p_hdr->num_entries; ++i, ++list_entry)
1779                 PD_DEBUG("ch7036 : ch7036_set_edid_display_supported_attr : \n"
1780                                   "list entry[%hhu]=%s, id=%lu, "
1781                                           "value=%lu, flags=0x%x \n",
1782                                           i, list_entry->name, list_entry->id,
1783                                           list_entry->value, (unsigned char)list_entry->flags);
1784 #endif
1785
1786
1787         return SS_SUCCESS;
1788 }
1789
1790
1791 uint8 * ch7036_get_mode_name(uint32 channel, uint8 index)
1792 {
1793         uint8* str = "Name String Is Not Yet Converted";
1794
1795         switch (channel) {
1796
1797                 case CHANNEL_LVDS_HDMI:
1798                         switch (index) {
1799                                 case OUT_HDMI_640x480P_59:
1800                                         return ("OUT_HDMI_640x480P_59");
1801                                 case OUT_HDMI_640x480P_60:
1802                                         return ("OUT_HDMI_640x480P_60");
1803                                 case OUT_HDMI_720x480P_59:
1804                                         return ("OUT_HDMI_720x480P_59");
1805                                 case OUT_HDMI_720x480P_60:
1806                                         return ("OUT_HDMI_720x480P_60");
1807                                 case OUT_HDMI_1280x720P_59:
1808                                         return ("OUT_HDMI_1280x720P_59");
1809                                 case OUT_HDMI_1280x720P_60:
1810                                         return ("OUT_HDMI_1280x720P_60");
1811                                 case OUT_HDMI_1920x1080I_59:
1812                                         return ("OUT_HDMI_1920x1080I_59");
1813                                 case OUT_HDMI_1920x1080I_60:
1814                                         return ("OUT_HDMI_1920x1080I_60");
1815                                 case OUT_HDMI_1920x1080P_59:
1816                                         return ("OUT_HDMI_1920x1080P_59");
1817                                 case OUT_HDMI_1920x1080P_60:
1818                                         return ("OUT_HDMI_1920x1080P_60");
1819
1820
1821                         }
1822                         break;
1823
1824                 case CHANNEL_LVDS_VGA:
1825
1826                         switch (index) {
1827
1828                                 case OUT_CRT_640x400_85:
1829                                         return ("OUT_CRT_640x400_85");
1830
1831                                 case OUT_CRT_640x480_60:
1832                                         return ("OUT_CRT_640x480_60");
1833                                 case OUT_CRT_640x480_72:
1834                                         return ("OUT_CRT_640x480_72");
1835                                 case OUT_CRT_640x480_75:
1836                                         return ("OUT_CRT_640x480_75");
1837                                 case OUT_CRT_640x480_85:
1838                                         return ("OUT_CRT_640x480_85");
1839
1840                                 case OUT_CRT_720x400_85:
1841                                         return ("OUT_CRT_720x400_85");
1842
1843                                 case OUT_CRT_800x600_56:
1844                                         return ("OUT_CRT_800x600_56");
1845                                 case OUT_CRT_800x600_60:
1846                                         return ("OUT_CRT_800x600_60");
1847                                 case OUT_CRT_800x600_72:
1848                                         return ("OUT_CRT_800x600_72");
1849                                 case OUT_CRT_800x600_75:
1850                                         return ("OUT_CRT_800x600_75");
1851
1852                                 case OUT_CRT_800x600_85:
1853                                         return ("OUT_CRT_800x600_85");
1854
1855                                 case OUT_CRT_1024x768_60:
1856                                         return ("OUT_CRT_1024x768_60");
1857                                 case OUT_CRT_1024x768_70:
1858                                         return ("OUT_CRT_1024x768_70");
1859                                 case OUT_CRT_1024x768_75:
1860                                         return ("OUT_CRT_1024x768_75");
1861                                 case OUT_CRT_1024x768_85:
1862                                         return ("OUT_CRT_1024x768_85");
1863
1864                                 case OUT_CRT_1152x864_75:
1865                                         return ("OUT_CRT_1152x864_75");
1866
1867                                 case OUT_CRT_1280x768_60:
1868                                         return ("OUT_CRT_1280x768_60");
1869                                 case OUT_CRT_1280x768_75:
1870                                         return ("OUT_CRT_1280x768_75");
1871                                 case OUT_CRT_1280x768_85:
1872                                         return ("OUT_CRT_1280x768_85");
1873
1874                                 case OUT_CRT_1280x960_60:
1875                                         return ("OUT_CRT_1280x960_60");
1876                                 case OUT_CRT_1280x960_85:
1877                                         return ("OUT_CRT_1280x960_85");
1878
1879                                 case OUT_CRT_1280x1024_60:
1880                                         return ("OUT_CRT_1280x1024_60");
1881                                 case OUT_CRT_1280x1024_75:
1882                                         return ("OUT_CRT_1280x1024_75");
1883                                 case OUT_CRT_1280x1024_85:
1884                                         return ("OUT_CRT_1280x1024_85");
1885
1886                                 case OUT_CRT_1360x768_60:
1887                                         return ("OUT_CRT_1360x768_60");
1888
1889                                 case OUT_CRT_1400x1050_60:
1890                                         return ("OUT_CRT_1400x1050_60");
1891                                 case OUT_CRT_1400x1050_75:
1892                                         return ("OUT_CRT_1400x1050_75");
1893
1894                                 case OUT_CRT_1440x900_60:
1895                                         return ("OUT_CRT_1440x900_60");
1896
1897                                 case OUT_CRT_1440x1050_60:
1898                                         return ("OUT_CRT_1440x1050_60");
1899
1900                                 case OUT_CRT_1600x900_60:
1901                                         return ("OUT_CRT_1600x900_60");
1902
1903                                 case OUT_CRT_1600x1200_60:
1904                                         return ("OUT_CRT_1600x1200_60");
1905
1906                                 case OUT_CRT_1920x1080_60:
1907                                         return ("OUT_CRT_1920x1080_60");
1908
1909                         }
1910                         break;
1911
1912                 default:
1913                         switch (index) {
1914                                 case OUT_DVI_640x480_60:
1915                                         return ("OUT_DVI_640x480_60");
1916                                 case OUT_DVI_640x480_72:
1917                                         return ("OUT_DVI_640x480_72");
1918
1919                                 case OUT_DVI_720x400_70:
1920                                         return ("OUT_DVI_720x400_70");
1921
1922                                 case OUT_DVI_800x600_56:
1923                                         return ("OUT_DVI_800x600_56");
1924                                 case OUT_DVI_800x600_60:
1925                                         return ("OUT_DVI_800x600_60");
1926                                 case OUT_DVI_800x600_72:
1927                                         return ("OUT_DVI_800x600_72");
1928                                 case OUT_DVI_800x600_75:
1929                                         return ("OUT_DVI_800x600_75");
1930
1931                                 case OUT_DVI_1024x768_60:
1932                                         return ("OUT_DVI_1024x768_60");
1933                                 case OUT_DVI_1024x768_70:
1934                                         return ("OUT_DVI_1024x768_70");
1935                                 case OUT_DVI_1024x768_75:
1936                                         return ("OUT_DVI_1024x768_75");
1937
1938                                 case OUT_DVI_1152x864_60:
1939                                         return ("OUT_CRT_1152x864_60");
1940
1941                                 case OUT_DVI_1280x720_60:
1942                                         return ("OUT_DVI_1280x720_60");
1943
1944                                 case OUT_DVI_1280x800_60:
1945                                         return ("OUT_DVI_1280x800_60");
1946
1947                                 case OUT_DVI_1280x960_60:
1948                                         return ("OUT_DVI_1280x960_60");
1949
1950                                 case OUT_DVI_1280x1024_60:
1951                                         return ("OUT_DVI_1280x1024_60");
1952                                 case OUT_DVI_1280x1024_75:
1953                                         return ("OUT_DVI_1280x1024_75");
1954
1955                                 case OUT_DVI_1360x768_60:
1956                                         return ("OUT_DVI_1360x768_60");
1957
1958                                 case OUT_DVI_1366x768_60:
1959                                         return ("OUT_DVI_1366x768_60");
1960
1961                                 case OUT_DVI_1400x1050_60:
1962                                         return ("OUT_DVI_1400x1050_60");
1963                                 case OUT_DVI_1400x1050_75:
1964                                         return ("OUT_DVI_1400x1050_75");
1965
1966                                 case OUT_DVI_1440x900_60:
1967                                         return ("OUT_DVI_1440x900_60");
1968
1969                                 case OUT_DVI_1440x1050_60:
1970                                         return ("OUT_DVI_1440x1050_60");
1971
1972                                 case OUT_DVI_1600x900_60:
1973                                         return ("OUT_DVI_1600x900_60");
1974
1975                                 case OUT_DVI_1600x1200_60:
1976                                         return ("OUT_DVI_1600x1200_60");
1977
1978                                 case OUT_DVI_1680x1050_60:
1979                                         return ("OUT_DVI_1680x1050_60");
1980
1981                                 case OUT_DVI_1920x1080_60:
1982                                         return ("OUT_DVI_1920x1080_60");
1983                         }
1984                         break;
1985
1986
1987         }
1988
1989
1990         return str;
1991
1992 }
1993