mirror of
https://github.com/ostreedev/ostree.git
synced 2025-03-14 04:59:00 +03:00
pull: Check free space when pulling deltas
Computing download/storage size for `archive` pulls is hard; there's `OSTREE_REPO_COMMIT_MODIFIER_FLAGS_GENERATE_SIZES` which was from a pre-static-deltas effort by Endless, but we aren't currently making use of this much. Static deltas were designed to solve this problem; we have the total uncompressed size. Let's check free space before doing a delta pull. Related: https://github.com/ostreedev/ostree/issues/962 Closes: #963 Approved by: jlebon
This commit is contained in:
parent
54db9ecab3
commit
4796cd0454
@ -49,6 +49,7 @@
|
||||
#endif /* OSTREE_ENABLE_EXPERIMENTAL_API */
|
||||
|
||||
#include <gio/gunixinputstream.h>
|
||||
#include <sys/statvfs.h>
|
||||
|
||||
#define OSTREE_REPO_PULL_CONTENT_PRIORITY (OSTREE_FETCHER_DEFAULT_PRIORITY)
|
||||
#define OSTREE_REPO_PULL_METADATA_PRIORITY (OSTREE_REPO_PULL_CONTENT_PRIORITY - 100)
|
||||
@ -1814,6 +1815,11 @@ process_one_static_delta (OtPullData *pull_data,
|
||||
headers = g_variant_get_child_value (delta_superblock, 6);
|
||||
fallback_objects = g_variant_get_child_value (delta_superblock, 7);
|
||||
|
||||
/* Gather free space so we can do a check below */
|
||||
struct statvfs stvfsbuf;
|
||||
if (TEMP_FAILURE_RETRY (fstatvfs (pull_data->repo->repo_dir_fd, &stvfsbuf)) < 0)
|
||||
return glnx_throw_errno_prefix (error, "fstatvfs");
|
||||
|
||||
/* First process the fallbacks */
|
||||
n = g_variant_n_children (fallback_objects);
|
||||
for (i = 0; i < n; i++)
|
||||
@ -1982,6 +1988,21 @@ process_one_static_delta (OtPullData *pull_data,
|
||||
}
|
||||
}
|
||||
|
||||
/* The free space check is here since at this point we've parsed the delta not
|
||||
* only the total size of the parts, but also whether or not we already have
|
||||
* them. TODO: Ideally this free space check would be above, but we'd have to
|
||||
* walk everything twice and keep track of state.
|
||||
*/
|
||||
const guint64 delta_required_blocks = (pull_data->total_deltapart_usize / stvfsbuf.f_bsize);
|
||||
if (delta_required_blocks > stvfsbuf.f_bfree)
|
||||
{
|
||||
g_autofree char *formatted_required = g_format_size (pull_data->total_deltapart_usize);
|
||||
g_autofree char *formatted_avail = g_format_size (((guint64)stvfsbuf.f_bsize) * stvfsbuf.f_bfree);
|
||||
glnx_throw (error, "Delta requires %s free space, but only %s available",
|
||||
formatted_required, formatted_avail);
|
||||
goto out;
|
||||
}
|
||||
|
||||
ret = TRUE;
|
||||
out:
|
||||
return ret;
|
||||
|
Loading…
x
Reference in New Issue
Block a user