Системные вызовы Реализация

Если пользовательское приложение делает системный вызов, срабатывает программное прерывание/исключение. Как я могу увидеть исходный код для генерации программного прерывания?


person user1458471    schedule 08.10.2012    source источник
comment
Вероятно, вам следует искать исходный код библиотеки (например, libc, GNU libc или uClibc), а не исходный код ядра.   -  person sawdust    schedule 08.10.2012


Ответы (3)


Это объясняется в Linux Assembly Howto. И вы должны прочитать википедию на странице syscall (а также о VDSO), а также введение(2) & системные вызовы(2) справочные страницы. См. также этот ответ и это один. Загляните также внутрь Gnu Libc и исходный код musl-libc. Научитесь также использовать strace, чтобы узнать, какие системные вызовы выполняются данной командой или процессом.

См. также соглашения о вызовах и спецификацию двоичного интерфейса приложения, относящуюся к вашей системе. Для x86-64 это здесь.

person Basile Starynkevitch    schedule 08.10.2012
comment
Прямо сейчас Linux Assembly Howto по-прежнему объясняет устаревший int 0x80 вместо системного вызова. - person ceving; 24.11.2013
comment
@ceving: Да. Не стесняйтесь вносить свой вклад в этот Assembly HowTo, чтобы улучшить его. Но я считаю, что в наши дни мало кто заботится об ассемблере, потому что компиляторы дают лучший код, чем может написать человек, и из-за VDSO... - person Basile Starynkevitch; 24.11.2013
comment
Это совершенно то же самое. Отличаются только числа и регистры. exit(n) это eax=60 edi=n syscall вместо eax=1 ebx=n int0x80. - person ceving; 24.11.2013

давным-давно в ядро ​​​​была ловушка int 0x80, но в настоящее время предпочтительнее sysenter.

вы можете получить код, сбросив раздел vsyscall, который автоматически отображается в каждый процесс ядром.

$ cat /proc/self/maps 
blah blah blah
...
blah blah blah
ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0                  [vsyscall]

для получения дополнительной информации см. эту статью

person Zang MingJie    schedule 08.10.2012

Программное прерывание может быть вызвано ассемблерной инструкцией Intel x86 int n, где n — номер прерывания. Системный вызов — это частный случай программного прерывания; в вы можете вручную сделать системный вызов

mov eax, m
int 0x80

где m следует заменить на номер прерывания. Ниже приведены списки 32-разрядных номеров системных вызовов и 64-битные номера системных вызовов со ссылками на онлайн-справочные страницы для каждой функции. Вам также необходимо передавать параметры в системный вызов через другие регистры (ebx, ecx и т. д.), и вы можете прочитать об этом подробнее здесь.

Это наиболее общий способ выполнения системных вызовов, поскольку он не зависит от внешних библиотек, таких как libc, и вы можете реализовать его на C/C++, если вам нужно, используя встроенный ассемблер.

person emprice    schedule 08.10.2012
comment
Это специфичный для реализации ответ на общий вопрос. - person Chris Stratton; 08.10.2012
comment
Ссылки не работают. Возможно, лучше напрямую ссылаться на исходный код ядра: 32 бит и 64 бит - person ceving; 24.11.2013