SIGNAL-SAFETY(7) | Руководство программиста Linux | SIGNAL-SAFETY(7) |
ИМЯ¶
signal-safety - функции async-signal-safe
ОПИСАНИЕ¶
Функцией async-signal-safe называется функция, которую безопасно вызывать внутри обработчика сигналов. Многие функции не являются async-signal-safe. В частности, нереентерабельные функции, обычно, небезопасно вызывать в обработчиках сигналов.
Виды проблем, которые делают функцию небезопасной, можно быстро понять на примере реализации библиотеки stdio, все функции которой являются не async-signal-safe.
При выполнении буферизируемого ввода-вывода в файл функции stdio должны вести статически выделенный буфер и связанные с ним счётчики и индексы (или указатели), содержащие количество данных и текущее положение в буфере. Предположим, что основная программа находится в середине вызова функции stdio, например printf(3), которая обновляет часть буфера и связанных переменных. Если в этот момент программа прервётся обработчиком сигнала, который также вызывает printf(3), то второй вызов printf(3) будет работать с не целостными данными и результат будет непредсказуем.
Чтобы не возникало проблем с небезопасными функциями есть два варианта:
- 1.
- Следить, чтобы (а) обработчик сигнала вызывал только функции async-signal-safe, и (б) сам обработчик сигнала был реентерабельным по отношению к глобальным переменным основной программы.
- 2.
- Блокировать доставку сигнала в основной программе при вызове небезопасных функций или при работе с глобальными данными, доступными из обработчика сигнала.
Обычно, второй вариант труден для программ любой сложности, поэтому используется первый вариант.
В POSIX.1 определён набор функций, реализация которых должна быть async-signal-safe (реализация может предоставлять безопасную реализацию и других функций, но это не требуется стандартом и другие реализации могут не предоставлять те же гарантии) Обычно, функция является async-signal-safe или потому что она реентерабельная, или из-за её атомарности по отношению к сигналам (т. е., её выполнение не может быть прервано обработчиком сигнала).
Набор функций async-signal-safe по POSIX.1 показан в таблице далее. Функции, если не указано обратное, являются async-signal-safe и по POSIX.1-2001; в таблице отмечены изменения в последующих стандартах.
функция | Примечания |
abort(3) | Добавлена в POSIX.1-2003 |
accept(2) | |
access(2) | |
aio_error(3) | |
aio_return(3) | |
aio_suspend(3) | смотрите замечания далее |
alarm(2) | |
bind(2) | |
cfgetispeed(3) | |
cfgetospeed(3) | |
cfsetispeed(3) | |
cfsetospeed(3) | |
chdir(2) | |
chmod(2) | |
chown(2) | |
clock_gettime(2) | |
close(2) | |
connect(2) | |
creat(2) | |
dup(2) | |
dup2(2) | |
execl(3) | Добавлена в POSIX.1-2008; смотрите замечания ниже |
execle(3) | смотрите замечания далее |
execv(3) | Добавлена в POSIX.1-2008 |
execve(2) | |
_exit(2) | |
_Exit(2) | |
faccessat(2) | Добавлена в POSIX.1-2008 |
fchdir(2) | Добавлена в POSIX.1-2013 |
fchmod(2) | |
fchmodat(2) | Добавлена в POSIX.1-2008 |
fchown(2) | |
fchownat(2) | Добавлена в POSIX.1-2008 |
fcntl(2) | |
fdatasync(2) | |
fexecve(3) | Добавлена в POSIX.1-2008 |
ffs(3) | Добавлена в POSIX.1-2016 |
fork(2) | смотрите замечания далее |
fstat(2) | |
fstatat(2) | Добавлена в POSIX.1-2008 |
fsync(2) | |
ftruncate(2) | |
futimens(3) | Добавлена в POSIX.1-2008 |
getegid(2) | |
geteuid(2) | |
getgid(2) | |
getgroups(2) | |
getpeername(2) | |
getpgrp(2) | |
getpid(2) | |
getppid(2) | |
getsockname(2) | |
getsockopt(2) | |
getuid(2) | |
htonl(3) | Добавлена в POSIX.1-2016 |
htons(3) | Добавлена в POSIX.1-2016 |
kill(2) | |
link(2) | |
linkat(2) | Добавлена в POSIX.1-2008 |
listen(2) | |
longjmp(3) | Добавлена в POSIX.1-2016; смотрите замечания ниже |
lseek(2) | |
lstat(2) | |
memccpy(3) | Добавлена в POSIX.1-2016 |
memchr(3) | Добавлена в POSIX.1-2016 |
memcmp(3) | Добавлена в POSIX.1-2016 |
memcpy(3) | Добавлена в POSIX.1-2016 |
memmove(3) | Добавлена в POSIX.1-2016 |
memset(3) | Добавлена в POSIX.1-2016 |
mkdir(2) | |
mkdirat(2) | Добавлена в POSIX.1-2008 |
mkfifo(3) | |
mkfifoat(3) | Добавлена в POSIX.1-2008 |
mknod(2) | Добавлена в POSIX.1-2008 |
mknodat(2) | Добавлена в POSIX.1-2008 |
ntohl(3) | Добавлена в POSIX.1-2016 |
ntohs(3) | Добавлена в POSIX.1-2016 |
open(2) | |
openat(2) | Добавлена в POSIX.1-2008 |
pause(2) | |
pipe(2) | |
poll(2) | |
posix_trace_event(3) | |
pselect(2) | |
pthread_kill(3) | Добавлена в POSIX.1-2013 |
pthread_self(3) | Добавлена в POSIX.1-2013 |
pthread_sigmask(3) | Добавлена в POSIX.1-2013 |
raise(3) | |
read(2) | |
readlink(2) | |
readlinkat(2) | Добавлена в POSIX.1-2008 |
recv(2) | |
recvfrom(2) | |
recvmsg(2) | |
rename(2) | |
renameat(2) | Добавлена в POSIX.1-2008 |
rmdir(2) | |
select(2) | |
sem_post(3) | |
send(2) | |
sendmsg(2) | |
sendto(2) | |
setgid(2) | |
setpgid(2) | |
setsid(2) | |
setsockopt(2) | |
setuid(2) | |
shutdown(2) | |
sigaction(2) | |
sigaddset(3) | |
sigdelset(3) | |
sigemptyset(3) | |
sigfillset(3) | |
sigismember(3) | |
siglongjmp(3) | Добавлена в POSIX.1-2016; смотрите замечания ниже |
signal(2) | |
sigpause(3) | |
sigpending(2) | |
sigprocmask(2) | |
sigqueue(2) | |
sigset(3) | |
sigsuspend(2) | |
sleep(3) | |
sockatmark(3) | Добавлена в POSIX.1-2004 |
socket(2) | |
socketpair(2) | |
stat(2) | |
stpcpy(3) | Добавлена в POSIX.1-2016 |
stpncpy(3) | Добавлена в POSIX.1-2016 |
strcat(3) | Добавлена в POSIX.1-2016 |
strchr(3) | Добавлена в POSIX.1-2016 |
strcmp(3) | Добавлена в POSIX.1-2016 |
strcpy(3) | Добавлена в POSIX.1-2016 |
strcspn(3) | Добавлена в POSIX.1-2016 |
strlen(3) | Добавлена в POSIX.1-2016 |
strncat(3) | Добавлена в POSIX.1-2016 |
strncmp(3) | Добавлена в POSIX.1-2016 |
strncpy(3) | Добавлена в POSIX.1-2016 |
strnlen(3) | Добавлена в POSIX.1-2016 |
strpbrk(3) | Добавлена в POSIX.1-2016 |
strrchr(3) | Добавлена в POSIX.1-2016 |
strspn(3) | Добавлена в POSIX.1-2016 |
strstr(3) | Добавлена в POSIX.1-2016 |
strtok_r(3) | Добавлена в POSIX.1-2016 |
symlink(2) | |
symlinkat(2) | Добавлена в POSIX.1-2008 |
tcdrain(3) | |
tcflow(3) | |
tcflush(3) | |
tcgetattr(3) | |
tcgetpgrp(3) | |
tcsendbreak(3) | |
tcsetattr(3) | |
tcsetpgrp(3) | |
time(2) | |
timer_getoverrun(2) | |
timer_gettime(2) | |
timer_settime(2) | |
times(2) | |
umask(2) | |
uname(2) | |
unlink(2) | |
unlinkat(2) | Добавлена в POSIX.1-2008 |
utime(2) | |
utimensat(2) | Добавлена в POSIX.1-2008 |
utimes(2) | Добавлена в POSIX.1-2008 |
wait(2) | |
waitpid(2) | |
wcpcpy(3) | Добавлена в POSIX.1-2016 |
wcpncpy(3) | Добавлена в POSIX.1-2016 |
wcscat(3) | Добавлена в POSIX.1-2016 |
wcschr(3) | Добавлена в POSIX.1-2016 |
wcscmp(3) | Добавлена в POSIX.1-2016 |
wcscpy(3) | Добавлена в POSIX.1-2016 |
wcscspn(3) | Добавлена в POSIX.1-2016 |
wcslen(3) | Добавлена в POSIX.1-2016 |
wcsncat(3) | Добавлена в POSIX.1-2016 |
wcsncmp(3) | Добавлена в POSIX.1-2016 |
wcsncpy(3) | Добавлена в POSIX.1-2016 |
wcsnlen(3) | Добавлена в POSIX.1-2016 |
wcspbrk(3) | Добавлена в POSIX.1-2016 |
wcsrchr(3) | Добавлена в POSIX.1-2016 |
wcsspn(3) | Добавлена в POSIX.1-2016 |
wcsstr(3) | Добавлена в POSIX.1-2016 |
wcstok(3) | Добавлена в POSIX.1-2016 |
wmemchr(3) | Добавлена в POSIX.1-2016 |
wmemcmp(3) | Добавлена в POSIX.1-2016 |
wmemcpy(3) | Добавлена в POSIX.1-2016 |
wmemmove(3) | Добавлена в POSIX.1-2016 |
wmemset(3) | Добавлена в POSIX.1-2016 |
write(2) |
Замечания:
- В POSIX.1-2001 и POSIX.1-2004 требуется, чтобы функции fpathconf(3), pathconf(3) и sysconf(3) были async-signal-safe, но это требование удалено в POSIX.1-2008.
- Если обработчик сигнала прерывает выполнение небезопасной функции и обработчик завершается вызовом longjmp(3) или siglongjmp(3) и далее программа вызывает небезопасную функцию, то поведение программы непредсказуемо.
- В POSIX.1-2003 уточнено, что если приложение вызывает fork(2) из обработчика сигнала и и зарегистрированный обработчик fork (с помощью pthread_atfork(3)) вызывает не async-signal-safe функцию, то поведение непредсказуемо. Вероятно, в будущих версиях стандарта вызов fork(2) будет удалён из списка функций async-signal-safe.
Отклонения в библиотеке GNU C¶
В библиотеке GNU C есть следующие известные отклонения от стандарта:
- До glibc 2.24 внутри execl(3) и execle(3) использовалась realloc(3) и поэтому они были не безопасны для асинхронных сигналов. Это было исправлено в glibc 2.24.
- Реализация aio_suspend(3) в glibc не является безопасной для асинхронных сигналов, так как в ней используется pthread_mutex_lock(3).
СМ. ТАКЖЕ¶
ЗАМЕЧАНИЯ¶
Эта страница является частью проекта Linux man-pages версии 4.16. Описание проекта, информацию об ошибках и последнюю версию этой страницы можно найти по адресу https://www.kernel.org/doc/man-pages/.
ПЕРЕВОД¶
Русский перевод этой страницы руководства был сделан Alexander Golubev <fatzer2@gmail.com>, Azamat Hackimov <azamat.hackimov@gmail.com>, Hotellook, Nikita <zxcvbnm3230@mail.ru>, Spiros Georgaras <sng@hellug.gr>, Vladislav <ivladislavefimov@gmail.com>, Yuri Kozlov <yuray@komyakino.ru> и Иван Павлов <pavia00@gmail.com>
Этот перевод является бесплатной документацией; прочитайте Стандартную общественную лицензию GNU версии 3 или более позднюю, чтобы узнать об условиях авторского права. Мы не несем НИКАКОЙ ОТВЕТСТВЕННОСТИ.
Если вы обнаружите ошибки в переводе этой страницы руководства, пожалуйста, отправьте электронное письмо на man-pages-ru-talks@lists.sourceforge.net.
13 марта 2017 г. | Linux |