mirror of
https://github.com/MariaDB/server.git
synced 2025-07-29 05:21:33 +03:00
Preliminary commit of HANDLER syntax (w/o LIMIT or column-list)
This commit is contained in:
26
mysql-test/r/handler.result
Normal file
26
mysql-test/r/handler.result
Normal file
@ -0,0 +1,26 @@
|
|||||||
|
a b
|
||||||
|
14 aaa
|
||||||
|
a b
|
||||||
|
15 bbb
|
||||||
|
a b
|
||||||
|
16 ccc
|
||||||
|
a b
|
||||||
|
15 bbb
|
||||||
|
a b
|
||||||
|
22 iii
|
||||||
|
a b
|
||||||
|
21 hhh
|
||||||
|
a b
|
||||||
|
20 ggg
|
||||||
|
a b
|
||||||
|
14 aaa
|
||||||
|
a b
|
||||||
|
a b
|
||||||
|
22 iii
|
||||||
|
a b
|
||||||
|
21 hhh
|
||||||
|
a b
|
||||||
|
22 iii
|
||||||
|
a b
|
||||||
|
a b
|
||||||
|
15 bbb
|
32
mysql-test/t/handler.test
Normal file
32
mysql-test/t/handler.test
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
#
|
||||||
|
# test of HANDLER ...
|
||||||
|
#
|
||||||
|
|
||||||
|
drop table if exists t1;
|
||||||
|
create table t1 (a int, b char(10), key a(a));
|
||||||
|
insert into t1 values
|
||||||
|
(14,"aaa"),(15,"bbb"),(16,"ccc"),
|
||||||
|
(17,"ddd"),(18,"eee"),(19,"fff"),
|
||||||
|
(20,"ggg"),(21,"hhh"),(22,"iii");
|
||||||
|
handler t1 open;
|
||||||
|
handler t1 read a first;
|
||||||
|
handler t1 read a next;
|
||||||
|
handler t1 read a next;
|
||||||
|
handler t1 read a prev;
|
||||||
|
handler t1 read a last;
|
||||||
|
handler t1 read a prev;
|
||||||
|
handler t1 read a prev;
|
||||||
|
|
||||||
|
handler t1 read a first;
|
||||||
|
handler t1 read a prev;
|
||||||
|
|
||||||
|
handler t1 read a last;
|
||||||
|
handler t1 read a prev;
|
||||||
|
handler t1 read a next;
|
||||||
|
handler t1 read a next;
|
||||||
|
|
||||||
|
handler t1 read a=(15);
|
||||||
|
|
||||||
|
handler t1 close;
|
||||||
|
drop table if exists t1;
|
||||||
|
|
@ -54,7 +54,7 @@ noinst_HEADERS = item.h item_func.h item_sum.h item_cmpfunc.h \
|
|||||||
sql_select.h structs.h table.h sql_udf.h hash_filo.h\
|
sql_select.h structs.h table.h sql_udf.h hash_filo.h\
|
||||||
lex.h lex_symbol.h sql_acl.h sql_crypt.h md5.h \
|
lex.h lex_symbol.h sql_acl.h sql_crypt.h md5.h \
|
||||||
log_event.h mini_client.h sql_repl.h slave.h
|
log_event.h mini_client.h sql_repl.h slave.h
|
||||||
mysqld_SOURCES = sql_lex.cc \
|
mysqld_SOURCES = sql_lex.cc sql_handler.cc \
|
||||||
item.cc item_sum.cc item_buff.cc item_func.cc \
|
item.cc item_sum.cc item_buff.cc item_func.cc \
|
||||||
item_cmpfunc.cc item_strfunc.cc item_timefunc.cc \
|
item_cmpfunc.cc item_strfunc.cc item_timefunc.cc \
|
||||||
thr_malloc.cc item_create.cc \
|
thr_malloc.cc item_create.cc \
|
||||||
|
@ -82,6 +82,7 @@ static SYMBOL symbols[] = {
|
|||||||
{ "CHANGED", SYM(CHANGED),0,0},
|
{ "CHANGED", SYM(CHANGED),0,0},
|
||||||
{ "CHECK", SYM(CHECK_SYM),0,0},
|
{ "CHECK", SYM(CHECK_SYM),0,0},
|
||||||
{ "CHECKSUM", SYM(CHECKSUM_SYM),0,0},
|
{ "CHECKSUM", SYM(CHECKSUM_SYM),0,0},
|
||||||
|
{ "CLOSE", SYM(CLOSE_SYM),0,0},
|
||||||
{ "COLUMN", SYM(COLUMN_SYM),0,0},
|
{ "COLUMN", SYM(COLUMN_SYM),0,0},
|
||||||
{ "COLUMNS", SYM(COLUMNS),0,0},
|
{ "COLUMNS", SYM(COLUMNS),0,0},
|
||||||
{ "COMMENT", SYM(COMMENT_SYM),0,0},
|
{ "COMMENT", SYM(COMMENT_SYM),0,0},
|
||||||
@ -152,6 +153,7 @@ static SYMBOL symbols[] = {
|
|||||||
{ "GRANTS", SYM(GRANTS),0,0},
|
{ "GRANTS", SYM(GRANTS),0,0},
|
||||||
{ "GROUP", SYM(GROUP),0,0},
|
{ "GROUP", SYM(GROUP),0,0},
|
||||||
{ "HAVING", SYM(HAVING),0,0},
|
{ "HAVING", SYM(HAVING),0,0},
|
||||||
|
{ "HANDLER", SYM(HANDLER_SYM),0,0},
|
||||||
{ "HEAP", SYM(HEAP_SYM),0,0},
|
{ "HEAP", SYM(HEAP_SYM),0,0},
|
||||||
{ "HIGH_PRIORITY", SYM(HIGH_PRIORITY),0,0},
|
{ "HIGH_PRIORITY", SYM(HIGH_PRIORITY),0,0},
|
||||||
{ "HOUR", SYM(HOUR_SYM),0,0},
|
{ "HOUR", SYM(HOUR_SYM),0,0},
|
||||||
@ -184,6 +186,7 @@ static SYMBOL symbols[] = {
|
|||||||
{ "KEY", SYM(KEY_SYM),0,0},
|
{ "KEY", SYM(KEY_SYM),0,0},
|
||||||
{ "KEYS", SYM(KEYS),0,0},
|
{ "KEYS", SYM(KEYS),0,0},
|
||||||
{ "KILL", SYM(KILL_SYM),0,0},
|
{ "KILL", SYM(KILL_SYM),0,0},
|
||||||
|
{ "LAST", SYM(LAST_SYM),0,0},
|
||||||
{ "LAST_INSERT_ID", SYM(LAST_INSERT_ID),0,0},
|
{ "LAST_INSERT_ID", SYM(LAST_INSERT_ID),0,0},
|
||||||
{ "LEADING", SYM(LEADING),0,0},
|
{ "LEADING", SYM(LEADING),0,0},
|
||||||
{ "LEFT", SYM(LEFT),0,0},
|
{ "LEFT", SYM(LEFT),0,0},
|
||||||
@ -225,11 +228,12 @@ static SYMBOL symbols[] = {
|
|||||||
{ "MYISAM", SYM(MYISAM_SYM),0,0},
|
{ "MYISAM", SYM(MYISAM_SYM),0,0},
|
||||||
{ "NATURAL", SYM(NATURAL),0,0},
|
{ "NATURAL", SYM(NATURAL),0,0},
|
||||||
{ "NATIONAL", SYM(NATIONAL_SYM),0,0},
|
{ "NATIONAL", SYM(NATIONAL_SYM),0,0},
|
||||||
|
{ "NEXT", SYM(NEXT_SYM),0,0},
|
||||||
{ "NCHAR", SYM(NCHAR_SYM),0,0},
|
{ "NCHAR", SYM(NCHAR_SYM),0,0},
|
||||||
{ "NUMERIC", SYM(NUMERIC_SYM),0,0},
|
|
||||||
{ "NO", SYM(NO_SYM),0,0},
|
{ "NO", SYM(NO_SYM),0,0},
|
||||||
{ "NOT", SYM(NOT),0,0},
|
{ "NOT", SYM(NOT),0,0},
|
||||||
{ "NULL", SYM(NULL_SYM),0,0},
|
{ "NULL", SYM(NULL_SYM),0,0},
|
||||||
|
{ "NUMERIC", SYM(NUMERIC_SYM),0,0},
|
||||||
{ "ON", SYM(ON),0,0},
|
{ "ON", SYM(ON),0,0},
|
||||||
{ "OPEN", SYM(OPEN_SYM),0,0},
|
{ "OPEN", SYM(OPEN_SYM),0,0},
|
||||||
{ "OPTIMIZE", SYM(OPTIMIZE),0,0},
|
{ "OPTIMIZE", SYM(OPTIMIZE),0,0},
|
||||||
@ -244,6 +248,7 @@ static SYMBOL symbols[] = {
|
|||||||
{ "PASSWORD", SYM(PASSWORD),0,0},
|
{ "PASSWORD", SYM(PASSWORD),0,0},
|
||||||
{ "PURGE", SYM(PURGE),0,0},
|
{ "PURGE", SYM(PURGE),0,0},
|
||||||
{ "PRECISION", SYM(PRECISION),0,0},
|
{ "PRECISION", SYM(PRECISION),0,0},
|
||||||
|
{ "PREV", SYM(PREV_SYM),0,0},
|
||||||
{ "PRIMARY", SYM(PRIMARY_SYM),0,0},
|
{ "PRIMARY", SYM(PRIMARY_SYM),0,0},
|
||||||
{ "PROCEDURE", SYM(PROCEDURE),0,0},
|
{ "PROCEDURE", SYM(PROCEDURE),0,0},
|
||||||
{ "PROCESS" , SYM(PROCESS),0,0},
|
{ "PROCESS" , SYM(PROCESS),0,0},
|
||||||
|
@ -381,6 +381,12 @@ int mysqld_show_status(THD *thd);
|
|||||||
int mysqld_show_variables(THD *thd,const char *wild);
|
int mysqld_show_variables(THD *thd,const char *wild);
|
||||||
int mysqld_show(THD *thd, const char *wild, show_var_st *variables);
|
int mysqld_show(THD *thd, const char *wild, show_var_st *variables);
|
||||||
|
|
||||||
|
/* sql_handler.cc */
|
||||||
|
int mysql_ha_open(THD *thd, TABLE_LIST *tables);
|
||||||
|
int mysql_ha_close(THD *thd, TABLE_LIST *tables);
|
||||||
|
int mysql_ha_read(THD *, TABLE_LIST *,enum enum_ha_read_modes,
|
||||||
|
char *,List<Item> *,enum ha_rkey_function);
|
||||||
|
|
||||||
/* sql_base.cc */
|
/* sql_base.cc */
|
||||||
void set_item_name(Item *item,char *pos,uint length);
|
void set_item_name(Item *item,char *pos,uint length);
|
||||||
bool add_field_to_list(char *field_name, enum enum_field_types type,
|
bool add_field_to_list(char *field_name, enum enum_field_types type,
|
||||||
@ -402,6 +408,8 @@ TABLE *unlink_open_table(THD *thd,TABLE *list,TABLE *find);
|
|||||||
SQL_SELECT *make_select(TABLE *head, table_map const_tables,
|
SQL_SELECT *make_select(TABLE *head, table_map const_tables,
|
||||||
table_map read_tables, COND *conds, int *error);
|
table_map read_tables, COND *conds, int *error);
|
||||||
Item ** find_item_in_list(Item *item,List<Item> &items);
|
Item ** find_item_in_list(Item *item,List<Item> &items);
|
||||||
|
bool insert_fields(THD *thd,TABLE_LIST *tables, const char *table_name,
|
||||||
|
List_iterator<Item> *it);
|
||||||
bool setup_tables(TABLE_LIST *tables);
|
bool setup_tables(TABLE_LIST *tables);
|
||||||
int setup_fields(THD *thd,TABLE_LIST *tables,List<Item> &item,
|
int setup_fields(THD *thd,TABLE_LIST *tables,List<Item> &item,
|
||||||
bool set_query_id,List<Item> *sum_func_list);
|
bool set_query_id,List<Item> *sum_func_list);
|
||||||
|
@ -34,8 +34,6 @@ HASH open_cache; /* Used by mysql_test */
|
|||||||
|
|
||||||
static int open_unireg_entry(THD *thd,TABLE *entry,const char *db,
|
static int open_unireg_entry(THD *thd,TABLE *entry,const char *db,
|
||||||
const char *name, const char *alias, bool locked);
|
const char *name, const char *alias, bool locked);
|
||||||
static bool insert_fields(THD *thd,TABLE_LIST *tables, const char *table_name,
|
|
||||||
List_iterator<Item> *it);
|
|
||||||
static void free_cache_entry(TABLE *entry);
|
static void free_cache_entry(TABLE *entry);
|
||||||
static void mysql_rm_tmp_tables(void);
|
static void mysql_rm_tmp_tables(void);
|
||||||
static key_map get_key_map_from_key_list(TABLE *table,
|
static key_map get_key_map_from_key_list(TABLE *table,
|
||||||
@ -409,7 +407,7 @@ void close_thread_tables(THD *thd, bool locked)
|
|||||||
{
|
{
|
||||||
DBUG_ENTER("close_thread_tables");
|
DBUG_ENTER("close_thread_tables");
|
||||||
|
|
||||||
if (thd->locked_tables)
|
if (thd->locked_tables || thd->manual_open)
|
||||||
DBUG_VOID_RETURN; // LOCK TABLES in use
|
DBUG_VOID_RETURN; // LOCK TABLES in use
|
||||||
|
|
||||||
TABLE *table,*next;
|
TABLE *table,*next;
|
||||||
@ -1807,7 +1805,7 @@ static key_map get_key_map_from_key_list(TABLE *table,
|
|||||||
** Returns pointer to last inserted field if ok
|
** Returns pointer to last inserted field if ok
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
static bool
|
bool
|
||||||
insert_fields(THD *thd,TABLE_LIST *tables, const char *table_name,
|
insert_fields(THD *thd,TABLE_LIST *tables, const char *table_name,
|
||||||
List_iterator<Item> *it)
|
List_iterator<Item> *it)
|
||||||
{
|
{
|
||||||
|
@ -76,7 +76,7 @@ static void free_var(user_var_entry *entry)
|
|||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
THD::THD():user_time(0),fatal_error(0),last_insert_id_used(0),
|
THD::THD():user_time(0),fatal_error(0),last_insert_id_used(0),
|
||||||
insert_id_used(0),in_lock_tables(0),
|
insert_id_used(0),in_lock_tables(0),manual_open(0),
|
||||||
global_read_lock(0),bootstrap(0)
|
global_read_lock(0),bootstrap(0)
|
||||||
{
|
{
|
||||||
host=user=priv_user=db=query=ip=0;
|
host=user=priv_user=db=query=ip=0;
|
||||||
@ -158,9 +158,10 @@ THD::~THD()
|
|||||||
net_end(&net);
|
net_end(&net);
|
||||||
}
|
}
|
||||||
ha_rollback(this);
|
ha_rollback(this);
|
||||||
if (locked_tables)
|
if (locked_tables || manual_open)
|
||||||
{
|
{
|
||||||
lock=locked_tables; locked_tables=0;
|
lock=locked_tables; locked_tables=0;
|
||||||
|
manual_open=0;
|
||||||
close_thread_tables(this);
|
close_thread_tables(this);
|
||||||
}
|
}
|
||||||
close_temporary_tables(this);
|
close_temporary_tables(this);
|
||||||
|
@ -24,7 +24,7 @@
|
|||||||
class Query_log_event;
|
class Query_log_event;
|
||||||
class Load_log_event;
|
class Load_log_event;
|
||||||
|
|
||||||
|
enum enum_ha_read_modes { RFIRST, RNEXT, RPREV, RLAST, RKEY };
|
||||||
enum enum_duplicates { DUP_ERROR, DUP_REPLACE, DUP_IGNORE };
|
enum enum_duplicates { DUP_ERROR, DUP_REPLACE, DUP_IGNORE };
|
||||||
enum enum_log_type { LOG_CLOSED, LOG_NORMAL, LOG_NEW, LOG_BIN };
|
enum enum_log_type { LOG_CLOSED, LOG_NORMAL, LOG_NEW, LOG_BIN };
|
||||||
|
|
||||||
@ -278,7 +278,7 @@ public:
|
|||||||
bool slave_thread;
|
bool slave_thread;
|
||||||
bool set_query_id,locked,count_cuted_fields,some_tables_deleted;
|
bool set_query_id,locked,count_cuted_fields,some_tables_deleted;
|
||||||
bool no_errors, allow_sum_func, password, fatal_error;
|
bool no_errors, allow_sum_func, password, fatal_error;
|
||||||
bool query_start_used,last_insert_id_used,insert_id_used;
|
bool query_start_used,last_insert_id_used,insert_id_used,manual_open;
|
||||||
bool system_thread,in_lock_tables,global_read_lock;
|
bool system_thread,in_lock_tables,global_read_lock;
|
||||||
bool query_error, bootstrap;
|
bool query_error, bootstrap;
|
||||||
bool volatile killed;
|
bool volatile killed;
|
||||||
|
172
sql/sql_handler.cc
Normal file
172
sql/sql_handler.cc
Normal file
@ -0,0 +1,172 @@
|
|||||||
|
/* Copyright (C) 2000 MySQL AB & MySQL Finland AB & TCX DataKonsult AB
|
||||||
|
|
||||||
|
This program is free software; you can redistribute it and/or modify
|
||||||
|
it under the terms of the GNU General Public License as published by
|
||||||
|
the Free Software Foundation; either version 2 of the License, or
|
||||||
|
(at your option) any later version.
|
||||||
|
|
||||||
|
This program is distributed in the hope that it will be useful,
|
||||||
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
GNU General Public License for more details.
|
||||||
|
|
||||||
|
You should have received a copy of the GNU General Public License
|
||||||
|
along with this program; if not, write to the Free Software
|
||||||
|
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
|
||||||
|
|
||||||
|
|
||||||
|
/* HANDLER ... commands - direct access to ISAM */
|
||||||
|
|
||||||
|
#include "mysql_priv.h"
|
||||||
|
#include "sql_select.h"
|
||||||
|
|
||||||
|
static TABLE *find_table_by_name(THD *thd, char *db, char *table_name);
|
||||||
|
|
||||||
|
int mysql_ha_open(THD *thd, TABLE_LIST *tables)
|
||||||
|
{
|
||||||
|
int err=open_tables(thd,tables);
|
||||||
|
if (!err)
|
||||||
|
{
|
||||||
|
thd->manual_open=1;
|
||||||
|
send_ok(&thd->net);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int mysql_ha_close(THD *thd, TABLE_LIST *tables)
|
||||||
|
{
|
||||||
|
send_ok(&thd->net);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
int mysql_ha_read(THD *thd, TABLE_LIST *tables,
|
||||||
|
enum enum_ha_read_modes mode, char *keyname, List<Item> *key_expr,
|
||||||
|
enum ha_rkey_function ha_rkey_mode)
|
||||||
|
{
|
||||||
|
int err;
|
||||||
|
TABLE *table=find_table_by_name(thd, tables->db, tables->name);
|
||||||
|
if (!table)
|
||||||
|
{
|
||||||
|
my_printf_error(ER_UNKNOWN_TABLE,ER(ER_UNKNOWN_TABLE),MYF(0),
|
||||||
|
tables->name,"HANDLER");
|
||||||
|
// send_error(&thd->net,ER_UNKNOWN_TABLE);
|
||||||
|
// send_ok(&thd->net);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
tables->table=table;
|
||||||
|
|
||||||
|
int keyno=find_type(keyname, &table->keynames, 1+2)-1;
|
||||||
|
if (keyno<0)
|
||||||
|
{
|
||||||
|
my_printf_error(ER_KEY_DOES_NOT_EXITS,ER(ER_KEY_DOES_NOT_EXITS),MYF(0),
|
||||||
|
keyname,tables->name);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
List<Item> list;
|
||||||
|
list.push_front(new Item_field(NULL,NULL,"*"));
|
||||||
|
List_iterator<Item> it(list);
|
||||||
|
it++;
|
||||||
|
|
||||||
|
insert_fields(thd,tables,tables->name,&it);
|
||||||
|
|
||||||
|
table->file->index_init(keyno);
|
||||||
|
|
||||||
|
switch(mode)
|
||||||
|
{
|
||||||
|
case RFIRST:
|
||||||
|
err=table->file->index_first(table->record[0]);
|
||||||
|
break;
|
||||||
|
case RLAST:
|
||||||
|
err=table->file->index_last(table->record[0]);
|
||||||
|
break;
|
||||||
|
case RNEXT:
|
||||||
|
err=table->file->index_next(table->record[0]);
|
||||||
|
break;
|
||||||
|
case RPREV:
|
||||||
|
err=table->file->index_prev(table->record[0]);
|
||||||
|
break;
|
||||||
|
case RKEY:
|
||||||
|
{
|
||||||
|
KEY *keyinfo=table->key_info+keyno;
|
||||||
|
uint key_len=0, i;
|
||||||
|
byte *key, *buf;
|
||||||
|
for (i=0; i < key_expr->elements; i++)
|
||||||
|
key_len+=keyinfo->key_part[i].store_length;
|
||||||
|
if (!(key=sql_calloc(ALIGN_SIZE(key_len))))
|
||||||
|
{
|
||||||
|
send_error(&thd->net,ER_OUTOFMEMORY);
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
List_iterator<Item> it_ke(*key_expr);
|
||||||
|
for (i=0, buf=key; i < key_expr->elements; i++)
|
||||||
|
{
|
||||||
|
uint maybe_null= test(keyinfo->key_part[i].null_bit);
|
||||||
|
store_key_item ski=store_key_item(keyinfo->key_part[i].field,
|
||||||
|
(char*)buf+maybe_null,maybe_null ? (char*) buf : 0,
|
||||||
|
keyinfo->key_part[i].length, it_ke++);
|
||||||
|
ski.copy();
|
||||||
|
buf+=keyinfo->key_part[i].store_length;
|
||||||
|
}
|
||||||
|
err=table->file->index_read(table->record[0],
|
||||||
|
key,key_len,ha_rkey_mode);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
send_error(&thd->net,ER_ILLEGAL_HA);
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (err && err != HA_ERR_KEY_NOT_FOUND && err != HA_ERR_END_OF_FILE)
|
||||||
|
{
|
||||||
|
sql_print_error("mysql_ha_read: Got error %d when reading table",
|
||||||
|
err);
|
||||||
|
table->file->print_error(err,MYF(0));
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
send_fields(thd,list,1);
|
||||||
|
if (!err)
|
||||||
|
{
|
||||||
|
String *packet = &thd->packet;
|
||||||
|
Item *item;
|
||||||
|
packet->length(0);
|
||||||
|
it.rewind();
|
||||||
|
while ((item=it++))
|
||||||
|
{
|
||||||
|
if (item->send(packet))
|
||||||
|
{
|
||||||
|
packet->free(); // Free used
|
||||||
|
my_error(ER_OUT_OF_RESOURCES,MYF(0));
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
my_net_write(&thd->net, (char*)packet->ptr(), packet->length());
|
||||||
|
}
|
||||||
|
send_eof(&thd->net);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**************************************************************************
|
||||||
|
2Monty: It could easily happen, that the following service functions are
|
||||||
|
already defined somewhere in the code, but I failed to find them.
|
||||||
|
If this is the case, just say a word and I'll use old functions here.
|
||||||
|
**************************************************************************/
|
||||||
|
|
||||||
|
/* Note: this function differs from find_locked_table() because we're looking
|
||||||
|
here for alias, not real table name
|
||||||
|
*/
|
||||||
|
static TABLE *find_table_by_name(THD *thd, char *db, char *table_name)
|
||||||
|
{
|
||||||
|
int dblen;
|
||||||
|
|
||||||
|
if (!db || ! *db) db=thd->db;
|
||||||
|
if (!db || ! *db) db="";
|
||||||
|
dblen=strlen(db);
|
||||||
|
|
||||||
|
for (TABLE *table=thd->open_tables; table ; table=table->next)
|
||||||
|
{
|
||||||
|
if (!memcmp(table->table_cache_key, db, dblen) &&
|
||||||
|
!my_strcasecmp(table->table_name,table_name))
|
||||||
|
return table;
|
||||||
|
}
|
||||||
|
return(0);
|
||||||
|
}
|
@ -53,7 +53,8 @@ enum enum_sql_command {
|
|||||||
SQLCOM_BEGIN, SQLCOM_LOAD_MASTER_TABLE, SQLCOM_CHANGE_MASTER,
|
SQLCOM_BEGIN, SQLCOM_LOAD_MASTER_TABLE, SQLCOM_CHANGE_MASTER,
|
||||||
SQLCOM_RENAME_TABLE, SQLCOM_BACKUP_TABLE, SQLCOM_RESTORE_TABLE,
|
SQLCOM_RENAME_TABLE, SQLCOM_BACKUP_TABLE, SQLCOM_RESTORE_TABLE,
|
||||||
SQLCOM_RESET, SQLCOM_PURGE, SQLCOM_SHOW_BINLOGS,
|
SQLCOM_RESET, SQLCOM_PURGE, SQLCOM_SHOW_BINLOGS,
|
||||||
SQLCOM_SHOW_OPEN_TABLES
|
SQLCOM_SHOW_OPEN_TABLES,
|
||||||
|
SQLCOM_HA_OPEN, SQLCOM_HA_CLOSE, SQLCOM_HA_READ
|
||||||
};
|
};
|
||||||
|
|
||||||
enum lex_states { STATE_START, STATE_CHAR, STATE_IDENT,
|
enum lex_states { STATE_START, STATE_CHAR, STATE_IDENT,
|
||||||
@ -141,6 +142,8 @@ typedef struct st_lex {
|
|||||||
enum lex_states next_state;
|
enum lex_states next_state;
|
||||||
enum enum_duplicates duplicates;
|
enum enum_duplicates duplicates;
|
||||||
enum enum_tx_isolation tx_isolation;
|
enum enum_tx_isolation tx_isolation;
|
||||||
|
enum enum_ha_read_modes ha_read_mode;
|
||||||
|
enum ha_rkey_function ha_rkey_mode;
|
||||||
uint in_sum_expr,grant,grant_tot_col,which_columns, sort_default;
|
uint in_sum_expr,grant,grant_tot_col,which_columns, sort_default;
|
||||||
thr_lock_type lock_option;
|
thr_lock_type lock_option;
|
||||||
bool create_refs,drop_primary,drop_if_exists,local_file;
|
bool create_refs,drop_primary,drop_if_exists,local_file;
|
||||||
|
@ -1996,6 +1996,23 @@ mysql_execute_command(void)
|
|||||||
res = mysql_show_grants(thd,lex->grant_user);
|
res = mysql_show_grants(thd,lex->grant_user);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case SQLCOM_HA_OPEN:
|
||||||
|
if (check_db_used(thd,tables) || check_table_access(thd,SELECT_ACL, tables))
|
||||||
|
goto error;
|
||||||
|
res = mysql_ha_open(thd, tables);
|
||||||
|
break;
|
||||||
|
case SQLCOM_HA_CLOSE:
|
||||||
|
if (check_db_used(thd,tables))
|
||||||
|
goto error;
|
||||||
|
res = mysql_ha_close(thd, tables);
|
||||||
|
break;
|
||||||
|
case SQLCOM_HA_READ:
|
||||||
|
if (check_db_used(thd,tables) || check_table_access(thd,SELECT_ACL, tables))
|
||||||
|
goto error;
|
||||||
|
res = mysql_ha_read(thd, tables, lex->ha_read_mode,
|
||||||
|
lex->backup_dir, lex->insert_list, lex->ha_rkey_mode);
|
||||||
|
break;
|
||||||
|
|
||||||
case SQLCOM_BEGIN:
|
case SQLCOM_BEGIN:
|
||||||
if (end_active_trans(thd))
|
if (end_active_trans(thd))
|
||||||
{
|
{
|
||||||
@ -2041,7 +2058,7 @@ mysql_execute_command(void)
|
|||||||
}
|
}
|
||||||
thd->proc_info="query end"; // QQ
|
thd->proc_info="query end"; // QQ
|
||||||
if (res < 0)
|
if (res < 0)
|
||||||
send_error(&thd->net,thd->killed ? ER_SERVER_SHUTDOWN : 0);
|
send_error(&thd->net,thd->killed ? ER_SERVER_SHUTDOWN : 0, 0);
|
||||||
|
|
||||||
error:
|
error:
|
||||||
DBUG_VOID_RETURN;
|
DBUG_VOID_RETURN;
|
||||||
|
@ -142,6 +142,7 @@ bool my_yyoverflow(short **a, YYSTYPE **b,int *yystacksize);
|
|||||||
%token CASCADE
|
%token CASCADE
|
||||||
%token CHECKSUM_SYM
|
%token CHECKSUM_SYM
|
||||||
%token CHECK_SYM
|
%token CHECK_SYM
|
||||||
|
%token CLOSE_SYM
|
||||||
%token COMMITTED_SYM
|
%token COMMITTED_SYM
|
||||||
%token COLUMNS
|
%token COLUMNS
|
||||||
%token COLUMN_SYM
|
%token COLUMN_SYM
|
||||||
@ -176,6 +177,7 @@ bool my_yyoverflow(short **a, YYSTYPE **b,int *yystacksize);
|
|||||||
%token GREATEST_SYM
|
%token GREATEST_SYM
|
||||||
%token GROUP
|
%token GROUP
|
||||||
%token HAVING
|
%token HAVING
|
||||||
|
%token HANDLER_SYM
|
||||||
%token HEAP_SYM
|
%token HEAP_SYM
|
||||||
%token HEX_NUM
|
%token HEX_NUM
|
||||||
%token HIGH_PRIORITY
|
%token HIGH_PRIORITY
|
||||||
@ -193,6 +195,7 @@ bool my_yyoverflow(short **a, YYSTYPE **b,int *yystacksize);
|
|||||||
%token JOIN_SYM
|
%token JOIN_SYM
|
||||||
%token KEYS
|
%token KEYS
|
||||||
%token KEY_SYM
|
%token KEY_SYM
|
||||||
|
%token LAST_SYM
|
||||||
%token LEADING
|
%token LEADING
|
||||||
%token LEAST_SYM
|
%token LEAST_SYM
|
||||||
%token LEVEL_SYM
|
%token LEVEL_SYM
|
||||||
@ -220,6 +223,7 @@ bool my_yyoverflow(short **a, YYSTYPE **b,int *yystacksize);
|
|||||||
%token NATIONAL_SYM
|
%token NATIONAL_SYM
|
||||||
%token NATURAL
|
%token NATURAL
|
||||||
%token NCHAR_SYM
|
%token NCHAR_SYM
|
||||||
|
%token NEXT_SYM
|
||||||
%token NOT
|
%token NOT
|
||||||
%token NO_SYM
|
%token NO_SYM
|
||||||
%token NULL_SYM
|
%token NULL_SYM
|
||||||
@ -236,6 +240,7 @@ bool my_yyoverflow(short **a, YYSTYPE **b,int *yystacksize);
|
|||||||
%token DUMPFILE
|
%token DUMPFILE
|
||||||
%token PACK_KEYS_SYM
|
%token PACK_KEYS_SYM
|
||||||
%token PARTIAL
|
%token PARTIAL
|
||||||
|
%token PREV_SYM
|
||||||
%token PRIMARY_SYM
|
%token PRIMARY_SYM
|
||||||
%token PRIVILEGES
|
%token PRIVILEGES
|
||||||
%token PROCESS
|
%token PROCESS
|
||||||
@ -516,13 +521,13 @@ bool my_yyoverflow(short **a, YYSTYPE **b,int *yystacksize);
|
|||||||
select_item_list select_item values_list no_braces
|
select_item_list select_item values_list no_braces
|
||||||
limit_clause delete_limit_clause fields opt_values values
|
limit_clause delete_limit_clause fields opt_values values
|
||||||
procedure_list procedure_list2 procedure_item
|
procedure_list procedure_list2 procedure_item
|
||||||
when_list2 expr_list2
|
when_list2 expr_list2 handler
|
||||||
opt_precision opt_ignore opt_column opt_restrict
|
opt_precision opt_ignore opt_column opt_restrict
|
||||||
grant revoke set lock unlock string_list field_options field_option
|
grant revoke set lock unlock string_list field_options field_option
|
||||||
field_opt_list opt_binary table_lock_list table_lock varchar
|
field_opt_list opt_binary table_lock_list table_lock varchar
|
||||||
references opt_on_delete opt_on_delete_list opt_on_delete_item use
|
references opt_on_delete opt_on_delete_list opt_on_delete_item use
|
||||||
opt_delete_options opt_delete_option
|
opt_delete_options opt_delete_option
|
||||||
opt_outer table_list table opt_option opt_place opt_low_priority
|
opt_outer table_list table_name opt_option opt_place opt_low_priority
|
||||||
opt_attribute opt_attribute_list attribute column_list column_list_id
|
opt_attribute opt_attribute_list attribute column_list column_list_id
|
||||||
opt_column_list grant_privileges opt_table user_list grant_option
|
opt_column_list grant_privileges opt_table user_list grant_option
|
||||||
grant_privilege grant_privilege_list
|
grant_privilege grant_privilege_list
|
||||||
@ -530,7 +535,7 @@ bool my_yyoverflow(short **a, YYSTYPE **b,int *yystacksize);
|
|||||||
equal optional_braces opt_key_definition key_usage_list2
|
equal optional_braces opt_key_definition key_usage_list2
|
||||||
opt_mi_check_type opt_to mi_check_types normal_join
|
opt_mi_check_type opt_to mi_check_types normal_join
|
||||||
table_to_table_list table_to_table opt_table_list opt_as
|
table_to_table_list table_to_table opt_table_list opt_as
|
||||||
END_OF_INPUT
|
handler_read_function handler_rkey_mode END_OF_INPUT
|
||||||
|
|
||||||
%type <NONE>
|
%type <NONE>
|
||||||
'-' '+' '*' '/' '%' '(' ')'
|
'-' '+' '*' '/' '%' '(' ')'
|
||||||
@ -579,6 +584,7 @@ verb_clause:
|
|||||||
| slave
|
| slave
|
||||||
| show
|
| show
|
||||||
| truncate
|
| truncate
|
||||||
|
| handler
|
||||||
| unlock
|
| unlock
|
||||||
| update
|
| update
|
||||||
| use
|
| use
|
||||||
@ -2003,10 +2009,10 @@ drop:
|
|||||||
|
|
||||||
|
|
||||||
table_list:
|
table_list:
|
||||||
table
|
table_name
|
||||||
| table_list ',' table
|
| table_list ',' table_name
|
||||||
|
|
||||||
table:
|
table_name:
|
||||||
table_ident
|
table_ident
|
||||||
{ if (!add_table_to_list($1,NULL,1)) YYABORT; }
|
{ if (!add_table_to_list($1,NULL,1)) YYABORT; }
|
||||||
|
|
||||||
@ -2039,7 +2045,7 @@ insert2:
|
|||||||
| insert_table {}
|
| insert_table {}
|
||||||
|
|
||||||
insert_table:
|
insert_table:
|
||||||
table
|
table_name
|
||||||
{
|
{
|
||||||
Lex->field_list.empty();
|
Lex->field_list.empty();
|
||||||
Lex->many_values.empty();
|
Lex->many_values.empty();
|
||||||
@ -2128,7 +2134,7 @@ values:
|
|||||||
/* Update rows in a table */
|
/* Update rows in a table */
|
||||||
|
|
||||||
update:
|
update:
|
||||||
UPDATE_SYM opt_low_priority opt_ignore table SET update_list where_clause delete_limit_clause
|
UPDATE_SYM opt_low_priority opt_ignore table_name SET update_list where_clause delete_limit_clause
|
||||||
{ Lex->sql_command = SQLCOM_UPDATE; }
|
{ Lex->sql_command = SQLCOM_UPDATE; }
|
||||||
|
|
||||||
update_list:
|
update_list:
|
||||||
@ -2155,7 +2161,7 @@ delete:
|
|||||||
Lex->sql_command= SQLCOM_DELETE; Lex->options=0;
|
Lex->sql_command= SQLCOM_DELETE; Lex->options=0;
|
||||||
Lex->lock_option= current_thd->update_lock_default;
|
Lex->lock_option= current_thd->update_lock_default;
|
||||||
}
|
}
|
||||||
opt_delete_options FROM table
|
opt_delete_options FROM table_name
|
||||||
where_clause delete_limit_clause
|
where_clause delete_limit_clause
|
||||||
|
|
||||||
|
|
||||||
@ -2168,7 +2174,7 @@ opt_delete_option:
|
|||||||
| LOW_PRIORITY { Lex->lock_option= TL_WRITE_LOW_PRIORITY; }
|
| LOW_PRIORITY { Lex->lock_option= TL_WRITE_LOW_PRIORITY; }
|
||||||
|
|
||||||
truncate:
|
truncate:
|
||||||
TRUNCATE_SYM opt_table_sym table
|
TRUNCATE_SYM opt_table_sym table_name
|
||||||
{ Lex->sql_command= SQLCOM_TRUNCATE; Lex->options=0;
|
{ Lex->sql_command= SQLCOM_TRUNCATE; Lex->options=0;
|
||||||
Lex->lock_option= current_thd->update_lock_default; }
|
Lex->lock_option= current_thd->update_lock_default; }
|
||||||
|
|
||||||
@ -2519,6 +2525,7 @@ keyword:
|
|||||||
| CHANGED {}
|
| CHANGED {}
|
||||||
| CHECKSUM_SYM {}
|
| CHECKSUM_SYM {}
|
||||||
| CHECK_SYM {}
|
| CHECK_SYM {}
|
||||||
|
| CLOSE_SYM {}
|
||||||
| COMMENT_SYM {}
|
| COMMENT_SYM {}
|
||||||
| COMMIT_SYM {}
|
| COMMIT_SYM {}
|
||||||
| COMMITTED_SYM {}
|
| COMMITTED_SYM {}
|
||||||
@ -2544,12 +2551,14 @@ keyword:
|
|||||||
| GEMINI_SYM {}
|
| GEMINI_SYM {}
|
||||||
| GLOBAL_SYM {}
|
| GLOBAL_SYM {}
|
||||||
| HEAP_SYM {}
|
| HEAP_SYM {}
|
||||||
|
| HANDLER_SYM {}
|
||||||
| HOSTS_SYM {}
|
| HOSTS_SYM {}
|
||||||
| HOUR_SYM {}
|
| HOUR_SYM {}
|
||||||
| IDENTIFIED_SYM {}
|
| IDENTIFIED_SYM {}
|
||||||
| ISOLATION {}
|
| ISOLATION {}
|
||||||
| ISAM_SYM {}
|
| ISAM_SYM {}
|
||||||
| INNOBASE_SYM {}
|
| INNOBASE_SYM {}
|
||||||
|
| LAST_SYM {}
|
||||||
| LEVEL_SYM {}
|
| LEVEL_SYM {}
|
||||||
| LOCAL_SYM {}
|
| LOCAL_SYM {}
|
||||||
| LOGS_SYM {}
|
| LOGS_SYM {}
|
||||||
@ -2572,10 +2581,12 @@ keyword:
|
|||||||
| MYISAM_SYM {}
|
| MYISAM_SYM {}
|
||||||
| NATIONAL_SYM {}
|
| NATIONAL_SYM {}
|
||||||
| NCHAR_SYM {}
|
| NCHAR_SYM {}
|
||||||
|
| NEXT_SYM {}
|
||||||
| NO_SYM {}
|
| NO_SYM {}
|
||||||
| OPEN_SYM {}
|
| OPEN_SYM {}
|
||||||
| PACK_KEYS_SYM {}
|
| PACK_KEYS_SYM {}
|
||||||
| PASSWORD {}
|
| PASSWORD {}
|
||||||
|
| PREV_SYM {}
|
||||||
| PROCESS {}
|
| PROCESS {}
|
||||||
| PROCESSLIST_SYM {}
|
| PROCESSLIST_SYM {}
|
||||||
| QUICK {}
|
| QUICK {}
|
||||||
@ -2832,6 +2843,63 @@ unlock:
|
|||||||
UNLOCK_SYM table_or_tables { Lex->sql_command=SQLCOM_UNLOCK_TABLES; }
|
UNLOCK_SYM table_or_tables { Lex->sql_command=SQLCOM_UNLOCK_TABLES; }
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
** Table: direct access to ISAM functions
|
||||||
|
*/
|
||||||
|
|
||||||
|
handler:
|
||||||
|
HANDLER_SYM table_ident OPEN_SYM opt_table_alias
|
||||||
|
{
|
||||||
|
Lex->sql_command = SQLCOM_HA_OPEN;
|
||||||
|
if (!add_table_to_list($2,$4,0))
|
||||||
|
YYABORT;
|
||||||
|
}
|
||||||
|
| HANDLER_SYM table_ident CLOSE_SYM
|
||||||
|
{
|
||||||
|
Lex->sql_command = SQLCOM_HA_CLOSE;
|
||||||
|
if (!add_table_to_list($2,0,0))
|
||||||
|
YYABORT;
|
||||||
|
}
|
||||||
|
| HANDLER_SYM table_ident READ_SYM ident handler_read_function
|
||||||
|
{
|
||||||
|
Lex->sql_command = SQLCOM_HA_READ;
|
||||||
|
Lex->backup_dir= $4.str;
|
||||||
|
if (!add_table_to_list($2,0,0))
|
||||||
|
YYABORT;
|
||||||
|
}
|
||||||
|
|
||||||
|
handler_read_function:
|
||||||
|
FIRST_SYM
|
||||||
|
{
|
||||||
|
Lex->ha_read_mode = RFIRST;
|
||||||
|
}
|
||||||
|
| NEXT_SYM
|
||||||
|
{
|
||||||
|
Lex->ha_read_mode = RNEXT;
|
||||||
|
}
|
||||||
|
| PREV_SYM
|
||||||
|
{
|
||||||
|
Lex->ha_read_mode = RPREV;
|
||||||
|
}
|
||||||
|
| LAST_SYM
|
||||||
|
{
|
||||||
|
Lex->ha_read_mode = RLAST;
|
||||||
|
}
|
||||||
|
| handler_rkey_mode
|
||||||
|
{
|
||||||
|
Lex->ha_read_mode = RKEY;
|
||||||
|
if (!(Lex->insert_list = new List_item))
|
||||||
|
YYABORT;
|
||||||
|
}
|
||||||
|
'(' values ')' { }
|
||||||
|
|
||||||
|
handler_rkey_mode:
|
||||||
|
EQ { Lex->ha_rkey_mode=HA_READ_KEY_EXACT; }
|
||||||
|
| GE { Lex->ha_rkey_mode=HA_READ_KEY_OR_NEXT; }
|
||||||
|
| LE { Lex->ha_rkey_mode=HA_READ_KEY_OR_PREV; }
|
||||||
|
| GT_SYM {Lex->ha_rkey_mode=HA_READ_AFTER_KEY; }
|
||||||
|
| LT { Lex->ha_rkey_mode=HA_READ_BEFORE_KEY; }
|
||||||
|
|
||||||
/* GRANT / REVOKE */
|
/* GRANT / REVOKE */
|
||||||
|
|
||||||
revoke:
|
revoke:
|
||||||
|
Reference in New Issue
Block a user