blob: fe748aeb468c8bfca959a765d52961926e9b60cd [file] [log] [blame]
Azim Khanb31aa442018-07-03 11:57:54 +01001#!/usr/bin/env python3
Mohammad Azim Khan78befd92018-03-06 11:49:41 +00002# Unit test for generate_test_code.py
Azim Khanf0e42fb2017-08-02 14:47:13 +01003#
Bence Szépkúti1e148272020-08-07 13:07:28 +02004# Copyright The Mbed TLS Contributors
Azim Khanf0e42fb2017-08-02 14:47:13 +01005# SPDX-License-Identifier: Apache-2.0
6#
7# Licensed under the Apache License, Version 2.0 (the "License"); you may
8# not use this file except in compliance with the License.
9# You may obtain a copy of the License at
10#
11# http://www.apache.org/licenses/LICENSE-2.0
12#
13# Unless required by applicable law or agreed to in writing, software
14# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
15# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16# See the License for the specific language governing permissions and
17# limitations under the License.
Azim Khan4b543232017-06-30 09:35:21 +010018
19"""
Mohammad Azim Khan78befd92018-03-06 11:49:41 +000020Unit tests for generate_test_code.py
Azim Khan4b543232017-06-30 09:35:21 +010021"""
22
Gilles Peskine38b66df2020-08-12 02:11:38 +020023from io import StringIO
Azim Khanb31aa442018-07-03 11:57:54 +010024from unittest import TestCase, main as unittest_main
Gilles Peskine38b66df2020-08-12 02:11:38 +020025from unittest.mock import patch
26
Azim Khanb31aa442018-07-03 11:57:54 +010027from generate_test_code import gen_dependencies, gen_dependencies_one_line
28from generate_test_code import gen_function_wrapper, gen_dispatch
29from generate_test_code import parse_until_pattern, GeneratorInputError
30from generate_test_code import parse_suite_dependencies
31from generate_test_code import parse_function_dependencies
Azim Khanfcdf6852018-07-05 17:31:46 +010032from generate_test_code import parse_function_arguments, parse_function_code
Azim Khanb31aa442018-07-03 11:57:54 +010033from generate_test_code import parse_functions, END_HEADER_REGEX
34from generate_test_code import END_SUITE_HELPERS_REGEX, escaped_split
35from generate_test_code import parse_test_data, gen_dep_check
36from generate_test_code import gen_expression_check, write_dependencies
37from generate_test_code import write_parameters, gen_suite_dep_checks
38from generate_test_code import gen_from_test_data
39
40
Azim Khan4b543232017-06-30 09:35:21 +010041class GenDep(TestCase):
42 """
43 Test suite for function gen_dep()
44 """
45
Azim Khanb31aa442018-07-03 11:57:54 +010046 def test_dependencies_list(self):
Azim Khan4b543232017-06-30 09:35:21 +010047 """
Azim Khanb31aa442018-07-03 11:57:54 +010048 Test that gen_dep() correctly creates dependencies for given
49 dependency list.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +010050 :return:
Azim Khan4b543232017-06-30 09:35:21 +010051 """
Azim Khanb31aa442018-07-03 11:57:54 +010052 dependencies = ['DEP1', 'DEP2']
53 dep_start, dep_end = gen_dependencies(dependencies)
54 preprocessor1, preprocessor2 = dep_start.splitlines()
Azim Khan4b543232017-06-30 09:35:21 +010055 endif1, endif2 = dep_end.splitlines()
Azim Khanb31aa442018-07-03 11:57:54 +010056 self.assertEqual(preprocessor1, '#if defined(DEP1)',
57 'Preprocessor generated incorrectly')
58 self.assertEqual(preprocessor2, '#if defined(DEP2)',
59 'Preprocessor generated incorrectly')
60 self.assertEqual(endif1, '#endif /* DEP2 */',
61 'Preprocessor generated incorrectly')
62 self.assertEqual(endif2, '#endif /* DEP1 */',
63 'Preprocessor generated incorrectly')
Azim Khan4b543232017-06-30 09:35:21 +010064
Azim Khanb31aa442018-07-03 11:57:54 +010065 def test_disabled_dependencies_list(self):
Azim Khan4b543232017-06-30 09:35:21 +010066 """
Azim Khanb31aa442018-07-03 11:57:54 +010067 Test that gen_dep() correctly creates dependencies for given
68 dependency list.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +010069 :return:
Azim Khan4b543232017-06-30 09:35:21 +010070 """
Azim Khanb31aa442018-07-03 11:57:54 +010071 dependencies = ['!DEP1', '!DEP2']
72 dep_start, dep_end = gen_dependencies(dependencies)
73 preprocessor1, preprocessor2 = dep_start.splitlines()
Azim Khan4b543232017-06-30 09:35:21 +010074 endif1, endif2 = dep_end.splitlines()
Azim Khanb31aa442018-07-03 11:57:54 +010075 self.assertEqual(preprocessor1, '#if !defined(DEP1)',
76 'Preprocessor generated incorrectly')
77 self.assertEqual(preprocessor2, '#if !defined(DEP2)',
78 'Preprocessor generated incorrectly')
79 self.assertEqual(endif1, '#endif /* !DEP2 */',
80 'Preprocessor generated incorrectly')
81 self.assertEqual(endif2, '#endif /* !DEP1 */',
82 'Preprocessor generated incorrectly')
Azim Khan4b543232017-06-30 09:35:21 +010083
Azim Khanb31aa442018-07-03 11:57:54 +010084 def test_mixed_dependencies_list(self):
Azim Khan4b543232017-06-30 09:35:21 +010085 """
Azim Khanb31aa442018-07-03 11:57:54 +010086 Test that gen_dep() correctly creates dependencies for given
87 dependency list.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +010088 :return:
Azim Khan4b543232017-06-30 09:35:21 +010089 """
Azim Khanb31aa442018-07-03 11:57:54 +010090 dependencies = ['!DEP1', 'DEP2']
91 dep_start, dep_end = gen_dependencies(dependencies)
92 preprocessor1, preprocessor2 = dep_start.splitlines()
Azim Khan4b543232017-06-30 09:35:21 +010093 endif1, endif2 = dep_end.splitlines()
Azim Khanb31aa442018-07-03 11:57:54 +010094 self.assertEqual(preprocessor1, '#if !defined(DEP1)',
95 'Preprocessor generated incorrectly')
96 self.assertEqual(preprocessor2, '#if defined(DEP2)',
97 'Preprocessor generated incorrectly')
98 self.assertEqual(endif1, '#endif /* DEP2 */',
99 'Preprocessor generated incorrectly')
100 self.assertEqual(endif2, '#endif /* !DEP1 */',
101 'Preprocessor generated incorrectly')
Azim Khan4b543232017-06-30 09:35:21 +0100102
Azim Khanb31aa442018-07-03 11:57:54 +0100103 def test_empty_dependencies_list(self):
Azim Khan4b543232017-06-30 09:35:21 +0100104 """
Azim Khanb31aa442018-07-03 11:57:54 +0100105 Test that gen_dep() correctly creates dependencies for given
106 dependency list.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100107 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100108 """
Azim Khanb31aa442018-07-03 11:57:54 +0100109 dependencies = []
110 dep_start, dep_end = gen_dependencies(dependencies)
111 self.assertEqual(dep_start, '', 'Preprocessor generated incorrectly')
112 self.assertEqual(dep_end, '', 'Preprocessor generated incorrectly')
Azim Khan4b543232017-06-30 09:35:21 +0100113
Azim Khanb31aa442018-07-03 11:57:54 +0100114 def test_large_dependencies_list(self):
Azim Khan4b543232017-06-30 09:35:21 +0100115 """
Azim Khanb31aa442018-07-03 11:57:54 +0100116 Test that gen_dep() correctly creates dependencies for given
117 dependency list.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100118 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100119 """
Azim Khanb31aa442018-07-03 11:57:54 +0100120 dependencies = []
Azim Khan4b543232017-06-30 09:35:21 +0100121 count = 10
122 for i in range(count):
Azim Khanb31aa442018-07-03 11:57:54 +0100123 dependencies.append('DEP%d' % i)
124 dep_start, dep_end = gen_dependencies(dependencies)
125 self.assertEqual(len(dep_start.splitlines()), count,
126 'Preprocessor generated incorrectly')
127 self.assertEqual(len(dep_end.splitlines()), count,
128 'Preprocessor generated incorrectly')
Azim Khan4b543232017-06-30 09:35:21 +0100129
130
131class GenDepOneLine(TestCase):
132 """
Azim Khanb31aa442018-07-03 11:57:54 +0100133 Test Suite for testing gen_dependencies_one_line()
Azim Khan4b543232017-06-30 09:35:21 +0100134 """
135
Azim Khanb31aa442018-07-03 11:57:54 +0100136 def test_dependencies_list(self):
Azim Khan4b543232017-06-30 09:35:21 +0100137 """
Azim Khanb31aa442018-07-03 11:57:54 +0100138 Test that gen_dep() correctly creates dependencies for given
139 dependency list.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100140 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100141 """
Azim Khanb31aa442018-07-03 11:57:54 +0100142 dependencies = ['DEP1', 'DEP2']
143 dep_str = gen_dependencies_one_line(dependencies)
144 self.assertEqual(dep_str, '#if defined(DEP1) && defined(DEP2)',
145 'Preprocessor generated incorrectly')
Azim Khan4b543232017-06-30 09:35:21 +0100146
Azim Khanb31aa442018-07-03 11:57:54 +0100147 def test_disabled_dependencies_list(self):
Azim Khan4b543232017-06-30 09:35:21 +0100148 """
Azim Khanb31aa442018-07-03 11:57:54 +0100149 Test that gen_dep() correctly creates dependencies for given
150 dependency list.
Azim Khan4b543232017-06-30 09:35:21 +0100151 :return:
152 """
Azim Khanb31aa442018-07-03 11:57:54 +0100153 dependencies = ['!DEP1', '!DEP2']
154 dep_str = gen_dependencies_one_line(dependencies)
155 self.assertEqual(dep_str, '#if !defined(DEP1) && !defined(DEP2)',
156 'Preprocessor generated incorrectly')
Azim Khan4b543232017-06-30 09:35:21 +0100157
Azim Khanb31aa442018-07-03 11:57:54 +0100158 def test_mixed_dependencies_list(self):
Azim Khan4b543232017-06-30 09:35:21 +0100159 """
Azim Khanb31aa442018-07-03 11:57:54 +0100160 Test that gen_dep() correctly creates dependencies for given
161 dependency list.
Azim Khan4b543232017-06-30 09:35:21 +0100162 :return:
163 """
Azim Khanb31aa442018-07-03 11:57:54 +0100164 dependencies = ['!DEP1', 'DEP2']
165 dep_str = gen_dependencies_one_line(dependencies)
166 self.assertEqual(dep_str, '#if !defined(DEP1) && defined(DEP2)',
167 'Preprocessor generated incorrectly')
Azim Khan4b543232017-06-30 09:35:21 +0100168
Azim Khanb31aa442018-07-03 11:57:54 +0100169 def test_empty_dependencies_list(self):
Azim Khan4b543232017-06-30 09:35:21 +0100170 """
Azim Khanb31aa442018-07-03 11:57:54 +0100171 Test that gen_dep() correctly creates dependencies for given
172 dependency list.
Azim Khan4b543232017-06-30 09:35:21 +0100173 :return:
174 """
Azim Khanb31aa442018-07-03 11:57:54 +0100175 dependencies = []
176 dep_str = gen_dependencies_one_line(dependencies)
177 self.assertEqual(dep_str, '', 'Preprocessor generated incorrectly')
Azim Khan4b543232017-06-30 09:35:21 +0100178
Azim Khanb31aa442018-07-03 11:57:54 +0100179 def test_large_dependencies_list(self):
Azim Khan4b543232017-06-30 09:35:21 +0100180 """
Azim Khanb31aa442018-07-03 11:57:54 +0100181 Test that gen_dep() correctly creates dependencies for given
182 dependency list.
Azim Khan4b543232017-06-30 09:35:21 +0100183 :return:
184 """
Azim Khanb31aa442018-07-03 11:57:54 +0100185 dependencies = []
Azim Khan4b543232017-06-30 09:35:21 +0100186 count = 10
187 for i in range(count):
Azim Khanb31aa442018-07-03 11:57:54 +0100188 dependencies.append('DEP%d' % i)
189 dep_str = gen_dependencies_one_line(dependencies)
190 expected = '#if ' + ' && '.join(['defined(%s)' %
191 x for x in dependencies])
192 self.assertEqual(dep_str, expected,
193 'Preprocessor generated incorrectly')
Azim Khan4b543232017-06-30 09:35:21 +0100194
195
196class GenFunctionWrapper(TestCase):
197 """
198 Test Suite for testing gen_function_wrapper()
199 """
200
201 def test_params_unpack(self):
202 """
203 Test that params are properly unpacked in the function call.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100204
205 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100206 """
207 code = gen_function_wrapper('test_a', '', ('a', 'b', 'c', 'd'))
208 expected = '''
209void test_a_wrapper( void ** params )
210{
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100211
Azim Khan4b543232017-06-30 09:35:21 +0100212 test_a( a, b, c, d );
213}
214'''
215 self.assertEqual(code, expected)
216
217 def test_local(self):
218 """
219 Test that params are properly unpacked in the function call.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100220
221 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100222 """
Azim Khanb31aa442018-07-03 11:57:54 +0100223 code = gen_function_wrapper('test_a',
224 'int x = 1;', ('x', 'b', 'c', 'd'))
Azim Khan4b543232017-06-30 09:35:21 +0100225 expected = '''
226void test_a_wrapper( void ** params )
227{
Azim Khan4b543232017-06-30 09:35:21 +0100228int x = 1;
229 test_a( x, b, c, d );
230}
231'''
232 self.assertEqual(code, expected)
233
234 def test_empty_params(self):
235 """
236 Test that params are properly unpacked in the function call.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100237
238 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100239 """
240 code = gen_function_wrapper('test_a', '', ())
241 expected = '''
242void test_a_wrapper( void ** params )
243{
244 (void)params;
245
246 test_a( );
247}
248'''
249 self.assertEqual(code, expected)
250
251
252class GenDispatch(TestCase):
253 """
254 Test suite for testing gen_dispatch()
255 """
256
257 def test_dispatch(self):
258 """
259 Test that dispatch table entry is generated correctly.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100260 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100261 """
262 code = gen_dispatch('test_a', ['DEP1', 'DEP2'])
263 expected = '''
264#if defined(DEP1) && defined(DEP2)
265 test_a_wrapper,
266#else
267 NULL,
268#endif
269'''
270 self.assertEqual(code, expected)
271
Azim Khanb31aa442018-07-03 11:57:54 +0100272 def test_empty_dependencies(self):
Azim Khan4b543232017-06-30 09:35:21 +0100273 """
274 Test empty dependency list.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100275 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100276 """
277 code = gen_dispatch('test_a', [])
278 expected = '''
279 test_a_wrapper,
280'''
281 self.assertEqual(code, expected)
282
283
Gilles Peskine184c0962020-03-24 18:25:17 +0100284class StringIOWrapper(StringIO):
Azim Khan4b543232017-06-30 09:35:21 +0100285 """
286 file like class to mock file object in tests.
287 """
Azim Khan4084ec72018-07-05 14:20:08 +0100288 def __init__(self, file_name, data, line_no=0):
Azim Khan4b543232017-06-30 09:35:21 +0100289 """
290 Init file handle.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100291
292 :param file_name:
Azim Khan4b543232017-06-30 09:35:21 +0100293 :param data:
294 :param line_no:
295 """
296 super(StringIOWrapper, self).__init__(data)
297 self.line_no = line_no
298 self.name = file_name
299
300 def next(self):
301 """
Azim Khanb31aa442018-07-03 11:57:54 +0100302 Iterator method. This method overrides base class's
303 next method and extends the next method to count the line
304 numbers as each line is read.
Azim Khan4b543232017-06-30 09:35:21 +0100305
Azim Khanb31aa442018-07-03 11:57:54 +0100306 :return: Line read from file.
307 """
Mohammad Azim Khan539aa062018-07-06 00:29:50 +0100308 parent = super(StringIOWrapper, self)
Gilles Peskine38b66df2020-08-12 02:11:38 +0200309 line = parent.__next__()
Azim Khan4084ec72018-07-05 14:20:08 +0100310 return line
Azim Khanb31aa442018-07-03 11:57:54 +0100311
Gilles Peskine38b66df2020-08-12 02:11:38 +0200312 def readline(self, _length=0):
Azim Khan4b543232017-06-30 09:35:21 +0100313 """
314 Wrap the base class readline.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100315
Azim Khanb31aa442018-07-03 11:57:54 +0100316 :param length:
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100317 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100318 """
319 line = super(StringIOWrapper, self).readline()
Azim Khan4084ec72018-07-05 14:20:08 +0100320 if line is not None:
Azim Khan4b543232017-06-30 09:35:21 +0100321 self.line_no += 1
322 return line
323
324
Mohammad Azim Khanb5229292018-02-06 13:08:01 +0000325class ParseUntilPattern(TestCase):
Azim Khan4b543232017-06-30 09:35:21 +0100326 """
Mohammad Azim Khanb5229292018-02-06 13:08:01 +0000327 Test Suite for testing parse_until_pattern().
Azim Khan4b543232017-06-30 09:35:21 +0100328 """
329
330 def test_suite_headers(self):
331 """
332 Test that suite headers are parsed correctly.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100333
334 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100335 """
336 data = '''#include "mbedtls/ecp.h"
337
338#define ECP_PF_UNKNOWN -1
339/* END_HEADER */
340'''
341 expected = '''#line 1 "test_suite_ut.function"
342#include "mbedtls/ecp.h"
343
344#define ECP_PF_UNKNOWN -1
345'''
Azim Khanb31aa442018-07-03 11:57:54 +0100346 stream = StringIOWrapper('test_suite_ut.function', data, line_no=0)
347 headers = parse_until_pattern(stream, END_HEADER_REGEX)
Azim Khan4b543232017-06-30 09:35:21 +0100348 self.assertEqual(headers, expected)
349
350 def test_line_no(self):
351 """
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100352 Test that #line is set to correct line no. in source .function file.
353
354 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100355 """
356 data = '''#include "mbedtls/ecp.h"
357
358#define ECP_PF_UNKNOWN -1
359/* END_HEADER */
360'''
361 offset_line_no = 5
362 expected = '''#line %d "test_suite_ut.function"
363#include "mbedtls/ecp.h"
364
365#define ECP_PF_UNKNOWN -1
366''' % (offset_line_no + 1)
Azim Khanb31aa442018-07-03 11:57:54 +0100367 stream = StringIOWrapper('test_suite_ut.function', data,
368 offset_line_no)
369 headers = parse_until_pattern(stream, END_HEADER_REGEX)
Azim Khan4b543232017-06-30 09:35:21 +0100370 self.assertEqual(headers, expected)
371
372 def test_no_end_header_comment(self):
373 """
Azim Khanb31aa442018-07-03 11:57:54 +0100374 Test that InvalidFileFormat is raised when end header comment is
375 missing.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100376 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100377 """
378 data = '''#include "mbedtls/ecp.h"
379
380#define ECP_PF_UNKNOWN -1
381
382'''
Azim Khanb31aa442018-07-03 11:57:54 +0100383 stream = StringIOWrapper('test_suite_ut.function', data)
384 self.assertRaises(GeneratorInputError, parse_until_pattern, stream,
385 END_HEADER_REGEX)
Azim Khan4b543232017-06-30 09:35:21 +0100386
387
Azim Khanb31aa442018-07-03 11:57:54 +0100388class ParseSuiteDependencies(TestCase):
Azim Khan4b543232017-06-30 09:35:21 +0100389 """
Azim Khanb31aa442018-07-03 11:57:54 +0100390 Test Suite for testing parse_suite_dependencies().
Azim Khan4b543232017-06-30 09:35:21 +0100391 """
392
Azim Khanb31aa442018-07-03 11:57:54 +0100393 def test_suite_dependencies(self):
Azim Khan4b543232017-06-30 09:35:21 +0100394 """
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100395
396 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100397 """
398 data = '''
399 * depends_on:MBEDTLS_ECP_C
400 * END_DEPENDENCIES
401 */
402'''
403 expected = ['MBEDTLS_ECP_C']
Azim Khanb31aa442018-07-03 11:57:54 +0100404 stream = StringIOWrapper('test_suite_ut.function', data)
405 dependencies = parse_suite_dependencies(stream)
406 self.assertEqual(dependencies, expected)
Azim Khan4b543232017-06-30 09:35:21 +0100407
408 def test_no_end_dep_comment(self):
409 """
410 Test that InvalidFileFormat is raised when end dep comment is missing.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100411 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100412 """
413 data = '''
414* depends_on:MBEDTLS_ECP_C
415'''
Azim Khanb31aa442018-07-03 11:57:54 +0100416 stream = StringIOWrapper('test_suite_ut.function', data)
417 self.assertRaises(GeneratorInputError, parse_suite_dependencies,
418 stream)
Azim Khan4b543232017-06-30 09:35:21 +0100419
Azim Khanb31aa442018-07-03 11:57:54 +0100420 def test_dependencies_split(self):
Azim Khan4b543232017-06-30 09:35:21 +0100421 """
422 Test that InvalidFileFormat is raised when end dep comment is missing.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100423 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100424 """
425 data = '''
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100426 * depends_on:MBEDTLS_ECP_C:A:B: C : D :F : G: !H
Azim Khan4b543232017-06-30 09:35:21 +0100427 * END_DEPENDENCIES
428 */
429'''
430 expected = ['MBEDTLS_ECP_C', 'A', 'B', 'C', 'D', 'F', 'G', '!H']
Azim Khanb31aa442018-07-03 11:57:54 +0100431 stream = StringIOWrapper('test_suite_ut.function', data)
432 dependencies = parse_suite_dependencies(stream)
433 self.assertEqual(dependencies, expected)
Azim Khan4b543232017-06-30 09:35:21 +0100434
435
Azim Khanb31aa442018-07-03 11:57:54 +0100436class ParseFuncDependencies(TestCase):
Azim Khan4b543232017-06-30 09:35:21 +0100437 """
Azim Khanb31aa442018-07-03 11:57:54 +0100438 Test Suite for testing parse_function_dependencies()
Azim Khan4b543232017-06-30 09:35:21 +0100439 """
440
Azim Khanb31aa442018-07-03 11:57:54 +0100441 def test_function_dependencies(self):
Azim Khan4b543232017-06-30 09:35:21 +0100442 """
Azim Khanb31aa442018-07-03 11:57:54 +0100443 Test that parse_function_dependencies() correctly parses function
444 dependencies.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100445 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100446 """
Azim Khanb31aa442018-07-03 11:57:54 +0100447 line = '/* BEGIN_CASE ' \
448 'depends_on:MBEDTLS_ENTROPY_NV_SEED:MBEDTLS_FS_IO */'
Azim Khan4b543232017-06-30 09:35:21 +0100449 expected = ['MBEDTLS_ENTROPY_NV_SEED', 'MBEDTLS_FS_IO']
Azim Khanb31aa442018-07-03 11:57:54 +0100450 dependencies = parse_function_dependencies(line)
451 self.assertEqual(dependencies, expected)
Azim Khan4b543232017-06-30 09:35:21 +0100452
Azim Khanb31aa442018-07-03 11:57:54 +0100453 def test_no_dependencies(self):
Azim Khan4b543232017-06-30 09:35:21 +0100454 """
Azim Khanb31aa442018-07-03 11:57:54 +0100455 Test that parse_function_dependencies() correctly parses function
456 dependencies.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100457 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100458 """
459 line = '/* BEGIN_CASE */'
Azim Khanb31aa442018-07-03 11:57:54 +0100460 dependencies = parse_function_dependencies(line)
461 self.assertEqual(dependencies, [])
Azim Khan4b543232017-06-30 09:35:21 +0100462
Azim Khanb31aa442018-07-03 11:57:54 +0100463 def test_tolerance(self):
Azim Khan4b543232017-06-30 09:35:21 +0100464 """
Azim Khanb31aa442018-07-03 11:57:54 +0100465 Test that parse_function_dependencies() correctly parses function
466 dependencies.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100467 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100468 """
469 line = '/* BEGIN_CASE depends_on:MBEDTLS_FS_IO: A : !B:C : F*/'
Azim Khanb31aa442018-07-03 11:57:54 +0100470 dependencies = parse_function_dependencies(line)
471 self.assertEqual(dependencies, ['MBEDTLS_FS_IO', 'A', '!B', 'C', 'F'])
Azim Khan4b543232017-06-30 09:35:21 +0100472
473
474class ParseFuncSignature(TestCase):
475 """
Azim Khanfcdf6852018-07-05 17:31:46 +0100476 Test Suite for parse_function_arguments().
Azim Khan4b543232017-06-30 09:35:21 +0100477 """
478
479 def test_int_and_char_params(self):
480 """
Azim Khanf0e42fb2017-08-02 14:47:13 +0100481 Test int and char parameters parsing
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100482 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100483 """
484 line = 'void entropy_threshold( char * a, int b, int result )'
Azim Khanfcdf6852018-07-05 17:31:46 +0100485 args, local, arg_dispatch = parse_function_arguments(line)
Azim Khan4b543232017-06-30 09:35:21 +0100486 self.assertEqual(args, ['char*', 'int', 'int'])
487 self.assertEqual(local, '')
Gilles Peskineb3c2eaf2022-12-04 13:10:55 +0100488 self.assertEqual(arg_dispatch,
489 ['(char *) params[0]',
Gilles Peskineb70c4e02023-04-26 19:59:28 +0200490 '((mbedtls_test_argument_t *) params[1])->sint',
491 '((mbedtls_test_argument_t *) params[2])->sint'])
Azim Khan4b543232017-06-30 09:35:21 +0100492
493 def test_hex_params(self):
494 """
Azim Khanf0e42fb2017-08-02 14:47:13 +0100495 Test hex parameters parsing
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100496 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100497 """
Azim Khan5fcca462018-06-29 11:05:32 +0100498 line = 'void entropy_threshold( char * a, data_t * h, int result )'
Azim Khanfcdf6852018-07-05 17:31:46 +0100499 args, local, arg_dispatch = parse_function_arguments(line)
Azim Khan4b543232017-06-30 09:35:21 +0100500 self.assertEqual(args, ['char*', 'hex', 'int'])
Azim Khanb31aa442018-07-03 11:57:54 +0100501 self.assertEqual(local,
Azim Khan4084ec72018-07-05 14:20:08 +0100502 ' data_t data1 = {(uint8_t *) params[1], '
Gilles Peskineb70c4e02023-04-26 19:59:28 +0200503 '((mbedtls_test_argument_t *) params[2])->len};\n')
Azim Khanb31aa442018-07-03 11:57:54 +0100504 self.assertEqual(arg_dispatch, ['(char *) params[0]',
Azim Khan4084ec72018-07-05 14:20:08 +0100505 '&data1',
Gilles Peskineb70c4e02023-04-26 19:59:28 +0200506 '((mbedtls_test_argument_t *) params[3])->sint'])
Azim Khan4b543232017-06-30 09:35:21 +0100507
Azim Khan4b543232017-06-30 09:35:21 +0100508 def test_unsupported_arg(self):
509 """
Gilles Peskine6f5082b2022-12-04 15:57:49 +0100510 Test unsupported argument type
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100511 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100512 """
Gilles Peskine6f5082b2022-12-04 15:57:49 +0100513 line = 'void entropy_threshold( char * a, data_t * h, unknown_t result )'
Azim Khanfcdf6852018-07-05 17:31:46 +0100514 self.assertRaises(ValueError, parse_function_arguments, line)
Azim Khan4b543232017-06-30 09:35:21 +0100515
Gilles Peskine47e2e882022-12-04 14:29:06 +0100516 def test_empty_params(self):
Azim Khan4b543232017-06-30 09:35:21 +0100517 """
Gilles Peskine47e2e882022-12-04 14:29:06 +0100518 Test no parameters (nothing between parentheses).
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100519 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100520 """
521 line = 'void entropy_threshold()'
Azim Khanfcdf6852018-07-05 17:31:46 +0100522 args, local, arg_dispatch = parse_function_arguments(line)
Azim Khan4b543232017-06-30 09:35:21 +0100523 self.assertEqual(args, [])
524 self.assertEqual(local, '')
525 self.assertEqual(arg_dispatch, [])
526
Gilles Peskine47e2e882022-12-04 14:29:06 +0100527 def test_blank_params(self):
528 """
529 Test no parameters (space between parentheses).
530 :return:
531 """
532 line = 'void entropy_threshold( )'
533 args, local, arg_dispatch = parse_function_arguments(line)
534 self.assertEqual(args, [])
535 self.assertEqual(local, '')
536 self.assertEqual(arg_dispatch, [])
537
538 def test_void_params(self):
539 """
540 Test no parameters (void keyword).
541 :return:
542 """
543 line = 'void entropy_threshold(void)'
544 args, local, arg_dispatch = parse_function_arguments(line)
545 self.assertEqual(args, [])
546 self.assertEqual(local, '')
547 self.assertEqual(arg_dispatch, [])
548
549 def test_void_space_params(self):
550 """
551 Test no parameters (void with spaces).
552 :return:
553 """
554 line = 'void entropy_threshold( void )'
555 args, local, arg_dispatch = parse_function_arguments(line)
556 self.assertEqual(args, [])
557 self.assertEqual(local, '')
558 self.assertEqual(arg_dispatch, [])
559
Azim Khan4b543232017-06-30 09:35:21 +0100560
561class ParseFunctionCode(TestCase):
562 """
563 Test suite for testing parse_function_code()
564 """
565
566 def test_no_function(self):
567 """
Azim Khanf0e42fb2017-08-02 14:47:13 +0100568 Test no test function found.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100569 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100570 """
571 data = '''
572No
573test
574function
575'''
Azim Khanb31aa442018-07-03 11:57:54 +0100576 stream = StringIOWrapper('test_suite_ut.function', data)
Azim Khanfcdf6852018-07-05 17:31:46 +0100577 err_msg = 'file: test_suite_ut.function - Test functions not found!'
Gilles Peskine38b66df2020-08-12 02:11:38 +0200578 self.assertRaisesRegex(GeneratorInputError, err_msg,
579 parse_function_code, stream, [], [])
Azim Khan4b543232017-06-30 09:35:21 +0100580
581 def test_no_end_case_comment(self):
582 """
Azim Khanf0e42fb2017-08-02 14:47:13 +0100583 Test missing end case.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100584 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100585 """
586 data = '''
587void test_func()
588{
589}
590'''
Azim Khanb31aa442018-07-03 11:57:54 +0100591 stream = StringIOWrapper('test_suite_ut.function', data)
Azim Khanfcdf6852018-07-05 17:31:46 +0100592 err_msg = r'file: test_suite_ut.function - '\
593 'end case pattern .*? not found!'
Gilles Peskine38b66df2020-08-12 02:11:38 +0200594 self.assertRaisesRegex(GeneratorInputError, err_msg,
595 parse_function_code, stream, [], [])
Azim Khan4b543232017-06-30 09:35:21 +0100596
Azim Khanfcdf6852018-07-05 17:31:46 +0100597 @patch("generate_test_code.parse_function_arguments")
Azim Khanb31aa442018-07-03 11:57:54 +0100598 def test_function_called(self,
Azim Khanfcdf6852018-07-05 17:31:46 +0100599 parse_function_arguments_mock):
Azim Khan4b543232017-06-30 09:35:21 +0100600 """
Azim Khanf0e42fb2017-08-02 14:47:13 +0100601 Test parse_function_code()
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100602 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100603 """
Azim Khanfcdf6852018-07-05 17:31:46 +0100604 parse_function_arguments_mock.return_value = ([], '', [])
Azim Khan4b543232017-06-30 09:35:21 +0100605 data = '''
606void test_func()
607{
608}
609'''
Azim Khanb31aa442018-07-03 11:57:54 +0100610 stream = StringIOWrapper('test_suite_ut.function', data)
611 self.assertRaises(GeneratorInputError, parse_function_code,
612 stream, [], [])
Azim Khanfcdf6852018-07-05 17:31:46 +0100613 self.assertTrue(parse_function_arguments_mock.called)
614 parse_function_arguments_mock.assert_called_with('void test_func()\n')
Azim Khan4b543232017-06-30 09:35:21 +0100615
Mohammad Azim Khan78befd92018-03-06 11:49:41 +0000616 @patch("generate_test_code.gen_dispatch")
Azim Khanb31aa442018-07-03 11:57:54 +0100617 @patch("generate_test_code.gen_dependencies")
Mohammad Azim Khan78befd92018-03-06 11:49:41 +0000618 @patch("generate_test_code.gen_function_wrapper")
Azim Khanfcdf6852018-07-05 17:31:46 +0100619 @patch("generate_test_code.parse_function_arguments")
620 def test_return(self, parse_function_arguments_mock,
Azim Khanb31aa442018-07-03 11:57:54 +0100621 gen_function_wrapper_mock,
622 gen_dependencies_mock,
623 gen_dispatch_mock):
Azim Khan4b543232017-06-30 09:35:21 +0100624 """
Azim Khanf0e42fb2017-08-02 14:47:13 +0100625 Test generated code.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100626 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100627 """
Azim Khanfcdf6852018-07-05 17:31:46 +0100628 parse_function_arguments_mock.return_value = ([], '', [])
Azim Khan4b543232017-06-30 09:35:21 +0100629 gen_function_wrapper_mock.return_value = ''
Azim Khanb31aa442018-07-03 11:57:54 +0100630 gen_dependencies_mock.side_effect = gen_dependencies
Azim Khan4b543232017-06-30 09:35:21 +0100631 gen_dispatch_mock.side_effect = gen_dispatch
632 data = '''
633void func()
634{
635 ba ba black sheep
636 have you any wool
637}
638/* END_CASE */
639'''
Azim Khanb31aa442018-07-03 11:57:54 +0100640 stream = StringIOWrapper('test_suite_ut.function', data)
641 name, arg, code, dispatch_code = parse_function_code(stream, [], [])
Azim Khan4b543232017-06-30 09:35:21 +0100642
Azim Khanfcdf6852018-07-05 17:31:46 +0100643 self.assertTrue(parse_function_arguments_mock.called)
644 parse_function_arguments_mock.assert_called_with('void func()\n')
Azim Khan4b543232017-06-30 09:35:21 +0100645 gen_function_wrapper_mock.assert_called_with('test_func', '', [])
646 self.assertEqual(name, 'test_func')
647 self.assertEqual(arg, [])
Azim Khan4084ec72018-07-05 14:20:08 +0100648 expected = '''#line 1 "test_suite_ut.function"
649
Azim Khan4b543232017-06-30 09:35:21 +0100650void test_func()
651{
652 ba ba black sheep
653 have you any wool
654exit:
Azim Khan4084ec72018-07-05 14:20:08 +0100655 ;
Azim Khan4b543232017-06-30 09:35:21 +0100656}
657'''
658 self.assertEqual(code, expected)
659 self.assertEqual(dispatch_code, "\n test_func_wrapper,\n")
660
Mohammad Azim Khan78befd92018-03-06 11:49:41 +0000661 @patch("generate_test_code.gen_dispatch")
Azim Khanb31aa442018-07-03 11:57:54 +0100662 @patch("generate_test_code.gen_dependencies")
Mohammad Azim Khan78befd92018-03-06 11:49:41 +0000663 @patch("generate_test_code.gen_function_wrapper")
Azim Khanfcdf6852018-07-05 17:31:46 +0100664 @patch("generate_test_code.parse_function_arguments")
665 def test_with_exit_label(self, parse_function_arguments_mock,
Azim Khanb31aa442018-07-03 11:57:54 +0100666 gen_function_wrapper_mock,
667 gen_dependencies_mock,
668 gen_dispatch_mock):
Azim Khan4b543232017-06-30 09:35:21 +0100669 """
Azim Khanf0e42fb2017-08-02 14:47:13 +0100670 Test when exit label is present.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100671 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100672 """
Azim Khanfcdf6852018-07-05 17:31:46 +0100673 parse_function_arguments_mock.return_value = ([], '', [])
Azim Khan4b543232017-06-30 09:35:21 +0100674 gen_function_wrapper_mock.return_value = ''
Azim Khanb31aa442018-07-03 11:57:54 +0100675 gen_dependencies_mock.side_effect = gen_dependencies
Azim Khan4b543232017-06-30 09:35:21 +0100676 gen_dispatch_mock.side_effect = gen_dispatch
677 data = '''
678void func()
679{
680 ba ba black sheep
681 have you any wool
682exit:
683 yes sir yes sir
684 3 bags full
685}
686/* END_CASE */
687'''
Azim Khanb31aa442018-07-03 11:57:54 +0100688 stream = StringIOWrapper('test_suite_ut.function', data)
689 _, _, code, _ = parse_function_code(stream, [], [])
Azim Khan4b543232017-06-30 09:35:21 +0100690
Azim Khan4084ec72018-07-05 14:20:08 +0100691 expected = '''#line 1 "test_suite_ut.function"
692
Azim Khan4b543232017-06-30 09:35:21 +0100693void test_func()
694{
695 ba ba black sheep
696 have you any wool
697exit:
698 yes sir yes sir
699 3 bags full
700}
701'''
702 self.assertEqual(code, expected)
703
Azim Khanfcdf6852018-07-05 17:31:46 +0100704 def test_non_void_function(self):
705 """
706 Test invalid signature (non void).
707 :return:
708 """
709 data = 'int entropy_threshold( char * a, data_t * h, int result )'
710 err_msg = 'file: test_suite_ut.function - Test functions not found!'
711 stream = StringIOWrapper('test_suite_ut.function', data)
Gilles Peskine38b66df2020-08-12 02:11:38 +0200712 self.assertRaisesRegex(GeneratorInputError, err_msg,
713 parse_function_code, stream, [], [])
Azim Khanfcdf6852018-07-05 17:31:46 +0100714
715 @patch("generate_test_code.gen_dispatch")
716 @patch("generate_test_code.gen_dependencies")
717 @patch("generate_test_code.gen_function_wrapper")
718 @patch("generate_test_code.parse_function_arguments")
Gilles Peskine0cf42202022-11-11 16:36:51 +0100719 def test_function_name_on_newline(self, parse_function_arguments_mock,
720 gen_function_wrapper_mock,
721 gen_dependencies_mock,
722 gen_dispatch_mock):
Azim Khanfcdf6852018-07-05 17:31:46 +0100723 """
Gilles Peskine0cf42202022-11-11 16:36:51 +0100724 Test with line break before the function name.
Azim Khanfcdf6852018-07-05 17:31:46 +0100725 :return:
726 """
727 parse_function_arguments_mock.return_value = ([], '', [])
728 gen_function_wrapper_mock.return_value = ''
729 gen_dependencies_mock.side_effect = gen_dependencies
730 gen_dispatch_mock.side_effect = gen_dispatch
731 data = '''
732void
733
734
735func()
736{
737 ba ba black sheep
738 have you any wool
739exit:
740 yes sir yes sir
741 3 bags full
742}
743/* END_CASE */
744'''
745 stream = StringIOWrapper('test_suite_ut.function', data)
746 _, _, code, _ = parse_function_code(stream, [], [])
747
748 expected = '''#line 1 "test_suite_ut.function"
749
750void
751
752
753test_func()
754{
755 ba ba black sheep
756 have you any wool
757exit:
758 yes sir yes sir
759 3 bags full
760}
761'''
762 self.assertEqual(code, expected)
763
Gilles Peskine07510f52022-11-11 16:37:16 +0100764 @patch("generate_test_code.gen_dispatch")
765 @patch("generate_test_code.gen_dependencies")
766 @patch("generate_test_code.gen_function_wrapper")
767 @patch("generate_test_code.parse_function_arguments")
768 def test_case_starting_with_comment(self, parse_function_arguments_mock,
769 gen_function_wrapper_mock,
770 gen_dependencies_mock,
771 gen_dispatch_mock):
772 """
773 Test with comments before the function signature
774 :return:
775 """
776 parse_function_arguments_mock.return_value = ([], '', [])
777 gen_function_wrapper_mock.return_value = ''
778 gen_dependencies_mock.side_effect = gen_dependencies
779 gen_dispatch_mock.side_effect = gen_dispatch
780 data = '''/* comment */
781/* more
782 * comment */
Gilles Peskine18f48eb2022-11-18 22:24:56 +0100783// this is\\
784still \\
Gilles Peskine07510f52022-11-11 16:37:16 +0100785a comment
786void func()
787{
788 ba ba black sheep
789 have you any wool
790exit:
791 yes sir yes sir
792 3 bags full
793}
794/* END_CASE */
795'''
796 stream = StringIOWrapper('test_suite_ut.function', data)
797 _, _, code, _ = parse_function_code(stream, [], [])
798
799 expected = '''#line 1 "test_suite_ut.function"
800
801
802
Gilles Peskined8c08032022-11-29 22:03:32 +0100803
Gilles Peskine18f70282022-11-30 16:38:49 +0100804
805
Gilles Peskine07510f52022-11-11 16:37:16 +0100806void test_func()
807{
808 ba ba black sheep
809 have you any wool
810exit:
811 yes sir yes sir
812 3 bags full
813}
814'''
815 self.assertEqual(code, expected)
816
817 @patch("generate_test_code.gen_dispatch")
818 @patch("generate_test_code.gen_dependencies")
819 @patch("generate_test_code.gen_function_wrapper")
820 @patch("generate_test_code.parse_function_arguments")
821 def test_comment_in_prototype(self, parse_function_arguments_mock,
822 gen_function_wrapper_mock,
823 gen_dependencies_mock,
824 gen_dispatch_mock):
825 """
826 Test with comments in the function prototype
827 :return:
828 """
829 parse_function_arguments_mock.return_value = ([], '', [])
830 gen_function_wrapper_mock.return_value = ''
831 gen_dependencies_mock.side_effect = gen_dependencies
832 gen_dispatch_mock.side_effect = gen_dispatch
833 data = '''
834void func( int x, // (line \\
835 comment)
836 int y /* lone closing parenthesis) */ )
837{
838 ba ba black sheep
839 have you any wool
840exit:
841 yes sir yes sir
842 3 bags full
843}
844/* END_CASE */
845'''
846 stream = StringIOWrapper('test_suite_ut.function', data)
847 _, _, code, _ = parse_function_code(stream, [], [])
848
849 expected = '''#line 1 "test_suite_ut.function"
850
851void test_func( int x,
Gilles Peskine18f70282022-11-30 16:38:49 +0100852
Gilles Peskine07510f52022-11-11 16:37:16 +0100853 int y )
854{
855 ba ba black sheep
856 have you any wool
857exit:
858 yes sir yes sir
859 3 bags full
860}
861'''
862 self.assertEqual(code, expected)
863
Gilles Peskine45747a02022-11-18 22:25:18 +0100864 @patch("generate_test_code.gen_dispatch")
865 @patch("generate_test_code.gen_dependencies")
866 @patch("generate_test_code.gen_function_wrapper")
867 @patch("generate_test_code.parse_function_arguments")
868 def test_line_comment_in_block_comment(self, parse_function_arguments_mock,
869 gen_function_wrapper_mock,
870 gen_dependencies_mock,
871 gen_dispatch_mock):
872 """
873 Test with line comment in block comment.
874 :return:
875 """
876 parse_function_arguments_mock.return_value = ([], '', [])
877 gen_function_wrapper_mock.return_value = ''
878 gen_dependencies_mock.side_effect = gen_dependencies
879 gen_dispatch_mock.side_effect = gen_dispatch
880 data = '''
881void func( int x /* // */ )
882{
883 ba ba black sheep
884 have you any wool
885exit:
886 yes sir yes sir
887 3 bags full
888}
889/* END_CASE */
890'''
891 stream = StringIOWrapper('test_suite_ut.function', data)
892 _, _, code, _ = parse_function_code(stream, [], [])
893
894 expected = '''#line 1 "test_suite_ut.function"
895
896void test_func( int x )
897{
898 ba ba black sheep
899 have you any wool
900exit:
901 yes sir yes sir
902 3 bags full
903}
904'''
905 self.assertEqual(code, expected)
906
907 @patch("generate_test_code.gen_dispatch")
908 @patch("generate_test_code.gen_dependencies")
909 @patch("generate_test_code.gen_function_wrapper")
910 @patch("generate_test_code.parse_function_arguments")
911 def test_block_comment_in_line_comment(self, parse_function_arguments_mock,
912 gen_function_wrapper_mock,
913 gen_dependencies_mock,
914 gen_dispatch_mock):
915 """
916 Test with block comment in line comment.
917 :return:
918 """
919 parse_function_arguments_mock.return_value = ([], '', [])
920 gen_function_wrapper_mock.return_value = ''
921 gen_dependencies_mock.side_effect = gen_dependencies
922 gen_dispatch_mock.side_effect = gen_dispatch
923 data = '''
924// /*
925void func( int x )
926{
927 ba ba black sheep
928 have you any wool
929exit:
930 yes sir yes sir
931 3 bags full
932}
933/* END_CASE */
934'''
935 stream = StringIOWrapper('test_suite_ut.function', data)
936 _, _, code, _ = parse_function_code(stream, [], [])
937
938 expected = '''#line 1 "test_suite_ut.function"
939
940
941void test_func( int x )
942{
943 ba ba black sheep
944 have you any wool
945exit:
946 yes sir yes sir
947 3 bags full
948}
949'''
950 self.assertEqual(code, expected)
951
Azim Khan4b543232017-06-30 09:35:21 +0100952
953class ParseFunction(TestCase):
954 """
955 Test Suite for testing parse_functions()
956 """
957
Mohammad Azim Khan78befd92018-03-06 11:49:41 +0000958 @patch("generate_test_code.parse_until_pattern")
Mohammad Azim Khanb5229292018-02-06 13:08:01 +0000959 def test_begin_header(self, parse_until_pattern_mock):
Azim Khan4b543232017-06-30 09:35:21 +0100960 """
Mohammad Azim Khanb5229292018-02-06 13:08:01 +0000961 Test that begin header is checked and parse_until_pattern() is called.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100962 :return:
Azim Khan4b543232017-06-30 09:35:21 +0100963 """
Azim Khanb31aa442018-07-03 11:57:54 +0100964 def stop(*_unused):
965 """Stop when parse_until_pattern is called."""
Azim Khan4b543232017-06-30 09:35:21 +0100966 raise Exception
Mohammad Azim Khanb5229292018-02-06 13:08:01 +0000967 parse_until_pattern_mock.side_effect = stop
Azim Khan4b543232017-06-30 09:35:21 +0100968 data = '''/* BEGIN_HEADER */
969#include "mbedtls/ecp.h"
970
971#define ECP_PF_UNKNOWN -1
972/* END_HEADER */
973'''
Azim Khanb31aa442018-07-03 11:57:54 +0100974 stream = StringIOWrapper('test_suite_ut.function', data)
975 self.assertRaises(Exception, parse_functions, stream)
976 parse_until_pattern_mock.assert_called_with(stream, END_HEADER_REGEX)
Azim Khan4084ec72018-07-05 14:20:08 +0100977 self.assertEqual(stream.line_no, 1)
Mohammad Azim Khanb5229292018-02-06 13:08:01 +0000978
Mohammad Azim Khan78befd92018-03-06 11:49:41 +0000979 @patch("generate_test_code.parse_until_pattern")
Mohammad Azim Khanb5229292018-02-06 13:08:01 +0000980 def test_begin_helper(self, parse_until_pattern_mock):
981 """
982 Test that begin helper is checked and parse_until_pattern() is called.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +0100983 :return:
Mohammad Azim Khanb5229292018-02-06 13:08:01 +0000984 """
Azim Khanb31aa442018-07-03 11:57:54 +0100985 def stop(*_unused):
986 """Stop when parse_until_pattern is called."""
Mohammad Azim Khanb5229292018-02-06 13:08:01 +0000987 raise Exception
988 parse_until_pattern_mock.side_effect = stop
989 data = '''/* BEGIN_SUITE_HELPERS */
Azim Khanb31aa442018-07-03 11:57:54 +0100990void print_hello_world()
Mohammad Azim Khanb5229292018-02-06 13:08:01 +0000991{
Azim Khanb31aa442018-07-03 11:57:54 +0100992 printf("Hello World!\n");
Mohammad Azim Khanb5229292018-02-06 13:08:01 +0000993}
994/* END_SUITE_HELPERS */
995'''
Azim Khanb31aa442018-07-03 11:57:54 +0100996 stream = StringIOWrapper('test_suite_ut.function', data)
997 self.assertRaises(Exception, parse_functions, stream)
998 parse_until_pattern_mock.assert_called_with(stream,
999 END_SUITE_HELPERS_REGEX)
Azim Khan4084ec72018-07-05 14:20:08 +01001000 self.assertEqual(stream.line_no, 1)
Azim Khan4b543232017-06-30 09:35:21 +01001001
Azim Khanb31aa442018-07-03 11:57:54 +01001002 @patch("generate_test_code.parse_suite_dependencies")
1003 def test_begin_dep(self, parse_suite_dependencies_mock):
Azim Khan4b543232017-06-30 09:35:21 +01001004 """
Azim Khanb31aa442018-07-03 11:57:54 +01001005 Test that begin dep is checked and parse_suite_dependencies() is
1006 called.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001007 :return:
Azim Khan4b543232017-06-30 09:35:21 +01001008 """
Azim Khanb31aa442018-07-03 11:57:54 +01001009 def stop(*_unused):
1010 """Stop when parse_until_pattern is called."""
Azim Khan4b543232017-06-30 09:35:21 +01001011 raise Exception
Azim Khanb31aa442018-07-03 11:57:54 +01001012 parse_suite_dependencies_mock.side_effect = stop
Azim Khan4b543232017-06-30 09:35:21 +01001013 data = '''/* BEGIN_DEPENDENCIES
1014 * depends_on:MBEDTLS_ECP_C
1015 * END_DEPENDENCIES
1016 */
1017'''
Azim Khanb31aa442018-07-03 11:57:54 +01001018 stream = StringIOWrapper('test_suite_ut.function', data)
1019 self.assertRaises(Exception, parse_functions, stream)
1020 parse_suite_dependencies_mock.assert_called_with(stream)
Azim Khan4084ec72018-07-05 14:20:08 +01001021 self.assertEqual(stream.line_no, 1)
Azim Khan4b543232017-06-30 09:35:21 +01001022
Azim Khanb31aa442018-07-03 11:57:54 +01001023 @patch("generate_test_code.parse_function_dependencies")
1024 def test_begin_function_dep(self, func_mock):
Azim Khan4b543232017-06-30 09:35:21 +01001025 """
Azim Khanb31aa442018-07-03 11:57:54 +01001026 Test that begin dep is checked and parse_function_dependencies() is
1027 called.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001028 :return:
Azim Khan4b543232017-06-30 09:35:21 +01001029 """
Azim Khanb31aa442018-07-03 11:57:54 +01001030 def stop(*_unused):
1031 """Stop when parse_until_pattern is called."""
Azim Khan4b543232017-06-30 09:35:21 +01001032 raise Exception
Azim Khanb31aa442018-07-03 11:57:54 +01001033 func_mock.side_effect = stop
Azim Khan4b543232017-06-30 09:35:21 +01001034
Azim Khanb31aa442018-07-03 11:57:54 +01001035 dependencies_str = '/* BEGIN_CASE ' \
1036 'depends_on:MBEDTLS_ENTROPY_NV_SEED:MBEDTLS_FS_IO */\n'
Azim Khan4b543232017-06-30 09:35:21 +01001037 data = '''%svoid test_func()
1038{
1039}
Azim Khanb31aa442018-07-03 11:57:54 +01001040''' % dependencies_str
1041 stream = StringIOWrapper('test_suite_ut.function', data)
1042 self.assertRaises(Exception, parse_functions, stream)
1043 func_mock.assert_called_with(dependencies_str)
Azim Khan4084ec72018-07-05 14:20:08 +01001044 self.assertEqual(stream.line_no, 1)
Azim Khan4b543232017-06-30 09:35:21 +01001045
Mohammad Azim Khan78befd92018-03-06 11:49:41 +00001046 @patch("generate_test_code.parse_function_code")
Azim Khanb31aa442018-07-03 11:57:54 +01001047 @patch("generate_test_code.parse_function_dependencies")
1048 def test_return(self, func_mock1, func_mock2):
Azim Khan4b543232017-06-30 09:35:21 +01001049 """
Mohammad Azim Khanb5229292018-02-06 13:08:01 +00001050 Test that begin case is checked and parse_function_code() is called.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001051 :return:
Azim Khan4b543232017-06-30 09:35:21 +01001052 """
Azim Khanb31aa442018-07-03 11:57:54 +01001053 func_mock1.return_value = []
1054 in_func_code = '''void test_func()
Azim Khan4b543232017-06-30 09:35:21 +01001055{
1056}
1057'''
1058 func_dispatch = '''
1059 test_func_wrapper,
1060'''
Azim Khanb31aa442018-07-03 11:57:54 +01001061 func_mock2.return_value = 'test_func', [],\
1062 in_func_code, func_dispatch
1063 dependencies_str = '/* BEGIN_CASE ' \
1064 'depends_on:MBEDTLS_ENTROPY_NV_SEED:MBEDTLS_FS_IO */\n'
Azim Khan4b543232017-06-30 09:35:21 +01001065 data = '''%svoid test_func()
1066{
1067}
Azim Khanb31aa442018-07-03 11:57:54 +01001068''' % dependencies_str
1069 stream = StringIOWrapper('test_suite_ut.function', data)
1070 suite_dependencies, dispatch_code, func_code, func_info = \
1071 parse_functions(stream)
1072 func_mock1.assert_called_with(dependencies_str)
1073 func_mock2.assert_called_with(stream, [], [])
1074 self.assertEqual(stream.line_no, 5)
1075 self.assertEqual(suite_dependencies, [])
Azim Khan4b543232017-06-30 09:35:21 +01001076 expected_dispatch_code = '''/* Function Id: 0 */
1077
1078 test_func_wrapper,
1079'''
1080 self.assertEqual(dispatch_code, expected_dispatch_code)
1081 self.assertEqual(func_code, in_func_code)
1082 self.assertEqual(func_info, {'test_func': (0, [])})
1083
1084 def test_parsing(self):
1085 """
Mohammad Azim Khanb5229292018-02-06 13:08:01 +00001086 Test case parsing.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001087 :return:
Azim Khan4b543232017-06-30 09:35:21 +01001088 """
1089 data = '''/* BEGIN_HEADER */
1090#include "mbedtls/ecp.h"
1091
1092#define ECP_PF_UNKNOWN -1
1093/* END_HEADER */
1094
1095/* BEGIN_DEPENDENCIES
1096 * depends_on:MBEDTLS_ECP_C
1097 * END_DEPENDENCIES
1098 */
1099
1100/* BEGIN_CASE depends_on:MBEDTLS_ENTROPY_NV_SEED:MBEDTLS_FS_IO */
1101void func1()
1102{
1103}
1104/* END_CASE */
1105
1106/* BEGIN_CASE depends_on:MBEDTLS_ENTROPY_NV_SEED:MBEDTLS_FS_IO */
1107void func2()
1108{
1109}
1110/* END_CASE */
1111'''
Azim Khanb31aa442018-07-03 11:57:54 +01001112 stream = StringIOWrapper('test_suite_ut.function', data)
1113 suite_dependencies, dispatch_code, func_code, func_info = \
1114 parse_functions(stream)
1115 self.assertEqual(stream.line_no, 23)
1116 self.assertEqual(suite_dependencies, ['MBEDTLS_ECP_C'])
Azim Khan4b543232017-06-30 09:35:21 +01001117
1118 expected_dispatch_code = '''/* Function Id: 0 */
1119
1120#if defined(MBEDTLS_ECP_C) && defined(MBEDTLS_ENTROPY_NV_SEED) && defined(MBEDTLS_FS_IO)
1121 test_func1_wrapper,
1122#else
1123 NULL,
1124#endif
1125/* Function Id: 1 */
1126
1127#if defined(MBEDTLS_ECP_C) && defined(MBEDTLS_ENTROPY_NV_SEED) && defined(MBEDTLS_FS_IO)
1128 test_func2_wrapper,
1129#else
1130 NULL,
1131#endif
1132'''
1133 self.assertEqual(dispatch_code, expected_dispatch_code)
1134 expected_func_code = '''#if defined(MBEDTLS_ECP_C)
Azim Khan4084ec72018-07-05 14:20:08 +01001135#line 2 "test_suite_ut.function"
Azim Khan4b543232017-06-30 09:35:21 +01001136#include "mbedtls/ecp.h"
1137
1138#define ECP_PF_UNKNOWN -1
1139#if defined(MBEDTLS_ENTROPY_NV_SEED)
1140#if defined(MBEDTLS_FS_IO)
Azim Khan4084ec72018-07-05 14:20:08 +01001141#line 13 "test_suite_ut.function"
Azim Khan4b543232017-06-30 09:35:21 +01001142void test_func1()
1143{
1144exit:
Azim Khan4084ec72018-07-05 14:20:08 +01001145 ;
Azim Khan4b543232017-06-30 09:35:21 +01001146}
1147
1148void test_func1_wrapper( void ** params )
1149{
1150 (void)params;
1151
1152 test_func1( );
1153}
1154#endif /* MBEDTLS_FS_IO */
1155#endif /* MBEDTLS_ENTROPY_NV_SEED */
1156#if defined(MBEDTLS_ENTROPY_NV_SEED)
1157#if defined(MBEDTLS_FS_IO)
Azim Khan4084ec72018-07-05 14:20:08 +01001158#line 19 "test_suite_ut.function"
Azim Khan4b543232017-06-30 09:35:21 +01001159void test_func2()
1160{
1161exit:
Azim Khan4084ec72018-07-05 14:20:08 +01001162 ;
Azim Khan4b543232017-06-30 09:35:21 +01001163}
1164
1165void test_func2_wrapper( void ** params )
1166{
1167 (void)params;
1168
1169 test_func2( );
1170}
1171#endif /* MBEDTLS_FS_IO */
1172#endif /* MBEDTLS_ENTROPY_NV_SEED */
1173#endif /* MBEDTLS_ECP_C */
1174'''
1175 self.assertEqual(func_code, expected_func_code)
Azim Khanb31aa442018-07-03 11:57:54 +01001176 self.assertEqual(func_info, {'test_func1': (0, []),
1177 'test_func2': (1, [])})
Azim Khan4b543232017-06-30 09:35:21 +01001178
1179 def test_same_function_name(self):
1180 """
Mohammad Azim Khanb5229292018-02-06 13:08:01 +00001181 Test name conflict.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001182 :return:
Azim Khan4b543232017-06-30 09:35:21 +01001183 """
1184 data = '''/* BEGIN_HEADER */
1185#include "mbedtls/ecp.h"
1186
1187#define ECP_PF_UNKNOWN -1
1188/* END_HEADER */
1189
1190/* BEGIN_DEPENDENCIES
1191 * depends_on:MBEDTLS_ECP_C
1192 * END_DEPENDENCIES
1193 */
1194
1195/* BEGIN_CASE depends_on:MBEDTLS_ENTROPY_NV_SEED:MBEDTLS_FS_IO */
1196void func()
1197{
1198}
1199/* END_CASE */
1200
1201/* BEGIN_CASE depends_on:MBEDTLS_ENTROPY_NV_SEED:MBEDTLS_FS_IO */
1202void func()
1203{
1204}
1205/* END_CASE */
1206'''
Azim Khanb31aa442018-07-03 11:57:54 +01001207 stream = StringIOWrapper('test_suite_ut.function', data)
1208 self.assertRaises(GeneratorInputError, parse_functions, stream)
Azim Khan4b543232017-06-30 09:35:21 +01001209
1210
Azim Khanb31aa442018-07-03 11:57:54 +01001211class EscapedSplit(TestCase):
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001212 """
Azim Khan599cd242017-07-06 17:34:27 +01001213 Test suite for testing escaped_split().
Azim Khanb31aa442018-07-03 11:57:54 +01001214 Note: Since escaped_split() output is used to write back to the
1215 intermediate data file. Any escape characters in the input are
1216 retained in the output.
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001217 """
1218
1219 def test_invalid_input(self):
1220 """
1221 Test when input split character is not a character.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001222 :return:
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001223 """
1224 self.assertRaises(ValueError, escaped_split, '', 'string')
1225
1226 def test_empty_string(self):
1227 """
Azim Khanb31aa442018-07-03 11:57:54 +01001228 Test empty string input.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001229 :return:
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001230 """
1231 splits = escaped_split('', ':')
1232 self.assertEqual(splits, [])
1233
1234 def test_no_escape(self):
1235 """
Azim Khanb31aa442018-07-03 11:57:54 +01001236 Test with no escape character. The behaviour should be same as
1237 str.split()
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001238 :return:
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001239 """
Azim Khanb31aa442018-07-03 11:57:54 +01001240 test_str = 'yahoo:google'
1241 splits = escaped_split(test_str, ':')
1242 self.assertEqual(splits, test_str.split(':'))
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001243
1244 def test_escaped_input(self):
1245 """
Azim Khanb31aa442018-07-03 11:57:54 +01001246 Test input that has escaped delimiter.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001247 :return:
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001248 """
Azim Khanb31aa442018-07-03 11:57:54 +01001249 test_str = r'yahoo\:google:facebook'
1250 splits = escaped_split(test_str, ':')
1251 self.assertEqual(splits, [r'yahoo\:google', 'facebook'])
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001252
1253 def test_escaped_escape(self):
1254 """
Azim Khanb31aa442018-07-03 11:57:54 +01001255 Test input that has escaped delimiter.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001256 :return:
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001257 """
Azim Khan4084ec72018-07-05 14:20:08 +01001258 test_str = r'yahoo\\:google:facebook'
Azim Khanb31aa442018-07-03 11:57:54 +01001259 splits = escaped_split(test_str, ':')
Azim Khan4084ec72018-07-05 14:20:08 +01001260 self.assertEqual(splits, [r'yahoo\\', 'google', 'facebook'])
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001261
1262 def test_all_at_once(self):
1263 """
Azim Khanb31aa442018-07-03 11:57:54 +01001264 Test input that has escaped delimiter.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001265 :return:
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001266 """
Azim Khan4084ec72018-07-05 14:20:08 +01001267 test_str = r'yahoo\\:google:facebook\:instagram\\:bbc\\:wikipedia'
Azim Khanb31aa442018-07-03 11:57:54 +01001268 splits = escaped_split(test_str, ':')
Azim Khan4084ec72018-07-05 14:20:08 +01001269 self.assertEqual(splits, [r'yahoo\\', r'google',
1270 r'facebook\:instagram\\',
1271 r'bbc\\', r'wikipedia'])
Azim Khan599cd242017-07-06 17:34:27 +01001272
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001273
1274class ParseTestData(TestCase):
1275 """
1276 Test suite for parse test data.
1277 """
1278
1279 def test_parser(self):
1280 """
1281 Test that tests are parsed correctly from data file.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001282 :return:
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001283 """
1284 data = """
1285Diffie-Hellman full exchange #1
1286dhm_do_dhm:10:"23":10:"5"
1287
1288Diffie-Hellman full exchange #2
1289dhm_do_dhm:10:"93450983094850938450983409623":10:"9345098304850938450983409622"
1290
1291Diffie-Hellman full exchange #3
1292dhm_do_dhm:10:"9345098382739712938719287391879381271":10:"9345098792137312973297123912791271"
1293
1294Diffie-Hellman selftest
1295dhm_selftest:
1296"""
Azim Khanb31aa442018-07-03 11:57:54 +01001297 stream = StringIOWrapper('test_suite_ut.function', data)
Gilles Peskine8b022352020-03-24 18:36:56 +01001298 # List of (name, function_name, dependencies, args)
1299 tests = list(parse_test_data(stream))
Azim Khanb31aa442018-07-03 11:57:54 +01001300 test1, test2, test3, test4 = tests
Gilles Peskine8b32d202023-02-23 20:47:24 +01001301 self.assertEqual(test1[0], 3)
Gilles Peskine8542f5c2022-12-03 22:58:52 +01001302 self.assertEqual(test1[1], 'Diffie-Hellman full exchange #1')
1303 self.assertEqual(test1[2], 'dhm_do_dhm')
1304 self.assertEqual(test1[3], [])
1305 self.assertEqual(test1[4], ['10', '"23"', '10', '"5"'])
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001306
Gilles Peskine8b32d202023-02-23 20:47:24 +01001307 self.assertEqual(test2[0], 6)
Gilles Peskine8542f5c2022-12-03 22:58:52 +01001308 self.assertEqual(test2[1], 'Diffie-Hellman full exchange #2')
1309 self.assertEqual(test2[2], 'dhm_do_dhm')
1310 self.assertEqual(test2[3], [])
1311 self.assertEqual(test2[4], ['10', '"93450983094850938450983409623"',
Azim Khanb31aa442018-07-03 11:57:54 +01001312 '10', '"9345098304850938450983409622"'])
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001313
Gilles Peskine8b32d202023-02-23 20:47:24 +01001314 self.assertEqual(test3[0], 9)
Gilles Peskine8542f5c2022-12-03 22:58:52 +01001315 self.assertEqual(test3[1], 'Diffie-Hellman full exchange #3')
1316 self.assertEqual(test3[2], 'dhm_do_dhm')
1317 self.assertEqual(test3[3], [])
1318 self.assertEqual(test3[4], ['10',
Azim Khanb31aa442018-07-03 11:57:54 +01001319 '"9345098382739712938719287391879381271"',
1320 '10',
1321 '"9345098792137312973297123912791271"'])
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001322
Gilles Peskine8b32d202023-02-23 20:47:24 +01001323 self.assertEqual(test4[0], 12)
Gilles Peskine8542f5c2022-12-03 22:58:52 +01001324 self.assertEqual(test4[1], 'Diffie-Hellman selftest')
1325 self.assertEqual(test4[2], 'dhm_selftest')
Azim Khanb31aa442018-07-03 11:57:54 +01001326 self.assertEqual(test4[3], [])
Gilles Peskine8542f5c2022-12-03 22:58:52 +01001327 self.assertEqual(test4[4], [])
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001328
1329 def test_with_dependencies(self):
1330 """
1331 Test that tests with dependencies are parsed.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001332 :return:
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001333 """
1334 data = """
1335Diffie-Hellman full exchange #1
1336depends_on:YAHOO
1337dhm_do_dhm:10:"23":10:"5"
1338
1339Diffie-Hellman full exchange #2
1340dhm_do_dhm:10:"93450983094850938450983409623":10:"9345098304850938450983409622"
1341
1342"""
Azim Khanb31aa442018-07-03 11:57:54 +01001343 stream = StringIOWrapper('test_suite_ut.function', data)
Gilles Peskine8b022352020-03-24 18:36:56 +01001344 # List of (name, function_name, dependencies, args)
1345 tests = list(parse_test_data(stream))
Azim Khanb31aa442018-07-03 11:57:54 +01001346 test1, test2 = tests
Gilles Peskine8b32d202023-02-23 20:47:24 +01001347 self.assertEqual(test1[0], 4)
Gilles Peskine8542f5c2022-12-03 22:58:52 +01001348 self.assertEqual(test1[1], 'Diffie-Hellman full exchange #1')
1349 self.assertEqual(test1[2], 'dhm_do_dhm')
1350 self.assertEqual(test1[3], ['YAHOO'])
1351 self.assertEqual(test1[4], ['10', '"23"', '10', '"5"'])
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001352
Gilles Peskine8b32d202023-02-23 20:47:24 +01001353 self.assertEqual(test2[0], 7)
Gilles Peskine8542f5c2022-12-03 22:58:52 +01001354 self.assertEqual(test2[1], 'Diffie-Hellman full exchange #2')
1355 self.assertEqual(test2[2], 'dhm_do_dhm')
1356 self.assertEqual(test2[3], [])
1357 self.assertEqual(test2[4], ['10', '"93450983094850938450983409623"',
Azim Khanb31aa442018-07-03 11:57:54 +01001358 '10', '"9345098304850938450983409622"'])
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001359
1360 def test_no_args(self):
1361 """
Azim Khanb31aa442018-07-03 11:57:54 +01001362 Test GeneratorInputError is raised when test function name and
1363 args line is missing.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001364 :return:
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001365 """
1366 data = """
1367Diffie-Hellman full exchange #1
1368depends_on:YAHOO
1369
1370
1371Diffie-Hellman full exchange #2
1372dhm_do_dhm:10:"93450983094850938450983409623":10:"9345098304850938450983409622"
1373
1374"""
Azim Khanb31aa442018-07-03 11:57:54 +01001375 stream = StringIOWrapper('test_suite_ut.function', data)
1376 err = None
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001377 try:
Gilles Peskine8542f5c2022-12-03 22:58:52 +01001378 for _, _, _, _, _ in parse_test_data(stream):
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001379 pass
Azim Khanb31aa442018-07-03 11:57:54 +01001380 except GeneratorInputError as err:
Mohammad Azim Khan539aa062018-07-06 00:29:50 +01001381 self.assertEqual(type(err), GeneratorInputError)
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001382
1383 def test_incomplete_data(self):
1384 """
Azim Khanb31aa442018-07-03 11:57:54 +01001385 Test GeneratorInputError is raised when test function name
1386 and args line is missing.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001387 :return:
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001388 """
1389 data = """
1390Diffie-Hellman full exchange #1
1391depends_on:YAHOO
1392"""
Azim Khanb31aa442018-07-03 11:57:54 +01001393 stream = StringIOWrapper('test_suite_ut.function', data)
1394 err = None
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001395 try:
Gilles Peskine8542f5c2022-12-03 22:58:52 +01001396 for _, _, _, _, _ in parse_test_data(stream):
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001397 pass
Azim Khanb31aa442018-07-03 11:57:54 +01001398 except GeneratorInputError as err:
Mohammad Azim Khan539aa062018-07-06 00:29:50 +01001399 self.assertEqual(type(err), GeneratorInputError)
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001400
1401
1402class GenDepCheck(TestCase):
1403 """
Azim Khanb31aa442018-07-03 11:57:54 +01001404 Test suite for gen_dep_check(). It is assumed this function is
1405 called with valid inputs.
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001406 """
1407
1408 def test_gen_dep_check(self):
1409 """
1410 Test that dependency check code generated correctly.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001411 :return:
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001412 """
1413 expected = """
Azim Khand61b8372017-07-10 11:54:01 +01001414 case 5:
1415 {
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001416#if defined(YAHOO)
Azim Khand61b8372017-07-10 11:54:01 +01001417 ret = DEPENDENCY_SUPPORTED;
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001418#else
Azim Khand61b8372017-07-10 11:54:01 +01001419 ret = DEPENDENCY_NOT_SUPPORTED;
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001420#endif
Azim Khand61b8372017-07-10 11:54:01 +01001421 }
1422 break;"""
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001423 out = gen_dep_check(5, 'YAHOO')
1424 self.assertEqual(out, expected)
1425
Azim Khanb31aa442018-07-03 11:57:54 +01001426 def test_not_defined_dependency(self):
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001427 """
1428 Test dependency with !.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001429 :return:
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001430 """
1431 expected = """
Azim Khand61b8372017-07-10 11:54:01 +01001432 case 5:
1433 {
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001434#if !defined(YAHOO)
Azim Khand61b8372017-07-10 11:54:01 +01001435 ret = DEPENDENCY_SUPPORTED;
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001436#else
Azim Khand61b8372017-07-10 11:54:01 +01001437 ret = DEPENDENCY_NOT_SUPPORTED;
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001438#endif
Azim Khand61b8372017-07-10 11:54:01 +01001439 }
1440 break;"""
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001441 out = gen_dep_check(5, '!YAHOO')
1442 self.assertEqual(out, expected)
1443
1444 def test_empty_dependency(self):
1445 """
1446 Test invalid dependency input.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001447 :return:
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001448 """
Mohammad Azim Khan3b06f222018-06-26 14:35:25 +01001449 self.assertRaises(GeneratorInputError, gen_dep_check, 5, '!')
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001450
1451 def test_negative_dep_id(self):
1452 """
1453 Test invalid dependency input.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001454 :return:
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001455 """
Mohammad Azim Khan3b06f222018-06-26 14:35:25 +01001456 self.assertRaises(GeneratorInputError, gen_dep_check, -1, 'YAHOO')
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001457
1458
1459class GenExpCheck(TestCase):
1460 """
Azim Khanb31aa442018-07-03 11:57:54 +01001461 Test suite for gen_expression_check(). It is assumed this function
1462 is called with valid inputs.
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001463 """
1464
1465 def test_gen_exp_check(self):
1466 """
1467 Test that expression check code generated correctly.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001468 :return:
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001469 """
1470 expected = """
Azim Khand61b8372017-07-10 11:54:01 +01001471 case 5:
1472 {
1473 *out_value = YAHOO;
1474 }
1475 break;"""
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001476 out = gen_expression_check(5, 'YAHOO')
1477 self.assertEqual(out, expected)
1478
1479 def test_invalid_expression(self):
1480 """
1481 Test invalid expression input.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001482 :return:
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001483 """
Mohammad Azim Khan3b06f222018-06-26 14:35:25 +01001484 self.assertRaises(GeneratorInputError, gen_expression_check, 5, '')
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001485
1486 def test_negative_exp_id(self):
1487 """
1488 Test invalid expression id.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001489 :return:
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001490 """
Azim Khanb31aa442018-07-03 11:57:54 +01001491 self.assertRaises(GeneratorInputError, gen_expression_check,
1492 -1, 'YAHOO')
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001493
1494
Azim Khanb31aa442018-07-03 11:57:54 +01001495class WriteDependencies(TestCase):
Azim Khan599cd242017-07-06 17:34:27 +01001496 """
Azim Khanb31aa442018-07-03 11:57:54 +01001497 Test suite for testing write_dependencies.
Azim Khan599cd242017-07-06 17:34:27 +01001498 """
1499
Azim Khanb31aa442018-07-03 11:57:54 +01001500 def test_no_test_dependencies(self):
Azim Khan599cd242017-07-06 17:34:27 +01001501 """
Azim Khanb31aa442018-07-03 11:57:54 +01001502 Test when test dependencies input is empty.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001503 :return:
Azim Khan599cd242017-07-06 17:34:27 +01001504 """
Azim Khanb31aa442018-07-03 11:57:54 +01001505 stream = StringIOWrapper('test_suite_ut.data', '')
1506 unique_dependencies = []
1507 dep_check_code = write_dependencies(stream, [], unique_dependencies)
Azim Khan599cd242017-07-06 17:34:27 +01001508 self.assertEqual(dep_check_code, '')
Azim Khanb31aa442018-07-03 11:57:54 +01001509 self.assertEqual(len(unique_dependencies), 0)
1510 self.assertEqual(stream.getvalue(), '')
Azim Khan599cd242017-07-06 17:34:27 +01001511
1512 def test_unique_dep_ids(self):
1513 """
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001514
1515 :return:
Azim Khan599cd242017-07-06 17:34:27 +01001516 """
Azim Khanb31aa442018-07-03 11:57:54 +01001517 stream = StringIOWrapper('test_suite_ut.data', '')
1518 unique_dependencies = []
1519 dep_check_code = write_dependencies(stream, ['DEP3', 'DEP2', 'DEP1'],
1520 unique_dependencies)
Azim Khan599cd242017-07-06 17:34:27 +01001521 expect_dep_check_code = '''
Azim Khand61b8372017-07-10 11:54:01 +01001522 case 0:
1523 {
Azim Khan599cd242017-07-06 17:34:27 +01001524#if defined(DEP3)
Azim Khand61b8372017-07-10 11:54:01 +01001525 ret = DEPENDENCY_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001526#else
Azim Khand61b8372017-07-10 11:54:01 +01001527 ret = DEPENDENCY_NOT_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001528#endif
Azim Khand61b8372017-07-10 11:54:01 +01001529 }
1530 break;
1531 case 1:
1532 {
Azim Khan599cd242017-07-06 17:34:27 +01001533#if defined(DEP2)
Azim Khand61b8372017-07-10 11:54:01 +01001534 ret = DEPENDENCY_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001535#else
Azim Khand61b8372017-07-10 11:54:01 +01001536 ret = DEPENDENCY_NOT_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001537#endif
Azim Khand61b8372017-07-10 11:54:01 +01001538 }
1539 break;
1540 case 2:
1541 {
Azim Khan599cd242017-07-06 17:34:27 +01001542#if defined(DEP1)
Azim Khand61b8372017-07-10 11:54:01 +01001543 ret = DEPENDENCY_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001544#else
Azim Khand61b8372017-07-10 11:54:01 +01001545 ret = DEPENDENCY_NOT_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001546#endif
Azim Khand61b8372017-07-10 11:54:01 +01001547 }
1548 break;'''
Azim Khan599cd242017-07-06 17:34:27 +01001549 self.assertEqual(dep_check_code, expect_dep_check_code)
Azim Khanb31aa442018-07-03 11:57:54 +01001550 self.assertEqual(len(unique_dependencies), 3)
1551 self.assertEqual(stream.getvalue(), 'depends_on:0:1:2\n')
Azim Khan599cd242017-07-06 17:34:27 +01001552
1553 def test_dep_id_repeat(self):
1554 """
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001555
1556 :return:
Azim Khan599cd242017-07-06 17:34:27 +01001557 """
Azim Khanb31aa442018-07-03 11:57:54 +01001558 stream = StringIOWrapper('test_suite_ut.data', '')
1559 unique_dependencies = []
Azim Khan599cd242017-07-06 17:34:27 +01001560 dep_check_code = ''
Azim Khanb31aa442018-07-03 11:57:54 +01001561 dep_check_code += write_dependencies(stream, ['DEP3', 'DEP2'],
1562 unique_dependencies)
1563 dep_check_code += write_dependencies(stream, ['DEP2', 'DEP1'],
1564 unique_dependencies)
1565 dep_check_code += write_dependencies(stream, ['DEP1', 'DEP3'],
1566 unique_dependencies)
Azim Khan599cd242017-07-06 17:34:27 +01001567 expect_dep_check_code = '''
Azim Khand61b8372017-07-10 11:54:01 +01001568 case 0:
1569 {
Azim Khan599cd242017-07-06 17:34:27 +01001570#if defined(DEP3)
Azim Khand61b8372017-07-10 11:54:01 +01001571 ret = DEPENDENCY_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001572#else
Azim Khand61b8372017-07-10 11:54:01 +01001573 ret = DEPENDENCY_NOT_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001574#endif
Azim Khand61b8372017-07-10 11:54:01 +01001575 }
1576 break;
1577 case 1:
1578 {
Azim Khan599cd242017-07-06 17:34:27 +01001579#if defined(DEP2)
Azim Khand61b8372017-07-10 11:54:01 +01001580 ret = DEPENDENCY_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001581#else
Azim Khand61b8372017-07-10 11:54:01 +01001582 ret = DEPENDENCY_NOT_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001583#endif
Azim Khand61b8372017-07-10 11:54:01 +01001584 }
1585 break;
1586 case 2:
1587 {
Azim Khan599cd242017-07-06 17:34:27 +01001588#if defined(DEP1)
Azim Khand61b8372017-07-10 11:54:01 +01001589 ret = DEPENDENCY_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001590#else
Azim Khand61b8372017-07-10 11:54:01 +01001591 ret = DEPENDENCY_NOT_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001592#endif
Azim Khand61b8372017-07-10 11:54:01 +01001593 }
1594 break;'''
Azim Khan599cd242017-07-06 17:34:27 +01001595 self.assertEqual(dep_check_code, expect_dep_check_code)
Azim Khanb31aa442018-07-03 11:57:54 +01001596 self.assertEqual(len(unique_dependencies), 3)
1597 self.assertEqual(stream.getvalue(),
1598 'depends_on:0:1\ndepends_on:1:2\ndepends_on:2:0\n')
Azim Khan599cd242017-07-06 17:34:27 +01001599
1600
1601class WriteParams(TestCase):
1602 """
1603 Test Suite for testing write_parameters().
1604 """
1605
1606 def test_no_params(self):
1607 """
1608 Test with empty test_args
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001609 :return:
Azim Khan599cd242017-07-06 17:34:27 +01001610 """
Azim Khanb31aa442018-07-03 11:57:54 +01001611 stream = StringIOWrapper('test_suite_ut.data', '')
Azim Khan599cd242017-07-06 17:34:27 +01001612 unique_expressions = []
Azim Khanb31aa442018-07-03 11:57:54 +01001613 expression_code = write_parameters(stream, [], [], unique_expressions)
Azim Khan599cd242017-07-06 17:34:27 +01001614 self.assertEqual(len(unique_expressions), 0)
1615 self.assertEqual(expression_code, '')
Azim Khanb31aa442018-07-03 11:57:54 +01001616 self.assertEqual(stream.getvalue(), '\n')
Azim Khan599cd242017-07-06 17:34:27 +01001617
1618 def test_no_exp_param(self):
1619 """
1620 Test when there is no macro or expression in the params.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001621 :return:
Azim Khan599cd242017-07-06 17:34:27 +01001622 """
Azim Khanb31aa442018-07-03 11:57:54 +01001623 stream = StringIOWrapper('test_suite_ut.data', '')
Azim Khan599cd242017-07-06 17:34:27 +01001624 unique_expressions = []
Azim Khanb31aa442018-07-03 11:57:54 +01001625 expression_code = write_parameters(stream, ['"Yahoo"', '"abcdef00"',
1626 '0'],
1627 ['char*', 'hex', 'int'],
Azim Khan599cd242017-07-06 17:34:27 +01001628 unique_expressions)
1629 self.assertEqual(len(unique_expressions), 0)
1630 self.assertEqual(expression_code, '')
Azim Khanb31aa442018-07-03 11:57:54 +01001631 self.assertEqual(stream.getvalue(),
1632 ':char*:"Yahoo":hex:"abcdef00":int:0\n')
Azim Khan599cd242017-07-06 17:34:27 +01001633
1634 def test_hex_format_int_param(self):
1635 """
1636 Test int parameter in hex format.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001637 :return:
Azim Khan599cd242017-07-06 17:34:27 +01001638 """
Azim Khanb31aa442018-07-03 11:57:54 +01001639 stream = StringIOWrapper('test_suite_ut.data', '')
Azim Khan599cd242017-07-06 17:34:27 +01001640 unique_expressions = []
Azim Khanb31aa442018-07-03 11:57:54 +01001641 expression_code = write_parameters(stream,
1642 ['"Yahoo"', '"abcdef00"', '0xAA'],
1643 ['char*', 'hex', 'int'],
Azim Khan599cd242017-07-06 17:34:27 +01001644 unique_expressions)
1645 self.assertEqual(len(unique_expressions), 0)
1646 self.assertEqual(expression_code, '')
Azim Khanb31aa442018-07-03 11:57:54 +01001647 self.assertEqual(stream.getvalue(),
1648 ':char*:"Yahoo":hex:"abcdef00":int:0xAA\n')
Azim Khan599cd242017-07-06 17:34:27 +01001649
1650 def test_with_exp_param(self):
1651 """
1652 Test when there is macro or expression in the params.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001653 :return:
Azim Khan599cd242017-07-06 17:34:27 +01001654 """
Azim Khanb31aa442018-07-03 11:57:54 +01001655 stream = StringIOWrapper('test_suite_ut.data', '')
Azim Khan599cd242017-07-06 17:34:27 +01001656 unique_expressions = []
Azim Khanb31aa442018-07-03 11:57:54 +01001657 expression_code = write_parameters(stream,
1658 ['"Yahoo"', '"abcdef00"', '0',
1659 'MACRO1', 'MACRO2', 'MACRO3'],
1660 ['char*', 'hex', 'int',
1661 'int', 'int', 'int'],
Azim Khan599cd242017-07-06 17:34:27 +01001662 unique_expressions)
1663 self.assertEqual(len(unique_expressions), 3)
1664 self.assertEqual(unique_expressions, ['MACRO1', 'MACRO2', 'MACRO3'])
1665 expected_expression_code = '''
Azim Khand61b8372017-07-10 11:54:01 +01001666 case 0:
1667 {
1668 *out_value = MACRO1;
1669 }
1670 break;
1671 case 1:
1672 {
1673 *out_value = MACRO2;
1674 }
1675 break;
1676 case 2:
1677 {
1678 *out_value = MACRO3;
1679 }
1680 break;'''
Azim Khan599cd242017-07-06 17:34:27 +01001681 self.assertEqual(expression_code, expected_expression_code)
Azim Khanb31aa442018-07-03 11:57:54 +01001682 self.assertEqual(stream.getvalue(),
1683 ':char*:"Yahoo":hex:"abcdef00":int:0:exp:0:exp:1'
1684 ':exp:2\n')
Azim Khan599cd242017-07-06 17:34:27 +01001685
Azim Khanb31aa442018-07-03 11:57:54 +01001686 def test_with_repeat_calls(self):
Azim Khan599cd242017-07-06 17:34:27 +01001687 """
1688 Test when write_parameter() is called with same macro or expression.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001689 :return:
Azim Khan599cd242017-07-06 17:34:27 +01001690 """
Azim Khanb31aa442018-07-03 11:57:54 +01001691 stream = StringIOWrapper('test_suite_ut.data', '')
Azim Khan599cd242017-07-06 17:34:27 +01001692 unique_expressions = []
1693 expression_code = ''
Azim Khanb31aa442018-07-03 11:57:54 +01001694 expression_code += write_parameters(stream,
1695 ['"Yahoo"', 'MACRO1', 'MACRO2'],
1696 ['char*', 'int', 'int'],
Azim Khan599cd242017-07-06 17:34:27 +01001697 unique_expressions)
Azim Khanb31aa442018-07-03 11:57:54 +01001698 expression_code += write_parameters(stream,
1699 ['"abcdef00"', 'MACRO2', 'MACRO3'],
1700 ['hex', 'int', 'int'],
Azim Khan599cd242017-07-06 17:34:27 +01001701 unique_expressions)
Azim Khanb31aa442018-07-03 11:57:54 +01001702 expression_code += write_parameters(stream,
1703 ['0', 'MACRO3', 'MACRO1'],
1704 ['int', 'int', 'int'],
Azim Khan599cd242017-07-06 17:34:27 +01001705 unique_expressions)
1706 self.assertEqual(len(unique_expressions), 3)
1707 self.assertEqual(unique_expressions, ['MACRO1', 'MACRO2', 'MACRO3'])
1708 expected_expression_code = '''
Azim Khand61b8372017-07-10 11:54:01 +01001709 case 0:
1710 {
1711 *out_value = MACRO1;
1712 }
1713 break;
1714 case 1:
1715 {
1716 *out_value = MACRO2;
1717 }
1718 break;
1719 case 2:
1720 {
1721 *out_value = MACRO3;
1722 }
1723 break;'''
Azim Khan599cd242017-07-06 17:34:27 +01001724 self.assertEqual(expression_code, expected_expression_code)
1725 expected_data_file = ''':char*:"Yahoo":exp:0:exp:1
1726:hex:"abcdef00":exp:1:exp:2
1727:int:0:exp:2:exp:0
1728'''
Azim Khanb31aa442018-07-03 11:57:54 +01001729 self.assertEqual(stream.getvalue(), expected_data_file)
Azim Khan599cd242017-07-06 17:34:27 +01001730
1731
Azim Khanb31aa442018-07-03 11:57:54 +01001732class GenTestSuiteDependenciesChecks(TestCase):
Azim Khan599cd242017-07-06 17:34:27 +01001733 """
Azim Khanb31aa442018-07-03 11:57:54 +01001734 Test suite for testing gen_suite_dep_checks()
Azim Khan599cd242017-07-06 17:34:27 +01001735 """
Azim Khanb31aa442018-07-03 11:57:54 +01001736 def test_empty_suite_dependencies(self):
Azim Khan599cd242017-07-06 17:34:27 +01001737 """
Azim Khanb31aa442018-07-03 11:57:54 +01001738 Test with empty suite_dependencies list.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001739
1740 :return:
Azim Khan599cd242017-07-06 17:34:27 +01001741 """
Azim Khanb31aa442018-07-03 11:57:54 +01001742 dep_check_code, expression_code = \
1743 gen_suite_dep_checks([], 'DEP_CHECK_CODE', 'EXPRESSION_CODE')
Azim Khan599cd242017-07-06 17:34:27 +01001744 self.assertEqual(dep_check_code, 'DEP_CHECK_CODE')
1745 self.assertEqual(expression_code, 'EXPRESSION_CODE')
1746
Azim Khanb31aa442018-07-03 11:57:54 +01001747 def test_suite_dependencies(self):
Azim Khan599cd242017-07-06 17:34:27 +01001748 """
Azim Khanb31aa442018-07-03 11:57:54 +01001749 Test with suite_dependencies list.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001750
1751 :return:
Azim Khan599cd242017-07-06 17:34:27 +01001752 """
Azim Khanb31aa442018-07-03 11:57:54 +01001753 dep_check_code, expression_code = \
1754 gen_suite_dep_checks(['SUITE_DEP'], 'DEP_CHECK_CODE',
1755 'EXPRESSION_CODE')
1756 expected_dep_check_code = '''
Azim Khan599cd242017-07-06 17:34:27 +01001757#if defined(SUITE_DEP)
1758DEP_CHECK_CODE
Azim Khan599cd242017-07-06 17:34:27 +01001759#endif
1760'''
1761 expected_expression_code = '''
1762#if defined(SUITE_DEP)
1763EXPRESSION_CODE
Azim Khan599cd242017-07-06 17:34:27 +01001764#endif
1765'''
Azim Khanb31aa442018-07-03 11:57:54 +01001766 self.assertEqual(dep_check_code, expected_dep_check_code)
Azim Khan599cd242017-07-06 17:34:27 +01001767 self.assertEqual(expression_code, expected_expression_code)
1768
1769 def test_no_dep_no_exp(self):
1770 """
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001771 Test when there are no dependency and expression code.
1772 :return:
Azim Khan599cd242017-07-06 17:34:27 +01001773 """
Azim Khanb31aa442018-07-03 11:57:54 +01001774 dep_check_code, expression_code = gen_suite_dep_checks([], '', '')
Azim Khand61b8372017-07-10 11:54:01 +01001775 self.assertEqual(dep_check_code, '')
1776 self.assertEqual(expression_code, '')
Azim Khan599cd242017-07-06 17:34:27 +01001777
1778
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001779class GenFromTestData(TestCase):
1780 """
1781 Test suite for gen_from_test_data()
1782 """
1783
Azim Khanb31aa442018-07-03 11:57:54 +01001784 @staticmethod
1785 @patch("generate_test_code.write_dependencies")
Mohammad Azim Khan78befd92018-03-06 11:49:41 +00001786 @patch("generate_test_code.write_parameters")
Azim Khan4084ec72018-07-05 14:20:08 +01001787 @patch("generate_test_code.gen_suite_dep_checks")
Azim Khanb31aa442018-07-03 11:57:54 +01001788 def test_intermediate_data_file(func_mock1,
1789 write_parameters_mock,
1790 write_dependencies_mock):
Azim Khan599cd242017-07-06 17:34:27 +01001791 """
1792 Test that intermediate data file is written with expected data.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001793 :return:
Azim Khan599cd242017-07-06 17:34:27 +01001794 """
1795 data = '''
1796My test
1797depends_on:DEP1
1798func1:0
1799'''
1800 data_f = StringIOWrapper('test_suite_ut.data', data)
1801 out_data_f = StringIOWrapper('test_suite_ut.datax', '')
1802 func_info = {'test_func1': (1, ('int',))}
Azim Khanb31aa442018-07-03 11:57:54 +01001803 suite_dependencies = []
Azim Khan599cd242017-07-06 17:34:27 +01001804 write_parameters_mock.side_effect = write_parameters
Azim Khanb31aa442018-07-03 11:57:54 +01001805 write_dependencies_mock.side_effect = write_dependencies
1806 func_mock1.side_effect = gen_suite_dep_checks
1807 gen_from_test_data(data_f, out_data_f, func_info, suite_dependencies)
1808 write_dependencies_mock.assert_called_with(out_data_f,
1809 ['DEP1'], ['DEP1'])
1810 write_parameters_mock.assert_called_with(out_data_f, ['0'],
1811 ('int',), [])
Azim Khan599cd242017-07-06 17:34:27 +01001812 expected_dep_check_code = '''
Azim Khand61b8372017-07-10 11:54:01 +01001813 case 0:
1814 {
Azim Khan599cd242017-07-06 17:34:27 +01001815#if defined(DEP1)
Azim Khand61b8372017-07-10 11:54:01 +01001816 ret = DEPENDENCY_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001817#else
Azim Khand61b8372017-07-10 11:54:01 +01001818 ret = DEPENDENCY_NOT_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001819#endif
Azim Khand61b8372017-07-10 11:54:01 +01001820 }
1821 break;'''
Azim Khanb31aa442018-07-03 11:57:54 +01001822 func_mock1.assert_called_with(
1823 suite_dependencies, expected_dep_check_code, '')
Azim Khan599cd242017-07-06 17:34:27 +01001824
1825 def test_function_not_found(self):
1826 """
1827 Test that AssertError is raised when function info in not found.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001828 :return:
Azim Khan599cd242017-07-06 17:34:27 +01001829 """
1830 data = '''
1831My test
1832depends_on:DEP1
1833func1:0
1834'''
1835 data_f = StringIOWrapper('test_suite_ut.data', data)
1836 out_data_f = StringIOWrapper('test_suite_ut.datax', '')
1837 func_info = {'test_func2': (1, ('int',))}
Azim Khanb31aa442018-07-03 11:57:54 +01001838 suite_dependencies = []
1839 self.assertRaises(GeneratorInputError, gen_from_test_data,
1840 data_f, out_data_f, func_info, suite_dependencies)
Azim Khan599cd242017-07-06 17:34:27 +01001841
1842 def test_different_func_args(self):
1843 """
Azim Khanb31aa442018-07-03 11:57:54 +01001844 Test that AssertError is raised when no. of parameters and
1845 function args differ.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001846 :return:
Azim Khan599cd242017-07-06 17:34:27 +01001847 """
1848 data = '''
1849My test
1850depends_on:DEP1
1851func1:0
1852'''
1853 data_f = StringIOWrapper('test_suite_ut.data', data)
1854 out_data_f = StringIOWrapper('test_suite_ut.datax', '')
Azim Khanb31aa442018-07-03 11:57:54 +01001855 func_info = {'test_func2': (1, ('int', 'hex'))}
1856 suite_dependencies = []
1857 self.assertRaises(GeneratorInputError, gen_from_test_data, data_f,
1858 out_data_f, func_info, suite_dependencies)
Azim Khan599cd242017-07-06 17:34:27 +01001859
1860 def test_output(self):
1861 """
1862 Test that intermediate data file is written with expected data.
Mohammad Azim Khanb73159d2018-06-13 16:31:26 +01001863 :return:
Azim Khan599cd242017-07-06 17:34:27 +01001864 """
1865 data = '''
1866My test 1
1867depends_on:DEP1
1868func1:0:0xfa:MACRO1:MACRO2
1869
1870My test 2
1871depends_on:DEP1:DEP2
1872func2:"yahoo":88:MACRO1
1873'''
1874 data_f = StringIOWrapper('test_suite_ut.data', data)
1875 out_data_f = StringIOWrapper('test_suite_ut.datax', '')
Azim Khanb31aa442018-07-03 11:57:54 +01001876 func_info = {'test_func1': (0, ('int', 'int', 'int', 'int')),
1877 'test_func2': (1, ('char*', 'int', 'int'))}
1878 suite_dependencies = []
1879 dep_check_code, expression_code = \
1880 gen_from_test_data(data_f, out_data_f, func_info,
1881 suite_dependencies)
Azim Khan599cd242017-07-06 17:34:27 +01001882 expected_dep_check_code = '''
Azim Khand61b8372017-07-10 11:54:01 +01001883 case 0:
1884 {
Azim Khan599cd242017-07-06 17:34:27 +01001885#if defined(DEP1)
Azim Khand61b8372017-07-10 11:54:01 +01001886 ret = DEPENDENCY_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001887#else
Azim Khand61b8372017-07-10 11:54:01 +01001888 ret = DEPENDENCY_NOT_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001889#endif
Azim Khand61b8372017-07-10 11:54:01 +01001890 }
1891 break;
1892 case 1:
1893 {
Azim Khan599cd242017-07-06 17:34:27 +01001894#if defined(DEP2)
Azim Khand61b8372017-07-10 11:54:01 +01001895 ret = DEPENDENCY_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001896#else
Azim Khand61b8372017-07-10 11:54:01 +01001897 ret = DEPENDENCY_NOT_SUPPORTED;
Azim Khan599cd242017-07-06 17:34:27 +01001898#endif
Azim Khand61b8372017-07-10 11:54:01 +01001899 }
1900 break;'''
Azim Khanb31aa442018-07-03 11:57:54 +01001901 expected_data = '''My test 1
Azim Khan599cd242017-07-06 17:34:27 +01001902depends_on:0
19030:int:0:int:0xfa:exp:0:exp:1
1904
1905My test 2
1906depends_on:0:1
19071:char*:"yahoo":int:88:exp:0
1908
1909'''
1910 expected_expression_code = '''
Azim Khand61b8372017-07-10 11:54:01 +01001911 case 0:
1912 {
1913 *out_value = MACRO1;
1914 }
1915 break;
1916 case 1:
1917 {
1918 *out_value = MACRO2;
1919 }
1920 break;'''
Azim Khan599cd242017-07-06 17:34:27 +01001921 self.assertEqual(dep_check_code, expected_dep_check_code)
Azim Khanb31aa442018-07-03 11:57:54 +01001922 self.assertEqual(out_data_f.getvalue(), expected_data)
Azim Khan599cd242017-07-06 17:34:27 +01001923 self.assertEqual(expression_code, expected_expression_code)
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001924
1925
Azim Khanb31aa442018-07-03 11:57:54 +01001926if __name__ == '__main__':
Azim Khan5e2ac1f2017-07-03 13:58:20 +01001927 unittest_main()