EIP zur Compilierzeit auslesen

Schnelle objektorientierte, kompilierende Programmiersprache.
Antworten
Benutzeravatar
Dirty Oerti
Beiträge: 2229
Registriert: Di Jul 08, 2008 5:05 pm
Wohnort: Thurndorf / Würzburg

EIP zur Compilierzeit auslesen

Beitrag von Dirty Oerti » Mo Mär 29, 2010 9:32 pm

Tag zusammen :)

Ich bin auf der Suche nach einer möglichst einfachen Methode, zur Compilierzeit den EIP (also den Instruction Pointer, der auf die jeweilig als nächstes auszuführende Anweisung im Speicher zeigt) an einer bestimmten Stelle innerhalb einer Funktion auszulesen.
Den Wert zur Laufzeit auszulesen ist kein Problem, dieser Wert ändert sich zur Laufzeit aber nicht (die jeweilige Anweisung wandert ja nicht durch den Speicher) und kann also vorher schon ausgelesen werden. Die Frage ist nur wie.
Ich dachte schon an eine Lösung zwecks Labels, womit ich mich aber wenig auskenne (die bösen Labels ;) )
Hier in dem Fall ist ein Label kein Problem, ich springe so oder so wild durch den Code ;)

Um das mal in Code zu setzen:

Code: Alles auswählen

void tu_etwas()
{
int a = 0;
int b = 12345;
LABEL:
a = a + 1;
a = a / b;
}

//...

asm volatile("mov %0, %%ecx" : : "r"(&LABEL);
asm volatile("jmp *%ecx"); // Danach sollte ich oben bei a = a +1; sein.
Ideen?
Bei Fragen einfach an daniel[ät]proggen[Punkt]org
Ich helfe gerne! :)
----------
Wenn du ein Licht am Ende des Tunnels siehst, freu dich nicht zu früh! Es könnte ein Zug sein, der auf dich zukommt!
----
It said: "Install Win95 or better ..." So I installed Linux.

Benutzeravatar
Dirty Oerti
Beiträge: 2229
Registriert: Di Jul 08, 2008 5:05 pm
Wohnort: Thurndorf / Würzburg

Re: EIP zur Compilierzeit auslesen

Beitrag von Dirty Oerti » Mo Mär 29, 2010 10:05 pm

Ok, für den GCC gibt es da etwas, ich würde es aber doch ganz gerne unabhängig vom verwendeten Compiler umsetzen.

http://en.wikipedia.org/wiki/C_syntax#S ... of_a_label
http://forum.chip.de/c-c/adresse-label-344602.html
Bei Fragen einfach an daniel[ät]proggen[Punkt]org
Ich helfe gerne! :)
----------
Wenn du ein Licht am Ende des Tunnels siehst, freu dich nicht zu früh! Es könnte ein Zug sein, der auf dich zukommt!
----
It said: "Install Win95 or better ..." So I installed Linux.

Benutzeravatar
Kerli
Beiträge: 1456
Registriert: So Jul 06, 2008 10:17 am
Wohnort: Österreich
Kontaktdaten:

Re: EIP zur Compilierzeit auslesen

Beitrag von Kerli » Mo Mär 29, 2010 10:14 pm

Ich bin mir da jetzt nicht ganz sicher, aber ich bilde mir ein wo gelesen zu haben, dass es nur Compilerabhängig möglich ist...
"Make it idiot-proof and someone will invent an even better idiot." (programmers wisdom)

OpenGL Tutorials und vieles mehr rund ums Programmieren: http://www.tomprogs.at

Benutzeravatar
Dirty Oerti
Beiträge: 2229
Registriert: Di Jul 08, 2008 5:05 pm
Wohnort: Thurndorf / Würzburg

Re: EIP zur Compilierzeit auslesen

Beitrag von Dirty Oerti » Mo Mär 29, 2010 10:32 pm

Hm, das ist aber nervig.
Es ist ja auch möglich, die Adresse einer Funktion zu erhalten...
Bei Fragen einfach an daniel[ät]proggen[Punkt]org
Ich helfe gerne! :)
----------
Wenn du ein Licht am Ende des Tunnels siehst, freu dich nicht zu früh! Es könnte ein Zug sein, der auf dich zukommt!
----
It said: "Install Win95 or better ..." So I installed Linux.

Benutzeravatar
Xin
nur zu Besuch hier
Beiträge: 8859
Registriert: Fr Jul 04, 2008 11:10 pm
Wohnort: /home/xin
Kontaktdaten:

Re: EIP zur Compilierzeit auslesen

Beitrag von Xin » Mo Mär 29, 2010 10:52 pm

Dirty Oerti hat geschrieben:Tag zusammen :)

Ich bin auf der Suche nach einer möglichst einfachen Methode, zur Compilierzeit den EIP (also den Instruction Pointer, der auf die jeweilig als nächstes auszuführende Anweisung im Speicher zeigt) an einer bestimmten Stelle innerhalb einer Funktion auszulesen.
In einem älteren System würde ich sagen, dass das nicht möglich ist, weil Du nicht weißt, wohin das Programm geladen wird.
Bei einem modernen System hast Du Deinen eigenen virtuellen Speicher. Das würde die Sache wieder realisierbar machen - aber dafür müsste der Compiler wissen, wie das OS Dich lädt. Du kannst daher eigentlich immer nur Sprünge relativ zur aktuellen Adresse machen.
Merke: Wer Ordnung hellt ist nicht zwangsläufig eine Leuchte.

Ich beantworte keine generellen Programmierfragen per PN oder Mail. Dafür ist das Forum da.

Benutzeravatar
Dirty Oerti
Beiträge: 2229
Registriert: Di Jul 08, 2008 5:05 pm
Wohnort: Thurndorf / Würzburg

Re: EIP zur Compilierzeit auslesen

Beitrag von Dirty Oerti » Di Mär 30, 2010 10:18 am

Der Compiler weiß, wie das Programm geladen wird. Besser gesagt wohin in den virtuellen Speicher.
Zumindest solange es sich nicht um eine relocable Elfdatei handelt.

Und ich hab jetzt auch eine Lösung gefunden, die zwar nicht unbedingt umwerfend elegant ist, aber sie funktioniert:

Code: Alles auswählen

void meine_funktion()
{
// code
asm volatile("meine_unterbrechung:");
a = a + 1;
}


unsigned int GetUnterbrechung()
{
unsigned int eip;
asm volatile("mov $meine_unterbrechung, %0" : "=r"(eip));
return eip;
}


// in irgendeiner anderen Funktion, wo dieser Wert gebraucht wird
unsigned int eip_aus_funktion = GetUnterbrechung();

Der Rückgabewert der Funktion GetUnterbrechung bleibt immer gleich, zumindest solange das Programm immer an die selbe Stelle im Speicher gelinkt wird.
Die Funktion an sich ist notwendig, damit man den eip auch aus anderen Dateien auslesen kann.
Mir ist nämlich leider noch keine Möglichkeit aufgefallen, das LABEL meine_unterbrechung als global zu deklarieren.
Bei Fragen einfach an daniel[ät]proggen[Punkt]org
Ich helfe gerne! :)
----------
Wenn du ein Licht am Ende des Tunnels siehst, freu dich nicht zu früh! Es könnte ein Zug sein, der auf dich zukommt!
----
It said: "Install Win95 or better ..." So I installed Linux.

Benutzeravatar
cloidnerux
Moderator
Beiträge: 3123
Registriert: Fr Sep 26, 2008 4:37 pm
Wohnort: Ram (Gibts wirklich)

Re: EIP zur Compilierzeit auslesen

Beitrag von cloidnerux » Di Mär 30, 2010 11:33 am

Als anmerkung zu deinem Code:
1 Zeile C-Code sind nicht 1 Zeile Maschinencode.
Der Fuktionaufruf und das return sind mitunter mehrere MAschinenanweisungen, sodass dann a nicht auf die Stelle die du Herausfinden willst zeigt, sondern noch innerhalb deiner GetUnterbechung ist.
Redundanz macht wiederholen unnötig.
quod erat expectandum

Benutzeravatar
Dirty Oerti
Beiträge: 2229
Registriert: Di Jul 08, 2008 5:05 pm
Wohnort: Thurndorf / Würzburg

Re: EIP zur Compilierzeit auslesen

Beitrag von Dirty Oerti » Di Mär 30, 2010 12:56 pm

Nö nö, da verstehst du jetzt was falsch :)
Der zurückgegebene Wert zeigt NIE auf eine Anweisung innerhalb der Get* Funktion.
Die Get Funktion tut nur das, was der Name auch schon sagt: Sie übergibt den Wert.
Der Wert wird ja zur Compilier/Linkzeit schon berechnet und da direkt eingesetzt, die Funktion sieht letztendlich also so aus wie

Code: Alles auswählen

unsigned int GetUnterbrechung()
{
unsigned int eip;
eip = 5;
return eip;
}
Nur eben mit angepasstem Wert.


Das 1 Zeile C Code nicht gleich 1 Zeile Assemblercode ist, ist klar.
Das definierte Label zeigt aber auf die nächste Anweisung. Und das ist die erste Anweisung von egal wie vielen Anweisungen, die aus der 1 Zeile C-Code "entstanden" sind.
Die einzigen Probleme, die hier entstehen (können und auch werden, wenn man das ernsthaft zu Sprüngen verwendet) sind Probleme mit dem Stack, da dieser dann evtl nicht gut aufgelöst wird.
Bei Fragen einfach an daniel[ät]proggen[Punkt]org
Ich helfe gerne! :)
----------
Wenn du ein Licht am Ende des Tunnels siehst, freu dich nicht zu früh! Es könnte ein Zug sein, der auf dich zukommt!
----
It said: "Install Win95 or better ..." So I installed Linux.

Antworten