• Igor Babaev's avatar
    MDEV-28615 Crash caused by multi-table UPDATE over derived with hanging CTE · 9e321a44
    Igor Babaev authored
    This bug affected only multi-table update statements and in very rare
    cases: one of the tables used at the top level of the statement must be
    a derived table containg a row construct with a subquery including hanging
    CTE.
    
    Before this patch was applied the function prepare_unreferenced() of the
    class With_element when invoked for the the hangin CTE did not properly
    restored the value of thd->lex->context_analysis_only. As a result it
    became 0 after the call of this function.
    For a query affected by the bug this function is called when
    JOIN::prepare() is called for the subquery with a hanging CTE. This happens
    when Item_row::fix_fields() calls fix_fields() for the subquery. Setting
    the value of thd->lex->context_analysis_only forces the caller function
    Item_row::fix_fields() to invoke the virtual method is_null() for the
    subquery that leads to execution of it. It causes an assertion failure
    because the call of Item_row::fix_fields() happens during the invocation
    of Multiupdate_prelocking_strategy::handle_end() that calls the function
    mysql_derived_prepare() for the derived table used by the UPDATE at the
    time when proper locks for the statement tables has not been acquired yet.
    
    With this patch the value of thd->lex->context_analysis_only is restored
    to CONTEXT_ANALYSIS_ONLY_DERIVED that is set in the function
    mysql_multi_update_prepare().
    
    Approved by Oleksandr Byelkin <sanja@mariadb.com>
    9e321a44
cte_nonrecursive.result 72.2 KB