Skip to content

Commit 295eade

Browse files
committed
turn hamt keys into bytes instead of strings
1 parent d4e402c commit 295eade

File tree

4 files changed

+93
-46
lines changed

4 files changed

+93
-46
lines changed

cbor_gen.go

Lines changed: 66 additions & 24 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

hamt.go

Lines changed: 18 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -55,7 +55,7 @@ func NewNode(cs cbor.IpldStore, options ...Option) *Node {
5555
}
5656

5757
type KV struct {
58-
Key string
58+
Key []byte
5959
Value *cbg.Deferred
6060
}
6161

@@ -68,7 +68,7 @@ type Pointer struct {
6868
}
6969

7070
func (n *Node) Find(ctx context.Context, k string, out interface{}) error {
71-
return n.getValue(ctx, &hashBits{b: hash(k)}, k, func(kv *KV) error {
71+
return n.getValue(ctx, &hashBits{b: hash([]byte(k))}, k, func(kv *KV) error {
7272
// used to just see if the thing exists in the set
7373
if out == nil {
7474
return nil
@@ -88,15 +88,16 @@ func (n *Node) Find(ctx context.Context, k string, out interface{}) error {
8888

8989
func (n *Node) FindRaw(ctx context.Context, k string) ([]byte, error) {
9090
var ret []byte
91-
err := n.getValue(ctx, &hashBits{b: hash(k)}, k, func(kv *KV) error {
91+
err := n.getValue(ctx, &hashBits{b: hash([]byte(k))}, k, func(kv *KV) error {
9292
ret = kv.Value.Raw
9393
return nil
9494
})
9595
return ret, err
9696
}
9797

9898
func (n *Node) Delete(ctx context.Context, k string) error {
99-
return n.modifyValue(ctx, &hashBits{b: hash(k)}, k, nil)
99+
kb := []byte(k)
100+
return n.modifyValue(ctx, &hashBits{b: hash(kb)}, kb, nil)
100101
}
101102

102103
var ErrNotFound = fmt.Errorf("not found")
@@ -125,7 +126,7 @@ func (n *Node) getValue(ctx context.Context, hv *hashBits, k string, cb func(*KV
125126
}
126127

127128
for _, kv := range c.KVs {
128-
if kv.Key == k {
129+
if string(kv.Key) == k {
129130
return cb(kv)
130131
}
131132
}
@@ -215,12 +216,15 @@ func (n *Node) Flush(ctx context.Context) error {
215216
// SetRaw sets key k to cbor bytes raw
216217
func (n *Node) SetRaw(ctx context.Context, k string, raw []byte) error {
217218
d := &cbg.Deferred{Raw: raw}
218-
return n.modifyValue(ctx, &hashBits{b: hash(k)}, k, d)
219+
kb := []byte(k)
220+
return n.modifyValue(ctx, &hashBits{b: hash(kb)}, kb, d)
219221
}
220222

221223
func (n *Node) Set(ctx context.Context, k string, v interface{}) error {
222224
var d *cbg.Deferred
223225

226+
kb := []byte(k)
227+
224228
cm, ok := v.(cbg.CBORMarshaler)
225229
if ok {
226230
buf := new(bytes.Buffer)
@@ -236,7 +240,7 @@ func (n *Node) Set(ctx context.Context, k string, v interface{}) error {
236240
d = &cbg.Deferred{Raw: b}
237241
}
238242

239-
return n.modifyValue(ctx, &hashBits{b: hash(k)}, k, d)
243+
return n.modifyValue(ctx, &hashBits{b: hash(kb)}, kb, d)
240244
}
241245

242246
func (n *Node) cleanChild(chnd *Node, cindex byte) error {
@@ -273,7 +277,7 @@ func (n *Node) cleanChild(chnd *Node, cindex byte) error {
273277
}
274278
}
275279

276-
func (n *Node) modifyValue(ctx context.Context, hv *hashBits, k string, v *cbg.Deferred) error {
280+
func (n *Node) modifyValue(ctx context.Context, hv *hashBits, k []byte, v *cbg.Deferred) error {
277281
idx, err := hv.Next(n.bitWidth)
278282
if err != nil {
279283
return ErrMaxDepth
@@ -308,7 +312,7 @@ func (n *Node) modifyValue(ctx context.Context, hv *hashBits, k string, v *cbg.D
308312

309313
if v == nil {
310314
for i, p := range child.KVs {
311-
if p.Key == k {
315+
if bytes.Equal(p.Key, k) {
312316
if len(child.KVs) == 1 {
313317
return n.rmChild(cindex, idx)
314318
}
@@ -323,7 +327,7 @@ func (n *Node) modifyValue(ctx context.Context, hv *hashBits, k string, v *cbg.D
323327

324328
// check if key already exists
325329
for _, p := range child.KVs {
326-
if p.Key == k {
330+
if bytes.Equal(p.Key, k) {
327331
p.Value = v
328332
return nil
329333
}
@@ -356,7 +360,7 @@ func (n *Node) modifyValue(ctx context.Context, hv *hashBits, k string, v *cbg.D
356360
// otherwise insert the new element into the array in order
357361
np := &KV{Key: k, Value: v}
358362
for i := 0; i < len(child.KVs); i++ {
359-
if k < child.KVs[i].Key {
363+
if bytes.Compare(k, child.KVs[i].Key) < 0 {
360364
child.KVs = append(child.KVs[:i], append([]*KV{np}, child.KVs[i:]...)...)
361365
return nil
362366
}
@@ -365,7 +369,7 @@ func (n *Node) modifyValue(ctx context.Context, hv *hashBits, k string, v *cbg.D
365369
return nil
366370
}
367371

368-
func (n *Node) insertChild(idx int, k string, v *cbg.Deferred) error {
372+
func (n *Node) insertChild(idx int, k []byte, v *cbg.Deferred) error {
369373
if v == nil {
370374
return ErrNotFound
371375
}
@@ -441,7 +445,8 @@ func (n *Node) ForEach(ctx context.Context, f func(k string, val interface{}) er
441445
}
442446
} else {
443447
for _, kv := range p.KVs {
444-
if err := f(kv.Key, kv.Value); err != nil {
448+
// TODO: consider removing 'strings as keys' from every interface, go full-on bytes everywhere
449+
if err := f(string(kv.Key), kv.Value); err != nil {
445450
return err
446451
}
447452
}

hamt_test.go

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -55,15 +55,15 @@ func dotGraph(n *Node) {
5555
fmt.Println("}")
5656
}
5757

58-
var identityHash = func(k string) []byte {
58+
var identityHash = func(k []byte) []byte {
5959
res := make([]byte, 32)
60-
copy(res, []byte(k))
60+
copy(res, k)
6161
return res
6262
}
6363

64-
var shortIdentityHash = func(k string) []byte {
64+
var shortIdentityHash = func(k []byte) []byte {
6565
res := make([]byte, 16)
66-
copy(res, []byte(k))
66+
copy(res, k)
6767
return res
6868
}
6969

@@ -213,7 +213,7 @@ func dotGraphRec(n *Node, name *int) {
213213
} else {
214214
var names []string
215215
for _, pt := range p.KVs {
216-
names = append(names, pt.Key)
216+
names = append(names, string(pt.Key))
217217
}
218218
fmt.Printf("\tn%d -> n%s;\n", cur, strings.Join(names, "_"))
219219
}
@@ -250,8 +250,8 @@ func statsrec(n *Node, st *hamtStats) {
250250
}
251251

252252
func TestHash(t *testing.T) {
253-
h1 := hash("abcd")
254-
h2 := hash("abce")
253+
h1 := hash([]byte("abcd"))
254+
h2 := hash([]byte("abce"))
255255
if h1[0] == h2[0] && h1[1] == h2[1] && h1[3] == h2[3] {
256256
t.Fatal("Hash should give different strings different hash prefixes")
257257
}

hash.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -49,8 +49,8 @@ func (hb *hashBits) next(i int) int {
4949
}
5050
}
5151

52-
var hash = func(val string) []byte {
52+
var hash = func(val []byte) []byte {
5353
h := murmur3.New64()
54-
h.Write([]byte(val))
54+
h.Write(val)
5555
return h.Sum(nil)
5656
}

0 commit comments

Comments
 (0)