MySQL 5.6.14 Source Code Document
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
testLongSig.cpp
1 /*
2  Copyright (c) 2003, 2010, Oracle and/or its affiliates. All rights reserved.
3 
4  This program is free software; you can redistribute it and/or modify
5  it under the terms of the GNU General Public License as published by
6  the Free Software Foundation; version 2 of the License.
7 
8  This program is distributed in the hope that it will be useful,
9  but WITHOUT ANY WARRANTY; without even the implied warranty of
10  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11  GNU General Public License for more details.
12 
13  You should have received a copy of the GNU General Public License
14  along with this program; if not, write to the Free Software
15  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
16 */
17 
18 
19 #include <ndb_global.h>
20 #include <NdbApi.hpp>
21 #include <readline/readline.h>
22 #include <../../ndbapi/SignalSender.hpp>
23 
24 void
25 print_help(){
26  ndbout << "The test menu" << endl;
27  ndbout << "1 - Sending of long signals w/ segmented sections" << endl;
28  ndbout << "2 - As 1 but using receiver group" << endl;
29  ndbout << "3 - Sending of long signals w/ linear sections" << endl;
30  ndbout << "4 - As 3 but using receiver group" << endl;
31  ndbout << "5 - Sending of manually fragmented signals w/ segmented sections"
32  << endl;
33  ndbout << "6 - As 5 but using receiver group" << endl;
34  ndbout << "7 - Sending of manually fragmented signals w/ linear sections"
35  << endl;
36  ndbout << "8 - As but using receiver group" << endl;
37 
38  ndbout << "9 - Sending of CONTINUEB fragmented signals w/ segmented sections"
39  << endl;
40  ndbout << "10 - As 9 but using receiver group" << endl;
41  ndbout << "11 - Sending of CONTINUEB fragmented signals w/ linear sections"
42  << endl;
43  ndbout << "12 - As but using receiver group" << endl;
44  ndbout << "13 - As 5 but with no release" << endl;
45  ndbout << "14 - As 13 but using receiver group" << endl;
46  ndbout << "15 - Send 100 * 1000 25 len signals wo/ sections" << endl;
47  ndbout << "r - Recive signal from anyone" << endl;
48  ndbout << "a - Run tests 1 - 14 with variable sizes - 10 loops" << endl;
49  ndbout << "b - Run tests 1 - 14 with variable sizes - 100 loops" << endl;
50  ndbout << "c - Run tests 1 - 14 with variable sizes - 1000k loops" << endl;
51 }
52 
53 void runTest(SignalSender &, Uint32 i, bool verbose);
54 
55 static
56 int
57 randRange(Uint32 min, Uint32 max){
58  float r = rand();
59  float f = (max - min + 1);
60  float d = (float)RAND_MAX + 1.0;
61  return min + (int)(f * r / d);
62 }
63 
64 static
65 int
66 randRange(const Uint32 odds[], Uint32 count){
67  Uint32 val = randRange((Uint32)0, 100);
68 
69  Uint32 i = 0;
70  Uint32 sum = 0;
71  while(sum <= val && i < count){
72  sum += odds[i];
73  i++;
74  }
75  return i - 1;
76 }
77 
86 int
87 main(int argc, char** argv) {
88  ndb_init();
89 
90  srand(NdbTick_CurrentMillisecond());
91 #if 0
92  for(int i = 0; i<100; i++)
93  ndbout_c("randRange(0, 3) = %d", randRange(0, 3));
94  return 0;
95 #endif
96 
97  if (argc != 2)
98  {
99  ndbout << "No connectstring given, usage : " << argv[0]
100  << " <connectstring>" << endl;
101  return -1;
102  }
103  Ndb_cluster_connection con(argv[1]);
104 
105  ndbout << "Connecting...";
106  if (con.connect(12,5,1) != 0)
107  {
108  ndbout << "Unable to connect to management server." << endl;
109  return -1;
110  }
111  if (con.wait_until_ready(30,0) < 0)
112  {
113  ndbout << "Cluster nodes not ready in 30 seconds." << endl;
114  return -1;
115  }
116  ndbout << "done" << endl;
117 
118  SignalSender ss(&con);
119 
120  ndbout_c("Connected as block=%d node=%d",
121  refToBlock(ss.getOwnRef()), refToNode(ss.getOwnRef()));
122 
123  Uint32 data[25];
124  Uint32 sec0[70];
125  Uint32 sec1[123];
126  Uint32 sec2[10];
127 
128  data[0] = ss.getOwnRef();
129  data[1] = 1;
130  data[2] = 76;
131  data[3] = 1;
132  data[4] = 1;
133  data[5] = 70;
134  data[6] = 123;
135  data[7] = 10;
136  const Uint32 theDataLen = 18;
137 
138  for(Uint32 i = 0; i<70; i++)
139  sec0[i] = i;
140 
141  for(Uint32 i = 0; i<123; i++)
142  sec1[i] = 70+i;
143 
144  for(Uint32 i = 0; i<10; i++)
145  sec2[i] = (i + 1)*(i + 1);
146 
147  SimpleSignal signal1;
148  signal1.set(ss, 0, CMVMI, GSN_TESTSIG, theDataLen + 2);
149  signal1.header.m_noOfSections = 1;
150  signal1.header.m_fragmentInfo = 1;
151 
152  memcpy(&signal1.theData[0], data, 4 * theDataLen );
153  signal1.theData[theDataLen + 0] = 0;
154  signal1.theData[theDataLen + 1] = 7; // FragmentId
155 
156  signal1.ptr[0].sz = 60;
157  signal1.ptr[0].p = &sec0[0];
158 
159  SimpleSignal signal2;
160 
161  Uint32 idx = 0;
162  memcpy(&signal2.theData[0], data, 4 * theDataLen );
163  signal2.theData[theDataLen + idx] = 0; idx++;
164  signal2.theData[theDataLen + idx] = 1; idx++;
165  //signal2.theData[theDataLen + idx] = 2; idx++;
166  signal2.theData[theDataLen + idx] = 7; idx++; // FragmentId
167 
168  signal2.set(ss, 0, CMVMI, GSN_TESTSIG, theDataLen + idx);
169  signal2.header.m_fragmentInfo = 3;
170  signal2.header.m_noOfSections = idx - 1;
171 
172  signal2.ptr[0].sz = 10;
173  signal2.ptr[0].p = &sec0[60];
174 
175  signal2.ptr[1].sz = 123;
176  signal2.ptr[1].p = &sec1[0];
177 
178  signal2.ptr[2].sz = 10;
179  signal2.ptr[2].p = &sec2[0];
180 
181  char * buf;
182  while((buf = readline("Enter command: "))){
183  add_history(buf);
184  data[1] = atoi(buf);
185  if(strcmp(buf, "r") == 0){
186  SimpleSignal * ret1 = ss.waitFor();
187  (* ret1).print();
188  continue;
189  }
190  if(strcmp(buf, "a") == 0){
191  runTest(ss, 10, true);
192  print_help();
193  continue;
194  }
195  if(strcmp(buf, "b") == 0){
196  runTest(ss, 100, false);
197  print_help();
198  continue;
199  }
200  if(strcmp(buf, "c") == 0){
201  runTest(ss, 1000000, false);
202  print_help();
203  continue;
204  }
205 
206  if(data[1] >= 1 && data[1] <= 14){
207  Uint32 nodeId = ss.getAliveNode();
208  ndbout_c("Sending 2 fragmented to node %d", nodeId);
209  ss.sendSignal(nodeId, &signal1);
210  ss.sendSignal(nodeId, &signal2);
211 
212  if(data[1] >= 5){
213  continue;
214  }
215  ndbout_c("Waiting for signal from %d", nodeId);
216 
217  SimpleSignal * ret1 = ss.waitFor((Uint16)nodeId);
218  (* ret1).print();
219  Uint32 count = ret1->theData[4] - 1;
220  while(count > 0){
221  ndbout << "Waiting for " << count << " signals... ";
222  SimpleSignal * ret1 = ss.waitFor();
223  ndbout_c("received from node %d",
224  refToNode(ret1->header.theSendersBlockRef));
225  (* ret1).print();
226  count--;
227  }
228  } else if (data[1] == 15) {
229  const Uint32 count = 3500;
230  const Uint32 loop = 1000;
231 
232  signal1.set(ss, 0, CMVMI, GSN_TESTSIG, 25);
233  signal1.header.m_fragmentInfo = 0;
234  signal1.header.m_noOfSections = 0;
235  signal1.theData[1] = 14;
236  signal1.theData[3] = 0; // Print
237  signal1.theData[8] = count;
238  signal1.theData[9] = loop;
239  Uint32 nodeId = ss.getAliveNode();
240  ndbout_c("Sending 25 len signal to node %d", nodeId);
241  ss.sendSignal(nodeId, &signal1);
242 
243  Uint32 total;
244  {
245  SimpleSignal * ret1 = ss.waitFor((Uint16)nodeId);
246  ndbout_c("received from node %d",
247  refToNode(ret1->header.theSendersBlockRef));
248  total = ret1->theData[10] - 1;
249  }
250 
251  do {
252  ndbout << "Waiting for " << total << " signals... " << flush;
253  SimpleSignal * ret1 = ss.waitFor((Uint16)nodeId);
254  ndbout_c("received from node %d",
255  refToNode(ret1->header.theSendersBlockRef));
256  total --;
257  } while(total > 0);
258  } else {
259  print_help();
260  }
261  }
262  ndbout << "Exiting" << endl;
263  ndb_end(0);
264 };
265 
266 void
267 runTest(SignalSender & ss, Uint32 count, bool verbose){
268 
269  SimpleSignal sig;
270  Uint32 sec0[256];
271  Uint32 sec1[256];
272  Uint32 sec2[256];
273  for(Uint32 i = 0; i<256; i++){
274  sec0[i] = i;
275  sec1[i] = i + i;
276  sec2[i] = i * i;
277  }
278 
279  sig.theData[0] = ss.getOwnRef();
280  sig.theData[1] = 1; // TestType
281  sig.theData[2] = 128; // FragSize
282  sig.theData[3] = 0; // Print
283  sig.theData[4] = 1; // RetCount
284 
285  sig.ptr[0].p = &sec0[0];
286  sig.ptr[1].p = &sec1[0];
287  sig.ptr[2].p = &sec2[0];
288 
289  for(unsigned loop = 0; loop < count; loop++){
290  const Uint32 odds[] = { 5, 40, 30, 25 };
291  const Uint32 secs = randRange(odds, 4);
292  sig.ptr[0].sz = randRange(1, 256);
293  sig.ptr[1].sz = randRange(1, 256);
294  sig.ptr[2].sz = randRange(1, 256);
295  sig.header.m_noOfSections = secs;
296  const Uint32 len = 5 + (secs > 0 ? 1 : 0) * (25 - 5 - 7);
297  sig.set(ss, 0, CMVMI, GSN_TESTSIG, len);
298  ndbout << "Loop " << loop << " #secs = " << secs << " sizes = [ ";
299  unsigned min = 256;
300  unsigned max = 0;
301  unsigned sum = 0;
302  for(unsigned i = 0; i<secs; i++){
303  const Uint32 sz = sig.ptr[i].sz;
304  ndbout << sz << " ";
305  min = (min < sz ? min : sz);
306  max = (max > sz ? max : sz);
307  sum += sz;
308  sig.theData[5+i] = sz;
309  }
310  ndbout_c("] len = %d", len);
311  for(int test = 1; test <= 14; test++){
312  sig.theData[1] = test;
313  Uint32 nodeId = ss.getAliveNode();
314  if(verbose){
315  ndbout << " Test " << test << " node " << nodeId << "...";
316  fflush(stdout);
317  }
318  SendStatus r = ss.sendSignal(nodeId, &sig);
319  assert(r == SEND_OK);
320  if(test < 5){
321  SimpleSignal * ret1 = ss.waitFor((Uint16)nodeId);
322  Uint32 count = ret1->theData[4] - 1;
323 
324  while(count > 0){
325  ret1 = ss.waitFor();
326  count--;
327  }
328  if(verbose)
329  ndbout << "done" << endl;
330  } else {
331  Uint32 nodes = ss.getNoOfConnectedNodes();
332  Uint32 sum2 = 0;
333  if((test & 1) == 1)
334  nodes = 1;
335  while(nodes > 0){
336  SimpleSignal * ret = ss.waitFor();
337  if(ret->header.m_fragmentInfo == 0){
338  for(Uint32 i = 0; i<ret->header.m_noOfSections; i++)
339  sum2 += ret->ptr[i].sz;
340  } else {
341  for(Uint32 i = 0; i<ret->header.m_noOfSections; i++)
342  if(ret->theData[i] != 3)
343  sum2 += ret->ptr[i].sz;
344  }
345  if(ret->header.m_fragmentInfo == 0 ||
346  ret->header.m_fragmentInfo == 3){
347  nodes--;
348  }
349  }
350  if(verbose)
351  ndbout_c("done sum=%d sum2=%d", sum, sum2);
352  }
353  }
354  }
355 }