Microcontroller not interfacing correctly with LCD

Go To Last Post
3 posts / 0 new
Author
Message
#1
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Hey everyone, I'm using an AT90s2313 chip to interface with a standard HD44780 LCD module in 4 bit mode. Every time after I initialize the LCD, it will not put characters on the screen. I'm using the lcd_lib.c and lcd_lib.h libraries and have included my code below. Since I edited the functions I'm using, I included the source code for those. I'm using the 10 MHz version of the chip, so is this too fast for the LCD, or is there something else I'm missing. I really need to figure out what's going on here, so any help you can give me would be much appreciated. Thanks guys.

#include "lcd_lib.h"
#include "lcd_lib.c"

void LCDsendCommand(uint8_t cmd) //Sends Command to LCD
{
#ifdef LCD_4bit
//4 bit part
LDP=(cmd&0b11110000);
LCP|=1<<LCD_E;
_delay_ms(1);
LCP&=~(1<<LCD_E);
_delay_ms(1);
LDP=((cmd&0b00001111)<<4);
LCP|=1<<LCD_E;
_delay_ms(1);
LCP&=~(1<<LCD_E);
_delay_ms(1);
#else
//8 bit part
LDP=cmd;
LCP|=1<<LCD_E;
_delay_ms(1);
LCP&=~(1<<LCD_E);
_delay_ms(1);
#endif
}

void LCDsendChar(uint8_t ch) //Sends Char to LCD
{

#ifdef LCD_4bit
//4 bit part
LDP=(ch&0b11110000);
LCP|=1<<LCD_RS;
LCP|=1<<LCD_E;
_delay_ms(1);
LCP&=~(1<<LCD_E);
LCP&=~(1<<LCD_RS);
_delay_ms(1);
LDP=((ch&0b00001111)<<4);
LCP|=1<<LCD_RS;
LCP|=1<<LCD_E;
_delay_ms(1);
LCP&=~(1<<LCD_E);
LCP&=~(1<<LCD_RS);
_delay_ms(1);
#else
//8 bit part
LDP=ch;
LCP|=1<<LCD_RS;
LCP|=1<<LCD_E;
_delay_ms(1);
LCP&=~(1<<LCD_E);
LCP&=~(1<<LCD_RS);
_delay_ms(1);
#endif

void LCDinit(void)//Initializes LCD
{
#ifdef LCD_4bit
//4 bit part
_delay_ms(15);
LDP=0x00;
LCP=0x00;
LDDR|=1<<LCD_D7|1<<LCD_D6|1<<LCD_D5|1<<LCD_D4;
LCDR|=1<<LCD_E|1<<LCD_RW|1<<LCD_RS;
//---------one------
LDP=0<<LCD_D7|0<<LCD_D6|1<<LCD_D5|1<<LCD_D4; //4 bit mode
LCP|=1<<LCD_E|0<<LCD_RW|0<<LCD_RS;
_delay_ms(1);
LCP&=~(1<<LCD_E);
_delay_ms(5);
//-----------two-----------
LDP=0<<LCD_D7|0<<LCD_D6|1<<LCD_D5|1<<LCD_D4; //4 bit mode
LCP|=1<<LCD_E|0<<LCD_RW|0<<LCD_RS;
_delay_ms(1);
LCP&=~(1<<LCD_E);
_delay_ms(1);
//-------three-------------
LDP=0<<LCD_D7|0<<LCD_D6|1<<LCD_D5|1<<LCD_D4; //4 bit mode
LCP|=1<<LCD_E|0<<LCD_RW|0<<LCD_RS;
_delay_ms(1);
LCP&=~(1<<LCD_E);
_delay_ms(1);
//--------4 bit--dual line---------------
LCDsendCommand(0b00100000);
_delay_ms(1);
LCDsendCommand(0b00101000);
_delay_ms(1);
LCDsendCommand(0b00001000);
_delay_ms(1);
LCDsendCommand(0b00000001);
_delay_ms(1);
LCDsendCommand(0b00000100);
_delay_ms(1);
LCDsendCommand(0b00011110);
_delay_ms(1);

#endif
}

void LCDclr(void) //Clears LCD
{
LCDsendCommand(1<<LCD_CLR);
_delay_ms(1);
}

void LCDstring(uint8_t* data, uint8_t nBytes) //Outputs string to LCD
{
register uint8_t i;

// check to make sure we have a good pointer
if (!data) return;

// print data
for(i=0; i<=nBytes; i++)
{
LCDsendChar(data[i]);
}
}

int main (void){

LCDinit();
LCDclr();
LCDstring("hello", 5);
return 1;
}

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I don't have the time to look at the code closely but, having scanned it quickly, I see _delay_ms. This probably means that you are using AVR-LIBC? If so, then be aware of the following note in the documentation:

Quote:
In order for these functions to work as intended, compiler optimizations must be enabled, and the delay time must be an expression that is a known constant at compile-time

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

If you are using winAvr, is there any reason why you are not using the working code supplied in stdiodemo?

John Samperi

Ampertronics Pty. Ltd.

www.ampertronics.com.au

* Electronic Design * Custom Products * Contract Assembly