1
0
mirror of https://github.com/MariaDB/server.git synced 2026-10-23 18:49:29 +03:00

Copy 4 MiB at a time

This commit is contained in:
Marko Mäkelä
2026-10-22 14:09:27 +03:00
parent 2947a7fc27
commit 4429caed95
3 changed files with 33 additions and 37 deletions

View File

@@ -95,7 +95,11 @@ static ssize_t pread_write(backup::handle in_fd, backup_fd out_fd,
#if SIZEOF_SIZE_T < 8
size_t size{65536};
#else
constexpr size_t max_size{1 << 20};
/*
Copy up to this much at a time. The copying of InnoDB data files
is additionally limited by fil_space_t::BACKUP_BATCH_SIZE.
*/
constexpr size_t max_size{4 << 20};
/* An integer multiple of 4096 bytes, up to max_size */
size_t size{count >= max_size ? max_size : (size_t(count) + 4095) & ~4095};
#endif

View File

@@ -662,6 +662,10 @@ public:
log_dst, log_dst, tracked, &target
};
ut_ad(ctx.BACKUP_BATCH_SIZE);
ut_ad(ut_is_2pow(ctx.BACKUP_BATCH_SIZE));
ut_ad(ctx.BACKUP_BATCH_SIZE <= ctx.BACKUP_BATCH_SIZE_MAX);
/* Collect all tablespaces that have been created before our
start checkpoint. Newer tablespaces will be recovered by the
innodb_log_archive=ON recovery.
@@ -2237,22 +2241,24 @@ int InnoDB_backup::copy_file_shortcut_try(int dst, fil_node_t *node,
# if 0
return 1; // work around https://github.com/rr-debugger/rr/issues/4059
# endif
const uint32_t BACKUP_BATCH_SIZE{innodb_backup.ctx.BACKUP_BATCH_SIZE};
const uint32_t BATCH{innodb_backup.ctx.BACKUP_BATCH_SIZE};
for (uint32_t page{0};;)
{
while (page < limit)
{
start+= BACKUP_BATCH_SIZE;
const uint32_t end_page{(start & ~(BATCH - 1)) + BATCH};
const uint32_t last{std::min(limit, page + (end_page - start))};
start+= last - page;
int err;
buf_page_t **end= backup_batch_start(blocks, node->space, start);
buf_page_t **end= backup_batch_start(blocks, node->space, end_page);
if (end)
{
const uint64_t o{uint64_t{page} * page_size};
page= std::min(limit, page + BACKUP_BATCH_SIZE);
/* TODO: avoid copying freed page ranges, or pages that were
allocated after the backup started */
err= copy_file_shortcut(node->handle, dst,
o, uint64_t{page} * page_size);
uint64_t{page} * page_size,
uint64_t{last} * page_size);
page= last;
}
else
{
@@ -2404,28 +2410,21 @@ int InnoDB_backup::backup(IF_WIN(const char *,int) target, fil_node_t *node,
if (err == 1)
#endif
{
const uint32_t BACKUP_BATCH_SIZE{innodb_backup.ctx.BACKUP_BATCH_SIZE};
const uint32_t BATCH{innodb_backup.ctx.BACKUP_BATCH_SIZE};
for (uint32_t page{0};;)
{
while (page < limit)
{
const uint32_t end_page{(start & ~(BATCH - 1)) + BATCH};
const uint32_t last{std::min(limit, page + (end_page - start))};
start+= last - page;
/* TODO: avoid copying freed page ranges, or pages that were
allocated after the backup started */
start+= BACKUP_BATCH_SIZE;
const uint64_t o{uint64_t{page} * page_size};
const uint32_t end_page{std::min(limit, page + BACKUP_BATCH_SIZE)};
#ifdef POSIX_FADV_WILLNEED
std::ignore= posix_fadvise(node->handle, o,
uint64_t{end_page} * page_size,
POSIX_FADV_WILLNEED);
#endif
buf_page_t **end= backup_batch_start(blocks, node->space, start);
buf_page_t **end= backup_batch_start(blocks, node->space, end_page);
if (end)
{
page= end_page;
err=
backup::copy(node->handle, f, o, uint64_t{page} * page_size);
}
err= backup::copy(node->handle, f,
uint64_t{page} * page_size,
uint64_t{last} * page_size);
else
{
end= blocks;
@@ -2434,6 +2433,7 @@ int InnoDB_backup::backup(IF_WIN(const char *,int) target, fil_node_t *node,
backup_batch_stop(node->space, blocks, end);
if (err)
break;
page= last;
}
if (final_limit != 0 && !err && page == buf_dblwr.begin())
@@ -2505,25 +2505,17 @@ int InnoDB_backup::stream(backup_fd stream, fil_node_t *node, const char *name,
int err{0};
uint32_t page{0};
const uint32_t BACKUP_BATCH_SIZE{innodb_backup.ctx.BACKUP_BATCH_SIZE};
loop:
/* TODO: avoid copying freed page ranges, or pages that were
allocated after the backup started */
do
{
buf_page_t *blocks[context::BACKUP_BATCH_SIZE_MAX], **end= blocks;
const uint32_t last{std::min(limit, page + BACKUP_BATCH_SIZE)};
#ifdef POSIX_FADV_WILLNEED
std::ignore= posix_fadvise(node->handle,
uint64_t{page} * page_size,
uint64_t{last} * page_size,
POSIX_FADV_WILLNEED);
#endif
{
const uint32_t end_page{start + BACKUP_BATCH_SIZE};
end= backup_batch_start(end, node->space, end_page);
start= end_page;
}
buf_page_t *blocks[context::BACKUP_BATCH_SIZE_MAX];
const uint32_t BATCH{innodb_backup.ctx.BACKUP_BATCH_SIZE};
const uint32_t end_page{(start & ~(BATCH - 1)) + BATCH};
const uint32_t last{std::min(limit, page + (end_page - start))};
start+= last - page;
buf_page_t **end= backup_batch_start(blocks, node->space, end_page);
if (end)
{
if (page ||

View File

@@ -1094,7 +1094,7 @@ public:
{ return backup_end.load(std::memory_order_acquire); }
/** the size of a backup::copy() batch in bytes */
static constexpr uint32_t BACKUP_BATCH_SIZE{1 << 20};
static constexpr uint32_t BACKUP_BATCH_SIZE{4 << 20};
/** @return the size of a backup::copy() batch in pages */
static uint32_t backup_batch_size() noexcept