diff options
39 files changed, 710 insertions, 381 deletions
diff --git a/mysql-test/include/ddl_i18n.check_views.inc b/mysql-test/include/ddl_i18n.check_views.inc index 727f3506e4a..db3ad02f459 100644 --- a/mysql-test/include/ddl_i18n.check_views.inc +++ b/mysql-test/include/ddl_i18n.check_views.inc @@ -9,6 +9,10 @@ SHOW CREATE VIEW v1| SHOW CREATE VIEW v2| +--echo + +SHOW CREATE VIEW v3| + # - Check INFORMATION_SCHEMA; --echo @@ -20,6 +24,10 @@ SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v1'| SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v2'| +--echo + +SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v3'| + # - Execute the views; --echo @@ -30,3 +38,7 @@ SELECT COLLATION(c1), COLLATION(c2) FROM v1| --echo SELECT COLLATION(c1) FROM v2| + +--echo + +SELECT * FROM v3| diff --git a/mysql-test/r/ddl_i18n_koi8r.result b/mysql-test/r/ddl_i18n_koi8r.result index dfdc8fd463e..34cea2a5a7d 100644 --- a/mysql-test/r/ddl_i18n_koi8r.result +++ b/mysql-test/r/ddl_i18n_koi8r.result @@ -16,6 +16,8 @@ FROM t1| CREATE VIEW v2 AS SELECT _utf8'теÑÑ‚' as c1| +CREATE VIEW v3 AS SELECT _utf8'теÑÑ‚'| + SHOW CREATE VIEW v1| @@ -26,15 +28,22 @@ SHOW CREATE VIEW v2| View Create View character_set_client collation_connection v2 CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v2` AS select _utf8'теÑÑ‚' AS `c1` koi8r koi8r_general_ci +SHOW CREATE VIEW v3| +View Create View character_set_client collation_connection +v3 CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v3` AS select _utf8'теÑÑ‚' AS `ÔÅÓÔ` koi8r koi8r_general_ci + SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v1'| TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION -NULL mysqltest1 v1 SELECT 'ÔÅÓÔ' AS c1, ËÏÌ AS c2 -FROM t1 NONE YES root@localhost DEFINER koi8r koi8r_general_ci +NULL mysqltest1 v1 select 'ÔÅÓÔ' AS `c1`,`mysqltest1`.`t1`.`ËÏÌ` AS `c2` from `mysqltest1`.`t1` NONE YES root@localhost DEFINER koi8r koi8r_general_ci SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v2'| TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION -NULL mysqltest1 v2 SELECT 'ÔÅÓÔ' as c1 NONE NO root@localhost DEFINER koi8r koi8r_general_ci +NULL mysqltest1 v2 select 'ÔÅÓÔ' AS `c1` NONE NO root@localhost DEFINER koi8r koi8r_general_ci + +SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v3'| +TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION +NULL mysqltest1 v3 select 'ÔÅÓÔ' AS `ÔÅÓÔ` NONE NO root@localhost DEFINER koi8r koi8r_general_ci SELECT COLLATION(c1), COLLATION(c2) FROM v1| @@ -45,6 +54,10 @@ SELECT COLLATION(c1) FROM v2| COLLATION(c1) utf8_general_ci +SELECT * FROM v3| +ÔÅÓÔ +ÔÅÓÔ + ALTER DATABASE mysqltest1 COLLATE cp866_general_ci| @@ -54,6 +67,7 @@ SET @@character_set_results= cp1251| SET @@collation_connection= cp1251_general_ci| SELECT * FROM mysqltest1.v1| SELECT * FROM mysqltest1.v2| +SELECT * FROM mysqltest1.v3| use mysqltest1| set names koi8r| @@ -66,15 +80,22 @@ SHOW CREATE VIEW v2| View Create View character_set_client collation_connection v2 CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v2` AS select _utf8'теÑÑ‚' AS `c1` koi8r koi8r_general_ci +SHOW CREATE VIEW v3| +View Create View character_set_client collation_connection +v3 CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v3` AS select _utf8'теÑÑ‚' AS `ÔÅÓÔ` koi8r koi8r_general_ci + SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v1'| TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION -NULL mysqltest1 v1 SELECT 'ÔÅÓÔ' AS c1, ËÏÌ AS c2 -FROM t1 NONE YES root@localhost DEFINER koi8r koi8r_general_ci +NULL mysqltest1 v1 select 'ÔÅÓÔ' AS `c1`,`mysqltest1`.`t1`.`ËÏÌ` AS `c2` from `mysqltest1`.`t1` NONE YES root@localhost DEFINER koi8r koi8r_general_ci SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v2'| TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION -NULL mysqltest1 v2 SELECT 'ÔÅÓÔ' as c1 NONE NO root@localhost DEFINER koi8r koi8r_general_ci +NULL mysqltest1 v2 select 'ÔÅÓÔ' AS `c1` NONE NO root@localhost DEFINER koi8r koi8r_general_ci + +SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v3'| +TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION +NULL mysqltest1 v3 select 'ÔÅÓÔ' AS `ÔÅÓÔ` NONE NO root@localhost DEFINER koi8r koi8r_general_ci SELECT COLLATION(c1), COLLATION(c2) FROM v1| @@ -85,6 +106,10 @@ SELECT COLLATION(c1) FROM v2| COLLATION(c1) utf8_general_ci +SELECT * FROM v3| +ÔÅÓÔ +ÔÅÓÔ + ---> Dumping mysqltest1 to ddl_i18n_koi8r.views.mysqltest1.sql @@ -99,6 +124,7 @@ SET @@character_set_results= cp1251| SET @@collation_connection= cp1251_general_ci| SELECT * FROM mysqltest1.v1| SELECT * FROM mysqltest1.v2| +SELECT * FROM mysqltest1.v3| use mysqltest1| set names koi8r| @@ -111,15 +137,23 @@ SHOW CREATE VIEW v2| View Create View character_set_client collation_connection v2 CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v2` AS select _utf8'теÑÑ‚' AS `c1` koi8r koi8r_general_ci +SHOW CREATE VIEW v3| +View Create View character_set_client collation_connection +v3 CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v3` AS select _utf8'теÑÑ‚' AS `ÔÅÓÔ` koi8r koi8r_general_ci + SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v1'| TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION -NULL mysqltest1 v1 select 'ÔÅÓÔ' AS `c1`,`t1`.`ËÏÌ` AS `c2` from `t1` NONE YES root@localhost DEFINER koi8r koi8r_general_ci +NULL mysqltest1 v1 select 'ÔÅÓÔ' AS `c1`,`mysqltest1`.`t1`.`ËÏÌ` AS `c2` from `mysqltest1`.`t1` NONE YES root@localhost DEFINER koi8r koi8r_general_ci SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v2'| TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION NULL mysqltest1 v2 select 'ÔÅÓÔ' AS `c1` NONE NO root@localhost DEFINER koi8r koi8r_general_ci +SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v3'| +TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION +NULL mysqltest1 v3 select 'ÔÅÓÔ' AS `ÔÅÓÔ` NONE NO root@localhost DEFINER koi8r koi8r_general_ci + SELECT COLLATION(c1), COLLATION(c2) FROM v1| COLLATION(c1) COLLATION(c2) @@ -129,6 +163,10 @@ SELECT COLLATION(c1) FROM v2| COLLATION(c1) utf8_general_ci +SELECT * FROM v3| +ÔÅÓÔ +ÔÅÓÔ + ---> connection: default use test| DROP DATABASE mysqltest1| diff --git a/mysql-test/r/ddl_i18n_utf8.result b/mysql-test/r/ddl_i18n_utf8.result index c009265d384..cf5dac3dc7c 100644 --- a/mysql-test/r/ddl_i18n_utf8.result +++ b/mysql-test/r/ddl_i18n_utf8.result @@ -16,6 +16,8 @@ FROM t1| CREATE VIEW v2 AS SELECT _koi8r'ÔÅÓÔ' as c1| +CREATE VIEW v3 AS SELECT _koi8r'ÔÅÓÔ'| + SHOW CREATE VIEW v1| @@ -26,15 +28,22 @@ SHOW CREATE VIEW v2| View Create View character_set_client collation_connection v2 CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v2` AS select _koi8r'ÔÅÓÔ' AS `c1` utf8 utf8_general_ci +SHOW CREATE VIEW v3| +View Create View character_set_client collation_connection +v3 CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v3` AS select _koi8r'ÔÅÓÔ' AS `теÑÑ‚` utf8 utf8_general_ci + SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v1'| TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION -NULL mysqltest1 v1 SELECT 'теÑÑ‚' AS c1, кол AS c2 -FROM t1 NONE YES root@localhost DEFINER utf8 utf8_general_ci +NULL mysqltest1 v1 select 'теÑÑ‚' AS `c1`,`mysqltest1`.`t1`.`кол` AS `c2` from `mysqltest1`.`t1` NONE YES root@localhost DEFINER utf8 utf8_general_ci SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v2'| TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION -NULL mysqltest1 v2 SELECT 'теÑÑ‚' as c1 NONE NO root@localhost DEFINER utf8 utf8_general_ci +NULL mysqltest1 v2 select 'теÑÑ‚' AS `c1` NONE NO root@localhost DEFINER utf8 utf8_general_ci + +SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v3'| +TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION +NULL mysqltest1 v3 select 'теÑÑ‚' AS `теÑÑ‚` NONE NO root@localhost DEFINER utf8 utf8_general_ci SELECT COLLATION(c1), COLLATION(c2) FROM v1| @@ -45,6 +54,10 @@ SELECT COLLATION(c1) FROM v2| COLLATION(c1) koi8r_general_ci +SELECT * FROM v3| +теÑÑ‚ +теÑÑ‚ + ALTER DATABASE mysqltest1 COLLATE cp866_general_ci| @@ -54,6 +67,7 @@ SET @@character_set_results= cp1251| SET @@collation_connection= cp1251_general_ci| SELECT * FROM mysqltest1.v1| SELECT * FROM mysqltest1.v2| +SELECT * FROM mysqltest1.v3| use mysqltest1| set names utf8| @@ -66,15 +80,22 @@ SHOW CREATE VIEW v2| View Create View character_set_client collation_connection v2 CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v2` AS select _koi8r'ÔÅÓÔ' AS `c1` utf8 utf8_general_ci +SHOW CREATE VIEW v3| +View Create View character_set_client collation_connection +v3 CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v3` AS select _koi8r'ÔÅÓÔ' AS `теÑÑ‚` utf8 utf8_general_ci + SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v1'| TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION -NULL mysqltest1 v1 SELECT 'теÑÑ‚' AS c1, кол AS c2 -FROM t1 NONE YES root@localhost DEFINER utf8 utf8_general_ci +NULL mysqltest1 v1 select 'теÑÑ‚' AS `c1`,`mysqltest1`.`t1`.`кол` AS `c2` from `mysqltest1`.`t1` NONE YES root@localhost DEFINER utf8 utf8_general_ci SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v2'| TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION -NULL mysqltest1 v2 SELECT 'теÑÑ‚' as c1 NONE NO root@localhost DEFINER utf8 utf8_general_ci +NULL mysqltest1 v2 select 'теÑÑ‚' AS `c1` NONE NO root@localhost DEFINER utf8 utf8_general_ci + +SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v3'| +TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION +NULL mysqltest1 v3 select 'теÑÑ‚' AS `теÑÑ‚` NONE NO root@localhost DEFINER utf8 utf8_general_ci SELECT COLLATION(c1), COLLATION(c2) FROM v1| @@ -85,6 +106,10 @@ SELECT COLLATION(c1) FROM v2| COLLATION(c1) koi8r_general_ci +SELECT * FROM v3| +теÑÑ‚ +теÑÑ‚ + ---> Dumping mysqltest1 to ddl_i18n_utf8views.mysqltest1.sql @@ -99,6 +124,7 @@ SET @@character_set_results= cp1251| SET @@collation_connection= cp1251_general_ci| SELECT * FROM mysqltest1.v1| SELECT * FROM mysqltest1.v2| +SELECT * FROM mysqltest1.v3| use mysqltest1| set names utf8| @@ -111,15 +137,23 @@ SHOW CREATE VIEW v2| View Create View character_set_client collation_connection v2 CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v2` AS select _koi8r'ÔÅÓÔ' AS `c1` utf8 utf8_general_ci +SHOW CREATE VIEW v3| +View Create View character_set_client collation_connection +v3 CREATE ALGORITHM=UNDEFINED DEFINER=`root`@`localhost` SQL SECURITY DEFINER VIEW `v3` AS select _koi8r'ÔÅÓÔ' AS `теÑÑ‚` utf8 utf8_general_ci + SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v1'| TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION -NULL mysqltest1 v1 select 'теÑÑ‚' AS `c1`,`t1`.`кол` AS `c2` from `t1` NONE YES root@localhost DEFINER utf8 utf8_general_ci +NULL mysqltest1 v1 select 'теÑÑ‚' AS `c1`,`mysqltest1`.`t1`.`кол` AS `c2` from `mysqltest1`.`t1` NONE YES root@localhost DEFINER utf8 utf8_general_ci SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v2'| TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION NULL mysqltest1 v2 select 'теÑÑ‚' AS `c1` NONE NO root@localhost DEFINER utf8 utf8_general_ci +SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE table_name = 'v3'| +TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION +NULL mysqltest1 v3 select 'теÑÑ‚' AS `теÑÑ‚` NONE NO root@localhost DEFINER utf8 utf8_general_ci + SELECT COLLATION(c1), COLLATION(c2) FROM v1| COLLATION(c1) COLLATION(c2) @@ -129,6 +163,10 @@ SELECT COLLATION(c1) FROM v2| COLLATION(c1) koi8r_general_ci +SELECT * FROM v3| +теÑÑ‚ +теÑÑ‚ + ---> connection: default use test| DROP DATABASE mysqltest1| diff --git a/mysql-test/r/information_schema.result b/mysql-test/r/information_schema.result index 708d8ab027d..7f4efa32dc2 100644 --- a/mysql-test/r/information_schema.result +++ b/mysql-test/r/information_schema.result @@ -387,15 +387,11 @@ show keys from v4; Table Non_unique Key_name Seq_in_index Column_name Collation Cardinality Sub_part Packed Null Index_type Comment select * from information_schema.views where TABLE_NAME like "v%"; TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION -NULL test v0 select schema_name from information_schema.schemata NONE NO root@localhost DEFINER latin1 latin1_swedish_ci -NULL test v1 select table_name from information_schema.tables -where table_name="v1" NONE NO root@localhost DEFINER latin1 latin1_swedish_ci -NULL test v2 select column_name from information_schema.columns -where table_name="v2" NONE NO root@localhost DEFINER latin1 latin1_swedish_ci -NULL test v3 select CHARACTER_SET_NAME from information_schema.character_sets -where CHARACTER_SET_NAME like "latin1%" NONE NO root@localhost DEFINER latin1 latin1_swedish_ci -NULL test v4 select COLLATION_NAME from information_schema.collations -where COLLATION_NAME like "latin1%" NONE NO root@localhost DEFINER latin1 latin1_swedish_ci +NULL test v0 select `schemata`.`SCHEMA_NAME` AS `c` from `information_schema`.`schemata` NONE NO root@localhost DEFINER latin1 latin1_swedish_ci +NULL test v1 select `tables`.`TABLE_NAME` AS `c` from `information_schema`.`tables` where (`tables`.`TABLE_NAME` = 'v1') NONE NO root@localhost DEFINER latin1 latin1_swedish_ci +NULL test v2 select `columns`.`COLUMN_NAME` AS `c` from `information_schema`.`columns` where (`columns`.`TABLE_NAME` = 'v2') NONE NO root@localhost DEFINER latin1 latin1_swedish_ci +NULL test v3 select `character_sets`.`CHARACTER_SET_NAME` AS `c` from `information_schema`.`character_sets` where (`character_sets`.`CHARACTER_SET_NAME` like 'latin1%') NONE NO root@localhost DEFINER latin1 latin1_swedish_ci +NULL test v4 select `collations`.`COLLATION_NAME` AS `c` from `information_schema`.`collations` where (`collations`.`COLLATION_NAME` like 'latin1%') NONE NO root@localhost DEFINER latin1 latin1_swedish_ci drop view v0, v1, v2, v3, v4; create table t1 (a int); grant select,update,insert on t1 to mysqltest_1@localhost; @@ -488,9 +484,9 @@ create view v2 (c) as select a from t1 WITH LOCAL CHECK OPTION; create view v3 (c) as select a from t1 WITH CASCADED CHECK OPTION; select * from information_schema.views; TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION -NULL test v1 select a from t1 with check option CASCADED YES root@localhost DEFINER latin1 latin1_swedish_ci -NULL test v2 select a from t1 WITH LOCAL CHECK OPTION LOCAL YES root@localhost DEFINER latin1 latin1_swedish_ci -NULL test v3 select a from t1 WITH CASCADED CHECK OPTION CASCADED YES root@localhost DEFINER latin1 latin1_swedish_ci +NULL test v1 select `test`.`t1`.`a` AS `c` from `test`.`t1` CASCADED YES root@localhost DEFINER latin1 latin1_swedish_ci +NULL test v2 select `test`.`t1`.`a` AS `c` from `test`.`t1` LOCAL YES root@localhost DEFINER latin1 latin1_swedish_ci +NULL test v3 select `test`.`t1`.`a` AS `c` from `test`.`t1` CASCADED YES root@localhost DEFINER latin1 latin1_swedish_ci grant select (a) on test.t1 to joe@localhost with grant option; select * from INFORMATION_SCHEMA.COLUMN_PRIVILEGES; GRANTEE TABLE_CATALOG TABLE_SCHEMA TABLE_NAME COLUMN_NAME PRIVILEGE_TYPE IS_GRANTABLE @@ -1175,7 +1171,7 @@ select * from information_schema.views where table_name='v1' or table_name='v2'; TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION NULL test v1 NONE YES root@localhost DEFINER latin1 latin1_swedish_ci -NULL test v2 select 1 NONE NO mysqltest_1@localhost DEFINER latin1 latin1_swedish_ci +NULL test v2 select 1 AS `1` NONE NO mysqltest_1@localhost DEFINER latin1 latin1_swedish_ci drop view v1, v2; drop table t1; drop user mysqltest_1@localhost; @@ -1559,8 +1555,7 @@ AS SELECT * FROM INFORMATION_SCHEMA.TABLES; SELECT VIEW_DEFINITION FROM INFORMATION_SCHEMA.VIEWS where TABLE_NAME = 'v1'; VIEW_DEFINITION -SELECT * -FROM INFORMATION_SCHEMA.TABLES +select `TABLES`.`TABLE_CATALOG` AS `TABLE_CATALOG`,`TABLES`.`TABLE_SCHEMA` AS `TABLE_SCHEMA`,`TABLES`.`TABLE_NAME` AS `TABLE_NAME`,`TABLES`.`TABLE_TYPE` AS `TABLE_TYPE`,`TABLES`.`ENGINE` AS `ENGINE`,`TABLES`.`VERSION` AS `VERSION`,`TABLES`.`ROW_FORMAT` AS `ROW_FORMAT`,`TABLES`.`TABLE_ROWS` AS `TABLE_ROWS`,`TABLES`.`AVG_ROW_LENGTH` AS `AVG_ROW_LENGTH`,`TABLES`.`DATA_LENGTH` AS `DATA_LENGTH`,`TABLES`.`MAX_DATA_LENGTH` AS `MAX_DATA_LENGTH`,`TABLES`.`INDEX_LENGTH` AS `INDEX_LENGTH`,`TABLES`.`DATA_FREE` AS `DATA_FREE`,`TABLES`.`AUTO_INCREMENT` AS `AUTO_INCREMENT`,`TABLES`.`CREATE_TIME` AS `CREATE_TIME`,`TABLES`.`UPDATE_TIME` AS `UPDATE_TIME`,`TABLES`.`CHECK_TIME` AS `CHECK_TIME`,`TABLES`.`TABLE_COLLATION` AS `TABLE_COLLATION`,`TABLES`.`CHECKSUM` AS `CHECKSUM`,`TABLES`.`CREATE_OPTIONS` AS `CREATE_OPTIONS`,`TABLES`.`TABLE_COMMENT` AS `TABLE_COMMENT` from `INFORMATION_SCHEMA`.`TABLES` DROP VIEW v1; SELECT SCHEMA_NAME FROM INFORMATION_SCHEMA.SCHEMATA WHERE SCHEMA_NAME ='information_schema'; diff --git a/mysql-test/r/information_schema_db.result b/mysql-test/r/information_schema_db.result index cb56fb3d5cc..3044a11fb39 100644 --- a/mysql-test/r/information_schema_db.result +++ b/mysql-test/r/information_schema_db.result @@ -210,7 +210,7 @@ v2 select view_definition from information_schema.views a where a.table_name = 'v2'; view_definition -select f1 from testdb_1.v1 +select `v1`.`f1` AS `f1` from `testdb_1`.`v1` select view_definition from information_schema.views a where a.table_name = 'testdb_1.v1'; view_definition diff --git a/mysql-test/r/mysqldump.result b/mysql-test/r/mysqldump.result index d0bfab6237a..a1b8eaa52f8 100644 --- a/mysql-test/r/mysqldump.result +++ b/mysql-test/r/mysqldump.result @@ -4230,6 +4230,40 @@ LOCK TABLES `test` WRITE; UNLOCK TABLES; drop database `test-database`; use test; + +# ----------------------------------------------------------------- +# -- Bug#30217: Views: changes in metadata behaviour between 5.0 and 5.1. +# ----------------------------------------------------------------- + +DROP DATABASE IF EXISTS mysqldump_test_db; +CREATE DATABASE mysqldump_test_db; +use mysqldump_test_db; + +CREATE VIEW v1(x, y) AS SELECT 'a', 'a'; + +SELECT view_definition +FROM INFORMATION_SCHEMA.VIEWS +WHERE table_schema = 'mysqldump_test_db' AND table_name = 'v1'; +view_definition +select 'a' AS `x`,'a' AS `y` + +---> Dumping mysqldump_test_db to bug30217.sql + +DROP DATABASE mysqldump_test_db; +use test; + +---> Restoring mysqldump_test_db... + +SELECT view_definition +FROM INFORMATION_SCHEMA.VIEWS +WHERE table_schema = 'mysqldump_test_db' AND table_name = 'v1'; +view_definition +select 'a' AS `x`,'a' AS `y` + +DROP DATABASE mysqldump_test_db; + +# -- End of test case for Bug#32538. + # # End of 5.1 tests # diff --git a/mysql-test/r/show_check.result b/mysql-test/r/show_check.result index 320550c0ccd..103b3c9a289 100644 --- a/mysql-test/r/show_check.result +++ b/mysql-test/r/show_check.result @@ -1075,7 +1075,7 @@ Catalog Database Table Table_alias Column Column_alias Type Length Max length Is def VIEWS TABLE_CATALOG TABLE_CATALOG 253 1536 0 Y 0 0 33 def VIEWS TABLE_SCHEMA TABLE_SCHEMA 253 192 4 N 1 0 33 def VIEWS TABLE_NAME TABLE_NAME 253 192 2 N 1 0 33 -def VIEWS VIEW_DEFINITION VIEW_DEFINITION 252 589815 8 N 17 0 33 +def VIEWS VIEW_DEFINITION VIEW_DEFINITION 252 589815 15 N 17 0 33 def VIEWS CHECK_OPTION CHECK_OPTION 253 24 4 N 1 0 33 def VIEWS IS_UPDATABLE IS_UPDATABLE 253 9 2 N 1 0 33 def VIEWS DEFINER DEFINER 253 231 14 N 1 0 33 @@ -1083,7 +1083,7 @@ def VIEWS SECURITY_TYPE SECURITY_TYPE 253 21 7 N 1 0 33 def VIEWS CHARACTER_SET_CLIENT CHARACTER_SET_CLIENT 253 96 6 N 1 0 33 def VIEWS COLLATION_CONNECTION COLLATION_CONNECTION 253 96 6 N 1 0 33 TABLE_CATALOG TABLE_SCHEMA TABLE_NAME VIEW_DEFINITION CHECK_OPTION IS_UPDATABLE DEFINER SECURITY_TYPE CHARACTER_SET_CLIENT COLLATION_CONNECTION -NULL test v1 SELECT 1 NONE NO root@localhost DEFINER binary binary +NULL test v1 select 1 AS `1` NONE NO root@localhost DEFINER binary binary ---------------------------------------------------------------- SHOW CREATE PROCEDURE p1; Catalog Database Table Table_alias Column Column_alias Type Length Max length Is_null Flags Decimals Charsetnr diff --git a/mysql-test/t/ddl_i18n_koi8r.test b/mysql-test/t/ddl_i18n_koi8r.test index 1d16adbad55..e3bed098126 100644 --- a/mysql-test/t/ddl_i18n_koi8r.test +++ b/mysql-test/t/ddl_i18n_koi8r.test @@ -85,6 +85,10 @@ CREATE VIEW v2 AS SELECT _utf8'теÑÑ‚' as c1| --echo +CREATE VIEW v3 AS SELECT _utf8'теÑÑ‚'| + +--echo + # # First-round checks. # @@ -120,6 +124,7 @@ SET @@collation_connection= cp1251_general_ci| --disable_result_log SELECT * FROM mysqltest1.v1| SELECT * FROM mysqltest1.v2| +SELECT * FROM mysqltest1.v3| --enable_result_log use mysqltest1| @@ -168,7 +173,7 @@ DROP DATABASE mysqltest1| --echo --echo ---> connection: con3 -# - Switch environment variables and trigger loading stored procedures; +# - Switch environment variables and trigger loading views; SET @@character_set_client= cp1251| SET @@character_set_results= cp1251| @@ -177,6 +182,7 @@ SET @@collation_connection= cp1251_general_ci| --disable_result_log SELECT * FROM mysqltest1.v1| SELECT * FROM mysqltest1.v2| +SELECT * FROM mysqltest1.v3| --enable_result_log use mysqltest1| diff --git a/mysql-test/t/ddl_i18n_utf8.test b/mysql-test/t/ddl_i18n_utf8.test index c80137a58b5..d76debcba5b 100644 --- a/mysql-test/t/ddl_i18n_utf8.test +++ b/mysql-test/t/ddl_i18n_utf8.test @@ -85,6 +85,10 @@ CREATE VIEW v2 AS SELECT _koi8r'ÔÅÓÔ' as c1| --echo +CREATE VIEW v3 AS SELECT _koi8r'ÔÅÓÔ'| + +--echo + # # First-round checks. # @@ -120,6 +124,7 @@ SET @@collation_connection= cp1251_general_ci| --disable_result_log SELECT * FROM mysqltest1.v1| SELECT * FROM mysqltest1.v2| +SELECT * FROM mysqltest1.v3| --enable_result_log use mysqltest1| @@ -168,7 +173,7 @@ DROP DATABASE mysqltest1| --echo --echo ---> connection: con3 -# - Switch environment variables and trigger loading stored procedures; +# - Switch environment variables and trigger loading views; SET @@character_set_client= cp1251| SET @@character_set_results= cp1251| @@ -177,6 +182,7 @@ SET @@collation_connection= cp1251_general_ci| --disable_result_log SELECT * FROM mysqltest1.v1| SELECT * FROM mysqltest1.v2| +SELECT * FROM mysqltest1.v3| --enable_result_log use mysqltest1| diff --git a/mysql-test/t/mysqldump.test b/mysql-test/t/mysqldump.test index 0e4e9989ffa..6cbe345bc8a 100644 --- a/mysql-test/t/mysqldump.test +++ b/mysql-test/t/mysqldump.test @@ -1799,6 +1799,61 @@ create table test (a int); drop database `test-database`; use test; +########################################################################### + +--echo +--echo # ----------------------------------------------------------------- +--echo # -- Bug#30217: Views: changes in metadata behaviour between 5.0 and 5.1. +--echo # ----------------------------------------------------------------- +--echo + +--disable_warnings +DROP DATABASE IF EXISTS mysqldump_test_db; +--enable_warnings + +CREATE DATABASE mysqldump_test_db; +use mysqldump_test_db; + +--echo + +CREATE VIEW v1(x, y) AS SELECT 'a', 'a'; + +--echo + +SELECT view_definition +FROM INFORMATION_SCHEMA.VIEWS +WHERE table_schema = 'mysqldump_test_db' AND table_name = 'v1'; + +--echo + +--echo ---> Dumping mysqldump_test_db to bug30217.sql +--exec $MYSQL_DUMP --character-sets-dir=$CHARSETSDIR --databases mysqldump_test_db > $MYSQLTEST_VARDIR/tmp/bug30217.sql + +--echo + +DROP DATABASE mysqldump_test_db; +use test; + +--echo + +--echo ---> Restoring mysqldump_test_db... +--exec $MYSQL test < $MYSQLTEST_VARDIR/tmp/bug30217.sql + +--echo + +SELECT view_definition +FROM INFORMATION_SCHEMA.VIEWS +WHERE table_schema = 'mysqldump_test_db' AND table_name = 'v1'; + +--echo + +DROP DATABASE mysqldump_test_db; + +--echo +--echo # -- End of test case for Bug#32538. +--echo + +########################################################################### --echo # --echo # End of 5.1 tests diff --git a/sql/ha_ndbcluster.cc b/sql/ha_ndbcluster.cc index 441da21bf1c..26292a0c57e 100644 --- a/sql/ha_ndbcluster.cc +++ b/sql/ha_ndbcluster.cc @@ -9446,7 +9446,7 @@ ha_ndbcluster::cond_push(const COND *cond) my_errno= HA_ERR_OUT_OF_MEM; DBUG_RETURN(NULL); } - DBUG_EXECUTE("where",print_where((COND *)cond, m_tabname);); + DBUG_EXECUTE("where",print_where((COND *)cond, m_tabname, QT_ORDINARY);); DBUG_RETURN(m_cond->cond_push(cond, table, (NDBTAB *)m_table)); } diff --git a/sql/item.cc b/sql/item.cc index 10c1c58aea8..f997518ac07 100644 --- a/sql/item.cc +++ b/sql/item.cc @@ -442,9 +442,10 @@ uint Item::decimal_precision() const } -void Item::print_item_w_name(String *str) +void Item::print_item_w_name(String *str, enum_query_type query_type) { - print(str); + print(str, query_type); + if (name) { THD *thd= current_thd; @@ -1128,7 +1129,7 @@ Item_splocal::this_item_addr(THD *thd, Item **) } -void Item_splocal::print(String *str) +void Item_splocal::print(String *str, enum_query_type) { str->reserve(m_name.length+8); str->append(m_name.str, m_name.length); @@ -1182,7 +1183,7 @@ Item_case_expr::this_item_addr(THD *thd, Item **) } -void Item_case_expr::print(String *str) +void Item_case_expr::print(String *str, enum_query_type) { if (str->reserve(MAX_INT_WIDTH + sizeof("case_expr@"))) return; /* purecov: inspected */ @@ -1276,12 +1277,12 @@ bool Item_name_const::fix_fields(THD *thd, Item **ref) } -void Item_name_const::print(String *str) +void Item_name_const::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("NAME_CONST(")); - name_item->print(str); + name_item->print(str, query_type); str->append(','); - value_item->print(str); + value_item->print(str, query_type); str->append(')'); } @@ -1298,12 +1299,12 @@ public: const char *table_name_arg, const char *field_name_arg) :Item_ref(context_arg, item, table_name_arg, field_name_arg) {} - void print (String *str) + virtual inline void print (String *str, enum_query_type query_type) { if (ref) - (*ref)->print(str); + (*ref)->print(str, query_type); else - Item_ident::print(str); + Item_ident::print(str, query_type); } }; @@ -1455,7 +1456,9 @@ bool DTCollation::aggregate(DTCollation &dt, uint flags) set(dt); } else - ; // Do nothing + { + // Do nothing + } } else if ((flags & MY_COLL_ALLOW_SUPERSET_CONV) && left_is_superset(this, &dt)) @@ -1872,7 +1875,7 @@ const char *Item_ident::full_name() const return tmp; } -void Item_ident::print(String *str) +void Item_ident::print(String *str, enum_query_type query_type) { THD *thd= current_thd; char d_name_buff[MAX_ALIAS_NAME], t_name_buff[MAX_ALIAS_NAME]; @@ -2134,7 +2137,7 @@ String *Item_int::val_str(String *str) return str; } -void Item_int::print(String *str) +void Item_int::print(String *str, enum_query_type query_type) { // my_charset_bin is good enough for numbers str_value.set(value, &my_charset_bin); @@ -2165,7 +2168,7 @@ String *Item_uint::val_str(String *str) } -void Item_uint::print(String *str) +void Item_uint::print(String *str, enum_query_type query_type) { // latin1 is good enough for numbers str_value.set((ulonglong) value, default_charset()); @@ -2257,7 +2260,7 @@ String *Item_decimal::val_str(String *result) return result; } -void Item_decimal::print(String *str) +void Item_decimal::print(String *str, enum_query_type query_type) { my_decimal2string(E_DEC_FATAL_ERROR, &decimal_value, 0, 0, 0, &str_value); str->append(str_value); @@ -2310,16 +2313,39 @@ my_decimal *Item_float::val_decimal(my_decimal *decimal_value) } -void Item_string::print(String *str) +void Item_string::print(String *str, enum_query_type query_type) { - if (is_cs_specified()) + if (query_type == QT_ORDINARY && is_cs_specified()) { str->append('_'); str->append(collation.collation->csname); } str->append('\''); - str_value.print(str); + + if (query_type == QT_ORDINARY || + my_charset_same(str_value.charset(), system_charset_info)) + { + str_value.print(str); + } + else + { + THD *thd= current_thd; + LEX_STRING utf8_lex_str; + + thd->convert_string(&utf8_lex_str, + system_charset_info, + str_value.c_ptr_safe(), + str_value.length(), + str_value.charset()); + + String utf8_str(utf8_lex_str.str, + utf8_lex_str.length, + system_charset_info); + + utf8_str.print(str); + } + str->append('\''); } @@ -3086,7 +3112,7 @@ Item_param::eq(const Item *arg, bool binary_cmp) const /* End of Item_param related */ -void Item_param::print(String *str) +void Item_param::print(String *str, enum_query_type query_type) { if (state == NO_VALUE) { @@ -4799,7 +4825,7 @@ int Item_float::save_in_field(Field *field, bool no_conversions) } -void Item_float::print(String *str) +void Item_float::print(String *str, enum_query_type query_type) { if (presentation) { @@ -4917,7 +4943,7 @@ warn: } -void Item_hex_string::print(String *str) +void Item_hex_string::print(String *str, enum_query_type query_type) { char *end= (char*) str_value.ptr() + str_value.length(), *ptr= end - min(str_value.length(), sizeof(longlong)); @@ -5179,7 +5205,7 @@ Item *Item_field::update_value_transformer(uchar *select_arg) } -void Item_field::print(String *str) +void Item_field::print(String *str, enum_query_type query_type) { if (field && field->table->const_table) { @@ -5191,7 +5217,7 @@ void Item_field::print(String *str) str->append('\''); return; } - Item_ident::print(str); + Item_ident::print(str, query_type); } @@ -5531,7 +5557,7 @@ void Item_ref::cleanup() } -void Item_ref::print(String *str) +void Item_ref::print(String *str, enum_query_type query_type) { if (ref) { @@ -5542,10 +5568,10 @@ void Item_ref::print(String *str) append_identifier(thd, str, name, (uint) strlen(name)); } else - (*ref)->print(str); + (*ref)->print(str, query_type); } else - Item_ident::print(str); + Item_ident::print(str, query_type); } @@ -5735,11 +5761,11 @@ Item *Item_ref::get_tmp_table_item(THD *thd) } -void Item_ref_null_helper::print(String *str) +void Item_ref_null_helper::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("<ref_null_helper>(")); if (ref) - (*ref)->print(str); + (*ref)->print(str, query_type); else str->append('?'); str->append(')'); @@ -5931,7 +5957,7 @@ error: } -void Item_default_value::print(String *str) +void Item_default_value::print(String *str, enum_query_type query_type) { if (!arg) { @@ -5939,7 +5965,7 @@ void Item_default_value::print(String *str) return; } str->append(STRING_WITH_LEN("default(")); - arg->print(str); + arg->print(str, query_type); str->append(')'); } @@ -6075,10 +6101,10 @@ bool Item_insert_value::fix_fields(THD *thd, Item **items) return FALSE; } -void Item_insert_value::print(String *str) +void Item_insert_value::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("values(")); - arg->print(str); + arg->print(str, query_type); str->append(')'); } @@ -6199,7 +6225,7 @@ bool Item_trigger_field::fix_fields(THD *thd, Item **items) } -void Item_trigger_field::print(String *str) +void Item_trigger_field::print(String *str, enum_query_type query_type) { str->append((row_version == NEW_ROW) ? "NEW" : "OLD", 3); str->append('.'); @@ -6389,13 +6415,13 @@ Item_cache* Item_cache::get_cache(const Item *item) } -void Item_cache::print(String *str) +void Item_cache::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("<cache>(")); if (example) - example->print(str); + example->print(str, query_type); else - Item::print(str); + Item::print(str, query_type); str->append(')'); } diff --git a/sql/item.h b/sql/item.h index b3cf9aa6e4c..e1c380a2a55 100644 --- a/sql/item.h +++ b/sql/item.h @@ -113,7 +113,6 @@ public: } }; - /*************************************************************************/ /* A framework to easily handle different return types for hybrid items @@ -769,20 +768,24 @@ public: */ virtual bool const_during_execution() const { return (used_tables() & ~PARAM_TABLE_BIT) == 0; } - /* - This is an essential method for correct functioning of VIEWS. - To save a view in an .frm file we need its unequivocal - definition in SQL that takes into account sql_mode and - environmental settings. Currently such definition is restored - by traversing through the parsed tree of a view and - print()'ing SQL syntax of every node to a String buffer. This - method is used to print the SQL definition of an item. The - second use of this method is for EXPLAIN EXTENDED, to print - the SQL of a query after all optimizations of the parsed tree - have been done. - */ - virtual void print(String *str_arg) { str_arg->append(full_name()); } - void print_item_w_name(String *); + + /** + This method is used for to: + - to generate a view definition query (SELECT-statement); + - to generate a SQL-query for EXPLAIN EXTENDED; + - to generate a SQL-query to be shown in INFORMATION_SCHEMA; + - debug. + + For more information about view definition query, INFORMATION_SCHEMA + query and why they should be generated from the Item-tree, @see + mysql_register_view(). + */ + virtual inline void print(String *str, enum_query_type query_type) + { + str->append(full_name()); + } + + void print_item_w_name(String *, enum_query_type query_type); virtual void update_used_tables() {} virtual void split_sum_func(THD *thd, Item **ref_pointer_array, List<Item> &fields) {} @@ -1134,7 +1137,7 @@ public: const Item *this_item() const; Item **this_item_addr(THD *thd, Item **); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); public: inline const LEX_STRING *my_name() const; @@ -1203,7 +1206,7 @@ public: Item_case_expr can not occur in views, so here it is only for debug purposes. */ - void print(String *str); + virtual void print(String *str, enum_query_type query_type); private: uint m_case_expr_id; @@ -1261,7 +1264,7 @@ public: String *val_str(String *sp); my_decimal *val_decimal(my_decimal *); bool is_null(); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); Item_result result_type() const { @@ -1343,7 +1346,7 @@ public: const char *full_name() const; void cleanup(); bool remove_dependence_processor(uchar * arg); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); virtual bool change_context_processor(uchar *cntx) { context= (Name_resolution_context *)cntx; return FALSE; } friend bool insert_fields(THD *thd, Name_resolution_context *context, @@ -1473,7 +1476,7 @@ public: Item *safe_charset_converter(CHARSET_INFO *tocs); int fix_outer_field(THD *thd, Field **field, Item **reference); virtual Item *update_value_transformer(uchar *select_arg); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); Field::geometry_type get_geometry_type() const { DBUG_ASSERT(field_type() == MYSQL_TYPE_GEOMETRY); @@ -1511,7 +1514,12 @@ public: bool basic_const_item() const { return 1; } Item *clone_item() { return new Item_null(name); } bool is_null() { return 1; } - void print(String *str) { str->append(STRING_WITH_LEN("NULL")); } + + virtual inline void print(String *str, enum_query_type query_type) + { + str->append(STRING_WITH_LEN("NULL")); + } + Item *safe_charset_converter(CHARSET_INFO *tocs); bool check_partition_func_processor(uchar *int_arg) {return FALSE;} }; @@ -1645,7 +1653,7 @@ public: */ virtual table_map used_tables() const { return state != NO_VALUE ? (table_map)0 : PARAM_TABLE_BIT; } - void print(String *str); + virtual void print(String *str, enum_query_type query_type); bool is_null() { DBUG_ASSERT(state != NO_VALUE); return state == NULL_VALUE; } bool basic_const_item() const; @@ -1703,7 +1711,7 @@ public: Item *clone_item() { return new Item_int(name,value,max_length); } // to prevent drop fixed flag (no need parent cleanup call) void cleanup() {} - void print(String *str); + virtual void print(String *str, enum_query_type query_type); Item_num *neg() { value= -value; return this; } uint decimal_precision() const { return (uint)(max_length - test(value < 0)); } @@ -1723,7 +1731,7 @@ public: String *val_str(String*); Item *clone_item() { return new Item_uint(name, value, max_length); } int save_in_field(Field *field, bool no_conversions); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); Item_num *neg (); uint decimal_precision() const { return max_length; } bool check_partition_func_processor(uchar *bool_arg) { return FALSE;} @@ -1759,7 +1767,7 @@ public: } // to prevent drop fixed flag (no need parent cleanup call) void cleanup() {} - void print(String *str); + virtual void print(String *str, enum_query_type query_type); Item_num *neg() { my_decimal_neg(&decimal_value); @@ -1818,7 +1826,7 @@ public: Item *clone_item() { return new Item_float(name, value, decimals, max_length); } Item_num *neg() { value= -value; return this; } - void print(String *str); + virtual void print(String *str, enum_query_type query_type); bool eq(const Item *, bool binary_cmp) const; }; @@ -1831,7 +1839,12 @@ public: uint length) :Item_float(NullS, val_arg, decimal_par, length), func_name(str) {} - void print(String *str) { str->append(func_name); } + + virtual inline void print(String *str, enum_query_type query_type) + { + str->append(func_name); + } + Item *safe_charset_converter(CHARSET_INFO *tocs); }; @@ -1922,7 +1935,7 @@ public: str_value.append(str, length); max_length= str_value.numchars() * collation.collation->mbmaxlen; } - void print(String *str); + virtual void print(String *str, enum_query_type query_type); // to prevent drop fixed flag (no need parent cleanup call) void cleanup() {} bool check_partition_func_processor(uchar *int_arg) {return FALSE;} @@ -1981,7 +1994,12 @@ public: :Item_string(NullS, str, length, cs, dv), func_name(name_par) {} Item *safe_charset_converter(CHARSET_INFO *tocs); - void print(String *str) { str->append(func_name); } + + virtual inline void print(String *str, enum_query_type query_type) + { + str->append(func_name); + } + bool check_partition_func_processor(uchar *int_arg) {return TRUE;} }; @@ -2071,7 +2089,7 @@ public: enum_field_types field_type() const { return MYSQL_TYPE_VARCHAR; } // to prevent drop fixed flag (no need parent cleanup call) void cleanup() {} - void print(String *str); + virtual void print(String *str, enum_query_type query_type); bool eq(const Item *item, bool binary_cmp) const; virtual Item *safe_charset_converter(CHARSET_INFO *tocs); bool check_partition_func_processor(uchar *int_arg) {return FALSE;} @@ -2192,7 +2210,7 @@ public: } bool walk(Item_processor processor, bool walk_subquery, uchar *arg) { return (*ref)->walk(processor, walk_subquery, arg); } - void print(String *str); + virtual void print(String *str, enum_query_type query_type); bool result_as_longlong() { return (*ref)->result_as_longlong(); @@ -2339,7 +2357,7 @@ public: my_decimal *val_decimal(my_decimal *); bool val_bool(); bool get_date(MYSQL_TIME *ltime, uint fuzzydate); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); /* we add RAND_TABLE_BIT to prevent moving this item from HAVING to WHERE */ @@ -2514,7 +2532,7 @@ public: enum Type type() const { return DEFAULT_VALUE_ITEM; } bool eq(const Item *item, bool binary_cmp) const; bool fix_fields(THD *, Item **); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); int save_in_field(Field *field_arg, bool no_conversions); table_map used_tables() const { return (table_map)0L; } @@ -2547,7 +2565,7 @@ public: arg(a) {} bool eq(const Item *item, bool binary_cmp) const; bool fix_fields(THD *, Item **); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); int save_in_field(Field *field_arg, bool no_conversions) { return Item_field::save_in_field(field_arg, no_conversions); @@ -2618,7 +2636,7 @@ public: enum Type type() const { return TRIGGER_FIELD_ITEM; } bool eq(const Item *item, bool binary_cmp) const; bool fix_fields(THD *, Item **); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); table_map used_tables() const { return (table_map)0L; } Field *get_tmp_table_field() { return 0; } Item *copy_or_same(THD *thd) { return this; } @@ -2711,7 +2729,7 @@ public: virtual void keep_array() {} // to prevent drop fixed flag (no need parent cleanup call) void cleanup() {} - void print(String *str); + virtual void print(String *str, enum_query_type query_type); bool eq_def(Field *field) { return cached_field ? cached_field->eq_def (field) : FALSE; diff --git a/sql/item_cmpfunc.cc b/sql/item_cmpfunc.cc index dc868376796..ae7ea95707c 100644 --- a/sql/item_cmpfunc.cc +++ b/sql/item_cmpfunc.cc @@ -286,10 +286,10 @@ longlong Item_func_not::val_int() higher than the precedence of NOT. */ -void Item_func_not::print(String *str) +void Item_func_not::print(String *str, enum_query_type query_type) { str->append('('); - Item_func::print(str); + Item_func::print(str, query_type); str->append(')'); } @@ -321,12 +321,12 @@ bool Item_func_not_all::empty_underlying_subquery() (test_sub_item && !test_sub_item->any_value())); } -void Item_func_not_all::print(String *str) +void Item_func_not_all::print(String *str, enum_query_type query_type) { if (show) - Item_func::print(str); + Item_func::print(str, query_type); else - args[0]->print(str); + args[0]->print(str, query_type); } @@ -1422,10 +1422,10 @@ void Item_func_truth::fix_length_and_dec() } -void Item_func_truth::print(String *str) +void Item_func_truth::print(String *str, enum_query_type query_type) { str->append('('); - args[0]->print(str); + args[0]->print(str, query_type); str->append(STRING_WITH_LEN(" is ")); if (! affirmative) str->append(STRING_WITH_LEN("not ")); @@ -2109,16 +2109,16 @@ longlong Item_func_between::val_int() } -void Item_func_between::print(String *str) +void Item_func_between::print(String *str, enum_query_type query_type) { str->append('('); - args[0]->print(str); + args[0]->print(str, query_type); if (negated) str->append(STRING_WITH_LEN(" not")); str->append(STRING_WITH_LEN(" between ")); - args[1]->print(str); + args[1]->print(str, query_type); str->append(STRING_WITH_LEN(" and ")); - args[2]->print(str); + args[2]->print(str, query_type); str->append(')'); } @@ -2763,26 +2763,26 @@ uint Item_func_case::decimal_precision() const Fix this so that it prints the whole CASE expression */ -void Item_func_case::print(String *str) +void Item_func_case::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("(case ")); if (first_expr_num != -1) { - args[first_expr_num]->print(str); + args[first_expr_num]->print(str, query_type); str->append(' '); } for (uint i=0 ; i < ncases ; i+=2) { str->append(STRING_WITH_LEN("when ")); - args[i]->print(str); + args[i]->print(str, query_type); str->append(STRING_WITH_LEN(" then ")); - args[i+1]->print(str); + args[i+1]->print(str, query_type); str->append(' '); } if (else_expr_num != -1) { str->append(STRING_WITH_LEN("else ")); - args[else_expr_num]->print(str); + args[else_expr_num]->print(str, query_type); str->append(' '); } str->append(STRING_WITH_LEN("end)")); @@ -3706,14 +3706,14 @@ void Item_func_in::fix_length_and_dec() } -void Item_func_in::print(String *str) +void Item_func_in::print(String *str, enum_query_type query_type) { str->append('('); - args[0]->print(str); + args[0]->print(str, query_type); if (negated) str->append(STRING_WITH_LEN(" not")); str->append(STRING_WITH_LEN(" in (")); - print_args(str, 1); + print_args(str, 1, query_type); str->append(STRING_WITH_LEN("))")); } @@ -4084,19 +4084,19 @@ void Item_cond::update_used_tables() } -void Item_cond::print(String *str) +void Item_cond::print(String *str, enum_query_type query_type) { str->append('('); List_iterator_fast<Item> li(list); Item *item; if ((item=li++)) - item->print(str); + item->print(str, query_type); while ((item=li++)) { str->append(' '); str->append(func_name()); str->append(' '); - item->print(str); + item->print(str, query_type); } str->append(')'); } @@ -4279,10 +4279,10 @@ longlong Item_func_isnotnull::val_int() } -void Item_func_isnotnull::print(String *str) +void Item_func_isnotnull::print(String *str, enum_query_type query_type) { str->append('('); - args[0]->print(str); + args[0]->print(str, query_type); str->append(STRING_WITH_LEN(" is not null)")); } @@ -5276,24 +5276,24 @@ Item *Item_equal::transform(Item_transformer transformer, uchar *arg) return Item_func::transform(transformer, arg); } -void Item_equal::print(String *str) +void Item_equal::print(String *str, enum_query_type query_type) { str->append(func_name()); str->append('('); List_iterator_fast<Item_field> it(fields); Item *item; if (const_item) - const_item->print(str); + const_item->print(str, query_type); else { item= it++; - item->print(str); + item->print(str, query_type); } while ((item= it++)) { str->append(','); str->append(' '); - item->print(str); + item->print(str, query_type); } str->append(')'); } diff --git a/sql/item_cmpfunc.h b/sql/item_cmpfunc.h index 188d87a69ca..0166a18029d 100644 --- a/sql/item_cmpfunc.h +++ b/sql/item_cmpfunc.h @@ -123,7 +123,7 @@ public: virtual bool val_bool(); virtual longlong val_int(); virtual void fix_length_and_dec(); - virtual void print(String *str); + virtual void print(String *str, enum_query_type query_type); protected: Item_func_truth(Item *a, bool a_value, bool a_affirmative) @@ -338,7 +338,12 @@ public: optimize_type select_optimize() const { return OPTIMIZE_OP; } virtual enum Functype rev_functype() const { return UNKNOWN_FUNC; } bool have_rev_func() const { return rev_functype() != UNKNOWN_FUNC; } - void print(String *str) { Item_func::print_op(str); } + + virtual inline void print(String *str, enum_query_type query_type) + { + Item_func::print_op(str, query_type); + } + bool is_null() { return test(args[0]->is_null() || args[1]->is_null()); } bool is_bool_func() { return 1; } CHARSET_INFO *compare_collation() { return cmp.cmp_collation.collation; } @@ -368,7 +373,7 @@ public: enum Functype functype() const { return NOT_FUNC; } const char *func_name() const { return "not"; } Item *neg_transformer(THD *thd); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); }; class Item_maxmin_subselect; @@ -433,7 +438,7 @@ public: longlong val_int(); enum Functype functype() const { return NOT_ALL_FUNC; } const char *func_name() const { return "<not>"; } - void print(String *str); + virtual void print(String *str, enum_query_type query_type); void set_sum_test(Item_sum_hybrid *item) { test_sum_item= item; }; void set_sub_test(Item_maxmin_subselect *item) { test_sub_item= item; }; bool empty_underlying_subquery(); @@ -594,7 +599,7 @@ public: const char *func_name() const { return "between"; } bool fix_fields(THD *, Item **); void fix_length_and_dec(); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); bool is_bool_func() { return 1; } CHARSET_INFO *compare_collation() { return cmp_collation.collation; } uint decimal_precision() const { return 1; } @@ -608,7 +613,11 @@ public: longlong val_int(); optimize_type select_optimize() const { return OPTIMIZE_NONE; } const char *func_name() const { return "strcmp"; } - void print(String *str) { Item_func::print(str); } + + virtual inline void print(String *str, enum_query_type query_type) + { + Item_func::print(str, query_type); + } }; @@ -711,7 +720,12 @@ public: void fix_length_and_dec(); uint decimal_precision() const { return args[0]->decimal_precision(); } const char *func_name() const { return "nullif"; } - void print(String *str) { Item_func::print(str); } + + virtual inline void print(String *str, enum_query_type query_type) + { + Item_func::print(str, query_type); + } + table_map not_null_tables() const { return 0; } bool is_null(); }; @@ -1141,7 +1155,7 @@ public: enum Item_result result_type () const { return cached_result_type; } enum_field_types field_type() const { return cached_field_type; } const char *func_name() const { return "case"; } - void print(String *str); + virtual void print(String *str, enum_query_type query_type); Item *find_item(String *str); CHARSET_INFO *compare_collation() { return cmp_collation.collation; } void cleanup(); @@ -1208,7 +1222,7 @@ public: } optimize_type select_optimize() const { return OPTIMIZE_KEY; } - void print(String *str); + virtual void print(String *str, enum_query_type query_type); enum Functype functype() const { return IN_FUNC; } const char *func_name() const { return " IN "; } bool nulls_in_row(); @@ -1330,7 +1344,7 @@ public: table_map not_null_tables() const { return abort_on_null ? not_null_tables_cache : 0; } Item *neg_transformer(THD *thd); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); CHARSET_INFO *compare_collation() { return args[0]->collation.collation; } void top_level_item() { abort_on_null=1; } }; @@ -1395,7 +1409,12 @@ public: longlong val_int(); bool fix_fields(THD *thd, Item **ref); const char *func_name() const { return "regexp"; } - void print(String *str) { print_op(str); } + + virtual inline void print(String *str, enum_query_type query_type) + { + print_op(str, query_type); + } + CHARSET_INFO *compare_collation() { return cmp_collation.collation; } }; @@ -1407,7 +1426,11 @@ public: Item_func_regex(Item *a,Item *b) :Item_bool_func(a,b) {} longlong val_int() { return 0;} const char *func_name() const { return "regex"; } - void print(String *str) { print_op(str); } + + virtual inline void print(String *str, enum_query_type query_type) + { + print_op(str, query_type); + } }; #endif /* USE_REGEX */ @@ -1444,7 +1467,7 @@ public: List<Item>* argument_list() { return &list; } table_map used_tables() const; void update_used_tables(); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); void split_sum_func(THD *thd, Item **ref_pointer_array, List<Item> &fields); friend int setup_conds(THD *thd, TABLE_LIST *tables, TABLE_LIST *leaves, COND **conds); @@ -1568,7 +1591,7 @@ public: void update_used_tables(); bool walk(Item_processor processor, bool walk_subquery, uchar *arg); Item *transform(Item_transformer transformer, uchar *arg); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); CHARSET_INFO *compare_collation() { return fields.head()->collation.collation; } }; diff --git a/sql/item_func.cc b/sql/item_func.cc index 6e9371de9dc..a7b562d3407 100644 --- a/sql/item_func.cc +++ b/sql/item_func.cc @@ -374,37 +374,37 @@ table_map Item_func::not_null_tables() const } -void Item_func::print(String *str) +void Item_func::print(String *str, enum_query_type query_type) { str->append(func_name()); str->append('('); - print_args(str, 0); + print_args(str, 0, query_type); str->append(')'); } -void Item_func::print_args(String *str, uint from) +void Item_func::print_args(String *str, uint from, enum_query_type query_type) { for (uint i=from ; i < arg_count ; i++) { if (i != from) str->append(','); - args[i]->print(str); + args[i]->print(str, query_type); } } -void Item_func::print_op(String *str) +void Item_func::print_op(String *str, enum_query_type query_type) { str->append('('); for (uint i=0 ; i < arg_count-1 ; i++) { - args[i]->print(str); + args[i]->print(str, query_type); str->append(' '); str->append(func_name()); str->append(' '); } - args[arg_count-1]->print(str); + args[arg_count-1]->print(str, query_type); str->append(')'); } @@ -884,10 +884,10 @@ my_decimal *Item_func_numhybrid::val_decimal(my_decimal *decimal_value) } -void Item_func_signed::print(String *str) +void Item_func_signed::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("cast(")); - args[0]->print(str); + args[0]->print(str, query_type); str->append(STRING_WITH_LEN(" as signed)")); } @@ -955,10 +955,10 @@ longlong Item_func_signed::val_int() } -void Item_func_unsigned::print(String *str) +void Item_func_unsigned::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("cast(")); - args[0]->print(str); + args[0]->print(str, query_type); str->append(STRING_WITH_LEN(" as unsigned)")); } @@ -1064,7 +1064,7 @@ err: } -void Item_decimal_typecast::print(String *str) +void Item_decimal_typecast::print(String *str, enum_query_type query_type) { char len_buf[20*3 + 1]; char *end; @@ -1072,7 +1072,7 @@ void Item_decimal_typecast::print(String *str) uint precision= my_decimal_length_to_precision(max_length, decimals, unsigned_flag); str->append(STRING_WITH_LEN("cast(")); - args[0]->print(str); + args[0]->print(str, query_type); str->append(STRING_WITH_LEN(" as decimal(")); end=int10_to_str(precision, len_buf,10); @@ -2537,16 +2537,16 @@ longlong Item_func_locate::val_int() } -void Item_func_locate::print(String *str) +void Item_func_locate::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("locate(")); - args[1]->print(str); + args[1]->print(str, query_type); str->append(','); - args[0]->print(str); + args[0]->print(str, query_type); if (arg_count == 3) { str->append(','); - args[2]->print(str); + args[2]->print(str, query_type); } str->append(')'); } @@ -3095,7 +3095,7 @@ void Item_udf_func::cleanup() } -void Item_udf_func::print(String *str) +void Item_udf_func::print(String *str, enum_query_type query_type) { str->append(func_name()); str->append('('); @@ -3103,7 +3103,7 @@ void Item_udf_func::print(String *str) { if (i != 0) str->append(','); - args[i]->print_item_w_name(str); + args[i]->print_item_w_name(str, query_type); } str->append(')'); } @@ -3683,12 +3683,12 @@ longlong Item_func_benchmark::val_int() } -void Item_func_benchmark::print(String *str) +void Item_func_benchmark::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("benchmark(")); - args[0]->print(str); + args[0]->print(str, query_type); str->append(','); - args[1]->print(str); + args[1]->print(str, query_type); str->append(')'); } @@ -4264,22 +4264,23 @@ my_decimal *Item_func_set_user_var::val_decimal_result(my_decimal *val) } -void Item_func_set_user_var::print(String *str) +void Item_func_set_user_var::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("(@")); str->append(name.str, name.length); str->append(STRING_WITH_LEN(":=")); - args[0]->print(str); + args[0]->print(str, query_type); str->append(')'); } -void Item_func_set_user_var::print_as_stmt(String *str) +void Item_func_set_user_var::print_as_stmt(String *str, + enum_query_type query_type) { str->append(STRING_WITH_LEN("set @")); str->append(name.str, name.length); str->append(STRING_WITH_LEN(":=")); - args[0]->print(str); + args[0]->print(str, query_type); str->append(')'); } @@ -4652,7 +4653,7 @@ enum Item_result Item_func_get_user_var::result_type() const } -void Item_func_get_user_var::print(String *str) +void Item_func_get_user_var::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("(@")); str->append(name.str,name.length); @@ -4750,7 +4751,7 @@ my_decimal* Item_user_var_as_out_param::val_decimal(my_decimal *decimal_buffer) } -void Item_user_var_as_out_param::print(String *str) +void Item_user_var_as_out_param::print(String *str, enum_query_type query_type) { str->append('@'); str->append(name.str,name.length); @@ -5089,12 +5090,12 @@ double Item_func_match::val_real() table->record[0], 0)); } -void Item_func_match::print(String *str) +void Item_func_match::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("(match ")); - print_args(str, 1); + print_args(str, 1, query_type); str->append(STRING_WITH_LEN(" against (")); - args[0]->print(str); + args[0]->print(str, query_type); if (flags & FT_BOOL) str->append(STRING_WITH_LEN(" in boolean mode")); else if (flags & FT_EXPAND) @@ -5505,7 +5506,7 @@ Item_result Item_func_sp::result_type() const { DBUG_ENTER("Item_func_sp::result_type"); - DBUG_PRINT("info", ("m_sp = %p", m_sp)); + DBUG_PRINT("info", ("m_sp = %p", (void *) m_sp)); DBUG_ASSERT(sp_result_field); DBUG_RETURN(sp_result_field->result_type()); } diff --git a/sql/item_func.h b/sql/item_func.h index e09b584de95..f8eb7ff6200 100644 --- a/sql/item_func.h +++ b/sql/item_func.h @@ -140,9 +140,9 @@ public: inline uint argument_count() const { return arg_count; } inline void remove_arguments() { arg_count=0; } void split_sum_func(THD *thd, Item **ref_pointer_array, List<Item> &fields); - void print(String *str); - void print_op(String *str); - void print_args(String *str, uint from); + virtual void print(String *str, enum_query_type query_type); + void print_op(String *str, enum_query_type query_type); + void print_args(String *str, uint from, enum_query_type query_type); virtual void fix_num_length_and_dec(); void count_only_length(); void count_real_length(); @@ -293,7 +293,12 @@ class Item_num_op :public Item_func_numhybrid public: Item_num_op(Item *a,Item *b) :Item_func_numhybrid(a, b) {} virtual void result_precision()= 0; - void print(String *str) { print_op(str); } + + virtual inline void print(String *str, enum_query_type query_type) + { + print_op(str, query_type); + } + void find_num_type(); String *str_op(String *str) { DBUG_ASSERT(0); return 0; } bool check_partition_func_processor(uchar *int_arg) {return FALSE;} @@ -339,7 +344,7 @@ public: longlong val_int_from_str(int *error); void fix_length_and_dec() { max_length=args[0]->max_length; unsigned_flag=0; } - void print(String *str); + virtual void print(String *str, enum_query_type query_type); uint decimal_precision() const { return args[0]->decimal_precision(); } }; @@ -352,7 +357,7 @@ public: void fix_length_and_dec() { max_length=args[0]->max_length; unsigned_flag=1; } longlong val_int(); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); }; @@ -373,7 +378,7 @@ public: enum_field_types field_type() const { return MYSQL_TYPE_NEWDECIMAL; } void fix_length_and_dec() {}; const char *func_name() const { return "decimal_typecast"; } - void print(String *); + virtual void print(String *str, enum_query_type query_type); }; @@ -441,7 +446,12 @@ public: longlong val_int(); const char *func_name() const { return "DIV"; } void fix_length_and_dec(); - void print(String *str) { print_op(str); } + + virtual inline void print(String *str, enum_query_type query_type) + { + print_op(str, query_type); + } + bool check_partition_func_processor(uchar *int_arg) {return FALSE;} }; @@ -843,7 +853,7 @@ public: const char *func_name() const { return "locate"; } longlong val_int(); void fix_length_and_dec(); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); }; @@ -900,7 +910,11 @@ public: Item_func_bit(Item *a, Item *b) :Item_int_func(a, b) {} Item_func_bit(Item *a) :Item_int_func(a) {} void fix_length_and_dec() { unsigned_flag= 1; } - void print(String *str) { print_op(str); } + + virtual inline void print(String *str, enum_query_type query_type) + { + print_op(str, query_type); + } }; class Item_func_bit_or :public Item_func_bit @@ -950,7 +964,11 @@ public: Item_func_bit_neg(Item *a) :Item_func_bit(a) {} longlong val_int(); const char *func_name() const { return "~"; } - void print(String *str) { Item_func::print(str); } + + virtual inline void print(String *str, enum_query_type query_type) + { + Item_func::print(str, query_type); + } }; @@ -979,7 +997,7 @@ public: longlong val_int(); const char *func_name() const { return "benchmark"; } void fix_length_and_dec() { max_length=1; maybe_null=0; } - void print(String *str); + virtual void print(String *str, enum_query_type query_type); }; @@ -1076,7 +1094,7 @@ public: Item_result result_type () const { return udf.result_type(); } table_map not_null_tables() const { return 0; } bool is_expensive() { return 1; } - void print(String *str); + virtual void print(String *str, enum_query_type query_type); }; @@ -1313,8 +1331,8 @@ public: enum Item_result result_type () const { return cached_result_type; } bool fix_fields(THD *thd, Item **ref); void fix_length_and_dec(); - void print(String *str); - void print_as_stmt(String *str); + virtual void print(String *str, enum_query_type query_type); + void print_as_stmt(String *str, enum_query_type query_type); const char *func_name() const { return "set_user_var"; } int save_in_field(Field *field, bool no_conversions, bool can_use_result_field); @@ -1344,7 +1362,7 @@ public: my_decimal *val_decimal(my_decimal*); String *val_str(String* str); void fix_length_and_dec(); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); enum Item_result result_type() const; /* We must always return variables as strings to guard against selects of type @@ -1389,7 +1407,7 @@ public: my_decimal *val_decimal(my_decimal *decimal_buffer); /* fix_fields() binds variable name with its entry structure */ bool fix_fields(THD *thd, Item **ref); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); void set_null_value(CHARSET_INFO* cs); void set_value(const char *str, uint length, CHARSET_INFO* cs); }; @@ -1467,7 +1485,7 @@ public: /* The following should be safe, even if we compare doubles */ longlong val_int() { DBUG_ASSERT(fixed == 1); return val_real() != 0.0; } double val_real(); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); bool fix_index(); void init_search(bool no_order); diff --git a/sql/item_geofunc.h b/sql/item_geofunc.h index 62be78eee9e..edbe104e307 100644 --- a/sql/item_geofunc.h +++ b/sql/item_geofunc.h @@ -224,8 +224,13 @@ public: DBUG_ASSERT(0); // Should never happened return "sp_unknown"; } - } - void print(String *str) { Item_func::print(str); } + } + + virtual inline void print(String *str, enum_query_type query_type) + { + Item_func::print(str, query_type); + } + void fix_length_and_dec() { maybe_null= 1; } bool is_null() { (void) val_int(); return null_value; } }; diff --git a/sql/item_row.cc b/sql/item_row.cc index 369aa04930e..28de03bf049 100644 --- a/sql/item_row.cc +++ b/sql/item_row.cc @@ -134,14 +134,14 @@ bool Item_row::check_cols(uint c) return 0; } -void Item_row::print(String *str) +void Item_row::print(String *str, enum_query_type query_type) { str->append('('); for (uint i= 0; i < arg_count; i++) { if (i) str->append(','); - items[i]->print(str); + items[i]->print(str, query_type); } str->append(')'); } diff --git a/sql/item_row.h b/sql/item_row.h index dd7436888f0..67441f49603 100644 --- a/sql/item_row.h +++ b/sql/item_row.h @@ -65,7 +65,7 @@ public: bool const_item() const { return const_item_cache; }; enum Item_result result_type() const { return ROW_RESULT; } void update_used_tables(); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); bool walk(Item_processor processor, bool walk_subquery, uchar *arg); Item *transform(Item_transformer transformer, uchar *arg); diff --git a/sql/item_strfunc.cc b/sql/item_strfunc.cc index 42314872997..fe805d7672a 100644 --- a/sql/item_strfunc.cc +++ b/sql/item_strfunc.cc @@ -1594,20 +1594,20 @@ void Item_func_trim::fix_length_and_dec() } } -void Item_func_trim::print(String *str) +void Item_func_trim::print(String *str, enum_query_type query_type) { if (arg_count == 1) { - Item_func::print(str); + Item_func::print(str, query_type); return; } str->append(Item_func_trim::func_name()); str->append('('); str->append(mode_name()); str->append(' '); - args[1]->print(str); + args[1]->print(str, query_type); str->append(STRING_WITH_LEN(" from ")); - args[0]->print(str); + args[0]->print(str, query_type); str->append(')'); } @@ -2116,12 +2116,12 @@ String *Item_func_format::val_str(String *str) } -void Item_func_format::print(String *str) +void Item_func_format::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("format(")); - args[0]->print(str); + args[0]->print(str, query_type); str->append(','); - args[1]->print(str); + args[1]->print(str, query_type); str->append(')'); } @@ -2292,14 +2292,14 @@ Item *Item_func_make_set::transform(Item_transformer transformer, uchar *arg) } -void Item_func_make_set::print(String *str) +void Item_func_make_set::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("make_set(")); - item->print(str); + item->print(str, query_type); if (arg_count) { str->append(','); - print_args(str, 0); + print_args(str, 0, query_type); } str->append(')'); } @@ -2710,10 +2710,10 @@ void Item_func_conv_charset::fix_length_and_dec() max_length = args[0]->max_length*conv_charset->mbmaxlen; } -void Item_func_conv_charset::print(String *str) +void Item_func_conv_charset::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("convert(")); - args[0]->print(str); + args[0]->print(str, query_type); str->append(STRING_WITH_LEN(" using ")); str->append(conv_charset->csname); str->append(')'); @@ -2781,10 +2781,10 @@ bool Item_func_set_collation::eq(const Item *item, bool binary_cmp) const } -void Item_func_set_collation::print(String *str) +void Item_func_set_collation::print(String *str, enum_query_type query_type) { str->append('('); - args[0]->print(str); + args[0]->print(str, query_type); str->append(STRING_WITH_LEN(" collate ")); DBUG_ASSERT(args[1]->basic_const_item() && args[1]->type() == Item::STRING_ITEM); @@ -2903,10 +2903,10 @@ String *Item_func_unhex::val_str(String *str) } -void Item_func_binary::print(String *str) +void Item_func_binary::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("cast(")); - args[0]->print(str); + args[0]->print(str, query_type); str->append(STRING_WITH_LEN(" as binary)")); } diff --git a/sql/item_strfunc.h b/sql/item_strfunc.h index 0d7cd66acff..81baf9a4c5f 100644 --- a/sql/item_strfunc.h +++ b/sql/item_strfunc.h @@ -225,7 +225,7 @@ public: String *val_str(String *); void fix_length_and_dec(); const char *func_name() const { return "trim"; } - void print(String *str); + virtual void print(String *str, enum_query_type query_type); virtual const char *mode_name() const { return "both"; } }; @@ -482,7 +482,7 @@ public: Item_str_func::walk(processor, walk_subquery, arg); } Item *transform(Item_transformer transformer, uchar *arg); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); }; @@ -494,7 +494,7 @@ public: String *val_str(String *); void fix_length_and_dec(); const char *func_name() const { return "format"; } - void print(String *); + virtual void print(String *str, enum_query_type query_type); }; @@ -617,7 +617,7 @@ public: collation.set(&my_charset_bin); max_length=args[0]->max_length; } - void print(String *str); + virtual void print(String *str, enum_query_type query_type); const char *func_name() const { return "cast_as_binary"; } }; @@ -719,7 +719,7 @@ public: String *val_str(String *); void fix_length_and_dec(); const char *func_name() const { return "convert"; } - void print(String *str); + virtual void print(String *str, enum_query_type query_type); }; class Item_func_set_collation :public Item_str_func @@ -731,7 +731,7 @@ public: bool eq(const Item *item, bool binary_cmp) const; const char *func_name() const { return "collate"; } enum Functype functype() const { return COLLATE_FUNC; } - void print(String *str); + virtual void print(String *str, enum_query_type query_type); Item_field *filed_for_view_update() { /* this function is transparent for view updating */ diff --git a/sql/item_subselect.cc b/sql/item_subselect.cc index 46b8d2e46cc..7b68d258d29 100644 --- a/sql/item_subselect.cc +++ b/sql/item_subselect.cc @@ -306,10 +306,10 @@ void Item_subselect::update_used_tables() } -void Item_subselect::print(String *str) +void Item_subselect::print(String *str, enum_query_type query_type) { str->append('('); - engine->print(str); + engine->print(str, query_type); str->append(')'); } @@ -391,10 +391,10 @@ void Item_maxmin_subselect::cleanup() } -void Item_maxmin_subselect::print(String *str) +void Item_maxmin_subselect::print(String *str, enum_query_type query_type) { str->append(max?"<max>":"<min>", 5); - Item_singlerow_subselect::print(str); + Item_singlerow_subselect::print(str, query_type); } @@ -630,10 +630,10 @@ Item_exists_subselect::Item_exists_subselect(st_select_lex *select_lex): } -void Item_exists_subselect::print(String *str) +void Item_exists_subselect::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("exists")); - Item_subselect::print(str); + Item_subselect::print(str, query_type); } @@ -1553,16 +1553,16 @@ err: } -void Item_in_subselect::print(String *str) +void Item_in_subselect::print(String *str, enum_query_type query_type) { if (transformed) str->append(STRING_WITH_LEN("<exists>")); else { - left_expr->print(str); + left_expr->print(str, query_type); str->append(STRING_WITH_LEN(" in ")); } - Item_subselect::print(str); + Item_subselect::print(str, query_type); } @@ -1587,18 +1587,18 @@ Item_allany_subselect::select_transformer(JOIN *join) } -void Item_allany_subselect::print(String *str) +void Item_allany_subselect::print(String *str, enum_query_type query_type) { if (transformed) str->append(STRING_WITH_LEN("<exists>")); else { - left_expr->print(str); + left_expr->print(str, query_type); str->append(' '); str->append(func->symbol(all)); str->append(all ? " all " : " any ", 5); } - Item_subselect::print(str); + Item_subselect::print(str, query_type); } @@ -2384,22 +2384,24 @@ table_map subselect_union_engine::upper_select_const_tables() } -void subselect_single_select_engine::print(String *str) +void subselect_single_select_engine::print(String *str, + enum_query_type query_type) { - select_lex->print(thd, str); + select_lex->print(thd, str, query_type); } -void subselect_union_engine::print(String *str) +void subselect_union_engine::print(String *str, enum_query_type query_type) { - unit->print(str); + unit->print(str, query_type); } -void subselect_uniquesubquery_engine::print(String *str) +void subselect_uniquesubquery_engine::print(String *str, + enum_query_type query_type) { str->append(STRING_WITH_LEN("<primary_index_lookup>(")); - tab->ref.items[0]->print(str); + tab->ref.items[0]->print(str, query_type); str->append(STRING_WITH_LEN(" in ")); str->append(tab->table->s->table_name.str, tab->table->s->table_name.length); KEY *key_info= tab->table->key_info+ tab->ref.key; @@ -2408,16 +2410,17 @@ void subselect_uniquesubquery_engine::print(String *str) if (cond) { str->append(STRING_WITH_LEN(" where ")); - cond->print(str); + cond->print(str, query_type); } str->append(')'); } -void subselect_indexsubquery_engine::print(String *str) +void subselect_indexsubquery_engine::print(String *str, + enum_query_type query_type) { str->append(STRING_WITH_LEN("<index_lookup>(")); - tab->ref.items[0]->print(str); + tab->ref.items[0]->print(str, query_type); str->append(STRING_WITH_LEN(" in ")); str->append(tab->table->s->table_name.str, tab->table->s->table_name.length); KEY *key_info= tab->table->key_info+ tab->ref.key; @@ -2428,12 +2431,12 @@ void subselect_indexsubquery_engine::print(String *str) if (cond) { str->append(STRING_WITH_LEN(" where ")); - cond->print(str); + cond->print(str, query_type); } if (having) { str->append(STRING_WITH_LEN(" having ")); - having->print(str); + having->print(str, query_type); } str->append(')'); } diff --git a/sql/item_subselect.h b/sql/item_subselect.h index de4b1cbdc06..d4aa621c083 100644 --- a/sql/item_subselect.h +++ b/sql/item_subselect.h @@ -103,7 +103,7 @@ public: inline bool get_const_item_cache() { return const_item_cache; } Item *get_tmp_table_item(THD *thd); void update_used_tables(); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); virtual bool have_guarded_conds() { return FALSE; } bool change_engine(subselect_engine *eng) { @@ -203,7 +203,7 @@ protected: public: Item_maxmin_subselect(THD *thd, Item_subselect *parent, st_select_lex *select_lex, bool max); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); void cleanup(); bool any_value() { return was_values; } void register_value() { was_values= TRUE; } @@ -234,7 +234,7 @@ public: my_decimal *val_decimal(my_decimal *); bool val_bool(); void fix_length_and_dec(); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); friend class select_exists_subselect; friend class subselect_uniquesubquery_engine; @@ -312,7 +312,7 @@ public: void top_level_item() { abort_on_null=1; } inline bool is_top_level_item() { return abort_on_null; } bool test_limit(st_select_lex_unit *unit); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); bool fix_fields(THD *thd, Item **ref); friend class Item_ref_null_helper; @@ -335,7 +335,7 @@ public: // only ALL subquery has upper not subs_type substype() { return all?ALL_SUBS:ANY_SUBS; } trans_res select_transformer(JOIN *join); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); }; @@ -399,7 +399,7 @@ public: virtual bool may_be_null() { return maybe_null; }; virtual table_map upper_select_const_tables()= 0; static table_map calc_const_tables(TABLE_LIST *); - virtual void print(String *str)= 0; + virtual void print(String *str, enum_query_type query_type)= 0; virtual bool change_result(Item_subselect *si, select_subselect *result)= 0; virtual bool no_tables()= 0; virtual bool is_executed() const { return FALSE; } @@ -430,7 +430,7 @@ public: uint8 uncacheable(); void exclude(); table_map upper_select_const_tables(); - void print (String *str); + virtual void print (String *str, enum_query_type query_type); bool change_result(Item_subselect *si, select_subselect *result); bool no_tables(); bool may_be_null(); @@ -454,7 +454,7 @@ public: uint8 uncacheable(); void exclude(); table_map upper_select_const_tables(); - void print (String *str); + virtual void print (String *str, enum_query_type query_type); bool change_result(Item_subselect *si, select_subselect *result); bool no_tables(); bool is_executed() const; @@ -511,7 +511,7 @@ public: uint8 uncacheable() { return UNCACHEABLE_DEPENDENT; } void exclude(); table_map upper_select_const_tables() { return 0; } - void print (String *str); + virtual void print (String *str, enum_query_type query_type); bool change_result(Item_subselect *si, select_subselect *result); bool no_tables(); int scan_table(); @@ -565,7 +565,7 @@ public: having(having_arg) {} int exec(); - void print (String *str); + virtual void print (String *str, enum_query_type query_type); }; diff --git a/sql/item_sum.cc b/sql/item_sum.cc index 27b964a9e15..f5a3956c1e4 100644 --- a/sql/item_sum.cc +++ b/sql/item_sum.cc @@ -359,14 +359,14 @@ void Item_sum::make_field(Send_field *tmp_field) } -void Item_sum::print(String *str) +void Item_sum::print(String *str, enum_query_type query_type) { str->append(func_name()); for (uint i=0 ; i < arg_count ; i++) { if (i) str->append(','); - args[i]->print(str); + args[i]->print(str, query_type); } str->append(')'); } @@ -2716,7 +2716,7 @@ void Item_udf_sum::cleanup() } -void Item_udf_sum::print(String *str) +void Item_udf_sum::print(String *str, enum_query_type query_type) { str->append(func_name()); str->append('('); @@ -2724,7 +2724,7 @@ void Item_udf_sum::print(String *str) { if (i) str->append(','); - args[i]->print(str); + args[i]->print(str, query_type); } str->append(')'); } @@ -3460,7 +3460,7 @@ String* Item_func_group_concat::val_str(String* str) } -void Item_func_group_concat::print(String *str) +void Item_func_group_concat::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("group_concat(")); if (distinct) @@ -3469,7 +3469,7 @@ void Item_func_group_concat::print(String *str) { if (i) str->append(','); - args[i]->print(str); + args[i]->print(str, query_type); } if (arg_count_order) { @@ -3478,7 +3478,7 @@ void Item_func_group_concat::print(String *str) { if (i) str->append(','); - (*order[i]->item)->print(str); + (*order[i]->item)->print(str, query_type); if (order[i]->asc) str->append(STRING_WITH_LEN(" ASC")); else diff --git a/sql/item_sum.h b/sql/item_sum.h index a3582967736..d1e6a74e85e 100644 --- a/sql/item_sum.h +++ b/sql/item_sum.h @@ -343,7 +343,7 @@ public: } virtual bool const_item() const { return forced_const; } void make_field(Send_field *field); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); void fix_num_length_and_dec(); /* @@ -984,7 +984,7 @@ public: void reset_field() {}; void update_field() {}; void cleanup(); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); }; @@ -1257,7 +1257,7 @@ public: String* val_str(String* str); Item *copy_or_same(THD* thd); void no_rows_in_result() {} - void print(String *str); + virtual void print(String *str, enum_query_type query_type); virtual bool change_context_processor(uchar *cntx) { context= (Name_resolution_context *)cntx; return FALSE; } }; diff --git a/sql/item_timefunc.cc b/sql/item_timefunc.cc index a0beadcd481..390f94945aa 100644 --- a/sql/item_timefunc.cc +++ b/sql/item_timefunc.cc @@ -2217,23 +2217,23 @@ static const char *interval_names[]= "second_microsecond" }; -void Item_date_add_interval::print(String *str) +void Item_date_add_interval::print(String *str, enum_query_type query_type) { str->append('('); - args[0]->print(str); + args[0]->print(str, query_type); str->append(date_sub_interval?" - interval ":" + interval "); - args[1]->print(str); + args[1]->print(str, query_type); str->append(' '); str->append(interval_names[int_type]); str->append(')'); } -void Item_extract::print(String *str) +void Item_extract::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("extract(")); str->append(interval_names[int_type]); str->append(STRING_WITH_LEN(" from ")); - args[0]->print(str); + args[0]->print(str, query_type); str->append(')'); } @@ -2374,20 +2374,20 @@ bool Item_char_typecast::eq(const Item *item, bool binary_cmp) const return 1; } -void Item_typecast::print(String *str) +void Item_typecast::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("cast(")); - args[0]->print(str); + args[0]->print(str, query_type); str->append(STRING_WITH_LEN(" as ")); str->append(cast_type()); str->append(')'); } -void Item_char_typecast::print(String *str) +void Item_char_typecast::print(String *str, enum_query_type query_type) { str->append(STRING_WITH_LEN("cast(")); - args[0]->print(str); + args[0]->print(str, query_type); str->append(STRING_WITH_LEN(" as char")); if (cast_length >= 0) { @@ -2822,7 +2822,7 @@ null_date: } -void Item_func_add_time::print(String *str) +void Item_func_add_time::print(String *str, enum_query_type query_type) { if (is_date) { @@ -2836,9 +2836,9 @@ void Item_func_add_time::print(String *str) else str->append(STRING_WITH_LEN("subtime(")); } - args[0]->print(str); + args[0]->print(str, query_type); str->append(','); - args[1]->print(str); + args[1]->print(str, query_type); str->append(')'); } @@ -3083,7 +3083,7 @@ null_date: } -void Item_func_timestamp_diff::print(String *str) +void Item_func_timestamp_diff::print(String *str, enum_query_type query_type) { str->append(func_name()); str->append('('); @@ -3123,7 +3123,7 @@ void Item_func_timestamp_diff::print(String *str) for (uint i=0 ; i < 2 ; i++) { str->append(','); - args[i]->print(str); + args[i]->print(str, query_type); } str->append(')'); } @@ -3163,7 +3163,7 @@ String *Item_func_get_format::val_str(String *str) } -void Item_func_get_format::print(String *str) +void Item_func_get_format::print(String *str, enum_query_type query_type) { str->append(func_name()); str->append('('); @@ -3181,7 +3181,7 @@ void Item_func_get_format::print(String *str) default: DBUG_ASSERT(0); } - args[0]->print(str); + args[0]->print(str, query_type); str->append(')'); } diff --git a/sql/item_timefunc.h b/sql/item_timefunc.h index 9be7e97db49..cfcf5fab080 100644 --- a/sql/item_timefunc.h +++ b/sql/item_timefunc.h @@ -694,7 +694,7 @@ public: longlong val_int(); bool get_date(MYSQL_TIME *res, uint fuzzy_date); bool eq(const Item *item, bool binary_cmp) const; - void print(String *str); + virtual void print(String *str, enum_query_type query_type); }; @@ -711,7 +711,7 @@ class Item_extract :public Item_int_func const char *func_name() const { return "extract"; } void fix_length_and_dec(); bool eq(const Item *item, bool binary_cmp) const; - void print(String *str); + virtual void print(String *str, enum_query_type query_type); bool check_partition_func_processor(uchar *int_arg) {return FALSE;} }; @@ -735,7 +735,7 @@ public: max_length=args[0]->max_length; } virtual const char* cast_type() const= 0; - void print(String *str); + virtual void print(String *str, enum_query_type query_type); }; @@ -767,7 +767,7 @@ public: const char* cast_type() const { return "char"; }; String *val_str(String *a); void fix_length_and_dec(); - void print(String *str); + virtual void print(String *str, enum_query_type query_type); }; @@ -901,7 +901,7 @@ public: { return tmp_table_field_from_field_type(table, 0); } - void print(String *str); + virtual void print(String *str, enum_query_type query_type); const char *func_name() const { return "add_time"; } double val_real() { return val_real_from_decimal(); } my_decimal *val_decimal(my_decimal *decimal_value) @@ -977,7 +977,7 @@ public: decimals=0; maybe_null=1; } - void print(String *str); + virtual void print(String *str, enum_query_type query_type); }; @@ -1001,7 +1001,7 @@ public: decimals=0; max_length=17*MY_CHARSET_BIN_MB_MAXLEN; } - void print(String *str); + virtual void print(String *str, enum_query_type query_type); }; diff --git a/sql/mysql_priv.h b/sql/mysql_priv.h index ea552414d9a..6c0234a9b0b 100644 --- a/sql/mysql_priv.h +++ b/sql/mysql_priv.h @@ -44,6 +44,19 @@ #include "sql_plugin.h" #include "scheduler.h" +/** + Query type constants. + + QT_ORDINARY -- ordinary SQL query. + QT_IS -- SQL query to be shown in INFORMATION_SCHEMA (in utf8 and without + character set introducers). +*/ +enum enum_query_type +{ + QT_ORDINARY, + QT_IS +}; + /* TODO convert all these three maps to Bitmap classes */ typedef ulonglong table_map; /* Used for table bits in join */ #if MAX_INDEXES <= 64 @@ -1708,7 +1721,7 @@ bool mysql_manager_submit(void (*action)()); /* sql_test.cc */ #ifndef DBUG_OFF -void print_where(COND *cond,const char *info); +void print_where(COND *cond,const char *info, enum_query_type query_type); void print_cached_tables(void); void TEST_filesort(SORT_FIELD *sortorder,uint s_length); void print_plan(JOIN* join,uint idx, double record_count, double read_time, diff --git a/sql/sp_head.cc b/sql/sp_head.cc index f42a5dde8ed..8bd10e00f15 100644 --- a/sql/sp_head.cc +++ b/sql/sp_head.cc @@ -2933,7 +2933,7 @@ sp_instr_set::print(String *str) } str->qs_append(m_offset); str->qs_append(' '); - m_value->print(str); + m_value->print(str, QT_ORDINARY); } @@ -2961,9 +2961,9 @@ void sp_instr_set_trigger_field::print(String *str) { str->append(STRING_WITH_LEN("set_trigger_field ")); - trigger_field->print(str); + trigger_field->print(str, QT_ORDINARY); str->append(STRING_WITH_LEN(":=")); - value->print(str); + value->print(str, QT_ORDINARY); } /* @@ -3089,7 +3089,7 @@ sp_instr_jump_if_not::print(String *str) str->qs_append('('); str->qs_append(m_cont_dest); str->qs_append(STRING_WITH_LEN(") ")); - m_expr->print(str); + m_expr->print(str, QT_ORDINARY); } @@ -3177,7 +3177,7 @@ sp_instr_freturn::print(String *str) str->qs_append(STRING_WITH_LEN("freturn ")); str->qs_append((uint)m_type); str->qs_append(' '); - m_value->print(str); + m_value->print(str, QT_ORDINARY); } /* @@ -3665,7 +3665,7 @@ sp_instr_set_case_expr::print(String *str) str->qs_append(STRING_WITH_LEN(") ")); str->qs_append(m_case_expr_id); str->qs_append(' '); - m_case_expr->print(str); + m_case_expr->print(str, QT_ORDINARY); } uint diff --git a/sql/sql_lex.cc b/sql/sql_lex.cc index 5352f8efbbb..b07efc62a00 100644 --- a/sql/sql_lex.cc +++ b/sql/sql_lex.cc @@ -1947,7 +1947,7 @@ bool st_select_lex::setup_ref_array(THD *thd, uint order_group_num) } -void st_select_lex_unit::print(String *str) +void st_select_lex_unit::print(String *str, enum_query_type query_type) { bool union_all= !union_distinct; for (SELECT_LEX *sl= first_select(); sl; sl= sl->next_select()) @@ -1962,7 +1962,7 @@ void st_select_lex_unit::print(String *str) } if (sl->braces) str->append('('); - sl->print(thd, str); + sl->print(thd, str, query_type); if (sl->braces) str->append(')'); } @@ -1971,16 +1971,19 @@ void st_select_lex_unit::print(String *str) if (fake_select_lex->order_list.elements) { str->append(STRING_WITH_LEN(" order by ")); - fake_select_lex->print_order(str, - (ORDER *) fake_select_lex-> - order_list.first); + fake_select_lex->print_order( + str, + (ORDER *) fake_select_lex->order_list.first, + query_type); } - fake_select_lex->print_limit(thd, str); + fake_select_lex->print_limit(thd, str, query_type); } } -void st_select_lex::print_order(String *str, ORDER *order) +void st_select_lex::print_order(String *str, + ORDER *order, + enum_query_type query_type) { for (; order; order= order->next) { @@ -1991,7 +1994,7 @@ void st_select_lex::print_order(String *str, ORDER *order) str->append(buffer, length); } else - (*order->item)->print(str); + (*order->item)->print(str, query_type); if (!order->asc) str->append(STRING_WITH_LEN(" desc")); if (order->next) @@ -2000,7 +2003,9 @@ void st_select_lex::print_order(String *str, ORDER *order) } -void st_select_lex::print_limit(THD *thd, String *str) +void st_select_lex::print_limit(THD *thd, + String *str, + enum_query_type query_type) { SELECT_LEX_UNIT *unit= master_unit(); Item_subselect *item= unit->item; @@ -2019,10 +2024,10 @@ void st_select_lex::print_limit(THD *thd, String *str) str->append(STRING_WITH_LEN(" limit ")); if (offset_limit) { - offset_limit->print(str); + offset_limit->print(str, query_type); str->append(','); } - select_limit->print(str); + select_limit->print(str, query_type); } } diff --git a/sql/sql_lex.h b/sql/sql_lex.h index 744019c8ae9..b1a0d506382 100644 --- a/sql/sql_lex.h +++ b/sql/sql_lex.h @@ -543,7 +543,7 @@ public: inline void unclean() { cleaned= 0; } void reinit_exec_mechanism(); - void print(String *str); + void print(String *str, enum_query_type query_type); bool add_fake_select_lex(THD *thd); void init_prepare_fake_select_lex(THD *thd); @@ -762,9 +762,11 @@ public: init_select(); } bool setup_ref_array(THD *thd, uint order_group_num); - void print(THD *thd, String *str); - static void print_order(String *str, ORDER *order); - void print_limit(THD *thd, String *str); + void print(THD *thd, String *str, enum_query_type query_type); + static void print_order(String *str, + ORDER *order, + enum_query_type query_type); + void print_limit(THD *thd, String *str, enum_query_type query_type); void fix_prepare_information(THD *thd, Item **conds, Item **having_conds); /* Destroy the used execution plan (JOIN) of this subtree (this @@ -1708,8 +1710,6 @@ typedef struct st_lex : public Query_tables_list */ bool use_only_table_context; - LEX_STRING view_body_utf8; - /* Reference to a struct that contains information in various commands to add/create/drop/change table spaces. diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index a78ac978a4a..e1ee2bd595b 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -4729,7 +4729,7 @@ static bool execute_sqlcom_select(THD *thd, TABLE_LIST *all_tables) char buff[1024]; String str(buff,(uint32) sizeof(buff), system_charset_info); str.length(0); - thd->lex->unit.print(&str); + thd->lex->unit.print(&str, QT_ORDINARY); str.append('\0'); push_warning(thd, MYSQL_ERROR::WARN_LEVEL_NOTE, ER_YES, str.ptr()); diff --git a/sql/sql_select.cc b/sql/sql_select.cc index d7e7be87d23..a520f9c57cf 100644 --- a/sql/sql_select.cc +++ b/sql/sql_select.cc @@ -945,7 +945,8 @@ JOIN::optimize() make_cond_for_table(conds, PSEUDO_TABLE_BITS, 0); DBUG_EXECUTE("where", print_where(table_independent_conds, - "where after opt_sum_query()");); + "where after opt_sum_query()", + QT_ORDINARY);); conds= table_independent_conds; } } @@ -1025,7 +1026,10 @@ JOIN::optimize() { conds= substitute_for_best_equal_field(conds, cond_equal, map2table); conds->update_used_tables(); - DBUG_EXECUTE("where", print_where(conds, "after substitute_best_equal");); + DBUG_EXECUTE("where", + print_where(conds, + "after substitute_best_equal", + QT_ORDINARY);); } /* @@ -2088,12 +2092,14 @@ JOIN::exec() curr_table->select_cond= curr_table->select->cond; curr_table->select_cond->top_level_item(); DBUG_EXECUTE("where",print_where(curr_table->select->cond, - "select and having");); + "select and having", + QT_ORDINARY);); curr_join->tmp_having= make_cond_for_table(curr_join->tmp_having, ~ (table_map) 0, ~used_tables); DBUG_EXECUTE("where",print_where(curr_join->tmp_having, - "having after sort");); + "having after sort", + QT_ORDINARY);); } } { @@ -5837,7 +5843,8 @@ static void add_not_null_conds(JOIN *join) if (notnull->fix_fields(join->thd, ¬null)) DBUG_VOID_RETURN; DBUG_EXECUTE("where",print_where(notnull, - referred_tab->table->alias);); + referred_tab->table->alias, + QT_ORDINARY);); add_cond_and_fix(&referred_tab->select_cond, notnull); } } @@ -5995,7 +6002,7 @@ make_join_select(JOIN *join,SQL_SELECT *select,COND *cond) make_cond_for_table(cond, join->const_table_map, (table_map) 0); - DBUG_EXECUTE("where",print_where(const_cond,"constants");); + DBUG_EXECUTE("where",print_where(const_cond,"constants", QT_ORDINARY);); for (JOIN_TAB *tab= join->join_tab+join->const_tables; tab < join->join_tab+join->tables ; tab++) { @@ -6096,7 +6103,7 @@ make_join_select(JOIN *join,SQL_SELECT *select,COND *cond) } if (tmp || !cond) { - DBUG_EXECUTE("where",print_where(tmp,tab->table->alias);); + DBUG_EXECUTE("where",print_where(tmp,tab->table->alias, QT_ORDINARY);); SQL_SELECT *sel= tab->select= ((SQL_SELECT*) thd->memdup((uchar*) select, sizeof(*select))); @@ -6136,7 +6143,7 @@ make_join_select(JOIN *join,SQL_SELECT *select,COND *cond) tab->select_cond= sel->cond= NULL; sel->head=tab->table; - DBUG_EXECUTE("where",print_where(tmp,tab->table->alias);); + DBUG_EXECUTE("where",print_where(tmp,tab->table->alias, QT_ORDINARY);); if (tab->quick) { /* Use quick key read if it's a constant and it's not used @@ -6248,7 +6255,7 @@ make_join_select(JOIN *join,SQL_SELECT *select,COND *cond) current_map, current_map))) { - DBUG_EXECUTE("where",print_where(tmp,"cache");); + DBUG_EXECUTE("where",print_where(tmp,"cache", QT_ORDINARY);); tab->cache.select=(SQL_SELECT*) thd->memdup((uchar*) sel, sizeof(SQL_SELECT)); tab->cache.select->cond=tmp; @@ -8872,10 +8879,10 @@ optimize_cond(JOIN *join, COND *conds, List<TABLE_LIST> *join_list, predicate. Substitute a constant instead of this field if the multiple equality contains a constant. */ - DBUG_EXECUTE("where", print_where(conds, "original");); + DBUG_EXECUTE("where", print_where(conds, "original", QT_ORDINARY);); conds= build_equal_items(join->thd, conds, NULL, join_list, &join->cond_equal); - DBUG_EXECUTE("where",print_where(conds,"after equal_items");); + DBUG_EXECUTE("where",print_where(conds,"after equal_items", QT_ORDINARY);); /* change field = field to field = const for each found field = const */ propagate_cond_constants(thd, (I_List<COND_CMP> *) 0, conds, conds); @@ -8883,9 +8890,9 @@ optimize_cond(JOIN *join, COND *conds, List<TABLE_LIST> *join_list, Remove all instances of item == item Remove all and-levels where CONST item != CONST item */ - DBUG_EXECUTE("where",print_where(conds,"after const change");); + DBUG_EXECUTE("where",print_where(conds,"after const change", QT_ORDINARY);); conds= remove_eq_conds(thd, conds, cond_value) ; - DBUG_EXECUTE("info",print_where(conds,"after remove");); + DBUG_EXECUTE("info",print_where(conds,"after remove", QT_ORDINARY);); } DBUG_RETURN(conds); } @@ -13357,7 +13364,7 @@ static bool fix_having(JOIN *join, Item **having) JOIN_TAB *table=&join->join_tab[join->const_tables]; table_map used_tables= join->const_table_map | table->table->map; - DBUG_EXECUTE("where",print_where(*having,"having");); + DBUG_EXECUTE("where",print_where(*having,"having", QT_ORDINARY);); Item* sort_table_cond=make_cond_for_table(*having,used_tables,used_tables); if (sort_table_cond) { @@ -13374,9 +13381,11 @@ static bool fix_having(JOIN *join, Item **having) table->select_cond=table->select->cond; table->select_cond->top_level_item(); DBUG_EXECUTE("where",print_where(table->select_cond, - "select and having");); + "select and having", + QT_ORDINARY);); *having=make_cond_for_table(*having,~ (table_map) 0,~used_tables); - DBUG_EXECUTE("where",print_where(*having,"having after make_cond");); + DBUG_EXECUTE("where", + print_where(*having,"having after make_cond", QT_ORDINARY);); } return 0; } @@ -15043,7 +15052,7 @@ change_to_use_tmp_fields(THD *thd, Item **ref_pointer_array, char buff[256]; String str(buff,sizeof(buff),&my_charset_bin); str.length(0); - item->print(&str); + item->print(&str, QT_ORDINARY); item_field->name= sql_strmake(str.ptr(),str.length()); } #endif @@ -16084,7 +16093,7 @@ static void select_describe(JOIN *join, bool need_tmp_table, bool need_order, if (thd->lex->describe & DESCRIBE_EXTENDED) { extra.append(STRING_WITH_LEN(": ")); - ((COND *)pushed_cond)->print(&extra); + ((COND *)pushed_cond)->print(&extra, QT_ORDINARY); } } else @@ -16233,9 +16242,13 @@ bool mysql_explain_union(THD *thd, SELECT_LEX_UNIT *unit, select_result *result) @param thd thread handler @param str string where table should be printed @param tables list of tables in join + @query_type type of the query is being generated */ -static void print_join(THD *thd, String *str, List<TABLE_LIST> *tables) +static void print_join(THD *thd, + String *str, + List<TABLE_LIST> *tables, + enum_query_type query_type) { /* List is reversed => we should reverse it before using */ List_iterator_fast<TABLE_LIST> ti(*tables); @@ -16248,7 +16261,7 @@ static void print_join(THD *thd, String *str, List<TABLE_LIST> *tables) *t= ti++; DBUG_ASSERT(tables->elements >= 1); - (*table)->print(thd, str); + (*table)->print(thd, str, query_type); TABLE_LIST **end= table + tables->elements; for (TABLE_LIST **tbl= table + 1; tbl < end; tbl++) @@ -16263,11 +16276,11 @@ static void print_join(THD *thd, String *str, List<TABLE_LIST> *tables) str->append(STRING_WITH_LEN(" straight_join ")); else str->append(STRING_WITH_LEN(" join ")); - curr->print(thd, str); + curr->print(thd, str, query_type); if (curr->on_expr) { str->append(STRING_WITH_LEN(" on(")); - curr->on_expr->print(str); + curr->on_expr->print(str, query_type); str->append(')'); } } @@ -16314,15 +16327,15 @@ Index_hint::print(THD *thd, String *str) /** Print table as it should be in join list. - @param str string where table should bbe printed + @param str string where table should be printed */ -void TABLE_LIST::print(THD *thd, String *str) +void TABLE_LIST::print(THD *thd, String *str, enum_query_type query_type) { if (nested_join) { str->append('('); - print_join(thd, str, &nested_join->join_list); + print_join(thd, str, &nested_join->join_list, query_type); str->append(')'); } else @@ -16345,7 +16358,7 @@ void TABLE_LIST::print(THD *thd, String *str) { // A derived table str->append('('); - derived->print(str); + derived->print(str, query_type); str->append(')'); cmp_name= ""; // Force printing of alias } @@ -16405,7 +16418,7 @@ void TABLE_LIST::print(THD *thd, String *str) } -void st_select_lex::print(THD *thd, String *str) +void st_select_lex::print(THD *thd, String *str, enum_query_type query_type) { /* QQ: thd may not be set for sub queries, but this should be fixed */ if (!thd) @@ -16453,7 +16466,7 @@ void st_select_lex::print(THD *thd, String *str) first= 0; else str->append(','); - item->print_item_w_name(str); + item->print_item_w_name(str, query_type); } /* @@ -16464,7 +16477,7 @@ void st_select_lex::print(THD *thd, String *str) { str->append(STRING_WITH_LEN(" from ")); /* go through join tree */ - print_join(thd, str, &top_join_list); + print_join(thd, str, &top_join_list, query_type); } // Where @@ -16475,7 +16488,7 @@ void st_select_lex::print(THD *thd, String *str) { str->append(STRING_WITH_LEN(" where ")); if (cur_where) - cur_where->print(str); + cur_where->print(str, query_type); else str->append(cond_value != Item::COND_FALSE ? "1" : "0"); } @@ -16484,7 +16497,7 @@ void st_select_lex::print(THD *thd, String *str) if (group_list.elements) { str->append(STRING_WITH_LEN(" group by ")); - print_order(str, (ORDER *) group_list.first); + print_order(str, (ORDER *) group_list.first, query_type); switch (olap) { case CUBE_TYPE: @@ -16507,7 +16520,7 @@ void st_select_lex::print(THD *thd, String *str) { str->append(STRING_WITH_LEN(" having ")); if (cur_having) - cur_having->print(str); + cur_having->print(str, query_type); else str->append(having_value != Item::COND_FALSE ? "1" : "0"); } @@ -16515,11 +16528,11 @@ void st_select_lex::print(THD *thd, String *str) if (order_list.elements) { str->append(STRING_WITH_LEN(" order by ")); - print_order(str, (ORDER *) order_list.first); + print_order(str, (ORDER *) order_list.first, query_type); } // limit - print_limit(thd, str); + print_limit(thd, str, query_type); // PROCEDURE unsupported here } diff --git a/sql/sql_show.cc b/sql/sql_show.cc index 9f56933a114..2c4251f0fde 100644 --- a/sql/sql_show.cc +++ b/sql/sql_show.cc @@ -1582,7 +1582,7 @@ view_store_create_info(THD *thd, TABLE_LIST *table, String *buff) We can't just use table->query, because our SQL_MODE may trigger a different syntax, like when ANSI_QUOTES is defined. */ - table->view->unit.print(buff); + table->view->unit.print(buff, QT_ORDINARY); if (table->with_check != VIEW_CHECK_NONE) { diff --git a/sql/sql_test.cc b/sql/sql_test.cc index 0fe299d4505..0bce4eb4a82 100644 --- a/sql/sql_test.cc +++ b/sql/sql_test.cc @@ -49,14 +49,14 @@ static const char *lock_descriptions[] = #ifndef DBUG_OFF void -print_where(COND *cond,const char *info) +print_where(COND *cond,const char *info, enum_query_type query_type) { if (cond) { char buff[256]; String str(buff,(uint32) sizeof(buff), system_charset_info); str.length(0); - cond->print(&str); + cond->print(&str, query_type); str.append('\0'); DBUG_LOCK_FILE; (void) fprintf(DBUG_FILE,"\nWHERE:(%s) ",info); @@ -143,7 +143,7 @@ void TEST_filesort(SORT_FIELD *sortorder,uint s_length) else { str.length(0); - sortorder->item->print(&str); + sortorder->item->print(&str, QT_ORDINARY); out.append(str); } } diff --git a/sql/sql_view.cc b/sql/sql_view.cc index f1eb0004577..68cc8e1839a 100644 --- a/sql/sql_view.cc +++ b/sql/sql_view.cc @@ -720,7 +720,42 @@ static int mysql_register_view(THD *thd, TABLE_LIST *view, { LEX *lex= thd->lex; char buff[4096]; - String view_query(buff, sizeof (buff), thd->charset()); + + /* + View definition query -- a SELECT statement that fully defines view. It + is generated from the Item-tree built from the original (specified by + the user) query. The idea is that generated query should eliminates all + ambiguities and fix view structure at CREATE-time (once for all). + Item::print() virtual operation is used to generate view definition + query. + + INFORMATION_SCHEMA query (IS query) -- a SQL statement describing a + view that is shown in INFORMATION_SCHEMA. Basically, it is 'view + definition query' with text literals converted to UTF8 and without + character set introducers. + + For example: + Let's suppose we have: + CREATE TABLE t1(a INT, b INT); + User specified query: + CREATE VIEW v1(x, y) AS SELECT * FROM t1; + Generated query: + SELECT a AS x, b AS y FROM t1; + IS query: + SELECT a AS x, b AS y FROM t1; + + View definition query is stored in the client character set. + */ + char view_query_buff[4096]; + String view_query(view_query_buff, + sizeof (view_query_buff), + thd->charset()); + + char is_query_buff[4096]; + String is_query(is_query_buff, + sizeof (is_query_buff), + system_charset_info); + char md5[MD5_BUFF_LENGTH]; bool can_be_merged; char dir_buff[FN_REFLEN], path_buff[FN_REFLEN]; @@ -728,12 +763,16 @@ static int mysql_register_view(THD *thd, TABLE_LIST *view, int error= 0; DBUG_ENTER("mysql_register_view"); - /* print query */ + /* Generate view definition and IS queries. */ view_query.length(0); + is_query.length(0); { ulong sql_mode= thd->variables.sql_mode & MODE_ANSI_QUOTES; thd->variables.sql_mode&= ~MODE_ANSI_QUOTES; - lex->unit.print(&view_query); + + lex->unit.print(&view_query, QT_ORDINARY); + lex->unit.print(&is_query, QT_IS); + thd->variables.sql_mode|= sql_mode; } DBUG_PRINT("info", ("View: %s", view_query.ptr())); @@ -872,7 +911,8 @@ loop_out: lex_string_set(&view->view_connection_cl_name, view->view_creation_ctx->get_connection_cl()->name); - view->view_body_utf8= lex->view_body_utf8; + view->view_body_utf8.str= is_query.c_ptr_safe(); + view->view_body_utf8.length= is_query.length(); /* Check that table of main select do not used in subqueries. diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index f1689b28719..7c669851db4 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -12005,27 +12005,7 @@ view_tail: if (!lex->select_lex.add_table_to_list(thd, $3, NULL, TL_OPTION_UPDATING)) MYSQL_YYABORT; } - view_list_opt AS - { - THD *thd= YYTHD; - Lex_input_stream *lip= thd->m_lip; - - lip->body_utf8_start(thd, lip->get_cpp_ptr()); - } - view_select - { - THD *thd= YYTHD; - LEX *lex= thd->lex; - Lex_input_stream *lip= thd->m_lip; - - lip->body_utf8_append(lip->get_cpp_ptr()); - - lex->view_body_utf8.str= thd->strmake(lip->get_body_utf8_str(), - lip->get_body_utf8_length()); - lex->view_body_utf8.length= lip->get_body_utf8_length(); - - trim_whitespace(&my_charset_utf8_general_ci, &lex->view_body_utf8); - } + view_list_opt AS view_select ; view_list_opt: diff --git a/sql/table.h b/sql/table.h index 284885658e0..941964ee24e 100644 --- a/sql/table.h +++ b/sql/table.h @@ -1148,7 +1148,7 @@ struct TABLE_LIST return derived || view || schema_table || create && !table->db_stat || !table; } - void print(THD *thd, String *str); + void print(THD *thd, String *str, enum_query_type query_type); bool check_single_table(TABLE_LIST **table, table_map map, TABLE_LIST *view); bool set_insert_values(MEM_ROOT *mem_root); |