Accessing Prefix WhoIs from C
One header, one source file, no dependencies beyond sockets. The same library resolves every hop in LFT and answers every WhoB query: origin AS, prefix, network and organization from Prefix WhoIs, with RIPE RIS, Team Cymru and RADB as alternate sources, one address at a time or 1,024 in a single round trip.
whois.h
/* * whois.h * Layer Four Traceroute * * This file is part of LFT. * * The LFT software provided in this Distribution is * Copyright 2007 VOSTROM Holdings, Inc. * * The full text of our legal notices is contained in the file called * COPYING, included with this Distribution. * */#ifndef WHOIS_H#define WHOIS_Hstruct ip_list_array { struct in_addr ipaddr[1024]; int asn[1024]; char netName[1024][32]; char orgName[1024][100]; char application[1024]; int numItems;};struct ext_ip_list_array { struct in_addr ipaddr[1024]; int asn[1024]; char prefix[1024][20]; char netName[1024][32]; char orgName[1024][100]; char application[1024]; double latitude[1024]; double longitude[1024]; char country[1024][50]; char state[1024][50]; char city[1024][50]; char country_code[1024][4]; char asOrgNameSource[1024][100]; char orgNameSource[1024][100]; char netNameSource[1024][100]; int geoavailable; int numItems;};#ifdef __cplusplusextern "C" {#endif/* Forward-DNS cache entry used when c-ares is compiled in */#ifdef HAVE_CARESstruct w_dns_entry { const char *host; /* pointer to the static server-name string */ struct in_addr addr; /* resolved IPv4 address (zero if unresolved) */ int resolved; /* set to 1 by callback (success or failure) */};#endiftypedef struct _whoissessionparams{ int w_noisy; /* Don't show debug msgs by default */ char pw_serv[256]; /* User can specify his own pwhois server */ char consolidated_asn[256]; /* ASN returned from pwhois */ char consolidated_asp[256]; /* AS-PATH returned from pwhois */ char consolidated_route[256]; /* Prefix returned from pwhois */ char consolidated_orgname[256]; /* OrgName returned from pwhois */ char consolidated_netname[256]; /* NetName returned from pwhois */ char tbuf[128]; time_t tval; void * logprintfCookie;#ifdef HAVE_CARES struct w_dns_entry w_dns_cache[8]; /* pre-resolved whois server addresses */ int w_dns_cache_count; /* number of entries populated */#endif}whois_session_params;/* must be called BEFORE making any queries */whois_session_params * w_init(void);whois_session_params * w_reinit(whois_session_params * wsess);void w_close(whois_session_params * wsess);/* return the origin-asn according to the RADB in "3356" format */int w_lookup_as(whois_session_params * wsess, char *);/* return the origin-asn according to Cyrmu in "3356" format */int w_lookup_as_cymru(whois_session_params * wsess, char *);/* return the origin-asn according to the RIPE RIS in "3356" format */int w_lookup_as_riswhois(whois_session_params * wsess, char *);/* return the origin-asn according to pwhois in "3356" format */int w_lookup_as_pwhois(whois_session_params * wsess, char *);/* return the network name from the registrar in a string */char *w_lookup_netname(whois_session_params * wsess, char *);/* return the organization name from the registrar in a string */char *w_lookup_orgname(whois_session_params * wsess, char *);/* return a pointer to an ip_list_array (see above) containing an 'asn' to each corresponding 'ipaddr' according to Cymru */int w_lookup_as_cymru_bulk(whois_session_params * wsess, struct ip_list_array*);/* return a pointer to an ip_list_array (see above) containing all ip_list_array vars to each corresponding 'ipaddr' according to pwhois */int w_lookup_all_pwhois_bulk(whois_session_params * wsess, struct ip_list_array*);int w_lookup_all_pwhois_bulk_ext(whois_session_params * wsess, struct ext_ip_list_array *iplist);/* return a pointer to an ip_list_array (see above) containing all ip_list_array vars to each corresponding 'ipaddr' according to RIS whois */int w_lookup_all_riswhois_bulk(whois_session_params * wsess, struct ip_list_array*);int w_lookup_all_pwhois(whois_session_params * wsess, char *addr);int w_lookup_all_riswhois(whois_session_params * wsess, char *addr);#ifdef __cplusplus}#endif#endif
Fourteen calls. Two structs.
Every query takes the session from w_init(). Single-address calls return the answer directly; bulk calls fill an ip_list_array (or ext_ip_list_array for prefix and geolocation) indexed by position.
whois_session_params *w_init(void);Create a session. Call once before any query; sets the default server and clears the consolidated result buffers.
whois_session_params *w_reinit(whois_session_params *);Reset a session between unrelated queries without paying the setup cost again.
void w_close(whois_session_params *);Release the session.
int w_lookup_as_pwhois(wsess, char *addr);Origin ASN for an address from Prefix WhoIs, as a plain integer (3356). Also fills consolidated_asp, _route, _orgname and _netname in the session.
int w_lookup_as(wsess, char *addr);Origin ASN according to the RADB routing registry.
int w_lookup_as_cymru(wsess, char *addr);Origin ASN according to Team Cymru.
int w_lookup_as_riswhois(wsess, char *addr);Origin ASN according to RIPE NCC RIS.
char *w_lookup_netname(wsess, char *addr);Network name from the registrar.
char *w_lookup_orgname(wsess, char *addr);Organization name from the registrar.
int w_lookup_all_pwhois(wsess, char *addr);One round trip for everything Prefix WhoIs knows about one address.
int w_lookup_all_pwhois_bulk(wsess, struct ip_list_array *);Fill an ip_list_array — up to 1,024 addresses — with ASN, network and organization in a single bulk query. This is what LFT uses to annotate a whole trace at once.
int w_lookup_all_pwhois_bulk_ext(wsess, struct ext_ip_list_array *);The bulk query with the extended record: prefix, geolocation (latitude, longitude, city, region, country) and the source of each name.
int w_lookup_as_cymru_bulk(wsess, struct ip_list_array *);Bulk origin-AS lookups via Team Cymru.
int w_lookup_all_riswhois_bulk(wsess, struct ip_list_array *);Bulk lookups via RIPE NCC RIS.
A minimal program
Link whois.c into your build, include the header, and:
#include "whois.h" whois_session_params *w = w_init(); int asn = w_lookup_as_pwhois(w, "4.2.2.1"); printf("%s is announced by AS%d (%s)\n", "4.2.2.1", asn, w->consolidated_orgname); w_close(w); // → 4.2.2.1 is announced by AS3356 (Level 3 Parent, LLC)