gem5  [DEVELOP-FOR-23.0]
All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Pages
matrix.test.cc
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2022 Arm Limited
3  * All rights reserved
4  *
5  * The license below extends only to copyright in the software and shall
6  * not be construed as granting a license to any other intellectual
7  * property including but not limited to intellectual property relating
8  * to a hardware implementation of the functionality of the software
9  * licensed hereunder. You may use the software subject to the license
10  * terms below provided that you ensure that this notice is replicated
11  * unmodified and in its entirety in all distributions of the software,
12  * modified or unmodified, in source code or in binary form.
13  *
14  * Redistribution and use in source and binary forms, with or without
15  * modification, are permitted provided that the following conditions are
16  * met: redistributions of source code must retain the above copyright
17  * notice, this list of conditions and the following disclaimer;
18  * redistributions in binary form must reproduce the above copyright
19  * notice, this list of conditions and the following disclaimer in the
20  * documentation and/or other materials provided with the distribution;
21  * neither the name of the copyright holders nor the names of its
22  * contributors may be used to endorse or promote products derived from
23  * this software without specific prior written permission.
24  *
25  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
26  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
27  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
28  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
29  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
30  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
31  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
32  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
33  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
34  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
35  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
36  */
37 
38 #include <gtest/gtest.h>
39 
40 #include "arch/arm/matrix.hh"
41 
42 using namespace gem5;
43 
44 TEST(Matrix, Size)
45 {
46  {
47  // Minimum size
48  MatStore<1, 1> mat;
49  ASSERT_EQ(1, mat.linearSize());
50  }
51 
52  {
53  // Medium size
54  constexpr size_t x_size = MaxMatRegRowLenInBytes / 2;
55  constexpr size_t y_size = MaxMatRegRows / 2;
57  ASSERT_EQ(x_size * y_size, mat.linearSize());
58  }
59 
60  {
61  // Maximum size
64  }
65 }
66 
68 {
69  constexpr size_t size = 16;
71  auto tile = mat.asTile<uint8_t>(0);
72 
73  // Initializing with non-zero value
74  for (auto i = 0; i < size; i++) {
75  for (auto j = 0; j < size; j++) {
76  tile[i][j] = 0xAA;
77  }
78  }
79 
80  // zeroing the matrix
81  mat.zero();
82 
83  // checking if every matrix element is set to zero
84  for (auto i = 0; i < size; i++) {
85  for (auto j = 0; j < size; j++) {
86  ASSERT_EQ(tile[i][j], 0);
87  }
88  }
89 }
90 
91 TEST(Matrix, ZeroTiles)
92 {
93  constexpr size_t size = 16;
95  auto byte_tile = mat.asTile<uint8_t>(0);
96 
97  // Initializing the whole tile with non-zero value
98  for (auto i = 0; i < size; i++) {
99  for (auto j = 0; j < size; j++) {
100  byte_tile[i][j] = 0xAA;
101  }
102  }
103 
104  // zeroing the half-word tile 0 of matrix
105  auto half_word_tile = mat.asTile<uint16_t>(0);
106  half_word_tile.zero();
107 
108  // Check that every element of half-word tile 0 is zero
109  for (auto i = 0; i < size / 2; i++) {
110  for (auto j = 0; j < size / 2; j++) {
111  ASSERT_EQ(half_word_tile[i][j], 0);
112  }
113  }
114 
115  // Check that every element of half-word tile 1 is 0xAAAA (note the
116  // double width of the element)
117  half_word_tile = mat.asTile<uint16_t>(1);
118  for (auto i = 0; i < size / 2; i++) {
119  for (auto j = 0; j < size / 2; j++) {
120  ASSERT_EQ(half_word_tile[i][j], 0xAAAA);
121  }
122  }
123 
124  // Check if every matrix element on an even row is set to zero
125  for (auto i = 0; i < size; i += 2) {
126  for (auto j = 0; j < size; j++) {
127  ASSERT_EQ(byte_tile[i][j], 0);
128  }
129  }
130 
131  // Check if every matrix element on an odd row is set to 0xAA
132  for (auto i = 1; i < size; i += 2) {
133  for (auto j = 0; j < size; j++) {
134  ASSERT_EQ(byte_tile[i][j], 0xAA);
135  }
136  }
137 }
138 
139 TEST(Matrix, ZeroTileHSlice)
140 {
141  constexpr size_t size = 16;
143  auto byte_tile = mat.asTile<uint8_t>(0);
144 
145  // Initializing the whole tile with non-zero value
146  for (auto i = 0; i < size; i++) {
147  for (auto j = 0; j < size; j++) {
148  byte_tile[i][j] = 0xAA;
149  }
150  }
151 
152  // zeroing the 0th row of half-word tile 0
153  auto half_word_tile = mat.asTile<uint16_t>(0);
154  auto row = half_word_tile.asHSlice(0);
155  row.zero();
156 
157  // Check that every element of the row is zero
158  for (auto i = 0; i < size / 2; i++) {
159  ASSERT_EQ(row[i], 0);
160  }
161 
162  // Check that every element of row 1 is 0xAAAA
163  row = half_word_tile.asHSlice(1);
164  for (auto i = 0; i < size / 2; i++) {
165  ASSERT_EQ(row[i], 0xAAAA);
166  }
167 
168  // Check that row 0 of the byte tile is zero, and that all remaining
169  // rows are unaffected
170  for (auto i = 0; i < size; i++) {
171  for (auto j = 0; j < size; j++) {
172  if (i == 0) {
173  ASSERT_EQ(byte_tile[i][j], 0);
174  } else {
175  ASSERT_EQ(byte_tile[i][j], 0xAA);
176  }
177  }
178  }
179 }
180 
181 TEST(Matrix, ZeroTileVSlice)
182 {
183  constexpr size_t size = 16;
185  auto byte_tile = mat.asTile<uint8_t>(0);
186 
187  // Initializing the whole tile with non-zero value
188  for (auto i = 0; i < size; i++) {
189  for (auto j = 0; j < size; j++) {
190  byte_tile[i][j] = 0xAA;
191  }
192  }
193 
194  // zeroing the 0th column of half-word tile 0
195  auto half_word_tile = mat.asTile<uint16_t>(0);
196  auto col = half_word_tile.asVSlice(0);
197  col.zero();
198 
199  // Check that every element of the column is zero
200  for (auto i = 0; i < size / 2; i++) {
201  ASSERT_EQ(col[i], 0);
202  }
203 
204  // Check that every element of column 1 is 0xAAAA
205  col = half_word_tile.asVSlice(1);
206  for (auto i = 0; i < size / 2; i++) {
207  ASSERT_EQ(col[i], 0xAAAA);
208  }
209 
210  // Check that elements 0 & 1 of the byte tile are zero for even rows,
211  // and that all remaining elements are unaffected
212  for (auto i = 0; i < size; i++) {
213  for (auto j = 0; j < size; j++) {
214  if (i % 2 == 0 && (j == 0 || j == 1)) {
215  ASSERT_EQ(byte_tile[i][j], 0);
216  } else {
217  ASSERT_EQ(byte_tile[i][j], 0xAA);
218  }
219  }
220  }
221 }
222 
223 TEST(Matrix, ZeroHSlice)
224 {
225  constexpr size_t size = 16;
227  auto byte_tile = mat.asTile<uint8_t>(0);
228 
229  // Initializing the whole tile with non-zero value
230  for (auto i = 0; i < size; i++) {
231  for (auto j = 0; j < size; j++) {
232  byte_tile[i][j] = 0xAA;
233  }
234  }
235 
236  // Now we get a row directly from the matrix (as words, because it
237  // should make no difference), zero it
238  auto row = mat.asHSlice<uint32_t>(4);
239  row.zero();
240 
241  // Check that every element of the row is zero
242  for (auto i = 0; i < size / 4; i++) {
243  ASSERT_EQ(row[i], 0);
244  }
245 
246  // Check that row 4 of the byte tile is zero, and that all remaining
247  // rows are unaffected
248  for (auto i = 0; i < size; i++) {
249  for (auto j = 0; j < size; j++) {
250  if (i == 4) {
251  ASSERT_EQ(byte_tile[i][j], 0);
252  } else {
253  ASSERT_EQ(byte_tile[i][j], 0xAA);
254  }
255  }
256  }
257 }
258 
259 TEST(Matrix, ZeroVSlice)
260 {
261  constexpr size_t size = 16;
263  auto byte_tile = mat.asTile<uint8_t>(0);
264 
265  // Initializing the whole tile with non-zero value
266  for (auto i = 0; i < size; i++) {
267  for (auto j = 0; j < size; j++) {
268  byte_tile[i][j] = 0xAA;
269  }
270  }
271 
272  // Now we get a column directly from the matrix, zero it
273  auto col = mat.asVSlice<uint8_t>(4);
274  col.zero();
275 
276  // Check that every element of the column is zero
277  for (auto i = 0; i < size; i++) {
278  ASSERT_EQ(col[i], 0);
279  }
280 
281  // Check that col 4 of the byte tile is zero, and that all remaining
282  // rows are unaffected
283  for (auto i = 0; i < size; i++) {
284  for (auto j = 0; j < size; j++) {
285  if (j == 4) {
286  ASSERT_EQ(byte_tile[i][j], 0);
287  } else {
288  ASSERT_EQ(byte_tile[i][j], 0xAA);
289  }
290  }
291  }
292 
293  // Now we repeat with a wider element type too. Reinitializing the
294  // whole tile with non-zero value
295  for (auto i = 0; i < size; i++) {
296  for (auto j = 0; j < size; j++) {
297  byte_tile[i][j] = 0xAA;
298  }
299  }
300 
301  // Now we get a word-wide column directly from the matrix, zero it
302  auto wide_col = mat.asVSlice<uint32_t>(1);
303  wide_col.zero();
304 
305  // Check that every element of the column is zero
306  for (auto i = 0; i < size; i++) {
307  ASSERT_EQ(wide_col[i], 0);
308  }
309 
310  // Check that cols 4-7 of the byte tile are zero, and that all
311  // remaining rows are unaffected
312  for (auto i = 0; i < size; i++) {
313  for (auto j = 0; j < size; j++) {
314  if (j >= 4 && j <= 7) {
315  ASSERT_EQ(byte_tile[i][j], 0);
316  } else {
317  ASSERT_EQ(byte_tile[i][j], 0xAA);
318  }
319  }
320  }
321 }
322 
323 class TwoDifferentMatRegs : public testing::Test
324 {
325  protected:
326  static constexpr size_t size = 4;
327 
330 
331  void
332  SetUp() override
333  {
334  auto tile1 = mat1.asTile<uint8_t>(0);
335  auto tile2 = mat2.asTile<uint8_t>(0);
336 
337  // Initializing with non-zero value for matrix 1
338  for (auto i = 0; i < size; i++) {
339  for (auto j = 0; j < size; j++) {
340  tile1[i][j] = 0xAA;
341  }
342  }
343 
344  // Initializing with zero value for matrix 2
345  for (auto i = 0; i < size; i++) {
346  for (auto j = 0; j < size; j++) {
347  tile2[i][j] = 0x0;
348  }
349  }
350  }
351 };
352 
353 // Testing operator=
355 {
356  // Copying the matrix
357  mat2 = mat1;
358 
359  auto tile2 = mat2.asTile<uint8_t>(0);
360 
361  // Checking if matrix 2 elements are 0xAA
362  for (auto i = 0; i < size; i++) {
363  for (auto j = 0; j < size; j++) {
364  ASSERT_EQ(tile2[i][j], 0xAA);
365  }
366  }
367 }
368 
369 // Testing operator==
371 {
372  // Equality check
373  ASSERT_TRUE(mat1 == mat1);
374  ASSERT_TRUE(mat2 == mat2);
375  ASSERT_FALSE(mat1 == mat2);
376 }
377 
378 // Testing operator!=
380 {
381  // Inequality check
382  ASSERT_FALSE(mat1 != mat1);
383  ASSERT_FALSE(mat2 != mat2);
384  ASSERT_TRUE(mat1 != mat2);
385 }
386 
387 // Testing operator<<
389 {
390  {
391  std::ostringstream stream;
392  stream << mat1;
393  ASSERT_EQ(stream.str(), "[aaaaaaaa_aaaaaaaa_aaaaaaaa_aaaaaaaa]");
394  }
395 
396  {
397  std::ostringstream stream;
398  stream << mat2;
399  ASSERT_EQ(stream.str(), "[00000000_00000000_00000000_00000000]");
400  }
401 }
402 
403 // Testing ParseParam
405 {
406  ParseParam<decltype(mat1)> parser;
407 
408  parser.parse("bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb", mat1);
409  parser.parse("cccccccccccccccccccccccccccccccc", mat2);
410 
411  for (auto i = 0; i < size; i++) {
412  for (auto j = 0; j < size; j++) {
413  ASSERT_EQ(mat1.asTile<uint8_t>(0)[i][j], 0xbb);
414  ASSERT_EQ(mat2.asTile<uint8_t>(0)[i][j], 0xcc);
415  }
416  }
417 }
418 
419 // Testing ParseParam Underflow
420 TEST_F(TwoDifferentMatRegs, ParseParamUnderflow)
421 {
422  ParseParam<decltype(mat1)> parser;
423 
424  // We should trigger a fatal() here.
425  EXPECT_ANY_THROW(parser.parse("b", mat1));
426 }
427 
428 // Testing ParseParam Overflow
429 TEST_F(TwoDifferentMatRegs, ParseParamOverflow)
430 {
431  ParseParam<decltype(mat1)> parser;
432 
433  // We should trigger a fatal() here.
434  EXPECT_ANY_THROW(parser.parse("bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb", mat1));
435 }
436 
437 // Testing ShowParam
439 {
440  ShowParam<decltype(mat1)> parser;
441 
442  {
443  std::stringstream ss;
444  parser.show(ss, mat1);
445  ASSERT_EQ(ss.str(), "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa");
446  }
447 
448  {
449  std::stringstream ss;
450  parser.show(ss, mat2);
451  ASSERT_EQ(ss.str(), "00000000000000000000000000000000");
452  }
453 }
TwoDifferentMatRegs::mat1
MatStore< size, size > mat1
Definition: matrix.test.cc:328
gem5::MatStore::asHSlice
auto asHSlice(size_t row_idx)
Definition: matrix.hh:468
gem5::MatStore
Backing store for matrices.
Definition: matrix.hh:129
gem5::ruby::Matrix
std::vector< std::vector< std::vector< int > > > Matrix
Definition: Topology.hh:58
gem5::MatStore::asTile
auto asTile(size_t index)
Definition: matrix.hh:461
gem5::ShowParam::show
static void show(std::ostream &os, const T &value)
Definition: serialize_handlers.hh:127
gem5::MatStore::zero
void zero()
Definition: matrix.hh:408
TEST
TEST(Matrix, Size)
Definition: matrix.test.cc:44
gem5::ArmISA::i
Bitfield< 7 > i
Definition: misc_types.hh:67
matrix.hh
TwoDifferentMatRegs::mat2
MatStore< size, size > mat2
Definition: matrix.test.cc:329
gem5::ShowParam
Definition: serialize_handlers.hh:125
TEST_F
TEST_F(TwoDifferentMatRegs, Assignment)
Definition: matrix.test.cc:354
gem5::MaxMatRegRowLenInBytes
constexpr unsigned MaxMatRegRowLenInBytes
Definition: matrix.hh:124
gem5::ArmISA::j
Bitfield< 24 > j
Definition: misc_types.hh:57
gem5::MatStore::asVSlice
auto asVSlice(size_t col_idx)
Definition: matrix.hh:475
TwoDifferentMatRegs
Definition: matrix.test.cc:323
gem5::MatStore::linearSize
static constexpr size_t linearSize()
Definition: matrix.hh:393
ss
std::stringstream ss
Definition: trace.test.cc:45
TwoDifferentMatRegs::SetUp
void SetUp() override
Definition: matrix.test.cc:332
gem5::ArmISA::cc_reg::Zero
constexpr RegId Zero
Definition: cc.hh:99
gem5::ParseParam
Definition: serialize_handlers.hh:78
gem5
Reference material can be found at the JEDEC website: UFS standard http://www.jedec....
Definition: gpu_translation_state.hh:37
gem5::MaxMatRegRows
constexpr unsigned MaxMatRegRows
Definition: matrix.hh:125

Generated on Sun Jul 30 2023 01:56:49 for gem5 by doxygen 1.8.17