Вопросы безопасности

Предыдущая  Содержание  Следующая V*D*V

Безопасность - всё более и более важная проблема в наше время. Мы обсудим связанные с безопасностью проблемы, поскольку они встречаются в книге повсюду. Однако, есть несколько общих понятий, которые заслуживают внимания сейчас. Любая проверка безопасности в системе выполняется кодом ядра. Если у ядра есть бреши в защите, то и у системы в целом есть бреши. В официально распространяемом ядре только авторизованный пользователь может загрузить модуль в ядро; системный вызов init_module проверяет, разрешено ли вызывающему процессу загрузить модуль в ядро. Таким образом, когда работает официальное ядро, только суперпользователь (* Технически, только кто-то с разрешением CAP_SYS_MODULE может выполнить эту операцию. Мы обсуждаем разрешения в Главе 6.), или злоумышленник, который смог получить эту привилегию, может использовать мощность привилегированного кода. Когда возможно, авторы драйверов должны избегать реализации политики безопасности в своем коде. Безопасность - результат ограничений, которые часто лучше всего обрабатываются на более высоких уровнях ядра, под управлением системного администратора. Однако, всегда есть исключения.

 

Как автор драйвера устройства, вы должны знать о ситуациях, в которых некоторые способы доступа к устройству могли бы неблагоприятно затронуть систему в целом и должны обеспечить адекватный контроль. Например, операции устройства, которые затрагивают глобальные ресурсы (такие как установка линии прерывания), которые могут повредить аппаратные средства (загрузку встроенного программного обеспечения, например), или могли бы затронуть других пользователей (таких как установка заданного по умолчанию размера блока на ленточном накопителе), обычно доступны только для достаточно привилегированных пользователей, и эта проверка должна быть осуществлена в драйвере непосредственно.

 

Конечно, авторы драйверов должны также быть внимательными, чтобы избежать внедрения ошибок безопасности. Язык программирования Си позволяет легко делать некоторые типы ошибок. Много текущих проблем безопасности созданы, например, ошибками переполнения буфера, когда программист забывает проверять, сколько данных записано в буфер, и данные продолжают записываться после окончания буфера, поверх совершенно других данных. Такие ошибки могут поставить под угрозу всю систему и их надо избегать. К счастью, обычно относительно просто избежать этих ошибок в контексте драйвера устройства, в котором интерфейс для пользователя чётко определен и строго контролируем.

 

Стоит иметь в виду и некоторые другие общие идеи безопасности. Любые данные, полученные от пользовательских процессов, должны быть обработаны с большим подозрением; никогда не доверяйте им, пока они не проверены. Будьте внимательны с неинициализированной памятью; любая память, полученная от ядра, должна быть обнулена или проинициализирована другим способом прежде, чем стать доступной пользовательскому процессу или устройству. Иначе, результатом может быть утечка информации (раскрытие данных, паролей и так далее). Если ваше устройство обрабатывает данные, посланные в него, убедитесь, что пользователь не может послать ничего, что могло бы поставить под угрозу систему. Наконец, думайте о возможном эффекте операций устройства; если есть определённые операции (например, перезагрузка встроенного программного обеспечения на плате адаптера или форматирование диска), которые могли бы затронуть систему, эти операции должны почти наверняка быть разрешены только привилегированным пользователям.

 

Будьте внимательны также, получая программное обеспечение от третьих лиц, особенно когда затрагивается ядро: потому что любой имеет доступ к исходному тексту, любой может сломать и перекомпилировать части. Хотя вы можете обычно доверять предварительно откомпилированным ядрам в ваших дистрибутивах, вы должны избегать запуска ядра, откомпилированного незнакомыми людьми - если вы избегаете запуска предварительно откомпилированного ядра как root, тогда вам лучше не запускать откомпилированное ядро. Например, злонамеренно изменённое ядро могло бы позволить любому загружать модуль, открывая таким образом неожиданную лазейку через init_module. Заметьте, что ядро Linux может быть откомпилировано так, чтобы вообще не поддерживать модули, закрывая таким образом любые связанные с модулем бреши в защите. Конечно, в этом случае все необходимые драйверы должны быть встроены непосредственно в само ядро. Отключение загрузки модулей ядра после начальной загрузки системы через соответствующий механизм стало возможно для версий, начиная с 2.2.

Предыдущая  Содержание  Следующая