1#!/usr/bin/python3 2# 3# This file and its contents are supplied under the terms of the 4# Common Development and Distribution License ("CDDL"), version 1.0. 5# You may only use this file in accordance with the terms of version 6# 1.0 of the CDDL. 7# 8# A full copy of the text of the CDDL should have accompanied this 9# source. A copy of the CDDL is also available via the Internet at 10# http://www.illumos.org/license/CDDL. 11# 12 13# 14# Copyright 2026 Gordon W. Ross 15# 16 17""" 18Unit tests for ProbeGen.gen_probe() - probe program source generation. 19 20Expected outputs were captured from the previous implementation. 21""" 22 23import unittest 24 25from symbol_test import ProbeGen, SymEntry 26 27 28def make_entry(directive, symbol, headers, rtype=None, atypes=None, defval=None): 29 return SymEntry( 30 directive=directive, 31 symbol=symbol, 32 env_spec='', 33 headers=headers, 34 rtype=rtype, 35 atypes=atypes or [], 36 defval=defval, 37 ) 38 39 40class TestGenProbeC(unittest.TestCase): 41 """Probe generation for lang='c'.""" 42 43 def test_type(self): 44 e = make_entry('type', 'size_t', ['stddef.h'], rtype='size_t') 45 expected = ( 46 '#include <stddef.h>\n' 47 'size_t test_type;\n' 48 ) 49 self.assertEqual(ProbeGen.gen_probe(e, 'c'), expected) 50 51 def test_value(self): 52 e = make_entry('value', 'M_PI', ['math.h'], rtype='double') 53 expected = ( 54 '#include <math.h>\n' 55 'double test_value;\n' 56 'void\n' 57 'test_func(void)\n' 58 '{\n' 59 '\ttest_value = M_PI;\n' 60 '}\n' 61 ) 62 self.assertEqual(ProbeGen.gen_probe(e, 'c'), expected) 63 64 def test_define_no_value(self): 65 e = make_entry('define', 'INFINITY', ['math.h']) 66 expected = ( 67 '#include <math.h>\n' 68 '#if !defined(INFINITY)\n' 69 '#error INFINITY is not defined or has the wrong value\n' 70 '#endif\n' 71 '\n' 72 ) 73 self.assertEqual(ProbeGen.gen_probe(e, 'c'), expected) 74 75 def test_define_with_value(self): 76 e = make_entry('define', 'FLT_RADIX', ['float.h'], defval='2') 77 expected = ( 78 '#include <float.h>\n' 79 '#if !defined(FLT_RADIX) || FLT_RADIX != 2\n' 80 '#error FLT_RADIX is not defined or has the wrong value\n' 81 '#endif\n' 82 '\n' 83 ) 84 self.assertEqual(ProbeGen.gen_probe(e, 'c'), expected) 85 86 def test_func_single_arg(self): 87 e = make_entry('func', 'log', ['math.h'], rtype='double', atypes=['double']) 88 expected = ( 89 '#include <math.h>\n' 90 'double \n' 91 'test_func(double a0)\n' 92 '{\n' 93 '\treturn log(a0);\n' 94 '}\n' 95 ) 96 self.assertEqual(ProbeGen.gen_probe(e, 'c'), expected) 97 98 def test_func_multi_arg(self): 99 e = make_entry('func', 'hypot', ['math.h'], rtype='double', 100 atypes=['double', 'double']) 101 expected = ( 102 '#include <math.h>\n' 103 'double \n' 104 'test_func(double a0, double a1)\n' 105 '{\n' 106 '\treturn hypot(a0, a1);\n' 107 '}\n' 108 ) 109 self.assertEqual(ProbeGen.gen_probe(e, 'c'), expected) 110 111 def test_func_void_return(self): 112 e = make_entry('func', 'free', ['stdlib.h'], rtype='void', 113 atypes=['void *']) 114 expected = ( 115 '#include <stdlib.h>\n' 116 'void \n' 117 'test_func(void * a0)\n' 118 '{\n' 119 '\tfree(a0);\n' 120 '}\n' 121 ) 122 self.assertEqual(ProbeGen.gen_probe(e, 'c'), expected) 123 124 125class TestGenProbeCxx(unittest.TestCase): 126 """Probe generation for lang='c++'.""" 127 128 def test_func_result_macro(self): 129 """Non-void non-fnptr return: RESULT() macro must be emitted.""" 130 e = make_entry('func', 'log', ['cmath'], rtype='double', atypes=['double']) 131 expected = ( 132 '#include <cmath>\n' 133 '#if __cplusplus >= 201103L\n' 134 '#define RESULT(v) result{v}\n' 135 '#else\n' 136 '#define RESULT(v) result = (v)\n' 137 '#endif\n' 138 'double \n' 139 'test_func(double a0)\n' 140 '{\n' 141 '\tdouble RESULT(log(a0));\n' 142 '\treturn result;\n' 143 '}\n' 144 ) 145 self.assertEqual(ProbeGen.gen_probe(e, 'c++'), expected) 146 147 def test_func_void_return(self): 148 """void return: no RESULT() macro; same form as C.""" 149 e = make_entry('func', 'free', ['cstdlib'], rtype='void', 150 atypes=['void *']) 151 expected = ( 152 '#include <cstdlib>\n' 153 'void \n' 154 'test_func(void * a0)\n' 155 '{\n' 156 '\tfree(a0);\n' 157 '}\n' 158 ) 159 self.assertEqual(ProbeGen.gen_probe(e, 'c++'), expected) 160 161 162if __name__ == '__main__': 163 unittest.main() 164