Программирование для Windows NT (том 2)

       

Функция CreateNamedPipe


Для создания именованного канала Pipe вы должны использовать функцию CreateNamedPipe. Вот прототип этой функции:

HANDLE CreateNamedPipe(

  LPCTSTR lpName,          // адрес строки имени канала

  DWORD   dwOpenMode,      // режим открытия канала

  DWORD   dwPipeMode,      // режим работы канала

  DWORD   nMaxInstances,   // максимальное количество

                           // реализаций канала

  DWORD   nOutBufferSize,  // размер выходного буфера в байтах

  DWORD   nInBufferSize,   // размер входного буфера в байтах

  DWORD   nDefaultTimeOut, // время ожидания в миллисекундах

  LPSECURITY_ATTRIBUTES lpSecurityAttributes); // адрес

                           // переменной для атрибутов защиты

Через параметр lpName передается адрес строки имени канала в форме \\.\pipe\ИмяКанала (напомним, что при создании канала имя сервера не указывается, так как канал можно создать только на той рабочей станции, где запущен процесс, создающий канал).

Параметр dwOpenMode задает режим, в котором открывается канал. Остановимся на этом параметре подробнее.

Канал Pipe может быть ориентирован либо на передачу потока байт, либо на передачу сообщений. В первом случае данные через канал передаются по байтам, во втором - отдельными блоками заданной длины.

Режим работы канала (ориентированный на передачу байт или сообщений) задается, соответственно, константами PIPE_TYPE_BYTE или PIPE_TYPE_MESSAGE, которые указываются в параметре dwOpenMode. По умолчанию используется режим PIPE_TYPE_BYTE.



Помимо способа передачи данных через канал, с помощью параметра dwOpenMode можно указать, будет ли данный канал использован только для чтения данных, только для записи или одновременно для чтения и записи. Способ использования канала задается указанием одной из следующих констант:

Константа

Использование канала

PIPE_ACCESS_INBOUND

Только для чтения

PIPE_ACCESS_OUTBOUND

Только для записи

PIPE_ACCESS_DUPLEX

Для чтения и записи

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

Константа

Использование канала

PIPE_READMODE_BYTE

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

PIPE_READMODE_MESSAGE

Канал открывается на чтение в режиме передачи отдельных сообщений указанной длины

PIPE_WAIT

Канал будет работать в блокирующем режиме, когда процесс переводится в состояние ожидания до завершения операций в канале

PIPE_NOWAIT

Неблокирующий режим работы канала. Если операция не может быть выполнена немедленно, в неблокирующем режиме функция завершается с ошибкой

FILE_FLAG_OVERLAPPED

Использование асинхронных операций (ввод и вывод с перекрытием). Данный режим позволяет процессу выполнять полезную работу параллельно с проведением операций в канале

FILE_FLAG_WRITE_THROUGH

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

<
Дополнительно к перечисленным выше флагам, через параметр dwOpenMode можно передавать следующие флаги защиты:

Флаг

Описание

WRITE_DAC

Вызывающий процесс должен иметь права доступа на запись к произвольному управляющему списку доступа именованного канала access control list (ACL)

WRITE_OWNER

Вызывающий процесс должен иметь права доступа на запись к процессу, владеющему именованным каналом Pipe

ACCESS_SYSTEM_SECURITY

Вызывающий процесс должен иметь права доступа на запись к управляющему списку доступа именованного канала access control list (ACL)

Подробное описание этих флагов выходит за рамки нашей книги. При необходимости обратитесь к документации, входящей в состав SDK.

Теперь перейдем к параметру dwPipeMode, определяющему режим работы канала. В этом параметре вы можете указать перечисленные выше константы PIPE_TYPE_BYTE, PIPE_TYPE_MESSAGE, PIPE_READMODE_BYTE, PIPE_READMODE_MESSAGE, PIPE_WAIT и PIPE_NOWAIT. Для всех реализаций канала необходимо указывать один и тот же набор констант.

Параметр nMaxInstances определяет максимальное количество реализаций, которые могут быть созданы для канала. Вы можете указывать здесь значения от 1 до PIPE_UNLIMITED_INSTANCES. В последнем случае максимальное количество реализаций ограничивается только наличием свободных системных ресурсов.

Заметим, что если один серверный процесс использует несколько реализаций канала для связи с несколькими клиенсткими, то общее количество реализаций может быть меньше, чем потенциальное максимальное количество клиентов. Это связано с тем, что клиенты могут использовать реализации по очереди, если только они не пожелают связаться с серверным процессом все одновременно.

Параметры nOutBufferSize и nInBufferSize определяют, соответственно, размер буферов, используемых для записи в канал и чтения из канала. При необходимости система может использовать буферы других, по сравнению с указанными, размеров.

Параметр nDefaultTimeOut определяет время ожидания для реализации канала. Для всех реализаций необходимо указывать одинаковое значение этого параметра.

Через параметр lpPipeAttributes передается адрес переменной, содержащей атрибуты защиты для создаваемого канала. В наших приложениях мы будем указывать этот параметр как NULL. В результате канал будет иметь атрибуты защиты, принятые по умолчанию.

В случае успеха функция CreateNamedPipe возвращает идентификатор созданной реализации канала, который можно использовать в операциях чтения и записи, выполняемых с помощью таких функций, как ReadFile и WriteFile.

При ошибке функция CreateNamedPipe возвращает значение INVALID_HANDLE_VALUE. Код ошибки вы можете уточнить, вызвав функцию GetLastError.


Содержание раздела