1
0
mirror of https://github.com/MariaDB/server.git synced 2025-07-30 16:24:05 +03:00

Merge kpettersson@bk-internal.mysql.com:/home/bk/mysql-5.1-runtime

into  adventure.(none):/home/thek/Development/cpp/mysql-5.1-runtime
This commit is contained in:
thek@adventure.(none)
2007-07-29 13:08:21 +02:00
5 changed files with 193 additions and 133 deletions

View File

@ -2889,135 +2889,6 @@ void st_table::reset_item_list(List<Item> *item_list) const
}
}
/**
Set the initial purpose of this TABLE_LIST object in the list of
used tables. We need to track this information on table-by-
table basis, since when this table becomes an element of the
pre-locked list, it's impossible to identify which SQL
sub-statement it has been originally used in.
E.g.:
User request: SELECT * FROM t1 WHERE f1();
FUNCTION f1(): DELETE FROM t2; RETURN 1;
BEFORE DELETE trigger on t2: INSERT INTO t3 VALUES (old.a);
For this user request, the pre-locked list will contain t1, t2, t3
table elements, each needed for different DML.
This method is called immediately after parsing for tables
of the table list of the top-level select lex.
The trigger event map is updated to reflect INSERT, UPDATE, DELETE,
REPLACE, LOAD DATA, CREATE TABLE .. SELECT, CREATE TABLE ..
REPLACE SELECT statements, and additionally ON DUPLICATE KEY UPDATE
clause.
*/
void
TABLE_LIST::set_trg_event_type(const st_lex *lex)
{
enum trg_event_type trg_event;
/*
Some auxiliary operations
(e.g. GRANT processing) create TABLE_LIST instances outside
the parser. Additionally, some commands (e.g. OPTIMIZE) change
the lock type for a table only after parsing is done. Luckily,
these do not fire triggers and do not need to pre-load them.
For these TABLE_LISTs set_trg_event_type is never called, and
trg_event_map is always empty. That means that the pre-locking
algorithm will ignore triggers defined on these tables, if
any, and the execution will either fail with an assert in
sql_trigger.cc or with an error that a used table was not
pre-locked, in case of a production build.
TODO: this usage pattern creates unnecessary module dependencies
and should be rewritten to go through the parser.
Table list instances created outside the parser in most cases
refer to mysql.* system tables. It is not allowed to have
a trigger on a system table, but keeping track of
initialization provides extra safety in case this limitation
is circumvented.
*/
/*
This is a fast check to filter out statements that do
not change data, or tables on the right side, in case of
INSERT .. SELECT, CREATE TABLE .. SELECT and so on.
Here we also filter out OPTIMIZE statement and non-updateable
views, for which lock_type is TL_UNLOCK or TL_READ after
parsing.
*/
if (static_cast<int>(lock_type) < static_cast<int>(TL_WRITE_ALLOW_WRITE))
return;
switch (lex->sql_command) {
/*
Basic INSERT. If there is an additional ON DUPLIATE KEY UPDATE
clause, it will be handled later in this method.
*/
case SQLCOM_INSERT: /* fall through */
case SQLCOM_INSERT_SELECT:
/*
LOAD DATA ... INFILE is expected to fire BEFORE/AFTER INSERT
triggers.
If the statement also has REPLACE clause, it will be
handled later in this method.
*/
case SQLCOM_LOAD: /* fall through */
/*
REPLACE is semantically equivalent to INSERT. In case
of a primary or unique key conflict, it deletes the old
record and inserts a new one. So we also may need to
fire ON DELETE triggers. This functionality is handled
later in this method.
*/
case SQLCOM_REPLACE: /* fall through */
case SQLCOM_REPLACE_SELECT:
/*
CREATE TABLE ... SELECT defaults to INSERT if the table or
view already exists. REPLACE option of CREATE TABLE ...
REPLACE SELECT is handled later in this method.
*/
case SQLCOM_CREATE_TABLE:
trg_event= TRG_EVENT_INSERT;
break;
/* Basic update and multi-update */
case SQLCOM_UPDATE: /* fall through */
case SQLCOM_UPDATE_MULTI:
trg_event= TRG_EVENT_UPDATE;
break;
/* Basic delete and multi-delete */
case SQLCOM_DELETE: /* fall through */
case SQLCOM_DELETE_MULTI:
trg_event= TRG_EVENT_DELETE;
break;
default:
/*
OK to return, since value of 'duplicates' is irrelevant
for non-updating commands.
*/
return;
}
trg_event_map|= static_cast<uint8>(1 << static_cast<int>(trg_event));
switch (lex->duplicates) {
case DUP_UPDATE:
trg_event= TRG_EVENT_UPDATE;
break;
case DUP_REPLACE:
trg_event= TRG_EVENT_DELETE;
break;
case DUP_ERROR:
default:
return;
}
trg_event_map|= static_cast<uint8>(1 << static_cast<int>(trg_event));
}
/*
calculate md5 of query