github.com/go-asm/go@v1.21.1-0.20240213172139-40c5ead50c48/cmd/obj/s390x/rotate_test.go (about)

     1  // Copyright 2020 The Go Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  package s390x
     6  
     7  import (
     8  	"testing"
     9  )
    10  
    11  func TestRotateParamsMask(t *testing.T) {
    12  	tests := []struct {
    13  		start, end, amount uint8
    14  		inMask, outMask    uint64
    15  	}{
    16  		// start before end, no rotation
    17  		{start: 0, end: 63, amount: 0, inMask: ^uint64(0), outMask: ^uint64(0)},
    18  		{start: 1, end: 63, amount: 0, inMask: ^uint64(0) >> 1, outMask: ^uint64(0) >> 1},
    19  		{start: 0, end: 62, amount: 0, inMask: ^uint64(1), outMask: ^uint64(1)},
    20  		{start: 1, end: 62, amount: 0, inMask: ^uint64(3) >> 1, outMask: ^uint64(3) >> 1},
    21  
    22  		// end before start, no rotation
    23  		{start: 63, end: 0, amount: 0, inMask: 1<<63 | 1, outMask: 1<<63 | 1},
    24  		{start: 62, end: 0, amount: 0, inMask: 1<<63 | 3, outMask: 1<<63 | 3},
    25  		{start: 63, end: 1, amount: 0, inMask: 3<<62 | 1, outMask: 3<<62 | 1},
    26  		{start: 62, end: 1, amount: 0, inMask: 3<<62 | 3, outMask: 3<<62 | 3},
    27  
    28  		// rotation
    29  		{start: 32, end: 63, amount: 32, inMask: 0xffffffff00000000, outMask: 0x00000000ffffffff},
    30  		{start: 48, end: 15, amount: 16, inMask: 0xffffffff00000000, outMask: 0xffff00000000ffff},
    31  		{start: 0, end: 7, amount: -8 & 63, inMask: 0xff, outMask: 0xff << 56},
    32  	}
    33  	for i, test := range tests {
    34  		r := NewRotateParams(test.start, test.end, test.amount)
    35  		if m := r.OutMask(); m != test.outMask {
    36  			t.Errorf("out mask %v: want %#x, got %#x", i, test.outMask, m)
    37  		}
    38  		if m := r.InMask(); m != test.inMask {
    39  			t.Errorf("in mask %v: want %#x, got %#x", i, test.inMask, m)
    40  		}
    41  	}
    42  }
    43  
    44  func TestRotateParamsMerge(t *testing.T) {
    45  	tests := []struct {
    46  		// inputs
    47  		src  RotateParams
    48  		mask uint64
    49  
    50  		// results
    51  		in  *RotateParams
    52  		out *RotateParams
    53  	}{
    54  		{
    55  			src:  RotateParams{Start: 48, End: 15, Amount: 16},
    56  			mask: 0xffffffffffffffff,
    57  			in:   &RotateParams{Start: 48, End: 15, Amount: 16},
    58  			out:  &RotateParams{Start: 48, End: 15, Amount: 16},
    59  		},
    60  		{
    61  			src:  RotateParams{Start: 16, End: 47, Amount: 0},
    62  			mask: 0x00000000ffffffff,
    63  			in:   &RotateParams{Start: 32, End: 47, Amount: 0},
    64  			out:  &RotateParams{Start: 32, End: 47, Amount: 0},
    65  		},
    66  		{
    67  			src:  RotateParams{Start: 16, End: 47, Amount: 0},
    68  			mask: 0xffff00000000ffff,
    69  			in:   nil,
    70  			out:  nil,
    71  		},
    72  		{
    73  			src:  RotateParams{Start: 0, End: 63, Amount: 0},
    74  			mask: 0xf7f0000000000000,
    75  			in:   nil,
    76  			out:  nil,
    77  		},
    78  		{
    79  			src:  RotateParams{Start: 0, End: 63, Amount: 1},
    80  			mask: 0x000000000000ff00,
    81  			in:   &RotateParams{Start: 47, End: 54, Amount: 1},
    82  			out:  &RotateParams{Start: 48, End: 55, Amount: 1},
    83  		},
    84  		{
    85  			src:  RotateParams{Start: 32, End: 63, Amount: 32},
    86  			mask: 0xffff00000000ffff,
    87  			in:   &RotateParams{Start: 32, End: 47, Amount: 32},
    88  			out:  &RotateParams{Start: 48, End: 63, Amount: 32},
    89  		},
    90  		{
    91  			src:  RotateParams{Start: 0, End: 31, Amount: 32},
    92  			mask: 0x8000000000000000,
    93  			in:   nil,
    94  			out:  &RotateParams{Start: 0, End: 0, Amount: 32},
    95  		},
    96  		{
    97  			src:  RotateParams{Start: 0, End: 31, Amount: 32},
    98  			mask: 0x0000000080000000,
    99  			in:   &RotateParams{Start: 0, End: 0, Amount: 32},
   100  			out:  nil,
   101  		},
   102  	}
   103  
   104  	eq := func(x, y *RotateParams) bool {
   105  		if x == nil && y == nil {
   106  			return true
   107  		}
   108  		if x == nil || y == nil {
   109  			return false
   110  		}
   111  		return *x == *y
   112  	}
   113  
   114  	for _, test := range tests {
   115  		if r := test.src.InMerge(test.mask); !eq(r, test.in) {
   116  			t.Errorf("%v merged with %#x (input): want %v, got %v", test.src, test.mask, test.in, r)
   117  		}
   118  		if r := test.src.OutMerge(test.mask); !eq(r, test.out) {
   119  			t.Errorf("%v merged with %#x (output): want %v, got %v", test.src, test.mask, test.out, r)
   120  		}
   121  	}
   122  }