mirror of
https://github.com/MariaDB/server.git
synced 2025-11-09 11:41:36 +03:00
LIMIT ROWS EXAMINED prematurely triggers during optimization
1. LIMIT ROWS EXAMINED clause allows to abort a query if a certain limit of rows involved in processing is exceeded. This limitation should be only enforced during the execution phase and not the optimization. 2. Unions are often executed using so-called "fake_select_lex" which collects the final result from union parts. During that finalization LIMIT ROWS EXAMINED must be ignored to avoid producing a potentially incomplete result. There is a workaround at `st_select_lex_unit::exec()` which deactivates the limit before fake_select_lex processing, and re-activates it when the processing is finished. However, this re-activation does not take into account whether the limit was active before the start of fake_select_lex processing. 3. `st_select_lex_unit::exec()` can be invoked during the optimization phase for evaluation of constant conditions with unions. At that time the limit trigger is not activated. Given that the re-activation mentioned above does not respect the previous state of the limit trigger, a premature activation of the limit may happen. This commit fixes that behavior by storing the state of the trigger before its deactivation at `st_select_lex_unit::exec()` and re-activating it only if the limit was active before. 4. This commit also removes the call to `thd->lex->set_rows_examined()` from `st_select_lex_unit::exec_recursive()` which was probably copied from `st_select_lex_unit::exec()`. But in the context of `exec_recursive()` the call does not make sense as there is no previous deactivation of the limit as at `exec()`. Reviewed by: Dave Gosselin, Sergei Petrunia
This commit is contained in:
@@ -3604,8 +3604,6 @@ public:
|
||||
{
|
||||
if (limit_rows_examined)
|
||||
limit_rows_examined_cnt= limit_rows_examined->val_uint();
|
||||
else
|
||||
limit_rows_examined_cnt= ULONGLONG_MAX; // Unreachable value
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -3617,7 +3615,7 @@ public:
|
||||
*/
|
||||
bool deactivate_limit_rows_examined()
|
||||
{
|
||||
bool was_activated= (limit_rows_examined_cnt == ULONGLONG_MAX);
|
||||
bool was_activated= (limit_rows_examined_cnt != ULONGLONG_MAX);
|
||||
limit_rows_examined_cnt= ULONGLONG_MAX; // Unreachable value
|
||||
return was_activated;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user