~drizzle-trunk/drizzle/development

575.1.5 by Monty Taylor
Moved stuff to handlerton.cc
1
/* -*- mode: c++; c-basic-offset: 2; indent-tabs-mode: nil; -*-
2
 *  vim:expandtab:shiftwidth=2:tabstop=2:smarttab:
3
 *
1999.6.1 by kalebral at gmail
update Copyright strings to a more common format to help with creating the master debian copyright file
4
 *  Copyright (C) 2008 Sun Microsystems, Inc.
575.1.5 by Monty Taylor
Moved stuff to handlerton.cc
5
 *
6
 *  This program is free software; you can redistribute it and/or modify
7
 *  it under the terms of the GNU General Public License as published by
8
 *  the Free Software Foundation; version 2 of the License.
9
 *
10
 *  This program is distributed in the hope that it will be useful,
11
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
12
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
 *  GNU General Public License for more details.
14
 *
15
 *  You should have received a copy of the GNU General Public License
16
 *  along with this program; if not, write to the Free Software
17
 *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
18
 */
1 by brian
clean slate
19
20
/**
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
21
  @file Cursor.cc
1 by brian
clean slate
22
23
  Handler-calling-functions
24
*/
25
2173.2.1 by Monty Taylor
Fixes incorrect usage of include
26
#include <config.h>
1241.9.1 by Monty Taylor
Removed global.h. Fixed all the headers.
27
#include <fcntl.h>
2173.2.1 by Monty Taylor
Fixes incorrect usage of include
28
#include <drizzled/error.h>
29
#include <drizzled/field/epoch.h>
30
#include <drizzled/gettext.h>
31
#include <drizzled/internal/my_sys.h>
32
#include <drizzled/item/empty_string.h>
33
#include <drizzled/item/int.h>
34
#include <drizzled/lock.h>
35
#include <drizzled/message/table.h>
36
#include <drizzled/optimizer/cost_vector.h>
37
#include <drizzled/plugin/client.h>
38
#include <drizzled/plugin/event_observer.h>
39
#include <drizzled/plugin/storage_engine.h>
40
#include <drizzled/probes.h>
41
#include <drizzled/session.h>
42
#include <drizzled/sql_base.h>
43
#include <drizzled/sql_parse.h>
44
#include <drizzled/transaction_services.h>
2198.1.1 by Olaf van der Spek
Remove unnecessary alter* includes
45
#include <drizzled/key.h>
572.1.4 by Monty Taylor
Removed a bunch of unusued tests and defines from autoconf.
46
919.2.14 by Monty Taylor
Use math.h instead of cmath... one of these days...
47
using namespace std;
1280.1.10 by Monty Taylor
Put everything in drizzled into drizzled namespace.
48
2221.7.5 by Olaf van der Spek
Refactor
49
namespace drizzled {
1 by brian
clean slate
50
51
/****************************************************************************
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
52
** General Cursor functions
1 by brian
clean slate
53
****************************************************************************/
1280.1.10 by Monty Taylor
Put everything in drizzled into drizzled namespace.
54
Cursor::Cursor(plugin::StorageEngine &engine_arg,
1869.1.4 by Brian Aker
TableShare is no longer in the house (i.e. we no longer directly have a copy
55
               Table &arg)
1869.1.5 by Brian Aker
getTable()
56
  : table(arg),
1869.1.7 by Brian Aker
Cleanup of caller to ha_open().
57
    engine(engine_arg),
58
    estimation_rows_to_insert(0),
1492 by Brian Aker
Dead code removal.
59
    ref(0),
1241.9.57 by Monty Taylor
Oy. Bigger change than I normally like - but this stuff is all intertwined.
60
    key_used_on_scan(MAX_KEY), active_index(MAX_KEY),
1280.1.10 by Monty Taylor
Put everything in drizzled into drizzled namespace.
61
    ref_length(sizeof(internal::my_off_t)),
1241.9.57 by Monty Taylor
Oy. Bigger change than I normally like - but this stuff is all intertwined.
62
    inited(NONE),
1491.1.8 by Jay Pipes
Removes HEAP-specific Cursor::implicit_emptied member. Was unused.
63
    locked(false),
1241.9.57 by Monty Taylor
Oy. Bigger change than I normally like - but this stuff is all intertwined.
64
    next_insert_id(0), insert_id_for_cur_row(0)
65
{ }
66
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
67
Cursor::~Cursor(void)
1022.2.29 by Monty Taylor
Fixed some no-inline warnings.
68
{
69
  assert(locked == false);
70
  /* TODO: assert(inited == NONE); */
71
}
72
73
1626.3.3 by Brian Aker
Additional checks on path.
74
/*
75
 * @note this only used in
76
 * optimizer::QuickRangeSelect::init_ror_merged_scan(bool reuse_handler) as
77
 * of the writing of this comment. -Brian
78
 */
1253.1.3 by Monty Taylor
MEM_ROOT == memory::Root
79
Cursor *Cursor::clone(memory::Root *mem_root)
1 by brian
clean slate
80
{
1869.1.5 by Brian Aker
getTable()
81
  Cursor *new_handler= getTable()->getMutableShare()->db_type()->getCursor(*getTable());
1185 by Brian Aker
Merge Engine changes.
82
1 by brian
clean slate
83
  /*
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
84
    Allocate Cursor->ref here because otherwise ha_open will allocate it
575.2.2 by Monty Taylor
Moved vio stuff into libdrizzle.
85
    on this->table->mem_root and we will not be able to reclaim that memory
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
86
    when the clone Cursor object is destroyed.
1 by brian
clean slate
87
  */
1485 by Brian Aker
Updates to confine memroot
88
  if (!(new_handler->ref= (unsigned char*) mem_root->alloc_root(ALIGN_SIZE(ref_length)*2)))
1 by brian
clean slate
89
    return NULL;
1578.2.9 by Brian Aker
Simplify ha_open.
90
2087.4.2 by Brian Aker
Modify TableIdentifier to fit with the rest of the identifiers.
91
  identifier::Table identifier(getTable()->getShare()->getSchemaName(),
1869.1.5 by Brian Aker
getTable()
92
                             getTable()->getShare()->getTableName(),
93
                             getTable()->getShare()->getType());
1626.3.1 by Brian Aker
Adding in TableIdentifier for ha_open; (first pass)
94
95
  if (new_handler && !new_handler->ha_open(identifier,
1869.1.5 by Brian Aker
getTable()
96
                                           getTable()->getDBStat(),
1 by brian
clean slate
97
                                           HA_OPEN_IGNORE_IF_LOCKED))
98
    return new_handler;
99
  return NULL;
100
}
101
1483 by Brian Aker
Small change to move over call to cursor API.
102
/*
103
  DESCRIPTION
104
    given a buffer with a key value, and a map of keyparts
105
    that are present in this value, returns the length of the value
106
*/
107
uint32_t Cursor::calculate_key_len(uint32_t key_position, key_part_map keypart_map_arg)
108
{
109
  /* works only with key prefixes */
110
  assert(((keypart_map_arg + 1) & keypart_map_arg) == 0);
111
1869.1.5 by Brian Aker
getTable()
112
  const KeyPartInfo *key_part_found= getTable()->getShare()->getKeyInfo(key_position).key_part;
113
  const KeyPartInfo *end_key_part_found= key_part_found + getTable()->getShare()->getKeyInfo(key_position).key_parts;
1483 by Brian Aker
Small change to move over call to cursor API.
114
  uint32_t length= 0;
115
116
  while (key_part_found < end_key_part_found && keypart_map_arg)
117
  {
118
    length+= key_part_found->store_length;
119
    keypart_map_arg >>= 1;
120
    key_part_found++;
121
  }
122
  return length;
123
}
124
1491.1.6 by Jay Pipes
Cursor::ha_index_init() -> Cursor::startIndexScan(). Cursor::ha_index_end() -> Cursor::endIndexScan()
125
int Cursor::startIndexScan(uint32_t idx, bool sorted)
575.1.4 by Monty Taylor
Moved implementation of some methods into handler.cc from handler.h.
126
{
127
  int result;
1046.1.9 by Brian Aker
Remove caller that wasn't correctly locking, and reverted code to 5.1
128
  assert(inited == NONE);
1491.1.6 by Jay Pipes
Cursor::ha_index_init() -> Cursor::startIndexScan(). Cursor::ha_index_end() -> Cursor::endIndexScan()
129
  if (!(result= doStartIndexScan(idx, sorted)))
575.1.4 by Monty Taylor
Moved implementation of some methods into handler.cc from handler.h.
130
    inited=INDEX;
131
  end_range= NULL;
1046.1.9 by Brian Aker
Remove caller that wasn't correctly locking, and reverted code to 5.1
132
  return result;
575.1.4 by Monty Taylor
Moved implementation of some methods into handler.cc from handler.h.
133
}
134
1491.1.6 by Jay Pipes
Cursor::ha_index_init() -> Cursor::startIndexScan(). Cursor::ha_index_end() -> Cursor::endIndexScan()
135
int Cursor::endIndexScan()
575.1.4 by Monty Taylor
Moved implementation of some methods into handler.cc from handler.h.
136
{
137
  assert(inited==INDEX);
138
  inited=NONE;
139
  end_range= NULL;
1491.1.6 by Jay Pipes
Cursor::ha_index_init() -> Cursor::startIndexScan(). Cursor::ha_index_end() -> Cursor::endIndexScan()
140
  return(doEndIndexScan());
575.1.4 by Monty Taylor
Moved implementation of some methods into handler.cc from handler.h.
141
}
142
1491.1.10 by Jay Pipes
ha_rnd_init -> startTableScan, rnd_init -> doStartTableScan, ha_rnd_end -> endTableScan, rnd_end -> doEndTableScan
143
int Cursor::startTableScan(bool scan)
575.1.4 by Monty Taylor
Moved implementation of some methods into handler.cc from handler.h.
144
{
145
  int result;
146
  assert(inited==NONE || (inited==RND && scan));
1491.1.10 by Jay Pipes
ha_rnd_init -> startTableScan, rnd_init -> doStartTableScan, ha_rnd_end -> endTableScan, rnd_end -> doEndTableScan
147
  inited= (result= doStartTableScan(scan)) ? NONE: RND;
1046.1.9 by Brian Aker
Remove caller that wasn't correctly locking, and reverted code to 5.1
148
149
  return result;
575.1.4 by Monty Taylor
Moved implementation of some methods into handler.cc from handler.h.
150
}
151
1491.1.10 by Jay Pipes
ha_rnd_init -> startTableScan, rnd_init -> doStartTableScan, ha_rnd_end -> endTableScan, rnd_end -> doEndTableScan
152
int Cursor::endTableScan()
575.1.4 by Monty Taylor
Moved implementation of some methods into handler.cc from handler.h.
153
{
154
  assert(inited==RND);
155
  inited=NONE;
1491.1.10 by Jay Pipes
ha_rnd_init -> startTableScan, rnd_init -> doStartTableScan, ha_rnd_end -> endTableScan, rnd_end -> doEndTableScan
156
  return(doEndTableScan());
575.1.4 by Monty Taylor
Moved implementation of some methods into handler.cc from handler.h.
157
}
158
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
159
int Cursor::ha_index_or_rnd_end()
575.1.4 by Monty Taylor
Moved implementation of some methods into handler.cc from handler.h.
160
{
1491.1.10 by Jay Pipes
ha_rnd_init -> startTableScan, rnd_init -> doStartTableScan, ha_rnd_end -> endTableScan, rnd_end -> doEndTableScan
161
  return inited == INDEX ? endIndexScan() : inited == RND ? endTableScan() : 0;
575.1.4 by Monty Taylor
Moved implementation of some methods into handler.cc from handler.h.
162
}
163
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
164
void Cursor::ha_start_bulk_insert(ha_rows rows)
575.1.4 by Monty Taylor
Moved implementation of some methods into handler.cc from handler.h.
165
{
166
  estimation_rows_to_insert= rows;
167
  start_bulk_insert(rows);
168
}
169
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
170
int Cursor::ha_end_bulk_insert()
575.1.4 by Monty Taylor
Moved implementation of some methods into handler.cc from handler.h.
171
{
172
  estimation_rows_to_insert= 0;
173
  return end_bulk_insert();
174
}
175
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
176
const key_map *Cursor::keys_to_use_for_scanning()
575.1.4 by Monty Taylor
Moved implementation of some methods into handler.cc from handler.h.
177
{
178
  return &key_map_empty;
179
}
180
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
181
bool Cursor::has_transactions()
575.1.4 by Monty Taylor
Moved implementation of some methods into handler.cc from handler.h.
182
{
1869.1.5 by Brian Aker
getTable()
183
  return (getTable()->getShare()->db_type()->check_flag(HTON_BIT_DOES_TRANSACTIONS));
575.1.4 by Monty Taylor
Moved implementation of some methods into handler.cc from handler.h.
184
}
1 by brian
clean slate
185
1561.3.12 by Joe Daly
add missing header file, and change ha_statistic_increment from ulong to uint64_t
186
void Cursor::ha_statistic_increment(uint64_t system_status_var::*offset) const
1 by brian
clean slate
187
{
1869.1.5 by Brian Aker
getTable()
188
  (getTable()->in_use->status_var.*offset)++;
1 by brian
clean slate
189
}
190
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
191
void **Cursor::ha_data(Session *session) const
1 by brian
clean slate
192
{
1869.1.3 by Brian Aker
Engine now as a referene.
193
  return session->getEngineData(getEngine());
1 by brian
clean slate
194
}
195
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
196
bool Cursor::is_fatal_error(int error, uint32_t flags)
575.1.4 by Monty Taylor
Moved implementation of some methods into handler.cc from handler.h.
197
{
198
  if (!error ||
199
      ((flags & HA_CHECK_DUP_KEY) &&
200
       (error == HA_ERR_FOUND_DUPP_KEY ||
201
        error == HA_ERR_FOUND_DUPP_UNIQUE)))
202
    return false;
203
  return true;
204
}
205
575.1.5 by Monty Taylor
Moved stuff to handlerton.cc
206
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
207
ha_rows Cursor::records() { return stats.records; }
1320.1.18 by Brian Aker
Overhaul of SHOW TABLE STATUS.
208
uint64_t Cursor::tableSize() { return stats.index_file_length + stats.data_file_length; }
1869.1.5 by Brian Aker
getTable()
209
uint64_t Cursor::rowSize() { return getTable()->getRecordLength() + getTable()->sizeFields(); }
575.1.5 by Monty Taylor
Moved stuff to handlerton.cc
210
2087.4.2 by Brian Aker
Modify TableIdentifier to fit with the rest of the identifiers.
211
int Cursor::doOpen(const identifier::Table &identifier, int mode, uint32_t test_if_locked)
1626.3.3 by Brian Aker
Additional checks on path.
212
{
213
  return open(identifier.getPath().c_str(), mode, test_if_locked);
214
}
215
1 by brian
clean slate
216
/**
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
217
  Open database-Cursor.
1 by brian
clean slate
218
219
  Try O_RDONLY if cannot open as O_RDWR
220
  Don't wait for locks if not HA_OPEN_WAIT_IF_LOCKED is set
221
*/
2087.4.2 by Brian Aker
Modify TableIdentifier to fit with the rest of the identifiers.
222
int Cursor::ha_open(const identifier::Table &identifier,
1749.3.9 by Brian Aker
Remove table name from ha_open (we modified this a while ago to just use
223
                    int mode,
1626.3.1 by Brian Aker
Adding in TableIdentifier for ha_open; (first pass)
224
                    int test_if_locked)
1 by brian
clean slate
225
{
226
  int error;
227
1626.3.3 by Brian Aker
Additional checks on path.
228
  if ((error= doOpen(identifier, mode, test_if_locked)))
1 by brian
clean slate
229
  {
230
    if ((error == EACCES || error == EROFS) && mode == O_RDWR &&
1869.1.5 by Brian Aker
getTable()
231
        (getTable()->db_stat & HA_TRY_READ_ONLY))
1 by brian
clean slate
232
    {
1869.1.5 by Brian Aker
getTable()
233
      getTable()->db_stat|=HA_READ_ONLY;
1626.3.3 by Brian Aker
Additional checks on path.
234
      error= doOpen(identifier, O_RDONLY,test_if_locked);
1 by brian
clean slate
235
    }
236
  }
237
  if (error)
238
  {
1241.9.57 by Monty Taylor
Oy. Bigger change than I normally like - but this stuff is all intertwined.
239
    errno= error;                            /* Safeguard */
1 by brian
clean slate
240
  }
241
  else
242
  {
1869.1.5 by Brian Aker
getTable()
243
    if (getTable()->getShare()->db_options_in_use & HA_OPTION_READ_ONLY_DATA)
244
      getTable()->db_stat|=HA_READ_ONLY;
1 by brian
clean slate
245
    (void) extra(HA_EXTRA_NO_READCHECK);	// Not needed in SQL
246
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
247
    /* ref is already allocated for us if we're called from Cursor::clone() */
1869.1.5 by Brian Aker
getTable()
248
    if (!ref && !(ref= (unsigned char*) getTable()->alloc_root(ALIGN_SIZE(ref_length)*2)))
1 by brian
clean slate
249
    {
250
      close();
251
      error=HA_ERR_OUT_OF_MEM;
252
    }
253
    else
254
      dup_ref=ref+ALIGN_SIZE(ref_length);
255
  }
1046.1.9 by Brian Aker
Remove caller that wasn't correctly locking, and reverted code to 5.1
256
  return error;
1 by brian
clean slate
257
}
258
259
/**
260
  Read first row (only) from a table.
261
262
  This is never called for InnoDB tables, as these table types
263
  has the HA_STATS_RECORDS_IS_EXACT set.
264
*/
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
265
int Cursor::read_first_row(unsigned char * buf, uint32_t primary_key)
1 by brian
clean slate
266
{
2170.5.1 by Olaf van der Spek
Remove register keyword
267
  int error;
1 by brian
clean slate
268
1273.16.8 by Brian Aker
Remove typedef.
269
  ha_statistic_increment(&system_status_var::ha_read_first_count);
1 by brian
clean slate
270
271
  /*
272
    If there is very few deleted rows in the table, find the first row by
273
    scanning the table.
2172.3.22 by Brian Aker
This patch adds safe_delete(). All of these locations in the code should be
274
    @todo remove the test for HA_READ_ORDER
1 by brian
clean slate
275
  */
276
  if (stats.deleted < 10 || primary_key >= MAX_KEY ||
1869.1.5 by Brian Aker
getTable()
277
      !(getTable()->index_flags(primary_key) & HA_READ_ORDER))
1 by brian
clean slate
278
  {
2049.2.1 by Stewart Smith
doStartTableScan() result not checked.
279
    error= startTableScan(1);
280
    if (error == 0)
281
    {
282
      while ((error= rnd_next(buf)) == HA_ERR_RECORD_DELETED) ;
283
      (void) endTableScan();
284
    }
1 by brian
clean slate
285
  }
286
  else
287
  {
288
    /* Find the first row through the primary key */
2049.2.5 by Stewart Smith
check return value of Cursor::startIndexScan in read_first_row
289
    error= startIndexScan(primary_key, 0);
290
    if (error == 0)
291
    {
292
      error=index_first(buf);
293
      (void) endIndexScan();
294
    }
1 by brian
clean slate
295
  }
1046.1.9 by Brian Aker
Remove caller that wasn't correctly locking, and reverted code to 5.1
296
  return error;
1 by brian
clean slate
297
}
298
299
/**
300
  Generate the next auto-increment number based on increment and offset.
301
  computes the lowest number
302
  - strictly greater than "nr"
303
  - of the form: auto_increment_offset + N * auto_increment_increment
304
305
  In most cases increment= offset= 1, in which case we get:
306
  @verbatim 1,2,3,4,5,... @endverbatim
307
    If increment=10 and offset=5 and previous number is 1, we get:
308
  @verbatim 1,5,15,25,35,... @endverbatim
309
*/
310
inline uint64_t
1878.3.2 by Monty Taylor
Split out show_type into its own header and made sys_var work through
311
compute_next_insert_id(uint64_t nr, drizzle_system_variables *variables)
1 by brian
clean slate
312
{
313
  if (variables->auto_increment_increment == 1)
314
    return (nr+1); // optimization of the formula below
315
  nr= (((nr+ variables->auto_increment_increment -
316
         variables->auto_increment_offset)) /
317
       (uint64_t) variables->auto_increment_increment);
318
  return (nr* (uint64_t) variables->auto_increment_increment +
319
          variables->auto_increment_offset);
320
}
321
322
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
323
void Cursor::adjust_next_insert_id_after_explicit_value(uint64_t nr)
1 by brian
clean slate
324
{
325
  /*
520.1.21 by Brian Aker
THD -> Session rename
326
    If we have set Session::next_insert_id previously and plan to insert an
1 by brian
clean slate
327
    explicitely-specified value larger than this, we need to increase
520.1.21 by Brian Aker
THD -> Session rename
328
    Session::next_insert_id to be greater than the explicit value.
1 by brian
clean slate
329
  */
330
  if ((next_insert_id > 0) && (nr >= next_insert_id))
1869.1.5 by Brian Aker
getTable()
331
    set_next_insert_id(compute_next_insert_id(nr, &getTable()->in_use->variables));
1 by brian
clean slate
332
}
333
334
335
/**
336
  Compute a previous insert id
337
338
  Computes the largest number X:
339
  - smaller than or equal to "nr"
340
  - of the form: auto_increment_offset + N * auto_increment_increment
341
    where N>=0.
342
343
  @param nr            Number to "round down"
344
  @param variables     variables struct containing auto_increment_increment and
345
                       auto_increment_offset
346
347
  @return
348
    The number X if it exists, "nr" otherwise.
349
*/
350
inline uint64_t
1878.3.2 by Monty Taylor
Split out show_type into its own header and made sys_var work through
351
prev_insert_id(uint64_t nr, drizzle_system_variables *variables)
1 by brian
clean slate
352
{
353
  if (unlikely(nr < variables->auto_increment_offset))
354
  {
355
    /*
356
      There's nothing good we can do here. That is a pathological case, where
357
      the offset is larger than the column's max possible value, i.e. not even
358
      the first sequence value may be inserted. User will receive warning.
359
    */
360
    return nr;
361
  }
362
  if (variables->auto_increment_increment == 1)
363
    return nr; // optimization of the formula below
364
  nr= (((nr - variables->auto_increment_offset)) /
365
       (uint64_t) variables->auto_increment_increment);
366
  return (nr * (uint64_t) variables->auto_increment_increment +
367
          variables->auto_increment_offset);
368
}
369
370
371
/**
372
  Update the auto_increment field if necessary.
373
374
  Updates columns with type NEXT_NUMBER if:
375
1055.2.2 by Jay Pipes
Cleanup of style, indentation, and documentation of Table class members. Removed 5 or 6 dead Table member variables.
376
  - If column value is set to NULL (in which case auto_increment_field_not_null is false)
1 by brian
clean slate
377
  - If column is set to 0 and (sql_mode & MODE_NO_AUTO_VALUE_ON_ZERO) is not
378
    set. In the future we will only set NEXT_NUMBER fields if one sets them
379
    to NULL (or they are not included in the insert list).
380
381
    In those cases, we check if the currently reserved interval still has
382
    values we have not used. If yes, we pick the smallest one and use it.
383
    Otherwise:
384
385
  - If a list of intervals has been provided to the statement via SET
386
    INSERT_ID or via an Intvar_log_event (in a replication slave), we pick the
387
    first unused interval from this list, consider it as reserved.
388
389
  - Otherwise we set the column for the first row to the value
390
    next_insert_id(get_auto_increment(column))) which is usually
391
    max-used-column-value+1.
392
    We call get_auto_increment() for the first row in a multi-row
393
    statement. get_auto_increment() will tell us the interval of values it
394
    reserved for us.
395
396
  - In both cases, for the following rows we use those reserved values without
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
397
    calling the Cursor again (we just progress in the interval, computing
1 by brian
clean slate
398
    each new value from the previous one). Until we have exhausted them, then
399
    we either take the next provided interval or call get_auto_increment()
400
    again to reserve a new interval.
401
402
  - In both cases, the reserved intervals are remembered in
520.1.22 by Brian Aker
Second pass of thd cleanup
403
    session->auto_inc_intervals_in_cur_stmt_for_binlog if statement-based
1 by brian
clean slate
404
    binlogging; the last reserved interval is remembered in
405
    auto_inc_interval_for_cur_row.
406
407
    The idea is that generated auto_increment values are predictable and
408
    independent of the column values in the table.  This is needed to be
409
    able to replicate into a table that already has rows with a higher
410
    auto-increment value than the one that is inserted.
411
412
    After we have already generated an auto-increment number and the user
413
    inserts a column with a higher value than the last used one, we will
414
    start counting from the inserted value.
415
416
    This function's "outputs" are: the table's auto_increment field is filled
520.1.22 by Brian Aker
Second pass of thd cleanup
417
    with a value, session->next_insert_id is filled with the value to use for the
1 by brian
clean slate
418
    next row, if a value was autogenerated for the current row it is stored in
520.1.22 by Brian Aker
Second pass of thd cleanup
419
    session->insert_id_for_cur_row, if get_auto_increment() was called
420
    session->auto_inc_interval_for_cur_row is modified, if that interval is not
421
    present in session->auto_inc_intervals_in_cur_stmt_for_binlog it is added to
1 by brian
clean slate
422
    this list.
423
424
  @todo
425
    Replace all references to "next number" or NEXT_NUMBER to
426
    "auto_increment", everywhere (see below: there is
427
    table->auto_increment_field_not_null, and there also exists
428
    table->next_number_field, it's not consistent).
429
430
  @retval
431
    0	ok
432
  @retval
433
    HA_ERR_AUTOINC_READ_FAILED  get_auto_increment() was called and
434
    returned ~(uint64_t) 0
435
  @retval
436
    HA_ERR_AUTOINC_ERANGE storing value in field caused strict mode
437
    failure.
438
*/
439
440
#define AUTO_INC_DEFAULT_NB_ROWS 1 // Some prefer 1024 here
441
#define AUTO_INC_DEFAULT_NB_MAX_BITS 16
442
#define AUTO_INC_DEFAULT_NB_MAX ((1 << AUTO_INC_DEFAULT_NB_MAX_BITS) - 1)
443
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
444
int Cursor::update_auto_increment()
1 by brian
clean slate
445
{
446
  uint64_t nr, nb_reserved_values;
56 by brian
Next pass of true/false update.
447
  bool append= false;
1869.1.5 by Brian Aker
getTable()
448
  Session *session= getTable()->in_use;
1878.3.2 by Monty Taylor
Split out show_type into its own header and made sys_var work through
449
  drizzle_system_variables *variables= &session->variables;
1 by brian
clean slate
450
451
  /*
452
    next_insert_id is a "cursor" into the reserved interval, it may go greater
453
    than the interval, but not smaller.
454
  */
51.1.77 by Jay Pipes
Standardized TRUE/FALSE, removed/replaced DBUG symbols
455
  assert(next_insert_id >= auto_inc_interval_for_cur_row.minimum());
1 by brian
clean slate
456
1055.2.2 by Jay Pipes
Cleanup of style, indentation, and documentation of Table class members. Removed 5 or 6 dead Table member variables.
457
  /* We check if auto_increment_field_not_null is false
1008.3.2 by Stewart Smith
Make sql_mode=NO_AUTO_VALUE_ON_ZERO default for Drizzle.
458
     for an auto increment column, not a magic value like NULL is.
459
     same as sql_mode=NO_AUTO_VALUE_ON_ZERO */
460
1869.1.5 by Brian Aker
getTable()
461
  if ((nr= getTable()->next_number_field->val_int()) != 0
462
      || getTable()->auto_increment_field_not_null)
1 by brian
clean slate
463
  {
464
    /*
465
      Update next_insert_id if we had already generated a value in this
466
      statement (case of INSERT VALUES(null),(3763),(null):
467
      the last NULL needs to insert 3764, not the value of the first NULL plus
468
      1).
469
    */
470
    adjust_next_insert_id_after_explicit_value(nr);
471
    insert_id_for_cur_row= 0; // didn't generate anything
1046.1.9 by Brian Aker
Remove caller that wasn't correctly locking, and reverted code to 5.1
472
473
    return 0;
1 by brian
clean slate
474
  }
475
476
  if ((nr= next_insert_id) >= auto_inc_interval_for_cur_row.maximum())
477
  {
478
    /* next_insert_id is beyond what is reserved, so we reserve more. */
479
    const Discrete_interval *forced=
520.1.22 by Brian Aker
Second pass of thd cleanup
480
      session->auto_inc_intervals_forced.get_next();
1 by brian
clean slate
481
    if (forced != NULL)
482
    {
483
      nr= forced->minimum();
484
      nb_reserved_values= forced->values();
485
    }
486
    else
487
    {
488
      /*
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
489
        Cursor::estimation_rows_to_insert was set by
490
        Cursor::ha_start_bulk_insert(); if 0 it means "unknown".
1 by brian
clean slate
491
      */
482 by Brian Aker
Remove uint.
492
      uint32_t nb_already_reserved_intervals=
520.1.22 by Brian Aker
Second pass of thd cleanup
493
        session->auto_inc_intervals_in_cur_stmt_for_binlog.nb_elements();
1 by brian
clean slate
494
      uint64_t nb_desired_values;
495
      /*
496
        If an estimation was given to the engine:
497
        - use it.
498
        - if we already reserved numbers, it means the estimation was
499
        not accurate, then we'll reserve 2*AUTO_INC_DEFAULT_NB_ROWS the 2nd
500
        time, twice that the 3rd time etc.
501
        If no estimation was given, use those increasing defaults from the
502
        start, starting from AUTO_INC_DEFAULT_NB_ROWS.
503
        Don't go beyond a max to not reserve "way too much" (because
504
        reservation means potentially losing unused values).
505
      */
506
      if (nb_already_reserved_intervals == 0 &&
507
          (estimation_rows_to_insert > 0))
508
        nb_desired_values= estimation_rows_to_insert;
509
      else /* go with the increasing defaults */
510
      {
511
        /* avoid overflow in formula, with this if() */
512
        if (nb_already_reserved_intervals <= AUTO_INC_DEFAULT_NB_MAX_BITS)
513
        {
575.2.2 by Monty Taylor
Moved vio stuff into libdrizzle.
514
          nb_desired_values= AUTO_INC_DEFAULT_NB_ROWS *
1 by brian
clean slate
515
            (1 << nb_already_reserved_intervals);
937.2.6 by Stewart Smith
make set_if_bigger typesafe for C and C++. Fix up everywhere.
516
          set_if_smaller(nb_desired_values, (uint64_t)AUTO_INC_DEFAULT_NB_MAX);
1 by brian
clean slate
517
        }
518
        else
519
          nb_desired_values= AUTO_INC_DEFAULT_NB_MAX;
520
      }
521
      /* This call ignores all its parameters but nr, currently */
522
      get_auto_increment(variables->auto_increment_offset,
523
                         variables->auto_increment_increment,
524
                         nb_desired_values, &nr,
525
                         &nb_reserved_values);
526
      if (nr == ~(uint64_t) 0)
1046.1.9 by Brian Aker
Remove caller that wasn't correctly locking, and reverted code to 5.1
527
        return HA_ERR_AUTOINC_READ_FAILED;  // Mark failure
575.2.2 by Monty Taylor
Moved vio stuff into libdrizzle.
528
1 by brian
clean slate
529
      /*
530
        That rounding below should not be needed when all engines actually
531
        respect offset and increment in get_auto_increment(). But they don't
532
        so we still do it. Wonder if for the not-first-in-index we should do
533
        it. Hope that this rounding didn't push us out of the interval; even
534
        if it did we cannot do anything about it (calling the engine again
535
        will not help as we inserted no row).
536
      */
537
      nr= compute_next_insert_id(nr-1, variables);
538
    }
575.2.2 by Monty Taylor
Moved vio stuff into libdrizzle.
539
1869.1.5 by Brian Aker
getTable()
540
    if (getTable()->getShare()->next_number_keypart == 0)
1 by brian
clean slate
541
    {
542
      /* We must defer the appending until "nr" has been possibly truncated */
56 by brian
Next pass of true/false update.
543
      append= true;
1 by brian
clean slate
544
    }
545
  }
546
1869.1.5 by Brian Aker
getTable()
547
  if (unlikely(getTable()->next_number_field->store((int64_t) nr, true)))
1 by brian
clean slate
548
  {
549
    /*
550
      first test if the query was aborted due to strict mode constraints
551
    */
1910.2.8 by Brian Aker
Enapsulate Kill.
552
    if (session->getKilled() == Session::KILL_BAD_DATA)
1046.1.9 by Brian Aker
Remove caller that wasn't correctly locking, and reverted code to 5.1
553
      return HA_ERR_AUTOINC_ERANGE;
1 by brian
clean slate
554
555
    /*
556
      field refused this value (overflow) and truncated it, use the result of
557
      the truncation (which is going to be inserted); however we try to
558
      decrease it to honour auto_increment_* variables.
559
      That will shift the left bound of the reserved interval, we don't
560
      bother shifting the right bound (anyway any other value from this
561
      interval will cause a duplicate key).
562
    */
1869.1.5 by Brian Aker
getTable()
563
    nr= prev_insert_id(getTable()->next_number_field->val_int(), variables);
564
    if (unlikely(getTable()->next_number_field->store((int64_t) nr, true)))
565
      nr= getTable()->next_number_field->val_int();
1 by brian
clean slate
566
  }
567
  if (append)
568
  {
569
    auto_inc_interval_for_cur_row.replace(nr, nb_reserved_values,
570
                                          variables->auto_increment_increment);
571
  }
572
573
  /*
574
    Record this autogenerated value. If the caller then
575
    succeeds to insert this value, it will call
576
    record_first_successful_insert_id_in_cur_stmt()
577
    which will set first_successful_insert_id_in_cur_stmt if it's not
578
    already set.
579
  */
580
  insert_id_for_cur_row= nr;
581
  /*
582
    Set next insert id to point to next auto-increment value to be able to
583
    handle multi-row statements.
584
  */
585
  set_next_insert_id(compute_next_insert_id(nr, variables));
586
1046.1.9 by Brian Aker
Remove caller that wasn't correctly locking, and reverted code to 5.1
587
  return 0;
1 by brian
clean slate
588
}
589
590
591
/**
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
592
  Reserves an interval of auto_increment values from the Cursor.
1 by brian
clean slate
593
594
  offset and increment means that we want values to be of the form
595
  offset + N * increment, where N>=0 is integer.
596
  If the function sets *first_value to ~(uint64_t)0 it means an error.
163 by Brian Aker
Merge Monty's code.
597
  If the function sets *nb_reserved_values to UINT64_MAX it means it has
1 by brian
clean slate
598
  reserved to "positive infinite".
599
600
  @param offset
601
  @param increment
602
  @param nb_desired_values   how many values we want
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
603
  @param first_value         (OUT) the first value reserved by the Cursor
604
  @param nb_reserved_values  (OUT) how many values the Cursor reserved
1 by brian
clean slate
605
*/
606
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
607
void Cursor::ha_release_auto_increment()
1 by brian
clean slate
608
{
609
  release_auto_increment();
610
  insert_id_for_cur_row= 0;
611
  auto_inc_interval_for_cur_row.replace(0, 0, 0);
612
  if (next_insert_id > 0)
613
  {
614
    next_insert_id= 0;
615
    /*
616
      this statement used forced auto_increment values if there were some,
617
      wipe them away for other statements.
618
    */
1869.1.5 by Brian Aker
getTable()
619
    getTable()->in_use->auto_inc_intervals_forced.empty();
1 by brian
clean slate
620
  }
621
}
622
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
623
void Cursor::drop_table(const char *)
1 by brian
clean slate
624
{
625
  close();
626
}
627
628
629
/**
630
  Performs checks upon the table.
631
520.1.22 by Brian Aker
Second pass of thd cleanup
632
  @param session                thread doing CHECK Table operation
1 by brian
clean slate
633
  @param check_opt          options from the parser
634
635
  @retval
636
    HA_ADMIN_OK               Successful upgrade
637
  @retval
638
    HA_ADMIN_NEEDS_UPGRADE    Table has structures requiring upgrade
639
  @retval
327.1.5 by Brian Aker
Refactor around classes. TABLE_LIST has been factored out of table.h
640
    HA_ADMIN_NEEDS_ALTER      Table has structures requiring ALTER Table
1 by brian
clean slate
641
  @retval
642
    HA_ADMIN_NOT_IMPLEMENTED
643
*/
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
644
int Cursor::ha_check(Session *, HA_CHECK_OPT *)
1 by brian
clean slate
645
{
590.1.4 by Stewart Smith
remove frm_version from TABLE_SHARE
646
  return HA_ADMIN_OK;
1 by brian
clean slate
647
}
648
649
/**
650
  A helper function to mark a transaction read-write,
651
  if it is started.
652
*/
653
654
inline
655
void
1273.1.12 by Jay Pipes
Cleanup style and documentation for ResourceContext and setTransactionReadWrite
656
Cursor::setTransactionReadWrite()
1 by brian
clean slate
657
{
1578.6.1 by Brian Aker
Remove ha_session where table->in_use should have been checked.
658
  ResourceContext *resource_context;
659
660
  /*
661
   * If the cursor has not context for execution then there should be no
662
   * possible resource to gain (and if there is... then there is a bug such
663
   * that in_use should have been set.
664
 */
1869.1.5 by Brian Aker
getTable()
665
  if (not getTable()->in_use)
1578.6.1 by Brian Aker
Remove ha_session where table->in_use should have been checked.
666
    return;
667
1869.1.5 by Brian Aker
getTable()
668
  resource_context= getTable()->in_use->getResourceContext(getEngine());
1 by brian
clean slate
669
  /*
670
    When a storage engine method is called, the transaction must
671
    have been started, unless it's a DDL call, for which the
672
    storage engine starts the transaction internally, and commits
673
    it internally, without registering in the ha_list.
674
    Unfortunately here we can't know know for sure if the engine
675
    has registered the transaction or not, so we must check.
676
  */
1273.1.12 by Jay Pipes
Cleanup style and documentation for ResourceContext and setTransactionReadWrite
677
  if (resource_context->isStarted())
1 by brian
clean slate
678
  {
1273.1.12 by Jay Pipes
Cleanup style and documentation for ResourceContext and setTransactionReadWrite
679
    resource_context->markModifiedData();
1 by brian
clean slate
680
  }
681
}
682
683
684
/**
685
  Delete all rows: public interface.
686
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
687
  @sa Cursor::delete_all_rows()
1143.4.6 by Jay Pipes
Adds test case to transaction log for TRUNCATE TABLE.
688
689
  @note
690
691
  This is now equalivalent to TRUNCATE TABLE.
1 by brian
clean slate
692
*/
693
694
int
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
695
Cursor::ha_delete_all_rows()
1 by brian
clean slate
696
{
1273.1.12 by Jay Pipes
Cleanup style and documentation for ResourceContext and setTransactionReadWrite
697
  setTransactionReadWrite();
1 by brian
clean slate
698
1143.4.6 by Jay Pipes
Adds test case to transaction log for TRUNCATE TABLE.
699
  int result= delete_all_rows();
700
701
  if (result == 0)
702
  {
703
    /** 
704
     * Trigger post-truncate notification to plugins... 
705
     *
1336.2.2 by Jay Pipes
NO CODE CHANGES - Simply moves pieces of ReplicationServices to TransactionServices. Preparation for making the ReplicationServices component only responsible for communication between replicators, appliers, publishers, and subscribers.
706
     * @todo Make TransactionServices generic to AfterTriggerServices
1143.4.6 by Jay Pipes
Adds test case to transaction log for TRUNCATE TABLE.
707
     * or similar...
708
     */
1869.1.5 by Brian Aker
getTable()
709
    Session *const session= getTable()->in_use;
1336.2.2 by Jay Pipes
NO CODE CHANGES - Simply moves pieces of ReplicationServices to TransactionServices. Preparation for making the ReplicationServices component only responsible for communication between replicators, appliers, publishers, and subscribers.
710
    TransactionServices &transaction_services= TransactionServices::singleton();
2096.2.1 by David Shrewsbury
Initial change to use references to Session in TransactionServices methods rather than pointers.
711
    transaction_services.truncateTable(*session, *getTable());
1143.4.6 by Jay Pipes
Adds test case to transaction log for TRUNCATE TABLE.
712
  }
713
714
  return result;
1 by brian
clean slate
715
}
716
717
718
/**
719
  Reset auto increment: public interface.
720
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
721
  @sa Cursor::reset_auto_increment()
1 by brian
clean slate
722
*/
723
724
int
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
725
Cursor::ha_reset_auto_increment(uint64_t value)
1 by brian
clean slate
726
{
1273.1.12 by Jay Pipes
Cleanup style and documentation for ResourceContext and setTransactionReadWrite
727
  setTransactionReadWrite();
1 by brian
clean slate
728
729
  return reset_auto_increment(value);
730
}
731
732
733
/**
734
  Analyze table: public interface.
735
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
736
  @sa Cursor::analyze()
1 by brian
clean slate
737
*/
738
739
int
1222.1.10 by Brian Aker
Removes options from DDL left in Cursor for admin operations (they were
740
Cursor::ha_analyze(Session* session, HA_CHECK_OPT*)
1 by brian
clean slate
741
{
1273.1.12 by Jay Pipes
Cleanup style and documentation for ResourceContext and setTransactionReadWrite
742
  setTransactionReadWrite();
1 by brian
clean slate
743
1222.1.10 by Brian Aker
Removes options from DDL left in Cursor for admin operations (they were
744
  return analyze(session);
1 by brian
clean slate
745
}
746
747
/**
748
  Disable indexes: public interface.
749
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
750
  @sa Cursor::disable_indexes()
1 by brian
clean slate
751
*/
752
753
int
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
754
Cursor::ha_disable_indexes(uint32_t mode)
1 by brian
clean slate
755
{
1273.1.12 by Jay Pipes
Cleanup style and documentation for ResourceContext and setTransactionReadWrite
756
  setTransactionReadWrite();
1 by brian
clean slate
757
758
  return disable_indexes(mode);
759
}
760
761
762
/**
763
  Enable indexes: public interface.
764
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
765
  @sa Cursor::enable_indexes()
1 by brian
clean slate
766
*/
767
768
int
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
769
Cursor::ha_enable_indexes(uint32_t mode)
1 by brian
clean slate
770
{
1273.1.12 by Jay Pipes
Cleanup style and documentation for ResourceContext and setTransactionReadWrite
771
  setTransactionReadWrite();
1 by brian
clean slate
772
773
  return enable_indexes(mode);
774
}
775
776
777
/**
778
  Discard or import tablespace: public interface.
779
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
780
  @sa Cursor::discard_or_import_tablespace()
1 by brian
clean slate
781
*/
782
783
int
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
784
Cursor::ha_discard_or_import_tablespace(bool discard)
1 by brian
clean slate
785
{
1273.1.12 by Jay Pipes
Cleanup style and documentation for ResourceContext and setTransactionReadWrite
786
  setTransactionReadWrite();
1 by brian
clean slate
787
788
  return discard_or_import_tablespace(discard);
789
}
790
791
/**
792
  Drop table in the engine: public interface.
793
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
794
  @sa Cursor::drop_table()
1 by brian
clean slate
795
*/
796
797
void
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
798
Cursor::closeMarkForDelete(const char *name)
1 by brian
clean slate
799
{
1273.1.12 by Jay Pipes
Cleanup style and documentation for ResourceContext and setTransactionReadWrite
800
  setTransactionReadWrite();
1 by brian
clean slate
801
802
  return drop_table(name);
803
}
804
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
805
int Cursor::index_next_same(unsigned char *buf, const unsigned char *key, uint32_t keylen)
1 by brian
clean slate
806
{
807
  int error;
808
  if (!(error=index_next(buf)))
809
  {
1869.1.5 by Brian Aker
getTable()
810
    ptrdiff_t ptrdiff= buf - getTable()->getInsertRecord();
481 by Brian Aker
Remove all of uchar.
811
    unsigned char *save_record_0= NULL;
1535 by Brian Aker
Rename of KEY to KeyInfo
812
    KeyInfo *key_info= NULL;
1534 by Brian Aker
Remove of KeyPartInfo
813
    KeyPartInfo *key_part;
814
    KeyPartInfo *key_part_end= NULL;
1 by brian
clean slate
815
816
    /*
1672.3.6 by Brian Aker
First pass in encapsulating row
817
      key_cmp_if_same() compares table->getInsertRecord() against 'key'.
818
      In parts it uses table->getInsertRecord() directly, in parts it uses
819
      field objects with their local pointers into table->getInsertRecord().
820
      If 'buf' is distinct from table->getInsertRecord(), we need to move
821
      all record references. This is table->getInsertRecord() itself and
1 by brian
clean slate
822
      the field pointers of the fields used in this key.
823
    */
824
    if (ptrdiff)
825
    {
1869.1.5 by Brian Aker
getTable()
826
      save_record_0= getTable()->getInsertRecord();
827
      getTable()->record[0]= buf;
828
      key_info= getTable()->key_info + active_index;
1 by brian
clean slate
829
      key_part= key_info->key_part;
830
      key_part_end= key_part + key_info->key_parts;
831
      for (; key_part < key_part_end; key_part++)
832
      {
51.1.77 by Jay Pipes
Standardized TRUE/FALSE, removed/replaced DBUG symbols
833
        assert(key_part->field);
1 by brian
clean slate
834
        key_part->field->move_field_offset(ptrdiff);
835
      }
836
    }
837
1869.1.5 by Brian Aker
getTable()
838
    if (key_cmp_if_same(getTable(), key, active_index, keylen))
1 by brian
clean slate
839
    {
1869.1.5 by Brian Aker
getTable()
840
      getTable()->status=STATUS_NOT_FOUND;
1 by brian
clean slate
841
      error=HA_ERR_END_OF_FILE;
842
    }
843
844
    /* Move back if necessary. */
845
    if (ptrdiff)
846
    {
1869.1.5 by Brian Aker
getTable()
847
      getTable()->record[0]= save_record_0;
1 by brian
clean slate
848
      for (key_part= key_info->key_part; key_part < key_part_end; key_part++)
849
        key_part->field->move_field_offset(-ptrdiff);
850
    }
851
  }
1046.1.9 by Brian Aker
Remove caller that wasn't correctly locking, and reverted code to 5.1
852
  return error;
1 by brian
clean slate
853
}
854
855
856
/****************************************************************************
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
857
** Some general functions that isn't in the Cursor class
1 by brian
clean slate
858
****************************************************************************/
859
860
/**
861
  Calculate cost of 'index only' scan for given index and number of records
862
863
  @param keynr    Index number
864
  @param records  Estimated number of records to be retrieved
865
866
  @note
867
    It is assumed that we will read trough the whole key range and that all
868
    key blocks are half full (normally things are much better). It is also
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
869
    assumed that each time we read the next key from the index, the Cursor
1 by brian
clean slate
870
    performs a random seek, thus the cost is proportional to the number of
871
    blocks read.
872
873
  @todo
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
874
    Consider joining this function and Cursor::read_time() into one
875
    Cursor::read_time(keynr, records, ranges, bool index_only) function.
1 by brian
clean slate
876
877
  @return
878
    Estimated cost of 'index only' scan
879
*/
880
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
881
double Cursor::index_only_read_time(uint32_t keynr, double key_records)
1 by brian
clean slate
882
{
482 by Brian Aker
Remove uint.
883
  uint32_t keys_per_block= (stats.block_size/2/
1869.1.5 by Brian Aker
getTable()
884
			(getTable()->key_info[keynr].key_length + ref_length) + 1);
779.3.10 by Monty Taylor
Turned on -Wshadow.
885
  return ((double) (key_records + keys_per_block-1) /
886
          (double) keys_per_block);
1 by brian
clean slate
887
}
888
889
890
/****************************************************************************
891
 * Default MRR implementation (MRR to non-MRR converter)
892
 ***************************************************************************/
893
894
/**
895
  Get cost and other information about MRR scan over a known list of ranges
896
897
  Calculate estimated cost and other information about an MRR scan for given
898
  sequence of ranges.
899
900
  @param keyno           Index number
901
  @param seq             Range sequence to be traversed
902
  @param seq_init_param  First parameter for seq->init()
903
  @param n_ranges_arg    Number of ranges in the sequence, or 0 if the caller
904
                         can't efficiently determine it
905
  @param bufsz    INOUT  IN:  Size of the buffer available for use
906
                         OUT: Size of the buffer that is expected to be actually
907
                              used, or 0 if buffer is not needed.
908
  @param flags    INOUT  A combination of HA_MRR_* flags
909
  @param cost     OUT    Estimated cost of MRR access
910
911
  @note
912
    This method (or an overriding one in a derived class) must check for
1910.2.8 by Brian Aker
Enapsulate Kill.
913
    session->getKilled() and return HA_POS_ERROR if it is not zero. This is required
1 by brian
clean slate
914
    for a user to be able to interrupt the calculation by killing the
915
    connection/query.
916
917
  @retval
918
    HA_POS_ERROR  Error or the engine is unable to perform the requested
919
                  scan. Values of OUT parameters are undefined.
920
  @retval
921
    other         OK, *cost contains cost of the scan, *bufsz and *flags
922
                  contain scan parameters.
923
*/
924
77.1.15 by Monty Taylor
Bunch of warning cleanups.
925
ha_rows
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
926
Cursor::multi_range_read_info_const(uint32_t keyno, RANGE_SEQ_IF *seq,
77.1.15 by Monty Taylor
Bunch of warning cleanups.
927
                                     void *seq_init_param,
779.1.27 by Monty Taylor
Got rid of __attribute__((unused)) and the like from the .cc files.
928
                                     uint32_t ,
1336.3.2 by Djellel E. Difallah
rename class COST_VECT to CostVector and move it to ./drizzled/optimizer directory
929
                                     uint32_t *bufsz, uint32_t *flags, optimizer::CostVector *cost)
1 by brian
clean slate
930
{
931
  KEY_MULTI_RANGE range;
932
  range_seq_t seq_it;
933
  ha_rows rows, total_rows= 0;
482 by Brian Aker
Remove uint.
934
  uint32_t n_ranges=0;
575.2.2 by Monty Taylor
Moved vio stuff into libdrizzle.
935
1 by brian
clean slate
936
  /* Default MRR implementation doesn't need buffer */
937
  *bufsz= 0;
938
939
  seq_it= seq->init(seq_init_param, n_ranges, *flags);
940
  while (!seq->next(seq_it, &range))
941
  {
942
    n_ranges++;
943
    key_range *min_endp, *max_endp;
944
    {
945
      min_endp= range.start_key.length? &range.start_key : NULL;
946
      max_endp= range.end_key.length? &range.end_key : NULL;
947
    }
948
    if ((range.range_flag & UNIQUE_RANGE) && !(range.range_flag & NULL_RANGE))
949
      rows= 1; /* there can be at most one row */
950
    else
951
    {
575.2.2 by Monty Taylor
Moved vio stuff into libdrizzle.
952
      if (HA_POS_ERROR == (rows= this->records_in_range(keyno, min_endp,
1 by brian
clean slate
953
                                                        max_endp)))
954
      {
955
        /* Can't scan one range => can't do MRR scan at all */
956
        total_rows= HA_POS_ERROR;
957
        break;
958
      }
959
    }
960
    total_rows += rows;
961
  }
575.2.2 by Monty Taylor
Moved vio stuff into libdrizzle.
962
1 by brian
clean slate
963
  if (total_rows != HA_POS_ERROR)
964
  {
965
    /* The following calculation is the same as in multi_range_read_info(): */
966
    *flags |= HA_MRR_USE_DEFAULT_IMPL;
967
    cost->zero();
1336.3.2 by Djellel E. Difallah
rename class COST_VECT to CostVector and move it to ./drizzled/optimizer directory
968
    cost->setAvgIOCost(1); /* assume random seeks */
1 by brian
clean slate
969
    if ((*flags & HA_MRR_INDEX_ONLY) && total_rows > 2)
1336.3.2 by Djellel E. Difallah
rename class COST_VECT to CostVector and move it to ./drizzled/optimizer directory
970
      cost->setIOCount(index_only_read_time(keyno, (uint32_t)total_rows));
1 by brian
clean slate
971
    else
1336.3.2 by Djellel E. Difallah
rename class COST_VECT to CostVector and move it to ./drizzled/optimizer directory
972
      cost->setIOCount(read_time(keyno, n_ranges, total_rows));
973
    cost->setCpuCost((double) total_rows / TIME_FOR_COMPARE + 0.01);
1 by brian
clean slate
974
  }
975
  return total_rows;
976
}
977
978
979
/**
980
  Get cost and other information about MRR scan over some sequence of ranges
981
982
  Calculate estimated cost and other information about an MRR scan for some
983
  sequence of ranges.
984
985
  The ranges themselves will be known only at execution phase. When this
986
  function is called we only know number of ranges and a (rough) E(#records)
987
  within those ranges.
988
989
  Currently this function is only called for "n-keypart singlepoint" ranges,
990
  i.e. each range is "keypart1=someconst1 AND ... AND keypartN=someconstN"
991
992
  The flags parameter is a combination of those flags: HA_MRR_SORTED,
993
  HA_MRR_INDEX_ONLY, HA_MRR_NO_ASSOCIATION, HA_MRR_LIMITS.
994
995
  @param keyno           Index number
996
  @param n_ranges        Estimated number of ranges (i.e. intervals) in the
997
                         range sequence.
998
  @param n_rows          Estimated total number of records contained within all
999
                         of the ranges
1000
  @param bufsz    INOUT  IN:  Size of the buffer available for use
1001
                         OUT: Size of the buffer that will be actually used, or
1002
                              0 if buffer is not needed.
1003
  @param flags    INOUT  A combination of HA_MRR_* flags
1004
  @param cost     OUT    Estimated cost of MRR access
1005
1006
  @retval
1007
    0     OK, *cost contains cost of the scan, *bufsz and *flags contain scan
1008
          parameters.
1009
  @retval
1010
    other Error or can't perform the requested scan
1011
*/
1012
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
1013
int Cursor::multi_range_read_info(uint32_t keyno, uint32_t n_ranges, uint32_t n_rows,
1336.3.2 by Djellel E. Difallah
rename class COST_VECT to CostVector and move it to ./drizzled/optimizer directory
1014
                                   uint32_t *bufsz, uint32_t *flags, optimizer::CostVector *cost)
1 by brian
clean slate
1015
{
1016
  *bufsz= 0; /* Default implementation doesn't need a buffer */
1017
1018
  *flags |= HA_MRR_USE_DEFAULT_IMPL;
1019
1020
  cost->zero();
1336.3.2 by Djellel E. Difallah
rename class COST_VECT to CostVector and move it to ./drizzled/optimizer directory
1021
  cost->setAvgIOCost(1); /* assume random seeks */
1 by brian
clean slate
1022
1023
  /* Produce the same cost as non-MRR code does */
1024
  if (*flags & HA_MRR_INDEX_ONLY)
1336.3.2 by Djellel E. Difallah
rename class COST_VECT to CostVector and move it to ./drizzled/optimizer directory
1025
    cost->setIOCount(index_only_read_time(keyno, n_rows));
1 by brian
clean slate
1026
  else
1336.3.2 by Djellel E. Difallah
rename class COST_VECT to CostVector and move it to ./drizzled/optimizer directory
1027
    cost->setIOCount(read_time(keyno, n_ranges, n_rows));
1 by brian
clean slate
1028
  return 0;
1029
}
1030
1031
1032
/**
1033
  Initialize the MRR scan
1034
575.2.2 by Monty Taylor
Moved vio stuff into libdrizzle.
1035
  Initialize the MRR scan. This function may do heavyweight scan
1 by brian
clean slate
1036
  initialization like row prefetching/sorting/etc (NOTE: but better not do
1037
  it here as we may not need it, e.g. if we never satisfy WHERE clause on
1038
  previous tables. For many implementations it would be natural to do such
1039
  initializations in the first multi_read_range_next() call)
1040
1041
  mode is a combination of the following flags: HA_MRR_SORTED,
575.2.2 by Monty Taylor
Moved vio stuff into libdrizzle.
1042
  HA_MRR_INDEX_ONLY, HA_MRR_NO_ASSOCIATION
1 by brian
clean slate
1043
1044
  @param seq             Range sequence to be traversed
1045
  @param seq_init_param  First parameter for seq->init()
1046
  @param n_ranges        Number of ranges in the sequence
1047
  @param mode            Flags, see the description section for the details
1048
  @param buf             INOUT: memory buffer to be used
1049
1050
  @note
1491.1.6 by Jay Pipes
Cursor::ha_index_init() -> Cursor::startIndexScan(). Cursor::ha_index_end() -> Cursor::endIndexScan()
1051
    One must have called doStartIndexScan() before calling this function. Several
1 by brian
clean slate
1052
    multi_range_read_init() calls may be made in course of one query.
1053
575.2.2 by Monty Taylor
Moved vio stuff into libdrizzle.
1054
    Until WL#2623 is done (see its text, section 3.2), the following will
1 by brian
clean slate
1055
    also hold:
1056
    The caller will guarantee that if "seq->init == mrr_ranges_array_init"
1057
    then seq_init_param is an array of n_ranges KEY_MULTI_RANGE structures.
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
1058
    This property will only be used by NDB Cursor until WL#2623 is done.
575.2.2 by Monty Taylor
Moved vio stuff into libdrizzle.
1059
1 by brian
clean slate
1060
    Buffer memory management is done according to the following scenario:
1061
    The caller allocates the buffer and provides it to the callee by filling
1062
    the members of HANDLER_BUFFER structure.
1063
    The callee consumes all or some fraction of the provided buffer space, and
1064
    sets the HANDLER_BUFFER members accordingly.
1065
    The callee may use the buffer memory until the next multi_range_read_init()
1491.1.6 by Jay Pipes
Cursor::ha_index_init() -> Cursor::startIndexScan(). Cursor::ha_index_end() -> Cursor::endIndexScan()
1066
    call is made, all records have been read, or until doEndIndexScan() call is
1 by brian
clean slate
1067
    made, whichever comes first.
1068
1069
  @retval 0  OK
1070
  @retval 1  Error
1071
*/
1072
1073
int
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
1074
Cursor::multi_range_read_init(RANGE_SEQ_IF *seq_funcs, void *seq_init_param,
1491 by Brian Aker
Remove call bits in dead mrr caller.
1075
                               uint32_t n_ranges, uint32_t mode)
1 by brian
clean slate
1076
{
1077
  mrr_iter= seq_funcs->init(seq_init_param, n_ranges, mode);
1078
  mrr_funcs= *seq_funcs;
1079
  mrr_is_output_sorted= test(mode & HA_MRR_SORTED);
56 by brian
Next pass of true/false update.
1080
  mrr_have_range= false;
1491 by Brian Aker
Remove call bits in dead mrr caller.
1081
1046.1.9 by Brian Aker
Remove caller that wasn't correctly locking, and reverted code to 5.1
1082
  return 0;
1 by brian
clean slate
1083
}
1084
1085
1086
/**
1087
  Get next record in MRR scan
1088
1089
  Default MRR implementation: read the next record
1090
1091
  @param range_info  OUT  Undefined if HA_MRR_NO_ASSOCIATION flag is in effect
1092
                          Otherwise, the opaque value associated with the range
1093
                          that contains the returned record.
1094
1095
  @retval 0      OK
1096
  @retval other  Error code
1097
*/
1098
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
1099
int Cursor::multi_range_read_next(char **range_info)
1 by brian
clean slate
1100
{
1101
  int result= 0;
236.2.2 by rbradfor
Using correct coding standards for variable initialization
1102
  int range_res= 0;
1 by brian
clean slate
1103
1492 by Brian Aker
Dead code removal.
1104
  if (not mrr_have_range)
1 by brian
clean slate
1105
  {
56 by brian
Next pass of true/false update.
1106
    mrr_have_range= true;
1 by brian
clean slate
1107
    goto start;
1108
  }
1109
1110
  do
1111
  {
1112
    /* Save a call if there can be only one row in range. */
1113
    if (mrr_cur_range.range_flag != (UNIQUE_RANGE | EQ_RANGE))
1114
    {
1115
      result= read_range_next();
1116
      /* On success or non-EOF errors jump to the end. */
1117
      if (result != HA_ERR_END_OF_FILE)
1118
        break;
1119
    }
1120
    else
1121
    {
1122
      if (was_semi_consistent_read())
1123
        goto scan_it_again;
1124
      /*
1125
        We need to set this for the last range only, but checking this
1126
        condition is more expensive than just setting the result code.
1127
      */
1128
      result= HA_ERR_END_OF_FILE;
1129
    }
1130
1131
start:
1132
    /* Try the next range(s) until one matches a record. */
1133
    while (!(range_res= mrr_funcs.next(mrr_iter, &mrr_cur_range)))
1134
    {
1135
scan_it_again:
1136
      result= read_range_first(mrr_cur_range.start_key.keypart_map ?
1137
                                 &mrr_cur_range.start_key : 0,
1138
                               mrr_cur_range.end_key.keypart_map ?
1139
                                 &mrr_cur_range.end_key : 0,
1140
                               test(mrr_cur_range.range_flag & EQ_RANGE),
1141
                               mrr_is_output_sorted);
1142
      if (result != HA_ERR_END_OF_FILE)
1143
        break;
1144
    }
1145
  }
1146
  while ((result == HA_ERR_END_OF_FILE) && !range_res);
1147
1148
  *range_info= mrr_cur_range.ptr;
1046.1.9 by Brian Aker
Remove caller that wasn't correctly locking, and reverted code to 5.1
1149
  return result;
1 by brian
clean slate
1150
}
1151
1152
1153
/* **************************************************************************
1154
 * DS-MRR implementation ends
1155
 ***************************************************************************/
1156
1157
/**
1158
  Read first row between two ranges.
1159
1160
  @param start_key		Start key. Is 0 if no min range
1161
  @param end_key		End key.  Is 0 if no max range
1162
  @param eq_range_arg	        Set to 1 if start_key == end_key
1163
  @param sorted		Set to 1 if result should be sorted per key
1164
1165
  @note
1672.3.6 by Brian Aker
First pass in encapsulating row
1166
    Record is read into table->getInsertRecord()
1 by brian
clean slate
1167
1168
  @retval
1169
    0			Found row
1170
  @retval
1171
    HA_ERR_END_OF_FILE	No rows in range
1172
  @retval
1173
    \#			Error code
1174
*/
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
1175
int Cursor::read_range_first(const key_range *start_key,
1183.1.4 by Brian Aker
Minor interface bits around Cursor.
1176
                             const key_range *end_key,
1177
                             bool eq_range_arg,
1178
                             bool )
1 by brian
clean slate
1179
{
1180
  int result;
1181
1182
  eq_range= eq_range_arg;
1183
  end_range= 0;
1184
  if (end_key)
1185
  {
1186
    end_range= &save_end_range;
1187
    save_end_range= *end_key;
1188
    key_compare_result_on_equal= ((end_key->flag == HA_READ_BEFORE_KEY) ? 1 :
1189
				  (end_key->flag == HA_READ_AFTER_KEY) ? -1 : 0);
1190
  }
1869.1.5 by Brian Aker
getTable()
1191
  range_key_part= getTable()->key_info[active_index].key_part;
1 by brian
clean slate
1192
1193
  if (!start_key)			// Read first record
1869.1.5 by Brian Aker
getTable()
1194
    result= index_first(getTable()->getInsertRecord());
1 by brian
clean slate
1195
  else
1869.1.5 by Brian Aker
getTable()
1196
    result= index_read_map(getTable()->getInsertRecord(),
1 by brian
clean slate
1197
                           start_key->key,
1198
                           start_key->keypart_map,
1199
                           start_key->flag);
1200
  if (result)
575.2.2 by Monty Taylor
Moved vio stuff into libdrizzle.
1201
    return((result == HA_ERR_KEY_NOT_FOUND)
1 by brian
clean slate
1202
		? HA_ERR_END_OF_FILE
1203
		: result);
1204
51.1.77 by Jay Pipes
Standardized TRUE/FALSE, removed/replaced DBUG symbols
1205
  return (compare_key(end_range) <= 0 ? 0 : HA_ERR_END_OF_FILE);
1 by brian
clean slate
1206
}
1207
1208
1209
/**
1210
  Read next row between two endpoints.
1211
1212
  @note
1672.3.6 by Brian Aker
First pass in encapsulating row
1213
    Record is read into table->getInsertRecord()
1 by brian
clean slate
1214
1215
  @retval
1216
    0			Found row
1217
  @retval
1218
    HA_ERR_END_OF_FILE	No rows in range
1219
  @retval
1220
    \#			Error code
1221
*/
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
1222
int Cursor::read_range_next()
1 by brian
clean slate
1223
{
1224
  int result;
1225
1226
  if (eq_range)
1227
  {
1228
    /* We trust that index_next_same always gives a row in range */
1869.1.5 by Brian Aker
getTable()
1229
    return(index_next_same(getTable()->getInsertRecord(),
1 by brian
clean slate
1230
                                end_range->key,
1231
                                end_range->length));
1232
  }
1869.1.5 by Brian Aker
getTable()
1233
  result= index_next(getTable()->getInsertRecord());
1 by brian
clean slate
1234
  if (result)
1046.1.9 by Brian Aker
Remove caller that wasn't correctly locking, and reverted code to 5.1
1235
    return result;
51.1.77 by Jay Pipes
Standardized TRUE/FALSE, removed/replaced DBUG symbols
1236
  return(compare_key(end_range) <= 0 ? 0 : HA_ERR_END_OF_FILE);
1 by brian
clean slate
1237
}
1238
1239
1240
/**
1241
  Compare if found key (in row) is over max-value.
1242
1243
  @param range		range to compare to row. May be 0 for no range
1244
1245
  @seealso
1246
    key.cc::key_cmp()
1247
1248
  @return
1249
    The return value is SIGN(key_in_row - range_key):
1250
1251
    - 0   : Key is equal to range or 'range' == 0 (no range)
1252
    - -1  : Key is less than range
1253
    - 1   : Key is larger than range
1254
*/
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
1255
int Cursor::compare_key(key_range *range)
1 by brian
clean slate
1256
{
1257
  int cmp;
1492 by Brian Aker
Dead code removal.
1258
  if (not range)
1 by brian
clean slate
1259
    return 0;					// No max range
1260
  cmp= key_cmp(range_key_part, range->key, range->length);
1261
  if (!cmp)
1262
    cmp= key_compare_result_on_equal;
1263
  return cmp;
1264
}
1265
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
1266
int Cursor::index_read_idx_map(unsigned char * buf, uint32_t index,
656.1.1 by Monty Taylor
OOOh doggie. Got rid of my_alloca.
1267
                                const unsigned char * key,
1 by brian
clean slate
1268
                                key_part_map keypart_map,
1269
                                enum ha_rkey_function find_flag)
1270
{
1271
  int error, error1;
1491.1.6 by Jay Pipes
Cursor::ha_index_init() -> Cursor::startIndexScan(). Cursor::ha_index_end() -> Cursor::endIndexScan()
1272
  error= doStartIndexScan(index, 0);
1 by brian
clean slate
1273
  if (!error)
1274
  {
1275
    error= index_read_map(buf, key, keypart_map, find_flag);
1491.1.6 by Jay Pipes
Cursor::ha_index_init() -> Cursor::startIndexScan(). Cursor::ha_index_end() -> Cursor::endIndexScan()
1276
    error1= doEndIndexScan();
1 by brian
clean slate
1277
  }
1278
  return error ?  error : error1;
1279
}
1280
1281
/**
1282
  Check if the conditions for row-based binlogging is correct for the table.
1283
1284
  A row in the given table should be replicated if:
1285
  - It is not a temporary table
1286
*/
1287
1039.1.16 by Brian Aker
A lot of little cleanups (most based off lcov)
1288
static bool log_row_for_replication(Table* table,
1143.2.20 by Jay Pipes
* Fixes bug in replication where inserts, updates, and
1289
                                    const unsigned char *before_record,
1290
                                    const unsigned char *after_record)
1 by brian
clean slate
1291
{
1336.2.2 by Jay Pipes
NO CODE CHANGES - Simply moves pieces of ReplicationServices to TransactionServices. Preparation for making the ReplicationServices component only responsible for communication between replicators, appliers, publishers, and subscribers.
1292
  TransactionServices &transaction_services= TransactionServices::singleton();
520.1.22 by Brian Aker
Second pass of thd cleanup
1293
  Session *const session= table->in_use;
1 by brian
clean slate
1294
1608.2.3 by Brian Aker
Encapsulate type for TableShare.
1295
  if (table->getShare()->getType() || not transaction_services.shouldConstructMessages())
1143.2.20 by Jay Pipes
* Fixes bug in replication where inserts, updates, and
1296
    return false;
1297
1143.4.15 by Jay Pipes
Adds error for when a record is inserted into a table containing
1298
  bool result= false;
1299
2187.2.2 by Brian Aker
getLex() usage and fix for table_name creation during admin commands.
1300
  switch (session->getLex()->sql_command)
661 by Brian Aker
First major pass through new replication.
1301
  {
1308.2.11 by Jay Pipes
* Adds CREATE TABLE as a specific CreateTableStatement message in the
1302
  case SQLCOM_CREATE_TABLE:
1303
    /*
1304
     * We are in a CREATE TABLE ... SELECT statement
1305
     * and the kernel has already created the table
1306
     * and put a CreateTableStatement in the active
1307
     * Transaction message.  Here, we add a new InsertRecord
1308
     * to a new Transaction message (because the above
1309
     * CREATE TABLE will commit the transaction containing
1310
     * it).
1311
     */
2096.2.1 by David Shrewsbury
Initial change to use references to Session in TransactionServices methods rather than pointers.
1312
    result= transaction_services.insertRecord(*session, *table);
1308.2.11 by Jay Pipes
* Adds CREATE TABLE as a specific CreateTableStatement message in the
1313
    break;
661 by Brian Aker
First major pass through new replication.
1314
  case SQLCOM_REPLACE:
1143.2.22 by Jay Pipes
Adds functionality to handle REPLACE statements correctly in the replication
1315
  case SQLCOM_REPLACE_SELECT:
1143.2.24 by Jay Pipes
Fixes some stuff from make check (include guards). Also adds stuff for REPLACE logic that does not work.
1316
    /*
1143.2.27 by Jay Pipes
Corrects problems where REPLACE and INSERT ... ON DUPLICATE KEY UPDATE
1317
     * This is a total hack because of the code that is
1318
     * in write_record() in sql_insert.cc. During
1491.1.2 by Jay Pipes
Cursor::write_row() -> Cursor::doInsertRecord(). Cursor::ha_write_row() -> Cursor::insertRecord()
1319
     * a REPLACE statement, a call to insertRecord() is
1491.1.4 by Jay Pipes
delete_row() is now deleteRecord() and doDeleteRecord() in Cursor
1320
     * called.  If it fails, then a call to deleteRecord()
1143.2.24 by Jay Pipes
Fixes some stuff from make check (include guards). Also adds stuff for REPLACE logic that does not work.
1321
     * is called, followed by a repeat of the original
1491.1.2 by Jay Pipes
Cursor::write_row() -> Cursor::doInsertRecord(). Cursor::ha_write_row() -> Cursor::insertRecord()
1322
     * call to insertRecord().  So, log_row_for_replication
1730.5.3 by David Shrewsbury
Correct comments regarding REPLACE logic.
1323
     * could be called multiple times for a REPLACE
1143.2.24 by Jay Pipes
Fixes some stuff from make check (include guards). Also adds stuff for REPLACE logic that does not work.
1324
     * statement.  The below looks at the values of before_record
1325
     * and after_record to determine which call to this
1326
     * function is for the delete or the insert, since NULL
1327
     * is passed for after_record for the delete and NULL is
1328
     * passed for before_record for the insert...
1143.2.27 by Jay Pipes
Corrects problems where REPLACE and INSERT ... ON DUPLICATE KEY UPDATE
1329
     *
1330
     * In addition, there is an optimization that allows an
1331
     * engine to convert the above delete + insert into an
1332
     * update, so we must also check for this case below...
1143.2.22 by Jay Pipes
Adds functionality to handle REPLACE statements correctly in the replication
1333
     */
1143.2.24 by Jay Pipes
Fixes some stuff from make check (include guards). Also adds stuff for REPLACE logic that does not work.
1334
    if (after_record == NULL)
1335
    {
1730.5.3 by David Shrewsbury
Correct comments regarding REPLACE logic.
1336
      /*
1337
       * The storage engine is passed the record in table->record[1]
1338
       * as the row to delete (this is the conflicting row), so
1339
       * we need to notify TransactionService to use that row.
1340
       */
2096.2.1 by David Shrewsbury
Initial change to use references to Session in TransactionServices methods rather than pointers.
1341
      transaction_services.deleteRecord(*session, *table, true);
1143.2.24 by Jay Pipes
Fixes some stuff from make check (include guards). Also adds stuff for REPLACE logic that does not work.
1342
      /* 
1343
       * We set the "current" statement message to NULL.  This triggers
1344
       * the replication services component to generate a new statement
1345
       * message for the inserted record which will come next.
1346
       */
2096.2.1 by David Shrewsbury
Initial change to use references to Session in TransactionServices methods rather than pointers.
1347
      transaction_services.finalizeStatementMessage(*session->getStatementMessage(), *session);
1143.2.24 by Jay Pipes
Fixes some stuff from make check (include guards). Also adds stuff for REPLACE logic that does not work.
1348
    }
1349
    else
1350
    {
1143.2.27 by Jay Pipes
Corrects problems where REPLACE and INSERT ... ON DUPLICATE KEY UPDATE
1351
      if (before_record == NULL)
2096.2.1 by David Shrewsbury
Initial change to use references to Session in TransactionServices methods rather than pointers.
1352
        result= transaction_services.insertRecord(*session, *table);
1143.2.27 by Jay Pipes
Corrects problems where REPLACE and INSERT ... ON DUPLICATE KEY UPDATE
1353
      else
2096.2.1 by David Shrewsbury
Initial change to use references to Session in TransactionServices methods rather than pointers.
1354
        transaction_services.updateRecord(*session, *table, before_record, after_record);
1143.2.24 by Jay Pipes
Fixes some stuff from make check (include guards). Also adds stuff for REPLACE logic that does not work.
1355
    }
1143.2.22 by Jay Pipes
Adds functionality to handle REPLACE statements correctly in the replication
1356
    break;
661 by Brian Aker
First major pass through new replication.
1357
  case SQLCOM_INSERT:
1358
  case SQLCOM_INSERT_SELECT:
1719.3.1 by David Shrewsbury
Fix to capture INSERTs from a LOAD DATA command in the replication stream.
1359
  case SQLCOM_LOAD:
1143.2.27 by Jay Pipes
Corrects problems where REPLACE and INSERT ... ON DUPLICATE KEY UPDATE
1360
    /*
1361
     * The else block below represents an 
1362
     * INSERT ... ON DUPLICATE KEY UPDATE that
1363
     * has hit a key conflict and actually done
1364
     * an update.
1365
     */
1366
    if (before_record == NULL)
2096.2.1 by David Shrewsbury
Initial change to use references to Session in TransactionServices methods rather than pointers.
1367
      result= transaction_services.insertRecord(*session, *table);
1143.2.27 by Jay Pipes
Corrects problems where REPLACE and INSERT ... ON DUPLICATE KEY UPDATE
1368
    else
2096.2.1 by David Shrewsbury
Initial change to use references to Session in TransactionServices methods rather than pointers.
1369
      transaction_services.updateRecord(*session, *table, before_record, after_record);
661 by Brian Aker
First major pass through new replication.
1370
    break;
1371
1372
  case SQLCOM_UPDATE:
2096.2.1 by David Shrewsbury
Initial change to use references to Session in TransactionServices methods rather than pointers.
1373
    transaction_services.updateRecord(*session, *table, before_record, after_record);
661 by Brian Aker
First major pass through new replication.
1374
    break;
1375
1376
  case SQLCOM_DELETE:
2096.2.1 by David Shrewsbury
Initial change to use references to Session in TransactionServices methods rather than pointers.
1377
    transaction_services.deleteRecord(*session, *table);
661 by Brian Aker
First major pass through new replication.
1378
    break;
1379
  default:
1380
    break;
1 by brian
clean slate
1381
  }
592 by Brian Aker
Remove one set.
1382
1143.4.15 by Jay Pipes
Adds error for when a record is inserted into a table containing
1383
  return result;
1 by brian
clean slate
1384
}
1385
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
1386
int Cursor::ha_external_lock(Session *session, int lock_type)
1 by brian
clean slate
1387
{
1388
  /*
1389
    Whether this is lock or unlock, this should be true, and is to verify that
1390
    if get_auto_increment() was called (thus may have reserved intervals or
1391
    taken a table lock), ha_release_auto_increment() was too.
1392
  */
51.1.77 by Jay Pipes
Standardized TRUE/FALSE, removed/replaced DBUG symbols
1393
  assert(next_insert_id == 0);
1 by brian
clean slate
1394
1241.7.5 by Padraig O'Sullivan
Added the lock related dtrace probes to the cursor interface.
1395
  if (DRIZZLE_CURSOR_RDLOCK_START_ENABLED() ||
1396
      DRIZZLE_CURSOR_WRLOCK_START_ENABLED() ||
1397
      DRIZZLE_CURSOR_UNLOCK_START_ENABLED())
1398
  {
1399
    if (lock_type == F_RDLCK)
1400
    {
1869.1.2 by Brian Aker
Remove table_share from being required in a cursor.
1401
      DRIZZLE_CURSOR_RDLOCK_START(getTable()->getShare()->getSchemaName(),
1402
                                  getTable()->getShare()->getTableName());
1241.7.5 by Padraig O'Sullivan
Added the lock related dtrace probes to the cursor interface.
1403
    }
1404
    else if (lock_type == F_WRLCK)
1405
    {
1869.1.2 by Brian Aker
Remove table_share from being required in a cursor.
1406
      DRIZZLE_CURSOR_WRLOCK_START(getTable()->getShare()->getSchemaName(),
1407
                                  getTable()->getShare()->getTableName());
1241.7.5 by Padraig O'Sullivan
Added the lock related dtrace probes to the cursor interface.
1408
    }
1409
    else if (lock_type == F_UNLCK)
1410
    {
1869.1.2 by Brian Aker
Remove table_share from being required in a cursor.
1411
      DRIZZLE_CURSOR_UNLOCK_START(getTable()->getShare()->getSchemaName(),
1412
                                  getTable()->getShare()->getTableName());
1241.7.5 by Padraig O'Sullivan
Added the lock related dtrace probes to the cursor interface.
1413
    }
1414
  }
1415
1 by brian
clean slate
1416
  /*
1417
    We cache the table flags if the locking succeeded. Otherwise, we
1418
    keep them as they were when they were fetched in ha_open().
1419
  */
1420
520.1.22 by Brian Aker
Second pass of thd cleanup
1421
  int error= external_lock(session, lock_type);
1126.10.11 by Padraig O'Sullivan
Added calls to the dtrace probes related to locks.
1422
1241.7.5 by Padraig O'Sullivan
Added the lock related dtrace probes to the cursor interface.
1423
  if (DRIZZLE_CURSOR_RDLOCK_DONE_ENABLED() ||
1424
      DRIZZLE_CURSOR_WRLOCK_DONE_ENABLED() ||
1425
      DRIZZLE_CURSOR_UNLOCK_DONE_ENABLED())
1426
  {
1427
    if (lock_type == F_RDLCK)
1428
    {
1429
      DRIZZLE_CURSOR_RDLOCK_DONE(error);
1430
    }
1431
    else if (lock_type == F_WRLCK)
1432
    {
1433
      DRIZZLE_CURSOR_WRLOCK_DONE(error);
1434
    }
1435
    else if (lock_type == F_UNLCK)
1436
    {
1437
      DRIZZLE_CURSOR_UNLOCK_DONE(error);
1438
    }
1439
  }
1440
1046.1.9 by Brian Aker
Remove caller that wasn't correctly locking, and reverted code to 5.1
1441
  return error;
1 by brian
clean slate
1442
}
1443
1444
1445
/**
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
1446
  Check Cursor usage and reset state of file to after 'open'
1 by brian
clean slate
1447
*/
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
1448
int Cursor::ha_reset()
1 by brian
clean slate
1449
{
1005.2.3 by Monty Taylor
Further reversion of P.
1450
  /* Check that we have called all proper deallocation functions */
1869.1.5 by Brian Aker
getTable()
1451
  assert(! getTable()->getShare()->all_set.none());
1452
  assert(getTable()->key_read == 0);
1491.1.10 by Jay Pipes
ha_rnd_init -> startTableScan, rnd_init -> doStartTableScan, ha_rnd_end -> endTableScan, rnd_end -> doEndTableScan
1453
  /* ensure that ha_index_end / endTableScan has been called */
51.1.77 by Jay Pipes
Standardized TRUE/FALSE, removed/replaced DBUG symbols
1454
  assert(inited == NONE);
1 by brian
clean slate
1455
  /* Free cache used by filesort */
1869.1.5 by Brian Aker
getTable()
1456
  getTable()->free_io_cache();
1 by brian
clean slate
1457
  /* reset the bitmaps to point to defaults */
1869.1.5 by Brian Aker
getTable()
1458
  getTable()->default_column_bitmaps();
51.1.77 by Jay Pipes
Standardized TRUE/FALSE, removed/replaced DBUG symbols
1459
  return(reset());
1 by brian
clean slate
1460
}
1461
1462
1491.1.2 by Jay Pipes
Cursor::write_row() -> Cursor::doInsertRecord(). Cursor::ha_write_row() -> Cursor::insertRecord()
1463
int Cursor::insertRecord(unsigned char *buf)
1 by brian
clean slate
1464
{
1465
  int error;
1466
1235.1.11 by Brian Aker
Small cleanups, did in MERGE table only engine flag.
1467
  /*
1468
   * If we have a timestamp column, update it to the current time
1469
   *
873.1.16 by Jay Pipes
This patch pulls the setting of the auto-set timestamp out of the individual
1470
   * @TODO Technically, the below two lines can be take even further out of the
1183.1.2 by Brian Aker
Rename of handler to Cursor. You would not believe how long I have wanted
1471
   * Cursor interface and into the fill_record() method.
873.1.16 by Jay Pipes
This patch pulls the setting of the auto-set timestamp out of the individual
1472
   */
1869.1.5 by Brian Aker
getTable()
1473
  if (getTable()->timestamp_field_type & TIMESTAMP_AUTO_SET_ON_INSERT)
1607 by Brian Aker
Cursor now fully handles the update to timestamp for the engine.
1474
  {
1869.1.5 by Brian Aker
getTable()
1475
    getTable()->timestamp_field->set_time();
1607 by Brian Aker
Cursor now fully handles the update to timestamp for the engine.
1476
  }
873.1.16 by Jay Pipes
This patch pulls the setting of the auto-set timestamp out of the individual
1477
1869.1.2 by Brian Aker
Remove table_share from being required in a cursor.
1478
  DRIZZLE_INSERT_ROW_START(getTable()->getShare()->getSchemaName(), getTable()->getShare()->getTableName());
1273.1.12 by Jay Pipes
Cleanup style and documentation for ResourceContext and setTransactionReadWrite
1479
  setTransactionReadWrite();
1502.5.2 by Barry.Leslie at PrimeBase
Changes made to drizzle source when building in the events plugin.
1480
  
1869.1.5 by Brian Aker
getTable()
1481
  if (unlikely(plugin::EventObserver::beforeInsertRecord(*getTable(), buf)))
1502.5.7 by Barry.Leslie at PrimeBase
Renamed the 'Event' plugin to 'EventObserver' plugin along with some internal class renames to make things clearer.
1482
  {
1483
    error= ER_EVENT_OBSERVER_PLUGIN;
1484
  }
1502.5.2 by Barry.Leslie at PrimeBase
Changes made to drizzle source when building in the events plugin.
1485
  else
1486
  {
1487
    error= doInsertRecord(buf);
1869.1.5 by Brian Aker
getTable()
1488
    if (unlikely(plugin::EventObserver::afterInsertRecord(*getTable(), buf, error))) 
1502.5.7 by Barry.Leslie at PrimeBase
Renamed the 'Event' plugin to 'EventObserver' plugin along with some internal class renames to make things clearer.
1489
    {
1490
      error= ER_EVENT_OBSERVER_PLUGIN;
1491
    }
1502.5.2 by Barry.Leslie at PrimeBase
Changes made to drizzle source when building in the events plugin.
1492
  }
1619.3.3 by Stewart Smith
move ha_statistic_increment for ha_write count (the Handler_write status variable) to the Cursor layer so that each Storage Engine's Cursor doesn't have to increment it.
1493
1494
  ha_statistic_increment(&system_status_var::ha_write_count);
1495
1241.7.4 by Padraig O'Sullivan
Inserted calls to the cursor related probes that fire on inserts, updates, and deletes.
1496
  DRIZZLE_INSERT_ROW_DONE(error);
1 by brian
clean slate
1497
1241.7.4 by Padraig O'Sullivan
Inserted calls to the cursor related probes that fire on inserts, updates, and deletes.
1498
  if (unlikely(error))
1126.10.17 by Padraig O'Sullivan
Added calls to the update related dtrace probes.
1499
  {
1046.1.9 by Brian Aker
Remove caller that wasn't correctly locking, and reverted code to 5.1
1500
    return error;
1126.10.17 by Padraig O'Sullivan
Added calls to the update related dtrace probes.
1501
  }
662 by Brian Aker
Remove dead methods.
1502
1869.1.5 by Brian Aker
getTable()
1503
  if (unlikely(log_row_for_replication(getTable(), NULL, buf)))
971.6.11 by Eric Day
Removed purecov messages.
1504
    return HA_ERR_RBR_LOGGING_FAILED;
662 by Brian Aker
Remove dead methods.
1505
1046.1.9 by Brian Aker
Remove caller that wasn't correctly locking, and reverted code to 5.1
1506
  return 0;
1 by brian
clean slate
1507
}
1508
1509
1491.1.3 by Jay Pipes
Cursor::update_row() changed to doUpdateRecord() and updateRecord()
1510
int Cursor::updateRecord(const unsigned char *old_data, unsigned char *new_data)
1 by brian
clean slate
1511
{
1512
  int error;
1513
1514
  /*
1672.3.6 by Brian Aker
First pass in encapsulating row
1515
    Some storage engines require that the new record is in getInsertRecord()
1516
    (and the old record is in getUpdateRecord()).
1 by brian
clean slate
1517
   */
1869.1.5 by Brian Aker
getTable()
1518
  assert(new_data == getTable()->getInsertRecord());
1 by brian
clean slate
1519
1869.1.2 by Brian Aker
Remove table_share from being required in a cursor.
1520
  DRIZZLE_UPDATE_ROW_START(getTable()->getShare()->getSchemaName(), getTable()->getShare()->getTableName());
1273.1.12 by Jay Pipes
Cleanup style and documentation for ResourceContext and setTransactionReadWrite
1521
  setTransactionReadWrite();
1869.1.5 by Brian Aker
getTable()
1522
  if (unlikely(plugin::EventObserver::beforeUpdateRecord(*getTable(), old_data, new_data)))
1502.5.7 by Barry.Leslie at PrimeBase
Renamed the 'Event' plugin to 'EventObserver' plugin along with some internal class renames to make things clearer.
1523
  {
1524
    error= ER_EVENT_OBSERVER_PLUGIN;
1525
  }
1502.5.2 by Barry.Leslie at PrimeBase
Changes made to drizzle source when building in the events plugin.
1526
  else
1527
  {
1869.1.5 by Brian Aker
getTable()
1528
    if (getTable()->timestamp_field_type & TIMESTAMP_AUTO_SET_ON_UPDATE)
1607 by Brian Aker
Cursor now fully handles the update to timestamp for the engine.
1529
    {
1869.1.5 by Brian Aker
getTable()
1530
      getTable()->timestamp_field->set_time();
1607 by Brian Aker
Cursor now fully handles the update to timestamp for the engine.
1531
    }
1532
1502.5.2 by Barry.Leslie at PrimeBase
Changes made to drizzle source when building in the events plugin.
1533
    error= doUpdateRecord(old_data, new_data);
1869.1.5 by Brian Aker
getTable()
1534
    if (unlikely(plugin::EventObserver::afterUpdateRecord(*getTable(), old_data, new_data, error)))
1502.5.7 by Barry.Leslie at PrimeBase
Renamed the 'Event' plugin to 'EventObserver' plugin along with some internal class renames to make things clearer.
1535
    {
1536
      error= ER_EVENT_OBSERVER_PLUGIN;
1537
    }
1502.5.2 by Barry.Leslie at PrimeBase
Changes made to drizzle source when building in the events plugin.
1538
  }
1539
1619.3.5 by Stewart Smith
move ha_statistic_increment for ha_update_count (the Handler_update status variable) to the Cursor layer so that each Storage Engine's Cursor doesn't have to increment it.
1540
  ha_statistic_increment(&system_status_var::ha_update_count);
1541
1241.7.4 by Padraig O'Sullivan
Inserted calls to the cursor related probes that fire on inserts, updates, and deletes.
1542
  DRIZZLE_UPDATE_ROW_DONE(error);
1 by brian
clean slate
1543
1241.7.4 by Padraig O'Sullivan
Inserted calls to the cursor related probes that fire on inserts, updates, and deletes.
1544
  if (unlikely(error))
1126.10.17 by Padraig O'Sullivan
Added calls to the update related dtrace probes.
1545
  {
1 by brian
clean slate
1546
    return error;
1126.10.17 by Padraig O'Sullivan
Added calls to the update related dtrace probes.
1547
  }
1548
1869.1.5 by Brian Aker
getTable()
1549
  if (unlikely(log_row_for_replication(getTable(), old_data, new_data)))
662 by Brian Aker
Remove dead methods.
1550
    return HA_ERR_RBR_LOGGING_FAILED;
1551
1 by brian
clean slate
1552
  return 0;
1553
}
1869.1.2 by Brian Aker
Remove table_share from being required in a cursor.
1554
TableShare *Cursor::getShare()
1555
{
1556
  return getTable()->getMutableShare();
1557
}
1 by brian
clean slate
1558
1491.1.4 by Jay Pipes
delete_row() is now deleteRecord() and doDeleteRecord() in Cursor
1559
int Cursor::deleteRecord(const unsigned char *buf)
1 by brian
clean slate
1560
{
1561
  int error;
1562
1869.1.2 by Brian Aker
Remove table_share from being required in a cursor.
1563
  DRIZZLE_DELETE_ROW_START(getTable()->getShare()->getSchemaName(), getTable()->getShare()->getTableName());
1273.1.12 by Jay Pipes
Cleanup style and documentation for ResourceContext and setTransactionReadWrite
1564
  setTransactionReadWrite();
1869.1.5 by Brian Aker
getTable()
1565
  if (unlikely(plugin::EventObserver::beforeDeleteRecord(*getTable(), buf)))
1502.5.7 by Barry.Leslie at PrimeBase
Renamed the 'Event' plugin to 'EventObserver' plugin along with some internal class renames to make things clearer.
1566
  {
1567
    error= ER_EVENT_OBSERVER_PLUGIN;
1568
  }
1502.5.2 by Barry.Leslie at PrimeBase
Changes made to drizzle source when building in the events plugin.
1569
  else
1570
  {
1571
    error= doDeleteRecord(buf);
1869.1.5 by Brian Aker
getTable()
1572
    if (unlikely(plugin::EventObserver::afterDeleteRecord(*getTable(), buf, error)))
1502.5.7 by Barry.Leslie at PrimeBase
Renamed the 'Event' plugin to 'EventObserver' plugin along with some internal class renames to make things clearer.
1573
    {
1574
      error= ER_EVENT_OBSERVER_PLUGIN;
1575
    }
1502.5.2 by Barry.Leslie at PrimeBase
Changes made to drizzle source when building in the events plugin.
1576
  }
1577
1619.3.7 by Stewart Smith
move ha_statistic_increment for ha_delete_count (the Handler_delete status variable) to the Cursor layer so that each Storage Engine's Cursor doesn't have to increment it.
1578
  ha_statistic_increment(&system_status_var::ha_delete_count);
1579
1241.7.4 by Padraig O'Sullivan
Inserted calls to the cursor related probes that fire on inserts, updates, and deletes.
1580
  DRIZZLE_DELETE_ROW_DONE(error);
1 by brian
clean slate
1581
1241.7.4 by Padraig O'Sullivan
Inserted calls to the cursor related probes that fire on inserts, updates, and deletes.
1582
  if (unlikely(error))
1 by brian
clean slate
1583
    return error;
662 by Brian Aker
Remove dead methods.
1584
1869.1.5 by Brian Aker
getTable()
1585
  if (unlikely(log_row_for_replication(getTable(), buf, NULL)))
662 by Brian Aker
Remove dead methods.
1586
    return HA_ERR_RBR_LOGGING_FAILED;
1587
1 by brian
clean slate
1588
  return 0;
1589
}
1280.1.10 by Monty Taylor
Put everything in drizzled into drizzled namespace.
1590
1591
} /* namespace drizzled */