+ if ((dst != NULL) && (dst != (uchar *)logo_bmp))
+ free(dst);
+ return 0;
+}
+
+
+int lcd_init(uchar *lcd_reg, uchar *lcd_mem, S1D_REGS *regs, int reg_count,
+ uchar *logo_bmp, ulong len)
+{
+ int i;
+ ushort s1dReg;
+ uchar s1dValue;
+ int reg_byte_swap;
+
+ /*
+ * Detect epson
+ */
+ out_8(&lcd_reg[0], 0x00);
+ out_8(&lcd_reg[1], 0x00);
+
+ if (in_8(&lcd_reg[0]) == 0x1c) {
+ /*
+ * Big epson detected
+ */
+ reg_byte_swap = FALSE;
+ palette_index = 0x1e2;
+ palette_value = 0x1e4;
+ lcd_depth = 16;
+ puts("LCD: S1D13806");
+ } else if (in_8(&lcd_reg[1]) == 0x1c) {
+ /*
+ * Big epson detected (with register swap bug)
+ */
+ reg_byte_swap = TRUE;
+ palette_index = 0x1e3;
+ palette_value = 0x1e5;
+ lcd_depth = 16;
+ puts("LCD: S1D13806S");
+ } else if (in_8(&lcd_reg[0]) == 0x18) {
+ /*
+ * Small epson detected (704)
+ */
+ reg_byte_swap = FALSE;
+ palette_index = 0x15;
+ palette_value = 0x17;
+ lcd_depth = 8;
+ puts("LCD: S1D13704");
+ } else if (in_8(&lcd_reg[0x10000]) == 0x24) {
+ /*
+ * Small epson detected (705)
+ */
+ reg_byte_swap = FALSE;
+ palette_index = 0x15;
+ palette_value = 0x17;
+ lcd_depth = 8;
+ lcd_reg += 0x10000; /* add offset for 705 regs */
+ puts("LCD: S1D13705");
+ } else {
+ out_8(&lcd_reg[0x1a], 0x00);
+ udelay(1000);
+ if (in_8(&lcd_reg[1]) == 0x0c) {
+ /*
+ * S1D13505 detected
+ */
+ reg_byte_swap = TRUE;
+ palette_index = 0x25;
+ palette_value = 0x27;
+ lcd_depth = 16;
+
+ puts("LCD: S1D13505");
+ } else {
+ puts("LCD: No controller detected!\n");
+ return 1;
+ }
+ }
+
+ /*
+ * Setup lcd controller regs
+ */
+ for (i = 0; i < reg_count; i++) {
+ s1dReg = regs[i].Index;
+ if (reg_byte_swap) {
+ if ((s1dReg & 0x0001) == 0)
+ s1dReg |= 0x0001;
+ else
+ s1dReg &= ~0x0001;
+ }
+ s1dValue = regs[i].Value;
+ out_8(&lcd_reg[s1dReg], s1dValue);
+ }
+
+ /*
+ * Save reg & mem pointer for later usage (e.g. bmp command)
+ */
+ glob_lcd_reg = lcd_reg;
+ glob_lcd_mem = lcd_mem;
+
+ /*
+ * Display bmp image
+ */
+ return lcd_bmp(logo_bmp);