static void st7586_set_addr_win(struct st7586fb_par *par, int xs, int ys, int xe, int ye) { st7586_write_cmd(par, ST7586_CASET); st7586_write_data(par, 0x00); st7586_write_data(par, xs); st7586_write_data(par, 0x00); st7586_write_data(par, ((xe+2)/3)-1); st7586_write_cmd(par, ST7586_RASET); st7586_write_data(par, 0x00); st7586_write_data(par, ys); st7586_write_data(par, 0x00); st7586_write_data(par, ye-1); }
static void st7586_run_cfg_script(struct st7586fb_par *par) { int i = 0; int end_script = 0; do { switch (st7586_cfg_script[i].cmd) { case ST7586_START: break; case ST7586_CLR: st7586_clear_ddrram(par); break; case ST7586_CMD: st7586_write_cmd(par, st7586_cfg_script[i].data & 0xff); break; case ST7586_DATA: st7586_write_data(par, st7586_cfg_script[i].data & 0xff); break; case ST7586_DELAY: mdelay(st7586_cfg_script[i].data); break; case ST7586_END: end_script = 1; } i++; } while (!end_script); }
static void st7586_clear_ddrram(struct st7586fb_par *par) { u8 *buf; buf = kzalloc(128*128, GFP_KERNEL); st7586_write_cmd(par, ST7586_RAMWR); st7586_write_data_buf(par, buf, 128*128); kfree(buf); }
static int st7586fb_init_display(struct st7586fb_par *par) { st7586_reset(par); st7586_run_cfg_script(par); /* Set row/column data window */ st7586_set_addr_win(par, 0, 0, WIDTH, HEIGHT); st7586_write_cmd(par, ST7586_DISPON); return 0; }
void lcd_refresh_tsk(intptr_t unused) { struct st7586fb_par *par = ((struct fb_info *)(spidev.drvdata))->par; while (1) { #if 0 // For test struct fb_info *info = spidev.drvdata; u8 *vmem = info->screen_base; static int i = 0; vmem[i++] = 0xFF; if (i == (WIDTH+2)/3*HEIGHT) i = 0; #endif st7586_set_addr_win(par, 0, 0, WIDTH, HEIGHT); st7586_write_cmd(par, ST7586_RAMWR); /* Blast frame buffer to ST7586 internal display RAM */ ER ercd = st7586_write_data_buf(par, on_display_fb->pixels, (WIDTH + 2) / 3 * HEIGHT); assert(ercd == E_OK); #if 0 // Legacy code st7586fb_deferred_io(spidev.drvdata, NULL); #endif tslp_tsk(1000 / (LCD_FRAME_RATE)); } }
static void st7586fb_update_display(struct st7586fb_par *par) { const int bytes_per_row_in = par->info->fix.line_length; const int bytes_per_row_out = (WIDTH + 2) / 3; const int out_size = bytes_per_row_out * HEIGHT; int ret = 0, i = 0; int row, in_offset, out_offset; u8 *vmem = par->info->screen_base; u8 *vmem2; vmem2 = kmalloc(out_size, GFP_KERNEL); if (vmem2 == NULL) { pr_err("%s: spi_write failed to update display buffer - kmalloc failed\n", par->info->fix.id); return; } for (row = 0; row < HEIGHT; row++) { in_offset = row * bytes_per_row_in; out_offset = row * bytes_per_row_out; for (i = 0; i < bytes_per_row_in; i++) { vmem2[out_offset] = vmem[i + in_offset] & 0x01 ? 7 << 5 : 0; vmem2[out_offset] |= vmem[i + in_offset] & 0x02 ? 7 << 2 : 0; vmem2[out_offset] |= vmem[i + in_offset] & 0x04 ? 3 : 0; out_offset++; vmem2[out_offset] = vmem[i + in_offset] & 0x08 ? 7 << 5 : 0; vmem2[out_offset] |= vmem[i + in_offset] & 0x10 ? 7 << 2 : 0; vmem2[out_offset] |= vmem[i + in_offset] & 0x20 ? 3 : 0; out_offset++; vmem2[out_offset] = vmem[i + in_offset] & 0x40 ? 7 << 5 : 0; vmem2[out_offset] |= vmem[i + in_offset] & 0x80 ? 7 << 2 : 0; if (++i >= bytes_per_row_in) break; vmem2[out_offset] |= vmem[i + in_offset] & 0x01 ? 3 : 0; out_offset++; vmem2[out_offset] = vmem[i + in_offset] & 0x02 ? 7 << 5 : 0; vmem2[out_offset] |= vmem[i + in_offset] & 0x04 ? 7 << 2 : 0; vmem2[out_offset] |= vmem[i + in_offset] & 0x08 ? 3 : 0; out_offset++; vmem2[out_offset] = vmem[i + in_offset] & 0x10 ? 7 << 5 : 0; vmem2[out_offset] |= vmem[i + in_offset] & 0x20 ? 7 << 2 : 0; vmem2[out_offset] |= vmem[i + in_offset] & 0x40 ? 3 : 0; out_offset++; vmem2[out_offset] = vmem[i + in_offset] & 0x80 ? 7 << 5 : 0; if (++i >= bytes_per_row_in) break; vmem2[out_offset] |= vmem[i + in_offset] & 0x01 ? 7 << 2 : 0; vmem2[out_offset] |= vmem[i + in_offset] & 0x02 ? 3 : 0; out_offset++; vmem2[out_offset] = vmem[i + in_offset] & 0x04 ? 7 << 5 : 0; vmem2[out_offset] |= vmem[i + in_offset] & 0x08 ? 7 << 2 : 0; vmem2[out_offset] |= vmem[i + in_offset] & 0x10 ? 3 : 0; out_offset++; vmem2[out_offset] = vmem[i + in_offset] & 0x20 ? 7 << 5 : 0; vmem2[out_offset] |= vmem[i + in_offset] & 0x40 ? 7 << 2 : 0; vmem2[out_offset] |= vmem[i + in_offset] & 0x80 ? 3 : 0; out_offset++; } } st7586_set_addr_win(par, 0, 0, WIDTH, HEIGHT); st7586_write_cmd(par, ST7586_RAMWR); /* Blast framebuffer to ST7586 internal display RAM */ ret = st7586_write_data_buf(par, vmem2, out_size); kfree(vmem2); if (ret < 0) pr_err("%s: spi_write failed to update display buffer\n", par->info->fix.id); }