LCD trouble-shooting FAQ
For existing LCD-driver library users
My compiler allocates two copies of the soft-font tables, one in RAM and one in ROM. How can I avoid the RAM copy?
Many embedded compilers require the use of a special (intrinsic) memory specifier key word to locate constant initialized data objects in ROM only. Typical memory type specifier keywords used are for instance: code, rom, program, const rom etc. Check your compiler manual for what is required with your specific compiler, and then map the GCODE, FCODE and PFCODE definitions to this memory type specifier keyword in the library configuration file gdispcfg.h
My CodeVisionAVR compiler makes a copy of font data in RAM.
How should I use this compiler so that font data are located in ROM only ?
Compilers which have the limitation that a pointer can only be used with objects located
in ROM or with objects located in RAM can be used with the library with
very little impact on functionality.
In most typical embedded applications, fonts are only read and never written.
Fonts can therefore be located in ROM via memory type qualifiers and accessed via pointers qualified only for access to ROM memory.
For the CodeVisionAVR compiler this is controlled via compiler specific memory type qualifiers.
Such intrinsic type qualifier keywords can inserted in the library code via the library configuration file (See QA above).
For CodeVisionAVR, you can simply change the default memory type qualifier mapping in the library configuration file to this:
A similar C standard conformance issue exists with some compilers which (incorrectly) interpret, for instance, const *ptr to
mean a pointer to ROM-only objects.
With such compilers, the same solution method as above can be used.
(The issue is that in standard C a const qualified pointer is just a guarantee that the object pointed to will not be modified through the pointer. The same pointer is allowed to be used with both objects located in ROM and objects located in RAM.
I.e. const object_type * qualifier is a just part of C's strong prototyping and says nothing about where the object itself is located)
More information can be found in the firstaid.pdf document included with the library.
My display module uses 8 bits for each R,G,B color.
How can I connect it to a display controller which uses 6 bits per color ?
Connect the MSB controller color bits to MSB display bits, and then repeat with MSB controller bits for the lower display module bits. In this way, you get full color saturation in both intensity directions.
|Display||Display controller RGB bus|
Connect the MSB controller color bits to MSB display bits, and skip use of the lower display controller bits.
|Display||Display controller RGB bus|
The library worked without problems in my old target system. However, I have changed
to a faster microcontroller (24MHz, before 12MHz), and now I have problems with my
graphic-LCD using KS0108.
Is there anywhere in the LCD-driver-library where I can
implement wait-states, or is there another way to solve the problem?
Such bus timing and similar hardware problems are normally outside the scope of the LCD software library.
If your display is connected directly to the processor bus, any timing problems must be solved in the target hardware or via the processor hardware configurations.
If your display is connected to I/O ports (single-chip mode), you can extend the E setup timing in the bussim.c functions by repeating some instructions. See the library application note for single-chip mode for further information.
For KS0108, SED1520 controllers, the critical timing is usually the R/W (read/write) and RS (register address select) setup times before the start of the E clock rising edge. Check the relative signal timings with an oscilloscope and compare with the data sheets for the display module / LCD controller.
When connecting an LCD using a 6800 type bus (R/W Eclk) to a processor using a 8080 type bus (/RD /WR), critical timing issues can often be solved by connecting the LCD R/W signal to an address bus line instead, and then accessing the LCD read and write registers at different addresses.
My T6963C display shows random spots all over the display.
This symptom has been found to be a hardware problem typically caused by a weak ground connection with respect to high-frequency signals. It is therefore not related to the LCD-driver library as such.
The symptom has been seen in places where ferrite beads have been mounted on all cable lines to the display module to reduce EMC problems. Replacing the ferrite bead in the power ground line with a 0-ohm resistor (using the same PCB footprint) has often solved the problem. Ferrite beads in the other signal lines cause no problems.
My SED1335 display "flickers" during update.
This is typical for the SED1335 controller and caused by "bus contention" when the processor and the internal video scan logic in SED1335 are competing over access to the LCD video RAM.
The problem is solved by not defining GHW_USE_FAST_UPDATE in the library configuration header file. The processor will then only update the display in between video line scans. See also comments in the library ghwinit.c module, and the hint below.
My S1D13700 display produces "sparkles" during area clear or fill operations.
This is typical for the S1D13700 controller and caused by "bus contention" when the processor and the internal video scan logic in S1D13700 are competing over access to the LCD video memory. It typically occurs when S1D13700 is configured for B&W mode with the internal hardware text font enabled
The problem can solved by defining GHW_NO_HDW_FONT in the library configuration header file. The default SYSFONT then becomes a software font so the built-in hardware font is not used. The clear area and fill area operations then do not need to clear the text memory page in S1D13700, reducing the risk of on-chip bus contention.
Existing text or graphics on the display are distorted when new text or graphics are written nearby.
This normally indicates that there is a problem with reading the LCD-controller memory, typically when doing read-modify-write operations directly on the LCD controller video data.
Explanation: If the new drawing operation (e.g. text output) does not cover a full memory byte, the library will do a read of the old content (which fails in your system for some reason), add the new bits, and then write the content back to the LCD-controller memory. The result is that only the newest text is shown in the screen data byte or that random bits are added.
For LCD controllers using vertical data bytes (like KS07xx and SED1520), the symptom is usually seen when two horizontal drawing operations follow each other on the same byte, for instance, part of the existing text above or below is clipped.
For LCD controllers using horizontal data bytes (like T6963C, and SED1335), the symptom is usually seen when two vertical drawing operations follow each other on the same byte, for instance, clipping parts of the previous character in the text line when soft fonts are used.
- Check the bus hardware signals during LCD-controller read.
- Check that the address definitions for read-registers are correct.
- If single-chip mode is being used, check the functionality of the read-access driver. Is the direction of the LCD-bus switched correctly?
- Do a work-around by compiling the library for buffered mode. The LCD-driver memory is then only written, so the symptoms are masked. The "cost", however, is the increased RAM consumption of buffered mode. See your main manual for details about setting buffered mode.
How do I use the library with Embedded Linux
The LCD driver library itself is Operating System independent. The only requirement is that the driver code is allowed to get direct access to the address range where the display controller chip is connected.
With Linux, hardware access is usually done via a handle (a pointer) obtained via the mmap(..) function. Use this pointer as a base address and define all the display controller registers as indexes relative to this base.
Just compile the library for single chip mode so that all read-write access is done via the two small access functions in bussim.c. Then update the body of these functions so that display controller register access is done via the base pointer obtained with mmap(..).