github.com/go-ng/xatomic@v0.0.0-20230519181013-85c0ec87e55f/map_test.go (about)

     1  package xatomic
     2  
     3  import (
     4  	"testing"
     5  	"unsafe"
     6  
     7  	"github.com/stretchr/testify/require"
     8  )
     9  
    10  type hmap struct{}
    11  
    12  //go:linkname hmap_incrnoverflow runtime.(*hmap).incrnoverflow
    13  func hmap_incrnoverflow(h *hmap)
    14  
    15  func TestMapIsPointer(t *testing.T) {
    16  	m := map[int]int{
    17  		1: 1,
    18  		2: 2,
    19  	}
    20  
    21  	t.Run("Store&Load", func(t *testing.T) {
    22  		var storage map[int]int
    23  		StoreMap(&storage, m)
    24  		require.Equal(t, m, storage)
    25  		v := LoadMap(&storage)
    26  		require.Equal(t, m, v)
    27  	})
    28  
    29  	// The test above should be good enough, but just in case some additional tests
    30  	// go below:
    31  
    32  	t.Run("call_internal_method", func(t *testing.T) {
    33  		// Rechecking the assumption that `map` is actually a pointer
    34  		// (to the map header structure).
    35  		//
    36  		// Assuming that it may segfault or something, if something is wrong:
    37  		hdr := (*hmap)(unref((unsafe.Pointer)(&m)))
    38  		hmap_incrnoverflow(hdr)
    39  	})
    40  }
    41  
    42  var v map[int]int
    43  var r map[int]int
    44  
    45  func Benchmark(b *testing.B) {
    46  	m := map[int]int{
    47  		1: 1,
    48  		2: 2,
    49  	}
    50  
    51  	b.Run("noop", func(b *testing.B) {
    52  		for i := 0; i < b.N; i++ {
    53  		}
    54  	})
    55  
    56  	b.Run("Map", func(b *testing.B) {
    57  		b.Run("Store", func(b *testing.B) {
    58  			b.Run("atomic", func(b *testing.B) {
    59  				for i := 0; i < b.N; i++ {
    60  					StoreMap(&v, m)
    61  				}
    62  			})
    63  			b.Run("unatomic", func(b *testing.B) {
    64  				for i := 0; i < b.N; i++ {
    65  					v = m
    66  				}
    67  			})
    68  		})
    69  		b.Run("Load", func(b *testing.B) {
    70  			b.Run("atomic", func(b *testing.B) {
    71  				for i := 0; i < b.N; i++ {
    72  					r = LoadMap(&v)
    73  				}
    74  			})
    75  			b.Run("unatomic", func(b *testing.B) {
    76  				for i := 0; i < b.N; i++ {
    77  					r = v
    78  				}
    79  			})
    80  		})
    81  	})
    82  }