Codebase list httping / bc3680c
Imported Upstream version 2.4 Abhijith PA 8 years ago
46 changed file(s) with 7592 addition(s) and 0 deletion(s). Raw diff Collapse all Expand all
0 # The GPL applies to this program.
1 # In addition, as a special exception, the copyright holders give
2 # permission to link the code of portions of this program with the
3 # OpenSSL library under certain conditions as described in each
4 # individual source file, and distribute linked combinations
5 # including the two.
6 # You must obey the GNU General Public License in all respects
7 # for all of the code used other than OpenSSL. If you modify
8 # file(s) with this exception, you may extend this exception to your
9 # version of the file(s), but you are not obligated to do so. If you
10 # do not wish to do so, delete this exception statement from your
11 # version. If you delete this exception statement from all source
12 # files in the program, then also delete it here.
13 # $Revision: 278 $
14
15 -include makefile.inc
16
17 # *** configure script ***
18 # support for tcp fast open?
19 #TFO=yes
20 # disable SSL? (no = disable so the default is use openssl)
21 # SSL=no
22 # enable NCURSES interface?
23 #NC=yes
24 # do fft in ncurses interface? (requires libfftw3)
25 #FW=yes
26
27 ############# do not change anything below here #############
28
29 include version
30
31 TARGET=httping
32
33 LOCALEDIR=/usr/share/locale
34
35 DEBUG=yes
36 WFLAGS=-Wall -W -Wextra -pedantic -D_FORTIFY_SOURCE=2
37 OFLAGS=
38 CFLAGS+=$(WFLAGS) $(OFLAGS) -DVERSION=\"$(VERSION)\" -DLOCALEDIR=\"$(LOCALEDIR)\"
39 LDFLAGS+=-lm
40
41 PACKAGE=$(TARGET)-$(VERSION)
42 PREFIX?=/usr
43 BINDIR=$(PREFIX)/bin
44 MANDIR=$(PREFIX)/share/man
45 DOCDIR=$(PREFIX)/share/doc/$(TARGET)
46
47 INSTALL=install
48 INSTALLDIR=$(INSTALL) -m 0755 -d
49 INSTALLBIN=$(INSTALL) -m 0755
50 INSTALLMAN=$(INSTALL) -m 0644
51 INSTALLDOC=$(INSTALL) -m 0644
52 STRIP=/usr/bin/strip
53 RMDIR=/bin/rm -rf
54 MKDIR=/bin/mkdir
55 ARCHIVE=/bin/tar cf -
56 COMPRESS=/bin/gzip -9
57
58 TRANSLATIONS=nl.mo
59
60 OBJS=gen.o http.o io.o error.o utils.o main.o tcp.o res.o socks5.o kalman.o cookies.o help.o colors.o
61
62 MAN_EN=httping.1
63 MAN_NL=httping-nl.1
64
65 DOCS=license.txt license.OpenSSL readme.txt
66
67 ifeq ($(SSL),no)
68 CFLAGS+=-DNO_SSL
69 else
70 OBJS+=mssl.o
71 LDFLAGS+=-lssl -lcrypto
72 endif
73
74 ifeq ($(TFO),yes)
75 CFLAGS+=-DTCP_TFO
76 endif
77
78 ifeq ($(NC),yes)
79 CFLAGS+=-DNC
80 OBJS+=nc.o
81 LDFLAGS+=-lncursesw
82 endif
83
84 ifeq ($(FW),yes)
85 CFLAGS+=-DFW
86 OBJS+=fft.o
87 LDFLAGS+=-lfftw3
88 endif
89
90 ifeq ($(DEBUG),yes)
91 CFLAGS+=-D_DEBUG -ggdb
92 LDFLAGS+=-g
93 endif
94
95 ifeq ($(ARM),yes)
96 CC=arm-linux-gcc
97 endif
98
99 all: $(TARGET) $(TRANSLATIONS)
100
101 $(TARGET): $(OBJS)
102 $(CC) $(WFLAGS) $(OBJS) $(LDFLAGS) -o $(TARGET)
103 #
104 # Oh, blatant plug: http://www.vanheusden.com/wishlist.php
105
106 install: $(TARGET) $(TRANSLATIONS)
107 $(INSTALLDIR) $(DESTDIR)/$(BINDIR)
108 $(INSTALLBIN) $(TARGET) $(DESTDIR)/$(BINDIR)
109 $(INSTALLDIR) $(DESTDIR)/$(MANDIR)/man1
110 $(INSTALLMAN) $(MAN_EN) $(DESTDIR)/$(MANDIR)/man1
111 $(INSTALLDIR) $(DESTDIR)/$(MANDIR)/nl/man1
112 $(INSTALLMAN) $(MAN_NL) $(DESTDIR)/$(MANDIR)/nl/man1
113 $(INSTALLDIR) $(DESTDIR)/$(DOCDIR)
114 $(INSTALLDOC) $(DOCS) $(DESTDIR)/$(DOCDIR)
115 ifneq ($(DEBUG),yes)
116 $(STRIP) $(DESTDIR)/$(BINDIR)/$(TARGET)
117 endif
118 mkdir -p $(DESTDIR)/$(PREFIX)/share/locale/nl/LC_MESSAGES
119 cp nl.mo $(DESTDIR)/$(PREFIX)/share/locale/nl/LC_MESSAGES/httping.mo
120
121 makefile.inc:
122 ./configure
123
124 nl.mo: nl.po
125 msgfmt -o nl.mo nl.po
126
127 clean:
128 $(RMDIR) $(OBJS) $(TARGET) *~ core cov-int *.mo
129
130 distclean: clean
131 rm -f makefile.inc
132
133 package:
134 # source package
135 $(RMDIR) $(PACKAGE)*
136 $(MKDIR) $(PACKAGE)
137 $(INSTALLDOC) *.c *.h configure Makefile *.po version $(MAN_EN) $(MAN_NL) $(DOCS) $(PACKAGE)
138 $(INSTALLBIN) configure $(PACKAGE)
139 $(ARCHIVE) $(PACKAGE) | $(COMPRESS) > $(PACKAGE).tgz
140 $(RMDIR) $(PACKAGE)
141
142 check: makefile.inc
143 cppcheck -v --force -j 3 --enable=all --std=c++11 --inconclusive -I. . 2> err.txt
144 #
145 make clean
146 scan-build make
147
148 coverity: makefile.inc
149 make clean
150 rm -rf cov-int
151 CC=gcc cov-build --dir cov-int make all
152 tar vczf ~/site/coverity/httping.tgz README cov-int/
153 putsite -q
154 /home/folkert/.coverity-hp.sh
0 #include "colors.h"
1
2 const char *c_error = "";
3 const char *c_normal = "";
4 const char *c_very_normal = "";
5 const char *c_red = "";
6 const char *c_blue = "";
7 const char *c_green = "";
8 const char *c_yellow = "";
9 const char *c_magenta = "";
10 const char *c_cyan = "";
11 const char *c_white = "";
12 const char *c_bright = "";
13
14 void set_colors(char nc)
15 {
16 if (nc)
17 {
18 c_red = COLOR_ESCAPE "1";
19 c_blue = COLOR_ESCAPE "2";
20 c_green = COLOR_ESCAPE "3";
21 c_yellow = COLOR_ESCAPE "4";
22 c_magenta = COLOR_ESCAPE "5";
23 c_cyan = COLOR_ESCAPE "6";
24 c_white = COLOR_ESCAPE "7";
25
26 c_bright = COLOR_ESCAPE "8";
27 c_normal = COLOR_ESCAPE "9";
28
29 c_very_normal = COLOR_ESCAPE "7" COLOR_ESCAPE "9";
30
31 c_error = COLOR_ESCAPE "1";
32 }
33 else
34 {
35 c_red = "\033[31;40m";
36 c_blue = "\033[34;40m";
37 c_green = "\033[32;40m";
38 c_yellow = "\033[33;40m";
39 c_magenta = "\033[35;40m";
40 c_cyan = "\033[36;40m";
41 c_white = "\033[37;40m";
42
43 c_bright = "\033[1;40m";
44 c_normal = "\033[0;37;40m";
45
46 c_very_normal = "\033[0m";
47
48 c_error = "\033[1;4;40m";
49 }
50 }
0 extern const char *c_error;
1 extern const char *c_normal;
2 extern const char *c_very_normal;
3 extern const char *c_red;
4 extern const char *c_blue;
5 extern const char *c_green;
6 extern const char *c_yellow;
7 extern const char *c_magenta;
8 extern const char *c_cyan;
9 extern const char *c_white;
10 extern const char *c_bright;
11
12 #define COLOR_ESCAPE "\001"
13
14 void set_colors(char nc);
0 #! /bin/sh
1
2 FILE=`mktemp`
3 FILE2=`mktemp`
4
5 echo \*\*\* HTTPing v`grep VERSION version | cut -d = -f 2` \(`echo $Revision$ | awk '{ print $2; }'`\) configure script \*\*\*
6 echo
7
8 if [ -z "$CC" ]
9 then
10 CC=gcc
11 fi
12
13 F_TFO=0
14 F_NC=0
15 F_OS=0
16 F_FW=0
17 for var in "$@"
18 do
19 case "$var" in
20 --with-tfo)
21 F_TFO=1
22 ;;
23
24 --with-ncurses)
25 F_NC=1
26 ;;
27
28 --with-openssl)
29 F_OS=1
30 ;;
31
32 --with-fftw3)
33 F_FW=1
34 ;;
35
36 --help)
37 echo "--with-tfo force enable tcp fast open"
38 echo "--with-ncurses force enable ncurses"
39 echo "--with-openssl force enable openssl"
40 echo "--with-fftw3 force enable fftw3"
41 exit 0
42 ;;
43
44 *)
45 echo WARNING: Command line parameter \"$var\" is not understood.
46 echo Re-run this script with --help to see a list of switches.
47 ;;
48 esac
49 done
50
51 $CC -O0 -o $FILE test_TFO.c 2> $FILE2
52 if [ $? -eq 0 ] || [ $F_TFO -eq 1 ] ; then
53 echo \+ system supports TCP fast open
54 TFO="TFO=yes"
55 else
56 echo \- this system does NOT support TCP fast open - this is an optional feature
57 TFO=""
58 fi
59
60 $CC -O0 -lncursesw -o $FILE test_ncurses.c 2> $FILE2
61 if [ $? -eq 0 ] || [ $F_NC -eq 1 ] ; then
62 echo \+ system has ncurses development libraries
63 NC="NC=yes"
64 else
65 echo \- this system does NOT have the ncurses development libraries - they are optional
66 NC=""
67 fi
68
69 $CC -O0 -lssl -lcrypto -o $FILE test_openssl.c 2> $FILE2
70 if [ $? -eq 0 ] || [ $F_OS -eq 1 ] ; then
71 echo \+ system has OpenSSL development libraries
72 SSL="SSL=yes"
73 else
74 echo \- this system does NOT have the OpenSSL development libraries - they are optional
75 SSL="SSL=no"
76 fi
77
78 $CC -O0 -lfftw3 -o $FILE test_fftw3.c 2> $FILE2
79 if [ $? -eq 0 ] || [ $F_FW -eq 1 ] ; then
80 echo \+ system has FFTW3 development libraries
81 FW="FW=yes"
82 else
83 echo \- this system does NOT have the FFTW3 development libraries - they are optional and only useful when also including ncurses
84 FW=""
85 fi
86
87 > makefile.inc
88 echo $NC >> makefile.inc
89 echo $SSL >> makefile.inc
90 echo $TFO >> makefile.inc
91 echo $FW >> makefile.inc
92
93 rm -f $FILE $FILE2
94
95 echo
0 #include <stdlib.h>
1 #include <string.h>
2
3 #include "utils.h"
4
5 void add_cookie(char ***cookies, int *n_cookies, char *in)
6 {
7 char *in_copy = strdup(in), *is = strchr(in_copy, '=');
8 int index = 0, found_at = -1;
9
10 if (is)
11 *is = 0x00;
12
13 for(index=0; index<*n_cookies; index++)
14 {
15 char *dummy = strdup((*cookies)[index]);
16
17 is = strchr(dummy, '=');
18 if (is)
19 *is = 0x00;
20
21 if (strcmp(in_copy, dummy) == 0)
22 {
23 found_at = index;
24 free(dummy);
25 break;
26 }
27
28 free(dummy);
29 }
30
31 if (found_at >= 0)
32 {
33 free((*cookies)[found_at]);
34
35 (*cookies)[found_at] = strdup(in);
36 }
37 else
38 {
39 *cookies = (char **)realloc(*cookies, (*n_cookies + 1) * sizeof(char *));
40
41 (*cookies)[*n_cookies] = strdup(in);
42
43 (*n_cookies)++;
44 }
45
46 free(in_copy);
47 }
48
49 void combine_cookie_lists(char ***destc, int *n_dest, char **src, int n_src)
50 {
51 int loop = 0;
52
53 *destc = (char **)realloc(*destc, (*n_dest + n_src) * sizeof(char *));
54
55 for(loop=0; loop<n_src; loop++)
56 (*destc)[*n_dest + loop] = strdup(src[loop]);
57
58 (*n_dest) += n_src;
59 }
60
61 void free_cookies(char **dynamic_cookies, int n_dynamic_cookies)
62 {
63 int index = 0;
64
65 for(index=0; index<n_dynamic_cookies; index++)
66 free(dynamic_cookies[index]);
67
68 free(dynamic_cookies);
69 }
70
71 void get_cookies(const char *headers, char ***dynamic_cookies, int *n_dynamic_cookies, char ***static_cookies, int *n_static_cookies)
72 {
73 int index = 0;
74 char **header_lines = NULL;
75 int n_header_lines = 0;
76
77 split_string(headers, "\r\n", &header_lines, &n_header_lines);
78
79 for(index=0; index<n_header_lines; index++)
80 {
81 char use_static = 0;
82 char *result = NULL;
83 int cparts_index = 0;
84 char **cparts = NULL;
85 int n_cparts = 0;
86
87 if (strncmp(header_lines[index], "Set-Cookie:", 11) != 0)
88 continue;
89
90 split_string(&header_lines[index][12], ";", &cparts, &n_cparts);
91
92 for(cparts_index=0; cparts_index<n_cparts; cparts_index++)
93 {
94 char *part = cparts[cparts_index];
95
96 while(*part == ' ')
97 part++;
98
99 if (strncmp(part, "expires=", 8) == 0)
100 {
101 use_static = 1;
102 continue;
103 }
104
105 if (strncmp(part, "path=", 5) == 0)
106 continue;
107
108 if (strncmp(part, "domain=", 7) == 0)
109 continue;
110
111 if (strncmp(part, "HttpOnly", 8) == 0)
112 continue;
113
114 str_add(&result, "%s ", part);
115 }
116
117 free_splitted_string(cparts, n_cparts);
118
119 if (use_static)
120 add_cookie(static_cookies, n_static_cookies, result);
121 else
122 add_cookie(dynamic_cookies, n_dynamic_cookies, result);
123
124 free(result);
125 }
126
127 free_splitted_string(header_lines, n_header_lines);
128 }
0 void add_cookie(char ***cookies, int *n_cookies, char *in);
1 void combine_cookie_lists(char ***destc, int *n_dest, char **src, int n_src);
2 void free_cookies(char **dynamic_cookies, int n_dynamic_cookies);
3 void get_cookies(const char *headers, char ***dynamic_cookies, int *n_dynamic_cookies, char ***static_cookies, int *n_static_cookies);
0 /* Released under GPLv2 with exception for the OpenSSL library. See license.txt */
1 /* $Revision$ */
2
3 #include <libintl.h>
4 #include <errno.h>
5 #include <stdarg.h>
6 #include <stdio.h>
7 #include <stdlib.h>
8 #include <string.h>
9 #include <sys/types.h>
10 #include <signal.h>
11
12 char last_error[4096] = { 0 };
13
14 void error_exit(char *format, ...)
15 {
16 int e = errno;
17 va_list ap;
18
19 va_start(ap, format);
20 (void)vfprintf(stderr, format, ap);
21 va_end(ap);
22
23 fprintf(stderr, gettext("\n\nerrno=%d which means %s (if applicable)\n"), e, strerror(e));
24
25 exit(1);
26 }
27
28 void set_error(const char *fmt, ...)
29 {
30 int buffer_size = sizeof last_error;
31 va_list ap;
32
33 if (last_error[0])
34 fprintf(stderr, "%s\n", last_error);
35
36 va_start(ap, fmt);
37 if (vsnprintf(last_error, sizeof last_error, fmt, ap) >= buffer_size)
38 error_exit(gettext("Error message '%s' truncated"), last_error);
39 va_end(ap);
40 }
41
42 void clear_error()
43 {
44 last_error[0] = 0x00;
45 }
46
47 char * get_error()
48 {
49 return last_error;
50 }
0 /* Released under GPLv2 with exception for the OpenSSL library. See license.txt */
1 /* $Revision$ */
2
3 void error_exit(const char *format, ...);
4 void set_error(const char *str, ...);
5 void clear_error(void);
6 char * get_error(void);
0 /* $Revision$ */
1 #include <libintl.h>
2 #include <math.h>
3 #include <stdlib.h>
4 #include <string.h>
5 #include <fftw3.h>
6
7 #include "error.h"
8
9 double *pin = NULL;
10 fftw_complex *pout = NULL;
11 fftw_plan plan;
12 int sample_rate = 44100;
13
14 void fft_init(int sample_rate_in)
15 {
16 sample_rate = sample_rate_in;
17
18 pin = (double *)malloc(sizeof(double) * sample_rate_in);
19 if (!pin)
20 error_exit(gettext("failed allocating memory for fft (1)"));
21
22 pout = (fftw_complex *)fftw_malloc(sizeof(fftw_complex) * sample_rate_in + 1);
23 if (!pout)
24 error_exit(gettext("failed allocating memory for fft (2)"));
25
26 /* init fftw */
27 plan = fftw_plan_dft_r2c_1d(sample_rate_in, pin, pout, FFTW_ESTIMATE);
28 if (!plan)
29 error_exit(gettext("failed calculating plan for fft"));
30 }
31
32 void fft_free(void)
33 {
34 if (pin)
35 {
36 fftw_free(pout);
37 free(pin);
38 }
39
40 fftw_destroy_plan(plan);
41 }
42
43 void fft_stop(void)
44 {
45 fftw_cleanup();
46 }
47
48 void fft_do(double *in, double *output_mag, double *output_phase)
49 {
50 int loop = 0;
51
52 memcpy(pin, in, sizeof(double) * sample_rate);
53
54 /* calc fft */
55 fftw_execute(plan);
56
57 for(loop=0; loop<(sample_rate / 2) + 1; loop++)
58 {
59 double real = pout[loop][0];
60 double img = pout[loop][1];
61
62 /* magnitude */
63 output_mag[loop] = sqrt(pow(real, 2.0) + pow(img, 2.0));
64
65 /* phase */
66 output_phase[loop] = (real == 0 && img == 0) ? 0 : atan2(real, img);
67 }
68 }
0 /* $Revision$ */
1 void fft_init(int sample_rate_in);
2 void fft_free(void);
3 void fft_do(double *in, double *output_mag, double *output_phase);
4 void fft_stop(void);
0 /* $Revision$ */
1 #include <math.h>
2 #include <string.h>
3
4 #include "gen.h"
5
6 void init_statst(stats_t *data)
7 {
8 memset(data, 0x00, sizeof(stats_t));
9
10 data -> min = MY_DOUBLE_INF;
11 data -> max = -data -> min;
12 }
13
14 void update_statst(stats_t *data, double in)
15 {
16 data -> cur = in;
17 data -> min = min(data -> min, in);
18 data -> max = max(data -> max, in);
19 data -> avg += in;
20 data -> sd += in * in;
21 (data -> n)++;
22 data -> valid = 1;
23 data -> cur_valid = 1;
24 }
25
26 void reset_statst_cur(stats_t *data)
27 {
28 data -> cur_valid = 0;
29 }
30
31 double calc_sd(stats_t *in)
32 {
33 double avg = 0.0;
34
35 if (in -> n == 0 || !in -> valid)
36 return 0;
37
38 avg = in -> avg / (double)in -> n;
39
40 return sqrt((in -> sd / (double)in -> n) - pow(avg, 2.0));
41 }
42
43 /* Base64 encoding start */
44 const char *alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
45
46 void encode_tryptique(char source[3], char result[4])
47 /* Encode 3 char in B64, result give 4 Char */
48 {
49 int tryptique, i;
50 tryptique = source[0];
51 tryptique *= 256;
52 tryptique += source[1];
53 tryptique *= 256;
54 tryptique += source[2];
55 for (i=0; i<4; i++)
56 {
57 result[3-i] = alphabet[tryptique%64];
58 tryptique /= 64;
59 }
60 }
61
62 int enc_b64(char *source, int source_lenght, char *target)
63 {
64 /* Divide string /3 and encode trio */
65 while (source_lenght >= 3) {
66 encode_tryptique(source, target);
67 source_lenght -= 3;
68 source += 3;
69 target += 4;
70 }
71 /* Add padding to the rest */
72 if (source_lenght > 0) {
73 char pad[3];
74 memset(pad, 0, sizeof pad);
75 memcpy(pad, source, source_lenght);
76 encode_tryptique(pad, target);
77 target[3] = '=';
78 if (source_lenght == 1) target[2] = '=';
79 target += 4;
80 }
81 target[0] = 0;
82 return 1;
83 }
84 /* Base64 encoding END */
0 /* Released under GPLv2 with exception for the OpenSSL library. See license.txt */
1 /* $Revision$ */
2
3 #ifndef __GEN_H__
4 #define __GEN_H__
5
6 #define RC_OK 0
7 #define RC_SHORTREAD -1
8 #define RC_SHORTWRITE -1
9 #define RC_TIMEOUT -2
10 #define RC_CTRLC -3
11 #define RC_INVAL -4
12
13 #define RECV_BUFFER_SIZE (128 * 1024)
14
15 #define SPAM_FILE "/tmp/httping.dat"
16
17 #define MAX_SHOW_SUPPRESSION 3
18
19 #ifdef NO_SSL
20 #define SSL void
21 #define SSL_CTX void
22 #define BIO void
23 #endif
24
25 #define PI (4 * atan(1.0))
26 #define MY_DOUBLE_INF 999999999999999.9
27
28 #ifdef TCP_TFO
29 #ifndef MSG_FASTOPEN
30 #define MSG_FASTOPEN 0x20000000
31 #endif
32
33 #ifndef TCP_FASTOPEN
34 #define TCP_FASTOPEN 23
35 #endif
36 #ifndef TCPI_OPT_SYN_DATA
37 #define TCPI_OPT_SYN_DATA 32
38 #endif
39 #endif
40
41 #define min(x, y) ((x) < (y) ? (x) : (y))
42 #define max(x, y) ((x) > (y) ? (x) : (y))
43
44 typedef struct
45 {
46 double cur, min, avg, max, sd;
47 int n;
48 char valid, cur_valid;
49 } stats_t;
50
51 int enc_b64(char *source, int source_lenght, char *target);
52
53 void init_statst(stats_t *data);
54 void update_statst(stats_t *data, double in);
55 void reset_statst_cur(stats_t *data);
56 double calc_sd(stats_t *in);
57
58 #endif
0 #include <stdio.h>
1 #include <stdlib.h>
2 #include <string.h>
3 #include <unistd.h>
4 #include <sys/utsname.h>
5 #include <libintl.h>
6
7 #include "gen.h"
8 #include "main.h"
9 #include "help.h"
10 #include "utils.h"
11
12 void new_version_alert(void)
13 {
14 char new_version = 0;
15 FILE *fh = fopen(SPAM_FILE, "r");
16 if (!fh)
17 new_version = 1;
18 else
19 {
20 char buffer[4096], *dummy = 0x00;
21
22 fgets(buffer, sizeof buffer, fh);
23
24 fclose(fh);
25
26 dummy = strchr(buffer, '\n');
27 if (dummy)
28 *dummy = 0x00;
29
30 if (strcmp(buffer, VERSION) != 0)
31 new_version = 1;
32 }
33
34 if (new_version)
35 {
36 struct utsname buf;
37 FILE *fh = fopen(SPAM_FILE, "w");
38 if (fh)
39 {
40 fprintf(fh, "%s\n", VERSION);
41
42 fclose(fh);
43 }
44
45 printf("Welcome to the new HTTPing version " VERSION "!\n\n");
46 #ifdef NC
47 printf("Did you know that with -K you can start a fullscreen GUI version with nice graphs and lots more information? And that you can disable the moving graphs with -D?\n");
48 #ifndef FW
49 printf("And if you compile this program with libfftw3, that it can also show a fourier transform of the measured values?\n");
50 #endif
51 #else
52 printf("Did you know that if you compile this program with NCURSES, that it then includes a nice GUI with lots more information and graphs?\n");
53 #endif
54
55 #if !defined(TCP_TFO) && defined(linux)
56 if (uname(&buf) == 0)
57 {
58 char **rparts = NULL;
59 int n_rparts = 0;
60
61 split_string(buf.release, ".", &rparts, &n_rparts);
62
63 if (n_rparts >= 2 && ((atoi(rparts[0]) >= 3 && atoi(rparts[1]) >= 6) || atoi(rparts[0]) >= 4))
64 printf("This program supports TCP Fast Open! (if compiled in and only on Linux kernels 3.6 or more recent) See the readme.txt how to enable this.\n");
65
66 free_splitted_string(rparts, n_rparts);
67 }
68 #endif
69
70 printf("\n\n");
71 }
72 }
73
74 void version(void)
75 {
76 fprintf(stderr, gettext("HTTPing v" VERSION ", (C) 2003-2013 folkert@vanheusden.com\n"));
77 #ifndef NO_SSL
78 fprintf(stderr, gettext(" * SSL support included (-l)\n"));
79 #endif
80
81 #ifdef NC
82 #ifdef FW
83 fprintf(stderr, gettext(" * ncurses interface with FFT included (-K)\n"));
84 #else
85 fprintf(stderr, gettext(" * ncurses interface included (-K)\n"));
86 #endif
87 #endif
88
89 #ifdef TCP_TFO
90 fprintf(stderr, gettext(" * TFO (TCP fast open) support included (-F)\n"));
91 #endif
92 fprintf(stderr, gettext("\n"));
93 }
94
95 void format_help(const char *short_str, const char *long_str, const char *descr)
96 {
97 int par_width = SWITCHES_COLUMN_WIDTH, max_wrap_width = par_width / 2, cur_par_width = 0;
98 int descr_width = max_x - (par_width + 1);
99 char *line = NULL, *p = (char *)descr;
100 char first = 1;
101
102 if (long_str && short_str)
103 str_add(&line, "%-4s / %s", short_str, long_str);
104 else if (long_str)
105 str_add(&line, "%s", long_str);
106 else
107 str_add(&line, "%s", short_str);
108
109 cur_par_width = fprintf(stderr, "%-*s ", par_width, line);
110
111 free(line);
112
113 if (par_width + 1 >= max_x || cur_par_width >= max_x)
114 {
115 fprintf(stderr, "%s\n", descr);
116 return;
117 }
118
119 for(;strlen(p);)
120 {
121 char *n = NULL, *kn = NULL, *copy = NULL;
122 int n_len = 0, len_after_ww = 0, len_before_ww = 0;
123 int str_len = 0, cur_descr_width = first ? max_x - cur_par_width : descr_width;
124
125 while(*p == ' ')
126 p++;
127
128 str_len = strlen(p);
129 if (!str_len)
130 break;
131
132 len_before_ww = min(str_len, cur_descr_width);
133
134 n = &p[len_before_ww];
135 kn = n;
136
137 if (str_len > cur_descr_width)
138 {
139 while (*n != ' ' && n_len < max_wrap_width)
140 {
141 n--;
142 n_len++;
143 }
144
145 if (n_len >= max_wrap_width)
146 n = kn;
147 }
148
149 len_after_ww = (int)(n - p);
150 if (len_after_ww <= 0)
151 break;
152
153 copy = (char *)malloc(len_after_ww + 1);
154 memcpy(copy, p, len_after_ww);
155 copy[len_after_ww] = 0x00;
156
157 if (first)
158 first = 0;
159 else
160 fprintf(stderr, "%*s ", par_width, "");
161
162 fprintf(stderr, "%s\n", copy);
163
164 free(copy);
165
166 p = n;
167 }
168 }
169
170 void usage(const char *me)
171 {
172 char *dummy = NULL, has_color = 0;
173 char host[256] = { 0 };
174
175 /* where to connect to */
176 fprintf(stderr, gettext(" *** where to connect to ***\n"));
177 format_help("-g x", "--url", gettext("URL to ping (e.g. -g http://localhost/)"));
178 format_help("-h x", "--hostname", gettext("hostname to ping (e.g. localhost) - use either -g or -h"));
179 format_help("-p x", "--port", gettext("portnumber (e.g. 80) - use with -h"));
180 format_help("-6", "--ipv6", gettext("use IPv6 when resolving/connecting"));
181 #ifndef NO_SSL
182 format_help("-l", "--use-ssl", gettext("connect using SSL. pinging an https URL automatically enables this setting"));
183 #endif
184 fprintf(stderr, gettext("\n"));
185
186 /* proxy settings */
187 fprintf(stderr, gettext(" *** proxy settings ***\n"));
188 format_help("-x x", "--proxy", gettext("x should be \"host:port\" which are the network settings of the http/https proxy server. ipv6 ip-address should be \"[ip:address]:port\""));
189 format_help("-E", NULL, gettext("fetch proxy settings from environment variables"));
190 format_help(NULL, "--proxy-user x", gettext("username for authentication against proxy"));
191 format_help(NULL, "--proxy-password x", gettext("password for authentication against proxy"));
192 format_help(NULL, "--proxy-password-file x", gettext("read password for proxy authentication from file x"));
193 format_help("-5", NULL, gettext("proxy is a socks5 server"));
194 format_help(NULL, "--proxy-buster x", gettext("adds \"&x=[random value]\" to the request URL"));
195 fprintf(stderr, gettext("\n"));
196
197 /* timing settings */
198 fprintf(stderr, gettext(" *** timing settings ***\n"));
199 format_help("-c x", "--count", gettext("how many times to ping"));
200 format_help("-i x", "--interval", gettext("delay between each ping"));
201 format_help("-t x", "--timeout", gettext("timeout (default: 30s)"));
202 format_help(NULL, "--ai / --adaptive-interval", gettext("execute pings at multiples of interval relative to start, automatically enabled in ncurses output mode"));
203 format_help("-f", "--flood", gettext("flood connect (no delays)"));
204 fprintf(stderr, gettext("\n"));
205
206 /* http settings */
207 fprintf(stderr, gettext(" *** HTTP settings ***\n"));
208 format_help("-Z", "--no-cache", gettext("ask any proxies on the way not to cache the requests"));
209 format_help(NULL, "--divert-connect", gettext("connect to a different host than in the URL given"));
210 format_help(NULL, "--keep-cookies", gettext("return the cookies given by the HTTP server in the following request(s)"));
211 format_help(NULL, "--no-host-header", gettext("do not add \"Host:\"-line to the request headers"));
212 format_help("-Q", "--persistent-connections", gettext("use a persistent connection. adds a 'C' to the output if httping had to reconnect"));
213 format_help("-I x", "--user-agent", gettext("use 'x' for the UserAgent header"));
214 format_help("-R x", "--referer", gettext("use 'x' for the Referer header"));
215 format_help(NULL, "--header", gettext("adds an extra request-header"));
216 fprintf(stderr, gettext("\n"));
217
218 /* network settings */
219 fprintf(stderr, gettext(" *** networking settings ***\n"));
220 format_help(NULL, "--max-mtu", gettext("limit the MTU size"));
221 format_help(NULL, "--no-tcp-nodelay", gettext("do not disable Naggle"));
222 format_help(NULL, "--recv-buffer", gettext("receive buffer size"));
223 format_help(NULL, "--tx-buffer", gettext("transmit buffer size"));
224 format_help("-r", "--resolve-once", gettext("resolve hostname only once (useful when pinging roundrobin DNS: also takes the first DNS lookup out of the loop so that the first measurement is also correct)"));
225 format_help("-W", NULL, gettext("do not abort the program if resolving failed: keep retrying"));
226 format_help("-y x", "--bind-to", gettext("bind to an ip-address (and thus interface) with an optional port"));
227 #ifdef TCP_TFO
228 format_help("-F", "--tcp-fast-open", gettext("\"TCP fast open\" (TFO), reduces the latency of TCP connects"));
229 #endif
230 #ifdef linux
231 format_help(NULL, "--priority", gettext("set priority of packets"));
232 #endif
233 format_help(NULL, "--tos", gettext("set TOS (type of service)"));
234 fprintf(stderr, gettext("\n"));
235
236 /* http authentication */
237 fprintf(stderr, gettext(" *** HTTP authentication ***\n"));
238 format_help("-A", "--basic-auth", gettext("activate (\"basic\") authentication"));
239 format_help("-U x", "--username", gettext("username for authentication"));
240 format_help("-P x", "--password", gettext("password for authentication"));
241 format_help("-T x", NULL, gettext("read the password fom the file 'x' (replacement for -P)"));
242 fprintf(stderr, gettext("\n"));
243
244 /* output settings */
245 fprintf(stderr, gettext(" *** output settings ***\n"));
246 format_help("-s", "--show-statuscodes", gettext("show statuscodes"));
247 format_help("-S", "--split-time", gettext("split measured time in its individual components (resolve, connect, send, etc."));
248 format_help(NULL, "--threshold-red", gettext("from what ping value to show the value in red (must be bigger than yellow), only in color mode (-Y)"));
249 format_help(NULL, "--threshold-yellow", gettext("from what ping value to show the value in yellow"));
250 format_help(NULL, "--threshold-show", gettext("from what ping value to show the results"));
251 format_help(NULL, "--timestamp / --ts", gettext("put a timestamp before the measured values, use -v to include the date and -vv to show in microseconds"));
252 format_help(NULL, "--aggregate x[,y[,z]]", gettext("show an aggregate each x[/y[/z[/etc]]] seconds"));
253 #ifndef NO_SSL
254 format_help("-z", "--show-fingerprint", gettext("show fingerprint (SSL)"));
255 #endif
256 format_help("-v", NULL, gettext("verbose mode"));
257 fprintf(stderr, gettext("\n"));
258
259 /* GET settings */
260 fprintf(stderr, gettext(" *** \"GET\" (instead of HTTP \"HEAD\") settings ***\n"));
261 format_help("-G", "--get-request", gettext("do a GET request instead of HEAD (read the contents of the page as well)"));
262 format_help("-b", "--show-transfer-speed", gettext("show transfer speed in KB/s (use with -G)"));
263 format_help("-B", "--show-xfer-speed-compressed", gettext("like -b but use compression if available"));
264 format_help("-L x", "--data-limit", gettext("limit the amount of data transferred (for -b) to 'x' (in bytes)"));
265 format_help("-X", "--show-kb", gettext("show the number of KB transferred (for -b)"));
266 fprintf(stderr, gettext("\n"));
267
268 /* output mode settings */
269 fprintf(stderr, gettext(" *** output mode settings ***\n"));
270 format_help("-q", "--quiet", gettext("quiet, only returncode"));
271 format_help("-m", "--parseable-output", gettext("give machine parseable output (see also -o and -e)"));
272 format_help("-M", NULL, gettext("json output, cannot be combined with -m"));
273 format_help("-o rc,rc,...", "--ok-result-codes", gettext("what http results codes indicate 'ok' comma seperated WITHOUT spaces inbetween default is 200, use with -e"));
274 format_help("-e x", "--result-string", gettext("string to display when http result code doesn't match"));
275 format_help("-n warn,crit", "--nagios-mode-1 / --nagios-mode-2", gettext("Nagios-mode: return 1 when avg. response time >= warn, 2 if >= crit, otherwhise return 0"));
276 format_help("-N x", NULL, gettext("Nagios mode 2: return 0 when all fine, 'x' when anything failes"));
277 format_help("-C cookie=value", "--cookie", gettext("add a cookie to the request"));
278 format_help("-Y", "--colors", gettext("add colors"));
279 format_help("-a", "--audible-ping", gettext("audible ping"));
280 fprintf(stderr, gettext("\n"));
281
282 /* GUI/ncurses mode */
283 #if defined(NC)
284 fprintf(stderr, gettext(" *** GUI/ncurses mode settings ***\n"));
285 format_help("-K", "--ncurses / --gui", gettext("ncurses/GUI mode"));
286 #if defined(FW)
287 format_help(NULL, "--draw-phase", gettext("draw phase (fourier transform) in gui"));
288 #endif
289 format_help(NULL, "--slow-log", gettext("when the duration is x or more, show ping line in the slow log window (the middle window)"));
290 format_help(NULL, "--graph-limit x", gettext("do not scale to values above x"));
291 format_help("-D", "--no-graph", gettext("do not show graphs (in ncurses/GUI mode)"));
292 fprintf(stderr, gettext("\n"));
293 #endif
294
295 format_help("-V", "--version", gettext("show the version"));
296 fprintf(stderr, gettext("\n"));
297
298 dummy = getenv("TERM");
299 if (dummy)
300 {
301 if (strstr(dummy, "ANSI") || strstr(dummy, "xterm") || strstr(dummy, "screen"))
302 has_color = 1;
303 }
304
305 if (gethostname(host, sizeof host))
306 strcpy(host, "localhost");
307
308 fprintf(stderr, gettext("Example:\n"));
309 fprintf(stderr, "\t%s %s%s -s -Z\n\n", me, host, has_color ? " -Y" : "");
310
311 new_version_alert();
312 }
0 #define SWITCHES_COLUMN_WIDTH 24
1
2 void new_version_alert(void);
3 void version(void);
4 void help_long(void);
5 void usage(const char *me);
0 /* Released under GPLv2 with exception for the OpenSSL library. See license.txt */
1 /* $Revision$ */
2
3 #include <assert.h>
4 #include <stdio.h>
5 #include <string.h>
6 #include <unistd.h>
7 #ifndef NO_SSL
8 #include <openssl/ssl.h>
9 #include "mssl.h"
10 #endif
11
12 #include "gen.h"
13 #include "http.h"
14 #include "io.h"
15 #include "utils.h"
16
17 int get_HTTP_headers(int socket_h, SSL *ssl_h, char **headers, int *overflow, double timeout)
18 {
19 char *term = NULL;
20 int len_in=0, len=4096;
21 char *buffer = (char *)malloc(len + 1);
22 int rc = RC_OK;
23
24 *headers = NULL;
25
26 memset(buffer, 0x00, len);
27
28 for(;;)
29 {
30 int rrc = -1;
31 int now_n = len - len_in;
32
33 #ifndef NO_SSL
34 if (ssl_h)
35 rrc = SSL_read(ssl_h, &buffer[len_in], now_n);
36 else
37 #endif
38 rrc = read_to(socket_h, &buffer[len_in], now_n, timeout);
39
40 if (rrc == 0 || rrc == RC_SHORTREAD) /* socket closed before request was read? */
41 {
42 rc = RC_SHORTREAD;
43 break;
44 }
45 else if (rrc < 0)
46 {
47 free(buffer);
48 return rrc;
49 }
50
51 len_in += rrc;
52
53 assert(len_in >= 0);
54 assert(len_in <= len);
55
56 buffer[len_in] = 0x00;
57
58 if (strstr(buffer, "\r\n\r\n") != NULL)
59 break;
60
61 if (len_in >= len)
62 {
63 len <<= 1;
64 buffer = (char *)realloc(buffer, len + 1);
65 }
66 }
67
68 *headers = buffer;
69
70 term = strstr(buffer, "\r\n\r\n");
71 if (term)
72 *overflow = len_in - (term - buffer + 4);
73 else
74 *overflow = 0;
75
76 return rc;
77 }
78
79 int dumb_get_HTTP_headers(int socket_h, char **headers, double timeout)
80 {
81 int len_in=0, len=4096;
82 char *buffer = (char *)malloc(len);
83 int rc = RC_OK;
84
85 *headers = NULL;
86
87 for(;;)
88 {
89 int rrc = read_to(socket_h, &buffer[len_in], 1, timeout);
90 if (rrc == 0 || rrc == RC_SHORTREAD) /* socket closed before request was read? */
91 {
92 rc = RC_SHORTREAD;
93 break;
94 }
95 else if (rrc == RC_TIMEOUT) /* timeout */
96 {
97 free(buffer);
98 return RC_TIMEOUT;
99 }
100
101 len_in += rrc;
102
103 buffer[len_in] = 0x00;
104 if (memcmp(&buffer[len_in - 4], "\r\n\r\n", 4) == 0)
105 break;
106 if (memcmp(&buffer[len_in - 2], "\n\n", 2) == 0) /* broken proxies */
107 break;
108
109 if (len_in == (len - 1))
110 {
111 len <<= 1;
112 buffer = (char *)realloc(buffer, len);
113 }
114 }
115
116 *headers = buffer;
117
118 return rc;
119 }
0 /* Released under GPLv2 with exception for the OpenSSL library. See license.txt */
1 /* $Revision$ */
2
3 int get_HTTP_headers(int socket_h, SSL *ssl_h, char **headers, int *overflow, double timeout);
4 int dumb_get_HTTP_headers(int socket_h, char **headers, double timeout);
0 .\" Copyright Folkert van Heusden, 2003-2013
1 .\"
2 .\" This file may be copied under the conditions described
3 .\" in the GNU GENERAL PUBLIC LICENSE, version 2
4 .\" that can be found on the website of the free software
5 .\" foundation.
6 .\"
7 .TH HTTPING 1 2013-03 "httping"
8 .SH NAME
9 httping - meten van de latency en doorvoorsnelheid van een http server
10 .SH SAMENVATTING
11 .BI "httping [" opties "]
12 .sp
13 een aantal opties:
14 .BI "[\-g URL] [\-h systeem naam] [\-p port nummer] [\-x proxy systeem naam:port] [\-c aantal] [\-i interval] [\-t duur limiet] [\-s] [\-K] [\-Y]
15 .SH BESCHRIJVING
16 The program
17 Het programma
18 .B httping
19 meet de latency van een http server. Sinds versie 1.0.6 kan ook de dooorvoorsnelheid gemeten worden.
20 .PP
21 .SH OPTIES
22 .TP
23 .B "\-5"
24 De geselecteerde server is een SOCKS5 server.
25 .TP
26 .B "\-6"
27 Schakel IPv6 mode in. Standaard instelling is IPv4.
28 .TP
29 .B "\-a"
30 Hoorbare ping
31 .TP
32 .B "\-b"
33 Gebruik deze optie samen met \-G. HTTPing zal dan de doorvoorsnelheid (in kB/s) tonen.
34 .TP
35 .B "\-B"
36 Gebruik deze optie samen met \-G. HTTPing zal dan de doorvoorsnelheid (in kB/s) tonen. HTTPing zal echter vragen aan de webserver of deze de data comprimeerd.
37 .TP
38 .B "\-c aantal"
39 Hoevaak te pingen.
40 .TP
41 .B "\-D"
42 Teken geen grafieken (in ncurses (\-K) mode).
43 .TP
44 .B "\-e str"
45 Als de status-code anders is dan die ingesteld is met \-o, dan zal 'str' getoond worden.
46 .TP
47 .B "\-E"
48 Haal de proxy instellingen uit omgevings variabelen.
49 .TP
50 .B "\-F"
51 Probeer verbindingen met "TFO (TCP Fast open)" op te zetten. Dit werkt alleen met Linux kernel 3.7 of recenter.
52 .TP
53 .B "\-f"
54 Ping zo snel als mogelijk achter elkaar.
55 .TP
56 .B "\-G"
57 Doe een GET-verzoek in plaats van een HEAD-verzoek. Daarmee wordt ook de pagina-inhoud opgehaald.
58 .TP
59 .B "\-g URL"
60 Kies welke URL gepinged moet worden. Bijvoorbeeld: http://www.microsoft.com/
61 .TP
62 .B "\-h systeem naam"
63 In plaats van een URL kan men ook alleen een systeem naam opgeven.
64 .TP
65 .B "\-I str"
66 Welke "UserAgent" te sturen naar de webserver.
67 .TP
68 .B "\-i interval"
69 Hoeveel seconden (of delen daarvan) te wachten tussen het verzenden van iedere ping.
70 .TP
71 .B "\-K"
72 Gebruik de ncurses gebruikers interface.
73 .TP
74 .B "\-L x"
75 In combinatie met -G zet dit een limiet op hoeveel data er binnengehaald wordt.
76 .TP
77 .B "\-l"
78 Maak een SSL verbinding. Dit vereist een https-URL.
79 .TP
80 .B "\-m"
81 Geef output die makkelijker met een script te bewerken is.
82 .TP
83 .B "\-N x"
84 Nagios-mode 1: geef 1 terug als de gemiddel reaktie snelheid >= "warn" en 2 als die snelheid >= "crit", anders geef 0 terug. Nagios mode 2: geef 0 terug als alles goed ging, anders 'x'.
85 .TP
86 .B "\-n warn,crit"
87 Schakelt HTTPing naar Nagios-plugin mode 1. Geef afsluit code 1 als de gemiddelde response tijd groter is dan 'warn', geef 2 terug als die tijd groter is dan 'crit'. Anders 0.
88 .TP
89 .B "\-o x,x,..."
90 Selecteer de HTTP status-codes die als 'ok' beschouwd worden.
91 .TP
92 .B "\-p portnumber"
93 Gebruik dit on combinatie met h. Het zet het port-nummer om te pingen.
94 .TP
95 .B "\-q"
96 Geef geen uitvoer, alleen een teruggave code.
97 .TP
98 .B "\-R str"
99 Welke "Referer" te zenden naar de webserver.
100 .TP
101 .B "\-r"
102 Eenmalig systeemnaam vertalen (dit is zinvol bij het pingen van een roterende DNS, bovendien haalt het de eerste vertaling uit de ping lus zodat de 1e ping niet een bovengemiddelde tijd duurt).
103 .TP
104 .B "\-S"
105 Toon alle individuele componenten (verbinden, zenden, etc) van de gemeten tijden.
106 .TP
107 .B "\-s"
108 Toon de HTTP statuscodes.
109 .TP
110 .B "\-T x"
111 Lees de toegangscode voor website authenticatie uit bestand 'x'.
112 .TP
113 .B "\-t timeout"
114 Hoelang te wachten op een reactie van de webserver.
115 .TP
116 .B "\-U"
117 Gebruik authenticatie bij toegang tot de website. Combineer dit met \-P of \-T.
118 .TP
119 .B "\-v"
120 Toon meer details.
121 .TP
122 .B "\-W"
123 Stop HTTPing niet als het opzoeken van de server naam niet lukt.
124 .TP
125 .B "\-X"
126 Gebruik deze in combinatie met \-G. Toon hoeveel data er ontvangen werd.
127 .TP
128 .B "\-x proxyhost[:port]
129 Gebruik een proxy server om een verbinding op te zetten.
130 .TP
131 .B "\-Y"
132 Gebruik kleuren.
133 .TP
134 .B "\-z"
135 Toon de vingerafdruk van de X.509 certificaten bij het opzetten van een SSL verbinding.
136 .TP
137 .B "\-\-abbreviate"
138 Kort waardes af wanneer ze groter zijn dan 1000/1000000/etc.
139 .TP
140 .B "\-\-adaptive-interval" or "\-\-ai"
141 Zorg ervoor dat pings steeds met dezelfde interval uitgevoerd worden, relatief tot het start tijdstip. deze instelling wordt automatisch aangezet in "ncurses"\-mode.
142 .TP
143 .B "\-\-aggregates x[,y[,z[,etc.]]]"
144 Toon cumulatief de waardes van x[/y[/etc]] seconden.
145 .TP
146 .B "\-\-divert\-connect x"
147 Gebruik niet de systeemnaam uit de URL om naar te verbinden. Verbind naar 'x'.
148 .TP
149 .B "\-\-draw-phase"
150 Toon fase diagram.
151 .TP
152 .B "\-\-graph\-limit x"
153 Bij het bepalen van de grafiek-bandbreedte: negeer waardes hoger dan x.
154 .TP
155 .B "\-\-header x"
156 Voeg een extra verzoek-regel toe.
157 .TP
158 .B "\-\-keep\-cookies"
159 Als de HTTP server cookies geeft, zend die dan mee terug bij volgende pings.
160 .TP
161 .B "\-\-max\-mtu x"
162 Welke MTU te gebruiken. Kan niet groter zijn dan de MTU van de netwerk adapter.
163 .TP
164 .B "\-\-no\-host\-header"
165 Voeg niet een "Host:"\-regel toe aan het verzoek.
166 .TP
167 .B "\-\-no\-tcp\-nodelay"
168 Zet het Naggle-algorithme niet uit.
169 .TP
170 .B "\-\-priority x"
171 Geef packets een bepaalde prioriteit.
172 .TP
173 .B "\-\-tos x"
174 Configureer de TOS.
175 .TP
176 .B "\-\-proxy\-user x"
177 Gebruikersnaam voor proxy authenticatie.
178 .TP
179 .B "\-\-proxy\-password x"
180 Toegangscode voor proxy authenticatie.
181 .TP
182 .B "\-\-proxy\-password-file x"
183 Lees toegangscode voor proxy authenticatie uit bestand 'x'.
184 .TP
185 .B "\-\-recv-buffer x"
186 Configureer de grootte van de ontvangst buffer.
187 .TP
188 .B "\-\-slow\-log x"
189 Als een ping-tijd meer dan x is, toon het resultaat dan in het middelste venster.
190 .TP
191 .B "\-\-threshold\-red x"
192 Toon metingen in rood als de gemeten waarde meer dan x is.
193 .TP
194 .B "\-\-threshold\-yellow x"
195 Toon metingen in geel als de gemeten waarde meer dan x is.
196 .TP
197 .B "\-\-threshold\-show x"
198 Toon metingen alleen als ze hoger dan x zijn.
199 .TP
200 .B "\-\-timestamp" or "\-\-ts"
201 Voeg een een tijdstempel toe aan de uitvoer. Gebruik -v om ook een datum te zien en \-vv om ook microseconden te zien.
202 .TP
203 .B "\-\-tx-buffer x"
204 Configureer de grootte van de zend-buffer.
205 .TP
206 .B "\-V"
207 Toon versie informatie.
208
209 .SH UITVOER
210 In de -S mode zal iets als "tijd=0.08+24.09+23.17+15.64+0.02=62.98 ms" getoond worden. De eerste waarde is hoe lang het duurde om de systeem naam te vertalen, de 2e waarde hoe lang het duurde om te verbinden, de 3e waarde geeft aan hoe lang het duurde om het verzoek te verzenden en de 4e waarde is hoelang het duurde voordat de http-server een antwoord formuleerde en terugzond. de 5e waarde geeft aan hoelang het duurde om de socket te sluiten.
211
212 .SH GRAFIEK
213 De grafiek in ncurses mode gebruikt een aantal kleuren. Groen: de waarde is minder dan de ondergrens. Rood: de waarde is hoger dan de bovengrens. Blauw: de waarde is gelimiteerd door '--graph-limit'. Cyaan: er is geen meetwaarde.
214
215 .SH TOETSEN
216 Druk <CTRL> + <c> om het programma af te breken. Er zal dan een samenvatting getoond worden.
217 In ncurses mode: <CTRL> + <l> ververst het scherm, H stopt (en hervat) de grafieken en ook q zal het programma stoppen.
218
219 .SH VOORBEELDEN
220 .TP
221 .B "httping \-g http://localhost/"
222 Ping de HTTP server op URL http://localhost/
223 .TP
224 .B "httping \-h localhost \-p 1000"
225 Ping de HTTP server op systeem 'localhost' en port nummer 1000.
226 .TP
227
228 .SH BUGS
229 Geen.
230
231 .SH "ZIE OOK"
232 .BR http://www.vanheusden.com/httping/
233
234 .SH NOTITIES
235 Deze man-page beschrijft
236 .B httping
237 versie 2.3: andere versies kunnen iets of wat verschillen.
238 Stuur a.u.b. correcties, toevingen en foutraporten naar folkert@vanheusden.com
239 Wanneer u een donatie wilt doen, dan kunt u Bitcoins sturen naar: 1N5Sn4jny4xVwTwSYLnf7WnFQEGoVRmTQF
0 .\" Copyright Folkert van Heusden, 2003-2013
1 .\"
2 .\" This file may be copied under the conditions described
3 .\" in the GNU GENERAL PUBLIC LICENSE, version 2
4 .\" that can be found on the website of the free software
5 .\" foundation.
6 .\"
7 .TH HTTPING 1 2013-07 "httping"
8 .SH NAME
9 httping - measure the latency and throughput of a webserver
10 .SH SYNOPSIS
11 .BI "httping [" options "]
12 .sp
13 options:
14 .BI "[\-g url] [\-h hostname] [\-p portnumber] [\-x proxyhost:port] [\-c count] [\-i interval] [\-t timeout] [\-s] [\-G] [\-b] [\-L xferlimit] [\-X] [\-l] [\-z] [\-f] [\-m] [\-o rc,...] [\-e string]"
15 .BI "[\-I useragent string] [\-R referer string] [\-r] [\-n warn,crit] [\-N mode] [\-q] [\-V]"
16 .SH DESCRIPTION
17 The program
18 .B httping
19 lets you measure the latency of a webserver. Since version 1.0.6 also the throughput can be measured.
20 .PP
21 .SH OPTIONS
22 .TP
23 .B "\-5"
24 The proxy server selected is a SOCKS5 server.
25 .TP
26 .B "\-6"
27 Enable IPv6 mode. Default is IPv4.
28 .TP
29 .B "\-a"
30 Audible ping
31 .TP
32 .B "\-b"
33 Use this switch together with '\-G'. When this option is used, the transferspeed (in KB/s) is shown.
34 .TP
35 .B "\-B"
36 Use this switch together with '\-G'. Ask the HTTP server to compress the returned data: this will reduce the influence of the bandwidth of your connection while increasing the influence of the processorpower of the HTTP server.
37 .TP
38 .B "\-c count"
39 How many probes to send before exiting.
40 .TP
41 .B "\-D"
42 Do not draw graphs in ncurses mode (\-K).
43 .TP
44 .B "\-e str"
45 When the status-code differs from the ones selected with '\-o', the given string is displayed.
46 .TP
47 .B "\-E"
48 Retrieve proxy settings from environment variables ('http_proxy' and 'https_proxy').
49 .TP
50 .B "\-F"
51 Attempt TCP Fast Open while trying to connect to a server (for Linux, version 3.7 onwards of the kernel)
52 .TP
53 .B "\-f"
54 Flood ping: do not sit idle between each ping but ping as fast as the computer and network allow you to.
55 .TP
56 .B "\-G"
57 Do a GET request instead of a HEAD request: this means that also the complete page/file must be transferred. Note that in this case you're no longer measuring the latency!
58 .TP
59 .B "\-g url"
60 This selects the url to probe. E.g.: http://localhost/
61 .TP
62 .B "\-h hostname"
63 Instead of '\-g' one can also set a hostname to probe with -h: -h localhost
64 .TP
65 .B "\-I str"
66 UserAgent-string to send to the webserver (instead of 'HTTPing <version>').
67 .TP
68 .B "\-i interval"
69 How many seconds to sleep between every probe sent.
70 .TP
71 .B "\-K"
72 Enable ncurses user interface.
73 .TP
74 .B "\-L x"
75 Use this switch together with '\-G'. Limit the amount of data transferred to 'x'. Note that this only affects the content of the page/file and not the headerdata.
76 .TP
77 .B "\-l"
78 Connect using SSL: for this to work you need to give a 'https'-url or a 443 portnumber.
79 .TP
80 .B "\-m"
81 Show machine readable output (also check '\-o' and '\-e').
82 .TP
83 .B "\-N x"
84 Switches HTTPing to Nagios-plugin mode 2: return 0 when everything is fine, 'x' when anything fails. E.g.: 1 => Nagios warning state, 2 => Nagios critical state.
85 .TP
86 .B "\-n warn,crit"
87 Switches HTTPing to Nagios-plugin mode 1: return exitcode '1' when the average response time is bigger then 'warn', return exitcode '2' when the the average response time is bigger then 'crit'. In all other cases return exitcode '0'.
88 .TP
89 .B "\-o x,x,..."
90 This selects the HTTP status-codes which are regarded as an OK-state (only with '\-m').
91 .TP
92 .B "\-p portnumber"
93 -p can be used together with \-h. \-p selects the portnumber to probe.
94 .TP
95 .B "\-q"
96 Be quiet, only return an exit-code.
97 .TP
98 .B "\-R str"
99 Referer-string to send to the webserver.
100 .TP
101 .B "\-r"
102 Only resolve the hostname once: this takes the resolving out of the loop so that the latency of the DNS is not measured. Also useful when you want to measure only 1 webserver while the DNS returns a different ip-address for each resolve ('roundrobin').
103 .TP
104 .B "\-S"
105 Split measured latency in time to connect and time to exchange a request with the HTTP server.
106 .TP
107 .B "\-s"
108 When a successfull transaction was done, show the HTTP statuscode (200, 404, etc.).
109 .TP
110 .B "\-T x"
111 Read the password for website authentication from file 'x' (instead of entering it on the command line).
112 .TP
113 .B "\-t timeout"
114 How long to wait for answer from the other side.
115 .TP
116 .B "\-U"
117 Enable authentication against website. Set username with \-U, set password with \-P (or \-T to read the password from a file).
118 .TP
119 .B "\-v"
120 Increase verbosity mode. To show standard deviation and dates in output.
121 .TP
122 .B "\-W"
123 Do not abort program if resolving fails.
124 .TP
125 .B "\-X"
126 Use this switch together with '-G'. For each "ping" show the amount of data transferred (excluding the headers).
127 .TP
128 .B "\-x proxyhost[:port]
129 Probe using a proxyserver. Note that you're also measuring the latency of the proxyserver!
130 .TP
131 .B "\-Y"
132 Enable colors
133 .TP
134 .B "\-z"
135 When connecting using SSL, display the fingerprint of the X509 certificate(s) of the peer.
136 .TP
137 .B "\-\-abbreviate"
138 Abbreviate values bigger than thousand, million, billion, etc.
139 .TP
140 .B "\-\-adaptive-interval" or "\-\-ai"
141 (Try to) ping on the same interval. E.g. if interval is set to 1.0 seconds and ping a ping t[n] occurs at 500s with duration 250ms, then the next ping (t[n+1]) will happen at 501 seconds and not at 501.25 seconds. Of course when the ping duration is > bigger than the interval, a ping will be "skipped" (not literally: the sequence number will continue) and t[n+1] will then be e.g. 502s instead of the expected 501s. This is useful for example in the ncurses output mode where an fft is calculated over the ping times.
142 .TP
143 .B "\-\-aggregates x[,y[,z[,etc.]]]"
144 Show aggregates every x[/y[/z[/etc]]] seconds.
145 .TP
146 .B "\-\-divert\-connect x"
147 Ignore the hostname in the URL and connect to 'x' instead. The given URL will be requested at 'x'.
148 .TP
149 .B "\-\-draw-phase"
150 Not only draw the magnitude of the fourier transform, draw the phase as well.
151 .TP
152 .B "\-\-graph\-limit x"
153 If values measured are bigger than x, then they're limitted to x.
154 .TP
155 .B "\-\-header x"
156 Add an additional request-header 'x'.
157 .TP
158 .B "\-\-keep\-cookies"
159 When the server sends a cookie, it will be returned in the next request.
160 .TP
161 .B "\-\-max\-mtu x"
162 Maximum MTU to use. Cannot be larger than network interface MTU.
163 .TP
164 .B "\-\-no\-host\-header"
165 Do not put a "Host:"-header in the request header.
166 .TP
167 .B "\-\-no\-tcp\-nodelay"
168 Do not disable "tcp delay" (Naggle).
169 .TP
170 .B "\-\-priority x"
171 Set priority of packets.
172 .TP
173 .B "\-\-tos x"
174 Set type of service.
175 .TP
176 .B "\-\-proxy\-user x"
177 Use username 'x' to authenticate against proxy (http/socks5) server (optional).
178 .TP
179 .B "\-\-proxy\-password x"
180 Use password 'x' to authenticate against proxy (http/socks5) server (optional).
181 .TP
182 .B "\-\-proxy\-password-file x"
183 Read password from file 'x' to authenticate against proxy (http/socks5) server (optional).
184 .TP
185 .B "\-\-recv-buffer x"
186 Set the size of the receive buffer (in bytes).
187 .TP
188 .B "\-\-slow\-log x"
189 When the duration is x or more, show ping line in the slow log window (the middle window).
190 .TP
191 .B "\-\-threshold\-red x"
192 If the measured threshold is higher than x (and -Y is given), then the shown value is colored red. If you also use --threshold-yellow, then this value must be bigger.
193 .TP
194 .B "\-\-threshold\-yellow x"
195 If the measured threshold is higher than x (and -Y is given), then the shown value is colored yellow.
196 .TP
197 .B "\-\-threshold\-show x"
198 If the measured threshold is higher than x, then the result is shown (default is show always). The value x is in ms.
199 .TP
200 .B "\-\-timestamp" or "\-\-ts"
201 Put a timestamp before the result-lines. Use -v to also show a date.
202 .TP
203 .B "\-\-tx-buffer x"
204 Set the size of the transmit buffer (in bytes).
205 .TP
206 .B "\-V"
207 Show the version and exit.
208
209 .SH OUTPUT
210 In split mode (-S) something like "time=0.08+24.09+23.17+15.64+0.02=62.98 ms" is shown. The first value is the time it took to resolve the hostname (or 'n/a' if it did not resolve in this iteration, e.g. in "resolve once" (-r) mode), then the time it took to connect (or -1 for example in persistent connection (-Q, HTTP v1.1), after that the time it took to put the request on the wire, then the time it took for the HTTP server to process the request and send it back and lastly the time it took to close the connection.
211
212 .SH GRAPH
213 The graph in the ncurses uses colors to encode a meaning. Green: value is less than 1 block. Red: the value did not fit in the graph. Blue: the value was limitted by --graph-limit. Cyan: no measurement for that point in time.
214
215 .SH KEYS
216 Press <CTRL> + <c> to exit the program. It will display a summary of what was measured.
217 In the ncurses gui, press <CTRL> + <l> to forcibly redraw the screen. Press 'H' to halt the graphs (and again to continue). Press 'q' to stop the program (<CTRL> + <c> will work too).
218
219 .SH EXAMPLES
220 .TP
221 .B "httping \-g http://localhost/"
222 Ping the webserver on host 'localhost'.
223 .TP
224 .B "httping \-h localhost \-p 1000"
225 Ping the webserver on host 'localhost' and portnumber 1000.
226 .TP
227 .B "httping \-l \-g https://localhost/"
228 Ping the webserver on host 'localhost' using an SSL connection.
229 .TP
230 .B "httping \-g http://localhost/ -U username -P password"
231 Ping the webserver on host 'localhost' using the Basic HTTP Authentication.
232 .SH BUGS
233 None. This program is totally bug-free.
234
235 .SH "SEE ALSO"
236 .BR http://www.vanheusden.com/httping/
237
238 .SH NOTES
239 This page describes
240 .B httping
241 as found in the httping-2.3 package; other versions may differ slightly.
242 Please mail corrections and additions to folkert@vanheusden.com.
243 Report bugs in the program to folkert@vanheusden.com.
244 Please consider sending bitcoins to 1N5Sn4jny4xVwTwSYLnf7WnFQEGoVRmTQF
+193
-0
io.c less more
0 /* Released under GPLv2 with exception for the OpenSSL library. See license.txt */
1 /* $Revision$ */
2
3 #include <errno.h>
4 #include <libintl.h>
5 #include <fcntl.h>
6 #include <stdlib.h>
7 #include <stdio.h>
8 #include <string.h>
9 #include <syslog.h>
10 #include <sys/time.h>
11 #include <sys/types.h>
12 #include <sys/stat.h>
13 #include <unistd.h>
14
15 #include "gen.h"
16 #include "error.h"
17
18 ssize_t read_to(int fd, char *whereto, size_t len, double timeout)
19 {
20 for(;;)
21 {
22 ssize_t rc;
23 struct timeval to;
24 fd_set rfds;
25
26 FD_ZERO(&rfds);
27 FD_SET(fd, &rfds);
28
29 to.tv_sec = (long)(timeout / 1000.0);
30 to.tv_usec = (long)(timeout * 1000.0) % 1000000;
31
32 rc = select(fd + 1, &rfds, NULL, NULL, &to);
33 if (rc == 0)
34 return RC_TIMEOUT;
35 else if (rc == -1)
36 {
37 if (errno == EAGAIN)
38 continue;
39 if (errno == EINTR)
40 return RC_CTRLC;
41
42 set_error(gettext("myread::select failed: %s"), strerror(errno));
43
44 return RC_SHORTREAD;
45 }
46
47 return read(fd, whereto, len);
48 }
49 }
50
51 ssize_t myread(int fd, char *whereto, size_t len, double timeout)
52 {
53 ssize_t cnt=0;
54
55 while(len>0)
56 {
57 ssize_t rc;
58 struct timeval to;
59 fd_set rfds;
60
61 FD_ZERO(&rfds);
62 FD_SET(fd, &rfds);
63
64 to.tv_sec = (long)(timeout / 1000.0);
65 to.tv_usec = (long)(timeout * 1000.0) % 1000000;
66
67 rc = select(fd + 1, &rfds, NULL, NULL, &to);
68 if (rc == 0)
69 return RC_TIMEOUT;
70 else if (rc == -1)
71 {
72 if (errno == EAGAIN)
73 continue;
74 if (errno == EINTR)
75 return RC_CTRLC;
76
77 set_error(gettext("myread::select failed: %s"), strerror(errno));
78
79 return RC_SHORTREAD;
80 }
81
82 if (FD_ISSET(fd, &rfds))
83 {
84 rc = read(fd, whereto, len);
85
86 if (rc == -1)
87 {
88 if (errno == EAGAIN)
89 continue;
90 if (errno == EINTR)
91 return RC_CTRLC;
92
93 set_error(gettext("myread::read failed: %s"), strerror(errno));
94
95 return RC_SHORTREAD;
96 }
97 else if (rc == 0)
98 break;
99 else
100 {
101 whereto += rc;
102 len -= rc;
103 cnt += rc;
104 }
105 }
106 }
107
108 return cnt;
109 }
110
111 ssize_t mywrite(int fd, char *wherefrom, size_t len, double timeout)
112 {
113 ssize_t cnt=0;
114
115 while(len>0)
116 {
117 ssize_t rc;
118 struct timeval to;
119 fd_set wfds;
120
121 FD_ZERO(&wfds);
122 FD_SET(fd, &wfds);
123
124 to.tv_sec = (long)(timeout / 1000.0);
125 to.tv_usec = (long)(timeout * 1000.0) % 1000000;
126
127 rc = select(fd + 1, NULL, &wfds, NULL, &to);
128 if (rc == 0)
129 return RC_TIMEOUT;
130 else if (rc == -1)
131 {
132 if (errno == EAGAIN)
133 continue;
134 if (errno == EINTR)
135 return RC_CTRLC;
136
137 set_error(gettext("mywrite::select failed: %s"), strerror(errno));
138
139 return RC_SHORTWRITE;
140 }
141
142 rc = write(fd, wherefrom, len);
143
144 if (rc == -1)
145 {
146 if (errno == EAGAIN)
147 continue;
148 if (errno == EINTR)
149 return RC_CTRLC;
150
151 set_error(gettext("mywrite::write failed: %s"), strerror(errno));
152
153 return RC_SHORTWRITE;
154 }
155 else if (rc == 0)
156 break;
157 else
158 {
159 wherefrom += rc;
160 len -= rc;
161 cnt += rc;
162 }
163 }
164
165 return cnt;
166 }
167
168 int set_fd_nonblocking(int fd)
169 {
170 /* set fd to non-blocking */
171 if (fcntl(fd, F_SETFL, O_NONBLOCK) == -1)
172 {
173 fprintf(stderr, gettext("set_fd_nonblocking failed! (%s)\n"), strerror(errno));
174
175 return -1;
176 }
177
178 return 0;
179 }
180
181 int set_fd_blocking(int fd)
182 {
183 /* set fd to blocking */
184 if (fcntl(fd, F_SETFL, 0) == -1)
185 {
186 fprintf(stderr, gettext("set_fd_blocking failed! (%s)\n"), strerror(errno));
187
188 return -1;
189 }
190
191 return 0;
192 }
0 /* Released under GPLv2 with exception for the OpenSSL library. See license.txt */
1 /* $Revision$ */
2
3 ssize_t read_to(int fd, char *whereto, size_t len, double timeout);
4 ssize_t myread(int fd, char *whereto, size_t len, double timeout);
5 ssize_t mywrite(int fd, const char *wherefrom, size_t len, double timeout);
6 int set_fd_nonblocking(int fd);
7 int set_fd_blocking(int fd);
0 /* #define _TEST */
1
2 #include <math.h>
3 #ifdef _TEST
4 #include <stdio.h>
5 #include <stdlib.h>
6 #endif
7
8 double x_est_last = 0.0, P_last = 0.0, Q = 0.0, R = 0.0, K = 0.0, P = 0.0, P_temp = 0.0, x_temp_est = 0.0, x_est = 0.0, z_measured = 0.0, z_real = 0.0, sum_error_kalman = 0.0, sum_error_measure = 0.0;
9 char first = 1;
10
11 void kalman_init(double ideal_value)
12 {
13 /* initial values for the kalman filter */
14 x_est_last = 0;
15 P_last = 0;
16 /* the noise in the system (FIXME?) */
17 Q = 0.022;
18 R = 0.617;
19 z_real = ideal_value; /* 0.5; the ideal value we wish to measure */
20
21 first = 1;
22 }
23
24 double kalman_do(double z_measured)
25 {
26 /* initialize with a measurement */
27 if (first)
28 {
29 first = 0;
30 x_est_last = z_measured;
31 }
32
33 /* do a prediction */
34 x_temp_est = x_est_last;
35 P_temp = P_last + Q;
36 /* calculate the Kalman gain */
37 K = P_temp * (1.0/(P_temp + R));
38 /* measure */
39 /*z_measured = z_real + frand()*0.09; the real measurement plus noise*/
40 /* correct */
41 x_est = x_temp_est + K * (z_measured - x_temp_est);
42 P = (1- K) * P_temp;
43 /* we have our new system */
44
45 #ifdef _TEST
46 printf("Ideal position: %6.3f \n",z_real);
47 printf("Mesaured position: %6.3f [diff:%.3f]\n",z_measured,fabs(z_real-z_measured));
48 printf("Kalman position: %6.3f [diff:%.3f]\n",x_est,fabs(z_real - x_est));
49 #endif
50
51 sum_error_kalman += fabs(z_real - x_est);
52 sum_error_measure += fabs(z_real-z_measured);
53
54 /* update our last's */
55 P_last = P;
56 x_est_last = x_est;
57
58 #ifdef _TEST
59 printf("Total error if using raw measured: %f\n",sum_error_measure);
60 printf("Total error if using kalman filter: %f\n",sum_error_kalman);
61 printf("Reduction in error: %d%% \n",100-(int)((sum_error_kalman/sum_error_measure)*100));
62 #endif
63
64 return x_est;
65 }
66
67 #ifdef _TEST
68 int main(int argc, char *argv[])
69 {
70 kalman_init(0.0);
71
72 for(int loop=0; loop<25; loop++)
73 {
74 double v = drand48();
75 printf("%d] %f %f\n", loop + 1, v, kalman_do(v));
76 }
77
78 return 0;
79 }
80 #endif
0 /* taken (and adapted) from http://www.dzone.com/snippets/simple-kalman-filter-c */
1
2 void kalman_init(double ideal_value);
3 double kalman_do(double value);
0 Please see license.txt.
0 HTTPing is (C) 2003-2013 by folkert@vanheusden.com
1
2 The GPL version 2 applies to this program. That document can be found
3 on the website of the free software foundation.
4
5 In addition, as a special exception, the copyright holder gives
6 permission to link the code of portions of this program with the
7 OpenSSL library under certain conditions as described in each
8 individual source file, and distribute linked combinations
9 including the two.
10 You must obey the GNU General Public License in all respects
11 for all of the code used other than OpenSSL. If you modify
12 file(s) with this exception, you may extend this exception to your
13 version of the file(s), but you are not obligated to do so. If you
14 do not wish to do so, delete this exception statement from your
15 version. If you delete this exception statement from all source
16 files in the program, then also delete it here.
+2442
-0
main.c less more
0 /* Released under GPLv2 with exception for the OpenSSL library. See license.txt */
1 /* $Revision: 278 $ */
2
3 #define _GNU_SOURCE
4 #include <sys/ioctl.h>
5 #include <stdio.h>
6 #include <locale.h>
7 #include <libintl.h>
8 #include <stdlib.h>
9 #include <errno.h>
10 #include <math.h>
11 #include <string.h>
12 #include <signal.h>
13 #include <unistd.h>
14 #include <getopt.h>
15 #include <sys/types.h>
16 #include <sys/socket.h>
17 #include <sys/ioctl.h>
18 #include <netinet/in.h>
19 #include <netinet/tcp.h>
20 #include <netdb.h>
21 #ifndef NO_SSL
22 #include <openssl/ssl.h>
23 #include "mssl.h"
24 #endif
25 #include <arpa/inet.h>
26 #include <time.h>
27 #include <sys/time.h>
28 #if defined(sun) || defined(__sun)
29 #include <sys/termios.h>
30 #endif
31 #ifdef NC
32 #include <ncurses.h>
33 #endif
34
35 #include "gen.h"
36 #include "help.h"
37 #include "colors.h"
38 #include "http.h"
39 #include "io.h"
40 #include "tcp.h"
41 #include "res.h"
42 #include "utils.h"
43 #include "error.h"
44 #include "socks5.h"
45 #ifdef NC
46 #include "nc.h"
47 #endif
48 #include "cookies.h"
49
50 volatile int stop = 0;
51
52 int quiet = 0;
53 char machine_readable = 0;
54 char json_output = 0;
55 char show_ts = 0;
56
57 int max_x = 80, max_y = 24;
58
59 char nagios_mode = 0;
60 char ncurses_mode = 0;
61
62 int fd = -1;
63
64 volatile char got_sigquit = 0;
65
66 void handler_quit(int s)
67 {
68 signal(SIGQUIT, handler_quit);
69
70 got_sigquit = 1;
71 }
72
73 void determine_terminal_size(int *max_y, int *max_x)
74 {
75 struct winsize size;
76
77 *max_x = *max_y = 0;
78
79 if (!isatty(1))
80 {
81 *max_y = 24;
82 *max_x = 80;
83 }
84 #ifdef TIOCGWINSZ
85 else if (ioctl(1, TIOCGWINSZ, &size) == 0)
86 {
87 *max_y = size.ws_row;
88 *max_x = size.ws_col;
89 }
90 #endif
91
92 if (!*max_x || !*max_y)
93 {
94 char *dummy = getenv("COLUMNS");
95 if (dummy)
96 *max_x = atoi(dummy);
97 else
98 *max_x = 80;
99
100 dummy = getenv("LINES");
101 if (dummy)
102 *max_y = atoi(dummy);
103 else
104 *max_y = 24;
105 }
106 }
107
108 void emit_statuslines(double run_time)
109 {
110 #ifdef NC
111 if (ncurses_mode)
112 {
113 time_t t = time(NULL);
114 char *t_str = ctime(&t);
115 char *dummy = strchr(t_str, '\n');
116
117 if (dummy)
118 *dummy = 0x00;
119
120 status_line(gettext("%s, run time: %.3fs, press ctrl + c to stop"), t_str, run_time);
121 }
122 #else
123 (void)run_time;
124 #endif
125 }
126
127 void emit_headers(char *in)
128 {
129 #ifdef NC
130 static char shown = 0;
131 int len_in = -1;
132
133 if (!shown && ncurses_mode && in != NULL && (len_in = strlen(in) - 4) > 0)
134 {
135 int pos = 0, pos_out = 0;
136 char *copy = (char *)malloc(len_in + 1), *dummy = NULL;
137
138 for(pos=0; pos<len_in; pos++)
139 {
140 if (in[pos] != '\r')
141 copy[pos_out++] = in[pos];
142 }
143
144 copy[pos_out] = 0x00;
145
146 /* in case more than the headers were sent */
147 dummy = strstr(copy, "\n\n");
148 if (dummy)
149 *dummy = 0x00;
150
151 slow_log("\n%s", copy);
152
153 free(copy);
154
155 shown = 1;
156 }
157 #else
158 (void)in;
159 #endif
160 }
161
162 void emit_json(char ok, int seq, double start_ts, stats_t *t_resolve, stats_t *t_connect, stats_t *t_request, int http_code, const char *msg, int header_size, int data_size, double Bps, const char *host, const char *ssl_fp, double toff_diff_ts, char tfo_success, stats_t *t_ssl, stats_t *t_write, stats_t *t_close, int n_cookies, stats_t *stats_to, stats_t *tcp_rtt_stats, int re_tx, int pmtu, int recv_tos, stats_t *t_total)
163 {
164 if (seq > 1)
165 printf(", \n");
166 printf("{ ");
167 printf("\"status\" : \"%d\", ", ok);
168 printf("\"seq\" : \"%d\", ", seq);
169 printf("\"start_ts\" : \"%f\", ", start_ts);
170 if (t_resolve!=NULL && t_resolve -> cur_valid)
171 printf("\"resolve_ms\" : \"%e\", ", t_resolve -> cur);
172 else
173 printf("\"resolve_ms\" : \"%e\", ",-1.0);
174 if (t_connect!=NULL && t_connect -> cur_valid)
175 printf("\"connect_ms\" : \"%e\", ", t_connect -> cur);
176 else
177 printf("\"connect_ms\" : \"%e\", ",-1.0);
178 printf("\"request_ms\" : \"%e\", ", t_request -> cur);
179 printf("\"total_ms\" : \"%e\", ", t_total -> cur);
180 printf("\"http_code\" : \"%d\", ", http_code);
181 printf("\"msg\" : \"%s\", ", msg);
182 printf("\"header_size\" : \"%d\", ", header_size);
183 printf("\"data_size\" : \"%d\", ", data_size);
184 printf("\"bps\" : \"%f\", ", Bps);
185 printf("\"host\" : \"%s\", ", host);
186 printf("\"ssl_fingerprint\" : \"%s\", ", ssl_fp ? ssl_fp : "");
187 printf("\"time_offset\" : \"%f\", ", toff_diff_ts);
188 printf("\"tfo_success\" : \"%s\", ", tfo_success ? "true" : "false");
189 if (t_ssl -> cur_valid)
190 printf("\"ssl_ms\" : \"%e\", ", t_ssl -> cur);
191 printf("\"tfo_succes\" : \"%s\", ", tfo_success ? "true" : "false");
192 if (t_ssl !=NULL && t_ssl -> cur_valid)
193 printf("\"ssl_ms\" : \"%e\", ", t_ssl -> cur);
194 printf("\"write\" : \"%e\", ", t_write -> cur);
195 printf("\"close\" : \"%e\", ", t_close -> cur);
196 printf("\"cookies\" : \"%d\", ", n_cookies);
197 if (stats_to != NULL && stats_to -> cur_valid)
198 printf("\"to\" : \"%e\", ", stats_to -> cur);
199 if (tcp_rtt_stats !=NULL && tcp_rtt_stats -> cur_valid)
200 printf("\"tcp_rtt_stats\" : \"%e\", ", tcp_rtt_stats -> cur);
201 printf("\"re_tx\" : \"%d\", ", re_tx);
202 printf("\"pmtu\" : \"%d\", ", pmtu);
203 printf("\"tos\" : \"%02x\" ", recv_tos);
204 printf("}");
205 }
206
207 char *get_ts_str(int verbose)
208 {
209 char buffer[4096] = { 0 };
210 struct tm *tvm = NULL;
211 struct timeval tv;
212
213 (void)gettimeofday(&tv, NULL);
214
215 tvm = localtime(&tv.tv_sec);
216
217 if (verbose == 1)
218 sprintf(buffer, "%04d/%02d/%02d ", tvm -> tm_year + 1900, tvm -> tm_mon + 1, tvm -> tm_mday);
219 else if (verbose >= 2)
220 sprintf(buffer, "%.6f", get_ts());
221
222 if (verbose <= 1)
223 sprintf(&buffer[strlen(buffer)], "%02d:%02d:%02d.%03d", tvm -> tm_hour, tvm -> tm_min, tvm -> tm_sec, (int)(tv.tv_usec / 1000));
224
225 return strdup(buffer);
226 }
227
228 void emit_error(int verbose, int seq, double start_ts)
229 {
230 char *ts = show_ts ? get_ts_str(verbose) : NULL;
231
232 #ifdef NC
233 if (ncurses_mode)
234 {
235 slow_log("\n%s%s", ts ? ts : "", get_error());
236 update_terminal();
237 }
238 else
239 #endif
240 if (!quiet && !machine_readable && !nagios_mode && !json_output)
241 printf("%s%s%s%s\n", ts ? ts : "", c_error, get_error(), c_normal);
242
243 if (json_output)
244 emit_json(0, seq, start_ts, NULL, NULL, NULL, -1, get_error(), -1, -1, -1, "", "", -1, 0, NULL, NULL, NULL, 0, NULL, NULL, 0, 0, 0, NULL);
245
246 clear_error();
247
248 free(ts);
249
250 fflush(NULL);
251 }
252
253 void handler(int sig)
254 {
255 #ifdef NC
256 if (sig == SIGWINCH)
257 win_resize = 1;
258 else
259 #endif
260 {
261 if (!json_output)
262 fprintf(stderr, gettext("Got signal %d\n"), sig);
263
264 stop = 1;
265 }
266 }
267
268 char * read_file(const char *file)
269 {
270 char buffer[4096] = { 0 }, *lf = NULL;
271 FILE *fh = fopen(file, "rb");
272 if (!fh)
273 error_exit(gettext("Cannot open password-file %s"), file);
274
275 if (!fgets(buffer, sizeof buffer, fh))
276 error_exit(gettext("Problem reading password from file %s"), file);
277
278 fclose(fh);
279
280 lf = strchr(buffer, '\n');
281 if (lf)
282 *lf = 0x00;
283
284 return strdup(buffer);
285 }
286
287 char * create_http_request_header(const char *get, char use_proxy_host, char get_instead_of_head, char persistent_connections, const char *hostname, const char *useragent, const char *referer, char ask_compression, char no_cache, const char *auth_usr, const char *auth_password, char **static_cookies, int n_static_cookies, char **dynamic_cookies, int n_dynamic_cookies, const char *proxy_buster, const char *proxy_user, const char *proxy_password, char **additional_headers, int n_additional_headers)
288 {
289 int index;
290 char *request = NULL;
291 char pb[128] = { 0 };
292
293 if (proxy_buster)
294 {
295 if (strchr(get, '?'))
296 pb[0] = '&';
297 else
298 pb[0] = '?';
299
300 snprintf(pb + 1, sizeof pb - 1, "%s=%ld", proxy_buster, lrand48());
301 }
302
303 if (use_proxy_host)
304 str_add(&request, "%s %s%s HTTP/1.%c\r\n", get_instead_of_head?"GET":"HEAD", get, pb, persistent_connections?'1':'0');
305 else
306 {
307 const char *dummy = get, *slash = NULL;
308 if (strncasecmp(dummy, "http://", 7) == 0)
309 dummy += 7;
310 else if (strncasecmp(dummy, "https://", 7) == 0)
311 dummy += 8;
312
313 slash = strchr(dummy, '/');
314 if (slash)
315 str_add(&request, "%s %s HTTP/1.%c\r\n", get_instead_of_head?"GET":"HEAD", slash, persistent_connections?'1':'0');
316 else
317 str_add(&request, "%s / HTTP/1.%c\r\n", get_instead_of_head?"GET":"HEAD", persistent_connections?'1':'0');
318 }
319
320 if (hostname)
321 str_add(&request, "Host: %s\r\n", hostname);
322
323 if (useragent)
324 str_add(&request, "User-Agent: %s\r\n", useragent);
325 else
326 str_add(&request, "User-Agent: HTTPing v" VERSION "\r\n");
327
328 if (referer)
329 str_add(&request, "Referer: %s\r\n", referer);
330
331 if (ask_compression)
332 str_add(&request, "Accept-Encoding: gzip,deflate\r\n");
333
334 if (no_cache)
335 {
336 str_add(&request, "Pragma: no-cache\r\n");
337 str_add(&request, "Cache-Control: no-cache\r\n");
338 }
339
340 /* Basic Authentification */
341 if (auth_usr)
342 {
343 char auth_string[256] = { 0 };
344 char b64_auth_string[512] = { 0 };
345
346 sprintf(auth_string, "%s:%s", auth_usr, auth_password);
347 enc_b64(auth_string, strlen(auth_string), b64_auth_string);
348
349 str_add(&request, "Authorization: Basic %s\r\n", b64_auth_string);
350 }
351
352 /* proxy authentication */
353 if (proxy_user)
354 {
355 char ppa_string[256] = { 0 };
356 char b64_ppa_string[512] = { 0 };
357
358 sprintf(ppa_string, "%s:%s", proxy_user, proxy_password);
359 enc_b64(ppa_string, strlen(ppa_string), b64_ppa_string);
360
361 str_add(&request, "Proxy-Authorization: Basic %s\r\n", b64_ppa_string);
362 }
363
364 /* Cookie insertion */
365 for(index=0; index<n_static_cookies; index++)
366 str_add(&request, "Cookie: %s\r\n", static_cookies[index]);
367 for(index=0; index<n_dynamic_cookies; index++)
368 str_add(&request, "Cookie: %s\r\n", dynamic_cookies[index]);
369
370 for(index=0; index<n_additional_headers; index++)
371 str_add(&request, "%s\r\n", additional_headers[index]);
372
373 if (persistent_connections)
374 str_add(&request, "Connection: keep-alive\r\n");
375
376 str_add(&request, "\r\n");
377
378 return request;
379 }
380
381 void interpret_url(const char *in, char **path, char **hostname, int *portnr, char use_ipv6, char use_ssl, char **complete_url, char **auth_user, char **auth_password)
382 {
383 char in_use[65536] = { 0 }, *dummy = NULL;
384
385 if (strlen(in) >= sizeof in_use)
386 error_exit(gettext("URL too big, HTTPing has a %d bytes limit"), sizeof in_use - 1);
387
388 /* make url complete, if not already */
389 if (strncasecmp(in, "http://", 7) == 0 || strncasecmp(in, "https://", 8) == 0) /* complete url? */
390 {
391 snprintf(in_use, sizeof in_use - 1, "%s", in);
392
393 if (strchr(&in[8], '/') == NULL)
394 in_use[strlen(in_use)] = '/';
395 }
396 else if (strchr(in, '/')) /* hostname + location without 'http://'? */
397 sprintf(in_use, "http://%s", in);
398 else if (use_ssl)
399 sprintf(in_use, "https://%s/", in);
400 else
401 sprintf(in_use, "http://%s/", in);
402
403 /* sanity check */
404 if (strncasecmp(in_use, "http://", 7) == 0 && use_ssl)
405 error_exit(gettext("using \"http://\" with SSL enabled (-l)"));
406
407 *complete_url = strdup(in_use);
408
409 /* fetch hostname */
410 if (strncasecmp(in_use, "http://", 7) == 0)
411 *hostname = strdup(&in_use[7]);
412 else /* https */
413 *hostname = strdup(&in_use[8]);
414
415 dummy = strchr(*hostname, '/');
416 if (dummy)
417 *dummy = 0x00;
418
419 /* fetch port number */
420 if (use_ssl || strncasecmp(in, "https://", 8) == 0)
421 *portnr = 443;
422 else
423 *portnr = 80;
424
425 if (!use_ipv6)
426 {
427 char *at = strchr(*hostname, '@');
428 char *colon = strchr(*hostname, ':');
429 char *colon2 = colon ? strchr(colon + 1, ':') : NULL;
430
431 if (colon2)
432 {
433 *colon2 = 0x00;
434 *portnr = atoi(colon2 + 1);
435
436 if (at)
437 {
438 *colon = 0x00;
439 *at = 0x00;
440
441 *auth_user = strdup(*hostname);
442 *auth_password = strdup(colon + 1);
443 }
444 }
445 else if (colon)
446 {
447 if (colon < at)
448 {
449 *colon = 0x00;
450 *at = 0x00;
451
452 *auth_user = strdup(*hostname);
453 *auth_password = strdup(colon + 1);
454 }
455 else if (at)
456 {
457 *at = 0x00;
458 *auth_user = strdup(*hostname);
459 }
460 else
461 {
462 *colon = 0x00;
463 *portnr = atoi(colon + 1);
464 }
465 }
466 }
467
468 /* fetch path */
469 dummy = strchr(&in_use[8], '/');
470 if (dummy)
471 *path = strdup(dummy);
472 else
473 *path = strdup("/");
474 }
475
476 typedef struct {
477 int interval, last_ts;
478 double value, sd, min, max;
479 int n_values;
480 } aggregate_t;
481
482 void set_aggregate(char *in, int *n_aggregates, aggregate_t **aggregates)
483 {
484 char *dummy = in;
485
486 *n_aggregates = 0;
487
488 for(;dummy;)
489 {
490 (*n_aggregates)++;
491
492 *aggregates = (aggregate_t *)realloc(*aggregates, *n_aggregates * sizeof(aggregate_t));
493
494 memset(&(*aggregates)[*n_aggregates - 1], 0x00, sizeof(aggregate_t));
495
496 (*aggregates)[*n_aggregates - 1].interval = atoi(dummy);
497 (*aggregates)[*n_aggregates - 1].max = -MY_DOUBLE_INF;
498 (*aggregates)[*n_aggregates - 1].min = MY_DOUBLE_INF;
499
500 dummy = strchr(dummy, ',');
501 if (dummy)
502 dummy++;
503 }
504 }
505
506 void do_aggregates(double cur_ms, int cur_ts, int n_aggregates, aggregate_t *aggregates, int verbose, char show_ts)
507 {
508 int index=0;
509
510 /* update measurements */
511 for(index=0; index<n_aggregates; index++)
512 {
513 aggregates[index].value += cur_ms;
514
515 if (cur_ms < aggregates[index].min)
516 aggregates[index].min = cur_ms;
517
518 if (cur_ms > aggregates[index].max)
519 aggregates[index].max = cur_ms;
520
521 aggregates[index].sd += cur_ms * cur_ms;
522
523 aggregates[index].n_values++;
524 }
525
526 /* emit */
527 for(index=0; index<n_aggregates && cur_ts > 0; index++)
528 {
529 aggregate_t *a = &aggregates[index];
530
531 if (cur_ts - a -> last_ts >= a -> interval)
532 {
533 char *line = NULL;
534 double avg = a -> n_values ? a -> value / (double)a -> n_values : -1.0;
535 char *ts = get_ts_str(verbose);
536
537 str_add(&line, "%s", show_ts ? ts : "");
538 free(ts);
539
540 str_add(&line, gettext("AGG[%d]: %d values, min/avg/max%s = %.1f/%.1f/%.1f"), a -> interval, a -> n_values, verbose ? gettext("/sd") : "", a -> min, avg, a -> max);
541
542 if (verbose)
543 {
544 double sd = -1.0;
545
546 if (a -> n_values)
547 sd = sqrt((a -> sd / (double)a -> n_values) - pow(avg, 2.0));
548
549 str_add(&line, "/%.1f", sd);
550 }
551
552 str_add(&line, " ms");
553
554 #ifdef NC
555 if (ncurses_mode)
556 slow_log("\n%s", line);
557 else
558 #endif
559 printf("%s\n", line);
560
561 free(line);
562
563 aggregates[index].value =
564 aggregates[index].sd = 0.0;
565 aggregates[index].min = MY_DOUBLE_INF;
566 aggregates[index].max = -MY_DOUBLE_INF;
567 aggregates[index].n_values = 0;
568 aggregates[index].last_ts = cur_ts;
569 }
570 }
571 }
572
573 void fetch_proxy_settings(char **proxy_user, char **proxy_password, char **proxy_host, int *proxy_port, char use_ssl, char use_ipv6)
574 {
575 char *str = getenv(use_ssl ? "https_proxy" : "http_proxy");
576
577 if (!str)
578 {
579 /* FIXME from wgetrc/curlrc? */
580 }
581
582 if (str)
583 {
584 char *path = NULL, *url = NULL;
585
586 interpret_url(str, &path, proxy_host, proxy_port, use_ipv6, use_ssl, &url, proxy_user, proxy_password);
587
588 free(url);
589 free(path);
590 }
591 }
592
593 void parse_nagios_settings(const char *in, double *nagios_warn, double *nagios_crit)
594 {
595 char *dummy = strchr(in, ',');
596 if (!dummy)
597 error_exit(gettext("-n: missing parameter\n"));
598
599 *nagios_warn = atof(in);
600
601 *nagios_crit = atof(dummy + 1);
602 }
603
604 void parse_bind_to(const char *in, struct sockaddr_in *bind_to_4, struct sockaddr_in6 *bind_to_6, struct sockaddr_in **bind_to)
605 {
606 char *dummy = strchr(in, ':');
607
608 if (dummy)
609 {
610 *bind_to = (struct sockaddr_in *)bind_to_6;
611 memset(bind_to_6, 0x00, sizeof *bind_to_6);
612 bind_to_6 -> sin6_family = AF_INET6;
613
614 if (inet_pton(AF_INET6, in, &bind_to_6 -> sin6_addr) != 1)
615 error_exit(gettext("cannot convert ip address '%s' (for -y)\n"), in);
616 }
617 else
618 {
619 *bind_to = (struct sockaddr_in *)bind_to_4;
620 memset(bind_to_4, 0x00, sizeof *bind_to_4);
621 bind_to_4 -> sin_family = AF_INET;
622
623 if (inet_pton(AF_INET, in, &bind_to_4 -> sin_addr) != 1)
624 error_exit(gettext("cannot convert ip address '%s' (for -y)\n"), in);
625 }
626 }
627
628 time_t parse_date_from_response_headers(const char *in)
629 {
630 char *date = NULL, *komma = NULL;
631 if (in == NULL)
632 return -1;
633
634 date = strstr(in, "\nDate:");
635 komma = date ? strchr(date, ',') : NULL;
636 if (date && komma)
637 {
638 struct tm tm;
639 memset(&tm, 0x00, sizeof tm);
640
641 /* 22 Feb 2013 09:13:56 */
642 if (strptime(komma + 1, "%d %b %Y %H:%M:%S %Z", &tm))
643 return mktime(&tm);
644 }
645
646 return -1;
647 }
648
649 int calc_page_age(const char *in, const time_t their_ts)
650 {
651 int age = -1;
652
653 if (in != NULL && their_ts > 0)
654 {
655 char *date = strstr(in, "\nLast-Modified:");
656 char *komma = date ? strchr(date, ',') : NULL;
657 if (date && komma)
658 {
659 struct tm tm;
660 memset(&tm, 0x00, sizeof tm);
661
662 /* 22 Feb 2013 09:13:56 */
663 if (strptime(komma + 1, "%d %b %Y %H:%M:%S %Z", &tm))
664 age = their_ts - mktime(&tm);
665 }
666 }
667
668 return age;
669 }
670
671 const char *get_location(const char *host, int port, char use_ssl, char *reply)
672 {
673 if (reply)
674 {
675 char *copy = strdup(reply);
676 char *head = strstr(copy, "\nLocation:");
677 char *lf = head ? strchr(head + 1, '\n') : NULL;
678
679 if (head)
680 {
681 char *buffer = NULL;
682 char *dest = head + 11;
683
684 if (lf)
685 *lf = 0x00;
686
687 if (memcmp(dest, "http", 4) == 0)
688 str_add(&buffer, "%s", dest);
689 else
690 str_add(&buffer, "http%s://%s:%d%s", use_ssl ? "s" : "", host, port, dest);
691
692 free(copy);
693
694 return buffer;
695 }
696
697 free(copy);
698 }
699
700 return NULL;
701 }
702
703 char check_compressed(const char *reply)
704 {
705 if (reply != NULL)
706 {
707 char *encoding = strstr(reply, "\nContent-Encoding:");
708
709 if (encoding)
710 {
711 char *dummy = strchr(encoding + 1, '\r');
712 if (dummy) *dummy = 0x00;
713
714 dummy = strchr(encoding + 1, '\n');
715 if (dummy) *dummy = 0x00;
716
717 if (strstr(encoding, "gzip") == 0 || strstr(encoding, "deflate") == 0)
718 return 1;
719 }
720 }
721
722 return 0;
723 }
724
725 int nagios_result(int ok, int nagios_mode, int nagios_exit_code, double avg_httping_time, double nagios_warn, double nagios_crit)
726 {
727 if (nagios_mode == 1)
728 {
729 if (ok == 0)
730 {
731 printf(gettext("CRITICAL - connecting failed: %s"), get_error());
732 return 2;
733 }
734 else if (avg_httping_time >= nagios_crit)
735 {
736 printf(gettext("CRITICAL - average httping-time is %.1f\n"), avg_httping_time);
737 return 2;
738 }
739 else if (avg_httping_time >= nagios_warn)
740 {
741 printf(gettext("WARNING - average httping-time is %.1f\n"), avg_httping_time);
742 return 1;
743 }
744
745 printf(gettext("OK - average httping-time is %.1f (%s)|ping=%f\n"), avg_httping_time, get_error(), avg_httping_time);
746
747 return 0;
748 }
749 else if (nagios_mode == 2)
750 {
751 const char *err = get_error();
752
753 if (ok && err[0] == 0x00)
754 {
755 printf(gettext("OK - all fine, avg httping time is %.1f|ping=%f\n"), avg_httping_time, avg_httping_time);
756 return 0;
757 }
758
759 printf(gettext("%s: - failed: %s"), nagios_exit_code == 1?"WARNING":(nagios_exit_code == 2?"CRITICAL":"ERROR"), err);
760 return nagios_exit_code;
761 }
762
763 return -1;
764 }
765
766 void proxy_to_host_and_port(char *in, char **proxy_host, int *proxy_port)
767 {
768 if (in[0] == '[')
769 {
770 char *dummy = NULL;
771
772 *proxy_host = strdup(in + 1);
773
774 dummy = strchr(*proxy_host, ']');
775 if (dummy)
776 {
777 *dummy = 0x00;
778
779 /* +2: ']:' */
780 *proxy_port = atoi(dummy + 2);
781 }
782 }
783 else
784 {
785 char *dummy = strchr(in, ':');
786
787 *proxy_host = in;
788
789 if (dummy)
790 {
791 *dummy=0x00;
792 *proxy_port = atoi(dummy + 1);
793 }
794 }
795 }
796
797 void stats_close(int *fd, stats_t *t_close, char is_failure)
798 {
799 double t_start = get_ts(), t_end = -1;;
800
801 if (is_failure)
802 failure_close(*fd);
803 else
804 close(*fd);
805
806 *fd = -1;
807
808 t_end = get_ts();
809
810 update_statst(t_close, (t_end - t_start) * 1000.0);
811 }
812
813 void add_header(char ***additional_headers, int *n_additional_headers, const char *in)
814 {
815 *additional_headers = (char **)realloc(*additional_headers, (*n_additional_headers + 1) * sizeof(char **));
816 (*additional_headers)[*n_additional_headers] = strdup(in);
817
818 (*n_additional_headers)++;
819 }
820
821 void free_headers(char **additional_headers, int n_additional_headers)
822 {
823 int index = 0;
824
825 for(index=0; index<n_additional_headers; index++)
826 free(additional_headers[index]);
827
828 free(additional_headers);
829 }
830
831 typedef struct
832 {
833 double Bps_min, Bps_max;
834 long long int Bps_avg;
835 } bps_t;
836
837 void stats_line(const char with_header, const char *const complete_url, const int count, const int curncount, const int err, const int ok, double started_at, const char verbose, const stats_t *const t_total, const double avg_httping_time, bps_t *const bps)
838 {
839 double total_took = get_ts() - started_at;
840 int dummy = count;
841
842 if (with_header)
843 printf(gettext("--- %s ping statistics ---\n"), complete_url);
844
845 if (curncount == 0 && err > 0)
846 fprintf(stderr, gettext("internal error! (curncount)\n"));
847
848 if (count == -1)
849 dummy = curncount;
850
851 printf(gettext("%s%d%s connects, %s%d%s ok, %s%3.2f%%%s failed, time %s%s%.0fms%s\n"), c_yellow, curncount, c_normal, c_green, ok, c_normal, c_red, (((double)err) / ((double)dummy)) * 100.0, c_normal, c_blue, c_bright, total_took * 1000.0, c_normal);
852
853 if (ok > 0)
854 {
855 printf(gettext("round-trip min/avg/max%s = %s%.1f%s/%s%.1f%s/%s%.1f%s"), verbose ? gettext("/sd") : "", c_bright, t_total -> min, c_normal, c_bright, avg_httping_time, c_normal, c_bright, t_total -> max, c_normal);
856
857 if (verbose)
858 {
859 double sd_final = t_total -> n ? sqrt((t_total -> sd / (double)t_total -> n) - pow(avg_httping_time, 2.0)) : -1.0;
860 printf("/%.1f", sd_final);
861 }
862
863 printf(" ms\n");
864
865 if (bps)
866 printf(gettext("Transfer speed: min/avg/max = %s%f%s/%s%f%s/%s%f%s KB\n"), c_bright, bps -> Bps_min / 1024, c_normal, c_bright, (bps -> Bps_avg / (double)ok) / 1024.0, c_normal, c_bright, bps -> Bps_max / 1024.0, c_normal);
867 }
868 }
869
870 int main(int argc, char *argv[])
871 {
872 double started_at = -1;
873 char do_fetch_proxy_settings = 0;
874 char *hostname = NULL;
875 char *proxy_host = NULL, *proxy_user = NULL, *proxy_password = NULL;
876 int proxy_port = 8080;
877 int portnr = 80;
878 char *get = NULL, *request = NULL;
879 int req_len = 0;
880 int c = 0;
881 int count = -1, curncount = 0;
882 double wait = 1.0;
883 char wait_set = 0;
884 int audible = 0;
885 int ok = 0, err = 0;
886 double timeout = 30.0;
887 char show_statuscodes = 0;
888 char use_ssl = 0;
889 const char *ok_str = "200";
890 const char *err_str = "-1";
891 const char *useragent = NULL;
892 const char *referer = NULL;
893 const char *auth_password = NULL;
894 const char *auth_usr = NULL;
895 char **static_cookies = NULL, **dynamic_cookies = NULL;
896 int n_static_cookies = 0, n_dynamic_cookies = 0;
897 char resolve_once = 0;
898 char have_resolved = 0;
899 double nagios_warn=0.0, nagios_crit=0.0;
900 int nagios_exit_code = 2;
901 double avg_httping_time = -1.0;
902 int get_instead_of_head = 0;
903 char show_Bps = 0, ask_compression = 0;
904 bps_t bps;
905 int Bps_limit = -1;
906 char show_bytes_xfer = 0, show_fp = 0;
907 SSL *ssl_h = NULL;
908 BIO *s_bio = NULL;
909 struct sockaddr_in *bind_to = NULL;
910 struct sockaddr_in bind_to_4;
911 struct sockaddr_in6 bind_to_6;
912 char split = 0, use_ipv6 = 0;
913 char persistent_connections = 0, persistent_did_reconnect = 0;
914 char no_cache = 0;
915 char use_tfo = 0;
916 char abort_on_resolve_failure = 1;
917 double offset_yellow = -1, offset_red = -1;
918 char colors = 0;
919 int verbose = 0;
920 double offset_show = -1.0;
921 char add_host_header = 1;
922 char *proxy_buster = NULL;
923 char proxy_is_socks5 = 0;
924 char *url = NULL, *complete_url = NULL;
925 int n_aggregates = 0;
926 aggregate_t *aggregates = NULL;
927 char *au_dummy = NULL, *ap_dummy = NULL;
928 stats_t t_connect, t_request, t_total, t_resolve, t_write, t_ssl, t_close, stats_to, tcp_rtt_stats, stats_header_size;
929 char first_resolve = 1;
930 double graph_limit = MY_DOUBLE_INF;
931 char nc_graph = 1;
932 char adaptive_interval = 0;
933 double show_slow_log = MY_DOUBLE_INF;
934 char use_tcp_nodelay = 1;
935 int max_mtu = -1;
936 int write_sleep = 500; /* in us (microseconds), determines resolution of transmit time determination */
937 char keep_cookies = 0;
938 char abbreviate = 0;
939 char *divert_connect = NULL;
940 int recv_buffer_size = -1, tx_buffer_size = -1;
941 int priority = -1, send_tos = -1;
942 char **additional_headers = NULL;
943 int n_additional_headers = 0;
944 #ifndef NO_SSL
945 SSL_CTX *client_ctx = NULL;
946 #endif
947 struct sockaddr_in6 addr;
948 struct addrinfo *ai = NULL, *ai_use = NULL;
949 struct addrinfo *ai_proxy = NULL, *ai_use_proxy = NULL;
950
951 static struct option long_options[] =
952 {
953 {"aggregate", 1, NULL, 9 },
954 {"url", 1, NULL, 'g' },
955 {"hostname", 1, NULL, 'h' },
956 {"port", 1, NULL, 'p' },
957 {"proxy", 1, NULL, 'x' },
958 {"count", 1, NULL, 'c' },
959 {"persistent-connections", 0, NULL, 'Q' },
960 {"interval", 1, NULL, 'i' },
961 {"timeout", 1, NULL, 't' },
962 {"ipv6", 0, NULL, '6' },
963 {"show-statuscodes", 0, NULL, 's' },
964 {"split-time", 0, NULL, 'S' },
965 {"get-request", 0, NULL, 'G' },
966 {"show-transfer-speed", 0, NULL, 'b' },
967 {"show-xfer-speed-compressed", 0, NULL, 'B' },
968 {"data-limit", 1, NULL, 'L' },
969 {"show-kb", 0, NULL, 'X' },
970 {"no-cache", 0, NULL, 'Z' },
971 #ifndef NO_SSL
972 {"use-ssl", 0, NULL, 'l' },
973 {"show-fingerprint", 0, NULL, 'z' },
974 #endif
975 {"flood", 0, NULL, 'f' },
976 {"audible-ping", 0, NULL, 'a' },
977 {"parseable-output", 0, NULL, 'm' },
978 {"ok-result-codes", 1, NULL, 'o' },
979 {"result-string", 1, NULL, 'e' },
980 {"user-agent", 1, NULL, 'I' },
981 {"referer", 1, NULL, 'S' },
982 {"resolve-once",0, NULL, 'r' },
983 {"nagios-mode-1", 1, NULL, 'n' },
984 {"nagios-mode-2", 1, NULL, 'n' },
985 {"bind-to", 1, NULL, 'y' },
986 {"quiet", 0, NULL, 'q' },
987 {"username", 1, NULL, 'U' },
988 {"password", 1, NULL, 'P' },
989 {"cookie", 1, NULL, 'C' },
990 {"colors", 0, NULL, 'Y' },
991 {"offset-yellow", 1, NULL, 1 },
992 {"threshold-yellow", 1, NULL, 1 },
993 {"offset-red", 1, NULL, 2 },
994 {"threshold-red", 1, NULL, 2 },
995 {"offset-show", 1, NULL, 3 },
996 {"show-offset", 1, NULL, 3 },
997 {"threshold-show", 1, NULL, 3 },
998 {"show-threshold", 1, NULL, 3 },
999 {"timestamp", 0, NULL, 4 },
1000 {"ts", 0, NULL, 4 },
1001 {"no-host-header", 0, NULL, 5 },
1002 {"proxy-buster", 1, NULL, 6 },
1003 {"proxy-user", 1, NULL, 7 },
1004 {"proxy-password", 1, NULL, 8 },
1005 {"proxy-password-file", 1, NULL, 10 },
1006 {"graph-limit", 1, NULL, 11 },
1007 {"adaptive-interval", 0, NULL, 12 },
1008 {"ai", 0, NULL, 12 },
1009 {"slow-log", 0, NULL, 13 },
1010 {"draw-phase", 0, NULL, 14 },
1011 {"no-tcp-nodelay", 0, NULL, 15 },
1012 {"max-mtu", 1, NULL, 16 },
1013 {"keep-cookies", 0, NULL, 17 },
1014 {"abbreviate", 0, NULL, 18 },
1015 {"divert-connect", 1, NULL, 19 },
1016 {"recv-buffer", 1, NULL, 20 },
1017 {"tx-buffer", 1, NULL, 21 },
1018 {"priority", 1, NULL, 23 },
1019 {"tos", 1, NULL, 24 },
1020 {"header", 1, NULL, 25 },
1021 #ifdef NC
1022 {"ncurses", 0, NULL, 'K' },
1023 {"gui", 0, NULL, 'K' },
1024 #ifdef FW
1025 {"no-graph", 0, NULL, 'D' },
1026 #endif
1027 #endif
1028 {"version", 0, NULL, 'V' },
1029 {"help", 0, NULL, 22 },
1030 {NULL, 0, NULL, 0 }
1031 };
1032
1033 bps.Bps_min = 1 << 30;
1034 bps.Bps_max = -bps.Bps_min;
1035 bps.Bps_avg = 0;
1036
1037 setlocale(LC_ALL, "");
1038 bindtextdomain("HTTPing", LOCALEDIR);
1039 textdomain("HTTPing");
1040
1041 init_statst(&t_resolve);
1042 init_statst(&t_connect);
1043 init_statst(&t_write);
1044 init_statst(&t_request);
1045 init_statst(&t_total);
1046 init_statst(&t_ssl);
1047 init_statst(&t_close);
1048
1049 init_statst(&stats_to);
1050 #if defined(linux) || defined(__FreeBSD__)
1051 init_statst(&tcp_rtt_stats);
1052 #endif
1053 init_statst(&stats_header_size);
1054
1055 determine_terminal_size(&max_y, &max_x);
1056
1057 signal(SIGPIPE, SIG_IGN);
1058
1059 while((c = getopt_long(argc, argv, "DKEA5MvYWT:ZQ6Sy:XL:bBg:h:p:c:i:Gx:t:o:e:falqsmV?I:R:rn:N:zP:U:C:F", long_options, NULL)) != -1)
1060 {
1061 switch(c)
1062 {
1063 case 25:
1064 add_header(&additional_headers, &n_additional_headers, optarg);
1065 break;
1066
1067 case 24:
1068 send_tos = atoi(optarg);
1069 break;
1070
1071 case 23:
1072 #ifdef linux
1073 priority = atoi(optarg);
1074 #else
1075 error_exit("Setting the network priority is only supported on Linux.\n");
1076 #endif
1077 break;
1078
1079 case 21:
1080 tx_buffer_size = atoi(optarg);
1081 break;
1082
1083 case 20:
1084 recv_buffer_size = atoi(optarg);
1085 break;
1086
1087 case 19:
1088 divert_connect = optarg;
1089 break;
1090
1091 case 18:
1092 abbreviate = 1;
1093 break;
1094
1095 case 17:
1096 keep_cookies = 1;
1097 break;
1098
1099 case 16:
1100 max_mtu = atoi(optarg);
1101 break;
1102
1103 case 15:
1104 use_tcp_nodelay = 0;
1105 break;
1106
1107 #ifdef NC
1108 case 14:
1109 draw_phase = 1;
1110 break;
1111 #endif
1112
1113 case 13:
1114 show_slow_log = atof(optarg);
1115 break;
1116
1117 case 12:
1118 adaptive_interval = 1;
1119 break;
1120
1121 case 11:
1122 graph_limit = atof(optarg);
1123 break;
1124
1125 #ifdef NC
1126 case 'K':
1127 ncurses_mode = 1;
1128 adaptive_interval = 1;
1129 if (!wait_set)
1130 wait = 0.5;
1131 break;
1132 #ifdef FW
1133 case 'D':
1134 nc_graph = 0;
1135 break;
1136 #endif
1137 #endif
1138
1139 case 'E':
1140 do_fetch_proxy_settings = 1;
1141 break;
1142
1143 case 'A':
1144 fprintf(stderr, gettext("\n *** -A is no longer required ***\n\n"));
1145 break;
1146
1147 case 'M':
1148 json_output = 1;
1149 break;
1150
1151 case 'v':
1152 verbose++;
1153 break;
1154
1155 case 1:
1156 offset_yellow = atof(optarg);
1157 break;
1158
1159 case 2:
1160 offset_red = atof(optarg);
1161 break;
1162
1163 case 3:
1164 offset_show = atof(optarg);
1165 break;
1166
1167 case 4:
1168 show_ts = 1;
1169 break;
1170
1171 case 5:
1172 add_host_header = 0;
1173 break;
1174
1175 case 6:
1176 proxy_buster = optarg;
1177 break;
1178
1179 case '5':
1180 proxy_is_socks5 = 1;
1181 break;
1182
1183 case 7:
1184 proxy_user = optarg;
1185 break;
1186
1187 case 8:
1188 proxy_password = optarg;
1189 break;
1190
1191 case 9:
1192 set_aggregate(optarg, &n_aggregates, &aggregates);
1193 break;
1194
1195 case 10:
1196 proxy_password = read_file(optarg);
1197 break;
1198
1199 case 'Y':
1200 colors = 1;
1201 break;
1202
1203 case 'W':
1204 abort_on_resolve_failure = 0;
1205 break;
1206
1207 case 'T':
1208 auth_password = read_file(optarg);
1209 break;
1210
1211 case 'Z':
1212 no_cache = 1;
1213 break;
1214
1215 case '6':
1216 use_ipv6 = 1;
1217 break;
1218
1219 case 'S':
1220 split = 1;
1221 break;
1222
1223 case 'Q':
1224 persistent_connections = 1;
1225 break;
1226
1227 case 'y':
1228 parse_bind_to(optarg, &bind_to_4, &bind_to_6, &bind_to);
1229 break;
1230
1231 case 'z':
1232 show_fp = 1;
1233 break;
1234
1235 case 'X':
1236 show_bytes_xfer = 1;
1237 break;
1238
1239 case 'L':
1240 Bps_limit = atoi(optarg);
1241 break;
1242
1243 case 'B':
1244 show_Bps = 1;
1245 ask_compression = 1;
1246 break;
1247
1248 case 'b':
1249 show_Bps = 1;
1250 break;
1251
1252 case 'e':
1253 err_str = optarg;
1254 break;
1255
1256 case 'o':
1257 ok_str = optarg;
1258 break;
1259
1260 case 'x':
1261 proxy_to_host_and_port(optarg, &proxy_host, &proxy_port);
1262 break;
1263
1264 case 'g':
1265 url = optarg;
1266 break;
1267
1268 case 'r':
1269 resolve_once = 1;
1270 break;
1271
1272 case 'h':
1273 free(url);
1274 url = NULL;
1275 str_add(&url, "http://%s/", optarg);
1276 break;
1277
1278 case 'p':
1279 portnr = atoi(optarg);
1280 break;
1281
1282 case 'c':
1283 count = atoi(optarg);
1284 break;
1285
1286 case 'i':
1287 wait = atof(optarg);
1288 if (wait < 0.0)
1289 error_exit(gettext("-i cannot have a value smaller than zero"));
1290 wait_set = 1;
1291 break;
1292
1293 case 't':
1294 timeout = atof(optarg);
1295 break;
1296
1297 case 'I':
1298 useragent = optarg;
1299 break;
1300
1301 case 'R':
1302 referer = optarg;
1303 break;
1304
1305 case 'a':
1306 audible = 1;
1307 break;
1308
1309 case 'f':
1310 wait = 0;
1311 wait_set = 1;
1312 adaptive_interval = 0;
1313 break;
1314
1315 case 'G':
1316 get_instead_of_head = 1;
1317 break;
1318
1319 #ifndef NO_SSL
1320 case 'l':
1321 use_ssl = 1;
1322 break;
1323 #endif
1324
1325 case 'm':
1326 machine_readable = 1;
1327 break;
1328
1329 case 'q':
1330 quiet = 1;
1331 break;
1332
1333 case 's':
1334 show_statuscodes = 1;
1335 break;
1336
1337 case 'V':
1338 version();
1339 return 0;
1340
1341 case 'n':
1342 if (nagios_mode)
1343 error_exit(gettext("-n and -N are mutual exclusive\n"));
1344 else
1345 nagios_mode = 1;
1346
1347 parse_nagios_settings(optarg, &nagios_warn, &nagios_crit);
1348 break;
1349
1350 case 'N':
1351 if (nagios_mode) error_exit(gettext("-n and -N are mutual exclusive\n"));
1352 nagios_mode = 2;
1353 nagios_exit_code = atoi(optarg);
1354 break;
1355
1356 case 'P':
1357 auth_password = optarg;
1358 break;
1359
1360 case 'U':
1361 auth_usr = optarg;
1362 break;
1363
1364 case 'C':
1365 add_cookie(&static_cookies, &n_static_cookies, optarg);
1366 break;
1367
1368 case 'F':
1369 #ifdef TCP_TFO
1370 use_tfo = 1;
1371 #else
1372 fprintf(stderr, gettext("Warning: TCP TFO is not supported. Disabling.\n"));
1373 #endif
1374 break;
1375
1376 case 22:
1377 version();
1378
1379 usage(argv[0]);
1380
1381 return 0;
1382
1383 case '?':
1384 default:
1385 fprintf(stderr, "\n");
1386 version();
1387
1388 fprintf(stderr, gettext("\n\nPlease run:\n\t%s --help\nto see a list of options.\n\n"), argv[0]);
1389
1390 return 1;
1391 }
1392 }
1393
1394 if (do_fetch_proxy_settings)
1395 fetch_proxy_settings(&proxy_user, &proxy_password, &proxy_host, &proxy_port, use_ssl, use_ipv6);
1396
1397 if (optind < argc)
1398 url = argv[optind];
1399
1400 if (!url)
1401 {
1402 fprintf(stderr, gettext("No URL/host to ping given\n\n"));
1403 return 1;
1404 }
1405
1406 if (machine_readable + json_output + ncurses_mode > 1)
1407 error_exit(gettext("Cannot combine -m, -M and -K"));
1408
1409 if ((machine_readable || json_output) && n_aggregates > 0)
1410 error_exit(gettext("Aggregates can only be used in non-machine/json-output mode"));
1411
1412 clear_error();
1413
1414 if (!(get_instead_of_head || use_ssl) && show_Bps)
1415 error_exit(gettext("-b/-B can only be used when also using -G (GET instead of HEAD) or -l (use SSL)\n"));
1416
1417 if (use_tfo && use_ssl)
1418 error_exit(gettext("TCP Fast open and SSL not supported together\n"));
1419
1420 if (colors)
1421 set_colors(ncurses_mode);
1422
1423 if (!machine_readable && !json_output)
1424 printf("%s%s", c_normal, c_white);
1425
1426 interpret_url(url, &get, &hostname, &portnr, use_ipv6, use_ssl, &complete_url, &au_dummy, &ap_dummy);
1427 if (!auth_usr)
1428 auth_usr = au_dummy;
1429 if (!auth_password)
1430 auth_password = ap_dummy;
1431
1432 #ifdef NC
1433 if (ncurses_mode)
1434 {
1435 if (wait == 0.0)
1436 wait = 0.001;
1437
1438 init_ncurses_ui(graph_limit, 1.0 / wait, colors);
1439 }
1440 #endif
1441
1442 if (strncmp(complete_url, "https://", 8) == 0 && !use_ssl)
1443 {
1444 use_ssl = 1;
1445 #ifdef NC
1446 if (ncurses_mode)
1447 {
1448 slow_log(gettext("\nAuto enabling SSL due to https-URL"));
1449 update_terminal();
1450 }
1451 else
1452 #endif
1453 {
1454 fprintf(stderr, gettext("Auto enabling SSL due to https-URL"));
1455 }
1456 }
1457
1458 if (verbose)
1459 {
1460 #ifdef NC
1461 if (ncurses_mode)
1462 {
1463 slow_log(gettext("\nConnecting to host %s, port %d and requesting file %s"), hostname, portnr, get);
1464
1465 if (proxy_host)
1466 slow_log(gettext("\nUsing proxyserver: %s:%d"), proxy_host, proxy_port);
1467 }
1468 else
1469 #endif
1470 {
1471 printf(gettext("Connecting to host %s, port %d and requesting file %s\n\n"), hostname, portnr, get);
1472
1473 if (proxy_host)
1474 fprintf(stderr, gettext("Using proxyserver: %s:%d\n"), proxy_host, proxy_port);
1475 }
1476 }
1477
1478 #ifndef NO_SSL
1479 if (use_ssl)
1480 {
1481 client_ctx = initialize_ctx(ask_compression);
1482 if (!client_ctx)
1483 {
1484 set_error(gettext("problem creating SSL context"));
1485 goto error_exit;
1486 }
1487 }
1488 #endif
1489
1490 if (!quiet && !machine_readable && !nagios_mode && !json_output)
1491 {
1492 #ifdef NC
1493 if (ncurses_mode)
1494 slow_log("\nPING %s:%d (%s):", hostname, portnr, get);
1495 else
1496 #endif
1497 printf("PING %s%s:%s%d%s (%s):\n", c_green, hostname, c_bright, portnr, c_normal, get);
1498 }
1499
1500 if (json_output)
1501 printf("[\n");
1502
1503 if (adaptive_interval && wait <= 0.0)
1504 error_exit(gettext("Interval must be > 0 when using adaptive interval"));
1505
1506 signal(SIGINT, handler);
1507 signal(SIGTERM, handler);
1508
1509 signal(SIGQUIT, handler_quit);
1510
1511 timeout *= 1000.0; /* change to ms */
1512
1513 /*
1514 if (follow_30x)
1515 {
1516 get headers
1517
1518 const char *get_location(const char *host, int port, char use_ssl, char *reply)
1519
1520 set new host/port/path/etc
1521 }
1522 */
1523
1524 started_at = get_ts();
1525 if (proxy_host)
1526 {
1527 #ifdef NC
1528 if (ncurses_mode)
1529 {
1530 slow_log(gettext("\nResolving hostname %s"), proxy_host);
1531 update_terminal();
1532 }
1533 #endif
1534
1535 if (resolve_host(proxy_host, &ai_proxy, use_ipv6, proxy_port) == -1)
1536 error_exit(get_error());
1537
1538 ai_use_proxy = select_resolved_host(ai_proxy, use_ipv6);
1539 if (!ai_use_proxy)
1540 error_exit(gettext("No valid IPv4 or IPv6 address found for %s"), proxy_host);
1541 }
1542 else if (resolve_once)
1543 {
1544 char *res_host = divert_connect ? divert_connect : hostname;
1545 #ifdef NC
1546 if (ncurses_mode)
1547 {
1548 slow_log(gettext("\nResolving hostname %s"), res_host);
1549 update_terminal();
1550 }
1551 #endif
1552
1553 if (resolve_host(res_host, &ai, use_ipv6, portnr) == -1)
1554 {
1555 err++;
1556 emit_error(verbose, -1, started_at);
1557 have_resolved = 0;
1558 if (abort_on_resolve_failure)
1559 error_exit(get_error());
1560 }
1561
1562 ai_use = select_resolved_host(ai, use_ipv6);
1563 if (!ai_use)
1564 {
1565 set_error(gettext("No valid IPv4 or IPv6 address found for %s"), res_host);
1566
1567 if (abort_on_resolve_failure)
1568 error_exit(get_error());
1569
1570 /* do not emit the resolve-error here: as 'have_resolved' is set to 0
1571 next, the program will try to resolve again anyway
1572 this prevents a double error-message while err is increased only
1573 once
1574 */
1575 have_resolved = 0;
1576 }
1577
1578 if (have_resolved)
1579 get_addr(ai_use, &addr);
1580 }
1581
1582 if (persistent_connections)
1583 fd = -1;
1584
1585 while((curncount < count || count == -1) && stop == 0)
1586 {
1587 double dstart = -1.0, dend = -1.0, dafter_connect = 0.0, dafter_resolve = 0.0, dafter_write_complete = 0.0;
1588 char *reply = NULL;
1589 double Bps = 0;
1590 char is_compressed = 0;
1591 long long int bytes_transferred = 0;
1592 time_t their_ts = 0;
1593 int age = -1;
1594 char *sc = NULL, *scdummy = NULL;
1595 char *fp = NULL;
1596 int re_tx = 0, pmtu = 0, recv_tos = 0;
1597 socklen_t recv_tos_len = sizeof recv_tos;
1598
1599 dstart = get_ts();
1600
1601 for(;;)
1602 {
1603 char did_reconnect = 0;
1604 int rc = -1;
1605 int persistent_tries = 0;
1606 int len = 0, overflow = 0, headers_len = 0;
1607 char req_sent = 0;
1608 double dummy_ms = 0.0;
1609 double their_est_ts = -1.0, toff_diff_ts = -1.0;
1610 char tfo_success = 0;
1611 double ssl_handshake = 0.0;
1612 char cur_have_resolved = 0;
1613 #if defined(linux) || defined(__FreeBSD__)
1614 struct tcp_info info;
1615 socklen_t info_len = sizeof(struct tcp_info);
1616 #endif
1617
1618 curncount++;
1619
1620 persistent_loop:
1621 if ((!resolve_once || (resolve_once == 1 && have_resolved == 0)) && fd == -1 && proxy_host == NULL)
1622 {
1623 char *res_host = divert_connect ? divert_connect : hostname;
1624
1625 memset(&addr, 0x00, sizeof addr);
1626
1627 #ifdef NC
1628 if (ncurses_mode && first_resolve)
1629 {
1630 slow_log(gettext("\nResolving hostname %s"), res_host);
1631 update_terminal();
1632 first_resolve = 0;
1633 }
1634 #endif
1635
1636 if (ai)
1637 {
1638 freeaddrinfo(ai);
1639
1640 ai_use = ai = NULL;
1641 }
1642
1643 if (resolve_host(res_host, &ai, use_ipv6, portnr) == -1)
1644 {
1645 err++;
1646 emit_error(verbose, curncount, dstart);
1647
1648 if (abort_on_resolve_failure)
1649 error_exit(get_error());
1650 break;
1651 }
1652
1653 ai_use = select_resolved_host(ai, use_ipv6);
1654 if (!ai_use)
1655 {
1656 set_error(gettext("No valid IPv4 or IPv6 address found for %s"), res_host);
1657 emit_error(verbose, curncount, dstart);
1658 err++;
1659
1660 if (abort_on_resolve_failure)
1661 error_exit(get_error());
1662
1663 break;
1664 }
1665
1666 get_addr(ai_use, &addr);
1667
1668 cur_have_resolved = have_resolved = 1;
1669 }
1670
1671 if (cur_have_resolved)
1672 {
1673 dafter_resolve = get_ts();
1674 dummy_ms = (dafter_resolve - dstart) * 1000.0;
1675 update_statst(&t_resolve, dummy_ms);
1676 }
1677
1678 free(request);
1679 request = create_http_request_header(proxy_host ? complete_url : get, proxy_host ? 1 : 0, get_instead_of_head, persistent_connections, add_host_header ? hostname : NULL, useragent, referer, ask_compression, no_cache, auth_usr, auth_password, static_cookies, n_static_cookies, dynamic_cookies, keep_cookies ? n_dynamic_cookies : 0, proxy_buster, proxy_user, proxy_password, additional_headers, n_additional_headers);
1680 req_len = strlen(request);
1681
1682 if (req_len >= 4096)
1683 {
1684 char *line = NULL;
1685 static int notify_cnt = 0;
1686
1687 notify_cnt++;
1688
1689 if (notify_cnt == MAX_SHOW_SUPPRESSION + 1)
1690 str_add(&line, gettext("Will no longer inform about request headers too large."));
1691 else if (notify_cnt <= MAX_SHOW_SUPPRESSION)
1692 str_add(&line, gettext("Request headers > 4KB! (%d bytes) This may give failures with some HTTP servers."), req_len);
1693
1694 if (line)
1695 {
1696 #ifdef NC
1697 if (ncurses_mode)
1698 slow_log("\n%s", line);
1699 else
1700 #endif
1701 printf("%s\n", line);
1702 }
1703
1704 free(line);
1705 }
1706
1707 if ((persistent_connections && fd < 0) || !persistent_connections)
1708 {
1709 int rc = -1;
1710 struct addrinfo *ai_dummy = proxy_host ? ai_use_proxy : ai_use;
1711
1712 fd = create_socket((struct sockaddr *)bind_to, ai_dummy, recv_buffer_size, tx_buffer_size, max_mtu, use_tcp_nodelay, priority, send_tos);
1713 if (fd < 0)
1714 rc = fd; /* FIXME need to fix this, this is ugly */
1715 else if (proxy_host)
1716 {
1717 if (proxy_is_socks5)
1718 rc = socks5connect(fd, ai_dummy, timeout, proxy_user, proxy_password, hostname, portnr, abort_on_resolve_failure);
1719 #ifndef NO_SSL
1720 else if (use_ssl)
1721 rc = connect_ssl_proxy(fd, ai_dummy, timeout, proxy_user, proxy_password, hostname, portnr, &use_tfo);
1722 #endif
1723 else
1724 rc = connect_to(fd, ai_dummy, timeout, &use_tfo, request, req_len, &req_sent);
1725 }
1726 else
1727 {
1728
1729 rc = connect_to(fd, ai_dummy, timeout, &use_tfo, request, req_len, &req_sent);
1730 }
1731
1732 if (rc < 0)
1733 {
1734 failure_close(fd);
1735 fd = rc; /* FIXME need to fix this */
1736 }
1737
1738 did_reconnect = 1;
1739 }
1740
1741 if (fd == RC_CTRLC) /* ^C pressed */
1742 break;
1743
1744 if (fd < 0)
1745 {
1746 emit_error(verbose, curncount, dstart);
1747 fd = -1;
1748 }
1749
1750 if (fd >= 0)
1751 {
1752 /* set fd blocking */
1753 if (set_fd_blocking(fd) == -1)
1754 {
1755 stats_close(&fd, &t_close, 1);
1756 break;
1757 }
1758
1759 #ifndef NO_SSL
1760 if (use_ssl && ssl_h == NULL)
1761 {
1762 int rc = connect_ssl(fd, client_ctx, &ssl_h, &s_bio, timeout, &ssl_handshake);
1763 if (rc == 0)
1764 update_statst(&t_ssl, ssl_handshake);
1765 else
1766 {
1767 stats_close(&fd, &t_close, 1);
1768 fd = rc;
1769
1770 if (persistent_connections && ++persistent_tries < 2)
1771 {
1772 persistent_did_reconnect = 1;
1773
1774 goto persistent_loop;
1775 }
1776 }
1777 }
1778 #endif
1779 }
1780
1781 dafter_connect = get_ts();
1782
1783 if (did_reconnect)
1784 {
1785 if (cur_have_resolved)
1786 dummy_ms = (dafter_connect - dafter_resolve) * 1000.0;
1787 else
1788 dummy_ms = (dafter_connect - dstart) * 1000.0;
1789
1790 update_statst(&t_connect, dummy_ms - ssl_handshake);
1791 }
1792
1793 if (fd < 0)
1794 {
1795 if (fd == RC_TIMEOUT)
1796 set_error(gettext("timeout connecting to host"));
1797
1798 emit_error(verbose, curncount, dstart);
1799 err++;
1800
1801 fd = -1;
1802
1803 break;
1804 }
1805
1806 #ifndef NO_SSL
1807 if (use_ssl)
1808 rc = WRITE_SSL(ssl_h, request, req_len);
1809 else
1810 #endif
1811 {
1812 if (!req_sent)
1813 rc = mywrite(fd, request, req_len, timeout);
1814 else
1815 rc = req_len;
1816 }
1817
1818 /* wait for data transmit(!) to complete,
1819 e.g. until the transmitbuffers are empty and the data was
1820 sent to the next hop
1821 */
1822 for(;;)
1823 {
1824 int bytes_left = 0;
1825 int i_rc = ioctl(fd, TIOCOUTQ, &bytes_left);
1826
1827 if (i_rc == -1 || bytes_left == 0 || stop)
1828 break;
1829
1830 dafter_write_complete = get_ts();
1831 if ((dafter_write_complete - dafter_connect) * 1000.0 >= timeout)
1832 break;
1833
1834 /* this keeps it somewhat from becoming a busy loop
1835 * I know of no other way to wait for the kernel to
1836 * finish the transmission
1837 */
1838 usleep(write_sleep);
1839 }
1840
1841 dafter_write_complete = get_ts();
1842
1843 dummy_ms = (dafter_write_complete - dafter_connect) * 1000.0;
1844 update_statst(&t_write, dummy_ms);
1845
1846 if (rc != req_len)
1847 {
1848 if (persistent_connections)
1849 {
1850 if (++persistent_tries < 2)
1851 {
1852 stats_close(&fd, &t_close, 0);
1853 persistent_did_reconnect = 1;
1854 goto persistent_loop;
1855 }
1856 }
1857
1858 if (rc == -1)
1859 set_error(gettext("error sending request to host"));
1860 else if (rc == RC_TIMEOUT)
1861 set_error(gettext("timeout sending to host"));
1862 else if (rc == RC_INVAL)
1863 set_error(gettext("retrieved invalid data from host"));
1864 else if (rc == RC_CTRLC)
1865 {/* ^C */}
1866 else if (rc == 0)
1867 set_error(gettext("connection prematurely closed by peer"));
1868
1869 emit_error(verbose, curncount, dstart);
1870
1871 stats_close(&fd, &t_close, 1);
1872 err++;
1873
1874 break;
1875 }
1876
1877 #if defined(linux) || defined(__FreeBSD__)
1878 #ifdef NC
1879 if (!use_ssl && ncurses_mode)
1880 {
1881 struct timeval tv;
1882 int t_rc = -1;
1883
1884 fd_set rfds;
1885 FD_ZERO(&rfds);
1886 FD_SET(fd, &rfds);
1887
1888 tv.tv_sec = (long)(timeout / 1000.0) % 1000000;
1889 tv.tv_usec = (long)(timeout * 1000.0) % 1000000;
1890
1891 t_rc = select(fd + 1, &rfds, NULL, NULL, &tv);
1892
1893 #ifdef linux
1894 if (t_rc == 1 && \
1895 FD_ISSET(fd, &rfds) && \
1896 getsockopt(fd, IPPROTO_TCP, TCP_INFO, &info, &info_len) == 0 && \
1897 info.tcpi_unacked > 0)
1898 {
1899 static int in_transit_cnt = 0;
1900
1901 in_transit_cnt++;
1902 if (in_transit_cnt == MAX_SHOW_SUPPRESSION + 1)
1903 slow_log(gettext("\nNo longer emitting message about \"still data in transit\""));
1904 else if (in_transit_cnt <= MAX_SHOW_SUPPRESSION)
1905 slow_log(gettext("\nHTTP server started sending data with %d bytes still in transit"), info.tcpi_unacked);
1906 }
1907 #endif
1908
1909 if (t_rc == 0)
1910 {
1911 stats_close(&fd, &t_close, 1);
1912
1913 rc = RC_TIMEOUT;
1914 set_error(gettext("timeout sending to host"));
1915
1916 emit_error(verbose, curncount, dstart);
1917
1918 err++;
1919
1920 break;
1921 }
1922 }
1923 #endif
1924
1925 if (getsockopt(fd, IPPROTO_IP, IP_TOS, &recv_tos, &recv_tos_len) == -1)
1926 {
1927 set_error(gettext("failed to obtain TOS info"));
1928 recv_tos = -1;
1929 }
1930 #endif
1931
1932 rc = get_HTTP_headers(fd, ssl_h, &reply, &overflow, timeout);
1933
1934 #ifdef NC
1935 if (ncurses_mode && !get_instead_of_head && overflow > 0)
1936 {
1937 static int more_data_cnt = 0;
1938
1939 more_data_cnt++;
1940 if (more_data_cnt == MAX_SHOW_SUPPRESSION + 1)
1941 slow_log(gettext("\nNo longer emitting message about \"more data than response headers\""));
1942 else if (more_data_cnt <= MAX_SHOW_SUPPRESSION)
1943 slow_log(gettext("\nHTTP server sent more data than just the response headers"));
1944 }
1945 #endif
1946
1947 emit_headers(reply);
1948
1949 if (reply)
1950 {
1951 free_cookies(dynamic_cookies, n_dynamic_cookies);
1952 dynamic_cookies = NULL;
1953 n_dynamic_cookies = 0;
1954
1955 get_cookies(reply, &dynamic_cookies, &n_dynamic_cookies, &static_cookies, &n_static_cookies);
1956 }
1957
1958 if ((show_statuscodes || machine_readable || json_output || ncurses_mode) && reply != NULL)
1959 {
1960 /* statuscode is in first line behind
1961 * 'HTTP/1.x'
1962 */
1963 char *dummy = strchr(reply, ' ');
1964
1965 if (dummy)
1966 {
1967 sc = strdup(dummy + 1);
1968
1969 /* lines are normally terminated with a
1970 * CR/LF
1971 */
1972 dummy = strchr(sc, '\r');
1973 if (dummy)
1974 *dummy = 0x00;
1975 dummy = strchr(sc, '\n');
1976 if (dummy)
1977 *dummy = 0x00;
1978 }
1979 }
1980
1981 their_ts = parse_date_from_response_headers(reply);
1982
1983 age = calc_page_age(reply, their_ts);
1984
1985 is_compressed = check_compressed(reply);
1986
1987 if (persistent_connections && show_bytes_xfer && reply != NULL)
1988 {
1989 char *length = strstr(reply, "\nContent-Length:");
1990 if (!length)
1991 {
1992 set_error(gettext("'Content-Length'-header missing!"));
1993 emit_error(verbose, curncount, dstart);
1994 stats_close(&fd, &t_close, 1);
1995 break;
1996 }
1997
1998 len = atoi(&length[17]);
1999 }
2000
2001 headers_len = 0;
2002 if (reply)
2003 {
2004 headers_len = strlen(reply) + 4 - overflow;
2005 free(reply);
2006 reply = NULL;
2007 }
2008
2009 update_statst(&stats_header_size, headers_len);
2010
2011 if (rc < 0)
2012 {
2013 if (persistent_connections)
2014 {
2015 if (++persistent_tries < 2)
2016 {
2017 stats_close(&fd, &t_close, 0);
2018 persistent_did_reconnect = 1;
2019 goto persistent_loop;
2020 }
2021 }
2022
2023 if (rc == RC_SHORTREAD)
2024 set_error(gettext("short read during receiving reply-headers from host"));
2025 else if (rc == RC_TIMEOUT)
2026 set_error(gettext("timeout while receiving reply-headers from host"));
2027
2028 emit_error(verbose, curncount, dstart);
2029
2030 stats_close(&fd, &t_close, 1);
2031 err++;
2032
2033 break;
2034 }
2035
2036 ok++;
2037
2038 if (get_instead_of_head && show_Bps)
2039 {
2040 int buffer_size = RECV_BUFFER_SIZE;
2041 char *buffer = (char *)malloc(buffer_size);
2042 double dl_start = get_ts(), dl_end;
2043 double cur_limit = Bps_limit;
2044
2045 if (persistent_connections)
2046 {
2047 if (cur_limit == -1 || len < cur_limit)
2048 cur_limit = len - overflow;
2049 }
2050
2051 for(;;)
2052 {
2053 int n = cur_limit != -1 ? min(cur_limit - bytes_transferred, buffer_size) : buffer_size;
2054 int rc = read(fd, buffer, n);
2055
2056 if (rc == -1)
2057 {
2058 if (errno != EINTR && errno != EAGAIN)
2059 error_exit(gettext("read of response body dataa failed"));
2060 }
2061 else if (rc == 0)
2062 {
2063 break;
2064 }
2065
2066 bytes_transferred += rc;
2067
2068 if (cur_limit != -1 && bytes_transferred >= cur_limit)
2069 break;
2070 }
2071
2072 free(buffer);
2073
2074 dl_end = get_ts();
2075
2076 Bps = (double)bytes_transferred / max(dl_end - dl_start, 0.000001);
2077 bps.Bps_min = min(bps.Bps_min, Bps);
2078 bps.Bps_max = max(bps.Bps_max, Bps);
2079 bps.Bps_avg += Bps;
2080 }
2081
2082 dend = get_ts();
2083
2084 #ifndef NO_SSL
2085 if (use_ssl)
2086 {
2087 if ((show_fp || json_output || ncurses_mode) && ssl_h != NULL)
2088 fp = get_fingerprint(ssl_h);
2089
2090 if (!persistent_connections)
2091 {
2092 if (close_ssl_connection(ssl_h) == -1)
2093 {
2094 set_error(gettext("error shutting down ssl"));
2095 emit_error(verbose, curncount, dstart);
2096 }
2097
2098 SSL_free(ssl_h);
2099 ssl_h = NULL;
2100 s_bio = NULL;
2101 }
2102 }
2103 #endif
2104
2105 #if defined(linux) || defined(__FreeBSD__)
2106 if (getsockopt(fd, IPPROTO_TCP, TCP_INFO, &info, &info_len) == 0)
2107 {
2108 #ifdef TCP_TFO
2109 if (info.tcpi_options & TCPI_OPT_SYN_DATA)
2110 tfo_success = 1;
2111 #endif
2112
2113 update_statst(&tcp_rtt_stats, (double)info.tcpi_rtt / 1000.0);
2114
2115 #ifdef linux
2116 re_tx = info.tcpi_retransmits;
2117 pmtu = info.tcpi_pmtu;
2118 #endif
2119 }
2120 #endif
2121
2122 if (!persistent_connections)
2123 stats_close(&fd, &t_close, 0);
2124
2125 dummy_ms = (dend - dafter_write_complete) * 1000.0;
2126 update_statst(&t_request, dummy_ms);
2127
2128 dummy_ms = (dend - dstart) * 1000.0;
2129 update_statst(&t_total, dummy_ms);
2130
2131 their_est_ts = (dend + dafter_connect) / 2.0; /* estimate of when other end started replying */
2132 toff_diff_ts = ((double)their_ts - their_est_ts) * 1000.0;
2133 update_statst(&stats_to, toff_diff_ts);
2134
2135 if (json_output)
2136 {
2137 char current_host[4096] = { 0 };
2138
2139 if (proxy_host)
2140 snprintf(current_host, sizeof current_host, "%s", hostname);
2141 else if (getnameinfo((const struct sockaddr *)&addr, sizeof addr, current_host, sizeof current_host, NULL, 0, NI_NUMERICHOST) == -1)
2142 snprintf(current_host, sizeof current_host, gettext("getnameinfo() failed: %d (%s)"), errno, strerror(errno));
2143
2144 emit_json(1, curncount, dstart, &t_resolve, &t_connect, &t_request, atoi(sc ? sc : "-1"), sc ? sc : "?", headers_len, len, Bps, current_host, fp, toff_diff_ts, tfo_success, &t_ssl, &t_write, &t_close, n_dynamic_cookies, &stats_to, &tcp_rtt_stats, re_tx, pmtu, recv_tos, &t_total);
2145 }
2146 else if (machine_readable)
2147 {
2148 if (sc)
2149 {
2150 char *dummy = strchr(sc, ' ');
2151 if (dummy)
2152 *dummy = 0x00;
2153
2154 if (strstr(ok_str, sc))
2155 printf("%f", t_total.cur);
2156 else
2157 printf("%s", err_str);
2158
2159 if (show_statuscodes)
2160 printf(" %s", sc);
2161 }
2162 else
2163 {
2164 printf("%s", err_str);
2165 }
2166
2167 if(audible)
2168 putchar('\a');
2169
2170 printf("\n");
2171 }
2172 else if (!quiet && !nagios_mode && t_total.cur >= offset_show)
2173 {
2174 char *tot_str = NULL;
2175 const char *i6_bs = "", *i6_be = "";
2176 char *line = NULL;
2177 const char *ms_color = c_green;
2178 char current_host[4096] = { 0 };
2179 char *operation = !persistent_connections ? gettext("connected to") : gettext("pinged host");
2180 const char *sep = c_bright, *unsep = c_normal;
2181
2182 if (show_ts || ncurses_mode)
2183 {
2184 char *ts = get_ts_str(verbose);
2185
2186 if (ncurses_mode)
2187 str_add(&line, "[%s] ", ts);
2188 else
2189 str_add(&line, "%s ", ts);
2190
2191 free(ts);
2192 }
2193
2194 if (curncount & 1)
2195 {
2196 str_add(&line, "%s", c_bright);
2197
2198 sep = c_normal;
2199 unsep = c_bright;
2200 }
2201
2202 if (proxy_host)
2203 snprintf(current_host, sizeof current_host, "%s", hostname);
2204 else if (getnameinfo((const struct sockaddr *)&addr, sizeof addr, current_host, sizeof current_host, NULL, 0, NI_NUMERICHOST) == -1)
2205 snprintf(current_host, sizeof current_host, gettext("getnameinfo() failed: %d (%s)"), errno, strerror(errno));
2206
2207 if (addr.sin6_family == AF_INET6)
2208 {
2209 i6_bs = "[";
2210 i6_be = "]";
2211 }
2212
2213 if (offset_red > 0.0 && t_total.cur >= offset_red)
2214 ms_color = c_red;
2215 else if (offset_yellow > 0.0 && t_total.cur >= offset_yellow)
2216 ms_color = c_yellow;
2217
2218 if (!ncurses_mode)
2219 str_add(&line, "%s%s ", c_white, operation);
2220
2221 if (persistent_connections && show_bytes_xfer)
2222 str_add(&line, gettext("%s%s%s%s%s:%s%d%s (%d/%d bytes), seq=%s%d%s "), c_red, i6_bs, current_host, i6_be, c_white, c_yellow, portnr, c_white, headers_len, len, c_blue, curncount-1, c_white);
2223 else
2224 str_add(&line, gettext("%s%s%s%s%s:%s%d%s (%d bytes), seq=%s%d%s "), c_red, i6_bs, current_host, i6_be, c_white, c_yellow, portnr, c_white, headers_len, c_blue, curncount-1, c_white);
2225
2226 tot_str = format_value(t_total.cur, 6, 2, abbreviate);
2227
2228 if (split)
2229 {
2230 char *res_str = t_resolve.cur_valid ? format_value(t_resolve.cur, 6, 2, abbreviate) : strdup(gettext(" n/a"));
2231 char *con_str = t_connect.cur_valid ? format_value(t_connect.cur, 6, 2, abbreviate) : strdup(gettext(" n/a"));
2232 char *wri_str = format_value(t_write.cur, 6, 2, abbreviate);
2233 char *req_str = format_value(t_request.cur, 6, 2, abbreviate);
2234 char *clo_str = format_value(t_close.cur, 6, 2, abbreviate);
2235
2236 str_add(&line, gettext("time=%s+%s+%s+%s+%s%s=%s%s%s%s ms %s%s%s"), res_str, con_str, wri_str, req_str, clo_str, sep, unsep, ms_color, tot_str, c_white, c_cyan, sc?sc:"", c_white);
2237
2238 free(clo_str);
2239 free(req_str);
2240 free(wri_str);
2241 free(con_str);
2242 free(res_str);
2243 }
2244 else
2245 {
2246 str_add(&line, gettext("time=%s%s%s ms %s%s%s"), ms_color, tot_str, c_white, c_cyan, sc?sc:"", c_white);
2247 }
2248
2249 free(tot_str);
2250
2251 if (persistent_did_reconnect)
2252 {
2253 str_add(&line, " %sC%s", c_magenta, c_white);
2254 persistent_did_reconnect = 0;
2255 }
2256
2257 if (show_Bps)
2258 {
2259 str_add(&line, " %dKB/s", (int)Bps / 1024);
2260 if (show_bytes_xfer)
2261 str_add(&line, " %dKB", (int)(bytes_transferred / 1024));
2262 if (ask_compression)
2263 {
2264 str_add(&line, " (");
2265 if (!is_compressed)
2266 str_add(&line, gettext("not "));
2267 str_add(&line, gettext("compressed)"));
2268 }
2269 }
2270
2271 if (use_ssl && show_fp && fp != NULL)
2272 {
2273 str_add(&line, " %s", fp);
2274 }
2275
2276 if (verbose > 0 && their_ts > 0)
2277 {
2278 /* if diff_ts > 0, then their clock is running too fast */
2279 str_add(&line, gettext(" toff=%d"), (int)toff_diff_ts);
2280 }
2281
2282 if (verbose > 0 && age > 0)
2283 str_add(&line, gettext(" age=%d"), age);
2284
2285 str_add(&line, "%s", c_normal);
2286
2287 if (audible)
2288 {
2289 #ifdef NC
2290 my_beep();
2291 #else
2292 putchar('\a');
2293 #endif
2294 }
2295
2296 #ifdef TCP_TFO
2297 if (tfo_success)
2298 str_add(&line, " F");
2299 #endif
2300
2301 #ifdef NC
2302 if (ncurses_mode)
2303 {
2304 if (dummy_ms >= show_slow_log)
2305 slow_log("\n%s", line);
2306 else
2307 fast_log("\n%s", line);
2308 }
2309 else
2310 #endif
2311 {
2312 printf("%s\n", line);
2313 }
2314
2315 do_aggregates(t_total.cur, (int)(get_ts() - started_at), n_aggregates, aggregates, verbose, show_ts);
2316
2317 free(line);
2318 }
2319
2320 if (show_statuscodes && ok_str != NULL && sc != NULL)
2321 {
2322 scdummy = strchr(sc, ' ');
2323 if (scdummy) *scdummy = 0x00;
2324
2325 if (strstr(ok_str, sc) == NULL)
2326 {
2327 ok--;
2328 err++;
2329 }
2330 }
2331
2332 if (got_sigquit && !quiet && !machine_readable && !nagios_mode && !json_output)
2333 {
2334 got_sigquit = 0;
2335 stats_line(0, complete_url, count, curncount, err, ok, started_at, verbose, &t_total, avg_httping_time, show_Bps ? &bps : NULL);
2336 }
2337
2338 break;
2339 }
2340
2341 emit_statuslines(get_ts() - started_at);
2342 #ifdef NC
2343 if (ncurses_mode)
2344 update_stats(&t_resolve, &t_connect, &t_request, &t_total, &t_ssl, curncount, err, sc, fp, use_tfo, nc_graph, &stats_to, &tcp_rtt_stats, re_tx, pmtu, recv_tos, &t_close, &t_write, n_dynamic_cookies, abbreviate, &stats_header_size);
2345 #endif
2346
2347 free(sc);
2348 free(fp);
2349
2350 #ifdef NC
2351 if (ncurses_mode)
2352 update_terminal();
2353 else
2354 #endif
2355 fflush(NULL);
2356
2357 if (!stop && wait > 0)
2358 {
2359 double cur_sleep = wait;
2360
2361 if (adaptive_interval)
2362 {
2363 double now = get_ts();
2364 double interval_left = fmod(now - started_at, wait);
2365
2366 if (interval_left <= 0.0)
2367 cur_sleep = wait;
2368 else
2369 cur_sleep = wait - interval_left;
2370 }
2371
2372 usleep((useconds_t)(cur_sleep * 1000000.0));
2373 }
2374
2375 reset_statst_cur(&t_resolve);
2376 reset_statst_cur(&t_connect);
2377 reset_statst_cur(&t_ssl);
2378 reset_statst_cur(&t_write);
2379 reset_statst_cur(&t_request);
2380 reset_statst_cur(&t_close);
2381 reset_statst_cur(&t_total);
2382 reset_statst_cur(&stats_to);
2383 #if defined(linux) || defined(__FreeBSD__)
2384 reset_statst_cur(&tcp_rtt_stats);
2385 #endif
2386 }
2387
2388 #ifdef NC
2389 if (ncurses_mode)
2390 end_ncurses();
2391 #endif
2392
2393 if (colors)
2394 set_colors(0);
2395
2396 if (ok)
2397 avg_httping_time = t_total.avg / (double)t_total.n;
2398 else
2399 avg_httping_time = -1.0;
2400
2401 if (!quiet && !machine_readable && !nagios_mode && !json_output)
2402 stats_line(1, complete_url, count, curncount, err, ok, started_at, verbose, &t_total, avg_httping_time, show_Bps ? &bps : NULL);
2403
2404 error_exit:
2405 if (nagios_mode)
2406 return nagios_result(ok, nagios_mode, nagios_exit_code, avg_httping_time, nagios_warn, nagios_crit);
2407
2408 if (!json_output && !machine_readable)
2409 printf("%s", c_very_normal);
2410
2411 if (json_output)
2412 printf("\n]\n");
2413
2414 free_cookies(static_cookies, n_static_cookies);
2415 free_cookies(dynamic_cookies, n_dynamic_cookies);
2416 freeaddrinfo(ai);
2417 free(request);
2418 free(get);
2419 free(hostname);
2420 free(complete_url);
2421
2422 free_headers(additional_headers, n_additional_headers);
2423
2424 free(aggregates);
2425
2426 #ifndef NO_SSL
2427 if (use_ssl)
2428 {
2429 SSL_CTX_free(client_ctx);
2430
2431 shutdown_ssl();
2432 }
2433 #endif
2434
2435 fflush(NULL);
2436
2437 if (ok)
2438 return 0;
2439 else
2440 return 127;
2441 }
0 extern volatile int stop;
1 extern int max_x, max_y;
2
3 void determine_terminal_size(int *max_y, int *max_x);
4 void handler(int sig);
0 /* Released under GPLv2 with exception for the OpenSSL library. See license.txt */
1 /* $Revision$ */
2
3 #include <errno.h>
4 #include <libintl.h>
5 #include <string.h>
6 #include <unistd.h>
7 #include <sys/types.h>
8 #include <sys/socket.h>
9 #include <sys/types.h>
10 #include <sys/time.h>
11 #include <sys/socket.h>
12 #include <openssl/bio.h>
13 #include <openssl/conf.h>
14 #include <openssl/engine.h>
15 #include <openssl/err.h>
16 #include <openssl/evp.h>
17 #include <openssl/md5.h>
18 #include <openssl/ssl.h>
19 #include <openssl/x509.h>
20
21 #include "error.h"
22 #include "gen.h"
23 #include "mssl.h"
24 #include "tcp.h"
25 #include "io.h"
26 #include "http.h"
27 #include "utils.h"
28
29 BIO *bio_err = NULL;
30
31 void shutdown_ssl(void)
32 {
33 BIO_free(bio_err);
34
35 ERR_free_strings();
36
37 ERR_remove_state(0);
38 ENGINE_cleanup();
39 CONF_modules_free();
40 EVP_cleanup();
41 CRYPTO_cleanup_all_ex_data();
42 }
43
44 char close_ssl_connection(SSL *ssl_h)
45 {
46 int rc = SSL_shutdown(ssl_h);
47
48 if (!rc)
49 rc = SSL_shutdown(ssl_h);
50
51 /*
52 ignoring failures: the socket will be closed
53 anyway later on so any openssl failures won't
54 do any harm
55 if (rc == -1)
56 {
57 fprintf(stderr, "SSL_shutdown failed: %s\n", strerror(errno));
58 return -1;
59 }
60 */
61
62 return 0;
63 }
64
65 int READ_SSL(SSL *ssl_h, char *whereto, int len)
66 {
67 int cnt=len;
68
69 while(len>0)
70 {
71 int rc;
72
73 rc = SSL_read(ssl_h, whereto, len);
74 if (rc == -1)
75 {
76 if (errno != EINTR && errno != EAGAIN)
77 {
78 set_error(gettext("READ_SSL: io-error: %s"), strerror(errno));
79 return -1;
80 }
81 }
82 else if (rc == 0)
83 {
84 return 0;
85 }
86 else
87 {
88 whereto += rc;
89 len -= rc;
90 }
91 }
92
93 return cnt;
94 }
95
96 int WRITE_SSL(SSL *ssl_h, const char *wherefrom, int len)
97 {
98 int cnt=len;
99
100 while(len>0)
101 {
102 int rc;
103
104 rc = SSL_write(ssl_h, wherefrom, len);
105 if (rc == -1)
106 {
107 if (errno != EINTR && errno != EAGAIN)
108 {
109 set_error(gettext("WRITE_SSL: io-error: %s"), strerror(errno));
110 return -1;
111 }
112 }
113 else if (rc == 0)
114 {
115 return 0;
116 }
117 else
118 {
119 wherefrom += rc;
120 len -= rc;
121 }
122 }
123
124 return cnt;
125 }
126
127 int connect_ssl(int fd, SSL_CTX *client_ctx, SSL **ssl_h, BIO **s_bio, double timeout, double *ssl_handshake)
128 {
129 int dummy = -1;
130 double dstart = get_ts();
131
132 struct timeval tv;
133 tv.tv_sec = (long)(timeout / 1000.0);
134 tv.tv_usec = (long)(timeout * 1000.0) % 1000000;
135
136 *ssl_handshake = -1.0;
137
138 if (setsockopt(fd, SOL_SOCKET, SO_RCVTIMEO, &tv, sizeof tv) == -1)
139 {
140 set_error(gettext("problem setting receive timeout (%s)"), strerror(errno));
141 return -1;
142 }
143
144 if (setsockopt(fd, SOL_SOCKET, SO_SNDTIMEO, &tv, sizeof tv) == -1)
145 {
146 set_error(gettext("problem setting transmit timeout (%s)"), strerror(errno));
147 return -1;
148 }
149
150 *ssl_h = SSL_new(client_ctx);
151
152 *s_bio = BIO_new_socket(fd, BIO_NOCLOSE);
153 SSL_set_bio(*ssl_h, *s_bio, *s_bio);
154
155 dummy = SSL_connect(*ssl_h);
156 if (dummy <= 0)
157 {
158 set_error(gettext("problem starting SSL connection: %d"), SSL_get_error(*ssl_h, dummy));
159 return -1;
160 }
161
162 *ssl_handshake = get_ts() - dstart;
163
164 return 0;
165 }
166
167 SSL_CTX * initialize_ctx(char ask_compression)
168 {
169 const SSL_METHOD *meth = NULL;
170 SSL_CTX *ctx = NULL;
171
172 if (!bio_err)
173 {
174 SSL_library_init();
175 SSL_load_error_strings();
176 ERR_load_crypto_strings();
177
178 /* error write context */
179 bio_err = BIO_new_fp(stderr, BIO_NOCLOSE);
180 }
181
182 /* create context */
183 meth = SSLv23_method();
184 ctx = SSL_CTX_new(meth);
185
186 #ifdef SSL_OP_NO_COMPRESSION
187 if (!ask_compression)
188 SSL_CTX_set_options(ctx, SSL_OP_NO_COMPRESSION);
189 #endif
190
191 return ctx;
192 }
193
194 char * get_fingerprint(SSL *ssl_h)
195 {
196 char *string = NULL;
197
198 unsigned char fp_digest[EVP_MAX_MD_SIZE];
199 X509 *x509_data = SSL_get_peer_certificate(ssl_h);
200
201 if (x509_data)
202 {
203 unsigned int fp_digest_size = sizeof fp_digest;
204
205 memset(fp_digest, 0x00, fp_digest_size);
206
207 if (X509_digest(x509_data, EVP_md5(), fp_digest, &fp_digest_size))
208 {
209 string = (char *)malloc(MD5_DIGEST_LENGTH * 3 + 1);
210 if (string)
211 {
212 int loop, pos =0;
213
214 for(loop=0; loop<MD5_DIGEST_LENGTH; loop++)
215 {
216 if (loop)
217 pos += sprintf(&string[pos], ":%02x", fp_digest[loop]);
218 else
219 pos = sprintf(&string[pos], "%02x", fp_digest[loop]);
220 }
221 }
222 }
223
224 X509_free(x509_data);
225 }
226
227 return string;
228 }
229
230 int connect_ssl_proxy(int fd, struct addrinfo *ai, double timeout, const char *proxy_user, const char *proxy_password, const char *hostname, int portnr, char *tfo)
231 {
232 int rc = -1;
233 char request_headers[4096] = { 0 };
234 int request_headers_len = -1;
235 char rh_sent = 0;
236 char *response_headers = NULL, *code = NULL, *term = NULL;
237
238 request_headers_len = snprintf(request_headers, sizeof request_headers, "CONNECT %s:%d HTTP/1.1\r\nUser-Agent: HTTPing v" VERSION \
239 "\r\nProxy-Connection: keep-alive\r\nConnection: keep-alive\r\nHost: %s\r\n", hostname, portnr, hostname);
240
241 if (proxy_user)
242 {
243 char ppa_string[256] = { 0 };
244 char b64_ppa_string[512] = { 0 };
245
246 sprintf(ppa_string, "%s:%s", proxy_user, proxy_password);
247 enc_b64(ppa_string, strlen(ppa_string), b64_ppa_string);
248 request_headers_len += snprintf(&request_headers[request_headers_len], sizeof request_headers - request_headers_len, "Proxy-Authorization: Basic %s\r\n", b64_ppa_string);
249 }
250
251 request_headers_len += snprintf(&request_headers[request_headers_len], sizeof request_headers - request_headers_len, "\r\n");
252
253 if ((rc = connect_to(fd, ai, timeout, tfo, request_headers, request_headers_len, &rh_sent)) < 0)
254 return rc;
255
256 if (!rh_sent)
257 {
258 if ((rc = mywrite(fd, request_headers, request_headers_len, timeout)) < RC_OK)
259 {
260 set_error(gettext("Problem sending request to proxy"));
261 return rc;
262 }
263 }
264
265 rc = dumb_get_HTTP_headers(fd, &response_headers, timeout);
266 if (rc != RC_OK)
267 {
268 free(response_headers);
269 set_error(gettext("Problem retrieving proxy response"));
270 return rc;
271 }
272
273 term = strchr(response_headers, '\r');
274 if (!term)
275 term = strchr(response_headers, '\n');
276 if (term)
277 *term = 0x00;
278
279 code = strchr(response_headers, ' ');
280 if (!code)
281 {
282 free(response_headers);
283 set_error(gettext("Invalid proxy response headers"));
284 return RC_INVAL;
285 }
286
287 if (atoi(code + 1) != 200)
288 {
289 free(response_headers);
290 set_error(gettext("Proxy indicated error: %s"), code + 1);
291 return RC_INVAL;
292 }
293
294 free(response_headers);
295
296 return RC_OK;
297 }
0 /* Released under GPLv2 with exception for the OpenSSL library. See license.txt */
1 /* $Revision$ */
2
3 #include <netdb.h>
4 #include <netinet/in.h>
5 #include <netinet/tcp.h>
6 #include <arpa/inet.h>
7
8 void shutdown_ssl(void);
9 char close_ssl_connection(SSL *ssl_h);
10 int READ_SSL(SSL *ssl_h, char *whereto, int len);
11 int WRITE_SSL(SSL *ssl_h, const char *whereto, int len);
12 int connect_ssl(int fd, SSL_CTX *client_ctx, SSL **ssl_h, BIO **s_bio, double timeout, double *ssl_handshake);
13 SSL_CTX * initialize_ctx(char ask_compression);
14 char * get_fingerprint(SSL *ssl_h);
15 int connect_ssl_proxy(int fd, struct addrinfo *ai, double timeout, const char *proxy_user, const char *proxy_password, const char *hostname, int portnr, char *tfo);
+845
-0
nc.c less more
0 /* $Revision$ */
1 #define _GNU_SOURCE
2 #include <stdio.h>
3 #include <libintl.h>
4 #include <math.h>
5 #include <poll.h>
6 #include <stdarg.h>
7 #include <signal.h>
8 #include <stdlib.h>
9 #include <string.h>
10 #include <sys/ioctl.h>
11
12 #include <ncurses.h>
13
14 #include "error.h"
15 #include "colors.h"
16 #include "gen.h"
17 #include "main.h"
18 #include "kalman.h"
19 #ifdef FW
20 #include "fft.h"
21 #endif
22 #include "utils.h"
23
24 char win_resize = 0;
25 WINDOW *w_stats = NULL, *w_line1 = NULL, *w_slow = NULL, *w_line2 = NULL, *w_fast = NULL;
26 int stats_h = 10;
27 int logs_n = 0, slow_n = 0, fast_n = 0;
28 char **slow_history = NULL, **fast_history = NULL;
29 int window_history_n = 0;
30 char use_colors = 0;
31
32 double graph_limit = MY_DOUBLE_INF;
33 double hz = 1.0;
34
35 double *history = NULL, *history_temp = NULL, *history_fft_magn = NULL, *history_fft_phase = NULL;
36 char *history_set = NULL;
37 int history_n = 0;
38
39 char draw_phase = 0;
40
41 char pause_graphs = 0;
42
43 typedef enum { C_WHITE = 0, C_GREEN, C_YELLOW, C_BLUE, C_MAGENTA, C_CYAN, C_RED } color_t;
44
45 void update_terminal(void)
46 {
47 wnoutrefresh(w_stats);
48 wnoutrefresh(w_slow);
49 wnoutrefresh(w_fast);
50
51 doupdate();
52 }
53
54 void create_windows(void)
55 {
56 char *r_a = gettext("realloc issue");
57 int nr = 0;
58
59 if (w_stats)
60 {
61 delwin(w_stats);
62 delwin(w_line1);
63 delwin(w_slow);
64 delwin(w_line2);
65 delwin(w_fast);
66 }
67
68 #ifdef FW
69 fft_free();
70 fft_init(max_x);
71 #endif
72
73 if (max_x > history_n)
74 {
75 history = (double *)realloc(history, sizeof(double) * max_x);
76 if (!history)
77 error_exit(r_a);
78
79 history_temp = (double *)realloc(history_temp, sizeof(double) * max_x);
80 if (!history_temp)
81 error_exit(r_a);
82
83 /* halve of it is enough really */
84 history_fft_magn = (double *)realloc(history_fft_magn, sizeof(double) * max_x);
85 if (!history_fft_magn)
86 error_exit(r_a);
87
88 history_fft_phase = (double *)realloc(history_fft_phase, sizeof(double) * max_x);
89 if (!history_fft_phase)
90 error_exit(r_a);
91
92 history_set = (char *)realloc(history_set, sizeof(char) * max_x);
93 if (!history_set)
94 error_exit(r_a);
95
96 memset(&history[history_n], 0x00, (max_x - history_n) * sizeof(double));
97 memset(&history_set[history_n], 0x00, (max_x - history_n) * sizeof(char));
98
99 history_n = max_x;
100 }
101
102 if ((int)max_y > window_history_n)
103 {
104 slow_history = (char **)realloc(slow_history, sizeof(char *) * max_y);
105 if (!slow_history)
106 error_exit(r_a);
107
108 fast_history = (char **)realloc(fast_history, sizeof(char *) * max_y);
109 if (!fast_history)
110 error_exit(r_a);
111
112 memset(&slow_history[window_history_n], 0x00, (max_y - window_history_n) * sizeof(char *));
113 memset(&fast_history[window_history_n], 0x00, (max_y - window_history_n) * sizeof(char *));
114
115 window_history_n = max_y;
116 }
117
118 w_stats = newwin(stats_h, max_x, 0, 0);
119 scrollok(w_stats, false);
120
121 w_line1 = newwin(1, max_x, stats_h, 0);
122 scrollok(w_line1, false);
123 wnoutrefresh(w_line1);
124
125 logs_n = max_y - (stats_h + 1 + 1);
126 fast_n = logs_n * 11 / 20;
127 slow_n = logs_n - fast_n;
128
129 w_slow = newwin(slow_n, max_x, (stats_h + 1), 0);
130 scrollok(w_slow, true);
131
132 w_line2 = newwin(1, max_x, (stats_h + 1) + slow_n, 0);
133 scrollok(w_line2, false);
134 wnoutrefresh(w_line2);
135
136 w_fast = newwin(fast_n, max_x, (stats_h + 1) + slow_n + 1, 0);
137 scrollok(w_fast, true);
138
139 wattron(w_line1, A_REVERSE);
140 wattron(w_line2, A_REVERSE);
141 for(nr=0; nr<max_x; nr++)
142 {
143 wprintw(w_line1, " ");
144 wprintw(w_line2, " ");
145 }
146 wattroff(w_line2, A_REVERSE);
147 wattroff(w_line1, A_REVERSE);
148
149 wnoutrefresh(w_line1);
150 wnoutrefresh(w_line2);
151
152 doupdate();
153
154 signal(SIGWINCH, handler);
155 }
156
157 void myprintloc(WINDOW *w, int y, int x, const char *fmt, ...)
158 {
159 char *line = NULL;
160 int line_len = 0;
161 va_list ap;
162
163 va_start(ap, fmt);
164 line_len = vasprintf(&line, fmt, ap);
165 va_end(ap);
166
167 wmove(w, y, x);
168
169 if (use_colors)
170 {
171 int index = 0;
172
173 for(index=0; index<line_len; index++)
174 {
175 static int clr = C_WHITE, att = A_NORMAL;
176
177 if (line[index] == COLOR_ESCAPE[0])
178 {
179 switch(line[++index])
180 {
181 case '1':
182 clr = C_RED;
183 break;
184 case '2':
185 clr = C_BLUE;
186 break;
187 case '3':
188 clr = C_GREEN;
189 break;
190 case '4':
191 clr = C_YELLOW;
192 break;
193 case '5':
194 clr = C_MAGENTA;
195 break;
196 case '6':
197 clr = C_CYAN;
198 break;
199 case '7':
200 clr = C_WHITE;
201 break;
202 case '8':
203 att = A_BOLD;
204 break;
205 case '9':
206 att = A_NORMAL;
207 break;
208 }
209
210 wattr_set(w, att, clr, NULL);
211 }
212 else
213 {
214 waddch(w, line[index]);
215 }
216 }
217 }
218 else
219 {
220 mvwprintw(w, y, x, "%s", line);
221 }
222
223 free(line);
224 }
225
226 void myprint(WINDOW *w, const char *what)
227 {
228 if (use_colors)
229 {
230 int y = -1, x = -1;
231
232 getyx(w, y, x);
233
234 myprintloc(w, y, x, what);
235 }
236 else
237 {
238 wprintw(w, what);
239 }
240 }
241
242 void recreate_terminal(void)
243 {
244 int index = 0;
245
246 determine_terminal_size(&max_y, &max_x);
247
248 resizeterm(max_y, max_x);
249
250 endwin();
251 refresh();
252
253 create_windows();
254
255 for(index = window_history_n - 1; index >= 0; index--)
256 {
257 if (slow_history[index])
258 myprint(w_slow, slow_history[index]);
259 if (fast_history[index])
260 myprint(w_fast, fast_history[index]);
261 }
262
263 doupdate();
264
265 win_resize = 0;
266 }
267
268 void init_ncurses_ui(double graph_limit_in, double hz_in, char use_colors_in)
269 {
270 graph_limit = graph_limit_in;
271 hz = hz_in;
272 use_colors = use_colors_in;
273
274 initscr();
275 start_color();
276 keypad(stdscr, TRUE);
277 intrflush(stdscr, FALSE);
278 noecho();
279 refresh();
280 nodelay(stdscr, FALSE);
281 meta(stdscr, TRUE); /* enable 8-bit input */
282 idlok(stdscr, TRUE); /* may give a little clunky screenredraw */
283 idcok(stdscr, TRUE); /* may give a little clunky screenredraw */
284 leaveok(stdscr, FALSE);
285
286 init_pair(C_WHITE, COLOR_WHITE, COLOR_BLACK);
287 init_pair(C_CYAN, COLOR_CYAN, COLOR_BLACK);
288 init_pair(C_MAGENTA, COLOR_MAGENTA, COLOR_BLACK);
289 init_pair(C_BLUE, COLOR_BLUE, COLOR_BLACK);
290 init_pair(C_YELLOW, COLOR_YELLOW, COLOR_BLACK);
291 init_pair(C_GREEN, COLOR_GREEN, COLOR_BLACK);
292 init_pair(C_RED, COLOR_RED, COLOR_BLACK);
293
294 kalman_init(0.0);
295
296 recreate_terminal();
297 }
298
299 void end_ncurses(void)
300 {
301 int index = 0;
302
303 for(index=0; index<window_history_n; index++)
304 {
305 free(slow_history[index]);
306 free(fast_history[index]);
307 }
308
309 free(slow_history);
310 free(fast_history);
311
312 if (w_stats)
313 {
314 delwin(w_stats);
315 delwin(w_line1);
316 delwin(w_slow);
317 delwin(w_line2);
318 delwin(w_fast);
319 }
320
321 endwin();
322
323 free(history);
324 free(history_set);
325
326 #ifdef FW
327 fft_free();
328 fft_stop();
329 #endif
330 free(history_temp);
331 free(history_fft_phase);
332 free(history_fft_magn);
333 }
334
335 void fast_log(const char *fmt, ...)
336 {
337 char buffer[4096] = { 0 };
338 va_list ap;
339
340 va_start(ap, fmt);
341 vsnprintf(buffer, sizeof buffer, fmt, ap);
342 va_end(ap);
343
344 free(fast_history[window_history_n - 1]);
345 memmove(&fast_history[1], &fast_history[0], (window_history_n - 1) * sizeof(char *));
346 fast_history[0] = strdup(buffer);
347
348 myprint(w_fast, buffer);
349
350 if (win_resize)
351 recreate_terminal();
352 }
353
354 void slow_log(const char *fmt, ...)
355 {
356 char buffer[4096] = { 0 };
357 va_list ap;
358
359 va_start(ap, fmt);
360 vsnprintf(buffer, sizeof buffer, fmt, ap);
361 va_end(ap);
362
363 free(slow_history[window_history_n - 1]);
364 memmove(&slow_history[1], &slow_history[0], (window_history_n - 1) * sizeof(char *));
365 slow_history[0] = strdup(buffer);
366
367 myprint(w_slow, buffer);
368
369 if (win_resize)
370 recreate_terminal();
371 }
372
373 void my_beep(void)
374 {
375 beep();
376 }
377
378 void status_line(char *fmt, ...)
379 {
380 char *line = NULL;
381 va_list ap;
382
383 wattron(w_line2, A_REVERSE);
384
385 wmove(w_line2, 0, 0);
386
387 va_start(ap, fmt);
388
389 vasprintf(&line, fmt, ap);
390 myprint(w_line2, line);
391 free(line);
392
393 va_end(ap);
394
395 wattroff(w_line2, A_REVERSE);
396
397 wnoutrefresh(w_line2);
398
399 if (win_resize)
400 recreate_terminal();
401 }
402
403 void draw_column(WINDOW *win, int x, int height, char overflow, char limitter)
404 {
405 void *dummy = NULL;
406 int y = 0, end_y = 0, win_h = 0, win_w = 0;
407
408 getmaxyx(win, win_h, win_w);
409 (void)win_w; /* silence warnings */
410
411 end_y = max(0, win_h - height);
412
413 for(y=win_h - 1; y >= end_y; y--)
414 mvwchgat(win, y, x, 1, A_REVERSE, C_YELLOW, dummy);
415
416 if (limitter)
417 mvwchgat(win, 0, x, 1, A_REVERSE, C_BLUE, dummy);
418 else if (overflow)
419 mvwchgat(win, 0, x, 1, A_REVERSE, C_RED, dummy);
420 else if (height == 0)
421 mvwchgat(win, win_h - 1, x, 1, A_REVERSE, C_GREEN, dummy);
422 }
423
424 void draw_rad_column(WINDOW *win, int x, double val)
425 {
426 void *dummy = NULL;
427 int y = 0, end_y = 0, win_h = 0, win_w = 0;
428 int center_y = 0;
429
430 getmaxyx(win, win_h, win_w);
431 (void)win_w; /* silence warnings */
432
433 center_y = win_h / 2;
434 end_y = (int)((double)(win_h / 2) * ((val / PI) + 1.0));
435
436 if (end_y > center_y)
437 {
438 for(y=center_y; y<end_y; y++)
439 mvwchgat(win, y, x, 1, A_REVERSE, C_YELLOW, dummy);
440 }
441 else
442 {
443 for(y=end_y; y<center_y; y++)
444 mvwchgat(win, y, x, 1, A_REVERSE, C_YELLOW, dummy);
445 }
446 }
447
448 double get_cur_scc()
449 {
450 double scc_val = 0.0;
451 double prev_val = 0.0, u0 = 0.0;
452 double t[3] = { 0 };
453 int loop = 0, n = 0;
454 char first = 1;
455
456 t[0] = t[1] = t[2] = 0.0;
457
458 for(loop=0; loop<history_n; loop++)
459 {
460 double cur_val = history[loop];
461
462 if (!history_set[loop])
463 continue;
464
465 if (first)
466 {
467 prev_val = 0;
468 u0 = cur_val;
469 first = 0;
470 }
471 else
472 {
473 t[0] += prev_val * cur_val;
474 }
475
476 t[1] = t[1] + cur_val;
477 t[2] = t[2] + (cur_val * cur_val);
478 prev_val = cur_val;
479
480 n++;
481 }
482
483 t[0] = t[0] + prev_val * u0;
484 t[1] = t[1] * t[1];
485
486 scc_val = (double)n * t[2] - t[1];
487
488 if (scc_val == 0.0)
489 return -1.0;
490
491 return ((double)n * t[0] - t[1]) / scc_val;
492 }
493
494 #ifdef FW
495 void draw_fft(void)
496 {
497 double mx_mag = 0.0;
498 int index = 0, highest = 0;
499 int cx = 0, cy = 0;
500 /* double max_freq = hz / 2.0; */
501 double highest_freq = 0, avg_freq_index = 0.0, total_val = 0.0, avg_freq = 0.0;
502 int dummy = 0;
503
504 getyx(w_slow, cy, cx);
505
506 for(index=0; index<max_x; index++)
507 {
508 double val = 0.0;
509
510 if (history_set[index])
511 val = history[index];
512 else
513 val = index > 0 ? history[index - 1] : 0;
514
515 if (val > graph_limit)
516 val = graph_limit;
517
518 history_temp[index] = val;
519 }
520
521 fft_do(history_temp, history_fft_magn, history_fft_phase);
522
523 for(index=1; index<max_x/2; index++)
524 {
525 avg_freq_index += (double)index * history_fft_magn[index];
526 total_val += history_fft_magn[index];
527
528 if (history_fft_magn[index] > mx_mag)
529 {
530 mx_mag = history_fft_magn[index];
531 highest = index;
532 }
533 }
534
535 highest_freq = (hz / (double)max_x) * (double)highest;
536
537 avg_freq_index /= total_val;
538 avg_freq = (hz / (double)max_x) * avg_freq_index;
539
540 wattron(w_line1, A_REVERSE);
541 myprintloc(w_line1, 0, 38, gettext("highest: %6.2fHz, avg: %6.2fHz"), highest_freq, avg_freq);
542 wattroff(w_line1, A_REVERSE);
543 wnoutrefresh(w_line1);
544
545 dummy = max_x / 2 + 1;
546
547 if (draw_phase)
548 {
549 int y = 0;
550
551 for(y=0; y<slow_n; y++)
552 mvwchgat(w_slow, y, dummy, 1, A_REVERSE, C_WHITE, NULL);
553
554 for(index=0; index<slow_n; index++)
555 mvwchgat(w_slow, index, 0, max_x, A_NORMAL, C_WHITE, NULL);
556
557 for(index=1; index<dummy - 1; index++)
558 draw_rad_column(w_slow, index - 1, history_fft_phase[index]);
559 }
560 else
561 {
562 for(index=0; index<slow_n; index++)
563 mvwchgat(w_slow, index, max_x / 2, max_x / 2, A_NORMAL, C_WHITE, NULL);
564 }
565
566 for(index=1; index<dummy; index++)
567 {
568 int height_magn = (int)((double)slow_n * (history_fft_magn[index] / mx_mag));
569 draw_column(w_slow, max_x / 2 + index - 1, height_magn, 0, 0);
570 }
571
572 wmove(w_slow, cy, cx);
573
574 wnoutrefresh(w_slow);
575 }
576 #endif
577
578 double calc_trend()
579 {
580 int half = history_n / 2, index = 0;
581 double v1 = 0.0, v2 = 0.0;
582 int n_v1 = 0, n_v2 = 0;
583
584 for(index=0; index<half; index++)
585 {
586 if (!history_set[index])
587 continue;
588
589 v1 += history[index];
590 n_v1++;
591 }
592
593 for(index=half; index<history_n; index++)
594 {
595 if (!history_set[index])
596 continue;
597
598 v2 += history[index];
599 n_v2++;
600 }
601
602 if (n_v2 == 0 || n_v1 == 0)
603 return 0;
604
605 v1 /= (double)n_v1;
606 v2 /= (double)n_v2;
607
608 return (v1 - v2) / (v2 / 100.0);
609 }
610
611 void draw_graph(double val)
612 {
613 int index = 0, loop_n = min(max_x, history_n), n = 0, n2 = 0;
614 double avg = 0, sd = 0;
615 double avg2 = 0, sd2 = 0;
616 double mi = MY_DOUBLE_INF, ma = -MY_DOUBLE_INF, diff = 0.0;
617
618 for(index=0; index<loop_n; index++)
619 {
620 double val = history[index];
621
622 if (!history_set[index])
623 continue;
624
625 mi = min(val, mi);
626 ma = max(val, ma);
627
628 avg += val;
629 sd += val * val;
630 n++;
631 }
632
633 if (!n)
634 return;
635
636 avg /= (double)n;
637 sd = sqrt((sd / (double)n) - pow(avg, 2.0));
638
639 mi = max(mi, avg - sd);
640 ma = min(ma, avg + sd);
641
642 for(index=0; index<loop_n; index++)
643 {
644 double val = history[index];
645
646 if (!history_set[index])
647 continue;
648
649 if (val < mi || val > ma)
650 continue;
651
652 avg2 += val;
653 sd2 += val * val;
654 n2++;
655 }
656
657 if (n2)
658 {
659 avg2 /= (double)n2;
660 sd2 = sqrt((sd2 / (double)n2) - pow(avg2, 2.0));
661
662 mi = max(mi, avg2 - sd2);
663 ma = min(ma, avg2 + sd2);
664 diff = ma - mi;
665
666 if (diff == 0.0)
667 diff = 1.0;
668
669 wattron(w_line1, A_REVERSE);
670 myprintloc(w_line1, 0, 0, gettext("graph range: %7.2fms - %7.2fms "), mi, ma);
671 wattroff(w_line1, A_REVERSE);
672 wnoutrefresh(w_line1);
673
674 /* fprintf(stderr, "%d| %f %f %f %f\n", h_stats.n, mi, avg, ma, sd); */
675
676 for(index=0; index<loop_n; index++)
677 {
678 char overflow = 0, limitter = 0;
679 double val = 0, height = 0;
680 int i_h = 0, x = max_x - (1 + index);
681
682 if (!history_set[index])
683 {
684 mvwchgat(w_stats, stats_h - 1, x, 1, A_REVERSE, C_CYAN, NULL);
685 continue;
686 }
687
688 if (history[index] < graph_limit)
689 val = history[index];
690 else
691 {
692 val = graph_limit;
693 limitter = 1;
694 }
695
696 height = (val - mi) / diff;
697
698 if (height > 1.0)
699 {
700 height = 1.0;
701 overflow = 1;
702 }
703
704 i_h = (int)(height * stats_h);
705 /* fprintf(stderr, "%d %f %f %d %d\n", index, history[index], height, i_h, overflow); */
706
707 draw_column(w_stats, x, i_h, overflow, limitter);
708 }
709 }
710 }
711
712 void show_stats_t(int y, int x, char *header, stats_t *data, char abbreviate)
713 {
714 if (data -> valid)
715 {
716 char *cur_str = format_value(data -> cur, 6, 2, abbreviate);
717 char *min_str = format_value(data -> min, 6, 2, abbreviate);
718 char *avg_str = format_value(data -> avg / (double)data -> n, 6, 2, abbreviate);
719 char *max_str = format_value(data -> max, 6, 2, abbreviate);
720 char *sd_str = format_value(calc_sd(data), 6, 2, abbreviate);
721
722 myprintloc(w_stats, y, x, "%s: %s %s %s %s %s", header,
723 data -> cur_valid ? cur_str : gettext(" n/a"),
724 min_str, avg_str, max_str, sd_str);
725
726 free(sd_str);
727 free(max_str);
728 free(avg_str);
729 free(min_str);
730 free(cur_str);
731 }
732 else
733 {
734 myprintloc(w_stats, y, x, gettext("%s: n/a"), header);
735 }
736 }
737
738 void update_stats(stats_t *resolve, stats_t *connect, stats_t *request, stats_t *total, stats_t *ssl_setup, int n_ok, int n_fail, const char *last_connect_str, const char *fp, char use_tfo, char dg, stats_t *st_to, stats_t *tcp_rtt_stats, int re_tx, int pmtu, int tos, stats_t *close_st, stats_t *t_write, int n_cookies, char abbreviate, stats_t *stats_header_size)
739 {
740 double k = 0.0;
741 char force_redraw = 0;
742 struct pollfd p = { 0, POLLIN, 0 };
743
744 werase(w_stats);
745
746 if (n_ok)
747 {
748 char buffer[4096] = { 0 }, *scc_str = NULL, *kalman_str = NULL;
749 int buflen = 0;
750
751 myprintloc(w_stats, 0, 0, " %6s %6s %6s %6s %6s", gettext("latest"), gettext("min"), gettext("avg"), gettext("max"), gettext("sd"));
752 show_stats_t(1, 0, gettext("resolve"), resolve, abbreviate);
753 show_stats_t(2, 0, gettext("connect"), connect, abbreviate);
754 show_stats_t(3, 0, gettext("ssl "), ssl_setup, abbreviate);
755 show_stats_t(4, 0, gettext("send "), t_write, abbreviate);
756 show_stats_t(5, 0, gettext("request"), request, abbreviate);
757 show_stats_t(6, 0, gettext("close "), close_st, abbreviate);
758 show_stats_t(7, 0, gettext("total "), total, abbreviate);
759
760 scc_str = format_value(get_cur_scc(), 5, 3, abbreviate);
761 kalman_str = format_value(kalman_do(total -> cur), 5, 3, abbreviate);
762 myprintloc(w_stats, 8, 0, gettext("ok: %3d, fail: %3d%s, scc: %s, kalman: %s"), n_ok, n_fail, use_tfo ? gettext(", with TFO") : "", scc_str, kalman_str);
763 free(kalman_str);
764 free(scc_str);
765
766 if (max_x >= 44 * 2 + 1)
767 {
768 double trend = calc_trend();
769 char trend_dir = ' ';
770
771 myprintloc(w_stats, 0, 45, " %6s %6s %6s %6s %6s", gettext("cur"), gettext("min"), gettext("avg"), gettext("max"), gettext("sd"));
772 show_stats_t(1, 45, gettext("t offst"), st_to, abbreviate);
773
774 #if defined(linux) || defined(__FreeBSD__)
775 show_stats_t(2, 45, gettext("tcp rtt"), tcp_rtt_stats, abbreviate);
776 #endif
777 show_stats_t(3, 45, gettext("headers"), stats_header_size, abbreviate);
778
779 if (trend < 0)
780 trend_dir = '-';
781 else if (trend > 0)
782 trend_dir = '+';
783
784 myprintloc(w_stats, 8, 48, gettext("# cookies: %d"), n_cookies);
785
786 #ifdef linux
787 myprintloc(w_stats, 9, 48, gettext("trend: %c%6.2f%%, re-tx: %2d, pmtu: %5d, TOS: %02x"), trend_dir, fabs(trend), re_tx, pmtu, tos);
788 #else
789 myprintloc(w_stats, 9, 48, gettext("trend: %c%6.2f%%, TOS: %02x"), trend_dir, fabs(trend), tos);
790 #endif
791 }
792
793 buflen = snprintf(buffer, sizeof buffer, gettext("HTTP rc: %s, SSL fp: %s"), last_connect_str, fp ? fp : gettext("n/a"));
794
795 if (buflen <= max_x)
796 myprintloc(w_stats, 9, 0, "%s", buffer);
797 else
798 {
799 static char prev_sf[48] = { 0 };
800
801 myprintloc(w_stats, 9, 0, gettext("http result code: %s"), last_connect_str);
802
803 if (fp && strcmp(prev_sf, fp))
804 {
805 slow_log(gettext("\nSSL fingerprint: %s"), fp);
806
807 memcpy(prev_sf, fp, 47);
808 }
809 }
810 }
811
812 memmove(&history[1], &history[0], (history_n - 1) * sizeof(double));
813 memmove(&history_set[1], &history_set[0], (history_n - 1) * sizeof(char));
814
815 history[0]= total -> cur;
816 history_set[0] = 1;
817
818 if (poll(&p, 1, 0) == 1 && p.revents == POLLIN)
819 {
820 int c = getch();
821
822 if (c == 12) /* ^L */
823 force_redraw = 1;
824
825 if (c == 'H')
826 pause_graphs = !pause_graphs;
827
828 if (c == 'q')
829 stop = 1;
830 }
831
832 if (dg && !pause_graphs)
833 {
834 draw_graph(k);
835 #ifdef FW
836 draw_fft();
837 #endif
838 }
839
840 wnoutrefresh(w_stats);
841
842 if (win_resize || force_redraw)
843 recreate_terminal();
844 }
0 /* $Revision$ */
1 #include <ncurses.h>
2
3 extern char win_resize;
4 extern char draw_phase;
5
6 void init_ncurses_ui(double graph_limit_in, double hz_in, char use_colors);
7 void end_ncurses(void);
8 void fast_log(const char *fmt, ...);
9 void slow_log(const char *fmt, ...);
10 void my_beep(void);
11 void update_terminal(void);
12 void status_line(char *fmt, ...);
13 void update_stats(stats_t *resolve, stats_t *connect, stats_t *request, stats_t *total, stats_t *ssl_setup, int n_ok, int n_fail, const char *last_connect_str, const char *fp, char use_tfo, char dg, stats_t *st_to, stats_t *tcp_rtt_stats, int re_tx, int pmtu, int tos, stats_t *close_st, stats_t *t_write, int n_cookies, char abbreviate, stats_t *stats_header_size);
+1229
-0
nl.po less more
0 # Dutch translations for HTTPing package.
1 # Copyright (C) 2013 folkert van heusden
2 # This file is distributed under the same license as the HTTPing package.
3 # folkert van heusden <folkert@vanheusden.com>, 2013.
4 # Translated by Joris Zwart - http://joriszwart.nl/
5 #
6 msgid ""
7 msgstr ""
8 "Project-Id-Version: HTTPing\n"
9 "Report-Msgid-Bugs-To: \n"
10 "POT-Creation-Date: 2013-05-04 15:29+0200\n"
11 "PO-Revision-Date: 2013-05-04 18:41+0100\n"
12 "Last-Translator: Joris Zwart <hallo@joriszwart.nl>\n"
13 "Language-Team: Dutch\n"
14 "Language: nl\n"
15 "MIME-Version: 1.0\n"
16 "Content-Type: text/plain; charset=UTF-8\n"
17 "Content-Transfer-Encoding: 8bit\n"
18 "Plural-Forms: nplurals=2; plural=(n != 1);\n"
19 "X-Poedit-Language: Dutch\n"
20 "X-Poedit-Country: NETHERLANDS\n"
21
22 #: error.c:23
23 #, c-format
24 msgid ""
25 "\n"
26 "\n"
27 "errno=%d which means %s (if applicable)\n"
28 msgstr ""
29 "\n"
30 "\n"
31 "errno=%d en dat betekent: %s (indien van toepassing)\n"
32
33 #: error.c:39
34 #, c-format
35 msgid "Error message '%s' truncated"
36 msgstr "De foutmelding '%s' past niet in de buffer."
37
38 #: fft.c:21
39 msgid "failed allocating memory for fft (1)"
40 msgstr "Geheugentoewijzingsprobleem voor 'fft (1)'."
41
42 #: fft.c:25
43 msgid "failed allocating memory for fft (2)"
44 msgstr "Geheugentoewijzingsprobleem voor 'fft (2)'."
45
46 #: fft.c:30
47 msgid "failed calculating plan for fft"
48 msgstr "Probleem bij het voorbereiden van de FFT berekening."
49
50 #: help.c:77
51 #, c-format
52 msgid "HTTPing v"
53 msgstr "HTTPing versie "
54
55 msgid "adds an extra request-header"
56 msgstr "voeg een extra verzoek-regel toe"
57
58 #: help.c:79
59 #, c-format
60 msgid " * SSL support included (-l)\n"
61 msgstr " * Ondersteuning voor SSL (-l)\n"
62
63 #: help.c:84
64 #, c-format
65 msgid " * ncurses interface with FFT included (-K)\n"
66 msgstr " * ncurses gebruikersinterface met fourier transformatie berekening (-K)\n"
67
68 #: help.c:86
69 #, c-format
70 msgid " * ncurses interface included (-K)\n"
71 msgstr " * ncurses gebruikersinterface (-K)\n"
72
73 #: help.c:91
74 #, c-format
75 msgid " * TFO (TCP fast open) support included (-F)\n"
76 msgstr " * Ondersteuning voor 'TFO (TCP fast open)' (-F)\n"
77
78 #: help.c:93
79 #: help.c:293
80 #, c-format
81 msgid "\n"
82 msgstr "\n"
83
84 #: help.c:176
85 #, c-format
86 msgid " *** where to connect to ***\n"
87 msgstr " *** adresspecificaties ***\n"
88
89 #: help.c:177
90 msgid "URL to ping (e.g. -g http://localhost/)"
91 msgstr "URL om te pingen (bijvoorbeeld -g http://localhost/)"
92
93 #: help.c:178
94 msgid "hostname to ping (e.g. localhost) - use either -g or -h"
95 msgstr "Systeemnaam om te pingen (bijvoorbeeld localhost). -g en -h kunnen niet gecombineerd worden"
96
97 #: help.c:179
98 msgid "portnumber (e.g. 80) - use with -h"
99 msgstr "poortnummer (bijv. 80), voor gebruik in combinatie met -h"
100
101 #: help.c:180
102 msgid "use IPv6 when resolving/connecting"
103 msgstr "gebruik IPv6 bij het omzetten van een systeemnaam en bij het maken van een verbinding"
104
105 #: help.c:182
106 msgid "connect using SSL. pinging an https URL automatically enables this setting"
107 msgstr "gebruik SSL encryptie. Wanneer men een https-URL kiest, dan zal deze optie automatisch ingeschakeld worden."
108
109 #: help.c:187
110 #, c-format
111 msgid " *** proxy settings ***\n"
112 msgstr " *** proxy instellingen ***\n"
113
114 #: help.c:188
115 msgid "x should be \"host:port\" which are the network settings of the http/https proxy server. ipv6 ip-address should be \"[ip:address]:port\""
116 msgstr "x moet zijn \"host:port\", dat zijn de parameters van de http/https proxyserver. ipv6 ip-adressen moeten opgebouwd zijn als volgt: \"[ip:adres]:port\""
117
118 #: help.c:189
119 msgid "fetch proxy settings from environment variables"
120 msgstr "haal de proxy-instellingen uit de omgevingsvariabelen"
121
122 #: help.c:190
123 msgid "username for authentication against proxy"
124 msgstr "gebruikersnaam voor proxy-authenticatie"
125
126 #: help.c:191
127 msgid "password for authentication against proxy"
128 msgstr "toegangscode voor proxy-authenticatie"
129
130 #: help.c:192
131 msgid "read password for proxy authentication from file x"
132 msgstr "lees toegangscode voor proxy-authenticatie uit bestand x"
133
134 #: help.c:193
135 msgid "proxy is a socks5 server"
136 msgstr "de proxy is een socks5 systeem"
137
138 #: help.c:194
139 msgid "adds \"&x=[random value]\" to the request URL"
140 msgstr "voeg een \"&x=[willekeurig getal]\" aan de geselecteerde URL"
141
142 #: help.c:198
143 #, c-format
144 msgid " *** timing settings ***\n"
145 msgstr " *** tijdsinstellingen ***\n"
146
147 #: help.c:199
148 msgid "how many times to ping"
149 msgstr "hoe vaak te pingen"
150
151 #: help.c:200
152 msgid "delay between each ping"
153 msgstr "pauze tussen iedere ping"
154
155 #: help.c:201
156 msgid "timeout (default: 30s)"
157 msgstr "hoelang te wachten op een server die niet reageert (standaard waarde: 30 seconden)"
158
159 #: help.c:202
160 msgid "execute pings at multiples of interval relative to start, automatically enabled in ncurses output mode"
161 msgstr "zorg ervoor dat pings steeds met dezelfde interval uitgevoerd worden, relatief tot het start tijdstip. deze instelling wordt automatisch aangezet in \"ncurses\"-mode"
162
163 #: help.c:203
164 msgid "flood connect (no delays)"
165 msgstr "geen vertraging tussen iedere ping"
166
167 #: help.c:207
168 #, c-format
169 msgid " *** HTTP settings ***\n"
170 msgstr " *** HTTP-instellingen ***\n"
171
172 #: help.c:208
173 msgid "ask any proxies on the way not to cache the requests"
174 msgstr "vraag aan de proxy-sysstemen in de route tussen het lokale systeem en het bestemmingssysteem om de verzoeken niet te cachen"
175
176 #: help.c:209
177 msgid "connect to a different host than in the URL given"
178 msgstr "verbind en zend de URL-verzoeken naar een ander systeem dan wat in de URL is opgegeven"
179
180 #: help.c:210
181 msgid "return the cookies given by the HTTP server in the following request(s)"
182 msgstr "als de HTTP-server cookies geeft, zend die dan mee terug bij volgende pings"
183
184 #: help.c:211
185 msgid "do not add \"Host:\"-line to the request headers"
186 msgstr "voeg geen \"Host:\"-regel in het verbindingsverzoek"
187
188 #: help.c:212
189 msgid "use a persistent connection. adds a 'C' to the output if httping had to reconnect"
190 msgstr "gebruik een blijvende verbinding. als het bestemmingssysteem de verbinding verbroken heeft, dan zal HTTPing een \"C\" toevoegen aan de uitvoer"
191
192 #: help.c:213
193 msgid "use 'x' for the UserAgent header"
194 msgstr "gebruik 'x' in de UserAgent verzoekinstellingen"
195
196 #: help.c:214
197 msgid "use 'x' for the Referer header"
198 msgstr "gebruik 'x' in de Referer verzoekinstellingen"
199
200 #: help.c:218
201 #, c-format
202 msgid " *** networking settings ***\n"
203 msgstr " *** netwerk instellingen ***\n"
204
205 #: help.c:219
206 msgid "limit the MTU size"
207 msgstr "beperkt de MTU omvang"
208
209 #: help.c:220
210 msgid "do not disable Naggle"
211 msgstr "zet het Naggle-algorithme niet uit"
212
213 #: help.c:221
214 msgid "receive buffer size"
215 msgstr "ontvangst buffer omvang"
216
217 #: help.c:222
218 msgid "transmit buffer size"
219 msgstr "verzend buffer omvang"
220
221 #: help.c:223
222 msgid "resolve hostname only once (useful when pinging roundrobin DNS: also takes the first DNS lookup out of the loop so that the first measurement is also correct)"
223 msgstr "eenmalig systeemnaam vertalen (dit is zinvol bij het pingen van een roterende DNS, bovendien haalt het de eerste vertaling uit de ping lus zodat de 1e ping niet een bovengemiddelde tijd duurt)"
224
225 #: help.c:224
226 msgid "do not abort the program if resolving failed: keep retrying"
227 msgstr "breek het programma niet af als de systeemnaamvertaling mislukt is"
228
229 #: help.c:225
230 msgid "bind to an ip-address (and thus interface) with an optional port"
231 msgstr "stuur verzoeken via een specifieke netwerk adapter, eventueel zelfs vanaf een specifieke port"
232
233 #: help.c:227
234 msgid "\"TCP fast open\" (TFO), reduces the latency of TCP connects"
235 msgstr "\"TCP fast open\" (TFO), dit verlaagt de latency van opvolgende TCP verbindingen"
236
237 #: help.c:229
238 msgid "set priority of packets"
239 msgstr "zet prioriteit van pakketten"
240
241 #: help.c:230
242 msgid "set TOS (type of service)"
243 msgstr "zet de TOS (diensttype)"
244
245 #: help.c:234
246 #, c-format
247 msgid " *** HTTP authentication ***\n"
248 msgstr " *** HTTP authenticatie ***\n"
249
250 #: help.c:235
251 msgid "activate (\"basic\") authentication"
252 msgstr "activeer (\"basic\")-authenticatie"
253
254 #: help.c:236
255 msgid "username for authentication"
256 msgstr "gebruikersnaam voor authenticatie"
257
258 #: help.c:237
259 msgid "password for authentication"
260 msgstr "toegangscode voor authenticatie"
261
262 #: help.c:238
263 msgid "read the password fom the file 'x' (replacement for -P)"
264 msgstr "lees de toegangscode uit bestand 'x'"
265
266 #: help.c:242
267 #, c-format
268 msgid " *** output settings ***\n"
269 msgstr " *** uitvoerinstellingen ***\n"
270
271 #: help.c:243
272 msgid "show statuscodes"
273 msgstr "toon statuscodes"
274
275 #: help.c:244
276 msgid "split measured time in its individual components (resolve, connect, send, etc."
277 msgstr "toon alle individuele componenten (verbinden, zenden, etc) van de gemeten tijden"
278
279 #: help.c:245
280 msgid "from what ping value to show the value in red (must be bigger than yellow), only in color mode (-Y)"
281 msgstr "toon de waardes in rood vanaf welke gemeten tijden"
282
283 #: help.c:246
284 msgid "from what ping value to show the value in yellow"
285 msgstr "toon de waardes in 't geel vanaf welke gemeten tijden"
286
287 #: help.c:247
288 msgid "from what ping value to show the results"
289 msgstr "filter alle metingen die beneden deze waarde vallen"
290
291 #: help.c:248
292 msgid "put a timestamp before the measured values, use -v to include the date and -vv to show in microseconds"
293 msgstr "toon een tijdstempel voor iedere gemeten waarde. gebruik -v om ook de datum te zien en -vv om ook microseconden te zien"
294
295 #: help.c:249
296 msgid "show an aggregate each x[/y[/z[/etc]]] seconds"
297 msgstr "toon cumulatief de waardes van x[/y[/etc]] seconden"
298
299 #: help.c:251
300 msgid "show fingerprint (SSL)"
301 msgstr "toon een vingerafdruk voor de SSL-verbinding"
302
303 #: help.c:253
304 msgid "verbose mode"
305 msgstr "toon meer details"
306
307 #: help.c:257
308 #, c-format
309 msgid " *** \"GET\" (instead of HTTP \"HEAD\") settings ***\n"
310 msgstr " *** \"GET\" (in plaats van HTTP \"HEAD\") instellingen ***\n"
311
312 #: help.c:258
313 msgid "do a GET request instead of HEAD (read the contents of the page as well)"
314 msgstr "doe een GET verzoek in plaats van een HEAD verzoek en haal ook de inhoud van een pagina op"
315
316 #: help.c:259
317 msgid "show transfer speed in KB/s (use with -G)"
318 msgstr "toon de verzendsnelheid in KB/s (gebruik in combinatie met -G)"
319
320 #: help.c:260
321 msgid "like -b but use compression if available"
322 msgstr "zoals -b maar gebruik compressie als het HTTP systeem dit ondersteunt"
323
324 #: help.c:261
325 msgid "limit the amount of data transferred (for -b) to 'x' (in bytes)"
326 msgstr "limiteer de hoeveelheid verzonden data (ism -b) tot 'x' bytes"
327
328 #: help.c:262
329 msgid "show the number of KB transferred (for -b)"
330 msgstr "toon de totaal verzonden hoeveelheid data (in KB, ism -b)"
331
332 #: help.c:266
333 #, c-format
334 msgid " *** output mode settings ***\n"
335 msgstr " *** uitvoer modeinstellingen ***\n"
336
337 #: help.c:267
338 msgid "quiet, only returncode"
339 msgstr "toon niets, geef alleen een resultaatwaarde terug"
340
341 #: help.c:268
342 msgid "give machine parseable output (see also -o and -e)"
343 msgstr "toon resultaat in computervriendelijkformaat (zie ook -o en -e)"
344
345 #: help.c:269
346 msgid "json output, cannot be combined with -m"
347 msgstr "json uitvoer, kan niet met -m gecombineerd worden"
348
349 #: help.c:270
350 msgid "what http results codes indicate 'ok' comma seperated WITHOUT spaces inbetween default is 200, use with -e"
351 msgstr "welke HTTP statuscodes als 'ok' te beschouwen. dit moet een met komma gescheiden lijst (geen spaties) zijn. de standaard waarde is 200. gebruik deze instelling ism -e"
352
353 #: help.c:271
354 msgid "string to display when http result code doesn't match"
355 msgstr "wat te laten zien als de HTTP statuscodes niet overeenkomen"
356
357 #: help.c:272
358 msgid "Nagios-mode: return 1 when avg. response time >= warn, 2 if >= crit, otherwhise return 0"
359 msgstr "Nagios-mode 1: geef 1 terug als de gemiddelde reactiesnelheid >= \"warn\" en 2 als die snelheid >= \"crit\", anders geef 0 terug"
360
361 #: help.c:273
362 msgid "Nagios mode 2: return 0 when all fine, 'x' when anything failes"
363 msgstr "Nagios mode 2: geef 0 terug als alles goed ging, anders 'x'"
364
365 #: help.c:274
366 msgid "add a cookie to the request"
367 msgstr "voeg een cookie toe aan het HTTP-verzoek"
368
369 #: help.c:275
370 msgid "add colors"
371 msgstr "gebruik kleuren"
372
373 #: help.c:276
374 msgid "audible ping"
375 msgstr "hoorbare piep"
376
377 #: help.c:281
378 #, c-format
379 msgid " *** GUI/ncurses mode settings ***\n"
380 msgstr " *** grafische interface/ncurses mode instellingen ***\n"
381
382 #: help.c:282
383 msgid "ncurses/GUI mode"
384 msgstr "ncurses/GUI mode"
385
386 #: help.c:284
387 msgid "draw phase (fourier transform) in gui"
388 msgstr "toon fasediagram"
389
390 #: help.c:286
391 msgid "when the duration is x or more, show ping line in the slow log window (the middle window)"
392 msgstr "als de tijdmetingen groter zijn dan x, toon dan het resultaat in het middelste venster"
393
394 #: help.c:287
395 msgid "do not scale to values above x"
396 msgstr "schaal niet naar waardes boven 'x'"
397
398 #: help.c:288
399 msgid "do not show graphs (in ncurses/GUI mode)"
400 msgstr "toon geen grafieken"
401
402 #: help.c:292
403 msgid "show the version"
404 msgstr "toon de versie van dit programma"
405
406 #: help.c:305
407 #, c-format
408 msgid "Voorbeeld:\n"
409 msgstr ""
410
411 #: io.c:43
412 #: io.c:78
413 #, c-format
414 msgid "myread::select failed: %s"
415 msgstr "leesfout: %s"
416
417 #: io.c:94
418 #, c-format
419 msgid "myread::read failed: %s"
420 msgstr "leesfout: %s"
421
422 #: io.c:138
423 #, c-format
424 msgid "mywrite::select failed: %s"
425 msgstr "selecteer fout: %s"
426
427 #: io.c:152
428 #, c-format
429 msgid "mywrite::write failed: %s"
430 msgstr "schrijffout: %s"
431
432 #: io.c:174
433 #, c-format
434 msgid "set_fd_nonblocking failed! (%s)\n"
435 msgstr "\"set_fd_nonblocking\" fout: %s\n"
436
437 #: io.c:187
438 #, c-format
439 msgid "set_fd_blocking failed! (%s)\n"
440 msgstr "\"set_fd_blocking\" fout: %s\n"
441
442 #: main.c:109
443 #: main.c:108
444 #, c-format
445 msgid "%s, run time: %.3fs, press ctrl + c to stop"
446 msgstr "%s, loop tijd: %.3fs, druk op ctrl + c om het programma te stoppen"
447
448 #: main.c:244
449 #: main.c:243
450 #, c-format
451 msgid "Got signal %d\n"
452 msgstr "Signaal %d\n"
453
454 #: main.c:255
455 #: main.c:254
456 #, c-format
457 msgid "Cannot open password-file %s"
458 msgstr "Kan het toegangscodebestand '%s' niet openen"
459
460 #: main.c:258
461 #: main.c:257
462 #, c-format
463 msgid "Problem reading password from file %s"
464 msgstr "Probleem bij het lezen van de toegangscode uit bestand '%s'"
465
466 #: main.c:365
467 #: main.c:364
468 #, c-format
469 msgid "URL too big, HTTPing has a %d bytes limit"
470 msgstr "URL is te groot, HTTPing heeft daar een limiet van %d bytes op"
471
472 #: main.c:384
473 #: main.c:383
474 msgid "using \"http://\" with SSL enabled (-l)"
475 msgstr "\"http://\" gebruikt met SSL ingeschakeld (-l)"
476
477 #: main.c:519
478 #: main.c:518
479 #, c-format
480 msgid "AGG[%d]: %d values, min/avg/max%s = %.1f/%.1f/%.1f"
481 msgstr "CUM[%d]: %d waardes, min/gem/max%s = %.1f/%.1f/%.1f"
482
483 #: main.c:519
484 #: main.c:2294
485 #: main.c:518
486 #: main.c:2289
487 msgid "/sd"
488 msgstr "/sd"
489
490 #: main.c:576
491 #: main.c:575
492 msgid "-n: missing parameter\n"
493 msgstr "-n: ontbrekende parameter\n"
494
495 #: main.c:594
496 #: main.c:603
497 #: main.c:593
498 #: main.c:602
499 #, c-format
500 msgid "cannot convert ip address '%s' (for -y)\n"
501 msgstr "kan het IP-adres '%s' niet vertalen (-y)\n"
502
503 #: main.c:710
504 #: main.c:709
505 #, c-format
506 msgid "CRITICAL - connecting failed: %s"
507 msgstr "KRITIEK - verbinding mislukt: %s"
508
509 #: main.c:715
510 #: main.c:714
511 #, c-format
512 msgid "CRITICAL - average httping-time is %.1f\n"
513 msgstr "KRITIEK - gemiddelde HTTPing tijd is %.1f\n"
514
515 #: main.c:720
516 #: main.c:719
517 #, c-format
518 msgid "WARNING - average httping-time is %.1f\n"
519 msgstr "WAARSCHUWING - gemiddelde HTTPing tijd is %.1f\n"
520
521 #: main.c:724
522 #: main.c:723
523 #, c-format
524 msgid "OK - average httping-time is %.1f (%s)|ping=%f\n"
525 msgstr "OK - gemiddelde HTTPing-tijd is %.1f (%s)|ping=%f\n"
526
527 #: main.c:734
528 #: main.c:733
529 #, c-format
530 msgid "OK - all fine, avg httping time is %.1f|ping=%f\n"
531 msgstr "OK - gemiddelde HTTPing-tijd is %.1f|ping=%f\n"
532
533 #: main.c:738
534 #: main.c:737
535 #, c-format
536 msgid "%s: - failed: %s"
537 msgstr "%s: - mislukt: %s"
538
539 #: main.c:1025
540 #: main.c:1020
541 #, c-format
542 msgid ""
543 "\n"
544 " *** -A is no longer required ***\n"
545 "\n"
546 msgstr ""
547 "\n"
548 " *** -A is niet langer nodig ***\n"
549 "\n"
550
551 #: main.c:1170
552 #: main.c:1165
553 msgid "-i cannot have a value smaller than zero"
554 msgstr "-i waarde kan niet kleiner dan 0 zijn"
555
556 #: main.c:1224
557 #: main.c:1232
558 #: main.c:1219
559 #: main.c:1227
560 msgid "-n and -N are mutual exclusive\n"
561 msgstr "-n en -N zijn wederzijds uitsluitende\n"
562
563 #: main.c:1253
564 #: main.c:1248
565 #, c-format
566 msgid "Warning: TCP TFO is not supported. Disabling.\n"
567 msgstr "Let op: TCP TFO is niet ondersteund.\n"
568
569 #: main.c:1269
570 #: main.c:1264
571 #, c-format
572 msgid ""
573 "\n"
574 "\n"
575 "Please run:\n"
576 "\t%s --help\n"
577 "to see a list of options.\n"
578 "\n"
579 msgstr ""
580 "\n"
581 "\n"
582 "Start:\n"
583 "\t%s --help\n"
584 "om een lijst van opties te zien.\n"
585 "\n"
586
587 #: main.c:1281
588 #, c-format
589 msgid ""
590 "No URL/host to ping given\n"
591 "\n"
592 msgstr ""
593 "Geen URL of systeemnaam gespecificeerd om te pingen\n"
594 "\n"
595
596 #: main.c:1291
597 #: main.c:1286
598 msgid "Cannot combine -m, -M and -K"
599 msgstr "-m, -M en -K kunnen niet gecombineerd worden"
600
601 #: main.c:1294
602 #: main.c:1289
603 msgid "Aggregates can only be used in non-machine/json-output mode"
604 msgstr "Cumulatieven kunnen niet in machine-uitvoer/json-uitvoer modi gebruikt worden"
605
606 #: main.c:1299
607 #: main.c:1294
608 msgid "-b/-B can only be used when also using -G (GET instead of HEAD) or -l (use SSL)\n"
609 msgstr "-b/-B kunnen alleen gebruikt worden ism -G or -l\n"
610
611 #: main.c:1302
612 #: main.c:1297
613 msgid "TCP Fast open and SSL not supported together\n"
614 msgstr "\"TCP Fast open\" en SSL kunnen niet gecombineerd worden\n"
615
616 #: main.c:1332
617 #: main.c:1327
618 msgid ""
619 "\n"
620 "Auto enabling SSL due to https-URL"
621 msgstr ""
622 "\n"
623 "SSL ingeschakeld vanwege https-URL"
624
625 #: main.c:1338
626 #: main.c:1333
627 #, c-format
628 msgid "Auto enabling SSL due to https-URL"
629 msgstr "SSL ingeschakeld vanwege https-URL"
630
631 #: main.c:1347
632 #: main.c:1342
633 #, c-format
634 msgid ""
635 "\n"
636 "Connecting to host %s, port %d and requesting file %s"
637 msgstr ""
638 "\n"
639 "Verbinden met %s:%d en opvragen van bestand %s"
640
641 #: main.c:1350
642 #: main.c:1345
643 #, c-format
644 msgid ""
645 "\n"
646 "Using proxyserver: %s:%d"
647 msgstr ""
648 "\n"
649 "Proxy %s:%d wordt gebruikt"
650
651 #: main.c:1355
652 #: main.c:1350
653 #, c-format
654 msgid ""
655 "Connecting to host %s, port %d and requesting file %s\n"
656 "\n"
657 msgstr ""
658 "Verbinden met %s:%d en opvragen van bestand %s\n"
659 "\n"
660
661 #: main.c:1358
662 #: main.c:1353
663 #, c-format
664 msgid "Using proxyserver: %s:%d\n"
665 msgstr "Proxy: %s:%d\n"
666
667 #: main.c:1369
668 #: main.c:1364
669 msgid "problem creating SSL context"
670 msgstr "Probleem bij aanmaken SSL-context"
671
672 #: main.c:1389
673 #: main.c:1384
674 msgid "Interval must be > 0 when using adaptive interval"
675 msgstr "Interval moet groter dan 0 zijn bij adaptieve interval"
676
677 #: main.c:1417
678 #: main.c:1435
679 #: main.c:1519
680 #: main.c:1412
681 #: main.c:1430
682 #: main.c:1514
683 #, c-format
684 msgid ""
685 "\n"
686 "Resolving hostname %s"
687 msgstr ""
688 "\n"
689 "Vertalen systeemnaam '%s'"
690
691 #: main.c:1427
692 #: main.c:1452
693 #: main.c:1545
694 #: main.c:1422
695 #: main.c:1447
696 #: main.c:1540
697 #, c-format
698 msgid "No valid IPv4 or IPv6 address found for %s"
699 msgstr "Geen geldig IPv4 of IPv6 adres gevonden voor '%s'"
700
701 #: main.c:1579
702 #: main.c:1574
703 msgid "Will no longer inform about request headers too large."
704 msgstr "Zal niet langer meldingen tonen over te grote verzoeken."
705
706 #: main.c:1581
707 #: main.c:1576
708 #, c-format
709 msgid "Request headers > 4KB! (%d bytes) This may give failures with some HTTP servers."
710 msgstr "Verzoek is groter dan 4KB! (%d bytes) Dit kan problemen opleveren met sommige HTTP-servers."
711
712 #: main.c:1685
713 #: main.c:1680
714 msgid "timeout connecting to host"
715 msgstr "systeem reageerde niet op tijd"
716
717 #: main.c:1748
718 #: main.c:1743
719 msgid "error sending request to host"
720 msgstr "probleem bij verzenden verzoek naar systeem"
721
722 #: main.c:1750
723 #: main.c:1800
724 #: main.c:1745
725 #: main.c:1795
726 msgid "timeout sending to host"
727 msgstr "systeem reageerde niet op tijd bij verzenden verzoek"
728
729 #: main.c:1752
730 #: main.c:1747
731 msgid "retrieved invalid data from host"
732 msgstr "ongeldige data ontvangen van systeem"
733
734 #: main.c:1756
735 #: main.c:1751
736 msgid "connection prematurely closed by peer"
737 msgstr "verbinding voortijdig gesloten door systeem"
738
739 #: main.c:1790
740 #: main.c:1785
741 msgid ""
742 "\n"
743 "No longer emitting message about \"still data in transit\""
744 msgstr ""
745 "\n"
746 "Er zullen geen meldingen meer getoond worden over data die nog getransporteerd wordt."
747
748 #: main.c:1792
749 #: main.c:1787
750 #, c-format
751 msgid ""
752 "\n"
753 "HTTP server started sending data with %d bytes still in transit"
754 msgstr ""
755 "\n"
756 "HTTP server begon al een reaktie te versturen terwijl er nog %d bytes onderweg waren"
757
758 #: main.c:1813
759 #: main.c:1808
760 msgid "failed to obtain TOS info"
761 msgstr "probleem bij ophalen TOS-informatie"
762
763 #: main.c:1827
764 #: main.c:1822
765 msgid ""
766 "\n"
767 "No longer emitting message about \"more data than response headers\""
768 msgstr ""
769 "\n"
770 "De melding \"HTTP server verzond meer data dan alleen de antwoord metadata\" zal niet meer getoond worden."
771
772 #: main.c:1829
773 #: main.c:1824
774 msgid ""
775 "\n"
776 "HTTP server sent more data than just the response headers"
777 msgstr ""
778 "\n"
779 "HTTP server verzond meer data dan alleen de antwoord metadata"
780
781 #: main.c:1878
782 #: main.c:1873
783 msgid "'Content-Length'-header missing!"
784 msgstr "'Content-Length' metadata ontbreekt"
785
786 #: main.c:1910
787 #: main.c:1905
788 msgid "short read during receiving reply-headers from host"
789 msgstr "ontvangprobleem bij metadata van systeem"
790
791 #: main.c:1912
792 #: main.c:1907
793 msgid "timeout while receiving reply-headers from host"
794 msgstr "geen reactie bij ontvangen metadata van systeem"
795
796 #: main.c:1945
797 #: main.c:1940
798 msgid "read of response body dataa failed"
799 msgstr "lezen van reactiedata mislukt"
800
801 #: main.c:1980
802 #: main.c:1975
803 msgid "error shutting down ssl"
804 msgstr "probleem bij stoppen SSL-verbinding"
805
806 #: main.c:2026
807 #: main.c:2087
808 #: main.c:2021
809 #: main.c:2082
810 #, c-format
811 msgid "getnameinfo() failed: %d (%s)"
812 msgstr "getnameinfo() faalde: %d (%s)"
813
814 #: main.c:2061
815 #: main.c:2056
816 msgid "connected to"
817 msgstr "verbinden met"
818
819 #: main.c:2061
820 #: main.c:2056
821 msgid "pinged host"
822 msgstr "gepingde systeem"
823
824 #: main.c:2105
825 #: main.c:2100
826 #, c-format
827 msgid "%s%s%s%s%s:%s%d%s (%d/%d bytes), seq=%s%d%s "
828 msgstr "%s%s%s%s%s:%s%d%s (%d/%d bytes), volgnr=%s%d%s "
829
830 #: main.c:2107
831 #: main.c:2102
832 #, c-format
833 msgid "%s%s%s%s%s:%s%d%s (%d bytes), seq=%s%d%s "
834 msgstr "%s%s%s%s%s:%s%d%s (%d bytes), volgnr=%s%d%s "
835
836 #: main.c:2113
837 #: main.c:2114
838 #: nc.c:721
839 #: main.c:2108
840 #: main.c:2109
841 msgid " n/a"
842 msgstr " ---"
843
844 #: main.c:2119
845 #: main.c:2114
846 #, c-format
847 msgid "time=%s+%s+%s+%s+%s%s=%s%s%s%s ms %s%s%s"
848 msgstr "tijd=%s+%s+%s+%s+%s%s=%s%s%s%s ms %s%s%s"
849
850 #: main.c:2129
851 #: main.c:2124
852 #, c-format
853 msgid "time=%s%s%s ms %s%s%s"
854 msgstr "tijd=%s%s%s ms %s%s%s"
855
856 #: main.c:2149
857 #: main.c:2144
858 msgid "not "
859 msgstr "niet "
860
861 #: main.c:2150
862 #: main.c:2145
863 msgid "compressed)"
864 msgstr "gecomprimeerd)"
865
866 #: main.c:2162
867 #: main.c:2157
868 #, c-format
869 msgid " toff=%d"
870 msgstr " tijdoffset=%d"
871
872 #: main.c:2166
873 #: main.c:2161
874 #, c-format
875 msgid " age=%d"
876 msgstr " leeftijd=%d"
877
878 #: main.c:2282
879 #: main.c:2277
880 #, c-format
881 msgid "--- %s ping statistics ---\n"
882 msgstr "--- %s ping statistieken ---\n"
883
884 #: main.c:2285
885 #: main.c:2280
886 #, c-format
887 msgid "internal error! (curncount)\n"
888 msgstr "interne fout! (curncount)\n"
889
890 #: main.c:2290
891 #: main.c:2285
892 #, c-format
893 msgid "%s%d%s connects, %s%d%s ok, %s%3.2f%%%s failed, time %s%s%.0fms%s\n"
894 msgstr "%s%d%s verbindingen, %s%d%s ok, %s%3.2f%%%s mislukt, tijd %s%s%.0fms%s\n"
895
896 #: main.c:2294
897 #: main.c:2289
898 #, c-format
899 msgid "round-trip min/avg/max%s = %s%.1f%s/%s%.1f%s/%s%.1f%s"
900 msgstr "retour min/gem/max%s = %s%.1f%s/%s%.1f%s/%s%.1f%s"
901
902 #: main.c:2305
903 #: main.c:2300
904 #, c-format
905 msgid "Transfer speed: min/avg/max = %s%f%s/%s%f%s/%s%f%s KB\n"
906 msgstr "Verzendsnelheid: min/gem/max = %s%f%s/%s%f%s/%s%f%s KB\n"
907
908 #: mssl.c:79
909 #, c-format
910 msgid "READ_SSL: io-error: %s"
911 msgstr "SSL lezen, I/O fout: %s"
912
913 #: mssl.c:110
914 #, c-format
915 msgid "WRITE_SSL: io-error: %s"
916 msgstr "SSL schrijven, I/O fout: %s"
917
918 #: mssl.c:141
919 #, c-format
920 msgid "problem setting receive timeout (%s)"
921 msgstr "probleem bij instellen ontvangsttijdslimiet (%s)"
922
923 #: mssl.c:147
924 #, c-format
925 msgid "problem setting transmit timeout (%s)"
926 msgstr "probleem bij instellen verzendtijdslimiet (%s)"
927
928 #: mssl.c:159
929 #, c-format
930 msgid "problem starting SSL connection: %d"
931 msgstr "probleem bij starten SSL verbinding: %d"
932
933 #: mssl.c:259
934 msgid "Problem sending request to proxy"
935 msgstr "Probleem bij verzenden verzoek naar proxy"
936
937 #: mssl.c:268
938 msgid "Problem retrieving proxy response"
939 msgstr "Probleem in ontvangen proxyreactie"
940
941 #: mssl.c:282
942 msgid "Invalid proxy response headers"
943 msgstr "Ongeldige proxyreactie"
944
945 #: mssl.c:289
946 #, c-format
947 msgid "Proxy indicated error: %s"
948 msgstr "Proxy gaf een fout aan: %s"
949
950 #: nc.c:57
951 msgid "realloc issue"
952 msgstr "geheugenfout"
953
954 #: nc.c:542
955 #, c-format
956 msgid "highest: %6.2fHz, avg: %6.2fHz"
957 msgstr "hoogste: %6.2fHz, gem: %6.2fHz"
958
959 #: nc.c:668
960 #, c-format
961 msgid "graph range: %7.2fms - %7.2fms "
962 msgstr "grafiekbandbreedte: %7.2fms - %7.2fms "
963
964 #: nc.c:732
965 #, c-format
966 msgid "%s: n/a"
967 msgstr "%s: ---"
968
969 #: nc.c:749
970 msgid "latest"
971 msgstr "laatste"
972
973 #: nc.c:749
974 #: nc.c:769
975 msgid "min"
976 msgstr "min"
977
978 #: nc.c:749
979 #: nc.c:769
980 msgid "avg"
981 msgstr "gem"
982
983 #: nc.c:749
984 #: nc.c:769
985 msgid "max"
986 msgstr "max"
987
988 #: nc.c:749
989 #: nc.c:769
990 msgid "sd"
991 msgstr "sd"
992
993 #: nc.c:750
994 msgid "resolve"
995 msgstr "vertaal"
996
997 #: nc.c:751
998 msgid "connect"
999 msgstr "verbind"
1000
1001 #: nc.c:752
1002 msgid "ssl "
1003 msgstr "ssl "
1004
1005 #: nc.c:753
1006 msgid "send "
1007 msgstr "zend "
1008
1009 #: nc.c:754
1010 msgid "request"
1011 msgstr "verzoek"
1012
1013 #: nc.c:755
1014 msgid "close "
1015 msgstr "sluiten"
1016
1017 #: nc.c:756
1018 msgid "total "
1019 msgstr "totaal "
1020
1021 #: nc.c:760
1022 #, c-format
1023 msgid "ok: %3d, fail: %3d%s, scc: %s, kalman: %s"
1024 msgstr "ok: %2d, mislukt: %2d%s, scc: %s, Kalman: %s"
1025
1026 #: nc.c:760
1027 msgid ", with TFO"
1028 msgstr ", met TFO"
1029
1030 #: nc.c:769
1031 msgid "cur"
1032 msgstr "nu"
1033
1034 #: nc.c:770
1035 msgid "t offst"
1036 msgstr "t offst"
1037
1038 #: nc.c:773
1039 msgid "tcp rtt"
1040 msgstr "TCP RTT"
1041
1042 #: nc.c:775
1043 msgid "headers"
1044 msgstr "meta "
1045
1046 #: nc.c:782
1047 #, c-format
1048 msgid "# cookies: %d"
1049 msgstr "# cookies: %d"
1050
1051 #: nc.c:784
1052 #, c-format
1053 msgid "trend: %c%6.2f%%, re-tx: %2d, pmtu: %5d, TOS: %02x"
1054 msgstr "trend: %c%6.2f%%, re-tx: %2d, pmtu: %5d, TOS: %02x"
1055
1056 #: nc.c:787
1057 #, c-format
1058 msgid "HTTP rc: %s, SSL fp: %s"
1059 msgstr "HTTP rc: %s, SSL va: %s"
1060
1061 #: nc.c:787
1062 msgid "n/a"
1063 msgstr "---"
1064
1065 #: nc.c:795
1066 #, c-format
1067 msgid "http result code: %s"
1068 msgstr "HTTP statuscode: %s"
1069
1070 #: nc.c:799
1071 #, c-format
1072 msgid ""
1073 "\n"
1074 "SSL fingerprint: %s"
1075 msgstr ""
1076 "\n"
1077 "SSL vingerafdruk: %s"
1078
1079 #: res.c:36
1080 #, c-format
1081 msgid "Resolving %s %sfailed: %s"
1082 msgstr "Vertalen %s %smislukt: %s"
1083
1084 #: res.c:36
1085 msgid "(IPv6) "
1086 msgstr "(IPv6) "
1087
1088 #: res.c:71
1089 #, c-format
1090 msgid "Problem resolving %s (IPv4): %s"
1091 msgstr "Probleem vertalen %s (IPv4): %s"
1092
1093 #: socks5.c:56
1094 #, c-format
1095 msgid "socks5connect: reply with requested authentication method does not say version 5 (%02x)"
1096 msgstr "socks5connect: reactie geeft niet versie 5 aan (%02x)"
1097
1098 #: socks5.c:70
1099 #, c-format
1100 msgid "socks5connect: socks5 refuses our authentication methods: %02x"
1101 msgstr "socks5connect: socks5 systeem wijst onze authenticatie methode af: %02x"
1102
1103 #: socks5.c:81
1104 msgid "socks5connect: socks5 server requests username/password authentication"
1105 msgstr "socks5connect: systeem vraagt gebruikersnaamauthenticatie"
1106
1107 #: socks5.c:90
1108 msgid "socks5connect: failed transmitting username/password to socks5 server"
1109 msgstr "socks5connect: probleem bij verzenden gebrukersnaam/toegangscode naar systeem"
1110
1111 #: socks5.c:96
1112 msgid "socks5connect: failed receiving authentication reply"
1113 msgstr "socks5connect: authenticatie reactie ontvangen mislukt"
1114
1115 #: socks5.c:102
1116 msgid "socks5connect: password authentication failed"
1117 msgstr "socks5connect: authenticatie faalde"
1118
1119 #: socks5.c:116
1120 #, c-format
1121 msgid "Cannot resolve %s"
1122 msgstr "Kan %s niet vertalen"
1123
1124 #: socks5.c:133
1125 msgid "socks5connect: failed to transmit associate request"
1126 msgstr "socks5connect: \"associatie\"-verzoek verzenden mislukt"
1127
1128 #: socks5.c:139
1129 msgid "socks5connect: command reply receive failure"
1130 msgstr "socks5connect: commando-reactie ontvangen mislukt"
1131
1132 #: socks5.c:146
1133 #, c-format
1134 msgid "socks5connect: bind request replies with version other than 0x05 (%02x)"
1135 msgstr "socks5connect: verbindingsreactie geeft ander versienummer (%02x) dan 0x05 terug"
1136
1137 #: socks5.c:152
1138 #, c-format
1139 msgid "socks5connect: failed to connect (%02x)"
1140 msgstr "socks5connect: verbinden mislukt (%02x)"
1141
1142 #: socks5.c:158
1143 #, c-format
1144 msgid "socks5connect: only accepting bind-replies with IPv4 address (%02x)"
1145 msgstr "socks5connect: alleen \"bind\"-reakties voor IPv4 ondersteund (%02x)"
1146
1147 #: tcp.c:31
1148 #: tcp.c:42
1149 #, c-format
1150 msgid "could not set TCP_NODELAY on socket (%s)"
1151 msgstr "kan TCP_NODELAY niet inschakelen op verbinding (%s)"
1152
1153 #: tcp.c:57
1154 #, c-format
1155 msgid "problem creating socket (%s)"
1156 msgstr "probleem bij maken socket (%s)"
1157
1158 #: tcp.c:69
1159 #, c-format
1160 msgid "error setting sockopt to interface (%s)"
1161 msgstr "sockopt zetten op adapter mislukt (%s)"
1162
1163 #: tcp.c:75
1164 #, c-format
1165 msgid "error binding to interface (%s)"
1166 msgstr "probleem bij binden aan adapter (%s)"
1167
1168 #: tcp.c:84
1169 #, c-format
1170 msgid "error setting MTU size (%s)"
1171 msgstr "probleem bij instellen MTU-grootte (%s)"
1172
1173 #: tcp.c:101
1174 #, c-format
1175 msgid "error setting transmit buffer size (%s)"
1176 msgstr "probleem bij instellen verzendbuffergrootte (%s)"
1177
1178 #: tcp.c:110
1179 #, c-format
1180 msgid "error setting receive buffer size (%s)"
1181 msgstr "probleem bij instellen ontvangstbuffergrootte (%s)"
1182
1183 #: tcp.c:119
1184 #, c-format
1185 msgid "error setting priority (%s)"
1186 msgstr "probleem bij instellen prioriteit (%s)"
1187
1188 #: tcp.c:128
1189 msgid "failed to set TOS info"
1190 msgstr "probleem bij instellen TOS-info"
1191
1192 #: tcp.c:165
1193 #, c-format
1194 msgid "TCP TFO Not Supported. Please check if \"/proc/sys/net/ipv4/tcp_fastopen\" is 1. Disabling TFO for now.\n"
1195 msgstr "TCP TFO is niet ondersteund. Controleer of \"/proc/sys/net/ipv4/tcp_fastopen\" de waarde 1 bevat.\n"
1196
1197 #: tcp.c:195
1198 #, c-format
1199 msgid "problem connecting to host: %s"
1200 msgstr "probleem bij verbinden met systeem: %s"
1201
1202 #: tcp.c:208
1203 msgid "connect time out"
1204 msgstr "verbindingstimeout"
1205
1206 #: tcp.c:216
1207 #, c-format
1208 msgid "select() failed: %s"
1209 msgstr "select() mislukt: %s"
1210
1211 #: tcp.c:228
1212 #, c-format
1213 msgid "getsockopt failed (%s)"
1214 msgstr "getsockopt mislukt (%s)"
1215
1216 #: tcp.c:240
1217 #, c-format
1218 msgid "could not connect (%s)"
1219 msgstr "kan niet verbinden (%s)"
1220
1221 #: utils.c:25
1222 msgid "gettimeofday failed"
1223 msgstr "gettimeofday mislukt"
1224
1225 #~ #: main.c:1276 main.c:1271
1226
1227 #~ msgid "Cannot combine maximum MTU size setting with proxy connections or SSL"
1228 #~ msgstr ""
0 Installation:
1 ------------
2 make install
3
4 This will first invoke the 'configure'-script and then build the sources.
5 You can also run 'configure' manually. Then the following switches apply:
6 --with-tfo force enable tcp fast open
7 --with-ncurses force enable ncurses
8 --with-openssl force enable openssl
9 --with-fftw3 force enable fftw3
10
11 Please note that TCP fast open requires a Linux kernel of version 3.7 or more recent.
12
13 'fftw3' support is only useful if you include the ncurses interface.
14
15 Debian package names:
16 ncurses requires libncursesw5-dev
17 fftw3 requires libfftw3-dev
18 openssl requires libssl-dev
19
20
21 Usage:
22 -----
23 httping www.vanheusden.com
24
25
26 See:
27 httping -h
28 for a list of commandline switches. Also check the man-page.
29
30 plot-json.py is a script to convert the json-output of httping to a script for gnuplot.
31
32 If this script fails with the following error:
33 ValueError: Expecting object: [...]
34 then make sure the json-file ends with a ']' (without the quotes).
35 In some cases this character is missing.
36
37
38 Thanks to Thanatos for cookie and authentication support.
39 Many thanks to Olaf van der Spek for lots of bug-reports, testing, ideas and suggestions.
40
41
42 For everything more or less related to 'httping', please feel free
43 to contact me on: folkert@vanheusden.com
44
45 Please support my opensource development: http://www.vanheusden.com/wishlist.php
46 Or send any surplus bitcoins to 1N5Sn4jny4xVwTwSYLnf7WnFQEGoVRmTQF
0 /* Released under GPLv2 with exception for the OpenSSL library. See license.txt */
1 /* $Revision$ */
2
3 #include <sys/types.h>
4 #include <sys/time.h>
5 #include <sys/socket.h>
6 #include <netinet/in.h>
7 #include <libintl.h>
8 #include <netdb.h>
9 #include <errno.h>
10 #include <stdio.h>
11 #include <string.h>
12 #include <unistd.h>
13
14 #include "gen.h"
15 #include "res.h"
16 #include "error.h"
17
18 int resolve_host(const char *host, struct addrinfo **ai, char use_ipv6, int portnr)
19 {
20 int rc = -1;
21 char servname[10];
22 struct addrinfo myaddr;
23
24 memset(&myaddr, 0, sizeof myaddr);
25
26 /* myaddr.ai_flags = AI_PASSIVE; */
27 myaddr.ai_socktype = SOCK_STREAM;
28 myaddr.ai_protocol = IPPROTO_TCP;
29 myaddr.ai_family = use_ipv6 ? AF_INET6 : AF_INET;
30 snprintf(servname, sizeof servname, "%d", portnr);
31
32 rc = getaddrinfo(host, servname, &myaddr, ai);
33
34 if (rc != 0)
35 set_error(gettext("Resolving %s %sfailed: %s"), host, use_ipv6 ? gettext("(IPv6) ") : "", gai_strerror(rc));
36
37 return rc;
38 }
39
40 struct addrinfo * select_resolved_host(struct addrinfo *ai, char use_ipv6)
41 {
42 struct addrinfo *p = ai;
43 while(p)
44 {
45 if (p -> ai_family == AF_INET6 && use_ipv6)
46 return p;
47
48 if (p -> ai_family == AF_INET)
49 return p;
50
51 p = p -> ai_next;
52 }
53
54 return NULL;
55 }
56
57 void get_addr(struct addrinfo *ai_use, struct sockaddr_in6 *addr)
58 {
59 memcpy(addr, ai_use->ai_addr, ai_use->ai_addrlen);
60 }
61
62 #define incopy(a) *((struct in_addr *)a)
63
64 int resolve_host_ipv4(const char *host, struct sockaddr_in *addr)
65 {
66 struct hostent *hostdnsentries = gethostbyname(host);
67
68 if (hostdnsentries == NULL)
69 {
70 set_error(gettext("Problem resolving %s (IPv4): %s"), host, hstrerror(h_errno));
71
72 return -1;
73 }
74
75 /* create address structure */
76 addr -> sin_family = hostdnsentries -> h_addrtype;
77 addr -> sin_addr = incopy(hostdnsentries -> h_addr_list[0]);
78
79 return 0;
80 }
0 /* Released under GPLv2 with exception for the OpenSSL library. See license.txt */
1 /* $Revision$ */
2
3 #define incopy(a) *((struct in_addr *)a)
4
5 int resolve_host(const char *host, struct addrinfo **ai, char use_ipv6, int portnr);
6 struct addrinfo * select_resolved_host(struct addrinfo *ai, char use_ipv6);
7 void get_addr(struct addrinfo *ai_use, struct sockaddr_in6 *addr);
8
9 int resolve_host_ipv4(const char *host, struct sockaddr_in *addr);
0 /* $Revision$ */
1 #include <libintl.h>
2 #include <unistd.h>
3 #include <stdio.h>
4 #include <string.h>
5 #include <sys/types.h>
6 #include <sys/socket.h>
7 #include <netinet/in.h>
8 #include <sys/time.h>
9 #include <time.h>
10 #include <netdb.h>
11 #include <arpa/inet.h>
12
13 #include "error.h"
14 #include "gen.h"
15 #include "io.h"
16 #include "res.h"
17 #include "tcp.h"
18
19 int socks5connect(int fd, struct addrinfo *ai, double timeout, const char *socks5_username, const char *socks5_password, const char *host, int port, char abort_on_resolve_failure)
20 {
21 struct sockaddr_in sai;
22 uint32_t addr = 0;
23 unsigned char io_buffer[256] = { 0 };
24 int io_len = 0, rc = -1;
25
26 if ((rc = connect_to(fd, ai, timeout, NULL, NULL, 0, NULL)) < 0)
27 return rc;
28
29 /* inform socks server about the auth. methods we support */
30 if (socks5_username != NULL)
31 {
32 io_buffer[0] = 0x05; /* version */
33 io_buffer[1] = 2; /* 2 authentication methods */
34 io_buffer[2] = 0x00; /* method 1: no authentication */
35 io_buffer[3] = 0x02; /* method 2: username/password */
36 io_len = 4;
37 }
38 else
39 {
40 io_buffer[0] = 0x05; /* version */
41 io_buffer[1] = 1; /* 2 authentication methods */
42 io_buffer[2] = 0x00; /* method 1: no authentication */
43 io_len = 3;
44 }
45
46 if ((rc = mywrite(fd, (char *)io_buffer, io_len, timeout)) < 0)
47 return rc;
48
49 /* wait for reply telling selected authentication method */
50 if ((rc = myread(fd, (char *)io_buffer, 2, timeout)) < 0)
51 return rc;
52
53 if (io_buffer[0] != 0x05)
54 {
55 set_error(gettext("socks5connect: reply with requested authentication method does not say version 5 (%02x)"), io_buffer[0]);
56 return RC_INVAL;
57 }
58
59 if (io_buffer[1] == 0x00)
60 {
61 /* printf("socks5connect: \"no authentication at all\" selected by server\n"); */
62 }
63 else if (io_buffer[1] == 0x02)
64 {
65 /* printf("socks5connect: selected username/password authentication\n"); */
66 }
67 else
68 {
69 set_error(gettext("socks5connect: socks5 refuses our authentication methods: %02x"), io_buffer[1]);
70 return RC_INVAL;
71 }
72
73 /* in case the socks5 server asks us to authenticate, do so */
74 if (io_buffer[1] == 0x02)
75 {
76 int io_len = 0;
77
78 if (socks5_username == NULL || socks5_password == NULL)
79 {
80 set_error(gettext("socks5connect: socks5 server requests username/password authentication"));
81 return RC_INVAL;
82 }
83
84 io_buffer[0] = 0x01; /* version */
85 io_len = snprintf((char *)&io_buffer[1], sizeof io_buffer - 1, "%c%s%c%s", (int)strlen(socks5_username), socks5_username, (int)strlen(socks5_password), socks5_password);
86
87 if ((rc = mywrite(fd, (char *)io_buffer, io_len + 1, timeout)) < 0)
88 {
89 set_error(gettext("socks5connect: failed transmitting username/password to socks5 server"));
90 return rc;
91 }
92
93 if ((rc = myread(fd, (char *)io_buffer, 2, timeout)) < 0)
94 {
95 set_error(gettext("socks5connect: failed receiving authentication reply"));
96 return rc;
97 }
98
99 if (io_buffer[1] != 0x00)
100 {
101 set_error(gettext("socks5connect: password authentication failed"));
102 return RC_INVAL;
103 }
104 }
105
106 /* ask socks5 server to associate with server */
107 io_buffer[0] = 0x05; /* version */
108 io_buffer[1] = 0x01; /* connect to */
109 io_buffer[2] = 0x00; /* reserved */
110 io_buffer[3] = 0x01; /* ipv4 */
111
112 if (resolve_host_ipv4(host, &sai) == -1)
113 {
114 if (abort_on_resolve_failure)
115 error_exit(gettext("Cannot resolve %s"), host);
116
117 return RC_INVAL;
118 }
119
120 addr = ntohl(sai.sin_addr.s_addr);
121
122 io_buffer[4] = (addr >> 24) & 255;
123 io_buffer[5] = (addr >> 16) & 255;
124 io_buffer[6] = (addr >> 8) & 255;
125 io_buffer[7] = (addr ) & 255;
126
127 io_buffer[8] = (port >> 8) & 255;
128 io_buffer[9] = (port ) & 255;
129
130 if ((rc = mywrite(fd, (char *)io_buffer, 10, timeout)) < 0)
131 {
132 set_error(gettext("socks5connect: failed to transmit associate request"));
133 return rc;
134 }
135
136 if ((rc = myread(fd, (char *)io_buffer, 10, timeout)) < 0)
137 {
138 set_error(gettext("socks5connect: command reply receive failure"));
139 return rc;
140 }
141
142 /* verify reply */
143 if (io_buffer[0] != 0x05)
144 {
145 set_error(gettext("socks5connect: bind request replies with version other than 0x05 (%02x)"), io_buffer[0]);
146 return RC_INVAL;
147 }
148
149 if (io_buffer[1] != 0x00)
150 {
151 set_error(gettext("socks5connect: failed to connect (%02x)"), io_buffer[1]);
152 return RC_INVAL;
153 }
154
155 if (io_buffer[3] != 0x01)
156 {
157 set_error(gettext("socks5connect: only accepting bind-replies with IPv4 address (%02x)"), io_buffer[3]);
158 return RC_INVAL;
159 }
160
161 return RC_OK;
162 }
0 /* $Revision$ */
1 int socks5connect(int fd, struct addrinfo *ai, double timeout, const char *socks5_username, const char *socks5_password, const char *host, int port, char abort_on_resolve_failure);
+252
-0
tcp.c less more
0 /* Released under GPLv2 with exception for the OpenSSL library. See license.txt */
1 /* $Revision$ */
2
3 #include <sys/types.h>
4 #include <sys/time.h>
5 #include <sys/socket.h>
6 #include <netinet/in.h>
7 #include <netinet/tcp.h>
8 #include <arpa/inet.h>
9 #include <libintl.h>
10 #include <netdb.h>
11 #include <errno.h>
12 #include <stdio.h>
13 #include <string.h>
14 #include <unistd.h>
15
16 #include "error.h"
17 #include "gen.h"
18 #include "io.h"
19 #include "main.h"
20 #include "tcp.h"
21
22 void failure_close(int fd)
23 {
24 struct linger sl;
25
26 sl.l_onoff = 1;
27 sl.l_linger = 0;
28
29 if (setsockopt(fd, SOL_SOCKET, SO_LINGER, &sl, sizeof sl) == -1)
30 set_error(gettext("could not set TCP_NODELAY on socket (%s)"), strerror(errno));
31
32 close(fd);
33 }
34
35 int set_no_delay(int fd)
36 {
37 int flag = 1;
38
39 if (setsockopt(fd, IPPROTO_TCP, TCP_NODELAY, (char *)&flag, sizeof(int)) < 0)
40 {
41 set_error(gettext("could not set TCP_NODELAY on socket (%s)"), strerror(errno));
42 return -1;
43 }
44
45 return 0;
46 }
47
48 int create_socket(struct sockaddr *bind_to, struct addrinfo *ai, int recv_buffer_size, int tx_buffer_size, int max_mtu, char use_no_delay, int priority, int tos)
49 {
50 int fd = -1;
51
52 /* create socket */
53 fd = socket(ai->ai_family, ai->ai_socktype, ai->ai_protocol);
54 if (fd == -1)
55 {
56 set_error(gettext("problem creating socket (%s)"), strerror(errno));
57 return RC_INVAL;
58 }
59
60 /* go through a specific interface? */
61 if (bind_to)
62 {
63 int set = 1;
64
65 /* set reuse flags */
66 if (setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, &set, sizeof set) == -1)
67 {
68 set_error(gettext("error setting sockopt to interface (%s)"), strerror(errno));
69 close(fd);
70 return RC_INVAL;
71 }
72
73 if (bind(fd, bind_to, sizeof *bind_to) == -1)
74 {
75 set_error(gettext("error binding to interface (%s)"), strerror(errno));
76 close(fd);
77 return RC_INVAL;
78 }
79 }
80
81 if (max_mtu >= 0)
82 {
83 if (setsockopt(fd, IPPROTO_TCP, TCP_MAXSEG, &max_mtu, sizeof max_mtu) == -1)
84 {
85 set_error(gettext("error setting MTU size (%s)"), strerror(errno));
86 close(fd);
87 return RC_INVAL;
88 }
89 }
90
91 if (use_no_delay)
92 {
93 int rc = -1;
94
95 if ((rc = set_no_delay(fd)) != 0)
96 return rc;
97 }
98
99 if (tx_buffer_size > 0)
100 {
101 if (setsockopt(fd, SOL_SOCKET, SO_SNDBUF, (char *)&tx_buffer_size, sizeof tx_buffer_size) == -1)
102 {
103 set_error(gettext("error setting transmit buffer size (%s)"), strerror(errno));
104 close(fd);
105 return RC_INVAL;
106 }
107 }
108
109 if (recv_buffer_size > 0)
110 {
111 if (setsockopt(fd, SOL_SOCKET, SO_RCVBUF, (char *)&recv_buffer_size, sizeof recv_buffer_size) == -1)
112 {
113 set_error(gettext("error setting receive buffer size (%s)"), strerror(errno));
114 close(fd);
115 return RC_INVAL;
116 }
117 }
118
119 #ifdef linux
120 if (priority >= 0)
121 {
122 if (setsockopt(fd, SOL_SOCKET, SO_PRIORITY, (char *)&priority, sizeof priority) == -1)
123 {
124 set_error(gettext("error setting priority (%s)"), strerror(errno));
125 close(fd);
126 return RC_INVAL;
127 }
128 }
129 #endif
130
131 if (tos >= 0)
132 {
133 if (setsockopt(fd, IPPROTO_IP, IP_TOS, (char *)&tos, sizeof tos) == -1)
134 {
135 set_error(gettext("failed to set TOS info"));
136 close(fd);
137 return RC_INVAL;
138 }
139 }
140
141 return fd;
142 }
143
144 int connect_to(int fd, struct addrinfo *ai, double timeout, char *tfo, char *msg, int msg_len, char *msg_accepted)
145 {
146 int rc = -1;
147 struct timeval to;
148 fd_set wfds;
149
150 /* make fd nonblocking */
151 if (set_fd_nonblocking(fd) == -1)
152 return RC_INVAL;
153
154 /* wait for connection */
155 FD_ZERO(&wfds);
156 FD_SET(fd, &wfds);
157
158 to.tv_sec = (long)(timeout / 1000.0);
159 to.tv_usec = (long)(timeout * 1000.0) % 1000000;
160
161 /* connect to peer */
162 #ifdef TCP_TFO
163 if (tfo && *tfo)
164 {
165 rc = sendto(fd, msg, msg_len, MSG_FASTOPEN, ai -> ai_addr, ai -> ai_addrlen);
166
167 if(rc == msg_len)
168 *msg_accepted = 1;
169 if(errno == 0)
170 return RC_OK;
171 if(errno == ENOTSUP)
172 {
173 printf(gettext("TCP TFO Not Supported. Please check if \"/proc/sys/net/ipv4/tcp_fastopen\" is 1. Disabling TFO for now.\n"));
174 *tfo = 0;
175 goto old_connect;
176 }
177 }
178
179 else
180 #else
181 (void)tfo;
182 (void)msg;
183 (void)msg_len;
184 (void)msg_accepted;
185 #endif
186 {
187 int rc = -1;
188
189 old_connect:
190 rc = connect(fd, ai -> ai_addr, ai -> ai_addrlen);
191
192 if (rc == 0)
193 {
194 /* connection made, return */
195 return RC_OK;
196 }
197
198 if (rc == -1)
199 {
200 /* problem connecting */
201 if (errno != EINPROGRESS)
202 {
203 set_error(gettext("problem connecting to host: %s"), strerror(errno));
204 return RC_INVAL;
205 }
206 }
207 }
208
209 if (stop)
210 return RC_CTRLC;
211
212 /* wait for connection */
213 rc = select(fd + 1, NULL, &wfds, NULL, &to);
214 if (rc == 0)
215 {
216 set_error(gettext("connect time out"));
217 return RC_TIMEOUT; /* timeout */
218 }
219 else if (rc == -1)
220 {
221 if (errno == EINTR)
222 return RC_CTRLC;/* ^C pressed */
223
224 set_error(gettext("select() failed: %s"), strerror(errno));
225
226 return RC_INVAL; /* error */
227 }
228 else
229 {
230 int optval=0;
231 socklen_t optvallen = sizeof optval;
232
233 /* see if the connect succeeded or failed */
234 if (getsockopt(fd, SOL_SOCKET, SO_ERROR, &optval, &optvallen) == -1)
235 {
236 set_error(gettext("getsockopt failed (%s)"), strerror(errno));
237 return RC_INVAL;
238 }
239
240 /* no error? */
241 if (optval == 0)
242 return RC_OK;
243
244 /* don't ask */
245 errno = optval;
246 }
247
248 set_error(gettext("could not connect (%s)"), strerror(errno));
249
250 return RC_INVAL;
251 }
0 /* Released under GPLv2 with exception for the OpenSSL library. See license.txt */
1 /* $Revision$ */
2
3 int create_socket(struct sockaddr *bind_to, struct addrinfo *ai, int recv_buffer_size, int tx_buffer_size, int max_mtu, char use_no_delay, int priority, int tos);
4 int connect_to(int fd, struct addrinfo *ai, double timeout, char *tfo, char *msg, int msg_len, char *msg_accepted);
5 void failure_close(int fd);
0 /* $Revision$ */
1 #include <stdio.h>
2 #include <sys/types.h>
3 #include <sys/socket.h>
4
5 int main(int argc, char *argv[])
6 {
7 int qlen = 5;
8
9 setsockopt(sfd, SOL_TCP, TCP_FASTOPEN, &qlen, sizeof(qlen));
10
11 return 0;
12 }
0 /* $Revision$ */
1 #include <fftw3.h>
2
3 int main(int argc, char *argv[])
4 {
5 /* note: it only needs to compile */
6 void *dummy = fftw_malloc(4096);
7 double *dummyd = (double *)dummy;
8
9 void *plan = fftw_plan_dft_r2c_1d(12345, dummyd, NULL, FFTW_ESTIMATE);
10
11 return 0;
12 }
0 /* $Revision$ */
1 #include <ncurses.h>
2
3 int main(int argc, char *argv[])
4 {
5 initscr();
6
7 return 0;
8 }
0 /* $Revision$ */
1 #include <ncurses/ncurses.h>
2
3 int main(int argc, char *argv[])
4 {
5 initscr();
6
7 return 0;
8 }
0 /* Released under GPLv2 with exception for the OpenSSL library. See license.txt */
1 /* $Revision$ */
2
3 #include <stdio.h>
4 #include <openssl/bio.h>
5 #include <openssl/conf.h>
6 #include <openssl/engine.h>
7 #include <openssl/err.h>
8 #include <openssl/evp.h>
9 #include <openssl/md5.h>
10 #include <openssl/ssl.h>
11 #include <openssl/x509.h>
12
13 int main(int argc, char *argv[])
14 {
15 BIO *bio_err = NULL;
16
17 SSL_library_init();
18 SSL_load_error_strings();
19 ERR_load_crypto_strings();
20
21 /* error write context */
22 bio_err = BIO_new_fp(stderr, BIO_NOCLOSE);
23
24 const SSL_METHOD *meth = SSLv23_method();
25
26 SSL_CTX *ctx = SSL_CTX_new(meth);
27
28 /***/
29
30 BIO_free(bio_err);
31
32 ERR_free_strings();
33
34 ERR_remove_state(0);
35 ENGINE_cleanup();
36 CONF_modules_free();
37 EVP_cleanup();
38 CRYPTO_cleanup_all_ex_data();
39
40 return 0;
41 }
0 /* Released under GPLv2 with exception for the OpenSSL library. See license.txt */
1 /* $Revision$ */
2
3 #define _GNU_SOURCE
4 #include <errno.h>
5 #include <math.h>
6 #include <stdarg.h>
7 #include <stdio.h>
8 #include <stdlib.h>
9 #include <string.h>
10 #include <unistd.h>
11 #include <sys/time.h>
12 #include <time.h>
13 #include <libintl.h>
14
15 #include "error.h"
16 #include "utils.h"
17
18 double get_ts(void)
19 {
20 struct timeval ts;
21 struct timezone tz;
22
23 if (gettimeofday(&ts, &tz) == -1)
24 error_exit(gettext("gettimeofday failed"));
25
26 return (double)ts.tv_sec + ((double)ts.tv_usec)/1000000.0 + (double)(tz.tz_minuteswest * 60);
27 }
28
29 void split_string(const char *in, const char *split, char ***list, int *list_n)
30 {
31 char *copy = strdup(in), *pc = copy;
32 int split_len = strlen(split);
33
34 for(;;)
35 {
36 char *term = strstr(pc, split);
37
38 if (term)
39 *term = 0x00;
40
41 *list = (char **)realloc(*list, (*list_n + 1) * sizeof(char *));
42 (*list)[*list_n] = strdup(pc);
43 (*list_n)++;
44
45 if (!term)
46 break;
47
48 pc = term + split_len;
49 }
50
51 free(copy);
52 }
53
54 void free_splitted_string(char **list, int n)
55 {
56 int index=0;
57
58 for(index=0; index<n; index++)
59 free(list[index]);
60
61 free(list);
62 }
63
64 void str_add(char **to, const char *what, ...)
65 {
66 int len_to = *to ? strlen(*to) : 0;
67 char *buffer = NULL;
68 int len_what = 0;
69
70 va_list ap;
71
72 /* FIXME: should aprintf here: does solaris have aprintf? */
73 va_start(ap, what);
74 len_what = vasprintf(&buffer, what, ap);
75 va_end(ap);
76
77 *to = (char *)realloc(*to, len_to + len_what + 1);
78
79 memcpy(&(*to)[len_to], buffer, len_what);
80
81 (*to)[len_to + len_what] = 0x00;
82
83 free(buffer);
84 }
85
86 char * format_value(double value, int digits_sig, int digits_nsig, char abbreviate)
87 {
88 char *out = NULL, *mul = "";
89 double a = fabs(value);
90 double div = 1.0;
91
92 if (!abbreviate)
93 {
94 }
95 else if (a >= GIGA)
96 {
97 div = GIGA;
98 mul = "G";
99 }
100 else if (a >= MEGA)
101 {
102 div = MEGA;
103 mul = "M";
104 }
105 else if (a >= KILO)
106 {
107 div = KILO;
108 mul = "k";
109 }
110
111 if (mul[0])
112 digits_sig--;
113
114 (void)asprintf(&out, "%*.*f%s", digits_sig, digits_nsig, value / div, mul);
115
116 return out;
117 }
0 /* Released under GPLv2 with exception for the OpenSSL library. See license.txt */
1 /* $Revision$ */
2
3 double get_ts(void);
4
5 void split_string(const char *in, const char *split, char ***list, int *list_n);
6 void free_splitted_string(char **list, int n);
7
8 void str_add(char **to, const char *what, ...);
9
10 #define GIGA 1000000000.0
11 #define MEGA 1000000.0
12 #define KILO 1000.0
13
14 char * format_value(double value, int digits_sig, int digits_nsig, char abbreviate);
15
16 #define min(x, y) ((x) < (y) ? (x) : (y))
17 #define max(x, y) ((x) > (y) ? (x) : (y))
0 VERSION=2.4