Grafikdisplay 320x240 ansteuern

  • nee, wie kommst Du da drauf, Du setzt doch nicht nur einen Portpin in Deiner SW.... ?(

    Ich habe mir die Ausgaben angeschaut. Da waren jeweils 12 Zeilen für das Setzen eines Pins.
    Sechs mal den Pin gesetzt, abwechselnd auf 1 und Null. Resultat: 6x12 Zeilen!



    Aber egal: Es gibt Grund zu feiern (für mich zumindest) - ich habe das Ding geknackt! Display läuft! [Blockierte Grafik: http://www.pagan-spirit.de/wcf/images/smilies/Jippie.gif
    Habe sogar schon eine erste Geschwindigkeitsoptimierung vorgenommen, siehe hier:



    Den ganzen Quelltext lege ich später offen, wenn ich noch mehr erreicht habe. Das hier nur erstmal wegen der wichtigen Bortschaft an die Bascomer, dass man Schleifen mit Endwerten über 255 besser mit verschachtelten Schleifen löst.


    Und nun lobt mich, mein Ego braucht das!!! [Blockierte Grafik: http://www.pagan-spirit.de/wcf/images/smilies/Eigenlob.gif] [Blockierte Grafik: http://www.pagan-spirit.de/wcf/images/smilies/Vielen_Dank_fuer_die_Blumen.gif]

  • Na, dann mal Gratulation! :thumbup:


    wo war denn nun genau das Problem..? - so viel muss man ja anscheinend gar nicht an das Display schicken, oder ist da noch ewig viel Config-Code davor..?


    oder ging es darum, wie die Daten rein kommen..? - das ist ja nun so wie bereits beschrieben:

    also einfach das Byte an den Datenbus anlegen, dann die anderen Leitungen dementsprechend schalten (CS auf Low, dann WR auf Low, etc.), so dass der das Byte übernimmt... das kann man auch in Bascom (einzelne Portpins high und low schalten)


    Ich habe mir die Ausgaben angeschaut. Da waren jeweils 12 Zeilen für das Setzen eines Pins.

    *Noch mal*: Das macht *Bascom* so, und k.A., was sich die Programmierer von Bascom dabei gedacht haben... ?( - in asm ist das eine Zeile (oder 3 bei nem extended Register), und *kein asm-Programmierer* schreibt 12 Zeilen, um nen Portpin zu setzen, wozu auch....?


    Doch ein 8-Bit AVR ist exrem langsam, im Inkrementieren von Variablen, die nicht vom Typ Byte sind.

    Nee - Bascom ist da extrem langsam, nicht der AVR, für den gibt's sowas wie "DWord" gar nicht... ;)


    Hierzu noch ein Tipp: in asm macht man das ja zwangsläufig mit verschachtelten Schleifen, wenn man mehr als 256 zählen muss (Ausnahme: 16 Bit kann man auch in nem "Doppel-Register" wie 24/25 26/27, 28/29 oder 30/31 zählen) - geht es nur darum, soundsoviel Wiederholungen zu zählen, dann setzt man erst ein Register, und zählt es runter statt rauf - warum..?


    Weil ich dann ganz einfach fragen kann:


    Code
    dec temp0 ; runterzählen
    brne _schleife ; wenn noch nicht null, dann Schleife wiederholen


    währenddessen, wenn ich z.B. von 1 bis 240 zähle, muss ich bei der Schleife fragen:


    Code
    inc temp0 ; raufzählen
    cpi temp0, 240 , schon 240 erreicht?
    brlo _schleife ; nein, Schleife weiter


    also ein Befehl mehr... der sich aber auch aufsummiert, bei 76.800 Wiederholungen sind's dann schon 76.800 Takte länger, die das Ganze braucht...


    ausserdem, es macht hier Null Sinn, die *Konstante* 240 (und die anderen beiden) in ner Variablen abzulegen - Bascom speichert das im RAM, so wie ich das einschätze (wenn der schon aus nem simplen Portpin setzen 12 Zeilen macht :D :| ) holt der das dann bei jedem Vergleich aus dem RAM in ein Register (die Zähl-Variable auch), wieder ein paar Takte mehr verschissen... (bzw. ich weiß, dass Bascom das so macht... ;))


    probier's mal aus, statt "For jc1=1 to PC1" mal "For jc1 = 239 to 0", würde mich wundern, wenn das nicht deutlich schneller ginge - bzw., wenn's keinen großen Unterschied macht, dann ist der Compiler noch schlechter als gedacht, wenn er dann nicht im asm-code da auch ne Konstante einfügt etc. ...


    ich weiß, das sind immer so Sachen, die Bascom-Programmierer nicht so interessieren, die sagen ja oft "Das Ding macht, was ich will, da ist's mir doch wurscht, was in dem µC genau vor sich geht", aber im Prinzip schadet es schon nicht, wenn man das doch weiß, bzw. eben einfach so grundsätzliche "Oldschool"-Sachen wie, dass der Computer sozusagen bei 0 zu zählen anfängt, nicht bei 1, manche Vergleiche (eben auf Null oder nicht) für ihn "einfacher" bzw. schneller sind, etc.


    nur so meine Meinung, man kommt natürlich auch prima ohne sowas zurecht...


    Das ermöglich das Einfärben in nur rund drei statt fünf Sekunden!

    8| 3 Sekunden, nur um das Display in einer Farbe zu haben...? - ist das nicht albern...? also z.B. Display löschen (= Farbe schwarz) dauert dann jedes Mal 3 Sekunden...? - und wie lange dann, bis ein Menue mit Buttons etc. aufgebaut wird... ?(


    ich will Dir Dein Bascom nicht ausreden, aber würde mir an Deiner Stelle echt überlegen, doch hier & da Inline-asm einzusetzen, damit es schneller geht...


    die Schleife zum Färben würde in asm so aussehen:



    und auf nem AVR mit 20 MHz ca. 0,1 Sekunden laufen, wenn Du das mit sts statt out machen musst, dann etwas länger (ca. 0,15 Sekunden)... ;)

    It's only light - but we like it!


    Da es sich in letzter Zeit häuft: Ich beantworte keine PNs mit Fragen, die sich auch im Forum beantworten lassen!
    Insbesondere solche von Mitgliedern mit 0 Beiträgen, die dann meist auch noch Sachen fragen, die bereits im entsprechenden Thread beantwortet wurden.
    Ich bin keine private Bastler-Hotline, technische Tipps etc. sollen möglichst vielen Lesern im Forum helfen!

  • wo war denn nun genau das Problem..? - so viel muss man ja anscheinend gar nicht an das Display schicken, oder ist da noch ewig viel Config-Code davor..?

    Da ist noch 'ne ganze Latte Config-Code davor. Den kompletten Code veröffentliche ich später, wenn ich aufgeräumt habe. Ist noch alles q&d.
    Wo das Problem lag? - Du würdest lachen, es ist ja so peinlich ...
    Erzähle ich später, wenn sich meine Scham gelegt hat.



    probier's mal aus, statt "For jc1=1 to PC1" mal "For jc1 = 239 to 0", würde mich wundern, wenn das nicht deutlich schneller ginge -

    Es dauert geringfügig länger.
    10 x einfärben dauert statt 25 Sekunden nun 27 Sekunden.



    die Schleife zum Färben würde in asm so aussehen:

    Habe das mal direkt eingebunden:


    Aber das erzeugt 'ne lange Fehlerliste.
    temp1 nicht definiert, temp2 nicht definiert ...


    und auf nem AVR mit 20 MHz ca. 0,1 Sekunden laufen, wenn Du das mit sts statt out machen musst, dann etwas länger (ca. 0,15 Sekunden)... ;)

    Dann bist Du erstens mein Hero und ich werde zweitens in Zukunft jede Menge Assembler einbinden!
    Aber erstmal muss das laufen.

  • Es dauert geringfügig länger.
    10 x einfärben dauert statt 25 Sekunden nun 27 Sekunden.

    Dann wundere ich mich, wie angekündigt, k.A. was der Bascom-Compiler da veranstaltet... ?(


    EDIT: Ganz was anderes: Irre ich mich, oder ist der XMega nicht ein 32-Bit-µC...? - da sollte dann aber *eigentlich* die große Schleife schneller laufen als drei verschachtelte, weil mit 32 Bit kann man ja leicht bis 76.800 zählen.... muss mir wohl doch mal das DB runterladen... noch mal EDIT: Nee, anscheinend ist der 16 Bit...


    Aber das erzeugt 'ne lange Fehlerliste.
    temp1 nicht definiert, temp2 nicht definiert ...

    klar, ist ja auch nirgends definiert... ;)


    das macht man bei nem Assembler-Programm ganz am Anfang mal "zentral", einfach den Registern Namen zuweisen zum besseren merken...


    kannst Du aber auch direkt hier im Schnipsel machen, oder einfach direkt die Register-Namen benutzen...


    zu dem Thema müsste man dann generell mal in die Bascom-Hilfe/Anleitung schauen, wie das mit dem Inline-asm funktioniert - Bascom "reserviert" ja bestimmte Register für sich, wenn man die dann überschreibt, kommt Murks bei raus... das kann man aber umgehen, indem man die einfach auf den Stack sichert... aber nun k.A., was passiert, wenn nun ein Interrupt dazwischen haut, der wieder in Bascom ausgeführt wird.... ?(


    hast Du nun die ganze SUB LCD_Coloring nur durch diesen Schnipsel ersetzt...? - das geht auch nicht, den Teil oben mit Befehl usw. brauchst Du schon noch, der asm-part ersetzt *nur* die Schleife!


    probier doch neugierhalber mal das aus:



    statt der *Schleife*, also nur die Zeilen 28-36 in Deinem vorletzten Post ersetzen, den Rest Bascom-Code so lassen - das sollte das Display mit nem bunten Muster färben... oder ne Fehlermeldung geben, falls man den PortK mit sts ansprechen muss (siehe DB, bitte selbst nachschauen, mag' mir nicht das Riesen-Teil runterladen für nen AVR, den ich nicht benutze)


    zumindest müssen es weniger Fehlermeldungen sein....


    hier wird nun einfach immer der Wert der Zähler ausgegeben, daher bunte Muster - Du musst ja dann deine Bascom-Variablen R, G und B irgendwie da benutzen - Bascom speichert die eben irgendwo im RAM, müsste man also rausfinden, an welcher Adresse - das sollte irgendwo in der Bascom-Hilfe zu finden sein, muss gehen, sonst wäre das ja sinnlos, wenn man da keine Werte "übergeben" könnte...

    It's only light - but we like it!


    Da es sich in letzter Zeit häuft: Ich beantworte keine PNs mit Fragen, die sich auch im Forum beantworten lassen!
    Insbesondere solche von Mitgliedern mit 0 Beiträgen, die dann meist auch noch Sachen fragen, die bereits im entsprechenden Thread beantwortet wurden.
    Ich bin keine private Bastler-Hotline, technische Tipps etc. sollen möglichst vielen Lesern im Forum helfen!

    Einmal editiert, zuletzt von Pesi ()

  • Habe einen ersten Erfolg zu vermelden, Pesi.
    Habe diese Schleife:

    Code
    For jc3=1 to PC3
      For jc2=1 to PC2
    	For jc1=1 to PC1
      	portk=G :PMWR=0 :PMWR=1   'Grün
      	portk=R :PMWR=0 :PMWR=1   'Rot
      	portk=B :PMWR=0 :PMWR=1   'Blau
    	Next jc1
      Next jc2
    Next jc3


    Erfolgreich durch das hier eretzen können:


    Das peppt schon mal, durchaus.
    Der zehnmalige Aufruf der Routine zum Displayfärben dauert jetzt nicht mehr 25 Sekunden, sonden nur noch 20,7 Sekunden.


    Vorher habe ich alle Varianten von Schleifen in Bascom durchprobiert, auch Rückwärtszähler mit Vergleich auf Null, auch auf ungleich Null, auch Goto-Konstrukte.
    Da war aber in Bascom keine großartige Beschleunigung mehr drin. Einmal war ich immerhin auf 22,X Sekunden (weiß aber nicht mehr, mit welcher Variante).
    Das bisher beste Ergebnis erzielt also eindeutig die Assembler-Einbettung, wenn sie auch noch deutlich hinter den Erwartungen hinterher hinkt.


    Nun muss ich mal schauen, dass ich auch noch die Schleifen selbst in Assembler gebacken bekomme.
    Jedenfalls schon mal vielen Dank Pesi; durch Deine Anregung habe ich mich überhaupt ertstmals mit der Einbettung von Assembler ernsthaft beschäftigt. Bin neugierig, ob sich Deine extremen Minimalzeiten tatsächlich erreichen lassen!

  • ja, sorry, c&p-Fehler, da fehlt der Unterstrich...


    also er soll ja unten in der inneren Schleife zu "_faerben_2" zurück springen, da steht aber falsch "faerben_2" - ebenso bei _faerben_1 und _faerben_0


    einfach mal korrigieren... ich würde den Unterstrich hin machen, das ist so ne Konvention, dass man gleich sieht, dass es ein Label ist...


    zum Verständnis: so Schleife an sich besteht aus den Teilen:


    Code
    ldi r18, 10
    
    
    _faerben_2:


    praktisch der Kopf, da wird erst mal in das Register der Wert 10 geladen, danach das Label, das ist ne Sprungmarke, also so wie man in Bascom ja auch Goto Blabla schreiben kann


    und unten dann der Fuß:

    Code
    dec r18
    	brne faerben_2


    da wird also das Register r18 runter gezählt, und wenn es nicht Null ist, dann wider hoch zum Kopf gesprungen - nach (hier) 10 Durchläufen ist r18 eben auf Null, und dann geht es weiter...


    Oh, Zwischenpost - ja das Schelifenkonstrukt in Bascom bremst halt jetzt noch...


    funktioniert das denn ansonsten, also zeigt das Display wirklich was an..? - ich habe mir inzwischen doch das DB vom XMega angesehen, und das so verstanden, dass das dort deutlich komplizierter wäre, gleich 12 Register pro Port (die man aber nicht alle benutzen muss) und die Ports leider in dem Bereich, den man mit STS und LDS ansprechen muss...?


    EDIT: Ja, ich bin auch sehr gespannt, ob ich halbwegs richtig gerechnet/Takte gezählt habe - und wie schon gesagt, so ist das halt schon ne gute Methode, Du musst ja nicht komplett auf asm umsteigen, aber an manchen Stellen rentiert es sich halt doch ziemlich... ;)

    It's only light - but we like it!


    Da es sich in letzter Zeit häuft: Ich beantworte keine PNs mit Fragen, die sich auch im Forum beantworten lassen!
    Insbesondere solche von Mitgliedern mit 0 Beiträgen, die dann meist auch noch Sachen fragen, die bereits im entsprechenden Thread beantwortet wurden.
    Ich bin keine private Bastler-Hotline, technische Tipps etc. sollen möglichst vielen Lesern im Forum helfen!

    Einmal editiert, zuletzt von Pesi ()

  • Habe ich so umgesetzt:



    Freudiges Ergebnis: Zehnmaliger Aufruf dauert nur noch 14,5 Sekunden. Also 1,45 Sekunden pro Aufruf.
    Das ist eindeutiger Bestwert bis jetzt, wenn auch weit von Deinen 0,1 Sekunden entfernt, immerhin noch Faktor 14,5 drüber.
    Für das Bestergebnis bedanke ich mich schon mal ganz herzlich! Aber wie kommt ein ein solcher Faktor zustande?
    OK, der Controller SCHEINT (weiß ich nicht genau) nur mit 8MHz zu laufen, nicht mit 20MHz. Aber einen Faktor von 14,5 erklärt das nicht.

  • 8| Also wenn das Teil da drauf nur mit 8 MHz läuft, dann wäre das schon bitter, der kann ja bis 32, soweit ich weiß...


    den Aufruf etc. machst Du aber immer noch in Bascom, oder...? - da geht ja auch wieder was verloren...


    z.B. Neni (Synvox), der sich mit Bascom wirklich gut auskennt, hat mir mal erzählt, dass der Aufruf einer Sub ohne nosave in Bascom gut 40-50 Takte braucht, verlassen dann noch mal - weil da eben jede Menge Variablen etc. gesichert werden.


    dann hast Du ja wieder Deine Portpins setzen in Bascom, jeweils 12 Takte, wie Du rausgefunden hast...


    und k.A., wo da sonst noch was verloren geht.... ?(


    das weiß man bei Bascom eben nicht so genau - in Assembler kann man das abzählen:


    der Inhalt der Schleife, also 3x dieses out, sbi, cbi sind 9 Takte - unten dec und brne sind zusammen noch mal 3 Takte - diese 11 Takte werden 76.800 mal durchlaufen, macht also 844.800 Takte - die Schleifen drum rum sind Pipifax, die äußere läuft 240 x durch, also 240 mal dec und brne sind 720 Takte zusätzlich - die innere läuft dann 240 x 32 mal durch, also 7680 x dec und brne, sind 23.040 Takte - dazu dann 7680 x ldi r18 und 240 x ldi r17...


    insgesamt also 876.480 Takte - bei 20 MHz dann eben 876.480 / 20.000.000 = 0,044 Sekunden... :huh: - bei 8 MHz 0,11 Sekunden...


    k.A., ob ich mich irgendwo grob verrechnet habe...? ?(


    EDIT: Ja, Datenblatt doch nicht so im Kopf - sbi und cbi sind jeweils 2 Takte, also für die innere Schleife dann 1.305.600 Takte, insg. 1.337.280, bei 20 MHz wären das 0,06 Sekunden...


    wirklich prüfen könnte man das nur, wenn man's komplett in asm macht...


    oder mal so: füllst Du die 10x in der selben Farbe..? - kannst Du mal 10x hintereinander in jeweils ner anderen (Kontrast) Farbe füllen...?


    Hintergrund: Wenn das füllen an sich wirklich 1,45 Sekunden dauern sollte, dann müsste man das sehen - also wie sich die neue Farbe praktisch über die alte "drüberschiebt"... bei ca. 0,1 Sekunden eher nicht mehr...


    oder es läuft noch irgendein (Timer? Bytes empfangen? oder senden?)-Interrupt, der dazwischen haut - mach' doch mal vor der Schleife cli rein und nach der Schleife sei, damit sperrst Du die Interrupts komplett während der Schleife, darf dann also nix mehr dazwischen funken...

    It's only light - but we like it!


    Da es sich in letzter Zeit häuft: Ich beantworte keine PNs mit Fragen, die sich auch im Forum beantworten lassen!
    Insbesondere solche von Mitgliedern mit 0 Beiträgen, die dann meist auch noch Sachen fragen, die bereits im entsprechenden Thread beantwortet wurden.
    Ich bin keine private Bastler-Hotline, technische Tipps etc. sollen möglichst vielen Lesern im Forum helfen!

    Einmal editiert, zuletzt von Pesi ()

  • den Aufruf etc. machst Du aber immer noch in Bascom, oder...? - da geht ja auch wieder was verloren...

    Nicht der Rede wert.
    Die Färberoutine wird aufgerufen und färbt den gesamten Screen ein.
    In der Hauptschleife mache ich das hier:



    Und man sieht sehr schön, wie das Display sich erst Blau färbt, dann Rot, dann Grün, dann Weiß, dann Schwarz.
    Und wieder von vorn.
    Ich lauere mit der Stoppuhr, bis die Schleife zweimal durch ist, dann gab es also 10 Aufrufe von LCD-coloring. Da kann nicht viel an Takten verloren gehen. Die Farbwechsel folgen auch ohne sichtbare Verzögerung aufeinander.


    Tja, und zwei Schleifendurchläufe, also 10 verschiedenartige Einfärbungen, dauern derzeit halt rund 14 Sekunden.


    Hintergrund: Wenn das füllen an sich wirklich 1,45 Sekunden dauern sollte, dann müsste man das sehen - also wie sich die neue Farbe praktisch über die alte "drüberschiebt"... bei ca. 0,1 Sekunden eher nicht mehr...

    So ist es auch. Sieht aus, wie wenn nacheinander verschiedenfarbige Rollos runtergezogen werden. Dauert je 1,4 Sekunden pro Umfärbung.


    oder es läuft noch irgendein (Timer? Bytes empfangen? oder senden?)-Interrupt, der dazwischen haut

    Nein.
    Habe das Programm von ultimativ minimalsitisch an hochgezogen. Da werden nur die Ports definiert, die Variablen definiert und dann geht es in die Porgrammschleife.
    Nichtmal den Watchdog verwende ich.

  • So ist es auch. Sieht aus, wie wenn nacheinander verschiedenfarbige Rollos runtergezogen werden. Dauert je 1,4 Sekunden pro Umfärbung.

    Das ist höchst seltsam....


    kannst Du mal irgendwie überprüfen, wie schnell der AVR gerade *wirklich* läuft...?


    ich weiß ja nicht, wie das bei XMega ist, aber die meisten ATMega laufen bei Auslieferung auf 1 MHz intern, man muss dann ja erst die Fuses setzen für externen Quarz etc.


    das würde nämlich schon gut hin kommen, 1.305.600 Takte bei 1 MHz wären 1,3 Sekunden, bisschen Bascom-Kram noch dazu, dann sind 1,4 Sekunden recht plausibel... ;)

    It's only light - but we like it!


    Da es sich in letzter Zeit häuft: Ich beantworte keine PNs mit Fragen, die sich auch im Forum beantworten lassen!
    Insbesondere solche von Mitgliedern mit 0 Beiträgen, die dann meist auch noch Sachen fragen, die bereits im entsprechenden Thread beantwortet wurden.
    Ich bin keine private Bastler-Hotline, technische Tipps etc. sollen möglichst vielen Lesern im Forum helfen!

  • Also das klingt gerade dermaßen plausibel ... :!:


    Das Board kommt schon mit aufgespieltem Bootloader und 'ner hinterlegten Grafikdatei daher. Wäre ja wohl sowas von daneben, denn der ab Werk auf nur 1MHz geflasht wäre ... :cursing:
    Ich progge den die ganze Zeit direkt über USB und den Bootloader, musste mich hier nie um die Fuses kümmern..


    Das ist echt blöd, normalerweise entwickle ich meine Schaltungen selbst. Da sehe ich überall Testpunkte vor und so.
    Dieses Board hat null Testpunkte, wo man sie brauchen würde.
    Bei selbstgefrickelten Schaltungen ist es das erste was ich tue, dass ich die Fuses korrekt setze und dann 'nen Bootloader draufknalle. Hier bekommt man das Ding einfach als fertige Baugruppe. Friss und stirb.


    Per USB komme ich aber nicht an die Fuesebits ran.
    Nun habe ich gerade den PDI-Connctor an den vorgesehenen Platz gelötet (ist ab Werk nicht bestückt) und mal mein Glück mit dem ekelhaften, krötenlahmen AVR Studio 5 und dem ACRISP mkII versucht. Da gibt es nur dauernd 'ne Fehlermeldung, dass das Auslesen der Fuses nicht gelungen ist.
    Die grüne LED am Progger leuchtet, sobald ich die Schaltung mit Strom versorge.
    Die Einstellungen für Tool, Device und Interface habe ich ebenfalls vorgenommen, im Studio, unter "AVR programming".


    Irgendwie hatte dieser AVRISP mkII mich noch nie richtig lieb.
    Voll doof, ich habe noch 'nen anderen Progger, aber der kann kein PDI. Jetzt sehe ich keine Möglichkeit, die Fuses auszulesen. ?(

  • Der läuft offenbar mit 2MHz.


    Habe am Anfang vom Programm das hier stehen:
    $regfile = "xm128A1def.dat" 'Verwendeter Controller
    $crystal = 8000000 'Quarzfrequenz


    Das heißt, Bascom "denkt", der Controller läuft mit acht Megaherz und stellt sich für Waitms entsprechend darauf ein.


    Nun habe ich in der Hauptschleife mal alles deaktiviert und nur diese eine Zeile reingesetzt:
    toggle LCD_BLED :waitms 1000


    Ergebnis: LED je vier Sekunden an, vier Sekunden aus ...
    F*ck!
    Wie kriege ich jetzt die Fusebits umgefrickelt, wenn der mkII mich nicht liebt?


    Aber danke für den Wink mit dem Zaunpfahl!
    Eine Beschleunigung um Faktor vier ist also schon mal leicht machbar, indem ich den nur auf echte 8MHz setze.
    Merkwürdig, dass das Färben dann immer noch um Faktor zwei zu langsam wäre.




    Edit:
    Ooohhhh!!!!, Ich sehe gerade was im Datenblatt:

    ------------schnipp---------------
    It is possible to switch between clock sources from software during run-time. After reset the
    device will always start up running from the 2 Mhz internal oscillator.


    A calibration feature is available, and can be used for automatic run-time calibration of the inter-
    nal 2 MHz and 32 MHz oscillators. This reduce frequency drift over voltage and temperature.
    ------------schnapp---------------



    Na da kommt doch Freude auf!!!


    Edit 2:
    WAAAAHHHHH!!!! ERFOOOLG!!!!
    Der saust ja jetzt ab wie Schmidts Katze!!!
    [Rumhüpf und Jauchz!]

    Pesi, ohne Dich hätte ich viel viel länger gebraucht, das herauszufinden! Vielen Dank!!!
    Das, was hier passiert, ist der Grund, warum ich Patente Sch**ße finde und auf Offenlegung & Austausch stehe! Bringt einfach mehr, für Alle.


    Was man in Bascom tun muss, um den ATxmega128 auf 32MHz zu prügeln, ist das hier am Anfang des Quellcodes:

    Code
    $regfile = "xm128A1def.dat"         	'Verwendeter Controller
    $crystal = 32000000   '8000000      	'Quarzfrequenz (in der Regel 8000000 oder 14745600 oder 16000000)
    
    
    $lib "xmega.lib"
    $external _xmegafix_clear
    $external _xmegafix_rol_r1014
    Config Osc = Enabled , 32mhzosc = Enabled     	'We use internal 32MHz
    Config Sysclock = 32mhz , Prescalea = 1 , Prescalebc = 1_1   	'Internal 32MHz, no prescaler


    Habe eben nochmal meine drei For/Next-Schleifen aktiviert und mit dem Assemblerteil verglichen.
    Ergebnis Bascom-Code: 100 Umfärbungen dauern 29 Sekunden. Also 0,29s pro Umfärbung.
    Ergebnis Assembler-Code: 100 Umfärbungen dauern 9,4 Sekunden. Also 0,094s pro Umfärbung.
    Assembler tut den Job also gut dreimal so schnell.


    Manno ey, gestern war ich noch froh, die knapp 5 Sekunden erst auf 3, schließlich "gar" auf 2,5 Sekunden optimiert zu haben. Heute sind wir bei 0,094 Sekunden!
    Boah, bin ich jetzt ein frohes Irrlicht!

  • Pesi,


    also ich muss sagen, dass Du echt einen total tollen, klaren Programmierstil drauf hast.
    Habe mir inzwischen verschiedene Assembler-Einbettung angeschaut, auf Roboternet und sonstwo, aber nirgendwo habe ich so klaren und effizienten Code gesehen.



    Komplettes Edit des gesamten Postings, fehlerhafter Code entfernt:
    Pesi, in Deinem Code waren die SBI und CBI jeweils vertauscht.
    Jetzt wird mir auch klar, dass das "S" in SBI für "set" steht und das "C" in CBI für "clear".
    Trotz vertauschtem Set und Clear funktionierte Dein Code, aber laut Datenbblatt (und meinem Bascom-Code) muss der PortJ.3, also das Signal PMWR negativ geclockt werden.



    Abermaliges komplettes Edit:
    Ich habe jetzt die Einfärbe-Routine erfolgreich komplett auf Assembler umgestellt.
    Vorher gab es noch ein Problem, als ich Register 23 verwendete. Nachdem ich das auf das noch freie Register 19 umstrickte, war alles gut.

  • ja, da müsste man eben mal in der Bascom-Hilfe gucken, was da noch an Registern frei ist etc.


    Pesi, in Deinem Code waren die SBI und CBI jeweils vertauscht.
    Jetzt wird mir auch klar, dass das "S" in SBI für "set" steht und das "C" in CBI für "clear".
    Trotz vertauschtem Set und Clear funktionierte Dein Code, aber laut Datenbblatt (und meinem Bascom-Code) muss der PortJ.3, also das Signal PMWR negativ geclockt werden.

    ah, sorry, das hatte ich verwechselt - anscheinend übernimmt der dann die Daten an der negativen Flanke, und so eine hat man ja auch mit sbi cbi...


    diese ganzen Assembler-Mnemonics sind praktisch Abkürzungen, die meist gebrauchten kann man sich auch gut merken wie eben sbi und cbi oder inc und dec, add, oder brne (Branch if not Equal) usw. - da gibt's bei Atmel auch ne Befehlsübersicht, wo die alle drin stehen, mit Infos dazu, welche Flags beeinflusst werden, wie viele Takte der Befehl braucht, etc.


    Danke für's Lob! - mir hat nebem dem Lesen des Datenblattes auch dieses Tutorial recht viel geholfen, als ich mit dem AVR-Assembler angefangen habe...


    jedenfalls coole Sache so, da kannst Du weiter in Bascom programmieren, aber hier und da mal Assembler rein machen, wenn's schneller gehen muss - das sind ja meist so Sachen, wo viele Daten rumgeschoben werden etc., und daher dann auch sehr einfacher Code...

    It's only light - but we like it!


    Da es sich in letzter Zeit häuft: Ich beantworte keine PNs mit Fragen, die sich auch im Forum beantworten lassen!
    Insbesondere solche von Mitgliedern mit 0 Beiträgen, die dann meist auch noch Sachen fragen, die bereits im entsprechenden Thread beantwortet wurden.
    Ich bin keine private Bastler-Hotline, technische Tipps etc. sollen möglichst vielen Lesern im Forum helfen!

  • Wenn auch noch längst nicht fertig, habe ich mich anderweitig breitschlagen lassen, den gegenwärtigen Ist-Stand zu veröffentlichen.


    Was geht:

    • Einfärben des ganzen Displays in beliebiger 24-Bit Farbe (dauert unter 0,1 Sekunde, dank Assembler-Einbindung - vielen Dank an Pesi!).
    • Setzen eines einzelnen Punktes an beliebiger Position, in beliebiger Farbe. (Schon recht gut geschwindigkeitsoptimiert: Jeden der 76800 Pixel einzeln mit 24 Bit umgefärbt, dauert nur 0,5 Sekunden, rein in Bascom.)
    • Ausgabe von Textmeldungen an beliebiger Position, in den Fontgrößen 5x8 Pixel und 8x16 Pixel.
    • Drehen des Displayinhalts um 90 Grad.


    Gibt es hier:
    http://www.edv-dompteur.de/download/...scom_V0.29.zip


    Das Archiv entpackt einen einzigen Ordner, der fünf Dateien enthält.


    Wie man aus den Dateinamen unschwer erkennen kann, ist "XMega Test_29.bas" das Hauptprogramm, von dem aus mit Hochsprachenbefehlen auf das Display zugegriffen werden kann.
    Die anderen vier Dateien, mit dem vorangestellten "incl_" werden ins Huptprogramm includet.


    Die auffällig markierte Hautschleife enthält noch ein paar auskommentierte Routinen.
    Die funktionieren auch, wenn man sie denn aktiviert.


    Compiliert man den Kram so wie er ist, passiert Folgendes:

    • Zunächst wird das Display grün gefärbt.
    • Dann erscheinen einige Zeilen Text in zwei Schriftfonts, wobei die Strings teilweise absichtlich länger sind, als auf den Screen passt. Der Text im größeren Font liegt dabei über dem Text mit dem kleinen Font.
    • Dann färbt sich das Display metallgrau.
    • Und schließlich dreht sich die Orientation um 90 Grad und wieder wird der Text ausgegeben.


    Das Drehen um 90 Grad plus Textausgabe läuft dann permanent in einer Schleife.


    Wer das im Startposting verlinkte Board von Mikroelektronika verwendet, braucht nichts anzupassen. Einfach kompillieren und flashen.
    Damit das bei Programm auch auf anderer Hardware läuft, muss in der includeten Initialisierung dieser Block angepasst werden:


    Code
    LCD_RST alias PortJ.1
    LCD_RST=0 'Reset. Lowaktiv, zu Anfang auf Reset halten.
    PMRD alias PortJ.2 :PMRD=1 'Read. Lowaaktiv
    PMWR alias PortJ.3 :PMWR=1 'Write. Lowaktiv
    LCD_RS alias PortJ.4 'Index/Command-Selector. Low für Zugriff auf Inxexregister, High für Zugriff auf Command.
    LCD_CS alias PORTJ.5 :LCD_CS=0 'Chip select


    Der 8-Bit Datenbus ist bei mir PortK. Muss gegebenenfalls ebenfalls angepasst werden.


    Weiterhin ist es wichtig, dass die Displaysignale IM0-IM3 wie folgt angesteuert werden:
    IM0 high
    IM1 high
    IM2 low
    IM3 low


    Ich werde später auf meiner Website einen Downloadbereich einrichten, wo man die jeweils akuelle Version herunterladen kann. Und zwar hier:
    http://www.EDV-Dompteur.de/download/download.htm
    (NOCH existiert die Seite nicht, daher zunächst obigen Direktlink verwenden)


    Der aktuellen Version 0.29 fehlen nämlich noch die grundlegenden Grafikroutinen.
    Auch ist der Quellcode noch ziemlich Baustelle. Funktioniert zwar, aber ist halt noch recht chaotisch.
    Ausgereiftere Versionen daher in Zukunft auf meiner Website (dann brauche ich die Info nicht in mehreren Foren zu posten).

  • coole Sache! :thumbup:


    ich habe gesehen, Du zeichnest den Text einfach weiß auf Schwarz...? (oder andersrum...) - mach' doch die beiden Farben auch noch in Variablen, dann kann man ganz einfach Text in beliebiger Kombination von Vorder- und Hintergrundfarbe ausgeben...


    evtl. mit der Option, nur die Pixel zu setzen, die in der Vorlage (Data-Zeilen) "1" sind, dann kann man auch Text transparent auf einen vorher gezeichneten Hintergrund machen... ;)


    Aus Neugier: Wie hast Du den Font denn erstellt...? - ich habe sowas vor 25 Jahren mal gemacht für nen Metallpapier-Drucker, ganz schnöde auf Karopapier gezeichnet, und dann selbst die Bytes "ausgerechnet"... :D


    aber dafür gibt's inzwischen ja bestimmt auch SW (der Matrix-Editor von Denim..?)

    It's only light - but we like it!


    Da es sich in letzter Zeit häuft: Ich beantworte keine PNs mit Fragen, die sich auch im Forum beantworten lassen!
    Insbesondere solche von Mitgliedern mit 0 Beiträgen, die dann meist auch noch Sachen fragen, die bereits im entsprechenden Thread beantwortet wurden.
    Ich bin keine private Bastler-Hotline, technische Tipps etc. sollen möglichst vielen Lesern im Forum helfen!

  • ich habe gesehen, Du zeichnest den Text einfach weiß auf Schwarz...? (oder andersrum...) - mach' doch die beiden Farben auch noch in Variablen, dann kann man ganz einfach Text in beliebiger Kombination von Vorder- und Hintergrundfarbe ausgeben...

    Das ist auch vorgesehen. Für die Pixelfarben dienen jetzt schon die globalen Variablen RGB_R, RGB_G und RGB_B.
    Die setze ich hier zwar noch testweise direkt in der Routine LCD_Text(), aber wenn man die da auskommentiert, kann man die vorher setzen.


    Ich will von Subroutines mit Übergabeparameter ganz weg, weil die unglaublich die Sache verlangsamen und den Code aufblähen. Statt dessen also globale Variablen, die man bei Bedarf zuvor setzt; wobei es genügt, die einmalig zu setzen, wenn man eine Ausgaberoutine anschließend mehrfach aufruft.
    Habe das gegenwärtig nur noch nicht voll umgesetzt - da herrscht noch ein fröhliches Durcheinander von Subs mit Parametern und globalen Variablen.
    Eigentlich noch zu früh, für eine Veröffentlichung, aber ich wurde darum gebeten ...



    evtl. mit der Option, nur die Pixel zu setzen, die in der Vorlage (Data-Zeilen) "1" sind, dann kann man auch Text transparent auf einen vorher gezeichneten Hintergrund machen... ;)

    Ebenfalls angedacht, aber das mit der Transparenz ist nicht einfach, wenn es schnell gehen soll.
    Die Routine zur Textausgabe birgt ohnehin noch Potenzial für starke Beschleunigung.
    Gegenwärtig ruft die für jedes ASCII-Zeichen einzeln die Routine LCD_cursor() auf, die ihrerseits die Routine Lcd_area() aufruft. Reine Zeitverschwendung.
    Besser ist es, wenn LCD_Text() zuvor ein Fenster berechnet, das den gesamten String aufnehmen kann und dieses Fenster dann füllt.
    Aber dabei ist Transparenz echt schwierig.


    Man beschreibt den jeweiligen Bereich halt in einem Rutsch. Das Display hat dazu eine Autoincrement-Funktion.
    Wenn man die umgeht, leidet die Geschwindigkeit sicher deutlich.



    Aus Neugier: Wie hast Du den Font denn erstellt...? - ich habe sowas vor 25 Jahren mal gemacht für nen Metallpapier-Drucker, ganz schnöde auf Karopapier gezeichnet, und dann selbst die Bytes "ausgerechnet"... :D

    Dazu war ich zu faul. Habe die beiden Fonts geguttenbergt und die resultierenden DATA-Zeilen so stark verändert, dass selbst der Autor sie nicht wiedererkennen würde.
    Davon abgesehen liegen Bascom schon Fonts bei, die ich nur noch nicht integriert habe.



    Font-Editoren mit Code-Ausgabe gibt's heutzutage wie Sand am Meer ;) . Als Beispiel hier mal der Link zu einem recht guten, welcher kostenlos erhältlich ist: GLCD Font Creator.

    Hey, danke für den konkreten Link!
    Ich war der irrtümlichen Meinung, Mikroelektronika würde diesen Fonteditor für teures Geld verkaufen.


    Aber Fonts mit einem Fonteditor selbst zu erstellen ist echt saumäßig viel Arbeit. Habe sowas vor 20 Jahren schon auf dem ATARI gemacht.
    Bin der Meinung, dass man derart grundlegende Sachen guttenbergen sollte.
    Das ist nun echt nichts in irgendwie "schöpferischer Höhe", das ist einfach nur Fleiß und stundenlanges Pixel-Geklicke.

  • Das ist auch vorgesehen. Für die Pixelfarben dienen jetzt schon die globalen Variablen RGB_R, RGB_G und RGB_B.
    Die setze ich hier zwar noch testweise direkt in der Routine LCD_Text(), aber wenn man die da auskommentiert, kann man die vorher setzen.

    Ah, klar - dann brauchst Du halt noch mal 3 Variablen, für den Hintergrund noch extra...


    Dass das mit der Transparenz nicht so einfach geht, ist mir nun (gestern war's doch schon spät... :whistling: ) auch klar, wenn Du kein Pixel setzt, dann gibt's ja auch kein Increment... da müsste man dann z.B. für jedes Text-Üixel die Position "abscannen" und dann je nachdem, ob da der Text ein Pixel hat, einzeln (mit Deiner Funktion "LCD_SetPoint()" ) das Pixel setzen - wenn die für das gesamte Display nur 0,5 Sekunden braucht, kann das für ne zeile Text auch nicht lange dauern... ;) (aber natürlich deutlich länger als jetzt, schon klar...)


    Besser ist es, wenn LCD_Text() zuvor ein Fenster berechnet, das den gesamten String aufnehmen kann und dieses Fenster dann füllt.
    Aber dabei ist Transparenz echt schwierig.


    Man beschreibt den jeweiligen Bereich halt in einem Rutsch. Das Display hat dazu eine Autoincrement-Funktion.

    Du meinst jetzt, den String im AVR-RAM berechnen, und dann das in einem Rutsch in den Display-Controller rüber...?


    da sollte das aber dann recht leicht gehen mit der Transparenz, erst den Bereich aus dem Controller in's RAM zurücklesen (das geht ja, oder? - auch mit Autoincrement?), dann nur die Bytes überschreiben, wo der Text ein Pixel hat, und dann wieder zurück...


    Neni: Von mir auch danke für den Link, sowas kann man immer brauchen.... ;)

    It's only light - but we like it!


    Da es sich in letzter Zeit häuft: Ich beantworte keine PNs mit Fragen, die sich auch im Forum beantworten lassen!
    Insbesondere solche von Mitgliedern mit 0 Beiträgen, die dann meist auch noch Sachen fragen, die bereits im entsprechenden Thread beantwortet wurden.
    Ich bin keine private Bastler-Hotline, technische Tipps etc. sollen möglichst vielen Lesern im Forum helfen!