2012-09-19 4 views

답변

2

적어도 Linux에는 syscalls이 있습니다. 사용자 공간이 커널에서 무엇인가를 원할 때, 소프트웨어 인터럽트 0x80은 레지스터에서 호출하고자하는 함수의 인덱스를 가지고 있습니다.

More here

+0

내가 알아야 할 것이 그 것이다. 내부에는 OS IVT가 처리하는 소프트웨어 인터럽트 문제가 있습니다. API는 이와 같은 것을 숨기 만합니다. 감사. –

+1

@ JoãoSilva : 이미 수년 동안 x86 프로세서는'syscall' /'sysenter' 명령을 통해 시스템 호출을 만드는 더 빠른 방법을 가지고 있습니다. glibc는 OS가 전달하는 정보를 사용하여 적절한 것을 선택합니다. – ninjalj

2

예, 아주 종종 인터럽트가있다.

인터럽트 및 예외 처리기와 시스템 호출은 종종 동일한 메커니즘을 사용하여 구현됩니다. 그 이유는이 모든 경우에 제어가 커널에 전송되어야하고 여러 레지스터가 이벤트 처리 이전에 보존되어야하고 복원되어야한다는 것입니다. 인터럽트 처리는 커널에서 발생하며 유비쿼터스 (드문 CPU는 인터럽트를 지원하지 않음)이며 인터럽트 처리, 예외 처리 및 시스템 호출에 대한 자연스러운 선택입니다.

어떤 경우에는 이미 커널 내에서 시스템 호출을 호출하는 것이 바람직합니다. 윈도우에서

예를 들어, 커널 코드는 종종 ZwFoo() 또는 NtFoo(), Foo 몇 가지 의미있는 함수 이름과 ZwNtFoo()의 두 버전을 구별 이름 접두어입니다 중 하나를 호출하는 옵션이 있습니다. ZwFoo()을 선택하면 Foo()이 직접 호출됩니다. OTOH라면 NtFoo()이 선택되면 컨트롤은 먼저 시스템 호출 (AKA 트랩) 메커니즘/코드를 통과해야만 실제 Foo()에 도달합니다. 두 버전 사이의 선택은 과 관련이 있습니다.

일부 단어에 Previous Mode ... 커널 코드가 신뢰됩니다. 사용자 코드가 신뢰할 수 없습니다. Foo()이 사용자 모드에서 호출되면, 커널은 모든 신뢰할 수없는 입력의 유효성을 검사하고 요청 된 것을 수행하기 전에 모든 권한이 제 위치에 있는지 확인하기 위해 최선을 다할 것입니다. 그것이 꼭해야하는 방법입니다. 이제 커널 자체가 Foo()에 전화해야 할 때가 있습니다. Foo()으로 전화하면 엄격한 수표를 발행 할 필요가 없습니다. 그러나 사용자 모드의 입력을 가진 사용자 코드를 대신하여 Foo()을 호출하면 (모두 신뢰할 수 없음) 해당 검사를 수행해야합니다. 따라서 상황에 따라 커널은 ZwFoo() 또는 NtFoo()을 호출합니다. NtFoo()이 호출되면 PreviousModeUserMode으로 설정되고 앞에서 설명한 검사의 필요성을 알립니다. ZwFoo()이 호출되면 PreviousMode은 사용자 모드 호출자의 경우 UserMode으로 유지되거나 커널 모드 호출자의 경우 KernelMode으로 설정됩니다. 따라서 사용자 모드 호출자는 검사를 피할 수는 없지만 커널은 필요한 경우 수행할지 여부를 결정합니다.

+0

아이디어를 얻기 위해'Foo'에'CreateFile' 또는'ReadFile'을 대신 쓸 수 있습니다. –

관련 문제