Przeglądałem źródła różnych implementacji setjmp
i longjmp
i zauważyłem, że nie wszystkie rejestry CPU są zapisywane w strukturze jmp_buf
. Po zapoznaniu się z ABI AMD64, zauważyłem, że zapisywane są tylko rejestry zapisane w trybie "the callee".Dlaczego setjmp (3) nie zapisuje wszystkich rejestrów na AMD64?
Nie rozumiem, w jaki sposób stan funkcji można w pełni wznowić, gdy tylko niektóre rejestry zostały zapisane. Z pewnością niezapisane rejestry musiały być wielokrotnie przeplatane, dopóki nie zadzwonię później pod numer longjmp
?
Wszystko działa idealnie, więc z pewnością jest coś, czego nie rozumiem. Miałem nadzieję, że ktoś może rzucić trochę światła na to.
Dzięki!
Istnieją implementacje setjmp, które zapisują jedynie wskaźnik instrukcji/wskaźnik ramki (patrz "libunwind"). Te mają bardzo szybki setjmp, ale stosunkowo powolne czasy longjmp i są oparte na tabelach ramek, które opisują, jak odzyskać inne rejestry z zapisanych lokalizacji wywołujących i takich. –
Gdzie mogę znaleźć źródło, na które patrzyłeś? – nullpotent
@AljoshaBre Są to najłatwiejsze do przeczytania do tej pory: [setjmp] (http://git.etalabs.net/cgi-bin/gitweb.cgi?p=musl;ablbl;f=src/setjmp /x86_64/setjmp.s;h=98f58b8d6551e391f426fc53c81678a03ac89074;hb=HEAD) i [longjmp] (http://git.etalabs.net/cgi-bin/gitweb.cgi?p=musl;a=blob;f=src/ setjmp/x86_64/longjmp.s; h = e175a4b9606bba41eccc8972c22244e533718f0a; hb = HEAD). – haste