Named pipes.

Named pipes have several features that make them an appropriate mechanism for implementing IPC-based applications, including networked client/server systems. Named pipe features (some are optional) include the following: For more information read Named Pipes on MSDN.

CreateNamedPipe

The CreateNamedPipe function creates an instance of a named pipe and returns a handle for subsequent pipe operations. A named pipe server process uses this function either to create the first instance of a specific named pipe and establish its basic attributes or to create a new instance of an existing named pipe.
HANDLE CreateNamedPipe(
  LPCTSTR lpName,                             // pipe name
  DWORD dwOpenMode,                           // pipe open mode
  DWORD dwPipeMode,                           // pipe-specific modes
  DWORD nMaxInstances,                        // maximum number of instances
  DWORD nOutBufferSize,                       // output buffer size
  DWORD nInBufferSize,                        // input buffer size
  DWORD nDefaultTimeOut,                      // time-out interval
  LPSECURITY_ATTRIBUTES lpSecurityAttributes  // SD
);

Parameters lpName [in]
Pointer to the null-terminated string that uniquely identifies the pipe. The string must have the following form: \\.\pipe\pipename
The pipename part of the name can include any character other than a backslash, including numbers and special characters. The entire pipe name string can be up to 256 characters long. Pipe names are not case sensitive.
Windows 95/98/Me: The pipe name cannot include a colon.

dwOpenMode[in]
Specifies the pipe access mode, the overlapped mode, the write-through mode, and the security access mode of the pipe handle.
CreateNamedPipe fails if dwOpenMode specifies any flags other than those listed in the following tables.
This parameter must specify one of the following pipe access mode flags. The same mode must be specified for each instance of the pipe.
ModeDescription
PIPE_ACCESS_DUPLEX The pipe is bi-directional; both server and client processes can read from and write to the pipe. This mode gives the server the equivalent of GENERIC_READ | GENERIC_WRITE access to the pipe. The client can specify GENERIC_READ or GENERIC_WRITE, or both, when it connects to the pipe using the CreateFile function.
PIPE_ACCESS_INBOUND The flow of data in the pipe goes from client to server only. This mode gives the server the equivalent of GENERIC_READ access to the pipe. The client must specify GENERIC_WRITE access when connecting to the pipe.
PIPE_ACCESS_OUTBOUND The flow of data in the pipe goes from server to client only. This mode gives the server the equivalent of GENERIC_WRITE access to the pipe. The client must specify GENERIC_READ access when connecting to the pipe.
This parameter can also include either or both of the following flags, which enable write-through mode and overlapped mode. These modes can be different for different instances of the same pipe.
ModeDescription
FILE_FLAG_FIRST_PIPE_INSTANCE If this flag is set and the first instance of the named pipe it is called to create already exists, this function will fail and a named pipe instance will not be created. If this flag is not set, a new instance of the specified pipe will be created.
FILE_FLAG_WRITE_THROUGH Write-through mode is enabled. This mode affects only write operations on byte-type pipes and, then, only when the client and server processes are on different computers. If this mode is enabled, functions writing to a named pipe do not return until the data written is transmitted across the network and is in the pipe's buffer on the remote computer. If this mode is not enabled, the system enhances the efficiency of network operations by buffering data until a minimum number of bytes accumulate or until a maximum time elapses.
FILE_FLAG_OVERLAPPED Overlapped mode is enabled. If this mode is enabled, functions performing read, write, and connect operations that may take a significant time to be completed can return immediately. This mode enables the thread that started the operation to perform other operations while the time-consuming operation executes in the background. For example, in overlapped mode, a thread can handle simultaneous input and output (I/O) operations on multiple instances of a pipe or perform simultaneous read and write operations on the same pipe handle. If overlapped mode is not enabled, functions performing read, write, and connect operations on the pipe handle do not return until the operation is finished. The ReadFileEx and WriteFileEx functions can only be used with a pipe handle in overlapped mode. The ReadFile, WriteFile, ConnectNamedPipe, and TransactNamedPipe functions can execute either synchronously or as overlapped operations.
This parameter can include any combination of the following security access mode flags. These modes can be different for different instances of the same pipe. They can be specified without concern for what other dwOpenMode modes have been specified.
ModeDescription
WRITE_DAC The caller will have write access to the named pipe's discretionary access control list (ACL).
WRITE_OWNER The caller will have write access to the named pipe's owner.
ACCESS_SYSTEM_SECURITY The caller will have write access to the named pipe's SACL. For more information, see Access-Control Lists (ACLs) and SACL Access Right.

dwPipeMode[in]
Specifies the type, read, and wait modes of the pipe handle.
One of the following type mode flags can be specified. The same type mode must be specified for each instance of the pipe. If you specify zero, the parameter defaults to byte-type mode.
ModeDescription
PIPE_TYPE_BYTE Data is written to the pipe as a stream of bytes. This mode cannot be used with PIPE_READMODE_MESSAGE.
PIPE_TYPE_MESSAGE Data is written to the pipe as a stream of messages. This mode can be used with either PIPE_READMODE_MESSAGE or PIPE_READMODE_BYTE.
One of the following read mode flags can be specified. Different instances of the same pipe can specify different read modes. If you specify zero, the parameter defaults to byte-read mode.
ModeDescription
PIPE_READMODE_BYTE Data is read from the pipe as a stream of bytes. This mode can be used with either PIPE_TYPE_MESSAGE or PIPE_TYPE_BYTE.
PIPE_READMODE_MESSAGE Data is read from the pipe as a stream of messages. This mode can be only used if PIPE_TYPE_MESSAGE is also specified.
One of the following wait mode flags can be specified. Different instances of the same pipe can specify different wait modes. If you specify zero, the parameter defaults to blocking mode.
ModeDescription
PIPE_WAIT Blocking mode is enabled. When the pipe handle is specified in the ReadFile, WriteFile, or ConnectNamedPipe function, the operations are not completed until there is data to read, all data is written, or a client is connected. Use of this mode can mean waiting indefinitely in some situations for a client process to perform an action.
PIPE_NOWAIT Nonblocking mode is enabled. In this mode, ReadFile, WriteFile, and ConnectNamedPipe always return immediately.

nMaxInstances [in]
Specifies the maximum number of instances that can be created for this pipe. The same number must be specified for all instances. Acceptable values are in the range 1 through PIPE_UNLIMITED_INSTANCES. If this parameter is PIPE_UNLIMITED_INSTANCES, the number of pipe instances that can be created is limited only by the availability of system resources.

nOutBufferSize [in]
Specifies the number of bytes to reserve for the output buffer. For a discussion on sizing named pipe buffers, see the following Remarks section.

nInBufferSize [in]
Specifies the number of bytes to reserve for the input buffer. For a discussion on sizing named pipe buffers, see the following Remarks section.

nDefaultTimeOut [in]
Specifies the default time-out value, in milliseconds, if the WaitNamedPipe function specifies NMPWAIT_USE_DEFAULT_WAIT. Each instance of a named pipe must specify the same value.

lpSecurityAttributes [in]
Pointer to a SECURITY_ATTRIBUTES structure that specifies a security descriptor for the new named pipe and determines whether child processes can inherit the returned handle. If lpSecurityAttributes is NULL, the named pipe gets a default security descriptor and the handle cannot be inherited.

Return Values
If the function succeeds, the return value is a handle to the server end of a named pipe instance. If the named pipe object existed before the function call, the function returns a handle to the existing object and GetLastError returns ERROR_ALREADY_EXISTS.

If the function fails, the return value is INVALID_HANDLE_VALUE. To get extended error information, call GetLastError. The return value is ERROR_INVALID_PARAMETER if nMaxInstances is greater than PIPE_UNLIMITED_INSTANCES.

Windows 2000 SP2, Windows XP: If you attempt to create multiple instances of a pipe with WRITE_OWNER mode, creation of the first instance succeeds, but creation of the next instance fails with ERROR_ACCESS_DENIED. This change was made for security purposes.

Remarks
To create an instance of a named pipe by using CreateNamedPipe, the user must have FILE_CREATE_PIPE_INSTANCE access to the named pipe object. If a new named pipe is being created, the access control list (ACL) from the security attributes parameter defines the discretionary access control for the named pipe.

All instances of a named pipe must specify the same pipe type (byte-type or message-type), pipe access (duplex, inbound, or outbound), instance count, and time-out value. If different values are used, this function fails and GetLastError returns ERROR_ACCESS_DENIED.

The client side of a named pipe starts out in byte mode, even if the server side is in message mode. To avoid problems receiving data, set the client side to message mode as well.

The input and output buffer sizes are advisory. The actual buffer size reserved for each end of the named pipe is either the system default, the system minimum or maximum, or the specified size rounded up to the next allocation boundary.

The pipe server should not perform a blocking read operation until the pipe client has started. Otherwise, a race condition can occur. This typically occurs when initialization code, such as the C run-time, needs to lock and examine inherited handles.

An instance of a named pipe is always deleted when the last handle to the instance of the named pipe is closed.

ConnectNamedPipe

The ConnectNamedPipe function enables a named pipe server process to wait for a client process to connect to an instance of a named pipe. A client process connects by calling either the CreateFile or CallNamedPipe function.
BOOL ConnectNamedPipe(
  HANDLE hNamedPipe,          // handle to named pipe
  LPOVERLAPPED lpOverlapped   // overlapped structure
);

Parameters
hNamedPipe [in]
Handle to the server end of a named pipe instance. This handle is returned by the CreateNamedPipe function.

lpOverlapped [in]
Pointer to an OVERLAPPED structure.
If hNamedPipe was opened with FILE_FLAG_OVERLAPPED, the lpOverlapped parameter must not be NULL. It must point to a valid OVERLAPPED structure. If hNamedPipe was opened with FILE_FLAG_OVERLAPPED and lpOverlapped is NULL, the function can incorrectly report that the connect operation is complete.
If hNamedPipe was created with FILE_FLAG_OVERLAPPED and lpOverlapped is not NULL, the OVERLAPPED structure must contain a handle to a manual-reset event object (which the server can create by using the CreateEvent function).
If hNamedPipe was not opened with FILE_FLAG_OVERLAPPED, the function does not return until a client is connected or an error occurs. Successful synchronous operations result in the function returning a nonzero value if a client connects after the function is called.

Return Values
If the function succeeds, the return value is nonzero.
If the function fails, the return value is zero. To get extended error information, call GetLastError.
If a client connects before the function is called, the function returns zero and GetLastError returns ERROR_PIPE_CONNECTED. This can happen if a client connects in the interval between the call to CreateNamedPipe and the call to ConnectNamedPipe. In this situation, there is a good connection between client and server, even though the function returns zero.

Remarks
A named pipe server process can use ConnectNamedPipe with a newly created pipe instance. It can also be used with an instance that was previously connected to another client process; in this case, the server process must first call the DisconnectNamedPipe function to disconnect the handle from the previous client before the handle can be reconnected to a new client. Otherwise, ConnectNamedPipe returns zero, and GetLastError returns ERROR_NO_DATA if the previous client has closed its handle or ERROR_PIPE_CONNECTED if it has not closed its handle.

The behavior of ConnectNamedPipe depends on two conditions: whether the pipe handle's wait mode is set to blocking or nonblocking and whether the function is set to execute synchronously or in overlapped mode. A server initially specifies a pipe handle's wait mode in the CreateNamedPipe function, and it can be changed by using the SetNamedPipeHandleState function.

The server process can use any of the wait functions or SleepEx — to determine when the state of the event object is signaled, and it can then use the GetOverlappedResult function to determine the results of the ConnectNamedPipe operation.

If the specified pipe handle is in nonblocking mode, ConnectNamedPipe always returns immediately. In nonblocking mode, ConnectNamedPipe returns a nonzero value the first time it is called for a pipe instance that is disconnected from a previous client. This indicates that the pipe is now available to be connected to a new client process. In all other situations when the pipe handle is in nonblocking mode, ConnectNamedPipe returns zero. In these situations, GetLastError returns ERROR_PIPE_LISTENING if no client is connected, ERROR_PIPE_CONNECTED if a client is connected, and ERROR_NO_DATA if a previous client has closed its pipe handle but the server has not disconnected. Note that a good connection between client and server exists only after the ERROR_PIPE_CONNECTED error is received.

WaitNamedPipe

The WaitNamedPipe function waits until either a time-out interval elapses or an instance of the specified named pipe is available for connection (that is, the pipe's server process has a pending ConnectNamedPipe operation on the pipe).
BOOL WaitNamedPipe(
  LPCTSTR lpNamedPipeName,  // pipe name
  DWORD nTimeOut            // time-out interval
);

Parameters
lpNamedPipeName [in]
Pointer to a null-terminated string that specifies the name of the named pipe. The string must include the name of the computer on which the server process is executing. A period may be used for the servername if the pipe is local. The following pipe name format is used: \\servername\pipe\pipename

nTimeOut [in]
Specifies the number of milliseconds that the function will wait for an instance of the named pipe to be available. You can used one of the following values instead of specifying a number of milliseconds.
Value Meaning
NMPWAIT_USE_DEFAULT_WAIT The time-out interval is the default value specified by the server process in the CreateNamedPipe function.
NMPWAIT_WAIT_FOREVER The function does not return until an instance of the named pipe is available.

Return Values
If an instance of the pipe is available before the time-out interval elapses, the return value is nonzero.
If an instance of the pipe is not available before the time-out interval elapses, the return value is zero. To get extended error information, call GetLastError.

Remarks
If no instances of the specified named pipe exist, the WaitNamedPipe function returns immediately, regardless of the time-out value.

If the function succeeds, the process should use the CreateFile function to open a handle to the named pipe. A return value of TRUE indicates that there is at least one instance of the pipe available. A subsequent CreateFile call to the pipe can fail, because the instance was closed by the server or opened by another client.

CallNamedPipe

The CallNamedPipe function connects to a message-type pipe (and waits if an instance of the pipe is not available), writes to and reads from the pipe, and then closes the pipe.
BOOL CallNamedPipe(
  LPCTSTR lpNamedPipeName,  // pipe name
  LPVOID lpInBuffer,        // write buffer
  DWORD nInBufferSize,      // size of write buffer
  LPVOID lpOutBuffer,       // read buffer
  DWORD nOutBufferSize,     // size of read buffer
  LPDWORD lpBytesRead,      // number of bytes read
  DWORD nTimeOut            // time-out value
);

Parameters
lpNamedPipeName [in]
Pointer to a null-terminated string specifying the pipe name.

lpInBuffer [in]
Pointer to the buffer containing the data written to the pipe.

nInBufferSize [in]
Specifies the size, in bytes, of the write buffer.

lpOutBuffer [out]
Pointer to the buffer that receives the data read from the pipe.

nOutBufferSize [in]
Specifies the size, in bytes, of the read buffer.

lpBytesRead [out]
Pointer to a variable that receives the number of bytes read from the pipe.

nTimeOut [in]
Specifies the number of milliseconds to wait for the named pipe to be available. In addition to numeric values, the following special values can be specified.
Value Meaning
NMPWAIT_NOWAIT Does not wait for the named pipe. If the named pipe is not available, the function returns an error.
NMPWAIT_WAIT_FOREVER Waits indefinitely.
NMPWAIT_USE_DEFAULT_WAIT Uses the default time-out specified in a call to the CreateNamedPipe function.

Return Values
If the function succeeds, the return value is nonzero.
If the function fails, the return value is zero. To get extended error information, call GetLastError.

Remarks
Calling CallNamedPipe is equivalent to calling the CreateFile (or WaitNamedPipe, if CreateFile cannot open the pipe immediately), TransactNamedPipe, and CloseHandle functions. CreateFile is called with an access flag of GENERIC_READ | GENERIC_WRITE, an inherit handle flag of FALSE, and a share mode of zero (indicating no sharing of this pipe instance).

If the message written to the pipe by the server process is longer than nOutBufferSize, CallNamedPipe returns FALSE, and GetLastError returns ERROR_MORE_DATA. The remainder of the message is discarded, because CallNamedPipe closes the handle to the pipe before returning.

CallNamedPipe fails if the pipe is a byte-type pipe.

DisconnectNamedPipe

The DisconnectNamedPipe function disconnects the server end of a named pipe instance from a client process.
BOOL DisconnectNamedPipe(
  HANDLE hNamedPipe   // handle to named pipe
);

Parameters
hNamedPipe [in]
Handle to an instance of a named pipe. This handle must be created by the CreateNamedPipe function.

Return Values
If the function succeeds, the return value is nonzero.
If the function fails, the return value is zero. To get extended error information, call GetLastError.

Remarks
If the client end of the named pipe is open, the DisconnectNamedPipe function forces that end of the named pipe closed. The client receives an error the next time it attempts to access the pipe. A client that is forced off a pipe by DisconnectNamedPipe must still use the CloseHandle function to close its end of the pipe.

When the server process disconnects a pipe instance, any unread data in the pipe is discarded. Before disconnecting, the server can make sure data is not lost by calling the FlushFileBuffers function, which does not return until the client process has read all the data.

The server process must call DisconnectNamedPipe to disconnect a pipe handle from its previous client before the handle can be connected to another client by using the ConnectNamedPipe function.