source: trunk/athena/bin/hostinfo/hostinfo.c @ 9358

Revision 9358, 6.4 KB checked in by ghudson, 28 years ago (diff)
Rename our copy of gehostbyname and gethostbyaddr to avoid conflicting with system versions.
Line 
1/* This program looks up a given hostname on the nameserver and prints
2 * its Internet address, official name, etc.
3 *
4 * Win Treese
5 * MIT Project Athena
6 *
7 * Copyright (c) 1986 by the Massachusetts Institute of Technology.
8 *
9 * Created:     08/29/86
10 *
11 * Modified:    02/03/87        Doug Alan
12 *              Let input also be in form of an internet address.
13 *
14 * Modified:    02/04/87        Doug Alan
15 *              Take flags to control output.
16 *
17 * Modified:    08/20/90        Tom Coppeto
18 *              Added HINFO and MX queries.
19 *              List all returned addresses
20 *              Allow for multiple hostnames.
21 *                     
22 */
23
24#ifndef lint
25static char rcsid[] = "$Header: /afs/dev.mit.edu/source/repository/athena/bin/hostinfo/hostinfo.c,v 1.11 1996-11-15 04:21:02 ghudson Exp $";
26#endif
27
28#include <stdio.h>                      /* Standard IO */
29#include <sys/types.h>                  /* System type defs. */
30#include <netdb.h>                      /* Networking defs. */
31#include <sys/socket.h>                 /* More network defs. */
32#include <string.h>                     /* String fct. declarations. */
33#include <ctype.h>                      /* Character type macros. */
34#include <netinet/in.h>                 /* Internet defs. */
35#include <arpa/inet.h>                  /* For inet_addr */
36
37typedef int bool;
38
39#define TRUE            1
40#define FALSE           0
41#define LINE_LENGTH     128
42#define ERROR           -1
43#define CPNULL          ((char *) NULL)
44
45extern char *gethinfobyname(), *getmxbyname();
46
47static char *usage[] = {
48  "Usage: %s <options> <host-names-or-addresses>",
49  "   -h: output only hostname",
50  "   -a: output only internet address",
51  "   -i: output only host info record",
52  "   -m: output only mx record",
53  "   -q: disable additional query for hinfo & mx",
54  "   -ns <server>: ask specified name server",
55  CPNULL,
56};
57
58char *myname;                           /* How program was invoked. */
59char *hostname = NULL;                  /* desired host */
60
61struct in_addr server_addr;
62int server_specified;
63
64bool h_flag = FALSE;
65bool a_flag = FALSE;
66bool n_flag = FALSE;
67bool m_flag = FALSE;
68bool i_flag = FALSE;
69bool q_flag = FALSE;
70
71static void usage_error();
72static void clear_flags();
73
74main(argc, argv)
75     int argc;
76     char **argv;
77     
78{
79  extern int h_errno;
80  struct hostent *host_entry = (struct hostent *)0;     
81  unsigned long host_address;
82  char *server = NULL;
83  char *hinfo = NULL;
84  char *mx = NULL;
85  int status = 0;
86  int set_server = 0;
87
88  myname = (myname = strrchr(argv[0], '/')) ? myname + 1 : argv[0];
89  if(argc == 1)
90    usage_error();
91  if(strcmp(argv[1], "-help") == 0)
92    usage_error();
93
94  while(*++argv)
95    {
96      if(hostname && !(a_flag || m_flag || i_flag || h_flag))
97        putchar('\n');
98
99      set_server = 0;
100      if(**argv == '-')
101        switch((*argv)[1])
102          {
103          case 'h':
104            clear_flags();
105            h_flag = TRUE;
106            continue;
107          case 'a':
108            clear_flags();
109            a_flag = TRUE;
110            continue;
111          case 'm':
112            clear_flags();
113            m_flag = TRUE;
114            continue;
115          case 'i':
116            clear_flags();
117            i_flag = TRUE;
118            continue;
119          case 'q':
120            clear_flags();
121            q_flag = TRUE;
122            continue;
123          case 'n':
124            if(!*++argv)
125              usage_error();
126            server = *argv;
127            set_server = 1;
128            break;
129          case '?':
130          default:
131            usage_error();
132            break;
133          }
134     
135      hinfo = NULL;
136      mx = NULL;
137      host_address = 0;
138      host_entry = NULL;
139      hostname = *argv;
140     
141      if (*hostname >= '0' && *hostname <= '9')
142        {
143          host_address = inet_addr(hostname);
144          if (host_address)
145            {
146              host_entry = hostinfo_gethostbyaddr((char *) &host_address, 4,
147                                                  AF_INET);
148              if(host_entry)
149                if(set_server)           
150                  memcpy(&server_addr, host_entry->h_addr,
151                         sizeof(server_addr));
152                else             
153                  print_host(host_entry);
154            }
155        }
156
157#ifdef SOLARIS
158      if(!host_entry)
159#else
160      if(host_entry == (struct hostent *)0)
161#endif
162        {
163          host_entry = hostinfo_gethostbyname(hostname);
164          if(host_entry)
165            {
166              if(set_server)
167                memcpy(&server_addr, host_entry->h_addr, sizeof(server_addr));
168              else
169                {
170                  print_host(host_entry);
171                  if(!q_flag)
172                    {
173                      hinfo = (char *) gethinfobyname(hostname);
174                      if(hinfo)
175                        {
176                          if(!h_flag && !a_flag && !m_flag)
177                            {
178                              int i = (int) hinfo[0];
179                              hinfo[i+1] = '/';
180                              if(i_flag)
181                                printf("%s\n", hinfo+1);
182                              else
183                                printf("Host info:\t%s\n", hinfo+1);
184                            }
185                        }
186                      if(!h_flag && !a_flag && !i_flag)
187                        if(mx = (char *) getmxbyname(hostname))
188                          if(m_flag)
189                            printf("%s\n", mx);
190                          else
191                            printf("MX address:\t%s\n", mx);             
192                    }
193                }
194            }
195        }
196 
197      if(host_entry && set_server)
198        {
199          struct in_addr internet_address;
200
201          server_specified = 1;
202          memcpy(&internet_address, host_entry->h_addr_list[0],
203                host_entry->h_length);
204          printf("Using domain server:\nHost name:\t%s\nHost Address\t%s\n",
205                 host_entry->h_name, inet_ntoa(internet_address));
206          continue;
207        }
208
209      if (!host_entry)
210        {
211          switch (h_errno)
212            {
213#ifdef ultrix
214              /* it can return NULL, h_errno == 0 in some cases when
215                 there is no name */
216            case 0:
217#endif
218            case HOST_NOT_FOUND:
219              printf("No such host '%s'.\n",hostname);
220              status = ERROR;
221              continue;
222              break;
223            default:
224            case TRY_AGAIN:
225            case NO_RECOVERY:
226              printf("Cannot resolve name '%s' due to network difficulties.\n",
227                     hostname);
228              status = ERROR;
229              continue;
230              break;
231            case NO_ADDRESS:
232            /* should look up MX record? */
233              /* this error return appears if there is some entry for the
234                 requested name, but no A record (e.g. only an NS record) */
235              printf("No address for '%s'.\n", hostname);
236              status = ERROR;
237              continue;
238              break;
239            }
240        }
241    }
242 
243  exit(status);
244} /* main */
245
246
247print_host(h)
248     struct hostent *h;
249{
250  struct in_addr internet_address;
251  char **alias;                           
252  char **addr;
253
254  if(m_flag || i_flag)
255    return;
256
257  if (h_flag)
258    printf("%s\n", h->h_name);
259  else 
260    {
261      if(!a_flag)
262        {
263          printf("Desired host:\t%s\n", hostname);
264          printf("Official name:\t%s\n", h->h_name);
265          for (alias = h->h_aliases; *alias; alias++)
266            printf("Alias:\t\t%s\n", *alias);
267        }
268         
269      for (addr = h->h_addr_list; *addr; addr++)
270        {
271          memcpy(&internet_address, *addr, h->h_length);
272          if(a_flag)
273            printf("%s\n", inet_ntoa(internet_address));
274          else
275            printf("Host address:\t%s\n", inet_ntoa(internet_address));
276        }
277    }
278}
279
280
281static void
282usage_error()
283{
284  int line = 0;                         /* current line */
285  while (usage[line] != CPNULL)
286    {
287      fprintf (stderr, usage[line++], myname);
288      putc('\n', stderr);
289    }
290  exit(ERROR);
291} /* usage_error */
292
293
294static void
295clear_flags()
296{
297  i_flag = m_flag = h_flag = a_flag = 0;
298}
Note: See TracBrowser for help on using the repository browser.