core: Add asynchronous checksum API, use it in checksum builtin
This commit is contained in:
parent
8af4a62665
commit
b0b0ffcd61
|
|
@ -320,6 +320,9 @@ ostree_checksum_file (GFile *f,
|
||||||
GFileInfo *file_info = NULL;
|
GFileInfo *file_info = NULL;
|
||||||
GChecksum *ret_checksum = NULL;
|
GChecksum *ret_checksum = NULL;
|
||||||
|
|
||||||
|
if (g_cancellable_set_error_if_cancelled (cancellable, error))
|
||||||
|
return NULL;
|
||||||
|
|
||||||
file_info = g_file_query_info (f, OSTREE_GIO_FAST_QUERYINFO,
|
file_info = g_file_query_info (f, OSTREE_GIO_FAST_QUERYINFO,
|
||||||
G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS,
|
G_FILE_QUERY_INFO_NOFOLLOW_SYMLINKS,
|
||||||
cancellable, error);
|
cancellable, error);
|
||||||
|
|
@ -345,6 +348,82 @@ ostree_checksum_file (GFile *f,
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
GFile *f;
|
||||||
|
OstreeObjectType objtype;
|
||||||
|
GChecksum *checksum;
|
||||||
|
} ChecksumFileAsyncData;
|
||||||
|
|
||||||
|
static void
|
||||||
|
checksum_file_async_thread (GSimpleAsyncResult *res,
|
||||||
|
GObject *object,
|
||||||
|
GCancellable *cancellable)
|
||||||
|
{
|
||||||
|
GError *error = NULL;
|
||||||
|
ChecksumFileAsyncData *data;
|
||||||
|
GChecksum *checksum = NULL;
|
||||||
|
|
||||||
|
data = g_simple_async_result_get_op_res_gpointer (res);
|
||||||
|
if (!ostree_checksum_file (data->f, data->objtype, &checksum, cancellable, &error))
|
||||||
|
g_simple_async_result_take_error (res, error);
|
||||||
|
else
|
||||||
|
data->checksum = checksum;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
checksum_file_async_data_free (gpointer datap)
|
||||||
|
{
|
||||||
|
ChecksumFileAsyncData *data = datap;
|
||||||
|
|
||||||
|
g_object_unref (data->f);
|
||||||
|
if (data->checksum)
|
||||||
|
g_checksum_free (data->checksum);
|
||||||
|
g_free (data);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
ostree_checksum_file_async (GFile *f,
|
||||||
|
OstreeObjectType objtype,
|
||||||
|
int io_priority,
|
||||||
|
GCancellable *cancellable,
|
||||||
|
GAsyncReadyCallback callback,
|
||||||
|
gpointer user_data)
|
||||||
|
{
|
||||||
|
GSimpleAsyncResult *res;
|
||||||
|
ChecksumFileAsyncData *data;
|
||||||
|
|
||||||
|
data = g_new0 (ChecksumFileAsyncData, 1);
|
||||||
|
data->f = g_object_ref (f);
|
||||||
|
data->objtype = objtype;
|
||||||
|
|
||||||
|
res = g_simple_async_result_new (G_OBJECT (f), callback, user_data, ostree_checksum_file_async);
|
||||||
|
g_simple_async_result_set_op_res_gpointer (res, data, (GDestroyNotify)checksum_file_async_data_free);
|
||||||
|
|
||||||
|
g_simple_async_result_run_in_thread (res, checksum_file_async_thread, io_priority, cancellable);
|
||||||
|
g_object_unref (res);
|
||||||
|
}
|
||||||
|
|
||||||
|
gboolean
|
||||||
|
ostree_checksum_file_async_finish (GFile *f,
|
||||||
|
GAsyncResult *result,
|
||||||
|
GChecksum **out_checksum,
|
||||||
|
GError **error)
|
||||||
|
{
|
||||||
|
GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (result);
|
||||||
|
ChecksumFileAsyncData *data;
|
||||||
|
|
||||||
|
g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == ostree_checksum_file_async);
|
||||||
|
|
||||||
|
if (g_simple_async_result_propagate_error (simple, error))
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
data = g_simple_async_result_get_op_res_gpointer (simple);
|
||||||
|
/* Transfer ownership */
|
||||||
|
*out_checksum = data->checksum;
|
||||||
|
data->checksum = NULL;
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
gboolean
|
gboolean
|
||||||
ostree_get_directory_metadata (GFile *dir,
|
ostree_get_directory_metadata (GFile *dir,
|
||||||
GFileInfo *dir_info,
|
GFileInfo *dir_info,
|
||||||
|
|
@ -912,6 +991,3 @@ ostree_unpack_object (GFile *file,
|
||||||
else
|
else
|
||||||
return unpack_file (file, dest, out_checksum, error);
|
return unpack_file (file, dest, out_checksum, error);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -116,6 +116,18 @@ gboolean ostree_checksum_file (GFile *f,
|
||||||
GCancellable *cancellable,
|
GCancellable *cancellable,
|
||||||
GError **error);
|
GError **error);
|
||||||
|
|
||||||
|
void ostree_checksum_file_async (GFile *f,
|
||||||
|
OstreeObjectType objtype,
|
||||||
|
int io_priority,
|
||||||
|
GCancellable *cancellable,
|
||||||
|
GAsyncReadyCallback callback,
|
||||||
|
gpointer user_data);
|
||||||
|
|
||||||
|
gboolean ostree_checksum_file_async_finish (GFile *f,
|
||||||
|
GAsyncResult *result,
|
||||||
|
GChecksum **out_checksum,
|
||||||
|
GError **error);
|
||||||
|
|
||||||
gboolean ostree_get_directory_metadata (GFile *dir,
|
gboolean ostree_get_directory_metadata (GFile *dir,
|
||||||
GFileInfo *dir_info,
|
GFileInfo *dir_info,
|
||||||
GVariant **out_metadata,
|
GVariant **out_metadata,
|
||||||
|
|
|
||||||
|
|
@ -31,13 +31,36 @@ static GOptionEntry options[] = {
|
||||||
{ NULL }
|
{ NULL }
|
||||||
};
|
};
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
GError **error;
|
||||||
|
GMainLoop *loop;
|
||||||
|
} AsyncChecksumData;
|
||||||
|
|
||||||
|
static void
|
||||||
|
on_checksum_received (GObject *obj,
|
||||||
|
GAsyncResult *result,
|
||||||
|
gpointer user_data)
|
||||||
|
{
|
||||||
|
GChecksum *checksum = NULL;
|
||||||
|
AsyncChecksumData *data = user_data;
|
||||||
|
|
||||||
|
if (!ostree_checksum_file_async_finish ((GFile*)obj, result, &checksum, data->error))
|
||||||
|
return;
|
||||||
|
|
||||||
|
g_print ("%s\n", g_checksum_get_string (checksum));
|
||||||
|
|
||||||
|
g_checksum_free (checksum);
|
||||||
|
|
||||||
|
g_main_loop_quit (data->loop);
|
||||||
|
}
|
||||||
|
|
||||||
gboolean
|
gboolean
|
||||||
ostree_builtin_checksum (int argc, char **argv, const char *repo_path, GError **error)
|
ostree_builtin_checksum (int argc, char **argv, const char *repo_path, GError **error)
|
||||||
{
|
{
|
||||||
GOptionContext *context;
|
GOptionContext *context;
|
||||||
gboolean ret = FALSE;
|
gboolean ret = FALSE;
|
||||||
GChecksum *checksum = NULL;
|
|
||||||
GFile *f = NULL;
|
GFile *f = NULL;
|
||||||
|
AsyncChecksumData data;
|
||||||
|
|
||||||
context = g_option_context_new ("FILENAME - Checksum a file or directory");
|
context = g_option_context_new ("FILENAME - Checksum a file or directory");
|
||||||
g_option_context_add_main_entries (context, options, NULL);
|
g_option_context_add_main_entries (context, options, NULL);
|
||||||
|
|
@ -54,15 +77,16 @@ ostree_builtin_checksum (int argc, char **argv, const char *repo_path, GError **
|
||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!ostree_checksum_file (f, OSTREE_OBJECT_TYPE_FILE, &checksum, NULL, error))
|
data.loop = g_main_loop_new (NULL, FALSE);
|
||||||
goto out;
|
data.error = error;
|
||||||
|
ostree_checksum_file_async (f, OSTREE_OBJECT_TYPE_FILE, G_PRIORITY_DEFAULT, NULL, on_checksum_received, &data);
|
||||||
|
|
||||||
|
g_main_loop_run (data.loop);
|
||||||
|
|
||||||
g_print ("%s\n", g_checksum_get_string (checksum));
|
|
||||||
|
|
||||||
ret = TRUE;
|
ret = TRUE;
|
||||||
out:
|
out:
|
||||||
if (checksum)
|
if (data.loop)
|
||||||
g_checksum_free (checksum);
|
g_main_loop_unref (data.loop);
|
||||||
g_clear_object (&f);
|
g_clear_object (&f);
|
||||||
if (context)
|
if (context)
|
||||||
g_option_context_free (context);
|
g_option_context_free (context);
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue