This parameter allows the branch update validation function to
optionally return a flag specifying the reason for failure, when
requested. This allows the caller to know why it was about to die.
This allows more useful error messages to be given to the user when
trying to rename a branch.

The flags are specified in the form of an enum and values for success
flags have been assigned explicitly to clearly express that certain
callers rely those values and they cannot be arbitrary.

Only the logic has been added but no caller has been made to use it, yet.
So, no functional changes.

Signed-off-by: Kaartic Sivaraam <kaarticsivaraam91...@gmail.com>
---
 branch.c           | 34 +++++++++++++++++++++++-----------
 branch.h           | 23 +++++++++++++++++++++--
 builtin/branch.c   |  2 +-
 builtin/checkout.c |  2 +-
 4 files changed, 46 insertions(+), 15 deletions(-)

diff --git a/branch.c b/branch.c
index 2020dedf6..9dda336a0 100644
--- a/branch.c
+++ b/branch.c
@@ -178,28 +178,40 @@ int read_branch_desc(struct strbuf *buf, const char 
*branch_name)
        return 0;
 }
 
-int validate_branch_update(const char *name, struct strbuf *ref,
-                          int could_exist, int clobber_head)
+int validate_branch_update(const char *name, struct strbuf *ref, int 
could_exist,
+                          int clobber_head, unsigned dont_fail)
 {
-       if (strbuf_check_branch_ref(ref, name))
-               die(_("'%s' is not a valid branch name."), name);
+       if (strbuf_check_branch_ref(ref, name)) {
+               if (dont_fail)
+                       return INVALID_BRANCH_NAME;
+               else
+                       die(_("'%s' is not a valid branch name."), name);
+       }
 
        if (!ref_exists(ref->buf))
-               return 0;
+               return VALID_BRANCH_NAME;
 
-       if (!could_exist)
-               die(_("A branch named '%s' already exists."), ref->buf + 
strlen("refs/heads/"));
+       if (!could_exist) {
+               if (dont_fail)
+                       return BRANCH_EXISTS;
+               else
+                       die(_("A branch named '%s' already exists."), ref->buf 
+ strlen("refs/heads/"));
+       }
 
        if (!clobber_head) {
                const char *head;
                struct object_id oid;
 
                head = resolve_ref_unsafe("HEAD", 0, oid.hash, NULL);
-               if (!is_bare_repository() && head && !strcmp(head, ref->buf))
-                       die(_("Cannot force update the current branch."));
+               if (!is_bare_repository() && head && !strcmp(head, ref->buf)) {
+                       if (dont_fail)
+                               return CANNOT_FORCE_UPDATE_CURRENT_BRANCH;
+                       else
+                               die(_("Cannot force update the current 
branch."));
+               }
        }
 
-       return 1;
+       return FORCE_UPDATING_BRANCH;
 }
 
 /*
@@ -268,7 +280,7 @@ void create_branch(const char *name, const char *start_name,
                validate_existing_branch(name, &ref);
                dont_change_ref = 1;
        } else {
-               forcing = validate_branch_update(name, &ref, force, 
clobber_head);
+               forcing = validate_branch_update(name, &ref, force, 
clobber_head, 0);
        }
 
        real_ref = NULL;
diff --git a/branch.h b/branch.h
index 6ada7af59..c6a8a75bb 100644
--- a/branch.h
+++ b/branch.h
@@ -27,6 +27,16 @@ void create_branch(const char *name, const char *start_name,
                   int force, int reflog,
                   int clobber_head, int quiet, enum branch_track track);
 
+enum branch_validation_result {
+       /* Flags that say it's NOT OK to update */
+       BRANCH_EXISTS = -3,
+       CANNOT_FORCE_UPDATE_CURRENT_BRANCH,
+       INVALID_BRANCH_NAME,
+       /* Flags that say it's OK to update */
+       VALID_BRANCH_NAME = 0,
+       FORCE_UPDATING_BRANCH = 1
+};
+
 /*
  * Validates whether the branch with the given name may be updated (created, 
renamed etc.,)
  * with respect to the given conditions. It returns the interpreted ref in ref.
@@ -36,10 +46,19 @@ void create_branch(const char *name, const char *start_name,
  * if 'could_exist' is true, clobber_head indicates whether the branch could 
be the
  * current branch else it has no effect.
  *
- * A non-zero return value indicates that a branch already exists and can be 
force updated.
+ * The return values have the following meaning,
+ *
+ *   - If dont_fail is 0, the function dies in case of failure and returns 
flags of
+ *     'validate_result' that specify it is OK to update the branch. The 
positive
+ *     non-zero flag implies that the branch can be force updated.
+ *
+ *   - If dont_fail is 1, the function doesn't die in case of failure but 
returns flags
+ *     of 'validate_result' that specify the reason for failure. The behaviour 
in case of
+ *     success is same as above.
  *
  */
-int validate_branch_update(const char *name, struct strbuf *ref, int 
could_exist, int clobber_head);
+int validate_branch_update(const char *name, struct strbuf *ref, int 
could_exist,
+                          int clobber_head, unsigned dont_fail);
 
 /*
  * Remove information about the state of working on the current
diff --git a/builtin/branch.c b/builtin/branch.c
index 27ddcad97..205c12a11 100644
--- a/builtin/branch.c
+++ b/builtin/branch.c
@@ -483,7 +483,7 @@ static void rename_branch(const char *oldname, const char 
*newname, int force)
         */
        clobber_head_ok = !strcmp(oldname, newname);
 
-       validate_branch_update(newname, &newref, force, clobber_head_ok);
+       validate_branch_update(newname, &newref, force, clobber_head_ok, 0);
 
        reject_rebase_or_bisect_branch(oldref.buf);
 
diff --git a/builtin/checkout.c b/builtin/checkout.c
index 2e870ab4b..c7e11c352 100644
--- a/builtin/checkout.c
+++ b/builtin/checkout.c
@@ -1284,7 +1284,7 @@ int cmd_checkout(int argc, const char **argv, const char 
*prefix)
                int force = opts.new_branch_force != NULL;
 
                opts.branch_exists = validate_branch_update(opts.new_branch, 
&buf,
-                                                           force, force);
+                                                           force, force, 0);
 
                strbuf_release(&buf);
        }
-- 
2.14.1.868.g66c78774b

Reply via email to