git-send-email: Do not make @-less message ID
[gitweb.git] / remote.c
index b53130fb5662cefde477c07bd0ddd9cf43a0854d..500ca4d968753485ac38d44e238e93ab86372c1c 100644 (file)
--- a/remote.c
+++ b/remote.c
@@ -333,7 +333,6 @@ static int count_refspec_match(const char *pattern,
        for (weak_match = match = 0; refs; refs = refs->next) {
                char *name = refs->name;
                int namelen = strlen(name);
-               int weak_match;
 
                if (namelen < patlen ||
                    memcmp(name + namelen - patlen, pattern, patlen))
@@ -406,6 +405,18 @@ static struct ref *try_explicit_object_name(const char *name)
        return ref;
 }
 
+static struct ref *make_dst(const char *name, struct ref ***dst_tail)
+{
+       struct ref *dst;
+       size_t len;
+
+       len = strlen(name) + 1;
+       dst = xcalloc(1, sizeof(*dst) + len);
+       memcpy(dst->name, name, len);
+       link_dst_tail(dst, dst_tail);
+       return dst;
+}
+
 static int match_explicit(struct ref *src, struct ref *dst,
                          struct ref ***dst_tail,
                          struct refspec *rs,
@@ -418,9 +429,6 @@ static int match_explicit(struct ref *src, struct ref *dst,
        if (rs->pattern)
                return errs;
 
-       if (dst_value == NULL)
-               dst_value = rs->src;
-
        matched_src = matched_dst = NULL;
        switch (count_refspec_match(rs->src, src, &matched_src)) {
        case 1:
@@ -433,52 +441,41 @@ static int match_explicit(struct ref *src, struct ref *dst,
                matched_src = try_explicit_object_name(rs->src);
                if (matched_src)
                        break;
-               errs = 1;
                error("src refspec %s does not match any.",
                      rs->src);
                break;
        default:
-               errs = 1;
+               matched_src = NULL;
                error("src refspec %s matches more than one.",
                      rs->src);
                break;
        }
+
+       if (!matched_src)
+               errs = 1;
+
+       if (dst_value == NULL)
+               dst_value = matched_src->name;
+
        switch (count_refspec_match(dst_value, dst, &matched_dst)) {
        case 1:
                break;
        case 0:
-               if (!memcmp(dst_value, "refs/", 5)) {
-                       int len = strlen(dst_value) + 1;
-                       matched_dst = xcalloc(1, sizeof(*dst) + len);
-                       memcpy(matched_dst->name, dst_value, len);
-                       link_dst_tail(matched_dst, dst_tail);
-               }
-               else if (!strcmp(rs->src, dst_value) &&
-                        matched_src) {
-                       /* pushing "master:master" when
-                        * remote does not have master yet.
-                        */
-                       int len = strlen(matched_src->name) + 1;
-                       matched_dst = xcalloc(1, sizeof(*dst) + len);
-                       memcpy(matched_dst->name, matched_src->name,
-                              len);
-                       link_dst_tail(matched_dst, dst_tail);
-               }
-               else {
-                       errs = 1;
+               if (!memcmp(dst_value, "refs/", 5))
+                       matched_dst = make_dst(dst_value, dst_tail);
+               else
                        error("dst refspec %s does not match any "
                              "existing ref on the remote and does "
                              "not start with refs/.", dst_value);
-               }
                break;
        default:
-               errs = 1;
+               matched_dst = NULL;
                error("dst refspec %s matches more than one.",
                      dst_value);
                break;
        }
-       if (errs)
-               return errs;
+       if (errs || matched_dst == NULL)
+               return 1;
        if (matched_dst->peer_ref) {
                errs = 1;
                error("dst ref %s receives from more than one src.",
@@ -549,13 +546,14 @@ int match_refs(struct ref *src, struct ref *dst, struct ref ***dst_tail,
                }
 
                if (pat) {
-                       dst_name = xmalloc(strlen(pat->dst) +
+                       const char *dst_side = pat->dst ? pat->dst : pat->src;
+                       dst_name = xmalloc(strlen(dst_side) +
                                           strlen(src->name) -
                                           strlen(pat->src) + 2);
-                       strcpy(dst_name, pat->dst);
+                       strcpy(dst_name, dst_side);
                        strcat(dst_name, src->name + strlen(pat->src));
                } else
-                       dst_name = strdup(src->name);
+                       dst_name = xstrdup(src->name);
                dst_peer = find_ref_by_name(dst, dst_name);
                if (dst_peer && dst_peer->peer_ref)
                        /* We're already sending something to this ref. */
@@ -567,11 +565,8 @@ int match_refs(struct ref *src, struct ref *dst, struct ref ***dst_tail,
                        goto free_name;
                if (!dst_peer) {
                        /* Create a new one and link it */
-                       int len = strlen(dst_name) + 1;
-                       dst_peer = xcalloc(1, sizeof(*dst_peer) + len);
-                       memcpy(dst_peer->name, dst_name, len);
+                       dst_peer = make_dst(dst_name, dst_tail);
                        hashcpy(dst_peer->new_sha1, src->new_sha1);
-                       link_dst_tail(dst_peer, dst_tail);
                }
                dst_peer->peer_ref = src;
        free_name: