Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
M
MariaDB
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
nexedi
MariaDB
Commits
e6a9ce27
Commit
e6a9ce27
authored
Mar 30, 2018
by
Sergey Vojtovich
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
MDEV-15773 - Simplified away trx_sys_t::m_views
Use trx_sys_t::trx_list instead.
parent
3d5f7ad2
Changes
5
Hide whitespace changes
Inline
Side-by-side
Showing
5 changed files
with
41 additions
and
120 deletions
+41
-120
storage/innobase/include/read0types.h
storage/innobase/include/read0types.h
+19
-45
storage/innobase/include/trx0sys.h
storage/innobase/include/trx0sys.h
+11
-14
storage/innobase/read/read0read.cc
storage/innobase/read/read0read.cc
+8
-49
storage/innobase/trx/trx0sys.cc
storage/innobase/trx/trx0sys.cc
+0
-2
storage/innobase/trx/trx0trx.cc
storage/innobase/trx/trx0trx.cc
+3
-10
No files found.
storage/innobase/include/read0types.h
View file @
e6a9ce27
...
@@ -33,17 +33,14 @@ Created 2/16/1997 Heikki Tuuri
...
@@ -33,17 +33,14 @@ Created 2/16/1997 Heikki Tuuri
#include "trx0types.h"
#include "trx0types.h"
/** View is not
in MVCC and not
visible to purge thread. */
/** View is not visible to purge thread. */
#define READ_VIEW_STATE_CLOSED 0
#define READ_VIEW_STATE_CLOSED 0
/** View is
in MVCC, but not visible to purge thread
. */
/** View is
being opened, purge thread must wait for state change
. */
#define READ_VIEW_STATE_
REGISTERED
1
#define READ_VIEW_STATE_
SNAPSHOT
1
/** View is in MVCC, purge thread must wait for READ_VIEW_STATE_OPEN. */
/** View is visible to purge thread. */
#define READ_VIEW_STATE_SNAPSHOT 2
#define READ_VIEW_STATE_OPEN 2
/** View is in MVCC and is visible to purge thread. */
#define READ_VIEW_STATE_OPEN 3
/**
/**
...
@@ -56,34 +53,25 @@ class ReadView
...
@@ -56,34 +53,25 @@ class ReadView
View state.
View state.
It is not defined as enum as it has to be updated using atomic operations.
It is not defined as enum as it has to be updated using atomic operations.
Possible values are READ_VIEW_STATE_CLOSED, READ_VIEW_STATE_
REGISTERED,
Possible values are READ_VIEW_STATE_CLOSED, READ_VIEW_STATE_
SNAPSHOT and
READ_VIEW_STATE_
SNAPSHOT and READ_VIEW_STATE_
OPEN.
READ_VIEW_STATE_OPEN.
Possible state transfers...
Possible state transfers...
Opening view for the first time:
Start view open:
READ_VIEW_STATE_CLOSED -> READ_VIEW_STATE_SNAPSHOT (non-atomic)
READ_VIEW_STATE_CLOSED -> READ_VIEW_STATE_SNAPSHOT
Complete first time open or reopen:
READ_VIEW_STATE_SNAPSHOT -> READ_VIEW_STATE_OPEN (atomic)
Close view but keep it in list:
READ_VIEW_STATE_OPEN -> READ_VIEW_STATE_REGISTERED (atomic)
C
lose view and remove it from list
:
C
omplete view open
:
READ_VIEW_STATE_
OPEN -> READ_VIEW_STATE_CLOSED (non-atomic)
READ_VIEW_STATE_
SNAPSHOT -> READ_VIEW_STATE_OPEN
Reusing view:
Close view:
READ_VIEW_STATE_REGISTERED -> READ_VIEW_STATE_SNAPSHOT (atomic)
READ_VIEW_STATE_OPEN -> READ_VIEW_STATE_CLOSED
Removing closed view from list:
READ_VIEW_STATE_REGISTERED -> READ_VIEW_STATE_CLOSED (non-atomic)
*/
*/
int32_t
m_state
;
int32_t
m_state
;
public:
public:
ReadView
()
:
m_state
(
READ_VIEW_STATE_CLOSED
)
{}
ReadView
()
:
m_state
(
READ_VIEW_STATE_CLOSED
)
,
m_low_limit_id
(
0
)
{}
/**
/**
...
@@ -136,7 +124,7 @@ class ReadView
...
@@ -136,7 +124,7 @@ class ReadView
Opens a read view where exactly the transactions serialized before this
Opens a read view where exactly the transactions serialized before this
point in time are seen in the view.
point in time are seen in the view.
View becomes visible to purge thread
via trx_sys.m_views
.
View becomes visible to purge thread.
@param[in,out] trx transaction
@param[in,out] trx transaction
*/
*/
...
@@ -146,23 +134,14 @@ class ReadView
...
@@ -146,23 +134,14 @@ class ReadView
/**
/**
Closes the view.
Closes the view.
View becomes not visible to purge thread
via trx_sys.m_views
.
View becomes not visible to purge thread.
*/
*/
void
close
();
void
close
()
/**
Marks view unused.
View is still in trx_sys.m_views list, but is not visible to purge threads.
*/
void
unuse
()
{
{
ut_ad
(
m_state
==
READ_VIEW_STATE_CLOSED
||
ut_ad
(
m_state
==
READ_VIEW_STATE_CLOSED
||
m_state
==
READ_VIEW_STATE_REGISTERED
||
m_state
==
READ_VIEW_STATE_OPEN
);
m_state
==
READ_VIEW_STATE_OPEN
);
if
(
m_state
==
READ_VIEW_STATE_OPEN
)
if
(
m_state
==
READ_VIEW_STATE_OPEN
)
my_atomic_store32_explicit
(
&
m_state
,
READ_VIEW_STATE_
REGISTER
ED
,
my_atomic_store32_explicit
(
&
m_state
,
READ_VIEW_STATE_
CLOS
ED
,
MY_MEMORY_ORDER_RELAXED
);
MY_MEMORY_ORDER_RELAXED
);
}
}
...
@@ -183,8 +162,7 @@ class ReadView
...
@@ -183,8 +162,7 @@ class ReadView
bool
is_open
()
const
bool
is_open
()
const
{
{
ut_ad
(
m_state
==
READ_VIEW_STATE_OPEN
||
ut_ad
(
m_state
==
READ_VIEW_STATE_OPEN
||
m_state
==
READ_VIEW_STATE_CLOSED
||
m_state
==
READ_VIEW_STATE_CLOSED
);
m_state
==
READ_VIEW_STATE_REGISTERED
);
return
m_state
==
READ_VIEW_STATE_OPEN
;
return
m_state
==
READ_VIEW_STATE_OPEN
;
}
}
...
@@ -302,10 +280,6 @@ class ReadView
...
@@ -302,10 +280,6 @@ class ReadView
whose transaction number is strictly smaller (<) than this value:
whose transaction number is strictly smaller (<) than this value:
they can be removed in purge if not needed by other views */
they can be removed in purge if not needed by other views */
trx_id_t
m_low_limit_no
;
trx_id_t
m_low_limit_no
;
byte
pad1
[
CACHE_LINE_SIZE
];
public:
UT_LIST_NODE_T
(
ReadView
)
m_view_list
;
};
};
#endif
#endif
storage/innobase/include/trx0sys.h
View file @
e6a9ce27
...
@@ -802,9 +802,6 @@ class trx_sys_t
...
@@ -802,9 +802,6 @@ class trx_sys_t
*/
*/
MY_ALIGNED
(
CACHE_LINE_SIZE
)
int32
rseg_history_len
;
MY_ALIGNED
(
CACHE_LINE_SIZE
)
int32
rseg_history_len
;
/** Active views. */
MY_ALIGNED
(
CACHE_LINE_SIZE
)
UT_LIST_BASE_NODE_T
(
ReadView
)
m_views
;
bool
m_initialised
;
bool
m_initialised
;
public:
public:
...
@@ -1051,27 +1048,27 @@ class trx_sys_t
...
@@ -1051,27 +1048,27 @@ class trx_sys_t
/**
/**
Registers
view in MVCC
.
Registers
transaction in trx_sys
.
@param
view view owned by the caller
@param
trx transaction
*/
*/
void
register_
view
(
ReadView
*
view
)
void
register_
trx
(
trx_t
*
trx
)
{
{
mutex_enter
(
&
mutex
);
mutex_enter
(
&
mutex
);
UT_LIST_ADD_FIRST
(
m_views
,
view
);
UT_LIST_ADD_FIRST
(
trx_list
,
trx
);
mutex_exit
(
&
mutex
);
mutex_exit
(
&
mutex
);
}
}
/**
/**
Deregisters
view in MVCC
.
Deregisters
transaction in trx_sys
.
@param
view view owned by the caller
@param
trx transaction
*/
*/
void
deregister_
view
(
ReadView
*
view
)
void
deregister_
trx
(
trx_t
*
trx
)
{
{
mutex_enter
(
&
mutex
);
mutex_enter
(
&
mutex
);
UT_LIST_REMOVE
(
m_views
,
view
);
UT_LIST_REMOVE
(
trx_list
,
trx
);
mutex_exit
(
&
mutex
);
mutex_exit
(
&
mutex
);
}
}
...
@@ -1092,10 +1089,10 @@ class trx_sys_t
...
@@ -1092,10 +1089,10 @@ class trx_sys_t
size_t
count
=
0
;
size_t
count
=
0
;
mutex_enter
(
&
mutex
);
mutex_enter
(
&
mutex
);
for
(
const
ReadView
*
view
=
UT_LIST_GET_FIRST
(
m_views
);
view
;
for
(
const
trx_t
*
trx
=
UT_LIST_GET_FIRST
(
trx_list
);
trx
;
view
=
UT_LIST_GET_NEXT
(
m_view_list
,
view
))
trx
=
UT_LIST_GET_NEXT
(
trx_list
,
trx
))
{
{
if
(
view
->
get_state
()
==
READ_VIEW_STATE_OPEN
)
if
(
trx
->
read_view
.
get_state
()
==
READ_VIEW_STATE_OPEN
)
++
count
;
++
count
;
}
}
mutex_exit
(
&
mutex
);
mutex_exit
(
&
mutex
);
...
...
storage/innobase/read/read0read.cc
View file @
e6a9ce27
...
@@ -193,7 +193,7 @@ inline void ReadView::snapshot(trx_t *trx)
...
@@ -193,7 +193,7 @@ inline void ReadView::snapshot(trx_t *trx)
Opens a read view where exactly the transactions serialized before this
Opens a read view where exactly the transactions serialized before this
point in time are seen in the view.
point in time are seen in the view.
View becomes visible to purge thread
via trx_sys.m_views
.
View becomes visible to purge thread.
@param[in,out] trx transaction
@param[in,out] trx transaction
*/
*/
...
@@ -205,8 +205,9 @@ void ReadView::open(trx_t *trx)
...
@@ -205,8 +205,9 @@ void ReadView::open(trx_t *trx)
case
READ_VIEW_STATE_OPEN
:
case
READ_VIEW_STATE_OPEN
:
ut_ad
(
!
srv_read_only_mode
);
ut_ad
(
!
srv_read_only_mode
);
return
;
return
;
case
READ_VIEW_STATE_REGISTERED
:
case
READ_VIEW_STATE_CLOSED
:
ut_ad
(
!
srv_read_only_mode
);
if
(
srv_read_only_mode
)
return
;
/*
/*
Reuse closed view if there were no read-write transactions since (and at)
Reuse closed view if there were no read-write transactions since (and at)
its creation time.
its creation time.
...
@@ -224,18 +225,6 @@ void ReadView::open(trx_t *trx)
...
@@ -224,18 +225,6 @@ void ReadView::open(trx_t *trx)
What bad things can happen because we allow this race?
What bad things can happen because we allow this race?
First, purge thread may be affected by this race condition only if this
view is the oldest open view. In other words this view is either last in
m_views list or there're no open views beyond.
In this case purge may not catch this view and clone some younger view
instead. It might be kind of alright, because there were no read-write
transactions and there should be nothing to purge. Besides younger view
must have exactly the same values.
Second, scary things start when there's a read-write transaction starting
concurrently.
Speculative execution may reorder state change before get_max_trx_id().
Speculative execution may reorder state change before get_max_trx_id().
In this case purge thread has short gap to clone outdated view. Which is
In this case purge thread has short gap to clone outdated view. Which is
probably not that bad: it just won't be able to purge things that it was
probably not that bad: it just won't be able to purge things that it was
...
@@ -268,12 +257,6 @@ void ReadView::open(trx_t *trx)
...
@@ -268,12 +257,6 @@ void ReadView::open(trx_t *trx)
my_atomic_store32_explicit
(
&
m_state
,
READ_VIEW_STATE_SNAPSHOT
,
my_atomic_store32_explicit
(
&
m_state
,
READ_VIEW_STATE_SNAPSHOT
,
MY_MEMORY_ORDER_RELAXED
);
MY_MEMORY_ORDER_RELAXED
);
break
;
break
;
case
READ_VIEW_STATE_CLOSED
:
if
(
srv_read_only_mode
)
return
;
m_state
=
READ_VIEW_STATE_SNAPSHOT
;
trx_sys
.
register_view
(
this
);
break
;
default:
default:
ut_ad
(
0
);
ut_ad
(
0
);
}
}
...
@@ -286,52 +269,28 @@ void ReadView::open(trx_t *trx)
...
@@ -286,52 +269,28 @@ void ReadView::open(trx_t *trx)
}
}
/**
Closes the view.
The view will become invisible to purge (deregistered from trx_sys).
*/
void
ReadView
::
close
()
{
ut_ad
(
m_state
==
READ_VIEW_STATE_OPEN
||
m_state
==
READ_VIEW_STATE_REGISTERED
||
m_state
==
READ_VIEW_STATE_CLOSED
);
if
(
m_state
!=
READ_VIEW_STATE_CLOSED
)
{
trx_sys
.
deregister_view
(
this
);
m_state
=
READ_VIEW_STATE_CLOSED
;
}
}
/**
/**
Clones the oldest view and stores it in view.
Clones the oldest view and stores it in view.
No need to call ReadView::close(). The caller owns the view that is passed
No need to call ReadView::close(). The caller owns the view that is passed
in. This function is called by purge thread to determine whether it should
in. This function is called by purge thread to determine whether it should
purge the delete marked record or not.
purge the delete marked record or not.
Since foreign views are accessed under the mutex protection, the only
possible state transfers are
READ_VIEW_STATE_SNAPSHOT -> READ_VIEW_STATE_OPEN
READ_VIEW_STATE_OPEN -> READ_VIEW_STATE_REGISTERED
All other state transfers are eliminated by the mutex.
*/
*/
void
trx_sys_t
::
clone_oldest_view
()
void
trx_sys_t
::
clone_oldest_view
()
{
{
purge_sys
.
view
.
snapshot
(
0
);
purge_sys
.
view
.
snapshot
(
0
);
mutex_enter
(
&
mutex
);
mutex_enter
(
&
mutex
);
/* Find oldest view. */
/* Find oldest view. */
for
(
const
ReadView
*
v
=
UT_LIST_GET_FIRST
(
m_views
);
v
;
for
(
const
trx_t
*
trx
=
UT_LIST_GET_FIRST
(
trx_list
);
trx
;
v
=
UT_LIST_GET_NEXT
(
m_view_list
,
v
))
trx
=
UT_LIST_GET_NEXT
(
trx_list
,
trx
))
{
{
int32_t
state
;
int32_t
state
;
while
((
state
=
v
->
get_state
())
==
READ_VIEW_STATE_SNAPSHOT
)
while
((
state
=
trx
->
read_view
.
get_state
())
==
READ_VIEW_STATE_SNAPSHOT
)
ut_delay
(
1
);
ut_delay
(
1
);
if
(
state
==
READ_VIEW_STATE_OPEN
)
if
(
state
==
READ_VIEW_STATE_OPEN
)
purge_sys
.
view
.
copy
(
*
v
);
purge_sys
.
view
.
copy
(
trx
->
read_view
);
}
}
mutex_exit
(
&
mutex
);
mutex_exit
(
&
mutex
);
}
}
storage/innobase/trx/trx0sys.cc
View file @
e6a9ce27
...
@@ -218,7 +218,6 @@ trx_sys_t::create()
...
@@ -218,7 +218,6 @@ trx_sys_t::create()
m_initialised
=
true
;
m_initialised
=
true
;
mutex_create
(
LATCH_ID_TRX_SYS
,
&
mutex
);
mutex_create
(
LATCH_ID_TRX_SYS
,
&
mutex
);
UT_LIST_INIT
(
trx_list
,
&
trx_t
::
trx_list
);
UT_LIST_INIT
(
trx_list
,
&
trx_t
::
trx_list
);
UT_LIST_INIT
(
m_views
,
&
ReadView
::
m_view_list
);
my_atomic_store32
(
&
rseg_history_len
,
0
);
my_atomic_store32
(
&
rseg_history_len
,
0
);
rw_trx_hash
.
init
();
rw_trx_hash
.
init
();
...
@@ -346,7 +345,6 @@ trx_sys_t::close()
...
@@ -346,7 +345,6 @@ trx_sys_t::close()
}
}
ut_a
(
UT_LIST_GET_LEN
(
trx_list
)
==
0
);
ut_a
(
UT_LIST_GET_LEN
(
trx_list
)
==
0
);
ut_ad
(
UT_LIST_GET_LEN
(
m_views
)
==
0
);
mutex_free
(
&
mutex
);
mutex_free
(
&
mutex
);
m_initialised
=
false
;
m_initialised
=
false
;
}
}
...
...
storage/innobase/trx/trx0trx.cc
View file @
e6a9ce27
...
@@ -423,9 +423,7 @@ trx_t *trx_create()
...
@@ -423,9 +423,7 @@ trx_t *trx_create()
trx
->
wsrep_event
=
NULL
;
trx
->
wsrep_event
=
NULL
;
#endif
/* WITH_WSREP */
#endif
/* WITH_WSREP */
mutex_enter
(
&
trx_sys
.
mutex
);
trx_sys
.
register_trx
(
trx
);
UT_LIST_ADD_FIRST
(
trx_sys
.
trx_list
,
trx
);
mutex_exit
(
&
trx_sys
.
mutex
);
return
(
trx
);
return
(
trx
);
}
}
...
@@ -472,9 +470,7 @@ void trx_free(trx_t*& trx)
...
@@ -472,9 +470,7 @@ void trx_free(trx_t*& trx)
trx
->
dict_operation
=
TRX_DICT_OP_NONE
;
trx
->
dict_operation
=
TRX_DICT_OP_NONE
;
assert_trx_is_inactive
(
trx
);
assert_trx_is_inactive
(
trx
);
mutex_enter
(
&
trx_sys
.
mutex
);
trx_sys
.
deregister_trx
(
trx
);
UT_LIST_REMOVE
(
trx_sys
.
trx_list
,
trx
);
mutex_exit
(
&
trx_sys
.
mutex
);
assert_trx_is_free
(
trx
);
assert_trx_is_free
(
trx
);
...
@@ -492,9 +488,6 @@ void trx_free(trx_t*& trx)
...
@@ -492,9 +488,6 @@ void trx_free(trx_t*& trx)
trx
->
mod_tables
.
clear
();
trx
->
mod_tables
.
clear
();
ut_ad
(
!
trx
->
read_view
.
is_open
());
trx
->
read_view
.
close
();
/* trx locking state should have been reset before returning trx
/* trx locking state should have been reset before returning trx
to pool */
to pool */
ut_ad
(
trx
->
will_lock
==
0
);
ut_ad
(
trx
->
will_lock
==
0
);
...
@@ -1308,7 +1301,7 @@ trx_commit_in_memory(
...
@@ -1308,7 +1301,7 @@ trx_commit_in_memory(
the transaction did not modify anything */
the transaction did not modify anything */
{
{
trx
->
must_flush_log_later
=
false
;
trx
->
must_flush_log_later
=
false
;
trx
->
read_view
.
unu
se
();
trx
->
read_view
.
clo
se
();
if
(
trx_is_autocommit_non_locking
(
trx
))
{
if
(
trx_is_autocommit_non_locking
(
trx
))
{
ut_ad
(
trx
->
id
==
0
);
ut_ad
(
trx
->
id
==
0
);
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment