Hi ihr,
ich habe da ein paar ADCs zu machen die für unterschiedliche Sachen
benutzt werden. Unter anderem ist da auch eine Frequenzbestimmung und
Aufnahme von zwei Signalen mit bei. Da mein kleiner Atmel nicht schnell
genug ist um alles gleichzeitig zu machen währe es nicht schlecht den
Inhalt der ISR ändern zu können. Also die Prozessor 3 Sachen
nacheinander machen lassen:
1. Frequenz bestimmen
2. Signale aufnehmen
3. Auswertung
Eine If Abfrage würd ich mir gerne in der ISR Sparen wenn möglich,
immerhin gebe ich ja vor was sie machen soll.
Für die Auswertung werden dann die ADCs gestoppt und eine Funktion
aufgerufen die das macht und hinterher den Frequenzzähler wieder
anschmeißt.
Bisher funktioniert alles drei wunderbar, auch der Wechsel zwischen
Aufnehmen und Auswerten, nur nicht der wechsel zwischen Frequenz
bestimmen und Signal aufnehmen.
Dieses Posting enthält keine Frage, noch nicht mal ein Fragezeichen. Es
erzeugt jedoch ein implizites Fragezeichen im Kopf dessen der versucht
zu verstehen was Du eigentlich mitteilen willst.
Für die Frequenzmessung nutzt man normal keinen ADC_interrupt. Vor allem
ist der ADC Interrupt beim AVR eher unkritisch, weil der ADC relativ
langsam ist (außer beim Xmega) - da hat man also genügend Zeit für einen
IF abfrage.
Der Code und die Interruptvektoren sind im Flash speicher, lassen sich
also nicht so ohne weiteres ändern. Wenn es sein müsste könnte man ggf.
Umschalten zwischen Bootloader und normalem Modus und damit die
Interruptvektoren umschalten. Normal geht es aber auch ohne. So lange
braucht die Abfrage in der ISR nicht.
Wenn es wirklich so Zeitkritisch ist, dann könnt man ggf. die ISR in ASM
schreiben. Die Compiler haben da noch ein wenig extra Overhead, den man
umgehen kann und dafür die Verzweigung einbauen kann.
Um welche Sprache geht es eigentlich ?
Ich halte zwar nichts von Deinem Ansatz, aber wie wär’s mit einem
indirekten Sprung am Anfang der ISR.
Die Sprungadresse wird dann - dem nach je - vom Hauptprogramm
manipuliert bzw. vorgegeben.
Es geht um C im AtmelStudio. AVR ist ein 1248p.
Konkret wird die Lestung und Phasenverschiebung eines komplett
unbekannten Systems gemessen. ich hatte keine bessere Idee, wenn du eine
hast dann immer her damit. Da ich noch anfänger bin bin ich für
Vorschläge immer offen.
Darki schrieb:> Da mein kleiner Atmel nicht schnell> genug ist um alles gleichzeitig zu machen
Der kleine Atmel ist ein M0? Dann nimm einen M3 oder M4. Dein Programm
ist 1:1 übertragbar. That 's modern computing, that 's ARM.
Also bei manchen PIC's (ich glaube z.B. der dsPIC30F33) gibt es für jede
ISR Adresse auch eine alternative.
Welche der beiden angesprungen wird, kann über ein Register eingestellt
werden. Gibt es sowas beim Atmel nicht?
Nachtrag:
Diese Art dein Problem zu lösen ist natürlich etwas kurzsichtig. Soll
dein Programm mal mit einer weiteren Messung erweitert werden, stehst du
ja wieder am Anfang. Also nimm wie schon von anderen gesagt einen
schnelleren Controller.
Da ich anfänger bin bleibe ich erstmal bei diesem niedlichen kleinen
Projekt mit meinem Atmega, mache danach noch das ein oder andere was
andere Anforderungen hat und steige dann eventuell mal um auf einen
Cortex.
Momentan geht es mir vorallem um Signal aufnehmen und verarbeiten. Also
kleinen Lautsprecher an Frequenzgenerator mit Shunt Strom und Spannung
messen und mal schauen was ich mit dem 1248p da rausholen kann.
Nein, das Projekt hat keinen tieferen Sinn außer lernen.
man oh man schrieb:> Bonner schrieb:>> Gibt es sowas beim Atmel nicht?>> Warum setzt jeder Atmel mit AVR gleich? Atmel hat auch andere> Architekturen!
Habe ich doch nicht! Darki hat in seinem ersten Post von Atmel
geschrieben worauf ich mich bezogen habe.
Darki schrieb:> Eine If Abfrage würd ich mir gerne in der ISR Sparen
Ich weiß zwar nicht, was Du alles in der ISR machen musst, aber ich kann
mit kaum vorstellen, dass "if" oder "case" nennenswert viel
Prozessorleistung kostet.
Oder Du bist sowieso schon so knapp an der Grenze, dass es nur eine
Frage der Zeit ist, dass Du einen schnelleren µC brauchst.
Gruß Dietrich
spunt schrieb:> Cortex mmm... , lecker schrieb:>> That 's modern computing, that 's ARM.>> www.mikrocontroller.net/topic/351863#new
Na Moby, jetzt als Jung-Spunt unterwegs. ;-)
Schau mal hier. Versuch da zu helfen, oder hast du keine Ahnung davon?
www.mikrocontroller.net/topic/351731#new
www.mikrocontroller.net/topic/351391#new
www.mikrocontroller.net/topic/351766#new
spunt schrieb:>> Atmel hat auch andere>> Architekturen!>> Die laufen nebenher.
Selbstsprechend ... ;-)))
Jetzt haben wir schon 3 Controllertypen im Gespräch, ich fände es schön
wenn wir bei einem bleiben könnten. Wie währe es mit dem des
Fragenstellers? also MEINEM?
Ich nutze einen AVR. Der AVR ist von Atmel. Der Cortex ist auch von
Atmel, hab ich aber nicht und nur weil ich das Programm darauf verwenden
kann keißt das nicht das ich so ein ding initialisieren kann/will. Daher
bleiben wir jetzt einfach mal bei den AVRs. In meinem konkreten Fall den
1248p. Wieso ich diesen Kontroller verwende: Er ist übersichtlich, hat
einiges an Funktionen und ist verständlich.
Wieso ich keinen Pic verwende: Sry, ich haben nunmal mit AVR angefangen.
Wieso ich keinen Cortex verwende: Er ist mir zu unübersichtlich für den
Anfang.
So, genug ausgekotzt.
Ist jetzt jemand bereit mir bei meinem Problem zu helfen?
Wie gesagt, Spannung und Strom aufnehmen. Die Berechnung kriegt das ding
nicht nebenher hin weil ich eine möglicht hohe Abtastrate brauche/haben
will. Daher schauen wie schnell es denn sein muss, Abtasten, berechnen.
Nein, ich will keinen fertigen Code, ich brauche einen Denkanstoß oder
den Befehl der mir fehlt oder eine Idee wie es anders geht.
Darki schrieb:> Da mein kleiner Atmel nicht schnell> genug ist um alles gleichzeitig zu machen
Erklär mal, warum nicht.
Um brauchbare Lösungen zu bekommen, mußt Du schon etwas konkreter
werden.
Allgemein lese ich alle benötigten ADC-Eingänge der Reihe nach aus und
speichere die Ergebnisse in einem Array. Das Main kann dann damit
machen, was es will.
Die Idee, verschiedene Sachen in Interrupts zu machen, klingt nicht gut.
Die Interrupts machen nur die nötigen Sachen, die Verarbeitung macht
dann das Main.
Darki schrieb:> Konkret wird die Lestung und Phasenverschiebung eines komplett> unbekannten Systems gemessen.
Das "unbekannt" glaub ich Dir jetzt nicht. Du wirst doch wissen, welche
Frequenz-, Spannungs- und Strombereiche gemessen werden sollen und mit
welcher Genauigkeit.
Ja was für eine Antwort willst du denn jetzt lesen? Will dich nicht vom
PIC überzeugen. Das war nur eine Rat mal ins DB zu sehen ob es die
Funktion auch bei deinem AVR gibt. Ich weiß es ja nicht.
Traurig aber wahr: Ist dein Controller zu langsam, ist er zu langsam.
Evtl. kannst du dein Code etwas optimieren aber den müsstest du dann
Posten.
Darki schrieb:> Nein, ich will keinen fertigen Code, ich brauche einen Denkanstoß oder> den Befehl der mir fehlt oder eine Idee wie es anders geht.
Die ISR ist fest ins FLASH gebrannt. Daran kannst du nichts ändern.
Was spricht denn gegen eine IF-Abfrage?
Warum kannst du die Auswertung nicht in der Hauptschleife machen?
Der Denkanstoss wäre: Kann man das Programm nicht anders gestalten?
STK500-Besitzer schrieb:> Der Denkanstoss wäre: Kann man das Programm nicht anders gestalten?
Ist mir auch schon öfter passiert, nach einem 2.Blick und Umstellen des
Programmablaufs wurden nur noch 10% der vorherigen Rechenleistung
benötigt.
Danke an Peter und STK500-Besitzer,
Die Antwort, "nein es geht nicht" passt mir schonmal. Damit weiß ich das
meine Idee nicht funktioniert und ich mir was anderes überlegen muss.
Wieso das Hauptprogramm nicht parallel zur ISR arbeiten soll:
Ich nehme das System als unbekannt an um es Variabel zu halten. Die
Pegel die ich bekomme kann ich natürlich über die Hardware vor dem AVR
beeinflussen.
Das Signal ist periodisch (oder wird als solches angenommen). Die
Frequenz ist variabel. Um eine höhere Bandbreite zu erreichen halt der
weg über unterschiedliche Zeiten in denen der Controller
unterschiedliche Sachen macht.
In der ISR sollte daher so wenig wie möglich stehen.
Amateur schrieb:> Was spricht eigentlich gegen meinen Vorschlag?
Daß niemand weiß, worin eigentlich der Flaschenhals besteht.
Bisher sieht der Thread ja so aus: "Ich verrate nix, aber benötige
Hilfe."
@Amateur
Da ich ihn noch nicht wirklich verstanden habe und zu viel mit den
anderen Antworten und durchdenken zutun hatte. Ich versuch das mal zu
überdenken wie du es meinst und wie es funktionieren könnte :D
Außerdem bin ich zu dem Zeitpunkt noch davon ausgegangen das es eine
Möglichkeit gibt den gleichen ISR Vector für unterschiedliche Funktionen
zu verwenden^^
@ Peter
Ein variabler Sprung am Anfang von Irgendetwas sollte unabhängig vom
eigentlichen Problem funktionieren.
Wie bereits gesagt: Halte ich den Ansatz für mittelprächtig, was aber am
Funktionieren des Ansatzes nichts ändert.
Auch wird die Lösung dem Prozessor nicht in den 100 MHz-Bereich
katapultieren.
Darki schrieb:> Eine If Abfrage würd ich mir gerne in der ISR Sparen wenn möglich
Wie gesagt, wenn möglich. Wenn nicht möglich dann halt nicht. Daher werd
ich mich jetzt dran machen das mit If oder dem Sprung zu machen.
@Darki
Bei den "normalen" Atmels liegt die Interrupt-Sprungtabelle im FLASH. Da
kann man nicht so einfach, an den Sprungzielen, rumfummeln.
Es gibt allerdings einen nicht ganz einfachen und auch langsamen Trick:
Du verwendest die Mechanismen, die eigentlich für den Bootstrap gedacht
sind.
Du gehst also in den Bootloader-Bereich, und schreibst eine komplette
Flash-Seite - die Interrupt-Tabelle - neu. Wer sagt denn, das:
a) Das ganze Programm neu geschrieben werden muss?
-) Ist zwar üblich, aber eine Speicherseite reicht ja.
b) Der Code nicht aus einem konstanten Bereich kommen kann?
-) Der Schreibroutine ist es egal, ob der Sermon über eine
serielle Schnittstelle kommt oder aus einer Konstanten im FLASH.
Nur die eventuelle Nutzung des Boot-Loaders wird dann noch
komplizierter.
Ohne immer noch keine Details zu kennen, man könnte auch einfach
verschiedene Interrupts enablen und disablen.
Z.B. TIMER1_COMPA, TIMER1_COMPB, TIMER1_OVF, TIMER3_COMPA, TIMER3_COMPB,
TIMER3_OVF sind schonmal 6 Möglichkeiten.
Allerdings kostet schon ein leerer Interrupt mit Prolog und Epilog 30
Zyklen. Und je nach Registernutzung könen es auch 50 und mehr werden.
Dagegen ist ein if() nur noch Pillepalle.
Darki schrieb:> Die> Frequenz ist variabel.
Also von 1mHz bis 1GHz oder wie?
Ehe man planlos drauflos programmiert, muß man erstmal den Meßbereich
festlegen.
keep cool schrieb:> Mensch Pedda, immer ruhig, ist doch 2ter Advent. ;-)))
Wenn er nichtmal weiß, welchen Frequenzbereich er messen will, dann
kommt mir das eben recht undurchdacht vor.
Mir ist es doch herzlich egal, was er da macht.
Ich hab eben nur meine Zweifel, ob Mikrooptimierungen überhaupt was
bringen.
Meine Erfahrung sagt: Nein.
Statt stur auf Mikrooptimierung zu verharren, wäre es erheblich
zielführender, erst einmal das Meßkonzept vorzustellen.
Und dann den relevanten Code. Oder zumindest den Code, wo man den
Flaschenhals vermutet.
@ Peter Dannegger (peda)
>Wenn er nichtmal weiß, welchen Frequenzbereich er messen will, dann>kommt mir das eben recht undurchdacht vor.
Das ist es auch. Alle seine "Beiträge" sind wirr und planlos.
>Ich hab eben nur meine Zweifel, ob Mikrooptimierungen überhaupt was>bringen.>Meine Erfahrung sagt: Nein.
Richtig.
>Statt stur auf Mikrooptimierung zu verharren, wäre es erheblich>zielführender, erst einmal das Meßkonzept vorzustellen.
Also vernünftig und solide arbeiten? Aber doch nicht in diesem Forum!
;-)