2 * Copyright 2000, International Business Machines Corporation and others.
5 * This software has been released under the terms of the IBM Public
6 * License. For details, see the LICENSE file in the top-level source
7 * directory or online at http://www.openafs.org/dl/license10.html
10 /* Sample program using multi_Rx, to execute calls in parallel to multiple hosts */
12 #include <afsconfig.h>
13 #include <afs/param.h>
16 #include <sys/types.h>
18 #include <netinet/in.h>
21 #include "rx/rx_clock.h"
23 /* Bogus procedure to get internet address of host */
25 GetIpAddress(hostname
)
28 struct hostent
*hostent
;
30 hostent
= gethostbyname(hostname
);
32 printf("host %s not found", hostname
);
35 if (hostent
->h_length
!= sizeof(u_long
)) {
36 printf("host address is disagreeable length (%d)", hostent
->h_length
);
39 memcpy((char *)&host
, hostent
->h_addr
, sizeof(host
));
46 struct rx_securityClass
*null_securityObject
;
53 struct rx_connection
*conns
[50];
59 struct clock startTime
, endTime
;
63 while (**argv
== '-') {
64 if (strcmp(*argv
, "-verbose") == 0)
66 else if (strcmp(*argv
, "-count") == 0)
67 trials
= atoi(*++argv
), argc
--;
68 else if (strcmp(*argv
, "-abort") == 0)
71 fprintf("Unknown option %s\n", *argv
);
78 host
[nHosts
].name
= *argv
;
79 host
[nHosts
].ipaddr
= GetIpAddress(*argv
);
80 arg
[nHosts
] = 10000 * (nHosts
+ 1); /* a bogus argument to show how an input argument to the multi call can be indexed by multi_i */
86 null_securityObject
= rxnull_NewClientSecurityObject();
87 for (i
= 0; i
< nHosts
; i
++) {
89 rx_NewConnection(host
[i
].ipaddr
, SAMPLE_SERVER_PORT
,
90 SAMPLE_SERVICE_ID
, null_securityObject
,
95 clock_GetTime(&startTime
);
96 for (i
= 0; i
< trials
; i
++) {
97 multi_Rx(conns
, nHosts
) {
98 /* Note that multi_i is available both for arguments (result could also be indexed by multi_i, if you want to keep the results apart, and after the call completes) and in the code which follows the completion of each multi_TEST_Add. At completion, multi_i will be set to the connection index of the call which completed, and multi_error will be set to the error code returned by that call. */
100 printf("%s: About to add %d to %d\n", host
[multi_i
].name
,
101 arg
[multi_i
], i
* 10, &result
);
102 multi_TEST_Add(verbose
, arg
[multi_i
], i
* 10, &result
);
104 printf("%s: error %d, %d + %d is %d\n", host
[multi_i
].name
,
105 multi_error
, arg
[multi_i
], i
* 10, result
);
106 if (abort
&& multi_error
)
108 if (multi_error
== 0)
111 printf("%s: error %d\n", host
[multi_i
].name
, multi_error
);
116 clock_GetTime(&endTime
);
117 msec
= clock_ElapsedTime(&startTime
, &endTime
);
119 ("nSuccesses=%d in %d msec; %d msec per iteration for %d iterations over %d hosts\n",
120 nSuccesses
, msec
, msec
/ trials
, trials
, nHosts
);
122 /* Allow Rx to idle down any calls; it's a good idea, but not essential, to call this routine */