diff options
author | unknown <monty@mysql.com> | 2005-05-16 15:26:40 +0300 |
---|---|---|
committer | unknown <monty@mysql.com> | 2005-05-16 15:26:40 +0300 |
commit | 4d3d703200f2ef575942d0c053371c6596b77b7d (patch) | |
tree | 947fb072bf07d38ba8947779578299a196136c92 /sql | |
parent | b9a4e7d88eabba5b7463da899d1a72a264a84093 (diff) | |
parent | d15f89c47afd2b674e666098eee69ec8bdfb901d (diff) | |
download | mariadb-git-4d3d703200f2ef575942d0c053371c6596b77b7d.tar.gz |
Merge bk-internal.mysql.com:/home/bk/mysql-5.0
into mysql.com:/home/my/mysql-5.0
BitKeeper/etc/logging_ok:
auto-union
Diffstat (limited to 'sql')
-rw-r--r-- | sql/handler.cc | 7 | ||||
-rw-r--r-- | sql/handler.h | 1 | ||||
-rw-r--r-- | sql/hostname.cc | 4 | ||||
-rw-r--r-- | sql/item_func.cc | 5 | ||||
-rw-r--r-- | sql/sql_table.cc | 38 | ||||
-rw-r--r-- | sql/sql_yacc.yy | 29 | ||||
-rw-r--r-- | sql/unireg.cc | 77 |
7 files changed, 90 insertions, 71 deletions
diff --git a/sql/handler.cc b/sql/handler.cc index a34b3bd8aac..d641628ac86 100644 --- a/sql/handler.cc +++ b/sql/handler.cc @@ -1420,6 +1420,7 @@ void handler::update_auto_increment() ulonglong nr; THD *thd= table->in_use; struct system_variables *variables= &thd->variables; + bool auto_increment_field_not_null; DBUG_ENTER("handler::update_auto_increment"); /* @@ -1427,13 +1428,14 @@ void handler::update_auto_increment() row was not inserted */ thd->prev_insert_id= thd->next_insert_id; + auto_increment_field_not_null= table->auto_increment_field_not_null; + table->auto_increment_field_not_null= FALSE; if ((nr= table->next_number_field->val_int()) != 0 || - table->auto_increment_field_not_null && + auto_increment_field_not_null && thd->variables.sql_mode & MODE_NO_AUTO_VALUE_ON_ZERO) { /* Clear flag for next row */ - table->auto_increment_field_not_null= FALSE; /* Mark that we didn't generate a new value **/ auto_increment_column_changed=0; @@ -1449,7 +1451,6 @@ void handler::update_auto_increment() } DBUG_VOID_RETURN; } - table->auto_increment_field_not_null= FALSE; if (!(nr= thd->next_insert_id)) { nr= get_auto_increment(); diff --git a/sql/handler.h b/sql/handler.h index 11f8dd0b4d7..6a259da0d43 100644 --- a/sql/handler.h +++ b/sql/handler.h @@ -378,6 +378,7 @@ typedef struct st_ha_create_information SQL_LIST merge_list; enum db_type db_type; enum row_type row_type; + uint null_bits; /* NULL bits at start of record */ uint options; /* OR of HA_CREATE_ options */ uint raid_type,raid_chunks; uint merge_insert_method; diff --git a/sql/hostname.cc b/sql/hostname.cc index ec5c6f29a27..39223556024 100644 --- a/sql/hostname.cc +++ b/sql/hostname.cc @@ -209,8 +209,8 @@ my_string ip_to_hostname(struct in_addr *in, uint *errors) DBUG_PRINT("error",("gethostbyaddr returned %d",errno)); if (errno == HOST_NOT_FOUND || errno == NO_DATA) - add_wrong_ip(in); /* only cache negative responses, not failures */ - + goto add_wrong_ip_and_return; + /* Failure, don't cache responce */ DBUG_RETURN(0); } if (!hp->h_name[0]) // Don't allow empty hostnames diff --git a/sql/item_func.cc b/sql/item_func.cc index db49b7b4ae9..2d537b1cccf 100644 --- a/sql/item_func.cc +++ b/sql/item_func.cc @@ -4311,6 +4311,11 @@ bool Item_func_match::fix_fields(THD *thd, TABLE_LIST *tlist, Item **ref) return TRUE; } table=((Item_field *)item)->field->table; + if (!(table->file->table_flags() & HA_CAN_FULLTEXT)) + { + my_error(ER_TABLE_CANT_HANDLE_FT, MYF(0)); + return 1; + } table->fulltext_searched=1; return agg_arg_collations_for_comparison(cmp_collation, args+1, arg_count-1); } diff --git a/sql/sql_table.cc b/sql/sql_table.cc index ad0a0baae2d..4ddef3fc653 100644 --- a/sql/sql_table.cc +++ b/sql/sql_table.cc @@ -640,9 +640,8 @@ static int mysql_prepare_table(THD *thd, HA_CREATE_INFO *create_info, { const char *key_name; create_field *sql_field,*dup_field; - uint field,null_fields,blob_columns; - uint max_key_length= file->max_key_length(); - ulong pos; + uint field,null_fields,blob_columns,max_key_length; + ulong record_offset= 0; KEY *key_info; KEY_PART_INFO *key_part_info; int timestamps= 0, timestamps_with_niladic= 0; @@ -655,6 +654,7 @@ static int mysql_prepare_table(THD *thd, HA_CREATE_INFO *create_info, select_field_pos= fields->elements - select_field_count; null_fields=blob_columns=0; create_info->varchar= 0; + max_key_length= file->max_key_length(); for (field_no=0; (sql_field=it++) ; field_no++) { @@ -836,10 +836,10 @@ static int mysql_prepare_table(THD *thd, HA_CREATE_INFO *create_info, (*db_options)|= HA_OPTION_PACK_RECORD; it2.rewind(); } - /* If fixed row records, we need one bit to check for deleted rows */ - if (!((*db_options) & HA_OPTION_PACK_RECORD)) - null_fields++; - pos= (null_fields + total_uneven_bit_length + 7) / 8; + + /* record_offset will be increased with 'length-of-null-bits' later */ + record_offset= 0; + null_fields+= total_uneven_bit_length; it.rewind(); while ((sql_field=it++)) @@ -852,10 +852,10 @@ static int mysql_prepare_table(THD *thd, HA_CREATE_INFO *create_info, DBUG_RETURN(-1); if (sql_field->sql_type == MYSQL_TYPE_VARCHAR) create_info->varchar= 1; - sql_field->offset= pos; + sql_field->offset= record_offset; if (MTYP_TYPENR(sql_field->unireg_check) == Field::NEXT_NUMBER) auto_increment++; - pos+=sql_field->pack_length; + record_offset+= sql_field->pack_length; } if (timestamps_with_niladic > 1) { @@ -1159,6 +1159,7 @@ static int mysql_prepare_table(THD *thd, HA_CREATE_INFO *create_info, /* Implicitly set primary key fields to NOT NULL for ISO conf. */ sql_field->flags|= NOT_NULL_FLAG; sql_field->pack_flag&= ~FIELDFLAG_MAYBE_NULL; + null_fields--; } else key_info->flags|= HA_NULL_PART_KEY; @@ -1190,10 +1191,10 @@ static int mysql_prepare_table(THD *thd, HA_CREATE_INFO *create_info, { if (f_is_blob(sql_field->pack_flag)) { - if ((length=column->length) > file->max_key_length() || + if ((length=column->length) > max_key_length || length > file->max_key_part_length()) { - length=min(file->max_key_length(), file->max_key_part_length()); + length=min(max_key_length, file->max_key_part_length()); if (key->type == Key::MULTIPLE) { /* not a critical problem */ @@ -1317,6 +1318,7 @@ static int mysql_prepare_table(THD *thd, HA_CREATE_INFO *create_info, /* Sort keys in optimized order */ qsort((gptr) *key_info_buffer, *key_count, sizeof(KEY), (qsort_cmp) sort_keys); + create_info->null_bits= null_fields; DBUG_RETURN(0); } @@ -3417,12 +3419,14 @@ bool mysql_alter_table(THD *thd,char *new_db, char *new_name, /* better have a negative test here, instead of positive, like - alter_info->flags & ALTER_ADD_COLUMN|ALTER_ADD_INDEX|... + alter_info->flags & ALTER_ADD_COLUMN|ALTER_ADD_INDEX|... so that ALTER TABLE won't break when somebody will add new flag */ - need_copy_table=(alter_info->flags & ~(ALTER_CHANGE_COLUMN_DEFAULT|ALTER_OPTIONS) || - create_info->used_fields & ~(HA_CREATE_USED_COMMENT|HA_CREATE_USED_PASSWORD) || - table->s->tmp_table); + need_copy_table= (alter_info->flags & + ~(ALTER_CHANGE_COLUMN_DEFAULT|ALTER_OPTIONS) || + (create_info->used_fields & + ~(HA_CREATE_USED_COMMENT|HA_CREATE_USED_PASSWORD)) || + table->s->tmp_table); create_info->frm_only= !need_copy_table; /* @@ -3827,8 +3831,8 @@ copy_data_between_tables(TABLE *from,TABLE *to, !(sortorder=make_unireg_sortorder(order, &length)) || (from->sort.found_records = filesort(thd, from, sortorder, length, (SQL_SELECT *) 0, HA_POS_ERROR, - &examined_rows)) - == HA_POS_ERROR) + &examined_rows)) == + HA_POS_ERROR) goto err; }; diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index 25a78178995..9328d7345c3 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -3986,7 +3986,14 @@ select_from: select_options: /* empty*/ - | select_option_list; + | select_option_list + { + if (test_all_bits(Select->options, SELECT_ALL | SELECT_DISTINCT)) + { + my_error(ER_WRONG_USAGE, MYF(0), "ALL", "DISTINCT"); + YYABORT; + } + } select_option_list: select_option_list select_option @@ -4000,15 +4007,7 @@ select_option: YYABORT; Lex->lock_option= TL_READ_HIGH_PRIORITY; } - | DISTINCT - { - if (Select->options & SELECT_ALL) - { - yyerror(ER(ER_SYNTAX_ERROR)); - YYABORT; - } - Select->options|= SELECT_DISTINCT; - } + | DISTINCT { Select->options|= SELECT_DISTINCT; } | SQL_SMALL_RESULT { Select->options|= SELECT_SMALL_RESULT; } | SQL_BIG_RESULT { Select->options|= SELECT_BIG_RESULT; } | SQL_BUFFER_RESULT @@ -4028,15 +4027,7 @@ select_option: { Lex->select_lex.options|= OPTION_TO_QUERY_CACHE; } - | ALL - { - if (Select->options & SELECT_DISTINCT) - { - yyerror(ER(ER_SYNTAX_ERROR)); - YYABORT; - } - Select->options|= SELECT_ALL; - } + | ALL { Select->options|= SELECT_ALL; } ; select_lock_type: diff --git a/sql/unireg.cc b/sql/unireg.cc index 00fc80a25fe..da463885f85 100644 --- a/sql/unireg.cc +++ b/sql/unireg.cc @@ -32,18 +32,20 @@ static uchar * pack_screens(List<create_field> &create_fields, uint *info_length, uint *screens, bool small_file); -static uint pack_keys(uchar *keybuff,uint key_count, KEY *key_info); +static uint pack_keys(uchar *keybuff,uint key_count, KEY *key_info, + ulong data_offset); static bool pack_header(uchar *forminfo,enum db_type table_type, List<create_field> &create_fields, uint info_length, uint screens, uint table_options, - handler *file); + ulong data_offset, handler *file); static uint get_interval_id(uint *int_count,List<create_field> &create_fields, create_field *last_field); -static bool pack_fields(File file, List<create_field> &create_fields); +static bool pack_fields(File file, List<create_field> &create_fields, + ulong data_offset); static bool make_empty_rec(THD *thd, int file, enum db_type table_type, uint table_options, List<create_field> &create_fields, - uint reclength,uint null_fields); + uint reclength, ulong data_offset); /* Create a frm (table definition) file @@ -69,9 +71,9 @@ bool mysql_create_frm(THD *thd, my_string file_name, uint keys, KEY *key_info, handler *db_file) { - uint reclength,info_length,screens,key_info_length,maxlength,null_fields; + uint reclength,info_length,screens,key_info_length,maxlength; File file; - ulong filepos; + ulong filepos, data_offset; uchar fileinfo[64],forminfo[288],*keybuff; TYPELIB formnames; uchar *screen_buff; @@ -81,9 +83,16 @@ bool mysql_create_frm(THD *thd, my_string file_name, if (!(screen_buff=pack_screens(create_fields,&info_length,&screens,0))) DBUG_RETURN(1); if (db_file == NULL) - db_file=get_new_handler((TABLE*) 0, create_info->db_type); + db_file= get_new_handler((TABLE*) 0, create_info->db_type); + + /* If fixed row records, we need one bit to check for deleted rows */ + if (!(create_info->table_options & HA_OPTION_PACK_RECORD)) + create_info->null_bits++; + data_offset= (create_info->null_bits + 7) / 8; + if (pack_header(forminfo, create_info->db_type,create_fields,info_length, - screens, create_info->table_options, db_file)) + screens, create_info->table_options, + data_offset, db_file)) { my_free((gptr) screen_buff,MYF(0)); if (thd->net.last_errno != ER_TOO_MANY_FIELDS) @@ -94,14 +103,13 @@ bool mysql_create_frm(THD *thd, my_string file_name, if (!(screen_buff=pack_screens(create_fields,&info_length,&screens,1))) DBUG_RETURN(1); if (pack_header(forminfo, create_info->db_type, create_fields,info_length, - screens, create_info->table_options, db_file)) + screens, create_info->table_options, data_offset, db_file)) { my_free((gptr) screen_buff,MYF(0)); DBUG_RETURN(1); } } reclength=uint2korr(forminfo+266); - null_fields=uint2korr(forminfo+282); if ((file=create_frm(file_name, reclength, fileinfo, create_info, keys)) < 0) @@ -112,7 +120,7 @@ bool mysql_create_frm(THD *thd, my_string file_name, uint key_buff_length=keys*(7+NAME_LEN+MAX_REF_PARTS*9)+16; keybuff=(uchar*) my_malloc(key_buff_length, MYF(0)); - key_info_length=pack_keys(keybuff,keys,key_info); + key_info_length= pack_keys(keybuff, keys, key_info, data_offset); VOID(get_form_pos(file,fileinfo,&formnames)); if (!(filepos=make_new_entry(file,fileinfo,&formnames,""))) goto err; @@ -135,13 +143,13 @@ bool mysql_create_frm(THD *thd, my_string file_name, (ulong) uint2korr(fileinfo+6)+ (ulong) key_buff_length, MY_SEEK_SET,MYF(0))); if (make_empty_rec(thd,file,create_info->db_type,create_info->table_options, - create_fields,reclength,null_fields)) + create_fields,reclength, data_offset)) goto err; VOID(my_seek(file,filepos,MY_SEEK_SET,MYF(0))); if (my_write(file,(byte*) forminfo,288,MYF_RW) || my_write(file,(byte*) screen_buff,info_length,MYF_RW) || - pack_fields(file,create_fields)) + pack_fields(file, create_fields, data_offset)) goto err; #ifdef HAVE_CRYPTED_FRM @@ -313,7 +321,8 @@ static uchar * pack_screens(List<create_field> &create_fields, /* Pack keyinfo and keynames to keybuff for save in form-file. */ -static uint pack_keys(uchar *keybuff,uint key_count,KEY *keyinfo) +static uint pack_keys(uchar *keybuff, uint key_count, KEY *keyinfo, + ulong data_offset) { uint key_parts,length; uchar *pos, *keyname_pos; @@ -340,10 +349,13 @@ static uint pack_keys(uchar *keybuff,uint key_count,KEY *keyinfo) key_part++) { - DBUG_PRINT("loop",("field: %d startpos: %ld length: %ld", - key_part->fieldnr,key_part->offset,key_part->length)); + uint offset; + DBUG_PRINT("loop",("field: %d startpos: %lu length: %ld", + key_part->fieldnr, key_part->offset + data_offset, + key_part->length)); int2store(pos,key_part->fieldnr+1+FIELD_NAME_USED); - int2store(pos+2,key_part->offset+1); + offset= (uint) (key_part->offset+data_offset+1); + int2store(pos+2, offset); pos[4]=0; // Sort order int2store(pos+5,key_part->key_type); int2store(pos+7,key_part->length); @@ -384,8 +396,8 @@ static uint pack_keys(uchar *keybuff,uint key_count,KEY *keyinfo) static bool pack_header(uchar *forminfo, enum db_type table_type, List<create_field> &create_fields, - uint info_length, uint screens,uint table_options, - handler *file) + uint info_length, uint screens, uint table_options, + ulong data_offset, handler *file) { uint length,int_count,int_length,no_empty, int_parts; uint time_stamp_pos,null_fields; @@ -425,10 +437,10 @@ static bool pack_header(uchar *forminfo, enum db_type table_type, if (field->sql_type == FIELD_TYPE_TIMESTAMP && MTYP_TYPENR(field->unireg_check) != Field::NONE && !time_stamp_pos) - time_stamp_pos=(int) field->offset+1; + time_stamp_pos= (uint) field->offset+ (uint) data_offset + 1; length=field->pack_length; - if ((int) field->offset+length > reclength) - reclength=(int) field->offset+length; + if ((uint) field->offset+ (uint) data_offset+ length > reclength) + reclength=(uint) (field->offset+ data_offset + length); n_length+= (ulong) strlen(field->field_name)+1; field->interval_id=0; if (field->interval) @@ -539,7 +551,8 @@ static uint get_interval_id(uint *int_count,List<create_field> &create_fields, /* Save fields, fieldnames and intervals */ -static bool pack_fields(File file,List<create_field> &create_fields) +static bool pack_fields(File file, List<create_field> &create_fields, + ulong data_offset) { reg2 uint i; uint int_count, comment_length=0; @@ -554,11 +567,13 @@ static bool pack_fields(File file,List<create_field> &create_fields) int_count=0; while ((field=it++)) { + uint recpos; buff[0]= (uchar) field->row; buff[1]= (uchar) field->col; buff[2]= (uchar) field->sc_length; int2store(buff+3, field->length); - uint recpos=(uint) field->offset+1; + /* The +1 is here becasue the col offset in .frm file have offset 1 */ + recpos= field->offset+1 + (uint) data_offset; int3store(buff+5,recpos); int2store(buff+8,field->pack_flag); int2store(buff+10,field->unireg_check); @@ -644,11 +659,12 @@ static bool pack_fields(File file,List<create_field> &create_fields) static bool make_empty_rec(THD *thd, File file,enum db_type table_type, uint table_options, List<create_field> &create_fields, - uint reclength, uint null_fields) + uint reclength, + ulong data_offset) { int error; Field::utype type; - uint null_count; + uint firstpos, null_count; uchar *buff,*null_pos; TABLE table; create_field *field; @@ -675,8 +691,7 @@ static bool make_empty_rec(THD *thd, File file,enum db_type table_type, null_count=0; if (!(table_options & HA_OPTION_PACK_RECORD)) { - null_fields++; // Need one bit for delete mark - null_count++; + null_count++; // Need one bit for delete mark *buff|= 1; } null_pos= buff; @@ -688,7 +703,8 @@ static bool make_empty_rec(THD *thd, File file,enum db_type table_type, /* regfield don't have to be deleted as it's allocated with sql_alloc() */ - Field *regfield=make_field((char*) buff+field->offset,field->length, + Field *regfield=make_field((char*) buff+field->offset + data_offset, + field->length, null_pos + null_count / 8, null_count & 7, field->pack_flag, @@ -737,12 +753,13 @@ static bool make_empty_rec(THD *thd, File file,enum db_type table_type, else regfield->reset(); } + DBUG_ASSERT(data_offset == ((null_count + 7) / 8)); /* Fill not used startpos */ if (null_count) *(null_pos + null_count / 8)|= ~(((uchar) 1 << (null_count & 7)) - 1); - error=(int) my_write(file,(byte*) buff,(uint) reclength,MYF_RW); + error=(int) my_write(file,(byte*) buff, (uint) reclength,MYF_RW); err: my_free((gptr) buff,MYF(MY_FAE)); |