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