diff options
Diffstat (limited to 'libmysql')
-rw-r--r-- | libmysql/libmysql.c | 109 | ||||
-rw-r--r-- | libmysql/libmysql.def | 2 |
2 files changed, 82 insertions, 29 deletions
diff --git a/libmysql/libmysql.c b/libmysql/libmysql.c index 455e5cc4118..bbff4e7a8d8 100644 --- a/libmysql/libmysql.c +++ b/libmysql/libmysql.c @@ -2132,17 +2132,6 @@ mysql_stmt_param_metadata(MYSQL_STMT *stmt) Prepare-execute, and param handling *********************************************************************/ -/* - Store the buffer type -*/ - -static void store_param_type(NET *net, uint type) -{ - int2store(net->write_pos, type); - net->write_pos+=2; -} - - /**************************************************************************** Functions to store parameter data from a prepared statement. @@ -2390,7 +2379,11 @@ int cli_stmt_execute(MYSQL_STMT *stmt) that is sent to the server. */ for (param= stmt->params; param < param_end ; param++) - store_param_type(net, (uint) param->buffer_type); + { + uint typecode= param->buffer_type | (param->is_unsigned ? 32768 : 0); + int2store(net->write_pos, typecode); + net->write_pos+= 2; + } } for (param= stmt->params; param < param_end; param++) @@ -2515,6 +2508,56 @@ stmt_read_row_no_data(MYSQL_STMT *stmt __attribute__((unused)), return MYSQL_NO_DATA; } + +/* + Get/set statement attributes + + SYNOPSIS + mysql_stmt_attr_get() + mysql_stmt_attr_set() + + attr_type statemenet attribute + value casted to const void * pointer to value. + + RETURN VALUE + 0 success + !0 wrong attribute type +*/ + +my_bool STDCALL mysql_stmt_attr_set(MYSQL_STMT *stmt, + enum enum_stmt_attr_type attr_type, + const void *value) +{ + switch (attr_type) { + case STMT_ATTR_UPDATE_MAX_LENGTH: + /* + Do we need a flags variable for all attributes or a bool for each + attribute? + */ + stmt->update_max_length= value ? *(const my_bool*) value : 0; + break; + default: + return TRUE; + } + return FALSE; +} + + +my_bool STDCALL mysql_stmt_attr_get(MYSQL_STMT *stmt, + enum enum_stmt_attr_type attr_type, + void *value) +{ + switch (attr_type) { + case STMT_ATTR_UPDATE_MAX_LENGTH: + *(unsigned long *) value= stmt->update_max_length; + break; + default: + return TRUE; + } + return FALSE; +} + + /* Execute the prepared query */ @@ -3218,28 +3261,28 @@ static void fetch_results(MYSQL_BIND *param, MYSQL_FIELD *field, uchar **row) static void fetch_result_tinyint(MYSQL_BIND *param, uchar **row) { - *param->buffer= (uchar) **row; + *param->buffer= **row; (*row)++; } static void fetch_result_short(MYSQL_BIND *param, uchar **row) { short value = (short)sint2korr(*row); - int2store(param->buffer, value); + shortstore(param->buffer, value); *row+= 2; } static void fetch_result_int32(MYSQL_BIND *param, uchar **row) { int32 value= (int32)sint4korr(*row); - int4store(param->buffer, value); + longstore(param->buffer, value); *row+= 4; } static void fetch_result_int64(MYSQL_BIND *param, uchar **row) { longlong value= (longlong)sint8korr(*row); - int8store(param->buffer, value); + longlongstore(param->buffer, value); *row+= 8; } @@ -3247,7 +3290,7 @@ static void fetch_result_float(MYSQL_BIND *param, uchar **row) { float value; float4get(value,*row); - float4store(param->buffer, value); + floatstore(param->buffer, value); *row+= 4; } @@ -3255,7 +3298,7 @@ static void fetch_result_double(MYSQL_BIND *param, uchar **row) { double value; float8get(value,*row); - float8store(param->buffer, value); + doublestore(param->buffer, value); *row+= 8; } @@ -3364,8 +3407,7 @@ my_bool STDCALL mysql_stmt_bind_result(MYSQL_STMT *stmt, MYSQL_BIND *bind) stmt->bind was initialized in mysql_stmt_prepare */ - memcpy((char*) stmt->bind, (char*) bind, - sizeof(MYSQL_BIND)*bind_count); + memcpy((char*) stmt->bind, (char*) bind, sizeof(MYSQL_BIND) * bind_count); for (param= stmt->bind, end= param + bind_count, field= stmt->fields ; param < end ; @@ -3537,10 +3579,20 @@ static int stmt_fetch_row(MYSQL_STMT *stmt, uchar *row) bind++, field++) { if (*null_ptr & bit) - *bind->is_null= bind->null_field= 1; + { + /* + We should set both inter_buffer and is_null to be able to see + nulls in mysql_stmt_fetch_column. This is because is_null may point + to user data which can be overwritten between mysql_stmt_fetch and + mysql_stmt_fetch_column, and in this case nullness of column will be + lost. See mysql_stmt_fetch_column for details. + */ + bind->inter_buffer= NULL; + *bind->is_null= 1; + } else { - *bind->is_null= bind->null_field= 0; + *bind->is_null= 0; bind->inter_buffer= row; if (field->type == bind->buffer_type) (*bind->fetch_result)(bind, &row); @@ -3626,14 +3678,8 @@ int STDCALL mysql_stmt_fetch_column(MYSQL_STMT *stmt, MYSQL_BIND *bind, DBUG_RETURN(1); } - - if (param->null_field) + if (param->inter_buffer) { - if (bind->is_null) - *bind->is_null= 1; - } - else - { MYSQL_FIELD *field= stmt->fields+column; uchar *row= param->inter_buffer; bind->offset= offset; @@ -3645,6 +3691,11 @@ int STDCALL mysql_stmt_fetch_column(MYSQL_STMT *stmt, MYSQL_BIND *bind, bind->length= ¶m->internal_length; /* Needed for fetch_result() */ fetch_results(bind, field, &row); } + else + { + if (bind->is_null) + *bind->is_null= 1; + } DBUG_RETURN(0); } diff --git a/libmysql/libmysql.def b/libmysql/libmysql.def index 4f6347776e0..1790b0fa888 100644 --- a/libmysql/libmysql.def +++ b/libmysql/libmysql.def @@ -127,3 +127,5 @@ EXPORTS mysql_stmt_prepare mysql_stmt_init mysql_stmt_insert_id + mysql_stmt_attr_get + mysql_stmt_attr_set |