Commit graph

1970 commits

Author SHA1 Message Date
Marko Mäkelä
921c5e9314 Merge bb-10.2-ext into 10.3
MDEV-11415 Remove excessive undo logging during ALTER TABLE…ALGORITHM=COPY

Move a test from innodb.rename_table_debug to innodb.alter_copy.

ha_innobase::extra(HA_EXTRA_BEGIN_ALTER_COPY): Register id-versioned
tables so that mysql.transaction_registry will be updated, even for
empty tables that are subjected to ALTER TABLE…ALGORITHM=COPY.
2018-01-30 21:26:53 +02:00
Marko Mäkelä
33714d2065 Merge bb-10.2-ext into 10.3 2018-01-30 21:04:48 +02:00
Marko Mäkelä
0c1f220611 Merge 10.2 into bb-10.2-ext 2018-01-30 20:47:12 +02:00
Marko Mäkelä
0ba6aaf030 MDEV-11415 Remove excessive undo logging during ALTER TABLE…ALGORITHM=COPY
If a crash occurs during ALTER TABLE…ALGORITHM=COPY, InnoDB would spend
a lot of time rolling back writes to the intermediate copy of the table.
To reduce the amount of busy work done, a work-around was introduced in
commit fd069e2bb3 in MySQL 4.1.8 and 5.0.2,
to commit the transaction after every 10,000 inserted rows.

A proper fix would have been to disable the undo logging altogether and
to simply drop the intermediate copy of the table on subsequent server
startup. This is what happens in MariaDB 10.3 with MDEV-14717,MDEV-14585.
In MariaDB 10.2, the intermediate copy of the table would be left behind
with a name starting with the string #sql.

This is a backport of a bug fix from MySQL 8.0.0 to MariaDB,
contributed by jixianliang <271365745@qq.com>.

Unlike recent MySQL, MariaDB supports ALTER IGNORE. For that operation
InnoDB must for now keep the undo logging enabled, so that the latest
row can be rolled back in case of an error.

In Galera cluster, the LOAD DATA statement will retain the existing
behaviour and commit the transaction after every 10,000 rows if
the parameter wsrep_load_data_splitting=ON is set. The logic to do
so (the wsrep_load_data_split() function and the call
handler::extra(HA_EXTRA_FAKE_START_STMT)) are joint work
by Ji Xianliang and Marko Mäkelä.

The original fix:

Author: Thirunarayanan Balathandayuthapani <thirunarayanan.balathandayuth@oracle.com>
Date:   Wed Dec 2 16:09:15 2015 +0530

Bug#17479594 AVOID INTERMEDIATE COMMIT WHILE DOING ALTER TABLE ALGORITHM=COPY

Problem:

During ALTER TABLE, we commit and restart the transaction for every
10,000 rows, so that the rollback after recovery would not take so long.

Fix:

Suppress the undo logging during copy alter operation. If fts_index is
present then insert directly into fts auxiliary table rather
than doing at commit time.

ha_innobase::num_write_row: Remove the variable.

ha_innobase::write_row(): Remove the hack for committing every 10000 rows.

row_lock_table_for_mysql(): Remove the extra 2 parameters.

lock_get_src_table(), lock_is_table_exclusive(): Remove.

Reviewed-by: Marko Mäkelä <marko.makela@oracle.com>
Reviewed-by: Shaohua Wang <shaohua.wang@oracle.com>
Reviewed-by: Jon Olav Hauglid <jon.hauglid@oracle.com>
2018-01-30 20:24:23 +02:00
Marko Mäkelä
6d390bab4a Merge 10.2 into bb-10.2-ext 2018-01-30 20:18:25 +02:00
Vladislav Vaintroub
28d412411d Fix type truncation warnings.
rx_i_s_cache_t is now bool, not ibool.
2018-01-29 18:31:26 +00:00
Marko Mäkelä
8b673d44ce Fix an integer type mismatch 2018-01-29 19:08:04 +02:00
Marko Mäkelä
d9c77f0341 Revert "MDEV-6928: Add trx pointer to struct mtr_t"
This reverts commit 3486135bb5.

The commit comment ended in the words: "This is needed later."
Apparently the "later" never arrived.
2018-01-29 15:45:16 +02:00
Marko Mäkelä
f74023b955 MDEV-15090 Reduce the overhead of writing undo log records
Remove unnecessary repeated lookups for undo pages.

trx_undo_assign(), trx_undo_assign_low(), trx_undo_seg_create(),
trx_undo_create(): Return the undo log block to the caller.
2018-01-29 15:15:10 +02:00
Marko Mäkelä
5d3c3b4927 MDEV-15090 Reduce the overhead of writing undo log records
Inside InnoDB, each mini-transaction that generates any redo log records
will acquire log_sys->mutex during mtr_t::commit() in order to copy the
records into the global log_sys->buf for writing into the redo log file.

For single-row transactions, this incurs quite a bit of overhead.
We would use two mini-transactions for writing a record into a
freshly updated undo log page. (Only if the undo record will
not fit in that page, then we will have to commit and restart
the mini-transaction.)

trx_undo_assign(): Assign undo log for a persistent transaction,
or return the already assigned one.

trx_undo_assign_low(): Assign undo log for an operation on a
persistent or temporary table.

trx_undo_create(), trx_undo_reuse_cached(): Remove redundant parameters.
Merge the logic from trx_undo_mark_as_dict_operation().
2018-01-29 15:15:10 +02:00
Marko Mäkelä
041a32abcd Remove trx_mod_tables_t::vers_by_trx
Only invoke set_versioned() on trx_id versioned tables.

dict_table_t::versioned_by_id(): New accessor, to determine if
a table is system versioned by transaction ID.
2018-01-28 22:21:48 +02:00
Marko Mäkelä
1da063a45b Remove unused metadata for non-existing sync_thread_mutex 2018-01-28 22:17:54 +02:00
Sergey Vojtovich
55277e8840 MDEV-15059 - Misc small InnoDB scalability fixes
Form better trx_sys API.
2018-01-26 10:25:33 +04:00
Sergey Vojtovich
064bd78038 MDEV-15059 - Misc small InnoDB scalability fixes
When cloning oldest view, don't copy ReadView::m_creator_trx_id.
It means that the owner thread is now allowed to access this member
without trx_sys.mutex protection.

To achieve this we have to keep ReadView::m_creator_trx_id in
ReadView::m_ids. This is required to not let purge thread process
records owned by transaction associated with oldest view.

It is only required if trsanction entered read-write mode before it's
view was created.

If transaction entered read-write mode after it's view was created
(trx_set_rw_mode()), purge thread won't be allowed to touch it because
m_low_limit_id >= m_creator_trx_id holds. Thus we don't have to add
this transaction id to ReadView::m_ids.

Cleanups:

ReadView::ids_t: don't seem to make any sense, just complicate matters.

ReadView::copy_trx_ids(): doesn't make sense anymore, integrated into
caller.

ReadView::copy_complete(): not needed anymore.

ReadView copy constructores: don't seem to make any sense.

trx_purge_truncate_history(): removed view argument, access
purge_sys->view directly instead.
2018-01-26 10:25:33 +04:00
Sergey Vojtovich
8389b45b7f MDEV-15059 - Misc small InnoDB scalability fixes
Moved mutex locking inside lock_rec_lock().
Moved monitor increment out of mutex.
Moved assertions that don't require protection out of mutex.
Removed duplicate assertions.
Moved duplicate debug injections into lock_rec_lock().
Let monitor updates use relaxed memory order.
Return directly without maintaining variables in lock_rec_lock_slow().
Moved lock_rec_lock_fast() body into lock_rec_lock(): saves at least one
trx_mutex_enter(), one switch() plus some code was moved out of mutex.
2018-01-26 10:25:33 +04:00
Sergey Vojtovich
ce04790065 MDEV-14482 - Cache line contention on ut_rnd_ulint_counter()
InnoDB RNG maintains global state, causing otherwise unnecessary bus
traffic. Even worse this is cross-mutex traffic. That is different
mutexes suffer from contention.

Fixed delay of 4 was verified to give best throughput by OLTP update
index and read-write benchmarks on Intel Broadwell (2/20/40) and
ARM (1/46/46).
2018-01-26 10:25:33 +04:00
Marko Mäkelä
92d233a512 MDEV-15061 TRUNCATE must honor InnoDB table locks
Traditionally, DROP TABLE and TRUNCATE TABLE discarded any locks that
may have been held on the table. This feels like an ACID violation.
Probably most occurrences of it were prevented by meta-data locks (MDL)
which were introduced in MySQL 5.5.

dict_table_t::n_foreign_key_checks_running: Reduce the number of
non-debug checks.

lock_remove_all_on_table(), lock_remove_all_on_table_for_trx(): Remove.

ha_innobase::truncate(): Acquire an exclusive InnoDB table lock
before proceeding. DROP TABLE and DISCARD/IMPORT were already doing
this.

row_truncate_table_for_mysql(): Convert the already started transaction
into a dictionary operation, and do not invoke lock_remove_all_on_table().

row_mysql_table_id_reassign(): Do not call lock_remove_all_on_table().
This function is only used in ALTER TABLE...DISCARD/IMPORT TABLESPACE,
which is already holding an exclusive InnoDB table lock.

TODO: Make n_foreign_key_checks running a debug-only variable.
This would require two fixes:
(1) DROP TABLE: Exclusively lock the table beforehand, to prevent
the possibility of concurrently running foreign key checks (which
would acquire a table IS lock and then record S locks).
(2) RENAME TABLE: Find out if n_foreign_key_checks_running>0 actually
constitutes a potential problem.
2018-01-25 22:43:43 +02:00
Marko Mäkelä
9aa461b187 Minor cleanup
ReadView::ReadView(): Define inline, and remove the memset().

ReadView::~ReadView(): Use the default destructor.
2018-01-24 14:01:45 +02:00
Marko Mäkelä
9875d5c3e1 Merge bb-10.2-ext into 10.3 2018-01-24 14:00:33 +02:00
Howard Su
6fe953cb71 Fix build on OSX with 10.13 SDK 2018-01-24 11:28:00 +02:00
Alexander Barkov
ec6b8c546a Merge remote-tracking branch 'origin/10.2' into bb-10.2-ext 2018-01-23 17:43:12 +04:00
Marko Mäkelä
89ae5d7f2f Allocate mutex_monitor, create_tracker statically 2018-01-22 16:30:38 +02:00
Marko Mäkelä
30f1d2f642 Remove useless method LatchCounter::sum_deregister() 2018-01-22 16:29:43 +02:00
Sergey Vojtovich
8e1adff959 Simplified away ReadView::complete()
It was supposed to be called out of mutex, but nevertheless was called
under trx_sys.mutex for normal threads adding one extra condtion in
critical section.
2018-01-22 16:23:16 +04:00
Sergey Vojtovich
4dc30f3c17 MDEV-15019 - InnoDB: store ReadView on trx
This will allow us to reduce critical section protected by
trx_sys.mutex:
- no need to maintain global m_free list
- eliminate if (trx->read_view == NULL) condition.

On x86_64 sizeof(Readview) is 144 mostly due to padding, sizeof(trx_t)
with ReadView is 1200.

Also don't close ReadView for read-write transactions, just mark it
closed similarly to read-only.

Clean-up: removed n_prepared_recovered_trx and n_prepared_trx, which
accidentally re-appeared after some rebase.
2018-01-22 16:23:15 +04:00
Marko Mäkelä
c425dcd8f2 Merge 10.2 into bb-10.2-ext 2018-01-22 09:04:32 +02:00
Marko Mäkelä
4f8555f1f6 MDEV-14941 Timeouts on persistent statistics tables caused by MDEV-14511
MDEV-14511 tried to avoid some consistency problems related to InnoDB
persistent statistics. The persistent statistics are being written by
an InnoDB internal SQL interpreter that requires the InnoDB data dictionary
cache to be locked.

Before MDEV-14511, the statistics were written during DDL in separate
transactions, which could unnecessarily reduce performance (each commit
would require a redo log flush) and break atomicity, because the statistics
would be updated separately from the dictionary transaction.

However, because it is unacceptable to hold the InnoDB data dictionary
cache locked while suspending the execution for waiting for a
transactional lock (in the mysql.innodb_index_stats or
mysql.innodb_table_stats tables) to be released, any lock conflict
was immediately be reported as "lock wait timeout".

To fix MDEV-14941, an attempt to reduce these lock conflicts by acquiring
transactional locks on the user tables in both the statistics and DDL
operations was made, but it would still not entirely prevent lock conflicts
on the mysql.innodb_index_stats and mysql.innodb_table_stats tables.

Fixing the remaining problems would require a change that is too intrusive
for a GA release series, such as MariaDB 10.2.

Thefefore, we revert the change MDEV-14511. To silence the
MDEV-13201 assertion, we use the pre-existing flag trx_t::internal.
2018-01-22 08:58:47 +02:00
Sergey Vojtovich
ec32c05072 Get rid of trx->read_view pointer juggling
trx->read_view|= 1 was done in a silly attempt to fix race condition
where trx->read_view was closed without trx_sys.mutex lock by read-only
trasnactions.

This just made the problem less likely to happen. In fact there was race
condition in const version of trx_get_read_view(): pointer may change to
garbage any moment after MVCC::is_view_active(trx->read_view) check and
before this function returns.

This patch doesn't fix this race condition, but rather makes it's
consequences less destructive.
2018-01-20 16:10:38 +04:00
Sergey Vojtovich
95070bf939 MVCC simplifications
Simplified away MVCC::get_oldest_view()
Simplified away MVCC::get_view()
Removed unused MVCC::view_release()
2018-01-20 16:10:38 +04:00
Sergey Vojtovich
90bf55673e Misc trx_sys scalability fixes
trx_erase_lists(): trx->read_view is owned by current thread and thus
doesn't need trx_sys.mutex protection for reading it's value. Move
trx->read_view check out of mutex

trx_start_low(): moved assertion out of mutex.

Call ReadView::creator_trx_id() directly: allows to inline this one-line
method.
2018-01-20 16:10:37 +04:00
Sergey Vojtovich
64048bafe0 Removed purge_trx_id_age and purge_view_trx_id_age
These were unused status variables available in debug builds only.
Also removed trx_sys.rw_max_trx_id: not used anymore.
2018-01-20 16:10:37 +04:00
Sergey Vojtovich
db5bb785f9 Allocate trx_sys.mvcc at link time
trx_sys.mvcc was allocated dynamically for no good reason.
2018-01-20 16:10:36 +04:00
Marko Mäkelä
f8882cce93 Replace trx_sys_t* trx_sys with trx_sys_t trx_sys
There is only one transaction system object in InnoDB.
Allocate the storage for it at link time, not at runtime.

lock_rec_fetch_page(): Use the correct fetch mode BUF_GET.
Pages may never be deallocated from a tablespace while
record locks are pointing to them.
2018-01-20 16:10:36 +04:00
Sergey Vojtovich
7078203389 MDEV-14756 - Remove trx_sys_t::rw_trx_list
Use atomic operations when accessing trx_sys_t::max_trx_id. We can't yet
move trx_sys_t::get_new_trx_id() out of mutex because it must be updated
atomically along with trx_sys_t::rw_trx_ids.
2018-01-20 16:10:35 +04:00
Sergey Vojtovich
c6d2842d9a MDEV-14756 - Remove trx_sys_t::rw_trx_list
Remove rw_trx_list.
2018-01-20 16:10:35 +04:00
Sergey Vojtovich
a447980ff3 MDEV-14756 - Remove trx_sys_t::rw_trx_list
Let lock_print_info_all_transactions() iterate rw_trx_hash instead of
rw_trx_list.

When printing info of locks for transactions, InnoDB monitor doesn't
attempt to read relevant page from disk anymore. The code was prone
to race conditions.

Note that TrxListIterator didn't work as advertised: it iterated
rw_trx_list only.
2018-01-20 16:10:34 +04:00
Sergey Vojtovich
886af392d3 MDEV-14756 - Remove trx_sys_t::rw_trx_list
Let trx_rollback_recovered() iterate rw_trx_hash instead of rw_trx_list.
2018-01-20 16:09:26 +04:00
Sergey Vojtovich
02270b44d0 MDEV-14756 - Remove trx_sys_t::rw_trx_list
Let lock_validate_table_locks(), lock_rec_other_trx_holds_expl(),
lock_table_locks_lookup(), trx_recover_for_mysql(), trx_get_trx_by_xid(),
trx_roll_must_shutdown(), fetch_data_into_cache() iterate rw_trx_hash
instead of rw_trx_list.
2018-01-20 16:09:26 +04:00
Sergey Vojtovich
d8c0caad32 MDEV-14756 - Remove trx_sys_t::rw_trx_list
Removed trx_sys_validate_trx_list(): with rw_trx_hash elements are not
required to be ordered by transaction id. Transaction state is now guarded
by asserts in rw_trx_hash_t.
2018-01-20 16:09:26 +04:00
Sergey Vojtovich
900b07908b MDEV-14756 - Remove trx_sys_t::rw_trx_list
Removed trx_sys_t::n_prepared_recovered_trx: never used.

Removed trx_sys_t::n_prepared_trx: used only at shutdown, we can perfectly
get this value from rw_trx_hash.
2018-01-20 16:09:26 +04:00
Sergey Vojtovich
a0b385ea2b MDEV-14756 - Remove trx_sys_t::rw_trx_list
Determine minimum transaction id by iterating rw_trx_hash, not rw_trx_list.

It is more expensive than previous implementation since it does linear
search, especially if there're many concurrent transactions running. But in
such case mutex is much bigger evil. And since it doesn't require
trx_sys->mutex protection it scales better.

For low concurrency performance difference is neglible.
2018-01-20 16:09:26 +04:00
Sergey Vojtovich
868c77df3e MDEV-14756 - Remove trx_sys_t::rw_trx_list
Replaced UT_LIST_GET_LEN(trx_sys->rw_trx_list) with
trx_sys->rw_trx_hash.size().
Moved freeing of trx objects at shutdown to rw_trx_hash destructor.
Small clean-up in trx_rollback_recovered().
2018-01-20 16:09:26 +04:00
Sergey Vojtovich
d09f146934 MDEV-14756 - Remove trx_sys_t::rw_trx_list
Reduce divergence between trx_sys_t::rw_trx_hash and trx_sys_t::rw_trx_list
by not adding recovered COMMITTED transactions to trx_sys_t::rw_trx_list.

Such transactions are discarded immediately without creating trx object.

This also required to split rollback and cleanup phases of recovery. To
reflect these updates the following renames happened:
trx_rollback_or_clean_all_recovered() -> trx_rollback_all_recovered()
trx_rollback_or_clean_is_active -> trx_rollback_is_active
trx_rollback_or_clean_recovered() -> trx_rollback_recovered()
trx_cleanup_at_db_startup() -> trx_cleanup_recovered()

Also removed a hack from lock_trx_release_locks(). Instead let recovery
rollback thread to skip committed XA transactions.
2018-01-20 16:09:26 +04:00
Sergei Golubchik
8f102b584d Merge branch 'github/10.3' into bb-10.3-temporal 2018-01-17 00:45:02 +01:00
Sergei Golubchik
edb6375910 compilation warning on windows 2018-01-17 00:44:11 +01:00
Marko Mäkelä
d87531a6a0 Follow-up to MDEV-14952: Remove some more btr_get_search_latch()
Replace some !rw_lock_own() assertions with the stronger
!btr_search_own_any(). Remove some redundant btr_get_search_latch()
calls.

btr_search_update_hash_ref(): Remove a duplicated assertion.

btr_search_build_page_hash_index(): Remove a duplicated assertion.
rw_lock_s_lock() asserts that the latch is not being held.

btr_search_disable_ref_count(): Remove an assertion. The only caller
is acquiring all adaptive hash index latches.
2018-01-16 14:08:48 +02:00
Marko Mäkelä
0664d633e4 MDEV-14952 Avoid repeated calls to btr_get_search_latch()
btr_cur_search_to_nth_level(), btr_search_guess_on_hash(),
btr_pcur_open_with_no_init_func(), row_sel_open_pcur():
Replace the parameter has_search_latch with the ahi_latch
(passed as NULL if the caller does not hold the latch).

btr_search_update_hash_node_on_insert(),
btr_search_update_hash_on_insert(),
btr_search_build_page_hash_index(): Add the parameter ahi_latch.

btr_search_x_lock(), btr_search_x_unlock(),
btr_search_s_lock(), btr_search_s_unlock(): Remove.
2018-01-15 19:51:09 +02:00
Marko Mäkelä
4ef25dbfd8 Merge bb-10.2-ext into 10.3 2018-01-15 19:11:28 +02:00
Marko Mäkelä
39f236a2f5 Merge 10.2 into bb-10.2-ext 2018-01-15 16:41:10 +02:00
Marko Mäkelä
ec062c6181 MDEV-12121 follow-up: Unbreak the WITH_INNODB_AHI=OFF build 2018-01-15 15:40:28 +02:00