tests: test eq and ne operators of fields and values against arbitrary objects and...
[babeltrace.git] / tests / bindings / python / bt2 / test_field.py
CommitLineData
d2d857a8
MJ
1#
2# Copyright (C) 2019 EfficiOS Inc.
3#
4# This program is free software; you can redistribute it and/or
5# modify it under the terms of the GNU General Public License
6# as published by the Free Software Foundation; only version 2
7# of the License.
8#
9# This program is distributed in the hope that it will be useful,
10# but WITHOUT ANY WARRANTY; without even the implied warranty of
11# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12# GNU General Public License for more details.
13#
14# You should have received a copy of the GNU General Public License
15# along with this program; if not, write to the Free Software
16# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
17#
18
9cf643d1
PP
19from functools import partial, partialmethod
20import operator
21import unittest
9cf643d1
PP
22import math
23import copy
b0bdda42 24import itertools
73051d46 25import collections
9cf643d1 26import bt2
1abe38eb 27from utils import get_default_trace_class, create_const_field
9cf643d1
PP
28
29
cfbd7cf3 30_COMP_BINOPS = (operator.eq, operator.ne)
9cf643d1
PP
31
32
1eccc498
SM
33# Create and return a stream with the field classes part of its stream packet
34# context.
35#
36# The stream is part of a dummy trace created from trace class `tc`.
37
cfbd7cf3 38
1eccc498
SM
39def _create_stream(tc, ctx_field_classes):
40 packet_context_fc = tc.create_structure_field_class()
41 for name, fc in ctx_field_classes:
42 packet_context_fc.append_member(name, fc)
43
44 trace = tc()
cfbd7cf3
FD
45 stream_class = tc.create_stream_class(
46 packet_context_field_class=packet_context_fc, supports_packets=True
47 )
1eccc498
SM
48
49 stream = trace.create_stream(stream_class)
50 return stream
51
52
53# Create a field of the given field class.
54#
55# The field is part of a dummy stream, itself part of a dummy trace created
56# from trace class `tc`.
57
cfbd7cf3 58
1eccc498
SM
59def _create_field(tc, field_class):
60 field_name = 'field'
61 stream = _create_stream(tc, [(field_name, field_class)])
62 packet = stream.create_packet()
63 return packet.context_field[field_name]
64
65
66# Create a field of type string.
67#
68# The field is part of a dummy stream, itself part of a dummy trace created
69# from trace class `tc`. It is made out of a dummy string field class.
70
cfbd7cf3 71
1eccc498
SM
72def _create_string_field(tc):
73 field_name = 'string_field'
74 stream = _create_stream(tc, [(field_name, tc.create_string_field_class())])
75 packet = stream.create_packet()
76 return packet.context_field[field_name]
77
78
79# Create a field of type static array of ints.
80#
81# The field is part of a dummy stream, itself part of a dummy trace created
82# from trace class `tc`. It is made out of a dummy static array field class,
83# with a dummy integer field class as element class.
84
cfbd7cf3 85
1eccc498
SM
86def _create_int_array_field(tc, length):
87 elem_fc = tc.create_signed_integer_field_class(32)
88 fc = tc.create_static_array_field_class(elem_fc, length)
89 field_name = 'int_array'
90 stream = _create_stream(tc, [(field_name, fc)])
91 packet = stream.create_packet()
92 return packet.context_field[field_name]
93
94
95# Create a field of type dynamic array of ints.
96#
97# The field is part of a dummy stream, itself part of a dummy trace created
98# from trace class `tc`. It is made out of a dummy static array field class,
99# with a dummy integer field class as element and length classes.
100
cfbd7cf3 101
1eccc498
SM
102def _create_dynamic_array(tc):
103 elem_fc = tc.create_signed_integer_field_class(32)
104 len_fc = tc.create_signed_integer_field_class(32)
105 fc = tc.create_dynamic_array_field_class(elem_fc)
106 field_name = 'int_dyn_array'
107 stream = _create_stream(tc, [('thelength', len_fc), (field_name, fc)])
108 packet = stream.create_packet()
109 packet.context_field[field_name].length = 3
110 return packet.context_field[field_name]
111
112
113# Create a field of type array of (empty) structures.
114#
115# The field is part of a dummy stream, itself part of a dummy trace created
116# from trace class `tc`. It is made out of a dummy static array field class,
117# with a dummy struct field class as element class.
118
cfbd7cf3 119
1eccc498
SM
120def _create_struct_array_field(tc, length):
121 elem_fc = tc.create_structure_field_class()
122 fc = tc.create_static_array_field_class(elem_fc, length)
123 field_name = 'struct_array'
124 stream = _create_stream(tc, [(field_name, fc)])
125 packet = stream.create_packet()
126 return packet.context_field[field_name]
127
128
ead8c3d4
PP
129class BitArrayFieldTestCase(unittest.TestCase):
130 def _create_field(self):
131 return _create_field(self._tc, self._tc.create_bit_array_field_class(24))
132
133 def setUp(self):
134 self._tc = get_default_trace_class()
135 self._def_value = 15497
136 self._def = self._create_field()
137 self._def.value_as_integer = self._def_value
138 self._def_new_value = 101542
139
140 def test_assign_invalid_type(self):
141 with self.assertRaises(TypeError):
142 self._def.value_as_integer = 'onze'
143
144 def test_assign(self):
145 self._def.value_as_integer = 199
146 self.assertEqual(self._def.value_as_integer, 199)
147
148 def test_assign_masked(self):
149 self._def.value_as_integer = 0xE1549BB
150 self.assertEqual(self._def.value_as_integer, 0xE1549BB & ((1 << 24) - 1))
151
152 def test_eq(self):
153 other = self._create_field()
154 other.value_as_integer = self._def_value
155 self.assertEqual(self._def, other)
156
157 def test_ne_same_type(self):
158 other = self._create_field()
159 other.value_as_integer = self._def_value - 1
160 self.assertNotEqual(self._def, other)
161
162 def test_ne_diff_type(self):
163 self.assertNotEqual(self._def, self._def_value)
164
165 def test_len(self):
166 self.assertEqual(len(self._def), 24)
167
168 def test_str(self):
169 self.assertEqual(str(self._def), str(self._def_value))
170
171 def test_repr(self):
172 self.assertEqual(repr(self._def), repr(self._def_value))
173
174
21368027
PP
175# Base class for numeric field test cases.
176#
177# To be compatible with this base class, a derived class must, in its
178# setUp() method:
179#
180# * Set `self._def` to a field object with an arbitrary value.
181# * Set `self._def_value` to the equivalent value of `self._def`.
1eccc498 182class _TestNumericField:
21368027
PP
183 # Tries the binary operation `op`:
184 #
185 # 1. Between `self._def`, which is a field object, and `rhs`.
186 # 2. Between `self._def_value`, which is the raw value of
187 # `self._def`, and `rhs`.
188 #
189 # Returns the results of 1. and 2.
190 #
191 # If there's an exception while performing 1. or 2., asserts that
192 # both operations raised exceptions, that both exceptions have the
193 # same type, and returns `None` for both results.
9cf643d1 194 def _binop(self, op, rhs):
21368027
PP
195 type_rexc = None
196 type_rvexc = None
9cf643d1
PP
197 comp_value = rhs
198
21368027 199 # try with field object
9cf643d1
PP
200 try:
201 r = op(self._def, rhs)
202 except Exception as e:
21368027 203 type_rexc = type(e)
9cf643d1 204
21368027 205 # try with value
9cf643d1
PP
206 try:
207 rv = op(self._def_value, comp_value)
208 except Exception as e:
21368027 209 type_rvexc = type(e)
9cf643d1 210
21368027 211 if type_rexc is not None or type_rvexc is not None:
9cf643d1
PP
212 # at least one of the operations raised an exception: in
213 # this case both operations should have raised the same
214 # type of exception (division by zero, bit shift with a
215 # floating point number operand, etc.)
21368027 216 self.assertIs(type_rexc, type_rvexc)
9cf643d1
PP
217 return None, None
218
219 return r, rv
220
21368027
PP
221 # Tries the unary operation `op`:
222 #
223 # 1. On `self._def`, which is a field object.
224 # 2. On `self._def_value`, which is the value of `self._def`.
225 #
226 # Returns the results of 1. and 2.
227 #
228 # If there's an exception while performing 1. or 2., asserts that
229 # both operations raised exceptions, that both exceptions have the
230 # same type, and returns `None` for both results.
9cf643d1 231 def _unaryop(self, op):
21368027
PP
232 type_rexc = None
233 type_rvexc = None
9cf643d1 234
21368027 235 # try with field object
9cf643d1
PP
236 try:
237 r = op(self._def)
238 except Exception as e:
21368027 239 type_rexc = type(e)
9cf643d1 240
21368027 241 # try with value
9cf643d1
PP
242 try:
243 rv = op(self._def_value)
244 except Exception as e:
21368027 245 type_rvexc = type(e)
9cf643d1 246
21368027 247 if type_rexc is not None or type_rvexc is not None:
9cf643d1
PP
248 # at least one of the operations raised an exception: in
249 # this case both operations should have raised the same
250 # type of exception (division by zero, bit shift with a
251 # floating point number operand, etc.)
21368027 252 self.assertIs(type_rexc, type_rvexc)
9cf643d1
PP
253 return None, None
254
255 return r, rv
256
21368027
PP
257 # Tests that the unary operation `op` gives results with the same
258 # type for both `self._def` and `self._def_value`.
9cf643d1
PP
259 def _test_unaryop_type(self, op):
260 r, rv = self._unaryop(op)
261
262 if r is None:
263 return
264
265 self.assertIsInstance(r, type(rv))
266
21368027
PP
267 # Tests that the unary operation `op` gives results with the same
268 # value for both `self._def` and `self._def_value`. This uses the
269 # __eq__() operator of `self._def`.
9cf643d1
PP
270 def _test_unaryop_value(self, op):
271 r, rv = self._unaryop(op)
272
273 if r is None:
274 return
275
276 self.assertEqual(r, rv)
277
21368027
PP
278 # Tests that the unary operation `op`, when applied to `self._def`,
279 # does not change its underlying BT object address.
9cf643d1
PP
280 def _test_unaryop_addr_same(self, op):
281 addr_before = self._def.addr
282 self._unaryop(op)
283 self.assertEqual(self._def.addr, addr_before)
284
21368027
PP
285 # Tests that the unary operation `op`, when applied to `self._def`,
286 # does not change its value.
9cf643d1 287 def _test_unaryop_value_same(self, op):
e1c6bebd 288 value_before = copy.copy(self._def_value)
9cf643d1 289 self._unaryop(op)
e1c6bebd 290 self.assertEqual(self._def, value_before)
9cf643d1 291
21368027
PP
292 # Tests that the binary operation `op` gives results with the same
293 # type for both `self._def` and `self._def_value`.
9cf643d1
PP
294 def _test_binop_type(self, op, rhs):
295 r, rv = self._binop(op, rhs)
296
297 if r is None:
298 return
299
300 if op in _COMP_BINOPS:
301 # __eq__() and __ne__() always return a 'bool' object
302 self.assertIsInstance(r, bool)
303 else:
304 self.assertIsInstance(r, type(rv))
305
21368027
PP
306 # Tests that the binary operation `op` gives results with the same
307 # value for both `self._def` and `self._def_value`. This uses the
308 # __eq__() operator of `self._def`.
9cf643d1
PP
309 def _test_binop_value(self, op, rhs):
310 r, rv = self._binop(op, rhs)
311
312 if r is None:
313 return
314
315 self.assertEqual(r, rv)
316
21368027
PP
317 # Tests that the binary operation `op`, when applied to `self._def`,
318 # does not change its underlying BT object address.
9cf643d1
PP
319 def _test_binop_lhs_addr_same(self, op, rhs):
320 addr_before = self._def.addr
321 r, rv = self._binop(op, rhs)
322 self.assertEqual(self._def.addr, addr_before)
323
21368027
PP
324 # Tests that the binary operation `op`, when applied to `self._def`,
325 # does not change its value.
9cf643d1 326 def _test_binop_lhs_value_same(self, op, rhs):
fd00253e 327 value_before = copy.copy(self._def_value)
9cf643d1 328 r, rv = self._binop(op, rhs)
e1c6bebd 329 self.assertEqual(self._def, value_before)
9cf643d1 330
21368027
PP
331 # The methods below which take the `test_cb` and/or `op` parameters
332 # are meant to be used with one of the _test_binop_*() functions
333 # above as `test_cb` and a binary operator function as `op`.
334 #
335 # For example:
336 #
337 # self._test_binop_rhs_pos_int(self._test_binop_value,
338 # operator.add)
339 #
340 # This tests that a numeric field object added to a positive integer
341 # value gives a result with the expected value.
342 #
343 # `vint` and `vfloat` mean a signed integer value object and a real
344 # value object.
345
7e481c9e 346 def _test_binop_unknown(self, op):
9cf643d1
PP
347 class A:
348 pass
349
7e481c9e
SM
350 # Operators == and != are defined when comparing the field to an
351 # arbitrary object.
352 if op is operator.eq:
353 self.assertIs(op(self._def, A()), False)
354 elif op is operator.ne:
355 self.assertIs(op(self._def, A()), True)
356 else:
357 # But not other operators.
358 with self.assertRaises(TypeError):
359 op(self._def, A())
360
361 def _test_binop_none(self, op):
362 # Operators == and != are defined when comparing the field to None.
363 if op is operator.eq:
364 self.assertIs(op(self._def, None), False)
365 elif op is operator.ne:
366 self.assertIs(op(self._def, None), True)
367 else:
368 # But not other operators.
369 with self.assertRaises(TypeError):
370 op(self._def, None)
9cf643d1 371
9cf643d1
PP
372 def _test_binop_rhs_false(self, test_cb, op):
373 test_cb(op, False)
374
375 def _test_binop_rhs_true(self, test_cb, op):
376 test_cb(op, True)
377
378 def _test_binop_rhs_pos_int(self, test_cb, op):
379 test_cb(op, 2)
380
381 def _test_binop_rhs_neg_int(self, test_cb, op):
382 test_cb(op, -23)
383
384 def _test_binop_rhs_zero_int(self, test_cb, op):
385 test_cb(op, 0)
386
387 def _test_binop_rhs_pos_vint(self, test_cb, op):
388 test_cb(op, bt2.create_value(2))
389
390 def _test_binop_rhs_neg_vint(self, test_cb, op):
391 test_cb(op, bt2.create_value(-23))
392
393 def _test_binop_rhs_zero_vint(self, test_cb, op):
394 test_cb(op, bt2.create_value(0))
395
396 def _test_binop_rhs_pos_float(self, test_cb, op):
397 test_cb(op, 2.2)
398
399 def _test_binop_rhs_neg_float(self, test_cb, op):
400 test_cb(op, -23.4)
401
402 def _test_binop_rhs_zero_float(self, test_cb, op):
403 test_cb(op, 0.0)
404
405 def _test_binop_rhs_pos_vfloat(self, test_cb, op):
406 test_cb(op, bt2.create_value(2.2))
407
408 def _test_binop_rhs_neg_vfloat(self, test_cb, op):
409 test_cb(op, bt2.create_value(-23.4))
410
411 def _test_binop_rhs_zero_vfloat(self, test_cb, op):
412 test_cb(op, bt2.create_value(0.0))
413
00512c97 414 def _test_binop_rhs_complex(self, test_cb, op):
cfbd7cf3 415 test_cb(op, -23 + 19j)
00512c97
PP
416
417 def _test_binop_rhs_zero_complex(self, test_cb, op):
418 test_cb(op, 0j)
419
9cf643d1
PP
420 def _test_binop_type_false(self, op):
421 self._test_binop_rhs_false(self._test_binop_type, op)
422
423 def _test_binop_type_true(self, op):
424 self._test_binop_rhs_true(self._test_binop_type, op)
425
426 def _test_binop_type_pos_int(self, op):
427 self._test_binop_rhs_pos_int(self._test_binop_type, op)
428
429 def _test_binop_type_neg_int(self, op):
430 self._test_binop_rhs_neg_int(self._test_binop_type, op)
431
432 def _test_binop_type_zero_int(self, op):
433 self._test_binop_rhs_zero_int(self._test_binop_type, op)
434
435 def _test_binop_type_pos_vint(self, op):
436 self._test_binop_rhs_pos_vint(self._test_binop_type, op)
437
438 def _test_binop_type_neg_vint(self, op):
439 self._test_binop_rhs_neg_vint(self._test_binop_type, op)
440
441 def _test_binop_type_zero_vint(self, op):
442 self._test_binop_rhs_zero_vint(self._test_binop_type, op)
443
444 def _test_binop_type_pos_float(self, op):
445 self._test_binop_rhs_pos_float(self._test_binop_type, op)
446
447 def _test_binop_type_neg_float(self, op):
448 self._test_binop_rhs_neg_float(self._test_binop_type, op)
449
450 def _test_binop_type_zero_float(self, op):
451 self._test_binop_rhs_zero_float(self._test_binop_type, op)
452
453 def _test_binop_type_pos_vfloat(self, op):
454 self._test_binop_rhs_pos_vfloat(self._test_binop_type, op)
455
456 def _test_binop_type_neg_vfloat(self, op):
457 self._test_binop_rhs_neg_vfloat(self._test_binop_type, op)
458
459 def _test_binop_type_zero_vfloat(self, op):
460 self._test_binop_rhs_zero_vfloat(self._test_binop_type, op)
461
00512c97
PP
462 def _test_binop_type_complex(self, op):
463 self._test_binop_rhs_complex(self._test_binop_type, op)
464
465 def _test_binop_type_zero_complex(self, op):
466 self._test_binop_rhs_zero_complex(self._test_binop_type, op)
467
9cf643d1
PP
468 def _test_binop_value_false(self, op):
469 self._test_binop_rhs_false(self._test_binop_value, op)
470
471 def _test_binop_value_true(self, op):
472 self._test_binop_rhs_true(self._test_binop_value, op)
473
474 def _test_binop_value_pos_int(self, op):
475 self._test_binop_rhs_pos_int(self._test_binop_value, op)
476
477 def _test_binop_value_neg_int(self, op):
478 self._test_binop_rhs_neg_int(self._test_binop_value, op)
479
480 def _test_binop_value_zero_int(self, op):
481 self._test_binop_rhs_zero_int(self._test_binop_value, op)
482
483 def _test_binop_value_pos_vint(self, op):
484 self._test_binop_rhs_pos_vint(self._test_binop_value, op)
485
486 def _test_binop_value_neg_vint(self, op):
487 self._test_binop_rhs_neg_vint(self._test_binop_value, op)
488
489 def _test_binop_value_zero_vint(self, op):
490 self._test_binop_rhs_zero_vint(self._test_binop_value, op)
491
492 def _test_binop_value_pos_float(self, op):
493 self._test_binop_rhs_pos_float(self._test_binop_value, op)
494
495 def _test_binop_value_neg_float(self, op):
496 self._test_binop_rhs_neg_float(self._test_binop_value, op)
497
498 def _test_binop_value_zero_float(self, op):
499 self._test_binop_rhs_zero_float(self._test_binop_value, op)
500
501 def _test_binop_value_pos_vfloat(self, op):
502 self._test_binop_rhs_pos_vfloat(self._test_binop_value, op)
503
504 def _test_binop_value_neg_vfloat(self, op):
505 self._test_binop_rhs_neg_vfloat(self._test_binop_value, op)
506
507 def _test_binop_value_zero_vfloat(self, op):
508 self._test_binop_rhs_zero_vfloat(self._test_binop_value, op)
509
00512c97
PP
510 def _test_binop_value_complex(self, op):
511 self._test_binop_rhs_complex(self._test_binop_value, op)
512
513 def _test_binop_value_zero_complex(self, op):
514 self._test_binop_rhs_zero_complex(self._test_binop_value, op)
515
9cf643d1
PP
516 def _test_binop_lhs_addr_same_false(self, op):
517 self._test_binop_rhs_false(self._test_binop_lhs_addr_same, op)
518
519 def _test_binop_lhs_addr_same_true(self, op):
520 self._test_binop_rhs_true(self._test_binop_lhs_addr_same, op)
521
522 def _test_binop_lhs_addr_same_pos_int(self, op):
523 self._test_binop_rhs_pos_int(self._test_binop_lhs_addr_same, op)
524
525 def _test_binop_lhs_addr_same_neg_int(self, op):
526 self._test_binop_rhs_neg_int(self._test_binop_lhs_addr_same, op)
527
528 def _test_binop_lhs_addr_same_zero_int(self, op):
529 self._test_binop_rhs_zero_int(self._test_binop_lhs_addr_same, op)
530
531 def _test_binop_lhs_addr_same_pos_vint(self, op):
532 self._test_binop_rhs_pos_vint(self._test_binop_lhs_addr_same, op)
533
534 def _test_binop_lhs_addr_same_neg_vint(self, op):
535 self._test_binop_rhs_neg_vint(self._test_binop_lhs_addr_same, op)
536
537 def _test_binop_lhs_addr_same_zero_vint(self, op):
538 self._test_binop_rhs_zero_vint(self._test_binop_lhs_addr_same, op)
539
540 def _test_binop_lhs_addr_same_pos_float(self, op):
541 self._test_binop_rhs_pos_float(self._test_binop_lhs_addr_same, op)
542
543 def _test_binop_lhs_addr_same_neg_float(self, op):
544 self._test_binop_rhs_neg_float(self._test_binop_lhs_addr_same, op)
545
546 def _test_binop_lhs_addr_same_zero_float(self, op):
547 self._test_binop_rhs_zero_float(self._test_binop_lhs_addr_same, op)
548
549 def _test_binop_lhs_addr_same_pos_vfloat(self, op):
550 self._test_binop_rhs_pos_vfloat(self._test_binop_lhs_addr_same, op)
551
552 def _test_binop_lhs_addr_same_neg_vfloat(self, op):
553 self._test_binop_rhs_neg_vfloat(self._test_binop_lhs_addr_same, op)
554
555 def _test_binop_lhs_addr_same_zero_vfloat(self, op):
556 self._test_binop_rhs_zero_vfloat(self._test_binop_lhs_addr_same, op)
557
00512c97
PP
558 def _test_binop_lhs_addr_same_complex(self, op):
559 self._test_binop_rhs_complex(self._test_binop_lhs_addr_same, op)
560
561 def _test_binop_lhs_addr_same_zero_complex(self, op):
562 self._test_binop_rhs_zero_complex(self._test_binop_lhs_addr_same, op)
563
9cf643d1
PP
564 def _test_binop_lhs_value_same_false(self, op):
565 self._test_binop_rhs_false(self._test_binop_lhs_value_same, op)
566
567 def _test_binop_lhs_value_same_true(self, op):
568 self._test_binop_rhs_true(self._test_binop_lhs_value_same, op)
569
570 def _test_binop_lhs_value_same_pos_int(self, op):
571 self._test_binop_rhs_pos_int(self._test_binop_lhs_value_same, op)
572
573 def _test_binop_lhs_value_same_neg_int(self, op):
574 self._test_binop_rhs_neg_int(self._test_binop_lhs_value_same, op)
575
576 def _test_binop_lhs_value_same_zero_int(self, op):
577 self._test_binop_rhs_zero_int(self._test_binop_lhs_value_same, op)
578
579 def _test_binop_lhs_value_same_pos_vint(self, op):
580 self._test_binop_rhs_pos_vint(self._test_binop_lhs_value_same, op)
581
582 def _test_binop_lhs_value_same_neg_vint(self, op):
583 self._test_binop_rhs_neg_vint(self._test_binop_lhs_value_same, op)
584
585 def _test_binop_lhs_value_same_zero_vint(self, op):
586 self._test_binop_rhs_zero_vint(self._test_binop_lhs_value_same, op)
587
588 def _test_binop_lhs_value_same_pos_float(self, op):
589 self._test_binop_rhs_pos_float(self._test_binop_lhs_value_same, op)
590
591 def _test_binop_lhs_value_same_neg_float(self, op):
592 self._test_binop_rhs_neg_float(self._test_binop_lhs_value_same, op)
593
594 def _test_binop_lhs_value_same_zero_float(self, op):
595 self._test_binop_rhs_zero_float(self._test_binop_lhs_value_same, op)
596
597 def _test_binop_lhs_value_same_pos_vfloat(self, op):
598 self._test_binop_rhs_pos_vfloat(self._test_binop_lhs_value_same, op)
599
600 def _test_binop_lhs_value_same_neg_vfloat(self, op):
601 self._test_binop_rhs_neg_vfloat(self._test_binop_lhs_value_same, op)
602
603 def _test_binop_lhs_value_same_zero_vfloat(self, op):
604 self._test_binop_rhs_zero_vfloat(self._test_binop_lhs_value_same, op)
605
00512c97
PP
606 def _test_binop_lhs_value_same_complex(self, op):
607 self._test_binop_rhs_complex(self._test_binop_lhs_value_same, op)
608
609 def _test_binop_lhs_value_same_zero_complex(self, op):
610 self._test_binop_rhs_zero_complex(self._test_binop_lhs_value_same, op)
611
9cf643d1
PP
612 def test_bool_op(self):
613 self.assertEqual(bool(self._def), bool(self._def_value))
614
615 def test_int_op(self):
616 self.assertEqual(int(self._def), int(self._def_value))
617
618 def test_float_op(self):
619 self.assertEqual(float(self._def), float(self._def_value))
620
621 def test_complex_op(self):
622 self.assertEqual(complex(self._def), complex(self._def_value))
623
624 def test_str_op(self):
625 self.assertEqual(str(self._def), str(self._def_value))
626
dda659b3
FD
627 def test_hash_op(self):
628 with self.assertRaises(TypeError):
629 hash(self._def)
630
631 def test_const_hash_op(self):
632 self.assertEqual(hash(self._def_const), hash(self._def_value))
633
634 def test_const_hash_dict(self):
635 my_dict = {}
636 my_dict[self._def_const] = 'my_value'
637 self.assertEqual(my_dict[self._def_value], 'my_value')
638
9cf643d1 639 def test_eq_none(self):
1eccc498
SM
640 # Ignore this lint error:
641 # E711 comparison to None should be 'if cond is None:'
642 # since this is what we want to test (even though not good practice).
cfbd7cf3 643 self.assertFalse(self._def == None) # noqa: E711
9cf643d1
PP
644
645 def test_ne_none(self):
1eccc498
SM
646 # Ignore this lint error:
647 # E711 comparison to None should be 'if cond is not None:'
648 # since this is what we want to test (even though not good practice).
cfbd7cf3 649 self.assertTrue(self._def != None) # noqa: E711
742e4747 650
9cf643d1 651
21368027
PP
652# This is a list of binary operators used for
653# _inject_numeric_testing_methods().
654#
655# Each entry is a pair of binary operator name (used as part of the
656# created testing method's name) and operator function.
9cf643d1
PP
657_BINOPS = (
658 ('lt', operator.lt),
659 ('le', operator.le),
660 ('eq', operator.eq),
661 ('ne', operator.ne),
662 ('ge', operator.ge),
663 ('gt', operator.gt),
664 ('add', operator.add),
665 ('radd', lambda a, b: operator.add(b, a)),
666 ('and', operator.and_),
667 ('rand', lambda a, b: operator.and_(b, a)),
668 ('floordiv', operator.floordiv),
669 ('rfloordiv', lambda a, b: operator.floordiv(b, a)),
670 ('lshift', operator.lshift),
671 ('rlshift', lambda a, b: operator.lshift(b, a)),
672 ('mod', operator.mod),
673 ('rmod', lambda a, b: operator.mod(b, a)),
674 ('mul', operator.mul),
675 ('rmul', lambda a, b: operator.mul(b, a)),
676 ('or', operator.or_),
677 ('ror', lambda a, b: operator.or_(b, a)),
678 ('pow', operator.pow),
679 ('rpow', lambda a, b: operator.pow(b, a)),
680 ('rshift', operator.rshift),
681 ('rrshift', lambda a, b: operator.rshift(b, a)),
682 ('sub', operator.sub),
683 ('rsub', lambda a, b: operator.sub(b, a)),
684 ('truediv', operator.truediv),
685 ('rtruediv', lambda a, b: operator.truediv(b, a)),
686 ('xor', operator.xor),
687 ('rxor', lambda a, b: operator.xor(b, a)),
688)
689
690
21368027
PP
691# This is a list of unary operators used for
692# _inject_numeric_testing_methods().
693#
694# Each entry is a pair of unary operator name (used as part of the
695# created testing method's name) and operator function.
9cf643d1
PP
696_UNARYOPS = (
697 ('neg', operator.neg),
698 ('pos', operator.pos),
699 ('abs', operator.abs),
700 ('invert', operator.invert),
701 ('round', round),
702 ('round_0', partial(round, ndigits=0)),
703 ('round_1', partial(round, ndigits=1)),
704 ('round_2', partial(round, ndigits=2)),
705 ('round_3', partial(round, ndigits=3)),
706 ('ceil', math.ceil),
707 ('floor', math.floor),
708 ('trunc', math.trunc),
709)
710
711
21368027
PP
712# This function injects a bunch of testing methods to a numeric
713# field test case.
714#
715# It is meant to be used like this:
716#
717# _inject_numeric_testing_methods(MyNumericFieldTestCase)
718#
719# This function injects:
720#
721# * One testing method for each _TestNumericField._test_binop_*()
722# method, for each binary operator in the _BINOPS tuple.
723#
724# * One testing method for each _TestNumericField._test_unaryop*()
725# method, for each unary operator in the _UNARYOPS tuple.
9cf643d1
PP
726def _inject_numeric_testing_methods(cls):
727 def test_binop_name(suffix):
728 return 'test_binop_{}_{}'.format(name, suffix)
729
9cf643d1
PP
730 def test_unaryop_name(suffix):
731 return 'test_unaryop_{}_{}'.format(name, suffix)
732
733 # inject testing methods for each binary operation
734 for name, binop in _BINOPS:
cfbd7cf3
FD
735 setattr(
736 cls,
7e481c9e
SM
737 test_binop_name('unknown'),
738 partialmethod(_TestNumericField._test_binop_unknown, op=binop),
cfbd7cf3
FD
739 )
740 setattr(
741 cls,
7e481c9e
SM
742 test_binop_name('none'),
743 partialmethod(_TestNumericField._test_binop_none, op=binop),
cfbd7cf3
FD
744 )
745 setattr(
746 cls,
747 test_binop_name('type_true'),
748 partialmethod(_TestNumericField._test_binop_type_true, op=binop),
749 )
750 setattr(
751 cls,
752 test_binop_name('type_pos_int'),
753 partialmethod(_TestNumericField._test_binop_type_pos_int, op=binop),
754 )
755 setattr(
756 cls,
757 test_binop_name('type_pos_vint'),
758 partialmethod(_TestNumericField._test_binop_type_pos_vint, op=binop),
759 )
760 setattr(
761 cls,
762 test_binop_name('value_true'),
763 partialmethod(_TestNumericField._test_binop_value_true, op=binop),
764 )
765 setattr(
766 cls,
767 test_binop_name('value_pos_int'),
768 partialmethod(_TestNumericField._test_binop_value_pos_int, op=binop),
769 )
770 setattr(
771 cls,
772 test_binop_name('value_pos_vint'),
773 partialmethod(_TestNumericField._test_binop_value_pos_vint, op=binop),
774 )
775 setattr(
776 cls,
777 test_binop_name('lhs_addr_same_true'),
778 partialmethod(_TestNumericField._test_binop_lhs_addr_same_true, op=binop),
779 )
780 setattr(
781 cls,
782 test_binop_name('lhs_addr_same_pos_int'),
783 partialmethod(
784 _TestNumericField._test_binop_lhs_addr_same_pos_int, op=binop
785 ),
786 )
787 setattr(
788 cls,
789 test_binop_name('lhs_addr_same_pos_vint'),
790 partialmethod(
791 _TestNumericField._test_binop_lhs_addr_same_pos_vint, op=binop
792 ),
793 )
794 setattr(
795 cls,
796 test_binop_name('lhs_value_same_true'),
797 partialmethod(_TestNumericField._test_binop_lhs_value_same_true, op=binop),
798 )
799 setattr(
800 cls,
801 test_binop_name('lhs_value_same_pos_int'),
802 partialmethod(
803 _TestNumericField._test_binop_lhs_value_same_pos_int, op=binop
804 ),
805 )
806 setattr(
807 cls,
808 test_binop_name('lhs_value_same_pos_vint'),
809 partialmethod(
810 _TestNumericField._test_binop_lhs_value_same_pos_vint, op=binop
811 ),
812 )
813 setattr(
814 cls,
815 test_binop_name('type_neg_int'),
816 partialmethod(_TestNumericField._test_binop_type_neg_int, op=binop),
817 )
818 setattr(
819 cls,
820 test_binop_name('type_neg_vint'),
821 partialmethod(_TestNumericField._test_binop_type_neg_vint, op=binop),
822 )
823 setattr(
824 cls,
825 test_binop_name('value_neg_int'),
826 partialmethod(_TestNumericField._test_binop_value_neg_int, op=binop),
827 )
828 setattr(
829 cls,
830 test_binop_name('value_neg_vint'),
831 partialmethod(_TestNumericField._test_binop_value_neg_vint, op=binop),
832 )
833 setattr(
834 cls,
835 test_binop_name('lhs_addr_same_neg_int'),
836 partialmethod(
837 _TestNumericField._test_binop_lhs_addr_same_neg_int, op=binop
838 ),
839 )
840 setattr(
841 cls,
842 test_binop_name('lhs_addr_same_neg_vint'),
843 partialmethod(
844 _TestNumericField._test_binop_lhs_addr_same_neg_vint, op=binop
845 ),
846 )
847 setattr(
848 cls,
849 test_binop_name('lhs_value_same_neg_int'),
850 partialmethod(
851 _TestNumericField._test_binop_lhs_value_same_neg_int, op=binop
852 ),
853 )
854 setattr(
855 cls,
856 test_binop_name('lhs_value_same_neg_vint'),
857 partialmethod(
858 _TestNumericField._test_binop_lhs_value_same_neg_vint, op=binop
859 ),
860 )
861 setattr(
862 cls,
863 test_binop_name('type_false'),
864 partialmethod(_TestNumericField._test_binop_type_false, op=binop),
865 )
866 setattr(
867 cls,
868 test_binop_name('type_zero_int'),
869 partialmethod(_TestNumericField._test_binop_type_zero_int, op=binop),
870 )
871 setattr(
872 cls,
873 test_binop_name('type_zero_vint'),
874 partialmethod(_TestNumericField._test_binop_type_zero_vint, op=binop),
875 )
876 setattr(
877 cls,
878 test_binop_name('value_false'),
879 partialmethod(_TestNumericField._test_binop_value_false, op=binop),
880 )
881 setattr(
882 cls,
883 test_binop_name('value_zero_int'),
884 partialmethod(_TestNumericField._test_binop_value_zero_int, op=binop),
885 )
886 setattr(
887 cls,
888 test_binop_name('value_zero_vint'),
889 partialmethod(_TestNumericField._test_binop_value_zero_vint, op=binop),
890 )
891 setattr(
892 cls,
893 test_binop_name('lhs_addr_same_false'),
894 partialmethod(_TestNumericField._test_binop_lhs_addr_same_false, op=binop),
895 )
896 setattr(
897 cls,
898 test_binop_name('lhs_addr_same_zero_int'),
899 partialmethod(
900 _TestNumericField._test_binop_lhs_addr_same_zero_int, op=binop
901 ),
902 )
903 setattr(
904 cls,
905 test_binop_name('lhs_addr_same_zero_vint'),
906 partialmethod(
907 _TestNumericField._test_binop_lhs_addr_same_zero_vint, op=binop
908 ),
909 )
910 setattr(
911 cls,
912 test_binop_name('lhs_value_same_false'),
913 partialmethod(_TestNumericField._test_binop_lhs_value_same_false, op=binop),
914 )
915 setattr(
916 cls,
917 test_binop_name('lhs_value_same_zero_int'),
918 partialmethod(
919 _TestNumericField._test_binop_lhs_value_same_zero_int, op=binop
920 ),
921 )
922 setattr(
923 cls,
924 test_binop_name('lhs_value_same_zero_vint'),
925 partialmethod(
926 _TestNumericField._test_binop_lhs_value_same_zero_vint, op=binop
927 ),
928 )
929 setattr(
930 cls,
931 test_binop_name('type_pos_float'),
932 partialmethod(_TestNumericField._test_binop_type_pos_float, op=binop),
933 )
934 setattr(
935 cls,
936 test_binop_name('type_neg_float'),
937 partialmethod(_TestNumericField._test_binop_type_neg_float, op=binop),
938 )
939 setattr(
940 cls,
941 test_binop_name('type_pos_vfloat'),
942 partialmethod(_TestNumericField._test_binop_type_pos_vfloat, op=binop),
943 )
944 setattr(
945 cls,
946 test_binop_name('type_neg_vfloat'),
947 partialmethod(_TestNumericField._test_binop_type_neg_vfloat, op=binop),
948 )
949 setattr(
950 cls,
951 test_binop_name('value_pos_float'),
952 partialmethod(_TestNumericField._test_binop_value_pos_float, op=binop),
953 )
954 setattr(
955 cls,
956 test_binop_name('value_neg_float'),
957 partialmethod(_TestNumericField._test_binop_value_neg_float, op=binop),
958 )
959 setattr(
960 cls,
961 test_binop_name('value_pos_vfloat'),
962 partialmethod(_TestNumericField._test_binop_value_pos_vfloat, op=binop),
963 )
964 setattr(
965 cls,
966 test_binop_name('value_neg_vfloat'),
967 partialmethod(_TestNumericField._test_binop_value_neg_vfloat, op=binop),
968 )
969 setattr(
970 cls,
971 test_binop_name('lhs_addr_same_pos_float'),
972 partialmethod(
973 _TestNumericField._test_binop_lhs_addr_same_pos_float, op=binop
974 ),
975 )
976 setattr(
977 cls,
978 test_binop_name('lhs_addr_same_neg_float'),
979 partialmethod(
980 _TestNumericField._test_binop_lhs_addr_same_neg_float, op=binop
981 ),
982 )
983 setattr(
984 cls,
985 test_binop_name('lhs_addr_same_pos_vfloat'),
986 partialmethod(
987 _TestNumericField._test_binop_lhs_addr_same_pos_vfloat, op=binop
988 ),
989 )
990 setattr(
991 cls,
992 test_binop_name('lhs_addr_same_neg_vfloat'),
993 partialmethod(
994 _TestNumericField._test_binop_lhs_addr_same_neg_vfloat, op=binop
995 ),
996 )
997 setattr(
998 cls,
999 test_binop_name('lhs_value_same_pos_float'),
1000 partialmethod(
1001 _TestNumericField._test_binop_lhs_value_same_pos_float, op=binop
1002 ),
1003 )
1004 setattr(
1005 cls,
1006 test_binop_name('lhs_value_same_neg_float'),
1007 partialmethod(
1008 _TestNumericField._test_binop_lhs_value_same_neg_float, op=binop
1009 ),
1010 )
1011 setattr(
1012 cls,
1013 test_binop_name('lhs_value_same_pos_vfloat'),
1014 partialmethod(
1015 _TestNumericField._test_binop_lhs_value_same_pos_vfloat, op=binop
1016 ),
1017 )
1018 setattr(
1019 cls,
1020 test_binop_name('lhs_value_same_neg_vfloat'),
1021 partialmethod(
1022 _TestNumericField._test_binop_lhs_value_same_neg_vfloat, op=binop
1023 ),
1024 )
1025 setattr(
1026 cls,
1027 test_binop_name('type_zero_float'),
1028 partialmethod(_TestNumericField._test_binop_type_zero_float, op=binop),
1029 )
1030 setattr(
1031 cls,
1032 test_binop_name('type_zero_vfloat'),
1033 partialmethod(_TestNumericField._test_binop_type_zero_vfloat, op=binop),
1034 )
1035 setattr(
1036 cls,
1037 test_binop_name('value_zero_float'),
1038 partialmethod(_TestNumericField._test_binop_value_zero_float, op=binop),
1039 )
1040 setattr(
1041 cls,
1042 test_binop_name('value_zero_vfloat'),
1043 partialmethod(_TestNumericField._test_binop_value_zero_vfloat, op=binop),
1044 )
1045 setattr(
1046 cls,
1047 test_binop_name('lhs_addr_same_zero_float'),
1048 partialmethod(
1049 _TestNumericField._test_binop_lhs_addr_same_zero_float, op=binop
1050 ),
1051 )
1052 setattr(
1053 cls,
1054 test_binop_name('lhs_addr_same_zero_vfloat'),
1055 partialmethod(
1056 _TestNumericField._test_binop_lhs_addr_same_zero_vfloat, op=binop
1057 ),
1058 )
1059 setattr(
1060 cls,
1061 test_binop_name('lhs_value_same_zero_float'),
1062 partialmethod(
1063 _TestNumericField._test_binop_lhs_value_same_zero_float, op=binop
1064 ),
1065 )
1066 setattr(
1067 cls,
1068 test_binop_name('lhs_value_same_zero_vfloat'),
1069 partialmethod(
1070 _TestNumericField._test_binop_lhs_value_same_zero_vfloat, op=binop
1071 ),
1072 )
1073 setattr(
1074 cls,
1075 test_binop_name('type_complex'),
1076 partialmethod(_TestNumericField._test_binop_type_complex, op=binop),
1077 )
1078 setattr(
1079 cls,
1080 test_binop_name('type_zero_complex'),
1081 partialmethod(_TestNumericField._test_binop_type_zero_complex, op=binop),
1082 )
1083 setattr(
1084 cls,
1085 test_binop_name('value_complex'),
1086 partialmethod(_TestNumericField._test_binop_value_complex, op=binop),
1087 )
1088 setattr(
1089 cls,
1090 test_binop_name('value_zero_complex'),
1091 partialmethod(_TestNumericField._test_binop_value_zero_complex, op=binop),
1092 )
1093 setattr(
1094 cls,
1095 test_binop_name('lhs_addr_same_complex'),
1096 partialmethod(
1097 _TestNumericField._test_binop_lhs_addr_same_complex, op=binop
1098 ),
1099 )
1100 setattr(
1101 cls,
1102 test_binop_name('lhs_addr_same_zero_complex'),
1103 partialmethod(
1104 _TestNumericField._test_binop_lhs_addr_same_zero_complex, op=binop
1105 ),
1106 )
1107 setattr(
1108 cls,
1109 test_binop_name('lhs_value_same_complex'),
1110 partialmethod(
1111 _TestNumericField._test_binop_lhs_value_same_complex, op=binop
1112 ),
1113 )
1114 setattr(
1115 cls,
1116 test_binop_name('lhs_value_same_zero_complex'),
1117 partialmethod(
1118 _TestNumericField._test_binop_lhs_value_same_zero_complex, op=binop
1119 ),
1120 )
9cf643d1
PP
1121
1122 # inject testing methods for each unary operation
1123 for name, unaryop in _UNARYOPS:
cfbd7cf3
FD
1124 setattr(
1125 cls,
1126 test_unaryop_name('type'),
1127 partialmethod(_TestNumericField._test_unaryop_type, op=unaryop),
1128 )
1129 setattr(
1130 cls,
1131 test_unaryop_name('value'),
1132 partialmethod(_TestNumericField._test_unaryop_value, op=unaryop),
1133 )
1134 setattr(
1135 cls,
1136 test_unaryop_name('addr_same'),
1137 partialmethod(_TestNumericField._test_unaryop_addr_same, op=unaryop),
1138 )
1139 setattr(
1140 cls,
1141 test_unaryop_name('value_same'),
1142 partialmethod(_TestNumericField._test_unaryop_value_same, op=unaryop),
1143 )
9cf643d1 1144
9cf643d1 1145
aae30e61 1146class BoolFieldTestCase(_TestNumericField, unittest.TestCase):
f0a42b33
FD
1147 @staticmethod
1148 def _const_value_setter(field):
1149 field.value = True
1150
aae30e61
PP
1151 def _create_fc(self, tc):
1152 return tc.create_bool_field_class()
1153
1154 def setUp(self):
1155 self._tc = get_default_trace_class()
1156 self._def = _create_field(self._tc, self._create_fc(self._tc))
1157 self._def.value = True
1158 self._def_value = True
6d9a6c9e 1159 self._def_const = create_const_field(
f0a42b33
FD
1160 self._tc, self._tc.create_bool_field_class(), self._const_value_setter
1161 )
aae30e61
PP
1162 self._def_new_value = False
1163
f0a42b33
FD
1164 def test_classes(self):
1165 self.assertIs(type(self._def), bt2._BoolField)
1166 self.assertIs(type(self._def_const), bt2._BoolFieldConst)
1167
aae30e61
PP
1168 def test_assign_true(self):
1169 raw = True
1170 self._def.value = raw
1171 self.assertEqual(self._def, raw)
1172
1173 def test_assign_false(self):
1174 raw = False
1175 self._def.value = raw
1176 self.assertEqual(self._def, raw)
1177
1178 def test_assign_field_true(self):
1179 field = _create_field(self._tc, self._create_fc(self._tc))
1180 raw = True
1181 field.value = raw
1182 self._def.value = field
1183 self.assertEqual(self._def, raw)
1184
1185 def test_assign_field_false(self):
1186 field = _create_field(self._tc, self._create_fc(self._tc))
1187 raw = False
1188 field.value = raw
1189 self._def.value = field
1190 self.assertEqual(self._def, raw)
1191
1192 def test_assign_invalid_type(self):
1193 with self.assertRaises(TypeError):
1194 self._def.value = 17
1195
1196 def test_str_op(self):
1197 self.assertEqual(str(self._def), str(self._def_value))
1198
1199
1200_inject_numeric_testing_methods(BoolFieldTestCase)
1201
1202
9cf643d1
PP
1203class _TestIntegerFieldCommon(_TestNumericField):
1204 def test_assign_true(self):
1205 raw = True
1206 self._def.value = raw
1207 self.assertEqual(self._def, raw)
9cf643d1
PP
1208
1209 def test_assign_false(self):
1210 raw = False
1211 self._def.value = raw
1212 self.assertEqual(self._def, raw)
9cf643d1
PP
1213
1214 def test_assign_pos_int(self):
1215 raw = 477
1216 self._def.value = raw
1217 self.assertEqual(self._def, raw)
9cf643d1
PP
1218
1219 def test_assign_neg_int(self):
1220 raw = -13
1221 self._def.value = raw
1222 self.assertEqual(self._def, raw)
9cf643d1
PP
1223
1224 def test_assign_int_field(self):
1225 raw = 999
1eccc498 1226 field = _create_field(self._tc, self._create_fc(self._tc))
9cf643d1
PP
1227 field.value = raw
1228 self._def.value = field
1229 self.assertEqual(self._def, raw)
9cf643d1 1230
9cf643d1
PP
1231 def test_assign_invalid_type(self):
1232 with self.assertRaises(TypeError):
1233 self._def.value = 'yes'
1234
1235 def test_assign_uint(self):
1eccc498
SM
1236 uint_fc = self._tc.create_unsigned_integer_field_class(32)
1237 field = _create_field(self._tc, uint_fc)
9cf643d1
PP
1238 raw = 1777
1239 field.value = 1777
1240 self.assertEqual(field, raw)
9cf643d1 1241
7bb4180f
FD
1242 def test_assign_big_uint(self):
1243 uint_fc = self._tc.create_unsigned_integer_field_class(64)
1244 field = _create_field(self._tc, uint_fc)
1245 # Larger than the IEEE 754 double-precision exact representation of
1246 # integers.
cfbd7cf3
FD
1247 raw = (2 ** 53) + 1
1248 field.value = (2 ** 53) + 1
7bb4180f
FD
1249 self.assertEqual(field, raw)
1250
1198c635
FD
1251 def test_assign_uint_out_of_range(self):
1252 uint_fc = self._tc.create_unsigned_integer_field_class(8)
1eccc498 1253 field = _create_field(self._tc, uint_fc)
9cf643d1 1254
1198c635
FD
1255 with self.assertRaises(ValueError) as ctx:
1256 field.value = 256
1257 self.assertEqual(
1258 str(ctx.exception), 'Value 256 is outside valid range [0, 255]'
1259 )
1260
1261 with self.assertRaises(ValueError) as ctx:
1262 field.value = -1
1263 self.assertEqual(str(ctx.exception), 'Value -1 is outside valid range [0, 255]')
1264
1265 def test_assign_int_out_of_range(self):
1266 int_fc = self._tc.create_signed_integer_field_class(8)
1267 field = _create_field(self._tc, int_fc)
1268
1269 with self.assertRaises(ValueError) as ctx:
1270 field.value = 128
1271 self.assertEqual(
1272 str(ctx.exception), 'Value 128 is outside valid range [-128, 127]'
1273 )
1274
1275 with self.assertRaises(ValueError) as ctx:
1276 field.value = -129
1277 self.assertEqual(
1278 str(ctx.exception), 'Value -129 is outside valid range [-128, 127]'
1279 )
9cf643d1 1280
b0bdda42
JG
1281 def test_str_op(self):
1282 self.assertEqual(str(self._def), str(self._def_value))
1283
9cf643d1
PP
1284
1285_inject_numeric_testing_methods(_TestIntegerFieldCommon)
1286
1287
1eccc498 1288class SignedIntegerFieldTestCase(_TestIntegerFieldCommon, unittest.TestCase):
dda659b3
FD
1289 @staticmethod
1290 def _const_value_setter(field):
1291 field.value = 17
1292
1eccc498
SM
1293 def _create_fc(self, tc):
1294 return tc.create_signed_integer_field_class(25)
1295
9cf643d1 1296 def setUp(self):
1eccc498
SM
1297 self._tc = get_default_trace_class()
1298 self._field = _create_field(self._tc, self._create_fc(self._tc))
1299 self._field.value = 17
1300 self._def = _create_field(self._tc, self._create_fc(self._tc))
9cf643d1
PP
1301 self._def.value = 17
1302 self._def_value = 17
6d9a6c9e 1303 self._def_const = create_const_field(
dda659b3
FD
1304 self._tc, self._create_fc(self._tc), self._const_value_setter
1305 )
9cf643d1
PP
1306 self._def_new_value = -101
1307
811644b8 1308
1eccc498 1309class SignedEnumerationFieldTestCase(_TestIntegerFieldCommon, unittest.TestCase):
dda659b3
FD
1310 @staticmethod
1311 def _const_value_setter(field):
1312 field.value = 17
1313
1eccc498
SM
1314 def _create_fc(self, tc):
1315 fc = tc.create_signed_enumeration_field_class(32)
45c51519
PP
1316 fc.add_mapping('something', bt2.SignedIntegerRangeSet([(17, 17)]))
1317 fc.add_mapping('speaker', bt2.SignedIntegerRangeSet([(12, 16)]))
1318 fc.add_mapping('can', bt2.SignedIntegerRangeSet([(18, 2540)]))
cfbd7cf3
FD
1319 fc.add_mapping(
1320 'whole range', bt2.SignedIntegerRangeSet([(-(2 ** 31), (2 ** 31) - 1)])
1321 )
45c51519 1322 fc.add_mapping('zip', bt2.SignedIntegerRangeSet([(-45, 1001)]))
1eccc498 1323 return fc
9cf643d1 1324
9cf643d1 1325 def setUp(self):
1eccc498
SM
1326 self._tc = get_default_trace_class()
1327 self._field = _create_field(self._tc, self._create_fc(self._tc))
1328 self._def = _create_field(self._tc, self._create_fc(self._tc))
9cf643d1
PP
1329 self._def.value = 17
1330 self._def_value = 17
6d9a6c9e 1331 self._def_const = create_const_field(
dda659b3
FD
1332 self._tc, self._create_fc(self._tc), self._const_value_setter
1333 )
9cf643d1
PP
1334 self._def_new_value = -101
1335
b0bdda42
JG
1336 def test_str_op(self):
1337 expected_string_found = False
1338 s = str(self._def)
1339
1340 # Establish all permutations of the three expected matches since
1341 # the order in which mappings are enumerated is not explicitly part of
1342 # the API.
cfbd7cf3 1343 for p in itertools.permutations(['whole range', 'something', 'zip']):
b0bdda42
JG
1344 candidate = '{} ({})'.format(self._def_value, ', '.join(p))
1345 if candidate == s:
1346 expected_string_found = True
1347 break
1348
1349 self.assertTrue(expected_string_found)
1350
1eccc498
SM
1351 def test_labels(self):
1352 self._field.value = 17
1353 labels = sorted(self._field.labels)
1354 self.assertEqual(labels, ['something', 'whole range', 'zip'])
1355
b0bdda42 1356
fe4df857
FD
1357class SingleRealFieldTestCase(_TestNumericField, unittest.TestCase):
1358 @staticmethod
1359 def _const_value_setter(field):
1360 field.value = 52.0
1361
1362 def _create_fc(self, tc):
1363 return tc.create_single_precision_real_field_class()
1364
1365 def setUp(self):
1366 self._tc = get_default_trace_class()
1367 self._field = _create_field(self._tc, self._create_fc(self._tc))
1368 self._def = _create_field(self._tc, self._create_fc(self._tc))
6d9a6c9e 1369 self._def_const = create_const_field(
fe4df857
FD
1370 self._tc,
1371 self._tc.create_single_precision_real_field_class(),
1372 self._const_value_setter,
1373 )
1374 self._def.value = 52.0
1375 self._def_value = 52.0
1376 self._def_new_value = -17.0
1377
1378 def _test_invalid_op(self, cb):
1379 with self.assertRaises(TypeError):
1380 cb()
1381
1382 def test_assign_true(self):
1383 self._def.value = True
1384 self.assertTrue(self._def)
1385
1386 def test_assign_false(self):
1387 self._def.value = False
1388 self.assertFalse(self._def)
1389
1390 def test_assign_pos_int(self):
1391 raw = 477
1392 self._def.value = raw
1393 self.assertEqual(self._def, float(raw))
1394
1395 def test_assign_neg_int(self):
1396 raw = -13
1397 self._def.value = raw
1398 self.assertEqual(self._def, float(raw))
1399
1400 def test_assign_int_field(self):
1401 int_fc = self._tc.create_signed_integer_field_class(32)
1402 int_field = _create_field(self._tc, int_fc)
1403 raw = 999
1404 int_field.value = raw
1405 self._def.value = int_field
1406 self.assertEqual(self._def, float(raw))
1407
1408 def test_assign_float(self):
1409 raw = -19.23
1410 self._def.value = raw
1411 # It's expected to have some lost of precision because of the field
1412 # that is in single precision.
1413 self.assertEqual(round(self._def, 5), raw)
1414
1415 def test_assign_float_field(self):
1416 field = _create_field(self._tc, self._create_fc(self._tc))
1417 raw = 101.32
1418 field.value = raw
1419 self._def.value = field
1420 # It's expected to have some lost of precision because of the field
1421 # that is in single precision.
1422 self.assertEqual(round(self._def, 5), raw)
1423
1424 def test_assign_invalid_type(self):
1425 with self.assertRaises(TypeError):
1426 self._def.value = 'yes'
1427
1428 def test_invalid_lshift(self):
1429 self._test_invalid_op(lambda: self._def << 23)
1430
1431 def test_invalid_rshift(self):
1432 self._test_invalid_op(lambda: self._def >> 23)
1433
1434 def test_invalid_and(self):
1435 self._test_invalid_op(lambda: self._def & 23)
1436
1437 def test_invalid_or(self):
1438 self._test_invalid_op(lambda: self._def | 23)
1439
1440 def test_invalid_xor(self):
1441 self._test_invalid_op(lambda: self._def ^ 23)
1442
1443 def test_invalid_invert(self):
1444 self._test_invalid_op(lambda: ~self._def)
1445
1446 def test_str_op(self):
1447 self.assertEqual(str(round(self._def, 5)), str(self._def_value))
1448
1449
1450_inject_numeric_testing_methods(SingleRealFieldTestCase)
1451
1452
1453class DoubleRealFieldTestCase(_TestNumericField, unittest.TestCase):
dda659b3
FD
1454 @staticmethod
1455 def _const_value_setter(field):
1456 field.value = 52.7
1457
1eccc498 1458 def _create_fc(self, tc):
fe4df857 1459 return tc.create_double_precision_real_field_class()
9cf643d1 1460
9cf643d1 1461 def setUp(self):
1eccc498
SM
1462 self._tc = get_default_trace_class()
1463 self._field = _create_field(self._tc, self._create_fc(self._tc))
1464 self._def = _create_field(self._tc, self._create_fc(self._tc))
6d9a6c9e 1465 self._def_const = create_const_field(
fe4df857
FD
1466 self._tc,
1467 self._tc.create_double_precision_real_field_class(),
1468 self._const_value_setter,
dda659b3 1469 )
9cf643d1
PP
1470 self._def.value = 52.7
1471 self._def_value = 52.7
1472 self._def_new_value = -17.164857
1473
1474 def _test_invalid_op(self, cb):
1475 with self.assertRaises(TypeError):
1476 cb()
1477
1478 def test_assign_true(self):
1479 self._def.value = True
1480 self.assertTrue(self._def)
9cf643d1
PP
1481
1482 def test_assign_false(self):
1483 self._def.value = False
1484 self.assertFalse(self._def)
9cf643d1
PP
1485
1486 def test_assign_pos_int(self):
1487 raw = 477
1488 self._def.value = raw
1489 self.assertEqual(self._def, float(raw))
9cf643d1
PP
1490
1491 def test_assign_neg_int(self):
1492 raw = -13
1493 self._def.value = raw
1494 self.assertEqual(self._def, float(raw))
9cf643d1
PP
1495
1496 def test_assign_int_field(self):
1eccc498
SM
1497 int_fc = self._tc.create_signed_integer_field_class(32)
1498 int_field = _create_field(self._tc, int_fc)
9cf643d1 1499 raw = 999
1eccc498
SM
1500 int_field.value = raw
1501 self._def.value = int_field
9cf643d1 1502 self.assertEqual(self._def, float(raw))
9cf643d1
PP
1503
1504 def test_assign_float(self):
1505 raw = -19.23
1506 self._def.value = raw
1507 self.assertEqual(self._def, raw)
9cf643d1
PP
1508
1509 def test_assign_float_field(self):
1eccc498 1510 field = _create_field(self._tc, self._create_fc(self._tc))
9cf643d1
PP
1511 raw = 101.32
1512 field.value = raw
1513 self._def.value = field
1514 self.assertEqual(self._def, raw)
9cf643d1
PP
1515
1516 def test_assign_invalid_type(self):
1517 with self.assertRaises(TypeError):
1518 self._def.value = 'yes'
1519
1520 def test_invalid_lshift(self):
1521 self._test_invalid_op(lambda: self._def << 23)
1522
1523 def test_invalid_rshift(self):
1524 self._test_invalid_op(lambda: self._def >> 23)
1525
1526 def test_invalid_and(self):
1527 self._test_invalid_op(lambda: self._def & 23)
1528
1529 def test_invalid_or(self):
1530 self._test_invalid_op(lambda: self._def | 23)
1531
1532 def test_invalid_xor(self):
1533 self._test_invalid_op(lambda: self._def ^ 23)
1534
1535 def test_invalid_invert(self):
1536 self._test_invalid_op(lambda: ~self._def)
1537
b0bdda42
JG
1538 def test_str_op(self):
1539 self.assertEqual(str(self._def), str(self._def_value))
1540
9cf643d1 1541
fe4df857 1542_inject_numeric_testing_methods(DoubleRealFieldTestCase)
9cf643d1
PP
1543
1544
1eccc498 1545class StringFieldTestCase(unittest.TestCase):
f0a42b33
FD
1546 @staticmethod
1547 def _const_value_setter(field):
1548 field.value = 'Hello, World!'
1549
9cf643d1 1550 def setUp(self):
1eccc498 1551 self._tc = get_default_trace_class()
9cf643d1 1552 self._def_value = 'Hello, World!'
1eccc498 1553 self._def = _create_string_field(self._tc)
6d9a6c9e 1554 self._def_const = create_const_field(
f0a42b33
FD
1555 self._tc, self._tc.create_string_field_class(), self._const_value_setter
1556 )
9cf643d1
PP
1557 self._def.value = self._def_value
1558 self._def_new_value = 'Yes!'
1559
1560 def test_assign_int(self):
1561 with self.assertRaises(TypeError):
1562 self._def.value = 283
1563
9cf643d1 1564 def test_assign_string_field(self):
1eccc498 1565 field = _create_string_field(self._tc)
9cf643d1
PP
1566 raw = 'zorg'
1567 field.value = raw
1568 self.assertEqual(field, raw)
1569
1570 def test_eq(self):
1571 self.assertEqual(self._def, self._def_value)
1572
f0a42b33
FD
1573 def test_const_eq(self):
1574 self.assertEqual(self._def_const, self._def_value)
1575
1eccc498 1576 def test_not_eq(self):
9cf643d1
PP
1577 self.assertNotEqual(self._def, 23)
1578
1579 def test_lt_vstring(self):
1eccc498 1580 s1 = _create_string_field(self._tc)
9cf643d1 1581 s1.value = 'allo'
1eccc498 1582 s2 = _create_string_field(self._tc)
9cf643d1
PP
1583 s2.value = 'bateau'
1584 self.assertLess(s1, s2)
1585
1586 def test_lt_string(self):
1eccc498 1587 s1 = _create_string_field(self._tc)
9cf643d1
PP
1588 s1.value = 'allo'
1589 self.assertLess(s1, 'bateau')
1590
1591 def test_le_vstring(self):
1eccc498 1592 s1 = _create_string_field(self._tc)
9cf643d1 1593 s1.value = 'allo'
1eccc498 1594 s2 = _create_string_field(self._tc)
9cf643d1
PP
1595 s2.value = 'bateau'
1596 self.assertLessEqual(s1, s2)
1597
1598 def test_le_string(self):
1eccc498 1599 s1 = _create_string_field(self._tc)
9cf643d1
PP
1600 s1.value = 'allo'
1601 self.assertLessEqual(s1, 'bateau')
1602
1603 def test_gt_vstring(self):
1eccc498 1604 s1 = _create_string_field(self._tc)
9cf643d1 1605 s1.value = 'allo'
1eccc498 1606 s2 = _create_string_field(self._tc)
9cf643d1
PP
1607 s2.value = 'bateau'
1608 self.assertGreater(s2, s1)
1609
1610 def test_gt_string(self):
1eccc498 1611 s1 = _create_string_field(self._tc)
9cf643d1
PP
1612 s1.value = 'allo'
1613 self.assertGreater('bateau', s1)
1614
1615 def test_ge_vstring(self):
1eccc498 1616 s1 = _create_string_field(self._tc)
9cf643d1 1617 s1.value = 'allo'
1eccc498 1618 s2 = _create_string_field(self._tc)
9cf643d1
PP
1619 s2.value = 'bateau'
1620 self.assertGreaterEqual(s2, s1)
1621
1622 def test_ge_string(self):
1eccc498 1623 s1 = _create_string_field(self._tc)
9cf643d1
PP
1624 s1.value = 'allo'
1625 self.assertGreaterEqual('bateau', s1)
1626
1627 def test_bool_op(self):
1628 self.assertEqual(bool(self._def), bool(self._def_value))
1629
1630 def test_str_op(self):
1631 self.assertEqual(str(self._def), str(self._def_value))
1632
1633 def test_len(self):
1634 self.assertEqual(len(self._def), len(self._def_value))
1635
1636 def test_getitem(self):
1637 self.assertEqual(self._def[5], self._def_value[5])
1638
f0a42b33
FD
1639 def test_const_getitem(self):
1640 self.assertEqual(self._def_const[5], self._def_value[5])
1641
9cf643d1
PP
1642 def test_append_str(self):
1643 to_append = 'meow meow meow'
1644 self._def += to_append
1645 self._def_value += to_append
1646 self.assertEqual(self._def, self._def_value)
1647
f0a42b33
FD
1648 def test_const_append_str(self):
1649 to_append = 'meow meow meow'
1650 with self.assertRaises(TypeError):
1651 self._def_const += to_append
1652 self.assertEqual(self._def_const, self._def_value)
1653
9cf643d1 1654 def test_append_string_field(self):
1eccc498 1655 field = _create_string_field(self._tc)
9cf643d1
PP
1656 to_append = 'meow meow meow'
1657 field.value = to_append
1658 self._def += field
1659 self._def_value += to_append
1660 self.assertEqual(self._def, self._def_value)
1661
dda659b3
FD
1662 def test_hash_op(self):
1663 with self.assertRaises(TypeError):
1664 hash(self._def)
1665
1666 def test_const_hash_op(self):
1667 self.assertEqual(hash(self._def_const), hash(self._def_value))
1668
1669 def test_const_hash_dict(self):
1670 my_dict = {}
1671 my_dict[self._def_const] = 'my_value'
1672 self.assertEqual(my_dict[self._def_value], 'my_value')
1673
742e4747 1674
1eccc498 1675class _TestArrayFieldCommon:
9cf643d1
PP
1676 def _modify_def(self):
1677 self._def[2] = 23
1678
1679 def test_bool_op_true(self):
1680 self.assertTrue(self._def)
1681
1682 def test_len(self):
1683 self.assertEqual(len(self._def), 3)
1684
1eccc498
SM
1685 def test_length(self):
1686 self.assertEqual(self._def.length, 3)
1687
9cf643d1
PP
1688 def test_getitem(self):
1689 field = self._def[1]
3fb99a22 1690 self.assertIs(type(field), bt2._SignedIntegerField)
9cf643d1
PP
1691 self.assertEqual(field, 1847)
1692
f0a42b33
FD
1693 def test_const_getitem(self):
1694 field = self._def_const[1]
1695 self.assertIs(type(field), bt2._SignedIntegerFieldConst)
1696 self.assertEqual(field, 1847)
1697
9cf643d1 1698 def test_eq(self):
1eccc498 1699 field = _create_int_array_field(self._tc, 3)
9cf643d1
PP
1700 field[0] = 45
1701 field[1] = 1847
1702 field[2] = 1948754
1703 self.assertEqual(self._def, field)
1704
1705 def test_eq_invalid_type(self):
1706 self.assertNotEqual(self._def, 23)
1707
1708 def test_eq_diff_len(self):
1eccc498 1709 field = _create_int_array_field(self._tc, 2)
9cf643d1
PP
1710 field[0] = 45
1711 field[1] = 1847
1712 self.assertNotEqual(self._def, field)
1713
1714 def test_eq_diff_content_same_len(self):
1eccc498 1715 field = _create_int_array_field(self._tc, 3)
9cf643d1
PP
1716 field[0] = 45
1717 field[1] = 1846
1718 field[2] = 1948754
1719 self.assertNotEqual(self._def, field)
1720
73051d46
PP
1721 def test_eq_non_sequence_iterable(self):
1722 dct = collections.OrderedDict([(1, 2), (3, 4), (5, 6)])
1723 field = _create_int_array_field(self._tc, 3)
1724 field[0] = 1
1725 field[1] = 3
1726 field[2] = 5
1727 self.assertEqual(field, list(dct.keys()))
1728 self.assertNotEqual(field, dct)
1729
9cf643d1
PP
1730 def test_setitem(self):
1731 self._def[2] = 24
1732 self.assertEqual(self._def[2], 24)
1733
1734 def test_setitem_int_field(self):
1eccc498
SM
1735 int_fc = self._tc.create_signed_integer_field_class(32)
1736 int_field = _create_field(self._tc, int_fc)
9cf643d1
PP
1737 int_field.value = 19487
1738 self._def[1] = int_field
1739 self.assertEqual(self._def[1], 19487)
1740
1741 def test_setitem_non_basic_field(self):
1eccc498 1742 array_field = _create_struct_array_field(self._tc, 2)
9cf643d1
PP
1743 with self.assertRaises(TypeError):
1744 array_field[1] = 23
1745
1746 def test_setitem_none(self):
1747 with self.assertRaises(TypeError):
1748 self._def[1] = None
1749
1750 def test_setitem_index_wrong_type(self):
1751 with self.assertRaises(TypeError):
1752 self._def['yes'] = 23
1753
1754 def test_setitem_index_neg(self):
1755 with self.assertRaises(IndexError):
1756 self._def[-2] = 23
1757
1758 def test_setitem_index_out_of_range(self):
1759 with self.assertRaises(IndexError):
1760 self._def[len(self._def)] = 134679
1761
f0a42b33
FD
1762 def test_const_setitem(self):
1763 with self.assertRaises(TypeError):
1764 self._def_const[0] = 134679
1765
9cf643d1
PP
1766 def test_iter(self):
1767 for field, value in zip(self._def, (45, 1847, 1948754)):
1768 self.assertEqual(field, value)
1769
f0a42b33
FD
1770 def test_const_iter(self):
1771 for field, value in zip(self._def_const, (45, 1847, 1948754)):
1772 self.assertEqual(field, value)
1773
7c54e2e7
JG
1774 def test_value_int_field(self):
1775 values = [45646, 145, 12145]
1776 self._def.value = values
1777 self.assertEqual(values, self._def)
1778
7c54e2e7
JG
1779 def test_value_check_sequence(self):
1780 values = 42
1781 with self.assertRaises(TypeError):
1782 self._def.value = values
1783
1784 def test_value_wrong_type_in_sequence(self):
1785 values = [32, 'hello', 11]
1786 with self.assertRaises(TypeError):
1787 self._def.value = values
1788
1789 def test_value_complex_type(self):
1eccc498
SM
1790 struct_fc = self._tc.create_structure_field_class()
1791 int_fc = self._tc.create_signed_integer_field_class(32)
1792 another_int_fc = self._tc.create_signed_integer_field_class(32)
1793 str_fc = self._tc.create_string_field_class()
1794 struct_fc.append_member(field_class=int_fc, name='an_int')
1795 struct_fc.append_member(field_class=str_fc, name='a_string')
1796 struct_fc.append_member(field_class=another_int_fc, name='another_int')
1797 array_fc = self._tc.create_static_array_field_class(struct_fc, 3)
1798 stream = _create_stream(self._tc, [('array_field', array_fc)])
7c54e2e7 1799 values = [
cfbd7cf3
FD
1800 {'an_int': 42, 'a_string': 'hello', 'another_int': 66},
1801 {'an_int': 1, 'a_string': 'goodbye', 'another_int': 488},
1802 {'an_int': 156, 'a_string': 'or not', 'another_int': 4648},
7c54e2e7
JG
1803 ]
1804
1eccc498 1805 array = stream.create_packet().context_field['array_field']
7c54e2e7
JG
1806 array.value = values
1807 self.assertEqual(values, array)
1808 values[0]['an_int'] = 'a string'
1809 with self.assertRaises(TypeError):
1810 array.value = values
9cf643d1 1811
b0bdda42
JG
1812 def test_str_op(self):
1813 s = str(self._def)
cfbd7cf3 1814 expected_string = '[{}]'.format(', '.join([repr(v) for v in self._def_value]))
b0bdda42
JG
1815 self.assertEqual(expected_string, s)
1816
742e4747 1817
1eccc498 1818class StaticArrayFieldTestCase(_TestArrayFieldCommon, unittest.TestCase):
f0a42b33
FD
1819 @staticmethod
1820 def _const_value_setter(field):
1821 field.value = [45, 1847, 1948754]
1822
9cf643d1 1823 def setUp(self):
1eccc498
SM
1824 self._tc = get_default_trace_class()
1825 self._def = _create_int_array_field(self._tc, 3)
9cf643d1
PP
1826 self._def[0] = 45
1827 self._def[1] = 1847
1828 self._def[2] = 1948754
7c54e2e7 1829 self._def_value = [45, 1847, 1948754]
6d9a6c9e 1830 self._def_const = create_const_field(
f0a42b33
FD
1831 self._tc,
1832 self._tc.create_static_array_field_class(
1833 self._tc.create_signed_integer_field_class(32), 3
1834 ),
1835 self._const_value_setter,
1836 )
9cf643d1 1837
7c54e2e7
JG
1838 def test_value_wrong_len(self):
1839 values = [45, 1847]
1840 with self.assertRaises(ValueError):
1841 self._def.value = values
1842
9cf643d1 1843
1eccc498 1844class DynamicArrayFieldTestCase(_TestArrayFieldCommon, unittest.TestCase):
f0a42b33
FD
1845 @staticmethod
1846 def _const_value_setter(field):
1847 field.value = [45, 1847, 1948754]
1848
9cf643d1 1849 def setUp(self):
1eccc498
SM
1850 self._tc = get_default_trace_class()
1851 self._def = _create_dynamic_array(self._tc)
9cf643d1
PP
1852 self._def[0] = 45
1853 self._def[1] = 1847
1854 self._def[2] = 1948754
7c54e2e7 1855 self._def_value = [45, 1847, 1948754]
6d9a6c9e 1856 self._def_const = create_const_field(
f0a42b33
FD
1857 self._tc,
1858 self._tc.create_dynamic_array_field_class(
1859 self._tc.create_signed_integer_field_class(32)
1860 ),
1861 self._const_value_setter,
1862 )
9cf643d1 1863
7c54e2e7
JG
1864 def test_value_resize(self):
1865 new_values = [1, 2, 3, 4]
1866 self._def.value = new_values
1867 self.assertCountEqual(self._def, new_values)
1868
1eccc498
SM
1869 def test_set_length(self):
1870 self._def.length = 4
1871 self._def[3] = 0
1872 self.assertEqual(len(self._def), 4)
7c54e2e7 1873
f0a42b33
FD
1874 def test_const_set_length(self):
1875 with self.assertRaises(AttributeError):
1876 self._def_const.length = 4
1877 self.assertEqual(len(self._def), 3)
1878
1eccc498 1879 def test_set_invalid_length(self):
7c54e2e7 1880 with self.assertRaises(TypeError):
1eccc498
SM
1881 self._def.length = 'cheval'
1882
1883
1884class StructureFieldTestCase(unittest.TestCase):
f0a42b33
FD
1885 @staticmethod
1886 def _const_value_setter(field):
1887 field.value = {
1888 'A': -1872,
1889 'B': 'salut',
1890 'C': 17.5,
1891 'D': 16497,
1892 'E': {},
1893 'F': {'F_1': 52},
1894 }
1895
1eccc498
SM
1896 def _create_fc(self, tc):
1897 fc = tc.create_structure_field_class()
1898 fc.append_member('A', self._fc0_fn())
1899 fc.append_member('B', self._fc1_fn())
1900 fc.append_member('C', self._fc2_fn())
1901 fc.append_member('D', self._fc3_fn())
1902 fc.append_member('E', self._fc4_fn())
1903 fc5 = self._fc5_fn()
1904 fc5.append_member('F_1', self._fc5_inner_fn())
1905 fc.append_member('F', fc5)
1906 return fc
7c54e2e7 1907
9cf643d1 1908 def setUp(self):
1eccc498
SM
1909 self._tc = get_default_trace_class()
1910 self._fc0_fn = self._tc.create_signed_integer_field_class
1911 self._fc1_fn = self._tc.create_string_field_class
fe4df857 1912 self._fc2_fn = self._tc.create_double_precision_real_field_class
1eccc498
SM
1913 self._fc3_fn = self._tc.create_signed_integer_field_class
1914 self._fc4_fn = self._tc.create_structure_field_class
1915 self._fc5_fn = self._tc.create_structure_field_class
1916 self._fc5_inner_fn = self._tc.create_signed_integer_field_class
1917
1918 self._fc = self._create_fc(self._tc)
1919 self._def = _create_field(self._tc, self._fc)
9cf643d1
PP
1920 self._def['A'] = -1872
1921 self._def['B'] = 'salut'
1922 self._def['C'] = 17.5
1923 self._def['D'] = 16497
1eccc498
SM
1924 self._def['E'] = {}
1925 self._def['F'] = {'F_1': 52}
b0bdda42
JG
1926 self._def_value = {
1927 'A': -1872,
1928 'B': 'salut',
1929 'C': 17.5,
1eccc498
SM
1930 'D': 16497,
1931 'E': {},
cfbd7cf3 1932 'F': {'F_1': 52},
b0bdda42 1933 }
9cf643d1 1934
6d9a6c9e 1935 self._def_const = create_const_field(
f0a42b33
FD
1936 self._tc, self._create_fc(self._tc), self._const_value_setter
1937 )
1938
9cf643d1
PP
1939 def _modify_def(self):
1940 self._def['B'] = 'hola'
1941
1942 def test_bool_op_true(self):
1943 self.assertTrue(self._def)
1944
1945 def test_bool_op_false(self):
1eccc498 1946 field = self._def['E']
9cf643d1
PP
1947 self.assertFalse(field)
1948
1949 def test_len(self):
1eccc498 1950 self.assertEqual(len(self._def), len(self._def_value))
9cf643d1
PP
1951
1952 def test_getitem(self):
f0a42b33
FD
1953 field1 = self._def['A']
1954 field2 = self._def['B']
1955 field3 = self._def['C']
1956 field4 = self._def['D']
1957 field5 = self._def['E']
1958 field6 = self._def['F']
1959
1960 self.assertIs(type(field1), bt2._SignedIntegerField)
1961 self.assertEqual(field1, -1872)
1962
1963 self.assertIs(type(field2), bt2._StringField)
1964 self.assertEqual(field2, 'salut')
1965
fe4df857 1966 self.assertIs(type(field3), bt2._DoublePrecisionRealField)
f0a42b33
FD
1967 self.assertEqual(field3, 17.5)
1968
1969 self.assertIs(type(field4), bt2._SignedIntegerField)
1970 self.assertEqual(field4, 16497)
1971
1972 self.assertIs(type(field5), bt2._StructureField)
1973 self.assertEqual(field5, {})
1974
1975 self.assertIs(type(field6), bt2._StructureField)
1976 self.assertEqual(field6, {'F_1': 52})
1977
1978 def test_const_getitem(self):
1979 field1 = self._def_const['A']
1980 field2 = self._def_const['B']
1981 field3 = self._def_const['C']
1982 field4 = self._def_const['D']
1983 field5 = self._def_const['E']
1984 field6 = self._def_const['F']
1985
1986 self.assertIs(type(field1), bt2._SignedIntegerFieldConst)
1987 self.assertEqual(field1, -1872)
1988
1989 self.assertIs(type(field2), bt2._StringFieldConst)
1990 self.assertEqual(field2, 'salut')
1991
fe4df857 1992 self.assertIs(type(field3), bt2._DoublePrecisionRealFieldConst)
f0a42b33
FD
1993 self.assertEqual(field3, 17.5)
1994
1995 self.assertIs(type(field4), bt2._SignedIntegerFieldConst)
1996 self.assertEqual(field4, 16497)
1997
1998 self.assertIs(type(field5), bt2._StructureFieldConst)
1999 self.assertEqual(field5, {})
2000
2001 self.assertIs(type(field6), bt2._StructureFieldConst)
2002 self.assertEqual(field6, {'F_1': 52})
9cf643d1 2003
1eccc498 2004 def test_member_at_index_out_of_bounds_after(self):
811644b8 2005 with self.assertRaises(IndexError):
1eccc498 2006 self._def.member_at_index(len(self._def_value))
811644b8 2007
9cf643d1 2008 def test_eq(self):
cfbd7cf3 2009 field = _create_field(self._tc, self._create_fc(self._tc))
9cf643d1
PP
2010 field['A'] = -1872
2011 field['B'] = 'salut'
2012 field['C'] = 17.5
2013 field['D'] = 16497
1eccc498
SM
2014 field['E'] = {}
2015 field['F'] = {'F_1': 52}
9cf643d1
PP
2016 self.assertEqual(self._def, field)
2017
f0a42b33
FD
2018 def test_const_eq(self):
2019 field = _create_field(self._tc, self._create_fc(self._tc))
2020 field['A'] = -1872
2021 field['B'] = 'salut'
2022 field['C'] = 17.5
2023 field['D'] = 16497
2024 field['E'] = {}
2025 field['F'] = {'F_1': 52}
2026 self.assertEqual(self._def_const, field)
2027
9cf643d1
PP
2028 def test_eq_invalid_type(self):
2029 self.assertNotEqual(self._def, 23)
2030
2031 def test_eq_diff_len(self):
1eccc498
SM
2032 fc = self._tc.create_structure_field_class()
2033 fc.append_member('A', self._fc0_fn())
2034 fc.append_member('B', self._fc1_fn())
2035 fc.append_member('C', self._fc2_fn())
2036
2037 field = _create_field(self._tc, fc)
9cf643d1
PP
2038 field['A'] = -1872
2039 field['B'] = 'salut'
2040 field['C'] = 17.5
2041 self.assertNotEqual(self._def, field)
2042
1eccc498
SM
2043 def test_eq_diff_keys(self):
2044 fc = self._tc.create_structure_field_class()
2045 fc.append_member('U', self._fc0_fn())
2046 fc.append_member('V', self._fc1_fn())
2047 fc.append_member('W', self._fc2_fn())
2048 fc.append_member('X', self._fc3_fn())
2049 fc.append_member('Y', self._fc4_fn())
2050 fc.append_member('Z', self._fc5_fn())
2051 field = _create_field(self._tc, fc)
2052 field['U'] = -1871
2053 field['V'] = "gerry"
2054 field['W'] = 18.19
2055 field['X'] = 16497
2056 field['Y'] = {}
2057 field['Z'] = {}
2058 self.assertNotEqual(self._def, field)
2059
9cf643d1 2060 def test_eq_diff_content_same_len(self):
1eccc498 2061 field = _create_field(self._tc, self._create_fc(self._tc))
9cf643d1
PP
2062 field['A'] = -1872
2063 field['B'] = 'salut'
2064 field['C'] = 17.4
2065 field['D'] = 16497
1eccc498
SM
2066 field['E'] = {}
2067 field['F'] = {'F_1': 0}
9cf643d1
PP
2068 self.assertNotEqual(self._def, field)
2069
2070 def test_eq_same_content_diff_keys(self):
1eccc498
SM
2071 fc = self._tc.create_structure_field_class()
2072 fc.append_member('A', self._fc0_fn())
2073 fc.append_member('B', self._fc1_fn())
2074 fc.append_member('E', self._fc2_fn())
2075 fc.append_member('D', self._fc3_fn())
2076 fc.append_member('C', self._fc4_fn())
2077 fc.append_member('F', self._fc5_fn())
2078 field = _create_field(self._tc, fc)
9cf643d1
PP
2079 field['A'] = -1872
2080 field['B'] = 'salut'
1eccc498 2081 field['E'] = 17.5
9cf643d1 2082 field['D'] = 16497
1eccc498
SM
2083 field['C'] = {}
2084 field['F'] = {}
9cf643d1
PP
2085 self.assertNotEqual(self._def, field)
2086
2087 def test_setitem(self):
2088 self._def['C'] = -18.47
2089 self.assertEqual(self._def['C'], -18.47)
2090
f0a42b33
FD
2091 def test_const_setitem(self):
2092 with self.assertRaises(TypeError):
2093 self._def_const['A'] = 134679
2094
9cf643d1 2095 def test_setitem_int_field(self):
1eccc498
SM
2096 int_fc = self._tc.create_signed_integer_field_class(32)
2097 int_field = _create_field(self._tc, int_fc)
9cf643d1
PP
2098 int_field.value = 19487
2099 self._def['D'] = int_field
2100 self.assertEqual(self._def['D'], 19487)
2101
2102 def test_setitem_non_basic_field(self):
1eccc498
SM
2103 elem_fc = self._tc.create_structure_field_class()
2104 struct_fc = self._tc.create_structure_field_class()
2105 struct_fc.append_member('A', elem_fc)
2106 struct_field = _create_field(self._tc, struct_fc)
9cf643d1 2107
236355c2
JG
2108 # Will fail on access to .items() of the value
2109 with self.assertRaises(AttributeError):
9cf643d1
PP
2110 struct_field['A'] = 23
2111
2112 def test_setitem_none(self):
2113 with self.assertRaises(TypeError):
2114 self._def['C'] = None
2115
2116 def test_setitem_key_wrong_type(self):
2117 with self.assertRaises(TypeError):
2118 self._def[3] = 23
2119
2120 def test_setitem_wrong_key(self):
2121 with self.assertRaises(KeyError):
2122 self._def['hi'] = 134679
2123
1eccc498
SM
2124 def test_member_at_index(self):
2125 self.assertEqual(self._def.member_at_index(1), 'salut')
9cf643d1 2126
f0a42b33
FD
2127 def test_const_member_at_index(self):
2128 self.assertEqual(self._def_const.member_at_index(1), 'salut')
2129
9cf643d1
PP
2130 def test_iter(self):
2131 orig_values = {
2132 'A': -1872,
2133 'B': 'salut',
2134 'C': 17.5,
2135 'D': 16497,
1eccc498 2136 'E': {},
cfbd7cf3 2137 'F': {'F_1': 52},
9cf643d1
PP
2138 }
2139
2140 for vkey, vval in self._def.items():
2141 val = orig_values[vkey]
2142 self.assertEqual(vval, val)
811644b8 2143
7c54e2e7
JG
2144 def test_value(self):
2145 orig_values = {
2146 'A': -1872,
2147 'B': 'salut',
2148 'C': 17.5,
2149 'D': 16497,
1eccc498 2150 'E': {},
cfbd7cf3 2151 'F': {'F_1': 52},
7c54e2e7
JG
2152 }
2153 self.assertEqual(self._def, orig_values)
2154
2155 def test_set_value(self):
1eccc498
SM
2156 int_fc = self._tc.create_signed_integer_field_class(32)
2157 another_int_fc = self._tc.create_signed_integer_field_class(32)
2158 str_fc = self._tc.create_string_field_class()
2159 struct_fc = self._tc.create_structure_field_class()
2160 struct_fc.append_member(field_class=int_fc, name='an_int')
2161 struct_fc.append_member(field_class=str_fc, name='a_string')
2162 struct_fc.append_member(field_class=another_int_fc, name='another_int')
cfbd7cf3 2163 values = {'an_int': 42, 'a_string': 'hello', 'another_int': 66}
7c54e2e7 2164
1eccc498 2165 struct = _create_field(self._tc, struct_fc)
7c54e2e7
JG
2166 struct.value = values
2167 self.assertEqual(values, struct)
2168
2169 bad_type_values = copy.deepcopy(values)
2170 bad_type_values['an_int'] = 'a string'
2171 with self.assertRaises(TypeError):
2172 struct.value = bad_type_values
2173
2174 unknown_key_values = copy.deepcopy(values)
2175 unknown_key_values['unknown_key'] = 16546
2176 with self.assertRaises(KeyError):
2177 struct.value = unknown_key_values
2178
b0bdda42
JG
2179 def test_str_op(self):
2180 expected_string_found = False
2181 s = str(self._def)
2182 # Establish all permutations of the three expected matches since
2183 # the order in which mappings are enumerated is not explicitly part of
2184 # the API.
2185 for p in itertools.permutations([(k, v) for k, v in self._def.items()]):
2186 items = ['{}: {}'.format(repr(k), repr(v)) for k, v in p]
2187 candidate = '{{{}}}'.format(', '.join(items))
2188 if candidate == s:
2189 expected_string_found = True
2190 break
2191
2192 self.assertTrue(expected_string_found)
2193
b0bdda42 2194
cec0261d 2195class OptionFieldTestCase(unittest.TestCase):
f0a42b33
FD
2196 @staticmethod
2197 def _const_value_setter(field):
2198 field.value = {'opt_field': 'hiboux'}
2199
cec0261d 2200 def _create_fc(self, tc):
0aa006b7
PP
2201 fc = tc.create_option_without_selector_field_class(
2202 tc.create_string_field_class()
2203 )
cec0261d
PP
2204 top_fc = tc.create_structure_field_class()
2205 top_fc.append_member('opt_field', fc)
2206 return top_fc
2207
2208 def setUp(self):
2209 self._tc = get_default_trace_class()
2210 fld = _create_field(self._tc, self._create_fc(self._tc))
2211 self._def = fld['opt_field']
f0a42b33 2212 self._def_value = 'hiboux'
6d9a6c9e 2213 self._def_const = create_const_field(
f0a42b33
FD
2214 self._tc, self._create_fc(self._tc), self._const_value_setter
2215 )['opt_field']
cec0261d
PP
2216
2217 def test_value_prop(self):
2218 self._def.value = 'hiboux'
2219 self.assertEqual(self._def.field, 'hiboux')
f0a42b33
FD
2220 self.assertIs(type(self._def), bt2._OptionField)
2221 self.assertIs(type(self._def.field), bt2._StringField)
cec0261d
PP
2222 self.assertTrue(self._def.has_field)
2223
f0a42b33
FD
2224 def test_const_value_prop(self):
2225 self.assertEqual(self._def_const.field, 'hiboux')
2226 self.assertIs(type(self._def_const), bt2._OptionFieldConst)
2227 self.assertIs(type(self._def_const.field), bt2._StringFieldConst)
2228 self.assertTrue(self._def_const.has_field)
2229
cec0261d
PP
2230 def test_has_field_prop_true(self):
2231 self._def.has_field = True
2232 self.assertTrue(self._def.has_field)
2233
d4db9beb 2234 def test_has_field_prop_false(self):
cec0261d
PP
2235 self._def.has_field = False
2236 self.assertFalse(self._def.has_field)
2237
2238 def test_bool_op_true(self):
2239 self._def.value = 'allo'
2240 self.assertTrue(self._def)
2241
d4db9beb 2242 def test_bool_op_false(self):
cec0261d
PP
2243 self._def.has_field = False
2244 self.assertFalse(self._def)
2245
2246 def test_field_prop_existing(self):
2247 self._def.value = 'meow'
2248 field = self._def.field
2249 self.assertEqual(field, 'meow')
2250
2251 def test_field_prop_none(self):
2252 self._def.has_field = False
2253 field = self._def.field
2254 self.assertIsNone(field)
2255
f0a42b33
FD
2256 def test_const_field_prop(self):
2257 with self.assertRaises(AttributeError):
2258 self._def_const.has_field = False
2259
2260 self.assertEqual(self._def_const, self._def_value)
2261 self.assertTrue(self._def_const.has_field)
2262
cec0261d
PP
2263 def test_field_prop_existing_then_none(self):
2264 self._def.value = 'meow'
2265 field = self._def.field
2266 self.assertEqual(field, 'meow')
2267 self._def.has_field = False
2268 field = self._def.field
2269 self.assertIsNone(field)
2270
2271 def test_eq(self):
2272 field = _create_field(self._tc, self._create_fc(self._tc))
2273 field = field['opt_field']
2274 field.value = 'walk'
2275 self._def.value = 'walk'
2276 self.assertEqual(self._def, field)
2277
f0a42b33
FD
2278 def test_const_eq(self):
2279 field = _create_field(self._tc, self._create_fc(self._tc))
2280 field = field['opt_field']
2281 field.value = 'hiboux'
2282 self.assertEqual(self._def_const, field)
2283 self.assertEqual(self._def_const, self._def_value)
2284
cec0261d
PP
2285 def test_eq_invalid_type(self):
2286 self._def.value = 'gerry'
2287 self.assertNotEqual(self._def, 23)
2288
2289 def test_str_op(self):
2290 self._def.value = 'marcel'
2291 self.assertEqual(str(self._def), str(self._def.field))
2292
2293 def test_repr_op(self):
2294 self._def.value = 'mireille'
2295 self.assertEqual(repr(self._def), repr(self._def.field))
2296
2297
1eccc498 2298class VariantFieldTestCase(unittest.TestCase):
f0a42b33
FD
2299 @staticmethod
2300 def _const_value_setter(field):
2301 field.selected_option_index = 3
2302 field.value = 1334
2303
1eccc498 2304 def _create_fc(self, tc):
1eccc498
SM
2305 ft0 = tc.create_signed_integer_field_class(32)
2306 ft1 = tc.create_string_field_class()
fe4df857 2307 ft2 = tc.create_double_precision_real_field_class()
1eccc498 2308 ft3 = tc.create_signed_integer_field_class(17)
1eccc498
SM
2309 fc = tc.create_variant_field_class()
2310 fc.append_option('corner', ft0)
2311 fc.append_option('zoom', ft1)
2312 fc.append_option('mellotron', ft2)
2313 fc.append_option('giorgio', ft3)
1eccc498 2314 top_fc = tc.create_structure_field_class()
1eccc498
SM
2315 top_fc.append_member('variant_field', fc)
2316 return top_fc
811644b8 2317
811644b8 2318 def setUp(self):
1eccc498
SM
2319 self._tc = get_default_trace_class()
2320 fld = _create_field(self._tc, self._create_fc(self._tc))
2321 self._def = fld['variant_field']
811644b8 2322
f0a42b33
FD
2323 self._def_value = 1334
2324 self._def_selected_index = 3
2325 const_fc = self._create_fc(self._tc)['variant_field']
2326
6d9a6c9e 2327 fld_const = create_const_field(
f0a42b33
FD
2328 self._tc, const_fc.field_class, self._const_value_setter
2329 )
2330 self._def_const = fld_const
2331
1eccc498
SM
2332 def test_bool_op(self):
2333 self._def.selected_option_index = 2
2334 self._def.value = -17.34
2335 with self.assertRaises(NotImplementedError):
2336 bool(self._def)
811644b8 2337
1eccc498
SM
2338 def test_selected_option_index(self):
2339 self._def.selected_option_index = 2
2340 self.assertEqual(self._def.selected_option_index, 2)
811644b8 2341
d431b4de
FD
2342 def test_selected_option_index_above_range(self):
2343 with self.assertRaises(IndexError):
2344 self._def.selected_option_index = 4
2345
2346 def test_selected_option_index_below_range(self):
2347 with self.assertRaises(IndexError):
2348 self._def.selected_option_index = -1
2349
f0a42b33
FD
2350 def test_const_selected_option_index(self):
2351 with self.assertRaises(AttributeError):
2352 self._def_const.selected_option_index = 2
2353 self.assertEqual(self._def_const.selected_option_index, 3)
2354
1eccc498
SM
2355 def test_selected_option(self):
2356 self._def.selected_option_index = 2
2357 self._def.value = -17.34
2358 self.assertEqual(self._def.selected_option, -17.34)
fe4df857 2359 self.assertEqual(type(self._def.selected_option), bt2._DoublePrecisionRealField)
1eccc498
SM
2360
2361 self._def.selected_option_index = 3
2362 self._def.value = 1921
2363 self.assertEqual(self._def.selected_option, 1921)
f0a42b33
FD
2364 self.assertEqual(type(self._def.selected_option), bt2._SignedIntegerField)
2365
2366 def test_const_selected_option(self):
2367 self.assertEqual(self._def_const.selected_option, 1334)
2368 self.assertEqual(
2369 type(self._def_const.selected_option), bt2._SignedIntegerFieldConst
2370 )
811644b8
PP
2371
2372 def test_eq(self):
1eccc498
SM
2373 field = _create_field(self._tc, self._create_fc(self._tc))
2374 field = field['variant_field']
2375 field.selected_option_index = 0
2376 field.value = 1774
2377 self._def.selected_option_index = 0
2378 self._def.value = 1774
811644b8
PP
2379 self.assertEqual(self._def, field)
2380
f0a42b33
FD
2381 def test_const_eq(self):
2382 field = _create_field(self._tc, self._create_fc(self._tc))
2383 field = field['variant_field']
2384 field.selected_option_index = 3
2385 field.value = 1334
2386 self.assertEqual(self._def_const, field)
2387
2b9aa00b
FD
2388 def test_len(self):
2389 self.assertEqual(len(self._def), 4)
2390
811644b8 2391 def test_eq_invalid_type(self):
1eccc498
SM
2392 self._def.selected_option_index = 1
2393 self._def.value = 'gerry'
811644b8 2394 self.assertNotEqual(self._def, 23)
742e4747 2395
b0bdda42 2396 def test_str_op_int(self):
1eccc498
SM
2397 field = _create_field(self._tc, self._create_fc(self._tc))
2398 field = field['variant_field']
2399 field.selected_option_index = 0
2400 field.value = 1774
2401 other_field = _create_field(self._tc, self._create_fc(self._tc))
2402 other_field = other_field['variant_field']
2403 other_field.selected_option_index = 0
2404 other_field.value = 1774
2405 self.assertEqual(str(field), str(other_field))
b0bdda42
JG
2406
2407 def test_str_op_str(self):
1eccc498
SM
2408 field = _create_field(self._tc, self._create_fc(self._tc))
2409 field = field['variant_field']
2410 field.selected_option_index = 1
2411 field.value = 'un beau grand bateau'
2412 other_field = _create_field(self._tc, self._create_fc(self._tc))
2413 other_field = other_field['variant_field']
2414 other_field.selected_option_index = 1
2415 other_field.value = 'un beau grand bateau'
2416 self.assertEqual(str(field), str(other_field))
2417
2418 def test_str_op_float(self):
2419 field = _create_field(self._tc, self._create_fc(self._tc))
2420 field = field['variant_field']
2421 field.selected_option_index = 2
2422 field.value = 14.4245
2423 other_field = _create_field(self._tc, self._create_fc(self._tc))
2424 other_field = other_field['variant_field']
2425 other_field.selected_option_index = 2
2426 other_field.value = 14.4245
2427 self.assertEqual(str(field), str(other_field))
d14ddbba
SM
2428
2429
2430if __name__ == '__main__':
2431 unittest.main()
This page took 0.15773 seconds and 4 git commands to generate.