diff options
author | Alexander Barkov <bar@mariadb.org> | 2015-12-03 15:20:57 +0400 |
---|---|---|
committer | Alexander Barkov <bar@mariadb.org> | 2015-12-03 15:20:57 +0400 |
commit | 8eefe57c91fd6ca43649af18949ebbb572ffc437 (patch) | |
tree | d0d41bf53f1a740d6c5f351d61c545a6204bd5e4 /sql/sp_head.cc | |
parent | f3ff8b35299855b9e89696c73bcdd9945a4311fc (diff) | |
download | mariadb-git-8eefe57c91fd6ca43649af18949ebbb572ffc437.tar.gz |
Fixing DBUG_ASSERT() introduced in e3fed3b9b4f488e9ad1afa57333ae80249e6cb17
(a change adding a helper method Column_definition::make_field())
to take into account the EXECUTE stage of a prepared statement.
This DBUG_ASSERT() caused crashes in a few tests when running "mtr --ps".
Diffstat (limited to 'sql/sp_head.cc')
-rw-r--r-- | sql/sp_head.cc | 39 |
1 files changed, 38 insertions, 1 deletions
diff --git a/sql/sp_head.cc b/sql/sp_head.cc index 0b95123c7d9..ce4ec09bede 100644 --- a/sql/sp_head.cc +++ b/sql/sp_head.cc @@ -845,7 +845,44 @@ sp_head::create_result_field(uint field_max_length, const char *field_name, DBUG_ENTER("sp_head::create_result_field"); - DBUG_ASSERT(field_max_length <= m_return_field_def.length); + /* + m_return_field_def.length is always set to the field length calculated + by the parser, according to the RETURNS clause. See prepare_create_field() + in sql_table.cc. Value examples, depending on data type: + - 11 for INT (character representation length) + - 20 for BIGINT (character representation length) + - 22 for DOUBLE (character representation length) + - N for CHAR(N) CHARACTER SET latin1 (octet length) + - 3*N for CHAR(N) CHARACTER SET utf8 (octet length) + - 8 for blob-alike data types (packed length !!!) + + field_max_length is also set according to the data type in the RETURNS + clause but can have different values depending on the execution stage: + + 1. During direct execution: + field_max_length is 0, because Item_func_sp::fix_length_and_dec() has + not been called yet, so Item_func_sp::max_length is 0 by default. + + 2a. During PREPARE: + field_max_length is 0, because Item_func_sp::fix_length_and_dec() + has not been called yet. It's called after create_result_field(). + + 2b. During EXEC: + field_max_length is set to the maximum possible octet length of the + RETURNS data type. + - N for CHAR(N) CHARACTER SET latin1 (octet length) + - 3*N for CHAR(N) CHARACTER SET utf8 (octet length) + - 255 for TINYBLOB (octet length, not packed length !!!) + + Perhaps we should refactor prepare_create_field() to set + Create_field::length to maximum octet length for BLOBs, + instead of packed length). + */ + DBUG_ASSERT(field_max_length <= m_return_field_def.length || + (current_thd->stmt_arena->is_stmt_execute() && + m_return_field_def.length == 8 && + (m_return_field_def.pack_flag & + (FIELDFLAG_BLOB|FIELDFLAG_GEOM)))); field= m_return_field_def.make_field(table->s, /* TABLE_SHARE ptr */ table->in_use->mem_root, |