Bei call wird die Rücksprungadresse doch automatisch auf dem Stack abgelegt?
kernel.map:0x00008330 _surprise
0x00008484 _settextcolor
void surprise(ULONG a, ULONG b)
{
while(TRUE)
{
asm ("push %0" : "=m" (b));
asm ("push %0" : "=m" (a));
asm ("call 0x00008484");
printformat("%d", getpid());
settextcolor(15,0);
}
}
Normaler Aufruf der Funktion settextcolor(15,0) in task1:
| STACK 0x001fffdc [0x00008423]
| STACK 0x001fffe0 [0x0000000f]
| STACK 0x001fffe4 [0x00000000]
Normaler Aufruf der Funktion settextcolor(15,0) in task2:
| STACK 0x401057e0 [0x000082e9]
| STACK 0x401057e4 [0x0000000f]
| STACK 0x401057e8 [0x00000000]
Normaler Aufruf der Funktion settextcolor(4,0) in task3:
| STACK 0x401097e0 [0x00008308]
| STACK 0x401097e4 [0x00000004]
| STACK 0x401097e8 [0x00000000]
Aufruf der Funktion settextcolor(...) in surprise über asm ("call 0x00008484"); in task 4:
| STACK 0x4010d7b0 [0x00008341]
| STACK 0x4010d7b4 [0x00000004]
| STACK 0x4010d7b8 [0x123890ab]
| STACK 0x4010d7bc [0x00000004]
... immer abwechselnd so weiter ...
| STACK 0x4010d7ec [0x00008330]
Hier sieht man nur türkis, die Zahl 4 sieht man nicht.
| STACK 0x4010d670 [0x00008363]
| STACK 0x4010d674 [0x0000000f]
| STACK 0x4010d678 [0x00000000]
Hier sieht man türkis Hintergrund und in rot die Zahl 4.
Das ist die Umschaltung auf weiß/schwarz nach Ausgabe der Zahl:
printformat("%d", getpid()); settextcolor(15,0); innerhalb surpirse(...)
Hier gibt es also zwei Zustände. Der hintere ist o.k., der erste nicht.
Da stört dieses 0x123890ab an der Stelle der Hintergrundfarbe.
Nun verstehe ich auch den Blink-Vorgang der Zahl 4.
Beim zweiten Durchgang durch Task 2 ist alles o.k.:
Umschalten auf Grün:
| STACK 0x401057e0 [0x000082ca]
| STACK 0x401057e4 [0x00000002]
| STACK 0x401057e8 [0x00000000]
Umschalten auf weiß:
| STACK 0x401057e0 [0x000082e9]
| STACK 0x401057e4 [0x0000000f]
| STACK 0x401057e8 [0x00000000]
Plötzlich kommt zwischen 2 und 3 etwas task 4 dazwischen!
Chaos
Task 3 läuft dann aber weiter und schaltet dann auch wieder auf 4 mit den zwei Zuständen:
falsch:
| STACK 0x4010ca08 [0x00008341]
| STACK 0x4010ca0c [0x00000004]
| STACK 0x4010ca10 [0x123890ab]
richtig:
| STACK 0x4010c9f8 [0x00008363]
| STACK 0x4010c9fc [0x0000000f]
| STACK 0x4010ca00 [0x00000000]
Na immerhin liegt ein while(1) zwischen den Parametern und meinem Push-Vorgang:
void surprise(ULONG
a, ULONG
b)
{
while(TRUE)
{ asm ("push %0" : "=m" (
b));
asm ("push %0" : "=m" (
a));
So geht das mehrere Durchläufe weiter. Es erfolgt kein Absturz.
Ich breche den Debug-Vorgang ab.
Lasse ich es normal laufen, kommt es genau bis 1-2-3-4-1-2-GPF.
Hat also auch etwas mit Geschwindigkeit zu tun, also dynamische Prozesse.
Kannst Du mir einen Tipp geben, wie die beiden Parameter sicher die while-Schleife überleben?
Was ist dieses 0x123890ab? Sieht "magic" aus. Ich habe gesucht:
#define HEAP_MAGIC 0x123890AB
Die Kernel-Stacks befinden sich ja auf dem Heap. Liegt daran, dass k_malloc Platz auf dem Heap sucht, sobald einer da ist (Erbe von James Molloy's Code). Ich habe nach diesem Wert in kheap.h/kheap.c gesucht:
Die Zahl wird dort als magische Zahl in Header/Footer von Holes verwendet.
Es wird im Heap-Code als Sanity-Check verwendet:
// Sanity checks.
ASSERT(header->magic == HEAP_MAGIC);
ASSERT(footer->magic == HEAP_MAGIC);
Da kommt also in task 4 etwas quer gehuscht.