Hi! Bin grad ziemlich am verzweifeln... Ich habe eine Schaltung mit STM32 und einem MG1206B-Display aufgebaut. Schaltpläne siehe Ahnung. Dazu habe ich dann Ansteuercode für das Display geschrieben, aber leider sehe ich gar nichts außer schwarzes Flimmern am Display, dass gibts aber auch ohne uC. Die Datenblätter zum Display sind hier: * http://www.everbouquet.com.tw/MG1206B.htm * http://www.ortodoxism.ro/datasheets2/e/0lz7coi0w34yg4tykozdpz9ox7cy.pdf Soweit ich das verstanden habe: * CS1/CS2 aktive High * RESET aktive Low (also zum Reset auf low ziehen) Der uC steuert das Display eigentlich korrekt an, am Oszi sah das ganze ziemlich genau so aus wie das Timing-Diagramm im Datenblatt. Allerdings sehe ich eben gar nichts außer eine Fläche auf der alle Pixel leuchten. Der Code ist angehängt, eigentlich sollten auf dem Display mehrere H erscheinen. Hab das ganze auch mal testweise mit dem Simulator (http://www.geocities.com/dinceraydin/djgfxlcdsim/djgfxlcdsim.html) durchgetestet und dort kommt abgesehen von CS1/CS2 aktive Low auch genau die erwartete Ausgabe. Wäre super, falls mir noch jemand einen Tipp geben kann. Danke, Johannes
>aber leider sehe ich gar nichts außer schwarzes >Flimmern am Display, dass gibts aber auch ohne uC. Schliess den Trimmer mal richtig an. So ist der Kontrast voll aufgedreht.
Hi! holger schrieb: >>aber leider sehe ich gar nichts außer schwarzes >>Flimmern am Display, dass gibts aber auch ohne uC. > > Schliess den Trimmer mal richtig an. So ist der > Kontrast voll aufgedreht. Ich kann den Trimmer von NULL-Kontrast bis Voll-Kontrast einstellen, aber da ich kein wirkliches Bild habe kann ich auch nicht sagen, wann der Kontrast richtig ist. Aber stimmt, der Trimmer könnte ihm Schaltplan falsch sein, hab aber leider sowieso keinen in SMD gefunden und daher einen ganz normalen passend eingelötet, also so, dass er auch trimmt. Trotzdem danke, Johannes
>Ich kann den Trimmer von NULL-Kontrast bis Voll-Kontrast einstellen,
Dann liegt es wohl an der Ansteuerung.
Dein uC ist ziemlich schnell. Der KS0108 aber stinkend langsam.
Den BusyCheck hab ich nie zum laufen bekommen und daher
immer mit Delays gearbeitet. Ich vermute mal ein Timing Problem.
Hi! Ich hab mit diversen Delays gearbeitet (bis zu 5us zwischen EN ON/OFF). Busy-Check ist laut Datenblatt normalerweise bei Mikrocontrollern (I/0-Ports) unnötig und wird nur gebraucht, wenn man Memory-Mapped IO verwendet (wie z.B. beim x86). Laut meinen Messungen mit dem Oszi stimmen aber auch die Timings mit dem Datenblatt überein (mindenstes 1us EN-cycle und dabei ca. 500ns EN-ON und 500ns EN-OFF. Eine kurze Frage zum Kontrast hätte ich aber noch: Was soll das Display wenn es nicht angesteuert wird zeigen? Sollen dann keine schwarzen Pixel zu sehen sein oder sind alle schwarz? Danke, Johannes
>Laut meinen Messungen mit dem Oszi stimmen aber auch die Timings mit dem >Datenblatt überein (mindenstes 1us EN-cycle und dabei ca. 500ns EN-ON >und 500ns EN-OFF. Viel zu kurz. Versuchs mal mit 5us EN-ON + 5us EN-OFF. Ein altes Displaytech brauchte bei mir 4us. Eins von Pollin nur 2us. Kommt drauf an wie schnell der Controller auf dem Display getaktet ist. >Eine kurze Frage zum Kontrast hätte ich aber noch: Was soll das Display >wenn es nicht angesteuert wird zeigen? Sollen dann keine schwarzen Pixel >zu sehen sein oder sind alle schwarz? Eigentlich sollte es dann leer sein. Also keine schwarzen Pixel.
1 | /* Ein NOP entspricht ca. 130ns */ |
2 | asm("nop"); |
Ich meine im Programming Manual gelesen zu haben, daß der Cortex ein NOP nicht unbedingt ausführt, wenn er (flapsig) grade keine Lust hat. Er schmeißt ihn evtl schon vorher aus seiner Queue. Oder so. Leider stand dort nichts genaueres. Habe leider grade keinen Zugriff auf das Manual. Jedenfalls bedeutet das wohl, daß ein NOP nicht unbedingt Zeit verbraucht. - dadurch macht Deine Wrteschleife evtl nicht unbedingt das, was du erwartest. Weiß jemand genaueres ?
... eigentlich gehört dort auch ein "volatile" hin. Bist Du sicher, daß Deine Warteschleife nicht komplett wegoptimiert wird ?
[quote] NOP does nothing. NOP is not necessarily a time-consuming NOP. The processor might remove it from the pipeline before it reaches the execution stage. Use NOP for padding, for example to place the following instruction on a 64-bit boundary. Condition flags This instruction does not change the flags. [/quote] Quelle: http://www.st.com/stonline/products/literature/pm/15491.pdf Was lernt man daraus ? Ein NOP hat in C-Programmen für den Cortex-M3 nicht viel Wert... Nimm einen der Timer.. es gibt ja genug davon :-) Dann bist du wenigstens Sicher, daß das Timing stimmt. Trotzdem würde mich interessieren, was "The processor might remove it from the pipeline before it reaches the execution stage." genau bedeutet. Wann genau trifft "might" zu ??
Die M3 Referenz legt nahe, dass sich die beiden verschiedenen NOPs in dieser Hinsicht unterscheiden und nur der 16-Bit NOP rausfliegen kann, der 32-Bit NOP jedoch nicht.
Wie lautet der Opcode für den 32-Bit nop ? Ich zweifle an meinen Google-Fähigkeiten, aber ich finde nix :-( Manchmal kann man sowas ja evtl. doch brauchen. Ich vermute, der GCC nimmt den kürzen 16-Bit Nop, wenn man asm("nop") schreibt, oder ?
Hi! Also dank eines freundliche Vier-Kanal-Oszis weiß ich, dass das NOP nicht wegoptimiert wird. Allerdings habe ich inzwischen auch auf eine andere delay-Methode umgestellt - ohne das sich etwas geändert hätte. Wenn es mal läuft werde ich wohl einen Timer + Befehls-Queue verwenden. Zum 32-bit NOP: Unterstützt der STM32 nicht nur Thumb-Befehlssatz, d.h. alle Befehle sind 16-bit? Trotzdem bin ich leider nicht wirklich weitergekommen. Auch bei 5us oder 10us EN-ON/OFF tut sich leider nix. Habe jetzt als nächstes versucht den Status auszulesen und der bleibt tatsächlich immer auf Busy. Das Display zieht D0-D7 auf active High, wenn ich RW auf High setze. Viel fällt mir nicht mehr ein. Das Datenblatt sagt, dass High Minimum 0,7Vdd oder 2V sein muss, sollte als bei meinen ca. 3,4V kein Problem sein. Alle Verbindungen passen, alles kommt an den Eingängen vom Display an. Alles Versogungsspannungen hab ich auch nachgemessen. Bin noch am überlegen ob ich RESET einfach per Pull-up auf 5V lege, aber eigentlich sollten 3,4V ja ausreichen. Ich frage mich, wie ich das Display dazu bringe, dass es nicht mehr Busy ist... Danke, Johannes
NOP schrieb: > /* Ein NOP entspricht ca. 130ns */ > asm("nop"); Das war übrigens falsch! Vielleicht wurde das NOP an dieser Stelle sogar wegoptmiert, aber die for-Schleife braucht pro Durchlauf eben 130s (Einmal Increment + einmal Vergleich). Da alles mit -0s übersetzt ist, optimiert der Compiler eigentlich auch nichts weg. Johannes
Johannes Schmid schrieb: > Zum 32-bit NOP: Unterstützt der STM32 nicht nur Thumb-Befehlssatz, d.h. > alle Befehle sind 16-bit? Er kann Thumb2 und da ist recht viel in 32 Bits codiert. Aber neu codiert, das ist nicht der alte ARM Befehlssatz.
Wie sieht denn deine Reset Sequenz aus? Ich hab vor kurzem das erste mal ein 160x32 Dot-Matrix Display von Electronic Assembly angesteuert (mit ATmega644). Damit das Display zuverlässig funktionierte muss ich für einen Reset die Reset-Leitung 3x für 100ms(!) low ziehen, danach noch den Controller initialisieren (zeilen, spalten setzen). Evtl. bekommst du so dein Display aus dem "Busy" Status.
>Da alles mit -0s übersetzt ist, >optimiert der Compiler eigentlich auch nichts weg. Wie meinen ? :-)
Hi! Andre R. schrieb: > Wie sieht denn deine Reset Sequenz aus? > > Ich hab vor kurzem das erste mal ein 160x32 Dot-Matrix Display von > Electronic Assembly angesteuert (mit ATmega644). Damit das Display > zuverlässig funktionierte muss ich für einen Reset die Reset-Leitung 3x > für 100ms(!) low ziehen, danach noch den Controller initialisieren > (zeilen, spalten setzen). > > Evtl. bekommst du so dein Display aus dem "Busy" Status. Hmm, klingt ganz plausibel, ich werds mal ausprobieren. Danke, Johannes
Hi! NOP schrieb: >>Da alles mit -0s übersetzt ist, >>optimiert der Compiler eigentlich auch nichts weg. > > Wie meinen ? > :-) Kein LAUFZEIT-Optmierung... Gruß Johannes
Pegel ??? VHi Min ist gleich Vdd * 0,7 = 3,5V !!! Also kann das Display niemals ein Hi erkennen.
Markus Müller schrieb:
> Also kann das Display niemals ein Hi erkennen.
Bischen krass formuliert. Genauer: Es ist nicht gewährleistet, dass das
Display Hi erkennt. Tatsächlich liegt die Schaltschwelle von CMOS meist
um die Vcc/2 herum.
Muss ich den alles auf dem Silbernen Tablett vorkauen? Datenblatt http://www.datasheetcatalog.org/datasheet2/e/0lz7coi0w34yg4tykozdpz9ox7cy.pdf Seite Vih1 = 0.7Vdd = 3,5V für die Pins unter Note (1) Das wäre z.B. RSTB Datenblatt http://www.everbouquet.com.tw/MG1206B.htm Ist das Pin 17 Also muss für diesen Pin der STM32 als "GPIO_Mode_Out_OD" definiert werden und es muss ein Pull-Up Widerstand auf +5V rein. Das LCD wird also niemals sein Reset-Zustand zuverlässig verlassen können. An Pin19 gehört sicher noch ein Vorwiderstand. Besser ist Pin19 an +5V, Pin20 mit Widerstand sind Transistor, den gesteuert mit einem Timer-Ausgang. Dann kann man das Display auch dimmen mit PWM.
NOP schrieb:
> Wie lautet der Opcode für den 32-Bit nop ?
16bit: 0xBF00.
32bit: 0xF3AF8000, offiziell NOP.W
> Damit das Display > zuverlässig funktionierte muss ich für einen Reset die Reset-Leitung 3x > für 100ms(!) low ziehen, danach noch den Controller initialisieren > (zeilen, spalten setzen). Kann ich nicht bestätigen. Bei mir hängt der Reset an einem AVR Pin. Beim einschalten floatet der. Dann setz ich ihn nur auf High und gut. Vermutlich kann man den einfach per Pullup hochziehen und dann nochn 100n gegen Masse. Als Init reicht 0x3F für Display on und 0xC0 für Display Start Line 0. Das funktioniert so mit einem uralten Displaytech 64240A und einem TG12864B von Pollin.
Hi! Markus Müller schrieb: > Muss ich den alles auf dem Silbernen Tablett vorkauen? Sorry, irgendwie hab ich mich in meinem Kopf mit den 0,7VDD total verrechnet (siehe auch Beitrag oben). Weiß auch nicht so genau, warum ich nicht auf die Spannungen geachtet habe, da ich auf der Platine für diverse andere Bauteile extra Pegelwandler verbaut habe. > Datenblatt > http://www.datasheetcatalog.org/datasheet2/e/0lz7c... > Seite Vih1 = 0.7Vdd = 3,5V für die Pins unter Note (1) > Das wäre z.B. RSTB > > Datenblatt > http://www.everbouquet.com.tw/MG1206B.htm > Ist das Pin 17 > > Also muss für diesen Pin der STM32 als "GPIO_Mode_Out_OD" definiert > werden und es muss ein Pull-Up Widerstand auf +5V rein. Danke für die genaue Erklärung. Macht auch viel Sinn. Werds morgen probieren. > An Pin19 gehört sicher noch ein Vorwiderstand. Besser ist Pin19 an +5V, > Pin20 mit Widerstand sind Transistor, den gesteuert mit einem > Timer-Ausgang. Dann kann man das Display auch dimmen mit PWM. Ich meine diesen Vorwiderstand in keinem Datenblatt gesehen zu haben, aber ich lass mich gern eines besseren belehren. Die Hintergrundbeleuchtung funktioniert allerdings (noch?). Leider krieg ich keine zusätzlichen Timer-Ausgänge mehr raus, eh schon alles sehr eng. Was tut man nicht alles für Raumzeigermodulation. @Holger: Dein AtMega(?) arbeitet auch mit 5V, ein ARM normalerweise eben nur mit 3,3V, wobei die (meisten) Eingänge 5V tolerant sind. Deshalb ist es am AVR kein Problem, der liefert dann auch die 5V an Reset. Vielen Dank für die Vorschläge! Gruß Johannes
Hi! Hmm, den Pull-up heute reingelötet, dazu eine sehr lange Reset-Sequence eingefügt, aber ich komm aus dem Busy-Status immer noch nicht raus. Was anzeigen geht dementsprechend auch nicht. Vielleicht hat noch jemand eine Idee, ansonsten werd ich weiter Datenblatt lesen... Danke, Johannes
A. K. schrieb:
>offiziell NOP.W
Super, herzlichen Dank.
Kann ich direkt brauchen (für eine kleine Verzögerung bei einem
Chipselect).
Hi! Markus Müller schrieb: > An Pin19 gehört sicher noch ein Vorwiderstand. Besser ist Pin19 an +5V, > Pin20 mit Widerstand sind Transistor, den gesteuert mit einem > Timer-Ausgang. Dann kann man das Display auch dimmen mit PWM. Nur so nebenbei: Ja, wer lesen kann ist klar im Vorteil... Natürlich steht im Datenblatt unter Note 4 auch die der Strom für den LED-Beleuchtung (250mA). Hab nen Widerstand eingefügt, auch wenn es mit dem eigentlich Problem nicht so viel zu tun hatte... Danke, Johannes
Probiere doch mal die Ausgabe im ms Raster (über Timer) aus zu geben. Einfach die Befehle in einen FOFI Buffer rein schreiben, der Timer arbeitet die Ausgabe dann schon ab. Ich meine ohne das Busy-Bit abzufragen. Diese FIFO Variante hat ja auch den Vorteil, dass man im Code nicht warten muss und die Applikation garantiert weiter arbeitet. Ich steuere die EADOG Displays alle über SPI Bus an, braucht weniger Leitung, dafür kann ich nichts aus dem Display lesen, auch kein Busy Flag, und funktioniert auch. (Ist halt ein einfaches 2x16 Zeichen Display) SPI kann leider dieser Samsung nicht. Ausserdem haben die EADOGs auch den Vorteil direkt mit 3,3V klar zu kommen. Der hat zwar einen Display-Teil der 5V braucht, kann die aber selbst erzeugen. Ich schließe die so an, dass die Display-Controller-Einheit mit 3,3V und die LCD Einheit mit 5V betrieben wird. Dann kann ich den Spannungsdoppeler aus lassen. Hat zwar nichts mit dem aktuellen Problem zu tun, aber vieleicht hilfts.
Hi! Nur zum Abschluss - da stehen so zwei kleine Zahlen an den enden der Pinleiste - nämlich 1 und 20. Und wenn man alles richtig rum anschließt geht's auch... duck Das mit dem Timer hab ich allerdings trotzdem gemacht, blockierende Routienen kann ich gar nicht brauchen... Gruß Johannes
Da musst Du blos die Pins vom Display umbiegen und das Display verkehrt herum einbauen, dann passt die Pinbelegung wieder ;-)
Hi Markus! Naja, genialerweise liegen bei dem Display ja auf 1,2 sowie auf 19,20 GND und 5V, d.h. es fällt einfach nicht auf, dass es genau verkehrt herum ist. Allerdings werd ich mir trotzdem ein Kabel machen, dass alles wieder tauscht (und die nächste Platine richtig...), weil es etwas blöd ist, dass D0-D7 jetzt natürlich genau umgekehrt auf dem PORT liegen und ich alles immer umrechnen muss. Aber jetzt kann ich wenigstes schonmal testen. Aber was solls, es geht. Hab viel über den Controller gelernt und nächste Woche kann ich dann auch anfangen meine Arbeit zu machen... Danke nochmal für die Hilfe! Johannes
Bits drehen, dafür hab ich was:
1 | // Bits drehen
|
2 | u32 revbit32(u32 uidata) |
3 | {
|
4 | asm("rbit r0,r0"); |
5 | return uidata; |
6 | };
|
der Assembler-Befehl rbit macht 32 Bit.
Markus Müller schrieb:
> der Assembler-Befehl rbit macht 32 Bit.
Dafür würde ich dann aber lieber die passende Fkt aus dem CMSIS nehmen:
uint32_t __RBIT(uint32_t value)
Ok, die ist auch in Assembler.
Da ist übrigens noch mehr nützliches drin :-) Reinschauen lohnt sich.
Hi! Würde dann aber wohl insgesamt auf das rauslaufen:
1 | uint8_t data = QUEUE_Pop(&queue); |
2 | uint32_t rdata = __RBIT(data); |
3 | data = (uint8_t) (rdata >> 24); |
Oder sehe ich das grad falsch? Aber an sich zum Testen keine schlechte Idee, in der endgültigen Fassung kann ich es dann hoffentlich rausnehmen! Gruß Johannes
Ja, genau. Mein letztes Projekt mit einem STM32. Hast Du vielleicht bereist gesehen: Beitrag "Re: Heizungssteurung im Eigenbau" Schaltplan ist auch dabei.
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.