Главная » Java » Класс AccessController и привилегированные операции

0

 

Класс AccessController имеет три области применений:

 

* поддерживает базовую  версию  метода  checkPermission,   используемую

менеджерами безопасности для выполнения проверки полномочий;

 

* обеспечивает средства создания моментального снимка (snapshot) текуще

го контекста с помощью метода getContext, который возвращает объект

AccessControlContext;

 

* предлагает     инструменты     выполнения     кода     на     привилегированном

(privileged) уровне, что позволяет изменить или отменить полностью набор

разрешений, которыми код обладает изначально.

 

Два первых вопроса мы уже вкратце обсуждали (в тех пределах и с такой степенью Полноты, насколько это уместно и целесообразно в данном случае). В этом разделе Мы остановим внимание на том, что означает привилегированное выполнение кода.

  Домен защиты (protection domain), представляемый объектом Java, security. ProtectionDomain, заключает в себе источник кода (code source)    (объект    Java, security. CodeSource)    и    множество    разрешений (permissions), которые предоставлены коду, происходящему из этого источника, как это определено текущей политикой безопасности (security policy). Источник кода расширяет понятие базы кода (code base) — местоположения классов, откуда они загружаются, — за счет включения в набор данных информации о цифровом сертификате (digital certificate) для каждого из этих классов. Цифровой сертификат может применяться для выяснения аутентичности файла и подтверждения того, что файл не был искажен каким бы то ни было образом. Классы, обладающие однородными сертификатами и происходящие из общего источника, образуют единый домен защиты, и каждый класс может принадлежать одному и только одному домену. Классы же, которые имеют одинаковые наборы разрешений, но относятся к различным источникам, принадлежат разным доменам.

   Каждый аплет (applet) или приложение работает в контексте соответствующего домена, определяемого источником кода. Чтобы позволить аплету (или приложению, работающему под управлением менеджера безопасности) выполнить определенную операцию, предполагающую контроль полномочий, следует снабдить аплет (приложение) соответствующим разрешением. Другими словами, при любой попытке выполнения потенциально опасной операции весь код, выполняемый текущим потоком вычислений до момента обращения к этой опера-ции, должен обладать правом на ее осуществление — если только некоторая часть кода потока не была помечена как привилегированная. Предположим, например, что механизм контроля доступа применяется к потоку вычислений, который выглядит как цепочка вызовов методов, — представьте, что один метод обращается к другому, оттуда вызывается третий и т.д., и это в общем случае способно привести к пересечению границ доменов защиты. Когда метод checkPermission объекта AccessController вызывается самым последним инициатором в цепочке, решение о том, следует ли позволить выполнение операции либо запретить ее, принимается в соответствии с базовым алгоритмом, который выглядит так:

 

"Если любой код-инициатор в цепочке вызовов не обладает соответствующим разрешением, выбрасывается исключение типа AccessControlException — если только этот код не помечен как привилегированный и все остальные фрагменты кода, вызываемые им непосредственно или косвенно, не располагают требуемым разрешением".

 

   Используя признак привилегированности, вы позволяете фрагменту кода, заслуживающему доверия, получить временный доступ к большему набору операций, нежели тот, который непосредственно доступен для кода-инициатора. Такой механизм удобен и полезен в нескольких ситуациях. Приложению, например, может быть не позволено напрямую обращаться к файлам шрифтов, но системный код, отображающий документ, который создан этим приложением, должен иметь право на получение необходимых шрифтов — прежде всего, в благо самого приложения. Чтобы достичь подобной цели, системный код на время загрузки шрифтов приобретает статус привилегированного.

   Статический метод  doPrivileged  класса AccessController  принимает качестве аргумента объект Java.security.PrivilegedAction, метод run которого определяет код, подлежащий выполнению на привилегированном уровне. Вызов doPrivi leged может быть осуществлен следующим образом:

 

void someMethod() {

// … Обычный код …

AccessController.doprivi1eged(new PrivilegedAction() {

      public Object run() {

// Пример привилегированного кода

 System.loadLibrary("awt");

return null;      // возвращать нечего }

   }

  }); // … Обычный код …

}

Метод doPrivileged позволяет коду метода run работать в привилегированном режиме. Привилегированное выполнение — это инструмент, посредством которого класс, обладающий определенным разрешением, может на время передать это разрешение потоку, призванному выполнить привилегированный код. При этом коду не удастся приобрести те разрешения, которыми он не обладал прежде. Класс, в котором объявлен метод someMethod нашего примера, должен иметь разрешение RuntimePermission("loadl_ibrary.awt"). поскольку в противном случае любой поток, вызвавший someMethod, получит исключение Securi tyException. После завершения кода метода run объекта Pri vi legedAction все выданные привилегии гарантированно аннулируются.

   PrivilegedAction — это интерфейс, в котором объявлен единственный метод run, возвращающий значение типа Object. Другой вариант метода doPrivi leged принимает в качестве аргумента объект типа PrivilegedExceptionAction, который также обладает методом run, возвращающим Object, но способным выбрасывать любое объявленное исключение. Для обоих вариантов методов doPrivi leged существуют перегруженные формы, предусматривающие возможность задания объекта класса AccessControl Context в качестве второго аргумента — тот определяет контекст и устанавливает разрешения, в рамках которых должен выполняться метод run.

  Обращаться к методу doPrivileged следует с особой осторожностью, убедившись, что фрагменты привилегированного кода настолько длинны, насколько это необходимо, и выполняют только те действия, которые вы в состоянии контролировать всецело. Например, решение о предоставлении прав на выполнение всех операций ввода-вывода методу, принимающему аргумент типа Runnable и осуществляющему вызов метода run последнего внутри привилегированного фрагмента кода, было бы крайне неосмотрительным.

Источник: Арнолд, Кен, Гослинг, Джеймс, Холмс, Дэвид. Язык программирования Java. 3-е изд .. : Пер. с англ. – М. : Издательский дом «Вильяме», 2001. – 624 с. : ил. – Парал. тит. англ.

По теме:

  • Комментарии