1## 2## Copyright(c) 2020-2024 Qualcomm Innovation Center, Inc. All Rights Reserved. 3## 4## This program is free software; you can redistribute it and/or modify 5## it under the terms of the GNU General Public License as published by 6## the Free Software Foundation; either version 2 of the License, or 7## (at your option) any later version. 8## 9## This program is distributed in the hope that it will be useful, 10## but WITHOUT ANY WARRANTY; without even the implied warranty of 11## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12## GNU General Public License for more details. 13## 14## You should have received a copy of the GNU General Public License 15## along with this program; if not, see <http://www.gnu.org/licenses/>. 16## 17 18hexagon_ss = ss.source_set() 19 20hex_common_py = 'hex_common.py' 21gen_tcg_h = meson.current_source_dir() / 'gen_tcg.h' 22gen_tcg_hvx_h = meson.current_source_dir() / 'gen_tcg_hvx.h' 23idef_parser_dir = meson.current_source_dir() / 'idef-parser' 24 25# 26# Step 1 27# We use a C program to create semantics_generated.pyinc 28# 29gen_semantics = executable( 30 'gen_semantics', 31 'gen_semantics.c', 32 native: true, build_by_default: false) 33 34semantics_generated = custom_target( 35 'semantics_generated.pyinc', 36 output: 'semantics_generated.pyinc', 37 command: [gen_semantics, '@OUTPUT@'], 38) 39hexagon_ss.add(semantics_generated) 40 41# 42# Step 2 43# We use Python scripts to generate the following files 44# tcg_func_table_generated.c.inc 45# printinsn_generated.h.inc 46# op_attribs_generated.h.inc 47# opcodes_def_generated.h.inc 48# 49tcg_func_table_generated = custom_target( 50 'tcg_func_table_generated.c.inc', 51 output: 'tcg_func_table_generated.c.inc', 52 depends: [semantics_generated], 53 depend_files: [hex_common_py], 54 command: [python, files('gen_tcg_func_table.py'), semantics_generated, '@OUTPUT@'], 55) 56hexagon_ss.add(tcg_func_table_generated) 57 58printinsn_generated = custom_target( 59 'printinsn_generated.h.inc', 60 output: 'printinsn_generated.h.inc', 61 depends: [semantics_generated], 62 depend_files: [hex_common_py], 63 command: [python, files('gen_printinsn.py'), semantics_generated, '@OUTPUT@'], 64) 65hexagon_ss.add(printinsn_generated) 66 67op_attribs_generated = custom_target( 68 'op_attribs_generated.h.inc', 69 output: 'op_attribs_generated.h.inc', 70 depends: [semantics_generated], 71 depend_files: [hex_common_py], 72 command: [python, files('gen_op_attribs.py'), semantics_generated, '@OUTPUT@'], 73) 74hexagon_ss.add(op_attribs_generated) 75 76opcodes_def_generated = custom_target( 77 'opcodes_def_generated.h.inc', 78 output: 'opcodes_def_generated.h.inc', 79 depends: [semantics_generated], 80 depend_files: [hex_common_py], 81 command: [python, files('gen_opcodes_def.py'), semantics_generated, '@OUTPUT@'], 82) 83hexagon_ss.add(opcodes_def_generated) 84 85# 86# Step 3 87# We use a C program to create iset.py which is imported into dectree.py 88# to create the decode tree 89# 90gen_dectree_import = executable( 91 'gen_dectree_import', 92 'gen_dectree_import.c', opcodes_def_generated, 93 native: true, build_by_default: false) 94 95iset_py = custom_target( 96 'iset.py', 97 output: 'iset.py', 98 command: [gen_dectree_import, '@OUTPUT@'], 99) 100hexagon_ss.add(iset_py) 101 102# 103# Step 4 104# Generate the input to the QEMU decodetree.py script 105# 106normal_decode_generated = custom_target( 107 'normal_decode_generated', 108 output: 'normal_decode_generated', 109 depends: [iset_py, semantics_generated], 110 env: {'PYTHONPATH': meson.current_build_dir()}, 111 command: [python, files('gen_decodetree.py'), semantics_generated, 'NORMAL', '@OUTPUT@'], 112) 113hexagon_ss.add(normal_decode_generated) 114 115hvx_decode_generated = custom_target( 116 'hvx_decode_generated', 117 output: 'hvx_decode_generated', 118 depends: [iset_py, semantics_generated], 119 env: {'PYTHONPATH': meson.current_build_dir()}, 120 command: [python, files('gen_decodetree.py'), semantics_generated, 'EXT_mmvec', '@OUTPUT@'], 121) 122hexagon_ss.add(hvx_decode_generated) 123 124subinsn_a_decode_generated = custom_target( 125 'subinsn_a_decode_generated', 126 output: 'subinsn_a_decode_generated', 127 depends: [iset_py, semantics_generated], 128 env: {'PYTHONPATH': meson.current_build_dir()}, 129 command: [python, files('gen_decodetree.py'), semantics_generated, 'SUBINSN_A', '@OUTPUT@'], 130) 131hexagon_ss.add(subinsn_a_decode_generated) 132 133subinsn_l1_decode_generated = custom_target( 134 'subinsn_l1_decode_generated', 135 output: 'subinsn_l1_decode_generated', 136 depends: [iset_py, semantics_generated], 137 env: {'PYTHONPATH': meson.current_build_dir()}, 138 command: [python, files('gen_decodetree.py'), semantics_generated, 'SUBINSN_L1', '@OUTPUT@'], 139) 140hexagon_ss.add(subinsn_l1_decode_generated) 141 142subinsn_l2_decode_generated = custom_target( 143 'subinsn_l2_decode_generated', 144 output: 'subinsn_l2_decode_generated', 145 depends: [iset_py, semantics_generated], 146 env: {'PYTHONPATH': meson.current_build_dir()}, 147 command: [python, files('gen_decodetree.py'), semantics_generated, 'SUBINSN_L2', '@OUTPUT@'], 148) 149hexagon_ss.add(subinsn_l2_decode_generated) 150 151subinsn_s1_decode_generated = custom_target( 152 'subinsn_s1_decode_generated', 153 output: 'subinsn_s1_decode_generated', 154 depends: [iset_py, semantics_generated], 155 env: {'PYTHONPATH': meson.current_build_dir()}, 156 command: [python, files('gen_decodetree.py'), semantics_generated, 'SUBINSN_S1', '@OUTPUT@'], 157) 158hexagon_ss.add(subinsn_s1_decode_generated) 159 160subinsn_s2_decode_generated = custom_target( 161 'subinsn_s2_decode_generated', 162 output: 'subinsn_s2_decode_generated', 163 depends: [iset_py, semantics_generated], 164 env: {'PYTHONPATH': meson.current_build_dir()}, 165 command: [python, files('gen_decodetree.py'), semantics_generated, 'SUBINSN_S2', '@OUTPUT@'], 166) 167hexagon_ss.add(subinsn_s2_decode_generated) 168 169# 170# Run the QEMU decodetree.py script to produce the instruction decoder 171# 172decodetree_py = meson.current_source_dir() / '../../scripts/decodetree.py' 173decode_normal_generated = custom_target( 174 'decode_normal_generated.c.inc', 175 output: 'decode_normal_generated.c.inc', 176 input: normal_decode_generated, 177 env: {'PYTHONPATH': meson.current_build_dir()}, 178 command: [python, files(decodetree_py), normal_decode_generated, '--static-decode=decode_normal', '-o', '@OUTPUT@'], 179) 180hexagon_ss.add(decode_normal_generated) 181 182decode_hvx_generated = custom_target( 183 'decode_hvx_generated.c.inc', 184 output: 'decode_hvx_generated.c.inc', 185 input: hvx_decode_generated, 186 env: {'PYTHONPATH': meson.current_build_dir()}, 187 command: [python, files(decodetree_py), hvx_decode_generated, '--static-decode=decode_hvx', '-o', '@OUTPUT@'], 188) 189hexagon_ss.add(decode_hvx_generated) 190 191decode_subinsn_a_generated = custom_target( 192 'decode_subinsn_a_generated.c.inc', 193 output: 'decode_subinsn_a_generated.c.inc', 194 input: subinsn_a_decode_generated, 195 env: {'PYTHONPATH': meson.current_build_dir()}, 196 command: [python, files(decodetree_py), subinsn_a_decode_generated, ['--static-decode=decode_subinsn_a', '--insnwidth=16'], '-o', '@OUTPUT@'], 197) 198hexagon_ss.add(decode_subinsn_a_generated) 199 200decode_subinsn_l1_generated = custom_target( 201 'decode_subinsn_l1_generated.c.inc', 202 output: 'decode_subinsn_l1_generated.c.inc', 203 input: subinsn_l1_decode_generated, 204 env: {'PYTHONPATH': meson.current_build_dir()}, 205 command: [python, files(decodetree_py), subinsn_l1_decode_generated, ['--static-decode=decode_subinsn_l1', '--insnwidth=16'], '-o', '@OUTPUT@'], 206) 207hexagon_ss.add(decode_subinsn_l1_generated) 208 209decode_subinsn_l2_generated = custom_target( 210 'decode_subinsn_l2_generated.c.inc', 211 output: 'decode_subinsn_l2_generated.c.inc', 212 input: subinsn_l2_decode_generated, 213 env: {'PYTHONPATH': meson.current_build_dir()}, 214 command: [python, files(decodetree_py), subinsn_l2_decode_generated, ['--static-decode=decode_subinsn_l2', '--insnwidth=16'], '-o', '@OUTPUT@'], 215) 216hexagon_ss.add(decode_subinsn_l2_generated) 217 218decode_subinsn_s1_generated = custom_target( 219 'decode_subinsn_s1_generated.c.inc', 220 output: 'decode_subinsn_s1_generated.c.inc', 221 input: subinsn_s1_decode_generated, 222 env: {'PYTHONPATH': meson.current_build_dir()}, 223 command: [python, files(decodetree_py), subinsn_s1_decode_generated, ['--static-decode=decode_subinsn_s1', '--insnwidth=16'], '-o', '@OUTPUT@'], 224) 225hexagon_ss.add(decode_subinsn_s1_generated) 226 227decode_subinsn_s2_generated = custom_target( 228 'decode_subinsn_s2_generated.c.inc', 229 output: 'decode_subinsn_s2_generated.c.inc', 230 input: subinsn_s2_decode_generated, 231 env: {'PYTHONPATH': meson.current_build_dir()}, 232 command: [python, files(decodetree_py), subinsn_s2_decode_generated, ['--static-decode=decode_subinsn_s2', '--insnwidth=16'], '-o', '@OUTPUT@'], 233) 234hexagon_ss.add(decode_subinsn_s2_generated) 235 236# 237# Generate the trans_* functions that the decoder will use 238# 239decodetree_trans_funcs_generated = custom_target( 240 'decodetree_trans_funcs_generated.c.inc', 241 output: 'decodetree_trans_funcs_generated.c.inc', 242 depends: [iset_py, semantics_generated], 243 env: {'PYTHONPATH': meson.current_build_dir()}, 244 command: [python, files('gen_trans_funcs.py'), semantics_generated, '@OUTPUT@'], 245) 246hexagon_ss.add(decodetree_trans_funcs_generated) 247 248hexagon_ss.add(files( 249 'cpu.c', 250 'translate.c', 251 'op_helper.c', 252 'gdbstub.c', 253 'genptr.c', 254 'reg_fields.c', 255 'decode.c', 256 'iclass.c', 257 'opcodes.c', 258 'printinsn.c', 259 'arch.c', 260 'fma_emu.c', 261 'mmvec/decode_ext_mmvec.c', 262 'mmvec/system_ext_mmvec.c', 263)) 264 265# 266# Step 4.5 267# We use flex/bison based idef-parser to generate TCG code for a lot 268# of instructions. idef-parser outputs 269# idef-generated-emitter.c 270# idef-generated-emitter.h.inc 271# idef-generated-enabled-instructions 272# 273idef_parser_enabled = get_option('hexagon_idef_parser') 274if idef_parser_enabled and 'hexagon-linux-user' in target_dirs 275 idef_parser_input_generated = custom_target( 276 'idef_parser_input.h.inc', 277 output: 'idef_parser_input.h.inc', 278 depends: [semantics_generated], 279 depend_files: [hex_common_py], 280 command: [python, files('gen_idef_parser_funcs.py'), semantics_generated, '@OUTPUT@'], 281 ) 282 283 preprocessed_idef_parser_input_generated = custom_target( 284 'idef_parser_input.preprocessed.h.inc', 285 output: 'idef_parser_input.preprocessed.h.inc', 286 input: idef_parser_input_generated, 287 depend_files: [idef_parser_dir / 'macros.inc'], 288 command: [idef_parser_dir / 'prepare', '@INPUT@', '-I' + idef_parser_dir, '-o', '@OUTPUT@'], 289 ) 290 291 flex = generator( 292 find_program('flex'), 293 output: ['@BASENAME@.yy.c', '@BASENAME@.yy.h'], 294 arguments: ['-o', '@OUTPUT0@', '--header-file=@OUTPUT1@', '@INPUT@'] 295 ) 296 297 bison = generator( 298 find_program('bison', version: '>=3.0'), 299 output: ['@BASENAME@.tab.c', '@BASENAME@.tab.h'], 300 arguments: ['@INPUT@', '--defines=@OUTPUT1@', '--output=@OUTPUT0@'] 301 ) 302 303 glib_dep = dependency('glib-2.0', native: true) 304 305 idef_parser = executable( 306 'idef-parser', 307 [flex.process(idef_parser_dir / 'idef-parser.lex'), 308 bison.process(idef_parser_dir / 'idef-parser.y'), 309 idef_parser_dir / 'parser-helpers.c'], 310 include_directories: ['idef-parser', '../../include/'], 311 dependencies: [glib_dep], 312 native: true 313 ) 314 315 idef_generated_tcg = custom_target( 316 'idef-generated-tcg', 317 output: ['idef-generated-emitter.c', 318 'idef-generated-emitter.h.inc', 319 'idef-generated-enabled-instructions'], 320 input: preprocessed_idef_parser_input_generated, 321 depend_files: [hex_common_py], 322 command: [idef_parser, '@INPUT@', '@OUTPUT0@', '@OUTPUT1@', '@OUTPUT2@'] 323 ) 324 325 indent = find_program('indent', required: false) 326 if indent.found() 327 idef_generated_tcg_c = custom_target( 328 'indent', 329 input: idef_generated_tcg[0], 330 output: 'idef-generated-emitter.indented.c', 331 command: [indent, '-linux', '@INPUT@', '-o', '@OUTPUT@'] 332 ) 333 else 334 idef_generated_tcg_c = custom_target( 335 'copy', 336 input: idef_generated_tcg[0], 337 output: 'idef-generated-emitter.indented.c', 338 command: ['cp', '@INPUT@', '@OUTPUT@'] 339 ) 340 endif 341 342 idef_generated_list = idef_generated_tcg[2].full_path() 343 344 hexagon_ss.add(idef_generated_tcg_c) 345 346 # Setup input and dependencies for the next step, this depends on whether or 347 # not idef-parser is enabled 348 helper_dep = [semantics_generated, idef_generated_tcg_c, idef_generated_tcg] 349 helper_in = [semantics_generated, gen_tcg_h, gen_tcg_hvx_h, idef_generated_list] 350else 351 # Setup input and dependencies for the next step, this depends on whether or 352 # not idef-parser is enabled 353 helper_dep = [semantics_generated] 354 helper_in = [semantics_generated, gen_tcg_h, gen_tcg_hvx_h] 355endif 356 357# 358# Step 5 359# We use Python scripts to generate the following files 360# helper_protos_generated.h.inc 361# helper_funcs_generated.c.inc 362# tcg_funcs_generated.c.inc 363# 364helper_protos_generated = custom_target( 365 'helper_protos_generated.h.inc', 366 output: 'helper_protos_generated.h.inc', 367 depends: helper_dep, 368 depend_files: [hex_common_py, gen_tcg_h, gen_tcg_hvx_h], 369 command: [python, files('gen_helper_protos.py'), helper_in, '@OUTPUT@'], 370) 371hexagon_ss.add(helper_protos_generated) 372 373helper_funcs_generated = custom_target( 374 'helper_funcs_generated.c.inc', 375 output: 'helper_funcs_generated.c.inc', 376 depends: helper_dep, 377 depend_files: [hex_common_py, gen_tcg_h, gen_tcg_hvx_h], 378 command: [python, files('gen_helper_funcs.py'), helper_in, '@OUTPUT@'], 379) 380hexagon_ss.add(helper_funcs_generated) 381 382tcg_funcs_generated = custom_target( 383 'tcg_funcs_generated.c.inc', 384 output: 'tcg_funcs_generated.c.inc', 385 depends: helper_dep, 386 depend_files: [hex_common_py, gen_tcg_h, gen_tcg_hvx_h], 387 command: [python, files('gen_tcg_funcs.py'), helper_in, '@OUTPUT@'], 388) 389hexagon_ss.add(tcg_funcs_generated) 390 391analyze_funcs_generated = custom_target( 392 'analyze_funcs_generated.c.inc', 393 output: 'analyze_funcs_generated.c.inc', 394 depends: helper_dep, 395 depend_files: [hex_common_py, gen_tcg_h, gen_tcg_hvx_h], 396 command: [python, files('gen_analyze_funcs.py'), helper_in, '@OUTPUT@'], 397) 398hexagon_ss.add(analyze_funcs_generated) 399 400target_arch += {'hexagon': hexagon_ss} 401