FX::QPipe Class Reference
[Synchronous i/o devices]

#include <QPipe.h>

Inheritance diagram for FX::QPipe:

FX::QIODeviceS FX::QIODevice List of all members.

Detailed Description

A named pipe i/o device.

This is one of the oldest pieces of code in my extensions to FOX - it was one of the first classes written for Tornado originally and it is a testament to how API compatible with Qt TnFOX is that very little work had to be done to port it. In fact, the below docs are almost identical too :)

QPipe is a synchronous i/o device like FX:QBlkSocket - in other words, reads from it block until data is available. To avoid this, check atEnd() before reading - however generally, you want it to block because you will have allocated a special thread whose sole purpose is to wait on incoming data and asynchronously do something useful with it. One action could be to post a message to some control in the GUI for example but more likely you'll combine it with FX::FXIPCMsgMonitorBase.

Reads and writes are threadsafe, but you should avoid more than two threads working with the same pipe (the same as more than two processes) because transfers occur in no more than maxAtomicLength() (usually 4096 bytes, but it is system dependent) - so two threads writing at the same time will cause the read data to be mixed blocks of data - which you probably don't want. If you do use a pipe which has more than two users, ensure all data transfers are less than maxAtomicLength(). If you want a pipe with less restrictions and only for intra-process communication, see FX::QLocalPipe. If you need less restrictions across multiple processes, see FX::QBlkSocket (though this is inefficient).

Default security is for FX::FXACLEntity::everything() to have full access. This makes sense as named pipes are generally for inter-process communication - if however it's a private pipe for communication with a known process it makes sense to restrict access to the user running that process at least. Note that until the pipe is opened, permissions() returns what will be applied to the pipe on open() rather than the pipe itself - if you want the latter, use the static method.

Like FX::QMemMap, the pipe name is deleted by its creator on POSIX only (on Windows it lasts until the last thing referring to it closes). If you don't want this, specify IO_DontUnlink in the flags to open().

Usage:

To use is pretty easy - simply construct one, set its name and have your intended server process call create(). Then have your client process call open(). Reads block (wait indefinitely) until someone connects and sends some data. If you set the isDeepPipe parameter on creation, extra deep buffers are set if supported by the host operating system.

If a pipe should break unexpectedly, a special informational exception FX::FXConnectionLostException is thrown which has a code of FXEXCEPTION_CONNECTIONLOST. You may or may not at this stage wish to call reset(). For anything more than non-trivial usage, you will need to trap and handle this in order to be handling errors correctly.

If you merely want some unique pipe for communication, use setUnique(). This chooses a randomised name and will retry rerandomised names until it finds one available during create(). Thereafter you can send its unique name (retrieved by name()) to the other process to open(). Note that reset() may rerandomise the name if it something else has claimed that name.

Warning:
On both POSIX and Win32, the read side of a pipe is operated in non-blocking mode (to prevent blocks on open or breaking waitForData() on POSIX and to emulate thread cancellation on Win32). You shouldn't ever notice this.

A major portability difference is that on Win32/64, named pipes are fundamentally broken in various minor ways plus must cope with thread cancellation. I originally spent many months getting this code to work around all the problems and make them behave like on Unix as much as possible - however it's possible I've missed some area. Please look at the source of QPipe to get some idea of the problems :(

Due to issues with cancelling overlapped i/o on Windows, close() the pipe from the same thread you last performed a read operation. Failure to do this results in free space corruption in the heap which may or may not have the CRT library throw an assertion when validating the MSVC heap. This bug took me two days to find, so I hope that you won't suffer the same!

Definition at line 109 of file QPipe.h.

Public Types

typedef FXfval Offset
 Default
 Unix
 MacOS
 MSDOS
 NoTranslation
 UTF8
 UTF16
 UTF16LE
 UTF32
 UTF32LE
enum  CRLFType { Default, Unix, MacOS, MSDOS }
enum  UnicodeType {
  NoTranslation, UTF8, UTF16, UTF16LE,
  UTF32, UTF32LE
}

Public Member Functions

 QPipe ()
 QPipe (const FXString &name, bool isDeepPipe=false)
 ~QPipe ()
const FXStringname () const
void setName (const FXString &name)
bool isUnique () const
void setUnique (bool a)
bool create (FXuint mode=IO_ReadWrite)
bool open (FXuint mode=IO_ReadWrite)
void close ()
void flush ()
bool reset ()
bool atEnd () const
FXfval size () const
void truncate (FXfval size)
FXfval at () const
bool at (FXfval newpos)
virtual const FXACLpermissions () const
virtual void setPermissions (const FXACL &perms)
FXuval readBlock (char *data, FXuval maxlen)
FXuval writeBlock (const char *data, FXuval maxlen)
int ungetch (int)
FXuval maxAtomicLength ()
virtual bool isSynchronous () const
virtual FXuval readBlockFrom (char *data, FXuval maxlen, FXfval pos)
FXuval readBlockFrom (FXuchar *data, FXuval maxlen, FXfval pos)
virtual FXuval writeBlockTo (FXfval pos, const char *data, FXuval maxlen)
FXuval writeBlockTo (FXfval pos, const FXuchar *data, FXuval maxlen)
FXuint flags () const
FXuint mode () const
FXuint state () const
CRLFType crlfFormat () const
void setCRLFFormat (CRLFType type)
UnicodeType unicodeTranslation () const
void setUnicodeTranslation (UnicodeType type)
bool isBuffered () const
bool isRaw () const
bool isTranslated () const
bool isUTF16Translated () const
bool isUTF32Translated () const
bool isReadable () const
bool isWriteable () const
bool isWritable () const
bool isReadWrite () const
bool isClosed () const
bool isInactive () const
bool isOpen () const
FXuval readBlock (FXuchar *data, FXuval maxlen)
FXuval writeBlock (const FXuchar *data, FXuval maxlen)
virtual FXuval readLine (char *data, FXuval maxlen)
virtual int getch ()
virtual int putch (int c)
FXfval shredData (FXfval offset, FXfval len=(FXfval)-1)

Static Public Member Functions

static FXACL permissions (const FXString &name)
static void setPermissions (const FXString &name, const FXACL &perms)
static bool waitForData (QIODeviceS **signalled, FXuint no, QIODeviceS **list, FXuint waitfor=FXINFINITE)
static FXuint waitForDataMax () throw ()
static UnicodeType determineUnicodeType (FXuchar *data, FXuval len) throw ()
static FXuval applyCRLF (FXuchar *FXRESTRICT output, const FXuchar *FXRESTRICT input, FXuval outputlen, FXuval &inputlen, CRLFType crlftype=Default, UnicodeType utftype=NoTranslation)
static FXuval removeCRLF (FXuchar *FXRESTRICT output, const FXuchar *FXRESTRICT input, FXuval outputlen, FXuval &inputlen, UnicodeType utftype=NoTranslation)

Protected Member Functions

void setFlags (int f)
void setMode (int m)
void setState (int s)

Protected Attributes

FXfval ioIndex

Friends

class FXIPCChannel
class QChildProcess
struct QChildProcessPrivate
FXAPI FXStreamoperator<< (FXStream &s, QIODevice &i)
FXAPI FXStreamoperator>> (FXStream &s, QIODevice &i)


The documentation for this class was generated from the following file:
(C) 2002-2009 Niall Douglas. Some parts (C) to assorted authors.
Generated on Fri Nov 20 18:37:42 2009 for TnFOX by doxygen v1.4.7