blob: 9e21e184253e7b7d4b1912d66c80425590a4297c [file] [log] [blame]
Patrick Williamsc124f4f2015-09-15 14:41:29 -05001#
2# BitBake Test for lib/bb/parse/
3#
4# Copyright (C) 2015 Richard Purdie
5#
Brad Bishopc342db32019-05-15 21:57:59 -04006# SPDX-License-Identifier: GPL-2.0-only
Patrick Williamsc124f4f2015-09-15 14:41:29 -05007#
8
9import unittest
10import tempfile
11import logging
12import bb
13import os
14
15logger = logging.getLogger('BitBake.TestParse')
16
17import bb.parse
18import bb.data
19import bb.siggen
20
21class ParseTest(unittest.TestCase):
22
23 testfile = """
24A = "1"
25B = "2"
26do_install() {
27 echo "hello"
28}
29
30C = "3"
31"""
32
33 def setUp(self):
Brad Bishop1a4b7ee2018-12-16 17:11:34 -080034 self.origdir = os.getcwd()
Patrick Williamsc124f4f2015-09-15 14:41:29 -050035 self.d = bb.data.init()
36 bb.parse.siggen = bb.siggen.init(self.d)
37
Brad Bishop1a4b7ee2018-12-16 17:11:34 -080038 def tearDown(self):
39 os.chdir(self.origdir)
40
Patrick Williamsc124f4f2015-09-15 14:41:29 -050041 def parsehelper(self, content, suffix = ".bb"):
42
43 f = tempfile.NamedTemporaryFile(suffix = suffix)
Patrick Williamsc0f7c042017-02-23 20:41:17 -060044 f.write(bytes(content, "utf-8"))
Patrick Williamsc124f4f2015-09-15 14:41:29 -050045 f.flush()
46 os.chdir(os.path.dirname(f.name))
47 return f
48
49 def test_parse_simple(self):
50 f = self.parsehelper(self.testfile)
51 d = bb.parse.handle(f.name, self.d)['']
Brad Bishop6e60e8b2018-02-01 10:27:11 -050052 self.assertEqual(d.getVar("A"), "1")
53 self.assertEqual(d.getVar("B"), "2")
54 self.assertEqual(d.getVar("C"), "3")
Patrick Williamsc124f4f2015-09-15 14:41:29 -050055
56 def test_parse_incomplete_function(self):
57 testfileB = self.testfile.replace("}", "")
58 f = self.parsehelper(testfileB)
59 with self.assertRaises(bb.parse.ParseError):
60 d = bb.parse.handle(f.name, self.d)['']
61
Patrick Williamsc0f7c042017-02-23 20:41:17 -060062 unsettest = """
63A = "1"
64B = "2"
65B[flag] = "3"
66
67unset A
68unset B[flag]
69"""
70
71 def test_parse_unset(self):
72 f = self.parsehelper(self.unsettest)
73 d = bb.parse.handle(f.name, self.d)['']
Brad Bishop6e60e8b2018-02-01 10:27:11 -050074 self.assertEqual(d.getVar("A"), None)
75 self.assertEqual(d.getVarFlag("A","flag"), None)
76 self.assertEqual(d.getVar("B"), "2")
Brad Bishopd7bf8c12018-02-25 22:55:05 -050077
78 exporttest = """
79A = "a"
80export B = "b"
81export C
82exportD = "d"
83"""
84
85 def test_parse_exports(self):
86 f = self.parsehelper(self.exporttest)
87 d = bb.parse.handle(f.name, self.d)['']
88 self.assertEqual(d.getVar("A"), "a")
89 self.assertIsNone(d.getVarFlag("A", "export"))
90 self.assertEqual(d.getVar("B"), "b")
91 self.assertEqual(d.getVarFlag("B", "export"), 1)
92 self.assertIsNone(d.getVar("C"))
93 self.assertEqual(d.getVarFlag("C", "export"), 1)
94 self.assertIsNone(d.getVar("D"))
95 self.assertIsNone(d.getVarFlag("D", "export"))
96 self.assertEqual(d.getVar("exportD"), "d")
97 self.assertIsNone(d.getVarFlag("exportD", "export"))
98
Patrick Williamsc0f7c042017-02-23 20:41:17 -060099
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500100 overridetest = """
101RRECOMMENDS_${PN} = "a"
102RRECOMMENDS_${PN}_libc = "b"
103OVERRIDES = "libc:${PN}"
104PN = "gtk+"
105"""
106
107 def test_parse_overrides(self):
108 f = self.parsehelper(self.overridetest)
109 d = bb.parse.handle(f.name, self.d)['']
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500110 self.assertEqual(d.getVar("RRECOMMENDS"), "b")
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500111 bb.data.expandKeys(d)
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500112 self.assertEqual(d.getVar("RRECOMMENDS"), "b")
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500113 d.setVar("RRECOMMENDS_gtk+", "c")
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500114 self.assertEqual(d.getVar("RRECOMMENDS"), "c")
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500115
116 overridetest2 = """
117EXTRA_OECONF = ""
118EXTRA_OECONF_class-target = "b"
119EXTRA_OECONF_append = " c"
120"""
121
122 def test_parse_overrides(self):
123 f = self.parsehelper(self.overridetest2)
124 d = bb.parse.handle(f.name, self.d)['']
125 d.appendVar("EXTRA_OECONF", " d")
126 d.setVar("OVERRIDES", "class-target")
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500127 self.assertEqual(d.getVar("EXTRA_OECONF"), "b c d")
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500128
129 overridetest3 = """
130DESCRIPTION = "A"
131DESCRIPTION_${PN}-dev = "${DESCRIPTION} B"
132PN = "bc"
133"""
134
135 def test_parse_combinations(self):
136 f = self.parsehelper(self.overridetest3)
137 d = bb.parse.handle(f.name, self.d)['']
138 bb.data.expandKeys(d)
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500139 self.assertEqual(d.getVar("DESCRIPTION_bc-dev"), "A B")
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500140 d.setVar("DESCRIPTION", "E")
141 d.setVar("DESCRIPTION_bc-dev", "C D")
142 d.setVar("OVERRIDES", "bc-dev")
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500143 self.assertEqual(d.getVar("DESCRIPTION"), "C D")
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500144
145
146 classextend = """
147VAR_var_override1 = "B"
148EXTRA = ":override1"
149OVERRIDES = "nothing${EXTRA}"
150
151BBCLASSEXTEND = "###CLASS###"
152"""
153 classextend_bbclass = """
154EXTRA = ""
155python () {
156 d.renameVar("VAR_var", "VAR_var2")
157}
158"""
159
160 #
161 # Test based upon a real world data corruption issue. One
162 # data store changing a variable poked through into a different data
163 # store. This test case replicates that issue where the value 'B' would
164 # become unset/disappear.
165 #
166 def test_parse_classextend_contamination(self):
167 cls = self.parsehelper(self.classextend_bbclass, suffix=".bbclass")
168 #clsname = os.path.basename(cls.name).replace(".bbclass", "")
169 self.classextend = self.classextend.replace("###CLASS###", cls.name)
170 f = self.parsehelper(self.classextend)
171 alldata = bb.parse.handle(f.name, self.d)
172 d1 = alldata['']
173 d2 = alldata[cls.name]
Brad Bishop6e60e8b2018-02-01 10:27:11 -0500174 self.assertEqual(d1.getVar("VAR_var"), "B")
175 self.assertEqual(d2.getVar("VAR_var"), None)
Patrick Williamsc124f4f2015-09-15 14:41:29 -0500176
Brad Bishopc342db32019-05-15 21:57:59 -0400177 addtask_deltask = """
178addtask do_patch after do_foo after do_unpack before do_configure before do_compile
179addtask do_fetch do_patch
180
Andrew Geisslerb7d28612020-07-24 16:15:54 -0500181MYVAR = "do_patch"
182EMPTYVAR = ""
183deltask do_fetch ${MYVAR} ${EMPTYVAR}
184deltask ${EMPTYVAR}
Brad Bishopc342db32019-05-15 21:57:59 -0400185"""
186 def test_parse_addtask_deltask(self):
187 import sys
188 f = self.parsehelper(self.addtask_deltask)
189 d = bb.parse.handle(f.name, self.d)['']
190
191 stdout = sys.stdout.getvalue()
192 self.assertTrue("addtask contained multiple 'before' keywords" in stdout)
193 self.assertTrue("addtask contained multiple 'after' keywords" in stdout)
194 self.assertTrue('addtask ignored: " do_patch"' in stdout)
Brad Bishopc342db32019-05-15 21:57:59 -0400195 #self.assertTrue('dependent task do_foo for do_patch does not exist' in stdout)
196