1#!/usr/bin/env python3 2 3## 4## Copyright(c) 2019-2022 Qualcomm Innovation Center, Inc. All Rights Reserved. 5## 6## This program is free software; you can redistribute it and/or modify 7## it under the terms of the GNU General Public License as published by 8## the Free Software Foundation; either version 2 of the License, or 9## (at your option) any later version. 10## 11## This program is distributed in the hope that it will be useful, 12## but WITHOUT ANY WARRANTY; without even the implied warranty of 13## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14## GNU General Public License for more details. 15## 16## You should have received a copy of the GNU General Public License 17## along with this program; if not, see <http://www.gnu.org/licenses/>. 18## 19 20import sys 21import re 22import string 23import hex_common 24 25## 26## Helpers for gen_tcg_func 27## 28def gen_decl_ea_tcg(f, tag): 29 f.write(" TCGv EA G_GNUC_UNUSED = tcg_temp_new();\n") 30 31def genptr_decl_pair_writable(f, tag, regtype, regid, regno): 32 regN="%s%sN" % (regtype,regid) 33 f.write(" TCGv_i64 %s%sV = tcg_temp_new_i64();\n" % \ 34 (regtype, regid)) 35 if (regtype == "C"): 36 f.write(" const int %s = insn->regno[%d] + HEX_REG_SA0;\n" % \ 37 (regN, regno)) 38 else: 39 f.write(" const int %s = insn->regno[%d];\n" % (regN, regno)) 40 if ('A_CONDEXEC' in hex_common.attribdict[tag]): 41 f.write(" if (!is_preloaded(ctx, %s)) {\n" % regN) 42 f.write(" tcg_gen_mov_tl(hex_new_value[%s], hex_gpr[%s]);\n" % \ 43 (regN, regN)) 44 f.write(" }\n") 45 f.write(" if (!is_preloaded(ctx, %s + 1)) {\n" % regN) 46 f.write(" tcg_gen_mov_tl(hex_new_value[%s + 1], hex_gpr[%s + 1]);\n" % \ 47 (regN, regN)) 48 f.write(" }\n") 49 50def genptr_decl_writable(f, tag, regtype, regid, regno): 51 regN="%s%sN" % (regtype,regid) 52 f.write(" TCGv %s%sV = tcg_temp_new();\n" % \ 53 (regtype, regid)) 54 if (regtype == "C"): 55 f.write(" const int %s = insn->regno[%d] + HEX_REG_SA0;\n" % \ 56 (regN, regno)) 57 else: 58 f.write(" const int %s = insn->regno[%d];\n" % (regN, regno)) 59 if ('A_CONDEXEC' in hex_common.attribdict[tag]): 60 f.write(" if (!is_preloaded(ctx, %s)) {\n" % regN) 61 f.write(" tcg_gen_mov_tl(hex_new_value[%s], hex_gpr[%s]);\n" % \ 62 (regN, regN)) 63 f.write(" }\n") 64 65def genptr_decl(f, tag, regtype, regid, regno): 66 regN="%s%sN" % (regtype,regid) 67 if (regtype == "R"): 68 if (regid in {"ss", "tt"}): 69 f.write(" TCGv_i64 %s%sV = tcg_temp_new_i64();\n" % \ 70 (regtype, regid)) 71 f.write(" const int %s = insn->regno[%d];\n" % \ 72 (regN, regno)) 73 elif (regid in {"dd", "ee", "xx", "yy"}): 74 genptr_decl_pair_writable(f, tag, regtype, regid, regno) 75 elif (regid in {"s", "t", "u", "v"}): 76 f.write(" TCGv %s%sV = hex_gpr[insn->regno[%d]];\n" % \ 77 (regtype, regid, regno)) 78 elif (regid in {"d", "e", "x", "y"}): 79 genptr_decl_writable(f, tag, regtype, regid, regno) 80 else: 81 print("Bad register parse: ", regtype, regid) 82 elif (regtype == "P"): 83 if (regid in {"s", "t", "u", "v"}): 84 f.write(" TCGv %s%sV = hex_pred[insn->regno[%d]];\n" % \ 85 (regtype, regid, regno)) 86 elif (regid in {"d", "e", "x"}): 87 genptr_decl_writable(f, tag, regtype, regid, regno) 88 else: 89 print("Bad register parse: ", regtype, regid) 90 elif (regtype == "C"): 91 if (regid == "ss"): 92 f.write(" TCGv_i64 %s%sV = tcg_temp_new_i64();\n" % \ 93 (regtype, regid)) 94 f.write(" const int %s = insn->regno[%d] + HEX_REG_SA0;\n" % \ 95 (regN, regno)) 96 elif (regid == "dd"): 97 genptr_decl_pair_writable(f, tag, regtype, regid, regno) 98 elif (regid == "s"): 99 f.write(" TCGv %s%sV = tcg_temp_new();\n" % \ 100 (regtype, regid)) 101 f.write(" const int %s%sN = insn->regno[%d] + HEX_REG_SA0;\n" % \ 102 (regtype, regid, regno)) 103 elif (regid == "d"): 104 genptr_decl_writable(f, tag, regtype, regid, regno) 105 else: 106 print("Bad register parse: ", regtype, regid) 107 elif (regtype == "M"): 108 if (regid == "u"): 109 f.write(" const int %s%sN = insn->regno[%d];\n"% \ 110 (regtype, regid, regno)) 111 f.write(" TCGv %s%sV = hex_gpr[%s%sN + HEX_REG_M0];\n" % \ 112 (regtype, regid, regtype, regid)) 113 else: 114 print("Bad register parse: ", regtype, regid) 115 elif (regtype == "V"): 116 if (regid in {"dd"}): 117 f.write(" const int %s%sN = insn->regno[%d];\n" %\ 118 (regtype, regid, regno)) 119 f.write(" const intptr_t %s%sV_off =\n" %\ 120 (regtype, regid)) 121 if (hex_common.is_tmp_result(tag)): 122 f.write(" ctx_tmp_vreg_off(ctx, %s%sN, 2, true);\n" % \ 123 (regtype, regid)) 124 else: 125 f.write(" ctx_future_vreg_off(ctx, %s%sN," % \ 126 (regtype, regid)) 127 f.write(" 2, true);\n") 128 if (not hex_common.skip_qemu_helper(tag)): 129 f.write(" TCGv_ptr %s%sV = tcg_temp_new_ptr();\n" % \ 130 (regtype, regid)) 131 f.write(" tcg_gen_addi_ptr(%s%sV, cpu_env, %s%sV_off);\n" % \ 132 (regtype, regid, regtype, regid)) 133 elif (regid in {"uu", "vv", "xx"}): 134 f.write(" const int %s%sN = insn->regno[%d];\n" % \ 135 (regtype, regid, regno)) 136 f.write(" const intptr_t %s%sV_off =\n" % \ 137 (regtype, regid)) 138 f.write(" offsetof(CPUHexagonState, %s%sV);\n" % \ 139 (regtype, regid)) 140 if (not hex_common.skip_qemu_helper(tag)): 141 f.write(" TCGv_ptr %s%sV = tcg_temp_new_ptr();\n" % \ 142 (regtype, regid)) 143 f.write(" tcg_gen_addi_ptr(%s%sV, cpu_env, %s%sV_off);\n" % \ 144 (regtype, regid, regtype, regid)) 145 elif (regid in {"s", "u", "v", "w"}): 146 f.write(" const int %s%sN = insn->regno[%d];\n" % \ 147 (regtype, regid, regno)) 148 f.write(" const intptr_t %s%sV_off =\n" % \ 149 (regtype, regid)) 150 f.write(" vreg_src_off(ctx, %s%sN);\n" % \ 151 (regtype, regid)) 152 if (not hex_common.skip_qemu_helper(tag)): 153 f.write(" TCGv_ptr %s%sV = tcg_temp_new_ptr();\n" % \ 154 (regtype, regid)) 155 elif (regid in {"d", "x", "y"}): 156 f.write(" const int %s%sN = insn->regno[%d];\n" % \ 157 (regtype, regid, regno)) 158 f.write(" const intptr_t %s%sV_off =\n" % \ 159 (regtype, regid)) 160 if (regid == "y"): 161 f.write(" offsetof(CPUHexagonState, vtmp);\n") 162 elif (hex_common.is_tmp_result(tag)): 163 f.write(" ctx_tmp_vreg_off(ctx, %s%sN, 1, true);\n" % \ 164 (regtype, regid)) 165 else: 166 f.write(" ctx_future_vreg_off(ctx, %s%sN," % \ 167 (regtype, regid)) 168 f.write(" 1, true);\n"); 169 if 'A_CONDEXEC' in hex_common.attribdict[tag]: 170 f.write(" if (!is_vreg_preloaded(ctx, %s)) {\n" % (regN)) 171 f.write(" intptr_t src_off =") 172 f.write(" offsetof(CPUHexagonState, VRegs[%s%sN]);\n"% \ 173 (regtype, regid)) 174 f.write(" tcg_gen_gvec_mov(MO_64, %s%sV_off,\n" % \ 175 (regtype, regid)) 176 f.write(" src_off,\n") 177 f.write(" sizeof(MMVector),\n") 178 f.write(" sizeof(MMVector));\n") 179 f.write(" }\n") 180 181 if (not hex_common.skip_qemu_helper(tag)): 182 f.write(" TCGv_ptr %s%sV = tcg_temp_new_ptr();\n" % \ 183 (regtype, regid)) 184 f.write(" tcg_gen_addi_ptr(%s%sV, cpu_env, %s%sV_off);\n" % \ 185 (regtype, regid, regtype, regid)) 186 else: 187 print("Bad register parse: ", regtype, regid) 188 elif (regtype == "Q"): 189 if (regid in {"d", "e", "x"}): 190 f.write(" const int %s%sN = insn->regno[%d];\n" % \ 191 (regtype, regid, regno)) 192 f.write(" const intptr_t %s%sV_off =\n" % \ 193 (regtype, regid)) 194 f.write(" offsetof(CPUHexagonState,\n") 195 f.write(" future_QRegs[%s%sN]);\n" % \ 196 (regtype, regid)) 197 if (not hex_common.skip_qemu_helper(tag)): 198 f.write(" TCGv_ptr %s%sV = tcg_temp_new_ptr();\n" % \ 199 (regtype, regid)) 200 f.write(" tcg_gen_addi_ptr(%s%sV, cpu_env, %s%sV_off);\n" % \ 201 (regtype, regid, regtype, regid)) 202 elif (regid in {"s", "t", "u", "v"}): 203 f.write(" const int %s%sN = insn->regno[%d];\n" % \ 204 (regtype, regid, regno)) 205 f.write(" const intptr_t %s%sV_off =\n" %\ 206 (regtype, regid)) 207 f.write(" offsetof(CPUHexagonState, QRegs[%s%sN]);\n" % \ 208 (regtype, regid)) 209 if (not hex_common.skip_qemu_helper(tag)): 210 f.write(" TCGv_ptr %s%sV = tcg_temp_new_ptr();\n" % \ 211 (regtype, regid)) 212 else: 213 print("Bad register parse: ", regtype, regid) 214 else: 215 print("Bad register parse: ", regtype, regid) 216 217def genptr_decl_new(f, tag, regtype, regid, regno): 218 if (regtype == "N"): 219 if (regid in {"s", "t"}): 220 f.write(" TCGv %s%sN = hex_new_value[insn->regno[%d]];\n" % \ 221 (regtype, regid, regno)) 222 else: 223 print("Bad register parse: ", regtype, regid) 224 elif (regtype == "P"): 225 if (regid in {"t", "u", "v"}): 226 f.write(" TCGv %s%sN = hex_new_pred_value[insn->regno[%d]];\n" % \ 227 (regtype, regid, regno)) 228 else: 229 print("Bad register parse: ", regtype, regid) 230 elif (regtype == "O"): 231 if (regid == "s"): 232 f.write(" const intptr_t %s%sN_num = insn->regno[%d];\n" % \ 233 (regtype, regid, regno)) 234 if (hex_common.skip_qemu_helper(tag)): 235 f.write(" const intptr_t %s%sN_off =\n" % \ 236 (regtype, regid)) 237 f.write(" ctx_future_vreg_off(ctx, %s%sN_num," % \ 238 (regtype, regid)) 239 f.write(" 1, true);\n") 240 else: 241 f.write(" TCGv %s%sN = tcg_constant_tl(%s%sN_num);\n" % \ 242 (regtype, regid, regtype, regid)) 243 else: 244 print("Bad register parse: ", regtype, regid) 245 else: 246 print("Bad register parse: ", regtype, regid) 247 248def genptr_decl_opn(f, tag, regtype, regid, toss, numregs, i): 249 if (hex_common.is_pair(regid)): 250 genptr_decl(f, tag, regtype, regid, i) 251 elif (hex_common.is_single(regid)): 252 if hex_common.is_old_val(regtype, regid, tag): 253 genptr_decl(f,tag, regtype, regid, i) 254 elif hex_common.is_new_val(regtype, regid, tag): 255 genptr_decl_new(f, tag, regtype, regid, i) 256 else: 257 print("Bad register parse: ",regtype,regid,toss,numregs) 258 else: 259 print("Bad register parse: ",regtype,regid,toss,numregs) 260 261def genptr_decl_imm(f,immlett): 262 if (immlett.isupper()): 263 i = 1 264 else: 265 i = 0 266 f.write(" int %s = insn->immed[%d];\n" % \ 267 (hex_common.imm_name(immlett), i)) 268 269def genptr_src_read(f, tag, regtype, regid): 270 if (regtype == "R"): 271 if (regid in {"ss", "tt", "xx", "yy"}): 272 f.write(" tcg_gen_concat_i32_i64(%s%sV, hex_gpr[%s%sN],\n" % \ 273 (regtype, regid, regtype, regid)) 274 f.write(" hex_gpr[%s%sN + 1]);\n" % \ 275 (regtype, regid)) 276 elif (regid in {"x", "y"}): 277 f.write(" tcg_gen_mov_tl(%s%sV, hex_gpr[%s%sN]);\n" % \ 278 (regtype,regid,regtype,regid)) 279 elif (regid not in {"s", "t", "u", "v"}): 280 print("Bad register parse: ", regtype, regid) 281 elif (regtype == "P"): 282 if (regid == "x"): 283 f.write(" tcg_gen_mov_tl(%s%sV, hex_pred[%s%sN]);\n" % \ 284 (regtype, regid, regtype, regid)) 285 elif (regid not in {"s", "t", "u", "v"}): 286 print("Bad register parse: ", regtype, regid) 287 elif (regtype == "C"): 288 if (regid == "ss"): 289 f.write(" gen_read_ctrl_reg_pair(ctx, %s%sN, %s%sV);\n" % \ 290 (regtype, regid, regtype, regid)) 291 elif (regid == "s"): 292 f.write(" gen_read_ctrl_reg(ctx, %s%sN, %s%sV);\n" % \ 293 (regtype, regid, regtype, regid)) 294 else: 295 print("Bad register parse: ", regtype, regid) 296 elif (regtype == "M"): 297 if (regid != "u"): 298 print("Bad register parse: ", regtype, regid) 299 elif (regtype == "V"): 300 if (regid in {"uu", "vv", "xx"}): 301 f.write(" tcg_gen_gvec_mov(MO_64, %s%sV_off,\n" % \ 302 (regtype, regid)) 303 f.write(" vreg_src_off(ctx, %s%sN),\n" % \ 304 (regtype, regid)) 305 f.write(" sizeof(MMVector), sizeof(MMVector));\n") 306 f.write(" tcg_gen_gvec_mov(MO_64,\n") 307 f.write(" %s%sV_off + sizeof(MMVector),\n" % \ 308 (regtype, regid)) 309 f.write(" vreg_src_off(ctx, %s%sN ^ 1),\n" % \ 310 (regtype, regid)) 311 f.write(" sizeof(MMVector), sizeof(MMVector));\n") 312 elif (regid in {"s", "u", "v", "w"}): 313 if (not hex_common.skip_qemu_helper(tag)): 314 f.write(" tcg_gen_addi_ptr(%s%sV, cpu_env, %s%sV_off);\n" % \ 315 (regtype, regid, regtype, regid)) 316 elif (regid in {"x", "y"}): 317 f.write(" tcg_gen_gvec_mov(MO_64, %s%sV_off,\n" % \ 318 (regtype, regid)) 319 f.write(" vreg_src_off(ctx, %s%sN),\n" % \ 320 (regtype, regid)) 321 f.write(" sizeof(MMVector), sizeof(MMVector));\n") 322 else: 323 print("Bad register parse: ", regtype, regid) 324 elif (regtype == "Q"): 325 if (regid in {"s", "t", "u", "v"}): 326 if (not hex_common.skip_qemu_helper(tag)): 327 f.write(" tcg_gen_addi_ptr(%s%sV, cpu_env, %s%sV_off);\n" % \ 328 (regtype, regid, regtype, regid)) 329 elif (regid in {"x"}): 330 f.write(" tcg_gen_gvec_mov(MO_64, %s%sV_off,\n" % \ 331 (regtype, regid)) 332 f.write(" offsetof(CPUHexagonState, QRegs[%s%sN]),\n" % \ 333 (regtype, regid)) 334 f.write(" sizeof(MMQReg), sizeof(MMQReg));\n") 335 else: 336 print("Bad register parse: ", regtype, regid) 337 else: 338 print("Bad register parse: ", regtype, regid) 339 340def genptr_src_read_new(f,regtype,regid): 341 if (regtype == "N"): 342 if (regid not in {"s", "t"}): 343 print("Bad register parse: ", regtype, regid) 344 elif (regtype == "P"): 345 if (regid not in {"t", "u", "v"}): 346 print("Bad register parse: ", regtype, regid) 347 elif (regtype == "O"): 348 if (regid != "s"): 349 print("Bad register parse: ", regtype, regid) 350 else: 351 print("Bad register parse: ", regtype, regid) 352 353def genptr_src_read_opn(f,regtype,regid,tag): 354 if (hex_common.is_pair(regid)): 355 genptr_src_read(f, tag, regtype, regid) 356 elif (hex_common.is_single(regid)): 357 if hex_common.is_old_val(regtype, regid, tag): 358 genptr_src_read(f, tag, regtype, regid) 359 elif hex_common.is_new_val(regtype, regid, tag): 360 genptr_src_read_new(f,regtype,regid) 361 else: 362 print("Bad register parse: ",regtype,regid,toss,numregs) 363 else: 364 print("Bad register parse: ",regtype,regid,toss,numregs) 365 366def gen_helper_call_opn(f, tag, regtype, regid, toss, numregs, i): 367 if (i > 0): f.write(", ") 368 if (hex_common.is_pair(regid)): 369 f.write("%s%sV" % (regtype,regid)) 370 elif (hex_common.is_single(regid)): 371 if hex_common.is_old_val(regtype, regid, tag): 372 f.write("%s%sV" % (regtype,regid)) 373 elif hex_common.is_new_val(regtype, regid, tag): 374 f.write("%s%sN" % (regtype,regid)) 375 else: 376 print("Bad register parse: ",regtype,regid,toss,numregs) 377 else: 378 print("Bad register parse: ",regtype,regid,toss,numregs) 379 380def gen_helper_decl_imm(f,immlett): 381 f.write(" TCGv tcgv_%s = tcg_constant_tl(%s);\n" % \ 382 (hex_common.imm_name(immlett), hex_common.imm_name(immlett))) 383 384def gen_helper_call_imm(f,immlett): 385 f.write(", tcgv_%s" % hex_common.imm_name(immlett)) 386 387def genptr_dst_write_pair(f, tag, regtype, regid): 388 if ('A_CONDEXEC' in hex_common.attribdict[tag]): 389 f.write(" gen_log_predicated_reg_write_pair(%s%sN, %s%sV, insn->slot);\n" % \ 390 (regtype, regid, regtype, regid)) 391 else: 392 f.write(" gen_log_reg_write_pair(%s%sN, %s%sV);\n" % \ 393 (regtype, regid, regtype, regid)) 394 f.write(" ctx_log_reg_write_pair(ctx, %s%sN);\n" % \ 395 (regtype, regid)) 396 397def genptr_dst_write(f, tag, regtype, regid): 398 if (regtype == "R"): 399 if (regid in {"dd", "xx", "yy"}): 400 genptr_dst_write_pair(f, tag, regtype, regid) 401 elif (regid in {"d", "e", "x", "y"}): 402 if ('A_CONDEXEC' in hex_common.attribdict[tag]): 403 f.write(" gen_log_predicated_reg_write(%s%sN, %s%sV,\n" % \ 404 (regtype, regid, regtype, regid)) 405 f.write(" insn->slot);\n") 406 else: 407 f.write(" gen_log_reg_write(%s%sN, %s%sV);\n" % \ 408 (regtype, regid, regtype, regid)) 409 f.write(" ctx_log_reg_write(ctx, %s%sN);\n" % \ 410 (regtype, regid)) 411 else: 412 print("Bad register parse: ", regtype, regid) 413 elif (regtype == "P"): 414 if (regid in {"d", "e", "x"}): 415 f.write(" gen_log_pred_write(ctx, %s%sN, %s%sV);\n" % \ 416 (regtype, regid, regtype, regid)) 417 f.write(" ctx_log_pred_write(ctx, %s%sN);\n" % \ 418 (regtype, regid)) 419 else: 420 print("Bad register parse: ", regtype, regid) 421 elif (regtype == "C"): 422 if (regid == "dd"): 423 f.write(" gen_write_ctrl_reg_pair(ctx, %s%sN, %s%sV);\n" % \ 424 (regtype, regid, regtype, regid)) 425 elif (regid == "d"): 426 f.write(" gen_write_ctrl_reg(ctx, %s%sN, %s%sV);\n" % \ 427 (regtype, regid, regtype, regid)) 428 else: 429 print("Bad register parse: ", regtype, regid) 430 else: 431 print("Bad register parse: ", regtype, regid) 432 433def genptr_dst_write_ext(f, tag, regtype, regid, newv="EXT_DFL"): 434 if (regtype == "V"): 435 if (regid in {"dd", "xx", "yy"}): 436 if ('A_CONDEXEC' in hex_common.attribdict[tag]): 437 is_predicated = "true" 438 else: 439 is_predicated = "false" 440 f.write(" gen_log_vreg_write_pair(ctx, %s%sV_off, %s%sN, " % \ 441 (regtype, regid, regtype, regid)) 442 f.write("%s, insn->slot, %s);\n" % \ 443 (newv, is_predicated)) 444 f.write(" ctx_log_vreg_write_pair(ctx, %s%sN, %s,\n" % \ 445 (regtype, regid, newv)) 446 f.write(" %s);\n" % (is_predicated)) 447 elif (regid in {"d", "x", "y"}): 448 if ('A_CONDEXEC' in hex_common.attribdict[tag]): 449 is_predicated = "true" 450 else: 451 is_predicated = "false" 452 f.write(" gen_log_vreg_write(ctx, %s%sV_off, %s%sN, %s, " % \ 453 (regtype, regid, regtype, regid, newv)) 454 f.write("insn->slot, %s);\n" % \ 455 (is_predicated)) 456 f.write(" ctx_log_vreg_write(ctx, %s%sN, %s, %s);\n" % \ 457 (regtype, regid, newv, is_predicated)) 458 else: 459 print("Bad register parse: ", regtype, regid) 460 elif (regtype == "Q"): 461 if (regid in {"d", "e", "x"}): 462 if ('A_CONDEXEC' in hex_common.attribdict[tag]): 463 is_predicated = "true" 464 else: 465 is_predicated = "false" 466 f.write(" gen_log_qreg_write(%s%sV_off, %s%sN, %s, " % \ 467 (regtype, regid, regtype, regid, newv)) 468 f.write("insn->slot, %s);\n" % (is_predicated)) 469 f.write(" ctx_log_qreg_write(ctx, %s%sN, %s);\n" % \ 470 (regtype, regid, is_predicated)) 471 else: 472 print("Bad register parse: ", regtype, regid) 473 else: 474 print("Bad register parse: ", regtype, regid) 475 476def genptr_dst_write_opn(f,regtype, regid, tag): 477 if (hex_common.is_pair(regid)): 478 if (hex_common.is_hvx_reg(regtype)): 479 if (hex_common.is_tmp_result(tag)): 480 genptr_dst_write_ext(f, tag, regtype, regid, "EXT_TMP") 481 else: 482 genptr_dst_write_ext(f, tag, regtype, regid) 483 else: 484 genptr_dst_write(f, tag, regtype, regid) 485 elif (hex_common.is_single(regid)): 486 if (hex_common.is_hvx_reg(regtype)): 487 if (hex_common.is_new_result(tag)): 488 genptr_dst_write_ext(f, tag, regtype, regid, "EXT_NEW") 489 elif (hex_common.is_tmp_result(tag)): 490 genptr_dst_write_ext(f, tag, regtype, regid, "EXT_TMP") 491 else: 492 genptr_dst_write_ext(f, tag, regtype, regid, "EXT_DFL") 493 else: 494 genptr_dst_write(f, tag, regtype, regid) 495 else: 496 print("Bad register parse: ",regtype,regid,toss,numregs) 497 498## 499## Generate the TCG code to call the helper 500## For A2_add: Rd32=add(Rs32,Rt32), { RdV=RsV+RtV;} 501## We produce: 502## static void generate_A2_add(DisasContext *ctx) 503## { 504## TCGv RdV = tcg_temp_new(); 505## const int RdN = insn->regno[0]; 506## TCGv RsV = hex_gpr[insn->regno[1]]; 507## TCGv RtV = hex_gpr[insn->regno[2]]; 508## <GEN> 509## gen_log_reg_write(RdN, RdV); 510## ctx_log_reg_write(ctx, RdN); 511## } 512## 513## where <GEN> depends on hex_common.skip_qemu_helper(tag) 514## if hex_common.skip_qemu_helper(tag) is True 515## <GEN> is fGEN_TCG_A2_add({ RdV=RsV+RtV;}); 516## if hex_common.skip_qemu_helper(tag) is False 517## <GEN> is gen_helper_A2_add(RdV, cpu_env, RsV, RtV); 518## 519def gen_tcg_func(f, tag, regs, imms): 520 f.write("static void generate_%s(DisasContext *ctx)\n" %tag) 521 f.write('{\n') 522 523 f.write(" Insn *insn __attribute__((unused)) = ctx->insn;\n") 524 525 if hex_common.need_ea(tag): gen_decl_ea_tcg(f, tag) 526 i=0 527 ## Declare all the operands (regs and immediates) 528 for regtype,regid,toss,numregs in regs: 529 genptr_decl_opn(f, tag, regtype, regid, toss, numregs, i) 530 i += 1 531 for immlett,bits,immshift in imms: 532 genptr_decl_imm(f,immlett) 533 534 if 'A_PRIV' in hex_common.attribdict[tag]: 535 f.write(' fCHECKFORPRIV();\n') 536 if 'A_GUEST' in hex_common.attribdict[tag]: 537 f.write(' fCHECKFORGUEST();\n') 538 539 ## Read all the inputs 540 for regtype,regid,toss,numregs in regs: 541 if (hex_common.is_read(regid)): 542 genptr_src_read_opn(f,regtype,regid,tag) 543 544 if hex_common.is_idef_parser_enabled(tag): 545 declared = [] 546 ## Handle registers 547 for regtype,regid,toss,numregs in regs: 548 if (hex_common.is_pair(regid) 549 or (hex_common.is_single(regid) 550 and hex_common.is_old_val(regtype, regid, tag))): 551 declared.append("%s%sV" % (regtype, regid)) 552 if regtype == "M": 553 declared.append("%s%sN" % (regtype, regid)) 554 elif hex_common.is_new_val(regtype, regid, tag): 555 declared.append("%s%sN" % (regtype,regid)) 556 else: 557 print("Bad register parse: ",regtype,regid,toss,numregs) 558 559 ## Handle immediates 560 for immlett,bits,immshift in imms: 561 declared.append(hex_common.imm_name(immlett)) 562 563 arguments = ", ".join(["ctx", "ctx->insn", "ctx->pkt"] + declared) 564 f.write(" emit_%s(%s);\n" % (tag, arguments)) 565 566 elif ( hex_common.skip_qemu_helper(tag) ): 567 f.write(" fGEN_TCG_%s(%s);\n" % (tag, hex_common.semdict[tag])) 568 else: 569 ## Generate the call to the helper 570 for immlett,bits,immshift in imms: 571 gen_helper_decl_imm(f,immlett) 572 if hex_common.need_pkt_has_multi_cof(tag): 573 f.write(" TCGv pkt_has_multi_cof = ") 574 f.write("tcg_constant_tl(ctx->pkt->pkt_has_multi_cof);\n") 575 if hex_common.need_part1(tag): 576 f.write(" TCGv part1 = tcg_constant_tl(insn->part1);\n") 577 if hex_common.need_slot(tag): 578 f.write(" TCGv slot = tcg_constant_tl(insn->slot);\n") 579 if hex_common.need_PC(tag): 580 f.write(" TCGv PC = tcg_constant_tl(ctx->pkt->pc);\n") 581 if hex_common.helper_needs_next_PC(tag): 582 f.write(" TCGv next_PC = tcg_constant_tl(ctx->next_PC);\n") 583 f.write(" gen_helper_%s(" % (tag)) 584 i=0 585 ## If there is a scalar result, it is the return type 586 for regtype,regid,toss,numregs in regs: 587 if (hex_common.is_written(regid)): 588 if (hex_common.is_hvx_reg(regtype)): 589 continue 590 gen_helper_call_opn(f, tag, regtype, regid, toss, numregs, i) 591 i += 1 592 if (i > 0): f.write(", ") 593 f.write("cpu_env") 594 i=1 595 for regtype,regid,toss,numregs in regs: 596 if (hex_common.is_written(regid)): 597 if (not hex_common.is_hvx_reg(regtype)): 598 continue 599 gen_helper_call_opn(f, tag, regtype, regid, toss, numregs, i) 600 i += 1 601 for regtype,regid,toss,numregs in regs: 602 if (hex_common.is_read(regid)): 603 if (hex_common.is_hvx_reg(regtype) and 604 hex_common.is_readwrite(regid)): 605 continue 606 gen_helper_call_opn(f, tag, regtype, regid, toss, numregs, i) 607 i += 1 608 for immlett,bits,immshift in imms: 609 gen_helper_call_imm(f,immlett) 610 611 if hex_common.need_pkt_has_multi_cof(tag): 612 f.write(", pkt_has_multi_cof") 613 if hex_common.need_PC(tag): f.write(", PC") 614 if hex_common.helper_needs_next_PC(tag): f.write(", next_PC") 615 if hex_common.need_slot(tag): f.write(", slot") 616 if hex_common.need_part1(tag): f.write(", part1" ) 617 f.write(");\n") 618 619 ## Write all the outputs 620 for regtype,regid,toss,numregs in regs: 621 if (hex_common.is_written(regid)): 622 genptr_dst_write_opn(f,regtype, regid, tag) 623 624 f.write("}\n\n") 625 626def gen_def_tcg_func(f, tag, tagregs, tagimms): 627 regs = tagregs[tag] 628 imms = tagimms[tag] 629 630 gen_tcg_func(f, tag, regs, imms) 631 632def main(): 633 hex_common.read_semantics_file(sys.argv[1]) 634 hex_common.read_attribs_file(sys.argv[2]) 635 hex_common.read_overrides_file(sys.argv[3]) 636 hex_common.read_overrides_file(sys.argv[4]) 637 hex_common.calculate_attribs() 638 ## Whether or not idef-parser is enabled is 639 ## determined by the number of arguments to 640 ## this script: 641 ## 642 ## 5 args. -> not enabled, 643 ## 6 args. -> idef-parser enabled. 644 ## 645 ## The 6:th arg. then holds a list of the successfully 646 ## parsed instructions. 647 is_idef_parser_enabled = len(sys.argv) > 6 648 if is_idef_parser_enabled: 649 hex_common.read_idef_parser_enabled_file(sys.argv[5]) 650 tagregs = hex_common.get_tagregs() 651 tagimms = hex_common.get_tagimms() 652 653 output_file = sys.argv[-1] 654 with open(output_file, 'w') as f: 655 f.write("#ifndef HEXAGON_TCG_FUNCS_H\n") 656 f.write("#define HEXAGON_TCG_FUNCS_H\n\n") 657 if is_idef_parser_enabled: 658 f.write("#include \"idef-generated-emitter.h.inc\"\n\n") 659 660 for tag in hex_common.tags: 661 ## Skip the priv instructions 662 if ( "A_PRIV" in hex_common.attribdict[tag] ) : 663 continue 664 ## Skip the guest instructions 665 if ( "A_GUEST" in hex_common.attribdict[tag] ) : 666 continue 667 ## Skip the diag instructions 668 if ( tag == "Y6_diag" ) : 669 continue 670 if ( tag == "Y6_diag0" ) : 671 continue 672 if ( tag == "Y6_diag1" ) : 673 continue 674 675 gen_def_tcg_func(f, tag, tagregs, tagimms) 676 677 f.write("#endif /* HEXAGON_TCG_FUNCS_H */\n") 678 679if __name__ == "__main__": 680 main() 681