1/* Copyright (C) 2008-2017 Kentoku Shiba
2
3 This program is free software; you can redistribute it and/or modify
4 it under the terms of the GNU General Public License as published by
5 the Free Software Foundation; version 2 of the License.
6
7 This program is distributed in the hope that it will be useful,
8 but WITHOUT ANY WARRANTY; without even the implied warranty of
9 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 GNU General Public License for more details.
11
12 You should have received a copy of the GNU General Public License
13 along with this program; if not, write to the Free Software
14 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
15
16#define MYSQL_SERVER 1
17#include <my_global.h>
18#include "mysql_version.h"
19#include "spd_environ.h"
20#if MYSQL_VERSION_ID < 50500
21#include "mysql_priv.h"
22#include <mysql/plugin.h>
23#else
24#include "sql_priv.h"
25#include "probes_mysql.h"
26#include "sql_class.h"
27#include "sql_partition.h"
28#include "ha_partition.h"
29#endif
30#include "sql_common.h"
31#include <errmsg.h>
32#include "spd_err.h"
33#include "spd_param.h"
34#include "spd_db_include.h"
35#include "spd_include.h"
36#include "ha_spider.h"
37#include "spd_conn.h"
38#include "spd_db_conn.h"
39#include "spd_malloc.h"
40#include "spd_table.h"
41#include "spd_ping_table.h"
42#include "spd_group_by_handler.h"
43
44extern handlerton *spider_hton_ptr;
45extern SPIDER_DBTON spider_dbton[SPIDER_DBTON_SIZE];
46
47spider_fields::spider_fields() :
48 dbton_count(0), current_dbton_num(0),
49 table_count(0), current_table_num(0), table_holder(NULL),
50 first_link_idx_chain(NULL), last_link_idx_chain(NULL), current_link_idx_chain(NULL),
51 first_conn_holder(NULL), last_conn_holder(NULL), current_conn_holder(NULL),
52 first_field_holder(NULL), last_field_holder(NULL), current_field_holder(NULL),
53 first_field_chain(NULL), last_field_chain(NULL), current_field_chain(NULL)
54{
55 DBUG_ENTER("spider_fields::spider_fields");
56 DBUG_PRINT("info",("spider this=%p", this));
57 DBUG_VOID_RETURN;
58}
59
60spider_fields::~spider_fields()
61{
62 DBUG_ENTER("spider_fields::~spider_fields");
63 DBUG_PRINT("info",("spider this=%p", this));
64 if (first_link_idx_chain)
65 {
66 while ((current_link_idx_chain = first_link_idx_chain))
67 {
68 first_link_idx_chain = current_link_idx_chain->next;
69 spider_free(spider_current_trx, current_link_idx_chain, MYF(0));
70 }
71 }
72 if (first_field_chain)
73 {
74 while ((current_field_chain = first_field_chain))
75 {
76 first_field_chain = current_field_chain->next;
77 spider_free(spider_current_trx, current_field_chain, MYF(0));
78 }
79 }
80 if (first_field_holder)
81 {
82 while ((current_field_holder = first_field_holder))
83 {
84 first_field_holder = current_field_holder->next;
85 spider_free(spider_current_trx, current_field_holder, MYF(0));
86 }
87 }
88 if (table_holder)
89 spider_free(spider_current_trx, table_holder, MYF(0));
90 if (first_conn_holder)
91 {
92 while ((current_conn_holder = first_conn_holder))
93 {
94 first_conn_holder = current_conn_holder->next;
95 free_conn_holder(current_conn_holder);
96 }
97 }
98 DBUG_VOID_RETURN;
99}
100
101void spider_fields::add_dbton_id(
102 uint dbton_id_arg
103) {
104 uint roop_count;
105 DBUG_ENTER("spider_fields::add_dbton_id");
106 DBUG_PRINT("info",("spider this=%p", this));
107 for (roop_count = 0; roop_count < dbton_count; ++roop_count)
108 {
109 if (dbton_ids[roop_count] == dbton_id_arg)
110 {
111 DBUG_VOID_RETURN;
112 }
113 }
114 dbton_ids[roop_count] = dbton_id_arg;
115 ++dbton_count;
116 DBUG_VOID_RETURN;
117}
118
119void spider_fields::set_pos_to_first_dbton_id(
120) {
121 DBUG_ENTER("spider_fields::set_pos_to_first_dbton_id");
122 DBUG_PRINT("info",("spider this=%p", this));
123 current_dbton_num = 0;
124 DBUG_VOID_RETURN;
125}
126
127uint spider_fields::get_next_dbton_id(
128) {
129 uint return_dbton_id;
130 DBUG_ENTER("spider_fields::get_next_dbton_id");
131 DBUG_PRINT("info",("spider this=%p", this));
132 if (current_dbton_num >= dbton_count)
133 DBUG_RETURN(SPIDER_DBTON_SIZE);
134 return_dbton_id = dbton_ids[current_dbton_num];
135 ++current_dbton_num;
136 DBUG_RETURN(return_dbton_id);
137}
138
139int spider_fields::make_link_idx_chain(
140 int link_status
141) {
142 uint roop_count, roop_count2;
143 SPIDER_CONN *conn;
144 SPIDER_CONN_HOLDER *conn_holder;
145 SPIDER_TABLE_LINK_IDX_HOLDER *table_link_idx_holder;
146 SPIDER_LINK_IDX_HOLDER *link_idx_holder, *add_link_idx_holder,
147 *dup_link_idx_holder, *current_link_idx_holder;
148 ha_spider *spider;
149 SPIDER_LINK_IDX_CHAIN *link_idx_chain;
150 SPIDER_SHARE *share;
151 DBUG_ENTER("spider_fields::make_link_idx_chain");
152 DBUG_PRINT("info",("spider this=%p", this));
153 conn_holder = first_conn_holder;
154 bool has_remain, skip;
155 do {
156 for (roop_count2 = 0; roop_count2 < table_count; ++roop_count2)
157 {
158 table_link_idx_holder = &conn_holder->table_link_idx_holder[roop_count2];
159 link_idx_holder = table_link_idx_holder->first_link_idx_holder;
160 dup_link_idx_holder = NULL;
161 for (roop_count = 0;
162 roop_count < conn_holder->link_idx_holder_count_max - 1; ++roop_count)
163 {
164 if (!link_idx_holder->next)
165 {
166 DBUG_PRINT("info",("spider fill link_idx_holder for %u",
167 roop_count2));
168 if (!(add_link_idx_holder = create_link_idx_holder()))
169 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
170 dup_link_idx_holder = get_dup_link_idx_holder(
171 table_link_idx_holder, dup_link_idx_holder);
172 add_link_idx_holder->table_link_idx_holder =
173 dup_link_idx_holder->table_link_idx_holder;
174 add_link_idx_holder->link_idx = dup_link_idx_holder->link_idx;
175 link_idx_holder->next = add_link_idx_holder;
176 }
177 link_idx_holder = link_idx_holder->next;
178 }
179 }
180
181 for (roop_count2 = 0; roop_count2 < table_count; ++roop_count2)
182 {
183 table_link_idx_holder = &conn_holder->table_link_idx_holder[roop_count2];
184 table_link_idx_holder->current_link_idx_holder =
185 table_link_idx_holder->first_link_idx_holder;
186 }
187 for (roop_count = 0;
188 roop_count < conn_holder->link_idx_holder_count_max; ++roop_count)
189 {
190 link_idx_holder = NULL;
191 for (roop_count2 = 0; roop_count2 < table_count; ++roop_count2)
192 {
193 table_link_idx_holder =
194 &conn_holder->table_link_idx_holder[roop_count2];
195 if (link_idx_holder)
196 {
197 link_idx_holder->next_table =
198 table_link_idx_holder->current_link_idx_holder;
199 }
200 link_idx_holder = table_link_idx_holder->current_link_idx_holder;
201 table_link_idx_holder->current_link_idx_holder = link_idx_holder->next;
202 }
203 }
204 } while ((conn_holder = conn_holder->next));
205
206 current_conn_holder = first_conn_holder;
207 do {
208 table_link_idx_holder =
209 &current_conn_holder->table_link_idx_holder[0];
210 table_link_idx_holder->current_link_idx_holder =
211 table_link_idx_holder->first_link_idx_holder;
212 } while ((current_conn_holder = current_conn_holder->next));
213
214 spider = table_holder[0].spider;
215 share = spider->share;
216 DBUG_PRINT("info",("spider create link_idx_chain sorted by 0"));
217 for (
218 roop_count = spider_conn_link_idx_next(share->link_statuses,
219 spider->conn_link_idx, -1, share->link_count,
220 link_status);
221 roop_count < share->link_count;
222 roop_count = spider_conn_link_idx_next(share->link_statuses,
223 spider->conn_link_idx, roop_count, share->link_count,
224 link_status)
225 ) {
226 conn = spider->conns[roop_count];
227 if (!conn->conn_holder_for_direct_join)
228 {
229 continue;
230 }
231 table_link_idx_holder =
232 &conn->conn_holder_for_direct_join->table_link_idx_holder[0];
233 link_idx_holder = table_link_idx_holder->current_link_idx_holder;
234 table_link_idx_holder->current_link_idx_holder = link_idx_holder->next;
235 DBUG_ASSERT(link_idx_holder->link_idx == (int) roop_count);
236 if (!(link_idx_chain = create_link_idx_chain()))
237 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
238 if (!first_link_idx_chain)
239 {
240 first_link_idx_chain = link_idx_chain;
241 } else {
242 last_link_idx_chain->next = link_idx_chain;
243 }
244 last_link_idx_chain = link_idx_chain;
245 link_idx_chain->conn = conn;
246 link_idx_chain->link_idx_holder = link_idx_holder;
247 do {
248 if (link_idx_chain->link_status < link_idx_holder->link_status)
249 {
250 link_idx_chain->link_status = link_idx_holder->link_status;
251 }
252 } while ((link_idx_holder = link_idx_holder->next_table));
253 }
254
255 do {
256 has_remain = FALSE;
257 current_conn_holder = first_conn_holder;
258 do {
259 table_link_idx_holder =
260 &current_conn_holder->table_link_idx_holder[0];
261 link_idx_holder = table_link_idx_holder->current_link_idx_holder;
262 if (link_idx_holder)
263 {
264 has_remain = TRUE;
265 for (roop_count2 = 1; roop_count2 < table_count; ++roop_count2)
266 {
267 if (table_link_idx_holder[roop_count2].link_idx_holder_count ==
268 current_conn_holder->link_idx_holder_count_max)
269 {
270 break;
271 }
272 }
273 break;
274 }
275 } while ((current_conn_holder = current_conn_holder->next));
276
277 if (has_remain)
278 {
279 current_conn_holder = first_conn_holder;
280 do {
281 table_link_idx_holder =
282 &current_conn_holder->table_link_idx_holder[0];
283 link_idx_holder = table_link_idx_holder->current_link_idx_holder;
284 if (link_idx_holder)
285 {
286 for (roop_count = 1; roop_count <= roop_count2; ++roop_count)
287 {
288 link_idx_holder = link_idx_holder->next_table;
289 }
290 table_link_idx_holder[roop_count2].current_link_idx_holder =
291 link_idx_holder;
292 } else {
293 table_link_idx_holder[roop_count2].current_link_idx_holder = NULL;
294 }
295 } while ((current_conn_holder = current_conn_holder->next));
296
297 spider = table_holder[roop_count2].spider;
298 share = spider->share;
299 DBUG_PRINT("info",("spider create link_idx_chain sorted by %d",
300 roop_count2));
301 for (
302 roop_count = spider_conn_link_idx_next(share->link_statuses,
303 spider->conn_link_idx, -1, share->link_count,
304 link_status);
305 roop_count < share->link_count;
306 roop_count = spider_conn_link_idx_next(share->link_statuses,
307 spider->conn_link_idx, roop_count, share->link_count,
308 link_status)
309 ) {
310 conn = spider->conns[roop_count];
311 if (!conn->conn_holder_for_direct_join)
312 {
313 continue;
314 }
315 table_link_idx_holder =
316 &conn->conn_holder_for_direct_join->table_link_idx_holder[0];
317 link_idx_holder =
318 table_link_idx_holder[roop_count2].current_link_idx_holder;
319 skip = FALSE;
320 if (link_idx_holder)
321 {
322 current_link_idx_holder = table_link_idx_holder->first_link_idx_holder;
323 while (current_link_idx_holder != link_idx_holder)
324 {
325 if (current_link_idx_holder->link_idx ==
326 link_idx_holder->link_idx)
327 {
328 skip = TRUE;
329 break;
330 }
331 current_link_idx_holder = current_link_idx_holder->next;
332 }
333 }
334 if (skip)
335 {
336 continue;
337 }
338 DBUG_PRINT("info",("spider create link_idx_chain for %d",
339 roop_count2));
340 table_link_idx_holder[roop_count2].current_link_idx_holder =
341 link_idx_holder->next;
342 link_idx_holder =
343 table_link_idx_holder->current_link_idx_holder;
344 table_link_idx_holder->current_link_idx_holder =
345 link_idx_holder->next;
346 if (!(link_idx_chain = create_link_idx_chain()))
347 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
348 DBUG_ASSERT(first_link_idx_chain);
349 last_link_idx_chain->next = link_idx_chain;
350 last_link_idx_chain = link_idx_chain;
351 link_idx_chain->conn = conn;
352 link_idx_chain->link_idx_holder = link_idx_holder;
353 do {
354 if (link_idx_chain->link_status < link_idx_holder->link_status)
355 {
356 link_idx_chain->link_status = link_idx_holder->link_status;
357 }
358 } while ((link_idx_holder = link_idx_holder->next_table));
359 }
360 }
361 } while (has_remain);
362 DBUG_RETURN(0);
363}
364
365SPIDER_LINK_IDX_CHAIN *spider_fields::create_link_idx_chain(
366) {
367 DBUG_ENTER("spider_fields::create_link_idx_chain");
368 DBUG_PRINT("info",("spider this=%p", this));
369 DBUG_RETURN((SPIDER_LINK_IDX_CHAIN *)
370 spider_malloc(spider_current_trx, 254, sizeof(SPIDER_LINK_IDX_CHAIN),
371 MYF(MY_WME | MY_ZEROFILL)));
372}
373
374void spider_fields::set_pos_to_first_link_idx_chain(
375) {
376 DBUG_ENTER("spider_fields::set_pos_to_first_link_idx_chain");
377 DBUG_PRINT("info",("spider this=%p", this));
378 current_link_idx_chain = first_link_idx_chain;
379 DBUG_VOID_RETURN;
380}
381
382SPIDER_LINK_IDX_CHAIN *spider_fields::get_next_link_idx_chain(
383) {
384 SPIDER_LINK_IDX_CHAIN *return_link_idx_chain = current_link_idx_chain;
385 DBUG_ENTER("spider_fields::get_next_link_idx_chain");
386 DBUG_PRINT("info",("spider this=%p", this));
387 if (current_link_idx_chain)
388 current_link_idx_chain = current_link_idx_chain->next;
389 DBUG_RETURN(return_link_idx_chain);
390}
391
392SPIDER_LINK_IDX_HOLDER *spider_fields::get_dup_link_idx_holder(
393 SPIDER_TABLE_LINK_IDX_HOLDER *table_link_idx_holder,
394 SPIDER_LINK_IDX_HOLDER *current
395) {
396 SPIDER_LINK_IDX_HOLDER *return_link_idx_holder;
397 DBUG_ENTER("spider_fields::get_dup_link_idx_holder");
398 DBUG_PRINT("info",("spider this=%p", this));
399 if (!current)
400 {
401 return_link_idx_holder = table_link_idx_holder->first_link_idx_holder;
402 do {
403 if (return_link_idx_holder->link_status == SPIDER_LINK_STATUS_OK)
404 break;
405 } while ((return_link_idx_holder = return_link_idx_holder->next));
406 if (!return_link_idx_holder)
407 {
408 return_link_idx_holder = table_link_idx_holder->first_link_idx_holder;
409 }
410 } else {
411 if (current->link_status == SPIDER_LINK_STATUS_OK)
412 {
413 return_link_idx_holder = current;
414 while ((return_link_idx_holder = return_link_idx_holder->next))
415 {
416 if (return_link_idx_holder->link_status == SPIDER_LINK_STATUS_OK)
417 break;
418 }
419 if (!return_link_idx_holder)
420 {
421 return_link_idx_holder = table_link_idx_holder->first_link_idx_holder;
422 do {
423 if (
424 return_link_idx_holder->link_status == SPIDER_LINK_STATUS_OK
425 )
426 break;
427 DBUG_ASSERT(return_link_idx_holder != current);
428 } while ((return_link_idx_holder = return_link_idx_holder->next));
429 }
430 } else {
431 if (!current->next)
432 {
433 return_link_idx_holder = table_link_idx_holder->first_link_idx_holder;
434 } else {
435 return_link_idx_holder = current->next;
436 }
437 }
438 }
439 DBUG_RETURN(return_link_idx_holder);
440}
441
442bool spider_fields::check_link_ok_chain(
443) {
444 DBUG_ENTER("spider_fields::check_link_ok_chain");
445 DBUG_PRINT("info",("spider this=%p", this));
446 for (current_link_idx_chain = first_link_idx_chain; current_link_idx_chain;
447 current_link_idx_chain = current_link_idx_chain->next)
448 {
449 if (current_link_idx_chain->link_status == SPIDER_LINK_STATUS_OK)
450 {
451 first_ok_link_idx_chain = current_link_idx_chain;
452 DBUG_RETURN(FALSE);
453 }
454 }
455 DBUG_RETURN(TRUE);
456}
457
458bool spider_fields::is_first_link_ok_chain(
459 SPIDER_LINK_IDX_CHAIN *link_idx_chain_arg
460) {
461 DBUG_ENTER("spider_fields::is_first_link_ok_chain");
462 DBUG_PRINT("info",("spider this=%p", this));
463 DBUG_RETURN(first_ok_link_idx_chain == link_idx_chain_arg);
464}
465
466int spider_fields::get_ok_link_idx(
467) {
468 DBUG_ENTER("spider_fields::get_ok_link_idx");
469 DBUG_PRINT("info",("spider this=%p", this));
470 DBUG_RETURN(first_ok_link_idx_chain->link_idx_holder->link_idx);
471}
472
473void spider_fields::set_first_link_idx(
474) {
475 SPIDER_TABLE_HOLDER *table_holder;
476 SPIDER_LINK_IDX_HOLDER *link_idx_holder;
477 SPIDER_LINK_IDX_CHAIN *link_idx_chain;
478 uint dbton_id;
479 ha_spider *spider;
480 spider_db_handler *dbton_hdl;
481 DBUG_ENTER("spider_fields::set_first_link_idx");
482 DBUG_PRINT("info",("spider this=%p", this));
483 set_pos_to_first_dbton_id();
484 while ((dbton_id = get_next_dbton_id()) < SPIDER_DBTON_SIZE)
485 {
486 set_pos_to_first_link_idx_chain();
487 while ((link_idx_chain = get_next_link_idx_chain()))
488 {
489 if (link_idx_chain->conn->dbton_id == dbton_id)
490 {
491 break;
492 }
493 }
494 DBUG_ASSERT(link_idx_chain);
495 set_pos_to_first_table_on_link_idx_chain(link_idx_chain);
496
497 set_pos_to_first_table_holder();
498 while ((table_holder = get_next_table_holder()))
499 {
500 link_idx_holder = get_next_table_on_link_idx_chain(link_idx_chain);
501 spider = table_holder->spider;
502 dbton_hdl = spider->dbton_handler[dbton_id];
503 dbton_hdl->first_link_idx = link_idx_holder->link_idx;
504 }
505 }
506 DBUG_VOID_RETURN;
507}
508
509int spider_fields::add_link_idx(
510 SPIDER_CONN_HOLDER *conn_holder_arg,
511 ha_spider *spider_arg,
512 int link_idx
513) {
514 SPIDER_TABLE_LINK_IDX_HOLDER *table_link_idx_holder;
515 SPIDER_LINK_IDX_HOLDER *link_idx_holder;
516 DBUG_ENTER("spider_fields::add_link_idx");
517 DBUG_PRINT("info",("spider this=%p", this));
518 table_link_idx_holder =
519 &conn_holder_arg->table_link_idx_holder[spider_arg->idx_for_direct_join];
520 if (!table_link_idx_holder->first_link_idx_holder)
521 {
522 link_idx_holder = create_link_idx_holder();
523 DBUG_PRINT("info",("spider link_idx_holder=%p", link_idx_holder));
524 if (!link_idx_holder)
525 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
526 table_link_idx_holder->first_link_idx_holder = link_idx_holder;
527 table_link_idx_holder->last_link_idx_holder = link_idx_holder;
528 table_link_idx_holder->table_holder =
529 &table_holder[spider_arg->idx_for_direct_join];
530 } else {
531 link_idx_holder = create_link_idx_holder();
532 DBUG_PRINT("info",("spider link_idx_holder=%p", link_idx_holder));
533 if (!link_idx_holder)
534 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
535 table_link_idx_holder->last_link_idx_holder->next = link_idx_holder;
536 table_link_idx_holder->last_link_idx_holder = link_idx_holder;
537 }
538 link_idx_holder->table_link_idx_holder = table_link_idx_holder;
539 link_idx_holder->link_idx = link_idx;
540 link_idx_holder->link_status = spider_conn_get_link_status(
541 spider_arg->share->link_statuses, spider_arg->conn_link_idx,
542 link_idx);
543 ++table_link_idx_holder->link_idx_holder_count;
544 if (conn_holder_arg->link_idx_holder_count_max <
545 table_link_idx_holder->link_idx_holder_count)
546 {
547 conn_holder_arg->link_idx_holder_count_max =
548 table_link_idx_holder->link_idx_holder_count;
549 }
550 DBUG_RETURN(0);
551}
552
553SPIDER_LINK_IDX_HOLDER *spider_fields::create_link_idx_holder(
554) {
555 DBUG_ENTER("spider_fields::create_link_idx_holder");
556 DBUG_PRINT("info",("spider this=%p", this));
557 DBUG_RETURN((SPIDER_LINK_IDX_HOLDER *)
558 spider_malloc(spider_current_trx, 253, sizeof(SPIDER_LINK_IDX_HOLDER),
559 MYF(MY_WME | MY_ZEROFILL)));
560}
561
562void spider_fields::set_pos_to_first_table_on_link_idx_chain(
563 SPIDER_LINK_IDX_CHAIN *link_idx_chain_arg
564) {
565 DBUG_ENTER("spider_fields::set_pos_to_first_table_on_link_idx_chain");
566 DBUG_PRINT("info",("spider this=%p", this));
567 link_idx_chain_arg->current_link_idx_holder =
568 link_idx_chain_arg->link_idx_holder;
569 DBUG_VOID_RETURN;
570}
571
572SPIDER_LINK_IDX_HOLDER *spider_fields::get_next_table_on_link_idx_chain(
573 SPIDER_LINK_IDX_CHAIN *link_idx_chain_arg
574) {
575 SPIDER_LINK_IDX_HOLDER *return_link_idx_holder;
576 DBUG_ENTER("spider_fields::get_next_table_on_link_idx_chain");
577 DBUG_PRINT("info",("spider this=%p", this));
578 if (!link_idx_chain_arg->current_link_idx_holder)
579 DBUG_RETURN(NULL);
580 return_link_idx_holder = link_idx_chain_arg->current_link_idx_holder;
581 link_idx_chain_arg->current_link_idx_holder =
582 link_idx_chain_arg->current_link_idx_holder->next_table;
583 DBUG_RETURN(return_link_idx_holder);
584}
585
586SPIDER_CONN_HOLDER *spider_fields::add_conn(
587 SPIDER_CONN *conn_arg,
588 long access_balance
589) {
590 SPIDER_CONN_HOLDER *conn_holder;
591 DBUG_ENTER("spider_fields::add_conn");
592 DBUG_PRINT("info",("spider this=%p", this));
593 if (!first_conn_holder)
594 {
595 conn_holder = create_conn_holder();
596 DBUG_PRINT("info",("spider conn_holder=%p", conn_holder));
597 if (!conn_holder)
598 DBUG_RETURN(NULL);
599 conn_holder->conn = conn_arg;
600 conn_holder->access_balance = access_balance;
601 first_conn_holder = conn_holder;
602 last_conn_holder = conn_holder;
603 conn_arg->conn_holder_for_direct_join = conn_holder;
604 add_dbton_id(conn_arg->dbton_id);
605 } else {
606 conn_holder = first_conn_holder;
607 do {
608 if (conn_holder->conn == conn_arg)
609 break;
610 } while ((conn_holder = conn_holder->next));
611 if (!conn_holder)
612 {
613 conn_holder = create_conn_holder();
614 DBUG_PRINT("info",("spider conn_holder=%p", conn_holder));
615 if (!conn_holder)
616 DBUG_RETURN(NULL);
617 conn_holder->conn = conn_arg;
618 conn_holder->access_balance = access_balance;
619 conn_holder->prev = last_conn_holder;
620 last_conn_holder->next = conn_holder;
621 last_conn_holder = conn_holder;
622 conn_arg->conn_holder_for_direct_join = conn_holder;
623 add_dbton_id(conn_arg->dbton_id);
624 }
625 }
626 DBUG_RETURN(conn_holder);
627}
628
629SPIDER_CONN_HOLDER *spider_fields::create_conn_holder(
630) {
631 SPIDER_CONN_HOLDER *return_conn_holder;
632 SPIDER_TABLE_LINK_IDX_HOLDER *table_link_idx_holder;
633 DBUG_ENTER("spider_fields::create_conn_holder");
634 DBUG_PRINT("info",("spider this=%p", this));
635 return_conn_holder = (SPIDER_CONN_HOLDER *)
636 spider_bulk_malloc(spider_current_trx, 252, MYF(MY_WME | MY_ZEROFILL),
637 &return_conn_holder, sizeof(SPIDER_CONN_HOLDER),
638 &table_link_idx_holder,
639 table_count * sizeof(SPIDER_TABLE_LINK_IDX_HOLDER),
640 NullS
641 );
642 if (!return_conn_holder)
643 DBUG_RETURN(NULL);
644 DBUG_PRINT("info",("spider table_count=%u", table_count));
645 DBUG_PRINT("info",("spider table_link_idx_holder=%p", table_link_idx_holder));
646 return_conn_holder->table_link_idx_holder = table_link_idx_holder;
647 DBUG_RETURN(return_conn_holder);
648}
649
650void spider_fields::set_pos_to_first_conn_holder(
651) {
652 DBUG_ENTER("spider_fields::set_pos_to_first_conn_holder");
653 DBUG_PRINT("info",("spider this=%p", this));
654 current_conn_holder = first_conn_holder;
655 DBUG_VOID_RETURN;
656}
657
658SPIDER_CONN_HOLDER *spider_fields::get_next_conn_holder(
659) {
660 SPIDER_CONN_HOLDER *return_conn_holder = current_conn_holder;
661 DBUG_ENTER("spider_fields::get_next_conn_holder");
662 DBUG_PRINT("info",("spider this=%p", this));
663 if (current_conn_holder)
664 current_conn_holder = current_conn_holder->next;
665 DBUG_RETURN(return_conn_holder);
666}
667
668bool spider_fields::has_conn_holder(
669) {
670 DBUG_ENTER("spider_fields::has_conn_holder");
671 DBUG_PRINT("info",("spider this=%p", this));
672 DBUG_RETURN(first_conn_holder);
673}
674
675void spider_fields::clear_conn_holder_from_conn(
676) {
677 DBUG_ENTER("spider_fields::clear_conn_checked_for_same_conn");
678 DBUG_PRINT("info",("spider this=%p", this));
679 for (current_conn_holder = first_conn_holder; current_conn_holder;
680 current_conn_holder = current_conn_holder->next)
681 {
682 current_conn_holder->checked_for_same_conn = FALSE;
683 }
684 DBUG_VOID_RETURN;
685}
686
687bool spider_fields::check_conn_same_conn(
688 SPIDER_CONN *conn_arg
689) {
690 DBUG_ENTER("spider_fields::check_conn_same_conn");
691 DBUG_PRINT("info",("spider this=%p", this));
692 for (current_conn_holder = first_conn_holder; current_conn_holder;
693 current_conn_holder = current_conn_holder->next)
694 {
695 if (current_conn_holder->conn == conn_arg)
696 {
697 current_conn_holder->checked_for_same_conn = TRUE;
698 DBUG_RETURN(TRUE);
699 }
700 }
701 DBUG_RETURN(FALSE);
702}
703
704bool spider_fields::remove_conn_if_not_checked(
705) {
706 SPIDER_CONN_HOLDER *conn_holder;
707 bool removed = FALSE;
708 DBUG_ENTER("spider_fields::remove_conn_if_not_checked");
709 DBUG_PRINT("info",("spider this=%p", this));
710 current_conn_holder = first_conn_holder;
711 while (current_conn_holder)
712 {
713 if (!current_conn_holder->checked_for_same_conn)
714 {
715 removed = TRUE;
716 DBUG_PRINT("info",("spider remove connection %p",
717 current_conn_holder->conn));
718 if (!current_conn_holder->prev)
719 {
720 first_conn_holder = current_conn_holder->next;
721 if (current_conn_holder->next)
722 {
723 current_conn_holder->next->prev = NULL;
724 } else {
725 last_conn_holder = NULL;
726 }
727 } else {
728 current_conn_holder->prev->next = current_conn_holder->next;
729 if (current_conn_holder->next)
730 {
731 current_conn_holder->next->prev = current_conn_holder->prev;
732 } else {
733 last_conn_holder = current_conn_holder->prev;
734 last_conn_holder->next = NULL;
735 }
736 }
737 conn_holder = current_conn_holder->next;
738 free_conn_holder(current_conn_holder);
739 current_conn_holder = conn_holder;
740 } else {
741 current_conn_holder = current_conn_holder->next;
742 }
743 }
744 DBUG_RETURN(removed);
745}
746
747void spider_fields::check_support_dbton(
748 uchar *dbton_bitmap
749) {
750 SPIDER_CONN_HOLDER *conn_holder;
751 DBUG_ENTER("spider_fields::check_support_dbton");
752 DBUG_PRINT("info",("spider this=%p", this));
753 current_conn_holder = first_conn_holder;
754 while (current_conn_holder)
755 {
756 if (!spider_bit_is_set(dbton_bitmap, current_conn_holder->conn->dbton_id))
757 {
758 DBUG_PRINT("info",("spider remove connection %p",
759 current_conn_holder->conn));
760 if (!current_conn_holder->prev)
761 {
762 first_conn_holder = current_conn_holder->next;
763 if (current_conn_holder->next)
764 {
765 current_conn_holder->next->prev = NULL;
766 } else {
767 last_conn_holder = NULL;
768 }
769 } else {
770 current_conn_holder->prev->next = current_conn_holder->next;
771 if (current_conn_holder->next)
772 {
773 current_conn_holder->next->prev = current_conn_holder->prev;
774 } else {
775 last_conn_holder = current_conn_holder->prev;
776 last_conn_holder->next = NULL;
777 }
778 }
779 conn_holder = current_conn_holder->next;
780 free_conn_holder(current_conn_holder);
781 current_conn_holder = conn_holder;
782 } else {
783 current_conn_holder = current_conn_holder->next;
784 }
785 }
786 DBUG_VOID_RETURN;
787}
788
789void spider_fields::choose_a_conn(
790) {
791 SPIDER_CONN_HOLDER *conn_holder;
792 longlong balance_total = 0, balance_val;
793 double rand_val;
794 THD *thd = table_holder[0].spider->trx->thd;
795 DBUG_ENTER("spider_fields::choose_a_conn");
796 DBUG_PRINT("info",("spider this=%p", this));
797 for (current_conn_holder = first_conn_holder; current_conn_holder;
798 current_conn_holder = current_conn_holder->next)
799 {
800 balance_total += current_conn_holder->access_balance;
801 }
802
803 rand_val = spider_rand(thd->variables.server_id + thd_get_thread_id(thd));
804 balance_val = (longlong) (rand_val * balance_total);
805
806 current_conn_holder = first_conn_holder;
807 while (current_conn_holder)
808 {
809 if (balance_val < current_conn_holder->access_balance)
810 break;
811 balance_val -= current_conn_holder->access_balance;
812
813 DBUG_PRINT("info",("spider remove connection %p",
814 current_conn_holder->conn));
815 first_conn_holder = current_conn_holder->next;
816 DBUG_ASSERT(current_conn_holder->next);
817 first_conn_holder->prev = NULL;
818 free_conn_holder(current_conn_holder);
819 current_conn_holder = first_conn_holder;
820 }
821
822 DBUG_PRINT("info",("spider choosed connection is %p",
823 current_conn_holder->conn));
824 last_conn_holder = current_conn_holder;
825 current_conn_holder = current_conn_holder->next;
826 last_conn_holder->next = NULL;
827
828 while (current_conn_holder)
829 {
830 DBUG_PRINT("info",("spider remove connection %p",
831 current_conn_holder->conn));
832 conn_holder = current_conn_holder->next;
833 free_conn_holder(current_conn_holder);
834 current_conn_holder = conn_holder;
835 }
836 DBUG_VOID_RETURN;
837}
838
839void spider_fields::free_conn_holder(
840 SPIDER_CONN_HOLDER *conn_holder_arg
841) {
842 uint roop_count;
843 DBUG_ENTER("spider_fields::free_conn_holder");
844 DBUG_PRINT("info",("spider this=%p", this));
845 for (roop_count = 0; roop_count < table_count; ++roop_count)
846 {
847 if (conn_holder_arg->table_link_idx_holder[roop_count].first_link_idx_holder)
848 {
849 SPIDER_LINK_IDX_HOLDER *first_link_idx_holder, *current_link_idx_holder;
850 first_link_idx_holder =
851 conn_holder_arg->table_link_idx_holder[roop_count].first_link_idx_holder;
852 while ((current_link_idx_holder = first_link_idx_holder))
853 {
854 first_link_idx_holder = current_link_idx_holder->next;
855 spider_free(spider_current_trx, current_link_idx_holder, MYF(0));
856 }
857 }
858 }
859 conn_holder_arg->conn->conn_holder_for_direct_join = NULL;
860 DBUG_PRINT("info",("spider free conn_holder=%p", conn_holder_arg));
861 spider_free(spider_current_trx, conn_holder_arg, MYF(0));
862 DBUG_VOID_RETURN;
863}
864
865SPIDER_TABLE_HOLDER *spider_fields::add_table(
866 ha_spider *spider_arg
867) {
868 spider_string *str;
869 uint length;
870 char tmp_buf[SPIDER_SQL_INT_LEN + 2];
871 SPIDER_TABLE_HOLDER *return_table_holder;
872 SPIDER_FIELD_HOLDER *field_holder;
873 TABLE *table = spider_arg->get_table();
874 Field *field;
875 DBUG_ENTER("spider_fields::add_table");
876 DBUG_PRINT("info",("spider this=%p", this));
877 DBUG_PRINT("info",("spider table_count=%u", table_count));
878 DBUG_PRINT("info",("spider idx_for_direct_join=%u",
879 spider_arg->idx_for_direct_join));
880 length = my_sprintf(tmp_buf, (tmp_buf, "t%u",
881 spider_arg->idx_for_direct_join));
882 str = &spider_arg->result_list.tmp_sqls[0];
883 str->length(0);
884 if (str->reserve(length + SPIDER_SQL_DOT_LEN))
885 {
886 DBUG_RETURN(NULL);
887 }
888 str->q_append(tmp_buf, length);
889 str->q_append(SPIDER_SQL_DOT_STR, SPIDER_SQL_DOT_LEN);
890
891 return_table_holder = &table_holder[spider_arg->idx_for_direct_join];
892 return_table_holder->table = spider_arg->get_table();
893 return_table_holder->spider = spider_arg;
894 return_table_holder->alias = str;
895
896 set_pos_to_first_field_holder();
897 while ((field_holder = get_next_field_holder()))
898 {
899 if (!field_holder->spider)
900 {
901 field = field_holder->field;
902 if (
903 field->field_index < table->s->fields &&
904 field == table->field[field->field_index]
905 ) {
906 field_holder->spider = spider_arg;
907 field_holder->alias = str;
908 }
909 }
910 }
911 DBUG_RETURN(return_table_holder);
912}
913
914int spider_fields::create_table_holder(
915 uint table_count_arg
916) {
917 DBUG_ENTER("spider_fields::create_table_holder");
918 DBUG_PRINT("info",("spider this=%p", this));
919 DBUG_ASSERT(!table_holder);
920 table_holder = (SPIDER_TABLE_HOLDER *)
921 spider_malloc(spider_current_trx, 249,
922 table_count_arg * sizeof(SPIDER_TABLE_HOLDER),
923 MYF(MY_WME | MY_ZEROFILL));
924 if (!table_holder)
925 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
926 table_count = table_count_arg;
927 current_table_num = 0;
928 DBUG_RETURN(0);
929}
930
931void spider_fields::set_pos_to_first_table_holder(
932) {
933 DBUG_ENTER("spider_fields::set_pos_to_first_table_holder");
934 DBUG_PRINT("info",("spider this=%p", this));
935 current_table_num = 0;
936 DBUG_VOID_RETURN;
937}
938
939SPIDER_TABLE_HOLDER *spider_fields::get_next_table_holder(
940) {
941 SPIDER_TABLE_HOLDER *return_table_holder;
942 DBUG_ENTER("spider_fields::get_next_table_holder");
943 DBUG_PRINT("info",("spider this=%p", this));
944 if (current_table_num >= table_count)
945 DBUG_RETURN(NULL);
946 return_table_holder = &table_holder[current_table_num];
947 ++current_table_num;
948 DBUG_RETURN(return_table_holder);
949}
950
951int spider_fields::add_field(
952 Field *field_arg
953) {
954 SPIDER_FIELD_HOLDER *field_holder;
955 SPIDER_FIELD_CHAIN *field_chain;
956 DBUG_ENTER("spider_fields::add_field");
957 DBUG_PRINT("info",("spider this=%p", this));
958 DBUG_PRINT("info",("spider field=%p", field_arg));
959 if (!first_field_holder)
960 {
961 field_holder = create_field_holder();
962 DBUG_PRINT("info",("spider field_holder=%p", field_holder));
963 if (!field_holder)
964 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
965 field_holder->field = field_arg;
966 first_field_holder = field_holder;
967 last_field_holder = field_holder;
968 } else {
969 field_holder = first_field_holder;
970 do {
971 if (field_holder->field == field_arg)
972 break;
973 } while ((field_holder = field_holder->next));
974 if (!field_holder)
975 {
976 field_holder = create_field_holder();
977 DBUG_PRINT("info",("spider field_holder=%p", field_holder));
978 if (!field_holder)
979 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
980 field_holder->field = field_arg;
981 last_field_holder->next = field_holder;
982 last_field_holder = field_holder;
983 }
984 }
985 field_chain = create_field_chain();
986 DBUG_PRINT("info",("spider field_chain=%p", field_chain));
987 if (!field_chain)
988 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
989 field_chain->field_holder = field_holder;
990 if (!first_field_chain)
991 {
992 first_field_chain = field_chain;
993 last_field_chain = field_chain;
994 } else {
995 last_field_chain->next = field_chain;
996 last_field_chain = field_chain;
997 }
998 DBUG_RETURN(0);
999}
1000
1001SPIDER_FIELD_HOLDER *spider_fields::create_field_holder(
1002) {
1003 DBUG_ENTER("spider_fields::create_field_holder");
1004 DBUG_PRINT("info",("spider this=%p", this));
1005 DBUG_RETURN((SPIDER_FIELD_HOLDER *)
1006 spider_malloc(spider_current_trx, 250, sizeof(SPIDER_FIELD_HOLDER),
1007 MYF(MY_WME | MY_ZEROFILL)));
1008}
1009
1010void spider_fields::set_pos_to_first_field_holder(
1011) {
1012 DBUG_ENTER("spider_fields::set_pos_to_first_field_holder");
1013 DBUG_PRINT("info",("spider this=%p", this));
1014 current_field_holder = first_field_holder;
1015 DBUG_VOID_RETURN;
1016}
1017
1018SPIDER_FIELD_HOLDER *spider_fields::get_next_field_holder(
1019) {
1020 SPIDER_FIELD_HOLDER *return_field_holder = current_field_holder;
1021 DBUG_ENTER("spider_fields::get_next_field_holder");
1022 DBUG_PRINT("info",("spider this=%p", this));
1023 if (current_field_holder)
1024 current_field_holder = current_field_holder->next;
1025 DBUG_RETURN(return_field_holder);
1026}
1027
1028SPIDER_FIELD_CHAIN *spider_fields::create_field_chain(
1029) {
1030 DBUG_ENTER("spider_fields::create_field_chain");
1031 DBUG_PRINT("info",("spider this=%p", this));
1032 DBUG_RETURN((SPIDER_FIELD_CHAIN *)
1033 spider_malloc(spider_current_trx, 251, sizeof(SPIDER_FIELD_CHAIN),
1034 MYF(MY_WME | MY_ZEROFILL)));
1035}
1036
1037void spider_fields::set_pos_to_first_field_chain(
1038) {
1039 DBUG_ENTER("spider_fields::set_pos_to_first_field_chain");
1040 DBUG_PRINT("info",("spider this=%p", this));
1041 current_field_chain = first_field_chain;
1042 DBUG_VOID_RETURN;
1043}
1044
1045SPIDER_FIELD_CHAIN *spider_fields::get_next_field_chain(
1046) {
1047 SPIDER_FIELD_CHAIN *return_field_chain = current_field_chain;
1048 DBUG_ENTER("spider_fields::get_next_field_chain");
1049 DBUG_PRINT("info",("spider this=%p", this));
1050 if (current_field_chain)
1051 current_field_chain = current_field_chain->next;
1052 DBUG_RETURN(return_field_chain);
1053}
1054
1055void spider_fields::set_field_ptr(
1056 Field **field_arg
1057) {
1058 DBUG_ENTER("spider_fields::set_field_ptr");
1059 DBUG_PRINT("info",("spider this=%p", this));
1060 DBUG_PRINT("info",("spider field_ptr=%p", field_arg));
1061 first_field_ptr = field_arg;
1062 current_field_ptr = field_arg;
1063 DBUG_VOID_RETURN;
1064}
1065
1066Field **spider_fields::get_next_field_ptr(
1067) {
1068 Field **return_field_ptr = current_field_ptr;
1069 DBUG_ENTER("spider_fields::get_next_field_ptr");
1070 DBUG_PRINT("info",("spider this=%p", this));
1071 if (*current_field_ptr)
1072 current_field_ptr++;
1073 DBUG_PRINT("info",("spider field_ptr=%p", return_field_ptr));
1074 DBUG_RETURN(return_field_ptr);
1075}
1076
1077int spider_fields::ping_table_mon_from_table(
1078 SPIDER_LINK_IDX_CHAIN *link_idx_chain
1079) {
1080 int error_num = 0, error_num_buf;
1081 ha_spider *tmp_spider;
1082 SPIDER_SHARE *tmp_share;
1083 int tmp_link_idx;
1084 SPIDER_TABLE_HOLDER *table_holder;
1085 SPIDER_LINK_IDX_HOLDER *link_idx_holder;
1086 DBUG_ENTER("spider_fields::ping_table_mon_from_table");
1087 set_pos_to_first_table_on_link_idx_chain(link_idx_chain);
1088 set_pos_to_first_table_holder();
1089 while ((table_holder = get_next_table_holder()))
1090 {
1091 link_idx_holder = get_next_table_on_link_idx_chain(link_idx_chain);
1092 tmp_spider = table_holder->spider;
1093 tmp_link_idx = link_idx_holder->link_idx;
1094 tmp_share = tmp_spider->share;
1095 if (tmp_share->monitoring_kind[tmp_link_idx])
1096 {
1097 error_num_buf = spider_ping_table_mon_from_table(
1098 tmp_spider->trx,
1099 tmp_spider->trx->thd,
1100 tmp_share,
1101 tmp_link_idx,
1102 (uint32) tmp_share->monitoring_sid[tmp_link_idx],
1103 tmp_share->table_name,
1104 tmp_share->table_name_length,
1105 tmp_spider->conn_link_idx[tmp_link_idx],
1106 NULL,
1107 0,
1108 tmp_share->monitoring_kind[tmp_link_idx],
1109 tmp_share->monitoring_limit[tmp_link_idx],
1110 tmp_share->monitoring_flag[tmp_link_idx],
1111 TRUE
1112 );
1113 if (!error_num)
1114 error_num = error_num_buf;
1115 }
1116 }
1117 DBUG_RETURN(error_num);
1118}
1119
1120#ifdef SPIDER_HAS_GROUP_BY_HANDLER
1121spider_group_by_handler::spider_group_by_handler(
1122 THD *thd_arg,
1123 Query *query_arg,
1124 spider_fields *fields_arg
1125) : group_by_handler(thd_arg, spider_hton_ptr),
1126 query(*query_arg), fields(fields_arg)
1127{
1128 DBUG_ENTER("spider_group_by_handler::spider_group_by_handler");
1129 fields->set_pos_to_first_table_holder();
1130 SPIDER_TABLE_HOLDER *table_holder = fields->get_next_table_holder();
1131 spider = table_holder->spider;
1132 trx = spider->trx;
1133 DBUG_VOID_RETURN;
1134}
1135
1136spider_group_by_handler::~spider_group_by_handler()
1137{
1138 DBUG_ENTER("spider_group_by_handler::~spider_group_by_handler");
1139 delete fields;
1140 DBUG_VOID_RETURN;
1141}
1142
1143int spider_group_by_handler::init_scan()
1144{
1145 int error_num, link_idx;
1146 uint dbton_id;
1147 spider_db_handler *dbton_hdl;
1148 st_select_lex *select_lex;
1149 longlong select_limit;
1150 longlong direct_order_limit;
1151 SPIDER_SHARE *share = spider->share;
1152 SPIDER_CONN *conn;
1153 SPIDER_RESULT_LIST *result_list = &spider->result_list;
1154 SPIDER_LINK_IDX_CHAIN *link_idx_chain;
1155 SPIDER_LINK_IDX_HOLDER *link_idx_holder;
1156 DBUG_ENTER("spider_group_by_handler::init_scan");
1157 store_error = 0;
1158#ifndef DBUG_OFF
1159 Field **field;
1160 for (
1161 field = table->field;
1162 *field;
1163 field++
1164 ) {
1165 DBUG_PRINT("info",("spider field_name=%s", (*field)->field_name.str));
1166 }
1167#endif
1168
1169 if (trx->thd->killed)
1170 {
1171 my_error(ER_QUERY_INTERRUPTED, MYF(0));
1172 DBUG_RETURN(ER_QUERY_INTERRUPTED);
1173 }
1174
1175 spider->use_fields = TRUE;
1176 spider->fields = fields;
1177
1178 spider->check_pre_call(TRUE);
1179
1180 spider->pushed_pos = NULL;
1181 result_list->sorted = (query.group_by || query.order_by);
1182 spider_set_result_list_param(spider);
1183 spider->mrr_with_cnt = FALSE;
1184 spider->init_index_handler = FALSE;
1185 spider->use_spatial_index = FALSE;
1186 result_list->check_direct_order_limit = FALSE;
1187 spider->select_column_mode = 0;
1188 spider->search_link_idx = fields->get_ok_link_idx();
1189 spider->result_link_idx = spider->search_link_idx;
1190
1191 spider_db_free_one_result_for_start_next(spider);
1192
1193 spider->sql_kinds = SPIDER_SQL_KIND_SQL;
1194 for (link_idx = 0; link_idx < (int) share->link_count; ++link_idx)
1195 spider->sql_kind[link_idx] = SPIDER_SQL_KIND_SQL;
1196
1197#ifdef HANDLER_HAS_DIRECT_UPDATE_ROWS
1198 spider->do_direct_update = FALSE;
1199 spider->direct_update_kinds = 0;
1200#endif
1201 spider_get_select_limit(spider, &select_lex, &select_limit, &offset_limit);
1202 direct_order_limit = spider_param_direct_order_limit(thd,
1203 share->direct_order_limit);
1204 if (
1205 direct_order_limit &&
1206 select_lex->explicit_limit &&
1207 !(select_lex->options & OPTION_FOUND_ROWS) &&
1208 select_limit < direct_order_limit /* - offset_limit */
1209 ) {
1210 result_list->internal_limit = select_limit /* + offset_limit */;
1211 result_list->split_read = select_limit /* + offset_limit */;
1212#ifndef WITHOUT_SPIDER_BG_SEARCH
1213 result_list->bgs_split_read = select_limit /* + offset_limit */;
1214#endif
1215
1216 result_list->split_read_base = 9223372036854775807LL;
1217 result_list->semi_split_read = 0;
1218 result_list->semi_split_read_limit = 9223372036854775807LL;
1219 result_list->first_read = 9223372036854775807LL;
1220 result_list->second_read = 9223372036854775807LL;
1221 trx->direct_order_limit_count++;
1222 }
1223 result_list->semi_split_read_base = 0;
1224 result_list->set_split_read = TRUE;
1225#ifndef WITHOUT_SPIDER_BG_SEARCH
1226 if ((error_num = spider_set_conn_bg_param(spider)))
1227 DBUG_RETURN(error_num);
1228#endif
1229 DBUG_PRINT("info",("spider result_list.finish_flg = FALSE"));
1230 result_list->finish_flg = FALSE;
1231 result_list->record_num = 0;
1232 result_list->keyread = FALSE;
1233 result_list->desc_flg = FALSE;
1234 result_list->sorted = FALSE;
1235 result_list->key_info = NULL;
1236 result_list->key_order = 0;
1237 result_list->limit_num =
1238 result_list->internal_limit >= result_list->split_read ?
1239 result_list->split_read : result_list->internal_limit;
1240
1241 if (select_lex->explicit_limit)
1242 {
1243 result_list->internal_offset += offset_limit;
1244 } else {
1245 offset_limit = 0;
1246 }
1247
1248 /* making a query */
1249 fields->set_pos_to_first_dbton_id();
1250 while ((dbton_id = fields->get_next_dbton_id()) < SPIDER_DBTON_SIZE)
1251 {
1252 dbton_hdl = spider->dbton_handler[dbton_id];
1253 result_list->direct_distinct = query.distinct;
1254 fields->set_pos_to_first_field_chain();
1255 if ((error_num = dbton_hdl->reset_sql(SPIDER_SQL_TYPE_SELECT_SQL)))
1256 {
1257 DBUG_RETURN(error_num);
1258 }
1259 if ((error_num = dbton_hdl->append_select_part(SPIDER_SQL_TYPE_SELECT_SQL)))
1260 {
1261 DBUG_RETURN(error_num);
1262 }
1263 fields->set_field_ptr(table->field);
1264 if ((error_num = dbton_hdl->append_list_item_select_part(
1265 query.select, NULL, 0, TRUE, fields, SPIDER_SQL_TYPE_SELECT_SQL)))
1266 {
1267 DBUG_RETURN(error_num);
1268 }
1269 if ((error_num = dbton_hdl->append_from_and_tables_part(
1270 fields, SPIDER_SQL_TYPE_SELECT_SQL)))
1271 {
1272 DBUG_RETURN(error_num);
1273 }
1274 if (query.where)
1275 {
1276 if ((error_num =
1277 dbton_hdl->append_where_part(SPIDER_SQL_TYPE_SELECT_SQL)))
1278 {
1279 DBUG_RETURN(error_num);
1280 }
1281 if ((error_num = dbton_hdl->append_item_type_part(
1282 query.where, NULL, 0, TRUE, fields, SPIDER_SQL_TYPE_SELECT_SQL)))
1283 {
1284 DBUG_RETURN(error_num);
1285 }
1286 }
1287 if (query.group_by)
1288 {
1289 if ((error_num = dbton_hdl->append_group_by_part(
1290 query.group_by, NULL, 0, TRUE, fields, SPIDER_SQL_TYPE_SELECT_SQL)))
1291 {
1292 DBUG_RETURN(error_num);
1293 }
1294 }
1295 if (query.having)
1296 {
1297 if ((error_num =
1298 dbton_hdl->append_having_part(SPIDER_SQL_TYPE_SELECT_SQL)))
1299 {
1300 DBUG_RETURN(error_num);
1301 }
1302 if ((error_num = dbton_hdl->append_item_type_part(
1303 query.having, NULL, 0, TRUE, fields, SPIDER_SQL_TYPE_SELECT_SQL)))
1304 {
1305 DBUG_RETURN(error_num);
1306 }
1307 }
1308 if (query.order_by)
1309 {
1310 if ((error_num = dbton_hdl->append_order_by_part(
1311 query.order_by, NULL, 0, TRUE, fields, SPIDER_SQL_TYPE_SELECT_SQL)))
1312 {
1313 DBUG_RETURN(error_num);
1314 }
1315 }
1316 if ((error_num = dbton_hdl->append_limit_part(result_list->internal_offset,
1317 result_list->limit_num, SPIDER_SQL_TYPE_SELECT_SQL)))
1318 {
1319 DBUG_RETURN(error_num);
1320 }
1321 if ((error_num = dbton_hdl->append_select_lock_part(
1322 SPIDER_SQL_TYPE_SELECT_SQL)))
1323 {
1324 DBUG_RETURN(error_num);
1325 }
1326 }
1327
1328 fields->set_pos_to_first_link_idx_chain();
1329 while ((link_idx_chain = fields->get_next_link_idx_chain()))
1330 {
1331 conn = link_idx_chain->conn;
1332 link_idx_holder = link_idx_chain->link_idx_holder;
1333 link_idx = link_idx_holder->link_idx;
1334 dbton_hdl = spider->dbton_handler[conn->dbton_id];
1335 spider->link_idx_chain = link_idx_chain;
1336#ifndef WITHOUT_SPIDER_BG_SEARCH
1337 if (result_list->bgs_phase > 0)
1338 {
1339 if ((error_num = spider_check_and_init_casual_read(trx->thd, spider,
1340 link_idx)))
1341 DBUG_RETURN(error_num);
1342 if ((error_num = spider_bg_conn_search(spider, link_idx,
1343 dbton_hdl->first_link_idx, TRUE, FALSE,
1344 !fields->is_first_link_ok_chain(link_idx_chain))))
1345 {
1346 if (
1347 error_num != HA_ERR_END_OF_FILE &&
1348 spider->need_mons[link_idx]
1349 ) {
1350 error_num = fields->ping_table_mon_from_table(link_idx_chain);
1351 }
1352 if ((error_num = spider->check_error_mode_eof(error_num)) == HA_ERR_END_OF_FILE)
1353 {
1354 store_error = HA_ERR_END_OF_FILE;
1355 error_num = 0;
1356 }
1357 DBUG_RETURN(error_num);
1358 }
1359 } else {
1360#endif
1361 if (dbton_hdl->need_lock_before_set_sql_for_exec(
1362 SPIDER_SQL_TYPE_SELECT_SQL))
1363 {
1364 pthread_mutex_lock(&conn->mta_conn_mutex);
1365 SPIDER_SET_FILE_POS(&conn->mta_conn_mutex_file_pos);
1366 }
1367 if ((error_num =
1368 dbton_hdl->set_sql_for_exec(SPIDER_SQL_TYPE_SELECT_SQL, link_idx,
1369 link_idx_chain)))
1370 {
1371 DBUG_RETURN(error_num);
1372 }
1373 if (!dbton_hdl->need_lock_before_set_sql_for_exec(
1374 SPIDER_SQL_TYPE_SELECT_SQL))
1375 {
1376 pthread_mutex_lock(&conn->mta_conn_mutex);
1377 SPIDER_SET_FILE_POS(&conn->mta_conn_mutex_file_pos);
1378 }
1379 conn->need_mon = &spider->need_mons[link_idx];
1380 conn->mta_conn_mutex_lock_already = TRUE;
1381 conn->mta_conn_mutex_unlock_later = TRUE;
1382 if ((error_num = spider_db_set_names(spider, conn,
1383 link_idx)))
1384 {
1385 conn->mta_conn_mutex_lock_already = FALSE;
1386 conn->mta_conn_mutex_unlock_later = FALSE;
1387 SPIDER_CLEAR_FILE_POS(&conn->mta_conn_mutex_file_pos);
1388 pthread_mutex_unlock(&conn->mta_conn_mutex);
1389 if (
1390 spider->need_mons[link_idx]
1391 ) {
1392 error_num = fields->ping_table_mon_from_table(link_idx_chain);
1393 }
1394 if ((error_num = spider->check_error_mode_eof(error_num)) == HA_ERR_END_OF_FILE)
1395 {
1396 store_error = HA_ERR_END_OF_FILE;
1397 error_num = 0;
1398 }
1399 DBUG_RETURN(error_num);
1400 }
1401 spider_conn_set_timeout_from_share(conn, link_idx,
1402 trx->thd, share);
1403 if (dbton_hdl->execute_sql(
1404 SPIDER_SQL_TYPE_SELECT_SQL,
1405 conn,
1406 spider->result_list.quick_mode,
1407 &spider->need_mons[link_idx])
1408 ) {
1409 conn->mta_conn_mutex_lock_already = FALSE;
1410 conn->mta_conn_mutex_unlock_later = FALSE;
1411 error_num = spider_db_errorno(conn);
1412 if (
1413 spider->need_mons[link_idx]
1414 ) {
1415 error_num = fields->ping_table_mon_from_table(link_idx_chain);
1416 }
1417 if ((error_num = spider->check_error_mode_eof(error_num)) == HA_ERR_END_OF_FILE)
1418 {
1419 store_error = HA_ERR_END_OF_FILE;
1420 error_num = 0;
1421 }
1422 DBUG_RETURN(error_num);
1423 }
1424 spider->connection_ids[link_idx] = conn->connection_id;
1425 conn->mta_conn_mutex_lock_already = FALSE;
1426 conn->mta_conn_mutex_unlock_later = FALSE;
1427 if (fields->is_first_link_ok_chain(link_idx_chain))
1428 {
1429 if ((error_num = spider_db_store_result(spider, link_idx, table)))
1430 {
1431 if (
1432 error_num != HA_ERR_END_OF_FILE &&
1433 spider->need_mons[link_idx]
1434 ) {
1435 error_num = fields->ping_table_mon_from_table(link_idx_chain);
1436 }
1437 if ((error_num = spider->check_error_mode_eof(error_num)) == HA_ERR_END_OF_FILE)
1438 {
1439 store_error = HA_ERR_END_OF_FILE;
1440 error_num = 0;
1441 }
1442 DBUG_RETURN(error_num);
1443 }
1444 spider->result_link_idx = link_idx;
1445 spider->result_link_idx_chain = link_idx_chain;
1446 } else {
1447 spider_db_discard_result(spider, link_idx, conn);
1448 SPIDER_CLEAR_FILE_POS(&conn->mta_conn_mutex_file_pos);
1449 pthread_mutex_unlock(&conn->mta_conn_mutex);
1450 }
1451#ifndef WITHOUT_SPIDER_BG_SEARCH
1452 }
1453#endif
1454 }
1455
1456 first = TRUE;
1457 DBUG_RETURN(0);
1458}
1459
1460int spider_group_by_handler::next_row()
1461{
1462 int error_num, link_idx;
1463 spider_db_handler *dbton_hdl;
1464 SPIDER_CONN *conn;
1465 SPIDER_LINK_IDX_CHAIN *link_idx_chain;
1466 SPIDER_LINK_IDX_HOLDER *link_idx_holder;
1467 DBUG_ENTER("spider_group_by_handler::next_row");
1468 if (trx->thd->killed)
1469 {
1470 my_error(ER_QUERY_INTERRUPTED, MYF(0));
1471 DBUG_RETURN(ER_QUERY_INTERRUPTED);
1472 }
1473 if (store_error)
1474 {
1475 if (store_error == HA_ERR_END_OF_FILE)
1476 {
1477 table->status = STATUS_NOT_FOUND;
1478 }
1479 DBUG_RETURN(store_error);
1480 }
1481 if (first)
1482 {
1483 first = FALSE;
1484 if (spider->use_pre_call)
1485 {
1486 if (spider->store_error_num)
1487 {
1488 if (spider->store_error_num == HA_ERR_END_OF_FILE)
1489 table->status = STATUS_NOT_FOUND;
1490 DBUG_RETURN(spider->store_error_num);
1491 }
1492#ifndef WITHOUT_SPIDER_BG_SEARCH
1493 if (spider->result_list.bgs_phase > 0)
1494 {
1495 fields->set_pos_to_first_link_idx_chain();
1496 while ((link_idx_chain = fields->get_next_link_idx_chain()))
1497 {
1498 conn = link_idx_chain->conn;
1499 link_idx_holder = link_idx_chain->link_idx_holder;
1500 link_idx = link_idx_holder->link_idx;
1501 dbton_hdl = spider->dbton_handler[conn->dbton_id];
1502 spider->link_idx_chain = link_idx_chain;
1503 if ((error_num = spider_bg_conn_search(spider, link_idx,
1504 dbton_hdl->first_link_idx, TRUE, TRUE,
1505 !fields->is_first_link_ok_chain(link_idx_chain))))
1506 {
1507 if (
1508 error_num != HA_ERR_END_OF_FILE &&
1509 spider->need_mons[link_idx]
1510 ) {
1511 error_num = fields->ping_table_mon_from_table(link_idx_chain);
1512 }
1513 if ((error_num = spider->check_error_mode_eof(error_num)) == HA_ERR_END_OF_FILE)
1514 {
1515 table->status = STATUS_NOT_FOUND;
1516 }
1517 DBUG_RETURN(error_num);
1518 }
1519 }
1520 }
1521#endif
1522 spider->use_pre_call = FALSE;
1523 }
1524 } else if (offset_limit)
1525 {
1526 --offset_limit;
1527 DBUG_RETURN(0);
1528 }
1529 if ((error_num = spider_db_seek_next(table->record[0], spider,
1530 spider->search_link_idx, table)))
1531 {
1532 if ((error_num = spider->check_error_mode_eof(error_num)) == HA_ERR_END_OF_FILE)
1533 {
1534 table->status = STATUS_NOT_FOUND;
1535 }
1536 DBUG_RETURN(error_num);
1537 }
1538 DBUG_RETURN(0);
1539}
1540
1541int spider_group_by_handler::end_scan()
1542{
1543 DBUG_ENTER("spider_group_by_handler::end_scan");
1544 DBUG_RETURN(0);
1545}
1546
1547group_by_handler *spider_create_group_by_handler(
1548 THD *thd,
1549 Query *query
1550) {
1551 spider_group_by_handler *group_by_handler;
1552 Item *item;
1553 TABLE_LIST *from;
1554 SPIDER_CONN *conn;
1555 ha_spider *spider;
1556 SPIDER_SHARE *share;
1557 int roop_count, lock_mode;
1558 List_iterator_fast<Item> it(*query->select);
1559 uchar dbton_bitmap[spider_bitmap_size(SPIDER_DBTON_SIZE)];
1560 uchar dbton_bitmap_tmp[spider_bitmap_size(SPIDER_DBTON_SIZE)];
1561 ORDER *order;
1562 bool keep_going;
1563 bool find_dbton = FALSE;
1564 spider_fields *fields = NULL, *fields_arg = NULL;
1565 uint table_idx, dbton_id;
1566 long tgt_link_status;
1567 DBUG_ENTER("spider_create_group_by_handler");
1568
1569 switch (thd_sql_command(thd))
1570 {
1571 case SQLCOM_UPDATE:
1572 case SQLCOM_UPDATE_MULTI:
1573 case SQLCOM_DELETE:
1574 case SQLCOM_DELETE_MULTI:
1575 DBUG_PRINT("info",("spider update and delete does not support this feature"));
1576 DBUG_RETURN(NULL);
1577 default:
1578 break;
1579 }
1580
1581#ifdef WITH_PARTITION_STORAGE_ENGINE
1582 from = query->from;
1583 do {
1584 DBUG_PRINT("info",("spider from=%p", from));
1585 if (from->table->const_table)
1586 continue;
1587 if (from->table->part_info)
1588 {
1589 DBUG_PRINT("info",("spider partition handler"));
1590#if defined(PARTITION_HAS_GET_CHILD_HANDLERS) && defined(PARTITION_HAS_GET_PART_SPEC)
1591 ha_partition *partition = (ha_partition *) from->table->file;
1592 part_id_range *part_spec = partition->get_part_spec();
1593 DBUG_PRINT("info",("spider part_spec->start_part=%u", part_spec->start_part));
1594 DBUG_PRINT("info",("spider part_spec->end_part=%u", part_spec->end_part));
1595 if (
1596 part_spec->start_part == partition->get_no_current_part_id() ||
1597 part_spec->start_part != part_spec->end_part
1598 ) {
1599 DBUG_PRINT("info",("spider using multiple partitions is not supported by this feature yet"));
1600#else
1601 DBUG_PRINT("info",("spider partition is not supported by this feature yet"));
1602#endif
1603 DBUG_RETURN(NULL);
1604#if defined(PARTITION_HAS_GET_CHILD_HANDLERS) && defined(PARTITION_HAS_GET_PART_SPEC)
1605 }
1606#endif
1607 }
1608 } while ((from = from->next_local));
1609#endif
1610
1611 table_idx = 0;
1612 from = query->from;
1613 while (from && from->table->const_table)
1614 {
1615 from = from->next_local;
1616 }
1617 if (!from)
1618 {
1619 /* all tables are const_table */
1620 DBUG_RETURN(NULL);
1621 }
1622#if defined(PARTITION_HAS_GET_CHILD_HANDLERS) && defined(PARTITION_HAS_GET_PART_SPEC)
1623 if (from->table->part_info)
1624 {
1625 ha_partition *partition = (ha_partition *) from->table->file;
1626 part_id_range *part_spec = partition->get_part_spec();
1627 handler **handlers = partition->get_child_handlers();
1628 spider = (ha_spider *) handlers[part_spec->start_part];
1629 } else {
1630#endif
1631 spider = (ha_spider *) from->table->file;
1632#if defined(PARTITION_HAS_GET_CHILD_HANDLERS) && defined(PARTITION_HAS_GET_PART_SPEC)
1633 }
1634#endif
1635 share = spider->share;
1636 spider->idx_for_direct_join = table_idx;
1637 ++table_idx;
1638 memset(dbton_bitmap, 0, spider_bitmap_size(SPIDER_DBTON_SIZE));
1639 for (roop_count = 0; roop_count < (int) share->use_dbton_count; ++roop_count)
1640 {
1641 dbton_id = share->use_sql_dbton_ids[roop_count];
1642 if (
1643 spider_dbton[dbton_id].support_direct_join &&
1644 spider_dbton[dbton_id].support_direct_join()
1645 ) {
1646 spider_set_bit(dbton_bitmap, dbton_id);
1647 }
1648 }
1649 while ((from = from->next_local))
1650 {
1651 if (from->table->const_table)
1652 continue;
1653#if defined(PARTITION_HAS_GET_CHILD_HANDLERS) && defined(PARTITION_HAS_GET_PART_SPEC)
1654 if (from->table->part_info)
1655 {
1656 ha_partition *partition = (ha_partition *) from->table->file;
1657 part_id_range *part_spec = partition->get_part_spec();
1658 handler **handlers = partition->get_child_handlers();
1659 spider = (ha_spider *) handlers[part_spec->start_part];
1660 } else {
1661#endif
1662 spider = (ha_spider *) from->table->file;
1663#if defined(PARTITION_HAS_GET_CHILD_HANDLERS) && defined(PARTITION_HAS_GET_PART_SPEC)
1664 }
1665#endif
1666 share = spider->share;
1667 spider->idx_for_direct_join = table_idx;
1668 ++table_idx;
1669 memset(dbton_bitmap_tmp, 0, spider_bitmap_size(SPIDER_DBTON_SIZE));
1670 for (roop_count = 0; roop_count < (int) share->use_dbton_count; ++roop_count)
1671 {
1672 dbton_id = share->use_sql_dbton_ids[roop_count];
1673 if (
1674 spider_dbton[dbton_id].support_direct_join &&
1675 spider_dbton[dbton_id].support_direct_join()
1676 ) {
1677 spider_set_bit(dbton_bitmap_tmp, dbton_id);
1678 }
1679 }
1680 for (roop_count = 0;
1681 roop_count < spider_bitmap_size(SPIDER_DBTON_SIZE); ++roop_count)
1682 {
1683 dbton_bitmap[roop_count] &= dbton_bitmap_tmp[roop_count];
1684 }
1685 }
1686
1687 from = query->from;
1688 do {
1689 if (from->table->const_table)
1690 continue;
1691#if defined(PARTITION_HAS_GET_CHILD_HANDLERS) && defined(PARTITION_HAS_GET_PART_SPEC)
1692 if (from->table->part_info)
1693 {
1694 ha_partition *partition = (ha_partition *) from->table->file;
1695 part_id_range *part_spec = partition->get_part_spec();
1696 handler **handlers = partition->get_child_handlers();
1697 spider = (ha_spider *) handlers[part_spec->start_part];
1698 } else {
1699#endif
1700 spider = (ha_spider *) from->table->file;
1701#if defined(PARTITION_HAS_GET_CHILD_HANDLERS) && defined(PARTITION_HAS_GET_PART_SPEC)
1702 }
1703#endif
1704 share = spider->share;
1705 if (spider_param_skip_default_condition(thd,
1706 share->skip_default_condition))
1707 {
1708 /* find skip_default_condition = 1 */
1709 break;
1710 }
1711 } while ((from = from->next_local));
1712
1713 for (roop_count = 0; roop_count < SPIDER_DBTON_SIZE; ++roop_count)
1714 {
1715 if (spider_bit_is_set(dbton_bitmap, roop_count))
1716 {
1717 if (!fields)
1718 {
1719 fields_arg = new spider_fields();
1720 if (!fields_arg)
1721 {
1722 DBUG_RETURN(NULL);
1723 }
1724 }
1725 keep_going = TRUE;
1726 it.init(*query->select);
1727 while ((item = it++))
1728 {
1729 DBUG_PRINT("info",("spider select item=%p", item));
1730 if (spider_db_print_item_type(item, spider, NULL, NULL, 0,
1731 roop_count, TRUE, fields_arg))
1732 {
1733 DBUG_PRINT("info",("spider dbton_id=%d can't create select", roop_count));
1734 spider_clear_bit(dbton_bitmap, roop_count);
1735 keep_going = FALSE;
1736 break;
1737 }
1738 }
1739 if (keep_going)
1740 {
1741 DBUG_PRINT("info",("spider query->where=%p", query->where));
1742 if (query->where)
1743 {
1744 if (spider_db_print_item_type(query->where, spider, NULL, NULL, 0,
1745 roop_count, TRUE, fields_arg))
1746 {
1747 DBUG_PRINT("info",("spider dbton_id=%d can't create where", roop_count));
1748 spider_clear_bit(dbton_bitmap, roop_count);
1749 keep_going = FALSE;
1750 }
1751 }
1752 }
1753 if (keep_going)
1754 {
1755 DBUG_PRINT("info",("spider query->group_by=%p", query->group_by));
1756 if (query->group_by)
1757 {
1758 for (order = query->group_by; order; order = order->next)
1759 {
1760 if (spider_db_print_item_type((*order->item), spider, NULL, NULL, 0,
1761 roop_count, TRUE, fields_arg))
1762 {
1763 DBUG_PRINT("info",("spider dbton_id=%d can't create group by", roop_count));
1764 spider_clear_bit(dbton_bitmap, roop_count);
1765 keep_going = FALSE;
1766 break;
1767 }
1768 }
1769 }
1770 }
1771 if (keep_going)
1772 {
1773 DBUG_PRINT("info",("spider query->order_by=%p", query->order_by));
1774 if (query->order_by)
1775 {
1776 for (order = query->order_by; order; order = order->next)
1777 {
1778 if (spider_db_print_item_type((*order->item), spider, NULL, NULL, 0,
1779 roop_count, TRUE, fields_arg))
1780 {
1781 DBUG_PRINT("info",("spider dbton_id=%d can't create order by", roop_count));
1782 spider_clear_bit(dbton_bitmap, roop_count);
1783 keep_going = FALSE;
1784 break;
1785 }
1786 }
1787 }
1788 }
1789 if (keep_going)
1790 {
1791 DBUG_PRINT("info",("spider query->having=%p", query->having));
1792 if (query->having)
1793 {
1794 if (spider_db_print_item_type(query->having, spider, NULL, NULL, 0,
1795 roop_count, TRUE, fields_arg))
1796 {
1797 DBUG_PRINT("info",("spider dbton_id=%d can't create having", roop_count));
1798 spider_clear_bit(dbton_bitmap, roop_count);
1799 keep_going = FALSE;
1800 }
1801 }
1802 }
1803 if (keep_going)
1804 {
1805 find_dbton = TRUE;
1806 fields = fields_arg;
1807 fields_arg = NULL;
1808 } else {
1809 delete fields_arg;
1810 }
1811 }
1812 }
1813 if (!find_dbton)
1814 {
1815 DBUG_RETURN(NULL);
1816 }
1817
1818 if (fields->create_table_holder(table_idx))
1819 {
1820 delete fields;
1821 DBUG_RETURN(NULL);
1822 }
1823
1824 from = query->from;
1825 while (from->table->const_table)
1826 {
1827 from = from->next_local;
1828 }
1829#if defined(PARTITION_HAS_GET_CHILD_HANDLERS) && defined(PARTITION_HAS_GET_PART_SPEC)
1830 if (from->table->part_info)
1831 {
1832 ha_partition *partition = (ha_partition *) from->table->file;
1833 part_id_range *part_spec = partition->get_part_spec();
1834 handler **handlers = partition->get_child_handlers();
1835 spider = (ha_spider *) handlers[part_spec->start_part];
1836 } else {
1837#endif
1838 spider = (ha_spider *) from->table->file;
1839#if defined(PARTITION_HAS_GET_CHILD_HANDLERS) && defined(PARTITION_HAS_GET_PART_SPEC)
1840 }
1841#endif
1842 share = spider->share;
1843 lock_mode = spider_conn_lock_mode(spider);
1844 if (lock_mode)
1845 {
1846 tgt_link_status = SPIDER_LINK_STATUS_RECOVERY;
1847 } else {
1848 tgt_link_status = SPIDER_LINK_STATUS_OK;
1849 }
1850 DBUG_PRINT("info",("spider s->db=%s", from->table->s->db.str));
1851 DBUG_PRINT("info",("spider s->table_name=%s", from->table->s->table_name.str));
1852 if (!fields->add_table(spider))
1853 {
1854 DBUG_PRINT("info",("spider can not add a table"));
1855 delete fields;
1856 DBUG_RETURN(NULL);
1857 }
1858 for (
1859 roop_count = spider_conn_link_idx_next(share->link_statuses,
1860 spider->conn_link_idx, -1, share->link_count,
1861 tgt_link_status);
1862 roop_count < (int) share->link_count;
1863 roop_count = spider_conn_link_idx_next(share->link_statuses,
1864 spider->conn_link_idx, roop_count, share->link_count,
1865 tgt_link_status)
1866 ) {
1867 if (spider_param_use_handler(thd, share->use_handlers[roop_count]))
1868 {
1869 DBUG_PRINT("info",("spider direct_join does not support use_handler"));
1870 if (lock_mode)
1871 {
1872 delete fields;
1873 DBUG_RETURN(NULL);
1874 }
1875 continue;
1876 }
1877 conn = spider->conns[roop_count];
1878 DBUG_PRINT("info",("spider roop_count=%d", roop_count));
1879 DBUG_PRINT("info",("spider conn=%p", conn));
1880 DBUG_ASSERT(conn);
1881 if (conn->table_lock)
1882 {
1883 DBUG_PRINT("info",("spider direct_join does not support with lock tables yet"));
1884 if (lock_mode)
1885 {
1886 delete fields;
1887 DBUG_RETURN(NULL);
1888 }
1889 continue;
1890 }
1891 if (!fields->add_conn(conn,
1892 share->access_balances[spider->conn_link_idx[roop_count]]))
1893 {
1894 DBUG_PRINT("info",("spider can not create conn_holder"));
1895 delete fields;
1896 DBUG_RETURN(NULL);
1897 }
1898 if (fields->add_link_idx(conn->conn_holder_for_direct_join, spider, roop_count))
1899 {
1900 DBUG_PRINT("info",("spider can not create link_idx_holder"));
1901 delete fields;
1902 DBUG_RETURN(NULL);
1903 }
1904 }
1905 if (!fields->has_conn_holder())
1906 {
1907 delete fields;
1908 DBUG_RETURN(NULL);
1909 }
1910
1911 while ((from = from->next_local))
1912 {
1913 if (from->table->const_table)
1914 continue;
1915 fields->clear_conn_holder_from_conn();
1916
1917#if defined(PARTITION_HAS_GET_CHILD_HANDLERS) && defined(PARTITION_HAS_GET_PART_SPEC)
1918 if (from->table->part_info)
1919 {
1920 ha_partition *partition = (ha_partition *) from->table->file;
1921 part_id_range *part_spec = partition->get_part_spec();
1922 handler **handlers = partition->get_child_handlers();
1923 spider = (ha_spider *) handlers[part_spec->start_part];
1924 } else {
1925#endif
1926 spider = (ha_spider *) from->table->file;
1927#if defined(PARTITION_HAS_GET_CHILD_HANDLERS) && defined(PARTITION_HAS_GET_PART_SPEC)
1928 }
1929#endif
1930 share = spider->share;
1931 if (!fields->add_table(spider))
1932 {
1933 DBUG_PRINT("info",("spider can not add a table"));
1934 delete fields;
1935 DBUG_RETURN(NULL);
1936 }
1937 DBUG_PRINT("info",("spider s->db=%s", from->table->s->db.str));
1938 DBUG_PRINT("info",("spider s->table_name=%s", from->table->s->table_name.str));
1939 for (
1940 roop_count = spider_conn_link_idx_next(share->link_statuses,
1941 spider->conn_link_idx, -1, share->link_count,
1942 tgt_link_status);
1943 roop_count < (int) share->link_count;
1944 roop_count = spider_conn_link_idx_next(share->link_statuses,
1945 spider->conn_link_idx, roop_count, share->link_count,
1946 tgt_link_status)
1947 ) {
1948 DBUG_PRINT("info",("spider roop_count=%d", roop_count));
1949 if (spider_param_use_handler(thd, share->use_handlers[roop_count]))
1950 {
1951 DBUG_PRINT("info",("spider direct_join does not support use_handler"));
1952 if (lock_mode)
1953 {
1954 delete fields;
1955 DBUG_RETURN(NULL);
1956 }
1957 continue;
1958 }
1959 conn = spider->conns[roop_count];
1960 DBUG_PRINT("info",("spider conn=%p", conn));
1961 if (!fields->check_conn_same_conn(conn))
1962 {
1963 DBUG_PRINT("info",("spider connection %p can not be used for this query with locking",
1964 conn));
1965 if (lock_mode)
1966 {
1967 delete fields;
1968 DBUG_RETURN(NULL);
1969 }
1970 continue;
1971 }
1972 if (fields->add_link_idx(conn->conn_holder_for_direct_join, spider, roop_count))
1973 {
1974 DBUG_PRINT("info",("spider can not create link_idx_holder"));
1975 delete fields;
1976 DBUG_RETURN(NULL);
1977 }
1978 }
1979
1980 if (fields->remove_conn_if_not_checked())
1981 {
1982 if (lock_mode)
1983 {
1984 DBUG_PRINT("info",("spider some connections can not be used for this query with locking"));
1985 delete fields;
1986 DBUG_RETURN(NULL);
1987 }
1988 }
1989 if (!fields->has_conn_holder())
1990 {
1991 delete fields;
1992 DBUG_RETURN(NULL);
1993 }
1994 }
1995
1996 fields->check_support_dbton(dbton_bitmap);
1997 if (!fields->has_conn_holder())
1998 {
1999 DBUG_PRINT("info",("spider all choosed connections can't match dbton_id"));
2000 delete fields;
2001 DBUG_RETURN(NULL);
2002 }
2003
2004 /* choose a connection */
2005 if (!lock_mode)
2006 {
2007 fields->choose_a_conn();
2008 }
2009
2010 if (fields->make_link_idx_chain(tgt_link_status))
2011 {
2012 DBUG_PRINT("info",("spider can not create link_idx_chain"));
2013 delete fields;
2014 DBUG_RETURN(NULL);
2015 }
2016
2017 /* choose link_id */
2018 if (fields->check_link_ok_chain())
2019 {
2020 DBUG_PRINT("info",("spider do not have link ok status"));
2021 delete fields;
2022 DBUG_RETURN(NULL);
2023 }
2024
2025 fields->set_first_link_idx();
2026
2027 if (!(group_by_handler = new spider_group_by_handler(thd, query, fields)))
2028 {
2029 DBUG_PRINT("info",("spider can't create group_by_handler"));
2030 delete fields;
2031 DBUG_RETURN(NULL);
2032 }
2033 query->distinct = FALSE;
2034 query->where = NULL;
2035 query->group_by = NULL;
2036 query->having = NULL;
2037 query->order_by = NULL;
2038 DBUG_RETURN(group_by_handler);
2039}
2040#endif
2041