1 /* Copyright (C) 2009-2018 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335 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 "sql_base.h"
29 #include "sql_servers.h"
30 #include "tztime.h"
31 #endif
32 #include "spd_err.h"
33 #include "spd_param.h"
34 #include "spd_db_include.h"
35 #include "spd_include.h"
36 #include "spd_sys_table.h"
37 #include "ha_spider.h"
38 #include "spd_db_conn.h"
39 #include "spd_trx.h"
40 #include "spd_conn.h"
41 #include "spd_table.h"
42 #include "spd_direct_sql.h"
43 #include "spd_udf.h"
44 #include "spd_malloc.h"
45
46 #if defined(MARIADB_BASE_VERSION) && MYSQL_VERSION_ID >= 100004
47 #define SPIDER_NEED_INIT_ONE_TABLE_FOR_FIND_TEMPORARY_TABLE
48 #endif
49
50 extern const char **spd_defaults_extra_file;
51 extern const char **spd_defaults_file;
52
53 extern handlerton *spider_hton_ptr;
54 extern SPIDER_DBTON spider_dbton[SPIDER_DBTON_SIZE];
55
56 #ifdef HAVE_PSI_INTERFACE
57 extern PSI_mutex_key spd_key_mutex_mta_conn;
58 extern PSI_mutex_key spd_key_mutex_bg_direct_sql;
59 extern PSI_cond_key spd_key_cond_bg_direct_sql;
60 #endif
61
62 extern HASH spider_open_connections;
63 extern HASH spider_ipport_conns;
64 extern pthread_mutex_t spider_conn_mutex;
65 extern pthread_mutex_t spider_conn_id_mutex;
66 extern pthread_mutex_t spider_ipport_conn_mutex;
67 extern ulonglong spider_conn_id;
68
69 /* UTC time zone for timestamp columns */
70 extern Time_zone *UTC;
71
spider_udf_calc_hash(char * key,uint mod)72 uint spider_udf_calc_hash(
73 char *key,
74 uint mod
75 ) {
76 uint sum = 0;
77 DBUG_ENTER("spider_udf_calc_hash");
78 while (*key != '\0')
79 {
80 sum += *key;
81 key++;
82 }
83 DBUG_PRINT("info",("spider calc hash = %u", sum % mod));
84 DBUG_RETURN(sum % mod);
85 }
86
spider_udf_direct_sql_create_table_list(SPIDER_DIRECT_SQL * direct_sql,char * table_name_list,uint table_name_list_length)87 int spider_udf_direct_sql_create_table_list(
88 SPIDER_DIRECT_SQL *direct_sql,
89 char *table_name_list,
90 uint table_name_list_length
91 ) {
92 int table_count, roop_count, length;
93 char *tmp_ptr, *tmp_ptr2, *tmp_ptr3, *tmp_name_ptr;
94 THD *thd = direct_sql->trx->thd;
95 DBUG_ENTER("spider_udf_direct_sql_create_table_list");
96 tmp_ptr = table_name_list;
97 while (*tmp_ptr == ' ')
98 tmp_ptr++;
99 if (*tmp_ptr)
100 table_count = 1;
101 else {
102 direct_sql->table_count = 0;
103 DBUG_RETURN(0);
104 }
105
106 while (TRUE)
107 {
108 if ((tmp_ptr2 = strchr(tmp_ptr, ' ')))
109 {
110 table_count++;
111 tmp_ptr = tmp_ptr2 + 1;
112 while (*tmp_ptr == ' ')
113 tmp_ptr++;
114 } else
115 break;
116 }
117 #if MYSQL_VERSION_ID < 50500
118 if (!(direct_sql->db_names = (char**)
119 spider_bulk_malloc(spider_current_trx, 31, MYF(MY_WME | MY_ZEROFILL),
120 &direct_sql->db_names, sizeof(char*) * table_count,
121 &direct_sql->table_names, sizeof(char*) * table_count,
122 &direct_sql->tables, sizeof(TABLE*) * table_count,
123 &tmp_name_ptr, sizeof(char) * (
124 table_name_list_length +
125 thd->db_length * table_count +
126 2 * table_count
127 ),
128 &direct_sql->iop, sizeof(int) * table_count,
129 NullS))
130 )
131 #else
132 if (!(direct_sql->db_names = (char**)
133 spider_bulk_malloc(spider_current_trx, 31, MYF(MY_WME | MY_ZEROFILL),
134 &direct_sql->db_names, sizeof(char*) * table_count,
135 &direct_sql->table_names, sizeof(char*) * table_count,
136 &direct_sql->tables, sizeof(TABLE*) * table_count,
137 &tmp_name_ptr, sizeof(char) * (
138 table_name_list_length +
139 SPIDER_THD_db_length(thd) * table_count +
140 2 * table_count
141 ),
142 &direct_sql->iop, sizeof(int) * table_count,
143 &direct_sql->table_list, sizeof(TABLE_LIST) * table_count,
144 &direct_sql->real_table_bitmap, sizeof(uchar) * ((table_count + 7) / 8),
145 NullS))
146 )
147 #endif
148 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
149
150 tmp_ptr = table_name_list;
151 while (*tmp_ptr == ' ')
152 tmp_ptr++;
153 roop_count = 0;
154 while (TRUE)
155 {
156 if ((tmp_ptr2 = strchr(tmp_ptr, ' ')))
157 *tmp_ptr2 = '\0';
158
159 direct_sql->db_names[roop_count] = tmp_name_ptr;
160
161 if ((tmp_ptr3 = strchr(tmp_ptr, '.')))
162 {
163 /* exist database name */
164 *tmp_ptr3 = '\0';
165 length = strlen(tmp_ptr);
166 memcpy(tmp_name_ptr, tmp_ptr, length + 1);
167 tmp_name_ptr += length + 1;
168 tmp_ptr = tmp_ptr3 + 1;
169 } else {
170 if (SPIDER_THD_db_str(thd))
171 {
172 memcpy(tmp_name_ptr, SPIDER_THD_db_str(thd),
173 SPIDER_THD_db_length(thd) + 1);
174 tmp_name_ptr += SPIDER_THD_db_length(thd) + 1;
175 } else {
176 direct_sql->db_names[roop_count] = (char *) "";
177 }
178 }
179
180 direct_sql->table_names[roop_count] = tmp_name_ptr;
181 length = strlen(tmp_ptr);
182 memcpy(tmp_name_ptr, tmp_ptr, length + 1);
183 tmp_name_ptr += length + 1;
184
185 DBUG_PRINT("info",("spider db=%s",
186 direct_sql->db_names[roop_count]));
187 DBUG_PRINT("info",("spider table_name=%s",
188 direct_sql->table_names[roop_count]));
189
190 if (!tmp_ptr2)
191 break;
192 tmp_ptr = tmp_ptr2 + 1;
193 while (*tmp_ptr == ' ')
194 tmp_ptr++;
195 roop_count++;
196 }
197 direct_sql->table_count = table_count;
198 DBUG_RETURN(0);
199 }
200
spider_udf_direct_sql_create_conn_key(SPIDER_DIRECT_SQL * direct_sql)201 int spider_udf_direct_sql_create_conn_key(
202 SPIDER_DIRECT_SQL *direct_sql
203 ) {
204 char *tmp_name, port_str[6];
205 DBUG_ENTER("spider_udf_direct_sql_create_conn_key");
206
207 /* tgt_db not use */
208 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
209 if (direct_sql->access_mode == 0)
210 {
211 #endif
212 direct_sql->conn_key_length
213 = 1
214 + direct_sql->tgt_wrapper_length + 1
215 + direct_sql->tgt_host_length + 1
216 + 5 + 1
217 + direct_sql->tgt_socket_length + 1
218 + direct_sql->tgt_username_length + 1
219 + direct_sql->tgt_password_length + 1
220 + direct_sql->tgt_ssl_ca_length + 1
221 + direct_sql->tgt_ssl_capath_length + 1
222 + direct_sql->tgt_ssl_cert_length + 1
223 + direct_sql->tgt_ssl_cipher_length + 1
224 + direct_sql->tgt_ssl_key_length + 1
225 + 1 + 1
226 + direct_sql->tgt_default_file_length + 1
227 + direct_sql->tgt_default_group_length;
228 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
229 } else {
230 direct_sql->conn_key_length
231 = 1
232 + direct_sql->tgt_wrapper_length + 1
233 + direct_sql->tgt_host_length + 1
234 + 5 + 1
235 + direct_sql->tgt_socket_length;
236 }
237 #endif
238 if (!(direct_sql->conn_key = (char *)
239 spider_malloc(spider_current_trx, 9, direct_sql->conn_key_length + 1,
240 MYF(MY_WME | MY_ZEROFILL)))
241 )
242 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
243 if (direct_sql->connection_channel > 48)
244 *direct_sql->conn_key = '0' + 48 - direct_sql->connection_channel;
245 else
246 *direct_sql->conn_key = '0' + direct_sql->connection_channel;
247 DBUG_PRINT("info",("spider tgt_wrapper=%s", direct_sql->tgt_wrapper));
248 tmp_name = strmov(direct_sql->conn_key + 1, direct_sql->tgt_wrapper);
249 DBUG_PRINT("info",("spider tgt_host=%s", direct_sql->tgt_host));
250 tmp_name = strmov(tmp_name + 1, direct_sql->tgt_host);
251 my_sprintf(port_str, (port_str, "%05ld", direct_sql->tgt_port));
252 DBUG_PRINT("info",("spider port_str=%s", port_str));
253 tmp_name = strmov(tmp_name + 1, port_str);
254 if (direct_sql->tgt_socket)
255 {
256 DBUG_PRINT("info",("spider tgt_socket=%s", direct_sql->tgt_socket));
257 tmp_name = strmov(tmp_name + 1, direct_sql->tgt_socket);
258 } else
259 tmp_name++;
260 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
261 if (direct_sql->access_mode == 0)
262 {
263 #endif
264 if (direct_sql->tgt_username)
265 {
266 DBUG_PRINT("info",("spider tgt_username=%s", direct_sql->tgt_username));
267 tmp_name = strmov(tmp_name + 1, direct_sql->tgt_username);
268 } else
269 tmp_name++;
270 if (direct_sql->tgt_password)
271 {
272 DBUG_PRINT("info",("spider tgt_password=%s", direct_sql->tgt_password));
273 tmp_name = strmov(tmp_name + 1, direct_sql->tgt_password);
274 } else
275 tmp_name++;
276 if (direct_sql->tgt_ssl_ca)
277 {
278 DBUG_PRINT("info",("spider tgt_ssl_ca=%s", direct_sql->tgt_ssl_ca));
279 tmp_name = strmov(tmp_name + 1, direct_sql->tgt_ssl_ca);
280 } else
281 tmp_name++;
282 if (direct_sql->tgt_ssl_capath)
283 {
284 DBUG_PRINT("info",("spider tgt_ssl_capath=%s",
285 direct_sql->tgt_ssl_capath));
286 tmp_name = strmov(tmp_name + 1, direct_sql->tgt_ssl_capath);
287 } else
288 tmp_name++;
289 if (direct_sql->tgt_ssl_cert)
290 {
291 DBUG_PRINT("info",("spider tgt_ssl_cert=%s", direct_sql->tgt_ssl_cert));
292 tmp_name = strmov(tmp_name + 1, direct_sql->tgt_ssl_cert);
293 } else
294 tmp_name++;
295 if (direct_sql->tgt_ssl_cipher)
296 {
297 DBUG_PRINT("info",("spider tgt_ssl_cipher=%s",
298 direct_sql->tgt_ssl_cipher));
299 tmp_name = strmov(tmp_name + 1, direct_sql->tgt_ssl_cipher);
300 } else
301 tmp_name++;
302 if (direct_sql->tgt_ssl_key)
303 {
304 DBUG_PRINT("info",("spider tgt_ssl_key=%s", direct_sql->tgt_ssl_key));
305 tmp_name = strmov(tmp_name + 1, direct_sql->tgt_ssl_key);
306 } else
307 tmp_name++;
308 tmp_name++;
309 *tmp_name = '0' + ((char) direct_sql->tgt_ssl_vsc);
310 if (direct_sql->tgt_default_file)
311 {
312 DBUG_PRINT("info",("spider tgt_default_file=%s",
313 direct_sql->tgt_default_file));
314 tmp_name = strmov(tmp_name + 1, direct_sql->tgt_default_file);
315 } else
316 tmp_name++;
317 if (direct_sql->tgt_default_group)
318 {
319 DBUG_PRINT("info",("spider tgt_default_group=%s",
320 direct_sql->tgt_default_group));
321 tmp_name = strmov(tmp_name + 1, direct_sql->tgt_default_group);
322 } else
323 tmp_name++;
324 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
325 }
326 #endif
327 uint roop_count2;
328 direct_sql->dbton_id = SPIDER_DBTON_SIZE;
329 DBUG_PRINT("info",("spider direct_sql->tgt_wrapper=%s",
330 direct_sql->tgt_wrapper));
331 for (roop_count2 = 0; roop_count2 < SPIDER_DBTON_SIZE; roop_count2++)
332 {
333 DBUG_PRINT("info",("spider spider_dbton[%d].wrapper=%s", roop_count2,
334 spider_dbton[roop_count2].wrapper ?
335 spider_dbton[roop_count2].wrapper : "NULL"));
336 if (
337 spider_dbton[roop_count2].wrapper &&
338 !strcmp(direct_sql->tgt_wrapper, spider_dbton[roop_count2].wrapper)
339 ) {
340 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
341 if (direct_sql->access_mode == 0)
342 {
343 #endif
344 if (spider_dbton[roop_count2].db_access_type ==
345 SPIDER_DB_ACCESS_TYPE_SQL)
346 {
347 direct_sql->dbton_id = roop_count2;
348 break;
349 }
350 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
351 } else {
352 if (spider_dbton[roop_count2].db_access_type ==
353 SPIDER_DB_ACCESS_TYPE_NOSQL)
354 {
355 direct_sql->dbton_id = roop_count2;
356 break;
357 }
358 }
359 #endif
360 }
361 }
362 if (direct_sql->dbton_id == SPIDER_DBTON_SIZE)
363 {
364 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
365 if (direct_sql->access_mode == 0)
366 {
367 #endif
368 my_printf_error(
369 ER_SPIDER_SQL_WRAPPER_IS_INVALID_NUM,
370 ER_SPIDER_SQL_WRAPPER_IS_INVALID_STR,
371 MYF(0), direct_sql->tgt_wrapper);
372 DBUG_RETURN(ER_SPIDER_SQL_WRAPPER_IS_INVALID_NUM);
373 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
374 } else {
375 my_printf_error(
376 ER_SPIDER_NOSQL_WRAPPER_IS_INVALID_NUM,
377 ER_SPIDER_NOSQL_WRAPPER_IS_INVALID_STR,
378 MYF(0), direct_sql->tgt_wrapper);
379 DBUG_RETURN(ER_SPIDER_NOSQL_WRAPPER_IS_INVALID_NUM);
380 }
381 #endif
382 }
383 #ifdef SPIDER_HAS_HASH_VALUE_TYPE
384 direct_sql->conn_key_hash_value = my_calc_hash(&spider_open_connections,
385 (uchar*) direct_sql->conn_key, direct_sql->conn_key_length);
386 #endif
387 DBUG_RETURN(0);
388 }
389
spider_udf_direct_sql_create_conn(const SPIDER_DIRECT_SQL * direct_sql,int * error_num)390 SPIDER_CONN *spider_udf_direct_sql_create_conn(
391 const SPIDER_DIRECT_SQL *direct_sql,
392 int *error_num
393 ) {
394 SPIDER_CONN *conn;
395 SPIDER_IP_PORT_CONN *ip_port_conn;
396 char *tmp_name, *tmp_host, *tmp_username, *tmp_password, *tmp_socket;
397 char *tmp_wrapper, *tmp_ssl_ca, *tmp_ssl_capath, *tmp_ssl_cert;
398 char *tmp_ssl_cipher, *tmp_ssl_key, *tmp_default_file, *tmp_default_group;
399 int *need_mon;
400 DBUG_ENTER("spider_udf_direct_sql_create_conn");
401
402 if (unlikely(!UTC))
403 {
404 /* UTC time zone for timestamp columns */
405 String tz_00_name(STRING_WITH_LEN("+00:00"), &my_charset_bin);
406 UTC = my_tz_find(current_thd, &tz_00_name);
407 }
408
409 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
410 if (direct_sql->access_mode == 0)
411 {
412 #endif
413 if (!(conn = (SPIDER_CONN *)
414 spider_bulk_malloc(spider_current_trx, 32, MYF(MY_WME | MY_ZEROFILL),
415 &conn, sizeof(*conn),
416 &tmp_name, direct_sql->conn_key_length + 1,
417 &tmp_host, direct_sql->tgt_host_length + 1,
418 &tmp_username, direct_sql->tgt_username_length + 1,
419 &tmp_password, direct_sql->tgt_password_length + 1,
420 &tmp_socket, direct_sql->tgt_socket_length + 1,
421 &tmp_wrapper, direct_sql->tgt_wrapper_length + 1,
422 &tmp_ssl_ca, direct_sql->tgt_ssl_ca_length + 1,
423 &tmp_ssl_capath, direct_sql->tgt_ssl_capath_length + 1,
424 &tmp_ssl_cert, direct_sql->tgt_ssl_cert_length + 1,
425 &tmp_ssl_cipher, direct_sql->tgt_ssl_cipher_length + 1,
426 &tmp_ssl_key, direct_sql->tgt_ssl_key_length + 1,
427 &tmp_default_file,
428 direct_sql->tgt_default_file_length + 1,
429 &tmp_default_group,
430 direct_sql->tgt_default_group_length + 1,
431 &need_mon, sizeof(int),
432 NullS))
433 ) {
434 *error_num = HA_ERR_OUT_OF_MEM;
435 goto error_alloc_conn;
436 }
437 conn->default_database.init_calc_mem(138);
438 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
439 } else {
440 if (!(conn = (SPIDER_CONN *)
441 spider_bulk_malloc(spider_current_trx, 33, MYF(MY_WME | MY_ZEROFILL),
442 &conn, sizeof(*conn),
443 &tmp_name, direct_sql->conn_key_length + 1,
444 &tmp_host, direct_sql->tgt_host_length + 1,
445 &tmp_socket, direct_sql->tgt_socket_length + 1,
446 &tmp_wrapper, direct_sql->tgt_wrapper_length + 1,
447 &need_mon, sizeof(int),
448 NullS))
449 ) {
450 *error_num = HA_ERR_OUT_OF_MEM;
451 goto error_alloc_conn;
452 }
453 conn->default_database.init_calc_mem(103);
454 }
455 #endif
456
457 conn->conn_key_length = direct_sql->conn_key_length;
458 conn->conn_key = tmp_name;
459 memcpy(conn->conn_key, direct_sql->conn_key, direct_sql->conn_key_length);
460 conn->tgt_wrapper_length = direct_sql->tgt_wrapper_length;
461 conn->tgt_wrapper = tmp_wrapper;
462 memcpy(conn->tgt_wrapper, direct_sql->tgt_wrapper,
463 direct_sql->tgt_wrapper_length);
464 conn->tgt_host_length = direct_sql->tgt_host_length;
465 conn->tgt_host = tmp_host;
466 memcpy(conn->tgt_host, direct_sql->tgt_host, direct_sql->tgt_host_length);
467 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
468 if (direct_sql->access_mode == 0)
469 {
470 #endif
471 conn->tgt_port = direct_sql->tgt_port;
472 conn->tgt_socket_length = direct_sql->tgt_socket_length;
473 conn->tgt_socket = tmp_socket;
474 memcpy(conn->tgt_socket, direct_sql->tgt_socket,
475 direct_sql->tgt_socket_length);
476 conn->tgt_username_length = direct_sql->tgt_username_length;
477 conn->tgt_username = tmp_username;
478 memcpy(conn->tgt_username, direct_sql->tgt_username,
479 direct_sql->tgt_username_length);
480 conn->tgt_password_length = direct_sql->tgt_password_length;
481 conn->tgt_password = tmp_password;
482 memcpy(conn->tgt_password, direct_sql->tgt_password,
483 direct_sql->tgt_password_length);
484 conn->tgt_ssl_ca_length = direct_sql->tgt_ssl_ca_length;
485 if (conn->tgt_ssl_ca_length)
486 {
487 conn->tgt_ssl_ca = tmp_ssl_ca;
488 memcpy(conn->tgt_ssl_ca, direct_sql->tgt_ssl_ca,
489 direct_sql->tgt_ssl_ca_length);
490 } else
491 conn->tgt_ssl_ca = NULL;
492 conn->tgt_ssl_capath_length = direct_sql->tgt_ssl_capath_length;
493 if (conn->tgt_ssl_capath_length)
494 {
495 conn->tgt_ssl_capath = tmp_ssl_capath;
496 memcpy(conn->tgt_ssl_capath, direct_sql->tgt_ssl_capath,
497 direct_sql->tgt_ssl_capath_length);
498 } else
499 conn->tgt_ssl_capath = NULL;
500 conn->tgt_ssl_cert_length = direct_sql->tgt_ssl_cert_length;
501 if (conn->tgt_ssl_cert_length)
502 {
503 conn->tgt_ssl_cert = tmp_ssl_cert;
504 memcpy(conn->tgt_ssl_cert, direct_sql->tgt_ssl_cert,
505 direct_sql->tgt_ssl_cert_length);
506 } else
507 conn->tgt_ssl_cert = NULL;
508 conn->tgt_ssl_cipher_length = direct_sql->tgt_ssl_cipher_length;
509 if (conn->tgt_ssl_cipher_length)
510 {
511 conn->tgt_ssl_cipher = tmp_ssl_cipher;
512 memcpy(conn->tgt_ssl_cipher, direct_sql->tgt_ssl_cipher,
513 direct_sql->tgt_ssl_cipher_length);
514 } else
515 conn->tgt_ssl_cipher = NULL;
516 conn->tgt_ssl_key_length = direct_sql->tgt_ssl_key_length;
517 if (conn->tgt_ssl_key_length)
518 {
519 conn->tgt_ssl_key = tmp_ssl_key;
520 memcpy(conn->tgt_ssl_key, direct_sql->tgt_ssl_key,
521 direct_sql->tgt_ssl_key_length);
522 } else
523 conn->tgt_ssl_key = NULL;
524 conn->tgt_default_file_length = direct_sql->tgt_default_file_length;
525 if (conn->tgt_default_file_length)
526 {
527 conn->tgt_default_file = tmp_default_file;
528 memcpy(conn->tgt_default_file, direct_sql->tgt_default_file,
529 direct_sql->tgt_default_file_length);
530 } else
531 conn->tgt_default_file = NULL;
532 conn->tgt_default_group_length = direct_sql->tgt_default_group_length;
533 if (conn->tgt_default_group_length)
534 {
535 conn->tgt_default_group = tmp_default_group;
536 memcpy(conn->tgt_default_group, direct_sql->tgt_default_group,
537 direct_sql->tgt_default_group_length);
538 } else
539 conn->tgt_default_group = NULL;
540 conn->tgt_ssl_vsc = direct_sql->tgt_ssl_vsc;
541 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
542 } else {
543 conn->hs_port = direct_sql->tgt_port;
544 if (direct_sql->tgt_socket)
545 {
546 conn->hs_sock_length = direct_sql->tgt_socket_length;
547 conn->hs_sock = tmp_socket;
548 memcpy(conn->hs_sock, direct_sql->tgt_socket,
549 direct_sql->tgt_socket_length);
550 }
551 }
552 #endif
553 conn->dbton_id = direct_sql->dbton_id;
554 conn->conn_need_mon = need_mon;
555 conn->need_mon = need_mon;
556 if (!(conn->db_conn = spider_dbton[conn->dbton_id].create_db_conn(conn)))
557 {
558 *error_num = HA_ERR_OUT_OF_MEM;
559 goto error_db_conn_create;
560 }
561 if ((*error_num = conn->db_conn->init()))
562 {
563 goto error_db_conn_init;
564 }
565 conn->join_trx = 0;
566 conn->thd = NULL;
567 conn->table_lock = 0;
568 conn->semi_trx_isolation = -2;
569 conn->semi_trx_isolation_chk = FALSE;
570 conn->semi_trx_chk = FALSE;
571 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
572 if (direct_sql->access_mode == 0)
573 {
574 #endif
575 conn->conn_kind = SPIDER_CONN_KIND_MYSQL;
576 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
577 } else if (direct_sql->access_mode == 1)
578 {
579 conn->conn_kind = SPIDER_CONN_KIND_HS_READ;
580 } else {
581 conn->conn_kind = SPIDER_CONN_KIND_HS_WRITE;
582 }
583 #endif
584
585 #if MYSQL_VERSION_ID < 50500
586 if (pthread_mutex_init(&conn->mta_conn_mutex, MY_MUTEX_INIT_FAST))
587 #else
588 if (mysql_mutex_init(spd_key_mutex_mta_conn, &conn->mta_conn_mutex,
589 MY_MUTEX_INIT_FAST))
590 #endif
591 {
592 *error_num = HA_ERR_OUT_OF_MEM;
593 goto error_mta_conn_mutex_init;
594 }
595
596 if ((*error_num = spider_db_udf_direct_sql_connect(direct_sql, conn)))
597 goto error;
598 conn->ping_time = (time_t) time((time_t*) 0);
599 conn->connect_error_time = conn->ping_time;
600 pthread_mutex_lock(&spider_conn_id_mutex);
601 conn->conn_id = spider_conn_id;
602 ++spider_conn_id;
603 pthread_mutex_unlock(&spider_conn_id_mutex);
604
605 pthread_mutex_lock(&spider_ipport_conn_mutex);
606 #ifdef SPIDER_HAS_HASH_VALUE_TYPE
607 if ((ip_port_conn = (SPIDER_IP_PORT_CONN*) my_hash_search_using_hash_value(
608 &spider_ipport_conns, conn->conn_key_hash_value,
609 (uchar*)conn->conn_key, conn->conn_key_length)))
610 #else
611 if ((ip_port_conn = (SPIDER_IP_PORT_CONN*) my_hash_search(
612 &spider_ipport_conns, (uchar*)conn->conn_key, conn->conn_key_length)))
613 #endif
614 { /* exists, +1 */
615 pthread_mutex_unlock(&spider_ipport_conn_mutex);
616 pthread_mutex_lock(&ip_port_conn->mutex);
617 if (spider_param_max_connections())
618 { /* enable conncetion pool */
619 if (ip_port_conn->ip_port_count >= spider_param_max_connections())
620 { /* bigger than the max num of connections, free conn and return NULL */
621 pthread_mutex_unlock(&ip_port_conn->mutex);
622 goto error_too_many_ipport_count;
623 }
624 }
625 ip_port_conn->ip_port_count++;
626 pthread_mutex_unlock(&ip_port_conn->mutex);
627 }
628 else
629 {// do not exist
630 ip_port_conn = spider_create_ipport_conn(conn);
631 if (!ip_port_conn) {
632 /* failed, always do not effect 'create conn' */
633 pthread_mutex_unlock(&spider_ipport_conn_mutex);
634 DBUG_RETURN(conn);
635 }
636 if (my_hash_insert(&spider_ipport_conns, (uchar *)ip_port_conn)) {
637 /* insert failed, always do not effect 'create conn' */
638 pthread_mutex_unlock(&spider_ipport_conn_mutex);
639 DBUG_RETURN(conn);
640 }
641 pthread_mutex_unlock(&spider_ipport_conn_mutex);
642 }
643 conn->ip_port_conn = ip_port_conn;
644
645 DBUG_RETURN(conn);
646
647 error:
648 DBUG_ASSERT(!conn->mta_conn_mutex_file_pos.file_name);
649 pthread_mutex_destroy(&conn->mta_conn_mutex);
650 error_too_many_ipport_count:
651 error_mta_conn_mutex_init:
652 error_db_conn_init:
653 delete conn->db_conn;
654 error_db_conn_create:
655 spider_free(spider_current_trx, conn, MYF(0));
656 error_alloc_conn:
657 DBUG_RETURN(NULL);
658 }
659
spider_udf_direct_sql_get_conn(const SPIDER_DIRECT_SQL * direct_sql,SPIDER_TRX * trx,int * error_num)660 SPIDER_CONN *spider_udf_direct_sql_get_conn(
661 const SPIDER_DIRECT_SQL *direct_sql,
662 SPIDER_TRX *trx,
663 int *error_num
664 ) {
665 SPIDER_CONN *conn = NULL;
666 DBUG_ENTER("spider_udf_direct_sql_get_conn");
667 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
668 DBUG_PRINT("info",("spider direct_sql->access_mode=%d",
669 direct_sql->access_mode));
670 #endif
671
672 #ifdef SPIDER_HAS_HASH_VALUE_TYPE
673 if (
674 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
675 (direct_sql->access_mode == 0 &&
676 #endif
677 !(conn = (SPIDER_CONN*) my_hash_search_using_hash_value(
678 &trx->trx_conn_hash, direct_sql->conn_key_hash_value,
679 (uchar*) direct_sql->conn_key, direct_sql->conn_key_length))
680 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
681 ) ||
682 (direct_sql->access_mode == 1 &&
683 !(conn = (SPIDER_CONN*) my_hash_search_using_hash_value(
684 &trx->trx_direct_hs_r_conn_hash, direct_sql->conn_key_hash_value,
685 (uchar*) direct_sql->conn_key, direct_sql->conn_key_length))
686 ) ||
687 (direct_sql->access_mode == 2 &&
688 !(conn = (SPIDER_CONN*) my_hash_search_using_hash_value(
689 &trx->trx_direct_hs_w_conn_hash, direct_sql->conn_key_hash_value,
690 (uchar*) direct_sql->conn_key, direct_sql->conn_key_length))
691 )
692 #endif
693 )
694 #else
695 if (
696 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
697 (direct_sql->access_mode == 0 &&
698 #endif
699 !(conn = (SPIDER_CONN*) my_hash_search(&trx->trx_conn_hash,
700 (uchar*) direct_sql->conn_key, direct_sql->conn_key_length))
701 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
702 ) ||
703 (direct_sql->access_mode == 1 &&
704 !(conn = (SPIDER_CONN*) my_hash_search(&trx->trx_direct_hs_r_conn_hash,
705 (uchar*) direct_sql->conn_key, direct_sql->conn_key_length))
706 ) ||
707 (direct_sql->access_mode == 2 &&
708 !(conn = (SPIDER_CONN*) my_hash_search(&trx->trx_direct_hs_w_conn_hash,
709 (uchar*) direct_sql->conn_key, direct_sql->conn_key_length))
710 )
711 #endif
712 )
713 #endif
714 {
715 if (
716 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
717 (direct_sql->access_mode == 0 &&
718 #endif
719 (
720 (spider_param_conn_recycle_mode(trx->thd) & 1) ||
721 spider_param_conn_recycle_strict(trx->thd)
722 )
723 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
724 ) ||
725 (direct_sql->access_mode == 1 &&
726 (
727 (spider_param_hs_r_conn_recycle_mode(trx->thd) & 1) ||
728 spider_param_hs_r_conn_recycle_strict(trx->thd)
729 )
730 ) ||
731 (direct_sql->access_mode == 2 &&
732 (
733 (spider_param_hs_w_conn_recycle_mode(trx->thd) & 1) ||
734 spider_param_hs_w_conn_recycle_strict(trx->thd)
735 )
736 )
737 #endif
738 ) {
739 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
740 if (direct_sql->access_mode == 0)
741 {
742 #endif
743 pthread_mutex_lock(&spider_conn_mutex);
744 #ifdef SPIDER_HAS_HASH_VALUE_TYPE
745 if (!(conn = (SPIDER_CONN*) my_hash_search_using_hash_value(
746 &spider_open_connections, direct_sql->conn_key_hash_value,
747 (uchar*) direct_sql->conn_key, direct_sql->conn_key_length)))
748 #else
749 if (!(conn = (SPIDER_CONN*) my_hash_search(&spider_open_connections,
750 (uchar*) direct_sql->conn_key, direct_sql->conn_key_length)))
751 #endif
752 {
753 pthread_mutex_unlock(&spider_conn_mutex);
754 DBUG_PRINT("info",("spider create new conn"));
755 if(!(conn = spider_udf_direct_sql_create_conn(direct_sql,
756 error_num)))
757 goto error;
758 } else {
759 #ifdef HASH_UPDATE_WITH_HASH_VALUE
760 my_hash_delete_with_hash_value(&spider_open_connections,
761 conn->conn_key_hash_value, (uchar*) conn);
762 #else
763 my_hash_delete(&spider_open_connections, (uchar*) conn);
764 #endif
765 pthread_mutex_unlock(&spider_conn_mutex);
766 DBUG_PRINT("info",("spider get global conn"));
767 }
768 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
769 }
770 #endif
771 } else {
772 DBUG_PRINT("info",("spider create new conn"));
773 /* conn_recycle_strict = 0 and conn_recycle_mode = 0 or 2 */
774 if(!(conn = spider_udf_direct_sql_create_conn(direct_sql, error_num)))
775 goto error;
776 }
777 conn->thd = trx->thd;
778 conn->priority = direct_sql->priority;
779
780 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
781 if (direct_sql->access_mode == 0)
782 {
783 #endif
784 uint old_elements = trx->trx_conn_hash.array.max_element;
785 #ifdef HASH_UPDATE_WITH_HASH_VALUE
786 if (my_hash_insert_with_hash_value(&trx->trx_conn_hash,
787 direct_sql->conn_key_hash_value, (uchar*) conn))
788 #else
789 if (my_hash_insert(&trx->trx_conn_hash, (uchar*) conn))
790 #endif
791 {
792 spider_free_conn(conn);
793 *error_num = HA_ERR_OUT_OF_MEM;
794 goto error;
795 }
796 if (trx->trx_conn_hash.array.max_element > old_elements)
797 {
798 spider_alloc_calc_mem(spider_current_trx,
799 trx->trx_conn_hash,
800 (trx->trx_conn_hash.array.max_element - old_elements) *
801 trx->trx_conn_hash.array.size_of_element);
802 }
803 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
804 } else if (direct_sql->access_mode == 1)
805 {
806 uint old_elements = trx->trx_direct_hs_r_conn_hash.array.max_element;
807 #ifdef HASH_UPDATE_WITH_HASH_VALUE
808 if (my_hash_insert_with_hash_value(&trx->trx_direct_hs_r_conn_hash,
809 direct_sql->conn_key_hash_value, (uchar*) conn))
810 #else
811 if (my_hash_insert(&trx->trx_direct_hs_r_conn_hash, (uchar*) conn))
812 #endif
813 {
814 spider_free_conn(conn);
815 *error_num = HA_ERR_OUT_OF_MEM;
816 goto error;
817 }
818 if (trx->trx_direct_hs_r_conn_hash.array.max_element > old_elements)
819 {
820 spider_alloc_calc_mem(spider_current_trx,
821 trx->trx_direct_hs_r_conn_hash,
822 (trx->trx_direct_hs_r_conn_hash.array.max_element - old_elements) *
823 trx->trx_direct_hs_r_conn_hash.array.size_of_element);
824 }
825 } else {
826 uint old_elements = trx->trx_direct_hs_w_conn_hash.array.max_element;
827 #ifdef HASH_UPDATE_WITH_HASH_VALUE
828 if (my_hash_insert_with_hash_value(&trx->trx_direct_hs_w_conn_hash,
829 direct_sql->conn_key_hash_value, (uchar*) conn))
830 #else
831 if (my_hash_insert(&trx->trx_direct_hs_w_conn_hash, (uchar*) conn))
832 #endif
833 {
834 spider_free_conn(conn);
835 *error_num = HA_ERR_OUT_OF_MEM;
836 goto error;
837 }
838 if (trx->trx_direct_hs_w_conn_hash.array.max_element > old_elements)
839 {
840 spider_alloc_calc_mem(spider_current_trx,
841 trx->trx_direct_hs_w_conn_hash,
842 (trx->trx_direct_hs_w_conn_hash.array.max_element - old_elements) *
843 trx->trx_direct_hs_w_conn_hash.array.size_of_element);
844 }
845 }
846 #endif
847 }
848
849 if (conn->queued_connect)
850 {
851 if ((*error_num = spider_db_udf_direct_sql_connect(direct_sql, conn)))
852 goto error;
853 conn->queued_connect = FALSE;
854 }
855
856 if (conn->queued_ping)
857 conn->queued_ping = FALSE;
858
859 DBUG_PRINT("info",("spider conn=%p", conn));
860 DBUG_PRINT("info",("spider conn->conn_kind=%u", conn->conn_kind));
861 DBUG_RETURN(conn);
862
863 error:
864 DBUG_RETURN(NULL);
865 }
866
spider_udf_direct_sql_get_server(SPIDER_DIRECT_SQL * direct_sql)867 int spider_udf_direct_sql_get_server(
868 SPIDER_DIRECT_SQL *direct_sql
869 ) {
870 MEM_ROOT mem_root;
871 int error_num, length;
872 FOREIGN_SERVER *server, server_buf;
873 DBUG_ENTER("spider_udf_direct_sql_get_server");
874 SPD_INIT_ALLOC_ROOT(&mem_root, 65, 0, MYF(MY_WME));
875
876 if (!(server
877 = get_server_by_name(&mem_root, direct_sql->server_name, &server_buf)))
878 {
879 error_num = ER_FOREIGN_SERVER_DOESNT_EXIST;
880 goto error_get_server;
881 }
882
883 if (!direct_sql->tgt_wrapper && server->scheme)
884 {
885 direct_sql->tgt_wrapper_length = strlen(server->scheme);
886 if (!(direct_sql->tgt_wrapper =
887 spider_create_string(server->scheme, direct_sql->tgt_wrapper_length)))
888 {
889 error_num = HA_ERR_OUT_OF_MEM;
890 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
891 goto error;
892 }
893 DBUG_PRINT("info",("spider tgt_wrapper=%s", direct_sql->tgt_wrapper));
894 }
895
896 if (!direct_sql->tgt_host && server->host)
897 {
898 direct_sql->tgt_host_length = strlen(server->host);
899 if (!(direct_sql->tgt_host =
900 spider_create_string(server->host, direct_sql->tgt_host_length)))
901 {
902 error_num = HA_ERR_OUT_OF_MEM;
903 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
904 goto error;
905 }
906 DBUG_PRINT("info",("spider tgt_host=%s", direct_sql->tgt_host));
907 }
908
909 if (direct_sql->tgt_port == -1)
910 {
911 direct_sql->tgt_port = server->port;
912 DBUG_PRINT("info",("spider tgt_port=%ld", direct_sql->tgt_port));
913 }
914
915 if (!direct_sql->tgt_socket && server->socket)
916 {
917 direct_sql->tgt_socket_length = strlen(server->socket);
918 if (!(direct_sql->tgt_socket =
919 spider_create_string(server->socket, direct_sql->tgt_socket_length)))
920 {
921 error_num = HA_ERR_OUT_OF_MEM;
922 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
923 goto error;
924 }
925 DBUG_PRINT("info",("spider tgt_socket=%s", direct_sql->tgt_socket));
926 }
927
928 if (!direct_sql->tgt_default_db_name && server->db &&
929 (length = strlen(server->db)))
930 {
931 direct_sql->tgt_default_db_name_length = length;
932 if (!(direct_sql->tgt_default_db_name =
933 spider_create_string(server->db, length)))
934 {
935 error_num = HA_ERR_OUT_OF_MEM;
936 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
937 goto error;
938 }
939 DBUG_PRINT("info",("spider tgt_default_db_name=%s",
940 direct_sql->tgt_default_db_name));
941 }
942
943 if (!direct_sql->tgt_username && server->username)
944 {
945 direct_sql->tgt_username_length = strlen(server->username);
946 if (!(direct_sql->tgt_username =
947 spider_create_string(server->username, direct_sql->tgt_username_length)))
948 {
949 error_num = HA_ERR_OUT_OF_MEM;
950 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
951 goto error;
952 }
953 DBUG_PRINT("info",("spider tgt_username=%s", direct_sql->tgt_username));
954 }
955
956 if (!direct_sql->tgt_password && server->password)
957 {
958 direct_sql->tgt_password_length = strlen(server->password);
959 if (!(direct_sql->tgt_password =
960 spider_create_string(server->password, direct_sql->tgt_password_length)))
961 {
962 error_num = HA_ERR_OUT_OF_MEM;
963 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
964 goto error;
965 }
966 DBUG_PRINT("info",("spider tgt_password=%s", direct_sql->tgt_password));
967 }
968
969 free_root(&mem_root, MYF(0));
970 DBUG_RETURN(0);
971
972 error_get_server:
973 my_error(error_num, MYF(0), direct_sql->server_name);
974 error:
975 free_root(&mem_root, MYF(0));
976 DBUG_RETURN(error_num);
977 }
978
979 #define SPIDER_PARAM_STR_LEN(name) name ## _length
980 #define SPIDER_PARAM_STR(title_name, param_name) \
981 if (!strncasecmp(tmp_ptr, title_name, title_length)) \
982 { \
983 DBUG_PRINT("info",("spider " title_name " start")); \
984 if (!direct_sql->param_name) \
985 { \
986 if ((direct_sql->param_name = spider_get_string_between_quote( \
987 start_ptr, TRUE, ¶m_string_parse))) \
988 direct_sql->SPIDER_PARAM_STR_LEN(param_name) = \
989 strlen(direct_sql->param_name); \
990 else { \
991 error_num = param_string_parse.print_param_error(); \
992 goto error; \
993 } \
994 DBUG_PRINT("info",("spider " title_name "=%s", direct_sql->param_name)); \
995 } \
996 break; \
997 }
998 #define SPIDER_PARAM_HINT_WITH_MAX(title_name, param_name, check_length, max_size, min_val, max_val) \
999 if (!strncasecmp(tmp_ptr, title_name, check_length)) \
1000 { \
1001 DBUG_PRINT("info",("spider " title_name " start")); \
1002 DBUG_PRINT("info",("spider max_size=%d", max_size)); \
1003 int hint_num = atoi(tmp_ptr + check_length) - 1; \
1004 DBUG_PRINT("info",("spider hint_num=%d", hint_num)); \
1005 DBUG_PRINT("info",("spider direct_sql->param_name=%p", \
1006 direct_sql->param_name)); \
1007 if (direct_sql->param_name) \
1008 { \
1009 if (hint_num < 0 || hint_num >= max_size) \
1010 { \
1011 error_num = param_string_parse.print_param_error(); \
1012 goto error; \
1013 } else if (direct_sql->param_name[hint_num] != -1) \
1014 break; \
1015 char *hint_str = spider_get_string_between_quote(start_ptr, FALSE); \
1016 if (hint_str) \
1017 { \
1018 direct_sql->param_name[hint_num] = atoi(hint_str); \
1019 if (direct_sql->param_name[hint_num] < min_val) \
1020 direct_sql->param_name[hint_num] = min_val; \
1021 else if (direct_sql->param_name[hint_num] > max_val) \
1022 direct_sql->param_name[hint_num] = max_val; \
1023 } else { \
1024 error_num = param_string_parse.print_param_error(); \
1025 goto error; \
1026 } \
1027 DBUG_PRINT("info",("spider " title_name "[%d]=%d", hint_num, \
1028 direct_sql->param_name[hint_num])); \
1029 } else { \
1030 error_num = param_string_parse.print_param_error(); \
1031 goto error; \
1032 } \
1033 break; \
1034 }
1035 #define SPIDER_PARAM_INT_WITH_MAX(title_name, param_name, min_val, max_val) \
1036 if (!strncasecmp(tmp_ptr, title_name, title_length)) \
1037 { \
1038 DBUG_PRINT("info",("spider " title_name " start")); \
1039 if (direct_sql->param_name == -1) \
1040 { \
1041 if ((tmp_ptr2 = spider_get_string_between_quote( \
1042 start_ptr, FALSE))) \
1043 { \
1044 direct_sql->param_name = atoi(tmp_ptr2); \
1045 if (direct_sql->param_name < min_val) \
1046 direct_sql->param_name = min_val; \
1047 else if (direct_sql->param_name > max_val) \
1048 direct_sql->param_name = max_val; \
1049 param_string_parse.set_param_value(tmp_ptr2, \
1050 tmp_ptr2 + \
1051 strlen(tmp_ptr2) + 1); \
1052 } else { \
1053 error_num = param_string_parse.print_param_error(); \
1054 goto error; \
1055 } \
1056 DBUG_PRINT("info",("spider " title_name "=%d", \
1057 (int) direct_sql->param_name)); \
1058 } \
1059 break; \
1060 }
1061 #define SPIDER_PARAM_INT(title_name, param_name, min_val) \
1062 if (!strncasecmp(tmp_ptr, title_name, title_length)) \
1063 { \
1064 DBUG_PRINT("info",("spider " title_name " start")); \
1065 if (direct_sql->param_name == -1) \
1066 { \
1067 if ((tmp_ptr2 = spider_get_string_between_quote( \
1068 start_ptr, FALSE))) \
1069 { \
1070 direct_sql->param_name = atoi(tmp_ptr2); \
1071 if (direct_sql->param_name < min_val) \
1072 direct_sql->param_name = min_val; \
1073 param_string_parse.set_param_value(tmp_ptr2, \
1074 tmp_ptr2 + \
1075 strlen(tmp_ptr2) + 1); \
1076 } else { \
1077 error_num = param_string_parse.print_param_error(); \
1078 goto error; \
1079 } \
1080 DBUG_PRINT("info",("spider " title_name "=%d", direct_sql->param_name)); \
1081 } \
1082 break; \
1083 }
1084 #define SPIDER_PARAM_LONGLONG(title_name, param_name, min_val) \
1085 if (!strncasecmp(tmp_ptr, title_name, title_length)) \
1086 { \
1087 DBUG_PRINT("info",("spider " title_name " start")); \
1088 if (direct_sql->param_name == -1) \
1089 { \
1090 if ((tmp_ptr2 = spider_get_string_between_quote( \
1091 start_ptr, FALSE))) \
1092 { \
1093 direct_sql->param_name = \
1094 my_strtoll10(tmp_ptr2, (char**) NULL, &error_num); \
1095 if (direct_sql->param_name < min_val) \
1096 direct_sql->param_name = min_val; \
1097 param_string_parse.set_param_value(tmp_ptr2, \
1098 tmp_ptr2 + \
1099 strlen(tmp_ptr2) + 1); \
1100 } else { \
1101 error_num = param_string_parse.print_param_error(); \
1102 goto error; \
1103 } \
1104 DBUG_PRINT("info",("spider " title_name "=%lld", \
1105 direct_sql->param_name)); \
1106 } \
1107 break; \
1108 }
1109
spider_udf_parse_direct_sql_param(SPIDER_TRX * trx,SPIDER_DIRECT_SQL * direct_sql,const char * param,int param_length)1110 int spider_udf_parse_direct_sql_param(
1111 SPIDER_TRX *trx,
1112 SPIDER_DIRECT_SQL *direct_sql,
1113 const char *param,
1114 int param_length
1115 ) {
1116 int error_num = 0, roop_count;
1117 char *param_string = NULL;
1118 char *sprit_ptr[2];
1119 char *tmp_ptr, *tmp_ptr2, *start_ptr;
1120 int title_length;
1121 SPIDER_PARAM_STRING_PARSE param_string_parse;
1122 DBUG_ENTER("spider_udf_parse_direct_sql_param");
1123 direct_sql->tgt_port = -1;
1124 direct_sql->tgt_ssl_vsc = -1;
1125 direct_sql->table_loop_mode = -1;
1126 direct_sql->priority = -1;
1127 direct_sql->connect_timeout = -1;
1128 direct_sql->net_read_timeout = -1;
1129 direct_sql->net_write_timeout = -1;
1130 direct_sql->bulk_insert_rows = -1;
1131 direct_sql->connection_channel = -1;
1132 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
1133 direct_sql->access_mode = -1;
1134 #endif
1135 #if MYSQL_VERSION_ID < 50500
1136 #else
1137 direct_sql->use_real_table = -1;
1138 #endif
1139 direct_sql->error_rw_mode = -1;
1140 for (roop_count = 0; roop_count < direct_sql->table_count; roop_count++)
1141 direct_sql->iop[roop_count] = -1;
1142
1143 if (param_length == 0)
1144 goto set_default;
1145 DBUG_PRINT("info",("spider create param_string string"));
1146 if (
1147 !(param_string = spider_create_string(
1148 param,
1149 param_length))
1150 ) {
1151 error_num = HA_ERR_OUT_OF_MEM;
1152 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
1153 goto error_alloc_param_string;
1154 }
1155 DBUG_PRINT("info",("spider param_string=%s", param_string));
1156
1157 sprit_ptr[0] = param_string;
1158 param_string_parse.init(param_string, ER_SPIDER_INVALID_UDF_PARAM_NUM);
1159 while (sprit_ptr[0])
1160 {
1161 if ((sprit_ptr[1] = strchr(sprit_ptr[0], ',')))
1162 {
1163 *sprit_ptr[1] = '\0';
1164 sprit_ptr[1]++;
1165 }
1166 tmp_ptr = sprit_ptr[0];
1167 sprit_ptr[0] = sprit_ptr[1];
1168 while (*tmp_ptr == ' ' || *tmp_ptr == '\r' ||
1169 *tmp_ptr == '\n' || *tmp_ptr == '\t')
1170 tmp_ptr++;
1171
1172 if (*tmp_ptr == '\0')
1173 continue;
1174
1175 title_length = 0;
1176 start_ptr = tmp_ptr;
1177 while (*start_ptr != ' ' && *start_ptr != '\'' &&
1178 *start_ptr != '"' && *start_ptr != '\0' &&
1179 *start_ptr != '\r' && *start_ptr != '\n' &&
1180 *start_ptr != '\t')
1181 {
1182 title_length++;
1183 start_ptr++;
1184 }
1185 param_string_parse.set_param_title(tmp_ptr, tmp_ptr + title_length);
1186
1187 switch (title_length)
1188 {
1189 case 0:
1190 error_num = param_string_parse.print_param_error();
1191 if (error_num)
1192 goto error;
1193 continue;
1194 case 3:
1195 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
1196 SPIDER_PARAM_INT_WITH_MAX("acm", access_mode, 0, 2);
1197 #endif
1198 SPIDER_PARAM_LONGLONG("bir", bulk_insert_rows, 0);
1199 SPIDER_PARAM_INT_WITH_MAX("cch", connection_channel, 0, 63);
1200 SPIDER_PARAM_INT("cto", connect_timeout, 0);
1201 SPIDER_PARAM_STR("dff", tgt_default_file);
1202 SPIDER_PARAM_STR("dfg", tgt_default_group);
1203 SPIDER_PARAM_LONGLONG("prt", priority, 0);
1204 SPIDER_PARAM_INT("rto", net_read_timeout, 0);
1205 SPIDER_PARAM_STR("sca", tgt_ssl_ca);
1206 SPIDER_PARAM_STR("sch", tgt_ssl_cipher);
1207 SPIDER_PARAM_STR("scp", tgt_ssl_capath);
1208 SPIDER_PARAM_STR("scr", tgt_ssl_cert);
1209 SPIDER_PARAM_STR("sky", tgt_ssl_key);
1210 SPIDER_PARAM_STR("srv", server_name);
1211 SPIDER_PARAM_INT_WITH_MAX("svc", tgt_ssl_vsc, 0, 1);
1212 SPIDER_PARAM_INT_WITH_MAX("tlm", table_loop_mode, 0, 2);
1213 #if MYSQL_VERSION_ID < 50500
1214 #else
1215 SPIDER_PARAM_INT_WITH_MAX("urt", use_real_table, 0, 1);
1216 #endif
1217 SPIDER_PARAM_INT("wto", net_write_timeout, 0);
1218 error_num = param_string_parse.print_param_error();
1219 goto error;
1220 case 4:
1221 SPIDER_PARAM_INT_WITH_MAX("erwm", error_rw_mode, 0, 1);
1222 SPIDER_PARAM_STR("host", tgt_host);
1223 SPIDER_PARAM_INT_WITH_MAX("port", tgt_port, 0, 65535);
1224 SPIDER_PARAM_STR("user", tgt_username);
1225 error_num = param_string_parse.print_param_error();
1226 goto error;
1227 case 6:
1228 SPIDER_PARAM_STR("server", server_name);
1229 SPIDER_PARAM_STR("socket", tgt_socket);
1230 SPIDER_PARAM_HINT_WITH_MAX("iop", iop, 3, direct_sql->table_count, 0, 2);
1231 SPIDER_PARAM_STR("ssl_ca", tgt_ssl_ca);
1232 error_num = param_string_parse.print_param_error();
1233 goto error;
1234 case 7:
1235 SPIDER_PARAM_STR("wrapper", tgt_wrapper);
1236 SPIDER_PARAM_STR("ssl_key", tgt_ssl_key);
1237 error_num = param_string_parse.print_param_error();
1238 goto error;
1239 case 8:
1240 SPIDER_PARAM_STR("database", tgt_default_db_name);
1241 SPIDER_PARAM_STR("password", tgt_password);
1242 SPIDER_PARAM_LONGLONG("priority", priority, 0);
1243 SPIDER_PARAM_STR("ssl_cert", tgt_ssl_cert);
1244 error_num = param_string_parse.print_param_error();
1245 goto error;
1246 case 10:
1247 SPIDER_PARAM_STR("ssl_cipher", tgt_ssl_cipher);
1248 SPIDER_PARAM_STR("ssl_capath", tgt_ssl_capath);
1249 error_num = param_string_parse.print_param_error();
1250 goto error;
1251 case 11:
1252 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
1253 SPIDER_PARAM_INT_WITH_MAX("access_mode", access_mode, 0, 2);
1254 #endif
1255 error_num = param_string_parse.print_param_error();
1256 goto error;
1257 case 12:
1258 SPIDER_PARAM_STR("default_file", tgt_default_file);
1259 error_num = param_string_parse.print_param_error();
1260 goto error;
1261 case 13:
1262 SPIDER_PARAM_STR("default_group", tgt_default_group);
1263 SPIDER_PARAM_INT_WITH_MAX("error_rw_mode", error_rw_mode, 0, 1);
1264 error_num = param_string_parse.print_param_error();
1265 goto error;
1266 case 14:
1267 #if MYSQL_VERSION_ID < 50500
1268 #else
1269 SPIDER_PARAM_INT_WITH_MAX("use_real_table", use_real_table, 0, 1);
1270 #endif
1271 error_num = param_string_parse.print_param_error();
1272 goto error;
1273 case 15:
1274 SPIDER_PARAM_INT_WITH_MAX("table_loop_mode", table_loop_mode, 0, 2);
1275 SPIDER_PARAM_INT("connect_timeout", connect_timeout, 0);
1276 error_num = param_string_parse.print_param_error();
1277 goto error;
1278 case 16:
1279 SPIDER_PARAM_LONGLONG("bulk_insert_rows", bulk_insert_rows, 1);
1280 SPIDER_PARAM_INT("net_read_timeout", net_read_timeout, 0);
1281 error_num = param_string_parse.print_param_error();
1282 goto error;
1283 case 17:
1284 SPIDER_PARAM_INT("net_write_timeout", net_write_timeout, 0);
1285 error_num = param_string_parse.print_param_error();
1286 goto error;
1287 case 18:
1288 SPIDER_PARAM_INT_WITH_MAX(
1289 "connection_channel", connection_channel, 0, 63);
1290 error_num = param_string_parse.print_param_error();
1291 goto error;
1292 case 22:
1293 SPIDER_PARAM_INT_WITH_MAX("ssl_verify_server_cert", tgt_ssl_vsc, 0, 1);
1294 error_num = param_string_parse.print_param_error();
1295 goto error;
1296 default:
1297 error_num = param_string_parse.print_param_error();
1298 goto error;
1299 }
1300
1301 /* Verify that the remainder of the parameter value is whitespace */
1302 if ((error_num = param_string_parse.has_extra_parameter_values()))
1303 goto error;
1304 }
1305
1306 set_default:
1307 if ((error_num = spider_udf_set_direct_sql_param_default(
1308 trx,
1309 direct_sql
1310 )))
1311 goto error;
1312
1313 if (param_string)
1314 {
1315 spider_free(spider_current_trx, param_string, MYF(0));
1316 }
1317 DBUG_RETURN(0);
1318
1319 error:
1320 if (param_string)
1321 {
1322 spider_free(spider_current_trx, param_string, MYF(0));
1323 }
1324 error_alloc_param_string:
1325 DBUG_RETURN(error_num);
1326 }
1327
spider_udf_set_direct_sql_param_default(SPIDER_TRX * trx,SPIDER_DIRECT_SQL * direct_sql)1328 int spider_udf_set_direct_sql_param_default(
1329 SPIDER_TRX *trx,
1330 SPIDER_DIRECT_SQL *direct_sql
1331 ) {
1332 int error_num, roop_count;
1333 DBUG_ENTER("spider_udf_set_direct_sql_param_default");
1334 if (direct_sql->server_name)
1335 {
1336 if ((error_num = spider_udf_direct_sql_get_server(direct_sql)))
1337 DBUG_RETURN(error_num);
1338 }
1339
1340 if (!direct_sql->tgt_default_db_name)
1341 {
1342 DBUG_PRINT("info",("spider create default tgt_default_db_name"));
1343 direct_sql->tgt_default_db_name_length = SPIDER_THD_db_length(trx->thd);
1344 if (
1345 !(direct_sql->tgt_default_db_name = spider_create_string(
1346 SPIDER_THD_db_str(trx->thd),
1347 direct_sql->tgt_default_db_name_length))
1348 ) {
1349 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
1350 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
1351 }
1352 }
1353
1354 if (!direct_sql->tgt_wrapper)
1355 {
1356 DBUG_PRINT("info",("spider create default tgt_wrapper"));
1357 direct_sql->tgt_wrapper_length = SPIDER_DB_WRAPPER_LEN;
1358 if (
1359 !(direct_sql->tgt_wrapper = spider_create_string(
1360 SPIDER_DB_WRAPPER_STR,
1361 direct_sql->tgt_wrapper_length))
1362 ) {
1363 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
1364 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
1365 }
1366 }
1367
1368 if (!direct_sql->tgt_host)
1369 {
1370 DBUG_PRINT("info",("spider create default tgt_host"));
1371 direct_sql->tgt_host_length = strlen(my_localhost);
1372 if (
1373 !(direct_sql->tgt_host = spider_create_string(
1374 my_localhost,
1375 direct_sql->tgt_host_length))
1376 ) {
1377 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
1378 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
1379 }
1380 }
1381
1382 if (
1383 !direct_sql->tgt_default_file &&
1384 direct_sql->tgt_default_group &&
1385 (*spd_defaults_file || *spd_defaults_extra_file)
1386 ) {
1387 DBUG_PRINT("info",("spider create default tgt_default_file"));
1388 if (*spd_defaults_extra_file)
1389 {
1390 direct_sql->tgt_default_file_length = strlen(*spd_defaults_extra_file);
1391 if (
1392 !(direct_sql->tgt_default_file = spider_create_string(
1393 *spd_defaults_extra_file,
1394 direct_sql->tgt_default_file_length))
1395 ) {
1396 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
1397 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
1398 }
1399 } else {
1400 direct_sql->tgt_default_file_length = strlen(*spd_defaults_file);
1401 if (
1402 !(direct_sql->tgt_default_file = spider_create_string(
1403 *spd_defaults_file,
1404 direct_sql->tgt_default_file_length))
1405 ) {
1406 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
1407 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
1408 }
1409 }
1410 }
1411
1412 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
1413 if (direct_sql->access_mode == -1)
1414 direct_sql->access_mode = 0;
1415 #endif
1416
1417 if (direct_sql->tgt_port == -1)
1418 {
1419 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
1420 if (direct_sql->access_mode == 1)
1421 direct_sql->tgt_port = 9998;
1422 else if (direct_sql->access_mode == 2)
1423 direct_sql->tgt_port = 9999;
1424 else
1425 #endif
1426 direct_sql->tgt_port = MYSQL_PORT;
1427 }
1428 else if (direct_sql->tgt_port < 0)
1429 direct_sql->tgt_port = 0;
1430 else if (direct_sql->tgt_port > 65535)
1431 direct_sql->tgt_port = 65535;
1432
1433 if (direct_sql->tgt_ssl_vsc == -1)
1434 direct_sql->tgt_ssl_vsc = 0;
1435
1436 if (
1437 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
1438 direct_sql->access_mode == 0 &&
1439 #endif
1440 !direct_sql->tgt_socket &&
1441 !strcmp(direct_sql->tgt_host, my_localhost)
1442 ) {
1443 DBUG_PRINT("info",("spider create default tgt_socket"));
1444 direct_sql->tgt_socket_length = strlen((char *) MYSQL_UNIX_ADDR);
1445 if (
1446 !(direct_sql->tgt_socket = spider_create_string(
1447 (char *) MYSQL_UNIX_ADDR,
1448 direct_sql->tgt_socket_length))
1449 ) {
1450 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
1451 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
1452 }
1453 }
1454
1455 if (direct_sql->table_loop_mode == -1)
1456 direct_sql->table_loop_mode = 0;
1457 if (direct_sql->priority == -1)
1458 direct_sql->priority = 1000000;
1459 if (direct_sql->connect_timeout == -1)
1460 direct_sql->connect_timeout = 6;
1461 if (direct_sql->net_read_timeout == -1)
1462 direct_sql->net_read_timeout = 600;
1463 if (direct_sql->net_write_timeout == -1)
1464 direct_sql->net_write_timeout = 600;
1465 if (direct_sql->bulk_insert_rows == -1)
1466 direct_sql->bulk_insert_rows = 3000;
1467 if (direct_sql->connection_channel == -1)
1468 direct_sql->connection_channel = 0;
1469 #if MYSQL_VERSION_ID < 50500
1470 #else
1471 if (direct_sql->use_real_table == -1)
1472 direct_sql->use_real_table = 0;
1473 #endif
1474 if (direct_sql->error_rw_mode == -1)
1475 direct_sql->error_rw_mode = 0;
1476 for (roop_count = 0; roop_count < direct_sql->table_count; roop_count++)
1477 {
1478 if (direct_sql->iop[roop_count] == -1)
1479 direct_sql->iop[roop_count] = 0;
1480 }
1481 DBUG_RETURN(0);
1482 }
1483
spider_udf_free_direct_sql_alloc(SPIDER_DIRECT_SQL * direct_sql,my_bool bg)1484 void spider_udf_free_direct_sql_alloc(
1485 SPIDER_DIRECT_SQL *direct_sql,
1486 my_bool bg
1487 ) {
1488 SPIDER_BG_DIRECT_SQL *bg_direct_sql;
1489 DBUG_ENTER("spider_udf_free_direct_sql_alloc");
1490 #ifndef WITHOUT_SPIDER_BG_SEARCH
1491 if (bg)
1492 {
1493 pthread_mutex_lock(direct_sql->bg_mutex);
1494 bg_direct_sql = (SPIDER_BG_DIRECT_SQL *) direct_sql->parent;
1495 if (bg_direct_sql->direct_sql == direct_sql)
1496 bg_direct_sql->direct_sql = direct_sql->next;
1497 if (direct_sql->next)
1498 direct_sql->next->prev = direct_sql->prev;
1499 if (direct_sql->prev)
1500 direct_sql->prev->next = direct_sql->next;
1501 pthread_cond_signal(direct_sql->bg_cond);
1502 pthread_mutex_unlock(direct_sql->bg_mutex);
1503 }
1504 #endif
1505 #if MYSQL_VERSION_ID < 50500
1506 #else
1507 if (direct_sql->real_table_used && direct_sql->open_tables_thd)
1508 {
1509 spider_sys_close_table(direct_sql->open_tables_thd,
1510 &direct_sql->open_tables_backup);
1511 }
1512 #endif
1513 if (direct_sql->server_name)
1514 {
1515 spider_free(spider_current_trx, direct_sql->server_name, MYF(0));
1516 }
1517 if (direct_sql->tgt_default_db_name)
1518 {
1519 spider_free(spider_current_trx, direct_sql->tgt_default_db_name, MYF(0));
1520 }
1521 if (direct_sql->tgt_host)
1522 {
1523 spider_free(spider_current_trx, direct_sql->tgt_host, MYF(0));
1524 }
1525 if (direct_sql->tgt_username)
1526 {
1527 spider_free(spider_current_trx, direct_sql->tgt_username, MYF(0));
1528 }
1529 if (direct_sql->tgt_password)
1530 {
1531 spider_free(spider_current_trx, direct_sql->tgt_password, MYF(0));
1532 }
1533 if (direct_sql->tgt_socket)
1534 {
1535 spider_free(spider_current_trx, direct_sql->tgt_socket, MYF(0));
1536 }
1537 if (direct_sql->tgt_wrapper)
1538 {
1539 spider_free(spider_current_trx, direct_sql->tgt_wrapper, MYF(0));
1540 }
1541 if (direct_sql->tgt_ssl_ca)
1542 {
1543 spider_free(spider_current_trx, direct_sql->tgt_ssl_ca, MYF(0));
1544 }
1545 if (direct_sql->tgt_ssl_capath)
1546 {
1547 spider_free(spider_current_trx, direct_sql->tgt_ssl_capath, MYF(0));
1548 }
1549 if (direct_sql->tgt_ssl_cert)
1550 {
1551 spider_free(spider_current_trx, direct_sql->tgt_ssl_cert, MYF(0));
1552 }
1553 if (direct_sql->tgt_ssl_cipher)
1554 {
1555 spider_free(spider_current_trx, direct_sql->tgt_ssl_cipher, MYF(0));
1556 }
1557 if (direct_sql->tgt_ssl_key)
1558 {
1559 spider_free(spider_current_trx, direct_sql->tgt_ssl_key, MYF(0));
1560 }
1561 if (direct_sql->tgt_default_file)
1562 {
1563 spider_free(spider_current_trx, direct_sql->tgt_default_file, MYF(0));
1564 }
1565 if (direct_sql->tgt_default_group)
1566 {
1567 spider_free(spider_current_trx, direct_sql->tgt_default_group, MYF(0));
1568 }
1569 if (direct_sql->conn_key)
1570 {
1571 spider_free(spider_current_trx, direct_sql->conn_key, MYF(0));
1572 }
1573 if (direct_sql->db_names)
1574 {
1575 spider_free(spider_current_trx, direct_sql->db_names, MYF(0));
1576 }
1577 spider_free(spider_current_trx, direct_sql, MYF(0));
1578 DBUG_VOID_RETURN;
1579 }
1580
spider_direct_sql_body(UDF_INIT * initid,UDF_ARGS * args,char * is_null,char * error,my_bool bg)1581 long long spider_direct_sql_body(
1582 UDF_INIT *initid,
1583 UDF_ARGS *args,
1584 char *is_null,
1585 char *error,
1586 my_bool bg
1587 ) {
1588 int error_num, roop_count;
1589 SPIDER_DIRECT_SQL *direct_sql = NULL, *tmp_direct_sql;
1590 THD *thd = current_thd;
1591 SPIDER_TRX *trx;
1592 SPIDER_CONN *conn;
1593 char *sql;
1594 TABLE_LIST table_list;
1595 SPIDER_BG_DIRECT_SQL *bg_direct_sql;
1596 #if MYSQL_VERSION_ID < 50500
1597 #else
1598 TABLE_LIST *real_table_list_last = NULL;
1599 uint use_real_table = 0;
1600 #endif
1601 DBUG_ENTER("spider_direct_sql_body");
1602 SPIDER_BACKUP_DASTATUS;
1603 if (!(direct_sql = (SPIDER_DIRECT_SQL *)
1604 spider_bulk_malloc(spider_current_trx, 34, MYF(MY_WME | MY_ZEROFILL),
1605 &direct_sql, sizeof(SPIDER_DIRECT_SQL),
1606 &sql, sizeof(char) * args->lengths[0],
1607 NullS))
1608 ) {
1609 error_num = HA_ERR_OUT_OF_MEM;
1610 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
1611 goto error;
1612 }
1613 #ifndef WITHOUT_SPIDER_BG_SEARCH
1614 if (bg)
1615 {
1616 bg_direct_sql = (SPIDER_BG_DIRECT_SQL *) initid->ptr;
1617 pthread_mutex_lock(&bg_direct_sql->bg_mutex);
1618 tmp_direct_sql = (SPIDER_DIRECT_SQL *) bg_direct_sql->direct_sql;
1619 bg_direct_sql->direct_sql = direct_sql;
1620 if (tmp_direct_sql)
1621 {
1622 tmp_direct_sql->prev = direct_sql;
1623 direct_sql->next = tmp_direct_sql;
1624 }
1625 pthread_mutex_unlock(&bg_direct_sql->bg_mutex);
1626 direct_sql->bg_mutex = &bg_direct_sql->bg_mutex;
1627 direct_sql->bg_cond = &bg_direct_sql->bg_cond;
1628 direct_sql->parent = bg_direct_sql;
1629 bg_direct_sql->called_cnt++;
1630 }
1631 #endif
1632 if (!(trx = spider_get_trx(thd, TRUE, &error_num)))
1633 {
1634 if (error_num == HA_ERR_OUT_OF_MEM)
1635 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
1636 goto error;
1637 }
1638 direct_sql->trx = trx;
1639
1640 if (args->args[1])
1641 {
1642 if ((error_num = spider_udf_direct_sql_create_table_list(
1643 direct_sql,
1644 args->args[1],
1645 args->lengths[1]
1646 ))) {
1647 if (error_num == HA_ERR_OUT_OF_MEM)
1648 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
1649 goto error;
1650 }
1651 } else {
1652 if ((error_num = spider_udf_direct_sql_create_table_list(
1653 direct_sql,
1654 (char *) "",
1655 0
1656 ))) {
1657 if (error_num == HA_ERR_OUT_OF_MEM)
1658 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
1659 goto error;
1660 }
1661 }
1662 if (args->args[2])
1663 {
1664 if ((error_num = spider_udf_parse_direct_sql_param(
1665 trx,
1666 direct_sql,
1667 args->args[2],
1668 args->lengths[2]
1669 ))) {
1670 goto error;
1671 }
1672 } else {
1673 if ((error_num = spider_udf_parse_direct_sql_param(
1674 trx,
1675 direct_sql,
1676 "",
1677 0
1678 ))) {
1679 goto error;
1680 }
1681 }
1682 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
1683 if (trx->trx_start && direct_sql->access_mode != 1)
1684 {
1685 #endif
1686 trx->updated_in_this_trx = TRUE;
1687 DBUG_PRINT("info",("spider trx->updated_in_this_trx=TRUE"));
1688 #if defined(HS_HAS_SQLCOM) && defined(HAVE_HANDLERSOCKET)
1689 }
1690 #endif
1691 #if MYSQL_VERSION_ID < 50500
1692 #else
1693 use_real_table = spider_param_udf_ds_use_real_table(thd,
1694 direct_sql->use_real_table);
1695 #endif
1696 for (roop_count = 0; roop_count < direct_sql->table_count; roop_count++)
1697 {
1698 #ifdef SPIDER_NEED_INIT_ONE_TABLE_FOR_FIND_TEMPORARY_TABLE
1699 #ifdef SPIDER_use_LEX_CSTRING_for_database_tablename_alias
1700 LEX_CSTRING db_name =
1701 {
1702 direct_sql->db_names[roop_count],
1703 strlen(direct_sql->db_names[roop_count])
1704 };
1705 LEX_CSTRING tbl_name =
1706 {
1707 direct_sql->table_names[roop_count],
1708 strlen(direct_sql->table_names[roop_count])
1709 };
1710 table_list.init_one_table(&db_name, &tbl_name, 0, TL_WRITE);
1711 #else
1712 table_list.init_one_table(direct_sql->db_names[roop_count],
1713 strlen(direct_sql->db_names[roop_count]),
1714 direct_sql->table_names[roop_count],
1715 strlen(direct_sql->table_names[roop_count]),
1716 direct_sql->table_names[roop_count], TL_WRITE);
1717 #endif
1718 #else
1719 SPIDER_TABLE_LIST_db_str(&table_list) = direct_sql->db_names[roop_count];
1720 SPIDER_TABLE_LIST_table_name_str(&table_list) =
1721 direct_sql->table_names[roop_count];
1722 #endif
1723 if (!(direct_sql->tables[roop_count] =
1724 spider_find_temporary_table(thd, &table_list)))
1725 {
1726 #if MYSQL_VERSION_ID < 50500
1727 #else
1728 if (!use_real_table)
1729 {
1730 #endif
1731 error_num = ER_SPIDER_UDF_TMP_TABLE_NOT_FOUND_NUM;
1732 my_printf_error(ER_SPIDER_UDF_TMP_TABLE_NOT_FOUND_NUM,
1733 ER_SPIDER_UDF_TMP_TABLE_NOT_FOUND_STR,
1734 MYF(0), SPIDER_TABLE_LIST_db_str(&table_list),
1735 SPIDER_TABLE_LIST_table_name_str(&table_list));
1736 goto error;
1737 #if MYSQL_VERSION_ID < 50500
1738 #else
1739 }
1740 TABLE_LIST *tables = &direct_sql->table_list[roop_count];
1741 #ifdef SPIDER_use_LEX_CSTRING_for_database_tablename_alias
1742 table_list.init_one_table(
1743 &table_list.db, &table_list.table_name, 0, TL_WRITE);
1744 #else
1745 tables->init_one_table(
1746 SPIDER_TABLE_LIST_db_str(&table_list),
1747 SPIDER_TABLE_LIST_db_length(&table_list),
1748 SPIDER_TABLE_LIST_table_name_str(&table_list),
1749 SPIDER_TABLE_LIST_table_name_length(&table_list),
1750 SPIDER_TABLE_LIST_table_name_str(&table_list), TL_WRITE);
1751 #endif
1752 tables->mdl_request.init(MDL_key::TABLE,
1753 SPIDER_TABLE_LIST_db_str(&table_list),
1754 SPIDER_TABLE_LIST_table_name_str(&table_list),
1755 MDL_SHARED_WRITE, MDL_TRANSACTION);
1756 if (!direct_sql->table_list_first)
1757 {
1758 direct_sql->table_list_first = tables;
1759 } else {
1760 real_table_list_last->next_global = tables;
1761 }
1762 real_table_list_last = tables;
1763 spider_set_bit(direct_sql->real_table_bitmap, roop_count);
1764 direct_sql->real_table_used = TRUE;
1765 #endif
1766 }
1767 }
1768 if ((error_num = spider_udf_direct_sql_create_conn_key(direct_sql)))
1769 {
1770 if (error_num == HA_ERR_OUT_OF_MEM)
1771 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
1772 goto error;
1773 }
1774 if (!(conn = spider_udf_direct_sql_get_conn(direct_sql, trx, &error_num)))
1775 {
1776 if (error_num == HA_ERR_OUT_OF_MEM)
1777 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
1778 goto error;
1779 }
1780 conn->error_mode = 0;
1781 direct_sql->conn = conn;
1782 if ((error_num = spider_db_udf_check_and_set_set_names(trx)))
1783 {
1784 if (error_num == HA_ERR_OUT_OF_MEM)
1785 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
1786 goto error;
1787 }
1788 if (args->args[0])
1789 {
1790 direct_sql->sql_length = args->lengths[0];
1791 memcpy(sql, args->args[0], direct_sql->sql_length);
1792 } else
1793 direct_sql->sql_length = 0;
1794 direct_sql->sql = sql;
1795
1796 #ifndef WITHOUT_SPIDER_BG_SEARCH
1797 if (bg)
1798 {
1799 if ((error_num = spider_udf_bg_direct_sql(direct_sql)))
1800 {
1801 if (error_num == HA_ERR_OUT_OF_MEM)
1802 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
1803 goto error;
1804 }
1805 } else {
1806 #endif
1807 if (conn->bg_init)
1808 pthread_mutex_lock(&conn->bg_conn_mutex);
1809 if ((error_num = spider_db_udf_direct_sql(direct_sql)))
1810 {
1811 if (conn->bg_init)
1812 pthread_mutex_unlock(&conn->bg_conn_mutex);
1813 if (direct_sql->modified_non_trans_table)
1814 thd->transaction.stmt.modified_non_trans_table = TRUE;
1815 if (error_num == HA_ERR_OUT_OF_MEM)
1816 my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
1817 goto error;
1818 }
1819 if (conn->bg_init)
1820 pthread_mutex_unlock(&conn->bg_conn_mutex);
1821 if (direct_sql->modified_non_trans_table)
1822 thd->transaction.stmt.modified_non_trans_table = TRUE;
1823 #ifndef WITHOUT_SPIDER_BG_SEARCH
1824 }
1825 if (!bg)
1826 {
1827 #endif
1828 spider_udf_free_direct_sql_alloc(direct_sql, FALSE);
1829 #ifndef WITHOUT_SPIDER_BG_SEARCH
1830 }
1831 #endif
1832 DBUG_RETURN(1);
1833
1834 error:
1835 if (direct_sql)
1836 {
1837 if (
1838 direct_sql->error_rw_mode &&
1839 spider_db_conn_is_network_error(error_num)
1840 ) {
1841 SPIDER_RESTORE_DASTATUS;
1842 spider_udf_free_direct_sql_alloc(direct_sql, bg);
1843 DBUG_RETURN(1);
1844 }
1845 spider_udf_free_direct_sql_alloc(direct_sql, bg);
1846 }
1847 *error = 1;
1848 DBUG_RETURN(0);
1849 }
1850
1851 my_bool spider_direct_sql_init_body(
1852 UDF_INIT *initid,
1853 UDF_ARGS *args,
1854 char *message,
1855 my_bool bg
1856 ) {
1857 SPIDER_BG_DIRECT_SQL *bg_direct_sql;
1858 DBUG_ENTER("spider_direct_sql_init_body");
1859 if (args->arg_count != 3)
1860 {
1861 strcpy(message, "spider_(bg)_direct_sql() requires 3 arguments");
1862 goto error;
1863 }
1864 if (
1865 args->arg_type[0] != STRING_RESULT ||
1866 args->arg_type[1] != STRING_RESULT ||
1867 args->arg_type[2] != STRING_RESULT
1868 ) {
1869 strcpy(message, "spider_(bg)_direct_sql() requires string arguments");
1870 goto error;
1871 }
1872 #ifndef WITHOUT_SPIDER_BG_SEARCH
1873 if (bg)
1874 {
1875 if (!(bg_direct_sql = (SPIDER_BG_DIRECT_SQL *)
1876 spider_malloc(spider_current_trx, 10, sizeof(SPIDER_BG_DIRECT_SQL),
1877 MYF(MY_WME | MY_ZEROFILL)))
1878 ) {
1879 strcpy(message, "spider_bg_direct_sql() out of memory");
1880 goto error;
1881 }
1882 #if MYSQL_VERSION_ID < 50500
1883 if (pthread_mutex_init(&bg_direct_sql->bg_mutex, MY_MUTEX_INIT_FAST))
1884 #else
1885 if (mysql_mutex_init(spd_key_mutex_bg_direct_sql,
1886 &bg_direct_sql->bg_mutex, MY_MUTEX_INIT_FAST))
1887 #endif
1888 {
1889 strcpy(message, "spider_bg_direct_sql() out of memory");
1890 goto error_mutex_init;
1891 }
1892 #if MYSQL_VERSION_ID < 50500
1893 if (pthread_cond_init(&bg_direct_sql->bg_cond, NULL))
1894 #else
1895 if (mysql_cond_init(spd_key_cond_bg_direct_sql,
1896 &bg_direct_sql->bg_cond, NULL))
1897 #endif
1898 {
1899 strcpy(message, "spider_bg_direct_sql() out of memory");
1900 goto error_cond_init;
1901 }
1902 initid->ptr = (char *) bg_direct_sql;
1903 }
1904 #endif
1905 DBUG_RETURN(FALSE);
1906
1907 #ifndef WITHOUT_SPIDER_BG_SEARCH
1908 error_cond_init:
1909 pthread_mutex_destroy(&bg_direct_sql->bg_mutex);
1910 error_mutex_init:
1911 spider_free(spider_current_trx, bg_direct_sql, MYF(0));
1912 #endif
1913 error:
1914 DBUG_RETURN(TRUE);
1915 }
1916
1917 void spider_direct_sql_deinit_body(
1918 UDF_INIT *initid
1919 ) {
1920 SPIDER_BG_DIRECT_SQL *bg_direct_sql = (SPIDER_BG_DIRECT_SQL *) initid->ptr;
1921 DBUG_ENTER("spider_direct_sql_deinit_body");
1922 if (bg_direct_sql)
1923 {
1924 pthread_mutex_lock(&bg_direct_sql->bg_mutex);
1925 while (bg_direct_sql->direct_sql)
1926 pthread_cond_wait(&bg_direct_sql->bg_cond, &bg_direct_sql->bg_mutex);
1927 pthread_mutex_unlock(&bg_direct_sql->bg_mutex);
1928 if (bg_direct_sql->modified_non_trans_table)
1929 {
1930 THD *thd = current_thd;
1931 thd->transaction.stmt.modified_non_trans_table = TRUE;
1932 }
1933 pthread_cond_destroy(&bg_direct_sql->bg_cond);
1934 pthread_mutex_destroy(&bg_direct_sql->bg_mutex);
1935 spider_free(spider_current_trx, bg_direct_sql, MYF(0));
1936 }
1937 DBUG_VOID_RETURN;
1938 }
1939
1940 #ifndef WITHOUT_SPIDER_BG_SEARCH
1941 void spider_direct_sql_bg_start(
1942 UDF_INIT *initid
1943 ) {
1944 SPIDER_BG_DIRECT_SQL *bg_direct_sql = (SPIDER_BG_DIRECT_SQL *) initid->ptr;
1945 DBUG_ENTER("spider_direct_sql_bg_start");
1946 bg_direct_sql->called_cnt = 0;
1947 bg_direct_sql->bg_error = 0;
1948 DBUG_VOID_RETURN;
1949 }
1950
1951 long long spider_direct_sql_bg_end(
1952 UDF_INIT *initid
1953 ) {
1954 THD *thd = current_thd;
1955 SPIDER_BG_DIRECT_SQL *bg_direct_sql = (SPIDER_BG_DIRECT_SQL *) initid->ptr;
1956 DBUG_ENTER("spider_direct_sql_bg_end");
1957 pthread_mutex_lock(&bg_direct_sql->bg_mutex);
1958 while (bg_direct_sql->direct_sql)
1959 pthread_cond_wait(&bg_direct_sql->bg_cond, &bg_direct_sql->bg_mutex);
1960 pthread_mutex_unlock(&bg_direct_sql->bg_mutex);
1961 if (bg_direct_sql->modified_non_trans_table)
1962 thd->transaction.stmt.modified_non_trans_table = TRUE;
1963 if (bg_direct_sql->bg_error)
1964 {
1965 my_message(bg_direct_sql->bg_error, bg_direct_sql->bg_error_msg, MYF(0));
1966 DBUG_RETURN(0);
1967 }
1968 DBUG_RETURN(bg_direct_sql->called_cnt);
1969 }
1970
1971 int spider_udf_bg_direct_sql(
1972 SPIDER_DIRECT_SQL *direct_sql
1973 ) {
1974 int error_num;
1975 SPIDER_CONN *conn = direct_sql->conn;
1976 DBUG_ENTER("spider_udf_bg_direct_sql");
1977 if ((error_num = spider_create_conn_thread(conn)))
1978 DBUG_RETURN(error_num);
1979 if (!pthread_mutex_trylock(&conn->bg_conn_mutex))
1980 {
1981 DBUG_PRINT("info",("spider get bg_conn_mutex"));
1982 conn->bg_target = direct_sql;
1983 conn->bg_direct_sql = TRUE;
1984 conn->bg_caller_sync_wait = TRUE;
1985 pthread_mutex_lock(&conn->bg_conn_sync_mutex);
1986 pthread_cond_signal(&conn->bg_conn_cond);
1987 pthread_mutex_unlock(&conn->bg_conn_mutex);
1988 pthread_cond_wait(&conn->bg_conn_sync_cond, &conn->bg_conn_sync_mutex);
1989 pthread_mutex_unlock(&conn->bg_conn_sync_mutex);
1990 conn->bg_caller_sync_wait = FALSE;
1991 } else {
1992 DBUG_PRINT("info",("spider get put job stack"));
1993 bool bg_get_job_stack = FALSE;
1994 pthread_mutex_lock(&conn->bg_job_stack_mutex);
1995 uint old_elements = conn->bg_job_stack.max_element;
1996 if (insert_dynamic(&conn->bg_job_stack, (uchar *) &direct_sql))
1997 {
1998 pthread_mutex_unlock(&conn->bg_job_stack_mutex);
1999 DBUG_RETURN(HA_ERR_OUT_OF_MEM);
2000 }
2001 if (conn->bg_job_stack.max_element > old_elements)
2002 {
2003 spider_alloc_calc_mem(spider_current_trx,
2004 conn->bg_job_stack,
2005 (conn->bg_job_stack.max_element - old_elements) *
2006 conn->bg_job_stack.size_of_element);
2007 }
2008 if (!conn->bg_get_job_stack_off)
2009 bg_get_job_stack = TRUE;
2010 pthread_mutex_unlock(&conn->bg_job_stack_mutex);
2011 if (bg_get_job_stack)
2012 {
2013 DBUG_PRINT("info",("spider get bg_conn_mutex"));
2014 pthread_mutex_lock(&conn->bg_conn_mutex);
2015 conn->bg_target = NULL;
2016 conn->bg_get_job_stack = TRUE;
2017 conn->bg_direct_sql = TRUE;
2018 conn->bg_caller_sync_wait = TRUE;
2019 pthread_mutex_lock(&conn->bg_conn_sync_mutex);
2020 pthread_cond_signal(&conn->bg_conn_cond);
2021 pthread_mutex_unlock(&conn->bg_conn_mutex);
2022 pthread_cond_wait(&conn->bg_conn_sync_cond, &conn->bg_conn_sync_mutex);
2023 pthread_mutex_unlock(&conn->bg_conn_sync_mutex);
2024 conn->bg_caller_sync_wait = FALSE;
2025 }
2026 }
2027 DBUG_RETURN(0);
2028 }
2029 #endif
2030