diff options
author | Colin Walters <walters@verbum.org> | 2012-11-16 12:26:29 -0500 |
---|---|---|
committer | Colin Walters <walters@verbum.org> | 2012-11-16 12:50:13 -0500 |
commit | 7861b98673ffcafbbe0a5fc83f5a4bf18e881b1a (patch) | |
tree | b23e39e2bb69863050a48000cfd85d5bb99e1720 /src/ostree/ot-builtin-prune.c | |
parent | 51b1dd7cbd1368e76cb0fcb71c4ea067293b36f1 (diff) | |
download | ostree-7861b98673ffcafbbe0a5fc83f5a4bf18e881b1a.tar.gz |
prune: Add option to traverse refs only
The previous code (unintentionally) only traversed from refs; so data
only reachable from previous commits would be deleted. That shouldn't
be the default, but we do want to offer it as an option.
So add a --refs-only option.
Diffstat (limited to 'src/ostree/ot-builtin-prune.c')
-rw-r--r-- | src/ostree/ot-builtin-prune.c | 98 |
1 files changed, 65 insertions, 33 deletions
diff --git a/src/ostree/ot-builtin-prune.c b/src/ostree/ot-builtin-prune.c index 5e09749f..693160ec 100644 --- a/src/ostree/ot-builtin-prune.c +++ b/src/ostree/ot-builtin-prune.c @@ -29,27 +29,31 @@ #include <glib/gprintf.h> static gboolean opt_no_prune; -static int opt_depth = -1; +static gint opt_depth = -1; +static gboolean opt_refs_only; static GOptionEntry options[] = { - { "depth", 0, 0, G_OPTION_ARG_INT, &opt_depth, "Only traverse commit objects by this count", NULL }, { "no-prune", 0, 0, G_OPTION_ARG_NONE, &opt_no_prune, "Only display unreachable objects; don't delete", NULL }, + { "refs-only", 0, 0, G_OPTION_ARG_NONE, &opt_refs_only, "Only compute reachability via refs", NULL }, + { "depth", 0, 0, G_OPTION_ARG_INT, &opt_depth, "Only traverse DEPTH parents for each commit (default: -1=infinite)", "DEPTH" }, { NULL } }; typedef struct { OstreeRepo *repo; GHashTable *reachable; - guint n_reachable; - guint n_unreachable; + guint n_reachable_meta; + guint n_reachable_content; + guint n_unreachable_meta; + guint n_unreachable_content; } OtPruneData; static gboolean -prune_loose_object (OtPruneData *data, - const char *checksum, - OstreeObjectType objtype, - GCancellable *cancellable, - GError **error) +maybe_prune_loose_object (OtPruneData *data, + const char *checksum, + OstreeObjectType objtype, + GCancellable *cancellable, + GError **error) { gboolean ret = FALSE; ot_lvariant GVariant *key = NULL; @@ -66,10 +70,18 @@ prune_loose_object (OtPruneData *data, if (!ot_gfile_unlink (objf, cancellable, error)) goto out; } - data->n_unreachable++; + if (OSTREE_OBJECT_TYPE_IS_META (objtype)) + data->n_unreachable_meta++; + else + data->n_unreachable_content++; } else - data->n_reachable++; + { + if (OSTREE_OBJECT_TYPE_IS_META (objtype)) + data->n_reachable_meta++; + else + data->n_reachable_content++; + } ret = TRUE; out: @@ -103,28 +115,47 @@ ostree_builtin_prune (int argc, char **argv, GFile *repo_path, GError **error) data.repo = repo; data.reachable = ostree_traverse_new_reachable (); - data.n_reachable = 0; - data.n_unreachable = 0; - - if (!ostree_repo_list_all_refs (repo, &all_refs, cancellable, error)) - goto out; - g_hash_table_iter_init (&hash_iter, all_refs); - - while (g_hash_table_iter_next (&hash_iter, &key, &value)) + if (opt_refs_only) { - const char *checksum = value; - - // g_print ("Computing reachable, currently %u total, from %s: %s\n", g_hash_table_size (data.reachable), name, checksum); - if (!ostree_traverse_commit (repo, checksum, opt_depth, data.reachable, cancellable, error)) + if (!ostree_repo_list_all_refs (repo, &all_refs, cancellable, error)) goto out; + + g_hash_table_iter_init (&hash_iter, all_refs); + + while (g_hash_table_iter_next (&hash_iter, &key, &value)) + { + const char *checksum = value; + + // g_print ("Computing reachable, currently %u total, from %s: %s\n", g_hash_table_size (data.reachable), name, checksum); + if (!ostree_traverse_commit (repo, checksum, opt_depth, data.reachable, cancellable, error)) + goto out; + } } if (!ostree_repo_list_objects (repo, OSTREE_REPO_LIST_OBJECTS_ALL, &objects, cancellable, error)) goto out; - g_hash_table_iter_init (&hash_iter, objects); + if (!opt_refs_only) + { + g_hash_table_iter_init (&hash_iter, objects); + while (g_hash_table_iter_next (&hash_iter, &key, &value)) + { + GVariant *serialized_key = key; + const char *checksum; + OstreeObjectType objtype; + ostree_object_name_deserialize (serialized_key, &checksum, &objtype); + + if (objtype != OSTREE_OBJECT_TYPE_COMMIT) + continue; + + if (!ostree_traverse_commit (repo, checksum, opt_depth, data.reachable, cancellable, error)) + goto out; + } + } + + g_hash_table_iter_init (&hash_iter, objects); while (g_hash_table_iter_next (&hash_iter, &key, &value)) { GVariant *serialized_key = key; @@ -132,20 +163,21 @@ ostree_builtin_prune (int argc, char **argv, GFile *repo_path, GError **error) const char *checksum; OstreeObjectType objtype; gboolean is_loose; - + ostree_object_name_deserialize (serialized_key, &checksum, &objtype); - g_variant_get_child (objdata, 0, "b", &is_loose); - if (is_loose) - { - if (!prune_loose_object (&data, checksum, objtype, cancellable, error)) - goto out; - } + if (!is_loose) + continue; + + if (!maybe_prune_loose_object (&data, checksum, objtype, cancellable, error)) + goto out; } - g_print ("Total reachable: %u\n", data.n_reachable); - g_print ("Total unreachable: %u\n", data.n_unreachable); + g_print ("Total reachable: %u meta, %u content\n", + data.n_reachable_meta, data.n_reachable_content); + g_print ("Total unreachable: %u meta, %u content\n", + data.n_unreachable_meta, data.n_unreachable_content); ret = TRUE; out: |