Именованные каналы для двунаправленного межпроцессного обмена нетипизированными данными между двумя Windows-машинами, страница 5

RPC –удаленный вызов процедур

               Одним из способов разработки распределенных приложений является неявное сетевое программирование. Оно осуществляется посредством удаленного вызова процедур. RPC обеспечивает двунаправленный межпроцессный обмен нетипизированными данными между двумя машинами, работающими под управлением любых ОС, поддерживающих RPС.

               Приложение кодируется с использованием тех же вызовов, что и обычное несетевое, но клиент и сервер могут находиться на разных узлах. То, что клиент и сервер находятся на разных узлах и для связи используется сетевое взаимодействие (организация связи идет по именованным каналам), большей частью остается скрыто от программиста. Одним из критериев оценки качества пакета RPC является именно скрытость лежащего в основе интерфейса сети. 

               Связь с отдельным ЕХЕ-компонентом через СОМ сложнее, чем связь с DLL-компонентом. ЕХЕ-компонент находится в другом процессе или даже на другом компьютере. Но не волнуйтесь. Пишите программы так, будто всегда существует прямая связь. О деталях позаботится СОМ посредством своей удаленной архитектуры, которая включает в себя вызов отдаленных процедур (Remote Procedure Calls, RPC).

               В RPC клиент обращается с вызовами к особой DLL, называемой заместителем (proxy). Заместитель передает поток данных так называемой заглушке (stub), которая представляет собой DLL в процессе компонента. Когда клиент вызывает функцию компонента, заместитель уведомляет об этом заглушку, посылая программе компонента сообщение, которое обрабатывается в ней скрытым окном. Механизм преобразования параметров в поток данных и обратно называется маршалингом (marshaling).  

               При использовании стандартных интерфейсов (т.е. тех, которые разработаны самой Microsoft) – таких, как IClassFactory и IPersist, - код заместителя и заглушки, реализующий маршалинг, находятся в библиотеке OLE32.DLL. Если же вы сами разрабатываете собственные интерфейсы, то писать коды заместителя и заглушки придется самостоятельно. Теперь для построения этого кода достаточно определить интерфейсы на специальном языке определения интерфейсов (Interface Definition Language, IDL) и скомпилировать код, создаваемый компилятором MIDL (Microsoft Interface Definition Language).

               COM играет важную роль во взаимодействии между клиентом и компонентом. СОМ поддерживает в памяти список фабрик классов, находящихся в активных ЕХЕ-компонентах, но не следит за отдельными СОМ-объектами. Такие объекты сами заботятся о своем уничтожении через механизм AddRef/Release. СОМ также участвует в завершении клиента. Если клиент использует ЕХЕ-сервер, то СОМ прослушивает коммуникационный канал связи клиента с сервером, отслеживая счетчик ссылок на каждый объект. При завершении клиента СОМ отключается от объектов компонента, что в определенных условиях вызывает их освобождение. Но не полагайтесь на это. Перед завершением обязательно убедитесь, что ваша клиентская программа освобождает все указатели на интерфейсы.   

  1. Описание функции на языке IDL mrpc.idl

 Его структура:

       [

uuid(f641fe49-1403-4be4-acf1-db4f5867da00),

pointer_default(unique),

version(1.0)

]

interface rpc

{

typedef [string,unique] char * str;

void MyFunc(

[in,out] str szString,

[in] unsigned long Count);

}

Файл mrpc.acf   (настройки)

[implicit_handle (handle_t global_rpc_handle)]

interface rpc

{

}

Далее компилируем эти файлы:

       Midl.exe  -cpp_cmd  cl  mrpc.idl

В результате получаем 3 файла:

  1. заголовочный файл – mrpc.h
  2. файл на языке С для клиента – mrpc_с.с
  3. файл на языке С для сервера_s.c
  4. Создание сервера

Настройки:

       Project->AddFilestoProject->

                                                                                 Mrpc_s.c

                                                                                 Mrpc.h

       Файлы на чистом С, поэтому отключаем:

       ProjectSetting->C/C++->Precompiled headers указываем

                                                                  Not Using precompiled headers

Для линковки:

ProjectSetting->Link->object/Library добавляем rpcrt4.lib и edkutils.lib