~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to plugin/innobase/handler/handler0alter.cc

  • Committer: tdavies
  • Date: 2010-10-10 05:31:41 UTC
  • mto: (1827.1.3 trunk-drizzle)
  • mto: This revision was merged to the branch mainline in revision 1829.
  • Revision ID: tdavies@molly-20101010053141-7rbcb8fe8a6xxrn8
Bug:621861 Changed C structs to C++ class in the following files: filesort.cc, filesort_info.h, sql_sort.h, table.h. removed the '_st' from the name of some of the classes. For more detail of changes made read the merge proposal notes.

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
1
/*****************************************************************************
2
2
 
3
 
Copyright (c) 2005, 2010, Innobase Oy. All Rights Reserved.
 
3
Copyright (c) 2005, 2009, Innobase Oy. All Rights Reserved.
4
4
 
5
5
This program is free software; you can redistribute it and/or modify it under
6
6
the terms of the GNU General Public License as published by the Free Software
103
103
#ifdef UNIV_DEBUG
104
104
        case DATA_MYSQL:
105
105
                ut_ad(flen >= len);
106
 
                ut_ad(DATA_MBMAXLEN(col->mbminmaxlen)
107
 
                      >= DATA_MBMINLEN(col->mbminmaxlen));
108
 
                ut_ad(DATA_MBMAXLEN(col->mbminmaxlen)
109
 
                      > DATA_MBMINLEN(col->mbminmaxlen) || flen == len);
 
106
                ut_ad(col->mbmaxlen >= col->mbminlen);
 
107
                ut_ad(col->mbmaxlen > col->mbminlen || flen == len);
110
108
                memcpy(dest, data, len);
111
109
                break;
112
110
 
233
231
innobase_check_index_keys(
234
232
/*======================*/
235
233
        const KeyInfo*  key_info,       /*!< in: Indexes to be created */
236
 
        ulint           num_of_keys,    /*!< in: Number of indexes to
 
234
        ulint           num_of_keys)    /*!< in: Number of indexes to
237
235
                                        be created */
238
 
        const dict_table_t*     table)  /*!< in: Existing indexes */
239
236
{
240
237
        ulint           key_num;
241
238
 
252
249
                        const KeyInfo&  key2 = key_info[i];
253
250
 
254
251
                        if (0 == strcmp(key.name, key2.name)) {
255
 
                                my_error(ER_WRONG_NAME_FOR_INDEX, MYF(0),
256
 
                                         key.name);
257
 
 
258
 
                                return(ER_WRONG_NAME_FOR_INDEX);
259
 
                        }
260
 
                }
261
 
 
262
 
                /* Check that the same index name does not already exist. */
263
 
 
264
 
                for (const dict_index_t* index
265
 
                             = dict_table_get_first_index(table);
266
 
                     index; index = dict_table_get_next_index(index)) {
267
 
 
268
 
                        if (0 == strcmp(key.name, index->name)) {
269
 
                                my_error(ER_WRONG_NAME_FOR_INDEX, MYF(0),
270
 
                                         key.name);
 
252
                                errmsg_printf(ERRMSG_LVL_ERROR, "InnoDB: key name `%s` appears"
 
253
                                                " twice in CREATE INDEX\n",
 
254
                                                key.name);
271
255
 
272
256
                                return(ER_WRONG_NAME_FOR_INDEX);
273
257
                        }
275
259
 
276
260
                /* Check that MySQL does not try to create a column
277
261
                prefix index field on an inappropriate data type and
278
 
                that the same column does not appear twice in the index. */
 
262
                that the same colum does not appear twice in the index. */
279
263
 
280
264
                for (ulint i = 0; i < key.key_parts; i++) {
281
265
                        const KeyPartInfo&      key_part1
306
290
                                        }
307
291
                                }
308
292
 
309
 
                                my_error(ER_WRONG_KEY_COLUMN, MYF(0),
310
 
                                         field->field_name);
 
293
                                errmsg_printf(ERRMSG_LVL_ERROR, "InnoDB: MySQL is trying to"
 
294
                                                " create a column prefix"
 
295
                                                " index field on an"
 
296
                                                " inappropriate data type."
 
297
                                                " column `%s`,"
 
298
                                                " index `%s`.\n",
 
299
                                                field->field_name,
 
300
                                                key.name);
311
301
                                return(ER_WRONG_KEY_COLUMN);
312
302
                        }
313
303
 
320
310
                                        continue;
321
311
                                }
322
312
 
323
 
                                my_error(ER_WRONG_KEY_COLUMN, MYF(0),
324
 
                                         key_part1.field->field_name);
 
313
                                errmsg_printf(ERRMSG_LVL_ERROR, "InnoDB: column `%s`"
 
314
                                                " is not allowed to occur"
 
315
                                                " twice in index `%s`.\n",
 
316
                                                key_part1.field->field_name,
 
317
                                                key.name);
325
318
                                return(ER_WRONG_KEY_COLUMN);
326
319
                        }
327
320
                }
522
515
                                     key_info->name, "PRIMARY");
523
516
 
524
517
        /* If there is a UNIQUE INDEX consisting entirely of NOT NULL
525
 
        columns and if the index does not contain column prefix(es)
526
 
        (only prefix/part of the column is indexed), MySQL will treat the
527
 
        index as a PRIMARY KEY unless the table already has one. */
 
518
        columns, MySQL will treat it as a PRIMARY KEY unless the
 
519
        table already has one. */
528
520
 
529
521
        if (!new_primary && (key_info->flags & HA_NOSAME)
530
 
            && (!(key_info->flags & HA_KEY_HAS_PART_KEY_SEG))
531
522
            && row_table_got_default_clust_index(table)) {
532
 
                uint    key_part = key_info->key_parts;
 
523
                uint    key_part = key_info->key_parts;
533
524
 
534
525
                new_primary = TRUE;
535
526
 
631
622
        ulint           num_created     = 0;
632
623
        ibool           dict_locked     = FALSE;
633
624
        ulint           new_primary;
634
 
        int             error;
 
625
        ulint           error;
635
626
 
636
627
        ut_a(i_table);
637
628
        ut_a(key_info);
658
649
        innodb_table = indexed_table
659
650
                = dict_table_get(prebuilt->table->name, FALSE);
660
651
 
661
 
        if (UNIV_UNLIKELY(!innodb_table)) {
662
 
                error = HA_ERR_NO_SUCH_TABLE;
663
 
                goto err_exit;
664
 
        }
 
652
        /* Check that index keys are sensible */
665
653
 
666
 
        /* Check if the index name is reserved. */
667
 
        if (innobase_index_name_is_reserved(trx, key_info, num_of_keys)) {
668
 
                error = -1;
669
 
        } else {
670
 
                /* Check that index keys are sensible */
671
 
                error = innobase_check_index_keys(key_info, num_of_keys,
672
 
                                                  innodb_table);
673
 
        }
 
654
        error = innobase_check_index_keys(key_info, num_of_keys);
674
655
 
675
656
        if (UNIV_UNLIKELY(error)) {
676
657
err_exit:
677
658
                mem_heap_free(heap);
678
 
                trx_general_rollback_for_mysql(trx, NULL);
 
659
                trx_general_rollback_for_mysql(trx, FALSE, NULL);
679
660
                trx_free_for_mysql(trx);
680
661
                trx_commit_for_mysql(prebuilt->trx);
681
662
                return(error);
716
697
        row_mysql_lock_data_dictionary(trx);
717
698
        dict_locked = TRUE;
718
699
 
719
 
        ut_d(dict_table_check_for_dup_indexes(innodb_table, FALSE));
720
 
 
721
700
        /* If a new primary key is defined for the table we need
722
701
        to drop the original table and rebuild all indexes. */
723
702
 
750
729
                                        user_session);
751
730
                        }
752
731
 
753
 
                        ut_d(dict_table_check_for_dup_indexes(innodb_table,
754
 
                                                              FALSE));
755
732
                        row_mysql_unlock_data_dictionary(trx);
756
733
                        goto err_exit;
757
734
                }
776
753
 
777
754
        ut_ad(error == DB_SUCCESS);
778
755
 
779
 
        /* We will need to rebuild index translation table. Set
780
 
        valid index entry count in the translation table to zero */
781
 
        share->idx_trans_tbl.index_count = 0;
782
 
 
783
756
        /* Commit the data dictionary transaction in order to release
784
 
        the table locks on the system tables.  This means that if
785
 
        MySQL crashes while creating a new primary key inside
786
 
        row_merge_build_indexes(), indexed_table will not be dropped
787
 
        by trx_rollback_active().  It will have to be recovered or
788
 
        dropped by the database administrator. */
 
757
        the table locks on the system tables.  Unfortunately, this
 
758
        means that if MySQL crashes while creating a new primary key
 
759
        inside row_merge_build_indexes(), indexed_table will not be
 
760
        dropped on crash recovery.  Thus, it will become orphaned. */
789
761
        trx_commit_for_mysql(trx);
790
762
 
791
763
        row_mysql_unlock_data_dictionary(trx);
815
787
                                        index, num_of_idx, i_table);
816
788
 
817
789
error_handling:
 
790
#ifdef UNIV_DEBUG
 
791
        /* TODO: At the moment we can't handle the following statement
 
792
        in our debugging code below:
 
793
 
 
794
        alter table t drop index b, add index (b);
 
795
 
 
796
        The fix will have to parse the SQL and note that the index
 
797
        being added has the same name as the the one being dropped and
 
798
        ignore that in the dup index check.*/
 
799
        //dict_table_check_for_dup_indexes(prebuilt->table);
 
800
#endif
818
801
 
819
802
        /* After an error, remove all those index definitions from the
820
803
        dictionary which were defined. */
827
810
                row_mysql_lock_data_dictionary(trx);
828
811
                dict_locked = TRUE;
829
812
 
830
 
                ut_d(dict_table_check_for_dup_indexes(prebuilt->table, TRUE));
831
 
 
832
813
                if (!new_primary) {
833
814
                        error = row_merge_rename_indexes(trx, indexed_table);
834
815
 
875
856
                indexed_table->n_mysql_handles_opened++;
876
857
 
877
858
                error = row_merge_drop_table(trx, innodb_table);
878
 
                innodb_table = indexed_table;
879
859
                goto convert_error;
880
860
 
881
861
        case DB_TOO_BIG_RECORD:
889
869
                prebuilt->trx->error_info = NULL;
890
870
                /* fall through */
891
871
        default:
892
 
                trx->error_state = DB_SUCCESS;
893
 
 
894
872
                if (new_primary) {
895
 
                        if (indexed_table != innodb_table) {
896
 
                                row_merge_drop_table(trx, indexed_table);
897
 
                        }
 
873
                        row_merge_drop_table(trx, indexed_table);
898
874
                } else {
899
875
                        if (!dict_locked) {
900
876
                                row_mysql_lock_data_dictionary(trx);
918
894
        }
919
895
 
920
896
        if (dict_locked) {
921
 
                ut_d(dict_table_check_for_dup_indexes(innodb_table, FALSE));
922
897
                row_mysql_unlock_data_dictionary(trx);
923
898
        }
924
899
 
961
936
        /* Test and mark all the indexes to be dropped */
962
937
 
963
938
        row_mysql_lock_data_dictionary(trx);
964
 
        ut_d(dict_table_check_for_dup_indexes(prebuilt->table, FALSE));
965
939
 
966
940
        /* Check that none of the indexes have previously been flagged
967
941
        for deletion. */
1127
1101
                } while (index);
1128
1102
        }
1129
1103
 
1130
 
        ut_d(dict_table_check_for_dup_indexes(prebuilt->table, FALSE));
1131
1104
        row_mysql_unlock_data_dictionary(trx);
1132
1105
 
1133
1106
        return(err);
1172
1145
                prebuilt->table->flags, user_session);
1173
1146
 
1174
1147
        row_mysql_lock_data_dictionary(trx);
1175
 
        ut_d(dict_table_check_for_dup_indexes(prebuilt->table, FALSE));
1176
1148
 
1177
1149
        if (UNIV_UNLIKELY(err)) {
1178
1150
 
1209
1181
                ut_a(!index->to_be_dropped);
1210
1182
        }
1211
1183
 
1212
 
        /* We will need to rebuild index translation table. Set
1213
 
        valid index entry count in the translation table to zero */
1214
 
        share->idx_trans_tbl.index_count = 0;
 
1184
#ifdef UNIV_DEBUG
 
1185
        dict_table_check_for_dup_indexes(prebuilt->table);
 
1186
#endif
1215
1187
 
1216
1188
func_exit:
1217
 
        ut_d(dict_table_check_for_dup_indexes(prebuilt->table, FALSE));
1218
1189
        trx_commit_for_mysql(trx);
1219
1190
        trx_commit_for_mysql(prebuilt->trx);
1220
1191
        row_mysql_unlock_data_dictionary(trx);