Commit 4ef789be authored by pdw's avatar pdw

Added alternative resolver.

Altered display of totals.
parent 0d9a9538
......@@ -5,19 +5,29 @@
# $Id$
#
VERSION = 0.10pre1
# C compiler to use.
#CC = gcc
# Give the location of pcap.h here:
CFLAGS += -I/usr/include/pcap
CFLAGS += -I/usr/include/pcap
# CFLAGS += -I/usr/pkg/include
# CFLAGS += -pg -a
# Give the location of libpcap here if it's not in one of the standard
# directories:
#LDFLAGS += -L/usr/local/lib
# LDFLAGS += -L/usr/local/lib
# LDFLAGS += -pg -a
LDFLAGS += -pthread
#
# Uncomment to use libresolv
#
#CFLAGS += -DUSELIBRESOLV
# This may be needed to use libresolv on Linux.
#LDLIBS += /usr/lib/libresolv.a
# PREFIX specifies the base directory for the installation.
PREFIX = /usr/local
......@@ -31,11 +41,11 @@ MANDIR = man
#MANDIR = share/man # FHS-ish
# You shouldn't need to change anything below this point.
VERSION = 0.9
CFLAGS += -g -Wall "-DIFTOP_VERSION=\"$(VERSION)\""
LDFLAGS += -g
LDFLAGS += -g -pthread
LDLIBS += -lpcap -lcurses -lm
SRCS = iftop.c addr_hash.c hash.c ns_hash.c resolver.c ui.c util.c sorted_list.c\
options.c serv_hash.c threadprof.c
HDRS = addr_hash.h hash.h iftop.h ns_hash.h resolver.h sorted_list.h ui.h options.h sll.h\
......
......@@ -14,11 +14,18 @@
#include <errno.h>
#include <string.h>
#ifdef USELIBRESOLV
#include <arpa/nameser.h>
#include <resolv.h>
#endif
#include "ns_hash.h"
#include "iftop.h"
#include "threadprof.h"
#define RESOLVE_QUEUE_LENGTH 20
struct in_addr resolve_queue[RESOLVE_QUEUE_LENGTH];
......@@ -31,6 +38,83 @@ hash_type* ns_hash;
int head;
int tail;
#ifndef USELIBRESOLV
/**
* Implementation of do_resolve for platforms with working gethostbyaddr_r
*/
char* do_resolve(struct in_addr * addr) {
struct hostent hostbuf, *hp;
size_t hstbuflen = 1024;
char *tmphstbuf;
int res;
int herr;
char * ret = NULL;
/* Allocate buffer, remember to free it to avoid memory leakage. */
tmphstbuf = xmalloc (hstbuflen);
while ((res = gethostbyaddr_r ((char*)addr, sizeof(struct in_addr), AF_INET,
&hostbuf, tmphstbuf, hstbuflen,
&hp, &herr)) == ERANGE) {
/* Enlarge the buffer. */
hstbuflen *= 2;
tmphstbuf = realloc (tmphstbuf, hstbuflen);
}
/* Check for errors. */
if (res || hp == NULL) {
/* failed */
/* Leave the unresolved IP in the hash */
}
else {
ret = xstrdup(hp->h_name);
}
xfree(tmphstbuf);
return ret;
}
#else
/**
* libresolv implementation
*/
char* do_resolve(struct in_addr * addr) {
char msg[PACKETSZ];
char s[35];
int l;
unsigned char* a;
char * ret = NULL;
a = (unsigned char*)addr;
snprintf(s, 35, "%d.%d.%d.%d.in-addr.arpa.",a[3], a[2], a[1], a[0]);
l = res_search(s, C_IN, T_PTR, msg, PACKETSZ);
if(l != -1) {
ns_msg nsmsg;
ns_rr rr;
if(ns_initparse(msg, l, &nsmsg) != -1) {
int c;
int i;
c = ns_msg_count(nsmsg, ns_s_an);
for(i = 0; i < c; i++) {
if(ns_parserr(&nsmsg, ns_s_an, i, &rr) == 0){
if(ns_rr_type(rr) == T_PTR) {
char buf[256];
ns_name_uncompress(msg, msg + l, ns_rr_rdata(rr), buf, 256);
ret = xstrdup(buf);
}
}
}
}
}
return ret;
}
#endif
void resolver_worker(void* ptr) {
struct timespec delay;
/* int thread_number = *(int*)ptr;*/
......@@ -45,12 +129,8 @@ void resolver_worker(void* ptr) {
/* Keep resolving until the queue is empty */
while(head != tail) {
char * hostname;
struct in_addr addr = resolve_queue[tail];
struct hostent hostbuf, *hp;
size_t hstbuflen;
char *tmphstbuf;
int res;
int herr;
/* mutex always locked at this point */
......@@ -58,40 +138,22 @@ void resolver_worker(void* ptr) {
pthread_mutex_unlock(&resolver_queue_mutex);
hstbuflen = 1024;
/* Allocate buffer, remember to free it to avoid memory leakage. */
tmphstbuf = xmalloc (hstbuflen);
while ((res = gethostbyaddr_r ((char*)&addr, sizeof(addr), AF_INET,
&hostbuf, tmphstbuf, hstbuflen,
&hp, &herr)) == ERANGE) {
/* Enlarge the buffer. */
hstbuflen *= 2;
tmphstbuf = realloc (tmphstbuf, hstbuflen);
}
hostname = do_resolve(&addr);
/*
* Store the result in ns_hash
*/
pthread_mutex_lock(&resolver_queue_mutex);
/* Check for errors. */
if (res || hp == NULL) {
/* failed */
/* Leave the unresolved IP in the hash */
}
else {
/* success */
char* hostname;
if(hash_find(ns_hash, &addr, (void**)&hostname) == HASH_STATUS_OK) {
if(hostname != NULL) {
char* old;
if(hash_find(ns_hash, &addr, (void**)&old) == HASH_STATUS_OK) {
hash_delete(ns_hash, &addr);
xfree(hostname);
xfree(old);
}
hostname = strdup(hp->h_name);
hash_insert(ns_hash, &addr, (void*)hostname);
}
xfree(tmphstbuf);
}
}
}
......
......@@ -71,6 +71,8 @@ sorted_list_type screen_list;
host_pair_line totals;
int peaksent, peakrecv, peaktotal;
int showhelphint = 0;
int screen_line_compare(void* a, void* b) {
int i;
host_pair_line* aa = (host_pair_line*)a;
......@@ -354,10 +356,6 @@ void sprint_host(char * line, struct in_addr* addr, unsigned int port, unsigned
}
left = strlen(hostname);
//TODO: Replace this with in-memory hash for speed.
//sent = getservbyport(port, "tcp");
if(port != 0) {
skey.port = port;
skey.protocol = protocol;
......@@ -405,37 +403,11 @@ void ui_print() {
}
clear();
/*
//erase();
move(0, 0);
attron(A_REVERSE);
addstr(" q ");
attroff(A_REVERSE);
addstr(" quit ");
attron(A_REVERSE);
addstr(" r ");
attroff(A_REVERSE);
addstr(options.dnsresolution ? " resolver off "
: " resolver on ");
attron(A_REVERSE);
addstr(" b ");
attroff(A_REVERSE);
addstr(options.showbars ? " bars off "
: " bars on ");
attron(A_REVERSE);
addstr(" s ");
attroff(A_REVERSE);
addstr(options.aggregate_src ? " show src "
: " hide src ");
attron(A_REVERSE);
addstr(" d ");
attroff(A_REVERSE);
addstr(options.aggregate_dest ? " show dest "
: " hide dest ");
*/
/*
* erase() is faster than clear(). Dunno why we switched to
* clear() -pdw 24/10/02
*/
erase();
draw_bar_scale(&y);
......@@ -461,7 +433,6 @@ void ui_print() {
sprint_host(line, &(screen_line->ap.src), screen_line->ap.src_port, screen_line->ap.protocol, L);
//sprintf(line, "%-*s", L, hostname);
mvaddstr(y, x, line);
x += L;
......@@ -483,9 +454,6 @@ void ui_print() {
y = LINES - 3;
//mvaddstr(y, 0, "total: ");
//mvaddstr(y+1, 0, " peak: ");
mvhline(y-1, 0, 0, COLS);
......@@ -521,6 +489,12 @@ void ui_print() {
draw_totals(&totals);
if(showhelphint > 0) {
mvaddstr(0, 0, "Press h for help ");
clrtoeol();
showhelphint--;
}
refresh();
......@@ -627,6 +601,12 @@ void ui_loop() {
case 'P':
options.paused = !options.paused;
break;
case ERR:
break;
default:
showhelphint = 2;
tick(1);
break;
}
tick(0);
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment