github.com/mhmtszr/concurrent-swiss-map@v1.0.8/maphash/runtime.go (about) 1 // Copyright 2022 Dolthub, Inc. 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 // 15 // This file incorporates work covered by the following copyright and 16 // permission notice: 17 // 18 // Copyright 2022 The Go Authors. All rights reserved. 19 // Use of this source code is governed by a BSD-style 20 // license that can be found in the LICENSE file. 21 22 //go:build go1.18 || go1.19 23 // +build go1.18 go1.19 24 25 package maphash 26 27 import ( 28 "math/rand" 29 "unsafe" 30 ) 31 32 type hashfn func(unsafe.Pointer, uintptr) uintptr 33 34 func getRuntimeHasher[K comparable]() (h hashfn) { 35 a := any(make(map[K]struct{})) 36 i := (*mapiface)(unsafe.Pointer(&a)) 37 h = i.typ.hasher 38 return 39 } 40 41 //nolint:gosec 42 var hashSeed = rand.Int() 43 44 func newHashSeed() uintptr { 45 return uintptr(hashSeed) 46 } 47 48 // noescape hides a pointer from escape analysis. It is the identity function 49 // but escape analysis doesn't think the output depends on the input. 50 // noescape is inlined and currently compiles down to zero instructions. 51 // USE CAREFULLY! 52 // This was copied from the runtime (via pkg "strings"); see issues 23382 and 7921. 53 // 54 //go:nosplit 55 //go:nocheckptr 56 //nolint:staticcheck 57 func noescape(p unsafe.Pointer) unsafe.Pointer { 58 x := uintptr(p) 59 return unsafe.Pointer(x ^ 0) 60 } 61 62 type mapiface struct { 63 typ *maptype 64 val *hmap 65 } 66 67 // go/src/runtime/type.go 68 type maptype struct { 69 typ _type 70 key *_type 71 elem *_type 72 bucket *_type 73 // function for hashing keys (ptr to key, seed) -> hash 74 hasher func(unsafe.Pointer, uintptr) uintptr 75 keysize uint8 76 elemsize uint8 77 bucketsize uint16 78 flags uint32 79 } 80 81 // go/src/runtime/map.go 82 type hmap struct { 83 count int 84 flags uint8 85 B uint8 86 noverflow uint16 87 // hash seed 88 hash0 uint32 89 buckets unsafe.Pointer 90 oldbuckets unsafe.Pointer 91 nevacuate uintptr 92 // true type is *mapextra 93 // but we don't need this data 94 extra unsafe.Pointer 95 } 96 97 // go/src/runtime/type.go 98 type ( 99 tflag uint8 100 nameOff int32 101 typeOff int32 102 ) 103 104 // go/src/runtime/type.go 105 type _type struct { 106 size uintptr 107 ptrdata uintptr 108 hash uint32 109 tflag tflag 110 align uint8 111 fieldAlign uint8 112 kind uint8 113 equal func(unsafe.Pointer, unsafe.Pointer) bool 114 gcdata *byte 115 str nameOff 116 ptrToThis typeOff 117 }