Commit 8ad2472e authored by istruewing@chilla.local's avatar istruewing@chilla.local

Merge bk-internal.mysql.com:/home/bk/mysql-5.1

into  chilla.local:/home/mydev/mysql-5.1-axmrg
parents 12960809 facba6ba
...@@ -20,6 +20,14 @@ CREATE TABLE first_db.t1 ( ...@@ -20,6 +20,14 @@ CREATE TABLE first_db.t1 (
`name` varchar(64) NOT NULL default '' `name` varchar(64) NOT NULL default ''
) )
DEFAULT CHARSET=latin1; DEFAULT CHARSET=latin1;
DROP TABLE IF EXISTS first_db.t2;
Warnings:
Note 1051 Unknown table 't2'
CREATE TABLE first_db.t2 (
`id` int(20) NOT NULL,
`name` varchar(64) NOT NULL default ''
)
DEFAULT CHARSET=latin1;
use second_db; use second_db;
DROP TABLE IF EXISTS second_db.t1; DROP TABLE IF EXISTS second_db.t1;
Warnings: Warnings:
...@@ -29,6 +37,14 @@ CREATE TABLE second_db.t1 ( ...@@ -29,6 +37,14 @@ CREATE TABLE second_db.t1 (
`name` varchar(64) NOT NULL default '' `name` varchar(64) NOT NULL default ''
) )
DEFAULT CHARSET=latin1; DEFAULT CHARSET=latin1;
DROP TABLE IF EXISTS second_db.t2;
Warnings:
Note 1051 Unknown table 't2'
CREATE TABLE second_db.t2 (
`id` int(20) NOT NULL,
`name` varchar(64) NOT NULL default ''
)
DEFAULT CHARSET=latin1;
drop server if exists 'server_one'; drop server if exists 'server_one';
create server 'server_one' foreign data wrapper 'mysql' options create server 'server_one' foreign data wrapper 'mysql' options
(HOST '127.0.0.1', (HOST '127.0.0.1',
...@@ -60,10 +76,10 @@ CREATE TABLE federated.old ( ...@@ -60,10 +76,10 @@ CREATE TABLE federated.old (
) )
ENGINE="FEDERATED" DEFAULT CHARSET=latin1 ENGINE="FEDERATED" DEFAULT CHARSET=latin1
CONNECTION='mysql://root@127.0.0.1:SLAVE_PORT/first_db/t1'; CONNECTION='mysql://root@127.0.0.1:SLAVE_PORT/first_db/t1';
INSERT INTO federated.old (id, name) values (1, 'federated.old url'); INSERT INTO federated.old (id, name) values (1, 'federated.old-> first_db.t1, url format');
SELECT * FROM federated.old; SELECT * FROM federated.old;
id name id name
1 federated.old url 1 federated.old-> first_db.t1, url format
DROP TABLE IF EXISTS federated.old2; DROP TABLE IF EXISTS federated.old2;
Warnings: Warnings:
Note 1051 Unknown table 'old2' Note 1051 Unknown table 'old2'
...@@ -72,8 +88,37 @@ CREATE TABLE federated.old2 ( ...@@ -72,8 +88,37 @@ CREATE TABLE federated.old2 (
`name` varchar(64) NOT NULL default '' `name` varchar(64) NOT NULL default ''
) )
ENGINE="FEDERATED" DEFAULT CHARSET=latin1 ENGINE="FEDERATED" DEFAULT CHARSET=latin1
CONNECTION='mysql://root@127.0.0.1:SLAVE_PORT/first_db/t2';
INSERT INTO federated.old2 (id, name) values (1, 'federated.old2-> first_db.t2, url format');
SELECT * FROM federated.old2;
id name
1 federated.old2-> first_db.t2, url format
DROP TABLE IF EXISTS federated.urldb2t1;
Warnings:
Note 1051 Unknown table 'urldb2t1'
CREATE TABLE federated.urldb2t1 (
`id` int(20) NOT NULL,
`name` varchar(64) NOT NULL default ''
)
ENGINE="FEDERATED" DEFAULT CHARSET=latin1
CONNECTION='mysql://root@127.0.0.1:SLAVE_PORT/second_db/t1'; CONNECTION='mysql://root@127.0.0.1:SLAVE_PORT/second_db/t1';
INSERT INTO federated.old2 (id, name) values (1, 'federated.old2 url'); INSERT INTO federated.urldb2t1 (id, name) values (1, 'federated.urldb2t1 -> second_db.t1, url format');
SELECT * FROM federated.urldb2t1;
id name
1 federated.urldb2t1 -> second_db.t1, url format
DROP TABLE IF EXISTS federated.urldb2t2;
Warnings:
Note 1051 Unknown table 'urldb2t2'
CREATE TABLE federated.urldb2t2 (
`id` int(20) NOT NULL,
`name` varchar(64) NOT NULL default ''
)
ENGINE="FEDERATED" DEFAULT CHARSET=latin1
CONNECTION='mysql://root@127.0.0.1:SLAVE_PORT/second_db/t2';
INSERT INTO federated.urldb2t2 (id, name) values (1, 'federated.urldb2t2 -> second_db.t2, url format');
SELECT * FROM federated.urldb2t2;
id name
1 federated.urldb2t2 -> second_db.t2, url format
DROP TABLE IF EXISTS federated.t1; DROP TABLE IF EXISTS federated.t1;
Warnings: Warnings:
Note 1051 Unknown table 't1' Note 1051 Unknown table 't1'
...@@ -83,18 +128,38 @@ CREATE TABLE federated.t1 ( ...@@ -83,18 +128,38 @@ CREATE TABLE federated.t1 (
) )
ENGINE="FEDERATED" DEFAULT CHARSET=latin1 ENGINE="FEDERATED" DEFAULT CHARSET=latin1
CONNECTION='server_one'; CONNECTION='server_one';
INSERT INTO federated.t1 (id, name) values (1, 'server_one, new scheme'); INSERT INTO federated.t1 (id, name) values (1, 'server_one, new scheme, first_db.t1');
SELECT * FROM federated.t1; SELECT * FROM federated.t1;
id name id name
1 federated.old url 1 federated.old-> first_db.t1, url format
1 server_one, new scheme 1 server_one, new scheme, first_db.t1
DROP TABLE IF EXISTS federated.whatever;
Warnings:
Note 1051 Unknown table 'whatever'
CREATE TABLE federated.whatever (
`id` int(20) NOT NULL,
`name` varchar(64) NOT NULL default ''
)
ENGINE="FEDERATED" DEFAULT CHARSET=latin1
CONNECTION='server_one/t1';
INSERT INTO federated.whatever (id, name) values (1, 'server_one, new scheme, whatever, first_db.t1');
SELECT * FROM federated.whatever;
id name
1 federated.old-> first_db.t1, url format
1 server_one, new scheme, first_db.t1
1 server_one, new scheme, whatever, first_db.t1
ALTER SERVER 'server_one' options(DATABASE 'second_db'); ALTER SERVER 'server_one' options(DATABASE 'second_db');
flush tables; INSERT INTO federated.t1 (id, name) values (1, 'server_two, new scheme, second_db.t1');
INSERT INTO federated.t1 (id, name) values (1, 'server_two, new scheme');
SELECT * FROM federated.t1; SELECT * FROM federated.t1;
id name id name
1 federated.old2 url 1 federated.urldb2t1 -> second_db.t1, url format
1 server_two, new scheme 1 server_two, new scheme, second_db.t1
INSERT INTO federated.whatever (id, name) values (1, 'server_two, new scheme, whatever, second_db.t1');
SELECT * FROM federated.whatever;
id name
1 federated.urldb2t1 -> second_db.t1, url format
1 server_two, new scheme, second_db.t1
1 server_two, new scheme, whatever, second_db.t1
drop table federated.t1; drop table federated.t1;
drop server 'server_one'; drop server 'server_one';
drop server 'server_two'; drop server 'server_two';
...@@ -104,6 +169,116 @@ drop table first_db.t1; ...@@ -104,6 +169,116 @@ drop table first_db.t1;
drop table second_db.t1; drop table second_db.t1;
drop database first_db; drop database first_db;
drop database second_db; drop database second_db;
create database db_legitimate;
create database db_bogus;
use db_legitimate;
CREATE TABLE db_legitimate.t1 (
`id` int(20) NOT NULL,
`name` varchar(64) NOT NULL default ''
);
INSERT INTO db_legitimate.t1 VALUES ('1','this is legitimate');
use db_bogus;
CREATE TABLE db_bogus.t1 (
`id` int(20) NOT NULL,
`name` varchar(64) NOT NULL default ''
)
;
INSERT INTO db_bogus.t1 VALUES ('2','this is bogus');
create server 's1' foreign data wrapper 'mysql' options
(HOST '127.0.0.1',
DATABASE 'db_legitimate',
USER 'root',
PASSWORD '',
PORT SLAVE_PORT,
SOCKET '',
OWNER 'root');
create user guest_select@localhost;
grant select on federated.* to guest_select@localhost;
create user guest_super@localhost;
grant select,SUPER,RELOAD on *.* to guest_super@localhost;
create user guest_usage@localhost;
grant usage on *.* to guest_usage@localhost;
CREATE TABLE federated.t1 (
`id` int(20) NOT NULL,
`name` varchar(64) NOT NULL default ''
) ENGINE = FEDERATED CONNECTION = 's1';
select * from federated.t1;
id name
1 this is legitimate
alter server s1 options (database 'db_bogus');
ERROR 42000: Access denied; you need the SUPER privilege for this operation
flush tables;
select * from federated.t1;
id name
1 this is legitimate
alter server s1 options (database 'db_bogus');
ERROR 42000: Access denied; you need the SUPER privilege for this operation
flush tables;
select * from federated.t1;
id name
1 this is legitimate
alter server s1 options (database 'db_bogus');
flush tables;
select * from federated.t1;
id name
2 this is bogus
drop server if exists 's1';
ERROR 42000: Access denied; you need the SUPER privilege for this operation
create server 's1' foreign data wrapper 'mysql' options
(HOST '127.0.0.1',
DATABASE 'db_legitimate',
USER 'root',
PASSWORD '',
PORT SLAVE_PORT,
SOCKET '',
OWNER 'root');
ERROR 42000: Access denied; you need the SUPER privilege for this operation
drop server 's1';
create server 's1' foreign data wrapper 'mysql' options
(HOST '127.0.0.1',
DATABASE 'db_legitimate',
USER 'root',
PASSWORD '',
PORT SLAVE_PORT,
SOCKET '',
OWNER 'root');
flush tables;
select * from federated.t1;
id name
1 this is legitimate
drop database db_legitimate;
drop database db_bogus;
drop user guest_super@localhost;
drop user guest_usage@localhost;
drop user guest_select@localhost;
drop table federated.t1;
drop server 's1';
# End of 5.1 tests
use test;
create procedure p1 ()
begin
DECLARE v INT DEFAULT 0;
DECLARE e INT DEFAULT 0;
DECLARE CONTINUE HANDLER FOR SQLEXCEPTION SET e = e + 1;
WHILE v < 10000 do
CREATE SERVER s
FOREIGN DATA WRAPPER mysql
OPTIONS (USER 'Remote', HOST '192.168.1.106', DATABASE 'test');
ALTER SERVER s OPTIONS (USER 'Remote');
DROP SERVER s;
SET v = v + 1;
END WHILE;
SELECT e > 0;
END//
use test;
call p1();
call p1();
e > 0
1
e > 0
1
drop procedure p1;
drop server if exists s;
DROP TABLE IF EXISTS federated.t1; DROP TABLE IF EXISTS federated.t1;
DROP DATABASE IF EXISTS federated; DROP DATABASE IF EXISTS federated;
DROP TABLE IF EXISTS federated.t1; DROP TABLE IF EXISTS federated.t1;
......
...@@ -280,6 +280,33 @@ a ...@@ -280,6 +280,33 @@ a
1 1
1 1
drop table t1; drop table t1;
CREATE TABLE t1 (
c1 CHAR(3),
c2 INTEGER,
KEY USING BTREE(c1),
KEY USING BTREE(c2)
) ENGINE= MEMORY;
INSERT INTO t1 VALUES ('ABC',0), ('A',0), ('B',0), ('C',0);
UPDATE t1 SET c2= c2 + 1 WHERE c1 = 'A';
SELECT * FROM t1;
c1 c2
ABC 0
A 1
B 0
C 0
DROP TABLE t1;
CREATE TABLE t1 (
c1 ENUM('1', '2'),
UNIQUE USING BTREE(c1)
) ENGINE= MEMORY DEFAULT CHARSET= utf8;
INSERT INTO t1 VALUES('1'), ('2');
DROP TABLE t1;
CREATE TABLE t1 (
c1 SET('1', '2'),
UNIQUE USING BTREE(c1)
) ENGINE= MEMORY DEFAULT CHARSET= utf8;
INSERT INTO t1 VALUES('1'), ('2');
DROP TABLE t1;
End of 4.1 tests End of 4.1 tests
CREATE TABLE t1(val INT, KEY USING BTREE(val)) ENGINE=memory; CREATE TABLE t1(val INT, KEY USING BTREE(val)) ENGINE=memory;
INSERT INTO t1 VALUES(0); INSERT INTO t1 VALUES(0);
......
...@@ -943,6 +943,156 @@ SHOW TABLE STATUS LIKE 't1'; ...@@ -943,6 +943,156 @@ SHOW TABLE STATUS LIKE 't1';
Name Engine Version Row_format Rows Avg_row_length Data_length Max_data_length Index_length Data_free Auto_increment Create_time Update_time Check_time Collation Checksum Create_options Comment Name Engine Version Row_format Rows Avg_row_length Data_length Max_data_length Index_length Data_free Auto_increment Create_time Update_time Check_time Collation Checksum Create_options Comment
t1 MyISAM 10 Dynamic X X X 72057594037927935 X X X X X X latin1_swedish_ci X max_rows=4100100100 avg_row_length=70100 t1 MyISAM 10 Dynamic X X X 72057594037927935 X X X X X X latin1_swedish_ci X max_rows=4100100100 avg_row_length=70100
DROP TABLE t1; DROP TABLE t1;
CREATE TABLE t1 (c1 TEXT NOT NULL, KEY c1 (c1(10))) ENGINE=MyISAM;
INSERT INTO t1 VALUES
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(''), (''), (''), (''),
(' B'), (' B'), (' B'), (' B');
SELECT DISTINCT COUNT(*) FROM t1 WHERE c1 = '';
COUNT(*)
4
SELECT DISTINCT length(c1), c1 FROM t1 WHERE c1 = '';
length(c1) c1
0
SELECT DISTINCT COUNT(*) FROM t1 IGNORE INDEX (c1) WHERE c1 = '';
COUNT(*)
4
SELECT DISTINCT length(c1), c1 FROM t1 IGNORE INDEX (c1) WHERE c1 = '';
length(c1) c1
0
SELECT DISTINCT length(c1), c1 FROM t1 ORDER BY c1;
length(c1) c1
0
2 A
2 B
DROP TABLE t1;
End of 4.1 tests End of 4.1 tests
set storage_engine=MyISAM; set storage_engine=MyISAM;
drop table if exists t1,t2,t3; drop table if exists t1,t2,t3;
......
...@@ -17,6 +17,13 @@ CREATE TABLE first_db.t1 ( ...@@ -17,6 +17,13 @@ CREATE TABLE first_db.t1 (
) )
DEFAULT CHARSET=latin1; DEFAULT CHARSET=latin1;
DROP TABLE IF EXISTS first_db.t2;
CREATE TABLE first_db.t2 (
`id` int(20) NOT NULL,
`name` varchar(64) NOT NULL default ''
)
DEFAULT CHARSET=latin1;
use second_db; use second_db;
DROP TABLE IF EXISTS second_db.t1; DROP TABLE IF EXISTS second_db.t1;
CREATE TABLE second_db.t1 ( CREATE TABLE second_db.t1 (
...@@ -25,6 +32,13 @@ CREATE TABLE second_db.t1 ( ...@@ -25,6 +32,13 @@ CREATE TABLE second_db.t1 (
) )
DEFAULT CHARSET=latin1; DEFAULT CHARSET=latin1;
DROP TABLE IF EXISTS second_db.t2;
CREATE TABLE second_db.t2 (
`id` int(20) NOT NULL,
`name` varchar(64) NOT NULL default ''
)
DEFAULT CHARSET=latin1;
connection master; connection master;
drop server if exists 'server_one'; drop server if exists 'server_one';
...@@ -61,7 +75,7 @@ eval CREATE TABLE federated.old ( ...@@ -61,7 +75,7 @@ eval CREATE TABLE federated.old (
ENGINE="FEDERATED" DEFAULT CHARSET=latin1 ENGINE="FEDERATED" DEFAULT CHARSET=latin1
CONNECTION='mysql://root@127.0.0.1:$SLAVE_MYPORT/first_db/t1'; CONNECTION='mysql://root@127.0.0.1:$SLAVE_MYPORT/first_db/t1';
INSERT INTO federated.old (id, name) values (1, 'federated.old url'); INSERT INTO federated.old (id, name) values (1, 'federated.old-> first_db.t1, url format');
SELECT * FROM federated.old; SELECT * FROM federated.old;
...@@ -72,9 +86,32 @@ eval CREATE TABLE federated.old2 ( ...@@ -72,9 +86,32 @@ eval CREATE TABLE federated.old2 (
`name` varchar(64) NOT NULL default '' `name` varchar(64) NOT NULL default ''
) )
ENGINE="FEDERATED" DEFAULT CHARSET=latin1 ENGINE="FEDERATED" DEFAULT CHARSET=latin1
CONNECTION='mysql://root@127.0.0.1:$SLAVE_MYPORT/first_db/t2';
INSERT INTO federated.old2 (id, name) values (1, 'federated.old2-> first_db.t2, url format');
SELECT * FROM federated.old2;
DROP TABLE IF EXISTS federated.urldb2t1;
--replace_result $SLAVE_MYPORT SLAVE_PORT
eval CREATE TABLE federated.urldb2t1 (
`id` int(20) NOT NULL,
`name` varchar(64) NOT NULL default ''
)
ENGINE="FEDERATED" DEFAULT CHARSET=latin1
CONNECTION='mysql://root@127.0.0.1:$SLAVE_MYPORT/second_db/t1'; CONNECTION='mysql://root@127.0.0.1:$SLAVE_MYPORT/second_db/t1';
INSERT INTO federated.urldb2t1 (id, name) values (1, 'federated.urldb2t1 -> second_db.t1, url format');
SELECT * FROM federated.urldb2t1;
INSERT INTO federated.old2 (id, name) values (1, 'federated.old2 url'); DROP TABLE IF EXISTS federated.urldb2t2;
--replace_result $SLAVE_MYPORT SLAVE_PORT
eval CREATE TABLE federated.urldb2t2 (
`id` int(20) NOT NULL,
`name` varchar(64) NOT NULL default ''
)
ENGINE="FEDERATED" DEFAULT CHARSET=latin1
CONNECTION='mysql://root@127.0.0.1:$SLAVE_MYPORT/second_db/t2';
INSERT INTO federated.urldb2t2 (id, name) values (1, 'federated.urldb2t2 -> second_db.t2, url format');
SELECT * FROM federated.urldb2t2;
DROP TABLE IF EXISTS federated.t1; DROP TABLE IF EXISTS federated.t1;
CREATE TABLE federated.t1 ( CREATE TABLE federated.t1 (
...@@ -84,17 +121,30 @@ CREATE TABLE federated.t1 ( ...@@ -84,17 +121,30 @@ CREATE TABLE federated.t1 (
ENGINE="FEDERATED" DEFAULT CHARSET=latin1 ENGINE="FEDERATED" DEFAULT CHARSET=latin1
CONNECTION='server_one'; CONNECTION='server_one';
INSERT INTO federated.t1 (id, name) values (1, 'server_one, new scheme'); INSERT INTO federated.t1 (id, name) values (1, 'server_one, new scheme, first_db.t1');
SELECT * FROM federated.t1; SELECT * FROM federated.t1;
DROP TABLE IF EXISTS federated.whatever;
CREATE TABLE federated.whatever (
`id` int(20) NOT NULL,
`name` varchar(64) NOT NULL default ''
)
ENGINE="FEDERATED" DEFAULT CHARSET=latin1
CONNECTION='server_one/t1';
INSERT INTO federated.whatever (id, name) values (1, 'server_one, new scheme, whatever, first_db.t1');
SELECT * FROM federated.whatever;
ALTER SERVER 'server_one' options(DATABASE 'second_db'); ALTER SERVER 'server_one' options(DATABASE 'second_db');
flush tables; # FLUSH TABLES is now unneccessary
INSERT INTO federated.t1 (id, name) values (1, 'server_two, new scheme'); INSERT INTO federated.t1 (id, name) values (1, 'server_two, new scheme, second_db.t1');
SELECT * FROM federated.t1; SELECT * FROM federated.t1;
INSERT INTO federated.whatever (id, name) values (1, 'server_two, new scheme, whatever, second_db.t1');
SELECT * FROM federated.whatever;
drop table federated.t1; drop table federated.t1;
drop server 'server_one'; drop server 'server_one';
...@@ -107,4 +157,166 @@ drop table second_db.t1; ...@@ -107,4 +157,166 @@ drop table second_db.t1;
drop database first_db; drop database first_db;
drop database second_db; drop database second_db;
#
# Bug#25671 - CREATE/DROP/ALTER SERVER should require privileges
#
# Changes to SERVER declarations should require SUPER privilege.
# Based upon test case by Giuseppe Maxia
create database db_legitimate;
create database db_bogus;
use db_legitimate;
CREATE TABLE db_legitimate.t1 (
`id` int(20) NOT NULL,
`name` varchar(64) NOT NULL default ''
);
INSERT INTO db_legitimate.t1 VALUES ('1','this is legitimate');
use db_bogus;
CREATE TABLE db_bogus.t1 (
`id` int(20) NOT NULL,
`name` varchar(64) NOT NULL default ''
)
;
INSERT INTO db_bogus.t1 VALUES ('2','this is bogus');
connection master;
--replace_result $SLAVE_MYPORT SLAVE_PORT
eval create server 's1' foreign data wrapper 'mysql' options
(HOST '127.0.0.1',
DATABASE 'db_legitimate',
USER 'root',
PASSWORD '',
PORT $SLAVE_MYPORT,
SOCKET '',
OWNER 'root');
create user guest_select@localhost;
grant select on federated.* to guest_select@localhost;
create user guest_super@localhost;
grant select,SUPER,RELOAD on *.* to guest_super@localhost;
create user guest_usage@localhost;
grant usage on *.* to guest_usage@localhost;
CREATE TABLE federated.t1 (
`id` int(20) NOT NULL,
`name` varchar(64) NOT NULL default ''
) ENGINE = FEDERATED CONNECTION = 's1';
select * from federated.t1;
connect (conn_select,127.0.0.1,guest_select,,federated,$MASTER_MYPORT);
connect (conn_usage,127.0.0.1,guest_usage,,,$MASTER_MYPORT);
connect (conn_super,127.0.0.1,guest_super,,,$MASTER_MYPORT);
connection conn_select;
--error ER_SPECIFIC_ACCESS_DENIED_ERROR
alter server s1 options (database 'db_bogus');
connection master;
flush tables;
select * from federated.t1;
connection conn_usage;
--error ER_SPECIFIC_ACCESS_DENIED_ERROR
alter server s1 options (database 'db_bogus');
connection master;
flush tables;
select * from federated.t1;
connection conn_super;
alter server s1 options (database 'db_bogus');
connection master;
flush tables;
select * from federated.t1;
connection conn_select;
--error ER_SPECIFIC_ACCESS_DENIED_ERROR
drop server if exists 's1';
--replace_result $SLAVE_MYPORT SLAVE_PORT
--error ER_SPECIFIC_ACCESS_DENIED_ERROR
eval create server 's1' foreign data wrapper 'mysql' options
(HOST '127.0.0.1',
DATABASE 'db_legitimate',
USER 'root',
PASSWORD '',
PORT $SLAVE_MYPORT,
SOCKET '',
OWNER 'root');
connection conn_super;
drop server 's1';
--replace_result $SLAVE_MYPORT SLAVE_PORT
eval create server 's1' foreign data wrapper 'mysql' options
(HOST '127.0.0.1',
DATABASE 'db_legitimate',
USER 'root',
PASSWORD '',
PORT $SLAVE_MYPORT,
SOCKET '',
OWNER 'root');
connection master;
flush tables;
select * from federated.t1;
# clean up test
connection slave;
drop database db_legitimate;
drop database db_bogus;
disconnect conn_select;
disconnect conn_usage;
disconnect conn_super;
connection master;
drop user guest_super@localhost;
drop user guest_usage@localhost;
drop user guest_select@localhost;
drop table federated.t1;
drop server 's1';
--echo # End of 5.1 tests
#
# Bug#25721 - deadlock with ALTER/CREATE SERVER
#
connect (other,localhost,root,,);
connection master;
use test;
delimiter //;
create procedure p1 ()
begin
DECLARE v INT DEFAULT 0;
DECLARE e INT DEFAULT 0;
DECLARE CONTINUE HANDLER FOR SQLEXCEPTION SET e = e + 1;
WHILE v < 10000 do
CREATE SERVER s
FOREIGN DATA WRAPPER mysql
OPTIONS (USER 'Remote', HOST '192.168.1.106', DATABASE 'test');
ALTER SERVER s OPTIONS (USER 'Remote');
DROP SERVER s;
SET v = v + 1;
END WHILE;
SELECT e > 0;
END//
delimiter ;//
connection other;
use test;
send call p1();
connection master;
call p1();
connection other;
reap;
drop procedure p1;
drop server if exists s;
source include/federated_cleanup.inc; source include/federated_cleanup.inc;
...@@ -182,6 +182,37 @@ delete from t1 where a >= 2; ...@@ -182,6 +182,37 @@ delete from t1 where a >= 2;
select a from t1 order by a; select a from t1 order by a;
drop table t1; drop table t1;
#
# Bug#26996 - Update of a Field in a Memory Table ends with wrong result
#
CREATE TABLE t1 (
c1 CHAR(3),
c2 INTEGER,
KEY USING BTREE(c1),
KEY USING BTREE(c2)
) ENGINE= MEMORY;
INSERT INTO t1 VALUES ('ABC',0), ('A',0), ('B',0), ('C',0);
UPDATE t1 SET c2= c2 + 1 WHERE c1 = 'A';
SELECT * FROM t1;
DROP TABLE t1;
#
# Bug#24985 - UTF8 ENUM primary key on MEMORY using BTREE
# causes incorrect duplicate entries
#
CREATE TABLE t1 (
c1 ENUM('1', '2'),
UNIQUE USING BTREE(c1)
) ENGINE= MEMORY DEFAULT CHARSET= utf8;
INSERT INTO t1 VALUES('1'), ('2');
DROP TABLE t1;
CREATE TABLE t1 (
c1 SET('1', '2'),
UNIQUE USING BTREE(c1)
) ENGINE= MEMORY DEFAULT CHARSET= utf8;
INSERT INTO t1 VALUES('1'), ('2');
DROP TABLE t1;
--echo End of 4.1 tests --echo End of 4.1 tests
# #
...@@ -205,3 +236,4 @@ INSERT INTO t1 VALUES(NULL),(NULL); ...@@ -205,3 +236,4 @@ INSERT INTO t1 VALUES(NULL),(NULL);
DROP TABLE t1; DROP TABLE t1;
--echo End of 5.0 tests --echo End of 5.0 tests
...@@ -874,6 +874,150 @@ CREATE TABLE t1 (c1 TEXT) AVG_ROW_LENGTH=70100 MAX_ROWS=4100100100; ...@@ -874,6 +874,150 @@ CREATE TABLE t1 (c1 TEXT) AVG_ROW_LENGTH=70100 MAX_ROWS=4100100100;
SHOW TABLE STATUS LIKE 't1'; SHOW TABLE STATUS LIKE 't1';
DROP TABLE t1; DROP TABLE t1;
#
# Bug#26231 - select count(*) on myisam table returns wrong value
# when index is used
#
CREATE TABLE t1 (c1 TEXT NOT NULL, KEY c1 (c1(10))) ENGINE=MyISAM;
# Fill at least two key blocks. "Tab, A" must be in both blocks.
INSERT INTO t1 VALUES
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)), (CHAR(9,65)),
(''), (''), (''), (''),
(' B'), (' B'), (' B'), (' B');
SELECT DISTINCT COUNT(*) FROM t1 WHERE c1 = '';
SELECT DISTINCT length(c1), c1 FROM t1 WHERE c1 = '';
SELECT DISTINCT COUNT(*) FROM t1 IGNORE INDEX (c1) WHERE c1 = '';
SELECT DISTINCT length(c1), c1 FROM t1 IGNORE INDEX (c1) WHERE c1 = '';
SELECT DISTINCT length(c1), c1 FROM t1 ORDER BY c1;
DROP TABLE t1;
--echo End of 4.1 tests --echo End of 4.1 tests
......
...@@ -37,7 +37,7 @@ uint my_pread(File Filedes, byte *Buffer, uint Count, my_off_t offset, ...@@ -37,7 +37,7 @@ uint my_pread(File Filedes, byte *Buffer, uint Count, my_off_t offset,
errno=0; /* Linux doesn't reset this */ errno=0; /* Linux doesn't reset this */
#endif #endif
#ifndef HAVE_PREAD #ifndef HAVE_PREAD
off_t old_offset; os_off_t old_offset;
pthread_mutex_lock(&my_file_info[Filedes].mutex); pthread_mutex_lock(&my_file_info[Filedes].mutex);
/* /*
...@@ -45,7 +45,7 @@ uint my_pread(File Filedes, byte *Buffer, uint Count, my_off_t offset, ...@@ -45,7 +45,7 @@ uint my_pread(File Filedes, byte *Buffer, uint Count, my_off_t offset,
before seeking to the given offset before seeking to the given offset
*/ */
error= (old_offset= (off_t)lseek(Filedes, 0L, MY_SEEK_CUR)) == -1L || error= (old_offset= lseek(Filedes, 0L, MY_SEEK_CUR)) == -1L ||
lseek(Filedes, offset, MY_SEEK_SET) == -1L; lseek(Filedes, offset, MY_SEEK_SET) == -1L;
if (!error) /* Seek was successful */ if (!error) /* Seek was successful */
...@@ -116,7 +116,7 @@ uint my_pwrite(int Filedes, const byte *Buffer, uint Count, my_off_t offset, ...@@ -116,7 +116,7 @@ uint my_pwrite(int Filedes, const byte *Buffer, uint Count, my_off_t offset,
{ {
#ifndef HAVE_PREAD #ifndef HAVE_PREAD
int error= 0; int error= 0;
off_t old_offset; os_off_t old_offset;
writenbytes= (uint) -1; writenbytes= (uint) -1;
pthread_mutex_lock(&my_file_info[Filedes].mutex); pthread_mutex_lock(&my_file_info[Filedes].mutex);
...@@ -124,7 +124,7 @@ uint my_pwrite(int Filedes, const byte *Buffer, uint Count, my_off_t offset, ...@@ -124,7 +124,7 @@ uint my_pwrite(int Filedes, const byte *Buffer, uint Count, my_off_t offset,
As we cannot change the file pointer, we save the old position, As we cannot change the file pointer, we save the old position,
before seeking to the given offset before seeking to the given offset
*/ */
error= ((old_offset= (off_t)lseek(Filedes, 0L, MY_SEEK_CUR)) == -1L || error= ((old_offset= lseek(Filedes, 0L, MY_SEEK_CUR)) == -1L ||
lseek(Filedes, offset, MY_SEEK_SET) == -1L); lseek(Filedes, offset, MY_SEEK_SET) == -1L);
if (!error) /* Seek was successful */ if (!error) /* Seek was successful */
......
...@@ -29,8 +29,6 @@ ...@@ -29,8 +29,6 @@
#define SCHED_POLICY SCHED_OTHER #define SCHED_POLICY SCHED_OTHER
#endif #endif
uint thd_lib_detected= 0;
uint thd_lib_detected; uint thd_lib_detected;
#ifndef my_pthread_setprio #ifndef my_pthread_setprio
......
...@@ -59,7 +59,7 @@ int my_redel(const char *org_name, const char *tmp_name, myf MyFlags) ...@@ -59,7 +59,7 @@ int my_redel(const char *org_name, const char *tmp_name, myf MyFlags)
MyFlags)) MyFlags))
goto end; goto end;
} }
else if (my_delete(org_name,MyFlags)) else if (my_delete_allow_opened(org_name, MyFlags))
goto end; goto end;
if (my_rename(tmp_name,org_name,MyFlags)) if (my_rename(tmp_name,org_name,MyFlags))
goto end; goto end;
......
...@@ -1445,6 +1445,9 @@ void close_system_tables(THD *thd, Open_tables_state *backup); ...@@ -1445,6 +1445,9 @@ void close_system_tables(THD *thd, Open_tables_state *backup);
TABLE *open_system_table_for_update(THD *thd, TABLE_LIST *one_table); TABLE *open_system_table_for_update(THD *thd, TABLE_LIST *one_table);
bool close_cached_tables(THD *thd, bool wait_for_refresh, TABLE_LIST *tables, bool have_lock = FALSE); bool close_cached_tables(THD *thd, bool wait_for_refresh, TABLE_LIST *tables, bool have_lock = FALSE);
bool close_cached_connection_tables(THD *thd, bool wait_for_refresh,
LEX_STRING *connect_string,
bool have_lock = FALSE);
void copy_field_from_tmp_record(Field *field,int offset); void copy_field_from_tmp_record(Field *field,int offset);
bool fill_record(THD *thd, Field **field, List<Item> &values, bool fill_record(THD *thd, Field **field, List<Item> &values,
bool ignore_errors); bool ignore_errors);
......
...@@ -858,6 +858,7 @@ void free_io_cache(TABLE *table) ...@@ -858,6 +858,7 @@ void free_io_cache(TABLE *table)
DBUG_VOID_RETURN; DBUG_VOID_RETURN;
} }
/* /*
Close all tables which aren't in use by any thread Close all tables which aren't in use by any thread
...@@ -969,6 +970,71 @@ bool close_cached_tables(THD *thd, bool if_wait_for_refresh, ...@@ -969,6 +970,71 @@ bool close_cached_tables(THD *thd, bool if_wait_for_refresh,
} }
/*
Close all tables which match specified connection string or
if specified string is NULL, then any table with a connection string.
*/
bool close_cached_connection_tables(THD *thd, bool if_wait_for_refresh,
LEX_STRING *connection, bool have_lock)
{
uint idx;
TABLE_LIST tmp, *tables= NULL;
bool result= FALSE;
DBUG_ENTER("close_cached_connections");
DBUG_ASSERT(thd);
bzero(&tmp, sizeof(TABLE_LIST));
if (!have_lock)
VOID(pthread_mutex_lock(&LOCK_open));
for (idx= 0; idx < table_def_cache.records; idx++)
{
TABLE_SHARE *share= (TABLE_SHARE *) hash_element(&table_def_cache, idx);
/* Ignore if table is not open or does not have a connect_string */
if (!share->connect_string.length || !share->ref_count)
continue;
/* Compare the connection string */
if (connection &&
(connection->length > share->connect_string.length ||
(connection->length < share->connect_string.length &&
(share->connect_string.str[connection->length] != '/' &&
share->connect_string.str[connection->length] != '\\')) ||
strncasecmp(connection->str, share->connect_string.str,
connection->length)))
continue;
/* close_cached_tables() only uses these elements */
tmp.db= share->db.str;
tmp.table_name= share->table_name.str;
tmp.next_local= tables;
tables= (TABLE_LIST *) memdup_root(thd->mem_root, (char*)&tmp,
sizeof(TABLE_LIST));
}
if (tables)
result= close_cached_tables(thd, FALSE, tables, TRUE);
if (!have_lock)
VOID(pthread_mutex_unlock(&LOCK_open));
if (if_wait_for_refresh)
{
pthread_mutex_lock(&thd->mysys_var->mutex);
thd->mysys_var->current_mutex= 0;
thd->mysys_var->current_cond= 0;
thd->proc_info=0;
pthread_mutex_unlock(&thd->mysys_var->mutex);
}
DBUG_RETURN(result);
}
/* /*
Mark all tables in the list which were used by current substatement Mark all tables in the list which were used by current substatement
as free for reuse. as free for reuse.
......
...@@ -4274,6 +4274,10 @@ mysql_execute_command(THD *thd) ...@@ -4274,6 +4274,10 @@ mysql_execute_command(THD *thd)
int error; int error;
LEX *lex= thd->lex; LEX *lex= thd->lex;
DBUG_PRINT("info", ("case SQLCOM_CREATE_SERVER")); DBUG_PRINT("info", ("case SQLCOM_CREATE_SERVER"));
if (check_global_access(thd, SUPER_ACL))
break;
if ((error= create_server(thd, &lex->server_options))) if ((error= create_server(thd, &lex->server_options)))
{ {
DBUG_PRINT("info", ("problem creating server <%s>", DBUG_PRINT("info", ("problem creating server <%s>",
...@@ -4289,6 +4293,10 @@ mysql_execute_command(THD *thd) ...@@ -4289,6 +4293,10 @@ mysql_execute_command(THD *thd)
int error; int error;
LEX *lex= thd->lex; LEX *lex= thd->lex;
DBUG_PRINT("info", ("case SQLCOM_ALTER_SERVER")); DBUG_PRINT("info", ("case SQLCOM_ALTER_SERVER"));
if (check_global_access(thd, SUPER_ACL))
break;
if ((error= alter_server(thd, &lex->server_options))) if ((error= alter_server(thd, &lex->server_options)))
{ {
DBUG_PRINT("info", ("problem altering server <%s>", DBUG_PRINT("info", ("problem altering server <%s>",
...@@ -4304,9 +4312,13 @@ mysql_execute_command(THD *thd) ...@@ -4304,9 +4312,13 @@ mysql_execute_command(THD *thd)
int err_code; int err_code;
LEX *lex= thd->lex; LEX *lex= thd->lex;
DBUG_PRINT("info", ("case SQLCOM_DROP_SERVER")); DBUG_PRINT("info", ("case SQLCOM_DROP_SERVER"));
if (check_global_access(thd, SUPER_ACL))
break;
if ((err_code= drop_server(thd, &lex->server_options))) if ((err_code= drop_server(thd, &lex->server_options)))
{ {
if (! lex->drop_if_exists && err_code == ER_FOREIGN_SERVER_EXISTS) if (! lex->drop_if_exists && err_code == ER_FOREIGN_SERVER_DOESNT_EXIST)
{ {
DBUG_PRINT("info", ("problem dropping server %s", DBUG_PRINT("info", ("problem dropping server %s",
lex->server_options.server_name)); lex->server_options.server_name));
......
This diff is collapsed.
...@@ -25,40 +25,19 @@ typedef struct st_federated_server ...@@ -25,40 +25,19 @@ typedef struct st_federated_server
} FOREIGN_SERVER; } FOREIGN_SERVER;
/* cache handlers */ /* cache handlers */
my_bool servers_init(bool dont_read_server_table); bool servers_init(bool dont_read_server_table);
my_bool servers_reload(THD *thd); bool servers_reload(THD *thd);
my_bool get_server_from_table_to_cache(TABLE *table);
void servers_free(bool end=0); void servers_free(bool end=0);
/* insert functions */ /* insert functions */
int create_server(THD *thd, LEX_SERVER_OPTIONS *server_options); int create_server(THD *thd, LEX_SERVER_OPTIONS *server_options);
int insert_server(THD *thd, FOREIGN_SERVER *server_options);
int insert_server_record(TABLE *table, FOREIGN_SERVER *server);
int insert_server_record_into_cache(FOREIGN_SERVER *server);
void store_server_fields_for_insert(TABLE *table, FOREIGN_SERVER *server);
void store_server_fields_for_insert(TABLE *table,
FOREIGN_SERVER *existing,
FOREIGN_SERVER *altered);
int prepare_server_struct_for_insert(LEX_SERVER_OPTIONS *server_options,
FOREIGN_SERVER *server);
/* drop functions */ /* drop functions */
int drop_server(THD *thd, LEX_SERVER_OPTIONS *server_options); int drop_server(THD *thd, LEX_SERVER_OPTIONS *server_options);
int delete_server_record(TABLE *table,
char *server_name,
int server_name_length);
int delete_server_record_in_cache(LEX_SERVER_OPTIONS *server_options);
/* update functions */ /* update functions */
int alter_server(THD *thd, LEX_SERVER_OPTIONS *server_options); int alter_server(THD *thd, LEX_SERVER_OPTIONS *server_options);
int prepare_server_struct_for_update(LEX_SERVER_OPTIONS *server_options,
FOREIGN_SERVER *existing, /* lookup functions */
FOREIGN_SERVER *altered); FOREIGN_SERVER *get_server_by_name(MEM_ROOT *mem, const char *server_name,
int update_server(THD *thd, FOREIGN_SERVER *existing, FOREIGN_SERVER *altered); FOREIGN_SERVER *server_buffer);
int update_server_record(TABLE *table, FOREIGN_SERVER *server);
int update_server_record_in_cache(FOREIGN_SERVER *existing,
FOREIGN_SERVER *altered);
/* utility functions */
void merge_server_struct(FOREIGN_SERVER *from, FOREIGN_SERVER *to);
FOREIGN_SERVER *get_server_by_name(const char *server_name);
my_bool server_exists_in_table(THD *thd, char *server_name);
This diff is collapsed.
...@@ -43,6 +43,8 @@ ...@@ -43,6 +43,8 @@
The example implements the minimum of what you will probably need. The example implements the minimum of what you will probably need.
*/ */
typedef struct st_federated_share { typedef struct st_federated_share {
MEM_ROOT mem_root;
bool parsed; bool parsed;
/* this key is unique db/tablename */ /* this key is unique db/tablename */
const char *share_key; const char *share_key;
...@@ -67,6 +69,7 @@ typedef struct st_federated_share { ...@@ -67,6 +69,7 @@ typedef struct st_federated_share {
char *sport; char *sport;
int share_key_length; int share_key_length;
ushort port; ushort port;
uint table_name_length, server_name_length, connect_string_length, use_count; uint table_name_length, server_name_length, connect_string_length, use_count;
pthread_mutex_t mutex; pthread_mutex_t mutex;
THR_LOCK lock; THR_LOCK lock;
......
...@@ -628,7 +628,10 @@ int ha_heap::create(const char *name, TABLE *table_arg, ...@@ -628,7 +628,10 @@ int ha_heap::create(const char *name, TABLE *table_arg,
seg->length= (uint) key_part->length; seg->length= (uint) key_part->length;
seg->flag= key_part->key_part_flag; seg->flag= key_part->key_part_flag;
seg->charset= field->charset(); if (field->flags & (ENUM_FLAG | SET_FLAG))
seg->charset= &my_charset_bin;
else
seg->charset= field->charset();
if (field->null_ptr) if (field->null_ptr)
{ {
seg->null_bit= field->null_bit; seg->null_bit= field->null_bit;
......
...@@ -105,7 +105,6 @@ int hp_rb_write_key(HP_INFO *info, HP_KEYDEF *keyinfo, const byte *record, ...@@ -105,7 +105,6 @@ int hp_rb_write_key(HP_INFO *info, HP_KEYDEF *keyinfo, const byte *record,
heap_rb_param custom_arg; heap_rb_param custom_arg;
uint old_allocated; uint old_allocated;
info->last_pos= NULL; /* For heap_rnext/heap_rprev */
custom_arg.keyseg= keyinfo->seg; custom_arg.keyseg= keyinfo->seg;
custom_arg.key_length= hp_rb_make_key(keyinfo, info->recbuf, record, recpos); custom_arg.key_length= hp_rb_make_key(keyinfo, info->recbuf, record, recpos);
if (keyinfo->flag & HA_NOSAME) if (keyinfo->flag & HA_NOSAME)
......
...@@ -635,6 +635,9 @@ bool ha_myisam::check_if_locking_is_allowed(uint sql_command, ...@@ -635,6 +635,9 @@ bool ha_myisam::check_if_locking_is_allowed(uint sql_command,
int ha_myisam::open(const char *name, int mode, uint test_if_locked) int ha_myisam::open(const char *name, int mode, uint test_if_locked)
{ {
MI_KEYDEF *keyinfo;
MI_COLUMNDEF *recinfo= 0;
uint recs;
uint i; uint i;
/* /*
...@@ -657,6 +660,26 @@ int ha_myisam::open(const char *name, int mode, uint test_if_locked) ...@@ -657,6 +660,26 @@ int ha_myisam::open(const char *name, int mode, uint test_if_locked)
if (!(file=mi_open(name, mode, test_if_locked | HA_OPEN_FROM_SQL_LAYER))) if (!(file=mi_open(name, mode, test_if_locked | HA_OPEN_FROM_SQL_LAYER)))
return (my_errno ? my_errno : -1); return (my_errno ? my_errno : -1);
if (!table->s->tmp_table) /* No need to perform a check for tmp table */
{
if ((my_errno= table2myisam(table, &keyinfo, &recinfo, &recs)))
{
/* purecov: begin inspected */
DBUG_PRINT("error", ("Failed to convert TABLE object to MyISAM "
"key and column definition"));
goto err;
/* purecov: end */
}
if (check_definition(keyinfo, recinfo, table->s->keys, recs,
file->s->keyinfo, file->s->rec,
file->s->base.keys, file->s->base.fields, true))
{
/* purecov: begin inspected */
my_errno= HA_ERR_CRASHED;
goto err;
/* purecov: end */
}
}
if (test_if_locked & (HA_OPEN_IGNORE_IF_LOCKED | HA_OPEN_TMP_TABLE)) if (test_if_locked & (HA_OPEN_IGNORE_IF_LOCKED | HA_OPEN_TMP_TABLE))
VOID(mi_extra(file, HA_EXTRA_NO_WAIT_LOCK, 0)); VOID(mi_extra(file, HA_EXTRA_NO_WAIT_LOCK, 0));
...@@ -677,7 +700,18 @@ int ha_myisam::open(const char *name, int mode, uint test_if_locked) ...@@ -677,7 +700,18 @@ int ha_myisam::open(const char *name, int mode, uint test_if_locked)
(struct st_mysql_ftparser *)parser->plugin->info; (struct st_mysql_ftparser *)parser->plugin->info;
table->key_info[i].block_size= file->s->keyinfo[i].block_length; table->key_info[i].block_size= file->s->keyinfo[i].block_length;
} }
return (0); my_errno= 0;
goto end;
err:
this->close();
end:
/*
Both recinfo and keydef are allocated by my_multi_malloc(), thus only
recinfo must be freed.
*/
if (recinfo)
my_free((gptr) recinfo, MYF(0));
return my_errno;
} }
int ha_myisam::close(void) int ha_myisam::close(void)
...@@ -1023,6 +1057,22 @@ int ha_myisam::repair(THD *thd, MI_CHECK &param, bool do_optimize) ...@@ -1023,6 +1057,22 @@ int ha_myisam::repair(THD *thd, MI_CHECK &param, bool do_optimize)
ha_rows rows= file->state->records; ha_rows rows= file->state->records;
DBUG_ENTER("ha_myisam::repair"); DBUG_ENTER("ha_myisam::repair");
/*
Normally this method is entered with a properly opened table. If the
repair fails, it can be repeated with more elaborate options. Under
special circumstances it can happen that a repair fails so that it
closed the data file and cannot re-open it. In this case file->dfile
is set to -1. We must not try another repair without an open data
file. (Bug #25289)
*/
if (file->dfile == -1)
{
sql_print_information("Retrying repair of: '%s' failed. "
"Please try REPAIR EXTENDED or myisamchk",
table->s->path.str);
DBUG_RETURN(HA_ADMIN_FAILED);
}
param.db_name= table->s->db.str; param.db_name= table->s->db.str;
param.table_name= table->alias; param.table_name= table->alias;
param.tmpfile_createflag = O_RDWR | O_TRUNC; param.tmpfile_createflag = O_RDWR | O_TRUNC;
......
...@@ -573,6 +573,10 @@ int mi_create(const char *name,uint keys,MI_KEYDEF *keydefs, ...@@ -573,6 +573,10 @@ int mi_create(const char *name,uint keys,MI_KEYDEF *keydefs,
pthread_mutex_lock(&THR_LOCK_myisam); pthread_mutex_lock(&THR_LOCK_myisam);
/*
NOTE: For test_if_reopen() we need a real path name. Hence we need
MY_RETURN_REAL_PATH for every fn_format(filename, ...).
*/
if (ci->index_file_name) if (ci->index_file_name)
{ {
char *iext= strrchr(ci->index_file_name, '.'); char *iext= strrchr(ci->index_file_name, '.');
...@@ -584,13 +588,14 @@ int mi_create(const char *name,uint keys,MI_KEYDEF *keydefs, ...@@ -584,13 +588,14 @@ int mi_create(const char *name,uint keys,MI_KEYDEF *keydefs,
if ((path= strrchr(ci->index_file_name, FN_LIBCHAR))) if ((path= strrchr(ci->index_file_name, FN_LIBCHAR)))
*path= '\0'; *path= '\0';
fn_format(filename, name, ci->index_file_name, MI_NAME_IEXT, fn_format(filename, name, ci->index_file_name, MI_NAME_IEXT,
MY_REPLACE_DIR | MY_UNPACK_FILENAME | MY_APPEND_EXT); MY_REPLACE_DIR | MY_UNPACK_FILENAME |
MY_RETURN_REAL_PATH | MY_APPEND_EXT);
} }
else else
{ {
fn_format(filename, ci->index_file_name, "", MI_NAME_IEXT, fn_format(filename, ci->index_file_name, "", MI_NAME_IEXT,
MY_UNPACK_FILENAME | (have_iext ? MY_REPLACE_EXT : MY_UNPACK_FILENAME | MY_RETURN_REAL_PATH |
MY_APPEND_EXT)); (have_iext ? MY_REPLACE_EXT : MY_APPEND_EXT));
} }
fn_format(linkname, name, "", MI_NAME_IEXT, fn_format(linkname, name, "", MI_NAME_IEXT,
MY_UNPACK_FILENAME|MY_APPEND_EXT); MY_UNPACK_FILENAME|MY_APPEND_EXT);
...@@ -603,10 +608,11 @@ int mi_create(const char *name,uint keys,MI_KEYDEF *keydefs, ...@@ -603,10 +608,11 @@ int mi_create(const char *name,uint keys,MI_KEYDEF *keydefs,
} }
else else
{ {
char *iext= strrchr(name, '.');
int have_iext= iext && !strcmp(iext, MI_NAME_IEXT);
fn_format(filename, name, "", MI_NAME_IEXT, fn_format(filename, name, "", MI_NAME_IEXT,
(MY_UNPACK_FILENAME | MY_UNPACK_FILENAME | MY_RETURN_REAL_PATH |
(flags & HA_DONT_TOUCH_DATA) ? MY_RETURN_REAL_PATH : 0) | (have_iext ? MY_REPLACE_EXT : MY_APPEND_EXT));
MY_APPEND_EXT);
linkname_ptr=0; linkname_ptr=0;
/* Replace the current file */ /* Replace the current file */
create_flag=MY_DELETE_OLD; create_flag=MY_DELETE_OLD;
...@@ -618,6 +624,9 @@ int mi_create(const char *name,uint keys,MI_KEYDEF *keydefs, ...@@ -618,6 +624,9 @@ int mi_create(const char *name,uint keys,MI_KEYDEF *keydefs,
A TRUNCATE command checks for the table in the cache only and could A TRUNCATE command checks for the table in the cache only and could
be fooled to believe, the table is not open. be fooled to believe, the table is not open.
Pull the emergency brake in this situation. (Bug #8306) Pull the emergency brake in this situation. (Bug #8306)
NOTE: The filename is compared against unique_file_name of every
open table. Hence we need a real path here.
*/ */
if (test_if_reopen(filename)) if (test_if_reopen(filename))
{ {
......
...@@ -138,8 +138,42 @@ static ha_rows _mi_record_pos(MI_INFO *info, const byte *key, ...@@ -138,8 +138,42 @@ static ha_rows _mi_record_pos(MI_INFO *info, const byte *key,
if (!(nextflag & (SEARCH_FIND | SEARCH_NO_FIND | SEARCH_LAST))) if (!(nextflag & (SEARCH_FIND | SEARCH_NO_FIND | SEARCH_LAST)))
key_len=USE_WHOLE_KEY; key_len=USE_WHOLE_KEY;
/*
my_handler.c:mi_compare_text() has a flag 'skip_end_space'.
This is set in my_handler.c:ha_key_cmp() in dependence on the
compare flags 'nextflag' and the column type.
TEXT columns are of type HA_KEYTYPE_VARTEXT. In this case the
condition is skip_end_space= ((nextflag & (SEARCH_FIND |
SEARCH_UPDATE)) == SEARCH_FIND).
SEARCH_FIND is used for an exact key search. The combination
SEARCH_FIND | SEARCH_UPDATE is used in write/update/delete
operations with a comment like "Not real duplicates", whatever this
means. From the condition above we can see that 'skip_end_space' is
always false for these operations. The result is that trailing space
counts in key comparison and hence, emtpy strings ('', string length
zero, but not NULL) compare less that strings starting with control
characters and these in turn compare less than strings starting with
blanks.
When estimating the number of records in a key range, we request an
exact search for the minimum key. This translates into a plain
SEARCH_FIND flag. Using this alone would lead to a 'skip_end_space'
compare. Empty strings would be expected above control characters.
Their keys would not be found because they are located below control
characters.
This is the reason that we add the SEARCH_UPDATE flag here. It makes
the key estimation compare in the same way like key write operations
do. Olny so we will find the keys where they have been inserted.
Adding the flag unconditionally does not hurt as it is used in the
above mentioned condition only. So it can safely be used together
with other flags.
*/
pos=_mi_search_pos(info,keyinfo,key_buff,key_len, pos=_mi_search_pos(info,keyinfo,key_buff,key_len,
nextflag | SEARCH_SAVE_BUFF, nextflag | SEARCH_SAVE_BUFF | SEARCH_UPDATE,
info->s->state.key_root[inx]); info->s->state.key_root[inx]);
if (pos >= 0.0) if (pos >= 0.0)
{ {
......
...@@ -926,11 +926,16 @@ uint _mi_get_binary_pack_key(register MI_KEYDEF *keyinfo, uint nod_flag, ...@@ -926,11 +926,16 @@ uint _mi_get_binary_pack_key(register MI_KEYDEF *keyinfo, uint nod_flag,
/* /*
Keys are compressed the following way: Keys are compressed the following way:
prefix length Packed length of prefix for the prev key. (1 or 3 bytes) prefix length Packed length of prefix common with prev key (1 or 3 bytes)
for each key segment: for each key segment:
[is null] Null indicator if can be null (1 byte, zero means null) [is null] Null indicator if can be null (1 byte, zero means null)
[length] Packed length if varlength (1 or 3 bytes) [length] Packed length if varlength (1 or 3 bytes)
key segment 'length' bytes of key segment value
pointer Reference to the data file (last_keyseg->length). pointer Reference to the data file (last_keyseg->length).
get_key_length() is a macro. It gets the prefix length from 'page'
and puts it into 'length'. It increments 'page' by 1 or 3, depending
on the packed length of the prefix length.
*/ */
get_key_length(length,page); get_key_length(length,page);
if (length) if (length)
...@@ -945,34 +950,44 @@ uint _mi_get_binary_pack_key(register MI_KEYDEF *keyinfo, uint nod_flag, ...@@ -945,34 +950,44 @@ uint _mi_get_binary_pack_key(register MI_KEYDEF *keyinfo, uint nod_flag,
my_errno=HA_ERR_CRASHED; my_errno=HA_ERR_CRASHED;
DBUG_RETURN(0); /* Wrong key */ DBUG_RETURN(0); /* Wrong key */
} }
from=key; from_end=key+length; /* Key is packed against prev key, take prefix from prev key. */
from= key;
from_end= key + length;
} }
else else
{ {
from=page; from_end=page_end; /* Not packed key */ /* Key is not packed against prev key, take all from page buffer. */
from= page;
from_end= page_end;
} }
/* /*
The trouble is that key is split in two parts: The trouble is that key can be split in two parts:
The first part is in from ...from_end-1. The first part (prefix) is in from .. from_end - 1.
The second part starts at page The second part starts at page.
The split can be at every byte position. So we need to check for
the end of the first part before using every byte.
*/ */
for (keyseg=keyinfo->seg ; keyseg->type ;keyseg++) for (keyseg=keyinfo->seg ; keyseg->type ;keyseg++)
{ {
if (keyseg->flag & HA_NULL_PART) if (keyseg->flag & HA_NULL_PART)
{ {
/* If prefix is used up, switch to rest. */
if (from == from_end) { from=page; from_end=page_end; } if (from == from_end) { from=page; from_end=page_end; }
if (!(*key++ = *from++)) if (!(*key++ = *from++))
continue; /* Null part */ continue; /* Null part */
} }
if (keyseg->flag & (HA_VAR_LENGTH_PART | HA_BLOB_PART | HA_SPACE_PACK)) if (keyseg->flag & (HA_VAR_LENGTH_PART | HA_BLOB_PART | HA_SPACE_PACK))
{ {
/* Get length of dynamic length key part */ /* If prefix is used up, switch to rest. */
if (from == from_end) { from=page; from_end=page_end; } if (from == from_end) { from=page; from_end=page_end; }
/* Get length of dynamic length key part */
if ((length= (*key++ = *from++)) == 255) if ((length= (*key++ = *from++)) == 255)
{ {
/* If prefix is used up, switch to rest. */
if (from == from_end) { from=page; from_end=page_end; } if (from == from_end) { from=page; from_end=page_end; }
length= (uint) ((*key++ = *from++)) << 8; length= (uint) ((*key++ = *from++)) << 8;
/* If prefix is used up, switch to rest. */
if (from == from_end) { from=page; from_end=page_end; } if (from == from_end) { from=page; from_end=page_end; }
length+= (uint) ((*key++ = *from++)); length+= (uint) ((*key++ = *from++));
} }
...@@ -992,14 +1007,26 @@ uint _mi_get_binary_pack_key(register MI_KEYDEF *keyinfo, uint nod_flag, ...@@ -992,14 +1007,26 @@ uint _mi_get_binary_pack_key(register MI_KEYDEF *keyinfo, uint nod_flag,
key+=length; key+=length;
from+=length; from+=length;
} }
/*
Last segment (type == 0) contains length of data pointer.
If we have mixed key blocks with data pointer and key block pointer,
we have to copy both.
*/
length=keyseg->length+nod_flag; length=keyseg->length+nod_flag;
if ((tmp=(uint) (from_end-from)) <= length) if ((tmp=(uint) (from_end-from)) <= length)
{ {
/* Remaining length is less or equal max possible length. */
memcpy(key+tmp,page,length-tmp); /* Get last part of key */ memcpy(key+tmp,page,length-tmp); /* Get last part of key */
*page_pos= page+length-tmp; *page_pos= page+length-tmp;
} }
else else
{ {
/*
Remaining length is greater than max possible length.
This can happen only if we switched to the new key bytes already.
'page_end' is calculated with MI_MAX_KEY_BUFF. So it can be far
behind the real end of the key.
*/
if (from_end != page_end) if (from_end != page_end)
{ {
DBUG_PRINT("error",("Error when unpacking key")); DBUG_PRINT("error",("Error when unpacking key"));
...@@ -1007,6 +1034,7 @@ uint _mi_get_binary_pack_key(register MI_KEYDEF *keyinfo, uint nod_flag, ...@@ -1007,6 +1034,7 @@ uint _mi_get_binary_pack_key(register MI_KEYDEF *keyinfo, uint nod_flag,
my_errno=HA_ERR_CRASHED; my_errno=HA_ERR_CRASHED;
DBUG_RETURN(0); /* Error */ DBUG_RETURN(0); /* Error */
} }
/* Copy data pointer and, if appropriate, key block pointer. */
memcpy((byte*) key,(byte*) from,(size_t) length); memcpy((byte*) key,(byte*) from,(size_t) length);
*page_pos= from+length; *page_pos= from+length;
} }
......
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