Commit 017a0fef authored by unknown's avatar unknown

Merge bk-internal:/home/bk/mysql-5.0-runtime

into  pilot.mysql.com:/data/msvensson/mysql/my50-r-bug30992

parents 662fb20f 2fec8bee
...@@ -6367,4 +6367,180 @@ DROP TABLE t1; ...@@ -6367,4 +6367,180 @@ DROP TABLE t1;
DROP PROCEDURE p1; DROP PROCEDURE p1;
DROP PROCEDURE p2; DROP PROCEDURE p2;
#
# Bug#31035.
#
#
# - Prepare.
#
DROP TABLE IF EXISTS t1;
DROP FUNCTION IF EXISTS f1;
DROP FUNCTION IF EXISTS f2;
DROP FUNCTION IF EXISTS f3;
DROP FUNCTION IF EXISTS f4;
#
# - Create required objects.
#
CREATE TABLE t1(c1 INT);
INSERT INTO t1 VALUES (1), (2), (3);
CREATE FUNCTION f1()
RETURNS INT
NOT DETERMINISTIC
RETURN 1;
CREATE FUNCTION f2(p INT)
RETURNS INT
NOT DETERMINISTIC
RETURN 1;
CREATE FUNCTION f3()
RETURNS INT
DETERMINISTIC
RETURN 1;
CREATE FUNCTION f4(p INT)
RETURNS INT
DETERMINISTIC
RETURN 1;
#
# - Check.
#
SELECT f1() AS a FROM t1 GROUP BY a;
a
1
SELECT f2(@a) AS a FROM t1 GROUP BY a;
a
1
SELECT f3() AS a FROM t1 GROUP BY a;
a
1
SELECT f4(0) AS a FROM t1 GROUP BY a;
a
1
SELECT f4(@a) AS a FROM t1 GROUP BY a;
a
1
#
# - Cleanup.
#
DROP TABLE t1;
DROP FUNCTION f1;
DROP FUNCTION f2;
DROP FUNCTION f3;
DROP FUNCTION f4;
#
# Bug#31191.
#
#
# - Prepare.
#
DROP TABLE IF EXISTS t1;
DROP TABLE IF EXISTS t2;
DROP FUNCTION IF EXISTS f1;
#
# - Create required objects.
#
CREATE TABLE t1 (
id INT(10) UNSIGNED NOT NULL AUTO_INCREMENT,
barcode INT(8) UNSIGNED ZEROFILL nOT NULL,
PRIMARY KEY (id),
UNIQUE KEY barcode (barcode)
);
INSERT INTO t1 (id, barcode) VALUES (1, 12345678);
INSERT INTO t1 (id, barcode) VALUES (2, 12345679);
CREATE TABLE test.t2 (
id INT(10) UNSIGNED NOT NULL AUTO_INCREMENT,
barcode BIGINT(11) UNSIGNED ZEROFILL NOT NULL,
PRIMARY KEY (id)
);
INSERT INTO test.t2 (id, barcode) VALUES (1, 12345106708);
INSERT INTO test.t2 (id, barcode) VALUES (2, 12345106709);
CREATE FUNCTION f1(p INT(8))
RETURNS BIGINT(11) UNSIGNED
READS SQL DATA
RETURN FLOOR(p/1000)*1000000 + 100000 + FLOOR((p MOD 1000)/10)*100 + (p MOD 10);
#
# - Check.
#
SELECT DISTINCT t1.barcode, f1(t1.barcode)
FROM t1
INNER JOIN t2
ON f1(t1.barcode) = t2.barcode
WHERE t1.barcode=12345678;
barcode f1(t1.barcode)
12345678 12345106708
#
# - Cleanup.
#
DROP TABLE t1;
DROP TABLE t2;
DROP FUNCTION f1;
#
# Bug#31226.
#
#
# - Prepare.
#
DROP TABLE IF EXISTS t1;
DROP FUNCTION IF EXISTS f1;
#
# - Create required objects.
#
CREATE TABLE t1(id INT);
INSERT INTO t1 VALUES (1), (2), (3);
CREATE FUNCTION f1()
RETURNS DATETIME
NOT DETERMINISTIC NO SQL
RETURN NOW();
#
# - Check.
#
SELECT f1() FROM t1 GROUP BY 1;
f1()
<timestamp>
#
# - Cleanup.
#
DROP TABLE t1;
DROP FUNCTION f1;
End of 5.0 tests End of 5.0 tests
...@@ -7354,4 +7354,294 @@ DROP TABLE t1; ...@@ -7354,4 +7354,294 @@ DROP TABLE t1;
DROP PROCEDURE p1; DROP PROCEDURE p1;
DROP PROCEDURE p2; DROP PROCEDURE p2;
###########################################################################
#
# Bug#31035: select from function, group by result crasher.
#
###########################################################################
--echo
--echo #
--echo # Bug#31035.
--echo #
--echo
--echo #
--echo # - Prepare.
--echo #
--echo
--disable_warnings
DROP TABLE IF EXISTS t1;
DROP FUNCTION IF EXISTS f1;
DROP FUNCTION IF EXISTS f2;
DROP FUNCTION IF EXISTS f3;
DROP FUNCTION IF EXISTS f4;
--enable_warnings
--echo
--echo #
--echo # - Create required objects.
--echo #
--echo
CREATE TABLE t1(c1 INT);
--echo
INSERT INTO t1 VALUES (1), (2), (3);
--echo
CREATE FUNCTION f1()
RETURNS INT
NOT DETERMINISTIC
RETURN 1;
--echo
CREATE FUNCTION f2(p INT)
RETURNS INT
NOT DETERMINISTIC
RETURN 1;
--echo
CREATE FUNCTION f3()
RETURNS INT
DETERMINISTIC
RETURN 1;
--echo
CREATE FUNCTION f4(p INT)
RETURNS INT
DETERMINISTIC
RETURN 1;
--echo
--echo #
--echo # - Check.
--echo #
--echo
# Not deterministic function, no arguments.
SELECT f1() AS a FROM t1 GROUP BY a;
--echo
# Not deterministic function, non-constant argument.
SELECT f2(@a) AS a FROM t1 GROUP BY a;
--echo
# Deterministic function, no arguments.
SELECT f3() AS a FROM t1 GROUP BY a;
--echo
# Deterministic function, constant argument.
SELECT f4(0) AS a FROM t1 GROUP BY a;
--echo
# Deterministic function, non-constant argument.
SELECT f4(@a) AS a FROM t1 GROUP BY a;
--echo
--echo #
--echo # - Cleanup.
--echo #
--echo
DROP TABLE t1;
DROP FUNCTION f1;
DROP FUNCTION f2;
DROP FUNCTION f3;
DROP FUNCTION f4;
--echo
###########################################################################
#
# Bug#31191: JOIN in combination with stored function crashes the server.
#
###########################################################################
--echo #
--echo # Bug#31191.
--echo #
--echo
--echo #
--echo # - Prepare.
--echo #
--echo
--disable_warnings
DROP TABLE IF EXISTS t1;
DROP TABLE IF EXISTS t2;
DROP FUNCTION IF EXISTS f1;
--enable_warnings
--echo
--echo #
--echo # - Create required objects.
--echo #
--echo
CREATE TABLE t1 (
id INT(10) UNSIGNED NOT NULL AUTO_INCREMENT,
barcode INT(8) UNSIGNED ZEROFILL nOT NULL,
PRIMARY KEY (id),
UNIQUE KEY barcode (barcode)
);
--echo
INSERT INTO t1 (id, barcode) VALUES (1, 12345678);
INSERT INTO t1 (id, barcode) VALUES (2, 12345679);
--echo
CREATE TABLE test.t2 (
id INT(10) UNSIGNED NOT NULL AUTO_INCREMENT,
barcode BIGINT(11) UNSIGNED ZEROFILL NOT NULL,
PRIMARY KEY (id)
);
--echo
INSERT INTO test.t2 (id, barcode) VALUES (1, 12345106708);
INSERT INTO test.t2 (id, barcode) VALUES (2, 12345106709);
--echo
CREATE FUNCTION f1(p INT(8))
RETURNS BIGINT(11) UNSIGNED
READS SQL DATA
RETURN FLOOR(p/1000)*1000000 + 100000 + FLOOR((p MOD 1000)/10)*100 + (p MOD 10);
--echo
--echo #
--echo # - Check.
--echo #
--echo
SELECT DISTINCT t1.barcode, f1(t1.barcode)
FROM t1
INNER JOIN t2
ON f1(t1.barcode) = t2.barcode
WHERE t1.barcode=12345678;
--echo
--echo #
--echo # - Cleanup.
--echo #
--echo
DROP TABLE t1;
DROP TABLE t2;
DROP FUNCTION f1;
--echo
###########################################################################
#
# Bug#31226: Group by function crashes mysql.
#
###########################################################################
--echo #
--echo # Bug#31226.
--echo #
--echo
--echo #
--echo # - Prepare.
--echo #
--echo
--disable_warnings
DROP TABLE IF EXISTS t1;
DROP FUNCTION IF EXISTS f1;
--enable_warnings
--echo
--echo #
--echo # - Create required objects.
--echo #
--echo
CREATE TABLE t1(id INT);
--echo
INSERT INTO t1 VALUES (1), (2), (3);
--echo
CREATE FUNCTION f1()
RETURNS DATETIME
NOT DETERMINISTIC NO SQL
RETURN NOW();
--echo
--echo #
--echo # - Check.
--echo #
--echo
--replace_column 1 <timestamp>
SELECT f1() FROM t1 GROUP BY 1;
--echo
--echo #
--echo # - Cleanup.
--echo #
--echo
DROP TABLE t1;
DROP FUNCTION f1;
--echo
###########################################################################
--echo End of 5.0 tests --echo End of 5.0 tests
...@@ -5583,8 +5583,13 @@ Item_func_sp::fix_fields(THD *thd, Item **ref) ...@@ -5583,8 +5583,13 @@ Item_func_sp::fix_fields(THD *thd, Item **ref)
#endif /* ! NO_EMBEDDED_ACCESS_CHECKS */ #endif /* ! NO_EMBEDDED_ACCESS_CHECKS */
} }
if (!m_sp->m_chistics->detistic) if (!m_sp->m_chistics->detistic)
used_tables_cache |= RAND_TABLE_BIT; {
used_tables_cache |= RAND_TABLE_BIT;
const_item_cache= FALSE;
}
DBUG_RETURN(res); DBUG_RETURN(res);
} }
...@@ -5592,6 +5597,10 @@ Item_func_sp::fix_fields(THD *thd, Item **ref) ...@@ -5592,6 +5597,10 @@ Item_func_sp::fix_fields(THD *thd, Item **ref)
void Item_func_sp::update_used_tables() void Item_func_sp::update_used_tables()
{ {
Item_func::update_used_tables(); Item_func::update_used_tables();
if (!m_sp->m_chistics->detistic) if (!m_sp->m_chistics->detistic)
used_tables_cache |= RAND_TABLE_BIT; {
used_tables_cache |= RAND_TABLE_BIT;
const_item_cache= FALSE;
}
} }
...@@ -65,11 +65,6 @@ ...@@ -65,11 +65,6 @@
static enum enum_ha_read_modes rkey_to_rnext[]= static enum enum_ha_read_modes rkey_to_rnext[]=
{ RNEXT_SAME, RNEXT, RPREV, RNEXT, RPREV, RNEXT, RPREV, RPREV }; { RNEXT_SAME, RNEXT, RPREV, RNEXT, RPREV, RNEXT, RPREV, RPREV };
#define HANDLER_TABLES_HACK(thd) { \
TABLE *tmp=thd->open_tables; \
thd->open_tables=thd->handler_tables; \
thd->handler_tables=tmp; }
static int mysql_ha_flush_table(THD *thd, TABLE **table_ptr, uint mode_flags); static int mysql_ha_flush_table(THD *thd, TABLE **table_ptr, uint mode_flags);
...@@ -187,6 +182,7 @@ bool mysql_ha_open(THD *thd, TABLE_LIST *tables, bool reopen) ...@@ -187,6 +182,7 @@ bool mysql_ha_open(THD *thd, TABLE_LIST *tables, bool reopen)
char *db, *name, *alias; char *db, *name, *alias;
uint dblen, namelen, aliaslen, counter; uint dblen, namelen, aliaslen, counter;
int error; int error;
TABLE *backup_open_tables, *backup_handler_tables;
DBUG_ENTER("mysql_ha_open"); DBUG_ENTER("mysql_ha_open");
DBUG_PRINT("enter",("'%s'.'%s' as '%s' reopen: %d", DBUG_PRINT("enter",("'%s'.'%s' as '%s' reopen: %d",
tables->db, tables->table_name, tables->alias, tables->db, tables->table_name, tables->alias,
...@@ -215,18 +211,31 @@ bool mysql_ha_open(THD *thd, TABLE_LIST *tables, bool reopen) ...@@ -215,18 +211,31 @@ bool mysql_ha_open(THD *thd, TABLE_LIST *tables, bool reopen)
} }
} }
/* save open_ and handler_ tables state */
backup_open_tables= thd->open_tables;
backup_handler_tables= thd->handler_tables;
/* no pre-opened tables */
thd->open_tables= NULL;
/* to avoid flushes */
thd->handler_tables= NULL;
/* /*
open_tables() will set 'tables->table' if successful. open_tables() will set 'tables->table' if successful.
It must be NULL for a real open when calling open_tables(). It must be NULL for a real open when calling open_tables().
*/ */
DBUG_ASSERT(! tables->table); DBUG_ASSERT(! tables->table);
HANDLER_TABLES_HACK(thd);
/* for now HANDLER can be used only for real TABLES */ /* for now HANDLER can be used only for real TABLES */
tables->required_type= FRMTYPE_TABLE; tables->required_type= FRMTYPE_TABLE;
error= open_tables(thd, &tables, &counter, 0); error= open_tables(thd, &tables, &counter, 0);
HANDLER_TABLES_HACK(thd); /* restore the state and merge the opened table into handler_tables list */
thd->handler_tables= thd->open_tables ?
thd->open_tables->next= backup_handler_tables,
thd->open_tables : backup_handler_tables;
thd->open_tables= backup_open_tables;
if (error) if (error)
goto err; goto err;
...@@ -351,7 +360,7 @@ bool mysql_ha_read(THD *thd, TABLE_LIST *tables, ...@@ -351,7 +360,7 @@ bool mysql_ha_read(THD *thd, TABLE_LIST *tables,
ha_rows select_limit_cnt, ha_rows offset_limit_cnt) ha_rows select_limit_cnt, ha_rows offset_limit_cnt)
{ {
TABLE_LIST *hash_tables; TABLE_LIST *hash_tables;
TABLE *table; TABLE *table, *backup_open_tables, *backup_handler_tables;
MYSQL_LOCK *lock; MYSQL_LOCK *lock;
List<Item> list; List<Item> list;
Protocol *protocol= thd->protocol; Protocol *protocol= thd->protocol;
...@@ -361,7 +370,7 @@ bool mysql_ha_read(THD *thd, TABLE_LIST *tables, ...@@ -361,7 +370,7 @@ bool mysql_ha_read(THD *thd, TABLE_LIST *tables,
uint num_rows; uint num_rows;
byte *key; byte *key;
uint key_len; uint key_len;
bool not_used; bool need_reopen;
DBUG_ENTER("mysql_ha_read"); DBUG_ENTER("mysql_ha_read");
DBUG_PRINT("enter",("'%s'.'%s' as '%s'", DBUG_PRINT("enter",("'%s'.'%s' as '%s'",
tables->db, tables->table_name, tables->alias)); tables->db, tables->table_name, tables->alias));
...@@ -375,6 +384,7 @@ bool mysql_ha_read(THD *thd, TABLE_LIST *tables, ...@@ -375,6 +384,7 @@ bool mysql_ha_read(THD *thd, TABLE_LIST *tables,
List_iterator<Item> it(list); List_iterator<Item> it(list);
it++; it++;
retry:
if ((hash_tables= (TABLE_LIST*) hash_search(&thd->handler_tables_hash, if ((hash_tables= (TABLE_LIST*) hash_search(&thd->handler_tables_hash,
(byte*) tables->alias, (byte*) tables->alias,
strlen(tables->alias) + 1))) strlen(tables->alias) + 1)))
...@@ -427,9 +437,28 @@ bool mysql_ha_read(THD *thd, TABLE_LIST *tables, ...@@ -427,9 +437,28 @@ bool mysql_ha_read(THD *thd, TABLE_LIST *tables,
} }
tables->table=table; tables->table=table;
HANDLER_TABLES_HACK(thd); /* save open_ and handler_ tables state */
lock= mysql_lock_tables(thd, &tables->table, 1, 0, &not_used); backup_open_tables= thd->open_tables;
HANDLER_TABLES_HACK(thd); backup_handler_tables= thd->handler_tables;
/* no pre-opened tables */
thd->open_tables= NULL;
/* to avoid flushes */
thd->handler_tables= NULL;
lock= mysql_lock_tables(thd, &tables->table, 1,
MYSQL_LOCK_NOTIFY_IF_NEED_REOPEN, &need_reopen);
/* restore previous context */
thd->handler_tables= backup_handler_tables;
thd->open_tables= backup_open_tables;
if (need_reopen)
{
mysql_ha_close_table(thd, tables);
hash_tables->table= NULL;
goto retry;
}
if (!lock) if (!lock)
goto err0; // mysql_lock_tables() printed error message already goto err0; // mysql_lock_tables() printed error message already
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment