1 /* 2 * Driver for the LCD display on the Tensilica LX60 Board. 3 * 4 * This file is subject to the terms and conditions of the GNU General Public 5 * License. See the file "COPYING" in the main directory of this archive 6 * for more details. 7 * 8 * Copyright (C) 2001, 2006 Tensilica Inc. 9 */ 10 11 /* 12 * 13 * FIXME: this code is from the examples from the LX60 user guide. 14 * 15 * The lcd_pause function does busy waiting, which is probably not 16 * great. Maybe the code could be changed to use kernel timers, or 17 * change the hardware to not need to wait. 18 */ 19 20 #include <linux/init.h> 21 #include <linux/io.h> 22 23 #include <platform/hardware.h> 24 #include <platform/lcd.h> 25 #include <linux/delay.h> 26 27 #define LCD_PAUSE_ITERATIONS 4000 28 #define LCD_CLEAR 0x1 29 #define LCD_DISPLAY_ON 0xc 30 31 /* 8bit and 2 lines display */ 32 #define LCD_DISPLAY_MODE8BIT 0x38 33 #define LCD_DISPLAY_POS 0x80 34 #define LCD_SHIFT_LEFT 0x18 35 #define LCD_SHIFT_RIGHT 0x1c 36 37 static int __init lcd_init(void) 38 { 39 *LCD_INSTR_ADDR = LCD_DISPLAY_MODE8BIT; 40 mdelay(5); 41 *LCD_INSTR_ADDR = LCD_DISPLAY_MODE8BIT; 42 udelay(200); 43 *LCD_INSTR_ADDR = LCD_DISPLAY_MODE8BIT; 44 udelay(50); 45 *LCD_INSTR_ADDR = LCD_DISPLAY_ON; 46 udelay(50); 47 *LCD_INSTR_ADDR = LCD_CLEAR; 48 mdelay(10); 49 lcd_disp_at_pos("XTENSA LINUX", 0); 50 return 0; 51 } 52 53 void lcd_disp_at_pos(char *str, unsigned char pos) 54 { 55 *LCD_INSTR_ADDR = LCD_DISPLAY_POS | pos; 56 udelay(100); 57 while (*str != 0) { 58 *LCD_DATA_ADDR = *str; 59 udelay(200); 60 str++; 61 } 62 } 63 64 void lcd_shiftleft(void) 65 { 66 *LCD_INSTR_ADDR = LCD_SHIFT_LEFT; 67 udelay(50); 68 } 69 70 void lcd_shiftright(void) 71 { 72 *LCD_INSTR_ADDR = LCD_SHIFT_RIGHT; 73 udelay(50); 74 } 75 76 arch_initcall(lcd_init); 77