Merge pull request #2216 from jwillemsen/jwi-cxxversionchecks
[ACE_TAO.git] / ACE / examples / IPC_SAP / ATM_SAP / CPP-client.cpp
blob4623ff1ae84fefaf4cf250aff18ef631312032f4
1 #include "ace/OS_main.h"
2 #include "ace/ATM_Connector.h"
3 #include "ace/ATM_Addr.h"
4 #include "ace/High_Res_Timer.h"
5 #include "ace/Log_Msg.h"
8 #if defined (ACE_HAS_ATM)
10 #define MAX_LEAVES 32
12 /* ACE_ATM Client */
14 int ACE_TMAIN (int argc, ACE_TCHAR *argv[])
16 if ( argc < 2 )
17 ACE_ERROR_RETURN ((LM_ERROR,
18 "Usage: %s <rate> <PDU> <session> <host> <selector> [ host sel ] ...\n"
19 "\tUse 0 for default values\n",
20 argv[0]),
21 1);
23 int rate = ACE_OS::atoi( argv[ 1 ]);
24 rate = ( rate != 0 ) ? rate : 170000;
25 int pdu_size = ACE_OS::atoi( argv[ 2 ]) * 1024;
26 pdu_size = ( pdu_size != 0 ) ? pdu_size : 8192;
27 int session = ACE_OS::atoi( argv[ 3 ]);
28 session = ( session != 0 ) ? session : 100;
30 ACE_OS::printf( "ATM_Client: rate: %d c/s, PDU: %dB, session: %d pkts\n",
31 rate, pdu_size, session );
33 // Record all hosts/selectors
34 ACE_ATM_Addr hosts[ MAX_LEAVES ];
35 int num_leaves = argc / 2 - 2;
37 ACE_OS::printf( "ATM_Client: Connecting to ...\n" );
38 for ( int i = 0; i < num_leaves; i++ )
40 hosts[ i ].set( argv[ i*2 + 4 ],
41 ( argv[ i*2 + 5 ] != 0 )
42 ? ACE_OS::atoi( argv[ i*2 + 5 ]) : ACE_ATM_Addr::DEFAULT_SELECTOR );
43 ACE_OS::printf( "ATM_Client: leaf: %s (%s), sel: %d\n",
44 argv[ i*2 + 4 ],
45 hosts[ i ].addr_to_string(),
46 hosts[ i ].get_selector());
49 // The timeout really gets ignored since FORE's drivers don't work when
50 // ioctl or fcntl calls are made on the transport id/file descriptor
51 int timeout = ACE_DEFAULT_TIMEOUT;
52 char buf[BUFSIZ];
53 ACE_ATM_Stream atm_stream;
55 char hostname[ MAXNAMELEN ];
56 ACE_OS::hostname( hostname, MAXNAMELEN );
57 ACE_ATM_Addr local_addr( hostname, hosts[ 0 ].get_selector());
59 ACE_OS::printf( "ATM_Client: local host: %s(%s)\n",
60 hostname, local_addr.addr_to_string());
62 // In order to construct connections options the file handle is
63 // needed. Therefore, we need to open the ATM_Stream before we
64 // construct the options.
65 ACE_OS::printf( "ATM_Client: to open a stream\n" );
66 if (atm_stream.open () == -1)
67 ACE_ERROR_RETURN ((LM_ERROR,
68 "%p\n",
69 "open failed"),
70 1);
72 ACE_DEBUG ((LM_DEBUG,
73 "ATM_Client: starting non-blocking connection\n"));
75 // Initiate timed, non-blocking connection with server.
76 ACE_ATM_Connector con;
78 // Construct QoS options - currently FORE only supports bandwidth
79 ACE_OS::printf( "ATM_Client: specify cell rate at %d c/s\n", rate );
80 ACE_ATM_QoS qos;
81 qos.set_rate(atm_stream.get_handle (),
82 rate,
83 ACE_ATM_QoS::OPT_FLAGS_CPID);
85 if ( num_leaves == 1 )
87 // Point-to-point connection
88 // Not sure why but reuse_addr set to true/1 causes problems for
89 // FORE/XTI/ATM - this is now handled in ACE_ATM_Connector::connect()
90 ACE_OS::printf( "ATM_Client: to open a connection\n" );
91 ACE_ATM_Params params = ACE_ATM_Params();
92 if (con.connect (atm_stream,
93 hosts[ 0 ],
94 params,
95 qos,
96 (ACE_Time_Value *) &ACE_Time_Value::zero,
97 local_addr,
99 0 ) == -1)
101 if (errno != EWOULDBLOCK)
102 ACE_ERROR_RETURN ((LM_ERROR,
103 "%p\n",
104 "ATM_Client: connection failed"),
107 ACE_DEBUG ((LM_DEBUG,
108 "ATM_Client: starting timed connection\n"));
110 // Check if non-blocking connection is in progress, and wait up
111 // to timeout seconds for it to complete.
112 ACE_Time_Value tv (timeout);
114 ACE_OS::printf( "ATM_Client: connection completed\n" );
115 if (con.complete (atm_stream,
116 &hosts[ 0 ],
117 &tv) == -1)
118 ACE_ERROR_RETURN ((LM_ERROR,
119 "%p\n",
120 "ATM_Client: connection failed"),
122 else
123 ACE_DEBUG ((LM_DEBUG,
124 "ATM_Client: connected to %s\n",
125 hosts[ 0 ].addr_to_string()));
127 } else {
128 // Point-to-multipoint connection
129 for ( int i = 0; i < num_leaves; i++ ) {
130 con.add_leaf( atm_stream,
131 hosts[ i ],
133 0 );
135 } /* if num_leaves == 1 */
137 ACE_UINT16 vpi, vci;
138 atm_stream.get_vpi_vci(vpi, vci);
139 ACE_DEBUG ((LM_DEBUG,
140 "ATM_Client: connected to VPI %d VCI %d\n",
141 vpi, vci));
143 // Send data to server (correctly handles "incomplete writes").
145 int s_bytes;
146 int total;
147 int xmit = 0;
148 ACE_High_Res_Timer timer;
149 ACE_Time_Value elapsed;
150 double real_time;
151 double actual_rate;
153 for ( ;; ) {
154 total = 0;
156 timer.start_incr();
158 for ( ;; ) {
159 s_bytes = atm_stream.send_n( buf, BUFSIZ, 0 );
160 if ( s_bytes == -1 )
161 ACE_ERROR_RETURN ((LM_ERROR,
162 "%p\n",
163 "send_n"),
166 total += s_bytes;
168 if ( total >= session * pdu_size )
169 break;
172 timer.stop_incr();
173 timer.elapsed_time_incr( elapsed );
174 real_time = elapsed.sec() * ACE_ONE_SECOND_IN_USECS + elapsed.usec();
175 xmit += total;
176 actual_rate = ( double )xmit * ( double )8 / real_time;
178 ACE_DEBUG ((LM_DEBUG,
179 ACE_TEXT ("(%t) bytes = %d, usec = %f, rate = %0.00f Mbps\n"),
180 xmit,
181 real_time,
182 actual_rate < 0 ? 0 : actual_rate ));
185 // Explicitly close the connection.
186 ACE_OS::printf( "ATM_Client: close connection\n" );
187 if (atm_stream.close () == -1)
188 ACE_ERROR_RETURN ((LM_ERROR,
189 "%p\n",
190 "close"),
191 -1);
192 return 0;
194 #else
195 int ACE_TMAIN (int, ACE_TCHAR *[])
197 ACE_ERROR_RETURN ((LM_ERROR,
198 "your platform isn't configured to support ATM\n"),
201 #endif /* ACE_HAS_ATM */