@@ -317,6 +317,17 @@ static void fsl_diu_free(void *virt, size_t size)
317
317
free_pages_exact (virt , size );
318
318
}
319
319
320
+ /*
321
+ * Workaround for failed writing desc register of planes.
322
+ * Needed with MPC5121 DIU rev 2.0 silicon.
323
+ */
324
+ void wr_reg_wa (u32 * reg , u32 val )
325
+ {
326
+ do {
327
+ out_be32 (reg , val );
328
+ } while (in_be32 (reg ) != val );
329
+ }
330
+
320
331
static int fsl_diu_enable_panel (struct fb_info * info )
321
332
{
322
333
struct mfb_info * pmfbi , * cmfbi , * mfbi = info -> par ;
@@ -330,7 +341,7 @@ static int fsl_diu_enable_panel(struct fb_info *info)
330
341
switch (mfbi -> index ) {
331
342
case 0 : /* plane 0 */
332
343
if (hw -> desc [0 ] != ad -> paddr )
333
- out_be32 (& hw -> desc [0 ], ad -> paddr );
344
+ wr_reg_wa (& hw -> desc [0 ], ad -> paddr );
334
345
break ;
335
346
case 1 : /* plane 1 AOI 0 */
336
347
cmfbi = machine_data -> fsl_diu_info [2 ]-> par ;
@@ -340,7 +351,7 @@ static int fsl_diu_enable_panel(struct fb_info *info)
340
351
cpu_to_le32 (cmfbi -> ad -> paddr );
341
352
else
342
353
ad -> next_ad = 0 ;
343
- out_be32 (& hw -> desc [1 ], ad -> paddr );
354
+ wr_reg_wa (& hw -> desc [1 ], ad -> paddr );
344
355
}
345
356
break ;
346
357
case 3 : /* plane 2 AOI 0 */
@@ -351,22 +362,22 @@ static int fsl_diu_enable_panel(struct fb_info *info)
351
362
cpu_to_le32 (cmfbi -> ad -> paddr );
352
363
else
353
364
ad -> next_ad = 0 ;
354
- out_be32 (& hw -> desc [2 ], ad -> paddr );
365
+ wr_reg_wa (& hw -> desc [2 ], ad -> paddr );
355
366
}
356
367
break ;
357
368
case 2 : /* plane 1 AOI 1 */
358
369
pmfbi = machine_data -> fsl_diu_info [1 ]-> par ;
359
370
ad -> next_ad = 0 ;
360
371
if (hw -> desc [1 ] == machine_data -> dummy_ad -> paddr )
361
- out_be32 (& hw -> desc [1 ], ad -> paddr );
372
+ wr_reg_wa (& hw -> desc [1 ], ad -> paddr );
362
373
else /* AOI0 open */
363
374
pmfbi -> ad -> next_ad = cpu_to_le32 (ad -> paddr );
364
375
break ;
365
376
case 4 : /* plane 2 AOI 1 */
366
377
pmfbi = machine_data -> fsl_diu_info [3 ]-> par ;
367
378
ad -> next_ad = 0 ;
368
379
if (hw -> desc [2 ] == machine_data -> dummy_ad -> paddr )
369
- out_be32 (& hw -> desc [2 ], ad -> paddr );
380
+ wr_reg_wa (& hw -> desc [2 ], ad -> paddr );
370
381
else /* AOI0 was open */
371
382
pmfbi -> ad -> next_ad = cpu_to_le32 (ad -> paddr );
372
383
break ;
@@ -390,27 +401,24 @@ static int fsl_diu_disable_panel(struct fb_info *info)
390
401
switch (mfbi -> index ) {
391
402
case 0 : /* plane 0 */
392
403
if (hw -> desc [0 ] != machine_data -> dummy_ad -> paddr )
393
- out_be32 (& hw -> desc [0 ],
394
- machine_data -> dummy_ad -> paddr );
404
+ wr_reg_wa (& hw -> desc [0 ], machine_data -> dummy_ad -> paddr );
395
405
break ;
396
406
case 1 : /* plane 1 AOI 0 */
397
407
cmfbi = machine_data -> fsl_diu_info [2 ]-> par ;
398
408
if (cmfbi -> count > 0 ) /* AOI1 is open */
399
- out_be32 (& hw -> desc [1 ], cmfbi -> ad -> paddr );
409
+ wr_reg_wa (& hw -> desc [1 ], cmfbi -> ad -> paddr );
400
410
/* move AOI1 to the first */
401
411
else /* AOI1 was closed */
402
- out_be32 (& hw -> desc [1 ],
403
- machine_data -> dummy_ad -> paddr );
412
+ wr_reg_wa (& hw -> desc [1 ], machine_data -> dummy_ad -> paddr );
404
413
/* close AOI 0 */
405
414
break ;
406
415
case 3 : /* plane 2 AOI 0 */
407
416
cmfbi = machine_data -> fsl_diu_info [4 ]-> par ;
408
417
if (cmfbi -> count > 0 ) /* AOI1 is open */
409
- out_be32 (& hw -> desc [2 ], cmfbi -> ad -> paddr );
418
+ wr_reg_wa (& hw -> desc [2 ], cmfbi -> ad -> paddr );
410
419
/* move AOI1 to the first */
411
420
else /* AOI1 was closed */
412
- out_be32 (& hw -> desc [2 ],
413
- machine_data -> dummy_ad -> paddr );
421
+ wr_reg_wa (& hw -> desc [2 ], machine_data -> dummy_ad -> paddr );
414
422
/* close AOI 0 */
415
423
break ;
416
424
case 2 : /* plane 1 AOI 1 */
@@ -421,7 +429,7 @@ static int fsl_diu_disable_panel(struct fb_info *info)
421
429
/* AOI0 is open, must be the first */
422
430
pmfbi -> ad -> next_ad = 0 ;
423
431
} else /* AOI1 is the first in the chain */
424
- out_be32 (& hw -> desc [1 ], machine_data -> dummy_ad -> paddr );
432
+ wr_reg_wa (& hw -> desc [1 ], machine_data -> dummy_ad -> paddr );
425
433
/* close AOI 1 */
426
434
break ;
427
435
case 4 : /* plane 2 AOI 1 */
@@ -432,7 +440,7 @@ static int fsl_diu_disable_panel(struct fb_info *info)
432
440
/* AOI0 is open, must be the first */
433
441
pmfbi -> ad -> next_ad = 0 ;
434
442
} else /* AOI1 is the first in the chain */
435
- out_be32 (& hw -> desc [2 ], machine_data -> dummy_ad -> paddr );
443
+ wr_reg_wa (& hw -> desc [2 ], machine_data -> dummy_ad -> paddr );
436
444
/* close AOI 1 */
437
445
break ;
438
446
default :
0 commit comments