2 * $Id: zoom-benchmark.c,v 1.15 2006-10-04 16:59:35 mike Exp $
4 * Asynchronous multi-target client doing search and piggyback retrieval
13 #include <yaz/xmalloc.h>
14 #include <yaz/options.h>
19 static char* zoom_events[10];
21 /* re-sorting event numbers to progress numbers */
22 static int zoom_progress[10];
24 /* commando line parameters */
25 static struct parameters_t {
50 void print_event_line(struct event_line_t *pel)
52 printf ("%d\t%ld.%06ld\t%d\t%d\t%s\t%d\t%s\n",
53 pel->connection, pel->time_sec, pel->time_usec,
55 pel->event, pel->zoom_event,
56 pel->error, pel->errmsg);
59 void update_events(int *elc, struct event_line_t *els,
66 const char * eventmsg,
70 int ielc = repeat*parameters.concurrent + conn;
71 int iels = repeat*parameters.concurrent*10 + conn*10 + elc[ielc];
73 els[iels].connection = conn;
74 els[iels].time_sec = sec;
75 els[iels].time_usec = usec;
76 els[iels].progress = prog;
77 els[iels].event = event;
80 strcpy(els[iels].zoom_event, eventmsg);
82 strcpy(els[iels].zoom_event, "---");
84 els[iels].error = error;
85 strcpy(els[iels].errmsg, errmsg);
86 /* print_event_line(&els[iels]); */
90 void print_events(int *elc, struct event_line_t *els,
98 for (k=0; k < parameters.repeat; k++){
99 for (i=0; i < connections; i++){
100 ielc = k * parameters.concurrent + i;
101 for (j=0; j < elc[ielc]; j++){
102 iels = k * parameters.concurrent * 10 + i * 10 + j;
103 print_event_line(&els[iels]);
113 void init_statics(void)
116 char nullstring[1] = "";
119 zoom_events[ZOOM_EVENT_NONE] = "ZOOM_EVENT_NONE";
120 zoom_events[ZOOM_EVENT_CONNECT] = "ZOOM_EVENT_CONNECT";
121 zoom_events[ZOOM_EVENT_SEND_DATA] = "ZOOM_EVENT_SEND_DATA";
122 zoom_events[ZOOM_EVENT_RECV_DATA] = "ZOOM_EVENT_RECV_DATA";
123 zoom_events[ZOOM_EVENT_TIMEOUT] = "ZOOM_EVENT_TIMEOUT";
124 zoom_events[ZOOM_EVENT_UNKNOWN] = "ZOOM_EVENT_UNKNOWN";
125 zoom_events[ZOOM_EVENT_SEND_APDU] = "ZOOM_EVENT_SEND_APDU";
126 zoom_events[ZOOM_EVENT_RECV_APDU] = "ZOOM_EVENT_RECV_APDU";
127 zoom_events[ZOOM_EVENT_RECV_RECORD] = "ZOOM_EVENT_RECV_RECORD";
128 zoom_events[ZOOM_EVENT_RECV_SEARCH] = "ZOOM_EVENT_RECV_SEARCH";
129 zoom_events[ZOOM_EVENT_END] = "ZOOM_EVENT_END";
131 /* re-sorting event numbers to progress numbers */
132 zoom_progress[ZOOM_EVENT_NONE] = 0;
133 zoom_progress[ZOOM_EVENT_CONNECT] = 1;
134 zoom_progress[ZOOM_EVENT_SEND_DATA] = 3;
135 zoom_progress[ZOOM_EVENT_RECV_DATA] = 4;
136 zoom_progress[ZOOM_EVENT_TIMEOUT] = 9;
137 zoom_progress[ZOOM_EVENT_UNKNOWN] = 10;
138 zoom_progress[ZOOM_EVENT_SEND_APDU] = 2;
139 zoom_progress[ZOOM_EVENT_RECV_APDU] = 5;
140 zoom_progress[ZOOM_EVENT_RECV_RECORD] = 7;
141 zoom_progress[ZOOM_EVENT_RECV_SEARCH] = 6;
142 zoom_progress[ZOOM_EVENT_END] = 8;
145 parameters.concurrent = 1;
146 parameters.timeout = 0;
147 parameters.repeat = 1;
148 strcpy(parameters.proxy, nullstring);
149 parameters.gnuplot = 0;
150 parameters.piggypack = 0;
152 /* progress initializing */
153 for (i = 0; i < 4096; i++){
154 parameters.progress[i] = 0;
167 void time_init(struct time_type *ptime)
169 gettimeofday(&(ptime->now), 0);
170 gettimeofday(&(ptime->then), 0);
175 void time_stamp(struct time_type *ptime)
177 gettimeofday(&(ptime->now), 0);
178 ptime->sec = ptime->now.tv_sec - ptime->then.tv_sec;
179 ptime->usec = ptime->now.tv_usec - ptime->then.tv_usec;
180 if (ptime->usec < 0){
182 ptime->usec += 1000000;
186 long time_sec(struct time_type *ptime)
191 long time_usec(struct time_type *ptime)
196 void print_option_error(void)
198 fprintf(stderr, "zoom-benchmark: Call error\n");
199 fprintf(stderr, "zoom-benchmark -h host:port -q pqf-query "
200 "[-c no_concurrent (max 4096)] "
203 "[-g (gnuplot outfile)] "
205 /* "[-t timeout] \n"); */
210 void read_params(int argc, char **argv, struct parameters_t *p_parameters){
213 while ((ret = options("h:q:c:t:p:bgn:", argv, argc, &arg)) != -2)
218 strcpy(p_parameters->host, arg);
221 strcpy(p_parameters->query, arg);
224 strcpy(p_parameters->proxy, arg);
227 p_parameters->concurrent = atoi(arg);
231 p_parameters->timeout = atoi(arg);
235 p_parameters->piggypack = 1;
238 p_parameters->gnuplot = 1;
241 p_parameters->repeat = atoi(arg);
244 print_option_error();
247 print_option_error();
252 printf("zoom-benchmark\n");
253 printf(" host: %s \n", p_parameters->host);
254 printf(" query: %s \n", p_parameters->query);
255 printf(" concurrent: %d \n", p_parameters->concurrent);
256 printf(" repeat: %d \n", p_parameters->repeat);
258 printf(" timeout: %d \n", p_parameters->timeout);
260 printf(" proxy: %s \n", p_parameters->proxy);
261 printf(" piggypack: %d \n\n", p_parameters->piggypack);
262 printf(" gnuplot: %d \n\n", p_parameters->gnuplot);
265 if (! strlen(p_parameters->host))
266 print_option_error();
267 if (! strlen(p_parameters->query))
268 print_option_error();
269 if (! (p_parameters->concurrent > 0))
270 print_option_error();
271 if (! (p_parameters->repeat > 0))
272 print_option_error();
273 if (! (p_parameters->timeout >= 0))
274 print_option_error();
275 if (! ( p_parameters->concurrent <= 4096))
276 print_option_error();
279 void print_table_header(void)
281 if (parameters.gnuplot)
283 printf ("target\tsecond.usec\tprogress\tevent\teventname\t");
284 printf("error\terrorname\n");
288 int main(int argc, char **argv)
290 struct time_type time;
294 struct event_line_t *els;
301 read_params(argc, argv, ¶meters);
303 z = xmalloc(sizeof(*z) * parameters.concurrent);
304 r = xmalloc(sizeof(*r) * parameters.concurrent);
305 elc = xmalloc(sizeof(*elc) * parameters.concurrent * parameters.repeat);
306 els = xmalloc(sizeof(*els)
307 * parameters.concurrent * parameters.repeat * 10);
308 o = ZOOM_options_create();
311 ZOOM_options_set (o, "async", "1");
313 /* get first record of result set (using piggypack) */
314 if (parameters.piggypack)
315 ZOOM_options_set (o, "count", "1");
318 if (strlen(parameters.proxy))
319 ZOOM_options_set (o, "proxy", parameters.proxy);
322 /* preferred record syntax */
324 ZOOM_options_set (o, "preferredRecordSyntax", "usmarc");
325 ZOOM_options_set (o, "elementSetName", "F");
330 for (k = 0; k < parameters.repeat; k++){
332 /* progress zeroing */
333 for (i = 0; i < 4096; i++){
334 parameters.progress[i] = k * 5 -1;
337 /* connect to all concurrent connections*/
338 for ( i = 0; i < parameters.concurrent; i++){
339 /* set event count to zero */
340 elc[k * parameters.concurrent + i] = 0;
342 /* create connection - pass options (they are the same for all) */
343 z[i] = ZOOM_connection_create(o);
345 /* connect and init */
346 ZOOM_connection_connect(z[i], parameters.host, 0);
349 for (i = 0; i < parameters.concurrent; i++)
350 r[i] = ZOOM_connection_search_pqf (z[i], parameters.query);
352 /* network I/O. pass number of connections and array of connections */
353 while ((i = ZOOM_event (parameters.concurrent, z))){
354 int event = ZOOM_connection_last_event(z[i-1]);
358 int progress = zoom_progress[event];
360 if (event == ZOOM_EVENT_SEND_DATA || event == ZOOM_EVENT_RECV_DATA)
365 /* updating events and event list */
366 error = ZOOM_connection_error(z[i-1] , &errmsg, &addinfo);
368 parameters.progress[i] = -progress;
370 parameters.progress[i] += 1;
372 update_events(elc, els,
374 time_sec(&time), time_usec(&time),
375 parameters.progress[i],
376 event, zoom_events[event],
380 /* destroy connections */
381 for (i = 0; i<parameters.concurrent; i++)
383 ZOOM_resultset_destroy (r[i]);
384 ZOOM_connection_destroy (z[i]);
389 } /* for (k = 0; k < parameters.repeat; k++) repeat loop */
393 if (parameters.gnuplot){
394 printf("# gnuplot data and instruction file \n");
395 printf("# gnuplot thisfile \n");
397 printf("set title \"Z39.50 connection plot\"\n");
398 printf("set xlabel \"Connection\"\n");
399 printf("set ylabel \"Time Seconds\"\n");
400 printf("set zlabel \"Progress\"\n");
401 printf("set ticslevel 0\n");
402 printf("set grid\n");
403 printf("set pm3d\n");
404 printf("splot '-' using ($1):($2):($3) t '' with points\n");
409 print_table_header();
410 print_events(elc, els, parameters.concurrent);
412 if (parameters.gnuplot){
414 printf("pause -1 \"Hit ENTER to return\"\n");
417 /* destroy data structures and exit */
422 ZOOM_options_destroy(o);
428 * indent-tabs-mode: nil
430 * vim: shiftwidth=4 tabstop=8 expandtab