1 /* 2 * Intel XScale PXA255/270 LCDC emulation. 3 * 4 * Copyright (c) 2006 Openedhand Ltd. 5 * Written by Andrzej Zaborowski <balrog@zabor.org> 6 * 7 * This code is licensed under the GPLv2. 8 * 9 * Contributions after 2012-01-13 are licensed under the terms of the 10 * GNU GPL, version 2 or (at your option) any later version. 11 */ 12 13 #include "qemu/osdep.h" 14 #include "hw/hw.h" 15 #include "hw/irq.h" 16 #include "migration/vmstate.h" 17 #include "ui/console.h" 18 #include "hw/arm/pxa.h" 19 #include "ui/pixel_ops.h" 20 /* FIXME: For graphic_rotate. Should probably be done in common code. */ 21 #include "sysemu/sysemu.h" 22 #include "framebuffer.h" 23 24 struct DMAChannel { 25 uint32_t branch; 26 uint8_t up; 27 uint8_t palette[1024]; 28 uint8_t pbuffer[1024]; 29 void (*redraw)(PXA2xxLCDState *s, hwaddr addr, 30 int *miny, int *maxy); 31 32 uint32_t descriptor; 33 uint32_t source; 34 uint32_t id; 35 uint32_t command; 36 }; 37 38 struct PXA2xxLCDState { 39 MemoryRegion *sysmem; 40 MemoryRegion iomem; 41 MemoryRegionSection fbsection; 42 qemu_irq irq; 43 int irqlevel; 44 45 int invalidated; 46 QemuConsole *con; 47 drawfn *line_fn[2]; 48 int dest_width; 49 int xres, yres; 50 int pal_for; 51 int transp; 52 enum { 53 pxa_lcdc_2bpp = 1, 54 pxa_lcdc_4bpp = 2, 55 pxa_lcdc_8bpp = 3, 56 pxa_lcdc_16bpp = 4, 57 pxa_lcdc_18bpp = 5, 58 pxa_lcdc_18pbpp = 6, 59 pxa_lcdc_19bpp = 7, 60 pxa_lcdc_19pbpp = 8, 61 pxa_lcdc_24bpp = 9, 62 pxa_lcdc_25bpp = 10, 63 } bpp; 64 65 uint32_t control[6]; 66 uint32_t status[2]; 67 uint32_t ovl1c[2]; 68 uint32_t ovl2c[2]; 69 uint32_t ccr; 70 uint32_t cmdcr; 71 uint32_t trgbr; 72 uint32_t tcr; 73 uint32_t liidr; 74 uint8_t bscntr; 75 76 struct DMAChannel dma_ch[7]; 77 78 qemu_irq vsync_cb; 79 int orientation; 80 }; 81 82 typedef struct QEMU_PACKED { 83 uint32_t fdaddr; 84 uint32_t fsaddr; 85 uint32_t fidr; 86 uint32_t ldcmd; 87 } PXAFrameDescriptor; 88 89 #define LCCR0 0x000 /* LCD Controller Control register 0 */ 90 #define LCCR1 0x004 /* LCD Controller Control register 1 */ 91 #define LCCR2 0x008 /* LCD Controller Control register 2 */ 92 #define LCCR3 0x00c /* LCD Controller Control register 3 */ 93 #define LCCR4 0x010 /* LCD Controller Control register 4 */ 94 #define LCCR5 0x014 /* LCD Controller Control register 5 */ 95 96 #define FBR0 0x020 /* DMA Channel 0 Frame Branch register */ 97 #define FBR1 0x024 /* DMA Channel 1 Frame Branch register */ 98 #define FBR2 0x028 /* DMA Channel 2 Frame Branch register */ 99 #define FBR3 0x02c /* DMA Channel 3 Frame Branch register */ 100 #define FBR4 0x030 /* DMA Channel 4 Frame Branch register */ 101 #define FBR5 0x110 /* DMA Channel 5 Frame Branch register */ 102 #define FBR6 0x114 /* DMA Channel 6 Frame Branch register */ 103 104 #define LCSR1 0x034 /* LCD Controller Status register 1 */ 105 #define LCSR0 0x038 /* LCD Controller Status register 0 */ 106 #define LIIDR 0x03c /* LCD Controller Interrupt ID register */ 107 108 #define TRGBR 0x040 /* TMED RGB Seed register */ 109 #define TCR 0x044 /* TMED Control register */ 110 111 #define OVL1C1 0x050 /* Overlay 1 Control register 1 */ 112 #define OVL1C2 0x060 /* Overlay 1 Control register 2 */ 113 #define OVL2C1 0x070 /* Overlay 2 Control register 1 */ 114 #define OVL2C2 0x080 /* Overlay 2 Control register 2 */ 115 #define CCR 0x090 /* Cursor Control register */ 116 117 #define CMDCR 0x100 /* Command Control register */ 118 #define PRSR 0x104 /* Panel Read Status register */ 119 120 #define PXA_LCDDMA_CHANS 7 121 #define DMA_FDADR 0x00 /* Frame Descriptor Address register */ 122 #define DMA_FSADR 0x04 /* Frame Source Address register */ 123 #define DMA_FIDR 0x08 /* Frame ID register */ 124 #define DMA_LDCMD 0x0c /* Command register */ 125 126 /* LCD Buffer Strength Control register */ 127 #define BSCNTR 0x04000054 128 129 /* Bitfield masks */ 130 #define LCCR0_ENB (1 << 0) 131 #define LCCR0_CMS (1 << 1) 132 #define LCCR0_SDS (1 << 2) 133 #define LCCR0_LDM (1 << 3) 134 #define LCCR0_SOFM0 (1 << 4) 135 #define LCCR0_IUM (1 << 5) 136 #define LCCR0_EOFM0 (1 << 6) 137 #define LCCR0_PAS (1 << 7) 138 #define LCCR0_DPD (1 << 9) 139 #define LCCR0_DIS (1 << 10) 140 #define LCCR0_QDM (1 << 11) 141 #define LCCR0_PDD (0xff << 12) 142 #define LCCR0_BSM0 (1 << 20) 143 #define LCCR0_OUM (1 << 21) 144 #define LCCR0_LCDT (1 << 22) 145 #define LCCR0_RDSTM (1 << 23) 146 #define LCCR0_CMDIM (1 << 24) 147 #define LCCR0_OUC (1 << 25) 148 #define LCCR0_LDDALT (1 << 26) 149 #define LCCR1_PPL(x) ((x) & 0x3ff) 150 #define LCCR2_LPP(x) ((x) & 0x3ff) 151 #define LCCR3_API (15 << 16) 152 #define LCCR3_BPP(x) ((((x) >> 24) & 7) | (((x) >> 26) & 8)) 153 #define LCCR3_PDFOR(x) (((x) >> 30) & 3) 154 #define LCCR4_K1(x) (((x) >> 0) & 7) 155 #define LCCR4_K2(x) (((x) >> 3) & 7) 156 #define LCCR4_K3(x) (((x) >> 6) & 7) 157 #define LCCR4_PALFOR(x) (((x) >> 15) & 3) 158 #define LCCR5_SOFM(ch) (1 << (ch - 1)) 159 #define LCCR5_EOFM(ch) (1 << (ch + 7)) 160 #define LCCR5_BSM(ch) (1 << (ch + 15)) 161 #define LCCR5_IUM(ch) (1 << (ch + 23)) 162 #define OVLC1_EN (1 << 31) 163 #define CCR_CEN (1 << 31) 164 #define FBR_BRA (1 << 0) 165 #define FBR_BINT (1 << 1) 166 #define FBR_SRCADDR (0xfffffff << 4) 167 #define LCSR0_LDD (1 << 0) 168 #define LCSR0_SOF0 (1 << 1) 169 #define LCSR0_BER (1 << 2) 170 #define LCSR0_ABC (1 << 3) 171 #define LCSR0_IU0 (1 << 4) 172 #define LCSR0_IU1 (1 << 5) 173 #define LCSR0_OU (1 << 6) 174 #define LCSR0_QD (1 << 7) 175 #define LCSR0_EOF0 (1 << 8) 176 #define LCSR0_BS0 (1 << 9) 177 #define LCSR0_SINT (1 << 10) 178 #define LCSR0_RDST (1 << 11) 179 #define LCSR0_CMDINT (1 << 12) 180 #define LCSR0_BERCH(x) (((x) & 7) << 28) 181 #define LCSR1_SOF(ch) (1 << (ch - 1)) 182 #define LCSR1_EOF(ch) (1 << (ch + 7)) 183 #define LCSR1_BS(ch) (1 << (ch + 15)) 184 #define LCSR1_IU(ch) (1 << (ch + 23)) 185 #define LDCMD_LENGTH(x) ((x) & 0x001ffffc) 186 #define LDCMD_EOFINT (1 << 21) 187 #define LDCMD_SOFINT (1 << 22) 188 #define LDCMD_PAL (1 << 26) 189 190 /* Route internal interrupt lines to the global IC */ 191 static void pxa2xx_lcdc_int_update(PXA2xxLCDState *s) 192 { 193 int level = 0; 194 level |= (s->status[0] & LCSR0_LDD) && !(s->control[0] & LCCR0_LDM); 195 level |= (s->status[0] & LCSR0_SOF0) && !(s->control[0] & LCCR0_SOFM0); 196 level |= (s->status[0] & LCSR0_IU0) && !(s->control[0] & LCCR0_IUM); 197 level |= (s->status[0] & LCSR0_IU1) && !(s->control[5] & LCCR5_IUM(1)); 198 level |= (s->status[0] & LCSR0_OU) && !(s->control[0] & LCCR0_OUM); 199 level |= (s->status[0] & LCSR0_QD) && !(s->control[0] & LCCR0_QDM); 200 level |= (s->status[0] & LCSR0_EOF0) && !(s->control[0] & LCCR0_EOFM0); 201 level |= (s->status[0] & LCSR0_BS0) && !(s->control[0] & LCCR0_BSM0); 202 level |= (s->status[0] & LCSR0_RDST) && !(s->control[0] & LCCR0_RDSTM); 203 level |= (s->status[0] & LCSR0_CMDINT) && !(s->control[0] & LCCR0_CMDIM); 204 level |= (s->status[1] & ~s->control[5]); 205 206 qemu_set_irq(s->irq, !!level); 207 s->irqlevel = level; 208 } 209 210 /* Set Branch Status interrupt high and poke associated registers */ 211 static inline void pxa2xx_dma_bs_set(PXA2xxLCDState *s, int ch) 212 { 213 int unmasked; 214 if (ch == 0) { 215 s->status[0] |= LCSR0_BS0; 216 unmasked = !(s->control[0] & LCCR0_BSM0); 217 } else { 218 s->status[1] |= LCSR1_BS(ch); 219 unmasked = !(s->control[5] & LCCR5_BSM(ch)); 220 } 221 222 if (unmasked) { 223 if (s->irqlevel) 224 s->status[0] |= LCSR0_SINT; 225 else 226 s->liidr = s->dma_ch[ch].id; 227 } 228 } 229 230 /* Set Start Of Frame Status interrupt high and poke associated registers */ 231 static inline void pxa2xx_dma_sof_set(PXA2xxLCDState *s, int ch) 232 { 233 int unmasked; 234 if (!(s->dma_ch[ch].command & LDCMD_SOFINT)) 235 return; 236 237 if (ch == 0) { 238 s->status[0] |= LCSR0_SOF0; 239 unmasked = !(s->control[0] & LCCR0_SOFM0); 240 } else { 241 s->status[1] |= LCSR1_SOF(ch); 242 unmasked = !(s->control[5] & LCCR5_SOFM(ch)); 243 } 244 245 if (unmasked) { 246 if (s->irqlevel) 247 s->status[0] |= LCSR0_SINT; 248 else 249 s->liidr = s->dma_ch[ch].id; 250 } 251 } 252 253 /* Set End Of Frame Status interrupt high and poke associated registers */ 254 static inline void pxa2xx_dma_eof_set(PXA2xxLCDState *s, int ch) 255 { 256 int unmasked; 257 if (!(s->dma_ch[ch].command & LDCMD_EOFINT)) 258 return; 259 260 if (ch == 0) { 261 s->status[0] |= LCSR0_EOF0; 262 unmasked = !(s->control[0] & LCCR0_EOFM0); 263 } else { 264 s->status[1] |= LCSR1_EOF(ch); 265 unmasked = !(s->control[5] & LCCR5_EOFM(ch)); 266 } 267 268 if (unmasked) { 269 if (s->irqlevel) 270 s->status[0] |= LCSR0_SINT; 271 else 272 s->liidr = s->dma_ch[ch].id; 273 } 274 } 275 276 /* Set Bus Error Status interrupt high and poke associated registers */ 277 static inline void pxa2xx_dma_ber_set(PXA2xxLCDState *s, int ch) 278 { 279 s->status[0] |= LCSR0_BERCH(ch) | LCSR0_BER; 280 if (s->irqlevel) 281 s->status[0] |= LCSR0_SINT; 282 else 283 s->liidr = s->dma_ch[ch].id; 284 } 285 286 /* Load new Frame Descriptors from DMA */ 287 static void pxa2xx_descriptor_load(PXA2xxLCDState *s) 288 { 289 PXAFrameDescriptor desc; 290 hwaddr descptr; 291 int i; 292 293 for (i = 0; i < PXA_LCDDMA_CHANS; i ++) { 294 s->dma_ch[i].source = 0; 295 296 if (!s->dma_ch[i].up) 297 continue; 298 299 if (s->dma_ch[i].branch & FBR_BRA) { 300 descptr = s->dma_ch[i].branch & FBR_SRCADDR; 301 if (s->dma_ch[i].branch & FBR_BINT) 302 pxa2xx_dma_bs_set(s, i); 303 s->dma_ch[i].branch &= ~FBR_BRA; 304 } else 305 descptr = s->dma_ch[i].descriptor; 306 307 if (!((descptr >= PXA2XX_SDRAM_BASE && descptr + 308 sizeof(desc) <= PXA2XX_SDRAM_BASE + ram_size) || 309 (descptr >= PXA2XX_INTERNAL_BASE && descptr + sizeof(desc) <= 310 PXA2XX_INTERNAL_BASE + PXA2XX_INTERNAL_SIZE))) { 311 continue; 312 } 313 314 cpu_physical_memory_read(descptr, &desc, sizeof(desc)); 315 s->dma_ch[i].descriptor = le32_to_cpu(desc.fdaddr); 316 s->dma_ch[i].source = le32_to_cpu(desc.fsaddr); 317 s->dma_ch[i].id = le32_to_cpu(desc.fidr); 318 s->dma_ch[i].command = le32_to_cpu(desc.ldcmd); 319 } 320 } 321 322 static uint64_t pxa2xx_lcdc_read(void *opaque, hwaddr offset, 323 unsigned size) 324 { 325 PXA2xxLCDState *s = (PXA2xxLCDState *) opaque; 326 int ch; 327 328 switch (offset) { 329 case LCCR0: 330 return s->control[0]; 331 case LCCR1: 332 return s->control[1]; 333 case LCCR2: 334 return s->control[2]; 335 case LCCR3: 336 return s->control[3]; 337 case LCCR4: 338 return s->control[4]; 339 case LCCR5: 340 return s->control[5]; 341 342 case OVL1C1: 343 return s->ovl1c[0]; 344 case OVL1C2: 345 return s->ovl1c[1]; 346 case OVL2C1: 347 return s->ovl2c[0]; 348 case OVL2C2: 349 return s->ovl2c[1]; 350 351 case CCR: 352 return s->ccr; 353 354 case CMDCR: 355 return s->cmdcr; 356 357 case TRGBR: 358 return s->trgbr; 359 case TCR: 360 return s->tcr; 361 362 case 0x200 ... 0x1000: /* DMA per-channel registers */ 363 ch = (offset - 0x200) >> 4; 364 if (!(ch >= 0 && ch < PXA_LCDDMA_CHANS)) 365 goto fail; 366 367 switch (offset & 0xf) { 368 case DMA_FDADR: 369 return s->dma_ch[ch].descriptor; 370 case DMA_FSADR: 371 return s->dma_ch[ch].source; 372 case DMA_FIDR: 373 return s->dma_ch[ch].id; 374 case DMA_LDCMD: 375 return s->dma_ch[ch].command; 376 default: 377 goto fail; 378 } 379 380 case FBR0: 381 return s->dma_ch[0].branch; 382 case FBR1: 383 return s->dma_ch[1].branch; 384 case FBR2: 385 return s->dma_ch[2].branch; 386 case FBR3: 387 return s->dma_ch[3].branch; 388 case FBR4: 389 return s->dma_ch[4].branch; 390 case FBR5: 391 return s->dma_ch[5].branch; 392 case FBR6: 393 return s->dma_ch[6].branch; 394 395 case BSCNTR: 396 return s->bscntr; 397 398 case PRSR: 399 return 0; 400 401 case LCSR0: 402 return s->status[0]; 403 case LCSR1: 404 return s->status[1]; 405 case LIIDR: 406 return s->liidr; 407 408 default: 409 fail: 410 hw_error("%s: Bad offset " REG_FMT "\n", __func__, offset); 411 } 412 413 return 0; 414 } 415 416 static void pxa2xx_lcdc_write(void *opaque, hwaddr offset, 417 uint64_t value, unsigned size) 418 { 419 PXA2xxLCDState *s = (PXA2xxLCDState *) opaque; 420 int ch; 421 422 switch (offset) { 423 case LCCR0: 424 /* ACK Quick Disable done */ 425 if ((s->control[0] & LCCR0_ENB) && !(value & LCCR0_ENB)) 426 s->status[0] |= LCSR0_QD; 427 428 if (!(s->control[0] & LCCR0_LCDT) && (value & LCCR0_LCDT)) 429 printf("%s: internal frame buffer unsupported\n", __func__); 430 431 if ((s->control[3] & LCCR3_API) && 432 (value & LCCR0_ENB) && !(value & LCCR0_LCDT)) 433 s->status[0] |= LCSR0_ABC; 434 435 s->control[0] = value & 0x07ffffff; 436 pxa2xx_lcdc_int_update(s); 437 438 s->dma_ch[0].up = !!(value & LCCR0_ENB); 439 s->dma_ch[1].up = (s->ovl1c[0] & OVLC1_EN) || (value & LCCR0_SDS); 440 break; 441 442 case LCCR1: 443 s->control[1] = value; 444 break; 445 446 case LCCR2: 447 s->control[2] = value; 448 break; 449 450 case LCCR3: 451 s->control[3] = value & 0xefffffff; 452 s->bpp = LCCR3_BPP(value); 453 break; 454 455 case LCCR4: 456 s->control[4] = value & 0x83ff81ff; 457 break; 458 459 case LCCR5: 460 s->control[5] = value & 0x3f3f3f3f; 461 break; 462 463 case OVL1C1: 464 if (!(s->ovl1c[0] & OVLC1_EN) && (value & OVLC1_EN)) 465 printf("%s: Overlay 1 not supported\n", __func__); 466 467 s->ovl1c[0] = value & 0x80ffffff; 468 s->dma_ch[1].up = (value & OVLC1_EN) || (s->control[0] & LCCR0_SDS); 469 break; 470 471 case OVL1C2: 472 s->ovl1c[1] = value & 0x000fffff; 473 break; 474 475 case OVL2C1: 476 if (!(s->ovl2c[0] & OVLC1_EN) && (value & OVLC1_EN)) 477 printf("%s: Overlay 2 not supported\n", __func__); 478 479 s->ovl2c[0] = value & 0x80ffffff; 480 s->dma_ch[2].up = !!(value & OVLC1_EN); 481 s->dma_ch[3].up = !!(value & OVLC1_EN); 482 s->dma_ch[4].up = !!(value & OVLC1_EN); 483 break; 484 485 case OVL2C2: 486 s->ovl2c[1] = value & 0x007fffff; 487 break; 488 489 case CCR: 490 if (!(s->ccr & CCR_CEN) && (value & CCR_CEN)) 491 printf("%s: Hardware cursor unimplemented\n", __func__); 492 493 s->ccr = value & 0x81ffffe7; 494 s->dma_ch[5].up = !!(value & CCR_CEN); 495 break; 496 497 case CMDCR: 498 s->cmdcr = value & 0xff; 499 break; 500 501 case TRGBR: 502 s->trgbr = value & 0x00ffffff; 503 break; 504 505 case TCR: 506 s->tcr = value & 0x7fff; 507 break; 508 509 case 0x200 ... 0x1000: /* DMA per-channel registers */ 510 ch = (offset - 0x200) >> 4; 511 if (!(ch >= 0 && ch < PXA_LCDDMA_CHANS)) 512 goto fail; 513 514 switch (offset & 0xf) { 515 case DMA_FDADR: 516 s->dma_ch[ch].descriptor = value & 0xfffffff0; 517 break; 518 519 default: 520 goto fail; 521 } 522 break; 523 524 case FBR0: 525 s->dma_ch[0].branch = value & 0xfffffff3; 526 break; 527 case FBR1: 528 s->dma_ch[1].branch = value & 0xfffffff3; 529 break; 530 case FBR2: 531 s->dma_ch[2].branch = value & 0xfffffff3; 532 break; 533 case FBR3: 534 s->dma_ch[3].branch = value & 0xfffffff3; 535 break; 536 case FBR4: 537 s->dma_ch[4].branch = value & 0xfffffff3; 538 break; 539 case FBR5: 540 s->dma_ch[5].branch = value & 0xfffffff3; 541 break; 542 case FBR6: 543 s->dma_ch[6].branch = value & 0xfffffff3; 544 break; 545 546 case BSCNTR: 547 s->bscntr = value & 0xf; 548 break; 549 550 case PRSR: 551 break; 552 553 case LCSR0: 554 s->status[0] &= ~(value & 0xfff); 555 if (value & LCSR0_BER) 556 s->status[0] &= ~LCSR0_BERCH(7); 557 break; 558 559 case LCSR1: 560 s->status[1] &= ~(value & 0x3e3f3f); 561 break; 562 563 default: 564 fail: 565 hw_error("%s: Bad offset " REG_FMT "\n", __func__, offset); 566 } 567 } 568 569 static const MemoryRegionOps pxa2xx_lcdc_ops = { 570 .read = pxa2xx_lcdc_read, 571 .write = pxa2xx_lcdc_write, 572 .endianness = DEVICE_NATIVE_ENDIAN, 573 }; 574 575 /* Load new palette for a given DMA channel, convert to internal format */ 576 static void pxa2xx_palette_parse(PXA2xxLCDState *s, int ch, int bpp) 577 { 578 DisplaySurface *surface = qemu_console_surface(s->con); 579 int i, n, format, r, g, b, alpha; 580 uint32_t *dest; 581 uint8_t *src; 582 s->pal_for = LCCR4_PALFOR(s->control[4]); 583 format = s->pal_for; 584 585 switch (bpp) { 586 case pxa_lcdc_2bpp: 587 n = 4; 588 break; 589 case pxa_lcdc_4bpp: 590 n = 16; 591 break; 592 case pxa_lcdc_8bpp: 593 n = 256; 594 break; 595 default: 596 return; 597 } 598 599 src = (uint8_t *) s->dma_ch[ch].pbuffer; 600 dest = (uint32_t *) s->dma_ch[ch].palette; 601 alpha = r = g = b = 0; 602 603 for (i = 0; i < n; i ++) { 604 switch (format) { 605 case 0: /* 16 bpp, no transparency */ 606 alpha = 0; 607 if (s->control[0] & LCCR0_CMS) { 608 r = g = b = *(uint16_t *) src & 0xff; 609 } 610 else { 611 r = (*(uint16_t *) src & 0xf800) >> 8; 612 g = (*(uint16_t *) src & 0x07e0) >> 3; 613 b = (*(uint16_t *) src & 0x001f) << 3; 614 } 615 src += 2; 616 break; 617 case 1: /* 16 bpp plus transparency */ 618 alpha = *(uint32_t *) src & (1 << 24); 619 if (s->control[0] & LCCR0_CMS) 620 r = g = b = *(uint32_t *) src & 0xff; 621 else { 622 r = (*(uint32_t *) src & 0xf80000) >> 16; 623 g = (*(uint32_t *) src & 0x00fc00) >> 8; 624 b = (*(uint32_t *) src & 0x0000f8); 625 } 626 src += 4; 627 break; 628 case 2: /* 18 bpp plus transparency */ 629 alpha = *(uint32_t *) src & (1 << 24); 630 if (s->control[0] & LCCR0_CMS) 631 r = g = b = *(uint32_t *) src & 0xff; 632 else { 633 r = (*(uint32_t *) src & 0xfc0000) >> 16; 634 g = (*(uint32_t *) src & 0x00fc00) >> 8; 635 b = (*(uint32_t *) src & 0x0000fc); 636 } 637 src += 4; 638 break; 639 case 3: /* 24 bpp plus transparency */ 640 alpha = *(uint32_t *) src & (1 << 24); 641 if (s->control[0] & LCCR0_CMS) 642 r = g = b = *(uint32_t *) src & 0xff; 643 else { 644 r = (*(uint32_t *) src & 0xff0000) >> 16; 645 g = (*(uint32_t *) src & 0x00ff00) >> 8; 646 b = (*(uint32_t *) src & 0x0000ff); 647 } 648 src += 4; 649 break; 650 } 651 switch (surface_bits_per_pixel(surface)) { 652 case 8: 653 *dest = rgb_to_pixel8(r, g, b) | alpha; 654 break; 655 case 15: 656 *dest = rgb_to_pixel15(r, g, b) | alpha; 657 break; 658 case 16: 659 *dest = rgb_to_pixel16(r, g, b) | alpha; 660 break; 661 case 24: 662 *dest = rgb_to_pixel24(r, g, b) | alpha; 663 break; 664 case 32: 665 *dest = rgb_to_pixel32(r, g, b) | alpha; 666 break; 667 } 668 dest ++; 669 } 670 } 671 672 static void pxa2xx_lcdc_dma0_redraw_rot0(PXA2xxLCDState *s, 673 hwaddr addr, int *miny, int *maxy) 674 { 675 DisplaySurface *surface = qemu_console_surface(s->con); 676 int src_width, dest_width; 677 drawfn fn = NULL; 678 if (s->dest_width) 679 fn = s->line_fn[s->transp][s->bpp]; 680 if (!fn) 681 return; 682 683 src_width = (s->xres + 3) & ~3; /* Pad to a 4 pixels multiple */ 684 if (s->bpp == pxa_lcdc_19pbpp || s->bpp == pxa_lcdc_18pbpp) 685 src_width *= 3; 686 else if (s->bpp > pxa_lcdc_16bpp) 687 src_width *= 4; 688 else if (s->bpp > pxa_lcdc_8bpp) 689 src_width *= 2; 690 691 dest_width = s->xres * s->dest_width; 692 *miny = 0; 693 if (s->invalidated) { 694 framebuffer_update_memory_section(&s->fbsection, s->sysmem, 695 addr, s->yres, src_width); 696 } 697 framebuffer_update_display(surface, &s->fbsection, s->xres, s->yres, 698 src_width, dest_width, s->dest_width, 699 s->invalidated, 700 fn, s->dma_ch[0].palette, miny, maxy); 701 } 702 703 static void pxa2xx_lcdc_dma0_redraw_rot90(PXA2xxLCDState *s, 704 hwaddr addr, int *miny, int *maxy) 705 { 706 DisplaySurface *surface = qemu_console_surface(s->con); 707 int src_width, dest_width; 708 drawfn fn = NULL; 709 if (s->dest_width) 710 fn = s->line_fn[s->transp][s->bpp]; 711 if (!fn) 712 return; 713 714 src_width = (s->xres + 3) & ~3; /* Pad to a 4 pixels multiple */ 715 if (s->bpp == pxa_lcdc_19pbpp || s->bpp == pxa_lcdc_18pbpp) 716 src_width *= 3; 717 else if (s->bpp > pxa_lcdc_16bpp) 718 src_width *= 4; 719 else if (s->bpp > pxa_lcdc_8bpp) 720 src_width *= 2; 721 722 dest_width = s->yres * s->dest_width; 723 *miny = 0; 724 if (s->invalidated) { 725 framebuffer_update_memory_section(&s->fbsection, s->sysmem, 726 addr, s->yres, src_width); 727 } 728 framebuffer_update_display(surface, &s->fbsection, s->xres, s->yres, 729 src_width, s->dest_width, -dest_width, 730 s->invalidated, 731 fn, s->dma_ch[0].palette, 732 miny, maxy); 733 } 734 735 static void pxa2xx_lcdc_dma0_redraw_rot180(PXA2xxLCDState *s, 736 hwaddr addr, int *miny, int *maxy) 737 { 738 DisplaySurface *surface = qemu_console_surface(s->con); 739 int src_width, dest_width; 740 drawfn fn = NULL; 741 if (s->dest_width) { 742 fn = s->line_fn[s->transp][s->bpp]; 743 } 744 if (!fn) { 745 return; 746 } 747 748 src_width = (s->xres + 3) & ~3; /* Pad to a 4 pixels multiple */ 749 if (s->bpp == pxa_lcdc_19pbpp || s->bpp == pxa_lcdc_18pbpp) { 750 src_width *= 3; 751 } else if (s->bpp > pxa_lcdc_16bpp) { 752 src_width *= 4; 753 } else if (s->bpp > pxa_lcdc_8bpp) { 754 src_width *= 2; 755 } 756 757 dest_width = s->xres * s->dest_width; 758 *miny = 0; 759 if (s->invalidated) { 760 framebuffer_update_memory_section(&s->fbsection, s->sysmem, 761 addr, s->yres, src_width); 762 } 763 framebuffer_update_display(surface, &s->fbsection, s->xres, s->yres, 764 src_width, -dest_width, -s->dest_width, 765 s->invalidated, 766 fn, s->dma_ch[0].palette, miny, maxy); 767 } 768 769 static void pxa2xx_lcdc_dma0_redraw_rot270(PXA2xxLCDState *s, 770 hwaddr addr, int *miny, int *maxy) 771 { 772 DisplaySurface *surface = qemu_console_surface(s->con); 773 int src_width, dest_width; 774 drawfn fn = NULL; 775 if (s->dest_width) { 776 fn = s->line_fn[s->transp][s->bpp]; 777 } 778 if (!fn) { 779 return; 780 } 781 782 src_width = (s->xres + 3) & ~3; /* Pad to a 4 pixels multiple */ 783 if (s->bpp == pxa_lcdc_19pbpp || s->bpp == pxa_lcdc_18pbpp) { 784 src_width *= 3; 785 } else if (s->bpp > pxa_lcdc_16bpp) { 786 src_width *= 4; 787 } else if (s->bpp > pxa_lcdc_8bpp) { 788 src_width *= 2; 789 } 790 791 dest_width = s->yres * s->dest_width; 792 *miny = 0; 793 if (s->invalidated) { 794 framebuffer_update_memory_section(&s->fbsection, s->sysmem, 795 addr, s->yres, src_width); 796 } 797 framebuffer_update_display(surface, &s->fbsection, s->xres, s->yres, 798 src_width, -s->dest_width, dest_width, 799 s->invalidated, 800 fn, s->dma_ch[0].palette, 801 miny, maxy); 802 } 803 804 static void pxa2xx_lcdc_resize(PXA2xxLCDState *s) 805 { 806 int width, height; 807 if (!(s->control[0] & LCCR0_ENB)) 808 return; 809 810 width = LCCR1_PPL(s->control[1]) + 1; 811 height = LCCR2_LPP(s->control[2]) + 1; 812 813 if (width != s->xres || height != s->yres) { 814 if (s->orientation == 90 || s->orientation == 270) { 815 qemu_console_resize(s->con, height, width); 816 } else { 817 qemu_console_resize(s->con, width, height); 818 } 819 s->invalidated = 1; 820 s->xres = width; 821 s->yres = height; 822 } 823 } 824 825 static void pxa2xx_update_display(void *opaque) 826 { 827 PXA2xxLCDState *s = (PXA2xxLCDState *) opaque; 828 hwaddr fbptr; 829 int miny, maxy; 830 int ch; 831 if (!(s->control[0] & LCCR0_ENB)) 832 return; 833 834 pxa2xx_descriptor_load(s); 835 836 pxa2xx_lcdc_resize(s); 837 miny = s->yres; 838 maxy = 0; 839 s->transp = s->dma_ch[2].up || s->dma_ch[3].up; 840 /* Note: With overlay planes the order depends on LCCR0 bit 25. */ 841 for (ch = 0; ch < PXA_LCDDMA_CHANS; ch ++) 842 if (s->dma_ch[ch].up) { 843 if (!s->dma_ch[ch].source) { 844 pxa2xx_dma_ber_set(s, ch); 845 continue; 846 } 847 fbptr = s->dma_ch[ch].source; 848 if (!((fbptr >= PXA2XX_SDRAM_BASE && 849 fbptr <= PXA2XX_SDRAM_BASE + ram_size) || 850 (fbptr >= PXA2XX_INTERNAL_BASE && 851 fbptr <= PXA2XX_INTERNAL_BASE + PXA2XX_INTERNAL_SIZE))) { 852 pxa2xx_dma_ber_set(s, ch); 853 continue; 854 } 855 856 if (s->dma_ch[ch].command & LDCMD_PAL) { 857 cpu_physical_memory_read(fbptr, s->dma_ch[ch].pbuffer, 858 MAX(LDCMD_LENGTH(s->dma_ch[ch].command), 859 sizeof(s->dma_ch[ch].pbuffer))); 860 pxa2xx_palette_parse(s, ch, s->bpp); 861 } else { 862 /* Do we need to reparse palette */ 863 if (LCCR4_PALFOR(s->control[4]) != s->pal_for) 864 pxa2xx_palette_parse(s, ch, s->bpp); 865 866 /* ACK frame start */ 867 pxa2xx_dma_sof_set(s, ch); 868 869 s->dma_ch[ch].redraw(s, fbptr, &miny, &maxy); 870 s->invalidated = 0; 871 872 /* ACK frame completed */ 873 pxa2xx_dma_eof_set(s, ch); 874 } 875 } 876 877 if (s->control[0] & LCCR0_DIS) { 878 /* ACK last frame completed */ 879 s->control[0] &= ~LCCR0_ENB; 880 s->status[0] |= LCSR0_LDD; 881 } 882 883 if (miny >= 0) { 884 switch (s->orientation) { 885 case 0: 886 dpy_gfx_update(s->con, 0, miny, s->xres, maxy - miny + 1); 887 break; 888 case 90: 889 dpy_gfx_update(s->con, miny, 0, maxy - miny + 1, s->xres); 890 break; 891 case 180: 892 maxy = s->yres - maxy - 1; 893 miny = s->yres - miny - 1; 894 dpy_gfx_update(s->con, 0, maxy, s->xres, miny - maxy + 1); 895 break; 896 case 270: 897 maxy = s->yres - maxy - 1; 898 miny = s->yres - miny - 1; 899 dpy_gfx_update(s->con, maxy, 0, miny - maxy + 1, s->xres); 900 break; 901 } 902 } 903 pxa2xx_lcdc_int_update(s); 904 905 qemu_irq_raise(s->vsync_cb); 906 } 907 908 static void pxa2xx_invalidate_display(void *opaque) 909 { 910 PXA2xxLCDState *s = (PXA2xxLCDState *) opaque; 911 s->invalidated = 1; 912 } 913 914 static void pxa2xx_lcdc_orientation(void *opaque, int angle) 915 { 916 PXA2xxLCDState *s = (PXA2xxLCDState *) opaque; 917 918 switch (angle) { 919 case 0: 920 s->dma_ch[0].redraw = pxa2xx_lcdc_dma0_redraw_rot0; 921 break; 922 case 90: 923 s->dma_ch[0].redraw = pxa2xx_lcdc_dma0_redraw_rot90; 924 break; 925 case 180: 926 s->dma_ch[0].redraw = pxa2xx_lcdc_dma0_redraw_rot180; 927 break; 928 case 270: 929 s->dma_ch[0].redraw = pxa2xx_lcdc_dma0_redraw_rot270; 930 break; 931 } 932 933 s->orientation = angle; 934 s->xres = s->yres = -1; 935 pxa2xx_lcdc_resize(s); 936 } 937 938 static const VMStateDescription vmstate_dma_channel = { 939 .name = "dma_channel", 940 .version_id = 0, 941 .minimum_version_id = 0, 942 .fields = (VMStateField[]) { 943 VMSTATE_UINT32(branch, struct DMAChannel), 944 VMSTATE_UINT8(up, struct DMAChannel), 945 VMSTATE_BUFFER(pbuffer, struct DMAChannel), 946 VMSTATE_UINT32(descriptor, struct DMAChannel), 947 VMSTATE_UINT32(source, struct DMAChannel), 948 VMSTATE_UINT32(id, struct DMAChannel), 949 VMSTATE_UINT32(command, struct DMAChannel), 950 VMSTATE_END_OF_LIST() 951 } 952 }; 953 954 static int pxa2xx_lcdc_post_load(void *opaque, int version_id) 955 { 956 PXA2xxLCDState *s = opaque; 957 958 s->bpp = LCCR3_BPP(s->control[3]); 959 s->xres = s->yres = s->pal_for = -1; 960 961 return 0; 962 } 963 964 static const VMStateDescription vmstate_pxa2xx_lcdc = { 965 .name = "pxa2xx_lcdc", 966 .version_id = 0, 967 .minimum_version_id = 0, 968 .post_load = pxa2xx_lcdc_post_load, 969 .fields = (VMStateField[]) { 970 VMSTATE_INT32(irqlevel, PXA2xxLCDState), 971 VMSTATE_INT32(transp, PXA2xxLCDState), 972 VMSTATE_UINT32_ARRAY(control, PXA2xxLCDState, 6), 973 VMSTATE_UINT32_ARRAY(status, PXA2xxLCDState, 2), 974 VMSTATE_UINT32_ARRAY(ovl1c, PXA2xxLCDState, 2), 975 VMSTATE_UINT32_ARRAY(ovl2c, PXA2xxLCDState, 2), 976 VMSTATE_UINT32(ccr, PXA2xxLCDState), 977 VMSTATE_UINT32(cmdcr, PXA2xxLCDState), 978 VMSTATE_UINT32(trgbr, PXA2xxLCDState), 979 VMSTATE_UINT32(tcr, PXA2xxLCDState), 980 VMSTATE_UINT32(liidr, PXA2xxLCDState), 981 VMSTATE_UINT8(bscntr, PXA2xxLCDState), 982 VMSTATE_STRUCT_ARRAY(dma_ch, PXA2xxLCDState, 7, 0, 983 vmstate_dma_channel, struct DMAChannel), 984 VMSTATE_END_OF_LIST() 985 } 986 }; 987 988 #define BITS 8 989 #include "pxa2xx_template.h" 990 #define BITS 15 991 #include "pxa2xx_template.h" 992 #define BITS 16 993 #include "pxa2xx_template.h" 994 #define BITS 24 995 #include "pxa2xx_template.h" 996 #define BITS 32 997 #include "pxa2xx_template.h" 998 999 static const GraphicHwOps pxa2xx_ops = { 1000 .invalidate = pxa2xx_invalidate_display, 1001 .gfx_update = pxa2xx_update_display, 1002 }; 1003 1004 PXA2xxLCDState *pxa2xx_lcdc_init(MemoryRegion *sysmem, 1005 hwaddr base, qemu_irq irq) 1006 { 1007 PXA2xxLCDState *s; 1008 DisplaySurface *surface; 1009 1010 s = (PXA2xxLCDState *) g_malloc0(sizeof(PXA2xxLCDState)); 1011 s->invalidated = 1; 1012 s->irq = irq; 1013 s->sysmem = sysmem; 1014 1015 pxa2xx_lcdc_orientation(s, graphic_rotate); 1016 1017 memory_region_init_io(&s->iomem, NULL, &pxa2xx_lcdc_ops, s, 1018 "pxa2xx-lcd-controller", 0x00100000); 1019 memory_region_add_subregion(sysmem, base, &s->iomem); 1020 1021 s->con = graphic_console_init(NULL, 0, &pxa2xx_ops, s); 1022 surface = qemu_console_surface(s->con); 1023 1024 switch (surface_bits_per_pixel(surface)) { 1025 case 0: 1026 s->dest_width = 0; 1027 break; 1028 case 8: 1029 s->line_fn[0] = pxa2xx_draw_fn_8; 1030 s->line_fn[1] = pxa2xx_draw_fn_8t; 1031 s->dest_width = 1; 1032 break; 1033 case 15: 1034 s->line_fn[0] = pxa2xx_draw_fn_15; 1035 s->line_fn[1] = pxa2xx_draw_fn_15t; 1036 s->dest_width = 2; 1037 break; 1038 case 16: 1039 s->line_fn[0] = pxa2xx_draw_fn_16; 1040 s->line_fn[1] = pxa2xx_draw_fn_16t; 1041 s->dest_width = 2; 1042 break; 1043 case 24: 1044 s->line_fn[0] = pxa2xx_draw_fn_24; 1045 s->line_fn[1] = pxa2xx_draw_fn_24t; 1046 s->dest_width = 3; 1047 break; 1048 case 32: 1049 s->line_fn[0] = pxa2xx_draw_fn_32; 1050 s->line_fn[1] = pxa2xx_draw_fn_32t; 1051 s->dest_width = 4; 1052 break; 1053 default: 1054 fprintf(stderr, "%s: Bad color depth\n", __func__); 1055 exit(1); 1056 } 1057 1058 vmstate_register(NULL, 0, &vmstate_pxa2xx_lcdc, s); 1059 1060 return s; 1061 } 1062 1063 void pxa2xx_lcd_vsync_notifier(PXA2xxLCDState *s, qemu_irq handler) 1064 { 1065 s->vsync_cb = handler; 1066 } 1067