Сущность технологии COM




Контроль доступа - часть 6


Имея эту функцию, приложение может связать вновь созданный объект контроля доступа с его процессом следующим образом:

IAccessControl *pac = 0; HRESULT hr = CreateAccessControl(pac); assert(SUCCEEDED(hr)); hr = CoInitializeSecurity(pac, -1, 0, 0, RPC_C_AUTHN_LEVEL_PKT, RPC_C_IMP_LEVEL_IDENTIFY, 0, EOAC_ACCESS_CONTROL, // use IAccessControl // используем IAccessControl 0);

assert(SUCCEEDED(hr)); pac->Release(); // COM holds reference until last CoUninitialize // COM сохраняет ссылку до последнего CoUninitialize

Флаг EOAC_ACCESS_CONTROL показывает, что первый параметр в функции СоInitializeSecurity является указателем на интерфейс IAccessControl, а не указателем на SECURITY_DESCRIPTOR NT. При каждом поступающем запросе на связь COM будет использовать метод этого объекта IsAccessAllowed для определения того, разрешен или запрещен доступ к объектам процесса. Отметим, что хотя этот код должен исполняться до первого интересного вызова COM, вызов CoCreateInstance для получения реализации по умолчанию IAccessControl является допустимым, так как COM не рассматривает его как интересный.

Если список авторизованных пользователей не может быть известен во время запуска процесса, то можно зарегистрировать специальную (custom) реализацию IAccessControl, которая выполняет определенного рода проверку доступа во время выполнения в своей реализации метода IsAccessAllowed. Поскольку сама COM использует только метод IsAccessAllowed, то такая специальная реализация могла бы безошибочно возвращать E_NOTIMPL для всех других методов IAccessControl. Ниже приведена простая реализация IAccessControl, позволяющая получить доступ к объектам процесса только пользователям с символом "x" в именах своих учетных записей:

class XOnly : public IAccessControl { // Unknown methods // методы IUnknown STDMETHODIMP QueryInterface(REFIID riid, void **ppv) { if (riid == IID_IAccessControl riid == IID_IUnknown) *ppv = static_cast<IAccessControl*>(this); else return (*ppv = 0), E_NOINTERFACE; ((IUnknown*)*ppv)->AddRef(); return S_OK; }




Содержание  Назад  Вперед