Применимость: Linux, FreeBSD, UNIX
Слова для поиска: доступ, права
У меня не хватает доступа, я не могу скопировать изменить или перенести файл.
Здесь и далее «файл» понимается в широком смысле этого слова — файл, каталог, символическая ссылка, сокет, устройство и др. Раз все в Unix это файлы, речь идет о доступе ко всему. Разделяемые области памяти процессов также попадают под категорию объект доступа и там действуют те же принципы.
В основе механизмов разграничения доступа лежат имена пользователей и имена групп пользователей.
Создавать и удалять пользователей может только суперпользователь - root.
Кроме того, в системе управления доступом учитывается некоторое число групп пользователей, причем каждый пользователь может быть включен в одну или несколько групп. Члены разных групп могут иметь разные права по доступу к файлам, например, группа администраторов может иметь больше прав, чем группа программистов.
Создавать и удалять группы может только суперпользователь - root, только он может изменять состав участников той или иной группы.
Для каждого пользователя зарегистрирована основная группа.
Каждому процессу сопоставлено имя пользователя и основная группа, то есть процесс выполняется от имени определенного пользователя.
Если какой либо процесс создает файл или каталог, в индексный дескриптор файла (inode) записывается унаследованное у процесса значение имени так называемого владельца файла и группы, которая имеет права на этот файл.
Владельца и группу файла можно поменять в ходе дальнейшей работы с помощью команд chown и chgrp, но сделать это может только root (подробнее будет сказано чуть позже).
Ядро при определении разрешения на доступ различает владельца, группу и всех остальных пользователей.
При попытке процесса выполнить операцию с файлом ядро проверяет имя пользователя от имени которого выполняется процесс, атрибуты доступа файла и принимает решение разрешить или отклонить операцию.
Алгоритм проверки прав пользователя при обращении к файлу можно описать следующим образом:
Система вначале проверяет, совпадает ли имя пользователя с именем владельца файла. Если эти имена совпадают (т. е. владелец обращается к своему файлу), то проверяется, имеет ли владелец соответствующее право доступа на чтение, на запись или на выполнение
не удивляйтесь, суперпользователь или владелец может лишить некоторых прав и владельца файла.
Если право такое есть, то соответствующая операция разрешается.
Если же нужного права владелец не имеет, то проверка прав, предоставляемых через группу или через группу атрибутов доступа для остальных пользователей, уже даже не проверяются, а пользователю выдается сообщение о невозможности выполнения затребованного действия (обычно что-то вроде «Permission denied»).
Однако право на изменение атрибутов доступа к файлам за владельцем сохраняется всегда.
Если имя пользователя, обращающегося к файлу, не совпадает с именем владельца, то система проверяет, принадлежит ли владелец к группе, которая сопоставлена данному файлу (будем просто называть ее группой файла). Если принадлежит, то для определения возможности доступа к файлу используются атрибуты, относящиеся к группе, а на атрибуты для владельца и всех остальных пользователей внимания не обращается. Если же пользователь не является владельцем файла и не входит в группу файла, то его права определяются атрибутами для остальных пользователей. Таким образом, третья группа атрибутов, определяющих права доступа к файлу, относится ко всем пользователям, кроме владельца файла и пользователей, входящих в группу файла.
Давайте выполним команду ls -l и зададим ей в качестве дополнительного параметра имя конкретного файла, например, файла, задающего саму команду ls. (Обратите, кстати, внимание на эту возможность команды ls -l — получить информацию о конкретном файле, а не о всех файлах каталога сразу).
[user]$ ls -l /bin/ls -rwxr-xr-x 1 root root 49940 Sep 12 1999 /bin/ls
Вы видите, что в данном случае владельцем файла является пользователь root и группа root. Но нас сейчас в выводе этой команды больше интересует первое поле, определяющее тип файла и права доступа к файлу. Это поле в приведенном примере представлено цепочкой символов -rwxr-xr-x. Эти символы можно условно разделить на 4 группы.
Первая группа, состоящая из единственного символа, определяет тип файла. Этот символ в соответствии с возможными типами файлов, рассмотренными в предыдущем разделе, может принимать такие значения:
Далее следуют три группы по три символа, которые и определяют права доступа к файлу соответственно
В нашем примере права доступа для владельца определены как rwx, что означает, что владелец (root) имеет право читать файл ®, производить запись в этот файл (w), и запускать файл на выполнение (x).
Замена любого из этих символов прочерком (-) будет означать, что пользователь лишается соответствующего права. В том же примере мы видим, что все остальные пользователи (включая и тех, которые вошли в группу root) лишены права записи в этот файл, т. е. не могут файл редактировать и вообще как-то изменять.
Вообще говоря, права доступа и информация о типе файла в UNIX®-системах хранятся в индексных дескрипторах в отдельной структуре, состоящей из двух байтов, т. е. из 16 бит (это естественно, ведь компьютер оперирует битами, а не символами r, w, x).
Четыре бита из этих 16-ти отведены для кодированной записи о типе файла. Следующие три бита задают особые свойства исполняемых файлов, о которых мы скажем чуть позже. И, наконец, оставшиеся 9 бит определяют права доступа к файлу. Эти 9 бит разделяются на 3 группы по три бита. Первые три бита задают права пользователя, следующие три бита — права группы, последние 3 бита определяют права всех остальных пользователей (т. е. всех пользователей, за исключением владельца файла и группы файла).
При этом, если соответствующий бит имеет значение 1, то право предоставляется, а если он равен 0, то право не предоставляется. В символьной форме записи прав единица заменяется соответствующим символом (r, w или x), а 0 представляется прочерком.
Право на чтение ® файла означает, что пользователь может просматривать содержимое файла с помощью различных команд просмотра, например, командой more или с помощью любого текстового редактора. Но, подредактировав содержимое файла в текстовом редакторе, вы не сможете сохранить изменения в файле на диске, если не имеете права на запись (w) в этот файл.
Право на выполнение (x) означает, что вы можете загрузить файл в память и попытаться запустить его на выполнение как исполняемую программу. Конечно, если в действительности файл не является программой (или скриптом shell), то запустить этот файл на выполнение не удастся, но, с другой стороны, даже если файл действительно является программой, но право на выполнение для него не установлено, то он тоже не запустится.
Вот мы и узнали, какие файлы в Linux являются исполняемыми! Как видите, расширение имени файла тут не при чем, все определяется установкой атрибута «исполняемый», причем право на исполнение может быть предоставлено не всем!
Если выполнить ту же команду ls -l, но в качестве последнего аргумента ей указать не имя файла, а имя каталога, мы увидим, что для каталогов тоже определены права доступа, причем они задаются теми же самыми символами rwx. Например, выполнив команду ls –l /, мы увидим, что каталогу bin соответствует строка:
drwxr-xr-x 2 root root 2048 Jun 21 21:11 bin
Естественно, что по отношению к каталогам трактовка понятий «право на чтение», «право на запись» и «право на выполнение» несколько изменяется. Право на чтение по отношению к каталогам легко понять, если вспомнить, что каталог — это просто файл, содержащий список файлов в данном каталоге. Следовательно, если вы имеете право на чтение каталога, то вы можете просматривать его содержимое (этот самый список файлов в каталоге). Право на запись тоже понятно — имея такое право, вы сможете создавать и удалять файлы в этом каталоге, т. е. просто добавлять в каталог или удалять из него запись, содержащую имя какого-то файла и соответствующие ссылки. Право на выполнение интуитивно менее понятно. Оно в данном случае означает право переходить в этот каталог. Если вы, как владелец, хотите дать доступ другим пользователям на просмотр какого-то файла в своем каталоге, вы должны дать им право доступа в каталог, т. е. дать им «право на выполнение каталога». Более того, надо дать пользователю право на выполнение для всех каталогов, стоящих в дереве выше данного каталога. Поэтому в принципе для всех каталогов по умолчанию устанавливается право на выполнение как для владельца и группы, так и для всех остальных пользователей. И, уж если вы хотите закрыть доступ в каталог, то лишите всех пользователей (включая группу) права входить в этот каталог. Только не лишайте и себя такого права, а то придется обращаться к суперпользователю!
После прочтения предыдущего абзаца может показаться, что право на чтение каталога не дает ничего нового по сравнению с правом на выполнение. Однако разница в этих правах все же есть. Если задать только право на выполнение, вы сможете войти в каталог, но не увидите там ни одного файла (этот эффект особенно наглядно проявляется в том случае, если вы пользуетесь каким-то файловым менеджером, например, программой Midnight Commander). Если вы имеете право доступа в каком-то из подкаталогов этого каталога, то вы можете перейти в него (командой cd), но, как говорится «вслепую», по памяти, потому что списка файлов и подкаталогов текущего каталога вы не увидите.
Для изменения прав доступа к файлу используется команда chmod. Ее можно использовать в двух вариантах. В первом варианте вы должны явно указать, кому какое право даете или кого этого права лишаете:
[user]$ chmod <категория><действие><набор_прав> < файл >
категория управления доступом
действие:
Набор прав:
Вот несколько примеров использования команды chmod:
[user]$ chmod a+x file_name
предоставляет всем пользователям системы право на выполнение данного файла.
[user]$ chmod go-rw file_name
удаляет право на чтение и запись для всех, кроме владельца файла.
[user]$ chmod ugo+rwx file_name
дает всем права на чтение, запись и выполнение.
Если опустить указание на то, кому предоставляется данное право, то подразумевается, что речь идет вообще обо всех пользователях, т. е. вместо [user]$ chmod a+x file_name
можно записать просто
[user]$ chmod +x file_name
Второй вариант задания команды chmod (он используется чаще) основан на цифровом представлении прав. Для этого мы кодируем символ r цифрой 4, символ w — цифрой 2, а символ x — цифрой 1. Для того, чтобы предоставить пользователям какой-то набор прав, надо сложить соответствующие цифры. Получив, таким образом, нужные цифровые значения для владельца файла, для группы файла и для всех остальных пользователей, задаем эти три цифры в качестве аргумента команды chmod (ставим эти цифры после имени команды перед вторым аргументом, который задает имя файла). Например, если надо дать все права владельцу (4+2+1=7), право на чтение и запись — группе (4+2=6), и не давать никаких прав остальным, то следует дать такую команду:
[user]$ chmod 760 file_name
Если вы знакомы с двоичным кодированием восьмеричных цифр, то вы поймете, что цифры после имени команды в этой форме ее представления есть не что иное, как восьмеричная запись тех самых 9 бит, которые задают права для владельца файла, группы файла и для всех пользователей.
Выполнять смену прав доступа к файлу с помощью команды chmod может только сам владелец файла или суперпользователь. Для того, чтобы иметь возможность изменить права группы, владелец должен дополнительно быть членом той группы, которой он хочет дать права на данный файл.
Чтобы завершить рассказ о правах доступа к файлам, надо рассказать еще о трех возможных атрибутах файла, устанавливаемых с помощью той же команды chmod. Это те самые атрибуты для исполняемых файлов, которые в индексном дескрипторе файла в двухбайтовой структуре, определяющей права на файл, занимают позиции 5-7, сразу после кода типа файла.
Первый из этих атрибутов — так называемый «бит смены идентификатора пользователя». Смысл этого бита состоит в следующем.
Обычно, когда пользователь запускает некоторую программу на выполнение, эта программа получает те же права доступа к файлам и каталогам, которые имеет пользователь, запустивший программу. Если же установлен «бит смены идентификатора пользователя», то программа получит права доступа к файлам и каталогам, которые имеет владелец файла программы (таким образом, рассматриваемый атрибут лучше называть «битом смены идентификатора владельца»). Это позволяет решать некоторые задачи, которые иначе было бы трудно выполнить. Самый характерный пример — команда смены пароля passwd. Все пароли пользователей хранятся в файле /etc/passwd, владельцем которого является суперпользователь root. Поэтому программы, запущенные обычными пользователями, в том числе команда passwd, не могут производить запись в этот файл. А, значит, пользователь как бы не может менять свой собственный пароль. Но для файла /usr/bin/passwd установлен «бит смены идентификатора владельца», каковым является пользователь root. Следовательно, программа смены пароля passwd запускается с правами root и получает право записи в файл /etc/passwd (уже средствами самой программы обеспечивается то, что пользователь может изменить только одну строку в этом файле).
Установить «бит смены идентификатора владельца» может суперпользователь с помощью команды
[root]# chmod +s file_name
Аналогичным образом работает «бит смены идентификатора группы».
ls -l `which su` -rwsr-xr-x 1 root root 22924 May 4 2005 /bin/su
Биты «х» сообщают, что любой пользователь может запустить эту программу, а бит «s» — о том, что во время ее выполнения он будет пользоваться правами суперпользователя root (если, конечно, знает пароль).
Обратите внимание на применение обратных апострофов: они нужны для того, чтобы направить вывод команды which на вход команды Is.Следует учитывать, что программы, требующие установления SUID (или SGID) для своей работы, являются потенциальными дырами в системе безопасности. Представьте такую ситуацию: у вас в системе установлена программа superformat, которая предназначена для форматирования дисков. Создание файловой системы, пусть даже на дискете, — это привилегированная операция, требующая полномочий суперпользователя. При установке этой программы для нее сразу устанавливается право SUID, чтобы разрешить пользователям форматировать дискеты. Пользователь запускает ее для форматирования дискеты. Программа запускается, получает права root, форматирует дискету и нормально завершает работу.
Еще один возможный атрибут исполняемого файла — это «бит сохранения задачи» или «sticky bit» (дословно — «бит прилипчивости»).
[root]# chmod +t /dir
Если используется цифровой вариант задания атрибутов в команде chmod, то цифровое значение этих атрибутов должно предшествовать цифрам, задающим права пользователя:
[root]# chmod 4775 file_name
При этом веса этих битов для получения нужного суммарного результата задаются следующим образом:
Если какие-то из этих трех битов установлены в 1, то несколько изменяется вывод команды ls -l в части отображения установленных атрибутов прав доступа. Если установлен в 1 «бит смены идентификатора пользователя», то символ «x» в группе, определяющей права владельца файла, заменяется символом «s». Причем, если владелец имеет право на выполнение файла, то символ «x» заменяется на маленькое «s», а если владелец не имеет права на выполнение файла (например, файл вообще не исполняемый), то вместо «x» ставится «S». Аналогичные замены имеют место при задании «бита смены идентификатора группы», но заменяется символ «x» в группе атрибутов, задающих права группы. Если равен 1 «бит сохранения задачи (sticky bit)», то заменяется символ «x» в группе атрибутов, определяющей права для всех остальных пользователей, причем «x» заменяется символом «t», если все пользователи могут запускать файл на выполнение, и символом «T», если они такого права не имеют.
Таким образом, хотя в выводе команды ls -l не предусмотрено отдельных позиций для отображения значений битов смены идентификаторов и бита сохранения задачи, соответствующая информация выводится. Вот небольшой пример того, как это будет выглядеть:
[root]# ls -l prim1 -rwSrwsrwT 1 kos root 12 Dec 18 23:17 prim1
Команда chattr (действует для ext2, ext3, xfs) позволяет изменять параметры ФС для отдельного файла или директории:
Работает аналогично символьному варианту chmod с использованием +, - и =
Пример:
chattr -R +i /bin /sbin /usr/bin /usr/sbin - запрещаем изменение бинарников chattr +a /var/log/secure - предотвращаем модификацию лога злоумышленником
Для просмотра расширенных атрибутов используется утилита lsattr. Для использования атрибутов ext нужно монтировать с опцией user_xattr, для reiserfs опция attrs, а для xfs опций не нужно, она всегда использует xattr. Опция 'j' только для ext3. Опции 'j', 'a' и 'i' может устанавливать только root.