]> asedeno.scripts.mit.edu Git - 1ts-debian.git/blob - zephyr/clients/zstat/zstat.c
r4275@bucket (orig r265): kcr | 2008-01-21 02:57:32 -0500
[1ts-debian.git] / zephyr / clients / zstat / zstat.c
1 /* This file is part of the Project Athena Zephyr Notification System.
2  * It contains the zstat program.
3  *
4  *      Created by:     David C. Jedlinsky
5  *
6  *      $Id$
7  *
8  *      Copyright (c) 1987,1988 by the Massachusetts Institute of Technology.
9  *      For copying and distribution information, see the file
10  *      "mit-copyright.h". 
11  */
12
13 /* There should be library interfaces for the operations in zstat; for now,
14  * however, zstat is more or less internal to the Zephyr system. */
15 #include <internal.h>
16
17 #include <sys/socket.h>
18 #include <netinet/in.h>
19 #include <arpa/inet.h>
20 #include "zserver.h"
21
22 #if !defined(lint) && !defined(SABER)
23 static const char rcsid_zstat_c[] = "$Id$";
24 #endif
25
26 const char *hm_head[] = {
27     "Current server =",
28     "Items in queue:",
29     "Client packets received:",
30     "Server packets received:",
31     "Server changes:",
32     "Version:",
33     "Looking for a new server:",
34     "Time running:",
35     "Size:",
36     "Machine type:"
37 };
38 #define HM_SIZE (sizeof(hm_head) / sizeof (char *))
39 const char *srv_head[] = { 
40     "Current server version =",
41     "Packets handled:",
42     "Uptime:",
43     "Server states:",
44 };
45 #define SRV_SIZE        (sizeof(srv_head) / sizeof (char *))
46
47 int outoftime = 0;
48
49 int serveronly = 0,hmonly = 0;
50 u_short srv_port;
51
52 void usage(char *);
53 void do_stat(char *);
54 int srv_stat(char *);
55 int hm_stat(char *, char *);
56
57 RETSIGTYPE
58 timeout(int ignored)
59 {
60         outoftime = 1;
61 }
62
63 int
64 main(int argc,
65      char *argv[])
66 {
67         Code_t ret;
68         char hostname[MAXHOSTNAMELEN];
69         int optchar;
70         struct servent *sp;
71         extern char *optarg;
72         extern int optind;
73
74         if ((ret = ZInitialize()) != ZERR_NONE) {
75                 com_err("zstat", ret, "initializing");
76                 exit(-1);
77         }
78
79         if ((ret = ZOpenPort((u_short *)0)) != ZERR_NONE) {
80                 com_err("zstat", ret, "opening port");
81                 exit(-1);
82         }
83
84         while ((optchar = getopt(argc, argv, "sh")) != EOF) {
85                 switch(optchar) {
86                 case 's':
87                         serveronly++;
88                         break;
89                 case 'h':
90                         hmonly++;
91                         break;
92                 case '?':
93                 default:
94                         usage(argv[0]);
95                         exit(1);
96                 }
97         }
98
99         if (serveronly && hmonly) {
100                 fprintf(stderr,"Only one of -s and -h may be specified\n");
101                 exit(1);
102         }
103
104         sp = getservbyname(SERVER_SVCNAME,"udp");
105         srv_port = (sp) ? sp->s_port : SERVER_SVC_FALLBACK;
106
107         if (optind == argc) {
108                 if (gethostname(hostname, MAXHOSTNAMELEN) < 0) {
109                         com_err("zstat",errno,"while finding hostname");
110                         exit(-1);
111                 }
112                 do_stat(hostname);
113                 exit(0);
114         }
115
116         for (;optind<argc;optind++)
117                 do_stat(argv[optind]);
118
119         exit(0);
120 }
121
122 void
123 do_stat(char *host)
124 {
125         char srv_host[MAXHOSTNAMELEN];
126         
127         if (serveronly) {
128                 (void) srv_stat(host);
129                 return;
130         }
131
132         if (hm_stat(host,srv_host))
133                 return;
134
135         if (!hmonly)
136                 (void) srv_stat(srv_host);
137 }
138
139 int
140 hm_stat(char *host,
141         char *server)
142 {
143         struct in_addr inaddr;
144         Code_t code;
145
146         char *line[20],*mp;
147         int i,nf;
148         struct hostent *hp;
149         time_t runtime;
150         struct tm *tim;
151         ZNotice_t notice;
152         
153         if ((inaddr.s_addr = inet_addr(host)) == (unsigned)(-1)) {
154             if ((hp = gethostbyname(host)) == NULL) {
155                 fprintf(stderr,"Unknown host: %s\n",host);
156                 exit(-1);
157             }
158             (void) memcpy((char *) &inaddr, hp->h_addr, hp->h_length);
159
160             printf("Hostmanager stats: %s\n", hp->h_name);
161         } else {
162             printf("Hostmanager stats: %s\n", host);
163         }
164         
165         if ((code = ZhmStat(&inaddr, &notice)) != ZERR_NONE) {
166             com_err("zstat", code, "getting hostmanager status");
167             exit(-1);
168         }
169         
170         mp = notice.z_message;
171         for (nf=0;mp<notice.z_message+notice.z_message_len;nf++) {
172                 line[nf] = mp;
173                 mp += strlen(mp)+1;
174         }
175
176         (void) strcpy(server,line[0]);
177
178         printf("HostManager protocol version = %s\n",notice.z_version);
179
180         for (i=0; (i < nf) && (i < HM_SIZE); i++) {
181                 if (!strncmp("Time",hm_head[i],4)) {
182                         runtime = atol(line[i]);
183                         tim = gmtime(&runtime);
184                         printf("%s %d days, %02d:%02d:%02d\n", hm_head[i],
185                                 tim->tm_yday,
186                                 tim->tm_hour,
187                                 tim->tm_min,
188                                 tim->tm_sec);
189                 }
190                 else
191                         printf("%s %s\n",hm_head[i],line[i]);
192         }
193
194         printf("\n");
195         
196         ZFreeNotice(&notice);
197         return(0);
198 }
199
200 int
201 srv_stat(char *host)
202 {
203         char *line[20],*mp;
204         int sock,i,nf,ret;
205         struct hostent *hp;
206         struct sockaddr_in sin;
207         ZNotice_t notice;
208         time_t runtime;
209         struct tm *tim;
210 #ifdef _POSIX_VERSION
211         struct sigaction sa;
212 #endif
213                 
214         (void) memset((char *) &sin, 0, sizeof(struct sockaddr_in));
215
216         sin.sin_port = srv_port;
217
218         if ((sock = socket(PF_INET, SOCK_DGRAM, 0)) < 0) {
219                 perror("socket:");
220                 exit(-1);
221         }
222         
223         sin.sin_family = AF_INET;
224
225         if ((sin.sin_addr.s_addr = inet_addr(host)) == (unsigned)(-1)) {
226             if ((hp = gethostbyname(host)) == NULL) {
227                 fprintf(stderr,"Unknown host: %s\n",host);
228                 exit(-1);
229             }
230             (void) memcpy((char *) &sin.sin_addr, hp->h_addr, hp->h_length);
231
232             printf("Server stats: %s\n", hp->h_name);
233         } else {
234             printf("Server stats: %s\n", host);
235         }
236         
237         (void) memset((char *)&notice, 0, sizeof(notice));
238         notice.z_kind = UNSAFE;
239         notice.z_port = 0;
240         notice.z_class = ZEPHYR_ADMIN_CLASS;
241         notice.z_class_inst = "";
242         notice.z_opcode = ADMIN_STATUS;
243         notice.z_sender = "";
244         notice.z_recipient = "";
245         notice.z_default_format = "";
246         notice.z_message_len = 0;
247         
248         if ((ret = ZSetDestAddr(&sin)) != ZERR_NONE) {
249                 com_err("zstat", ret, "setting destination");
250                 exit(-1);
251         }
252         if ((ret = ZSendNotice(&notice, ZNOAUTH)) != ZERR_NONE) {
253                 com_err("zstat", ret, "sending notice");
254                 exit(-1);
255         }
256
257 #ifdef _POSIX_VERSION
258         sigemptyset(&sa.sa_mask);
259         sa.sa_flags = 0;
260         sa.sa_handler = timeout;
261         (void) sigaction(SIGALRM, &sa, (struct sigaction *)0);
262 #else
263         (void) signal(SIGALRM,timeout);
264 #endif
265         outoftime = 0;
266         (void) alarm(10);
267         if (((ret = ZReceiveNotice(&notice, (struct sockaddr_in *) 0))
268             != ZERR_NONE) &&
269             ret != EINTR) {
270                 com_err("zstat", ret, "receiving notice");
271                 return (1);
272         }
273         (void) alarm(0);
274         if (outoftime) {
275                 fprintf(stderr,"No response after 10 seconds.\n");
276                 return (1);
277         } 
278         
279         mp = notice.z_message;
280         for (nf=0;mp<notice.z_message+notice.z_message_len;nf++) {
281                 line[nf] = mp;
282                 mp += strlen(mp)+1;
283         }
284
285         printf("Server protocol version = %s\n",notice.z_version);
286         
287         for (i=0; i < nf; i++) {
288                 if (i < 2)
289                         printf("%s %s\n",srv_head[i],line[i]);
290                 else if (i == 2) { /* uptime field */
291                         runtime = atol(line[i]);
292                         tim = gmtime(&runtime);
293                         printf("%s %d days, %02d:%02d:%02d\n",
294                                srv_head[i],
295                                tim->tm_yday,
296                                tim->tm_hour,
297                                tim->tm_min,
298                                tim->tm_sec);
299                 } else if (i == 3) {
300                         printf("%s\n",srv_head[i]);
301                         printf("%s\n",line[i]);
302                 } else printf("%s\n",line[i]);
303         }
304         printf("\n");
305         
306         (void) close(sock);
307         ZFreeNotice(&notice);
308         return(0);
309 }
310
311 void
312 usage(char *s)
313 {
314         fprintf(stderr,"usage: %s [-s] [-h] [host ...]\n",s);
315         exit(1);
316 }