~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to drizzled/table.cc

  • Committer: Stewart Smith
  • Date: 2010-02-15 01:56:32 UTC
  • mto: (1273.13.96 build)
  • mto: This revision was merged to the branch mainline in revision 1308.
  • Revision ID: stewart@flamingspork.com-20100215015632-pm7lnxfq5j5uh8kj
move DATABASE() to function plugin. modify parser so that it looks for a function named 'database' when DATABASE() is called. Special case still needed in parser due to hilarity of not-really-reserved words.

Show diffs side-by-side

added added

removed removed

Lines of Context:
28
28
#include <drizzled/error.h>
29
29
#include <drizzled/gettext.h>
30
30
 
31
 
#include "drizzled/plugin/transactional_storage_engine.h"
32
 
#include "drizzled/plugin/authorization.h"
 
31
#include "drizzled/plugin/info_schema_table.h"
33
32
#include <drizzled/nested_join.h>
34
33
#include <drizzled/sql_parse.h>
35
34
#include <drizzled/item/sum.h>
80
79
  return (unsigned char*) (*buff)->field_name;
81
80
}
82
81
 
 
82
static TABLE_CATEGORY get_table_category(const LEX_STRING *db)
 
83
{
 
84
  assert(db != NULL);
 
85
 
 
86
  if ((db->length == INFORMATION_SCHEMA_NAME.length()) &&
 
87
      (my_strcasecmp(system_charset_info,
 
88
                    INFORMATION_SCHEMA_NAME.c_str(),
 
89
                    db->str) == 0))
 
90
  {
 
91
    return TABLE_CATEGORY_INFORMATION;
 
92
  }
 
93
 
 
94
  return TABLE_CATEGORY_USER;
 
95
}
 
96
 
 
97
 
83
98
/*
84
99
  Allocate a setup TableShare structure
85
100
 
100
115
  memory::Root mem_root;
101
116
  TableShare *share;
102
117
  char *key_buff, *path_buff;
103
 
  std::string path;
104
 
 
105
 
  build_table_filename(path, table_list->db, table_list->table_name, false);
106
 
 
 
118
  char path[FN_REFLEN];
 
119
  uint32_t path_length;
 
120
 
 
121
  path_length= build_table_filename(path, sizeof(path) - 1,
 
122
                                    table_list->db,
 
123
                                    table_list->table_name, false);
107
124
  memory::init_sql_alloc(&mem_root, TABLE_ALLOC_BLOCK_SIZE, 0);
108
125
  if (multi_alloc_root(&mem_root,
109
126
                       &share, sizeof(*share),
110
127
                       &key_buff, key_length,
111
 
                       &path_buff, path.length() + 1,
 
128
                       &path_buff, path_length + 1,
112
129
                       NULL))
113
130
  {
114
131
    memset(share, 0, sizeof(*share));
115
132
 
116
133
    share->set_table_cache_key(key_buff, key, key_length);
117
134
 
118
 
    share->path.str= path_buff,
119
 
    share->path.length= path.length();
120
 
    strcpy(share->path.str, path.c_str());
 
135
    share->path.str= path_buff;
 
136
    share->path.length= path_length;
 
137
    strcpy(share->path.str, path);
121
138
    share->normalized_path.str=    share->path.str;
122
 
    share->normalized_path.length= path.length();
 
139
    share->normalized_path.length= path_length;
123
140
 
124
141
    share->version=       refresh_version;
125
142
 
512
529
      break;
513
530
    case DRIZZLE_TYPE_ENUM:
514
531
      {
515
 
        message::Table::Field::EnumerationValues field_options= pfield.enumeration_values();
 
532
        message::Table::Field::SetFieldOptions field_options= pfield.set_options();
516
533
 
517
534
        field_pack_length[fieldnr]=
518
535
          get_enum_pack_length(field_options.field_value_size());
614
631
    if (pfield.type() != message::Table::Field::ENUM)
615
632
      continue;
616
633
 
617
 
    message::Table::Field::EnumerationValues field_options= pfield.enumeration_values();
 
634
    message::Table::Field::SetFieldOptions field_options= pfield.set_options();
618
635
 
619
636
    const CHARSET_INFO *charset= get_charset(field_options.has_collation_id() ?
620
637
                                             field_options.collation_id() : 0);
761
778
 
762
779
    if (field_type == DRIZZLE_TYPE_ENUM)
763
780
    {
764
 
      message::Table::Field::EnumerationValues field_options= pfield.enumeration_values();
 
781
      message::Table::Field::SetFieldOptions field_options= pfield.set_options();
765
782
 
766
783
      charset= get_charset(field_options.has_collation_id()?
767
784
                           field_options.collation_id() : 0);
873
890
    {
874
891
      field_length= 0;
875
892
 
876
 
      message::Table::Field::EnumerationValues fo= pfield.enumeration_values();
 
893
      message::Table::Field::SetFieldOptions fo= pfield.set_options();
877
894
 
878
 
      for (int valnr= 0; valnr < fo.field_value_size(); valnr++)
 
895
      for(int valnr= 0; valnr < fo.field_value_size(); valnr++)
879
896
      {
880
897
        if (fo.field_value(valnr).length() > field_length)
881
 
        {
882
898
          field_length= charset->cset->numchars(charset,
883
899
                                                fo.field_value(valnr).c_str(),
884
900
                                                fo.field_value(valnr).c_str()
885
901
                                                + fo.field_value(valnr).length())
886
902
            * charset->mbmaxlen;
887
 
        }
888
903
      }
889
904
    }
890
 
    break;
 
905
      break;
891
906
    case DRIZZLE_TYPE_LONG:
892
907
      {
893
908
        uint32_t sign_len= pfield.constraints().is_unsigned() ? 0 : 1;
1239
1254
   6    Unknown .frm version
1240
1255
*/
1241
1256
 
1242
 
int open_table_def(Session& session, TableIdentifier &identifier, TableShare *share)
 
1257
int open_table_def(Session& session, TableShare *share)
1243
1258
{
1244
1259
  int error;
1245
1260
  bool error_given;
1249
1264
 
1250
1265
  message::Table table;
1251
1266
 
1252
 
  error= plugin::StorageEngine::getTableDefinition(session, identifier, table);
 
1267
  error= plugin::StorageEngine::getTableDefinition(session, share->normalized_path.str,
 
1268
                                                   share->db.str,
 
1269
                                                   share->table_name.str,
 
1270
                                                   false,
 
1271
                                                   &table);
1253
1272
 
1254
1273
  if (error != EEXIST)
1255
1274
  {
1256
 
    if (error > 0)
 
1275
    if (error>0)
1257
1276
    {
1258
1277
      errno= error;
1259
1278
      error= 1;
1260
1279
    }
1261
1280
    else
1262
1281
    {
1263
 
      if (not table.IsInitialized())
 
1282
      if (!table.IsInitialized())
1264
1283
      {
1265
1284
        error= 4;
1266
1285
      }
1270
1289
 
1271
1290
  error= parse_table_proto(session, table, share);
1272
1291
 
1273
 
  share->table_category= TABLE_CATEGORY_USER;
 
1292
  share->table_category= get_table_category(& share->db);
 
1293
 
 
1294
  if (!error)
 
1295
    session.status_var.opened_shares++;
1274
1296
 
1275
1297
err_not_open:
1276
1298
  if (error && !error_given)
1324
1346
  outparam->resetTable(session, share, db_stat);
1325
1347
 
1326
1348
 
1327
 
  if (not (outparam->alias= strdup(alias)))
 
1349
  if (!(outparam->alias= strdup(alias)))
1328
1350
    goto err;
1329
1351
 
1330
1352
  /* Allocate Cursor */
1331
 
  if (not (outparam->cursor= share->db_type()->getCursor(*share, &outparam->mem_root)))
 
1353
  if (!(outparam->cursor= share->db_type()->getCursor(*share, &outparam->mem_root)))
1332
1354
    goto err;
1333
1355
 
1334
1356
  error= 4;
1500
1522
  memset(bitmaps, 0, bitmap_size*3);
1501
1523
#endif
1502
1524
 
1503
 
  return 0;
 
1525
  session->status_var.opened_tables++;
 
1526
 
 
1527
  return (0);
1504
1528
 
1505
1529
 err:
1506
1530
  if (!error_reported)
1546
1570
  cursor= 0;                            /* For easier errorchecking */
1547
1571
  if (free_share)
1548
1572
  {
1549
 
    if (s->tmp_table == message::Table::STANDARD)
 
1573
    if (s->tmp_table == NO_TMP_TABLE)
1550
1574
      TableShare::release(s);
1551
1575
    else
1552
1576
      s->free_table_share();
1672
1696
      my_error(ER_NO_SUCH_TABLE, MYF(0), db.str, table_name.str);
1673
1697
    else
1674
1698
    {
1675
 
      snprintf(buff, sizeof(buff), "%s",normalized_path.str);
 
1699
      sprintf(buff,"%s",normalized_path.str);
1676
1700
      my_error((db_errno == EMFILE) ? ER_CANT_OPEN_FILE : ER_FILE_NOT_FOUND,
1677
1701
               errortype, buff, db_errno);
1678
1702
    }
1692
1716
    }
1693
1717
    err_no= (db_errno == ENOENT) ? ER_FILE_NOT_FOUND : (db_errno == EAGAIN) ?
1694
1718
      ER_FILE_USED : ER_CANT_OPEN_FILE;
1695
 
    snprintf(buff, sizeof(buff), "%s%s", normalized_path.str,datext);
 
1719
    sprintf(buff,"%s%s", normalized_path.str,datext);
1696
1720
    my_error(err_no,errortype, buff, db_errno);
1697
1721
    delete cursor;
1698
1722
    break;
1712
1736
    break;
1713
1737
  }
1714
1738
  case 6:
1715
 
    snprintf(buff, sizeof(buff), "%s", normalized_path.str);
 
1739
    sprintf(buff,"%s", normalized_path.str);
1716
1740
    my_printf_error(ER_NOT_FORM_FILE,
1717
1741
                    _("Table '%-.64s' was created with a different version "
1718
1742
                    "of Drizzle and cannot be read"),
1722
1746
    break;
1723
1747
  default:                              /* Better wrong error than none */
1724
1748
  case 4:
1725
 
    snprintf(buff, sizeof(buff), "%s", normalized_path.str);
 
1749
    sprintf(buff,"%s", normalized_path.str);
1726
1750
    my_error(ER_NOT_FORM_FILE, errortype, buff, 0);
1727
1751
    break;
1728
1752
  }
1918
1942
    org_name            Name of database and length
1919
1943
 
1920
1944
  RETURN
1921
 
    false error
1922
 
    true ok
 
1945
    0   ok
 
1946
    1   error
1923
1947
*/
1924
1948
 
1925
 
bool check_db_name(SchemaIdentifier &schema_identifier)
 
1949
bool check_db_name(LEX_STRING *org_name)
1926
1950
{
1927
 
  if (not plugin::Authorization::isAuthorized(current_session->getSecurityContext(), schema_identifier))
1928
 
  {
1929
 
    return false;
1930
 
  }
1931
 
 
1932
 
  return schema_identifier.isValid();
 
1951
  char *name= org_name->str;
 
1952
  uint32_t name_length= org_name->length;
 
1953
 
 
1954
  if (!name_length || name_length > NAME_LEN || name[name_length - 1] == ' ')
 
1955
    return 1;
 
1956
 
 
1957
  my_casedn_str(files_charset_info, name);
 
1958
 
 
1959
  return check_identifier_name(org_name);
1933
1960
}
1934
1961
 
1935
1962
/*
3286
3313
  session->set_proc_info("removing tmp table");
3287
3314
 
3288
3315
  // Release latches since this can take a long time
3289
 
  plugin::TransactionalStorageEngine::releaseTemporaryLatches(session);
 
3316
  plugin::StorageEngine::releaseTemporaryLatches(session);
3290
3317
 
3291
3318
  if (cursor)
3292
3319
  {
3293
3320
    if (db_stat)
3294
3321
      cursor->closeMarkForDelete(s->table_name.str);
3295
3322
 
3296
 
    TableIdentifier identifier(s->getSchemaName(), s->table_name.str, s->table_name.str);
3297
 
    s->db_type()->doDropTable(*session, identifier);
 
3323
    s->db_type()->doDropTable(*session, s->table_name.str);
3298
3324
 
3299
3325
    delete cursor;
3300
3326
  }
3331
3357
  }
3332
3358
 
3333
3359
  // Release latches since this can take a long time
3334
 
  plugin::TransactionalStorageEngine::releaseTemporaryLatches(session);
 
3360
  plugin::StorageEngine::releaseTemporaryLatches(session);
3335
3361
 
3336
3362
  new_table= *table;
3337
3363
  share= *table->s;
3338
3364
  new_table.s= &share;
3339
3365
  new_table.s->storage_engine= myisam_engine;
3340
 
  if (not (new_table.cursor= new_table.s->db_type()->getCursor(share, &new_table.mem_root)))
 
3366
  if (!(new_table.cursor= new_table.s->db_type()->getCursor(share, &new_table.mem_root)))
3341
3367
    return true;                                // End of memory
3342
3368
 
3343
3369
  save_proc_info=session->get_proc_info();
3405
3431
  table->print_error(write_err, MYF(0));
3406
3432
  (void) table->cursor->ha_rnd_end();
3407
3433
  (void) new_table.cursor->close();
3408
 
 
3409
3434
 err1:
3410
 
  {
3411
 
    TableIdentifier identifier(new_table.s->getSchemaName(), new_table.s->table_name.str, new_table.s->table_name.str);
3412
 
    new_table.s->db_type()->doDropTable(*session, identifier);
3413
 
  }
3414
 
 
 
3435
  new_table.s->db_type()->doDropTable(*session, new_table.s->table_name.str);
3415
3436
 err2:
3416
3437
  delete new_table.cursor;
3417
3438
  session->set_proc_info(save_proc_info);
3670
3691
  session->slave_proxy_id, separated by '\0'.
3671
3692
*/
3672
3693
 
3673
 
bool Table::renameAlterTemporaryTable(TableIdentifier &identifier)
 
3694
bool Table::rename_temporary_table(const char *db, const char *table_name)
3674
3695
{
3675
3696
  char *key;
3676
3697
  uint32_t key_length;
3677
3698
  TableShare *share= s;
3678
3699
 
3679
 
  if (not (key=(char*) alloc_root(&share->mem_root, MAX_DBKEY_LENGTH)))
 
3700
  if (!(key=(char*) alloc_root(&share->mem_root, MAX_DBKEY_LENGTH)))
3680
3701
    return true;
3681
3702
 
3682
 
  key_length= TableShare::createKey(key, identifier);
 
3703
  key_length= TableShare::createKey(key, db, table_name);
3683
3704
  share->set_table_cache_key(key, key_length);
3684
3705
 
3685
 
  message::Table *message= share->getTableProto();
3686
 
 
3687
 
  message->set_name(identifier.getTableName());
3688
 
  message->set_schema(identifier.getSchemaName());
3689
 
 
3690
3706
  return false;
3691
3707
}
3692
3708