mirror of
https://github.com/MariaDB/server.git
synced 2025-08-01 03:47:19 +03:00
Fixed stack overrun with some INSERT ... SELECT ... GROUP BY queries (Bug #3265)
Ensure that raid_chunks is not set to higher than 255 as this could cause problems with DROP DATABASE. (Bug #3182)
This commit is contained in:
@ -2,6 +2,14 @@ create database test_raid;
|
||||
create table test_raid.r1 (i int) raid_type=1;
|
||||
create table test_raid.r2 (i int) raid_type=1 raid_chunks=32;
|
||||
drop database test_raid;
|
||||
create database test_raid;
|
||||
create table test_raid.r2 (i int) raid_type=1 raid_chunks=257;
|
||||
show create table test_raid.r2;
|
||||
Table Create Table
|
||||
r2 CREATE TABLE `r2` (
|
||||
`i` int(11) default NULL
|
||||
) TYPE=MyISAM RAID_TYPE=striped RAID_CHUNKS=255 RAID_CHUNKSIZE=256
|
||||
drop database test_raid;
|
||||
DROP TABLE IF EXISTS t1,t2;
|
||||
CREATE TABLE t1 (
|
||||
id int unsigned not null auto_increment primary key,
|
||||
|
@ -11,6 +11,15 @@ create database test_raid;
|
||||
create table test_raid.r1 (i int) raid_type=1;
|
||||
create table test_raid.r2 (i int) raid_type=1 raid_chunks=32;
|
||||
drop database test_raid;
|
||||
|
||||
#
|
||||
# Bug #3182: Test using more than 257 raid chunks
|
||||
#
|
||||
create database test_raid;
|
||||
create table test_raid.r2 (i int) raid_type=1 raid_chunks=257;
|
||||
show create table test_raid.r2;
|
||||
drop database test_raid;
|
||||
|
||||
DROP TABLE IF EXISTS t1,t2;
|
||||
CREATE TABLE t1 (
|
||||
id int unsigned not null auto_increment primary key,
|
||||
|
12
sql/item.cc
12
sql/item.cc
@ -322,6 +322,15 @@ String *Item_copy_string::val_str(String *str)
|
||||
return &str_value;
|
||||
}
|
||||
|
||||
bool Item_copy_string::save_in_field(Field *field, bool no_conversions)
|
||||
{
|
||||
if (null_value)
|
||||
return set_field_to_null(field);
|
||||
field->set_notnull();
|
||||
field->store(str_value.ptr(), str_value.length());
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
** Functions to convert item to field (for send_fields)
|
||||
*/
|
||||
@ -520,7 +529,10 @@ bool Item::save_in_field(Field *field, bool no_conversions)
|
||||
str_value.set_quick(buff,sizeof(buff));
|
||||
result=val_str(&str_value);
|
||||
if (null_value)
|
||||
{
|
||||
str_value.set_quick(0, 0);
|
||||
return set_field_to_null_with_conversions(field, no_conversions);
|
||||
}
|
||||
field->set_notnull();
|
||||
field->store(result->ptr(),result->length());
|
||||
str_value.set_quick(0, 0);
|
||||
|
@ -499,6 +499,7 @@ public:
|
||||
String *val_str(String*);
|
||||
void make_field(Send_field *field) { item->make_field(field); }
|
||||
void copy();
|
||||
bool save_in_field(Field *field, bool no_conversions);
|
||||
table_map used_tables() const { return (table_map) 1L; }
|
||||
bool const_item() const { return 0; }
|
||||
bool is_null() { return null_value; }
|
||||
|
@ -391,6 +391,7 @@ int write_record(TABLE *table,COPY_INFO *info)
|
||||
{
|
||||
int error;
|
||||
char *key=0;
|
||||
DBUG_ENTER("write_record");
|
||||
|
||||
info->records++;
|
||||
if (info->handle_duplicates == DUP_REPLACE)
|
||||
@ -474,14 +475,14 @@ int write_record(TABLE *table,COPY_INFO *info)
|
||||
info->copied++;
|
||||
if (key)
|
||||
my_safe_afree(key,table->max_unique_length,MAX_KEY_LENGTH);
|
||||
return 0;
|
||||
DBUG_RETURN(0);
|
||||
|
||||
err:
|
||||
if (key)
|
||||
my_afree(key);
|
||||
info->last_errno= error;
|
||||
table->file->print_error(error,MYF(0));
|
||||
return 1;
|
||||
DBUG_RETURN(1);
|
||||
}
|
||||
|
||||
|
||||
@ -1342,24 +1343,25 @@ select_insert::~select_insert()
|
||||
|
||||
bool select_insert::send_data(List<Item> &values)
|
||||
{
|
||||
DBUG_ENTER("select_insert::send_data");
|
||||
if (thd->offset_limit)
|
||||
{ // using limit offset,count
|
||||
thd->offset_limit--;
|
||||
return 0;
|
||||
DBUG_RETURN(0);
|
||||
}
|
||||
if (fields->elements)
|
||||
fill_record(*fields, values, 1);
|
||||
else
|
||||
fill_record(table->field, values, 1);
|
||||
if (write_record(table,&info))
|
||||
return 1;
|
||||
DBUG_RETURN(1);
|
||||
if (table->next_number_field) // Clear for next record
|
||||
{
|
||||
table->next_number_field->reset();
|
||||
if (! last_insert_id && thd->insert_id_used)
|
||||
last_insert_id=thd->insert_id();
|
||||
}
|
||||
return 0;
|
||||
DBUG_RETURN(0);
|
||||
}
|
||||
|
||||
|
||||
|
@ -1040,6 +1040,11 @@ File create_frm(register my_string name, uint reclength, uchar *fileinfo,
|
||||
if (create_info->min_rows > ~(ulong) 0)
|
||||
create_info->min_rows= ~(ulong) 0;
|
||||
#endif
|
||||
/*
|
||||
Ensure that raid_chunks can't be larger than 255, as this would cause
|
||||
problems with drop database
|
||||
*/
|
||||
set_if_smaller(create_info->raid_chunks, 255);
|
||||
|
||||
if ((file=my_create(name,CREATE_MODE,O_RDWR | O_TRUNC,MYF(MY_WME))) >= 0)
|
||||
{
|
||||
|
Reference in New Issue
Block a user