MySQL 8.3.0
Source Code Documentation
recovery.h
Go to the documentation of this file.
1/* Copyright (c) 2022, 2023, Oracle and/or its affiliates.
2
3 This program is free software; you can redistribute it and/or modify
4 it under the terms of the GNU General Public License, version 2.0,
5 as published by the Free Software Foundation.
6
7 This program is also distributed with certain software (including
8 but not limited to OpenSSL) that is licensed under separate terms,
9 as designated in a particular file or component or in included license
10 documentation. The authors of MySQL hereby grant you an additional
11 permission to link the program and your derivative works with the
12 separately licensed software that they have included with MySQL.
13
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License, version 2.0, for more details.
18
19 You should have received a copy of the GNU General Public License
20 along with this program; if not, write to the Free Software
21 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */
22
23#ifndef BINLOG_RECOVERY_H_INCLUDED
24#define BINLOG_RECOVERY_H_INCLUDED
25
26#include "sql/binlog/global.h"
27#include "sql/binlog_ostream.h" // binlog::tools::Iterator
28#include "sql/binlog_reader.h" // Binlog_file_reader
29#include "sql/log_event.h" // Log_event
30#include "sql/xa.h" // XID
31
32namespace binlog {
33/**
34 Recovers from last crashed binlog at server start.
35
36 After a crash, storage engines may contain transactions that are prepared
37 but not committed (in theory any engine, in practice InnoDB). This
38 classe's methods use the binary log as the source of truth to determine
39 which of these transactions should be committed and which should be
40 rolled back.
41
42 The `Binlog::recovery()` method collects the following from the last
43 available binary log:
44 - the list of internally coordinated transactions (normal) that are
45 completely written to the binary log.
46 - the list of externally coordinated transactions (XA) that appear in the
47 binary log, along the state those transactions are in.
48
49 The list of XIDs of all internally coordinated transactions that are
50 completely written to the binary log is passed to the storage engines
51 through the ha_recover function in the handler interface. This tells the
52 storage engines to commit all prepared transactions that are in the set,
53 and to roll back all prepared transactions that are not in the set.
54
55 The list of XIDs of all externally coordinated transactions that appear
56 in the binary log, along with the state they are in, is passed to the
57 storage engines through the ha_recover function in the handler
58 interface. The storage engine will determine if the transaction is to be
59 kept at PREPARE, is to be COMMITTED or ROLLED BACK, in accordance with:
60 the state that is provided in the list; the internal storage engine state
61 for the transaction.
62*/
64 public:
65 /**
66 Class constructor.
67
68 @param binlog_file_reader The already instantiated and initialized file
69 reader for the last available binary log
70 file.
71 */
72 Binlog_recovery(Binlog_file_reader &binlog_file_reader);
73 virtual ~Binlog_recovery() = default;
74
75 /**
76 Retrieves the position of the last binlog event that ended a
77 transaction.
78
79 @return The position of the last binlog event that ended a
80 transaction.
81 */
82 my_off_t get_valid_pos() const;
83 /**
84 Retrieves whether or not the recovery process ended successfully.
85
86 @see Binlog_recovery::is_binlog_malformed()
87 @see Binlog_recovery::has_engine_recovery_failed()
88
89 @return true if the recovery process ended with errors, false
90 otherwise.
91 */
92 bool has_failures() const;
93 /**
94 Retrieves whether or not the binary log was correctly processed in
95 full.
96
97 @return true if the binary log processing ended with errors, false
98 otherwise.
99 */
100 bool is_binlog_malformed() const;
101 /**
102 Retrieves whether or not the storage engines XA recovery process
103 completed successfully.
104
105 @return false if the storge engines completed the XA recovery process
106 successfully, true otherwise.
107 */
108 bool has_engine_recovery_failed() const;
109 /**
110 Retrieves the textual representation of the encontered failure, if any.
111
112 @return the string containing the textual representation of the failure,
113 an empty string otherwise.
114 */
115 std::string const &get_failure_message() const;
116 /**
117 Uses the provided binary log file reader to inspect the binary log and
118 extract transaction information.
119
120 The following is collected from the provided binlog file reader:
121 - the list of internally coordinated transactions (normal) that are
122 completely written to the binary log.
123 - the list of externally coordinated transactions (XA) that appear in
124 the binary log, along the state those transactions are in.
125
126 The list of XIDs of all internally coordinated transactions that are
127 completely written to the binary log is passed to the storage engines
128 through the ha_recover function in the handler interface. This tells the
129 storage engines to commit all prepared transactions that are in the set,
130 and to roll back all prepared transactions that are not in the set.
131
132 The list of XIDs of all externally coordinated transactions that appear
133 in the binary log, along with the state they are in, is passed to the
134 storage engines through the ha_recover function in the handler
135 interface. The storage engine will determine if the transaction is to be
136 kept at PREPARE, is to be COMMITTED or ROLLED BACK, in accordance with:
137 the state that is provided in the list; the internal storage engine state
138 for the transaction.
139
140 After `recover()` returns, `has_failures()` should be invoked to
141 determine if the recover process ended successfully. Additionally,
142 `is_binlog_malformed()` and `has_engine_recovery_failed()` can be
143 invoked to determine the type of error that occurred.
144
145 @return This instance's reference, for chaining purposes.
146 */
148
149 private:
150 /** File reader for the last available binary log file */
152 /** Position of the last binlog event that ended a transaction */
154 /** Whether or not the event being processed is within a transaction */
155 bool m_in_transaction{false};
156 /** Whether or not the binary log is malformed/corrupted */
157 bool m_is_malformed{false};
158 /** Whether or not the recovery in the storage engines failed */
160 /** Textual representation of the encountered failure */
161 std::string m_failure_message{""};
162 /** Memory pool to use for the XID lists */
164 /** Memory pool allocator to use with the normal transaction list */
166 /** Memory pool allocator to use with the XA transaction list */
168 /** List of normal transactions fully written to the binary log */
170 /** List of XA transactions and states that appear in the binary log */
172
173 /**
174 Invoked when a `Query_log_event` is read from the binary log file
175 reader. The underlying query string is inspected to determine if the
176 SQL command starts or ends a transaction. The following commands are
177 searched for:
178 - BEGIN
179 - COMMIT
180 - ROLLBACK
181 - DDL
182 - XA START
183 - XA COMMIT
184 - XA ROLLBACK
185
186 Check below for the description of the action that is taken for each.
187
188 @param ev The `Query_log_event` to process
189 */
190 void process_query_event(Query_log_event const &ev);
191 /**
192 Invoked when a `Xid_log_event` is read from the binary log file
193 reader.
194
195 Actions taken to process the event:
196 - If `m_in_transaction` flag is set to false, `m_is_malformed` is set
197 to true, indicating that the binary log is malformed.
198 - The `m_in_transaction` flag is set to false, indicating that the
199 event ends a transaction.
200 - The XID of the transaction is extracted and added to the list of
201 internally coordinated transactions `m_internal_xids`.
202 - If the XID already exists in the list, `m_is_malformed` is set to
203 true, indicating that the binary log is malformed.
204
205 @param ev The `Xid_log_event` to process
206 */
207 void process_xid_event(Xid_log_event const &ev);
208 /**
209 Invoked when a `XA_prepare_log_event` is read from the binary log file
210 reader.
211
212 Actions taken to process the event:
213 - If `m_in_transaction` flag is set to false, `m_is_malformed` is set
214 to true, indicating that the binary log is malformed.
215 - The `m_in_transaction` flag is set to false, indicating that the
216 event ends a transaction.
217 - The XID of the transaction is extracted and added to the list of
218 externally coordinated transactions `m_external_xids`, along side the
219 state COMMITTED if the event represents an `XA COMMIT ONE_PHASE` or
220 PREPARED if not.
221 - If the XID already exists in the list associated with a state other
222 than `COMMITTED` or `ROLLEDBACK`, `m_is_malformed` is set to true,
223 indicating that the binary log is malformed.
224
225 @param ev The `XA_prepare_log_event` to process
226 */
228 /**
229 Invoked when a `BEGIN` or an `XA START' is found in a
230 `Query_log_event`.
231
232 Actions taken to process the statement:
233 - If `m_in_transaction` flag is set to true, `m_is_malformed` is set
234 to true, indicating that the binary log is malformed.
235 - The `m_in_transaction` flag is set to true, indicating that the
236 event starts a transaction.
237 */
238 void process_start();
239 /**
240 Invoked when a `COMMIT` is found in a `Query_log_event`.
241
242 Actions taken to process the statement:
243 - If `m_in_transaction` flag is set to false, `m_is_malformed` is set
244 to true, indicating that the binary log is malformed.
245 - The `m_in_transaction` flag is set to false, indicating that the
246 event starts a transaction.
247 */
248 void process_commit();
249 /**
250 Invoked when a `ROLLBACK` is found in a `Query_log_event`.
251
252 Actions taken to process the statement:
253 - If `m_in_transaction` flag is set to false, `m_is_malformed` is set
254 to true, indicating that the binary log is malformed.
255 - The `m_in_transaction` flag is set to false, indicating that the
256 event starts a transaction.
257 */
258 void process_rollback();
259 /**
260 Invoked when a DDL is found in a `Query_log_event`.
261
262 Actions taken to process the statement:
263 - If `m_in_transaction` flag is set to true, `m_is_malformed` is set
264 to true, indicating that the binary log is malformed.
265 - The XID of the transaction is extracted and added to the list of
266 internally coordinated transactions `m_internal_xids`.
267 - If the XID already exists in the list, `m_is_malformed` is set to
268 true, indicating that the binary log is malformed.
269
270 @param ev The `Query_log_event` to process
271 */
272 void process_atomic_ddl(Query_log_event const &ev);
273 /**
274 Invoked when an `XA COMMIT` is found in a `Query_log_event`.
275
276 Actions taken to process the statement:
277 - If `m_in_transaction` flag is set to true, `m_is_malformed` is set
278 to true, indicating that the binary log is malformed.
279 - The `m_in_transaction` flag is set to false, indicating that the
280 event ends a transaction.
281 - The XID of the transaction is extracted and added to the list of
282 externally coordinated transactions `m_external_xids`, alongside the
283 state COMMITTED.
284 - If the XID already exists in the list associated with a state other
285 than `PREPARED`, `m_is_malformed` is set to true, indicating that the
286 binary log is malformed.
287
288 @param query The query string to process
289 */
290 void process_xa_commit(std::string const &query);
291 /**
292 Invoked when an `XA ROLLBACK` is found in a `Query_log_event`.
293
294 Actions taken to process the statement:
295 - If `m_in_transaction` flag is set to true, `m_is_malformed` is set
296 to true, indicating that the binary log is malformed.
297 - The `m_in_transaction` flag is set to false, indicating that the
298 event ends a transaction.
299 - The XID of the transaction is extracted and added to the list of
300 externally coordinated transactions `m_external_xids`, along side the
301 state ROLLEDBACK.
302 - If the XID already exists in the list associated with a state other
303 than `PREPARED`, `m_is_malformed` is set to true, indicating that the
304 binary log is malformed.
305
306 @param query The query string to process
307 */
308 void process_xa_rollback(std::string const &query);
309 /**
310 Parses the provided string for an XID and adds it to the externally
311 coordinated transactions map, along side the provided state.
312
313 @param query The query to search and retrieve the XID from
314 @param state The state to add to the map, along side the XID
315 */
316 void add_external_xid(std::string const &query,
318};
319} // namespace binlog
320
321#endif // BINLOG_RECOVERY_H_INCLUDED
It owns an allocator, a byte stream, an event_data stream and an event object stream.
Definition: binlog_reader.h:294
Mem_root_allocator is a C++ STL memory allocator based on MEM_ROOT.
Definition: mem_root_allocator.h:67
A Query event is written to the binary log whenever the database is modified on the master,...
Definition: log_event.h:1284
Similar to Xid_log_event except that.
Definition: log_event.h:1820
std::map< XID, enum_ha_recover_xa_state, std::less< XID >, Xa_state_list::allocator > list
Definition: handler.h:1263
This is the subclass of Xid_event defined in libbinlogevent, An XID event is generated for a commit o...
Definition: log_event.h:1769
Recovers from last crashed binlog at server start.
Definition: recovery.h:63
void process_xa_commit(std::string const &query)
Invoked when an XA COMMIT is found in a Query_log_event.
Definition: recovery.cc:234
bool m_is_malformed
Whether or not the binary log is malformed/corrupted.
Definition: recovery.h:157
bool m_no_engine_recovery
Whether or not the recovery in the storage engines failed.
Definition: recovery.h:159
Binlog_file_reader & m_reader
File reader for the last available binary log file.
Definition: recovery.h:151
Mem_root_allocator< my_xid > m_set_alloc
Memory pool allocator to use with the normal transaction list.
Definition: recovery.h:165
Binlog_recovery(Binlog_file_reader &binlog_file_reader)
Class constructor.
Definition: recovery.cc:31
bool has_failures() const
Retrieves whether or not the recovery process ended successfully.
Definition: recovery.cc:44
void process_start()
Invoked when a BEGIN or an ‘XA START’ is found in a Query_log_event.
Definition: recovery.cc:192
Mem_root_allocator< std::pair< const XID, XID_STATE::xa_states > > m_map_alloc
Memory pool allocator to use with the XA transaction list.
Definition: recovery.h:167
bool m_in_transaction
Whether or not the event being processed is within a transaction.
Definition: recovery.h:155
void process_rollback()
Invoked when a ROLLBACK is found in a Query_log_event.
Definition: recovery.cc:210
virtual ~Binlog_recovery()=default
Xa_state_list::list m_external_xids
List of XA transactions and states that appear in the binary log.
Definition: recovery.h:171
Binlog_recovery & recover()
Uses the provided binary log file reader to inspect the binary log and extract transaction informatio...
Definition: recovery.cc:60
void process_atomic_ddl(Query_log_event const &ev)
Invoked when a DDL is found in a Query_log_event.
Definition: recovery.cc:219
Xid_commit_list m_internal_xids
List of normal transactions fully written to the binary log.
Definition: recovery.h:169
void process_xa_prepare_event(XA_prepare_log_event const &ev)
Invoked when a XA_prepare_log_event is read from the binary log file reader.
Definition: recovery.cc:160
void process_xa_rollback(std::string const &query)
Invoked when an XA ROLLBACK is found in a Query_log_event.
Definition: recovery.cc:250
void process_query_event(Query_log_event const &ev)
Invoked when a Query_log_event is read from the binary log file reader.
Definition: recovery.cc:123
void process_xid_event(Xid_log_event const &ev)
Invoked when a Xid_log_event is read from the binary log file reader.
Definition: recovery.cc:145
my_off_t get_valid_pos() const
Retrieves the position of the last binlog event that ended a transaction.
Definition: recovery.cc:40
void process_commit()
Invoked when a COMMIT is found in a Query_log_event.
Definition: recovery.cc:201
std::string const & get_failure_message() const
Retrieves the textual representation of the encontered failure, if any.
Definition: recovery.cc:56
void add_external_xid(std::string const &query, enum_ha_recover_xa_state state)
Parses the provided string for an XID and adds it to the externally coordinated transactions map,...
Definition: recovery.cc:266
std::string m_failure_message
Textual representation of the encountered failure.
Definition: recovery.h:161
my_off_t m_valid_pos
Position of the last binlog event that ended a transaction.
Definition: recovery.h:153
bool is_binlog_malformed() const
Retrieves whether or not the binary log was correctly processed in full.
Definition: recovery.cc:48
MEM_ROOT m_mem_root
Memory pool to use for the XID lists.
Definition: recovery.h:163
bool has_engine_recovery_failed() const
Retrieves whether or not the storage engines XA recovery process completed successfully.
Definition: recovery.cc:52
Binary log event definitions.
ulonglong my_off_t
Definition: my_inttypes.h:71
static char * query
Definition: myisam_ftdump.cc:46
Definition: pfs.cc:37
enum_ha_recover_xa_state
Enumeration of possible states for externally coordinated transactions (XA).
Definition: handler.h:1238
std::unordered_set< my_xid, std::hash< my_xid >, std::equal_to< my_xid >, Mem_root_allocator< my_xid > > Xid_commit_list
Single occurrence set of XIDs of internally coordinated transactions found as been committed in the t...
Definition: handler.h:1252
The MEM_ROOT is a simple arena, where allocations are carved out of larger blocks.
Definition: my_alloc.h:82