특정 주소(예: 0x43C00000)에서 읽거나 쓸 수 있는 메모리 매핑된 주변 장치가 있다고 가정해 보겠습니다. 주변 장치와 통신하기 위해 Linux 운영 체제의 동일한 메모리 위치에서 데이터를 읽을 수 있기를 원합니다. 문제의 주소는 물리적 주소이므로 해당 주소 위치에서 읽을 수 있는 커널 모듈을 작성할 수 있어야 합니다.
커널에서 다음과 같은 것이 있다면
#define BASE_ADDR 0x43C00000
#define OFFSET 4
int * mem_addr;
mem_addr = BASEADDR + OFFSET;
내 생각에는 이것이 주변기기의 두 번째 쓰기 블록(0x43C00004)에 대한 포인터를 제공해야 한다고 생각합니다. 인쇄
printk(KERN_INFO "%p\n", mem_addr)
이것이 맞다고 말하는 것 같습니다.
이제 내가 다음과 같은 일을 하려고 하면
printk(KERN_INFO "%d\n", *mem_addr);
나는 주변기기가 메모리에 쓰고 있는 데이터를 읽어서 내가 원하는 것을 성취해야 한다고 생각했을 것입니다. 그러나 그러한 명령문을 모듈에 넣으려고 하면 Linux가 해당 명령문을 종료합니다. 내 /var/log/messages를 보면 다음과 같습니다.
Oops: 0000 [#1] SMP
Modules linked in; TEST_MOD(0+) ...
다음은 레지스터 상태에 대한 정보입니다. 그래서 분명히 나는 이런 식으로 메모리를 읽는 것이 허용되지 않습니다. 커널 모듈에 메모리 읽기 권한을 부여하는 방법이 있습니까?
답변1
해당 위치에 대한 커널 가상 주소 매핑을 설정해야 합니다.
mem_addr = ioremap_nocache(BASEADDR + OFFSET, SIZE);
(같은 질문을 두 번 하신 것 같습니다.여기에 링크 설명을 입력하세요).