~drizzle-trunk/drizzle/development

1 by brian
clean slate
1
/* Copyright (C) 2005 MySQL AB
2
3
   This program is free software; you can redistribute it and/or modify
4
   it under the terms of the GNU General Public License as published by
5
   the Free Software Foundation; version 2 of the License.
6
7
   This program is distributed in the hope that it will be useful,
8
   but WITHOUT ANY WARRANTY; without even the implied warranty of
9
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
10
   GNU General Public License for more details.
11
12
   You should have received a copy of the GNU General Public License
13
   along with this program; if not, write to the Free Software
14
   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */
15
243.1.17 by Jay Pipes
FINAL PHASE removal of mysql_priv.h (Bye, bye my friend.)
16
#include <drizzled/server_includes.h>
212.5.21 by Monty Taylor
Moved my_getopt.h
17
#include <mysys/my_getopt.h>
584.1.15 by Monty Taylor
The mega-patch from hell. Renamed sql_class to session (since that's what it is) and removed it and field and table from common_includes.
18
#include <mysys/hash.h>
499.2.9 by Mark Atwood
fix mistakes
19
549 by Monty Taylor
Took gettext.h out of header files.
20
#include <drizzled/authentication.h>
21
#include <drizzled/logging.h>
22
#include <drizzled/errmsg.h>
23
#include <drizzled/qcache.h>
520.8.2 by Monty Taylor
Moved sql_parse.h and sql_error.h out of common_includes.
24
#include <drizzled/sql_parse.h>
549 by Monty Taylor
Took gettext.h out of header files.
25
#include <drizzled/scheduling.h>
1039.5.31 by Jay Pipes
This patch does a few things:
26
#include <drizzled/replication_services.h>
575.4.7 by Monty Taylor
More header cleanup.
27
#include <drizzled/show.h>
584.1.15 by Monty Taylor
The mega-patch from hell. Renamed sql_class to session (since that's what it is) and removed it and field and table from common_includes.
28
#include <drizzled/handler.h>
29
#include <drizzled/set_var.h>
30
#include <drizzled/session.h>
642.1.20 by Lee
header file clean up
31
#include <drizzled/item/null.h>
1110.1.5 by Monty Taylor
Renamed PluginRegistry to plugin::Registry.
32
#include <drizzled/plugin/registry.h>
499.2.9 by Mark Atwood
fix mistakes
33
534 by Monty Taylor
Removed stxnmov. Also deleted strstr which had already been removed.
34
#include <string>
656.1.1 by Monty Taylor
OOOh doggie. Got rid of my_alloca.
35
#include <vector>
873.2.21 by Monty Taylor
Removed the HASH for plugin_hash.
36
#include <map>
1067.4.4 by Nathan Williams
The rest of the files in the drizzled directory were purged of the cmin macro and replace with std::min (except for the definition in globals.h and 1 usage in stacktrace.cc).
37
#include <algorithm>
534 by Monty Taylor
Removed stxnmov. Also deleted strstr which had already been removed.
38
549 by Monty Taylor
Took gettext.h out of header files.
39
#include <drizzled/error.h>
40
#include <drizzled/gettext.h>
499.2.7 by Mark Atwood
some bugs in errmsg plugin
41
1 by brian
clean slate
42
#define REPORT_TO_LOG  1
43
#define REPORT_TO_USER 2
44
534 by Monty Taylor
Removed stxnmov. Also deleted strstr which had already been removed.
45
using namespace std;
1093.3.1 by Monty Taylor
Rename of plugin classes.
46
using namespace drizzled;
992.1.39 by Monty Taylor
Removed the m4-based plugin system.
47
 
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
48
typedef plugin::Manifest builtin_plugin[];
1093.9.13 by Monty Taylor
pandora-build v0.42 - Started splitting out plugin system into pandora-build
49
extern builtin_plugin PANDORA_BUILTIN_LIST;
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
50
static plugin::Manifest *drizzled_builtins[]=
992.1.39 by Monty Taylor
Removed the m4-based plugin system.
51
{
1115.3.8 by Jay Pipes
Merge and resolve conflicts on pandora build fixes.
52
  PANDORA_BUILTIN_LIST,(plugin::Manifest *)NULL
992.1.39 by Monty Taylor
Removed the m4-based plugin system.
53
};
1101.1.27 by Monty Taylor
Fixed the plugin string valgrind leak.
54
class sys_var_pluginvar;
55
static vector<sys_var_pluginvar *> plugin_sysvar_vec;
1 by brian
clean slate
56
57
char *opt_plugin_load= NULL;
1093.9.13 by Monty Taylor
pandora-build v0.42 - Started splitting out plugin system into pandora-build
58
const char *opt_plugin_load_default= QUOTE_ARG(PANDORA_PLUGIN_LIST);
1 by brian
clean slate
59
char *opt_plugin_dir_ptr;
60
char opt_plugin_dir[FN_REFLEN];
1093.3.1 by Monty Taylor
Rename of plugin classes.
61
static const char *plugin_declarations_sym= "_drizzled_plugin_declaration_";
1 by brian
clean slate
62
63
/* Note that 'int version' must be the first field of every plugin
64
   sub-structure (plugin->info).
65
*/
66
962.1.6 by Brian Aker
Cut down on shutdown loop of plugins (cutting stuff out in order to simplify
67
static bool initialized= false;
1 by brian
clean slate
68
69
static DYNAMIC_ARRAY plugin_dl_array;
70
static DYNAMIC_ARRAY plugin_array;
908.2.1 by Monty Taylor
First pass at refactoring plugins - factored out sql_map.
71
1 by brian
clean slate
72
static bool reap_needed= false;
73
74
/*
75
  write-lock on LOCK_system_variables_hash is required before modifying
76
  the following variables/structures
77
*/
78
static MEM_ROOT plugin_mem_root;
482 by Brian Aker
Remove uint.
79
static uint32_t global_variables_dynamic_size= 0;
1 by brian
clean slate
80
static HASH bookmark_hash;
81
82
83
/*
84
  hidden part of opaque value passed to variable check functions.
85
  Used to provide a object-like structure to non C++ consumers.
86
*/
87
struct st_item_value_holder : public st_mysql_value
88
{
89
  Item *item;
90
};
91
92
93
/*
94
  stored in bookmark_hash, this structure is never removed from the
520.1.22 by Brian Aker
Second pass of thd cleanup
95
  hash and is used to mark a single offset for a session local variable
1 by brian
clean slate
96
  even if plugins have been uninstalled and reinstalled, repeatedly.
97
  This structure is allocated from plugin_mem_root.
98
99
  The key format is as follows:
100
    1 byte         - variable type code
101
    name_len bytes - variable name
102
    '\0'           - end of key
103
*/
104
struct st_bookmark
105
{
482 by Brian Aker
Remove uint.
106
  uint32_t name_len;
1 by brian
clean slate
107
  int offset;
482 by Brian Aker
Remove uint.
108
  uint32_t version;
1 by brian
clean slate
109
  char key[1];
110
};
111
112
113
/*
114
  skeleton of a plugin variable - portion of structure common to all.
115
*/
116
struct st_mysql_sys_var
117
{
319.1.1 by Grant Limberg
renamed all instances of MYSQL_ to DRIZZLE_
118
  DRIZZLE_PLUGIN_VAR_HEADER;
1 by brian
clean slate
119
};
120
121
122
/*
123
  sys_var class for access to all plugin variables visible to the user
124
*/
125
class sys_var_pluginvar: public sys_var
126
{
127
public:
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
128
  plugin::Handle *plugin;
1 by brian
clean slate
129
  struct st_mysql_sys_var *plugin_var;
130
1101.1.27 by Monty Taylor
Fixed the plugin string valgrind leak.
131
  sys_var_pluginvar(const std::string name_arg,
1 by brian
clean slate
132
                    struct st_mysql_sys_var *plugin_var_arg)
133
    :sys_var(name_arg), plugin_var(plugin_var_arg) {}
134
  sys_var_pluginvar *cast_pluginvar() { return this; }
135
  bool is_readonly() const { return plugin_var->flags & PLUGIN_VAR_READONLY; }
136
  bool check_type(enum_var_type type)
520.1.21 by Brian Aker
THD -> Session rename
137
  { return !(plugin_var->flags & PLUGIN_VAR_SessionLOCAL) && type != OPT_GLOBAL; }
1 by brian
clean slate
138
  bool check_update_type(Item_result type);
139
  SHOW_TYPE show_type();
520.1.22 by Brian Aker
Second pass of thd cleanup
140
  unsigned char* real_value_ptr(Session *session, enum_var_type type);
1 by brian
clean slate
141
  TYPELIB* plugin_var_typelib(void);
779.3.10 by Monty Taylor
Turned on -Wshadow.
142
  unsigned char* value_ptr(Session *session, enum_var_type type,
143
                           const LEX_STRING *base);
520.1.22 by Brian Aker
Second pass of thd cleanup
144
  bool check(Session *session, set_var *var);
654 by Brian Aker
Remove unused (yet more)
145
  bool check_default(enum_var_type)
77.1.46 by Monty Taylor
Finished the warnings work!
146
    { return is_readonly(); }
654 by Brian Aker
Remove unused (yet more)
147
  void set_default(Session *session, enum_var_type);
520.1.22 by Brian Aker
Second pass of thd cleanup
148
  bool update(Session *session, set_var *var);
1 by brian
clean slate
149
};
150
151
152
/* prototypes */
1110.1.5 by Monty Taylor
Renamed PluginRegistry to plugin::Registry.
153
static bool plugin_load_list(plugin::Registry &registry,
1110.1.3 by Monty Taylor
Added ListenHandler as a member of PluginRegistry.
154
                             MEM_ROOT *tmp_root, int *argc, char **argv,
1 by brian
clean slate
155
                             const char *list);
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
156
static int test_plugin_options(MEM_ROOT *, plugin::Handle *,
135 by Brian Aker
Random cleanup. Dead partition tests, pass operator in sql_plugin, mtr based
157
                               int *, char **);
1110.1.5 by Monty Taylor
Renamed PluginRegistry to plugin::Registry.
158
static bool register_builtin(plugin::Registry &registry,
1110.1.3 by Monty Taylor
Added ListenHandler as a member of PluginRegistry.
159
                             plugin::Handle *,
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
160
                             plugin::Handle **);
520.1.22 by Brian Aker
Second pass of thd cleanup
161
static void unlock_variables(Session *session, struct system_variables *vars);
162
static void cleanup_variables(Session *session, struct system_variables *vars);
1 by brian
clean slate
163
static void plugin_vars_free_values(sys_var *vars);
164
static void plugin_opt_set_limits(struct my_option *options,
165
                                  const struct st_mysql_sys_var *opt);
1110.1.5 by Monty Taylor
Renamed PluginRegistry to plugin::Registry.
166
static void reap_plugins(plugin::Registry &plugins);
1 by brian
clean slate
167
168
169
/* declared in set_var.cc */
482 by Brian Aker
Remove uint.
170
extern sys_var *intern_find_sys_var(const char *str, uint32_t length, bool no_error);
520.1.22 by Brian Aker
Second pass of thd cleanup
171
extern bool throw_bounds_warning(Session *session, bool fixed, bool unsignd,
1022.2.38 by Monty Taylor
Changed name to std::string.
172
                                 const std::string &name, int64_t val);
173
174
static bool throw_bounds_warning(Session *session, bool fixed, bool unsignd,
175
                                 const char *name, int64_t val)
176
{
177
  const std::string name_str(name);
178
  return throw_bounds_warning(session, fixed, unsignd, name_str, val);
179
}
1 by brian
clean slate
180
181
/****************************************************************************
182
  Value type thunks, allows the C world to play in the C++ world
183
****************************************************************************/
184
185
static int item_value_type(struct st_mysql_value *value)
186
{
187
  switch (((st_item_value_holder*)value)->item->result_type()) {
188
  case INT_RESULT:
319.1.1 by Grant Limberg
renamed all instances of MYSQL_ to DRIZZLE_
189
    return DRIZZLE_VALUE_TYPE_INT;
1 by brian
clean slate
190
  case REAL_RESULT:
319.1.1 by Grant Limberg
renamed all instances of MYSQL_ to DRIZZLE_
191
    return DRIZZLE_VALUE_TYPE_REAL;
1 by brian
clean slate
192
  default:
319.1.1 by Grant Limberg
renamed all instances of MYSQL_ to DRIZZLE_
193
    return DRIZZLE_VALUE_TYPE_STRING;
1 by brian
clean slate
194
  }
195
}
196
197
static const char *item_val_str(struct st_mysql_value *value,
198
                                char *buffer, int *length)
199
{
200
  String str(buffer, *length, system_charset_info), *res;
201
  if (!(res= ((st_item_value_holder*)value)->item->val_str(&str)))
202
    return NULL;
203
  *length= res->length();
204
  if (res->c_ptr_quick() == buffer)
205
    return buffer;
206
207
  /*
208
    Lets be nice and create a temporary string since the
209
    buffer was too small
210
  */
520.1.22 by Brian Aker
Second pass of thd cleanup
211
  return current_session->strmake(res->c_ptr_quick(), res->length());
1 by brian
clean slate
212
}
213
214
53.2.2 by Monty Taylor
Updated everything that needs updating to compile with -std=gnu99 -pedantic
215
static int item_val_int(struct st_mysql_value *value, int64_t *buf)
1 by brian
clean slate
216
{
217
  Item *item= ((st_item_value_holder*)value)->item;
218
  *buf= item->val_int();
219
  if (item->is_null())
220
    return 1;
221
  return 0;
222
}
223
224
225
static int item_val_real(struct st_mysql_value *value, double *buf)
226
{
227
  Item *item= ((st_item_value_holder*)value)->item;
228
  *buf= item->val_real();
229
  if (item->is_null())
230
    return 1;
231
  return 0;
232
}
233
234
235
/****************************************************************************
236
  Plugin support code
237
****************************************************************************/
238
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
239
static plugin::Library *plugin_dl_find(const LEX_STRING *dl)
1 by brian
clean slate
240
{
482 by Brian Aker
Remove uint.
241
  uint32_t i;
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
242
  plugin::Library *tmp;
681 by Brian Aker
Style cleanup
243
1 by brian
clean slate
244
  for (i= 0; i < plugin_dl_array.elements; i++)
245
  {
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
246
    tmp= *dynamic_element(&plugin_dl_array, i, plugin::Library **);
962.1.5 by Brian Aker
Remove ref_count from DLL plugin.
247
    if (! my_strnncoll(files_charset_info,
481 by Brian Aker
Remove all of uchar.
248
                       (const unsigned char *)dl->str, dl->length,
249
                       (const unsigned char *)tmp->dl.str, tmp->dl.length))
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
250
      return(tmp);
1 by brian
clean slate
251
  }
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
252
  return(0);
1 by brian
clean slate
253
}
254
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
255
static plugin::Library *plugin_dl_insert_or_reuse(plugin::Library *plugin_dl)
1 by brian
clean slate
256
{
482 by Brian Aker
Remove uint.
257
  uint32_t i;
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
258
  plugin::Library *tmp;
681 by Brian Aker
Style cleanup
259
1 by brian
clean slate
260
  for (i= 0; i < plugin_dl_array.elements; i++)
261
  {
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
262
    tmp= *dynamic_element(&plugin_dl_array, i, plugin::Library **);
1 by brian
clean slate
263
    {
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
264
      memcpy(tmp, plugin_dl, sizeof(plugin::Library));
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
265
      return(tmp);
1 by brian
clean slate
266
    }
267
  }
481 by Brian Aker
Remove all of uchar.
268
  if (insert_dynamic(&plugin_dl_array, (unsigned char*)&plugin_dl))
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
269
    return(0);
1 by brian
clean slate
270
  tmp= *dynamic_element(&plugin_dl_array, plugin_dl_array.elements - 1,
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
271
                        plugin::Library **)=
272
      (plugin::Library *) memdup_root(&plugin_mem_root,
273
                                      (unsigned char*)plugin_dl,
274
                                      sizeof(plugin::Library));
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
275
  return(tmp);
1 by brian
clean slate
276
}
277
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
278
static inline void free_plugin_mem(plugin::Library *p)
1 by brian
clean slate
279
{
280
  if (p->handle)
281
    dlclose(p->handle);
477 by Monty Taylor
Removed my_free(). It turns out that it had been def'd to ignore the flags passed to it in the second arg anyway. Gotta love that.
282
  free(p->dl.str);
1 by brian
clean slate
283
}
284
285
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
286
static plugin::Library *plugin_dl_add(const LEX_STRING *dl, int report)
1 by brian
clean slate
287
{
534 by Monty Taylor
Removed stxnmov. Also deleted strstr which had already been removed.
288
  string dlpath;
1054.2.11 by Monty Taylor
Removed copy_and_convert.
289
  uint32_t plugin_dir_len;
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
290
  plugin::Library *tmp, plugin_dl;
1 by brian
clean slate
291
  void *sym;
292
  plugin_dir_len= strlen(opt_plugin_dir);
534 by Monty Taylor
Removed stxnmov. Also deleted strstr which had already been removed.
293
  dlpath.reserve(FN_REFLEN);
1 by brian
clean slate
294
  /*
295
    Ensure that the dll doesn't have a path.
296
    This is done to ensure that only approved libraries from the
297
    plugin directory are used (to make this even remotely secure).
298
  */
266.1.26 by Monty Taylor
Removed my_strchr.
299
  if (strchr(dl->str, FN_LIBCHAR) ||
1 by brian
clean slate
300
      check_string_char_length((LEX_STRING *) dl, "", NAME_CHAR_LEN,
301
                               system_charset_info, 1) ||
302
      plugin_dir_len + dl->length + 1 >= FN_REFLEN)
303
  {
304
    if (report & REPORT_TO_USER)
305
      my_error(ER_UDF_NO_PATHS, MYF(0));
306
    if (report & REPORT_TO_LOG)
755.2.1 by Mark Atwood
replace sql_print_error etc with errmsg_print
307
      errmsg_printf(ERRMSG_LVL_ERROR, "%s",ER(ER_UDF_NO_PATHS));
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
308
    return(0);
1 by brian
clean slate
309
  }
310
  /* If this dll is already loaded just increase ref_count. */
311
  if ((tmp= plugin_dl_find(dl)))
312
  {
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
313
    return(tmp);
1 by brian
clean slate
314
  }
212.6.1 by Mats Kindahl
Replacing all bzero() calls with memset() calls and removing the bzero.c file.
315
  memset(&plugin_dl, 0, sizeof(plugin_dl));
1 by brian
clean slate
316
  /* Compile dll path */
534 by Monty Taylor
Removed stxnmov. Also deleted strstr which had already been removed.
317
  dlpath.append(opt_plugin_dir);
318
  dlpath.append("/");
319
  dlpath.append(dl->str);
1 by brian
clean slate
320
  /* Open new dll handle */
534 by Monty Taylor
Removed stxnmov. Also deleted strstr which had already been removed.
321
  if (!(plugin_dl.handle= dlopen(dlpath.c_str(), RTLD_LAZY|RTLD_GLOBAL)))
1 by brian
clean slate
322
  {
323
    const char *errmsg=dlerror();
534 by Monty Taylor
Removed stxnmov. Also deleted strstr which had already been removed.
324
    uint32_t dlpathlen= dlpath.length();
325
    if (!dlpath.compare(0, dlpathlen, errmsg))
1 by brian
clean slate
326
    { // if errmsg starts from dlpath, trim this prefix.
327
      errmsg+=dlpathlen;
328
      if (*errmsg == ':') errmsg++;
329
      if (*errmsg == ' ') errmsg++;
330
    }
331
    if (report & REPORT_TO_USER)
534 by Monty Taylor
Removed stxnmov. Also deleted strstr which had already been removed.
332
      my_error(ER_CANT_OPEN_LIBRARY, MYF(0), dlpath.c_str(), errno, errmsg);
1 by brian
clean slate
333
    if (report & REPORT_TO_LOG)
755.2.1 by Mark Atwood
replace sql_print_error etc with errmsg_print
334
      errmsg_printf(ERRMSG_LVL_ERROR, ER(ER_CANT_OPEN_LIBRARY), dlpath.c_str(), errno, errmsg);
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
335
    return(0);
1 by brian
clean slate
336
  }
177.4.1 by mark
remove some useless version checking code from sql_plugin.cc
337
1 by brian
clean slate
338
  /* Find plugin declarations */
339
  if (!(sym= dlsym(plugin_dl.handle, plugin_declarations_sym)))
340
  {
341
    free_plugin_mem(&plugin_dl);
342
    if (report & REPORT_TO_USER)
343
      my_error(ER_CANT_FIND_DL_ENTRY, MYF(0), plugin_declarations_sym);
344
    if (report & REPORT_TO_LOG)
755.2.1 by Mark Atwood
replace sql_print_error etc with errmsg_print
345
      errmsg_printf(ERRMSG_LVL_ERROR, ER(ER_CANT_FIND_DL_ENTRY), plugin_declarations_sym);
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
346
    return(0);
1 by brian
clean slate
347
  }
348
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
349
  plugin_dl.plugins= static_cast<plugin::Manifest *>(sym);
1 by brian
clean slate
350
351
  /* Duplicate and convert dll name */
352
  plugin_dl.dl.length= dl->length * files_charset_info->mbmaxlen + 1;
1054.2.11 by Monty Taylor
Removed copy_and_convert.
353
  if (! (plugin_dl.dl.str= (char*) calloc(plugin_dl.dl.length, sizeof(char))))
1 by brian
clean slate
354
  {
355
    free_plugin_mem(&plugin_dl);
356
    if (report & REPORT_TO_USER)
357
      my_error(ER_OUTOFMEMORY, MYF(0), plugin_dl.dl.length);
358
    if (report & REPORT_TO_LOG)
755.2.1 by Mark Atwood
replace sql_print_error etc with errmsg_print
359
      errmsg_printf(ERRMSG_LVL_ERROR, ER(ER_OUTOFMEMORY), plugin_dl.dl.length);
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
360
    return(0);
1 by brian
clean slate
361
  }
1054.2.11 by Monty Taylor
Removed copy_and_convert.
362
  strcpy(plugin_dl.dl.str, dl->str);
1 by brian
clean slate
363
  /* Add this dll to array */
364
  if (! (tmp= plugin_dl_insert_or_reuse(&plugin_dl)))
365
  {
366
    free_plugin_mem(&plugin_dl);
367
    if (report & REPORT_TO_USER)
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
368
      my_error(ER_OUTOFMEMORY, MYF(0), sizeof(plugin::Library));
1 by brian
clean slate
369
    if (report & REPORT_TO_LOG)
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
370
      errmsg_printf(ERRMSG_LVL_ERROR, ER(ER_OUTOFMEMORY),
371
                    sizeof(plugin::Library));
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
372
    return(0);
1 by brian
clean slate
373
  }
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
374
  return(tmp);
1 by brian
clean slate
375
}
376
377
378
static void plugin_dl_del(const LEX_STRING *dl)
379
{
482 by Brian Aker
Remove uint.
380
  uint32_t i;
1 by brian
clean slate
381
382
  for (i= 0; i < plugin_dl_array.elements; i++)
383
  {
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
384
    plugin::Library *tmp= *dynamic_element(&plugin_dl_array, i,
385
                                           plugin::Library **);
962.1.5 by Brian Aker
Remove ref_count from DLL plugin.
386
    if (! my_strnncoll(files_charset_info,
481 by Brian Aker
Remove all of uchar.
387
                       (const unsigned char *)dl->str, dl->length,
388
                       (const unsigned char *)tmp->dl.str, tmp->dl.length))
1 by brian
clean slate
389
    {
390
      /* Do not remove this element, unless no other plugin uses this dll. */
391
      {
392
        free_plugin_mem(tmp);
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
393
        memset(tmp, 0, sizeof(plugin::Library));
1 by brian
clean slate
394
      }
395
      break;
396
    }
397
  }
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
398
  return;
1 by brian
clean slate
399
}
400
401
402
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
403
static plugin::Handle *plugin_insert_or_reuse(plugin::Handle *plugin)
1 by brian
clean slate
404
{
481 by Brian Aker
Remove all of uchar.
405
  if (insert_dynamic(&plugin_array, (unsigned char*)&plugin))
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
406
    return(0);
1093.3.4 by Monty Taylor
Naming cleanups.
407
  plugin= *dynamic_element(&plugin_array, plugin_array.elements - 1,
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
408
                        plugin::Handle **);
1093.3.4 by Monty Taylor
Naming cleanups.
409
  return(plugin);
1 by brian
clean slate
410
}
411
412
413
/*
414
  NOTE
415
    Requires that a write-lock is held on LOCK_system_variables_hash
416
*/
1110.1.5 by Monty Taylor
Renamed PluginRegistry to plugin::Registry.
417
static bool plugin_add(plugin::Registry &registry, MEM_ROOT *tmp_root,
1 by brian
clean slate
418
                       const LEX_STRING *name, const LEX_STRING *dl,
419
                       int *argc, char **argv, int report)
420
{
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
421
  plugin::Manifest *manifest;
908.2.1 by Monty Taylor
First pass at refactoring plugins - factored out sql_map.
422
  if (! initialized)
423
    return(0);
424
971.1.54 by Monty Taylor
Trimmed out some plugin type stuff.
425
  if (registry.find(name))
1 by brian
clean slate
426
  {
427
    if (report & REPORT_TO_USER)
428
      my_error(ER_UDF_EXISTS, MYF(0), name->str);
429
    if (report & REPORT_TO_LOG)
755.2.1 by Mark Atwood
replace sql_print_error etc with errmsg_print
430
      errmsg_printf(ERRMSG_LVL_ERROR, ER(ER_UDF_EXISTS), name->str);
163 by Brian Aker
Merge Monty's code.
431
    return(true);
1 by brian
clean slate
432
  }
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
433
  plugin::Library *library= plugin_dl_add(dl, report);
1093.3.4 by Monty Taylor
Naming cleanups.
434
  if (library == NULL)
435
    return true;
436
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
437
  plugin::Handle *tmp= NULL;
1 by brian
clean slate
438
  /* Find plugin by name */
1093.3.4 by Monty Taylor
Naming cleanups.
439
  for (manifest= library->plugins; manifest->name; manifest++)
1 by brian
clean slate
440
  {
971.1.55 by Monty Taylor
Removed now meaningless plugin_type.
441
    if (! my_strnncoll(system_charset_info,
481 by Brian Aker
Remove all of uchar.
442
                       (const unsigned char *)name->str, name->length,
1093.3.4 by Monty Taylor
Naming cleanups.
443
                       (const unsigned char *)manifest->name,
444
                       strlen(manifest->name)))
1 by brian
clean slate
445
    {
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
446
      tmp= new (std::nothrow) plugin::Handle(manifest, library);
1093.3.4 by Monty Taylor
Naming cleanups.
447
      if (tmp == NULL)
448
        return true;
177.4.1 by mark
remove some useless version checking code from sql_plugin.cc
449
1093.3.4 by Monty Taylor
Naming cleanups.
450
      if (!test_plugin_options(tmp_root, tmp, argc, argv))
1 by brian
clean slate
451
      {
1093.3.4 by Monty Taylor
Naming cleanups.
452
        if ((tmp= plugin_insert_or_reuse(tmp)))
1 by brian
clean slate
453
        {
1093.3.4 by Monty Taylor
Naming cleanups.
454
          registry.add(tmp);
455
          init_alloc_root(&tmp->mem_root, 4096, 4096);
873.2.21 by Monty Taylor
Removed the HASH for plugin_hash.
456
          return(false);
1 by brian
clean slate
457
        }
1093.3.4 by Monty Taylor
Naming cleanups.
458
        mysql_del_sys_var_chain(tmp->system_vars);
1 by brian
clean slate
459
        goto err;
460
      }
461
      /* plugin was disabled */
462
      plugin_dl_del(dl);
163 by Brian Aker
Merge Monty's code.
463
      return(false);
1 by brian
clean slate
464
    }
465
  }
466
  if (report & REPORT_TO_USER)
467
    my_error(ER_CANT_FIND_DL_ENTRY, MYF(0), name->str);
468
  if (report & REPORT_TO_LOG)
755.2.1 by Mark Atwood
replace sql_print_error etc with errmsg_print
469
    errmsg_printf(ERRMSG_LVL_ERROR, ER(ER_CANT_FIND_DL_ENTRY), name->str);
1 by brian
clean slate
470
err:
471
  plugin_dl_del(dl);
163 by Brian Aker
Merge Monty's code.
472
  return(true);
1 by brian
clean slate
473
}
474
475
1110.1.5 by Monty Taylor
Renamed PluginRegistry to plugin::Registry.
476
static void plugin_del(plugin::Registry &registry, plugin::Handle *plugin)
1 by brian
clean slate
477
{
965.1.1 by Brian Aker
Refactor plugin loading to remove mask (one step closer to getting rid of
478
  if (plugin->isInited)
479
  {
1093.3.4 by Monty Taylor
Naming cleanups.
480
    if (plugin->getManifest().status_vars)
965.1.1 by Brian Aker
Refactor plugin loading to remove mask (one step closer to getting rid of
481
    {
1093.3.4 by Monty Taylor
Naming cleanups.
482
      remove_status_vars(plugin->getManifest().status_vars);
965.1.1 by Brian Aker
Refactor plugin loading to remove mask (one step closer to getting rid of
483
    }
484
1093.3.4 by Monty Taylor
Naming cleanups.
485
    if (plugin->getManifest().deinit)
486
      plugin->getManifest().deinit(registry);
965.1.1 by Brian Aker
Refactor plugin loading to remove mask (one step closer to getting rid of
487
  }
488
1 by brian
clean slate
489
  /* Free allocated strings before deleting the plugin. */
490
  plugin_vars_free_values(plugin->system_vars);
491
  if (plugin->plugin_dl)
492
    plugin_dl_del(&plugin->plugin_dl->dl);
965.1.1 by Brian Aker
Refactor plugin loading to remove mask (one step closer to getting rid of
493
  plugin->isInited= false;
658 by Brian Aker
Part removal of my_pthread.h
494
  pthread_rwlock_wrlock(&LOCK_system_variables_hash);
1 by brian
clean slate
495
  mysql_del_sys_var_chain(plugin->system_vars);
658 by Brian Aker
Part removal of my_pthread.h
496
  pthread_rwlock_unlock(&LOCK_system_variables_hash);
1093.3.4 by Monty Taylor
Naming cleanups.
497
  delete plugin;
1 by brian
clean slate
498
}
499
1110.1.5 by Monty Taylor
Renamed PluginRegistry to plugin::Registry.
500
static void reap_plugins(plugin::Registry &plugins)
1 by brian
clean slate
501
{
656.1.1 by Monty Taylor
OOOh doggie. Got rid of my_alloca.
502
  size_t count;
503
  uint32_t idx;
1119.1.2 by Monty Taylor
Fixed style issues. /me smacks /me.
504
  plugin::Handle *plugin;
660.1.6 by Eric Herman
trailing whitespace fixup
505
1 by brian
clean slate
506
  count= plugin_array.elements;
507
508
  for (idx= 0; idx < count; idx++)
509
  {
1119.1.2 by Monty Taylor
Fixed style issues. /me smacks /me.
510
    plugin= *dynamic_element(&plugin_array, idx, plugin::Handle **);
1110.1.3 by Monty Taylor
Added ListenHandler as a member of PluginRegistry.
511
    plugin_del(plugins, plugin);
688 by Brian Aker
Second pass through memory allocation issues (this solves the ones around
512
  }
1101.1.27 by Monty Taylor
Fixed the plugin string valgrind leak.
513
  drizzle_del_plugin_sysvar();
1 by brian
clean slate
514
}
515
1119.1.1 by Monty Taylor
--help doesn't need --datadir to work.
516
1119.1.2 by Monty Taylor
Fixed style issues. /me smacks /me.
517
static void plugin_initialize_vars(plugin::Handle *plugin)
1 by brian
clean slate
518
{
1093.3.4 by Monty Taylor
Naming cleanups.
519
  if (plugin->getManifest().status_vars)
1 by brian
clean slate
520
  {
1093.3.4 by Monty Taylor
Naming cleanups.
521
    add_status_vars(plugin->getManifest().status_vars); // add_status_vars makes a copy
1 by brian
clean slate
522
  }
523
524
  /*
525
    set the plugin attribute of plugin's sys vars so they are pointing
526
    to the active plugin
527
  */
528
  if (plugin->system_vars)
529
  {
530
    sys_var_pluginvar *var= plugin->system_vars->cast_pluginvar();
531
    for (;;)
532
    {
533
      var->plugin= plugin;
1055.2.20 by Jay Pipes
Refactors sys_var class -- doxygenates and documents the class members and functions. Protects all member variables and adds public getters/setters.
534
      if (! var->getNext())
1 by brian
clean slate
535
        break;
1055.2.20 by Jay Pipes
Refactors sys_var class -- doxygenates and documents the class members and functions. Protects all member variables and adds public getters/setters.
536
      var= var->getNext()->cast_pluginvar();
1 by brian
clean slate
537
    }
538
  }
1119.1.1 by Monty Taylor
--help doesn't need --datadir to work.
539
}
540
541
542
static bool plugin_initialize(plugin::Registry &registry,
1119.1.2 by Monty Taylor
Fixed style issues. /me smacks /me.
543
                              plugin::Handle *plugin)
1119.1.1 by Monty Taylor
--help doesn't need --datadir to work.
544
{
545
  assert(plugin->isInited == false);
546
547
  if (plugin->getManifest().init)
548
  {
549
    if (plugin->getManifest().init(registry))
550
    {
551
      errmsg_printf(ERRMSG_LVL_ERROR,
552
                    _("Plugin '%s' init function returned error.\n"),
553
                    plugin->getName().c_str());
554
      return true;
555
    }
556
  }
557
  plugin->isInited= true;
558
1 by brian
clean slate
559
965.1.1 by Brian Aker
Refactor plugin loading to remove mask (one step closer to getting rid of
560
  return false;
1 by brian
clean slate
561
}
562
563
481 by Brian Aker
Remove all of uchar.
564
extern "C" unsigned char *get_bookmark_hash_key(const unsigned char *, size_t *, bool);
565
566
654 by Brian Aker
Remove unused (yet more)
567
unsigned char *get_bookmark_hash_key(const unsigned char *buff, size_t *length, bool)
1 by brian
clean slate
568
{
569
  struct st_bookmark *var= (st_bookmark *)buff;
570
  *length= var->name_len + 1;
481 by Brian Aker
Remove all of uchar.
571
  return (unsigned char*) var->key;
1 by brian
clean slate
572
}
573
574
575
/*
576
  The logic is that we first load and initialize all compiled in plugins.
577
  From there we load up the dynamic types (assuming we have not been told to
578
  skip this part).
579
580
  Finally we initialize everything, aka the dynamic that have yet to initialize.
581
*/
1110.1.5 by Monty Taylor
Renamed PluginRegistry to plugin::Registry.
582
int plugin_init(plugin::Registry &registry, int *argc, char **argv, int flags)
1 by brian
clean slate
583
{
656.1.1 by Monty Taylor
OOOh doggie. Got rid of my_alloca.
584
  uint32_t idx;
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
585
  plugin::Manifest **builtins;
586
  plugin::Manifest *manifest;
587
  plugin::Handle *handle;
1 by brian
clean slate
588
  MEM_ROOT tmp_root;
589
590
  if (initialized)
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
591
    return(0);
1 by brian
clean slate
592
593
  init_alloc_root(&plugin_mem_root, 4096, 4096);
594
  init_alloc_root(&tmp_root, 4096, 4096);
595
596
  if (hash_init(&bookmark_hash, &my_charset_bin, 16, 0, 0,
597
                  get_bookmark_hash_key, NULL, HASH_UNIQUE))
598
      goto err;
599
600
601
  if (my_init_dynamic_array(&plugin_dl_array,
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
602
                            sizeof(plugin::Library *),16,16) ||
1 by brian
clean slate
603
      my_init_dynamic_array(&plugin_array,
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
604
                            sizeof(plugin::Handle *),16,16))
1 by brian
clean slate
605
    goto err;
606
607
  initialized= 1;
608
609
  /*
610
    First we register builtin plugins
611
  */
992.1.39 by Monty Taylor
Removed the m4-based plugin system.
612
  for (builtins= drizzled_builtins; *builtins; builtins++)
1 by brian
clean slate
613
  {
1093.3.4 by Monty Taylor
Naming cleanups.
614
    for (manifest= *builtins; manifest->name; manifest++)
1 by brian
clean slate
615
    {
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
616
      handle= new (std::nothrow) plugin::Handle(manifest);
1093.3.4 by Monty Taylor
Naming cleanups.
617
      if (handle == NULL)
618
        return true;
1 by brian
clean slate
619
620
      free_root(&tmp_root, MYF(MY_MARK_BLOCKS_FREE));
1093.3.4 by Monty Taylor
Naming cleanups.
621
      if (test_plugin_options(&tmp_root, handle, argc, argv))
1 by brian
clean slate
622
        continue;
623
1110.1.3 by Monty Taylor
Added ListenHandler as a member of PluginRegistry.
624
      if (register_builtin(registry, handle, &handle))
1 by brian
clean slate
625
        goto err_unlock;
626
1119.1.1 by Monty Taylor
--help doesn't need --datadir to work.
627
      plugin_initialize_vars(handle);
1 by brian
clean slate
628
1119.1.2 by Monty Taylor
Fixed style issues. /me smacks /me.
629
      if (! (flags & PLUGIN_INIT_SKIP_INITIALIZATION))
1119.1.1 by Monty Taylor
--help doesn't need --datadir to work.
630
      {
631
        if (plugin_initialize(registry, handle))
632
          goto err_unlock;
633
      }
1 by brian
clean slate
634
    }
635
  }
636
637
638
  /* Register all dynamic plugins */
1119.1.2 by Monty Taylor
Fixed style issues. /me smacks /me.
639
  if (! (flags & PLUGIN_INIT_SKIP_DYNAMIC_LOADING))
1 by brian
clean slate
640
  {
641
    if (opt_plugin_load)
1110.1.3 by Monty Taylor
Added ListenHandler as a member of PluginRegistry.
642
      plugin_load_list(registry, &tmp_root, argc, argv, opt_plugin_load);
1 by brian
clean slate
643
  }
644
645
  if (flags & PLUGIN_INIT_SKIP_INITIALIZATION)
646
    goto end;
647
648
  /*
649
    Now we initialize all remaining plugins
650
  */
656.1.1 by Monty Taylor
OOOh doggie. Got rid of my_alloca.
651
  for (idx= 0; idx < plugin_array.elements; idx++)
1 by brian
clean slate
652
  {
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
653
    handle= *dynamic_element(&plugin_array, idx, plugin::Handle **);
1093.3.4 by Monty Taylor
Naming cleanups.
654
    if (handle->isInited == false)
1 by brian
clean slate
655
    {
1119.1.1 by Monty Taylor
--help doesn't need --datadir to work.
656
      plugin_initialize_vars(handle);
657
1110.1.3 by Monty Taylor
Added ListenHandler as a member of PluginRegistry.
658
      if (plugin_initialize(registry, handle))
659
        plugin_del(registry, handle);
1 by brian
clean slate
660
    }
661
  }
662
663
664
end:
665
  free_root(&tmp_root, MYF(0));
666
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
667
  return(0);
1 by brian
clean slate
668
669
err_unlock:
670
err:
671
  free_root(&tmp_root, MYF(0));
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
672
  return(1);
1 by brian
clean slate
673
}
674
675
1110.1.5 by Monty Taylor
Renamed PluginRegistry to plugin::Registry.
676
static bool register_builtin(plugin::Registry &registry,
1110.1.3 by Monty Taylor
Added ListenHandler as a member of PluginRegistry.
677
                             plugin::Handle *tmp,
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
678
                             plugin::Handle **ptr)
1 by brian
clean slate
679
{
680
965.1.1 by Brian Aker
Refactor plugin loading to remove mask (one step closer to getting rid of
681
  tmp->isInited= false;
1 by brian
clean slate
682
  tmp->plugin_dl= 0;
683
481 by Brian Aker
Remove all of uchar.
684
  if (insert_dynamic(&plugin_array, (unsigned char*)&tmp))
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
685
    return(1);
1 by brian
clean slate
686
687
  *ptr= *dynamic_element(&plugin_array, plugin_array.elements - 1,
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
688
                         plugin::Handle **);
1 by brian
clean slate
689
971.1.54 by Monty Taylor
Trimmed out some plugin type stuff.
690
  registry.add(*ptr);
1 by brian
clean slate
691
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
692
  return(0);
1 by brian
clean slate
693
}
694
695
696
/*
697
  called only by plugin_init()
698
*/
1110.1.5 by Monty Taylor
Renamed PluginRegistry to plugin::Registry.
699
static bool plugin_load_list(plugin::Registry &plugins,
1110.1.3 by Monty Taylor
Added ListenHandler as a member of PluginRegistry.
700
                             MEM_ROOT *tmp_root, int *argc, char **argv,
1 by brian
clean slate
701
                             const char *list)
702
{
703
  char buffer[FN_REFLEN];
704
  LEX_STRING name= {buffer, 0}, dl= {NULL, 0}, *str= &name;
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
705
  plugin::Library *plugin_dl;
706
  plugin::Manifest *plugin;
1 by brian
clean slate
707
  char *p= buffer;
708
  while (list)
709
  {
710
    if (p == buffer + sizeof(buffer) - 1)
711
    {
755.2.1 by Mark Atwood
replace sql_print_error etc with errmsg_print
712
      errmsg_printf(ERRMSG_LVL_ERROR, _("plugin-load parameter too long"));
163 by Brian Aker
Merge Monty's code.
713
      return(true);
1 by brian
clean slate
714
    }
715
716
    switch ((*(p++)= *(list++))) {
717
    case '\0':
718
      list= NULL; /* terminate the loop */
719
      /* fall through */
720
    case ':':     /* can't use this as delimiter as it may be drive letter */
721
    case ';':
722
      str->str[str->length]= '\0';
723
      if (str == &name)  // load all plugins in named module
724
      {
725
        if (!name.length)
726
        {
727
          p--;    /* reset pointer */
728
          continue;
729
        }
730
731
        dl= name;
732
        if ((plugin_dl= plugin_dl_add(&dl, REPORT_TO_LOG)))
733
        {
177.4.3 by mark
ripped out more plugin ABI and API version checking, and plugin versions are now strings
734
          for (plugin= plugin_dl->plugins; plugin->name; plugin++)
1 by brian
clean slate
735
          {
736
            name.str= (char *) plugin->name;
737
            name.length= strlen(name.str);
738
739
            free_root(tmp_root, MYF(MY_MARK_BLOCKS_FREE));
1110.1.3 by Monty Taylor
Added ListenHandler as a member of PluginRegistry.
740
            if (plugin_add(plugins, tmp_root, &name, &dl,
741
                           argc, argv, REPORT_TO_LOG))
1 by brian
clean slate
742
              goto error;
743
          }
744
          plugin_dl_del(&dl); // reduce ref count
745
        }
746
      }
747
      else
748
      {
749
        free_root(tmp_root, MYF(MY_MARK_BLOCKS_FREE));
1110.1.3 by Monty Taylor
Added ListenHandler as a member of PluginRegistry.
750
        if (plugin_add(plugins, tmp_root, &name, &dl,
751
                       argc, argv, REPORT_TO_LOG))
1 by brian
clean slate
752
          goto error;
753
      }
754
      name.length= dl.length= 0;
755
      dl.str= NULL; name.str= p= buffer;
756
      str= &name;
757
      continue;
758
    case '=':
759
    case '#':
760
      if (str == &name)
761
      {
762
        name.str[name.length]= '\0';
763
        str= &dl;
764
        str->str= p;
765
        continue;
766
      }
767
    default:
768
      str->length++;
769
      continue;
770
    }
771
  }
163 by Brian Aker
Merge Monty's code.
772
  return(false);
1 by brian
clean slate
773
error:
755.2.1 by Mark Atwood
replace sql_print_error etc with errmsg_print
774
  errmsg_printf(ERRMSG_LVL_ERROR, _("Couldn't load plugin named '%s' with soname '%s'."),
1 by brian
clean slate
775
                  name.str, dl.str);
163 by Brian Aker
Merge Monty's code.
776
  return(true);
1 by brian
clean slate
777
}
778
779
1110.1.5 by Monty Taylor
Renamed PluginRegistry to plugin::Registry.
780
void plugin_shutdown(plugin::Registry &registry)
1 by brian
clean slate
781
{
962.1.6 by Brian Aker
Cut down on shutdown loop of plugins (cutting stuff out in order to simplify
782
  uint32_t idx;
656.1.1 by Monty Taylor
OOOh doggie. Got rid of my_alloca.
783
  size_t count= plugin_array.elements;
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
784
  vector<plugin::Handle *> plugins;
785
  vector<plugin::Library *> dl;
1 by brian
clean slate
786
787
  if (initialized)
788
  {
789
    reap_needed= true;
790
1110.1.3 by Monty Taylor
Added ListenHandler as a member of PluginRegistry.
791
    reap_plugins(registry);
962.1.6 by Brian Aker
Cut down on shutdown loop of plugins (cutting stuff out in order to simplify
792
    unlock_variables(NULL, &global_system_variables);
793
    unlock_variables(NULL, &max_system_variables);
1 by brian
clean slate
794
795
    cleanup_variables(NULL, &global_system_variables);
796
    cleanup_variables(NULL, &max_system_variables);
797
798
    initialized= 0;
799
  }
800
801
  /* Dispose of the memory */
802
803
  delete_dynamic(&plugin_array);
804
805
  count= plugin_dl_array.elements;
656.1.1 by Monty Taylor
OOOh doggie. Got rid of my_alloca.
806
  dl.reserve(count);
807
  for (idx= 0; idx < count; idx++)
808
    dl.push_back(*dynamic_element(&plugin_dl_array, idx,
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
809
                 plugin::Library **));
656.1.1 by Monty Taylor
OOOh doggie. Got rid of my_alloca.
810
  for (idx= 0; idx < count; idx++)
811
    free_plugin_mem(dl[idx]);
1 by brian
clean slate
812
  delete_dynamic(&plugin_dl_array);
813
814
  hash_free(&bookmark_hash);
815
  free_root(&plugin_mem_root, MYF(0));
816
817
  global_variables_dynamic_size= 0;
818
}
819
820
/****************************************************************************
821
  Internal type declarations for variables support
822
****************************************************************************/
823
319.1.1 by Grant Limberg
renamed all instances of MYSQL_ to DRIZZLE_
824
#undef DRIZZLE_SYSVAR_NAME
825
#define DRIZZLE_SYSVAR_NAME(name) name
1 by brian
clean slate
826
#define PLUGIN_VAR_TYPEMASK 0x007f
827
828
#define EXTRA_OPTIONS 3 /* options for: 'foo', 'plugin-foo' and NULL */
829
319.1.1 by Grant Limberg
renamed all instances of MYSQL_ to DRIZZLE_
830
typedef DECLARE_DRIZZLE_SYSVAR_BASIC(sysvar_bool_t, bool);
520.1.22 by Brian Aker
Second pass of thd cleanup
831
typedef DECLARE_DRIZZLE_SessionVAR_BASIC(sessionvar_bool_t, bool);
319.1.1 by Grant Limberg
renamed all instances of MYSQL_ to DRIZZLE_
832
typedef DECLARE_DRIZZLE_SYSVAR_BASIC(sysvar_str_t, char *);
520.1.22 by Brian Aker
Second pass of thd cleanup
833
typedef DECLARE_DRIZZLE_SessionVAR_BASIC(sessionvar_str_t, char *);
319.1.1 by Grant Limberg
renamed all instances of MYSQL_ to DRIZZLE_
834
835
typedef DECLARE_DRIZZLE_SYSVAR_TYPELIB(sysvar_enum_t, unsigned long);
520.1.22 by Brian Aker
Second pass of thd cleanup
836
typedef DECLARE_DRIZZLE_SessionVAR_TYPELIB(sessionvar_enum_t, unsigned long);
319.1.1 by Grant Limberg
renamed all instances of MYSQL_ to DRIZZLE_
837
typedef DECLARE_DRIZZLE_SYSVAR_TYPELIB(sysvar_set_t, uint64_t);
520.1.22 by Brian Aker
Second pass of thd cleanup
838
typedef DECLARE_DRIZZLE_SessionVAR_TYPELIB(sessionvar_set_t, uint64_t);
319.1.1 by Grant Limberg
renamed all instances of MYSQL_ to DRIZZLE_
839
840
typedef DECLARE_DRIZZLE_SYSVAR_SIMPLE(sysvar_int_t, int);
841
typedef DECLARE_DRIZZLE_SYSVAR_SIMPLE(sysvar_long_t, long);
842
typedef DECLARE_DRIZZLE_SYSVAR_SIMPLE(sysvar_int64_t_t, int64_t);
843
typedef DECLARE_DRIZZLE_SYSVAR_SIMPLE(sysvar_uint_t, uint);
844
typedef DECLARE_DRIZZLE_SYSVAR_SIMPLE(sysvar_ulong_t, ulong);
845
typedef DECLARE_DRIZZLE_SYSVAR_SIMPLE(sysvar_uint64_t_t, uint64_t);
846
520.1.22 by Brian Aker
Second pass of thd cleanup
847
typedef DECLARE_DRIZZLE_SessionVAR_SIMPLE(sessionvar_int_t, int);
848
typedef DECLARE_DRIZZLE_SessionVAR_SIMPLE(sessionvar_long_t, long);
849
typedef DECLARE_DRIZZLE_SessionVAR_SIMPLE(sessionvar_int64_t_t, int64_t);
850
typedef DECLARE_DRIZZLE_SessionVAR_SIMPLE(sessionvar_uint_t, uint);
851
typedef DECLARE_DRIZZLE_SessionVAR_SIMPLE(sessionvar_ulong_t, ulong);
852
typedef DECLARE_DRIZZLE_SessionVAR_SIMPLE(sessionvar_uint64_t_t, uint64_t);
1 by brian
clean slate
853
520.1.22 by Brian Aker
Second pass of thd cleanup
854
typedef bool *(*mysql_sys_var_ptr_p)(Session* a_session, int offset);
1 by brian
clean slate
855
856
857
/****************************************************************************
858
  default variable data check and update functions
859
****************************************************************************/
860
654 by Brian Aker
Remove unused (yet more)
861
static int check_func_bool(Session *, struct st_mysql_sys_var *var,
1 by brian
clean slate
862
                           void *save, st_mysql_value *value)
863
{
864
  char buff[STRING_BUFFER_USUAL_SIZE];
865
  const char *strvalue= "NULL", *str;
866
  int result, length;
53.2.2 by Monty Taylor
Updated everything that needs updating to compile with -std=gnu99 -pedantic
867
  int64_t tmp;
1 by brian
clean slate
868
319.1.1 by Grant Limberg
renamed all instances of MYSQL_ to DRIZZLE_
869
  if (value->value_type(value) == DRIZZLE_VALUE_TYPE_STRING)
1 by brian
clean slate
870
  {
871
    length= sizeof(buff);
872
    if (!(str= value->val_str(value, buff, &length)) ||
873
        (result= find_type(&bool_typelib, str, length, 1)-1) < 0)
874
    {
875
      if (str)
876
        strvalue= str;
877
      goto err;
878
    }
879
  }
880
  else
881
  {
882
    if (value->val_int(value, &tmp) < 0)
883
      goto err;
884
    if (tmp > 1)
885
    {
886
      llstr(tmp, buff);
887
      strvalue= buff;
888
      goto err;
889
    }
890
    result= (int) tmp;
891
  }
892
  *(int*)save= -result;
893
  return 0;
894
err:
895
  my_error(ER_WRONG_VALUE_FOR_VAR, MYF(0), var->name, strvalue);
896
  return 1;
897
}
898
899
520.1.22 by Brian Aker
Second pass of thd cleanup
900
static int check_func_int(Session *session, struct st_mysql_sys_var *var,
1 by brian
clean slate
901
                          void *save, st_mysql_value *value)
902
{
143 by Brian Aker
Bool cleanup.
903
  bool fixed;
53.2.2 by Monty Taylor
Updated everything that needs updating to compile with -std=gnu99 -pedantic
904
  int64_t tmp;
1 by brian
clean slate
905
  struct my_option options;
906
  value->val_int(value, &tmp);
907
  plugin_opt_set_limits(&options, var);
908
909
  if (var->flags & PLUGIN_VAR_UNSIGNED)
895 by Brian Aker
Completion (?) of uint conversion.
910
    *(uint32_t *)save= (uint32_t) getopt_ull_limit_value((uint64_t) tmp, &options,
1 by brian
clean slate
911
                                                   &fixed);
912
  else
913
    *(int *)save= (int) getopt_ll_limit_value(tmp, &options, &fixed);
914
520.1.22 by Brian Aker
Second pass of thd cleanup
915
  return throw_bounds_warning(session, fixed, var->flags & PLUGIN_VAR_UNSIGNED,
152 by Brian Aker
longlong replacement
916
                              var->name, (int64_t) tmp);
1 by brian
clean slate
917
}
918
919
520.1.22 by Brian Aker
Second pass of thd cleanup
920
static int check_func_long(Session *session, struct st_mysql_sys_var *var,
1 by brian
clean slate
921
                          void *save, st_mysql_value *value)
922
{
143 by Brian Aker
Bool cleanup.
923
  bool fixed;
53.2.2 by Monty Taylor
Updated everything that needs updating to compile with -std=gnu99 -pedantic
924
  int64_t tmp;
1 by brian
clean slate
925
  struct my_option options;
926
  value->val_int(value, &tmp);
927
  plugin_opt_set_limits(&options, var);
928
929
  if (var->flags & PLUGIN_VAR_UNSIGNED)
151 by Brian Aker
Ulonglong to uint64_t
930
    *(ulong *)save= (ulong) getopt_ull_limit_value((uint64_t) tmp, &options,
1 by brian
clean slate
931
                                                   &fixed);
932
  else
933
    *(long *)save= (long) getopt_ll_limit_value(tmp, &options, &fixed);
934
520.1.22 by Brian Aker
Second pass of thd cleanup
935
  return throw_bounds_warning(session, fixed, var->flags & PLUGIN_VAR_UNSIGNED,
152 by Brian Aker
longlong replacement
936
                              var->name, (int64_t) tmp);
1 by brian
clean slate
937
}
938
939
520.1.22 by Brian Aker
Second pass of thd cleanup
940
static int check_func_int64_t(Session *session, struct st_mysql_sys_var *var,
1 by brian
clean slate
941
                               void *save, st_mysql_value *value)
942
{
143 by Brian Aker
Bool cleanup.
943
  bool fixed;
53.2.2 by Monty Taylor
Updated everything that needs updating to compile with -std=gnu99 -pedantic
944
  int64_t tmp;
1 by brian
clean slate
945
  struct my_option options;
946
  value->val_int(value, &tmp);
947
  plugin_opt_set_limits(&options, var);
948
949
  if (var->flags & PLUGIN_VAR_UNSIGNED)
151 by Brian Aker
Ulonglong to uint64_t
950
    *(uint64_t *)save= getopt_ull_limit_value((uint64_t) tmp, &options,
1 by brian
clean slate
951
                                               &fixed);
952
  else
152 by Brian Aker
longlong replacement
953
    *(int64_t *)save= getopt_ll_limit_value(tmp, &options, &fixed);
1 by brian
clean slate
954
520.1.22 by Brian Aker
Second pass of thd cleanup
955
  return throw_bounds_warning(session, fixed, var->flags & PLUGIN_VAR_UNSIGNED,
152 by Brian Aker
longlong replacement
956
                              var->name, (int64_t) tmp);
1 by brian
clean slate
957
}
958
654 by Brian Aker
Remove unused (yet more)
959
static int check_func_str(Session *session, struct st_mysql_sys_var *,
1 by brian
clean slate
960
                          void *save, st_mysql_value *value)
961
{
962
  char buff[STRING_BUFFER_USUAL_SIZE];
963
  const char *str;
964
  int length;
965
966
  length= sizeof(buff);
967
  if ((str= value->val_str(value, buff, &length)))
520.1.22 by Brian Aker
Second pass of thd cleanup
968
    str= session->strmake(str, length);
1 by brian
clean slate
969
  *(const char**)save= str;
970
  return 0;
971
}
972
973
654 by Brian Aker
Remove unused (yet more)
974
static int check_func_enum(Session *, struct st_mysql_sys_var *var,
1 by brian
clean slate
975
                           void *save, st_mysql_value *value)
976
{
977
  char buff[STRING_BUFFER_USUAL_SIZE];
978
  const char *strvalue= "NULL", *str;
979
  TYPELIB *typelib;
53.2.2 by Monty Taylor
Updated everything that needs updating to compile with -std=gnu99 -pedantic
980
  int64_t tmp;
1 by brian
clean slate
981
  long result;
982
  int length;
983
520.1.21 by Brian Aker
THD -> Session rename
984
  if (var->flags & PLUGIN_VAR_SessionLOCAL)
520.1.22 by Brian Aker
Second pass of thd cleanup
985
    typelib= ((sessionvar_enum_t*) var)->typelib;
1 by brian
clean slate
986
  else
987
    typelib= ((sysvar_enum_t*) var)->typelib;
988
319.1.1 by Grant Limberg
renamed all instances of MYSQL_ to DRIZZLE_
989
  if (value->value_type(value) == DRIZZLE_VALUE_TYPE_STRING)
1 by brian
clean slate
990
  {
991
    length= sizeof(buff);
992
    if (!(str= value->val_str(value, buff, &length)))
993
      goto err;
994
    if ((result= (long)find_type(typelib, str, length, 1)-1) < 0)
995
    {
996
      strvalue= str;
997
      goto err;
998
    }
999
  }
1000
  else
1001
  {
1002
    if (value->val_int(value, &tmp))
1003
      goto err;
1004
    if (tmp >= typelib->count)
1005
    {
1006
      llstr(tmp, buff);
1007
      strvalue= buff;
1008
      goto err;
1009
    }
1010
    result= (long) tmp;
1011
  }
1012
  *(long*)save= result;
1013
  return 0;
1014
err:
1015
  my_error(ER_WRONG_VALUE_FOR_VAR, MYF(0), var->name, strvalue);
1016
  return 1;
1017
}
1018
1019
654 by Brian Aker
Remove unused (yet more)
1020
static int check_func_set(Session *, struct st_mysql_sys_var *var,
1 by brian
clean slate
1021
                          void *save, st_mysql_value *value)
1022
{
1023
  char buff[STRING_BUFFER_USUAL_SIZE], *error= 0;
1024
  const char *strvalue= "NULL", *str;
1025
  TYPELIB *typelib;
151 by Brian Aker
Ulonglong to uint64_t
1026
  uint64_t result;
482 by Brian Aker
Remove uint.
1027
  uint32_t error_len;
1 by brian
clean slate
1028
  bool not_used;
1029
  int length;
1030
520.1.21 by Brian Aker
THD -> Session rename
1031
  if (var->flags & PLUGIN_VAR_SessionLOCAL)
520.1.22 by Brian Aker
Second pass of thd cleanup
1032
    typelib= ((sessionvar_set_t*) var)->typelib;
1 by brian
clean slate
1033
  else
1034
    typelib= ((sysvar_set_t*)var)->typelib;
1035
319.1.1 by Grant Limberg
renamed all instances of MYSQL_ to DRIZZLE_
1036
  if (value->value_type(value) == DRIZZLE_VALUE_TYPE_STRING)
1 by brian
clean slate
1037
  {
1038
    length= sizeof(buff);
1039
    if (!(str= value->val_str(value, buff, &length)))
1040
      goto err;
1041
    result= find_set(typelib, str, length, NULL,
1042
                     &error, &error_len, &not_used);
1043
    if (error_len)
1044
    {
1067.4.16 by Nathan Williams
Fixed a few more system dependent type errors (size_t vs unsigned vs long unsigned).
1045
      length= min((uint32_t)sizeof(buff), error_len);
629.5.2 by Toru Maesaka
Second pass of replacing MySQL's strmake() with libc calls
1046
      strncpy(buff, error, length);
1047
      buff[length]= '\0';
1 by brian
clean slate
1048
      strvalue= buff;
1049
      goto err;
1050
    }
1051
  }
1052
  else
1053
  {
53.2.2 by Monty Taylor
Updated everything that needs updating to compile with -std=gnu99 -pedantic
1054
    if (value->val_int(value, (int64_t *)&result))
1 by brian
clean slate
1055
      goto err;
398.1.8 by Monty Taylor
Enabled -Wlong-long.
1056
    if (unlikely((result >= (1UL << typelib->count)) &&
1 by brian
clean slate
1057
                 (typelib->count < sizeof(long)*8)))
1058
    {
1059
      llstr(result, buff);
1060
      strvalue= buff;
1061
      goto err;
1062
    }
1063
  }
151 by Brian Aker
Ulonglong to uint64_t
1064
  *(uint64_t*)save= result;
1 by brian
clean slate
1065
  return 0;
1066
err:
1067
  my_error(ER_WRONG_VALUE_FOR_VAR, MYF(0), var->name, strvalue);
1068
  return 1;
1069
}
1070
1071
654 by Brian Aker
Remove unused (yet more)
1072
static void update_func_bool(Session *, struct st_mysql_sys_var *,
1 by brian
clean slate
1073
                             void *tgt, const void *save)
1074
{
199 by Brian Aker
my_bool...
1075
  *(bool *) tgt= *(int *) save ? 1 : 0;
1 by brian
clean slate
1076
}
1077
1078
654 by Brian Aker
Remove unused (yet more)
1079
static void update_func_int(Session *, struct st_mysql_sys_var *,
1 by brian
clean slate
1080
                             void *tgt, const void *save)
1081
{
1082
  *(int *)tgt= *(int *) save;
1083
}
1084
1085
654 by Brian Aker
Remove unused (yet more)
1086
static void update_func_long(Session *, struct st_mysql_sys_var *,
1 by brian
clean slate
1087
                             void *tgt, const void *save)
1088
{
1089
  *(long *)tgt= *(long *) save;
1090
}
1091
1092
654 by Brian Aker
Remove unused (yet more)
1093
static void update_func_int64_t(Session *, struct st_mysql_sys_var *,
77.1.46 by Monty Taylor
Finished the warnings work!
1094
                                 void *tgt, const void *save)
1 by brian
clean slate
1095
{
152 by Brian Aker
longlong replacement
1096
  *(int64_t *)tgt= *(uint64_t *) save;
1 by brian
clean slate
1097
}
1098
1099
654 by Brian Aker
Remove unused (yet more)
1100
static void update_func_str(Session *, struct st_mysql_sys_var *var,
1 by brian
clean slate
1101
                             void *tgt, const void *save)
1102
{
1103
  char *old= *(char **) tgt;
1104
  *(char **)tgt= *(char **) save;
1105
  if (var->flags & PLUGIN_VAR_MEMALLOC)
1106
  {
656.1.19 by Monty Taylor
Removed my_strdup from drizzled/
1107
    *(char **)tgt= strdup(*(char **) save);
477 by Monty Taylor
Removed my_free(). It turns out that it had been def'd to ignore the flags passed to it in the second arg anyway. Gotta love that.
1108
    free(old);
656.1.52 by Monty Taylor
Added more return value checks.
1109
    /*
1110
     * There isn't a _really_ good thing to do here until this whole set_var
1111
     * mess gets redesigned
1112
     */
1113
    if (tgt == NULL)
755.2.1 by Mark Atwood
replace sql_print_error etc with errmsg_print
1114
      errmsg_printf(ERRMSG_LVL_ERROR, _("Out of memory."));
656.1.52 by Monty Taylor
Added more return value checks.
1115
1 by brian
clean slate
1116
  }
1117
}
1118
1119
1120
/****************************************************************************
1121
  System Variables support
1122
****************************************************************************/
1123
1124
970.1.1 by Brian Aker
Removed dead passed variables.
1125
sys_var *find_sys_var(Session *, const char *str, uint32_t length)
1 by brian
clean slate
1126
{
1127
  sys_var *var;
1128
  sys_var_pluginvar *pi= NULL;
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
1129
  plugin::Handle *plugin;
1 by brian
clean slate
1130
658 by Brian Aker
Part removal of my_pthread.h
1131
  pthread_rwlock_rdlock(&LOCK_system_variables_hash);
1 by brian
clean slate
1132
  if ((var= intern_find_sys_var(str, length, false)) &&
1133
      (pi= var->cast_pluginvar()))
1134
  {
658 by Brian Aker
Part removal of my_pthread.h
1135
    pthread_rwlock_unlock(&LOCK_system_variables_hash);
971.1.19 by Monty Taylor
Remove most of plugin_ref. Fix several leaks (where the malloc was happening but never freed). One step away from no more plugin_ref. Yippee. It's so much easier the second time you try to do this.
1136
    if (!(plugin= pi->plugin))
1 by brian
clean slate
1137
      var= NULL; /* failed to lock it, it must be uninstalling */
971.1.19 by Monty Taylor
Remove most of plugin_ref. Fix several leaks (where the malloc was happening but never freed). One step away from no more plugin_ref. Yippee. It's so much easier the second time you try to do this.
1138
    else if (plugin->isInited == false)
1 by brian
clean slate
1139
    {
1140
      var= NULL;
1141
    }
1142
  }
1143
  else
658 by Brian Aker
Part removal of my_pthread.h
1144
    pthread_rwlock_unlock(&LOCK_system_variables_hash);
1 by brian
clean slate
1145
1146
  /*
1147
    If the variable exists but the plugin it is associated with is not ready
1148
    then the intern_plugin_lock did not raise an error, so we do it here.
1149
  */
1150
  if (pi && !var)
1151
    my_error(ER_UNKNOWN_SYSTEM_VARIABLE, MYF(0), (char*) str);
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
1152
  return(var);
1 by brian
clean slate
1153
}
1154
1155
1156
/*
1157
  called by register_var, construct_options and test_plugin_options.
1158
  Returns the 'bookmark' for the named variable.
1159
  LOCK_system_variables_hash should be at least read locked
1160
*/
138 by Brian Aker
Refactoring around sql_plugin.
1161
static st_bookmark *find_bookmark(const char *plugin, const char *name, int flags)
1 by brian
clean slate
1162
{
1163
  st_bookmark *result= NULL;
482 by Brian Aker
Remove uint.
1164
  uint32_t namelen, length, pluginlen= 0;
1 by brian
clean slate
1165
  char *varname, *p;
1166
520.1.21 by Brian Aker
THD -> Session rename
1167
  if (!(flags & PLUGIN_VAR_SessionLOCAL))
1 by brian
clean slate
1168
    return NULL;
1169
1170
  namelen= strlen(name);
1171
  if (plugin)
1172
    pluginlen= strlen(plugin) + 1;
1173
  length= namelen + pluginlen + 2;
656.1.1 by Monty Taylor
OOOh doggie. Got rid of my_alloca.
1174
  varname= (char*) malloc(length);
1 by brian
clean slate
1175
1176
  if (plugin)
1177
  {
673.2.1 by Toru Maesaka
First pass of replacing MySQL's strxmov with libc alternatives
1178
    sprintf(varname+1,"%s_%s",plugin,name);
1 by brian
clean slate
1179
    for (p= varname + 1; *p; p++)
1180
      if (*p == '-')
1181
        *p= '_';
1182
  }
1183
  else
1184
    memcpy(varname + 1, name, namelen + 1);
1185
1186
  varname[0]= flags & PLUGIN_VAR_TYPEMASK;
1187
1188
  result= (st_bookmark*) hash_search(&bookmark_hash,
481 by Brian Aker
Remove all of uchar.
1189
                                     (const unsigned char*) varname, length - 1);
1 by brian
clean slate
1190
656.1.1 by Monty Taylor
OOOh doggie. Got rid of my_alloca.
1191
  free(varname);
1 by brian
clean slate
1192
  return result;
1193
}
1194
1195
1196
/*
520.1.22 by Brian Aker
Second pass of thd cleanup
1197
  returns a bookmark for session-local variables, creating if neccessary.
1198
  returns null for non session-local variables.
1 by brian
clean slate
1199
  Requires that a write lock is obtained on LOCK_system_variables_hash
1200
*/
1201
static st_bookmark *register_var(const char *plugin, const char *name,
1202
                                 int flags)
1203
{
482 by Brian Aker
Remove uint.
1204
  uint32_t length= strlen(plugin) + strlen(name) + 3, size= 0, offset, new_size;
1 by brian
clean slate
1205
  st_bookmark *result;
1206
  char *varname, *p;
1207
520.1.21 by Brian Aker
THD -> Session rename
1208
  if (!(flags & PLUGIN_VAR_SessionLOCAL))
1 by brian
clean slate
1209
    return NULL;
1210
1211
  switch (flags & PLUGIN_VAR_TYPEMASK) {
1212
  case PLUGIN_VAR_BOOL:
937.2.12 by Stewart Smith
ensure correct alignment of all plugin variables. Manifesting as innodb_mysql test failure with SIGBUS on Sparc
1213
    size= ALIGN_SIZE(sizeof(bool));
1 by brian
clean slate
1214
    break;
1215
  case PLUGIN_VAR_INT:
937.2.12 by Stewart Smith
ensure correct alignment of all plugin variables. Manifesting as innodb_mysql test failure with SIGBUS on Sparc
1216
    size= ALIGN_SIZE(sizeof(int));
1 by brian
clean slate
1217
    break;
1218
  case PLUGIN_VAR_LONG:
1219
  case PLUGIN_VAR_ENUM:
937.2.12 by Stewart Smith
ensure correct alignment of all plugin variables. Manifesting as innodb_mysql test failure with SIGBUS on Sparc
1220
    size= ALIGN_SIZE(sizeof(long));
1 by brian
clean slate
1221
    break;
1222
  case PLUGIN_VAR_LONGLONG:
1223
  case PLUGIN_VAR_SET:
937.2.12 by Stewart Smith
ensure correct alignment of all plugin variables. Manifesting as innodb_mysql test failure with SIGBUS on Sparc
1224
    size= ALIGN_SIZE(sizeof(uint64_t));
1 by brian
clean slate
1225
    break;
1226
  case PLUGIN_VAR_STR:
937.2.12 by Stewart Smith
ensure correct alignment of all plugin variables. Manifesting as innodb_mysql test failure with SIGBUS on Sparc
1227
    size= ALIGN_SIZE(sizeof(char*));
1 by brian
clean slate
1228
    break;
1229
  default:
51.1.62 by Jay Pipes
Removed/replaced BUG symbols and standardized TRUE/FALSE
1230
    assert(0);
1 by brian
clean slate
1231
    return NULL;
1232
  };
1233
656.1.1 by Monty Taylor
OOOh doggie. Got rid of my_alloca.
1234
  varname= ((char*) malloc(length));
673.2.1 by Toru Maesaka
First pass of replacing MySQL's strxmov with libc alternatives
1235
  sprintf(varname+1, "%s_%s", plugin, name);
1 by brian
clean slate
1236
  for (p= varname + 1; *p; p++)
1237
    if (*p == '-')
1238
      *p= '_';
1239
1240
  if (!(result= find_bookmark(NULL, varname + 1, flags)))
1241
  {
1242
    result= (st_bookmark*) alloc_root(&plugin_mem_root,
1243
                                      sizeof(struct st_bookmark) + length-1);
1244
    varname[0]= flags & PLUGIN_VAR_TYPEMASK;
1245
    memcpy(result->key, varname, length);
1246
    result->name_len= length - 2;
1247
    result->offset= -1;
1248
51.1.62 by Jay Pipes
Removed/replaced BUG symbols and standardized TRUE/FALSE
1249
    assert(size && !(size & (size-1))); /* must be power of 2 */
1 by brian
clean slate
1250
1251
    offset= global_system_variables.dynamic_variables_size;
1252
    offset= (offset + size - 1) & ~(size - 1);
1253
    result->offset= (int) offset;
1254
1255
    new_size= (offset + size + 63) & ~63;
1256
1257
    if (new_size > global_variables_dynamic_size)
1258
    {
656.1.46 by Monty Taylor
More malloc return cleanups.
1259
      char* tmpptr= NULL;
1260
      if (!(tmpptr=
1261
              (char *)realloc(global_system_variables.dynamic_variables_ptr,
1262
                              new_size)))
1263
        return NULL;
1264
      global_system_variables.dynamic_variables_ptr= tmpptr;
1265
      tmpptr= NULL;
1266
      if (!(tmpptr=
1267
              (char *)realloc(max_system_variables.dynamic_variables_ptr,
1268
                              new_size)))
1269
        return NULL;
1270
      max_system_variables.dynamic_variables_ptr= tmpptr;
656.1.26 by Monty Taylor
Finally removed all of the my_malloc stuff.
1271
           
1 by brian
clean slate
1272
      /*
1273
        Clear the new variable value space. This is required for string
1274
        variables. If their value is non-NULL, it must point to a valid
1275
        string.
1276
      */
212.6.1 by Mats Kindahl
Replacing all bzero() calls with memset() calls and removing the bzero.c file.
1277
      memset(global_system_variables.dynamic_variables_ptr +
1278
             global_variables_dynamic_size, 0,
1279
             new_size - global_variables_dynamic_size);
1280
      memset(max_system_variables.dynamic_variables_ptr +
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
1281
             global_variables_dynamic_size, 0,
212.6.1 by Mats Kindahl
Replacing all bzero() calls with memset() calls and removing the bzero.c file.
1282
             new_size - global_variables_dynamic_size);
1 by brian
clean slate
1283
      global_variables_dynamic_size= new_size;
1284
    }
1285
1286
    global_system_variables.dynamic_variables_head= offset;
1287
    max_system_variables.dynamic_variables_head= offset;
1288
    global_system_variables.dynamic_variables_size= offset + size;
1289
    max_system_variables.dynamic_variables_size= offset + size;
1290
    global_system_variables.dynamic_variables_version++;
1291
    max_system_variables.dynamic_variables_version++;
1292
1293
    result->version= global_system_variables.dynamic_variables_version;
1294
1295
    /* this should succeed because we have already checked if a dup exists */
481 by Brian Aker
Remove all of uchar.
1296
    if (my_hash_insert(&bookmark_hash, (unsigned char*) result))
1 by brian
clean slate
1297
    {
1298
      fprintf(stderr, "failed to add placeholder to hash");
51.1.62 by Jay Pipes
Removed/replaced BUG symbols and standardized TRUE/FALSE
1299
      assert(0);
1 by brian
clean slate
1300
    }
1301
  }
656.1.1 by Monty Taylor
OOOh doggie. Got rid of my_alloca.
1302
  free(varname);
1 by brian
clean slate
1303
  return result;
1304
}
1305
1306
1307
/*
520.1.22 by Brian Aker
Second pass of thd cleanup
1308
  returns a pointer to the memory which holds the session-local variable or
1309
  a pointer to the global variable if session==null.
1 by brian
clean slate
1310
  If required, will sync with global variables if the requested variable
1311
  has not yet been allocated in the current thread.
1312
*/
520.1.22 by Brian Aker
Second pass of thd cleanup
1313
static unsigned char *intern_sys_var_ptr(Session* session, int offset, bool global_lock)
1 by brian
clean slate
1314
{
51.1.62 by Jay Pipes
Removed/replaced BUG symbols and standardized TRUE/FALSE
1315
  assert(offset >= 0);
895 by Brian Aker
Completion (?) of uint conversion.
1316
  assert((uint32_t)offset <= global_system_variables.dynamic_variables_head);
1 by brian
clean slate
1317
520.1.22 by Brian Aker
Second pass of thd cleanup
1318
  if (!session)
481 by Brian Aker
Remove all of uchar.
1319
    return (unsigned char*) global_system_variables.dynamic_variables_ptr + offset;
1 by brian
clean slate
1320
1321
  /*
1322
    dynamic_variables_head points to the largest valid offset
1323
  */
520.1.22 by Brian Aker
Second pass of thd cleanup
1324
  if (!session->variables.dynamic_variables_ptr ||
895 by Brian Aker
Completion (?) of uint conversion.
1325
      (uint32_t)offset > session->variables.dynamic_variables_head)
1 by brian
clean slate
1326
  {
482 by Brian Aker
Remove uint.
1327
    uint32_t idx;
1 by brian
clean slate
1328
658 by Brian Aker
Part removal of my_pthread.h
1329
    pthread_rwlock_rdlock(&LOCK_system_variables_hash);
1 by brian
clean slate
1330
656.1.46 by Monty Taylor
More malloc return cleanups.
1331
    char *tmpptr= NULL;
1332
    if (!(tmpptr= (char *)realloc(session->variables.dynamic_variables_ptr,
1333
                                  global_variables_dynamic_size)))
1334
      return NULL;
1335
    session->variables.dynamic_variables_ptr= tmpptr;
1 by brian
clean slate
1336
1337
    if (global_lock)
1338
      pthread_mutex_lock(&LOCK_global_system_variables);
1339
1340
    safe_mutex_assert_owner(&LOCK_global_system_variables);
1341
520.1.22 by Brian Aker
Second pass of thd cleanup
1342
    memcpy(session->variables.dynamic_variables_ptr +
1343
             session->variables.dynamic_variables_size,
1 by brian
clean slate
1344
           global_system_variables.dynamic_variables_ptr +
520.1.22 by Brian Aker
Second pass of thd cleanup
1345
             session->variables.dynamic_variables_size,
1 by brian
clean slate
1346
           global_system_variables.dynamic_variables_size -
520.1.22 by Brian Aker
Second pass of thd cleanup
1347
             session->variables.dynamic_variables_size);
1 by brian
clean slate
1348
1349
    /*
1350
      now we need to iterate through any newly copied 'defaults'
1351
      and if it is a string type with MEMALLOC flag, we need to strdup
1352
    */
1353
    for (idx= 0; idx < bookmark_hash.records; idx++)
1354
    {
1355
      sys_var_pluginvar *pi;
1356
      sys_var *var;
1357
      st_bookmark *v= (st_bookmark*) hash_element(&bookmark_hash,idx);
1358
520.1.22 by Brian Aker
Second pass of thd cleanup
1359
      if (v->version <= session->variables.dynamic_variables_version ||
1 by brian
clean slate
1360
          !(var= intern_find_sys_var(v->key + 1, v->name_len, true)) ||
1361
          !(pi= var->cast_pluginvar()) ||
1362
          v->key[0] != (pi->plugin_var->flags & PLUGIN_VAR_TYPEMASK))
1363
        continue;
1364
1365
      /* Here we do anything special that may be required of the data types */
1366
1367
      if ((pi->plugin_var->flags & PLUGIN_VAR_TYPEMASK) == PLUGIN_VAR_STR &&
1368
          pi->plugin_var->flags & PLUGIN_VAR_MEMALLOC)
1369
      {
520.1.22 by Brian Aker
Second pass of thd cleanup
1370
         char **pp= (char**) (session->variables.dynamic_variables_ptr +
1 by brian
clean slate
1371
                             *(int*)(pi->plugin_var + 1));
1372
         if ((*pp= *(char**) (global_system_variables.dynamic_variables_ptr +
1373
                             *(int*)(pi->plugin_var + 1))))
656.1.19 by Monty Taylor
Removed my_strdup from drizzled/
1374
           *pp= strdup(*pp);
656.1.52 by Monty Taylor
Added more return value checks.
1375
         if (*pp == NULL)
1376
           return NULL;
1 by brian
clean slate
1377
      }
1378
    }
1379
1380
    if (global_lock)
1381
      pthread_mutex_unlock(&LOCK_global_system_variables);
1382
520.1.22 by Brian Aker
Second pass of thd cleanup
1383
    session->variables.dynamic_variables_version=
1 by brian
clean slate
1384
           global_system_variables.dynamic_variables_version;
520.1.22 by Brian Aker
Second pass of thd cleanup
1385
    session->variables.dynamic_variables_head=
1 by brian
clean slate
1386
           global_system_variables.dynamic_variables_head;
520.1.22 by Brian Aker
Second pass of thd cleanup
1387
    session->variables.dynamic_variables_size=
1 by brian
clean slate
1388
           global_system_variables.dynamic_variables_size;
1389
658 by Brian Aker
Part removal of my_pthread.h
1390
    pthread_rwlock_unlock(&LOCK_system_variables_hash);
1 by brian
clean slate
1391
  }
520.1.22 by Brian Aker
Second pass of thd cleanup
1392
  return (unsigned char*)session->variables.dynamic_variables_ptr + offset;
1393
}
1394
1395
static bool *mysql_sys_var_ptr_bool(Session* a_session, int offset)
1396
{
1397
  return (bool *)intern_sys_var_ptr(a_session, offset, true);
1398
}
1399
1400
static int *mysql_sys_var_ptr_int(Session* a_session, int offset)
1401
{
1402
  return (int *)intern_sys_var_ptr(a_session, offset, true);
1403
}
1404
1405
static long *mysql_sys_var_ptr_long(Session* a_session, int offset)
1406
{
1407
  return (long *)intern_sys_var_ptr(a_session, offset, true);
1408
}
1409
1410
static int64_t *mysql_sys_var_ptr_int64_t(Session* a_session, int offset)
1411
{
1412
  return (int64_t *)intern_sys_var_ptr(a_session, offset, true);
1413
}
1414
1415
static char **mysql_sys_var_ptr_str(Session* a_session, int offset)
1416
{
1417
  return (char **)intern_sys_var_ptr(a_session, offset, true);
1418
}
1419
1420
static uint64_t *mysql_sys_var_ptr_set(Session* a_session, int offset)
1421
{
1422
  return (uint64_t *)intern_sys_var_ptr(a_session, offset, true);
1423
}
1424
1425
static unsigned long *mysql_sys_var_ptr_enum(Session* a_session, int offset)
1426
{
1427
  return (unsigned long *)intern_sys_var_ptr(a_session, offset, true);
1428
}
1429
1430
1431
void plugin_sessionvar_init(Session *session)
1432
{
971.1.21 by Monty Taylor
Store StorageEngine in system variables, rather than storage engine plugin.
1433
  session->variables.storage_engine= NULL;
520.1.22 by Brian Aker
Second pass of thd cleanup
1434
  cleanup_variables(session, &session->variables);
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
1435
520.1.22 by Brian Aker
Second pass of thd cleanup
1436
  session->variables= global_system_variables;
971.1.21 by Monty Taylor
Store StorageEngine in system variables, rather than storage engine plugin.
1437
  session->variables.storage_engine= NULL;
1 by brian
clean slate
1438
1439
  /* we are going to allocate these lazily */
520.1.22 by Brian Aker
Second pass of thd cleanup
1440
  session->variables.dynamic_variables_version= 0;
1441
  session->variables.dynamic_variables_size= 0;
1442
  session->variables.dynamic_variables_ptr= 0;
1 by brian
clean slate
1443
971.1.21 by Monty Taylor
Store StorageEngine in system variables, rather than storage engine plugin.
1444
  session->variables.storage_engine= global_system_variables.storage_engine;
1 by brian
clean slate
1445
}
1446
1447
1448
/*
1449
  Unlocks all system variables which hold a reference
1450
*/
654 by Brian Aker
Remove unused (yet more)
1451
static void unlock_variables(Session *, struct system_variables *vars)
1 by brian
clean slate
1452
{
971.1.21 by Monty Taylor
Store StorageEngine in system variables, rather than storage engine plugin.
1453
  vars->storage_engine= NULL;
1 by brian
clean slate
1454
}
1455
1456
1457
/*
1458
  Frees memory used by system variables
1459
1460
  Unlike plugin_vars_free_values() it frees all variables of all plugins,
1461
  it's used on shutdown.
1462
*/
520.1.22 by Brian Aker
Second pass of thd cleanup
1463
static void cleanup_variables(Session *session, struct system_variables *vars)
1 by brian
clean slate
1464
{
1465
  st_bookmark *v;
1466
  sys_var_pluginvar *pivar;
1467
  sys_var *var;
1468
  int flags;
482 by Brian Aker
Remove uint.
1469
  uint32_t idx;
1 by brian
clean slate
1470
658 by Brian Aker
Part removal of my_pthread.h
1471
  pthread_rwlock_rdlock(&LOCK_system_variables_hash);
1 by brian
clean slate
1472
  for (idx= 0; idx < bookmark_hash.records; idx++)
1473
  {
1474
    v= (st_bookmark*) hash_element(&bookmark_hash, idx);
1475
    if (v->version > vars->dynamic_variables_version ||
1476
        !(var= intern_find_sys_var(v->key + 1, v->name_len, true)) ||
1477
        !(pivar= var->cast_pluginvar()) ||
1478
        v->key[0] != (pivar->plugin_var->flags & PLUGIN_VAR_TYPEMASK))
1479
      continue;
1480
1481
    flags= pivar->plugin_var->flags;
1482
1483
    if ((flags & PLUGIN_VAR_TYPEMASK) == PLUGIN_VAR_STR &&
520.1.21 by Brian Aker
THD -> Session rename
1484
        flags & PLUGIN_VAR_SessionLOCAL && flags & PLUGIN_VAR_MEMALLOC)
1 by brian
clean slate
1485
    {
520.1.22 by Brian Aker
Second pass of thd cleanup
1486
      char **ptr= (char**) pivar->real_value_ptr(session, OPT_SESSION);
477 by Monty Taylor
Removed my_free(). It turns out that it had been def'd to ignore the flags passed to it in the second arg anyway. Gotta love that.
1487
      free(*ptr);
1 by brian
clean slate
1488
      *ptr= NULL;
1489
    }
1490
  }
658 by Brian Aker
Part removal of my_pthread.h
1491
  pthread_rwlock_unlock(&LOCK_system_variables_hash);
1 by brian
clean slate
1492
971.1.21 by Monty Taylor
Store StorageEngine in system variables, rather than storage engine plugin.
1493
  assert(vars->storage_engine == NULL);
1 by brian
clean slate
1494
477 by Monty Taylor
Removed my_free(). It turns out that it had been def'd to ignore the flags passed to it in the second arg anyway. Gotta love that.
1495
  free(vars->dynamic_variables_ptr);
1 by brian
clean slate
1496
  vars->dynamic_variables_ptr= NULL;
1497
  vars->dynamic_variables_size= 0;
1498
  vars->dynamic_variables_version= 0;
1499
}
1500
1501
520.1.22 by Brian Aker
Second pass of thd cleanup
1502
void plugin_sessionvar_cleanup(Session *session)
1 by brian
clean slate
1503
{
520.1.22 by Brian Aker
Second pass of thd cleanup
1504
  unlock_variables(session, &session->variables);
1505
  cleanup_variables(session, &session->variables);
1 by brian
clean slate
1506
}
1507
1508
1509
/**
1510
  @brief Free values of thread variables of a plugin.
1511
1512
  This must be called before a plugin is deleted. Otherwise its
1513
  variables are no longer accessible and the value space is lost. Note
1514
  that only string values with PLUGIN_VAR_MEMALLOC are allocated and
1515
  must be freed.
1516
1517
  @param[in]        vars        Chain of system variables of a plugin
1518
*/
1519
1520
static void plugin_vars_free_values(sys_var *vars)
1521
{
1522
1055.2.20 by Jay Pipes
Refactors sys_var class -- doxygenates and documents the class members and functions. Protects all member variables and adds public getters/setters.
1523
  for (sys_var *var= vars; var; var= var->getNext())
1 by brian
clean slate
1524
  {
1525
    sys_var_pluginvar *piv= var->cast_pluginvar();
1526
    if (piv &&
1527
        ((piv->plugin_var->flags & PLUGIN_VAR_TYPEMASK) == PLUGIN_VAR_STR) &&
1528
        (piv->plugin_var->flags & PLUGIN_VAR_MEMALLOC))
1529
    {
1530
      /* Free the string from global_system_variables. */
1531
      char **valptr= (char**) piv->real_value_ptr(NULL, OPT_GLOBAL);
477 by Monty Taylor
Removed my_free(). It turns out that it had been def'd to ignore the flags passed to it in the second arg anyway. Gotta love that.
1532
      free(*valptr);
1 by brian
clean slate
1533
      *valptr= NULL;
1534
    }
1535
  }
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
1536
  return;
1 by brian
clean slate
1537
}
1538
1539
1540
bool sys_var_pluginvar::check_update_type(Item_result type)
1541
{
1542
  if (is_readonly())
1543
    return 1;
1544
  switch (plugin_var->flags & PLUGIN_VAR_TYPEMASK) {
1545
  case PLUGIN_VAR_INT:
1546
  case PLUGIN_VAR_LONG:
1547
  case PLUGIN_VAR_LONGLONG:
1548
    return type != INT_RESULT;
1549
  case PLUGIN_VAR_STR:
1550
    return type != STRING_RESULT;
1551
  default:
1552
    return 0;
1553
  }
1554
}
1555
1556
1557
SHOW_TYPE sys_var_pluginvar::show_type()
1558
{
1559
  switch (plugin_var->flags & PLUGIN_VAR_TYPEMASK) {
1560
  case PLUGIN_VAR_BOOL:
1561
    return SHOW_MY_BOOL;
1562
  case PLUGIN_VAR_INT:
1563
    return SHOW_INT;
1564
  case PLUGIN_VAR_LONG:
1565
    return SHOW_LONG;
1566
  case PLUGIN_VAR_LONGLONG:
1567
    return SHOW_LONGLONG;
1568
  case PLUGIN_VAR_STR:
1569
    return SHOW_CHAR_PTR;
1570
  case PLUGIN_VAR_ENUM:
1571
  case PLUGIN_VAR_SET:
1572
    return SHOW_CHAR;
1573
  default:
51.1.62 by Jay Pipes
Removed/replaced BUG symbols and standardized TRUE/FALSE
1574
    assert(0);
1 by brian
clean slate
1575
    return SHOW_UNDEF;
1576
  }
1577
}
1578
1579
520.1.22 by Brian Aker
Second pass of thd cleanup
1580
unsigned char* sys_var_pluginvar::real_value_ptr(Session *session, enum_var_type type)
1 by brian
clean slate
1581
{
520.1.22 by Brian Aker
Second pass of thd cleanup
1582
  assert(session || (type == OPT_GLOBAL));
520.1.21 by Brian Aker
THD -> Session rename
1583
  if (plugin_var->flags & PLUGIN_VAR_SessionLOCAL)
1 by brian
clean slate
1584
  {
1585
    if (type == OPT_GLOBAL)
520.1.22 by Brian Aker
Second pass of thd cleanup
1586
      session= NULL;
1 by brian
clean slate
1587
520.1.22 by Brian Aker
Second pass of thd cleanup
1588
    return intern_sys_var_ptr(session, *(int*) (plugin_var+1), false);
1 by brian
clean slate
1589
  }
481 by Brian Aker
Remove all of uchar.
1590
  return *(unsigned char**) (plugin_var+1);
1 by brian
clean slate
1591
}
1592
1593
1594
TYPELIB* sys_var_pluginvar::plugin_var_typelib(void)
1595
{
520.1.21 by Brian Aker
THD -> Session rename
1596
  switch (plugin_var->flags & (PLUGIN_VAR_TYPEMASK | PLUGIN_VAR_SessionLOCAL)) {
1 by brian
clean slate
1597
  case PLUGIN_VAR_ENUM:
1598
    return ((sysvar_enum_t *)plugin_var)->typelib;
1599
  case PLUGIN_VAR_SET:
1600
    return ((sysvar_set_t *)plugin_var)->typelib;
520.1.21 by Brian Aker
THD -> Session rename
1601
  case PLUGIN_VAR_ENUM | PLUGIN_VAR_SessionLOCAL:
520.1.22 by Brian Aker
Second pass of thd cleanup
1602
    return ((sessionvar_enum_t *)plugin_var)->typelib;
520.1.21 by Brian Aker
THD -> Session rename
1603
  case PLUGIN_VAR_SET | PLUGIN_VAR_SessionLOCAL:
520.1.22 by Brian Aker
Second pass of thd cleanup
1604
    return ((sessionvar_set_t *)plugin_var)->typelib;
1 by brian
clean slate
1605
  default:
1606
    return NULL;
1607
  }
1608
  return NULL;
1609
}
1610
1611
779.3.10 by Monty Taylor
Turned on -Wshadow.
1612
unsigned char* sys_var_pluginvar::value_ptr(Session *session, enum_var_type type, const LEX_STRING *)
1 by brian
clean slate
1613
{
481 by Brian Aker
Remove all of uchar.
1614
  unsigned char* result;
1 by brian
clean slate
1615
520.1.22 by Brian Aker
Second pass of thd cleanup
1616
  result= real_value_ptr(session, type);
1 by brian
clean slate
1617
1618
  if ((plugin_var->flags & PLUGIN_VAR_TYPEMASK) == PLUGIN_VAR_ENUM)
481 by Brian Aker
Remove all of uchar.
1619
    result= (unsigned char*) get_type(plugin_var_typelib(), *(ulong*)result);
1 by brian
clean slate
1620
  else if ((plugin_var->flags & PLUGIN_VAR_TYPEMASK) == PLUGIN_VAR_SET)
1621
  {
1622
    char buffer[STRING_BUFFER_USUAL_SIZE];
1623
    String str(buffer, sizeof(buffer), system_charset_info);
1624
    TYPELIB *typelib= plugin_var_typelib();
151 by Brian Aker
Ulonglong to uint64_t
1625
    uint64_t mask= 1, value= *(uint64_t*) result;
482 by Brian Aker
Remove uint.
1626
    uint32_t i;
1 by brian
clean slate
1627
1628
    str.length(0);
1629
    for (i= 0; i < typelib->count; i++, mask<<=1)
1630
    {
1631
      if (!(value & mask))
1632
        continue;
1633
      str.append(typelib->type_names[i], typelib->type_lengths[i]);
1634
      str.append(',');
1635
    }
1636
481 by Brian Aker
Remove all of uchar.
1637
    result= (unsigned char*) "";
1 by brian
clean slate
1638
    if (str.length())
520.1.22 by Brian Aker
Second pass of thd cleanup
1639
      result= (unsigned char*) session->strmake(str.ptr(), str.length()-1);
1 by brian
clean slate
1640
  }
1641
  return result;
1642
}
1643
1644
520.1.22 by Brian Aker
Second pass of thd cleanup
1645
bool sys_var_pluginvar::check(Session *session, set_var *var)
1 by brian
clean slate
1646
{
1647
  st_item_value_holder value;
51.1.62 by Jay Pipes
Removed/replaced BUG symbols and standardized TRUE/FALSE
1648
  assert(is_readonly() || plugin_var->check);
1 by brian
clean slate
1649
1650
  value.value_type= item_value_type;
1651
  value.val_str= item_val_str;
1652
  value.val_int= item_val_int;
1653
  value.val_real= item_val_real;
1654
  value.item= var->value;
1655
1656
  return is_readonly() ||
520.1.22 by Brian Aker
Second pass of thd cleanup
1657
         plugin_var->check(session, plugin_var, &var->save_result, &value);
1 by brian
clean slate
1658
}
1659
1660
520.1.22 by Brian Aker
Second pass of thd cleanup
1661
void sys_var_pluginvar::set_default(Session *session, enum_var_type type)
1 by brian
clean slate
1662
{
1663
  const void *src;
1664
  void *tgt;
1665
51.1.62 by Jay Pipes
Removed/replaced BUG symbols and standardized TRUE/FALSE
1666
  assert(is_readonly() || plugin_var->update);
1 by brian
clean slate
1667
1668
  if (is_readonly())
1669
    return;
1670
1671
  pthread_mutex_lock(&LOCK_global_system_variables);
520.1.22 by Brian Aker
Second pass of thd cleanup
1672
  tgt= real_value_ptr(session, type);
1 by brian
clean slate
1673
  src= ((void **) (plugin_var + 1) + 1);
1674
520.1.21 by Brian Aker
THD -> Session rename
1675
  if (plugin_var->flags & PLUGIN_VAR_SessionLOCAL)
1 by brian
clean slate
1676
  {
1677
    if (type != OPT_GLOBAL)
520.1.22 by Brian Aker
Second pass of thd cleanup
1678
      src= real_value_ptr(session, OPT_GLOBAL);
1 by brian
clean slate
1679
    else
1680
    switch (plugin_var->flags & PLUGIN_VAR_TYPEMASK) {
1681
	case PLUGIN_VAR_INT:
520.1.22 by Brian Aker
Second pass of thd cleanup
1682
	  src= &((sessionvar_uint_t*) plugin_var)->def_val;
1 by brian
clean slate
1683
	  break;
1684
	case PLUGIN_VAR_LONG:
520.1.22 by Brian Aker
Second pass of thd cleanup
1685
	  src= &((sessionvar_ulong_t*) plugin_var)->def_val;
1 by brian
clean slate
1686
	  break;
1687
	case PLUGIN_VAR_LONGLONG:
520.1.22 by Brian Aker
Second pass of thd cleanup
1688
	  src= &((sessionvar_uint64_t_t*) plugin_var)->def_val;
1 by brian
clean slate
1689
	  break;
1690
	case PLUGIN_VAR_ENUM:
520.1.22 by Brian Aker
Second pass of thd cleanup
1691
	  src= &((sessionvar_enum_t*) plugin_var)->def_val;
1 by brian
clean slate
1692
	  break;
1693
	case PLUGIN_VAR_SET:
520.1.22 by Brian Aker
Second pass of thd cleanup
1694
	  src= &((sessionvar_set_t*) plugin_var)->def_val;
1 by brian
clean slate
1695
	  break;
1696
	case PLUGIN_VAR_BOOL:
520.1.22 by Brian Aker
Second pass of thd cleanup
1697
	  src= &((sessionvar_bool_t*) plugin_var)->def_val;
1 by brian
clean slate
1698
	  break;
1699
	case PLUGIN_VAR_STR:
520.1.22 by Brian Aker
Second pass of thd cleanup
1700
	  src= &((sessionvar_str_t*) plugin_var)->def_val;
1 by brian
clean slate
1701
	  break;
1702
	default:
51.1.62 by Jay Pipes
Removed/replaced BUG symbols and standardized TRUE/FALSE
1703
	  assert(0);
1 by brian
clean slate
1704
	}
1705
  }
1706
520.1.22 by Brian Aker
Second pass of thd cleanup
1707
  /* session must equal current_session if PLUGIN_VAR_SessionLOCAL flag is set */
520.1.21 by Brian Aker
THD -> Session rename
1708
  assert(!(plugin_var->flags & PLUGIN_VAR_SessionLOCAL) ||
520.1.22 by Brian Aker
Second pass of thd cleanup
1709
              session == current_session);
1 by brian
clean slate
1710
520.1.21 by Brian Aker
THD -> Session rename
1711
  if (!(plugin_var->flags & PLUGIN_VAR_SessionLOCAL) || type == OPT_GLOBAL)
1 by brian
clean slate
1712
  {
520.1.22 by Brian Aker
Second pass of thd cleanup
1713
    plugin_var->update(session, plugin_var, tgt, src);
1 by brian
clean slate
1714
    pthread_mutex_unlock(&LOCK_global_system_variables);
1715
  }
1716
  else
1717
  {
1718
    pthread_mutex_unlock(&LOCK_global_system_variables);
520.1.22 by Brian Aker
Second pass of thd cleanup
1719
    plugin_var->update(session, plugin_var, tgt, src);
1 by brian
clean slate
1720
  }
1721
}
1722
1723
520.1.22 by Brian Aker
Second pass of thd cleanup
1724
bool sys_var_pluginvar::update(Session *session, set_var *var)
1 by brian
clean slate
1725
{
1726
  void *tgt;
1727
51.1.62 by Jay Pipes
Removed/replaced BUG symbols and standardized TRUE/FALSE
1728
  assert(is_readonly() || plugin_var->update);
1 by brian
clean slate
1729
520.1.22 by Brian Aker
Second pass of thd cleanup
1730
  /* session must equal current_session if PLUGIN_VAR_SessionLOCAL flag is set */
520.1.21 by Brian Aker
THD -> Session rename
1731
  assert(!(plugin_var->flags & PLUGIN_VAR_SessionLOCAL) ||
520.1.22 by Brian Aker
Second pass of thd cleanup
1732
              session == current_session);
1 by brian
clean slate
1733
1734
  if (is_readonly())
1735
    return 1;
1736
1737
  pthread_mutex_lock(&LOCK_global_system_variables);
520.1.22 by Brian Aker
Second pass of thd cleanup
1738
  tgt= real_value_ptr(session, var->type);
1 by brian
clean slate
1739
520.1.21 by Brian Aker
THD -> Session rename
1740
  if (!(plugin_var->flags & PLUGIN_VAR_SessionLOCAL) || var->type == OPT_GLOBAL)
1 by brian
clean slate
1741
  {
1742
    /* variable we are updating has global scope, so we unlock after updating */
520.1.22 by Brian Aker
Second pass of thd cleanup
1743
    plugin_var->update(session, plugin_var, tgt, &var->save_result);
1 by brian
clean slate
1744
    pthread_mutex_unlock(&LOCK_global_system_variables);
1745
  }
1746
  else
1747
  {
1748
    pthread_mutex_unlock(&LOCK_global_system_variables);
520.1.22 by Brian Aker
Second pass of thd cleanup
1749
    plugin_var->update(session, plugin_var, tgt, &var->save_result);
1 by brian
clean slate
1750
  }
1751
 return 0;
1752
}
1753
1754
1755
#define OPTION_SET_LIMITS(type, options, opt) \
322.2.2 by Mats Kindahl
Hiding THD::proc_info field and providing a setter and getter.
1756
  options->var_type= type;                    \
1757
  options->def_value= (opt)->def_val;         \
1758
  options->min_value= (opt)->min_val;         \
1759
  options->max_value= (opt)->max_val;         \
1 by brian
clean slate
1760
  options->block_size= (long) (opt)->blk_sz
1761
1762
1763
static void plugin_opt_set_limits(struct my_option *options,
1764
                                  const struct st_mysql_sys_var *opt)
1765
{
1766
  options->sub_size= 0;
1767
1768
  switch (opt->flags & (PLUGIN_VAR_TYPEMASK |
520.1.21 by Brian Aker
THD -> Session rename
1769
                        PLUGIN_VAR_UNSIGNED | PLUGIN_VAR_SessionLOCAL)) {
1 by brian
clean slate
1770
  /* global system variables */
1771
  case PLUGIN_VAR_INT:
1772
    OPTION_SET_LIMITS(GET_INT, options, (sysvar_int_t*) opt);
1773
    break;
1774
  case PLUGIN_VAR_INT | PLUGIN_VAR_UNSIGNED:
1775
    OPTION_SET_LIMITS(GET_UINT, options, (sysvar_uint_t*) opt);
1776
    break;
1777
  case PLUGIN_VAR_LONG:
1778
    OPTION_SET_LIMITS(GET_LONG, options, (sysvar_long_t*) opt);
1779
    break;
1780
  case PLUGIN_VAR_LONG | PLUGIN_VAR_UNSIGNED:
896.4.16 by Stewart Smith
for getopt, replace GET_ULONG with GET_UINT32.
1781
    OPTION_SET_LIMITS(GET_ULONG_IS_FAIL, options, (sysvar_ulong_t*) opt);
1 by brian
clean slate
1782
    break;
1783
  case PLUGIN_VAR_LONGLONG:
152 by Brian Aker
longlong replacement
1784
    OPTION_SET_LIMITS(GET_LL, options, (sysvar_int64_t_t*) opt);
1 by brian
clean slate
1785
    break;
1786
  case PLUGIN_VAR_LONGLONG | PLUGIN_VAR_UNSIGNED:
151 by Brian Aker
Ulonglong to uint64_t
1787
    OPTION_SET_LIMITS(GET_ULL, options, (sysvar_uint64_t_t*) opt);
1 by brian
clean slate
1788
    break;
1789
  case PLUGIN_VAR_ENUM:
1790
    options->var_type= GET_ENUM;
1791
    options->typelib= ((sysvar_enum_t*) opt)->typelib;
1792
    options->def_value= ((sysvar_enum_t*) opt)->def_val;
1793
    options->min_value= options->block_size= 0;
1794
    options->max_value= options->typelib->count - 1;
1795
    break;
1796
  case PLUGIN_VAR_SET:
1797
    options->var_type= GET_SET;
1798
    options->typelib= ((sysvar_set_t*) opt)->typelib;
1799
    options->def_value= ((sysvar_set_t*) opt)->def_val;
1800
    options->min_value= options->block_size= 0;
398.1.8 by Monty Taylor
Enabled -Wlong-long.
1801
    options->max_value= (1UL << options->typelib->count) - 1;
1 by brian
clean slate
1802
    break;
1803
  case PLUGIN_VAR_BOOL:
1804
    options->var_type= GET_BOOL;
1805
    options->def_value= ((sysvar_bool_t*) opt)->def_val;
1806
    break;
1807
  case PLUGIN_VAR_STR:
1808
    options->var_type= ((opt->flags & PLUGIN_VAR_MEMALLOC) ?
1809
                        GET_STR_ALLOC : GET_STR);
157 by Brian Aker
Second pass cleanup on removal of my_uint types
1810
    options->def_value= (intptr_t) ((sysvar_str_t*) opt)->def_val;
1 by brian
clean slate
1811
    break;
1812
  /* threadlocal variables */
520.1.21 by Brian Aker
THD -> Session rename
1813
  case PLUGIN_VAR_INT | PLUGIN_VAR_SessionLOCAL:
520.1.22 by Brian Aker
Second pass of thd cleanup
1814
    OPTION_SET_LIMITS(GET_INT, options, (sessionvar_int_t*) opt);
1 by brian
clean slate
1815
    break;
520.1.21 by Brian Aker
THD -> Session rename
1816
  case PLUGIN_VAR_INT | PLUGIN_VAR_UNSIGNED | PLUGIN_VAR_SessionLOCAL:
520.1.22 by Brian Aker
Second pass of thd cleanup
1817
    OPTION_SET_LIMITS(GET_UINT, options, (sessionvar_uint_t*) opt);
1 by brian
clean slate
1818
    break;
520.1.21 by Brian Aker
THD -> Session rename
1819
  case PLUGIN_VAR_LONG | PLUGIN_VAR_SessionLOCAL:
520.1.22 by Brian Aker
Second pass of thd cleanup
1820
    OPTION_SET_LIMITS(GET_LONG, options, (sessionvar_long_t*) opt);
1 by brian
clean slate
1821
    break;
520.1.21 by Brian Aker
THD -> Session rename
1822
  case PLUGIN_VAR_LONG | PLUGIN_VAR_UNSIGNED | PLUGIN_VAR_SessionLOCAL:
896.4.16 by Stewart Smith
for getopt, replace GET_ULONG with GET_UINT32.
1823
    OPTION_SET_LIMITS(GET_ULONG_IS_FAIL, options, (sessionvar_ulong_t*) opt);
1 by brian
clean slate
1824
    break;
520.1.21 by Brian Aker
THD -> Session rename
1825
  case PLUGIN_VAR_LONGLONG | PLUGIN_VAR_SessionLOCAL:
520.1.22 by Brian Aker
Second pass of thd cleanup
1826
    OPTION_SET_LIMITS(GET_LL, options, (sessionvar_int64_t_t*) opt);
1 by brian
clean slate
1827
    break;
520.1.21 by Brian Aker
THD -> Session rename
1828
  case PLUGIN_VAR_LONGLONG | PLUGIN_VAR_UNSIGNED | PLUGIN_VAR_SessionLOCAL:
520.1.22 by Brian Aker
Second pass of thd cleanup
1829
    OPTION_SET_LIMITS(GET_ULL, options, (sessionvar_uint64_t_t*) opt);
1 by brian
clean slate
1830
    break;
520.1.21 by Brian Aker
THD -> Session rename
1831
  case PLUGIN_VAR_ENUM | PLUGIN_VAR_SessionLOCAL:
1 by brian
clean slate
1832
    options->var_type= GET_ENUM;
520.1.22 by Brian Aker
Second pass of thd cleanup
1833
    options->typelib= ((sessionvar_enum_t*) opt)->typelib;
1834
    options->def_value= ((sessionvar_enum_t*) opt)->def_val;
1 by brian
clean slate
1835
    options->min_value= options->block_size= 0;
1836
    options->max_value= options->typelib->count - 1;
1837
    break;
520.1.21 by Brian Aker
THD -> Session rename
1838
  case PLUGIN_VAR_SET | PLUGIN_VAR_SessionLOCAL:
1 by brian
clean slate
1839
    options->var_type= GET_SET;
520.1.22 by Brian Aker
Second pass of thd cleanup
1840
    options->typelib= ((sessionvar_set_t*) opt)->typelib;
1841
    options->def_value= ((sessionvar_set_t*) opt)->def_val;
1 by brian
clean slate
1842
    options->min_value= options->block_size= 0;
398.1.8 by Monty Taylor
Enabled -Wlong-long.
1843
    options->max_value= (1UL << options->typelib->count) - 1;
1 by brian
clean slate
1844
    break;
520.1.21 by Brian Aker
THD -> Session rename
1845
  case PLUGIN_VAR_BOOL | PLUGIN_VAR_SessionLOCAL:
1 by brian
clean slate
1846
    options->var_type= GET_BOOL;
520.1.22 by Brian Aker
Second pass of thd cleanup
1847
    options->def_value= ((sessionvar_bool_t*) opt)->def_val;
1 by brian
clean slate
1848
    break;
520.1.21 by Brian Aker
THD -> Session rename
1849
  case PLUGIN_VAR_STR | PLUGIN_VAR_SessionLOCAL:
1 by brian
clean slate
1850
    options->var_type= ((opt->flags & PLUGIN_VAR_MEMALLOC) ?
1851
                        GET_STR_ALLOC : GET_STR);
520.1.22 by Brian Aker
Second pass of thd cleanup
1852
    options->def_value= (intptr_t) ((sessionvar_str_t*) opt)->def_val;
1 by brian
clean slate
1853
    break;
1854
  default:
51.1.62 by Jay Pipes
Removed/replaced BUG symbols and standardized TRUE/FALSE
1855
    assert(0);
1 by brian
clean slate
1856
  }
1857
  options->arg_type= REQUIRED_ARG;
1858
  if (opt->flags & PLUGIN_VAR_NOCMDARG)
1859
    options->arg_type= NO_ARG;
1860
  if (opt->flags & PLUGIN_VAR_OPCMDARG)
1861
    options->arg_type= OPT_ARG;
1862
}
1863
143 by Brian Aker
Bool cleanup.
1864
extern "C" bool get_one_plugin_option(int optid, const struct my_option *,
1 by brian
clean slate
1865
                                         char *);
1866
654 by Brian Aker
Remove unused (yet more)
1867
bool get_one_plugin_option(int, const struct my_option *, char *)
1 by brian
clean slate
1868
{
1869
  return 0;
1870
}
1871
1872
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
1873
static int construct_options(MEM_ROOT *mem_root, plugin::Handle *tmp,
138 by Brian Aker
Refactoring around sql_plugin.
1874
                             my_option *options, bool can_disable)
1 by brian
clean slate
1875
{
1093.3.4 by Monty Taylor
Naming cleanups.
1876
  const char *plugin_name= tmp->getManifest().name;
482 by Brian Aker
Remove uint.
1877
  uint32_t namelen= strlen(plugin_name), optnamelen;
1878
  uint32_t buffer_length= namelen * 4 + (can_disable ? 75 : 10);
1119.6.1 by Stewart Smith
remove nasty malloc() optimisation in --help plugin for sql_plugin. Also document the general turdiness of this area of code.
1879
  char *name= (char*) alloc_root(mem_root, buffer_length);
1880
  bool *enabled_value= (bool*) alloc_root(mem_root, sizeof(bool));
1 by brian
clean slate
1881
  char *optname, *p;
1882
  int index= 0, offset= 0;
1883
  st_mysql_sys_var *opt, **plugin_option;
1884
  st_bookmark *v;
1885
1886
  /* support --skip-plugin-foo syntax */
1887
  memcpy(name, plugin_name, namelen + 1);
383.1.12 by Brian Aker
Much closer toward UTF8 being around all the time...
1888
  my_casedn_str(&my_charset_utf8_general_ci, name);
673.2.1 by Toru Maesaka
First pass of replacing MySQL's strxmov with libc alternatives
1889
  sprintf(name+namelen+1, "plugin-%s", name);
1 by brian
clean slate
1890
  /* Now we have namelen + 1 + 7 + namelen + 1 == namelen * 2 + 9. */
1891
1892
  for (p= name + namelen*2 + 8; p > name; p--)
1893
    if (*p == '_')
1894
      *p= '-';
1895
1896
  if (can_disable)
1897
  {
673.2.1 by Toru Maesaka
First pass of replacing MySQL's strxmov with libc alternatives
1898
    sprintf(name+namelen*2+10,
1899
            "Enable %s plugin. Disable with --skip-%s (will save memory).",
1900
            plugin_name, name);
1 by brian
clean slate
1901
    /*
1902
      Now we have namelen * 2 + 10 (one char unused) + 7 + namelen + 9 +
1903
      20 + namelen + 20 + 1 == namelen * 4 + 67.
1904
    */
1905
1906
    options[0].comment= name + namelen*2 + 10;
1907
  }
1908
1119.6.1 by Stewart Smith
remove nasty malloc() optimisation in --help plugin for sql_plugin. Also document the general turdiness of this area of code.
1909
  /*
1910
    This whole code around variables and command line parameters is turd
1911
    soup.
1912
1913
    e.g. the below assignemnt of having the plugin alaways enabled is never
1914
    changed so that './drizzled --skip-innodb --help' shows innodb as enabled.
1915
1916
    But this is just as broken as it was in MySQL and properly fixing everything
1917
    is a decent amount of "future work"
1918
  */
1919
  *enabled_value= true; /* by default, plugin enabled */
1920
1 by brian
clean slate
1921
  options[1].name= (options[0].name= name) + namelen + 1;
1922
  options[0].id= options[1].id= 256; /* must be >255. dup id ok */
1923
  options[0].var_type= options[1].var_type= GET_BOOL;
1924
  options[0].arg_type= options[1].arg_type= NO_ARG;
138 by Brian Aker
Refactoring around sql_plugin.
1925
  options[0].def_value= options[1].def_value= true;
1 by brian
clean slate
1926
  options[0].value= options[0].u_max_value=
1119.6.1 by Stewart Smith
remove nasty malloc() optimisation in --help plugin for sql_plugin. Also document the general turdiness of this area of code.
1927
  options[1].value= options[1].u_max_value= (char**) enabled_value;
1 by brian
clean slate
1928
  options+= 2;
1929
1930
  /*
1931
    Two passes as the 2nd pass will take pointer addresses for use
1932
    by my_getopt and register_var() in the first pass uses realloc
1933
  */
1934
1093.3.4 by Monty Taylor
Naming cleanups.
1935
  for (plugin_option= tmp->getManifest().system_vars;
1 by brian
clean slate
1936
       plugin_option && *plugin_option; plugin_option++, index++)
1937
  {
1938
    opt= *plugin_option;
520.1.21 by Brian Aker
THD -> Session rename
1939
    if (!(opt->flags & PLUGIN_VAR_SessionLOCAL))
1 by brian
clean slate
1940
      continue;
1941
    if (!(register_var(name, opt->name, opt->flags)))
1942
      continue;
1943
    switch (opt->flags & PLUGIN_VAR_TYPEMASK) {
1944
    case PLUGIN_VAR_BOOL:
520.1.22 by Brian Aker
Second pass of thd cleanup
1945
      (((sessionvar_bool_t *)opt)->resolve)= mysql_sys_var_ptr_bool;
1 by brian
clean slate
1946
      break;
1947
    case PLUGIN_VAR_INT:
520.1.22 by Brian Aker
Second pass of thd cleanup
1948
      (((sessionvar_int_t *)opt)->resolve)= mysql_sys_var_ptr_int;
1 by brian
clean slate
1949
      break;
1950
    case PLUGIN_VAR_LONG:
520.1.22 by Brian Aker
Second pass of thd cleanup
1951
      (((sessionvar_long_t *)opt)->resolve)= mysql_sys_var_ptr_long;
1 by brian
clean slate
1952
      break;
1953
    case PLUGIN_VAR_LONGLONG:
520.1.22 by Brian Aker
Second pass of thd cleanup
1954
      (((sessionvar_int64_t_t *)opt)->resolve)= mysql_sys_var_ptr_int64_t;
1 by brian
clean slate
1955
      break;
1956
    case PLUGIN_VAR_STR:
520.1.22 by Brian Aker
Second pass of thd cleanup
1957
      (((sessionvar_str_t *)opt)->resolve)= mysql_sys_var_ptr_str;
1 by brian
clean slate
1958
      break;
1959
    case PLUGIN_VAR_ENUM:
520.1.22 by Brian Aker
Second pass of thd cleanup
1960
      (((sessionvar_enum_t *)opt)->resolve)= mysql_sys_var_ptr_enum;
1 by brian
clean slate
1961
      break;
1962
    case PLUGIN_VAR_SET:
520.1.22 by Brian Aker
Second pass of thd cleanup
1963
      (((sessionvar_set_t *)opt)->resolve)= mysql_sys_var_ptr_set;
1 by brian
clean slate
1964
      break;
1965
    default:
755.2.1 by Mark Atwood
replace sql_print_error etc with errmsg_print
1966
      errmsg_printf(ERRMSG_LVL_ERROR, _("Unknown variable type code 0x%x in plugin '%s'."),
1 by brian
clean slate
1967
                      opt->flags, plugin_name);
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
1968
      return(-1);
1 by brian
clean slate
1969
    };
1970
  }
1971
1093.3.4 by Monty Taylor
Naming cleanups.
1972
  for (plugin_option= tmp->getManifest().system_vars;
1 by brian
clean slate
1973
       plugin_option && *plugin_option; plugin_option++, index++)
1974
  {
1975
    switch ((opt= *plugin_option)->flags & PLUGIN_VAR_TYPEMASK) {
1976
    case PLUGIN_VAR_BOOL:
1977
      if (!opt->check)
1978
        opt->check= check_func_bool;
1979
      if (!opt->update)
1980
        opt->update= update_func_bool;
1981
      break;
1982
    case PLUGIN_VAR_INT:
1983
      if (!opt->check)
1984
        opt->check= check_func_int;
1985
      if (!opt->update)
1986
        opt->update= update_func_int;
1987
      break;
1988
    case PLUGIN_VAR_LONG:
1989
      if (!opt->check)
1990
        opt->check= check_func_long;
1991
      if (!opt->update)
1992
        opt->update= update_func_long;
1993
      break;
1994
    case PLUGIN_VAR_LONGLONG:
1995
      if (!opt->check)
152 by Brian Aker
longlong replacement
1996
        opt->check= check_func_int64_t;
1 by brian
clean slate
1997
      if (!opt->update)
152 by Brian Aker
longlong replacement
1998
        opt->update= update_func_int64_t;
1 by brian
clean slate
1999
      break;
2000
    case PLUGIN_VAR_STR:
2001
      if (!opt->check)
2002
        opt->check= check_func_str;
2003
      if (!opt->update)
2004
      {
2005
        opt->update= update_func_str;
9 by Brian Aker
Warnings cleanup
2006
        if ((opt->flags & (PLUGIN_VAR_MEMALLOC | PLUGIN_VAR_READONLY)) == false)
1 by brian
clean slate
2007
        {
2008
          opt->flags|= PLUGIN_VAR_READONLY;
755.2.1 by Mark Atwood
replace sql_print_error etc with errmsg_print
2009
          errmsg_printf(ERRMSG_LVL_WARN, _("Server variable %s of plugin %s was forced "
1 by brian
clean slate
2010
                            "to be read-only: string variable without "
338 by Monty Taylor
Tagged more strings.
2011
                            "update_func and PLUGIN_VAR_MEMALLOC flag"),
1 by brian
clean slate
2012
                            opt->name, plugin_name);
2013
        }
2014
      }
2015
      break;
2016
    case PLUGIN_VAR_ENUM:
2017
      if (!opt->check)
2018
        opt->check= check_func_enum;
2019
      if (!opt->update)
2020
        opt->update= update_func_long;
2021
      break;
2022
    case PLUGIN_VAR_SET:
2023
      if (!opt->check)
2024
        opt->check= check_func_set;
2025
      if (!opt->update)
152 by Brian Aker
longlong replacement
2026
        opt->update= update_func_int64_t;
1 by brian
clean slate
2027
      break;
2028
    default:
755.2.1 by Mark Atwood
replace sql_print_error etc with errmsg_print
2029
      errmsg_printf(ERRMSG_LVL_ERROR, _("Unknown variable type code 0x%x in plugin '%s'."),
1 by brian
clean slate
2030
                      opt->flags, plugin_name);
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
2031
      return(-1);
1 by brian
clean slate
2032
    }
2033
520.1.21 by Brian Aker
THD -> Session rename
2034
    if ((opt->flags & (PLUGIN_VAR_NOCMDOPT | PLUGIN_VAR_SessionLOCAL))
1 by brian
clean slate
2035
                    == PLUGIN_VAR_NOCMDOPT)
2036
      continue;
2037
2038
    if (!opt->name)
2039
    {
755.2.1 by Mark Atwood
replace sql_print_error etc with errmsg_print
2040
      errmsg_printf(ERRMSG_LVL_ERROR, _("Missing variable name in plugin '%s'."),
1 by brian
clean slate
2041
                      plugin_name);
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
2042
      return(-1);
1 by brian
clean slate
2043
    }
2044
520.1.21 by Brian Aker
THD -> Session rename
2045
    if (!(opt->flags & PLUGIN_VAR_SessionLOCAL))
1 by brian
clean slate
2046
    {
2047
      optnamelen= strlen(opt->name);
2048
      optname= (char*) alloc_root(mem_root, namelen + optnamelen + 2);
673.2.1 by Toru Maesaka
First pass of replacing MySQL's strxmov with libc alternatives
2049
      sprintf(optname, "%s-%s", name, opt->name);
1 by brian
clean slate
2050
      optnamelen= namelen + optnamelen + 1;
2051
    }
2052
    else
2053
    {
2054
      /* this should not fail because register_var should create entry */
2055
      if (!(v= find_bookmark(name, opt->name, opt->flags)))
2056
      {
755.2.1 by Mark Atwood
replace sql_print_error etc with errmsg_print
2057
        errmsg_printf(ERRMSG_LVL_ERROR, _("Thread local variable '%s' not allocated "
338 by Monty Taylor
Tagged more strings.
2058
                        "in plugin '%s'."), opt->name, plugin_name);
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
2059
        return(-1);
1 by brian
clean slate
2060
      }
2061
2062
      *(int*)(opt + 1)= offset= v->offset;
2063
2064
      if (opt->flags & PLUGIN_VAR_NOCMDOPT)
2065
        continue;
2066
660.1.3 by Eric Herman
removed trailing whitespace with simple script:
2067
      optname= (char*) memdup_root(mem_root, v->key + 1,
1 by brian
clean slate
2068
                                   (optnamelen= v->name_len) + 1);
2069
    }
2070
2071
    /* convert '_' to '-' */
2072
    for (p= optname; *p; p++)
2073
      if (*p == '_')
2074
        *p= '-';
2075
2076
    options->name= optname;
2077
    options->comment= opt->comment;
2078
    options->app_type= opt;
2079
    options->id= (options-1)->id + 1;
2080
2081
    plugin_opt_set_limits(options, opt);
2082
520.1.21 by Brian Aker
THD -> Session rename
2083
    if (opt->flags & PLUGIN_VAR_SessionLOCAL)
77.1.78 by Monty Taylor
One last bunch of warnings edits.
2084
      options->value= options->u_max_value= (char**)
1 by brian
clean slate
2085
        (global_system_variables.dynamic_variables_ptr + offset);
2086
    else
77.1.78 by Monty Taylor
One last bunch of warnings edits.
2087
      options->value= options->u_max_value= *(char***) (opt + 1);
1 by brian
clean slate
2088
2089
    options[1]= options[0];
2090
    options[1].name= p= (char*) alloc_root(mem_root, optnamelen + 8);
2091
    options[1].comment= 0; // hidden
673.2.1 by Toru Maesaka
First pass of replacing MySQL's strxmov with libc alternatives
2092
    sprintf(p,"plugin-%s",optname);
1 by brian
clean slate
2093
2094
    options+= 2;
2095
  }
2096
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
2097
  return(0);
1 by brian
clean slate
2098
}
2099
2100
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
2101
static my_option *construct_help_options(MEM_ROOT *mem_root, plugin::Handle *p)
1 by brian
clean slate
2102
{
2103
  st_mysql_sys_var **opt;
2104
  my_option *opts;
138 by Brian Aker
Refactoring around sql_plugin.
2105
  bool can_disable;
482 by Brian Aker
Remove uint.
2106
  uint32_t count= EXTRA_OPTIONS;
1 by brian
clean slate
2107
1093.3.4 by Monty Taylor
Naming cleanups.
2108
  for (opt= p->getManifest().system_vars; opt && *opt; opt++, count+= 2) {};
1 by brian
clean slate
2109
1093.3.5 by Monty Taylor
Removed a dynamic array.
2110
  opts= (my_option*)alloc_root(mem_root, (sizeof(my_option) * count));
2111
  if (opts == NULL)
1019.1.6 by Brian Aker
A number of random cleanups.
2112
    return NULL;
1 by brian
clean slate
2113
212.6.1 by Mats Kindahl
Replacing all bzero() calls with memset() calls and removing the bzero.c file.
2114
  memset(opts, 0, sizeof(my_option) * count);
1 by brian
clean slate
2115
1093.3.4 by Monty Taylor
Naming cleanups.
2116
  if ((my_strcasecmp(&my_charset_utf8_general_ci, p->getName().c_str(), "MyISAM") == 0))
138 by Brian Aker
Refactoring around sql_plugin.
2117
    can_disable= false;
1093.3.4 by Monty Taylor
Naming cleanups.
2118
  else if ((my_strcasecmp(&my_charset_utf8_general_ci, p->getName().c_str(), "MEMORY") == 0))
138 by Brian Aker
Refactoring around sql_plugin.
2119
    can_disable= false;
2120
  else
2121
    can_disable= true;
2122
2123
2124
  if (construct_options(mem_root, p, opts, can_disable))
1019.1.6 by Brian Aker
A number of random cleanups.
2125
    return NULL;
1 by brian
clean slate
2126
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
2127
  return(opts);
1 by brian
clean slate
2128
}
2129
1101.1.27 by Monty Taylor
Fixed the plugin string valgrind leak.
2130
void drizzle_add_plugin_sysvar(sys_var_pluginvar *var)
2131
{
2132
  plugin_sysvar_vec.push_back(var);
2133
}
2134
2135
void drizzle_del_plugin_sysvar()
2136
{
2137
  vector<sys_var_pluginvar *>::iterator iter= plugin_sysvar_vec.begin();
2138
  while(iter != plugin_sysvar_vec.end())
2139
  {
2140
    delete *iter;
2141
    ++iter;
2142
  }
2143
  plugin_sysvar_vec.clear();
2144
}
1 by brian
clean slate
2145
2146
/*
2147
  SYNOPSIS
2148
    test_plugin_options()
2149
    tmp_root                    temporary scratch space
2150
    plugin                      internal plugin structure
2151
    argc                        user supplied arguments
2152
    argv                        user supplied arguments
2153
    default_enabled             default plugin enable status
2154
  RETURNS:
2155
    0 SUCCESS - plugin should be enabled/loaded
2156
  NOTE:
2157
    Requires that a write-lock is held on LOCK_system_variables_hash
2158
*/
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
2159
static int test_plugin_options(MEM_ROOT *tmp_root, plugin::Handle *tmp,
135 by Brian Aker
Random cleanup. Dead partition tests, pass operator in sql_plugin, mtr based
2160
                               int *argc, char **argv)
1 by brian
clean slate
2161
{
2162
  struct sys_var_chain chain= { NULL, NULL };
138 by Brian Aker
Refactoring around sql_plugin.
2163
  bool can_disable;
1 by brian
clean slate
2164
  st_mysql_sys_var **opt;
2165
  my_option *opts= NULL;
2166
  int error;
2167
  st_mysql_sys_var *o;
2168
  struct st_bookmark *var;
482 by Brian Aker
Remove uint.
2169
  uint32_t len, count= EXTRA_OPTIONS;
1 by brian
clean slate
2170
1093.3.4 by Monty Taylor
Naming cleanups.
2171
  for (opt= tmp->getManifest().system_vars; opt && *opt; opt++)
1 by brian
clean slate
2172
    count+= 2; /* --{plugin}-{optname} and --plugin-{plugin}-{optname} */
2173
1093.3.4 by Monty Taylor
Naming cleanups.
2174
  if ((my_strcasecmp(&my_charset_utf8_general_ci, tmp->getName().c_str(), "MyISAM") == 0))
138 by Brian Aker
Refactoring around sql_plugin.
2175
    can_disable= false;
1093.3.4 by Monty Taylor
Naming cleanups.
2176
  else if ((my_strcasecmp(&my_charset_utf8_general_ci, tmp->getName().c_str(), "MEMORY") == 0))
138 by Brian Aker
Refactoring around sql_plugin.
2177
    can_disable= false;
2178
  else
2179
    can_disable= true;
1 by brian
clean slate
2180
2181
  if (count > EXTRA_OPTIONS || (*argc > 1))
2182
  {
2183
    if (!(opts= (my_option*) alloc_root(tmp_root, sizeof(my_option) * count)))
2184
    {
1093.3.4 by Monty Taylor
Naming cleanups.
2185
      errmsg_printf(ERRMSG_LVL_ERROR, _("Out of memory for plugin '%s'."), tmp->getName().c_str());
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
2186
      return(-1);
1 by brian
clean slate
2187
    }
212.6.1 by Mats Kindahl
Replacing all bzero() calls with memset() calls and removing the bzero.c file.
2188
    memset(opts, 0, sizeof(my_option) * count);
1 by brian
clean slate
2189
138 by Brian Aker
Refactoring around sql_plugin.
2190
    if (construct_options(tmp_root, tmp, opts, can_disable))
1 by brian
clean slate
2191
    {
1093.3.4 by Monty Taylor
Naming cleanups.
2192
      errmsg_printf(ERRMSG_LVL_ERROR, _("Bad options for plugin '%s'."), tmp->getName().c_str());
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
2193
      return(-1);
1 by brian
clean slate
2194
    }
2195
2196
    error= handle_options(argc, &argv, opts, get_one_plugin_option);
2197
    (*argc)++; /* add back one for the program name */
2198
2199
    if (error)
2200
    {
755.2.1 by Mark Atwood
replace sql_print_error etc with errmsg_print
2201
       errmsg_printf(ERRMSG_LVL_ERROR, _("Parsing options for plugin '%s' failed."),
1093.3.4 by Monty Taylor
Naming cleanups.
2202
                       tmp->getName().c_str());
1 by brian
clean slate
2203
       goto err;
2204
    }
2205
  }
2206
2207
  error= 1;
2208
779.3.53 by Monty Taylor
Revert the fail.
2209
  {
1093.3.4 by Monty Taylor
Naming cleanups.
2210
    for (opt= tmp->getManifest().system_vars; opt && *opt; opt++)
779.3.53 by Monty Taylor
Revert the fail.
2211
    {
1106.1.2 by Brian Aker
Additional fixes from Monty
2212
      sys_var *v;
779.3.53 by Monty Taylor
Revert the fail.
2213
      if (((o= *opt)->flags & PLUGIN_VAR_NOSYSVAR))
2214
        continue;
2215
1093.3.4 by Monty Taylor
Naming cleanups.
2216
      if ((var= find_bookmark(tmp->getName().c_str(), o->name, o->flags)))
1101.1.27 by Monty Taylor
Fixed the plugin string valgrind leak.
2217
        v= new sys_var_pluginvar(var->key + 1, o);
779.3.53 by Monty Taylor
Revert the fail.
2218
      else
2219
      {
1093.3.4 by Monty Taylor
Naming cleanups.
2220
        len= tmp->getName().length() + strlen(o->name) + 2;
1101.1.27 by Monty Taylor
Fixed the plugin string valgrind leak.
2221
        string vname(tmp->getName());
2222
        vname.push_back('-');
2223
        vname.append(o->name);
2224
        transform(vname.begin(), vname.end(), vname.begin(), ::tolower);
2225
        string::iterator p= vname.begin();      
2226
        while  (p != vname.end())
2227
        {
779.3.53 by Monty Taylor
Revert the fail.
2228
          if (*p == '-')
2229
            *p= '_';
1101.1.27 by Monty Taylor
Fixed the plugin string valgrind leak.
2230
          ++p;
2231
        }
779.3.53 by Monty Taylor
Revert the fail.
2232
1101.1.27 by Monty Taylor
Fixed the plugin string valgrind leak.
2233
        v= new sys_var_pluginvar(vname, o);
779.3.53 by Monty Taylor
Revert the fail.
2234
      }
2235
      assert(v); /* check that an object was actually constructed */
2236
1101.1.27 by Monty Taylor
Fixed the plugin string valgrind leak.
2237
      drizzle_add_plugin_sysvar(static_cast<sys_var_pluginvar *>(v));
779.3.53 by Monty Taylor
Revert the fail.
2238
      /*
2239
        Add to the chain of variables.
2240
        Done like this for easier debugging so that the
2241
        pointer to v is not lost on optimized builds.
2242
      */
2243
      v->chain_sys_var(&chain);
2244
    }
2245
    if (chain.first)
2246
    {
1055.2.20 by Jay Pipes
Refactors sys_var class -- doxygenates and documents the class members and functions. Protects all member variables and adds public getters/setters.
2247
      chain.last->setNext(NULL);
779.3.53 by Monty Taylor
Revert the fail.
2248
      if (mysql_add_sys_var_chain(chain.first, NULL))
2249
      {
2250
        errmsg_printf(ERRMSG_LVL_ERROR, _("Plugin '%s' has conflicting system variables"),
1093.3.4 by Monty Taylor
Naming cleanups.
2251
                        tmp->getName().c_str());
779.3.53 by Monty Taylor
Revert the fail.
2252
        goto err;
2253
      }
2254
      tmp->system_vars= chain.first;
2255
    }
2256
    return(0);
2257
  }
2258
1 by brian
clean slate
2259
err:
2260
  if (opts)
2261
    my_cleanup_options(opts);
51.1.1 by Jay Pipes
Merged PatG's removal of various DBUG stuff with still keeping DBUG_ASSERT calls since they seem to be breaking test runs
2262
  return(error);
1 by brian
clean slate
2263
}
2264
2265
2266
/****************************************************************************
2267
  Help Verbose text with Plugin System Variables
2268
****************************************************************************/
2269
1093.3.5 by Monty Taylor
Removed a dynamic array.
2270
class OptionCmp
2271
{
2272
public:
2273
  bool operator() (const my_option &a, const my_option &b)
2274
  {
2275
    return my_strcasecmp(&my_charset_utf8_general_ci, a.name, b.name);
2276
  }
2277
};
2278
2279
2280
void my_print_help_inc_plugins(my_option *main_options)
2281
{
2282
  vector<my_option> all_options;
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
2283
  plugin::Handle *p;
1 by brian
clean slate
2284
  MEM_ROOT mem_root;
1093.3.5 by Monty Taylor
Removed a dynamic array.
2285
  my_option *opt= NULL;
1 by brian
clean slate
2286
2287
  init_alloc_root(&mem_root, 4096, 4096);
2288
2289
  if (initialized)
482 by Brian Aker
Remove uint.
2290
    for (uint32_t idx= 0; idx < plugin_array.elements; idx++)
1 by brian
clean slate
2291
    {
1101.2.1 by Monty Taylor
Fixed the first set of using namespace
2292
      p= *dynamic_element(&plugin_array, idx, plugin::Handle **);
1 by brian
clean slate
2293
1093.3.5 by Monty Taylor
Removed a dynamic array.
2294
      if (p->getManifest().system_vars == NULL)
2295
        continue;
2296
2297
      opt= construct_help_options(&mem_root, p);
2298
      if (opt == NULL)
1 by brian
clean slate
2299
        continue;
2300
2301
      /* Only options with a non-NULL comment are displayed in help text */
2302
      for (;opt->id; opt++)
1093.3.5 by Monty Taylor
Removed a dynamic array.
2303
      {
1 by brian
clean slate
2304
        if (opt->comment)
1093.3.5 by Monty Taylor
Removed a dynamic array.
2305
        {
2306
          all_options.push_back(*opt);
2307
          
2308
        }
2309
      }
1 by brian
clean slate
2310
    }
2311
2312
  for (;main_options->id; main_options++)
1093.3.5 by Monty Taylor
Removed a dynamic array.
2313
  {
2314
    if (main_options->comment)
2315
    {
2316
      all_options.push_back(*main_options);
2317
    }
2318
  }
1 by brian
clean slate
2319
1093.3.5 by Monty Taylor
Removed a dynamic array.
2320
  /** 
2321
   * @TODO: Fix the my_option building so that it doens't break sort
2322
   *
2323
   * sort(all_options.begin(), all_options.end(), OptionCmp());
2324
   */
1 by brian
clean slate
2325
2326
  /* main_options now points to the empty option terminator */
1093.3.5 by Monty Taylor
Removed a dynamic array.
2327
  all_options.push_back(*main_options);
2328
2329
  my_print_help(&*(all_options.begin()));
2330
  my_print_variables(&*(all_options.begin()));
2331
1 by brian
clean slate
2332
  free_root(&mem_root, MYF(0));
1093.3.5 by Monty Taylor
Removed a dynamic array.
2333
1 by brian
clean slate
2334
}
2335