blob: 2e6febe8f380285da6ca9c01204a1bf49a23be19 [file] [log] [blame]
Simon Glass2ba98752018-07-06 10:27:24 -06001#!/usr/bin/python
2# SPDX-License-Identifier: GPL-2.0+
3# Copyright (c) 2018 Google, Inc
4# Written by Simon Glass <sjg@chromium.org>
5#
6
7from optparse import OptionParser
8import glob
9import os
10import sys
11import unittest
12
13# Bring in the patman libraries
14our_path = os.path.dirname(os.path.realpath(__file__))
15for dirname in ['../patman', '..']:
16 sys.path.insert(0, os.path.join(our_path, dirname))
17
18import command
19import fdt
20from fdt import TYPE_BYTE, TYPE_INT, TYPE_STRING, TYPE_BOOL
Simon Glass2a2d91d2018-07-06 10:27:28 -060021import fdt_util
Simon Glass2ba98752018-07-06 10:27:24 -060022from fdt_util import fdt32_to_cpu
23import libfdt
24import test_util
25import tools
26
Simon Glassf9b88b32018-07-06 10:27:29 -060027def _GetPropertyValue(dtb, node, prop_name):
28 """Low-level function to get the property value based on its offset
29
30 This looks directly in the device tree at the property's offset to find
31 its value. It is useful as a check that the property is in the correct
32 place.
33
34 Args:
35 node: Node to look in
36 prop_name: Property name to find
37
38 Returns:
39 Tuple:
40 Prop object found
41 Value of property as a string (found using property offset)
42 """
43 prop = node.props[prop_name]
44
45 # Add 12, which is sizeof(struct fdt_property), to get to start of data
46 offset = prop.GetOffset() + 12
47 data = dtb.GetContents()[offset:offset + len(prop.value)]
48 return prop, [chr(x) for x in data]
49
50
Simon Glass2ba98752018-07-06 10:27:24 -060051class TestFdt(unittest.TestCase):
52 """Tests for the Fdt module
53
54 This includes unit tests for some functions and functional tests for the fdt
55 module.
56 """
57 @classmethod
58 def setUpClass(cls):
59 tools.PrepareOutputDir(None)
60
61 @classmethod
62 def tearDownClass(cls):
Simon Glasse0e62752018-10-01 21:12:41 -060063 tools.FinaliseOutputDir()
Simon Glass2ba98752018-07-06 10:27:24 -060064
65 def setUp(self):
66 self.dtb = fdt.FdtScan('tools/dtoc/dtoc_test_simple.dts')
67
68 def testFdt(self):
69 """Test that we can open an Fdt"""
70 self.dtb.Scan()
71 root = self.dtb.GetRoot()
72 self.assertTrue(isinstance(root, fdt.Node))
73
74 def testGetNode(self):
75 """Test the GetNode() method"""
76 node = self.dtb.GetNode('/spl-test')
77 self.assertTrue(isinstance(node, fdt.Node))
78 node = self.dtb.GetNode('/i2c@0/pmic@9')
79 self.assertTrue(isinstance(node, fdt.Node))
80 self.assertEqual('pmic@9', node.name)
Simon Glass2a2d91d2018-07-06 10:27:28 -060081 self.assertIsNone(self.dtb.GetNode('/i2c@0/pmic@9/missing'))
Simon Glass2ba98752018-07-06 10:27:24 -060082
83 def testFlush(self):
84 """Check that we can flush the device tree out to its file"""
85 fname = self.dtb._fname
86 with open(fname) as fd:
87 data = fd.read()
88 os.remove(fname)
89 with self.assertRaises(IOError):
90 open(fname)
91 self.dtb.Flush()
92 with open(fname) as fd:
93 data = fd.read()
94
95 def testPack(self):
96 """Test that packing a device tree works"""
97 self.dtb.Pack()
98
99 def testGetFdt(self):
100 """Tetst that we can access the raw device-tree data"""
Simon Glass96066242018-07-06 10:27:27 -0600101 self.assertTrue(isinstance(self.dtb.GetContents(), bytearray))
Simon Glass2ba98752018-07-06 10:27:24 -0600102
103 def testGetProps(self):
104 """Tests obtaining a list of properties"""
105 node = self.dtb.GetNode('/spl-test')
106 props = self.dtb.GetProps(node)
107 self.assertEqual(['boolval', 'bytearray', 'byteval', 'compatible',
Simon Glass2a2d91d2018-07-06 10:27:28 -0600108 'intarray', 'intval', 'longbytearray', 'notstring',
Simon Glass2ba98752018-07-06 10:27:24 -0600109 'stringarray', 'stringval', 'u-boot,dm-pre-reloc'],
110 sorted(props.keys()))
111
112 def testCheckError(self):
113 """Tests the ChecKError() function"""
114 with self.assertRaises(ValueError) as e:
Simon Glass2a2d91d2018-07-06 10:27:28 -0600115 fdt.CheckErr(-libfdt.NOTFOUND, 'hello')
Simon Glass2ba98752018-07-06 10:27:24 -0600116 self.assertIn('FDT_ERR_NOTFOUND: hello', str(e.exception))
117
Simon Glass94a7c602018-07-17 13:25:46 -0600118 def testGetFdt(self):
119 node = self.dtb.GetNode('/spl-test')
120 self.assertEqual(self.dtb, node.GetFdt())
Simon Glass2ba98752018-07-06 10:27:24 -0600121
122class TestNode(unittest.TestCase):
123 """Test operation of the Node class"""
124
125 @classmethod
126 def setUpClass(cls):
127 tools.PrepareOutputDir(None)
128
129 @classmethod
130 def tearDownClass(cls):
Simon Glasse0e62752018-10-01 21:12:41 -0600131 tools.FinaliseOutputDir()
Simon Glass2ba98752018-07-06 10:27:24 -0600132
133 def setUp(self):
134 self.dtb = fdt.FdtScan('tools/dtoc/dtoc_test_simple.dts')
135 self.node = self.dtb.GetNode('/spl-test')
136
137 def testOffset(self):
138 """Tests that we can obtain the offset of a node"""
139 self.assertTrue(self.node.Offset() > 0)
140
141 def testDelete(self):
142 """Tests that we can delete a property"""
143 node2 = self.dtb.GetNode('/spl-test2')
144 offset1 = node2.Offset()
145 self.node.DeleteProp('intval')
146 offset2 = node2.Offset()
147 self.assertTrue(offset2 < offset1)
148 self.node.DeleteProp('intarray')
149 offset3 = node2.Offset()
150 self.assertTrue(offset3 < offset2)
Simon Glass2a2d91d2018-07-06 10:27:28 -0600151 with self.assertRaises(libfdt.FdtException):
152 self.node.DeleteProp('missing')
Simon Glass2ba98752018-07-06 10:27:24 -0600153
Simon Glassf9b88b32018-07-06 10:27:29 -0600154 def testDeleteGetOffset(self):
155 """Test that property offset update when properties are deleted"""
156 self.node.DeleteProp('intval')
157 prop, value = _GetPropertyValue(self.dtb, self.node, 'longbytearray')
158 self.assertEqual(prop.value, value)
159
Simon Glass2ba98752018-07-06 10:27:24 -0600160 def testFindNode(self):
Simon Glass1d858882018-07-17 13:25:41 -0600161 """Tests that we can find a node using the FindNode() functoin"""
162 node = self.dtb.GetRoot().FindNode('i2c@0')
Simon Glass2ba98752018-07-06 10:27:24 -0600163 self.assertEqual('i2c@0', node.name)
Simon Glass1d858882018-07-17 13:25:41 -0600164 subnode = node.FindNode('pmic@9')
Simon Glass2ba98752018-07-06 10:27:24 -0600165 self.assertEqual('pmic@9', subnode.name)
Simon Glass1d858882018-07-17 13:25:41 -0600166 self.assertEqual(None, node.FindNode('missing'))
Simon Glass2ba98752018-07-06 10:27:24 -0600167
Simon Glassf9b88b32018-07-06 10:27:29 -0600168 def testRefreshMissingNode(self):
169 """Test refreshing offsets when an extra node is present in dtb"""
170 # Delete it from our tables, not the device tree
171 del self.dtb._root.subnodes[-1]
172 with self.assertRaises(ValueError) as e:
173 self.dtb.Refresh()
174 self.assertIn('Internal error, offset', str(e.exception))
175
176 def testRefreshExtraNode(self):
177 """Test refreshing offsets when an expected node is missing"""
178 # Delete it from the device tre, not our tables
179 self.dtb.GetFdtObj().del_node(self.node.Offset())
180 with self.assertRaises(ValueError) as e:
181 self.dtb.Refresh()
182 self.assertIn('Internal error, node name mismatch '
183 'spl-test != spl-test2', str(e.exception))
184
185 def testRefreshMissingProp(self):
186 """Test refreshing offsets when an extra property is present in dtb"""
187 # Delete it from our tables, not the device tree
188 del self.node.props['notstring']
189 with self.assertRaises(ValueError) as e:
190 self.dtb.Refresh()
191 self.assertIn("Internal error, property 'notstring' missing, offset ",
192 str(e.exception))
193
Simon Glass94a7c602018-07-17 13:25:46 -0600194 def testLookupPhandle(self):
195 """Test looking up a single phandle"""
196 dtb = fdt.FdtScan('tools/dtoc/dtoc_test_phandle.dts')
197 node = dtb.GetNode('/phandle-source2')
198 prop = node.props['clocks']
199 target = dtb.GetNode('/phandle-target')
200 self.assertEqual(target, dtb.LookupPhandle(fdt32_to_cpu(prop.value)))
201
Simon Glass2ba98752018-07-06 10:27:24 -0600202
203class TestProp(unittest.TestCase):
204 """Test operation of the Prop class"""
205
206 @classmethod
207 def setUpClass(cls):
208 tools.PrepareOutputDir(None)
209
210 @classmethod
211 def tearDownClass(cls):
Simon Glasse0e62752018-10-01 21:12:41 -0600212 tools.FinaliseOutputDir()
Simon Glass2ba98752018-07-06 10:27:24 -0600213
214 def setUp(self):
215 self.dtb = fdt.FdtScan('tools/dtoc/dtoc_test_simple.dts')
216 self.node = self.dtb.GetNode('/spl-test')
217 self.fdt = self.dtb.GetFdtObj()
218
Simon Glassb9066ff2018-07-06 10:27:30 -0600219 def testMissingNode(self):
220 self.assertEqual(None, self.dtb.GetNode('missing'))
221
Simon Glass2a2d91d2018-07-06 10:27:28 -0600222 def testPhandle(self):
223 dtb = fdt.FdtScan('tools/dtoc/dtoc_test_phandle.dts')
Simon Glass760b7172018-07-06 10:27:31 -0600224 node = dtb.GetNode('/phandle-source2')
225 prop = node.props['clocks']
226 self.assertTrue(fdt32_to_cpu(prop.value) > 0)
Simon Glass2a2d91d2018-07-06 10:27:28 -0600227
228 def _ConvertProp(self, prop_name):
229 """Helper function to look up a property in self.node and return it
230
231 Args:
232 Property name to find
233
234 Return fdt.Prop object for this property
235 """
Simon Glass50c59522018-07-26 14:02:13 -0600236 p = self.fdt.getprop(self.node.Offset(), prop_name)
Simon Glass2a2d91d2018-07-06 10:27:28 -0600237 return fdt.Prop(self.node, -1, prop_name, p)
238
239 def testMakeProp(self):
240 """Test we can convert all the the types that are supported"""
241 prop = self._ConvertProp('boolval')
242 self.assertEqual(fdt.TYPE_BOOL, prop.type)
243 self.assertEqual(True, prop.value)
244
245 prop = self._ConvertProp('intval')
246 self.assertEqual(fdt.TYPE_INT, prop.type)
247 self.assertEqual(1, fdt32_to_cpu(prop.value))
248
249 prop = self._ConvertProp('intarray')
250 self.assertEqual(fdt.TYPE_INT, prop.type)
251 val = [fdt32_to_cpu(val) for val in prop.value]
252 self.assertEqual([2, 3, 4], val)
253
254 prop = self._ConvertProp('byteval')
255 self.assertEqual(fdt.TYPE_BYTE, prop.type)
256 self.assertEqual(5, ord(prop.value))
257
258 prop = self._ConvertProp('longbytearray')
259 self.assertEqual(fdt.TYPE_BYTE, prop.type)
260 val = [ord(val) for val in prop.value]
261 self.assertEqual([9, 10, 11, 12, 13, 14, 15, 16, 17], val)
262
263 prop = self._ConvertProp('stringval')
264 self.assertEqual(fdt.TYPE_STRING, prop.type)
265 self.assertEqual('message', prop.value)
266
267 prop = self._ConvertProp('stringarray')
268 self.assertEqual(fdt.TYPE_STRING, prop.type)
269 self.assertEqual(['multi-word', 'message'], prop.value)
270
271 prop = self._ConvertProp('notstring')
272 self.assertEqual(fdt.TYPE_BYTE, prop.type)
273 val = [ord(val) for val in prop.value]
274 self.assertEqual([0x20, 0x21, 0x22, 0x10, 0], val)
275
Simon Glass2ba98752018-07-06 10:27:24 -0600276 def testGetEmpty(self):
277 """Tests the GetEmpty() function for the various supported types"""
278 self.assertEqual(True, fdt.Prop.GetEmpty(fdt.TYPE_BOOL))
279 self.assertEqual(chr(0), fdt.Prop.GetEmpty(fdt.TYPE_BYTE))
280 self.assertEqual(chr(0) * 4, fdt.Prop.GetEmpty(fdt.TYPE_INT))
281 self.assertEqual('', fdt.Prop.GetEmpty(fdt.TYPE_STRING))
282
283 def testGetOffset(self):
284 """Test we can get the offset of a property"""
Simon Glassf9b88b32018-07-06 10:27:29 -0600285 prop, value = _GetPropertyValue(self.dtb, self.node, 'longbytearray')
286 self.assertEqual(prop.value, value)
Simon Glass2ba98752018-07-06 10:27:24 -0600287
288 def testWiden(self):
289 """Test widening of values"""
290 node2 = self.dtb.GetNode('/spl-test2')
291 prop = self.node.props['intval']
292
293 # No action
294 prop2 = node2.props['intval']
295 prop.Widen(prop2)
296 self.assertEqual(fdt.TYPE_INT, prop.type)
297 self.assertEqual(1, fdt32_to_cpu(prop.value))
298
299 # Convert singla value to array
300 prop2 = self.node.props['intarray']
301 prop.Widen(prop2)
302 self.assertEqual(fdt.TYPE_INT, prop.type)
303 self.assertTrue(isinstance(prop.value, list))
304
305 # A 4-byte array looks like a single integer. When widened by a longer
306 # byte array, it should turn into an array.
307 prop = self.node.props['longbytearray']
308 prop2 = node2.props['longbytearray']
309 self.assertFalse(isinstance(prop2.value, list))
310 self.assertEqual(4, len(prop2.value))
311 prop2.Widen(prop)
312 self.assertTrue(isinstance(prop2.value, list))
313 self.assertEqual(9, len(prop2.value))
314
315 # Similarly for a string array
316 prop = self.node.props['stringval']
317 prop2 = node2.props['stringarray']
318 self.assertFalse(isinstance(prop.value, list))
319 self.assertEqual(7, len(prop.value))
320 prop.Widen(prop2)
321 self.assertTrue(isinstance(prop.value, list))
322 self.assertEqual(3, len(prop.value))
323
324 # Enlarging an existing array
325 prop = self.node.props['stringarray']
326 prop2 = node2.props['stringarray']
327 self.assertTrue(isinstance(prop.value, list))
328 self.assertEqual(2, len(prop.value))
329 prop.Widen(prop2)
330 self.assertTrue(isinstance(prop.value, list))
331 self.assertEqual(3, len(prop.value))
332
Simon Glass116adec2018-07-06 10:27:38 -0600333 def testAdd(self):
334 """Test adding properties"""
335 self.fdt.pack()
336 # This function should automatically expand the device tree
337 self.node.AddZeroProp('one')
338 self.node.AddZeroProp('two')
339 self.node.AddZeroProp('three')
Simon Glassfa80c252018-09-14 04:57:13 -0600340 self.dtb.Sync(auto_resize=True)
Simon Glass116adec2018-07-06 10:27:38 -0600341
342 # Updating existing properties should be OK, since the device-tree size
343 # does not change
344 self.fdt.pack()
345 self.node.SetInt('one', 1)
346 self.node.SetInt('two', 2)
347 self.node.SetInt('three', 3)
Simon Glassfa80c252018-09-14 04:57:13 -0600348 self.dtb.Sync(auto_resize=False)
Simon Glass116adec2018-07-06 10:27:38 -0600349
350 # This should fail since it would need to increase the device-tree size
Simon Glassfa80c252018-09-14 04:57:13 -0600351 self.node.AddZeroProp('four')
Simon Glass116adec2018-07-06 10:27:38 -0600352 with self.assertRaises(libfdt.FdtException) as e:
Simon Glassfa80c252018-09-14 04:57:13 -0600353 self.dtb.Sync(auto_resize=False)
Simon Glass116adec2018-07-06 10:27:38 -0600354 self.assertIn('FDT_ERR_NOSPACE', str(e.exception))
Simon Glass64349612018-09-14 04:57:16 -0600355 self.dtb.Sync(auto_resize=True)
Simon Glass116adec2018-07-06 10:27:38 -0600356
Simon Glassfa80c252018-09-14 04:57:13 -0600357 def testAddNode(self):
358 self.fdt.pack()
Simon Glasse21c27a2018-09-14 04:57:15 -0600359 self.node.AddSubnode('subnode')
360 with self.assertRaises(libfdt.FdtException) as e:
361 self.dtb.Sync(auto_resize=False)
362 self.assertIn('FDT_ERR_NOSPACE', str(e.exception))
363
364 self.dtb.Sync(auto_resize=True)
365 offset = self.fdt.path_offset('/spl-test/subnode')
366 self.assertTrue(offset > 0)
Simon Glassfa80c252018-09-14 04:57:13 -0600367
Simon Glass64349612018-09-14 04:57:16 -0600368 def testAddMore(self):
369 """Test various other methods for adding and setting properties"""
370 self.node.AddZeroProp('one')
371 self.dtb.Sync(auto_resize=True)
372 data = self.fdt.getprop(self.node.Offset(), 'one')
373 self.assertEqual(0, fdt32_to_cpu(data))
374
375 self.node.SetInt('one', 1)
376 self.dtb.Sync(auto_resize=False)
377 data = self.fdt.getprop(self.node.Offset(), 'one')
378 self.assertEqual(1, fdt32_to_cpu(data))
379
380 val = '123' + chr(0) + '456'
381 self.node.AddString('string', val)
382 self.dtb.Sync(auto_resize=True)
383 data = self.fdt.getprop(self.node.Offset(), 'string')
384 self.assertEqual(val + '\0', data)
385
386 self.fdt.pack()
387 self.node.SetString('string', val + 'x')
388 with self.assertRaises(libfdt.FdtException) as e:
389 self.dtb.Sync(auto_resize=False)
390 self.assertIn('FDT_ERR_NOSPACE', str(e.exception))
391 self.node.SetString('string', val[:-1])
392
393 prop = self.node.props['string']
394 prop.SetData(val)
395 self.dtb.Sync(auto_resize=False)
396 data = self.fdt.getprop(self.node.Offset(), 'string')
397 self.assertEqual(val, data)
398
399 self.node.AddEmptyProp('empty', 5)
400 self.dtb.Sync(auto_resize=True)
401 prop = self.node.props['empty']
402 prop.SetData(val)
403 self.dtb.Sync(auto_resize=False)
404 data = self.fdt.getprop(self.node.Offset(), 'empty')
405 self.assertEqual(val, data)
406
407 self.node.SetData('empty', '123')
408 self.assertEqual('123', prop.bytes)
409
Simon Glass746aee32018-09-14 04:57:17 -0600410 def testFromData(self):
411 dtb2 = fdt.Fdt.FromData(self.dtb.GetContents())
412 self.assertEqual(dtb2.GetContents(), self.dtb.GetContents())
413
414 self.node.AddEmptyProp('empty', 5)
415 self.dtb.Sync(auto_resize=True)
416 self.assertTrue(dtb2.GetContents() != self.dtb.GetContents())
417
Simon Glass2ba98752018-07-06 10:27:24 -0600418
Simon Glass2a2d91d2018-07-06 10:27:28 -0600419class TestFdtUtil(unittest.TestCase):
420 """Tests for the fdt_util module
421
422 This module will likely be mostly replaced at some point, once upstream
423 libfdt has better Python support. For now, this provides tests for current
424 functionality.
425 """
426 @classmethod
427 def setUpClass(cls):
428 tools.PrepareOutputDir(None)
429
Simon Glasse0e62752018-10-01 21:12:41 -0600430 @classmethod
431 def tearDownClass(cls):
432 tools.FinaliseOutputDir()
433
Simon Glass2a2d91d2018-07-06 10:27:28 -0600434 def setUp(self):
435 self.dtb = fdt.FdtScan('tools/dtoc/dtoc_test_simple.dts')
436 self.node = self.dtb.GetNode('/spl-test')
437
438 def testGetInt(self):
439 self.assertEqual(1, fdt_util.GetInt(self.node, 'intval'))
440 self.assertEqual(3, fdt_util.GetInt(self.node, 'missing', 3))
441
442 with self.assertRaises(ValueError) as e:
443 self.assertEqual(3, fdt_util.GetInt(self.node, 'intarray'))
444 self.assertIn("property 'intarray' has list value: expecting a single "
445 'integer', str(e.exception))
446
447 def testGetString(self):
448 self.assertEqual('message', fdt_util.GetString(self.node, 'stringval'))
449 self.assertEqual('test', fdt_util.GetString(self.node, 'missing',
450 'test'))
451
452 with self.assertRaises(ValueError) as e:
453 self.assertEqual(3, fdt_util.GetString(self.node, 'stringarray'))
454 self.assertIn("property 'stringarray' has list value: expecting a "
455 'single string', str(e.exception))
456
457 def testGetBool(self):
458 self.assertEqual(True, fdt_util.GetBool(self.node, 'boolval'))
459 self.assertEqual(False, fdt_util.GetBool(self.node, 'missing'))
460 self.assertEqual(True, fdt_util.GetBool(self.node, 'missing', True))
461 self.assertEqual(False, fdt_util.GetBool(self.node, 'missing', False))
462
Simon Glass3af8e492018-07-17 13:25:40 -0600463 def testGetByte(self):
464 self.assertEqual(5, fdt_util.GetByte(self.node, 'byteval'))
465 self.assertEqual(3, fdt_util.GetByte(self.node, 'missing', 3))
466
467 with self.assertRaises(ValueError) as e:
468 fdt_util.GetByte(self.node, 'longbytearray')
469 self.assertIn("property 'longbytearray' has list value: expecting a "
470 'single byte', str(e.exception))
471
472 with self.assertRaises(ValueError) as e:
473 fdt_util.GetByte(self.node, 'intval')
474 self.assertIn("property 'intval' has length 4, expecting 1",
475 str(e.exception))
476
Simon Glass94a7c602018-07-17 13:25:46 -0600477 def testGetPhandleList(self):
478 dtb = fdt.FdtScan('tools/dtoc/dtoc_test_phandle.dts')
479 node = dtb.GetNode('/phandle-source2')
480 self.assertEqual([1], fdt_util.GetPhandleList(node, 'clocks'))
481 node = dtb.GetNode('/phandle-source')
482 self.assertEqual([1, 2, 11, 3, 12, 13, 1],
483 fdt_util.GetPhandleList(node, 'clocks'))
484 self.assertEqual(None, fdt_util.GetPhandleList(node, 'missing'))
485
Simon Glass53af22a2018-07-17 13:25:32 -0600486 def testGetDataType(self):
487 self.assertEqual(1, fdt_util.GetDatatype(self.node, 'intval', int))
488 self.assertEqual('message', fdt_util.GetDatatype(self.node, 'stringval',
489 str))
490 with self.assertRaises(ValueError) as e:
491 self.assertEqual(3, fdt_util.GetDatatype(self.node, 'boolval',
492 bool))
Simon Glass2a2d91d2018-07-06 10:27:28 -0600493 def testFdtCellsToCpu(self):
494 val = self.node.props['intarray'].value
495 self.assertEqual(0, fdt_util.fdt_cells_to_cpu(val, 0))
496 self.assertEqual(2, fdt_util.fdt_cells_to_cpu(val, 1))
497
498 dtb2 = fdt.FdtScan('tools/dtoc/dtoc_test_addr64.dts')
499 node2 = dtb2.GetNode('/test1')
500 val = node2.props['reg'].value
501 self.assertEqual(0x1234, fdt_util.fdt_cells_to_cpu(val, 2))
502
503 def testEnsureCompiled(self):
504 """Test a degenerate case of this function"""
505 dtb = fdt_util.EnsureCompiled('tools/dtoc/dtoc_test_simple.dts')
506 self.assertEqual(dtb, fdt_util.EnsureCompiled(dtb))
507
508 def testGetPlainBytes(self):
509 self.assertEqual('fred', fdt_util.get_plain_bytes('fred'))
510
511
512def RunTestCoverage():
513 """Run the tests and check that we get 100% coverage"""
514 test_util.RunTestCoverage('tools/dtoc/test_fdt.py', None,
515 ['tools/patman/*.py', '*test_fdt.py'], options.build_dir)
516
517
Simon Glass2ba98752018-07-06 10:27:24 -0600518def RunTests(args):
519 """Run all the test we have for the fdt model
520
521 Args:
522 args: List of positional args provided to fdt. This can hold a test
523 name to execute (as in 'fdt -t testFdt', for example)
524 """
525 result = unittest.TestResult()
526 sys.argv = [sys.argv[0]]
527 test_name = args and args[0] or None
Simon Glass2a2d91d2018-07-06 10:27:28 -0600528 for module in (TestFdt, TestNode, TestProp, TestFdtUtil):
Simon Glass2ba98752018-07-06 10:27:24 -0600529 if test_name:
530 try:
531 suite = unittest.TestLoader().loadTestsFromName(test_name, module)
532 except AttributeError:
533 continue
534 else:
535 suite = unittest.TestLoader().loadTestsFromTestCase(module)
536 suite.run(result)
537
538 print result
539 for _, err in result.errors:
540 print err
541 for _, err in result.failures:
542 print err
543
544if __name__ != '__main__':
545 sys.exit(1)
546
547parser = OptionParser()
Simon Glass2a2d91d2018-07-06 10:27:28 -0600548parser.add_option('-B', '--build-dir', type='string', default='b',
549 help='Directory containing the build output')
Simon Glass2ba98752018-07-06 10:27:24 -0600550parser.add_option('-t', '--test', action='store_true', dest='test',
551 default=False, help='run tests')
Simon Glass2a2d91d2018-07-06 10:27:28 -0600552parser.add_option('-T', '--test-coverage', action='store_true',
553 default=False, help='run tests and check for 100% coverage')
Simon Glass2ba98752018-07-06 10:27:24 -0600554(options, args) = parser.parse_args()
555
556# Run our meagre tests
557if options.test:
558 RunTests(args)
Simon Glass2a2d91d2018-07-06 10:27:28 -0600559elif options.test_coverage:
560 RunTestCoverage()