mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik Problem mit LCD an ATMega 644


Autor: Trax Xavier (trax)
Datum:
Angehängte Dateien:

Bewertung
0 lesenswert
nicht lesenswert
Hi, ich versuche grade ein LCD 
(http://www.pollin.de/shop/downloads/D120060D.PDF) an einem Atmega 644 
anzuschließen, der steckt auf so einem ABR-NET-IO Board 
(http://www.pollin.de/shop/downloads/D810058B.PDF)
Die anleitung aus dem 
http://www.mikrocontroller.net/articles/AVR-GCC-Tutorial passte nicht 
ganz da auf dem Board andere Ports für die Kommunikation vorgesehen 
sind, daher habe ich Codes hoffentlich korrekt angepasst.
Leider bekomme ich immer noch kein bild, das der LCD an sich geht weis 
ich da er am LPT Port mit dem Proggi stlcd Funtzt.

Könnte mit einer bitte helfen das zum laufen zu bekommen.

Autor: ... ... (docean) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
wird F_CPU gesetzt? (über define)

Was sagt der Compiler beim Neuerstellen?

Autor: Trax Xavier (trax)
Datum:
Angehängte Dateien:

Bewertung
0 lesenswert
nicht lesenswert
F_CPU ist gesetzt und stimmt auch, wen ich eine LED im sekunden takt 
blinken lasse dann ist es auch ziemlich genau ne sekunde.

Den Kompiler output is in console.txt im Anhang.

Autor: Stefan B. (stefan) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Schaltplan?

Gemäß Code oben (hier ein Ausschnitt)

#define LCD_RW        PD2
#define LCD_RS        PD3

// DB4 bis DB7 des LCD sind mit PD0 bis PD3 des AVR verbunden


Hast du eine unzulässige Doppelbelegung von PD2 und PD3 bei 
Datenleitungen (DB6 und DB7) und Steuerleitungen (RW, RS).

Autor: TraxXavier (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Der Schaltplan ist in meinem ersten post 
http://www.pollin.de/shop/downloads/D810058B.PDF irgendwo in der Mitte 
ist ein plan des Boards, und am ende eine Pinbelegung für ein LCD am EXT 
Stecker.

Doppel Belegung sollte nicht sein die LCD Daten pins DB4 bis DB7 sollten 
auf die pins PD4 bis PD7 am atmel gehen, RW auf PD2, RS PD3, und Enable 
auf PB0

Autor: Stefan B. (stefan) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
> Der Schaltplan ist in meinem ersten post
> http://www.pollin.de/shop/downloads/D810058B.PDF irgendwo in der Mitte
> ist ein plan des Boards, und am ende eine Pinbelegung für ein LCD am EXT
> Stecker.

Du musst es wissen, ob du deinen aktuellen Aufbau zeigst oder 
irgendwas in der Mitte in verschiedenen Hersteller-PDFs zweier 
Baugruppen.

Ich hätte die Frage anders gestellt bzw. nach einer Rückfrage 
schleunigst den Schaltplan beigeschafft ;-)

> Doppel Belegung sollte nicht sein die LCD Daten pins DB4 bis DB7 sollten
> auf die pins PD4 bis PD7 am atmel gehen, RW auf PD2, RS PD3, und Enable
> auf PB0

Der Kommentar im Code sagt was anderes.

Der Kommentar stammt aus der Originalsource aus dem AVR-GCC-Tutorial. Es 
könnte natürlich sein, dass du im eigentlichen LCD-Code umprogrammiert 
hast und nur den Kommentar unverändert übernommen hast. Ich habe im Code 
nachgesehen, ob dementsprechende Kommentare vorhanden sind. Das ist 
nicht der Fall. Eine weitere Analyse habe ich deshalb (und weil der 
Schaltplan nicht vorliegt) nicht gemacht.

Autor: TraxXavier (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ich habe den code umgeschrieben um auf die höheren bits des Ports zu 
schreiben, ich habe nichts kommentiert und auch die alten Kommentare 
unverändert gelassen da das alles es eher schell und provisorisch war.

Ich hoffe das das so stimmt, weis aber nicht mit Sicherheit ob ich da 
alles richtig umgeändert habe.

Der Schaltplan entspricht zu 100% der Beschreibung im PDF damit das dann 
auch mit der originalen firmware kompatibel ist falls ich aus 
irgendeinem Grund wieder den kleineren Atmega 32 mit der Pollin Software 
reinsetzen möchte.

Autor: Trax Xavier (trax)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Niemand ne idee?

Autor: Trax Xavier (trax)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
habe das jetzt mit eigenem code am LPT port halbwegs zum laufen 
gebracht, leider funtzt die 2te zeile immer noch nicht, und wen ich am 
anfang 0011 auf die daten pins lege so wie im tutorial beschrieben kommt 
kein bild.

Hat wer ne idee wie man das ding zum laufen kebommen kan?
#define LCD_EN 0
#define LCD_RS 2

void EN(int x)
{
  UCHAR value = DlPortReadPortUchar(0x37A);
  if(!x)  // ACHTUNG INVERTIERT!
    value |= (1<<LCD_EN);
  else
    value &= ~(1<<LCD_EN);
  DlPortWritePortUchar(0x37A,value);
}

void RS(int x)
{
  UCHAR value = DlPortReadPortUchar(0x37A);
  if(x)
    value |= (1<<LCD_RS);
  else
    value &= ~(1<<LCD_RS);
  DlPortWritePortUchar(0x37A,value);
}

__inline void _delay_us(int c)
{
  for(int i=0;i<c*800;i++)
    __noop;
}

__inline void _delay_ms(int c)
{
  Sleep(c);
}

// erzeugt den Enable-Puls
void lcd_enable(void)
{
  // Bei Problemen ggf. Pause gemäß Datenblatt des LCD Controllers einfügen
  // http://www.mikrocontroller.net/topic/81974#685882
  EN(1);
  _delay_us(1);
  // Bei Problemen ggf. Pause gemäß Datenblatt des LCD Controllers verlängern
  // http://www.mikrocontroller.net/topic/80900
  EN(0);
}

void lcd_send(unsigned char temp1, unsigned char rs)
{
   unsigned char temp2 = temp1;

   RS(rs);                    // RS auf x setzen

   temp1 = temp1 >> 4;              // oberes Nibble holen
   temp1 = temp1 & 0x0F;            // maskieren

   UCHAR value = DlPortReadPortUchar(0x378);
   value &= 0x0F;
   value |= temp1 << 4;        // setzen
   DlPortWritePortUchar(0x378,value);
   lcd_enable();

   temp2 = temp2 & 0x0F;            // unteres Nibble holen und maskieren
   value &= 0x0F;
   value |= temp2 << 4;        // setzen
   DlPortWritePortUchar(0x378,value);
   lcd_enable();

   _delay_us(42);
}

void lcd_nibble(unsigned char temp1)
{
  UCHAR value = DlPortReadPortUchar(0x378);
  value &= 0x0F;
  value |= temp1 << 4;        // setzen
  DlPortWritePortUchar(0x378,value);
  lcd_enable();
}

int _tmain(int argc, TCHAR* argv[], TCHAR* envp[])
{

#if 1
  EN(0);
  RS(0);

    // lcd_nibble(3); - wen das an ist gibts kein bild

    _delay_ms(5);
    lcd_enable();
    _delay_ms(5);
    lcd_enable();
    _delay_ms(5);


  lcd_nibble(2);  // Enable 4-bit mode

  Sleep(140);

  lcd_send(0x06,0); // inkrement / kein Scrollen
  lcd_send(0x0C,0); // Display ein / Cursor aus / kein Blinken
  //lcd_send(0x28,0); //4 Bit Operation,2 Line,5x7 Font  5  --  wen das an ist gibts kein bild
  

  lcd_send(0x01,0); // Clear Display

  Sleep(500);

  // Write Line 1
  lcd_send(0x80,0); // Line 1

  lcd_send('0',1);
  lcd_send('1',1);
  lcd_send('2',1);
  lcd_send('3',1);
  lcd_send('4',1);
  lcd_send('5',1);
  lcd_send('6',1);
  lcd_send('7',1);
  lcd_send('8',1);
  lcd_send('9',1);
  lcd_send('A',1);
  lcd_send('B',1);
  lcd_send('C',1);
  lcd_send('D',1);
  lcd_send('E',1);
  lcd_send('F',1);

  // Write Line 2
  lcd_send(0xC0,0); // Line 2 (does not work yet)

  lcd_send('f',1);
  lcd_send('e',1);
  lcd_send('d',1);
  lcd_send('c',1);
  lcd_send('b',1);
  lcd_send('a',1);
  lcd_send('9',1);
  lcd_send('8',1);
  lcd_send('7',1);
  lcd_send('6',1);
  lcd_send('5',1);
  lcd_send('4',1);
  lcd_send('3',1);
  lcd_send('2',1);
  lcd_send('1',1);
  lcd_send('0',1);

  Sleep(5000);

  // Clear Diaplay x2
  lcd_send(0x01,0);
  lcd_send(0x01,0);

Autor: Stefan B. (stefan) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
> leider funtzt die 2te zeile immer noch nicht

Das ist ein Indiz dafür, dass die Softwareresetsequenz des LCDs nicht 
funktioniert, bei dem die Anzahl der Zeilen eingestellt wird.

Der Kommentar
>   //lcd_send(0x28,0); //4 Bit Operation,2 Line,5x7 Font  5
>                         --  wen das an ist gibts kein bild
passt dazu.

Insgesamt kann das mehrere Ursachen haben:

1/ Die Hardwareresetsequenz des LCDs ist noch nicht angeschlossen, wenn 
versucht wird, per Sofware zu resetten und auf 2 Zeilen zu 
initialisieren. Hier könnte eine längere Wartezeit (mehrere 100 ms) vor 
dem lcd_init() helfen.

2/ Das Timing zwischen den einzelnen Befehlen an das LCD stimmt nicht. 
Wenn mit Warteschleifen gearbeitet wird, müssen diese auch 
funktionieren. D.h. bei _delay_us und _delay_ms muss Optimierung 
eingeschaltet sein usw. Die Zeiten an sich müssen mit dem Datenblatt 
übereinstimmen. Die LCD-Library aus dem AVR-GCC-Tutorial hat z.B. auch 
einen Kommentar zur Länge des EN-Pulses...

3/ Die Befehle an sich müssen stimmen. Es gibt unterschiedliche 
LCD-Controller, die unterschiedlich behandelt werden müssen.

4/ Die Verdrahtung muss passen. Die originale LCD-Library aus dem 
AVR-GCC-Tutorial berücksichtigt z.B. die R/W Leitung nicht, sondern 
arbeitet mit festen Warteschleifen. Umgekert heisst das diese Leitung 
muss auf "Dauerwrite" stehen, d.h. über einen Pulldown auf LOW gezogen 
werden.

Mit http://www.pollin.de/shop/downloads/D120060D.PDF kann man das Timing 
und die Befehle nicht kontrollieren, weil sie einfach darin nicht 
angegeben sind. Und für vergleichbare Datenblätter fehlt die Angabe 
welcher LCD-Controller verbaut ist.

Autor: Trax Xavier (trax)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Also auf PCB des LCD'S sind 2 chips verbaut:

OKI
M5839b
4152B04-2

und

Hitahi 2h2
hd44780a00

ich nähme mal stark an das der hd44780a00 der relevante hier ist.

Autor: Stefan B. (stefan) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Richtig, der HD44780 ist es. Das ist eigentlich der Klassiker. Die 
LCD-Library im Tutorial ist darauf zugeschnitten.

Teste mal mit den drei Änderungen:

1/ Längere Wartezeit vor lcd_int()
2/ _delay_us(4); statt _delay_us(1); in lcd_enable()
3/ R/W Leitung über 10K Pulldown an GND gebunden

Wenn es geht, markiere die Zeilen im Code, die du geändert hast. Dann 
braucht man nicht zwei Dateien miteinander zu vergleichen.

void lcd_enable(void)
{
  LCD_PORT_EX |= (1<<LCD_EN);
  _delay_us(4);                   // kurze Pause (geändert)
  // _delay_us(1);                   // kurze Pause (Original)
  LCD_PORT_EX &= ~(1<<LCD_EN);
}


Man auch oben in der Datei ein Symvol definieren und das entsprechend 
wahr oder falsch setzen. Ich mache das normalerweise so, weil ich dann 
einfach zwischen Originalcode und geändertem Code umschalten kann:

#define NEUER_CODE 1
...
#if NEUER_CODE
  // hier neuer Code
  _delay_us(4);                   // kurze Pause (geändert)
#else
  // hier alter Code
  _delay_us(1);                   // kurze Pause (Original)
#endif /* NEUER_CODE */

Viel Arbeit? Denk mal so: Wenn dir diese Arbeit beim Schreiben des Codes 
bereits zuviel ist, wieviel Arbeit mag sich der potentielle Problemlöser 
beim Lesen des Codes machen?

Autor: Trax Xavier (trax)
Datum:
Angehängte Dateien:

Bewertung
0 lesenswert
nicht lesenswert
Also mit dem Code im Anhang funtzt die erste Zeile vom LCD, und der code
sollte jetzt lesbarer sein ;)
Die Wartezeiten haben nichts geändert, R/W ist auf GND, und ich habe
etwas die Pinbelegung geändert so das nur noch Port D benutzt wird, aber
wie vorher in Umgekehrte nibble folge.

Pin #-LCD  Bezeichnung-LCD  Pin-µC
1  Vss  GND
2  Vcc  5V
3  Vee  GND
4  RS  PD3 am AVR
5  RW  GND
6  E  PD2 am AVR
7  DB0  offen
8  DB1  offen
9  DB2  offen
10  DB3  offen
11  DB4  PD4 am AVR
12  DB5  PD5 am AVR
13  DB6  PD6 am AVR
14  DB7  PD7 am AVR

lcd_command(0x28); // 4Bit  2 Zeilen  5x7 wird nun akzeptiert jedoch
geht wie vorher nur eine Zeile

in der soft Reset Routine musste ich das 0x30 mit einem 0x20 wie bei auf
4-bit setzen tauschen sonst kein bild

laut der Seite da: http://www.geocities.com/dinceraydin/lcd/commands.htm
ist 0x20 4-bit 1 Zeile und 0x28 4-bit 2 Zeilen
kann es sein das da das LCD jetzt immer auf eine Zeile initialisiert und
sich danach nicht mehr auf 2 umstellen lässt?

Ich könnte mal versuchen DB3 auf +5v mit einem 10k zu setzen so das
solange das teil am initialisieren ist und noch im 8 bit Modus es sofort
auf 4 bit 2 Zeilen gesetzt wird also mit einem 0x28, glaubst Du das ist
ne gute Idee?

Autor: Trax Xavier (trax)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
PS: DB3 auf High hat leider keinen erfolg gebracht.

Ne Idee was ich da weiter machen könnte damit dieses teil endlich so 
Funktioniert wie es sollte?

Autor: Peter Dannegger (peda)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Trax Xavier wrote:
> Ne Idee was ich da weiter machen könnte damit dieses teil endlich so
> Funktioniert wie es sollte?

Ein bewährter Code:

http://www.mikrocontroller.net/attachment/30300/lcd_drv.zip


Peter

Autor: Trax Xavier (trax)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Auch mit dem lcd_driver code das selbe Problem:
So wie er da steht geht es nicht, erst wen ich in der Reset Routine 0x30 
mit 0x20 Ersätze, dann aber eben geht nur eine Zeile.

Was für ein behämmertes Display ist den das?

Autor: Trax Xavier (trax)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hat niemand ne idee wie ich das ding endlich unter Kontrolle bekommen 
könnte?
es kann dich nicht sein das sonst niemand dieses model hat, wird ja von 
Pollin vertrieben.

Autor: Stephan Henning (stephan-)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
>> Die Wartezeiten haben nichts geändert, R/W ist auf GND, und ich habe

Arbeitet die Routine mit Busy ???
Das wird dann so nichts.
Falls R/W an GND liegt mußt Du striktes Timing einhalten.
Ich schreibe konstant mit 1ms nach dem Init.
Für den Init 5ms. (ist an der Grenze )

Autor: Trax Xavier (trax)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Also zwischen jedem nibble oder jeden 2 nibbles ein MS pause?
und 5ms pause nach dem init, oki, noch was?

bei dem code hier: 
http://www.mikrocontroller.net/attachment/30300/lcd_drv.zip
was würdest du alles ändern?

bzw: wo gibtes ein sample welches das Busy evaluiert?

Autor: Stefan B. (stefan) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Trax Xavier wrote:

> bzw: wo gibt es ein sample welches das Busy evaluiert?

"R/W Leitung vom Text-LCD ist fix mit GND verbunden und die Ansteuerung 
mit der LCD/AVR-Library von Peter Fleury funktioniert nicht! Was ist 
los?
Die Fleury LCD Library erwartet, dass R/W nicht fix ist, sondern vom 
Programm gesteuert werden kann. Das muss auch so sein, denn Peter liest 
das Busy Flag aus, um Warteschleifen zu vermeiden."
http://www.mikrocontroller.net/articles/LCD#FAQ

Autor: Trax Xavier (trax)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Joa,
ich teste die lib morgen mal durch...

Autor: Trax Xavier (trax)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Naja, wie könnte es den anders sein auch mit dem auslesen des busy flag 
funtzt das kack teil nicht!!!

erst wen ich die Zeile:
LCD_DATA0_PORT |= _BV(LCD_DATA0_PIN);  // _BV(LCD_FUNCTION_8BIT)>>4;
mit der
LCD_DATA0_PORT &= ~_BV(LCD_DATA0_PIN);  // _BV(LCD_FUNCTION_8BIT)>>4;
Ersätze funtzt die 1te Zeile, das selbe wie bei dem lcd_drv code ohne 
busy flag.

Hat den niemand dieses model und könnte mir verraten wie man damit 
zurecht kommt?

Autor: holger (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
>Hat den niemand dieses model und könnte mir verraten wie man damit
>zurecht kommt?

Folge dem Datenblatt und programmiere alles 1:1.
Wenn es kein vernünftiges Datenblatt gibt dann schmeiss
das Teil einfach weg. Besorg dir ein LCD
für das es ein ausreichendes Datenblatt gibt.

Vieleicht ist dein LCD bei deinen Versuchen
beschädigt worden oder war schon defekt.

Aber wer kann das schon wissen.

Autor: Trax Xavier (trax)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Naja, es ist 1:1 und ich bin normalerweise recht gut bei all solchen 
Basteleien und so, bis auf das kack LCD läuft alles bestens, falls 
niemand noch ne gute idee hat hohle ich mit am Montang oder so 'n neues, 
Geld ist ja dazu da das man es ausgibt ;)

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.