blob: f7c6a8ac3ee7199a09e635e19ef25fdd320f1ef8 [file] [log] [blame]
Gilles Peskinea1bb3f82020-03-24 18:20:59 +01001#!/usr/bin/env python3
2
Azim Khan951a2c82018-06-29 03:47:08 +01003# Greentea host test script for Mbed TLS on-target test suite testing.
Azim Khanf0e42fb2017-08-02 14:47:13 +01004#
Bence Szépkútia2947ac2020-08-19 16:37:36 +02005# Copyright The Mbed TLS Contributors
Bence Szépkútif744bd72020-06-05 13:02:18 +02006# SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later
7#
8# This file is provided under the Apache License 2.0, or the
9# GNU General Public License v2.0 or later.
10#
11# **********
12# Apache License 2.0:
Azim Khanf0e42fb2017-08-02 14:47:13 +010013#
14# Licensed under the Apache License, Version 2.0 (the "License"); you may
15# not use this file except in compliance with the License.
16# You may obtain a copy of the License at
17#
18# http://www.apache.org/licenses/LICENSE-2.0
19#
20# Unless required by applicable law or agreed to in writing, software
21# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
22# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
23# See the License for the specific language governing permissions and
24# limitations under the License.
25#
Bence Szépkútif744bd72020-06-05 13:02:18 +020026# **********
27#
28# **********
29# GNU General Public License v2.0 or later:
30#
31# This program is free software; you can redistribute it and/or modify
32# it under the terms of the GNU General Public License as published by
33# the Free Software Foundation; either version 2 of the License, or
34# (at your option) any later version.
35#
36# This program is distributed in the hope that it will be useful,
37# but WITHOUT ANY WARRANTY; without even the implied warranty of
38# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
39# GNU General Public License for more details.
40#
41# You should have received a copy of the GNU General Public License along
42# with this program; if not, write to the Free Software Foundation, Inc.,
43# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
44#
45# **********
Azim Khanf0e42fb2017-08-02 14:47:13 +010046
47
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +010048"""
Azim Khan8d686bf2018-07-04 23:29:46 +010049Mbed TLS on-target test suite tests are implemented as Greentea
Azim Khan951a2c82018-06-29 03:47:08 +010050tests. Greentea tests are implemented in two parts: target test and
51host test. Target test is a C application that is built for the
52target platform and executes on the target. Host test is a Python
53class derived from mbed_host_tests.BaseHostTest. Target communicates
Azim Khan8d686bf2018-07-04 23:29:46 +010054with the host over serial for the test data and sends back the result.
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +010055
Azim Khanb31aa442018-07-03 11:57:54 +010056Python tool mbedgt (Greentea) is responsible for flashing the test
Azim Khan8d686bf2018-07-04 23:29:46 +010057binary on to the target and dynamically loading this host test module.
Azim Khan951a2c82018-06-29 03:47:08 +010058
Azim Khan8d686bf2018-07-04 23:29:46 +010059Greentea documentation can be found here:
60https://github.com/ARMmbed/greentea
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +010061"""
62
Azim Khanf0e42fb2017-08-02 14:47:13 +010063
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +010064import re
65import os
Azim Khan663d4702017-07-07 15:40:26 +010066import binascii
Gilles Peskineafd19dd2019-02-25 21:39:42 +010067
68from mbed_host_tests import BaseHostTest, event_callback # pylint: disable=import-error
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +010069
70
Azim Khanb98e6ee2018-06-28 17:11:33 +010071class TestDataParserError(Exception):
72 """Indicates error in test data, read from .data file."""
73 pass
74
75
Gilles Peskinea1bb3f82020-03-24 18:20:59 +010076class TestDataParser:
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +010077 """
Azim Khan951a2c82018-06-29 03:47:08 +010078 Parses test name, dependencies, test function name and test parameters
79 from the data file.
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +010080 """
81
82 def __init__(self):
83 """
84 Constructor
85 """
86 self.tests = []
87
88 def parse(self, data_file):
89 """
Azim Khanf0e42fb2017-08-02 14:47:13 +010090 Data file parser.
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +010091
Azim Khanf0e42fb2017-08-02 14:47:13 +010092 :param data_file: Data file path
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +010093 """
Azim Khanb31aa442018-07-03 11:57:54 +010094 with open(data_file, 'r') as data_f:
95 self.__parse(data_f)
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +010096
97 @staticmethod
Azim Khanb31aa442018-07-03 11:57:54 +010098 def __escaped_split(inp_str, split_char):
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +010099 """
Azim Khanb31aa442018-07-03 11:57:54 +0100100 Splits inp_str on split_char except when escaped.
Azim Khanf0e42fb2017-08-02 14:47:13 +0100101
Azim Khanb31aa442018-07-03 11:57:54 +0100102 :param inp_str: String to split
103 :param split_char: Split character
Azim Khanf0e42fb2017-08-02 14:47:13 +0100104 :return: List of splits
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100105 """
Ron Eldor111ba0e2018-11-18 17:05:05 +0200106 split_colon_fn = lambda x: re.sub(r'\\' + split_char, split_char, x)
Azim Khanb31aa442018-07-03 11:57:54 +0100107 if len(split_char) > 1:
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100108 raise ValueError('Expected split character. Found string!')
Ron Eldor56b6e522019-05-29 17:17:10 +0300109 out = list(map(split_colon_fn, re.split(r'(?<!\\)' + split_char, inp_str)))
Ron Eldor7c52e222019-06-25 14:52:19 +0300110 out = [x for x in out if x]
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100111 return out
112
Azim Khanb31aa442018-07-03 11:57:54 +0100113 def __parse(self, data_f):
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100114 """
Azim Khanf0e42fb2017-08-02 14:47:13 +0100115 Parses data file using supplied file object.
116
Azim Khanb31aa442018-07-03 11:57:54 +0100117 :param data_f: Data file object
Azim Khanf0e42fb2017-08-02 14:47:13 +0100118 :return:
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100119 """
Ron Eldorb43fe572019-06-03 11:38:42 +0300120 for line in data_f:
121 line = line.strip()
Azim Khanb31aa442018-07-03 11:57:54 +0100122 if not line:
Ron Eldorb43fe572019-06-03 11:38:42 +0300123 continue
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100124 # Read test name
125 name = line
126
127 # Check dependencies
Azim Khanb31aa442018-07-03 11:57:54 +0100128 dependencies = []
Ron Eldorb43fe572019-06-03 11:38:42 +0300129 line = next(data_f).strip()
Azim Khanb31aa442018-07-03 11:57:54 +0100130 match = re.search('depends_on:(.*)', line)
131 if match:
132 dependencies = [int(x) for x in match.group(1).split(':')]
Ron Eldorb43fe572019-06-03 11:38:42 +0300133 line = next(data_f).strip()
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100134
135 # Read test vectors
Azim Khan663d4702017-07-07 15:40:26 +0100136 line = line.replace('\\n', '\n')
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100137 parts = self.__escaped_split(line, ':')
Azim Khanb31aa442018-07-03 11:57:54 +0100138 function_name = int(parts[0])
139 args = parts[1:]
140 args_count = len(args)
141 if args_count % 2 != 0:
Ron Eldor111ba0e2018-11-18 17:05:05 +0200142 err_str_fmt = "Number of test arguments({}) should be even: {}"
143 raise TestDataParserError(err_str_fmt.format(args_count, line))
Azim Khanb31aa442018-07-03 11:57:54 +0100144 grouped_args = [(args[i * 2], args[(i * 2) + 1])
Ron Eldor56b6e522019-05-29 17:17:10 +0300145 for i in range(int(len(args)/2))]
Azim Khanb31aa442018-07-03 11:57:54 +0100146 self.tests.append((name, function_name, dependencies,
147 grouped_args))
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100148
149 def get_test_data(self):
150 """
Azim Khanf0e42fb2017-08-02 14:47:13 +0100151 Returns test data.
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100152 """
153 return self.tests
154
155
156class MbedTlsTest(BaseHostTest):
157 """
Azim Khanb31aa442018-07-03 11:57:54 +0100158 Host test for Mbed TLS unit tests. This script is loaded at
159 run time by Greentea for executing Mbed TLS test suites. Each
Azim Khan951a2c82018-06-29 03:47:08 +0100160 communication from the target is received in this object as
161 an event, which is then handled by the event handler method
162 decorated by the associated event. Ex: @event_callback('GO').
163
164 Target test sends requests for dispatching next test. It reads
165 tests from the intermediate data file and sends test function
166 identifier, dependency identifiers, expression identifiers and
Azim Khanb31aa442018-07-03 11:57:54 +0100167 the test data in binary form. Target test checks dependencies
Azim Khan951a2c82018-06-29 03:47:08 +0100168 , evaluate integer constant expressions and dispatches the test
Azim Khan8d686bf2018-07-04 23:29:46 +0100169 function with received test parameters. After test function is
170 finished, target sends the result. This class handles the result
171 event and prints verdict in the form that Greentea understands.
Azim Khan951a2c82018-06-29 03:47:08 +0100172
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100173 """
Azim Khan951a2c82018-06-29 03:47:08 +0100174 # status/error codes from suites/helpers.function
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100175 DEPENDENCY_SUPPORTED = 0
176 KEY_VALUE_MAPPING_FOUND = DEPENDENCY_SUPPORTED
177 DISPATCH_TEST_SUCCESS = DEPENDENCY_SUPPORTED
178
Azim Khan951a2c82018-06-29 03:47:08 +0100179 KEY_VALUE_MAPPING_NOT_FOUND = -1 # Expression Id not found.
180 DEPENDENCY_NOT_SUPPORTED = -2 # Dependency not supported.
181 DISPATCH_TEST_FN_NOT_FOUND = -3 # Test function not found.
182 DISPATCH_INVALID_TEST_DATA = -4 # Invalid parameter type.
183 DISPATCH_UNSUPPORTED_SUITE = -5 # Test suite not supported/enabled.
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100184
185 def __init__(self):
186 """
Azim Khanf0e42fb2017-08-02 14:47:13 +0100187 Constructor initialises test index to 0.
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100188 """
189 super(MbedTlsTest, self).__init__()
190 self.tests = []
191 self.test_index = -1
192 self.dep_index = 0
Ron Eldor8672cb72018-11-13 18:42:35 +0200193 self.suite_passed = True
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100194 self.error_str = dict()
Azim Khanb31aa442018-07-03 11:57:54 +0100195 self.error_str[self.DEPENDENCY_SUPPORTED] = \
196 'DEPENDENCY_SUPPORTED'
197 self.error_str[self.KEY_VALUE_MAPPING_NOT_FOUND] = \
198 'KEY_VALUE_MAPPING_NOT_FOUND'
199 self.error_str[self.DEPENDENCY_NOT_SUPPORTED] = \
200 'DEPENDENCY_NOT_SUPPORTED'
201 self.error_str[self.DISPATCH_TEST_FN_NOT_FOUND] = \
202 'DISPATCH_TEST_FN_NOT_FOUND'
203 self.error_str[self.DISPATCH_INVALID_TEST_DATA] = \
204 'DISPATCH_INVALID_TEST_DATA'
205 self.error_str[self.DISPATCH_UNSUPPORTED_SUITE] = \
206 'DISPATCH_UNSUPPORTED_SUITE'
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100207
208 def setup(self):
209 """
Azim Khan951a2c82018-06-29 03:47:08 +0100210 Setup hook implementation. Reads test suite data file and parses out
211 tests.
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100212 """
213 binary_path = self.get_config_item('image_path')
214 script_dir = os.path.split(os.path.abspath(__file__))[0]
215 suite_name = os.path.splitext(os.path.basename(binary_path))[0]
Ron Eldorc242eea2018-11-05 16:22:36 +0200216 data_file = ".".join((suite_name, 'datax'))
Azim Khan951a2c82018-06-29 03:47:08 +0100217 data_file = os.path.join(script_dir, '..', 'mbedtls',
218 suite_name, data_file)
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100219 if os.path.exists(data_file):
220 self.log("Running tests from %s" % data_file)
221 parser = TestDataParser()
222 parser.parse(data_file)
223 self.tests = parser.get_test_data()
224 self.print_test_info()
225 else:
226 self.log("Data file not found: %s" % data_file)
227 self.notify_complete(False)
228
229 def print_test_info(self):
230 """
Azim Khanf0e42fb2017-08-02 14:47:13 +0100231 Prints test summary read by Greentea to detect test cases.
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100232 """
233 self.log('{{__testcase_count;%d}}' % len(self.tests))
234 for name, _, _, _ in self.tests:
235 self.log('{{__testcase_name;%s}}' % name)
236
237 @staticmethod
Azim Khanb31aa442018-07-03 11:57:54 +0100238 def align_32bit(data_bytes):
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100239 """
Azim Khanf0e42fb2017-08-02 14:47:13 +0100240 4 byte aligns input byte array.
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100241
242 :return:
243 """
Azim Khanb31aa442018-07-03 11:57:54 +0100244 data_bytes += bytearray((4 - (len(data_bytes))) % 4)
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100245
Azim Khand59391a2017-06-01 14:04:17 +0100246 @staticmethod
247 def hex_str_bytes(hex_str):
248 """
249 Converts Hex string representation to byte array
250
Azim Khanf0e42fb2017-08-02 14:47:13 +0100251 :param hex_str: Hex in string format.
252 :return: Output Byte array
Azim Khand59391a2017-06-01 14:04:17 +0100253 """
Azim Khanb98e6ee2018-06-28 17:11:33 +0100254 if hex_str[0] != '"' or hex_str[len(hex_str) - 1] != '"':
255 raise TestDataParserError("HEX test parameter missing '\"':"
256 " %s" % hex_str)
Azim Khand59391a2017-06-01 14:04:17 +0100257 hex_str = hex_str.strip('"')
Azim Khanb98e6ee2018-06-28 17:11:33 +0100258 if len(hex_str) % 2 != 0:
259 raise TestDataParserError("HEX parameter len should be mod of "
260 "2: %s" % hex_str)
Azim Khand59391a2017-06-01 14:04:17 +0100261
Azim Khanb31aa442018-07-03 11:57:54 +0100262 data_bytes = binascii.unhexlify(hex_str)
263 return data_bytes
Azim Khand59391a2017-06-01 14:04:17 +0100264
Azim Khan663d4702017-07-07 15:40:26 +0100265 @staticmethod
Azim Khanb31aa442018-07-03 11:57:54 +0100266 def int32_to_big_endian_bytes(i):
Azim Khan663d4702017-07-07 15:40:26 +0100267 """
Azim Khanb31aa442018-07-03 11:57:54 +0100268 Coverts i to byte array in big endian format.
Azim Khan663d4702017-07-07 15:40:26 +0100269
Azim Khanf0e42fb2017-08-02 14:47:13 +0100270 :param i: Input integer
271 :return: Output bytes array in big endian or network order
Azim Khan663d4702017-07-07 15:40:26 +0100272 """
Azim Khanb31aa442018-07-03 11:57:54 +0100273 data_bytes = bytearray([((i >> x) & 0xff) for x in [24, 16, 8, 0]])
274 return data_bytes
Azim Khan663d4702017-07-07 15:40:26 +0100275
Azim Khanb31aa442018-07-03 11:57:54 +0100276 def test_vector_to_bytes(self, function_id, dependencies, parameters):
Azim Khan663d4702017-07-07 15:40:26 +0100277 """
278 Converts test vector into a byte array that can be sent to the target.
279
Azim Khanf0e42fb2017-08-02 14:47:13 +0100280 :param function_id: Test Function Identifier
Azim Khanb31aa442018-07-03 11:57:54 +0100281 :param dependencies: Dependency list
Azim Khanf0e42fb2017-08-02 14:47:13 +0100282 :param parameters: Test function input parameters
283 :return: Byte array and its length
Azim Khan663d4702017-07-07 15:40:26 +0100284 """
Azim Khanb31aa442018-07-03 11:57:54 +0100285 data_bytes = bytearray([len(dependencies)])
286 if dependencies:
287 data_bytes += bytearray(dependencies)
288 data_bytes += bytearray([function_id, len(parameters)])
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100289 for typ, param in parameters:
Gilles Peskine399b82f2020-03-24 18:36:56 +0100290 if typ in ('int', 'exp'):
Ron Eldor7c52e222019-06-25 14:52:19 +0300291 i = int(param, 0)
Ron Eldorb43fe572019-06-03 11:38:42 +0300292 data_bytes += b'I' if typ == 'int' else b'E'
Azim Khanb31aa442018-07-03 11:57:54 +0100293 self.align_32bit(data_bytes)
294 data_bytes += self.int32_to_big_endian_bytes(i)
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100295 elif typ == 'char*':
296 param = param.strip('"')
297 i = len(param) + 1 # + 1 for null termination
Ron Eldorb43fe572019-06-03 11:38:42 +0300298 data_bytes += b'S'
Azim Khanb31aa442018-07-03 11:57:54 +0100299 self.align_32bit(data_bytes)
300 data_bytes += self.int32_to_big_endian_bytes(i)
Ron Eldor9d40da22019-06-03 13:39:21 +0300301 data_bytes += bytearray(param, encoding='ascii')
Ron Eldorb43fe572019-06-03 11:38:42 +0300302 data_bytes += b'\0' # Null terminate
Azim Khand59391a2017-06-01 14:04:17 +0100303 elif typ == 'hex':
Azim Khanb31aa442018-07-03 11:57:54 +0100304 binary_data = self.hex_str_bytes(param)
Ron Eldorb43fe572019-06-03 11:38:42 +0300305 data_bytes += b'H'
Azim Khanb31aa442018-07-03 11:57:54 +0100306 self.align_32bit(data_bytes)
307 i = len(binary_data)
308 data_bytes += self.int32_to_big_endian_bytes(i)
309 data_bytes += binary_data
310 length = self.int32_to_big_endian_bytes(len(data_bytes))
311 return data_bytes, length
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100312
313 def run_next_test(self):
314 """
Azim Khan951a2c82018-06-29 03:47:08 +0100315 Fetch next test information and execute the test.
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100316
317 """
318 self.test_index += 1
319 self.dep_index = 0
320 if self.test_index < len(self.tests):
Azim Khanb31aa442018-07-03 11:57:54 +0100321 name, function_id, dependencies, args = self.tests[self.test_index]
322 self.run_test(name, function_id, dependencies, args)
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100323 else:
Ron Eldor8672cb72018-11-13 18:42:35 +0200324 self.notify_complete(self.suite_passed)
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100325
Azim Khanb31aa442018-07-03 11:57:54 +0100326 def run_test(self, name, function_id, dependencies, args):
Azim Khan663d4702017-07-07 15:40:26 +0100327 """
Azim Khan951a2c82018-06-29 03:47:08 +0100328 Execute the test on target by sending next test information.
Azim Khan663d4702017-07-07 15:40:26 +0100329
Azim Khanf0e42fb2017-08-02 14:47:13 +0100330 :param name: Test name
331 :param function_id: function identifier
Azim Khanb31aa442018-07-03 11:57:54 +0100332 :param dependencies: Dependencies list
Azim Khanf0e42fb2017-08-02 14:47:13 +0100333 :param args: test parameters
Azim Khan663d4702017-07-07 15:40:26 +0100334 :return:
335 """
336 self.log("Running: %s" % name)
337
Azim Khanb31aa442018-07-03 11:57:54 +0100338 param_bytes, length = self.test_vector_to_bytes(function_id,
339 dependencies, args)
Darryl Green349a0792019-12-17 10:17:20 +0000340 self.send_kv(
341 ''.join('{:02x}'.format(x) for x in length),
342 ''.join('{:02x}'.format(x) for x in param_bytes)
343 )
Azim Khan663d4702017-07-07 15:40:26 +0100344
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100345 @staticmethod
346 def get_result(value):
Azim Khanf0e42fb2017-08-02 14:47:13 +0100347 """
348 Converts result from string type to integer
349 :param value: Result code in string
Azim Khan8d686bf2018-07-04 23:29:46 +0100350 :return: Integer result code. Value is from the test status
351 constants defined under the MbedTlsTest class.
Azim Khanf0e42fb2017-08-02 14:47:13 +0100352 """
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100353 try:
354 return int(value)
355 except ValueError:
Azim Khanb31aa442018-07-03 11:57:54 +0100356 ValueError("Result should return error number. "
357 "Instead received %s" % value)
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100358
359 @event_callback('GO')
Azim Khanb31aa442018-07-03 11:57:54 +0100360 def on_go(self, _key, _value, _timestamp):
Azim Khanf0e42fb2017-08-02 14:47:13 +0100361 """
Azim Khan951a2c82018-06-29 03:47:08 +0100362 Sent by the target to start first test.
Azim Khanf0e42fb2017-08-02 14:47:13 +0100363
Azim Khanb31aa442018-07-03 11:57:54 +0100364 :param _key: Event key
365 :param _value: Value. ignored
366 :param _timestamp: Timestamp ignored.
Azim Khanf0e42fb2017-08-02 14:47:13 +0100367 :return:
368 """
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100369 self.run_next_test()
370
371 @event_callback("R")
Azim Khanb31aa442018-07-03 11:57:54 +0100372 def on_result(self, _key, value, _timestamp):
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100373 """
Azim Khan951a2c82018-06-29 03:47:08 +0100374 Handle result. Prints test start, finish required by Greentea
375 to detect test execution.
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100376
Azim Khanb31aa442018-07-03 11:57:54 +0100377 :param _key: Event key
Azim Khanf0e42fb2017-08-02 14:47:13 +0100378 :param value: Value. ignored
Azim Khanb31aa442018-07-03 11:57:54 +0100379 :param _timestamp: Timestamp ignored.
Azim Khanf0e42fb2017-08-02 14:47:13 +0100380 :return:
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100381 """
382 int_val = self.get_result(value)
Azim Khanb31aa442018-07-03 11:57:54 +0100383 name, _, _, _ = self.tests[self.test_index]
Azim Khan5e7f8df2017-05-31 20:33:39 +0100384 self.log('{{__testcase_start;%s}}' % name)
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100385 self.log('{{__testcase_finish;%s;%d;%d}}' % (name, int_val == 0,
386 int_val != 0))
Ron Eldor8672cb72018-11-13 18:42:35 +0200387 if int_val != 0:
388 self.suite_passed = False
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100389 self.run_next_test()
390
391 @event_callback("F")
Azim Khanb31aa442018-07-03 11:57:54 +0100392 def on_failure(self, _key, value, _timestamp):
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100393 """
Azim Khanf0e42fb2017-08-02 14:47:13 +0100394 Handles test execution failure. That means dependency not supported or
395 Test function not supported. Hence marking test as skipped.
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100396
Azim Khanb31aa442018-07-03 11:57:54 +0100397 :param _key: Event key
Azim Khanf0e42fb2017-08-02 14:47:13 +0100398 :param value: Value. ignored
Azim Khanb31aa442018-07-03 11:57:54 +0100399 :param _timestamp: Timestamp ignored.
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100400 :return:
401 """
402 int_val = self.get_result(value)
Mohammad Azim Khan7a0d84f2017-04-01 03:18:20 +0100403 if int_val in self.error_str:
404 err = self.error_str[int_val]
405 else:
406 err = 'Unknown error'
407 # For skip status, do not write {{__testcase_finish;...}}
408 self.log("Error: %s" % err)
409 self.run_next_test()