// Register: BAUDCTL
extern volatile unsigned char BAUDCTL @ 0x09B;
#ifndef _LIB_BUILD
asm("BAUDCTL equ 09Bh");
#endif
@ 기호는 무엇입니까? 주소 0x09B에서 캐시 할 수없는 부호없는 char을 정의한다는 의미입니까? 그러면 어셈블리에서 asm 함수가 필요한 이유는 무엇입니까?C에서 다음을 정의합니다.
// Register: BAUDCTL
extern volatile unsigned char BAUDCTL @ 0x09B;
#ifndef _LIB_BUILD
asm("BAUDCTL equ 09Bh");
#endif
@ 기호는 무엇입니까? 주소 0x09B에서 캐시 할 수없는 부호없는 char을 정의한다는 의미입니까? 그러면 어셈블리에서 asm 함수가 필요한 이유는 무엇입니까?C에서 다음을 정의합니다.
컴파일러 확장자 이고 표준 C의 일부가 아닙니다. 변수를 주소 0x09b
에 배치합니다. 임베디드 플랫폼 용 컴파일러의 작은 하위 집합에만 사용되며 하드웨어 레지스터에 대한 변수를 갖는 것이 일반적입니다.
이것에 대한 또 다른 일반적인 기술은 자신의 선언에 @
을 (그들이 준수 더 기준은 즉)를 지원하지 않습니다 컴파일러에 포인터를 사용하는 것입니다. 그런 다음이의 단점은 전송 제어 레지스터는 현재 메모리에 두 곳, 포인터 변수의 실제 하드웨어 레지스터, 다른 하나를 차지한다는 것입니다
volatile unsigned char *BAUDCTL = (unsigned char *) 0x09b;
과 같을 것입니다. 또 다른 단점은 레지스터에 액세스 할 때 포인터 역 참조 연산자를 사용해야한다는 것입니다.
이것은 표준 C가 아니며 확장의 일부 형식이므로 구현에 따라 다릅니다. 그러나 나는 당신이 옳았다는 것이 아주 좋은 기회라고 말했을 것이고 그것은 기본적으로 그 캐릭터가 주소 0x9b
에 있다고 말하고있다.
이것은 일반적으로 임베디드 시스템에서 메모리 매핑 I/O가 수행되는 방식입니다. asm
비트의 필요성에 관해서는
는, 다시는 (잘 교육이지만) 추측이다 : 당신 나중에 asm
블록 내에서 사용하려는 경우 extern
는 음, C
코드 BAUDCTL을 정의 할 수 있지만, 또한 어셈블러 정의가 필요할 수도 있습니다. asm
블록 내의 C 정의를 쉽게 얻을 수있는 방법이 없을 수도 있습니다.
나는 마이크로 칩이 이것을 링커에 맡겨두고 시작했다고 생각한다. 나는 그것을 완전히 이해하지는 못했지만 헤더 파일과 일치하는 링커 스크립트를 작성한다고 생각하기 때문에 코드에서 이름을 사용하여 메모리 맵 레지스터로 취급 할 수 있지만 여전히 적절한 C를 작성한다. – detly