core: Ensure we delete duplicate files in a transaction
If multiple files have the same hash, we need to ensure we're not overwriting other tempfiles in the same transaction. Instead just delete them, since we know they're in the repo.
This commit is contained in:
parent
9910c0ddf4
commit
ebe35dbefe
|
|
@ -887,7 +887,7 @@ ostree_create_temp_file_from_input (GFile *dir,
|
|||
g_free (possible_name);
|
||||
possible_name = subst_xxxxxx (tmp_name->str);
|
||||
g_clear_object (&possible_file);
|
||||
possible_file = ot_gfile_new_for_path (possible_name);
|
||||
possible_file = g_file_get_child (dir, possible_name);
|
||||
|
||||
if (!ostree_create_file_from_input (possible_file, finfo, xattrs, input,
|
||||
objtype,
|
||||
|
|
|
|||
|
|
@ -755,6 +755,39 @@ stage_object_impl (OstreeRepo *self,
|
|||
GCancellable *cancellable,
|
||||
GError **error);
|
||||
|
||||
static gboolean
|
||||
insert_into_transaction (OstreeRepo *self,
|
||||
const char *checksum,
|
||||
OstreeObjectType objtype,
|
||||
GFile *tempfile_path,
|
||||
GError **error)
|
||||
{
|
||||
gboolean ret = FALSE;
|
||||
OstreeRepoPrivate *priv = GET_PRIVATE (self);
|
||||
char *key;
|
||||
|
||||
key = create_checksum_and_objtype (checksum, objtype);
|
||||
|
||||
if (g_hash_table_lookup (priv->pending_transaction_tmpfiles, key))
|
||||
{
|
||||
if (unlink (ot_gfile_get_path_cached (tempfile_path)) < 0)
|
||||
{
|
||||
ot_util_set_error_from_errno (error, errno);
|
||||
goto out;
|
||||
}
|
||||
g_free (key);
|
||||
}
|
||||
else
|
||||
{
|
||||
g_hash_table_insert (priv->pending_transaction_tmpfiles,
|
||||
key, g_strdup (ot_gfile_get_basename_cached (tempfile_path)));
|
||||
}
|
||||
|
||||
ret = TRUE;
|
||||
out:
|
||||
return ret;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
impl_stage_archive_file_object_from_raw (OstreeRepo *self,
|
||||
GFileInfo *file_info,
|
||||
|
|
@ -828,12 +861,13 @@ impl_stage_archive_file_object_from_raw (OstreeRepo *self,
|
|||
else
|
||||
actual_checksum = g_checksum_get_string (ret_checksum);
|
||||
|
||||
g_hash_table_insert (priv->pending_transaction_tmpfiles,
|
||||
create_checksum_and_objtype (actual_checksum, OSTREE_OBJECT_TYPE_ARCHIVED_FILE_CONTENT),
|
||||
g_strdup (ot_gfile_get_basename_cached (content_temp_file)));
|
||||
g_hash_table_insert (priv->pending_transaction_tmpfiles,
|
||||
create_checksum_and_objtype (actual_checksum, OSTREE_OBJECT_TYPE_ARCHIVED_FILE_META),
|
||||
g_strdup (ot_gfile_get_basename_cached (meta_temp_file)));
|
||||
if (!insert_into_transaction (self, actual_checksum, OSTREE_OBJECT_TYPE_ARCHIVED_FILE_CONTENT,
|
||||
content_temp_file, error))
|
||||
goto out;
|
||||
|
||||
if (!insert_into_transaction (self, actual_checksum, OSTREE_OBJECT_TYPE_ARCHIVED_FILE_META,
|
||||
meta_temp_file, error))
|
||||
goto out;
|
||||
|
||||
ret = TRUE;
|
||||
ot_transfer_out_value (out_checksum, &ret_checksum);
|
||||
|
|
@ -910,7 +944,7 @@ stage_object_impl (OstreeRepo *self,
|
|||
else
|
||||
{
|
||||
if (!ostree_create_temp_file_from_input (priv->transaction_dir,
|
||||
"store-tmp-", NULL,
|
||||
ostree_object_type_to_string (objtype), NULL,
|
||||
file_info, xattrs, input,
|
||||
objtype,
|
||||
&temp_file,
|
||||
|
|
@ -933,9 +967,9 @@ stage_object_impl (OstreeRepo *self,
|
|||
}
|
||||
}
|
||||
|
||||
g_hash_table_insert (priv->pending_transaction_tmpfiles,
|
||||
create_checksum_and_objtype (actual_checksum, objtype),
|
||||
g_strdup (ot_gfile_get_basename_cached (temp_file)));
|
||||
if (!insert_into_transaction (self, actual_checksum, objtype,
|
||||
temp_file, error))
|
||||
goto out;
|
||||
g_clear_object (&temp_file);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue