~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to drizzled/handlerton.cc

  • Committer: Brian Aker
  • Date: 2008-08-11 04:55:59 UTC
  • Revision ID: brian@tangent.org-20080811045559-azgfc343y0igyzsz
ulong cleanup, remove log code from myisam.

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
/* -*- mode: c++; c-basic-offset: 2; indent-tabs-mode: nil; -*-
2
 
 *  vim:expandtab:shiftwidth=2:tabstop=2:smarttab:
3
 
 *
4
 
 *  Copyright (C) 2008 Sun Microsystems
5
 
 *
6
 
 *  This program is free software; you can redistribute it and/or modify
7
 
 *  it under the terms of the GNU General Public License as published by
8
 
 *  the Free Software Foundation; version 2 of the License.
9
 
 *
10
 
 *  This program is distributed in the hope that it will be useful,
11
 
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
12
 
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
 
 *  GNU General Public License for more details.
14
 
 *
15
 
 *  You should have received a copy of the GNU General Public License
16
 
 *  along with this program; if not, write to the Free Software
17
 
 *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
18
 
 */
19
 
 
20
 
#include <drizzled/server_includes.h>
21
 
#include <drizzled/definitions.h>
22
 
#include <drizzled/base.h>
23
 
#include <drizzled/handler.h>
24
 
#include <drizzled/handlerton.h>
25
 
#include <drizzled/session.h>
26
 
#include <drizzled/error.h>
27
 
#include <drizzled/gettext.h>
28
 
 
29
 
#include CSTDINT_H
30
 
 
31
 
/*
32
 
  While we have legacy_db_type, we have this array to
33
 
  check for dups and to find handlerton from legacy_db_type.
34
 
  Remove when legacy_db_type is finally gone
35
 
*/
36
 
st_plugin_int *hton2plugin[MAX_HA];
37
 
 
38
 
static handlerton *installed_htons[128];
39
 
 
40
 
static const LEX_STRING sys_table_aliases[]=
41
 
{
42
 
  { C_STRING_WITH_LEN("INNOBASE") },  { C_STRING_WITH_LEN("INNODB") },
43
 
  { C_STRING_WITH_LEN("HEAP") },      { C_STRING_WITH_LEN("MEMORY") },
44
 
  {NULL, 0}
45
 
};
46
 
 
47
 
 
48
 
handlerton *ha_resolve_by_legacy_type(Session *session,
49
 
                                      enum legacy_db_type db_type)
50
 
{
51
 
  plugin_ref plugin;
52
 
  switch (db_type) {
53
 
  case DB_TYPE_DEFAULT:
54
 
    return ha_default_handlerton(session);
55
 
  default:
56
 
    if (db_type > DB_TYPE_UNKNOWN && db_type < DB_TYPE_DEFAULT &&
57
 
        (plugin= ha_lock_engine(session, installed_htons[db_type])))
58
 
      return plugin_data(plugin, handlerton*);
59
 
    /* fall through */
60
 
  case DB_TYPE_UNKNOWN:
61
 
    return NULL;
62
 
  }
63
 
}
64
 
 
65
 
 
66
 
static plugin_ref ha_default_plugin(Session *session)
67
 
{
68
 
  if (session->variables.table_plugin)
69
 
    return session->variables.table_plugin;
70
 
  return my_plugin_lock(session, &global_system_variables.table_plugin);
71
 
}
72
 
 
73
 
 
74
 
/**
75
 
  Return the default storage engine handlerton for thread
76
 
 
77
 
  @param ha_default_handlerton(session)
78
 
  @param session         current thread
79
 
 
80
 
  @return
81
 
    pointer to handlerton
82
 
*/
83
 
handlerton *ha_default_handlerton(Session *session)
84
 
{
85
 
  plugin_ref plugin= ha_default_plugin(session);
86
 
  assert(plugin);
87
 
  handlerton *hton= plugin_data(plugin, handlerton*);
88
 
  assert(hton);
89
 
  return hton;
90
 
}
91
 
 
92
 
 
93
 
/**
94
 
  Return the storage engine handlerton for the supplied name
95
 
 
96
 
  @param session         current thread
97
 
  @param name        name of storage engine
98
 
 
99
 
  @return
100
 
    pointer to storage engine plugin handle
101
 
*/
102
 
plugin_ref ha_resolve_by_name(Session *session, const LEX_STRING *name)
103
 
{
104
 
  const LEX_STRING *table_alias;
105
 
  plugin_ref plugin;
106
 
 
107
 
redo:
108
 
  /* my_strnncoll is a macro and gcc doesn't do early expansion of macro */
109
 
  if (session && !my_charset_utf8_general_ci.coll->strnncoll(&my_charset_utf8_general_ci,
110
 
                           (const unsigned char *)name->str, name->length,
111
 
                           (const unsigned char *)STRING_WITH_LEN("DEFAULT"), 0))
112
 
    return ha_default_plugin(session);
113
 
 
114
 
  if ((plugin= my_plugin_lock_by_name(session, name, DRIZZLE_STORAGE_ENGINE_PLUGIN)))
115
 
  {
116
 
    handlerton *hton= plugin_data(plugin, handlerton *);
117
 
    if (!(hton->flags.test(HTON_BIT_NOT_USER_SELECTABLE)))
118
 
      return plugin;
119
 
 
120
 
    /*
121
 
      unlocking plugin immediately after locking is relatively low cost.
122
 
    */
123
 
    plugin_unlock(session, plugin);
124
 
  }
125
 
 
126
 
  /*
127
 
    We check for the historical aliases.
128
 
  */
129
 
  for (table_alias= sys_table_aliases; table_alias->str; table_alias+= 2)
130
 
  {
131
 
    if (!my_strnncoll(&my_charset_utf8_general_ci,
132
 
                      (const unsigned char *)name->str, name->length,
133
 
                      (const unsigned char *)table_alias->str,
134
 
                      table_alias->length))
135
 
    {
136
 
      name= table_alias + 1;
137
 
      goto redo;
138
 
    }
139
 
  }
140
 
 
141
 
  return NULL;
142
 
}
143
 
 
144
 
 
145
 
plugin_ref ha_lock_engine(Session *session, handlerton *hton)
146
 
{
147
 
  if (hton)
148
 
  {
149
 
    st_plugin_int **plugin= hton2plugin + hton->slot;
150
 
 
151
 
    return my_plugin_lock(session, &plugin);
152
 
  }
153
 
  return NULL;
154
 
}
155
 
 
156
 
 
157
 
/**
158
 
  Use other database handler if databasehandler is not compiled in.
159
 
*/
160
 
handlerton *ha_checktype(Session *session, enum legacy_db_type database_type,
161
 
                          bool no_substitute, bool report_error)
162
 
{
163
 
  handlerton *hton= ha_resolve_by_legacy_type(session, database_type);
164
 
  if (ha_storage_engine_is_enabled(hton))
165
 
    return hton;
166
 
 
167
 
  if (no_substitute)
168
 
  {
169
 
    if (report_error)
170
 
    {
171
 
      const char *engine_name= ha_resolve_storage_engine_name(hton);
172
 
      my_error(ER_FEATURE_DISABLED,MYF(0),engine_name,engine_name);
173
 
    }
174
 
    return NULL;
175
 
  }
176
 
 
177
 
  return ha_default_handlerton(session);
178
 
} /* ha_checktype */
179
 
 
180
 
 
181
 
handler *get_new_handler(TABLE_SHARE *share, MEM_ROOT *alloc,
182
 
                         handlerton *db_type)
183
 
{
184
 
  handler *file;
185
 
 
186
 
  if (db_type && db_type->state == SHOW_OPTION_YES && db_type->create)
187
 
  {
188
 
    if ((file= db_type->create(db_type, share, alloc)))
189
 
      file->init();
190
 
    return(file);
191
 
  }
192
 
  /*
193
 
    Try the default table type
194
 
    Here the call to current_session() is ok as we call this function a lot of
195
 
    times but we enter this branch very seldom.
196
 
  */
197
 
  return(get_new_handler(share, alloc, ha_default_handlerton(current_session)));
198
 
}
199
 
 
200
 
 
201
 
int ha_finalize_handlerton(st_plugin_int *plugin)
202
 
{
203
 
  handlerton *hton= (handlerton *)plugin->data;
204
 
 
205
 
  switch (hton->state)
206
 
  {
207
 
  case SHOW_OPTION_NO:
208
 
  case SHOW_OPTION_DISABLED:
209
 
    break;
210
 
  case SHOW_OPTION_YES:
211
 
    if (installed_htons[hton->db_type] == hton)
212
 
      installed_htons[hton->db_type]= NULL;
213
 
    break;
214
 
  };
215
 
 
216
 
  if (hton && plugin->plugin->deinit)
217
 
    (void)plugin->plugin->deinit(hton);
218
 
 
219
 
  free((unsigned char*)hton);
220
 
 
221
 
  return(0);
222
 
}
223
 
 
224
 
 
225
 
int ha_initialize_handlerton(st_plugin_int *plugin)
226
 
{
227
 
  handlerton *hton;
228
 
 
229
 
  hton= (handlerton *)malloc(sizeof(handlerton));
230
 
  memset(hton, 0, sizeof(handlerton));
231
 
 
232
 
  /* Historical Requirement */
233
 
  plugin->data= hton; // shortcut for the future
234
 
  if (plugin->plugin->init)
235
 
  {
236
 
    if (plugin->plugin->init(hton))
237
 
    {
238
 
      sql_print_error(_("Plugin '%s' init function returned error."),
239
 
                      plugin->name.str);
240
 
      goto err;
241
 
    }
242
 
  }
243
 
 
244
 
  hton->name= plugin->name.str;
245
 
 
246
 
  /*
247
 
    the switch below and hton->state should be removed when
248
 
    command-line options for plugins will be implemented
249
 
  */
250
 
  switch (hton->state) {
251
 
  case SHOW_OPTION_NO:
252
 
    break;
253
 
  case SHOW_OPTION_YES:
254
 
    {
255
 
      uint32_t tmp;
256
 
      /* now check the db_type for conflict */
257
 
      if (hton->db_type <= DB_TYPE_UNKNOWN ||
258
 
          hton->db_type >= DB_TYPE_DEFAULT ||
259
 
          installed_htons[hton->db_type])
260
 
      {
261
 
        int idx= (int) DB_TYPE_FIRST_DYNAMIC;
262
 
 
263
 
        while (idx < (int) DB_TYPE_DEFAULT && installed_htons[idx])
264
 
          idx++;
265
 
 
266
 
        if (idx == (int) DB_TYPE_DEFAULT)
267
 
        {
268
 
          sql_print_warning(_("Too many storage engines!"));
269
 
          return(1);
270
 
        }
271
 
        if (hton->db_type != DB_TYPE_UNKNOWN)
272
 
          sql_print_warning(_("Storage engine '%s' has conflicting typecode. "
273
 
                            "Assigning value %d."), plugin->plugin->name, idx);
274
 
        hton->db_type= (enum legacy_db_type) idx;
275
 
      }
276
 
      installed_htons[hton->db_type]= hton;
277
 
      tmp= hton->savepoint_offset;
278
 
      hton->savepoint_offset= savepoint_alloc_size;
279
 
      savepoint_alloc_size+= tmp;
280
 
      hton->slot= total_ha++;
281
 
      hton2plugin[hton->slot]=plugin;
282
 
      if (hton->prepare)
283
 
        total_ha_2pc++;
284
 
      break;
285
 
    }
286
 
    /* fall through */
287
 
  default:
288
 
    hton->state= SHOW_OPTION_DISABLED;
289
 
    break;
290
 
  }
291
 
 
292
 
  /*
293
 
    This is entirely for legacy. We will create a new "disk based" hton and a
294
 
    "memory" hton which will be configurable longterm. We should be able to
295
 
    remove partition and myisammrg.
296
 
  */
297
 
  if (strcmp(plugin->plugin->name, "MEMORY") == 0)
298
 
    heap_hton= hton;
299
 
 
300
 
  if (strcmp(plugin->plugin->name, "MyISAM") == 0)
301
 
    myisam_hton= hton;
302
 
 
303
 
  return(0);
304
 
err:
305
 
  return(1);
306
 
}
307
 
 
308
 
enum legacy_db_type ha_legacy_type(const handlerton *db_type)
309
 
{
310
 
  return (db_type == NULL) ? DB_TYPE_UNKNOWN : db_type->db_type;
311
 
}
312
 
 
313
 
const char *ha_resolve_storage_engine_name(const handlerton *db_type)
314
 
{
315
 
  return db_type == NULL ? "UNKNOWN" : hton2plugin[db_type->slot]->name.str;
316
 
}
317
 
 
318
 
bool ha_check_storage_engine_flag(const handlerton *db_type, const hton_flag_bits flag)
319
 
{
320
 
  return db_type == NULL ? false : db_type->flags.test(static_cast<size_t>(flag));
321
 
}
322
 
 
323
 
bool ha_storage_engine_is_enabled(const handlerton *db_type)
324
 
{
325
 
  return (db_type && db_type->create) ?
326
 
         (db_type->state == SHOW_OPTION_YES) : false;
327
 
}
328
 
 
329
 
LEX_STRING *ha_storage_engine_name(const handlerton *hton)
330
 
{
331
 
  return &hton2plugin[hton->slot]->name;
332
 
}