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
babb000a
Commit
babb000a
authored
Nov 28, 2018
by
Marko Mäkelä
Browse files
Options
Browse Files
Download
Plain Diff
Merge 10.2 into 10.3
parents
4b88d5ee
4a92165f
Changes
13
Hide whitespace changes
Inline
Side-by-side
Showing
13 changed files
with
264 additions
and
502 deletions
+264
-502
extra/mariabackup/fil_cur.cc
extra/mariabackup/fil_cur.cc
+5
-4
extra/mariabackup/xtrabackup.cc
extra/mariabackup/xtrabackup.cc
+10
-54
storage/innobase/fil/fil0fil.cc
storage/innobase/fil/fil0fil.cc
+156
-214
storage/innobase/fsp/fsp0space.cc
storage/innobase/fsp/fsp0space.cc
+5
-8
storage/innobase/fsp/fsp0sysspace.cc
storage/innobase/fsp/fsp0sysspace.cc
+8
-9
storage/innobase/handler/ha_innodb.cc
storage/innobase/handler/ha_innodb.cc
+2
-2
storage/innobase/include/fil0fil.h
storage/innobase/include/fil0fil.h
+19
-24
storage/innobase/include/mem0mem.h
storage/innobase/include/mem0mem.h
+0
-100
storage/innobase/include/srv0srv.h
storage/innobase/include/srv0srv.h
+1
-1
storage/innobase/srv/srv0mon.cc
storage/innobase/srv/srv0mon.cc
+1
-1
storage/innobase/srv/srv0srv.cc
storage/innobase/srv/srv0srv.cc
+1
-1
storage/innobase/srv/srv0start.cc
storage/innobase/srv/srv0start.cc
+53
-79
storage/innobase/trx/trx0trx.cc
storage/innobase/trx/trx0trx.cc
+3
-5
No files found.
extra/mariabackup/fil_cur.cc
View file @
babb000a
...
...
@@ -109,7 +109,6 @@ xb_fil_node_close_file(
ut_a
(
fil_system
.
n_open
>
0
);
fil_system
.
n_open
--
;
fil_n_file_opened
--
;
if
(
node
->
space
->
purpose
==
FIL_TYPE_TABLESPACE
&&
fil_is_user_tablespace_id
(
node
->
space
->
id
))
{
...
...
@@ -159,8 +158,11 @@ xb_fil_cur_open(
/* In the backup mode we should already have a tablespace handle created
by fil_ibd_load() unless it is a system
tablespace. Otherwise we open the file here. */
if
(
cursor
->
is_system
()
||
srv_operation
==
SRV_OPERATION_RESTORE_DELTA
||
xb_close_files
)
{
if
(
!
node
->
is_open
())
{
ut_ad
(
cursor
->
is_system
()
||
srv_operation
==
SRV_OPERATION_RESTORE_DELTA
||
xb_close_files
);
node
->
handle
=
os_file_create_simple_no_error_handling
(
0
,
node
->
name
,
OS_FILE_OPEN
,
...
...
@@ -178,7 +180,6 @@ xb_fil_cur_open(
mutex_enter
(
&
fil_system
.
mutex
);
fil_system
.
n_open
++
;
fil_n_file_opened
++
;
if
(
node
->
space
->
purpose
==
FIL_TYPE_TABLESPACE
&&
fil_is_user_tablespace_id
(
node
->
space
->
id
))
{
...
...
extra/mariabackup/xtrabackup.cc
View file @
babb000a
...
...
@@ -3094,11 +3094,8 @@ xb_load_single_table_tablespace(
ut_a
(
space
!=
NULL
);
if
(
!
fil_node_create
(
file
->
filepath
(),
ulint
(
n_pages
),
space
,
false
,
false
))
{
ut_error
;
}
space
->
add
(
file
->
filepath
(),
OS_FILE_CLOSED
,
ulint
(
n_pages
),
false
,
false
);
/* by opening the tablespace we forcing node and space objects
in the cache to be populated with fields from space header */
space
->
open
();
...
...
@@ -3775,22 +3772,17 @@ xb_filters_free()
}
/*********************************************************************//**
Creates or opens the log files and closes them.
@return DB_SUCCESS or error code */
Create log file metadata. */
static
ulint
void
open_or_create_log_file
(
/*====================*/
fil_space_t
*
space
,
ibool
*
log_file_created
,
/*!< out: TRUE if new log file
created */
ulint
i
)
/*!< in: log file number in group */
{
char
name
[
10000
];
ulint
dirnamelen
;
*
log_file_created
=
FALSE
;
os_normalize_path
(
srv_log_group_home_dir
);
dirnamelen
=
strlen
(
srv_log_group_home_dir
);
...
...
@@ -3802,14 +3794,13 @@ open_or_create_log_file(
name
[
dirnamelen
++
]
=
OS_PATH_SEPARATOR
;
}
sprintf
(
name
+
dirnamelen
,
"%s%
lu"
,
"ib_logfile"
,
(
ulong
)
i
);
sprintf
(
name
+
dirnamelen
,
"%s%
zu"
,
"ib_logfile"
,
i
);
ut_a
(
fil_validate
());
ut_a
(
fil_node_create
(
name
,
ulint
(
srv_log_file_size
>>
srv_page_size_shift
),
space
,
false
,
false
));
return
(
DB_SUCCESS
);
space
->
add
(
name
,
OS_FILE_CLOSED
,
ulint
(
srv_log_file_size
>>
srv_page_size_shift
),
false
,
false
);
}
/***********************************************************************
...
...
@@ -4069,13 +4060,6 @@ xtrabackup_backup_func()
xb_filters_init
();
{
ibool
log_file_created
;
ibool
log_created
=
FALSE
;
ibool
log_opened
=
FALSE
;
ulint
err
;
ulint
i
;
xb_fil_io_init
();
srv_n_file_io_threads
=
srv_n_read_io_threads
;
...
...
@@ -4088,36 +4072,8 @@ xtrabackup_backup_func()
"innodb_redo_log"
,
SRV_LOG_SPACE_FIRST_ID
,
0
,
FIL_TYPE_LOG
,
NULL
);
for
(
i
=
0
;
i
<
srv_n_log_files
;
i
++
)
{
err
=
open_or_create_log_file
(
space
,
&
log_file_created
,
i
);
if
(
err
!=
DB_SUCCESS
)
{
goto
fail
;
}
if
(
log_file_created
)
{
log_created
=
TRUE
;
}
else
{
log_opened
=
TRUE
;
}
if
((
log_opened
&&
log_created
))
{
msg
(
"mariabackup: Error: all log files must be created at the same time.
\n
"
"mariabackup: All log files must be created also in database creation.
\n
"
"mariabackup: If you want bigger or smaller log files, shut down the
\n
"
"mariabackup: database and make sure there were no errors in shutdown.
\n
"
"mariabackup: Then delete the existing log files. Edit the .cnf file
\n
"
"mariabackup: and start the database again.
\n
"
);
goto
fail
;
}
}
/* log_file_created must not be TRUE, if online */
if
(
log_file_created
)
{
msg
(
"mariabackup: Something wrong with source files...
\n
"
);
goto
fail
;
}
for
(
ulint
i
=
0
;
i
<
srv_n_log_files
;
i
++
)
{
open_or_create_log_file
(
space
,
i
);
}
/* create extra LSN dir if it does not exist. */
...
...
storage/innobase/fil/fil0fil.cc
View file @
babb000a
...
...
@@ -166,9 +166,6 @@ ulint fil_n_pending_log_flushes = 0;
/** Number of pending tablespace flushes */
ulint
fil_n_pending_tablespace_flushes
=
0
;
/** Number of files currently open */
ulint
fil_n_file_opened
=
0
;
/** The null file address */
const
fil_addr_t
fil_addr_null
=
{
FIL_NULL
,
0
};
...
...
@@ -437,36 +434,25 @@ fil_space_is_flushed(
/** Append a file to the chain of files of a space.
@param[in] name file name of a file that is not open
@param[in]
size file size in entire database blocks
@param[in
,out] space tablespace from fil_space_create()
@param[in] is_raw whether this is a raw device
or partition
@param[in] atomic_write true if
the file could use atomic write
@param[in]
handle file handle, or OS_FILE_CLOSED
@param[in
] size file size in entire database pages
@param[in] is_raw whether this is a raw device
@param[in] atomic_write true if
atomic write could be enabled
@param[in] max_pages maximum number of pages in file,
ULINT_MAX means the file size is unlimited.
@return pointer to the file name
@retval NULL if error */
static
fil_node_t
*
fil_node_create_low
(
const
char
*
name
,
ulint
size
,
fil_space_t
*
space
,
bool
is_raw
,
bool
atomic_write
,
ulint
max_pages
=
ULINT_MAX
)
or ULINT_MAX for unlimited
@return file object */
fil_node_t
*
fil_space_t
::
add
(
const
char
*
name
,
pfs_os_file_t
handle
,
ulint
size
,
bool
is_raw
,
bool
atomic_write
,
ulint
max_pages
)
{
fil_node_t
*
node
;
ut_ad
(
name
!=
NULL
);
ut_ad
(
fil_system
.
is_initialised
());
if
(
space
==
NULL
)
{
return
(
NULL
);
}
node
=
reinterpret_cast
<
fil_node_t
*>
(
ut_zalloc_nokey
(
sizeof
(
*
node
)));
node
->
handle
=
OS_FILE_CLOSED
;
node
->
handle
=
handle
;
node
->
name
=
mem_strdup
(
name
);
...
...
@@ -483,55 +469,115 @@ fil_node_create_low(
node
->
init_size
=
size
;
node
->
max_size
=
max_pages
;
mutex_enter
(
&
fil_system
.
mutex
);
space
->
size
+=
size
;
node
->
space
=
space
;
node
->
space
=
this
;
node
->
atomic_write
=
atomic_write
;
UT_LIST_ADD_LAST
(
space
->
chain
,
node
);
mutex_enter
(
&
fil_system
.
mutex
);
this
->
size
+=
size
;
UT_LIST_ADD_LAST
(
chain
,
node
);
if
(
node
->
is_open
())
{
fil_system
.
n_open
++
;
}
mutex_exit
(
&
fil_system
.
mutex
);
return
(
node
)
;
return
node
;
}
/** Appends a new file to the chain of files of a space. File must be closed.
@param[in] name file name (file must be closed)
@param[in] size file size in database blocks, rounded downwards to
an integer
@param[in,out] space space where to append
@param[in] is_raw true if a raw device or a raw disk partition
@param[in] atomic_write true if the file could use atomic write
@param[in] max_pages maximum number of pages in file,
ULINT_MAX means the file size is unlimited.
@return pointer to the file name
@retval NULL if error */
char
*
fil_node_create
(
const
char
*
name
,
ulint
size
,
fil_space_t
*
space
,
bool
is_raw
,
bool
atomic_write
,
ulint
max_pages
)
/** Read the first page of a data file.
@param[in] first whether this is the very first read
@return whether the page was found valid */
bool
fil_node_t
::
read_page0
(
bool
first
)
{
fil_node_t
*
node
;
ut_ad
(
mutex_own
(
&
fil_system
.
mutex
));
ut_a
(
space
->
purpose
!=
FIL_TYPE_LOG
);
const
page_size_t
page_size
(
space
->
flags
);
const
ulint
psize
=
page_size
.
physical
();
os_offset_t
size_bytes
=
os_file_get_size
(
handle
);
ut_a
(
size_bytes
!=
(
os_offset_t
)
-
1
);
const
ulint
min_size
=
FIL_IBD_FILE_INITIAL_SIZE
*
psize
;
node
=
fil_node_create_low
(
name
,
size
,
space
,
is_raw
,
atomic_write
,
max_pages
);
if
(
size_bytes
<
min_size
)
{
ib
::
error
()
<<
"The size of the file "
<<
name
<<
" is only "
<<
size_bytes
<<
" bytes, should be at least "
<<
min_size
;
return
false
;
}
return
(
node
==
NULL
?
NULL
:
node
->
name
);
byte
*
buf2
=
static_cast
<
byte
*>
(
ut_malloc_nokey
(
2
*
psize
));
/* Align the memory for file i/o if we might have O_DIRECT set */
byte
*
page
=
static_cast
<
byte
*>
(
ut_align
(
buf2
,
psize
));
IORequest
request
(
IORequest
::
READ
);
if
(
!
os_file_read
(
request
,
handle
,
page
,
0
,
psize
))
{
ib
::
error
()
<<
"Unable to read first page of file "
<<
name
;
ut_free
(
buf2
);
return
false
;
}
srv_stats
.
page0_read
.
add
(
1
);
const
ulint
space_id
=
fsp_header_get_space_id
(
page
);
ulint
flags
=
fsp_header_get_flags
(
page
);
const
ulint
size
=
fsp_header_get_field
(
page
,
FSP_SIZE
);
const
ulint
free_limit
=
fsp_header_get_field
(
page
,
FSP_FREE_LIMIT
);
const
ulint
free_len
=
flst_get_len
(
FSP_HEADER_OFFSET
+
FSP_FREE
+
page
);
/* Try to read crypt_data from page 0 if it is not yet read. */
if
(
!
space
->
crypt_data
)
{
space
->
crypt_data
=
fil_space_read_crypt_data
(
page_size
,
page
);
}
ut_free
(
buf2
);
if
(
!
fsp_flags_is_valid
(
flags
,
space
->
id
))
{
ulint
cflags
=
fsp_flags_convert_from_101
(
flags
);
if
(
cflags
==
ULINT_UNDEFINED
||
(
cflags
^
space
->
flags
)
&
~
FSP_FLAGS_MEM_MASK
)
{
ib
::
error
()
<<
"Expected tablespace flags "
<<
ib
::
hex
(
space
->
flags
)
<<
" but found "
<<
ib
::
hex
(
flags
)
<<
" in the file "
<<
name
;
return
false
;
}
flags
=
cflags
;
}
if
(
UNIV_UNLIKELY
(
space_id
!=
space
->
id
))
{
ib
::
error
()
<<
"Expected tablespace id "
<<
space
->
id
<<
" but found "
<<
space_id
<<
" in the file "
<<
name
;
return
false
;
}
ut_ad
(
space
->
free_limit
==
0
||
space
->
free_limit
==
free_limit
);
ut_ad
(
space
->
free_len
==
0
||
space
->
free_len
==
free_len
);
space
->
size_in_header
=
size
;
space
->
free_limit
=
free_limit
;
space
->
free_len
=
free_len
;
if
(
first
)
{
/* Truncate the size to a multiple of extent size. */
ulint
mask
=
psize
*
FSP_EXTENT_SIZE
-
1
;
if
(
size_bytes
<=
mask
)
{
/* .ibd files start smaller than an
extent size. Do not truncate valid data. */
}
else
{
size_bytes
&=
~
os_offset_t
(
mask
);
}
this
->
size
=
ulint
(
size_bytes
/
psize
);
space
->
size
+=
this
->
size
;
}
return
true
;
}
/** Open a file node of a tablespace.
@param[in,out] node File node
@return false if the file can't be opened, otherwise true */
static
bool
fil_node_open_file
(
fil_node_t
*
node
)
static
bool
fil_node_open_file
(
fil_node_t
*
node
)
{
bool
success
;
bool
read_only_mode
;
...
...
@@ -559,9 +605,12 @@ fil_node_open_file(
from a file opened for async I/O! */
retry:
node
->
handle
=
os_file_create_simple_no_error_handling
(
innodb_data_file_key
,
node
->
name
,
OS_FILE_OPEN
,
OS_FILE_READ_ONLY
,
read_only_mode
,
&
success
);
node
->
handle
=
os_file_create
(
innodb_data_file_key
,
node
->
name
,
node
->
is_raw_disk
?
OS_FILE_OPEN_RAW
|
OS_FILE_ON_ERROR_NO_EXIT
:
OS_FILE_OPEN
|
OS_FILE_ON_ERROR_NO_EXIT
,
OS_FILE_AIO
,
OS_DATA_FILE
,
read_only_mode
,
&
success
);
if
(
!
success
)
{
/* The following call prints an error message */
...
...
@@ -577,156 +626,52 @@ fil_node_open_file(
return
(
false
);
}
os_offset_t
size_bytes
=
os_file_get_size
(
node
->
handle
);
ut_a
(
size_bytes
!=
(
os_offset_t
)
-
1
);
ut_a
(
space
->
purpose
!=
FIL_TYPE_LOG
);
const
page_size_t
page_size
(
space
->
flags
);
const
ulint
psize
=
page_size
.
physical
();
const
ulint
min_size
=
FIL_IBD_FILE_INITIAL_SIZE
*
psize
;
if
(
size_bytes
<
min_size
)
{
ib
::
error
()
<<
"The size of the file "
<<
node
->
name
<<
" is only "
<<
size_bytes
<<
" bytes, should be at least "
<<
min_size
;
if
(
!
node
->
read_page0
(
first_time_open
))
{
os_file_close
(
node
->
handle
);
node
->
handle
=
OS_FILE_CLOSED
;
return
(
false
);
}
/* Read the first page of the tablespace */
byte
*
buf2
=
static_cast
<
byte
*>
(
ut_malloc_nokey
(
2
*
psize
));
/* Align the memory for file i/o if we might have O_DIRECT
set */
byte
*
page
=
static_cast
<
byte
*>
(
ut_align
(
buf2
,
psize
));
IORequest
request
(
IORequest
::
READ
);
success
=
os_file_read
(
request
,
node
->
handle
,
page
,
0
,
psize
);
srv_stats
.
page0_read
.
add
(
1
);
const
ulint
space_id
=
fsp_header_get_space_id
(
page
);
ulint
flags
=
fsp_header_get_flags
(
page
);
const
ulint
size
=
fsp_header_get_field
(
page
,
FSP_SIZE
);
const
ulint
free_limit
=
fsp_header_get_field
(
page
,
FSP_FREE_LIMIT
);
const
ulint
free_len
=
flst_get_len
(
FSP_HEADER_OFFSET
+
FSP_FREE
+
page
);
/* Try to read crypt_data from page 0 if it is not yet
read. */
if
(
!
space
->
crypt_data
)
{
space
->
crypt_data
=
fil_space_read_crypt_data
(
page_size_t
(
space
->
flags
),
page
);
}
ut_free
(
buf2
);
os_file_close
(
node
->
handle
);
node
->
handle
=
OS_FILE_CLOSED
;
if
(
!
fsp_flags_is_valid
(
flags
,
space
->
id
))
{
ulint
cflags
=
fsp_flags_convert_from_101
(
flags
);
if
(
cflags
==
ULINT_UNDEFINED
||
(
cflags
^
space
->
flags
)
&
~
FSP_FLAGS_MEM_MASK
)
{
ib
::
error
()
<<
"Expected tablespace flags "
<<
ib
::
hex
(
space
->
flags
)
<<
" but found "
<<
ib
::
hex
(
flags
)
<<
" in the file "
<<
node
->
name
;
return
(
false
);
}
flags
=
cflags
;
}
if
(
UNIV_UNLIKELY
(
space_id
!=
space
->
id
))
{
ib
::
error
()
<<
"Expected tablespace id "
<<
space
->
id
<<
" but found "
<<
space_id
<<
" in the file"
<<
node
->
name
;
return
(
false
);
}
ut_ad
(
space
->
free_limit
==
0
||
space
->
free_limit
==
free_limit
);
ut_ad
(
space
->
free_len
==
0
||
space
->
free_len
==
free_len
);
space
->
size_in_header
=
size
;
space
->
free_limit
=
free_limit
;
space
->
free_len
=
free_len
;
if
(
first_time_open
)
{
/* Truncate the size to a multiple of extent size. */
ulint
mask
=
psize
*
FSP_EXTENT_SIZE
-
1
;
if
(
size_bytes
<=
mask
)
{
/* .ibd files start smaller than an
extent size. Do not truncate valid data. */
}
else
{
size_bytes
&=
~
os_offset_t
(
mask
);
}
node
->
size
=
ulint
(
size_bytes
/
psize
);
space
->
size
+=
node
->
size
;
return
false
;
}
}
/* printf("Opening file %s\n", node->name); */
/* Open the file for reading and writing, in Windows normally in the
unbuffered async I/O mode, though global variables may make
os_file_create() to fall back to the normal file I/O mode. */
if
(
space
->
purpose
==
FIL_TYPE_LOG
)
{
}
else
if
(
space
->
purpose
==
FIL_TYPE_LOG
)
{
node
->
handle
=
os_file_create
(
innodb_log_file_key
,
node
->
name
,
OS_FILE_OPEN
,
OS_FILE_AIO
,
OS_LOG_FILE
,
read_only_mode
,
&
success
);
}
else
if
(
node
->
is_raw_disk
)
{
node
->
handle
=
os_file_create
(
innodb_data_file_key
,
node
->
name
,
OS_FILE_OPEN_RAW
,
OS_FILE_AIO
,
OS_DATA_FILE
,
read_only_mode
,
&
success
);
}
else
{
node
->
handle
=
os_file_create
(
innodb_data_file_key
,
node
->
name
,
OS_FILE_OPEN
,
innodb_data_file_key
,
node
->
name
,
node
->
is_raw_disk
?
OS_FILE_OPEN_RAW
|
OS_FILE_ON_ERROR_NO_EXIT
:
OS_FILE_OPEN
|
OS_FILE_ON_ERROR_NO_EXIT
,
OS_FILE_AIO
,
OS_DATA_FILE
,
read_only_mode
,
&
success
);
}
if
(
first_time_open
)
{
/*
For the temporary tablespace and during the
non-redo-logged adjustments in
IMPORT TABLESPACE, we do not care about
the atomicity of writes.
Atomic writes is supported if the file can be used
with atomic_writes (not log file), O_DIRECT is
used (tested in ha_innodb.cc) and the file is
device and file system that supports atomic writes
for the given block size
*/
space
->
atomic_write_supported
=
space
->
purpose
==
FIL_TYPE_TEMPORARY
||
space
->
purpose
==
FIL_TYPE_IMPORT
||
(
node
->
atomic_write
&&
srv_use_atomic_writes
&&
my_test_if_atomic_write
(
node
->
handle
,
int
(
page_size_t
(
space
->
flags
)
.
physical
())));
}
}
if
(
space
->
purpose
!=
FIL_TYPE_LOG
)
{
/*
For the temporary tablespace and during the
non-redo-logged adjustments in
IMPORT TABLESPACE, we do not care about
the atomicity of writes.
Atomic writes is supported if the file can be used
with atomic_writes (not log file), O_DIRECT is
used (tested in ha_innodb.cc) and the file is
device and file system that supports atomic writes
for the given block size
*/
space
->
atomic_write_supported
=
space
->
purpose
==
FIL_TYPE_TEMPORARY
||
space
->
purpose
==
FIL_TYPE_IMPORT
||
(
node
->
atomic_write
&&
srv_use_atomic_writes
&&
my_test_if_atomic_write
(
node
->
handle
,
int
(
page_size_t
(
space
->
flags
)
.
physical
())));
}
ut_a
(
success
);
ut_a
(
node
->
is_open
());
fil_system
.
n_open
++
;
fil_n_file_opened
++
;
if
(
fil_space_belongs_in_lru
(
space
))
{
...
...
@@ -761,7 +706,6 @@ void fil_node_t::close()
ut_ad
(
!
is_open
());
ut_a
(
fil_system
.
n_open
>
0
);
fil_system
.
n_open
--
;
fil_n_file_opened
--
;
if
(
fil_space_belongs_in_lru
(
space
))
{
ut_a
(
UT_LIST_GET_LEN
(
fil_system
.
LRU
)
>
0
);
...
...
@@ -1396,7 +1340,7 @@ Error messages are issued to the server log.
@param[in] purpose tablespace purpose
@param[in,out] crypt_data encryption information
@param[in] mode encryption mode
@return pointer to created tablespace, to be filled in with fil_
node_create
()
@return pointer to created tablespace, to be filled in with fil_
space_t::add
()
@retval NULL on failure (such as when the same tablespace exists) */
fil_space_t
*
fil_space_create
(
...
...
@@ -1472,7 +1416,7 @@ fil_space_create(
if
(
space
->
purpose
==
FIL_TYPE_TEMPORARY
)
{
/* SysTablespace::open_or_create() would pass
size!=0 to fil_
node_create
(), so first_time_open
size!=0 to fil_
space_t::add
(), so first_time_open
would not hold in fil_node_open_file(), and we
must assign this manually. We do not care about
the durability or atomicity of writes to the
...
...
@@ -3225,17 +3169,17 @@ fil_ibd_create(
free
(
crypt_data
);
*
err
=
DB_ERROR
;
}
else
{
fil_node_t
*
node
=
fil_node_create_low
(
path
,
size
,
spac
e
,
false
,
true
);
fil_node_t
*
file
=
space
->
add
(
path
,
OS_FILE_CLOSED
,
siz
e
,
false
,
true
);
mtr_t
mtr
;
mtr
.
start
();
fil_op_write_log
(
MLOG_FILE_CREATE2
,
space_id
,
0
,
nod
e
->
name
,
MLOG_FILE_CREATE2
,
space_id
,
0
,
fil
e
->
name
,
NULL
,
space
->
flags
&
~
FSP_FLAGS_MEM_MASK
,
&
mtr
);
fil_name_write
(
space
,
0
,
nod
e
,
&
mtr
);
fil_name_write
(
space
,
0
,
fil
e
,
&
mtr
);
mtr
.
commit
();
nod
e
->
block_size
=
block_size
;
fil
e
->
block_size
=
block_size
;
space
->
punch_hole
=
punch_hole
;
*
err
=
DB_SUCCESS
;
...
...
@@ -3603,17 +3547,17 @@ fil_ibd_open(
fil_space_t
*
space
=
fil_space_create
(
tablename
.
m_name
,
id
,
flags
,
purpose
,
crypt_data
);
if
(
!
space
)
{
goto
error
;
}
/* We do not measure the size of the file, that is why
we pass the 0 below */
if
(
fil_node_create_low
(
df_remote
.
is_open
()
?
df_remote
.
filepath
()
:
df_dict
.
is_open
()
?
df_dict
.
filepath
()
:
df_default
.
filepath
(),
0
,
space
,
false
,
true
)
==
NULL
)
{
goto
error
;
}
space
->
add
(
df_remote
.
is_open
()
?
df_remote
.
filepath
()
:
df_dict
.
is_open
()
?
df_dict
.
filepath
()
:
df_default
.
filepath
(),
OS_FILE_CLOSED
,
0
,
false
,
true
);
if
(
validate
&&
purpose
!=
FIL_TYPE_IMPORT
&&
!
srv_read_only_mode
)
{
df_remote
.
close
();
...
...
@@ -3962,9 +3906,7 @@ fil_ibd_load(
the rounding formula for extents and pages is somewhat complex; we
let fil_node_open() do that task. */
if
(
!
fil_node_create_low
(
file
.
filepath
(),
0
,
space
,
false
,
false
))
{
ut_error
;
}
space
->
add
(
file
.
filepath
(),
OS_FILE_CLOSED
,
0
,
false
,
false
);
return
(
FIL_LOAD_OK
);
}
...
...
storage/innobase/fsp/fsp0space.cc
View file @
babb000a
...
...
@@ -123,18 +123,15 @@ Tablespace::open_or_create(bool is_temp)
is_temp
?
FIL_TYPE_TEMPORARY
:
FIL_TYPE_TABLESPACE
,
NULL
);
if
(
!
space
)
{
return
DB_ERROR
;
}
}
ut_a
(
fil_validate
());
/* Create the tablespace node entry for this data file. */
if
(
!
fil_node_create
(
it
->
m_filepath
,
it
->
m_size
,
space
,
false
,
TRUE
))
{
err
=
DB_ERROR
;
break
;
}
space
->
add
(
it
->
m_filepath
,
OS_FILE_CLOSED
,
it
->
m_size
,
false
,
true
);
}
return
(
err
);
...
...
storage/innobase/fsp/fsp0sysspace.cc
View file @
babb000a
...
...
@@ -907,12 +907,18 @@ SysTablespace::open_or_create(
space
=
fil_system
.
temp_space
=
fil_space_create
(
name
(),
SRV_TMP_SPACE_ID
,
flags
(),
FIL_TYPE_TEMPORARY
,
NULL
);
if
(
!
space
)
{
return
DB_ERROR
;
}
}
else
{
ut_ad
(
!
fil_system
.
sys_space
);
ut_ad
(
space_id
()
==
TRX_SYS_SPACE
);
space
=
fil_system
.
sys_space
=
fil_space_create
(
name
(),
TRX_SYS_SPACE
,
flags
(),
FIL_TYPE_TABLESPACE
,
NULL
);
if
(
!
space
)
{
return
DB_ERROR
;
}
}
ut_a
(
fil_validate
());
...
...
@@ -923,15 +929,8 @@ SysTablespace::open_or_create(
:
m_last_file_size_max
)
:
it
->
m_size
);
/* Add the datafile to the fil_system cache. */
if
(
!
fil_node_create
(
it
->
m_filepath
,
it
->
m_size
,
space
,
it
->
m_type
!=
SRV_NOT_RAW
,
TRUE
,
max_size
))
{
err
=
DB_ERROR
;
break
;
}
space
->
add
(
it
->
m_filepath
,
OS_FILE_CLOSED
,
it
->
m_size
,
it
->
m_type
!=
SRV_NOT_RAW
,
true
,
max_size
);
}
return
(
err
);
...
...
storage/innobase/handler/ha_innodb.cc
View file @
babb000a
...
...
@@ -12360,7 +12360,7 @@ int create_table_info_t::create_table(bool create_fk)
the failed creation. */
m_trx
->
error_state
=
DB_SUCCESS
;
row_drop_table_for_mysql
(
m_table_name
,
m_trx
,
SQLCOM_
DROP_DB
);
SQLCOM_
TRUNCATE
);
trx_rollback_to_savepoint
(
m_trx
,
NULL
);
m_trx
->
error_state
=
DB_SUCCESS
;
...
...
@@ -12592,7 +12592,7 @@ ha_innobase::create(
that could have been renamed before the failed creation. */
trx
->
error_state
=
DB_SUCCESS
;
row_drop_table_for_mysql
(
info
.
table_name
(),
trx
,
SQLCOM_
DROP_DB
,
true
);
SQLCOM_
TRUNCATE
,
true
);
trx_rollback_for_mysql
(
trx
);
row_mysql_unlock_data_dictionary
(
trx
);
if
(
own_trx
)
{
...
...
storage/innobase/include/fil0fil.h
View file @
babb000a
...
...
@@ -189,6 +189,19 @@ struct fil_space_t {
&&
srv_use_doublewrite_buf
&&
buf_dblwr
;
}
/** Append a file to the chain of files of a space.
@param[in] name file name of a file that is not open
@param[in] handle file handle, or OS_FILE_CLOSED
@param[in] size file size in entire database pages
@param[in] is_raw whether this is a raw device
@param[in] atomic_write true if atomic write could be enabled
@param[in] max_pages maximum number of pages in file,
or ULINT_MAX for unlimited
@return file object */
fil_node_t
*
add
(
const
char
*
name
,
pfs_os_file_t
handle
,
ulint
size
,
bool
is_raw
,
bool
atomic_write
,
ulint
max_pages
=
ULINT_MAX
);
/** Try to reserve free extents.
@param[in] n_free_now current number of free extents
@param[in] n_to_reserve number of extents to reserve
...
...
@@ -324,6 +337,11 @@ struct fil_node_t {
return
(
handle
!=
OS_FILE_CLOSED
);
}
/** Read the first page of a data file.
@param[in] first whether this is the very first read
@return whether the page was found valid */
bool
read_page0
(
bool
first
);
/** Close the file handle. */
void
close
();
};
...
...
@@ -528,9 +546,6 @@ extern ulint fil_n_pending_log_flushes;
/** Number of pending tablespace flushes */
extern
ulint
fil_n_pending_tablespace_flushes
;
/** Number of files currently open */
extern
ulint
fil_n_file_opened
;
#ifndef UNIV_INNOCHECKSUM
/** Look up a tablespace.
...
...
@@ -645,26 +660,6 @@ fil_space_get_latch(
ulint
id
,
ulint
*
flags
);
/** Append a file to the chain of files of a space.
@param[in] name file name of a file that is not open
@param[in] size file size in entire database blocks
@param[in,out] space tablespace from fil_space_create()
@param[in] is_raw whether this is a raw device or partition
@param[in] atomic_write true if atomic write could be enabled
@param[in] max_pages maximum number of pages in file,
ULINT_MAX means the file size is unlimited.
@return pointer to the file name
@retval NULL if error */
char
*
fil_node_create
(
const
char
*
name
,
ulint
size
,
fil_space_t
*
space
,
bool
is_raw
,
bool
atomic_write
,
ulint
max_pages
=
ULINT_MAX
)
MY_ATTRIBUTE
((
warn_unused_result
));
/** Create a space memory object and put it to the fil_system hash table.
Error messages are issued to the server log.
@param[in] name tablespace name
...
...
@@ -673,7 +668,7 @@ Error messages are issued to the server log.
@param[in] purpose tablespace purpose
@param[in,out] crypt_data encryption information
@param[in] mode encryption mode
@return pointer to created tablespace, to be filled in with fil_
node_create
()
@return pointer to created tablespace, to be filled in with fil_
space_t::add
()
@retval NULL on failure (such as when the same tablespace exists) */
fil_space_t
*
fil_space_create
(
...
...
storage/innobase/include/mem0mem.h
View file @
babb000a
...
...
@@ -418,104 +418,4 @@ struct mem_block_info_t {
UNIV_MEM_ALIGNMENT)
#include "mem0mem.ic"
/** A C++ wrapper class to the mem_heap_t routines, so that it can be used
as an STL allocator */
template
<
typename
T
>
class
mem_heap_allocator
{
public:
typedef
T
value_type
;
typedef
size_t
size_type
;
typedef
ptrdiff_t
difference_type
;
typedef
T
*
pointer
;
typedef
const
T
*
const_pointer
;
typedef
T
&
reference
;
typedef
const
T
&
const_reference
;
mem_heap_allocator
(
mem_heap_t
*
heap
)
:
m_heap
(
heap
)
{
}
mem_heap_allocator
(
const
mem_heap_allocator
&
other
)
:
m_heap
(
other
.
m_heap
)
{
// Do nothing
}
template
<
typename
U
>
mem_heap_allocator
(
const
mem_heap_allocator
<
U
>&
other
)
:
m_heap
(
other
.
m_heap
)
{
// Do nothing
}
~
mem_heap_allocator
()
{
m_heap
=
0
;
}
size_type
max_size
()
const
{
return
(
ULONG_MAX
/
sizeof
(
T
));
}
/** This function returns a pointer to the first element of a newly
allocated array large enough to contain n objects of type T; only the
memory is allocated, and the objects are not constructed. Moreover,
an optional pointer argument (that points to an object already
allocated by mem_heap_allocator) can be used as a hint to the
implementation about where the new memory should be allocated in
order to improve locality. */
pointer
allocate
(
size_type
n
)
{
return
(
reinterpret_cast
<
pointer
>
(
mem_heap_alloc
(
m_heap
,
n
*
sizeof
(
T
))));
}
pointer
allocate
(
size_type
n
,
const_pointer
)
{
return
allocate
(
n
);
}
void
deallocate
(
pointer
,
size_type
)
{}
pointer
address
(
reference
r
)
const
{
return
(
&
r
);
}
const_pointer
address
(
const_reference
r
)
const
{
return
(
&
r
);
}
void
construct
(
pointer
p
,
const_reference
t
)
{
new
(
reinterpret_cast
<
void
*>
(
p
))
T
(
t
);
}
void
destroy
(
pointer
p
)
{
(
reinterpret_cast
<
T
*>
(
p
))
->~
T
();
}
/** Allocators are required to supply the below template class member
which enables the possibility of obtaining a related allocator,
parametrized in terms of a different type. For example, given an
allocator type IntAllocator for objects of type int, a related
allocator type for objects of type long could be obtained using
IntAllocator::rebind<long>::other */
template
<
typename
U
>
struct
rebind
{
typedef
mem_heap_allocator
<
U
>
other
;
};
private:
mem_heap_t
*
m_heap
;
template
<
typename
U
>
friend
class
mem_heap_allocator
;
};
template
<
class
T
>
bool
operator
==
(
const
mem_heap_allocator
<
T
>&
left
,
const
mem_heap_allocator
<
T
>&
right
)
{
return
(
left
.
heap
==
right
.
heap
);
}
template
<
class
T
>
bool
operator
!=
(
const
mem_heap_allocator
<
T
>&
left
,
const
mem_heap_allocator
<
T
>&
right
)
{
return
(
left
.
heap
!=
right
.
heap
);
}
#endif
storage/innobase/include/srv0srv.h
View file @
babb000a
...
...
@@ -993,7 +993,7 @@ struct export_var_t{
ulint
innodb_system_rows_inserted
;
/*!< srv_n_system_rows_inserted */
ulint
innodb_system_rows_updated
;
/*!< srv_n_system_rows_updated */
ulint
innodb_system_rows_deleted
;
/*!< srv_n_system_rows_deleted*/
ulint
innodb_num_open_files
;
/*!< fil_
n_file_opened
*/
ulint
innodb_num_open_files
;
/*!< fil_
system_t::n_open
*/
ulint
innodb_truncated_status_writes
;
/*!< srv_truncated_status_writes */
ulint
innodb_available_undo_logs
;
/*!< srv_available_undo_logs
*/
...
...
storage/innobase/srv/srv0mon.cc
View file @
babb000a
...
...
@@ -1960,7 +1960,7 @@ srv_mon_process_existing_counter(
break
;
case
MONITOR_OVLD_N_FILE_OPENED
:
value
=
fil_
n_file_opened
;
value
=
fil_
system
.
n_open
;
break
;
case
MONITOR_OVLD_IBUF_MERGE_INSERT
:
...
...
storage/innobase/srv/srv0srv.cc
View file @
babb000a
...
...
@@ -1580,7 +1580,7 @@ srv_export_innodb_status(void)
export_vars
.
innodb_system_rows_deleted
=
srv_stats
.
n_system_rows_deleted
;
export_vars
.
innodb_num_open_files
=
fil_
n_file_opened
;
export_vars
.
innodb_num_open_files
=
fil_
system
.
n_open
;
export_vars
.
innodb_truncated_status_writes
=
srv_truncated_status_writes
;
...
...
storage/innobase/srv/srv0start.cc
View file @
babb000a
...
...
@@ -464,23 +464,16 @@ create_log_files(
const
ulint
size
=
ulint
(
srv_log_file_size
>>
srv_page_size_shift
);
logfile0
=
fil_node_create
(
logfilename
,
size
,
log_space
,
false
,
false
)
;
logfile0
=
log_space
->
add
(
logfilename
,
OS_FILE_CLOSED
,
size
,
false
,
false
)
->
name
;
ut_a
(
logfile0
);
for
(
unsigned
i
=
1
;
i
<
srv_n_log_files
;
i
++
)
{
sprintf
(
logfilename
+
dirnamelen
,
"ib_logfile%u"
,
i
);
if
(
!
fil_node_create
(
logfilename
,
size
,
log_space
,
false
,
false
))
{
ib
::
error
()
<<
"Cannot create file node for log file "
<<
logfilename
;
return
(
DB_ERROR
);
}
log_space
->
add
(
logfilename
,
OS_FILE_CLOSED
,
size
,
false
,
false
);
}
log_sys
.
log
.
create
(
srv_n_log_files
);
...
...
@@ -628,83 +621,68 @@ srv_undo_tablespace_create(
return
(
err
);
}
/*********************************************************************//**
Open an undo tablespace.
@return DB_SUCCESS or error code */
static
dberr_t
srv_undo_tablespace_open
(
/*=====================*/
const
char
*
name
,
/*!< in: tablespace file name */
ulint
space_id
)
/*!< in: tablespace id */
/** Open an undo tablespace.
@param[in] name tablespace file name
@param[in] space_id tablespace ID
@param[in] create_new_db whether undo tablespaces are being created
@return whether the tablespace was opened */
static
bool
srv_undo_tablespace_open
(
const
char
*
name
,
ulint
space_id
,
bool
create_new_db
)
{
pfs_os_file_t
fh
;
bool
ret
;
dberr_t
err
=
DB_ERROR
;
bool
success
;
char
undo_name
[
sizeof
"innodb_undo000"
];
snprintf
(
undo_name
,
sizeof
(
undo_name
),
"innodb_undo%03u"
,
static_cast
<
unsigned
>
(
space_id
));
if
(
!
srv_file_check_mode
(
name
))
{
ib
::
error
()
<<
"UNDO tablespaces must be "
<<
(
srv_read_only_mode
?
"writable"
:
"readable"
)
<<
"!"
;
return
(
DB_ERROR
);
}
fh
=
os_file_create
(
innodb_data_file_key
,
name
,
OS_FILE_OPEN_RETRY
|
OS_FILE_ON_ERROR_NO_EXIT
|
OS_FILE_ON_ERROR_SILENT
,
OS_FILE_NORMAL
,
OS_DATA_FILE
,
srv_read_only_mode
,
&
ret
);
/* If the file open was successful then load the tablespace. */
if
(
ret
)
{
os_offset_t
size
;
fil_space_t
*
space
;
size
=
os_file_get_size
(
fh
);
ut_a
(
size
!=
(
os_offset_t
)
-
1
);
innodb_data_file_key
,
name
,
OS_FILE_OPEN
|
OS_FILE_ON_ERROR_NO_EXIT
|
OS_FILE_ON_ERROR_SILENT
,
OS_FILE_AIO
,
OS_DATA_FILE
,
srv_read_only_mode
,
&
success
);
if
(
!
success
)
{
return
false
;
}
ret
=
os_file_clos
e
(
fh
);
ut_a
(
ret
);
os_offset_t
size
=
os_file_get_siz
e
(
fh
);
ut_a
(
size
!=
os_offset_t
(
-
1
)
);
/* Load the tablespace into InnoDB's internal
data structures. */
/* Load the tablespace into InnoDB's internal data structures. */
/* We set the biggest space id to the undo tablespace
because InnoDB hasn't opened any other tablespace apart
from the system tablespace. */
/* We set the biggest space id to the undo tablespace
because InnoDB hasn't opened any other tablespace apart
from the system tablespace. */
fil_set_max_space_id_if_bigger
(
space_id
);
fil_set_max_space_id_if_bigger
(
space_id
);
space
=
fil_space_create
(
undo_name
,
space_id
,
FSP_FLAGS_PAGE_SSIZE
(),
FIL_TYPE_TABLESPACE
,
NULL
);
fil_space_t
*
space
=
fil_space_create
(
undo_name
,
space_id
,
FSP_FLAGS_PAGE_SSIZE
(),
FIL_TYPE_TABLESPACE
,
NULL
);
ut_a
(
fil_validate
());
ut_a
(
space
);
ut_a
(
fil_validate
());
ut_a
(
space
);
os_offset_t
n_pages
=
size
>>
srv_page_size_shift
;
fil_node_t
*
file
=
space
->
add
(
name
,
fh
,
0
,
false
,
true
)
;
/* On 32-bit platforms, ulint is 32 bits and os_offset_t
is 64 bits. It is OK to cast the n_pages to ulint because
the unit has been scaled to pages and page number is always
32 bits. */
if
(
fil_node_create
(
name
,
(
ulint
)
n_pages
,
space
,
false
,
TRUE
))
{
mutex_enter
(
&
fil_system
.
mutex
);
err
=
DB_SUCCESS
;
if
(
create_new_db
)
{
space
->
size
=
file
->
size
=
ulint
(
size
>>
srv_page_size_shift
);
space
->
size_in_header
=
SRV_UNDO_TABLESPACE_SIZE_IN_PAGES
;
}
else
{
success
=
file
->
read_page0
(
true
);
if
(
!
success
)
{
os_file_close
(
file
->
handle
);
file
->
handle
=
OS_FILE_CLOSED
;
ut_a
(
fil_system
.
n_open
>
0
);
fil_system
.
n_open
--
;
}
}
return
(
err
);
mutex_exit
(
&
fil_system
.
mutex
);
return
success
;
}
/** Check if undo tablespaces and redo log files exist before creating a
...
...
@@ -930,12 +908,11 @@ srv_undo_tablespaces_init(bool create_new_db)
ut_a
(
undo_tablespace_ids
[
i
]
!=
0
);
ut_a
(
undo_tablespace_ids
[
i
]
!=
ULINT_UNDEFINED
);
err
=
srv_undo_tablespace_open
(
name
,
undo_tablespace_ids
[
i
]);
if
(
err
!=
DB_SUCCESS
)
{
if
(
!
srv_undo_tablespace_open
(
name
,
undo_tablespace_ids
[
i
],
create_new_db
))
{
ib
::
error
()
<<
"Unable to open undo tablespace '"
<<
name
<<
"'."
;
return
(
err
)
;
return
DB_ERROR
;
}
prev_space_id
=
undo_tablespace_ids
[
i
];
...
...
@@ -960,9 +937,8 @@ srv_undo_tablespaces_init(bool create_new_db)
name
,
sizeof
(
name
),
"%s%cundo%03zu"
,
srv_undo_dir
,
OS_PATH_SEPARATOR
,
i
);
err
=
srv_undo_tablespace_open
(
name
,
i
);
if
(
err
!=
DB_SUCCESS
)
{
if
(
!
srv_undo_tablespace_open
(
name
,
i
,
create_new_db
))
{
err
=
DB_ERROR
;
break
;
}
...
...
@@ -1863,10 +1839,8 @@ dberr_t srv_start(bool create_new_db)
for
(
unsigned
j
=
0
;
j
<
srv_n_log_files_found
;
j
++
)
{
sprintf
(
logfilename
+
dirnamelen
,
"ib_logfile%u"
,
j
);
if
(
!
fil_node_create
(
logfilename
,
size
,
log_space
,
false
,
false
))
{
return
(
srv_init_abort
(
DB_ERROR
));
}
log_space
->
add
(
logfilename
,
OS_FILE_CLOSED
,
size
,
false
,
false
);
}
log_sys
.
log
.
create
(
srv_n_log_files_found
);
...
...
storage/innobase/trx/trx0trx.cc
View file @
babb000a
...
...
@@ -779,9 +779,7 @@ trx_lists_init_at_db_start()
evenly distributed between 0 and innodb_undo_logs-1
@return persistent rollback segment
@retval NULL if innodb_read_only */
static
trx_rseg_t
*
trx_assign_rseg_low
()
static
trx_rseg_t
*
trx_assign_rseg_low
()
{
if
(
srv_read_only_mode
)
{
ut_ad
(
srv_undo_logs
==
ULONG_UNDEFINED
);
...
...
@@ -832,8 +830,8 @@ trx_assign_rseg_low()
ut_ad
(
rseg
->
is_persistent
());
if
(
rseg
->
space
!=
fil_system
.
sys_space
)
{
ut_ad
(
srv_undo_tablespaces
>
1
);
if
(
rseg
->
skip_allocation
)
{
if
(
rseg
->
skip_allocation
||
!
srv_undo_tablespaces
)
{
continue
;
}
}
else
if
(
trx_rseg_t
*
next
...
...
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