date and time created 87/02/05 15:19:17 by slatteng
[unix-history] / usr / src / usr.bin / talk / ctl_transact.c
CommitLineData
d0aeaf5a
DF
1/*
2 * Copyright (c) 1983 Regents of the University of California.
3 * All rights reserved. The Berkeley software License Agreement
4 * specifies the terms and conditions for redistribution.
5 */
6
963ce42e 7#ifndef lint
4fa2ac2d 8static char sccsid[] = "@(#)ctl_transact.c 5.2 (Berkeley) %G%";
d0aeaf5a 9#endif not lint
963ce42e 10
0328946e
MK
11#include "talk_ctl.h"
12#include <sys/time.h>
13
963ce42e 14#define CTL_WAIT 2 /* time to wait for a response, in seconds */
0328946e 15
963ce42e
MK
16/*
17 * SOCKDGRAM is unreliable, so we must repeat messages if we have
18 * not recieved an acknowledgement within a reasonable amount
19 * of time
20 */
4fa2ac2d 21ctl_transact(target, msg, type, rp)
963ce42e
MK
22 struct in_addr target;
23 CTL_MSG msg;
24 int type;
4fa2ac2d 25 CTL_RESPONSE *rp;
0328946e 26{
4fa2ac2d 27 int read_mask, ctl_mask, nready, cc;
963ce42e
MK
28 struct timeval wait;
29
963ce42e
MK
30 msg.type = type;
31 daemon_addr.sin_addr = target;
32 daemon_addr.sin_port = daemon_port;
33 ctl_mask = 1 << ctl_sockt;
0328946e
MK
34
35 /*
4fa2ac2d
KM
36 * Keep sending the message until a response of
37 * the proper type is obtained.
0328946e 38 */
0328946e 39 do {
3f3b4df0
JB
40 wait.tv_sec = CTL_WAIT;
41 wait.tv_usec = 0;
4fa2ac2d 42 /* resend message until a response is obtained */
963ce42e 43 do {
4fa2ac2d
KM
44 cc = sendto(ctl_sockt, (char *)&msg, sizeof (msg), 0,
45 &daemon_addr, sizeof (daemon_addr));
46 if (cc != sizeof (msg)) {
963ce42e
MK
47 if (errno == EINTR)
48 continue;
49 p_error("Error on write to talk daemon");
50 }
51 read_mask = ctl_mask;
4fa2ac2d
KM
52 nready = select(32, &read_mask, 0, 0, &wait);
53 if (nready < 0) {
963ce42e
MK
54 if (errno == EINTR)
55 continue;
56 p_error("Error waiting for daemon response");
57 }
58 } while (nready == 0);
4fa2ac2d
KM
59 /*
60 * Keep reading while there are queued messages
61 * (this is not necessary, it just saves extra
62 * request/acknowledgements being sent)
963ce42e
MK
63 */
64 do {
4fa2ac2d 65 cc = recv(ctl_sockt, (char *)rp, sizeof (*rp), 0);
963ce42e
MK
66 if (cc < 0) {
67 if (errno == EINTR)
68 continue;
69 p_error("Error on read from talk daemon");
70 }
71 read_mask = ctl_mask;
72 /* an immediate poll */
73 timerclear(&wait);
74 nready = select(32, &read_mask, 0, 0, &wait);
4fa2ac2d
KM
75 } while (nready > 0 && (rp->vers != TALK_VERSION ||
76 rp->type != type));
77 } while (rp->vers != TALK_VERSION || rp->type != type);
78 rp->id_num = ntohl(rp->id_num);
79 rp->addr.sa_family = ntohs(rp->addr.sa_family);
0328946e 80}