因为移植的需要,对linux内核的fb驱动进行了封装,但是由于以前没有调试过fb驱动所以还是遇到了很多未知的问题,所以先把封装好的驱动移植到uboot中进行调试,下面是为这次fb驱动移植所做的总结:
首先在这篇文章中把代码贴出来,后续文章对fb驱动移植进行总结!!!
1.uboot中frame buffer hal驱动的头文件:
复制代码
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224#ifndef __JZ_FB_HAL_H__ #define __JZ_FB_HAL_H__ /* smart lcd init code type */ enum smart_config_type { SMART_CONFIG_CMD = 0, SMART_CONFIG_DATA = 1, SMART_CONFIG_UDELAY = 2, }; struct smart_lcd_data_table { enum smart_config_type type; uint32_t value; }; struct fb_videomode { const char *name; /* optional */ u32 refresh; /* optional */ u32 xres; u32 yres; u32 pixclock; u32 left_margin; u32 right_margin; u32 upper_margin; u32 lower_margin; u32 hsync_len; u32 vsync_len; u32 sync; u32 vmode; u32 flag; }; struct jz_fb_dma_descriptor { u_long fdadr; /* Frame descriptor address register */ u_long fsadr; /* Frame source address register */ u_long fidr; /* Frame ID register */ u_long ldcmd; /* Command register */ u_long offsize; /* Stride Offsize(in word) */ u_long page_width; /* Stride Pagewidth(in word) */ u_long cmd_num; /* Command Number(for SLCD) */ u_long desc_size; /* Foreground Size */ }; /** * @next: physical address of next frame descriptor * @databuf: physical address of buffer * @id: frame ID * @cmd: DMA command and buffer length(in word) * @offsize: DMA off size, in word * @page_width: DMA page width, in word * @cpos: smart LCD mode is commands' number, other is bpp, * premulti and position of foreground 0, 1 * @desc_size: alpha and size of foreground 0, 1 */ struct jzfb_framedesc { uint32_t next; uint32_t databuf; uint32_t id; uint32_t cmd; uint32_t offsize; uint32_t page_width; uint32_t cpos; uint32_t desc_size; }; /** * @framedesc: framedesc pointer * @framedesc_phys: framedesc phys address * @databuf: phys address to databuf, 0 if not enable this fg * @bpp: foreground bpp * @x: foreground start position x * @y: foreground start position y * @w: foreground width * @h: foreground height */ struct jzfb_fg_t { struct jzfb_framedesc *framedesc; long framedesc_phys; u32 databuf; u32 bpp; u32 x; u32 y; u32 w; u32 h; u32 line_length; }; enum format_order { FORMAT_X8R8G8B8 = 1, FORMAT_X8B8G8R8, }; /* LCD controller supported display device output mode */ enum lcd_type { LCD_TYPE_GENERIC_16_BIT = 0, LCD_TYPE_GENERIC_18_BIT = 0 | (1 << 7), LCD_TYPE_GENERIC_24_BIT = 0 | (1 << 6), LCD_TYPE_SPECIAL_TFT_1 = 1, LCD_TYPE_SPECIAL_TFT_2 = 2, LCD_TYPE_SPECIAL_TFT_3 = 3, LCD_TYPE_NON_INTERLACED_TV = 4 | (1 << 26), LCD_TYPE_INTERLACED_TV = 6 | (1 << 6) | (1 << 30), LCD_TYPE_8BIT_SERIAL = 0xc, LCD_TYPE_SLCD = 0xd | (1 << 31), }; /* smart lcd interface_type */ enum smart_lcd_type { SMART_LCD_TYPE_PARALLEL, SMART_LCD_TYPE_SERIAL, }; /* smart lcd command width */ enum smart_lcd_cwidth { SMART_LCD_CWIDTH_16_BIT_ONCE = (0 << 8), SMART_LCD_CWIDTH_9_BIT_ONCE = SMART_LCD_CWIDTH_16_BIT_ONCE, SMART_LCD_CWIDTH_8_BIT_ONCE = (0x1 << 8), SMART_LCD_CWIDTH_18_BIT_ONCE = (0x2 << 8), SMART_LCD_CWIDTH_24_BIT_ONCE = (0x3 << 8), }; /* smart lcd data width */ enum smart_lcd_dwidth { SMART_LCD_DWIDTH_18_BIT_ONCE_PARALLEL_SERIAL = (0 << 10), SMART_LCD_DWIDTH_16_BIT_ONCE_PARALLEL_SERIAL = (0x1 << 10), SMART_LCD_DWIDTH_8_BIT_THIRD_TIME_PARALLEL = (0x2 << 10), SMART_LCD_DWIDTH_8_BIT_TWICE_TIME_PARALLEL = (0x3 << 10), SMART_LCD_DWIDTH_8_BIT_ONCE_PARALLEL_SERIAL = (0x4 << 10), SMART_LCD_DWIDTH_24_BIT_ONCE_PARALLEL = (0x5 << 10), SMART_LCD_DWIDTH_9_BIT_TWICE_TIME_PARALLEL = (0x7 << 10), SMART_LCD_DWIDTH_MASK = (0x7 << 10) }; /* smart lcd new data width */ enum smart_lcd_new_dwidth { SMART_LCD_NEW_DWIDTH_24_BIT = (4 << 13), SMART_LCD_NEW_DWIDTH_18_BIT = (3 << 13), SMART_LCD_NEW_DWIDTH_16_BIT = (2 << 13), SMART_LCD_NEW_DWIDTH_9_BIT = (1 << 13), SMART_LCD_NEW_DWIDTH_8_BIT = (0 << 13), }; /* smart lcd data times */ enum smart_lcd_new_dtimes { SMART_LCD_NEW_DTIMES_ONCE = (0 << 8), SMART_LCD_NEW_DTIMES_TWICE = (1 << 8), SMART_LCD_NEW_DTIMES_THICE = (2 << 8), SMART_LCD_NEW_DTIMES_MASK = (3 << 8), }; struct jzfb_hal { int base; unsigned int is_enable:1; struct fb_videomode *mode; enum lcd_type lcd_type; enum format_order fmt_order; /* frame buffer pixel format order */ unsigned int bpp; unsigned pinmd:1; unsigned booting:1; unsigned pixclk_falling_edge:1; unsigned data_enable_active_low:1; struct { enum smart_lcd_type smart_type; unsigned clkply_active_rising:1; unsigned rsply_cmd_high:1; unsigned csply_active_high:1; unsigned newcfg_6800_md:1; unsigned newcfg_fmt_conv:1; unsigned newcfg_datatx_type:1; unsigned newcfg_cmdtx_type:1; unsigned newcfg_cmd_9bit:1; size_t length_cmd; unsigned long *write_gram_cmd; unsigned bus_width; unsigned int length_data_table; /* array size of data table */ struct smart_lcd_data_table *data_table; /* init data table */ } smart_config; unsigned dither_enable:1; struct { unsigned dither_red; unsigned dither_green; unsigned dither_blue; } dither; struct { uint32_t spl; uint32_t cls; uint32_t ps; uint32_t rev; } special_tft_config; struct jzfb_framedesc *cmd_framedesc; long cmd_framedesc_phys; struct jzfb_fg_t fg0; struct jzfb_fg_t fg1; }; #define PICOS2KHZ(a) (1000000000/(a)) #define KHZ2PICOS(a) (1000000000/(a)) #define FB_MODE_IS_VGA (1 << 30) #define FB_SYNC_HOR_HIGH_ACT 1 /* horizontal sync high active */ #define FB_SYNC_VERT_HIGH_ACT 2 /* vertical sync high active */ #define FB_SYNC_EXT 4 /* external sync */ #define FB_SYNC_COMP_HIGH_ACT 8 /* composite sync high active */ #define FB_SYNC_BROADCAST 16 /* broadcast video timings */ /* vtotal = 144d/288n/576i => PAL */ /* vtotal = 121d/242n/484i => NTSC */ #define FB_SYNC_ON_GREEN 32 /* sync on green */ #define FB_VMODE_NONINTERLACED 0 /* non interlaced */ #define FB_VMODE_INTERLACED 1 /* interlaced */ #define FB_VMODE_DOUBLE 2 /* double scan */ #define FB_VMODE_ODD_FLD_FIRST 4 /* interlaced: top line first */ #define FB_VMODE_MASK 255 extern struct fb_videomode jzfb1_videomode; extern void jzfb_hal_enable(struct jzfb_hal *hal); extern void jzfb_hal_disable(struct jzfb_hal *hal); extern void jzfb_hal_refresh_pixclock_auto_adapt(struct jzfb_hal *hal); extern int jzfb_hal_set_par(struct jzfb_hal *hal); #endif /* __JZ_FB_HAL_H__ */
2.uboot中frame buffer hal的驱动代码:
复制代码
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575#include <common.h> #include <asm/io.h> #include <asm/arch/lcdc.h> #include <jz_lcd/jz_lcd_v1_2.h> #ifdef debug #undef debug #define debug printf #endif #ifdef error #undef error #define error printf #endif #define hal_reg_write(hal, addr, config) writel(config, hal->base + addr) #define hal_reg_read(hal, addr) readl(hal->base + addr) extern struct dsi_device *dsi; extern void flush_cache_all(void); extern void jzfb_mipi_config(void); extern void jzfb_dsi_video_cfg(void); extern void dump_dsi_reg(struct dsi_device *dsi); extern void dump_lcd_reg(void); void jzfb_hal_mipi_config(void) { jzfb_mipi_config(); } void jzfb_hal_dsi_video_cfg(void) { jzfb_dsi_video_cfg(); } int jzfb_hal_get_controller_bpp(unsigned int bpp) { switch (bpp) { case 18: case 24: return 32; case 15: return 16; default: return bpp; } } static void inline jzfb_hal_enable_frame_end_irq(struct jzfb_hal *hal) { unsigned long reg; reg = hal_reg_read(hal, LCDC_CTRL); if ( reg & LCDC_CTRL_EOFM ) { return; } /* clear previous EOF flag */ reg = hal_reg_read(hal, LCDC_STATE); hal_reg_write(hal, LCDC_STATE, reg & ~LCDC_STATE_EOF); /* enable end of frame interrupt */ reg = hal_reg_read(hal, LCDC_CTRL); hal_reg_write(hal, LCDC_CTRL, reg | LCDC_CTRL_EOFM); return ; } static void inline jzfb_hal_disable_frame_end_irq(struct jzfb_hal *hal) { unsigned long reg; reg = hal_reg_read(hal, LCDC_CTRL); if ( reg & LCDC_CTRL_EOFM ) { hal_reg_write(hal, LCDC_CTRL, reg & ~LCDC_CTRL_EOFM); } return ; } void jzfb_hal_refresh_pixclock_auto_adapt(struct jzfb_hal *hal) { struct fb_videomode *mode; uint16_t hds, vds; uint16_t hde, vde; uint16_t ht, vt; unsigned long rate; if (hal == NULL) { error("invalid argument: struct jzfb_config_info *hal == NULL.n"); return ; } mode = hal->mode; if (mode == NULL) { error("%s error: get video mode failed.n", __func__); return ; } hds = mode->hsync_len + mode->left_margin; hde = hds + mode->xres; ht = hde + mode->right_margin; vds = mode->vsync_len + mode->upper_margin; vde = vds + mode->yres; vt = vde + mode->lower_margin; if (mode->refresh) { if (hal->lcd_type == LCD_TYPE_8BIT_SERIAL) { rate = mode->refresh * (vt + 2 * mode->xres) * ht; } else { rate = mode->refresh * ht * vt; } mode->pixclock = KHZ2PICOS(rate / 1000); } else if (mode->pixclock) { rate = PICOS2KHZ(mode->pixclock) * 1000; mode->refresh = rate / vt / ht; } else { error("%s error: lcd important config hal is absenced.n", __func__); } } extern struct jzfb_hal *save_hal; void lcd_restart_dma(void) { #ifndef CONFIG_SLCDC_CONTINUA if (save_hal->is_enable != 0) { int smart_ctrl = 0; smart_ctrl = hal_reg_read(save_hal, SLCDC_CTRL); smart_ctrl |= SLCDC_CTRL_DMA_START; //trigger a new frame hal_reg_write(save_hal, SLCDC_CTRL, smart_ctrl); } #endif } void jzfb_hal_slcd_restart(struct jzfb_hal *hal) { unsigned int tmp; tmp = hal_reg_read(hal, SLCDC_CTRL); tmp |= SLCDC_CTRL_DMA_START | SLCDC_CTRL_DMA_MODE; hal_reg_write(hal, SLCDC_CTRL, tmp); } static void jzfb_hal_config_tft_lcd_dma(struct jzfb_hal *hal) { struct jzfb_fg_t *fg = &hal->fg0; struct jzfb_framedesc *framedesc = fg->framedesc; #define BYTES_PER_PANEL (((hal->mode->xres * jzfb_hal_get_controller_bpp(hal->bpp) / 8 + 3) >> 2 << 2) * hal->mode->yres) framedesc->id = 0xda0; framedesc->next = fg->framedesc_phys; framedesc->databuf = fg->databuf; framedesc->cmd = LCDC_CMD_EOFINT | LCDC_CMD_FRM_EN; framedesc->cmd |= BYTES_PER_PANEL / 4; framedesc->offsize = 0; framedesc->page_width = 0; switch(fg->bpp) { case 16: framedesc->cpos = LCDC_CPOS_RGB_RGB565 | LCDC_CPOS_BPP_16; break; case 30: framedesc->cpos = LCDC_CPOS_BPP_30; break; default: framedesc->cpos = LCDC_CPOS_BPP_18_24; break; } /* global alpha mode */ framedesc->cpos |= 0; /* data has not been premultied */ framedesc->cpos |= LCDC_CPOS_PREMULTI; /* coef_sle 0 use 1 */ framedesc->cpos |= LCDC_CPOS_COEF_SLE_1; /* fg0 alpha value */ framedesc->desc_size = 0xff << LCDC_DESSIZE_ALPHA_BIT; framedesc->desc_size |= (((hal->mode->yres - 1) << LCDC_DESSIZE_HEIGHT_BIT & LCDC_DESSIZE_HEIGHT_MASK) | ((hal->mode->xres - 1) << LCDC_DESSIZE_WIDTH_BIT & LCDC_DESSIZE_WIDTH_MASK)); } static void jzfb_hal_config_smart_lcd_dma(struct jzfb_hal *hal) { unsigned long bypes_per_panel; struct jzfb_fg_t *fg0 = &hal->fg0; struct jzfb_fg_t *fg1 = &hal->fg1; struct jzfb_framedesc *framedesc0 = fg0->framedesc; struct jzfb_framedesc *framedesc1 = fg1->framedesc; struct jzfb_framedesc *cmd_framedesc = hal->cmd_framedesc; struct jzfb_config_info *info = (struct jzfb_config_info *)hal; fg0->bpp = jzfb_hal_get_controller_bpp(hal->bpp); fg0->x = 0; fg0->y = 0; fg0->w = hal->mode->xres; fg0->h = hal->mode->yres; fg1->bpp = jzfb_hal_get_controller_bpp(hal->bpp); fg1->x = 0; fg1->y = 0; fg1->w = hal->mode->xres; fg1->h = hal->mode->yres; bypes_per_panel = (((hal->mode->xres * jzfb_hal_get_controller_bpp(hal->bpp) / 8 + 3) >> 2 << 2) * hal->mode->yres); /* framedesc0 */ framedesc0->id = 0xda0; framedesc0->next = hal->cmd_framedesc_phys; framedesc0->databuf = fg0->databuf; framedesc0->cmd = LCDC_CMD_EOFINT | LCDC_CMD_FRM_EN; framedesc0->cmd |= bypes_per_panel / 4; framedesc0->offsize = 0; framedesc0->page_width = 0; switch (fg0->bpp) { case 16: framedesc0->cpos = LCDC_CPOS_RGB_RGB565 | LCDC_CPOS_BPP_16; break; case 30: framedesc0->cpos = LCDC_CPOS_BPP_30; break; default: framedesc0->cpos = LCDC_CPOS_BPP_18_24; break; } /* global alpha mode */ framedesc0->cpos |= 0; /* data has not been premultied */ framedesc0->cpos |= LCDC_CPOS_PREMULTI; /* coef_sle 0 use 1 */ framedesc0->cpos |= LCDC_CPOS_COEF_SLE_1; /* fg0 alpha value */ framedesc0->desc_size = 0xff << LCDC_DESSIZE_ALPHA_BIT; framedesc0->desc_size |= (((hal->mode->yres - 1) << LCDC_DESSIZE_HEIGHT_BIT & LCDC_DESSIZE_HEIGHT_MASK) | ((hal->mode->xres - 1) << LCDC_DESSIZE_WIDTH_BIT & LCDC_DESSIZE_WIDTH_MASK)); /* framedesc1 */ framedesc1->id = 0xda1; framedesc1->next = fg1->framedesc_phys; framedesc1->databuf = fg1->databuf; framedesc1->cmd = (LCDC_CMD_EOFINT & ~LCDC_CMD_FRM_EN) | (bypes_per_panel / 4); framedesc1->offsize = 0; framedesc1->page_width = 0; framedesc1->cpos = LCDC_CPOS_BPP_18_24 | LCDC_CPOS_COEF_SLE_3 | LCDC_CPOS_PREMULTI; framedesc1->desc_size = (((hal->mode->yres - 1) << LCDC_DESSIZE_HEIGHT_BIT & LCDC_DESSIZE_HEIGHT_MASK) | ((hal->mode->xres - 1) << LCDC_DESSIZE_WIDTH_BIT & LCDC_DESSIZE_WIDTH_MASK)); framedesc1->desc_size |= 0xff << LCDC_DESSIZE_ALPHA_BIT; /* cmd_framedesc */ cmd_framedesc->id = 0xda2; cmd_framedesc->next = fg0->framedesc_phys; cmd_framedesc->databuf = info->desc_cmd_phys; cmd_framedesc->offsize = 0; cmd_framedesc->page_width = 0; cmd_framedesc->desc_size = 0; /* if connect mipi smart lcd, do not sent command by slcdc, send command by mipi dsi controller. */ #ifdef CONFIG_JZ_MIPI_DSI cmd_framedesc->cmd = LCDC_CMD_CMD | LCDC_CMD_FRM_EN | 0; cmd_framedesc->cpos = 0; #else /* CONFIG_JZ_MIPI_DSI */ switch (hal->smart_config.bus_width) { case 8: cmd_framedesc->cmd = LCDC_CMD_CMD | LCDC_CMD_FRM_EN | 1; cmd_framedesc->cpos = 4; break; case 9: case 16: cmd_framdesc->cmd = LCDC_CMD_CMD | LCDC_CMD_FRM_EN | 1; cmd_framedesc->cpos = 2; break; default: cmd_framdesc->cmd = LCDC_CMD_CMD | LCDC_CMD_FRM_EN | 1; cmd_framedesc->cpos = 1; break; } #endif /* CONFIG_JZ_MIPI_DSI */ hal_reg_write(hal, LCDC_DA0, hal->cmd_framedesc_phys); } static void jzfb_hal_config_fg1_dma(struct jzfb_hal *hal) { struct jzfb_fg_t *fg = &hal->fg1; hal_reg_write(hal, LCDC_DA1, fg->framedesc_phys); } static int jzfb_hal_prepare_dma_desc(struct jzfb_hal *hal) { unsigned int rgb_ctrl, cfg; /* OSD mode enable and alpha blending is enabled */ cfg = LCDC_OSDC_OSDEN | LCDC_OSDC_ALPHAEN; cfg |= 1 << 16; /* once transfer two pixels */ if (hal->fmt_order == FORMAT_X8B8G8R8) { rgb_ctrl = LCDC_RGBC_RGBFMT | LCDC_RGBC_ODD_BGR | LCDC_RGBC_EVEN_BGR; } else { /* default: FORMAT_X8R8G8B8 */ rgb_ctrl = LCDC_RGBC_RGBFMT | LCDC_RGBC_ODD_RGB | LCDC_RGBC_EVEN_RGB; } hal_reg_write(hal, LCDC_OSDC, cfg); hal_reg_write(hal, LCDC_RGBC, rgb_ctrl); if (hal->lcd_type != LCD_TYPE_SLCD) { jzfb_hal_config_tft_lcd_dma(hal); } else { jzfb_hal_config_smart_lcd_dma(hal); } jzfb_hal_config_fg1_dma(hal); return 0; } void jzfb_hal_enable(struct jzfb_hal *hal) { uint32_t ctrl; if (hal->is_enable == 0) { hal_reg_write(hal, LCDC_STATE, 0); hal_reg_write(hal, LCDC_OSDS, 0); ctrl = hal_reg_read(hal, LCDC_CTRL); ctrl |= LCDC_CTRL_ENA; ctrl &= ~LCDC_CTRL_DIS; hal_reg_write(hal, LCDC_CTRL, ctrl); } hal->is_enable = 1; //dump_dsi_reg(dsi); //dump_lcd_reg(); } void jzfb_hal_disable(struct jzfb_hal *hal) { uint32_t ctrl; // int count = 20000; if (hal->is_enable == 1) { if (hal->lcd_type != LCD_TYPE_SLCD) { ctrl = hal_reg_read(hal, LCDC_CTRL); ctrl |= LCDC_CTRL_DIS; hal_reg_write(hal, LCDC_CTRL, ctrl); while (!(hal_reg_read(hal, LCDC_STATE) & LCDC_STATE_LDD)); } else { /* SLCD and TVE only support quick disable */ ctrl = hal_reg_read(hal, LCDC_CTRL); ctrl &= ~LCDC_CTRL_ENA; hal_reg_write(hal, LCDC_CTRL, ctrl); } } hal->is_enable = 0; } /* Sent a command without data (18-bit bus, 16-bit index) */ void jzfb_hal_slcd_send_mcu_command(struct jzfb_hal *hal, unsigned long cmd) { int count = 10000; cmd &= 0x3fffffff; while ((hal_reg_read(hal, SLCDC_STATE) & SLCDC_STATE_BUSY) && count--) { udelay(10); } if (count < 0) { error("SLCDC wait busy state wrong"); } hal_reg_write(hal, SLCDC_DATA, SLCDC_DATA_RS_COMMAND | cmd); } void jzfb_hal_slcd_send_mcu_data(struct jzfb_hal *hal, unsigned long data) { int count = 10000; data &= 0x3fffffff; while ((hal_reg_read(hal, SLCDC_STATE) & SLCDC_STATE_BUSY) && count--) { udelay(10); } if (count < 0) { error("SLCDC wait busy state wrong"); } hal_reg_write(hal, SLCDC_DATA, SLCDC_DATA_RS_DATA | data); } static void jzfb_slcd_mcu_init(struct jzfb_hal *hal) { unsigned int is_enable, i; unsigned long tmp; if (hal->lcd_type != LCD_TYPE_SLCD) return; is_enable = hal->is_enable; if (!is_enable) { jzfb_hal_enable(hal); } if (hal->smart_config.length_data_table && hal->smart_config.data_table) { for (i = 0; i < hal->smart_config.length_data_table; i++) { switch (hal->smart_config.data_table[i].type) { case SMART_CONFIG_DATA: jzfb_hal_slcd_send_mcu_data(hal, hal->smart_config.data_table[i].value); break; case SMART_CONFIG_CMD: jzfb_hal_slcd_send_mcu_command(hal, hal->smart_config.data_table[i].value); break; case SMART_CONFIG_UDELAY: udelay(hal->smart_config.data_table[i].value); break; default: error("Unknow SLCD data type!n"); break; } } { int count = 10000; while ((hal_reg_read(hal, SLCDC_STATE) & SLCDC_STATE_BUSY) && count--) { udelay(10); } if (count < 0) { error("SLCD wait busy state wrong!n"); } } } if (hal->bpp / hal->smart_config.bus_width != 1) { unsigned int tmp = hal_reg_read(hal, SLCDC_CFG_NEW); tmp &= ~(SMART_LCD_DWIDTH_MASK); //mask the 8~9bit tmp |= (hal->bpp / hal->smart_config.bus_width) == 2 ? SMART_LCD_NEW_DTIMES_TWICE : SMART_LCD_NEW_DTIMES_THICE; hal_reg_write(hal, SLCDC_CFG_NEW, tmp); printf("the slcd slcd_cfg_new is %08xn", tmp); } /* SLCD DMA mode select 0 */ if (!is_enable) { jzfb_hal_disable(hal); } } int jzfb_hal_set_par(struct jzfb_hal *hal) { struct fb_videomode *mode = hal->mode; uint16_t hds, vds; uint16_t hde, vde; uint16_t ht, vt; uint32_t cfg, ctrl; uint32_t size0, size1; uint32_t smart_cfg = 0, smart_ctrl = 0; uint32_t smart_new_cfg = 0; uint32_t smart_wtime = 0, smart_tas = 0; uint32_t pcfg; //unsigned long rate; hds = mode->hsync_len + mode->left_margin; hde = hds + mode->xres; ht = hde + mode->right_margin; vds = mode->vsync_len + mode->upper_margin; vde = vds + mode->yres; vt = vde + mode->lower_margin; /* * configure LCDC config register * use 8words descriptor, not use palette * ! M200 NOT SUPPORT PALETTE FUNCTION, DO NOT SET LCDC_CFG_PALBP(BIT27), IT CAUGHT BPP16 COLOR ERROR. */ /*SET PALBP TO AVOID FORMAT TRANSFER */ cfg = LCDC_CFG_NEWDES | LCDC_CFG_RECOVER; cfg |= hal->lcd_type; if (!(mode->sync & FB_SYNC_HOR_HIGH_ACT)) cfg |= LCDC_CFG_HSP; if (!(mode->sync & FB_SYNC_VERT_HIGH_ACT)) cfg |= LCDC_CFG_VSP; if (hal->pixclk_falling_edge) cfg |= LCDC_CFG_PCP; if (hal->data_enable_active_low) cfg |= LCDC_CFG_DEP; /* configure LCDC control register */ ctrl = LCDC_CTRL_BST_64 | LCDC_CTRL_OFUM; if (hal->pinmd) ctrl |= LCDC_CTRL_PINMD; /* new add the ctrl */ ctrl |= LCDC_CTRL_BPP_18_24; /* configure smart LCDC registers */ if (hal->lcd_type == LCD_TYPE_SLCD) { smart_cfg = hal->smart_config.smart_type | SMART_LCD_DWIDTH_24_BIT_ONCE_PARALLEL; switch(hal->smart_config.bus_width){ case 8: smart_cfg |= SMART_LCD_CWIDTH_8_BIT_ONCE; smart_new_cfg |= SMART_LCD_NEW_DWIDTH_8_BIT; break; case 9: smart_cfg |= SMART_LCD_CWIDTH_9_BIT_ONCE; smart_new_cfg |= SMART_LCD_NEW_DWIDTH_9_BIT; break; case 16: smart_cfg |= SMART_LCD_CWIDTH_16_BIT_ONCE; smart_new_cfg |= SMART_LCD_NEW_DWIDTH_16_BIT; break; case 18: smart_cfg |= SMART_LCD_CWIDTH_18_BIT_ONCE; smart_new_cfg |= SMART_LCD_NEW_DWIDTH_18_BIT; break; case 24: smart_cfg |= SMART_LCD_CWIDTH_24_BIT_ONCE; smart_new_cfg |= SMART_LCD_NEW_DWIDTH_24_BIT; break; default: debug("ERR: please check out your bus width confign"); break; } if (hal->smart_config.clkply_active_rising) smart_cfg |= SLCDC_CFG_CLK_ACTIVE_RISING; if (hal->smart_config.rsply_cmd_high) smart_cfg |= SLCDC_CFG_RS_CMD_HIGH; if (hal->smart_config.csply_active_high) smart_cfg |= SLCDC_CFG_CS_ACTIVE_HIGH; smart_ctrl = SLCDC_CTRL_DMA_MODE; //smart_ctrl |= SLCDC_CTRL_GATE_MASK; //for saving power smart_ctrl &= ~SLCDC_CTRL_GATE_MASK; smart_ctrl |= (SLCDC_CTRL_NEW_MODE | SLCDC_CTRL_NOT_USE_TE); //new slcd mode smart_ctrl &= ~SLCDC_CTRL_MIPI_MODE; smart_new_cfg |= SMART_LCD_NEW_DTIMES_ONCE; if (hal->smart_config.newcfg_6800_md) smart_new_cfg |= SLCDC_NEW_CFG_6800_MD; if (hal->smart_config.newcfg_datatx_type && hal->smart_config.newcfg_cmdtx_type) smart_new_cfg |= SLCDC_NEW_CFG_DTYPE_SERIAL | SLCDC_NEW_CFG_CTYPE_SERIAL; /* if (hal->smart_config.datatx_type_serial && hal->smart_config.cmdtx_type_serial) smart_new_cfg |= SLCDC_NEW_CFG_DTYPE_SERIAL | SLCDC_NEW_CFG_CTYPE_SERIAL; */ if (hal->smart_config.newcfg_cmd_9bit) smart_new_cfg |= SLCDC_NEW_CFG_CMD_9BIT; smart_wtime = 0; smart_tas = 0; } switch (hal->lcd_type) { case LCD_TYPE_SPECIAL_TFT_1: case LCD_TYPE_SPECIAL_TFT_2: case LCD_TYPE_SPECIAL_TFT_3: hal_reg_write(hal, LCDC_SPL, hal->special_tft_config.spl); hal_reg_write(hal, LCDC_CLS, hal->special_tft_config.cls); hal_reg_write(hal, LCDC_PS, hal->special_tft_config.ps); hal_reg_write(hal, LCDC_REV, hal->special_tft_config.ps); break; default: cfg |= LCDC_CFG_PSM; cfg |= LCDC_CFG_CLSM; cfg |= LCDC_CFG_SPLM; cfg |= LCDC_CFG_REVM; break; } if (hal->lcd_type != LCD_TYPE_SLCD) { hal_reg_write(hal, LCDC_VAT, (ht << 16) | vt); hal_reg_write(hal, LCDC_DAH, (hds << 16) | hde); hal_reg_write(hal, LCDC_DAV, (vds << 16) | vde); hal_reg_write(hal, LCDC_HSYNC, mode->hsync_len); hal_reg_write(hal, LCDC_VSYNC, mode->vsync_len); } else { #ifdef CONFIG_JZ_MIPI_DSI smart_cfg |= 1 << 16; smart_new_cfg |= 4 << 13; smart_ctrl |= 1 << 7 | 1 << 6; jzfb_hal_mipi_config(); #endif hal_reg_write(hal, LCDC_VAT, (mode->xres << 16) | mode->yres); hal_reg_write(hal, LCDC_DAH, mode->xres); hal_reg_write(hal, LCDC_DAV, mode->yres); hal_reg_write(hal, LCDC_HSYNC, 0); hal_reg_write(hal, LCDC_VSYNC, 0); hal_reg_write(hal, SLCDC_CFG, smart_cfg); hal_reg_write(hal, SLCDC_CTRL, smart_ctrl); hal_reg_write(hal, SLCDC_CFG_NEW, smart_new_cfg); hal_reg_write(hal, SLCDC_WTIME, smart_wtime); hal_reg_write(hal, SLCDC_TAS, smart_tas); } hal_reg_write(hal, LCDC_CFG, cfg); hal_reg_write(hal, LCDC_CTRL, ctrl); pcfg = 0xC0000000 | (511 << 18) | (400 << 9) | (256 << 0); hal_reg_write(hal, LCDC_PCFG, pcfg); size0 = (hal->mode->xres << LCDC_SIZE_WIDTH_BIT) & LCDC_SIZE_WIDTH_MASK; size0 |= ((hal->mode-> yres << LCDC_SIZE_HEIGHT_BIT) & LCDC_SIZE_HEIGHT_MASK); size1 = size0; hal_reg_write(hal, LCDC_SIZE0, size0); hal_reg_write(hal, LCDC_SIZE1, size1); /* prepare dma descriptor */ jzfb_hal_prepare_dma_desc(hal); if (hal->lcd_type == LCD_TYPE_SLCD) { /* jzfb_slcd_mcu_init */ jzfb_slcd_mcu_init(hal); #ifdef CONFIG_SLCDC_CONTINUA smart_ctrl &= ~SLCDC_CTRL_DMA_MODE; #else smart_ctrl |= SLCDC_CTRL_DMA_START; #endif smart_ctrl |= SLCDC_CTRL_DMA_EN; #ifdef CONFIG_SLCDC_USE_TE smart_ctrl &= ~SLCDC_CTRL_NOT_USE_TE; #endif if (hal->smart_config.newcfg_fmt_conv) { smart_new_cfg = hal_reg_read(hal, SLCDC_CFG_NEW); smart_new_cfg |= SLCDC_NEW_CFG_FMT_CONV_EN; hal_reg_write(hal, SLCDC_CFG_NEW, smart_new_cfg); } hal_reg_write(hal, SLCDC_CTRL, smart_ctrl); } #ifdef CONFIG_JZ_MIPI_DSI else { cfg = hal_reg_read(hal, LCDC_CFG); //maby can delete cfg |= 1 << 24; hal_reg_write(hal, LCDC_CFG, cfg); /* jzfb->dsi->master_ops->video_cfg(jzfb->dsi); */ jzfb_hal_dsi_video_cfg(); } #endif return 0; }
3.uboot中frame buffer驱动的头文件:
复制代码
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45#ifndef __JZ_LCD_V1_2_H__ #define __JZ_LCD_V1_2_H__ #include <common.h> #include <linux/types.h> #include "jz_fb_hal.h" void panel_pin_init(void); void panel_power_on(void); void panel_power_off(void); void panel_suspend(void); void board_set_lcd_power_on(void); void board_set_lcd_power_off(void); #if PWM_BACKLIGHT_CHIP void lcd_set_backlight_level(int num); void lcd_close_backlight(void); #else void lcd_init_backlight(int num); void send_low_pulse(int num); void lcd_set_backlight_level(int num); void lcd_close_backlight(void); #endif #ifdef CONFIG_TWO_FRAME_BUFFERS #define NUM_FRAME_BUFFERS 2 #endif #ifdef CONFIG_THREE_FRAME_BUFFERS #define NUM_FRAME_BUFFERS 3 #endif #define PIXEL_ALIGN 16 #define MODE_NAME_LEN 32 struct jzfb_config_info lcd_config_info; struct jzfb_config_info { struct jzfb_hal hal; struct jzfb_framedesc *framedesc; unsigned long framedesc_phys; unsigned long *desc_cmd_vidmem; unsigned long desc_cmd_phys; void *vidmem; unsigned long vidmem_phys; }; int jzfb_get_controller_bpp(unsigned int); extern struct jzfb_config_info lcd_config_info; extern struct jzfb_config_info jzfb1_init_data; extern struct fb_videomode jzfb1_videomode; extern struct dsi_device jz_dsi; #endif /*__JZ_LCD_H__*/
4.uboot中frame buffer的驱动代码:
复制代码
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422#include <asm/io.h> #include <config.h> #include <serial.h> #include <common.h> #include <lcd.h> #include <asm/arch/lcdc.h> #include <asm/arch/gpio.h> #include <asm/arch/clk.h> #include <jz_lcd/jz_lcd_v1_2.h> /*#define DEBUG*/ #ifdef CONFIG_JZ_MIPI_DSI #include <jz_lcd/jz_dsim.h> #include "./jz_mipi_dsi/jz_mipi_dsi_regs.h" #include "./jz_mipi_dsi/jz_mipi_dsih_hal.h" struct dsi_device *dsi; void jz_dsi_init(struct dsi_device *dsi); int jz_dsi_video_cfg(struct dsi_device *dsi); #endif void panel_init_set_sequence(struct dsi_device *dsi); void board_set_lcd_power_on(void); void flush_cache_all(void); void lcd_close_backlight(void); void lcd_set_backlight_level(int num); #define reg_write(addr,config) writel(config,lcd_config_info.hal.base+addr) #define reg_read(addr) readl(lcd_config_info.hal.base+addr) struct jzfb_config_info lcd_config_info; struct jzfb_hal *save_hal; void dump_dsi_reg(struct dsi_device *dsi) { printf( "===========>dump dsi regn"); printf( "VERSION------------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VERSION)); printf( "PWR_UP:------------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_PWR_UP)); printf( "CLKMGR_CFG---------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_CLKMGR_CFG)); printf( "DPI_VCID-----------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_DPI_VCID)); printf( "DPI_COLOR_CODING---:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_DPI_COLOR_CODING)); printf( "DPI_CFG_POL--------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_DPI_CFG_POL)); printf( "DPI_LP_CMD_TIM-----:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_DPI_LP_CMD_TIM)); printf( "DBI_VCID-----------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_DBI_VCID)); printf( "DBI_CFG------------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_DBI_CFG)); printf( "DBI_PARTITIONING_EN:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_DBI_PARTITIONING_EN)); printf( "DBI_CMDSIZE--------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_DBI_CMDSIZE)); printf( "PCKHDL_CFG---------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_PCKHDL_CFG)); printf( "GEN_VCID-----------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_GEN_VCID)); printf( "MODE_CFG-----------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_MODE_CFG)); printf( "VID_MODE_CFG-------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_MODE_CFG)); printf( "VID_PKT_SIZE-------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_PKT_SIZE)); printf( "VID_NUM_CHUNKS-----:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_NUM_CHUNKS)); printf( "VID_NULL_SIZE------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_NULL_SIZE)); printf( "VID_HSA_TIME-------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_HSA_TIME)); printf( "VID_HBP_TIME-------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_HBP_TIME)); printf( "VID_HLINE_TIME-----:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_HLINE_TIME)); printf( "VID_VSA_LINES------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_VSA_LINES)); printf( "VID_VBP_LINES------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_VBP_LINES)); printf( "VID_VFP_LINES------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_VFP_LINES)); printf( "VID_VACTIVE_LINES--:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_VACTIVE_LINES)); printf( "EDPI_CMD_SIZE------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_EDPI_CMD_SIZE)); printf( "CMD_MODE_CFG-------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_CMD_MODE_CFG)); printf( "GEN_HDR------------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_GEN_HDR)); printf( "GEN_PLD_DATA-------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_GEN_PLD_DATA)); printf( "CMD_PKT_STATUS-----:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_CMD_PKT_STATUS)); printf( "TO_CNT_CFG---------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_TO_CNT_CFG)); printf( "HS_RD_TO_CNT-------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_HS_RD_TO_CNT)); printf( "LP_RD_TO_CNT-------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_LP_RD_TO_CNT)); printf( "HS_WR_TO_CNT-------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_HS_WR_TO_CNT)); printf( "LP_WR_TO_CNT_CFG---:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_LP_WR_TO_CNT)); printf( "BTA_TO_CNT---------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_BTA_TO_CNT)); printf( "SDF_3D-------------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_SDF_3D)); printf( "LPCLK_CTRL---------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_LPCLK_CTRL)); printf( "PHY_TMR_LPCLK_CFG--:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_PHY_TMR_LPCLK_CFG)); printf( "PHY_TMR_CFG--------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_PHY_TMR_CFG)); printf( "PHY_RSTZ-----------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_PHY_RSTZ)); printf( "PHY_IF_CFG---------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_PHY_IF_CFG)); printf( "PHY_ULPS_CTRL------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_PHY_ULPS_CTRL)); printf( "PHY_TX_TRIGGERS----:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_PHY_TX_TRIGGERS)); printf( "PHY_STATUS---------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_PHY_STATUS)); printf( "PHY_TST_CTRL0------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_PHY_TST_CTRL0)); printf( "PHY_TST_CTRL1------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_PHY_TST_CTRL1)); printf( "INT_ST0------------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_INT_ST0)); printf( "INT_ST1------------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_INT_ST1)); printf( "INT_MSK0-----------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_INT_MSK0)); printf( "INT_MSK1-----------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_INT_MSK1)); printf( "INT_FORCE0---------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_INT_FORCE0)); printf( "INT_FORCE1---------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_INT_FORCE1)); printf( "VID_SHADOW_CTRL----:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_SHADOW_CTRL)); printf( "DPI_VCID_ACT-------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_DPI_VCID_ACT)); printf( "DPI_COLOR_CODING_AC:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_DPI_COLOR_CODING_ACT)); printf( "DPI_LP_CMD_TIM_ACT-:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_DPI_LP_CMD_TIM_ACT)); printf( "VID_MODE_CFG_ACT---:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_MODE_CFG_ACT)); printf( "VID_PKT_SIZE_ACT---:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_PKT_SIZE_ACT)); printf( "VID_NUM_CHUNKS_ACT-:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_NUM_CHUNKS_ACT)); printf( "VID_HSA_TIME_ACT---:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_HSA_TIME_ACT)); printf( "VID_HBP_TIME_ACT---:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_HBP_TIME_ACT)); printf( "VID_HLINE_TIME_ACT-:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_HLINE_TIME_ACT)); printf( "VID_VSA_LINES_ACT--:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_VSA_LINES_ACT)); printf( "VID_VBP_LINES_ACT--:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_VBP_LINES_ACT)); printf( "VID_VFP_LINES_ACT--:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_VFP_LINES_ACT)); printf( "VID_VACTIVE_LINES_ACT:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_VID_VACTIVE_LINES_ACT)); printf( "SDF_3D_ACT---------:%08xn", mipi_dsih_read_word(dsi, R_DSI_HOST_SDF_3D_ACT)); } void dump_lcd_reg(void) { printf("$$$dump_lcd_regn"); int tmp; printf("LCDC_CFG:(0x%08x) t0x%08xn", LCDC_CFG,reg_read(LCDC_CFG)); printf("LCDC_CTRL:(0x%08x)t0x%08xn",LCDC_CTRL,reg_read(LCDC_CTRL)); printf("LCDC_STATE:(0x%08x)t0x%08xn",LCDC_STATE,reg_read(LCDC_STATE)); printf("LCDC_OSDC:(0x%08x)t0x%08xn", LCDC_OSDC,reg_read(LCDC_OSDC)); printf("LCDC_OSDCTRL:(0x%08x)t0x%08xn",LCDC_OSDCTRL,reg_read(LCDC_OSDCTRL)); printf("LCDC_OSDS:(0x%08x)t0x%08xn",LCDC_OSDS,reg_read(LCDC_OSDS)); printf("LCDC_BGC0:(0x%08x)t0x%08xn",LCDC_BGC0,reg_read(LCDC_BGC0)); printf("LCDC_BGC1:(0x%08x)t0x%08xn",LCDC_BGC1,reg_read(LCDC_BGC1)); printf("LCDC_KEY0:(0x%08x)t0x%08xn",LCDC_KEY0, reg_read(LCDC_KEY0)); printf("LCDC_KEY1:(0x%08x)t0x%08xn",LCDC_KEY1, reg_read(LCDC_KEY1)); printf("LCDC_ALPHA:(0x%08x)t0x%08xn",LCDC_ALPHA, reg_read(LCDC_ALPHA)); printf("==================================n"); tmp = reg_read(LCDC_VAT); printf("LCDC_VAT:(0x%08x) t0x%08x, HT = %d, VT = %dn",LCDC_VAT, tmp, (tmp & LCDC_VAT_HT_MASK) >> LCDC_VAT_HT_BIT, (tmp & LCDC_VAT_VT_MASK) >> LCDC_VAT_VT_BIT); tmp = reg_read(LCDC_DAH); printf("LCDC_DAH:(0x%08x) t0x%08x, HDS = %d, HDE = %dn",LCDC_DAH, tmp, (tmp & LCDC_DAH_HDS_MASK) >> LCDC_DAH_HDS_BIT, (tmp & LCDC_DAH_HDE_MASK) >> LCDC_DAH_HDE_BIT); tmp = reg_read(LCDC_DAV); printf("LCDC_DAV:(0x%08x) t0x%08x, VDS = %d, VDE = %dn",LCDC_DAV, tmp, (tmp & LCDC_DAV_VDS_MASK) >> LCDC_DAV_VDS_BIT, (tmp & LCDC_DAV_VDE_MASK) >> LCDC_DAV_VDE_BIT); tmp = reg_read(LCDC_HSYNC); printf("LCDC_HSYNC:(0x%08x)t0x%08x, HPS = %d, HPE = %dn",LCDC_HSYNC, tmp, (tmp & LCDC_HSYNC_HPS_MASK) >> LCDC_HSYNC_HPS_BIT, (tmp & LCDC_HSYNC_HPE_MASK) >> LCDC_HSYNC_HPE_BIT); tmp = reg_read(LCDC_VSYNC); printf("LCDC_VSYNC:(0x%08x)t0x%08x, VPS = %d, VPE = %dn", LCDC_VSYNC,tmp, (tmp & LCDC_VSYNC_VPS_MASK) >> LCDC_VSYNC_VPS_BIT, (tmp & LCDC_VSYNC_VPE_MASK) >> LCDC_VSYNC_VPE_BIT); printf("==================================n"); printf("LCDC_XYP0:(0x%08x)t0x%08xn",LCDC_XYP0, reg_read(LCDC_XYP0)); printf("LCDC_XYP1:(0x%08x)t0x%08xn",LCDC_XYP1, reg_read(LCDC_XYP1)); printf("LCDC_SIZE0:(0x%08x)t0x%08xn",LCDC_SIZE0, reg_read(LCDC_SIZE0)); printf("LCDC_SIZE1:(0x%08x)t0x%08xn",LCDC_SIZE1, reg_read(LCDC_SIZE1)); printf("LCDC_RGBC:(0x%08x) t0x%08xn",LCDC_RGBC, reg_read(LCDC_RGBC)); printf("LCDC_PS:(0x%08x) t0x%08xn",LCDC_PS, reg_read(LCDC_PS)); printf("LCDC_CLS:(0x%08x) t0x%08xn", LCDC_CLS,reg_read(LCDC_CLS)); printf("LCDC_SPL:(0x%08x) t0x%08xn",LCDC_SPL, reg_read(LCDC_SPL)); printf("LCDC_REV:(0x%08x) t0x%08xn",LCDC_REV, reg_read(LCDC_REV)); printf("LCDC_IID:(0x%08x) t0x%08xn",LCDC_IID, reg_read(LCDC_IID)); printf("==================================n"); printf("LCDC_DA0:(0x%08x) t0x%08xn",LCDC_DA0, reg_read(LCDC_DA0)); printf("LCDC_SA0:(0x%08x) t0x%08xn",LCDC_SA0, reg_read(LCDC_SA0)); printf("LCDC_FID0:(0x%08x)t0x%08xn",LCDC_FID0, reg_read(LCDC_FID0)); printf("LCDC_CMD0:(0x%08x)t0x%08xn",LCDC_CMD0, reg_read(LCDC_CMD0)); printf("LCDC_OFFS0:(0x%08x)t0x%08xn",LCDC_OFFS0, reg_read(LCDC_OFFS0)); printf("LCDC_PW0:(0x%08x) t0x%08xn", LCDC_PW0,reg_read(LCDC_PW0)); printf("LCDC_CNUM0:(0x%08x)t0x%08xn",LCDC_CNUM0, reg_read(LCDC_CNUM0)); printf("LCDC_DESSIZE0:(0x%08x)t0x%08xn",LCDC_DESSIZE0, reg_read(LCDC_DESSIZE0)); printf("==================================n"); printf("LCDC_DA1:(0x%08x) t0x%08xn", LCDC_DA1, reg_read(LCDC_DA1)); printf("LCDC_SA1:(0x%08x) t0x%08xn",LCDC_SA1, reg_read(LCDC_SA1)); printf("LCDC_FID1:(0x%08x)t0x%08xn",LCDC_FID1, reg_read(LCDC_FID1)); printf("LCDC_CMD1:(0x%08x)t0x%08xn",LCDC_CMD1, reg_read(LCDC_CMD1)); printf("LCDC_OFFS1:(0x%08x)t0x%08xn",LCDC_OFFS1, reg_read(LCDC_OFFS1)); printf("LCDC_PW1:(0x%08x) t0x%08xn",LCDC_PW1, reg_read(LCDC_PW1)); printf("LCDC_CNUM1:(0x%08x)t0x%08xn",LCDC_CNUM1, reg_read(LCDC_CNUM1)); printf("LCDC_DESSIZE1:(0x%08x)t0x%08xn",LCDC_DESSIZE1, reg_read(LCDC_DESSIZE1)); printf("==================================n"); printf("LCDC_PCFG:(0x%08x)t0x%08xn", LCDC_PCFG,reg_read(LCDC_PCFG)); printf("==================================n"); printf("SLCDC_CFG:(0x%08x) t0x%08xn", SLCDC_CFG,reg_read(SLCDC_CFG)); printf("SLCDC_CTRL:(0x%08x) t0x%08xn", SLCDC_CTRL,reg_read(SLCDC_CTRL)); printf("SLCDC_STATE:(0x%08x) t0x%08xn", SLCDC_STATE,reg_read(SLCDC_STATE)); printf("SLCDC_DATA:(0x%08x)t0x%08xn", SLCDC_DATA,reg_read(SLCDC_DATA)); printf("SLCDC_CFG_NEW:(0x%08x) t0x%08xn", SLCDC_CFG_NEW,reg_read(SLCDC_CFG_NEW)); printf("SLCDC_WTIME:(0x%08x) t0x%08xn", SLCDC_WTIME,reg_read(SLCDC_WTIME)); printf("SLCDC_TAS:(0x%08x) t0x%08xn", SLCDC_TAS,reg_read(SLCDC_TAS)); printf("==================================n"); printf("reg:0x10000020 value=0x%08x (24bit) Clock Gate Register0n", *(unsigned int *)0xb0000020); printf("reg:0x100000e4 value=0x%08x (5bit_lcdc 21bit_lcdcs) Power Gate Register: n", *(unsigned int *)0xb00000e4); printf("reg:0x100000b8 value=0x%08x (10bit) SRAM Power Control Register0 n", *(unsigned int *)0xb00000b8); printf("reg:0x10000064 value=0x%08x Lcd pixclock n", *(unsigned int *)0xb0000064); printf("==================================n"); printf("PCINT:t0x%08xn", *(unsigned int *)0xb0010210); printf("PCMASK:t0x%08xn",*(unsigned int *)0xb0010220); printf("PCPAT1:t0x%08xn",*(unsigned int *)0xb0010230); printf("PCPAT0:t0x%08xn",*(unsigned int *)0xb0010240); printf("==================================n"); }/*end dump_lcd_reg*/ void lcd_enable(void) { jzfb_hal_enable(&lcd_config_info.hal); } void lcd_disable(void) { jzfb_hal_disable(&lcd_config_info.hal); } void jzfb_mipi_config(void) { mipi_dsih_write_word(dsi, R_DSI_HOST_CMD_MODE_CFG, 0x1); //te mipi_dsih_dphy_enable_hs_clk(dsi, 1); mipi_dsih_hal_gen_set_mode(dsi, 1); mipi_dsih_hal_dpi_color_coding(dsi, dsi->video_config->color_coding); } void jzfb_dsi_video_cfg(void) { jz_dsi_video_cfg(dsi); } int jzfb_get_controller_bpp(unsigned int bpp) { switch (bpp) { case 18: case 24: return 32; case 15: return 16; default: return bpp; } } static void jzfb_alloc_devmem(void *lcdbase, struct jzfb_config_info *info) { unsigned long palette_mem_size; int fb_size = (info->hal.mode->xres * (jzfb_get_controller_bpp(info->hal.bpp) / 8)) * info->hal.mode->yres; info->vidmem = lcdbase; info->vidmem_phys = virt_to_phys((void *)info->vidmem); palette_mem_size = 256 * sizeof(u16); info->framedesc = (struct jzfb_framedesc *)(lcdbase + fb_size + PAGE_SIZE - palette_mem_size) - 4; info->framedesc_phys = virt_to_phys((void *)info->framedesc); info->desc_cmd_vidmem = ((unsigned long)lcdbase + fb_size + PAGE_SIZE -1) & ~(PAGE_SIZE - 1); info->desc_cmd_phys = virt_to_phys((void *)info->desc_cmd_vidmem); if (info->hal.lcd_type == LCD_TYPE_SLCD) { int i; unsigned long *ptr; ptr = (unsigned long *)info->desc_cmd_vidmem; for (i = 0; i < info->hal.smart_config.length_cmd; i++) { ptr[i] = info->hal.smart_config.write_gram_cmd[i]; } flush_cache_all(); } } static void jzfb_init_fg(struct jzfb_config_info *info) { struct jzfb_fg_t *fg0 = &info->hal.fg0; struct jzfb_fg_t *fg1 = &info->hal.fg1; struct fb_videomode *mode = info->hal.mode; #define BYTES_PER_PANEL (((info->hal.mode->xres * jzfb_get_controller_bpp(info->hal.bpp) / 8 + 3) >> 2 << 2) * info->hal.mode->yres) fg0->framedesc = info->framedesc + 0; fg0->framedesc_phys = info->framedesc_phys; fg0->databuf = info->vidmem_phys; fg0->bpp = info->hal.bpp; fg0->h = mode->yres; fg0->w = mode->xres; fg0->x = 0; fg0->y = 0; fg1->framedesc = info->framedesc + 1; fg1->framedesc_phys = info->framedesc_phys + 1 * sizeof(*info->framedesc); fg1->databuf = virt_to_phys((void *)(info->vidmem + BYTES_PER_PANEL)); fg1->bpp = info->hal.bpp; fg1->h = mode->yres; fg1->w = mode->xres; fg1->x = 0; fg1->y = 0; if (info->hal.lcd_type == LCD_TYPE_SLCD) { info->hal.cmd_framedesc = info->framedesc + 2; info->hal.cmd_framedesc_phys = info->framedesc_phys + 2 * sizeof(*info->framedesc); } } static void refresh_pixclock_auto_adapt(struct jzfb_config_info *info) { jzfb_hal_refresh_pixclock_auto_adapt(&info->hal); } static void jzfb_set_par(struct jzfb_config_info *info) { jzfb_hal_set_par(&info->hal); } void lcd_ctrl_init(void *lcd_base) { unsigned long pixel_clock_rate; /* init registers base address */ lcd_config_info = jzfb1_init_data; save_hal = &lcd_config_info.hal; lcd_config_info.hal.base = 0; #ifdef CONFIG_JZ_MIPI_DSI dsi = &jz_dsi; #endif lcd_set_flush_dcache(1); refresh_pixclock_auto_adapt(&lcd_config_info); pixel_clock_rate = PICOS2KHZ(lcd_config_info.hal.mode->pixclock); /* smart lcd WR freq = (lcd pixel clock)/2 */ if (lcd_config_info.hal.lcd_type == LCD_TYPE_SLCD) { pixel_clock_rate *= 2; } clk_set_rate(LCD, pixel_clock_rate); lcd_close_backlight(); panel_pin_init(); #ifdef CONFIG_LCD_FORMAT_X8B8G8R8 lcd_config_info.hal.fmt_order = FORMAT_X8B8G8R8; #else lcd_config_info.hal.fmt_order = FORMAT_X8R8G8B8; #endif //jz_lcd_init_mem(lcd_base, &lcd_config_info); jzfb_alloc_devmem(lcd_base, &lcd_config_info); jzfb_init_fg(&lcd_config_info); board_set_lcd_power_on(); panel_power_on(); #ifdef CONFIG_JZ_MIPI_DSI jz_dsi_init(dsi); panel_init_set_sequence(dsi); #endif jzfb_set_par(&lcd_config_info); flush_cache_all(); dump_dsi_reg(dsi); dump_lcd_reg(); return; } void lcd_show_board_info(void) { return; } void lcd_setcolreg(ushort regno, ushort red, ushort green, ushort blue) { return; } void __attribute__((weak)) panel_suspend(void) { printf("no %s implementn", __func__); } void __attribute__((weak)) board_set_lcd_power_off(void) { printf("no %s implementn", __func__); } static int do_lcd_suspend(cmd_tbl_t * cmdtp, int flag, int argc, char *const argv[]) { // lcd_clear_black(); panel_suspend(); board_set_lcd_power_off(); return CMD_RET_SUCCESS; } U_BOOT_CMD(lcd_suspend, 4, 1, do_lcd_suspend, "suspend the lcd panel", "lcd_suspend");
最后
以上就是体贴黑猫最近收集整理的关于frame buffer驱动的全部内容,更多相关frame内容请搜索靠谱客的其他文章。
本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
发表评论 取消回复