summaryrefslogtreecommitdiff
path: root/sql
diff options
context:
space:
mode:
authorRaghav Kapoor <raghav.kapoor@oracle.com>2014-06-25 18:06:28 +0530
committerRaghav Kapoor <raghav.kapoor@oracle.com>2014-06-25 18:06:28 +0530
commitcdf72d51c631aecb46505ff94cdb9ef667d4444c (patch)
treee8010dce623c94162e25a3479aa7d290baaf0132 /sql
parentd63645c890550cc190416e2c90585c1c6903b529 (diff)
downloadmariadb-git-cdf72d51c631aecb46505ff94cdb9ef667d4444c.tar.gz
BUG#17665767 - FAILING ASSERTION: PRIMARY_KEY_NO == -1 || PRIMARY_KEY_NO == 0
BACKGROUND: This bug is a followup on Bug#16368875. The assertion failure happens because in SQL layer the key does not get promoted to PRIMARY KEY but InnoDB takes it as PRIMARY KEY. ANALYSIS: Here we are trying to create an index on POINT (GEOMETRY) data type which is a type of BLOB (since GEOMETRY is a subclass of BLOB). In general, we can't create an index over GEOMETRY family type field unless we specify the length of the keypart (similar to BLOB fields). Only exception is the POINT field type. The POINT column max size is 25. The problem is that the field is not treated as PRIMARY KEY when we create a index on POINT column using its max column size as key part prefix. The fix would allow index on POINT column to be treated as PRIMARY KEY. FIX: Patch for Bug#16368875 is extended to take into account GEOMETRY datatype, POINT in particular to consider it as PRIMARY KEY in SQL layer.
Diffstat (limited to 'sql')
-rw-r--r--sql/sql_table.cc2
-rw-r--r--sql/sql_table.h3
-rw-r--r--sql/sql_yacc.yy3
-rw-r--r--sql/table.cc11
4 files changed, 17 insertions, 2 deletions
diff --git a/sql/sql_table.cc b/sql/sql_table.cc
index 1664f94515a..8b4873cb834 100644
--- a/sql/sql_table.cc
+++ b/sql/sql_table.cc
@@ -3459,7 +3459,7 @@ mysql_prepare_create_table(THD *thd, HA_CREATE_INFO *create_info,
}
if (f_is_geom(sql_field->pack_flag) && sql_field->geom_type ==
Field::GEOM_POINT)
- column->length= 25;
+ column->length= MAX_LEN_GEOM_POINT_FIELD;
if (!column->length)
{
my_error(ER_BLOB_KEY_WITHOUT_LENGTH, MYF(0), column->field_name.str);
diff --git a/sql/sql_table.h b/sql/sql_table.h
index 6f09db12bb9..82f6dfb9658 100644
--- a/sql/sql_table.h
+++ b/sql/sql_table.h
@@ -105,6 +105,9 @@ enum enum_explain_filename_mode
EXPLAIN_PARTITIONS_AS_COMMENT
};
+/* Maximum length of GEOM_POINT Field */
+#define MAX_LEN_GEOM_POINT_FIELD 25
+
/* depends on errmsg.txt Database `db`, Table `t` ... */
#define EXPLAIN_FILENAME_MAX_EXTRA_LENGTH 63
diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy
index bd5d4dc5604..74a21c9f6b6 100644
--- a/sql/sql_yacc.yy
+++ b/sql/sql_yacc.yy
@@ -5603,7 +5603,8 @@ spatial_type:
| GEOMETRYCOLLECTION { $$= Field::GEOM_GEOMETRYCOLLECTION; }
| POINT_SYM
{
- Lex->length= (char*)"25";
+ Lex->length= const_cast<char*>(STRINGIFY_ARG
+ (MAX_LEN_GEOM_POINT_FIELD));
$$= Field::GEOM_POINT;
}
| MULTIPOINT { $$= Field::GEOM_MULTIPOINT; }
diff --git a/sql/table.cc b/sql/table.cc
index ba1839bb6ec..b24e03fbe1a 100644
--- a/sql/table.cc
+++ b/sql/table.cc
@@ -1539,6 +1539,17 @@ static int open_binary_frm(THD *thd, TABLE_SHARE *share, uchar *head,
table_field->type() == MYSQL_TYPE_BLOB &&
table_field->field_length == key_part[i].length)
continue;
+ /*
+ If the key column is of NOT NULL GEOMETRY type, specifically POINT
+ type whose length is known internally (which is 25). And key part
+ prefix size is equal to the POINT column max size, then we can
+ promote it to primary key.
+ */
+ if (!table_field->real_maybe_null() &&
+ table_field->type() == MYSQL_TYPE_GEOMETRY &&
+ table_field->get_geometry_type() == Field::GEOM_POINT &&
+ key_part[i].length == MAX_LEN_GEOM_POINT_FIELD)
+ continue;
if (table_field->real_maybe_null() ||
table_field->key_length() != key_part[i].length)