~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to drizzled/handler.cc

  • Committer: Monty Taylor
  • Date: 2008-10-16 06:32:30 UTC
  • mto: (511.1.5 codestyle)
  • mto: This revision was merged to the branch mainline in revision 521.
  • Revision ID: monty@inaugust.com-20081016063230-4brxsra0qsmsg84q
Added -Wunused-macros.

Show diffs side-by-side

added added

removed removed

Lines of Context:
19
19
  Handler-calling-functions
20
20
*/
21
21
 
22
 
#ifdef USE_PRAGMA_IMPLEMENTATION
23
 
#pragma implementation                          // gcc: Class implementation
24
 
#endif
25
 
 
26
 
#include "mysql_priv.h"
 
22
#include <drizzled/server_includes.h>
27
23
#include "rpl_filter.h"
28
 
#include <myisampack.h>
29
 
#include <errno.h>
 
24
#include <drizzled/drizzled_error_messages.h>
30
25
 
31
26
/*
32
27
  While we have legacy_db_type, we have this array to
39
34
 
40
35
#define BITMAP_STACKBUF_SIZE (128/8)
41
36
 
42
 
KEY_CREATE_INFO default_key_create_info= { HA_KEY_ALG_UNDEF, 0, {NullS,0}, {NullS,0} };
 
37
KEY_CREATE_INFO default_key_create_info= { HA_KEY_ALG_UNDEF, 0, {NULL,0}, {NULL,0} };
43
38
 
44
39
/* number of entries in handlertons[] */
45
 
ulong total_ha= 0;
 
40
uint32_t total_ha= 0;
46
41
/* number of storage engines (from handlertons[]) that support 2pc */
47
 
ulong total_ha_2pc= 0;
 
42
uint32_t total_ha_2pc= 0;
48
43
/* size of savepoint storage area (see ha_init) */
49
 
ulong savepoint_alloc_size= 0;
 
44
uint32_t savepoint_alloc_size= 0;
50
45
 
51
46
static const LEX_STRING sys_table_aliases[]=
52
47
{
53
48
  { C_STRING_WITH_LEN("INNOBASE") },  { C_STRING_WITH_LEN("INNODB") },
54
49
  { C_STRING_WITH_LEN("HEAP") },      { C_STRING_WITH_LEN("MEMORY") },
55
 
  {NullS, 0}
 
50
  {NULL, 0}
56
51
};
57
52
 
58
53
const char *ha_row_type[] = {
61
56
 
62
57
const char *tx_isolation_names[] =
63
58
{ "READ-UNCOMMITTED", "READ-COMMITTED", "REPEATABLE-READ", "SERIALIZABLE",
64
 
  NullS};
 
59
  NULL};
65
60
TYPELIB tx_isolation_typelib= {array_elements(tx_isolation_names)-1,"",
66
61
                               tx_isolation_names, NULL};
67
62
 
68
63
static TYPELIB known_extensions= {0,"known_exts", NULL, NULL};
69
 
uint known_extensions_id= 0;
 
64
uint32_t known_extensions_id= 0;
70
65
 
71
66
 
72
67
 
90
85
handlerton *ha_default_handlerton(THD *thd)
91
86
{
92
87
  plugin_ref plugin= ha_default_plugin(thd);
93
 
  DBUG_ASSERT(plugin);
 
88
  assert(plugin);
94
89
  handlerton *hton= plugin_data(plugin, handlerton*);
95
 
  DBUG_ASSERT(hton);
 
90
  assert(hton);
96
91
  return hton;
97
92
}
98
93
 
113
108
 
114
109
redo:
115
110
  /* my_strnncoll is a macro and gcc doesn't do early expansion of macro */
116
 
  if (thd && !my_charset_latin1.coll->strnncoll(&my_charset_latin1,
117
 
                           (const uchar *)name->str, name->length,
118
 
                           (const uchar *)STRING_WITH_LEN("DEFAULT"), 0))
 
111
  if (thd && !my_charset_utf8_general_ci.coll->strnncoll(&my_charset_utf8_general_ci,
 
112
                           (const unsigned char *)name->str, name->length,
 
113
                           (const unsigned char *)STRING_WITH_LEN("DEFAULT"), 0))
119
114
    return ha_default_plugin(thd);
120
115
 
121
 
  if ((plugin= my_plugin_lock_by_name(thd, name, MYSQL_STORAGE_ENGINE_PLUGIN)))
 
116
  if ((plugin= my_plugin_lock_by_name(thd, name, DRIZZLE_STORAGE_ENGINE_PLUGIN)))
122
117
  {
123
118
    handlerton *hton= plugin_data(plugin, handlerton *);
124
119
    if (!(hton->flags & HTON_NOT_USER_SELECTABLE))
135
130
  */
136
131
  for (table_alias= sys_table_aliases; table_alias->str; table_alias+= 2)
137
132
  {
138
 
    if (!my_strnncoll(&my_charset_latin1,
139
 
                      (const uchar *)name->str, name->length,
140
 
                      (const uchar *)table_alias->str, table_alias->length))
 
133
    if (!my_strnncoll(&my_charset_utf8_general_ci,
 
134
                      (const unsigned char *)name->str, name->length,
 
135
                      (const unsigned char *)table_alias->str, table_alias->length))
141
136
    {
142
137
      name= table_alias + 1;
143
138
      goto redo;
154
149
  {
155
150
    st_plugin_int **plugin= hton2plugin + hton->slot;
156
151
    
157
 
#ifdef DBUG_OFF
158
 
    return my_plugin_lock(thd, plugin);
159
 
#else
160
152
    return my_plugin_lock(thd, &plugin);
161
 
#endif
162
153
  }
163
154
  return NULL;
164
155
}
201
192
    return NULL;
202
193
  }
203
194
 
204
 
  switch (database_type) {
205
 
  case DB_TYPE_HASH:
206
 
    return ha_resolve_by_legacy_type(thd, DB_TYPE_HASH);
207
 
  default:
208
 
    break;
209
 
  }
210
 
 
211
195
  return ha_default_handlerton(thd);
212
196
} /* ha_checktype */
213
197
 
216
200
                         handlerton *db_type)
217
201
{
218
202
  handler *file;
219
 
  DBUG_ENTER("get_new_handler");
220
 
  DBUG_PRINT("enter", ("alloc: 0x%lx", (long) alloc));
221
203
 
222
204
  if (db_type && db_type->state == SHOW_OPTION_YES && db_type->create)
223
205
  {
224
206
    if ((file= db_type->create(db_type, share, alloc)))
225
207
      file->init();
226
 
    DBUG_RETURN(file);
 
208
    return(file);
227
209
  }
228
210
  /*
229
211
    Try the default table type
230
212
    Here the call to current_thd() is ok as we call this function a lot of
231
213
    times but we enter this branch very seldom.
232
214
  */
233
 
  DBUG_RETURN(get_new_handler(share, alloc, ha_default_handlerton(current_thd)));
 
215
  return(get_new_handler(share, alloc, ha_default_handlerton(current_thd)));
234
216
}
235
217
 
236
218
 
317
299
  /* Allocate a pointer array for the error message strings. */
318
300
  if (! (errmsgs= my_error_unregister(HA_ERR_FIRST, HA_ERR_LAST)))
319
301
    return 1;
320
 
  my_free((uchar*) errmsgs, MYF(0));
 
302
  free((unsigned char*) errmsgs);
321
303
  return 0;
322
304
}
323
305
 
325
307
int ha_finalize_handlerton(st_plugin_int *plugin)
326
308
{
327
309
  handlerton *hton= (handlerton *)plugin->data;
328
 
  DBUG_ENTER("ha_finalize_handlerton");
329
310
 
330
311
  switch (hton->state)
331
312
  {
338
319
    break;
339
320
  };
340
321
 
341
 
  if (hton->panic)
342
 
    hton->panic(hton, HA_PANIC_CLOSE);
343
 
 
344
 
  if (plugin->plugin->deinit)
345
 
  {
346
 
    /*
347
 
      Today we have no defined/special behavior for uninstalling
348
 
      engine plugins.
349
 
    */
350
 
    DBUG_PRINT("info", ("Deinitializing plugin: '%s'", plugin->name.str));
351
 
    if (plugin->plugin->deinit(NULL))
352
 
    {
353
 
      DBUG_PRINT("warning", ("Plugin '%s' deinit function returned error.",
354
 
                             plugin->name.str));
355
 
    }
356
 
  }
357
 
 
358
 
  my_free((uchar*)hton, MYF(0));
359
 
 
360
 
  DBUG_RETURN(0);
 
322
  if (hton && plugin->plugin->deinit)
 
323
    (void)plugin->plugin->deinit(hton);
 
324
 
 
325
  free((unsigned char*)hton);
 
326
 
 
327
  return(0);
361
328
}
362
329
 
363
330
 
364
331
int ha_initialize_handlerton(st_plugin_int *plugin)
365
332
{
366
333
  handlerton *hton;
367
 
  DBUG_ENTER("ha_initialize_handlerton");
368
 
  DBUG_PRINT("plugin", ("initialize plugin: '%s'", plugin->name.str));
369
334
 
370
335
  hton= (handlerton *)my_malloc(sizeof(handlerton),
371
336
                                MYF(MY_WME | MY_ZEROFILL));
376
341
    structure. Apparently get_backup_engine was not NULL even though it was
377
342
    not initialized.
378
343
   */
379
 
  bzero(hton, sizeof(hton));
 
344
  memset(hton, 0, sizeof(hton));
380
345
  /* Historical Requirement */
381
346
  plugin->data= hton; // shortcut for the future
382
347
  if (plugin->plugin->init)
383
348
  {
384
349
    if (plugin->plugin->init(hton))
385
350
    {
386
 
      sql_print_error("Plugin '%s' init function returned error.",
 
351
      sql_print_error(_("Plugin '%s' init function returned error."),
387
352
                      plugin->name.str);
388
353
      goto err;
389
354
    }
398
363
    break;
399
364
  case SHOW_OPTION_YES:
400
365
    {
401
 
      uint tmp;
 
366
      uint32_t tmp;
402
367
      /* now check the db_type for conflict */
403
368
      if (hton->db_type <= DB_TYPE_UNKNOWN ||
404
369
          hton->db_type >= DB_TYPE_DEFAULT ||
411
376
 
412
377
        if (idx == (int) DB_TYPE_DEFAULT)
413
378
        {
414
 
          sql_print_warning("Too many storage engines!");
415
 
          DBUG_RETURN(1);
 
379
          sql_print_warning(_("Too many storage engines!"));
 
380
          return(1);
416
381
        }
417
382
        if (hton->db_type != DB_TYPE_UNKNOWN)
418
 
          sql_print_warning("Storage engine '%s' has conflicting typecode. "
419
 
                            "Assigning value %d.", plugin->plugin->name, idx);
 
383
          sql_print_warning(_("Storage engine '%s' has conflicting typecode. "
 
384
                            "Assigning value %d."), plugin->plugin->name, idx);
420
385
        hton->db_type= (enum legacy_db_type) idx;
421
386
      }
422
387
      installed_htons[hton->db_type]= hton;
440
405
    "memory" hton which will be configurable longterm. We should be able to 
441
406
    remove partition and myisammrg.
442
407
  */
443
 
  switch (hton->db_type) {
444
 
  case DB_TYPE_HEAP:
 
408
  if (strcmp(plugin->plugin->name, "MEMORY") == 0)
445
409
    heap_hton= hton;
446
 
    break;
447
 
  case DB_TYPE_MYISAM:
 
410
 
 
411
  if (strcmp(plugin->plugin->name, "MyISAM") == 0)
448
412
    myisam_hton= hton;
449
 
    break;
450
 
  default:
451
 
    break;
452
 
  };
453
413
 
454
 
  DBUG_RETURN(0);
 
414
  return(0);
455
415
err:
456
 
  DBUG_RETURN(1);
 
416
  return(1);
457
417
}
458
418
 
459
419
int ha_init()
460
420
{
461
421
  int error= 0;
462
 
  DBUG_ENTER("ha_init");
463
422
 
464
 
  DBUG_ASSERT(total_ha < MAX_HA);
 
423
  assert(total_ha < MAX_HA);
465
424
  /*
466
425
    Check if there is a transaction-capable storage engine besides the
467
426
    binary log (which is considered a transaction-capable storage engine in
468
427
    counting total_ha)
469
428
  */
470
 
  opt_using_transactions= total_ha>(ulong)opt_bin_log;
 
429
  opt_using_transactions= total_ha>(uint32_t)opt_bin_log;
471
430
  savepoint_alloc_size+= sizeof(SAVEPOINT);
472
 
  DBUG_RETURN(error);
 
431
  return(error);
473
432
}
474
433
 
475
434
int ha_end()
476
435
{
477
436
  int error= 0;
478
 
  DBUG_ENTER("ha_end");
479
 
 
480
437
 
481
438
  /* 
482
439
    This should be eventualy based  on the graceful shutdown flag.
486
443
  if (ha_finish_errors())
487
444
    error= 1;
488
445
 
489
 
  DBUG_RETURN(error);
 
446
  return(error);
490
447
}
491
448
 
492
 
static my_bool dropdb_handlerton(THD *unused1, plugin_ref plugin,
493
 
                                 void *path)
 
449
static bool dropdb_handlerton(THD *unused1 __attribute__((unused)),
 
450
                              plugin_ref plugin,
 
451
                              void *path)
494
452
{
495
453
  handlerton *hton= plugin_data(plugin, handlerton *);
496
454
  if (hton->state == SHOW_OPTION_YES && hton->drop_database)
497
455
    hton->drop_database(hton, (char *)path);
498
 
  return FALSE;
 
456
  return false;
499
457
}
500
458
 
501
459
 
502
460
void ha_drop_database(char* path)
503
461
{
504
 
  plugin_foreach(NULL, dropdb_handlerton, MYSQL_STORAGE_ENGINE_PLUGIN, path);
 
462
  plugin_foreach(NULL, dropdb_handlerton, DRIZZLE_STORAGE_ENGINE_PLUGIN, path);
505
463
}
506
464
 
507
465
 
508
 
static my_bool closecon_handlerton(THD *thd, plugin_ref plugin,
509
 
                                   void *unused)
 
466
static bool closecon_handlerton(THD *thd, plugin_ref plugin,
 
467
                                void *unused __attribute__((unused)))
510
468
{
511
469
  handlerton *hton= plugin_data(plugin, handlerton *);
512
470
  /*
516
474
  if (hton->state == SHOW_OPTION_YES && hton->close_connection &&
517
475
      thd_get_ha_data(thd, hton))
518
476
    hton->close_connection(hton, thd);
519
 
  return FALSE;
 
477
  return false;
520
478
}
521
479
 
522
480
 
526
484
*/
527
485
void ha_close_connection(THD* thd)
528
486
{
529
 
  plugin_foreach(thd, closecon_handlerton, MYSQL_STORAGE_ENGINE_PLUGIN, 0);
 
487
  plugin_foreach(thd, closecon_handlerton, DRIZZLE_STORAGE_ENGINE_PLUGIN, 0);
530
488
}
531
489
 
532
490
/* ========================================================================
802
760
  to maintain atomicity: if CREATE TABLE .. SELECT failed,
803
761
  the newly created table is deleted.
804
762
  In addition, some DDL statements issue interim transaction
805
 
  commits: e.g. ALTER TABLE issues a commit after data is copied
 
763
  commits: e.g. ALTER Table issues a commit after data is copied
806
764
  from the original table to the internal temporary table. Other
807
765
  statements, e.g. CREATE TABLE ... SELECT do not always commit
808
766
  after itself.
809
767
  And finally there is a group of DDL statements such as
810
 
  RENAME/DROP TABLE that doesn't start a new transaction
 
768
  RENAME/DROP Table that doesn't start a new transaction
811
769
  and doesn't commit.
812
770
 
813
771
  This diversity makes it hard to say what will happen if
839
797
{
840
798
  THD_TRANS *trans;
841
799
  Ha_trx_info *ha_info;
842
 
  DBUG_ENTER("trans_register_ha");
843
 
  DBUG_PRINT("enter",("%s", all ? "all" : "stmt"));
844
800
 
845
801
  if (all)
846
802
  {
853
809
  ha_info= thd->ha_data[ht_arg->slot].ha_info + static_cast<unsigned>(all);
854
810
 
855
811
  if (ha_info->is_started())
856
 
    DBUG_VOID_RETURN; /* already registered, return */
 
812
    return; /* already registered, return */
857
813
 
858
814
  ha_info->register_ha(trans, ht_arg);
859
815
 
861
817
  if (thd->transaction.xid_state.xid.is_null())
862
818
    thd->transaction.xid_state.xid.set(thd->query_id);
863
819
 
864
 
  DBUG_VOID_RETURN;
 
820
  return;
865
821
}
866
822
 
867
823
/**
875
831
  int error=0, all=1;
876
832
  THD_TRANS *trans=all ? &thd->transaction.all : &thd->transaction.stmt;
877
833
  Ha_trx_info *ha_info= trans->ha_list;
878
 
  DBUG_ENTER("ha_prepare");
879
834
  if (ha_info)
880
835
  {
881
836
    for (; ha_info; ha_info= ha_info->next())
895
850
      }
896
851
      else
897
852
      {
898
 
        push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_WARN,
 
853
        push_warning_printf(thd, DRIZZLE_ERROR::WARN_LEVEL_WARN,
899
854
                            ER_ILLEGAL_HA, ER(ER_ILLEGAL_HA),
900
855
                            ha_resolve_storage_engine_name(ht));
901
856
      }
902
857
    }
903
858
  }
904
 
  DBUG_RETURN(error);
 
859
  return(error);
905
860
}
906
861
 
907
862
/**
911
866
  As a side effect, propagates the read-only/read-write flags
912
867
  of the statement transaction to its enclosing normal transaction.
913
868
 
914
 
  @retval TRUE   we must run a two-phase commit. Returned
 
869
  @retval true   we must run a two-phase commit. Returned
915
870
                 if we have at least two engines with read-write changes.
916
 
  @retval FALSE  Don't need two-phase commit. Even if we have two
 
871
  @retval false  Don't need two-phase commit. Even if we have two
917
872
                 transactional engines, we can run two independent
918
873
                 commits if changes in one of the engines are read-only.
919
874
*/
935
890
    if (! all)
936
891
    {
937
892
      Ha_trx_info *ha_info_all= &thd->ha_data[ha_info->ht()->slot].ha_info[1];
938
 
      DBUG_ASSERT(ha_info != ha_info_all);
 
893
      assert(ha_info != ha_info_all);
939
894
      /*
940
895
        Merge read-only/read-write information about statement
941
896
        transaction to its enclosing normal transaction. Do this
943
898
        that ha_info_all is registered in thd->transaction.all.
944
899
        Since otherwise we only clutter the normal transaction flags.
945
900
      */
946
 
      if (ha_info_all->is_started()) /* FALSE if autocommit. */
 
901
      if (ha_info_all->is_started()) /* false if autocommit. */
947
902
        ha_info_all->coalesce_trx_with(ha_info);
948
903
    }
949
904
    else if (rw_ha_count > 1)
985
940
  bool is_real_trans= all || thd->transaction.all.ha_list == 0;
986
941
  Ha_trx_info *ha_info= trans->ha_list;
987
942
  my_xid xid= thd->transaction.xid_state.xid.get_my_xid();
988
 
  DBUG_ENTER("ha_commit_trans");
989
943
 
990
944
  /*
991
945
    We must not commit the normal transaction if a statement
993
947
    flags will not get propagated to its normal transaction's
994
948
    counterpart.
995
949
  */
996
 
  DBUG_ASSERT(thd->transaction.stmt.ha_list == NULL ||
 
950
  assert(thd->transaction.stmt.ha_list == NULL ||
997
951
              trans == &thd->transaction.stmt);
998
952
 
999
 
  if (thd->in_sub_stmt)
1000
 
  {
1001
 
    /*
1002
 
      Since we don't support nested statement transactions in 5.0,
1003
 
      we can't commit or rollback stmt transactions while we are inside
1004
 
      stored functions or triggers. So we simply do nothing now.
1005
 
      TODO: This should be fixed in later ( >= 5.1) releases.
1006
 
    */
1007
 
    if (!all)
1008
 
      DBUG_RETURN(0);
1009
 
    /*
1010
 
      We assume that all statements which commit or rollback main transaction
1011
 
      are prohibited inside of stored functions or triggers. So they should
1012
 
      bail out with error even before ha_commit_trans() call. To be 100% safe
1013
 
      let us throw error in non-debug builds.
1014
 
    */
1015
 
    DBUG_ASSERT(0);
1016
 
    my_error(ER_COMMIT_NOT_ALLOWED_IN_SF_OR_TRG, MYF(0));
1017
 
    DBUG_RETURN(2);
1018
 
  }
1019
953
  if (ha_info)
1020
954
  {
1021
955
    bool must_2pc;
1023
957
    if (is_real_trans && wait_if_global_read_lock(thd, 0, 0))
1024
958
    {
1025
959
      ha_rollback_trans(thd, all);
1026
 
      DBUG_RETURN(1);
 
960
      return(1);
1027
961
    }
1028
962
 
1029
963
    if (   is_real_trans
1063
997
        }
1064
998
        status_var_increment(thd->status_var.ha_prepare_count);
1065
999
      }
1066
 
      DBUG_EXECUTE_IF("crash_commit_after_prepare", abort(););
1067
1000
      if (error || (is_real_trans && xid &&
1068
1001
                    (error= !(cookie= tc_log->log_xid(thd, xid)))))
1069
1002
      {
1071
1004
        error= 1;
1072
1005
        goto end;
1073
1006
      }
1074
 
      DBUG_EXECUTE_IF("crash_commit_after_log", abort(););
1075
1007
    }
1076
1008
    error=ha_commit_one_phase(thd, all) ? (cookie ? 2 : 1) : 0;
1077
 
    DBUG_EXECUTE_IF("crash_commit_before_unlog", abort(););
1078
1009
    if (cookie)
1079
1010
      tc_log->unlog(cookie, xid);
1080
 
    DBUG_EXECUTE_IF("crash_commit_after", abort(););
1081
1011
end:
1082
1012
    if (is_real_trans)
1083
1013
      start_waiting_global_read_lock(thd);
1084
1014
  }
1085
 
  DBUG_RETURN(error);
 
1015
  return(error);
1086
1016
}
1087
1017
 
1088
1018
/**
1095
1025
  THD_TRANS *trans=all ? &thd->transaction.all : &thd->transaction.stmt;
1096
1026
  bool is_real_trans=all || thd->transaction.all.ha_list == 0;
1097
1027
  Ha_trx_info *ha_info= trans->ha_list, *ha_info_next;
1098
 
  DBUG_ENTER("ha_commit_one_phase");
1099
1028
  if (ha_info)
1100
1029
  {
1101
1030
    for (; ha_info; ha_info= ha_info_next)
1121
1050
      thd->transaction.cleanup();
1122
1051
    }
1123
1052
  }
1124
 
  DBUG_RETURN(error);
 
1053
  return(error);
1125
1054
}
1126
1055
 
1127
1056
 
1131
1060
  THD_TRANS *trans=all ? &thd->transaction.all : &thd->transaction.stmt;
1132
1061
  Ha_trx_info *ha_info= trans->ha_list, *ha_info_next;
1133
1062
  bool is_real_trans=all || thd->transaction.all.ha_list == 0;
1134
 
  DBUG_ENTER("ha_rollback_trans");
1135
1063
 
1136
1064
  /*
1137
1065
    We must not rollback the normal transaction if a statement
1138
1066
    transaction is pending.
1139
1067
  */
1140
 
  DBUG_ASSERT(thd->transaction.stmt.ha_list == NULL ||
 
1068
  assert(thd->transaction.stmt.ha_list == NULL ||
1141
1069
              trans == &thd->transaction.stmt);
1142
1070
 
1143
 
  if (thd->in_sub_stmt)
1144
 
  {
1145
 
    /*
1146
 
      If we are inside stored function or trigger we should not commit or
1147
 
      rollback current statement transaction. See comment in ha_commit_trans()
1148
 
      call for more information.
1149
 
    */
1150
 
    if (!all)
1151
 
      DBUG_RETURN(0);
1152
 
    DBUG_ASSERT(0);
1153
 
    my_error(ER_COMMIT_NOT_ALLOWED_IN_SF_OR_TRG, MYF(0));
1154
 
    DBUG_RETURN(1);
1155
 
  }
1156
1071
  if (ha_info)
1157
1072
  {
1158
1073
    for (; ha_info; ha_info= ha_info_next)
1179
1094
    }
1180
1095
  }
1181
1096
  if (all)
1182
 
    thd->transaction_rollback_request= FALSE;
 
1097
    thd->transaction_rollback_request= false;
1183
1098
 
1184
1099
  /*
1185
1100
    If a non-transactional table was updated, warn; don't warn if this is a
1192
1107
  */
1193
1108
  if (is_real_trans && thd->transaction.all.modified_non_trans_table &&
1194
1109
      !thd->slave_thread && thd->killed != THD::KILL_CONNECTION)
1195
 
    push_warning(thd, MYSQL_ERROR::WARN_LEVEL_WARN,
 
1110
    push_warning(thd, DRIZZLE_ERROR::WARN_LEVEL_WARN,
1196
1111
                 ER_WARNING_NOT_COMPLETE_ROLLBACK,
1197
1112
                 ER(ER_WARNING_NOT_COMPLETE_ROLLBACK));
1198
 
  DBUG_RETURN(error);
 
1113
  return(error);
1199
1114
}
1200
1115
 
1201
1116
/**
1211
1126
*/
1212
1127
int ha_autocommit_or_rollback(THD *thd, int error)
1213
1128
{
1214
 
  DBUG_ENTER("ha_autocommit_or_rollback");
1215
1129
  if (thd->transaction.stmt.ha_list)
1216
1130
  {
1217
1131
    if (!error)
1222
1136
    else 
1223
1137
    {
1224
1138
      (void) ha_rollback_trans(thd, 0);
1225
 
      if (thd->transaction_rollback_request && !thd->in_sub_stmt)
 
1139
      if (thd->transaction_rollback_request)
1226
1140
        (void) ha_rollback(thd);
1227
1141
    }
1228
1142
 
1229
1143
    thd->variables.tx_isolation=thd->session_tx_isolation;
1230
1144
  }
1231
 
  DBUG_RETURN(error);
 
1145
  return(error);
1232
1146
}
1233
1147
 
1234
1148
 
1237
1151
  int result;
1238
1152
};
1239
1153
 
1240
 
static my_bool xacommit_handlerton(THD *unused1, plugin_ref plugin,
1241
 
                                   void *arg)
 
1154
static bool xacommit_handlerton(THD *unused1 __attribute__((unused)),
 
1155
                                plugin_ref plugin,
 
1156
                                void *arg)
1242
1157
{
1243
1158
  handlerton *hton= plugin_data(plugin, handlerton *);
1244
1159
  if (hton->state == SHOW_OPTION_YES && hton->recover)
1246
1161
    hton->commit_by_xid(hton, ((struct xahton_st *)arg)->xid);
1247
1162
    ((struct xahton_st *)arg)->result= 0;
1248
1163
  }
1249
 
  return FALSE;
 
1164
  return false;
1250
1165
}
1251
1166
 
1252
 
static my_bool xarollback_handlerton(THD *unused1, plugin_ref plugin,
1253
 
                                     void *arg)
 
1167
static bool xarollback_handlerton(THD *unused1 __attribute__((unused)),
 
1168
                                  plugin_ref plugin,
 
1169
                                  void *arg)
1254
1170
{
1255
1171
  handlerton *hton= plugin_data(plugin, handlerton *);
1256
1172
  if (hton->state == SHOW_OPTION_YES && hton->recover)
1258
1174
    hton->rollback_by_xid(hton, ((struct xahton_st *)arg)->xid);
1259
1175
    ((struct xahton_st *)arg)->result= 0;
1260
1176
  }
1261
 
  return FALSE;
 
1177
  return false;
1262
1178
}
1263
1179
 
1264
1180
 
1269
1185
  xaop.result= 1;
1270
1186
 
1271
1187
  plugin_foreach(NULL, commit ? xacommit_handlerton : xarollback_handlerton,
1272
 
                 MYSQL_STORAGE_ENGINE_PLUGIN, &xaop);
 
1188
                 DRIZZLE_STORAGE_ENGINE_PLUGIN, &xaop);
1273
1189
 
1274
1190
  return xaop.result;
1275
1191
}
1276
1192
 
1277
 
 
1278
 
#ifndef DBUG_OFF
1279
 
/**
1280
 
  @note
1281
 
    This does not need to be multi-byte safe or anything
1282
 
*/
1283
 
static char* xid_to_str(char *buf, XID *xid)
1284
 
{
1285
 
  int i;
1286
 
  char *s=buf;
1287
 
  *s++='\'';
1288
 
  for (i=0; i < xid->gtrid_length+xid->bqual_length; i++)
1289
 
  {
1290
 
    uchar c=(uchar)xid->data[i];
1291
 
    /* is_next_dig is set if next character is a number */
1292
 
    bool is_next_dig= FALSE;
1293
 
    if (i < XIDDATASIZE)
1294
 
    {
1295
 
      char ch= xid->data[i+1];
1296
 
      is_next_dig= (ch >= '0' && ch <='9');
1297
 
    }
1298
 
    if (i == xid->gtrid_length)
1299
 
    {
1300
 
      *s++='\'';
1301
 
      if (xid->bqual_length)
1302
 
      {
1303
 
        *s++='.';
1304
 
        *s++='\'';
1305
 
      }
1306
 
    }
1307
 
    if (c < 32 || c > 126)
1308
 
    {
1309
 
      *s++='\\';
1310
 
      /*
1311
 
        If next character is a number, write current character with
1312
 
        3 octal numbers to ensure that the next number is not seen
1313
 
        as part of the octal number
1314
 
      */
1315
 
      if (c > 077 || is_next_dig)
1316
 
        *s++=_dig_vec_lower[c >> 6];
1317
 
      if (c > 007 || is_next_dig)
1318
 
        *s++=_dig_vec_lower[(c >> 3) & 7];
1319
 
      *s++=_dig_vec_lower[c & 7];
1320
 
    }
1321
 
    else
1322
 
    {
1323
 
      if (c == '\'' || c == '\\')
1324
 
        *s++='\\';
1325
 
      *s++=c;
1326
 
    }
1327
 
  }
1328
 
  *s++='\'';
1329
 
  *s=0;
1330
 
  return buf;
1331
 
}
1332
 
#endif
1333
 
 
1334
1193
/**
1335
1194
  recover() step of xa.
1336
1195
 
1355
1214
  bool dry_run;
1356
1215
};
1357
1216
 
1358
 
static my_bool xarecover_handlerton(THD *unused, plugin_ref plugin,
1359
 
                                    void *arg)
 
1217
static bool xarecover_handlerton(THD *unused __attribute__((unused)),
 
1218
                                 plugin_ref plugin,
 
1219
                                 void *arg)
1360
1220
{
1361
1221
  handlerton *hton= plugin_data(plugin, handlerton *);
1362
1222
  struct xarecover_st *info= (struct xarecover_st *) arg;
1366
1226
  {
1367
1227
    while ((got= hton->recover(hton, info->list, info->len)) > 0 )
1368
1228
    {
1369
 
      sql_print_information("Found %d prepared transaction(s) in %s",
 
1229
      sql_print_information(_("Found %d prepared transaction(s) in %s"),
1370
1230
                            got, ha_resolve_storage_engine_name(hton));
1371
1231
      for (int i=0; i < got; i ++)
1372
1232
      {
1373
1233
        my_xid x=info->list[i].get_my_xid();
1374
1234
        if (!x) // not "mine" - that is generated by external TM
1375
1235
        {
1376
 
#ifndef DBUG_OFF
1377
 
          char buf[XIDDATASIZE*4+6]; // see xid_to_str
1378
 
          sql_print_information("ignore xid %s", xid_to_str(buf, info->list+i));
1379
 
#endif
1380
1236
          xid_cache_insert(info->list+i, XA_PREPARED);
1381
1237
          info->found_foreign_xids++;
1382
1238
          continue;
1388
1244
        }
1389
1245
        // recovery mode
1390
1246
        if (info->commit_list ?
1391
 
            hash_search(info->commit_list, (uchar *)&x, sizeof(x)) != 0 :
 
1247
            hash_search(info->commit_list, (unsigned char *)&x, sizeof(x)) != 0 :
1392
1248
            tc_heuristic_recover == TC_HEURISTIC_RECOVER_COMMIT)
1393
1249
        {
1394
 
#ifndef DBUG_OFF
1395
 
          char buf[XIDDATASIZE*4+6]; // see xid_to_str
1396
 
          sql_print_information("commit xid %s", xid_to_str(buf, info->list+i));
1397
 
#endif
1398
1250
          hton->commit_by_xid(hton, info->list+i);
1399
1251
        }
1400
1252
        else
1401
1253
        {
1402
 
#ifndef DBUG_OFF
1403
 
          char buf[XIDDATASIZE*4+6]; // see xid_to_str
1404
 
          sql_print_information("rollback xid %s",
1405
 
                                xid_to_str(buf, info->list+i));
1406
 
#endif
1407
1254
          hton->rollback_by_xid(hton, info->list+i);
1408
1255
        }
1409
1256
      }
1411
1258
        break;
1412
1259
    }
1413
1260
  }
1414
 
  return FALSE;
 
1261
  return false;
1415
1262
}
1416
1263
 
1417
1264
int ha_recover(HASH *commit_list)
1418
1265
{
1419
1266
  struct xarecover_st info;
1420
 
  DBUG_ENTER("ha_recover");
1421
1267
  info.found_foreign_xids= info.found_my_xids= 0;
1422
1268
  info.commit_list= commit_list;
1423
1269
  info.dry_run= (info.commit_list==0 && tc_heuristic_recover==0);
1424
1270
  info.list= NULL;
1425
1271
 
1426
1272
  /* commit_list and tc_heuristic_recover cannot be set both */
1427
 
  DBUG_ASSERT(info.commit_list==0 || tc_heuristic_recover==0);
 
1273
  assert(info.commit_list==0 || tc_heuristic_recover==0);
1428
1274
  /* if either is set, total_ha_2pc must be set too */
1429
 
  DBUG_ASSERT(info.dry_run || total_ha_2pc>(ulong)opt_bin_log);
 
1275
  assert(info.dry_run || total_ha_2pc>(uint32_t)opt_bin_log);
1430
1276
 
1431
 
  if (total_ha_2pc <= (ulong)opt_bin_log)
1432
 
    DBUG_RETURN(0);
 
1277
  if (total_ha_2pc <= (uint32_t)opt_bin_log)
 
1278
    return(0);
1433
1279
 
1434
1280
  if (info.commit_list)
1435
 
    sql_print_information("Starting crash recovery...");
 
1281
    sql_print_information(_("Starting crash recovery..."));
1436
1282
 
1437
1283
 
1438
1284
#ifndef WILL_BE_DELETED_LATER
1442
1288
    rollback all pending transactions, without risking inconsistent data
1443
1289
  */
1444
1290
 
1445
 
  DBUG_ASSERT(total_ha_2pc == (ulong) opt_bin_log+1); // only InnoDB and binlog
 
1291
  assert(total_ha_2pc == (uint32_t) opt_bin_log+1); // only InnoDB and binlog
1446
1292
  tc_heuristic_recover= TC_HEURISTIC_RECOVER_ROLLBACK; // forcing ROLLBACK
1447
 
  info.dry_run=FALSE;
 
1293
  info.dry_run=false;
1448
1294
#endif
1449
1295
 
1450
1296
 
1456
1302
  if (!info.list)
1457
1303
  {
1458
1304
    sql_print_error(ER(ER_OUTOFMEMORY), info.len*sizeof(XID));
1459
 
    DBUG_RETURN(1);
 
1305
    return(1);
1460
1306
  }
1461
1307
 
1462
1308
  plugin_foreach(NULL, xarecover_handlerton, 
1463
 
                 MYSQL_STORAGE_ENGINE_PLUGIN, &info);
 
1309
                 DRIZZLE_STORAGE_ENGINE_PLUGIN, &info);
1464
1310
 
1465
 
  my_free((uchar*)info.list, MYF(0));
 
1311
  free((unsigned char*)info.list);
1466
1312
  if (info.found_foreign_xids)
1467
 
    sql_print_warning("Found %d prepared XA transactions", 
 
1313
    sql_print_warning(_("Found %d prepared XA transactions"), 
1468
1314
                      info.found_foreign_xids);
1469
1315
  if (info.dry_run && info.found_my_xids)
1470
1316
  {
1471
 
    sql_print_error("Found %d prepared transactions! It means that mysqld was "
1472
 
                    "not shut down properly last time and critical recovery "
1473
 
                    "information (last binlog or %s file) was manually deleted "
1474
 
                    "after a crash. You have to start mysqld with "
1475
 
                    "--tc-heuristic-recover switch to commit or rollback "
1476
 
                    "pending transactions.",
 
1317
    sql_print_error(_("Found %d prepared transactions! It means that drizzled "
 
1318
                    "was not shut down properly last time and critical "
 
1319
                    "recovery information (last binlog or %s file) was "
 
1320
                    "manually deleted after a crash. You have to start "
 
1321
                    "drizzled with the --tc-heuristic-recover switch to "
 
1322
                    "commit or rollback pending transactions."),
1477
1323
                    info.found_my_xids, opt_tc_log_file);
1478
 
    DBUG_RETURN(1);
 
1324
    return(1);
1479
1325
  }
1480
1326
  if (info.commit_list)
1481
 
    sql_print_information("Crash recovery finished.");
1482
 
  DBUG_RETURN(0);
 
1327
    sql_print_information(_("Crash recovery finished."));
 
1328
  return(0);
1483
1329
}
1484
1330
 
1485
1331
/**
1496
1342
  Protocol *protocol= thd->protocol;
1497
1343
  int i=0;
1498
1344
  XID_STATE *xs;
1499
 
  DBUG_ENTER("mysql_xa_recover");
1500
1345
 
1501
1346
  field_list.push_back(new Item_int("formatID", 0, MY_INT32_NUM_DECIMAL_DIGITS));
1502
1347
  field_list.push_back(new Item_int("gtrid_length", 0, MY_INT32_NUM_DECIMAL_DIGITS));
1505
1350
 
1506
1351
  if (protocol->send_fields(&field_list,
1507
1352
                            Protocol::SEND_NUM_ROWS | Protocol::SEND_EOF))
1508
 
    DBUG_RETURN(1);
 
1353
    return(1);
1509
1354
 
1510
1355
  pthread_mutex_lock(&LOCK_xid_cache);
1511
1356
  while ((xs= (XID_STATE*)hash_element(&xid_cache, i++)))
1513
1358
    if (xs->xa_state==XA_PREPARED)
1514
1359
    {
1515
1360
      protocol->prepare_for_resend();
1516
 
      protocol->store_longlong((longlong)xs->xid.formatID, FALSE);
1517
 
      protocol->store_longlong((longlong)xs->xid.gtrid_length, FALSE);
1518
 
      protocol->store_longlong((longlong)xs->xid.bqual_length, FALSE);
 
1361
      protocol->store_int64_t((int64_t)xs->xid.formatID, false);
 
1362
      protocol->store_int64_t((int64_t)xs->xid.gtrid_length, false);
 
1363
      protocol->store_int64_t((int64_t)xs->xid.bqual_length, false);
1519
1364
      protocol->store(xs->xid.data, xs->xid.gtrid_length+xs->xid.bqual_length,
1520
1365
                      &my_charset_bin);
1521
1366
      if (protocol->write())
1522
1367
      {
1523
1368
        pthread_mutex_unlock(&LOCK_xid_cache);
1524
 
        DBUG_RETURN(1);
 
1369
        return(1);
1525
1370
      }
1526
1371
    }
1527
1372
  }
1528
1373
 
1529
1374
  pthread_mutex_unlock(&LOCK_xid_cache);
1530
1375
  my_eof(thd);
1531
 
  DBUG_RETURN(0);
 
1376
  return(0);
1532
1377
}
1533
1378
 
1534
1379
/**
1549
1394
  @return
1550
1395
    always 0
1551
1396
*/
1552
 
static my_bool release_temporary_latches(THD *thd, plugin_ref plugin,
1553
 
                                 void *unused)
 
1397
static bool release_temporary_latches(THD *thd, plugin_ref plugin,
 
1398
                                      void *unused __attribute__((unused)))
1554
1399
{
1555
1400
  handlerton *hton= plugin_data(plugin, handlerton *);
1556
1401
 
1557
1402
  if (hton->state == SHOW_OPTION_YES && hton->release_temporary_latches)
1558
1403
    hton->release_temporary_latches(hton, thd);
1559
1404
 
1560
 
  return FALSE;
 
1405
  return false;
1561
1406
}
1562
1407
 
1563
1408
 
1564
1409
int ha_release_temporary_latches(THD *thd)
1565
1410
{
1566
 
  plugin_foreach(thd, release_temporary_latches, MYSQL_STORAGE_ENGINE_PLUGIN, 
 
1411
  plugin_foreach(thd, release_temporary_latches, DRIZZLE_STORAGE_ENGINE_PLUGIN, 
1567
1412
                 NULL);
1568
1413
 
1569
1414
  return 0;
1572
1417
int ha_rollback_to_savepoint(THD *thd, SAVEPOINT *sv)
1573
1418
{
1574
1419
  int error=0;
1575
 
  THD_TRANS *trans= (thd->in_sub_stmt ? &thd->transaction.stmt :
1576
 
                                        &thd->transaction.all);
 
1420
  THD_TRANS *trans= &thd->transaction.all;
1577
1421
  Ha_trx_info *ha_info, *ha_info_next;
1578
1422
 
1579
 
  DBUG_ENTER("ha_rollback_to_savepoint");
1580
 
 
1581
1423
  trans->no_2pc=0;
1582
1424
  /*
1583
1425
    rolling back to savepoint in all storage engines that were part of the
1587
1429
  {
1588
1430
    int err;
1589
1431
    handlerton *ht= ha_info->ht();
1590
 
    DBUG_ASSERT(ht);
1591
 
    DBUG_ASSERT(ht->savepoint_set != 0);
 
1432
    assert(ht);
 
1433
    assert(ht->savepoint_set != 0);
1592
1434
    if ((err= ht->savepoint_rollback(ht, thd,
1593
 
                                     (uchar *)(sv+1)+ht->savepoint_offset)))
 
1435
                                     (unsigned char *)(sv+1)+ht->savepoint_offset)))
1594
1436
    { // cannot happen
1595
1437
      my_error(ER_ERROR_DURING_ROLLBACK, MYF(0), err);
1596
1438
      error=1;
1607
1449
  {
1608
1450
    int err;
1609
1451
    handlerton *ht= ha_info->ht();
1610
 
    if ((err= ht->rollback(ht, thd, !thd->in_sub_stmt)))
 
1452
    if ((err= ht->rollback(ht, thd, !(0))))
1611
1453
    { // cannot happen
1612
1454
      my_error(ER_ERROR_DURING_ROLLBACK, MYF(0), err);
1613
1455
      error=1;
1617
1459
    ha_info->reset(); /* keep it conveniently zero-filled */
1618
1460
  }
1619
1461
  trans->ha_list= sv->ha_list;
1620
 
  DBUG_RETURN(error);
 
1462
  return(error);
1621
1463
}
1622
1464
 
1623
1465
/**
1629
1471
int ha_savepoint(THD *thd, SAVEPOINT *sv)
1630
1472
{
1631
1473
  int error=0;
1632
 
  THD_TRANS *trans= (thd->in_sub_stmt ? &thd->transaction.stmt :
1633
 
                                        &thd->transaction.all);
 
1474
  THD_TRANS *trans= &thd->transaction.all;
1634
1475
  Ha_trx_info *ha_info= trans->ha_list;
1635
 
  DBUG_ENTER("ha_savepoint");
1636
1476
  for (; ha_info; ha_info= ha_info->next())
1637
1477
  {
1638
1478
    int err;
1639
1479
    handlerton *ht= ha_info->ht();
1640
 
    DBUG_ASSERT(ht);
 
1480
    assert(ht);
1641
1481
    if (! ht->savepoint_set)
1642
1482
    {
1643
1483
      my_error(ER_CHECK_NOT_IMPLEMENTED, MYF(0), "SAVEPOINT");
1644
1484
      error=1;
1645
1485
      break;
1646
1486
    }
1647
 
    if ((err= ht->savepoint_set(ht, thd, (uchar *)(sv+1)+ht->savepoint_offset)))
 
1487
    if ((err= ht->savepoint_set(ht, thd, (unsigned char *)(sv+1)+ht->savepoint_offset)))
1648
1488
    { // cannot happen
1649
1489
      my_error(ER_GET_ERRNO, MYF(0), err);
1650
1490
      error=1;
1656
1496
    engines are prepended to the beginning of the list.
1657
1497
  */
1658
1498
  sv->ha_list= trans->ha_list;
1659
 
  DBUG_RETURN(error);
 
1499
  return(error);
1660
1500
}
1661
1501
 
1662
1502
int ha_release_savepoint(THD *thd, SAVEPOINT *sv)
1663
1503
{
1664
1504
  int error=0;
1665
1505
  Ha_trx_info *ha_info= sv->ha_list;
1666
 
  DBUG_ENTER("ha_release_savepoint");
1667
1506
 
1668
1507
  for (; ha_info; ha_info= ha_info->next())
1669
1508
  {
1670
1509
    int err;
1671
1510
    handlerton *ht= ha_info->ht();
1672
1511
    /* Savepoint life time is enclosed into transaction life time. */
1673
 
    DBUG_ASSERT(ht);
 
1512
    assert(ht);
1674
1513
    if (!ht->savepoint_release)
1675
1514
      continue;
1676
1515
    if ((err= ht->savepoint_release(ht, thd,
1677
 
                                    (uchar *)(sv+1) + ht->savepoint_offset)))
 
1516
                                    (unsigned char *)(sv+1) + ht->savepoint_offset)))
1678
1517
    { // cannot happen
1679
1518
      my_error(ER_GET_ERRNO, MYF(0), err);
1680
1519
      error=1;
1681
1520
    }
1682
1521
  }
1683
 
  DBUG_RETURN(error);
 
1522
  return(error);
1684
1523
}
1685
1524
 
1686
1525
 
1687
 
static my_bool snapshot_handlerton(THD *thd, plugin_ref plugin,
1688
 
                                   void *arg)
 
1526
static bool snapshot_handlerton(THD *thd, plugin_ref plugin, void *arg)
1689
1527
{
1690
1528
  handlerton *hton= plugin_data(plugin, handlerton *);
1691
1529
  if (hton->state == SHOW_OPTION_YES &&
1694
1532
    hton->start_consistent_snapshot(hton, thd);
1695
1533
    *((bool *)arg)= false;
1696
1534
  }
1697
 
  return FALSE;
 
1535
  return false;
1698
1536
}
1699
1537
 
1700
1538
int ha_start_consistent_snapshot(THD *thd)
1701
1539
{
1702
1540
  bool warn= true;
1703
1541
 
1704
 
  plugin_foreach(thd, snapshot_handlerton, MYSQL_STORAGE_ENGINE_PLUGIN, &warn);
 
1542
  plugin_foreach(thd, snapshot_handlerton, DRIZZLE_STORAGE_ENGINE_PLUGIN, &warn);
1705
1543
 
1706
1544
  /*
1707
1545
    Same idea as when one wants to CREATE TABLE in one engine which does not
1708
1546
    exist:
1709
1547
  */
1710
1548
  if (warn)
1711
 
    push_warning(thd, MYSQL_ERROR::WARN_LEVEL_WARN, ER_UNKNOWN_ERROR,
 
1549
    push_warning(thd, DRIZZLE_ERROR::WARN_LEVEL_WARN, ER_UNKNOWN_ERROR,
1712
1550
                 "This MySQL server does not support any "
1713
1551
                 "consistent-read capable storage engine");
1714
1552
  return 0;
1715
1553
}
1716
1554
 
1717
1555
 
1718
 
static my_bool flush_handlerton(THD *thd, plugin_ref plugin,
1719
 
                                void *arg)
 
1556
static bool flush_handlerton(THD *thd __attribute__((unused)),
 
1557
                             plugin_ref plugin,
 
1558
                             void *arg __attribute__((unused)))
1720
1559
{
1721
1560
  handlerton *hton= plugin_data(plugin, handlerton *);
1722
1561
  if (hton->state == SHOW_OPTION_YES && hton->flush_logs && 
1723
1562
      hton->flush_logs(hton))
1724
 
    return TRUE;
1725
 
  return FALSE;
 
1563
    return true;
 
1564
  return false;
1726
1565
}
1727
1566
 
1728
1567
 
1731
1570
  if (db_type == NULL)
1732
1571
  {
1733
1572
    if (plugin_foreach(NULL, flush_handlerton,
1734
 
                          MYSQL_STORAGE_ENGINE_PLUGIN, 0))
1735
 
      return TRUE;
 
1573
                          DRIZZLE_STORAGE_ENGINE_PLUGIN, 0))
 
1574
      return true;
1736
1575
  }
1737
1576
  else
1738
1577
  {
1739
1578
    if (db_type->state != SHOW_OPTION_YES ||
1740
1579
        (db_type->flush_logs && db_type->flush_logs(db_type)))
1741
 
      return TRUE;
 
1580
      return true;
1742
1581
  }
1743
 
  return FALSE;
 
1582
  return false;
1744
1583
}
1745
1584
 
1746
1585
static const char *check_lowercase_names(handler *file, const char *path,
1751
1590
 
1752
1591
  /* Ensure that table handler get path in lower case */
1753
1592
  if (tmp_path != path)
1754
 
    strmov(tmp_path, path);
 
1593
    my_stpcpy(tmp_path, path);
1755
1594
 
1756
1595
  /*
1757
1596
    we only should turn into lowercase database/table part
1771
1610
struct Ha_delete_table_error_handler: public Internal_error_handler
1772
1611
{
1773
1612
public:
1774
 
  virtual bool handle_error(uint sql_errno,
 
1613
  virtual bool handle_error(uint32_t sql_errno,
1775
1614
                            const char *message,
1776
 
                            MYSQL_ERROR::enum_warning_level level,
 
1615
                            DRIZZLE_ERROR::enum_warning_level level,
1777
1616
                            THD *thd);
1778
 
  char buff[MYSQL_ERRMSG_SIZE];
 
1617
  char buff[DRIZZLE_ERRMSG_SIZE];
1779
1618
};
1780
1619
 
1781
1620
 
1782
1621
bool
1783
1622
Ha_delete_table_error_handler::
1784
 
handle_error(uint sql_errno,
 
1623
handle_error(uint32_t sql_errno  __attribute__((unused)),
1785
1624
             const char *message,
1786
 
             MYSQL_ERROR::enum_warning_level level,
1787
 
             THD *thd)
 
1625
             DRIZZLE_ERROR::enum_warning_level level __attribute__((unused)),
 
1626
             THD *thd __attribute__((unused)))
1788
1627
{
1789
1628
  /* Grab the error message */
1790
1629
  strmake(buff, message, sizeof(buff)-1);
1791
 
  return TRUE;
 
1630
  return true;
1792
1631
}
1793
1632
 
1794
1633
 
1802
1641
  handler *file;
1803
1642
  char tmp_path[FN_REFLEN];
1804
1643
  int error;
1805
 
  TABLE dummy_table;
 
1644
  Table dummy_table;
1806
1645
  TABLE_SHARE dummy_share;
1807
 
  DBUG_ENTER("ha_delete_table");
1808
1646
 
1809
 
  bzero((char*) &dummy_table, sizeof(dummy_table));
1810
 
  bzero((char*) &dummy_share, sizeof(dummy_share));
 
1647
  memset(&dummy_table, 0, sizeof(dummy_table));
 
1648
  memset(&dummy_share, 0, sizeof(dummy_share));
1811
1649
  dummy_table.s= &dummy_share;
1812
1650
 
1813
 
  /* DB_TYPE_UNKNOWN is used in ALTER TABLE when renaming only .frm files */
 
1651
  /* DB_TYPE_UNKNOWN is used in ALTER Table when renaming only .frm files */
1814
1652
  if (table_type == NULL ||
1815
1653
      ! (file=get_new_handler((TABLE_SHARE*)0, thd->mem_root, table_type)))
1816
 
    DBUG_RETURN(ENOENT);
 
1654
    return(ENOENT);
1817
1655
 
1818
1656
  path= check_lowercase_names(file, path, tmp_path);
1819
1657
  if ((error= file->ha_delete_table(path)) && generate_warning)
1846
1684
      XXX: should we convert *all* errors to warnings here?
1847
1685
      What if the error is fatal?
1848
1686
    */
1849
 
    push_warning(thd, MYSQL_ERROR::WARN_LEVEL_ERROR, error,
 
1687
    push_warning(thd, DRIZZLE_ERROR::WARN_LEVEL_ERROR, error,
1850
1688
                ha_delete_table_error_handler.buff);
1851
1689
  }
1852
1690
  delete file;
1853
 
  DBUG_RETURN(error);
 
1691
  return(error);
1854
1692
}
1855
1693
 
1856
1694
/****************************************************************************
1864
1702
    on this->table->mem_root and we will not be able to reclaim that memory 
1865
1703
    when the clone handler object is destroyed.
1866
1704
  */
1867
 
  if (!(new_handler->ref= (uchar*) alloc_root(mem_root, ALIGN_SIZE(ref_length)*2)))
 
1705
  if (!(new_handler->ref= (unsigned char*) alloc_root(mem_root, ALIGN_SIZE(ref_length)*2)))
1868
1706
    return NULL;
1869
1707
  if (new_handler && !new_handler->ha_open(table,
1870
1708
                                           table->s->normalized_path.str,
1871
 
                                           table->db_stat,
 
1709
                                           table->getDBStat(),
1872
1710
                                           HA_OPEN_IGNORE_IF_LOCKED))
1873
1711
    return new_handler;
1874
1712
  return NULL;
1888
1726
 
1889
1727
THD *handler::ha_thd(void) const
1890
1728
{
1891
 
  DBUG_ASSERT(!table || !table->in_use || table->in_use == current_thd);
 
1729
  assert(!table || !table->in_use || table->in_use == current_thd);
1892
1730
  return (table && table->in_use) ? table->in_use : current_thd;
1893
1731
}
1894
1732
 
1895
 
 
1896
 
/**
1897
 
   Get tablespace name from handler 
1898
 
   Returns the tablespace name associated
1899
 
   with the table or NULL if not defined
1900
 
*/
1901
 
const 
1902
 
char* handler::get_tablespace_name()
1903
 
{
1904
 
  return table->s->tablespace;
1905
 
}
1906
 
 
1907
1733
/**
1908
1734
  Open database-handler.
1909
1735
 
1910
1736
  Try O_RDONLY if cannot open as O_RDWR
1911
1737
  Don't wait for locks if not HA_OPEN_WAIT_IF_LOCKED is set
1912
1738
*/
1913
 
int handler::ha_open(TABLE *table_arg, const char *name, int mode,
 
1739
int handler::ha_open(Table *table_arg, const char *name, int mode,
1914
1740
                     int test_if_locked)
1915
1741
{
1916
1742
  int error;
1917
 
  DBUG_ENTER("handler::ha_open");
1918
 
  DBUG_PRINT("enter",
1919
 
             ("name: %s  db_type: %d  db_stat: %d  mode: %d  lock_test: %d",
1920
 
              name, ht->db_type, table_arg->db_stat, mode,
1921
 
              test_if_locked));
1922
1743
 
1923
1744
  table= table_arg;
1924
 
  DBUG_ASSERT(table->s == table_share);
1925
 
  DBUG_ASSERT(alloc_root_inited(&table->mem_root));
 
1745
  assert(table->s == table_share);
 
1746
  assert(alloc_root_inited(&table->mem_root));
1926
1747
 
1927
1748
  if ((error=open(name,mode,test_if_locked)))
1928
1749
  {
1936
1757
  if (error)
1937
1758
  {
1938
1759
    my_errno= error;                            /* Safeguard */
1939
 
    DBUG_PRINT("error",("error: %d  errno: %d",error,errno));
1940
1760
  }
1941
1761
  else
1942
1762
  {
1945
1765
    (void) extra(HA_EXTRA_NO_READCHECK);        // Not needed in SQL
1946
1766
 
1947
1767
    /* ref is already allocated for us if we're called from handler::clone() */
1948
 
    if (!ref && !(ref= (uchar*) alloc_root(&table->mem_root, 
 
1768
    if (!ref && !(ref= (unsigned char*) alloc_root(&table->mem_root, 
1949
1769
                                          ALIGN_SIZE(ref_length)*2)))
1950
1770
    {
1951
1771
      close();
1955
1775
      dup_ref=ref+ALIGN_SIZE(ref_length);
1956
1776
    cached_table_flags= table_flags();
1957
1777
  }
1958
 
  DBUG_RETURN(error);
 
1778
  return(error);
1959
1779
}
1960
1780
 
1961
1781
/**
1965
1785
  handlers for random position
1966
1786
*/
1967
1787
 
1968
 
int handler::rnd_pos_by_record(uchar *record)
 
1788
int handler::rnd_pos_by_record(unsigned char *record)
1969
1789
{
1970
1790
  register int error;
1971
 
  DBUG_ENTER("handler::rnd_pos_by_record");
1972
1791
 
1973
1792
  position(record);
1974
1793
  if (inited && (error= ha_index_end()))
1975
 
    DBUG_RETURN(error);
1976
 
  if ((error= ha_rnd_init(FALSE)))
1977
 
    DBUG_RETURN(error);
 
1794
    return(error);
 
1795
  if ((error= ha_rnd_init(false)))
 
1796
    return(error);
1978
1797
 
1979
 
  DBUG_RETURN(rnd_pos(record, ref));
 
1798
  return(rnd_pos(record, ref));
1980
1799
}
1981
1800
 
1982
1801
/**
1985
1804
  This is never called for InnoDB tables, as these table types
1986
1805
  has the HA_STATS_RECORDS_IS_EXACT set.
1987
1806
*/
1988
 
int handler::read_first_row(uchar * buf, uint primary_key)
 
1807
int handler::read_first_row(unsigned char * buf, uint32_t primary_key)
1989
1808
{
1990
1809
  register int error;
1991
 
  DBUG_ENTER("handler::read_first_row");
1992
1810
 
1993
1811
  ha_statistic_increment(&SSV::ha_read_first_count);
1994
1812
 
2011
1829
    error=index_first(buf);
2012
1830
    (void) ha_index_end();
2013
1831
  }
2014
 
  DBUG_RETURN(error);
 
1832
  return(error);
2015
1833
}
2016
1834
 
2017
1835
/**
2075
1893
      the offset is larger than the column's max possible value, i.e. not even
2076
1894
      the first sequence value may be inserted. User will receive warning.
2077
1895
    */
2078
 
    DBUG_PRINT("info",("auto_increment: nr: %lu cannot honour "
2079
 
                       "auto_increment_offset: %lu",
2080
 
                       (ulong) nr, variables->auto_increment_offset));
2081
1896
    return nr;
2082
1897
  }
2083
1898
  if (variables->auto_increment_increment == 1)
2166
1981
int handler::update_auto_increment()
2167
1982
{
2168
1983
  uint64_t nr, nb_reserved_values;
2169
 
  bool append= FALSE;
 
1984
  bool append= false;
2170
1985
  THD *thd= table->in_use;
2171
1986
  struct system_variables *variables= &thd->variables;
2172
 
  DBUG_ENTER("handler::update_auto_increment");
2173
1987
 
2174
1988
  /*
2175
1989
    next_insert_id is a "cursor" into the reserved interval, it may go greater
2176
1990
    than the interval, but not smaller.
2177
1991
  */
2178
 
  DBUG_ASSERT(next_insert_id >= auto_inc_interval_for_cur_row.minimum());
 
1992
  assert(next_insert_id >= auto_inc_interval_for_cur_row.minimum());
2179
1993
 
2180
 
  if (((nr= table->next_number_field->val_int()) != 0) || 
2181
 
      (table->auto_increment_field_not_null && (thd->variables.sql_mode & MODE_NO_AUTO_VALUE_ON_ZERO)))
 
1994
  if ((nr= table->next_number_field->val_int()) != 0)
2182
1995
  {
2183
1996
    /*
2184
1997
      Update next_insert_id if we had already generated a value in this
2188
2001
    */
2189
2002
    adjust_next_insert_id_after_explicit_value(nr);
2190
2003
    insert_id_for_cur_row= 0; // didn't generate anything
2191
 
    DBUG_RETURN(0);
 
2004
    return(0);
2192
2005
  }
2193
2006
 
2194
2007
  if ((nr= next_insert_id) >= auto_inc_interval_for_cur_row.maximum())
2207
2020
        handler::estimation_rows_to_insert was set by
2208
2021
        handler::ha_start_bulk_insert(); if 0 it means "unknown".
2209
2022
      */
2210
 
      uint nb_already_reserved_intervals=
 
2023
      uint32_t nb_already_reserved_intervals=
2211
2024
        thd->auto_inc_intervals_in_cur_stmt_for_binlog.nb_elements();
2212
2025
      uint64_t nb_desired_values;
2213
2026
      /*
2242
2055
                         nb_desired_values, &nr,
2243
2056
                         &nb_reserved_values);
2244
2057
      if (nr == ~(uint64_t) 0)
2245
 
        DBUG_RETURN(HA_ERR_AUTOINC_READ_FAILED);  // Mark failure
 
2058
        return(HA_ERR_AUTOINC_READ_FAILED);  // Mark failure
2246
2059
      
2247
2060
      /*
2248
2061
        That rounding below should not be needed when all engines actually
2258
2071
    if (table->s->next_number_keypart == 0)
2259
2072
    {
2260
2073
      /* We must defer the appending until "nr" has been possibly truncated */
2261
 
      append= TRUE;
2262
 
    }
2263
 
    else
2264
 
    {
2265
 
      /*
2266
 
        For such auto_increment there is no notion of interval, just a
2267
 
        singleton. The interval is not even stored in
2268
 
        thd->auto_inc_interval_for_cur_row, so we are sure to call the engine
2269
 
        for next row.
2270
 
      */
2271
 
      DBUG_PRINT("info",("auto_increment: special not-first-in-index"));
 
2074
      append= true;
2272
2075
    }
2273
2076
  }
2274
2077
 
2275
 
  DBUG_PRINT("info",("auto_increment: %lu", (ulong) nr));
2276
 
 
2277
 
  if (unlikely(table->next_number_field->store((longlong) nr, TRUE)))
 
2078
  if (unlikely(table->next_number_field->store((int64_t) nr, true)))
2278
2079
  {
2279
2080
    /*
2280
2081
      first test if the query was aborted due to strict mode constraints
2281
2082
    */
2282
2083
    if (thd->killed == THD::KILL_BAD_DATA)
2283
 
      DBUG_RETURN(HA_ERR_AUTOINC_ERANGE);
 
2084
      return(HA_ERR_AUTOINC_ERANGE);
2284
2085
 
2285
2086
    /*
2286
2087
      field refused this value (overflow) and truncated it, use the result of
2291
2092
      interval will cause a duplicate key).
2292
2093
    */
2293
2094
    nr= prev_insert_id(table->next_number_field->val_int(), variables);
2294
 
    if (unlikely(table->next_number_field->store((longlong) nr, TRUE)))
 
2095
    if (unlikely(table->next_number_field->store((int64_t) nr, true)))
2295
2096
      nr= table->next_number_field->val_int();
2296
2097
  }
2297
2098
  if (append)
2319
2120
  */
2320
2121
  set_next_insert_id(compute_next_insert_id(nr, variables));
2321
2122
 
2322
 
  DBUG_RETURN(0);
 
2123
  return(0);
2323
2124
}
2324
2125
 
2325
2126
 
2337
2138
*/
2338
2139
void handler::column_bitmaps_signal()
2339
2140
{
2340
 
  DBUG_ENTER("column_bitmaps_signal");
2341
 
  DBUG_PRINT("info", ("read_set: 0x%lx  write_set: 0x%lx", (long) table->read_set,
2342
 
                      (long) table->write_set));
2343
 
  DBUG_VOID_RETURN;
 
2141
  return;
2344
2142
}
2345
2143
 
2346
2144
 
2350
2148
  offset and increment means that we want values to be of the form
2351
2149
  offset + N * increment, where N>=0 is integer.
2352
2150
  If the function sets *first_value to ~(uint64_t)0 it means an error.
2353
 
  If the function sets *nb_reserved_values to ULONGLONG_MAX it means it has
 
2151
  If the function sets *nb_reserved_values to UINT64_MAX it means it has
2354
2152
  reserved to "positive infinite".
2355
2153
 
2356
2154
  @param offset
2359
2157
  @param first_value         (OUT) the first value reserved by the handler
2360
2158
  @param nb_reserved_values  (OUT) how many values the handler reserved
2361
2159
*/
2362
 
void handler::get_auto_increment(uint64_t offset, uint64_t increment,
2363
 
                                 uint64_t nb_desired_values,
 
2160
void handler::get_auto_increment(uint64_t offset __attribute__((unused)),
 
2161
                                 uint64_t increment __attribute__((unused)),
 
2162
                                 uint64_t nb_desired_values __attribute__((unused)),
2364
2163
                                 uint64_t *first_value,
2365
2164
                                 uint64_t *nb_reserved_values)
2366
2165
{
2380
2179
      use nr+increment without checking again with the handler, in
2381
2180
      handler::update_auto_increment()), so reserves to infinite.
2382
2181
    */
2383
 
    *nb_reserved_values= ULONGLONG_MAX;
 
2182
    *nb_reserved_values= UINT64_MAX;
2384
2183
  }
2385
2184
  else
2386
2185
  {
2387
 
    uchar key[MAX_KEY_LENGTH];
 
2186
    unsigned char key[MAX_KEY_LENGTH];
2388
2187
    key_copy(key, table->record[0],
2389
2188
             table->key_info + table->s->next_number_index,
2390
2189
             table->s->next_number_key_offset);
2428
2227
}
2429
2228
 
2430
2229
 
2431
 
void handler::print_keydup_error(uint key_nr, const char *msg)
 
2230
void handler::print_keydup_error(uint32_t key_nr, const char *msg)
2432
2231
{
2433
2232
  /* Write the duplicated key in the error message */
2434
2233
  char key[MAX_KEY_LENGTH];
2444
2243
  {
2445
2244
    /* Table is opened and defined at this point */
2446
2245
    key_unpack(&str,table,(uint) key_nr);
2447
 
    uint max_length=MYSQL_ERRMSG_SIZE-(uint) strlen(msg);
 
2246
    uint32_t max_length=DRIZZLE_ERRMSG_SIZE-(uint) strlen(msg);
2448
2247
    if (str.length() >= max_length)
2449
2248
    {
2450
2249
      str.length(max_length-4);
2467
2266
*/
2468
2267
void handler::print_error(int error, myf errflag)
2469
2268
{
2470
 
  DBUG_ENTER("handler::print_error");
2471
 
  DBUG_PRINT("enter",("error: %d",error));
2472
 
 
2473
2269
  int textno=ER_GET_ERRNO;
2474
2270
  switch (error) {
2475
2271
  case EACCES:
2491
2287
    break;
2492
2288
  case HA_ERR_FOUND_DUPP_KEY:
2493
2289
  {
2494
 
    uint key_nr=get_dup_key(error);
 
2290
    uint32_t key_nr=get_dup_key(error);
2495
2291
    if ((int) key_nr >= 0)
2496
2292
    {
2497
2293
      print_keydup_error(key_nr, ER(ER_DUP_ENTRY_WITH_KEY_NAME));
2498
 
      DBUG_VOID_RETURN;
 
2294
      return;
2499
2295
    }
2500
2296
    textno=ER_DUP_KEY;
2501
2297
    break;
2502
2298
  }
2503
2299
  case HA_ERR_FOREIGN_DUPLICATE_KEY:
2504
2300
  {
2505
 
    uint key_nr= get_dup_key(error);
 
2301
    uint32_t key_nr= get_dup_key(error);
2506
2302
    if ((int) key_nr >= 0)
2507
2303
    {
2508
 
      uint max_length;
 
2304
      uint32_t max_length;
2509
2305
      /* Write the key in the error message */
2510
2306
      char key[MAX_KEY_LENGTH];
2511
2307
      String str(key,sizeof(key),system_charset_info);
2512
2308
      /* Table is opened and defined at this point */
2513
2309
      key_unpack(&str,table,(uint) key_nr);
2514
 
      max_length= (MYSQL_ERRMSG_SIZE-
 
2310
      max_length= (DRIZZLE_ERRMSG_SIZE-
2515
2311
                   (uint) strlen(ER(ER_FOREIGN_DUPLICATE_KEY)));
2516
2312
      if (str.length() >= max_length)
2517
2313
      {
2520
2316
      }
2521
2317
      my_error(ER_FOREIGN_DUPLICATE_KEY, MYF(0), table_share->table_name.str,
2522
2318
        str.c_ptr(), key_nr+1);
2523
 
      DBUG_VOID_RETURN;
 
2319
      return;
2524
2320
    }
2525
2321
    textno= ER_DUP_KEY;
2526
2322
    break;
2582
2378
    String str;
2583
2379
    get_error_message(error, &str);
2584
2380
    my_error(ER_ROW_IS_REFERENCED_2, MYF(0), str.c_ptr_safe());
2585
 
    DBUG_VOID_RETURN;
 
2381
    return;
2586
2382
  }
2587
2383
  case HA_ERR_NO_REFERENCED_ROW:
2588
2384
  {
2589
2385
    String str;
2590
2386
    get_error_message(error, &str);
2591
2387
    my_error(ER_NO_REFERENCED_ROW_2, MYF(0), str.c_ptr_safe());
2592
 
    DBUG_VOID_RETURN;
 
2388
    return;
2593
2389
  }
2594
2390
  case HA_ERR_TABLE_DEF_CHANGED:
2595
2391
    textno=ER_TABLE_DEF_CHANGED;
2597
2393
  case HA_ERR_NO_SUCH_TABLE:
2598
2394
    my_error(ER_NO_SUCH_TABLE, MYF(0), table_share->db.str,
2599
2395
             table_share->table_name.str);
2600
 
    DBUG_VOID_RETURN;
 
2396
    return;
2601
2397
  case HA_ERR_RBR_LOGGING_FAILED:
2602
2398
    textno= ER_BINLOG_ROW_LOGGING_FAILED;
2603
2399
    break;
2604
2400
  case HA_ERR_DROP_INDEX_FK:
2605
2401
  {
2606
2402
    const char *ptr= "???";
2607
 
    uint key_nr= get_dup_key(error);
 
2403
    uint32_t key_nr= get_dup_key(error);
2608
2404
    if ((int) key_nr >= 0)
2609
2405
      ptr= table->key_info[key_nr].name;
2610
2406
    my_error(ER_DROP_INDEX_FK, MYF(0), ptr);
2611
 
    DBUG_VOID_RETURN;
 
2407
    return;
2612
2408
  }
2613
2409
  case HA_ERR_TABLE_NEEDS_UPGRADE:
2614
2410
    textno=ER_TABLE_NEEDS_UPGRADE;
2625
2421
  case HA_ERR_LOCK_OR_ACTIVE_TRANSACTION:
2626
2422
    my_message(ER_LOCK_OR_ACTIVE_TRANSACTION,
2627
2423
               ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0));
2628
 
    DBUG_VOID_RETURN;
 
2424
    return;
2629
2425
    break;
2630
2426
  default:
2631
2427
    {
2632
2428
      /* The error was "unknown" to this function.
2633
2429
         Ask handler if it has got a message for this error */
2634
 
      bool temporary= FALSE;
 
2430
      bool temporary= false;
2635
2431
      String str;
2636
2432
      temporary= get_error_message(error, &str);
2637
2433
      if (!str.is_empty())
2644
2440
      }
2645
2441
      else
2646
2442
        my_error(ER_GET_ERRNO,errflag,error);
2647
 
      DBUG_VOID_RETURN;
 
2443
      return;
2648
2444
    }
2649
2445
  }
2650
2446
  my_error(textno, errflag, table_share->table_name.str, error);
2651
 
  DBUG_VOID_RETURN;
 
2447
  return;
2652
2448
}
2653
2449
 
2654
2450
 
2661
2457
  @return
2662
2458
    Returns true if this is a temporary error
2663
2459
*/
2664
 
bool handler::get_error_message(int error, String* buf)
 
2460
bool handler::get_error_message(int error __attribute__((unused)),
 
2461
                                String* buf __attribute__((unused)))
2665
2462
{
2666
 
  return FALSE;
 
2463
  return false;
2667
2464
}
2668
2465
 
2669
2466
 
2686
2483
        if (!keypart->fieldnr)
2687
2484
          continue;
2688
2485
        Field *field= table->field[keypart->fieldnr-1];
2689
 
        if (field->type() == MYSQL_TYPE_BLOB)
 
2486
        if (field->type() == DRIZZLE_TYPE_BLOB)
2690
2487
        {
2691
2488
          if (check_opt->sql_flags & TT_FOR_UPGRADE)
2692
2489
            check_opt->flags= T_MEDIUM;
2706
2503
}
2707
2504
 
2708
2505
 
2709
 
static bool update_frm_version(TABLE *table)
 
2506
static bool update_frm_version(Table *table)
2710
2507
{
2711
2508
  char path[FN_REFLEN];
2712
2509
  File file;
2713
2510
  bool result= true;
2714
 
  DBUG_ENTER("update_frm_version");
2715
2511
 
2716
2512
  /*
2717
2513
    No need to update frm version in case table was created or checked
2719
2515
    update frm version for temporary tables as this code doesn't support
2720
2516
    temporary tables.
2721
2517
  */
2722
 
  if (table->s->mysql_version == MYSQL_VERSION_ID)
2723
 
    DBUG_RETURN(0);
2724
 
 
2725
 
  strxmov(path, table->s->normalized_path.str, reg_ext, NullS);
2726
 
 
2727
 
  if ((file= my_open(path, O_RDWR|O_BINARY, MYF(MY_WME))) >= 0)
 
2518
  if (table->s->mysql_version == DRIZZLE_VERSION_ID)
 
2519
    return(0);
 
2520
 
 
2521
  strxmov(path, table->s->normalized_path.str, reg_ext, NULL);
 
2522
 
 
2523
  if ((file= my_open(path, O_RDWR, MYF(MY_WME))) >= 0)
2728
2524
  {
2729
 
    uchar version[4];
 
2525
    unsigned char version[4];
2730
2526
    char *key= table->s->table_cache_key.str;
2731
 
    uint key_length= table->s->table_cache_key.length;
2732
 
    TABLE *entry;
 
2527
    uint32_t key_length= table->s->table_cache_key.length;
 
2528
    Table *entry;
2733
2529
    HASH_SEARCH_STATE state;
2734
2530
 
2735
 
    int4store(version, MYSQL_VERSION_ID);
 
2531
    int4store(version, DRIZZLE_VERSION_ID);
2736
2532
 
2737
 
    if (pwrite(file, (uchar*)version, 4, 51L) == 0)
 
2533
    if (pwrite(file, (unsigned char*)version, 4, 51L) == 0)
2738
2534
    {
2739
2535
      result= false;
2740
2536
      goto err;
2741
2537
    }
2742
2538
 
2743
 
    for (entry=(TABLE*) hash_first(&open_cache,(uchar*) key,key_length, &state);
 
2539
    for (entry=(Table*) hash_first(&open_cache,(unsigned char*) key,key_length, &state);
2744
2540
         entry;
2745
 
         entry= (TABLE*) hash_next(&open_cache,(uchar*) key,key_length, &state))
2746
 
      entry->s->mysql_version= MYSQL_VERSION_ID;
 
2541
         entry= (Table*) hash_next(&open_cache,(unsigned char*) key,key_length, &state))
 
2542
      entry->s->mysql_version= DRIZZLE_VERSION_ID;
2747
2543
  }
2748
2544
err:
2749
2545
  if (file >= 0)
2750
 
    VOID(my_close(file,MYF(MY_WME)));
2751
 
  DBUG_RETURN(result);
 
2546
    my_close(file,MYF(MY_WME));
 
2547
  return(result);
2752
2548
}
2753
2549
 
2754
2550
 
2757
2553
  @return
2758
2554
    key if error because of duplicated keys
2759
2555
*/
2760
 
uint handler::get_dup_key(int error)
 
2556
uint32_t handler::get_dup_key(int error)
2761
2557
{
2762
 
  DBUG_ENTER("handler::get_dup_key");
2763
2558
  table->file->errkey  = (uint) -1;
2764
2559
  if (error == HA_ERR_FOUND_DUPP_KEY || error == HA_ERR_FOREIGN_DUPLICATE_KEY ||
2765
2560
      error == HA_ERR_FOUND_DUPP_UNIQUE ||
2766
2561
      error == HA_ERR_DROP_INDEX_FK)
2767
2562
    info(HA_STATUS_ERRKEY | HA_STATUS_NO_LOCK);
2768
 
  DBUG_RETURN(table->file->errkey);
 
2563
  return(table->file->errkey);
2769
2564
}
2770
2565
 
2771
2566
 
2832
2627
/**
2833
2628
  Performs checks upon the table.
2834
2629
 
2835
 
  @param thd                thread doing CHECK TABLE operation
 
2630
  @param thd                thread doing CHECK Table operation
2836
2631
  @param check_opt          options from the parser
2837
2632
 
2838
2633
  @retval
2840
2635
  @retval
2841
2636
    HA_ADMIN_NEEDS_UPGRADE    Table has structures requiring upgrade
2842
2637
  @retval
2843
 
    HA_ADMIN_NEEDS_ALTER      Table has structures requiring ALTER TABLE
 
2638
    HA_ADMIN_NEEDS_ALTER      Table has structures requiring ALTER Table
2844
2639
  @retval
2845
2640
    HA_ADMIN_NOT_IMPLEMENTED
2846
2641
*/
2848
2643
{
2849
2644
  int error;
2850
2645
 
2851
 
  if ((table->s->mysql_version >= MYSQL_VERSION_ID) &&
 
2646
  if ((table->s->mysql_version >= DRIZZLE_VERSION_ID) &&
2852
2647
      (check_opt->sql_flags & TT_FOR_UPGRADE))
2853
2648
    return 0;
2854
2649
 
2855
 
  if (table->s->mysql_version < MYSQL_VERSION_ID)
 
2650
  if (table->s->mysql_version < DRIZZLE_VERSION_ID)
2856
2651
  {
2857
2652
    if ((error= check_old_types()))
2858
2653
      return error;
2887
2682
  */
2888
2683
  if (ha_info->is_started())
2889
2684
  {
2890
 
    DBUG_ASSERT(has_transactions());
 
2685
    assert(has_transactions());
2891
2686
    /*
2892
2687
      table_share can be NULL in ha_delete_table(). See implementation
2893
2688
      of standalone function ha_delete_table() in sql_base.cc.
2923
2718
*/
2924
2719
 
2925
2720
int
2926
 
handler::ha_bulk_update_row(const uchar *old_data, uchar *new_data,
2927
 
                            uint *dup_key_found)
 
2721
handler::ha_bulk_update_row(const unsigned char *old_data, unsigned char *new_data,
 
2722
                            uint32_t *dup_key_found)
2928
2723
{
2929
2724
  mark_trx_read_write();
2930
2725
 
3014
2809
*/
3015
2810
 
3016
2811
int
3017
 
handler::ha_disable_indexes(uint mode)
 
2812
handler::ha_disable_indexes(uint32_t mode)
3018
2813
{
3019
2814
  mark_trx_read_write();
3020
2815
 
3029
2824
*/
3030
2825
 
3031
2826
int
3032
 
handler::ha_enable_indexes(uint mode)
 
2827
handler::ha_enable_indexes(uint32_t mode)
3033
2828
{
3034
2829
  mark_trx_read_write();
3035
2830
 
3044
2839
*/
3045
2840
 
3046
2841
int
3047
 
handler::ha_discard_or_import_tablespace(my_bool discard)
 
2842
handler::ha_discard_or_import_tablespace(bool discard)
3048
2843
{
3049
2844
  mark_trx_read_write();
3050
2845
 
3121
2916
*/
3122
2917
 
3123
2918
int
3124
 
handler::ha_create(const char *name, TABLE *form, HA_CREATE_INFO *info)
 
2919
handler::ha_create(const char *name, Table *form, HA_CREATE_INFO *info)
3125
2920
{
3126
2921
  mark_trx_read_write();
3127
2922
 
3148
2943
/**
3149
2944
  Tell the storage engine that it is allowed to "disable transaction" in the
3150
2945
  handler. It is a hint that ACID is not required - it is used in NDB for
3151
 
  ALTER TABLE, for example, when data are copied to temporary table.
 
2946
  ALTER Table, for example, when data are copied to temporary table.
3152
2947
  A storage engine may treat this hint any way it likes. NDB for example
3153
2948
  starts to commit every now and then automatically.
3154
2949
  This hint can be safely ignored.
3156
2951
int ha_enable_transaction(THD *thd, bool on)
3157
2952
{
3158
2953
  int error=0;
3159
 
  DBUG_ENTER("ha_enable_transaction");
3160
 
  DBUG_PRINT("enter", ("on: %d", (int) on));
3161
2954
 
3162
2955
  if ((thd->transaction.on= on))
3163
2956
  {
3170
2963
    if (!(error= ha_commit_trans(thd, 0)))
3171
2964
      error= end_trans(thd, COMMIT);
3172
2965
  }
3173
 
  DBUG_RETURN(error);
 
2966
  return(error);
3174
2967
}
3175
2968
 
3176
 
int handler::index_next_same(uchar *buf, const uchar *key, uint keylen)
 
2969
int handler::index_next_same(unsigned char *buf, const unsigned char *key, uint32_t keylen)
3177
2970
{
3178
2971
  int error;
3179
 
  DBUG_ENTER("index_next_same");
3180
2972
  if (!(error=index_next(buf)))
3181
2973
  {
3182
2974
    my_ptrdiff_t ptrdiff= buf - table->record[0];
3183
 
    uchar *save_record_0= NULL;
 
2975
    unsigned char *save_record_0= NULL;
3184
2976
    KEY *key_info= NULL;
3185
2977
    KEY_PART_INFO *key_part;
3186
2978
    KEY_PART_INFO *key_part_end= NULL;
3202
2994
      key_part_end= key_part + key_info->key_parts;
3203
2995
      for (; key_part < key_part_end; key_part++)
3204
2996
      {
3205
 
        DBUG_ASSERT(key_part->field);
 
2997
        assert(key_part->field);
3206
2998
        key_part->field->move_field_offset(ptrdiff);
3207
2999
      }
3208
3000
    }
3221
3013
        key_part->field->move_field_offset(-ptrdiff);
3222
3014
    }
3223
3015
  }
3224
 
  DBUG_RETURN(error);
 
3016
  return(error);
3225
3017
}
3226
3018
 
3227
3019
 
3243
3035
                    bool update_create_info)
3244
3036
{
3245
3037
  int error= 1;
3246
 
  TABLE table;
 
3038
  Table table;
3247
3039
  char name_buff[FN_REFLEN];
3248
3040
  const char *name;
3249
3041
  TABLE_SHARE share;
3250
 
  DBUG_ENTER("ha_create_table");
3251
3042
  
3252
3043
  init_tmp_table_share(thd, &share, db, 0, table_name, path);
3253
3044
  if (open_table_def(thd, &share, 0) ||
3256
3047
    goto err;
3257
3048
 
3258
3049
  if (update_create_info)
3259
 
    update_create_info_from_table(create_info, &table);
 
3050
    table.updateCreateInfo(create_info);
3260
3051
 
3261
3052
  name= check_lowercase_names(table.file, share.path.str, name_buff);
3262
3053
 
3263
3054
  error= table.file->ha_create(name, &table, create_info);
3264
 
  VOID(closefrm(&table, 0));
 
3055
  closefrm(&table, 0);
3265
3056
  if (error)
3266
3057
  {
3267
 
    strxmov(name_buff, db, ".", table_name, NullS);
 
3058
    strxmov(name_buff, db, ".", table_name, NULL);
3268
3059
    my_error(ER_CANT_CREATE_TABLE, MYF(ME_BELL+ME_WAITTANG), name_buff, error);
3269
3060
  }
3270
3061
err:
3271
3062
  free_table_share(&share);
3272
 
  DBUG_RETURN(error != 0);
 
3063
  return(error != 0);
3273
3064
}
3274
3065
 
3275
3066
/**
3288
3079
int ha_create_table_from_engine(THD* thd, const char *db, const char *name)
3289
3080
{
3290
3081
  int error;
3291
 
  uchar *frmblob;
 
3082
  unsigned char *frmblob;
3292
3083
  size_t frmlen;
3293
3084
  char path[FN_REFLEN];
3294
3085
  HA_CREATE_INFO create_info;
3295
 
  TABLE table;
 
3086
  Table table;
3296
3087
  TABLE_SHARE share;
3297
 
  DBUG_ENTER("ha_create_table_from_engine");
3298
 
  DBUG_PRINT("enter", ("name '%s'.'%s'", db, name));
3299
3088
 
3300
 
  bzero((uchar*) &create_info,sizeof(create_info));
 
3089
  memset(&create_info, 0, sizeof(create_info));
3301
3090
  if ((error= ha_discover(thd, db, name, &frmblob, &frmlen)))
3302
3091
  {
3303
3092
    /* Table could not be discovered and thus not created */
3304
 
    DBUG_RETURN(error);
 
3093
    return(error);
3305
3094
  }
3306
3095
 
3307
3096
  /*
3312
3101
  build_table_filename(path, FN_REFLEN-1, db, name, "", 0);
3313
3102
  // Save the frm file
3314
3103
  error= writefrm(path, frmblob, frmlen);
3315
 
  my_free(frmblob, MYF(0));
 
3104
  free(frmblob);
3316
3105
  if (error)
3317
 
    DBUG_RETURN(2);
 
3106
    return(2);
3318
3107
 
3319
3108
  init_tmp_table_share(thd, &share, db, 0, name, path);
3320
3109
  if (open_table_def(thd, &share, 0))
3321
3110
  {
3322
 
    DBUG_RETURN(3);
 
3111
    return(3);
3323
3112
  }
3324
3113
  if (open_table_from_share(thd, &share, "" ,0, 0, 0, &table, OTM_OPEN))
3325
3114
  {
3326
3115
    free_table_share(&share);
3327
 
    DBUG_RETURN(3);
 
3116
    return(3);
3328
3117
  }
3329
3118
 
3330
 
  update_create_info_from_table(&create_info, &table);
 
3119
  table.updateCreateInfo(&create_info);
3331
3120
  create_info.table_options|= HA_OPTION_CREATE_FROM_ENGINE;
3332
3121
 
3333
3122
  check_lowercase_names(table.file, path, path);
3334
3123
  error=table.file->ha_create(path, &table, &create_info);
3335
 
  VOID(closefrm(&table, 1));
 
3124
  closefrm(&table, 1);
3336
3125
 
3337
 
  DBUG_RETURN(error != 0);
 
3126
  return(error != 0);
3338
3127
}
3339
3128
 
3340
3129
void st_ha_check_opt::init()
3357
3146
/**
3358
3147
  Init a key cache if it has not been initied before.
3359
3148
*/
3360
 
int ha_init_key_cache(const char *name, KEY_CACHE *key_cache)
 
3149
int ha_init_key_cache(const char *name __attribute__((unused)),
 
3150
                      KEY_CACHE *key_cache)
3361
3151
{
3362
 
  DBUG_ENTER("ha_init_key_cache");
3363
 
 
3364
3152
  if (!key_cache->key_cache_inited)
3365
3153
  {
3366
3154
    pthread_mutex_lock(&LOCK_global_system_variables);
3367
 
    ulong tmp_buff_size= (ulong) key_cache->param_buff_size;
3368
 
    uint tmp_block_size= (uint) key_cache->param_block_size;
3369
 
    uint division_limit= key_cache->param_division_limit;
3370
 
    uint age_threshold=  key_cache->param_age_threshold;
 
3155
    uint32_t tmp_buff_size= (uint32_t) key_cache->param_buff_size;
 
3156
    uint32_t tmp_block_size= (uint) key_cache->param_block_size;
 
3157
    uint32_t division_limit= key_cache->param_division_limit;
 
3158
    uint32_t age_threshold=  key_cache->param_age_threshold;
3371
3159
    pthread_mutex_unlock(&LOCK_global_system_variables);
3372
 
    DBUG_RETURN(!init_key_cache(key_cache,
 
3160
    return(!init_key_cache(key_cache,
3373
3161
                                tmp_block_size,
3374
3162
                                tmp_buff_size,
3375
3163
                                division_limit, age_threshold));
3376
3164
  }
3377
 
  DBUG_RETURN(0);
 
3165
  return(0);
3378
3166
}
3379
3167
 
3380
3168
 
3383
3171
*/
3384
3172
int ha_resize_key_cache(KEY_CACHE *key_cache)
3385
3173
{
3386
 
  DBUG_ENTER("ha_resize_key_cache");
3387
 
 
3388
3174
  if (key_cache->key_cache_inited)
3389
3175
  {
3390
3176
    pthread_mutex_lock(&LOCK_global_system_variables);
3391
3177
    long tmp_buff_size= (long) key_cache->param_buff_size;
3392
3178
    long tmp_block_size= (long) key_cache->param_block_size;
3393
 
    uint division_limit= key_cache->param_division_limit;
3394
 
    uint age_threshold=  key_cache->param_age_threshold;
 
3179
    uint32_t division_limit= key_cache->param_division_limit;
 
3180
    uint32_t age_threshold=  key_cache->param_age_threshold;
3395
3181
    pthread_mutex_unlock(&LOCK_global_system_variables);
3396
 
    DBUG_RETURN(!resize_key_cache(key_cache, tmp_block_size,
 
3182
    return(!resize_key_cache(key_cache, tmp_block_size,
3397
3183
                                  tmp_buff_size,
3398
3184
                                  division_limit, age_threshold));
3399
3185
  }
3400
 
  DBUG_RETURN(0);
 
3186
  return(0);
3401
3187
}
3402
3188
 
3403
3189
 
3409
3195
  if (key_cache->key_cache_inited)
3410
3196
  {
3411
3197
    pthread_mutex_lock(&LOCK_global_system_variables);
3412
 
    uint division_limit= key_cache->param_division_limit;
3413
 
    uint age_threshold=  key_cache->param_age_threshold;
 
3198
    uint32_t division_limit= key_cache->param_division_limit;
 
3199
    uint32_t age_threshold=  key_cache->param_age_threshold;
3414
3200
    pthread_mutex_unlock(&LOCK_global_system_variables);
3415
3201
    change_key_cache_param(key_cache, division_limit, age_threshold);
3416
3202
  }
3451
3237
{
3452
3238
  const char *db;
3453
3239
  const char *name;
3454
 
  uchar **frmblob; 
 
3240
  unsigned char **frmblob; 
3455
3241
  size_t *frmlen;
3456
3242
};
3457
3243
 
3458
 
static my_bool discover_handlerton(THD *thd, plugin_ref plugin,
3459
 
                                   void *arg)
 
3244
static bool discover_handlerton(THD *thd, plugin_ref plugin,
 
3245
                                void *arg)
3460
3246
{
3461
3247
  st_discover_args *vargs= (st_discover_args *)arg;
3462
3248
  handlerton *hton= plugin_data(plugin, handlerton *);
3464
3250
      (!(hton->discover(hton, thd, vargs->db, vargs->name, 
3465
3251
                        vargs->frmblob, 
3466
3252
                        vargs->frmlen))))
3467
 
    return TRUE;
 
3253
    return true;
3468
3254
 
3469
 
  return FALSE;
 
3255
  return false;
3470
3256
}
3471
3257
 
3472
3258
int ha_discover(THD *thd, const char *db, const char *name,
3473
 
                uchar **frmblob, size_t *frmlen)
 
3259
                unsigned char **frmblob, size_t *frmlen)
3474
3260
{
3475
3261
  int error= -1; // Table does not exist in any handler
3476
 
  DBUG_ENTER("ha_discover");
3477
 
  DBUG_PRINT("enter", ("db: %s, name: %s", db, name));
3478
3262
  st_discover_args args= {db, name, frmblob, frmlen};
3479
3263
 
3480
3264
  if (is_prefix(name,tmp_file_prefix)) /* skip temporary tables */
3481
 
    DBUG_RETURN(error);
 
3265
    return(error);
3482
3266
 
3483
3267
  if (plugin_foreach(thd, discover_handlerton,
3484
 
                 MYSQL_STORAGE_ENGINE_PLUGIN, &args))
 
3268
                 DRIZZLE_STORAGE_ENGINE_PLUGIN, &args))
3485
3269
    error= 0;
3486
3270
 
3487
3271
  if (!error)
3488
3272
    status_var_increment(thd->status_var.ha_discover_count);
3489
 
  DBUG_RETURN(error);
 
3273
  return(error);
3490
3274
}
3491
3275
 
3492
3276
 
3520
3304
  int err;
3521
3305
};
3522
3306
 
3523
 
static my_bool table_exists_in_engine_handlerton(THD *thd, plugin_ref plugin,
3524
 
                                   void *arg)
 
3307
static bool table_exists_in_engine_handlerton(THD *thd, plugin_ref plugin,
 
3308
                                              void *arg)
3525
3309
{
3526
3310
  st_table_exists_in_engine_args *vargs= (st_table_exists_in_engine_args *)arg;
3527
3311
  handlerton *hton= plugin_data(plugin, handlerton *);
3533
3317
 
3534
3318
  vargs->err = err;
3535
3319
  if (vargs->err == HA_ERR_TABLE_EXIST)
3536
 
    return TRUE;
 
3320
    return true;
3537
3321
 
3538
 
  return FALSE;
 
3322
  return false;
3539
3323
}
3540
3324
 
3541
3325
int ha_table_exists_in_engine(THD* thd, const char* db, const char* name)
3542
3326
{
3543
 
  DBUG_ENTER("ha_table_exists_in_engine");
3544
 
  DBUG_PRINT("enter", ("db: %s, name: %s", db, name));
3545
3327
  st_table_exists_in_engine_args args= {db, name, HA_ERR_NO_SUCH_TABLE};
3546
3328
  plugin_foreach(thd, table_exists_in_engine_handlerton,
3547
 
                 MYSQL_STORAGE_ENGINE_PLUGIN, &args);
3548
 
  DBUG_PRINT("exit", ("error: %d", args.err));
3549
 
  DBUG_RETURN(args.err);
 
3329
                 DRIZZLE_STORAGE_ENGINE_PLUGIN, &args);
 
3330
  return(args.err);
3550
3331
}
3551
3332
 
3552
3333
/**
3570
3351
    Estimated cost of 'index only' scan
3571
3352
*/
3572
3353
 
3573
 
double handler::index_only_read_time(uint keynr, double records)
 
3354
double handler::index_only_read_time(uint32_t keynr, double records)
3574
3355
{
3575
3356
  double read_time;
3576
 
  uint keys_per_block= (stats.block_size/2/
 
3357
  uint32_t keys_per_block= (stats.block_size/2/
3577
3358
                        (table->key_info[keynr].key_length + ref_length) + 1);
3578
3359
  read_time=((double) (records + keys_per_block-1) /
3579
3360
             (double) keys_per_block);
3616
3397
                  contain scan parameters.
3617
3398
*/
3618
3399
 
3619
 
ha_rows 
3620
 
handler::multi_range_read_info_const(uint keyno, RANGE_SEQ_IF *seq,
3621
 
                                     void *seq_init_param, uint n_ranges_arg,
3622
 
                                     uint *bufsz, uint *flags, COST_VECT *cost)
 
3400
ha_rows
 
3401
handler::multi_range_read_info_const(uint32_t keyno, RANGE_SEQ_IF *seq,
 
3402
                                     void *seq_init_param,
 
3403
                                     uint32_t n_ranges_arg __attribute__((unused)),
 
3404
                                     uint32_t *bufsz, uint32_t *flags, COST_VECT *cost)
3623
3405
{
3624
3406
  KEY_MULTI_RANGE range;
3625
3407
  range_seq_t seq_it;
3626
3408
  ha_rows rows, total_rows= 0;
3627
 
  uint n_ranges=0;
 
3409
  uint32_t n_ranges=0;
3628
3410
  THD *thd= current_thd;
3629
3411
  
3630
3412
  /* Default MRR implementation doesn't need buffer */
3707
3489
    other Error or can't perform the requested scan
3708
3490
*/
3709
3491
 
3710
 
int handler::multi_range_read_info(uint keyno, uint n_ranges, uint n_rows,
3711
 
                                   uint *bufsz, uint *flags, COST_VECT *cost)
 
3492
int handler::multi_range_read_info(uint32_t keyno, uint32_t n_ranges, uint32_t n_rows,
 
3493
                                   uint32_t *bufsz, uint32_t *flags, COST_VECT *cost)
3712
3494
{
3713
3495
  *bufsz= 0; /* Default implementation doesn't need a buffer */
3714
3496
 
3769
3551
 
3770
3552
int
3771
3553
handler::multi_range_read_init(RANGE_SEQ_IF *seq_funcs, void *seq_init_param,
3772
 
                               uint n_ranges, uint mode, HANDLER_BUFFER *buf)
 
3554
                               uint32_t n_ranges, uint32_t mode,
 
3555
                               HANDLER_BUFFER *buf __attribute__((unused)))
3773
3556
{
3774
 
  DBUG_ENTER("handler::multi_range_read_init");
3775
3557
  mrr_iter= seq_funcs->init(seq_init_param, n_ranges, mode);
3776
3558
  mrr_funcs= *seq_funcs;
3777
3559
  mrr_is_output_sorted= test(mode & HA_MRR_SORTED);
3778
 
  mrr_have_range= FALSE;
3779
 
  DBUG_RETURN(0);
 
3560
  mrr_have_range= false;
 
3561
  return(0);
3780
3562
}
3781
3563
 
3782
3564
 
3796
3578
int handler::multi_range_read_next(char **range_info)
3797
3579
{
3798
3580
  int result= 0;
3799
 
  int range_res;
3800
 
  DBUG_ENTER("handler::multi_range_read_next");
 
3581
  int range_res= 0;
3801
3582
 
3802
3583
  if (!mrr_have_range)
3803
3584
  {
3804
 
    mrr_have_range= TRUE;
 
3585
    mrr_have_range= true;
3805
3586
    goto start;
3806
3587
  }
3807
3588
 
3844
3625
  while ((result == HA_ERR_END_OF_FILE) && !range_res);
3845
3626
 
3846
3627
  *range_info= mrr_cur_range.ptr;
3847
 
  DBUG_PRINT("exit",("handler::multi_range_read_next result %d", result));
3848
 
  DBUG_RETURN(result);
 
3628
  return(result);
3849
3629
}
3850
3630
 
3851
3631
 
3873
3653
 
3874
3654
int DsMrr_impl::dsmrr_init(handler *h, KEY *key,
3875
3655
                           RANGE_SEQ_IF *seq_funcs, void *seq_init_param,
3876
 
                           uint n_ranges, uint mode, HANDLER_BUFFER *buf)
 
3656
                           uint32_t n_ranges, uint32_t mode, HANDLER_BUFFER *buf)
3877
3657
{
3878
 
  uint elem_size;
3879
 
  uint keyno;
 
3658
  uint32_t elem_size;
 
3659
  uint32_t keyno;
3880
3660
  Item *pushed_cond= NULL;
3881
3661
  handler *new_h2;
3882
 
  DBUG_ENTER("DsMrr_impl::dsmrr_init");
3883
3662
  keyno= h->active_index;
3884
 
  DBUG_ASSERT(h2 == NULL);
 
3663
  assert(h2 == NULL);
3885
3664
  if (mode & HA_MRR_USE_DEFAULT_IMPL || mode & HA_MRR_SORTED)
3886
3665
  {
3887
 
    use_default_impl= TRUE;
3888
 
    DBUG_RETURN(h->handler::multi_range_read_init(seq_funcs, seq_init_param,
 
3666
    use_default_impl= true;
 
3667
    return(h->handler::multi_range_read_init(seq_funcs, seq_init_param,
3889
3668
                                                  n_ranges, mode, buf));
3890
3669
  }
3891
3670
  rowids_buf= buf->buffer;
3907
3686
      new_h2->ha_external_lock(thd, F_RDLCK))
3908
3687
  {
3909
3688
    delete new_h2;
3910
 
    DBUG_RETURN(1);
 
3689
    return(1);
3911
3690
  }
3912
3691
 
3913
3692
  if (keyno == h->pushed_idx_cond_keyno)
3922
3701
  table->prepare_for_position();
3923
3702
  new_h2->extra(HA_EXTRA_KEYREAD);
3924
3703
 
3925
 
  if (h2->ha_index_init(keyno, FALSE) || 
 
3704
  if (h2->ha_index_init(keyno, false) || 
3926
3705
      h2->handler::multi_range_read_init(seq_funcs, seq_init_param, n_ranges,
3927
3706
                                         mode, buf))
3928
3707
    goto error;
3929
 
  use_default_impl= FALSE;
 
3708
  use_default_impl= false;
3930
3709
  
3931
3710
  if (pushed_cond)
3932
3711
    h2->idx_cond_push(keyno, pushed_cond);
3940
3719
  if (dsmrr_eof) 
3941
3720
    buf->end_of_used_area= rowids_buf_last;
3942
3721
 
3943
 
  if (h->ha_rnd_init(FALSE))
 
3722
  if (h->ha_rnd_init(false))
3944
3723
    goto error;
3945
3724
  
3946
 
  DBUG_RETURN(0);
 
3725
  return(0);
3947
3726
error:
3948
3727
  h2->ha_index_or_rnd_end();
3949
3728
  h2->ha_external_lock(thd, F_UNLCK);
3950
3729
  h2->close();
3951
3730
  delete h2;
3952
 
  DBUG_RETURN(1);
 
3731
  return(1);
3953
3732
}
3954
3733
 
3955
3734
 
3956
3735
void DsMrr_impl::dsmrr_close()
3957
3736
{
3958
 
  DBUG_ENTER("DsMrr_impl::dsmrr_close");
3959
3737
  if (h2)
3960
3738
  {
3961
3739
    h2->ha_external_lock(current_thd, F_UNLCK);
3963
3741
    delete h2;
3964
3742
    h2= NULL;
3965
3743
  }
3966
 
  use_default_impl= TRUE;
3967
 
  DBUG_VOID_RETURN;
 
3744
  use_default_impl= true;
 
3745
  return;
3968
3746
}
3969
3747
 
3970
3748
 
3971
 
static int rowid_cmp(void *h, uchar *a, uchar *b)
 
3749
static int rowid_cmp(void *h, unsigned char *a, unsigned char *b)
3972
3750
{
3973
3751
  return ((handler*)h)->cmp_ref(a, b);
3974
3752
}
3991
3769
  @retval other  Error
3992
3770
*/
3993
3771
 
3994
 
int DsMrr_impl::dsmrr_fill_buffer(handler *unused)
 
3772
int DsMrr_impl::dsmrr_fill_buffer(handler *unused __attribute__((unused)))
3995
3773
{
3996
3774
  char *range_info;
3997
 
  int res;
3998
 
  DBUG_ENTER("DsMrr_impl::dsmrr_fill_buffer");
 
3775
  int res = 0;
3999
3776
 
4000
3777
  rowids_buf_cur= rowids_buf;
4001
3778
  while ((rowids_buf_cur < rowids_buf_end) && 
4014
3791
  }
4015
3792
 
4016
3793
  if (res && res != HA_ERR_END_OF_FILE)
4017
 
    DBUG_RETURN(res); 
 
3794
    return(res); 
4018
3795
  dsmrr_eof= test(res == HA_ERR_END_OF_FILE);
4019
3796
 
4020
3797
  /* Sort the buffer contents by rowid */
4021
 
  uint elem_size= h->ref_length + (int)is_mrr_assoc * sizeof(void*);
4022
 
  uint n_rowids= (rowids_buf_cur - rowids_buf) / elem_size;
 
3798
  uint32_t elem_size= h->ref_length + (int)is_mrr_assoc * sizeof(void*);
 
3799
  uint32_t n_rowids= (rowids_buf_cur - rowids_buf) / elem_size;
4023
3800
  
4024
3801
  my_qsort2(rowids_buf, n_rowids, elem_size, (qsort2_cmp)rowid_cmp,
4025
3802
            (void*)h);
4026
3803
  rowids_buf_last= rowids_buf_cur;
4027
3804
  rowids_buf_cur=  rowids_buf;
4028
 
  DBUG_RETURN(0);
 
3805
  return(0);
4029
3806
}
4030
3807
 
4031
3808
 
4077
3854
/**
4078
3855
  DS-MRR implementation: multi_range_read_info() function
4079
3856
*/
4080
 
int DsMrr_impl::dsmrr_info(uint keyno, uint n_ranges, uint rows, uint *bufsz,
4081
 
                           uint *flags, COST_VECT *cost)
 
3857
int DsMrr_impl::dsmrr_info(uint32_t keyno, uint32_t n_ranges, uint32_t rows, uint32_t *bufsz,
 
3858
                           uint32_t *flags, COST_VECT *cost)
4082
3859
{  
4083
3860
  int res;
4084
 
  uint def_flags= *flags;
4085
 
  uint def_bufsz= *bufsz;
 
3861
  uint32_t def_flags= *flags;
 
3862
  uint32_t def_bufsz= *bufsz;
4086
3863
 
4087
3864
  /* Get cost/flags/mem_usage of default MRR implementation */
4088
3865
  res= h->handler::multi_range_read_info(keyno, n_ranges, rows, &def_bufsz,
4089
3866
                                         &def_flags, cost);
4090
 
  DBUG_ASSERT(!res);
 
3867
  assert(!res);
4091
3868
 
4092
3869
  if ((*flags & HA_MRR_USE_DEFAULT_IMPL) || 
4093
3870
      choose_mrr_impl(keyno, rows, &def_flags, &def_bufsz, cost))
4094
3871
  {
4095
3872
    /* Default implementation is choosen */
4096
 
    DBUG_PRINT("info", ("Default MRR implementation choosen"));
4097
3873
    *flags= def_flags;
4098
3874
    *bufsz= def_bufsz;
4099
3875
  }
4100
 
  else
4101
 
  {
4102
 
    DBUG_PRINT("info", ("DS-MRR implementation choosen"));
4103
 
  }
4104
3876
  return 0;
4105
3877
}
4106
3878
 
4109
3881
  DS-MRR Implementation: multi_range_read_info_const() function
4110
3882
*/
4111
3883
 
4112
 
ha_rows DsMrr_impl::dsmrr_info_const(uint keyno, RANGE_SEQ_IF *seq,
4113
 
                                 void *seq_init_param, uint n_ranges, 
4114
 
                                 uint *bufsz, uint *flags, COST_VECT *cost)
 
3884
ha_rows DsMrr_impl::dsmrr_info_const(uint32_t keyno, RANGE_SEQ_IF *seq,
 
3885
                                 void *seq_init_param, uint32_t n_ranges, 
 
3886
                                 uint32_t *bufsz, uint32_t *flags, COST_VECT *cost)
4115
3887
{
4116
3888
  ha_rows rows;
4117
 
  uint def_flags= *flags;
4118
 
  uint def_bufsz= *bufsz;
 
3889
  uint32_t def_flags= *flags;
 
3890
  uint32_t def_bufsz= *bufsz;
4119
3891
  /* Get cost/flags/mem_usage of default MRR implementation */
4120
3892
  rows= h->handler::multi_range_read_info_const(keyno, seq, seq_init_param,
4121
3893
                                                n_ranges, &def_bufsz, 
4134
3906
  if ((*flags & HA_MRR_USE_DEFAULT_IMPL) ||
4135
3907
      choose_mrr_impl(keyno, rows, flags, bufsz, cost))
4136
3908
  {
4137
 
    DBUG_PRINT("info", ("Default MRR implementation choosen"));
4138
3909
    *flags= def_flags;
4139
3910
    *bufsz= def_bufsz;
4140
3911
  }
4141
3912
  else
4142
3913
  {
4143
3914
    *flags &= ~HA_MRR_USE_DEFAULT_IMPL;
4144
 
    DBUG_PRINT("info", ("DS-MRR implementation choosen"));
4145
3915
  }
4146
3916
  return rows;
4147
3917
}
4161
3931
    Allow use of DS-MRR in cases where the index has partially-covered
4162
3932
    components but they are not used for scanning.
4163
3933
 
4164
 
  @retval TRUE   Yes
4165
 
  @retval FALSE  No
 
3934
  @retval true   Yes
 
3935
  @retval false  No
4166
3936
*/
4167
3937
 
4168
 
bool DsMrr_impl::key_uses_partial_cols(uint keyno)
 
3938
bool DsMrr_impl::key_uses_partial_cols(uint32_t keyno)
4169
3939
{
4170
3940
  KEY_PART_INFO *kp= table->key_info[keyno].key_part;
4171
3941
  KEY_PART_INFO *kp_end= kp + table->key_info[keyno].key_parts;
4172
3942
  for (; kp != kp_end; kp++)
4173
3943
  {
4174
3944
    if (!kp->field->part_of_key.is_set(keyno))
4175
 
      return TRUE;
 
3945
      return true;
4176
3946
  }
4177
 
  return FALSE;
 
3947
  return false;
4178
3948
}
4179
3949
 
4180
3950
 
4197
3967
                OUT  If DS-MRR is choosen, cost of DS-MRR scan
4198
3968
                     else the value is not modified
4199
3969
 
4200
 
  @retval TRUE   Default MRR implementation should be used
4201
 
  @retval FALSE  DS-MRR implementation should be used
 
3970
  @retval true   Default MRR implementation should be used
 
3971
  @retval false  DS-MRR implementation should be used
4202
3972
*/
4203
3973
 
4204
 
bool DsMrr_impl::choose_mrr_impl(uint keyno, ha_rows rows, uint *flags,
4205
 
                                 uint *bufsz, COST_VECT *cost)
 
3974
bool DsMrr_impl::choose_mrr_impl(uint32_t keyno, ha_rows rows, uint32_t *flags,
 
3975
                                 uint32_t *bufsz, COST_VECT *cost)
4206
3976
{
4207
3977
  COST_VECT dsmrr_cost;
4208
3978
  bool res;
4215
3985
  {
4216
3986
    /* Use the default implementation */
4217
3987
    *flags |= HA_MRR_USE_DEFAULT_IMPL;
4218
 
    return TRUE;
 
3988
    return true;
4219
3989
  }
4220
3990
  
4221
 
  uint add_len= table->key_info[keyno].key_length + h->ref_length; 
 
3991
  uint32_t add_len= table->key_info[keyno].key_length + h->ref_length; 
4222
3992
  *bufsz -= add_len;
4223
3993
  if (get_disk_sweep_mrr_cost(keyno, rows, *flags, bufsz, &dsmrr_cost))
4224
 
    return TRUE;
 
3994
    return true;
4225
3995
  *bufsz += add_len;
4226
3996
  
4227
3997
  bool force_dsmrr;
4240
4010
    *flags &= ~HA_MRR_USE_DEFAULT_IMPL;  /* Use the DS-MRR implementation */
4241
4011
    *flags &= ~HA_MRR_SORTED;          /* We will return unordered output */
4242
4012
    *cost= dsmrr_cost;
4243
 
    res= FALSE;
 
4013
    res= false;
4244
4014
  }
4245
4015
  else
4246
4016
  {
4247
4017
    /* Use the default MRR implementation */
4248
 
    res= TRUE;
 
4018
    res= true;
4249
4019
  }
4250
4020
  return res;
4251
4021
}
4252
4022
 
4253
4023
 
4254
 
static void get_sort_and_sweep_cost(TABLE *table, ha_rows nrows, COST_VECT *cost);
 
4024
static void get_sort_and_sweep_cost(Table *table, ha_rows nrows, COST_VECT *cost);
4255
4025
 
4256
4026
 
4257
4027
/**
4263
4033
  @param buffer_size INOUT  Buffer size
4264
4034
  @param cost        OUT    The cost
4265
4035
 
4266
 
  @retval FALSE  OK
4267
 
  @retval TRUE   Error, DS-MRR cannot be used (the buffer is too small
 
4036
  @retval false  OK
 
4037
  @retval true   Error, DS-MRR cannot be used (the buffer is too small
4268
4038
                 for even 1 rowid)
4269
4039
*/
4270
4040
 
4271
 
bool DsMrr_impl::get_disk_sweep_mrr_cost(uint keynr, ha_rows rows, uint flags,
4272
 
                                         uint *buffer_size, COST_VECT *cost)
 
4041
bool DsMrr_impl::get_disk_sweep_mrr_cost(uint32_t keynr, ha_rows rows, uint32_t flags,
 
4042
                                         uint32_t *buffer_size, COST_VECT *cost)
4273
4043
{
4274
 
  ulong max_buff_entries, elem_size;
 
4044
  uint32_t max_buff_entries, elem_size;
4275
4045
  ha_rows rows_in_full_step, rows_in_last_step;
4276
 
  uint n_full_steps;
 
4046
  uint32_t n_full_steps;
4277
4047
  double index_read_cost;
4278
4048
 
4279
4049
  elem_size= h->ref_length + sizeof(void*) * (!test(flags & HA_MRR_NO_ASSOCIATION));
4280
4050
  max_buff_entries = *buffer_size / elem_size;
4281
4051
 
4282
4052
  if (!max_buff_entries)
4283
 
    return TRUE; /* Buffer has not enough space for even 1 rowid */
 
4053
    return true; /* Buffer has not enough space for even 1 rowid */
4284
4054
 
4285
4055
  /* Number of iterations we'll make with full buffer */
4286
4056
  n_full_steps= (uint)floor(rows2double(rows) / max_buff_entries);
4302
4072
  else
4303
4073
  {
4304
4074
    cost->zero();
4305
 
    *buffer_size= max(*buffer_size, 
 
4075
    *buffer_size= cmax((ulong)*buffer_size, 
4306
4076
                      (size_t)(1.2*rows_in_last_step) * elem_size + 
4307
4077
                      h->ref_length + table->key_info[keynr].key_length);
4308
4078
  }
4319
4089
  /* Total cost of all index accesses */
4320
4090
  index_read_cost= h->index_only_read_time(keynr, (double)rows);
4321
4091
  cost->add_io(index_read_cost, 1 /* Random seeks */);
4322
 
  return FALSE;
 
4092
  return false;
4323
4093
}
4324
4094
 
4325
4095
 
4339
4109
*/
4340
4110
 
4341
4111
static 
4342
 
void get_sort_and_sweep_cost(TABLE *table, ha_rows nrows, COST_VECT *cost)
 
4112
void get_sort_and_sweep_cost(Table *table, ha_rows nrows, COST_VECT *cost)
4343
4113
{
4344
4114
  if (nrows)
4345
4115
  {
4346
 
    get_sweep_read_cost(table, nrows, FALSE, cost);
 
4116
    get_sweep_read_cost(table, nrows, false, cost);
4347
4117
    /* Add cost of qsort call: n * log2(n) * cost(rowid_comparison) */
4348
4118
    double cmp_op= rows2double(nrows) * (1.0 / TIME_FOR_COMPARE_ROWID);
4349
4119
    if (cmp_op < 3)
4393
4163
 
4394
4164
  @param table             Table to be accessed
4395
4165
  @param nrows             Number of rows to retrieve
4396
 
  @param interrupted       TRUE <=> Assume that the disk sweep will be
4397
 
                           interrupted by other disk IO. FALSE - otherwise.
 
4166
  @param interrupted       true <=> Assume that the disk sweep will be
 
4167
                           interrupted by other disk IO. false - otherwise.
4398
4168
  @param cost         OUT  The cost.
4399
4169
*/
4400
4170
 
4401
 
void get_sweep_read_cost(TABLE *table, ha_rows nrows, bool interrupted, 
 
4171
void get_sweep_read_cost(Table *table, ha_rows nrows, bool interrupted, 
4402
4172
                         COST_VECT *cost)
4403
4173
{
4404
 
  DBUG_ENTER("get_sweep_read_cost");
4405
 
 
4406
4174
  cost->zero();
4407
4175
  if (table->file->primary_key_is_clustered())
4408
4176
  {
4412
4180
  else
4413
4181
  {
4414
4182
    double n_blocks=
4415
 
      ceil(ulonglong2double(table->file->stats.data_file_length) / IO_SIZE);
 
4183
      ceil(uint64_t2double(table->file->stats.data_file_length) / IO_SIZE);
4416
4184
    double busy_blocks=
4417
4185
      n_blocks * (1.0 - pow(1.0 - 1.0/n_blocks, rows2double(nrows)));
4418
4186
    if (busy_blocks < 1.0)
4419
4187
      busy_blocks= 1.0;
4420
4188
 
4421
 
    DBUG_PRINT("info",("sweep: nblocks=%g, busy_blocks=%g", n_blocks,
4422
 
                       busy_blocks));
4423
4189
    cost->io_count= busy_blocks;
4424
4190
 
4425
4191
    if (!interrupted)
4429
4195
                          DISK_SEEK_PROP_COST*n_blocks/busy_blocks);
4430
4196
    }
4431
4197
  }
4432
 
  DBUG_PRINT("info",("returning cost=%g", cost->total_cost()));
4433
 
  DBUG_VOID_RETURN;
 
4198
  return;
4434
4199
}
4435
4200
 
4436
4201
 
4459
4224
int handler::read_range_first(const key_range *start_key,
4460
4225
                              const key_range *end_key,
4461
4226
                              bool eq_range_arg,
4462
 
                              bool sorted /* ignored */)
 
4227
                              bool sorted  __attribute__((unused)))
4463
4228
{
4464
4229
  int result;
4465
 
  DBUG_ENTER("handler::read_range_first");
4466
4230
 
4467
4231
  eq_range= eq_range_arg;
4468
4232
  end_range= 0;
4483
4247
                           start_key->keypart_map,
4484
4248
                           start_key->flag);
4485
4249
  if (result)
4486
 
    DBUG_RETURN((result == HA_ERR_KEY_NOT_FOUND) 
 
4250
    return((result == HA_ERR_KEY_NOT_FOUND) 
4487
4251
                ? HA_ERR_END_OF_FILE
4488
4252
                : result);
4489
4253
 
4490
 
  DBUG_RETURN (compare_key(end_range) <= 0 ? 0 : HA_ERR_END_OF_FILE);
 
4254
  return (compare_key(end_range) <= 0 ? 0 : HA_ERR_END_OF_FILE);
4491
4255
}
4492
4256
 
4493
4257
 
4507
4271
int handler::read_range_next()
4508
4272
{
4509
4273
  int result;
4510
 
  DBUG_ENTER("handler::read_range_next");
4511
4274
 
4512
4275
  if (eq_range)
4513
4276
  {
4514
4277
    /* We trust that index_next_same always gives a row in range */
4515
 
    DBUG_RETURN(index_next_same(table->record[0],
 
4278
    return(index_next_same(table->record[0],
4516
4279
                                end_range->key,
4517
4280
                                end_range->length));
4518
4281
  }
4519
4282
  result= index_next(table->record[0]);
4520
4283
  if (result)
4521
 
    DBUG_RETURN(result);
4522
 
  DBUG_RETURN(compare_key(end_range) <= 0 ? 0 : HA_ERR_END_OF_FILE);
 
4284
    return(result);
 
4285
  return(compare_key(end_range) <= 0 ? 0 : HA_ERR_END_OF_FILE);
4523
4286
}
4524
4287
 
4525
4288
 
4566
4329
  return cmp;
4567
4330
}
4568
4331
 
4569
 
int handler::index_read_idx_map(uchar * buf, uint index, const uchar * key,
 
4332
int handler::index_read_idx_map(unsigned char * buf, uint32_t index, const unsigned char * key,
4570
4333
                                key_part_map keypart_map,
4571
4334
                                enum ha_rkey_function find_flag)
4572
4335
{
4591
4354
  @retval
4592
4355
    pointer             pointer to TYPELIB structure
4593
4356
*/
4594
 
static my_bool exts_handlerton(THD *unused, plugin_ref plugin,
4595
 
                               void *arg)
 
4357
static bool exts_handlerton(THD *unused __attribute__((unused)),
 
4358
                            plugin_ref plugin,
 
4359
                            void *arg)
4596
4360
{
4597
4361
  List<char> *found_exts= (List<char> *) arg;
4598
4362
  handlerton *hton= plugin_data(plugin, handlerton *);
4617
4381
    }
4618
4382
    delete file;
4619
4383
  }
4620
 
  return FALSE;
 
4384
  return false;
4621
4385
}
4622
4386
 
4623
4387
TYPELIB *ha_known_exts(void)
4630
4394
    known_extensions_id= mysys_usage_id;
4631
4395
 
4632
4396
    plugin_foreach(NULL, exts_handlerton,
4633
 
                   MYSQL_STORAGE_ENGINE_PLUGIN, &found_exts);
 
4397
                   DRIZZLE_STORAGE_ENGINE_PLUGIN, &found_exts);
4634
4398
 
4635
4399
    ext= (const char **) my_once_alloc(sizeof(char *)*
4636
4400
                                       (found_exts.elements+1),
4637
4401
                                       MYF(MY_WME | MY_FAE));
4638
4402
 
4639
 
    DBUG_ASSERT(ext != 0);
 
4403
    assert(ext != 0);
4640
4404
    known_extensions.count= found_exts.elements;
4641
4405
    known_extensions.type_names= ext;
4642
4406
 
4649
4413
}
4650
4414
 
4651
4415
 
4652
 
static bool stat_print(THD *thd, const char *type, uint type_len,
4653
 
                       const char *file, uint file_len,
4654
 
                       const char *status, uint status_len)
 
4416
static bool stat_print(THD *thd, const char *type, uint32_t type_len,
 
4417
                       const char *file, uint32_t file_len,
 
4418
                       const char *status, uint32_t status_len)
4655
4419
{
4656
4420
  Protocol *protocol= thd->protocol;
4657
4421
  protocol->prepare_for_resend();
4659
4423
  protocol->store(file, file_len, system_charset_info);
4660
4424
  protocol->store(status, status_len, system_charset_info);
4661
4425
  if (protocol->write())
4662
 
    return TRUE;
4663
 
  return FALSE;
 
4426
    return true;
 
4427
  return false;
4664
4428
}
4665
4429
 
4666
4430
bool ha_show_status(THD *thd, handlerton *db_type, enum ha_stat_type stat)
4675
4439
 
4676
4440
  if (protocol->send_fields(&field_list,
4677
4441
                            Protocol::SEND_NUM_ROWS | Protocol::SEND_EOF))
4678
 
    return TRUE;
 
4442
    return true;
4679
4443
 
4680
4444
  result= db_type->show_status &&
4681
4445
    db_type->show_status(db_type, thd, stat_print, stat) ? 1 : 0;
4698
4462
  - table is not mysql.event
4699
4463
*/
4700
4464
 
4701
 
static bool check_table_binlog_row_based(THD *thd, TABLE *table)
 
4465
static bool check_table_binlog_row_based(THD *thd, Table *table)
4702
4466
{
4703
4467
  if (table->s->cached_row_logging_check == -1)
4704
4468
  {
4707
4471
    table->s->cached_row_logging_check= check;
4708
4472
  }
4709
4473
 
4710
 
  DBUG_ASSERT(table->s->cached_row_logging_check == 0 ||
 
4474
  assert(table->s->cached_row_logging_check == 0 ||
4711
4475
              table->s->cached_row_logging_check == 1);
4712
4476
 
4713
4477
  return (thd->current_stmt_binlog_row_based &&
4738
4502
 
4739
4503
static int write_locked_table_maps(THD *thd)
4740
4504
{
4741
 
  DBUG_ENTER("write_locked_table_maps");
4742
 
  DBUG_PRINT("enter", ("thd: 0x%lx  thd->lock: 0x%lx  thd->locked_tables: 0x%lx  "
4743
 
                       "thd->extra_lock: 0x%lx",
4744
 
                       (long) thd, (long) thd->lock,
4745
 
                       (long) thd->locked_tables, (long) thd->extra_lock));
4746
 
 
4747
4505
  if (thd->get_binlog_table_maps() == 0)
4748
4506
  {
4749
 
    MYSQL_LOCK *locks[3];
 
4507
    DRIZZLE_LOCK *locks[3];
4750
4508
    locks[0]= thd->extra_lock;
4751
4509
    locks[1]= thd->lock;
4752
4510
    locks[2]= thd->locked_tables;
4753
 
    for (uint i= 0 ; i < sizeof(locks)/sizeof(*locks) ; ++i )
 
4511
    for (uint32_t i= 0 ; i < sizeof(locks)/sizeof(*locks) ; ++i )
4754
4512
    {
4755
 
      MYSQL_LOCK const *const lock= locks[i];
 
4513
      DRIZZLE_LOCK const *const lock= locks[i];
4756
4514
      if (lock == NULL)
4757
4515
        continue;
4758
4516
 
4759
 
      TABLE **const end_ptr= lock->table + lock->table_count;
4760
 
      for (TABLE **table_ptr= lock->table ; 
 
4517
      Table **const end_ptr= lock->table + lock->table_count;
 
4518
      for (Table **table_ptr= lock->table ; 
4761
4519
           table_ptr != end_ptr ;
4762
4520
           ++table_ptr)
4763
4521
      {
4764
 
        TABLE *const table= *table_ptr;
4765
 
        DBUG_PRINT("info", ("Checking table %s", table->s->table_name.str));
 
4522
        Table *const table= *table_ptr;
4766
4523
        if (table->current_lock == F_WRLCK &&
4767
4524
            check_table_binlog_row_based(thd, table))
4768
4525
        {
4773
4530
            roll back the transaction.
4774
4531
          */
4775
4532
          if (unlikely(error))
4776
 
            DBUG_RETURN(1);
 
4533
            return(1);
4777
4534
        }
4778
4535
      }
4779
4536
    }
4780
4537
  }
4781
 
  DBUG_RETURN(0);
 
4538
  return(0);
4782
4539
}
4783
4540
 
4784
4541
 
4785
 
typedef bool Log_func(THD*, TABLE*, bool, const uchar*, const uchar*);
 
4542
typedef bool Log_func(THD*, Table*, bool, const unsigned char*, const unsigned char*);
4786
4543
 
4787
 
static int binlog_log_row(TABLE* table,
4788
 
                          const uchar *before_record,
4789
 
                          const uchar *after_record,
 
4544
static int binlog_log_row(Table* table,
 
4545
                          const unsigned char *before_record,
 
4546
                          const unsigned char *after_record,
4790
4547
                          Log_func *log_func)
4791
4548
{
4792
4549
  if (table->no_replicate)
4796
4553
 
4797
4554
  if (check_table_binlog_row_based(thd, table))
4798
4555
  {
4799
 
    DBUG_DUMP("read_set 10", (uchar*) table->read_set->bitmap,
4800
 
              (table->s->fields + 7) / 8);
4801
4556
    /*
4802
4557
      If there are no table maps written to the binary log, this is
4803
4558
      the first row handled in this statement. In that case, we need
4814
4569
 
4815
4570
int handler::ha_external_lock(THD *thd, int lock_type)
4816
4571
{
4817
 
  DBUG_ENTER("handler::ha_external_lock");
4818
4572
  /*
4819
4573
    Whether this is lock or unlock, this should be true, and is to verify that
4820
4574
    if get_auto_increment() was called (thus may have reserved intervals or
4821
4575
    taken a table lock), ha_release_auto_increment() was too.
4822
4576
  */
4823
 
  DBUG_ASSERT(next_insert_id == 0);
 
4577
  assert(next_insert_id == 0);
4824
4578
 
4825
4579
  /*
4826
4580
    We cache the table flags if the locking succeeded. Otherwise, we
4827
4581
    keep them as they were when they were fetched in ha_open().
4828
4582
  */
4829
 
  MYSQL_EXTERNAL_LOCK(lock_type);
 
4583
  DRIZZLE_EXTERNAL_LOCK(lock_type);
4830
4584
 
4831
4585
  int error= external_lock(thd, lock_type);
4832
4586
  if (error == 0)
4833
4587
    cached_table_flags= table_flags();
4834
 
  DBUG_RETURN(error);
 
4588
  return(error);
4835
4589
}
4836
4590
 
4837
4591
 
4840
4594
*/
4841
4595
int handler::ha_reset()
4842
4596
{
4843
 
  DBUG_ENTER("ha_reset");
4844
4597
  /* Check that we have called all proper deallocation functions */
4845
 
  DBUG_ASSERT((uchar*) table->def_read_set.bitmap +
 
4598
  assert((unsigned char*) table->def_read_set.bitmap +
4846
4599
              table->s->column_bitmap_size ==
4847
 
              (uchar*) table->def_write_set.bitmap);
4848
 
  DBUG_ASSERT(bitmap_is_set_all(&table->s->all_set));
4849
 
  DBUG_ASSERT(table->key_read == 0);
 
4600
              (unsigned char*) table->def_write_set.bitmap);
 
4601
  assert(bitmap_is_set_all(&table->s->all_set));
 
4602
  assert(table->key_read == 0);
4850
4603
  /* ensure that ha_index_end / ha_rnd_end has been called */
4851
 
  DBUG_ASSERT(inited == NONE);
 
4604
  assert(inited == NONE);
4852
4605
  /* Free cache used by filesort */
4853
4606
  free_io_cache(table);
4854
4607
  /* reset the bitmaps to point to defaults */
4855
4608
  table->default_column_bitmaps();
4856
 
  DBUG_RETURN(reset());
 
4609
  return(reset());
4857
4610
}
4858
4611
 
4859
4612
 
4860
 
int handler::ha_write_row(uchar *buf)
 
4613
int handler::ha_write_row(unsigned char *buf)
4861
4614
{
4862
4615
  int error;
4863
4616
  Log_func *log_func= Write_rows_log_event::binlog_row_logging_function;
4864
 
  DBUG_ENTER("handler::ha_write_row");
4865
 
  MYSQL_INSERT_ROW_START();
 
4617
  DRIZZLE_INSERT_ROW_START();
4866
4618
 
4867
4619
  mark_trx_read_write();
4868
4620
 
4869
4621
  if (unlikely(error= write_row(buf)))
4870
 
    DBUG_RETURN(error);
 
4622
    return(error);
4871
4623
  if (unlikely(error= binlog_log_row(table, 0, buf, log_func)))
4872
 
    DBUG_RETURN(error); /* purecov: inspected */
4873
 
  MYSQL_INSERT_ROW_END();
4874
 
  DBUG_RETURN(0);
 
4624
    return(error); /* purecov: inspected */
 
4625
  DRIZZLE_INSERT_ROW_END();
 
4626
  return(0);
4875
4627
}
4876
4628
 
4877
4629
 
4878
 
int handler::ha_update_row(const uchar *old_data, uchar *new_data)
 
4630
int handler::ha_update_row(const unsigned char *old_data, unsigned char *new_data)
4879
4631
{
4880
4632
  int error;
4881
4633
  Log_func *log_func= Update_rows_log_event::binlog_row_logging_function;
4884
4636
    Some storage engines require that the new record is in record[0]
4885
4637
    (and the old record is in record[1]).
4886
4638
   */
4887
 
  DBUG_ASSERT(new_data == table->record[0]);
 
4639
  assert(new_data == table->record[0]);
4888
4640
 
4889
4641
  mark_trx_read_write();
4890
4642
 
4895
4647
  return 0;
4896
4648
}
4897
4649
 
4898
 
int handler::ha_delete_row(const uchar *buf)
 
4650
int handler::ha_delete_row(const unsigned char *buf)
4899
4651
{
4900
4652
  int error;
4901
4653
  Log_func *log_func= Delete_rows_log_event::binlog_row_logging_function;