Pages

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.

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.

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

LCD_PutCmd (LINE1 + 3);

is:

LCD_PutCmd (StartinPosition + Offset);

IT IS NOT

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.

You can avoid reality, for a while. But you can't avoid the consequences of reality! - C.W. Livingston

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....

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.

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

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.

Attachment(s):

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here.

No guarantees, but if we don't report problems they won't get much of a chance to be fixed! Details/discussions at link given just above.

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

...it might be that Carls code does not follow that sequence to the letter):

This might, in fact, be the case! Although, it will be very close.

I have since done a lot more work on my LCD project, though, it doesn't apply to a tutorial and, it also dosen't use 4 bit mode anymore but, rather; it is for a project that is required to write data to the LCD text based display at a serial communications rate of 115.2K BAUD.

I seriously doubt that a standard text based LCD display can reliably deal with processing and displaying data at 115.2K BAUD using 4 bit mode.

This project has been a real trip - especially getting it to work reliably on about 10 different manufacturers at 115.2K BAUD. But be advised, my current project was inspired by this thread and this thread caused me to get off of my lazy AS.. and, finally get through it. Thanks!

Oh! This is one project that I plan to deposit into the "Projects" forum.

You can avoid reality, for a while. But you can't avoid the consequences of reality! - C.W. Livingston

i have some doubts that i would like to put you. Not now because i need to sleep. But tomorow!

You are most welcome.

Quote:

If you are available to answer them, of course!

There is a high probablility that I will spend much of the weekend in front of my computer (as if I didn't do that all week...), and I will be focusing on LCD issues. Yes, it is about the Tutorial, and I wantyour feedback, which very well could be in form of questions or doubts. Bring it on!

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here.

No guarantees, but if we don't report problems they won't get much of a chance to be fixed! Details/discussions at link given just above.

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

Hi,
I also have some issues with LCD's. I use several (4 bit mode) with the cvavr library. In general all works well but sometimes the LCDs do not reset correctly.
I assume that one can repeat the init sequence anytime to get clean conditions but I have some doubts about it now. On several occasions the LCD seems to hang (must be revived by interrupting the Vcc) if the init is applied after doing some output.
BTW in 4 bit mode do you ground the D0..D3 pins on the LCD and use pull-ups for the others?

I gave a light look across all the code and i have some doubts that i would like to put you.
Not now because i need to sleep. But tomorow!

It's the day after "tomorrow". I'm just about to start another writing pass. It would be nice if you could post what your "doubts" where so I can take them into consideration. Please...

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here.

No guarantees, but if we don't report problems they won't get much of a chance to be fixed! Details/discussions at link given just above.

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

I am using very simple C code program with standard lcd.c and lcd.h libraries for managing 16x1 LCD with KS0066 driver. Trouble is that on LCD is visible only
first half of characters and second half is empty.
I assume that program is working properly (first 8 characters is always visible). In lcd.h is setting only for D44780 and KS0073 controllers. I think that trouble is maybe in internal KS0066 addressing???
Do you know this type of LCD trouble? Can you help me? Thank you. Tomas :(

WE had the same problem in another recent thread. There are 16x1 LCDs that actually function as two-line displays. The first eight characters are on line 1, and the last eight characters are on line two. Try to set your display to two lines and see if that helps. Please note that the addressing is not linear, but rather like this (hex): 00, 01, ... 07, 41, 42, ... 47.

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here.

No guarantees, but if we don't report problems they won't get much of a chance to be fixed! Details/discussions at link given just above.

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

Without looking at the code again, I think you'd have to look at two things:

1) The short timing constraints that is required while sending one byte/nibble. Eg the "data steady time" before E drops. For up to 4 MHz you cant break this constraint even in hand-optimized assembly (IIRC, I actually have the same program in assembler with timing comments but I'm at work now). You might have to insert short "time-wasters"/NOPs.

2) The longer delays are done with delay_ms/delau_us. When the clock is frequency is raised the maximum time that these routines can delay falls. See the avr-libc documentation for the nitty-gritty...

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here.

No guarantees, but if we don't report problems they won't get much of a chance to be fixed! Details/discussions at link given just above.

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

Oppps. Must have copied/pasted some code. The volatile qualifier is not needed.

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here.

No guarantees, but if we don't report problems they won't get much of a chance to be fixed! Details/discussions at link given just above.

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

In case you missed it, the CodeVisionAVR C compiler comes with library function to support your LCD Char. display. I think they offer limited student or eval version and the full price is only a few hundred dollars so maybe you might consider buying that compiler then you could move on with your project.

THANK YOU. After hours of tearing my hair out after never using LCD's before, i finally got my 2x20 lcd working correctly and have a bit of a better understanding of how the commands are sent after examining your code, very helpful. :)

So, what did you end up with? Did you solve the avr-libc issue with util/delay.h? If so, what was it? Or did you take the CodeVision AVR approach?

Can I rub my ego with another running instance of my demo code? :wink:

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here.

No guarantees, but if we don't report problems they won't get much of a chance to be fixed! Details/discussions at link given just above.

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

Johan,your code looks very nice; even an illiterate like me can follow it without a problem. It was just the right thing I needed to get a grip on LCD control.

But... I'm sure the code is right but my display just pulls out a pixel version of a Jackson Pollock art piece and goes blank in a second.It didn't came with instructions so I probably have some of the wiring wrong.

Thanks for sharing it and I'll let you know if I can make the display work later.

So I reckon this first line filled with black blocks means that there was an intialization error, right?

I put a delay before the initialization, in case the power wasn't kicking in fast enough. Still doesn't work.
I doubled the delays on the different functions in case they where too short. Nope
I changed the MCU frequency to 4MHz and still doesn't work.

I'm sure the wiring is right now, so I'm clueless about why it doesn't work.

Perhaps I should try with an external, crystal oscillator instead of the internal one?

Superfreak code of JohanEkdahl worked like a charm !!!
thank you *very* much ...

"same" code that worked ok in assembler was driving me fool with C and i was losing my religion dealing with the hundreds of libraries available here and there but i wasn't able to get a single pixel on :-(

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

This sequence was wrong.
Every command need at least the minimal wait time (37Âµs) after it, so waiting 100Âµs was fine.
So you must insert 100Âµs delay after step 6 and 7.

Yes, I should have made it clear that apart from the (special) delays explicitly mentioned in that sequence the "standard" timing requirements from the data sheet always apply.

It is my belief that after step 6 above the display interface is in "normal operation mode" so the usual timing requirements from the data sheet apply. Could have made that clearer also.

Re the 5 ms: The purpose of my small program has never been to be a real application. (For that, one is better off using e.g. your LCD code.)

The purpose has all the time been to introduce a minimal test - e.g. to prove that the hardware wiring is correct, the contrast control is set correctly etc. For that purpose code like the one from Procyon, Fleury, or your LCD code, can actually be troublesome for an LCD noob. Being clueless they have more code than necessary to mess around with, ultimately onfusing them even more. Then they either give up or come here displaying a total mess - and we then have to start them over from square one. While the minimal test code was evolving I have some time tossed in that 5 ms delay to be well on the safe side - not pretty perhaps, but will not do any harm for the purposes the code has. If all you're doing is testing "Hello LCD!" on your 44780-based module then you're wasting a lot of CPU time any way.. :wink:

Never advocated using my minimal test code for a real app - I try to always recommend going with something already written and proved. E.g. your code.

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here.

No guarantees, but if we don't report problems they won't get much of a chance to be fixed! Details/discussions at link given just above.

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

It is my belief that after step 6 above the display interface is in "normal operation mode" so the usual timing requirements from the data sheet apply. Could have made that clearer also.

It is my belief that the data sheet flowchart is ambiguous about the BF at this point. For that particular instruction the information to the right says: "BF cannot be checked before this instruction." For the next instruction the information to the right says: "BF can be checked after the following instructions". There is no information given about the use of the BF between those two instructions. As Danni says "Every command need at least the minimal wait time (37Âµs) after it, so waiting 100Âµs was fine." I too use 100us since that is what was specified for the previous instruction.

Yes, Don. I agree with that. So, instead of relying on the BF at that point I assume that the timings for the execution of the instruction as given in the data sheet should be used. (Going on memory here - it's been a while since I dabbled with CLCDs on this level).

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here.

No guarantees, but if we don't report problems they won't get much of a chance to be fixed! Details/discussions at link given just above.

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

That's fine for most (but not all) of the instructions after you have finished the first few steps in the initialization sequence.

In this case we are talking about the reset portion of the initialization sequence. Here all of the specified delays are significantly longer than 50 uSec and the mode is always 8-bit so there are no nibbles to consider.