1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
|
/*
* Butchered from the dnbd3-fuse by C.K.
**/
#include "connection.h"
#include "helper.h"
#include "../shared/protocol.h"
#include "../shared/log.h"
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <inttypes.h>
#include <getopt.h>
#include <pthread.h>
#define debugf(...) do { logadd( LOG_DEBUG1, __VA_ARGS__ ); } while (0)
static void printUsage(char *argv0, int exitCode)
{
printf( "Usage: %s [--debug] --host <serverAddress(es)> --image <imageName> [--rid revision]\n", argv0 );
printf( "Or: %s [-d] -h <serverAddress(es)> -i <imageName> [-r revision]\n", argv0 );
printf( " -h --host List of space separated hosts to use\n" );
printf( " -i --image Remote image name to request\n" );
printf( " -r --rid Revision to use (omit or pass 0 for latest)\n" );
printf( " -n --runs Number of connection attempts per thread\n" );
printf( " -t --threads number of threads\n" );
printf( " -b --blocksize Size of blocks to request (def. 4096)\n" );
exit( exitCode );
}
static const char *optString = "b:h:i:n:t:Hv";
static const struct option longOpts[] = {
{ "host", required_argument, NULL, 'h' },
{ "image", required_argument, NULL, 'i' },
{ "nruns", optional_argument, NULL, 'n' },
{ "threads", required_argument, NULL, 't' },
{ "blocksize", required_argument, NULL, 'b' },
{ "help", no_argument, NULL, 'H' },
{ "version", no_argument, NULL, 'v' },
{ 0, 0, 0, 0 }
};
static void printBenchCounters(BenchCounters* c) {
printf ("Attempts:\t%d\n", c->attempts);
printf ("Success :\t%d\n", c->success);
printf ("Fails :\t%d\n", c->fails);
}
void* runBenchThread(void* t) {
BenchThreadData* data = t;
connection_init_n_times(
data->server_address,
data->image_name,
0,
data->runs,
data->bs,
data->counter);
printf("Thread #%d finished\n", data->threadNumber);
return NULL;
}
int main(int argc, char *argv[])
{
char *server_address = NULL;
char *image_Name = NULL;
int opt, lidx;
bool closeSockets = false;
int n_runs = 100;
int n_threads = 1;
int bs = 4096;
if ( argc <= 1 || strcmp( argv[1], "--help" ) == 0 || strcmp( argv[1], "--usage" ) == 0 ) {
printUsage( argv[0], 0 );
}
while ( ( opt = getopt_long( argc, argv, optString, longOpts, &lidx ) ) != -1 ) {
switch ( opt ) {
case 'h':
server_address = strdup(optarg);
break;
case 'i':
image_Name = strdup(optarg);
break;
case 'n':
n_runs = atoi(optarg);
break;
case 't':
n_threads = atoi(optarg);
break;
case 'b':
bs = atoi(optarg);
break;
case 'c':
closeSockets = true;
break;
case 'H':
printUsage( argv[0], 0 );
break;
default:
printUsage( argv[0], EXIT_FAILURE );
}
}
printf("Welcome to dnbd3 benchmark tool\n");
/* all counters */
BenchCounters counters[n_threads];
BenchThreadData threadData[n_threads];
pthread_t threads[n_threads];
/* create all threads */
for (int i = 0; i < n_threads; i++) {
BenchCounters tmp1 = {0,0,0};
counters[i] = tmp1;
BenchThreadData tmp2 = {
&(counters[i]),
server_address,
image_Name,
n_runs,
bs,
i,
closeSockets};
threadData[i] = tmp2;
pthread_create(&(threads[i]), NULL, runBenchThread, &(threadData[i]));
}
/* join all threads*/
for (int i = 0; i < n_threads; ++i) {
pthread_join(threads[i], NULL);
}
/* print out all counters & sum up */
BenchCounters total = {0,0,0};
for (int i = 0; i < n_threads; ++i) {
printf("#### Thread %d\n", i);
printBenchCounters(&counters[i]);
total.attempts += counters[i].attempts;
total.success += counters[i].success;
total.fails += counters[i].fails;
}
/* print out summary */
printf("\n\n#### SUMMARY\n");
printBenchCounters(&total);
printf("\n-- End of program");
}
|