Commit 31ad5e49 authored by monty@mysql.com's avatar monty@mysql.com

Merge bk-internal.mysql.com:/home/bk/mysql-4.0

into mysql.com:/home/my/mysql-4.0
parents e71325ca ed44e769
......@@ -2138,19 +2138,37 @@ dict_scan_col(
return(ptr);
}
if (*ptr == '`') {
ptr++;
}
old_ptr = ptr;
if (*ptr == '`' || *ptr == '"') {
/*
The identifier is quoted. Search for end quote.
We can't use the general code here as the name may contain
special characters like space.
*/
char quote= *ptr++;
old_ptr= ptr;
/*
The colum name should always end with 'quote' but we check for
end zero just to be safe if this is called outside of MySQL
*/
while (*ptr && *ptr != quote)
ptr++;
*column_name_len = (ulint)(ptr - old_ptr);
if (*ptr) /* Skip end quote */
ptr++;
}
else
{
old_ptr = ptr;
while (!isspace(*ptr) && *ptr != ',' && *ptr != ')' && *ptr != '`'
&& *ptr != '\0') {
while (!isspace(*ptr) && *ptr != ',' && *ptr != ')'
&& *ptr != '\0') {
ptr++;
}
*column_name_len = (ulint)(ptr - old_ptr);
}
*column_name_len = (ulint)(ptr - old_ptr);
if (table == NULL) {
*success = TRUE;
......@@ -2161,9 +2179,9 @@ dict_scan_col(
col = dict_table_get_nth_col(table, i);
if (ut_strlen(col->name) == (ulint)(ptr - old_ptr)
if (ut_strlen(col->name) == *column_name_len
&& 0 == ut_cmp_in_lower_case(col->name, old_ptr,
(ulint)(ptr - old_ptr))) {
*column_name_len)) {
/* Found */
*success = TRUE;
......@@ -2175,10 +2193,6 @@ dict_scan_col(
}
}
if (*ptr == '`') {
ptr++;
}
return(ptr);
}
......@@ -2200,6 +2214,7 @@ dict_scan_table_name(
char* dot_ptr = NULL;
char* old_ptr;
ulint i;
char quote = 0;
*success = FALSE;
*table = NULL;
......@@ -2213,14 +2228,16 @@ dict_scan_table_name(
return(ptr);
}
if (*ptr == '`') {
ptr++;
if (*ptr == '`' || *ptr == '"') {
quote= *ptr++;
}
old_ptr = ptr;
while (!isspace(*ptr) && *ptr != '(' && *ptr != '`' && *ptr != '\0') {
if (*ptr == '.') {
while (*ptr != quote &&
(quote || (!isspace(*ptr) && *ptr != '(')) &&
*ptr != '\0') {
if (!quote && *ptr == '.') {
dot_ptr = ptr;
}
......@@ -2273,7 +2290,7 @@ dict_scan_table_name(
*table = dict_table_get_low(second_table_name);
if (*ptr == '`') {
if (*ptr && *ptr == quote) {
ptr++;
}
......@@ -2293,7 +2310,7 @@ dict_scan_id(
scannable */
ulint* len) /* out: length of the id */
{
ibool scanned_backquote = FALSE;
char quote = 0;
*start = NULL;
......@@ -2306,23 +2323,23 @@ dict_scan_id(
return(ptr);
}
if (*ptr == '`') {
scanned_backquote = TRUE;
ptr++;
if (*ptr == '`' || *ptr == '"') {
quote = *ptr++;
}
*start = ptr;
while (!isspace(*ptr) && *ptr != ',' && *ptr != '(' && *ptr != ')'
&& *ptr != '\0' && *ptr != '`') {
while (*ptr != quote &&
(!quote || (!isspace(*ptr) && *ptr != ',' && *ptr != '(' &&
*ptr != ')'))
&& *ptr != '\0') {
ptr++;
}
*len = (ulint) (ptr - *start);
if (scanned_backquote) {
if (*ptr == '`') {
if (quote) {
if (*ptr == quote) {
ptr++;
} else {
/* Syntax error */
......
......@@ -1243,3 +1243,6 @@ a
3
4
drop table t1;
CREATE TABLE t1 (`id 1` INT NOT NULL, PRIMARY KEY (`id 1`)) TYPE=INNODB;
CREATE TABLE t2 (id INT PRIMARY KEY, t1_id INT, INDEX par_ind (t1_id), FOREIGN KEY (`t1_id`) REFERENCES `t1`(`id 1`) ON DELETE CASCADE ) TYPE=INNODB;
drop table t1,t2;
......@@ -869,3 +869,12 @@ truncate table t1;
insert into t1 (a) values (NULL),(NULL);
SELECT * from t1;
drop table t1;
#
# Test dictionary handling with spaceand quoting
#
CREATE TABLE t1 (`id 1` INT NOT NULL, PRIMARY KEY (`id 1`)) TYPE=INNODB;
CREATE TABLE t2 (id INT PRIMARY KEY, t1_id INT, INDEX par_ind (t1_id), FOREIGN KEY (`t1_id`) REFERENCES `t1`(`id 1`) ON DELETE CASCADE ) TYPE=INNODB;
#show create table t2;
drop table t1,t2;
......@@ -538,7 +538,6 @@ select_export::~select_export()
int
select_export::prepare(List<Item> &list)
{
char path[FN_REFLEN];
uint option=4;
bool blob_flag=0;
#ifdef DONT_ALLOW_FULL_LOAD_DATA_PATHS
......@@ -739,9 +738,13 @@ err:
void select_export::send_error(uint errcode,const char *err)
{
::send_error(&thd->net,errcode,err);
(void) end_io_cache(&cache);
(void) my_close(file,MYF(0));
file= -1;
if (file > 0)
{
(void) end_io_cache(&cache);
(void) my_close(file,MYF(0));
(void) my_delete(path,MYF(0)); // Delete file on error
file= -1;
}
}
......@@ -849,10 +852,13 @@ err:
void select_dump::send_error(uint errcode,const char *err)
{
::send_error(&thd->net,errcode,err);
(void) end_io_cache(&cache);
(void) my_close(file,MYF(0));
(void) my_delete(path,MYF(0)); // Delete file on error
file= -1;
if (file > 0)
{
(void) end_io_cache(&cache);
(void) my_close(file,MYF(0));
(void) my_delete(path,MYF(0)); // Delete file on error
file= -1;
}
}
......
......@@ -665,11 +665,13 @@ class select_export :public select_result {
File file;
IO_CACHE cache;
ha_rows row_count;
char path[FN_REFLEN];
uint field_term_length;
int field_sep_char,escape_char,line_sep_char;
bool fixed_row_size;
public:
select_export(sql_exchange *ex) :exchange(ex),file(-1),row_count(0L) {}
select_export(sql_exchange *ex) :exchange(ex),file(-1),row_count(0L)
{ path[0]=0; }
~select_export();
int prepare(List<Item> &list);
bool send_fields(List<Item> &list,
......
......@@ -1912,7 +1912,8 @@ find_best(JOIN *join,table_map rest_tables,uint idx,double record_count,
read_time+=record_count/(double) TIME_FOR_COMPARE;
if (join->sort_by_table &&
join->sort_by_table != join->positions[join->const_tables].table->table)
join->sort_by_table !=
join->positions[join->const_tables].table->table)
read_time+=record_count; // We have to make a temp table
if (read_time < join->best_read)
{
......@@ -1946,7 +1947,7 @@ find_best(JOIN *join,table_map rest_tables,uint idx,double record_count,
uint max_key_part=0;
/* Test how we can use keys */
rec= s->records/MATCHING_ROWS_IN_OTHER_TABLE; /* Assumed records/key */
rec= s->records/MATCHING_ROWS_IN_OTHER_TABLE; // Assumed records/key
for (keyuse=s->keyuse ; keyuse->table == table ;)
{
key_map found_part=0;
......@@ -2085,7 +2086,7 @@ find_best(JOIN *join,table_map rest_tables,uint idx,double record_count,
will match
*/
if (table->quick_keys & ((key_map) 1 << key) &&
table->quick_key_parts[key] <= max_key_part)
table->quick_key_parts[key] == max_key_part)
tmp=records= (double) table->quick_rows[key];
else
{
......@@ -2127,6 +2128,14 @@ find_best(JOIN *join,table_map rest_tables,uint idx,double record_count,
}
records=(ulong) tmp;
}
/*
If quick_select was used on a part of this key, we know
the maximum number of rows that the key can match.
*/
if (table->quick_keys & ((key_map) 1 << key) &&
table->quick_key_parts[key] <= max_key_part &&
records > (double) table->quick_rows[key])
tmp= records= (double) table->quick_rows[key];
}
/* Limit the number of matched rows */
set_if_smaller(tmp, (double) thd->variables.max_seeks_for_key);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment