95
88
extern size_t table_def_size;
98
static enum_field_types proto_field_type_to_drizzle_type(const message::Table::Field &field)
90
/*****************************************************************************
91
Functions to handle table definition cach (TableShare)
92
*****************************************************************************/
95
Mark that we are not using table share anymore.
102
If ref_count goes to zero and (we have done a refresh or if we have
103
already too many open table shares) then delete the definition.
106
void TableShare::release(TableShare *share)
108
bool to_be_deleted= false;
109
safe_mutex_assert_owner(table::Cache::singleton().mutex().native_handle);
112
if (!--share->ref_count)
120
definition::Cache::singleton().erase(share->getCacheKey());
124
void TableShare::release(TableShare::shared_ptr &share)
126
bool to_be_deleted= false;
127
safe_mutex_assert_owner(table::Cache::singleton().mutex().native_handle);
130
if (!--share->ref_count)
138
definition::Cache::singleton().erase(share->getCacheKey());
142
void TableShare::release(const TableIdentifier &identifier)
144
TableShare::shared_ptr share= definition::Cache::singleton().find(identifier.getKey());
147
share->version= 0; // Mark for delete
148
if (share->ref_count == 0)
150
definition::Cache::singleton().erase(identifier.getKey());
156
static TableShare::shared_ptr foundTableShare(TableShare::shared_ptr share)
159
We found an existing table definition. Return it if we didn't get
160
an error when reading the table definition from file.
163
/* We must do a lock to ensure that the structure is initialized */
166
/* Table definition contained an error */
167
share->open_table_error(share->error, share->open_errno, share->errarg);
169
return TableShare::shared_ptr();
172
share->incrementTableCount();
178
Get TableShare for a table.
181
session Thread handle
182
table_list Table that should be opened
184
key_length Length of key
185
error out: Error code from open_table_def()
188
Get a table definition from the table definition cache.
189
If it doesn't exist, create a new from the table definition file.
192
We must have wrlock on table::Cache::singleton().mutex() when we come here
193
(To be changed later)
200
TableShare::shared_ptr TableShare::getShareCreate(Session *session,
201
const TableIdentifier &identifier,
204
TableShare::shared_ptr share;
208
/* Read table definition from cache */
209
if ((share= definition::Cache::singleton().find(identifier.getKey())))
210
return foundTableShare(share);
212
share.reset(new TableShare(message::Table::STANDARD, identifier));
214
if (share->open_table_def(*session, identifier))
216
in_error= share->error;
218
return TableShare::shared_ptr();
220
share->ref_count++; // Mark in use
222
plugin::EventObserver::registerTableEvents(*share);
224
bool ret= definition::Cache::singleton().insert(identifier.getKey(), share);
227
return TableShare::shared_ptr();
232
static enum_field_types proto_field_type_to_drizzle_type(uint32_t proto_field_type)
234
enum_field_types field_type;
236
switch(proto_field_type)
102
238
case message::Table::Field::INTEGER:
103
return DRIZZLE_TYPE_LONG;
239
field_type= DRIZZLE_TYPE_LONG;
105
241
case message::Table::Field::DOUBLE:
106
return DRIZZLE_TYPE_DOUBLE;
108
case message::Table::Field::EPOCH:
109
if (field.has_time_options() and field.time_options().microseconds())
110
return DRIZZLE_TYPE_MICROTIME;
112
return DRIZZLE_TYPE_TIMESTAMP;
242
field_type= DRIZZLE_TYPE_DOUBLE;
244
case message::Table::Field::TIMESTAMP:
245
field_type= DRIZZLE_TYPE_TIMESTAMP;
114
247
case message::Table::Field::BIGINT:
115
return DRIZZLE_TYPE_LONGLONG;
248
field_type= DRIZZLE_TYPE_LONGLONG;
117
250
case message::Table::Field::DATETIME:
118
return DRIZZLE_TYPE_DATETIME;
251
field_type= DRIZZLE_TYPE_DATETIME;
120
253
case message::Table::Field::DATE:
121
return DRIZZLE_TYPE_DATE;
254
field_type= DRIZZLE_TYPE_DATE;
123
256
case message::Table::Field::VARCHAR:
124
return DRIZZLE_TYPE_VARCHAR;
257
field_type= DRIZZLE_TYPE_VARCHAR;
126
259
case message::Table::Field::DECIMAL:
127
return DRIZZLE_TYPE_DECIMAL;
260
field_type= DRIZZLE_TYPE_DECIMAL;
129
262
case message::Table::Field::ENUM:
130
return DRIZZLE_TYPE_ENUM;
263
field_type= DRIZZLE_TYPE_ENUM;
132
265
case message::Table::Field::BLOB:
133
return DRIZZLE_TYPE_BLOB;
266
field_type= DRIZZLE_TYPE_BLOB;
135
268
case message::Table::Field::UUID:
136
return DRIZZLE_TYPE_UUID;
138
case message::Table::Field::BOOLEAN:
139
return DRIZZLE_TYPE_BOOLEAN;
141
case message::Table::Field::TIME:
142
return DRIZZLE_TYPE_TIME;
269
field_type= DRIZZLE_TYPE_UUID;
273
abort(); // Programming error
148
279
static Item *default_value_item(enum_field_types field_type,
576
719
table_name.str= db.str + db.length + 1;
577
720
table_name.length= strlen(table_name.str);
579
getTableMessage()->set_name(identifier_arg.getTableName());
580
getTableMessage()->set_schema(identifier_arg.getSchemaName());
722
table_proto->set_name(identifier_arg.getTableName());
723
table_proto->set_schema(identifier_arg.getSchemaName());
583
bool TableShare::parse_table_proto(Session& session, message::Table &table)
726
int TableShare::inner_parse_table_proto(Session& session, message::Table &table)
585
drizzled::error_t local_error= EE_OK;
587
730
if (! table.IsInitialized())
589
my_error(ER_CORRUPT_TABLE_DEFINITION, MYF(0),
590
table.name().empty() ? " " : table.name().c_str(),
591
table.InitializationErrorString().c_str());
732
my_error(ER_CORRUPT_TABLE_DEFINITION, MYF(0), table.InitializationErrorString().c_str());
593
733
return ER_CORRUPT_TABLE_DEFINITION;
596
setTableMessage(table);
736
setTableProto(new(nothrow) message::Table(table));
598
738
storage_engine= plugin::StorageEngine::findByName(session, table.engine().name());
599
739
assert(storage_engine); // We use an assert() here because we should never get this far and still have no suitable engine.
620
760
table_charset= get_charset(table_options.collation_id());
622
if (not table_charset)
624
my_error(ER_CORRUPT_TABLE_DEFINITION_UNKNOWN_COLLATION, MYF(0),
625
table_options.collation().c_str(),
626
table.name().c_str());
765
snprintf(errmsg, sizeof(errmsg),
766
_("Table %s has invalid/unknown collation: %d,%s"),
768
table_options.collation_id(),
769
table_options.collation().c_str());
628
return ER_CORRUPT_TABLE_DEFINITION; // Historical
772
my_error(ER_CORRUPT_TABLE_DEFINITION, MYF(0), errmsg);
773
return ER_CORRUPT_TABLE_DEFINITION;
631
776
db_record_offset= 1;
778
blob_ptr_size= portable_sizeof_char_ptr; // more bonghits.
633
780
keys= table.indexes_size();
790
937
std::vector<uint32_t> field_offsets;
791
938
std::vector<uint32_t> field_pack_length;
793
field_offsets.resize(_field_size);
794
field_pack_length.resize(_field_size);
940
field_offsets.resize(fields);
941
field_pack_length.resize(fields);
796
943
uint32_t interval_count= 0;
797
944
uint32_t interval_parts= 0;
799
946
uint32_t stored_columns_reclength= 0;
801
for (unsigned int fieldnr= 0; fieldnr < _field_size; fieldnr++)
948
for (unsigned int fieldnr= 0; fieldnr < fields; fieldnr++)
803
950
message::Table::Field pfield= table.field(fieldnr);
804
if (pfield.constraints().is_nullable()) // Historical reference
808
else if (not pfield.constraints().is_notnull())
951
if (pfield.constraints().is_nullable())
813
enum_field_types drizzle_field_type= proto_field_type_to_drizzle_type(pfield);
954
enum_field_types drizzle_field_type=
955
proto_field_type_to_drizzle_type(pfield.type());
815
957
field_offsets[fieldnr]= stored_columns_reclength;
1164
1315
case DRIZZLE_TYPE_LONGLONG:
1166
uint32_t sign_len= pfield.constraints().is_unsigned() ? 0 : 1;
1167
field_length= MAX_BIGINT_WIDTH+sign_len;
1316
field_length= MAX_BIGINT_WIDTH;
1170
1318
case DRIZZLE_TYPE_UUID:
1171
1319
field_length= field::Uuid::max_string_length();
1173
case DRIZZLE_TYPE_BOOLEAN:
1174
field_length= field::Boolean::max_string_length();
1176
case DRIZZLE_TYPE_MICROTIME:
1177
field_length= field::Microtime::max_string_length();
1179
case DRIZZLE_TYPE_TIMESTAMP:
1180
field_length= field::Epoch::max_string_length();
1182
case DRIZZLE_TYPE_TIME:
1183
field_length= field::Time::max_string_length();
1185
1321
case DRIZZLE_TYPE_NULL:
1186
1322
abort(); // Programming error
1189
bool is_not_null= false;
1191
if (not pfield.constraints().is_nullable())
1195
else if (pfield.constraints().is_notnull())
1200
Field* f= make_field(pfield,
1201
record + field_offsets[fieldnr] + data_offset,
1325
assert(enum_field_types_size == 12);
1327
Field* f= make_field(record + field_offsets[fieldnr] + data_offset,
1329
pfield.constraints().is_nullable(),
1525
1664
6 Unknown .frm version
1528
int TableShare::open_table_def(Session& session, const identifier::Table &identifier)
1667
int TableShare::open_table_def(Session& session, const TableIdentifier &identifier)
1530
drizzled::error_t local_error= EE_OK;
1532
message::table::shared_ptr table= plugin::StorageEngine::getTableMessage(session, identifier, local_error);
1534
if (table and table->IsInitialized())
1675
message::table::shared_ptr table;
1677
local_error= plugin::StorageEngine::getTableDefinition(session, identifier, table);
1679
if (local_error != EEXIST)
1536
if (parse_table_proto(session, *table))
1681
if (local_error > 0)
1538
local_error= ER_CORRUPT_TABLE_DEFINITION_UNKNOWN;
1539
my_error(ER_CORRUPT_TABLE_DEFINITION_UNKNOWN, identifier);
1543
setTableCategory(TABLE_CATEGORY_USER);
1688
if (not table->IsInitialized())
1547
else if (table and not table->IsInitialized())
1549
local_error= ER_CORRUPT_TABLE_DEFINITION_UNKNOWN;
1550
my_error(ER_CORRUPT_TABLE_DEFINITION_UNKNOWN, identifier);
1554
local_error= ER_TABLE_UNKNOWN;
1555
my_error(ER_TABLE_UNKNOWN, identifier);
1558
return static_cast<int>(local_error);
1696
local_error= parse_table_proto(session, *table);
1698
setTableCategory(TABLE_CATEGORY_USER);
1701
if (local_error && !error_given)
1704
open_table_error(error, (open_errno= errno), 0);