ark1668e_lcd.c 9.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320
  1. #include <asm-generic/gpio.h>
  2. #include <asm/arch/ark-common.h>
  3. #include "ark1668e_lcd.h"
  4. void ark_osd_en_layer(int id, unsigned int enable)
  5. {
  6. unsigned int pos;
  7. /* CLCD_CONTROL REG0x04 */
  8. switch (id)
  9. {
  10. case 0: // osd1
  11. pos = 7;
  12. break;
  13. case 1: // osd2
  14. pos = 8;
  15. break;
  16. case 2: // osd3
  17. pos = 9;
  18. break;
  19. default:
  20. return;
  21. }
  22. if (enable)
  23. rLCD_CONTROL |= (1 << pos); /* enable osd layer on LCD screen */
  24. else
  25. rLCD_CONTROL &= ~(1 << pos); /* disable osd layer on LCD screen */
  26. }
  27. void ark_disp_set_video_layer_position(int id, int x, int y)
  28. {
  29. unsigned int x_sign, y_sign;
  30. int x_start, y_start;
  31. if (x < 0) {
  32. x_sign = 1;
  33. x_start = 0 - x;
  34. } else {
  35. x_sign = 0;
  36. x_start = x;
  37. }
  38. if(y < 0) {
  39. y_sign = 1;
  40. y_start = 0 - y;
  41. } else {
  42. y_sign = 0;
  43. y_start = y;
  44. }
  45. if (id == 0) {
  46. /* CLCD_VIDEO_POSITION REG0x04c */
  47. rLCD_VIDEO1_POSITION =
  48. y_sign << 25 | // sign of y
  49. y_start << 13 | // 24-13: y of video layer
  50. x_sign << 12 | // sign of x
  51. x_start << 0; // 11-0: x of video layer
  52. } else if (id == 1) {
  53. /* CLCD_VIDEO2_POSITION REG0x334 */
  54. rLCD_VIDEO2_POSITION =
  55. y_sign << 25 | // sign of y
  56. y_start << 13 | // 24-13: y position of video2 layer
  57. x_sign << 12 | // sign of x
  58. x_start << 0; // 11-0: x position of video2 layer
  59. }
  60. }
  61. void ark_disp_set_osd_layer_position(int id, int x, int y)
  62. {
  63. unsigned int x_sign, y_sign;
  64. int x_start, y_start;
  65. if (x < 0) {
  66. x_sign = 1;
  67. x_start = 0 - x;
  68. } else {
  69. x_sign = 0;
  70. x_start = x;
  71. }
  72. if (y < 0) {
  73. y_sign = 1;
  74. y_start = 0 - y;
  75. } else {
  76. y_sign = 0;
  77. y_start = y;
  78. }
  79. switch (id)
  80. {
  81. case 0:
  82. /* CLCD_OSD1_POSITION REG0x7c */
  83. rLCD_OSD1_POSITION =
  84. y_sign << 25 | // sign of y
  85. y_start << 13 | // 24-13: y value of osd1 position on display
  86. x_sign << 12 | // sign of x
  87. x_start << 0; // 11-0: x value of osd1 position on display
  88. break;
  89. case 1:
  90. /* CLCD_OSD2_POSITION REG0x90 */
  91. rLCD_OSD2_POSITION =
  92. y_sign << 25 | // sign of y
  93. y_start << 13 | // 24-13: y value of osd2 position on display
  94. x_sign << 12 | // sign of x
  95. x_start << 0; // 11-0: x value of osd2 position on display
  96. break;
  97. case 2:
  98. /* CLCD_OSD3_POSITION REG0xa0 */
  99. rLCD_OSD3_POSITION =
  100. y_sign << 25 | // sign of y
  101. y_start << 13 | // y value of osd3 layer position on display
  102. x_sign << 12 | // sign of x
  103. x_start << 0; // x value of osd3 layer position on display
  104. break;
  105. default:
  106. break;
  107. }
  108. }
  109. void ark_display_video_image(unsigned int width,unsigned int height,unsigned int * buf,int format)
  110. {
  111. unsigned int rgb_ycbcr_bypass=0;
  112. unsigned int y_uv_order=0;
  113. if(format >= SEQ_Y_UV422)
  114. {
  115. y_uv_order = 1;
  116. format &= 1;
  117. rgb_ycbcr_bypass = 1;
  118. }
  119. else if(format <= YUV444)//rgb565
  120. {
  121. rgb_ycbcr_bypass = 1;
  122. }
  123. else
  124. {
  125. rgb_ycbcr_bypass = 0;
  126. }
  127. /*0x400322 ----> 0x420312*/
  128. rLCD_VIDEO1_CTL = (1<<22) /*0x3c*/
  129. | (y_uv_order<<21) // 0
  130. | (1<<17)
  131. | (1<<9)
  132. | (1<<8)
  133. | (1<<5)
  134. | (rgb_ycbcr_bypass<<4) // 0
  135. | (format<<0); // 2
  136. if(format == SEQ_YUV420)
  137. rLCD_VIDEO1_CTL |= (1<<11);
  138. /*swidth=3120 c30, sheight=4208 1070*/
  139. rLCD_VIDEO1_WIN_POINT = 0; /*0x15c*/
  140. rLCD_VIDEO1_WIN_SIZE = (height<<12) | (width<<0); /*0x40*/
  141. rLCD_VIDEO1_POSITION = 0; /*0x4c*/
  142. rLCD_VIDEO1_SIZE = (height<<12) | (width<<0); /*0x44*/
  143. rLCD_VIDEO1_SOURCE_SIZE = (height << 12) | (width); /*0x16c*/
  144. rLCD_VIDEO1_ADDR1 = (unsigned int )buf; /*0x054*/
  145. rLCD_VIDEO1_ADDR2 = (unsigned int )buf + width*height; /*0x058*//*c3bc280*/
  146. if(format == SEQ_YUV420)
  147. {
  148. rLCD_VIDEO1_ADDR3 = rLCD_VIDEO1_ADDR2 + width*height/4;
  149. }
  150. else
  151. {
  152. rLCD_VIDEO1_ADDR3 = rLCD_VIDEO1_ADDR2 + width*height/2; /*0x5c*/
  153. }
  154. if((format>= 4)&&(format <= 12))
  155. {
  156. rLCD_VIDEO1_COLOUR_MATRIX_REG0 = 0 ;//k0
  157. rLCD_VIDEO1_COLOUR_MATRIX_REG1 = 0 ;//k1
  158. rLCD_VIDEO1_COLOUR_MATRIX_REG2 = 0 ;//k2
  159. rLCD_VIDEO1_COLOUR_MATRIX_REG3 = 0 ;//rgb offset
  160. rLCD_VIDEO1_COLOUR_MATRIX_REG4 = 0 ;//k1
  161. rLCD_VIDEO1_COLOUR_MATRIX_REG5 = 0 ;//k2
  162. }
  163. else
  164. {
  165. rLCD_VIDEO1_COLOUR_MATRIX_REG0 = 0x01000100;//k0
  166. rLCD_VIDEO1_COLOUR_MATRIX_REG1 = 0x100167;//k1
  167. rLCD_VIDEO1_COLOUR_MATRIX_REG2 = 0xf4afa8 ;//k2
  168. rLCD_VIDEO1_COLOUR_MATRIX_REG3 = 0x12d100;//k3 offset
  169. rLCD_VIDEO1_COLOUR_MATRIX_REG4 = 0xf4d000 ;//k4--offset
  170. rLCD_VIDEO1_COLOUR_MATRIX_REG5 = 0xf69086;//rgb offset
  171. // rLCD_VIDEO_YUV2RGB0 |=(1<<24);
  172. }
  173. rLCD_CONTROL |= (1<<5);
  174. }
  175. void ark_set_osd_image(enum DISP_OSD_LAYER_ID layer_id,
  176. int format, int width, int height)
  177. {
  178. unsigned int rgb_ycbcr_bypass;
  179. unsigned int rgb_order = 0;
  180. unsigned int yuv_order = 0;
  181. unsigned int order;
  182. order = DispGetYUVOrder(format);
  183. format = DispGetYUVFormat(format);
  184. if(format == DISP_YUV422 || format == DISP_YUV444)
  185. {
  186. rgb_ycbcr_bypass = 1;
  187. yuv_order = order;
  188. }
  189. else
  190. {
  191. rgb_ycbcr_bypass = 0;
  192. rgb_order = order;
  193. }
  194. switch(layer_id)
  195. {
  196. case OSD1_LAYER:
  197. rLCD_OSD1_SIZE = (height<<12) | width;
  198. rLCD_OSD1_SOURCE_SIZE = (height << 12) | (width);
  199. rLCD_OSD1_WIN_POINT = (0 << 12) | (0);
  200. rLCD_OSD1_CTL &= ~(0x7FF<<12);
  201. rLCD_OSD1_CTL |= (yuv_order << 21) | (rgb_order << 18) |
  202. (1 << 17) | (rgb_ycbcr_bypass << 16) | (format << 12);
  203. if((format>= 4)&&(format <= 12))
  204. {
  205. rLCD_OSD1_COLOUR_MATRIX_REG0 = 0 ;//k0
  206. rLCD_OSD1_COLOUR_MATRIX_REG1 = 0 ;//k1
  207. rLCD_OSD1_COLOUR_MATRIX_REG2 = 0 ;//k2
  208. rLCD_OSD1_COLOUR_MATRIX_REG3 = 0 ;//rgb offset
  209. rLCD_OSD1_COLOUR_MATRIX_REG4 = 0 ;//k1
  210. rLCD_OSD1_COLOUR_MATRIX_REG5 = 0 ;//k2
  211. }
  212. else
  213. {
  214. rLCD_OSD1_COLOUR_MATRIX_REG0 = 0x01000100;//k0
  215. rLCD_OSD1_COLOUR_MATRIX_REG1 = 0x100167;//k1
  216. rLCD_OSD1_COLOUR_MATRIX_REG2 = 0xf4afa8 ;//k2
  217. rLCD_OSD1_COLOUR_MATRIX_REG3 = 0x12d100;//k3 offset
  218. rLCD_OSD1_COLOUR_MATRIX_REG4 = 0xf4d000 ;//k4--offset
  219. rLCD_OSD1_COLOUR_MATRIX_REG5 = 0xf69086;//rgb offset
  220. }
  221. break;
  222. case OSD2_LAYER:
  223. rLCD_OSD2_SIZE = (height<<12) | width;
  224. rLCD_OSD2_SOURCE_SIZE = (height << 12) | (width);
  225. rLCD_OSD2_WIN_POINT = (0 << 12) | (0);
  226. rLCD_OSD2_CTL &= ~(0x7FF<<12);
  227. rLCD_OSD2_CTL |= (yuv_order << 21) | (rgb_order << 18) |
  228. (1 << 17) | (rgb_ycbcr_bypass << 16) | (format << 12);
  229. if((format>= 4)&&(format <= 12))
  230. {
  231. rLCD_OSD2_COLOUR_MATRIX_REG0 = 0 ;//k0
  232. rLCD_OSD2_COLOUR_MATRIX_REG1 = 0 ;//k1
  233. rLCD_OSD2_COLOUR_MATRIX_REG2 = 0 ;//k2
  234. rLCD_OSD2_COLOUR_MATRIX_REG3 = 0 ;//rgb offset
  235. rLCD_OSD2_COLOUR_MATRIX_REG4 = 0 ;//k1
  236. rLCD_OSD2_COLOUR_MATRIX_REG5 = 0 ;//k2
  237. }
  238. else
  239. {
  240. rLCD_OSD2_COLOUR_MATRIX_REG0 = 0x01000100;//k0
  241. rLCD_OSD2_COLOUR_MATRIX_REG1 = 0x100167;//k1
  242. rLCD_OSD2_COLOUR_MATRIX_REG2 = 0xf4afa8 ;//k2
  243. rLCD_OSD2_COLOUR_MATRIX_REG3 = 0x12d100;//k3 offset
  244. rLCD_OSD2_COLOUR_MATRIX_REG4 = 0xf4d000 ;//k4--offset
  245. rLCD_OSD2_COLOUR_MATRIX_REG5 = 0xf69086;//rgb offset
  246. }
  247. break;
  248. case OSD3_LAYER:
  249. rLCD_OSD3_SIZE = (height<<12) | width;
  250. rLCD_OSD3_SOURCE_SIZE = (height << 12) | (width);
  251. rLCD_OSD3_WIN_POINT = (0 << 12) | (0);
  252. rLCD_OSD3_CTL &= ~(0x7FF<<12);
  253. rLCD_OSD3_CTL |= (yuv_order << 21) | (rgb_order << 18) |
  254. (1 << 17) | (rgb_ycbcr_bypass << 16) | (format << 12);
  255. if((format>= 4)&&(format <= 12))
  256. {
  257. rLCD_OSD3_COLOUR_MATRIX_REG0 = 0 ;//k0
  258. rLCD_OSD3_COLOUR_MATRIX_REG1 = 0 ;//k1
  259. rLCD_OSD3_COLOUR_MATRIX_REG2 = 0 ;//k2
  260. rLCD_OSD3_COLOUR_MATRIX_REG3 = 0 ;//rgb offset
  261. rLCD_OSD3_COLOUR_MATRIX_REG4 = 0 ;//k1
  262. rLCD_OSD3_COLOUR_MATRIX_REG5 = 0 ;//k2
  263. }
  264. else
  265. {
  266. rLCD_OSD3_COLOUR_MATRIX_REG0 = 0x01000100;//k0
  267. rLCD_OSD3_COLOUR_MATRIX_REG1 = 0x100167;//k1
  268. rLCD_OSD3_COLOUR_MATRIX_REG2 = 0xf4afa8 ;//k2
  269. rLCD_OSD3_COLOUR_MATRIX_REG3 = 0x12d100;//k3 offset
  270. rLCD_OSD3_COLOUR_MATRIX_REG4 = 0xf4d000 ;//k4--offset
  271. rLCD_OSD3_COLOUR_MATRIX_REG5 = 0xf69086;//rgb offset
  272. }
  273. break;
  274. default:
  275. printf("error osd layer_id %d.\n", layer_id);
  276. break;
  277. }
  278. }
  279. void ark_set_osd_addr(enum DISP_OSD_LAYER_ID layer_id, unsigned int addr)
  280. {
  281. if( layer_id == OSD1_LAYER ) rLCD_OSD1_ADDR = addr;
  282. else if ( layer_id == OSD2_LAYER ) rLCD_OSD2_ADDR = addr;
  283. else if ( layer_id == OSD3_LAYER ) rLCD_OSD3_ADDR = addr;
  284. else printf("error osd layer_id %d.\n", layer_id);
  285. }
  286. void ark_disp_wait_lcd_frame_int(void)
  287. {
  288. // wait until LCD timing point intr happens (which is VSync here)
  289. rLCD_INTERRUPT_STATUS = 0;
  290. while(!(rLCD_INTERRUPT_STATUS & 0x01));
  291. // the timing point is set at bit22-21 on CLCD_CONTROL reg
  292. }
  293. void ark_disp_wait_tvenc_frame_int(void)
  294. {
  295. // wait until TV timing point intr happens (which is VSYNC here)
  296. rLCD_INTERRUPT_STATUS = 0;
  297. while(!(rLCD_INTERRUPT_STATUS & 0x08));
  298. // NOTE: the timing point is set at bit12-11 on CLCD_CONTROL reg
  299. }