Mercurial > hg
view tests/test-setdiscovery.t @ 50400:95acba2c29f6
encoding: avoid quadratic time complexity when json-encoding non-UTF8 strings
Apparently the code uses "+=" with a bytes object, which is linear-time, so the
whole encoding is quadratic-time. This patch makes us use a bytearray object,
instead, which has a(n amortized-)constant-time append operation.
The encoding is still not particularly fast, but at least a 10MB file
takes tens of seconds, not many hours to encode.
author | Arseniy Alekseyev <aalekseyev@janestreet.com> |
---|---|
date | Mon, 06 Mar 2023 11:27:57 +0000 |
parents | 236702592ff0 |
children |
line wrap: on
line source
Function to test discovery between two repos in both directions, using both the local shortcut (which is currently not activated by default) and the full remotable protocol: $ testdesc() { # revs_a, revs_b, dagdesc > if [ -d foo ]; then rm -rf foo; fi > hg init foo > cd foo > hg debugbuilddag "$3" > hg clone . a $1 --quiet > hg clone . b $2 --quiet > echo > echo "% -- a -> b tree" > hg -R a debugdiscovery b --verbose --old > echo > echo "% -- a -> b set" > hg -R a debugdiscovery b --verbose --debug --config progress.debug=true > echo > echo "% -- a -> b set (tip only)" > hg -R a debugdiscovery b --verbose --debug --config progress.debug=true --rev tip > echo > echo "% -- b -> a tree" > hg -R b debugdiscovery a --verbose --old > echo > echo "% -- b -> a set" > hg -R b debugdiscovery a --verbose --debug --config progress.debug=true > echo > echo "% -- b -> a set (tip only)" > hg -R b debugdiscovery a --verbose --debug --config progress.debug=true --rev tip > cd .. > } Small superset: $ testdesc '-ra1 -ra2' '-rb1 -rb2 -rb3' ' > +2:f +1:a1:b1 > <f +4 :a2 > +5 :b2 > <f +3 :b3' % -- a -> b tree comparing with b searching for changes unpruned common: 01241442b3c2 66f7d451a68b b5714e113bc0 elapsed time: * seconds (glob) round-trips: 4 queries: 6 queries-branches: 2 queries-between: 4 heads summary: total common heads: 2 also local heads: 2 also remote heads: 1 both: 1 local heads: 2 common: 2 missing: 0 remote heads: 3 common: 1 unknown: 2 local changesets: 7 common: 7 heads: 2 roots: 1 missing: 0 heads: 0 roots: 0 first undecided set: 3 heads: 1 roots: 1 common: 3 missing: 0 common heads: 01241442b3c2 b5714e113bc0 % -- a -> b set comparing with b query 1; heads searching for changes all local changesets known remotely elapsed time: * seconds (glob) round-trips: 1 queries: 2 heads summary: total common heads: 2 also local heads: 2 also remote heads: 1 both: 1 local heads: 2 common: 2 missing: 0 remote heads: 3 common: 1 unknown: 2 local changesets: 7 common: 7 heads: 2 roots: 1 missing: 0 heads: 0 roots: 0 first undecided set: 3 heads: 1 roots: 1 common: 3 missing: 0 common heads: 01241442b3c2 b5714e113bc0 % -- a -> b set (tip only) comparing with b query 1; heads searching for changes all local changesets known remotely elapsed time: * seconds (glob) round-trips: 1 queries: 1 heads summary: total common heads: 1 also local heads: 1 also remote heads: 0 both: 0 local heads: 2 common: 1 missing: 1 remote heads: 3 common: 0 unknown: 3 local changesets: 7 common: 6 heads: 1 roots: 1 missing: 1 heads: 1 roots: 1 first undecided set: 6 heads: 2 roots: 1 common: 5 missing: 1 common heads: b5714e113bc0 % -- b -> a tree comparing with a searching for changes unpruned common: 01241442b3c2 b5714e113bc0 elapsed time: * seconds (glob) round-trips: 1 queries: 0 queries-branches: 0 queries-between: 0 heads summary: total common heads: 2 also local heads: 1 also remote heads: 2 both: 1 local heads: 3 common: 1 missing: 2 remote heads: 2 common: 2 unknown: 0 local changesets: 15 common: 7 heads: 2 roots: 1 missing: 8 heads: 2 roots: 2 first undecided set: 8 heads: 2 roots: 2 common: 0 missing: 8 common heads: 01241442b3c2 b5714e113bc0 % -- b -> a set comparing with a query 1; heads searching for changes all remote heads known locally elapsed time: * seconds (glob) round-trips: 1 queries: 3 heads summary: total common heads: 2 also local heads: 1 also remote heads: 2 both: 1 local heads: 3 common: 1 missing: 2 remote heads: 2 common: 2 unknown: 0 local changesets: 15 common: 7 heads: 2 roots: 1 missing: 8 heads: 2 roots: 2 first undecided set: 8 heads: 2 roots: 2 common: 0 missing: 8 common heads: 01241442b3c2 b5714e113bc0 % -- b -> a set (tip only) comparing with a query 1; heads searching for changes all remote heads known locally elapsed time: * seconds (glob) round-trips: 1 queries: 1 heads summary: total common heads: 2 also local heads: 1 also remote heads: 2 both: 1 local heads: 3 common: 1 missing: 2 remote heads: 2 common: 2 unknown: 0 local changesets: 15 common: 7 heads: 2 roots: 1 missing: 8 heads: 2 roots: 2 first undecided set: 8 heads: 2 roots: 2 common: 0 missing: 8 common heads: 01241442b3c2 b5714e113bc0 Many new: $ testdesc '-ra1 -ra2' '-rb' ' > +2:f +3:a1 +3:b > <f +30 :a2' % -- a -> b tree comparing with b searching for changes unpruned common: bebd167eb94d elapsed time: * seconds (glob) round-trips: 4 queries: 3 queries-branches: 1 queries-between: 2 heads summary: total common heads: 1 also local heads: 1 also remote heads: 0 both: 0 local heads: 2 common: 1 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 35 common: 5 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 34 heads: 2 roots: 1 common: 4 missing: 30 common heads: bebd167eb94d % -- a -> b set comparing with b query 1; heads searching for changes taking initial sample searching: 2 queries query 2; still undecided: 29, sample size is: 29 2 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 2 queries: 31 heads summary: total common heads: 1 also local heads: 1 also remote heads: 0 both: 0 local heads: 2 common: 1 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 35 common: 5 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 34 heads: 2 roots: 1 common: 4 missing: 30 common heads: bebd167eb94d % -- a -> b set (tip only) comparing with b query 1; heads searching for changes taking quick initial sample searching: 2 queries query 2; still undecided: 31, sample size is: 31 2 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 2 queries: 32 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 2 common: 0 missing: 2 remote heads: 1 common: 0 unknown: 1 local changesets: 35 common: 2 heads: 1 roots: 1 missing: 33 heads: 2 roots: 2 first undecided set: 35 heads: 2 roots: 1 common: 2 missing: 33 common heads: 66f7d451a68b % -- b -> a tree comparing with a searching for changes unpruned common: 66f7d451a68b bebd167eb94d elapsed time: * seconds (glob) round-trips: 6 queries: 5 queries-branches: 1 queries-between: 4 heads summary: total common heads: 1 also local heads: 0 also remote heads: 1 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 2 common: 1 unknown: 1 local changesets: 8 common: 5 heads: 1 roots: 1 missing: 3 heads: 1 roots: 1 first undecided set: 3 heads: 1 roots: 1 common: 0 missing: 3 common heads: bebd167eb94d % -- b -> a set comparing with a query 1; heads searching for changes taking initial sample searching: 2 queries query 2; still undecided: 2, sample size is: 2 2 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 2 queries: 3 heads summary: total common heads: 1 also local heads: 0 also remote heads: 1 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 2 common: 1 unknown: 1 local changesets: 8 common: 5 heads: 1 roots: 1 missing: 3 heads: 1 roots: 1 first undecided set: 3 heads: 1 roots: 1 common: 0 missing: 3 common heads: bebd167eb94d % -- b -> a set (tip only) comparing with a query 1; heads searching for changes taking initial sample searching: 2 queries query 2; still undecided: 2, sample size is: 2 2 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 2 queries: 3 heads summary: total common heads: 1 also local heads: 0 also remote heads: 1 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 2 common: 1 unknown: 1 local changesets: 8 common: 5 heads: 1 roots: 1 missing: 3 heads: 1 roots: 1 first undecided set: 3 heads: 1 roots: 1 common: 0 missing: 3 common heads: bebd167eb94d Both sides many new with stub: $ testdesc '-ra1 -ra2' '-rb' ' > +2:f +2:a1 +30 :b > <f +30 :a2' % -- a -> b tree comparing with b searching for changes unpruned common: 2dc09a01254d elapsed time: * seconds (glob) round-trips: 6 queries: 5 queries-branches: 1 queries-between: 4 heads summary: total common heads: 1 also local heads: 1 also remote heads: 0 both: 0 local heads: 2 common: 1 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 34 common: 4 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 33 heads: 2 roots: 1 common: 3 missing: 30 common heads: 2dc09a01254d % -- a -> b set comparing with b query 1; heads searching for changes taking initial sample searching: 2 queries query 2; still undecided: 29, sample size is: 29 2 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 2 queries: 31 heads summary: total common heads: 1 also local heads: 1 also remote heads: 0 both: 0 local heads: 2 common: 1 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 34 common: 4 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 33 heads: 2 roots: 1 common: 3 missing: 30 common heads: 2dc09a01254d % -- a -> b set (tip only) comparing with b query 1; heads searching for changes taking quick initial sample searching: 2 queries query 2; still undecided: 31, sample size is: 31 2 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 2 queries: 32 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 2 common: 0 missing: 2 remote heads: 1 common: 0 unknown: 1 local changesets: 34 common: 2 heads: 1 roots: 1 missing: 32 heads: 2 roots: 2 first undecided set: 34 heads: 2 roots: 1 common: 2 missing: 32 common heads: 66f7d451a68b % -- b -> a tree comparing with a searching for changes unpruned common: 2dc09a01254d 66f7d451a68b elapsed time: * seconds (glob) round-trips: 6 queries: 5 queries-branches: 1 queries-between: 4 heads summary: total common heads: 1 also local heads: 0 also remote heads: 1 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 2 common: 1 unknown: 1 local changesets: 34 common: 4 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 30 heads: 1 roots: 1 common: 0 missing: 30 common heads: 2dc09a01254d % -- b -> a set comparing with a query 1; heads searching for changes taking initial sample searching: 2 queries query 2; still undecided: 29, sample size is: 29 2 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 2 queries: 30 heads summary: total common heads: 1 also local heads: 0 also remote heads: 1 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 2 common: 1 unknown: 1 local changesets: 34 common: 4 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 30 heads: 1 roots: 1 common: 0 missing: 30 common heads: 2dc09a01254d % -- b -> a set (tip only) comparing with a query 1; heads searching for changes taking initial sample searching: 2 queries query 2; still undecided: 29, sample size is: 29 2 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 2 queries: 30 heads summary: total common heads: 1 also local heads: 0 also remote heads: 1 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 2 common: 1 unknown: 1 local changesets: 34 common: 4 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 30 heads: 1 roots: 1 common: 0 missing: 30 common heads: 2dc09a01254d Both many new: $ testdesc '-ra' '-rb' ' > +2:f +30 :b > <f +30 :a' % -- a -> b tree comparing with b searching for changes unpruned common: 66f7d451a68b elapsed time: * seconds (glob) round-trips: 6 queries: 5 queries-branches: 1 queries-between: 4 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 32 common: 2 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 32 heads: 1 roots: 1 common: 2 missing: 30 common heads: 66f7d451a68b % -- a -> b set comparing with b query 1; heads searching for changes taking quick initial sample searching: 2 queries query 2; still undecided: 31, sample size is: 31 2 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 2 queries: 32 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 32 common: 2 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 32 heads: 1 roots: 1 common: 2 missing: 30 common heads: 66f7d451a68b % -- a -> b set (tip only) comparing with b query 1; heads searching for changes taking quick initial sample searching: 2 queries query 2; still undecided: 31, sample size is: 31 2 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 2 queries: 32 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 32 common: 2 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 32 heads: 1 roots: 1 common: 2 missing: 30 common heads: 66f7d451a68b % -- b -> a tree comparing with a searching for changes unpruned common: 66f7d451a68b elapsed time: * seconds (glob) round-trips: 6 queries: 5 queries-branches: 1 queries-between: 4 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 32 common: 2 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 32 heads: 1 roots: 1 common: 2 missing: 30 common heads: 66f7d451a68b % -- b -> a set comparing with a query 1; heads searching for changes taking quick initial sample searching: 2 queries query 2; still undecided: 31, sample size is: 31 2 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 2 queries: 32 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 32 common: 2 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 32 heads: 1 roots: 1 common: 2 missing: 30 common heads: 66f7d451a68b % -- b -> a set (tip only) comparing with a query 1; heads searching for changes taking quick initial sample searching: 2 queries query 2; still undecided: 31, sample size is: 31 2 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 2 queries: 32 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 32 common: 2 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 32 heads: 1 roots: 1 common: 2 missing: 30 common heads: 66f7d451a68b Both many new skewed: $ testdesc '-ra' '-rb' ' > +2:f +30 :b > <f +50 :a' % -- a -> b tree comparing with b searching for changes unpruned common: 66f7d451a68b elapsed time: * seconds (glob) round-trips: 6 queries: 5 queries-branches: 1 queries-between: 4 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 52 common: 2 heads: 1 roots: 1 missing: 50 heads: 1 roots: 1 first undecided set: 52 heads: 1 roots: 1 common: 2 missing: 50 common heads: 66f7d451a68b % -- a -> b set comparing with b query 1; heads searching for changes taking quick initial sample searching: 2 queries query 2; still undecided: 51, sample size is: 51 2 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 2 queries: 52 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 52 common: 2 heads: 1 roots: 1 missing: 50 heads: 1 roots: 1 first undecided set: 52 heads: 1 roots: 1 common: 2 missing: 50 common heads: 66f7d451a68b % -- a -> b set (tip only) comparing with b query 1; heads searching for changes taking quick initial sample searching: 2 queries query 2; still undecided: 51, sample size is: 51 2 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 2 queries: 52 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 52 common: 2 heads: 1 roots: 1 missing: 50 heads: 1 roots: 1 first undecided set: 52 heads: 1 roots: 1 common: 2 missing: 50 common heads: 66f7d451a68b % -- b -> a tree comparing with a searching for changes unpruned common: 66f7d451a68b elapsed time: * seconds (glob) round-trips: 5 queries: 4 queries-branches: 1 queries-between: 3 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 32 common: 2 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 32 heads: 1 roots: 1 common: 2 missing: 30 common heads: 66f7d451a68b % -- b -> a set comparing with a query 1; heads searching for changes taking quick initial sample searching: 2 queries query 2; still undecided: 31, sample size is: 31 2 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 2 queries: 32 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 32 common: 2 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 32 heads: 1 roots: 1 common: 2 missing: 30 common heads: 66f7d451a68b % -- b -> a set (tip only) comparing with a query 1; heads searching for changes taking quick initial sample searching: 2 queries query 2; still undecided: 31, sample size is: 31 2 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 2 queries: 32 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 32 common: 2 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 32 heads: 1 roots: 1 common: 2 missing: 30 common heads: 66f7d451a68b Both many new on top of long history: $ testdesc '-ra' '-rb' ' > +1000:f +30 :b > <f +50 :a' % -- a -> b tree comparing with b searching for changes unpruned common: 7ead0cba2838 elapsed time: * seconds (glob) round-trips: 6 queries: 5 queries-branches: 1 queries-between: 4 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 1050 common: 1000 heads: 1 roots: 1 missing: 50 heads: 1 roots: 1 first undecided set: 1050 heads: 1 roots: 1 common: 1000 missing: 50 common heads: 7ead0cba2838 % -- a -> b set comparing with b query 1; heads searching for changes taking quick initial sample searching: 2 queries query 2; still undecided: 1049, sample size is: 11 sampling from both directions searching: 3 queries query 3; still undecided: 31, sample size is: 31 3 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 3 queries: 43 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 1050 common: 1000 heads: 1 roots: 1 missing: 50 heads: 1 roots: 1 first undecided set: 1050 heads: 1 roots: 1 common: 1000 missing: 50 common heads: 7ead0cba2838 % -- a -> b set (tip only) comparing with b query 1; heads searching for changes taking quick initial sample searching: 2 queries query 2; still undecided: 1049, sample size is: 11 sampling from both directions searching: 3 queries query 3; still undecided: 31, sample size is: 31 3 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 3 queries: 43 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 1050 common: 1000 heads: 1 roots: 1 missing: 50 heads: 1 roots: 1 first undecided set: 1050 heads: 1 roots: 1 common: 1000 missing: 50 common heads: 7ead0cba2838 % -- b -> a tree comparing with a searching for changes unpruned common: 7ead0cba2838 elapsed time: * seconds (glob) round-trips: 5 queries: 4 queries-branches: 1 queries-between: 3 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 1030 common: 1000 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 1030 heads: 1 roots: 1 common: 1000 missing: 30 common heads: 7ead0cba2838 % -- b -> a set comparing with a query 1; heads searching for changes taking quick initial sample searching: 2 queries query 2; still undecided: 1029, sample size is: 11 sampling from both directions searching: 3 queries query 3; still undecided: 15, sample size is: 15 3 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 3 queries: 27 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 1030 common: 1000 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 1030 heads: 1 roots: 1 common: 1000 missing: 30 common heads: 7ead0cba2838 % -- b -> a set (tip only) comparing with a query 1; heads searching for changes taking quick initial sample searching: 2 queries query 2; still undecided: 1029, sample size is: 11 sampling from both directions searching: 3 queries query 3; still undecided: 15, sample size is: 15 3 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 3 queries: 27 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 1 common: 0 missing: 1 remote heads: 1 common: 0 unknown: 1 local changesets: 1030 common: 1000 heads: 1 roots: 1 missing: 30 heads: 1 roots: 1 first undecided set: 1030 heads: 1 roots: 1 common: 1000 missing: 30 common heads: 7ead0cba2838 One with >200 heads. We now switch to send them all in the initial roundtrip, but still do sampling for the later request. $ hg init manyheads $ cd manyheads $ echo "+300:r @a" >dagdesc $ echo "*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3 *r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3" >>dagdesc # 20 heads $ echo "*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3 *r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3" >>dagdesc # 20 heads $ echo "*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3 *r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3" >>dagdesc # 20 heads $ echo "*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3 *r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3" >>dagdesc # 20 heads $ echo "*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3 *r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3" >>dagdesc # 20 heads $ echo "*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3 *r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3" >>dagdesc # 20 heads $ echo "*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3 *r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3" >>dagdesc # 20 heads $ echo "*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3 *r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3" >>dagdesc # 20 heads $ echo "*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3 *r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3" >>dagdesc # 20 heads $ echo "*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3 *r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3" >>dagdesc # 20 heads $ echo "*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3 *r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3" >>dagdesc # 20 heads $ echo "*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3 *r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3" >>dagdesc # 20 heads $ echo "*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3 *r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3*r+3" >>dagdesc # 20 heads $ echo "@b *r+3" >>dagdesc # one more head $ hg debugbuilddag <dagdesc reading DAG from stdin $ hg heads -t --template . | wc -c \s*261 (re) $ hg clone -b a . a adding changesets adding manifests adding file changes added 1340 changesets with 0 changes to 0 files (+259 heads) new changesets 1ea73414a91b:1c51e2c80832 updating to branch a 0 files updated, 0 files merged, 0 files removed, 0 files unresolved $ hg clone -b b . b adding changesets adding manifests adding file changes added 304 changesets with 0 changes to 0 files new changesets 1ea73414a91b:513314ca8b3a updating to branch b 0 files updated, 0 files merged, 0 files removed, 0 files unresolved $ hg -R a debugdiscovery b --debug --verbose --config progress.debug=true --config devel.discovery.randomize=false --config devel.discovery.sample-size.initial=50 comparing with b query 1; heads searching for changes taking quick initial sample searching: 2 queries query 2; still undecided: 1080, sample size is: 50 sampling from both directions searching: 3 queries query 3; still undecided: 1030, sample size is: 200 sampling from both directions searching: 4 queries query 4; still undecided: 547, sample size is: 210 sampling from both directions searching: 5 queries query 5; still undecided: 336, sample size is: 220 sampling from both directions searching: 6 queries query 6; still undecided: 114, sample size is: 114 6 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 6 queries: 1054 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 260 common: 0 missing: 260 remote heads: 1 common: 0 unknown: 1 local changesets: 1340 common: 300 heads: 1 roots: 1 missing: 1040 heads: 260 roots: 260 first undecided set: 1340 heads: 260 roots: 1 common: 300 missing: 1040 common heads: 3ee37d65064a $ hg -R a debugdiscovery b --debug --verbose --config progress.debug=true --rev tip comparing with b query 1; heads searching for changes taking quick initial sample searching: 2 queries query 2; still undecided: 303, sample size is: 9 sampling from both directions searching: 3 queries query 3; still undecided: 3, sample size is: 3 3 total queries in *.????s (glob) elapsed time: * seconds (glob) round-trips: 3 queries: 13 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 260 common: 0 missing: 260 remote heads: 1 common: 0 unknown: 1 local changesets: 1340 common: 300 heads: 1 roots: 1 missing: 1040 heads: 260 roots: 260 first undecided set: 1340 heads: 260 roots: 1 common: 300 missing: 1040 common heads: 3ee37d65064a $ hg -R a debugdiscovery b --debug --config devel.discovery.exchange-heads=false --config devel.discovery.randomize=false --config devel.discovery.grow-sample.rate=1.20 --config devel.discovery.sample-size=50 comparing with b searching for changes sampling from both directions query 1; still undecided: 1340, sample size is: 50 sampling from both directions query 2; still undecided: 995, sample size is: 60 sampling from both directions query 3; still undecided: 913, sample size is: 72 sampling from both directions query 4; still undecided: 816, sample size is: 204 sampling from both directions query 5; still undecided: 612, sample size is: 153 sampling from both directions query 6; still undecided: 456, sample size is: 123 sampling from both directions query 7; still undecided: 332, sample size is: 147 sampling from both directions query 8; still undecided: 184, sample size is: 176 sampling from both directions query 9; still undecided: 8, sample size is: 8 9 total queries in *s (glob) elapsed time: * seconds (glob) round-trips: 9 queries: 993 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 260 common: 0 missing: 260 remote heads: 1 common: 0 unknown: 1 local changesets: 1340 common: 300 heads: 1 roots: 1 missing: 1040 heads: 260 roots: 260 first undecided set: 1340 heads: 260 roots: 1 common: 300 missing: 1040 common heads: 3ee37d65064a Test actual protocol when pulling one new head in addition to common heads $ hg clone -U b c $ hg -R c id -ir tip 513314ca8b3a $ hg -R c up -qr default $ touch c/f $ hg -R c ci -Aqm "extra head" $ hg -R c id -i e64a39e7da8b $ hg serve -R c -p $HGPORT -d --pid-file=hg.pid -A access.log -E errors.log $ cat hg.pid >> $DAEMON_PIDS $ hg -R b incoming http://localhost:$HGPORT/ -T '{node|short}\n' comparing with http://localhost:$HGPORT/ searching for changes e64a39e7da8b $ killdaemons.py $ cut -d' ' -f6- access.log | grep -v cmd=known # cmd=known uses random sampling "GET /?cmd=capabilities HTTP/1.1" 200 - "GET /?cmd=batch HTTP/1.1" 200 - x-hgarg-1:cmds=heads+%3Bknown+nodes%3D513314ca8b3ae4dac8eec56966265b00fcf866db x-hgproto-1:0.1 0.2 comp=$USUAL_COMPRESSIONS$ partial-pull "GET /?cmd=getbundle HTTP/1.1" 200 - x-hgarg-1:$USUAL_BUNDLE_CAPS$&cg=1&common=513314ca8b3ae4dac8eec56966265b00fcf866db&heads=e64a39e7da8b0d54bc63e81169aff001c13b3477 x-hgproto-1:0.1 0.2 comp=$USUAL_COMPRESSIONS$ partial-pull "GET /?cmd=listkeys HTTP/1.1" 200 - x-hgarg-1:namespace=phases x-hgproto-1:0.1 0.2 comp=$USUAL_COMPRESSIONS$ partial-pull $ cat errors.log $ cd .. Issue 4438 - test coverage for 3ef893520a85 issues. $ mkdir issue4438 $ cd issue4438 #if false generate new bundles: $ hg init r1 $ for i in `"$PYTHON" $TESTDIR/seq.py 101`; do hg -R r1 up -qr null && hg -R r1 branch -q b$i && hg -R r1 ci -qmb$i; done $ hg clone -q r1 r2 $ for i in `"$PYTHON" $TESTDIR/seq.py 10`; do hg -R r1 up -qr null && hg -R r1 branch -q c$i && hg -R r1 ci -qmc$i; done $ hg -R r2 branch -q r2change && hg -R r2 ci -qmr2change $ hg -R r1 bundle -qa $TESTDIR/bundles/issue4438-r1.hg $ hg -R r2 bundle -qa $TESTDIR/bundles/issue4438-r2.hg #else use existing bundles: $ hg init r1 $ hg -R r1 -q unbundle $TESTDIR/bundles/issue4438-r1.hg $ hg -R r1 -q up $ hg init r2 $ hg -R r2 -q unbundle $TESTDIR/bundles/issue4438-r2.hg $ hg -R r2 -q up #endif Set iteration order could cause wrong and unstable results - fixed in 73cfaa348650: $ hg -R r1 outgoing r2 -T'{rev} ' comparing with r2 searching for changes 101 102 103 104 105 106 107 108 109 110 (no-eol) The case where all the 'initialsamplesize' samples already were common would give 'all remote heads known locally' without checking the remaining heads - fixed in 86c35b7ae300: $ cat >> r1/.hg/hgrc << EOF > [devel] > discovery.randomize = False > EOF $ hg -R r1 outgoing r2 -T'{rev} ' --config extensions.blackbox= \ > --config blackbox.track='command commandfinish discovery' comparing with r2 searching for changes 101 102 103 104 105 106 107 108 109 110 (no-eol) $ hg -R r1 --config extensions.blackbox= blackbox --config blackbox.track= * @5d0b986a083e0d91f116de4691e2aaa54d5bbec0 (*)> serve --no-profile --cmdserver chgunix * (glob) (chg !) * @5d0b986a083e0d91f116de4691e2aaa54d5bbec0 (*)> -R r1 outgoing r2 *-T{rev} * --config *extensions.blackbox=* (glob) * @5d0b986a083e0d91f116de4691e2aaa54d5bbec0 (*)> found 101 common and 1 unknown server heads, 1 roundtrips in *.????s (glob) * @5d0b986a083e0d91f116de4691e2aaa54d5bbec0 (*)> -R r1 outgoing r2 *-T{rev} * --config *extensions.blackbox=* exited 0 after *.?? seconds (glob) $ cd .. Even if the set of revs to discover is restricted, unrelated revs may be returned as common heads. $ mkdir ancestorsof $ cd ancestorsof $ hg init a $ hg clone a b -q $ cd b $ hg debugbuilddag '.:root *root *root' $ hg log -G -T '{node|short}' o fa942426a6fd | | o 66f7d451a68b |/ o 1ea73414a91b $ hg push -r 66f7d451a68b -q $ hg debugdiscovery --verbose --rev fa942426a6fd comparing with $TESTTMP/ancestorsof/a searching for changes elapsed time: * seconds (glob) round-trips: 1 queries: 1 heads summary: total common heads: 1 also local heads: 1 also remote heads: 1 both: 1 local heads: 2 common: 1 missing: 1 remote heads: 1 common: 1 unknown: 0 local changesets: 3 common: 2 heads: 1 roots: 1 missing: 1 heads: 1 roots: 1 first undecided set: 1 heads: 1 roots: 1 common: 0 missing: 1 common heads: 66f7d451a68b $ cd .. Test debuging discovery using different subset of the same repository ===================================================================== remote is a local subset ------------------------ remote will be last 25 heads of the local graph $ cd $TESTTMP/manyheads $ hg -R a debugdiscovery \ > --debug \ > --remote-as-revs 'last(heads(all()), 25)' \ > --config devel.discovery.randomize=false query 1; heads searching for changes all remote heads known locally elapsed time: * seconds (glob) round-trips: 1 queries: 260 heads summary: total common heads: 25 also local heads: 25 also remote heads: 25 both: 25 local heads: 260 common: 25 missing: 235 remote heads: 25 common: 25 unknown: 0 local changesets: 1340 common: 400 heads: 25 roots: 1 missing: 940 heads: 235 roots: 235 first undecided set: 940 heads: 235 roots: 235 common: 0 missing: 940 common heads: 0dfd965d91c6 0fe09b60448d 14a17233ce9d 175c0a3072cf 1c51e2c80832 1e51600e0698 24eb5f9bdbab 25ce09526613 36bd00abde57 426989fdefa0 596d87362679 5dd1039ea5c0 5ef24f022278 5f230dc19419 80b39998accb 88f40688ffb5 9e37ddf8c632 abf4d55b075e b2ce801fddfe b368b6ac3ce3 c959bf2e869c c9fba6ba4e2e d783207cf649 d9a51e256f21 e3717a4e3753 local is a local subset ------------------------ remote will be last 25 heads of the local graph $ cd $TESTTMP/manyheads $ hg -R a debugdiscovery b \ > --debug \ > --local-as-revs 'first(heads(all()), 25)' \ > --config devel.discovery.randomize=false comparing with b query 1; heads searching for changes taking quick initial sample query 2; still undecided: 375, sample size is: 81 sampling from both directions query 3; still undecided: 3, sample size is: 3 3 total queries *s (glob) elapsed time: * seconds (glob) round-trips: 3 queries: 109 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 25 common: 0 missing: 25 remote heads: 1 common: 0 unknown: 1 local changesets: 400 common: 300 heads: 1 roots: 1 missing: 100 heads: 25 roots: 25 first undecided set: 400 heads: 25 roots: 1 common: 300 missing: 100 common heads: 3ee37d65064a both local and remove are subset ------------------------ remote will be last 25 heads of the local graph $ cd $TESTTMP/manyheads $ hg -R a debugdiscovery \ > --debug \ > --local-as-revs 'first(heads(all()), 25)' \ > --remote-as-revs 'last(heads(all()), 25)' \ > --config devel.discovery.randomize=false query 1; heads searching for changes taking quick initial sample query 2; still undecided: 375, sample size is: 81 sampling from both directions query 3; still undecided: 3, sample size is: 3 3 total queries in *s (glob) elapsed time: * seconds (glob) round-trips: 3 queries: 109 heads summary: total common heads: 1 also local heads: 0 also remote heads: 0 both: 0 local heads: 25 common: 0 missing: 25 remote heads: 25 common: 0 unknown: 25 local changesets: 400 common: 300 heads: 1 roots: 1 missing: 100 heads: 25 roots: 25 first undecided set: 400 heads: 25 roots: 1 common: 300 missing: 100 common heads: 3ee37d65064a Test -T json output ------------------- $ hg -R a debugdiscovery \ > -T json \ > --debug \ > --local-as-revs 'first(heads(all()), 25)' \ > --remote-as-revs 'last(heads(all()), 25)' \ > --config devel.discovery.randomize=false [ { "elapsed": *, (glob) "nb-common-heads": 1, "nb-common-heads-both": 0, "nb-common-heads-local": 0, "nb-common-heads-remote": 0, "nb-common-roots": 1, "nb-head-local": 25, "nb-head-local-missing": 25, "nb-head-remote": 25, "nb-head-remote-unknown": 25, "nb-ini_und": 400, "nb-ini_und-common": 300, "nb-ini_und-heads": 25, "nb-ini_und-missing": 100, "nb-ini_und-roots": 1, "nb-missing-heads": 25, "nb-missing-roots": 25, "nb-revs": 400, "nb-revs-common": 300, "nb-revs-missing": 100, "output": "query 1; heads\nsearching for changes\ntaking quick initial sample\nquery 2; still undecided: 375, sample size is: 81\nsampling from both directions\nquery 3; still undecided: 3, sample size is: 3\n3 total queries in *s\n", (glob) "total-queries": 109, "total-roundtrips": 3 } ]