1 /* $Header: /home/cvs/wavplay/msg.c,v 1.2 1999/12/04 00:01:20 wwg Exp $
2  * Warren W. Gay VE3WWG		Tue Feb 25 22:45:09 1997
3  *
4  * MESSAGE QUEUE FUNCTIONS:
5  *
6  * 	X LessTif WAV Play :
7  *
8  * 	Copyright (C) 1997  Warren W. Gay VE3WWG
9  *
10  * This  program is free software; you can redistribute it and/or modify it
11  * under the  terms  of  the GNU General Public License as published by the
12  * Free Software Foundation version 2 of the License.
13  *
14  * This  program  is  distributed  in  the hope that it will be useful, but
15  * WITHOUT   ANY   WARRANTY;   without   even  the   implied   warranty  of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
17  * Public License for more details (see enclosed file COPYING).
18  *
19  * You  should have received a copy of the GNU General Public License along
20  * with this  program; if not, write to the Free Software Foundation, Inc.,
21  * 675 Mass Ave, Cambridge, MA 02139, USA.
22  *
23  * Send correspondance to:
24  *
25  * 	Warren W. Gay VE3WWG
26  *
27  * Email:
28  *	ve3wwg@yahoo.com
29  *	wgay@mackenziefinancial.com
30  *
31  * $Log: msg.c,v $
32  * Revision 1.2  1999/12/04 00:01:20  wwg
33  * Implement wavplay-1.4 release changes
34  *
35  * Revision 1.1.1.1  1999/11/21 19:50:56  wwg
36  * Import wavplay-1.3 into CVS
37  *
38  * Revision 1.1  1997/04/14 00:20:55  wwg
39  * Initial revision
40  *
41  */
42 static const char rcsid[] = "@(#)msg.c $Revision: 1.2 $";
43 
44 #include <stdio.h>
45 #include <stdlib.h>
46 #include <stdarg.h>
47 #include <unistd.h>
48 #include <errno.h>
49 #include <fcntl.h>
50 #ifndef FREEBSD
51 #include <malloc.h>
52 #endif
53 #include <string.h>
54 #include <memory.h>
55 #include <signal.h>
56 #include <sys/types.h>
57 #include <sys/ipc.h>
58 #include <sys/msg.h>
59 #include <sys/ioctl.h>
60 #include <assert.h>
61 #ifndef FREEBSD
62 #include <linux/soundcard.h>
63 #else
64 #include <sys/soundcard.h>
65 #endif
66 #include "wavplay.h"
67 
68 /*
69  * Create a private message queue:
70  */
71 int
MsgCreate(void)72 MsgCreate(void) {
73 	int ipcid;
74 
75 	if ( (ipcid = msgget(IPC_PRIVATE,IPC_CREAT|0600)) < 0 )
76 		return -1;			/* Failed: check errno */
77 	return ipcid;				/* Success: ipcid */
78 }
79 
80 /*
81  * Close (remove) a message queue:
82  */
83 int
MsgClose(int ipcid)84 MsgClose(int ipcid) {
85 	return msgctl(ipcid,IPC_RMID,NULL);
86 }
87 
88 /*
89  * Send a Client/Server message:
90  *	flags:	0		blocks on write
91  *		IPC_NOWAIT	no blocking on write
92  * Returns 0 if success, else -1
93  */
94 int
MsgSend(int ipcid,SVRMSG * msg,int flags,long msgtype)95 MsgSend(int ipcid,SVRMSG *msg,int flags,long msgtype) {
96 	UInt16 hdrlen;					/* Length of the message header */
97 	UInt16 len;					/* Byte length of char mtext[] */
98 	int z;						/* Status return code */
99 
100 	msg->type = msgtype;				/* 1=client, 2=server */
101 
102 	hdrlen = ((char *) &msg->u - (char *)msg)	/* Get offset to the start of the union */
103 		- sizeof msg->type;			/* The message type does not get included */
104 	len = hdrlen + msg->bytes;			/* The final message length */
105 
106 	while ( (z = msgsnd(ipcid,(struct msgbuf *)msg,len,flags)) < 0 && errno == EINTR )
107 		;				/* Repeat interrupted system calls */
108 
109 	if ( cmdopt_x )
110 		fprintf(stderr,"%5d => Msg %s (%u bytes/%u) : %s\n",
111 			getpid(),
112 			msg_name(msg->msg_type),
113 			(unsigned)msg->bytes,
114 			(unsigned)len,
115 			z >= 0 ? "Sent" : "Not-sent");
116 
117 	return z >= 0 ? 0 : -1;			/* Returns 0 if successful, else check errno */
118 }
119 
120 /*
121  * Receive a Client/Server Message:
122  *	flags:	0		blocks on read
123  *		IPC_NOWAIT	no blocking on read
124  * Returns 0 if success, else -1
125  */
126 int
MsgRecv(int ipcid,SVRMSG * msg,int flags,long msgtype)127 MsgRecv(int ipcid,SVRMSG *msg,int flags,long msgtype) {
128 	int z;
129 
130 	while ( (z = msgrcv(ipcid,(struct msgbuf *)msg,sizeof *msg-sizeof(long),msgtype,flags)) < 0 && errno == EINTR )
131 		; /* Repeat interrupted system calls */
132 
133 	if ( cmdopt_x && (flags == 0 || z >= 0) )
134 		fprintf(stderr,"%5d <= Msg %s (%u bytes/%u) : %s\n",
135 			getpid(),
136 			msg_name(msg->msg_type),
137 			(unsigned)msg->bytes,
138 			(unsigned)z,
139 			z >= 0 ? "Recvd" : "Not-recvd");
140 	return z >= 0 ? 0 : -1;
141 }
142 
143 /*
144  * Return a string name for the enumerated message type:
145  */
146 char *
msg_name(MSGTYP mtyp)147 msg_name(MSGTYP mtyp) {
148 	int x = (int) mtyp;			/* Message type as an (int) */
149 	static char *msg_names[] = {
150 		"ToClnt_Fatal",			/* Fatal server error */
151 		"ToClnt_Ready",			/* Tell client that server is ready */
152 		"ToSvr_Bye",			/* Client tells server to exit */
153 		"ToSvr_Path",			/* Client tells server a pathname */
154 		"ToClnt_Path",			/* Server acks pathname change */
155 		"ToClnt_Stat",			/* Server tells client stat info about pathname */
156 		"ToClnt_WavInfo",		/* Server responds with WAV header info */
157 		"ToSvr_Play",			/* Client tells server to play */
158 		"ToSvr_Pause",			/* Tell server to pause */
159 		"ToSvr_Stop",			/* Tell server to stop */
160 		"ToSvr_Bits",			/* Tell server new bits setting */
161 		"ToClnt_Bits",			/* Tell client current bits setting */
162 		"ToClnt_Settings",		/* Tell client current server settings */
163 		"ToSvr_SamplingRate",		/* Tell server new overriding sampling rate */
164 		"ToSvr_Restore",		/* Tell server to cancel overrides */
165 		"ToSvr_Chan",			/* Tell server new mono/stereo setting */
166 		"ToSvr_Record",			/* Tell server to start recording */
167 		"ToSvr_Debug",			/* Tell server debug mode setting */
168 		"ToClnt_ErrMsg",		/* Tell client an error message from server */
169 		"ToSvr_SemReset",		/* Tell server to reset its locking semaphores */
170                 "ToSvr_StartSample",            /* Tell server where to start playback from */
171                 "ToClnt_PlayState",             /* Tell client state of playback */
172                 "ToClnt_RecState"               /* Tell client state of recording */
173 	};
174 	static char buf[16];
175 
176 	if ( x < 0 || x >= (int) MSGTYP_Last ) {
177 		sprintf(buf,"msgtyp=%d",x);
178 		return buf;			/* Wild message type */
179 	}
180 
181 	return msg_names[x];			/* Proper message type */
182 }
183 
184 /* $Source: /home/cvs/wavplay/msg.c,v $ */
185