QNX Neutrino distributed
At the heart of QNX Neutrino native networking is the Qnet protocol, which is deployed as a network of tightly coupled trusted machines.
Qnet lets these machines share their resources efficiently with little overhead. Using Qnet, you can use the standard OS utilities (cp, mv, and so on) to manipulate files anywhere on the Qnet network as if they were on your machine. In addition, the Qnet protocol doesn't do any authentication of remote requests; files are protected by the normal permissions that apply to users and groups. Besides files, you can also access and start/stop processes, including managers, that reside on any machine on the Qnet network.
The distributed processing power of Qnet lets you do the following tasks efficiently:
- Access your remote filesystem.
- Scale your application with unprecedented ease.
- Write applications using a collection of cooperating processes that communicate transparently with each other using QNX Neutrino message-passing.
- Extend your application easily beyond a single processor or SMP machine to several single-processor machines and distribute your processes among those CPUs.
- Divide your large application into several processes, where each process can perform different functions. These processes coordinate their work using message passing.
- Take advantage of Qnet's inherent remote procedure call functionality.
Moreover, since Qnet extends QNX Neutrino message passing over the network, other forms of IPC (e.g., signals, message queues) also work over the network.
To understand how network-wide IPC works, consider two
processes that wish to communicate with each other: a client
process and a server process (in this case, the serial port
manager process). In the single-node case, the client simply
calls
open(),
read(),
write(),
etc. As we'll see shortly, a high-level
POSIX call such as open() actually entails
message-passing kernel calls underneath
(ConnectAttach(),
MsgSend(), etc.).
But the client doesn't need to concern itself with those
functions; it simply calls open().
fd = open("/dev/ser1", O_RDWR,...); /* Open a serial device */
Now consider the case of a simple network with two machines—one contains the client process, the other contains the server process.
The code required for client-server communication is identical to the code in the single-node case, but with one important exception: the pathname. The pathname will contain a prefix that specifies the node that the service (/dev/ser1) resides on. As we'll see later, this prefix will be translated into a node descriptor for the lower-level ConnectAttach() kernel call that will take place. Each node in the network is assigned a node descriptor, which serves as the only visible means to determine whether the OS is running as a network or standalone.
For more information on node descriptors, see the Transparent Distributed Processing with Qnet chapter of the QNX Neutrino Programmer's Guide.
