1674 |
1674 |
1675 return keys; |
1675 return keys; |
1676 } |
1676 } |
1677 |
1677 |
1678 /* |
1678 /* |
1679 * Given a (possibly overlapping) set of revs, return the greatest |
1679 * Given a (possibly overlapping) set of revs, return all the |
1680 * common ancestors: those with the longest path to the root. |
1680 * common ancestors heads: heads(::args[0] and ::a[1] and ...) |
1681 */ |
1681 */ |
1682 static PyObject *index_ancestors(indexObject *self, PyObject *args) |
1682 static PyObject *index_commonancestorsheads(indexObject *self, PyObject *args) |
1683 { |
1683 { |
1684 PyObject *ret = NULL, *gca = NULL; |
1684 PyObject *ret = NULL; |
1685 Py_ssize_t argcount, i, len; |
1685 Py_ssize_t argcount, i, len; |
1686 bitmask repeat = 0; |
1686 bitmask repeat = 0; |
1687 int revcount = 0; |
1687 int revcount = 0; |
1688 int *revs; |
1688 int *revs; |
1689 |
1689 |
1752 goto bail; |
1752 goto bail; |
1753 PyList_SET_ITEM(ret, 0, obj); |
1753 PyList_SET_ITEM(ret, 0, obj); |
1754 goto done; |
1754 goto done; |
1755 } |
1755 } |
1756 |
1756 |
1757 gca = find_gca_candidates(self, revs, revcount); |
|
1758 if (gca == NULL) |
|
1759 goto bail; |
|
1760 |
|
1761 if (PyList_GET_SIZE(gca) <= 1) { |
|
1762 ret = gca; |
|
1763 Py_INCREF(gca); |
|
1764 } |
|
1765 else ret = find_deepest(self, gca); |
|
1766 |
|
1767 done: |
|
1768 free(revs); |
|
1769 Py_XDECREF(gca); |
|
1770 |
|
1771 return ret; |
|
1772 |
|
1773 bail: |
|
1774 free(revs); |
|
1775 Py_XDECREF(gca); |
|
1776 Py_XDECREF(ret); |
|
1777 return NULL; |
|
1778 } |
|
1779 |
|
1780 /* |
|
1781 * Given a (possibly overlapping) set of revs, return all the |
|
1782 * common ancestors heads: heads(::args[0] and ::a[1] and ...) |
|
1783 */ |
|
1784 static PyObject *index_commonancestorsheads(indexObject *self, PyObject *args) |
|
1785 { |
|
1786 PyObject *ret = NULL; |
|
1787 Py_ssize_t argcount, i, len; |
|
1788 bitmask repeat = 0; |
|
1789 int revcount = 0; |
|
1790 int *revs; |
|
1791 |
|
1792 argcount = PySequence_Length(args); |
|
1793 revs = malloc(argcount * sizeof(*revs)); |
|
1794 if (argcount > 0 && revs == NULL) |
|
1795 return PyErr_NoMemory(); |
|
1796 len = index_length(self) - 1; |
|
1797 |
|
1798 for (i = 0; i < argcount; i++) { |
|
1799 static const int capacity = 24; |
|
1800 PyObject *obj = PySequence_GetItem(args, i); |
|
1801 bitmask x; |
|
1802 long val; |
|
1803 |
|
1804 if (!PyInt_Check(obj)) { |
|
1805 PyErr_SetString(PyExc_TypeError, |
|
1806 "arguments must all be ints"); |
|
1807 Py_DECREF(obj); |
|
1808 goto bail; |
|
1809 } |
|
1810 val = PyInt_AsLong(obj); |
|
1811 Py_DECREF(obj); |
|
1812 if (val == -1) { |
|
1813 ret = PyList_New(0); |
|
1814 goto done; |
|
1815 } |
|
1816 if (val < 0 || val >= len) { |
|
1817 PyErr_SetString(PyExc_IndexError, |
|
1818 "index out of range"); |
|
1819 goto bail; |
|
1820 } |
|
1821 /* this cheesy bloom filter lets us avoid some more |
|
1822 * expensive duplicate checks in the common set-is-disjoint |
|
1823 * case */ |
|
1824 x = 1ull << (val & 0x3f); |
|
1825 if (repeat & x) { |
|
1826 int k; |
|
1827 for (k = 0; k < revcount; k++) { |
|
1828 if (val == revs[k]) |
|
1829 goto duplicate; |
|
1830 } |
|
1831 } |
|
1832 else repeat |= x; |
|
1833 if (revcount >= capacity) { |
|
1834 PyErr_Format(PyExc_OverflowError, |
|
1835 "bitset size (%d) > capacity (%d)", |
|
1836 revcount, capacity); |
|
1837 goto bail; |
|
1838 } |
|
1839 revs[revcount++] = (int)val; |
|
1840 duplicate:; |
|
1841 } |
|
1842 |
|
1843 if (revcount == 0) { |
|
1844 ret = PyList_New(0); |
|
1845 goto done; |
|
1846 } |
|
1847 if (revcount == 1) { |
|
1848 PyObject *obj; |
|
1849 ret = PyList_New(1); |
|
1850 if (ret == NULL) |
|
1851 goto bail; |
|
1852 obj = PyInt_FromLong(revs[0]); |
|
1853 if (obj == NULL) |
|
1854 goto bail; |
|
1855 PyList_SET_ITEM(ret, 0, obj); |
|
1856 goto done; |
|
1857 } |
|
1858 |
|
1859 ret = find_gca_candidates(self, revs, revcount); |
1757 ret = find_gca_candidates(self, revs, revcount); |
1860 if (ret == NULL) |
1758 if (ret == NULL) |
1861 goto bail; |
1759 goto bail; |
1862 |
1760 |
1863 done: |
1761 done: |