# include <stdio.h>
# include <stdlib.h>
# include <string.h>
# include <unistd.h>
# include <fcntl.h>
# include <sys/types.h>
# include <sys/stat.h>
const char *test_file="/home/user/test.txt";
void func(void)
{
char c;
pid_t pid;
/* create file descriptor in read and write mode */
int fd = open(test_file, O_RDWR);
if (fd == -1)
{
/* Handle error */
abort();
}
/* fork process */
pid = fork();
if (pid == -1)
{
/* Handle error */
abort();
}
else if (pid == 0)
{ /* Child process accesses file descriptor inherited
from parent process */
(void)read(fd, &c, 1);
}
else
{ /* Parent process access same file descriptor as
child process */
(void)read(fd, &c, 1);
}
}
В этом примере, дескриптор файла fd
создается в режиме чтения и режиме записи. Процесс затем разветвлен. Дочерний процесс наследовался и доступы fd
с теми же полномочиями как родительский процесс. Состояние состязания существует между родительскими и дочерними процессами. Содержимое файла уязвимо для нападений посредством дочернего процесса.
Коррекция — закрывает и вновь открыла наследованный дескриптор файлаПосле того, как вы создадите дескриптор файла, проверяйте файл на вмешательство. Затем закройте наследованный дескриптор файла в дочернем процессе и вновь откройте его в режиме только для чтения.
# include <stdio.h>
# include <stdlib.h>
# include <string.h>
# include <unistd.h>
# include <fcntl.h>
# include <sys/types.h>
# include <sys/stat.h>
const char *test_file="/home/user/test.txt";
void func(void)
{
char c;
pid_t pid;
/* Get the state of file for further file tampering checking */
/* create file descriptor in read and write mode */
int fd = open(test_file, O_RDWR);
if (fd == -1)
{
/* Handle error */
abort();
}
/* Be sure the file was not tampered with while opening */
/* fork process */
pid = fork();
if (pid == -1)
{
/* Handle error */
(void)close(fd);
abort();
}
else if (pid == 0)
{ /* Close file descriptor in child process and repoen
it in read only mode */
(void)close(fd);
fd = open(test_file, O_RDONLY);
if (fd == -1)
{
/* Handle error */
abort();
}
(void)read(fd, &c, 1);
(void)close(fd);
}
else
{ /* Parent acceses original file descriptor */
(void)read(fd, &c, 1);
(void)close(fd);
}
}