* Given the set of refs the local repository has, the set of refs the * remote repository has, and the refspec used for push, determine * what remote refs we will update and with what value by setting * peer_ref (which object is being pushed) and force (if the push is * forced) in elements of "dst". The function may add new elements to * dst (e.g. pushing to a new branch, done in match_explic
| 1570 | * dst (e.g. pushing to a new branch, done in match_explicit_refs). |
| 1571 | */ |
| 1572 | int match_push_refs(struct ref *src, struct ref **dst, |
| 1573 | struct refspec *rs, int flags) |
| 1574 | { |
| 1575 | int send_all = flags & MATCH_REFS_ALL; |
| 1576 | int send_mirror = flags & MATCH_REFS_MIRROR; |
| 1577 | int send_prune = flags & MATCH_REFS_PRUNE; |
| 1578 | int errs; |
| 1579 | struct ref *ref, **dst_tail = tail_ref(dst); |
| 1580 | struct string_list dst_ref_index = STRING_LIST_INIT_NODUP; |
| 1581 | |
| 1582 | /* If no refspec is provided, use the default ":" */ |
| 1583 | if (!rs->nr) |
| 1584 | refspec_append(rs, ":"); |
| 1585 | |
| 1586 | errs = match_explicit_refs(src, *dst, &dst_tail, rs); |
| 1587 | |
| 1588 | /* pick the remainder */ |
| 1589 | for (ref = src; ref; ref = ref->next) { |
| 1590 | struct string_list_item *dst_item; |
| 1591 | struct ref *dst_peer; |
| 1592 | const struct refspec_item *pat = NULL; |
| 1593 | char *dst_name; |
| 1594 | |
| 1595 | dst_name = get_ref_match(rs, ref, send_mirror, FROM_SRC, &pat); |
| 1596 | if (!dst_name) |
| 1597 | continue; |
| 1598 | |
| 1599 | if (!dst_ref_index.nr) |
| 1600 | prepare_ref_index(&dst_ref_index, *dst); |
| 1601 | |
| 1602 | dst_item = string_list_lookup(&dst_ref_index, dst_name); |
| 1603 | dst_peer = dst_item ? dst_item->util : NULL; |
| 1604 | if (dst_peer) { |
| 1605 | if (dst_peer->peer_ref) |
| 1606 | /* We're already sending something to this ref. */ |
| 1607 | goto free_name; |
| 1608 | } else { |
| 1609 | if (pat->matching && !(send_all || send_mirror)) |
| 1610 | /* |
| 1611 | * Remote doesn't have it, and we have no |
| 1612 | * explicit pattern, and we don't have |
| 1613 | * --all or --mirror. |
| 1614 | */ |
| 1615 | goto free_name; |
| 1616 | |
| 1617 | /* Create a new one and link it */ |
| 1618 | dst_peer = make_linked_ref(dst_name, &dst_tail); |
| 1619 | oidcpy(&dst_peer->new_oid, &ref->new_oid); |
| 1620 | string_list_insert(&dst_ref_index, |
| 1621 | dst_peer->name)->util = dst_peer; |
| 1622 | } |
| 1623 | dst_peer->peer_ref = copy_ref(ref); |
| 1624 | dst_peer->force = pat->force; |
| 1625 | free_name: |
| 1626 | free(dst_name); |
| 1627 | } |
| 1628 | |
| 1629 | string_list_clear(&dst_ref_index, 0); |
no test coverage detected