Hallo wie kann man ̲ohne globale Variablen(!) eine Variable erstellen, die innerhalb von ISR funktioniert und zwischen 2 ISR Aufrufen sein Wert nicht verliert? z.B ISR(Timer) // ISR jede 50ms aufgerufen { uint8_t puffer[10]; // soll Werte zw. ISR Aufrufen behalten! do { puffer[i]=ADC; //10 Messwerte sollen im Array gespeichert werden /* Problem: ISR ist Timer-gesteuert und kann z.B. bei einem Wert i=5 unterbrechen und ISR wird dann von neuem aufgerufen. i muss aber vom Wert 5 weitermachen und nicht zu 0 zurückkehren. */ i++; }while(i<10); } danke!
Schlüsselwort static aber warum keine globale- bzw. Modulvariable für so was nehmen?
Cyblord -. schrieb: > Schlüsselwort static > > aber warum keine globale- bzw. Modulvariable für so was nehmen? Hallo Cyblord, danke für die schnelle Antwort. Eine globale Variable ist in Aufgabestellung verboten, anscheinend um andere Möglichkeiten zu lernen. Danke noch mal! )
wäre das dann richtig?
1 | ISR(Timer) // ISR jede 50ms aufgerufen |
2 | {
|
3 | static uint8_t puffer[10]; // soll Werte zw. ISR Aufrufen behalten! |
4 | static int i = 0; /* würde i an dieser Stelle nicht bei jedem neuen ISR Aufruf wieder 0 werden?*/ |
5 | |
6 | do
|
7 | {
|
8 | puffer[i]=ADC; //10 Messwerte sollen im Array gespeichert werden |
9 | |
10 | /* Problem: ISR ist Timer-gesteuert und kann z.B. bei einem Wert
|
11 | i=5 unterbrechen und ISR wird dann von neuem aufgerufen. i muss aber vom
|
12 | Wert 5 weitermachen und nicht zu 0 zurückkehren. */
|
13 | |
14 | i++; |
15 | }while(i<10); |
16 | }
|
static wurde ja schon genannt. Bei meinem Compiler (CodeVision) führen static-Variablen gegenüber globalen allerdings zu mehr Code und zu mehr Laufzeit. Wenns kritisch wird (manchmal zählt gerade bei ISRs jeder Takt) nehme ich dann doch globale Variablen dafür her.
@ Sascha M. (stmech)
>wäre das dann richtig?
Wenn man die schlechte Formatierung mal ignoriert, ist das so OK.
@H.Joachim Seifert (crazyhorse) >Bei meinem Compiler (CodeVision) führen static-Variablen gegenüber >globalen allerdings zu mehr Code und zu mehr Laufzeit. Dann würde ich das Ding wegwerfen, dann dafür gibt es keinerlei Grund. Physikalisch sind statische Variablen in Funktionen identisch zu globalen, nur dass sie nicht im globalen Namensraum auftauchen. Sie werden genauso wie globale beim Programmstart initialisiert und landen auch im gleichen Variablensegment.
Sascha M. schrieb: > static int i = 0; /* würde i an dieser Stelle nicht bei jedem neuen > ISR Aufruf wieder 0 werden?*/ nein, die Initialisierung wird nur beim ersten Aufruf durchgeführt. Je nach Compiler merkt sich der "irgendwo" in einem Flag, ob die Initialisierung durchgeführt wurde, dieses Flag wird dann auch bei jedem Aufruf der ISR überprüft, was ein paar Takte mehr Laufzeit kostet.
Sascha M. schrieb: > wäre das dann richtig? also da, im ISR ganz oben static int i=0; deklariert ist, würde i an dieser Stelle doch ständig 0 werden und den Wert in der do while Schleife nicht behalten.
Der Grund ist, dass globale Variablen falls noch möglich in Registern gehalten werden, static-Variablen jedoch immer im RAM. unsigned char ex0_count; // External Interrupt 0 service routine interrupt [EXT_INT0] void ext_int0_isr(void) { ex0_count++; } // External Interrupt 1 service routine interrupt [EXT_INT1] void ext_int1_isr(void) { static unsigned char ex1_count; ex1_count++; } .CSEG _ext_int0_isr: ; .FSTART _ext_int0_isr ST -Y,R30 IN R30,SREG ; 0000 001F ex0_count++; INC R4 ; 0000 0020 ; 0000 0021 } OUT SREG,R30 LD R30,Y+ RETI ; .FEND ; ;// External Interrupt 1 service routine ;interrupt [EXT_INT1] void ext_int1_isr(void) ; 0000 0025 { _ext_int1_isr: ; .FSTART _ext_int1_isr ST -Y,R30 IN R30,SREG ST -Y,R30 ; 0000 0026 static unsigned char ex1_count; ; 0000 0027 ex1_count++; LDS R30,_ex1_count_S0000001000 SUBI R30,-LOW(1) STS _ex1_count_S0000001000,R30 ; 0000 0028 } LD R30,Y+ OUT SREG,R30 LD R30,Y+ RETI ; .FEND
ach sooo das macht mir jetzt nun alles klar! super, vielen Dank Euch allen für die freundliche Unterstützung!
:
Bearbeitet durch User
> static int i = 0;
Wobei mein Lehrer dafür damals einen Punkt abgezogen hätte, denn alle
globalen uns statischen Variablen werden ohnehin schon beim
Programmstart mit 0 initialisiert.
Bei den damals aktuellen Compilern hätte man durch obige Code-Zeile die
Variable zweimal mit 0 initialisiert, und damit unnötigen Code erzeugt.
Der aktuelle gcc optimiert das jedoch schön weg.
Ich persönlich bevorzuge die Angabe des Startwertes, wenn er für den
Programmablsuf wichtig ist (auch wenn es 0 ist). So wird der Code besser
lesbar.
Aber dein Lehrer sieht das möglicherweise anders, vor allem wenn er in
den 80er Jahren stecken geblieben ist :-)
@ rmu (Gast) >> static int i = 0; /* würde i an dieser Stelle nicht bei jedem neuen >> ISR Aufruf wieder 0 werden?*/ >nein, die Initialisierung wird nur beim ersten Aufruf durchgeführt. Richtig. Genauer, vor dem Programmstart, so wie globale Variablen. >Je >nach Compiler merkt sich der "irgendwo" in einem Flag, ob die >Initialisierung durchgeführt wurde, dieses Flag wird dann auch bei jedem >Aufruf der ISR überprüft, was ein paar Takte mehr Laufzeit kostet. Nein, das ist in C nicht so, nur in C++.
Sascha M. schrieb: > rmu schrieb: > >> nein, die Initialisierung wird nur beim ersten Aufruf durchgeführt. Je >> nach Compiler merkt sich der "irgendwo" in einem Flag, ob die >> Initialisierung durchgeführt wurde, dieses Flag wird dann auch bei jedem >> Aufruf der ISR überprüft, was ein paar Takte mehr Laufzeit kostet. > > ach sooo das macht mir jetzt nun alles klar! In C++ wird die Variable beim ersten Aufruf der Funktion initialisiert, das muss dann in einem Flag vermerkt werden, und ist je nach C++-Version u.U. nicht thread-safe. In C kann die Initialisierung zur Compile-Zeit erfolgen, ergo sollte es dann auch keinen Laufzeit-Overhead geben.
@ H.Joachim Seifert (crazyhorse) >Der Grund ist, dass globale Variablen falls noch möglich in Registern >gehalten werden, static-Variablen jedoch immer im RAM. ??? Damit blockiert sich der Compiler DAUERHAFT CPU-Register? Ziemlicher Murks. Solche Mikro-Testprogramme sind auch wenig praxisrelevant, denn wenn das Programm einen Tick größer wird ist es Essig mit freien Registern für globale Variablen.
> Je nach Compiler merkt sich der "irgendwo" in einem Flag, ob die > Initialisierung durchgeführt wurde Ich hatte das so gelernt: Im Flash Speicher befindet sich ein Array mit den Startwerten aller Variablen, die beim Programmstart initialisiert werden (diese static Variable gehört dazu). Nach dem Reset aber bevor die main() Funktion gestartet wird, kopiert ein kleines Stück Code (den der Copmpiler einfügt) dieses Array ins RAM. Alle übrigen globalen und statischen Variablen werden mit 0 initialisiert. Ein Flag "irgendwo" ist daher gar nicht notwendig.
> Damit blockiert sich der Compiler DAUERHAFT CPU-Register? > Ziemlicher Murks. Keineswegs, das ergibt kleine effiziente Programme. Bedenke, dass es µC mit sehr vielen Regitern gibt, wie die AVR Serie und die MCS51 Serie. Meine Funk-Uhr, die dem Düsseldorfer Rheinturm nachempfunden wurde, hatte gar keine Variablen im RAM verwendet, sondern ausschließlich Register. Es war mehr als genug vorhanden. Das war zwar Assembler, aber warum sollte der C Compiler nicht auch möglichst viele Register verwenden?
> In C kann die Initialisierung zur Compile-Zeit erfolgen
Wie das? Der Compiler hat keinen Zugriff auf das RAM des
Mikrocontrollers und außerdem ist RAM flüchtig. Wenn mein Compiler auf
meinem PC die Variable wie auch immer initialisieren würden, dann dürfte
ich mein Target niemals stromlos schalten. Denn dann verlieren sowohl
RAM als auch Register ihren Inhalt.
Kann man ja einstellen, ob man das will oder nicht (automatic global register allocation). Gilt dann für R4-R15. Globale Variablen (nur char und int, long nicht) werden dann in den Registern gehalten in der Reihenfolge der Deklaration. Ich finds praktisch und seh keinen Nachteil darin, sondern den schon erwähnten Vorteil, zeitkritische Sachen so schnell wie eben möglich erledigen zu können.
@: Stefan Us (stefanus) >> Damit blockiert sich der Compiler DAUERHAFT CPU-Register? >> Ziemlicher Murks. >Keineswegs, das ergibt kleine effiziente Programme. Bedenke, dass es µC >mit sehr vielen Regitern gibt, wie die AVR Serie und die MCS51 Serie. Eben, nur bei SEHR kleinen Programmen geht so was. Sobald die ETWAS größer werden geht das nicht mehr! >Meine Funk-Uhr, die dem Düsseldorfer Rheinturm nachempfunden wurde, >hatte gar keine Variablen im RAM verwendet, sondern ausschließlich >Register. Es war mehr als genug vorhanden. Jaja, und gleich kommt Moby und erklärt uns, daß Variablen im RAM Verschwendung und überflüssig sind ;-) >Das war zwar Assembler, aber warum sollte der C Compiler nicht auch >möglichst viele Register verwenden? Das tut er auch, aber anders als ein eng fokussierter ASM-Fan. Die Strategie zur Registernutzung ist gar nicht soo einfach. Globale Variablen dauerhaft in CPU-Registern zu halten ist nur in sehr wenigen Ausnahmefällen sinnvoll und möglich.
@ Stefan Us (stefanus) >> In C kann die Initialisierung zur Compile-Zeit erfolgen >Wie das? Weil das der C Standard so definiert hat! >Der Compiler hat keinen Zugriff auf das RAM des >Mikrocontrollers Bitte? > und außerdem ist RAM flüchtig. Wenn mein Compiler auf >meinem PC die Variable wie auch immer initialisieren würden, dann dürfte >ich mein Target niemals stromlos schalten. Denn dann verlieren sowohl >RAM als auch Register ihren Inhalt. Du sprichst wirr.
@ H.Joachim Seifert (crazyhorse) >Kann man ja einstellen, ob man das will oder nicht (automatic global >register allocation). Gilt dann für R4-R15. Globale Variablen (nur char >und int, long nicht) werden dann in den Registern gehalten in der >Reihenfolge der Deklaration. OK, das klingt brauchbar. >Ich finds praktisch und seh keinen Nachteil >darin, sondern den schon erwähnten Vorteil, zeitkritische Sachen so >schnell wie eben möglich erledigen zu können. Naja, die allerwenigsten ISRs sind auf 1 Takt mehr oder weniger wirklich angewiesen. Extremfälle kann man immer konstruieren.
Falk B. schrieb: > @ Stefan Us (stefanus) > >>> In C kann die Initialisierung zur Compile-Zeit erfolgen > >>Wie das? > > Weil das der C Standard so definiert hat! Jaja, also wenn ich mein Programm kompiliere ist der µC schon initialisiert. Und das obwohl er noch in der ESD-Tüte ist... Geht das über Verschränkung? Woher weiß der Compiler denn welchen µC ich denn initialisieren möchte? Also nochmal für dich: Den Ram kann der Compiler nur über irgendwelchen Code initialisieren. Genauso wie die Register. Und initialisiert wird genau dann, wenn dieser Code ausgeführt wird, also zur Laufzeit.
@Falk: klar, meist ist es nicht nötig. Aber es gibt dennoch immer wieder mal Sachen, wo man auf der Suche nach Optimierungen ist. Und in dem obigen kleinen Beispiel ist es nicht 1 Takte Unterschied, sondern 8. Und 6 word Programmspeicher. Spielt auch in den allermeisten Fällen keine Rolle, aber ich habe auch schon Fälle gehabt, wo man durch nachträgliche Softwareerweiterungen bedenklich nahe an die Programmspeichergrösse kam... Was macht eigentlich der gcc mit R2-R15? Werden die tatsächlich für irgendwas benutzt oder liegen die eh brach?
Stefan U. schrieb: >> In C kann die Initialisierung zur Compile-Zeit erfolgen > > Wie das? Der Compiler hat keinen Zugriff auf das RAM des > Mikrocontrollers Das war halt etwas mißverständlich ausgedrückt. Natürlich erfolgt die Initialisierung durch ein ablaufendes Programm, aber es erfolgt vor dem eigentlichen C-Programm. Aus Sicht des C-Programmierers damit nicht zur Laufzeit seines Programms. Oliver
@ avr (Gast) >> Weil das der C Standard so definiert hat! >Jaja, also wenn ich mein Programm kompiliere ist der µC schon >initialisiert. Und das obwohl er noch in der ESD-Tüte ist... Jaja. >Geht das über Verschränkung? Besser als Beschränkung, die du hier hervorragend demonstrierst! >Also nochmal für dich: Den Ram kann der Compiler nur über irgendwelchen >Code initialisieren. Genauso wie die Register. Das hat doch keiner bestritten. > Und initialisiert wird >genau dann, wenn dieser Code ausgeführt wird, also zur Laufzeit. Jain. Einfach mal lesen und 5 Sekunden nachdenken, bevor hier wild rumposaunt wird. In C (NICHT C++ !) werden globale sowie statische Variablen VOR der Ausführung von main() einmalig initialisiert. In einer Funktion mit statischen Variablen wird NICHT noch einmal eine Initialisierung oder gar Prüfung auf diese erstmalige Initialisierung durchgeführt! Damit ist die praktische Anwendung von globalen und statischen Variablen nahezu gleich. Der Unterschied liegt nur darin, daß globale Variablen global sichtbar sind, lokale statische Variablen nur lokal.
Falk B. schrieb: >>Je >>nach Compiler merkt sich der "irgendwo" in einem Flag, ob die >>Initialisierung durchgeführt wurde, dieses Flag wird dann auch bei jedem >>Aufruf der ISR überprüft, was ein paar Takte mehr Laufzeit kostet. > > Nein, das ist in C nicht so, nur in C++. Hm. Seit wann das den? In dem hier besprochen Fall
1 | static int foo = 42; |
innerhalb einer Funktion wird die Initialiserung auch in C++ vor dem Start von main ausgeführt. Da gibt's keine Flags oder ähnliches. Oliver
@ H.Joachim Seifert (crazyhorse) >nachträgliche Softwareerweiterungen bedenklich nahe an die >Programmspeichergrösse kam... Hatte ich auch mal, da war ein AT8515 mit nur noch ACHT Bytes freiem Flash! In der nächsten Revision wurde es dann ein ATmega644 ;-) >Was macht eigentlich der gcc mit R2-R15? Benutzen. > Werden die tatsächlich für >irgendwas benutzt Ja sicher! > oder liegen die eh brach? Keinesfalls!
>>Der Compiler hat keinen Zugriff auf das RAM des >>Mikrocontrollers >Bitte? Der Compiler kann nur Code (und feste Datenstrukturen(also keine Variablen)) erzeugen, den ich anschließend mit dem Programmiertool in den Flash Speicher des Mikrocontrollers übertrage. Der Compiler hat keinen Zugriff auf die Ziel-Hardware, daher kann er sie nicht initialisieren. Er kann lediglich Code erzeugen, der diese Initialisierung ZUR LAUFZEIT durchführt. Das ist bei PC-Software nicht anders. Wenn ich auf meinem PC ein Programm compiliere, dass du später ausführst, dann kann der Compiler unmöglich deine RAM initialisieren. Er hat ja gar keine Verbindung zu deiner Maschine.
rmu schrieb: > Sascha M. schrieb: >> static int i = 0; /* würde i an dieser Stelle nicht bei jedem neuen >> ISR Aufruf wieder 0 werden?*/ > > nein, die Initialisierung wird nur beim ersten Aufruf durchgeführt. Falsch. Statische Variablen werden praktisch immer zusammen mit initialisierten globalen Variablen intialisiert. Und zwar noch bevor(!) die main() Funktion aufgerufen wird. > Je nach Compiler merkt sich der "irgendwo" in einem Flag, ob die > Initialisierung durchgeführt wurde, dieses Flag wird dann auch bei jedem > Aufruf der ISR überprüft, was ein paar Takte mehr Laufzeit kostet. Zeigen. Wenn es einen solchen Compiler gibt (was ich erst glaube wenn ich es sehe) denn gehört der weggeworfen. Weit.
Falk B. schrieb: > In C (NICHT C++ !) werden globale sowie statische Variablen VOR der > Ausführung von main() einmalig initialisiert. Keine Ahnung wie genau Laufzeit definiert wird. Für mich gehört zur Laufzeit auch sämtlicher Startup-Code. Aber der gehört definitiv nicht zur Compile-Zeit! Compile-Zeit ist während dem kompilieren. Soviel dazu: Falk B. schrieb: > Jain. Einfach mal lesen und 5 Sekunden nachdenken, bevor hier wild > rumposaunt wird. H.Joachim S. schrieb: > Was macht eigentlich der gcc mit R2-R15? Werden die tatsächlich für > irgendwas benutzt oder liegen die eh brach? Wenn ich mich richtig erinnere müssen gerade diese Register bei Funktionsaufrufen nicht gesichert werden. Der Compiler packt da gerne Variablen rein, anstatt sie dauernd auf den Stack zu legen. Die Anzahl der Stackoperationen wird sicherlich stark steigen, wenn man ihm diese Register nimmt.
Oliver S. schrieb: > Hm. Seit wann das den? > > In dem hier besprochen Fall static int foo = 42; > innerhalb einer Funktion wird die Initialiserung auch in C++ vor dem > Start von main ausgeführt. Da gibt's keine Flags oder ähnliches. doch gibt es
1 | #include <stdio.h> |
2 | class cx |
3 | {
|
4 | public:
|
5 | cx() { |
6 | printf("init\n"); |
7 | }
|
8 | };
|
9 | |
10 | void foo() { |
11 | static cx x; |
12 | }
|
13 | |
14 | int main() { |
15 | printf("start\n"); |
16 | foo(); |
17 | printf("next\n"); |
18 | foo(); |
19 | return 0; |
20 | };
|
Peter II schrieb: > Oliver S. schrieb: >> Hm. Seit wann das den? >> >> In dem hier besprochen Fall static int foo = 42; >> innerhalb einer Funktion wird die Initialiserung auch in C++ vor dem >> Start von main ausgeführt. Da gibt's keine Flags oder ähnliches. > > doch gibt es (schnipp) Äpfel und Birnen. Nochmal für dich: >> In dem hier besprochen Fall static int foo = 42;
> ISR(Timer) // ISR jede 50ms aufgerufen >{ > static uint8_t puffer[10]; > static int i = 0; > do { > puffer[i]=ADC; > i++; } > while(i<10); >} ist Murks, denn ein ADC Aufruf ist nicht instantan.
Sascha M. schrieb: > /* Problem: ISR ist Timer-gesteuert und kann z.B. bei einem Wert > i=5 unterbrechen und ISR wird dann von neuem aufgerufen. i muss aber vom > Wert 5 weitermachen und nicht zu 0 zurückkehren. */ Nach jeder Unterbrechrung macht die CPU genau da weiter, wo sie unterbrochen wurde. Das gilt auch für nested Interrupts. Ein static ist daher fehl am Platze. Hier würde die Schleife mit i = 10 verlassen, d.h. die Schleife wird nie wieder ausgeführt.
Oder D. schrieb: > ist Murks, denn ein ADC Aufruf ist nicht instantan. Verstehe hier den Begirff "instantan" nicht. Kannst Du erklären was Du meinst? @Sascha M. Erkläre mal was nach dem Code-Auschnitt im weiteren Verlauf gemacht werden soll.
> Verstehe hier den Begirff "instantan" nicht. Kannst Du erklären was Du meinst? Der Befehl > puffer[i]=ADC; wird nicht in einem clock abgearbeitet, nehm ich an. Die Memory mapped ADC sind sehr unueblich. Dauert viel zu lange. Dh man darf nicht in einem Timerinterrupt lesen. Sondern im main, oder im ADC Interrupt.
:
Bearbeitet durch User
Oder D. schrieb: >> Verstehe hier den Begirff "instantan" nicht. Kannst Du erklären was Du > meinst? > > > Der Befehl >> puffer[i]=ADC; > > wird nicht in einem clock abgearbeitet, nehm ich an. Was macht es ob es nun 1 Clock oder 10 Clocks sind? Es werden lediglich 2 Register gelesen und in eine 16 Bit Variable gesteckt. Natürlich läuft das nicht synchron zum ADC Trigger. Der ADC wird freilaufend sein nehme ich an. Wenn aber die Aufrufzeit zwischen den ISR hinreichend lang ist, spielt das keine Rolle.
Cyblord -. schrieb: > Was macht es ob es nun 1 Clock oder 10 Clocks sind? Es werden lediglich > 2 Register gelesen und in eine 16 Bit Variable gesteckt. > > Natürlich läuft das nicht synchron zum ADC Trigger. Der ADC wird > freilaufend sein nehme ich an. > Wenn aber die Aufrufzeit zwischen den ISR hinreichend lang ist, spielt > das keine Rolle. Der nächste der nicht lesen kann. Hier war mal so ein Zitat: > Einfach mal lesen und 5 Sekunden nachdenken, bevor hier wild > rumposaunt wird. Der ADC wird in der Schleife 10 mal eingelesen. Ich nehme an, dass der ADC nicht so schnell ist, bzw. der Controller so langsam getaktet wird, dass man bei jedem Schleifendurchlauf einen neuen ADC-Wert bekommt. Es macht keinen Sinn ein Register 10 mal auszulesen, wenn es sich in der Zeit nicht ändert.
Axel S. schrieb: > rmu schrieb: >> Sascha M. schrieb: >>> static int i = 0; /* würde i an dieser Stelle nicht bei jedem neuen >>> ISR Aufruf wieder 0 werden?*/ >> >> nein, die Initialisierung wird nur beim ersten Aufruf durchgeführt. > > Falsch. Statische Variablen werden praktisch immer zusammen mit > initialisierten globalen Variablen intialisiert. Und zwar noch > bevor(!) die main() Funktion aufgerufen wird. wie weiter unten geschrieben war ich im c++ modus. sorry. >> Je nach Compiler merkt sich der "irgendwo" in einem Flag, ob die >> Initialisierung durchgeführt wurde, dieses Flag wird dann auch bei jedem >> Aufruf der ISR überprüft, was ein paar Takte mehr Laufzeit kostet. > > Zeigen. > > Wenn es einen solchen Compiler gibt (was ich erst glaube wenn ich > es sehe) denn gehört der weggeworfen. Weit. vermutlich. aber wenn man in c++ sowas wie "static int i = f();" verwendet oder ein objekt mit nicht-trivialem constructor anlegt dann gibts ein flag was merkt ob initialisiert wurde oder nicht.
Anno Studio 4.?? gab es eine genaue Beschreibung, welche Register der GNU-Compiler verwendet. Es würde mich wundern, wenn es zu den aktuellen Versionen so etwas nicht mehr gibt. Andernfalls könnte man ja Assembler (z.B. in der ISR), im gemischten Modus, auch nicht nutzen. Wenn ich mich richtig erinnere, waren das die Register 0,1 (rund um die Division) und 2 (für Null). Dann war Ruhe bis incl. R15. Ab R16 galt dann (a)uf (e)igene (G)efahr (Zeiger, Variablen, usw.). Ob die Register R3 bis R15 würglich nicht genutzt wurden, oder ob push und pop dafür herhalten mussten, weiß ich aber nicht mehr.
@ Amateur (Gast) >Anno Studio 4.?? gab es eine genaue Beschreibung, welche Register der >GNU-Compiler verwendet. Wirklich? >Andernfalls könnte man ja Assembler (z.B. in der ISR), im gemischten >Modus, auch nicht nutzen. Doch. Denn bei Inlineassembler schreibt man meistens keine direkten Registrnamen sondern symbolische Platzhalter und der Compiler sucht sich dann ein freies Register aus. >Wenn ich mich richtig erinnere, waren das die Register 0,1 (rund um die >Division) und 2 (für Null). Dann war Ruhe bis incl. R15. Nein, auch R3-R15 werden benutzt. >Ab R16 galt dann (a)uf (e)igene (G)efahr (Zeiger, Variablen, usw.). Nein, denn man sollte sich so oder so an die Vorgaben des Compiler zum Thema Inline-Assembler halten. Es sei denn, man schreibt die komplette ISR in ASM.
HI >Wenn ich mich richtig erinnere, waren das die Register 0,1 (rund um die >Division) und 2 (für Null). Du erinnerst dich falsch: https://gcc.gnu.org/wiki/avr-gcc MfG Spess
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.