]> Cypherpunks repositories - gostls13.git/commitdiff
unique,internal/concurrent: add some more tests
authorMichael Anthony Knyszek <mknyszek@google.com>
Thu, 19 Sep 2024 15:43:14 +0000 (15:43 +0000)
committerGopher Robot <gobot@golang.org>
Thu, 26 Sep 2024 20:13:12 +0000 (20:13 +0000)
One is a test of unsafe.String usage, which was broken before CL 610738
was merged.

The other is trying to improve coverage of "near collision" scenarios in
the HashTrieMap where only the last few bits differ. This is intended to
catch off-by-one errors in iterating down the tree.

For #69534.

Change-Id: I3f302e148e81269a50e93b5edf83cafc2d291098
Reviewed-on: https://go-review.googlesource.com/c/go/+/614475
Auto-Submit: Michael Knyszek <mknyszek@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Ian Lance Taylor <iant@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
src/internal/concurrent/hashtriemap_test.go
src/unique/handle_test.go

index e233824c0f08fe4a2c56c26456c7a74101f0224d..498ead8c1d38f3e27171b5960d62990eabd9895a 100644 (file)
@@ -6,6 +6,7 @@ package concurrent
 
 import (
        "fmt"
+       "internal/abi"
        "math"
        "runtime"
        "strconv"
@@ -33,6 +34,23 @@ func TestHashTrieMapBadHash(t *testing.T) {
        })
 }
 
+func TestHashTrieMapTruncHash(t *testing.T) {
+       testHashTrieMap(t, func() *HashTrieMap[string, int] {
+               // Stub out the good hash function with a different terrible one
+               // (truncated hash). Everything should still work as expected.
+               // This is useful to test independently to catch issues with
+               // near collisions, where only the last few bits of the hash differ.
+               m := NewHashTrieMap[string, int]()
+               var mx map[string]int
+               mapType := abi.TypeOf(mx).MapType()
+               hasher := mapType.Hasher
+               m.keyHash = func(p unsafe.Pointer, n uintptr) uintptr {
+                       return hasher(p, n) & ((uintptr(1) << 4) - 1)
+               }
+               return m
+       })
+}
+
 func testHashTrieMap(t *testing.T, newMap func() *HashTrieMap[string, int]) {
        t.Run("LoadEmpty", func(t *testing.T) {
                m := newMap()
index 98a1b731cfad5680c6ae800183cdc41c35452ca6..e271770651b9a1e4a34cafc6e282f3ece825f876 100644 (file)
@@ -9,6 +9,7 @@ import (
        "internal/abi"
        "reflect"
        "runtime"
+       "strconv"
        "strings"
        "testing"
        "time"
@@ -138,3 +139,26 @@ func TestMakeClonesStrings(t *testing.T) {
        }
        runtime.KeepAlive(h)
 }
+
+func TestHandleUnsafeString(t *testing.T) {
+       var testData []string
+       for i := range 1024 {
+               testData = append(testData, strconv.Itoa(i))
+       }
+       var buf []byte
+       var handles []Handle[string]
+       for _, s := range testData {
+               if len(buf) < len(s) {
+                       buf = make([]byte, len(s)*2)
+               }
+               copy(buf, s)
+               sbuf := unsafe.String(&buf[0], len(s))
+               handles = append(handles, Make(sbuf))
+       }
+       for i, s := range testData {
+               h := Make(s)
+               if handles[i].Value() != h.Value() {
+                       t.Fatal("unsafe string improperly retained internally")
+               }
+       }
+}