summaryrefslogtreecommitdiff
path: root/components/hx8347/hx8347.c
diff options
context:
space:
mode:
Diffstat (limited to 'components/hx8347/hx8347.c')
-rw-r--r--components/hx8347/hx8347.c415
1 files changed, 415 insertions, 0 deletions
diff --git a/components/hx8347/hx8347.c b/components/hx8347/hx8347.c
new file mode 100644
index 0000000..bc80d08
--- /dev/null
+++ b/components/hx8347/hx8347.c
@@ -0,0 +1,415 @@
+/* ----------------------------------------------------------------------------
+ * ATMEL Microcontroller Software Support
+ * ----------------------------------------------------------------------------
+ * Copyright (c) 2008, Atmel Corporation
+ *
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * - Redistributions of source code must retain the above copyright notice,
+ * this list of conditions and the disclaimer below.
+ *
+ * Atmel's name may not be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * DISCLAIMER: THIS SOFTWARE IS PROVIDED BY ATMEL "AS IS" AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT ARE
+ * DISCLAIMED. IN NO EVENT SHALL ATMEL BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA,
+ * OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
+ * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ----------------------------------------------------------------------------
+ */
+
+//------------------------------------------------------------------------------
+/// \unit
+///
+/// !Purpose
+///
+/// HX8347 driver
+///
+/// !Usage
+///
+/// Explanation on the usage of the code made available through the header file.
+//------------------------------------------------------------------------------
+
+//------------------------------------------------------------------------------
+// Headers
+//------------------------------------------------------------------------------
+#include <board.h>
+#include <stdio.h>
+
+#ifdef BOARD_LCD_HX8347
+
+#include "hx8347.h"
+
+//------------------------------------------------------------------------------
+// Types
+//------------------------------------------------------------------------------
+typedef volatile unsigned short REG16;
+
+//------------------------------------------------------------------------------
+// Definitions
+//------------------------------------------------------------------------------
+/// LCD index register address
+#define LCD_IR(baseAddr) (*((REG16 *)(baseAddr)))
+/// LCD status register address
+#define LCD_SR(baseAddr) (*((REG16 *)(baseAddr)))
+/// LCD data address
+#define LCD_D(baseAddr) (*((REG16 *)((unsigned int)(baseAddr) + BOARD_LCD_RS)))
+
+/// HX8347 ID code
+#define HX8347_HIMAXID_CODE 0x47
+
+/// HX8347 LCD Registers
+#define HX8347_R00H 0x00
+#define HX8347_R01H 0x01
+#define HX8347_R02H 0x02
+#define HX8347_R03H 0x03
+#define HX8347_R04H 0x04
+#define HX8347_R05H 0x05
+#define HX8347_R06H 0x06
+#define HX8347_R07H 0x07
+#define HX8347_R08H 0x08
+#define HX8347_R09H 0x09
+#define HX8347_R0AH 0x0A
+#define HX8347_R0CH 0x0C
+#define HX8347_R0DH 0x0D
+#define HX8347_R0EH 0x0E
+#define HX8347_R0FH 0x0F
+#define HX8347_R10H 0x10
+#define HX8347_R11H 0x11
+#define HX8347_R12H 0x12
+#define HX8347_R13H 0x13
+#define HX8347_R14H 0x14
+#define HX8347_R15H 0x15
+#define HX8347_R16H 0x16
+#define HX8347_R18H 0x18
+#define HX8347_R19H 0x19
+#define HX8347_R1AH 0x1A
+#define HX8347_R1BH 0x1B
+#define HX8347_R1CH 0x1C
+#define HX8347_R1DH 0x1D
+#define HX8347_R1EH 0x1E
+#define HX8347_R1FH 0x1F
+#define HX8347_R20H 0x20
+#define HX8347_R21H 0x21
+#define HX8347_R22H 0x22
+#define HX8347_R23H 0x23
+#define HX8347_R24H 0x24
+#define HX8347_R25H 0x25
+#define HX8347_R26H 0x26
+#define HX8347_R27H 0x27
+#define HX8347_R28H 0x28
+#define HX8347_R29H 0x29
+#define HX8347_R2AH 0x2A
+#define HX8347_R2BH 0x2B
+#define HX8347_R2CH 0x2C
+#define HX8347_R2DH 0x2D
+#define HX8347_R35H 0x35
+#define HX8347_R36H 0x36
+#define HX8347_R37H 0x37
+#define HX8347_R38H 0x38
+#define HX8347_R39H 0x39
+#define HX8347_R3AH 0x3A
+#define HX8347_R3BH 0x3B
+#define HX8347_R3CH 0x3C
+#define HX8347_R3DH 0x3D
+#define HX8347_R3EH 0x3E
+#define HX8347_R40H 0x40
+#define HX8347_R41H 0x41
+#define HX8347_R42H 0x42
+#define HX8347_R43H 0x43
+#define HX8347_R44H 0x44
+#define HX8347_R45H 0x45
+#define HX8347_R46H 0x46
+#define HX8347_R47H 0x47
+#define HX8347_R48H 0x48
+#define HX8347_R49H 0x49
+#define HX8347_R4AH 0x4A
+#define HX8347_R4BH 0x4B
+#define HX8347_R4CH 0x4C
+#define HX8347_R4DH 0x4D
+#define HX8347_R4EH 0x4E
+#define HX8347_R4FH 0x4F
+#define HX8347_R50H 0x50
+#define HX8347_R51H 0x51
+#define HX8347_R64H 0x64
+#define HX8347_R65H 0x65
+#define HX8347_R66H 0x66
+#define HX8347_R67H 0x67
+#define HX8347_R70H 0x70
+#define HX8347_R72H 0x72
+#define HX8347_R90H 0x90
+#define HX8347_R91H 0x91
+#define HX8347_R93H 0x93
+#define HX8347_R94H 0x94
+#define HX8347_R95H 0x95
+
+//------------------------------------------------------------------------------
+// External functions
+//------------------------------------------------------------------------------
+// External delay 1 ms function
+extern void DelayMS(unsigned int ms);
+#define Delay(ms) DelayMS(ms)
+
+//------------------------------------------------------------------------------
+// Global functions
+//------------------------------------------------------------------------------
+
+//------------------------------------------------------------------------------
+/// Write data to LCD Register.
+/// \param pLcdBase LCD base address.
+/// \param reg Register address.
+/// \param data Data to be written.
+//------------------------------------------------------------------------------
+void LCD_WriteReg(void *pLcdBase, unsigned char reg, unsigned short data)
+{
+ LCD_IR(pLcdBase) = reg;
+ LCD_D(pLcdBase) = data;
+}
+
+//------------------------------------------------------------------------------
+/// Read data from LCD Register.
+/// \param pLcdBase LCD base address.
+/// \param reg Register address.
+/// \return data Data to be read.
+//------------------------------------------------------------------------------
+unsigned short LCD_ReadReg(void *pLcdBase, unsigned char reg)
+{
+ LCD_IR(pLcdBase) = reg;
+ return LCD_D(pLcdBase);
+}
+
+//------------------------------------------------------------------------------
+/// Read LCD status Register.
+/// \param pLcdBase LCD base address.
+/// \param reg Register address.
+/// \return data Status Data.
+//------------------------------------------------------------------------------
+unsigned short LCD_ReadStatus(void *pLcdBase)
+{
+ return LCD_SR(pLcdBase);
+}
+
+//------------------------------------------------------------------------------
+/// Prepare to write GRAM data.
+/// \param pLcdBase LCD base address.
+//------------------------------------------------------------------------------
+void LCD_WriteRAM_Prepare(void *pLcdBase)
+{
+ LCD_IR(pLcdBase) = HX8347_R22H;
+}
+
+//------------------------------------------------------------------------------
+/// Write data to LCD GRAM.
+/// \param pLcdBase LCD base address.
+/// \param color 16-bits RGB color.
+//------------------------------------------------------------------------------
+void LCD_WriteRAM(void *pLcdBase, unsigned short color)
+{
+ // Write 16-bit GRAM Reg
+ LCD_D(pLcdBase) = color;
+}
+
+//------------------------------------------------------------------------------
+/// Prepare to read GRAM data.
+/// \param pLcdBase LCD base address.
+//------------------------------------------------------------------------------
+void LCD_ReadRAM_Prepare(void *pLcdBase)
+{
+ LCD_IR(pLcdBase) = HX8347_R22H;
+}
+
+//------------------------------------------------------------------------------
+/// Read GRAM data.
+/// \param pLcdBase LCD base address.
+/// \return 16-bits RGB color.
+//------------------------------------------------------------------------------
+unsigned short LCD_ReadRAM(void *pLcdBase)
+{
+ // Read 16-bit GRAM Reg
+ return LCD_D(pLcdBase);
+}
+
+//------------------------------------------------------------------------------
+/// Dump register data.
+/// \param pLcdBase LCD base address.
+/// \param startAddr Register start address.
+/// \param endAddr Register end address.
+//------------------------------------------------------------------------------
+void LCD_DumpReg(void *pLcdBase, unsigned char startAddr, unsigned char endAddr)
+{
+ unsigned short tmp;
+ unsigned char addr;
+
+ for (addr = startAddr; addr <= endAddr; addr++) {
+
+ tmp = LCD_ReadReg(pLcdBase, addr);
+ printf("LCD.r 0x%x = 0x%x\n\r", addr, tmp);
+ }
+}
+
+//------------------------------------------------------------------------------
+/// Initialize the LCD controller.
+/// \param pLcdBase LCD base address.
+//------------------------------------------------------------------------------
+void LCD_Initialize(void *pLcdBase)
+{
+ unsigned short chipid;
+
+ // Check HX8347 chipid
+ chipid = LCD_ReadReg(pLcdBase, HX8347_R67H);
+ if(chipid != HX8347_HIMAXID_CODE) {
+
+ printf("Read HX8347 chip ID error, skip initialization.\r\n");
+ return ;
+ }
+
+ // Start internal OSC
+ LCD_WriteReg(pLcdBase, HX8347_R19H, 0x49); // OSCADJ=10 0000, OSD_EN=1 //60Hz
+ LCD_WriteReg(pLcdBase, HX8347_R93H, 0x0C); // RADJ=1100
+
+ // Power on flow
+ LCD_WriteReg(pLcdBase, HX8347_R44H, 0x4D); // VCM=100 1101
+ LCD_WriteReg(pLcdBase, HX8347_R45H, 0x11); // VDV=1 0001
+ LCD_WriteReg(pLcdBase, HX8347_R20H, 0x40); // BT=0100
+ LCD_WriteReg(pLcdBase, HX8347_R1DH, 0x07); // VC1=111
+ LCD_WriteReg(pLcdBase, HX8347_R1EH, 0x00); // VC3=000
+ LCD_WriteReg(pLcdBase, HX8347_R1FH, 0x04); // VRH=0100
+
+ LCD_WriteReg(pLcdBase, HX8347_R1CH, 0x04); // AP=100
+ LCD_WriteReg(pLcdBase, HX8347_R1BH, 0x10); // GASENB=0, PON=1, DK=0, XDK=0, DDVDH_TRI=0, STB=0
+ Delay(50);
+
+ LCD_WriteReg(pLcdBase, HX8347_R43H, 0x80); // Set VCOMG=1
+ Delay(50);
+
+ // Gamma for CMO 2.8
+ LCD_WriteReg(pLcdBase, HX8347_R46H, 0x95);
+ LCD_WriteReg(pLcdBase, HX8347_R47H, 0x51);
+ LCD_WriteReg(pLcdBase, HX8347_R48H, 0x00);
+ LCD_WriteReg(pLcdBase, HX8347_R49H, 0x36);
+ LCD_WriteReg(pLcdBase, HX8347_R4AH, 0x11);
+ LCD_WriteReg(pLcdBase, HX8347_R4BH, 0x66);
+ LCD_WriteReg(pLcdBase, HX8347_R4CH, 0x14);
+ LCD_WriteReg(pLcdBase, HX8347_R4DH, 0x77);
+ LCD_WriteReg(pLcdBase, HX8347_R4EH, 0x13);
+ LCD_WriteReg(pLcdBase, HX8347_R4FH, 0x4C);
+ LCD_WriteReg(pLcdBase, HX8347_R50H, 0x46);
+ LCD_WriteReg(pLcdBase, HX8347_R51H, 0x46);
+
+ //240x320 window setting
+ LCD_WriteReg(pLcdBase, HX8347_R02H, 0x00); // Column address start2
+ LCD_WriteReg(pLcdBase, HX8347_R03H, 0x00); // Column address start1
+ LCD_WriteReg(pLcdBase, HX8347_R04H, 0x00); // Column address end2
+ LCD_WriteReg(pLcdBase, HX8347_R05H, 0xEF); // Column address end1
+ LCD_WriteReg(pLcdBase, HX8347_R06H, 0x00); // Row address start2
+ LCD_WriteReg(pLcdBase, HX8347_R07H, 0x00); // Row address start1
+ LCD_WriteReg(pLcdBase, HX8347_R08H, 0x01); // Row address end2
+ LCD_WriteReg(pLcdBase, HX8347_R09H, 0x3F); // Row address end1
+
+ // Display Setting
+ LCD_WriteReg(pLcdBase, HX8347_R01H, 0x06); // IDMON=0, INVON=1, NORON=1, PTLON=0
+ LCD_WriteReg(pLcdBase, HX8347_R16H, 0xC8); // MY=1, MX=1, MV=0, BGR=1
+ LCD_WriteReg(pLcdBase, HX8347_R23H, 0x95); // N_DC=1001 0101
+ LCD_WriteReg(pLcdBase, HX8347_R24H, 0x95); // P_DC=1001 0101
+ LCD_WriteReg(pLcdBase, HX8347_R25H, 0xFF); // I_DC=1111 1111
+ LCD_WriteReg(pLcdBase, HX8347_R27H, 0x06); // N_BP=0000 0110
+ LCD_WriteReg(pLcdBase, HX8347_R28H, 0x06); // N_FP=0000 0110
+ LCD_WriteReg(pLcdBase, HX8347_R29H, 0x06); // P_BP=0000 0110
+ LCD_WriteReg(pLcdBase, HX8347_R2AH, 0x06); // P_FP=0000 0110
+ LCD_WriteReg(pLcdBase, HX8347_R2CH, 0x06); // I_BP=0000 0110
+ LCD_WriteReg(pLcdBase, HX8347_R2DH, 0x06); // I_FP=0000 0110
+ LCD_WriteReg(pLcdBase, HX8347_R3AH, 0x01); // N_RTN=0000, N_NW=001
+ LCD_WriteReg(pLcdBase, HX8347_R3BH, 0x01); // P_RTN=0000, P_NW=001
+ LCD_WriteReg(pLcdBase, HX8347_R3CH, 0xF0); // I_RTN=1111, I_NW=000
+ LCD_WriteReg(pLcdBase, HX8347_R3DH, 0x00); // DIV=00
+ LCD_WriteReg(pLcdBase, HX8347_R3EH, 0x38); // SON=38h
+ LCD_WriteReg(pLcdBase, HX8347_R40H, 0x0F); // GDON=0Fh
+ LCD_WriteReg(pLcdBase, HX8347_R41H, 0xF0); // GDOF=F0h
+}
+
+//------------------------------------------------------------------------------
+/// Turn on the LCD.
+/// \param pLcdBase LCD base address.
+//------------------------------------------------------------------------------
+void LCD_On(void *pLcdBase)
+{
+ // Display ON Setting
+ LCD_WriteReg(pLcdBase, HX8347_R90H, 0x7F); // SAP=0111 1111
+ LCD_WriteReg(pLcdBase, HX8347_R26H, 0x04); // GON=0, DTE=0, D=01
+ Delay(100);
+ LCD_WriteReg(pLcdBase, HX8347_R26H, 0x24); // GON=1, DTE=0, D=01
+ LCD_WriteReg(pLcdBase, HX8347_R26H, 0x2C); // GON=1, DTE=0, D=11
+ Delay(100);
+ LCD_WriteReg(pLcdBase, HX8347_R26H, 0x3C); // GON=1, DTE=1, D=11
+}
+
+//------------------------------------------------------------------------------
+/// Turn off the LCD.
+/// \param pLcdBase LCD base address.
+//------------------------------------------------------------------------------
+void LCD_Off(void *pLcdBase)
+{
+ LCD_WriteReg(pLcdBase, HX8347_R90H, 0x00); // SAP=0000 0000
+ LCD_WriteReg(pLcdBase, HX8347_R26H, 0x00); // GON=0, DTE=0, D=00
+}
+
+//------------------------------------------------------------------------------
+/// Set cursor of LCD srceen.
+/// \param pLcdBase LCD base address.
+/// \param x X-coordinate of upper-left corner on LCD.
+/// \param y Y-coordinate of upper-left corner on LCD.
+//------------------------------------------------------------------------------
+void LCD_SetCursor(void *pLcdBase, unsigned short x, unsigned short y)
+{
+ unsigned char x1, x2, y1, y2;
+
+ x1 = x & 0xff;
+ x2 = (x & 0xff00) >>8;
+ y1 = y & 0xff;
+ y2 = (y & 0xff00) >>8;
+ LCD_WriteReg(pLcdBase, HX8347_R02H, x2); // column high
+ LCD_WriteReg(pLcdBase, HX8347_R03H, x1); // column low
+ LCD_WriteReg(pLcdBase, HX8347_R06H, y2); // row high
+ LCD_WriteReg(pLcdBase, HX8347_R07H, y1); // row low
+}
+
+//------------------------------------------------------------------------------
+/// Set the window size user can access.
+/// \param pLcdBase LCD base address.
+/// \param x_start X-coordinate of upper-left corner on LCD.
+/// \param y_start Y-coordinate of upper-left corner on LCD.
+/// \param x_end X-coordinate of bottom-right corner on LCD.
+/// \param y_end Y-coordinate of bottom-right corner on LCD.
+//------------------------------------------------------------------------------
+void LCD_SetWindow(void *pLcdBase,unsigned short x_start, unsigned short y_start,unsigned short x_end, unsigned short y_end)
+{
+ unsigned char x1, x2, y1, y2;
+
+ x1 = x_start & 0xff;
+ x2 = (x_start & 0xff00) >>8;
+ y1 = y_start & 0xff;
+ y2 = (y_start & 0xff00) >>8;
+ LCD_WriteReg(pLcdBase, 0x02, x2); // column high
+ LCD_WriteReg(pLcdBase, 0x03, x1); // column low
+ LCD_WriteReg(pLcdBase, 0x06, y2); // row high
+ LCD_WriteReg(pLcdBase, 0x07, y1); // row low
+
+ x1 = x_end & 0xff;
+ x2 = (x_end & 0xff00) >>8;
+ y1 = y_end & 0xff;
+ y2 = (y_end & 0xff00) >>8;
+ LCD_WriteReg(pLcdBase, 0x04, x2); // column high
+ LCD_WriteReg(pLcdBase, 0x05, x1); // column low
+ LCD_WriteReg(pLcdBase, 0x08, y2); // row high
+ LCD_WriteReg(pLcdBase, 0x09, y1); // row low
+}
+#endif //#ifdef BOARD_LCD_HX8347
personal git repositories of Harald Welte. Your mileage may vary