2014-02-07 6 views
0

인라인 어셈블리를 사용하여 긴 점프를 수행하는 프로그램에서 작업하고 있습니다. 필자가 이해해야 할 것은 FP와 PC를 저장된 FP와 PC로 대체하는 것입니다. 어셈블리를 사용하면 프레임 포인터 (% ebp)를 바꿀 수 있지만 PC에서는 할 수 없습니다.저장된 주소로 프로그램 카운터 (PC) 수정

int jump(int x) 
{ 
    int oldFP = getebp(); //the FP of the calling function 
    int oldPC = getebp()+4; //the PC of the calling function 

    ljump(); //uses assembly to change FP (works) but can't figure out PC 

    return x; 
} 

ljump() 그러나 나는 보통 세그먼트 오류가 PC가 점프를 사용하고 변경할 수

ljump: # return stack frame pointer FP 
     movl savedFP, %ebp 
     ret 

내 이전 시도이다.

모든 의견을 보내 주시면 감사하겠습니다.

+0

답이 무엇인지 잘 모르겠지만 플랫폼에'setjmp'와'longjmp'가 어떻게 구현되어 있는지 살펴보고 비슷한 것을 시도해 볼 수 있습니다. –

+1

'longjmp'를 다시 구현하는 대신'longjmp' 만 사용하십시오. 로컬이 아닌 전송은보기보다 어렵습니다. 더 나은 런타임 라이브러리가 당신을 위해 그것을하게하십시오. 비 로컬 전송에 대한 다양한 ABI 요구 사항을 이해합니다. (x86에서는 비 휘발성 레지스터를 복원해야합니다.) –

+0

제안에 감사드립니다. longjmp에 대한 소스 코드를 살펴 봤지만 읽는 데 어려움을 겪고 있습니다. 프레임 포인터를 바꾸는 것만으로도 충분히 간단하고 작동하지만 PC를 바꾸는 것이 더 어려워지는 것입니다. – Kosz

답변

1

당신은 당신의 코드가 일부 미리 정의 된 주소를 계속하려는 경우 당신은 당신의 ASM 코드 (의사)에서이 같은 그것을 할 수 :

push myNewAddress 
ret 

또는 레지스터를 사용하여, 다른 방식을 선호하는 경우 :

mov eax, myNewAddress 
jmp eax 

명령어를 사용하여 PC를 직접 수정할 수는 없습니다. PC는 현재 명령어가 항상 있기 때문에 수정할 수 없습니다. 그러나 스택이 제대로 처리되지 않을 수 있으므로 메모리 누수 또는 기타 부작용이 발생할 수 있음을 알고 있어야합니다.

+0

감사합니다! 불행하게도 점프하려고 할 때 "세분화 오류"가 계속 발생하지만 올바른 위치에 있다고 생각합니다 – Kosz

+0

어느 것을 시도 했습니까? 'ret'를 사용한다면 푸시와 ret를위한 올바른 명령어 크기를 가지고 있는지 확인하십시오. – Devolus