~drizzle-trunk/drizzle/development

1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
1
/*
2
  Copyright (C) 2010 Stewart Smith
3
4
  This program is free software; you can redistribute it and/or
5
  modify it under the terms of the GNU General Public License
6
  as published by the Free Software Foundation; either version 2
7
  of the License, or (at your option) any later version.
8
9
  This program is distributed in the hope that it will be useful,
10
  but WITHOUT ANY WARRANTY; without even the implied warranty of
11
  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12
  GNU General Public License for more details.
13
14
  You should have received a copy of the GNU General Public License
15
  along with this program; if not, write to the Free Software
16
  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
17
*/
18
1283.37.4 by Stewart Smith
fix embedded_innodb auto_increment for negative values (just strange really).
19
/* innobase_get_int_col_max_value() comes from ha_innodb.cc which is under
20
   the following license and Copyright */
21
22
/*****************************************************************************
23
24
Copyright (c) 2000, 2009, MySQL AB & Innobase Oy. All Rights Reserved.
25
Copyright (c) 2008, 2009 Google Inc.
26
27
Portions of this file contain modifications contributed and copyrighted by
1283.61.8 by Stewart Smith
support correct isolation levels for Embedded InnoDB. READ COMMITTED doesn't work because of bug lp:587772 - it doesn't work for innobase either. We also add tests for READ UNCOMMITTED and REPEATABLE READ
28
Google, Inc. Those modifications are gratefully acknowledged and are described
1283.37.4 by Stewart Smith
fix embedded_innodb auto_increment for negative values (just strange really).
29
briefly in the InnoDB documentation. The contributions by Google are
30
incorporated with their permission, and subject to the conditions contained in
31
the file COPYING.Google.
32
33
This program is free software; you can redistribute it and/or modify it under
34
the terms of the GNU General Public License as published by the Free Software
35
Foundation; version 2 of the License.
36
37
This program is distributed in the hope that it will be useful, but WITHOUT
38
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
39
FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
40
41
You should have received a copy of the GNU General Public License along with
42
this program; if not, write to the Free Software Foundation, Inc., 59 Temple
43
Place, Suite 330, Boston, MA 02111-1307 USA
44
45
*****************************************************************************/
46
/***********************************************************************
47
48
Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved.
49
Copyright (c) 2009, Percona Inc.
50
51
Portions of this file contain modifications contributed and copyrighted
52
by Percona Inc.. Those modifications are
53
gratefully acknowledged and are described briefly in the InnoDB
54
documentation. The contributions by Percona Inc. are incorporated with
55
their permission, and subject to the conditions contained in the file
56
COPYING.Percona.
57
58
This program is free software; you can redistribute it and/or modify it
59
under the terms of the GNU General Public License as published by the
60
Free Software Foundation; version 2 of the License.
61
62
This program is distributed in the hope that it will be useful, but
63
WITHOUT ANY WARRANTY; without even the implied warranty of
64
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
65
Public License for more details.
66
67
You should have received a copy of the GNU General Public License along
68
with this program; if not, write to the Free Software Foundation, Inc.,
69
59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
70
71
***********************************************************************/
72
73
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
74
#include "config.h"
75
#include <drizzled/table.h>
76
#include <drizzled/error.h>
77
#include "drizzled/internal/my_pthread.h"
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
78
#include <drizzled/plugin/transactional_storage_engine.h>
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
79
80
#include <fcntl.h>
81
82
#include <string>
1598.2.1 by Stewart Smith
support ROW_FORMAT for embedded_innodb. test both types of operation where DYNAMIC=COMPACT when runnning with antelope. it's all fail really... but anyway, the parsing works.
83
#include <boost/algorithm/string.hpp>
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
84
#include <map>
85
#include <fstream>
86
#include <drizzled/message/table.pb.h>
87
#include "drizzled/internal/m_string.h"
88
89
#include "drizzled/global_charset_info.h"
90
1283.3.5 by Stewart Smith
add LIBINNODB_VERSION() function
91
#include "libinnodb_version_func.h"
1283.10.2 by Stewart Smith
simple LIBINNODB_DATADICT_DUMP() function to dump contents of libinnodb data dict as string.
92
#include "libinnodb_datadict_dump_func.h"
1283.28.3 by Stewart Smith
simple table function for Embedded InnoDB Configuration. Currently returns nothing.
93
#include "config_table_function.h"
1283.28.9 by Stewart Smith
basic DATA_DICTIONARY.INNODB_STATUS table_function plugin. This gets the InnoDB status and lets the user query it.
94
#include "status_table_function.h"
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
95
1689.6.2 by Monty Taylor
Updated embedded_innodb to use haildb if it's there.
96
#if defined(HAVE_HAILDB_H)
97
# include <haildb.h>
98
#else
99
# include <embedded_innodb-1.0/innodb.h>
100
#endif /* HAVE_HAILDB_H */
1283.3.9 by Stewart Smith
call basic embedded innodb init functions (ib_init() and ib_startup()). Also shutdown functions.
101
1283.3.27 by Stewart Smith
basic code to insert a integer
102
#include "embedded_innodb_engine.h"
103
104
#include <drizzled/field.h>
1283.35.40 by Stewart Smith
update timestamp column for ON UPDATE NOW() in embedded_innodb
105
#include "drizzled/field/timestamp.h" // needed for UPDATE NOW()
1283.60.5 by Stewart Smith
add BLOB support to embedded_innodb along with a simple test.
106
#include "drizzled/field/blob.h"
1579.3.14 by Stewart Smith
have a constant for the maximum number of enum elements
107
#include "drizzled/field/enum.h"
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
108
#include <drizzled/session.h>
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
109
#include <boost/program_options.hpp>
110
#include <drizzled/module/option_map.h>
111
#include <iostream>
1283.67.1 by Stewart Smith
support prefix indexes in embedded_innodb. Add a test and get things right for the different collations (utf8 or binary)
112
#include <drizzled/charset.h>
1283.3.27 by Stewart Smith
basic code to insert a integer
113
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
114
namespace po= boost::program_options;
1685.2.12 by Brian Aker
This fixes the lower casing of names from Schema even when we should not.
115
#include <boost/algorithm/string.hpp>
116
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
117
using namespace std;
118
using namespace google;
119
using namespace drizzled;
120
1283.60.10 by Stewart Smith
the memory management for BLOBS is completely insane. For certain types of index lookups we *must* do a copy and clear it *only* in ::reset() or ::extra(). This patch fixes up any valgrind warnings/assertions for embedded_innodb executing type_blob test.
121
int read_row_from_innodb(unsigned char* buf, ib_crsr_t cursor, ib_tpl_t tuple, Table* table, bool has_hidden_primary_key, uint64_t *hidden_pkey, drizzled::memory::Root **blobroot= NULL);
1283.28.29 by Stewart Smith
implement rnd_pos for embedded_innodb. Also fix up fill_ib_search_tpl_froM_drizzle_key for primary keys that aren't all at the start of the table. It turns out that the clustered index search tuple numbers columns just in the clustered index, not anything to do with column numbers in the table.
122
static void fill_ib_search_tpl_from_drizzle_key(ib_tpl_t search_tuple,
1475.2.9 by Stewart Smith
fix many compile failures that people introduced in embedded_innodb because it's not built by default.. i.e. plugin=disabled is EPIC FAIL
123
                                                const drizzled::KeyInfo *key_info,
1283.28.29 by Stewart Smith
implement rnd_pos for embedded_innodb. Also fix up fill_ib_search_tpl_froM_drizzle_key for primary keys that aren't all at the start of the table. It turns out that the clustered index search tuple numbers columns just in the clustered index, not anything to do with column numbers in the table.
124
                                                const unsigned char *key_ptr,
125
                                                uint32_t key_len);
1283.43.5 by Stewart Smith
fix up store_key_value_from_innodb() prototype after switch from KEY to KeyInfo
126
static void store_key_value_from_innodb(KeyInfo *key_info, unsigned char* ref, int ref_len, const unsigned char *record);
1283.3.43 by Stewart Smith
refactor out rnd_next() into read_row_from_innodb() and a call to ib_cursor_next(). This allows us to make the row reading code generic for index scans/lookups.
127
1283.4.1 by Stewart Smith
currently storage engine plugins definition file extension *must* be 3 characters.
128
#define EMBEDDED_INNODB_EXT ".EID"
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
129
1283.17.13 by Stewart Smith
define should be a const char*
130
const char INNODB_TABLE_DEFINITIONS_TABLE[]= "data_dictionary/innodb_table_definitions";
1283.3.85 by Stewart Smith
take a savepoint at the start of each embedded innodb statement and roll back to that savepoint on error.
131
const string statement_savepoint_name("STATEMENT");
132
1283.17.12 by Stewart Smith
use define to set the name of the innodb_table_definitions table instead of repeating it 5 times through the code
133
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
134
static const char *EmbeddedInnoDBCursor_exts[] = {
135
  NULL
136
};
137
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
138
class EmbeddedInnoDBEngine : public drizzled::plugin::TransactionalStorageEngine
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
139
{
140
public:
141
  EmbeddedInnoDBEngine(const string &name_arg)
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
142
   : drizzled::plugin::TransactionalStorageEngine(name_arg,
143
                                                  HTON_NULL_IN_KEY |
144
                                                  HTON_CAN_INDEX_BLOBS |
145
                                                  HTON_AUTO_PART_KEY |
1283.39.11 by Stewart Smith
fix write_row_to_innodb_tuple for proper WriteSet behaviour. oh my the API is bonghits.
146
                                                  HTON_PARTIAL_COLUMN_READ |
1283.26.13 by Stewart Smith
merge trunk
147
                                                  HTON_HAS_DOES_TRANSACTIONS)
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
148
  {
149
    table_definition_ext= EMBEDDED_INNODB_EXT;
150
  }
151
1283.23.10 by Stewart Smith
merge libinnodb init/de-init with trunk
152
  ~EmbeddedInnoDBEngine();
153
1680.6.1 by Brian Aker
Remove call for using special new for a cursor.
154
  virtual Cursor *create(TableShare &table)
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
155
  {
1680.6.1 by Brian Aker
Remove call for using special new for a cursor.
156
    return new EmbeddedInnoDBCursor(*this, table);
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
157
  }
158
159
  const char **bas_ext() const {
160
    return EmbeddedInnoDBCursor_exts;
161
  }
162
1598.2.1 by Stewart Smith
support ROW_FORMAT for embedded_innodb. test both types of operation where DYNAMIC=COMPACT when runnning with antelope. it's all fail really... but anyway, the parsing works.
163
  bool validateCreateTableOption(const std::string &key,
164
                                 const std::string &state);
165
1283.4.19 by Stewart Smith
merge fixes for embedded_innodb: changed prototypes for engine
166
  int doCreateTable(Session&,
1283.11.19 by Stewart Smith
fix up create table for new bits of storage engine API r.e. TableIdentifier
167
                    Table& table_arg,
1627.2.6 by Monty Taylor
Merged in constification of TableIdentifier from Brian.
168
                    const drizzled::TableIdentifier &identifier,
1283.11.19 by Stewart Smith
fix up create table for new bits of storage engine API r.e. TableIdentifier
169
                    drizzled::message::Table& proto);
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
170
1627.2.6 by Monty Taylor
Merged in constification of TableIdentifier from Brian.
171
  int doDropTable(Session&, const TableIdentifier &identifier);
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
172
1283.4.16 by Stewart Smith
fix up plugin initialisation and add doRenameTable empty function as it's now pure virtual
173
  int doRenameTable(drizzled::Session&,
1627.2.6 by Monty Taylor
Merged in constification of TableIdentifier from Brian.
174
                    const drizzled::TableIdentifier&,
175
                    const drizzled::TableIdentifier&);
1283.4.16 by Stewart Smith
fix up plugin initialisation and add doRenameTable empty function as it's now pure virtual
176
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
177
  int doGetTableDefinition(Session& session,
1627.2.6 by Monty Taylor
Merged in constification of TableIdentifier from Brian.
178
                           const TableIdentifier &identifier,
1283.4.13 by Stewart Smith
update embedded_innodb for TableIdentifier
179
                           drizzled::message::Table &table_proto);
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
180
1627.2.6 by Monty Taylor
Merged in constification of TableIdentifier from Brian.
181
  bool doDoesTableExist(Session&, const TableIdentifier &identifier);
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
182
1283.16.32 by Stewart Smith
implement both doGetTableNames and doGetTableIdentifiers through a common function
183
private:
1642 by Brian Aker
This adds const to SchemaIdentifier.
184
  void getTableNamesInSchemaFromInnoDB(const drizzled::SchemaIdentifier &schema,
1283.16.32 by Stewart Smith
implement both doGetTableNames and doGetTableIdentifiers through a common function
185
                                       drizzled::plugin::TableNameList *set_of_names,
186
                                       drizzled::TableIdentifiers *identifiers);
187
188
public:
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
189
  void doGetTableNames(drizzled::CachedDirectory &,
1642 by Brian Aker
This adds const to SchemaIdentifier.
190
                       const drizzled::SchemaIdentifier &schema,
1283.16.28 by Stewart Smith
merge trunk, fix up table name in doGetTableDefinition due to bug lp:552178
191
                       drizzled::plugin::TableNameList &set_of_names);
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
192
1283.4.21 by Stewart Smith
add two new empty functions that are required for a skeleton engine: get_auto_increment and doGetTableIdentifiers
193
  void doGetTableIdentifiers(drizzled::CachedDirectory &,
1642 by Brian Aker
This adds const to SchemaIdentifier.
194
                             const drizzled::SchemaIdentifier &schema,
1283.16.32 by Stewart Smith
implement both doGetTableNames and doGetTableIdentifiers through a common function
195
                             drizzled::TableIdentifiers &identifiers);
1283.4.21 by Stewart Smith
add two new empty functions that are required for a skeleton engine: get_auto_increment and doGetTableIdentifiers
196
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
197
  /* The following defines can be increased if necessary */
1283.66.1 by Stewart Smith
put in the proper limits from the embedded_innodb docs on max indexes et al. Also, a small test.
198
  uint32_t max_supported_keys()          const { return 1000; }
1283.66.2 by Stewart Smith
get limits close to reality with current libinnodb. these should all really be API calls.
199
  uint32_t max_supported_key_length()    const { return 3500; }
200
  uint32_t max_supported_key_part_length() const { return 767; }
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
201
202
  uint32_t index_flags(enum  ha_key_alg) const
203
  {
204
    return (HA_READ_NEXT |
205
            HA_READ_PREV |
206
            HA_READ_RANGE |
207
            HA_READ_ORDER |
208
            HA_KEYREAD_ONLY);
209
  }
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
210
  virtual int doStartTransaction(Session *session,
211
                                 start_transaction_option_t options);
212
  virtual void doStartStatement(Session *session);
213
  virtual void doEndStatement(Session *session);
214
215
  virtual int doSetSavepoint(Session* session,
216
                                 drizzled::NamedSavepoint &savepoint);
217
  virtual int doRollbackToSavepoint(Session* session,
218
                                     drizzled::NamedSavepoint &savepoint);
219
  virtual int doReleaseSavepoint(Session* session,
220
                                     drizzled::NamedSavepoint &savepoint);
221
  virtual int doCommit(Session* session, bool all);
222
  virtual int doRollback(Session* session, bool all);
223
224
  typedef std::map<std::string, EmbeddedInnoDBTableShare*> EmbeddedInnoDBMap;
225
  EmbeddedInnoDBMap embedded_innodb_open_tables;
226
  EmbeddedInnoDBTableShare *findOpenTable(const std::string table_name);
227
  void addOpenTable(const std::string &table_name, EmbeddedInnoDBTableShare *);
228
  void deleteOpenTable(const std::string &table_name);
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
229
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
230
  uint64_t getInitialAutoIncrementValue(EmbeddedInnoDBCursor *cursor);
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
231
  uint64_t getHiddenPrimaryKeyInitialAutoIncrementValue(EmbeddedInnoDBCursor *cursor);
232
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
233
};
234
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
235
static drizzled::plugin::StorageEngine *embedded_innodb_engine= NULL;
236
237
238
static ib_trx_t* get_trx(Session* session)
239
{
240
  return (ib_trx_t*) session->getEngineData(embedded_innodb_engine);
241
}
242
1283.63.1 by Stewart Smith
support SELECT ... FOR UPDATE locking for embedded_innodb. Do stupid shit because of the complete lack of error checking for startTableScan in parts of the upper layer.
243
/* This is a superset of the map from innobase plugin.
244
   Unlike innobase plugin we don't act on errors here, we just
245
   map error codes. */
246
static int ib_err_t_to_drizzle_error(ib_err_t err)
247
{
248
  switch (err)
249
  {
250
  case DB_SUCCESS:
251
    return 0;
252
253
  case DB_ERROR:
254
  default:
255
    return -1;
256
257
  case DB_INTERRUPTED:
258
    return ER_QUERY_INTERRUPTED; // FIXME: is this correct?
259
260
  case DB_OUT_OF_MEMORY:
261
    return HA_ERR_OUT_OF_MEM;
262
263
  case DB_DUPLICATE_KEY:
264
    return HA_ERR_FOUND_DUPP_KEY;
265
266
  case DB_FOREIGN_DUPLICATE_KEY:
267
    return HA_ERR_FOREIGN_DUPLICATE_KEY;
268
269
  case DB_MISSING_HISTORY:
270
    return HA_ERR_TABLE_DEF_CHANGED;
271
272
  case DB_RECORD_NOT_FOUND:
273
    return HA_ERR_NO_ACTIVE_RECORD;
274
275
  case DB_DEADLOCK:
276
    return HA_ERR_LOCK_DEADLOCK;
277
278
  case DB_LOCK_WAIT_TIMEOUT:
279
    return HA_ERR_LOCK_WAIT_TIMEOUT;
280
281
  case DB_NO_REFERENCED_ROW:
282
    return HA_ERR_NO_REFERENCED_ROW;
283
284
  case DB_ROW_IS_REFERENCED:
285
    return HA_ERR_ROW_IS_REFERENCED;
286
287
  case DB_CANNOT_ADD_CONSTRAINT:
288
    return HA_ERR_CANNOT_ADD_FOREIGN;
289
290
  case DB_CANNOT_DROP_CONSTRAINT:
291
    return HA_ERR_ROW_IS_REFERENCED; /* misleading. should have new err code */
292
293
  case DB_COL_APPEARS_TWICE_IN_INDEX:
294
  case DB_CORRUPTION:
295
    return HA_ERR_CRASHED;
296
297
  case DB_MUST_GET_MORE_FILE_SPACE:
298
  case DB_OUT_OF_FILE_SPACE:
299
    return HA_ERR_RECORD_FILE_FULL;
300
301
  case DB_TABLE_IS_BEING_USED:
302
    return HA_ERR_WRONG_COMMAND;
303
304
  case DB_TABLE_NOT_FOUND:
305
    return HA_ERR_NO_SUCH_TABLE;
306
307
  case DB_TOO_BIG_RECORD:
308
    return HA_ERR_TO_BIG_ROW;
309
310
  case DB_NO_SAVEPOINT:
311
    return HA_ERR_NO_SAVEPOINT;
312
313
  case DB_LOCK_TABLE_FULL:
314
    return HA_ERR_LOCK_TABLE_FULL;
315
316
  case DB_PRIMARY_KEY_IS_NULL:
317
    return ER_PRIMARY_CANT_HAVE_NULL;
318
319
  case DB_TOO_MANY_CONCURRENT_TRXS:
320
    return HA_ERR_RECORD_FILE_FULL; /* need better error code */
321
1283.65.5 by Stewart Smith
make ::index_first() use proper error conversion
322
  case DB_END_OF_INDEX:
323
    return HA_ERR_END_OF_FILE;
324
1283.63.1 by Stewart Smith
support SELECT ... FOR UPDATE locking for embedded_innodb. Do stupid shit because of the complete lack of error checking for startTableScan in parts of the upper layer.
325
  case DB_UNSUPPORTED:
326
    return HA_ERR_UNSUPPORTED;
327
  }
328
}
329
1283.61.8 by Stewart Smith
support correct isolation levels for Embedded InnoDB. READ COMMITTED doesn't work because of bug lp:587772 - it doesn't work for innobase either. We also add tests for READ UNCOMMITTED and REPEATABLE READ
330
static ib_trx_level_t tx_isolation_to_ib_trx_level(enum_tx_isolation level)
331
{
332
  switch(level)
333
  {
334
  case ISO_REPEATABLE_READ:
335
    return IB_TRX_REPEATABLE_READ;
336
  case ISO_READ_COMMITTED:
337
    return IB_TRX_READ_COMMITTED;
338
  case ISO_SERIALIZABLE:
339
    return IB_TRX_SERIALIZABLE;
340
  case ISO_READ_UNCOMMITTED:
341
    return IB_TRX_READ_UNCOMMITTED;
342
  }
1584 by Brian Aker
Fix for compiler warning.
343
344
  assert(0);
345
  return IB_TRX_REPEATABLE_READ;
1283.61.8 by Stewart Smith
support correct isolation levels for Embedded InnoDB. READ COMMITTED doesn't work because of bug lp:587772 - it doesn't work for innobase either. We also add tests for READ UNCOMMITTED and REPEATABLE READ
346
}
347
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
348
int EmbeddedInnoDBEngine::doStartTransaction(Session *session,
349
                                             start_transaction_option_t options)
350
{
351
  ib_trx_t *transaction;
1283.61.8 by Stewart Smith
support correct isolation levels for Embedded InnoDB. READ COMMITTED doesn't work because of bug lp:587772 - it doesn't work for innobase either. We also add tests for READ UNCOMMITTED and REPEATABLE READ
352
  ib_trx_level_t isolation_level;
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
353
354
  (void)options;
355
356
  transaction= get_trx(session);
1283.61.8 by Stewart Smith
support correct isolation levels for Embedded InnoDB. READ COMMITTED doesn't work because of bug lp:587772 - it doesn't work for innobase either. We also add tests for READ UNCOMMITTED and REPEATABLE READ
357
  isolation_level= tx_isolation_to_ib_trx_level((enum_tx_isolation)session_tx_isolation(session));
358
  *transaction= ib_trx_begin(isolation_level);
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
359
360
  return 0;
361
}
362
363
void EmbeddedInnoDBEngine::doStartStatement(Session *session)
364
{
365
  if(*get_trx(session) == NULL)
366
    doStartTransaction(session, START_TRANS_NO_OPTIONS);
1283.3.85 by Stewart Smith
take a savepoint at the start of each embedded innodb statement and roll back to that savepoint on error.
367
368
  ib_savepoint_take(*get_trx(session), statement_savepoint_name.c_str(),
369
                    statement_savepoint_name.length());
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
370
}
371
372
void EmbeddedInnoDBEngine::doEndStatement(Session *session)
373
{
374
  doCommit(session, false);
375
}
376
377
int EmbeddedInnoDBEngine::doSetSavepoint(Session* session,
378
                                         drizzled::NamedSavepoint &savepoint)
379
{
1283.3.86 by Stewart Smith
basic savepoints for embedded innodb
380
  ib_trx_t *transaction= get_trx(session);
381
  ib_savepoint_take(*transaction, savepoint.getName().c_str(),
382
                    savepoint.getName().length());
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
383
  return 0;
384
}
385
386
int EmbeddedInnoDBEngine::doRollbackToSavepoint(Session* session,
387
                                                drizzled::NamedSavepoint &savepoint)
388
{
1283.3.86 by Stewart Smith
basic savepoints for embedded innodb
389
  ib_trx_t *transaction= get_trx(session);
390
  ib_err_t err;
391
392
  err= ib_savepoint_rollback(*transaction, savepoint.getName().c_str(),
393
                             savepoint.getName().length());
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
394
1283.65.7 by Stewart Smith
make doRollbackToSavepoint use proper error conversion
395
  return ib_err_t_to_drizzle_error(err);
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
396
}
397
398
int EmbeddedInnoDBEngine::doReleaseSavepoint(Session* session,
399
                                             drizzled::NamedSavepoint &savepoint)
400
{
1283.3.86 by Stewart Smith
basic savepoints for embedded innodb
401
  ib_trx_t *transaction= get_trx(session);
402
  ib_err_t err;
403
404
  err= ib_savepoint_release(*transaction, savepoint.getName().c_str(),
405
                            savepoint.getName().length());
406
  if (err != DB_SUCCESS)
1283.63.7 by Stewart Smith
use proper error code conversion routine for parts of embedded_innodb
407
    return ib_err_t_to_drizzle_error(err);
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
408
409
  return 0;
410
}
411
412
int EmbeddedInnoDBEngine::doCommit(Session* session, bool all)
413
{
414
  ib_err_t err;
415
  ib_trx_t *transaction= get_trx(session);
416
417
  if (all || (!session_test_options(session, OPTION_NOT_AUTOCOMMIT | OPTION_BEGIN)))
418
  {
419
    err= ib_trx_commit(*transaction);
420
421
    if (err != DB_SUCCESS)
1283.63.7 by Stewart Smith
use proper error code conversion routine for parts of embedded_innodb
422
      return ib_err_t_to_drizzle_error(err);
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
423
424
    *transaction= NULL;
425
  }
426
427
  return 0;
428
}
429
430
int EmbeddedInnoDBEngine::doRollback(Session* session, bool all)
431
{
1283.3.83 by Stewart Smith
implement basic ROLLBACK (with test) for embedded innodb
432
  ib_err_t err;
433
  ib_trx_t *transaction= get_trx(session);
434
435
  if (all || !session_test_options(session, OPTION_NOT_AUTOCOMMIT | OPTION_BEGIN))
436
  {
437
    err= ib_trx_rollback(*transaction);
438
439
    if (err != DB_SUCCESS)
1283.63.7 by Stewart Smith
use proper error code conversion routine for parts of embedded_innodb
440
      return ib_err_t_to_drizzle_error(err);
1283.3.83 by Stewart Smith
implement basic ROLLBACK (with test) for embedded innodb
441
442
    *transaction= NULL;
443
  }
1283.3.85 by Stewart Smith
take a savepoint at the start of each embedded innodb statement and roll back to that savepoint on error.
444
  else
445
  {
446
    err= ib_savepoint_rollback(*transaction, statement_savepoint_name.c_str(),
447
                               statement_savepoint_name.length());
448
    if (err != DB_SUCCESS)
1283.63.7 by Stewart Smith
use proper error code conversion routine for parts of embedded_innodb
449
      return ib_err_t_to_drizzle_error(err);
1283.3.85 by Stewart Smith
take a savepoint at the start of each embedded innodb statement and roll back to that savepoint on error.
450
  }
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
451
452
  return 0;
453
}
454
455
EmbeddedInnoDBTableShare *EmbeddedInnoDBEngine::findOpenTable(const string table_name)
456
{
457
  EmbeddedInnoDBMap::iterator find_iter=
458
    embedded_innodb_open_tables.find(table_name);
459
460
  if (find_iter != embedded_innodb_open_tables.end())
461
    return (*find_iter).second;
462
  else
463
    return NULL;
464
}
465
466
void EmbeddedInnoDBEngine::addOpenTable(const string &table_name, EmbeddedInnoDBTableShare *share)
467
{
468
  embedded_innodb_open_tables[table_name]= share;
469
}
470
471
void EmbeddedInnoDBEngine::deleteOpenTable(const string &table_name)
472
{
473
  embedded_innodb_open_tables.erase(table_name);
474
}
475
476
static pthread_mutex_t embedded_innodb_mutex= PTHREAD_MUTEX_INITIALIZER;
477
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
478
uint64_t EmbeddedInnoDBCursor::getHiddenPrimaryKeyInitialAutoIncrementValue()
479
{
480
  uint64_t nr;
481
  ib_err_t err;
1578.6.2 by Brian Aker
Remove ha_session.
482
  ib_trx_t transaction= *get_trx(table->in_use);
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
483
  ib_cursor_attach_trx(cursor, transaction);
484
  tuple= ib_clust_read_tuple_create(cursor);
485
  err= ib_cursor_last(cursor);
486
  assert(err == DB_SUCCESS || err == DB_END_OF_INDEX); // Probably a FIXME
487
  err= ib_cursor_read_row(cursor, tuple);
488
  if (err == DB_RECORD_NOT_FOUND)
489
    nr= 1;
490
  else
491
  {
492
    assert (err == DB_SUCCESS);
1532.1.15 by Brian Aker
Partial encapsulation of TableShare from Table.
493
    err= ib_tuple_read_u64(tuple, table->getShare()->fields, &nr);
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
494
    nr++;
495
  }
496
  ib_tuple_delete(tuple);
497
  err= ib_cursor_reset(cursor);
498
  assert(err == DB_SUCCESS);
499
  return nr;
500
}
501
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
502
uint64_t EmbeddedInnoDBCursor::getInitialAutoIncrementValue()
503
{
504
  uint64_t nr;
505
  int error;
506
507
  (void) extra(HA_EXTRA_KEYREAD);
1532.1.15 by Brian Aker
Partial encapsulation of TableShare from Table.
508
  table->mark_columns_used_by_index_no_reset(table->getShare()->next_number_index);
509
  doStartIndexScan(table->getShare()->next_number_index, 1);
510
  if (table->getShare()->next_number_keypart == 0)
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
511
  {						// Autoincrement at key-start
1672.3.6 by Brian Aker
First pass in encapsulating row
512
    error=index_last(table->getUpdateRecord());
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
513
  }
514
  else
515
  {
516
    unsigned char key[MAX_KEY_LENGTH];
1672.3.6 by Brian Aker
First pass in encapsulating row
517
    key_copy(key, table->getInsertRecord(),
1532.1.15 by Brian Aker
Partial encapsulation of TableShare from Table.
518
             table->key_info + table->getShare()->next_number_index,
519
             table->getShare()->next_number_key_offset);
1672.3.6 by Brian Aker
First pass in encapsulating row
520
    error= index_read_map(table->getUpdateRecord(), key,
1532.1.15 by Brian Aker
Partial encapsulation of TableShare from Table.
521
                          make_prev_keypart_map(table->getShare()->next_number_keypart),
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
522
                          HA_READ_PREFIX_LAST);
523
  }
524
525
  if (error)
526
    nr=1;
527
  else
528
    nr= ((uint64_t) table->found_next_number_field->
1532.1.15 by Brian Aker
Partial encapsulation of TableShare from Table.
529
         val_int_offset(table->getShare()->rec_buff_length)+1);
1283.37.10 by Stewart Smith
getInitialAutoIncrementValue() calls new names for index_init and index_end()
530
  doEndIndexScan();
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
531
  (void) extra(HA_EXTRA_NO_KEYREAD);
532
1532.1.15 by Brian Aker
Partial encapsulation of TableShare from Table.
533
  if (table->getShare()->getTableProto()->options().auto_increment_value() > nr)
534
    nr= table->getShare()->getTableProto()->options().auto_increment_value();
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
535
536
  return nr;
537
}
538
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
539
EmbeddedInnoDBTableShare::EmbeddedInnoDBTableShare(const char* name, bool hidden_primary_key)
540
  : use_count(0), has_hidden_primary_key(hidden_primary_key)
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
541
{
542
  table_name.assign(name);
543
}
544
545
uint64_t EmbeddedInnoDBEngine::getInitialAutoIncrementValue(EmbeddedInnoDBCursor *cursor)
546
{
547
  doStartTransaction(current_session, START_TRANS_NO_OPTIONS);
548
  uint64_t initial_auto_increment_value= cursor->getInitialAutoIncrementValue();
549
  doCommit(current_session, true);
550
551
  return initial_auto_increment_value;
552
}
553
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
554
uint64_t EmbeddedInnoDBEngine::getHiddenPrimaryKeyInitialAutoIncrementValue(EmbeddedInnoDBCursor *cursor)
555
{
556
  doStartTransaction(current_session, START_TRANS_NO_OPTIONS);
557
  uint64_t initial_auto_increment_value= cursor->getHiddenPrimaryKeyInitialAutoIncrementValue();
558
  doCommit(current_session, true);
559
560
  return initial_auto_increment_value;
561
}
562
563
EmbeddedInnoDBTableShare *EmbeddedInnoDBCursor::get_share(const char *table_name, bool has_hidden_primary_key, int *rc)
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
564
{
565
  pthread_mutex_lock(&embedded_innodb_mutex);
566
567
  EmbeddedInnoDBEngine *a_engine= static_cast<EmbeddedInnoDBEngine *>(engine);
568
  share= a_engine->findOpenTable(table_name);
569
570
  if (!share)
571
  {
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
572
    share= new EmbeddedInnoDBTableShare(table_name, has_hidden_primary_key);
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
573
574
    if (share == NULL)
575
    {
576
      pthread_mutex_unlock(&embedded_innodb_mutex);
577
      *rc= HA_ERR_OUT_OF_MEM;
578
      return(NULL);
579
    }
580
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
581
    if (table->found_next_number_field)
582
    {
583
      share->auto_increment_value.fetch_and_store(
584
                                  a_engine->getInitialAutoIncrementValue(this));
585
586
    }
587
588
    if (has_hidden_primary_key)
589
    {
590
      uint64_t hidden_pkey= 0;
591
      hidden_pkey= a_engine->getHiddenPrimaryKeyInitialAutoIncrementValue(this);
592
      share->hidden_pkey_auto_increment_value.fetch_and_store(hidden_pkey);
593
    }
594
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
595
    a_engine->addOpenTable(share->table_name, share);
596
    thr_lock_init(&share->lock);
597
  }
598
  share->use_count++;
599
600
  pthread_mutex_unlock(&embedded_innodb_mutex);
601
602
  return(share);
603
}
604
605
int EmbeddedInnoDBCursor::free_share()
606
{
607
  pthread_mutex_lock(&embedded_innodb_mutex);
608
  if (!--share->use_count)
609
  {
610
    EmbeddedInnoDBEngine *a_engine= static_cast<EmbeddedInnoDBEngine *>(engine);
611
    a_engine->deleteOpenTable(share->table_name);
612
    delete share;
613
  }
614
  pthread_mutex_unlock(&embedded_innodb_mutex);
615
616
  return 0;
617
}
618
619
620
THR_LOCK_DATA **EmbeddedInnoDBCursor::store_lock(Session *session,
621
                                                 THR_LOCK_DATA **to,
622
                                                 thr_lock_type lock_type)
623
{
624
  /* Currently, we can get a transaction start by ::store_lock
625
     instead of beginTransaction, startStatement.
626
627
     See https://bugs.launchpad.net/drizzle/+bug/535528
628
629
     all stemming from the transactional engine interface needing
630
     a severe amount of immodium.
631
   */
632
633
  if(*get_trx(session) == NULL)
634
  {
1283.61.10 by Stewart Smith
static cast to EmbeddedInnoDBEngine, we don't need reinterpret in this path
635
    static_cast<EmbeddedInnoDBEngine*>(getEngine())->
1283.61.8 by Stewart Smith
support correct isolation levels for Embedded InnoDB. READ COMMITTED doesn't work because of bug lp:587772 - it doesn't work for innobase either. We also add tests for READ UNCOMMITTED and REPEATABLE READ
636
                    doStartTransaction(session, START_TRANS_NO_OPTIONS);
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
637
  }
638
1283.3.85 by Stewart Smith
take a savepoint at the start of each embedded innodb statement and roll back to that savepoint on error.
639
  if (lock_type != TL_UNLOCK)
640
  {
641
    ib_savepoint_take(*get_trx(session), statement_savepoint_name.c_str(),
642
                      statement_savepoint_name.length());
643
  }
644
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
645
  /* the below is just copied from ha_archive.cc in some dim hope it's
646
     kinda right. */
647
648
  if (lock_type != TL_IGNORE && lock.type == TL_UNLOCK)
649
  {
650
    /*
651
      Here is where we get into the guts of a row level lock.
652
      If TL_UNLOCK is set
653
      If we are not doing a LOCK Table or DISCARD/IMPORT
654
      TABLESPACE, then allow multiple writers
655
    */
656
657
    if ((lock_type >= TL_WRITE_CONCURRENT_INSERT &&
658
         lock_type <= TL_WRITE)
659
        && !session_tablespace_op(session))
660
      lock_type = TL_WRITE_ALLOW_WRITE;
661
662
    /*
663
      In queries of type INSERT INTO t1 SELECT ... FROM t2 ...
664
      MySQL would use the lock TL_READ_NO_INSERT on t2, and that
665
      would conflict with TL_WRITE_ALLOW_WRITE, blocking all inserts
666
      to t2. Convert the lock to a normal read lock to allow
667
      concurrent inserts to t2.
668
    */
669
670
    if (lock_type == TL_READ_NO_INSERT)
671
      lock_type = TL_READ;
672
673
    lock.type=lock_type;
674
  }
675
676
  *to++= &lock;
677
678
  return to;
679
}
680
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
681
void EmbeddedInnoDBCursor::get_auto_increment(uint64_t, //offset,
682
                                              uint64_t, //increment,
683
                                              uint64_t, //nb_dis,
684
                                              uint64_t *first_value,
685
                                              uint64_t *nb_reserved_values)
686
{
1283.37.4 by Stewart Smith
fix embedded_innodb auto_increment for negative values (just strange really).
687
fetch:
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
688
  *first_value= share->auto_increment_value.fetch_and_increment();
1283.37.4 by Stewart Smith
fix embedded_innodb auto_increment for negative values (just strange really).
689
  if (*first_value == 0)
690
  {
691
    /* if it's zero, then we skip it... why? because of ass.
692
       set auto-inc to -1 and the sequence is:
693
       -1, 1.
694
       Zero is still "magic".
695
    */
696
    share->auto_increment_value.compare_and_swap(1, 0);
697
    goto fetch;
698
  }
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
699
  *nb_reserved_values= 1;
700
}
701
1598.4.1 by Stewart Smith
support temporary tables in embedded_innodb - this means we can also run the alter_table test.
702
static const char* table_path_to_innodb_name(const char* name)
703
{
704
  size_t l= strlen(name);
705
706
  int slashes= 2;
707
  while(slashes>0 && l > 0)
708
  {
709
    l--;
710
    if (name[l] == '/')
711
      slashes--;
712
  }
713
  if (slashes==0)
714
    l++;
715
716
  return &name[l];
717
}
718
1627.2.6 by Monty Taylor
Merged in constification of TableIdentifier from Brian.
719
static void TableIdentifier_to_innodb_name(const TableIdentifier &identifier, std::string *str)
1283.11.19 by Stewart Smith
fix up create table for new bits of storage engine API r.e. TableIdentifier
720
{
1598.4.1 by Stewart Smith
support temporary tables in embedded_innodb - this means we can also run the alter_table test.
721
  str->assign(table_path_to_innodb_name(identifier.getPath().c_str()));
1283.11.19 by Stewart Smith
fix up create table for new bits of storage engine API r.e. TableIdentifier
722
}
723
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
724
EmbeddedInnoDBCursor::EmbeddedInnoDBCursor(drizzled::plugin::StorageEngine &engine_arg,
725
                           TableShare &table_arg)
1283.39.8 by Stewart Smith
add support for REPLACE to embedded_innodb. On duplicate key on insert if we have HA_EXTRA_WRITE_CAN_REPLACE set, then we delete the row and insert.
726
  :Cursor(engine_arg, table_arg),
1283.63.1 by Stewart Smith
support SELECT ... FOR UPDATE locking for embedded_innodb. Do stupid shit because of the complete lack of error checking for startTableScan in parts of the upper layer.
727
   ib_lock_mode(IB_LOCK_NONE),
1283.60.10 by Stewart Smith
the memory management for BLOBS is completely insane. For certain types of index lookups we *must* do a copy and clear it *only* in ::reset() or ::extra(). This patch fixes up any valgrind warnings/assertions for embedded_innodb executing type_blob test.
728
   write_can_replace(false),
729
   blobroot(NULL)
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
730
{ }
731
1283.63.28 by Stewart Smith
style fixes
732
static unsigned int get_first_unique_index(drizzled::Table &table)
1283.63.13 by Stewart Smith
fix ::rnd_pos and ::position (hence ref_length) for tables with implicit clustered/primary keys.
733
{
1283.63.28 by Stewart Smith
style fixes
734
  for (uint32_t k= 0; k < table.getShare()->keys; k++)
1283.63.13 by Stewart Smith
fix ::rnd_pos and ::position (hence ref_length) for tables with implicit clustered/primary keys.
735
  {
1283.63.28 by Stewart Smith
style fixes
736
    if (table.key_info[k].flags & HA_NOSAME)
1283.63.13 by Stewart Smith
fix ::rnd_pos and ::position (hence ref_length) for tables with implicit clustered/primary keys.
737
    {
738
      return k;
739
    }
740
  }
1283.63.28 by Stewart Smith
style fixes
741
1283.63.13 by Stewart Smith
fix ::rnd_pos and ::position (hence ref_length) for tables with implicit clustered/primary keys.
742
  return 0;
743
}
744
1283.3.27 by Stewart Smith
basic code to insert a integer
745
int EmbeddedInnoDBCursor::open(const char *name, int, uint32_t)
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
746
{
1598.4.1 by Stewart Smith
support temporary tables in embedded_innodb - this means we can also run the alter_table test.
747
  const char* innodb_table_name= table_path_to_innodb_name(name);
748
  ib_err_t err= ib_cursor_open_table(innodb_table_name, NULL, &cursor);
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
749
  bool has_hidden_primary_key= false;
750
  ib_id_t idx_id;
751
1283.63.7 by Stewart Smith
use proper error code conversion routine for parts of embedded_innodb
752
  if (err != DB_SUCCESS)
753
    return ib_err_t_to_drizzle_error(err);
754
1598.4.1 by Stewart Smith
support temporary tables in embedded_innodb - this means we can also run the alter_table test.
755
  err= ib_index_get_id(innodb_table_name, "HIDDEN_PRIMARY", &idx_id);
1283.63.11 by Stewart Smith
merge
756
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
757
  if (err == DB_SUCCESS)
758
    has_hidden_primary_key= true;
1283.3.27 by Stewart Smith
basic code to insert a integer
759
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
760
  int rc;
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
761
  share= get_share(name, has_hidden_primary_key, &rc);
1689.2.13 by Brian Aker
More encapsulation of thr_lock
762
  lock.init(&share->lock);
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
763
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
764
1618 by Brian Aker
This is a rollup set of patches for modifications to TableIdentifier to have
765
  if (table->getShare()->getPrimaryKey() != MAX_KEY)
766
    ref_length= table->key_info[table->getShare()->getPrimaryKey()].key_length;
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
767
  else if (share->has_hidden_primary_key)
768
    ref_length= sizeof(uint64_t);
1283.28.24 by Stewart Smith
store ref_length in ::open() for ::position() in embedded_innodb. This method doesn't work for tables without a primary key though.... :/
769
  else
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
770
  {
1283.63.28 by Stewart Smith
style fixes
771
    unsigned int keynr= get_first_unique_index(*table);
1283.63.13 by Stewart Smith
fix ::rnd_pos and ::position (hence ref_length) for tables with implicit clustered/primary keys.
772
    ref_length= table->key_info[keynr].key_length;
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
773
  }
1283.28.24 by Stewart Smith
store ref_length in ::open() for ::position() in embedded_innodb. This method doesn't work for tables without a primary key though.... :/
774
1283.60.11 by Stewart Smith
doStartTableScan() can be called twice in a row without a doEndTableScan()
775
  in_table_scan= false;
776
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
777
  return(0);
778
}
779
780
int EmbeddedInnoDBCursor::close(void)
781
{
1283.19.28 by Stewart Smith
fixup error checking
782
  ib_err_t err= ib_cursor_close(cursor);
783
  if (err != DB_SUCCESS)
1283.63.7 by Stewart Smith
use proper error code conversion routine for parts of embedded_innodb
784
    return ib_err_t_to_drizzle_error(err);
1283.19.28 by Stewart Smith
fixup error checking
785
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
786
  free_share();
787
1283.60.10 by Stewart Smith
the memory management for BLOBS is completely insane. For certain types of index lookups we *must* do a copy and clear it *only* in ::reset() or ::extra(). This patch fixes up any valgrind warnings/assertions for embedded_innodb executing type_blob test.
788
  delete blobroot;
789
  blobroot= NULL;
790
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
791
  return 0;
792
}
793
1283.61.8 by Stewart Smith
support correct isolation levels for Embedded InnoDB. READ COMMITTED doesn't work because of bug lp:587772 - it doesn't work for innobase either. We also add tests for READ UNCOMMITTED and REPEATABLE READ
794
int EmbeddedInnoDBCursor::external_lock(Session* session, int lock_type)
795
{
796
  ib_cursor_stmt_begin(cursor);
797
798
  (void)session;
1283.63.1 by Stewart Smith
support SELECT ... FOR UPDATE locking for embedded_innodb. Do stupid shit because of the complete lack of error checking for startTableScan in parts of the upper layer.
799
800
  if (lock_type == F_WRLCK)
801
  {
802
    /* SELECT ... FOR UPDATE or UPDATE TABLE */
803
    ib_lock_mode= IB_LOCK_X;
804
  }
805
  else
806
    ib_lock_mode= IB_LOCK_NONE;
1283.61.8 by Stewart Smith
support correct isolation levels for Embedded InnoDB. READ COMMITTED doesn't work because of bug lp:587772 - it doesn't work for innobase either. We also add tests for READ UNCOMMITTED and REPEATABLE READ
807
808
  return 0;
809
}
810
1283.3.13 by Stewart Smith
beginning of creating the table specified in the table proto. Embedded InnoDB now creates at least INT and VARCHAR types.
811
static int create_table_add_field(ib_tbl_sch_t schema,
1283.11.9 by Stewart Smith
create_table_add_field should take const reference of the field
812
                                  const message::Table::Field &field,
1283.3.13 by Stewart Smith
beginning of creating the table specified in the table proto. Embedded InnoDB now creates at least INT and VARCHAR types.
813
                                  ib_err_t *err)
814
{
815
  ib_col_attr_t column_attr= IB_COL_NONE;
816
1283.11.10 by Stewart Smith
fix setting of IB_COL_NOT_NULL flag
817
  if (field.has_constraints() && ! field.constraints().is_nullable())
1283.3.13 by Stewart Smith
beginning of creating the table specified in the table proto. Embedded InnoDB now creates at least INT and VARCHAR types.
818
    column_attr= IB_COL_NOT_NULL;
819
820
  switch (field.type())
821
  {
822
  case message::Table::Field::VARCHAR:
823
    *err= ib_table_schema_add_col(schema, field.name().c_str(), IB_VARCHAR,
824
                                  column_attr, 0,
825
                                  field.string_options().length());
826
    break;
827
  case message::Table::Field::INTEGER:
828
    *err= ib_table_schema_add_col(schema, field.name().c_str(), IB_INT,
829
                                  column_attr, 0, 4);
830
    break;
831
  case message::Table::Field::BIGINT:
832
    *err= ib_table_schema_add_col(schema, field.name().c_str(), IB_INT,
833
                                  column_attr, 0, 8);
834
    break;
1283.35.1 by Stewart Smith
basic DOUBLE type support. Currently fails some of the type_float test, researching error.
835
  case message::Table::Field::DOUBLE:
1283.35.45 by Stewart Smith
enable DATE type for embedded_innodb.
836
  case message::Table::Field::DATETIME:
1283.35.1 by Stewart Smith
basic DOUBLE type support. Currently fails some of the type_float test, researching error.
837
    *err= ib_table_schema_add_col(schema, field.name().c_str(), IB_DOUBLE,
838
                                  column_attr, 0, sizeof(double));
839
    break;
1283.35.27 by Stewart Smith
add ENUM SQL type support to Embedded InnoDB
840
  case message::Table::Field::ENUM:
841
  {
842
    message::Table::Field::EnumerationValues field_options=
843
      field.enumeration_values();
844
845
    if (field_options.field_value_size() <= 256)
846
      *err= ib_table_schema_add_col(schema, field.name().c_str(), IB_INT,
847
                                    column_attr, 0, 1);
848
    else if (field_options.field_value_size() > 256)
849
      *err= ib_table_schema_add_col(schema, field.name().c_str(), IB_INT,
850
                                    column_attr, 0, 2);
851
    else
852
    {
1579.3.14 by Stewart Smith
have a constant for the maximum number of enum elements
853
      assert(field_options.field_value_size() <= Field_enum::max_supported_elements);
1283.35.27 by Stewart Smith
add ENUM SQL type support to Embedded InnoDB
854
    }
855
    break;
856
  }
1283.35.45 by Stewart Smith
enable DATE type for embedded_innodb.
857
  case message::Table::Field::DATE:
1283.35.30 by Stewart Smith
support creating embedded_innodb tables with timestamp columns.
858
  case message::Table::Field::TIMESTAMP:
859
    *err= ib_table_schema_add_col(schema, field.name().c_str(), IB_INT,
860
                                  column_attr, 0, 4);
861
    break;
1283.60.5 by Stewart Smith
add BLOB support to embedded_innodb along with a simple test.
862
  case message::Table::Field::BLOB:
863
    *err= ib_table_schema_add_col(schema, field.name().c_str(), IB_BLOB,
864
                                  column_attr, 0, 0);
865
    break;
1283.61.1 by Stewart Smith
very simple addition to create fields of DECIMAL type
866
  case message::Table::Field::DECIMAL:
867
    *err= ib_table_schema_add_col(schema, field.name().c_str(), IB_DECIMAL,
868
                                  column_attr, 0, 0);
869
    break;
1283.3.13 by Stewart Smith
beginning of creating the table specified in the table proto. Embedded InnoDB now creates at least INT and VARCHAR types.
870
  default:
871
    my_error(ER_CHECK_NOT_IMPLEMENTED, MYF(0), "Column Type");
872
    return(HA_ERR_UNSUPPORTED);
873
  }
874
875
  return 0;
876
}
877
1283.17.15 by Stewart Smith
add proper error checking to store_table_message() and roll back the data dictionary transaction if there was an error storing the table proto
878
static ib_err_t store_table_message(ib_trx_t transaction, const char* table_name, drizzled::message::Table& table_message)
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
879
{
880
  ib_crsr_t cursor;
1283.17.11 by Stewart Smith
change data_dictionary.innodb_table_proto to data_dictionary.innodb_table_definition
881
  ib_tpl_t message_tuple;
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
882
  ib_err_t err;
1283.17.15 by Stewart Smith
add proper error checking to store_table_message() and roll back the data dictionary transaction if there was an error storing the table proto
883
  string serialized_message;
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
884
1283.17.12 by Stewart Smith
use define to set the name of the innodb_table_definitions table instead of repeating it 5 times through the code
885
  err= ib_cursor_open_table(INNODB_TABLE_DEFINITIONS_TABLE, transaction, &cursor);
1283.17.15 by Stewart Smith
add proper error checking to store_table_message() and roll back the data dictionary transaction if there was an error storing the table proto
886
  if (err != DB_SUCCESS)
887
    return err;
1283.17.11 by Stewart Smith
change data_dictionary.innodb_table_proto to data_dictionary.innodb_table_definition
888
889
  message_tuple= ib_clust_read_tuple_create(cursor);
890
891
  err= ib_col_set_value(message_tuple, 0, table_name, strlen(table_name));
1283.17.15 by Stewart Smith
add proper error checking to store_table_message() and roll back the data dictionary transaction if there was an error storing the table proto
892
  if (err != DB_SUCCESS)
893
    goto cleanup;
1283.17.11 by Stewart Smith
change data_dictionary.innodb_table_proto to data_dictionary.innodb_table_definition
894
1608.1.2 by Brian Aker
Merge enum test
895
  try {
896
    table_message.SerializeToString(&serialized_message);
897
  }
898
  catch (...)
899
  {
900
    goto cleanup;
901
  }
1283.17.11 by Stewart Smith
change data_dictionary.innodb_table_proto to data_dictionary.innodb_table_definition
902
903
  err= ib_col_set_value(message_tuple, 1, serialized_message.c_str(),
904
                        serialized_message.length());
1283.17.15 by Stewart Smith
add proper error checking to store_table_message() and roll back the data dictionary transaction if there was an error storing the table proto
905
  if (err != DB_SUCCESS)
906
    goto cleanup;
1283.17.11 by Stewart Smith
change data_dictionary.innodb_table_proto to data_dictionary.innodb_table_definition
907
908
  err= ib_cursor_insert_row(cursor, message_tuple);
909
1283.17.15 by Stewart Smith
add proper error checking to store_table_message() and roll back the data dictionary transaction if there was an error storing the table proto
910
cleanup:
1283.17.11 by Stewart Smith
change data_dictionary.innodb_table_proto to data_dictionary.innodb_table_definition
911
  ib_tuple_delete(message_tuple);
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
912
1283.19.28 by Stewart Smith
fixup error checking
913
  ib_err_t cleanup_err= ib_cursor_close(cursor);
914
  if (err == DB_SUCCESS)
915
    err= cleanup_err;
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
916
1283.17.15 by Stewart Smith
add proper error checking to store_table_message() and roll back the data dictionary transaction if there was an error storing the table proto
917
  return err;
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
918
}
919
1598.2.1 by Stewart Smith
support ROW_FORMAT for embedded_innodb. test both types of operation where DYNAMIC=COMPACT when runnning with antelope. it's all fail really... but anyway, the parsing works.
920
bool EmbeddedInnoDBEngine::validateCreateTableOption(const std::string &key,
921
                                                     const std::string &state)
922
{
923
  if (boost::iequals(key, "ROW_FORMAT"))
924
  {
925
    if (boost::iequals(state, "COMPRESSED"))
926
      return true;
927
928
    if (boost::iequals(state, "COMPACT"))
929
      return true;
930
931
    if (boost::iequals(state, "DYNAMIC"))
932
      return true;
933
934
    if (boost::iequals(state, "REDUNDANT"))
935
      return true;
936
  }
937
938
  return false;
939
}
940
941
static ib_tbl_fmt_t parse_ib_table_format(const std::string &value)
942
{
943
  if (boost::iequals(value, "REDUNDANT"))
944
    return IB_TBL_REDUNDANT;
945
  else if (boost::iequals(value, "COMPACT"))
946
    return IB_TBL_COMPACT;
947
  else if (boost::iequals(value, "DYNAMIC"))
948
    return IB_TBL_DYNAMIC;
949
  else if (boost::iequals(value, "COMPRESSED"))
950
    return IB_TBL_COMPRESSED;
951
952
  assert(false); /* You need to add possible table formats here */
953
  return IB_TBL_COMPACT;
954
}
1283.17.38 by Stewart Smith
merge trunk
955
1283.11.25 by Stewart Smith
merge trunk
956
int EmbeddedInnoDBEngine::doCreateTable(Session &session,
1283.11.19 by Stewart Smith
fix up create table for new bits of storage engine API r.e. TableIdentifier
957
                                        Table& table_obj,
1627.2.6 by Monty Taylor
Merged in constification of TableIdentifier from Brian.
958
                                        const drizzled::TableIdentifier &identifier,
1283.11.19 by Stewart Smith
fix up create table for new bits of storage engine API r.e. TableIdentifier
959
                                        drizzled::message::Table& table_message)
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
960
{
1283.3.12 by Stewart Smith
incredibly simple CREATE TABLE (and test) for embedded innodb. just creates a table with the supplied name (NOT with the supplied schema). Tests that we can't create the same table twice and that we're talking okay to libinnodb.
961
  ib_tbl_sch_t innodb_table_schema= NULL;
1283.3.13 by Stewart Smith
beginning of creating the table specified in the table proto. Embedded InnoDB now creates at least INT and VARCHAR types.
962
//  ib_idx_sch_t innodb_pkey= NULL;
1283.3.12 by Stewart Smith
incredibly simple CREATE TABLE (and test) for embedded innodb. just creates a table with the supplied name (NOT with the supplied schema). Tests that we can't create the same table twice and that we're talking okay to libinnodb.
963
  ib_trx_t innodb_schema_transaction;
964
  ib_id_t innodb_table_id;
965
  ib_err_t innodb_err= DB_SUCCESS;
1283.11.19 by Stewart Smith
fix up create table for new bits of storage engine API r.e. TableIdentifier
966
  string innodb_table_name;
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
967
  bool has_explicit_pkey= false;
1283.11.25 by Stewart Smith
merge trunk
968
1283.3.12 by Stewart Smith
incredibly simple CREATE TABLE (and test) for embedded innodb. just creates a table with the supplied name (NOT with the supplied schema). Tests that we can't create the same table twice and that we're talking okay to libinnodb.
969
  (void)table_obj;
970
1598.4.1 by Stewart Smith
support temporary tables in embedded_innodb - this means we can also run the alter_table test.
971
  if (table_message.type() == message::Table::TEMPORARY)
972
  {
973
    ib_bool_t create_db_err= ib_database_create(GLOBAL_TEMPORARY_EXT);
974
    if (create_db_err != IB_TRUE)
975
      return -1;
976
  }
977
1283.11.19 by Stewart Smith
fix up create table for new bits of storage engine API r.e. TableIdentifier
978
  TableIdentifier_to_innodb_name(identifier, &innodb_table_name);
979
1598.2.1 by Stewart Smith
support ROW_FORMAT for embedded_innodb. test both types of operation where DYNAMIC=COMPACT when runnning with antelope. it's all fail really... but anyway, the parsing works.
980
  ib_tbl_fmt_t innodb_table_format= IB_TBL_COMPACT;
981
982
  const size_t num_engine_options= table_message.engine().options_size();
983
  for (size_t x= 0; x < num_engine_options; x++)
984
  {
985
    const message::Engine::Option &engine_option= table_message.engine().options(x);
986
    if (boost::iequals(engine_option.name(), "ROW_FORMAT"))
987
    {
988
      innodb_table_format= parse_ib_table_format(engine_option.state());
989
    }
990
  }
991
1283.11.19 by Stewart Smith
fix up create table for new bits of storage engine API r.e. TableIdentifier
992
  innodb_err= ib_table_schema_create(innodb_table_name.c_str(),
1598.2.1 by Stewart Smith
support ROW_FORMAT for embedded_innodb. test both types of operation where DYNAMIC=COMPACT when runnning with antelope. it's all fail really... but anyway, the parsing works.
993
                                     &innodb_table_schema,
994
                                     innodb_table_format, 0);
1283.3.12 by Stewart Smith
incredibly simple CREATE TABLE (and test) for embedded innodb. just creates a table with the supplied name (NOT with the supplied schema). Tests that we can't create the same table twice and that we're talking okay to libinnodb.
995
996
  if (innodb_err != DB_SUCCESS)
997
  {
1283.11.25 by Stewart Smith
merge trunk
998
    push_warning_printf(&session, DRIZZLE_ERROR::WARN_LEVEL_ERROR,
1283.3.12 by Stewart Smith
incredibly simple CREATE TABLE (and test) for embedded innodb. just creates a table with the supplied name (NOT with the supplied schema). Tests that we can't create the same table twice and that we're talking okay to libinnodb.
999
                        ER_CANT_CREATE_TABLE,
1000
                        _("Cannot create table %s. InnoDB Error %d (%s)\n"),
1283.11.19 by Stewart Smith
fix up create table for new bits of storage engine API r.e. TableIdentifier
1001
                        innodb_table_name.c_str(), innodb_err, ib_strerror(innodb_err));
1283.63.7 by Stewart Smith
use proper error code conversion routine for parts of embedded_innodb
1002
    return ib_err_t_to_drizzle_error(innodb_err);
1283.3.12 by Stewart Smith
incredibly simple CREATE TABLE (and test) for embedded innodb. just creates a table with the supplied name (NOT with the supplied schema). Tests that we can't create the same table twice and that we're talking okay to libinnodb.
1003
  }
1004
1283.3.13 by Stewart Smith
beginning of creating the table specified in the table proto. Embedded InnoDB now creates at least INT and VARCHAR types.
1005
  for (int colnr= 0; colnr < table_message.field_size() ; colnr++)
1006
  {
1007
    const message::Table::Field field = table_message.field(colnr);
1008
1009
    int field_err= create_table_add_field(innodb_table_schema, field,
1010
                                          &innodb_err);
1011
1012
    if (innodb_err != DB_SUCCESS || field_err != 0)
1013
      ib_table_schema_delete(innodb_table_schema); /* cleanup */
1014
1015
    if (innodb_err != DB_SUCCESS)
1016
    {
1283.11.25 by Stewart Smith
merge trunk
1017
      push_warning_printf(&session, DRIZZLE_ERROR::WARN_LEVEL_ERROR,
1283.3.13 by Stewart Smith
beginning of creating the table specified in the table proto. Embedded InnoDB now creates at least INT and VARCHAR types.
1018
                          ER_CANT_CREATE_TABLE,
1019
                          _("Cannot create field %s on table %s."
1020
                            " InnoDB Error %d (%s)\n"),
1283.11.19 by Stewart Smith
fix up create table for new bits of storage engine API r.e. TableIdentifier
1021
                          field.name().c_str(), innodb_table_name.c_str(),
1283.3.13 by Stewart Smith
beginning of creating the table specified in the table proto. Embedded InnoDB now creates at least INT and VARCHAR types.
1022
                          innodb_err, ib_strerror(innodb_err));
1283.63.7 by Stewart Smith
use proper error code conversion routine for parts of embedded_innodb
1023
      return ib_err_t_to_drizzle_error(innodb_err);
1283.3.13 by Stewart Smith
beginning of creating the table specified in the table proto. Embedded InnoDB now creates at least INT and VARCHAR types.
1024
    }
1025
    if (field_err != 0)
1026
      return field_err;
1027
  }
1283.3.37 by Stewart Smith
basic support for indexes in CREATE TABLE for embedded innodb engine
1028
1283.35.49 by Stewart Smith
allow embedded_innodb tables to be created with a first not null unique index instead of just explicit PRIMARY KEY. We use this key as the clustered index (which is really our requirement)
1029
  bool has_primary= false;
1283.3.37 by Stewart Smith
basic support for indexes in CREATE TABLE for embedded innodb engine
1030
  for (int indexnr= 0; indexnr < table_message.indexes_size() ; indexnr++)
1031
  {
1032
    message::Table::Index *index = table_message.mutable_indexes(indexnr);
1033
1034
    ib_idx_sch_t innodb_index;
1035
1283.18.31 by Stewart Smith
fix up error handling in index creation
1036
    innodb_err= ib_table_schema_add_index(innodb_table_schema, index->name().c_str(),
1037
                                   &innodb_index);
1038
    if (innodb_err != DB_SUCCESS)
1039
      goto schema_error;
1283.3.37 by Stewart Smith
basic support for indexes in CREATE TABLE for embedded innodb engine
1040
1041
    if (index->is_primary())
1283.18.31 by Stewart Smith
fix up error handling in index creation
1042
    {
1283.35.49 by Stewart Smith
allow embedded_innodb tables to be created with a first not null unique index instead of just explicit PRIMARY KEY. We use this key as the clustered index (which is really our requirement)
1043
      has_primary= true;
1283.18.31 by Stewart Smith
fix up error handling in index creation
1044
      innodb_err= ib_index_schema_set_clustered(innodb_index);
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
1045
      has_explicit_pkey= true;
1283.18.31 by Stewart Smith
fix up error handling in index creation
1046
      if (innodb_err != DB_SUCCESS)
1047
        goto schema_error;
1048
    }
1283.3.37 by Stewart Smith
basic support for indexes in CREATE TABLE for embedded innodb engine
1049
1050
    if (index->is_unique())
1283.18.31 by Stewart Smith
fix up error handling in index creation
1051
    {
1052
      innodb_err= ib_index_schema_set_unique(innodb_index);
1053
      if (innodb_err != DB_SUCCESS)
1054
        goto schema_error;
1055
    }
1283.3.37 by Stewart Smith
basic support for indexes in CREATE TABLE for embedded innodb engine
1056
1057
    if (index->type() == message::Table::Index::UNKNOWN_INDEX)
1058
      index->set_type(message::Table::Index::BTREE);
1059
1060
    for (int partnr= 0; partnr < index->index_part_size(); partnr++)
1061
    {
1062
      const message::Table::Index::IndexPart part= index->index_part(partnr);
1283.67.1 by Stewart Smith
support prefix indexes in embedded_innodb. Add a test and get things right for the different collations (utf8 or binary)
1063
      const message::Table::Field::FieldType part_type= table_message.field(part.fieldnr()).type();
1064
      uint64_t compare_length= 0;
1065
1283.67.12 by Stewart Smith
prefix index fix for previosu Table protobuf fix for compare_length()
1066
      if (part_type == message::Table::Field::BLOB
1067
          || part_type == message::Table::Field::VARCHAR)
1283.67.1 by Stewart Smith
support prefix indexes in embedded_innodb. Add a test and get things right for the different collations (utf8 or binary)
1068
        compare_length= part.compare_length();
1069
1070
      innodb_err= ib_index_schema_add_col(innodb_index,
1071
                            table_message.field(part.fieldnr()).name().c_str(),
1072
                                          compare_length);
1283.18.31 by Stewart Smith
fix up error handling in index creation
1073
      if (innodb_err != DB_SUCCESS)
1074
        goto schema_error;
1283.3.37 by Stewart Smith
basic support for indexes in CREATE TABLE for embedded innodb engine
1075
    }
1283.35.49 by Stewart Smith
allow embedded_innodb tables to be created with a first not null unique index instead of just explicit PRIMARY KEY. We use this key as the clustered index (which is really our requirement)
1076
1077
    if (! has_primary && index->is_unique())
1078
    {
1079
      innodb_err= ib_index_schema_set_clustered(innodb_index);
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
1080
      has_explicit_pkey= true;
1283.35.49 by Stewart Smith
allow embedded_innodb tables to be created with a first not null unique index instead of just explicit PRIMARY KEY. We use this key as the clustered index (which is really our requirement)
1081
      if (innodb_err != DB_SUCCESS)
1082
        goto schema_error;
1083
    }
1084
1283.3.37 by Stewart Smith
basic support for indexes in CREATE TABLE for embedded innodb engine
1085
  }
1086
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
1087
  if (! has_explicit_pkey)
1088
  {
1089
    ib_idx_sch_t innodb_index;
1090
1091
    innodb_err= ib_table_schema_add_col(innodb_table_schema, "hidden_primary_key_col",
1092
                                        IB_INT, IB_COL_NOT_NULL, 0, 8);
1093
1094
    innodb_err= ib_table_schema_add_index(innodb_table_schema, "HIDDEN_PRIMARY",
1095
                                          &innodb_index);
1096
    if (innodb_err != DB_SUCCESS)
1097
      goto schema_error;
1098
1099
    innodb_err= ib_index_schema_set_clustered(innodb_index);
1100
    if (innodb_err != DB_SUCCESS)
1101
      goto schema_error;
1102
1103
    innodb_err= ib_index_schema_add_col(innodb_index, "hidden_primary_key_col", 0);
1104
    if (innodb_err != DB_SUCCESS)
1105
      goto schema_error;
1106
  }
1107
1283.3.12 by Stewart Smith
incredibly simple CREATE TABLE (and test) for embedded innodb. just creates a table with the supplied name (NOT with the supplied schema). Tests that we can't create the same table twice and that we're talking okay to libinnodb.
1108
  innodb_schema_transaction= ib_trx_begin(IB_TRX_REPEATABLE_READ);
1283.11.15 by Stewart Smith
fix up checking return codes used in CREATE TABLE for Embedded InnoDB Engine
1109
  innodb_err= ib_schema_lock_exclusive(innodb_schema_transaction);
1110
  if (innodb_err != DB_SUCCESS)
1111
  {
1112
    ib_err_t rollback_err= ib_trx_rollback(innodb_schema_transaction);
1113
    ib_table_schema_delete(innodb_table_schema);
1114
1283.11.25 by Stewart Smith
merge trunk
1115
    push_warning_printf(&session, DRIZZLE_ERROR::WARN_LEVEL_ERROR,
1283.11.15 by Stewart Smith
fix up checking return codes used in CREATE TABLE for Embedded InnoDB Engine
1116
                        ER_CANT_CREATE_TABLE,
1117
                        _("Cannot Lock Embedded InnoDB Data Dictionary. InnoDB Error %d (%s)\n"),
1118
                        innodb_err, ib_strerror(innodb_err));
1119
1120
    assert (rollback_err == DB_SUCCESS);
1121
1122
    return HA_ERR_GENERIC;
1123
  }
1283.3.12 by Stewart Smith
incredibly simple CREATE TABLE (and test) for embedded innodb. just creates a table with the supplied name (NOT with the supplied schema). Tests that we can't create the same table twice and that we're talking okay to libinnodb.
1124
1125
  innodb_err= ib_table_create(innodb_schema_transaction, innodb_table_schema,
1126
                              &innodb_table_id);
1127
1128
  if (innodb_err != DB_SUCCESS)
1129
  {
1283.11.15 by Stewart Smith
fix up checking return codes used in CREATE TABLE for Embedded InnoDB Engine
1130
    ib_err_t rollback_err= ib_trx_rollback(innodb_schema_transaction);
1283.3.12 by Stewart Smith
incredibly simple CREATE TABLE (and test) for embedded innodb. just creates a table with the supplied name (NOT with the supplied schema). Tests that we can't create the same table twice and that we're talking okay to libinnodb.
1131
    ib_table_schema_delete(innodb_table_schema);
1132
1133
    if (innodb_err == DB_TABLE_IS_BEING_USED)
1134
      return EEXIST;
1135
1283.11.25 by Stewart Smith
merge trunk
1136
    push_warning_printf(&session, DRIZZLE_ERROR::WARN_LEVEL_ERROR,
1283.3.12 by Stewart Smith
incredibly simple CREATE TABLE (and test) for embedded innodb. just creates a table with the supplied name (NOT with the supplied schema). Tests that we can't create the same table twice and that we're talking okay to libinnodb.
1137
                        ER_CANT_CREATE_TABLE,
1138
                        _("Cannot create table %s. InnoDB Error %d (%s)\n"),
1283.11.19 by Stewart Smith
fix up create table for new bits of storage engine API r.e. TableIdentifier
1139
                        innodb_table_name.c_str(),
1140
                        innodb_err, ib_strerror(innodb_err));
1283.11.15 by Stewart Smith
fix up checking return codes used in CREATE TABLE for Embedded InnoDB Engine
1141
1142
    assert (rollback_err == DB_SUCCESS);
1283.3.12 by Stewart Smith
incredibly simple CREATE TABLE (and test) for embedded innodb. just creates a table with the supplied name (NOT with the supplied schema). Tests that we can't create the same table twice and that we're talking okay to libinnodb.
1143
    return HA_ERR_GENERIC;
1144
  }
1145
1598.4.1 by Stewart Smith
support temporary tables in embedded_innodb - this means we can also run the alter_table test.
1146
  if (table_message.type() == message::Table::TEMPORARY)
1147
  {
1148
    session.storeTableMessage(identifier, table_message);
1149
    innodb_err= DB_SUCCESS;
1150
  }
1151
  else
1152
    innodb_err= store_table_message(innodb_schema_transaction,
1153
                                    innodb_table_name.c_str(),
1154
                                    table_message);
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
1155
1283.17.15 by Stewart Smith
add proper error checking to store_table_message() and roll back the data dictionary transaction if there was an error storing the table proto
1156
  if (innodb_err == DB_SUCCESS)
1157
    innodb_err= ib_trx_commit(innodb_schema_transaction);
1158
  else
1159
    innodb_err= ib_trx_rollback(innodb_schema_transaction);
1283.3.12 by Stewart Smith
incredibly simple CREATE TABLE (and test) for embedded innodb. just creates a table with the supplied name (NOT with the supplied schema). Tests that we can't create the same table twice and that we're talking okay to libinnodb.
1160
1283.18.31 by Stewart Smith
fix up error handling in index creation
1161
schema_error:
1283.3.12 by Stewart Smith
incredibly simple CREATE TABLE (and test) for embedded innodb. just creates a table with the supplied name (NOT with the supplied schema). Tests that we can't create the same table twice and that we're talking okay to libinnodb.
1162
  ib_table_schema_delete(innodb_table_schema);
1163
1164
  if (innodb_err != DB_SUCCESS)
1165
  {
1283.11.25 by Stewart Smith
merge trunk
1166
    push_warning_printf(&session, DRIZZLE_ERROR::WARN_LEVEL_ERROR,
1283.3.12 by Stewart Smith
incredibly simple CREATE TABLE (and test) for embedded innodb. just creates a table with the supplied name (NOT with the supplied schema). Tests that we can't create the same table twice and that we're talking okay to libinnodb.
1167
                        ER_CANT_CREATE_TABLE,
1168
                        _("Cannot create table %s. InnoDB Error %d (%s)\n"),
1283.11.19 by Stewart Smith
fix up create table for new bits of storage engine API r.e. TableIdentifier
1169
                        innodb_table_name.c_str(),
1170
                        innodb_err, ib_strerror(innodb_err));
1283.63.7 by Stewart Smith
use proper error code conversion routine for parts of embedded_innodb
1171
    return ib_err_t_to_drizzle_error(innodb_err);
1283.3.12 by Stewart Smith
incredibly simple CREATE TABLE (and test) for embedded innodb. just creates a table with the supplied name (NOT with the supplied schema). Tests that we can't create the same table twice and that we're talking okay to libinnodb.
1172
  }
1173
1174
  return 0;
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
1175
}
1176
1283.17.11 by Stewart Smith
change data_dictionary.innodb_table_proto to data_dictionary.innodb_table_definition
1177
static int delete_table_message_from_innodb(ib_trx_t transaction, const char* table_name)
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
1178
{
1179
  ib_crsr_t cursor;
1180
  ib_tpl_t search_tuple;
1181
  int res;
1182
  ib_err_t err;
1183
1283.19.28 by Stewart Smith
fixup error checking
1184
  err= ib_cursor_open_table(INNODB_TABLE_DEFINITIONS_TABLE, transaction, &cursor);
1185
  if (err != DB_SUCCESS)
1186
    return err;
1187
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
1188
  search_tuple= ib_clust_search_tuple_create(cursor);
1189
1283.19.28 by Stewart Smith
fixup error checking
1190
  err= ib_col_set_value(search_tuple, 0, table_name, strlen(table_name));
1191
  if (err != DB_SUCCESS)
1192
    goto rollback;
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
1193
1194
//  ib_cursor_set_match_mode(cursor, IB_EXACT_MATCH);
1195
1196
  err= ib_cursor_moveto(cursor, search_tuple, IB_CUR_GE, &res);
1197
  if (err == DB_RECORD_NOT_FOUND || res != 0)
1198
    goto rollback;
1199
1200
  err= ib_cursor_delete_row(cursor);
1201
  assert (err == DB_SUCCESS);
1202
1203
rollback:
1283.19.28 by Stewart Smith
fixup error checking
1204
  ib_err_t rollback_err= ib_cursor_close(cursor);
1205
  if (err == DB_SUCCESS)
1206
    err= rollback_err;
1207
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
1208
  ib_tuple_delete(search_tuple);
1209
1210
  return err;
1211
}
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
1212
1283.15.22 by Stewart Smith
fix up drop table for new bits of storage engine API r.e. TableIdentifier
1213
int EmbeddedInnoDBEngine::doDropTable(Session &session,
1627.2.6 by Monty Taylor
Merged in constification of TableIdentifier from Brian.
1214
                                      const TableIdentifier &identifier)
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
1215
{
1283.3.23 by Stewart Smith
Add basic DROP TABLE support to embedded innodb engine.
1216
  ib_trx_t innodb_schema_transaction;
1217
  ib_err_t innodb_err;
1283.15.22 by Stewart Smith
fix up drop table for new bits of storage engine API r.e. TableIdentifier
1218
  string innodb_table_name;
1219
1220
  TableIdentifier_to_innodb_name(identifier, &innodb_table_name);
1283.3.23 by Stewart Smith
Add basic DROP TABLE support to embedded innodb engine.
1221
1222
  innodb_schema_transaction= ib_trx_begin(IB_TRX_REPEATABLE_READ);
1283.15.18 by Stewart Smith
lock schema in drop table (needed for drop table to work
1223
  innodb_err= ib_schema_lock_exclusive(innodb_schema_transaction);
1224
  if (innodb_err != DB_SUCCESS)
1225
  {
1226
    ib_err_t rollback_err= ib_trx_rollback(innodb_schema_transaction);
1227
1228
    push_warning_printf(&session, DRIZZLE_ERROR::WARN_LEVEL_ERROR,
1229
                        ER_CANT_DELETE_FILE,
1230
                        _("Cannot Lock Embedded InnoDB Data Dictionary. InnoDB Error %d (%s)\n"),
1231
                        innodb_err, ib_strerror(innodb_err));
1232
1233
    assert (rollback_err == DB_SUCCESS);
1234
1235
    return HA_ERR_GENERIC;
1236
  }
1283.3.23 by Stewart Smith
Add basic DROP TABLE support to embedded innodb engine.
1237
1598.4.1 by Stewart Smith
support temporary tables in embedded_innodb - this means we can also run the alter_table test.
1238
  if (identifier.getType() == message::Table::TEMPORARY)
1239
  {
1240
      session.removeTableMessage(identifier);
1241
      delete_table_message_from_innodb(innodb_schema_transaction,
1242
                                       innodb_table_name.c_str());
1243
  }
1244
  else
1245
  {
1246
    if (delete_table_message_from_innodb(innodb_schema_transaction, innodb_table_name.c_str()) != DB_SUCCESS)
1247
    {
1248
      ib_schema_unlock(innodb_schema_transaction);
1249
      ib_err_t rollback_err= ib_trx_rollback(innodb_schema_transaction);
1250
      assert(rollback_err == DB_SUCCESS);
1251
      return HA_ERR_GENERIC;
1252
    }
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
1253
  }
1254
1283.15.22 by Stewart Smith
fix up drop table for new bits of storage engine API r.e. TableIdentifier
1255
  innodb_err= ib_table_drop(innodb_schema_transaction, innodb_table_name.c_str());
1283.3.23 by Stewart Smith
Add basic DROP TABLE support to embedded innodb engine.
1256
1257
  if (innodb_err == DB_TABLE_NOT_FOUND)
1258
  {
1283.15.17 by Stewart Smith
assert out on rollback errors in error states in drop table
1259
    innodb_err= ib_trx_rollback(innodb_schema_transaction);
1260
    assert(innodb_err == DB_SUCCESS);
1283.3.23 by Stewart Smith
Add basic DROP TABLE support to embedded innodb engine.
1261
    return ENOENT;
1262
  }
1263
  else if (innodb_err != DB_SUCCESS)
1264
  {
1283.15.17 by Stewart Smith
assert out on rollback errors in error states in drop table
1265
    ib_err_t rollback_err= ib_trx_rollback(innodb_schema_transaction);
1283.3.23 by Stewart Smith
Add basic DROP TABLE support to embedded innodb engine.
1266
1267
    push_warning_printf(&session, DRIZZLE_ERROR::WARN_LEVEL_ERROR,
1268
                        ER_CANT_DELETE_FILE,
1269
                        _("Cannot DROP table %s. InnoDB Error %d (%s)\n"),
1283.15.22 by Stewart Smith
fix up drop table for new bits of storage engine API r.e. TableIdentifier
1270
                        innodb_table_name.c_str(),
1283.3.23 by Stewart Smith
Add basic DROP TABLE support to embedded innodb engine.
1271
                        innodb_err, ib_strerror(innodb_err));
1283.15.17 by Stewart Smith
assert out on rollback errors in error states in drop table
1272
1273
    assert(rollback_err == DB_SUCCESS);
1274
1283.3.23 by Stewart Smith
Add basic DROP TABLE support to embedded innodb engine.
1275
    return HA_ERR_GENERIC;
1276
  }
1277
1278
  innodb_err= ib_trx_commit(innodb_schema_transaction);
1279
  if (innodb_err != DB_SUCCESS)
1280
  {
1283.15.17 by Stewart Smith
assert out on rollback errors in error states in drop table
1281
    ib_err_t rollback_err= ib_trx_rollback(innodb_schema_transaction);
1283.3.23 by Stewart Smith
Add basic DROP TABLE support to embedded innodb engine.
1282
1283
    push_warning_printf(&session, DRIZZLE_ERROR::WARN_LEVEL_ERROR,
1284
                        ER_CANT_DELETE_FILE,
1285
                        _("Cannot DROP table %s. InnoDB Error %d (%s)\n"),
1283.15.22 by Stewart Smith
fix up drop table for new bits of storage engine API r.e. TableIdentifier
1286
                        innodb_table_name.c_str(),
1283.3.23 by Stewart Smith
Add basic DROP TABLE support to embedded innodb engine.
1287
                        innodb_err, ib_strerror(innodb_err));
1283.15.17 by Stewart Smith
assert out on rollback errors in error states in drop table
1288
1289
    assert(rollback_err == DB_SUCCESS);
1283.3.23 by Stewart Smith
Add basic DROP TABLE support to embedded innodb engine.
1290
    return HA_ERR_GENERIC;
1291
  }
1292
1293
  return 0;
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
1294
}
1295
1627.2.6 by Monty Taylor
Merged in constification of TableIdentifier from Brian.
1296
static ib_err_t rename_table_message(ib_trx_t transaction, const TableIdentifier &from_identifier, const TableIdentifier &to_identifier)
1283.28.2 by Stewart Smith
add basic RENAME TABLE support for Embedded InnoDB. Also add a basic test, and copy over the rename.test test and run it against embedded innodb.
1297
{
1298
  ib_crsr_t cursor;
1299
  ib_tpl_t search_tuple;
1300
  ib_tpl_t read_tuple;
1301
  ib_tpl_t update_tuple;
1302
  int res;
1303
  ib_err_t err;
1304
  ib_err_t rollback_err;
1283.30.12 by Stewart Smith
fix rename table for new prototype as well as that table names are read from the proto instead of from getTableNames, which means on rename we must read the table proto, modify ita nd then store it again.
1305
  const char *message;
1306
  ib_ulint_t message_len;
1307
  drizzled::message::Table table_message;
1308
  string from_innodb_table_name;
1309
  string to_innodb_table_name;
1310
  const char *from;
1311
  const char *to;
1312
  string serialized_message;
1313
  ib_col_meta_t col_meta;
1314
1315
  TableIdentifier_to_innodb_name(from_identifier, &from_innodb_table_name);
1316
  TableIdentifier_to_innodb_name(to_identifier, &to_innodb_table_name);
1317
1318
  from= from_innodb_table_name.c_str();
1319
  to= to_innodb_table_name.c_str();
1283.28.2 by Stewart Smith
add basic RENAME TABLE support for Embedded InnoDB. Also add a basic test, and copy over the rename.test test and run it against embedded innodb.
1320
1321
  err= ib_cursor_open_table(INNODB_TABLE_DEFINITIONS_TABLE, transaction, &cursor);
1322
  if (err != DB_SUCCESS)
1323
  {
1324
    rollback_err= ib_trx_rollback(transaction);
1325
    assert(rollback_err == DB_SUCCESS);
1326
    return err;
1327
  }
1328
1329
  search_tuple= ib_clust_search_tuple_create(cursor);
1330
  read_tuple= ib_clust_read_tuple_create(cursor);
1331
1332
  err= ib_col_set_value(search_tuple, 0, from, strlen(from));
1333
  if (err != DB_SUCCESS)
1334
    goto rollback;
1335
1336
//  ib_cursor_set_match_mode(cursor, IB_EXACT_MATCH);
1337
1338
  err= ib_cursor_moveto(cursor, search_tuple, IB_CUR_GE, &res);
1339
  if (err == DB_RECORD_NOT_FOUND || res != 0)
1340
    goto rollback;
1341
1342
  err= ib_cursor_read_row(cursor, read_tuple);
1343
  if (err == DB_RECORD_NOT_FOUND || res != 0)
1344
    goto rollback;
1345
1283.30.12 by Stewart Smith
fix rename table for new prototype as well as that table names are read from the proto instead of from getTableNames, which means on rename we must read the table proto, modify ita nd then store it again.
1346
  message= (const char*)ib_col_get_value(read_tuple, 1);
1347
  message_len= ib_col_get_meta(read_tuple, 1, &col_meta);
1348
1349
  if (table_message.ParseFromArray(message, message_len) == false)
1350
    goto rollback;
1351
1352
  table_message.set_name(to_identifier.getTableName());
1353
  table_message.set_schema(to_identifier.getSchemaName());
1354
1283.28.2 by Stewart Smith
add basic RENAME TABLE support for Embedded InnoDB. Also add a basic test, and copy over the rename.test test and run it against embedded innodb.
1355
  update_tuple= ib_clust_read_tuple_create(cursor);
1356
1357
  err= ib_tuple_copy(update_tuple, read_tuple);
1358
  assert(err == DB_SUCCESS);
1359
1360
  err= ib_col_set_value(update_tuple, 0, to, strlen(to));
1283.30.12 by Stewart Smith
fix rename table for new prototype as well as that table names are read from the proto instead of from getTableNames, which means on rename we must read the table proto, modify ita nd then store it again.
1361
1608.1.2 by Brian Aker
Merge enum test
1362
  try {
1363
    table_message.SerializeToString(&serialized_message);
1364
  }
1365
  catch (...)
1366
  {
1367
    goto rollback;
1368
  }
1283.30.12 by Stewart Smith
fix rename table for new prototype as well as that table names are read from the proto instead of from getTableNames, which means on rename we must read the table proto, modify ita nd then store it again.
1369
1370
  err= ib_col_set_value(update_tuple, 1, serialized_message.c_str(),
1371
                        serialized_message.length());
1372
1283.28.2 by Stewart Smith
add basic RENAME TABLE support for Embedded InnoDB. Also add a basic test, and copy over the rename.test test and run it against embedded innodb.
1373
  err= ib_cursor_update_row(cursor, read_tuple, update_tuple);
1374
1375
1376
  ib_tuple_delete(update_tuple);
1377
  ib_tuple_delete(read_tuple);
1378
  ib_tuple_delete(search_tuple);
1379
1380
  err= ib_cursor_close(cursor);
1381
1382
rollback:
1383
  return err;
1384
}
1385
1283.30.12 by Stewart Smith
fix rename table for new prototype as well as that table names are read from the proto instead of from getTableNames, which means on rename we must read the table proto, modify ita nd then store it again.
1386
int EmbeddedInnoDBEngine::doRenameTable(drizzled::Session &session,
1627.2.6 by Monty Taylor
Merged in constification of TableIdentifier from Brian.
1387
                                        const drizzled::TableIdentifier &from,
1388
                                        const drizzled::TableIdentifier &to)
1283.28.2 by Stewart Smith
add basic RENAME TABLE support for Embedded InnoDB. Also add a basic test, and copy over the rename.test test and run it against embedded innodb.
1389
{
1390
  ib_trx_t innodb_schema_transaction;
1391
  ib_err_t err;
1283.30.12 by Stewart Smith
fix rename table for new prototype as well as that table names are read from the proto instead of from getTableNames, which means on rename we must read the table proto, modify ita nd then store it again.
1392
  string from_innodb_table_name;
1393
  string to_innodb_table_name;
1394
1598.4.1 by Stewart Smith
support temporary tables in embedded_innodb - this means we can also run the alter_table test.
1395
  if (to.getType() == message::Table::TEMPORARY
1396
      && from.getType() == message::Table::TEMPORARY)
1397
  {
1398
    session.renameTableMessage(from, to);
1399
    return 0;
1400
  }
1401
1283.30.12 by Stewart Smith
fix rename table for new prototype as well as that table names are read from the proto instead of from getTableNames, which means on rename we must read the table proto, modify ita nd then store it again.
1402
  TableIdentifier_to_innodb_name(from, &from_innodb_table_name);
1403
  TableIdentifier_to_innodb_name(to, &to_innodb_table_name);
1283.28.2 by Stewart Smith
add basic RENAME TABLE support for Embedded InnoDB. Also add a basic test, and copy over the rename.test test and run it against embedded innodb.
1404
1405
  innodb_schema_transaction= ib_trx_begin(IB_TRX_REPEATABLE_READ);
1406
  err= ib_schema_lock_exclusive(innodb_schema_transaction);
1407
  if (err != DB_SUCCESS)
1408
  {
1283.30.12 by Stewart Smith
fix rename table for new prototype as well as that table names are read from the proto instead of from getTableNames, which means on rename we must read the table proto, modify ita nd then store it again.
1409
    push_warning_printf(&session, DRIZZLE_ERROR::WARN_LEVEL_ERROR,
1283.28.2 by Stewart Smith
add basic RENAME TABLE support for Embedded InnoDB. Also add a basic test, and copy over the rename.test test and run it against embedded innodb.
1410
                        ER_CANT_DELETE_FILE,
1411
                        _("Cannot Lock Embedded InnoDB Data Dictionary. InnoDB Error %d (%s)\n"),
1412
                        err, ib_strerror(err));
1413
1414
    goto rollback;
1415
  }
1416
1417
  err= ib_table_rename(innodb_schema_transaction,
1283.30.12 by Stewart Smith
fix rename table for new prototype as well as that table names are read from the proto instead of from getTableNames, which means on rename we must read the table proto, modify ita nd then store it again.
1418
                       from_innodb_table_name.c_str(),
1419
                       to_innodb_table_name.c_str());
1283.28.2 by Stewart Smith
add basic RENAME TABLE support for Embedded InnoDB. Also add a basic test, and copy over the rename.test test and run it against embedded innodb.
1420
  if (err != DB_SUCCESS)
1421
    goto rollback;
1422
1283.30.12 by Stewart Smith
fix rename table for new prototype as well as that table names are read from the proto instead of from getTableNames, which means on rename we must read the table proto, modify ita nd then store it again.
1423
  err= rename_table_message(innodb_schema_transaction, from, to);
1424
1283.28.2 by Stewart Smith
add basic RENAME TABLE support for Embedded InnoDB. Also add a basic test, and copy over the rename.test test and run it against embedded innodb.
1425
  if (err != DB_SUCCESS)
1426
    goto rollback;
1427
1428
  err= ib_trx_commit(innodb_schema_transaction);
1429
  if (err != DB_SUCCESS)
1430
    goto rollback;
1431
1432
  return 0;
1433
rollback:
1434
  ib_err_t rollback_err= ib_schema_unlock(innodb_schema_transaction);
1435
  assert(rollback_err == DB_SUCCESS);
1436
  rollback_err= ib_trx_rollback(innodb_schema_transaction);
1437
  assert(rollback_err == DB_SUCCESS);
1283.63.8 by Stewart Smith
use proper error code conversion routine for embedded_innodb rename table
1438
  return ib_err_t_to_drizzle_error(err);
1283.28.2 by Stewart Smith
add basic RENAME TABLE support for Embedded InnoDB. Also add a basic test, and copy over the rename.test test and run it against embedded innodb.
1439
}
1440
1283.16.32 by Stewart Smith
implement both doGetTableNames and doGetTableIdentifiers through a common function
1441
void EmbeddedInnoDBEngine::getTableNamesInSchemaFromInnoDB(
1642 by Brian Aker
This adds const to SchemaIdentifier.
1442
                                 const drizzled::SchemaIdentifier &schema,
1283.16.32 by Stewart Smith
implement both doGetTableNames and doGetTableIdentifiers through a common function
1443
                                 drizzled::plugin::TableNameList *set_of_names,
1444
                                 drizzled::TableIdentifiers *identifiers)
1283.3.24 by Stewart Smith
add SHOW TABLES support to embedded innodb engine
1445
{
1446
  ib_trx_t   transaction;
1447
  ib_crsr_t  cursor;
1685.2.12 by Brian Aker
This fixes the lower casing of names from Schema even when we should not.
1448
  /* 
1449
    Why not use getPath()?
1450
  */
1451
  string search_string(schema.getSchemaName());
1452
1453
  boost::algorithm::to_lower(search_string);
1283.3.24 by Stewart Smith
add SHOW TABLES support to embedded innodb engine
1454
1455
  search_string.append("/");
1456
1457
  transaction = ib_trx_begin(IB_TRX_REPEATABLE_READ);
1283.16.18 by Stewart Smith
check error codse in doGetTableNames for embedded innodb
1458
  ib_err_t innodb_err= ib_schema_lock_exclusive(transaction);
1459
  assert(innodb_err == DB_SUCCESS); /* FIXME: doGetTableNames needs to be able to return error */
1460
1461
1462
  innodb_err= ib_cursor_open_table("SYS_TABLES", transaction, &cursor);
1463
  assert(innodb_err == DB_SUCCESS); /* FIXME */
1464
1283.3.24 by Stewart Smith
add SHOW TABLES support to embedded innodb engine
1465
  ib_tpl_t read_tuple;
1283.16.19 by Stewart Smith
use search tuple in doGetTableNames to scan SYS_TABLES using an index read instead of full table scan.
1466
  ib_tpl_t search_tuple;
1283.3.24 by Stewart Smith
add SHOW TABLES support to embedded innodb engine
1467
1468
  read_tuple= ib_clust_read_tuple_create(cursor);
1283.16.19 by Stewart Smith
use search tuple in doGetTableNames to scan SYS_TABLES using an index read instead of full table scan.
1469
  search_tuple= ib_clust_search_tuple_create(cursor);
1470
1471
  innodb_err= ib_col_set_value(search_tuple, 0, search_string.c_str(),
1472
                               search_string.length());
1473
  assert (innodb_err == DB_SUCCESS); // FIXME
1474
1475
  int res;
1476
  innodb_err = ib_cursor_moveto(cursor, search_tuple, IB_CUR_GE, &res);
1477
  // fixme: check error above
1283.3.24 by Stewart Smith
add SHOW TABLES support to embedded innodb engine
1478
1283.16.18 by Stewart Smith
check error codse in doGetTableNames for embedded innodb
1479
  while (innodb_err == DB_SUCCESS)
1283.3.24 by Stewart Smith
add SHOW TABLES support to embedded innodb engine
1480
  {
1283.16.18 by Stewart Smith
check error codse in doGetTableNames for embedded innodb
1481
    innodb_err= ib_cursor_read_row(cursor, read_tuple);
1283.3.24 by Stewart Smith
add SHOW TABLES support to embedded innodb engine
1482
1483
    const char *table_name;
1484
    int table_name_len;
1485
    ib_col_meta_t column_metadata;
1486
1487
    table_name= (const char*)ib_col_get_value(read_tuple, 0);
1488
    table_name_len=  ib_col_get_meta(read_tuple, 0, &column_metadata);
1489
1490
    if (search_string.compare(0, search_string.length(),
1491
                              table_name, search_string.length()) == 0)
1492
    {
1493
      const char *just_table_name= strchr(table_name, '/');
1494
      assert(just_table_name);
1495
      just_table_name++; /* skip over '/' */
1283.16.32 by Stewart Smith
implement both doGetTableNames and doGetTableIdentifiers through a common function
1496
      if (set_of_names)
1497
        set_of_names->insert(just_table_name);
1498
      if (identifiers)
1685.2.12 by Brian Aker
This fixes the lower casing of names from Schema even when we should not.
1499
        identifiers->push_back(TableIdentifier(schema.getSchemaName(), just_table_name));
1283.3.24 by Stewart Smith
add SHOW TABLES support to embedded innodb engine
1500
    }
1501
1502
1283.16.18 by Stewart Smith
check error codse in doGetTableNames for embedded innodb
1503
    innodb_err= ib_cursor_next(cursor);
1283.3.24 by Stewart Smith
add SHOW TABLES support to embedded innodb engine
1504
    read_tuple= ib_tuple_clear(read_tuple);
1505
  }
1506
1507
  ib_tuple_delete(read_tuple);
1283.16.19 by Stewart Smith
use search tuple in doGetTableNames to scan SYS_TABLES using an index read instead of full table scan.
1508
  ib_tuple_delete(search_tuple);
1283.3.24 by Stewart Smith
add SHOW TABLES support to embedded innodb engine
1509
1283.16.18 by Stewart Smith
check error codse in doGetTableNames for embedded innodb
1510
  innodb_err= ib_cursor_close(cursor);
1511
  assert(innodb_err == DB_SUCCESS); // FIXME
1283.3.24 by Stewart Smith
add SHOW TABLES support to embedded innodb engine
1512
1283.16.18 by Stewart Smith
check error codse in doGetTableNames for embedded innodb
1513
  innodb_err= ib_trx_commit(transaction);
1514
  assert(innodb_err == DB_SUCCESS); // FIXME
1283.3.24 by Stewart Smith
add SHOW TABLES support to embedded innodb engine
1515
}
1516
1283.16.32 by Stewart Smith
implement both doGetTableNames and doGetTableIdentifiers through a common function
1517
void EmbeddedInnoDBEngine::doGetTableNames(drizzled::CachedDirectory &,
1642 by Brian Aker
This adds const to SchemaIdentifier.
1518
                                           const drizzled::SchemaIdentifier &schema,
1283.16.32 by Stewart Smith
implement both doGetTableNames and doGetTableIdentifiers through a common function
1519
                                           drizzled::plugin::TableNameList &set_of_names)
1520
{
1521
  getTableNamesInSchemaFromInnoDB(schema, &set_of_names, NULL);
1522
}
1523
1524
void EmbeddedInnoDBEngine::doGetTableIdentifiers(drizzled::CachedDirectory &,
1642 by Brian Aker
This adds const to SchemaIdentifier.
1525
                                                 const drizzled::SchemaIdentifier &schema,
1283.16.32 by Stewart Smith
implement both doGetTableNames and doGetTableIdentifiers through a common function
1526
                                                 drizzled::TableIdentifiers &identifiers)
1527
{
1528
  getTableNamesInSchemaFromInnoDB(schema, NULL, &identifiers);
1529
}
1530
1283.17.11 by Stewart Smith
change data_dictionary.innodb_table_proto to data_dictionary.innodb_table_definition
1531
static int read_table_message_from_innodb(const char* table_name, drizzled::message::Table *table_message)
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
1532
{
1533
  ib_trx_t transaction;
1534
  ib_tpl_t search_tuple;
1535
  ib_tpl_t read_tuple;
1536
  ib_crsr_t cursor;
1283.17.11 by Stewart Smith
change data_dictionary.innodb_table_proto to data_dictionary.innodb_table_definition
1537
  const char *message;
1538
  ib_ulint_t message_len;
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
1539
  ib_col_meta_t col_meta;
1540
  int res;
1541
  ib_err_t err;
1283.19.28 by Stewart Smith
fixup error checking
1542
  ib_err_t rollback_err;
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
1543
1544
  transaction= ib_trx_begin(IB_TRX_REPEATABLE_READ);
1283.19.28 by Stewart Smith
fixup error checking
1545
  err= ib_schema_lock_exclusive(transaction);
1546
  if (err != DB_SUCCESS)
1547
  {
1548
    rollback_err= ib_trx_rollback(transaction);
1549
    assert(rollback_err == DB_SUCCESS);
1550
    return err;
1551
  }
1552
1553
  err= ib_cursor_open_table(INNODB_TABLE_DEFINITIONS_TABLE, transaction, &cursor);
1554
  if (err != DB_SUCCESS)
1555
  {
1556
    rollback_err= ib_trx_rollback(transaction);
1557
    assert(rollback_err == DB_SUCCESS);
1558
    return err;
1559
  }
1560
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
1561
  search_tuple= ib_clust_search_tuple_create(cursor);
1283.17.5 by Stewart Smith
generate a basic table proto for data_dictionary/innodb_table_proto system table.
1562
  read_tuple= ib_clust_read_tuple_create(cursor);
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
1563
1283.19.28 by Stewart Smith
fixup error checking
1564
  err= ib_col_set_value(search_tuple, 0, table_name, strlen(table_name));
1565
  if (err != DB_SUCCESS)
1566
    goto rollback;
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
1567
1568
//  ib_cursor_set_match_mode(cursor, IB_EXACT_MATCH);
1569
1570
  err= ib_cursor_moveto(cursor, search_tuple, IB_CUR_GE, &res);
1571
  if (err == DB_RECORD_NOT_FOUND || res != 0)
1572
    goto rollback;
1573
1574
  err= ib_cursor_read_row(cursor, read_tuple);
1575
  if (err == DB_RECORD_NOT_FOUND || res != 0)
1576
    goto rollback;
1577
1283.17.11 by Stewart Smith
change data_dictionary.innodb_table_proto to data_dictionary.innodb_table_definition
1578
  message= (const char*)ib_col_get_value(read_tuple, 1);
1579
  message_len= ib_col_get_meta(read_tuple, 1, &col_meta);
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
1580
1283.17.11 by Stewart Smith
change data_dictionary.innodb_table_proto to data_dictionary.innodb_table_definition
1581
  if (table_message->ParseFromArray(message, message_len) == false)
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
1582
    goto rollback;
1583
1584
  ib_tuple_delete(search_tuple);
1585
  ib_tuple_delete(read_tuple);
1283.19.28 by Stewart Smith
fixup error checking
1586
  err= ib_cursor_close(cursor);
1587
  if (err != DB_SUCCESS)
1588
    goto rollback_close_err;
1589
  err= ib_trx_commit(transaction);
1590
  if (err != DB_SUCCESS)
1591
    goto rollback_close_err;
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
1592
1593
  return 0;
1594
1595
rollback:
1283.17.5 by Stewart Smith
generate a basic table proto for data_dictionary/innodb_table_proto system table.
1596
  ib_tuple_delete(search_tuple);
1597
  ib_tuple_delete(read_tuple);
1283.19.28 by Stewart Smith
fixup error checking
1598
  rollback_err= ib_cursor_close(cursor);
1599
  assert(rollback_err == DB_SUCCESS);
1600
rollback_close_err:
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
1601
  ib_schema_unlock(transaction);
1283.19.28 by Stewart Smith
fixup error checking
1602
  rollback_err= ib_trx_rollback(transaction);
1603
  assert(rollback_err == DB_SUCCESS);
1283.17.5 by Stewart Smith
generate a basic table proto for data_dictionary/innodb_table_proto system table.
1604
1283.17.12 by Stewart Smith
use define to set the name of the innodb_table_definitions table instead of repeating it 5 times through the code
1605
  if (strcmp(table_name, INNODB_TABLE_DEFINITIONS_TABLE) == 0)
1283.17.5 by Stewart Smith
generate a basic table proto for data_dictionary/innodb_table_proto system table.
1606
  {
1475.2.9 by Stewart Smith
fix many compile failures that people introduced in embedded_innodb because it's not built by default.. i.e. plugin=disabled is EPIC FAIL
1607
    message::Engine *engine= table_message->mutable_engine();
1283.17.5 by Stewart Smith
generate a basic table proto for data_dictionary/innodb_table_proto system table.
1608
    engine->set_name("InnoDB");
1283.17.29 by Stewart Smith
store (bogus) values for creation_timestamp and update_timestamp in the table proto for data_dictionary.innodb_table_definitions
1609
    table_message->set_name("innodb_table_definitions");
1283.17.31 by Stewart Smith
fix up store/read table message for TableIdentifier
1610
    table_message->set_schema("data_dictionary");
1283.17.5 by Stewart Smith
generate a basic table proto for data_dictionary/innodb_table_proto system table.
1611
    table_message->set_type(message::Table::STANDARD);
1283.17.29 by Stewart Smith
store (bogus) values for creation_timestamp and update_timestamp in the table proto for data_dictionary.innodb_table_definitions
1612
    table_message->set_creation_timestamp(0);
1613
    table_message->set_update_timestamp(0);
1283.17.5 by Stewart Smith
generate a basic table proto for data_dictionary/innodb_table_proto system table.
1614
1283.17.26 by Stewart Smith
fix up table message table proto for collation to always be binary.
1615
    message::Table::TableOptions *options= table_message->mutable_options();
1616
    options->set_collation_id(my_charset_bin.number);
1617
    options->set_collation(my_charset_bin.name);
1618
1283.17.5 by Stewart Smith
generate a basic table proto for data_dictionary/innodb_table_proto system table.
1619
    message::Table::Field *field= table_message->add_field();
1620
    field->set_name("table_name");
1621
    field->set_type(message::Table::Field::VARCHAR);
1622
    message::Table::Field::StringFieldOptions *stropt= field->mutable_string_options();
1623
    stropt->set_length(IB_MAX_TABLE_NAME_LEN);
1283.19.2 by Stewart Smith
read the count of the number of tables in the data_dictionary/innodb_table_proto table. Currently don't report the existence of an index on the table as we don't have index scan yet
1624
    stropt->set_collation_id(my_charset_bin.number);
1283.17.26 by Stewart Smith
fix up table message table proto for collation to always be binary.
1625
    stropt->set_collation(my_charset_bin.name);
1283.17.5 by Stewart Smith
generate a basic table proto for data_dictionary/innodb_table_proto system table.
1626
1627
    field= table_message->add_field();
1283.17.11 by Stewart Smith
change data_dictionary.innodb_table_proto to data_dictionary.innodb_table_definition
1628
    field->set_name("message");
1283.17.5 by Stewart Smith
generate a basic table proto for data_dictionary/innodb_table_proto system table.
1629
    field->set_type(message::Table::Field::BLOB);
1283.17.26 by Stewart Smith
fix up table message table proto for collation to always be binary.
1630
    stropt= field->mutable_string_options();
1631
    stropt->set_collation_id(my_charset_bin.number);
1632
    stropt->set_collation(my_charset_bin.name);
1283.17.5 by Stewart Smith
generate a basic table proto for data_dictionary/innodb_table_proto system table.
1633
1634
    message::Table::Index *index= table_message->add_indexes();
1635
    index->set_name("PRIMARY");
1636
    index->set_is_primary(true);
1637
    index->set_is_unique(true);
1638
    index->set_type(message::Table::Index::BTREE);
1639
    index->set_key_length(IB_MAX_TABLE_NAME_LEN);
1640
    message::Table::Index::IndexPart *part= index->add_index_part();
1641
    part->set_fieldnr(0);
1642
    part->set_compare_length(IB_MAX_TABLE_NAME_LEN);
1283.3.48 by Stewart Smith
since index reads work, we can expose the primary key of data_dictionary.innodb_table_proto to the sql server.
1643
1283.17.5 by Stewart Smith
generate a basic table proto for data_dictionary/innodb_table_proto system table.
1644
    return 0;
1645
  }
1283.3.26 by Stewart Smith
basic store/read/delete table proto from embedded innodb table. This makes CREATE TABLE 100% crash safe. This also makes SHOW CREATE TABLE work for embedded innodb tables.
1646
1647
  return -1;
1648
}
1649
1598.5.4 by Stewart Smith
merge trunk
1650
int EmbeddedInnoDBEngine::doGetTableDefinition(Session &session,
1627.2.6 by Monty Taylor
Merged in constification of TableIdentifier from Brian.
1651
                                               const TableIdentifier &identifier,
1283.14.19 by Stewart Smith
fix up table exists for new bits of storage engine API r.e. TableIdentifier
1652
                                               drizzled::message::Table &table)
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
1653
{
1283.3.22 by Stewart Smith
to really work with drop table, doGetTableDefinition must fill out the Engine part of the protobuf.
1654
  ib_crsr_t innodb_cursor= NULL;
1283.14.19 by Stewart Smith
fix up table exists for new bits of storage engine API r.e. TableIdentifier
1655
  string innodb_table_name;
1656
1598.4.1 by Stewart Smith
support temporary tables in embedded_innodb - this means we can also run the alter_table test.
1657
  /* Check temporary tables!? */
1658
  if (session.getTableMessage(identifier, table))
1659
    return EEXIST;
1660
1283.14.19 by Stewart Smith
fix up table exists for new bits of storage engine API r.e. TableIdentifier
1661
  TableIdentifier_to_innodb_name(identifier, &innodb_table_name);
1662
1663
  if (ib_cursor_open_table(innodb_table_name.c_str(), NULL, &innodb_cursor) != DB_SUCCESS)
1283.3.20 by Stewart Smith
*really* simple embeddded_innodb check if a table exists in doGetTableDefinition.
1664
    return ENOENT;
1665
1283.17.21 by Stewart Smith
fix up ib_cursor_close() error checking in doGetTableDefinition
1666
  ib_err_t err= ib_cursor_close(innodb_cursor);
1667
1668
  assert (err == DB_SUCCESS);
1283.3.20 by Stewart Smith
*really* simple embeddded_innodb check if a table exists in doGetTableDefinition.
1669
1283.17.31 by Stewart Smith
fix up store/read table message for TableIdentifier
1670
  read_table_message_from_innodb(innodb_table_name.c_str(), &table);
1283.3.22 by Stewart Smith
to really work with drop table, doGetTableDefinition must fill out the Engine part of the protobuf.
1671
1283.3.20 by Stewart Smith
*really* simple embeddded_innodb check if a table exists in doGetTableDefinition.
1672
  return EEXIST;
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
1673
}
1674
1283.14.19 by Stewart Smith
fix up table exists for new bits of storage engine API r.e. TableIdentifier
1675
bool EmbeddedInnoDBEngine::doDoesTableExist(Session &,
1627.2.6 by Monty Taylor
Merged in constification of TableIdentifier from Brian.
1676
                                            const TableIdentifier& identifier)
1283.11.19 by Stewart Smith
fix up create table for new bits of storage engine API r.e. TableIdentifier
1677
{
1283.14.19 by Stewart Smith
fix up table exists for new bits of storage engine API r.e. TableIdentifier
1678
  ib_crsr_t innodb_cursor;
1679
  string innodb_table_name;
1680
1681
  TableIdentifier_to_innodb_name(identifier, &innodb_table_name);
1682
1683
  if (ib_cursor_open_table(innodb_table_name.c_str(), NULL, &innodb_cursor) != DB_SUCCESS)
1684
    return false;
1685
1686
  ib_err_t err= ib_cursor_close(innodb_cursor);
1687
  assert(err == DB_SUCCESS);
1688
1689
  return true;
1283.11.19 by Stewart Smith
fix up create table for new bits of storage engine API r.e. TableIdentifier
1690
}
1691
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
1692
const char *EmbeddedInnoDBCursor::index_type(uint32_t)
1693
{
1694
  return("BTREE");
1695
}
1696
1283.28.1 by Stewart Smith
basic UPDATE row for Embedded InnoDB Engine.
1697
static ib_err_t write_row_to_innodb_tuple(Field **fields, ib_tpl_t tuple)
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
1698
{
1283.28.1 by Stewart Smith
basic UPDATE row for Embedded InnoDB Engine.
1699
  int colnr= 0;
1539.1.2 by Brian Aker
Fix Hades build error.
1700
  ib_err_t err= DB_ERROR;
1283.28.1 by Stewart Smith
basic UPDATE row for Embedded InnoDB Engine.
1701
1702
  for (Field **field= fields; *field; field++, colnr++)
1283.3.27 by Stewart Smith
basic code to insert a integer
1703
  {
1283.39.11 by Stewart Smith
fix write_row_to_innodb_tuple for proper WriteSet behaviour. oh my the API is bonghits.
1704
    if (! (**field).isWriteSet() && (**field).is_null())
1705
      continue;
1706
1283.12.31 by Stewart Smith
fix storing of NULL in embedded innodb. Need to explicitly set column value to IB_SQL_NULL
1707
    if ((**field).is_null())
1708
    {
1709
      err= ib_col_set_value(tuple, colnr, NULL, IB_SQL_NULL);
1710
      assert(err == DB_SUCCESS);
1711
      continue;
1712
    }
1713
1283.12.7 by Stewart Smith
store VARCHAR columns correctly. Don't store the length bytes. instead use and abuse Field_varstring::val_str() to get the length and pointer to data to tell innodb.
1714
    if ((**field).type() == DRIZZLE_TYPE_VARCHAR)
1715
    {
1716
      /* To get around the length bytes (1 or 2) at (**field).ptr
1717
         we can use Field_varstring::val_str to a String
1718
         to get a pointer to the real string without copying it.
1719
      */
1720
      String str;
1721
      (**field).setReadSet();
1722
      (**field).val_str(&str);
1723
      err= ib_col_set_value(tuple, colnr, str.ptr(), str.length());
1724
    }
1283.35.27 by Stewart Smith
add ENUM SQL type support to Embedded InnoDB
1725
    else if ((**field).type() == DRIZZLE_TYPE_ENUM)
1726
    {
1727
      if ((*field)->data_length() == 1)
1728
        err= ib_tuple_write_u8(tuple, colnr, *((ib_u8_t*)(*field)->ptr));
1729
      else if ((*field)->data_length() == 2)
1730
        err= ib_tuple_write_u16(tuple, colnr, *((ib_u16_t*)(*field)->ptr));
1731
      else
1732
      {
1733
        assert((*field)->data_length() <= 2);
1734
      }
1735
    }
1283.35.45 by Stewart Smith
enable DATE type for embedded_innodb.
1736
    else if ((**field).type() == DRIZZLE_TYPE_DATE)
1737
    {
1738
      (**field).setReadSet();
1739
      err= ib_tuple_write_u32(tuple, colnr, (*field)->val_int());
1740
    }
1283.60.5 by Stewart Smith
add BLOB support to embedded_innodb along with a simple test.
1741
    else if ((**field).type() == DRIZZLE_TYPE_BLOB)
1742
    {
1743
      Field_blob *blob= reinterpret_cast<Field_blob*>(*field);
1744
      unsigned char* blob_ptr;
1745
      uint32_t blob_length= blob->get_length();
1746
      blob->get_ptr(&blob_ptr);
1747
      err= ib_col_set_value(tuple, colnr, blob_ptr, blob_length);
1748
    }
1283.12.7 by Stewart Smith
store VARCHAR columns correctly. Don't store the length bytes. instead use and abuse Field_varstring::val_str() to get the length and pointer to data to tell innodb.
1749
    else
1750
    {
1751
      err= ib_col_set_value(tuple, colnr, (*field)->ptr, (*field)->data_length());
1752
    }
1753
1283.12.15 by Stewart Smith
style fixups: == and spaces
1754
    assert (err == DB_SUCCESS);
1283.3.27 by Stewart Smith
basic code to insert a integer
1755
  }
1756
1283.28.1 by Stewart Smith
basic UPDATE row for Embedded InnoDB Engine.
1757
  return err;
1758
}
1759
1283.37.4 by Stewart Smith
fix embedded_innodb auto_increment for negative values (just strange really).
1760
static uint64_t innobase_get_int_col_max_value(const Field* field)
1761
{
1762
  uint64_t	max_value = 0;
1763
1764
  switch(field->key_type()) {
1765
    /* TINY */
1766
  case HA_KEYTYPE_BINARY:
1767
    max_value = 0xFFULL;
1768
    break;
1769
    /* MEDIUM */
1770
  case HA_KEYTYPE_UINT24:
1771
    max_value = 0xFFFFFFULL;
1772
    break;
1773
    /* LONG */
1774
  case HA_KEYTYPE_ULONG_INT:
1775
    max_value = 0xFFFFFFFFULL;
1776
    break;
1777
  case HA_KEYTYPE_LONG_INT:
1778
    max_value = 0x7FFFFFFFULL;
1779
    break;
1780
    /* BIG */
1781
  case HA_KEYTYPE_ULONGLONG:
1782
    max_value = 0xFFFFFFFFFFFFFFFFULL;
1783
    break;
1784
  case HA_KEYTYPE_LONGLONG:
1785
    max_value = 0x7FFFFFFFFFFFFFFFULL;
1786
    break;
1787
  case HA_KEYTYPE_DOUBLE:
1788
    /* We use the maximum as per IEEE754-2008 standard, 2^53 */
1789
    max_value = 0x20000000000000ULL;
1790
    break;
1791
  default:
1792
    assert(false);
1793
  }
1794
1795
  return(max_value);
1796
}
1797
1283.39.8 by Stewart Smith
add support for REPLACE to embedded_innodb. On duplicate key on insert if we have HA_EXTRA_WRITE_CAN_REPLACE set, then we delete the row and insert.
1798
int EmbeddedInnoDBCursor::doInsertRecord(unsigned char *record)
1283.28.1 by Stewart Smith
basic UPDATE row for Embedded InnoDB Engine.
1799
{
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
1800
  ib_err_t err;
1801
  int ret= 0;
1802
1578.6.2 by Brian Aker
Remove ha_session.
1803
  ib_trx_t transaction= *get_trx(table->in_use);
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
1804
1805
  tuple= ib_clust_read_tuple_create(cursor);
1806
1807
  ib_cursor_attach_trx(cursor, transaction);
1808
1809
  err= ib_cursor_first(cursor);
1283.36.24 by Stewart Smith
fix CREATE SELECT for Embedded Innodb. Special case of DB_MISSING_HISTORY due to transaction started before destination table exists.
1810
  if (current_session->lex->sql_command == SQLCOM_CREATE_TABLE
1811
      && err == DB_MISSING_HISTORY)
1812
  {
1813
    /* See https://bugs.launchpad.net/drizzle/+bug/556978
1814
     *
1815
     * In CREATE SELECT, transaction is started in ::store_lock
1816
     * at the start of the statement, before the table is created.
1817
     * This means the table doesn't exist in our snapshot,
1818
     * and we get a DB_MISSING_HISTORY error on ib_cursor_first().
1819
     * The way to get around this is to here, restart the transaction
1820
     * and continue.
1821
     *
1822
     * yuck.
1823
     */
1824
1825
    EmbeddedInnoDBEngine *innodb_engine= static_cast<EmbeddedInnoDBEngine*>(engine);
1826
    err= ib_cursor_reset(cursor);
1827
    innodb_engine->doCommit(current_session, true);
1828
    innodb_engine->doStartTransaction(current_session, START_TRANS_NO_OPTIONS);
1578.6.2 by Brian Aker
Remove ha_session.
1829
    transaction= *get_trx(table->in_use);
1283.36.24 by Stewart Smith
fix CREATE SELECT for Embedded Innodb. Special case of DB_MISSING_HISTORY due to transaction started before destination table exists.
1830
    assert(err == DB_SUCCESS);
1831
    ib_cursor_attach_trx(cursor, transaction);
1832
    err= ib_cursor_first(cursor);
1833
  }
1834
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
1835
  assert(err == DB_SUCCESS || err == DB_END_OF_INDEX);
1836
1837
1283.28.1 by Stewart Smith
basic UPDATE row for Embedded InnoDB Engine.
1838
  if (table->next_number_field)
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
1839
  {
1283.28.1 by Stewart Smith
basic UPDATE row for Embedded InnoDB Engine.
1840
    update_auto_increment();
1841
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
1842
    uint64_t temp_auto= table->next_number_field->val_int();
1843
1283.37.4 by Stewart Smith
fix embedded_innodb auto_increment for negative values (just strange really).
1844
    if (temp_auto <= innobase_get_int_col_max_value(table->next_number_field))
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
1845
    {
1283.37.4 by Stewart Smith
fix embedded_innodb auto_increment for negative values (just strange really).
1846
      while (true)
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
1847
      {
1283.37.4 by Stewart Smith
fix embedded_innodb auto_increment for negative values (just strange really).
1848
        uint64_t fetched_auto= share->auto_increment_value;
1849
1850
        if (temp_auto >= fetched_auto)
1851
        {
1852
          uint64_t store_value= temp_auto+1;
1853
          if (store_value == 0)
1854
            store_value++;
1855
1856
          if (share->auto_increment_value.compare_and_swap(store_value, fetched_auto) == fetched_auto)
1857
            break;
1858
        }
1859
        else
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
1860
          break;
1861
      }
1862
    }
1863
1864
  }
1283.28.1 by Stewart Smith
basic UPDATE row for Embedded InnoDB Engine.
1865
1593 by Brian Aker
Merge in Barry.
1866
  write_row_to_innodb_tuple(table->getFields(), tuple);
1283.28.1 by Stewart Smith
basic UPDATE row for Embedded InnoDB Engine.
1867
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
1868
  if (share->has_hidden_primary_key)
1869
  {
1532.1.15 by Brian Aker
Partial encapsulation of TableShare from Table.
1870
    err= ib_tuple_write_u64(tuple, table->getShare()->fields, share->hidden_pkey_auto_increment_value.fetch_and_increment());
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
1871
  }
1872
1283.3.27 by Stewart Smith
basic code to insert a integer
1873
  err= ib_cursor_insert_row(cursor, tuple);
1283.3.39 by Stewart Smith
return HA_ERR_FOUND_DUPP_KEY on duplicate key error from embedded innodb.
1874
1875
  if (err == DB_DUPLICATE_KEY)
1283.39.8 by Stewart Smith
add support for REPLACE to embedded_innodb. On duplicate key on insert if we have HA_EXTRA_WRITE_CAN_REPLACE set, then we delete the row and insert.
1876
  {
1877
    if (write_can_replace)
1878
    {
1618 by Brian Aker
This is a rollup set of patches for modifications to TableIdentifier to have
1879
      store_key_value_from_innodb(table->key_info + table->getShare()->getPrimaryKey(),
1283.39.8 by Stewart Smith
add support for REPLACE to embedded_innodb. On duplicate key on insert if we have HA_EXTRA_WRITE_CAN_REPLACE set, then we delete the row and insert.
1880
                                  ref, ref_length, record);
1881
1882
      ib_tpl_t search_tuple= ib_clust_search_tuple_create(cursor);
1883
1884
      fill_ib_search_tpl_from_drizzle_key(search_tuple,
1885
                                          table->key_info + 0,
1886
                                          ref, ref_length);
1887
1888
      int res;
1889
      err= ib_cursor_moveto(cursor, search_tuple, IB_CUR_GE, &res);
1890
      assert(err == DB_SUCCESS);
1891
      ib_tuple_delete(search_tuple);
1892
1893
      tuple= ib_tuple_clear(tuple);
1894
      err= ib_cursor_delete_row(cursor);
1895
1896
      err= ib_cursor_first(cursor);
1897
      assert(err == DB_SUCCESS || err == DB_END_OF_INDEX);
1898
1593 by Brian Aker
Merge in Barry.
1899
      write_row_to_innodb_tuple(table->getFields(), tuple);
1283.39.8 by Stewart Smith
add support for REPLACE to embedded_innodb. On duplicate key on insert if we have HA_EXTRA_WRITE_CAN_REPLACE set, then we delete the row and insert.
1900
1901
      err= ib_cursor_insert_row(cursor, tuple);
1902
      assert(err==DB_SUCCESS); // probably be nice and process errors
1903
    }
1904
    else
1905
      ret= HA_ERR_FOUND_DUPP_KEY;
1906
  }
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
1907
  else if (err != DB_SUCCESS)
1283.63.9 by Stewart Smith
use proper error code conversion routine for embedded_innodb insert record
1908
    ret= ib_err_t_to_drizzle_error(err);
1283.3.27 by Stewart Smith
basic code to insert a integer
1909
1283.19.28 by Stewart Smith
fixup error checking
1910
  tuple= ib_tuple_clear(tuple);
1283.3.36 by Stewart Smith
'correctly' deal with transaction in an autocommit type way. this means queries like 'insert select' work as we're always in the correct transactional context.
1911
  ib_tuple_delete(tuple);
1283.19.28 by Stewart Smith
fixup error checking
1912
  err= ib_cursor_reset(cursor);
1283.3.27 by Stewart Smith
basic code to insert a integer
1913
1283.3.39 by Stewart Smith
return HA_ERR_FOUND_DUPP_KEY on duplicate key error from embedded innodb.
1914
  return ret;
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
1915
}
1916
1283.39.11 by Stewart Smith
fix write_row_to_innodb_tuple for proper WriteSet behaviour. oh my the API is bonghits.
1917
int EmbeddedInnoDBCursor::doUpdateRecord(const unsigned char *,
1918
                                         unsigned char *)
1283.28.1 by Stewart Smith
basic UPDATE row for Embedded InnoDB Engine.
1919
{
1920
  ib_tpl_t update_tuple;
1921
  ib_err_t err;
1922
1923
  update_tuple= ib_clust_read_tuple_create(cursor);
1924
1925
  err= ib_tuple_copy(update_tuple, tuple);
1926
  assert(err == DB_SUCCESS);
1927
1593 by Brian Aker
Merge in Barry.
1928
  write_row_to_innodb_tuple(table->getFields(), update_tuple);
1283.28.1 by Stewart Smith
basic UPDATE row for Embedded InnoDB Engine.
1929
1930
  err= ib_cursor_update_row(cursor, tuple, update_tuple);
1931
1932
  ib_tuple_delete(update_tuple);
1283.60.4 by Stewart Smith
Change when we call ib_cursor_next/prev. Instead of calling it after reading
1933
1934
  advance_cursor= true;
1283.28.1 by Stewart Smith
basic UPDATE row for Embedded InnoDB Engine.
1935
1936
  if (err == DB_SUCCESS)
1937
    return 0;
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
1938
  else if (err == DB_DUPLICATE_KEY)
1939
    return HA_ERR_FOUND_DUPP_KEY;
1283.28.1 by Stewart Smith
basic UPDATE row for Embedded InnoDB Engine.
1940
  else
1941
    return -1;
1942
}
1943
1475.2.4 by Stewart Smith
fix update_record nad delete_record in embedded_innodb to be doUpdateRecord and doDeleteRecord
1944
int EmbeddedInnoDBCursor::doDeleteRecord(const unsigned char *)
1283.3.53 by Stewart Smith
support delete_row() in Embedded InnoDB. We move to the previous record in the cursor as after any of the read methods, the cursor always points to the *next* record to be read.
1945
{
1283.3.78 by Stewart Smith
fix up error code checking
1946
  ib_err_t err;
1947
1948
  err= ib_cursor_delete_row(cursor);
1949
  if (err != DB_SUCCESS)
1950
    return -1; // FIXME
1951
1283.60.4 by Stewart Smith
Change when we call ib_cursor_next/prev. Instead of calling it after reading
1952
  advance_cursor= true;
1283.3.53 by Stewart Smith
support delete_row() in Embedded InnoDB. We move to the previous record in the cursor as after any of the read methods, the cursor always points to the *next* record to be read.
1953
  return 0;
1954
}
1955
1283.3.79 by Stewart Smith
implement TRUNCATE TABLE for Embedded Innodb using the (fast) ib_cursor_truncate() call instead of deleting each row individually.
1956
int EmbeddedInnoDBCursor::delete_all_rows(void)
1957
{
1958
  /* I *think* ib_truncate is non-transactional....
1959
     so only support TRUNCATE and not DELETE FROM t;
1960
     (this is what ha_innodb does)
1961
  */
1578.6.2 by Brian Aker
Remove ha_session.
1962
  if (session_sql_command(table->in_use) != SQLCOM_TRUNCATE)
1283.3.79 by Stewart Smith
implement TRUNCATE TABLE for Embedded Innodb using the (fast) ib_cursor_truncate() call instead of deleting each row individually.
1963
    return HA_ERR_WRONG_COMMAND;
1964
1965
  ib_id_t id;
1966
  ib_err_t err;
1967
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
1968
  ib_trx_t transaction= ib_trx_begin(IB_TRX_REPEATABLE_READ);
1283.3.79 by Stewart Smith
implement TRUNCATE TABLE for Embedded Innodb using the (fast) ib_cursor_truncate() call instead of deleting each row individually.
1969
1970
  ib_cursor_attach_trx(cursor, transaction);
1971
1972
  err= ib_schema_lock_exclusive(transaction);
1973
  if (err != DB_SUCCESS)
1974
  {
1975
    ib_err_t rollback_err= ib_trx_rollback(transaction);
1976
1578.6.2 by Brian Aker
Remove ha_session.
1977
    push_warning_printf(table->in_use, DRIZZLE_ERROR::WARN_LEVEL_ERROR,
1283.3.79 by Stewart Smith
implement TRUNCATE TABLE for Embedded Innodb using the (fast) ib_cursor_truncate() call instead of deleting each row individually.
1978
                        ER_CANT_DELETE_FILE,
1979
                        _("Cannot Lock Embedded InnoDB Data Dictionary. InnoDB Error %d (%s)\n"),
1980
                        err, ib_strerror(err));
1981
1982
    assert (rollback_err == DB_SUCCESS);
1983
1984
    return HA_ERR_GENERIC;
1985
  }
1986
1283.39.9 by Stewart Smith
TRUNCATE TABLE should reset auto increment value
1987
  share->auto_increment_value.fetch_and_store(1);
1988
1283.3.79 by Stewart Smith
implement TRUNCATE TABLE for Embedded Innodb using the (fast) ib_cursor_truncate() call instead of deleting each row individually.
1989
  err= ib_cursor_truncate(&cursor, &id);
1990
  if (err != DB_SUCCESS)
1991
    goto err;
1992
1993
  ib_schema_unlock(transaction);
1994
  /* ib_cursor_truncate commits on success */
1995
1996
  err= ib_cursor_open_table_using_id(id, NULL, &cursor);
1997
  if (err != DB_SUCCESS)
1998
    goto err;
1999
2000
  return 0;
2001
2002
err:
2003
  ib_schema_unlock(transaction);
2004
  ib_err_t rollback_err= ib_trx_rollback(transaction);
2005
  assert(rollback_err == DB_SUCCESS);
2006
  return err;
2007
}
2008
1491.1.10 by Jay Pipes
ha_rnd_init -> startTableScan, rnd_init -> doStartTableScan, ha_rnd_end -> endTableScan, rnd_end -> doEndTableScan
2009
int EmbeddedInnoDBCursor::doStartTableScan(bool)
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2010
{
1283.63.1 by Stewart Smith
support SELECT ... FOR UPDATE locking for embedded_innodb. Do stupid shit because of the complete lack of error checking for startTableScan in parts of the upper layer.
2011
  ib_err_t err;
1283.36.13 by Stewart Smith
basic auto_increment implementation for embedded_innodb. On startup, fetch the maximum value for the auto_increment column (or what's in the table message as the auto_increment value). Use an atomic variable in the embedded-innodb table share to keep track of the auto_increment_value. We can then use atomic ops to get an autoinc value (or several) as well as update it in the event of inserting a larger number. Currently there's a bug (well, difference in behaviour) around inserting -1 into an auto-inc field where the table already has a value 'higher' than that and then asking for another auto-inc value. Check the auto_increment test case failure for it. This will be fixed in a later commit.
2012
  ib_trx_t transaction;
2013
1283.60.11 by Stewart Smith
doStartTableScan() can be called twice in a row without a doEndTableScan()
2014
  if (in_table_scan)
2015
    doEndTableScan();
2016
  in_table_scan= true;
2017
1578.6.2 by Brian Aker
Remove ha_session.
2018
  transaction= *get_trx(table->in_use);
1283.3.36 by Stewart Smith
'correctly' deal with transaction in an autocommit type way. this means queries like 'insert select' work as we're always in the correct transactional context.
2019
1510.4.2 by Jay Pipes
Fixes Bug #552420. Because the copied-to table in ALTER TABLE is temporary, mysql_lock_tables() is not called, and the automatic StorageEngine::startStatement() is also not called. So, we call it manually to ensure transactional engines have a notification of a new statement/transaction.
2020
  assert(transaction != NULL);
2021
1283.3.36 by Stewart Smith
'correctly' deal with transaction in an autocommit type way. this means queries like 'insert select' work as we're always in the correct transactional context.
2022
  ib_cursor_attach_trx(cursor, transaction);
2023
1283.63.1 by Stewart Smith
support SELECT ... FOR UPDATE locking for embedded_innodb. Do stupid shit because of the complete lack of error checking for startTableScan in parts of the upper layer.
2024
  err= ib_cursor_set_lock_mode(cursor, ib_lock_mode);
2025
  assert(err == DB_SUCCESS); // FIXME
2026
1283.3.36 by Stewart Smith
'correctly' deal with transaction in an autocommit type way. this means queries like 'insert select' work as we're always in the correct transactional context.
2027
  tuple= ib_clust_read_tuple_create(cursor);
2028
1283.63.1 by Stewart Smith
support SELECT ... FOR UPDATE locking for embedded_innodb. Do stupid shit because of the complete lack of error checking for startTableScan in parts of the upper layer.
2029
  err= ib_cursor_first(cursor);
1283.19.28 by Stewart Smith
fixup error checking
2030
  if (err != DB_SUCCESS && err != DB_END_OF_INDEX)
1283.63.1 by Stewart Smith
support SELECT ... FOR UPDATE locking for embedded_innodb. Do stupid shit because of the complete lack of error checking for startTableScan in parts of the upper layer.
2031
  {
2032
    previous_error= ib_err_t_to_drizzle_error(err);
1283.63.12 by Stewart Smith
on error in doStartTableScan, reset the ib_cursor. This manifested itself as a warning in basic_select_for_update test on lock wait timeout that there was still an open cursor in the transaction being rolled back (it turns out that Cursor isn't closed before rollback).
2033
    err= ib_cursor_reset(cursor);
1283.63.1 by Stewart Smith
support SELECT ... FOR UPDATE locking for embedded_innodb. Do stupid shit because of the complete lack of error checking for startTableScan in parts of the upper layer.
2034
    return previous_error;
2035
  }
1283.3.28 by Stewart Smith
simple rnd_init/rnd_next implementation for embedded innodb. It now works for inserting 1 row with an int column and selecting that row back (at least).
2036
1283.60.4 by Stewart Smith
Change when we call ib_cursor_next/prev. Instead of calling it after reading
2037
  advance_cursor= false;
2038
1283.63.1 by Stewart Smith
support SELECT ... FOR UPDATE locking for embedded_innodb. Do stupid shit because of the complete lack of error checking for startTableScan in parts of the upper layer.
2039
  previous_error= 0;
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2040
  return(0);
2041
}
2042
1283.60.10 by Stewart Smith
the memory management for BLOBS is completely insane. For certain types of index lookups we *must* do a copy and clear it *only* in ::reset() or ::extra(). This patch fixes up any valgrind warnings/assertions for embedded_innodb executing type_blob test.
2043
int read_row_from_innodb(unsigned char* buf, ib_crsr_t cursor, ib_tpl_t tuple, Table* table, bool has_hidden_primary_key, uint64_t *hidden_pkey, drizzled::memory::Root **blobroot)
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2044
{
1283.3.28 by Stewart Smith
simple rnd_init/rnd_next implementation for embedded innodb. It now works for inserting 1 row with an int column and selecting that row back (at least).
2045
  ib_err_t err;
1672.3.6 by Brian Aker
First pass in encapsulating row
2046
  ptrdiff_t row_offset= buf - table->getInsertRecord();
1283.3.28 by Stewart Smith
simple rnd_init/rnd_next implementation for embedded innodb. It now works for inserting 1 row with an int column and selecting that row back (at least).
2047
2048
  err= ib_cursor_read_row(cursor, tuple);
2049
2050
  if (err != DB_SUCCESS) // FIXME
2051
    return HA_ERR_END_OF_FILE;
2052
2053
  int colnr= 0;
2054
1283.60.8 by Stewart Smith
A ::position() call requires teh primary key in the record buffer, so we must *always* read the primary key in the various read methods in case we get a ::position() call. This was showing up in the simple ORDER BY test in type_blob_func.test
2055
  /* We need the primary key for ::position() to work */
1618 by Brian Aker
This is a rollup set of patches for modifications to TableIdentifier to have
2056
  if (table->s->getPrimaryKey() != MAX_KEY)
2057
    table->mark_columns_used_by_index_no_reset(table->s->getPrimaryKey());
1283.60.8 by Stewart Smith
A ::position() call requires teh primary key in the record buffer, so we must *always* read the primary key in the various read methods in case we get a ::position() call. This was showing up in the simple ORDER BY test in type_blob_func.test
2058
1593 by Brian Aker
Merge in Barry.
2059
  for (Field **field= table->getFields() ; *field ; field++, colnr++)
1283.3.28 by Stewart Smith
simple rnd_init/rnd_next implementation for embedded innodb. It now works for inserting 1 row with an int column and selecting that row back (at least).
2060
  {
1283.19.3 by Stewart Smith
fix up rnd_next for reading tables a bit more properly: respect readset, set writeset (to assert we're getting everything). Also use the Field::store() method to store the result in the Drizzle row buffer. This means the Field classes look after things like the length bytes.
2061
    if (! (**field).isReadSet())
2062
      continue;
2063
1283.36.1 by Stewart Smith
fix read_row_from_innodb to respect which buffer the row should be written into from innodb by using the amazing Field::move_field_offset() call properly.
2064
    (**field).move_field_offset(row_offset);
2065
1283.19.3 by Stewart Smith
fix up rnd_next for reading tables a bit more properly: respect readset, set writeset (to assert we're getting everything). Also use the Field::store() method to store the result in the Drizzle row buffer. This means the Field classes look after things like the length bytes.
2066
    (**field).setWriteSet();
2067
2068
    uint32_t length= ib_col_get_len(tuple, colnr);
2069
    if (length == IB_SQL_NULL)
1283.19.33 by Stewart Smith
fix reading null values from embedded innodb. don't try and retrieve a value for a column taht is null
2070
    {
1283.19.3 by Stewart Smith
fix up rnd_next for reading tables a bit more properly: respect readset, set writeset (to assert we're getting everything). Also use the Field::store() method to store the result in the Drizzle row buffer. This means the Field classes look after things like the length bytes.
2071
      (**field).set_null();
1283.19.33 by Stewart Smith
fix reading null values from embedded innodb. don't try and retrieve a value for a column taht is null
2072
      continue;
2073
    }
1283.19.3 by Stewart Smith
fix up rnd_next for reading tables a bit more properly: respect readset, set writeset (to assert we're getting everything). Also use the Field::store() method to store the result in the Drizzle row buffer. This means the Field classes look after things like the length bytes.
2074
    else
1283.19.5 by Stewart Smith
retrieve non-VARCHAR columns properly from embedded InnoDB. We should just shunt the bytes around except if we need to do things with strings...
2075
      (**field).set_notnull();
2076
2077
    if ((**field).type() == DRIZZLE_TYPE_VARCHAR)
1283.19.3 by Stewart Smith
fix up rnd_next for reading tables a bit more properly: respect readset, set writeset (to assert we're getting everything). Also use the Field::store() method to store the result in the Drizzle row buffer. This means the Field classes look after things like the length bytes.
2078
    {
2079
      (*field)->store((const char*)ib_col_get_value(tuple, colnr),
2080
                      length,
2081
                      &my_charset_bin);
1283.19.5 by Stewart Smith
retrieve non-VARCHAR columns properly from embedded InnoDB. We should just shunt the bytes around except if we need to do things with strings...
2082
    }
1283.35.45 by Stewart Smith
enable DATE type for embedded_innodb.
2083
    else if ((**field).type() == DRIZZLE_TYPE_DATE)
2084
    {
2085
      uint32_t date_read;
2086
      err= ib_tuple_read_u32(tuple, colnr, &date_read);
2087
      (*field)->store(date_read);
2088
    }
1283.60.5 by Stewart Smith
add BLOB support to embedded_innodb along with a simple test.
2089
    else if ((**field).type() == DRIZZLE_TYPE_BLOB)
2090
    {
1283.60.10 by Stewart Smith
the memory management for BLOBS is completely insane. For certain types of index lookups we *must* do a copy and clear it *only* in ::reset() or ::extra(). This patch fixes up any valgrind warnings/assertions for embedded_innodb executing type_blob test.
2091
      if (blobroot == NULL)
2092
        (reinterpret_cast<Field_blob*>(*field))->set_ptr(length,
2093
                                      (unsigned char*)ib_col_get_value(tuple,
2094
                                                                       colnr));
2095
      else
2096
      {
2097
        if (*blobroot == NULL)
2098
        {
2099
          *blobroot= new drizzled::memory::Root();
2100
          (**blobroot).init_alloc_root();
2101
        }
2102
2103
        unsigned char *blob_ptr= (unsigned char*)(**blobroot).alloc_root(length);
2104
        memcpy(blob_ptr, ib_col_get_value(tuple, colnr), length);
2105
        (reinterpret_cast<Field_blob*>(*field))->set_ptr(length, blob_ptr);
2106
      }
1283.60.5 by Stewart Smith
add BLOB support to embedded_innodb along with a simple test.
2107
    }
1283.19.5 by Stewart Smith
retrieve non-VARCHAR columns properly from embedded InnoDB. We should just shunt the bytes around except if we need to do things with strings...
2108
    else
2109
    {
2110
      ib_col_copy_value(tuple, colnr, (*field)->ptr, (*field)->data_length());
1283.19.3 by Stewart Smith
fix up rnd_next for reading tables a bit more properly: respect readset, set writeset (to assert we're getting everything). Also use the Field::store() method to store the result in the Drizzle row buffer. This means the Field classes look after things like the length bytes.
2111
    }
1283.36.1 by Stewart Smith
fix read_row_from_innodb to respect which buffer the row should be written into from innodb by using the amazing Field::move_field_offset() call properly.
2112
2113
    (**field).move_field_offset(-row_offset);
2114
1283.3.28 by Stewart Smith
simple rnd_init/rnd_next implementation for embedded innodb. It now works for inserting 1 row with an int column and selecting that row back (at least).
2115
  }
2116
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
2117
  if (has_hidden_primary_key)
2118
  {
2119
    err= ib_tuple_read_u64(tuple, colnr, hidden_pkey);
2120
  }
2121
1283.3.43 by Stewart Smith
refactor out rnd_next() into read_row_from_innodb() and a call to ib_cursor_next(). This allows us to make the row reading code generic for index scans/lookups.
2122
  return 0;
2123
}
2124
1283.36.1 by Stewart Smith
fix read_row_from_innodb to respect which buffer the row should be written into from innodb by using the amazing Field::move_field_offset() call properly.
2125
int EmbeddedInnoDBCursor::rnd_next(unsigned char *buf)
1283.3.43 by Stewart Smith
refactor out rnd_next() into read_row_from_innodb() and a call to ib_cursor_next(). This allows us to make the row reading code generic for index scans/lookups.
2126
{
2127
  ib_err_t err;
2128
  int ret;
2129
1283.63.1 by Stewart Smith
support SELECT ... FOR UPDATE locking for embedded_innodb. Do stupid shit because of the complete lack of error checking for startTableScan in parts of the upper layer.
2130
  if (previous_error)
2131
    return previous_error;
2132
1283.60.4 by Stewart Smith
Change when we call ib_cursor_next/prev. Instead of calling it after reading
2133
  if (advance_cursor)
2134
    err= ib_cursor_next(cursor);
2135
1283.28.1 by Stewart Smith
basic UPDATE row for Embedded InnoDB Engine.
2136
  tuple= ib_tuple_clear(tuple);
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
2137
  ret= read_row_from_innodb(buf, cursor, tuple, table,
2138
                            share->has_hidden_primary_key,
2139
                            &hidden_autoinc_pkey_position);
1283.3.43 by Stewart Smith
refactor out rnd_next() into read_row_from_innodb() and a call to ib_cursor_next(). This allows us to make the row reading code generic for index scans/lookups.
2140
1283.60.4 by Stewart Smith
Change when we call ib_cursor_next/prev. Instead of calling it after reading
2141
  advance_cursor= true;
1283.3.43 by Stewart Smith
refactor out rnd_next() into read_row_from_innodb() and a call to ib_cursor_next(). This allows us to make the row reading code generic for index scans/lookups.
2142
  return ret;
1283.3.28 by Stewart Smith
simple rnd_init/rnd_next implementation for embedded innodb. It now works for inserting 1 row with an int column and selecting that row back (at least).
2143
}
2144
1491.1.10 by Jay Pipes
ha_rnd_init -> startTableScan, rnd_init -> doStartTableScan, ha_rnd_end -> endTableScan, rnd_end -> doEndTableScan
2145
int EmbeddedInnoDBCursor::doEndTableScan()
1283.3.28 by Stewart Smith
simple rnd_init/rnd_next implementation for embedded innodb. It now works for inserting 1 row with an int column and selecting that row back (at least).
2146
{
1283.19.28 by Stewart Smith
fixup error checking
2147
  ib_err_t err;
2148
1283.3.36 by Stewart Smith
'correctly' deal with transaction in an autocommit type way. this means queries like 'insert select' work as we're always in the correct transactional context.
2149
  ib_tuple_delete(tuple);
1283.19.28 by Stewart Smith
fixup error checking
2150
  err= ib_cursor_reset(cursor);
2151
  assert(err == DB_SUCCESS);
1283.60.11 by Stewart Smith
doStartTableScan() can be called twice in a row without a doEndTableScan()
2152
  in_table_scan= false;
1283.63.1 by Stewart Smith
support SELECT ... FOR UPDATE locking for embedded_innodb. Do stupid shit because of the complete lack of error checking for startTableScan in parts of the upper layer.
2153
  previous_error= 0;
1283.3.28 by Stewart Smith
simple rnd_init/rnd_next implementation for embedded innodb. It now works for inserting 1 row with an int column and selecting that row back (at least).
2154
  return 0;
2155
}
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2156
1283.36.1 by Stewart Smith
fix read_row_from_innodb to respect which buffer the row should be written into from innodb by using the amazing Field::move_field_offset() call properly.
2157
int EmbeddedInnoDBCursor::rnd_pos(unsigned char *buf, unsigned char *pos)
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2158
{
1283.28.29 by Stewart Smith
implement rnd_pos for embedded_innodb. Also fix up fill_ib_search_tpl_froM_drizzle_key for primary keys that aren't all at the start of the table. It turns out that the clustered index search tuple numbers columns just in the clustered index, not anything to do with column numbers in the table.
2159
  ib_err_t err;
2160
  int res;
1283.60.7 by Stewart Smith
improve error handling in EmbeddedInnoDBCursor::rnd_pos()
2161
  int ret= 0;
1283.28.29 by Stewart Smith
implement rnd_pos for embedded_innodb. Also fix up fill_ib_search_tpl_froM_drizzle_key for primary keys that aren't all at the start of the table. It turns out that the clustered index search tuple numbers columns just in the clustered index, not anything to do with column numbers in the table.
2162
  ib_tpl_t search_tuple= ib_clust_search_tuple_create(cursor);
2163
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
2164
  if (share->has_hidden_primary_key)
2165
  {
1283.60.7 by Stewart Smith
improve error handling in EmbeddedInnoDBCursor::rnd_pos()
2166
    err= ib_col_set_value(search_tuple, 0,
1283.60.9 by Stewart Smith
fix (rather embarrassing) bug where with a hidden primary key in rnd_pos() we would go to the row in ref rather tahn the parameter pos. If we had a style of m_ prefix for members, this would not have been a problem.
2167
                          ((uint64_t*)(pos)), sizeof(uint64_t));
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
2168
  }
2169
  else
2170
  {
1283.63.13 by Stewart Smith
fix ::rnd_pos and ::position (hence ref_length) for tables with implicit clustered/primary keys.
2171
    unsigned int keynr;
1283.63.17 by Stewart Smith
fix getShare()->primary_key to getPrimaryKey()
2172
    if (table->getShare()->getPrimaryKey() != MAX_KEY)
2173
      keynr= table->getShare()->getPrimaryKey();
1283.63.13 by Stewart Smith
fix ::rnd_pos and ::position (hence ref_length) for tables with implicit clustered/primary keys.
2174
    else
1283.63.28 by Stewart Smith
style fixes
2175
      keynr= get_first_unique_index(*table);
1283.63.13 by Stewart Smith
fix ::rnd_pos and ::position (hence ref_length) for tables with implicit clustered/primary keys.
2176
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
2177
    fill_ib_search_tpl_from_drizzle_key(search_tuple,
1283.63.13 by Stewart Smith
fix ::rnd_pos and ::position (hence ref_length) for tables with implicit clustered/primary keys.
2178
                                        table->key_info + keynr,
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
2179
                                        pos, ref_length);
2180
  }
1283.28.29 by Stewart Smith
implement rnd_pos for embedded_innodb. Also fix up fill_ib_search_tpl_froM_drizzle_key for primary keys that aren't all at the start of the table. It turns out that the clustered index search tuple numbers columns just in the clustered index, not anything to do with column numbers in the table.
2181
2182
  err= ib_cursor_moveto(cursor, search_tuple, IB_CUR_GE, &res);
2183
  assert(err == DB_SUCCESS);
1283.60.7 by Stewart Smith
improve error handling in EmbeddedInnoDBCursor::rnd_pos()
2184
2185
  assert(res==0);
2186
  if (res != 0)
2187
    ret= -1;
2188
1283.28.29 by Stewart Smith
implement rnd_pos for embedded_innodb. Also fix up fill_ib_search_tpl_froM_drizzle_key for primary keys that aren't all at the start of the table. It turns out that the clustered index search tuple numbers columns just in the clustered index, not anything to do with column numbers in the table.
2189
  ib_tuple_delete(search_tuple);
2190
2191
  tuple= ib_tuple_clear(tuple);
1283.60.7 by Stewart Smith
improve error handling in EmbeddedInnoDBCursor::rnd_pos()
2192
2193
  if (ret == 0)
2194
    ret= read_row_from_innodb(buf, cursor, tuple, table,
2195
                              share->has_hidden_primary_key,
2196
                              &hidden_autoinc_pkey_position);
1283.28.29 by Stewart Smith
implement rnd_pos for embedded_innodb. Also fix up fill_ib_search_tpl_froM_drizzle_key for primary keys that aren't all at the start of the table. It turns out that the clustered index search tuple numbers columns just in the clustered index, not anything to do with column numbers in the table.
2197
1283.60.4 by Stewart Smith
Change when we call ib_cursor_next/prev. Instead of calling it after reading
2198
  advance_cursor= true;
1283.28.29 by Stewart Smith
implement rnd_pos for embedded_innodb. Also fix up fill_ib_search_tpl_froM_drizzle_key for primary keys that aren't all at the start of the table. It turns out that the clustered index search tuple numbers columns just in the clustered index, not anything to do with column numbers in the table.
2199
1283.60.7 by Stewart Smith
improve error handling in EmbeddedInnoDBCursor::rnd_pos()
2200
  return(ret);
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2201
}
2202
1475.2.9 by Stewart Smith
fix many compile failures that people introduced in embedded_innodb because it's not built by default.. i.e. plugin=disabled is EPIC FAIL
2203
static void store_key_value_from_innodb(KeyInfo *key_info, unsigned char* ref, int ref_len, const unsigned char *record)
1283.28.25 by Stewart Smith
simple ::position() implementation for embedded innodb. include simple test (that does call it).
2204
{
1475.2.9 by Stewart Smith
fix many compile failures that people introduced in embedded_innodb because it's not built by default.. i.e. plugin=disabled is EPIC FAIL
2205
  KeyPartInfo* key_part= key_info->key_part;
2206
  KeyPartInfo* end= key_info->key_part + key_info->key_parts;
1283.28.25 by Stewart Smith
simple ::position() implementation for embedded innodb. include simple test (that does call it).
2207
  unsigned char* ref_start= ref;
2208
2209
  memset(ref, 0, ref_len);
2210
2211
  for (; key_part != end; key_part++)
2212
  {
2213
    char is_null= 0;
2214
2215
    if(key_part->null_bit)
2216
    {
2217
      *ref= is_null= record[key_part->null_offset] & key_part->null_bit;
2218
      ref++;
2219
    }
2220
2221
    Field *field= key_part->field;
2222
2223
    if (field->type() == DRIZZLE_TYPE_VARCHAR)
2224
    {
2225
      if (is_null)
2226
      {
2227
        ref+= key_part->length + 2; /* 2 bytes for length */
2228
        continue;
2229
      }
2230
2231
      String str;
2232
      field->val_str(&str);
2233
2234
      *ref++= (char)(str.length() & 0x000000ff);
2235
      *ref++= (char)((str.length()>>8) & 0x000000ff);
2236
2237
      memcpy(ref, str.ptr(), str.length());
1283.28.28 by Stewart Smith
fix up store_key_value_from_innodb for embedded_innodb ::position() with varchar columns that weren't full.
2238
      ref+= key_part->length;
1283.28.25 by Stewart Smith
simple ::position() implementation for embedded innodb. include simple test (that does call it).
2239
    }
2240
    // FIXME: blobs.
2241
    else
2242
    {
2243
      if (is_null)
2244
      {
2245
        ref+= key_part->length;
2246
        continue;
2247
      }
2248
2249
      memcpy(ref, record+key_part->offset, key_part->length);
2250
      ref+= key_part->length;
2251
    }
2252
2253
  }
2254
2255
  assert(ref == ref_start + ref_len);
2256
}
2257
2258
void EmbeddedInnoDBCursor::position(const unsigned char *record)
2259
{
1283.63.13 by Stewart Smith
fix ::rnd_pos and ::position (hence ref_length) for tables with implicit clustered/primary keys.
2260
  if (share->has_hidden_primary_key)
2261
    *((uint64_t*) ref)= hidden_autoinc_pkey_position;
2262
  else
2263
  {
2264
    unsigned int keynr;
1283.63.16 by Stewart Smith
merge trunk
2265
    if (table->getShare()->getPrimaryKey() != MAX_KEY)
2266
      keynr= table->getShare()->getPrimaryKey();
1283.63.13 by Stewart Smith
fix ::rnd_pos and ::position (hence ref_length) for tables with implicit clustered/primary keys.
2267
    else
1283.63.28 by Stewart Smith
style fixes
2268
      keynr= get_first_unique_index(*table);
1283.63.13 by Stewart Smith
fix ::rnd_pos and ::position (hence ref_length) for tables with implicit clustered/primary keys.
2269
2270
    store_key_value_from_innodb(table->key_info + keynr,
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
2271
                                ref, ref_length, record);
1283.63.13 by Stewart Smith
fix ::rnd_pos and ::position (hence ref_length) for tables with implicit clustered/primary keys.
2272
  }
2273
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2274
  return;
2275
}
2276
1283.3.42 by Stewart Smith
basic index scan of embedded innodb clustered index
2277
double EmbeddedInnoDBCursor::scan_time()
2278
{
2279
  return 0.1;
2280
}
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2281
2282
int EmbeddedInnoDBCursor::info(uint32_t flag)
2283
{
1283.3.42 by Stewart Smith
basic index scan of embedded innodb clustered index
2284
  stats.records= 2;
1283.3.36 by Stewart Smith
'correctly' deal with transaction in an autocommit type way. this means queries like 'insert select' work as we're always in the correct transactional context.
2285
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2286
  if (flag & HA_STATUS_AUTO)
2287
    stats.auto_increment_value= 1;
2288
  return(0);
2289
}
2290
1491.1.6 by Jay Pipes
Cursor::ha_index_init() -> Cursor::startIndexScan(). Cursor::ha_index_end() -> Cursor::endIndexScan()
2291
int EmbeddedInnoDBCursor::doStartIndexScan(uint32_t keynr, bool)
1283.3.42 by Stewart Smith
basic index scan of embedded innodb clustered index
2292
{
1578.6.2 by Brian Aker
Remove ha_session.
2293
  ib_trx_t transaction= *get_trx(table->in_use);
1283.3.80 by Stewart Smith
add basic transactional support to Embedded InnoDB engine.
2294
1283.3.42 by Stewart Smith
basic index scan of embedded innodb clustered index
2295
  active_index= keynr;
2296
2297
  ib_cursor_attach_trx(cursor, transaction);
2298
1598.4.7 by Stewart Smith
for start index scan and index_read, we only do a clustered index scan if we don't have a hidden primary key (i.e. index 0 == clustered index). This was causing func_group test case crashes due to mismatching index.
2299
  if (active_index == 0 && ! share->has_hidden_primary_key)
1283.3.42 by Stewart Smith
basic index scan of embedded innodb clustered index
2300
  {
2301
    tuple= ib_clust_read_tuple_create(cursor);
2302
  }
2303
  else
2304
  {
1283.28.15 by Stewart Smith
support secondary index scan in embedded_innodb. we add a next_innodb_error member to EmbeddedInnodbCursor as unlike clustered indexes, trying to fetch a row after you have gotten DB_END_OF_INDEX results in a much nastier crash than a simple error code.
2305
    ib_err_t err;
2306
    ib_id_t index_id;
1598.4.1 by Stewart Smith
support temporary tables in embedded_innodb - this means we can also run the alter_table test.
2307
    err= ib_index_get_id(table_path_to_innodb_name(table_share->getPath()),
1574.1.3 by Brian Aker
Encapsulate Key info in share.
2308
                         table_share->getKeyInfo(keynr).name,
1283.28.15 by Stewart Smith
support secondary index scan in embedded_innodb. we add a next_innodb_error member to EmbeddedInnodbCursor as unlike clustered indexes, trying to fetch a row after you have gotten DB_END_OF_INDEX results in a much nastier crash than a simple error code.
2309
                         &index_id);
2310
    if (err != DB_SUCCESS)
2311
      return -1;
2312
2313
    err= ib_cursor_close(cursor);
1283.63.1 by Stewart Smith
support SELECT ... FOR UPDATE locking for embedded_innodb. Do stupid shit because of the complete lack of error checking for startTableScan in parts of the upper layer.
2314
    assert(err == DB_SUCCESS);
1283.28.15 by Stewart Smith
support secondary index scan in embedded_innodb. we add a next_innodb_error member to EmbeddedInnodbCursor as unlike clustered indexes, trying to fetch a row after you have gotten DB_END_OF_INDEX results in a much nastier crash than a simple error code.
2315
    err= ib_cursor_open_index_using_id(index_id, transaction, &cursor);
2316
2317
    if (err != DB_SUCCESS)
2318
      return -1;
2319
2320
    tuple= ib_clust_read_tuple_create(cursor);
2321
    ib_cursor_set_cluster_access(cursor);
1283.3.42 by Stewart Smith
basic index scan of embedded innodb clustered index
2322
  }
2323
1283.63.1 by Stewart Smith
support SELECT ... FOR UPDATE locking for embedded_innodb. Do stupid shit because of the complete lack of error checking for startTableScan in parts of the upper layer.
2324
  ib_err_t err= ib_cursor_set_lock_mode(cursor, ib_lock_mode);
2325
  assert(err == DB_SUCCESS);
2326
1283.60.4 by Stewart Smith
Change when we call ib_cursor_next/prev. Instead of calling it after reading
2327
  advance_cursor= false;
1283.3.42 by Stewart Smith
basic index scan of embedded innodb clustered index
2328
  return 0;
2329
}
2330
1283.28.16 by Stewart Smith
use appropriate ib_srch_mode for index_read. implement ha_rkey_function to ib_sch_mode function.
2331
static ib_srch_mode_t ha_rkey_function_to_ib_srch_mode(drizzled::ha_rkey_function find_flag)
2332
{
2333
  switch (find_flag)
2334
  {
2335
  case HA_READ_KEY_EXACT:
2336
    return IB_CUR_GE;
2337
  case HA_READ_KEY_OR_NEXT:
2338
    return IB_CUR_GE;
2339
  case HA_READ_KEY_OR_PREV:
2340
    return IB_CUR_LE;
2341
  case HA_READ_AFTER_KEY:
2342
    return IB_CUR_G;
2343
  case HA_READ_BEFORE_KEY:
2344
    return IB_CUR_L;
2345
  case HA_READ_PREFIX:
2346
    return IB_CUR_GE;
2347
  case HA_READ_PREFIX_LAST:
2348
    return IB_CUR_LE;
2349
  case HA_READ_PREFIX_LAST_OR_PREV:
2350
    return IB_CUR_LE;
2351
  case HA_READ_MBR_CONTAIN:
2352
  case HA_READ_MBR_INTERSECT:
2353
  case HA_READ_MBR_WITHIN:
2354
  case HA_READ_MBR_DISJOINT:
2355
  case HA_READ_MBR_EQUAL:
2356
    assert(false); /* these just exist in the enum, not used. */
2357
  }
2358
2359
  assert(false);
1530.5.10 by Monty Taylor
Fixed build errors on FreeBSD.
2360
  /* Must return or compiler complains about reaching end of function */
2361
  return (ib_srch_mode_t)0;
1283.28.16 by Stewart Smith
use appropriate ib_srch_mode for index_read. implement ha_rkey_function to ib_sch_mode function.
2362
}
2363
1283.28.17 by Stewart Smith
implement index_read for multi column indexes
2364
static void fill_ib_search_tpl_from_drizzle_key(ib_tpl_t search_tuple,
1475.2.9 by Stewart Smith
fix many compile failures that people introduced in embedded_innodb because it's not built by default.. i.e. plugin=disabled is EPIC FAIL
2365
                                                const drizzled::KeyInfo *key_info,
1283.28.17 by Stewart Smith
implement index_read for multi column indexes
2366
                                                const unsigned char *key_ptr,
2367
                                                uint32_t key_len)
2368
{
1475.2.9 by Stewart Smith
fix many compile failures that people introduced in embedded_innodb because it's not built by default.. i.e. plugin=disabled is EPIC FAIL
2369
  KeyPartInfo *key_part= key_info->key_part;
2370
  KeyPartInfo *end= key_part + key_info->key_parts;
1283.28.17 by Stewart Smith
implement index_read for multi column indexes
2371
  const unsigned char *buff= key_ptr;
2372
  ib_err_t err;
2373
1283.28.29 by Stewart Smith
implement rnd_pos for embedded_innodb. Also fix up fill_ib_search_tpl_froM_drizzle_key for primary keys that aren't all at the start of the table. It turns out that the clustered index search tuple numbers columns just in the clustered index, not anything to do with column numbers in the table.
2374
  int fieldnr= 0;
2375
1283.28.17 by Stewart Smith
implement index_read for multi column indexes
2376
  for(; key_part != end && buff < key_ptr + key_len; key_part++)
2377
  {
2378
    Field *field= key_part->field;
2379
    bool is_null= false;
2380
2381
    if (key_part->null_bit)
2382
    {
2383
      is_null= *buff;
2384
      if (is_null)
2385
      {
1283.28.29 by Stewart Smith
implement rnd_pos for embedded_innodb. Also fix up fill_ib_search_tpl_froM_drizzle_key for primary keys that aren't all at the start of the table. It turns out that the clustered index search tuple numbers columns just in the clustered index, not anything to do with column numbers in the table.
2386
        err= ib_col_set_value(search_tuple, fieldnr, NULL, IB_SQL_NULL);
1283.28.17 by Stewart Smith
implement index_read for multi column indexes
2387
        assert(err == DB_SUCCESS);
2388
      }
2389
      buff++;
2390
    }
2391
2392
    if (field->type() == DRIZZLE_TYPE_VARCHAR)
2393
    {
2394
      if (is_null)
2395
      {
2396
        buff+= key_part->length + 2; /* 2 bytes length */
2397
        continue;
2398
      }
2399
2400
      int length= *buff + (*(buff + 1) << 8);
1283.28.29 by Stewart Smith
implement rnd_pos for embedded_innodb. Also fix up fill_ib_search_tpl_froM_drizzle_key for primary keys that aren't all at the start of the table. It turns out that the clustered index search tuple numbers columns just in the clustered index, not anything to do with column numbers in the table.
2401
      buff+=2;
2402
      err= ib_col_set_value(search_tuple, fieldnr, buff, length);
1283.28.17 by Stewart Smith
implement index_read for multi column indexes
2403
      assert(err == DB_SUCCESS);
2404
1283.28.29 by Stewart Smith
implement rnd_pos for embedded_innodb. Also fix up fill_ib_search_tpl_froM_drizzle_key for primary keys that aren't all at the start of the table. It turns out that the clustered index search tuple numbers columns just in the clustered index, not anything to do with column numbers in the table.
2405
      buff+= key_part->length;
1283.28.17 by Stewart Smith
implement index_read for multi column indexes
2406
    }
1283.35.45 by Stewart Smith
enable DATE type for embedded_innodb.
2407
    else if (field->type() == DRIZZLE_TYPE_DATE)
2408
    {
1283.46.3 by Stewart Smith
simplify filling search tuple for DATE types in embedded_innodb
2409
      uint32_t date_int= static_cast<uint32_t>(field->val_int());
1283.35.45 by Stewart Smith
enable DATE type for embedded_innodb.
2410
      err= ib_col_set_value(search_tuple, fieldnr, &date_int, 4);
2411
      buff+= key_part->length;
2412
    }
1283.28.17 by Stewart Smith
implement index_read for multi column indexes
2413
    // FIXME: BLOBs
2414
    else
2415
    {
2416
      if (is_null)
2417
      {
2418
        buff+= key_part->length;
2419
        continue;
2420
      }
2421
1283.28.29 by Stewart Smith
implement rnd_pos for embedded_innodb. Also fix up fill_ib_search_tpl_froM_drizzle_key for primary keys that aren't all at the start of the table. It turns out that the clustered index search tuple numbers columns just in the clustered index, not anything to do with column numbers in the table.
2422
      err= ib_col_set_value(search_tuple, fieldnr,
1283.28.17 by Stewart Smith
implement index_read for multi column indexes
2423
                            buff, key_part->length);
2424
      assert(err == DB_SUCCESS);
2425
2426
      buff+= key_part->length;
2427
    }
1283.28.29 by Stewart Smith
implement rnd_pos for embedded_innodb. Also fix up fill_ib_search_tpl_froM_drizzle_key for primary keys that aren't all at the start of the table. It turns out that the clustered index search tuple numbers columns just in the clustered index, not anything to do with column numbers in the table.
2428
2429
    fieldnr++;
1283.28.17 by Stewart Smith
implement index_read for multi column indexes
2430
  }
2431
2432
  assert(buff == key_ptr + key_len);
2433
}
2434
1283.60.10 by Stewart Smith
the memory management for BLOBS is completely insane. For certain types of index lookups we *must* do a copy and clear it *only* in ::reset() or ::extra(). This patch fixes up any valgrind warnings/assertions for embedded_innodb executing type_blob test.
2435
int EmbeddedInnoDBCursor::innodb_index_read(unsigned char *buf,
2436
                                            const unsigned char *key_ptr,
2437
                                            uint32_t key_len,
2438
                                            drizzled::ha_rkey_function find_flag,
2439
                                            bool allocate_blobs)
1283.3.52 by Stewart Smith
simple index_read() for embedded innodb. Add a test for first column beivng primary key and index lookups/scans.
2440
{
2441
  ib_tpl_t search_tuple;
2442
  int res;
2443
  ib_err_t err;
2444
  int ret;
1283.28.16 by Stewart Smith
use appropriate ib_srch_mode for index_read. implement ha_rkey_function to ib_sch_mode function.
2445
  ib_srch_mode_t search_mode;
1283.3.52 by Stewart Smith
simple index_read() for embedded innodb. Add a test for first column beivng primary key and index lookups/scans.
2446
1283.28.16 by Stewart Smith
use appropriate ib_srch_mode for index_read. implement ha_rkey_function to ib_sch_mode function.
2447
  search_mode= ha_rkey_function_to_ib_srch_mode(find_flag);
2448
1598.4.7 by Stewart Smith
for start index scan and index_read, we only do a clustered index scan if we don't have a hidden primary key (i.e. index 0 == clustered index). This was causing func_group test case crashes due to mismatching index.
2449
  if (active_index == 0 && ! share->has_hidden_primary_key)
1283.28.17 by Stewart Smith
implement index_read for multi column indexes
2450
    search_tuple= ib_clust_search_tuple_create(cursor);
2451
  else
2452
    search_tuple= ib_sec_search_tuple_create(cursor);
1283.3.52 by Stewart Smith
simple index_read() for embedded innodb. Add a test for first column beivng primary key and index lookups/scans.
2453
1283.28.17 by Stewart Smith
implement index_read for multi column indexes
2454
  fill_ib_search_tpl_from_drizzle_key(search_tuple,
2455
                                      table->key_info + active_index,
2456
                                      key_ptr, key_len);
1283.3.52 by Stewart Smith
simple index_read() for embedded innodb. Add a test for first column beivng primary key and index lookups/scans.
2457
1283.28.16 by Stewart Smith
use appropriate ib_srch_mode for index_read. implement ha_rkey_function to ib_sch_mode function.
2458
  err= ib_cursor_moveto(cursor, search_tuple, search_mode, &res);
1283.28.17 by Stewart Smith
implement index_read for multi column indexes
2459
  ib_tuple_delete(search_tuple);
2460
1283.60.14 by Stewart Smith
we actually don't need to check the result, just set status correctly
2461
  if ((err == DB_RECORD_NOT_FOUND || err == DB_END_OF_INDEX))
1283.60.12 by Stewart Smith
check that we really did move to the right row in EmbeddedInnoDBCursor::innodb_index_read(). This emans type_blob test now passes. We need to update table->status as well here.
2462
  {
1283.60.14 by Stewart Smith
we actually don't need to check the result, just set status correctly
2463
    table->status= STATUS_NOT_FOUND;
1283.60.12 by Stewart Smith
check that we really did move to the right row in EmbeddedInnoDBCursor::innodb_index_read(). This emans type_blob test now passes. We need to update table->status as well here.
2464
    return HA_ERR_KEY_NOT_FOUND;
2465
  }
2466
1283.63.3 by Stewart Smith
fix up (and test) SELECT ... FOR UPDATE locking for embedded_innodb with pkey index
2467
  if (err != DB_SUCCESS)
2468
  {
2469
    return ib_err_t_to_drizzle_error(err);
2470
  }
1283.3.52 by Stewart Smith
simple index_read() for embedded innodb. Add a test for first column beivng primary key and index lookups/scans.
2471
1283.28.1 by Stewart Smith
basic UPDATE row for Embedded InnoDB Engine.
2472
  tuple= ib_tuple_clear(tuple);
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
2473
  ret= read_row_from_innodb(buf, cursor, tuple, table,
2474
                            share->has_hidden_primary_key,
1283.60.10 by Stewart Smith
the memory management for BLOBS is completely insane. For certain types of index lookups we *must* do a copy and clear it *only* in ::reset() or ::extra(). This patch fixes up any valgrind warnings/assertions for embedded_innodb executing type_blob test.
2475
                            &hidden_autoinc_pkey_position,
2476
                            (allocate_blobs)? &blobroot : NULL);
1283.60.12 by Stewart Smith
check that we really did move to the right row in EmbeddedInnoDBCursor::innodb_index_read(). This emans type_blob test now passes. We need to update table->status as well here.
2477
  if (ret == 0)
2478
    table->status= 0;
2479
  else
2480
    table->status= STATUS_NOT_FOUND;
2481
1283.60.4 by Stewart Smith
Change when we call ib_cursor_next/prev. Instead of calling it after reading
2482
  advance_cursor= true;
1283.3.52 by Stewart Smith
simple index_read() for embedded innodb. Add a test for first column beivng primary key and index lookups/scans.
2483
1283.60.12 by Stewart Smith
check that we really did move to the right row in EmbeddedInnoDBCursor::innodb_index_read(). This emans type_blob test now passes. We need to update table->status as well here.
2484
  return ret;
1283.3.52 by Stewart Smith
simple index_read() for embedded innodb. Add a test for first column beivng primary key and index lookups/scans.
2485
}
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2486
1283.60.10 by Stewart Smith
the memory management for BLOBS is completely insane. For certain types of index lookups we *must* do a copy and clear it *only* in ::reset() or ::extra(). This patch fixes up any valgrind warnings/assertions for embedded_innodb executing type_blob test.
2487
int EmbeddedInnoDBCursor::index_read(unsigned char *buf,
2488
                                     const unsigned char *key_ptr,
2489
                                     uint32_t key_len,
2490
                                     drizzled::ha_rkey_function find_flag)
2491
{
2492
  return innodb_index_read(buf, key_ptr, key_len, find_flag, false);
2493
}
2494
2495
/* This is straight from cursor.cc, but it's private there :( */
2496
uint32_t EmbeddedInnoDBCursor::calculate_key_len(uint32_t key_position,
2497
                                                 key_part_map keypart_map_arg)
2498
{
2499
  /* works only with key prefixes */
2500
  assert(((keypart_map_arg + 1) & keypart_map_arg) == 0);
2501
1574.1.3 by Brian Aker
Encapsulate Key info in share.
2502
  KeyPartInfo *key_part_found= table->s->getKeyInfo(key_position).key_part;
2503
  KeyPartInfo *end_key_part_found= key_part_found + table->s->getKeyInfo(key_position).key_parts;
1283.60.10 by Stewart Smith
the memory management for BLOBS is completely insane. For certain types of index lookups we *must* do a copy and clear it *only* in ::reset() or ::extra(). This patch fixes up any valgrind warnings/assertions for embedded_innodb executing type_blob test.
2504
  uint32_t length= 0;
2505
2506
  while (key_part_found < end_key_part_found && keypart_map_arg)
2507
  {
2508
    length+= key_part_found->store_length;
2509
    keypart_map_arg >>= 1;
2510
    key_part_found++;
2511
  }
2512
  return length;
2513
}
2514
2515
2516
int EmbeddedInnoDBCursor::innodb_index_read_map(unsigned char * buf,
2517
                                                const unsigned char *key,
2518
                                                key_part_map keypart_map,
2519
                                                enum ha_rkey_function find_flag,
2520
                                                bool allocate_blobs)
2521
{
2522
  uint32_t key_len= calculate_key_len(active_index, keypart_map);
2523
  return  innodb_index_read(buf, key, key_len, find_flag, allocate_blobs);
2524
}
2525
2526
int EmbeddedInnoDBCursor::index_read_idx_map(unsigned char * buf,
2527
                                             uint32_t index,
2528
                                             const unsigned char * key,
2529
                                             key_part_map keypart_map,
2530
                                             enum ha_rkey_function find_flag)
2531
{
2532
  int error, error1;
2533
  error= doStartIndexScan(index, 0);
2534
  if (!error)
2535
  {
2536
    error= innodb_index_read_map(buf, key, keypart_map, find_flag, true);
2537
    error1= doEndIndexScan();
2538
  }
2539
  return error ?  error : error1;
2540
}
2541
2542
int EmbeddedInnoDBCursor::reset()
2543
{
2544
  if (blobroot)
2545
    blobroot->free_root(MYF(0));
2546
2547
  return 0;
2548
}
2549
1283.36.1 by Stewart Smith
fix read_row_from_innodb to respect which buffer the row should be written into from innodb by using the amazing Field::move_field_offset() call properly.
2550
int EmbeddedInnoDBCursor::index_next(unsigned char *buf)
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2551
{
1283.3.43 by Stewart Smith
refactor out rnd_next() into read_row_from_innodb() and a call to ib_cursor_next(). This allows us to make the row reading code generic for index scans/lookups.
2552
  int ret= HA_ERR_END_OF_FILE;
1283.28.15 by Stewart Smith
support secondary index scan in embedded_innodb. we add a next_innodb_error member to EmbeddedInnodbCursor as unlike clustered indexes, trying to fetch a row after you have gotten DB_END_OF_INDEX results in a much nastier crash than a simple error code.
2553
1283.60.4 by Stewart Smith
Change when we call ib_cursor_next/prev. Instead of calling it after reading
2554
  if (advance_cursor)
2555
  {
2556
    ib_err_t err= ib_cursor_next(cursor);
2557
    if (err == DB_END_OF_INDEX)
2558
      return HA_ERR_END_OF_FILE;
2559
  }
1283.28.15 by Stewart Smith
support secondary index scan in embedded_innodb. we add a next_innodb_error member to EmbeddedInnodbCursor as unlike clustered indexes, trying to fetch a row after you have gotten DB_END_OF_INDEX results in a much nastier crash than a simple error code.
2560
2561
  tuple= ib_tuple_clear(tuple);
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
2562
  ret= read_row_from_innodb(buf, cursor, tuple, table,
2563
                            share->has_hidden_primary_key,
2564
                            &hidden_autoinc_pkey_position);
1283.3.42 by Stewart Smith
basic index scan of embedded innodb clustered index
2565
1283.60.4 by Stewart Smith
Change when we call ib_cursor_next/prev. Instead of calling it after reading
2566
  advance_cursor= true;
1283.3.43 by Stewart Smith
refactor out rnd_next() into read_row_from_innodb() and a call to ib_cursor_next(). This allows us to make the row reading code generic for index scans/lookups.
2567
  return ret;
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2568
}
2569
1491.1.6 by Jay Pipes
Cursor::ha_index_init() -> Cursor::startIndexScan(). Cursor::ha_index_end() -> Cursor::endIndexScan()
2570
int EmbeddedInnoDBCursor::doEndIndexScan()
1283.3.42 by Stewart Smith
basic index scan of embedded innodb clustered index
2571
{
2572
  active_index= MAX_KEY;
2573
1491.1.10 by Jay Pipes
ha_rnd_init -> startTableScan, rnd_init -> doStartTableScan, ha_rnd_end -> endTableScan, rnd_end -> doEndTableScan
2574
  return doEndTableScan();
1283.3.42 by Stewart Smith
basic index scan of embedded innodb clustered index
2575
}
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2576
1283.36.1 by Stewart Smith
fix read_row_from_innodb to respect which buffer the row should be written into from innodb by using the amazing Field::move_field_offset() call properly.
2577
int EmbeddedInnoDBCursor::index_prev(unsigned char *buf)
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2578
{
1283.3.44 by Stewart Smith
reverse index scanning for embedded innodb. support index_last and index_prev
2579
  int ret= HA_ERR_END_OF_FILE;
2580
  ib_err_t err;
2581
1283.60.4 by Stewart Smith
Change when we call ib_cursor_next/prev. Instead of calling it after reading
2582
  if (advance_cursor)
1598.4.9 by Stewart Smith
fix index_prev for secondary indexes.
2583
  {
1283.60.4 by Stewart Smith
Change when we call ib_cursor_next/prev. Instead of calling it after reading
2584
    err= ib_cursor_prev(cursor);
1598.4.9 by Stewart Smith
fix index_prev for secondary indexes.
2585
    if (err != DB_SUCCESS)
2586
    {
2587
      if (err == DB_END_OF_INDEX)
2588
        return HA_ERR_END_OF_FILE;
2589
      else
2590
        return -1; // FIXME
2591
    }
1283.3.44 by Stewart Smith
reverse index scanning for embedded innodb. support index_last and index_prev
2592
  }
2593
1598.4.9 by Stewart Smith
fix index_prev for secondary indexes.
2594
  tuple= ib_tuple_clear(tuple);
2595
  ret= read_row_from_innodb(buf, cursor, tuple, table,
2596
                            share->has_hidden_primary_key,
2597
                            &hidden_autoinc_pkey_position);
2598
1283.60.4 by Stewart Smith
Change when we call ib_cursor_next/prev. Instead of calling it after reading
2599
  advance_cursor= true;
2600
1283.3.44 by Stewart Smith
reverse index scanning for embedded innodb. support index_last and index_prev
2601
  return ret;
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2602
}
2603
2604
1283.36.1 by Stewart Smith
fix read_row_from_innodb to respect which buffer the row should be written into from innodb by using the amazing Field::move_field_offset() call properly.
2605
int EmbeddedInnoDBCursor::index_first(unsigned char *buf)
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2606
{
1283.3.43 by Stewart Smith
refactor out rnd_next() into read_row_from_innodb() and a call to ib_cursor_next(). This allows us to make the row reading code generic for index scans/lookups.
2607
  int ret= HA_ERR_END_OF_FILE;
2608
  ib_err_t err;
2609
1283.21.21 by Stewart Smith
fix up error code checking
2610
  err= ib_cursor_first(cursor);
2611
  if (err != DB_SUCCESS)
1283.65.5 by Stewart Smith
make ::index_first() use proper error conversion
2612
    return ib_err_t_to_drizzle_error(err);
1283.3.42 by Stewart Smith
basic index scan of embedded innodb clustered index
2613
1283.28.15 by Stewart Smith
support secondary index scan in embedded_innodb. we add a next_innodb_error member to EmbeddedInnodbCursor as unlike clustered indexes, trying to fetch a row after you have gotten DB_END_OF_INDEX results in a much nastier crash than a simple error code.
2614
  tuple= ib_tuple_clear(tuple);
1283.35.97 by Stewart Smith
support tables without an explicit primary key in embedded_innodb by creating a hidden auto_increment primary key. We also have to support tables without an explicit primary key but with an auto increment, so we have our own hidden one. yes, it hurts.
2615
  ret= read_row_from_innodb(buf, cursor, tuple, table,
2616
                            share->has_hidden_primary_key,
2617
                            &hidden_autoinc_pkey_position);
1283.60.4 by Stewart Smith
Change when we call ib_cursor_next/prev. Instead of calling it after reading
2618
2619
  advance_cursor= true;
1283.3.42 by Stewart Smith
basic index scan of embedded innodb clustered index
2620
1283.3.43 by Stewart Smith
refactor out rnd_next() into read_row_from_innodb() and a call to ib_cursor_next(). This allows us to make the row reading code generic for index scans/lookups.
2621
  return ret;
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2622
}
2623
2624
1283.36.1 by Stewart Smith
fix read_row_from_innodb to respect which buffer the row should be written into from innodb by using the amazing Field::move_field_offset() call properly.
2625
int EmbeddedInnoDBCursor::index_last(unsigned char *buf)
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2626
{
1283.3.44 by Stewart Smith
reverse index scanning for embedded innodb. support index_last and index_prev
2627
  int ret= HA_ERR_END_OF_FILE;
2628
  ib_err_t err;
2629
1283.21.21 by Stewart Smith
fix up error code checking
2630
  err= ib_cursor_last(cursor);
2631
  if (err != DB_SUCCESS)
1283.65.6 by Stewart Smith
make ::index_last() use proper error conversion
2632
    return ib_err_t_to_drizzle_error(err);
1283.3.44 by Stewart Smith
reverse index scanning for embedded innodb. support index_last and index_prev
2633
1598.4.9 by Stewart Smith
fix index_prev for secondary indexes.
2634
  tuple= ib_tuple_clear(tuple);
2635
  ret= read_row_from_innodb(buf, cursor, tuple, table,
2636
                            share->has_hidden_primary_key,
2637
                            &hidden_autoinc_pkey_position);
2638
  advance_cursor= true;
1283.3.44 by Stewart Smith
reverse index scanning for embedded innodb. support index_last and index_prev
2639
2640
  return ret;
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2641
}
2642
1283.39.8 by Stewart Smith
add support for REPLACE to embedded_innodb. On duplicate key on insert if we have HA_EXTRA_WRITE_CAN_REPLACE set, then we delete the row and insert.
2643
int EmbeddedInnoDBCursor::extra(enum ha_extra_function operation)
2644
{
2645
  switch (operation)
2646
  {
1283.60.10 by Stewart Smith
the memory management for BLOBS is completely insane. For certain types of index lookups we *must* do a copy and clear it *only* in ::reset() or ::extra(). This patch fixes up any valgrind warnings/assertions for embedded_innodb executing type_blob test.
2647
  case HA_EXTRA_FLUSH:
2648
    if (blobroot)
2649
      blobroot->free_root(MYF(0));
2650
    break;
1283.39.8 by Stewart Smith
add support for REPLACE to embedded_innodb. On duplicate key on insert if we have HA_EXTRA_WRITE_CAN_REPLACE set, then we delete the row and insert.
2651
  case HA_EXTRA_WRITE_CAN_REPLACE:
2652
    write_can_replace= true;
2653
    break;
2654
  case HA_EXTRA_WRITE_CANNOT_REPLACE:
2655
    write_can_replace= false;
2656
    break;
2657
  default:
2658
    break;
2659
  }
2660
2661
  return 0;
2662
}
2663
1283.17.11 by Stewart Smith
change data_dictionary.innodb_table_proto to data_dictionary.innodb_table_definition
2664
static int create_table_message_table()
1283.3.25 by Stewart Smith
basic creating of data_dictionary/innodb_table_proto table on startup
2665
{
2666
  ib_tbl_sch_t schema;
2667
  ib_idx_sch_t index_schema;
2668
  ib_trx_t transaction;
2669
  ib_id_t table_id;
1283.17.34 by Stewart Smith
rework error handling in create_table_message_table() for embedded_innodb to not use transaction uninitialised in teh error case of setting up the table structure for innodb.
2670
  ib_err_t err, rollback_err;
1283.19.28 by Stewart Smith
fixup error checking
2671
  ib_bool_t create_db_err;
2672
2673
  create_db_err= ib_database_create("data_dictionary");
2674
  if (create_db_err != IB_TRUE)
2675
    return -1;
2676
2677
  err= ib_table_schema_create(INNODB_TABLE_DEFINITIONS_TABLE, &schema,
2678
                              IB_TBL_COMPACT, 0);
2679
  if (err != DB_SUCCESS)
2680
    return err;
2681
2682
  err= ib_table_schema_add_col(schema, "table_name", IB_VARCHAR, IB_COL_NONE, 0,
2683
                               IB_MAX_TABLE_NAME_LEN);
2684
  if (err != DB_SUCCESS)
1283.17.34 by Stewart Smith
rework error handling in create_table_message_table() for embedded_innodb to not use transaction uninitialised in teh error case of setting up the table structure for innodb.
2685
    goto free_err;
1283.19.28 by Stewart Smith
fixup error checking
2686
2687
  err= ib_table_schema_add_col(schema, "message", IB_BLOB, IB_COL_NONE, 0, 0);
2688
  if (err != DB_SUCCESS)
1283.17.34 by Stewart Smith
rework error handling in create_table_message_table() for embedded_innodb to not use transaction uninitialised in teh error case of setting up the table structure for innodb.
2689
    goto free_err;
1283.19.28 by Stewart Smith
fixup error checking
2690
2691
  err= ib_table_schema_add_index(schema, "PRIMARY_KEY", &index_schema);
2692
  if (err != DB_SUCCESS)
1283.17.34 by Stewart Smith
rework error handling in create_table_message_table() for embedded_innodb to not use transaction uninitialised in teh error case of setting up the table structure for innodb.
2693
    goto free_err;
1283.19.28 by Stewart Smith
fixup error checking
2694
2695
  err= ib_index_schema_add_col(index_schema, "table_name", 0);
2696
  if (err != DB_SUCCESS)
1283.17.34 by Stewart Smith
rework error handling in create_table_message_table() for embedded_innodb to not use transaction uninitialised in teh error case of setting up the table structure for innodb.
2697
    goto free_err;
1283.19.28 by Stewart Smith
fixup error checking
2698
  err= ib_index_schema_set_clustered(index_schema);
2699
  if (err != DB_SUCCESS)
1283.17.34 by Stewart Smith
rework error handling in create_table_message_table() for embedded_innodb to not use transaction uninitialised in teh error case of setting up the table structure for innodb.
2700
    goto free_err;
1283.3.25 by Stewart Smith
basic creating of data_dictionary/innodb_table_proto table on startup
2701
2702
  transaction= ib_trx_begin(IB_TRX_REPEATABLE_READ);
1283.19.28 by Stewart Smith
fixup error checking
2703
  err= ib_schema_lock_exclusive(transaction);
2704
  if (err != DB_SUCCESS)
2705
    goto rollback;
2706
2707
  err= ib_table_create(transaction, schema, &table_id);
2708
  if (err != DB_SUCCESS)
2709
    goto rollback;
2710
2711
  err= ib_trx_commit(transaction);
2712
  if (err != DB_SUCCESS)
2713
    goto rollback;
1283.3.25 by Stewart Smith
basic creating of data_dictionary/innodb_table_proto table on startup
2714
2715
  ib_table_schema_delete(schema);
2716
2717
  return 0;
1283.19.28 by Stewart Smith
fixup error checking
2718
rollback:
2719
  ib_schema_unlock(transaction);
1283.17.34 by Stewart Smith
rework error handling in create_table_message_table() for embedded_innodb to not use transaction uninitialised in teh error case of setting up the table structure for innodb.
2720
  rollback_err= ib_trx_rollback(transaction);
1283.19.28 by Stewart Smith
fixup error checking
2721
  assert(rollback_err == DB_SUCCESS);
1283.17.34 by Stewart Smith
rework error handling in create_table_message_table() for embedded_innodb to not use transaction uninitialised in teh error case of setting up the table structure for innodb.
2722
free_err:
2723
  ib_table_schema_delete(schema);
1283.19.28 by Stewart Smith
fixup error checking
2724
  return err;
1283.3.25 by Stewart Smith
basic creating of data_dictionary/innodb_table_proto table on startup
2725
}
2726
1283.35.51 by Stewart Smith
add support (and tests) for innodb-checksums configuration variable to embedded_innodb
2727
static bool  innobase_use_checksums= true;
1283.35.52 by Stewart Smith
add data_home_dir configuration option to embedded_innodb
2728
static char*  innobase_data_home_dir      = NULL;
1283.35.71 by Stewart Smith
support log_group_home_dir for embedded_innodb
2729
static char*  innobase_log_group_home_dir   = NULL;
1283.35.53 by Stewart Smith
add innodb_doublewrite configuration option to embedded_innodb along with tests for explicitly disabling and enabling it.
2730
static bool innobase_use_doublewrite= true;
1283.35.54 by Stewart Smith
add innodb_io_capacity configuration option for embedded_innodb. Check that both sysvar is set and that we get the right answer from embedded_innodb
2731
static unsigned long srv_io_capacity= 200;
1283.35.56 by Stewart Smith
support innodb_fast_shutdown configuration for embedded_innodb. Currently the tests miss any ability to check what kind of shutdown was actually done... not sure how to get around that.
2732
static unsigned long innobase_fast_shutdown= 1;
1283.35.57 by Stewart Smith
add innodb_file_per_table option to embedded_innodb. Include a test to see that a file is indeed created for it.
2733
static bool srv_file_per_table= false;
1283.35.79 by Stewart Smith
add adaptive_hash_index toggle configuration option to embedded_innodb
2734
static bool innobase_adaptive_hash_index;
1283.35.81 by Stewart Smith
add innodb_adaptive_flushing config option to embedded_innodb
2735
static bool srv_adaptive_flushing;
1283.35.90 by Stewart Smith
add print_verbose_log to embedded_innodB
2736
static bool innobase_print_verbose_log;
1283.35.91 by Stewart Smith
rollback_on_timeout for embedded_innodb
2737
static bool innobase_rollback_on_timeout;
1283.35.92 by Stewart Smith
support innodb_status_file. We allow it to be switched at runtime (unlike innobase plugin) due to this being supported by libinnodb.
2738
static bool innobase_create_status_file;
1283.35.94 by Stewart Smith
add use_sys_malloc for embedded_innodb
2739
static bool srv_use_sys_malloc;
1711.1.5 by Monty Taylor
Fixed a valgrind error and some missed opt files.
2740
static char*  innobase_file_format_name   = const_cast<char *>("Barracuda");
1283.35.69 by Stewart Smith
support innodb_flush_method configuration for embedded_innodb. We don't give as clear error message as innobase currently as we just get back 'invalid option' from libinnodb, not anything more descriptive.
2741
static char*  innobase_unix_file_flush_method   = NULL;
1283.35.65 by Stewart Smith
support innodb_flush_trx_log_at_commit config option for embedded_innodb. Test tests that we set it in libinnodb, not that it actually works (as that's hard).
2742
static unsigned long srv_flush_log_at_trx_commit;
1283.35.72 by Stewart Smith
support max_dirty_pages_pct for embedded_innodb
2743
static unsigned long srv_max_buf_pool_modified_pct;
1283.35.74 by Stewart Smith
add max_purge_lag to embedded_innodb. because we should also support black magic configuration variables.
2744
static unsigned long srv_max_purge_lag;
1283.35.75 by Stewart Smith
add lru_old_blocks_pct and lru_block_access_recency configuration options to embedded_innodb. Exciting and new for Drizzle.
2745
static unsigned long innobase_lru_old_blocks_pct;
2746
static unsigned long innobase_lru_block_access_recency;
1283.35.77 by Stewart Smith
add read_io_threads to embedded_innodb configuration variables
2747
static unsigned long innobase_read_io_threads;
1283.35.78 by Stewart Smith
add write_io_threads config variable to embedded_innodb
2748
static unsigned long innobase_write_io_threads;
1283.35.83 by Stewart Smith
add innodb_autoextend_increment config option to embedded_innodb
2749
static unsigned int srv_auto_extend_increment;
1283.35.88 by Stewart Smith
make lock_wait_timeout work for embedded_innodb. A difference is that it is now global, not a Session variable. I don't think this matters to anyone (but is also a limitation of libinnodb). we don't have a 'default' test due to the fact that dtr sets it as a parameter'
2750
static unsigned long innobase_lock_wait_timeout;
1283.35.93 by Stewart Smith
add sync_spin_loops config option to embedded_innodb
2751
static unsigned long srv_n_spin_wait_rounds;
1283.35.84 by Stewart Smith
add innodb_buffer_pool_size config option to embedded_innodb
2752
static int64_t innobase_buffer_pool_size;
1283.35.76 by Stewart Smith
support innodb_open_files for embedded_innodb
2753
static long innobase_open_files;
1283.35.82 by Stewart Smith
add innodb_additional_mem_pool_size config option to embedded_innodb
2754
static long innobase_additional_mem_pool_size;
1283.35.87 by Stewart Smith
add force_recovery to embedded_innodb
2755
static long innobase_force_recovery;
1283.35.89 by Stewart Smith
add log_buffer_size config option to embedded_innodb
2756
static long innobase_log_buffer_size;
1283.13.7 by Stewart Smith
Add innodb_log_file_size and innodb_log_files_in_group to embedded_innodb. Also make their defaults *exactly* the same as the standard innobase plugin (same goes for innodb_data_file_path). This fixse an incompatibility with the log file sizes between innobase and embedded_innodb that would prevent the server being restarted with the other plugin loaded.
2757
static char  default_innodb_data_file_path[]= "ibdata1:10M:autoextend";
2758
static char* innodb_data_file_path= NULL;
2759
2760
static int64_t innodb_log_file_size;
2761
static int64_t innodb_log_files_in_group;
2762
1530.2.6 by Monty Taylor
Moved plugin::Context to module::Context.
2763
static int embedded_innodb_init(drizzled::module::Context &context)
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
2764
{
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2765
2766
  const module::option_map &vm= context.getOptions();
2767
  if (vm.count("additional-mem-pool-size"))
2768
  { 
2769
    if (innobase_additional_mem_pool_size > LONG_MAX || innobase_additional_mem_pool_size < 512*1024L)
2770
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2771
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of additional-mem-pool-size"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2772
      exit(-1);
2773
    }
2774
    innobase_additional_mem_pool_size/= 1024;
2775
    innobase_additional_mem_pool_size*= 1024;
2776
  }
2777
2778
  if (vm.count("autoextend-increment"))
2779
  { 
2780
    if (srv_auto_extend_increment > 1000L || srv_auto_extend_increment < 1L)
2781
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2782
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of autoextend-increment"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2783
      exit(-1);
2784
    }
2785
  }
2786
2787
  if (vm.count("buffer-pool-size"))
2788
  { 
2789
    if (innobase_buffer_pool_size > INT64_MAX || innobase_buffer_pool_size < 5*1024*1024L)
2790
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2791
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of buffer-pool-size"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2792
      exit(-1);
2793
    }
2794
    innobase_buffer_pool_size/= 1024*1024L;
2795
    innobase_buffer_pool_size*= 1024*1024L;
2796
  }
2797
2798
  if (vm.count("io-capacity"))
2799
  { 
2800
    if (srv_io_capacity > (unsigned long)~0L || srv_io_capacity < 100)
2801
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2802
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of io-capacity"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2803
      exit(-1);
2804
    }
2805
  }
2806
2807
  if (vm.count("fast-shutdown"))
2808
  { 
2809
    if (innobase_fast_shutdown > 2)
2810
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2811
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of fast-shutdown"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2812
      exit(-1);
2813
    }
2814
  }
2815
2816
  if (vm.count("flush-log-at-trx-commit"))
2817
  { 
2818
    if (srv_flush_log_at_trx_commit > 2)
2819
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2820
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of flush-log-at-trx-commit"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2821
      exit(-1);
2822
    }
2823
  }
2824
2825
  if (vm.count("force-recovery"))
2826
  { 
2827
    if (innobase_force_recovery > 6)
2828
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2829
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of force-recovery"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2830
      exit(-1);
2831
    }
2832
  }
2833
2834
  if (vm.count("log-file-size"))
2835
  { 
2836
    if (innodb_log_file_size > INT64_MAX || innodb_log_file_size < 1*1024*1024L)
2837
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2838
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of log-file-size"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2839
      exit(-1);
2840
    }
2841
    innodb_log_file_size/= 1024*1024L;
2842
    innodb_log_file_size*= 1024*1024L;
2843
  }
2844
2845
  if (vm.count("log-files-in-group"))
2846
  { 
2847
    if (innodb_log_files_in_group > 100 || innodb_log_files_in_group < 2)
2848
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2849
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of log-files-in-group"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2850
      exit(-1);
2851
    }
2852
  }
2853
2854
  if (vm.count("lock-wait-timeout"))
2855
  { 
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2856
    if (innobase_lock_wait_timeout > 1024*1024*1024 || innobase_lock_wait_timeout < 1)
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2857
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2858
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of lock-wait-timeout"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2859
      exit(-1);
2860
    }
2861
  }
2862
2863
  if (vm.count("log-buffer-size"))
2864
  { 
2865
    if (innobase_log_buffer_size > LONG_MAX || innobase_log_buffer_size < 256*1024L)
2866
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2867
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of log-buffer-size"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2868
      exit(-1);
2869
    }
2870
    innobase_log_buffer_size/= 1024;
2871
    innobase_log_buffer_size*= 1024;
2872
  }
2873
2874
  if (vm.count("lru-old-blocks-pct"))
2875
  { 
2876
    if (innobase_lru_old_blocks_pct > 95 || innobase_lru_old_blocks_pct < 5)
2877
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2878
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of lru-old-blocks-pct"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2879
      exit(-1);
2880
    }
2881
  }
2882
2883
  if (vm.count("lru-block-access-recency"))
2884
  { 
2885
    if (innobase_lru_block_access_recency > ULONG_MAX)
2886
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2887
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of lru-block-access-recency"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2888
      exit(-1);
2889
    }
2890
  }
2891
2892
  if (vm.count("max-dirty-pages-pct"))
2893
  { 
2894
    if (srv_max_buf_pool_modified_pct > 99)
2895
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2896
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of max-dirty-pages-pct"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2897
      exit(-1);
2898
    }
2899
  }
2900
2901
  if (vm.count("max-purge-lag"))
2902
  { 
2903
    if (srv_max_purge_lag > (unsigned long)~0L)
2904
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2905
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of max-purge-lag"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2906
      exit(-1);
2907
    }
2908
  }
2909
2910
  if (vm.count("open-files"))
2911
  { 
2912
    if (innobase_open_files > LONG_MAX || innobase_open_files < 10L)
2913
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2914
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of open-files"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2915
      exit(-1);
2916
    }
2917
  }
2918
2919
  if (vm.count("read-io-threads"))
2920
  { 
2921
    if (innobase_read_io_threads > 64 || innobase_read_io_threads < 1)
2922
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2923
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of read-io-threads"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2924
      exit(-1);
2925
    }
2926
  }
2927
2928
  if (vm.count("sync-spin-loops"))
2929
  { 
2930
    if (srv_n_spin_wait_rounds > (unsigned long)~0L)
2931
    {
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
2932
      errmsg_printf(ERRMSG_LVL_ERROR, _("Invalid value of sync_spin_loops"));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2933
      exit(-1);
2934
    }
2935
  }
2936
2937
  if (vm.count("data-home-dir"))
2938
  {
1711.1.5 by Monty Taylor
Fixed a valgrind error and some missed opt files.
2939
    innobase_data_home_dir= const_cast<char *>(vm["data-home-dir"].as<string>().c_str());
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2940
  }
2941
2942
  if (vm.count("file-format"))
2943
  {
1711.1.5 by Monty Taylor
Fixed a valgrind error and some missed opt files.
2944
    innobase_file_format_name= const_cast<char *>(vm["file-format"].as<string>().c_str());
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2945
  }
2946
2947
  if (vm.count("log-group-home-dir"))
2948
  {
1711.1.5 by Monty Taylor
Fixed a valgrind error and some missed opt files.
2949
    innobase_log_group_home_dir= const_cast<char *>(vm["log-group-home-dir"].as<string>().c_str());
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2950
  }
2951
2952
  if (vm.count("flush-method"))
2953
  {
1711.1.5 by Monty Taylor
Fixed a valgrind error and some missed opt files.
2954
    innobase_unix_file_flush_method= const_cast<char *>(vm["flush-method"].as<string>().c_str());
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2955
  }
2956
2957
  if (vm.count("data-file-path"))
2958
  {
1711.1.5 by Monty Taylor
Fixed a valgrind error and some missed opt files.
2959
    innodb_data_file_path= const_cast<char *>(vm["data-file-path"].as<string>().c_str());
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
2960
  }
2961
1283.23.3 by Stewart Smith
check return code from ib_init().
2962
  ib_err_t err;
1283.3.9 by Stewart Smith
call basic embedded innodb init functions (ib_init() and ib_startup()). Also shutdown functions.
2963
1283.23.3 by Stewart Smith
check return code from ib_init().
2964
  err= ib_init();
2965
  if (err != DB_SUCCESS)
1283.13.10 by Stewart Smith
check all return codes from ib_cfg in plugin init for embedded innodb. Embedded InnoDB 1.0.6 has warn_unused_result for all of these.
2966
    goto innodb_error;
1283.3.9 by Stewart Smith
call basic embedded innodb init functions (ib_init() and ib_startup()). Also shutdown functions.
2967
1283.35.52 by Stewart Smith
add data_home_dir configuration option to embedded_innodb
2968
  if (innobase_data_home_dir)
2969
  {
2970
    err= ib_cfg_set_text("data_home_dir", innobase_data_home_dir);
2971
    if (err != DB_SUCCESS)
2972
      goto innodb_error;
2973
  }
2974
1283.35.71 by Stewart Smith
support log_group_home_dir for embedded_innodb
2975
  if (innobase_log_group_home_dir)
2976
  {
2977
    err= ib_cfg_set_text("log_group_home_dir", innobase_log_group_home_dir);
2978
    if (err != DB_SUCCESS)
2979
      goto innodb_error;
2980
  }
2981
1283.13.7 by Stewart Smith
Add innodb_log_file_size and innodb_log_files_in_group to embedded_innodb. Also make their defaults *exactly* the same as the standard innobase plugin (same goes for innodb_data_file_path). This fixse an incompatibility with the log file sizes between innobase and embedded_innodb that would prevent the server being restarted with the other plugin loaded.
2982
  if (innodb_data_file_path == NULL)
2983
    innodb_data_file_path= default_innodb_data_file_path;
2984
1283.35.90 by Stewart Smith
add print_verbose_log to embedded_innodB
2985
  if (innobase_print_verbose_log)
2986
    err= ib_cfg_set_bool_on("print_verbose_log");
2987
  else
2988
    err= ib_cfg_set_bool_off("print_verbose_log");
2989
2990
  if (err != DB_SUCCESS)
2991
    goto innodb_error;
2992
1283.35.91 by Stewart Smith
rollback_on_timeout for embedded_innodb
2993
  if (innobase_rollback_on_timeout)
2994
    err= ib_cfg_set_bool_on("rollback_on_timeout");
2995
  else
2996
    err= ib_cfg_set_bool_off("rollback_on_timeout");
2997
2998
  if (err != DB_SUCCESS)
2999
    goto innodb_error;
3000
1283.35.53 by Stewart Smith
add innodb_doublewrite configuration option to embedded_innodb along with tests for explicitly disabling and enabling it.
3001
  if (innobase_use_doublewrite)
3002
    err= ib_cfg_set_bool_on("doublewrite");
3003
  else
3004
    err= ib_cfg_set_bool_off("doublewrite");
3005
3006
  if (err != DB_SUCCESS)
3007
    goto innodb_error;
3008
1283.35.79 by Stewart Smith
add adaptive_hash_index toggle configuration option to embedded_innodb
3009
  if (innobase_adaptive_hash_index)
3010
    err= ib_cfg_set_bool_on("adaptive_hash_index");
3011
  else
3012
    err= ib_cfg_set_bool_off("adaptive_hash_index");
3013
3014
  if (err != DB_SUCCESS)
3015
    goto innodb_error;
3016
1283.35.81 by Stewart Smith
add innodb_adaptive_flushing config option to embedded_innodb
3017
  if (srv_adaptive_flushing)
3018
    err= ib_cfg_set_bool_on("adaptive_flushing");
3019
  else
3020
    err= ib_cfg_set_bool_off("adaptive_flushing");
3021
3022
  if (err != DB_SUCCESS)
3023
    goto innodb_error;
3024
1283.35.82 by Stewart Smith
add innodb_additional_mem_pool_size config option to embedded_innodb
3025
  err= ib_cfg_set_int("additional_mem_pool_size", innobase_additional_mem_pool_size);
3026
  if (err != DB_SUCCESS)
3027
    goto innodb_error;
3028
1283.35.83 by Stewart Smith
add innodb_autoextend_increment config option to embedded_innodb
3029
  err= ib_cfg_set_int("autoextend_increment", srv_auto_extend_increment);
3030
  if (err != DB_SUCCESS)
3031
    goto innodb_error;
3032
1283.35.84 by Stewart Smith
add innodb_buffer_pool_size config option to embedded_innodb
3033
  err= ib_cfg_set_int("buffer_pool_size", innobase_buffer_pool_size);
3034
  if (err != DB_SUCCESS)
3035
    goto innodb_error;
3036
1283.35.54 by Stewart Smith
add innodb_io_capacity configuration option for embedded_innodb. Check that both sysvar is set and that we get the right answer from embedded_innodb
3037
  err= ib_cfg_set_int("io_capacity", srv_io_capacity);
3038
  if (err != DB_SUCCESS)
3039
    goto innodb_error;
3040
1283.35.57 by Stewart Smith
add innodb_file_per_table option to embedded_innodb. Include a test to see that a file is indeed created for it.
3041
  if (srv_file_per_table)
3042
    err= ib_cfg_set_bool_on("file_per_table");
3043
  else
3044
    err= ib_cfg_set_bool_off("file_per_table");
3045
3046
  if (err != DB_SUCCESS)
3047
    goto innodb_error;
3048
1283.35.65 by Stewart Smith
support innodb_flush_trx_log_at_commit config option for embedded_innodb. Test tests that we set it in libinnodb, not that it actually works (as that's hard).
3049
  err= ib_cfg_set_int("flush_log_at_trx_commit", srv_flush_log_at_trx_commit);
3050
  if (err != DB_SUCCESS)
3051
    goto innodb_error;
3052
1283.35.69 by Stewart Smith
support innodb_flush_method configuration for embedded_innodb. We don't give as clear error message as innobase currently as we just get back 'invalid option' from libinnodb, not anything more descriptive.
3053
  if (innobase_unix_file_flush_method)
3054
  {
3055
    err= ib_cfg_set_text("flush_method", innobase_unix_file_flush_method);
3056
    if (err != DB_SUCCESS)
3057
      goto innodb_error;
3058
  }
3059
1283.35.87 by Stewart Smith
add force_recovery to embedded_innodb
3060
  err= ib_cfg_set_int("force_recovery", innobase_force_recovery);
3061
  if (err != DB_SUCCESS)
3062
    goto innodb_error;
3063
1283.13.10 by Stewart Smith
check all return codes from ib_cfg in plugin init for embedded innodb. Embedded InnoDB 1.0.6 has warn_unused_result for all of these.
3064
  err= ib_cfg_set_text("data_file_path", innodb_data_file_path);
3065
  if (err != DB_SUCCESS)
3066
    goto innodb_error;
3067
3068
  err= ib_cfg_set_int("log_file_size", innodb_log_file_size);
3069
  if (err != DB_SUCCESS)
3070
    goto innodb_error;
3071
1283.35.89 by Stewart Smith
add log_buffer_size config option to embedded_innodb
3072
  err= ib_cfg_set_int("log_buffer_size", innobase_log_buffer_size);
3073
  if (err != DB_SUCCESS)
3074
    goto innodb_error;
3075
1283.13.10 by Stewart Smith
check all return codes from ib_cfg in plugin init for embedded innodb. Embedded InnoDB 1.0.6 has warn_unused_result for all of these.
3076
  err= ib_cfg_set_int("log_files_in_group", innodb_log_files_in_group);
3077
  if (err != DB_SUCCESS)
3078
    goto innodb_error;
1283.13.7 by Stewart Smith
Add innodb_log_file_size and innodb_log_files_in_group to embedded_innodb. Also make their defaults *exactly* the same as the standard innobase plugin (same goes for innodb_data_file_path). This fixse an incompatibility with the log file sizes between innobase and embedded_innodb that would prevent the server being restarted with the other plugin loaded.
3079
1283.35.51 by Stewart Smith
add support (and tests) for innodb-checksums configuration variable to embedded_innodb
3080
  err= ib_cfg_set_int("checksums", innobase_use_checksums);
3081
  if (err != DB_SUCCESS)
3082
    goto innodb_error;
3083
1283.35.88 by Stewart Smith
make lock_wait_timeout work for embedded_innodb. A difference is that it is now global, not a Session variable. I don't think this matters to anyone (but is also a limitation of libinnodb). we don't have a 'default' test due to the fact that dtr sets it as a parameter'
3084
  err= ib_cfg_set_int("lock_wait_timeout", innobase_lock_wait_timeout);
3085
  if (err != DB_SUCCESS)
3086
    goto innodb_error;
3087
1283.35.72 by Stewart Smith
support max_dirty_pages_pct for embedded_innodb
3088
  err= ib_cfg_set_int("max_dirty_pages_pct", srv_max_buf_pool_modified_pct);
3089
  if (err != DB_SUCCESS)
3090
    goto innodb_error;
3091
1283.35.74 by Stewart Smith
add max_purge_lag to embedded_innodb. because we should also support black magic configuration variables.
3092
  err= ib_cfg_set_int("max_purge_lag", srv_max_purge_lag);
3093
  if (err != DB_SUCCESS)
3094
    goto innodb_error;
3095
1283.35.76 by Stewart Smith
support innodb_open_files for embedded_innodb
3096
  err= ib_cfg_set_int("open_files", innobase_open_files);
3097
  if (err != DB_SUCCESS)
3098
    goto innodb_error;
3099
1283.35.77 by Stewart Smith
add read_io_threads to embedded_innodb configuration variables
3100
  err= ib_cfg_set_int("read_io_threads", innobase_read_io_threads);
3101
  if (err != DB_SUCCESS)
3102
    goto innodb_error;
3103
1283.35.78 by Stewart Smith
add write_io_threads config variable to embedded_innodb
3104
  err= ib_cfg_set_int("write_io_threads", innobase_write_io_threads);
3105
  if (err != DB_SUCCESS)
3106
    goto innodb_error;
3107
1283.35.93 by Stewart Smith
add sync_spin_loops config option to embedded_innodb
3108
  err= ib_cfg_set_int("sync_spin_loops", srv_n_spin_wait_rounds);
3109
  if (err != DB_SUCCESS)
3110
    goto innodb_error;
3111
1283.35.94 by Stewart Smith
add use_sys_malloc for embedded_innodb
3112
  if (srv_use_sys_malloc)
3113
    err= ib_cfg_set_bool_on("use_sys_malloc");
3114
  else
3115
    err= ib_cfg_set_bool_off("use_sys_malloc");
3116
3117
  if (err != DB_SUCCESS)
3118
    goto innodb_error;
3119
1283.52.3 by Stewart Smith
remove mem leak as well as properly show the default innodb_file_format.
3120
  err= ib_startup(innobase_file_format_name);
1283.3.9 by Stewart Smith
call basic embedded innodb init functions (ib_init() and ib_startup()). Also shutdown functions.
3121
  if (err != DB_SUCCESS)
1283.13.10 by Stewart Smith
check all return codes from ib_cfg in plugin init for embedded innodb. Embedded InnoDB 1.0.6 has warn_unused_result for all of these.
3122
    goto innodb_error;
1283.3.9 by Stewart Smith
call basic embedded innodb init functions (ib_init() and ib_startup()). Also shutdown functions.
3123
1283.17.11 by Stewart Smith
change data_dictionary.innodb_table_proto to data_dictionary.innodb_table_definition
3124
  create_table_message_table();
1283.3.25 by Stewart Smith
basic creating of data_dictionary/innodb_table_proto table on startup
3125
1283.3.11 by Stewart Smith
Name the EMBEDDED_INNODB plugin as InnoDB and add two variables (data_file_path and lock_wait_timeout) to make test-run.pl happy.
3126
  embedded_innodb_engine= new EmbeddedInnoDBEngine("InnoDB");
1283.4.16 by Stewart Smith
fix up plugin initialisation and add doRenameTable empty function as it's now pure virtual
3127
  context.add(embedded_innodb_engine);
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
3128
1283.7.15 by Stewart Smith
merge plugin init with trunk: plugin::Context instead of Registry
3129
  libinnodb_version_func_initialize(context);
1283.10.24 by Stewart Smith
merge trunk
3130
  libinnodb_datadict_dump_func_initialize(context);
1283.31.11 by Stewart Smith
merge trunk
3131
  config_table_function_initialize(context);
1283.32.9 by Stewart Smith
merge trunk
3132
  status_table_function_initialize(context);
1283.3.5 by Stewart Smith
add LIBINNODB_VERSION() function
3133
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
3134
  return 0;
1283.13.10 by Stewart Smith
check all return codes from ib_cfg in plugin init for embedded innodb. Embedded InnoDB 1.0.6 has warn_unused_result for all of these.
3135
innodb_error:
3136
  fprintf(stderr, _("Error starting Embedded InnoDB %d (%s)\n"),
3137
          err, ib_strerror(err));
3138
  return -1;
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
3139
}
3140
1283.23.10 by Stewart Smith
merge libinnodb init/de-init with trunk
3141
3142
EmbeddedInnoDBEngine::~EmbeddedInnoDBEngine()
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
3143
{
1283.23.10 by Stewart Smith
merge libinnodb init/de-init with trunk
3144
  ib_err_t err;
1283.35.56 by Stewart Smith
support innodb_fast_shutdown configuration for embedded_innodb. Currently the tests miss any ability to check what kind of shutdown was actually done... not sure how to get around that.
3145
  ib_shutdown_t shutdown_flag= IB_SHUTDOWN_NORMAL;
3146
3147
  if (innobase_fast_shutdown == 1)
3148
    shutdown_flag= IB_SHUTDOWN_NO_IBUFMERGE_PURGE;
3149
  else if (innobase_fast_shutdown == 2)
3150
    shutdown_flag= IB_SHUTDOWN_NO_BUFPOOL_FLUSH;
3151
3152
  err= ib_shutdown(shutdown_flag);
1283.3.9 by Stewart Smith
call basic embedded innodb init functions (ib_init() and ib_startup()). Also shutdown functions.
3153
3154
  if (err != DB_SUCCESS)
3155
  {
1283.23.10 by Stewart Smith
merge libinnodb init/de-init with trunk
3156
    fprintf(stderr,"Error %d shutting down Embedded InnoDB!\n", err);
1283.3.9 by Stewart Smith
call basic embedded innodb init functions (ib_init() and ib_startup()). Also shutdown functions.
3157
  }
1666.4.19 by Monty Taylor
Free strdup'd option strings.
3158
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
3159
}
3160
1283.35.64 by Stewart Smith
add file_format configuration option to embedded_innodb. Also add a simple test for changing it
3161
static char innodb_file_format_name_storage[100];
3162
3163
static int innodb_file_format_name_validate(Session*, drizzle_sys_var*,
3164
                                            void *save,
3165
                                            drizzle_value *value)
3166
{
3167
  ib_err_t err;
3168
  char buff[100];
3169
  int len= sizeof(buff);
3170
  const char *format= value->val_str(value, buff, &len);
3171
3172
  *static_cast<const char**>(save)= NULL;
3173
3174
  if (format == NULL)
3175
    return 1;
3176
3177
  err= ib_cfg_set_text("file_format", format);
3178
3179
  if (err == DB_SUCCESS)
3180
  {
3181
    strncpy(innodb_file_format_name_storage, format, sizeof(innodb_file_format_name_storage));;
1283.52.2 by Stewart Smith
fix setting of \0 for innodb_file_format. compiler warnings FTW:
3182
    innodb_file_format_name_storage[sizeof(innodb_file_format_name_storage)-1]= 0;
1283.35.64 by Stewart Smith
add file_format configuration option to embedded_innodb. Also add a simple test for changing it
3183
3184
    *static_cast<const char**>(save)= innodb_file_format_name_storage;
3185
    return 0;
3186
  }
3187
  else
3188
    return 1;
3189
}
3190
3191
static void innodb_file_format_name_update(Session*, drizzle_sys_var*,
3192
                                           void *var_ptr,
3193
                                           const void *save)
3194
3195
{
3196
  const char* format;
3197
3198
  assert(var_ptr != NULL);
3199
  assert(save != NULL);
3200
3201
  format= *static_cast<const char*const*>(save);
3202
3203
  /* Format is already set in validate */
1598.2.6 by Stewart Smith
In config_file_format test, we were getting overlap in strncpy() call. Simply
3204
  memmove(innodb_file_format_name_storage, format, sizeof(innodb_file_format_name_storage));;
3205
  innodb_file_format_name_storage[sizeof(innodb_file_format_name_storage)-1]= 0;
1283.35.64 by Stewart Smith
add file_format configuration option to embedded_innodb. Also add a simple test for changing it
3206
3207
  *static_cast<const char**>(var_ptr)= innodb_file_format_name_storage;
3208
}
3209
1283.35.75 by Stewart Smith
add lru_old_blocks_pct and lru_block_access_recency configuration options to embedded_innodb. Exciting and new for Drizzle.
3210
static void innodb_lru_old_blocks_pct_update(Session*, drizzle_sys_var*,
3211
                                             void *,
3212
                                             const void *save)
3213
3214
{
3215
  unsigned long pct;
3216
3217
  pct= *static_cast<const unsigned long*>(save);
3218
3219
  ib_err_t err= ib_cfg_set_int("lru_old_blocks_pct", pct);
3220
  if (err == DB_SUCCESS)
3221
    innobase_lru_old_blocks_pct= pct;
3222
}
3223
3224
static void innodb_lru_block_access_recency_update(Session*, drizzle_sys_var*,
3225
                                                   void *,
3226
                                                   const void *save)
3227
3228
{
3229
  unsigned long ms;
3230
3231
  ms= *static_cast<const unsigned long*>(save);
3232
3233
  ib_err_t err= ib_cfg_set_int("lru_block_access_recency", ms);
3234
3235
  if (err == DB_SUCCESS)
3236
    innobase_lru_block_access_recency= ms;
3237
}
3238
1283.35.92 by Stewart Smith
support innodb_status_file. We allow it to be switched at runtime (unlike innobase plugin) due to this being supported by libinnodb.
3239
static void innodb_status_file_update(Session*, drizzle_sys_var*,
3240
                                      void *,
3241
                                      const void *save)
3242
3243
{
3244
  bool status_file_enabled;
3245
  ib_err_t err;
3246
3247
  status_file_enabled= *static_cast<const bool*>(save);
3248
3249
3250
  if (status_file_enabled)
3251
    err= ib_cfg_set_bool_on("status_file");
3252
  else
3253
    err= ib_cfg_set_bool_off("status_file");
3254
3255
  if (err == DB_SUCCESS)
3256
    innobase_create_status_file= status_file_enabled;
3257
}
3258
1283.35.79 by Stewart Smith
add adaptive_hash_index toggle configuration option to embedded_innodb
3259
static DRIZZLE_SYSVAR_BOOL(adaptive_hash_index, innobase_adaptive_hash_index,
3260
  PLUGIN_VAR_NOCMDARG,
3261
  "Enable InnoDB adaptive hash index (enabled by default).  ",
3262
  NULL, NULL, true);
1283.35.75 by Stewart Smith
add lru_old_blocks_pct and lru_block_access_recency configuration options to embedded_innodb. Exciting and new for Drizzle.
3263
1283.35.81 by Stewart Smith
add innodb_adaptive_flushing config option to embedded_innodb
3264
static DRIZZLE_SYSVAR_BOOL(adaptive_flushing, srv_adaptive_flushing,
3265
  PLUGIN_VAR_NOCMDARG,
3266
  "Attempt flushing dirty pages to avoid IO bursts at checkpoints.",
3267
  NULL, NULL, true);
3268
1283.35.82 by Stewart Smith
add innodb_additional_mem_pool_size config option to embedded_innodb
3269
static DRIZZLE_SYSVAR_LONG(additional_mem_pool_size, innobase_additional_mem_pool_size,
3270
  PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
3271
  "Size of a memory pool InnoDB uses to store data dictionary information and other internal data structures.",
3272
  NULL, NULL, 8*1024*1024L, 512*1024L, LONG_MAX, 1024);
3273
1283.35.83 by Stewart Smith
add innodb_autoextend_increment config option to embedded_innodb
3274
static DRIZZLE_SYSVAR_UINT(autoextend_increment, srv_auto_extend_increment,
3275
  PLUGIN_VAR_RQCMDARG,
3276
  "Data file autoextend increment in megabytes",
3277
  NULL, NULL, 8L, 1L, 1000L, 0);
3278
1283.35.84 by Stewart Smith
add innodb_buffer_pool_size config option to embedded_innodb
3279
static DRIZZLE_SYSVAR_LONGLONG(buffer_pool_size, innobase_buffer_pool_size,
3280
  PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
3281
  "The size of the memory buffer InnoDB uses to cache data and indexes of its tables.",
3282
  NULL, NULL, 128*1024*1024L, 5*1024*1024L, INT64_MAX, 1024*1024L);
3283
1283.35.51 by Stewart Smith
add support (and tests) for innodb-checksums configuration variable to embedded_innodb
3284
static DRIZZLE_SYSVAR_BOOL(checksums, innobase_use_checksums,
3285
  PLUGIN_VAR_NOCMDARG | PLUGIN_VAR_READONLY,
3286
  "Enable InnoDB checksums validation (enabled by default). "
3287
  "Disable with --skip-innodb-checksums.",
3288
  NULL, NULL, true);
3289
1283.35.52 by Stewart Smith
add data_home_dir configuration option to embedded_innodb
3290
static DRIZZLE_SYSVAR_STR(data_home_dir, innobase_data_home_dir,
3291
  PLUGIN_VAR_READONLY,
3292
  "The common part for InnoDB table spaces.",
3293
  NULL, NULL, NULL);
3294
1283.35.53 by Stewart Smith
add innodb_doublewrite configuration option to embedded_innodb along with tests for explicitly disabling and enabling it.
3295
static DRIZZLE_SYSVAR_BOOL(doublewrite, innobase_use_doublewrite,
3296
  PLUGIN_VAR_NOCMDARG | PLUGIN_VAR_READONLY,
3297
  "Enable InnoDB doublewrite buffer (enabled by default). "
3298
  "Disable with --skip-innodb-doublewrite.",
3299
  NULL, NULL, true);
3300
1283.35.54 by Stewart Smith
add innodb_io_capacity configuration option for embedded_innodb. Check that both sysvar is set and that we get the right answer from embedded_innodb
3301
static DRIZZLE_SYSVAR_ULONG(io_capacity, srv_io_capacity,
3302
  PLUGIN_VAR_RQCMDARG,
3303
  "Number of IOPs the server can do. Tunes the background IO rate",
3304
  NULL, NULL, 200, 100, ~0L, 0);
3305
1283.35.56 by Stewart Smith
support innodb_fast_shutdown configuration for embedded_innodb. Currently the tests miss any ability to check what kind of shutdown was actually done... not sure how to get around that.
3306
static DRIZZLE_SYSVAR_ULONG(fast_shutdown, innobase_fast_shutdown,
3307
  PLUGIN_VAR_OPCMDARG,
3308
  "Speeds up the shutdown process of the InnoDB storage engine. Possible "
3309
  "values are 0, 1 (faster)"
3310
  " or 2 (fastest - crash-like)"
3311
  ".",
3312
  NULL, NULL, 1, 0, 2, 0);
3313
1283.35.57 by Stewart Smith
add innodb_file_per_table option to embedded_innodb. Include a test to see that a file is indeed created for it.
3314
static DRIZZLE_SYSVAR_BOOL(file_per_table, srv_file_per_table,
3315
  PLUGIN_VAR_NOCMDARG,
3316
  "Stores each InnoDB table to an .ibd file in the database dir.",
3317
  NULL, NULL, false);
3318
1283.35.64 by Stewart Smith
add file_format configuration option to embedded_innodb. Also add a simple test for changing it
3319
static DRIZZLE_SYSVAR_STR(file_format, innobase_file_format_name,
3320
  PLUGIN_VAR_RQCMDARG,
3321
  "File format to use for new tables in .ibd files.",
3322
  innodb_file_format_name_validate,
1283.52.3 by Stewart Smith
remove mem leak as well as properly show the default innodb_file_format.
3323
  innodb_file_format_name_update, "Barracuda");
1283.35.64 by Stewart Smith
add file_format configuration option to embedded_innodb. Also add a simple test for changing it
3324
1283.35.65 by Stewart Smith
support innodb_flush_trx_log_at_commit config option for embedded_innodb. Test tests that we set it in libinnodb, not that it actually works (as that's hard).
3325
static DRIZZLE_SYSVAR_ULONG(flush_log_at_trx_commit, srv_flush_log_at_trx_commit,
3326
  PLUGIN_VAR_OPCMDARG,
3327
  "Set to 0 (write and flush once per second),"
3328
  " 1 (write and flush at each commit)"
3329
  " or 2 (write at commit, flush once per second).",
3330
  NULL, NULL, 1, 0, 2, 0);
3331
1283.35.69 by Stewart Smith
support innodb_flush_method configuration for embedded_innodb. We don't give as clear error message as innobase currently as we just get back 'invalid option' from libinnodb, not anything more descriptive.
3332
static DRIZZLE_SYSVAR_STR(flush_method, innobase_unix_file_flush_method,
3333
  PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
3334
  "With which method to flush data.", NULL, NULL, NULL);
3335
1283.35.87 by Stewart Smith
add force_recovery to embedded_innodb
3336
static DRIZZLE_SYSVAR_LONG(force_recovery, innobase_force_recovery,
3337
  PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
3338
  "Helps to save your data in case the disk image of the database becomes corrupt.",
3339
  NULL, NULL, 0, 0, 6, 0);
3340
1283.3.11 by Stewart Smith
Name the EMBEDDED_INNODB plugin as InnoDB and add two variables (data_file_path and lock_wait_timeout) to make test-run.pl happy.
3341
static DRIZZLE_SYSVAR_STR(data_file_path, innodb_data_file_path,
3342
  PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
1283.13.7 by Stewart Smith
Add innodb_log_file_size and innodb_log_files_in_group to embedded_innodb. Also make their defaults *exactly* the same as the standard innobase plugin (same goes for innodb_data_file_path). This fixse an incompatibility with the log file sizes between innobase and embedded_innodb that would prevent the server being restarted with the other plugin loaded.
3343
  "Path to individual files and their sizes.",
1283.3.11 by Stewart Smith
Name the EMBEDDED_INNODB plugin as InnoDB and add two variables (data_file_path and lock_wait_timeout) to make test-run.pl happy.
3344
  NULL, NULL, NULL);
1283.13.7 by Stewart Smith
Add innodb_log_file_size and innodb_log_files_in_group to embedded_innodb. Also make their defaults *exactly* the same as the standard innobase plugin (same goes for innodb_data_file_path). This fixse an incompatibility with the log file sizes between innobase and embedded_innodb that would prevent the server being restarted with the other plugin loaded.
3345
1283.35.71 by Stewart Smith
support log_group_home_dir for embedded_innodb
3346
static DRIZZLE_SYSVAR_STR(log_group_home_dir, innobase_log_group_home_dir,
3347
  PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
3348
  "Path to InnoDB log files.", NULL, NULL, NULL);
3349
1283.13.7 by Stewart Smith
Add innodb_log_file_size and innodb_log_files_in_group to embedded_innodb. Also make their defaults *exactly* the same as the standard innobase plugin (same goes for innodb_data_file_path). This fixse an incompatibility with the log file sizes between innobase and embedded_innodb that would prevent the server being restarted with the other plugin loaded.
3350
static DRIZZLE_SYSVAR_LONGLONG(log_file_size, innodb_log_file_size,
3351
  PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
3352
  "Size of each log file in a log group.",
1645.1.2 by Monty Taylor
Changed embedded innodb's default log file size to be the same as normal innodb so that the test suite doesn't die horribly.
3353
  NULL, NULL, 20*1024*1024L, 1*1024*1024L, INT64_MAX, 1024*1024L);
1283.13.7 by Stewart Smith
Add innodb_log_file_size and innodb_log_files_in_group to embedded_innodb. Also make their defaults *exactly* the same as the standard innobase plugin (same goes for innodb_data_file_path). This fixse an incompatibility with the log file sizes between innobase and embedded_innodb that would prevent the server being restarted with the other plugin loaded.
3354
3355
static DRIZZLE_SYSVAR_LONGLONG(log_files_in_group, innodb_log_files_in_group,
3356
  PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
3357
  "Number of log files in the log group. InnoDB writes to the files in a circular fashion. Value 3 is recommended here.",
3358
  NULL, NULL, 2, 2, 100, 0);
3359
1283.35.88 by Stewart Smith
make lock_wait_timeout work for embedded_innodb. A difference is that it is now global, not a Session variable. I don't think this matters to anyone (but is also a limitation of libinnodb). we don't have a 'default' test due to the fact that dtr sets it as a parameter'
3360
static DRIZZLE_SYSVAR_ULONG(lock_wait_timeout, innobase_lock_wait_timeout,
3361
  PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
3362
  "Timeout in seconds an InnoDB transaction may wait for a lock before being rolled back. Values above 100000000 disable the timeout.",
1684.7.6 by Vijay Samuel
Merge trunk and changed default value of lock_wait_timeout from 50 to 5. Thanks Stewart!
3363
  NULL, NULL, 5, 1, 1024 * 1024 * 1024, 0);
1283.3.11 by Stewart Smith
Name the EMBEDDED_INNODB plugin as InnoDB and add two variables (data_file_path and lock_wait_timeout) to make test-run.pl happy.
3364
1283.35.89 by Stewart Smith
add log_buffer_size config option to embedded_innodb
3365
static DRIZZLE_SYSVAR_LONG(log_buffer_size, innobase_log_buffer_size,
3366
  PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
3367
  "The size of the buffer which InnoDB uses to write log to the log files on disk.",
3368
  NULL, NULL, 8*1024*1024L, 256*1024L, LONG_MAX, 1024);
3369
1283.35.75 by Stewart Smith
add lru_old_blocks_pct and lru_block_access_recency configuration options to embedded_innodb. Exciting and new for Drizzle.
3370
static DRIZZLE_SYSVAR_ULONG(lru_old_blocks_pct, innobase_lru_old_blocks_pct,
3371
  PLUGIN_VAR_RQCMDARG,
3372
  "Sets the point in the LRU list from where all pages are classified as "
3373
  "old (Advanced users)",
3374
  NULL,
3375
  innodb_lru_old_blocks_pct_update, 37, 5, 95, 0);
3376
3377
static DRIZZLE_SYSVAR_ULONG(lru_block_access_recency, innobase_lru_block_access_recency,
3378
  PLUGIN_VAR_RQCMDARG,
3379
  "Milliseconds between accesses to a block at which it is made young. "
3380
  "0=disabled (Advanced users)",
3381
  NULL,
3382
  innodb_lru_block_access_recency_update, 0, 0, ULONG_MAX, 0);
3383
3384
1283.35.72 by Stewart Smith
support max_dirty_pages_pct for embedded_innodb
3385
static DRIZZLE_SYSVAR_ULONG(max_dirty_pages_pct, srv_max_buf_pool_modified_pct,
3386
  PLUGIN_VAR_RQCMDARG,
3387
  "Percentage of dirty pages allowed in bufferpool.",
3388
  NULL, NULL, 75, 0, 99, 0);
3389
1283.35.74 by Stewart Smith
add max_purge_lag to embedded_innodb. because we should also support black magic configuration variables.
3390
static DRIZZLE_SYSVAR_ULONG(max_purge_lag, srv_max_purge_lag,
3391
  PLUGIN_VAR_RQCMDARG,
3392
  "Desired maximum length of the purge queue (0 = no limit)",
3393
  NULL, NULL, 0, 0, ~0L, 0);
3394
1283.35.91 by Stewart Smith
rollback_on_timeout for embedded_innodb
3395
static DRIZZLE_SYSVAR_BOOL(rollback_on_timeout, innobase_rollback_on_timeout,
3396
  PLUGIN_VAR_OPCMDARG | PLUGIN_VAR_READONLY,
3397
  "Roll back the complete transaction on lock wait timeout, for 4.x compatibility (disabled by default)",
3398
  NULL, NULL, false);
3399
1283.35.76 by Stewart Smith
support innodb_open_files for embedded_innodb
3400
static DRIZZLE_SYSVAR_LONG(open_files, innobase_open_files,
3401
  PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
3402
  "How many files at the maximum InnoDB keeps open at the same time.",
3403
  NULL, NULL, 300L, 10L, LONG_MAX, 0);
3404
1283.35.77 by Stewart Smith
add read_io_threads to embedded_innodb configuration variables
3405
static DRIZZLE_SYSVAR_ULONG(read_io_threads, innobase_read_io_threads,
3406
  PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
3407
  "Number of background read I/O threads in InnoDB.",
3408
  NULL, NULL, 4, 1, 64, 0);
3409
1283.35.78 by Stewart Smith
add write_io_threads config variable to embedded_innodb
3410
static DRIZZLE_SYSVAR_ULONG(write_io_threads, innobase_write_io_threads,
3411
  PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
3412
  "Number of background write I/O threads in InnoDB.",
3413
  NULL, NULL, 4, 1, 64, 0);
3414
1283.35.90 by Stewart Smith
add print_verbose_log to embedded_innodB
3415
static DRIZZLE_SYSVAR_BOOL(print_verbose_log, innobase_print_verbose_log,
3416
  PLUGIN_VAR_NOCMDARG,
3417
  "Disable if you want to reduce the number of messages written to the log (default: enabled).",
3418
  NULL, NULL, true);
3419
1283.35.92 by Stewart Smith
support innodb_status_file. We allow it to be switched at runtime (unlike innobase plugin) due to this being supported by libinnodb.
3420
static DRIZZLE_SYSVAR_BOOL(status_file, innobase_create_status_file,
3421
  PLUGIN_VAR_OPCMDARG,
3422
  "Enable SHOW INNODB STATUS output in the log",
3423
  NULL, innodb_status_file_update, false);
3424
1283.35.93 by Stewart Smith
add sync_spin_loops config option to embedded_innodb
3425
static DRIZZLE_SYSVAR_ULONG(sync_spin_loops, srv_n_spin_wait_rounds,
3426
  PLUGIN_VAR_RQCMDARG,
3427
  "Count of spin-loop rounds in InnoDB mutexes (30 by default)",
3428
  NULL, NULL, 30L, 0L, ~0L, 0);
3429
1283.35.94 by Stewart Smith
add use_sys_malloc for embedded_innodb
3430
static DRIZZLE_SYSVAR_BOOL(use_sys_malloc, srv_use_sys_malloc,
3431
  PLUGIN_VAR_NOCMDARG | PLUGIN_VAR_READONLY,
3432
  "Use OS memory allocator instead of InnoDB's internal memory allocator",
3433
  NULL, NULL, true);
3434
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
3435
static void init_options(drizzled::module::option_context &context)
3436
{
3437
  context("adaptive-hash-index", 
1749.2.1 by Vijay Samuel
Merge fix to standardize commandline boolean options for embedded_innodb
3438
          po::value<bool>(&innobase_adaptive_hash_index)->default_value(true)->zero_tokens()->multitoken(),
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
3439
          N_("Enable InnoDB adaptive hash index (enabled by default)."));
3440
  context("adaptive-flushing",
1749.2.1 by Vijay Samuel
Merge fix to standardize commandline boolean options for embedded_innodb
3441
          po::value<bool>(&srv_adaptive_flushing)->default_value(true)->zero_tokens()->multitoken(),
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
3442
          N_("Attempt flushing dirty pages to avoid IO bursts at checkpoints."));
3443
  context("additional-mem-pool-size",
3444
          po::value<long>(&innobase_additional_mem_pool_size)->default_value(8*1024*1024L),
3445
          N_("Size of a memory pool InnoDB uses to store data dictionary information and other internal data structures."));
3446
  context("autoextend-increment",
3447
          po::value<unsigned int>(&srv_auto_extend_increment)->default_value(8L),
3448
          N_("Data file autoextend increment in megabytes"));
3449
  context("buffer-pool-size",
3450
          po::value<int64_t>(&innobase_buffer_pool_size)->default_value(128*1024*1024L),
3451
          N_("The size of the memory buffer InnoDB uses to cache data and indexes of its tables."));
3452
  context("data-home-dir",
3453
          po::value<string>(),
3454
          N_("The common part for InnoDB table spaces."));
3455
  context("checksums",
1749.2.1 by Vijay Samuel
Merge fix to standardize commandline boolean options for embedded_innodb
3456
          po::value<bool>(&innobase_use_checksums)->default_value(true)->zero_tokens()->multitoken(),
3457
          N_("Enable InnoDB checksums validation (enabled by default)."));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
3458
  context("doublewrite",
1749.2.1 by Vijay Samuel
Merge fix to standardize commandline boolean options for embedded_innodb
3459
          po::value<bool>(&innobase_use_doublewrite)->default_value(true)->zero_tokens()->multitoken(),
3460
          N_("Enable InnoDB doublewrite buffer (enabled by default)."));
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
3461
  context("io-capacity",
3462
          po::value<unsigned long>(&srv_io_capacity)->default_value(200),
3463
          N_("Number of IOPs the server can do. Tunes the background IO rate"));
3464
  context("fast-shutdown",
3465
          po::value<unsigned long>(&innobase_fast_shutdown)->default_value(1),
3466
          N_("Speeds up the shutdown process of the InnoDB storage engine. Possible values are 0, 1 (faster) or 2 (fastest - crash-like)."));
3467
  context("file-per-table", 
1749.2.1 by Vijay Samuel
Merge fix to standardize commandline boolean options for embedded_innodb
3468
          po::value<bool>(&srv_file_per_table)->default_value(false)->zero_tokens()->multitoken(),
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
3469
          N_("Stores each InnoDB table to an .ibd file in the database dir."));
3470
  context("file-format",
3471
          po::value<string>(),
3472
          N_("File format to use for new tables in .ibd files."));
3473
  context("flush-log-at-trx-commit",
3474
          po::value<unsigned long>(&srv_flush_log_at_trx_commit)->default_value(1),
3475
          N_("Set to 0 (write and flush once per second),1 (write and flush at each commit) or 2 (write at commit, flush once per second)."));
3476
  context("flush-method",
3477
          po::value<string>(),
3478
          N_("With which method to flush data."));
3479
  context("force-recovery",
3480
          po::value<long>(&innobase_force_recovery)->default_value(0),
3481
          N_("Helps to save your data in case the disk image of the database becomes corrupt."));        
3482
  context("data-file-path",
3483
          po::value<string>(),
3484
          N_("Path to individual files and their sizes."));
3485
  context("log-group-home-dir",
3486
          po::value<string>(),
3487
          N_("Path to individual files and their sizes."));
3488
  context("log-group-home-dir",
3489
          po::value<string>(),
3490
          N_("Path to InnoDB log files."));
3491
  context("log-file-size",
1684.7.4 by Vijay Samuel
Merge corrections for printing errors, removal of --innodb.lock-wait-timeout from test-run.pl
3492
          po::value<int64_t>(&innodb_log_file_size)->default_value(20*1024*1024L),
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
3493
          N_("Size of each log file in a log group."));
3494
  context("innodb-log-files-in-group",
3495
          po::value<int64_t>(&innodb_log_files_in_group)->default_value(2),
3496
          N_("Number of log files in the log group. InnoDB writes to the files in a circular fashion. Value 3 is recommended here."));
3497
  context("lock-wait-timeout",
1684.7.6 by Vijay Samuel
Merge trunk and changed default value of lock_wait_timeout from 50 to 5. Thanks Stewart!
3498
          po::value<unsigned long>(&innobase_lock_wait_timeout)->default_value(5),
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
3499
          N_("Timeout in seconds an InnoDB transaction may wait for a lock before being rolled back. Values above 100000000 disable the timeout."));
3500
  context("log-buffer-size",
3501
        po::value<long>(&innobase_log_buffer_size)->default_value(8*1024*1024L),
3502
        N_("The size of the buffer which InnoDB uses to write log to the log files on disk."));
3503
  context("lru-old-blocks-pct",
3504
          po::value<unsigned long>(&innobase_lru_old_blocks_pct)->default_value(37),
3505
          N_("Sets the point in the LRU list from where all pages are classified as old (Advanced users)"));
3506
  context("lru-block-access-recency",
3507
          po::value<unsigned long>(&innobase_lru_block_access_recency)->default_value(0),
3508
          N_("Milliseconds between accesses to a block at which it is made young. 0=disabled (Advanced users)"));
3509
  context("max-dirty-pages-pct",
3510
          po::value<unsigned long>(&srv_max_buf_pool_modified_pct)->default_value(75),
3511
          N_("Percentage of dirty pages allowed in bufferpool."));
3512
  context("max-purge-lag",
3513
          po::value<unsigned long>(&srv_max_purge_lag)->default_value(0),
3514
          N_("Desired maximum length of the purge queue (0 = no limit)"));
3515
  context("rollback-on-timeout",
1749.2.1 by Vijay Samuel
Merge fix to standardize commandline boolean options for embedded_innodb
3516
          po::value<bool>(&innobase_rollback_on_timeout)->default_value(false)->zero_tokens()->multitoken(),
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
3517
          N_("Roll back the complete transaction on lock wait timeout, for 4.x compatibility (disabled by default)"));
3518
  context("open-files",
3519
          po::value<long>(&innobase_open_files)->default_value(300),
3520
          N_("How many files at the maximum InnoDB keeps open at the same time."));
3521
  context("read-io-threads",
3522
          po::value<unsigned long>(&innobase_read_io_threads)->default_value(4),
3523
          N_("Number of background read I/O threads in InnoDB."));
3524
  context("write-io-threads",
3525
          po::value<unsigned long>(&innobase_write_io_threads)->default_value(4),
3526
          N_("Number of background write I/O threads in InnoDB."));
3527
  context("print-verbose-log",
1749.2.1 by Vijay Samuel
Merge fix to standardize commandline boolean options for embedded_innodb
3528
          po::value<bool>(&innobase_print_verbose_log)->default_value(true)->zero_tokens()->multitoken(),
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
3529
          N_("Disable if you want to reduce the number of messages written to the log (default: enabled)."));
3530
  context("status-file",
1749.2.1 by Vijay Samuel
Merge fix to standardize commandline boolean options for embedded_innodb
3531
          po::value<bool>(&innobase_create_status_file)->default_value(false)->zero_tokens()->multitoken(),
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
3532
          N_("Enable SHOW INNODB STATUS output in the log"));
3533
  context("sync-spin-loops",
3534
          po::value<unsigned long>(&srv_n_spin_wait_rounds)->default_value(30L),
3535
          N_("Count of spin-loop rounds in InnoDB mutexes (30 by default)"));
3536
  context("use-sys-malloc",
1749.2.1 by Vijay Samuel
Merge fix to standardize commandline boolean options for embedded_innodb
3537
          po::value<bool>(&srv_use_sys_malloc)->default_value(true)->zero_tokens()->multitoken(),
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
3538
          N_("Use OS memory allocator instead of InnoDB's internal memory allocator"));
3539
}
3540
1283.3.11 by Stewart Smith
Name the EMBEDDED_INNODB plugin as InnoDB and add two variables (data_file_path and lock_wait_timeout) to make test-run.pl happy.
3541
static drizzle_sys_var* innobase_system_variables[]= {
1283.35.79 by Stewart Smith
add adaptive_hash_index toggle configuration option to embedded_innodb
3542
  DRIZZLE_SYSVAR(adaptive_hash_index),
1283.35.81 by Stewart Smith
add innodb_adaptive_flushing config option to embedded_innodb
3543
  DRIZZLE_SYSVAR(adaptive_flushing),
1283.35.82 by Stewart Smith
add innodb_additional_mem_pool_size config option to embedded_innodb
3544
  DRIZZLE_SYSVAR(additional_mem_pool_size),
1283.35.83 by Stewart Smith
add innodb_autoextend_increment config option to embedded_innodb
3545
  DRIZZLE_SYSVAR(autoextend_increment),
1283.35.84 by Stewart Smith
add innodb_buffer_pool_size config option to embedded_innodb
3546
  DRIZZLE_SYSVAR(buffer_pool_size),
1283.35.51 by Stewart Smith
add support (and tests) for innodb-checksums configuration variable to embedded_innodb
3547
  DRIZZLE_SYSVAR(checksums),
1283.35.52 by Stewart Smith
add data_home_dir configuration option to embedded_innodb
3548
  DRIZZLE_SYSVAR(data_home_dir),
1283.35.53 by Stewart Smith
add innodb_doublewrite configuration option to embedded_innodb along with tests for explicitly disabling and enabling it.
3549
  DRIZZLE_SYSVAR(doublewrite),
1283.35.54 by Stewart Smith
add innodb_io_capacity configuration option for embedded_innodb. Check that both sysvar is set and that we get the right answer from embedded_innodb
3550
  DRIZZLE_SYSVAR(io_capacity),
1283.35.56 by Stewart Smith
support innodb_fast_shutdown configuration for embedded_innodb. Currently the tests miss any ability to check what kind of shutdown was actually done... not sure how to get around that.
3551
  DRIZZLE_SYSVAR(fast_shutdown),
1283.35.57 by Stewart Smith
add innodb_file_per_table option to embedded_innodb. Include a test to see that a file is indeed created for it.
3552
  DRIZZLE_SYSVAR(file_per_table),
1283.35.64 by Stewart Smith
add file_format configuration option to embedded_innodb. Also add a simple test for changing it
3553
  DRIZZLE_SYSVAR(file_format),
1283.35.65 by Stewart Smith
support innodb_flush_trx_log_at_commit config option for embedded_innodb. Test tests that we set it in libinnodb, not that it actually works (as that's hard).
3554
  DRIZZLE_SYSVAR(flush_log_at_trx_commit),
1283.35.69 by Stewart Smith
support innodb_flush_method configuration for embedded_innodb. We don't give as clear error message as innobase currently as we just get back 'invalid option' from libinnodb, not anything more descriptive.
3555
  DRIZZLE_SYSVAR(flush_method),
1283.35.87 by Stewart Smith
add force_recovery to embedded_innodb
3556
  DRIZZLE_SYSVAR(force_recovery),
1283.35.71 by Stewart Smith
support log_group_home_dir for embedded_innodb
3557
  DRIZZLE_SYSVAR(log_group_home_dir),
1283.3.11 by Stewart Smith
Name the EMBEDDED_INNODB plugin as InnoDB and add two variables (data_file_path and lock_wait_timeout) to make test-run.pl happy.
3558
  DRIZZLE_SYSVAR(data_file_path),
3559
  DRIZZLE_SYSVAR(lock_wait_timeout),
1283.13.7 by Stewart Smith
Add innodb_log_file_size and innodb_log_files_in_group to embedded_innodb. Also make their defaults *exactly* the same as the standard innobase plugin (same goes for innodb_data_file_path). This fixse an incompatibility with the log file sizes between innobase and embedded_innodb that would prevent the server being restarted with the other plugin loaded.
3560
  DRIZZLE_SYSVAR(log_file_size),
3561
  DRIZZLE_SYSVAR(log_files_in_group),
1283.35.89 by Stewart Smith
add log_buffer_size config option to embedded_innodb
3562
  DRIZZLE_SYSVAR(log_buffer_size),
1283.35.75 by Stewart Smith
add lru_old_blocks_pct and lru_block_access_recency configuration options to embedded_innodb. Exciting and new for Drizzle.
3563
  DRIZZLE_SYSVAR(lru_old_blocks_pct),
3564
  DRIZZLE_SYSVAR(lru_block_access_recency),
1283.35.72 by Stewart Smith
support max_dirty_pages_pct for embedded_innodb
3565
  DRIZZLE_SYSVAR(max_dirty_pages_pct),
1283.35.74 by Stewart Smith
add max_purge_lag to embedded_innodb. because we should also support black magic configuration variables.
3566
  DRIZZLE_SYSVAR(max_purge_lag),
1283.35.76 by Stewart Smith
support innodb_open_files for embedded_innodb
3567
  DRIZZLE_SYSVAR(open_files),
1283.35.77 by Stewart Smith
add read_io_threads to embedded_innodb configuration variables
3568
  DRIZZLE_SYSVAR(read_io_threads),
1283.35.91 by Stewart Smith
rollback_on_timeout for embedded_innodb
3569
  DRIZZLE_SYSVAR(rollback_on_timeout),
1283.35.78 by Stewart Smith
add write_io_threads config variable to embedded_innodb
3570
  DRIZZLE_SYSVAR(write_io_threads),
1283.35.90 by Stewart Smith
add print_verbose_log to embedded_innodB
3571
  DRIZZLE_SYSVAR(print_verbose_log),
1283.35.92 by Stewart Smith
support innodb_status_file. We allow it to be switched at runtime (unlike innobase plugin) due to this being supported by libinnodb.
3572
  DRIZZLE_SYSVAR(status_file),
1283.35.93 by Stewart Smith
add sync_spin_loops config option to embedded_innodb
3573
  DRIZZLE_SYSVAR(sync_spin_loops),
1283.35.94 by Stewart Smith
add use_sys_malloc for embedded_innodb
3574
  DRIZZLE_SYSVAR(use_sys_malloc),
1283.3.11 by Stewart Smith
Name the EMBEDDED_INNODB plugin as InnoDB and add two variables (data_file_path and lock_wait_timeout) to make test-run.pl happy.
3575
  NULL
3576
};
3577
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
3578
DRIZZLE_DECLARE_PLUGIN
3579
{
3580
  DRIZZLE_VERSION_ID,
1283.3.11 by Stewart Smith
Name the EMBEDDED_INNODB plugin as InnoDB and add two variables (data_file_path and lock_wait_timeout) to make test-run.pl happy.
3581
  "INNODB",
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
3582
  "1.0",
3583
  "Stewart Smith",
1283.4.8 by Stewart Smith
fix description of embedded innodB
3584
  "Transactional Storage Engine using the Embedded InnoDB Library",
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
3585
  PLUGIN_LICENSE_GPL,
3586
  embedded_innodb_init,     /* Plugin Init */
1283.3.11 by Stewart Smith
Name the EMBEDDED_INNODB plugin as InnoDB and add two variables (data_file_path and lock_wait_timeout) to make test-run.pl happy.
3587
  innobase_system_variables, /* system variables */
1684.7.1 by Vijay Samuel
Merge re factored command line for embedded innodb
3588
  init_options                /* config options   */
1283.3.1 by Stewart Smith
Skeleton embedded_innodb plugin. Does nothing.
3589
}
3590
DRIZZLE_DECLARE_PLUGIN_END;