msgreceivepulse and msgsendpulse

Hello,

I’ve a question about msgreceivepulse and msgsendpulse.

I’ve 2 thread :

The first send a pulse like this:

int commande=1; MsgSendPulse(coid, 10, _PULSE_CODE_MAXAVAIL, commande);

The second receive a pulse like this :

int rcvid;
struct _pulse buffer;

rcvid= MsgReceivePulse(cid, &buffer, sizeof(buffer), NULL);

I want that the second thread get the command value for use it. How can i get this value? is it in the buffer?

Thanks[/list]

Yes, the value is in the “code” member of the _pulse structure. Take a look at the entry for _pulse in the Neutrino Library Reference.

i’ve tried to get buffer.code but it’s not my value…

The value in buffer.code is 0 or 127 never the same… , me, i want to get 1 if commande=1 , 2 if commande=2…

well, i think it is in the buffer.value.sival_int …

I’ve tried this to.

When buffer.code=0 , buffer.value.sival_int=0
and when buffer.code=127 , buffer.value.sival_int=1

:frowning:

I don’t understand…

i just made a test program and it works very well

what exactly u dont understand ?

You are getting a pulse code 0 from somewhere else (i.e. not as the result of your MsgSendPulse). You can simply check that pulse.code == _PULSE_CODE_MAXAVAIL before checking the sival_int for your command.

Can you send me a sample?

[code]#include <sys/iofunc.h>
#include <sys/dispatch.h>
#include <sys/neutrino.h>

#define D_Name “pulse_test”
#define D_MyPulseCode _PULSE_CODE_MAXAVAIL

int main (int argc, char *argv[])
{
name_attach_t *na;
struct _pulse buf;
int coid, rcvid;
int value;

if (argc == 2)
{
	value = atoi(argv[1]);

	coid = name_open(D_Name, 0);
	MsgSendPulse(coid, 10, D_MyPulseCode, value);

	return 0;
}

if (argc == 1)
{
	na = name_attach(NULL, D_Name, 0);

	for (;;)
	{
		rcvid = MsgReceive(na->chid, &buf, sizeof(buf), NULL);
	
		if (rcvid == 0)
		{
			if (buf.code == D_MyPulseCode)
			{
				printf("received my pulse: value %d\n", buf.value.sival_int);
			}
			else if (buf.code == _PULSE_CODE_DISCONNECT)
			{
				printf("received pulse: client disconnected\n");
			}
			else
			{
				printf("received a pulse: code %d, value %d\n", buf.code, buf.value.sival_int);
			}
		}
		else if (rcvid > 0)
		{
			printf("received message\n");
			MsgError(rcvid, -1);
		}
		else
			printf("MsgReceive failed\n");
	}
	
	return 0;
}

return -1;

} [/code]

thanks

I have a question about MsgSendPulse().
According to QNX documentation, MsgSendPulse() sends “a tiny non-blocking message (pulse)”. I am not sure I understand the term “non-blocking”.
I thought “non-blocking” means if there is no process calling MsgReceivePulse(), the pulse will be discarded.
From this link: qnx.com/developers/docs/mome … pulse.html
“Pulses are queued for the receiving process in the system, …”
So the pulses are saved, instead of being discarded.

How can I discard the pulses, if no process is waiting for the pulse? This is the requirement of my application.
Or how can the receiver clear all the pulse in the queue and wait for the next pulse?

“non-blocking” means that MsgSendPulse will return after sending the pulse what ever the state of the receiving end. A block call means it will block until the receiving end indicates it is done with the message.

You cannot discard pulses, you need to either consume them, or close the channel they were send on and open a new one.

I think this is a short coming in the OS. Under QNX4 it’s possible to clear the pulses (proxy) queue on a per proxy basis.

^
||
||
Do you refer to the QNX4 function Creceive()?
There is an article saying that Creceive function can be implemented in QNX6 with:
MsgReceive() preceded immediately by:

event.sigev_notify = SIGEV_UNBLOCK;
TimerTimeout(CLOCK_REALTIME, _NTO_TIMEOUT_RECEIVE,
            &event, NULL, NULL );

I think it also apply to MsgReceivePulse, right?

The sender in my application generates events at certain frequencies.
When the receiver wakes up, it is only interested in events that happens later, disregarding previous events.
If pulses don’t work, is there any other mechanism can realize this functionality?

Creceive can be partly emulated yes, but receive() and Creceive() have the ability to receive only from a specify process or proxy, that cannot be done with TimerTimeout.

Hence MsgReceivePulse will receive ALL pulses. But if all you will be receiving on that channel is that single pulse then it’s doable.

If not maybe if you can send some sort of time stamp along with the pulse so that the receiver can tell wether they should be disregarded or not.

This already sounds like bad design. What does it mean that the receiver wakes up? Wake up from a MsgReceive? If so, how can it be interested in events that happen later. That would be events in the future right?

Let’s assume that you mean later than some time in the past. What is the resolution? Clearly if the resolution is 1 second, the sender could send the value of time() along in the pulse. If the resolution is finer, then you will have to be a bit careful in case there is a roll over issue.

Why does the sender need to be unblocked immediately? Another way of thinking about a pulse, is that there is an invisible queueing mechanism in the OS. Maybe you need a queueing mechanism that isn’t limited to the package size that a pulse sends.

I’ve often run into the fear, and misunderstanding, that such an arrangement would not create the same affect, non-blocking, but
there is really no difference if engineered right. Sending a Pulse involves a kernel call, just like a MsgSend. If the queueing thread is at a higher priority, it runs immediately, queues the message, and the client is running again. A pulse is more efficient in that the OS doesn’t have to schedule another process, but it still has to queue the pulse.
Either way the results are the same except for the latency, which is small in both cases.