notes.h/c: Allow combine_notes functions to remove notes

Allow combine_notes functions to request that a note be removed, by setting
the resulting note SHA1 to null_sha1 (0000000...).

For consistency, also teach note_tree_insert() to skip insertion of an empty
note (a note with entry->val_sha1 equal to null_sha1) when there is no note
to combine it with.

In general, an empty note (null_sha1) is treated identically to no note at
all, but when adding an empty note where there already exists a non-empty
note, we allow the combine_notes function to potentially record a new/changed
note. Document this behaviour, and clearly specify how combine_notes functions
are expected to handle null_sha1 in input.

Before this patch, storing null_sha1s in the notes tree were silently allowed,
causing an invalid notes tree (referring to blobs with null_sha1) to be
produced by write_notes_tree().

Signed-off-by: Johan Herland <johan@herland.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
This commit is contained in:
Johan Herland
2010-11-09 22:49:41 +01:00
committed by Junio C Hamano
parent a5cdebea55
commit e2656c82fd
2 changed files with 26 additions and 2 deletions

16
notes.h
View File

@ -12,7 +12,10 @@
* resulting SHA1 into the first SHA1 argument (cur_sha1). A non-zero return
* value indicates failure.
*
* The two given SHA1s must both be non-NULL and different from each other.
* The two given SHA1s shall both be non-NULL and different from each other.
* Either of them (but not both) may be == null_sha1, which indicates an
* empty/non-existent note. If the resulting SHA1 (cur_sha1) is == null_sha1,
* the note will be removed from the notes tree.
*
* The default combine_notes function (you get this when passing NULL) is
* combine_notes_concatenate(), which appends the contents of the new note to
@ -90,6 +93,17 @@ void init_notes(struct notes_tree *t, const char *notes_ref,
/*
* Add the given note object to the given notes_tree structure
*
* If there already exists a note for the given object_sha1, the given
* combine_notes function is invoked to break the tie. If not given (i.e.
* combine_notes == NULL), the default combine_notes function for the given
* notes_tree is used.
*
* Passing note_sha1 == null_sha1 indicates the addition of an
* empty/non-existent note. This is a (potentially expensive) no-op unless
* there already exists a note for the given object_sha1, AND combining that
* note with the empty note (using the given combine_notes function) results
* in a new/changed note.
*
* IMPORTANT: The changes made by add_note() to the given notes_tree structure
* are not persistent until a subsequent call to write_notes_tree() returns
* zero.