Xref: utzoo comp.lang.c:9504 comp.unix.xenix:2069 Path: utzoo!mnetor!uunet!husc6!uwvax!rutgers!bellcore!tness7!mechjgh From: mechjgh@tness7.UUCP (Greg Hackney ) Newsgroups: comp.lang.c,comp.unix.xenix Subject: Re: Interprocess Communication on UNIX SVR3 Message-ID: <922@tness7.UUCP> Date: 20 Apr 88 23:36:34 GMT References: <2592@ihuxv.ATT.COM> Reply-To: mechjgh@tness1.UUCP (Greg Hackney) Organization: Southwestern Bell, Network Engineering, Dallas Lines: 278 Keywords: Producer/Consumer Problem In article <2592@ihuxv.ATT.COM> bareta@ihuxv.ATT.COM (Benyukhis) writes: >the producer has to produce >a char and deposit it in the shareable buffer for consumer to pick it up >from. Both processes must use binary semaphores as a means of >synchronization. It looks trivial, but for someone that has never >written anything for more than one process I'm not sure if this is what you want, but here are 4 simple demo programs for writing lines of IPC "messages", open.c, send.c, receive.c, and close.c. open 777 # opens a message queue ipcs # show the queue status send 777 text # send some text ipcs # show the queue status send 777 text1 # send some more text ipcs # show the queue status rec 777 # read some text rec 777 # read some text close 777 # close the queue ipcs # show the queue status -- Greg {ihnp4 | bellcore}!tness1!mechjgh #!/bin/sh # This is a shell archive, meaning: # 1. Remove everything above the #!/bin/sh line. # 2. Save the resulting text in a file. # 3. Execute the file with /bin/sh (not csh) to create the files: # close.c # open.c # rec.c # send.c # This archive created: Wed Apr 20 18:19:26 1988 export PATH; PATH=/bin:$PATH if test -f 'close.c' then echo shar: over-writing existing file "'close.c'" fi cat << \SHAR_EOF > 'close.c' /* close.c */ #include #include #include #include main(argc,argv) int argc; char *argv[]; { int qid; int syserr(); /*see if the queue is open, and get queue ID number */ if((qid=msgget(atoi(argv[1]),0666 & ~IPC_CREAT))== -1) syserr("Queue was not open!\n"); /*close the queue*/ if((msgctl(qid,IPC_RMID,NULL)) == -1) syserr("Can't close the queue\n"); printf("Queue closed successfully\n"); exit(0); } syserr(msg) char *msg; { extern int errno, sys_nerr; extern char *sys_errlist[]; fprintf(stderr,"ERROR: %s (%d", msg, errno); if(errno > 0 && errno < sys_nerr) fprintf(stderr, ";%s)\n", sys_errlist[errno]); else fprintf(stderr,")\n"); exit(1); } SHAR_EOF if test -f 'open.c' then echo shar: over-writing existing file "'open.c'" fi cat << \SHAR_EOF > 'open.c' /*open.c*/ #include #include #include #include #define MAXOPEN 20 main(argc,argv) int argc; char *argv[]; { int id; int syserr(); if((id=openqueue(atoi(argv[1]))) == -1) syserr("Can't open a queue\n"); printf("Queue ID is %ld\n",id); exit(0); } static int openqueue(key) /* return queue ID; create if necessary */ long key; { static struct{ long key; int qid; }queues[MAXOPEN]; int i, avail, qid; extern int errno; avail = -1; for(i=0; i < MAXOPEN; i++){ if(queues[i].key == key) return(queues[i].qid); if(queues[i].key == 0 && avail == -1) avail=i; } if(avail == -1){ errno=0; return(-1); } if((qid=msgget(key,0666 | IPC_CREAT))== -1) return(-1); queues[avail].key = key; queues[avail].qid = qid; return(qid); } syserr(msg) char *msg; { extern int errno, sys_nerr; extern char *sys_errlist[]; fprintf(stderr,"ERROR: %s (%d", msg, errno); if(errno > 0 && errno < sys_nerr) fprintf(stderr, ";%s)\n", sys_errlist[errno]); else fprintf(stderr,")\n"); exit(1); } SHAR_EOF if test -f 'rec.c' then echo shar: over-writing existing file "'rec.c'" fi cat << \SHAR_EOF > 'rec.c' /*receive.c*/ #include #include #include #include #define MSGSIZE 100 struct foo { long mtype; /* message type */ char mtext[100]; /* message text */ }; struct foo buf; main(argc,argv) int argc; char *argv[]; { int qid; int ret; int syserr(); /* check to see if the message queue has been opened, and get the queue ID number */ if((qid=msgget(atoi(argv[1]),0666 & ~IPC_CREAT))== -1) syserr("Queue was not open!\n"); printf("Got a qid of %d\n",qid); /*set the message type*/ buf.mtype=1; /*get the message from queue */ if((msgrcv(qid,&buf,sizeof(buf) - sizeof(buf.mtype),0L,0)) == -1){ printf("Return was %d\n",ret); syserr("Can't read the queue\n"); } printf("Return was %d\n",ret); printf("%s\n",buf.mtext); exit(0); } syserr(msg) char *msg; { extern int errno, sys_nerr; extern char *sys_errlist[]; fprintf(stderr,"ERROR: %s (%d", msg, errno); if(errno > 0 && errno < sys_nerr) fprintf(stderr, ";%s)\n", sys_errlist[errno]); else fprintf(stderr,")\n"); exit(1); } SHAR_EOF if test -f 'send.c' then echo shar: over-writing existing file "'send.c'" fi cat << \SHAR_EOF > 'send.c' /*send.c*/ #include #include #include #include #define MSGSIZE 100 struct foo { long mtype; /* message type */ char mtext[100]; /* message text */ }; struct foo BUF; main(argc,argv) int argc; char *argv[]; { int qid; int ret; int syserr(); /*see if the queue is open, and get the queue ID */ if((qid=msgget(atoi(argv[1]),0666 & ~IPC_CREAT))== -1) syserr("Queue was not open!\n"); /*set the message type*/ BUF.mtype = 1; sprintf(BUF.mtext,"%s\0",argv[2]); /*put the message in queue*/ if((ret=msgsnd(qid,&BUF,sizeof(BUF) - sizeof(BUF.mtype),0)) == -1) syserr("Can't send the queue\n"); printf("Return was %d\n",ret); printf("Message queued successfully\n"); exit(0); } syserr(msg) char *msg; { extern int errno, sys_nerr; extern char *sys_errlist[]; fprintf(stderr,"ERROR: %s (%d", msg, errno); if(errno > 0 && errno < sys_nerr) fprintf(stderr, ";%s)\n", sys_errlist[errno]); else fprintf(stderr,")\n"); exit(1); } SHAR_EOF # End of shell archive exit 0