2016-10-18 1 views
3

스택 포인터를 제외하고 함수 호출에서 모든 레지스터를 파괴하는 함수 f()이 있습니다. 이것을 gcc으로 어떻게 전송하면 호출자는 저장하기를 원하는 모든 레지스터를 저장하고 나서 f()으로 호출 할 수 있습니까?함수를 dirty로 표시 (호출자가 모든 레지스터를 저장하도록 지정)

EDIT : 다른 코 루틴으로 전환하기 전에 상태를 저장해야하는 coroutine 처리기를 작성 중이므로 가능한 최소 상태를 저장하고 싶습니다. 스택 포인터를 제외한 모든 것을 파괴하는 "더러운"이라고 표시된 함수 yield()이 있다고 가정 해보십시오. 이 함수는 컨트롤이 우리 코 루틴으로 반환 된 후에 마술처럼 돌아 오지만 호출자가 호출자가 저장해야하는 레지스터를 가장 잘 알고 있기 때문에 호출자가 yield()을 호출하기 전에 저장해야하는 모든 레지스터를 저장 한 다음 복원하는 것이 가장 좋습니다 나중에.

+0

아마도 [clobber 목록] (https://www.ibiblio.org/gferg/ldp/GCC-Inline-Assembly-HOWTO.html#ss5.3)을 찾고 있습니까? –

+0

@RandomDavis 아니요. clobbered 레지스터는 호출 수신자가 아닌 호출 수신자가 저장합니다. 호출자가 보존하고자하는 모든 레지스터를 보존 (푸시/팝)하고 싶습니다. 'f()'는 스택 포인터 만 보존합니다. – user1095108

+0

코멘트에? gcc가 그것을 알아야하는 이유는 무엇입니까? 자동으로 해보기를 원하면 그럴 방법이 없다고 생각합니다. –

답변

3

아이디어는 principle of least astonishment을 위반하므로 피해야합니다.

호출자는 함수를 호출 할 때 레지스터 내용에 대해 걱정할 필요가 없다고 생각합니다. 또한 호출자가 처리하도록하려면 f() 내부에서 처리하지 않는 것이 좋습니다. 호출자는 인식 할 필요가 없을뿐만 아니라 구현이 하나만 필요합니다. 당신이 제안하고있는 것과 같이, 각 호출자는 컨텍스트를 저장/복원하는 것을 처리해야하며, 이는 매우 오류가 발생할 가능성이 높습니다.

기본 솔루션은 RAII을 사용하여 f()에서 처리 할 수 ​​있습니다. 예 :

class ContextGuard { 
    public: 
    // Stores the current context 
    ContextGuard() { ... } 
    // Restores the current context 
    ~ContextGuard() { ... } 
    private: 
    ... 
}; 

... 

void f() { 
    ContextGuard contextGuard; // Saves the current context 
    ... // Do stuff that mucks with the registers 
} <-- contextGuard is destroyed here and the context is restored. 

컨텍스트를 저장/복원하는 방법은 다른 문제입니다. Boost.Context은 필요한 것을 제공 할 수 있습니다.

마지막으로 스택 포인터를 넘어서 레지스터와 관련하여 몇 가지 복잡한 점이 있습니다. 여기에 플랫폼 별 함수 호출 규칙을 고려해야하며 다른 요인들도 고려해야합니다. 레지스터를 복원해야한다고 생각하는 방식으로 레지스터를 조작하는 경우이 코드를 실행하려는 모든 플랫폼의 복잡성을 실제로 이해해야합니다.

+0

호출자가 저장된 내용을 가장 잘 알고 있기 때문에 호출 수신자는 알지 못합니다. 그것은 단지 모든 것을 저장할 수 있습니다. – user1095108

+0

@ user1095108 네, 그게 핵심입니다. "중요하지 않은"레지스터 중 하나에서 데이터를 잃어 버리면 발신자가 완전히 망가지는 100 만개의 상황에 빠지지 않을 것이라는 보장이 없으므로 아무 것도 저장하지 않아도됩니다. –

+0

하지만 컴파일러는 모든 것을 알고 있습니다. 그것은 사용자가 아닌 저장합니다. 나는 어떤 경악도 보지 않는다. 어떤 레지스터가 사용되고 어떤 레지스터가 아는지를 알고 있습니다. – user1095108

관련 문제