Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
alist-org
GitHub Repository: alist-org/alist
Path: blob/main/pkg/utils/hash/gcid.go
1562 views
1
package hash_extend
2
3
import (
4
"crypto/sha1"
5
"encoding"
6
"fmt"
7
"hash"
8
"strconv"
9
10
"github.com/alist-org/alist/v3/pkg/utils"
11
)
12
13
var GCID = utils.RegisterHashWithParam("gcid", "GCID", 40, func(a ...any) hash.Hash {
14
var (
15
size int64
16
err error
17
)
18
if len(a) > 0 {
19
size, err = strconv.ParseInt(fmt.Sprint(a[0]), 10, 64)
20
if err != nil {
21
panic(err)
22
}
23
}
24
return NewGcid(size)
25
})
26
27
func NewGcid(size int64) hash.Hash {
28
calcBlockSize := func(j int64) int64 {
29
var psize int64 = 0x40000
30
for float64(j)/float64(psize) > 0x200 && psize < 0x200000 {
31
psize = psize << 1
32
}
33
return psize
34
}
35
36
return &gcid{
37
hash: sha1.New(),
38
hashState: sha1.New(),
39
blockSize: int(calcBlockSize(size)),
40
}
41
}
42
43
type gcid struct {
44
hash hash.Hash
45
hashState hash.Hash
46
blockSize int
47
48
offset int
49
}
50
51
func (h *gcid) Write(p []byte) (n int, err error) {
52
n = len(p)
53
for len(p) > 0 {
54
if h.offset < h.blockSize {
55
var lastSize = h.blockSize - h.offset
56
if lastSize > len(p) {
57
lastSize = len(p)
58
}
59
60
h.hashState.Write(p[:lastSize])
61
h.offset += lastSize
62
p = p[lastSize:]
63
}
64
65
if h.offset >= h.blockSize {
66
h.hash.Write(h.hashState.Sum(nil))
67
h.hashState.Reset()
68
h.offset = 0
69
}
70
}
71
return
72
}
73
74
func (h *gcid) Sum(b []byte) []byte {
75
if h.offset != 0 {
76
if hashm, ok := h.hash.(encoding.BinaryMarshaler); ok {
77
if hashum, ok := h.hash.(encoding.BinaryUnmarshaler); ok {
78
tempData, _ := hashm.MarshalBinary()
79
defer hashum.UnmarshalBinary(tempData)
80
h.hash.Write(h.hashState.Sum(nil))
81
}
82
}
83
}
84
return h.hash.Sum(b)
85
}
86
87
func (h *gcid) Reset() {
88
h.hash.Reset()
89
h.hashState.Reset()
90
}
91
92
func (h *gcid) Size() int {
93
return h.hash.Size()
94
}
95
96
func (h *gcid) BlockSize() int {
97
return h.blockSize
98
}
99
100