]> git.cameronkatri.com Git - bsdgames-darwin.git/blob - hunt/huntd/faketalk.c
Remove uses of __P.
[bsdgames-darwin.git] / hunt / huntd / faketalk.c
1 /* $NetBSD: faketalk.c,v 1.9 2004/01/27 20:30:29 jsm Exp $ */
2 /*
3 * Copyright (c) 1983-2003, Regents of the University of California.
4 * All rights reserved.
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions are
8 * met:
9 *
10 * + Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * + Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
15 * + Neither the name of the University of California, San Francisco nor
16 * the names of its contributors may be used to endorse or promote
17 * products derived from this software without specific prior written
18 * permission.
19 *
20 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
21 * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
22 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
23 * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
24 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
25 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
26 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
27 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
28 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
29 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
30 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31 */
32
33 #include <sys/cdefs.h>
34 #ifndef lint
35 __RCSID("$NetBSD: faketalk.c,v 1.9 2004/01/27 20:30:29 jsm Exp $");
36 #endif /* not lint */
37
38 #include "bsd.h"
39 #include "hunt.h"
40
41 #if defined(TALK_43) || defined(TALK_42)
42
43 # include <sys/time.h>
44 # include <sys/wait.h>
45 # include <ctype.h>
46 # include <netdb.h>
47 # include <signal.h>
48 # include <stdio.h>
49 # include <string.h>
50 # include <unistd.h>
51 # include "talk_ctl.h"
52
53 # define TRUE 1
54 # define FALSE 0
55
56 /* defines for fake talk message to announce start of game */
57 # ifdef TALK_43
58 # define MASQUERADE "\"Hunt Game\""
59 # else
60 # define MASQUERADE "HuntGame"
61 # endif
62 # define RENDEZVOUS "hunt-players"
63 # define ARGV0 "HUNT-ANNOUNCE"
64
65 extern char *my_machine_name;
66 extern char *First_arg, *Last_arg;
67 extern char **environ;
68
69 static void do_announce(char *);
70 SIGNAL_TYPE exorcise(int);
71 /*
72 * exorcise - disspell zombies
73 */
74
75 SIGNAL_TYPE
76 exorcise(dummy)
77 int dummy;
78 {
79 (void) wait(0);
80 }
81
82 /*
83 * query the local SMTP daemon to expand the RENDEZVOUS mailing list
84 * and fake a talk request to each address thus found.
85 */
86
87 void
88 faketalk()
89 {
90 struct servent *sp;
91 char buf[BUFSIZ];
92 FILE *f;
93 int service; /* socket of service */
94 struct sockaddr_in des; /* address of destination */
95 char *a, *b;
96
97 (void) signal(SIGCHLD, exorcise);
98
99 if (fork() != 0)
100 return;
101
102 (void) signal(SIGINT, SIG_IGN);
103 (void) signal(SIGPIPE, SIG_IGN);
104
105 /*
106 * change argv so that a ps shows ARGV0
107 */
108 *environ = NULL;
109 for (a = First_arg, b = ARGV0; a < Last_arg; a++) {
110 if (*b)
111 *a = *b++;
112 else
113 *a = ' ';
114 }
115
116 /*
117 * initialize "talk"
118 */
119 get_local_name(MASQUERADE);
120 open_ctl();
121
122 /*
123 * start fetching addresses
124 */
125
126 if ((sp = getservbyname("smtp", (char *) NULL)) == NULL) {
127 # ifdef LOG
128 syslog(LOG_ERR, "faketalk: smtp protocol not supported\n");
129 # else
130 warn("faketalk: stmp protocol not supported");
131 # endif
132 _exit(1);
133 }
134
135 memset(&des, 0, sizeof (des));
136 des.sin_family = AF_INET;
137 des.sin_addr = my_machine_addr;
138 des.sin_port = sp->s_port;
139
140 if ((service = socket(des.sin_family, SOCK_STREAM, 0)) < 0) {
141 # ifdef LOG
142 syslog(LOG_ERR, "falktalk: socket");
143 # else
144 warn("falktalk: socket");
145 # endif
146 _exit(1);
147 }
148
149 if (connect(service, (struct sockaddr *) &des, sizeof(des)) != 0) {
150 # ifdef LOG
151 syslog(LOG_ERR, "faketalk: connect");
152 # else
153 warn("faketalk: connect");
154 # endif
155 _exit(1);
156 }
157 if ((f = fdopen(service, "r")) == NULL) {
158 # ifdef LOG
159 syslog(LOG_ERR, "fdopen failed\n");
160 # else
161 warn("faketalk: fdopen");
162 # endif
163 _exit(2);
164 }
165
166 (void) fgets(buf, BUFSIZ, f);
167 (void) sprintf(buf, "HELO HuntGame@%s\r\n", my_machine_name);
168 (void) write(service, buf, strlen(buf));
169 (void) fgets(buf, BUFSIZ, f);
170 (void) sprintf(buf, "EXPN %s@%s\r\n", RENDEZVOUS, my_machine_name);
171 (void) write(service, buf, strlen(buf));
172 while (fgets(buf, BUFSIZ, f) != NULL) {
173 char *s, *t;
174
175 if (buf[0] != '2' || buf[1] != '5' || buf[2] != '0')
176 break;
177 if ((s = strchr(buf + 4, '<')) == NULL)
178 s = buf + 4, t = buf + strlen(buf) - 1;
179 else {
180 s += 1;
181 if ((t = strrchr(s, '>')) == NULL)
182 t = s + strlen(s) - 1;
183 else
184 t -= 1;
185 }
186 while (isspace(*s))
187 s += 1;
188 if (*s == '\\')
189 s += 1;
190 while (isspace(*t))
191 t -= 1;
192 *(t + 1) = '\0';
193 do_announce(s); /* construct and send talk request */
194 if (buf[3] == ' ')
195 break;
196 }
197 (void) shutdown(service, 2);
198 (void) close(service);
199 _exit(0);
200 }
201
202 /*
203 * The msg.id's for the invitations on the local and remote machines.
204 * These are used to delete the invitations.
205 */
206
207 static void
208 do_announce(s)
209 char *s;
210 {
211 CTL_RESPONSE response;
212
213 get_remote_name(s); /* setup his_machine_addr, msg.r_name */
214
215 # ifdef TALK_43
216 # if BSD_RELEASE >= 44
217 msg.ctl_addr = *(struct osockaddr *) &ctl_addr;
218 # else
219 msg.ctl_addr = *(struct sockaddr *) &ctl_addr;
220 # endif
221 msg.ctl_addr.sa_family = htons(msg.ctl_addr.sa_family);
222 # else
223 msg.ctl_addr = ctl_addr;
224 msg.ctl_addr.sin_family = htons(msg.ctl_addr.sin_family);
225 # endif
226 msg.id_num = (int) htonl((u_int32_t) -1); /* an impossible id_num */
227 ctl_transact(his_machine_addr, msg, ANNOUNCE, &response);
228 if (response.answer != SUCCESS)
229 return;
230
231 /*
232 * Have the daemons delete the invitations now that we
233 * have announced.
234 */
235
236 /* we don't care if cleanup doesn't make it. */
237 msg.type = DELETE;
238 msg.id_num = (int) htonl(response.id_num);
239 daemon_addr.sin_addr = his_machine_addr;
240 if (sendto(ctl_sockt, (char *) &msg, sizeof (msg), 0,
241 (struct sockaddr *) &daemon_addr, sizeof(daemon_addr))
242 != sizeof(msg))
243 p_error("send delete remote");
244 }
245 #else
246 void
247 faketalk()
248 {
249 return;
250 }
251 #endif