ionotify confusion

I am trying to write a simple program using ionotify in place of select, just to get the feel of it. If there is data ready at the time I call ionotify everything works OK, but if it arrives later I never seem to get a notification pulse. What am I doing wrong? And what does the manual section mean when it says:

What is a “continuous” action? I can’t find a definition anywhere.

Here is the program source. I tried to attach it, but kept getting complaints about the file name extension. Life is too short.

#include <stdio.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/socket.h>
#include <sys/iomsg.h>
#include <sys/neutrino.h>
#include <netinet/in.h>

int main()
{
    const in_addr_t myAddr = 0xc0a8115a; /* 192.168.17.90 */
    int r;
    int fflags;
    int c;
    int sockL;
    int sock;
    socklen_t sockLen;
    struct sockaddr_in sockAddr;
    struct sockaddr_in sockAddrRemote;
    struct _pulse msgPulse;
    int myChannel;
    struct sigevent ioEvent;

    sockL = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
    if (sockL < 0)
    {
	perror("socket");
	return 1;
    }

    r = 1;
    setsockopt(sockL, SOL_SOCKET, SO_REUSEADDR, &r, sizeof(r));

    memset(&sockAddr, 0, sizeof(sockAddr));
    /* sockAddr.sin_len = ? */
    sockAddr.sin_family = AF_INET;
    sockAddr.sin_port = htons(3333);
    sockAddr.sin_addr.s_addr = htonl(myAddr);

    if (bind (sockL, (struct sockaddr*)&sockAddr, sizeof(sockAddr)) != 0)
    {
	perror("bind");
	return 1;
    }

    if (listen(sockL, 1) != 0)
    {
	perror("listen");
	return 1;
    }

    sockLen =   sizeof(sockAddrRemote);
    sock = accept(sockL, (struct sockaddr*)&sockAddrRemote, &sockLen);
		
    if (sock < 0)
    {
	perror("accept");
	return 1;
    }
    
    myChannel = ChannelCreate(_NTO_CHF_UNBLOCK);
    if (myChannel < 0)
    {
	perror("ChannelCreate");
	return 1;
    }

    SIGEV_PULSE_INIT(&ioEvent, myChannel, 1, 
		     _PULSE_CODE_MINAVAIL + 1, "xyz");

    fflags = fcntl(sock, F_GETFL);
    fflags |= O_NONBLOCK;
    if (fcntl(sock, F_SETFL, fflags) == -1)
    {
	perror("fcntl");
    }

    while ((r = ionotify(sock, _NOTIFY_ACTION_POLLARM, _NOTIFY_COND_INPUT, &ioEvent)) > 0)
    {
	if (read(sock, &c, 1) != 1)
	    perror("read");
	else putchar(c);
    }

    if (r < 0)
    {
	perror("ionotify");
    }

    /* expecting a pulse.  return value > 0 indicates actual msg */
    while ((r = MsgReceivePulse(myChannel, &msgPulse, 
			   sizeof(msgPulse), NULL)) == 0)
    {
	if (read(sock, &c, 1) != 1)
	    perror("read 2");
	else
	    putchar(c);
    }
    if (r > 0)
	printf("MsgReceive: %x\n", r);
    else
	perror("MsgReceive");

    return 0;
}

Looks like you are initializing the pulse event with a channel ID instead of a connection ID. You need to do a

myConnection=ConnectAttach(0,0,myChannel,_NTO_SIDE_CHANNEL,0);
SIGEV_PULSE_INIT(&ioEvent, myConnection=, 1,  _PULSE_CODE_MINAVAIL + 1, "xyz");

Thank you: now that I RTFM more carefully I notice that point. Unfortunately, the program works no better than before. MsgReceivePulse never wakes up.

Further thoughts greatly appreciated. I’m going to look into tracing stuff and see if that provides any hints.

I tried your example - you are receiving a pulse, but then trying to wait for another. Once you receive one pulse you need
to re-arm with another ionotify.

Aha! So, this must not be a “continuous action” :slight_smile: OK, it appears to work now, and I have much better grasp of what to expect.

Thank you all very much for you help.