1 | /* Copyright (C) 2006 MySQL AB & MySQL Finland AB & TCX DataKonsult AB |
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 as published by |
5 | the Free Software Foundation; version 2 of the License. |
6 | |
7 | This program is distributed in the hope that it will be useful, |
8 | but WITHOUT ANY WARRANTY; without even the implied warranty of |
9 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
10 | GNU General Public License for more details. |
11 | |
12 | You should have received a copy of the GNU General Public License |
13 | along with this program; if not, write to the Free Software |
14 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02111-1301 USA */ |
15 | |
16 | /* Initialize an maria-database */ |
17 | |
18 | #include "maria_def.h" |
19 | #include <ft_global.h> |
20 | #include "ma_blockrec.h" |
21 | #include "trnman_public.h" |
22 | #include "ma_checkpoint.h" |
23 | #include <hash.h> |
24 | |
25 | void history_state_free(MARIA_STATE_HISTORY_CLOSED *closed_history) |
26 | { |
27 | MARIA_STATE_HISTORY *history, *next; |
28 | |
29 | /* |
30 | Free all active history |
31 | In case of maria_open() this list should be empty as the history is moved |
32 | to handler->share. |
33 | */ |
34 | for (history= closed_history->state_history; history ; history= next) |
35 | { |
36 | next= history->next; |
37 | my_free(history); |
38 | } |
39 | my_free(closed_history); |
40 | } |
41 | |
42 | |
43 | static int dummy_maria_create_trn_hook(MARIA_HA *info __attribute__((unused))) |
44 | { |
45 | return 0; |
46 | } |
47 | |
48 | /* |
49 | Initialize maria |
50 | |
51 | SYNOPSIS |
52 | maria_init() |
53 | |
54 | TODO |
55 | Open log files and do recovery if need |
56 | |
57 | RETURN |
58 | 0 ok |
59 | # error number |
60 | */ |
61 | |
62 | int maria_init(void) |
63 | { |
64 | DBUG_ASSERT(maria_block_size && |
65 | maria_block_size % MARIA_MIN_KEY_BLOCK_LENGTH == 0); |
66 | if (!maria_inited) |
67 | { |
68 | maria_inited= TRUE; |
69 | mysql_mutex_init(key_THR_LOCK_maria, &THR_LOCK_maria, MY_MUTEX_INIT_SLOW); |
70 | _ma_init_block_record_data(); |
71 | trnman_end_trans_hook= _ma_trnman_end_trans_hook; |
72 | maria_create_trn_hook= dummy_maria_create_trn_hook; |
73 | } |
74 | my_hash_init(&maria_stored_state, &my_charset_bin, 32, |
75 | 0, sizeof(LSN), 0, (my_hash_free_key) history_state_free, 0); |
76 | DBUG_PRINT("info" ,("dummy_transaction_object: %p" , |
77 | &dummy_transaction_object)); |
78 | return 0; |
79 | } |
80 | |
81 | |
82 | void maria_end(void) |
83 | { |
84 | if (maria_inited) |
85 | { |
86 | TrID trid; |
87 | maria_inited= maria_multi_threaded= FALSE; |
88 | ft_free_stopwords(); |
89 | ma_checkpoint_end(); |
90 | if (translog_status == TRANSLOG_OK) |
91 | { |
92 | translog_soft_sync_end(); |
93 | translog_sync(); |
94 | } |
95 | if ((trid= trnman_get_max_trid()) > max_trid_in_control_file) |
96 | { |
97 | /* |
98 | Store max transaction id into control file, in case logs are removed |
99 | by user, or maria_chk wants to check tables (it cannot access max trid |
100 | from the log, as it cannot process REDOs). |
101 | */ |
102 | (void)ma_control_file_write_and_force(last_checkpoint_lsn, last_logno, |
103 | trid, recovery_failures); |
104 | } |
105 | trnman_destroy(); |
106 | if (translog_status == TRANSLOG_OK || translog_status == TRANSLOG_READONLY) |
107 | translog_destroy(); |
108 | end_pagecache(maria_log_pagecache, TRUE); |
109 | end_pagecache(maria_pagecache, TRUE); |
110 | ma_control_file_end(); |
111 | mysql_mutex_destroy(&THR_LOCK_maria); |
112 | my_hash_free(&maria_stored_state); |
113 | } |
114 | } |
115 | |
116 | /** |
117 | Upgrade from older Aria versions: |
118 | |
119 | - In MariaDB 5.1, the name of the control file and log files had the |
120 | 'maria' prefix, now they have the 'aria' prefix. |
121 | |
122 | @return: 0 ok |
123 | 1 error |
124 | |
125 | */ |
126 | |
127 | my_bool maria_upgrade() |
128 | { |
129 | char name[FN_REFLEN], new_name[FN_REFLEN]; |
130 | DBUG_ENTER("maria_upgrade" ); |
131 | |
132 | fn_format(name, "maria_log_control" , maria_data_root, "" , MYF(MY_WME)); |
133 | |
134 | if (!my_access(name,F_OK)) |
135 | { |
136 | /* |
137 | Old style control file found; Rename the control file and the log files. |
138 | We start by renaming all log files, so that if we get a crash |
139 | we will continue from where we left. |
140 | */ |
141 | uint i; |
142 | MY_DIR *dir= my_dir(maria_data_root, MYF(MY_WME)); |
143 | if (!dir) |
144 | DBUG_RETURN(1); |
145 | |
146 | my_message(HA_ERR_INITIALIZATION, |
147 | "Found old style Maria log files; " |
148 | "Converting them to Aria names" , |
149 | MYF(ME_JUST_INFO)); |
150 | |
151 | for (i= 0; i < dir->number_of_files; i++) |
152 | { |
153 | const char *file= dir->dir_entry[i].name; |
154 | if (strncmp(file, "maria_log." , 10) == 0 && |
155 | file[10] >= '0' && file[10] <= '9' && |
156 | file[11] >= '0' && file[11] <= '9' && |
157 | file[12] >= '0' && file[12] <= '9' && |
158 | file[13] >= '0' && file[13] <= '9' && |
159 | file[14] >= '0' && file[14] <= '9' && |
160 | file[15] >= '0' && file[15] <= '9' && |
161 | file[16] >= '0' && file[16] <= '9' && |
162 | file[17] >= '0' && file[17] <= '9' && |
163 | file[18] == '\0') |
164 | { |
165 | /* Remove the 'm' in 'maria' */ |
166 | char old_logname[FN_REFLEN], new_logname[FN_REFLEN]; |
167 | fn_format(old_logname, file, maria_data_root, "" , MYF(0)); |
168 | fn_format(new_logname, file+1, maria_data_root, "" , MYF(0)); |
169 | if (mysql_file_rename(key_file_translog, old_logname, |
170 | new_logname, MYF(MY_WME))) |
171 | { |
172 | my_dirend(dir); |
173 | DBUG_RETURN(1); |
174 | } |
175 | } |
176 | } |
177 | my_dirend(dir); |
178 | |
179 | fn_format(new_name, CONTROL_FILE_BASE_NAME, maria_data_root, "" , MYF(0)); |
180 | if (mysql_file_rename(key_file_control, name, new_name, MYF(MY_WME))) |
181 | DBUG_RETURN(1); |
182 | } |
183 | DBUG_RETURN(0); |
184 | } |
185 | |