Forum Menu




 


Log in Problems?
New User? Sign Up!
AVR Freaks Forum Index

Post new topic   Reply to topic
View previous topic Printable version Log in to check your private messages View next topic
Author Message
JohanEkdahl
PostPosted: Jan 05, 2007 - 03:39 PM
10k+ Postman


Joined: Mar 27, 2002
Posts: 22212
Location: Lund, Sweden

Yes, bob. He's probably reading right out of the data sheet where the first two columns are the RS and R/W signals. So the instruction proper is 0011NFXX.
 
 View user's profile Send private message Visit poster's website 
Reply with quote Back to top
sinosoidal
PostPosted: Jan 05, 2007 - 08:07 PM
Hangaround


Joined: Apr 07, 2006
Posts: 407
Location: Braga, Portugal

Yes, i forgot to mention that!

Sorry!
 
 View user's profile Send private message Visit poster's website 
Reply with quote Back to top
sinosoidal
PostPosted: Jan 06, 2007 - 02:12 PM
Hangaround


Joined: Apr 07, 2006
Posts: 407
Location: Braga, Portugal

I took off every connection and made all the wiring up again. Nothing different!

My module has the reference GDM1602A

The one page datahseet can be found here:

http://www.datasheetarchive.com/datasheet.php?article=1547161

Can you guys see here anything that helps?

:S

Thx for all the help you guys gave me until now.

This is getting sick for me! Sad

Best regards,

Nuno
 
 View user's profile Send private message Visit poster's website 
Reply with quote Back to top
bobgardner
PostPosted: Jan 06, 2007 - 05:44 PM
10k+ Postman


Joined: Sep 04, 2002
Posts: 24095
Location: Orlando Florida

Its a timing thing. Does the mega88 have a clkdiv fuse to run it at 8mhz or 1mhz? You THINK it is running at 8, but seems like it should still work even if it is running at 1. Does the mega88 have JTAG? Is it on portc? Do you need to turn the jtag fuse off to get portc to work like an output port? Can you edit, compile, burn and run ANY other program using this avr and your compiler setup that shows ANY correct behavior on the cpu, like flash an led on and off once each second, and it really flashes once per second and not once per 8 seconds?
 
 View user's profile Send private message Send e-mail Visit poster's website 
Reply with quote Back to top
microcarl
PostPosted: Jan 06, 2007 - 05:59 PM
Raving lunatic


Joined: May 30, 2004
Posts: 8502
Location: Cincinnati, Ohio

bobgardner wrote:
Its a timing thing. Does the mega88 have a clkdiv fuse to run it at 8mhz or 1mhz? You THINK it is running at 8, but seems like it should still work even if it is running at 1.


Running at 1MHz is far more tollerable then running at 8MHz. You can have the display running with an 8MHz machine and drop down to 1MHz with any problems at all but, you can't have the display timing critically set to run with a 1MHz machine and jump up to 8MHz and expect the LCD display to operate correctly, without re-adjusting all of the appropriate timing.

bobgardner wrote:
Can you edit, compile, burn and run ANY other program using this avr...

Good point! Will it even program to simply flash an LED on & off?

_________________
Carl W. Livingston, KC5OTL
microcarl@roadrunner.com

"There are only two ways to sleep well at night... be ignorant or be prepared."

The original Dragon Slayer !

Long live the AVR!!!
 
 View user's profile Send private message Send e-mail  
Reply with quote Back to top
sinosoidal
PostPosted: Jan 06, 2007 - 07:29 PM
Hangaround


Joined: Apr 07, 2006
Posts: 407
Location: Braga, Portugal

Yes, i can compile and program right.

I tried the LED program and you guys are right. It's a timing thing.

I will need your help here.

I'm running the following program to do the led test:

Code:

#include <avr/io.h>
#define F_CPU 1000000
#include <util/delay.h>

void my_delay_ms(uint16_t delay_count) {
   uint16_t i;

   for (i=0; i<delay_count; i++) {
      _delay_ms(1);
   }
}

int main (void) {
   DDRB = 0xFF;
   PORTB = 0;

   while (1) {
      my_delay_ms(1000);
      PORTB ^= 0xFF;
   }
}


I'm using the divider to have a frequency clock of 1 Mhz and i was expecting the led to light 1 second and then stay 1 second turned off.

In portb 0 its blinking very fast. in the other B ports it doesnt blink.

If i take the divider the blinking of portb0 is even greater but it doesnt change, changing the delay... :S

I have tried this in both mega88 and mega168?

What is happening here?

Any clue?

Best regards,

Nuno
 
 View user's profile Send private message Visit poster's website 
Reply with quote Back to top
sinosoidal
PostPosted: Jan 06, 2007 - 07:57 PM
Hangaround


Joined: Apr 07, 2006
Posts: 407
Location: Braga, Portugal

Hey guys,

I wont believe this....

The problem with the led test was that i was always progamming the chip with a hex file that was not related with that project, and with the lcd project as well....

I though that it was the problem since the begining.

Unfortunetly i wasnt. I have the same behaviour.

I even tried to clean the code again and past again Carl's code.

Well... I now have sure that i'm programming the right file.

I'm suspect to talk now! :S

Nuno
 
 View user's profile Send private message Visit poster's website 
Reply with quote Back to top
JohanEkdahl
PostPosted: Jan 06, 2007 - 08:03 PM
10k+ Postman


Joined: Mar 27, 2002
Posts: 22212
Location: Lund, Sweden

1. You will not get the result you expect with _delay_ms(1000) unless you run your AVR with a clock that is substantially lower than 1 MHz. You need to read up on the avr-libc documentation, and on _delay_ms(). There is a limitation on how long delays it can generate. I can't remember the limits of hand and I could look it up for you, but you might as well do it yourself.

2. When you say "take the divider" I assume you are referring to the CKDIV8 fuse. If you change the CKDIV8 fuse, but do not change the F_CPU defined constant then the blinking frequency will change, as _delay_ms() depends on this define.
 
 View user's profile Send private message Visit poster's website 
Reply with quote Back to top
sinosoidal
PostPosted: Jan 06, 2007 - 08:16 PM
Hangaround


Joined: Apr 07, 2006
Posts: 407
Location: Braga, Portugal

Hey!

I finally have good news!

After all the problem was in flashing with the correct file!

Dahhhh

You could post a news with the title "The lamest freak!"

ehehehhe

With the rewiring i forgot to plug R/W to the ground.

The output i have in the lcd with carl's code is:

"vnso"

I believe this is related to the fact i have a 2x16 lcd module and the code is for a 4 line.

Need help to understand the display chaacter address codes

Thx a lot!

Best regards,

Nuno
 
 View user's profile Send private message Visit poster's website 
Reply with quote Back to top
sinosoidal
PostPosted: Jan 06, 2007 - 08:57 PM
Hangaround


Joined: Apr 07, 2006
Posts: 407
Location: Braga, Portugal

I have been playing a little bit with the LCD and i have a thing to ask you, Carl:
Code:

   LCD_PutCmd (LINE1+5);
   LCD_PutString (BANNER_1);


Why do you have LINE1+5 in the PutCmd function?

The output i'm having right now is:

__________H_____
_nuF_gniva______

This is the BANNER "Having Fun".

I'm doing the initialization using my datasheet values:

#define PWR_CMD 0x3C
#define DL_CMD 0x0F

Thx,

Nuno
 
 View user's profile Send private message Visit poster's website 
Reply with quote Back to top
microcarl
PostPosted: Jan 06, 2007 - 09:56 PM
Raving lunatic


Joined: May 30, 2004
Posts: 8502
Location: Cincinnati, Ohio

sinosoidal wrote:
I have been playing a little bit with the LCD and i have a thing to ask you, Carl:
Code:

   LCD_PutCmd (LINE1+5);
   LCD_PutString (BANNER_1);


Why do you have LINE1+5 in the PutCmd function?

The output i'm having right now is:

__________H_____
_nuF_gniva______

This is the BANNER "Having Fun".

I'm doing the initialization using my datasheet values:

#define PWR_CMD 0x3C
#define DL_CMD 0x0F

Thx,

Nuno


Because I use primarily a 4x20 display.

The very first character in LINE1 is defined as 0x80 - the left most display position on line 1. This will be the same for every common text based LCD module, no mater how many lines it has.

LINE2 is defined as 0xC0. This too is that same for every text based display I have ever used.

I have tested the exact same setup with a 2x16 character display and:
"Having"
"Fun"
is still displayed correctly on the smaller display but, shifted to the right by 5 character positions - without and code changes.

Just change the PutCmd() variable from:
Code:
LCD_PutCmd (LINE1+5);
LCD_PutString (BANNER_1);

to
Code:
LCD_PutCmd (LINE1);
LCD_PutString (BANNER_1);


sinosoidal wrote:
I'm doing the initialization using my datasheet values:

#define PWR_CMD 0x3C
#define DL_CMD 0x0F


I am currently at work and don't have a datasheet available so, I don't know what the different bit positions represent and can't presume how the display is being set up. What I do know is that, the PWR_CMD & DL_CMD that I posted are what I'm using.

Now, with the DL_CMD, if you are using a two line display and a blinking cursor and what ever the other options there are, that's not really an issue.

However, the PWR_CMD value could be an issue. I just don't have enough information to determine what your values actually mean at the moment. I'll look them up tonight, after I get home - about 0:30, Jan 07, 2007.

Edit:

One thing you can do is to print just one character, followed be a space characer, such as
"H " on only one line - over and over. See what happens.

Then print:
"Ha " over and over.

Provide some detailed feedback as to the exact text position from each test. This might lead to clues as to whether its a command timing issue ot a character printing issue.

_________________
Carl W. Livingston, KC5OTL
microcarl@roadrunner.com

"There are only two ways to sleep well at night... be ignorant or be prepared."

The original Dragon Slayer !

Long live the AVR!!!
 
 View user's profile Send private message Send e-mail  
Reply with quote Back to top
bobgardner
PostPosted: Jan 07, 2007 - 01:37 AM
10k+ Postman


Joined: Sep 04, 2002
Posts: 24095
Location: Orlando Florida

There is an 'entry mode' command that lets you select whether to shift the cursor or the display, and if you shift the display, whether it shifts left or right. If you want it to act like a crt, the cursor should shift, not the display, and it should increment (move to the right) unless you want it to print arabic, which goes to the left.
 
 View user's profile Send private message Send e-mail Visit poster's website 
Reply with quote Back to top
sinosoidal
PostPosted: Jan 08, 2007 - 01:21 PM
Hangaround


Joined: Apr 07, 2006
Posts: 407
Location: Braga, Portugal

I follow Carl's advice to write only one caracter at line 0x80 and it was sucessefully drawn.

But with this issue i can say that i really dont understand datasheets!!

In the small datasheet of my LCD module the start address is 0x00 for the first line and 0x40 for the second! :S

Can somebody explain me why? And... how can i trust a datasheet if she tells me something that is wrong?

Another thing i realized with the experiment is that i need to LCD_PutCmd(LINE+numberOfCharacteresToBeWritten) to have a string written.

My entry mode i defined it as increment mode and entire shift off (what is this one related with?).

Another problem is that i can write a string in the first line and in the second.

But if try to write booth it doesnt work:

Code:

#define LINE1 0x80
#define LINE2 0xC0

const char BANNER_1[] = {"Control: 100"};
const char BANNER_2[] = {"Value: 127"};

LCD_PutCmd (LINE1+strlen(BANNER_1));
LCD_PutString (BANNER_1);
LCD_PutCmd (LINE2+strlen(BANNER_2));
LCD_PutString (BANNER_2);


The result is each case separetly is correct. The result of both lines instructions is 00 in the first line....

Any tips?

Thx

Nuno
 
 View user's profile Send private message Visit poster's website 
Reply with quote Back to top
microcarl
PostPosted: Jan 08, 2007 - 02:11 PM
Raving lunatic


Joined: May 30, 2004
Posts: 8502
Location: Cincinnati, Ohio

sinosoidal wrote:
I follow Carl's advice to write only one caracter at line 0x80 and it was sucessefully drawn.

But with this issue i can say that i really dont understand datasheets!!

In the small datasheet of my LCD module the start address is 0x00 for the first line and 0x40 for the second!


But by the datasheet that you provided, DB7 must be set to gain access to the address counter. There are 7 data bit address lines, DB6:DB0. The 8th data bit, DB7, is used to select between CGRAM and DDRAM. When CGRAM, DB7, is set to logic 0, the address counter of the custom characters is being selected. When DDRAM, DB7 is set to logic 1, DDRAM the DDRAM address counter is being use to select the internal character generator. CGRAM is used to select the memory store where "Custom Built" characters are stored. DDRAM is the character generator that the display uses to display its "Built-In" character set.

If DB6:DB0 (127 possible characters) are used as the CGRAM OR DDRAM address counter and the first character position on line 1 is 0x00 then the data to select that position using the default display characters must be 0x80 because, DB7 must be set to logic 1 to enable the default character generator set.

So, if line 1 starts at 0x00 then, line 1 position 0 becomes:
Code:
 0x00
+0x80
------
 0x80


That is why 0x80 is used for line1:position 0.

And, if line 1 starts at 0x40 then line 2 position 0 becomes:
Code:
 0x40
+0x80
------
 0xC0

That is why 0xC0 is used for line2:position 0.

By the datasheet you provided.

_________________
Carl W. Livingston, KC5OTL
microcarl@roadrunner.com

"There are only two ways to sleep well at night... be ignorant or be prepared."

The original Dragon Slayer !

Long live the AVR!!!
 
 View user's profile Send private message Send e-mail  
Reply with quote Back to top
microcarl
PostPosted: Jan 08, 2007 - 02:24 PM
Raving lunatic


Joined: May 30, 2004
Posts: 8502
Location: Cincinnati, Ohio

sinosoidal wrote:
Another thing i realized with the experiment is that i need to LCD_PutCmd(LINE+numberOfCharacteresToBeWritten) to have a string written.

My entry mode i defined it as increment mode and entire shift off (what is this one related with?).

Another problem is that i can write a string in the first line and in the second.

But if try to write booth it doesnt work:

Code:

#define LINE1 0x80
#define LINE2 0xC0

const char BANNER_1[] = {"Control: 100"};
const char BANNER_2[] = {"Value: 127"};

LCD_PutCmd (LINE1+strlen(BANNER_1));
LCD_PutString (BANNER_1);
LCD_PutCmd (LINE2+strlen(BANNER_2));
LCD_PutString (BANNER_2);


Nuno



No! It is:

Code:
LCD_PutCmd (LINE1 + Offset);
LCD_PutString (BANNER_1);
LCD_PutCmd (LINE2 + Offset);
LCD_PutString (BANNER_2);


String length is determined by the fact that the character strings are inherently NULL terminated by the compiler when they are assigned to the array when it was defined - at least in ImageCraft ICCAVR they are.

The format for
Code:
LCD_PutCmd (LINE1 + 3);

is:
Code:
LCD_PutCmd (StartinPosition + Offset);


IT IS NOT
Code:
LCD_PutCmd (StartingPosition + CharacterCount);

If this is the case, you have either changed my LCD_PutCmd (); function or, your compiler doesn't handle string terminations to the C standard.

_________________
Carl W. Livingston, KC5OTL
microcarl@roadrunner.com

"There are only two ways to sleep well at night... be ignorant or be prepared."

The original Dragon Slayer !

Long live the AVR!!!
 
 View user's profile Send private message Send e-mail  
Reply with quote Back to top
sinosoidal
PostPosted: Jan 08, 2007 - 05:36 PM
Hangaround


Joined: Apr 07, 2006
Posts: 407
Location: Braga, Portugal

Ok. Definitly. I don't know how to read datasheets!

Well. Its seems all clear now!

About that other issue about strlen. It isnt having that behaviour. Now that i got back to this it was not working.

The first thing i tried was to take off that +strlen and put a 0 offset.

Its working perfectly.

Maybe something like the entry set was not defined yet and after the long power out it was now initialized with that.

I just got to thank you all for the incredible patient!

Thx!!!

Best regards,

Nuno
 
 View user's profile Send private message Visit poster's website 
Reply with quote Back to top
sinosoidal
PostPosted: Jan 11, 2007 - 07:49 PM
Hangaround


Joined: Apr 07, 2006
Posts: 407
Location: Braga, Portugal

Hi again,

I'm trying to adapt carl's code to use only port. In this case, only PORTD.

I have the pins 0,1,2 and 3 connected to DB4,DB5,DB6 and DB7.

The pins 4, 5 and 6 are connected to RS,RW and E.

The code i'm using is the following. I'm just trying to initialize for now. Maybe my problem is the bit operations. I'm still very confused about it.

The actual behaviour is the first line filled with black squares and the cursor blinking at the third square. If i program it again, the blinking cursor jumps one time to the right.

Code:

#define F_CPU 1000000
#include <avr/io.h>
#include <util/delay.h>

// Define LCD Register Select as PORTD, 0x10;
#define LCD_RS 4
// Define LCD Read/Write as PORTD, 0x20;
#define LCD_RW 5
// Define LCD Enable as PORTD, 0x40;
#define LCD_E 6

// DISPLAY ON, 2 LINE MODE
#define   PWR_CMD1   0x20
#define   PWR_CMD2   0x20
#define   PWR_CMD3   0xC0

// DISPLAY ON, CURSOR ON, BLINK ON
#define   DL_CMD1   0x00
#define   DL_CMD2   0xF0

// CLEAR DISPLAY COMMAND     
#define CLR_DSP1 0x00
#define CLR_DSP2 0x10

// ENTRY MODE SET
#define ENT_MOD1 0x00
#define ENT_MOD2 0x60

#define LINE1 0x80
#define LINE2 0xC0

#define NULL 0x00

const char BANNER_1[] = {"Control: 100"};
const char BANNER_2[] = {"Value: 127"};

void LCD_Delay (unsigned long int d);
void LCD_IO_INIT (void);
void LCD_INIT (void);
void LCD_PutCmd (char);
void LCD_PutChar (char);
void LCD_PutString (const char *);

void main (void) {
   DDRB = 0xFF;
   PORTB = 0xFF;

   LCD_IO_INIT ();
   LCD_INIT ();

   /*
   LCD_PutCmd (LINE1);
   LCD_PutString (result);
   LCD_PutCmd (LINE2);
   LCD_PutString (BANNER_2);
   */
}

void LCD_Delay (unsigned long int d) {
    unsigned long int n;
    for (n = 0; n < d; n++);
}

void LCD_IO_INIT (void) {
    DDRD = 0xFF; // PORTD is the LCD DATA AND CONTROL LINES
    PORTD = 0x00;
    PORTD |= (1<<LCD_RS);
   PORTD |= (1<<LCD_E);
   LCD_Delay (500); // Wait for the up LCD to power up         
}

void LCD_INIT (void) {
   LCD_PutCmd (PWR_CMD1);
   LCD_PutCmd (PWR_CMD2);
   LCD_PutCmd (PWR_CMD3);

   _delay_us(40);
   
   LCD_PutCmd (DL_CMD1);
   LCD_PutCmd (DL_CMD2);

   _delay_us(40);
   
   LCD_PutCmd (CLR_DSP1);
   LCD_PutCmd (CLR_DSP2);

   _delay_ms(2);

   LCD_PutCmd (ENT_MOD1);
   LCD_PutCmd (ENT_MOD2);

    LCD_Delay (500); // Wait for the LCD to boot up   
}
 
void LCD_PutCmd (char c) {
  PORTD &= ~(1<<LCD_RS);
  LCD_Delay (5); // Wait for the proper setup time to respond to the RS control line
  LCD_PutChar(c);
  LCD_Delay (5); // Wait for the proper setup time to respond to the command being applied
  PORTD |= (1<<LCD_RS);
}

void LCD_PutChar (char c) {
    PORTD |= (1<<LCD_E);
    LCD_Delay (5); // Wait for the proper setup time to respond to the E pulse   
    PORTD = c;
    LCD_Delay (5); // Wait for the proper setup time to respond to the character being applied
    PORTD &= ~(1<<LCD_E);
}
 
void LCD_PutString (const char *p) {
    char n = NULL; // Pointer position counter.
    while (p[n] != NULL) // Keep sending data until the NULL character is found.
         LCD_PutChar(p[n++]);
}
 
 View user's profile Send private message Visit poster's website 
Reply with quote Back to top
bobgardner
PostPosted: Jan 11, 2007 - 08:32 PM
10k+ Postman


Joined: Sep 04, 2002
Posts: 24095
Location: Orlando Florida

Back to 4 bit mode... we went thru this a couple days ago.... the putchar routine that used to put all 8 bits now is two subroutines.. put hi nib of c out on the hi bits, and another sub to put lo nib of c out on the hi bits... involves anding c with 0f and f0 and shifting.... I dont see that you've added that part to Carl's 8 bit program, so need to go look for a 4 bit example to port over....
 
 View user's profile Send private message Send e-mail Visit poster's website 
Reply with quote Back to top
sinosoidal
PostPosted: Jan 11, 2007 - 08:49 PM
Hangaround


Joined: Apr 07, 2006
Posts: 407
Location: Braga, Portugal

bobgardner wrote:
Back to 4 bit mode... we went thru this a couple days ago.... the putchar routine that used to put all 8 bits now is two subroutines.. put hi nib of c out on the hi bits, and another sub to put lo nib of c out on the hi bits... involves anding c with 0f and f0 and shifting.... I dont see that you've added that part to Carl's 8 bit program, so need to go look for a 4 bit example to port over....


Ohh.... ok... But the initialization is not being done correctly. Before write anything to the module i need a correct initialization.

Can you see anything wrong beside that?

Thx
 
 View user's profile Send private message Visit poster's website 
Reply with quote Back to top
JohanEkdahl
PostPosted: Jan 11, 2007 - 11:29 PM
10k+ Postman


Joined: Mar 27, 2002
Posts: 22212
Location: Lund, Sweden

One or several of the first instructions you send to the display is not correct.

When the display powers up it is in 8-bit mode.

So the display wants to se all instructions up to, and including, the one that sets it in 4-bit mode as 8-bit instructions. (Your code sends all instructions as 8-bit instructions, by sending them as two consecutive nibbles. That will not work).

How is this possible in 4-bit mode?, you ask. Well, as the low nibble of these instructions are "don't care" then what you need is to send only the high nible of these instructions - the low nibble of the LCD is unconnected (or maybe tied to ground) and will be read by the display as zeroes).

So you need to follow the sequence below (and I am following the official init sequence, as documented in Hitachis 44780 data sheet - it might be that Carls code does not follow that sequence to the letter):

1. Wait at least 15 ms
2. Send the high nibble of a Function Set instruction
3. Wait at least 4.1 ms
4. Send the high nibble of a Function Set instruction
5. Wait at least 0.1 ms (100 us)
6. Send the high nibble of a Function Set instruction
7. Send the high nibble of a Function Set instruction for 4-bit interface
It is at his point the 4-bit interface becomes interactive. From now on you send complete 8-bit instructions as twop consecutive nibbles, high nibble first.
8. Send a Function Set instruction, 4-bit interface, and N and F bits set to your liking.
9. Send a Display Off
10. Send a Display Clear instruction
11. Send a Entry Mode Set instruction
And then finally
12. Send a Display On instruction

The document that I am referencing is in this thread: http://www.avrfreaks.net/index.php?name=PNphpBB2&file=viewtopic&p=116409#116409, in the file 99rtd006d2.zip, which contains a PDF by the same name. The 4-bit init sequence is on p 46.

Also, as a "preview" I attach a small test program for 4-bit interface and the avr-gcc compiler. It was not my intention to let this out in public just yet as it is intended for a LCD tutorial I am working on, but it might help you move forward. You may use it on the condition that you supply me with any feedback on it that you have. Really! I mean it - you get it in return for being my giunea-pig. If you don't try it out at all I would like to know that too. I have tried it on a ATmega88 and it worked flawlessly for me. I think you will find that the comments in the code should clarify what you will need to change for it to fit your connection of the display. Only one thing that might be akward: You have to have the 4 data bits (DB4..DB7) on the 4 high pins of a port, but I don't think that this will be a problem. If you really need them on the low bits of a port then I can hlp you with this in the week-end. You will also find that all instruction names and signals are in close resemblace with their names in the data sheet I am referring to.

Also, please note that I in no way am saying that Carls code is not working. On the contrary, I am quite sure that it is. View my code merely as as an alternative test.

Hope this helps!


Last edited by JohanEkdahl on Sep 25, 2007 - 10:20 PM; edited 1 time in total
 
 View user's profile Send private message Visit poster's website 
Reply with quote Back to top
Display posts from previous:     
Jump to:  
All times are GMT + 1 Hour
Post new topic   Reply to topic
View previous topic Printable version Log in to check your private messages View next topic
Powered by PNphpBB2 © 2003-2006 The PNphpBB Group
Credits