8.9. Функция mprotect(): задание прав доступа к памяти
8.9. Функция mprotect(): задание прав доступа к памяти
В разделе 5.3, "Отображение файлов в памяти", рассказывалось о том, как осуществляется отображение файла в памяти. Вспомните, что третьим аргументом функции mmap() является битовое объединение флагов доступа: флаги PROT_READ, PROT_WRITE и PROT_EXEC задают права чтения, записи и выполнения файла, а флаг PROT_NONE означает запрет доступа. Если программа пытается выполнить над отображаемым файлом недопустимую операцию, ей посылается сигнал SIGSEGV (нарушение сегментации), который приводит к завершению программы.
После того как файл был отображен в памяти, изменить права доступа к нему позволяет функция mprotect(). Ее аргументами является адрес области памяти, размер области и новый набор флагов доступа. Область должна состоять из целых страниц, т.е. начинаться и заканчиваться на границе между страницами.
Корректное выделение памяти
Учтите, что память, выделяемая функцией malloc(), обычно не выравнивается по границе страниц, даже если размер области кратен размеру страницы. Если требуется защищать память, выделяемую функцией malloc(), нужно запросить более крупный блок, а затем найти в нем участок, выровненный по границе страниц.
Кроме того, с помощью функции mmap() можно обойти функцию malloc() и запрашивать память непосредственно у ядра Linux.
Предположим, к примеру, что программа выделяет страницу, отображая в памяти файл /dev/zero. Память инициализируется как для чтения, так и для записи:
int fd = open("/dev/zero", O_RDONLY);
char* memory =
mmap(NULL, page_size, PROT_READ | PROT_WRITE,
MAP_PRIVATE, fd, 0);
close(fd);
Далее программа запрещает запись в эту область памяти, вызывая функцию mprotect():
mprotect(memory, page_size, PROT_READ);
Существует оригинальная методика контроля памяти: можно защитить область памяти с помощью функций mmap() и mprotect(), а затем обрабатывать сигнал SIGSEGV, посылаемый при попытке доступа к этой памяти. Эта методика иллюстрируется в листинге 8.7.
Листинг 8.7. (mprotect.c) Обнаружение попыток доступа к памяти благодаря функции mprotect()
#include <fcntl.h>
#include <signal.h>
#include <stdio.h>
#include <string.h>
#include <sys/mman.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
static int alloc_size;
static char* memory;
void segv_handler(int signal_number) {
printf("memory accessed! ");
mprotect(memory, alloc_size, PROT_READ | PROT_WRITE);
}
int main() {
int fd;
struct sigaction sa;
/* Назначение функции segv_handler() обработчиком сигнала
SIGSEGV. */
memset(&sa, 0, sizeof(sa));
sa.sa_handler = &segv_handler;
sigaction(SIGSEGV, &sa, NULL);
/* Выделение одной страницы путем отображения в памяти файла
/dev/zero. Сначала память доступна только для записи. */
alloc_size = getpagesize();
fd = open("/dev/zero", O_RDONLY);
memory =
mmap(NULL, alloc_size, PROT_WRITE, MAP_PRIVATE, fd, 0);
close(fd);
/* Запись на страницу для получения ее копии в частное
использование. */
memory[0] = 0;
/* Запрет на запись в память. */
mprotect(memory, alloc_size, PROT_NONE);
/* Попытка записи в память. */
memory[0] = 1;
/* Удаление памяти. */
printf("all done ");
munmap(memory, alloc_size);
return 0;
}
Программа работает по следующей схеме.
1. Задается обработчик сигнала SIGSEGV.
2. Файл /dev/zero отображается в памяти, из которой выделяется одна страница. В эту страницу записывается инициализирующее значение, благодаря чему программе предоставляется частная копия страницы.
3. Программа защищает память, вызывая функцию mprotect() с флагом PROT_NONE.
4. Когда программа впоследствии обращается к памяти, Linux посылает ей сигнал SIGSEGV, который обрабатывается в функции segv_handler(). Обработчик сигнала отменяет защиту памяти, разрешая выполнить операцию записи.
5. Программа удаляет область память с помощью функции munmap().
Более 800 000 книг и аудиокниг! 📚
Получи 2 месяца Литрес Подписки в подарок и наслаждайся неограниченным чтением
ПОЛУЧИТЬ ПОДАРОКЧитайте также
5.5. Смена владельца, прав доступа и времени изменения
5.5. Смена владельца, прав доступа и времени изменения Несколько других системных вызовов дают вам возможность изменять другие относящиеся к файлу сведения: в частности, владельца и группу файла, права доступа к файлу и времена доступа и изменения
5.5.2. Изменение прав доступа: chmod() и fchmod()
5.5.2. Изменение прав доступа: chmod() и fchmod() Изменение прав доступа осуществляется с помощью одного из двух системных вызовов, chmod() и fchmod():#include <sys/types.h> /* POSIX */#include <sys/stat.h>int chmod(const char *path, mode_t mode);int fchmod(int fildes, mode_t mode);chmod() работает с аргументом имени файла, a fchmod() работает с
11.1. Проверка прав доступа
11.1. Проверка прав доступа Как мы видели в разделе 5.4.2 «Получение информации о файлах», файловая система хранит идентификаторы владельца и группы файла в виде числовых значений; это типы uid_t и gid_t соответственно. Для краткости мы используем для «идентификатора владельца
11.1.2. Модификаторы прав доступа к файлам
11.1.2. Модификаторы прав доступа к файлам Модификаторы прав доступа файлов — это также битовые маски, значения которых представляют биты setuid, setgid и sticky-бит ("липкий" бит). Если бит setuid установлен для исполняемого файла, то эффективный идентификатор пользователя процесса
11.3.3. Простое определение прав доступа
11.3.3. Простое определение прав доступа Хотя режим файла представляет всю информацию, которая может понадобиться программе, для определения того, имеет ли она доступ к файлу, тестирование набора прав — дело хитрое и чреватое ошибкам. Поскольку ядро ухе включает в себя код
11.3.4. Изменение прав доступа к файлу
11.3.4. Изменение прав доступа к файлу Права доступа и модификаторы прав доступа к файлу изменяются с помощью системного вызова chmod().#include <sys/stat.h>int chmod(const char *pathname, mode_t mode);int fchmod(int fd, mode_t mode);Хотя chmod() позволяет указать путь, помните, что права доступа к файлу определяет inode, а
Режимы доступа к памяти
Режимы доступа к памяти Все обращения к памяти в AS/400 выполняются под управлением четырех битов режима: «Сквозная запись» W (Write Through), «Кэширование запрещено» I (Caching Inhibited), «Когерентность памяти» M (Memory Coherence ) и «Отслеживаемая память» G (Guarded Storage). Одна из характеристик
Приложение В. Команды chmod и chown: изменение прав доступа
Приложение В. Команды chmod и chown: изменение прав доступа В Linux есть понятие владельца файла (каталога) и прав доступа к нему. С данными понятиями мы познакомились в главе I, но подробно не рассматривали их. Здесь мы поговорим об этом подробнее.В Linux существует три типа прав
Настройка прав доступа к файлам и ограничение прав пользователей
Настройка прав доступа к файлам и ограничение прав пользователей В процессе работы на компьютере часто возникает необходимость защитить те или иные свои данные от неквалифицированного и несанкционированного просмотра и редактирования. Эта задача обычно возникает при
Явное задание размера памяти
Явное задание размера памяти Иной путь выделения памяти заключается в явном ее задании. Во внешнем описании мы могли бы скачать: char m1[44] = "Только ограничьтесь одной строкой.";вместо char m1[ ] = "Только ограничьтесь одной строкой."; Можно быть уверенным, что число
8.2. Функция access(): проверка прав доступа к файлу
8.2. Функция access(): проверка прав доступа к файлу Функция access() определяет, имеет ли вызывающий ее процесс право доступа к заданному файлу. Функция способна проверить любую комбинацию привилегий чтения, записи и выполнения, а также факт существования файла.Функция access()
1.4. Изменение прав доступа к файлу
1.4. Изменение прав доступа к файлу Вы можете изменять режим доступа к файлам, которыми владеете, с помощью команды chmod. Аргументы этой команды могут быть заданы либо в числовом виде (абсолютный режим), либо в символьном (символьный режим). Сначала рассмотрим символьный
17.1. Проверка прав доступа к файлу
17.1. Проверка прав доступа к файлу Основные форматы команды test:test условиеили[ условие ]Обратите внимание, что с обеих сторон от условия обязательно остаются пробелы. При проверке права на доступ к файлу может применяться довольно много условий. В табл. 17.1 содержится
18.3.7. Проверка прав доступа к файлу
18.3.7. Проверка прав доступа к файлу Вы можете также осуществлять контроль прав доступа к файлу. Ниже приводится несложная проверка на предмет того, можно ли вести записи в файле test.txt, который переприсвоен переменной logfile.$ pg ifwr#!/bin/sh# ifwrLOGFILE=test.txt echo $LOGFILEif [ ! —w "$LOGFILE" ]; thenecho " You