How to implement a blocked interrupt handler in QNX?

How to set a specific channel that has higher priority?

Also I notice from the QNX library example of using “MsgDeliverEvent()”, the server first create a channel (#1) to receive a “cookie” from the client, the client then create another channel (#2) to receive pulse sigevent from the server. When the server has the need of notifying the client, it calls “MsgDeliverEvent(channel(#1), sigevent)” to deliver a pulse through channel #1 to the client that’s waiting for pulse on channel #2. My question is why is necessary to create two channel to do this? Is one channel enough for receiving message and pulse event? The example code is as follows:

#########client.c############
/* we need a channel to receive the pulse notification on */
chid = ChannelCreate( 0 );

/* and we need a connection to that channel for the pulse to be
delivered on */
coid = ConnectAttach( 0, 0, chid, _NTO_SIDE_CHANNEL, 0 );

/* fill in the event structure for a pulse */
SIGEV_PULSE_INIT( &msg.event, coid, SIGEV_PULSE_PRIO_INHERIT,
MY_PULSE_CODE, 0 );
msg.type = MSG_GIVE_PULSE;

/* find the server */
if ( (srv_coid = name_open( MY_SERV, 0 )) == -1)
{
printf(“failed to find server, errno %d\n”, errno );
exit(1);
}

/* give the pulse event we initialized above to the server for
later delivery */
MsgSend( srv_coid, &msg, sizeof(msg), NULL, 0 );

/* wait for the pulse from the server */
rcvid = MsgReceivePulse( chid, &pulse, sizeof( pulse ), NULL );
printf(“got pulse with code %d, waiting for %d\n”, pulse.code,
MY_PULSE_CODE );

###########server.c#########
/* attach the name the client will use to find us /
/
our channel will be in the attach structure */
if ( (attach = name_attach( NULL, MY_SERV, 0 )) == NULL)
{
printf(“server:failed to attach name, errno %d\n”, errno );
exit(1);
}

/* wait for the message from the client /
rcvid = MsgReceive( attach->chid, &msg, sizeof( msg ), NULL );
MsgReply(rcvid, 0, NULL, 0);
if ( msg.type == MSG_GIVE_PULSE )
{
/
wait until it is time to notify the client */
sleep(2);

 /* deliver notification to client that client requested */
 MsgDeliverEvent( rcvid, &msg.event );
 printf("server:delivered event\n");

} else
{
printf(“server: unexpected message \n”);
}

yicheng,

  1. Normally, the priority is determined by the message or pulse you receive on a channel. You can use the flag _NTO_CHF_FIXED_PRIORITY with ChannelCreate. This turns off the priority inheritance on this channel.

  2. A process needs a channel to receive messages and/or pulses. In your example you have two processes - the server and the client - and both need their own channel to be able to receive messages and/or pulses. The server uses its channel to receive both - messages and pulses - from the client. And the client needs its channel to receive the notification pulses from the server.

  • Peter

I think there’s misunderstanding here. My question is how to set the priority of the specific channel, not the thread that send/receive message on this channel. The kernel must have some mechanism of selecting which channel to poll next.

Let me make it more clear. In this example, the server calls “MsgDeliverEvent(channel(#1), sigevent)” to deliver a pulse through channel #1 to the client that’s waiting for pulse on channel #2. Since the client already create channel #2 to receive a pulse, can the server attach itself to the channel #2 and deliver the pulse through #2? Just like this:
ChannelAttach(#2);
MsgDeliverEvent(channel(#2), sigevent);

  1. There is no “channel priority”. The kernel doesn’t “poll” the channels. A thread is blocked on a channel when calling MsgReceive() - like on a mutex - until a message or a pulse is sent to this channel. The kernel call invoked by the sender causes the unblocking of a waiting receiver thread. But the scheduler decides on the base of the thread’s priority if the ready thread can run or not. The priority of the receiving thread is determined by the priority of the pulse or the priority of the thread that sent the message (priority inheritance). If you turn off priority inheritance on a channel, the priority is determined by the receiving thread itself.

  2. The server can’t use it’s own channel #1 for sending pulses to the client. As far as I understand, MsgDeliverEvent() needs the rcvid from channel #1 to determine the node and process id of the sender. If the event is a pulse (it can be something other - e.g. a signal!), the connection id contained in the event (set to channel #2 by the client) is used to send the pulse. I guess MsgDeliverEvent() needs the information from the rcvid to translate the connection id from the client side to the server side in this case.

The example shows how a server can notify clients without knowing a lot of details (node id, process id, channel id, event type, event informations).

-Peter

Dude, you need to do a lot more reading before asking more questions. It is difficult to answer your questions because there is a lot of basic understanding of the architecture missing, and this forum is the wrong place to gain that info.

As Peter said, there is no polling, and there is no priority for a channel (there is a flag that prevents inheritance from threads doing a receive on a channel, but this should never be used as it breaks priority inheritance system wide).

Again, as Peter said the MsgDeliverEvent uses the rcvid to determine which channel to send the pulse on (in the case of a pulse it actually has this information in the sigevent struct, but it cannot rely on this as the client can configure sigevent variants that don’t have this information).

First thanks all of you for the clearification.

I do read the QNX system architechture and library reference before I post the question. However those document still don’t clear my confuse. If this forum is not for this kind of discussion, then what’s this forum for and where should it be such discussion?

Best!

It’s obvious english is not your first language, maybe you need to find documentation in your native language. The problem is that the question you ask show a total lack of understanding of QNX.

A question like “My question is how to set the priority of the specific channel” although grammatically correct doesn’t make sense in the QNX world. You are not even close to understanding some basic QNX concept. To correct your misunderstanding one would need to write a whole chapter. And these chapters are already written and available in the documentation…

I think what you need to understand is that a forum like this is a very inefficient way to get the level of information and detail that you seem to require.

It’s like trying to learn C++ over forum and the guy ask: I’m trying to print the content of a file and I’m using printf( “filename” ); but I get on the screen is the text filename, what am I doing wrong? If you know C and you were to read this question you’d probably tell yourself “oh my god” and sigh at the idea of explaining to this guy what he is doing wrong. Well I think it’s safe to say that’s how most of us feel about your question.

Good luck.

I’d just add, that if the situation was reversed and I was trying to understand docs written in (is it Chinese?) I would suck far worse! :slight_smile: