12
12
You should have received a copy of the GNU General Public License
13
13
along with this program; if not, write to the Free Software
14
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */
14
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
17
17
/* Insert of records */
19
19
#include "config.h"
21
20
#include <drizzled/sql_select.h>
22
21
#include <drizzled/show.h>
23
22
#include <drizzled/error.h>
315
293
if (values->elements != value_count)
317
295
my_error(ER_WRONG_VALUE_COUNT_ON_ROW, MYF(0), counter);
320
table->cursor->ha_release_auto_increment();
322
free_underlaid_joins(session, &session->lex->select_lex);
323
session->abort_on_warning= 0;
324
DRIZZLE_INSERT_DONE(1, 0);
328
298
if (setup_fields(session, 0, *values, MARK_COLUMNS_READ, 0, 0))
331
table->cursor->ha_release_auto_increment();
333
free_underlaid_joins(session, &session->lex->select_lex);
334
session->abort_on_warning= 0;
335
DRIZZLE_INSERT_DONE(1, 0);
446
411
transactional_table= table->cursor->has_transactions();
448
413
changed= (info.copied || info.deleted || info.updated);
449
if ((changed && error <= 0) || session->transaction.stmt.hasModifiedNonTransData())
414
if ((changed && error <= 0) || session->transaction.stmt.modified_non_trans_table)
451
if (session->transaction.stmt.hasModifiedNonTransData())
452
session->transaction.all.markModifiedNonTransData();
416
if (session->transaction.stmt.modified_non_trans_table)
417
session->transaction.all.modified_non_trans_table= true;
454
assert(transactional_table || !changed || session->transaction.stmt.hasModifiedNonTransData());
419
assert(transactional_table || !changed || session->transaction.stmt.modified_non_trans_table);
457
422
session->set_proc_info("end");
502
snprintf(buff, sizeof(buff), ER(ER_INSERT_INFO), (ulong) info.records,
458
sprintf(buff, ER(ER_INSERT_INFO), (ulong) info.records,
503
459
(ulong) (info.records - info.copied), (ulong) session->cuted_fields);
505
snprintf(buff, sizeof(buff), ER(ER_INSERT_INFO), (ulong) info.records,
461
sprintf(buff, ER(ER_INSERT_INFO), (ulong) info.records,
506
462
(ulong) (info.deleted + info.updated), (ulong) session->cuted_fields);
507
463
session->row_count_func= info.copied + info.deleted + info.updated;
508
464
session->my_ok((ulong) session->row_count_func,
509
465
info.copied + info.deleted + info.touched, id, buff);
511
session->status_var.inserted_row_count+= session->row_count_func;
512
467
session->abort_on_warning= 0;
513
468
DRIZZLE_INSERT_DONE(0, session->row_count_func);
473
table->cursor->ha_release_auto_increment();
475
free_underlaid_joins(session, &session->lex->select_lex);
476
session->abort_on_warning= 0;
477
DRIZZLE_INSERT_DONE(1, 0);
819
key.resize(table->getShare()->max_unique_length);
782
if (!(key=(char*) malloc(table->s->max_unique_length)))
821
key_copy(&key[0], table->getInsertRecord(), table->key_info+key_nr, 0);
822
if ((error=(table->cursor->index_read_idx_map(table->getUpdateRecord(),key_nr,
823
&key[0], HA_WHOLE_KEY,
788
key_copy((unsigned char*) key,table->record[0],table->key_info+key_nr,0);
789
if ((error=(table->cursor->index_read_idx_map(table->record[1],key_nr,
790
(unsigned char*) key, HA_WHOLE_KEY,
824
791
HA_READ_KEY_EXACT))))
846
813
table->cursor->adjust_next_insert_id_after_explicit_value(
847
814
table->next_number_field->val_int());
850
if (! table->records_are_comparable() || table->compare_records())
816
if ((table->cursor->getEngine()->check_flag(HTON_BIT_PARTIAL_COLUMN_READ) &&
817
!bitmap_is_subset(table->write_set, table->read_set)) ||
818
table->compare_record())
852
if ((error=table->cursor->updateRecord(table->getUpdateRecord(),
853
table->getInsertRecord())) &&
820
if ((error=table->cursor->ha_update_row(table->record[1],
821
table->record[0])) &&
854
822
error != HA_ERR_RECORD_IS_THE_SAME)
856
824
if (info->ignore &&
1068
1040
List<Item> *update_fields,
1069
1041
List<Item> *update_values,
1070
1042
enum_duplicates duplic,
1071
bool ignore_check_option_errors) :
1072
table_list(table_list_par), table(table_par), fields(fields_par),
1073
autoinc_value_of_last_inserted_row(0),
1074
insert_into_view(table_list_par && 0 != 0)
1043
bool ignore_check_option_errors)
1044
:table_list(table_list_par), table(table_par), fields(fields_par),
1045
autoinc_value_of_last_inserted_row(0),
1046
insert_into_view(table_list_par && 0 != 0)
1048
memset(&info, 0, sizeof(info));
1076
1049
info.handle_duplicates= duplic;
1077
1050
info.ignore= ignore_check_option_errors;
1078
1051
info.update_fields= update_fields;
1352
1324
We must invalidate the table in the query cache before binlog writing
1353
and autocommitOrRollback.
1325
and ha_autocommit_or_rollback.
1355
if (session->transaction.stmt.hasModifiedNonTransData())
1356
session->transaction.all.markModifiedNonTransData();
1327
if (session->transaction.stmt.modified_non_trans_table)
1328
session->transaction.all.modified_non_trans_table= true;
1358
1330
assert(trans_table || !changed ||
1359
session->transaction.stmt.hasModifiedNonTransData());
1331
session->transaction.stmt.modified_non_trans_table);
1361
1333
table->cursor->ha_release_auto_increment();
1369
1341
char buff[160];
1370
1342
if (info.ignore)
1371
snprintf(buff, sizeof(buff), ER(ER_INSERT_INFO), (ulong) info.records,
1343
sprintf(buff, ER(ER_INSERT_INFO), (ulong) info.records,
1372
1344
(ulong) (info.records - info.copied), (ulong) session->cuted_fields);
1374
snprintf(buff, sizeof(buff), ER(ER_INSERT_INFO), (ulong) info.records,
1346
sprintf(buff, ER(ER_INSERT_INFO), (ulong) info.records,
1375
1347
(ulong) (info.deleted+info.updated), (ulong) session->cuted_fields);
1376
1348
session->row_count_func= info.copied + info.deleted + info.updated;
1481
1452
static Table *create_table_from_items(Session *session, HA_CREATE_INFO *create_info,
1482
1453
TableList *create_table,
1483
message::Table &table_proto,
1454
message::Table *table_proto,
1484
1455
AlterInfo *alter_info,
1485
1456
List<Item> *items,
1486
1457
bool is_if_not_exists,
1488
TableIdentifier &identifier)
1458
DRIZZLE_LOCK **lock)
1490
TableShare share(message::Table::INTERNAL);
1460
Table tmp_table; // Used during 'CreateField()'
1491
1463
uint32_t select_field_count= items->elements;
1492
1464
/* Add selected items to field list */
1493
1465
List_iterator_fast<Item> it(*items);
1503
1478
create_info->table_existed= 1; // Mark that table existed
1504
1479
push_warning_printf(session, DRIZZLE_ERROR::WARN_LEVEL_NOTE,
1505
1480
ER_TABLE_EXISTS_ERROR, ER(ER_TABLE_EXISTS_ERROR),
1506
create_table->getTableName());
1481
create_table->table_name);
1507
1482
return create_table->table;
1510
my_error(ER_TABLE_EXISTS_ERROR, MYF(0), create_table->getTableName());
1485
my_error(ER_TABLE_EXISTS_ERROR, MYF(0), create_table->table_name);
1490
tmp_table.timestamp_field= 0;
1491
tmp_table.s= &share;
1493
tmp_table.s->db_create_options=0;
1494
tmp_table.s->blob_ptr_size= portable_sizeof_char_ptr;
1495
tmp_table.s->db_low_byte_first=
1496
test(create_info->db_type == myisam_engine ||
1497
create_info->db_type == heap_engine);
1498
tmp_table.null_row= false;
1499
tmp_table.maybe_null= false;
1515
table::Shell tmp_table(share); // Used during 'CreateField()'
1516
tmp_table.timestamp_field= 0;
1518
tmp_table.getMutableShare()->db_create_options= 0;
1519
tmp_table.getMutableShare()->blob_ptr_size= portable_sizeof_char_ptr;
1521
if (not table_proto.engine().name().compare("MyISAM"))
1522
tmp_table.getMutableShare()->db_low_byte_first= true;
1523
else if (not table_proto.engine().name().compare("MEMORY"))
1524
tmp_table.getMutableShare()->db_low_byte_first= true;
1526
tmp_table.null_row= false;
1527
tmp_table.maybe_null= false;
1529
tmp_table.in_use= session;
1533
CreateField *cr_field;
1534
Field *field, *def_field;
1535
if (item->type() == Item::FUNC_ITEM)
1537
if (item->result_type() != STRING_RESULT)
1539
field= item->tmp_table_field(&tmp_table);
1543
field= item->tmp_table_field_from_field_type(&tmp_table, 0);
1503
CreateField *cr_field;
1504
Field *field, *def_field;
1505
if (item->type() == Item::FUNC_ITEM)
1506
if (item->result_type() != STRING_RESULT)
1507
field= item->tmp_table_field(&tmp_table);
1548
field= create_tmp_field(session, &tmp_table, item, item->type(),
1549
(Item ***) 0, &tmp_field, &def_field, false,
1554
!(cr_field=new CreateField(field,(item->type() == Item::FIELD_ITEM ?
1555
((Item_field *)item)->field :
1561
if (item->maybe_null)
1563
cr_field->flags &= ~NOT_NULL_FLAG;
1566
alter_info->create_list.push_back(cr_field);
1509
field= item->tmp_table_field_from_field_type(&tmp_table, 0);
1511
field= create_tmp_field(session, &tmp_table, item, item->type(),
1512
(Item ***) 0, &tmp_field, &def_field, 0, 0, 0, 0,
1515
!(cr_field=new CreateField(field,(item->type() == Item::FIELD_ITEM ?
1516
((Item_field *)item)->field :
1519
if (item->maybe_null)
1520
cr_field->flags &= ~NOT_NULL_FLAG;
1521
alter_info->create_list.push_back(cr_field);
1524
TableIdentifier identifier(create_table->db,
1525
create_table->table_name,
1526
lex_identified_temp_table ? TEMP_TABLE :
1571
1531
Create and lock table.
1574
1534
creating base table on which name we have exclusive lock. So code below
1575
1535
should not cause deadlocks or races.
1579
if (not mysql_create_table_no_lock(session,
1538
if (!mysql_create_table_no_lock(session,
1588
if (create_info->table_existed && not identifier.isTmp())
1547
if (create_info->table_existed &&
1548
!(lex_identified_temp_table))
1591
1551
This means that someone created table underneath server
1592
1552
or it was created via different mysqld front-end to the
1593
1553
cluster. We don't have much options but throw an error.
1595
my_error(ER_TABLE_EXISTS_ERROR, MYF(0), create_table->getTableName());
1555
my_error(ER_TABLE_EXISTS_ERROR, MYF(0), create_table->table_name);
1599
if (not identifier.isTmp())
1559
if (!(lex_identified_temp_table))
1601
/* CREATE TABLE... has found that the table already exists for insert and is adapting to use it */
1602
boost::mutex::scoped_lock scopedLock(table::Cache::singleton().mutex());
1604
if (create_table->table)
1561
pthread_mutex_lock(&LOCK_open); /* CREATE TABLE... has found that the table already exists for insert and is adapting to use it */
1562
if (session->reopen_name_locked_table(create_table, false))
1606
table::Concurrent *concurrent_table= static_cast<table::Concurrent *>(create_table->table);
1608
if (concurrent_table->reopen_name_locked_table(create_table, session))
1610
plugin::StorageEngine::dropTable(*session, identifier);
1614
table= create_table->table;
1564
quick_rm_table(*session, identifier);
1619
plugin::StorageEngine::dropTable(*session, identifier);
1567
table= create_table->table;
1568
pthread_mutex_unlock(&LOCK_open);
1624
if (not (table= session->openTable(create_table, (bool*) 0,
1625
DRIZZLE_OPEN_TEMPORARY_ONLY)) &&
1626
not create_info->table_existed)
1572
if (!(table= session->openTable(create_table, (bool*) 0,
1573
DRIZZLE_OPEN_TEMPORARY_ONLY)) &&
1574
!create_info->table_existed)
1629
1577
This shouldn't happen as creation of temporary table should make
1630
1578
it preparable for open. But let us do close_temporary_table() here
1633
session->drop_temporary_table(identifier);
1581
session->drop_temporary_table(create_table);
1637
if (not table) // open failed
1585
if (!table) // open failed
1641
1589
table->reginfo.lock_type=TL_WRITE;
1642
if (! ((*lock)= session->lockTables(&table, 1, DRIZZLE_LOCK_IGNORE_FLUSH, ¬_used)))
1590
if (! ((*lock)= mysql_lock_tables(session, &table, 1,
1591
DRIZZLE_LOCK_IGNORE_FLUSH, ¬_used)))
1646
session->unlockTables(*lock);
1595
mysql_unlock_tables(session, *lock);
1650
if (not create_info->table_existed)
1651
session->drop_open_table(table, identifier);
1599
if (!create_info->table_existed)
1600
session->drop_open_table(table, create_table->db, create_table->table_name);
1660
1609
select_create::prepare(List<Item> &values, Select_Lex_Unit *u)
1662
DrizzleLock *extra_lock= NULL;
1611
bool lex_identified_temp_table= (table_proto->type() == drizzled::message::Table::TEMPORARY);
1613
DRIZZLE_LOCK *extra_lock= NULL;
1664
For replication, the CREATE-SELECT statement is written
1665
in two pieces: the first transaction messsage contains
1666
the CREATE TABLE statement as a CreateTableStatement message
1667
necessary to create the table.
1669
The second transaction message contains all the InsertStatement
1670
and associated InsertRecords that should go into the table.
1615
For row-based replication, the CREATE-SELECT statement is written
1616
in two pieces: the first one contain the CREATE TABLE statement
1617
necessary to create the table and the second part contain the rows
1618
that should go into the table.
1620
For non-temporary tables, the start of the CREATE-SELECT
1621
implicitly commits the previous transaction, and all events
1622
forming the statement will be stored the transaction cache. At end
1623
of the statement, the entire statement is committed as a
1624
transaction, and all events are written to the binary log.
1626
On the master, the table is locked for the duration of the
1627
statement, but since the CREATE part is replicated as a simple
1628
statement, there is no way to lock the table for accesses on the
1629
slave. Hence, we have to hold on to the CREATE part of the
1630
statement until the statement has finished.
1675
if (not (table= create_table_from_items(session, create_info, create_table,
1677
alter_info, &values,
1679
&extra_lock, identifier)))
1636
Start a statement transaction before the create if we are using
1637
row-based replication for the statement. If we are creating a
1638
temporary table, we need to start a statement transaction.
1641
if (!(table= create_table_from_items(session, create_info, create_table,
1643
alter_info, &values,
1681
1646
return(-1); // abort() deletes table
1684
1648
if (extra_lock)
1686
1650
assert(m_plock == NULL);
1688
if (identifier.isTmp())
1652
if (lex_identified_temp_table)
1689
1653
m_plock= &m_lock;
1691
1655
m_plock= &session->extra_lock;
1693
1657
*m_plock= extra_lock;
1696
if (table->getShare()->sizeFields() < values.elements)
1660
if (table->s->fields < values.elements)
1698
1662
my_error(ER_WRONG_VALUE_COUNT_ON_ROW, MYF(0), 1);
1702
1666
/* First field to copy */
1703
field= table->getFields() + table->getShare()->sizeFields() - values.elements;
1667
field= table->field+table->s->fields - values.elements;
1705
1669
/* Mark all fields that are given values */
1706
1670
for (Field **f= field ; *f ; f++)
1708
table->setWriteSet((*f)->position());
1671
table->setWriteSet((*f)->field_index);
1711
1673
/* Don't set timestamp if used */
1712
1674
table->timestamp_field_type= TIMESTAMP_NO_AUTO_SET;