1 // Copyright 2014 The Go Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style
3 // license that can be found in the LICENSE file.
5 // This file provides a compact encoding of
6 // a map of Mercurial hashes to Git hashes.
20 // hashMap is a map of Mercurial hashes to Git hashes.
26 // newHashMap takes a file handle that contains a map of Mercurial to Git
27 // hashes. The file should be a sequence of pairs of little-endian encoded
28 // uint32s, representing a hgHash and a gitHash respectively.
29 // The sequence must be sorted by hgHash.
30 // The file must remain open for as long as the returned hashMap is used.
31 func newHashMap(f *os.File) (*hashMap, error) {
36 return &hashMap{file: f, entries: int(fi.Size() / 8)}, nil
39 // Lookup finds an hgHash in the map that matches the given prefix, and returns
40 // its corresponding gitHash. The prefix must be at least 8 characters long.
41 func (m *hashMap) Lookup(s string) gitHash {
45 hg, err := hgHashFromString(s)
51 sort.Search(m.entries, func(i int) bool {
52 n, err := m.file.ReadAt(b, int64(i*8))
57 panic(io.ErrUnexpectedEOF)
59 v := hgHash(binary.LittleEndian.Uint32(b[:4]))
61 git = gitHash(binary.LittleEndian.Uint32(b[4:]))
68 // hgHash represents the lower (leftmost) 32 bits of a Mercurial hash.
71 func (h hgHash) String() string {
72 return intToHash(int64(h))
75 func hgHashFromString(s string) (hgHash, error) {
77 return 0, fmt.Errorf("string too small: len(s) = %d", len(s))
80 i, err := strconv.ParseInt(hash, 16, 64)
87 // gitHash represents the leftmost 28 bits of a Git hash in its upper 28 bits,
88 // and it encodes hash's repository in the lower 4 bits.
91 func (h gitHash) Hash() string {
92 return intToHash(int64(h))[:7]
95 func (h gitHash) Repo() string {
96 return repo(h & 0xF).String()
99 func intToHash(i int64) string {
100 s := strconv.FormatInt(i, 16)
102 s = strings.Repeat("0", 8-len(s)) + s
107 // repo represents a Go Git repository.
124 func (r repo) String() string {
125 return map[repo]string{
128 repoCrypto: "crypto",
131 repoMobile: "mobile",