📜 ⬆️ ⬇️

QNX RTOS: loosely coupled cross-tasking PPS

Another continuation of the cycle of notes on the QNX real-time operating system . Today I would again like to talk about inter-tasking interaction, but only about one specific mechanism - Persistent Publish / Subscribe (PPS, sustainable publishing / subscribing service). Just want to note, this is a new kind of interaction in QNX Neutrino, which appeared only in version 6.5.0. The PPS technology is not implemented in the microkernel, and a special manager with a speaker called pps is responsible for the operation of this mechanism.

PPS has proven so reliable, convenient and easy to use that it is used in new solutions and products, such as, for example, Smart Energy , QNX Car and even a BlackBerry PlayBook tablet.

In this article we will get acquainted with PPS in practice, it will be told about the features of the technology, and at the very end it will be shown that PPS is a real cosmopolitan among the mechanisms of inter-task interaction, and many programming languages ​​support it out of the box.
')

What is PPS for?


Using PPS allows you to simplify the construction of systems consisting of many components. In the future, these components can be modified, supplemented and even deleted without altering the entire system as a whole and without changing other components. Different development teams that develop applications using different technologies and programming languages ​​can develop components that will interact with each other without any knowledge of each other.

The main advantages of PSS over other methods of inter-task interaction:


Most likely, if the system already consists of three or four components, and in the future it can be changed and expanded, the use of PPS will be the right step.

What is PPS?


PPS is pretty simple. These are files in which objects with their properties are displayed. They are not even displayed, but they live right there. Only one object is stored in one file. Any process can read and write such a file, if the POSIX access attributes allow it. You can work with PPS from the program in almost any language, since to access objects, use the usual functions read() , write() , etc. Probably enough tediousness and, perhaps, it's time to start practical exercises.

The first step is to start the pps manager:

 # pps 

The manager, of course, has command line arguments, but for us there is nothing of principle. Anyone can read the description in the reference manual. When performing all the following exercises, we will assume that the pps manager is already running. Now let's try to create some object, for example, figure :

 # touch /fs/pps/figure 

It's all. Now the object can be read:

 # cat /fs/pps/figure @figure 

So you can see the name of the object. The object has no properties yet. You can add them, for example, form :

 # echo "form::square" >> /fs/pps/figure # cat /fs/pps/figure @figure form::square 

You can add another property, for example, color :

 # echo "color::red" >> /fs/pps/figure # cat /fs/pps/figure @figure color::red form::square 

Be careful, the following command will delete the object and create it again with one property:

 # echo "color::green" > /fs/pps/figure # cat /fs/pps/figure @figure color::green 

Hope you know the difference between> and >>. Any property or several properties of an object can be changed or added at any time:

 # echo "color::blue\nform::circle" >> /fs/pps/figure # cat /fs/pps/figure @figure color::blue form::circle 

Any property of an object can be deleted:

 # echo "-color" >> /fs/pps/figure # cat /fs/pps/figure @figure form::circle 

If the object itself is no longer needed, then it can be deleted:

 # rm /fs/pps/figure # cat /fs/pps/figure /fs/pps/figure: No such file or directory 

I think that Habr's readers are literate enough people to understand the meaning of the examples and rewrite them in their favorite language.

And now, it seems to me, it's time to explain the meaning of the name PPS - Persistent Publish / Subscribe.

Persistent


Service PPS during operation stores data in RAM. But at the same time, PPS ensures that data is stored between reboots in non-volatile storage. Typically, data is stored in the file system on disk or flash-memory. If necessary, the developer can organize the preservation of data on non-standard media.

At startup, the pps manager recovers data from non-volatile storage. You can specify various data recovery modes using the -l option:


Publishing


We already know enough about this 1 . You just need to open the file to write and write and delete the attributes of the object:

 sprintf( ppsobj, "-color\n" ); // Delete the "color" attribute write( ppsobj-fd, ppsobj, strlen( ppsobj ) ); 

It is probably worth noting that several processes can simultaneously open the same object for writing and change attributes. This can be useful if different processes are responsible for different attributes.

Subscribing


On the subscription, we also already know something, but not all. You do not think that PPS is so simple and trivial. Yes, there was a dog somewhere. And she rummaged in the subscription. There are subtleties of a subscription, such as, for example, blocking reading and delta mode. Consider some of these features.

Blocking read

By default, reading from a PPS object file is non-blocking. This is common behavior for other file systems. It is made specifically for standard utilities to behave as usual. The easiest way (but not always the best) is to get object changes in a timely manner, this is a blocking read. To open a PPS object in the blocking read mode, just open the file with the qualifier ? Wait .

Let's conduct a bold experiment and in one console we will change the properties of the object, and in the other we will follow these changes. To do this, you need two consoles. If the Photon graphical environment is running, then everything is simple. If the work goes on in the text console, then switching between them is carried out using the key combination Ctrl + Alt + n (here n is the key with the number 1, 2, etc., and not the F1, F2 function key as in Linux, for example). And so, we create an object:

 # echo "color::green" >> /fs/pps/figure 

And in the second console, open it in blocking read mode:

 # cat /fs/pps/figure?wait @figure color::green 

Note that the cat utility does not terminate, but is blocked by reading. Now in the first console, type a couple of commands:

 # echo color::red >> /fs/pps/figure # echo color::white >> /fs/pps/figure 

In the second console, the output continues:

 @figure color::red @figure color::white 

Especially clearly do all this in Photon, when two consoles before his eyes. You can exit cat usual Ctrl + C.

You can switch the reading mode on the fly. The following C code illustrates this feature:

 flags = fcntl( fd, F_GETFL ); flags |= O_NONBLOCK; fcntl( fd, F_SETFL, flags ); 

Notification of new data

There are two ways to get new data from PPS in a timely manner:


Using the select() function is preferable because allows you to change the properties of several objects.

Subscription Modes

There are two subscription modes:


image
Fig. 1. Full and "delta" PPS subscription modes.

It should be noted that in full mode the object is always read in its entirety with all its properties that exist at the time of reading the object. This means that if between readings the same property was changed several times, then the last change will be read.

In the “delta” mode, on the contrary, the subscriber receives all changes in the properties of the object, i.e. Nothing will be missed 2 . To open an object in delta mode, you must specify the qualifier ? Delta after the object name.

The following example shows the reading of an object in delta mode. On the first console, create an object:

 # echo "color::red\nform::square" >> /fs/pps/figure 

On the second console, subscribe to it in delta mode:

 # cat /fs/pps/figure?delta,wait @figure color::red form::square 

Change the color:

 # echo "color::green" >> /fs/pps/figure 

We observe changes:

 @figure color::green 

Change the shape:

 # echo "form::circle" >> /fs/pps/figure 

We observe changes:

 @figure form::circle 

We change two properties at once:

 # echo "color::red\nform::square" >> /fs/pps/figure 

And we get one change:

 @figure color::red form::square 

Server mode


The PPS object may have a server, i.e. such a process that is paramount among publishers. It is also called a critical subscriber. To open an object in server mode, you must specify the ? Server qualifier. The remaining subscribers become clients.

If any of the clients changes the property of the object, only the server will receive the notification and change of the object. The client identifier (number) is also added to the object identifier, for example:

 @figure.1234 

If a new client subscribes to an object, the server receives a notification with a plus sign (+):

 +@figure.1234 

A similar notification arrives if the client unsubscribes from the object, only with a minus sign (-). If the server wants to respond only to the client, then it must record the object with the client identifier, otherwise all clients will receive a notification. In fig. Figure 2 shows the interaction between the PPS server and client.

image
Fig. 2. PPS server mode.

It is difficult to show an example of server operation using only command line utilities, so, in case of interest, it is proposed to develop it yourself, for example, in C.

PPS support in various programming languages


The main programming language in QNX is C. But other languages ​​and platforms are supported. Will they support PPS? Yes, they will. For a strategic platform like Adobe Flash, there are extensions and classes for working with PPS. And what about other languages?

As it was possible to be convinced from everything that was told in this note, for interaction through PPS it is enough only to be able to open files, read from and write to them. For comfortable work, you will need an implementation of the select() function. That's probably all the requirements. And these requirements are met, for example, by Python. Do not believe? Yes, there is nothing easier, let's boldly create two PPS objects using the following commands:

 # echo "form::triangle\ncolor::green" >> /fs/pps/figure # echo verb::runs >> /fs/pps/action 

In another console, run the following Python script:

 #!/usr/qnx650/host/qnx6/x86/usr/bin/python import select action = { "verb" : "stop" } figure = { "form" : "circle", "color" : "black" } sentence = { "action" : action, "figure" : figure } f1 = open('/fs/pps/figure?delta', 'r') f2 = open('/fs/pps/action?delta', 'r') while 1: r, w, e = select.select( [f1, f2], [], [] ) for f in r: d = f.read().split() for a in d[1:]: k, v = a.split( "::" ) sentence[ d[0][1:] ][k] = v print figure["color"], figure["form"], action["verb"] 

In the first console, we will try to change the different attributes of the figure and action objects, and in the second we will observe a change in the output. Try to play yourself, you should get something like the following output:

 green triangle runs green circle runs blue circle runs white square runs white square stops 

The Python script is quite simple and serves only to illustrate the possibilities of working with various programming languages ​​with PPS. There is no so-called anti-fool. But pay attention to how simple the program is. Wow, you don’t have to do anything special to interact with each other. Personally, I really liked the PPS technology.

Additional materials


  1. PPS technology
  2. Sustainable QNX Publish / Subscribe Service
  3. QNX Persistent Publish / Subscribe Developer's Guide


1 It is worth noting the server mode, which is considered separately.

2 In the event of a restart of the operating system, changes accumulated in the delta mode will be lost.

Source: https://habr.com/ru/post/129196/


All Articles