x86_64 va_list 구조의 형식은 무엇입니까?
누구든지 다음의 표현에 대한 참고 자료를 가지고 있습니다.va_list
x86_64 ABI(Linux에서 사용되는 ABI)에서?스택이나 인수가 손상된 것처럼 보이는 코드를 디버그하려고 하는데 제가 봐야 할 내용을 이해하는 데 정말 도움이 될 것 같습니다.
x86-64 System V Abi document가 도움이 될 수 있습니다.비록 가볍지만 참고용입니다.
Variable Argument List 참조는 54페이지에서 시작하여 56-57페이지 문서로 이어집니다.va_list
:
그
va_list
유형그
va_list
type은 하나의 구조의 단일 요소를 포함하는 배열로 구현하기 위해 필요한 정보를 포함합니다.va_arg
macro. 의 C 정의.va_list
유형은 figure 3.34에 제시되어 있습니다.그림 3.34:
va_list
유형 선언typedef struct { unsigned int gp_offset; unsigned int fp_offset; void *overflow_arg_area; void *reg_save_area; } va_list[1];
그
va_start
매크로그
va_start
macro는 다음과 같이 구조를 초기화합니다.
reg_save_area
요소가 레지스터 저장 영역의 시작을 가리킵니다.
overflow_arg_area
이 포인터는 스택에 전달된 인수를 가져오는 데 사용됩니다.스택에 전달된 첫 번째 인수의 주소(있는 경우)로 초기화된 다음 스택의 다음 인수의 시작을 가리키도록 항상 업데이트됩니다.
gp_offset
요소는 오프셋(바이트 단위)을 보유합니다.reg_save_area
다음으로 사용 가능한 범용 인수 레지스터가 저장되는 곳으로 이동합니다.인수 레지스터가 모두 소진된 경우 값 48(6 * 8)로 설정됩니다.
fp_offset
요소는 오프셋(바이트 단위)을 보유합니다.reg_save_area
다음 사용 가능한 부동 소수점 인수 레지스터가 저장되는 위치로 이동합니다.인수 레지스터가 모두 소진된 경우 값 304(6 * 8 + 16 * 16)로 설정됩니다.
문제는 gcc의 제작이었습니다.va_list
배열형제 기능은 다음과 같습니다.
void foo(va_list ap);
그리고 나는 그에게 포인터를 주고 싶었습니다.ap
다른 기능을 위해, 그래서 나는 이렇게 했습니다.
void foo(va_list ap)
{
bar(&ap);
}
불행히도 배열 유형은 함수 인수 목록에서 포인터 유형으로 붕괴되므로 원래 구조에 포인터를 전달하는 대신 포인터를 포인터로 전달했습니다.
문제를 해결하기 위해 코드를 다음과 같이 변경했습니다.
void foo(va_list ap)
{
va_list ap2;
va_copy(ap2, ap);
bar(&ap2);
va_end(ap2);
}
이것이 내가 생각해낼 수 있는 유일한 휴대용 솔루션이며, 두 가지 가능성을 모두 설명합니다.va_list
배열 유형이고 아닐 가능성도 있습니다.
i386 아키텍처에서 va_list는 포인터 유형입니다.그러나 AMD64 아키텍처에서는 어레이 유형입니다.뭐가 다른 거지?실제로 포인터 유형에 & 연산을 적용하면 이 포인터 변수의 주소를 얻을 수 있습니다.그러나 배열 유형에 적용 및 연산을 아무리 많이 해도 값은 동일하며 이 배열의 주소와 동일합니다.
그렇다면 AMD64에서 무엇을 해야 합니까?함수에서 va_list의 변수를 전달하는 가장 쉬운 방법은 * 또는 & 연산자 없이 전달하는 것입니다.
예를 들어,
void foo(const char *fmt, ...) {
va_list ap;
int cnt;
va_start(ap, fmt);
bar(fmt, ap);
va_end(ap);
return cnt;
}
void bar(const char *fmt, va_list ap) {
va_arg(ap, int);
//do something
test(ap);
}
void test(va_list ap) {
va_arg(ap, int);
//do something
}
그냥 돼요!그리고 당신이 얼마나 많은 논쟁을 하고 있는지에 대해서는 걱정할 필요가.
언급URL : https://stackoverflow.com/questions/4958384/what-is-the-format-of-the-x86-64-va-list-structure
'programing' 카테고리의 다른 글
약속을 사용할 때 내부수업 방식이 정의되지 않은 이유는 무엇입니까? (0) | 2023.10.26 |
---|---|
PHP에서 Final을 언제 사용할 것인가요? (0) | 2023.10.26 |
JavaScript에서 프로토타입 상속 이해 (0) | 2023.10.26 |
반조류 판다 (0) | 2023.10.26 |
@AttributeOverride가 있는 @Embeddable 항목의 JPA @ElementCollection (0) | 2023.10.26 |