2014-12-08 2 views
3

최근 인터뷰에서 글로벌 레지스터 변수에 대해 질문했습니다. 모든 글로벌 변수가 데이터 세그먼트에 저장 될 것이라고 엉망이되었습니다.하지만 GCC에 대해 질문을 받았습니다. 인터뷰 후 나는 gcc는 전역 레지스터 변수를 지원합니다. 여기gcc에있는 전역 레지스터 변수

#include<stdio.h> 

register int var asm("ebx"); //storing global variable in register explicitly 

int main(void) 
{ 
....... 
} 

링크 https://gcc.gnu.org/onlinedocs/gcc/Global-Reg-Vars.html#Global-Reg-Vars

이다하지만 지금은 수명과 범위에 대한 혼란 스러워요과 정상 전역 변수 또는 레지스터 변수로 작동 여부? 또한 어떤 방법이나 일부 gcc에 명령을 그래서 우리는 컴파일러가 단순히 register 키워드를 무시하지 않으며 실제 등록에 저장됩니다 확신 할 것인가?

+0

디버거를 통해 시험해 볼 수 없습니까? – MrSykkox

+0

@ MrSykkox : 이걸 좀 도와 주실 래요? 또한 내 첫 번째 질문에 대한 답변을 제공해 주시겠습니까? 나는 감사 할 것이다. – Ankur

+0

평생에 대해서는 잘 모르겠지만 테스트 해보는 것이 좋습니다. gdb (-ggdb)를 사용하는 경우 디버그 플래그 (-g)로 컴파일합니다. 주 코드에서 var = something을 설정하십시오. 종료 전에 중단 점을 설정하십시오. 레지스터 값 (정보 레지스터 ebx)을 출력하십시오. – MrSykkox

답변

3

많은 사람들이 지적했듯이 등록기를 전 세계적으로 예약하는 것은 일반적으로 좋지 않습니다. 나는 여기에 원래 의도합니다 (docs에서)이었다 믿는다

이 같은 프로그래밍 언어 자주 를 액세스 전역 변수의 몇 가지있다 통역 프로그램에 유용 할 수 있습니다.

이 기능이 실제로 유용 할 수도 있고, 악화 될지도 모른다는 점은 특정 경우에만 결정될 수 있습니다. 당신의 경우 (인터뷰 질문), 그것은 정말로 중요하지 않습니다.

전역 선언과 마찬가지로 선언의 범위는 선언을 보는 모든 것입니다.

그러나 구현은 약간 까다 롭습니다. 다시 말하지만, 문서에서 인용 :

적어도 현재 편집 내에서 특정 레지스터 매장량이 사용하기 위해 전체 등록 , 에서 전역 레지스터 변수를 정의. 레지스터는 현재 컴파일의 함수 에서 다른 용도로 할당되지 않으며 저장되지 않고 이 함수에 의해 복원됩니다.

따라서 해당 선언문을 사용하여 컴파일 된 모든 코드는 해당 용도로 등록됩니다. 그러나이 예약으로 컴파일되지 않은 다른 코드에 연결하면 해당 예약이 예약되지 않습니다.

docs는 qsort의 훌륭한 예입니다. 코드가이 선언으로 컴파일 된 다음 c 런타임 (이 선언으로 컴파일되지 않은 것임)에서 qsort를 호출 한 다음 qsort가 코드로 다시 호출하면 (콜백 함수는 비교할 수 없습니다) compare 함수를 호출하기 전에 qsort가 레지스터에 스톰하지 않는지 확인하십시오.

라이브러리 함수를 호출 할 때 레지스터를 밟을 수있는 경우 어떻게 작동합니까? 다시 문서에서 : 그 라이브러리 루틴이 그것을 소지품되지 않도록

가 정상적으로 저장 기능을 컴퓨터에 호출에 의해 복원 된 레지스터를 선택합니다.그것도에서

:

또는 제어 이상의 스레드로부터 신호 핸들러 글로벌 레지스터 변수 액세스 안전하지

시스템 라이브러리 루틴이 일시적를 사용할 수 있기 때문에 다른 것들을 등록하십시오 (당면 과제를 위해 특별히 컴파일하지 않는 한) . 귀하의 질문의 마지막 부분에 관해서는

:

컴파일러

단순히 키워드를 등록 무시하지 않으며 실제 레지스터에 저장 될 것이다

난 당신이 무슨 뜻인지 모르겠어요 . 컴파일러가 어떤 식 으로든 asm("ebx")을 무시하면 레지스터에 저장되지 않습니다. 이것을 사용하는 요점은 var이 실제 ebx 레지스터에 저장되었는지 확인하는 것입니다.