Сведения о функциях API приведены в таблице ниже.
Динамическое создание IPC-канала на стороне сервера
Динамическое создание IPC-канала на стороне сервера включает следующие шаги:
DCM
вызовом функции DcmInit()
.DCM
, используя функцию DcmPublishEndpoint()
.В параметре serverHandle
функции DcmPublishEndpoint()
нужно указать дескриптор, идентифицирующий сервер. В качестве дескриптора, идентифицирующего сервер, можно использовать дескриптор этого серверного процесса, полученный последовательностью вызовов функций KosTaskGetSelf()
и KosTaskGetHandle()
из API task.h, или дескриптор, созданный вызовом функции KnHandleCreateUserObject()
из API handle_api.h. (При вызове функции KnHandleCreateUserObject()
в параметре rights
должны быть указаны флаги OCAP_HANDLE_TRANSFER
и OCAP_HANDLE_GET_SID
.) Можно опубликовать несколько служб, указывая один и тот же или разные дескрипторы, идентифицирующие сервер. (Клиенты могут получить потомков этих дескрипторов через опциональный параметр outServerHandle
функции DcmReadPubQueue()
.) После публикации служб дескриптор, идентифицирующий сервер, можно закрыть.
В результате вызова функции DcmPublishEndpoint()
создается DCM-дескриптор, позволяющий получать запросы клиентов на создание IPC-каналов для использования заданной службы с заданным интерфейсом.
Чтобы отменить публикацию службы, нужно вызовом функции DcmCloseHandle()
закрыть DCM-дескриптор, созданный при ее публикации. Также публикация всех опубликованных служб сервера будет отменена, если сервер завершится.
DcmListen()
.Вызовы функции DcmListen()
с одним и тем же DCM-дескриптором в параметре pubHandle
позволяют получить только те запросы клиентов, которые направлены на создание IPC-каналов для использования той службы с тем интерфейсом, которые были заданы при создании этого DCM-дескриптора на шаге 2.
Через опциональные параметры outClientHandle
и outClientName
функции DcmListen()
можно получить дескриптор, идентифицирующий клиента, и имя клиента соответственно. (Дескриптор, идентифицирующий клиента, является потомком дескриптора, указанного в параметре clientHandle
функции DcmCreateConnection()
, вызванной на стороне клиента.) Эти данные можно использовать, чтобы принять решение о принятии или отклонении запроса клиента. При этом дескриптор, идентифицирующий клиента, может быть использован, например, для получения сведений о клиенте от других процессов или для получения SID по этому дескриптору для сравнения с другими имеющимся у сервера дескрипторами, идентифицирующими клиентов. После принятия решения можно закрыть дескриптор, идентифицирующий клиента.
В результате вызова функции DcmListen()
создается DCM-дескриптор, позволяющий принять или отклонить запрос клиента на создание IPC-канала.
DcmAccept()
.В параметре connectionId
функции DcmAccept()
нужно указать DCM-дескриптор, полученный на шаге 3.
В параметре sessionHandle
функции DcmAccept()
нужно указать callable-дескриптор для передачи клиенту. Чтобы создать callable-дескриптор, нужно вызвать функцию KnHandleCreateUserObjectEx()
из API handle_api.h. (При вызове функции KnHandleCreateUserObjectEx()
в параметре rights
должны быть указаны флаги OCAP_IPC_CALL
и OCAP_HANDLE_TRANSFER
, а в параметрах ipcChannel
и riid
требуется указать серверный IPC-дескриптор создаваемого IPC-канала и идентификатор службы (RIID) соответственно. Серверный IPC-дескриптор используется для инициализации IPC-транспорта и управления обработкой IPC-запросов на стороне сервера. Для создания серверного дескриптора можно использовать функцию KnHandleCreateListener()
из API handle_api.h. Идентификатор службы является константой в автоматически генерируемом транспортном коде, например, FsDriver_operationsComp_fileOperations_iid
.) После принятия запроса клиента callable-дескриптор можно закрыть.
Передачу callable-дескриптора клиенту можно ассоциировать с объектом контекста передачи ресурса, указав дескриптор этого объекта в параметре badgeHandle
функции DcmAccept()
. Это позволит, используя API notice_api.h, отследить, когда будут закрыты или отозваны потомки callable-дескриптора, которые образуют поддерево наследования дескрипторов, корневой узел которого порожден передачей клиенту этого callable-дескриптора. (Переданный callable-дескриптор может быть закрыт клиентом, но также закрытие этого дескриптора выполняется в результате завершения клиента.) Чтобы создать объект контекста передачи ресурса, нужно вызвать функцию KnHandleCreateBadge()
из API handle_api.h.
Через параметр context
функций KnHandleCreateUserObjectEx()
и KnHandleCreateBadge()
можно задать данные для ассоциации с callable-дескриптором и передачей callable-дескриптора соответственно (аналогично контексту пользовательского ресурса и контексту передачи ресурса). Сервер сможет получить указатель на эти данные при разыменовании callable-дескриптора. (Несмотря на то что callable-дескриптор является IPC-дескриптором, он помещается ядром в поле base_.self
фиксированной части IPC-запроса.)
Один и тот же callable-дескриптор можно использовать, чтобы принять несколько запросов одного или нескольких клиентов.
Чтобы отклонить запрос клиента на создание IPC-канала, нужно вызовом функции DcmCloseHandle()
закрыть DCM-дескриптор, полученный на шаге 3. (При этом вызов функции DcmConnect()
на стороне клиента завершится с ошибкой rcNotConnected
.) В случае принятия запроса клиента DCM-дескриптор, полученный на шаге 3, нужно также закрыть, но после вызова функции DcmAccept()
.
Динамическое создание IPC-канала на стороне клиента
Динамическое создание IPC-канала на стороне клиента включает следующие шаги:
DCM
вызовом функции DcmInit()
.Чтобы выполнить этот шаг, нужно вызвать функцию DcmSetSubscription()
.
Опциональные параметры endpointName
, serverName
и serverHandle
функции DcmSetSubscription()
нужно использовать, чтобы включить фильтрацию уведомлений по квалифицированному имени службы, имени сервера и дескриптору, идентифицирующему сервер, соответственно. (Дескриптор, идентифицирующий сервер, является потомком дескриптора, указанного в параметре serverHandle
функции DcmPublishEndpoint()
, вызванной на стороне сервера. Клиент может получить этот дескриптор, например, от другого процесса.)
В результате вызова функции DcmSetSubscription()
создается DCM-дескриптор, позволяющий получать уведомления о публикации и отмене публикации служб с заданным интерфейсом. При этом формируется очередь уведомлений о публикации служб, которые были опубликованы до вызова DcmSetSubscription()
и соответствуют критериям фильтрации. Если больше не требуется получать уведомления о публикации и отмене публикации служб с заданным интерфейсом, то этот DCM-дескриптор нужно закрыть вызовом функции DcmCloseHandle()
.
DcmReadPubQueue()
.В параметре subscrHandle
функции DcmReadPubQueue()
нужно указать DCM-дескриптор, полученный на шаге 2.
Через опциональные параметры outServerHandle
, outServerName
и outEndpointName
функции DcmReadPubQueue()
можно получить дескриптор, идентифицирующий сервер, имя сервера и квалифицированное имя службы соответственно. (Дескриптор, идентифицирующий сервер, является потомком дескриптора, указанного в параметре serverHandle
функции DcmPublishEndpoint()
, вызванной на стороне сервера.) Эти данные можно использовать, чтобы принять решение о выполнении запроса на создание IPC-канала с сервером. При этом дескриптор, идентифицирующий сервер, может быть использован, например, для получения сведений о сервере от других процессов или для получения SID по этому дескриптору для сравнения с другими имеющимися у клиента дескрипторами, идентифицирующими серверы.
Значение, полученное через параметр outPubStatus
функции DcmReadPubQueue()
, отражает, что служба опубликована, или публикация службы отменена. Уведомление об отмене публикации службы появляется, если сервер отменил публикацию этой службы, а также при завершении сервера.
Чтобы выполнить этот шаг, нужно вызвать функцию DcmCreateConnection()
.
В параметре serverHandle
функции DcmCreateConnection()
нужно указать дескриптор, идентифицирующий сервер. Этот дескриптор может быть получен на шаге 3 через параметр outServerHandle
функции DcmReadPubQueue()
или другим способом (например, от другого процесса).
В параметре clientHandle
функции DcmCreateConnection()
нужно указать дескриптор, идентифицирующий клиента. В качестве дескриптора, идентифицирующего клиента, можно использовать дескриптор этого клиентского процесса, полученный последовательностью вызовов функций KosTaskGetSelf()
и KosTaskGetHandle()
из API task.h, или дескриптор, созданный вызовом функции KnHandleCreateUserObject()
из API handle_api.h. (При вызове функции KnHandleCreateUserObject()
в параметре rights
должны быть указаны флаги OCAP_HANDLE_TRANSFER
и OCAP_HANDLE_GET_SID
.) Можно создать несколько DCM-дескрипторов, позволяющих выполнить запрос на создание IPC-канала, указывая в параметре clientHandle
функции DcmCreateConnection()
один и тот же или разные дескрипторы, идентифицирующие клиента. (Серверы могут получить потомков этих дескрипторов через опциональный параметр outClientHandle
функции DcmListen()
.) После создания DCM-дескриптора, позволяющего выполнить запрос на создание IPC-канала, дескриптор, идентифицирующий клиента, можно закрыть.
В результате вызова функции DcmCreateConnection()
создается DCM-дескриптор, позволяющий выполнить запрос на создание IPC-канала с сервером для использования заданной службы с заданным интерфейсом.
DcmConnect()
.В параметре connectionId
нужно указать DCM-дескриптор, полученный на шаге 4.
В результате вызова функции DcmConnect()
клиент получает через параметр outSessionHandle
callable-дескриптор. Клиент использует этот дескриптор для инициализации IPC-транспорта. При этом в функции инициализации прокси-объекта клиент указывает значение INVALID_RIID
в качестве идентификатор службы (RIID).
После получения callable-дескриптора DCM-дескриптор, полученный на шаге 4, нужно закрыть вызовом функции DcmCloseHandle()
.
Прерывание блокирующих вызовов функций
Чтобы прервать блокирующий вызов функции DcmConnect()
, DcmReadPubQueue()
или DcmListen()
из другого потока исполнения, нужно вызвать функцию DcmInterruptBlockingCall()
.
Использование уведомлений
Используя функции DcmSubscribeToEvents()
и DcmUnsubscribeFromEvents()
совместно с функциями из API notice_api.h, можно получать уведомления о том, что произошли следующие события: публикация или отмена публикации сервером службы в DCM
(флаг DCM_PUBLICATION_CHANGED
), получение сервером запроса от клиента на создание IPC-канала (флаг DCM_CLIENT_CONNECTED
), прерывание блокирующего вызова функции DcmConnect()
, DcmReadPubQueue()
или DcmListen()
(флаг DCM_BLOCKING_CALL_INTERRUPTED
), прием или отклонение сервером запроса клиента на создание IPC-канала (флаг DCM_CLIENT_RELEASED_BY_SERVER
). (Флаги маски событий и идентификатор записи вида "ресурс – маска событий" DCM_EVENT_ID
определены в заголовочном файле sysroot-*-kos/include/dcm/dcm_api.h
из состава KasperskyOS SDK.) Функции DcmSubscribeToEvents()
и DcmUnsubscribeFromEvents()
позволяют настроить приемник уведомлений, соответственно добавляя и удаляя отслеживаемые объекты, идентифицируемые DCM-дескрипторами.
Удаление динамически созданных IPC-каналов
Динамически созданный IPC-канал будет удален при закрытии callable-дескриптора и серверного IPC-дескриптора этого IPC-канала.
Удаление подключения к DCM
Если использовать DCM
больше не требуется, нужно вызвать функцию DcmFini()
, чтобы удалить подключение к DCM
и тем самым освободить связанные с этим подключением ресурсы.
Сведения о функциях API
Функции dcm_api.h
Функция |
Сведения о функции |
---|---|
|
Назначение Создает подключение к Параметры Нет. Возвращаемые значения В случае успеха возвращает Если IPC-канал до Дополнительные сведения Потокобезопасная функция. Неблокирующий вызов. |
|
Назначение Удаляет подключение к Параметры Нет. Возвращаемые значения Нет. Дополнительные сведения Потокобезопасная функция. Неблокирующий вызов. |
|
Назначение Настраивает приемник уведомлений, чтобы он получал уведомления о событиях, связанных с объектом, идентифицируемым заданным DCM-дескриптором. Параметры
Возвращаемые значения В случае успеха возвращает |
|
Назначение Настраивает приемник уведомлений, чтобы он не получал уведомления о событиях, связанных с объектом, идентифицируемым заданным DCM-дескриптором. Параметры
Возвращаемые значения В случае успеха возвращает |
|
Назначение Закрывает DCM-дескриптор, полученный вызовом функции Параметры
Возвращаемые значения В случае успеха возвращает |
|
Назначение Прерывает блокирующий вызов функции Параметры
Возвращаемые значения В случае успеха возвращает |
|
Назначение Создает DCM-дескриптор, позволяющий получать уведомления о публикации и отмене публикации служб с заданным интерфейсом. Параметры
Возвращаемые значения В случае успеха возвращает |
|
Назначение Извлекает уведомление о публикации или отмене публикации службы из очереди этих уведомлений. Параметры
Возвращаемые значения В случае успеха возвращает Если блокирующий вызов был прерван вызовом функции Дополнительные сведения Неблокирующий вызов, если в параметре |
|
Назначение Создает DCM-дескриптор, позволяющий выполнить запрос на создание IPC-канала с сервером для использования заданной службы с заданным интерфейсом. Параметры
Возвращаемые значения В случае успеха возвращает |
|
Назначение Выполняет запрос на создание IPC-канала с сервером. Параметры
Возвращаемые значения В случае успеха возвращает Если в параметре Если блокирующий вызов был прерван вызовом функции Дополнительные сведения Неблокирующий вызов, если в параметре |
|
Назначение Публикует службу в Параметры
Возвращаемые значения В случае успеха возвращает |
|
Назначение Позволяет получить запрос клиента на создание IPC-канала. Параметры
Возвращаемые значения В случае успеха возвращает Если блокирующий вызов был прерван вызовом функции Дополнительные сведения Неблокирующий вызов, если в параметре |
|
Назначение Принимает запрос клиента на создание IPC-канала. Параметры
Возвращаемые значения В случае успеха возвращает |