summaryrefslogtreecommitdiff
path: root/src/ostree/ot-builtin-prune.c
diff options
context:
space:
mode:
authorColin Walters <walters@verbum.org>2012-11-16 12:26:29 -0500
committerColin Walters <walters@verbum.org>2012-11-16 12:50:13 -0500
commit7861b98673ffcafbbe0a5fc83f5a4bf18e881b1a (patch)
treeb23e39e2bb69863050a48000cfd85d5bb99e1720 /src/ostree/ot-builtin-prune.c
parent51b1dd7cbd1368e76cb0fcb71c4ea067293b36f1 (diff)
downloadostree-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.c98
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: