wa-lang.org/wazero@v1.0.2/internal/wasm/binary/memory_test.go (about)

     1  package binary
     2  
     3  import (
     4  	"bytes"
     5  	"fmt"
     6  	"testing"
     7  
     8  	"wa-lang.org/wazero/internal/testing/require"
     9  	"wa-lang.org/wazero/internal/wasm"
    10  )
    11  
    12  func Test_newMemorySizer(t *testing.T) {
    13  	zero := uint32(0)
    14  	one := uint32(1)
    15  	limit := wasm.MemoryLimitPages
    16  
    17  	tests := []struct {
    18  		name                                       string
    19  		memoryCapacityFromMax                      bool
    20  		min                                        uint32
    21  		max                                        *uint32
    22  		expectedMin, expectedCapacity, expectedMax uint32
    23  	}{
    24  		{
    25  			name:             "min 0",
    26  			min:              zero,
    27  			max:              &limit,
    28  			expectedMin:      zero,
    29  			expectedCapacity: zero,
    30  			expectedMax:      limit,
    31  		},
    32  		{
    33  			name:             "min 0 defaults max to limit",
    34  			min:              zero,
    35  			expectedMin:      zero,
    36  			expectedCapacity: zero,
    37  			expectedMax:      limit,
    38  		},
    39  		{
    40  			name:             "min 0, max 0",
    41  			min:              zero,
    42  			max:              &zero,
    43  			expectedMin:      zero,
    44  			expectedCapacity: zero,
    45  			expectedMax:      zero,
    46  		},
    47  		{
    48  			name:             "min 0, max 1",
    49  			min:              zero,
    50  			max:              &one,
    51  			expectedMin:      zero,
    52  			expectedCapacity: zero,
    53  			expectedMax:      one,
    54  		},
    55  		{
    56  			name:                  "min 0, max 1 memoryCapacityFromMax",
    57  			memoryCapacityFromMax: true,
    58  			min:                   zero,
    59  			max:                   &one,
    60  			expectedMin:           zero,
    61  			expectedCapacity:      one,
    62  			expectedMax:           one,
    63  		},
    64  		{
    65  			name:             "min=max",
    66  			min:              one,
    67  			max:              &one,
    68  			expectedMin:      one,
    69  			expectedCapacity: one,
    70  			expectedMax:      one,
    71  		},
    72  	}
    73  
    74  	for _, tt := range tests {
    75  		tc := tt
    76  		t.Run(tc.name, func(t *testing.T) {
    77  			sizer := newMemorySizer(limit, tc.memoryCapacityFromMax)
    78  			min, capacity, max := sizer(tc.min, tc.max)
    79  			require.Equal(t, tc.expectedMin, min)
    80  			require.Equal(t, tc.expectedCapacity, capacity)
    81  			require.Equal(t, tc.expectedMax, max)
    82  		})
    83  	}
    84  }
    85  
    86  func TestMemoryType(t *testing.T) {
    87  	zero := uint32(0)
    88  	max := wasm.MemoryLimitPages
    89  
    90  	tests := []struct {
    91  		name     string
    92  		input    *wasm.Memory
    93  		expected []byte
    94  	}{
    95  		{
    96  			name:     "min 0",
    97  			input:    &wasm.Memory{Max: max, IsMaxEncoded: true},
    98  			expected: []byte{0x1, 0, 0x80, 0x80, 0x4},
    99  		},
   100  		{
   101  			name:     "min 0 default max",
   102  			input:    &wasm.Memory{Max: max},
   103  			expected: []byte{0x0, 0},
   104  		},
   105  		{
   106  			name:     "min 0, max 0",
   107  			input:    &wasm.Memory{Max: zero, IsMaxEncoded: true},
   108  			expected: []byte{0x1, 0, 0},
   109  		},
   110  		{
   111  			name:     "min=max",
   112  			input:    &wasm.Memory{Min: 1, Cap: 1, Max: 1, IsMaxEncoded: true},
   113  			expected: []byte{0x1, 1, 1},
   114  		},
   115  		{
   116  			name:     "min 0, max largest",
   117  			input:    &wasm.Memory{Max: max, IsMaxEncoded: true},
   118  			expected: []byte{0x1, 0, 0x80, 0x80, 0x4},
   119  		},
   120  		{
   121  			name:     "min largest max largest",
   122  			input:    &wasm.Memory{Min: max, Cap: max, Max: max, IsMaxEncoded: true},
   123  			expected: []byte{0x1, 0x80, 0x80, 0x4, 0x80, 0x80, 0x4},
   124  		},
   125  	}
   126  
   127  	for _, tt := range tests {
   128  		tc := tt
   129  
   130  		b := encodeMemory(tc.input)
   131  		t.Run(fmt.Sprintf("encode %s", tc.name), func(t *testing.T) {
   132  			require.Equal(t, tc.expected, b)
   133  		})
   134  
   135  		t.Run(fmt.Sprintf("decode %s", tc.name), func(t *testing.T) {
   136  			binary, err := decodeMemory(bytes.NewReader(b), newMemorySizer(max, false), max)
   137  			require.NoError(t, err)
   138  			require.Equal(t, binary, tc.input)
   139  		})
   140  	}
   141  }
   142  
   143  func TestDecodeMemoryType_Errors(t *testing.T) {
   144  	max := wasm.MemoryLimitPages
   145  
   146  	tests := []struct {
   147  		name        string
   148  		input       []byte
   149  		expectedErr string
   150  	}{
   151  		{
   152  			name:        "max < min",
   153  			input:       []byte{0x1, 0x80, 0x80, 0x4, 0},
   154  			expectedErr: "min 65536 pages (4 Gi) > max 0 pages (0 Ki)",
   155  		},
   156  		{
   157  			name:        "min > limit",
   158  			input:       []byte{0x0, 0xff, 0xff, 0xff, 0xff, 0xf},
   159  			expectedErr: "min 4294967295 pages (3 Ti) over limit of 65536 pages (4 Gi)",
   160  		},
   161  		{
   162  			name:        "max > limit",
   163  			input:       []byte{0x1, 0, 0xff, 0xff, 0xff, 0xff, 0xf},
   164  			expectedErr: "max 4294967295 pages (3 Ti) over limit of 65536 pages (4 Gi)",
   165  		},
   166  	}
   167  
   168  	for _, tt := range tests {
   169  		tc := tt
   170  
   171  		t.Run(tc.name, func(t *testing.T) {
   172  			_, err := decodeMemory(bytes.NewReader(tc.input), newMemorySizer(max, false), max)
   173  			require.EqualError(t, err, tc.expectedErr)
   174  		})
   175  	}
   176  }