mirror of
https://github.com/MariaDB/server.git
synced 2025-08-08 11:22:35 +03:00
Bug#27836
"sql_plugin.cc, dynamic_array is not dynamic" When the DYNAMIC_ARRAYs were resized, pointers became invalid. Solved by only storing pointers within the DYNAMIC_ARRAYs.
This commit is contained in:
@@ -278,7 +278,7 @@ static struct st_plugin_dl *plugin_dl_find(const LEX_STRING *dl)
|
|||||||
DBUG_ENTER("plugin_dl_find");
|
DBUG_ENTER("plugin_dl_find");
|
||||||
for (i= 0; i < plugin_dl_array.elements; i++)
|
for (i= 0; i < plugin_dl_array.elements; i++)
|
||||||
{
|
{
|
||||||
tmp= dynamic_element(&plugin_dl_array, i, struct st_plugin_dl *);
|
tmp= *dynamic_element(&plugin_dl_array, i, struct st_plugin_dl **);
|
||||||
if (tmp->ref_count &&
|
if (tmp->ref_count &&
|
||||||
! my_strnncoll(files_charset_info,
|
! my_strnncoll(files_charset_info,
|
||||||
(const uchar *)dl->str, dl->length,
|
(const uchar *)dl->str, dl->length,
|
||||||
@@ -296,17 +296,20 @@ static st_plugin_dl *plugin_dl_insert_or_reuse(struct st_plugin_dl *plugin_dl)
|
|||||||
DBUG_ENTER("plugin_dl_insert_or_reuse");
|
DBUG_ENTER("plugin_dl_insert_or_reuse");
|
||||||
for (i= 0; i < plugin_dl_array.elements; i++)
|
for (i= 0; i < plugin_dl_array.elements; i++)
|
||||||
{
|
{
|
||||||
tmp= dynamic_element(&plugin_dl_array, i, struct st_plugin_dl *);
|
tmp= *dynamic_element(&plugin_dl_array, i, struct st_plugin_dl **);
|
||||||
if (! tmp->ref_count)
|
if (! tmp->ref_count)
|
||||||
{
|
{
|
||||||
memcpy(tmp, plugin_dl, sizeof(struct st_plugin_dl));
|
memcpy(tmp, plugin_dl, sizeof(struct st_plugin_dl));
|
||||||
DBUG_RETURN(tmp);
|
DBUG_RETURN(tmp);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (insert_dynamic(&plugin_dl_array, (gptr)plugin_dl))
|
if (insert_dynamic(&plugin_dl_array, (gptr)&plugin_dl))
|
||||||
DBUG_RETURN(0);
|
DBUG_RETURN(0);
|
||||||
DBUG_RETURN(dynamic_element(&plugin_dl_array, plugin_dl_array.elements - 1,
|
tmp= *dynamic_element(&plugin_dl_array, plugin_dl_array.elements - 1,
|
||||||
struct st_plugin_dl *));
|
struct st_plugin_dl **)=
|
||||||
|
(struct st_plugin_dl *) memdup_root(&plugin_mem_root, (gptr)plugin_dl,
|
||||||
|
sizeof(struct st_plugin_dl));
|
||||||
|
DBUG_RETURN(tmp);
|
||||||
}
|
}
|
||||||
#endif /* HAVE_DLOPEN */
|
#endif /* HAVE_DLOPEN */
|
||||||
|
|
||||||
@@ -516,8 +519,8 @@ static void plugin_dl_del(const LEX_STRING *dl)
|
|||||||
|
|
||||||
for (i= 0; i < plugin_dl_array.elements; i++)
|
for (i= 0; i < plugin_dl_array.elements; i++)
|
||||||
{
|
{
|
||||||
struct st_plugin_dl *tmp= dynamic_element(&plugin_dl_array, i,
|
struct st_plugin_dl *tmp= *dynamic_element(&plugin_dl_array, i,
|
||||||
struct st_plugin_dl *);
|
struct st_plugin_dl **);
|
||||||
if (tmp->ref_count &&
|
if (tmp->ref_count &&
|
||||||
! my_strnncoll(files_charset_info,
|
! my_strnncoll(files_charset_info,
|
||||||
(const uchar *)dl->str, dl->length,
|
(const uchar *)dl->str, dl->length,
|
||||||
@@ -665,21 +668,24 @@ plugin_ref plugin_lock_by_name(THD *thd, const LEX_STRING *name, int type
|
|||||||
static st_plugin_int *plugin_insert_or_reuse(struct st_plugin_int *plugin)
|
static st_plugin_int *plugin_insert_or_reuse(struct st_plugin_int *plugin)
|
||||||
{
|
{
|
||||||
uint i;
|
uint i;
|
||||||
|
struct st_plugin_int *tmp;
|
||||||
DBUG_ENTER("plugin_insert_or_reuse");
|
DBUG_ENTER("plugin_insert_or_reuse");
|
||||||
for (i= 0; i < plugin_array.elements; i++)
|
for (i= 0; i < plugin_array.elements; i++)
|
||||||
{
|
{
|
||||||
struct st_plugin_int *tmp= dynamic_element(&plugin_array, i,
|
tmp= *dynamic_element(&plugin_array, i, struct st_plugin_int **);
|
||||||
struct st_plugin_int *);
|
|
||||||
if (tmp->state == PLUGIN_IS_FREED)
|
if (tmp->state == PLUGIN_IS_FREED)
|
||||||
{
|
{
|
||||||
memcpy(tmp, plugin, sizeof(struct st_plugin_int));
|
memcpy(tmp, plugin, sizeof(struct st_plugin_int));
|
||||||
DBUG_RETURN(tmp);
|
DBUG_RETURN(tmp);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (insert_dynamic(&plugin_array, (gptr)plugin))
|
if (insert_dynamic(&plugin_array, (gptr)&plugin))
|
||||||
DBUG_RETURN(0);
|
DBUG_RETURN(0);
|
||||||
DBUG_RETURN(dynamic_element(&plugin_array, plugin_array.elements - 1,
|
tmp= *dynamic_element(&plugin_array, plugin_array.elements - 1,
|
||||||
struct st_plugin_int *));
|
struct st_plugin_int **)=
|
||||||
|
(struct st_plugin_int *) memdup_root(&plugin_mem_root, (gptr)plugin,
|
||||||
|
sizeof(struct st_plugin_int));
|
||||||
|
DBUG_RETURN(tmp);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -874,7 +880,7 @@ static void reap_plugins(void)
|
|||||||
|
|
||||||
for (idx= 0; idx < count; idx++)
|
for (idx= 0; idx < count; idx++)
|
||||||
{
|
{
|
||||||
plugin= dynamic_element(&plugin_array, idx, struct st_plugin_int *);
|
plugin= *dynamic_element(&plugin_array, idx, struct st_plugin_int **);
|
||||||
if (plugin->state == PLUGIN_IS_DELETED && !plugin->ref_count)
|
if (plugin->state == PLUGIN_IS_DELETED && !plugin->ref_count)
|
||||||
{
|
{
|
||||||
/* change the status flag to prevent reaping by another thread */
|
/* change the status flag to prevent reaping by another thread */
|
||||||
@@ -1097,9 +1103,9 @@ int plugin_init(int *argc, char **argv, int flags)
|
|||||||
pthread_mutex_init(&LOCK_plugin, MY_MUTEX_INIT_FAST);
|
pthread_mutex_init(&LOCK_plugin, MY_MUTEX_INIT_FAST);
|
||||||
|
|
||||||
if (my_init_dynamic_array(&plugin_dl_array,
|
if (my_init_dynamic_array(&plugin_dl_array,
|
||||||
sizeof(struct st_plugin_dl),16,16) ||
|
sizeof(struct st_plugin_dl *),16,16) ||
|
||||||
my_init_dynamic_array(&plugin_array,
|
my_init_dynamic_array(&plugin_array,
|
||||||
sizeof(struct st_plugin_int),16,16))
|
sizeof(struct st_plugin_int *),16,16))
|
||||||
goto err;
|
goto err;
|
||||||
|
|
||||||
for (i= 0; i < MYSQL_MAX_PLUGIN_TYPE_NUM; i++)
|
for (i= 0; i < MYSQL_MAX_PLUGIN_TYPE_NUM; i++)
|
||||||
@@ -1185,7 +1191,7 @@ int plugin_init(int *argc, char **argv, int flags)
|
|||||||
|
|
||||||
for (i= 0; i < plugin_array.elements; i++)
|
for (i= 0; i < plugin_array.elements; i++)
|
||||||
{
|
{
|
||||||
plugin_ptr= dynamic_element(&plugin_array, i, struct st_plugin_int *);
|
plugin_ptr= *dynamic_element(&plugin_array, i, struct st_plugin_int **);
|
||||||
if (plugin_ptr->state == PLUGIN_IS_UNINITIALIZED)
|
if (plugin_ptr->state == PLUGIN_IS_UNINITIALIZED)
|
||||||
{
|
{
|
||||||
if (plugin_initialize(plugin_ptr))
|
if (plugin_initialize(plugin_ptr))
|
||||||
@@ -1232,11 +1238,13 @@ static bool register_builtin(struct st_mysql_plugin *plugin,
|
|||||||
tmp->ref_count= 0;
|
tmp->ref_count= 0;
|
||||||
tmp->plugin_dl= 0;
|
tmp->plugin_dl= 0;
|
||||||
|
|
||||||
if (insert_dynamic(&plugin_array, (gptr)tmp))
|
if (insert_dynamic(&plugin_array, (gptr)&tmp))
|
||||||
DBUG_RETURN(1);
|
DBUG_RETURN(1);
|
||||||
|
|
||||||
*ptr= dynamic_element(&plugin_array, plugin_array.elements - 1,
|
*ptr= *dynamic_element(&plugin_array, plugin_array.elements - 1,
|
||||||
struct st_plugin_int *);
|
struct st_plugin_int **)=
|
||||||
|
(struct st_plugin_int *) memdup_root(&plugin_mem_root, (gptr)tmp,
|
||||||
|
sizeof(struct st_plugin_int));
|
||||||
|
|
||||||
if (my_hash_insert(&plugin_hash[plugin->type],(byte*) *ptr))
|
if (my_hash_insert(&plugin_hash[plugin->type],(byte*) *ptr))
|
||||||
DBUG_RETURN(1);
|
DBUG_RETURN(1);
|
||||||
@@ -1458,7 +1466,7 @@ void plugin_shutdown(void)
|
|||||||
reap_plugins();
|
reap_plugins();
|
||||||
for (i= free_slots= 0; i < count; i++)
|
for (i= free_slots= 0; i < count; i++)
|
||||||
{
|
{
|
||||||
plugin= dynamic_element(&plugin_array, i, struct st_plugin_int *);
|
plugin= *dynamic_element(&plugin_array, i, struct st_plugin_int **);
|
||||||
switch (plugin->state) {
|
switch (plugin->state) {
|
||||||
case PLUGIN_IS_READY:
|
case PLUGIN_IS_READY:
|
||||||
plugin->state= PLUGIN_IS_DELETED;
|
plugin->state= PLUGIN_IS_DELETED;
|
||||||
@@ -1490,7 +1498,7 @@ void plugin_shutdown(void)
|
|||||||
*/
|
*/
|
||||||
for (i= 0; i < count; i++)
|
for (i= 0; i < count; i++)
|
||||||
{
|
{
|
||||||
plugins[i]= dynamic_element(&plugin_array, i, struct st_plugin_int *);
|
plugins[i]= *dynamic_element(&plugin_array, i, struct st_plugin_int **);
|
||||||
/* change the state to ensure no reaping races */
|
/* change the state to ensure no reaping races */
|
||||||
if (plugins[i]->state == PLUGIN_IS_DELETED)
|
if (plugins[i]->state == PLUGIN_IS_DELETED)
|
||||||
plugins[i]->state= PLUGIN_IS_DYING;
|
plugins[i]->state= PLUGIN_IS_DYING;
|
||||||
@@ -1555,7 +1563,7 @@ void plugin_shutdown(void)
|
|||||||
count= plugin_dl_array.elements;
|
count= plugin_dl_array.elements;
|
||||||
dl= (struct st_plugin_dl **)my_alloca(sizeof(void*) * count);
|
dl= (struct st_plugin_dl **)my_alloca(sizeof(void*) * count);
|
||||||
for (i= 0; i < count; i++)
|
for (i= 0; i < count; i++)
|
||||||
dl[i]= dynamic_element(&plugin_dl_array, i, struct st_plugin_dl *);
|
dl[i]= *dynamic_element(&plugin_dl_array, i, struct st_plugin_dl **);
|
||||||
for (i= 0; i < plugin_dl_array.elements; i++)
|
for (i= 0; i < plugin_dl_array.elements; i++)
|
||||||
free_plugin_mem(dl[i]);
|
free_plugin_mem(dl[i]);
|
||||||
my_afree(dl);
|
my_afree(dl);
|
||||||
@@ -1714,7 +1722,7 @@ bool plugin_foreach_with_mask(THD *thd, plugin_foreach_func *func,
|
|||||||
{
|
{
|
||||||
for (idx= 0; idx < total; idx++)
|
for (idx= 0; idx < total; idx++)
|
||||||
{
|
{
|
||||||
plugin= dynamic_element(&plugin_array, idx, struct st_plugin_int *);
|
plugin= *dynamic_element(&plugin_array, idx, struct st_plugin_int **);
|
||||||
plugins[idx]= !(plugin->state & state_mask) ? plugin : NULL;
|
plugins[idx]= !(plugin->state & state_mask) ? plugin : NULL;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -3139,7 +3147,7 @@ void my_print_help_inc_plugins(my_option *main_options, uint size)
|
|||||||
if (initialized)
|
if (initialized)
|
||||||
for (uint idx= 0; idx < plugin_array.elements; idx++)
|
for (uint idx= 0; idx < plugin_array.elements; idx++)
|
||||||
{
|
{
|
||||||
p= dynamic_element(&plugin_array, idx, struct st_plugin_int *);
|
p= *dynamic_element(&plugin_array, idx, struct st_plugin_int **);
|
||||||
|
|
||||||
if (!p->plugin->system_vars ||
|
if (!p->plugin->system_vars ||
|
||||||
!(opt= construct_help_options(&mem_root, p)))
|
!(opt= construct_help_options(&mem_root, p)))
|
||||||
|
Reference in New Issue
Block a user