1 /* vi: set sw=4 ts=4: */
3 * whois - tiny client for the whois directory service
5 * Copyright (c) 2011 Pere Orga <gotrunks@gmail.com>
6 * Licensed under GPLv2 or later, see file LICENSE in this source tree.
13 //config: bool "whois (6.6 kb)"
16 //config: whois is a client for the whois directory service
18 //applet:IF_WHOIS(APPLET(whois, BB_DIR_USR_BIN, BB_SUID_DROP))
20 //kbuild:lib-$(CONFIG_WHOIS) += whois.o
22 //usage:#define whois_trivial_usage
23 //usage: "[-i] [-h SERVER] [-p PORT] NAME..."
24 //usage:#define whois_full_usage "\n\n"
25 //usage: "Query WHOIS info about NAME\n"
26 //usage: "\n -i Show redirect results too"
27 //usage: "\n -h,-p Server to query"
35 static char *query(const char *host, int port, const char *domain)
47 printf("[Querying %s:%d '%s%s']\n", host, port, pfx, domain);
48 fd = create_and_connect_stream_or_die(host, port);
50 fdprintf(fd, "%s%s\r\n", pfx, domain);
51 fp = xfdopen_for_read(fd);
53 while (fgets(linebuf, sizeof(linebuf), fp)) {
54 unsigned len = strcspn(linebuf, "\r\n");
55 linebuf[len++] = '\n';
57 buf = xrealloc(buf, bufpos + len + 1);
58 memcpy(buf + bufpos, linebuf, len);
62 if (!redir || !success) {
66 success = is_prefixed_with(linebuf, "domain:")
67 || is_prefixed_with(linebuf, "domain name:");
70 char *p = is_prefixed_with(linebuf, "whois server:");
72 p = is_prefixed_with(linebuf, "whois:");
74 redir = xstrdup(skip_whitespace(p));
78 fclose(fp); /* closes fd too */
79 if (!success && !pfx[0]) {
81 * Looking at /etc/jwhois.conf, some whois servers use
82 * "domain = DOMAIN", "DOMAIN ID <DOMAIN>"
83 * and "domain=DOMAIN_WITHOUT_LAST_COMPONENT"
84 * formats, but those are rare.
85 * (There are a few even more contrived ones.)
86 * We are trying only "domain DOMAIN", the typical one.
94 if (redir && strcmp(redir, host) == 0) {
95 /* Redirect to self does not count */
99 if (!redir || (option_mask32 & OPT_i)) {
100 /* Output saved text */
101 printf("[%s]\n%s", host, buf ? buf : "");
107 static void recursive_query(const char *host, int port, const char *domain)
109 char *free_me = NULL;
112 redir = query(host, port, domain);
115 printf("[Redirected to %s]\n", redir);
116 host = free_me = redir;
122 /* One of "big" whois implementations has these options:
125 * jwhois version 4.0, Copyright (C) 1999-2007 Free Software Foundation, Inc.
126 * -v, --verbose verbose debug output
127 * -c FILE, --config=FILE use FILE as configuration file
128 * -h HOST, --host=HOST explicitly query HOST
129 * -n, --no-redirect disable content redirection
130 * -s, --no-whoisservers disable whois-servers.net service support
131 * -a, --raw disable reformatting of the query
132 * -i, --display-redirections display all redirects instead of hiding them
133 * -p PORT, --port=PORT use port number PORT (in conjunction with HOST)
134 * -r, --rwhois force an rwhois query to be made
135 * --rwhois-display=DISPLAY sets the display option in rwhois queries
136 * --rwhois-limit=LIMIT sets the maximum number of matches to return
138 * Example of its output:
140 * [Querying whois.verisign-grs.com]
141 * [Redirected to whois.corporatedomains.com]
142 * [Querying whois.corporatedomains.com]
143 * [whois.corporatedomains.com]
144 * ...text of the reply...
146 * With -i, reply from each server is printed, after all redirects are done:
147 * [Querying whois.verisign-grs.com]
148 * [Redirected to whois.corporatedomains.com]
149 * [Querying whois.corporatedomains.com]
150 * [whois.verisign-grs.com]
151 * ...text of the reply...
152 * [whois.corporatedomains.com]
153 * ...text of the reply...
155 * With -a, no "DOMAIN" -> "domain DOMAIN" transformation is attempted.
157 * With -n, the first reply is shown, redirects are not followed:
158 * [Querying whois.verisign-grs.com]
159 * [whois.verisign-grs.com]
160 * ...text of the reply...
163 int whois_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
164 int whois_main(int argc UNUSED_PARAM, char **argv)
167 const char *host = "whois.iana.org";
169 getopt32(argv, "^" "ih:p:+" "\0" "-1", &host, &port);
173 recursive_query(host, port, *argv);