refs.c: change ref_transaction_create to do error checking and return status
Do basic error checking in ref_transaction_create() and make it return non-zero on error. Update all callers to check the result of ref_transaction_create(). There are currently no conditions in _create that will return error but there will be in the future. Add an err argument that will be updated on failure. Signed-off-by: Ronnie Sahlberg <sahlberg@google.com> Reviewed-by: Michael Haggerty <mhagger@alum.mit.edu> Signed-off-by: Jonathan Nieder <jrnieder@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
Ronnie Sahlberg committed
Apr 16, 2014 at 15:26 UTC
b416af5bcdca3ac8426220f09efbfca2f1bec6e0
3 files changed
+56
-14
builtin/update-ref.c
+3
-1
@@ -226,7 +226,9 @@ static const char *parse_cmd_create(struct strbuf *input, const char *next)
226
if (*next != line_termination)
227
die("create %s: extra input: %s", refname, next);
228
229
- ref_transaction_create(transaction, refname, new_sha1, update_flags);
229
+ if (ref_transaction_create(transaction, refname, new_sha1,
230
+ update_flags, &err))
231
+ die("%s", err.buf);
232
233
update_flags = 0;
234
free(refname);
refs.c
+12
-6
@@ -3449,18 +3449,24 @@ int ref_transaction_update(struct ref_transaction *transaction,
3449
return 0;
3450
}
3451
3452
-void ref_transaction_create(struct ref_transaction *transaction,
3453
- const char *refname,
3454
- const unsigned char *new_sha1,
3455
- int flags)
3452
+int ref_transaction_create(struct ref_transaction *transaction,
3453
+ const char *refname,
3454
+ const unsigned char *new_sha1,
3455
+ int flags,
3456
+ struct strbuf *err)
3457
{
3457
- struct ref_update *update = add_update(transaction, refname);
3458
+ struct ref_update *update;
3459
+
3460
+ if (!new_sha1 || is_null_sha1(new_sha1))
3461
+ die("BUG: create ref with null new_sha1");
3462
+
3463
+ update = add_update(transaction, refname);
3464
3459
- assert(!is_null_sha1(new_sha1));
3465
hashcpy(update->new_sha1, new_sha1);
3466
hashclr(update->old_sha1);
3467
update->flags = flags;
3468
update->have_old = 1;
3469
+ return 0;
3470
}
3471
3472
void ref_transaction_delete(struct ref_transaction *transaction,
refs.h
+41
-7
@@ -10,6 +10,38 @@ struct ref_lock {
10
int force_write;
11
};
12
13
+/*
14
+ * A ref_transaction represents a collection of ref updates
15
+ * that should succeed or fail together.
16
+ *
17
+ * Calling sequence
18
+ * ----------------
19
+ * - Allocate and initialize a `struct ref_transaction` by calling
20
+ * `ref_transaction_begin()`.
21
+ *
22
+ * - List intended ref updates by calling functions like
23
+ * `ref_transaction_update()` and `ref_transaction_create()`.
24
+ *
25
+ * - Call `ref_transaction_commit()` to execute the transaction.
26
+ * If this succeeds, the ref updates will have taken place and
27
+ * the transaction cannot be rolled back.
28
+ *
29
+ * - At any time call `ref_transaction_free()` to discard the
30
+ * transaction and free associated resources. In particular,
31
+ * this rolls back the transaction if it has not been
32
+ * successfully committed.
33
+ *
34
+ * Error handling
35
+ * --------------
36
+ *
37
+ * On error, transaction functions append a message about what
38
+ * went wrong to the 'err' argument. The message mentions what
39
+ * ref was being updated (if any) when the error occurred so it
40
+ * can be passed to 'die' or 'error' as-is.
41
+ *
42
+ * The message is appended to err without first clearing err.
43
+ * err will not be '\n' terminated.
44
+ */
45
struct ref_transaction;
46
47
/*
@@ -248,7 +280,7 @@ struct ref_transaction *ref_transaction_begin(void);
280
* it must not have existed beforehand.
281
* Function returns 0 on success and non-zero on failure. A failure to update
282
* means that the transaction as a whole has failed and will need to be
251
- * rolled back. On failure the err buffer will be updated.
283
+ * rolled back.
284
*/
285
int ref_transaction_update(struct ref_transaction *transaction,
286
const char *refname,
@@ -262,11 +294,15 @@ int ref_transaction_update(struct ref_transaction *transaction,
294
* that the reference should have after the update; it must not be the
295
* null SHA-1. It is verified that the reference does not exist
296
* already.
297
+ * Function returns 0 on success and non-zero on failure. A failure to create
298
+ * means that the transaction as a whole has failed and will need to be
299
+ * rolled back.
300
*/
266
-void ref_transaction_create(struct ref_transaction *transaction,
267
- const char *refname,
268
- const unsigned char *new_sha1,
269
- int flags);
301
+int ref_transaction_create(struct ref_transaction *transaction,
302
+ const char *refname,
303
+ const unsigned char *new_sha1,
304
+ int flags,
305
+ struct strbuf *err);
306
307
/*
308
* Add a reference deletion to transaction. If have_old is true, then
@@ -282,8 +318,6 @@ void ref_transaction_delete(struct ref_transaction *transaction,
318
* Commit all of the changes that have been queued in transaction, as
319
* atomically as possible. Return a nonzero value if there is a
320
* problem.
285
- * If err is non-NULL we will add an error string to it to explain why
286
- * the transaction failed. The string does not end in newline.
321
*/
322
int ref_transaction_commit(struct ref_transaction *transaction,
323
const char *msg, struct strbuf *err);