1 /* -*- mode: C; c-basic-offset: 3; -*- */ 2 3 /*---------------------------------------------------------------*/ 4 /*--- begin guest_s390_toIR.c ---*/ 5 /*---------------------------------------------------------------*/ 6 7 /* 8 This file is part of Valgrind, a dynamic binary instrumentation 9 framework. 10 11 Copyright IBM Corp. 2010-2017 12 13 This program is free software; you can redistribute it and/or 14 modify it under the terms of the GNU General Public License as 15 published by the Free Software Foundation; either version 2 of the 16 License, or (at your option) any later version. 17 18 This program is distributed in the hope that it will be useful, but 19 WITHOUT ANY WARRANTY; without even the implied warranty of 20 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 21 General Public License for more details. 22 23 You should have received a copy of the GNU General Public License 24 along with this program; if not, write to the Free Software 25 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 26 02110-1301, USA. 27 28 The GNU General Public License is contained in the file COPYING. 29 */ 30 31 /* Contributed by Florian Krohm and Christian Borntraeger */ 32 33 /* Translates s390 code to IR. */ 34 35 #include "libvex_basictypes.h" 36 #include "libvex_ir.h" 37 #include "libvex_emnote.h" 38 #include "libvex_s390x_common.h" 39 #include "main_util.h" /* vassert */ 40 #include "main_globals.h" /* vex_traceflags */ 41 #include "guest_generic_bb_to_IR.h" /* DisResult */ 42 #include "guest_s390_defs.h" /* prototypes for this file's functions */ 43 #include "s390_disasm.h" 44 #include "s390_defs.h" /* S390_BFP_ROUND_xyzzy */ 45 #include "host_s390_defs.h" /* s390_host_has_xyzzy */ 46 47 48 /*------------------------------------------------------------*/ 49 /*--- Forward declarations ---*/ 50 /*------------------------------------------------------------*/ 51 static UInt s390_decode_and_irgen(const UChar *, UInt, DisResult *); 52 static void s390_irgen_xonc(IROp, IRTemp, IRTemp, IRTemp); 53 static void s390_irgen_CLC_EX(IRTemp, IRTemp, IRTemp); 54 55 56 /*------------------------------------------------------------*/ 57 /*--- Globals ---*/ 58 /*------------------------------------------------------------*/ 59 60 /* The IRSB* into which we're generating code. */ 61 static IRSB *irsb; 62 63 /* The guest address for the instruction currently being 64 translated. */ 65 static Addr64 guest_IA_curr_instr; 66 67 /* The guest address for the instruction following the current instruction. */ 68 static Addr64 guest_IA_next_instr; 69 70 /* Result of disassembly step. */ 71 static DisResult *dis_res; 72 73 /* Resteer function and callback data */ 74 static Bool (*resteer_fn)(void *, Addr); 75 static void *resteer_data; 76 77 /* Whether to print diagnostics for illegal instructions. */ 78 static Bool sigill_diag; 79 80 /* The last seen execute target instruction */ 81 ULong last_execute_target; 82 83 /* The possible outcomes of a decoding operation */ 84 typedef enum { 85 S390_DECODE_OK, 86 S390_DECODE_UNKNOWN_INSN, 87 S390_DECODE_UNIMPLEMENTED_INSN, 88 S390_DECODE_UNKNOWN_SPECIAL_INSN, 89 S390_DECODE_ERROR 90 } s390_decode_t; 91 92 93 /*------------------------------------------------------------*/ 94 /*--- Helpers for constructing IR. ---*/ 95 /*------------------------------------------------------------*/ 96 97 /* Add a statement to the current irsb. */ 98 static __inline__ void 99 stmt(IRStmt *st) 100 { 101 addStmtToIRSB(irsb, st); 102 } 103 104 /* Allocate a new temporary of the given type. */ 105 static __inline__ IRTemp 106 newTemp(IRType type) 107 { 108 vassert(isPlausibleIRType(type)); 109 110 return newIRTemp(irsb->tyenv, type); 111 } 112 113 /* Create an expression node for a temporary */ 114 static __inline__ IRExpr * 115 mkexpr(IRTemp tmp) 116 { 117 return IRExpr_RdTmp(tmp); 118 } 119 120 /* Generate an expression node for an address. */ 121 static __inline__ IRExpr * 122 mkaddr_expr(Addr64 addr) 123 { 124 return IRExpr_Const(IRConst_U64(addr)); 125 } 126 127 /* Add a statement that assigns to a temporary */ 128 static __inline__ void 129 assign(IRTemp dst, IRExpr *expr) 130 { 131 stmt(IRStmt_WrTmp(dst, expr)); 132 } 133 134 /* Write an address into the guest_IA */ 135 static __inline__ void 136 put_IA(IRExpr *address) 137 { 138 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_IA), address)); 139 } 140 141 /* Create a temporary of the given type and assign the expression to it */ 142 static __inline__ IRTemp 143 mktemp(IRType type, IRExpr *expr) 144 { 145 IRTemp temp = newTemp(type); 146 147 assign(temp, expr); 148 149 return temp; 150 } 151 152 /* Create a unary expression */ 153 static __inline__ IRExpr * 154 unop(IROp kind, IRExpr *op) 155 { 156 return IRExpr_Unop(kind, op); 157 } 158 159 /* Create a binary expression */ 160 static __inline__ IRExpr * 161 binop(IROp kind, IRExpr *op1, IRExpr *op2) 162 { 163 return IRExpr_Binop(kind, op1, op2); 164 } 165 166 /* Create a ternary expression */ 167 static __inline__ IRExpr * 168 triop(IROp kind, IRExpr *op1, IRExpr *op2, IRExpr *op3) 169 { 170 return IRExpr_Triop(kind, op1, op2, op3); 171 } 172 173 /* Create a quaternary expression */ 174 static __inline__ IRExpr * 175 qop(IROp kind, IRExpr *op1, IRExpr *op2, IRExpr *op3, IRExpr *op4) 176 { 177 return IRExpr_Qop(kind, op1, op2, op3, op4); 178 } 179 180 /* Create an expression node for an 8-bit integer constant */ 181 static __inline__ IRExpr * 182 mkU8(UInt value) 183 { 184 vassert(value < 256); 185 186 return IRExpr_Const(IRConst_U8((UChar)value)); 187 } 188 189 /* Create an expression node for a 16-bit integer constant */ 190 static __inline__ IRExpr * 191 mkU16(UInt value) 192 { 193 vassert(value < 65536); 194 195 return IRExpr_Const(IRConst_U16((UShort)value)); 196 } 197 198 /* Create an expression node for a 32-bit integer constant */ 199 static __inline__ IRExpr * 200 mkU32(UInt value) 201 { 202 return IRExpr_Const(IRConst_U32(value)); 203 } 204 205 /* Create an expression node for a 64-bit integer constant */ 206 static __inline__ IRExpr * 207 mkU64(ULong value) 208 { 209 return IRExpr_Const(IRConst_U64(value)); 210 } 211 212 /* Create an expression node for a 32-bit floating point constant 213 whose value is given by a bit pattern. */ 214 static __inline__ IRExpr * 215 mkF32i(UInt value) 216 { 217 return IRExpr_Const(IRConst_F32i(value)); 218 } 219 220 /* Create an expression node for a 32-bit floating point constant 221 whose value is given by a bit pattern. */ 222 static __inline__ IRExpr * 223 mkF64i(ULong value) 224 { 225 return IRExpr_Const(IRConst_F64i(value)); 226 } 227 228 /* Little helper function for my sanity. ITE = if-then-else */ 229 static IRExpr * 230 mkite(IRExpr *condition, IRExpr *iftrue, IRExpr *iffalse) 231 { 232 vassert(typeOfIRExpr(irsb->tyenv, condition) == Ity_I1); 233 234 return IRExpr_ITE(condition, iftrue, iffalse); 235 } 236 237 /* Add a statement that stores DATA at ADDR. This is a big-endian machine. */ 238 static __inline__ void 239 store(IRExpr *addr, IRExpr *data) 240 { 241 stmt(IRStmt_Store(Iend_BE, addr, data)); 242 } 243 244 /* Create an expression that loads a TYPE sized value from ADDR. 245 This is a big-endian machine. */ 246 static __inline__ IRExpr * 247 load(IRType type, IRExpr *addr) 248 { 249 return IRExpr_Load(Iend_BE, type, addr); 250 } 251 252 /* Function call */ 253 static void 254 call_function(IRExpr *callee_address) 255 { 256 put_IA(callee_address); 257 258 dis_res->whatNext = Dis_StopHere; 259 dis_res->jk_StopHere = Ijk_Call; 260 } 261 262 /* Function call with known target. */ 263 static void 264 call_function_and_chase(Addr64 callee_address) 265 { 266 if (resteer_fn(resteer_data, callee_address)) { 267 dis_res->whatNext = Dis_ResteerU; 268 dis_res->continueAt = callee_address; 269 } else { 270 put_IA(mkaddr_expr(callee_address)); 271 272 dis_res->whatNext = Dis_StopHere; 273 dis_res->jk_StopHere = Ijk_Call; 274 } 275 } 276 277 /* Function return sequence */ 278 static void 279 return_from_function(IRExpr *return_address) 280 { 281 put_IA(return_address); 282 283 dis_res->whatNext = Dis_StopHere; 284 dis_res->jk_StopHere = Ijk_Ret; 285 } 286 287 /* A conditional branch whose target is not known at instrumentation time. 288 289 if (condition) goto computed_target; 290 291 Needs to be represented as: 292 293 if (! condition) goto next_instruction; 294 goto computed_target; 295 */ 296 static void 297 if_condition_goto_computed(IRExpr *condition, IRExpr *target) 298 { 299 vassert(typeOfIRExpr(irsb->tyenv, condition) == Ity_I1); 300 301 condition = unop(Iop_Not1, condition); 302 303 stmt(IRStmt_Exit(condition, Ijk_Boring, IRConst_U64(guest_IA_next_instr), 304 S390X_GUEST_OFFSET(guest_IA))); 305 306 put_IA(target); 307 308 dis_res->whatNext = Dis_StopHere; 309 dis_res->jk_StopHere = Ijk_Boring; 310 } 311 312 /* A conditional branch whose target is known at instrumentation time. */ 313 static void 314 if_condition_goto(IRExpr *condition, Addr64 target) 315 { 316 vassert(typeOfIRExpr(irsb->tyenv, condition) == Ity_I1); 317 318 stmt(IRStmt_Exit(condition, Ijk_Boring, IRConst_U64(target), 319 S390X_GUEST_OFFSET(guest_IA))); 320 321 put_IA(mkaddr_expr(guest_IA_next_instr)); 322 323 dis_res->whatNext = Dis_StopHere; 324 dis_res->jk_StopHere = Ijk_Boring; 325 } 326 327 /* An unconditional branch. Target may or may not be known at instrumentation 328 time. */ 329 static void 330 always_goto(IRExpr *target) 331 { 332 put_IA(target); 333 334 dis_res->whatNext = Dis_StopHere; 335 dis_res->jk_StopHere = Ijk_Boring; 336 } 337 338 339 /* An unconditional branch to a known target. */ 340 static void 341 always_goto_and_chase(Addr64 target) 342 { 343 if (resteer_fn(resteer_data, target)) { 344 /* Follow into the target */ 345 dis_res->whatNext = Dis_ResteerU; 346 dis_res->continueAt = target; 347 } else { 348 put_IA(mkaddr_expr(target)); 349 350 dis_res->whatNext = Dis_StopHere; 351 dis_res->jk_StopHere = Ijk_Boring; 352 } 353 } 354 355 /* A system call */ 356 static void 357 system_call(IRExpr *sysno) 358 { 359 /* Store the system call number in the pseudo register. */ 360 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_SYSNO), sysno)); 361 362 /* Store the current IA into guest_IP_AT_SYSCALL. libvex_ir.h says so. */ 363 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_IP_AT_SYSCALL), 364 mkU64(guest_IA_curr_instr))); 365 366 put_IA(mkaddr_expr(guest_IA_next_instr)); 367 368 /* It's important that all ArchRegs carry their up-to-date value 369 at this point. So we declare an end-of-block here, which 370 forces any TempRegs caching ArchRegs to be flushed. */ 371 dis_res->whatNext = Dis_StopHere; 372 dis_res->jk_StopHere = Ijk_Sys_syscall; 373 } 374 375 /* A side exit that branches back to the current insn if CONDITION is 376 true. Does not set DisResult. */ 377 static void 378 iterate_if(IRExpr *condition) 379 { 380 vassert(typeOfIRExpr(irsb->tyenv, condition) == Ity_I1); 381 382 stmt(IRStmt_Exit(condition, Ijk_Boring, IRConst_U64(guest_IA_curr_instr), 383 S390X_GUEST_OFFSET(guest_IA))); 384 } 385 386 /* A side exit that branches back to the current insn. 387 Does not set DisResult. */ 388 static __inline__ void 389 iterate(void) 390 { 391 iterate_if(IRExpr_Const(IRConst_U1(True))); 392 } 393 394 /* A side exit that branches back to the insn immediately following the 395 current insn if CONDITION is true. Does not set DisResult. */ 396 static void 397 next_insn_if(IRExpr *condition) 398 { 399 vassert(typeOfIRExpr(irsb->tyenv, condition) == Ity_I1); 400 401 stmt(IRStmt_Exit(condition, Ijk_Boring, IRConst_U64(guest_IA_next_instr), 402 S390X_GUEST_OFFSET(guest_IA))); 403 } 404 405 /* Convenience function to restart the current insn */ 406 static void 407 restart_if(IRExpr *condition) 408 { 409 vassert(typeOfIRExpr(irsb->tyenv, condition) == Ity_I1); 410 411 stmt(IRStmt_Exit(condition, Ijk_InvalICache, 412 IRConst_U64(guest_IA_curr_instr), 413 S390X_GUEST_OFFSET(guest_IA))); 414 } 415 416 /* Convenience function to yield to thread scheduler */ 417 static void 418 yield_if(IRExpr *condition) 419 { 420 stmt(IRStmt_Exit(condition, Ijk_Yield, IRConst_U64(guest_IA_next_instr), 421 S390X_GUEST_OFFSET(guest_IA))); 422 } 423 424 static __inline__ IRExpr *get_fpr_dw0(UInt); 425 static __inline__ void put_fpr_dw0(UInt, IRExpr *); 426 static __inline__ IRExpr *get_dpr_dw0(UInt); 427 static __inline__ void put_dpr_dw0(UInt, IRExpr *); 428 429 /* Read a floating point register pair and combine their contents into a 430 128-bit value */ 431 static IRExpr * 432 get_fpr_pair(UInt archreg) 433 { 434 IRExpr *high = get_fpr_dw0(archreg); 435 IRExpr *low = get_fpr_dw0(archreg + 2); 436 437 return binop(Iop_F64HLtoF128, high, low); 438 } 439 440 /* Write a 128-bit floating point value into a register pair. */ 441 static void 442 put_fpr_pair(UInt archreg, IRExpr *expr) 443 { 444 IRExpr *high = unop(Iop_F128HItoF64, expr); 445 IRExpr *low = unop(Iop_F128LOtoF64, expr); 446 447 put_fpr_dw0(archreg, high); 448 put_fpr_dw0(archreg + 2, low); 449 } 450 451 /* Read a floating point register pair cointaining DFP value 452 and combine their contents into a 128-bit value */ 453 454 static IRExpr * 455 get_dpr_pair(UInt archreg) 456 { 457 IRExpr *high = get_dpr_dw0(archreg); 458 IRExpr *low = get_dpr_dw0(archreg + 2); 459 460 return binop(Iop_D64HLtoD128, high, low); 461 } 462 463 /* Write a 128-bit decimal floating point value into a register pair. */ 464 static void 465 put_dpr_pair(UInt archreg, IRExpr *expr) 466 { 467 IRExpr *high = unop(Iop_D128HItoD64, expr); 468 IRExpr *low = unop(Iop_D128LOtoD64, expr); 469 470 put_dpr_dw0(archreg, high); 471 put_dpr_dw0(archreg + 2, low); 472 } 473 474 /* Terminate the current IRSB with an emulation failure. */ 475 static void 476 emulation_failure_with_expr(IRExpr *emfailure) 477 { 478 vassert(typeOfIRExpr(irsb->tyenv, emfailure) == Ity_I32); 479 480 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_EMNOTE), emfailure)); 481 dis_res->whatNext = Dis_StopHere; 482 dis_res->jk_StopHere = Ijk_EmFail; 483 } 484 485 static void 486 emulation_failure(VexEmNote fail_kind) 487 { 488 emulation_failure_with_expr(mkU32(fail_kind)); 489 } 490 491 /* Terminate the current IRSB with an emulation warning. */ 492 static void 493 emulation_warning_with_expr(IRExpr *emwarning) 494 { 495 vassert(typeOfIRExpr(irsb->tyenv, emwarning) == Ity_I32); 496 497 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_EMNOTE), emwarning)); 498 dis_res->whatNext = Dis_StopHere; 499 dis_res->jk_StopHere = Ijk_EmWarn; 500 } 501 502 static void 503 emulation_warning(VexEmNote warn_kind) 504 { 505 emulation_warning_with_expr(mkU32(warn_kind)); 506 } 507 508 /*------------------------------------------------------------*/ 509 /*--- IR Debugging aids. ---*/ 510 /*------------------------------------------------------------*/ 511 #if 0 512 513 static ULong 514 s390_do_print(HChar *text, ULong value) 515 { 516 vex_printf("%s %llu\n", text, value); 517 return 0; 518 } 519 520 static void 521 s390_print(HChar *text, IRExpr *value) 522 { 523 IRDirty *d; 524 525 d = unsafeIRDirty_0_N(0 /* regparms */, "s390_do_print", &s390_do_print, 526 mkIRExprVec_2(mkU64((ULong)text), value)); 527 stmt(IRStmt_Dirty(d)); 528 } 529 #endif 530 531 532 /*------------------------------------------------------------*/ 533 /*--- Build the flags thunk. ---*/ 534 /*------------------------------------------------------------*/ 535 536 /* Completely fill the flags thunk. We're always filling all fields. 537 Apparently, that is better for redundant PUT elimination. */ 538 static void 539 s390_cc_thunk_fill(IRExpr *op, IRExpr *dep1, IRExpr *dep2, IRExpr *ndep) 540 { 541 UInt op_off, dep1_off, dep2_off, ndep_off; 542 543 op_off = S390X_GUEST_OFFSET(guest_CC_OP); 544 dep1_off = S390X_GUEST_OFFSET(guest_CC_DEP1); 545 dep2_off = S390X_GUEST_OFFSET(guest_CC_DEP2); 546 ndep_off = S390X_GUEST_OFFSET(guest_CC_NDEP); 547 548 stmt(IRStmt_Put(op_off, op)); 549 stmt(IRStmt_Put(dep1_off, dep1)); 550 stmt(IRStmt_Put(dep2_off, dep2)); 551 stmt(IRStmt_Put(ndep_off, ndep)); 552 } 553 554 555 /* Create an expression for V and widen the result to 64 bit. */ 556 static IRExpr * 557 s390_cc_widen(IRTemp v, Bool sign_extend) 558 { 559 IRExpr *expr; 560 561 expr = mkexpr(v); 562 563 switch (typeOfIRTemp(irsb->tyenv, v)) { 564 case Ity_I64: 565 break; 566 case Ity_I32: 567 expr = unop(sign_extend ? Iop_32Sto64 : Iop_32Uto64, expr); 568 break; 569 case Ity_I16: 570 expr = unop(sign_extend ? Iop_16Sto64 : Iop_16Uto64, expr); 571 break; 572 case Ity_I8: 573 expr = unop(sign_extend ? Iop_8Sto64 : Iop_8Uto64, expr); 574 break; 575 default: 576 vpanic("s390_cc_widen"); 577 } 578 579 return expr; 580 } 581 582 static void 583 s390_cc_thunk_put1(UInt opc, IRTemp d1, Bool sign_extend) 584 { 585 IRExpr *op, *dep1, *dep2, *ndep; 586 587 op = mkU64(opc); 588 dep1 = s390_cc_widen(d1, sign_extend); 589 dep2 = mkU64(0); 590 ndep = mkU64(0); 591 592 s390_cc_thunk_fill(op, dep1, dep2, ndep); 593 } 594 595 596 static void 597 s390_cc_thunk_put2(UInt opc, IRTemp d1, IRTemp d2, Bool sign_extend) 598 { 599 IRExpr *op, *dep1, *dep2, *ndep; 600 601 op = mkU64(opc); 602 dep1 = s390_cc_widen(d1, sign_extend); 603 dep2 = s390_cc_widen(d2, sign_extend); 604 ndep = mkU64(0); 605 606 s390_cc_thunk_fill(op, dep1, dep2, ndep); 607 } 608 609 610 /* memcheck believes that the NDEP field in the flags thunk is always 611 defined. But for some flag computations (e.g. add with carry) that is 612 just not true. We therefore need to convey to memcheck that the value 613 of the ndep field does matter and therefore we make the DEP2 field 614 depend on it: 615 616 DEP2 = original_DEP2 ^ NDEP 617 618 In s390_calculate_cc we exploit that (a^b)^b == a 619 I.e. we xor the DEP2 value with the NDEP value to recover the 620 original_DEP2 value. */ 621 static void 622 s390_cc_thunk_put3(UInt opc, IRTemp d1, IRTemp d2, IRTemp nd, Bool sign_extend) 623 { 624 IRExpr *op, *dep1, *dep2, *ndep, *dep2x; 625 626 op = mkU64(opc); 627 dep1 = s390_cc_widen(d1, sign_extend); 628 dep2 = s390_cc_widen(d2, sign_extend); 629 ndep = s390_cc_widen(nd, sign_extend); 630 631 dep2x = binop(Iop_Xor64, dep2, ndep); 632 633 s390_cc_thunk_fill(op, dep1, dep2x, ndep); 634 } 635 636 637 /* Write one floating point value into the flags thunk */ 638 static void 639 s390_cc_thunk_put1f(UInt opc, IRTemp d1) 640 { 641 IRExpr *op, *dep1, *dep2, *ndep; 642 643 /* Make the CC_DEP1 slot appear completely defined. 644 Otherwise, assigning a 32-bit value will cause memcheck 645 to trigger an undefinedness error. 646 */ 647 if (sizeofIRType(typeOfIRTemp(irsb->tyenv, d1)) == 4) { 648 UInt dep1_off = S390X_GUEST_OFFSET(guest_CC_DEP1); 649 stmt(IRStmt_Put(dep1_off, mkU64(0))); 650 } 651 op = mkU64(opc); 652 dep1 = mkexpr(d1); 653 dep2 = mkU64(0); 654 ndep = mkU64(0); 655 656 s390_cc_thunk_fill(op, dep1, dep2, ndep); 657 } 658 659 660 /* Write a floating point value and an integer into the flags thunk. The 661 integer value is zero-extended first. */ 662 static void 663 s390_cc_thunk_putFZ(UInt opc, IRTemp d1, IRTemp d2) 664 { 665 IRExpr *op, *dep1, *dep2, *ndep; 666 667 /* Make the CC_DEP1 slot appear completely defined. 668 Otherwise, assigning a 32-bit value will cause memcheck 669 to trigger an undefinedness error. 670 */ 671 if (sizeofIRType(typeOfIRTemp(irsb->tyenv, d1)) == 4) { 672 UInt dep1_off = S390X_GUEST_OFFSET(guest_CC_DEP1); 673 stmt(IRStmt_Put(dep1_off, mkU64(0))); 674 } 675 op = mkU64(opc); 676 dep1 = mkexpr(d1); 677 dep2 = s390_cc_widen(d2, False); 678 ndep = mkU64(0); 679 680 s390_cc_thunk_fill(op, dep1, dep2, ndep); 681 } 682 683 684 /* Write a 128-bit floating point value into the flags thunk. This is 685 done by splitting the value into two 64-bits values. */ 686 static void 687 s390_cc_thunk_put1f128(UInt opc, IRTemp d1) 688 { 689 IRExpr *op, *hi, *lo, *ndep; 690 691 op = mkU64(opc); 692 hi = unop(Iop_F128HItoF64, mkexpr(d1)); 693 lo = unop(Iop_F128LOtoF64, mkexpr(d1)); 694 ndep = mkU64(0); 695 696 s390_cc_thunk_fill(op, hi, lo, ndep); 697 } 698 699 700 /* Write a 128-bit floating point value and an integer into the flags thunk. 701 The integer value is zero-extended first. */ 702 static void 703 s390_cc_thunk_put1f128Z(UInt opc, IRTemp d1, IRTemp nd) 704 { 705 IRExpr *op, *hi, *lo, *lox, *ndep; 706 707 op = mkU64(opc); 708 hi = unop(Iop_F128HItoF64, mkexpr(d1)); 709 lo = unop(Iop_ReinterpF64asI64, unop(Iop_F128LOtoF64, mkexpr(d1))); 710 ndep = s390_cc_widen(nd, False); 711 712 lox = binop(Iop_Xor64, lo, ndep); /* convey dependency */ 713 714 s390_cc_thunk_fill(op, hi, lox, ndep); 715 } 716 717 718 /* Write a 128-bit decimal floating point value into the flags thunk. 719 This is done by splitting the value into two 64-bits values. */ 720 static void 721 s390_cc_thunk_put1d128(UInt opc, IRTemp d1) 722 { 723 IRExpr *op, *hi, *lo, *ndep; 724 725 op = mkU64(opc); 726 hi = unop(Iop_D128HItoD64, mkexpr(d1)); 727 lo = unop(Iop_D128LOtoD64, mkexpr(d1)); 728 ndep = mkU64(0); 729 730 s390_cc_thunk_fill(op, hi, lo, ndep); 731 } 732 733 734 /* Write a 128-bit decimal floating point value and an integer into the flags 735 thunk. The integer value is zero-extended first. */ 736 static void 737 s390_cc_thunk_put1d128Z(UInt opc, IRTemp d1, IRTemp nd) 738 { 739 IRExpr *op, *hi, *lo, *lox, *ndep; 740 741 op = mkU64(opc); 742 hi = unop(Iop_D128HItoD64, mkexpr(d1)); 743 lo = unop(Iop_ReinterpD64asI64, unop(Iop_D128LOtoD64, mkexpr(d1))); 744 ndep = s390_cc_widen(nd, False); 745 746 lox = binop(Iop_Xor64, lo, ndep); /* convey dependency */ 747 748 s390_cc_thunk_fill(op, hi, lox, ndep); 749 } 750 751 752 static void 753 s390_cc_set(UInt val) 754 { 755 s390_cc_thunk_fill(mkU64(S390_CC_OP_SET), 756 mkU64(val), mkU64(0), mkU64(0)); 757 } 758 759 /* Build IR to calculate the condition code from flags thunk. 760 Returns an expression of type Ity_I32 */ 761 static IRExpr * 762 s390_call_calculate_cc(void) 763 { 764 IRExpr **args, *call, *op, *dep1, *dep2, *ndep; 765 766 op = IRExpr_Get(S390X_GUEST_OFFSET(guest_CC_OP), Ity_I64); 767 dep1 = IRExpr_Get(S390X_GUEST_OFFSET(guest_CC_DEP1), Ity_I64); 768 dep2 = IRExpr_Get(S390X_GUEST_OFFSET(guest_CC_DEP2), Ity_I64); 769 ndep = IRExpr_Get(S390X_GUEST_OFFSET(guest_CC_NDEP), Ity_I64); 770 771 args = mkIRExprVec_4(op, dep1, dep2, ndep); 772 call = mkIRExprCCall(Ity_I32, 0 /*regparm*/, 773 "s390_calculate_cc", &s390_calculate_cc, args); 774 775 /* Exclude OP and NDEP from definedness checking. We're only 776 interested in DEP1 and DEP2. */ 777 call->Iex.CCall.cee->mcx_mask = (1<<0) | (1<<3); 778 779 return call; 780 } 781 782 /* Build IR to calculate the internal condition code for a "compare and branch" 783 insn. Returns an expression of type Ity_I32 */ 784 static IRExpr * 785 s390_call_calculate_icc(UInt m, UInt opc, IRTemp op1, IRTemp op2) 786 { 787 IRExpr **args, *call, *op, *dep1, *dep2, *mask; 788 789 switch (opc) { 790 case S390_CC_OP_SIGNED_COMPARE: 791 dep1 = s390_cc_widen(op1, True); 792 dep2 = s390_cc_widen(op2, True); 793 break; 794 795 case S390_CC_OP_UNSIGNED_COMPARE: 796 dep1 = s390_cc_widen(op1, False); 797 dep2 = s390_cc_widen(op2, False); 798 break; 799 800 default: 801 vpanic("s390_call_calculate_icc"); 802 } 803 804 mask = mkU64(m); 805 op = mkU64(opc); 806 807 args = mkIRExprVec_5(mask, op, dep1, dep2, mkU64(0) /* unused */); 808 call = mkIRExprCCall(Ity_I32, 0 /*regparm*/, 809 "s390_calculate_cond", &s390_calculate_cond, args); 810 811 /* Exclude the requested condition, OP and NDEP from definedness 812 checking. We're only interested in DEP1 and DEP2. */ 813 call->Iex.CCall.cee->mcx_mask = (1<<0) | (1<<1) | (1<<4); 814 815 return call; 816 } 817 818 /* Build IR to calculate the condition code from flags thunk. 819 Returns an expression of type Ity_I32 */ 820 static IRExpr * 821 s390_call_calculate_cond(UInt m) 822 { 823 IRExpr **args, *call, *op, *dep1, *dep2, *ndep, *mask; 824 825 mask = mkU64(m); 826 op = IRExpr_Get(S390X_GUEST_OFFSET(guest_CC_OP), Ity_I64); 827 dep1 = IRExpr_Get(S390X_GUEST_OFFSET(guest_CC_DEP1), Ity_I64); 828 dep2 = IRExpr_Get(S390X_GUEST_OFFSET(guest_CC_DEP2), Ity_I64); 829 ndep = IRExpr_Get(S390X_GUEST_OFFSET(guest_CC_NDEP), Ity_I64); 830 831 args = mkIRExprVec_5(mask, op, dep1, dep2, ndep); 832 call = mkIRExprCCall(Ity_I32, 0 /*regparm*/, 833 "s390_calculate_cond", &s390_calculate_cond, args); 834 835 /* Exclude the requested condition, OP and NDEP from definedness 836 checking. We're only interested in DEP1 and DEP2. */ 837 call->Iex.CCall.cee->mcx_mask = (1<<0) | (1<<1) | (1<<4); 838 839 return call; 840 } 841 842 #define s390_cc_thunk_putZ(op,dep1) s390_cc_thunk_put1(op,dep1,False) 843 #define s390_cc_thunk_putS(op,dep1) s390_cc_thunk_put1(op,dep1,True) 844 #define s390_cc_thunk_putF(op,dep1) s390_cc_thunk_put1f(op,dep1) 845 #define s390_cc_thunk_putZZ(op,dep1,dep2) s390_cc_thunk_put2(op,dep1,dep2,False) 846 #define s390_cc_thunk_putSS(op,dep1,dep2) s390_cc_thunk_put2(op,dep1,dep2,True) 847 #define s390_cc_thunk_putFF(op,dep1,dep2) s390_cc_thunk_put2f(op,dep1,dep2) 848 #define s390_cc_thunk_putZZZ(op,dep1,dep2,ndep) \ 849 s390_cc_thunk_put3(op,dep1,dep2,ndep,False) 850 #define s390_cc_thunk_putSSS(op,dep1,dep2,ndep) \ 851 s390_cc_thunk_put3(op,dep1,dep2,ndep,True) 852 853 854 855 856 /*------------------------------------------------------------*/ 857 /*--- Guest register access ---*/ 858 /*------------------------------------------------------------*/ 859 860 861 /*------------------------------------------------------------*/ 862 /*--- ar registers ---*/ 863 /*------------------------------------------------------------*/ 864 865 /* Return the guest state offset of a ar register. */ 866 static UInt 867 ar_offset(UInt archreg) 868 { 869 static const UInt offset[16] = { 870 S390X_GUEST_OFFSET(guest_a0), 871 S390X_GUEST_OFFSET(guest_a1), 872 S390X_GUEST_OFFSET(guest_a2), 873 S390X_GUEST_OFFSET(guest_a3), 874 S390X_GUEST_OFFSET(guest_a4), 875 S390X_GUEST_OFFSET(guest_a5), 876 S390X_GUEST_OFFSET(guest_a6), 877 S390X_GUEST_OFFSET(guest_a7), 878 S390X_GUEST_OFFSET(guest_a8), 879 S390X_GUEST_OFFSET(guest_a9), 880 S390X_GUEST_OFFSET(guest_a10), 881 S390X_GUEST_OFFSET(guest_a11), 882 S390X_GUEST_OFFSET(guest_a12), 883 S390X_GUEST_OFFSET(guest_a13), 884 S390X_GUEST_OFFSET(guest_a14), 885 S390X_GUEST_OFFSET(guest_a15), 886 }; 887 888 vassert(archreg < 16); 889 890 return offset[archreg]; 891 } 892 893 894 /* Return the guest state offset of word #0 of a ar register. */ 895 static __inline__ UInt 896 ar_w0_offset(UInt archreg) 897 { 898 return ar_offset(archreg) + 0; 899 } 900 901 /* Write word #0 of a ar to the guest state. */ 902 static __inline__ void 903 put_ar_w0(UInt archreg, IRExpr *expr) 904 { 905 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I32); 906 907 stmt(IRStmt_Put(ar_w0_offset(archreg), expr)); 908 } 909 910 /* Read word #0 of a ar register. */ 911 static __inline__ IRExpr * 912 get_ar_w0(UInt archreg) 913 { 914 return IRExpr_Get(ar_w0_offset(archreg), Ity_I32); 915 } 916 917 918 /*------------------------------------------------------------*/ 919 /*--- fpr registers ---*/ 920 /*------------------------------------------------------------*/ 921 922 /* Return the guest state offset of a fpr register. */ 923 static UInt 924 fpr_offset(UInt archreg) 925 { 926 static const UInt offset[16] = { 927 S390X_GUEST_OFFSET(guest_f0), 928 S390X_GUEST_OFFSET(guest_f1), 929 S390X_GUEST_OFFSET(guest_f2), 930 S390X_GUEST_OFFSET(guest_f3), 931 S390X_GUEST_OFFSET(guest_f4), 932 S390X_GUEST_OFFSET(guest_f5), 933 S390X_GUEST_OFFSET(guest_f6), 934 S390X_GUEST_OFFSET(guest_f7), 935 S390X_GUEST_OFFSET(guest_f8), 936 S390X_GUEST_OFFSET(guest_f9), 937 S390X_GUEST_OFFSET(guest_f10), 938 S390X_GUEST_OFFSET(guest_f11), 939 S390X_GUEST_OFFSET(guest_f12), 940 S390X_GUEST_OFFSET(guest_f13), 941 S390X_GUEST_OFFSET(guest_f14), 942 S390X_GUEST_OFFSET(guest_f15), 943 }; 944 945 vassert(archreg < 16); 946 947 return offset[archreg]; 948 } 949 950 951 /* Return the guest state offset of word #0 of a fpr register. */ 952 static __inline__ UInt 953 fpr_w0_offset(UInt archreg) 954 { 955 return fpr_offset(archreg) + 0; 956 } 957 958 /* Write word #0 of a fpr to the guest state. */ 959 static __inline__ void 960 put_fpr_w0(UInt archreg, IRExpr *expr) 961 { 962 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_F32); 963 964 stmt(IRStmt_Put(fpr_w0_offset(archreg), expr)); 965 } 966 967 /* Read word #0 of a fpr register. */ 968 static __inline__ IRExpr * 969 get_fpr_w0(UInt archreg) 970 { 971 return IRExpr_Get(fpr_w0_offset(archreg), Ity_F32); 972 } 973 974 /* Return the guest state offset of double word #0 of a fpr register. */ 975 static __inline__ UInt 976 fpr_dw0_offset(UInt archreg) 977 { 978 return fpr_offset(archreg) + 0; 979 } 980 981 /* Write double word #0 of a fpr to the guest state. */ 982 static __inline__ void 983 put_fpr_dw0(UInt archreg, IRExpr *expr) 984 { 985 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_F64); 986 987 stmt(IRStmt_Put(fpr_dw0_offset(archreg), expr)); 988 } 989 990 /* Read double word #0 of a fpr register. */ 991 static __inline__ IRExpr * 992 get_fpr_dw0(UInt archreg) 993 { 994 return IRExpr_Get(fpr_dw0_offset(archreg), Ity_F64); 995 } 996 997 /* Write word #0 of a dpr to the guest state. */ 998 static __inline__ void 999 put_dpr_w0(UInt archreg, IRExpr *expr) 1000 { 1001 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_D32); 1002 1003 stmt(IRStmt_Put(fpr_w0_offset(archreg), expr)); 1004 } 1005 1006 /* Read word #0 of a dpr register. */ 1007 static __inline__ IRExpr * 1008 get_dpr_w0(UInt archreg) 1009 { 1010 return IRExpr_Get(fpr_w0_offset(archreg), Ity_D32); 1011 } 1012 1013 /* Write double word #0 of a fpr containg DFP value to the guest state. */ 1014 static __inline__ void 1015 put_dpr_dw0(UInt archreg, IRExpr *expr) 1016 { 1017 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_D64); 1018 1019 stmt(IRStmt_Put(fpr_dw0_offset(archreg), expr)); 1020 } 1021 1022 /* Read double word #0 of a fpr register containing DFP value. */ 1023 static __inline__ IRExpr * 1024 get_dpr_dw0(UInt archreg) 1025 { 1026 return IRExpr_Get(fpr_dw0_offset(archreg), Ity_D64); 1027 } 1028 1029 /*------------------------------------------------------------*/ 1030 /*--- gpr registers ---*/ 1031 /*------------------------------------------------------------*/ 1032 1033 /* Return the guest state offset of a gpr register. */ 1034 static UInt 1035 gpr_offset(UInt archreg) 1036 { 1037 static const UInt offset[16] = { 1038 S390X_GUEST_OFFSET(guest_r0), 1039 S390X_GUEST_OFFSET(guest_r1), 1040 S390X_GUEST_OFFSET(guest_r2), 1041 S390X_GUEST_OFFSET(guest_r3), 1042 S390X_GUEST_OFFSET(guest_r4), 1043 S390X_GUEST_OFFSET(guest_r5), 1044 S390X_GUEST_OFFSET(guest_r6), 1045 S390X_GUEST_OFFSET(guest_r7), 1046 S390X_GUEST_OFFSET(guest_r8), 1047 S390X_GUEST_OFFSET(guest_r9), 1048 S390X_GUEST_OFFSET(guest_r10), 1049 S390X_GUEST_OFFSET(guest_r11), 1050 S390X_GUEST_OFFSET(guest_r12), 1051 S390X_GUEST_OFFSET(guest_r13), 1052 S390X_GUEST_OFFSET(guest_r14), 1053 S390X_GUEST_OFFSET(guest_r15), 1054 }; 1055 1056 vassert(archreg < 16); 1057 1058 return offset[archreg]; 1059 } 1060 1061 1062 /* Return the guest state offset of word #0 of a gpr register. */ 1063 static __inline__ UInt 1064 gpr_w0_offset(UInt archreg) 1065 { 1066 return gpr_offset(archreg) + 0; 1067 } 1068 1069 /* Write word #0 of a gpr to the guest state. */ 1070 static __inline__ void 1071 put_gpr_w0(UInt archreg, IRExpr *expr) 1072 { 1073 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I32); 1074 1075 stmt(IRStmt_Put(gpr_w0_offset(archreg), expr)); 1076 } 1077 1078 /* Read word #0 of a gpr register. */ 1079 static __inline__ IRExpr * 1080 get_gpr_w0(UInt archreg) 1081 { 1082 return IRExpr_Get(gpr_w0_offset(archreg), Ity_I32); 1083 } 1084 1085 /* Return the guest state offset of double word #0 of a gpr register. */ 1086 static __inline__ UInt 1087 gpr_dw0_offset(UInt archreg) 1088 { 1089 return gpr_offset(archreg) + 0; 1090 } 1091 1092 /* Write double word #0 of a gpr to the guest state. */ 1093 static __inline__ void 1094 put_gpr_dw0(UInt archreg, IRExpr *expr) 1095 { 1096 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I64); 1097 1098 stmt(IRStmt_Put(gpr_dw0_offset(archreg), expr)); 1099 } 1100 1101 /* Read double word #0 of a gpr register. */ 1102 static __inline__ IRExpr * 1103 get_gpr_dw0(UInt archreg) 1104 { 1105 return IRExpr_Get(gpr_dw0_offset(archreg), Ity_I64); 1106 } 1107 1108 /* Return the guest state offset of half word #1 of a gpr register. */ 1109 static __inline__ UInt 1110 gpr_hw1_offset(UInt archreg) 1111 { 1112 return gpr_offset(archreg) + 2; 1113 } 1114 1115 /* Write half word #1 of a gpr to the guest state. */ 1116 static __inline__ void 1117 put_gpr_hw1(UInt archreg, IRExpr *expr) 1118 { 1119 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I16); 1120 1121 stmt(IRStmt_Put(gpr_hw1_offset(archreg), expr)); 1122 } 1123 1124 /* Read half word #1 of a gpr register. */ 1125 static __inline__ IRExpr * 1126 get_gpr_hw1(UInt archreg) 1127 { 1128 return IRExpr_Get(gpr_hw1_offset(archreg), Ity_I16); 1129 } 1130 1131 /* Return the guest state offset of byte #6 of a gpr register. */ 1132 static __inline__ UInt 1133 gpr_b6_offset(UInt archreg) 1134 { 1135 return gpr_offset(archreg) + 6; 1136 } 1137 1138 /* Write byte #6 of a gpr to the guest state. */ 1139 static __inline__ void 1140 put_gpr_b6(UInt archreg, IRExpr *expr) 1141 { 1142 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I8); 1143 1144 stmt(IRStmt_Put(gpr_b6_offset(archreg), expr)); 1145 } 1146 1147 /* Read byte #6 of a gpr register. */ 1148 static __inline__ IRExpr * 1149 get_gpr_b6(UInt archreg) 1150 { 1151 return IRExpr_Get(gpr_b6_offset(archreg), Ity_I8); 1152 } 1153 1154 /* Return the guest state offset of byte #3 of a gpr register. */ 1155 static __inline__ UInt 1156 gpr_b3_offset(UInt archreg) 1157 { 1158 return gpr_offset(archreg) + 3; 1159 } 1160 1161 /* Write byte #3 of a gpr to the guest state. */ 1162 static __inline__ void 1163 put_gpr_b3(UInt archreg, IRExpr *expr) 1164 { 1165 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I8); 1166 1167 stmt(IRStmt_Put(gpr_b3_offset(archreg), expr)); 1168 } 1169 1170 /* Read byte #3 of a gpr register. */ 1171 static __inline__ IRExpr * 1172 get_gpr_b3(UInt archreg) 1173 { 1174 return IRExpr_Get(gpr_b3_offset(archreg), Ity_I8); 1175 } 1176 1177 /* Return the guest state offset of byte #0 of a gpr register. */ 1178 static __inline__ UInt 1179 gpr_b0_offset(UInt archreg) 1180 { 1181 return gpr_offset(archreg) + 0; 1182 } 1183 1184 /* Write byte #0 of a gpr to the guest state. */ 1185 static __inline__ void 1186 put_gpr_b0(UInt archreg, IRExpr *expr) 1187 { 1188 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I8); 1189 1190 stmt(IRStmt_Put(gpr_b0_offset(archreg), expr)); 1191 } 1192 1193 /* Read byte #0 of a gpr register. */ 1194 static __inline__ IRExpr * 1195 get_gpr_b0(UInt archreg) 1196 { 1197 return IRExpr_Get(gpr_b0_offset(archreg), Ity_I8); 1198 } 1199 1200 /* Return the guest state offset of word #1 of a gpr register. */ 1201 static __inline__ UInt 1202 gpr_w1_offset(UInt archreg) 1203 { 1204 return gpr_offset(archreg) + 4; 1205 } 1206 1207 /* Write word #1 of a gpr to the guest state. */ 1208 static __inline__ void 1209 put_gpr_w1(UInt archreg, IRExpr *expr) 1210 { 1211 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I32); 1212 1213 stmt(IRStmt_Put(gpr_w1_offset(archreg), expr)); 1214 } 1215 1216 /* Read word #1 of a gpr register. */ 1217 static __inline__ IRExpr * 1218 get_gpr_w1(UInt archreg) 1219 { 1220 return IRExpr_Get(gpr_w1_offset(archreg), Ity_I32); 1221 } 1222 1223 /* Return the guest state offset of half word #3 of a gpr register. */ 1224 static __inline__ UInt 1225 gpr_hw3_offset(UInt archreg) 1226 { 1227 return gpr_offset(archreg) + 6; 1228 } 1229 1230 /* Write half word #3 of a gpr to the guest state. */ 1231 static __inline__ void 1232 put_gpr_hw3(UInt archreg, IRExpr *expr) 1233 { 1234 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I16); 1235 1236 stmt(IRStmt_Put(gpr_hw3_offset(archreg), expr)); 1237 } 1238 1239 /* Read half word #3 of a gpr register. */ 1240 static __inline__ IRExpr * 1241 get_gpr_hw3(UInt archreg) 1242 { 1243 return IRExpr_Get(gpr_hw3_offset(archreg), Ity_I16); 1244 } 1245 1246 /* Return the guest state offset of byte #7 of a gpr register. */ 1247 static __inline__ UInt 1248 gpr_b7_offset(UInt archreg) 1249 { 1250 return gpr_offset(archreg) + 7; 1251 } 1252 1253 /* Write byte #7 of a gpr to the guest state. */ 1254 static __inline__ void 1255 put_gpr_b7(UInt archreg, IRExpr *expr) 1256 { 1257 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I8); 1258 1259 stmt(IRStmt_Put(gpr_b7_offset(archreg), expr)); 1260 } 1261 1262 /* Read byte #7 of a gpr register. */ 1263 static __inline__ IRExpr * 1264 get_gpr_b7(UInt archreg) 1265 { 1266 return IRExpr_Get(gpr_b7_offset(archreg), Ity_I8); 1267 } 1268 1269 /* Return the guest state offset of half word #0 of a gpr register. */ 1270 static __inline__ UInt 1271 gpr_hw0_offset(UInt archreg) 1272 { 1273 return gpr_offset(archreg) + 0; 1274 } 1275 1276 /* Write half word #0 of a gpr to the guest state. */ 1277 static __inline__ void 1278 put_gpr_hw0(UInt archreg, IRExpr *expr) 1279 { 1280 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I16); 1281 1282 stmt(IRStmt_Put(gpr_hw0_offset(archreg), expr)); 1283 } 1284 1285 /* Read half word #0 of a gpr register. */ 1286 static __inline__ IRExpr * 1287 get_gpr_hw0(UInt archreg) 1288 { 1289 return IRExpr_Get(gpr_hw0_offset(archreg), Ity_I16); 1290 } 1291 1292 /* Return the guest state offset of byte #4 of a gpr register. */ 1293 static __inline__ UInt 1294 gpr_b4_offset(UInt archreg) 1295 { 1296 return gpr_offset(archreg) + 4; 1297 } 1298 1299 /* Write byte #4 of a gpr to the guest state. */ 1300 static __inline__ void 1301 put_gpr_b4(UInt archreg, IRExpr *expr) 1302 { 1303 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I8); 1304 1305 stmt(IRStmt_Put(gpr_b4_offset(archreg), expr)); 1306 } 1307 1308 /* Read byte #4 of a gpr register. */ 1309 static __inline__ IRExpr * 1310 get_gpr_b4(UInt archreg) 1311 { 1312 return IRExpr_Get(gpr_b4_offset(archreg), Ity_I8); 1313 } 1314 1315 /* Return the guest state offset of byte #1 of a gpr register. */ 1316 static __inline__ UInt 1317 gpr_b1_offset(UInt archreg) 1318 { 1319 return gpr_offset(archreg) + 1; 1320 } 1321 1322 /* Write byte #1 of a gpr to the guest state. */ 1323 static __inline__ void 1324 put_gpr_b1(UInt archreg, IRExpr *expr) 1325 { 1326 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I8); 1327 1328 stmt(IRStmt_Put(gpr_b1_offset(archreg), expr)); 1329 } 1330 1331 /* Read byte #1 of a gpr register. */ 1332 static __inline__ IRExpr * 1333 get_gpr_b1(UInt archreg) 1334 { 1335 return IRExpr_Get(gpr_b1_offset(archreg), Ity_I8); 1336 } 1337 1338 /* Return the guest state offset of half word #2 of a gpr register. */ 1339 static __inline__ UInt 1340 gpr_hw2_offset(UInt archreg) 1341 { 1342 return gpr_offset(archreg) + 4; 1343 } 1344 1345 /* Write half word #2 of a gpr to the guest state. */ 1346 static __inline__ void 1347 put_gpr_hw2(UInt archreg, IRExpr *expr) 1348 { 1349 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I16); 1350 1351 stmt(IRStmt_Put(gpr_hw2_offset(archreg), expr)); 1352 } 1353 1354 /* Read half word #2 of a gpr register. */ 1355 static __inline__ IRExpr * 1356 get_gpr_hw2(UInt archreg) 1357 { 1358 return IRExpr_Get(gpr_hw2_offset(archreg), Ity_I16); 1359 } 1360 1361 /* Return the guest state offset of byte #5 of a gpr register. */ 1362 static __inline__ UInt 1363 gpr_b5_offset(UInt archreg) 1364 { 1365 return gpr_offset(archreg) + 5; 1366 } 1367 1368 /* Write byte #5 of a gpr to the guest state. */ 1369 static __inline__ void 1370 put_gpr_b5(UInt archreg, IRExpr *expr) 1371 { 1372 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I8); 1373 1374 stmt(IRStmt_Put(gpr_b5_offset(archreg), expr)); 1375 } 1376 1377 /* Read byte #5 of a gpr register. */ 1378 static __inline__ IRExpr * 1379 get_gpr_b5(UInt archreg) 1380 { 1381 return IRExpr_Get(gpr_b5_offset(archreg), Ity_I8); 1382 } 1383 1384 /* Return the guest state offset of byte #2 of a gpr register. */ 1385 static __inline__ UInt 1386 gpr_b2_offset(UInt archreg) 1387 { 1388 return gpr_offset(archreg) + 2; 1389 } 1390 1391 /* Write byte #2 of a gpr to the guest state. */ 1392 static __inline__ void 1393 put_gpr_b2(UInt archreg, IRExpr *expr) 1394 { 1395 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I8); 1396 1397 stmt(IRStmt_Put(gpr_b2_offset(archreg), expr)); 1398 } 1399 1400 /* Read byte #2 of a gpr register. */ 1401 static __inline__ IRExpr * 1402 get_gpr_b2(UInt archreg) 1403 { 1404 return IRExpr_Get(gpr_b2_offset(archreg), Ity_I8); 1405 } 1406 1407 /* Return the guest state offset of the counter register. */ 1408 static UInt 1409 counter_offset(void) 1410 { 1411 return S390X_GUEST_OFFSET(guest_counter); 1412 } 1413 1414 /* Return the guest state offset of double word #0 of the counter register. */ 1415 static __inline__ UInt 1416 counter_dw0_offset(void) 1417 { 1418 return counter_offset() + 0; 1419 } 1420 1421 /* Write double word #0 of the counter to the guest state. */ 1422 static __inline__ void 1423 put_counter_dw0(IRExpr *expr) 1424 { 1425 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I64); 1426 1427 stmt(IRStmt_Put(counter_dw0_offset(), expr)); 1428 } 1429 1430 /* Read double word #0 of the counter register. */ 1431 static __inline__ IRExpr * 1432 get_counter_dw0(void) 1433 { 1434 return IRExpr_Get(counter_dw0_offset(), Ity_I64); 1435 } 1436 1437 /* Return the guest state offset of word #0 of the counter register. */ 1438 static __inline__ UInt 1439 counter_w0_offset(void) 1440 { 1441 return counter_offset() + 0; 1442 } 1443 1444 /* Return the guest state offset of word #1 of the counter register. */ 1445 static __inline__ UInt 1446 counter_w1_offset(void) 1447 { 1448 return counter_offset() + 4; 1449 } 1450 1451 /* Write word #0 of the counter to the guest state. */ 1452 static __inline__ void 1453 put_counter_w0(IRExpr *expr) 1454 { 1455 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I32); 1456 1457 stmt(IRStmt_Put(counter_w0_offset(), expr)); 1458 } 1459 1460 /* Read word #0 of the counter register. */ 1461 static __inline__ IRExpr * 1462 get_counter_w0(void) 1463 { 1464 return IRExpr_Get(counter_w0_offset(), Ity_I32); 1465 } 1466 1467 /* Write word #1 of the counter to the guest state. */ 1468 static __inline__ void 1469 put_counter_w1(IRExpr *expr) 1470 { 1471 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I32); 1472 1473 stmt(IRStmt_Put(counter_w1_offset(), expr)); 1474 } 1475 1476 /* Read word #1 of the counter register. */ 1477 static __inline__ IRExpr * 1478 get_counter_w1(void) 1479 { 1480 return IRExpr_Get(counter_w1_offset(), Ity_I32); 1481 } 1482 1483 /* Return the guest state offset of the fpc register. */ 1484 static UInt 1485 fpc_offset(void) 1486 { 1487 return S390X_GUEST_OFFSET(guest_fpc); 1488 } 1489 1490 /* Return the guest state offset of word #0 of the fpc register. */ 1491 static __inline__ UInt 1492 fpc_w0_offset(void) 1493 { 1494 return fpc_offset() + 0; 1495 } 1496 1497 /* Write word #0 of the fpc to the guest state. */ 1498 static __inline__ void 1499 put_fpc_w0(IRExpr *expr) 1500 { 1501 vassert(typeOfIRExpr(irsb->tyenv, expr) == Ity_I32); 1502 1503 stmt(IRStmt_Put(fpc_w0_offset(), expr)); 1504 } 1505 1506 /* Read word #0 of the fpc register. */ 1507 static __inline__ IRExpr * 1508 get_fpc_w0(void) 1509 { 1510 return IRExpr_Get(fpc_w0_offset(), Ity_I32); 1511 } 1512 1513 1514 /*------------------------------------------------------------*/ 1515 /*--- Rounding modes ---*/ 1516 /*------------------------------------------------------------*/ 1517 1518 /* Extract the bfp rounding mode from the guest FPC reg and encode it as an 1519 IRRoundingMode: 1520 1521 rounding mode | s390 | IR 1522 ------------------------- 1523 to nearest | 00 | 00 1524 to zero | 01 | 11 1525 to +infinity | 10 | 10 1526 to -infinity | 11 | 01 1527 1528 So: IR = (4 - s390) & 3 1529 */ 1530 static IRExpr * 1531 get_bfp_rounding_mode_from_fpc(void) 1532 { 1533 IRTemp fpc_bits = newTemp(Ity_I32); 1534 1535 /* For z196 and later the bfp rounding mode is stored in bits [29:31]. 1536 Prior to that bits [30:31] contained the bfp rounding mode with 1537 bit 29 being unused and having a value of 0. So we can always 1538 extract the least significant 3 bits. */ 1539 assign(fpc_bits, binop(Iop_And32, get_fpc_w0(), mkU32(7))); 1540 1541 /* fixs390: 1542 1543 1544 if (! s390_host_has_fpext && rounding_mode > 3) { 1545 emulation warning @ runtime and 1546 set fpc to round nearest 1547 } 1548 */ 1549 1550 /* For now silently adjust an unsupported rounding mode to "nearest" */ 1551 IRExpr *rm_s390 = mkite(binop(Iop_CmpLE32S, mkexpr(fpc_bits), mkU32(3)), 1552 mkexpr(fpc_bits), 1553 mkU32(S390_FPC_BFP_ROUND_NEAREST_EVEN)); 1554 1555 // rm_IR = (4 - rm_s390) & 3; 1556 return binop(Iop_And32, binop(Iop_Sub32, mkU32(4), rm_s390), mkU32(3)); 1557 } 1558 1559 /* Encode the s390 rounding mode as it appears in the m3 field of certain 1560 instructions to VEX's IRRoundingMode. Rounding modes that cannot be 1561 represented in VEX are converted to Irrm_NEAREST. The rationale is, that 1562 Irrm_NEAREST refers to IEEE 754's roundTiesToEven which the standard 1563 considers the default rounding mode (4.3.3). */ 1564 static IRTemp 1565 encode_bfp_rounding_mode(UChar mode) 1566 { 1567 IRExpr *rm; 1568 1569 switch (mode) { 1570 case S390_BFP_ROUND_PER_FPC: 1571 rm = get_bfp_rounding_mode_from_fpc(); 1572 break; 1573 case S390_BFP_ROUND_NEAREST_AWAY: /* not supported */ 1574 case S390_BFP_ROUND_PREPARE_SHORT: /* not supported */ 1575 case S390_BFP_ROUND_NEAREST_EVEN: rm = mkU32(Irrm_NEAREST); break; 1576 case S390_BFP_ROUND_ZERO: rm = mkU32(Irrm_ZERO); break; 1577 case S390_BFP_ROUND_POSINF: rm = mkU32(Irrm_PosINF); break; 1578 case S390_BFP_ROUND_NEGINF: rm = mkU32(Irrm_NegINF); break; 1579 default: 1580 vpanic("encode_bfp_rounding_mode"); 1581 } 1582 1583 return mktemp(Ity_I32, rm); 1584 } 1585 1586 /* Extract the DFP rounding mode from the guest FPC reg and encode it as an 1587 IRRoundingMode: 1588 1589 rounding mode | s390 | IR 1590 ------------------------------------------------ 1591 to nearest, ties to even | 000 | 000 1592 to zero | 001 | 011 1593 to +infinity | 010 | 010 1594 to -infinity | 011 | 001 1595 to nearest, ties away from 0 | 100 | 100 1596 to nearest, ties toward 0 | 101 | 111 1597 to away from 0 | 110 | 110 1598 to prepare for shorter precision | 111 | 101 1599 1600 So: IR = (s390 ^ ((s390 << 1) & 2)) 1601 */ 1602 static IRExpr * 1603 get_dfp_rounding_mode_from_fpc(void) 1604 { 1605 IRTemp fpc_bits = newTemp(Ity_I32); 1606 1607 /* The dfp rounding mode is stored in bits [25:27]. 1608 extract the bits at 25:27 and right shift 4 times. */ 1609 assign(fpc_bits, binop(Iop_Shr32, 1610 binop(Iop_And32, get_fpc_w0(), mkU32(0x70)), 1611 mkU8(4))); 1612 1613 IRExpr *rm_s390 = mkexpr(fpc_bits); 1614 // rm_IR = (rm_s390 ^ ((rm_s390 << 1) & 2)); 1615 1616 return binop(Iop_Xor32, rm_s390, 1617 binop( Iop_And32, 1618 binop(Iop_Shl32, rm_s390, mkU8(1)), 1619 mkU32(2))); 1620 } 1621 1622 /* Encode the s390 rounding mode as it appears in the m3 field of certain 1623 instructions to VEX's IRRoundingMode. */ 1624 static IRTemp 1625 encode_dfp_rounding_mode(UChar mode) 1626 { 1627 IRExpr *rm; 1628 1629 switch (mode) { 1630 case S390_DFP_ROUND_PER_FPC_0: 1631 case S390_DFP_ROUND_PER_FPC_2: 1632 rm = get_dfp_rounding_mode_from_fpc(); break; 1633 case S390_DFP_ROUND_NEAREST_EVEN_4: 1634 case S390_DFP_ROUND_NEAREST_EVEN_8: 1635 rm = mkU32(Irrm_NEAREST); break; 1636 case S390_DFP_ROUND_NEAREST_TIE_AWAY_0_1: 1637 case S390_DFP_ROUND_NEAREST_TIE_AWAY_0_12: 1638 rm = mkU32(Irrm_NEAREST_TIE_AWAY_0); break; 1639 case S390_DFP_ROUND_PREPARE_SHORT_3: 1640 case S390_DFP_ROUND_PREPARE_SHORT_15: 1641 rm = mkU32(Irrm_PREPARE_SHORTER); break; 1642 case S390_DFP_ROUND_ZERO_5: 1643 case S390_DFP_ROUND_ZERO_9: 1644 rm = mkU32(Irrm_ZERO ); break; 1645 case S390_DFP_ROUND_POSINF_6: 1646 case S390_DFP_ROUND_POSINF_10: 1647 rm = mkU32(Irrm_PosINF); break; 1648 case S390_DFP_ROUND_NEGINF_7: 1649 case S390_DFP_ROUND_NEGINF_11: 1650 rm = mkU32(Irrm_NegINF); break; 1651 case S390_DFP_ROUND_NEAREST_TIE_TOWARD_0: 1652 rm = mkU32(Irrm_NEAREST_TIE_TOWARD_0); break; 1653 case S390_DFP_ROUND_AWAY_0: 1654 rm = mkU32(Irrm_AWAY_FROM_ZERO); break; 1655 default: 1656 vpanic("encode_dfp_rounding_mode"); 1657 } 1658 1659 return mktemp(Ity_I32, rm); 1660 } 1661 1662 1663 /*------------------------------------------------------------*/ 1664 /*--- Condition code helpers ---*/ 1665 /*------------------------------------------------------------*/ 1666 1667 /* The result of a Iop_CmpFxx operation is a condition code. It is 1668 encoded using the values defined in type IRCmpFxxResult. 1669 Before we can store the condition code into the guest state (or do 1670 anything else with it for that matter) we need to convert it to 1671 the encoding that s390 uses. This is what this function does. 1672 1673 s390 VEX b6 b2 b0 cc.1 cc.0 1674 0 0x40 EQ 1 0 0 0 0 1675 1 0x01 LT 0 0 1 0 1 1676 2 0x00 GT 0 0 0 1 0 1677 3 0x45 Unordered 1 1 1 1 1 1678 1679 The following bits from the VEX encoding are interesting: 1680 b0, b2, b6 with b0 being the LSB. We observe: 1681 1682 cc.0 = b0; 1683 cc.1 = b2 | (~b0 & ~b6) 1684 1685 with cc being the s390 condition code. 1686 */ 1687 static IRExpr * 1688 convert_vex_bfpcc_to_s390(IRTemp vex_cc) 1689 { 1690 IRTemp cc0 = newTemp(Ity_I32); 1691 IRTemp cc1 = newTemp(Ity_I32); 1692 IRTemp b0 = newTemp(Ity_I32); 1693 IRTemp b2 = newTemp(Ity_I32); 1694 IRTemp b6 = newTemp(Ity_I32); 1695 1696 assign(b0, binop(Iop_And32, mkexpr(vex_cc), mkU32(1))); 1697 assign(b2, binop(Iop_And32, binop(Iop_Shr32, mkexpr(vex_cc), mkU8(2)), 1698 mkU32(1))); 1699 assign(b6, binop(Iop_And32, binop(Iop_Shr32, mkexpr(vex_cc), mkU8(6)), 1700 mkU32(1))); 1701 1702 assign(cc0, mkexpr(b0)); 1703 assign(cc1, binop(Iop_Or32, mkexpr(b2), 1704 binop(Iop_And32, 1705 binop(Iop_Sub32, mkU32(1), mkexpr(b0)), /* ~b0 */ 1706 binop(Iop_Sub32, mkU32(1), mkexpr(b6)) /* ~b6 */ 1707 ))); 1708 1709 return binop(Iop_Or32, mkexpr(cc0), binop(Iop_Shl32, mkexpr(cc1), mkU8(1))); 1710 } 1711 1712 1713 /* The result of a Iop_CmpDxx operation is a condition code. It is 1714 encoded using the values defined in type IRCmpDxxResult. 1715 Before we can store the condition code into the guest state (or do 1716 anything else with it for that matter) we need to convert it to 1717 the encoding that s390 uses. This is what this function does. */ 1718 static IRExpr * 1719 convert_vex_dfpcc_to_s390(IRTemp vex_cc) 1720 { 1721 /* The VEX encodings for IRCmpDxxResult and IRCmpFxxResult are the 1722 same. currently. */ 1723 return convert_vex_bfpcc_to_s390(vex_cc); 1724 } 1725 1726 1727 /*------------------------------------------------------------*/ 1728 /*--- Build IR for formats ---*/ 1729 /*------------------------------------------------------------*/ 1730 static void 1731 s390_format_I(const HChar *(*irgen)(UChar i), 1732 UChar i) 1733 { 1734 const HChar *mnm = irgen(i); 1735 1736 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1737 s390_disasm(ENC2(MNM, UINT), mnm, i); 1738 } 1739 1740 static void 1741 s390_format_E(const HChar *(*irgen)(void)) 1742 { 1743 const HChar *mnm = irgen(); 1744 1745 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1746 s390_disasm(ENC1(MNM), mnm); 1747 } 1748 1749 static void 1750 s390_format_RI(const HChar *(*irgen)(UChar r1, UShort i2), 1751 UChar r1, UShort i2) 1752 { 1753 irgen(r1, i2); 1754 } 1755 1756 static void 1757 s390_format_RI_RU(const HChar *(*irgen)(UChar r1, UShort i2), 1758 UChar r1, UShort i2) 1759 { 1760 const HChar *mnm = irgen(r1, i2); 1761 1762 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1763 s390_disasm(ENC3(MNM, GPR, UINT), mnm, r1, i2); 1764 } 1765 1766 static void 1767 s390_format_RI_RI(const HChar *(*irgen)(UChar r1, UShort i2), 1768 UChar r1, UShort i2) 1769 { 1770 const HChar *mnm = irgen(r1, i2); 1771 1772 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1773 s390_disasm(ENC3(MNM, GPR, INT), mnm, r1, (Int)(Short)i2); 1774 } 1775 1776 static void 1777 s390_format_RI_RP(const HChar *(*irgen)(UChar r1, UShort i2), 1778 UChar r1, UShort i2) 1779 { 1780 const HChar *mnm = irgen(r1, i2); 1781 1782 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1783 s390_disasm(ENC3(MNM, GPR, PCREL), mnm, r1, (Int)(Short)i2); 1784 } 1785 1786 static void 1787 s390_format_RIE_RRP(const HChar *(*irgen)(UChar r1, UChar r3, UShort i2), 1788 UChar r1, UChar r3, UShort i2) 1789 { 1790 const HChar *mnm = irgen(r1, r3, i2); 1791 1792 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1793 s390_disasm(ENC4(MNM, GPR, GPR, PCREL), mnm, r1, r3, (Int)(Short)i2); 1794 } 1795 1796 static void 1797 s390_format_RIE_RRI0(const HChar *(*irgen)(UChar r1, UChar r3, UShort i2), 1798 UChar r1, UChar r3, UShort i2) 1799 { 1800 const HChar *mnm = irgen(r1, r3, i2); 1801 1802 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1803 s390_disasm(ENC4(MNM, GPR, GPR, INT), mnm, r1, r3, (Int)(Short)i2); 1804 } 1805 1806 static void 1807 s390_format_RIE_RRUUU(const HChar *(*irgen)(UChar r1, UChar r2, UChar i3, 1808 UChar i4, UChar i5), 1809 UChar r1, UChar r2, UChar i3, UChar i4, UChar i5) 1810 { 1811 const HChar *mnm = irgen(r1, r2, i3, i4, i5); 1812 1813 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1814 s390_disasm(ENC6(MNM, GPR, GPR, UINT, UINT, UINT), mnm, r1, r2, i3, i4, 1815 i5); 1816 } 1817 1818 static void 1819 s390_format_RIE_RRPU(const HChar *(*irgen)(UChar r1, UChar r2, UShort i4, 1820 UChar m3), 1821 UChar r1, UChar r2, UShort i4, UChar m3) 1822 { 1823 const HChar *mnm = irgen(r1, r2, i4, m3); 1824 1825 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1826 s390_disasm(ENC5(XMNM, GPR, GPR, CABM, PCREL), S390_XMNM_CAB, mnm, m3, r1, 1827 r2, m3, (Int)(Short)i4); 1828 } 1829 1830 static void 1831 s390_format_RIE_RUPU(const HChar *(*irgen)(UChar r1, UChar m3, UShort i4, 1832 UChar i2), 1833 UChar r1, UChar m3, UShort i4, UChar i2) 1834 { 1835 const HChar *mnm = irgen(r1, m3, i4, i2); 1836 1837 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1838 s390_disasm(ENC5(XMNM, GPR, UINT, CABM, PCREL), S390_XMNM_CAB, mnm, m3, 1839 r1, i2, m3, (Int)(Short)i4); 1840 } 1841 1842 static void 1843 s390_format_RIE_RUPI(const HChar *(*irgen)(UChar r1, UChar m3, UShort i4, 1844 UChar i2), 1845 UChar r1, UChar m3, UShort i4, UChar i2) 1846 { 1847 const HChar *mnm = irgen(r1, m3, i4, i2); 1848 1849 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1850 s390_disasm(ENC5(XMNM, GPR, INT, CABM, PCREL), S390_XMNM_CAB, mnm, m3, r1, 1851 (Int)(Char)i2, m3, (Int)(Short)i4); 1852 } 1853 1854 static void 1855 s390_format_RIL(const HChar *(*irgen)(UChar r1, UInt i2), 1856 UChar r1, UInt i2) 1857 { 1858 irgen(r1, i2); 1859 } 1860 1861 static void 1862 s390_format_RIL_RU(const HChar *(*irgen)(UChar r1, UInt i2), 1863 UChar r1, UInt i2) 1864 { 1865 const HChar *mnm = irgen(r1, i2); 1866 1867 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1868 s390_disasm(ENC3(MNM, GPR, UINT), mnm, r1, i2); 1869 } 1870 1871 static void 1872 s390_format_RIL_RI(const HChar *(*irgen)(UChar r1, UInt i2), 1873 UChar r1, UInt i2) 1874 { 1875 const HChar *mnm = irgen(r1, i2); 1876 1877 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1878 s390_disasm(ENC3(MNM, GPR, INT), mnm, r1, i2); 1879 } 1880 1881 static void 1882 s390_format_RIL_RP(const HChar *(*irgen)(UChar r1, UInt i2), 1883 UChar r1, UInt i2) 1884 { 1885 const HChar *mnm = irgen(r1, i2); 1886 1887 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1888 s390_disasm(ENC3(MNM, GPR, PCREL), mnm, r1, i2); 1889 } 1890 1891 static void 1892 s390_format_RIL_UP(const HChar *(*irgen)(void), 1893 UChar r1, UInt i2) 1894 { 1895 const HChar *mnm = irgen(); 1896 1897 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1898 s390_disasm(ENC3(MNM, UINT, PCREL), mnm, r1, i2); 1899 } 1900 1901 static void 1902 s390_format_RIS_RURDI(const HChar *(*irgen)(UChar r1, UChar m3, UChar i2, 1903 IRTemp op4addr), 1904 UChar r1, UChar m3, UChar b4, UShort d4, UChar i2) 1905 { 1906 const HChar *mnm; 1907 IRTemp op4addr = newTemp(Ity_I64); 1908 1909 assign(op4addr, binop(Iop_Add64, mkU64(d4), b4 != 0 ? get_gpr_dw0(b4) : 1910 mkU64(0))); 1911 1912 mnm = irgen(r1, m3, i2, op4addr); 1913 1914 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1915 s390_disasm(ENC5(XMNM, GPR, INT, CABM, UDXB), S390_XMNM_CAB, mnm, m3, r1, 1916 (Int)(Char)i2, m3, d4, 0, b4); 1917 } 1918 1919 static void 1920 s390_format_RIS_RURDU(const HChar *(*irgen)(UChar r1, UChar m3, UChar i2, 1921 IRTemp op4addr), 1922 UChar r1, UChar m3, UChar b4, UShort d4, UChar i2) 1923 { 1924 const HChar *mnm; 1925 IRTemp op4addr = newTemp(Ity_I64); 1926 1927 assign(op4addr, binop(Iop_Add64, mkU64(d4), b4 != 0 ? get_gpr_dw0(b4) : 1928 mkU64(0))); 1929 1930 mnm = irgen(r1, m3, i2, op4addr); 1931 1932 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1933 s390_disasm(ENC5(XMNM, GPR, UINT, CABM, UDXB), S390_XMNM_CAB, mnm, m3, r1, 1934 i2, m3, d4, 0, b4); 1935 } 1936 1937 static void 1938 s390_format_RR(const HChar *(*irgen)(UChar r1, UChar r2), 1939 UChar r1, UChar r2) 1940 { 1941 irgen(r1, r2); 1942 } 1943 1944 static void 1945 s390_format_RR_RR(const HChar *(*irgen)(UChar r1, UChar r2), 1946 UChar r1, UChar r2) 1947 { 1948 const HChar *mnm = irgen(r1, r2); 1949 1950 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1951 s390_disasm(ENC3(MNM, GPR, GPR), mnm, r1, r2); 1952 } 1953 1954 static void 1955 s390_format_RR_FF(const HChar *(*irgen)(UChar r1, UChar r2), 1956 UChar r1, UChar r2) 1957 { 1958 const HChar *mnm = irgen(r1, r2); 1959 1960 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1961 s390_disasm(ENC3(MNM, FPR, FPR), mnm, r1, r2); 1962 } 1963 1964 static void 1965 s390_format_RRE(const HChar *(*irgen)(UChar r1, UChar r2), 1966 UChar r1, UChar r2) 1967 { 1968 irgen(r1, r2); 1969 } 1970 1971 static void 1972 s390_format_RRE_RR(const HChar *(*irgen)(UChar r1, UChar r2), 1973 UChar r1, UChar r2) 1974 { 1975 const HChar *mnm = irgen(r1, r2); 1976 1977 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1978 s390_disasm(ENC3(MNM, GPR, GPR), mnm, r1, r2); 1979 } 1980 1981 static void 1982 s390_format_RRE_FF(const HChar *(*irgen)(UChar r1, UChar r2), 1983 UChar r1, UChar r2) 1984 { 1985 const HChar *mnm = irgen(r1, r2); 1986 1987 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1988 s390_disasm(ENC3(MNM, FPR, FPR), mnm, r1, r2); 1989 } 1990 1991 static void 1992 s390_format_RRE_RF(const HChar *(*irgen)(UChar, UChar), 1993 UChar r1, UChar r2) 1994 { 1995 const HChar *mnm = irgen(r1, r2); 1996 1997 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 1998 s390_disasm(ENC3(MNM, GPR, FPR), mnm, r1, r2); 1999 } 2000 2001 static void 2002 s390_format_RRE_FR(const HChar *(*irgen)(UChar r1, UChar r2), 2003 UChar r1, UChar r2) 2004 { 2005 const HChar *mnm = irgen(r1, r2); 2006 2007 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2008 s390_disasm(ENC3(MNM, FPR, GPR), mnm, r1, r2); 2009 } 2010 2011 static void 2012 s390_format_RRE_R0(const HChar *(*irgen)(UChar r1), 2013 UChar r1) 2014 { 2015 const HChar *mnm = irgen(r1); 2016 2017 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2018 s390_disasm(ENC2(MNM, GPR), mnm, r1); 2019 } 2020 2021 static void 2022 s390_format_RRE_F0(const HChar *(*irgen)(UChar r1), 2023 UChar r1) 2024 { 2025 const HChar *mnm = irgen(r1); 2026 2027 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2028 s390_disasm(ENC2(MNM, FPR), mnm, r1); 2029 } 2030 2031 static void 2032 s390_format_RRF_M0RERE(const HChar *(*irgen)(UChar m3, UChar r1, UChar r2), 2033 UChar m3, UChar r1, UChar r2) 2034 { 2035 const HChar *mnm = irgen(m3, r1, r2); 2036 2037 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2038 s390_disasm(ENC4(MNM, GPR, GPR, UINT), mnm, r1, r2, m3); 2039 } 2040 2041 static void 2042 s390_format_RRF_F0FF(const HChar *(*irgen)(UChar, UChar, UChar), 2043 UChar r1, UChar r3, UChar r2) 2044 { 2045 const HChar *mnm = irgen(r1, r3, r2); 2046 2047 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2048 s390_disasm(ENC4(MNM, FPR, FPR, FPR), mnm, r1, r3, r2); 2049 } 2050 2051 static void 2052 s390_format_RRF_F0FR(const HChar *(*irgen)(UChar, UChar, UChar), 2053 UChar r3, UChar r1, UChar r2) 2054 { 2055 const HChar *mnm = irgen(r3, r1, r2); 2056 2057 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2058 s390_disasm(ENC4(MNM, FPR, FPR, GPR), mnm, r1, r3, r2); 2059 } 2060 2061 static void 2062 s390_format_RRF_UUFF(const HChar *(*irgen)(UChar m3, UChar m4, UChar r1, 2063 UChar r2), 2064 UChar m3, UChar m4, UChar r1, UChar r2) 2065 { 2066 const HChar *mnm = irgen(m3, m4, r1, r2); 2067 2068 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2069 s390_disasm(ENC5(MNM, FPR, UINT, FPR, UINT), mnm, r1, m3, r2, m4); 2070 } 2071 2072 static void 2073 s390_format_RRF_0UFF(const HChar *(*irgen)(UChar m4, UChar r1, UChar r2), 2074 UChar m4, UChar r1, UChar r2) 2075 { 2076 const HChar *mnm = irgen(m4, r1, r2); 2077 2078 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2079 s390_disasm(ENC4(MNM, FPR, FPR, UINT), mnm, r1, r2, m4); 2080 } 2081 2082 static void 2083 s390_format_RRF_UUFR(const HChar *(*irgen)(UChar m3, UChar m4, UChar r1, 2084 UChar r2), 2085 UChar m3, UChar m4, UChar r1, UChar r2) 2086 { 2087 const HChar *mnm = irgen(m3, m4, r1, r2); 2088 2089 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2090 s390_disasm(ENC5(MNM, FPR, UINT, GPR, UINT), mnm, r1, m3, r2, m4); 2091 } 2092 2093 static void 2094 s390_format_RRF_UURF(const HChar *(*irgen)(UChar m3, UChar m4, UChar r1, 2095 UChar r2), 2096 UChar m3, UChar m4, UChar r1, UChar r2) 2097 { 2098 const HChar *mnm = irgen(m3, m4, r1, r2); 2099 2100 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2101 s390_disasm(ENC5(MNM, GPR, UINT, FPR, UINT), mnm, r1, m3, r2, m4); 2102 } 2103 2104 2105 static void 2106 s390_format_RRF_U0RR(const HChar *(*irgen)(UChar m3, UChar r1, UChar r2), 2107 UChar m3, UChar r1, UChar r2, Int xmnm_kind) 2108 { 2109 irgen(m3, r1, r2); 2110 2111 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2112 s390_disasm(ENC3(XMNM, GPR, GPR), xmnm_kind, m3, r1, r2); 2113 } 2114 2115 static void 2116 s390_format_RRF_F0FF2(const HChar *(*irgen)(UChar, UChar, UChar), 2117 UChar r3, UChar r1, UChar r2) 2118 { 2119 const HChar *mnm = irgen(r3, r1, r2); 2120 2121 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2122 s390_disasm(ENC4(MNM, FPR, FPR, FPR), mnm, r1, r3, r2); 2123 } 2124 2125 static void 2126 s390_format_RRF_FFRU(const HChar *(*irgen)(UChar, UChar, UChar, UChar), 2127 UChar r3, UChar m4, UChar r1, UChar r2) 2128 { 2129 const HChar *mnm = irgen(r3, m4, r1, r2); 2130 2131 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2132 s390_disasm(ENC5(MNM, FPR, FPR, GPR, UINT), mnm, r1, r3, r2, m4); 2133 } 2134 2135 static void 2136 s390_format_RRF_FUFF(const HChar *(*irgen)(UChar, UChar, UChar, UChar), 2137 UChar r3, UChar m4, UChar r1, UChar r2) 2138 { 2139 const HChar *mnm = irgen(r3, m4, r1, r2); 2140 2141 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2142 s390_disasm(ENC5(MNM, FPR, FPR, FPR, UINT), mnm, r1, r3, r2, m4); 2143 } 2144 2145 static void 2146 s390_format_RRF_FUFF2(const HChar *(*irgen)(UChar, UChar, UChar, UChar), 2147 UChar r3, UChar m4, UChar r1, UChar r2) 2148 { 2149 const HChar *mnm = irgen(r3, m4, r1, r2); 2150 2151 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2152 s390_disasm(ENC5(MNM, FPR, FPR, FPR, UINT), mnm, r1, r2, r3, m4); 2153 } 2154 2155 static void 2156 s390_format_RRF_R0RR2(const HChar *(*irgen)(UChar r3, UChar r1, UChar r2), 2157 UChar r3, UChar r1, UChar r2) 2158 { 2159 const HChar *mnm = irgen(r3, r1, r2); 2160 2161 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2162 s390_disasm(ENC4(MNM, GPR, GPR, GPR), mnm, r1, r2, r3); 2163 } 2164 2165 static void 2166 s390_format_RRS(const HChar *(*irgen)(UChar r1, UChar r2, UChar m3, 2167 IRTemp op4addr), 2168 UChar r1, UChar r2, UChar b4, UShort d4, UChar m3) 2169 { 2170 const HChar *mnm; 2171 IRTemp op4addr = newTemp(Ity_I64); 2172 2173 assign(op4addr, binop(Iop_Add64, mkU64(d4), b4 != 0 ? get_gpr_dw0(b4) : 2174 mkU64(0))); 2175 2176 mnm = irgen(r1, r2, m3, op4addr); 2177 2178 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2179 s390_disasm(ENC5(XMNM, GPR, GPR, CABM, UDXB), S390_XMNM_CAB, mnm, m3, r1, 2180 r2, m3, d4, 0, b4); 2181 } 2182 2183 static void 2184 s390_format_RS_R0RD(const HChar *(*irgen)(UChar r1, IRTemp op2addr), 2185 UChar r1, UChar b2, UShort d2) 2186 { 2187 const HChar *mnm; 2188 IRTemp op2addr = newTemp(Ity_I64); 2189 2190 assign(op2addr, binop(Iop_Add64, mkU64(d2), b2 != 0 ? get_gpr_dw0(b2) : 2191 mkU64(0))); 2192 2193 mnm = irgen(r1, op2addr); 2194 2195 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2196 s390_disasm(ENC3(MNM, GPR, UDXB), mnm, r1, d2, 0, b2); 2197 } 2198 2199 static void 2200 s390_format_RS_RRRD(const HChar *(*irgen)(UChar r1, UChar r3, IRTemp op2addr), 2201 UChar r1, UChar r3, UChar b2, UShort d2) 2202 { 2203 const HChar *mnm; 2204 IRTemp op2addr = newTemp(Ity_I64); 2205 2206 assign(op2addr, binop(Iop_Add64, mkU64(d2), b2 != 0 ? get_gpr_dw0(b2) : 2207 mkU64(0))); 2208 2209 mnm = irgen(r1, r3, op2addr); 2210 2211 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2212 s390_disasm(ENC4(MNM, GPR, GPR, UDXB), mnm, r1, r3, d2, 0, b2); 2213 } 2214 2215 static void 2216 s390_format_RS_RURD(const HChar *(*irgen)(UChar r1, UChar r3, IRTemp op2addr), 2217 UChar r1, UChar r3, UChar b2, UShort d2) 2218 { 2219 const HChar *mnm; 2220 IRTemp op2addr = newTemp(Ity_I64); 2221 2222 assign(op2addr, binop(Iop_Add64, mkU64(d2), b2 != 0 ? get_gpr_dw0(b2) : 2223 mkU64(0))); 2224 2225 mnm = irgen(r1, r3, op2addr); 2226 2227 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2228 s390_disasm(ENC4(MNM, GPR, UINT, UDXB), mnm, r1, r3, d2, 0, b2); 2229 } 2230 2231 static void 2232 s390_format_RS_AARD(const HChar *(*irgen)(UChar, UChar, IRTemp), 2233 UChar r1, UChar r3, UChar b2, UShort d2) 2234 { 2235 const HChar *mnm; 2236 IRTemp op2addr = newTemp(Ity_I64); 2237 2238 assign(op2addr, binop(Iop_Add64, mkU64(d2), b2 != 0 ? get_gpr_dw0(b2) : 2239 mkU64(0))); 2240 2241 mnm = irgen(r1, r3, op2addr); 2242 2243 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2244 s390_disasm(ENC4(MNM, AR, AR, UDXB), mnm, r1, r3, d2, 0, b2); 2245 } 2246 2247 static void 2248 s390_format_RSI_RRP(const HChar *(*irgen)(UChar r1, UChar r3, UShort i2), 2249 UChar r1, UChar r3, UShort i2) 2250 { 2251 const HChar *mnm = irgen(r1, r3, i2); 2252 2253 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2254 s390_disasm(ENC4(MNM, GPR, GPR, PCREL), mnm, r1, r3, (Int)(Short)i2); 2255 } 2256 2257 static void 2258 s390_format_RSY_RRRD(const HChar *(*irgen)(UChar r1, UChar r3, IRTemp op2addr), 2259 UChar r1, UChar r3, UChar b2, UShort dl2, UChar dh2) 2260 { 2261 const HChar *mnm; 2262 IRTemp op2addr = newTemp(Ity_I64); 2263 IRTemp d2 = newTemp(Ity_I64); 2264 2265 assign(d2, mkU64(((ULong)(Long)(Char)dh2 << 12) | ((ULong)dl2))); 2266 assign(op2addr, binop(Iop_Add64, mkexpr(d2), b2 != 0 ? get_gpr_dw0(b2) : 2267 mkU64(0))); 2268 2269 mnm = irgen(r1, r3, op2addr); 2270 2271 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2272 s390_disasm(ENC4(MNM, GPR, GPR, SDXB), mnm, r1, r3, dh2, dl2, 0, b2); 2273 } 2274 2275 static void 2276 s390_format_RSY_AARD(const HChar *(*irgen)(UChar, UChar, IRTemp), 2277 UChar r1, UChar r3, UChar b2, UShort dl2, UChar dh2) 2278 { 2279 const HChar *mnm; 2280 IRTemp op2addr = newTemp(Ity_I64); 2281 IRTemp d2 = newTemp(Ity_I64); 2282 2283 assign(d2, mkU64(((ULong)(Long)(Char)dh2 << 12) | ((ULong)dl2))); 2284 assign(op2addr, binop(Iop_Add64, mkexpr(d2), b2 != 0 ? get_gpr_dw0(b2) : 2285 mkU64(0))); 2286 2287 mnm = irgen(r1, r3, op2addr); 2288 2289 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2290 s390_disasm(ENC4(MNM, AR, AR, SDXB), mnm, r1, r3, dh2, dl2, 0, b2); 2291 } 2292 2293 static void 2294 s390_format_RSY_RURD(const HChar *(*irgen)(UChar r1, UChar r3, IRTemp op2addr), 2295 UChar r1, UChar r3, UChar b2, UShort dl2, UChar dh2) 2296 { 2297 const HChar *mnm; 2298 IRTemp op2addr = newTemp(Ity_I64); 2299 IRTemp d2 = newTemp(Ity_I64); 2300 2301 assign(d2, mkU64(((ULong)(Long)(Char)dh2 << 12) | ((ULong)dl2))); 2302 assign(op2addr, binop(Iop_Add64, mkexpr(d2), b2 != 0 ? get_gpr_dw0(b2) : 2303 mkU64(0))); 2304 2305 mnm = irgen(r1, r3, op2addr); 2306 2307 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2308 s390_disasm(ENC4(MNM, GPR, UINT, SDXB), mnm, r1, r3, dh2, dl2, 0, b2); 2309 } 2310 2311 static void 2312 s390_format_RSY_RDRM(const HChar *(*irgen)(UChar r1, IRTemp op2addr), 2313 UChar r1, UChar m3, UChar b2, UShort dl2, UChar dh2, 2314 Int xmnm_kind) 2315 { 2316 IRTemp op2addr = newTemp(Ity_I64); 2317 IRTemp d2 = newTemp(Ity_I64); 2318 2319 next_insn_if(binop(Iop_CmpEQ32, s390_call_calculate_cond(m3), mkU32(0))); 2320 2321 assign(d2, mkU64(((ULong)(Long)(Char)dh2 << 12) | ((ULong)dl2))); 2322 assign(op2addr, binop(Iop_Add64, mkexpr(d2), b2 != 0 ? get_gpr_dw0(b2) : 2323 mkU64(0))); 2324 2325 irgen(r1, op2addr); 2326 2327 vassert(dis_res->whatNext == Dis_Continue); 2328 2329 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2330 s390_disasm(ENC3(XMNM, GPR, SDXB), xmnm_kind, m3, r1, dh2, dl2, 0, b2); 2331 } 2332 2333 static void 2334 s390_format_RX(const HChar *(*irgen)(UChar r1, UChar x2, UChar b2, UShort d2, 2335 IRTemp op2addr), 2336 UChar r1, UChar x2, UChar b2, UShort d2) 2337 { 2338 IRTemp op2addr = newTemp(Ity_I64); 2339 2340 assign(op2addr, binop(Iop_Add64, binop(Iop_Add64, mkU64(d2), 2341 b2 != 0 ? get_gpr_dw0(b2) : mkU64(0)), x2 != 0 ? get_gpr_dw0(x2) : 2342 mkU64(0))); 2343 2344 irgen(r1, x2, b2, d2, op2addr); 2345 } 2346 2347 static void 2348 s390_format_RX_RRRD(const HChar *(*irgen)(UChar r1, IRTemp op2addr), 2349 UChar r1, UChar x2, UChar b2, UShort d2) 2350 { 2351 const HChar *mnm; 2352 IRTemp op2addr = newTemp(Ity_I64); 2353 2354 assign(op2addr, binop(Iop_Add64, binop(Iop_Add64, mkU64(d2), 2355 b2 != 0 ? get_gpr_dw0(b2) : mkU64(0)), x2 != 0 ? get_gpr_dw0(x2) : 2356 mkU64(0))); 2357 2358 mnm = irgen(r1, op2addr); 2359 2360 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2361 s390_disasm(ENC3(MNM, GPR, UDXB), mnm, r1, d2, x2, b2); 2362 } 2363 2364 static void 2365 s390_format_RX_FRRD(const HChar *(*irgen)(UChar r1, IRTemp op2addr), 2366 UChar r1, UChar x2, UChar b2, UShort d2) 2367 { 2368 const HChar *mnm; 2369 IRTemp op2addr = newTemp(Ity_I64); 2370 2371 assign(op2addr, binop(Iop_Add64, binop(Iop_Add64, mkU64(d2), 2372 b2 != 0 ? get_gpr_dw0(b2) : mkU64(0)), x2 != 0 ? get_gpr_dw0(x2) : 2373 mkU64(0))); 2374 2375 mnm = irgen(r1, op2addr); 2376 2377 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2378 s390_disasm(ENC3(MNM, FPR, UDXB), mnm, r1, d2, x2, b2); 2379 } 2380 2381 static void 2382 s390_format_RXE_FRRD(const HChar *(*irgen)(UChar r1, IRTemp op2addr), 2383 UChar r1, UChar x2, UChar b2, UShort d2) 2384 { 2385 const HChar *mnm; 2386 IRTemp op2addr = newTemp(Ity_I64); 2387 2388 assign(op2addr, binop(Iop_Add64, binop(Iop_Add64, mkU64(d2), 2389 b2 != 0 ? get_gpr_dw0(b2) : mkU64(0)), x2 != 0 ? get_gpr_dw0(x2) : 2390 mkU64(0))); 2391 2392 mnm = irgen(r1, op2addr); 2393 2394 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2395 s390_disasm(ENC3(MNM, FPR, UDXB), mnm, r1, d2, x2, b2); 2396 } 2397 2398 static void 2399 s390_format_RXF_FRRDF(const HChar *(*irgen)(UChar, IRTemp, UChar), 2400 UChar r3, UChar x2, UChar b2, UShort d2, UChar r1) 2401 { 2402 const HChar *mnm; 2403 IRTemp op2addr = newTemp(Ity_I64); 2404 2405 assign(op2addr, binop(Iop_Add64, binop(Iop_Add64, mkU64(d2), 2406 b2 != 0 ? get_gpr_dw0(b2) : mkU64(0)), x2 != 0 ? get_gpr_dw0(x2) : 2407 mkU64(0))); 2408 2409 mnm = irgen(r3, op2addr, r1); 2410 2411 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2412 s390_disasm(ENC4(MNM, FPR, FPR, UDXB), mnm, r1, r3, d2, x2, b2); 2413 } 2414 2415 static void 2416 s390_format_RXY_RRRD(const HChar *(*irgen)(UChar r1, IRTemp op2addr), 2417 UChar r1, UChar x2, UChar b2, UShort dl2, UChar dh2) 2418 { 2419 const HChar *mnm; 2420 IRTemp op2addr = newTemp(Ity_I64); 2421 IRTemp d2 = newTemp(Ity_I64); 2422 2423 assign(d2, mkU64(((ULong)(Long)(Char)dh2 << 12) | ((ULong)dl2))); 2424 assign(op2addr, binop(Iop_Add64, binop(Iop_Add64, mkexpr(d2), 2425 b2 != 0 ? get_gpr_dw0(b2) : mkU64(0)), x2 != 0 ? get_gpr_dw0(x2) : 2426 mkU64(0))); 2427 2428 mnm = irgen(r1, op2addr); 2429 2430 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2431 s390_disasm(ENC3(MNM, GPR, SDXB), mnm, r1, dh2, dl2, x2, b2); 2432 } 2433 2434 static void 2435 s390_format_RXY_FRRD(const HChar *(*irgen)(UChar r1, IRTemp op2addr), 2436 UChar r1, UChar x2, UChar b2, UShort dl2, UChar dh2) 2437 { 2438 const HChar *mnm; 2439 IRTemp op2addr = newTemp(Ity_I64); 2440 IRTemp d2 = newTemp(Ity_I64); 2441 2442 assign(d2, mkU64(((ULong)(Long)(Char)dh2 << 12) | ((ULong)dl2))); 2443 assign(op2addr, binop(Iop_Add64, binop(Iop_Add64, mkexpr(d2), 2444 b2 != 0 ? get_gpr_dw0(b2) : mkU64(0)), x2 != 0 ? get_gpr_dw0(x2) : 2445 mkU64(0))); 2446 2447 mnm = irgen(r1, op2addr); 2448 2449 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2450 s390_disasm(ENC3(MNM, FPR, SDXB), mnm, r1, dh2, dl2, x2, b2); 2451 } 2452 2453 static void 2454 s390_format_RXY_URRD(const HChar *(*irgen)(void), 2455 UChar r1, UChar x2, UChar b2, UShort dl2, UChar dh2) 2456 { 2457 const HChar *mnm; 2458 IRTemp op2addr = newTemp(Ity_I64); 2459 IRTemp d2 = newTemp(Ity_I64); 2460 2461 assign(d2, mkU64(((ULong)(Long)(Char)dh2 << 12) | ((ULong)dl2))); 2462 assign(op2addr, binop(Iop_Add64, binop(Iop_Add64, mkexpr(d2), 2463 b2 != 0 ? get_gpr_dw0(b2) : mkU64(0)), x2 != 0 ? get_gpr_dw0(x2) : 2464 mkU64(0))); 2465 2466 mnm = irgen(); 2467 2468 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2469 s390_disasm(ENC3(MNM, UINT, SDXB), mnm, r1, dh2, dl2, x2, b2); 2470 } 2471 2472 static void 2473 s390_format_S_RD(const HChar *(*irgen)(IRTemp op2addr), 2474 UChar b2, UShort d2) 2475 { 2476 const HChar *mnm; 2477 IRTemp op2addr = newTemp(Ity_I64); 2478 2479 assign(op2addr, binop(Iop_Add64, mkU64(d2), b2 != 0 ? get_gpr_dw0(b2) : 2480 mkU64(0))); 2481 2482 mnm = irgen(op2addr); 2483 2484 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2485 s390_disasm(ENC2(MNM, UDXB), mnm, d2, 0, b2); 2486 } 2487 2488 static void 2489 s390_format_SI_URD(const HChar *(*irgen)(UChar i2, IRTemp op1addr), 2490 UChar i2, UChar b1, UShort d1) 2491 { 2492 const HChar *mnm; 2493 IRTemp op1addr = newTemp(Ity_I64); 2494 2495 assign(op1addr, binop(Iop_Add64, mkU64(d1), b1 != 0 ? get_gpr_dw0(b1) : 2496 mkU64(0))); 2497 2498 mnm = irgen(i2, op1addr); 2499 2500 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2501 s390_disasm(ENC3(MNM, UDXB, UINT), mnm, d1, 0, b1, i2); 2502 } 2503 2504 static void 2505 s390_format_SIY_URD(const HChar *(*irgen)(UChar i2, IRTemp op1addr), 2506 UChar i2, UChar b1, UShort dl1, UChar dh1) 2507 { 2508 const HChar *mnm; 2509 IRTemp op1addr = newTemp(Ity_I64); 2510 IRTemp d1 = newTemp(Ity_I64); 2511 2512 assign(d1, mkU64(((ULong)(Long)(Char)dh1 << 12) | ((ULong)dl1))); 2513 assign(op1addr, binop(Iop_Add64, mkexpr(d1), b1 != 0 ? get_gpr_dw0(b1) : 2514 mkU64(0))); 2515 2516 mnm = irgen(i2, op1addr); 2517 2518 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2519 s390_disasm(ENC3(MNM, SDXB, UINT), mnm, dh1, dl1, 0, b1, i2); 2520 } 2521 2522 static void 2523 s390_format_SIY_IRD(const HChar *(*irgen)(UChar i2, IRTemp op1addr), 2524 UChar i2, UChar b1, UShort dl1, UChar dh1) 2525 { 2526 const HChar *mnm; 2527 IRTemp op1addr = newTemp(Ity_I64); 2528 IRTemp d1 = newTemp(Ity_I64); 2529 2530 assign(d1, mkU64(((ULong)(Long)(Char)dh1 << 12) | ((ULong)dl1))); 2531 assign(op1addr, binop(Iop_Add64, mkexpr(d1), b1 != 0 ? get_gpr_dw0(b1) : 2532 mkU64(0))); 2533 2534 mnm = irgen(i2, op1addr); 2535 2536 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2537 s390_disasm(ENC3(MNM, SDXB, INT), mnm, dh1, dl1, 0, b1, (Int)(Char)i2); 2538 } 2539 2540 static void 2541 s390_format_SS_L0RDRD(const HChar *(*irgen)(UChar, IRTemp, IRTemp), 2542 UChar l, UChar b1, UShort d1, UChar b2, UShort d2) 2543 { 2544 const HChar *mnm; 2545 IRTemp op1addr = newTemp(Ity_I64); 2546 IRTemp op2addr = newTemp(Ity_I64); 2547 2548 assign(op1addr, binop(Iop_Add64, mkU64(d1), b1 != 0 ? get_gpr_dw0(b1) : 2549 mkU64(0))); 2550 assign(op2addr, binop(Iop_Add64, mkU64(d2), b2 != 0 ? get_gpr_dw0(b2) : 2551 mkU64(0))); 2552 2553 mnm = irgen(l, op1addr, op2addr); 2554 2555 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2556 s390_disasm(ENC3(MNM, UDLB, UDXB), mnm, d1, l, b1, d2, 0, b2); 2557 } 2558 2559 static void 2560 s390_format_SIL_RDI(const HChar *(*irgen)(UShort i2, IRTemp op1addr), 2561 UChar b1, UShort d1, UShort i2) 2562 { 2563 const HChar *mnm; 2564 IRTemp op1addr = newTemp(Ity_I64); 2565 2566 assign(op1addr, binop(Iop_Add64, mkU64(d1), b1 != 0 ? get_gpr_dw0(b1) : 2567 mkU64(0))); 2568 2569 mnm = irgen(i2, op1addr); 2570 2571 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2572 s390_disasm(ENC3(MNM, UDXB, INT), mnm, d1, 0, b1, (Int)(Short)i2); 2573 } 2574 2575 static void 2576 s390_format_SIL_RDU(const HChar *(*irgen)(UShort i2, IRTemp op1addr), 2577 UChar b1, UShort d1, UShort i2) 2578 { 2579 const HChar *mnm; 2580 IRTemp op1addr = newTemp(Ity_I64); 2581 2582 assign(op1addr, binop(Iop_Add64, mkU64(d1), b1 != 0 ? get_gpr_dw0(b1) : 2583 mkU64(0))); 2584 2585 mnm = irgen(i2, op1addr); 2586 2587 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 2588 s390_disasm(ENC3(MNM, UDXB, UINT), mnm, d1, 0, b1, i2); 2589 } 2590 2591 2592 2593 /*------------------------------------------------------------*/ 2594 /*--- Build IR for opcodes ---*/ 2595 /*------------------------------------------------------------*/ 2596 2597 static const HChar * 2598 s390_irgen_AR(UChar r1, UChar r2) 2599 { 2600 IRTemp op1 = newTemp(Ity_I32); 2601 IRTemp op2 = newTemp(Ity_I32); 2602 IRTemp result = newTemp(Ity_I32); 2603 2604 assign(op1, get_gpr_w1(r1)); 2605 assign(op2, get_gpr_w1(r2)); 2606 assign(result, binop(Iop_Add32, mkexpr(op1), mkexpr(op2))); 2607 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_32, op1, op2); 2608 put_gpr_w1(r1, mkexpr(result)); 2609 2610 return "ar"; 2611 } 2612 2613 static const HChar * 2614 s390_irgen_AGR(UChar r1, UChar r2) 2615 { 2616 IRTemp op1 = newTemp(Ity_I64); 2617 IRTemp op2 = newTemp(Ity_I64); 2618 IRTemp result = newTemp(Ity_I64); 2619 2620 assign(op1, get_gpr_dw0(r1)); 2621 assign(op2, get_gpr_dw0(r2)); 2622 assign(result, binop(Iop_Add64, mkexpr(op1), mkexpr(op2))); 2623 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_64, op1, op2); 2624 put_gpr_dw0(r1, mkexpr(result)); 2625 2626 return "agr"; 2627 } 2628 2629 static const HChar * 2630 s390_irgen_AGFR(UChar r1, UChar r2) 2631 { 2632 IRTemp op1 = newTemp(Ity_I64); 2633 IRTemp op2 = newTemp(Ity_I64); 2634 IRTemp result = newTemp(Ity_I64); 2635 2636 assign(op1, get_gpr_dw0(r1)); 2637 assign(op2, unop(Iop_32Sto64, get_gpr_w1(r2))); 2638 assign(result, binop(Iop_Add64, mkexpr(op1), mkexpr(op2))); 2639 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_64, op1, op2); 2640 put_gpr_dw0(r1, mkexpr(result)); 2641 2642 return "agfr"; 2643 } 2644 2645 static const HChar * 2646 s390_irgen_ARK(UChar r3, UChar r1, UChar r2) 2647 { 2648 IRTemp op2 = newTemp(Ity_I32); 2649 IRTemp op3 = newTemp(Ity_I32); 2650 IRTemp result = newTemp(Ity_I32); 2651 2652 assign(op2, get_gpr_w1(r2)); 2653 assign(op3, get_gpr_w1(r3)); 2654 assign(result, binop(Iop_Add32, mkexpr(op2), mkexpr(op3))); 2655 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_32, op2, op3); 2656 put_gpr_w1(r1, mkexpr(result)); 2657 2658 return "ark"; 2659 } 2660 2661 static const HChar * 2662 s390_irgen_AGRK(UChar r3, UChar r1, UChar r2) 2663 { 2664 IRTemp op2 = newTemp(Ity_I64); 2665 IRTemp op3 = newTemp(Ity_I64); 2666 IRTemp result = newTemp(Ity_I64); 2667 2668 assign(op2, get_gpr_dw0(r2)); 2669 assign(op3, get_gpr_dw0(r3)); 2670 assign(result, binop(Iop_Add64, mkexpr(op2), mkexpr(op3))); 2671 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_64, op2, op3); 2672 put_gpr_dw0(r1, mkexpr(result)); 2673 2674 return "agrk"; 2675 } 2676 2677 static const HChar * 2678 s390_irgen_A(UChar r1, IRTemp op2addr) 2679 { 2680 IRTemp op1 = newTemp(Ity_I32); 2681 IRTemp op2 = newTemp(Ity_I32); 2682 IRTemp result = newTemp(Ity_I32); 2683 2684 assign(op1, get_gpr_w1(r1)); 2685 assign(op2, load(Ity_I32, mkexpr(op2addr))); 2686 assign(result, binop(Iop_Add32, mkexpr(op1), mkexpr(op2))); 2687 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_32, op1, op2); 2688 put_gpr_w1(r1, mkexpr(result)); 2689 2690 return "a"; 2691 } 2692 2693 static const HChar * 2694 s390_irgen_AY(UChar r1, IRTemp op2addr) 2695 { 2696 IRTemp op1 = newTemp(Ity_I32); 2697 IRTemp op2 = newTemp(Ity_I32); 2698 IRTemp result = newTemp(Ity_I32); 2699 2700 assign(op1, get_gpr_w1(r1)); 2701 assign(op2, load(Ity_I32, mkexpr(op2addr))); 2702 assign(result, binop(Iop_Add32, mkexpr(op1), mkexpr(op2))); 2703 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_32, op1, op2); 2704 put_gpr_w1(r1, mkexpr(result)); 2705 2706 return "ay"; 2707 } 2708 2709 static const HChar * 2710 s390_irgen_AG(UChar r1, IRTemp op2addr) 2711 { 2712 IRTemp op1 = newTemp(Ity_I64); 2713 IRTemp op2 = newTemp(Ity_I64); 2714 IRTemp result = newTemp(Ity_I64); 2715 2716 assign(op1, get_gpr_dw0(r1)); 2717 assign(op2, load(Ity_I64, mkexpr(op2addr))); 2718 assign(result, binop(Iop_Add64, mkexpr(op1), mkexpr(op2))); 2719 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_64, op1, op2); 2720 put_gpr_dw0(r1, mkexpr(result)); 2721 2722 return "ag"; 2723 } 2724 2725 static const HChar * 2726 s390_irgen_AGF(UChar r1, IRTemp op2addr) 2727 { 2728 IRTemp op1 = newTemp(Ity_I64); 2729 IRTemp op2 = newTemp(Ity_I64); 2730 IRTemp result = newTemp(Ity_I64); 2731 2732 assign(op1, get_gpr_dw0(r1)); 2733 assign(op2, unop(Iop_32Sto64, load(Ity_I32, mkexpr(op2addr)))); 2734 assign(result, binop(Iop_Add64, mkexpr(op1), mkexpr(op2))); 2735 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_64, op1, op2); 2736 put_gpr_dw0(r1, mkexpr(result)); 2737 2738 return "agf"; 2739 } 2740 2741 static const HChar * 2742 s390_irgen_AFI(UChar r1, UInt i2) 2743 { 2744 IRTemp op1 = newTemp(Ity_I32); 2745 Int op2; 2746 IRTemp result = newTemp(Ity_I32); 2747 2748 assign(op1, get_gpr_w1(r1)); 2749 op2 = (Int)i2; 2750 assign(result, binop(Iop_Add32, mkexpr(op1), mkU32((UInt)op2))); 2751 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_32, op1, mktemp(Ity_I32, 2752 mkU32((UInt)op2))); 2753 put_gpr_w1(r1, mkexpr(result)); 2754 2755 return "afi"; 2756 } 2757 2758 static const HChar * 2759 s390_irgen_AGFI(UChar r1, UInt i2) 2760 { 2761 IRTemp op1 = newTemp(Ity_I64); 2762 Long op2; 2763 IRTemp result = newTemp(Ity_I64); 2764 2765 assign(op1, get_gpr_dw0(r1)); 2766 op2 = (Long)(Int)i2; 2767 assign(result, binop(Iop_Add64, mkexpr(op1), mkU64((ULong)op2))); 2768 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_64, op1, mktemp(Ity_I64, 2769 mkU64((ULong)op2))); 2770 put_gpr_dw0(r1, mkexpr(result)); 2771 2772 return "agfi"; 2773 } 2774 2775 static const HChar * 2776 s390_irgen_AHIK(UChar r1, UChar r3, UShort i2) 2777 { 2778 Int op2; 2779 IRTemp op3 = newTemp(Ity_I32); 2780 IRTemp result = newTemp(Ity_I32); 2781 2782 op2 = (Int)(Short)i2; 2783 assign(op3, get_gpr_w1(r3)); 2784 assign(result, binop(Iop_Add32, mkU32((UInt)op2), mkexpr(op3))); 2785 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_32, mktemp(Ity_I32, mkU32((UInt) 2786 op2)), op3); 2787 put_gpr_w1(r1, mkexpr(result)); 2788 2789 return "ahik"; 2790 } 2791 2792 static const HChar * 2793 s390_irgen_AGHIK(UChar r1, UChar r3, UShort i2) 2794 { 2795 Long op2; 2796 IRTemp op3 = newTemp(Ity_I64); 2797 IRTemp result = newTemp(Ity_I64); 2798 2799 op2 = (Long)(Short)i2; 2800 assign(op3, get_gpr_dw0(r3)); 2801 assign(result, binop(Iop_Add64, mkU64((ULong)op2), mkexpr(op3))); 2802 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_64, mktemp(Ity_I64, mkU64((ULong) 2803 op2)), op3); 2804 put_gpr_dw0(r1, mkexpr(result)); 2805 2806 return "aghik"; 2807 } 2808 2809 static const HChar * 2810 s390_irgen_ASI(UChar i2, IRTemp op1addr) 2811 { 2812 IRTemp op1 = newTemp(Ity_I32); 2813 Int op2; 2814 IRTemp result = newTemp(Ity_I32); 2815 2816 assign(op1, load(Ity_I32, mkexpr(op1addr))); 2817 op2 = (Int)(Char)i2; 2818 assign(result, binop(Iop_Add32, mkexpr(op1), mkU32((UInt)op2))); 2819 store(mkexpr(op1addr), mkexpr(result)); 2820 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_32, op1, mktemp(Ity_I32, 2821 mkU32((UInt)op2))); 2822 2823 return "asi"; 2824 } 2825 2826 static const HChar * 2827 s390_irgen_AGSI(UChar i2, IRTemp op1addr) 2828 { 2829 IRTemp op1 = newTemp(Ity_I64); 2830 Long op2; 2831 IRTemp result = newTemp(Ity_I64); 2832 2833 assign(op1, load(Ity_I64, mkexpr(op1addr))); 2834 op2 = (Long)(Char)i2; 2835 assign(result, binop(Iop_Add64, mkexpr(op1), mkU64((ULong)op2))); 2836 store(mkexpr(op1addr), mkexpr(result)); 2837 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_64, op1, mktemp(Ity_I64, 2838 mkU64((ULong)op2))); 2839 2840 return "agsi"; 2841 } 2842 2843 static const HChar * 2844 s390_irgen_AH(UChar r1, IRTemp op2addr) 2845 { 2846 IRTemp op1 = newTemp(Ity_I32); 2847 IRTemp op2 = newTemp(Ity_I32); 2848 IRTemp result = newTemp(Ity_I32); 2849 2850 assign(op1, get_gpr_w1(r1)); 2851 assign(op2, unop(Iop_16Sto32, load(Ity_I16, mkexpr(op2addr)))); 2852 assign(result, binop(Iop_Add32, mkexpr(op1), mkexpr(op2))); 2853 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_32, op1, op2); 2854 put_gpr_w1(r1, mkexpr(result)); 2855 2856 return "ah"; 2857 } 2858 2859 static const HChar * 2860 s390_irgen_AHY(UChar r1, IRTemp op2addr) 2861 { 2862 IRTemp op1 = newTemp(Ity_I32); 2863 IRTemp op2 = newTemp(Ity_I32); 2864 IRTemp result = newTemp(Ity_I32); 2865 2866 assign(op1, get_gpr_w1(r1)); 2867 assign(op2, unop(Iop_16Sto32, load(Ity_I16, mkexpr(op2addr)))); 2868 assign(result, binop(Iop_Add32, mkexpr(op1), mkexpr(op2))); 2869 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_32, op1, op2); 2870 put_gpr_w1(r1, mkexpr(result)); 2871 2872 return "ahy"; 2873 } 2874 2875 static const HChar * 2876 s390_irgen_AHI(UChar r1, UShort i2) 2877 { 2878 IRTemp op1 = newTemp(Ity_I32); 2879 Int op2; 2880 IRTemp result = newTemp(Ity_I32); 2881 2882 assign(op1, get_gpr_w1(r1)); 2883 op2 = (Int)(Short)i2; 2884 assign(result, binop(Iop_Add32, mkexpr(op1), mkU32((UInt)op2))); 2885 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_32, op1, mktemp(Ity_I32, 2886 mkU32((UInt)op2))); 2887 put_gpr_w1(r1, mkexpr(result)); 2888 2889 return "ahi"; 2890 } 2891 2892 static const HChar * 2893 s390_irgen_AGHI(UChar r1, UShort i2) 2894 { 2895 IRTemp op1 = newTemp(Ity_I64); 2896 Long op2; 2897 IRTemp result = newTemp(Ity_I64); 2898 2899 assign(op1, get_gpr_dw0(r1)); 2900 op2 = (Long)(Short)i2; 2901 assign(result, binop(Iop_Add64, mkexpr(op1), mkU64((ULong)op2))); 2902 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_64, op1, mktemp(Ity_I64, 2903 mkU64((ULong)op2))); 2904 put_gpr_dw0(r1, mkexpr(result)); 2905 2906 return "aghi"; 2907 } 2908 2909 static const HChar * 2910 s390_irgen_AHHHR(UChar r3, UChar r1, UChar r2) 2911 { 2912 IRTemp op2 = newTemp(Ity_I32); 2913 IRTemp op3 = newTemp(Ity_I32); 2914 IRTemp result = newTemp(Ity_I32); 2915 2916 assign(op2, get_gpr_w0(r2)); 2917 assign(op3, get_gpr_w0(r3)); 2918 assign(result, binop(Iop_Add32, mkexpr(op2), mkexpr(op3))); 2919 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_32, op2, op3); 2920 put_gpr_w0(r1, mkexpr(result)); 2921 2922 return "ahhhr"; 2923 } 2924 2925 static const HChar * 2926 s390_irgen_AHHLR(UChar r3, UChar r1, UChar r2) 2927 { 2928 IRTemp op2 = newTemp(Ity_I32); 2929 IRTemp op3 = newTemp(Ity_I32); 2930 IRTemp result = newTemp(Ity_I32); 2931 2932 assign(op2, get_gpr_w0(r2)); 2933 assign(op3, get_gpr_w1(r3)); 2934 assign(result, binop(Iop_Add32, mkexpr(op2), mkexpr(op3))); 2935 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_32, op2, op3); 2936 put_gpr_w0(r1, mkexpr(result)); 2937 2938 return "ahhlr"; 2939 } 2940 2941 static const HChar * 2942 s390_irgen_AIH(UChar r1, UInt i2) 2943 { 2944 IRTemp op1 = newTemp(Ity_I32); 2945 Int op2; 2946 IRTemp result = newTemp(Ity_I32); 2947 2948 assign(op1, get_gpr_w0(r1)); 2949 op2 = (Int)i2; 2950 assign(result, binop(Iop_Add32, mkexpr(op1), mkU32((UInt)op2))); 2951 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_32, op1, mktemp(Ity_I32, 2952 mkU32((UInt)op2))); 2953 put_gpr_w0(r1, mkexpr(result)); 2954 2955 return "aih"; 2956 } 2957 2958 static const HChar * 2959 s390_irgen_ALR(UChar r1, UChar r2) 2960 { 2961 IRTemp op1 = newTemp(Ity_I32); 2962 IRTemp op2 = newTemp(Ity_I32); 2963 IRTemp result = newTemp(Ity_I32); 2964 2965 assign(op1, get_gpr_w1(r1)); 2966 assign(op2, get_gpr_w1(r2)); 2967 assign(result, binop(Iop_Add32, mkexpr(op1), mkexpr(op2))); 2968 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_32, op1, op2); 2969 put_gpr_w1(r1, mkexpr(result)); 2970 2971 return "alr"; 2972 } 2973 2974 static const HChar * 2975 s390_irgen_ALGR(UChar r1, UChar r2) 2976 { 2977 IRTemp op1 = newTemp(Ity_I64); 2978 IRTemp op2 = newTemp(Ity_I64); 2979 IRTemp result = newTemp(Ity_I64); 2980 2981 assign(op1, get_gpr_dw0(r1)); 2982 assign(op2, get_gpr_dw0(r2)); 2983 assign(result, binop(Iop_Add64, mkexpr(op1), mkexpr(op2))); 2984 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_64, op1, op2); 2985 put_gpr_dw0(r1, mkexpr(result)); 2986 2987 return "algr"; 2988 } 2989 2990 static const HChar * 2991 s390_irgen_ALGFR(UChar r1, UChar r2) 2992 { 2993 IRTemp op1 = newTemp(Ity_I64); 2994 IRTemp op2 = newTemp(Ity_I64); 2995 IRTemp result = newTemp(Ity_I64); 2996 2997 assign(op1, get_gpr_dw0(r1)); 2998 assign(op2, unop(Iop_32Uto64, get_gpr_w1(r2))); 2999 assign(result, binop(Iop_Add64, mkexpr(op1), mkexpr(op2))); 3000 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_64, op1, op2); 3001 put_gpr_dw0(r1, mkexpr(result)); 3002 3003 return "algfr"; 3004 } 3005 3006 static const HChar * 3007 s390_irgen_ALRK(UChar r3, UChar r1, UChar r2) 3008 { 3009 IRTemp op2 = newTemp(Ity_I32); 3010 IRTemp op3 = newTemp(Ity_I32); 3011 IRTemp result = newTemp(Ity_I32); 3012 3013 assign(op2, get_gpr_w1(r2)); 3014 assign(op3, get_gpr_w1(r3)); 3015 assign(result, binop(Iop_Add32, mkexpr(op2), mkexpr(op3))); 3016 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_32, op2, op3); 3017 put_gpr_w1(r1, mkexpr(result)); 3018 3019 return "alrk"; 3020 } 3021 3022 static const HChar * 3023 s390_irgen_ALGRK(UChar r3, UChar r1, UChar r2) 3024 { 3025 IRTemp op2 = newTemp(Ity_I64); 3026 IRTemp op3 = newTemp(Ity_I64); 3027 IRTemp result = newTemp(Ity_I64); 3028 3029 assign(op2, get_gpr_dw0(r2)); 3030 assign(op3, get_gpr_dw0(r3)); 3031 assign(result, binop(Iop_Add64, mkexpr(op2), mkexpr(op3))); 3032 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_64, op2, op3); 3033 put_gpr_dw0(r1, mkexpr(result)); 3034 3035 return "algrk"; 3036 } 3037 3038 static const HChar * 3039 s390_irgen_AL(UChar r1, IRTemp op2addr) 3040 { 3041 IRTemp op1 = newTemp(Ity_I32); 3042 IRTemp op2 = newTemp(Ity_I32); 3043 IRTemp result = newTemp(Ity_I32); 3044 3045 assign(op1, get_gpr_w1(r1)); 3046 assign(op2, load(Ity_I32, mkexpr(op2addr))); 3047 assign(result, binop(Iop_Add32, mkexpr(op1), mkexpr(op2))); 3048 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_32, op1, op2); 3049 put_gpr_w1(r1, mkexpr(result)); 3050 3051 return "al"; 3052 } 3053 3054 static const HChar * 3055 s390_irgen_ALY(UChar r1, IRTemp op2addr) 3056 { 3057 IRTemp op1 = newTemp(Ity_I32); 3058 IRTemp op2 = newTemp(Ity_I32); 3059 IRTemp result = newTemp(Ity_I32); 3060 3061 assign(op1, get_gpr_w1(r1)); 3062 assign(op2, load(Ity_I32, mkexpr(op2addr))); 3063 assign(result, binop(Iop_Add32, mkexpr(op1), mkexpr(op2))); 3064 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_32, op1, op2); 3065 put_gpr_w1(r1, mkexpr(result)); 3066 3067 return "aly"; 3068 } 3069 3070 static const HChar * 3071 s390_irgen_ALG(UChar r1, IRTemp op2addr) 3072 { 3073 IRTemp op1 = newTemp(Ity_I64); 3074 IRTemp op2 = newTemp(Ity_I64); 3075 IRTemp result = newTemp(Ity_I64); 3076 3077 assign(op1, get_gpr_dw0(r1)); 3078 assign(op2, load(Ity_I64, mkexpr(op2addr))); 3079 assign(result, binop(Iop_Add64, mkexpr(op1), mkexpr(op2))); 3080 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_64, op1, op2); 3081 put_gpr_dw0(r1, mkexpr(result)); 3082 3083 return "alg"; 3084 } 3085 3086 static const HChar * 3087 s390_irgen_ALGF(UChar r1, IRTemp op2addr) 3088 { 3089 IRTemp op1 = newTemp(Ity_I64); 3090 IRTemp op2 = newTemp(Ity_I64); 3091 IRTemp result = newTemp(Ity_I64); 3092 3093 assign(op1, get_gpr_dw0(r1)); 3094 assign(op2, unop(Iop_32Uto64, load(Ity_I32, mkexpr(op2addr)))); 3095 assign(result, binop(Iop_Add64, mkexpr(op1), mkexpr(op2))); 3096 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_64, op1, op2); 3097 put_gpr_dw0(r1, mkexpr(result)); 3098 3099 return "algf"; 3100 } 3101 3102 static const HChar * 3103 s390_irgen_ALFI(UChar r1, UInt i2) 3104 { 3105 IRTemp op1 = newTemp(Ity_I32); 3106 UInt op2; 3107 IRTemp result = newTemp(Ity_I32); 3108 3109 assign(op1, get_gpr_w1(r1)); 3110 op2 = i2; 3111 assign(result, binop(Iop_Add32, mkexpr(op1), mkU32(op2))); 3112 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_32, op1, mktemp(Ity_I32, 3113 mkU32(op2))); 3114 put_gpr_w1(r1, mkexpr(result)); 3115 3116 return "alfi"; 3117 } 3118 3119 static const HChar * 3120 s390_irgen_ALGFI(UChar r1, UInt i2) 3121 { 3122 IRTemp op1 = newTemp(Ity_I64); 3123 ULong op2; 3124 IRTemp result = newTemp(Ity_I64); 3125 3126 assign(op1, get_gpr_dw0(r1)); 3127 op2 = (ULong)i2; 3128 assign(result, binop(Iop_Add64, mkexpr(op1), mkU64(op2))); 3129 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_64, op1, mktemp(Ity_I64, 3130 mkU64(op2))); 3131 put_gpr_dw0(r1, mkexpr(result)); 3132 3133 return "algfi"; 3134 } 3135 3136 static const HChar * 3137 s390_irgen_ALHHHR(UChar r3, UChar r1, UChar r2) 3138 { 3139 IRTemp op2 = newTemp(Ity_I32); 3140 IRTemp op3 = newTemp(Ity_I32); 3141 IRTemp result = newTemp(Ity_I32); 3142 3143 assign(op2, get_gpr_w0(r2)); 3144 assign(op3, get_gpr_w0(r3)); 3145 assign(result, binop(Iop_Add32, mkexpr(op2), mkexpr(op3))); 3146 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_32, op2, op3); 3147 put_gpr_w0(r1, mkexpr(result)); 3148 3149 return "alhhhr"; 3150 } 3151 3152 static const HChar * 3153 s390_irgen_ALHHLR(UChar r3, UChar r1, UChar r2) 3154 { 3155 IRTemp op2 = newTemp(Ity_I32); 3156 IRTemp op3 = newTemp(Ity_I32); 3157 IRTemp result = newTemp(Ity_I32); 3158 3159 assign(op2, get_gpr_w0(r2)); 3160 assign(op3, get_gpr_w1(r3)); 3161 assign(result, binop(Iop_Add32, mkexpr(op2), mkexpr(op3))); 3162 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_32, op2, op3); 3163 put_gpr_w0(r1, mkexpr(result)); 3164 3165 return "alhhlr"; 3166 } 3167 3168 static const HChar * 3169 s390_irgen_ALCR(UChar r1, UChar r2) 3170 { 3171 IRTemp op1 = newTemp(Ity_I32); 3172 IRTemp op2 = newTemp(Ity_I32); 3173 IRTemp result = newTemp(Ity_I32); 3174 IRTemp carry_in = newTemp(Ity_I32); 3175 3176 assign(op1, get_gpr_w1(r1)); 3177 assign(op2, get_gpr_w1(r2)); 3178 assign(carry_in, binop(Iop_Shr32, s390_call_calculate_cc(), mkU8(1))); 3179 assign(result, binop(Iop_Add32, binop(Iop_Add32, mkexpr(op1), mkexpr(op2)), 3180 mkexpr(carry_in))); 3181 s390_cc_thunk_putZZZ(S390_CC_OP_UNSIGNED_ADDC_32, op1, op2, carry_in); 3182 put_gpr_w1(r1, mkexpr(result)); 3183 3184 return "alcr"; 3185 } 3186 3187 static const HChar * 3188 s390_irgen_ALCGR(UChar r1, UChar r2) 3189 { 3190 IRTemp op1 = newTemp(Ity_I64); 3191 IRTemp op2 = newTemp(Ity_I64); 3192 IRTemp result = newTemp(Ity_I64); 3193 IRTemp carry_in = newTemp(Ity_I64); 3194 3195 assign(op1, get_gpr_dw0(r1)); 3196 assign(op2, get_gpr_dw0(r2)); 3197 assign(carry_in, unop(Iop_32Uto64, binop(Iop_Shr32, s390_call_calculate_cc(), 3198 mkU8(1)))); 3199 assign(result, binop(Iop_Add64, binop(Iop_Add64, mkexpr(op1), mkexpr(op2)), 3200 mkexpr(carry_in))); 3201 s390_cc_thunk_putZZZ(S390_CC_OP_UNSIGNED_ADDC_64, op1, op2, carry_in); 3202 put_gpr_dw0(r1, mkexpr(result)); 3203 3204 return "alcgr"; 3205 } 3206 3207 static const HChar * 3208 s390_irgen_ALC(UChar r1, IRTemp op2addr) 3209 { 3210 IRTemp op1 = newTemp(Ity_I32); 3211 IRTemp op2 = newTemp(Ity_I32); 3212 IRTemp result = newTemp(Ity_I32); 3213 IRTemp carry_in = newTemp(Ity_I32); 3214 3215 assign(op1, get_gpr_w1(r1)); 3216 assign(op2, load(Ity_I32, mkexpr(op2addr))); 3217 assign(carry_in, binop(Iop_Shr32, s390_call_calculate_cc(), mkU8(1))); 3218 assign(result, binop(Iop_Add32, binop(Iop_Add32, mkexpr(op1), mkexpr(op2)), 3219 mkexpr(carry_in))); 3220 s390_cc_thunk_putZZZ(S390_CC_OP_UNSIGNED_ADDC_32, op1, op2, carry_in); 3221 put_gpr_w1(r1, mkexpr(result)); 3222 3223 return "alc"; 3224 } 3225 3226 static const HChar * 3227 s390_irgen_ALCG(UChar r1, IRTemp op2addr) 3228 { 3229 IRTemp op1 = newTemp(Ity_I64); 3230 IRTemp op2 = newTemp(Ity_I64); 3231 IRTemp result = newTemp(Ity_I64); 3232 IRTemp carry_in = newTemp(Ity_I64); 3233 3234 assign(op1, get_gpr_dw0(r1)); 3235 assign(op2, load(Ity_I64, mkexpr(op2addr))); 3236 assign(carry_in, unop(Iop_32Uto64, binop(Iop_Shr32, s390_call_calculate_cc(), 3237 mkU8(1)))); 3238 assign(result, binop(Iop_Add64, binop(Iop_Add64, mkexpr(op1), mkexpr(op2)), 3239 mkexpr(carry_in))); 3240 s390_cc_thunk_putZZZ(S390_CC_OP_UNSIGNED_ADDC_64, op1, op2, carry_in); 3241 put_gpr_dw0(r1, mkexpr(result)); 3242 3243 return "alcg"; 3244 } 3245 3246 static const HChar * 3247 s390_irgen_ALSI(UChar i2, IRTemp op1addr) 3248 { 3249 IRTemp op1 = newTemp(Ity_I32); 3250 UInt op2; 3251 IRTemp result = newTemp(Ity_I32); 3252 3253 assign(op1, load(Ity_I32, mkexpr(op1addr))); 3254 op2 = (UInt)(Int)(Char)i2; 3255 assign(result, binop(Iop_Add32, mkexpr(op1), mkU32(op2))); 3256 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_32, op1, mktemp(Ity_I32, 3257 mkU32(op2))); 3258 store(mkexpr(op1addr), mkexpr(result)); 3259 3260 return "alsi"; 3261 } 3262 3263 static const HChar * 3264 s390_irgen_ALGSI(UChar i2, IRTemp op1addr) 3265 { 3266 IRTemp op1 = newTemp(Ity_I64); 3267 ULong op2; 3268 IRTemp result = newTemp(Ity_I64); 3269 3270 assign(op1, load(Ity_I64, mkexpr(op1addr))); 3271 op2 = (ULong)(Long)(Char)i2; 3272 assign(result, binop(Iop_Add64, mkexpr(op1), mkU64(op2))); 3273 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_64, op1, mktemp(Ity_I64, 3274 mkU64(op2))); 3275 store(mkexpr(op1addr), mkexpr(result)); 3276 3277 return "algsi"; 3278 } 3279 3280 static const HChar * 3281 s390_irgen_ALHSIK(UChar r1, UChar r3, UShort i2) 3282 { 3283 UInt op2; 3284 IRTemp op3 = newTemp(Ity_I32); 3285 IRTemp result = newTemp(Ity_I32); 3286 3287 op2 = (UInt)(Int)(Short)i2; 3288 assign(op3, get_gpr_w1(r3)); 3289 assign(result, binop(Iop_Add32, mkU32(op2), mkexpr(op3))); 3290 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_32, mktemp(Ity_I32, mkU32(op2)), 3291 op3); 3292 put_gpr_w1(r1, mkexpr(result)); 3293 3294 return "alhsik"; 3295 } 3296 3297 static const HChar * 3298 s390_irgen_ALGHSIK(UChar r1, UChar r3, UShort i2) 3299 { 3300 ULong op2; 3301 IRTemp op3 = newTemp(Ity_I64); 3302 IRTemp result = newTemp(Ity_I64); 3303 3304 op2 = (ULong)(Long)(Short)i2; 3305 assign(op3, get_gpr_dw0(r3)); 3306 assign(result, binop(Iop_Add64, mkU64(op2), mkexpr(op3))); 3307 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_64, mktemp(Ity_I64, mkU64(op2)), 3308 op3); 3309 put_gpr_dw0(r1, mkexpr(result)); 3310 3311 return "alghsik"; 3312 } 3313 3314 static const HChar * 3315 s390_irgen_ALSIH(UChar r1, UInt i2) 3316 { 3317 IRTemp op1 = newTemp(Ity_I32); 3318 UInt op2; 3319 IRTemp result = newTemp(Ity_I32); 3320 3321 assign(op1, get_gpr_w0(r1)); 3322 op2 = i2; 3323 assign(result, binop(Iop_Add32, mkexpr(op1), mkU32(op2))); 3324 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_32, op1, mktemp(Ity_I32, 3325 mkU32(op2))); 3326 put_gpr_w0(r1, mkexpr(result)); 3327 3328 return "alsih"; 3329 } 3330 3331 static const HChar * 3332 s390_irgen_ALSIHN(UChar r1, UInt i2) 3333 { 3334 IRTemp op1 = newTemp(Ity_I32); 3335 UInt op2; 3336 IRTemp result = newTemp(Ity_I32); 3337 3338 assign(op1, get_gpr_w0(r1)); 3339 op2 = i2; 3340 assign(result, binop(Iop_Add32, mkexpr(op1), mkU32(op2))); 3341 put_gpr_w0(r1, mkexpr(result)); 3342 3343 return "alsihn"; 3344 } 3345 3346 static const HChar * 3347 s390_irgen_NR(UChar r1, UChar r2) 3348 { 3349 IRTemp op1 = newTemp(Ity_I32); 3350 IRTemp op2 = newTemp(Ity_I32); 3351 IRTemp result = newTemp(Ity_I32); 3352 3353 assign(op1, get_gpr_w1(r1)); 3354 assign(op2, get_gpr_w1(r2)); 3355 assign(result, binop(Iop_And32, mkexpr(op1), mkexpr(op2))); 3356 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 3357 put_gpr_w1(r1, mkexpr(result)); 3358 3359 return "nr"; 3360 } 3361 3362 static const HChar * 3363 s390_irgen_NGR(UChar r1, UChar r2) 3364 { 3365 IRTemp op1 = newTemp(Ity_I64); 3366 IRTemp op2 = newTemp(Ity_I64); 3367 IRTemp result = newTemp(Ity_I64); 3368 3369 assign(op1, get_gpr_dw0(r1)); 3370 assign(op2, get_gpr_dw0(r2)); 3371 assign(result, binop(Iop_And64, mkexpr(op1), mkexpr(op2))); 3372 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 3373 put_gpr_dw0(r1, mkexpr(result)); 3374 3375 return "ngr"; 3376 } 3377 3378 static const HChar * 3379 s390_irgen_NRK(UChar r3, UChar r1, UChar r2) 3380 { 3381 IRTemp op2 = newTemp(Ity_I32); 3382 IRTemp op3 = newTemp(Ity_I32); 3383 IRTemp result = newTemp(Ity_I32); 3384 3385 assign(op2, get_gpr_w1(r2)); 3386 assign(op3, get_gpr_w1(r3)); 3387 assign(result, binop(Iop_And32, mkexpr(op2), mkexpr(op3))); 3388 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 3389 put_gpr_w1(r1, mkexpr(result)); 3390 3391 return "nrk"; 3392 } 3393 3394 static const HChar * 3395 s390_irgen_NGRK(UChar r3, UChar r1, UChar r2) 3396 { 3397 IRTemp op2 = newTemp(Ity_I64); 3398 IRTemp op3 = newTemp(Ity_I64); 3399 IRTemp result = newTemp(Ity_I64); 3400 3401 assign(op2, get_gpr_dw0(r2)); 3402 assign(op3, get_gpr_dw0(r3)); 3403 assign(result, binop(Iop_And64, mkexpr(op2), mkexpr(op3))); 3404 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 3405 put_gpr_dw0(r1, mkexpr(result)); 3406 3407 return "ngrk"; 3408 } 3409 3410 static const HChar * 3411 s390_irgen_N(UChar r1, IRTemp op2addr) 3412 { 3413 IRTemp op1 = newTemp(Ity_I32); 3414 IRTemp op2 = newTemp(Ity_I32); 3415 IRTemp result = newTemp(Ity_I32); 3416 3417 assign(op1, get_gpr_w1(r1)); 3418 assign(op2, load(Ity_I32, mkexpr(op2addr))); 3419 assign(result, binop(Iop_And32, mkexpr(op1), mkexpr(op2))); 3420 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 3421 put_gpr_w1(r1, mkexpr(result)); 3422 3423 return "n"; 3424 } 3425 3426 static const HChar * 3427 s390_irgen_NY(UChar r1, IRTemp op2addr) 3428 { 3429 IRTemp op1 = newTemp(Ity_I32); 3430 IRTemp op2 = newTemp(Ity_I32); 3431 IRTemp result = newTemp(Ity_I32); 3432 3433 assign(op1, get_gpr_w1(r1)); 3434 assign(op2, load(Ity_I32, mkexpr(op2addr))); 3435 assign(result, binop(Iop_And32, mkexpr(op1), mkexpr(op2))); 3436 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 3437 put_gpr_w1(r1, mkexpr(result)); 3438 3439 return "ny"; 3440 } 3441 3442 static const HChar * 3443 s390_irgen_NG(UChar r1, IRTemp op2addr) 3444 { 3445 IRTemp op1 = newTemp(Ity_I64); 3446 IRTemp op2 = newTemp(Ity_I64); 3447 IRTemp result = newTemp(Ity_I64); 3448 3449 assign(op1, get_gpr_dw0(r1)); 3450 assign(op2, load(Ity_I64, mkexpr(op2addr))); 3451 assign(result, binop(Iop_And64, mkexpr(op1), mkexpr(op2))); 3452 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 3453 put_gpr_dw0(r1, mkexpr(result)); 3454 3455 return "ng"; 3456 } 3457 3458 static const HChar * 3459 s390_irgen_NI(UChar i2, IRTemp op1addr) 3460 { 3461 IRTemp op1 = newTemp(Ity_I8); 3462 UChar op2; 3463 IRTemp result = newTemp(Ity_I8); 3464 3465 assign(op1, load(Ity_I8, mkexpr(op1addr))); 3466 op2 = i2; 3467 assign(result, binop(Iop_And8, mkexpr(op1), mkU8(op2))); 3468 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 3469 store(mkexpr(op1addr), mkexpr(result)); 3470 3471 return "ni"; 3472 } 3473 3474 static const HChar * 3475 s390_irgen_NIY(UChar i2, IRTemp op1addr) 3476 { 3477 IRTemp op1 = newTemp(Ity_I8); 3478 UChar op2; 3479 IRTemp result = newTemp(Ity_I8); 3480 3481 assign(op1, load(Ity_I8, mkexpr(op1addr))); 3482 op2 = i2; 3483 assign(result, binop(Iop_And8, mkexpr(op1), mkU8(op2))); 3484 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 3485 store(mkexpr(op1addr), mkexpr(result)); 3486 3487 return "niy"; 3488 } 3489 3490 static const HChar * 3491 s390_irgen_NIHF(UChar r1, UInt i2) 3492 { 3493 IRTemp op1 = newTemp(Ity_I32); 3494 UInt op2; 3495 IRTemp result = newTemp(Ity_I32); 3496 3497 assign(op1, get_gpr_w0(r1)); 3498 op2 = i2; 3499 assign(result, binop(Iop_And32, mkexpr(op1), mkU32(op2))); 3500 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 3501 put_gpr_w0(r1, mkexpr(result)); 3502 3503 return "nihf"; 3504 } 3505 3506 static const HChar * 3507 s390_irgen_NIHH(UChar r1, UShort i2) 3508 { 3509 IRTemp op1 = newTemp(Ity_I16); 3510 UShort op2; 3511 IRTemp result = newTemp(Ity_I16); 3512 3513 assign(op1, get_gpr_hw0(r1)); 3514 op2 = i2; 3515 assign(result, binop(Iop_And16, mkexpr(op1), mkU16(op2))); 3516 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 3517 put_gpr_hw0(r1, mkexpr(result)); 3518 3519 return "nihh"; 3520 } 3521 3522 static const HChar * 3523 s390_irgen_NIHL(UChar r1, UShort i2) 3524 { 3525 IRTemp op1 = newTemp(Ity_I16); 3526 UShort op2; 3527 IRTemp result = newTemp(Ity_I16); 3528 3529 assign(op1, get_gpr_hw1(r1)); 3530 op2 = i2; 3531 assign(result, binop(Iop_And16, mkexpr(op1), mkU16(op2))); 3532 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 3533 put_gpr_hw1(r1, mkexpr(result)); 3534 3535 return "nihl"; 3536 } 3537 3538 static const HChar * 3539 s390_irgen_NILF(UChar r1, UInt i2) 3540 { 3541 IRTemp op1 = newTemp(Ity_I32); 3542 UInt op2; 3543 IRTemp result = newTemp(Ity_I32); 3544 3545 assign(op1, get_gpr_w1(r1)); 3546 op2 = i2; 3547 assign(result, binop(Iop_And32, mkexpr(op1), mkU32(op2))); 3548 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 3549 put_gpr_w1(r1, mkexpr(result)); 3550 3551 return "nilf"; 3552 } 3553 3554 static const HChar * 3555 s390_irgen_NILH(UChar r1, UShort i2) 3556 { 3557 IRTemp op1 = newTemp(Ity_I16); 3558 UShort op2; 3559 IRTemp result = newTemp(Ity_I16); 3560 3561 assign(op1, get_gpr_hw2(r1)); 3562 op2 = i2; 3563 assign(result, binop(Iop_And16, mkexpr(op1), mkU16(op2))); 3564 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 3565 put_gpr_hw2(r1, mkexpr(result)); 3566 3567 return "nilh"; 3568 } 3569 3570 static const HChar * 3571 s390_irgen_NILL(UChar r1, UShort i2) 3572 { 3573 IRTemp op1 = newTemp(Ity_I16); 3574 UShort op2; 3575 IRTemp result = newTemp(Ity_I16); 3576 3577 assign(op1, get_gpr_hw3(r1)); 3578 op2 = i2; 3579 assign(result, binop(Iop_And16, mkexpr(op1), mkU16(op2))); 3580 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 3581 put_gpr_hw3(r1, mkexpr(result)); 3582 3583 return "nill"; 3584 } 3585 3586 static const HChar * 3587 s390_irgen_BASR(UChar r1, UChar r2) 3588 { 3589 IRTemp target = newTemp(Ity_I64); 3590 3591 if (r2 == 0) { 3592 put_gpr_dw0(r1, mkU64(guest_IA_curr_instr + 2ULL)); 3593 } else { 3594 if (r1 != r2) { 3595 put_gpr_dw0(r1, mkU64(guest_IA_curr_instr + 2ULL)); 3596 call_function(get_gpr_dw0(r2)); 3597 } else { 3598 assign(target, get_gpr_dw0(r2)); 3599 put_gpr_dw0(r1, mkU64(guest_IA_curr_instr + 2ULL)); 3600 call_function(mkexpr(target)); 3601 } 3602 } 3603 3604 return "basr"; 3605 } 3606 3607 static const HChar * 3608 s390_irgen_BAS(UChar r1, IRTemp op2addr) 3609 { 3610 IRTemp target = newTemp(Ity_I64); 3611 3612 put_gpr_dw0(r1, mkU64(guest_IA_curr_instr + 4ULL)); 3613 assign(target, mkexpr(op2addr)); 3614 call_function(mkexpr(target)); 3615 3616 return "bas"; 3617 } 3618 3619 static const HChar * 3620 s390_irgen_BCR(UChar r1, UChar r2) 3621 { 3622 IRTemp cond = newTemp(Ity_I32); 3623 3624 if (r2 == 0 && (r1 >= 14)) { /* serialization */ 3625 stmt(IRStmt_MBE(Imbe_Fence)); 3626 } 3627 3628 if ((r2 == 0) || (r1 == 0)) { 3629 } else { 3630 if (r1 == 15) { 3631 return_from_function(get_gpr_dw0(r2)); 3632 } else { 3633 assign(cond, s390_call_calculate_cond(r1)); 3634 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 3635 get_gpr_dw0(r2)); 3636 } 3637 } 3638 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 3639 s390_disasm(ENC2(XMNM, GPR), S390_XMNM_BCR, r1, r2); 3640 3641 return "bcr"; 3642 } 3643 3644 static const HChar * 3645 s390_irgen_BC(UChar r1, UChar x2, UChar b2, UShort d2, IRTemp op2addr) 3646 { 3647 IRTemp cond = newTemp(Ity_I32); 3648 3649 if (r1 == 0) { 3650 } else { 3651 if (r1 == 15) { 3652 always_goto(mkexpr(op2addr)); 3653 } else { 3654 assign(cond, s390_call_calculate_cond(r1)); 3655 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 3656 mkexpr(op2addr)); 3657 } 3658 } 3659 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 3660 s390_disasm(ENC2(XMNM, UDXB), S390_XMNM_BC, r1, d2, x2, b2); 3661 3662 return "bc"; 3663 } 3664 3665 static const HChar * 3666 s390_irgen_BCTR(UChar r1, UChar r2) 3667 { 3668 put_gpr_w1(r1, binop(Iop_Sub32, get_gpr_w1(r1), mkU32(1))); 3669 if (r2 != 0) { 3670 if_condition_goto_computed(binop(Iop_CmpNE32, get_gpr_w1(r1), mkU32(0)), 3671 get_gpr_dw0(r2)); 3672 } 3673 3674 return "bctr"; 3675 } 3676 3677 static const HChar * 3678 s390_irgen_BCTGR(UChar r1, UChar r2) 3679 { 3680 put_gpr_dw0(r1, binop(Iop_Sub64, get_gpr_dw0(r1), mkU64(1))); 3681 if (r2 != 0) { 3682 if_condition_goto_computed(binop(Iop_CmpNE64, get_gpr_dw0(r1), mkU64(0)), 3683 get_gpr_dw0(r2)); 3684 } 3685 3686 return "bctgr"; 3687 } 3688 3689 static const HChar * 3690 s390_irgen_BCT(UChar r1, IRTemp op2addr) 3691 { 3692 put_gpr_w1(r1, binop(Iop_Sub32, get_gpr_w1(r1), mkU32(1))); 3693 if_condition_goto_computed(binop(Iop_CmpNE32, get_gpr_w1(r1), mkU32(0)), 3694 mkexpr(op2addr)); 3695 3696 return "bct"; 3697 } 3698 3699 static const HChar * 3700 s390_irgen_BCTG(UChar r1, IRTemp op2addr) 3701 { 3702 put_gpr_dw0(r1, binop(Iop_Sub64, get_gpr_dw0(r1), mkU64(1))); 3703 if_condition_goto_computed(binop(Iop_CmpNE64, get_gpr_dw0(r1), mkU64(0)), 3704 mkexpr(op2addr)); 3705 3706 return "bctg"; 3707 } 3708 3709 static const HChar * 3710 s390_irgen_BXH(UChar r1, UChar r3, IRTemp op2addr) 3711 { 3712 IRTemp value = newTemp(Ity_I32); 3713 3714 assign(value, get_gpr_w1(r3 | 1)); 3715 put_gpr_w1(r1, binop(Iop_Add32, get_gpr_w1(r1), get_gpr_w1(r3))); 3716 if_condition_goto_computed(binop(Iop_CmpLT32S, mkexpr(value), 3717 get_gpr_w1(r1)), mkexpr(op2addr)); 3718 3719 return "bxh"; 3720 } 3721 3722 static const HChar * 3723 s390_irgen_BXHG(UChar r1, UChar r3, IRTemp op2addr) 3724 { 3725 IRTemp value = newTemp(Ity_I64); 3726 3727 assign(value, get_gpr_dw0(r3 | 1)); 3728 put_gpr_dw0(r1, binop(Iop_Add64, get_gpr_dw0(r1), get_gpr_dw0(r3))); 3729 if_condition_goto_computed(binop(Iop_CmpLT64S, mkexpr(value), 3730 get_gpr_dw0(r1)), mkexpr(op2addr)); 3731 3732 return "bxhg"; 3733 } 3734 3735 static const HChar * 3736 s390_irgen_BXLE(UChar r1, UChar r3, IRTemp op2addr) 3737 { 3738 IRTemp value = newTemp(Ity_I32); 3739 3740 assign(value, get_gpr_w1(r3 | 1)); 3741 put_gpr_w1(r1, binop(Iop_Add32, get_gpr_w1(r1), get_gpr_w1(r3))); 3742 if_condition_goto_computed(binop(Iop_CmpLE32S, get_gpr_w1(r1), 3743 mkexpr(value)), mkexpr(op2addr)); 3744 3745 return "bxle"; 3746 } 3747 3748 static const HChar * 3749 s390_irgen_BXLEG(UChar r1, UChar r3, IRTemp op2addr) 3750 { 3751 IRTemp value = newTemp(Ity_I64); 3752 3753 assign(value, get_gpr_dw0(r3 | 1)); 3754 put_gpr_dw0(r1, binop(Iop_Add64, get_gpr_dw0(r1), get_gpr_dw0(r3))); 3755 if_condition_goto_computed(binop(Iop_CmpLE64S, get_gpr_dw0(r1), 3756 mkexpr(value)), mkexpr(op2addr)); 3757 3758 return "bxleg"; 3759 } 3760 3761 static const HChar * 3762 s390_irgen_BRAS(UChar r1, UShort i2) 3763 { 3764 put_gpr_dw0(r1, mkU64(guest_IA_curr_instr + 4ULL)); 3765 call_function_and_chase(guest_IA_curr_instr + ((ULong)(Long)(Short)i2 << 1)); 3766 3767 return "bras"; 3768 } 3769 3770 static const HChar * 3771 s390_irgen_BRASL(UChar r1, UInt i2) 3772 { 3773 put_gpr_dw0(r1, mkU64(guest_IA_curr_instr + 6ULL)); 3774 call_function_and_chase(guest_IA_curr_instr + ((ULong)(Long)(Int)i2 << 1)); 3775 3776 return "brasl"; 3777 } 3778 3779 static const HChar * 3780 s390_irgen_BRC(UChar r1, UShort i2) 3781 { 3782 IRTemp cond = newTemp(Ity_I32); 3783 3784 if (r1 == 0) { 3785 } else { 3786 if (r1 == 15) { 3787 always_goto_and_chase( 3788 guest_IA_curr_instr + ((ULong)(Long)(Short)i2 << 1)); 3789 } else { 3790 assign(cond, s390_call_calculate_cond(r1)); 3791 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 3792 guest_IA_curr_instr + ((ULong)(Long)(Short)i2 << 1)); 3793 3794 } 3795 } 3796 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 3797 s390_disasm(ENC2(XMNM, PCREL), S390_XMNM_BRC, r1, (Int)(Short)i2); 3798 3799 return "brc"; 3800 } 3801 3802 static const HChar * 3803 s390_irgen_BRCL(UChar r1, UInt i2) 3804 { 3805 IRTemp cond = newTemp(Ity_I32); 3806 3807 if (r1 == 0) { 3808 } else { 3809 if (r1 == 15) { 3810 always_goto_and_chase(guest_IA_curr_instr + ((ULong)(Long)(Int)i2 << 1)); 3811 } else { 3812 assign(cond, s390_call_calculate_cond(r1)); 3813 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 3814 guest_IA_curr_instr + ((ULong)(Long)(Int)i2 << 1)); 3815 } 3816 } 3817 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 3818 s390_disasm(ENC2(XMNM, PCREL), S390_XMNM_BRCL, r1, i2); 3819 3820 return "brcl"; 3821 } 3822 3823 static const HChar * 3824 s390_irgen_BRCT(UChar r1, UShort i2) 3825 { 3826 put_gpr_w1(r1, binop(Iop_Sub32, get_gpr_w1(r1), mkU32(1))); 3827 if_condition_goto(binop(Iop_CmpNE32, get_gpr_w1(r1), mkU32(0)), 3828 guest_IA_curr_instr + ((ULong)(Long)(Short)i2 << 1)); 3829 3830 return "brct"; 3831 } 3832 3833 static const HChar * 3834 s390_irgen_BRCTH(UChar r1, UInt i2) 3835 { 3836 put_gpr_w0(r1, binop(Iop_Sub32, get_gpr_w0(r1), mkU32(1))); 3837 if_condition_goto(binop(Iop_CmpNE32, get_gpr_w0(r1), mkU32(0)), 3838 guest_IA_curr_instr + ((ULong)(Long)(Short)i2 << 1)); 3839 3840 return "brcth"; 3841 } 3842 3843 static const HChar * 3844 s390_irgen_BRCTG(UChar r1, UShort i2) 3845 { 3846 put_gpr_dw0(r1, binop(Iop_Sub64, get_gpr_dw0(r1), mkU64(1))); 3847 if_condition_goto(binop(Iop_CmpNE64, get_gpr_dw0(r1), mkU64(0)), 3848 guest_IA_curr_instr + ((ULong)(Long)(Short)i2 << 1)); 3849 3850 return "brctg"; 3851 } 3852 3853 static const HChar * 3854 s390_irgen_BRXH(UChar r1, UChar r3, UShort i2) 3855 { 3856 IRTemp value = newTemp(Ity_I32); 3857 3858 assign(value, get_gpr_w1(r3 | 1)); 3859 put_gpr_w1(r1, binop(Iop_Add32, get_gpr_w1(r1), get_gpr_w1(r3))); 3860 if_condition_goto(binop(Iop_CmpLT32S, mkexpr(value), get_gpr_w1(r1)), 3861 guest_IA_curr_instr + ((ULong)(Long)(Short)i2 << 1)); 3862 3863 return "brxh"; 3864 } 3865 3866 static const HChar * 3867 s390_irgen_BRXHG(UChar r1, UChar r3, UShort i2) 3868 { 3869 IRTemp value = newTemp(Ity_I64); 3870 3871 assign(value, get_gpr_dw0(r3 | 1)); 3872 put_gpr_dw0(r1, binop(Iop_Add64, get_gpr_dw0(r1), get_gpr_dw0(r3))); 3873 if_condition_goto(binop(Iop_CmpLT64S, mkexpr(value), get_gpr_dw0(r1)), 3874 guest_IA_curr_instr + ((ULong)(Long)(Short)i2 << 1)); 3875 3876 return "brxhg"; 3877 } 3878 3879 static const HChar * 3880 s390_irgen_BRXLE(UChar r1, UChar r3, UShort i2) 3881 { 3882 IRTemp value = newTemp(Ity_I32); 3883 3884 assign(value, get_gpr_w1(r3 | 1)); 3885 put_gpr_w1(r1, binop(Iop_Add32, get_gpr_w1(r1), get_gpr_w1(r3))); 3886 if_condition_goto(binop(Iop_CmpLE32S, get_gpr_w1(r1), mkexpr(value)), 3887 guest_IA_curr_instr + ((ULong)(Long)(Short)i2 << 1)); 3888 3889 return "brxle"; 3890 } 3891 3892 static const HChar * 3893 s390_irgen_BRXLG(UChar r1, UChar r3, UShort i2) 3894 { 3895 IRTemp value = newTemp(Ity_I64); 3896 3897 assign(value, get_gpr_dw0(r3 | 1)); 3898 put_gpr_dw0(r1, binop(Iop_Add64, get_gpr_dw0(r1), get_gpr_dw0(r3))); 3899 if_condition_goto(binop(Iop_CmpLE64S, get_gpr_dw0(r1), mkexpr(value)), 3900 guest_IA_curr_instr + ((ULong)(Long)(Short)i2 << 1)); 3901 3902 return "brxlg"; 3903 } 3904 3905 static const HChar * 3906 s390_irgen_CR(UChar r1, UChar r2) 3907 { 3908 IRTemp op1 = newTemp(Ity_I32); 3909 IRTemp op2 = newTemp(Ity_I32); 3910 3911 assign(op1, get_gpr_w1(r1)); 3912 assign(op2, get_gpr_w1(r2)); 3913 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 3914 3915 return "cr"; 3916 } 3917 3918 static const HChar * 3919 s390_irgen_CGR(UChar r1, UChar r2) 3920 { 3921 IRTemp op1 = newTemp(Ity_I64); 3922 IRTemp op2 = newTemp(Ity_I64); 3923 3924 assign(op1, get_gpr_dw0(r1)); 3925 assign(op2, get_gpr_dw0(r2)); 3926 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 3927 3928 return "cgr"; 3929 } 3930 3931 static const HChar * 3932 s390_irgen_CGFR(UChar r1, UChar r2) 3933 { 3934 IRTemp op1 = newTemp(Ity_I64); 3935 IRTemp op2 = newTemp(Ity_I64); 3936 3937 assign(op1, get_gpr_dw0(r1)); 3938 assign(op2, unop(Iop_32Sto64, get_gpr_w1(r2))); 3939 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 3940 3941 return "cgfr"; 3942 } 3943 3944 static const HChar * 3945 s390_irgen_C(UChar r1, IRTemp op2addr) 3946 { 3947 IRTemp op1 = newTemp(Ity_I32); 3948 IRTemp op2 = newTemp(Ity_I32); 3949 3950 assign(op1, get_gpr_w1(r1)); 3951 assign(op2, load(Ity_I32, mkexpr(op2addr))); 3952 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 3953 3954 return "c"; 3955 } 3956 3957 static const HChar * 3958 s390_irgen_CY(UChar r1, IRTemp op2addr) 3959 { 3960 IRTemp op1 = newTemp(Ity_I32); 3961 IRTemp op2 = newTemp(Ity_I32); 3962 3963 assign(op1, get_gpr_w1(r1)); 3964 assign(op2, load(Ity_I32, mkexpr(op2addr))); 3965 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 3966 3967 return "cy"; 3968 } 3969 3970 static const HChar * 3971 s390_irgen_CG(UChar r1, IRTemp op2addr) 3972 { 3973 IRTemp op1 = newTemp(Ity_I64); 3974 IRTemp op2 = newTemp(Ity_I64); 3975 3976 assign(op1, get_gpr_dw0(r1)); 3977 assign(op2, load(Ity_I64, mkexpr(op2addr))); 3978 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 3979 3980 return "cg"; 3981 } 3982 3983 static const HChar * 3984 s390_irgen_CGF(UChar r1, IRTemp op2addr) 3985 { 3986 IRTemp op1 = newTemp(Ity_I64); 3987 IRTemp op2 = newTemp(Ity_I64); 3988 3989 assign(op1, get_gpr_dw0(r1)); 3990 assign(op2, unop(Iop_32Sto64, load(Ity_I32, mkexpr(op2addr)))); 3991 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 3992 3993 return "cgf"; 3994 } 3995 3996 static const HChar * 3997 s390_irgen_CFI(UChar r1, UInt i2) 3998 { 3999 IRTemp op1 = newTemp(Ity_I32); 4000 Int op2; 4001 4002 assign(op1, get_gpr_w1(r1)); 4003 op2 = (Int)i2; 4004 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, mktemp(Ity_I32, 4005 mkU32((UInt)op2))); 4006 4007 return "cfi"; 4008 } 4009 4010 static const HChar * 4011 s390_irgen_CGFI(UChar r1, UInt i2) 4012 { 4013 IRTemp op1 = newTemp(Ity_I64); 4014 Long op2; 4015 4016 assign(op1, get_gpr_dw0(r1)); 4017 op2 = (Long)(Int)i2; 4018 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, mktemp(Ity_I64, 4019 mkU64((ULong)op2))); 4020 4021 return "cgfi"; 4022 } 4023 4024 static const HChar * 4025 s390_irgen_CRL(UChar r1, UInt i2) 4026 { 4027 IRTemp op1 = newTemp(Ity_I32); 4028 IRTemp op2 = newTemp(Ity_I32); 4029 4030 assign(op1, get_gpr_w1(r1)); 4031 assign(op2, load(Ity_I32, mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int) 4032 i2 << 1)))); 4033 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4034 4035 return "crl"; 4036 } 4037 4038 static const HChar * 4039 s390_irgen_CGRL(UChar r1, UInt i2) 4040 { 4041 IRTemp op1 = newTemp(Ity_I64); 4042 IRTemp op2 = newTemp(Ity_I64); 4043 4044 assign(op1, get_gpr_dw0(r1)); 4045 assign(op2, load(Ity_I64, mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int) 4046 i2 << 1)))); 4047 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4048 4049 return "cgrl"; 4050 } 4051 4052 static const HChar * 4053 s390_irgen_CGFRL(UChar r1, UInt i2) 4054 { 4055 IRTemp op1 = newTemp(Ity_I64); 4056 IRTemp op2 = newTemp(Ity_I64); 4057 4058 assign(op1, get_gpr_dw0(r1)); 4059 assign(op2, unop(Iop_32Sto64, load(Ity_I32, mkU64(guest_IA_curr_instr + 4060 ((ULong)(Long)(Int)i2 << 1))))); 4061 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4062 4063 return "cgfrl"; 4064 } 4065 4066 static const HChar * 4067 s390_irgen_CRB(UChar r1, UChar r2, UChar m3, IRTemp op4addr) 4068 { 4069 IRTemp op1 = newTemp(Ity_I32); 4070 IRTemp op2 = newTemp(Ity_I32); 4071 IRTemp cond = newTemp(Ity_I32); 4072 4073 if (m3 == 0) { 4074 } else { 4075 if (m3 == 14) { 4076 always_goto(mkexpr(op4addr)); 4077 } else { 4078 assign(op1, get_gpr_w1(r1)); 4079 assign(op2, get_gpr_w1(r2)); 4080 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_SIGNED_COMPARE, 4081 op1, op2)); 4082 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), 4083 mkU32(0)), mkexpr(op4addr)); 4084 } 4085 } 4086 4087 return "crb"; 4088 } 4089 4090 static const HChar * 4091 s390_irgen_CGRB(UChar r1, UChar r2, UChar m3, IRTemp op4addr) 4092 { 4093 IRTemp op1 = newTemp(Ity_I64); 4094 IRTemp op2 = newTemp(Ity_I64); 4095 IRTemp cond = newTemp(Ity_I32); 4096 4097 if (m3 == 0) { 4098 } else { 4099 if (m3 == 14) { 4100 always_goto(mkexpr(op4addr)); 4101 } else { 4102 assign(op1, get_gpr_dw0(r1)); 4103 assign(op2, get_gpr_dw0(r2)); 4104 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_SIGNED_COMPARE, 4105 op1, op2)); 4106 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), 4107 mkU32(0)), mkexpr(op4addr)); 4108 } 4109 } 4110 4111 return "cgrb"; 4112 } 4113 4114 static const HChar * 4115 s390_irgen_CRJ(UChar r1, UChar r2, UShort i4, UChar m3) 4116 { 4117 IRTemp op1 = newTemp(Ity_I32); 4118 IRTemp op2 = newTemp(Ity_I32); 4119 IRTemp cond = newTemp(Ity_I32); 4120 4121 if (m3 == 0) { 4122 } else { 4123 if (m3 == 14) { 4124 always_goto_and_chase( 4125 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4126 } else { 4127 assign(op1, get_gpr_w1(r1)); 4128 assign(op2, get_gpr_w1(r2)); 4129 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_SIGNED_COMPARE, 4130 op1, op2)); 4131 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4132 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4133 4134 } 4135 } 4136 4137 return "crj"; 4138 } 4139 4140 static const HChar * 4141 s390_irgen_CGRJ(UChar r1, UChar r2, UShort i4, UChar m3) 4142 { 4143 IRTemp op1 = newTemp(Ity_I64); 4144 IRTemp op2 = newTemp(Ity_I64); 4145 IRTemp cond = newTemp(Ity_I32); 4146 4147 if (m3 == 0) { 4148 } else { 4149 if (m3 == 14) { 4150 always_goto_and_chase( 4151 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4152 } else { 4153 assign(op1, get_gpr_dw0(r1)); 4154 assign(op2, get_gpr_dw0(r2)); 4155 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_SIGNED_COMPARE, 4156 op1, op2)); 4157 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4158 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4159 4160 } 4161 } 4162 4163 return "cgrj"; 4164 } 4165 4166 static const HChar * 4167 s390_irgen_CIB(UChar r1, UChar m3, UChar i2, IRTemp op4addr) 4168 { 4169 IRTemp op1 = newTemp(Ity_I32); 4170 Int op2; 4171 IRTemp cond = newTemp(Ity_I32); 4172 4173 if (m3 == 0) { 4174 } else { 4175 if (m3 == 14) { 4176 always_goto(mkexpr(op4addr)); 4177 } else { 4178 assign(op1, get_gpr_w1(r1)); 4179 op2 = (Int)(Char)i2; 4180 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_SIGNED_COMPARE, op1, 4181 mktemp(Ity_I32, mkU32((UInt)op2)))); 4182 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4183 mkexpr(op4addr)); 4184 } 4185 } 4186 4187 return "cib"; 4188 } 4189 4190 static const HChar * 4191 s390_irgen_CGIB(UChar r1, UChar m3, UChar i2, IRTemp op4addr) 4192 { 4193 IRTemp op1 = newTemp(Ity_I64); 4194 Long op2; 4195 IRTemp cond = newTemp(Ity_I32); 4196 4197 if (m3 == 0) { 4198 } else { 4199 if (m3 == 14) { 4200 always_goto(mkexpr(op4addr)); 4201 } else { 4202 assign(op1, get_gpr_dw0(r1)); 4203 op2 = (Long)(Char)i2; 4204 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_SIGNED_COMPARE, op1, 4205 mktemp(Ity_I64, mkU64((ULong)op2)))); 4206 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4207 mkexpr(op4addr)); 4208 } 4209 } 4210 4211 return "cgib"; 4212 } 4213 4214 static const HChar * 4215 s390_irgen_CIJ(UChar r1, UChar m3, UShort i4, UChar i2) 4216 { 4217 IRTemp op1 = newTemp(Ity_I32); 4218 Int op2; 4219 IRTemp cond = newTemp(Ity_I32); 4220 4221 if (m3 == 0) { 4222 } else { 4223 if (m3 == 14) { 4224 always_goto_and_chase(guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4225 } else { 4226 assign(op1, get_gpr_w1(r1)); 4227 op2 = (Int)(Char)i2; 4228 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_SIGNED_COMPARE, op1, 4229 mktemp(Ity_I32, mkU32((UInt)op2)))); 4230 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4231 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4232 4233 } 4234 } 4235 4236 return "cij"; 4237 } 4238 4239 static const HChar * 4240 s390_irgen_CGIJ(UChar r1, UChar m3, UShort i4, UChar i2) 4241 { 4242 IRTemp op1 = newTemp(Ity_I64); 4243 Long op2; 4244 IRTemp cond = newTemp(Ity_I32); 4245 4246 if (m3 == 0) { 4247 } else { 4248 if (m3 == 14) { 4249 always_goto_and_chase(guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4250 } else { 4251 assign(op1, get_gpr_dw0(r1)); 4252 op2 = (Long)(Char)i2; 4253 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_SIGNED_COMPARE, op1, 4254 mktemp(Ity_I64, mkU64((ULong)op2)))); 4255 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4256 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4257 4258 } 4259 } 4260 4261 return "cgij"; 4262 } 4263 4264 static const HChar * 4265 s390_irgen_CH(UChar r1, IRTemp op2addr) 4266 { 4267 IRTemp op1 = newTemp(Ity_I32); 4268 IRTemp op2 = newTemp(Ity_I32); 4269 4270 assign(op1, get_gpr_w1(r1)); 4271 assign(op2, unop(Iop_16Sto32, load(Ity_I16, mkexpr(op2addr)))); 4272 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4273 4274 return "ch"; 4275 } 4276 4277 static const HChar * 4278 s390_irgen_CHY(UChar r1, IRTemp op2addr) 4279 { 4280 IRTemp op1 = newTemp(Ity_I32); 4281 IRTemp op2 = newTemp(Ity_I32); 4282 4283 assign(op1, get_gpr_w1(r1)); 4284 assign(op2, unop(Iop_16Sto32, load(Ity_I16, mkexpr(op2addr)))); 4285 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4286 4287 return "chy"; 4288 } 4289 4290 static const HChar * 4291 s390_irgen_CGH(UChar r1, IRTemp op2addr) 4292 { 4293 IRTemp op1 = newTemp(Ity_I64); 4294 IRTemp op2 = newTemp(Ity_I64); 4295 4296 assign(op1, get_gpr_dw0(r1)); 4297 assign(op2, unop(Iop_16Sto64, load(Ity_I16, mkexpr(op2addr)))); 4298 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4299 4300 return "cgh"; 4301 } 4302 4303 static const HChar * 4304 s390_irgen_CHI(UChar r1, UShort i2) 4305 { 4306 IRTemp op1 = newTemp(Ity_I32); 4307 Int op2; 4308 4309 assign(op1, get_gpr_w1(r1)); 4310 op2 = (Int)(Short)i2; 4311 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, mktemp(Ity_I32, 4312 mkU32((UInt)op2))); 4313 4314 return "chi"; 4315 } 4316 4317 static const HChar * 4318 s390_irgen_CGHI(UChar r1, UShort i2) 4319 { 4320 IRTemp op1 = newTemp(Ity_I64); 4321 Long op2; 4322 4323 assign(op1, get_gpr_dw0(r1)); 4324 op2 = (Long)(Short)i2; 4325 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, mktemp(Ity_I64, 4326 mkU64((ULong)op2))); 4327 4328 return "cghi"; 4329 } 4330 4331 static const HChar * 4332 s390_irgen_CHHSI(UShort i2, IRTemp op1addr) 4333 { 4334 IRTemp op1 = newTemp(Ity_I16); 4335 Short op2; 4336 4337 assign(op1, load(Ity_I16, mkexpr(op1addr))); 4338 op2 = (Short)i2; 4339 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, mktemp(Ity_I16, 4340 mkU16((UShort)op2))); 4341 4342 return "chhsi"; 4343 } 4344 4345 static const HChar * 4346 s390_irgen_CHSI(UShort i2, IRTemp op1addr) 4347 { 4348 IRTemp op1 = newTemp(Ity_I32); 4349 Int op2; 4350 4351 assign(op1, load(Ity_I32, mkexpr(op1addr))); 4352 op2 = (Int)(Short)i2; 4353 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, mktemp(Ity_I32, 4354 mkU32((UInt)op2))); 4355 4356 return "chsi"; 4357 } 4358 4359 static const HChar * 4360 s390_irgen_CGHSI(UShort i2, IRTemp op1addr) 4361 { 4362 IRTemp op1 = newTemp(Ity_I64); 4363 Long op2; 4364 4365 assign(op1, load(Ity_I64, mkexpr(op1addr))); 4366 op2 = (Long)(Short)i2; 4367 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, mktemp(Ity_I64, 4368 mkU64((ULong)op2))); 4369 4370 return "cghsi"; 4371 } 4372 4373 static const HChar * 4374 s390_irgen_CHRL(UChar r1, UInt i2) 4375 { 4376 IRTemp op1 = newTemp(Ity_I32); 4377 IRTemp op2 = newTemp(Ity_I32); 4378 4379 assign(op1, get_gpr_w1(r1)); 4380 assign(op2, unop(Iop_16Sto32, load(Ity_I16, mkU64(guest_IA_curr_instr + 4381 ((ULong)(Long)(Int)i2 << 1))))); 4382 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4383 4384 return "chrl"; 4385 } 4386 4387 static const HChar * 4388 s390_irgen_CGHRL(UChar r1, UInt i2) 4389 { 4390 IRTemp op1 = newTemp(Ity_I64); 4391 IRTemp op2 = newTemp(Ity_I64); 4392 4393 assign(op1, get_gpr_dw0(r1)); 4394 assign(op2, unop(Iop_16Sto64, load(Ity_I16, mkU64(guest_IA_curr_instr + 4395 ((ULong)(Long)(Int)i2 << 1))))); 4396 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4397 4398 return "cghrl"; 4399 } 4400 4401 static const HChar * 4402 s390_irgen_CHHR(UChar r1, UChar r2) 4403 { 4404 IRTemp op1 = newTemp(Ity_I32); 4405 IRTemp op2 = newTemp(Ity_I32); 4406 4407 assign(op1, get_gpr_w0(r1)); 4408 assign(op2, get_gpr_w0(r2)); 4409 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4410 4411 return "chhr"; 4412 } 4413 4414 static const HChar * 4415 s390_irgen_CHLR(UChar r1, UChar r2) 4416 { 4417 IRTemp op1 = newTemp(Ity_I32); 4418 IRTemp op2 = newTemp(Ity_I32); 4419 4420 assign(op1, get_gpr_w0(r1)); 4421 assign(op2, get_gpr_w1(r2)); 4422 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4423 4424 return "chlr"; 4425 } 4426 4427 static const HChar * 4428 s390_irgen_CHF(UChar r1, IRTemp op2addr) 4429 { 4430 IRTemp op1 = newTemp(Ity_I32); 4431 IRTemp op2 = newTemp(Ity_I32); 4432 4433 assign(op1, get_gpr_w0(r1)); 4434 assign(op2, load(Ity_I32, mkexpr(op2addr))); 4435 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4436 4437 return "chf"; 4438 } 4439 4440 static const HChar * 4441 s390_irgen_CIH(UChar r1, UInt i2) 4442 { 4443 IRTemp op1 = newTemp(Ity_I32); 4444 Int op2; 4445 4446 assign(op1, get_gpr_w0(r1)); 4447 op2 = (Int)i2; 4448 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, mktemp(Ity_I32, 4449 mkU32((UInt)op2))); 4450 4451 return "cih"; 4452 } 4453 4454 static const HChar * 4455 s390_irgen_CLR(UChar r1, UChar r2) 4456 { 4457 IRTemp op1 = newTemp(Ity_I32); 4458 IRTemp op2 = newTemp(Ity_I32); 4459 4460 assign(op1, get_gpr_w1(r1)); 4461 assign(op2, get_gpr_w1(r2)); 4462 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4463 4464 return "clr"; 4465 } 4466 4467 static const HChar * 4468 s390_irgen_CLGR(UChar r1, UChar r2) 4469 { 4470 IRTemp op1 = newTemp(Ity_I64); 4471 IRTemp op2 = newTemp(Ity_I64); 4472 4473 assign(op1, get_gpr_dw0(r1)); 4474 assign(op2, get_gpr_dw0(r2)); 4475 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4476 4477 return "clgr"; 4478 } 4479 4480 static const HChar * 4481 s390_irgen_CLGFR(UChar r1, UChar r2) 4482 { 4483 IRTemp op1 = newTemp(Ity_I64); 4484 IRTemp op2 = newTemp(Ity_I64); 4485 4486 assign(op1, get_gpr_dw0(r1)); 4487 assign(op2, unop(Iop_32Uto64, get_gpr_w1(r2))); 4488 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4489 4490 return "clgfr"; 4491 } 4492 4493 static const HChar * 4494 s390_irgen_CL(UChar r1, IRTemp op2addr) 4495 { 4496 IRTemp op1 = newTemp(Ity_I32); 4497 IRTemp op2 = newTemp(Ity_I32); 4498 4499 assign(op1, get_gpr_w1(r1)); 4500 assign(op2, load(Ity_I32, mkexpr(op2addr))); 4501 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4502 4503 return "cl"; 4504 } 4505 4506 static const HChar * 4507 s390_irgen_CLY(UChar r1, IRTemp op2addr) 4508 { 4509 IRTemp op1 = newTemp(Ity_I32); 4510 IRTemp op2 = newTemp(Ity_I32); 4511 4512 assign(op1, get_gpr_w1(r1)); 4513 assign(op2, load(Ity_I32, mkexpr(op2addr))); 4514 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4515 4516 return "cly"; 4517 } 4518 4519 static const HChar * 4520 s390_irgen_CLG(UChar r1, IRTemp op2addr) 4521 { 4522 IRTemp op1 = newTemp(Ity_I64); 4523 IRTemp op2 = newTemp(Ity_I64); 4524 4525 assign(op1, get_gpr_dw0(r1)); 4526 assign(op2, load(Ity_I64, mkexpr(op2addr))); 4527 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4528 4529 return "clg"; 4530 } 4531 4532 static const HChar * 4533 s390_irgen_CLGF(UChar r1, IRTemp op2addr) 4534 { 4535 IRTemp op1 = newTemp(Ity_I64); 4536 IRTemp op2 = newTemp(Ity_I64); 4537 4538 assign(op1, get_gpr_dw0(r1)); 4539 assign(op2, unop(Iop_32Uto64, load(Ity_I32, mkexpr(op2addr)))); 4540 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4541 4542 return "clgf"; 4543 } 4544 4545 static const HChar * 4546 s390_irgen_CLFI(UChar r1, UInt i2) 4547 { 4548 IRTemp op1 = newTemp(Ity_I32); 4549 UInt op2; 4550 4551 assign(op1, get_gpr_w1(r1)); 4552 op2 = i2; 4553 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, mktemp(Ity_I32, 4554 mkU32(op2))); 4555 4556 return "clfi"; 4557 } 4558 4559 static const HChar * 4560 s390_irgen_CLGFI(UChar r1, UInt i2) 4561 { 4562 IRTemp op1 = newTemp(Ity_I64); 4563 ULong op2; 4564 4565 assign(op1, get_gpr_dw0(r1)); 4566 op2 = (ULong)i2; 4567 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, mktemp(Ity_I64, 4568 mkU64(op2))); 4569 4570 return "clgfi"; 4571 } 4572 4573 static const HChar * 4574 s390_irgen_CLI(UChar i2, IRTemp op1addr) 4575 { 4576 IRTemp op1 = newTemp(Ity_I8); 4577 UChar op2; 4578 4579 assign(op1, load(Ity_I8, mkexpr(op1addr))); 4580 op2 = i2; 4581 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, mktemp(Ity_I8, 4582 mkU8(op2))); 4583 4584 return "cli"; 4585 } 4586 4587 static const HChar * 4588 s390_irgen_CLIY(UChar i2, IRTemp op1addr) 4589 { 4590 IRTemp op1 = newTemp(Ity_I8); 4591 UChar op2; 4592 4593 assign(op1, load(Ity_I8, mkexpr(op1addr))); 4594 op2 = i2; 4595 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, mktemp(Ity_I8, 4596 mkU8(op2))); 4597 4598 return "cliy"; 4599 } 4600 4601 static const HChar * 4602 s390_irgen_CLFHSI(UShort i2, IRTemp op1addr) 4603 { 4604 IRTemp op1 = newTemp(Ity_I32); 4605 UInt op2; 4606 4607 assign(op1, load(Ity_I32, mkexpr(op1addr))); 4608 op2 = (UInt)i2; 4609 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, mktemp(Ity_I32, 4610 mkU32(op2))); 4611 4612 return "clfhsi"; 4613 } 4614 4615 static const HChar * 4616 s390_irgen_CLGHSI(UShort i2, IRTemp op1addr) 4617 { 4618 IRTemp op1 = newTemp(Ity_I64); 4619 ULong op2; 4620 4621 assign(op1, load(Ity_I64, mkexpr(op1addr))); 4622 op2 = (ULong)i2; 4623 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, mktemp(Ity_I64, 4624 mkU64(op2))); 4625 4626 return "clghsi"; 4627 } 4628 4629 static const HChar * 4630 s390_irgen_CLHHSI(UShort i2, IRTemp op1addr) 4631 { 4632 IRTemp op1 = newTemp(Ity_I16); 4633 UShort op2; 4634 4635 assign(op1, load(Ity_I16, mkexpr(op1addr))); 4636 op2 = i2; 4637 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, mktemp(Ity_I16, 4638 mkU16(op2))); 4639 4640 return "clhhsi"; 4641 } 4642 4643 static const HChar * 4644 s390_irgen_CLRL(UChar r1, UInt i2) 4645 { 4646 IRTemp op1 = newTemp(Ity_I32); 4647 IRTemp op2 = newTemp(Ity_I32); 4648 4649 assign(op1, get_gpr_w1(r1)); 4650 assign(op2, load(Ity_I32, mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int) 4651 i2 << 1)))); 4652 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4653 4654 return "clrl"; 4655 } 4656 4657 static const HChar * 4658 s390_irgen_CLGRL(UChar r1, UInt i2) 4659 { 4660 IRTemp op1 = newTemp(Ity_I64); 4661 IRTemp op2 = newTemp(Ity_I64); 4662 4663 assign(op1, get_gpr_dw0(r1)); 4664 assign(op2, load(Ity_I64, mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int) 4665 i2 << 1)))); 4666 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4667 4668 return "clgrl"; 4669 } 4670 4671 static const HChar * 4672 s390_irgen_CLGFRL(UChar r1, UInt i2) 4673 { 4674 IRTemp op1 = newTemp(Ity_I64); 4675 IRTemp op2 = newTemp(Ity_I64); 4676 4677 assign(op1, get_gpr_dw0(r1)); 4678 assign(op2, unop(Iop_32Uto64, load(Ity_I32, mkU64(guest_IA_curr_instr + 4679 ((ULong)(Long)(Int)i2 << 1))))); 4680 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4681 4682 return "clgfrl"; 4683 } 4684 4685 static const HChar * 4686 s390_irgen_CLHRL(UChar r1, UInt i2) 4687 { 4688 IRTemp op1 = newTemp(Ity_I32); 4689 IRTemp op2 = newTemp(Ity_I32); 4690 4691 assign(op1, get_gpr_w1(r1)); 4692 assign(op2, unop(Iop_16Uto32, load(Ity_I16, mkU64(guest_IA_curr_instr + 4693 ((ULong)(Long)(Int)i2 << 1))))); 4694 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4695 4696 return "clhrl"; 4697 } 4698 4699 static const HChar * 4700 s390_irgen_CLGHRL(UChar r1, UInt i2) 4701 { 4702 IRTemp op1 = newTemp(Ity_I64); 4703 IRTemp op2 = newTemp(Ity_I64); 4704 4705 assign(op1, get_gpr_dw0(r1)); 4706 assign(op2, unop(Iop_16Uto64, load(Ity_I16, mkU64(guest_IA_curr_instr + 4707 ((ULong)(Long)(Int)i2 << 1))))); 4708 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4709 4710 return "clghrl"; 4711 } 4712 4713 static const HChar * 4714 s390_irgen_CLRB(UChar r1, UChar r2, UChar m3, IRTemp op4addr) 4715 { 4716 IRTemp op1 = newTemp(Ity_I32); 4717 IRTemp op2 = newTemp(Ity_I32); 4718 IRTemp cond = newTemp(Ity_I32); 4719 4720 if (m3 == 0) { 4721 } else { 4722 if (m3 == 14) { 4723 always_goto(mkexpr(op4addr)); 4724 } else { 4725 assign(op1, get_gpr_w1(r1)); 4726 assign(op2, get_gpr_w1(r2)); 4727 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_UNSIGNED_COMPARE, 4728 op1, op2)); 4729 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4730 mkexpr(op4addr)); 4731 } 4732 } 4733 4734 return "clrb"; 4735 } 4736 4737 static const HChar * 4738 s390_irgen_CLGRB(UChar r1, UChar r2, UChar m3, IRTemp op4addr) 4739 { 4740 IRTemp op1 = newTemp(Ity_I64); 4741 IRTemp op2 = newTemp(Ity_I64); 4742 IRTemp cond = newTemp(Ity_I32); 4743 4744 if (m3 == 0) { 4745 } else { 4746 if (m3 == 14) { 4747 always_goto(mkexpr(op4addr)); 4748 } else { 4749 assign(op1, get_gpr_dw0(r1)); 4750 assign(op2, get_gpr_dw0(r2)); 4751 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_UNSIGNED_COMPARE, 4752 op1, op2)); 4753 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4754 mkexpr(op4addr)); 4755 } 4756 } 4757 4758 return "clgrb"; 4759 } 4760 4761 static const HChar * 4762 s390_irgen_CLRJ(UChar r1, UChar r2, UShort i4, UChar m3) 4763 { 4764 IRTemp op1 = newTemp(Ity_I32); 4765 IRTemp op2 = newTemp(Ity_I32); 4766 IRTemp cond = newTemp(Ity_I32); 4767 4768 if (m3 == 0) { 4769 } else { 4770 if (m3 == 14) { 4771 always_goto_and_chase(guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4772 } else { 4773 assign(op1, get_gpr_w1(r1)); 4774 assign(op2, get_gpr_w1(r2)); 4775 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_UNSIGNED_COMPARE, 4776 op1, op2)); 4777 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4778 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4779 4780 } 4781 } 4782 4783 return "clrj"; 4784 } 4785 4786 static const HChar * 4787 s390_irgen_CLGRJ(UChar r1, UChar r2, UShort i4, UChar m3) 4788 { 4789 IRTemp op1 = newTemp(Ity_I64); 4790 IRTemp op2 = newTemp(Ity_I64); 4791 IRTemp cond = newTemp(Ity_I32); 4792 4793 if (m3 == 0) { 4794 } else { 4795 if (m3 == 14) { 4796 always_goto_and_chase(guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4797 } else { 4798 assign(op1, get_gpr_dw0(r1)); 4799 assign(op2, get_gpr_dw0(r2)); 4800 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_UNSIGNED_COMPARE, 4801 op1, op2)); 4802 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4803 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4804 4805 } 4806 } 4807 4808 return "clgrj"; 4809 } 4810 4811 static const HChar * 4812 s390_irgen_CLIB(UChar r1, UChar m3, UChar i2, IRTemp op4addr) 4813 { 4814 IRTemp op1 = newTemp(Ity_I32); 4815 UInt op2; 4816 IRTemp cond = newTemp(Ity_I32); 4817 4818 if (m3 == 0) { 4819 } else { 4820 if (m3 == 14) { 4821 always_goto(mkexpr(op4addr)); 4822 } else { 4823 assign(op1, get_gpr_w1(r1)); 4824 op2 = (UInt)i2; 4825 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_UNSIGNED_COMPARE, op1, 4826 mktemp(Ity_I32, mkU32(op2)))); 4827 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4828 mkexpr(op4addr)); 4829 } 4830 } 4831 4832 return "clib"; 4833 } 4834 4835 static const HChar * 4836 s390_irgen_CLGIB(UChar r1, UChar m3, UChar i2, IRTemp op4addr) 4837 { 4838 IRTemp op1 = newTemp(Ity_I64); 4839 ULong op2; 4840 IRTemp cond = newTemp(Ity_I32); 4841 4842 if (m3 == 0) { 4843 } else { 4844 if (m3 == 14) { 4845 always_goto(mkexpr(op4addr)); 4846 } else { 4847 assign(op1, get_gpr_dw0(r1)); 4848 op2 = (ULong)i2; 4849 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_UNSIGNED_COMPARE, op1, 4850 mktemp(Ity_I64, mkU64(op2)))); 4851 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4852 mkexpr(op4addr)); 4853 } 4854 } 4855 4856 return "clgib"; 4857 } 4858 4859 static const HChar * 4860 s390_irgen_CLIJ(UChar r1, UChar m3, UShort i4, UChar i2) 4861 { 4862 IRTemp op1 = newTemp(Ity_I32); 4863 UInt op2; 4864 IRTemp cond = newTemp(Ity_I32); 4865 4866 if (m3 == 0) { 4867 } else { 4868 if (m3 == 14) { 4869 always_goto_and_chase(guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4870 } else { 4871 assign(op1, get_gpr_w1(r1)); 4872 op2 = (UInt)i2; 4873 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_UNSIGNED_COMPARE, op1, 4874 mktemp(Ity_I32, mkU32(op2)))); 4875 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4876 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4877 4878 } 4879 } 4880 4881 return "clij"; 4882 } 4883 4884 static const HChar * 4885 s390_irgen_CLGIJ(UChar r1, UChar m3, UShort i4, UChar i2) 4886 { 4887 IRTemp op1 = newTemp(Ity_I64); 4888 ULong op2; 4889 IRTemp cond = newTemp(Ity_I32); 4890 4891 if (m3 == 0) { 4892 } else { 4893 if (m3 == 14) { 4894 always_goto_and_chase(guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4895 } else { 4896 assign(op1, get_gpr_dw0(r1)); 4897 op2 = (ULong)i2; 4898 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_UNSIGNED_COMPARE, op1, 4899 mktemp(Ity_I64, mkU64(op2)))); 4900 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4901 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4902 4903 } 4904 } 4905 4906 return "clgij"; 4907 } 4908 4909 static const HChar * 4910 s390_irgen_CLM(UChar r1, UChar r3, IRTemp op2addr) 4911 { 4912 IRTemp op1 = newTemp(Ity_I32); 4913 IRTemp op2 = newTemp(Ity_I32); 4914 IRTemp b0 = newTemp(Ity_I32); 4915 IRTemp b1 = newTemp(Ity_I32); 4916 IRTemp b2 = newTemp(Ity_I32); 4917 IRTemp b3 = newTemp(Ity_I32); 4918 IRTemp c0 = newTemp(Ity_I32); 4919 IRTemp c1 = newTemp(Ity_I32); 4920 IRTemp c2 = newTemp(Ity_I32); 4921 IRTemp c3 = newTemp(Ity_I32); 4922 UChar n; 4923 4924 n = 0; 4925 if ((r3 & 8) != 0) { 4926 assign(b0, unop(Iop_8Uto32, get_gpr_b4(r1))); 4927 assign(c0, unop(Iop_8Uto32, load(Ity_I8, mkexpr(op2addr)))); 4928 n = n + 1; 4929 } else { 4930 assign(b0, mkU32(0)); 4931 assign(c0, mkU32(0)); 4932 } 4933 if ((r3 & 4) != 0) { 4934 assign(b1, unop(Iop_8Uto32, get_gpr_b5(r1))); 4935 assign(c1, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 4936 mkU64(n))))); 4937 n = n + 1; 4938 } else { 4939 assign(b1, mkU32(0)); 4940 assign(c1, mkU32(0)); 4941 } 4942 if ((r3 & 2) != 0) { 4943 assign(b2, unop(Iop_8Uto32, get_gpr_b6(r1))); 4944 assign(c2, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 4945 mkU64(n))))); 4946 n = n + 1; 4947 } else { 4948 assign(b2, mkU32(0)); 4949 assign(c2, mkU32(0)); 4950 } 4951 if ((r3 & 1) != 0) { 4952 assign(b3, unop(Iop_8Uto32, get_gpr_b7(r1))); 4953 assign(c3, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 4954 mkU64(n))))); 4955 n = n + 1; 4956 } else { 4957 assign(b3, mkU32(0)); 4958 assign(c3, mkU32(0)); 4959 } 4960 assign(op1, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Shl32, 4961 mkexpr(b0), mkU8(24)), binop(Iop_Shl32, mkexpr(b1), mkU8(16))), 4962 binop(Iop_Shl32, mkexpr(b2), mkU8(8))), mkexpr(b3))); 4963 assign(op2, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Shl32, 4964 mkexpr(c0), mkU8(24)), binop(Iop_Shl32, mkexpr(c1), mkU8(16))), 4965 binop(Iop_Shl32, mkexpr(c2), mkU8(8))), mkexpr(c3))); 4966 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4967 4968 return "clm"; 4969 } 4970 4971 static const HChar * 4972 s390_irgen_CLMY(UChar r1, UChar r3, IRTemp op2addr) 4973 { 4974 IRTemp op1 = newTemp(Ity_I32); 4975 IRTemp op2 = newTemp(Ity_I32); 4976 IRTemp b0 = newTemp(Ity_I32); 4977 IRTemp b1 = newTemp(Ity_I32); 4978 IRTemp b2 = newTemp(Ity_I32); 4979 IRTemp b3 = newTemp(Ity_I32); 4980 IRTemp c0 = newTemp(Ity_I32); 4981 IRTemp c1 = newTemp(Ity_I32); 4982 IRTemp c2 = newTemp(Ity_I32); 4983 IRTemp c3 = newTemp(Ity_I32); 4984 UChar n; 4985 4986 n = 0; 4987 if ((r3 & 8) != 0) { 4988 assign(b0, unop(Iop_8Uto32, get_gpr_b4(r1))); 4989 assign(c0, unop(Iop_8Uto32, load(Ity_I8, mkexpr(op2addr)))); 4990 n = n + 1; 4991 } else { 4992 assign(b0, mkU32(0)); 4993 assign(c0, mkU32(0)); 4994 } 4995 if ((r3 & 4) != 0) { 4996 assign(b1, unop(Iop_8Uto32, get_gpr_b5(r1))); 4997 assign(c1, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 4998 mkU64(n))))); 4999 n = n + 1; 5000 } else { 5001 assign(b1, mkU32(0)); 5002 assign(c1, mkU32(0)); 5003 } 5004 if ((r3 & 2) != 0) { 5005 assign(b2, unop(Iop_8Uto32, get_gpr_b6(r1))); 5006 assign(c2, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 5007 mkU64(n))))); 5008 n = n + 1; 5009 } else { 5010 assign(b2, mkU32(0)); 5011 assign(c2, mkU32(0)); 5012 } 5013 if ((r3 & 1) != 0) { 5014 assign(b3, unop(Iop_8Uto32, get_gpr_b7(r1))); 5015 assign(c3, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 5016 mkU64(n))))); 5017 n = n + 1; 5018 } else { 5019 assign(b3, mkU32(0)); 5020 assign(c3, mkU32(0)); 5021 } 5022 assign(op1, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Shl32, 5023 mkexpr(b0), mkU8(24)), binop(Iop_Shl32, mkexpr(b1), mkU8(16))), 5024 binop(Iop_Shl32, mkexpr(b2), mkU8(8))), mkexpr(b3))); 5025 assign(op2, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Shl32, 5026 mkexpr(c0), mkU8(24)), binop(Iop_Shl32, mkexpr(c1), mkU8(16))), 5027 binop(Iop_Shl32, mkexpr(c2), mkU8(8))), mkexpr(c3))); 5028 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 5029 5030 return "clmy"; 5031 } 5032 5033 static const HChar * 5034 s390_irgen_CLMH(UChar r1, UChar r3, IRTemp op2addr) 5035 { 5036 IRTemp op1 = newTemp(Ity_I32); 5037 IRTemp op2 = newTemp(Ity_I32); 5038 IRTemp b0 = newTemp(Ity_I32); 5039 IRTemp b1 = newTemp(Ity_I32); 5040 IRTemp b2 = newTemp(Ity_I32); 5041 IRTemp b3 = newTemp(Ity_I32); 5042 IRTemp c0 = newTemp(Ity_I32); 5043 IRTemp c1 = newTemp(Ity_I32); 5044 IRTemp c2 = newTemp(Ity_I32); 5045 IRTemp c3 = newTemp(Ity_I32); 5046 UChar n; 5047 5048 n = 0; 5049 if ((r3 & 8) != 0) { 5050 assign(b0, unop(Iop_8Uto32, get_gpr_b0(r1))); 5051 assign(c0, unop(Iop_8Uto32, load(Ity_I8, mkexpr(op2addr)))); 5052 n = n + 1; 5053 } else { 5054 assign(b0, mkU32(0)); 5055 assign(c0, mkU32(0)); 5056 } 5057 if ((r3 & 4) != 0) { 5058 assign(b1, unop(Iop_8Uto32, get_gpr_b1(r1))); 5059 assign(c1, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 5060 mkU64(n))))); 5061 n = n + 1; 5062 } else { 5063 assign(b1, mkU32(0)); 5064 assign(c1, mkU32(0)); 5065 } 5066 if ((r3 & 2) != 0) { 5067 assign(b2, unop(Iop_8Uto32, get_gpr_b2(r1))); 5068 assign(c2, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 5069 mkU64(n))))); 5070 n = n + 1; 5071 } else { 5072 assign(b2, mkU32(0)); 5073 assign(c2, mkU32(0)); 5074 } 5075 if ((r3 & 1) != 0) { 5076 assign(b3, unop(Iop_8Uto32, get_gpr_b3(r1))); 5077 assign(c3, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 5078 mkU64(n))))); 5079 n = n + 1; 5080 } else { 5081 assign(b3, mkU32(0)); 5082 assign(c3, mkU32(0)); 5083 } 5084 assign(op1, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Shl32, 5085 mkexpr(b0), mkU8(24)), binop(Iop_Shl32, mkexpr(b1), mkU8(16))), 5086 binop(Iop_Shl32, mkexpr(b2), mkU8(8))), mkexpr(b3))); 5087 assign(op2, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Shl32, 5088 mkexpr(c0), mkU8(24)), binop(Iop_Shl32, mkexpr(c1), mkU8(16))), 5089 binop(Iop_Shl32, mkexpr(c2), mkU8(8))), mkexpr(c3))); 5090 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 5091 5092 return "clmh"; 5093 } 5094 5095 static const HChar * 5096 s390_irgen_CLHHR(UChar r1, UChar r2) 5097 { 5098 IRTemp op1 = newTemp(Ity_I32); 5099 IRTemp op2 = newTemp(Ity_I32); 5100 5101 assign(op1, get_gpr_w0(r1)); 5102 assign(op2, get_gpr_w0(r2)); 5103 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 5104 5105 return "clhhr"; 5106 } 5107 5108 static const HChar * 5109 s390_irgen_CLHLR(UChar r1, UChar r2) 5110 { 5111 IRTemp op1 = newTemp(Ity_I32); 5112 IRTemp op2 = newTemp(Ity_I32); 5113 5114 assign(op1, get_gpr_w0(r1)); 5115 assign(op2, get_gpr_w1(r2)); 5116 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 5117 5118 return "clhlr"; 5119 } 5120 5121 static const HChar * 5122 s390_irgen_CLHF(UChar r1, IRTemp op2addr) 5123 { 5124 IRTemp op1 = newTemp(Ity_I32); 5125 IRTemp op2 = newTemp(Ity_I32); 5126 5127 assign(op1, get_gpr_w0(r1)); 5128 assign(op2, load(Ity_I32, mkexpr(op2addr))); 5129 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 5130 5131 return "clhf"; 5132 } 5133 5134 static const HChar * 5135 s390_irgen_CLIH(UChar r1, UInt i2) 5136 { 5137 IRTemp op1 = newTemp(Ity_I32); 5138 UInt op2; 5139 5140 assign(op1, get_gpr_w0(r1)); 5141 op2 = i2; 5142 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, mktemp(Ity_I32, 5143 mkU32(op2))); 5144 5145 return "clih"; 5146 } 5147 5148 static const HChar * 5149 s390_irgen_CPYA(UChar r1, UChar r2) 5150 { 5151 put_ar_w0(r1, get_ar_w0(r2)); 5152 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 5153 s390_disasm(ENC3(MNM, AR, AR), "cpya", r1, r2); 5154 5155 return "cpya"; 5156 } 5157 5158 static const HChar * 5159 s390_irgen_XR(UChar r1, UChar r2) 5160 { 5161 IRTemp op1 = newTemp(Ity_I32); 5162 IRTemp op2 = newTemp(Ity_I32); 5163 IRTemp result = newTemp(Ity_I32); 5164 5165 if (r1 == r2) { 5166 assign(result, mkU32(0)); 5167 } else { 5168 assign(op1, get_gpr_w1(r1)); 5169 assign(op2, get_gpr_w1(r2)); 5170 assign(result, binop(Iop_Xor32, mkexpr(op1), mkexpr(op2))); 5171 } 5172 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5173 put_gpr_w1(r1, mkexpr(result)); 5174 5175 return "xr"; 5176 } 5177 5178 static const HChar * 5179 s390_irgen_XGR(UChar r1, UChar r2) 5180 { 5181 IRTemp op1 = newTemp(Ity_I64); 5182 IRTemp op2 = newTemp(Ity_I64); 5183 IRTemp result = newTemp(Ity_I64); 5184 5185 if (r1 == r2) { 5186 assign(result, mkU64(0)); 5187 } else { 5188 assign(op1, get_gpr_dw0(r1)); 5189 assign(op2, get_gpr_dw0(r2)); 5190 assign(result, binop(Iop_Xor64, mkexpr(op1), mkexpr(op2))); 5191 } 5192 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5193 put_gpr_dw0(r1, mkexpr(result)); 5194 5195 return "xgr"; 5196 } 5197 5198 static const HChar * 5199 s390_irgen_XRK(UChar r3, UChar r1, UChar r2) 5200 { 5201 IRTemp op2 = newTemp(Ity_I32); 5202 IRTemp op3 = newTemp(Ity_I32); 5203 IRTemp result = newTemp(Ity_I32); 5204 5205 assign(op2, get_gpr_w1(r2)); 5206 assign(op3, get_gpr_w1(r3)); 5207 assign(result, binop(Iop_Xor32, mkexpr(op2), mkexpr(op3))); 5208 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5209 put_gpr_w1(r1, mkexpr(result)); 5210 5211 return "xrk"; 5212 } 5213 5214 static const HChar * 5215 s390_irgen_XGRK(UChar r3, UChar r1, UChar r2) 5216 { 5217 IRTemp op2 = newTemp(Ity_I64); 5218 IRTemp op3 = newTemp(Ity_I64); 5219 IRTemp result = newTemp(Ity_I64); 5220 5221 assign(op2, get_gpr_dw0(r2)); 5222 assign(op3, get_gpr_dw0(r3)); 5223 assign(result, binop(Iop_Xor64, mkexpr(op2), mkexpr(op3))); 5224 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5225 put_gpr_dw0(r1, mkexpr(result)); 5226 5227 return "xgrk"; 5228 } 5229 5230 static const HChar * 5231 s390_irgen_X(UChar r1, IRTemp op2addr) 5232 { 5233 IRTemp op1 = newTemp(Ity_I32); 5234 IRTemp op2 = newTemp(Ity_I32); 5235 IRTemp result = newTemp(Ity_I32); 5236 5237 assign(op1, get_gpr_w1(r1)); 5238 assign(op2, load(Ity_I32, mkexpr(op2addr))); 5239 assign(result, binop(Iop_Xor32, mkexpr(op1), mkexpr(op2))); 5240 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5241 put_gpr_w1(r1, mkexpr(result)); 5242 5243 return "x"; 5244 } 5245 5246 static const HChar * 5247 s390_irgen_XY(UChar r1, IRTemp op2addr) 5248 { 5249 IRTemp op1 = newTemp(Ity_I32); 5250 IRTemp op2 = newTemp(Ity_I32); 5251 IRTemp result = newTemp(Ity_I32); 5252 5253 assign(op1, get_gpr_w1(r1)); 5254 assign(op2, load(Ity_I32, mkexpr(op2addr))); 5255 assign(result, binop(Iop_Xor32, mkexpr(op1), mkexpr(op2))); 5256 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5257 put_gpr_w1(r1, mkexpr(result)); 5258 5259 return "xy"; 5260 } 5261 5262 static const HChar * 5263 s390_irgen_XG(UChar r1, IRTemp op2addr) 5264 { 5265 IRTemp op1 = newTemp(Ity_I64); 5266 IRTemp op2 = newTemp(Ity_I64); 5267 IRTemp result = newTemp(Ity_I64); 5268 5269 assign(op1, get_gpr_dw0(r1)); 5270 assign(op2, load(Ity_I64, mkexpr(op2addr))); 5271 assign(result, binop(Iop_Xor64, mkexpr(op1), mkexpr(op2))); 5272 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5273 put_gpr_dw0(r1, mkexpr(result)); 5274 5275 return "xg"; 5276 } 5277 5278 static const HChar * 5279 s390_irgen_XI(UChar i2, IRTemp op1addr) 5280 { 5281 IRTemp op1 = newTemp(Ity_I8); 5282 UChar op2; 5283 IRTemp result = newTemp(Ity_I8); 5284 5285 assign(op1, load(Ity_I8, mkexpr(op1addr))); 5286 op2 = i2; 5287 assign(result, binop(Iop_Xor8, mkexpr(op1), mkU8(op2))); 5288 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5289 store(mkexpr(op1addr), mkexpr(result)); 5290 5291 return "xi"; 5292 } 5293 5294 static const HChar * 5295 s390_irgen_XIY(UChar i2, IRTemp op1addr) 5296 { 5297 IRTemp op1 = newTemp(Ity_I8); 5298 UChar op2; 5299 IRTemp result = newTemp(Ity_I8); 5300 5301 assign(op1, load(Ity_I8, mkexpr(op1addr))); 5302 op2 = i2; 5303 assign(result, binop(Iop_Xor8, mkexpr(op1), mkU8(op2))); 5304 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5305 store(mkexpr(op1addr), mkexpr(result)); 5306 5307 return "xiy"; 5308 } 5309 5310 static const HChar * 5311 s390_irgen_XIHF(UChar r1, UInt i2) 5312 { 5313 IRTemp op1 = newTemp(Ity_I32); 5314 UInt op2; 5315 IRTemp result = newTemp(Ity_I32); 5316 5317 assign(op1, get_gpr_w0(r1)); 5318 op2 = i2; 5319 assign(result, binop(Iop_Xor32, mkexpr(op1), mkU32(op2))); 5320 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5321 put_gpr_w0(r1, mkexpr(result)); 5322 5323 return "xihf"; 5324 } 5325 5326 static const HChar * 5327 s390_irgen_XILF(UChar r1, UInt i2) 5328 { 5329 IRTemp op1 = newTemp(Ity_I32); 5330 UInt op2; 5331 IRTemp result = newTemp(Ity_I32); 5332 5333 assign(op1, get_gpr_w1(r1)); 5334 op2 = i2; 5335 assign(result, binop(Iop_Xor32, mkexpr(op1), mkU32(op2))); 5336 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5337 put_gpr_w1(r1, mkexpr(result)); 5338 5339 return "xilf"; 5340 } 5341 5342 static const HChar * 5343 s390_irgen_EAR(UChar r1, UChar r2) 5344 { 5345 put_gpr_w1(r1, get_ar_w0(r2)); 5346 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 5347 s390_disasm(ENC3(MNM, GPR, AR), "ear", r1, r2); 5348 5349 return "ear"; 5350 } 5351 5352 static const HChar * 5353 s390_irgen_IC(UChar r1, IRTemp op2addr) 5354 { 5355 put_gpr_b7(r1, load(Ity_I8, mkexpr(op2addr))); 5356 5357 return "ic"; 5358 } 5359 5360 static const HChar * 5361 s390_irgen_ICY(UChar r1, IRTemp op2addr) 5362 { 5363 put_gpr_b7(r1, load(Ity_I8, mkexpr(op2addr))); 5364 5365 return "icy"; 5366 } 5367 5368 static const HChar * 5369 s390_irgen_ICM(UChar r1, UChar r3, IRTemp op2addr) 5370 { 5371 UChar n; 5372 IRTemp result = newTemp(Ity_I32); 5373 UInt mask; 5374 5375 n = 0; 5376 mask = (UInt)r3; 5377 if ((mask & 8) != 0) { 5378 put_gpr_b4(r1, load(Ity_I8, mkexpr(op2addr))); 5379 n = n + 1; 5380 } 5381 if ((mask & 4) != 0) { 5382 put_gpr_b5(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5383 5384 n = n + 1; 5385 } 5386 if ((mask & 2) != 0) { 5387 put_gpr_b6(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5388 5389 n = n + 1; 5390 } 5391 if ((mask & 1) != 0) { 5392 put_gpr_b7(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5393 5394 n = n + 1; 5395 } 5396 assign(result, get_gpr_w1(r1)); 5397 s390_cc_thunk_putZZ(S390_CC_OP_INSERT_CHAR_MASK_32, result, mktemp(Ity_I32, 5398 mkU32(mask))); 5399 5400 return "icm"; 5401 } 5402 5403 static const HChar * 5404 s390_irgen_ICMY(UChar r1, UChar r3, IRTemp op2addr) 5405 { 5406 UChar n; 5407 IRTemp result = newTemp(Ity_I32); 5408 UInt mask; 5409 5410 n = 0; 5411 mask = (UInt)r3; 5412 if ((mask & 8) != 0) { 5413 put_gpr_b4(r1, load(Ity_I8, mkexpr(op2addr))); 5414 n = n + 1; 5415 } 5416 if ((mask & 4) != 0) { 5417 put_gpr_b5(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5418 5419 n = n + 1; 5420 } 5421 if ((mask & 2) != 0) { 5422 put_gpr_b6(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5423 5424 n = n + 1; 5425 } 5426 if ((mask & 1) != 0) { 5427 put_gpr_b7(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5428 5429 n = n + 1; 5430 } 5431 assign(result, get_gpr_w1(r1)); 5432 s390_cc_thunk_putZZ(S390_CC_OP_INSERT_CHAR_MASK_32, result, mktemp(Ity_I32, 5433 mkU32(mask))); 5434 5435 return "icmy"; 5436 } 5437 5438 static const HChar * 5439 s390_irgen_ICMH(UChar r1, UChar r3, IRTemp op2addr) 5440 { 5441 UChar n; 5442 IRTemp result = newTemp(Ity_I32); 5443 UInt mask; 5444 5445 n = 0; 5446 mask = (UInt)r3; 5447 if ((mask & 8) != 0) { 5448 put_gpr_b0(r1, load(Ity_I8, mkexpr(op2addr))); 5449 n = n + 1; 5450 } 5451 if ((mask & 4) != 0) { 5452 put_gpr_b1(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5453 5454 n = n + 1; 5455 } 5456 if ((mask & 2) != 0) { 5457 put_gpr_b2(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5458 5459 n = n + 1; 5460 } 5461 if ((mask & 1) != 0) { 5462 put_gpr_b3(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5463 5464 n = n + 1; 5465 } 5466 assign(result, get_gpr_w0(r1)); 5467 s390_cc_thunk_putZZ(S390_CC_OP_INSERT_CHAR_MASK_32, result, mktemp(Ity_I32, 5468 mkU32(mask))); 5469 5470 return "icmh"; 5471 } 5472 5473 static const HChar * 5474 s390_irgen_IIHF(UChar r1, UInt i2) 5475 { 5476 put_gpr_w0(r1, mkU32(i2)); 5477 5478 return "iihf"; 5479 } 5480 5481 static const HChar * 5482 s390_irgen_IIHH(UChar r1, UShort i2) 5483 { 5484 put_gpr_hw0(r1, mkU16(i2)); 5485 5486 return "iihh"; 5487 } 5488 5489 static const HChar * 5490 s390_irgen_IIHL(UChar r1, UShort i2) 5491 { 5492 put_gpr_hw1(r1, mkU16(i2)); 5493 5494 return "iihl"; 5495 } 5496 5497 static const HChar * 5498 s390_irgen_IILF(UChar r1, UInt i2) 5499 { 5500 put_gpr_w1(r1, mkU32(i2)); 5501 5502 return "iilf"; 5503 } 5504 5505 static const HChar * 5506 s390_irgen_IILH(UChar r1, UShort i2) 5507 { 5508 put_gpr_hw2(r1, mkU16(i2)); 5509 5510 return "iilh"; 5511 } 5512 5513 static const HChar * 5514 s390_irgen_IILL(UChar r1, UShort i2) 5515 { 5516 put_gpr_hw3(r1, mkU16(i2)); 5517 5518 return "iill"; 5519 } 5520 5521 static const HChar * 5522 s390_irgen_LR(UChar r1, UChar r2) 5523 { 5524 put_gpr_w1(r1, get_gpr_w1(r2)); 5525 5526 return "lr"; 5527 } 5528 5529 static const HChar * 5530 s390_irgen_LGR(UChar r1, UChar r2) 5531 { 5532 put_gpr_dw0(r1, get_gpr_dw0(r2)); 5533 5534 return "lgr"; 5535 } 5536 5537 static const HChar * 5538 s390_irgen_LGFR(UChar r1, UChar r2) 5539 { 5540 put_gpr_dw0(r1, unop(Iop_32Sto64, get_gpr_w1(r2))); 5541 5542 return "lgfr"; 5543 } 5544 5545 static const HChar * 5546 s390_irgen_L(UChar r1, IRTemp op2addr) 5547 { 5548 put_gpr_w1(r1, load(Ity_I32, mkexpr(op2addr))); 5549 5550 return "l"; 5551 } 5552 5553 static const HChar * 5554 s390_irgen_LY(UChar r1, IRTemp op2addr) 5555 { 5556 put_gpr_w1(r1, load(Ity_I32, mkexpr(op2addr))); 5557 5558 return "ly"; 5559 } 5560 5561 static const HChar * 5562 s390_irgen_LG(UChar r1, IRTemp op2addr) 5563 { 5564 put_gpr_dw0(r1, load(Ity_I64, mkexpr(op2addr))); 5565 5566 return "lg"; 5567 } 5568 5569 static const HChar * 5570 s390_irgen_LGF(UChar r1, IRTemp op2addr) 5571 { 5572 put_gpr_dw0(r1, unop(Iop_32Sto64, load(Ity_I32, mkexpr(op2addr)))); 5573 5574 return "lgf"; 5575 } 5576 5577 static const HChar * 5578 s390_irgen_LGFI(UChar r1, UInt i2) 5579 { 5580 put_gpr_dw0(r1, mkU64((ULong)(Long)(Int)i2)); 5581 5582 return "lgfi"; 5583 } 5584 5585 static const HChar * 5586 s390_irgen_LRL(UChar r1, UInt i2) 5587 { 5588 put_gpr_w1(r1, load(Ity_I32, mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int) 5589 i2 << 1)))); 5590 5591 return "lrl"; 5592 } 5593 5594 static const HChar * 5595 s390_irgen_LGRL(UChar r1, UInt i2) 5596 { 5597 put_gpr_dw0(r1, load(Ity_I64, mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int) 5598 i2 << 1)))); 5599 5600 return "lgrl"; 5601 } 5602 5603 static const HChar * 5604 s390_irgen_LGFRL(UChar r1, UInt i2) 5605 { 5606 put_gpr_dw0(r1, unop(Iop_32Sto64, load(Ity_I32, mkU64(guest_IA_curr_instr + 5607 ((ULong)(Long)(Int)i2 << 1))))); 5608 5609 return "lgfrl"; 5610 } 5611 5612 static const HChar * 5613 s390_irgen_LA(UChar r1, IRTemp op2addr) 5614 { 5615 put_gpr_dw0(r1, mkexpr(op2addr)); 5616 5617 return "la"; 5618 } 5619 5620 static const HChar * 5621 s390_irgen_LAY(UChar r1, IRTemp op2addr) 5622 { 5623 put_gpr_dw0(r1, mkexpr(op2addr)); 5624 5625 return "lay"; 5626 } 5627 5628 static const HChar * 5629 s390_irgen_LAE(UChar r1, IRTemp op2addr) 5630 { 5631 put_gpr_dw0(r1, mkexpr(op2addr)); 5632 5633 return "lae"; 5634 } 5635 5636 static const HChar * 5637 s390_irgen_LAEY(UChar r1, IRTemp op2addr) 5638 { 5639 put_gpr_dw0(r1, mkexpr(op2addr)); 5640 5641 return "laey"; 5642 } 5643 5644 static const HChar * 5645 s390_irgen_LARL(UChar r1, UInt i2) 5646 { 5647 put_gpr_dw0(r1, mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int)i2 << 1))); 5648 5649 return "larl"; 5650 } 5651 5652 /* The IR representation of LAA and friends is an approximation of what 5653 happens natively. Essentially a loop containing a compare-and-swap is 5654 constructed which will iterate until the CAS succeeds. As a consequence, 5655 instrumenters may see more memory accesses than happen natively. See also 5656 discussion here: https://bugs.kde.org/show_bug.cgi?id=306035 */ 5657 static void 5658 s390_irgen_load_and_add32(UChar r1, UChar r3, IRTemp op2addr, Bool is_signed) 5659 { 5660 IRCAS *cas; 5661 IRTemp old_mem = newTemp(Ity_I32); 5662 IRTemp op2 = newTemp(Ity_I32); 5663 IRTemp op3 = newTemp(Ity_I32); 5664 IRTemp result = newTemp(Ity_I32); 5665 5666 assign(op2, load(Ity_I32, mkexpr(op2addr))); 5667 assign(op3, get_gpr_w1(r3)); 5668 assign(result, binop(Iop_Add32, mkexpr(op2), mkexpr(op3))); 5669 5670 /* Place the addition of second operand and third operand at the 5671 second-operand location everytime */ 5672 cas = mkIRCAS(IRTemp_INVALID, old_mem, 5673 Iend_BE, mkexpr(op2addr), 5674 NULL, mkexpr(op2), /* expected value */ 5675 NULL, mkexpr(result) /* new value */); 5676 stmt(IRStmt_CAS(cas)); 5677 5678 /* Set CC according to 32-bit addition */ 5679 if (is_signed) { 5680 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_32, op2, op3); 5681 } else { 5682 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_32, op2, op3); 5683 } 5684 5685 /* If old_mem contains the expected value, then the CAS succeeded. 5686 Otherwise, it did not */ 5687 yield_if(binop(Iop_CmpNE32, mkexpr(old_mem), mkexpr(op2))); 5688 put_gpr_w1(r1, mkexpr(old_mem)); 5689 } 5690 5691 static void 5692 s390_irgen_load_and_add64(UChar r1, UChar r3, IRTemp op2addr, Bool is_signed) 5693 { 5694 IRCAS *cas; 5695 IRTemp old_mem = newTemp(Ity_I64); 5696 IRTemp op2 = newTemp(Ity_I64); 5697 IRTemp op3 = newTemp(Ity_I64); 5698 IRTemp result = newTemp(Ity_I64); 5699 5700 assign(op2, load(Ity_I64, mkexpr(op2addr))); 5701 assign(op3, get_gpr_dw0(r3)); 5702 assign(result, binop(Iop_Add64, mkexpr(op2), mkexpr(op3))); 5703 5704 /* Place the addition of second operand and third operand at the 5705 second-operand location everytime */ 5706 cas = mkIRCAS(IRTemp_INVALID, old_mem, 5707 Iend_BE, mkexpr(op2addr), 5708 NULL, mkexpr(op2), /* expected value */ 5709 NULL, mkexpr(result) /* new value */); 5710 stmt(IRStmt_CAS(cas)); 5711 5712 /* Set CC according to 64-bit addition */ 5713 if (is_signed) { 5714 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_64, op2, op3); 5715 } else { 5716 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_64, op2, op3); 5717 } 5718 5719 /* If old_mem contains the expected value, then the CAS succeeded. 5720 Otherwise, it did not */ 5721 yield_if(binop(Iop_CmpNE64, mkexpr(old_mem), mkexpr(op2))); 5722 put_gpr_dw0(r1, mkexpr(old_mem)); 5723 } 5724 5725 static void 5726 s390_irgen_load_and_bitwise32(UChar r1, UChar r3, IRTemp op2addr, IROp op) 5727 { 5728 IRCAS *cas; 5729 IRTemp old_mem = newTemp(Ity_I32); 5730 IRTemp op2 = newTemp(Ity_I32); 5731 IRTemp op3 = newTemp(Ity_I32); 5732 IRTemp result = newTemp(Ity_I32); 5733 5734 assign(op2, load(Ity_I32, mkexpr(op2addr))); 5735 assign(op3, get_gpr_w1(r3)); 5736 assign(result, binop(op, mkexpr(op2), mkexpr(op3))); 5737 5738 /* Place the addition of second operand and third operand at the 5739 second-operand location everytime */ 5740 cas = mkIRCAS(IRTemp_INVALID, old_mem, 5741 Iend_BE, mkexpr(op2addr), 5742 NULL, mkexpr(op2), /* expected value */ 5743 NULL, mkexpr(result) /* new value */); 5744 stmt(IRStmt_CAS(cas)); 5745 5746 /* Set CC according to bitwise operation */ 5747 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5748 5749 /* If old_mem contains the expected value, then the CAS succeeded. 5750 Otherwise, it did not */ 5751 yield_if(binop(Iop_CmpNE32, mkexpr(old_mem), mkexpr(op2))); 5752 put_gpr_w1(r1, mkexpr(old_mem)); 5753 } 5754 5755 static void 5756 s390_irgen_load_and_bitwise64(UChar r1, UChar r3, IRTemp op2addr, IROp op) 5757 { 5758 IRCAS *cas; 5759 IRTemp old_mem = newTemp(Ity_I64); 5760 IRTemp op2 = newTemp(Ity_I64); 5761 IRTemp op3 = newTemp(Ity_I64); 5762 IRTemp result = newTemp(Ity_I64); 5763 5764 assign(op2, load(Ity_I64, mkexpr(op2addr))); 5765 assign(op3, get_gpr_dw0(r3)); 5766 assign(result, binop(op, mkexpr(op2), mkexpr(op3))); 5767 5768 /* Place the addition of second operand and third operand at the 5769 second-operand location everytime */ 5770 cas = mkIRCAS(IRTemp_INVALID, old_mem, 5771 Iend_BE, mkexpr(op2addr), 5772 NULL, mkexpr(op2), /* expected value */ 5773 NULL, mkexpr(result) /* new value */); 5774 stmt(IRStmt_CAS(cas)); 5775 5776 /* Set CC according to bitwise operation */ 5777 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5778 5779 /* If old_mem contains the expected value, then the CAS succeeded. 5780 Otherwise, it did not */ 5781 yield_if(binop(Iop_CmpNE64, mkexpr(old_mem), mkexpr(op2))); 5782 put_gpr_dw0(r1, mkexpr(old_mem)); 5783 } 5784 5785 static const HChar * 5786 s390_irgen_LAA(UChar r1, UChar r3, IRTemp op2addr) 5787 { 5788 s390_irgen_load_and_add32(r1, r3, op2addr, True /* is_signed */); 5789 5790 return "laa"; 5791 } 5792 5793 static const HChar * 5794 s390_irgen_LAAG(UChar r1, UChar r3, IRTemp op2addr) 5795 { 5796 s390_irgen_load_and_add64(r1, r3, op2addr, True /* is_signed */); 5797 5798 return "laag"; 5799 } 5800 5801 static const HChar * 5802 s390_irgen_LAAL(UChar r1, UChar r3, IRTemp op2addr) 5803 { 5804 s390_irgen_load_and_add32(r1, r3, op2addr, False /* is_signed */); 5805 5806 return "laal"; 5807 } 5808 5809 static const HChar * 5810 s390_irgen_LAALG(UChar r1, UChar r3, IRTemp op2addr) 5811 { 5812 s390_irgen_load_and_add64(r1, r3, op2addr, False /* is_signed */); 5813 5814 return "laalg"; 5815 } 5816 5817 static const HChar * 5818 s390_irgen_LAN(UChar r1, UChar r3, IRTemp op2addr) 5819 { 5820 s390_irgen_load_and_bitwise32(r1, r3, op2addr, Iop_And32); 5821 5822 return "lan"; 5823 } 5824 5825 static const HChar * 5826 s390_irgen_LANG(UChar r1, UChar r3, IRTemp op2addr) 5827 { 5828 s390_irgen_load_and_bitwise64(r1, r3, op2addr, Iop_And64); 5829 5830 return "lang"; 5831 } 5832 5833 static const HChar * 5834 s390_irgen_LAX(UChar r1, UChar r3, IRTemp op2addr) 5835 { 5836 s390_irgen_load_and_bitwise32(r1, r3, op2addr, Iop_Xor32); 5837 5838 return "lax"; 5839 } 5840 5841 static const HChar * 5842 s390_irgen_LAXG(UChar r1, UChar r3, IRTemp op2addr) 5843 { 5844 s390_irgen_load_and_bitwise64(r1, r3, op2addr, Iop_Xor64); 5845 5846 return "laxg"; 5847 } 5848 5849 static const HChar * 5850 s390_irgen_LAO(UChar r1, UChar r3, IRTemp op2addr) 5851 { 5852 s390_irgen_load_and_bitwise32(r1, r3, op2addr, Iop_Or32); 5853 5854 return "lao"; 5855 } 5856 5857 static const HChar * 5858 s390_irgen_LAOG(UChar r1, UChar r3, IRTemp op2addr) 5859 { 5860 s390_irgen_load_and_bitwise64(r1, r3, op2addr, Iop_Or64); 5861 5862 return "laog"; 5863 } 5864 5865 static const HChar * 5866 s390_irgen_LTR(UChar r1, UChar r2) 5867 { 5868 IRTemp op2 = newTemp(Ity_I32); 5869 5870 assign(op2, get_gpr_w1(r2)); 5871 put_gpr_w1(r1, mkexpr(op2)); 5872 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, op2); 5873 5874 return "ltr"; 5875 } 5876 5877 static const HChar * 5878 s390_irgen_LTGR(UChar r1, UChar r2) 5879 { 5880 IRTemp op2 = newTemp(Ity_I64); 5881 5882 assign(op2, get_gpr_dw0(r2)); 5883 put_gpr_dw0(r1, mkexpr(op2)); 5884 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, op2); 5885 5886 return "ltgr"; 5887 } 5888 5889 static const HChar * 5890 s390_irgen_LTGFR(UChar r1, UChar r2) 5891 { 5892 IRTemp op2 = newTemp(Ity_I64); 5893 5894 assign(op2, unop(Iop_32Sto64, get_gpr_w1(r2))); 5895 put_gpr_dw0(r1, mkexpr(op2)); 5896 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, op2); 5897 5898 return "ltgfr"; 5899 } 5900 5901 static const HChar * 5902 s390_irgen_LT(UChar r1, IRTemp op2addr) 5903 { 5904 IRTemp op2 = newTemp(Ity_I32); 5905 5906 assign(op2, load(Ity_I32, mkexpr(op2addr))); 5907 put_gpr_w1(r1, mkexpr(op2)); 5908 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, op2); 5909 5910 return "lt"; 5911 } 5912 5913 static const HChar * 5914 s390_irgen_LTG(UChar r1, IRTemp op2addr) 5915 { 5916 IRTemp op2 = newTemp(Ity_I64); 5917 5918 assign(op2, load(Ity_I64, mkexpr(op2addr))); 5919 put_gpr_dw0(r1, mkexpr(op2)); 5920 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, op2); 5921 5922 return "ltg"; 5923 } 5924 5925 static const HChar * 5926 s390_irgen_LTGF(UChar r1, IRTemp op2addr) 5927 { 5928 IRTemp op2 = newTemp(Ity_I64); 5929 5930 assign(op2, unop(Iop_32Sto64, load(Ity_I32, mkexpr(op2addr)))); 5931 put_gpr_dw0(r1, mkexpr(op2)); 5932 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, op2); 5933 5934 return "ltgf"; 5935 } 5936 5937 static const HChar * 5938 s390_irgen_LBR(UChar r1, UChar r2) 5939 { 5940 put_gpr_w1(r1, unop(Iop_8Sto32, get_gpr_b7(r2))); 5941 5942 return "lbr"; 5943 } 5944 5945 static const HChar * 5946 s390_irgen_LGBR(UChar r1, UChar r2) 5947 { 5948 put_gpr_dw0(r1, unop(Iop_8Sto64, get_gpr_b7(r2))); 5949 5950 return "lgbr"; 5951 } 5952 5953 static const HChar * 5954 s390_irgen_LB(UChar r1, IRTemp op2addr) 5955 { 5956 put_gpr_w1(r1, unop(Iop_8Sto32, load(Ity_I8, mkexpr(op2addr)))); 5957 5958 return "lb"; 5959 } 5960 5961 static const HChar * 5962 s390_irgen_LGB(UChar r1, IRTemp op2addr) 5963 { 5964 put_gpr_dw0(r1, unop(Iop_8Sto64, load(Ity_I8, mkexpr(op2addr)))); 5965 5966 return "lgb"; 5967 } 5968 5969 static const HChar * 5970 s390_irgen_LBH(UChar r1, IRTemp op2addr) 5971 { 5972 put_gpr_w0(r1, unop(Iop_8Sto32, load(Ity_I8, mkexpr(op2addr)))); 5973 5974 return "lbh"; 5975 } 5976 5977 static const HChar * 5978 s390_irgen_LCR(UChar r1, UChar r2) 5979 { 5980 Int op1; 5981 IRTemp op2 = newTemp(Ity_I32); 5982 IRTemp result = newTemp(Ity_I32); 5983 5984 op1 = 0; 5985 assign(op2, get_gpr_w1(r2)); 5986 assign(result, binop(Iop_Sub32, mkU32((UInt)op1), mkexpr(op2))); 5987 put_gpr_w1(r1, mkexpr(result)); 5988 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, mktemp(Ity_I32, mkU32((UInt) 5989 op1)), op2); 5990 5991 return "lcr"; 5992 } 5993 5994 static const HChar * 5995 s390_irgen_LCGR(UChar r1, UChar r2) 5996 { 5997 Long op1; 5998 IRTemp op2 = newTemp(Ity_I64); 5999 IRTemp result = newTemp(Ity_I64); 6000 6001 op1 = 0ULL; 6002 assign(op2, get_gpr_dw0(r2)); 6003 assign(result, binop(Iop_Sub64, mkU64((ULong)op1), mkexpr(op2))); 6004 put_gpr_dw0(r1, mkexpr(result)); 6005 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_64, mktemp(Ity_I64, mkU64((ULong) 6006 op1)), op2); 6007 6008 return "lcgr"; 6009 } 6010 6011 static const HChar * 6012 s390_irgen_LCGFR(UChar r1, UChar r2) 6013 { 6014 Long op1; 6015 IRTemp op2 = newTemp(Ity_I64); 6016 IRTemp result = newTemp(Ity_I64); 6017 6018 op1 = 0ULL; 6019 assign(op2, unop(Iop_32Sto64, get_gpr_w1(r2))); 6020 assign(result, binop(Iop_Sub64, mkU64((ULong)op1), mkexpr(op2))); 6021 put_gpr_dw0(r1, mkexpr(result)); 6022 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_64, mktemp(Ity_I64, mkU64((ULong) 6023 op1)), op2); 6024 6025 return "lcgfr"; 6026 } 6027 6028 static const HChar * 6029 s390_irgen_LHR(UChar r1, UChar r2) 6030 { 6031 put_gpr_w1(r1, unop(Iop_16Sto32, get_gpr_hw3(r2))); 6032 6033 return "lhr"; 6034 } 6035 6036 static const HChar * 6037 s390_irgen_LGHR(UChar r1, UChar r2) 6038 { 6039 put_gpr_dw0(r1, unop(Iop_16Sto64, get_gpr_hw3(r2))); 6040 6041 return "lghr"; 6042 } 6043 6044 static const HChar * 6045 s390_irgen_LH(UChar r1, IRTemp op2addr) 6046 { 6047 put_gpr_w1(r1, unop(Iop_16Sto32, load(Ity_I16, mkexpr(op2addr)))); 6048 6049 return "lh"; 6050 } 6051 6052 static const HChar * 6053 s390_irgen_LHY(UChar r1, IRTemp op2addr) 6054 { 6055 put_gpr_w1(r1, unop(Iop_16Sto32, load(Ity_I16, mkexpr(op2addr)))); 6056 6057 return "lhy"; 6058 } 6059 6060 static const HChar * 6061 s390_irgen_LGH(UChar r1, IRTemp op2addr) 6062 { 6063 put_gpr_dw0(r1, unop(Iop_16Sto64, load(Ity_I16, mkexpr(op2addr)))); 6064 6065 return "lgh"; 6066 } 6067 6068 static const HChar * 6069 s390_irgen_LHI(UChar r1, UShort i2) 6070 { 6071 put_gpr_w1(r1, mkU32((UInt)(Int)(Short)i2)); 6072 6073 return "lhi"; 6074 } 6075 6076 static const HChar * 6077 s390_irgen_LGHI(UChar r1, UShort i2) 6078 { 6079 put_gpr_dw0(r1, mkU64((ULong)(Long)(Short)i2)); 6080 6081 return "lghi"; 6082 } 6083 6084 static const HChar * 6085 s390_irgen_LHRL(UChar r1, UInt i2) 6086 { 6087 put_gpr_w1(r1, unop(Iop_16Sto32, load(Ity_I16, mkU64(guest_IA_curr_instr + 6088 ((ULong)(Long)(Int)i2 << 1))))); 6089 6090 return "lhrl"; 6091 } 6092 6093 static const HChar * 6094 s390_irgen_LGHRL(UChar r1, UInt i2) 6095 { 6096 put_gpr_dw0(r1, unop(Iop_16Sto64, load(Ity_I16, mkU64(guest_IA_curr_instr + 6097 ((ULong)(Long)(Int)i2 << 1))))); 6098 6099 return "lghrl"; 6100 } 6101 6102 static const HChar * 6103 s390_irgen_LHH(UChar r1, IRTemp op2addr) 6104 { 6105 put_gpr_w0(r1, unop(Iop_16Sto32, load(Ity_I16, mkexpr(op2addr)))); 6106 6107 return "lhh"; 6108 } 6109 6110 static const HChar * 6111 s390_irgen_LFH(UChar r1, IRTemp op2addr) 6112 { 6113 put_gpr_w0(r1, load(Ity_I32, mkexpr(op2addr))); 6114 6115 return "lfh"; 6116 } 6117 6118 static const HChar * 6119 s390_irgen_LLGFR(UChar r1, UChar r2) 6120 { 6121 put_gpr_dw0(r1, unop(Iop_32Uto64, get_gpr_w1(r2))); 6122 6123 return "llgfr"; 6124 } 6125 6126 static const HChar * 6127 s390_irgen_LLGF(UChar r1, IRTemp op2addr) 6128 { 6129 put_gpr_dw0(r1, unop(Iop_32Uto64, load(Ity_I32, mkexpr(op2addr)))); 6130 6131 return "llgf"; 6132 } 6133 6134 static const HChar * 6135 s390_irgen_LLGFRL(UChar r1, UInt i2) 6136 { 6137 put_gpr_dw0(r1, unop(Iop_32Uto64, load(Ity_I32, mkU64(guest_IA_curr_instr + 6138 ((ULong)(Long)(Int)i2 << 1))))); 6139 6140 return "llgfrl"; 6141 } 6142 6143 static const HChar * 6144 s390_irgen_LLCR(UChar r1, UChar r2) 6145 { 6146 put_gpr_w1(r1, unop(Iop_8Uto32, get_gpr_b7(r2))); 6147 6148 return "llcr"; 6149 } 6150 6151 static const HChar * 6152 s390_irgen_LLGCR(UChar r1, UChar r2) 6153 { 6154 put_gpr_dw0(r1, unop(Iop_8Uto64, get_gpr_b7(r2))); 6155 6156 return "llgcr"; 6157 } 6158 6159 static const HChar * 6160 s390_irgen_LLC(UChar r1, IRTemp op2addr) 6161 { 6162 put_gpr_w1(r1, unop(Iop_8Uto32, load(Ity_I8, mkexpr(op2addr)))); 6163 6164 return "llc"; 6165 } 6166 6167 static const HChar * 6168 s390_irgen_LLGC(UChar r1, IRTemp op2addr) 6169 { 6170 put_gpr_dw0(r1, unop(Iop_8Uto64, load(Ity_I8, mkexpr(op2addr)))); 6171 6172 return "llgc"; 6173 } 6174 6175 static const HChar * 6176 s390_irgen_LLCH(UChar r1, IRTemp op2addr) 6177 { 6178 put_gpr_w0(r1, unop(Iop_8Uto32, load(Ity_I8, mkexpr(op2addr)))); 6179 6180 return "llch"; 6181 } 6182 6183 static const HChar * 6184 s390_irgen_LLHR(UChar r1, UChar r2) 6185 { 6186 put_gpr_w1(r1, unop(Iop_16Uto32, get_gpr_hw3(r2))); 6187 6188 return "llhr"; 6189 } 6190 6191 static const HChar * 6192 s390_irgen_LLGHR(UChar r1, UChar r2) 6193 { 6194 put_gpr_dw0(r1, unop(Iop_16Uto64, get_gpr_hw3(r2))); 6195 6196 return "llghr"; 6197 } 6198 6199 static const HChar * 6200 s390_irgen_LLH(UChar r1, IRTemp op2addr) 6201 { 6202 put_gpr_w1(r1, unop(Iop_16Uto32, load(Ity_I16, mkexpr(op2addr)))); 6203 6204 return "llh"; 6205 } 6206 6207 static const HChar * 6208 s390_irgen_LLGH(UChar r1, IRTemp op2addr) 6209 { 6210 put_gpr_dw0(r1, unop(Iop_16Uto64, load(Ity_I16, mkexpr(op2addr)))); 6211 6212 return "llgh"; 6213 } 6214 6215 static const HChar * 6216 s390_irgen_LLHRL(UChar r1, UInt i2) 6217 { 6218 put_gpr_w1(r1, unop(Iop_16Uto32, load(Ity_I16, mkU64(guest_IA_curr_instr + 6219 ((ULong)(Long)(Int)i2 << 1))))); 6220 6221 return "llhrl"; 6222 } 6223 6224 static const HChar * 6225 s390_irgen_LLGHRL(UChar r1, UInt i2) 6226 { 6227 put_gpr_dw0(r1, unop(Iop_16Uto64, load(Ity_I16, mkU64(guest_IA_curr_instr + 6228 ((ULong)(Long)(Int)i2 << 1))))); 6229 6230 return "llghrl"; 6231 } 6232 6233 static const HChar * 6234 s390_irgen_LLHH(UChar r1, IRTemp op2addr) 6235 { 6236 put_gpr_w0(r1, unop(Iop_16Uto32, load(Ity_I16, mkexpr(op2addr)))); 6237 6238 return "llhh"; 6239 } 6240 6241 static const HChar * 6242 s390_irgen_LLIHF(UChar r1, UInt i2) 6243 { 6244 put_gpr_dw0(r1, mkU64(((ULong)i2) << 32)); 6245 6246 return "llihf"; 6247 } 6248 6249 static const HChar * 6250 s390_irgen_LLIHH(UChar r1, UShort i2) 6251 { 6252 put_gpr_dw0(r1, mkU64(((ULong)i2) << 48)); 6253 6254 return "llihh"; 6255 } 6256 6257 static const HChar * 6258 s390_irgen_LLIHL(UChar r1, UShort i2) 6259 { 6260 put_gpr_dw0(r1, mkU64(((ULong)i2) << 32)); 6261 6262 return "llihl"; 6263 } 6264 6265 static const HChar * 6266 s390_irgen_LLILF(UChar r1, UInt i2) 6267 { 6268 put_gpr_dw0(r1, mkU64(i2)); 6269 6270 return "llilf"; 6271 } 6272 6273 static const HChar * 6274 s390_irgen_LLILH(UChar r1, UShort i2) 6275 { 6276 put_gpr_dw0(r1, mkU64(((ULong)i2) << 16)); 6277 6278 return "llilh"; 6279 } 6280 6281 static const HChar * 6282 s390_irgen_LLILL(UChar r1, UShort i2) 6283 { 6284 put_gpr_dw0(r1, mkU64(i2)); 6285 6286 return "llill"; 6287 } 6288 6289 static const HChar * 6290 s390_irgen_LLGTR(UChar r1, UChar r2) 6291 { 6292 put_gpr_dw0(r1, unop(Iop_32Uto64, binop(Iop_And32, get_gpr_w1(r2), 6293 mkU32(2147483647)))); 6294 6295 return "llgtr"; 6296 } 6297 6298 static const HChar * 6299 s390_irgen_LLGT(UChar r1, IRTemp op2addr) 6300 { 6301 put_gpr_dw0(r1, unop(Iop_32Uto64, binop(Iop_And32, load(Ity_I32, 6302 mkexpr(op2addr)), mkU32(2147483647)))); 6303 6304 return "llgt"; 6305 } 6306 6307 static const HChar * 6308 s390_irgen_LNR(UChar r1, UChar r2) 6309 { 6310 IRTemp op2 = newTemp(Ity_I32); 6311 IRTemp result = newTemp(Ity_I32); 6312 6313 assign(op2, get_gpr_w1(r2)); 6314 assign(result, mkite(binop(Iop_CmpLE32S, mkexpr(op2), mkU32(0)), mkexpr(op2), 6315 binop(Iop_Sub32, mkU32(0), mkexpr(op2)))); 6316 put_gpr_w1(r1, mkexpr(result)); 6317 s390_cc_thunk_putS(S390_CC_OP_BITWISE, result); 6318 6319 return "lnr"; 6320 } 6321 6322 static const HChar * 6323 s390_irgen_LNGR(UChar r1, UChar r2) 6324 { 6325 IRTemp op2 = newTemp(Ity_I64); 6326 IRTemp result = newTemp(Ity_I64); 6327 6328 assign(op2, get_gpr_dw0(r2)); 6329 assign(result, mkite(binop(Iop_CmpLE64S, mkexpr(op2), mkU64(0)), mkexpr(op2), 6330 binop(Iop_Sub64, mkU64(0), mkexpr(op2)))); 6331 put_gpr_dw0(r1, mkexpr(result)); 6332 s390_cc_thunk_putS(S390_CC_OP_BITWISE, result); 6333 6334 return "lngr"; 6335 } 6336 6337 static const HChar * 6338 s390_irgen_LNGFR(UChar r1, UChar r2 __attribute__((unused))) 6339 { 6340 IRTemp op2 = newTemp(Ity_I64); 6341 IRTemp result = newTemp(Ity_I64); 6342 6343 assign(op2, unop(Iop_32Sto64, get_gpr_w1(r1))); 6344 assign(result, mkite(binop(Iop_CmpLE64S, mkexpr(op2), mkU64(0)), mkexpr(op2), 6345 binop(Iop_Sub64, mkU64(0), mkexpr(op2)))); 6346 put_gpr_dw0(r1, mkexpr(result)); 6347 s390_cc_thunk_putS(S390_CC_OP_BITWISE, result); 6348 6349 return "lngfr"; 6350 } 6351 6352 static const HChar * 6353 s390_irgen_LOCR(UChar m3, UChar r1, UChar r2) 6354 { 6355 next_insn_if(binop(Iop_CmpEQ32, s390_call_calculate_cond(m3), mkU32(0))); 6356 put_gpr_w1(r1, get_gpr_w1(r2)); 6357 6358 return "locr"; 6359 } 6360 6361 static const HChar * 6362 s390_irgen_LOCGR(UChar m3, UChar r1, UChar r2) 6363 { 6364 next_insn_if(binop(Iop_CmpEQ32, s390_call_calculate_cond(m3), mkU32(0))); 6365 put_gpr_dw0(r1, get_gpr_dw0(r2)); 6366 6367 return "locgr"; 6368 } 6369 6370 static const HChar * 6371 s390_irgen_LOC(UChar r1, IRTemp op2addr) 6372 { 6373 /* condition is checked in format handler */ 6374 put_gpr_w1(r1, load(Ity_I32, mkexpr(op2addr))); 6375 6376 return "loc"; 6377 } 6378 6379 static const HChar * 6380 s390_irgen_LOCG(UChar r1, IRTemp op2addr) 6381 { 6382 /* condition is checked in format handler */ 6383 put_gpr_dw0(r1, load(Ity_I64, mkexpr(op2addr))); 6384 6385 return "locg"; 6386 } 6387 6388 static const HChar * 6389 s390_irgen_LPQ(UChar r1, IRTemp op2addr) 6390 { 6391 put_gpr_dw0(r1, load(Ity_I64, mkexpr(op2addr))); 6392 put_gpr_dw0(r1 + 1, load(Ity_I64, binop(Iop_Add64, mkexpr(op2addr), mkU64(8)) 6393 )); 6394 6395 return "lpq"; 6396 } 6397 6398 static const HChar * 6399 s390_irgen_LPR(UChar r1, UChar r2) 6400 { 6401 IRTemp op2 = newTemp(Ity_I32); 6402 IRTemp result = newTemp(Ity_I32); 6403 6404 assign(op2, get_gpr_w1(r2)); 6405 assign(result, mkite(binop(Iop_CmpLT32S, mkexpr(op2), mkU32(0)), 6406 binop(Iop_Sub32, mkU32(0), mkexpr(op2)), mkexpr(op2))); 6407 put_gpr_w1(r1, mkexpr(result)); 6408 s390_cc_thunk_putS(S390_CC_OP_LOAD_POSITIVE_32, op2); 6409 6410 return "lpr"; 6411 } 6412 6413 static const HChar * 6414 s390_irgen_LPGR(UChar r1, UChar r2) 6415 { 6416 IRTemp op2 = newTemp(Ity_I64); 6417 IRTemp result = newTemp(Ity_I64); 6418 6419 assign(op2, get_gpr_dw0(r2)); 6420 assign(result, mkite(binop(Iop_CmpLT64S, mkexpr(op2), mkU64(0)), 6421 binop(Iop_Sub64, mkU64(0), mkexpr(op2)), mkexpr(op2))); 6422 put_gpr_dw0(r1, mkexpr(result)); 6423 s390_cc_thunk_putS(S390_CC_OP_LOAD_POSITIVE_64, op2); 6424 6425 return "lpgr"; 6426 } 6427 6428 static const HChar * 6429 s390_irgen_LPGFR(UChar r1, UChar r2) 6430 { 6431 IRTemp op2 = newTemp(Ity_I64); 6432 IRTemp result = newTemp(Ity_I64); 6433 6434 assign(op2, unop(Iop_32Sto64, get_gpr_w1(r2))); 6435 assign(result, mkite(binop(Iop_CmpLT64S, mkexpr(op2), mkU64(0)), 6436 binop(Iop_Sub64, mkU64(0), mkexpr(op2)), mkexpr(op2))); 6437 put_gpr_dw0(r1, mkexpr(result)); 6438 s390_cc_thunk_putS(S390_CC_OP_LOAD_POSITIVE_64, op2); 6439 6440 return "lpgfr"; 6441 } 6442 6443 static const HChar * 6444 s390_irgen_LRVR(UChar r1, UChar r2) 6445 { 6446 IRTemp b0 = newTemp(Ity_I8); 6447 IRTemp b1 = newTemp(Ity_I8); 6448 IRTemp b2 = newTemp(Ity_I8); 6449 IRTemp b3 = newTemp(Ity_I8); 6450 6451 assign(b3, get_gpr_b7(r2)); 6452 assign(b2, get_gpr_b6(r2)); 6453 assign(b1, get_gpr_b5(r2)); 6454 assign(b0, get_gpr_b4(r2)); 6455 put_gpr_b4(r1, mkexpr(b3)); 6456 put_gpr_b5(r1, mkexpr(b2)); 6457 put_gpr_b6(r1, mkexpr(b1)); 6458 put_gpr_b7(r1, mkexpr(b0)); 6459 6460 return "lrvr"; 6461 } 6462 6463 static const HChar * 6464 s390_irgen_LRVGR(UChar r1, UChar r2) 6465 { 6466 IRTemp b0 = newTemp(Ity_I8); 6467 IRTemp b1 = newTemp(Ity_I8); 6468 IRTemp b2 = newTemp(Ity_I8); 6469 IRTemp b3 = newTemp(Ity_I8); 6470 IRTemp b4 = newTemp(Ity_I8); 6471 IRTemp b5 = newTemp(Ity_I8); 6472 IRTemp b6 = newTemp(Ity_I8); 6473 IRTemp b7 = newTemp(Ity_I8); 6474 6475 assign(b7, get_gpr_b7(r2)); 6476 assign(b6, get_gpr_b6(r2)); 6477 assign(b5, get_gpr_b5(r2)); 6478 assign(b4, get_gpr_b4(r2)); 6479 assign(b3, get_gpr_b3(r2)); 6480 assign(b2, get_gpr_b2(r2)); 6481 assign(b1, get_gpr_b1(r2)); 6482 assign(b0, get_gpr_b0(r2)); 6483 put_gpr_b0(r1, mkexpr(b7)); 6484 put_gpr_b1(r1, mkexpr(b6)); 6485 put_gpr_b2(r1, mkexpr(b5)); 6486 put_gpr_b3(r1, mkexpr(b4)); 6487 put_gpr_b4(r1, mkexpr(b3)); 6488 put_gpr_b5(r1, mkexpr(b2)); 6489 put_gpr_b6(r1, mkexpr(b1)); 6490 put_gpr_b7(r1, mkexpr(b0)); 6491 6492 return "lrvgr"; 6493 } 6494 6495 static const HChar * 6496 s390_irgen_LRVH(UChar r1, IRTemp op2addr) 6497 { 6498 IRTemp op2 = newTemp(Ity_I16); 6499 6500 assign(op2, load(Ity_I16, mkexpr(op2addr))); 6501 put_gpr_b6(r1, unop(Iop_16to8, mkexpr(op2))); 6502 put_gpr_b7(r1, unop(Iop_16HIto8, mkexpr(op2))); 6503 6504 return "lrvh"; 6505 } 6506 6507 static const HChar * 6508 s390_irgen_LRV(UChar r1, IRTemp op2addr) 6509 { 6510 IRTemp op2 = newTemp(Ity_I32); 6511 6512 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6513 put_gpr_b4(r1, unop(Iop_32to8, binop(Iop_And32, mkexpr(op2), mkU32(255)))); 6514 put_gpr_b5(r1, unop(Iop_32to8, binop(Iop_And32, binop(Iop_Shr32, mkexpr(op2), 6515 mkU8(8)), mkU32(255)))); 6516 put_gpr_b6(r1, unop(Iop_32to8, binop(Iop_And32, binop(Iop_Shr32, mkexpr(op2), 6517 mkU8(16)), mkU32(255)))); 6518 put_gpr_b7(r1, unop(Iop_32to8, binop(Iop_And32, binop(Iop_Shr32, mkexpr(op2), 6519 mkU8(24)), mkU32(255)))); 6520 6521 return "lrv"; 6522 } 6523 6524 static const HChar * 6525 s390_irgen_LRVG(UChar r1, IRTemp op2addr) 6526 { 6527 IRTemp op2 = newTemp(Ity_I64); 6528 6529 assign(op2, load(Ity_I64, mkexpr(op2addr))); 6530 put_gpr_b0(r1, unop(Iop_64to8, binop(Iop_And64, mkexpr(op2), mkU64(255)))); 6531 put_gpr_b1(r1, unop(Iop_64to8, binop(Iop_And64, binop(Iop_Shr64, mkexpr(op2), 6532 mkU8(8)), mkU64(255)))); 6533 put_gpr_b2(r1, unop(Iop_64to8, binop(Iop_And64, binop(Iop_Shr64, mkexpr(op2), 6534 mkU8(16)), mkU64(255)))); 6535 put_gpr_b3(r1, unop(Iop_64to8, binop(Iop_And64, binop(Iop_Shr64, mkexpr(op2), 6536 mkU8(24)), mkU64(255)))); 6537 put_gpr_b4(r1, unop(Iop_64to8, binop(Iop_And64, binop(Iop_Shr64, mkexpr(op2), 6538 mkU8(32)), mkU64(255)))); 6539 put_gpr_b5(r1, unop(Iop_64to8, binop(Iop_And64, binop(Iop_Shr64, mkexpr(op2), 6540 mkU8(40)), mkU64(255)))); 6541 put_gpr_b6(r1, unop(Iop_64to8, binop(Iop_And64, binop(Iop_Shr64, mkexpr(op2), 6542 mkU8(48)), mkU64(255)))); 6543 put_gpr_b7(r1, unop(Iop_64to8, binop(Iop_And64, binop(Iop_Shr64, mkexpr(op2), 6544 mkU8(56)), mkU64(255)))); 6545 6546 return "lrvg"; 6547 } 6548 6549 static const HChar * 6550 s390_irgen_MVHHI(UShort i2, IRTemp op1addr) 6551 { 6552 store(mkexpr(op1addr), mkU16(i2)); 6553 6554 return "mvhhi"; 6555 } 6556 6557 static const HChar * 6558 s390_irgen_MVHI(UShort i2, IRTemp op1addr) 6559 { 6560 store(mkexpr(op1addr), mkU32((UInt)(Int)(Short)i2)); 6561 6562 return "mvhi"; 6563 } 6564 6565 static const HChar * 6566 s390_irgen_MVGHI(UShort i2, IRTemp op1addr) 6567 { 6568 store(mkexpr(op1addr), mkU64((ULong)(Long)(Short)i2)); 6569 6570 return "mvghi"; 6571 } 6572 6573 static const HChar * 6574 s390_irgen_MVI(UChar i2, IRTemp op1addr) 6575 { 6576 store(mkexpr(op1addr), mkU8(i2)); 6577 6578 return "mvi"; 6579 } 6580 6581 static const HChar * 6582 s390_irgen_MVIY(UChar i2, IRTemp op1addr) 6583 { 6584 store(mkexpr(op1addr), mkU8(i2)); 6585 6586 return "mviy"; 6587 } 6588 6589 static const HChar * 6590 s390_irgen_MR(UChar r1, UChar r2) 6591 { 6592 IRTemp op1 = newTemp(Ity_I32); 6593 IRTemp op2 = newTemp(Ity_I32); 6594 IRTemp result = newTemp(Ity_I64); 6595 6596 assign(op1, get_gpr_w1(r1 + 1)); 6597 assign(op2, get_gpr_w1(r2)); 6598 assign(result, binop(Iop_MullS32, mkexpr(op1), mkexpr(op2))); 6599 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 6600 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 6601 6602 return "mr"; 6603 } 6604 6605 static const HChar * 6606 s390_irgen_M(UChar r1, IRTemp op2addr) 6607 { 6608 IRTemp op1 = newTemp(Ity_I32); 6609 IRTemp op2 = newTemp(Ity_I32); 6610 IRTemp result = newTemp(Ity_I64); 6611 6612 assign(op1, get_gpr_w1(r1 + 1)); 6613 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6614 assign(result, binop(Iop_MullS32, mkexpr(op1), mkexpr(op2))); 6615 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 6616 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 6617 6618 return "m"; 6619 } 6620 6621 static const HChar * 6622 s390_irgen_MFY(UChar r1, IRTemp op2addr) 6623 { 6624 IRTemp op1 = newTemp(Ity_I32); 6625 IRTemp op2 = newTemp(Ity_I32); 6626 IRTemp result = newTemp(Ity_I64); 6627 6628 assign(op1, get_gpr_w1(r1 + 1)); 6629 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6630 assign(result, binop(Iop_MullS32, mkexpr(op1), mkexpr(op2))); 6631 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 6632 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 6633 6634 return "mfy"; 6635 } 6636 6637 static const HChar * 6638 s390_irgen_MH(UChar r1, IRTemp op2addr) 6639 { 6640 IRTemp op1 = newTemp(Ity_I32); 6641 IRTemp op2 = newTemp(Ity_I16); 6642 IRTemp result = newTemp(Ity_I64); 6643 6644 assign(op1, get_gpr_w1(r1)); 6645 assign(op2, load(Ity_I16, mkexpr(op2addr))); 6646 assign(result, binop(Iop_MullS32, mkexpr(op1), unop(Iop_16Sto32, mkexpr(op2)) 6647 )); 6648 put_gpr_w1(r1, unop(Iop_64to32, mkexpr(result))); 6649 6650 return "mh"; 6651 } 6652 6653 static const HChar * 6654 s390_irgen_MHY(UChar r1, IRTemp op2addr) 6655 { 6656 IRTemp op1 = newTemp(Ity_I32); 6657 IRTemp op2 = newTemp(Ity_I16); 6658 IRTemp result = newTemp(Ity_I64); 6659 6660 assign(op1, get_gpr_w1(r1)); 6661 assign(op2, load(Ity_I16, mkexpr(op2addr))); 6662 assign(result, binop(Iop_MullS32, mkexpr(op1), unop(Iop_16Sto32, mkexpr(op2)) 6663 )); 6664 put_gpr_w1(r1, unop(Iop_64to32, mkexpr(result))); 6665 6666 return "mhy"; 6667 } 6668 6669 static const HChar * 6670 s390_irgen_MHI(UChar r1, UShort i2) 6671 { 6672 IRTemp op1 = newTemp(Ity_I32); 6673 Short op2; 6674 IRTemp result = newTemp(Ity_I64); 6675 6676 assign(op1, get_gpr_w1(r1)); 6677 op2 = (Short)i2; 6678 assign(result, binop(Iop_MullS32, mkexpr(op1), unop(Iop_16Sto32, 6679 mkU16((UShort)op2)))); 6680 put_gpr_w1(r1, unop(Iop_64to32, mkexpr(result))); 6681 6682 return "mhi"; 6683 } 6684 6685 static const HChar * 6686 s390_irgen_MGHI(UChar r1, UShort i2) 6687 { 6688 IRTemp op1 = newTemp(Ity_I64); 6689 Short op2; 6690 IRTemp result = newTemp(Ity_I128); 6691 6692 assign(op1, get_gpr_dw0(r1)); 6693 op2 = (Short)i2; 6694 assign(result, binop(Iop_MullS64, mkexpr(op1), unop(Iop_16Sto64, 6695 mkU16((UShort)op2)))); 6696 put_gpr_dw0(r1, unop(Iop_128to64, mkexpr(result))); 6697 6698 return "mghi"; 6699 } 6700 6701 static const HChar * 6702 s390_irgen_MLR(UChar r1, UChar r2) 6703 { 6704 IRTemp op1 = newTemp(Ity_I32); 6705 IRTemp op2 = newTemp(Ity_I32); 6706 IRTemp result = newTemp(Ity_I64); 6707 6708 assign(op1, get_gpr_w1(r1 + 1)); 6709 assign(op2, get_gpr_w1(r2)); 6710 assign(result, binop(Iop_MullU32, mkexpr(op1), mkexpr(op2))); 6711 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 6712 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 6713 6714 return "mlr"; 6715 } 6716 6717 static const HChar * 6718 s390_irgen_MLGR(UChar r1, UChar r2) 6719 { 6720 IRTemp op1 = newTemp(Ity_I64); 6721 IRTemp op2 = newTemp(Ity_I64); 6722 IRTemp result = newTemp(Ity_I128); 6723 6724 assign(op1, get_gpr_dw0(r1 + 1)); 6725 assign(op2, get_gpr_dw0(r2)); 6726 assign(result, binop(Iop_MullU64, mkexpr(op1), mkexpr(op2))); 6727 put_gpr_dw0(r1, unop(Iop_128HIto64, mkexpr(result))); 6728 put_gpr_dw0(r1 + 1, unop(Iop_128to64, mkexpr(result))); 6729 6730 return "mlgr"; 6731 } 6732 6733 static const HChar * 6734 s390_irgen_ML(UChar r1, IRTemp op2addr) 6735 { 6736 IRTemp op1 = newTemp(Ity_I32); 6737 IRTemp op2 = newTemp(Ity_I32); 6738 IRTemp result = newTemp(Ity_I64); 6739 6740 assign(op1, get_gpr_w1(r1 + 1)); 6741 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6742 assign(result, binop(Iop_MullU32, mkexpr(op1), mkexpr(op2))); 6743 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 6744 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 6745 6746 return "ml"; 6747 } 6748 6749 static const HChar * 6750 s390_irgen_MLG(UChar r1, IRTemp op2addr) 6751 { 6752 IRTemp op1 = newTemp(Ity_I64); 6753 IRTemp op2 = newTemp(Ity_I64); 6754 IRTemp result = newTemp(Ity_I128); 6755 6756 assign(op1, get_gpr_dw0(r1 + 1)); 6757 assign(op2, load(Ity_I64, mkexpr(op2addr))); 6758 assign(result, binop(Iop_MullU64, mkexpr(op1), mkexpr(op2))); 6759 put_gpr_dw0(r1, unop(Iop_128HIto64, mkexpr(result))); 6760 put_gpr_dw0(r1 + 1, unop(Iop_128to64, mkexpr(result))); 6761 6762 return "mlg"; 6763 } 6764 6765 static const HChar * 6766 s390_irgen_MSR(UChar r1, UChar r2) 6767 { 6768 IRTemp op1 = newTemp(Ity_I32); 6769 IRTemp op2 = newTemp(Ity_I32); 6770 IRTemp result = newTemp(Ity_I64); 6771 6772 assign(op1, get_gpr_w1(r1)); 6773 assign(op2, get_gpr_w1(r2)); 6774 assign(result, binop(Iop_MullS32, mkexpr(op1), mkexpr(op2))); 6775 put_gpr_w1(r1, unop(Iop_64to32, mkexpr(result))); 6776 6777 return "msr"; 6778 } 6779 6780 static const HChar * 6781 s390_irgen_MSGR(UChar r1, UChar r2) 6782 { 6783 IRTemp op1 = newTemp(Ity_I64); 6784 IRTemp op2 = newTemp(Ity_I64); 6785 IRTemp result = newTemp(Ity_I128); 6786 6787 assign(op1, get_gpr_dw0(r1)); 6788 assign(op2, get_gpr_dw0(r2)); 6789 assign(result, binop(Iop_MullS64, mkexpr(op1), mkexpr(op2))); 6790 put_gpr_dw0(r1, unop(Iop_128to64, mkexpr(result))); 6791 6792 return "msgr"; 6793 } 6794 6795 static const HChar * 6796 s390_irgen_MSGFR(UChar r1, UChar r2) 6797 { 6798 IRTemp op1 = newTemp(Ity_I64); 6799 IRTemp op2 = newTemp(Ity_I32); 6800 IRTemp result = newTemp(Ity_I128); 6801 6802 assign(op1, get_gpr_dw0(r1)); 6803 assign(op2, get_gpr_w1(r2)); 6804 assign(result, binop(Iop_MullS64, mkexpr(op1), unop(Iop_32Sto64, mkexpr(op2)) 6805 )); 6806 put_gpr_dw0(r1, unop(Iop_128to64, mkexpr(result))); 6807 6808 return "msgfr"; 6809 } 6810 6811 static const HChar * 6812 s390_irgen_MS(UChar r1, IRTemp op2addr) 6813 { 6814 IRTemp op1 = newTemp(Ity_I32); 6815 IRTemp op2 = newTemp(Ity_I32); 6816 IRTemp result = newTemp(Ity_I64); 6817 6818 assign(op1, get_gpr_w1(r1)); 6819 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6820 assign(result, binop(Iop_MullS32, mkexpr(op1), mkexpr(op2))); 6821 put_gpr_w1(r1, unop(Iop_64to32, mkexpr(result))); 6822 6823 return "ms"; 6824 } 6825 6826 static const HChar * 6827 s390_irgen_MSY(UChar r1, IRTemp op2addr) 6828 { 6829 IRTemp op1 = newTemp(Ity_I32); 6830 IRTemp op2 = newTemp(Ity_I32); 6831 IRTemp result = newTemp(Ity_I64); 6832 6833 assign(op1, get_gpr_w1(r1)); 6834 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6835 assign(result, binop(Iop_MullS32, mkexpr(op1), mkexpr(op2))); 6836 put_gpr_w1(r1, unop(Iop_64to32, mkexpr(result))); 6837 6838 return "msy"; 6839 } 6840 6841 static const HChar * 6842 s390_irgen_MSG(UChar r1, IRTemp op2addr) 6843 { 6844 IRTemp op1 = newTemp(Ity_I64); 6845 IRTemp op2 = newTemp(Ity_I64); 6846 IRTemp result = newTemp(Ity_I128); 6847 6848 assign(op1, get_gpr_dw0(r1)); 6849 assign(op2, load(Ity_I64, mkexpr(op2addr))); 6850 assign(result, binop(Iop_MullS64, mkexpr(op1), mkexpr(op2))); 6851 put_gpr_dw0(r1, unop(Iop_128to64, mkexpr(result))); 6852 6853 return "msg"; 6854 } 6855 6856 static const HChar * 6857 s390_irgen_MSGF(UChar r1, IRTemp op2addr) 6858 { 6859 IRTemp op1 = newTemp(Ity_I64); 6860 IRTemp op2 = newTemp(Ity_I32); 6861 IRTemp result = newTemp(Ity_I128); 6862 6863 assign(op1, get_gpr_dw0(r1)); 6864 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6865 assign(result, binop(Iop_MullS64, mkexpr(op1), unop(Iop_32Sto64, mkexpr(op2)) 6866 )); 6867 put_gpr_dw0(r1, unop(Iop_128to64, mkexpr(result))); 6868 6869 return "msgf"; 6870 } 6871 6872 static const HChar * 6873 s390_irgen_MSFI(UChar r1, UInt i2) 6874 { 6875 IRTemp op1 = newTemp(Ity_I32); 6876 Int op2; 6877 IRTemp result = newTemp(Ity_I64); 6878 6879 assign(op1, get_gpr_w1(r1)); 6880 op2 = (Int)i2; 6881 assign(result, binop(Iop_MullS32, mkexpr(op1), mkU32((UInt)op2))); 6882 put_gpr_w1(r1, unop(Iop_64to32, mkexpr(result))); 6883 6884 return "msfi"; 6885 } 6886 6887 static const HChar * 6888 s390_irgen_MSGFI(UChar r1, UInt i2) 6889 { 6890 IRTemp op1 = newTemp(Ity_I64); 6891 Int op2; 6892 IRTemp result = newTemp(Ity_I128); 6893 6894 assign(op1, get_gpr_dw0(r1)); 6895 op2 = (Int)i2; 6896 assign(result, binop(Iop_MullS64, mkexpr(op1), unop(Iop_32Sto64, mkU32((UInt) 6897 op2)))); 6898 put_gpr_dw0(r1, unop(Iop_128to64, mkexpr(result))); 6899 6900 return "msgfi"; 6901 } 6902 6903 static const HChar * 6904 s390_irgen_OR(UChar r1, UChar r2) 6905 { 6906 IRTemp op1 = newTemp(Ity_I32); 6907 IRTemp op2 = newTemp(Ity_I32); 6908 IRTemp result = newTemp(Ity_I32); 6909 6910 assign(op1, get_gpr_w1(r1)); 6911 assign(op2, get_gpr_w1(r2)); 6912 assign(result, binop(Iop_Or32, mkexpr(op1), mkexpr(op2))); 6913 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 6914 put_gpr_w1(r1, mkexpr(result)); 6915 6916 return "or"; 6917 } 6918 6919 static const HChar * 6920 s390_irgen_OGR(UChar r1, UChar r2) 6921 { 6922 IRTemp op1 = newTemp(Ity_I64); 6923 IRTemp op2 = newTemp(Ity_I64); 6924 IRTemp result = newTemp(Ity_I64); 6925 6926 assign(op1, get_gpr_dw0(r1)); 6927 assign(op2, get_gpr_dw0(r2)); 6928 assign(result, binop(Iop_Or64, mkexpr(op1), mkexpr(op2))); 6929 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 6930 put_gpr_dw0(r1, mkexpr(result)); 6931 6932 return "ogr"; 6933 } 6934 6935 static const HChar * 6936 s390_irgen_ORK(UChar r3, UChar r1, UChar r2) 6937 { 6938 IRTemp op2 = newTemp(Ity_I32); 6939 IRTemp op3 = newTemp(Ity_I32); 6940 IRTemp result = newTemp(Ity_I32); 6941 6942 assign(op2, get_gpr_w1(r2)); 6943 assign(op3, get_gpr_w1(r3)); 6944 assign(result, binop(Iop_Or32, mkexpr(op2), mkexpr(op3))); 6945 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 6946 put_gpr_w1(r1, mkexpr(result)); 6947 6948 return "ork"; 6949 } 6950 6951 static const HChar * 6952 s390_irgen_OGRK(UChar r3, UChar r1, UChar r2) 6953 { 6954 IRTemp op2 = newTemp(Ity_I64); 6955 IRTemp op3 = newTemp(Ity_I64); 6956 IRTemp result = newTemp(Ity_I64); 6957 6958 assign(op2, get_gpr_dw0(r2)); 6959 assign(op3, get_gpr_dw0(r3)); 6960 assign(result, binop(Iop_Or64, mkexpr(op2), mkexpr(op3))); 6961 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 6962 put_gpr_dw0(r1, mkexpr(result)); 6963 6964 return "ogrk"; 6965 } 6966 6967 static const HChar * 6968 s390_irgen_O(UChar r1, IRTemp op2addr) 6969 { 6970 IRTemp op1 = newTemp(Ity_I32); 6971 IRTemp op2 = newTemp(Ity_I32); 6972 IRTemp result = newTemp(Ity_I32); 6973 6974 assign(op1, get_gpr_w1(r1)); 6975 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6976 assign(result, binop(Iop_Or32, mkexpr(op1), mkexpr(op2))); 6977 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 6978 put_gpr_w1(r1, mkexpr(result)); 6979 6980 return "o"; 6981 } 6982 6983 static const HChar * 6984 s390_irgen_OY(UChar r1, IRTemp op2addr) 6985 { 6986 IRTemp op1 = newTemp(Ity_I32); 6987 IRTemp op2 = newTemp(Ity_I32); 6988 IRTemp result = newTemp(Ity_I32); 6989 6990 assign(op1, get_gpr_w1(r1)); 6991 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6992 assign(result, binop(Iop_Or32, mkexpr(op1), mkexpr(op2))); 6993 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 6994 put_gpr_w1(r1, mkexpr(result)); 6995 6996 return "oy"; 6997 } 6998 6999 static const HChar * 7000 s390_irgen_OG(UChar r1, IRTemp op2addr) 7001 { 7002 IRTemp op1 = newTemp(Ity_I64); 7003 IRTemp op2 = newTemp(Ity_I64); 7004 IRTemp result = newTemp(Ity_I64); 7005 7006 assign(op1, get_gpr_dw0(r1)); 7007 assign(op2, load(Ity_I64, mkexpr(op2addr))); 7008 assign(result, binop(Iop_Or64, mkexpr(op1), mkexpr(op2))); 7009 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7010 put_gpr_dw0(r1, mkexpr(result)); 7011 7012 return "og"; 7013 } 7014 7015 static const HChar * 7016 s390_irgen_OI(UChar i2, IRTemp op1addr) 7017 { 7018 IRTemp op1 = newTemp(Ity_I8); 7019 UChar op2; 7020 IRTemp result = newTemp(Ity_I8); 7021 7022 assign(op1, load(Ity_I8, mkexpr(op1addr))); 7023 op2 = i2; 7024 assign(result, binop(Iop_Or8, mkexpr(op1), mkU8(op2))); 7025 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7026 store(mkexpr(op1addr), mkexpr(result)); 7027 7028 return "oi"; 7029 } 7030 7031 static const HChar * 7032 s390_irgen_OIY(UChar i2, IRTemp op1addr) 7033 { 7034 IRTemp op1 = newTemp(Ity_I8); 7035 UChar op2; 7036 IRTemp result = newTemp(Ity_I8); 7037 7038 assign(op1, load(Ity_I8, mkexpr(op1addr))); 7039 op2 = i2; 7040 assign(result, binop(Iop_Or8, mkexpr(op1), mkU8(op2))); 7041 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7042 store(mkexpr(op1addr), mkexpr(result)); 7043 7044 return "oiy"; 7045 } 7046 7047 static const HChar * 7048 s390_irgen_OIHF(UChar r1, UInt i2) 7049 { 7050 IRTemp op1 = newTemp(Ity_I32); 7051 UInt op2; 7052 IRTemp result = newTemp(Ity_I32); 7053 7054 assign(op1, get_gpr_w0(r1)); 7055 op2 = i2; 7056 assign(result, binop(Iop_Or32, mkexpr(op1), mkU32(op2))); 7057 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7058 put_gpr_w0(r1, mkexpr(result)); 7059 7060 return "oihf"; 7061 } 7062 7063 static const HChar * 7064 s390_irgen_OIHH(UChar r1, UShort i2) 7065 { 7066 IRTemp op1 = newTemp(Ity_I16); 7067 UShort op2; 7068 IRTemp result = newTemp(Ity_I16); 7069 7070 assign(op1, get_gpr_hw0(r1)); 7071 op2 = i2; 7072 assign(result, binop(Iop_Or16, mkexpr(op1), mkU16(op2))); 7073 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7074 put_gpr_hw0(r1, mkexpr(result)); 7075 7076 return "oihh"; 7077 } 7078 7079 static const HChar * 7080 s390_irgen_OIHL(UChar r1, UShort i2) 7081 { 7082 IRTemp op1 = newTemp(Ity_I16); 7083 UShort op2; 7084 IRTemp result = newTemp(Ity_I16); 7085 7086 assign(op1, get_gpr_hw1(r1)); 7087 op2 = i2; 7088 assign(result, binop(Iop_Or16, mkexpr(op1), mkU16(op2))); 7089 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7090 put_gpr_hw1(r1, mkexpr(result)); 7091 7092 return "oihl"; 7093 } 7094 7095 static const HChar * 7096 s390_irgen_OILF(UChar r1, UInt i2) 7097 { 7098 IRTemp op1 = newTemp(Ity_I32); 7099 UInt op2; 7100 IRTemp result = newTemp(Ity_I32); 7101 7102 assign(op1, get_gpr_w1(r1)); 7103 op2 = i2; 7104 assign(result, binop(Iop_Or32, mkexpr(op1), mkU32(op2))); 7105 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7106 put_gpr_w1(r1, mkexpr(result)); 7107 7108 return "oilf"; 7109 } 7110 7111 static const HChar * 7112 s390_irgen_OILH(UChar r1, UShort i2) 7113 { 7114 IRTemp op1 = newTemp(Ity_I16); 7115 UShort op2; 7116 IRTemp result = newTemp(Ity_I16); 7117 7118 assign(op1, get_gpr_hw2(r1)); 7119 op2 = i2; 7120 assign(result, binop(Iop_Or16, mkexpr(op1), mkU16(op2))); 7121 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7122 put_gpr_hw2(r1, mkexpr(result)); 7123 7124 return "oilh"; 7125 } 7126 7127 static const HChar * 7128 s390_irgen_OILL(UChar r1, UShort i2) 7129 { 7130 IRTemp op1 = newTemp(Ity_I16); 7131 UShort op2; 7132 IRTemp result = newTemp(Ity_I16); 7133 7134 assign(op1, get_gpr_hw3(r1)); 7135 op2 = i2; 7136 assign(result, binop(Iop_Or16, mkexpr(op1), mkU16(op2))); 7137 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7138 put_gpr_hw3(r1, mkexpr(result)); 7139 7140 return "oill"; 7141 } 7142 7143 static const HChar * 7144 s390_irgen_PFD(void) 7145 { 7146 7147 return "pfd"; 7148 } 7149 7150 static const HChar * 7151 s390_irgen_PFDRL(void) 7152 { 7153 7154 return "pfdrl"; 7155 } 7156 7157 static IRExpr * 7158 get_rounding_mode_from_gr0(void) 7159 { 7160 IRTemp rm_bits = newTemp(Ity_I32); 7161 IRExpr *s390rm; 7162 IRExpr *irrm; 7163 7164 /* The dfp/bfp rounding mode is stored in bits [60:63] of GR 0 7165 when PFPO insn is called. So, extract the bits at [60:63] */ 7166 assign(rm_bits, binop(Iop_And32, get_gpr_w1(0), mkU32(0xf))); 7167 s390rm = mkexpr(rm_bits); 7168 irrm = mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0x1)), 7169 mkexpr(encode_bfp_rounding_mode( S390_BFP_ROUND_PER_FPC)), 7170 mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0x8)), 7171 mkexpr(encode_dfp_rounding_mode(S390_DFP_ROUND_NEAREST_EVEN_8)), 7172 mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0x9)), 7173 mkexpr(encode_dfp_rounding_mode(S390_DFP_ROUND_ZERO_9)), 7174 mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0xa)), 7175 mkexpr(encode_dfp_rounding_mode(S390_DFP_ROUND_POSINF_10)), 7176 mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0xb)), 7177 mkexpr(encode_dfp_rounding_mode(S390_DFP_ROUND_NEGINF_11)), 7178 mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0xc)), 7179 mkexpr(encode_dfp_rounding_mode( 7180 S390_DFP_ROUND_NEAREST_TIE_AWAY_0_12)), 7181 mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0xd)), 7182 mkexpr(encode_dfp_rounding_mode( 7183 S390_DFP_ROUND_NEAREST_TIE_TOWARD_0)), 7184 mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0xe)), 7185 mkexpr(encode_dfp_rounding_mode( 7186 S390_DFP_ROUND_AWAY_0)), 7187 mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0xf)), 7188 mkexpr(encode_dfp_rounding_mode( 7189 S390_DFP_ROUND_PREPARE_SHORT_15)), 7190 /* if rounding mode is 0 or invalid (2-7) 7191 set S390_DFP_ROUND_PER_FPC_0 */ 7192 mkexpr(encode_dfp_rounding_mode( 7193 S390_DFP_ROUND_PER_FPC_0))))))))))); 7194 7195 return irrm; 7196 } 7197 7198 static IRExpr * 7199 s390_call_pfpo_helper(IRExpr *gr0) 7200 { 7201 IRExpr **args, *call; 7202 7203 args = mkIRExprVec_1(gr0); 7204 call = mkIRExprCCall(Ity_I32, 0 /*regparm*/, 7205 "s390_do_pfpo", &s390_do_pfpo, args); 7206 /* Nothing is excluded from definedness checking. */ 7207 call->Iex.CCall.cee->mcx_mask = 0; 7208 7209 return call; 7210 } 7211 7212 static const HChar * 7213 s390_irgen_PFPO(void) 7214 { 7215 IRTemp gr0 = newTemp(Ity_I32); /* word 1 [32:63] of GR 0 */ 7216 IRTemp test_bit = newTemp(Ity_I32); /* bit 32 of GR 0 - test validity */ 7217 IRTemp fn = newTemp(Ity_I32); /* [33:55] of GR 0 - function code */ 7218 IRTemp ef = newTemp(Ity_I32); /* Emulation Failure */ 7219 IRTemp src1 = newTemp(Ity_F32); 7220 IRTemp dst1 = newTemp(Ity_D32); 7221 IRTemp src2 = newTemp(Ity_F32); 7222 IRTemp dst2 = newTemp(Ity_D64); 7223 IRTemp src3 = newTemp(Ity_F32); 7224 IRTemp dst3 = newTemp(Ity_D128); 7225 IRTemp src4 = newTemp(Ity_F64); 7226 IRTemp dst4 = newTemp(Ity_D32); 7227 IRTemp src5 = newTemp(Ity_F64); 7228 IRTemp dst5 = newTemp(Ity_D64); 7229 IRTemp src6 = newTemp(Ity_F64); 7230 IRTemp dst6 = newTemp(Ity_D128); 7231 IRTemp src7 = newTemp(Ity_F128); 7232 IRTemp dst7 = newTemp(Ity_D32); 7233 IRTemp src8 = newTemp(Ity_F128); 7234 IRTemp dst8 = newTemp(Ity_D64); 7235 IRTemp src9 = newTemp(Ity_F128); 7236 IRTemp dst9 = newTemp(Ity_D128); 7237 IRTemp src10 = newTemp(Ity_D32); 7238 IRTemp dst10 = newTemp(Ity_F32); 7239 IRTemp src11 = newTemp(Ity_D32); 7240 IRTemp dst11 = newTemp(Ity_F64); 7241 IRTemp src12 = newTemp(Ity_D32); 7242 IRTemp dst12 = newTemp(Ity_F128); 7243 IRTemp src13 = newTemp(Ity_D64); 7244 IRTemp dst13 = newTemp(Ity_F32); 7245 IRTemp src14 = newTemp(Ity_D64); 7246 IRTemp dst14 = newTemp(Ity_F64); 7247 IRTemp src15 = newTemp(Ity_D64); 7248 IRTemp dst15 = newTemp(Ity_F128); 7249 IRTemp src16 = newTemp(Ity_D128); 7250 IRTemp dst16 = newTemp(Ity_F32); 7251 IRTemp src17 = newTemp(Ity_D128); 7252 IRTemp dst17 = newTemp(Ity_F64); 7253 IRTemp src18 = newTemp(Ity_D128); 7254 IRTemp dst18 = newTemp(Ity_F128); 7255 IRExpr *irrm; 7256 7257 if (! s390_host_has_pfpo) { 7258 emulation_failure(EmFail_S390X_pfpo); 7259 goto done; 7260 } 7261 7262 assign(gr0, get_gpr_w1(0)); 7263 /* get function code */ 7264 assign(fn, binop(Iop_And32, binop(Iop_Shr32, mkexpr(gr0), mkU8(8)), 7265 mkU32(0x7fffff))); 7266 /* get validity test bit */ 7267 assign(test_bit, binop(Iop_And32, binop(Iop_Shr32, mkexpr(gr0), mkU8(31)), 7268 mkU32(0x1))); 7269 irrm = get_rounding_mode_from_gr0(); 7270 7271 /* test_bit is 1 */ 7272 assign(src1, get_fpr_w0(4)); /* get source from FPR 4,6 */ 7273 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_64, src1, gr0); 7274 7275 /* Return code set in GR1 is usually 0. Non-zero value is set only 7276 when exceptions are raised. See Programming Notes point 5 in the 7277 instrcution description of pfpo in POP. Since valgrind does not 7278 model exception, it might be safe to just set 0 to GR 1. */ 7279 put_gpr_w1(1, mkU32(0x0)); 7280 next_insn_if(binop(Iop_CmpEQ32, mkexpr(test_bit), mkU32(0x1))); 7281 7282 /* Check validity of function code in GR 0 */ 7283 assign(ef, s390_call_pfpo_helper(unop(Iop_32Uto64, mkexpr(gr0)))); 7284 emulation_failure_with_expr(mkexpr(ef)); 7285 7286 stmt( 7287 IRStmt_Exit( 7288 binop(Iop_CmpNE32, mkexpr(ef), mkU32(EmNote_NONE)), 7289 Ijk_EmFail, 7290 IRConst_U64(guest_IA_next_instr), 7291 S390X_GUEST_OFFSET(guest_IA) 7292 ) 7293 ); 7294 7295 /* F32 -> D32 */ 7296 /* get source from FPR 4,6 - already set in src1 */ 7297 assign(dst1, binop(Iop_F32toD32, irrm, mkexpr(src1))); 7298 put_dpr_w0(0, mkexpr(dst1)); /* put the result in FPR 0,2 */ 7299 put_gpr_w1(1, mkU32(0x0)); 7300 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_32, src1, gr0); 7301 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F32_TO_D32))); 7302 7303 /* F32 -> D64 */ 7304 assign(src2, get_fpr_w0(4)); /* get source from FPR 4,6 */ 7305 assign(dst2, binop(Iop_F32toD64, irrm, mkexpr(src2))); 7306 put_dpr_dw0(0, mkexpr(dst2)); /* put the result in FPR 0,2 */ 7307 put_gpr_w1(1, mkU32(0x0)); 7308 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_32, src2, gr0); 7309 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F32_TO_D64))); 7310 7311 /* F32 -> D128 */ 7312 assign(src3, get_fpr_w0(4)); /* get source from FPR 4,6 */ 7313 assign(dst3, binop(Iop_F32toD128, irrm, mkexpr(src3))); 7314 put_dpr_pair(0, mkexpr(dst3)); /* put the result in FPR 0,2 */ 7315 put_gpr_w1(1, mkU32(0x0)); 7316 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_32, src3, gr0); 7317 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F32_TO_D128))); 7318 7319 /* F64 -> D32 */ 7320 assign(src4, get_fpr_dw0(4)); /* get source from FPR 4,6 */ 7321 assign(dst4, binop(Iop_F64toD32, irrm, mkexpr(src4))); 7322 put_dpr_w0(0, mkexpr(dst4)); /* put the result in FPR 0,2 */ 7323 put_gpr_w1(1, mkU32(0x0)); 7324 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_64, src4, gr0); 7325 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F64_TO_D32))); 7326 7327 /* F64 -> D64 */ 7328 assign(src5, get_fpr_dw0(4)); /* get source from FPR 4,6 */ 7329 assign(dst5, binop(Iop_F64toD64, irrm, mkexpr(src5))); 7330 put_dpr_dw0(0, mkexpr(dst5)); /* put the result in FPR 0,2 */ 7331 put_gpr_w1(1, mkU32(0x0)); 7332 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_64, src5, gr0); 7333 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F64_TO_D64))); 7334 7335 /* F64 -> D128 */ 7336 assign(src6, get_fpr_dw0(4)); /* get source from FPR 4,6 */ 7337 assign(dst6, binop(Iop_F64toD128, irrm, mkexpr(src6))); 7338 put_dpr_pair(0, mkexpr(dst6)); /* put the result in FPR 0,2 */ 7339 put_gpr_w1(1, mkU32(0x0)); 7340 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_64, src6, gr0); 7341 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F64_TO_D128))); 7342 7343 /* F128 -> D32 */ 7344 assign(src7, get_fpr_pair(4)); /* get source from FPR 4,6 */ 7345 assign(dst7, binop(Iop_F128toD32, irrm, mkexpr(src7))); 7346 put_dpr_w0(0, mkexpr(dst7)); /* put the result in FPR 0,2 */ 7347 put_gpr_w1(1, mkU32(0x0)); 7348 s390_cc_thunk_put1f128Z(S390_CC_OP_PFPO_128, src7, gr0); 7349 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F128_TO_D32))); 7350 7351 /* F128 -> D64 */ 7352 assign(src8, get_fpr_pair(4)); /* get source from FPR 4,6 */ 7353 assign(dst8, binop(Iop_F128toD64, irrm, mkexpr(src8))); 7354 put_dpr_dw0(0, mkexpr(dst8)); /* put the result in FPR 0,2 */ 7355 put_gpr_w1(1, mkU32(0x0)); 7356 s390_cc_thunk_put1f128Z(S390_CC_OP_PFPO_128, src8, gr0); 7357 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F128_TO_D64))); 7358 7359 /* F128 -> D128 */ 7360 assign(src9, get_fpr_pair(4)); /* get source from FPR 4,6 */ 7361 assign(dst9, binop(Iop_F128toD128, irrm, mkexpr(src9))); 7362 put_dpr_pair(0, mkexpr(dst9)); /* put the result in FPR 0,2 */ 7363 put_gpr_w1(1, mkU32(0x0)); 7364 s390_cc_thunk_put1f128Z(S390_CC_OP_PFPO_128, src9, gr0); 7365 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F128_TO_D128))); 7366 7367 /* D32 -> F32 */ 7368 assign(src10, get_dpr_w0(4)); /* get source from FPR 4,6 */ 7369 assign(dst10, binop(Iop_D32toF32, irrm, mkexpr(src10))); 7370 put_fpr_w0(0, mkexpr(dst10)); /* put the result in FPR 0,2 */ 7371 put_gpr_w1(1, mkU32(0x0)); 7372 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_32, src10, gr0); 7373 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D32_TO_F32))); 7374 7375 /* D32 -> F64 */ 7376 assign(src11, get_dpr_w0(4)); /* get source from FPR 4,6 */ 7377 assign(dst11, binop(Iop_D32toF64, irrm, mkexpr(src11))); 7378 put_fpr_dw0(0, mkexpr(dst11)); /* put the result in FPR 0,2 */ 7379 put_gpr_w1(1, mkU32(0x0)); 7380 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_32, src11, gr0); 7381 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D32_TO_F64))); 7382 7383 /* D32 -> F128 */ 7384 assign(src12, get_dpr_w0(4)); /* get source from FPR 4,6 */ 7385 assign(dst12, binop(Iop_D32toF128, irrm, mkexpr(src12))); 7386 put_fpr_pair(0, mkexpr(dst12)); /* put the result in FPR 0,2 */ 7387 put_gpr_w1(1, mkU32(0x0)); 7388 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_32, src12, gr0); 7389 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D32_TO_F128))); 7390 7391 /* D64 -> F32 */ 7392 assign(src13, get_dpr_dw0(4)); /* get source from FPR 4,6 */ 7393 assign(dst13, binop(Iop_D64toF32, irrm, mkexpr(src13))); 7394 put_fpr_w0(0, mkexpr(dst13)); /* put the result in FPR 0,2 */ 7395 put_gpr_w1(1, mkU32(0x0)); 7396 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_64, src13, gr0); 7397 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D64_TO_F32))); 7398 7399 /* D64 -> F64 */ 7400 assign(src14, get_dpr_dw0(4)); /* get source from FPR 4,6 */ 7401 assign(dst14, binop(Iop_D64toF64, irrm, mkexpr(src14))); 7402 put_fpr_dw0(0, mkexpr(dst14)); /* put the result in FPR 0,2 */ 7403 put_gpr_w1(1, mkU32(0x0)); 7404 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_64, src14, gr0); 7405 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D64_TO_F64))); 7406 7407 /* D64 -> F128 */ 7408 assign(src15, get_dpr_dw0(4)); /* get source from FPR 4,6 */ 7409 assign(dst15, binop(Iop_D64toF128, irrm, mkexpr(src15))); 7410 put_fpr_pair(0, mkexpr(dst15)); /* put the result in FPR 0,2 */ 7411 put_gpr_w1(1, mkU32(0x0)); 7412 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_64, src15, gr0); 7413 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D64_TO_F128))); 7414 7415 /* D128 -> F32 */ 7416 assign(src16, get_dpr_pair(4)); /* get source from FPR 4,6 */ 7417 assign(dst16, binop(Iop_D128toF32, irrm, mkexpr(src16))); 7418 put_fpr_w0(0, mkexpr(dst16)); /* put the result in FPR 0,2 */ 7419 put_gpr_w1(1, mkU32(0x0)); 7420 s390_cc_thunk_put1d128Z(S390_CC_OP_PFPO_128, src16, gr0); 7421 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D128_TO_F32))); 7422 7423 /* D128 -> F64 */ 7424 assign(src17, get_dpr_pair(4)); /* get source from FPR 4,6 */ 7425 assign(dst17, binop(Iop_D128toF64, irrm, mkexpr(src17))); 7426 put_fpr_dw0(0, mkexpr(dst17)); /* put the result in FPR 0,2 */ 7427 put_gpr_w1(1, mkU32(0x0)); 7428 s390_cc_thunk_put1d128Z(S390_CC_OP_PFPO_128, src17, gr0); 7429 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D128_TO_F64))); 7430 7431 /* D128 -> F128 */ 7432 assign(src18, get_dpr_pair(4)); /* get source from FPR 4,6 */ 7433 assign(dst18, binop(Iop_D128toF128, irrm, mkexpr(src18))); 7434 put_fpr_pair(0, mkexpr(dst18)); /* put the result in FPR 0,2 */ 7435 put_gpr_w1(1, mkU32(0x0)); 7436 s390_cc_thunk_put1d128Z(S390_CC_OP_PFPO_128, src18, gr0); 7437 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D128_TO_F128))); 7438 7439 done: 7440 return "pfpo"; 7441 } 7442 7443 static const HChar * 7444 s390_irgen_RLL(UChar r1, UChar r3, IRTemp op2addr) 7445 { 7446 IRTemp amount = newTemp(Ity_I64); 7447 IRTemp op = newTemp(Ity_I32); 7448 7449 assign(amount, binop(Iop_And64, mkexpr(op2addr), mkU64(31))); 7450 assign(op, get_gpr_w1(r3)); 7451 put_gpr_w1(r1, binop(Iop_Or32, binop(Iop_Shl32, mkexpr(op), unop(Iop_64to8, 7452 mkexpr(amount))), binop(Iop_Shr32, mkexpr(op), unop(Iop_64to8, 7453 binop(Iop_Sub64, mkU64(32), mkexpr(amount)))))); 7454 7455 return "rll"; 7456 } 7457 7458 static const HChar * 7459 s390_irgen_RLLG(UChar r1, UChar r3, IRTemp op2addr) 7460 { 7461 IRTemp amount = newTemp(Ity_I64); 7462 IRTemp op = newTemp(Ity_I64); 7463 7464 assign(amount, binop(Iop_And64, mkexpr(op2addr), mkU64(63))); 7465 assign(op, get_gpr_dw0(r3)); 7466 put_gpr_dw0(r1, binop(Iop_Or64, binop(Iop_Shl64, mkexpr(op), unop(Iop_64to8, 7467 mkexpr(amount))), binop(Iop_Shr64, mkexpr(op), unop(Iop_64to8, 7468 binop(Iop_Sub64, mkU64(64), mkexpr(amount)))))); 7469 7470 return "rllg"; 7471 } 7472 7473 static const HChar * 7474 s390_irgen_RNSBG(UChar r1, UChar r2, UChar i3, UChar i4, UChar i5) 7475 { 7476 UChar from; 7477 UChar to; 7478 UChar rot; 7479 UChar t_bit; 7480 ULong mask; 7481 ULong maskc; 7482 IRTemp result = newTemp(Ity_I64); 7483 IRTemp op2 = newTemp(Ity_I64); 7484 7485 from = i3 & 63; 7486 to = i4 & 63; 7487 rot = i5 & 63; 7488 t_bit = i3 & 128; 7489 assign(op2, rot == 0 ? get_gpr_dw0(r2) : binop(Iop_Or64, binop(Iop_Shl64, 7490 get_gpr_dw0(r2), mkU8(rot)), binop(Iop_Shr64, get_gpr_dw0(r2), 7491 mkU8(64 - rot)))); 7492 if (from <= to) { 7493 mask = ~0ULL; 7494 mask = (mask >> from) & (mask << (63 - to)); 7495 maskc = ~mask; 7496 } else { 7497 maskc = ~0ULL; 7498 maskc = (maskc >> (to + 1)) & (maskc << (64 - from)); 7499 mask = ~maskc; 7500 } 7501 assign(result, binop(Iop_And64, binop(Iop_And64, get_gpr_dw0(r1), mkexpr(op2) 7502 ), mkU64(mask))); 7503 if (t_bit == 0) { 7504 put_gpr_dw0(r1, binop(Iop_Or64, binop(Iop_And64, get_gpr_dw0(r1), 7505 mkU64(maskc)), mkexpr(result))); 7506 } 7507 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7508 7509 return "rnsbg"; 7510 } 7511 7512 static const HChar * 7513 s390_irgen_RXSBG(UChar r1, UChar r2, UChar i3, UChar i4, UChar i5) 7514 { 7515 UChar from; 7516 UChar to; 7517 UChar rot; 7518 UChar t_bit; 7519 ULong mask; 7520 ULong maskc; 7521 IRTemp result = newTemp(Ity_I64); 7522 IRTemp op2 = newTemp(Ity_I64); 7523 7524 from = i3 & 63; 7525 to = i4 & 63; 7526 rot = i5 & 63; 7527 t_bit = i3 & 128; 7528 assign(op2, rot == 0 ? get_gpr_dw0(r2) : binop(Iop_Or64, binop(Iop_Shl64, 7529 get_gpr_dw0(r2), mkU8(rot)), binop(Iop_Shr64, get_gpr_dw0(r2), 7530 mkU8(64 - rot)))); 7531 if (from <= to) { 7532 mask = ~0ULL; 7533 mask = (mask >> from) & (mask << (63 - to)); 7534 maskc = ~mask; 7535 } else { 7536 maskc = ~0ULL; 7537 maskc = (maskc >> (to + 1)) & (maskc << (64 - from)); 7538 mask = ~maskc; 7539 } 7540 assign(result, binop(Iop_And64, binop(Iop_Xor64, get_gpr_dw0(r1), mkexpr(op2) 7541 ), mkU64(mask))); 7542 if (t_bit == 0) { 7543 put_gpr_dw0(r1, binop(Iop_Or64, binop(Iop_And64, get_gpr_dw0(r1), 7544 mkU64(maskc)), mkexpr(result))); 7545 } 7546 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7547 7548 return "rxsbg"; 7549 } 7550 7551 static const HChar * 7552 s390_irgen_ROSBG(UChar r1, UChar r2, UChar i3, UChar i4, UChar i5) 7553 { 7554 UChar from; 7555 UChar to; 7556 UChar rot; 7557 UChar t_bit; 7558 ULong mask; 7559 ULong maskc; 7560 IRTemp result = newTemp(Ity_I64); 7561 IRTemp op2 = newTemp(Ity_I64); 7562 7563 from = i3 & 63; 7564 to = i4 & 63; 7565 rot = i5 & 63; 7566 t_bit = i3 & 128; 7567 assign(op2, rot == 0 ? get_gpr_dw0(r2) : binop(Iop_Or64, binop(Iop_Shl64, 7568 get_gpr_dw0(r2), mkU8(rot)), binop(Iop_Shr64, get_gpr_dw0(r2), 7569 mkU8(64 - rot)))); 7570 if (from <= to) { 7571 mask = ~0ULL; 7572 mask = (mask >> from) & (mask << (63 - to)); 7573 maskc = ~mask; 7574 } else { 7575 maskc = ~0ULL; 7576 maskc = (maskc >> (to + 1)) & (maskc << (64 - from)); 7577 mask = ~maskc; 7578 } 7579 assign(result, binop(Iop_And64, binop(Iop_Or64, get_gpr_dw0(r1), mkexpr(op2) 7580 ), mkU64(mask))); 7581 if (t_bit == 0) { 7582 put_gpr_dw0(r1, binop(Iop_Or64, binop(Iop_And64, get_gpr_dw0(r1), 7583 mkU64(maskc)), mkexpr(result))); 7584 } 7585 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7586 7587 return "rosbg"; 7588 } 7589 7590 static const HChar * 7591 s390_irgen_RISBGx(UChar r1, UChar r2, UChar i3, UChar i4, UChar i5, 7592 Bool set_cc) 7593 { 7594 UChar from; 7595 UChar to; 7596 UChar rot; 7597 UChar z_bit; 7598 ULong mask; 7599 ULong maskc; 7600 IRTemp op2 = newTemp(Ity_I64); 7601 IRTemp result = newTemp(Ity_I64); 7602 7603 from = i3 & 63; 7604 to = i4 & 63; 7605 rot = i5 & 63; 7606 z_bit = i4 & 128; 7607 assign(op2, rot == 0 ? get_gpr_dw0(r2) : binop(Iop_Or64, binop(Iop_Shl64, 7608 get_gpr_dw0(r2), mkU8(rot)), binop(Iop_Shr64, get_gpr_dw0(r2), 7609 mkU8(64 - rot)))); 7610 if (from <= to) { 7611 mask = ~0ULL; 7612 mask = (mask >> from) & (mask << (63 - to)); 7613 maskc = ~mask; 7614 } else { 7615 maskc = ~0ULL; 7616 maskc = (maskc >> (to + 1)) & (maskc << (64 - from)); 7617 mask = ~maskc; 7618 } 7619 if (z_bit == 0) { 7620 put_gpr_dw0(r1, binop(Iop_Or64, binop(Iop_And64, get_gpr_dw0(r1), 7621 mkU64(maskc)), binop(Iop_And64, mkexpr(op2), mkU64(mask)))); 7622 } else { 7623 put_gpr_dw0(r1, binop(Iop_And64, mkexpr(op2), mkU64(mask))); 7624 } 7625 assign(result, get_gpr_dw0(r1)); 7626 if (set_cc) { 7627 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, result); 7628 return "risbg"; 7629 } 7630 7631 return "risbgn"; 7632 } 7633 7634 static const HChar * 7635 s390_irgen_RISBG(UChar r1, UChar r2, UChar i3, UChar i4, UChar i5) 7636 { 7637 return s390_irgen_RISBGx(r1, r2, i3, i4, i5, True); 7638 } 7639 7640 static const HChar * 7641 s390_irgen_RISBGN(UChar r1, UChar r2, UChar i3, UChar i4, UChar i5) 7642 { 7643 return s390_irgen_RISBGx(r1, r2, i3, i4, i5, False); 7644 } 7645 7646 static IRExpr * 7647 s390_irgen_RISBxG(UChar r1, UChar r2, UChar i3, UChar i4, UChar i5, 7648 Bool high) 7649 { 7650 UChar from; 7651 UChar to; 7652 UChar rot; 7653 UChar z_bit; 7654 UInt mask; 7655 UInt maskc; 7656 IRTemp op2 = newTemp(Ity_I32); 7657 7658 from = i3 & 31; 7659 to = i4 & 31; 7660 rot = i5 & 63; 7661 z_bit = i4 & 128; 7662 if (rot == 0) { 7663 assign(op2, high ? get_gpr_w0(r2) : get_gpr_w1(r2)); 7664 } else if (rot == 32) { 7665 assign(op2, high ? get_gpr_w1(r2) : get_gpr_w0(r2)); 7666 } else { 7667 assign(op2, 7668 unop(high ? Iop_64HIto32 : Iop_64to32, 7669 binop(Iop_Or64, 7670 binop(Iop_Shl64, get_gpr_dw0(r2), mkU8(rot)), 7671 binop(Iop_Shr64, get_gpr_dw0(r2), mkU8(64 - rot))))); 7672 } 7673 if (from <= to) { 7674 mask = ~0U; 7675 mask = (mask >> from) & (mask << (31 - to)); 7676 maskc = ~mask; 7677 } else { 7678 maskc = ~0U; 7679 maskc = (maskc >> (to + 1)) & (maskc << (32 - from)); 7680 mask = ~maskc; 7681 } 7682 if (z_bit) { 7683 return binop(Iop_And32, mkexpr(op2), mkU32(mask)); 7684 } 7685 return binop(Iop_Or32, 7686 binop(Iop_And32, high ? get_gpr_w0(r1) : get_gpr_w1(r1), 7687 mkU32(maskc)), 7688 binop(Iop_And32, mkexpr(op2), mkU32(mask))); 7689 } 7690 7691 static const HChar * 7692 s390_irgen_RISBHG(UChar r1, UChar r2, UChar i3, UChar i4, UChar i5) 7693 { 7694 put_gpr_w0(r1, s390_irgen_RISBxG(r1, r2, i3, i4, i5, True)); 7695 return "risbhg"; 7696 } 7697 7698 static const HChar * 7699 s390_irgen_RISBLG(UChar r1, UChar r2, UChar i3, UChar i4, UChar i5) 7700 { 7701 put_gpr_w1(r1, s390_irgen_RISBxG(r1, r2, i3, i4, i5, False)); 7702 return "risblg"; 7703 } 7704 7705 static const HChar * 7706 s390_irgen_SAR(UChar r1, UChar r2) 7707 { 7708 put_ar_w0(r1, get_gpr_w1(r2)); 7709 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 7710 s390_disasm(ENC3(MNM, AR, GPR), "sar", r1, r2); 7711 7712 return "sar"; 7713 } 7714 7715 static const HChar * 7716 s390_irgen_SLDA(UChar r1, IRTemp op2addr) 7717 { 7718 IRTemp p1 = newTemp(Ity_I64); 7719 IRTemp p2 = newTemp(Ity_I64); 7720 IRTemp op = newTemp(Ity_I64); 7721 IRTemp result = newTemp(Ity_I64); 7722 ULong sign_mask; 7723 IRTemp shift_amount = newTemp(Ity_I64); 7724 7725 assign(p1, unop(Iop_32Uto64, get_gpr_w1(r1))); 7726 assign(p2, unop(Iop_32Uto64, get_gpr_w1(r1 + 1))); 7727 assign(op, binop(Iop_Or64, binop(Iop_Shl64, mkexpr(p1), mkU8(32)), mkexpr(p2) 7728 )); 7729 sign_mask = 1ULL << 63; 7730 assign(shift_amount, binop(Iop_And64, mkexpr(op2addr), mkU64(63))); 7731 assign(result, binop(Iop_Or64, binop(Iop_And64, binop(Iop_Shl64, mkexpr(op), 7732 unop(Iop_64to8, mkexpr(shift_amount))), mkU64(~sign_mask)), 7733 binop(Iop_And64, mkexpr(op), mkU64(sign_mask)))); 7734 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 7735 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 7736 s390_cc_thunk_putZZ(S390_CC_OP_SHIFT_LEFT_64, op, shift_amount); 7737 7738 return "slda"; 7739 } 7740 7741 static const HChar * 7742 s390_irgen_SLDL(UChar r1, IRTemp op2addr) 7743 { 7744 IRTemp p1 = newTemp(Ity_I64); 7745 IRTemp p2 = newTemp(Ity_I64); 7746 IRTemp result = newTemp(Ity_I64); 7747 7748 assign(p1, unop(Iop_32Uto64, get_gpr_w1(r1))); 7749 assign(p2, unop(Iop_32Uto64, get_gpr_w1(r1 + 1))); 7750 assign(result, binop(Iop_Shl64, binop(Iop_Or64, binop(Iop_Shl64, mkexpr(p1), 7751 mkU8(32)), mkexpr(p2)), unop(Iop_64to8, binop(Iop_And64, 7752 mkexpr(op2addr), mkU64(63))))); 7753 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 7754 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 7755 7756 return "sldl"; 7757 } 7758 7759 static const HChar * 7760 s390_irgen_SLA(UChar r1, IRTemp op2addr) 7761 { 7762 IRTemp uop = newTemp(Ity_I32); 7763 IRTemp result = newTemp(Ity_I32); 7764 UInt sign_mask; 7765 IRTemp shift_amount = newTemp(Ity_I64); 7766 IRTemp op = newTemp(Ity_I32); 7767 7768 assign(op, get_gpr_w1(r1)); 7769 assign(uop, get_gpr_w1(r1)); 7770 sign_mask = 2147483648U; 7771 assign(shift_amount, binop(Iop_And64, mkexpr(op2addr), mkU64(63))); 7772 assign(result, binop(Iop_Or32, binop(Iop_And32, binop(Iop_Shl32, mkexpr(uop), 7773 unop(Iop_64to8, mkexpr(shift_amount))), mkU32(~sign_mask)), 7774 binop(Iop_And32, mkexpr(uop), mkU32(sign_mask)))); 7775 put_gpr_w1(r1, mkexpr(result)); 7776 s390_cc_thunk_putZZ(S390_CC_OP_SHIFT_LEFT_32, op, shift_amount); 7777 7778 return "sla"; 7779 } 7780 7781 static const HChar * 7782 s390_irgen_SLAK(UChar r1, UChar r3, IRTemp op2addr) 7783 { 7784 IRTemp uop = newTemp(Ity_I32); 7785 IRTemp result = newTemp(Ity_I32); 7786 UInt sign_mask; 7787 IRTemp shift_amount = newTemp(Ity_I64); 7788 IRTemp op = newTemp(Ity_I32); 7789 7790 assign(op, get_gpr_w1(r3)); 7791 assign(uop, get_gpr_w1(r3)); 7792 sign_mask = 2147483648U; 7793 assign(shift_amount, binop(Iop_And64, mkexpr(op2addr), mkU64(63))); 7794 assign(result, binop(Iop_Or32, binop(Iop_And32, binop(Iop_Shl32, mkexpr(uop), 7795 unop(Iop_64to8, mkexpr(shift_amount))), mkU32(~sign_mask)), 7796 binop(Iop_And32, mkexpr(uop), mkU32(sign_mask)))); 7797 put_gpr_w1(r1, mkexpr(result)); 7798 s390_cc_thunk_putZZ(S390_CC_OP_SHIFT_LEFT_32, op, shift_amount); 7799 7800 return "slak"; 7801 } 7802 7803 static const HChar * 7804 s390_irgen_SLAG(UChar r1, UChar r3, IRTemp op2addr) 7805 { 7806 IRTemp uop = newTemp(Ity_I64); 7807 IRTemp result = newTemp(Ity_I64); 7808 ULong sign_mask; 7809 IRTemp shift_amount = newTemp(Ity_I64); 7810 IRTemp op = newTemp(Ity_I64); 7811 7812 assign(op, get_gpr_dw0(r3)); 7813 assign(uop, get_gpr_dw0(r3)); 7814 sign_mask = 9223372036854775808ULL; 7815 assign(shift_amount, binop(Iop_And64, mkexpr(op2addr), mkU64(63))); 7816 assign(result, binop(Iop_Or64, binop(Iop_And64, binop(Iop_Shl64, mkexpr(uop), 7817 unop(Iop_64to8, mkexpr(shift_amount))), mkU64(~sign_mask)), 7818 binop(Iop_And64, mkexpr(uop), mkU64(sign_mask)))); 7819 put_gpr_dw0(r1, mkexpr(result)); 7820 s390_cc_thunk_putZZ(S390_CC_OP_SHIFT_LEFT_64, op, shift_amount); 7821 7822 return "slag"; 7823 } 7824 7825 static const HChar * 7826 s390_irgen_SLL(UChar r1, IRTemp op2addr) 7827 { 7828 put_gpr_w1(r1, binop(Iop_Shl32, get_gpr_w1(r1), unop(Iop_64to8, 7829 binop(Iop_And64, mkexpr(op2addr), mkU64(63))))); 7830 7831 return "sll"; 7832 } 7833 7834 static const HChar * 7835 s390_irgen_SLLK(UChar r1, UChar r3, IRTemp op2addr) 7836 { 7837 put_gpr_w1(r1, binop(Iop_Shl32, get_gpr_w1(r3), unop(Iop_64to8, 7838 binop(Iop_And64, mkexpr(op2addr), mkU64(63))))); 7839 7840 return "sllk"; 7841 } 7842 7843 static const HChar * 7844 s390_irgen_SLLG(UChar r1, UChar r3, IRTemp op2addr) 7845 { 7846 put_gpr_dw0(r1, binop(Iop_Shl64, get_gpr_dw0(r3), unop(Iop_64to8, 7847 binop(Iop_And64, mkexpr(op2addr), mkU64(63))))); 7848 7849 return "sllg"; 7850 } 7851 7852 static const HChar * 7853 s390_irgen_SRDA(UChar r1, IRTemp op2addr) 7854 { 7855 IRTemp p1 = newTemp(Ity_I64); 7856 IRTemp p2 = newTemp(Ity_I64); 7857 IRTemp result = newTemp(Ity_I64); 7858 7859 assign(p1, unop(Iop_32Uto64, get_gpr_w1(r1))); 7860 assign(p2, unop(Iop_32Uto64, get_gpr_w1(r1 + 1))); 7861 assign(result, binop(Iop_Sar64, binop(Iop_Or64, binop(Iop_Shl64, mkexpr(p1), 7862 mkU8(32)), mkexpr(p2)), unop(Iop_64to8, binop(Iop_And64, 7863 mkexpr(op2addr), mkU64(63))))); 7864 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 7865 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 7866 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, result); 7867 7868 return "srda"; 7869 } 7870 7871 static const HChar * 7872 s390_irgen_SRDL(UChar r1, IRTemp op2addr) 7873 { 7874 IRTemp p1 = newTemp(Ity_I64); 7875 IRTemp p2 = newTemp(Ity_I64); 7876 IRTemp result = newTemp(Ity_I64); 7877 7878 assign(p1, unop(Iop_32Uto64, get_gpr_w1(r1))); 7879 assign(p2, unop(Iop_32Uto64, get_gpr_w1(r1 + 1))); 7880 assign(result, binop(Iop_Shr64, binop(Iop_Or64, binop(Iop_Shl64, mkexpr(p1), 7881 mkU8(32)), mkexpr(p2)), unop(Iop_64to8, binop(Iop_And64, 7882 mkexpr(op2addr), mkU64(63))))); 7883 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 7884 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 7885 7886 return "srdl"; 7887 } 7888 7889 static const HChar * 7890 s390_irgen_SRA(UChar r1, IRTemp op2addr) 7891 { 7892 IRTemp result = newTemp(Ity_I32); 7893 IRTemp op = newTemp(Ity_I32); 7894 7895 assign(op, get_gpr_w1(r1)); 7896 assign(result, binop(Iop_Sar32, mkexpr(op), unop(Iop_64to8, binop(Iop_And64, 7897 mkexpr(op2addr), mkU64(63))))); 7898 put_gpr_w1(r1, mkexpr(result)); 7899 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, result); 7900 7901 return "sra"; 7902 } 7903 7904 static const HChar * 7905 s390_irgen_SRAK(UChar r1, UChar r3, IRTemp op2addr) 7906 { 7907 IRTemp result = newTemp(Ity_I32); 7908 IRTemp op = newTemp(Ity_I32); 7909 7910 assign(op, get_gpr_w1(r3)); 7911 assign(result, binop(Iop_Sar32, mkexpr(op), unop(Iop_64to8, binop(Iop_And64, 7912 mkexpr(op2addr), mkU64(63))))); 7913 put_gpr_w1(r1, mkexpr(result)); 7914 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, result); 7915 7916 return "srak"; 7917 } 7918 7919 static const HChar * 7920 s390_irgen_SRAG(UChar r1, UChar r3, IRTemp op2addr) 7921 { 7922 IRTemp result = newTemp(Ity_I64); 7923 IRTemp op = newTemp(Ity_I64); 7924 7925 assign(op, get_gpr_dw0(r3)); 7926 assign(result, binop(Iop_Sar64, mkexpr(op), unop(Iop_64to8, binop(Iop_And64, 7927 mkexpr(op2addr), mkU64(63))))); 7928 put_gpr_dw0(r1, mkexpr(result)); 7929 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, result); 7930 7931 return "srag"; 7932 } 7933 7934 static const HChar * 7935 s390_irgen_SRL(UChar r1, IRTemp op2addr) 7936 { 7937 IRTemp op = newTemp(Ity_I32); 7938 7939 assign(op, get_gpr_w1(r1)); 7940 put_gpr_w1(r1, binop(Iop_Shr32, mkexpr(op), unop(Iop_64to8, binop(Iop_And64, 7941 mkexpr(op2addr), mkU64(63))))); 7942 7943 return "srl"; 7944 } 7945 7946 static const HChar * 7947 s390_irgen_SRLK(UChar r1, UChar r3, IRTemp op2addr) 7948 { 7949 IRTemp op = newTemp(Ity_I32); 7950 7951 assign(op, get_gpr_w1(r3)); 7952 put_gpr_w1(r1, binop(Iop_Shr32, mkexpr(op), unop(Iop_64to8, binop(Iop_And64, 7953 mkexpr(op2addr), mkU64(63))))); 7954 7955 return "srlk"; 7956 } 7957 7958 static const HChar * 7959 s390_irgen_SRLG(UChar r1, UChar r3, IRTemp op2addr) 7960 { 7961 IRTemp op = newTemp(Ity_I64); 7962 7963 assign(op, get_gpr_dw0(r3)); 7964 put_gpr_dw0(r1, binop(Iop_Shr64, mkexpr(op), unop(Iop_64to8, binop(Iop_And64, 7965 mkexpr(op2addr), mkU64(63))))); 7966 7967 return "srlg"; 7968 } 7969 7970 static const HChar * 7971 s390_irgen_ST(UChar r1, IRTemp op2addr) 7972 { 7973 store(mkexpr(op2addr), get_gpr_w1(r1)); 7974 7975 return "st"; 7976 } 7977 7978 static const HChar * 7979 s390_irgen_STY(UChar r1, IRTemp op2addr) 7980 { 7981 store(mkexpr(op2addr), get_gpr_w1(r1)); 7982 7983 return "sty"; 7984 } 7985 7986 static const HChar * 7987 s390_irgen_STG(UChar r1, IRTemp op2addr) 7988 { 7989 store(mkexpr(op2addr), get_gpr_dw0(r1)); 7990 7991 return "stg"; 7992 } 7993 7994 static const HChar * 7995 s390_irgen_STRL(UChar r1, UInt i2) 7996 { 7997 store(mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int)i2 << 1)), 7998 get_gpr_w1(r1)); 7999 8000 return "strl"; 8001 } 8002 8003 static const HChar * 8004 s390_irgen_STGRL(UChar r1, UInt i2) 8005 { 8006 store(mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int)i2 << 1)), 8007 get_gpr_dw0(r1)); 8008 8009 return "stgrl"; 8010 } 8011 8012 static const HChar * 8013 s390_irgen_STC(UChar r1, IRTemp op2addr) 8014 { 8015 store(mkexpr(op2addr), get_gpr_b7(r1)); 8016 8017 return "stc"; 8018 } 8019 8020 static const HChar * 8021 s390_irgen_STCY(UChar r1, IRTemp op2addr) 8022 { 8023 store(mkexpr(op2addr), get_gpr_b7(r1)); 8024 8025 return "stcy"; 8026 } 8027 8028 static const HChar * 8029 s390_irgen_STCH(UChar r1, IRTemp op2addr) 8030 { 8031 store(mkexpr(op2addr), get_gpr_b3(r1)); 8032 8033 return "stch"; 8034 } 8035 8036 static const HChar * 8037 s390_irgen_STCM(UChar r1, UChar r3, IRTemp op2addr) 8038 { 8039 UChar mask; 8040 UChar n; 8041 8042 mask = (UChar)r3; 8043 n = 0; 8044 if ((mask & 8) != 0) { 8045 store(mkexpr(op2addr), get_gpr_b4(r1)); 8046 n = n + 1; 8047 } 8048 if ((mask & 4) != 0) { 8049 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b5(r1)); 8050 n = n + 1; 8051 } 8052 if ((mask & 2) != 0) { 8053 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b6(r1)); 8054 n = n + 1; 8055 } 8056 if ((mask & 1) != 0) { 8057 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b7(r1)); 8058 } 8059 8060 return "stcm"; 8061 } 8062 8063 static const HChar * 8064 s390_irgen_STCMY(UChar r1, UChar r3, IRTemp op2addr) 8065 { 8066 UChar mask; 8067 UChar n; 8068 8069 mask = (UChar)r3; 8070 n = 0; 8071 if ((mask & 8) != 0) { 8072 store(mkexpr(op2addr), get_gpr_b4(r1)); 8073 n = n + 1; 8074 } 8075 if ((mask & 4) != 0) { 8076 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b5(r1)); 8077 n = n + 1; 8078 } 8079 if ((mask & 2) != 0) { 8080 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b6(r1)); 8081 n = n + 1; 8082 } 8083 if ((mask & 1) != 0) { 8084 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b7(r1)); 8085 } 8086 8087 return "stcmy"; 8088 } 8089 8090 static const HChar * 8091 s390_irgen_STCMH(UChar r1, UChar r3, IRTemp op2addr) 8092 { 8093 UChar mask; 8094 UChar n; 8095 8096 mask = (UChar)r3; 8097 n = 0; 8098 if ((mask & 8) != 0) { 8099 store(mkexpr(op2addr), get_gpr_b0(r1)); 8100 n = n + 1; 8101 } 8102 if ((mask & 4) != 0) { 8103 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b1(r1)); 8104 n = n + 1; 8105 } 8106 if ((mask & 2) != 0) { 8107 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b2(r1)); 8108 n = n + 1; 8109 } 8110 if ((mask & 1) != 0) { 8111 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b3(r1)); 8112 } 8113 8114 return "stcmh"; 8115 } 8116 8117 static const HChar * 8118 s390_irgen_STH(UChar r1, IRTemp op2addr) 8119 { 8120 store(mkexpr(op2addr), get_gpr_hw3(r1)); 8121 8122 return "sth"; 8123 } 8124 8125 static const HChar * 8126 s390_irgen_STHY(UChar r1, IRTemp op2addr) 8127 { 8128 store(mkexpr(op2addr), get_gpr_hw3(r1)); 8129 8130 return "sthy"; 8131 } 8132 8133 static const HChar * 8134 s390_irgen_STHRL(UChar r1, UInt i2) 8135 { 8136 store(mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int)i2 << 1)), 8137 get_gpr_hw3(r1)); 8138 8139 return "sthrl"; 8140 } 8141 8142 static const HChar * 8143 s390_irgen_STHH(UChar r1, IRTemp op2addr) 8144 { 8145 store(mkexpr(op2addr), get_gpr_hw1(r1)); 8146 8147 return "sthh"; 8148 } 8149 8150 static const HChar * 8151 s390_irgen_STFH(UChar r1, IRTemp op2addr) 8152 { 8153 store(mkexpr(op2addr), get_gpr_w0(r1)); 8154 8155 return "stfh"; 8156 } 8157 8158 static const HChar * 8159 s390_irgen_STOC(UChar r1, IRTemp op2addr) 8160 { 8161 /* condition is checked in format handler */ 8162 store(mkexpr(op2addr), get_gpr_w1(r1)); 8163 8164 return "stoc"; 8165 } 8166 8167 static const HChar * 8168 s390_irgen_STOCG(UChar r1, IRTemp op2addr) 8169 { 8170 /* condition is checked in format handler */ 8171 store(mkexpr(op2addr), get_gpr_dw0(r1)); 8172 8173 return "stocg"; 8174 } 8175 8176 static const HChar * 8177 s390_irgen_STPQ(UChar r1, IRTemp op2addr) 8178 { 8179 store(mkexpr(op2addr), get_gpr_dw0(r1)); 8180 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(8)), get_gpr_dw0(r1 + 1)); 8181 8182 return "stpq"; 8183 } 8184 8185 static const HChar * 8186 s390_irgen_STRVH(UChar r1, IRTemp op2addr) 8187 { 8188 store(mkexpr(op2addr), get_gpr_b7(r1)); 8189 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(1)), get_gpr_b6(r1)); 8190 8191 return "strvh"; 8192 } 8193 8194 static const HChar * 8195 s390_irgen_STRV(UChar r1, IRTemp op2addr) 8196 { 8197 store(mkexpr(op2addr), get_gpr_b7(r1)); 8198 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(1)), get_gpr_b6(r1)); 8199 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(2)), get_gpr_b5(r1)); 8200 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(3)), get_gpr_b4(r1)); 8201 8202 return "strv"; 8203 } 8204 8205 static const HChar * 8206 s390_irgen_STRVG(UChar r1, IRTemp op2addr) 8207 { 8208 store(mkexpr(op2addr), get_gpr_b7(r1)); 8209 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(1)), get_gpr_b6(r1)); 8210 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(2)), get_gpr_b5(r1)); 8211 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(3)), get_gpr_b4(r1)); 8212 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(4)), get_gpr_b3(r1)); 8213 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(5)), get_gpr_b2(r1)); 8214 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(6)), get_gpr_b1(r1)); 8215 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(7)), get_gpr_b0(r1)); 8216 8217 return "strvg"; 8218 } 8219 8220 static const HChar * 8221 s390_irgen_SR(UChar r1, UChar r2) 8222 { 8223 IRTemp op1 = newTemp(Ity_I32); 8224 IRTemp op2 = newTemp(Ity_I32); 8225 IRTemp result = newTemp(Ity_I32); 8226 8227 assign(op1, get_gpr_w1(r1)); 8228 assign(op2, get_gpr_w1(r2)); 8229 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2))); 8230 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, op1, op2); 8231 put_gpr_w1(r1, mkexpr(result)); 8232 8233 return "sr"; 8234 } 8235 8236 static const HChar * 8237 s390_irgen_SGR(UChar r1, UChar r2) 8238 { 8239 IRTemp op1 = newTemp(Ity_I64); 8240 IRTemp op2 = newTemp(Ity_I64); 8241 IRTemp result = newTemp(Ity_I64); 8242 8243 assign(op1, get_gpr_dw0(r1)); 8244 assign(op2, get_gpr_dw0(r2)); 8245 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2))); 8246 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_64, op1, op2); 8247 put_gpr_dw0(r1, mkexpr(result)); 8248 8249 return "sgr"; 8250 } 8251 8252 static const HChar * 8253 s390_irgen_SGFR(UChar r1, UChar r2) 8254 { 8255 IRTemp op1 = newTemp(Ity_I64); 8256 IRTemp op2 = newTemp(Ity_I64); 8257 IRTemp result = newTemp(Ity_I64); 8258 8259 assign(op1, get_gpr_dw0(r1)); 8260 assign(op2, unop(Iop_32Sto64, get_gpr_w1(r2))); 8261 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2))); 8262 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_64, op1, op2); 8263 put_gpr_dw0(r1, mkexpr(result)); 8264 8265 return "sgfr"; 8266 } 8267 8268 static const HChar * 8269 s390_irgen_SRK(UChar r3, UChar r1, UChar r2) 8270 { 8271 IRTemp op2 = newTemp(Ity_I32); 8272 IRTemp op3 = newTemp(Ity_I32); 8273 IRTemp result = newTemp(Ity_I32); 8274 8275 assign(op2, get_gpr_w1(r2)); 8276 assign(op3, get_gpr_w1(r3)); 8277 assign(result, binop(Iop_Sub32, mkexpr(op2), mkexpr(op3))); 8278 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, op2, op3); 8279 put_gpr_w1(r1, mkexpr(result)); 8280 8281 return "srk"; 8282 } 8283 8284 static const HChar * 8285 s390_irgen_SGRK(UChar r3, UChar r1, UChar r2) 8286 { 8287 IRTemp op2 = newTemp(Ity_I64); 8288 IRTemp op3 = newTemp(Ity_I64); 8289 IRTemp result = newTemp(Ity_I64); 8290 8291 assign(op2, get_gpr_dw0(r2)); 8292 assign(op3, get_gpr_dw0(r3)); 8293 assign(result, binop(Iop_Sub64, mkexpr(op2), mkexpr(op3))); 8294 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_64, op2, op3); 8295 put_gpr_dw0(r1, mkexpr(result)); 8296 8297 return "sgrk"; 8298 } 8299 8300 static const HChar * 8301 s390_irgen_S(UChar r1, IRTemp op2addr) 8302 { 8303 IRTemp op1 = newTemp(Ity_I32); 8304 IRTemp op2 = newTemp(Ity_I32); 8305 IRTemp result = newTemp(Ity_I32); 8306 8307 assign(op1, get_gpr_w1(r1)); 8308 assign(op2, load(Ity_I32, mkexpr(op2addr))); 8309 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2))); 8310 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, op1, op2); 8311 put_gpr_w1(r1, mkexpr(result)); 8312 8313 return "s"; 8314 } 8315 8316 static const HChar * 8317 s390_irgen_SY(UChar r1, IRTemp op2addr) 8318 { 8319 IRTemp op1 = newTemp(Ity_I32); 8320 IRTemp op2 = newTemp(Ity_I32); 8321 IRTemp result = newTemp(Ity_I32); 8322 8323 assign(op1, get_gpr_w1(r1)); 8324 assign(op2, load(Ity_I32, mkexpr(op2addr))); 8325 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2))); 8326 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, op1, op2); 8327 put_gpr_w1(r1, mkexpr(result)); 8328 8329 return "sy"; 8330 } 8331 8332 static const HChar * 8333 s390_irgen_SG(UChar r1, IRTemp op2addr) 8334 { 8335 IRTemp op1 = newTemp(Ity_I64); 8336 IRTemp op2 = newTemp(Ity_I64); 8337 IRTemp result = newTemp(Ity_I64); 8338 8339 assign(op1, get_gpr_dw0(r1)); 8340 assign(op2, load(Ity_I64, mkexpr(op2addr))); 8341 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2))); 8342 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_64, op1, op2); 8343 put_gpr_dw0(r1, mkexpr(result)); 8344 8345 return "sg"; 8346 } 8347 8348 static const HChar * 8349 s390_irgen_SGF(UChar r1, IRTemp op2addr) 8350 { 8351 IRTemp op1 = newTemp(Ity_I64); 8352 IRTemp op2 = newTemp(Ity_I64); 8353 IRTemp result = newTemp(Ity_I64); 8354 8355 assign(op1, get_gpr_dw0(r1)); 8356 assign(op2, unop(Iop_32Sto64, load(Ity_I32, mkexpr(op2addr)))); 8357 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2))); 8358 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_64, op1, op2); 8359 put_gpr_dw0(r1, mkexpr(result)); 8360 8361 return "sgf"; 8362 } 8363 8364 static const HChar * 8365 s390_irgen_SH(UChar r1, IRTemp op2addr) 8366 { 8367 IRTemp op1 = newTemp(Ity_I32); 8368 IRTemp op2 = newTemp(Ity_I32); 8369 IRTemp result = newTemp(Ity_I32); 8370 8371 assign(op1, get_gpr_w1(r1)); 8372 assign(op2, unop(Iop_16Sto32, load(Ity_I16, mkexpr(op2addr)))); 8373 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2))); 8374 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, op1, op2); 8375 put_gpr_w1(r1, mkexpr(result)); 8376 8377 return "sh"; 8378 } 8379 8380 static const HChar * 8381 s390_irgen_SHY(UChar r1, IRTemp op2addr) 8382 { 8383 IRTemp op1 = newTemp(Ity_I32); 8384 IRTemp op2 = newTemp(Ity_I32); 8385 IRTemp result = newTemp(Ity_I32); 8386 8387 assign(op1, get_gpr_w1(r1)); 8388 assign(op2, unop(Iop_16Sto32, load(Ity_I16, mkexpr(op2addr)))); 8389 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2))); 8390 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, op1, op2); 8391 put_gpr_w1(r1, mkexpr(result)); 8392 8393 return "shy"; 8394 } 8395 8396 static const HChar * 8397 s390_irgen_SHHHR(UChar r3 __attribute__((unused)), UChar r1, UChar r2) 8398 { 8399 IRTemp op2 = newTemp(Ity_I32); 8400 IRTemp op3 = newTemp(Ity_I32); 8401 IRTemp result = newTemp(Ity_I32); 8402 8403 assign(op2, get_gpr_w0(r1)); 8404 assign(op3, get_gpr_w0(r2)); 8405 assign(result, binop(Iop_Sub32, mkexpr(op2), mkexpr(op3))); 8406 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, op2, op3); 8407 put_gpr_w0(r1, mkexpr(result)); 8408 8409 return "shhhr"; 8410 } 8411 8412 static const HChar * 8413 s390_irgen_SHHLR(UChar r3 __attribute__((unused)), UChar r1, UChar r2) 8414 { 8415 IRTemp op2 = newTemp(Ity_I32); 8416 IRTemp op3 = newTemp(Ity_I32); 8417 IRTemp result = newTemp(Ity_I32); 8418 8419 assign(op2, get_gpr_w0(r1)); 8420 assign(op3, get_gpr_w1(r2)); 8421 assign(result, binop(Iop_Sub32, mkexpr(op2), mkexpr(op3))); 8422 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, op2, op3); 8423 put_gpr_w0(r1, mkexpr(result)); 8424 8425 return "shhlr"; 8426 } 8427 8428 static const HChar * 8429 s390_irgen_SLR(UChar r1, UChar r2) 8430 { 8431 IRTemp op1 = newTemp(Ity_I32); 8432 IRTemp op2 = newTemp(Ity_I32); 8433 IRTemp result = newTemp(Ity_I32); 8434 8435 assign(op1, get_gpr_w1(r1)); 8436 assign(op2, get_gpr_w1(r2)); 8437 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2))); 8438 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_32, op1, op2); 8439 put_gpr_w1(r1, mkexpr(result)); 8440 8441 return "slr"; 8442 } 8443 8444 static const HChar * 8445 s390_irgen_SLGR(UChar r1, UChar r2) 8446 { 8447 IRTemp op1 = newTemp(Ity_I64); 8448 IRTemp op2 = newTemp(Ity_I64); 8449 IRTemp result = newTemp(Ity_I64); 8450 8451 assign(op1, get_gpr_dw0(r1)); 8452 assign(op2, get_gpr_dw0(r2)); 8453 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2))); 8454 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_64, op1, op2); 8455 put_gpr_dw0(r1, mkexpr(result)); 8456 8457 return "slgr"; 8458 } 8459 8460 static const HChar * 8461 s390_irgen_SLGFR(UChar r1, UChar r2) 8462 { 8463 IRTemp op1 = newTemp(Ity_I64); 8464 IRTemp op2 = newTemp(Ity_I64); 8465 IRTemp result = newTemp(Ity_I64); 8466 8467 assign(op1, get_gpr_dw0(r1)); 8468 assign(op2, unop(Iop_32Uto64, get_gpr_w1(r2))); 8469 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2))); 8470 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_64, op1, op2); 8471 put_gpr_dw0(r1, mkexpr(result)); 8472 8473 return "slgfr"; 8474 } 8475 8476 static const HChar * 8477 s390_irgen_SLRK(UChar r3, UChar r1, UChar r2) 8478 { 8479 IRTemp op2 = newTemp(Ity_I32); 8480 IRTemp op3 = newTemp(Ity_I32); 8481 IRTemp result = newTemp(Ity_I32); 8482 8483 assign(op2, get_gpr_w1(r2)); 8484 assign(op3, get_gpr_w1(r3)); 8485 assign(result, binop(Iop_Sub32, mkexpr(op2), mkexpr(op3))); 8486 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_32, op2, op3); 8487 put_gpr_w1(r1, mkexpr(result)); 8488 8489 return "slrk"; 8490 } 8491 8492 static const HChar * 8493 s390_irgen_SLGRK(UChar r3, UChar r1, UChar r2) 8494 { 8495 IRTemp op2 = newTemp(Ity_I64); 8496 IRTemp op3 = newTemp(Ity_I64); 8497 IRTemp result = newTemp(Ity_I64); 8498 8499 assign(op2, get_gpr_dw0(r2)); 8500 assign(op3, get_gpr_dw0(r3)); 8501 assign(result, binop(Iop_Sub64, mkexpr(op2), mkexpr(op3))); 8502 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_64, op2, op3); 8503 put_gpr_dw0(r1, mkexpr(result)); 8504 8505 return "slgrk"; 8506 } 8507 8508 static const HChar * 8509 s390_irgen_SL(UChar r1, IRTemp op2addr) 8510 { 8511 IRTemp op1 = newTemp(Ity_I32); 8512 IRTemp op2 = newTemp(Ity_I32); 8513 IRTemp result = newTemp(Ity_I32); 8514 8515 assign(op1, get_gpr_w1(r1)); 8516 assign(op2, load(Ity_I32, mkexpr(op2addr))); 8517 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2))); 8518 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_32, op1, op2); 8519 put_gpr_w1(r1, mkexpr(result)); 8520 8521 return "sl"; 8522 } 8523 8524 static const HChar * 8525 s390_irgen_SLY(UChar r1, IRTemp op2addr) 8526 { 8527 IRTemp op1 = newTemp(Ity_I32); 8528 IRTemp op2 = newTemp(Ity_I32); 8529 IRTemp result = newTemp(Ity_I32); 8530 8531 assign(op1, get_gpr_w1(r1)); 8532 assign(op2, load(Ity_I32, mkexpr(op2addr))); 8533 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2))); 8534 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_32, op1, op2); 8535 put_gpr_w1(r1, mkexpr(result)); 8536 8537 return "sly"; 8538 } 8539 8540 static const HChar * 8541 s390_irgen_SLG(UChar r1, IRTemp op2addr) 8542 { 8543 IRTemp op1 = newTemp(Ity_I64); 8544 IRTemp op2 = newTemp(Ity_I64); 8545 IRTemp result = newTemp(Ity_I64); 8546 8547 assign(op1, get_gpr_dw0(r1)); 8548 assign(op2, load(Ity_I64, mkexpr(op2addr))); 8549 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2))); 8550 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_64, op1, op2); 8551 put_gpr_dw0(r1, mkexpr(result)); 8552 8553 return "slg"; 8554 } 8555 8556 static const HChar * 8557 s390_irgen_SLGF(UChar r1, IRTemp op2addr) 8558 { 8559 IRTemp op1 = newTemp(Ity_I64); 8560 IRTemp op2 = newTemp(Ity_I64); 8561 IRTemp result = newTemp(Ity_I64); 8562 8563 assign(op1, get_gpr_dw0(r1)); 8564 assign(op2, unop(Iop_32Uto64, load(Ity_I32, mkexpr(op2addr)))); 8565 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2))); 8566 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_64, op1, op2); 8567 put_gpr_dw0(r1, mkexpr(result)); 8568 8569 return "slgf"; 8570 } 8571 8572 static const HChar * 8573 s390_irgen_SLFI(UChar r1, UInt i2) 8574 { 8575 IRTemp op1 = newTemp(Ity_I32); 8576 UInt op2; 8577 IRTemp result = newTemp(Ity_I32); 8578 8579 assign(op1, get_gpr_w1(r1)); 8580 op2 = i2; 8581 assign(result, binop(Iop_Sub32, mkexpr(op1), mkU32(op2))); 8582 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_32, op1, mktemp(Ity_I32, 8583 mkU32(op2))); 8584 put_gpr_w1(r1, mkexpr(result)); 8585 8586 return "slfi"; 8587 } 8588 8589 static const HChar * 8590 s390_irgen_SLGFI(UChar r1, UInt i2) 8591 { 8592 IRTemp op1 = newTemp(Ity_I64); 8593 ULong op2; 8594 IRTemp result = newTemp(Ity_I64); 8595 8596 assign(op1, get_gpr_dw0(r1)); 8597 op2 = (ULong)i2; 8598 assign(result, binop(Iop_Sub64, mkexpr(op1), mkU64(op2))); 8599 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_64, op1, mktemp(Ity_I64, 8600 mkU64(op2))); 8601 put_gpr_dw0(r1, mkexpr(result)); 8602 8603 return "slgfi"; 8604 } 8605 8606 static const HChar * 8607 s390_irgen_SLHHHR(UChar r3 __attribute__((unused)), UChar r1, UChar r2) 8608 { 8609 IRTemp op2 = newTemp(Ity_I32); 8610 IRTemp op3 = newTemp(Ity_I32); 8611 IRTemp result = newTemp(Ity_I32); 8612 8613 assign(op2, get_gpr_w0(r1)); 8614 assign(op3, get_gpr_w0(r2)); 8615 assign(result, binop(Iop_Sub32, mkexpr(op2), mkexpr(op3))); 8616 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_32, op2, op3); 8617 put_gpr_w0(r1, mkexpr(result)); 8618 8619 return "slhhhr"; 8620 } 8621 8622 static const HChar * 8623 s390_irgen_SLHHLR(UChar r3 __attribute__((unused)), UChar r1, UChar r2) 8624 { 8625 IRTemp op2 = newTemp(Ity_I32); 8626 IRTemp op3 = newTemp(Ity_I32); 8627 IRTemp result = newTemp(Ity_I32); 8628 8629 assign(op2, get_gpr_w0(r1)); 8630 assign(op3, get_gpr_w1(r2)); 8631 assign(result, binop(Iop_Sub32, mkexpr(op2), mkexpr(op3))); 8632 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_32, op2, op3); 8633 put_gpr_w0(r1, mkexpr(result)); 8634 8635 return "slhhlr"; 8636 } 8637 8638 static const HChar * 8639 s390_irgen_SLBR(UChar r1, UChar r2) 8640 { 8641 IRTemp op1 = newTemp(Ity_I32); 8642 IRTemp op2 = newTemp(Ity_I32); 8643 IRTemp result = newTemp(Ity_I32); 8644 IRTemp borrow_in = newTemp(Ity_I32); 8645 8646 assign(op1, get_gpr_w1(r1)); 8647 assign(op2, get_gpr_w1(r2)); 8648 assign(borrow_in, binop(Iop_Sub32, mkU32(1), binop(Iop_Shr32, 8649 s390_call_calculate_cc(), mkU8(1)))); 8650 assign(result, binop(Iop_Sub32, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2)), 8651 mkexpr(borrow_in))); 8652 s390_cc_thunk_putZZZ(S390_CC_OP_UNSIGNED_SUBB_32, op1, op2, borrow_in); 8653 put_gpr_w1(r1, mkexpr(result)); 8654 8655 return "slbr"; 8656 } 8657 8658 static const HChar * 8659 s390_irgen_SLBGR(UChar r1, UChar r2) 8660 { 8661 IRTemp op1 = newTemp(Ity_I64); 8662 IRTemp op2 = newTemp(Ity_I64); 8663 IRTemp result = newTemp(Ity_I64); 8664 IRTemp borrow_in = newTemp(Ity_I64); 8665 8666 assign(op1, get_gpr_dw0(r1)); 8667 assign(op2, get_gpr_dw0(r2)); 8668 assign(borrow_in, unop(Iop_32Uto64, binop(Iop_Sub32, mkU32(1), 8669 binop(Iop_Shr32, s390_call_calculate_cc(), mkU8(1))))); 8670 assign(result, binop(Iop_Sub64, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2)), 8671 mkexpr(borrow_in))); 8672 s390_cc_thunk_putZZZ(S390_CC_OP_UNSIGNED_SUBB_64, op1, op2, borrow_in); 8673 put_gpr_dw0(r1, mkexpr(result)); 8674 8675 return "slbgr"; 8676 } 8677 8678 static const HChar * 8679 s390_irgen_SLB(UChar r1, IRTemp op2addr) 8680 { 8681 IRTemp op1 = newTemp(Ity_I32); 8682 IRTemp op2 = newTemp(Ity_I32); 8683 IRTemp result = newTemp(Ity_I32); 8684 IRTemp borrow_in = newTemp(Ity_I32); 8685 8686 assign(op1, get_gpr_w1(r1)); 8687 assign(op2, load(Ity_I32, mkexpr(op2addr))); 8688 assign(borrow_in, binop(Iop_Sub32, mkU32(1), binop(Iop_Shr32, 8689 s390_call_calculate_cc(), mkU8(1)))); 8690 assign(result, binop(Iop_Sub32, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2)), 8691 mkexpr(borrow_in))); 8692 s390_cc_thunk_putZZZ(S390_CC_OP_UNSIGNED_SUBB_32, op1, op2, borrow_in); 8693 put_gpr_w1(r1, mkexpr(result)); 8694 8695 return "slb"; 8696 } 8697 8698 static const HChar * 8699 s390_irgen_SLBG(UChar r1, IRTemp op2addr) 8700 { 8701 IRTemp op1 = newTemp(Ity_I64); 8702 IRTemp op2 = newTemp(Ity_I64); 8703 IRTemp result = newTemp(Ity_I64); 8704 IRTemp borrow_in = newTemp(Ity_I64); 8705 8706 assign(op1, get_gpr_dw0(r1)); 8707 assign(op2, load(Ity_I64, mkexpr(op2addr))); 8708 assign(borrow_in, unop(Iop_32Uto64, binop(Iop_Sub32, mkU32(1), 8709 binop(Iop_Shr32, s390_call_calculate_cc(), mkU8(1))))); 8710 assign(result, binop(Iop_Sub64, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2)), 8711 mkexpr(borrow_in))); 8712 s390_cc_thunk_putZZZ(S390_CC_OP_UNSIGNED_SUBB_64, op1, op2, borrow_in); 8713 put_gpr_dw0(r1, mkexpr(result)); 8714 8715 return "slbg"; 8716 } 8717 8718 static const HChar * 8719 s390_irgen_SVC(UChar i) 8720 { 8721 IRTemp sysno = newTemp(Ity_I64); 8722 8723 if (i != 0) { 8724 assign(sysno, mkU64(i)); 8725 } else { 8726 assign(sysno, unop(Iop_32Uto64, get_gpr_w1(1))); 8727 } 8728 system_call(mkexpr(sysno)); 8729 8730 return "svc"; 8731 } 8732 8733 static const HChar * 8734 s390_irgen_TM(UChar i2, IRTemp op1addr) 8735 { 8736 UChar mask; 8737 IRTemp value = newTemp(Ity_I8); 8738 8739 mask = i2; 8740 assign(value, load(Ity_I8, mkexpr(op1addr))); 8741 s390_cc_thunk_putZZ(S390_CC_OP_TEST_UNDER_MASK_8, value, mktemp(Ity_I8, 8742 mkU8(mask))); 8743 8744 return "tm"; 8745 } 8746 8747 static const HChar * 8748 s390_irgen_TMY(UChar i2, IRTemp op1addr) 8749 { 8750 UChar mask; 8751 IRTemp value = newTemp(Ity_I8); 8752 8753 mask = i2; 8754 assign(value, load(Ity_I8, mkexpr(op1addr))); 8755 s390_cc_thunk_putZZ(S390_CC_OP_TEST_UNDER_MASK_8, value, mktemp(Ity_I8, 8756 mkU8(mask))); 8757 8758 return "tmy"; 8759 } 8760 8761 static const HChar * 8762 s390_irgen_TMHH(UChar r1, UShort i2) 8763 { 8764 UShort mask; 8765 IRTemp value = newTemp(Ity_I16); 8766 8767 mask = i2; 8768 assign(value, get_gpr_hw0(r1)); 8769 s390_cc_thunk_putZZ(S390_CC_OP_TEST_UNDER_MASK_16, value, mktemp(Ity_I16, 8770 mkU16(mask))); 8771 8772 return "tmhh"; 8773 } 8774 8775 static const HChar * 8776 s390_irgen_TMHL(UChar r1, UShort i2) 8777 { 8778 UShort mask; 8779 IRTemp value = newTemp(Ity_I16); 8780 8781 mask = i2; 8782 assign(value, get_gpr_hw1(r1)); 8783 s390_cc_thunk_putZZ(S390_CC_OP_TEST_UNDER_MASK_16, value, mktemp(Ity_I16, 8784 mkU16(mask))); 8785 8786 return "tmhl"; 8787 } 8788 8789 static const HChar * 8790 s390_irgen_TMLH(UChar r1, UShort i2) 8791 { 8792 UShort mask; 8793 IRTemp value = newTemp(Ity_I16); 8794 8795 mask = i2; 8796 assign(value, get_gpr_hw2(r1)); 8797 s390_cc_thunk_putZZ(S390_CC_OP_TEST_UNDER_MASK_16, value, mktemp(Ity_I16, 8798 mkU16(mask))); 8799 8800 return "tmlh"; 8801 } 8802 8803 static const HChar * 8804 s390_irgen_TMLL(UChar r1, UShort i2) 8805 { 8806 UShort mask; 8807 IRTemp value = newTemp(Ity_I16); 8808 8809 mask = i2; 8810 assign(value, get_gpr_hw3(r1)); 8811 s390_cc_thunk_putZZ(S390_CC_OP_TEST_UNDER_MASK_16, value, mktemp(Ity_I16, 8812 mkU16(mask))); 8813 8814 return "tmll"; 8815 } 8816 8817 static const HChar * 8818 s390_irgen_EFPC(UChar r1) 8819 { 8820 put_gpr_w1(r1, get_fpc_w0()); 8821 8822 return "efpc"; 8823 } 8824 8825 static const HChar * 8826 s390_irgen_LER(UChar r1, UChar r2) 8827 { 8828 put_fpr_w0(r1, get_fpr_w0(r2)); 8829 8830 return "ler"; 8831 } 8832 8833 static const HChar * 8834 s390_irgen_LDR(UChar r1, UChar r2) 8835 { 8836 put_fpr_dw0(r1, get_fpr_dw0(r2)); 8837 8838 return "ldr"; 8839 } 8840 8841 static const HChar * 8842 s390_irgen_LDER(UChar r1, UChar r2) 8843 { 8844 put_fpr_dw0(r1, mkF64i(0x0)); 8845 put_fpr_w0(r1, get_fpr_w0(r2)); 8846 8847 return "lder"; 8848 } 8849 8850 static const HChar * 8851 s390_irgen_LXR(UChar r1, UChar r2) 8852 { 8853 put_fpr_dw0(r1, get_fpr_dw0(r2)); 8854 put_fpr_dw0(r1 + 2, get_fpr_dw0(r2 + 2)); 8855 8856 return "lxr"; 8857 } 8858 8859 static const HChar * 8860 s390_irgen_LE(UChar r1, IRTemp op2addr) 8861 { 8862 put_fpr_w0(r1, load(Ity_F32, mkexpr(op2addr))); 8863 8864 return "le"; 8865 } 8866 8867 static const HChar * 8868 s390_irgen_LD(UChar r1, IRTemp op2addr) 8869 { 8870 put_fpr_dw0(r1, load(Ity_F64, mkexpr(op2addr))); 8871 8872 return "ld"; 8873 } 8874 8875 static const HChar * 8876 s390_irgen_LDE(UChar r1, IRTemp op2addr) 8877 { 8878 put_fpr_dw0(r1, mkF64i(0x0)); 8879 put_fpr_w0(r1, load(Ity_F32, mkexpr(op2addr))); 8880 8881 return "lde"; 8882 } 8883 8884 static const HChar * 8885 s390_irgen_LEY(UChar r1, IRTemp op2addr) 8886 { 8887 put_fpr_w0(r1, load(Ity_F32, mkexpr(op2addr))); 8888 8889 return "ley"; 8890 } 8891 8892 static const HChar * 8893 s390_irgen_LDY(UChar r1, IRTemp op2addr) 8894 { 8895 put_fpr_dw0(r1, load(Ity_F64, mkexpr(op2addr))); 8896 8897 return "ldy"; 8898 } 8899 8900 static const HChar * 8901 s390_irgen_LFPC(IRTemp op2addr) 8902 { 8903 put_fpc_w0(load(Ity_I32, mkexpr(op2addr))); 8904 8905 return "lfpc"; 8906 } 8907 8908 static const HChar * 8909 s390_irgen_LZER(UChar r1) 8910 { 8911 put_fpr_w0(r1, mkF32i(0x0)); 8912 8913 return "lzer"; 8914 } 8915 8916 static const HChar * 8917 s390_irgen_LZDR(UChar r1) 8918 { 8919 put_fpr_dw0(r1, mkF64i(0x0)); 8920 8921 return "lzdr"; 8922 } 8923 8924 static const HChar * 8925 s390_irgen_LZXR(UChar r1) 8926 { 8927 put_fpr_dw0(r1, mkF64i(0x0)); 8928 put_fpr_dw0(r1 + 2, mkF64i(0x0)); 8929 8930 return "lzxr"; 8931 } 8932 8933 static const HChar * 8934 s390_irgen_SRNM(IRTemp op2addr) 8935 { 8936 UInt input_mask, fpc_mask; 8937 8938 input_mask = 3; 8939 fpc_mask = s390_host_has_fpext ? 7 : 3; 8940 8941 put_fpc_w0(binop(Iop_Or32, 8942 binop(Iop_And32, get_fpc_w0(), mkU32(~fpc_mask)), 8943 binop(Iop_And32, unop(Iop_64to32, mkexpr(op2addr)), 8944 mkU32(input_mask)))); 8945 return "srnm"; 8946 } 8947 8948 static const HChar * 8949 s390_irgen_SRNMB(IRTemp op2addr) 8950 { 8951 UInt input_mask, fpc_mask; 8952 8953 input_mask = 7; 8954 fpc_mask = 7; 8955 8956 put_fpc_w0(binop(Iop_Or32, 8957 binop(Iop_And32, get_fpc_w0(), mkU32(~fpc_mask)), 8958 binop(Iop_And32, unop(Iop_64to32, mkexpr(op2addr)), 8959 mkU32(input_mask)))); 8960 return "srnmb"; 8961 } 8962 8963 static void 8964 s390_irgen_srnmb_wrapper(UChar b2, UShort d2) 8965 { 8966 if (b2 == 0) { /* This is the typical case */ 8967 if (d2 > 3) { 8968 if (s390_host_has_fpext && d2 == 7) { 8969 /* ok */ 8970 } else { 8971 emulation_warning(EmWarn_S390X_invalid_rounding); 8972 d2 = S390_FPC_BFP_ROUND_NEAREST_EVEN; 8973 } 8974 } 8975 } 8976 8977 s390_format_S_RD(s390_irgen_SRNMB, b2, d2); 8978 } 8979 8980 /* Wrapper to validate the parameter as in SRNMB is not required, as all 8981 the 8 values in op2addr[61:63] correspond to a valid DFP rounding mode */ 8982 static const HChar * 8983 s390_irgen_SRNMT(IRTemp op2addr) 8984 { 8985 UInt input_mask, fpc_mask; 8986 8987 input_mask = 7; 8988 fpc_mask = 0x70; 8989 8990 /* fpc[25:27] <- op2addr[61:63] 8991 fpc = (fpc & ~(0x70)) | ((op2addr & 7) << 4) */ 8992 put_fpc_w0(binop(Iop_Or32, binop(Iop_And32, get_fpc_w0(), mkU32(~fpc_mask)), 8993 binop(Iop_Shl32, binop(Iop_And32, 8994 unop(Iop_64to32, mkexpr(op2addr)), 8995 mkU32(input_mask)), mkU8(4)))); 8996 return "srnmt"; 8997 } 8998 8999 9000 static const HChar * 9001 s390_irgen_SFPC(UChar r1) 9002 { 9003 put_fpc_w0(get_gpr_w1(r1)); 9004 9005 return "sfpc"; 9006 } 9007 9008 static const HChar * 9009 s390_irgen_STE(UChar r1, IRTemp op2addr) 9010 { 9011 store(mkexpr(op2addr), get_fpr_w0(r1)); 9012 9013 return "ste"; 9014 } 9015 9016 static const HChar * 9017 s390_irgen_STD(UChar r1, IRTemp op2addr) 9018 { 9019 store(mkexpr(op2addr), get_fpr_dw0(r1)); 9020 9021 return "std"; 9022 } 9023 9024 static const HChar * 9025 s390_irgen_STEY(UChar r1, IRTemp op2addr) 9026 { 9027 store(mkexpr(op2addr), get_fpr_w0(r1)); 9028 9029 return "stey"; 9030 } 9031 9032 static const HChar * 9033 s390_irgen_STDY(UChar r1, IRTemp op2addr) 9034 { 9035 store(mkexpr(op2addr), get_fpr_dw0(r1)); 9036 9037 return "stdy"; 9038 } 9039 9040 static const HChar * 9041 s390_irgen_STFPC(IRTemp op2addr) 9042 { 9043 store(mkexpr(op2addr), get_fpc_w0()); 9044 9045 return "stfpc"; 9046 } 9047 9048 static const HChar * 9049 s390_irgen_AEBR(UChar r1, UChar r2) 9050 { 9051 IRTemp op1 = newTemp(Ity_F32); 9052 IRTemp op2 = newTemp(Ity_F32); 9053 IRTemp result = newTemp(Ity_F32); 9054 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9055 9056 assign(op1, get_fpr_w0(r1)); 9057 assign(op2, get_fpr_w0(r2)); 9058 assign(result, triop(Iop_AddF32, mkexpr(rounding_mode), mkexpr(op1), 9059 mkexpr(op2))); 9060 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_32, result); 9061 put_fpr_w0(r1, mkexpr(result)); 9062 9063 return "aebr"; 9064 } 9065 9066 static const HChar * 9067 s390_irgen_ADBR(UChar r1, UChar r2) 9068 { 9069 IRTemp op1 = newTemp(Ity_F64); 9070 IRTemp op2 = newTemp(Ity_F64); 9071 IRTemp result = newTemp(Ity_F64); 9072 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9073 9074 assign(op1, get_fpr_dw0(r1)); 9075 assign(op2, get_fpr_dw0(r2)); 9076 assign(result, triop(Iop_AddF64, mkexpr(rounding_mode), mkexpr(op1), 9077 mkexpr(op2))); 9078 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_64, result); 9079 put_fpr_dw0(r1, mkexpr(result)); 9080 9081 return "adbr"; 9082 } 9083 9084 static const HChar * 9085 s390_irgen_AEB(UChar r1, IRTemp op2addr) 9086 { 9087 IRTemp op1 = newTemp(Ity_F32); 9088 IRTemp op2 = newTemp(Ity_F32); 9089 IRTemp result = newTemp(Ity_F32); 9090 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9091 9092 assign(op1, get_fpr_w0(r1)); 9093 assign(op2, load(Ity_F32, mkexpr(op2addr))); 9094 assign(result, triop(Iop_AddF32, mkexpr(rounding_mode), mkexpr(op1), 9095 mkexpr(op2))); 9096 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_32, result); 9097 put_fpr_w0(r1, mkexpr(result)); 9098 9099 return "aeb"; 9100 } 9101 9102 static const HChar * 9103 s390_irgen_ADB(UChar r1, IRTemp op2addr) 9104 { 9105 IRTemp op1 = newTemp(Ity_F64); 9106 IRTemp op2 = newTemp(Ity_F64); 9107 IRTemp result = newTemp(Ity_F64); 9108 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9109 9110 assign(op1, get_fpr_dw0(r1)); 9111 assign(op2, load(Ity_F64, mkexpr(op2addr))); 9112 assign(result, triop(Iop_AddF64, mkexpr(rounding_mode), mkexpr(op1), 9113 mkexpr(op2))); 9114 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_64, result); 9115 put_fpr_dw0(r1, mkexpr(result)); 9116 9117 return "adb"; 9118 } 9119 9120 static const HChar * 9121 s390_irgen_CEFBR(UChar m3, UChar m4 __attribute__((unused)), 9122 UChar r1, UChar r2) 9123 { 9124 if (! s390_host_has_fpext && m3 != S390_BFP_ROUND_PER_FPC) { 9125 emulation_warning(EmWarn_S390X_fpext_rounding); 9126 m3 = S390_BFP_ROUND_PER_FPC; 9127 } 9128 IRTemp op2 = newTemp(Ity_I32); 9129 9130 assign(op2, get_gpr_w1(r2)); 9131 put_fpr_w0(r1, binop(Iop_I32StoF32, mkexpr(encode_bfp_rounding_mode(m3)), 9132 mkexpr(op2))); 9133 9134 return "cefbr"; 9135 } 9136 9137 static const HChar * 9138 s390_irgen_CDFBR(UChar m3 __attribute__((unused)), 9139 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 9140 { 9141 IRTemp op2 = newTemp(Ity_I32); 9142 9143 assign(op2, get_gpr_w1(r2)); 9144 put_fpr_dw0(r1, unop(Iop_I32StoF64, mkexpr(op2))); 9145 9146 return "cdfbr"; 9147 } 9148 9149 static const HChar * 9150 s390_irgen_CEGBR(UChar m3, UChar m4 __attribute__((unused)), 9151 UChar r1, UChar r2) 9152 { 9153 if (! s390_host_has_fpext && m3 != S390_BFP_ROUND_PER_FPC) { 9154 emulation_warning(EmWarn_S390X_fpext_rounding); 9155 m3 = S390_BFP_ROUND_PER_FPC; 9156 } 9157 IRTemp op2 = newTemp(Ity_I64); 9158 9159 assign(op2, get_gpr_dw0(r2)); 9160 put_fpr_w0(r1, binop(Iop_I64StoF32, mkexpr(encode_bfp_rounding_mode(m3)), 9161 mkexpr(op2))); 9162 9163 return "cegbr"; 9164 } 9165 9166 static const HChar * 9167 s390_irgen_CDGBR(UChar m3, UChar m4 __attribute__((unused)), 9168 UChar r1, UChar r2) 9169 { 9170 if (! s390_host_has_fpext && m3 != S390_BFP_ROUND_PER_FPC) { 9171 emulation_warning(EmWarn_S390X_fpext_rounding); 9172 m3 = S390_BFP_ROUND_PER_FPC; 9173 } 9174 IRTemp op2 = newTemp(Ity_I64); 9175 9176 assign(op2, get_gpr_dw0(r2)); 9177 put_fpr_dw0(r1, binop(Iop_I64StoF64, mkexpr(encode_bfp_rounding_mode(m3)), 9178 mkexpr(op2))); 9179 9180 return "cdgbr"; 9181 } 9182 9183 static const HChar * 9184 s390_irgen_CELFBR(UChar m3, UChar m4 __attribute__((unused)), 9185 UChar r1, UChar r2) 9186 { 9187 if (! s390_host_has_fpext) { 9188 emulation_failure(EmFail_S390X_fpext); 9189 } else { 9190 IRTemp op2 = newTemp(Ity_I32); 9191 9192 assign(op2, get_gpr_w1(r2)); 9193 put_fpr_w0(r1, binop(Iop_I32UtoF32, mkexpr(encode_bfp_rounding_mode(m3)), 9194 mkexpr(op2))); 9195 } 9196 return "celfbr"; 9197 } 9198 9199 static const HChar * 9200 s390_irgen_CDLFBR(UChar m3 __attribute__((unused)), 9201 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 9202 { 9203 if (! s390_host_has_fpext) { 9204 emulation_failure(EmFail_S390X_fpext); 9205 } else { 9206 IRTemp op2 = newTemp(Ity_I32); 9207 9208 assign(op2, get_gpr_w1(r2)); 9209 put_fpr_dw0(r1, unop(Iop_I32UtoF64, mkexpr(op2))); 9210 } 9211 return "cdlfbr"; 9212 } 9213 9214 static const HChar * 9215 s390_irgen_CELGBR(UChar m3, UChar m4 __attribute__((unused)), 9216 UChar r1, UChar r2) 9217 { 9218 if (! s390_host_has_fpext) { 9219 emulation_failure(EmFail_S390X_fpext); 9220 } else { 9221 IRTemp op2 = newTemp(Ity_I64); 9222 9223 assign(op2, get_gpr_dw0(r2)); 9224 put_fpr_w0(r1, binop(Iop_I64UtoF32, mkexpr(encode_bfp_rounding_mode(m3)), 9225 mkexpr(op2))); 9226 } 9227 return "celgbr"; 9228 } 9229 9230 static const HChar * 9231 s390_irgen_CDLGBR(UChar m3, UChar m4 __attribute__((unused)), 9232 UChar r1, UChar r2) 9233 { 9234 if (! s390_host_has_fpext) { 9235 emulation_failure(EmFail_S390X_fpext); 9236 } else { 9237 IRTemp op2 = newTemp(Ity_I64); 9238 9239 assign(op2, get_gpr_dw0(r2)); 9240 put_fpr_dw0(r1, binop(Iop_I64UtoF64, 9241 mkexpr(encode_bfp_rounding_mode(m3)), 9242 mkexpr(op2))); 9243 } 9244 return "cdlgbr"; 9245 } 9246 9247 static const HChar * 9248 s390_irgen_CLFEBR(UChar m3, UChar m4 __attribute__((unused)), 9249 UChar r1, UChar r2) 9250 { 9251 if (! s390_host_has_fpext) { 9252 emulation_failure(EmFail_S390X_fpext); 9253 } else { 9254 IRTemp op = newTemp(Ity_F32); 9255 IRTemp result = newTemp(Ity_I32); 9256 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 9257 9258 assign(op, get_fpr_w0(r2)); 9259 assign(result, binop(Iop_F32toI32U, mkexpr(rounding_mode), 9260 mkexpr(op))); 9261 put_gpr_w1(r1, mkexpr(result)); 9262 s390_cc_thunk_putFZ(S390_CC_OP_BFP_32_TO_UINT_32, op, rounding_mode); 9263 } 9264 return "clfebr"; 9265 } 9266 9267 static const HChar * 9268 s390_irgen_CLFDBR(UChar m3, UChar m4 __attribute__((unused)), 9269 UChar r1, UChar r2) 9270 { 9271 if (! s390_host_has_fpext) { 9272 emulation_failure(EmFail_S390X_fpext); 9273 } else { 9274 IRTemp op = newTemp(Ity_F64); 9275 IRTemp result = newTemp(Ity_I32); 9276 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 9277 9278 assign(op, get_fpr_dw0(r2)); 9279 assign(result, binop(Iop_F64toI32U, mkexpr(rounding_mode), 9280 mkexpr(op))); 9281 put_gpr_w1(r1, mkexpr(result)); 9282 s390_cc_thunk_putFZ(S390_CC_OP_BFP_64_TO_UINT_32, op, rounding_mode); 9283 } 9284 return "clfdbr"; 9285 } 9286 9287 static const HChar * 9288 s390_irgen_CLGEBR(UChar m3, UChar m4 __attribute__((unused)), 9289 UChar r1, UChar r2) 9290 { 9291 if (! s390_host_has_fpext) { 9292 emulation_failure(EmFail_S390X_fpext); 9293 } else { 9294 IRTemp op = newTemp(Ity_F32); 9295 IRTemp result = newTemp(Ity_I64); 9296 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 9297 9298 assign(op, get_fpr_w0(r2)); 9299 assign(result, binop(Iop_F32toI64U, mkexpr(rounding_mode), 9300 mkexpr(op))); 9301 put_gpr_dw0(r1, mkexpr(result)); 9302 s390_cc_thunk_putFZ(S390_CC_OP_BFP_32_TO_UINT_64, op, rounding_mode); 9303 } 9304 return "clgebr"; 9305 } 9306 9307 static const HChar * 9308 s390_irgen_CLGDBR(UChar m3, UChar m4 __attribute__((unused)), 9309 UChar r1, UChar r2) 9310 { 9311 if (! s390_host_has_fpext) { 9312 emulation_failure(EmFail_S390X_fpext); 9313 } else { 9314 IRTemp op = newTemp(Ity_F64); 9315 IRTemp result = newTemp(Ity_I64); 9316 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 9317 9318 assign(op, get_fpr_dw0(r2)); 9319 assign(result, binop(Iop_F64toI64U, mkexpr(rounding_mode), 9320 mkexpr(op))); 9321 put_gpr_dw0(r1, mkexpr(result)); 9322 s390_cc_thunk_putFZ(S390_CC_OP_BFP_64_TO_UINT_64, op, rounding_mode); 9323 } 9324 return "clgdbr"; 9325 } 9326 9327 static const HChar * 9328 s390_irgen_CFEBR(UChar m3, UChar m4 __attribute__((unused)), 9329 UChar r1, UChar r2) 9330 { 9331 IRTemp op = newTemp(Ity_F32); 9332 IRTemp result = newTemp(Ity_I32); 9333 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 9334 9335 assign(op, get_fpr_w0(r2)); 9336 assign(result, binop(Iop_F32toI32S, mkexpr(rounding_mode), 9337 mkexpr(op))); 9338 put_gpr_w1(r1, mkexpr(result)); 9339 s390_cc_thunk_putFZ(S390_CC_OP_BFP_32_TO_INT_32, op, rounding_mode); 9340 9341 return "cfebr"; 9342 } 9343 9344 static const HChar * 9345 s390_irgen_CFDBR(UChar m3, UChar m4 __attribute__((unused)), 9346 UChar r1, UChar r2) 9347 { 9348 IRTemp op = newTemp(Ity_F64); 9349 IRTemp result = newTemp(Ity_I32); 9350 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 9351 9352 assign(op, get_fpr_dw0(r2)); 9353 assign(result, binop(Iop_F64toI32S, mkexpr(rounding_mode), 9354 mkexpr(op))); 9355 put_gpr_w1(r1, mkexpr(result)); 9356 s390_cc_thunk_putFZ(S390_CC_OP_BFP_64_TO_INT_32, op, rounding_mode); 9357 9358 return "cfdbr"; 9359 } 9360 9361 static const HChar * 9362 s390_irgen_CGEBR(UChar m3, UChar m4 __attribute__((unused)), 9363 UChar r1, UChar r2) 9364 { 9365 IRTemp op = newTemp(Ity_F32); 9366 IRTemp result = newTemp(Ity_I64); 9367 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 9368 9369 assign(op, get_fpr_w0(r2)); 9370 assign(result, binop(Iop_F32toI64S, mkexpr(rounding_mode), 9371 mkexpr(op))); 9372 put_gpr_dw0(r1, mkexpr(result)); 9373 s390_cc_thunk_putFZ(S390_CC_OP_BFP_32_TO_INT_64, op, rounding_mode); 9374 9375 return "cgebr"; 9376 } 9377 9378 static const HChar * 9379 s390_irgen_CGDBR(UChar m3, UChar m4 __attribute__((unused)), 9380 UChar r1, UChar r2) 9381 { 9382 IRTemp op = newTemp(Ity_F64); 9383 IRTemp result = newTemp(Ity_I64); 9384 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 9385 9386 assign(op, get_fpr_dw0(r2)); 9387 assign(result, binop(Iop_F64toI64S, mkexpr(rounding_mode), 9388 mkexpr(op))); 9389 put_gpr_dw0(r1, mkexpr(result)); 9390 s390_cc_thunk_putFZ(S390_CC_OP_BFP_64_TO_INT_64, op, rounding_mode); 9391 9392 return "cgdbr"; 9393 } 9394 9395 static const HChar * 9396 s390_irgen_DEBR(UChar r1, UChar r2) 9397 { 9398 IRTemp op1 = newTemp(Ity_F32); 9399 IRTemp op2 = newTemp(Ity_F32); 9400 IRTemp result = newTemp(Ity_F32); 9401 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9402 9403 assign(op1, get_fpr_w0(r1)); 9404 assign(op2, get_fpr_w0(r2)); 9405 assign(result, triop(Iop_DivF32, mkexpr(rounding_mode), mkexpr(op1), 9406 mkexpr(op2))); 9407 put_fpr_w0(r1, mkexpr(result)); 9408 9409 return "debr"; 9410 } 9411 9412 static const HChar * 9413 s390_irgen_DDBR(UChar r1, UChar r2) 9414 { 9415 IRTemp op1 = newTemp(Ity_F64); 9416 IRTemp op2 = newTemp(Ity_F64); 9417 IRTemp result = newTemp(Ity_F64); 9418 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9419 9420 assign(op1, get_fpr_dw0(r1)); 9421 assign(op2, get_fpr_dw0(r2)); 9422 assign(result, triop(Iop_DivF64, mkexpr(rounding_mode), mkexpr(op1), 9423 mkexpr(op2))); 9424 put_fpr_dw0(r1, mkexpr(result)); 9425 9426 return "ddbr"; 9427 } 9428 9429 static const HChar * 9430 s390_irgen_DEB(UChar r1, IRTemp op2addr) 9431 { 9432 IRTemp op1 = newTemp(Ity_F32); 9433 IRTemp op2 = newTemp(Ity_F32); 9434 IRTemp result = newTemp(Ity_F32); 9435 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9436 9437 assign(op1, get_fpr_w0(r1)); 9438 assign(op2, load(Ity_F32, mkexpr(op2addr))); 9439 assign(result, triop(Iop_DivF32, mkexpr(rounding_mode), mkexpr(op1), 9440 mkexpr(op2))); 9441 put_fpr_w0(r1, mkexpr(result)); 9442 9443 return "deb"; 9444 } 9445 9446 static const HChar * 9447 s390_irgen_DDB(UChar r1, IRTemp op2addr) 9448 { 9449 IRTemp op1 = newTemp(Ity_F64); 9450 IRTemp op2 = newTemp(Ity_F64); 9451 IRTemp result = newTemp(Ity_F64); 9452 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9453 9454 assign(op1, get_fpr_dw0(r1)); 9455 assign(op2, load(Ity_F64, mkexpr(op2addr))); 9456 assign(result, triop(Iop_DivF64, mkexpr(rounding_mode), mkexpr(op1), 9457 mkexpr(op2))); 9458 put_fpr_dw0(r1, mkexpr(result)); 9459 9460 return "ddb"; 9461 } 9462 9463 static const HChar * 9464 s390_irgen_LTEBR(UChar r1, UChar r2) 9465 { 9466 IRTemp result = newTemp(Ity_F32); 9467 9468 assign(result, get_fpr_w0(r2)); 9469 put_fpr_w0(r1, mkexpr(result)); 9470 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_32, result); 9471 9472 return "ltebr"; 9473 } 9474 9475 static const HChar * 9476 s390_irgen_LTDBR(UChar r1, UChar r2) 9477 { 9478 IRTemp result = newTemp(Ity_F64); 9479 9480 assign(result, get_fpr_dw0(r2)); 9481 put_fpr_dw0(r1, mkexpr(result)); 9482 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_64, result); 9483 9484 return "ltdbr"; 9485 } 9486 9487 static const HChar * 9488 s390_irgen_LCEBR(UChar r1, UChar r2) 9489 { 9490 IRTemp result = newTemp(Ity_F32); 9491 9492 assign(result, unop(Iop_NegF32, get_fpr_w0(r2))); 9493 put_fpr_w0(r1, mkexpr(result)); 9494 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_32, result); 9495 9496 return "lcebr"; 9497 } 9498 9499 static const HChar * 9500 s390_irgen_LCDBR(UChar r1, UChar r2) 9501 { 9502 IRTemp result = newTemp(Ity_F64); 9503 9504 assign(result, unop(Iop_NegF64, get_fpr_dw0(r2))); 9505 put_fpr_dw0(r1, mkexpr(result)); 9506 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_64, result); 9507 9508 return "lcdbr"; 9509 } 9510 9511 static const HChar * 9512 s390_irgen_LDEBR(UChar r1, UChar r2) 9513 { 9514 IRTemp op = newTemp(Ity_F32); 9515 9516 assign(op, get_fpr_w0(r2)); 9517 put_fpr_dw0(r1, unop(Iop_F32toF64, mkexpr(op))); 9518 9519 return "ldebr"; 9520 } 9521 9522 static const HChar * 9523 s390_irgen_LDEB(UChar r1, IRTemp op2addr) 9524 { 9525 IRTemp op = newTemp(Ity_F32); 9526 9527 assign(op, load(Ity_F32, mkexpr(op2addr))); 9528 put_fpr_dw0(r1, unop(Iop_F32toF64, mkexpr(op))); 9529 9530 return "ldeb"; 9531 } 9532 9533 static const HChar * 9534 s390_irgen_LEDBR(UChar m3, UChar m4 __attribute__((unused)), 9535 UChar r1, UChar r2) 9536 { 9537 if (! s390_host_has_fpext && m3 != S390_BFP_ROUND_PER_FPC) { 9538 emulation_warning(EmWarn_S390X_fpext_rounding); 9539 m3 = S390_BFP_ROUND_PER_FPC; 9540 } 9541 IRTemp op = newTemp(Ity_F64); 9542 9543 assign(op, get_fpr_dw0(r2)); 9544 put_fpr_w0(r1, binop(Iop_F64toF32, mkexpr(encode_bfp_rounding_mode(m3)), 9545 mkexpr(op))); 9546 9547 return "ledbr"; 9548 } 9549 9550 static const HChar * 9551 s390_irgen_MEEBR(UChar r1, UChar r2) 9552 { 9553 IRTemp op1 = newTemp(Ity_F32); 9554 IRTemp op2 = newTemp(Ity_F32); 9555 IRTemp result = newTemp(Ity_F32); 9556 IRRoundingMode rounding_mode = 9557 encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9558 9559 assign(op1, get_fpr_w0(r1)); 9560 assign(op2, get_fpr_w0(r2)); 9561 assign(result, triop(Iop_MulF32, mkexpr(rounding_mode), mkexpr(op1), 9562 mkexpr(op2))); 9563 put_fpr_w0(r1, mkexpr(result)); 9564 9565 return "meebr"; 9566 } 9567 9568 static const HChar * 9569 s390_irgen_MDBR(UChar r1, UChar r2) 9570 { 9571 IRTemp op1 = newTemp(Ity_F64); 9572 IRTemp op2 = newTemp(Ity_F64); 9573 IRTemp result = newTemp(Ity_F64); 9574 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9575 9576 assign(op1, get_fpr_dw0(r1)); 9577 assign(op2, get_fpr_dw0(r2)); 9578 assign(result, triop(Iop_MulF64, mkexpr(rounding_mode), mkexpr(op1), 9579 mkexpr(op2))); 9580 put_fpr_dw0(r1, mkexpr(result)); 9581 9582 return "mdbr"; 9583 } 9584 9585 static const HChar * 9586 s390_irgen_MEEB(UChar r1, IRTemp op2addr) 9587 { 9588 IRTemp op1 = newTemp(Ity_F32); 9589 IRTemp op2 = newTemp(Ity_F32); 9590 IRTemp result = newTemp(Ity_F32); 9591 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9592 9593 assign(op1, get_fpr_w0(r1)); 9594 assign(op2, load(Ity_F32, mkexpr(op2addr))); 9595 assign(result, triop(Iop_MulF32, mkexpr(rounding_mode), mkexpr(op1), 9596 mkexpr(op2))); 9597 put_fpr_w0(r1, mkexpr(result)); 9598 9599 return "meeb"; 9600 } 9601 9602 static const HChar * 9603 s390_irgen_MDB(UChar r1, IRTemp op2addr) 9604 { 9605 IRTemp op1 = newTemp(Ity_F64); 9606 IRTemp op2 = newTemp(Ity_F64); 9607 IRTemp result = newTemp(Ity_F64); 9608 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9609 9610 assign(op1, get_fpr_dw0(r1)); 9611 assign(op2, load(Ity_F64, mkexpr(op2addr))); 9612 assign(result, triop(Iop_MulF64, mkexpr(rounding_mode), mkexpr(op1), 9613 mkexpr(op2))); 9614 put_fpr_dw0(r1, mkexpr(result)); 9615 9616 return "mdb"; 9617 } 9618 9619 static const HChar * 9620 s390_irgen_SEBR(UChar r1, UChar r2) 9621 { 9622 IRTemp op1 = newTemp(Ity_F32); 9623 IRTemp op2 = newTemp(Ity_F32); 9624 IRTemp result = newTemp(Ity_F32); 9625 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9626 9627 assign(op1, get_fpr_w0(r1)); 9628 assign(op2, get_fpr_w0(r2)); 9629 assign(result, triop(Iop_SubF32, mkexpr(rounding_mode), mkexpr(op1), 9630 mkexpr(op2))); 9631 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_32, result); 9632 put_fpr_w0(r1, mkexpr(result)); 9633 9634 return "sebr"; 9635 } 9636 9637 static const HChar * 9638 s390_irgen_SDBR(UChar r1, UChar r2) 9639 { 9640 IRTemp op1 = newTemp(Ity_F64); 9641 IRTemp op2 = newTemp(Ity_F64); 9642 IRTemp result = newTemp(Ity_F64); 9643 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9644 9645 assign(op1, get_fpr_dw0(r1)); 9646 assign(op2, get_fpr_dw0(r2)); 9647 assign(result, triop(Iop_SubF64, mkexpr(rounding_mode), mkexpr(op1), 9648 mkexpr(op2))); 9649 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_64, result); 9650 put_fpr_dw0(r1, mkexpr(result)); 9651 9652 return "sdbr"; 9653 } 9654 9655 static const HChar * 9656 s390_irgen_SEB(UChar r1, IRTemp op2addr) 9657 { 9658 IRTemp op1 = newTemp(Ity_F32); 9659 IRTemp op2 = newTemp(Ity_F32); 9660 IRTemp result = newTemp(Ity_F32); 9661 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9662 9663 assign(op1, get_fpr_w0(r1)); 9664 assign(op2, load(Ity_F32, mkexpr(op2addr))); 9665 assign(result, triop(Iop_SubF32, mkexpr(rounding_mode), mkexpr(op1), 9666 mkexpr(op2))); 9667 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_32, result); 9668 put_fpr_w0(r1, mkexpr(result)); 9669 9670 return "seb"; 9671 } 9672 9673 static const HChar * 9674 s390_irgen_SDB(UChar r1, IRTemp op2addr) 9675 { 9676 IRTemp op1 = newTemp(Ity_F64); 9677 IRTemp op2 = newTemp(Ity_F64); 9678 IRTemp result = newTemp(Ity_F64); 9679 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9680 9681 assign(op1, get_fpr_dw0(r1)); 9682 assign(op2, load(Ity_F64, mkexpr(op2addr))); 9683 assign(result, triop(Iop_SubF64, mkexpr(rounding_mode), mkexpr(op1), 9684 mkexpr(op2))); 9685 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_64, result); 9686 put_fpr_dw0(r1, mkexpr(result)); 9687 9688 return "sdb"; 9689 } 9690 9691 static const HChar * 9692 s390_irgen_ADTRA(UChar r3, UChar m4, UChar r1, UChar r2) 9693 { 9694 if (! s390_host_has_dfp) { 9695 emulation_failure(EmFail_S390X_DFP_insn); 9696 } else { 9697 IRTemp op1 = newTemp(Ity_D64); 9698 IRTemp op2 = newTemp(Ity_D64); 9699 IRTemp result = newTemp(Ity_D64); 9700 IRTemp rounding_mode; 9701 9702 if (! s390_host_has_fpext && m4 != S390_DFP_ROUND_PER_FPC_0) { 9703 emulation_warning(EmWarn_S390X_fpext_rounding); 9704 m4 = S390_DFP_ROUND_PER_FPC_0; 9705 } 9706 9707 rounding_mode = encode_dfp_rounding_mode(m4); 9708 assign(op1, get_dpr_dw0(r2)); 9709 assign(op2, get_dpr_dw0(r3)); 9710 assign(result, triop(Iop_AddD64, mkexpr(rounding_mode), mkexpr(op1), 9711 mkexpr(op2))); 9712 s390_cc_thunk_putF(S390_CC_OP_DFP_RESULT_64, result); 9713 put_dpr_dw0(r1, mkexpr(result)); 9714 } 9715 return (m4 == 0) ? "adtr" : "adtra"; 9716 } 9717 9718 static const HChar * 9719 s390_irgen_AXTRA(UChar r3, UChar m4, UChar r1, UChar r2) 9720 { 9721 if (! s390_host_has_dfp) { 9722 emulation_failure(EmFail_S390X_DFP_insn); 9723 } else { 9724 IRTemp op1 = newTemp(Ity_D128); 9725 IRTemp op2 = newTemp(Ity_D128); 9726 IRTemp result = newTemp(Ity_D128); 9727 IRTemp rounding_mode; 9728 9729 if (! s390_host_has_fpext && m4 != S390_DFP_ROUND_PER_FPC_0) { 9730 emulation_warning(EmWarn_S390X_fpext_rounding); 9731 m4 = S390_DFP_ROUND_PER_FPC_0; 9732 } 9733 9734 rounding_mode = encode_dfp_rounding_mode(m4); 9735 assign(op1, get_dpr_pair(r2)); 9736 assign(op2, get_dpr_pair(r3)); 9737 assign(result, triop(Iop_AddD128, mkexpr(rounding_mode), mkexpr(op1), 9738 mkexpr(op2))); 9739 put_dpr_pair(r1, mkexpr(result)); 9740 9741 s390_cc_thunk_put1d128(S390_CC_OP_DFP_RESULT_128, result); 9742 } 9743 return (m4 == 0) ? "axtr" : "axtra"; 9744 } 9745 9746 static const HChar * 9747 s390_irgen_CDTR(UChar r1, UChar r2) 9748 { 9749 IRTemp op1 = newTemp(Ity_D64); 9750 IRTemp op2 = newTemp(Ity_D64); 9751 IRTemp cc_vex = newTemp(Ity_I32); 9752 IRTemp cc_s390 = newTemp(Ity_I32); 9753 9754 assign(op1, get_dpr_dw0(r1)); 9755 assign(op2, get_dpr_dw0(r2)); 9756 assign(cc_vex, binop(Iop_CmpD64, mkexpr(op1), mkexpr(op2))); 9757 9758 assign(cc_s390, convert_vex_dfpcc_to_s390(cc_vex)); 9759 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 9760 9761 return "cdtr"; 9762 } 9763 9764 static const HChar * 9765 s390_irgen_CXTR(UChar r1, UChar r2) 9766 { 9767 IRTemp op1 = newTemp(Ity_D128); 9768 IRTemp op2 = newTemp(Ity_D128); 9769 IRTemp cc_vex = newTemp(Ity_I32); 9770 IRTemp cc_s390 = newTemp(Ity_I32); 9771 9772 assign(op1, get_dpr_pair(r1)); 9773 assign(op2, get_dpr_pair(r2)); 9774 assign(cc_vex, binop(Iop_CmpD128, mkexpr(op1), mkexpr(op2))); 9775 9776 assign(cc_s390, convert_vex_dfpcc_to_s390(cc_vex)); 9777 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 9778 9779 return "cxtr"; 9780 } 9781 9782 static const HChar * 9783 s390_irgen_CDFTR(UChar m3 __attribute__((unused)), 9784 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 9785 { 9786 if (! s390_host_has_dfp) { 9787 emulation_failure(EmFail_S390X_DFP_insn); 9788 } else { 9789 if (! s390_host_has_fpext) { 9790 emulation_failure(EmFail_S390X_fpext); 9791 } else { 9792 IRTemp op2 = newTemp(Ity_I32); 9793 9794 assign(op2, get_gpr_w1(r2)); 9795 put_dpr_dw0(r1, unop(Iop_I32StoD64, mkexpr(op2))); 9796 } 9797 } 9798 return "cdftr"; 9799 } 9800 9801 static const HChar * 9802 s390_irgen_CXFTR(UChar m3 __attribute__((unused)), 9803 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 9804 { 9805 if (! s390_host_has_dfp) { 9806 emulation_failure(EmFail_S390X_DFP_insn); 9807 } else { 9808 if (! s390_host_has_fpext) { 9809 emulation_failure(EmFail_S390X_fpext); 9810 } else { 9811 IRTemp op2 = newTemp(Ity_I32); 9812 9813 assign(op2, get_gpr_w1(r2)); 9814 put_dpr_pair(r1, unop(Iop_I32StoD128, mkexpr(op2))); 9815 } 9816 } 9817 return "cxftr"; 9818 } 9819 9820 static const HChar * 9821 s390_irgen_CDGTRA(UChar m3, UChar m4 __attribute__((unused)), 9822 UChar r1, UChar r2) 9823 { 9824 if (! s390_host_has_dfp) { 9825 emulation_failure(EmFail_S390X_DFP_insn); 9826 } else { 9827 IRTemp op2 = newTemp(Ity_I64); 9828 9829 if (! s390_host_has_fpext && m3 != S390_DFP_ROUND_PER_FPC_0) { 9830 emulation_warning(EmWarn_S390X_fpext_rounding); 9831 m3 = S390_DFP_ROUND_PER_FPC_0; 9832 } 9833 9834 assign(op2, get_gpr_dw0(r2)); 9835 put_dpr_dw0(r1, binop(Iop_I64StoD64, mkexpr(encode_dfp_rounding_mode(m3)), 9836 mkexpr(op2))); 9837 } 9838 return (m3 == 0) ? "cdgtr" : "cdgtra"; 9839 } 9840 9841 static const HChar * 9842 s390_irgen_CXGTR(UChar m3 __attribute__((unused)), 9843 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 9844 { 9845 if (! s390_host_has_dfp) { 9846 emulation_failure(EmFail_S390X_DFP_insn); 9847 } else { 9848 IRTemp op2 = newTemp(Ity_I64); 9849 9850 /* No emulation warning here about an non-zero m3 on hosts without 9851 floating point extension facility. No rounding is performed */ 9852 9853 assign(op2, get_gpr_dw0(r2)); 9854 put_dpr_pair(r1, unop(Iop_I64StoD128, mkexpr(op2))); 9855 } 9856 return "cxgtr"; 9857 } 9858 9859 static const HChar * 9860 s390_irgen_CDLFTR(UChar m3 __attribute__((unused)), 9861 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 9862 { 9863 if (! s390_host_has_dfp) { 9864 emulation_failure(EmFail_S390X_DFP_insn); 9865 } else { 9866 if (! s390_host_has_fpext) { 9867 emulation_failure(EmFail_S390X_fpext); 9868 } else { 9869 IRTemp op2 = newTemp(Ity_I32); 9870 9871 assign(op2, get_gpr_w1(r2)); 9872 put_dpr_dw0(r1, unop(Iop_I32UtoD64, mkexpr(op2))); 9873 } 9874 } 9875 return "cdlftr"; 9876 } 9877 9878 static const HChar * 9879 s390_irgen_CXLFTR(UChar m3 __attribute__((unused)), 9880 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 9881 { 9882 if (! s390_host_has_dfp) { 9883 emulation_failure(EmFail_S390X_DFP_insn); 9884 } else { 9885 if (! s390_host_has_fpext) { 9886 emulation_failure(EmFail_S390X_fpext); 9887 } else { 9888 IRTemp op2 = newTemp(Ity_I32); 9889 9890 assign(op2, get_gpr_w1(r2)); 9891 put_dpr_pair(r1, unop(Iop_I32UtoD128, mkexpr(op2))); 9892 } 9893 } 9894 return "cxlftr"; 9895 } 9896 9897 static const HChar * 9898 s390_irgen_CDLGTR(UChar m3, UChar m4 __attribute__((unused)), 9899 UChar r1, UChar r2) 9900 { 9901 if (! s390_host_has_dfp) { 9902 emulation_failure(EmFail_S390X_DFP_insn); 9903 } else { 9904 if (! s390_host_has_fpext) { 9905 emulation_failure(EmFail_S390X_fpext); 9906 } else { 9907 IRTemp op2 = newTemp(Ity_I64); 9908 9909 assign(op2, get_gpr_dw0(r2)); 9910 put_dpr_dw0(r1, binop(Iop_I64UtoD64, 9911 mkexpr(encode_dfp_rounding_mode(m3)), 9912 mkexpr(op2))); 9913 } 9914 } 9915 return "cdlgtr"; 9916 } 9917 9918 static const HChar * 9919 s390_irgen_CXLGTR(UChar m3 __attribute__((unused)), 9920 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 9921 { 9922 if (! s390_host_has_dfp) { 9923 emulation_failure(EmFail_S390X_DFP_insn); 9924 } else { 9925 if (! s390_host_has_fpext) { 9926 emulation_failure(EmFail_S390X_fpext); 9927 } else { 9928 IRTemp op2 = newTemp(Ity_I64); 9929 9930 assign(op2, get_gpr_dw0(r2)); 9931 put_dpr_pair(r1, unop(Iop_I64UtoD128, mkexpr(op2))); 9932 } 9933 } 9934 return "cxlgtr"; 9935 } 9936 9937 static const HChar * 9938 s390_irgen_CFDTR(UChar m3, UChar m4 __attribute__((unused)), 9939 UChar r1, UChar r2) 9940 { 9941 if (! s390_host_has_dfp) { 9942 emulation_failure(EmFail_S390X_DFP_insn); 9943 } else { 9944 if (! s390_host_has_fpext) { 9945 emulation_failure(EmFail_S390X_fpext); 9946 } else { 9947 IRTemp op = newTemp(Ity_D64); 9948 IRTemp result = newTemp(Ity_I32); 9949 IRTemp rounding_mode = encode_dfp_rounding_mode(m3); 9950 9951 assign(op, get_dpr_dw0(r2)); 9952 assign(result, binop(Iop_D64toI32S, mkexpr(rounding_mode), 9953 mkexpr(op))); 9954 put_gpr_w1(r1, mkexpr(result)); 9955 s390_cc_thunk_putFZ(S390_CC_OP_DFP_64_TO_INT_32, op, rounding_mode); 9956 } 9957 } 9958 return "cfdtr"; 9959 } 9960 9961 static const HChar * 9962 s390_irgen_CFXTR(UChar m3, UChar m4 __attribute__((unused)), 9963 UChar r1, UChar r2) 9964 { 9965 if (! s390_host_has_dfp) { 9966 emulation_failure(EmFail_S390X_DFP_insn); 9967 } else { 9968 if (! s390_host_has_fpext) { 9969 emulation_failure(EmFail_S390X_fpext); 9970 } else { 9971 IRTemp op = newTemp(Ity_D128); 9972 IRTemp result = newTemp(Ity_I32); 9973 IRTemp rounding_mode = encode_dfp_rounding_mode(m3); 9974 9975 assign(op, get_dpr_pair(r2)); 9976 assign(result, binop(Iop_D128toI32S, mkexpr(rounding_mode), 9977 mkexpr(op))); 9978 put_gpr_w1(r1, mkexpr(result)); 9979 s390_cc_thunk_put1d128Z(S390_CC_OP_DFP_128_TO_INT_32, op, 9980 rounding_mode); 9981 } 9982 } 9983 return "cfxtr"; 9984 } 9985 9986 static const HChar * 9987 s390_irgen_CGDTR(UChar m3, UChar m4 __attribute__((unused)), 9988 UChar r1, UChar r2) 9989 { 9990 if (! s390_host_has_dfp) { 9991 emulation_failure(EmFail_S390X_DFP_insn); 9992 } else { 9993 IRTemp op = newTemp(Ity_D64); 9994 IRTemp rounding_mode = encode_dfp_rounding_mode(m3); 9995 9996 /* If fpext is not installed and m3 is in 1:7, 9997 rounding mode performed is unpredictable */ 9998 if (! s390_host_has_fpext && m3 > 0 && m3 < 8) { 9999 emulation_warning(EmWarn_S390X_fpext_rounding); 10000 m3 = S390_DFP_ROUND_PER_FPC_0; 10001 } 10002 10003 assign(op, get_dpr_dw0(r2)); 10004 put_gpr_dw0(r1, binop(Iop_D64toI64S, mkexpr(rounding_mode), mkexpr(op))); 10005 s390_cc_thunk_putFZ(S390_CC_OP_DFP_64_TO_INT_64, op, rounding_mode); 10006 } 10007 return "cgdtr"; 10008 } 10009 10010 static const HChar * 10011 s390_irgen_CGXTR(UChar m3, UChar m4 __attribute__((unused)), 10012 UChar r1, UChar r2) 10013 { 10014 if (! s390_host_has_dfp) { 10015 emulation_failure(EmFail_S390X_DFP_insn); 10016 } else { 10017 IRTemp op = newTemp(Ity_D128); 10018 IRTemp rounding_mode = encode_dfp_rounding_mode(m3); 10019 10020 /* If fpext is not installed and m3 is in 1:7, 10021 rounding mode performed is unpredictable */ 10022 if (! s390_host_has_fpext && m3 > 0 && m3 < 8) { 10023 emulation_warning(EmWarn_S390X_fpext_rounding); 10024 m3 = S390_DFP_ROUND_PER_FPC_0; 10025 } 10026 assign(op, get_dpr_pair(r2)); 10027 put_gpr_dw0(r1, binop(Iop_D128toI64S, mkexpr(rounding_mode), mkexpr(op))); 10028 s390_cc_thunk_put1d128Z(S390_CC_OP_DFP_128_TO_INT_64, op, rounding_mode); 10029 } 10030 return "cgxtr"; 10031 } 10032 10033 static const HChar * 10034 s390_irgen_CEDTR(UChar r1, UChar r2) 10035 { 10036 if (! s390_host_has_dfp) { 10037 emulation_failure(EmFail_S390X_DFP_insn); 10038 } else { 10039 IRTemp op1 = newTemp(Ity_D64); 10040 IRTemp op2 = newTemp(Ity_D64); 10041 IRTemp cc_vex = newTemp(Ity_I32); 10042 IRTemp cc_s390 = newTemp(Ity_I32); 10043 10044 assign(op1, get_dpr_dw0(r1)); 10045 assign(op2, get_dpr_dw0(r2)); 10046 assign(cc_vex, binop(Iop_CmpExpD64, mkexpr(op1), mkexpr(op2))); 10047 10048 assign(cc_s390, convert_vex_dfpcc_to_s390(cc_vex)); 10049 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 10050 } 10051 return "cedtr"; 10052 } 10053 10054 static const HChar * 10055 s390_irgen_CEXTR(UChar r1, UChar r2) 10056 { 10057 if (! s390_host_has_dfp) { 10058 emulation_failure(EmFail_S390X_DFP_insn); 10059 } else { 10060 IRTemp op1 = newTemp(Ity_D128); 10061 IRTemp op2 = newTemp(Ity_D128); 10062 IRTemp cc_vex = newTemp(Ity_I32); 10063 IRTemp cc_s390 = newTemp(Ity_I32); 10064 10065 assign(op1, get_dpr_pair(r1)); 10066 assign(op2, get_dpr_pair(r2)); 10067 assign(cc_vex, binop(Iop_CmpExpD128, mkexpr(op1), mkexpr(op2))); 10068 10069 assign(cc_s390, convert_vex_dfpcc_to_s390(cc_vex)); 10070 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 10071 } 10072 return "cextr"; 10073 } 10074 10075 static const HChar * 10076 s390_irgen_CLFDTR(UChar m3, UChar m4 __attribute__((unused)), 10077 UChar r1, UChar r2) 10078 { 10079 if (! s390_host_has_dfp) { 10080 emulation_failure(EmFail_S390X_DFP_insn); 10081 } else { 10082 if (! s390_host_has_fpext) { 10083 emulation_failure(EmFail_S390X_fpext); 10084 } else { 10085 IRTemp op = newTemp(Ity_D64); 10086 IRTemp result = newTemp(Ity_I32); 10087 IRTemp rounding_mode = encode_dfp_rounding_mode(m3); 10088 10089 assign(op, get_dpr_dw0(r2)); 10090 assign(result, binop(Iop_D64toI32U, mkexpr(rounding_mode), 10091 mkexpr(op))); 10092 put_gpr_w1(r1, mkexpr(result)); 10093 s390_cc_thunk_putFZ(S390_CC_OP_DFP_64_TO_UINT_32, op, rounding_mode); 10094 } 10095 } 10096 return "clfdtr"; 10097 } 10098 10099 static const HChar * 10100 s390_irgen_CLFXTR(UChar m3, UChar m4 __attribute__((unused)), 10101 UChar r1, UChar r2) 10102 { 10103 if (! s390_host_has_dfp) { 10104 emulation_failure(EmFail_S390X_DFP_insn); 10105 } else { 10106 if (! s390_host_has_fpext) { 10107 emulation_failure(EmFail_S390X_fpext); 10108 } else { 10109 IRTemp op = newTemp(Ity_D128); 10110 IRTemp result = newTemp(Ity_I32); 10111 IRTemp rounding_mode = encode_dfp_rounding_mode(m3); 10112 10113 assign(op, get_dpr_pair(r2)); 10114 assign(result, binop(Iop_D128toI32U, mkexpr(rounding_mode), 10115 mkexpr(op))); 10116 put_gpr_w1(r1, mkexpr(result)); 10117 s390_cc_thunk_put1d128Z(S390_CC_OP_DFP_128_TO_UINT_32, op, 10118 rounding_mode); 10119 } 10120 } 10121 return "clfxtr"; 10122 } 10123 10124 static const HChar * 10125 s390_irgen_CLGDTR(UChar m3, UChar m4 __attribute__((unused)), 10126 UChar r1, UChar r2) 10127 { 10128 if (! s390_host_has_dfp) { 10129 emulation_failure(EmFail_S390X_DFP_insn); 10130 } else { 10131 if (! s390_host_has_fpext) { 10132 emulation_failure(EmFail_S390X_fpext); 10133 } else { 10134 IRTemp op = newTemp(Ity_D64); 10135 IRTemp result = newTemp(Ity_I64); 10136 IRTemp rounding_mode = encode_dfp_rounding_mode(m3); 10137 10138 assign(op, get_dpr_dw0(r2)); 10139 assign(result, binop(Iop_D64toI64U, mkexpr(rounding_mode), 10140 mkexpr(op))); 10141 put_gpr_dw0(r1, mkexpr(result)); 10142 s390_cc_thunk_putFZ(S390_CC_OP_DFP_64_TO_UINT_64, op, rounding_mode); 10143 } 10144 } 10145 return "clgdtr"; 10146 } 10147 10148 static const HChar * 10149 s390_irgen_CLGXTR(UChar m3, UChar m4 __attribute__((unused)), 10150 UChar r1, UChar r2) 10151 { 10152 if (! s390_host_has_dfp) { 10153 emulation_failure(EmFail_S390X_DFP_insn); 10154 } else { 10155 if (! s390_host_has_fpext) { 10156 emulation_failure(EmFail_S390X_fpext); 10157 } else { 10158 IRTemp op = newTemp(Ity_D128); 10159 IRTemp result = newTemp(Ity_I64); 10160 IRTemp rounding_mode = encode_dfp_rounding_mode(m3); 10161 10162 assign(op, get_dpr_pair(r2)); 10163 assign(result, binop(Iop_D128toI64U, mkexpr(rounding_mode), 10164 mkexpr(op))); 10165 put_gpr_dw0(r1, mkexpr(result)); 10166 s390_cc_thunk_put1d128Z(S390_CC_OP_DFP_128_TO_UINT_64, op, 10167 rounding_mode); 10168 } 10169 } 10170 return "clgxtr"; 10171 } 10172 10173 static const HChar * 10174 s390_irgen_DDTRA(UChar r3, UChar m4, UChar r1, UChar r2) 10175 { 10176 if (! s390_host_has_dfp) { 10177 emulation_failure(EmFail_S390X_DFP_insn); 10178 } else { 10179 IRTemp op1 = newTemp(Ity_D64); 10180 IRTemp op2 = newTemp(Ity_D64); 10181 IRTemp result = newTemp(Ity_D64); 10182 IRTemp rounding_mode; 10183 10184 if (! s390_host_has_fpext && m4 != S390_DFP_ROUND_PER_FPC_0) { 10185 emulation_warning(EmWarn_S390X_fpext_rounding); 10186 m4 = S390_DFP_ROUND_PER_FPC_0; 10187 } 10188 10189 rounding_mode = encode_dfp_rounding_mode(m4); 10190 assign(op1, get_dpr_dw0(r2)); 10191 assign(op2, get_dpr_dw0(r3)); 10192 assign(result, triop(Iop_DivD64, mkexpr(rounding_mode), mkexpr(op1), 10193 mkexpr(op2))); 10194 put_dpr_dw0(r1, mkexpr(result)); 10195 } 10196 return (m4 == 0) ? "ddtr" : "ddtra"; 10197 } 10198 10199 static const HChar * 10200 s390_irgen_DXTRA(UChar r3, UChar m4, UChar r1, UChar r2) 10201 { 10202 if (! s390_host_has_dfp) { 10203 emulation_failure(EmFail_S390X_DFP_insn); 10204 } else { 10205 IRTemp op1 = newTemp(Ity_D128); 10206 IRTemp op2 = newTemp(Ity_D128); 10207 IRTemp result = newTemp(Ity_D128); 10208 IRTemp rounding_mode; 10209 10210 if (! s390_host_has_fpext && m4 != S390_DFP_ROUND_PER_FPC_0) { 10211 emulation_warning(EmWarn_S390X_fpext_rounding); 10212 m4 = S390_DFP_ROUND_PER_FPC_0; 10213 } 10214 10215 rounding_mode = encode_dfp_rounding_mode(m4); 10216 assign(op1, get_dpr_pair(r2)); 10217 assign(op2, get_dpr_pair(r3)); 10218 assign(result, triop(Iop_DivD128, mkexpr(rounding_mode), mkexpr(op1), 10219 mkexpr(op2))); 10220 put_dpr_pair(r1, mkexpr(result)); 10221 } 10222 return (m4 == 0) ? "dxtr" : "dxtra"; 10223 } 10224 10225 static const HChar * 10226 s390_irgen_EEDTR(UChar r1, UChar r2) 10227 { 10228 if (! s390_host_has_dfp) { 10229 emulation_failure(EmFail_S390X_DFP_insn); 10230 } else { 10231 put_gpr_dw0(r1, unop(Iop_ExtractExpD64, get_dpr_dw0(r2))); 10232 } 10233 return "eedtr"; 10234 } 10235 10236 static const HChar * 10237 s390_irgen_EEXTR(UChar r1, UChar r2) 10238 { 10239 if (! s390_host_has_dfp) { 10240 emulation_failure(EmFail_S390X_DFP_insn); 10241 } else { 10242 put_gpr_dw0(r1, unop(Iop_ExtractExpD128, get_dpr_pair(r2))); 10243 } 10244 return "eextr"; 10245 } 10246 10247 static const HChar * 10248 s390_irgen_ESDTR(UChar r1, UChar r2) 10249 { 10250 if (! s390_host_has_dfp) { 10251 emulation_failure(EmFail_S390X_DFP_insn); 10252 } else { 10253 put_gpr_dw0(r1, unop(Iop_ExtractSigD64, get_dpr_dw0(r2))); 10254 } 10255 return "esdtr"; 10256 } 10257 10258 static const HChar * 10259 s390_irgen_ESXTR(UChar r1, UChar r2) 10260 { 10261 if (! s390_host_has_dfp) { 10262 emulation_failure(EmFail_S390X_DFP_insn); 10263 } else { 10264 put_gpr_dw0(r1, unop(Iop_ExtractSigD128, get_dpr_pair(r2))); 10265 } 10266 return "esxtr"; 10267 } 10268 10269 static const HChar * 10270 s390_irgen_IEDTR(UChar r3, UChar r1, UChar r2) 10271 { 10272 if (! s390_host_has_dfp) { 10273 emulation_failure(EmFail_S390X_DFP_insn); 10274 } else { 10275 IRTemp op1 = newTemp(Ity_I64); 10276 IRTemp op2 = newTemp(Ity_D64); 10277 IRTemp result = newTemp(Ity_D64); 10278 10279 assign(op1, get_gpr_dw0(r2)); 10280 assign(op2, get_dpr_dw0(r3)); 10281 assign(result, binop(Iop_InsertExpD64, mkexpr(op1), mkexpr(op2))); 10282 put_dpr_dw0(r1, mkexpr(result)); 10283 } 10284 return "iedtr"; 10285 } 10286 10287 static const HChar * 10288 s390_irgen_IEXTR(UChar r3, UChar r1, UChar r2) 10289 { 10290 if (! s390_host_has_dfp) { 10291 emulation_failure(EmFail_S390X_DFP_insn); 10292 } else { 10293 IRTemp op1 = newTemp(Ity_I64); 10294 IRTemp op2 = newTemp(Ity_D128); 10295 IRTemp result = newTemp(Ity_D128); 10296 10297 assign(op1, get_gpr_dw0(r2)); 10298 assign(op2, get_dpr_pair(r3)); 10299 assign(result, binop(Iop_InsertExpD128, mkexpr(op1), mkexpr(op2))); 10300 put_dpr_pair(r1, mkexpr(result)); 10301 } 10302 return "iextr"; 10303 } 10304 10305 static const HChar * 10306 s390_irgen_LDETR(UChar m4 __attribute__((unused)), UChar r1, UChar r2) 10307 { 10308 if (! s390_host_has_dfp) { 10309 emulation_failure(EmFail_S390X_DFP_insn); 10310 } else { 10311 IRTemp op = newTemp(Ity_D32); 10312 10313 assign(op, get_dpr_w0(r2)); 10314 put_dpr_dw0(r1, unop(Iop_D32toD64, mkexpr(op))); 10315 } 10316 return "ldetr"; 10317 } 10318 10319 static const HChar * 10320 s390_irgen_LXDTR(UChar m4 __attribute__((unused)), UChar r1, UChar r2) 10321 { 10322 IRTemp op = newTemp(Ity_D64); 10323 10324 assign(op, get_dpr_dw0(r2)); 10325 put_dpr_pair(r1, unop(Iop_D64toD128, mkexpr(op))); 10326 10327 return "lxdtr"; 10328 } 10329 10330 static const HChar * 10331 s390_irgen_LDXTR(UChar m3, UChar m4 __attribute__((unused)), 10332 UChar r1, UChar r2) 10333 { 10334 if (! s390_host_has_dfp) { 10335 emulation_failure(EmFail_S390X_DFP_insn); 10336 } else { 10337 /* If fpext is not installed and m3 is in 1:7, 10338 rounding mode performed is unpredictable */ 10339 if (! s390_host_has_fpext && m3 > 0 && m3 < 8) { 10340 emulation_warning(EmWarn_S390X_fpext_rounding); 10341 m3 = S390_DFP_ROUND_PER_FPC_0; 10342 } 10343 IRTemp result = newTemp(Ity_D64); 10344 10345 assign(result, binop(Iop_D128toD64, mkexpr(encode_dfp_rounding_mode(m3)), 10346 get_dpr_pair(r2))); 10347 put_dpr_dw0(r1, mkexpr(result)); 10348 } 10349 return "ldxtr"; 10350 } 10351 10352 static const HChar * 10353 s390_irgen_LEDTR(UChar m3, UChar m4 __attribute__((unused)), 10354 UChar r1, UChar r2) 10355 { 10356 if (! s390_host_has_dfp) { 10357 emulation_failure(EmFail_S390X_DFP_insn); 10358 } else { 10359 /* If fpext is not installed and m3 is in 1:7, 10360 rounding mode performed is unpredictable */ 10361 if (! s390_host_has_fpext && m3 > 0 && m3 < 8) { 10362 emulation_warning(EmWarn_S390X_fpext_rounding); 10363 m3 = S390_DFP_ROUND_PER_FPC_0; 10364 } 10365 IRTemp op = newTemp(Ity_D64); 10366 10367 assign(op, get_dpr_dw0(r2)); 10368 put_dpr_w0(r1, binop(Iop_D64toD32, mkexpr(encode_dfp_rounding_mode(m3)), 10369 mkexpr(op))); 10370 } 10371 return "ledtr"; 10372 } 10373 10374 static const HChar * 10375 s390_irgen_LTDTR(UChar r1, UChar r2) 10376 { 10377 IRTemp result = newTemp(Ity_D64); 10378 10379 assign(result, get_dpr_dw0(r2)); 10380 put_dpr_dw0(r1, mkexpr(result)); 10381 s390_cc_thunk_putF(S390_CC_OP_DFP_RESULT_64, result); 10382 10383 return "ltdtr"; 10384 } 10385 10386 static const HChar * 10387 s390_irgen_LTXTR(UChar r1, UChar r2) 10388 { 10389 IRTemp result = newTemp(Ity_D128); 10390 10391 assign(result, get_dpr_pair(r2)); 10392 put_dpr_pair(r1, mkexpr(result)); 10393 s390_cc_thunk_put1d128(S390_CC_OP_DFP_RESULT_128, result); 10394 10395 return "ltxtr"; 10396 } 10397 10398 static const HChar * 10399 s390_irgen_MDTRA(UChar r3, UChar m4, UChar r1, UChar r2) 10400 { 10401 if (! s390_host_has_dfp) { 10402 emulation_failure(EmFail_S390X_DFP_insn); 10403 } else { 10404 IRTemp op1 = newTemp(Ity_D64); 10405 IRTemp op2 = newTemp(Ity_D64); 10406 IRTemp result = newTemp(Ity_D64); 10407 IRTemp rounding_mode; 10408 10409 if (! s390_host_has_fpext && m4 != S390_DFP_ROUND_PER_FPC_0) { 10410 emulation_warning(EmWarn_S390X_fpext_rounding); 10411 m4 = S390_DFP_ROUND_PER_FPC_0; 10412 } 10413 10414 rounding_mode = encode_dfp_rounding_mode(m4); 10415 assign(op1, get_dpr_dw0(r2)); 10416 assign(op2, get_dpr_dw0(r3)); 10417 assign(result, triop(Iop_MulD64, mkexpr(rounding_mode), mkexpr(op1), 10418 mkexpr(op2))); 10419 put_dpr_dw0(r1, mkexpr(result)); 10420 } 10421 return (m4 == 0) ? "mdtr" : "mdtra"; 10422 } 10423 10424 static const HChar * 10425 s390_irgen_MXTRA(UChar r3, UChar m4, UChar r1, UChar r2) 10426 { 10427 if (! s390_host_has_dfp) { 10428 emulation_failure(EmFail_S390X_DFP_insn); 10429 } else { 10430 IRTemp op1 = newTemp(Ity_D128); 10431 IRTemp op2 = newTemp(Ity_D128); 10432 IRTemp result = newTemp(Ity_D128); 10433 IRTemp rounding_mode; 10434 10435 if (! s390_host_has_fpext && m4 != S390_DFP_ROUND_PER_FPC_0) { 10436 emulation_warning(EmWarn_S390X_fpext_rounding); 10437 m4 = S390_DFP_ROUND_PER_FPC_0; 10438 } 10439 10440 rounding_mode = encode_dfp_rounding_mode(m4); 10441 assign(op1, get_dpr_pair(r2)); 10442 assign(op2, get_dpr_pair(r3)); 10443 assign(result, triop(Iop_MulD128, mkexpr(rounding_mode), mkexpr(op1), 10444 mkexpr(op2))); 10445 put_dpr_pair(r1, mkexpr(result)); 10446 } 10447 return (m4 == 0) ? "mxtr" : "mxtra"; 10448 } 10449 10450 static const HChar * 10451 s390_irgen_QADTR(UChar r3, UChar m4, UChar r1, UChar r2) 10452 { 10453 if (! s390_host_has_dfp) { 10454 emulation_failure(EmFail_S390X_DFP_insn); 10455 } else { 10456 IRTemp op1 = newTemp(Ity_D64); 10457 IRTemp op2 = newTemp(Ity_D64); 10458 IRTemp result = newTemp(Ity_D64); 10459 IRTemp rounding_mode; 10460 10461 /* If fpext is not installed and m4 is in 1:7, 10462 rounding mode performed is unpredictable */ 10463 if (! s390_host_has_fpext && m4 > 0 && m4 < 8) { 10464 emulation_warning(EmWarn_S390X_fpext_rounding); 10465 m4 = S390_DFP_ROUND_PER_FPC_0; 10466 } 10467 10468 rounding_mode = encode_dfp_rounding_mode(m4); 10469 assign(op1, get_dpr_dw0(r2)); 10470 assign(op2, get_dpr_dw0(r3)); 10471 assign(result, triop(Iop_QuantizeD64, mkexpr(rounding_mode), mkexpr(op1), 10472 mkexpr(op2))); 10473 put_dpr_dw0(r1, mkexpr(result)); 10474 } 10475 return "qadtr"; 10476 } 10477 10478 static const HChar * 10479 s390_irgen_QAXTR(UChar r3, UChar m4, UChar r1, UChar r2) 10480 { 10481 if (! s390_host_has_dfp) { 10482 emulation_failure(EmFail_S390X_DFP_insn); 10483 } else { 10484 IRTemp op1 = newTemp(Ity_D128); 10485 IRTemp op2 = newTemp(Ity_D128); 10486 IRTemp result = newTemp(Ity_D128); 10487 IRTemp rounding_mode; 10488 10489 /* If fpext is not installed and m4 is in 1:7, 10490 rounding mode performed is unpredictable */ 10491 if (! s390_host_has_fpext && m4 > 0 && m4 < 8) { 10492 emulation_warning(EmWarn_S390X_fpext_rounding); 10493 m4 = S390_DFP_ROUND_PER_FPC_0; 10494 } 10495 10496 rounding_mode = encode_dfp_rounding_mode(m4); 10497 assign(op1, get_dpr_pair(r2)); 10498 assign(op2, get_dpr_pair(r3)); 10499 assign(result, triop(Iop_QuantizeD128, mkexpr(rounding_mode), mkexpr(op1), 10500 mkexpr(op2))); 10501 put_dpr_pair(r1, mkexpr(result)); 10502 } 10503 return "qaxtr"; 10504 } 10505 10506 static const HChar * 10507 s390_irgen_RRDTR(UChar r3, UChar m4, UChar r1, UChar r2) 10508 { 10509 if (! s390_host_has_dfp) { 10510 emulation_failure(EmFail_S390X_DFP_insn); 10511 } else { 10512 IRTemp op1 = newTemp(Ity_I8); 10513 IRTemp op2 = newTemp(Ity_D64); 10514 IRTemp result = newTemp(Ity_D64); 10515 IRTemp rounding_mode; 10516 10517 /* If fpext is not installed and m4 is in 1:7, 10518 rounding mode performed is unpredictable */ 10519 if (! s390_host_has_fpext && m4 > 0 && m4 < 8) { 10520 emulation_warning(EmWarn_S390X_fpext_rounding); 10521 m4 = S390_DFP_ROUND_PER_FPC_0; 10522 } 10523 10524 rounding_mode = encode_dfp_rounding_mode(m4); 10525 assign(op1, get_gpr_b7(r2)); 10526 assign(op2, get_dpr_dw0(r3)); 10527 assign(result, triop(Iop_SignificanceRoundD64, mkexpr(rounding_mode), 10528 mkexpr(op1), mkexpr(op2))); 10529 put_dpr_dw0(r1, mkexpr(result)); 10530 } 10531 return "rrdtr"; 10532 } 10533 10534 static const HChar * 10535 s390_irgen_RRXTR(UChar r3, UChar m4, UChar r1, UChar r2) 10536 { 10537 if (! s390_host_has_dfp) { 10538 emulation_failure(EmFail_S390X_DFP_insn); 10539 } else { 10540 IRTemp op1 = newTemp(Ity_I8); 10541 IRTemp op2 = newTemp(Ity_D128); 10542 IRTemp result = newTemp(Ity_D128); 10543 IRTemp rounding_mode; 10544 10545 /* If fpext is not installed and m4 is in 1:7, 10546 rounding mode performed is unpredictable */ 10547 if (! s390_host_has_fpext && m4 > 0 && m4 < 8) { 10548 emulation_warning(EmWarn_S390X_fpext_rounding); 10549 m4 = S390_DFP_ROUND_PER_FPC_0; 10550 } 10551 10552 rounding_mode = encode_dfp_rounding_mode(m4); 10553 assign(op1, get_gpr_b7(r2)); 10554 assign(op2, get_dpr_pair(r3)); 10555 assign(result, triop(Iop_SignificanceRoundD128, mkexpr(rounding_mode), 10556 mkexpr(op1), mkexpr(op2))); 10557 put_dpr_pair(r1, mkexpr(result)); 10558 } 10559 return "rrxtr"; 10560 } 10561 10562 static const HChar * 10563 s390_irgen_SDTRA(UChar r3, UChar m4, UChar r1, UChar r2) 10564 { 10565 if (! s390_host_has_dfp) { 10566 emulation_failure(EmFail_S390X_DFP_insn); 10567 } else { 10568 IRTemp op1 = newTemp(Ity_D64); 10569 IRTemp op2 = newTemp(Ity_D64); 10570 IRTemp result = newTemp(Ity_D64); 10571 IRTemp rounding_mode; 10572 10573 if (! s390_host_has_fpext && m4 != S390_DFP_ROUND_PER_FPC_0) { 10574 emulation_warning(EmWarn_S390X_fpext_rounding); 10575 m4 = S390_DFP_ROUND_PER_FPC_0; 10576 } 10577 10578 rounding_mode = encode_dfp_rounding_mode(m4); 10579 assign(op1, get_dpr_dw0(r2)); 10580 assign(op2, get_dpr_dw0(r3)); 10581 assign(result, triop(Iop_SubD64, mkexpr(rounding_mode), mkexpr(op1), 10582 mkexpr(op2))); 10583 s390_cc_thunk_putF(S390_CC_OP_DFP_RESULT_64, result); 10584 put_dpr_dw0(r1, mkexpr(result)); 10585 } 10586 return (m4 == 0) ? "sdtr" : "sdtra"; 10587 } 10588 10589 static const HChar * 10590 s390_irgen_SXTRA(UChar r3, UChar m4, UChar r1, UChar r2) 10591 { 10592 if (! s390_host_has_dfp) { 10593 emulation_failure(EmFail_S390X_DFP_insn); 10594 } else { 10595 IRTemp op1 = newTemp(Ity_D128); 10596 IRTemp op2 = newTemp(Ity_D128); 10597 IRTemp result = newTemp(Ity_D128); 10598 IRTemp rounding_mode; 10599 10600 if (! s390_host_has_fpext && m4 != S390_DFP_ROUND_PER_FPC_0) { 10601 emulation_warning(EmWarn_S390X_fpext_rounding); 10602 m4 = S390_DFP_ROUND_PER_FPC_0; 10603 } 10604 10605 rounding_mode = encode_dfp_rounding_mode(m4); 10606 assign(op1, get_dpr_pair(r2)); 10607 assign(op2, get_dpr_pair(r3)); 10608 assign(result, triop(Iop_SubD128, mkexpr(rounding_mode), mkexpr(op1), 10609 mkexpr(op2))); 10610 put_dpr_pair(r1, mkexpr(result)); 10611 10612 s390_cc_thunk_put1d128(S390_CC_OP_DFP_RESULT_128, result); 10613 } 10614 return (m4 == 0) ? "sxtr" : "sxtra"; 10615 } 10616 10617 static const HChar * 10618 s390_irgen_SLDT(UChar r3, IRTemp op2addr, UChar r1) 10619 { 10620 if (! s390_host_has_dfp) { 10621 emulation_failure(EmFail_S390X_DFP_insn); 10622 } else { 10623 IRTemp op = newTemp(Ity_D64); 10624 10625 assign(op, get_dpr_dw0(r3)); 10626 put_dpr_dw0(r1, binop(Iop_ShlD64, mkexpr(op), 10627 unop(Iop_64to8, binop(Iop_And64, mkexpr(op2addr), 10628 mkU64(63))))); 10629 } 10630 return "sldt"; 10631 } 10632 10633 static const HChar * 10634 s390_irgen_SLXT(UChar r3, IRTemp op2addr, UChar r1) 10635 { 10636 if (! s390_host_has_dfp) { 10637 emulation_failure(EmFail_S390X_DFP_insn); 10638 } else { 10639 IRTemp op = newTemp(Ity_D128); 10640 10641 assign(op, get_dpr_pair(r3)); 10642 put_dpr_pair(r1, binop(Iop_ShlD128, mkexpr(op), 10643 unop(Iop_64to8, binop(Iop_And64, mkexpr(op2addr), 10644 mkU64(63))))); 10645 } 10646 return "slxt"; 10647 } 10648 10649 static const HChar * 10650 s390_irgen_SRDT(UChar r3, IRTemp op2addr, UChar r1) 10651 { 10652 if (! s390_host_has_dfp) { 10653 emulation_failure(EmFail_S390X_DFP_insn); 10654 } else { 10655 IRTemp op = newTemp(Ity_D64); 10656 10657 assign(op, get_dpr_dw0(r3)); 10658 put_dpr_dw0(r1, binop(Iop_ShrD64, mkexpr(op), 10659 unop(Iop_64to8, binop(Iop_And64, mkexpr(op2addr), 10660 mkU64(63))))); 10661 } 10662 return "srdt"; 10663 } 10664 10665 static const HChar * 10666 s390_irgen_SRXT(UChar r3, IRTemp op2addr, UChar r1) 10667 { 10668 if (! s390_host_has_dfp) { 10669 emulation_failure(EmFail_S390X_DFP_insn); 10670 } else { 10671 IRTemp op = newTemp(Ity_D128); 10672 10673 assign(op, get_dpr_pair(r3)); 10674 put_dpr_pair(r1, binop(Iop_ShrD128, mkexpr(op), 10675 unop(Iop_64to8, binop(Iop_And64, mkexpr(op2addr), 10676 mkU64(63))))); 10677 } 10678 return "srxt"; 10679 } 10680 10681 static const HChar * 10682 s390_irgen_TDCET(UChar r1, IRTemp op2addr) 10683 { 10684 if (! s390_host_has_dfp) { 10685 emulation_failure(EmFail_S390X_DFP_insn); 10686 } else { 10687 IRTemp value = newTemp(Ity_D32); 10688 10689 assign(value, get_dpr_w0(r1)); 10690 10691 s390_cc_thunk_putFZ(S390_CC_OP_DFP_TDC_32, value, op2addr); 10692 } 10693 return "tdcet"; 10694 } 10695 10696 static const HChar * 10697 s390_irgen_TDCDT(UChar r1, IRTemp op2addr) 10698 { 10699 if (! s390_host_has_dfp) { 10700 emulation_failure(EmFail_S390X_DFP_insn); 10701 } else { 10702 IRTemp value = newTemp(Ity_D64); 10703 10704 assign(value, get_dpr_dw0(r1)); 10705 10706 s390_cc_thunk_putFZ(S390_CC_OP_DFP_TDC_64, value, op2addr); 10707 } 10708 return "tdcdt"; 10709 } 10710 10711 static const HChar * 10712 s390_irgen_TDCXT(UChar r1, IRTemp op2addr) 10713 { 10714 if (! s390_host_has_dfp) { 10715 emulation_failure(EmFail_S390X_DFP_insn); 10716 } else { 10717 IRTemp value = newTemp(Ity_D128); 10718 10719 assign(value, get_dpr_pair(r1)); 10720 10721 s390_cc_thunk_put1d128Z(S390_CC_OP_DFP_TDC_128, value, op2addr); 10722 } 10723 return "tdcxt"; 10724 } 10725 10726 static const HChar * 10727 s390_irgen_TDGET(UChar r1, IRTemp op2addr) 10728 { 10729 if (! s390_host_has_dfp) { 10730 emulation_failure(EmFail_S390X_DFP_insn); 10731 } else { 10732 IRTemp value = newTemp(Ity_D32); 10733 10734 assign(value, get_dpr_w0(r1)); 10735 10736 s390_cc_thunk_putFZ(S390_CC_OP_DFP_TDG_32, value, op2addr); 10737 } 10738 return "tdget"; 10739 } 10740 10741 static const HChar * 10742 s390_irgen_TDGDT(UChar r1, IRTemp op2addr) 10743 { 10744 if (! s390_host_has_dfp) { 10745 emulation_failure(EmFail_S390X_DFP_insn); 10746 } else { 10747 IRTemp value = newTemp(Ity_D64); 10748 10749 assign(value, get_dpr_dw0(r1)); 10750 10751 s390_cc_thunk_putFZ(S390_CC_OP_DFP_TDG_64, value, op2addr); 10752 } 10753 return "tdgdt"; 10754 } 10755 10756 static const HChar * 10757 s390_irgen_TDGXT(UChar r1, IRTemp op2addr) 10758 { 10759 if (! s390_host_has_dfp) { 10760 emulation_failure(EmFail_S390X_DFP_insn); 10761 } else { 10762 IRTemp value = newTemp(Ity_D128); 10763 10764 assign(value, get_dpr_pair(r1)); 10765 10766 s390_cc_thunk_put1d128Z(S390_CC_OP_DFP_TDG_128, value, op2addr); 10767 } 10768 return "tdgxt"; 10769 } 10770 10771 static const HChar * 10772 s390_irgen_CLC(UChar length, IRTemp start1, IRTemp start2) 10773 { 10774 IRTemp len = newTemp(Ity_I64); 10775 10776 assign(len, mkU64(length)); 10777 s390_irgen_CLC_EX(len, start1, start2); 10778 10779 return "clc"; 10780 } 10781 10782 static const HChar * 10783 s390_irgen_CLCL(UChar r1, UChar r2) 10784 { 10785 IRTemp addr1 = newTemp(Ity_I64); 10786 IRTemp addr2 = newTemp(Ity_I64); 10787 IRTemp addr1_load = newTemp(Ity_I64); 10788 IRTemp addr2_load = newTemp(Ity_I64); 10789 IRTemp len1 = newTemp(Ity_I32); 10790 IRTemp len2 = newTemp(Ity_I32); 10791 IRTemp r1p1 = newTemp(Ity_I32); /* contents of r1 + 1 */ 10792 IRTemp r2p1 = newTemp(Ity_I32); /* contents of r2 + 1 */ 10793 IRTemp single1 = newTemp(Ity_I8); 10794 IRTemp single2 = newTemp(Ity_I8); 10795 IRTemp pad = newTemp(Ity_I8); 10796 10797 assign(addr1, get_gpr_dw0(r1)); 10798 assign(r1p1, get_gpr_w1(r1 + 1)); 10799 assign(len1, binop(Iop_And32, mkexpr(r1p1), mkU32(0x00ffffff))); 10800 assign(addr2, get_gpr_dw0(r2)); 10801 assign(r2p1, get_gpr_w1(r2 + 1)); 10802 assign(len2, binop(Iop_And32, mkexpr(r2p1), mkU32(0x00ffffff))); 10803 assign(pad, get_gpr_b4(r2 + 1)); 10804 10805 /* len1 == 0 and len2 == 0? Exit */ 10806 s390_cc_set(0); 10807 next_insn_if(binop(Iop_CmpEQ32, binop(Iop_Or32, mkexpr(len1), 10808 mkexpr(len2)), mkU32(0))); 10809 10810 /* Because mkite evaluates both the then-clause and the else-clause 10811 we cannot load directly from addr1 here. If len1 is 0, then adddr1 10812 may be NULL and loading from there would segfault. So we provide a 10813 valid dummy address in that case. Loading from there does no harm and 10814 the value will be discarded at runtime. */ 10815 assign(addr1_load, 10816 mkite(binop(Iop_CmpEQ32, mkexpr(len1), mkU32(0)), 10817 mkU64(guest_IA_curr_instr), mkexpr(addr1))); 10818 assign(single1, 10819 mkite(binop(Iop_CmpEQ32, mkexpr(len1), mkU32(0)), 10820 mkexpr(pad), load(Ity_I8, mkexpr(addr1_load)))); 10821 10822 assign(addr2_load, 10823 mkite(binop(Iop_CmpEQ32, mkexpr(len2), mkU32(0)), 10824 mkU64(guest_IA_curr_instr), mkexpr(addr2))); 10825 assign(single2, 10826 mkite(binop(Iop_CmpEQ32, mkexpr(len2), mkU32(0)), 10827 mkexpr(pad), load(Ity_I8, mkexpr(addr2_load)))); 10828 10829 s390_cc_thunk_put2(S390_CC_OP_UNSIGNED_COMPARE, single1, single2, False); 10830 /* Fields differ ? */ 10831 next_insn_if(binop(Iop_CmpNE8, mkexpr(single1), mkexpr(single2))); 10832 10833 /* Update len1 and addr1, unless len1 == 0. */ 10834 put_gpr_dw0(r1, 10835 mkite(binop(Iop_CmpEQ32, mkexpr(len1), mkU32(0)), 10836 mkexpr(addr1), 10837 binop(Iop_Add64, mkexpr(addr1), mkU64(1)))); 10838 10839 /* When updating len1 we must not modify bits (r1+1)[0:39] */ 10840 put_gpr_w1(r1 + 1, 10841 mkite(binop(Iop_CmpEQ32, mkexpr(len1), mkU32(0)), 10842 binop(Iop_And32, mkexpr(r1p1), mkU32(0xFF000000u)), 10843 binop(Iop_Sub32, mkexpr(r1p1), mkU32(1)))); 10844 10845 /* Update len2 and addr2, unless len2 == 0. */ 10846 put_gpr_dw0(r2, 10847 mkite(binop(Iop_CmpEQ32, mkexpr(len2), mkU32(0)), 10848 mkexpr(addr2), 10849 binop(Iop_Add64, mkexpr(addr2), mkU64(1)))); 10850 10851 /* When updating len2 we must not modify bits (r2+1)[0:39] */ 10852 put_gpr_w1(r2 + 1, 10853 mkite(binop(Iop_CmpEQ32, mkexpr(len2), mkU32(0)), 10854 binop(Iop_And32, mkexpr(r2p1), mkU32(0xFF000000u)), 10855 binop(Iop_Sub32, mkexpr(r2p1), mkU32(1)))); 10856 10857 iterate(); 10858 10859 return "clcl"; 10860 } 10861 10862 static const HChar * 10863 s390_irgen_CLCLE(UChar r1, UChar r3, IRTemp pad2) 10864 { 10865 IRTemp addr1, addr3, addr1_load, addr3_load, len1, len3, single1, single3; 10866 10867 addr1 = newTemp(Ity_I64); 10868 addr3 = newTemp(Ity_I64); 10869 addr1_load = newTemp(Ity_I64); 10870 addr3_load = newTemp(Ity_I64); 10871 len1 = newTemp(Ity_I64); 10872 len3 = newTemp(Ity_I64); 10873 single1 = newTemp(Ity_I8); 10874 single3 = newTemp(Ity_I8); 10875 10876 assign(addr1, get_gpr_dw0(r1)); 10877 assign(len1, get_gpr_dw0(r1 + 1)); 10878 assign(addr3, get_gpr_dw0(r3)); 10879 assign(len3, get_gpr_dw0(r3 + 1)); 10880 10881 /* len1 == 0 and len3 == 0? Exit */ 10882 s390_cc_set(0); 10883 next_insn_if(binop(Iop_CmpEQ64,binop(Iop_Or64, mkexpr(len1), 10884 mkexpr(len3)), mkU64(0))); 10885 10886 /* A mux requires both ways to be possible. This is a way to prevent clcle 10887 from reading from addr1 if it should read from the pad. Since the pad 10888 has no address, just read from the instruction, we discard that anyway */ 10889 assign(addr1_load, 10890 mkite(binop(Iop_CmpEQ64, mkexpr(len1), mkU64(0)), 10891 mkU64(guest_IA_curr_instr), mkexpr(addr1))); 10892 10893 /* same for addr3 */ 10894 assign(addr3_load, 10895 mkite(binop(Iop_CmpEQ64, mkexpr(len3), mkU64(0)), 10896 mkU64(guest_IA_curr_instr), mkexpr(addr3))); 10897 10898 assign(single1, 10899 mkite(binop(Iop_CmpEQ64, mkexpr(len1), mkU64(0)), 10900 unop(Iop_64to8, mkexpr(pad2)), 10901 load(Ity_I8, mkexpr(addr1_load)))); 10902 10903 assign(single3, 10904 mkite(binop(Iop_CmpEQ64, mkexpr(len3), mkU64(0)), 10905 unop(Iop_64to8, mkexpr(pad2)), 10906 load(Ity_I8, mkexpr(addr3_load)))); 10907 10908 s390_cc_thunk_put2(S390_CC_OP_UNSIGNED_COMPARE, single1, single3, False); 10909 /* Both fields differ ? */ 10910 next_insn_if(binop(Iop_CmpNE8, mkexpr(single1), mkexpr(single3))); 10911 10912 /* If a length in 0 we must not change this length and the address */ 10913 put_gpr_dw0(r1, 10914 mkite(binop(Iop_CmpEQ64, mkexpr(len1), mkU64(0)), 10915 mkexpr(addr1), 10916 binop(Iop_Add64, mkexpr(addr1), mkU64(1)))); 10917 10918 put_gpr_dw0(r1 + 1, 10919 mkite(binop(Iop_CmpEQ64, mkexpr(len1), mkU64(0)), 10920 mkU64(0), binop(Iop_Sub64, mkexpr(len1), mkU64(1)))); 10921 10922 put_gpr_dw0(r3, 10923 mkite(binop(Iop_CmpEQ64, mkexpr(len3), mkU64(0)), 10924 mkexpr(addr3), 10925 binop(Iop_Add64, mkexpr(addr3), mkU64(1)))); 10926 10927 put_gpr_dw0(r3 + 1, 10928 mkite(binop(Iop_CmpEQ64, mkexpr(len3), mkU64(0)), 10929 mkU64(0), binop(Iop_Sub64, mkexpr(len3), mkU64(1)))); 10930 10931 iterate(); 10932 10933 return "clcle"; 10934 } 10935 10936 10937 static void 10938 s390_irgen_XC_EX(IRTemp length, IRTemp start1, IRTemp start2) 10939 { 10940 s390_irgen_xonc(Iop_Xor8, length, start1, start2); 10941 } 10942 10943 10944 static void 10945 s390_irgen_NC_EX(IRTemp length, IRTemp start1, IRTemp start2) 10946 { 10947 s390_irgen_xonc(Iop_And8, length, start1, start2); 10948 } 10949 10950 10951 static void 10952 s390_irgen_OC_EX(IRTemp length, IRTemp start1, IRTemp start2) 10953 { 10954 s390_irgen_xonc(Iop_Or8, length, start1, start2); 10955 } 10956 10957 10958 static void 10959 s390_irgen_CLC_EX(IRTemp length, IRTemp start1, IRTemp start2) 10960 { 10961 IRTemp current1 = newTemp(Ity_I8); 10962 IRTemp current2 = newTemp(Ity_I8); 10963 IRTemp counter = newTemp(Ity_I64); 10964 10965 assign(counter, get_counter_dw0()); 10966 put_counter_dw0(mkU64(0)); 10967 10968 assign(current1, load(Ity_I8, binop(Iop_Add64, mkexpr(start1), 10969 mkexpr(counter)))); 10970 assign(current2, load(Ity_I8, binop(Iop_Add64, mkexpr(start2), 10971 mkexpr(counter)))); 10972 s390_cc_thunk_put2(S390_CC_OP_UNSIGNED_COMPARE, current1, current2, 10973 False); 10974 10975 /* Both fields differ ? */ 10976 next_insn_if(binop(Iop_CmpNE8, mkexpr(current1), mkexpr(current2))); 10977 10978 /* Check for end of field */ 10979 put_counter_dw0(binop(Iop_Add64, mkexpr(counter), mkU64(1))); 10980 iterate_if(binop(Iop_CmpNE64, mkexpr(counter), mkexpr(length))); 10981 put_counter_dw0(mkU64(0)); 10982 } 10983 10984 static void 10985 s390_irgen_MVC_EX(IRTemp length, IRTemp start1, IRTemp start2) 10986 { 10987 IRTemp counter = newTemp(Ity_I64); 10988 10989 assign(counter, get_counter_dw0()); 10990 10991 store(binop(Iop_Add64, mkexpr(start1), mkexpr(counter)), 10992 load(Ity_I8, binop(Iop_Add64, mkexpr(start2), mkexpr(counter)))); 10993 10994 /* Check for end of field */ 10995 put_counter_dw0(binop(Iop_Add64, mkexpr(counter), mkU64(1))); 10996 iterate_if(binop(Iop_CmpNE64, mkexpr(counter), mkexpr(length))); 10997 put_counter_dw0(mkU64(0)); 10998 } 10999 11000 static void 11001 s390_irgen_MVCIN_EX(IRTemp length, IRTemp start1, IRTemp start2) 11002 { 11003 IRTemp counter = newTemp(Ity_I64); 11004 11005 assign(counter, get_counter_dw0()); 11006 11007 store(binop(Iop_Add64, mkexpr(start1), mkexpr(counter)), 11008 load(Ity_I8, binop(Iop_Sub64, mkexpr(start2), mkexpr(counter)))); 11009 11010 /* Check for end of field */ 11011 put_counter_dw0(binop(Iop_Add64, mkexpr(counter), mkU64(1))); 11012 iterate_if(binop(Iop_CmpNE64, mkexpr(counter), mkexpr(length))); 11013 put_counter_dw0(mkU64(0)); 11014 } 11015 11016 static void 11017 s390_irgen_TR_EX(IRTemp length, IRTemp start1, IRTemp start2) 11018 { 11019 IRTemp op = newTemp(Ity_I8); 11020 IRTemp op1 = newTemp(Ity_I8); 11021 IRTemp result = newTemp(Ity_I64); 11022 IRTemp counter = newTemp(Ity_I64); 11023 11024 assign(counter, get_counter_dw0()); 11025 11026 assign(op, load(Ity_I8, binop(Iop_Add64, mkexpr(start1), mkexpr(counter)))); 11027 11028 assign(result, binop(Iop_Add64, unop(Iop_8Uto64, mkexpr(op)), mkexpr(start2))); 11029 11030 assign(op1, load(Ity_I8, mkexpr(result))); 11031 store(binop(Iop_Add64, mkexpr(start1), mkexpr(counter)), mkexpr(op1)); 11032 11033 put_counter_dw0(binop(Iop_Add64, mkexpr(counter), mkU64(1))); 11034 iterate_if(binop(Iop_CmpNE64, mkexpr(counter), mkexpr(length))); 11035 put_counter_dw0(mkU64(0)); 11036 } 11037 11038 11039 static void 11040 s390_irgen_EX_SS(UChar r, IRTemp addr2, 11041 void (*irgen)(IRTemp length, IRTemp start1, IRTemp start2), 11042 UInt lensize) 11043 { 11044 struct SS { 11045 unsigned int op : 8; 11046 unsigned int l : 8; 11047 unsigned int b1 : 4; 11048 unsigned int d1 : 12; 11049 unsigned int b2 : 4; 11050 unsigned int d2 : 12; 11051 }; 11052 union { 11053 struct SS dec; 11054 unsigned long bytes; 11055 } ss; 11056 IRTemp cond; 11057 IRDirty *d; 11058 IRTemp torun; 11059 11060 IRTemp start1 = newTemp(Ity_I64); 11061 IRTemp start2 = newTemp(Ity_I64); 11062 IRTemp len = newTemp(lensize == 64 ? Ity_I64 : Ity_I32); 11063 cond = newTemp(Ity_I1); 11064 torun = newTemp(Ity_I64); 11065 11066 assign(torun, load(Ity_I64, mkexpr(addr2))); 11067 /* Start with a check that the saved code is still correct */ 11068 assign(cond, binop(Iop_CmpNE64, mkexpr(torun), mkU64(last_execute_target))); 11069 /* If not, save the new value */ 11070 d = unsafeIRDirty_0_N (0, "s390x_dirtyhelper_EX", &s390x_dirtyhelper_EX, 11071 mkIRExprVec_1(mkexpr(torun))); 11072 d->guard = mkexpr(cond); 11073 stmt(IRStmt_Dirty(d)); 11074 11075 /* and restart */ 11076 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_CMSTART), 11077 mkU64(guest_IA_curr_instr))); 11078 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_CMLEN), mkU64(4))); 11079 restart_if(mkexpr(cond)); 11080 11081 ss.bytes = last_execute_target; 11082 assign(start1, binop(Iop_Add64, mkU64(ss.dec.d1), 11083 ss.dec.b1 != 0 ? get_gpr_dw0(ss.dec.b1) : mkU64(0))); 11084 assign(start2, binop(Iop_Add64, mkU64(ss.dec.d2), 11085 ss.dec.b2 != 0 ? get_gpr_dw0(ss.dec.b2) : mkU64(0))); 11086 assign(len, unop(lensize == 64 ? Iop_8Uto64 : Iop_8Uto32, binop(Iop_Or8, 11087 r != 0 ? get_gpr_b7(r): mkU8(0), mkU8(ss.dec.l)))); 11088 irgen(len, start1, start2); 11089 11090 last_execute_target = 0; 11091 } 11092 11093 static const HChar * 11094 s390_irgen_EX(UChar r1, IRTemp addr2) 11095 { 11096 switch(last_execute_target & 0xff00000000000000ULL) { 11097 case 0: 11098 { 11099 /* no code information yet */ 11100 IRDirty *d; 11101 11102 /* so safe the code... */ 11103 d = unsafeIRDirty_0_N (0, "s390x_dirtyhelper_EX", &s390x_dirtyhelper_EX, 11104 mkIRExprVec_1(load(Ity_I64, mkexpr(addr2)))); 11105 stmt(IRStmt_Dirty(d)); 11106 /* and restart */ 11107 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_CMSTART), 11108 mkU64(guest_IA_curr_instr))); 11109 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_CMLEN), mkU64(4))); 11110 restart_if(IRExpr_Const(IRConst_U1(True))); 11111 11112 /* we know that this will be invalidated */ 11113 put_IA(mkaddr_expr(guest_IA_next_instr)); 11114 dis_res->whatNext = Dis_StopHere; 11115 dis_res->jk_StopHere = Ijk_InvalICache; 11116 break; 11117 } 11118 11119 case 0xd200000000000000ULL: 11120 /* special case MVC */ 11121 s390_irgen_EX_SS(r1, addr2, s390_irgen_MVC_EX, 64); 11122 return "ex@mvc"; 11123 11124 case 0xd500000000000000ULL: 11125 /* special case CLC */ 11126 s390_irgen_EX_SS(r1, addr2, s390_irgen_CLC_EX, 64); 11127 return "ex@clc"; 11128 11129 case 0xd700000000000000ULL: 11130 /* special case XC */ 11131 s390_irgen_EX_SS(r1, addr2, s390_irgen_XC_EX, 32); 11132 return "ex@xc"; 11133 11134 case 0xd600000000000000ULL: 11135 /* special case OC */ 11136 s390_irgen_EX_SS(r1, addr2, s390_irgen_OC_EX, 32); 11137 return "ex@oc"; 11138 11139 case 0xd400000000000000ULL: 11140 /* special case NC */ 11141 s390_irgen_EX_SS(r1, addr2, s390_irgen_NC_EX, 32); 11142 return "ex@nc"; 11143 11144 case 0xdc00000000000000ULL: 11145 /* special case TR */ 11146 s390_irgen_EX_SS(r1, addr2, s390_irgen_TR_EX, 64); 11147 return "ex@tr"; 11148 11149 case 0xe800000000000000ULL: 11150 /* special case MVCIN */ 11151 s390_irgen_EX_SS(r1, addr2, s390_irgen_MVCIN_EX, 64); 11152 return "ex@mvcin"; 11153 11154 default: 11155 { 11156 /* everything else will get a self checking prefix that also checks the 11157 register content */ 11158 IRDirty *d; 11159 UChar *bytes; 11160 IRTemp cond; 11161 IRTemp orperand; 11162 IRTemp torun; 11163 11164 cond = newTemp(Ity_I1); 11165 orperand = newTemp(Ity_I64); 11166 torun = newTemp(Ity_I64); 11167 11168 if (r1 == 0) 11169 assign(orperand, mkU64(0)); 11170 else 11171 assign(orperand, unop(Iop_8Uto64,get_gpr_b7(r1))); 11172 /* This code is going to be translated */ 11173 assign(torun, binop(Iop_Or64, load(Ity_I64, mkexpr(addr2)), 11174 binop(Iop_Shl64, mkexpr(orperand), mkU8(48)))); 11175 11176 /* Start with a check that saved code is still correct */ 11177 assign(cond, binop(Iop_CmpNE64, mkexpr(torun), 11178 mkU64(last_execute_target))); 11179 /* If not, save the new value */ 11180 d = unsafeIRDirty_0_N (0, "s390x_dirtyhelper_EX", &s390x_dirtyhelper_EX, 11181 mkIRExprVec_1(mkexpr(torun))); 11182 d->guard = mkexpr(cond); 11183 stmt(IRStmt_Dirty(d)); 11184 11185 /* and restart */ 11186 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_CMSTART), mkU64(guest_IA_curr_instr))); 11187 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_CMLEN), mkU64(4))); 11188 restart_if(mkexpr(cond)); 11189 11190 /* Now comes the actual translation */ 11191 bytes = (UChar *) &last_execute_target; 11192 s390_decode_and_irgen(bytes, ((((bytes[0] >> 6) + 1) >> 1) + 1) << 1, 11193 dis_res); 11194 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 11195 vex_printf(" which was executed by\n"); 11196 /* dont make useless translations in the next execute */ 11197 last_execute_target = 0; 11198 } 11199 } 11200 return "ex"; 11201 } 11202 11203 static const HChar * 11204 s390_irgen_EXRL(UChar r1, UInt offset) 11205 { 11206 IRTemp addr = newTemp(Ity_I64); 11207 /* we might save one round trip because we know the target */ 11208 if (!last_execute_target) 11209 last_execute_target = *(ULong *)(HWord) 11210 (guest_IA_curr_instr + offset * 2UL); 11211 assign(addr, mkU64(guest_IA_curr_instr + offset * 2UL)); 11212 s390_irgen_EX(r1, addr); 11213 return "exrl"; 11214 } 11215 11216 static const HChar * 11217 s390_irgen_IPM(UChar r1) 11218 { 11219 // As long as we dont support SPM, lets just assume 0 as program mask 11220 put_gpr_b4(r1, unop(Iop_32to8, binop(Iop_Or32, mkU32(0 /* program mask */), 11221 binop(Iop_Shl32, s390_call_calculate_cc(), mkU8(4))))); 11222 11223 return "ipm"; 11224 } 11225 11226 11227 static const HChar * 11228 s390_irgen_SRST(UChar r1, UChar r2) 11229 { 11230 IRTemp address = newTemp(Ity_I64); 11231 IRTemp next = newTemp(Ity_I64); 11232 IRTemp delim = newTemp(Ity_I8); 11233 IRTemp counter = newTemp(Ity_I64); 11234 IRTemp byte = newTemp(Ity_I8); 11235 11236 assign(address, get_gpr_dw0(r2)); 11237 assign(next, get_gpr_dw0(r1)); 11238 11239 assign(counter, get_counter_dw0()); 11240 put_counter_dw0(mkU64(0)); 11241 11242 // start = next? CC=2 and out r1 and r2 unchanged 11243 s390_cc_set(2); 11244 put_gpr_dw0(r2, binop(Iop_Sub64, mkexpr(address), mkexpr(counter))); 11245 next_insn_if(binop(Iop_CmpEQ64, mkexpr(address), mkexpr(next))); 11246 11247 assign(byte, load(Ity_I8, mkexpr(address))); 11248 assign(delim, get_gpr_b7(0)); 11249 11250 // byte = delim? CC=1, R1=address 11251 s390_cc_set(1); 11252 put_gpr_dw0(r1, mkexpr(address)); 11253 next_insn_if(binop(Iop_CmpEQ8, mkexpr(delim), mkexpr(byte))); 11254 11255 // else: all equal, no end yet, loop 11256 put_counter_dw0(binop(Iop_Add64, mkexpr(counter), mkU64(1))); 11257 put_gpr_dw0(r1, mkexpr(next)); 11258 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(address), mkU64(1))); 11259 11260 iterate(); 11261 11262 return "srst"; 11263 } 11264 11265 static const HChar * 11266 s390_irgen_CLST(UChar r1, UChar r2) 11267 { 11268 IRTemp address1 = newTemp(Ity_I64); 11269 IRTemp address2 = newTemp(Ity_I64); 11270 IRTemp end = newTemp(Ity_I8); 11271 IRTemp counter = newTemp(Ity_I64); 11272 IRTemp byte1 = newTemp(Ity_I8); 11273 IRTemp byte2 = newTemp(Ity_I8); 11274 11275 assign(address1, get_gpr_dw0(r1)); 11276 assign(address2, get_gpr_dw0(r2)); 11277 assign(end, get_gpr_b7(0)); 11278 assign(counter, get_counter_dw0()); 11279 put_counter_dw0(mkU64(0)); 11280 assign(byte1, load(Ity_I8, mkexpr(address1))); 11281 assign(byte2, load(Ity_I8, mkexpr(address2))); 11282 11283 // end in both? all equal, reset r1 and r2 to start values 11284 s390_cc_set(0); 11285 put_gpr_dw0(r1, binop(Iop_Sub64, mkexpr(address1), mkexpr(counter))); 11286 put_gpr_dw0(r2, binop(Iop_Sub64, mkexpr(address2), mkexpr(counter))); 11287 next_insn_if(binop(Iop_CmpEQ8, mkU8(0), 11288 binop(Iop_Or8, 11289 binop(Iop_Xor8, mkexpr(byte1), mkexpr(end)), 11290 binop(Iop_Xor8, mkexpr(byte2), mkexpr(end))))); 11291 11292 put_gpr_dw0(r1, mkexpr(address1)); 11293 put_gpr_dw0(r2, mkexpr(address2)); 11294 11295 // End found in string1 11296 s390_cc_set(1); 11297 next_insn_if(binop(Iop_CmpEQ8, mkexpr(end), mkexpr(byte1))); 11298 11299 // End found in string2 11300 s390_cc_set(2); 11301 next_insn_if(binop(Iop_CmpEQ8, mkexpr(end), mkexpr(byte2))); 11302 11303 // string1 < string2 11304 s390_cc_set(1); 11305 next_insn_if(binop(Iop_CmpLT32U, unop(Iop_8Uto32, mkexpr(byte1)), 11306 unop(Iop_8Uto32, mkexpr(byte2)))); 11307 11308 // string2 < string1 11309 s390_cc_set(2); 11310 next_insn_if(binop(Iop_CmpLT32U, unop(Iop_8Uto32, mkexpr(byte2)), 11311 unop(Iop_8Uto32, mkexpr(byte1)))); 11312 11313 // else: all equal, no end yet, loop 11314 put_counter_dw0(binop(Iop_Add64, mkexpr(counter), mkU64(1))); 11315 put_gpr_dw0(r1, binop(Iop_Add64, get_gpr_dw0(r1), mkU64(1))); 11316 put_gpr_dw0(r2, binop(Iop_Add64, get_gpr_dw0(r2), mkU64(1))); 11317 11318 iterate(); 11319 11320 return "clst"; 11321 } 11322 11323 static void 11324 s390_irgen_load_multiple_32bit(UChar r1, UChar r3, IRTemp op2addr) 11325 { 11326 UChar reg; 11327 IRTemp addr = newTemp(Ity_I64); 11328 11329 assign(addr, mkexpr(op2addr)); 11330 reg = r1; 11331 do { 11332 IRTemp old = addr; 11333 11334 reg %= 16; 11335 put_gpr_w1(reg, load(Ity_I32, mkexpr(addr))); 11336 addr = newTemp(Ity_I64); 11337 assign(addr, binop(Iop_Add64, mkexpr(old), mkU64(4))); 11338 reg++; 11339 } while (reg != (r3 + 1)); 11340 } 11341 11342 static const HChar * 11343 s390_irgen_LM(UChar r1, UChar r3, IRTemp op2addr) 11344 { 11345 s390_irgen_load_multiple_32bit(r1, r3, op2addr); 11346 11347 return "lm"; 11348 } 11349 11350 static const HChar * 11351 s390_irgen_LMY(UChar r1, UChar r3, IRTemp op2addr) 11352 { 11353 s390_irgen_load_multiple_32bit(r1, r3, op2addr); 11354 11355 return "lmy"; 11356 } 11357 11358 static const HChar * 11359 s390_irgen_LMH(UChar r1, UChar r3, IRTemp op2addr) 11360 { 11361 UChar reg; 11362 IRTemp addr = newTemp(Ity_I64); 11363 11364 assign(addr, mkexpr(op2addr)); 11365 reg = r1; 11366 do { 11367 IRTemp old = addr; 11368 11369 reg %= 16; 11370 put_gpr_w0(reg, load(Ity_I32, mkexpr(addr))); 11371 addr = newTemp(Ity_I64); 11372 assign(addr, binop(Iop_Add64, mkexpr(old), mkU64(4))); 11373 reg++; 11374 } while (reg != (r3 + 1)); 11375 11376 return "lmh"; 11377 } 11378 11379 static const HChar * 11380 s390_irgen_LMG(UChar r1, UChar r3, IRTemp op2addr) 11381 { 11382 UChar reg; 11383 IRTemp addr = newTemp(Ity_I64); 11384 11385 assign(addr, mkexpr(op2addr)); 11386 reg = r1; 11387 do { 11388 IRTemp old = addr; 11389 11390 reg %= 16; 11391 put_gpr_dw0(reg, load(Ity_I64, mkexpr(addr))); 11392 addr = newTemp(Ity_I64); 11393 assign(addr, binop(Iop_Add64, mkexpr(old), mkU64(8))); 11394 reg++; 11395 } while (reg != (r3 + 1)); 11396 11397 return "lmg"; 11398 } 11399 11400 static void 11401 s390_irgen_store_multiple_32bit(UChar r1, UChar r3, IRTemp op2addr) 11402 { 11403 UChar reg; 11404 IRTemp addr = newTemp(Ity_I64); 11405 11406 assign(addr, mkexpr(op2addr)); 11407 reg = r1; 11408 do { 11409 IRTemp old = addr; 11410 11411 reg %= 16; 11412 store(mkexpr(addr), get_gpr_w1(reg)); 11413 addr = newTemp(Ity_I64); 11414 assign(addr, binop(Iop_Add64, mkexpr(old), mkU64(4))); 11415 reg++; 11416 } while( reg != (r3 + 1)); 11417 } 11418 11419 static const HChar * 11420 s390_irgen_STM(UChar r1, UChar r3, IRTemp op2addr) 11421 { 11422 s390_irgen_store_multiple_32bit(r1, r3, op2addr); 11423 11424 return "stm"; 11425 } 11426 11427 static const HChar * 11428 s390_irgen_STMY(UChar r1, UChar r3, IRTemp op2addr) 11429 { 11430 s390_irgen_store_multiple_32bit(r1, r3, op2addr); 11431 11432 return "stmy"; 11433 } 11434 11435 static const HChar * 11436 s390_irgen_STMH(UChar r1, UChar r3, IRTemp op2addr) 11437 { 11438 UChar reg; 11439 IRTemp addr = newTemp(Ity_I64); 11440 11441 assign(addr, mkexpr(op2addr)); 11442 reg = r1; 11443 do { 11444 IRTemp old = addr; 11445 11446 reg %= 16; 11447 store(mkexpr(addr), get_gpr_w0(reg)); 11448 addr = newTemp(Ity_I64); 11449 assign(addr, binop(Iop_Add64, mkexpr(old), mkU64(4))); 11450 reg++; 11451 } while( reg != (r3 + 1)); 11452 11453 return "stmh"; 11454 } 11455 11456 static const HChar * 11457 s390_irgen_STMG(UChar r1, UChar r3, IRTemp op2addr) 11458 { 11459 UChar reg; 11460 IRTemp addr = newTemp(Ity_I64); 11461 11462 assign(addr, mkexpr(op2addr)); 11463 reg = r1; 11464 do { 11465 IRTemp old = addr; 11466 11467 reg %= 16; 11468 store(mkexpr(addr), get_gpr_dw0(reg)); 11469 addr = newTemp(Ity_I64); 11470 assign(addr, binop(Iop_Add64, mkexpr(old), mkU64(8))); 11471 reg++; 11472 } while( reg != (r3 + 1)); 11473 11474 return "stmg"; 11475 } 11476 11477 static void 11478 s390_irgen_xonc(IROp op, IRTemp length, IRTemp start1, IRTemp start2) 11479 { 11480 IRTemp old1 = newTemp(Ity_I8); 11481 IRTemp old2 = newTemp(Ity_I8); 11482 IRTemp new1 = newTemp(Ity_I8); 11483 IRTemp counter = newTemp(Ity_I32); 11484 IRTemp addr1 = newTemp(Ity_I64); 11485 11486 assign(counter, get_counter_w0()); 11487 11488 assign(addr1, binop(Iop_Add64, mkexpr(start1), 11489 unop(Iop_32Uto64, mkexpr(counter)))); 11490 11491 assign(old1, load(Ity_I8, mkexpr(addr1))); 11492 assign(old2, load(Ity_I8, binop(Iop_Add64, mkexpr(start2), 11493 unop(Iop_32Uto64,mkexpr(counter))))); 11494 assign(new1, binop(op, mkexpr(old1), mkexpr(old2))); 11495 11496 /* Special case: xc is used to zero memory */ 11497 if (op == Iop_Xor8) { 11498 store(mkexpr(addr1), 11499 mkite(binop(Iop_CmpEQ64, mkexpr(start1), mkexpr(start2)), 11500 mkU8(0), mkexpr(new1))); 11501 } else 11502 store(mkexpr(addr1), mkexpr(new1)); 11503 put_counter_w1(binop(Iop_Or32, unop(Iop_8Uto32, mkexpr(new1)), 11504 get_counter_w1())); 11505 11506 /* Check for end of field */ 11507 put_counter_w0(binop(Iop_Add32, mkexpr(counter), mkU32(1))); 11508 iterate_if(binop(Iop_CmpNE32, mkexpr(counter), mkexpr(length))); 11509 s390_cc_thunk_put1(S390_CC_OP_BITWISE, mktemp(Ity_I32, get_counter_w1()), 11510 False); 11511 put_counter_dw0(mkU64(0)); 11512 } 11513 11514 static const HChar * 11515 s390_irgen_XC(UChar length, IRTemp start1, IRTemp start2) 11516 { 11517 IRTemp len = newTemp(Ity_I32); 11518 11519 assign(len, mkU32(length)); 11520 s390_irgen_xonc(Iop_Xor8, len, start1, start2); 11521 11522 return "xc"; 11523 } 11524 11525 static void 11526 s390_irgen_XC_sameloc(UChar length, UChar b, UShort d) 11527 { 11528 IRTemp counter = newTemp(Ity_I32); 11529 IRTemp start = newTemp(Ity_I64); 11530 IRTemp addr = newTemp(Ity_I64); 11531 11532 assign(start, 11533 binop(Iop_Add64, mkU64(d), b != 0 ? get_gpr_dw0(b) : mkU64(0))); 11534 11535 if (length < 8) { 11536 UInt i; 11537 11538 for (i = 0; i <= length; ++i) { 11539 store(binop(Iop_Add64, mkexpr(start), mkU64(i)), mkU8(0)); 11540 } 11541 } else { 11542 assign(counter, get_counter_w0()); 11543 11544 assign(addr, binop(Iop_Add64, mkexpr(start), 11545 unop(Iop_32Uto64, mkexpr(counter)))); 11546 11547 store(mkexpr(addr), mkU8(0)); 11548 11549 /* Check for end of field */ 11550 put_counter_w0(binop(Iop_Add32, mkexpr(counter), mkU32(1))); 11551 iterate_if(binop(Iop_CmpNE32, mkexpr(counter), mkU32(length))); 11552 11553 /* Reset counter */ 11554 put_counter_dw0(mkU64(0)); 11555 } 11556 11557 s390_cc_thunk_put1(S390_CC_OP_BITWISE, mktemp(Ity_I32, mkU32(0)), False); 11558 11559 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 11560 s390_disasm(ENC3(MNM, UDLB, UDXB), "xc", d, length, b, d, 0, b); 11561 } 11562 11563 static const HChar * 11564 s390_irgen_NC(UChar length, IRTemp start1, IRTemp start2) 11565 { 11566 IRTemp len = newTemp(Ity_I32); 11567 11568 assign(len, mkU32(length)); 11569 s390_irgen_xonc(Iop_And8, len, start1, start2); 11570 11571 return "nc"; 11572 } 11573 11574 static const HChar * 11575 s390_irgen_OC(UChar length, IRTemp start1, IRTemp start2) 11576 { 11577 IRTemp len = newTemp(Ity_I32); 11578 11579 assign(len, mkU32(length)); 11580 s390_irgen_xonc(Iop_Or8, len, start1, start2); 11581 11582 return "oc"; 11583 } 11584 11585 11586 static const HChar * 11587 s390_irgen_MVC(UChar length, IRTemp start1, IRTemp start2) 11588 { 11589 IRTemp len = newTemp(Ity_I64); 11590 11591 assign(len, mkU64(length)); 11592 s390_irgen_MVC_EX(len, start1, start2); 11593 11594 return "mvc"; 11595 } 11596 11597 static const HChar * 11598 s390_irgen_MVCIN(UChar length, IRTemp start1, IRTemp start2) 11599 { 11600 IRTemp len = newTemp(Ity_I64); 11601 11602 assign(len, mkU64(length)); 11603 s390_irgen_MVCIN_EX(len, start1, start2); 11604 11605 return "mvcin"; 11606 } 11607 11608 static const HChar * 11609 s390_irgen_MVCL(UChar r1, UChar r2) 11610 { 11611 IRTemp addr1 = newTemp(Ity_I64); 11612 IRTemp addr2 = newTemp(Ity_I64); 11613 IRTemp addr2_load = newTemp(Ity_I64); 11614 IRTemp r1p1 = newTemp(Ity_I32); /* contents of r1 + 1 */ 11615 IRTemp r2p1 = newTemp(Ity_I32); /* contents of r2 + 1 */ 11616 IRTemp len1 = newTemp(Ity_I32); 11617 IRTemp len2 = newTemp(Ity_I32); 11618 IRTemp pad = newTemp(Ity_I8); 11619 IRTemp single = newTemp(Ity_I8); 11620 11621 assign(addr1, get_gpr_dw0(r1)); 11622 assign(r1p1, get_gpr_w1(r1 + 1)); 11623 assign(len1, binop(Iop_And32, mkexpr(r1p1), mkU32(0x00ffffff))); 11624 assign(addr2, get_gpr_dw0(r2)); 11625 assign(r2p1, get_gpr_w1(r2 + 1)); 11626 assign(len2, binop(Iop_And32, mkexpr(r2p1), mkU32(0x00ffffff))); 11627 assign(pad, get_gpr_b4(r2 + 1)); 11628 11629 /* len1 == 0 ? */ 11630 s390_cc_thunk_put2(S390_CC_OP_UNSIGNED_COMPARE, len1, len2, False); 11631 next_insn_if(binop(Iop_CmpEQ32, mkexpr(len1), mkU32(0))); 11632 11633 /* Check for destructive overlap: 11634 addr1 > addr2 && addr2 + len1 > addr1 && (addr2 + len2) > addr1 */ 11635 s390_cc_set(3); 11636 IRTemp cond1 = newTemp(Ity_I32); 11637 assign(cond1, unop(Iop_1Uto32, 11638 binop(Iop_CmpLT64U, mkexpr(addr2), mkexpr(addr1)))); 11639 IRTemp cond2 = newTemp(Ity_I32); 11640 assign(cond2, unop(Iop_1Uto32, 11641 binop(Iop_CmpLT64U, mkexpr(addr1), 11642 binop(Iop_Add64, mkexpr(addr2), 11643 unop(Iop_32Uto64, mkexpr(len1)))))); 11644 IRTemp cond3 = newTemp(Ity_I32); 11645 assign(cond3, unop(Iop_1Uto32, 11646 binop(Iop_CmpLT64U, 11647 mkexpr(addr1), 11648 binop(Iop_Add64, mkexpr(addr2), 11649 unop(Iop_32Uto64, mkexpr(len2)))))); 11650 11651 next_insn_if(binop(Iop_CmpEQ32, 11652 binop(Iop_And32, 11653 binop(Iop_And32, mkexpr(cond1), mkexpr(cond2)), 11654 mkexpr(cond3)), 11655 mkU32(1))); 11656 11657 /* See s390_irgen_CLCL for explanation why we cannot load directly 11658 and need two steps. */ 11659 assign(addr2_load, 11660 mkite(binop(Iop_CmpEQ32, mkexpr(len2), mkU32(0)), 11661 mkU64(guest_IA_curr_instr), mkexpr(addr2))); 11662 assign(single, 11663 mkite(binop(Iop_CmpEQ32, mkexpr(len2), mkU32(0)), 11664 mkexpr(pad), load(Ity_I8, mkexpr(addr2_load)))); 11665 11666 store(mkexpr(addr1), mkexpr(single)); 11667 11668 /* Update addr1 and len1 */ 11669 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(addr1), mkU64(1))); 11670 put_gpr_w1(r1 + 1, binop(Iop_Sub32, mkexpr(r1p1), mkU32(1))); 11671 11672 /* Update addr2 and len2 */ 11673 put_gpr_dw0(r2, 11674 mkite(binop(Iop_CmpEQ32, mkexpr(len2), mkU32(0)), 11675 mkexpr(addr2), 11676 binop(Iop_Add64, mkexpr(addr2), mkU64(1)))); 11677 11678 /* When updating len2 we must not modify bits (r2+1)[0:39] */ 11679 put_gpr_w1(r2 + 1, 11680 mkite(binop(Iop_CmpEQ32, mkexpr(len2), mkU32(0)), 11681 binop(Iop_And32, mkexpr(r2p1), mkU32(0xFF000000u)), 11682 binop(Iop_Sub32, mkexpr(r2p1), mkU32(1)))); 11683 11684 s390_cc_thunk_put2(S390_CC_OP_UNSIGNED_COMPARE, len1, len2, False); 11685 iterate_if(binop(Iop_CmpNE32, mkexpr(len1), mkU32(1))); 11686 11687 return "mvcl"; 11688 } 11689 11690 11691 static const HChar * 11692 s390_irgen_MVCLE(UChar r1, UChar r3, IRTemp pad2) 11693 { 11694 IRTemp addr1, addr3, addr3_load, len1, len3, single; 11695 11696 addr1 = newTemp(Ity_I64); 11697 addr3 = newTemp(Ity_I64); 11698 addr3_load = newTemp(Ity_I64); 11699 len1 = newTemp(Ity_I64); 11700 len3 = newTemp(Ity_I64); 11701 single = newTemp(Ity_I8); 11702 11703 assign(addr1, get_gpr_dw0(r1)); 11704 assign(len1, get_gpr_dw0(r1 + 1)); 11705 assign(addr3, get_gpr_dw0(r3)); 11706 assign(len3, get_gpr_dw0(r3 + 1)); 11707 11708 // len1 == 0 ? 11709 s390_cc_thunk_put2(S390_CC_OP_UNSIGNED_COMPARE, len1, len3, False); 11710 next_insn_if(binop(Iop_CmpEQ64,mkexpr(len1), mkU64(0))); 11711 11712 /* This is a hack to prevent mvcle from reading from addr3 if it 11713 should read from the pad. Since the pad has no address, just 11714 read from the instruction, we discard that anyway */ 11715 assign(addr3_load, 11716 mkite(binop(Iop_CmpEQ64, mkexpr(len3), mkU64(0)), 11717 mkU64(guest_IA_curr_instr), mkexpr(addr3))); 11718 11719 assign(single, 11720 mkite(binop(Iop_CmpEQ64, mkexpr(len3), mkU64(0)), 11721 unop(Iop_64to8, mkexpr(pad2)), 11722 load(Ity_I8, mkexpr(addr3_load)))); 11723 store(mkexpr(addr1), mkexpr(single)); 11724 11725 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(addr1), mkU64(1))); 11726 11727 put_gpr_dw0(r1 + 1, binop(Iop_Sub64, mkexpr(len1), mkU64(1))); 11728 11729 put_gpr_dw0(r3, 11730 mkite(binop(Iop_CmpEQ64, mkexpr(len3), mkU64(0)), 11731 mkexpr(addr3), 11732 binop(Iop_Add64, mkexpr(addr3), mkU64(1)))); 11733 11734 put_gpr_dw0(r3 + 1, 11735 mkite(binop(Iop_CmpEQ64, mkexpr(len3), mkU64(0)), 11736 mkU64(0), binop(Iop_Sub64, mkexpr(len3), mkU64(1)))); 11737 11738 s390_cc_thunk_put2(S390_CC_OP_UNSIGNED_COMPARE, len1, len3, False); 11739 iterate_if(binop(Iop_CmpNE64, mkexpr(len1), mkU64(1))); 11740 11741 return "mvcle"; 11742 } 11743 11744 static const HChar * 11745 s390_irgen_MVST(UChar r1, UChar r2) 11746 { 11747 IRTemp addr1 = newTemp(Ity_I64); 11748 IRTemp addr2 = newTemp(Ity_I64); 11749 IRTemp end = newTemp(Ity_I8); 11750 IRTemp byte = newTemp(Ity_I8); 11751 IRTemp counter = newTemp(Ity_I64); 11752 11753 assign(addr1, get_gpr_dw0(r1)); 11754 assign(addr2, get_gpr_dw0(r2)); 11755 assign(counter, get_counter_dw0()); 11756 assign(end, get_gpr_b7(0)); 11757 assign(byte, load(Ity_I8, binop(Iop_Add64, mkexpr(addr2),mkexpr(counter)))); 11758 store(binop(Iop_Add64,mkexpr(addr1),mkexpr(counter)), mkexpr(byte)); 11759 11760 // We use unlimited as cpu-determined number 11761 put_counter_dw0(binop(Iop_Add64, mkexpr(counter), mkU64(1))); 11762 iterate_if(binop(Iop_CmpNE8, mkexpr(end), mkexpr(byte))); 11763 11764 // and always set cc=1 at the end + update r1 11765 s390_cc_set(1); 11766 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(addr1), mkexpr(counter))); 11767 put_counter_dw0(mkU64(0)); 11768 11769 return "mvst"; 11770 } 11771 11772 static void 11773 s390_irgen_divide_64to32(IROp op, UChar r1, IRTemp op2) 11774 { 11775 IRTemp op1 = newTemp(Ity_I64); 11776 IRTemp result = newTemp(Ity_I64); 11777 11778 assign(op1, binop(Iop_32HLto64, 11779 get_gpr_w1(r1), // high 32 bits 11780 get_gpr_w1(r1 + 1))); // low 32 bits 11781 assign(result, binop(op, mkexpr(op1), mkexpr(op2))); 11782 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); // remainder 11783 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); // quotient 11784 } 11785 11786 static void 11787 s390_irgen_divide_128to64(IROp op, UChar r1, IRTemp op2) 11788 { 11789 IRTemp op1 = newTemp(Ity_I128); 11790 IRTemp result = newTemp(Ity_I128); 11791 11792 assign(op1, binop(Iop_64HLto128, 11793 get_gpr_dw0(r1), // high 64 bits 11794 get_gpr_dw0(r1 + 1))); // low 64 bits 11795 assign(result, binop(op, mkexpr(op1), mkexpr(op2))); 11796 put_gpr_dw0(r1, unop(Iop_128HIto64, mkexpr(result))); // remainder 11797 put_gpr_dw0(r1 + 1, unop(Iop_128to64, mkexpr(result))); // quotient 11798 } 11799 11800 static void 11801 s390_irgen_divide_64to64(IROp op, UChar r1, IRTemp op2) 11802 { 11803 IRTemp op1 = newTemp(Ity_I64); 11804 IRTemp result = newTemp(Ity_I128); 11805 11806 assign(op1, get_gpr_dw0(r1 + 1)); 11807 assign(result, binop(op, mkexpr(op1), mkexpr(op2))); 11808 put_gpr_dw0(r1, unop(Iop_128HIto64, mkexpr(result))); // remainder 11809 put_gpr_dw0(r1 + 1, unop(Iop_128to64, mkexpr(result))); // quotient 11810 } 11811 11812 static const HChar * 11813 s390_irgen_DR(UChar r1, UChar r2) 11814 { 11815 IRTemp op2 = newTemp(Ity_I32); 11816 11817 assign(op2, get_gpr_w1(r2)); 11818 11819 s390_irgen_divide_64to32(Iop_DivModS64to32, r1, op2); 11820 11821 return "dr"; 11822 } 11823 11824 static const HChar * 11825 s390_irgen_D(UChar r1, IRTemp op2addr) 11826 { 11827 IRTemp op2 = newTemp(Ity_I32); 11828 11829 assign(op2, load(Ity_I32, mkexpr(op2addr))); 11830 11831 s390_irgen_divide_64to32(Iop_DivModS64to32, r1, op2); 11832 11833 return "d"; 11834 } 11835 11836 static const HChar * 11837 s390_irgen_DLR(UChar r1, UChar r2) 11838 { 11839 IRTemp op2 = newTemp(Ity_I32); 11840 11841 assign(op2, get_gpr_w1(r2)); 11842 11843 s390_irgen_divide_64to32(Iop_DivModU64to32, r1, op2); 11844 11845 return "dlr"; 11846 } 11847 11848 static const HChar * 11849 s390_irgen_DL(UChar r1, IRTemp op2addr) 11850 { 11851 IRTemp op2 = newTemp(Ity_I32); 11852 11853 assign(op2, load(Ity_I32, mkexpr(op2addr))); 11854 11855 s390_irgen_divide_64to32(Iop_DivModU64to32, r1, op2); 11856 11857 return "dl"; 11858 } 11859 11860 static const HChar * 11861 s390_irgen_DLG(UChar r1, IRTemp op2addr) 11862 { 11863 IRTemp op2 = newTemp(Ity_I64); 11864 11865 assign(op2, load(Ity_I64, mkexpr(op2addr))); 11866 11867 s390_irgen_divide_128to64(Iop_DivModU128to64, r1, op2); 11868 11869 return "dlg"; 11870 } 11871 11872 static const HChar * 11873 s390_irgen_DLGR(UChar r1, UChar r2) 11874 { 11875 IRTemp op2 = newTemp(Ity_I64); 11876 11877 assign(op2, get_gpr_dw0(r2)); 11878 11879 s390_irgen_divide_128to64(Iop_DivModU128to64, r1, op2); 11880 11881 return "dlgr"; 11882 } 11883 11884 static const HChar * 11885 s390_irgen_DSGR(UChar r1, UChar r2) 11886 { 11887 IRTemp op2 = newTemp(Ity_I64); 11888 11889 assign(op2, get_gpr_dw0(r2)); 11890 11891 s390_irgen_divide_64to64(Iop_DivModS64to64, r1, op2); 11892 11893 return "dsgr"; 11894 } 11895 11896 static const HChar * 11897 s390_irgen_DSG(UChar r1, IRTemp op2addr) 11898 { 11899 IRTemp op2 = newTemp(Ity_I64); 11900 11901 assign(op2, load(Ity_I64, mkexpr(op2addr))); 11902 11903 s390_irgen_divide_64to64(Iop_DivModS64to64, r1, op2); 11904 11905 return "dsg"; 11906 } 11907 11908 static const HChar * 11909 s390_irgen_DSGFR(UChar r1, UChar r2) 11910 { 11911 IRTemp op2 = newTemp(Ity_I64); 11912 11913 assign(op2, unop(Iop_32Sto64, get_gpr_w1(r2))); 11914 11915 s390_irgen_divide_64to64(Iop_DivModS64to64, r1, op2); 11916 11917 return "dsgfr"; 11918 } 11919 11920 static const HChar * 11921 s390_irgen_DSGF(UChar r1, IRTemp op2addr) 11922 { 11923 IRTemp op2 = newTemp(Ity_I64); 11924 11925 assign(op2, unop(Iop_32Sto64, load(Ity_I32, mkexpr(op2addr)))); 11926 11927 s390_irgen_divide_64to64(Iop_DivModS64to64, r1, op2); 11928 11929 return "dsgf"; 11930 } 11931 11932 static void 11933 s390_irgen_load_ar_multiple(UChar r1, UChar r3, IRTemp op2addr) 11934 { 11935 UChar reg; 11936 IRTemp addr = newTemp(Ity_I64); 11937 11938 assign(addr, mkexpr(op2addr)); 11939 reg = r1; 11940 do { 11941 IRTemp old = addr; 11942 11943 reg %= 16; 11944 put_ar_w0(reg, load(Ity_I32, mkexpr(addr))); 11945 addr = newTemp(Ity_I64); 11946 assign(addr, binop(Iop_Add64, mkexpr(old), mkU64(4))); 11947 reg++; 11948 } while (reg != (r3 + 1)); 11949 } 11950 11951 static const HChar * 11952 s390_irgen_LAM(UChar r1, UChar r3, IRTemp op2addr) 11953 { 11954 s390_irgen_load_ar_multiple(r1, r3, op2addr); 11955 11956 return "lam"; 11957 } 11958 11959 static const HChar * 11960 s390_irgen_LAMY(UChar r1, UChar r3, IRTemp op2addr) 11961 { 11962 s390_irgen_load_ar_multiple(r1, r3, op2addr); 11963 11964 return "lamy"; 11965 } 11966 11967 static void 11968 s390_irgen_store_ar_multiple(UChar r1, UChar r3, IRTemp op2addr) 11969 { 11970 UChar reg; 11971 IRTemp addr = newTemp(Ity_I64); 11972 11973 assign(addr, mkexpr(op2addr)); 11974 reg = r1; 11975 do { 11976 IRTemp old = addr; 11977 11978 reg %= 16; 11979 store(mkexpr(addr), get_ar_w0(reg)); 11980 addr = newTemp(Ity_I64); 11981 assign(addr, binop(Iop_Add64, mkexpr(old), mkU64(4))); 11982 reg++; 11983 } while (reg != (r3 + 1)); 11984 } 11985 11986 static const HChar * 11987 s390_irgen_STAM(UChar r1, UChar r3, IRTemp op2addr) 11988 { 11989 s390_irgen_store_ar_multiple(r1, r3, op2addr); 11990 11991 return "stam"; 11992 } 11993 11994 static const HChar * 11995 s390_irgen_STAMY(UChar r1, UChar r3, IRTemp op2addr) 11996 { 11997 s390_irgen_store_ar_multiple(r1, r3, op2addr); 11998 11999 return "stamy"; 12000 } 12001 12002 12003 /* Implementation for 32-bit compare-and-swap */ 12004 static void 12005 s390_irgen_cas_32(UChar r1, UChar r3, IRTemp op2addr) 12006 { 12007 IRCAS *cas; 12008 IRTemp op1 = newTemp(Ity_I32); 12009 IRTemp old_mem = newTemp(Ity_I32); 12010 IRTemp op3 = newTemp(Ity_I32); 12011 IRTemp result = newTemp(Ity_I32); 12012 IRTemp nequal = newTemp(Ity_I1); 12013 12014 assign(op1, get_gpr_w1(r1)); 12015 assign(op3, get_gpr_w1(r3)); 12016 12017 /* The first and second operands are compared. If they are equal, 12018 the third operand is stored at the second- operand location. */ 12019 cas = mkIRCAS(IRTemp_INVALID, old_mem, 12020 Iend_BE, mkexpr(op2addr), 12021 NULL, mkexpr(op1), /* expected value */ 12022 NULL, mkexpr(op3) /* new value */); 12023 stmt(IRStmt_CAS(cas)); 12024 12025 /* Set CC. Operands compared equal -> 0, else 1. */ 12026 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(old_mem))); 12027 s390_cc_thunk_put1(S390_CC_OP_BITWISE, result, False); 12028 12029 /* If operands were equal (cc == 0) just store the old value op1 in r1. 12030 Otherwise, store the old_value from memory in r1 and yield. */ 12031 assign(nequal, binop(Iop_CmpNE32, s390_call_calculate_cc(), mkU32(0))); 12032 put_gpr_w1(r1, mkite(mkexpr(nequal), mkexpr(old_mem), mkexpr(op1))); 12033 yield_if(mkexpr(nequal)); 12034 } 12035 12036 static const HChar * 12037 s390_irgen_CS(UChar r1, UChar r3, IRTemp op2addr) 12038 { 12039 s390_irgen_cas_32(r1, r3, op2addr); 12040 12041 return "cs"; 12042 } 12043 12044 static const HChar * 12045 s390_irgen_CSY(UChar r1, UChar r3, IRTemp op2addr) 12046 { 12047 s390_irgen_cas_32(r1, r3, op2addr); 12048 12049 return "csy"; 12050 } 12051 12052 static const HChar * 12053 s390_irgen_CSG(UChar r1, UChar r3, IRTemp op2addr) 12054 { 12055 IRCAS *cas; 12056 IRTemp op1 = newTemp(Ity_I64); 12057 IRTemp old_mem = newTemp(Ity_I64); 12058 IRTemp op3 = newTemp(Ity_I64); 12059 IRTemp result = newTemp(Ity_I64); 12060 IRTemp nequal = newTemp(Ity_I1); 12061 12062 assign(op1, get_gpr_dw0(r1)); 12063 assign(op3, get_gpr_dw0(r3)); 12064 12065 /* The first and second operands are compared. If they are equal, 12066 the third operand is stored at the second- operand location. */ 12067 cas = mkIRCAS(IRTemp_INVALID, old_mem, 12068 Iend_BE, mkexpr(op2addr), 12069 NULL, mkexpr(op1), /* expected value */ 12070 NULL, mkexpr(op3) /* new value */); 12071 stmt(IRStmt_CAS(cas)); 12072 12073 /* Set CC. Operands compared equal -> 0, else 1. */ 12074 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(old_mem))); 12075 s390_cc_thunk_put1(S390_CC_OP_BITWISE, result, False); 12076 12077 /* If operands were equal (cc == 0) just store the old value op1 in r1. 12078 Otherwise, store the old_value from memory in r1 and yield. */ 12079 assign(nequal, binop(Iop_CmpNE32, s390_call_calculate_cc(), mkU32(0))); 12080 put_gpr_dw0(r1, mkite(mkexpr(nequal), mkexpr(old_mem), mkexpr(op1))); 12081 yield_if(mkexpr(nequal)); 12082 12083 return "csg"; 12084 } 12085 12086 /* Implementation for 32-bit compare-double-and-swap */ 12087 static void 12088 s390_irgen_cdas_32(UChar r1, UChar r3, IRTemp op2addr) 12089 { 12090 IRCAS *cas; 12091 IRTemp op1_high = newTemp(Ity_I32); 12092 IRTemp op1_low = newTemp(Ity_I32); 12093 IRTemp old_mem_high = newTemp(Ity_I32); 12094 IRTemp old_mem_low = newTemp(Ity_I32); 12095 IRTemp op3_high = newTemp(Ity_I32); 12096 IRTemp op3_low = newTemp(Ity_I32); 12097 IRTemp result = newTemp(Ity_I32); 12098 IRTemp nequal = newTemp(Ity_I1); 12099 12100 assign(op1_high, get_gpr_w1(r1)); 12101 assign(op1_low, get_gpr_w1(r1+1)); 12102 assign(op3_high, get_gpr_w1(r3)); 12103 assign(op3_low, get_gpr_w1(r3+1)); 12104 12105 /* The first and second operands are compared. If they are equal, 12106 the third operand is stored at the second-operand location. */ 12107 cas = mkIRCAS(old_mem_high, old_mem_low, 12108 Iend_BE, mkexpr(op2addr), 12109 mkexpr(op1_high), mkexpr(op1_low), /* expected value */ 12110 mkexpr(op3_high), mkexpr(op3_low) /* new value */); 12111 stmt(IRStmt_CAS(cas)); 12112 12113 /* Set CC. Operands compared equal -> 0, else 1. */ 12114 assign(result, unop(Iop_1Uto32, 12115 binop(Iop_CmpNE32, 12116 binop(Iop_Or32, 12117 binop(Iop_Xor32, mkexpr(op1_high), mkexpr(old_mem_high)), 12118 binop(Iop_Xor32, mkexpr(op1_low), mkexpr(old_mem_low))), 12119 mkU32(0)))); 12120 12121 s390_cc_thunk_put1(S390_CC_OP_BITWISE, result, False); 12122 12123 /* If operands were equal (cc == 0) just store the old value op1 in r1. 12124 Otherwise, store the old_value from memory in r1 and yield. */ 12125 assign(nequal, binop(Iop_CmpNE32, s390_call_calculate_cc(), mkU32(0))); 12126 put_gpr_w1(r1, mkite(mkexpr(nequal), mkexpr(old_mem_high), mkexpr(op1_high))); 12127 put_gpr_w1(r1+1, mkite(mkexpr(nequal), mkexpr(old_mem_low), mkexpr(op1_low))); 12128 yield_if(mkexpr(nequal)); 12129 } 12130 12131 static const HChar * 12132 s390_irgen_CDS(UChar r1, UChar r3, IRTemp op2addr) 12133 { 12134 s390_irgen_cdas_32(r1, r3, op2addr); 12135 12136 return "cds"; 12137 } 12138 12139 static const HChar * 12140 s390_irgen_CDSY(UChar r1, UChar r3, IRTemp op2addr) 12141 { 12142 s390_irgen_cdas_32(r1, r3, op2addr); 12143 12144 return "cdsy"; 12145 } 12146 12147 static const HChar * 12148 s390_irgen_CDSG(UChar r1, UChar r3, IRTemp op2addr) 12149 { 12150 IRCAS *cas; 12151 IRTemp op1_high = newTemp(Ity_I64); 12152 IRTemp op1_low = newTemp(Ity_I64); 12153 IRTemp old_mem_high = newTemp(Ity_I64); 12154 IRTemp old_mem_low = newTemp(Ity_I64); 12155 IRTemp op3_high = newTemp(Ity_I64); 12156 IRTemp op3_low = newTemp(Ity_I64); 12157 IRTemp result = newTemp(Ity_I64); 12158 IRTemp nequal = newTemp(Ity_I1); 12159 12160 assign(op1_high, get_gpr_dw0(r1)); 12161 assign(op1_low, get_gpr_dw0(r1+1)); 12162 assign(op3_high, get_gpr_dw0(r3)); 12163 assign(op3_low, get_gpr_dw0(r3+1)); 12164 12165 /* The first and second operands are compared. If they are equal, 12166 the third operand is stored at the second-operand location. */ 12167 cas = mkIRCAS(old_mem_high, old_mem_low, 12168 Iend_BE, mkexpr(op2addr), 12169 mkexpr(op1_high), mkexpr(op1_low), /* expected value */ 12170 mkexpr(op3_high), mkexpr(op3_low) /* new value */); 12171 stmt(IRStmt_CAS(cas)); 12172 12173 /* Set CC. Operands compared equal -> 0, else 1. */ 12174 assign(result, unop(Iop_1Uto64, 12175 binop(Iop_CmpNE64, 12176 binop(Iop_Or64, 12177 binop(Iop_Xor64, mkexpr(op1_high), mkexpr(old_mem_high)), 12178 binop(Iop_Xor64, mkexpr(op1_low), mkexpr(old_mem_low))), 12179 mkU64(0)))); 12180 12181 s390_cc_thunk_put1(S390_CC_OP_BITWISE, result, False); 12182 12183 /* If operands were equal (cc == 0) just store the old value op1 in r1. 12184 Otherwise, store the old_value from memory in r1 and yield. */ 12185 assign(nequal, binop(Iop_CmpNE32, s390_call_calculate_cc(), mkU32(0))); 12186 put_gpr_dw0(r1, mkite(mkexpr(nequal), mkexpr(old_mem_high), mkexpr(op1_high))); 12187 put_gpr_dw0(r1+1, mkite(mkexpr(nequal), mkexpr(old_mem_low), mkexpr(op1_low))); 12188 yield_if(mkexpr(nequal)); 12189 12190 return "cdsg"; 12191 } 12192 12193 12194 /* Binary floating point */ 12195 12196 static const HChar * 12197 s390_irgen_AXBR(UChar r1, UChar r2) 12198 { 12199 IRTemp op1 = newTemp(Ity_F128); 12200 IRTemp op2 = newTemp(Ity_F128); 12201 IRTemp result = newTemp(Ity_F128); 12202 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12203 12204 assign(op1, get_fpr_pair(r1)); 12205 assign(op2, get_fpr_pair(r2)); 12206 assign(result, triop(Iop_AddF128, mkexpr(rounding_mode), mkexpr(op1), 12207 mkexpr(op2))); 12208 put_fpr_pair(r1, mkexpr(result)); 12209 12210 s390_cc_thunk_put1f128(S390_CC_OP_BFP_RESULT_128, result); 12211 12212 return "axbr"; 12213 } 12214 12215 static const HChar * 12216 s390_irgen_CEBR(UChar r1, UChar r2) 12217 { 12218 IRTemp op1 = newTemp(Ity_F32); 12219 IRTemp op2 = newTemp(Ity_F32); 12220 IRTemp cc_vex = newTemp(Ity_I32); 12221 IRTemp cc_s390 = newTemp(Ity_I32); 12222 12223 assign(op1, get_fpr_w0(r1)); 12224 assign(op2, get_fpr_w0(r2)); 12225 assign(cc_vex, binop(Iop_CmpF32, mkexpr(op1), mkexpr(op2))); 12226 12227 assign(cc_s390, convert_vex_bfpcc_to_s390(cc_vex)); 12228 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 12229 12230 return "cebr"; 12231 } 12232 12233 static const HChar * 12234 s390_irgen_CDBR(UChar r1, UChar r2) 12235 { 12236 IRTemp op1 = newTemp(Ity_F64); 12237 IRTemp op2 = newTemp(Ity_F64); 12238 IRTemp cc_vex = newTemp(Ity_I32); 12239 IRTemp cc_s390 = newTemp(Ity_I32); 12240 12241 assign(op1, get_fpr_dw0(r1)); 12242 assign(op2, get_fpr_dw0(r2)); 12243 assign(cc_vex, binop(Iop_CmpF64, mkexpr(op1), mkexpr(op2))); 12244 12245 assign(cc_s390, convert_vex_bfpcc_to_s390(cc_vex)); 12246 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 12247 12248 return "cdbr"; 12249 } 12250 12251 static const HChar * 12252 s390_irgen_CXBR(UChar r1, UChar r2) 12253 { 12254 IRTemp op1 = newTemp(Ity_F128); 12255 IRTemp op2 = newTemp(Ity_F128); 12256 IRTemp cc_vex = newTemp(Ity_I32); 12257 IRTemp cc_s390 = newTemp(Ity_I32); 12258 12259 assign(op1, get_fpr_pair(r1)); 12260 assign(op2, get_fpr_pair(r2)); 12261 assign(cc_vex, binop(Iop_CmpF128, mkexpr(op1), mkexpr(op2))); 12262 12263 assign(cc_s390, convert_vex_bfpcc_to_s390(cc_vex)); 12264 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 12265 12266 return "cxbr"; 12267 } 12268 12269 static const HChar * 12270 s390_irgen_CEB(UChar r1, IRTemp op2addr) 12271 { 12272 IRTemp op1 = newTemp(Ity_F32); 12273 IRTemp op2 = newTemp(Ity_F32); 12274 IRTemp cc_vex = newTemp(Ity_I32); 12275 IRTemp cc_s390 = newTemp(Ity_I32); 12276 12277 assign(op1, get_fpr_w0(r1)); 12278 assign(op2, load(Ity_F32, mkexpr(op2addr))); 12279 assign(cc_vex, binop(Iop_CmpF32, mkexpr(op1), mkexpr(op2))); 12280 12281 assign(cc_s390, convert_vex_bfpcc_to_s390(cc_vex)); 12282 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 12283 12284 return "ceb"; 12285 } 12286 12287 static const HChar * 12288 s390_irgen_CDB(UChar r1, IRTemp op2addr) 12289 { 12290 IRTemp op1 = newTemp(Ity_F64); 12291 IRTemp op2 = newTemp(Ity_F64); 12292 IRTemp cc_vex = newTemp(Ity_I32); 12293 IRTemp cc_s390 = newTemp(Ity_I32); 12294 12295 assign(op1, get_fpr_dw0(r1)); 12296 assign(op2, load(Ity_F64, mkexpr(op2addr))); 12297 assign(cc_vex, binop(Iop_CmpF64, mkexpr(op1), mkexpr(op2))); 12298 12299 assign(cc_s390, convert_vex_bfpcc_to_s390(cc_vex)); 12300 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 12301 12302 return "cdb"; 12303 } 12304 12305 static const HChar * 12306 s390_irgen_CXFBR(UChar m3 __attribute__((unused)), 12307 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 12308 { 12309 IRTemp op2 = newTemp(Ity_I32); 12310 12311 assign(op2, get_gpr_w1(r2)); 12312 put_fpr_pair(r1, unop(Iop_I32StoF128, mkexpr(op2))); 12313 12314 return "cxfbr"; 12315 } 12316 12317 static const HChar * 12318 s390_irgen_CXLFBR(UChar m3 __attribute__((unused)), 12319 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 12320 { 12321 if (! s390_host_has_fpext) { 12322 emulation_failure(EmFail_S390X_fpext); 12323 } else { 12324 IRTemp op2 = newTemp(Ity_I32); 12325 12326 assign(op2, get_gpr_w1(r2)); 12327 put_fpr_pair(r1, unop(Iop_I32UtoF128, mkexpr(op2))); 12328 } 12329 return "cxlfbr"; 12330 } 12331 12332 12333 static const HChar * 12334 s390_irgen_CXGBR(UChar m3 __attribute__((unused)), 12335 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 12336 { 12337 IRTemp op2 = newTemp(Ity_I64); 12338 12339 assign(op2, get_gpr_dw0(r2)); 12340 put_fpr_pair(r1, unop(Iop_I64StoF128, mkexpr(op2))); 12341 12342 return "cxgbr"; 12343 } 12344 12345 static const HChar * 12346 s390_irgen_CXLGBR(UChar m3 __attribute__((unused)), 12347 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 12348 { 12349 if (! s390_host_has_fpext) { 12350 emulation_failure(EmFail_S390X_fpext); 12351 } else { 12352 IRTemp op2 = newTemp(Ity_I64); 12353 12354 assign(op2, get_gpr_dw0(r2)); 12355 put_fpr_pair(r1, unop(Iop_I64UtoF128, mkexpr(op2))); 12356 } 12357 return "cxlgbr"; 12358 } 12359 12360 static const HChar * 12361 s390_irgen_CFXBR(UChar m3, UChar m4 __attribute__((unused)), 12362 UChar r1, UChar r2) 12363 { 12364 IRTemp op = newTemp(Ity_F128); 12365 IRTemp result = newTemp(Ity_I32); 12366 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 12367 12368 assign(op, get_fpr_pair(r2)); 12369 assign(result, binop(Iop_F128toI32S, mkexpr(rounding_mode), 12370 mkexpr(op))); 12371 put_gpr_w1(r1, mkexpr(result)); 12372 s390_cc_thunk_put1f128Z(S390_CC_OP_BFP_128_TO_INT_32, op, rounding_mode); 12373 12374 return "cfxbr"; 12375 } 12376 12377 static const HChar * 12378 s390_irgen_CLFXBR(UChar m3, UChar m4 __attribute__((unused)), 12379 UChar r1, UChar r2) 12380 { 12381 if (! s390_host_has_fpext) { 12382 emulation_failure(EmFail_S390X_fpext); 12383 } else { 12384 IRTemp op = newTemp(Ity_F128); 12385 IRTemp result = newTemp(Ity_I32); 12386 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 12387 12388 assign(op, get_fpr_pair(r2)); 12389 assign(result, binop(Iop_F128toI32U, mkexpr(rounding_mode), 12390 mkexpr(op))); 12391 put_gpr_w1(r1, mkexpr(result)); 12392 s390_cc_thunk_put1f128Z(S390_CC_OP_BFP_128_TO_UINT_32, op, rounding_mode); 12393 } 12394 return "clfxbr"; 12395 } 12396 12397 12398 static const HChar * 12399 s390_irgen_CGXBR(UChar m3, UChar m4 __attribute__((unused)), 12400 UChar r1, UChar r2) 12401 { 12402 IRTemp op = newTemp(Ity_F128); 12403 IRTemp result = newTemp(Ity_I64); 12404 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 12405 12406 assign(op, get_fpr_pair(r2)); 12407 assign(result, binop(Iop_F128toI64S, mkexpr(rounding_mode), 12408 mkexpr(op))); 12409 put_gpr_dw0(r1, mkexpr(result)); 12410 s390_cc_thunk_put1f128Z(S390_CC_OP_BFP_128_TO_INT_64, op, rounding_mode); 12411 12412 return "cgxbr"; 12413 } 12414 12415 static const HChar * 12416 s390_irgen_CLGXBR(UChar m3, UChar m4 __attribute__((unused)), 12417 UChar r1, UChar r2) 12418 { 12419 if (! s390_host_has_fpext) { 12420 emulation_failure(EmFail_S390X_fpext); 12421 } else { 12422 IRTemp op = newTemp(Ity_F128); 12423 IRTemp result = newTemp(Ity_I64); 12424 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 12425 12426 assign(op, get_fpr_pair(r2)); 12427 assign(result, binop(Iop_F128toI64U, mkexpr(rounding_mode), 12428 mkexpr(op))); 12429 put_gpr_dw0(r1, mkexpr(result)); 12430 s390_cc_thunk_put1f128Z(S390_CC_OP_BFP_128_TO_UINT_64, op, 12431 rounding_mode); 12432 } 12433 return "clgxbr"; 12434 } 12435 12436 static const HChar * 12437 s390_irgen_DXBR(UChar r1, UChar r2) 12438 { 12439 IRTemp op1 = newTemp(Ity_F128); 12440 IRTemp op2 = newTemp(Ity_F128); 12441 IRTemp result = newTemp(Ity_F128); 12442 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12443 12444 assign(op1, get_fpr_pair(r1)); 12445 assign(op2, get_fpr_pair(r2)); 12446 assign(result, triop(Iop_DivF128, mkexpr(rounding_mode), mkexpr(op1), 12447 mkexpr(op2))); 12448 put_fpr_pair(r1, mkexpr(result)); 12449 12450 return "dxbr"; 12451 } 12452 12453 static const HChar * 12454 s390_irgen_LTXBR(UChar r1, UChar r2) 12455 { 12456 IRTemp result = newTemp(Ity_F128); 12457 12458 assign(result, get_fpr_pair(r2)); 12459 put_fpr_pair(r1, mkexpr(result)); 12460 s390_cc_thunk_put1f128(S390_CC_OP_BFP_RESULT_128, result); 12461 12462 return "ltxbr"; 12463 } 12464 12465 static const HChar * 12466 s390_irgen_LCXBR(UChar r1, UChar r2) 12467 { 12468 IRTemp result = newTemp(Ity_F128); 12469 12470 assign(result, unop(Iop_NegF128, get_fpr_pair(r2))); 12471 put_fpr_pair(r1, mkexpr(result)); 12472 s390_cc_thunk_put1f128(S390_CC_OP_BFP_RESULT_128, result); 12473 12474 return "lcxbr"; 12475 } 12476 12477 static const HChar * 12478 s390_irgen_LXDBR(UChar r1, UChar r2) 12479 { 12480 IRTemp op = newTemp(Ity_F64); 12481 12482 assign(op, get_fpr_dw0(r2)); 12483 put_fpr_pair(r1, unop(Iop_F64toF128, mkexpr(op))); 12484 12485 return "lxdbr"; 12486 } 12487 12488 static const HChar * 12489 s390_irgen_LXEBR(UChar r1, UChar r2) 12490 { 12491 IRTemp op = newTemp(Ity_F32); 12492 12493 assign(op, get_fpr_w0(r2)); 12494 put_fpr_pair(r1, unop(Iop_F32toF128, mkexpr(op))); 12495 12496 return "lxebr"; 12497 } 12498 12499 static const HChar * 12500 s390_irgen_LXDB(UChar r1, IRTemp op2addr) 12501 { 12502 IRTemp op = newTemp(Ity_F64); 12503 12504 assign(op, load(Ity_F64, mkexpr(op2addr))); 12505 put_fpr_pair(r1, unop(Iop_F64toF128, mkexpr(op))); 12506 12507 return "lxdb"; 12508 } 12509 12510 static const HChar * 12511 s390_irgen_LXEB(UChar r1, IRTemp op2addr) 12512 { 12513 IRTemp op = newTemp(Ity_F32); 12514 12515 assign(op, load(Ity_F32, mkexpr(op2addr))); 12516 put_fpr_pair(r1, unop(Iop_F32toF128, mkexpr(op))); 12517 12518 return "lxeb"; 12519 } 12520 12521 static const HChar * 12522 s390_irgen_FIEBRA(UChar m3, UChar m4 __attribute__((unused)), 12523 UChar r1, UChar r2) 12524 { 12525 IRTemp result = newTemp(Ity_F32); 12526 12527 assign(result, binop(Iop_RoundF32toInt, mkexpr(encode_bfp_rounding_mode(m3)), 12528 get_fpr_w0(r2))); 12529 put_fpr_w0(r1, mkexpr(result)); 12530 12531 return "fiebra"; 12532 } 12533 12534 static const HChar * 12535 s390_irgen_FIDBRA(UChar m3, UChar m4 __attribute__((unused)), 12536 UChar r1, UChar r2) 12537 { 12538 IRTemp result = newTemp(Ity_F64); 12539 12540 assign(result, binop(Iop_RoundF64toInt, mkexpr(encode_bfp_rounding_mode(m3)), 12541 get_fpr_dw0(r2))); 12542 put_fpr_dw0(r1, mkexpr(result)); 12543 12544 return "fidbra"; 12545 } 12546 12547 static const HChar * 12548 s390_irgen_FIXBRA(UChar m3, UChar m4 __attribute__((unused)), 12549 UChar r1, UChar r2) 12550 { 12551 IRTemp result = newTemp(Ity_F128); 12552 12553 assign(result, binop(Iop_RoundF128toInt, mkexpr(encode_bfp_rounding_mode(m3)), 12554 get_fpr_pair(r2))); 12555 put_fpr_pair(r1, mkexpr(result)); 12556 12557 return "fixbra"; 12558 } 12559 12560 static const HChar * 12561 s390_irgen_LNEBR(UChar r1, UChar r2) 12562 { 12563 IRTemp result = newTemp(Ity_F32); 12564 12565 assign(result, unop(Iop_NegF32, unop(Iop_AbsF32, get_fpr_w0(r2)))); 12566 put_fpr_w0(r1, mkexpr(result)); 12567 s390_cc_thunk_put1f(S390_CC_OP_BFP_RESULT_32, result); 12568 12569 return "lnebr"; 12570 } 12571 12572 static const HChar * 12573 s390_irgen_LNDBR(UChar r1, UChar r2) 12574 { 12575 IRTemp result = newTemp(Ity_F64); 12576 12577 assign(result, unop(Iop_NegF64, unop(Iop_AbsF64, get_fpr_dw0(r2)))); 12578 put_fpr_dw0(r1, mkexpr(result)); 12579 s390_cc_thunk_put1f(S390_CC_OP_BFP_RESULT_64, result); 12580 12581 return "lndbr"; 12582 } 12583 12584 static const HChar * 12585 s390_irgen_LNXBR(UChar r1, UChar r2) 12586 { 12587 IRTemp result = newTemp(Ity_F128); 12588 12589 assign(result, unop(Iop_NegF128, unop(Iop_AbsF128, get_fpr_pair(r2)))); 12590 put_fpr_pair(r1, mkexpr(result)); 12591 s390_cc_thunk_put1f128(S390_CC_OP_BFP_RESULT_128, result); 12592 12593 return "lnxbr"; 12594 } 12595 12596 static const HChar * 12597 s390_irgen_LPEBR(UChar r1, UChar r2) 12598 { 12599 IRTemp result = newTemp(Ity_F32); 12600 12601 assign(result, unop(Iop_AbsF32, get_fpr_w0(r2))); 12602 put_fpr_w0(r1, mkexpr(result)); 12603 s390_cc_thunk_put1f(S390_CC_OP_BFP_RESULT_32, result); 12604 12605 return "lpebr"; 12606 } 12607 12608 static const HChar * 12609 s390_irgen_LPDBR(UChar r1, UChar r2) 12610 { 12611 IRTemp result = newTemp(Ity_F64); 12612 12613 assign(result, unop(Iop_AbsF64, get_fpr_dw0(r2))); 12614 put_fpr_dw0(r1, mkexpr(result)); 12615 s390_cc_thunk_put1f(S390_CC_OP_BFP_RESULT_64, result); 12616 12617 return "lpdbr"; 12618 } 12619 12620 static const HChar * 12621 s390_irgen_LPXBR(UChar r1, UChar r2) 12622 { 12623 IRTemp result = newTemp(Ity_F128); 12624 12625 assign(result, unop(Iop_AbsF128, get_fpr_pair(r2))); 12626 put_fpr_pair(r1, mkexpr(result)); 12627 s390_cc_thunk_put1f128(S390_CC_OP_BFP_RESULT_128, result); 12628 12629 return "lpxbr"; 12630 } 12631 12632 static const HChar * 12633 s390_irgen_LDXBR(UChar m3, UChar m4 __attribute__((unused)), 12634 UChar r1, UChar r2) 12635 { 12636 if (! s390_host_has_fpext && m3 != S390_BFP_ROUND_PER_FPC) { 12637 emulation_warning(EmWarn_S390X_fpext_rounding); 12638 m3 = S390_BFP_ROUND_PER_FPC; 12639 } 12640 IRTemp result = newTemp(Ity_F64); 12641 12642 assign(result, binop(Iop_F128toF64, mkexpr(encode_bfp_rounding_mode(m3)), 12643 get_fpr_pair(r2))); 12644 put_fpr_dw0(r1, mkexpr(result)); 12645 12646 return "ldxbr"; 12647 } 12648 12649 static const HChar * 12650 s390_irgen_LEXBR(UChar m3, UChar m4 __attribute__((unused)), 12651 UChar r1, UChar r2) 12652 { 12653 if (! s390_host_has_fpext && m3 != S390_BFP_ROUND_PER_FPC) { 12654 emulation_warning(EmWarn_S390X_fpext_rounding); 12655 m3 = S390_BFP_ROUND_PER_FPC; 12656 } 12657 IRTemp result = newTemp(Ity_F32); 12658 12659 assign(result, binop(Iop_F128toF32, mkexpr(encode_bfp_rounding_mode(m3)), 12660 get_fpr_pair(r2))); 12661 put_fpr_w0(r1, mkexpr(result)); 12662 12663 return "lexbr"; 12664 } 12665 12666 static const HChar * 12667 s390_irgen_MXBR(UChar r1, UChar r2) 12668 { 12669 IRTemp op1 = newTemp(Ity_F128); 12670 IRTemp op2 = newTemp(Ity_F128); 12671 IRTemp result = newTemp(Ity_F128); 12672 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12673 12674 assign(op1, get_fpr_pair(r1)); 12675 assign(op2, get_fpr_pair(r2)); 12676 assign(result, triop(Iop_MulF128, mkexpr(rounding_mode), mkexpr(op1), 12677 mkexpr(op2))); 12678 put_fpr_pair(r1, mkexpr(result)); 12679 12680 return "mxbr"; 12681 } 12682 12683 static const HChar * 12684 s390_irgen_MAEBR(UChar r1, UChar r3, UChar r2) 12685 { 12686 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12687 12688 put_fpr_w0(r1, qop(Iop_MAddF32, mkexpr(rounding_mode), 12689 get_fpr_w0(r3), get_fpr_w0(r2), get_fpr_w0(r1))); 12690 12691 return "maebr"; 12692 } 12693 12694 static const HChar * 12695 s390_irgen_MADBR(UChar r1, UChar r3, UChar r2) 12696 { 12697 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12698 12699 put_fpr_dw0(r1, qop(Iop_MAddF64, mkexpr(rounding_mode), 12700 get_fpr_dw0(r3), get_fpr_dw0(r2), get_fpr_dw0(r1))); 12701 12702 return "madbr"; 12703 } 12704 12705 static const HChar * 12706 s390_irgen_MAEB(UChar r3, IRTemp op2addr, UChar r1) 12707 { 12708 IRExpr *op2 = load(Ity_F32, mkexpr(op2addr)); 12709 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12710 12711 put_fpr_w0(r1, qop(Iop_MAddF32, mkexpr(rounding_mode), 12712 get_fpr_w0(r3), op2, get_fpr_w0(r1))); 12713 12714 return "maeb"; 12715 } 12716 12717 static const HChar * 12718 s390_irgen_MADB(UChar r3, IRTemp op2addr, UChar r1) 12719 { 12720 IRExpr *op2 = load(Ity_F64, mkexpr(op2addr)); 12721 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12722 12723 put_fpr_dw0(r1, qop(Iop_MAddF64, mkexpr(rounding_mode), 12724 get_fpr_dw0(r3), op2, get_fpr_dw0(r1))); 12725 12726 return "madb"; 12727 } 12728 12729 static const HChar * 12730 s390_irgen_MSEBR(UChar r1, UChar r3, UChar r2) 12731 { 12732 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12733 12734 put_fpr_w0(r1, qop(Iop_MSubF32, mkexpr(rounding_mode), 12735 get_fpr_w0(r3), get_fpr_w0(r2), get_fpr_w0(r1))); 12736 12737 return "msebr"; 12738 } 12739 12740 static const HChar * 12741 s390_irgen_MSDBR(UChar r1, UChar r3, UChar r2) 12742 { 12743 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12744 12745 put_fpr_dw0(r1, qop(Iop_MSubF64, mkexpr(rounding_mode), 12746 get_fpr_dw0(r3), get_fpr_dw0(r2), get_fpr_dw0(r1))); 12747 12748 return "msdbr"; 12749 } 12750 12751 static const HChar * 12752 s390_irgen_MSEB(UChar r3, IRTemp op2addr, UChar r1) 12753 { 12754 IRExpr *op2 = load(Ity_F32, mkexpr(op2addr)); 12755 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12756 12757 put_fpr_w0(r1, qop(Iop_MSubF32, mkexpr(rounding_mode), 12758 get_fpr_w0(r3), op2, get_fpr_w0(r1))); 12759 12760 return "mseb"; 12761 } 12762 12763 static const HChar * 12764 s390_irgen_MSDB(UChar r3, IRTemp op2addr, UChar r1) 12765 { 12766 IRExpr *op2 = load(Ity_F64, mkexpr(op2addr)); 12767 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12768 12769 put_fpr_dw0(r1, qop(Iop_MSubF64, mkexpr(rounding_mode), 12770 get_fpr_dw0(r3), op2, get_fpr_dw0(r1))); 12771 12772 return "msdb"; 12773 } 12774 12775 static const HChar * 12776 s390_irgen_SQEBR(UChar r1, UChar r2) 12777 { 12778 IRTemp result = newTemp(Ity_F32); 12779 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12780 12781 assign(result, binop(Iop_SqrtF32, mkexpr(rounding_mode), get_fpr_w0(r2))); 12782 put_fpr_w0(r1, mkexpr(result)); 12783 12784 return "sqebr"; 12785 } 12786 12787 static const HChar * 12788 s390_irgen_SQDBR(UChar r1, UChar r2) 12789 { 12790 IRTemp result = newTemp(Ity_F64); 12791 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12792 12793 assign(result, binop(Iop_SqrtF64, mkexpr(rounding_mode), get_fpr_dw0(r2))); 12794 put_fpr_dw0(r1, mkexpr(result)); 12795 12796 return "sqdbr"; 12797 } 12798 12799 static const HChar * 12800 s390_irgen_SQXBR(UChar r1, UChar r2) 12801 { 12802 IRTemp result = newTemp(Ity_F128); 12803 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12804 12805 assign(result, binop(Iop_SqrtF128, mkexpr(rounding_mode), 12806 get_fpr_pair(r2))); 12807 put_fpr_pair(r1, mkexpr(result)); 12808 12809 return "sqxbr"; 12810 } 12811 12812 static const HChar * 12813 s390_irgen_SQEB(UChar r1, IRTemp op2addr) 12814 { 12815 IRTemp op = newTemp(Ity_F32); 12816 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12817 12818 assign(op, load(Ity_F32, mkexpr(op2addr))); 12819 put_fpr_w0(r1, binop(Iop_SqrtF32, mkexpr(rounding_mode), mkexpr(op))); 12820 12821 return "sqeb"; 12822 } 12823 12824 static const HChar * 12825 s390_irgen_SQDB(UChar r1, IRTemp op2addr) 12826 { 12827 IRTemp op = newTemp(Ity_F64); 12828 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12829 12830 assign(op, load(Ity_F64, mkexpr(op2addr))); 12831 put_fpr_dw0(r1, binop(Iop_SqrtF64, mkexpr(rounding_mode), mkexpr(op))); 12832 12833 return "sqdb"; 12834 } 12835 12836 static const HChar * 12837 s390_irgen_SXBR(UChar r1, UChar r2) 12838 { 12839 IRTemp op1 = newTemp(Ity_F128); 12840 IRTemp op2 = newTemp(Ity_F128); 12841 IRTemp result = newTemp(Ity_F128); 12842 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12843 12844 assign(op1, get_fpr_pair(r1)); 12845 assign(op2, get_fpr_pair(r2)); 12846 assign(result, triop(Iop_SubF128, mkexpr(rounding_mode), mkexpr(op1), 12847 mkexpr(op2))); 12848 put_fpr_pair(r1, mkexpr(result)); 12849 s390_cc_thunk_put1f128(S390_CC_OP_BFP_RESULT_128, result); 12850 12851 return "sxbr"; 12852 } 12853 12854 static const HChar * 12855 s390_irgen_TCEB(UChar r1, IRTemp op2addr) 12856 { 12857 IRTemp value = newTemp(Ity_F32); 12858 12859 assign(value, get_fpr_w0(r1)); 12860 12861 s390_cc_thunk_putFZ(S390_CC_OP_BFP_TDC_32, value, op2addr); 12862 12863 return "tceb"; 12864 } 12865 12866 static const HChar * 12867 s390_irgen_TCDB(UChar r1, IRTemp op2addr) 12868 { 12869 IRTemp value = newTemp(Ity_F64); 12870 12871 assign(value, get_fpr_dw0(r1)); 12872 12873 s390_cc_thunk_putFZ(S390_CC_OP_BFP_TDC_64, value, op2addr); 12874 12875 return "tcdb"; 12876 } 12877 12878 static const HChar * 12879 s390_irgen_TCXB(UChar r1, IRTemp op2addr) 12880 { 12881 IRTemp value = newTemp(Ity_F128); 12882 12883 assign(value, get_fpr_pair(r1)); 12884 12885 s390_cc_thunk_put1f128Z(S390_CC_OP_BFP_TDC_128, value, op2addr); 12886 12887 return "tcxb"; 12888 } 12889 12890 static const HChar * 12891 s390_irgen_LCDFR(UChar r1, UChar r2) 12892 { 12893 IRTemp result = newTemp(Ity_F64); 12894 12895 assign(result, unop(Iop_NegF64, get_fpr_dw0(r2))); 12896 put_fpr_dw0(r1, mkexpr(result)); 12897 12898 return "lcdfr"; 12899 } 12900 12901 static const HChar * 12902 s390_irgen_LNDFR(UChar r1, UChar r2) 12903 { 12904 IRTemp result = newTemp(Ity_F64); 12905 12906 assign(result, unop(Iop_NegF64, unop(Iop_AbsF64, get_fpr_dw0(r2)))); 12907 put_fpr_dw0(r1, mkexpr(result)); 12908 12909 return "lndfr"; 12910 } 12911 12912 static const HChar * 12913 s390_irgen_LPDFR(UChar r1, UChar r2) 12914 { 12915 IRTemp result = newTemp(Ity_F64); 12916 12917 assign(result, unop(Iop_AbsF64, get_fpr_dw0(r2))); 12918 put_fpr_dw0(r1, mkexpr(result)); 12919 12920 return "lpdfr"; 12921 } 12922 12923 static const HChar * 12924 s390_irgen_LDGR(UChar r1, UChar r2) 12925 { 12926 put_fpr_dw0(r1, unop(Iop_ReinterpI64asF64, get_gpr_dw0(r2))); 12927 12928 return "ldgr"; 12929 } 12930 12931 static const HChar * 12932 s390_irgen_LGDR(UChar r1, UChar r2) 12933 { 12934 put_gpr_dw0(r1, unop(Iop_ReinterpF64asI64, get_fpr_dw0(r2))); 12935 12936 return "lgdr"; 12937 } 12938 12939 12940 static const HChar * 12941 s390_irgen_CPSDR(UChar r3, UChar r1, UChar r2) 12942 { 12943 IRTemp sign = newTemp(Ity_I64); 12944 IRTemp value = newTemp(Ity_I64); 12945 12946 assign(sign, binop(Iop_And64, unop(Iop_ReinterpF64asI64, get_fpr_dw0(r3)), 12947 mkU64(1ULL << 63))); 12948 assign(value, binop(Iop_And64, unop(Iop_ReinterpF64asI64, get_fpr_dw0(r2)), 12949 mkU64((1ULL << 63) - 1))); 12950 put_fpr_dw0(r1, unop(Iop_ReinterpI64asF64, binop(Iop_Or64, mkexpr(value), 12951 mkexpr(sign)))); 12952 12953 return "cpsdr"; 12954 } 12955 12956 12957 static IRExpr * 12958 s390_call_cvb(IRExpr *in) 12959 { 12960 IRExpr **args, *call; 12961 12962 args = mkIRExprVec_1(in); 12963 call = mkIRExprCCall(Ity_I32, 0 /*regparm*/, 12964 "s390_do_cvb", &s390_do_cvb, args); 12965 12966 /* Nothing is excluded from definedness checking. */ 12967 call->Iex.CCall.cee->mcx_mask = 0; 12968 12969 return call; 12970 } 12971 12972 static const HChar * 12973 s390_irgen_CVB(UChar r1, IRTemp op2addr) 12974 { 12975 put_gpr_w1(r1, s390_call_cvb(load(Ity_I64, mkexpr(op2addr)))); 12976 12977 return "cvb"; 12978 } 12979 12980 static const HChar * 12981 s390_irgen_CVBY(UChar r1, IRTemp op2addr) 12982 { 12983 put_gpr_w1(r1, s390_call_cvb(load(Ity_I64, mkexpr(op2addr)))); 12984 12985 return "cvby"; 12986 } 12987 12988 12989 static IRExpr * 12990 s390_call_cvd(IRExpr *in) 12991 { 12992 IRExpr **args, *call; 12993 12994 args = mkIRExprVec_1(in); 12995 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, 12996 "s390_do_cvd", &s390_do_cvd, args); 12997 12998 /* Nothing is excluded from definedness checking. */ 12999 call->Iex.CCall.cee->mcx_mask = 0; 13000 13001 return call; 13002 } 13003 13004 static const HChar * 13005 s390_irgen_CVD(UChar r1, IRTemp op2addr) 13006 { 13007 store(mkexpr(op2addr), s390_call_cvd(unop(Iop_32Uto64, get_gpr_w1(r1)))); 13008 13009 return "cvd"; 13010 } 13011 13012 static const HChar * 13013 s390_irgen_CVDY(UChar r1, IRTemp op2addr) 13014 { 13015 store(mkexpr(op2addr), s390_call_cvd(get_gpr_w1(r1))); 13016 13017 return "cvdy"; 13018 } 13019 13020 static const HChar * 13021 s390_irgen_FLOGR(UChar r1, UChar r2) 13022 { 13023 IRTemp input = newTemp(Ity_I64); 13024 IRTemp not_zero = newTemp(Ity_I64); 13025 IRTemp tmpnum = newTemp(Ity_I64); 13026 IRTemp num = newTemp(Ity_I64); 13027 IRTemp shift_amount = newTemp(Ity_I8); 13028 13029 /* We use the "count leading zeroes" operator because the number of 13030 leading zeroes is identical with the bit position of the first '1' bit. 13031 However, that operator does not work when the input value is zero. 13032 Therefore, we set the LSB of the input value to 1 and use Clz64 on 13033 the modified value. If input == 0, then the result is 64. Otherwise, 13034 the result of Clz64 is what we want. */ 13035 13036 assign(input, get_gpr_dw0(r2)); 13037 assign(not_zero, binop(Iop_Or64, mkexpr(input), mkU64(1))); 13038 assign(tmpnum, unop(Iop_Clz64, mkexpr(not_zero))); 13039 13040 /* num = (input == 0) ? 64 : tmpnum */ 13041 assign(num, mkite(binop(Iop_CmpEQ64, mkexpr(input), mkU64(0)), 13042 /* == 0 */ mkU64(64), 13043 /* != 0 */ mkexpr(tmpnum))); 13044 13045 put_gpr_dw0(r1, mkexpr(num)); 13046 13047 /* Set the leftmost '1' bit of the input value to zero. The general scheme 13048 is to first shift the input value by NUM + 1 bits to the left which 13049 causes the leftmost '1' bit to disappear. Then we shift logically to 13050 the right by NUM + 1 bits. Because the semantics of Iop_Shl64 and 13051 Iop_Shr64 are undefined if the shift-amount is greater than or equal to 13052 the width of the value-to-be-shifted, we need to special case 13053 NUM + 1 >= 64. This is equivalent to INPUT != 0 && INPUT != 1. 13054 For both such INPUT values the result will be 0. */ 13055 13056 assign(shift_amount, unop(Iop_64to8, binop(Iop_Add64, mkexpr(num), 13057 mkU64(1)))); 13058 13059 put_gpr_dw0(r1 + 1, 13060 mkite(binop(Iop_CmpLE64U, mkexpr(input), mkU64(1)), 13061 /* == 0 || == 1*/ mkU64(0), 13062 /* otherwise */ 13063 binop(Iop_Shr64, 13064 binop(Iop_Shl64, mkexpr(input), 13065 mkexpr(shift_amount)), 13066 mkexpr(shift_amount)))); 13067 13068 /* Compare the original value as an unsigned integer with 0. */ 13069 s390_cc_thunk_put2(S390_CC_OP_UNSIGNED_COMPARE, input, 13070 mktemp(Ity_I64, mkU64(0)), False); 13071 13072 return "flogr"; 13073 } 13074 13075 static const HChar * 13076 s390_irgen_POPCNT(UChar r1, UChar r2) 13077 { 13078 Int i; 13079 IRTemp val = newTemp(Ity_I64); 13080 IRTemp mask[3]; 13081 13082 assign(val, get_gpr_dw0(r2)); 13083 for (i = 0; i < 3; i++) { 13084 mask[i] = newTemp(Ity_I64); 13085 } 13086 assign(mask[0], mkU64(0x5555555555555555ULL)); 13087 assign(mask[1], mkU64(0x3333333333333333ULL)); 13088 assign(mask[2], mkU64(0x0F0F0F0F0F0F0F0FULL)); 13089 for (i = 0; i < 3; i++) { 13090 IRTemp tmp = newTemp(Ity_I64); 13091 13092 assign(tmp, 13093 binop(Iop_Add64, 13094 binop(Iop_And64, 13095 mkexpr(val), 13096 mkexpr(mask[i])), 13097 binop(Iop_And64, 13098 binop(Iop_Shr64, mkexpr(val), mkU8(1 << i)), 13099 mkexpr(mask[i])))); 13100 val = tmp; 13101 } 13102 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, val); 13103 put_gpr_dw0(r1, mkexpr(val)); 13104 return "popcnt"; 13105 } 13106 13107 static const HChar * 13108 s390_irgen_STCK(IRTemp op2addr) 13109 { 13110 IRDirty *d; 13111 IRTemp cc = newTemp(Ity_I64); 13112 13113 d = unsafeIRDirty_1_N(cc, 0, "s390x_dirtyhelper_STCK", 13114 &s390x_dirtyhelper_STCK, 13115 mkIRExprVec_1(mkexpr(op2addr))); 13116 d->mFx = Ifx_Write; 13117 d->mAddr = mkexpr(op2addr); 13118 d->mSize = 8; 13119 stmt(IRStmt_Dirty(d)); 13120 s390_cc_thunk_fill(mkU64(S390_CC_OP_SET), 13121 mkexpr(cc), mkU64(0), mkU64(0)); 13122 return "stck"; 13123 } 13124 13125 static const HChar * 13126 s390_irgen_STCKF(IRTemp op2addr) 13127 { 13128 if (! s390_host_has_stckf) { 13129 emulation_failure(EmFail_S390X_stckf); 13130 } else { 13131 IRTemp cc = newTemp(Ity_I64); 13132 13133 IRDirty *d = unsafeIRDirty_1_N(cc, 0, "s390x_dirtyhelper_STCKF", 13134 &s390x_dirtyhelper_STCKF, 13135 mkIRExprVec_1(mkexpr(op2addr))); 13136 d->mFx = Ifx_Write; 13137 d->mAddr = mkexpr(op2addr); 13138 d->mSize = 8; 13139 stmt(IRStmt_Dirty(d)); 13140 s390_cc_thunk_fill(mkU64(S390_CC_OP_SET), 13141 mkexpr(cc), mkU64(0), mkU64(0)); 13142 } 13143 return "stckf"; 13144 } 13145 13146 static const HChar * 13147 s390_irgen_STCKE(IRTemp op2addr) 13148 { 13149 IRDirty *d; 13150 IRTemp cc = newTemp(Ity_I64); 13151 13152 d = unsafeIRDirty_1_N(cc, 0, "s390x_dirtyhelper_STCKE", 13153 &s390x_dirtyhelper_STCKE, 13154 mkIRExprVec_1(mkexpr(op2addr))); 13155 d->mFx = Ifx_Write; 13156 d->mAddr = mkexpr(op2addr); 13157 d->mSize = 16; 13158 stmt(IRStmt_Dirty(d)); 13159 s390_cc_thunk_fill(mkU64(S390_CC_OP_SET), 13160 mkexpr(cc), mkU64(0), mkU64(0)); 13161 return "stcke"; 13162 } 13163 13164 static const HChar * 13165 s390_irgen_STFLE(IRTemp op2addr) 13166 { 13167 if (! s390_host_has_stfle) { 13168 emulation_failure(EmFail_S390X_stfle); 13169 return "stfle"; 13170 } 13171 13172 IRDirty *d; 13173 IRTemp cc = newTemp(Ity_I64); 13174 13175 /* IRExpr_GSPTR() => Need to pass pointer to guest state to helper */ 13176 d = unsafeIRDirty_1_N(cc, 0, "s390x_dirtyhelper_STFLE", 13177 &s390x_dirtyhelper_STFLE, 13178 mkIRExprVec_2(IRExpr_GSPTR(), mkexpr(op2addr))); 13179 13180 d->nFxState = 1; 13181 vex_bzero(&d->fxState, sizeof(d->fxState)); 13182 13183 d->fxState[0].fx = Ifx_Modify; /* read then write */ 13184 d->fxState[0].offset = S390X_GUEST_OFFSET(guest_r0); 13185 d->fxState[0].size = sizeof(ULong); 13186 13187 d->mAddr = mkexpr(op2addr); 13188 /* Pretend all double words are written */ 13189 d->mSize = S390_NUM_FACILITY_DW * sizeof(ULong); 13190 d->mFx = Ifx_Write; 13191 13192 stmt(IRStmt_Dirty(d)); 13193 13194 s390_cc_thunk_fill(mkU64(S390_CC_OP_SET), mkexpr(cc), mkU64(0), mkU64(0)); 13195 13196 return "stfle"; 13197 } 13198 13199 static const HChar * 13200 s390_irgen_CKSM(UChar r1,UChar r2) 13201 { 13202 IRTemp addr = newTemp(Ity_I64); 13203 IRTemp op = newTemp(Ity_I32); 13204 IRTemp len = newTemp(Ity_I64); 13205 IRTemp oldval = newTemp(Ity_I32); 13206 IRTemp mask = newTemp(Ity_I32); 13207 IRTemp newop = newTemp(Ity_I32); 13208 IRTemp result = newTemp(Ity_I32); 13209 IRTemp result1 = newTemp(Ity_I32); 13210 IRTemp inc = newTemp(Ity_I64); 13211 13212 assign(oldval, get_gpr_w1(r1)); 13213 assign(addr, get_gpr_dw0(r2)); 13214 assign(len, get_gpr_dw0(r2+1)); 13215 13216 /* Condition code is always zero. */ 13217 s390_cc_set(0); 13218 13219 /* If length is zero, there is no need to calculate the checksum */ 13220 next_insn_if(binop(Iop_CmpEQ64, mkexpr(len), mkU64(0))); 13221 13222 /* Assiging the increment variable to adjust address and length 13223 later on. */ 13224 assign(inc, mkite(binop(Iop_CmpLT64U, mkexpr(len), mkU64(4)), 13225 mkexpr(len), mkU64(4))); 13226 13227 /* If length < 4 the final 4-byte 2nd operand value is computed by 13228 appending the remaining bytes to the right with 0. This is done 13229 by AND'ing the 4 bytes loaded from memory with an appropriate 13230 mask. If length >= 4, that mask is simply 0xffffffff. */ 13231 13232 assign(mask, mkite(binop(Iop_CmpLT64U, mkexpr(len), mkU64(4)), 13233 /* Mask computation when len < 4: 13234 0xffffffff << (32 - (len % 4)*8) */ 13235 binop(Iop_Shl32, mkU32(0xffffffff), 13236 unop(Iop_32to8, 13237 binop(Iop_Sub32, mkU32(32), 13238 binop(Iop_Shl32, 13239 unop(Iop_64to32, 13240 binop(Iop_And64, 13241 mkexpr(len), mkU64(3))), 13242 mkU8(3))))), 13243 mkU32(0xffffffff))); 13244 13245 assign(op, load(Ity_I32, mkexpr(addr))); 13246 assign(newop, binop(Iop_And32, mkexpr(op), mkexpr(mask))); 13247 assign(result, binop(Iop_Add32, mkexpr(newop), mkexpr(oldval))); 13248 13249 /* Checking for carry */ 13250 assign(result1, mkite(binop(Iop_CmpLT32U, mkexpr(result), mkexpr(newop)), 13251 binop(Iop_Add32, mkexpr(result), mkU32(1)), 13252 mkexpr(result))); 13253 13254 put_gpr_w1(r1, mkexpr(result1)); 13255 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(addr), mkexpr(inc))); 13256 put_gpr_dw0(r2+1, binop(Iop_Sub64, mkexpr(len), mkexpr(inc))); 13257 13258 iterate_if(binop(Iop_CmpNE64, mkexpr(len), mkU64(0))); 13259 13260 return "cksm"; 13261 } 13262 13263 static const HChar * 13264 s390_irgen_TROO(UChar m3, UChar r1, UChar r2) 13265 { 13266 IRTemp src_addr, des_addr, tab_addr, src_len, test_byte; 13267 src_addr = newTemp(Ity_I64); 13268 des_addr = newTemp(Ity_I64); 13269 tab_addr = newTemp(Ity_I64); 13270 test_byte = newTemp(Ity_I8); 13271 src_len = newTemp(Ity_I64); 13272 13273 assign(src_addr, get_gpr_dw0(r2)); 13274 assign(des_addr, get_gpr_dw0(r1)); 13275 assign(tab_addr, get_gpr_dw0(1)); 13276 assign(src_len, get_gpr_dw0(r1+1)); 13277 assign(test_byte, get_gpr_b7(0)); 13278 13279 IRTemp op = newTemp(Ity_I8); 13280 IRTemp op1 = newTemp(Ity_I8); 13281 IRTemp result = newTemp(Ity_I64); 13282 13283 /* End of source string? We're done; proceed to next insn */ 13284 s390_cc_set(0); 13285 next_insn_if(binop(Iop_CmpEQ64, mkexpr(src_len), mkU64(0))); 13286 13287 /* Load character from source string, index translation table and 13288 store translated character in op1. */ 13289 assign(op, load(Ity_I8, mkexpr(src_addr))); 13290 13291 assign(result, binop(Iop_Add64, unop(Iop_8Uto64, mkexpr(op)), 13292 mkexpr(tab_addr))); 13293 assign(op1, load(Ity_I8, mkexpr(result))); 13294 13295 if (! s390_host_has_etf2 || (m3 & 0x1) == 0) { 13296 s390_cc_set(1); 13297 next_insn_if(binop(Iop_CmpEQ8, mkexpr(op1), mkexpr(test_byte))); 13298 } 13299 store(get_gpr_dw0(r1), mkexpr(op1)); 13300 13301 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(des_addr), mkU64(1))); 13302 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(src_addr), mkU64(1))); 13303 put_gpr_dw0(r1+1, binop(Iop_Sub64, mkexpr(src_len), mkU64(1))); 13304 13305 iterate(); 13306 13307 return "troo"; 13308 } 13309 13310 static const HChar * 13311 s390_irgen_TRTO(UChar m3, UChar r1, UChar r2) 13312 { 13313 IRTemp src_addr, des_addr, tab_addr, src_len, test_byte; 13314 src_addr = newTemp(Ity_I64); 13315 des_addr = newTemp(Ity_I64); 13316 tab_addr = newTemp(Ity_I64); 13317 test_byte = newTemp(Ity_I8); 13318 src_len = newTemp(Ity_I64); 13319 13320 assign(src_addr, get_gpr_dw0(r2)); 13321 assign(des_addr, get_gpr_dw0(r1)); 13322 assign(tab_addr, get_gpr_dw0(1)); 13323 assign(src_len, get_gpr_dw0(r1+1)); 13324 assign(test_byte, get_gpr_b7(0)); 13325 13326 IRTemp op = newTemp(Ity_I16); 13327 IRTemp op1 = newTemp(Ity_I8); 13328 IRTemp result = newTemp(Ity_I64); 13329 13330 /* End of source string? We're done; proceed to next insn */ 13331 s390_cc_set(0); 13332 next_insn_if(binop(Iop_CmpEQ64, mkexpr(src_len), mkU64(0))); 13333 13334 /* Load character from source string, index translation table and 13335 store translated character in op1. */ 13336 assign(op, load(Ity_I16, mkexpr(src_addr))); 13337 13338 assign(result, binop(Iop_Add64, unop(Iop_16Uto64, mkexpr(op)), 13339 mkexpr(tab_addr))); 13340 13341 assign(op1, load(Ity_I8, mkexpr(result))); 13342 13343 if (! s390_host_has_etf2 || (m3 & 0x1) == 0) { 13344 s390_cc_set(1); 13345 next_insn_if(binop(Iop_CmpEQ8, mkexpr(op1), mkexpr(test_byte))); 13346 } 13347 store(get_gpr_dw0(r1), mkexpr(op1)); 13348 13349 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(src_addr), mkU64(2))); 13350 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(des_addr), mkU64(1))); 13351 put_gpr_dw0(r1+1, binop(Iop_Sub64, mkexpr(src_len), mkU64(2))); 13352 13353 iterate(); 13354 13355 return "trto"; 13356 } 13357 13358 static const HChar * 13359 s390_irgen_TROT(UChar m3, UChar r1, UChar r2) 13360 { 13361 IRTemp src_addr, des_addr, tab_addr, src_len, test_byte; 13362 src_addr = newTemp(Ity_I64); 13363 des_addr = newTemp(Ity_I64); 13364 tab_addr = newTemp(Ity_I64); 13365 test_byte = newTemp(Ity_I16); 13366 src_len = newTemp(Ity_I64); 13367 13368 assign(src_addr, get_gpr_dw0(r2)); 13369 assign(des_addr, get_gpr_dw0(r1)); 13370 assign(tab_addr, get_gpr_dw0(1)); 13371 assign(src_len, get_gpr_dw0(r1+1)); 13372 assign(test_byte, get_gpr_hw3(0)); 13373 13374 IRTemp op = newTemp(Ity_I8); 13375 IRTemp op1 = newTemp(Ity_I16); 13376 IRTemp result = newTemp(Ity_I64); 13377 13378 /* End of source string? We're done; proceed to next insn */ 13379 s390_cc_set(0); 13380 next_insn_if(binop(Iop_CmpEQ64, mkexpr(src_len), mkU64(0))); 13381 13382 /* Load character from source string, index translation table and 13383 store translated character in op1. */ 13384 assign(op, binop(Iop_Shl8, load(Ity_I8, mkexpr(src_addr)), mkU8(1))); 13385 13386 assign(result, binop(Iop_Add64, unop(Iop_8Uto64, mkexpr(op)), 13387 mkexpr(tab_addr))); 13388 assign(op1, load(Ity_I16, mkexpr(result))); 13389 13390 if (! s390_host_has_etf2 || (m3 & 0x1) == 0) { 13391 s390_cc_set(1); 13392 next_insn_if(binop(Iop_CmpEQ16, mkexpr(op1), mkexpr(test_byte))); 13393 } 13394 store(get_gpr_dw0(r1), mkexpr(op1)); 13395 13396 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(src_addr), mkU64(1))); 13397 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(des_addr), mkU64(2))); 13398 put_gpr_dw0(r1+1, binop(Iop_Sub64, mkexpr(src_len), mkU64(1))); 13399 13400 iterate(); 13401 13402 return "trot"; 13403 } 13404 13405 static const HChar * 13406 s390_irgen_TRTT(UChar m3, UChar r1, UChar r2) 13407 { 13408 IRTemp src_addr, des_addr, tab_addr, src_len, test_byte; 13409 src_addr = newTemp(Ity_I64); 13410 des_addr = newTemp(Ity_I64); 13411 tab_addr = newTemp(Ity_I64); 13412 test_byte = newTemp(Ity_I16); 13413 src_len = newTemp(Ity_I64); 13414 13415 assign(src_addr, get_gpr_dw0(r2)); 13416 assign(des_addr, get_gpr_dw0(r1)); 13417 assign(tab_addr, get_gpr_dw0(1)); 13418 assign(src_len, get_gpr_dw0(r1+1)); 13419 assign(test_byte, get_gpr_hw3(0)); 13420 13421 IRTemp op = newTemp(Ity_I16); 13422 IRTemp op1 = newTemp(Ity_I16); 13423 IRTemp result = newTemp(Ity_I64); 13424 13425 /* End of source string? We're done; proceed to next insn */ 13426 s390_cc_set(0); 13427 next_insn_if(binop(Iop_CmpEQ64, mkexpr(src_len), mkU64(0))); 13428 13429 /* Load character from source string, index translation table and 13430 store translated character in op1. */ 13431 assign(op, binop(Iop_Shl16, load(Ity_I16, mkexpr(src_addr)), mkU8(1))); 13432 13433 assign(result, binop(Iop_Add64, unop(Iop_16Uto64, mkexpr(op)), 13434 mkexpr(tab_addr))); 13435 assign(op1, load(Ity_I16, mkexpr(result))); 13436 13437 if (! s390_host_has_etf2 || (m3 & 0x1) == 0) { 13438 s390_cc_set(1); 13439 next_insn_if(binop(Iop_CmpEQ16, mkexpr(op1), mkexpr(test_byte))); 13440 } 13441 13442 store(get_gpr_dw0(r1), mkexpr(op1)); 13443 13444 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(src_addr), mkU64(2))); 13445 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(des_addr), mkU64(2))); 13446 put_gpr_dw0(r1+1, binop(Iop_Sub64, mkexpr(src_len), mkU64(2))); 13447 13448 iterate(); 13449 13450 return "trtt"; 13451 } 13452 13453 static const HChar * 13454 s390_irgen_TR(UChar length, IRTemp start1, IRTemp start2) 13455 { 13456 IRTemp len = newTemp(Ity_I64); 13457 13458 assign(len, mkU64(length)); 13459 s390_irgen_TR_EX(len, start1, start2); 13460 13461 return "tr"; 13462 } 13463 13464 static const HChar * 13465 s390_irgen_TRE(UChar r1,UChar r2) 13466 { 13467 IRTemp src_addr, tab_addr, src_len, test_byte; 13468 src_addr = newTemp(Ity_I64); 13469 tab_addr = newTemp(Ity_I64); 13470 src_len = newTemp(Ity_I64); 13471 test_byte = newTemp(Ity_I8); 13472 13473 assign(src_addr, get_gpr_dw0(r1)); 13474 assign(src_len, get_gpr_dw0(r1+1)); 13475 assign(tab_addr, get_gpr_dw0(r2)); 13476 assign(test_byte, get_gpr_b7(0)); 13477 13478 IRTemp op = newTemp(Ity_I8); 13479 IRTemp op1 = newTemp(Ity_I8); 13480 IRTemp result = newTemp(Ity_I64); 13481 13482 /* End of source string? We're done; proceed to next insn */ 13483 s390_cc_set(0); 13484 next_insn_if(binop(Iop_CmpEQ64, mkexpr(src_len), mkU64(0))); 13485 13486 /* Load character from source string and compare with test byte */ 13487 assign(op, load(Ity_I8, mkexpr(src_addr))); 13488 13489 s390_cc_set(1); 13490 next_insn_if(binop(Iop_CmpEQ8, mkexpr(op), mkexpr(test_byte))); 13491 13492 assign(result, binop(Iop_Add64, unop(Iop_8Uto64, mkexpr(op)), 13493 mkexpr(tab_addr))); 13494 13495 assign(op1, load(Ity_I8, mkexpr(result))); 13496 13497 store(get_gpr_dw0(r1), mkexpr(op1)); 13498 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(src_addr), mkU64(1))); 13499 put_gpr_dw0(r1+1, binop(Iop_Sub64, mkexpr(src_len), mkU64(1))); 13500 13501 iterate(); 13502 13503 return "tre"; 13504 } 13505 13506 static IRExpr * 13507 s390_call_cu21(IRExpr *srcval, IRExpr *low_surrogate) 13508 { 13509 IRExpr **args, *call; 13510 args = mkIRExprVec_2(srcval, low_surrogate); 13511 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, 13512 "s390_do_cu21", &s390_do_cu21, args); 13513 13514 /* Nothing is excluded from definedness checking. */ 13515 call->Iex.CCall.cee->mcx_mask = 0; 13516 13517 return call; 13518 } 13519 13520 static const HChar * 13521 s390_irgen_CU21(UChar m3, UChar r1, UChar r2) 13522 { 13523 IRTemp addr1 = newTemp(Ity_I64); 13524 IRTemp addr2 = newTemp(Ity_I64); 13525 IRTemp len1 = newTemp(Ity_I64); 13526 IRTemp len2 = newTemp(Ity_I64); 13527 13528 assign(addr1, get_gpr_dw0(r1)); 13529 assign(addr2, get_gpr_dw0(r2)); 13530 assign(len1, get_gpr_dw0(r1 + 1)); 13531 assign(len2, get_gpr_dw0(r2 + 1)); 13532 13533 /* We're processing the 2nd operand 2 bytes at a time. Therefore, if 13534 there are less than 2 bytes left, then the 2nd operand is exhausted 13535 and we're done here. cc = 0 */ 13536 s390_cc_set(0); 13537 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len2), mkU64(2))); 13538 13539 /* There are at least two bytes there. Read them. */ 13540 IRTemp srcval = newTemp(Ity_I32); 13541 assign(srcval, unop(Iop_16Uto32, load(Ity_I16, mkexpr(addr2)))); 13542 13543 /* Find out whether this is a high surrogate. I.e. SRCVAL lies 13544 inside the interval [0xd800 - 0xdbff] */ 13545 IRTemp is_high_surrogate = newTemp(Ity_I32); 13546 IRExpr *flag1 = mkite(binop(Iop_CmpLE32U, mkU32(0xd800), mkexpr(srcval)), 13547 mkU32(1), mkU32(0)); 13548 IRExpr *flag2 = mkite(binop(Iop_CmpLE32U, mkexpr(srcval), mkU32(0xdbff)), 13549 mkU32(1), mkU32(0)); 13550 assign(is_high_surrogate, binop(Iop_And32, flag1, flag2)); 13551 13552 /* If SRCVAL is a high surrogate and there are less than 4 bytes left, 13553 then the 2nd operand is exhausted and we're done here. cc = 0 */ 13554 IRExpr *not_enough_bytes = 13555 mkite(binop(Iop_CmpLT64U, mkexpr(len2), mkU64(4)), mkU32(1), mkU32(0)); 13556 13557 next_insn_if(binop(Iop_CmpEQ32, 13558 binop(Iop_And32, mkexpr(is_high_surrogate), 13559 not_enough_bytes), mkU32(1))); 13560 13561 /* The 2nd operand is not exhausted. If the first 2 bytes are a high 13562 surrogate, read the next two bytes (low surrogate). */ 13563 IRTemp low_surrogate = newTemp(Ity_I32); 13564 IRExpr *low_surrogate_addr = binop(Iop_Add64, mkexpr(addr2), mkU64(2)); 13565 13566 assign(low_surrogate, 13567 mkite(binop(Iop_CmpEQ32, mkexpr(is_high_surrogate), mkU32(1)), 13568 unop(Iop_16Uto32, load(Ity_I16, low_surrogate_addr)), 13569 mkU32(0))); // any value is fine; it will not be used 13570 13571 /* Call the helper */ 13572 IRTemp retval = newTemp(Ity_I64); 13573 assign(retval, s390_call_cu21(unop(Iop_32Uto64, mkexpr(srcval)), 13574 unop(Iop_32Uto64, mkexpr(low_surrogate)))); 13575 13576 /* Before we can test whether the 1st operand is exhausted we need to 13577 test for an invalid low surrogate. Because cc=2 outranks cc=1. */ 13578 if (s390_host_has_etf3 && (m3 & 0x1) == 1) { 13579 IRExpr *invalid_low_surrogate = 13580 binop(Iop_And64, mkexpr(retval), mkU64(0xff)); 13581 13582 s390_cc_set(2); 13583 next_insn_if(binop(Iop_CmpEQ64, invalid_low_surrogate, mkU64(1))); 13584 } 13585 13586 /* Now test whether the 1st operand is exhausted */ 13587 IRTemp num_bytes = newTemp(Ity_I64); 13588 assign(num_bytes, binop(Iop_And64, 13589 binop(Iop_Shr64, mkexpr(retval), mkU8(8)), 13590 mkU64(0xff))); 13591 s390_cc_set(1); 13592 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len1), mkexpr(num_bytes))); 13593 13594 /* Extract the bytes to be stored at addr1 */ 13595 IRTemp data = newTemp(Ity_I64); 13596 assign(data, binop(Iop_Shr64, mkexpr(retval), mkU8(16))); 13597 13598 /* To store the bytes construct 4 dirty helper calls. The helper calls 13599 are guarded (num_bytes == 1, num_bytes == 2, etc) such that only 13600 one of them will be called at runtime. */ 13601 UInt i; 13602 for (i = 1; i <= 4; ++i) { 13603 IRDirty *d; 13604 13605 d = unsafeIRDirty_0_N(0 /* regparms */, "s390x_dirtyhelper_CUxy", 13606 &s390x_dirtyhelper_CUxy, 13607 mkIRExprVec_3(mkexpr(addr1), mkexpr(data), 13608 mkexpr(num_bytes))); 13609 d->guard = binop(Iop_CmpEQ64, mkexpr(num_bytes), mkU64(i)); 13610 d->mFx = Ifx_Write; 13611 d->mAddr = mkexpr(addr1); 13612 d->mSize = i; 13613 stmt(IRStmt_Dirty(d)); 13614 } 13615 13616 /* Update source address and length */ 13617 IRTemp num_src_bytes = newTemp(Ity_I64); 13618 assign(num_src_bytes, 13619 mkite(binop(Iop_CmpEQ32, mkexpr(is_high_surrogate), mkU32(1)), 13620 mkU64(4), mkU64(2))); 13621 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(addr2), mkexpr(num_src_bytes))); 13622 put_gpr_dw0(r2 + 1, binop(Iop_Sub64, mkexpr(len2), mkexpr(num_src_bytes))); 13623 13624 /* Update destination address and length */ 13625 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(addr1), mkexpr(num_bytes))); 13626 put_gpr_dw0(r1 + 1, binop(Iop_Sub64, mkexpr(len1), mkexpr(num_bytes))); 13627 13628 iterate(); 13629 13630 return "cu21"; 13631 } 13632 13633 static IRExpr * 13634 s390_call_cu24(IRExpr *srcval, IRExpr *low_surrogate) 13635 { 13636 IRExpr **args, *call; 13637 args = mkIRExprVec_2(srcval, low_surrogate); 13638 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, 13639 "s390_do_cu24", &s390_do_cu24, args); 13640 13641 /* Nothing is excluded from definedness checking. */ 13642 call->Iex.CCall.cee->mcx_mask = 0; 13643 13644 return call; 13645 } 13646 13647 static const HChar * 13648 s390_irgen_CU24(UChar m3, UChar r1, UChar r2) 13649 { 13650 IRTemp addr1 = newTemp(Ity_I64); 13651 IRTemp addr2 = newTemp(Ity_I64); 13652 IRTemp len1 = newTemp(Ity_I64); 13653 IRTemp len2 = newTemp(Ity_I64); 13654 13655 assign(addr1, get_gpr_dw0(r1)); 13656 assign(addr2, get_gpr_dw0(r2)); 13657 assign(len1, get_gpr_dw0(r1 + 1)); 13658 assign(len2, get_gpr_dw0(r2 + 1)); 13659 13660 /* We're processing the 2nd operand 2 bytes at a time. Therefore, if 13661 there are less than 2 bytes left, then the 2nd operand is exhausted 13662 and we're done here. cc = 0 */ 13663 s390_cc_set(0); 13664 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len2), mkU64(2))); 13665 13666 /* There are at least two bytes there. Read them. */ 13667 IRTemp srcval = newTemp(Ity_I32); 13668 assign(srcval, unop(Iop_16Uto32, load(Ity_I16, mkexpr(addr2)))); 13669 13670 /* Find out whether this is a high surrogate. I.e. SRCVAL lies 13671 inside the interval [0xd800 - 0xdbff] */ 13672 IRTemp is_high_surrogate = newTemp(Ity_I32); 13673 IRExpr *flag1 = mkite(binop(Iop_CmpLE32U, mkU32(0xd800), mkexpr(srcval)), 13674 mkU32(1), mkU32(0)); 13675 IRExpr *flag2 = mkite(binop(Iop_CmpLE32U, mkexpr(srcval), mkU32(0xdbff)), 13676 mkU32(1), mkU32(0)); 13677 assign(is_high_surrogate, binop(Iop_And32, flag1, flag2)); 13678 13679 /* If SRCVAL is a high surrogate and there are less than 4 bytes left, 13680 then the 2nd operand is exhausted and we're done here. cc = 0 */ 13681 IRExpr *not_enough_bytes = 13682 mkite(binop(Iop_CmpLT64U, mkexpr(len2), mkU64(4)), mkU32(1), mkU32(0)); 13683 13684 next_insn_if(binop(Iop_CmpEQ32, 13685 binop(Iop_And32, mkexpr(is_high_surrogate), 13686 not_enough_bytes), 13687 mkU32(1))); 13688 13689 /* The 2nd operand is not exhausted. If the first 2 bytes are a high 13690 surrogate, read the next two bytes (low surrogate). */ 13691 IRTemp low_surrogate = newTemp(Ity_I32); 13692 IRExpr *low_surrogate_addr = binop(Iop_Add64, mkexpr(addr2), mkU64(2)); 13693 13694 assign(low_surrogate, 13695 mkite(binop(Iop_CmpEQ32, mkexpr(is_high_surrogate), mkU32(1)), 13696 unop(Iop_16Uto32, load(Ity_I16, low_surrogate_addr)), 13697 mkU32(0))); // any value is fine; it will not be used 13698 13699 /* Call the helper */ 13700 IRTemp retval = newTemp(Ity_I64); 13701 assign(retval, s390_call_cu24(unop(Iop_32Uto64, mkexpr(srcval)), 13702 unop(Iop_32Uto64, mkexpr(low_surrogate)))); 13703 13704 /* Before we can test whether the 1st operand is exhausted we need to 13705 test for an invalid low surrogate. Because cc=2 outranks cc=1. */ 13706 if (s390_host_has_etf3 && (m3 & 0x1) == 1) { 13707 IRExpr *invalid_low_surrogate = 13708 binop(Iop_And64, mkexpr(retval), mkU64(0xff)); 13709 13710 s390_cc_set(2); 13711 next_insn_if(binop(Iop_CmpEQ64, invalid_low_surrogate, mkU64(1))); 13712 } 13713 13714 /* Now test whether the 1st operand is exhausted */ 13715 s390_cc_set(1); 13716 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len1), mkU64(4))); 13717 13718 /* Extract the bytes to be stored at addr1 */ 13719 IRExpr *data = unop(Iop_64to32, binop(Iop_Shr64, mkexpr(retval), mkU8(8))); 13720 13721 store(mkexpr(addr1), data); 13722 13723 /* Update source address and length */ 13724 IRTemp num_src_bytes = newTemp(Ity_I64); 13725 assign(num_src_bytes, 13726 mkite(binop(Iop_CmpEQ32, mkexpr(is_high_surrogate), mkU32(1)), 13727 mkU64(4), mkU64(2))); 13728 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(addr2), mkexpr(num_src_bytes))); 13729 put_gpr_dw0(r2 + 1, binop(Iop_Sub64, mkexpr(len2), mkexpr(num_src_bytes))); 13730 13731 /* Update destination address and length */ 13732 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(addr1), mkU64(4))); 13733 put_gpr_dw0(r1 + 1, binop(Iop_Sub64, mkexpr(len1), mkU64(4))); 13734 13735 iterate(); 13736 13737 return "cu24"; 13738 } 13739 13740 static IRExpr * 13741 s390_call_cu42(IRExpr *srcval) 13742 { 13743 IRExpr **args, *call; 13744 args = mkIRExprVec_1(srcval); 13745 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, 13746 "s390_do_cu42", &s390_do_cu42, args); 13747 13748 /* Nothing is excluded from definedness checking. */ 13749 call->Iex.CCall.cee->mcx_mask = 0; 13750 13751 return call; 13752 } 13753 13754 static const HChar * 13755 s390_irgen_CU42(UChar r1, UChar r2) 13756 { 13757 IRTemp addr1 = newTemp(Ity_I64); 13758 IRTemp addr2 = newTemp(Ity_I64); 13759 IRTemp len1 = newTemp(Ity_I64); 13760 IRTemp len2 = newTemp(Ity_I64); 13761 13762 assign(addr1, get_gpr_dw0(r1)); 13763 assign(addr2, get_gpr_dw0(r2)); 13764 assign(len1, get_gpr_dw0(r1 + 1)); 13765 assign(len2, get_gpr_dw0(r2 + 1)); 13766 13767 /* We're processing the 2nd operand 4 bytes at a time. Therefore, if 13768 there are less than 4 bytes left, then the 2nd operand is exhausted 13769 and we're done here. cc = 0 */ 13770 s390_cc_set(0); 13771 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len2), mkU64(4))); 13772 13773 /* Read the 2nd operand. */ 13774 IRTemp srcval = newTemp(Ity_I32); 13775 assign(srcval, load(Ity_I32, mkexpr(addr2))); 13776 13777 /* Call the helper */ 13778 IRTemp retval = newTemp(Ity_I64); 13779 assign(retval, s390_call_cu42(unop(Iop_32Uto64, mkexpr(srcval)))); 13780 13781 /* If the UTF-32 character was invalid, set cc=2 and we're done. 13782 cc=2 outranks cc=1 (1st operand exhausted) */ 13783 IRExpr *invalid_character = binop(Iop_And64, mkexpr(retval), mkU64(0xff)); 13784 13785 s390_cc_set(2); 13786 next_insn_if(binop(Iop_CmpEQ64, invalid_character, mkU64(1))); 13787 13788 /* Now test whether the 1st operand is exhausted */ 13789 IRTemp num_bytes = newTemp(Ity_I64); 13790 assign(num_bytes, binop(Iop_And64, 13791 binop(Iop_Shr64, mkexpr(retval), mkU8(8)), 13792 mkU64(0xff))); 13793 s390_cc_set(1); 13794 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len1), mkexpr(num_bytes))); 13795 13796 /* Extract the bytes to be stored at addr1 */ 13797 IRTemp data = newTemp(Ity_I64); 13798 assign(data, binop(Iop_Shr64, mkexpr(retval), mkU8(16))); 13799 13800 /* To store the bytes construct 2 dirty helper calls. The helper calls 13801 are guarded (num_bytes == 2 and num_bytes == 4, respectively) such 13802 that only one of them will be called at runtime. */ 13803 13804 Int i; 13805 for (i = 2; i <= 4; ++i) { 13806 IRDirty *d; 13807 13808 if (i == 3) continue; // skip this one 13809 13810 d = unsafeIRDirty_0_N(0 /* regparms */, "s390x_dirtyhelper_CUxy", 13811 &s390x_dirtyhelper_CUxy, 13812 mkIRExprVec_3(mkexpr(addr1), mkexpr(data), 13813 mkexpr(num_bytes))); 13814 d->guard = binop(Iop_CmpEQ64, mkexpr(num_bytes), mkU64(i)); 13815 d->mFx = Ifx_Write; 13816 d->mAddr = mkexpr(addr1); 13817 d->mSize = i; 13818 stmt(IRStmt_Dirty(d)); 13819 } 13820 13821 /* Update source address and length */ 13822 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(addr2), mkU64(4))); 13823 put_gpr_dw0(r2 + 1, binop(Iop_Sub64, mkexpr(len2), mkU64(4))); 13824 13825 /* Update destination address and length */ 13826 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(addr1), mkexpr(num_bytes))); 13827 put_gpr_dw0(r1 + 1, binop(Iop_Sub64, mkexpr(len1), mkexpr(num_bytes))); 13828 13829 iterate(); 13830 13831 return "cu42"; 13832 } 13833 13834 static IRExpr * 13835 s390_call_cu41(IRExpr *srcval) 13836 { 13837 IRExpr **args, *call; 13838 args = mkIRExprVec_1(srcval); 13839 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, 13840 "s390_do_cu41", &s390_do_cu41, args); 13841 13842 /* Nothing is excluded from definedness checking. */ 13843 call->Iex.CCall.cee->mcx_mask = 0; 13844 13845 return call; 13846 } 13847 13848 static const HChar * 13849 s390_irgen_CU41(UChar r1, UChar r2) 13850 { 13851 IRTemp addr1 = newTemp(Ity_I64); 13852 IRTemp addr2 = newTemp(Ity_I64); 13853 IRTemp len1 = newTemp(Ity_I64); 13854 IRTemp len2 = newTemp(Ity_I64); 13855 13856 assign(addr1, get_gpr_dw0(r1)); 13857 assign(addr2, get_gpr_dw0(r2)); 13858 assign(len1, get_gpr_dw0(r1 + 1)); 13859 assign(len2, get_gpr_dw0(r2 + 1)); 13860 13861 /* We're processing the 2nd operand 4 bytes at a time. Therefore, if 13862 there are less than 4 bytes left, then the 2nd operand is exhausted 13863 and we're done here. cc = 0 */ 13864 s390_cc_set(0); 13865 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len2), mkU64(4))); 13866 13867 /* Read the 2nd operand. */ 13868 IRTemp srcval = newTemp(Ity_I32); 13869 assign(srcval, load(Ity_I32, mkexpr(addr2))); 13870 13871 /* Call the helper */ 13872 IRTemp retval = newTemp(Ity_I64); 13873 assign(retval, s390_call_cu41(unop(Iop_32Uto64, mkexpr(srcval)))); 13874 13875 /* If the UTF-32 character was invalid, set cc=2 and we're done. 13876 cc=2 outranks cc=1 (1st operand exhausted) */ 13877 IRExpr *invalid_character = binop(Iop_And64, mkexpr(retval), mkU64(0xff)); 13878 13879 s390_cc_set(2); 13880 next_insn_if(binop(Iop_CmpEQ64, invalid_character, mkU64(1))); 13881 13882 /* Now test whether the 1st operand is exhausted */ 13883 IRTemp num_bytes = newTemp(Ity_I64); 13884 assign(num_bytes, binop(Iop_And64, 13885 binop(Iop_Shr64, mkexpr(retval), mkU8(8)), 13886 mkU64(0xff))); 13887 s390_cc_set(1); 13888 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len1), mkexpr(num_bytes))); 13889 13890 /* Extract the bytes to be stored at addr1 */ 13891 IRTemp data = newTemp(Ity_I64); 13892 assign(data, binop(Iop_Shr64, mkexpr(retval), mkU8(16))); 13893 13894 /* To store the bytes construct 4 dirty helper calls. The helper calls 13895 are guarded (num_bytes == 1, num_bytes == 2, etc) such that only 13896 one of them will be called at runtime. */ 13897 UInt i; 13898 for (i = 1; i <= 4; ++i) { 13899 IRDirty *d; 13900 13901 d = unsafeIRDirty_0_N(0 /* regparms */, "s390x_dirtyhelper_CUxy", 13902 &s390x_dirtyhelper_CUxy, 13903 mkIRExprVec_3(mkexpr(addr1), mkexpr(data), 13904 mkexpr(num_bytes))); 13905 d->guard = binop(Iop_CmpEQ64, mkexpr(num_bytes), mkU64(i)); 13906 d->mFx = Ifx_Write; 13907 d->mAddr = mkexpr(addr1); 13908 d->mSize = i; 13909 stmt(IRStmt_Dirty(d)); 13910 } 13911 13912 /* Update source address and length */ 13913 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(addr2), mkU64(4))); 13914 put_gpr_dw0(r2 + 1, binop(Iop_Sub64, mkexpr(len2), mkU64(4))); 13915 13916 /* Update destination address and length */ 13917 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(addr1), mkexpr(num_bytes))); 13918 put_gpr_dw0(r1 + 1, binop(Iop_Sub64, mkexpr(len1), mkexpr(num_bytes))); 13919 13920 iterate(); 13921 13922 return "cu41"; 13923 } 13924 13925 static IRExpr * 13926 s390_call_cu12_cu14_helper1(IRExpr *byte1, IRExpr *etf3_and_m3_is_1) 13927 { 13928 IRExpr **args, *call; 13929 args = mkIRExprVec_2(byte1, etf3_and_m3_is_1); 13930 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, "s390_do_cu12_cu14_helper1", 13931 &s390_do_cu12_cu14_helper1, args); 13932 13933 /* Nothing is excluded from definedness checking. */ 13934 call->Iex.CCall.cee->mcx_mask = 0; 13935 13936 return call; 13937 } 13938 13939 static IRExpr * 13940 s390_call_cu12_helper2(IRExpr *byte1, IRExpr *byte2, IRExpr *byte3, 13941 IRExpr *byte4, IRExpr *stuff) 13942 { 13943 IRExpr **args, *call; 13944 args = mkIRExprVec_5(byte1, byte2, byte3, byte4, stuff); 13945 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, 13946 "s390_do_cu12_helper2", &s390_do_cu12_helper2, args); 13947 13948 /* Nothing is excluded from definedness checking. */ 13949 call->Iex.CCall.cee->mcx_mask = 0; 13950 13951 return call; 13952 } 13953 13954 static IRExpr * 13955 s390_call_cu14_helper2(IRExpr *byte1, IRExpr *byte2, IRExpr *byte3, 13956 IRExpr *byte4, IRExpr *stuff) 13957 { 13958 IRExpr **args, *call; 13959 args = mkIRExprVec_5(byte1, byte2, byte3, byte4, stuff); 13960 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, 13961 "s390_do_cu14_helper2", &s390_do_cu14_helper2, args); 13962 13963 /* Nothing is excluded from definedness checking. */ 13964 call->Iex.CCall.cee->mcx_mask = 0; 13965 13966 return call; 13967 } 13968 13969 static void 13970 s390_irgen_cu12_cu14(UChar m3, UChar r1, UChar r2, Bool is_cu12) 13971 { 13972 IRTemp addr1 = newTemp(Ity_I64); 13973 IRTemp addr2 = newTemp(Ity_I64); 13974 IRTemp len1 = newTemp(Ity_I64); 13975 IRTemp len2 = newTemp(Ity_I64); 13976 13977 assign(addr1, get_gpr_dw0(r1)); 13978 assign(addr2, get_gpr_dw0(r2)); 13979 assign(len1, get_gpr_dw0(r1 + 1)); 13980 assign(len2, get_gpr_dw0(r2 + 1)); 13981 13982 UInt extended_checking = s390_host_has_etf3 && (m3 & 0x1) == 1; 13983 13984 /* We're processing the 2nd operand 1 byte at a time. Therefore, if 13985 there is less than 1 byte left, then the 2nd operand is exhausted 13986 and we're done here. cc = 0 */ 13987 s390_cc_set(0); 13988 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len2), mkU64(1))); 13989 13990 /* There is at least one byte there. Read it. */ 13991 IRTemp byte1 = newTemp(Ity_I64); 13992 assign(byte1, unop(Iop_8Uto64, load(Ity_I8, mkexpr(addr2)))); 13993 13994 /* Call the helper to get number of bytes and invalid byte indicator */ 13995 IRTemp retval1 = newTemp(Ity_I64); 13996 assign(retval1, s390_call_cu12_cu14_helper1(mkexpr(byte1), 13997 mkU64(extended_checking))); 13998 13999 /* Check for invalid 1st byte */ 14000 IRExpr *is_invalid = unop(Iop_64to1, mkexpr(retval1)); 14001 s390_cc_set(2); 14002 next_insn_if(is_invalid); 14003 14004 /* How many bytes do we have to read? */ 14005 IRTemp num_src_bytes = newTemp(Ity_I64); 14006 assign(num_src_bytes, binop(Iop_Shr64, mkexpr(retval1), mkU8(8))); 14007 14008 /* Now test whether the 2nd operand is exhausted */ 14009 s390_cc_set(0); 14010 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len2), mkexpr(num_src_bytes))); 14011 14012 /* Read the remaining bytes */ 14013 IRExpr *cond, *addr, *byte2, *byte3, *byte4; 14014 14015 cond = binop(Iop_CmpLE64U, mkU64(2), mkexpr(num_src_bytes)); 14016 addr = binop(Iop_Add64, mkexpr(addr2), mkU64(1)); 14017 byte2 = mkite(cond, unop(Iop_8Uto64, load(Ity_I8, addr)), mkU64(0)); 14018 cond = binop(Iop_CmpLE64U, mkU64(3), mkexpr(num_src_bytes)); 14019 addr = binop(Iop_Add64, mkexpr(addr2), mkU64(2)); 14020 byte3 = mkite(cond, unop(Iop_8Uto64, load(Ity_I8, addr)), mkU64(0)); 14021 cond = binop(Iop_CmpLE64U, mkU64(4), mkexpr(num_src_bytes)); 14022 addr = binop(Iop_Add64, mkexpr(addr2), mkU64(3)); 14023 byte4 = mkite(cond, unop(Iop_8Uto64, load(Ity_I8, addr)), mkU64(0)); 14024 14025 /* Call the helper to get the converted value and invalid byte indicator. 14026 We can pass at most 5 arguments; therefore some encoding is needed 14027 here */ 14028 IRExpr *stuff = binop(Iop_Or64, 14029 binop(Iop_Shl64, mkexpr(num_src_bytes), mkU8(1)), 14030 mkU64(extended_checking)); 14031 IRTemp retval2 = newTemp(Ity_I64); 14032 14033 if (is_cu12) { 14034 assign(retval2, s390_call_cu12_helper2(mkexpr(byte1), byte2, byte3, 14035 byte4, stuff)); 14036 } else { 14037 assign(retval2, s390_call_cu14_helper2(mkexpr(byte1), byte2, byte3, 14038 byte4, stuff)); 14039 } 14040 14041 /* Check for invalid character */ 14042 s390_cc_set(2); 14043 is_invalid = unop(Iop_64to1, mkexpr(retval2)); 14044 next_insn_if(is_invalid); 14045 14046 /* Now test whether the 1st operand is exhausted */ 14047 IRTemp num_bytes = newTemp(Ity_I64); 14048 assign(num_bytes, binop(Iop_And64, 14049 binop(Iop_Shr64, mkexpr(retval2), mkU8(8)), 14050 mkU64(0xff))); 14051 s390_cc_set(1); 14052 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len1), mkexpr(num_bytes))); 14053 14054 /* Extract the bytes to be stored at addr1 */ 14055 IRTemp data = newTemp(Ity_I64); 14056 assign(data, binop(Iop_Shr64, mkexpr(retval2), mkU8(16))); 14057 14058 if (is_cu12) { 14059 /* To store the bytes construct 2 dirty helper calls. The helper calls 14060 are guarded (num_bytes == 2 and num_bytes == 4, respectively) such 14061 that only one of them will be called at runtime. */ 14062 14063 Int i; 14064 for (i = 2; i <= 4; ++i) { 14065 IRDirty *d; 14066 14067 if (i == 3) continue; // skip this one 14068 14069 d = unsafeIRDirty_0_N(0 /* regparms */, "s390x_dirtyhelper_CUxy", 14070 &s390x_dirtyhelper_CUxy, 14071 mkIRExprVec_3(mkexpr(addr1), mkexpr(data), 14072 mkexpr(num_bytes))); 14073 d->guard = binop(Iop_CmpEQ64, mkexpr(num_bytes), mkU64(i)); 14074 d->mFx = Ifx_Write; 14075 d->mAddr = mkexpr(addr1); 14076 d->mSize = i; 14077 stmt(IRStmt_Dirty(d)); 14078 } 14079 } else { 14080 // cu14 14081 store(mkexpr(addr1), unop(Iop_64to32, mkexpr(data))); 14082 } 14083 14084 /* Update source address and length */ 14085 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(addr2), mkexpr(num_src_bytes))); 14086 put_gpr_dw0(r2 + 1, binop(Iop_Sub64, mkexpr(len2), mkexpr(num_src_bytes))); 14087 14088 /* Update destination address and length */ 14089 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(addr1), mkexpr(num_bytes))); 14090 put_gpr_dw0(r1 + 1, binop(Iop_Sub64, mkexpr(len1), mkexpr(num_bytes))); 14091 14092 iterate(); 14093 } 14094 14095 static const HChar * 14096 s390_irgen_CU12(UChar m3, UChar r1, UChar r2) 14097 { 14098 s390_irgen_cu12_cu14(m3, r1, r2, /* is_cu12 = */ 1); 14099 14100 return "cu12"; 14101 } 14102 14103 static const HChar * 14104 s390_irgen_CU14(UChar m3, UChar r1, UChar r2) 14105 { 14106 s390_irgen_cu12_cu14(m3, r1, r2, /* is_cu12 = */ 0); 14107 14108 return "cu14"; 14109 } 14110 14111 static IRExpr * 14112 s390_call_ecag(IRExpr *op2addr) 14113 { 14114 IRExpr **args, *call; 14115 14116 args = mkIRExprVec_1(op2addr); 14117 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, 14118 "s390_do_ecag", &s390_do_ecag, args); 14119 14120 /* Nothing is excluded from definedness checking. */ 14121 call->Iex.CCall.cee->mcx_mask = 0; 14122 14123 return call; 14124 } 14125 14126 static const HChar * 14127 s390_irgen_ECAG(UChar r1, UChar r3 __attribute__((unused)), IRTemp op2addr) 14128 { 14129 if (! s390_host_has_gie) { 14130 emulation_failure(EmFail_S390X_ecag); 14131 } else { 14132 put_gpr_dw0(r1, s390_call_ecag(mkexpr(op2addr))); 14133 } 14134 14135 return "ecag"; 14136 } 14137 14138 14139 /* New insns are added here. 14140 If an insn is contingent on a facility being installed also 14141 check whether the list of supported facilities in function 14142 s390x_dirtyhelper_STFLE needs updating */ 14143 14144 /*------------------------------------------------------------*/ 14145 /*--- Build IR for special instructions ---*/ 14146 /*------------------------------------------------------------*/ 14147 14148 static void 14149 s390_irgen_client_request(void) 14150 { 14151 if (0) 14152 vex_printf("%%R3 = client_request ( %%R2 )\n"); 14153 14154 Addr64 next = guest_IA_curr_instr + S390_SPECIAL_OP_PREAMBLE_SIZE 14155 + S390_SPECIAL_OP_SIZE; 14156 14157 dis_res->jk_StopHere = Ijk_ClientReq; 14158 dis_res->whatNext = Dis_StopHere; 14159 14160 put_IA(mkaddr_expr(next)); 14161 } 14162 14163 static void 14164 s390_irgen_guest_NRADDR(void) 14165 { 14166 if (0) 14167 vex_printf("%%R3 = guest_NRADDR\n"); 14168 14169 put_gpr_dw0(3, IRExpr_Get(S390X_GUEST_OFFSET(guest_NRADDR), Ity_I64)); 14170 } 14171 14172 static void 14173 s390_irgen_call_noredir(void) 14174 { 14175 Addr64 next = guest_IA_curr_instr + S390_SPECIAL_OP_PREAMBLE_SIZE 14176 + S390_SPECIAL_OP_SIZE; 14177 14178 /* Continue after special op */ 14179 put_gpr_dw0(14, mkaddr_expr(next)); 14180 14181 /* The address is in REG1, all parameters are in the right (guest) places */ 14182 put_IA(get_gpr_dw0(1)); 14183 14184 dis_res->whatNext = Dis_StopHere; 14185 dis_res->jk_StopHere = Ijk_NoRedir; 14186 } 14187 14188 /* Force proper alignment for the structures below. */ 14189 #pragma pack(1) 14190 14191 14192 static s390_decode_t 14193 s390_decode_2byte_and_irgen(const UChar *bytes) 14194 { 14195 typedef union { 14196 struct { 14197 unsigned int op : 16; 14198 } E; 14199 struct { 14200 unsigned int op : 8; 14201 unsigned int i : 8; 14202 } I; 14203 struct { 14204 unsigned int op : 8; 14205 unsigned int r1 : 4; 14206 unsigned int r2 : 4; 14207 } RR; 14208 } formats; 14209 union { 14210 formats fmt; 14211 UShort value; 14212 } ovl; 14213 14214 vassert(sizeof(formats) == 2); 14215 14216 ((UChar *)(&ovl.value))[0] = bytes[0]; 14217 ((UChar *)(&ovl.value))[1] = bytes[1]; 14218 14219 switch (ovl.value & 0xffff) { 14220 case 0x0101: /* PR */ goto unimplemented; 14221 case 0x0102: /* UPT */ goto unimplemented; 14222 case 0x0104: /* PTFF */ goto unimplemented; 14223 case 0x0107: /* SCKPF */ goto unimplemented; 14224 case 0x010a: s390_format_E(s390_irgen_PFPO); goto ok; 14225 case 0x010b: /* TAM */ goto unimplemented; 14226 case 0x010c: /* SAM24 */ goto unimplemented; 14227 case 0x010d: /* SAM31 */ goto unimplemented; 14228 case 0x010e: /* SAM64 */ goto unimplemented; 14229 case 0x01ff: /* TRAP2 */ goto unimplemented; 14230 } 14231 14232 switch ((ovl.value & 0xff00) >> 8) { 14233 case 0x04: /* SPM */ goto unimplemented; 14234 case 0x05: /* BALR */ goto unimplemented; 14235 case 0x06: s390_format_RR_RR(s390_irgen_BCTR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14236 goto ok; 14237 case 0x07: s390_format_RR(s390_irgen_BCR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14238 goto ok; 14239 case 0x0a: s390_format_I(s390_irgen_SVC, ovl.fmt.I.i); goto ok; 14240 case 0x0b: /* BSM */ goto unimplemented; 14241 case 0x0c: /* BASSM */ goto unimplemented; 14242 case 0x0d: s390_format_RR_RR(s390_irgen_BASR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14243 goto ok; 14244 case 0x0e: s390_format_RR(s390_irgen_MVCL, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14245 goto ok; 14246 case 0x0f: s390_format_RR(s390_irgen_CLCL, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14247 goto ok; 14248 case 0x10: s390_format_RR_RR(s390_irgen_LPR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14249 goto ok; 14250 case 0x11: s390_format_RR_RR(s390_irgen_LNR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14251 goto ok; 14252 case 0x12: s390_format_RR_RR(s390_irgen_LTR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14253 goto ok; 14254 case 0x13: s390_format_RR_RR(s390_irgen_LCR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14255 goto ok; 14256 case 0x14: s390_format_RR_RR(s390_irgen_NR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14257 goto ok; 14258 case 0x15: s390_format_RR_RR(s390_irgen_CLR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14259 goto ok; 14260 case 0x16: s390_format_RR_RR(s390_irgen_OR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14261 goto ok; 14262 case 0x17: s390_format_RR_RR(s390_irgen_XR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14263 goto ok; 14264 case 0x18: s390_format_RR_RR(s390_irgen_LR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14265 goto ok; 14266 case 0x19: s390_format_RR_RR(s390_irgen_CR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14267 goto ok; 14268 case 0x1a: s390_format_RR_RR(s390_irgen_AR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14269 goto ok; 14270 case 0x1b: s390_format_RR_RR(s390_irgen_SR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14271 goto ok; 14272 case 0x1c: s390_format_RR_RR(s390_irgen_MR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14273 goto ok; 14274 case 0x1d: s390_format_RR_RR(s390_irgen_DR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14275 goto ok; 14276 case 0x1e: s390_format_RR_RR(s390_irgen_ALR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14277 goto ok; 14278 case 0x1f: s390_format_RR_RR(s390_irgen_SLR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14279 goto ok; 14280 case 0x20: /* LPDR */ goto unimplemented; 14281 case 0x21: /* LNDR */ goto unimplemented; 14282 case 0x22: /* LTDR */ goto unimplemented; 14283 case 0x23: /* LCDR */ goto unimplemented; 14284 case 0x24: /* HDR */ goto unimplemented; 14285 case 0x25: /* LDXR */ goto unimplemented; 14286 case 0x26: /* MXR */ goto unimplemented; 14287 case 0x27: /* MXDR */ goto unimplemented; 14288 case 0x28: s390_format_RR_FF(s390_irgen_LDR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14289 goto ok; 14290 case 0x29: /* CDR */ goto unimplemented; 14291 case 0x2a: /* ADR */ goto unimplemented; 14292 case 0x2b: /* SDR */ goto unimplemented; 14293 case 0x2c: /* MDR */ goto unimplemented; 14294 case 0x2d: /* DDR */ goto unimplemented; 14295 case 0x2e: /* AWR */ goto unimplemented; 14296 case 0x2f: /* SWR */ goto unimplemented; 14297 case 0x30: /* LPER */ goto unimplemented; 14298 case 0x31: /* LNER */ goto unimplemented; 14299 case 0x32: /* LTER */ goto unimplemented; 14300 case 0x33: /* LCER */ goto unimplemented; 14301 case 0x34: /* HER */ goto unimplemented; 14302 case 0x35: /* LEDR */ goto unimplemented; 14303 case 0x36: /* AXR */ goto unimplemented; 14304 case 0x37: /* SXR */ goto unimplemented; 14305 case 0x38: s390_format_RR_FF(s390_irgen_LER, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14306 goto ok; 14307 case 0x39: /* CER */ goto unimplemented; 14308 case 0x3a: /* AER */ goto unimplemented; 14309 case 0x3b: /* SER */ goto unimplemented; 14310 case 0x3c: /* MDER */ goto unimplemented; 14311 case 0x3d: /* DER */ goto unimplemented; 14312 case 0x3e: /* AUR */ goto unimplemented; 14313 case 0x3f: /* SUR */ goto unimplemented; 14314 } 14315 14316 return S390_DECODE_UNKNOWN_INSN; 14317 14318 ok: 14319 return S390_DECODE_OK; 14320 14321 unimplemented: 14322 return S390_DECODE_UNIMPLEMENTED_INSN; 14323 } 14324 14325 static s390_decode_t 14326 s390_decode_4byte_and_irgen(const UChar *bytes) 14327 { 14328 typedef union { 14329 struct { 14330 unsigned int op1 : 8; 14331 unsigned int r1 : 4; 14332 unsigned int op2 : 4; 14333 unsigned int i2 : 16; 14334 } RI; 14335 struct { 14336 unsigned int op : 16; 14337 unsigned int : 8; 14338 unsigned int r1 : 4; 14339 unsigned int r2 : 4; 14340 } RRE; 14341 struct { 14342 unsigned int op : 16; 14343 unsigned int r1 : 4; 14344 unsigned int : 4; 14345 unsigned int r3 : 4; 14346 unsigned int r2 : 4; 14347 } RRF; 14348 struct { 14349 unsigned int op : 16; 14350 unsigned int m3 : 4; 14351 unsigned int m4 : 4; 14352 unsigned int r1 : 4; 14353 unsigned int r2 : 4; 14354 } RRF2; 14355 struct { 14356 unsigned int op : 16; 14357 unsigned int r3 : 4; 14358 unsigned int : 4; 14359 unsigned int r1 : 4; 14360 unsigned int r2 : 4; 14361 } RRF3; 14362 struct { 14363 unsigned int op : 16; 14364 unsigned int r3 : 4; 14365 unsigned int : 4; 14366 unsigned int r1 : 4; 14367 unsigned int r2 : 4; 14368 } RRR; 14369 struct { 14370 unsigned int op : 16; 14371 unsigned int r3 : 4; 14372 unsigned int m4 : 4; 14373 unsigned int r1 : 4; 14374 unsigned int r2 : 4; 14375 } RRF4; 14376 struct { 14377 unsigned int op : 16; 14378 unsigned int : 4; 14379 unsigned int m4 : 4; 14380 unsigned int r1 : 4; 14381 unsigned int r2 : 4; 14382 } RRF5; 14383 struct { 14384 unsigned int op : 8; 14385 unsigned int r1 : 4; 14386 unsigned int r3 : 4; 14387 unsigned int b2 : 4; 14388 unsigned int d2 : 12; 14389 } RS; 14390 struct { 14391 unsigned int op : 8; 14392 unsigned int r1 : 4; 14393 unsigned int r3 : 4; 14394 unsigned int i2 : 16; 14395 } RSI; 14396 struct { 14397 unsigned int op : 8; 14398 unsigned int r1 : 4; 14399 unsigned int x2 : 4; 14400 unsigned int b2 : 4; 14401 unsigned int d2 : 12; 14402 } RX; 14403 struct { 14404 unsigned int op : 16; 14405 unsigned int b2 : 4; 14406 unsigned int d2 : 12; 14407 } S; 14408 struct { 14409 unsigned int op : 8; 14410 unsigned int i2 : 8; 14411 unsigned int b1 : 4; 14412 unsigned int d1 : 12; 14413 } SI; 14414 } formats; 14415 union { 14416 formats fmt; 14417 UInt value; 14418 } ovl; 14419 14420 vassert(sizeof(formats) == 4); 14421 14422 ((UChar *)(&ovl.value))[0] = bytes[0]; 14423 ((UChar *)(&ovl.value))[1] = bytes[1]; 14424 ((UChar *)(&ovl.value))[2] = bytes[2]; 14425 ((UChar *)(&ovl.value))[3] = bytes[3]; 14426 14427 switch ((ovl.value & 0xff0f0000) >> 16) { 14428 case 0xa500: s390_format_RI_RU(s390_irgen_IIHH, ovl.fmt.RI.r1, 14429 ovl.fmt.RI.i2); goto ok; 14430 case 0xa501: s390_format_RI_RU(s390_irgen_IIHL, ovl.fmt.RI.r1, 14431 ovl.fmt.RI.i2); goto ok; 14432 case 0xa502: s390_format_RI_RU(s390_irgen_IILH, ovl.fmt.RI.r1, 14433 ovl.fmt.RI.i2); goto ok; 14434 case 0xa503: s390_format_RI_RU(s390_irgen_IILL, ovl.fmt.RI.r1, 14435 ovl.fmt.RI.i2); goto ok; 14436 case 0xa504: s390_format_RI_RU(s390_irgen_NIHH, ovl.fmt.RI.r1, 14437 ovl.fmt.RI.i2); goto ok; 14438 case 0xa505: s390_format_RI_RU(s390_irgen_NIHL, ovl.fmt.RI.r1, 14439 ovl.fmt.RI.i2); goto ok; 14440 case 0xa506: s390_format_RI_RU(s390_irgen_NILH, ovl.fmt.RI.r1, 14441 ovl.fmt.RI.i2); goto ok; 14442 case 0xa507: s390_format_RI_RU(s390_irgen_NILL, ovl.fmt.RI.r1, 14443 ovl.fmt.RI.i2); goto ok; 14444 case 0xa508: s390_format_RI_RU(s390_irgen_OIHH, ovl.fmt.RI.r1, 14445 ovl.fmt.RI.i2); goto ok; 14446 case 0xa509: s390_format_RI_RU(s390_irgen_OIHL, ovl.fmt.RI.r1, 14447 ovl.fmt.RI.i2); goto ok; 14448 case 0xa50a: s390_format_RI_RU(s390_irgen_OILH, ovl.fmt.RI.r1, 14449 ovl.fmt.RI.i2); goto ok; 14450 case 0xa50b: s390_format_RI_RU(s390_irgen_OILL, ovl.fmt.RI.r1, 14451 ovl.fmt.RI.i2); goto ok; 14452 case 0xa50c: s390_format_RI_RU(s390_irgen_LLIHH, ovl.fmt.RI.r1, 14453 ovl.fmt.RI.i2); goto ok; 14454 case 0xa50d: s390_format_RI_RU(s390_irgen_LLIHL, ovl.fmt.RI.r1, 14455 ovl.fmt.RI.i2); goto ok; 14456 case 0xa50e: s390_format_RI_RU(s390_irgen_LLILH, ovl.fmt.RI.r1, 14457 ovl.fmt.RI.i2); goto ok; 14458 case 0xa50f: s390_format_RI_RU(s390_irgen_LLILL, ovl.fmt.RI.r1, 14459 ovl.fmt.RI.i2); goto ok; 14460 case 0xa700: s390_format_RI_RU(s390_irgen_TMLH, ovl.fmt.RI.r1, 14461 ovl.fmt.RI.i2); goto ok; 14462 case 0xa701: s390_format_RI_RU(s390_irgen_TMLL, ovl.fmt.RI.r1, 14463 ovl.fmt.RI.i2); goto ok; 14464 case 0xa702: s390_format_RI_RU(s390_irgen_TMHH, ovl.fmt.RI.r1, 14465 ovl.fmt.RI.i2); goto ok; 14466 case 0xa703: s390_format_RI_RU(s390_irgen_TMHL, ovl.fmt.RI.r1, 14467 ovl.fmt.RI.i2); goto ok; 14468 case 0xa704: s390_format_RI(s390_irgen_BRC, ovl.fmt.RI.r1, ovl.fmt.RI.i2); 14469 goto ok; 14470 case 0xa705: s390_format_RI_RP(s390_irgen_BRAS, ovl.fmt.RI.r1, 14471 ovl.fmt.RI.i2); goto ok; 14472 case 0xa706: s390_format_RI_RP(s390_irgen_BRCT, ovl.fmt.RI.r1, 14473 ovl.fmt.RI.i2); goto ok; 14474 case 0xa707: s390_format_RI_RP(s390_irgen_BRCTG, ovl.fmt.RI.r1, 14475 ovl.fmt.RI.i2); goto ok; 14476 case 0xa708: s390_format_RI_RI(s390_irgen_LHI, ovl.fmt.RI.r1, ovl.fmt.RI.i2); 14477 goto ok; 14478 case 0xa709: s390_format_RI_RI(s390_irgen_LGHI, ovl.fmt.RI.r1, 14479 ovl.fmt.RI.i2); goto ok; 14480 case 0xa70a: s390_format_RI_RI(s390_irgen_AHI, ovl.fmt.RI.r1, ovl.fmt.RI.i2); 14481 goto ok; 14482 case 0xa70b: s390_format_RI_RI(s390_irgen_AGHI, ovl.fmt.RI.r1, 14483 ovl.fmt.RI.i2); goto ok; 14484 case 0xa70c: s390_format_RI_RI(s390_irgen_MHI, ovl.fmt.RI.r1, ovl.fmt.RI.i2); 14485 goto ok; 14486 case 0xa70d: s390_format_RI_RI(s390_irgen_MGHI, ovl.fmt.RI.r1, 14487 ovl.fmt.RI.i2); goto ok; 14488 case 0xa70e: s390_format_RI_RI(s390_irgen_CHI, ovl.fmt.RI.r1, ovl.fmt.RI.i2); 14489 goto ok; 14490 case 0xa70f: s390_format_RI_RI(s390_irgen_CGHI, ovl.fmt.RI.r1, 14491 ovl.fmt.RI.i2); goto ok; 14492 } 14493 14494 switch ((ovl.value & 0xffff0000) >> 16) { 14495 case 0x8000: /* SSM */ goto unimplemented; 14496 case 0x8200: /* LPSW */ goto unimplemented; 14497 case 0x9300: /* TS */ goto unimplemented; 14498 case 0xb202: /* STIDP */ goto unimplemented; 14499 case 0xb204: /* SCK */ goto unimplemented; 14500 case 0xb205: s390_format_S_RD(s390_irgen_STCK, ovl.fmt.S.b2, ovl.fmt.S.d2); 14501 goto ok; 14502 case 0xb206: /* SCKC */ goto unimplemented; 14503 case 0xb207: /* STCKC */ goto unimplemented; 14504 case 0xb208: /* SPT */ goto unimplemented; 14505 case 0xb209: /* STPT */ goto unimplemented; 14506 case 0xb20a: /* SPKA */ goto unimplemented; 14507 case 0xb20b: /* IPK */ goto unimplemented; 14508 case 0xb20d: /* PTLB */ goto unimplemented; 14509 case 0xb210: /* SPX */ goto unimplemented; 14510 case 0xb211: /* STPX */ goto unimplemented; 14511 case 0xb212: /* STAP */ goto unimplemented; 14512 case 0xb214: /* SIE */ goto unimplemented; 14513 case 0xb218: /* PC */ goto unimplemented; 14514 case 0xb219: /* SAC */ goto unimplemented; 14515 case 0xb21a: /* CFC */ goto unimplemented; 14516 case 0xb221: /* IPTE */ goto unimplemented; 14517 case 0xb222: s390_format_RRE_R0(s390_irgen_IPM, ovl.fmt.RRE.r1); goto ok; 14518 case 0xb223: /* IVSK */ goto unimplemented; 14519 case 0xb224: /* IAC */ goto unimplemented; 14520 case 0xb225: /* SSAR */ goto unimplemented; 14521 case 0xb226: /* EPAR */ goto unimplemented; 14522 case 0xb227: /* ESAR */ goto unimplemented; 14523 case 0xb228: /* PT */ goto unimplemented; 14524 case 0xb229: /* ISKE */ goto unimplemented; 14525 case 0xb22a: /* RRBE */ goto unimplemented; 14526 case 0xb22b: /* SSKE */ goto unimplemented; 14527 case 0xb22c: /* TB */ goto unimplemented; 14528 case 0xb22d: /* DXR */ goto unimplemented; 14529 case 0xb22e: /* PGIN */ goto unimplemented; 14530 case 0xb22f: /* PGOUT */ goto unimplemented; 14531 case 0xb230: /* CSCH */ goto unimplemented; 14532 case 0xb231: /* HSCH */ goto unimplemented; 14533 case 0xb232: /* MSCH */ goto unimplemented; 14534 case 0xb233: /* SSCH */ goto unimplemented; 14535 case 0xb234: /* STSCH */ goto unimplemented; 14536 case 0xb235: /* TSCH */ goto unimplemented; 14537 case 0xb236: /* TPI */ goto unimplemented; 14538 case 0xb237: /* SAL */ goto unimplemented; 14539 case 0xb238: /* RSCH */ goto unimplemented; 14540 case 0xb239: /* STCRW */ goto unimplemented; 14541 case 0xb23a: /* STCPS */ goto unimplemented; 14542 case 0xb23b: /* RCHP */ goto unimplemented; 14543 case 0xb23c: /* SCHM */ goto unimplemented; 14544 case 0xb240: /* BAKR */ goto unimplemented; 14545 case 0xb241: s390_format_RRE(s390_irgen_CKSM, ovl.fmt.RRE.r1, 14546 ovl.fmt.RRE.r2); goto ok; 14547 case 0xb244: /* SQDR */ goto unimplemented; 14548 case 0xb245: /* SQER */ goto unimplemented; 14549 case 0xb246: /* STURA */ goto unimplemented; 14550 case 0xb247: /* MSTA */ goto unimplemented; 14551 case 0xb248: /* PALB */ goto unimplemented; 14552 case 0xb249: /* EREG */ goto unimplemented; 14553 case 0xb24a: /* ESTA */ goto unimplemented; 14554 case 0xb24b: /* LURA */ goto unimplemented; 14555 case 0xb24c: /* TAR */ goto unimplemented; 14556 case 0xb24d: s390_format_RRE(s390_irgen_CPYA, ovl.fmt.RRE.r1, 14557 ovl.fmt.RRE.r2); goto ok; 14558 case 0xb24e: s390_format_RRE(s390_irgen_SAR, ovl.fmt.RRE.r1, ovl.fmt.RRE.r2); 14559 goto ok; 14560 case 0xb24f: s390_format_RRE(s390_irgen_EAR, ovl.fmt.RRE.r1, ovl.fmt.RRE.r2); 14561 goto ok; 14562 case 0xb250: /* CSP */ goto unimplemented; 14563 case 0xb252: s390_format_RRE_RR(s390_irgen_MSR, ovl.fmt.RRE.r1, 14564 ovl.fmt.RRE.r2); goto ok; 14565 case 0xb254: /* MVPG */ goto unimplemented; 14566 case 0xb255: s390_format_RRE_RR(s390_irgen_MVST, ovl.fmt.RRE.r1, 14567 ovl.fmt.RRE.r2); goto ok; 14568 case 0xb257: /* CUSE */ goto unimplemented; 14569 case 0xb258: /* BSG */ goto unimplemented; 14570 case 0xb25a: /* BSA */ goto unimplemented; 14571 case 0xb25d: s390_format_RRE_RR(s390_irgen_CLST, ovl.fmt.RRE.r1, 14572 ovl.fmt.RRE.r2); goto ok; 14573 case 0xb25e: s390_format_RRE_RR(s390_irgen_SRST, ovl.fmt.RRE.r1, 14574 ovl.fmt.RRE.r2); goto ok; 14575 case 0xb263: /* CMPSC */ goto unimplemented; 14576 case 0xb274: /* SIGA */ goto unimplemented; 14577 case 0xb276: /* XSCH */ goto unimplemented; 14578 case 0xb277: /* RP */ goto unimplemented; 14579 case 0xb278: s390_format_S_RD(s390_irgen_STCKE, ovl.fmt.S.b2, ovl.fmt.S.d2);goto ok; 14580 case 0xb279: /* SACF */ goto unimplemented; 14581 case 0xb27c: s390_format_S_RD(s390_irgen_STCKF, ovl.fmt.S.b2, ovl.fmt.S.d2);goto ok; 14582 case 0xb27d: /* STSI */ goto unimplemented; 14583 case 0xb280: /* LPP */ goto unimplemented; 14584 case 0xb284: /* LCCTL */ goto unimplemented; 14585 case 0xb285: /* LPCTL */ goto unimplemented; 14586 case 0xb286: /* QSI */ goto unimplemented; 14587 case 0xb287: /* LSCTL */ goto unimplemented; 14588 case 0xb28e: /* QCTRI */ goto unimplemented; 14589 case 0xb299: s390_format_S_RD(s390_irgen_SRNM, ovl.fmt.S.b2, ovl.fmt.S.d2); 14590 goto ok; 14591 case 0xb29c: s390_format_S_RD(s390_irgen_STFPC, ovl.fmt.S.b2, ovl.fmt.S.d2); 14592 goto ok; 14593 case 0xb29d: s390_format_S_RD(s390_irgen_LFPC, ovl.fmt.S.b2, ovl.fmt.S.d2); 14594 goto ok; 14595 case 0xb2a5: s390_format_RRE_FF(s390_irgen_TRE, ovl.fmt.RRE.r1, ovl.fmt.RRE.r2); goto ok; 14596 case 0xb2a6: s390_format_RRF_M0RERE(s390_irgen_CU21, ovl.fmt.RRF3.r3, 14597 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); 14598 goto ok; 14599 case 0xb2a7: s390_format_RRF_M0RERE(s390_irgen_CU12, ovl.fmt.RRF3.r3, 14600 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); 14601 goto ok; 14602 case 0xb2b0: s390_format_S_RD(s390_irgen_STFLE, ovl.fmt.S.b2, ovl.fmt.S.d2); 14603 goto ok; 14604 case 0xb2b1: /* STFL */ goto unimplemented; 14605 case 0xb2b2: /* LPSWE */ goto unimplemented; 14606 case 0xb2b8: s390_irgen_srnmb_wrapper(ovl.fmt.S.b2, ovl.fmt.S.d2); 14607 goto ok; 14608 case 0xb2b9: s390_format_S_RD(s390_irgen_SRNMT, ovl.fmt.S.b2, ovl.fmt.S.d2); 14609 goto ok; 14610 case 0xb2bd: /* LFAS */ goto unimplemented; 14611 case 0xb2e0: /* SCCTR */ goto unimplemented; 14612 case 0xb2e1: /* SPCTR */ goto unimplemented; 14613 case 0xb2e4: /* ECCTR */ goto unimplemented; 14614 case 0xb2e5: /* EPCTR */ goto unimplemented; 14615 case 0xb2e8: /* PPA */ goto unimplemented; 14616 case 0xb2ec: /* ETND */ goto unimplemented; 14617 case 0xb2ed: /* ECPGA */ goto unimplemented; 14618 case 0xb2f8: /* TEND */ goto unimplemented; 14619 case 0xb2fa: /* NIAI */ goto unimplemented; 14620 case 0xb2fc: /* TABORT */ goto unimplemented; 14621 case 0xb2ff: /* TRAP4 */ goto unimplemented; 14622 case 0xb300: s390_format_RRE_FF(s390_irgen_LPEBR, ovl.fmt.RRE.r1, 14623 ovl.fmt.RRE.r2); goto ok; 14624 case 0xb301: s390_format_RRE_FF(s390_irgen_LNEBR, ovl.fmt.RRE.r1, 14625 ovl.fmt.RRE.r2); goto ok; 14626 case 0xb302: s390_format_RRE_FF(s390_irgen_LTEBR, ovl.fmt.RRE.r1, 14627 ovl.fmt.RRE.r2); goto ok; 14628 case 0xb303: s390_format_RRE_FF(s390_irgen_LCEBR, ovl.fmt.RRE.r1, 14629 ovl.fmt.RRE.r2); goto ok; 14630 case 0xb304: s390_format_RRE_FF(s390_irgen_LDEBR, ovl.fmt.RRE.r1, 14631 ovl.fmt.RRE.r2); goto ok; 14632 case 0xb305: s390_format_RRE_FF(s390_irgen_LXDBR, ovl.fmt.RRE.r1, 14633 ovl.fmt.RRE.r2); goto ok; 14634 case 0xb306: s390_format_RRE_FF(s390_irgen_LXEBR, ovl.fmt.RRE.r1, 14635 ovl.fmt.RRE.r2); goto ok; 14636 case 0xb307: /* MXDBR */ goto unimplemented; 14637 case 0xb308: /* KEBR */ goto unimplemented; 14638 case 0xb309: s390_format_RRE_FF(s390_irgen_CEBR, ovl.fmt.RRE.r1, 14639 ovl.fmt.RRE.r2); goto ok; 14640 case 0xb30a: s390_format_RRE_FF(s390_irgen_AEBR, ovl.fmt.RRE.r1, 14641 ovl.fmt.RRE.r2); goto ok; 14642 case 0xb30b: s390_format_RRE_FF(s390_irgen_SEBR, ovl.fmt.RRE.r1, 14643 ovl.fmt.RRE.r2); goto ok; 14644 case 0xb30c: /* MDEBR */ goto unimplemented; 14645 case 0xb30d: s390_format_RRE_FF(s390_irgen_DEBR, ovl.fmt.RRE.r1, 14646 ovl.fmt.RRE.r2); goto ok; 14647 case 0xb30e: s390_format_RRF_F0FF(s390_irgen_MAEBR, ovl.fmt.RRF.r1, 14648 ovl.fmt.RRF.r3, ovl.fmt.RRF.r2); goto ok; 14649 case 0xb30f: s390_format_RRF_F0FF(s390_irgen_MSEBR, ovl.fmt.RRF.r1, 14650 ovl.fmt.RRF.r3, ovl.fmt.RRF.r2); goto ok; 14651 case 0xb310: s390_format_RRE_FF(s390_irgen_LPDBR, ovl.fmt.RRE.r1, 14652 ovl.fmt.RRE.r2); goto ok; 14653 case 0xb311: s390_format_RRE_FF(s390_irgen_LNDBR, ovl.fmt.RRE.r1, 14654 ovl.fmt.RRE.r2); goto ok; 14655 case 0xb312: s390_format_RRE_FF(s390_irgen_LTDBR, ovl.fmt.RRE.r1, 14656 ovl.fmt.RRE.r2); goto ok; 14657 case 0xb313: s390_format_RRE_FF(s390_irgen_LCDBR, ovl.fmt.RRE.r1, 14658 ovl.fmt.RRE.r2); goto ok; 14659 case 0xb314: s390_format_RRE_FF(s390_irgen_SQEBR, ovl.fmt.RRE.r1, 14660 ovl.fmt.RRE.r2); goto ok; 14661 case 0xb315: s390_format_RRE_FF(s390_irgen_SQDBR, ovl.fmt.RRE.r1, 14662 ovl.fmt.RRE.r2); goto ok; 14663 case 0xb316: s390_format_RRE_FF(s390_irgen_SQXBR, ovl.fmt.RRE.r1, 14664 ovl.fmt.RRE.r2); goto ok; 14665 case 0xb317: s390_format_RRE_FF(s390_irgen_MEEBR, ovl.fmt.RRE.r1, 14666 ovl.fmt.RRE.r2); goto ok; 14667 case 0xb318: /* KDBR */ goto unimplemented; 14668 case 0xb319: s390_format_RRE_FF(s390_irgen_CDBR, ovl.fmt.RRE.r1, 14669 ovl.fmt.RRE.r2); goto ok; 14670 case 0xb31a: s390_format_RRE_FF(s390_irgen_ADBR, ovl.fmt.RRE.r1, 14671 ovl.fmt.RRE.r2); goto ok; 14672 case 0xb31b: s390_format_RRE_FF(s390_irgen_SDBR, ovl.fmt.RRE.r1, 14673 ovl.fmt.RRE.r2); goto ok; 14674 case 0xb31c: s390_format_RRE_FF(s390_irgen_MDBR, ovl.fmt.RRE.r1, 14675 ovl.fmt.RRE.r2); goto ok; 14676 case 0xb31d: s390_format_RRE_FF(s390_irgen_DDBR, ovl.fmt.RRE.r1, 14677 ovl.fmt.RRE.r2); goto ok; 14678 case 0xb31e: s390_format_RRF_F0FF(s390_irgen_MADBR, ovl.fmt.RRF.r1, 14679 ovl.fmt.RRF.r3, ovl.fmt.RRF.r2); goto ok; 14680 case 0xb31f: s390_format_RRF_F0FF(s390_irgen_MSDBR, ovl.fmt.RRF.r1, 14681 ovl.fmt.RRF.r3, ovl.fmt.RRF.r2); goto ok; 14682 case 0xb324: s390_format_RRE_FF(s390_irgen_LDER, ovl.fmt.RRE.r1, 14683 ovl.fmt.RRE.r2); goto ok; 14684 case 0xb325: /* LXDR */ goto unimplemented; 14685 case 0xb326: /* LXER */ goto unimplemented; 14686 case 0xb32e: /* MAER */ goto unimplemented; 14687 case 0xb32f: /* MSER */ goto unimplemented; 14688 case 0xb336: /* SQXR */ goto unimplemented; 14689 case 0xb337: /* MEER */ goto unimplemented; 14690 case 0xb338: /* MAYLR */ goto unimplemented; 14691 case 0xb339: /* MYLR */ goto unimplemented; 14692 case 0xb33a: /* MAYR */ goto unimplemented; 14693 case 0xb33b: /* MYR */ goto unimplemented; 14694 case 0xb33c: /* MAYHR */ goto unimplemented; 14695 case 0xb33d: /* MYHR */ goto unimplemented; 14696 case 0xb33e: /* MADR */ goto unimplemented; 14697 case 0xb33f: /* MSDR */ goto unimplemented; 14698 case 0xb340: s390_format_RRE_FF(s390_irgen_LPXBR, ovl.fmt.RRE.r1, 14699 ovl.fmt.RRE.r2); goto ok; 14700 case 0xb341: s390_format_RRE_FF(s390_irgen_LNXBR, ovl.fmt.RRE.r1, 14701 ovl.fmt.RRE.r2); goto ok; 14702 case 0xb342: s390_format_RRE_FF(s390_irgen_LTXBR, ovl.fmt.RRE.r1, 14703 ovl.fmt.RRE.r2); goto ok; 14704 case 0xb343: s390_format_RRE_FF(s390_irgen_LCXBR, ovl.fmt.RRE.r1, 14705 ovl.fmt.RRE.r2); goto ok; 14706 case 0xb344: s390_format_RRF_UUFF(s390_irgen_LEDBR, ovl.fmt.RRF2.m3, 14707 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14708 ovl.fmt.RRF2.r2); goto ok; 14709 case 0xb345: s390_format_RRF_UUFF(s390_irgen_LDXBR, ovl.fmt.RRF2.m3, 14710 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14711 ovl.fmt.RRF2.r2); goto ok; 14712 case 0xb346: s390_format_RRF_UUFF(s390_irgen_LEXBR, ovl.fmt.RRF2.m3, 14713 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14714 ovl.fmt.RRF2.r2); goto ok; 14715 case 0xb347: s390_format_RRF_UUFF(s390_irgen_FIXBRA, ovl.fmt.RRF2.m3, 14716 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14717 ovl.fmt.RRF2.r2); goto ok; 14718 case 0xb348: /* KXBR */ goto unimplemented; 14719 case 0xb349: s390_format_RRE_FF(s390_irgen_CXBR, ovl.fmt.RRE.r1, 14720 ovl.fmt.RRE.r2); goto ok; 14721 case 0xb34a: s390_format_RRE_FF(s390_irgen_AXBR, ovl.fmt.RRE.r1, 14722 ovl.fmt.RRE.r2); goto ok; 14723 case 0xb34b: s390_format_RRE_FF(s390_irgen_SXBR, ovl.fmt.RRE.r1, 14724 ovl.fmt.RRE.r2); goto ok; 14725 case 0xb34c: s390_format_RRE_FF(s390_irgen_MXBR, ovl.fmt.RRE.r1, 14726 ovl.fmt.RRE.r2); goto ok; 14727 case 0xb34d: s390_format_RRE_FF(s390_irgen_DXBR, ovl.fmt.RRE.r1, 14728 ovl.fmt.RRE.r2); goto ok; 14729 case 0xb350: /* TBEDR */ goto unimplemented; 14730 case 0xb351: /* TBDR */ goto unimplemented; 14731 case 0xb353: /* DIEBR */ goto unimplemented; 14732 case 0xb357: s390_format_RRF_UUFF(s390_irgen_FIEBRA, ovl.fmt.RRF2.m3, 14733 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14734 ovl.fmt.RRF2.r2); goto ok; 14735 case 0xb358: /* THDER */ goto unimplemented; 14736 case 0xb359: /* THDR */ goto unimplemented; 14737 case 0xb35b: /* DIDBR */ goto unimplemented; 14738 case 0xb35f: s390_format_RRF_UUFF(s390_irgen_FIDBRA, ovl.fmt.RRF2.m3, 14739 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14740 ovl.fmt.RRF2.r2); goto ok; 14741 case 0xb360: /* LPXR */ goto unimplemented; 14742 case 0xb361: /* LNXR */ goto unimplemented; 14743 case 0xb362: /* LTXR */ goto unimplemented; 14744 case 0xb363: /* LCXR */ goto unimplemented; 14745 case 0xb365: s390_format_RRE_FF(s390_irgen_LXR, ovl.fmt.RRE.r1, 14746 ovl.fmt.RRE.r2); goto ok; 14747 case 0xb366: /* LEXR */ goto unimplemented; 14748 case 0xb367: /* FIXR */ goto unimplemented; 14749 case 0xb369: /* CXR */ goto unimplemented; 14750 case 0xb370: s390_format_RRE_FF(s390_irgen_LPDFR, ovl.fmt.RRE.r1, 14751 ovl.fmt.RRE.r2); goto ok; 14752 case 0xb371: s390_format_RRE_FF(s390_irgen_LNDFR, ovl.fmt.RRE.r1, 14753 ovl.fmt.RRE.r2); goto ok; 14754 case 0xb372: s390_format_RRF_F0FF2(s390_irgen_CPSDR, ovl.fmt.RRF3.r3, 14755 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); 14756 goto ok; 14757 case 0xb373: s390_format_RRE_FF(s390_irgen_LCDFR, ovl.fmt.RRE.r1, 14758 ovl.fmt.RRE.r2); goto ok; 14759 case 0xb374: s390_format_RRE_F0(s390_irgen_LZER, ovl.fmt.RRE.r1); goto ok; 14760 case 0xb375: s390_format_RRE_F0(s390_irgen_LZDR, ovl.fmt.RRE.r1); goto ok; 14761 case 0xb376: s390_format_RRE_F0(s390_irgen_LZXR, ovl.fmt.RRE.r1); goto ok; 14762 case 0xb377: /* FIER */ goto unimplemented; 14763 case 0xb37f: /* FIDR */ goto unimplemented; 14764 case 0xb384: s390_format_RRE_R0(s390_irgen_SFPC, ovl.fmt.RRE.r1); goto ok; 14765 case 0xb385: /* SFASR */ goto unimplemented; 14766 case 0xb38c: s390_format_RRE_R0(s390_irgen_EFPC, ovl.fmt.RRE.r1); goto ok; 14767 case 0xb390: s390_format_RRF_UUFR(s390_irgen_CELFBR, ovl.fmt.RRF2.m3, 14768 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14769 ovl.fmt.RRF2.r2); goto ok; 14770 case 0xb391: s390_format_RRF_UUFR(s390_irgen_CDLFBR, ovl.fmt.RRF2.m3, 14771 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14772 ovl.fmt.RRF2.r2); goto ok; 14773 case 0xb392: s390_format_RRF_UUFR(s390_irgen_CXLFBR, ovl.fmt.RRF2.m3, 14774 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14775 ovl.fmt.RRF2.r2); goto ok; 14776 case 0xb394: s390_format_RRF_UUFR(s390_irgen_CEFBR, ovl.fmt.RRF2.m3, 14777 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14778 ovl.fmt.RRF2.r2); goto ok; 14779 case 0xb395: s390_format_RRF_UUFR(s390_irgen_CDFBR, ovl.fmt.RRF2.m3, 14780 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14781 ovl.fmt.RRF2.r2); goto ok; 14782 case 0xb396: s390_format_RRF_UUFR(s390_irgen_CXFBR, ovl.fmt.RRF2.m3, 14783 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14784 ovl.fmt.RRF2.r2); goto ok; 14785 case 0xb398: s390_format_RRF_UURF(s390_irgen_CFEBR, ovl.fmt.RRF2.m3, 14786 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14787 ovl.fmt.RRF2.r2); goto ok; 14788 case 0xb399: s390_format_RRF_UURF(s390_irgen_CFDBR, ovl.fmt.RRF2.m3, 14789 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14790 ovl.fmt.RRF2.r2); goto ok; 14791 case 0xb39a: s390_format_RRF_UURF(s390_irgen_CFXBR, ovl.fmt.RRF2.m3, 14792 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14793 ovl.fmt.RRF2.r2); goto ok; 14794 case 0xb39c: s390_format_RRF_UURF(s390_irgen_CLFEBR, ovl.fmt.RRF2.m3, 14795 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14796 ovl.fmt.RRF2.r2); goto ok; 14797 case 0xb39d: s390_format_RRF_UURF(s390_irgen_CLFDBR, ovl.fmt.RRF2.m3, 14798 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14799 ovl.fmt.RRF2.r2); goto ok; 14800 case 0xb39e: s390_format_RRF_UURF(s390_irgen_CLFXBR, ovl.fmt.RRF2.m3, 14801 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14802 ovl.fmt.RRF2.r2); goto ok; 14803 case 0xb3a0: s390_format_RRF_UUFR(s390_irgen_CELGBR, ovl.fmt.RRF2.m3, 14804 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14805 ovl.fmt.RRF2.r2); goto ok; 14806 case 0xb3a1: s390_format_RRF_UUFR(s390_irgen_CDLGBR, ovl.fmt.RRF2.m3, 14807 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14808 ovl.fmt.RRF2.r2); goto ok; 14809 case 0xb3a2: s390_format_RRF_UUFR(s390_irgen_CXLGBR, ovl.fmt.RRF2.m3, 14810 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14811 ovl.fmt.RRF2.r2); goto ok; 14812 case 0xb3a4: s390_format_RRF_UUFR(s390_irgen_CEGBR, ovl.fmt.RRF2.m3, 14813 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14814 ovl.fmt.RRF2.r2); goto ok; 14815 case 0xb3a5: s390_format_RRF_UUFR(s390_irgen_CDGBR, ovl.fmt.RRF2.m3, 14816 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14817 ovl.fmt.RRF2.r2); goto ok; 14818 case 0xb3a6: s390_format_RRF_UUFR(s390_irgen_CXGBR, ovl.fmt.RRF2.m3, 14819 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14820 ovl.fmt.RRF2.r2); goto ok; 14821 case 0xb3a8: s390_format_RRF_UURF(s390_irgen_CGEBR, ovl.fmt.RRF2.m3, 14822 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14823 ovl.fmt.RRF2.r2); goto ok; 14824 case 0xb3a9: s390_format_RRF_UURF(s390_irgen_CGDBR, ovl.fmt.RRF2.m3, 14825 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14826 ovl.fmt.RRF2.r2); goto ok; 14827 case 0xb3aa: s390_format_RRF_UURF(s390_irgen_CGXBR, ovl.fmt.RRF2.m3, 14828 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14829 ovl.fmt.RRF2.r2); goto ok; 14830 case 0xb3ac: s390_format_RRF_UURF(s390_irgen_CLGEBR, ovl.fmt.RRF2.m3, 14831 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14832 ovl.fmt.RRF2.r2); goto ok; 14833 case 0xb3ad: s390_format_RRF_UURF(s390_irgen_CLGDBR, ovl.fmt.RRF2.m3, 14834 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14835 ovl.fmt.RRF2.r2); goto ok; 14836 case 0xb3ae: s390_format_RRF_UURF(s390_irgen_CLGXBR, ovl.fmt.RRF2.m3, 14837 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14838 ovl.fmt.RRF2.r2); goto ok; 14839 case 0xb3b4: /* CEFR */ goto unimplemented; 14840 case 0xb3b5: /* CDFR */ goto unimplemented; 14841 case 0xb3b6: /* CXFR */ goto unimplemented; 14842 case 0xb3b8: /* CFER */ goto unimplemented; 14843 case 0xb3b9: /* CFDR */ goto unimplemented; 14844 case 0xb3ba: /* CFXR */ goto unimplemented; 14845 case 0xb3c1: s390_format_RRE_FR(s390_irgen_LDGR, ovl.fmt.RRE.r1, 14846 ovl.fmt.RRE.r2); goto ok; 14847 case 0xb3c4: /* CEGR */ goto unimplemented; 14848 case 0xb3c5: /* CDGR */ goto unimplemented; 14849 case 0xb3c6: /* CXGR */ goto unimplemented; 14850 case 0xb3c8: /* CGER */ goto unimplemented; 14851 case 0xb3c9: /* CGDR */ goto unimplemented; 14852 case 0xb3ca: /* CGXR */ goto unimplemented; 14853 case 0xb3cd: s390_format_RRE_RF(s390_irgen_LGDR, ovl.fmt.RRE.r1, 14854 ovl.fmt.RRE.r2); goto ok; 14855 case 0xb3d0: s390_format_RRF_FUFF2(s390_irgen_MDTRA, ovl.fmt.RRF4.r3, 14856 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14857 ovl.fmt.RRF4.r2); goto ok; 14858 case 0xb3d1: s390_format_RRF_FUFF2(s390_irgen_DDTRA, ovl.fmt.RRF4.r3, 14859 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14860 ovl.fmt.RRF4.r2); goto ok; 14861 case 0xb3d2: s390_format_RRF_FUFF2(s390_irgen_ADTRA, ovl.fmt.RRF4.r3, 14862 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14863 ovl.fmt.RRF4.r2); goto ok; 14864 case 0xb3d3: s390_format_RRF_FUFF2(s390_irgen_SDTRA, ovl.fmt.RRF4.r3, 14865 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14866 ovl.fmt.RRF4.r2); goto ok; 14867 case 0xb3d4: s390_format_RRF_0UFF(s390_irgen_LDETR, ovl.fmt.RRF5.m4, 14868 ovl.fmt.RRF5.r1, ovl.fmt.RRF5.r2); goto ok; 14869 case 0xb3d5: s390_format_RRF_UUFF(s390_irgen_LEDTR, ovl.fmt.RRF2.m3, 14870 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14871 ovl.fmt.RRF2.r2); goto ok; 14872 case 0xb3d6: s390_format_RRE_FF(s390_irgen_LTDTR, ovl.fmt.RRE.r1, 14873 ovl.fmt.RRE.r2); goto ok; 14874 case 0xb3d7: /* FIDTR */ goto unimplemented; 14875 case 0xb3d8: s390_format_RRF_FUFF2(s390_irgen_MXTRA, ovl.fmt.RRF4.r3, 14876 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14877 ovl.fmt.RRF4.r2); goto ok; 14878 case 0xb3d9: s390_format_RRF_FUFF2(s390_irgen_DXTRA, ovl.fmt.RRF4.r3, 14879 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14880 ovl.fmt.RRF4.r2); goto ok; 14881 case 0xb3da: s390_format_RRF_FUFF2(s390_irgen_AXTRA, ovl.fmt.RRF4.r3, 14882 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14883 ovl.fmt.RRF4.r2); goto ok; 14884 case 0xb3db: s390_format_RRF_FUFF2(s390_irgen_SXTRA, ovl.fmt.RRF4.r3, 14885 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14886 ovl.fmt.RRF4.r2); goto ok; 14887 case 0xb3dc: s390_format_RRF_0UFF(s390_irgen_LXDTR, ovl.fmt.RRF5.m4, 14888 ovl.fmt.RRF5.r1, ovl.fmt.RRF5.r2); goto ok; 14889 case 0xb3dd: s390_format_RRF_UUFF(s390_irgen_LDXTR, ovl.fmt.RRF2.m3, 14890 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14891 ovl.fmt.RRF2.r2); goto ok; 14892 case 0xb3de: s390_format_RRE_FF(s390_irgen_LTXTR, ovl.fmt.RRE.r1, 14893 ovl.fmt.RRE.r2); goto ok; 14894 case 0xb3df: /* FIXTR */ goto unimplemented; 14895 case 0xb3e0: /* KDTR */ goto unimplemented; 14896 case 0xb3e1: s390_format_RRF_UURF(s390_irgen_CGDTR, ovl.fmt.RRF2.m3, 14897 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14898 ovl.fmt.RRF2.r2); goto ok; 14899 case 0xb3e2: /* CUDTR */ goto unimplemented; 14900 case 0xb3e3: /* CSDTR */ goto unimplemented; 14901 case 0xb3e4: s390_format_RRE_FF(s390_irgen_CDTR, ovl.fmt.RRE.r1, 14902 ovl.fmt.RRE.r2); goto ok; 14903 case 0xb3e5: s390_format_RRE_RF(s390_irgen_EEDTR, ovl.fmt.RRE.r1, 14904 ovl.fmt.RRE.r2); goto ok; 14905 case 0xb3e7: s390_format_RRE_RF(s390_irgen_ESDTR, ovl.fmt.RRE.r1, 14906 ovl.fmt.RRE.r2); goto ok; 14907 case 0xb3e8: /* KXTR */ goto unimplemented; 14908 case 0xb3e9: s390_format_RRF_UURF(s390_irgen_CGXTR, ovl.fmt.RRF2.m3, 14909 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14910 ovl.fmt.RRF2.r2); goto ok; 14911 case 0xb3ea: /* CUXTR */ goto unimplemented; 14912 case 0xb3eb: /* CSXTR */ goto unimplemented; 14913 case 0xb3ec: s390_format_RRE_FF(s390_irgen_CXTR, ovl.fmt.RRE.r1, 14914 ovl.fmt.RRE.r2); goto ok; 14915 case 0xb3ed: s390_format_RRE_RF(s390_irgen_EEXTR, ovl.fmt.RRE.r1, 14916 ovl.fmt.RRE.r2); goto ok; 14917 case 0xb3ef: s390_format_RRE_RF(s390_irgen_ESXTR, ovl.fmt.RRE.r1, 14918 ovl.fmt.RRE.r2); goto ok; 14919 case 0xb3f1: s390_format_RRF_UUFR(s390_irgen_CDGTRA, ovl.fmt.RRF2.m3, 14920 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14921 ovl.fmt.RRF2.r2); goto ok; 14922 case 0xb3f2: /* CDUTR */ goto unimplemented; 14923 case 0xb3f3: /* CDSTR */ goto unimplemented; 14924 case 0xb3f4: s390_format_RRE_FF(s390_irgen_CEDTR, ovl.fmt.RRE.r1, 14925 ovl.fmt.RRE.r2); goto ok; 14926 case 0xb3f5: s390_format_RRF_FUFF(s390_irgen_QADTR, ovl.fmt.RRF4.r3, 14927 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14928 ovl.fmt.RRF4.r2); goto ok; 14929 case 0xb3f6: s390_format_RRF_F0FR(s390_irgen_IEDTR, ovl.fmt.RRF3.r3, 14930 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); goto ok; 14931 case 0xb3f7: s390_format_RRF_FFRU(s390_irgen_RRDTR, ovl.fmt.RRF4.r3, 14932 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14933 ovl.fmt.RRF4.r2); goto ok; 14934 case 0xb3f9: s390_format_RRF_UUFR(s390_irgen_CXGTR, ovl.fmt.RRF2.m3, 14935 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14936 ovl.fmt.RRF2.r2); goto ok; 14937 case 0xb3fa: /* CXUTR */ goto unimplemented; 14938 case 0xb3fb: /* CXSTR */ goto unimplemented; 14939 case 0xb3fc: s390_format_RRE_FF(s390_irgen_CEXTR, ovl.fmt.RRE.r1, 14940 ovl.fmt.RRE.r2); goto ok; 14941 case 0xb3fd: s390_format_RRF_FUFF(s390_irgen_QAXTR, ovl.fmt.RRF4.r3, 14942 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14943 ovl.fmt.RRF4.r2); goto ok; 14944 case 0xb3fe: s390_format_RRF_F0FR(s390_irgen_IEXTR, ovl.fmt.RRF3.r3, 14945 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); goto ok; 14946 case 0xb3ff: s390_format_RRF_FFRU(s390_irgen_RRXTR, ovl.fmt.RRF4.r3, 14947 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14948 ovl.fmt.RRF4.r2); goto ok; 14949 case 0xb900: s390_format_RRE_RR(s390_irgen_LPGR, ovl.fmt.RRE.r1, 14950 ovl.fmt.RRE.r2); goto ok; 14951 case 0xb901: s390_format_RRE_RR(s390_irgen_LNGR, ovl.fmt.RRE.r1, 14952 ovl.fmt.RRE.r2); goto ok; 14953 case 0xb902: s390_format_RRE_RR(s390_irgen_LTGR, ovl.fmt.RRE.r1, 14954 ovl.fmt.RRE.r2); goto ok; 14955 case 0xb903: s390_format_RRE_RR(s390_irgen_LCGR, ovl.fmt.RRE.r1, 14956 ovl.fmt.RRE.r2); goto ok; 14957 case 0xb904: s390_format_RRE_RR(s390_irgen_LGR, ovl.fmt.RRE.r1, 14958 ovl.fmt.RRE.r2); goto ok; 14959 case 0xb905: /* LURAG */ goto unimplemented; 14960 case 0xb906: s390_format_RRE_RR(s390_irgen_LGBR, ovl.fmt.RRE.r1, 14961 ovl.fmt.RRE.r2); goto ok; 14962 case 0xb907: s390_format_RRE_RR(s390_irgen_LGHR, ovl.fmt.RRE.r1, 14963 ovl.fmt.RRE.r2); goto ok; 14964 case 0xb908: s390_format_RRE_RR(s390_irgen_AGR, ovl.fmt.RRE.r1, 14965 ovl.fmt.RRE.r2); goto ok; 14966 case 0xb909: s390_format_RRE_RR(s390_irgen_SGR, ovl.fmt.RRE.r1, 14967 ovl.fmt.RRE.r2); goto ok; 14968 case 0xb90a: s390_format_RRE_RR(s390_irgen_ALGR, ovl.fmt.RRE.r1, 14969 ovl.fmt.RRE.r2); goto ok; 14970 case 0xb90b: s390_format_RRE_RR(s390_irgen_SLGR, ovl.fmt.RRE.r1, 14971 ovl.fmt.RRE.r2); goto ok; 14972 case 0xb90c: s390_format_RRE_RR(s390_irgen_MSGR, ovl.fmt.RRE.r1, 14973 ovl.fmt.RRE.r2); goto ok; 14974 case 0xb90d: s390_format_RRE_RR(s390_irgen_DSGR, ovl.fmt.RRE.r1, 14975 ovl.fmt.RRE.r2); goto ok; 14976 case 0xb90e: /* EREGG */ goto unimplemented; 14977 case 0xb90f: s390_format_RRE_RR(s390_irgen_LRVGR, ovl.fmt.RRE.r1, 14978 ovl.fmt.RRE.r2); goto ok; 14979 case 0xb910: s390_format_RRE_RR(s390_irgen_LPGFR, ovl.fmt.RRE.r1, 14980 ovl.fmt.RRE.r2); goto ok; 14981 case 0xb911: s390_format_RRE_RR(s390_irgen_LNGFR, ovl.fmt.RRE.r1, 14982 ovl.fmt.RRE.r2); goto ok; 14983 case 0xb912: s390_format_RRE_RR(s390_irgen_LTGFR, ovl.fmt.RRE.r1, 14984 ovl.fmt.RRE.r2); goto ok; 14985 case 0xb913: s390_format_RRE_RR(s390_irgen_LCGFR, ovl.fmt.RRE.r1, 14986 ovl.fmt.RRE.r2); goto ok; 14987 case 0xb914: s390_format_RRE_RR(s390_irgen_LGFR, ovl.fmt.RRE.r1, 14988 ovl.fmt.RRE.r2); goto ok; 14989 case 0xb916: s390_format_RRE_RR(s390_irgen_LLGFR, ovl.fmt.RRE.r1, 14990 ovl.fmt.RRE.r2); goto ok; 14991 case 0xb917: s390_format_RRE_RR(s390_irgen_LLGTR, ovl.fmt.RRE.r1, 14992 ovl.fmt.RRE.r2); goto ok; 14993 case 0xb918: s390_format_RRE_RR(s390_irgen_AGFR, ovl.fmt.RRE.r1, 14994 ovl.fmt.RRE.r2); goto ok; 14995 case 0xb919: s390_format_RRE_RR(s390_irgen_SGFR, ovl.fmt.RRE.r1, 14996 ovl.fmt.RRE.r2); goto ok; 14997 case 0xb91a: s390_format_RRE_RR(s390_irgen_ALGFR, ovl.fmt.RRE.r1, 14998 ovl.fmt.RRE.r2); goto ok; 14999 case 0xb91b: s390_format_RRE_RR(s390_irgen_SLGFR, ovl.fmt.RRE.r1, 15000 ovl.fmt.RRE.r2); goto ok; 15001 case 0xb91c: s390_format_RRE_RR(s390_irgen_MSGFR, ovl.fmt.RRE.r1, 15002 ovl.fmt.RRE.r2); goto ok; 15003 case 0xb91d: s390_format_RRE_RR(s390_irgen_DSGFR, ovl.fmt.RRE.r1, 15004 ovl.fmt.RRE.r2); goto ok; 15005 case 0xb91e: /* KMAC */ goto unimplemented; 15006 case 0xb91f: s390_format_RRE_RR(s390_irgen_LRVR, ovl.fmt.RRE.r1, 15007 ovl.fmt.RRE.r2); goto ok; 15008 case 0xb920: s390_format_RRE_RR(s390_irgen_CGR, ovl.fmt.RRE.r1, 15009 ovl.fmt.RRE.r2); goto ok; 15010 case 0xb921: s390_format_RRE_RR(s390_irgen_CLGR, ovl.fmt.RRE.r1, 15011 ovl.fmt.RRE.r2); goto ok; 15012 case 0xb925: /* STURG */ goto unimplemented; 15013 case 0xb926: s390_format_RRE_RR(s390_irgen_LBR, ovl.fmt.RRE.r1, 15014 ovl.fmt.RRE.r2); goto ok; 15015 case 0xb927: s390_format_RRE_RR(s390_irgen_LHR, ovl.fmt.RRE.r1, 15016 ovl.fmt.RRE.r2); goto ok; 15017 case 0xb928: /* PCKMO */ goto unimplemented; 15018 case 0xb92a: /* KMF */ goto unimplemented; 15019 case 0xb92b: /* KMO */ goto unimplemented; 15020 case 0xb92c: /* PCC */ goto unimplemented; 15021 case 0xb92d: /* KMCTR */ goto unimplemented; 15022 case 0xb92e: /* KM */ goto unimplemented; 15023 case 0xb92f: /* KMC */ goto unimplemented; 15024 case 0xb930: s390_format_RRE_RR(s390_irgen_CGFR, ovl.fmt.RRE.r1, 15025 ovl.fmt.RRE.r2); goto ok; 15026 case 0xb931: s390_format_RRE_RR(s390_irgen_CLGFR, ovl.fmt.RRE.r1, 15027 ovl.fmt.RRE.r2); goto ok; 15028 case 0xb93e: /* KIMD */ goto unimplemented; 15029 case 0xb93f: /* KLMD */ goto unimplemented; 15030 case 0xb941: s390_format_RRF_UURF(s390_irgen_CFDTR, ovl.fmt.RRF2.m3, 15031 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 15032 ovl.fmt.RRF2.r2); goto ok; 15033 case 0xb942: s390_format_RRF_UURF(s390_irgen_CLGDTR, ovl.fmt.RRF2.m3, 15034 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 15035 ovl.fmt.RRF2.r2); goto ok; 15036 case 0xb943: s390_format_RRF_UURF(s390_irgen_CLFDTR, ovl.fmt.RRF2.m3, 15037 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 15038 ovl.fmt.RRF2.r2); goto ok; 15039 case 0xb946: s390_format_RRE_RR(s390_irgen_BCTGR, ovl.fmt.RRE.r1, 15040 ovl.fmt.RRE.r2); goto ok; 15041 case 0xb949: s390_format_RRF_UURF(s390_irgen_CFXTR, ovl.fmt.RRF2.m3, 15042 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 15043 ovl.fmt.RRF2.r2); goto ok; 15044 case 0xb94a: s390_format_RRF_UURF(s390_irgen_CLGXTR, ovl.fmt.RRF2.m3, 15045 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 15046 ovl.fmt.RRF2.r2); goto ok; 15047 case 0xb94b: s390_format_RRF_UURF(s390_irgen_CLFXTR, ovl.fmt.RRF2.m3, 15048 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 15049 ovl.fmt.RRF2.r2); goto ok; 15050 case 0xb951: s390_format_RRF_UUFR(s390_irgen_CDFTR, ovl.fmt.RRF2.m3, 15051 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 15052 ovl.fmt.RRF2.r2); goto ok; 15053 case 0xb952: s390_format_RRF_UUFR(s390_irgen_CDLGTR, ovl.fmt.RRF2.m3, 15054 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 15055 ovl.fmt.RRF2.r2); goto ok; 15056 case 0xb953: s390_format_RRF_UUFR(s390_irgen_CDLFTR, ovl.fmt.RRF2.m3, 15057 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 15058 ovl.fmt.RRF2.r2); goto ok; 15059 case 0xb959: s390_format_RRF_UUFR(s390_irgen_CXFTR, ovl.fmt.RRF2.m3, 15060 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 15061 ovl.fmt.RRF2.r2); goto ok; 15062 case 0xb95a: s390_format_RRF_UUFR(s390_irgen_CXLGTR, ovl.fmt.RRF2.m3, 15063 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 15064 ovl.fmt.RRF2.r2); goto ok; 15065 case 0xb95b: s390_format_RRF_UUFR(s390_irgen_CXLFTR, ovl.fmt.RRF2.m3, 15066 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 15067 ovl.fmt.RRF2.r2); goto ok; 15068 case 0xb960: /* CGRT */ goto unimplemented; 15069 case 0xb961: /* CLGRT */ goto unimplemented; 15070 case 0xb972: /* CRT */ goto unimplemented; 15071 case 0xb973: /* CLRT */ goto unimplemented; 15072 case 0xb980: s390_format_RRE_RR(s390_irgen_NGR, ovl.fmt.RRE.r1, 15073 ovl.fmt.RRE.r2); goto ok; 15074 case 0xb981: s390_format_RRE_RR(s390_irgen_OGR, ovl.fmt.RRE.r1, 15075 ovl.fmt.RRE.r2); goto ok; 15076 case 0xb982: s390_format_RRE_RR(s390_irgen_XGR, ovl.fmt.RRE.r1, 15077 ovl.fmt.RRE.r2); goto ok; 15078 case 0xb983: s390_format_RRE_RR(s390_irgen_FLOGR, ovl.fmt.RRE.r1, 15079 ovl.fmt.RRE.r2); goto ok; 15080 case 0xb984: s390_format_RRE_RR(s390_irgen_LLGCR, ovl.fmt.RRE.r1, 15081 ovl.fmt.RRE.r2); goto ok; 15082 case 0xb985: s390_format_RRE_RR(s390_irgen_LLGHR, ovl.fmt.RRE.r1, 15083 ovl.fmt.RRE.r2); goto ok; 15084 case 0xb986: s390_format_RRE_RR(s390_irgen_MLGR, ovl.fmt.RRE.r1, 15085 ovl.fmt.RRE.r2); goto ok; 15086 case 0xb987: s390_format_RRE_RR(s390_irgen_DLGR, ovl.fmt.RRE.r1, 15087 ovl.fmt.RRE.r2); goto ok; 15088 case 0xb988: s390_format_RRE_RR(s390_irgen_ALCGR, ovl.fmt.RRE.r1, 15089 ovl.fmt.RRE.r2); goto ok; 15090 case 0xb989: s390_format_RRE_RR(s390_irgen_SLBGR, ovl.fmt.RRE.r1, 15091 ovl.fmt.RRE.r2); goto ok; 15092 case 0xb98a: /* CSPG */ goto unimplemented; 15093 case 0xb98d: /* EPSW */ goto unimplemented; 15094 case 0xb98e: /* IDTE */ goto unimplemented; 15095 case 0xb98f: /* CRDTE */ goto unimplemented; 15096 case 0xb990: s390_format_RRF_M0RERE(s390_irgen_TRTT, ovl.fmt.RRF3.r3, 15097 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); goto ok; 15098 case 0xb991: s390_format_RRF_M0RERE(s390_irgen_TRTO, ovl.fmt.RRF3.r3, 15099 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); goto ok; 15100 case 0xb992: s390_format_RRF_M0RERE(s390_irgen_TROT, ovl.fmt.RRF3.r3, 15101 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); goto ok; 15102 case 0xb993: s390_format_RRF_M0RERE(s390_irgen_TROO, ovl.fmt.RRF3.r3, 15103 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); goto ok; 15104 case 0xb994: s390_format_RRE_RR(s390_irgen_LLCR, ovl.fmt.RRE.r1, 15105 ovl.fmt.RRE.r2); goto ok; 15106 case 0xb995: s390_format_RRE_RR(s390_irgen_LLHR, ovl.fmt.RRE.r1, 15107 ovl.fmt.RRE.r2); goto ok; 15108 case 0xb996: s390_format_RRE_RR(s390_irgen_MLR, ovl.fmt.RRE.r1, 15109 ovl.fmt.RRE.r2); goto ok; 15110 case 0xb997: s390_format_RRE_RR(s390_irgen_DLR, ovl.fmt.RRE.r1, 15111 ovl.fmt.RRE.r2); goto ok; 15112 case 0xb998: s390_format_RRE_RR(s390_irgen_ALCR, ovl.fmt.RRE.r1, 15113 ovl.fmt.RRE.r2); goto ok; 15114 case 0xb999: s390_format_RRE_RR(s390_irgen_SLBR, ovl.fmt.RRE.r1, 15115 ovl.fmt.RRE.r2); goto ok; 15116 case 0xb99a: /* EPAIR */ goto unimplemented; 15117 case 0xb99b: /* ESAIR */ goto unimplemented; 15118 case 0xb99d: /* ESEA */ goto unimplemented; 15119 case 0xb99e: /* PTI */ goto unimplemented; 15120 case 0xb99f: /* SSAIR */ goto unimplemented; 15121 case 0xb9a2: /* PTF */ goto unimplemented; 15122 case 0xb9aa: /* LPTEA */ goto unimplemented; 15123 case 0xb9ae: /* RRBM */ goto unimplemented; 15124 case 0xb9af: /* PFMF */ goto unimplemented; 15125 case 0xb9b0: s390_format_RRF_M0RERE(s390_irgen_CU14, ovl.fmt.RRF3.r3, 15126 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); 15127 goto ok; 15128 case 0xb9b1: s390_format_RRF_M0RERE(s390_irgen_CU24, ovl.fmt.RRF3.r3, 15129 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); 15130 goto ok; 15131 case 0xb9b2: s390_format_RRE_RR(s390_irgen_CU41, ovl.fmt.RRE.r1, 15132 ovl.fmt.RRE.r2); goto ok; 15133 case 0xb9b3: s390_format_RRE_RR(s390_irgen_CU42, ovl.fmt.RRE.r1, 15134 ovl.fmt.RRE.r2); goto ok; 15135 case 0xb9bd: /* TRTRE */ goto unimplemented; 15136 case 0xb9be: /* SRSTU */ goto unimplemented; 15137 case 0xb9bf: /* TRTE */ goto unimplemented; 15138 case 0xb9c8: s390_format_RRF_R0RR2(s390_irgen_AHHHR, ovl.fmt.RRF4.r3, 15139 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15140 goto ok; 15141 case 0xb9c9: s390_format_RRF_R0RR2(s390_irgen_SHHHR, ovl.fmt.RRF4.r3, 15142 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15143 goto ok; 15144 case 0xb9ca: s390_format_RRF_R0RR2(s390_irgen_ALHHHR, ovl.fmt.RRF4.r3, 15145 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15146 goto ok; 15147 case 0xb9cb: s390_format_RRF_R0RR2(s390_irgen_SLHHHR, ovl.fmt.RRF4.r3, 15148 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15149 goto ok; 15150 case 0xb9cd: s390_format_RRE_RR(s390_irgen_CHHR, ovl.fmt.RRE.r1, 15151 ovl.fmt.RRE.r2); goto ok; 15152 case 0xb9cf: s390_format_RRE_RR(s390_irgen_CLHHR, ovl.fmt.RRE.r1, 15153 ovl.fmt.RRE.r2); goto ok; 15154 case 0xb9d8: s390_format_RRF_R0RR2(s390_irgen_AHHLR, ovl.fmt.RRF4.r3, 15155 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15156 goto ok; 15157 case 0xb9d9: s390_format_RRF_R0RR2(s390_irgen_SHHLR, ovl.fmt.RRF4.r3, 15158 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15159 goto ok; 15160 case 0xb9da: s390_format_RRF_R0RR2(s390_irgen_ALHHLR, ovl.fmt.RRF4.r3, 15161 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15162 goto ok; 15163 case 0xb9db: s390_format_RRF_R0RR2(s390_irgen_SLHHLR, ovl.fmt.RRF4.r3, 15164 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15165 goto ok; 15166 case 0xb9dd: s390_format_RRE_RR(s390_irgen_CHLR, ovl.fmt.RRE.r1, 15167 ovl.fmt.RRE.r2); goto ok; 15168 case 0xb9df: s390_format_RRE_RR(s390_irgen_CLHLR, ovl.fmt.RRE.r1, 15169 ovl.fmt.RRE.r2); goto ok; 15170 case 0xb9e1: s390_format_RRE_RR(s390_irgen_POPCNT, ovl.fmt.RRE.r1, 15171 ovl.fmt.RRE.r2); goto ok; 15172 case 0xb9e2: s390_format_RRF_U0RR(s390_irgen_LOCGR, ovl.fmt.RRF3.r3, 15173 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2, 15174 S390_XMNM_LOCGR); goto ok; 15175 case 0xb9e4: s390_format_RRF_R0RR2(s390_irgen_NGRK, ovl.fmt.RRF4.r3, 15176 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15177 goto ok; 15178 case 0xb9e6: s390_format_RRF_R0RR2(s390_irgen_OGRK, ovl.fmt.RRF4.r3, 15179 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15180 goto ok; 15181 case 0xb9e7: s390_format_RRF_R0RR2(s390_irgen_XGRK, ovl.fmt.RRF4.r3, 15182 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15183 goto ok; 15184 case 0xb9e8: s390_format_RRF_R0RR2(s390_irgen_AGRK, ovl.fmt.RRF4.r3, 15185 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15186 goto ok; 15187 case 0xb9e9: s390_format_RRF_R0RR2(s390_irgen_SGRK, ovl.fmt.RRF4.r3, 15188 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15189 goto ok; 15190 case 0xb9ea: s390_format_RRF_R0RR2(s390_irgen_ALGRK, ovl.fmt.RRF4.r3, 15191 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15192 goto ok; 15193 case 0xb9eb: s390_format_RRF_R0RR2(s390_irgen_SLGRK, ovl.fmt.RRF4.r3, 15194 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15195 goto ok; 15196 case 0xb9f2: s390_format_RRF_U0RR(s390_irgen_LOCR, ovl.fmt.RRF3.r3, 15197 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2, 15198 S390_XMNM_LOCR); goto ok; 15199 case 0xb9f4: s390_format_RRF_R0RR2(s390_irgen_NRK, ovl.fmt.RRF4.r3, 15200 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15201 goto ok; 15202 case 0xb9f6: s390_format_RRF_R0RR2(s390_irgen_ORK, ovl.fmt.RRF4.r3, 15203 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15204 goto ok; 15205 case 0xb9f7: s390_format_RRF_R0RR2(s390_irgen_XRK, ovl.fmt.RRF4.r3, 15206 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15207 goto ok; 15208 case 0xb9f8: s390_format_RRF_R0RR2(s390_irgen_ARK, ovl.fmt.RRF4.r3, 15209 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15210 goto ok; 15211 case 0xb9f9: s390_format_RRF_R0RR2(s390_irgen_SRK, ovl.fmt.RRF4.r3, 15212 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15213 goto ok; 15214 case 0xb9fa: s390_format_RRF_R0RR2(s390_irgen_ALRK, ovl.fmt.RRF4.r3, 15215 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15216 goto ok; 15217 case 0xb9fb: s390_format_RRF_R0RR2(s390_irgen_SLRK, ovl.fmt.RRF4.r3, 15218 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15219 goto ok; 15220 } 15221 15222 switch ((ovl.value & 0xff000000) >> 24) { 15223 case 0x40: s390_format_RX_RRRD(s390_irgen_STH, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15224 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15225 case 0x41: s390_format_RX_RRRD(s390_irgen_LA, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15226 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15227 case 0x42: s390_format_RX_RRRD(s390_irgen_STC, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15228 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15229 case 0x43: s390_format_RX_RRRD(s390_irgen_IC, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15230 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15231 case 0x44: s390_format_RX_RRRD(s390_irgen_EX, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15232 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15233 case 0x45: /* BAL */ goto unimplemented; 15234 case 0x46: s390_format_RX_RRRD(s390_irgen_BCT, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15235 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15236 case 0x47: s390_format_RX(s390_irgen_BC, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15237 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15238 case 0x48: s390_format_RX_RRRD(s390_irgen_LH, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15239 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15240 case 0x49: s390_format_RX_RRRD(s390_irgen_CH, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15241 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15242 case 0x4a: s390_format_RX_RRRD(s390_irgen_AH, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15243 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15244 case 0x4b: s390_format_RX_RRRD(s390_irgen_SH, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15245 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15246 case 0x4c: s390_format_RX_RRRD(s390_irgen_MH, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15247 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15248 case 0x4d: s390_format_RX_RRRD(s390_irgen_BAS, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15249 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15250 case 0x4e: s390_format_RX_RRRD(s390_irgen_CVD, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15251 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15252 case 0x4f: s390_format_RX_RRRD(s390_irgen_CVB, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15253 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15254 case 0x50: s390_format_RX_RRRD(s390_irgen_ST, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15255 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15256 case 0x51: s390_format_RX_RRRD(s390_irgen_LAE, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15257 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15258 case 0x54: s390_format_RX_RRRD(s390_irgen_N, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15259 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15260 case 0x55: s390_format_RX_RRRD(s390_irgen_CL, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15261 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15262 case 0x56: s390_format_RX_RRRD(s390_irgen_O, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15263 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15264 case 0x57: s390_format_RX_RRRD(s390_irgen_X, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15265 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15266 case 0x58: s390_format_RX_RRRD(s390_irgen_L, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15267 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15268 case 0x59: s390_format_RX_RRRD(s390_irgen_C, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15269 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15270 case 0x5a: s390_format_RX_RRRD(s390_irgen_A, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15271 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15272 case 0x5b: s390_format_RX_RRRD(s390_irgen_S, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15273 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15274 case 0x5c: s390_format_RX_RRRD(s390_irgen_M, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15275 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15276 case 0x5d: s390_format_RX_RRRD(s390_irgen_D, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15277 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15278 case 0x5e: s390_format_RX_RRRD(s390_irgen_AL, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15279 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15280 case 0x5f: s390_format_RX_RRRD(s390_irgen_SL, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15281 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15282 case 0x60: s390_format_RX_FRRD(s390_irgen_STD, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15283 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15284 case 0x67: /* MXD */ goto unimplemented; 15285 case 0x68: s390_format_RX_FRRD(s390_irgen_LD, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15286 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15287 case 0x69: /* CD */ goto unimplemented; 15288 case 0x6a: /* AD */ goto unimplemented; 15289 case 0x6b: /* SD */ goto unimplemented; 15290 case 0x6c: /* MD */ goto unimplemented; 15291 case 0x6d: /* DD */ goto unimplemented; 15292 case 0x6e: /* AW */ goto unimplemented; 15293 case 0x6f: /* SW */ goto unimplemented; 15294 case 0x70: s390_format_RX_FRRD(s390_irgen_STE, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15295 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15296 case 0x71: s390_format_RX_RRRD(s390_irgen_MS, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15297 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15298 case 0x78: s390_format_RX_FRRD(s390_irgen_LE, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15299 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15300 case 0x79: /* CE */ goto unimplemented; 15301 case 0x7a: /* AE */ goto unimplemented; 15302 case 0x7b: /* SE */ goto unimplemented; 15303 case 0x7c: /* MDE */ goto unimplemented; 15304 case 0x7d: /* DE */ goto unimplemented; 15305 case 0x7e: /* AU */ goto unimplemented; 15306 case 0x7f: /* SU */ goto unimplemented; 15307 case 0x83: /* DIAG */ goto unimplemented; 15308 case 0x84: s390_format_RSI_RRP(s390_irgen_BRXH, ovl.fmt.RSI.r1, 15309 ovl.fmt.RSI.r3, ovl.fmt.RSI.i2); goto ok; 15310 case 0x85: s390_format_RSI_RRP(s390_irgen_BRXLE, ovl.fmt.RSI.r1, 15311 ovl.fmt.RSI.r3, ovl.fmt.RSI.i2); goto ok; 15312 case 0x86: s390_format_RS_RRRD(s390_irgen_BXH, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15313 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15314 case 0x87: s390_format_RS_RRRD(s390_irgen_BXLE, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15315 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15316 case 0x88: s390_format_RS_R0RD(s390_irgen_SRL, ovl.fmt.RS.r1, ovl.fmt.RS.b2, 15317 ovl.fmt.RS.d2); goto ok; 15318 case 0x89: s390_format_RS_R0RD(s390_irgen_SLL, ovl.fmt.RS.r1, ovl.fmt.RS.b2, 15319 ovl.fmt.RS.d2); goto ok; 15320 case 0x8a: s390_format_RS_R0RD(s390_irgen_SRA, ovl.fmt.RS.r1, ovl.fmt.RS.b2, 15321 ovl.fmt.RS.d2); goto ok; 15322 case 0x8b: s390_format_RS_R0RD(s390_irgen_SLA, ovl.fmt.RS.r1, ovl.fmt.RS.b2, 15323 ovl.fmt.RS.d2); goto ok; 15324 case 0x8c: s390_format_RS_R0RD(s390_irgen_SRDL, ovl.fmt.RS.r1, ovl.fmt.RS.b2, 15325 ovl.fmt.RS.d2); goto ok; 15326 case 0x8d: s390_format_RS_R0RD(s390_irgen_SLDL, ovl.fmt.RS.r1, ovl.fmt.RS.b2, 15327 ovl.fmt.RS.d2); goto ok; 15328 case 0x8e: s390_format_RS_R0RD(s390_irgen_SRDA, ovl.fmt.RS.r1, ovl.fmt.RS.b2, 15329 ovl.fmt.RS.d2); goto ok; 15330 case 0x8f: s390_format_RS_R0RD(s390_irgen_SLDA, ovl.fmt.RS.r1, ovl.fmt.RS.b2, 15331 ovl.fmt.RS.d2); goto ok; 15332 case 0x90: s390_format_RS_RRRD(s390_irgen_STM, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15333 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15334 case 0x91: s390_format_SI_URD(s390_irgen_TM, ovl.fmt.SI.i2, ovl.fmt.SI.b1, 15335 ovl.fmt.SI.d1); goto ok; 15336 case 0x92: s390_format_SI_URD(s390_irgen_MVI, ovl.fmt.SI.i2, ovl.fmt.SI.b1, 15337 ovl.fmt.SI.d1); goto ok; 15338 case 0x94: s390_format_SI_URD(s390_irgen_NI, ovl.fmt.SI.i2, ovl.fmt.SI.b1, 15339 ovl.fmt.SI.d1); goto ok; 15340 case 0x95: s390_format_SI_URD(s390_irgen_CLI, ovl.fmt.SI.i2, ovl.fmt.SI.b1, 15341 ovl.fmt.SI.d1); goto ok; 15342 case 0x96: s390_format_SI_URD(s390_irgen_OI, ovl.fmt.SI.i2, ovl.fmt.SI.b1, 15343 ovl.fmt.SI.d1); goto ok; 15344 case 0x97: s390_format_SI_URD(s390_irgen_XI, ovl.fmt.SI.i2, ovl.fmt.SI.b1, 15345 ovl.fmt.SI.d1); goto ok; 15346 case 0x98: s390_format_RS_RRRD(s390_irgen_LM, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15347 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15348 case 0x99: /* TRACE */ goto unimplemented; 15349 case 0x9a: s390_format_RS_AARD(s390_irgen_LAM, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15350 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15351 case 0x9b: s390_format_RS_AARD(s390_irgen_STAM, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15352 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15353 case 0xa8: s390_format_RS_RRRD(s390_irgen_MVCLE, ovl.fmt.RS.r1, 15354 ovl.fmt.RS.r3, ovl.fmt.RS.b2, ovl.fmt.RS.d2); 15355 goto ok; 15356 case 0xa9: s390_format_RS_RRRD(s390_irgen_CLCLE, ovl.fmt.RS.r1, 15357 ovl.fmt.RS.r3, ovl.fmt.RS.b2, ovl.fmt.RS.d2); 15358 goto ok; 15359 case 0xac: /* STNSM */ goto unimplemented; 15360 case 0xad: /* STOSM */ goto unimplemented; 15361 case 0xae: /* SIGP */ goto unimplemented; 15362 case 0xaf: /* MC */ goto unimplemented; 15363 case 0xb1: /* LRA */ goto unimplemented; 15364 case 0xb6: /* STCTL */ goto unimplemented; 15365 case 0xb7: /* LCTL */ goto unimplemented; 15366 case 0xba: s390_format_RS_RRRD(s390_irgen_CS, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15367 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15368 case 0xbb: s390_format_RS_RRRD(s390_irgen_CDS, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15369 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15370 case 0xbd: s390_format_RS_RURD(s390_irgen_CLM, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15371 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15372 case 0xbe: s390_format_RS_RURD(s390_irgen_STCM, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15373 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15374 case 0xbf: s390_format_RS_RURD(s390_irgen_ICM, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15375 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15376 } 15377 15378 return S390_DECODE_UNKNOWN_INSN; 15379 15380 ok: 15381 return S390_DECODE_OK; 15382 15383 unimplemented: 15384 return S390_DECODE_UNIMPLEMENTED_INSN; 15385 } 15386 15387 static s390_decode_t 15388 s390_decode_6byte_and_irgen(const UChar *bytes) 15389 { 15390 typedef union { 15391 struct { 15392 unsigned int op1 : 8; 15393 unsigned int r1 : 4; 15394 unsigned int r3 : 4; 15395 unsigned int i2 : 16; 15396 unsigned int : 8; 15397 unsigned int op2 : 8; 15398 } RIE; 15399 struct { 15400 unsigned int op1 : 8; 15401 unsigned int r1 : 4; 15402 unsigned int r2 : 4; 15403 unsigned int i3 : 8; 15404 unsigned int i4 : 8; 15405 unsigned int i5 : 8; 15406 unsigned int op2 : 8; 15407 } RIE_RRUUU; 15408 struct { 15409 unsigned int op1 : 8; 15410 unsigned int r1 : 4; 15411 unsigned int : 4; 15412 unsigned int i2 : 16; 15413 unsigned int m3 : 4; 15414 unsigned int : 4; 15415 unsigned int op2 : 8; 15416 } RIEv1; 15417 struct { 15418 unsigned int op1 : 8; 15419 unsigned int r1 : 4; 15420 unsigned int r2 : 4; 15421 unsigned int i4 : 16; 15422 unsigned int m3 : 4; 15423 unsigned int : 4; 15424 unsigned int op2 : 8; 15425 } RIE_RRPU; 15426 struct { 15427 unsigned int op1 : 8; 15428 unsigned int r1 : 4; 15429 unsigned int m3 : 4; 15430 unsigned int i4 : 16; 15431 unsigned int i2 : 8; 15432 unsigned int op2 : 8; 15433 } RIEv3; 15434 struct { 15435 unsigned int op1 : 8; 15436 unsigned int r1 : 4; 15437 unsigned int op2 : 4; 15438 unsigned int i2 : 32; 15439 } RIL; 15440 struct { 15441 unsigned int op1 : 8; 15442 unsigned int r1 : 4; 15443 unsigned int m3 : 4; 15444 unsigned int b4 : 4; 15445 unsigned int d4 : 12; 15446 unsigned int i2 : 8; 15447 unsigned int op2 : 8; 15448 } RIS; 15449 struct { 15450 unsigned int op1 : 8; 15451 unsigned int r1 : 4; 15452 unsigned int r2 : 4; 15453 unsigned int b4 : 4; 15454 unsigned int d4 : 12; 15455 unsigned int m3 : 4; 15456 unsigned int : 4; 15457 unsigned int op2 : 8; 15458 } RRS; 15459 struct { 15460 unsigned int op1 : 8; 15461 unsigned int l1 : 4; 15462 unsigned int : 4; 15463 unsigned int b1 : 4; 15464 unsigned int d1 : 12; 15465 unsigned int : 8; 15466 unsigned int op2 : 8; 15467 } RSL; 15468 struct { 15469 unsigned int op1 : 8; 15470 unsigned int r1 : 4; 15471 unsigned int r3 : 4; 15472 unsigned int b2 : 4; 15473 unsigned int dl2 : 12; 15474 unsigned int dh2 : 8; 15475 unsigned int op2 : 8; 15476 } RSY; 15477 struct { 15478 unsigned int op1 : 8; 15479 unsigned int r1 : 4; 15480 unsigned int x2 : 4; 15481 unsigned int b2 : 4; 15482 unsigned int d2 : 12; 15483 unsigned int : 8; 15484 unsigned int op2 : 8; 15485 } RXE; 15486 struct { 15487 unsigned int op1 : 8; 15488 unsigned int r3 : 4; 15489 unsigned int x2 : 4; 15490 unsigned int b2 : 4; 15491 unsigned int d2 : 12; 15492 unsigned int r1 : 4; 15493 unsigned int : 4; 15494 unsigned int op2 : 8; 15495 } RXF; 15496 struct { 15497 unsigned int op1 : 8; 15498 unsigned int r1 : 4; 15499 unsigned int x2 : 4; 15500 unsigned int b2 : 4; 15501 unsigned int dl2 : 12; 15502 unsigned int dh2 : 8; 15503 unsigned int op2 : 8; 15504 } RXY; 15505 struct { 15506 unsigned int op1 : 8; 15507 unsigned int i2 : 8; 15508 unsigned int b1 : 4; 15509 unsigned int dl1 : 12; 15510 unsigned int dh1 : 8; 15511 unsigned int op2 : 8; 15512 } SIY; 15513 struct { 15514 unsigned int op : 8; 15515 unsigned int l : 8; 15516 unsigned int b1 : 4; 15517 unsigned int d1 : 12; 15518 unsigned int b2 : 4; 15519 unsigned int d2 : 12; 15520 } SS; 15521 struct { 15522 unsigned int op : 8; 15523 unsigned int l1 : 4; 15524 unsigned int l2 : 4; 15525 unsigned int b1 : 4; 15526 unsigned int d1 : 12; 15527 unsigned int b2 : 4; 15528 unsigned int d2 : 12; 15529 } SS_LLRDRD; 15530 struct { 15531 unsigned int op : 8; 15532 unsigned int r1 : 4; 15533 unsigned int r3 : 4; 15534 unsigned int b2 : 4; 15535 unsigned int d2 : 12; 15536 unsigned int b4 : 4; 15537 unsigned int d4 : 12; 15538 } SS_RRRDRD2; 15539 struct { 15540 unsigned int op : 16; 15541 unsigned int b1 : 4; 15542 unsigned int d1 : 12; 15543 unsigned int b2 : 4; 15544 unsigned int d2 : 12; 15545 } SSE; 15546 struct { 15547 unsigned int op1 : 8; 15548 unsigned int r3 : 4; 15549 unsigned int op2 : 4; 15550 unsigned int b1 : 4; 15551 unsigned int d1 : 12; 15552 unsigned int b2 : 4; 15553 unsigned int d2 : 12; 15554 } SSF; 15555 struct { 15556 unsigned int op : 16; 15557 unsigned int b1 : 4; 15558 unsigned int d1 : 12; 15559 unsigned int i2 : 16; 15560 } SIL; 15561 } formats; 15562 union { 15563 formats fmt; 15564 ULong value; 15565 } ovl; 15566 15567 vassert(sizeof(formats) == 6); 15568 15569 ((UChar *)(&ovl.value))[0] = bytes[0]; 15570 ((UChar *)(&ovl.value))[1] = bytes[1]; 15571 ((UChar *)(&ovl.value))[2] = bytes[2]; 15572 ((UChar *)(&ovl.value))[3] = bytes[3]; 15573 ((UChar *)(&ovl.value))[4] = bytes[4]; 15574 ((UChar *)(&ovl.value))[5] = bytes[5]; 15575 ((UChar *)(&ovl.value))[6] = 0x0; 15576 ((UChar *)(&ovl.value))[7] = 0x0; 15577 15578 switch ((ovl.value >> 16) & 0xff00000000ffULL) { 15579 case 0xe30000000002ULL: s390_format_RXY_RRRD(s390_irgen_LTG, ovl.fmt.RXY.r1, 15580 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15581 ovl.fmt.RXY.dl2, 15582 ovl.fmt.RXY.dh2); goto ok; 15583 case 0xe30000000003ULL: /* LRAG */ goto unimplemented; 15584 case 0xe30000000004ULL: s390_format_RXY_RRRD(s390_irgen_LG, ovl.fmt.RXY.r1, 15585 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15586 ovl.fmt.RXY.dl2, 15587 ovl.fmt.RXY.dh2); goto ok; 15588 case 0xe30000000006ULL: s390_format_RXY_RRRD(s390_irgen_CVBY, ovl.fmt.RXY.r1, 15589 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15590 ovl.fmt.RXY.dl2, 15591 ovl.fmt.RXY.dh2); goto ok; 15592 case 0xe30000000008ULL: s390_format_RXY_RRRD(s390_irgen_AG, ovl.fmt.RXY.r1, 15593 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15594 ovl.fmt.RXY.dl2, 15595 ovl.fmt.RXY.dh2); goto ok; 15596 case 0xe30000000009ULL: s390_format_RXY_RRRD(s390_irgen_SG, ovl.fmt.RXY.r1, 15597 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15598 ovl.fmt.RXY.dl2, 15599 ovl.fmt.RXY.dh2); goto ok; 15600 case 0xe3000000000aULL: s390_format_RXY_RRRD(s390_irgen_ALG, ovl.fmt.RXY.r1, 15601 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15602 ovl.fmt.RXY.dl2, 15603 ovl.fmt.RXY.dh2); goto ok; 15604 case 0xe3000000000bULL: s390_format_RXY_RRRD(s390_irgen_SLG, ovl.fmt.RXY.r1, 15605 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15606 ovl.fmt.RXY.dl2, 15607 ovl.fmt.RXY.dh2); goto ok; 15608 case 0xe3000000000cULL: s390_format_RXY_RRRD(s390_irgen_MSG, ovl.fmt.RXY.r1, 15609 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15610 ovl.fmt.RXY.dl2, 15611 ovl.fmt.RXY.dh2); goto ok; 15612 case 0xe3000000000dULL: s390_format_RXY_RRRD(s390_irgen_DSG, ovl.fmt.RXY.r1, 15613 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15614 ovl.fmt.RXY.dl2, 15615 ovl.fmt.RXY.dh2); goto ok; 15616 case 0xe3000000000eULL: /* CVBG */ goto unimplemented; 15617 case 0xe3000000000fULL: s390_format_RXY_RRRD(s390_irgen_LRVG, ovl.fmt.RXY.r1, 15618 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15619 ovl.fmt.RXY.dl2, 15620 ovl.fmt.RXY.dh2); goto ok; 15621 case 0xe30000000012ULL: s390_format_RXY_RRRD(s390_irgen_LT, ovl.fmt.RXY.r1, 15622 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15623 ovl.fmt.RXY.dl2, 15624 ovl.fmt.RXY.dh2); goto ok; 15625 case 0xe30000000013ULL: /* LRAY */ goto unimplemented; 15626 case 0xe30000000014ULL: s390_format_RXY_RRRD(s390_irgen_LGF, ovl.fmt.RXY.r1, 15627 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15628 ovl.fmt.RXY.dl2, 15629 ovl.fmt.RXY.dh2); goto ok; 15630 case 0xe30000000015ULL: s390_format_RXY_RRRD(s390_irgen_LGH, ovl.fmt.RXY.r1, 15631 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15632 ovl.fmt.RXY.dl2, 15633 ovl.fmt.RXY.dh2); goto ok; 15634 case 0xe30000000016ULL: s390_format_RXY_RRRD(s390_irgen_LLGF, ovl.fmt.RXY.r1, 15635 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15636 ovl.fmt.RXY.dl2, 15637 ovl.fmt.RXY.dh2); goto ok; 15638 case 0xe30000000017ULL: s390_format_RXY_RRRD(s390_irgen_LLGT, ovl.fmt.RXY.r1, 15639 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15640 ovl.fmt.RXY.dl2, 15641 ovl.fmt.RXY.dh2); goto ok; 15642 case 0xe30000000018ULL: s390_format_RXY_RRRD(s390_irgen_AGF, ovl.fmt.RXY.r1, 15643 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15644 ovl.fmt.RXY.dl2, 15645 ovl.fmt.RXY.dh2); goto ok; 15646 case 0xe30000000019ULL: s390_format_RXY_RRRD(s390_irgen_SGF, ovl.fmt.RXY.r1, 15647 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15648 ovl.fmt.RXY.dl2, 15649 ovl.fmt.RXY.dh2); goto ok; 15650 case 0xe3000000001aULL: s390_format_RXY_RRRD(s390_irgen_ALGF, ovl.fmt.RXY.r1, 15651 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15652 ovl.fmt.RXY.dl2, 15653 ovl.fmt.RXY.dh2); goto ok; 15654 case 0xe3000000001bULL: s390_format_RXY_RRRD(s390_irgen_SLGF, ovl.fmt.RXY.r1, 15655 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15656 ovl.fmt.RXY.dl2, 15657 ovl.fmt.RXY.dh2); goto ok; 15658 case 0xe3000000001cULL: s390_format_RXY_RRRD(s390_irgen_MSGF, ovl.fmt.RXY.r1, 15659 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15660 ovl.fmt.RXY.dl2, 15661 ovl.fmt.RXY.dh2); goto ok; 15662 case 0xe3000000001dULL: s390_format_RXY_RRRD(s390_irgen_DSGF, ovl.fmt.RXY.r1, 15663 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15664 ovl.fmt.RXY.dl2, 15665 ovl.fmt.RXY.dh2); goto ok; 15666 case 0xe3000000001eULL: s390_format_RXY_RRRD(s390_irgen_LRV, ovl.fmt.RXY.r1, 15667 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15668 ovl.fmt.RXY.dl2, 15669 ovl.fmt.RXY.dh2); goto ok; 15670 case 0xe3000000001fULL: s390_format_RXY_RRRD(s390_irgen_LRVH, ovl.fmt.RXY.r1, 15671 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15672 ovl.fmt.RXY.dl2, 15673 ovl.fmt.RXY.dh2); goto ok; 15674 case 0xe30000000020ULL: s390_format_RXY_RRRD(s390_irgen_CG, ovl.fmt.RXY.r1, 15675 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15676 ovl.fmt.RXY.dl2, 15677 ovl.fmt.RXY.dh2); goto ok; 15678 case 0xe30000000021ULL: s390_format_RXY_RRRD(s390_irgen_CLG, ovl.fmt.RXY.r1, 15679 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15680 ovl.fmt.RXY.dl2, 15681 ovl.fmt.RXY.dh2); goto ok; 15682 case 0xe30000000024ULL: s390_format_RXY_RRRD(s390_irgen_STG, ovl.fmt.RXY.r1, 15683 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15684 ovl.fmt.RXY.dl2, 15685 ovl.fmt.RXY.dh2); goto ok; 15686 case 0xe30000000025ULL: /* NTSTG */ goto unimplemented; 15687 case 0xe30000000026ULL: s390_format_RXY_RRRD(s390_irgen_CVDY, ovl.fmt.RXY.r1, 15688 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15689 ovl.fmt.RXY.dl2, 15690 ovl.fmt.RXY.dh2); goto ok; 15691 case 0xe3000000002eULL: /* CVDG */ goto unimplemented; 15692 case 0xe3000000002fULL: s390_format_RXY_RRRD(s390_irgen_STRVG, 15693 ovl.fmt.RXY.r1, ovl.fmt.RXY.x2, 15694 ovl.fmt.RXY.b2, ovl.fmt.RXY.dl2, 15695 ovl.fmt.RXY.dh2); goto ok; 15696 case 0xe30000000030ULL: s390_format_RXY_RRRD(s390_irgen_CGF, ovl.fmt.RXY.r1, 15697 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15698 ovl.fmt.RXY.dl2, 15699 ovl.fmt.RXY.dh2); goto ok; 15700 case 0xe30000000031ULL: s390_format_RXY_RRRD(s390_irgen_CLGF, ovl.fmt.RXY.r1, 15701 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15702 ovl.fmt.RXY.dl2, 15703 ovl.fmt.RXY.dh2); goto ok; 15704 case 0xe30000000032ULL: s390_format_RXY_RRRD(s390_irgen_LTGF, ovl.fmt.RXY.r1, 15705 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15706 ovl.fmt.RXY.dl2, 15707 ovl.fmt.RXY.dh2); goto ok; 15708 case 0xe30000000034ULL: s390_format_RXY_RRRD(s390_irgen_CGH, ovl.fmt.RXY.r1, 15709 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15710 ovl.fmt.RXY.dl2, 15711 ovl.fmt.RXY.dh2); goto ok; 15712 case 0xe30000000036ULL: s390_format_RXY_URRD(s390_irgen_PFD, ovl.fmt.RXY.r1, 15713 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15714 ovl.fmt.RXY.dl2, 15715 ovl.fmt.RXY.dh2); goto ok; 15716 case 0xe3000000003eULL: s390_format_RXY_RRRD(s390_irgen_STRV, ovl.fmt.RXY.r1, 15717 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15718 ovl.fmt.RXY.dl2, 15719 ovl.fmt.RXY.dh2); goto ok; 15720 case 0xe3000000003fULL: s390_format_RXY_RRRD(s390_irgen_STRVH, 15721 ovl.fmt.RXY.r1, ovl.fmt.RXY.x2, 15722 ovl.fmt.RXY.b2, ovl.fmt.RXY.dl2, 15723 ovl.fmt.RXY.dh2); goto ok; 15724 case 0xe30000000046ULL: s390_format_RXY_RRRD(s390_irgen_BCTG, ovl.fmt.RXY.r1, 15725 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15726 ovl.fmt.RXY.dl2, 15727 ovl.fmt.RXY.dh2); goto ok; 15728 case 0xe30000000050ULL: s390_format_RXY_RRRD(s390_irgen_STY, ovl.fmt.RXY.r1, 15729 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15730 ovl.fmt.RXY.dl2, 15731 ovl.fmt.RXY.dh2); goto ok; 15732 case 0xe30000000051ULL: s390_format_RXY_RRRD(s390_irgen_MSY, ovl.fmt.RXY.r1, 15733 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15734 ovl.fmt.RXY.dl2, 15735 ovl.fmt.RXY.dh2); goto ok; 15736 case 0xe30000000054ULL: s390_format_RXY_RRRD(s390_irgen_NY, ovl.fmt.RXY.r1, 15737 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15738 ovl.fmt.RXY.dl2, 15739 ovl.fmt.RXY.dh2); goto ok; 15740 case 0xe30000000055ULL: s390_format_RXY_RRRD(s390_irgen_CLY, ovl.fmt.RXY.r1, 15741 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15742 ovl.fmt.RXY.dl2, 15743 ovl.fmt.RXY.dh2); goto ok; 15744 case 0xe30000000056ULL: s390_format_RXY_RRRD(s390_irgen_OY, ovl.fmt.RXY.r1, 15745 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15746 ovl.fmt.RXY.dl2, 15747 ovl.fmt.RXY.dh2); goto ok; 15748 case 0xe30000000057ULL: s390_format_RXY_RRRD(s390_irgen_XY, ovl.fmt.RXY.r1, 15749 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15750 ovl.fmt.RXY.dl2, 15751 ovl.fmt.RXY.dh2); goto ok; 15752 case 0xe30000000058ULL: s390_format_RXY_RRRD(s390_irgen_LY, ovl.fmt.RXY.r1, 15753 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15754 ovl.fmt.RXY.dl2, 15755 ovl.fmt.RXY.dh2); goto ok; 15756 case 0xe30000000059ULL: s390_format_RXY_RRRD(s390_irgen_CY, ovl.fmt.RXY.r1, 15757 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15758 ovl.fmt.RXY.dl2, 15759 ovl.fmt.RXY.dh2); goto ok; 15760 case 0xe3000000005aULL: s390_format_RXY_RRRD(s390_irgen_AY, ovl.fmt.RXY.r1, 15761 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15762 ovl.fmt.RXY.dl2, 15763 ovl.fmt.RXY.dh2); goto ok; 15764 case 0xe3000000005bULL: s390_format_RXY_RRRD(s390_irgen_SY, ovl.fmt.RXY.r1, 15765 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15766 ovl.fmt.RXY.dl2, 15767 ovl.fmt.RXY.dh2); goto ok; 15768 case 0xe3000000005cULL: s390_format_RXY_RRRD(s390_irgen_MFY, ovl.fmt.RXY.r1, 15769 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15770 ovl.fmt.RXY.dl2, 15771 ovl.fmt.RXY.dh2); goto ok; 15772 case 0xe3000000005eULL: s390_format_RXY_RRRD(s390_irgen_ALY, ovl.fmt.RXY.r1, 15773 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15774 ovl.fmt.RXY.dl2, 15775 ovl.fmt.RXY.dh2); goto ok; 15776 case 0xe3000000005fULL: s390_format_RXY_RRRD(s390_irgen_SLY, ovl.fmt.RXY.r1, 15777 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15778 ovl.fmt.RXY.dl2, 15779 ovl.fmt.RXY.dh2); goto ok; 15780 case 0xe30000000070ULL: s390_format_RXY_RRRD(s390_irgen_STHY, ovl.fmt.RXY.r1, 15781 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15782 ovl.fmt.RXY.dl2, 15783 ovl.fmt.RXY.dh2); goto ok; 15784 case 0xe30000000071ULL: s390_format_RXY_RRRD(s390_irgen_LAY, ovl.fmt.RXY.r1, 15785 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15786 ovl.fmt.RXY.dl2, 15787 ovl.fmt.RXY.dh2); goto ok; 15788 case 0xe30000000072ULL: s390_format_RXY_RRRD(s390_irgen_STCY, ovl.fmt.RXY.r1, 15789 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15790 ovl.fmt.RXY.dl2, 15791 ovl.fmt.RXY.dh2); goto ok; 15792 case 0xe30000000073ULL: s390_format_RXY_RRRD(s390_irgen_ICY, ovl.fmt.RXY.r1, 15793 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15794 ovl.fmt.RXY.dl2, 15795 ovl.fmt.RXY.dh2); goto ok; 15796 case 0xe30000000075ULL: s390_format_RXY_RRRD(s390_irgen_LAEY, ovl.fmt.RXY.r1, 15797 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15798 ovl.fmt.RXY.dl2, 15799 ovl.fmt.RXY.dh2); goto ok; 15800 case 0xe30000000076ULL: s390_format_RXY_RRRD(s390_irgen_LB, ovl.fmt.RXY.r1, 15801 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15802 ovl.fmt.RXY.dl2, 15803 ovl.fmt.RXY.dh2); goto ok; 15804 case 0xe30000000077ULL: s390_format_RXY_RRRD(s390_irgen_LGB, ovl.fmt.RXY.r1, 15805 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15806 ovl.fmt.RXY.dl2, 15807 ovl.fmt.RXY.dh2); goto ok; 15808 case 0xe30000000078ULL: s390_format_RXY_RRRD(s390_irgen_LHY, ovl.fmt.RXY.r1, 15809 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15810 ovl.fmt.RXY.dl2, 15811 ovl.fmt.RXY.dh2); goto ok; 15812 case 0xe30000000079ULL: s390_format_RXY_RRRD(s390_irgen_CHY, ovl.fmt.RXY.r1, 15813 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15814 ovl.fmt.RXY.dl2, 15815 ovl.fmt.RXY.dh2); goto ok; 15816 case 0xe3000000007aULL: s390_format_RXY_RRRD(s390_irgen_AHY, ovl.fmt.RXY.r1, 15817 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15818 ovl.fmt.RXY.dl2, 15819 ovl.fmt.RXY.dh2); goto ok; 15820 case 0xe3000000007bULL: s390_format_RXY_RRRD(s390_irgen_SHY, ovl.fmt.RXY.r1, 15821 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15822 ovl.fmt.RXY.dl2, 15823 ovl.fmt.RXY.dh2); goto ok; 15824 case 0xe3000000007cULL: s390_format_RXY_RRRD(s390_irgen_MHY, ovl.fmt.RXY.r1, 15825 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15826 ovl.fmt.RXY.dl2, 15827 ovl.fmt.RXY.dh2); goto ok; 15828 case 0xe30000000080ULL: s390_format_RXY_RRRD(s390_irgen_NG, ovl.fmt.RXY.r1, 15829 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15830 ovl.fmt.RXY.dl2, 15831 ovl.fmt.RXY.dh2); goto ok; 15832 case 0xe30000000081ULL: s390_format_RXY_RRRD(s390_irgen_OG, ovl.fmt.RXY.r1, 15833 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15834 ovl.fmt.RXY.dl2, 15835 ovl.fmt.RXY.dh2); goto ok; 15836 case 0xe30000000082ULL: s390_format_RXY_RRRD(s390_irgen_XG, ovl.fmt.RXY.r1, 15837 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15838 ovl.fmt.RXY.dl2, 15839 ovl.fmt.RXY.dh2); goto ok; 15840 case 0xe30000000085ULL: /* LGAT */ goto unimplemented; 15841 case 0xe30000000086ULL: s390_format_RXY_RRRD(s390_irgen_MLG, ovl.fmt.RXY.r1, 15842 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15843 ovl.fmt.RXY.dl2, 15844 ovl.fmt.RXY.dh2); goto ok; 15845 case 0xe30000000087ULL: s390_format_RXY_RRRD(s390_irgen_DLG, ovl.fmt.RXY.r1, 15846 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15847 ovl.fmt.RXY.dl2, 15848 ovl.fmt.RXY.dh2); goto ok; 15849 case 0xe30000000088ULL: s390_format_RXY_RRRD(s390_irgen_ALCG, ovl.fmt.RXY.r1, 15850 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15851 ovl.fmt.RXY.dl2, 15852 ovl.fmt.RXY.dh2); goto ok; 15853 case 0xe30000000089ULL: s390_format_RXY_RRRD(s390_irgen_SLBG, ovl.fmt.RXY.r1, 15854 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15855 ovl.fmt.RXY.dl2, 15856 ovl.fmt.RXY.dh2); goto ok; 15857 case 0xe3000000008eULL: s390_format_RXY_RRRD(s390_irgen_STPQ, ovl.fmt.RXY.r1, 15858 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15859 ovl.fmt.RXY.dl2, 15860 ovl.fmt.RXY.dh2); goto ok; 15861 case 0xe3000000008fULL: s390_format_RXY_RRRD(s390_irgen_LPQ, ovl.fmt.RXY.r1, 15862 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15863 ovl.fmt.RXY.dl2, 15864 ovl.fmt.RXY.dh2); goto ok; 15865 case 0xe30000000090ULL: s390_format_RXY_RRRD(s390_irgen_LLGC, ovl.fmt.RXY.r1, 15866 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15867 ovl.fmt.RXY.dl2, 15868 ovl.fmt.RXY.dh2); goto ok; 15869 case 0xe30000000091ULL: s390_format_RXY_RRRD(s390_irgen_LLGH, ovl.fmt.RXY.r1, 15870 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15871 ovl.fmt.RXY.dl2, 15872 ovl.fmt.RXY.dh2); goto ok; 15873 case 0xe30000000094ULL: s390_format_RXY_RRRD(s390_irgen_LLC, ovl.fmt.RXY.r1, 15874 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15875 ovl.fmt.RXY.dl2, 15876 ovl.fmt.RXY.dh2); goto ok; 15877 case 0xe30000000095ULL: s390_format_RXY_RRRD(s390_irgen_LLH, ovl.fmt.RXY.r1, 15878 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15879 ovl.fmt.RXY.dl2, 15880 ovl.fmt.RXY.dh2); goto ok; 15881 case 0xe30000000096ULL: s390_format_RXY_RRRD(s390_irgen_ML, ovl.fmt.RXY.r1, 15882 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15883 ovl.fmt.RXY.dl2, 15884 ovl.fmt.RXY.dh2); goto ok; 15885 case 0xe30000000097ULL: s390_format_RXY_RRRD(s390_irgen_DL, ovl.fmt.RXY.r1, 15886 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15887 ovl.fmt.RXY.dl2, 15888 ovl.fmt.RXY.dh2); goto ok; 15889 case 0xe30000000098ULL: s390_format_RXY_RRRD(s390_irgen_ALC, ovl.fmt.RXY.r1, 15890 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15891 ovl.fmt.RXY.dl2, 15892 ovl.fmt.RXY.dh2); goto ok; 15893 case 0xe30000000099ULL: s390_format_RXY_RRRD(s390_irgen_SLB, ovl.fmt.RXY.r1, 15894 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15895 ovl.fmt.RXY.dl2, 15896 ovl.fmt.RXY.dh2); goto ok; 15897 case 0xe3000000009cULL: /* LLGTAT */ goto unimplemented; 15898 case 0xe3000000009dULL: /* LLGFAT */ goto unimplemented; 15899 case 0xe3000000009fULL: /* LAT */ goto unimplemented; 15900 case 0xe300000000c0ULL: s390_format_RXY_RRRD(s390_irgen_LBH, ovl.fmt.RXY.r1, 15901 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15902 ovl.fmt.RXY.dl2, 15903 ovl.fmt.RXY.dh2); goto ok; 15904 case 0xe300000000c2ULL: s390_format_RXY_RRRD(s390_irgen_LLCH, ovl.fmt.RXY.r1, 15905 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15906 ovl.fmt.RXY.dl2, 15907 ovl.fmt.RXY.dh2); goto ok; 15908 case 0xe300000000c3ULL: s390_format_RXY_RRRD(s390_irgen_STCH, ovl.fmt.RXY.r1, 15909 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15910 ovl.fmt.RXY.dl2, 15911 ovl.fmt.RXY.dh2); goto ok; 15912 case 0xe300000000c4ULL: s390_format_RXY_RRRD(s390_irgen_LHH, ovl.fmt.RXY.r1, 15913 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15914 ovl.fmt.RXY.dl2, 15915 ovl.fmt.RXY.dh2); goto ok; 15916 case 0xe300000000c6ULL: s390_format_RXY_RRRD(s390_irgen_LLHH, ovl.fmt.RXY.r1, 15917 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15918 ovl.fmt.RXY.dl2, 15919 ovl.fmt.RXY.dh2); goto ok; 15920 case 0xe300000000c7ULL: s390_format_RXY_RRRD(s390_irgen_STHH, ovl.fmt.RXY.r1, 15921 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15922 ovl.fmt.RXY.dl2, 15923 ovl.fmt.RXY.dh2); goto ok; 15924 case 0xe300000000c8ULL: /* LFHAT */ goto unimplemented; 15925 case 0xe300000000caULL: s390_format_RXY_RRRD(s390_irgen_LFH, ovl.fmt.RXY.r1, 15926 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15927 ovl.fmt.RXY.dl2, 15928 ovl.fmt.RXY.dh2); goto ok; 15929 case 0xe300000000cbULL: s390_format_RXY_RRRD(s390_irgen_STFH, ovl.fmt.RXY.r1, 15930 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15931 ovl.fmt.RXY.dl2, 15932 ovl.fmt.RXY.dh2); goto ok; 15933 case 0xe300000000cdULL: s390_format_RXY_RRRD(s390_irgen_CHF, ovl.fmt.RXY.r1, 15934 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15935 ovl.fmt.RXY.dl2, 15936 ovl.fmt.RXY.dh2); goto ok; 15937 case 0xe300000000cfULL: s390_format_RXY_RRRD(s390_irgen_CLHF, ovl.fmt.RXY.r1, 15938 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15939 ovl.fmt.RXY.dl2, 15940 ovl.fmt.RXY.dh2); goto ok; 15941 case 0xeb0000000004ULL: s390_format_RSY_RRRD(s390_irgen_LMG, ovl.fmt.RSY.r1, 15942 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15943 ovl.fmt.RSY.dl2, 15944 ovl.fmt.RSY.dh2); goto ok; 15945 case 0xeb000000000aULL: s390_format_RSY_RRRD(s390_irgen_SRAG, ovl.fmt.RSY.r1, 15946 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15947 ovl.fmt.RSY.dl2, 15948 ovl.fmt.RSY.dh2); goto ok; 15949 case 0xeb000000000bULL: s390_format_RSY_RRRD(s390_irgen_SLAG, ovl.fmt.RSY.r1, 15950 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15951 ovl.fmt.RSY.dl2, 15952 ovl.fmt.RSY.dh2); goto ok; 15953 case 0xeb000000000cULL: s390_format_RSY_RRRD(s390_irgen_SRLG, ovl.fmt.RSY.r1, 15954 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15955 ovl.fmt.RSY.dl2, 15956 ovl.fmt.RSY.dh2); goto ok; 15957 case 0xeb000000000dULL: s390_format_RSY_RRRD(s390_irgen_SLLG, ovl.fmt.RSY.r1, 15958 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15959 ovl.fmt.RSY.dl2, 15960 ovl.fmt.RSY.dh2); goto ok; 15961 case 0xeb000000000fULL: /* TRACG */ goto unimplemented; 15962 case 0xeb0000000014ULL: s390_format_RSY_RRRD(s390_irgen_CSY, ovl.fmt.RSY.r1, 15963 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15964 ovl.fmt.RSY.dl2, 15965 ovl.fmt.RSY.dh2); goto ok; 15966 case 0xeb000000001cULL: s390_format_RSY_RRRD(s390_irgen_RLLG, ovl.fmt.RSY.r1, 15967 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15968 ovl.fmt.RSY.dl2, 15969 ovl.fmt.RSY.dh2); goto ok; 15970 case 0xeb000000001dULL: s390_format_RSY_RRRD(s390_irgen_RLL, ovl.fmt.RSY.r1, 15971 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15972 ovl.fmt.RSY.dl2, 15973 ovl.fmt.RSY.dh2); goto ok; 15974 case 0xeb0000000020ULL: s390_format_RSY_RURD(s390_irgen_CLMH, ovl.fmt.RSY.r1, 15975 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15976 ovl.fmt.RSY.dl2, 15977 ovl.fmt.RSY.dh2); goto ok; 15978 case 0xeb0000000021ULL: s390_format_RSY_RURD(s390_irgen_CLMY, ovl.fmt.RSY.r1, 15979 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15980 ovl.fmt.RSY.dl2, 15981 ovl.fmt.RSY.dh2); goto ok; 15982 case 0xeb0000000023ULL: /* CLT */ goto unimplemented; 15983 case 0xeb0000000024ULL: s390_format_RSY_RRRD(s390_irgen_STMG, ovl.fmt.RSY.r1, 15984 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15985 ovl.fmt.RSY.dl2, 15986 ovl.fmt.RSY.dh2); goto ok; 15987 case 0xeb0000000025ULL: /* STCTG */ goto unimplemented; 15988 case 0xeb0000000026ULL: s390_format_RSY_RRRD(s390_irgen_STMH, ovl.fmt.RSY.r1, 15989 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15990 ovl.fmt.RSY.dl2, 15991 ovl.fmt.RSY.dh2); goto ok; 15992 case 0xeb000000002bULL: /* CLGT */ goto unimplemented; 15993 case 0xeb000000002cULL: s390_format_RSY_RURD(s390_irgen_STCMH, 15994 ovl.fmt.RSY.r1, ovl.fmt.RSY.r3, 15995 ovl.fmt.RSY.b2, ovl.fmt.RSY.dl2, 15996 ovl.fmt.RSY.dh2); goto ok; 15997 case 0xeb000000002dULL: s390_format_RSY_RURD(s390_irgen_STCMY, 15998 ovl.fmt.RSY.r1, ovl.fmt.RSY.r3, 15999 ovl.fmt.RSY.b2, ovl.fmt.RSY.dl2, 16000 ovl.fmt.RSY.dh2); goto ok; 16001 case 0xeb000000002fULL: /* LCTLG */ goto unimplemented; 16002 case 0xeb0000000030ULL: s390_format_RSY_RRRD(s390_irgen_CSG, ovl.fmt.RSY.r1, 16003 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16004 ovl.fmt.RSY.dl2, 16005 ovl.fmt.RSY.dh2); goto ok; 16006 case 0xeb0000000031ULL: s390_format_RSY_RRRD(s390_irgen_CDSY, ovl.fmt.RSY.r1, 16007 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16008 ovl.fmt.RSY.dl2, 16009 ovl.fmt.RSY.dh2); goto ok; 16010 case 0xeb000000003eULL: s390_format_RSY_RRRD(s390_irgen_CDSG, ovl.fmt.RSY.r1, 16011 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16012 ovl.fmt.RSY.dl2, 16013 ovl.fmt.RSY.dh2); goto ok; 16014 case 0xeb0000000044ULL: s390_format_RSY_RRRD(s390_irgen_BXHG, ovl.fmt.RSY.r1, 16015 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16016 ovl.fmt.RSY.dl2, 16017 ovl.fmt.RSY.dh2); goto ok; 16018 case 0xeb0000000045ULL: s390_format_RSY_RRRD(s390_irgen_BXLEG, 16019 ovl.fmt.RSY.r1, ovl.fmt.RSY.r3, 16020 ovl.fmt.RSY.b2, ovl.fmt.RSY.dl2, 16021 ovl.fmt.RSY.dh2); goto ok; 16022 case 0xeb000000004cULL: s390_format_RSY_RRRD(s390_irgen_ECAG, ovl.fmt.RSY.r1, 16023 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16024 ovl.fmt.RSY.dl2, 16025 ovl.fmt.RSY.dh2); goto ok; 16026 case 0xeb0000000051ULL: s390_format_SIY_URD(s390_irgen_TMY, ovl.fmt.SIY.i2, 16027 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 16028 ovl.fmt.SIY.dh1); goto ok; 16029 case 0xeb0000000052ULL: s390_format_SIY_URD(s390_irgen_MVIY, ovl.fmt.SIY.i2, 16030 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 16031 ovl.fmt.SIY.dh1); goto ok; 16032 case 0xeb0000000054ULL: s390_format_SIY_URD(s390_irgen_NIY, ovl.fmt.SIY.i2, 16033 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 16034 ovl.fmt.SIY.dh1); goto ok; 16035 case 0xeb0000000055ULL: s390_format_SIY_URD(s390_irgen_CLIY, ovl.fmt.SIY.i2, 16036 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 16037 ovl.fmt.SIY.dh1); goto ok; 16038 case 0xeb0000000056ULL: s390_format_SIY_URD(s390_irgen_OIY, ovl.fmt.SIY.i2, 16039 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 16040 ovl.fmt.SIY.dh1); goto ok; 16041 case 0xeb0000000057ULL: s390_format_SIY_URD(s390_irgen_XIY, ovl.fmt.SIY.i2, 16042 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 16043 ovl.fmt.SIY.dh1); goto ok; 16044 case 0xeb000000006aULL: s390_format_SIY_IRD(s390_irgen_ASI, ovl.fmt.SIY.i2, 16045 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 16046 ovl.fmt.SIY.dh1); goto ok; 16047 case 0xeb000000006eULL: s390_format_SIY_IRD(s390_irgen_ALSI, ovl.fmt.SIY.i2, 16048 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 16049 ovl.fmt.SIY.dh1); goto ok; 16050 case 0xeb000000007aULL: s390_format_SIY_IRD(s390_irgen_AGSI, ovl.fmt.SIY.i2, 16051 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 16052 ovl.fmt.SIY.dh1); goto ok; 16053 case 0xeb000000007eULL: s390_format_SIY_IRD(s390_irgen_ALGSI, ovl.fmt.SIY.i2, 16054 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 16055 ovl.fmt.SIY.dh1); goto ok; 16056 case 0xeb0000000080ULL: s390_format_RSY_RURD(s390_irgen_ICMH, ovl.fmt.RSY.r1, 16057 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16058 ovl.fmt.RSY.dl2, 16059 ovl.fmt.RSY.dh2); goto ok; 16060 case 0xeb0000000081ULL: s390_format_RSY_RURD(s390_irgen_ICMY, ovl.fmt.RSY.r1, 16061 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16062 ovl.fmt.RSY.dl2, 16063 ovl.fmt.RSY.dh2); goto ok; 16064 case 0xeb000000008eULL: /* MVCLU */ goto unimplemented; 16065 case 0xeb000000008fULL: /* CLCLU */ goto unimplemented; 16066 case 0xeb0000000090ULL: s390_format_RSY_RRRD(s390_irgen_STMY, ovl.fmt.RSY.r1, 16067 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16068 ovl.fmt.RSY.dl2, 16069 ovl.fmt.RSY.dh2); goto ok; 16070 case 0xeb0000000096ULL: s390_format_RSY_RRRD(s390_irgen_LMH, ovl.fmt.RSY.r1, 16071 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16072 ovl.fmt.RSY.dl2, 16073 ovl.fmt.RSY.dh2); goto ok; 16074 case 0xeb0000000098ULL: s390_format_RSY_RRRD(s390_irgen_LMY, ovl.fmt.RSY.r1, 16075 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16076 ovl.fmt.RSY.dl2, 16077 ovl.fmt.RSY.dh2); goto ok; 16078 case 0xeb000000009aULL: s390_format_RSY_AARD(s390_irgen_LAMY, ovl.fmt.RSY.r1, 16079 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16080 ovl.fmt.RSY.dl2, 16081 ovl.fmt.RSY.dh2); goto ok; 16082 case 0xeb000000009bULL: s390_format_RSY_AARD(s390_irgen_STAMY, 16083 ovl.fmt.RSY.r1, ovl.fmt.RSY.r3, 16084 ovl.fmt.RSY.b2, ovl.fmt.RSY.dl2, 16085 ovl.fmt.RSY.dh2); goto ok; 16086 case 0xeb00000000c0ULL: /* TP */ goto unimplemented; 16087 case 0xeb00000000dcULL: s390_format_RSY_RRRD(s390_irgen_SRAK, ovl.fmt.RSY.r1, 16088 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16089 ovl.fmt.RSY.dl2, 16090 ovl.fmt.RSY.dh2); goto ok; 16091 case 0xeb00000000ddULL: s390_format_RSY_RRRD(s390_irgen_SLAK, ovl.fmt.RSY.r1, 16092 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16093 ovl.fmt.RSY.dl2, 16094 ovl.fmt.RSY.dh2); goto ok; 16095 case 0xeb00000000deULL: s390_format_RSY_RRRD(s390_irgen_SRLK, ovl.fmt.RSY.r1, 16096 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16097 ovl.fmt.RSY.dl2, 16098 ovl.fmt.RSY.dh2); goto ok; 16099 case 0xeb00000000dfULL: s390_format_RSY_RRRD(s390_irgen_SLLK, ovl.fmt.RSY.r1, 16100 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16101 ovl.fmt.RSY.dl2, 16102 ovl.fmt.RSY.dh2); goto ok; 16103 case 0xeb00000000e2ULL: s390_format_RSY_RDRM(s390_irgen_LOCG, ovl.fmt.RSY.r1, 16104 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16105 ovl.fmt.RSY.dl2, 16106 ovl.fmt.RSY.dh2, 16107 S390_XMNM_LOCG); goto ok; 16108 case 0xeb00000000e3ULL: s390_format_RSY_RDRM(s390_irgen_STOCG, 16109 ovl.fmt.RSY.r1, ovl.fmt.RSY.r3, 16110 ovl.fmt.RSY.b2, ovl.fmt.RSY.dl2, 16111 ovl.fmt.RSY.dh2, 16112 S390_XMNM_STOCG); goto ok; 16113 case 0xeb00000000e4ULL: s390_format_RSY_RRRD(s390_irgen_LANG, ovl.fmt.RSY.r1, 16114 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16115 ovl.fmt.RSY.dl2, 16116 ovl.fmt.RSY.dh2); goto ok; 16117 case 0xeb00000000e6ULL: s390_format_RSY_RRRD(s390_irgen_LAOG, ovl.fmt.RSY.r1, 16118 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16119 ovl.fmt.RSY.dl2, 16120 ovl.fmt.RSY.dh2); goto ok; 16121 case 0xeb00000000e7ULL: s390_format_RSY_RRRD(s390_irgen_LAXG, ovl.fmt.RSY.r1, 16122 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16123 ovl.fmt.RSY.dl2, 16124 ovl.fmt.RSY.dh2); goto ok; 16125 case 0xeb00000000e8ULL: s390_format_RSY_RRRD(s390_irgen_LAAG, ovl.fmt.RSY.r1, 16126 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16127 ovl.fmt.RSY.dl2, 16128 ovl.fmt.RSY.dh2); goto ok; 16129 case 0xeb00000000eaULL: s390_format_RSY_RRRD(s390_irgen_LAALG, 16130 ovl.fmt.RSY.r1, ovl.fmt.RSY.r3, 16131 ovl.fmt.RSY.b2, ovl.fmt.RSY.dl2, 16132 ovl.fmt.RSY.dh2); goto ok; 16133 case 0xeb00000000f2ULL: s390_format_RSY_RDRM(s390_irgen_LOC, ovl.fmt.RSY.r1, 16134 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16135 ovl.fmt.RSY.dl2, 16136 ovl.fmt.RSY.dh2, S390_XMNM_LOC); 16137 goto ok; 16138 case 0xeb00000000f3ULL: s390_format_RSY_RDRM(s390_irgen_STOC, ovl.fmt.RSY.r1, 16139 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16140 ovl.fmt.RSY.dl2, 16141 ovl.fmt.RSY.dh2, 16142 S390_XMNM_STOC); goto ok; 16143 case 0xeb00000000f4ULL: s390_format_RSY_RRRD(s390_irgen_LAN, ovl.fmt.RSY.r1, 16144 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16145 ovl.fmt.RSY.dl2, 16146 ovl.fmt.RSY.dh2); goto ok; 16147 case 0xeb00000000f6ULL: s390_format_RSY_RRRD(s390_irgen_LAO, ovl.fmt.RSY.r1, 16148 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16149 ovl.fmt.RSY.dl2, 16150 ovl.fmt.RSY.dh2); goto ok; 16151 case 0xeb00000000f7ULL: s390_format_RSY_RRRD(s390_irgen_LAX, ovl.fmt.RSY.r1, 16152 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16153 ovl.fmt.RSY.dl2, 16154 ovl.fmt.RSY.dh2); goto ok; 16155 case 0xeb00000000f8ULL: s390_format_RSY_RRRD(s390_irgen_LAA, ovl.fmt.RSY.r1, 16156 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16157 ovl.fmt.RSY.dl2, 16158 ovl.fmt.RSY.dh2); goto ok; 16159 case 0xeb00000000faULL: s390_format_RSY_RRRD(s390_irgen_LAAL, ovl.fmt.RSY.r1, 16160 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 16161 ovl.fmt.RSY.dl2, 16162 ovl.fmt.RSY.dh2); goto ok; 16163 case 0xec0000000044ULL: s390_format_RIE_RRP(s390_irgen_BRXHG, ovl.fmt.RIE.r1, 16164 ovl.fmt.RIE.r3, ovl.fmt.RIE.i2); 16165 goto ok; 16166 case 0xec0000000045ULL: s390_format_RIE_RRP(s390_irgen_BRXLG, ovl.fmt.RIE.r1, 16167 ovl.fmt.RIE.r3, ovl.fmt.RIE.i2); 16168 goto ok; 16169 case 0xec0000000051ULL: s390_format_RIE_RRUUU(s390_irgen_RISBLG, 16170 ovl.fmt.RIE_RRUUU.r1, 16171 ovl.fmt.RIE_RRUUU.r2, 16172 ovl.fmt.RIE_RRUUU.i3, 16173 ovl.fmt.RIE_RRUUU.i4, 16174 ovl.fmt.RIE_RRUUU.i5); 16175 goto ok; 16176 case 0xec0000000054ULL: s390_format_RIE_RRUUU(s390_irgen_RNSBG, 16177 ovl.fmt.RIE_RRUUU.r1, 16178 ovl.fmt.RIE_RRUUU.r2, 16179 ovl.fmt.RIE_RRUUU.i3, 16180 ovl.fmt.RIE_RRUUU.i4, 16181 ovl.fmt.RIE_RRUUU.i5); 16182 goto ok; 16183 case 0xec0000000055ULL: s390_format_RIE_RRUUU(s390_irgen_RISBG, 16184 ovl.fmt.RIE_RRUUU.r1, 16185 ovl.fmt.RIE_RRUUU.r2, 16186 ovl.fmt.RIE_RRUUU.i3, 16187 ovl.fmt.RIE_RRUUU.i4, 16188 ovl.fmt.RIE_RRUUU.i5); 16189 goto ok; 16190 case 0xec0000000056ULL: s390_format_RIE_RRUUU(s390_irgen_ROSBG, 16191 ovl.fmt.RIE_RRUUU.r1, 16192 ovl.fmt.RIE_RRUUU.r2, 16193 ovl.fmt.RIE_RRUUU.i3, 16194 ovl.fmt.RIE_RRUUU.i4, 16195 ovl.fmt.RIE_RRUUU.i5); 16196 goto ok; 16197 case 0xec0000000057ULL: s390_format_RIE_RRUUU(s390_irgen_RXSBG, 16198 ovl.fmt.RIE_RRUUU.r1, 16199 ovl.fmt.RIE_RRUUU.r2, 16200 ovl.fmt.RIE_RRUUU.i3, 16201 ovl.fmt.RIE_RRUUU.i4, 16202 ovl.fmt.RIE_RRUUU.i5); 16203 goto ok; 16204 case 0xec0000000059ULL: s390_format_RIE_RRUUU(s390_irgen_RISBGN, 16205 ovl.fmt.RIE_RRUUU.r1, 16206 ovl.fmt.RIE_RRUUU.r2, 16207 ovl.fmt.RIE_RRUUU.i3, 16208 ovl.fmt.RIE_RRUUU.i4, 16209 ovl.fmt.RIE_RRUUU.i5); 16210 goto ok; 16211 case 0xec000000005dULL: s390_format_RIE_RRUUU(s390_irgen_RISBHG, 16212 ovl.fmt.RIE_RRUUU.r1, 16213 ovl.fmt.RIE_RRUUU.r2, 16214 ovl.fmt.RIE_RRUUU.i3, 16215 ovl.fmt.RIE_RRUUU.i4, 16216 ovl.fmt.RIE_RRUUU.i5); 16217 goto ok; 16218 case 0xec0000000064ULL: s390_format_RIE_RRPU(s390_irgen_CGRJ, 16219 ovl.fmt.RIE_RRPU.r1, 16220 ovl.fmt.RIE_RRPU.r2, 16221 ovl.fmt.RIE_RRPU.i4, 16222 ovl.fmt.RIE_RRPU.m3); goto ok; 16223 case 0xec0000000065ULL: s390_format_RIE_RRPU(s390_irgen_CLGRJ, 16224 ovl.fmt.RIE_RRPU.r1, 16225 ovl.fmt.RIE_RRPU.r2, 16226 ovl.fmt.RIE_RRPU.i4, 16227 ovl.fmt.RIE_RRPU.m3); goto ok; 16228 case 0xec0000000070ULL: /* CGIT */ goto unimplemented; 16229 case 0xec0000000071ULL: /* CLGIT */ goto unimplemented; 16230 case 0xec0000000072ULL: /* CIT */ goto unimplemented; 16231 case 0xec0000000073ULL: /* CLFIT */ goto unimplemented; 16232 case 0xec0000000076ULL: s390_format_RIE_RRPU(s390_irgen_CRJ, 16233 ovl.fmt.RIE_RRPU.r1, 16234 ovl.fmt.RIE_RRPU.r2, 16235 ovl.fmt.RIE_RRPU.i4, 16236 ovl.fmt.RIE_RRPU.m3); goto ok; 16237 case 0xec0000000077ULL: s390_format_RIE_RRPU(s390_irgen_CLRJ, 16238 ovl.fmt.RIE_RRPU.r1, 16239 ovl.fmt.RIE_RRPU.r2, 16240 ovl.fmt.RIE_RRPU.i4, 16241 ovl.fmt.RIE_RRPU.m3); goto ok; 16242 case 0xec000000007cULL: s390_format_RIE_RUPI(s390_irgen_CGIJ, 16243 ovl.fmt.RIEv3.r1, 16244 ovl.fmt.RIEv3.m3, 16245 ovl.fmt.RIEv3.i4, 16246 ovl.fmt.RIEv3.i2); goto ok; 16247 case 0xec000000007dULL: s390_format_RIE_RUPU(s390_irgen_CLGIJ, 16248 ovl.fmt.RIEv3.r1, 16249 ovl.fmt.RIEv3.m3, 16250 ovl.fmt.RIEv3.i4, 16251 ovl.fmt.RIEv3.i2); goto ok; 16252 case 0xec000000007eULL: s390_format_RIE_RUPI(s390_irgen_CIJ, 16253 ovl.fmt.RIEv3.r1, 16254 ovl.fmt.RIEv3.m3, 16255 ovl.fmt.RIEv3.i4, 16256 ovl.fmt.RIEv3.i2); goto ok; 16257 case 0xec000000007fULL: s390_format_RIE_RUPU(s390_irgen_CLIJ, 16258 ovl.fmt.RIEv3.r1, 16259 ovl.fmt.RIEv3.m3, 16260 ovl.fmt.RIEv3.i4, 16261 ovl.fmt.RIEv3.i2); goto ok; 16262 case 0xec00000000d8ULL: s390_format_RIE_RRI0(s390_irgen_AHIK, ovl.fmt.RIE.r1, 16263 ovl.fmt.RIE.r3, ovl.fmt.RIE.i2); 16264 goto ok; 16265 case 0xec00000000d9ULL: s390_format_RIE_RRI0(s390_irgen_AGHIK, 16266 ovl.fmt.RIE.r1, ovl.fmt.RIE.r3, 16267 ovl.fmt.RIE.i2); goto ok; 16268 case 0xec00000000daULL: s390_format_RIE_RRI0(s390_irgen_ALHSIK, 16269 ovl.fmt.RIE.r1, ovl.fmt.RIE.r3, 16270 ovl.fmt.RIE.i2); goto ok; 16271 case 0xec00000000dbULL: s390_format_RIE_RRI0(s390_irgen_ALGHSIK, 16272 ovl.fmt.RIE.r1, ovl.fmt.RIE.r3, 16273 ovl.fmt.RIE.i2); goto ok; 16274 case 0xec00000000e4ULL: s390_format_RRS(s390_irgen_CGRB, ovl.fmt.RRS.r1, 16275 ovl.fmt.RRS.r2, ovl.fmt.RRS.b4, 16276 ovl.fmt.RRS.d4, ovl.fmt.RRS.m3); 16277 goto ok; 16278 case 0xec00000000e5ULL: s390_format_RRS(s390_irgen_CLGRB, ovl.fmt.RRS.r1, 16279 ovl.fmt.RRS.r2, ovl.fmt.RRS.b4, 16280 ovl.fmt.RRS.d4, ovl.fmt.RRS.m3); 16281 goto ok; 16282 case 0xec00000000f6ULL: s390_format_RRS(s390_irgen_CRB, ovl.fmt.RRS.r1, 16283 ovl.fmt.RRS.r2, ovl.fmt.RRS.b4, 16284 ovl.fmt.RRS.d4, ovl.fmt.RRS.m3); 16285 goto ok; 16286 case 0xec00000000f7ULL: s390_format_RRS(s390_irgen_CLRB, ovl.fmt.RRS.r1, 16287 ovl.fmt.RRS.r2, ovl.fmt.RRS.b4, 16288 ovl.fmt.RRS.d4, ovl.fmt.RRS.m3); 16289 goto ok; 16290 case 0xec00000000fcULL: s390_format_RIS_RURDI(s390_irgen_CGIB, 16291 ovl.fmt.RIS.r1, ovl.fmt.RIS.m3, 16292 ovl.fmt.RIS.b4, ovl.fmt.RIS.d4, 16293 ovl.fmt.RIS.i2); goto ok; 16294 case 0xec00000000fdULL: s390_format_RIS_RURDU(s390_irgen_CLGIB, 16295 ovl.fmt.RIS.r1, ovl.fmt.RIS.m3, 16296 ovl.fmt.RIS.b4, ovl.fmt.RIS.d4, 16297 ovl.fmt.RIS.i2); goto ok; 16298 case 0xec00000000feULL: s390_format_RIS_RURDI(s390_irgen_CIB, ovl.fmt.RIS.r1, 16299 ovl.fmt.RIS.m3, ovl.fmt.RIS.b4, 16300 ovl.fmt.RIS.d4, 16301 ovl.fmt.RIS.i2); goto ok; 16302 case 0xec00000000ffULL: s390_format_RIS_RURDU(s390_irgen_CLIB, 16303 ovl.fmt.RIS.r1, ovl.fmt.RIS.m3, 16304 ovl.fmt.RIS.b4, ovl.fmt.RIS.d4, 16305 ovl.fmt.RIS.i2); goto ok; 16306 case 0xed0000000004ULL: s390_format_RXE_FRRD(s390_irgen_LDEB, ovl.fmt.RXE.r1, 16307 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16308 ovl.fmt.RXE.d2); goto ok; 16309 case 0xed0000000005ULL: s390_format_RXE_FRRD(s390_irgen_LXDB, ovl.fmt.RXE.r1, 16310 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16311 ovl.fmt.RXE.d2); goto ok; 16312 case 0xed0000000006ULL: s390_format_RXE_FRRD(s390_irgen_LXEB, ovl.fmt.RXE.r1, 16313 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16314 ovl.fmt.RXE.d2); goto ok; 16315 case 0xed0000000007ULL: /* MXDB */ goto unimplemented; 16316 case 0xed0000000008ULL: /* KEB */ goto unimplemented; 16317 case 0xed0000000009ULL: s390_format_RXE_FRRD(s390_irgen_CEB, ovl.fmt.RXE.r1, 16318 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16319 ovl.fmt.RXE.d2); goto ok; 16320 case 0xed000000000aULL: s390_format_RXE_FRRD(s390_irgen_AEB, ovl.fmt.RXE.r1, 16321 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16322 ovl.fmt.RXE.d2); goto ok; 16323 case 0xed000000000bULL: s390_format_RXE_FRRD(s390_irgen_SEB, ovl.fmt.RXE.r1, 16324 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16325 ovl.fmt.RXE.d2); goto ok; 16326 case 0xed000000000cULL: /* MDEB */ goto unimplemented; 16327 case 0xed000000000dULL: s390_format_RXE_FRRD(s390_irgen_DEB, ovl.fmt.RXE.r1, 16328 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16329 ovl.fmt.RXE.d2); goto ok; 16330 case 0xed000000000eULL: s390_format_RXF_FRRDF(s390_irgen_MAEB, 16331 ovl.fmt.RXF.r3, ovl.fmt.RXF.x2, 16332 ovl.fmt.RXF.b2, ovl.fmt.RXF.d2, 16333 ovl.fmt.RXF.r1); goto ok; 16334 case 0xed000000000fULL: s390_format_RXF_FRRDF(s390_irgen_MSEB, 16335 ovl.fmt.RXF.r3, ovl.fmt.RXF.x2, 16336 ovl.fmt.RXF.b2, ovl.fmt.RXF.d2, 16337 ovl.fmt.RXF.r1); goto ok; 16338 case 0xed0000000010ULL: s390_format_RXE_FRRD(s390_irgen_TCEB, ovl.fmt.RXE.r1, 16339 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16340 ovl.fmt.RXE.d2); goto ok; 16341 case 0xed0000000011ULL: s390_format_RXE_FRRD(s390_irgen_TCDB, ovl.fmt.RXE.r1, 16342 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16343 ovl.fmt.RXE.d2); goto ok; 16344 case 0xed0000000012ULL: s390_format_RXE_FRRD(s390_irgen_TCXB, ovl.fmt.RXE.r1, 16345 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16346 ovl.fmt.RXE.d2); goto ok; 16347 case 0xed0000000014ULL: s390_format_RXE_FRRD(s390_irgen_SQEB, ovl.fmt.RXE.r1, 16348 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16349 ovl.fmt.RXE.d2); goto ok; 16350 case 0xed0000000015ULL: s390_format_RXE_FRRD(s390_irgen_SQDB, ovl.fmt.RXE.r1, 16351 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16352 ovl.fmt.RXE.d2); goto ok; 16353 case 0xed0000000017ULL: s390_format_RXE_FRRD(s390_irgen_MEEB, ovl.fmt.RXE.r1, 16354 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16355 ovl.fmt.RXE.d2); goto ok; 16356 case 0xed0000000018ULL: /* KDB */ goto unimplemented; 16357 case 0xed0000000019ULL: s390_format_RXE_FRRD(s390_irgen_CDB, ovl.fmt.RXE.r1, 16358 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16359 ovl.fmt.RXE.d2); goto ok; 16360 case 0xed000000001aULL: s390_format_RXE_FRRD(s390_irgen_ADB, ovl.fmt.RXE.r1, 16361 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16362 ovl.fmt.RXE.d2); goto ok; 16363 case 0xed000000001bULL: s390_format_RXE_FRRD(s390_irgen_SDB, ovl.fmt.RXE.r1, 16364 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16365 ovl.fmt.RXE.d2); goto ok; 16366 case 0xed000000001cULL: s390_format_RXE_FRRD(s390_irgen_MDB, ovl.fmt.RXE.r1, 16367 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16368 ovl.fmt.RXE.d2); goto ok; 16369 case 0xed000000001dULL: s390_format_RXE_FRRD(s390_irgen_DDB, ovl.fmt.RXE.r1, 16370 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16371 ovl.fmt.RXE.d2); goto ok; 16372 case 0xed000000001eULL: s390_format_RXF_FRRDF(s390_irgen_MADB, 16373 ovl.fmt.RXF.r3, ovl.fmt.RXF.x2, 16374 ovl.fmt.RXF.b2, ovl.fmt.RXF.d2, 16375 ovl.fmt.RXF.r1); goto ok; 16376 case 0xed000000001fULL: s390_format_RXF_FRRDF(s390_irgen_MSDB, 16377 ovl.fmt.RXF.r3, ovl.fmt.RXF.x2, 16378 ovl.fmt.RXF.b2, ovl.fmt.RXF.d2, 16379 ovl.fmt.RXF.r1); goto ok; 16380 case 0xed0000000024ULL: s390_format_RXE_FRRD(s390_irgen_LDE, 16381 ovl.fmt.RXE.r1, ovl.fmt.RXE.x2, 16382 ovl.fmt.RXE.b2, 16383 ovl.fmt.RXE.d2); goto ok; 16384 case 0xed0000000025ULL: /* LXD */ goto unimplemented; 16385 case 0xed0000000026ULL: /* LXE */ goto unimplemented; 16386 case 0xed000000002eULL: /* MAE */ goto unimplemented; 16387 case 0xed000000002fULL: /* MSE */ goto unimplemented; 16388 case 0xed0000000034ULL: /* SQE */ goto unimplemented; 16389 case 0xed0000000035ULL: /* SQD */ goto unimplemented; 16390 case 0xed0000000037ULL: /* MEE */ goto unimplemented; 16391 case 0xed0000000038ULL: /* MAYL */ goto unimplemented; 16392 case 0xed0000000039ULL: /* MYL */ goto unimplemented; 16393 case 0xed000000003aULL: /* MAY */ goto unimplemented; 16394 case 0xed000000003bULL: /* MY */ goto unimplemented; 16395 case 0xed000000003cULL: /* MAYH */ goto unimplemented; 16396 case 0xed000000003dULL: /* MYH */ goto unimplemented; 16397 case 0xed000000003eULL: /* MAD */ goto unimplemented; 16398 case 0xed000000003fULL: /* MSD */ goto unimplemented; 16399 case 0xed0000000040ULL: s390_format_RXF_FRRDF(s390_irgen_SLDT, 16400 ovl.fmt.RXF.r3, ovl.fmt.RXF.x2, 16401 ovl.fmt.RXF.b2, ovl.fmt.RXF.d2, 16402 ovl.fmt.RXF.r1); goto ok; 16403 case 0xed0000000041ULL: s390_format_RXF_FRRDF(s390_irgen_SRDT, 16404 ovl.fmt.RXF.r3, ovl.fmt.RXF.x2, 16405 ovl.fmt.RXF.b2, ovl.fmt.RXF.d2, 16406 ovl.fmt.RXF.r1); goto ok; 16407 case 0xed0000000048ULL: s390_format_RXF_FRRDF(s390_irgen_SLXT, 16408 ovl.fmt.RXF.r3, ovl.fmt.RXF.x2, 16409 ovl.fmt.RXF.b2, ovl.fmt.RXF.d2, 16410 ovl.fmt.RXF.r1); goto ok; 16411 case 0xed0000000049ULL: s390_format_RXF_FRRDF(s390_irgen_SRXT, 16412 ovl.fmt.RXF.r3, ovl.fmt.RXF.x2, 16413 ovl.fmt.RXF.b2, ovl.fmt.RXF.d2, 16414 ovl.fmt.RXF.r1); goto ok; 16415 case 0xed0000000050ULL: s390_format_RXE_FRRD(s390_irgen_TDCET, ovl.fmt.RXE.r1, 16416 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16417 ovl.fmt.RXE.d2); goto ok; 16418 case 0xed0000000051ULL: s390_format_RXE_FRRD(s390_irgen_TDGET, ovl.fmt.RXE.r1, 16419 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16420 ovl.fmt.RXE.d2); goto ok; 16421 case 0xed0000000054ULL: s390_format_RXE_FRRD(s390_irgen_TDCDT, ovl.fmt.RXE.r1, 16422 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16423 ovl.fmt.RXE.d2); goto ok; 16424 case 0xed0000000055ULL: s390_format_RXE_FRRD(s390_irgen_TDGDT, ovl.fmt.RXE.r1, 16425 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16426 ovl.fmt.RXE.d2); goto ok; 16427 case 0xed0000000058ULL: s390_format_RXE_FRRD(s390_irgen_TDCXT, ovl.fmt.RXE.r1, 16428 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16429 ovl.fmt.RXE.d2); goto ok; 16430 case 0xed0000000059ULL: s390_format_RXE_FRRD(s390_irgen_TDGXT, ovl.fmt.RXE.r1, 16431 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16432 ovl.fmt.RXE.d2); goto ok; 16433 case 0xed0000000064ULL: s390_format_RXY_FRRD(s390_irgen_LEY, ovl.fmt.RXY.r1, 16434 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 16435 ovl.fmt.RXY.dl2, 16436 ovl.fmt.RXY.dh2); goto ok; 16437 case 0xed0000000065ULL: s390_format_RXY_FRRD(s390_irgen_LDY, ovl.fmt.RXY.r1, 16438 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 16439 ovl.fmt.RXY.dl2, 16440 ovl.fmt.RXY.dh2); goto ok; 16441 case 0xed0000000066ULL: s390_format_RXY_FRRD(s390_irgen_STEY, ovl.fmt.RXY.r1, 16442 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 16443 ovl.fmt.RXY.dl2, 16444 ovl.fmt.RXY.dh2); goto ok; 16445 case 0xed0000000067ULL: s390_format_RXY_FRRD(s390_irgen_STDY, ovl.fmt.RXY.r1, 16446 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 16447 ovl.fmt.RXY.dl2, 16448 ovl.fmt.RXY.dh2); goto ok; 16449 case 0xed00000000a8ULL: /* CZDT */ goto unimplemented; 16450 case 0xed00000000a9ULL: /* CZXT */ goto unimplemented; 16451 case 0xed00000000aaULL: /* CDZT */ goto unimplemented; 16452 case 0xed00000000abULL: /* CXZT */ goto unimplemented; 16453 } 16454 16455 switch (((ovl.value >> 16) & 0xff0f00000000ULL) >> 32) { 16456 case 0xc000ULL: s390_format_RIL_RP(s390_irgen_LARL, ovl.fmt.RIL.r1, 16457 ovl.fmt.RIL.i2); goto ok; 16458 case 0xc001ULL: s390_format_RIL_RI(s390_irgen_LGFI, ovl.fmt.RIL.r1, 16459 ovl.fmt.RIL.i2); goto ok; 16460 case 0xc004ULL: s390_format_RIL(s390_irgen_BRCL, ovl.fmt.RIL.r1, 16461 ovl.fmt.RIL.i2); goto ok; 16462 case 0xc005ULL: s390_format_RIL_RP(s390_irgen_BRASL, ovl.fmt.RIL.r1, 16463 ovl.fmt.RIL.i2); goto ok; 16464 case 0xc006ULL: s390_format_RIL_RU(s390_irgen_XIHF, ovl.fmt.RIL.r1, 16465 ovl.fmt.RIL.i2); goto ok; 16466 case 0xc007ULL: s390_format_RIL_RU(s390_irgen_XILF, ovl.fmt.RIL.r1, 16467 ovl.fmt.RIL.i2); goto ok; 16468 case 0xc008ULL: s390_format_RIL_RU(s390_irgen_IIHF, ovl.fmt.RIL.r1, 16469 ovl.fmt.RIL.i2); goto ok; 16470 case 0xc009ULL: s390_format_RIL_RU(s390_irgen_IILF, ovl.fmt.RIL.r1, 16471 ovl.fmt.RIL.i2); goto ok; 16472 case 0xc00aULL: s390_format_RIL_RU(s390_irgen_NIHF, ovl.fmt.RIL.r1, 16473 ovl.fmt.RIL.i2); goto ok; 16474 case 0xc00bULL: s390_format_RIL_RU(s390_irgen_NILF, ovl.fmt.RIL.r1, 16475 ovl.fmt.RIL.i2); goto ok; 16476 case 0xc00cULL: s390_format_RIL_RU(s390_irgen_OIHF, ovl.fmt.RIL.r1, 16477 ovl.fmt.RIL.i2); goto ok; 16478 case 0xc00dULL: s390_format_RIL_RU(s390_irgen_OILF, ovl.fmt.RIL.r1, 16479 ovl.fmt.RIL.i2); goto ok; 16480 case 0xc00eULL: s390_format_RIL_RU(s390_irgen_LLIHF, ovl.fmt.RIL.r1, 16481 ovl.fmt.RIL.i2); goto ok; 16482 case 0xc00fULL: s390_format_RIL_RU(s390_irgen_LLILF, ovl.fmt.RIL.r1, 16483 ovl.fmt.RIL.i2); goto ok; 16484 case 0xc200ULL: s390_format_RIL_RI(s390_irgen_MSGFI, ovl.fmt.RIL.r1, 16485 ovl.fmt.RIL.i2); goto ok; 16486 case 0xc201ULL: s390_format_RIL_RI(s390_irgen_MSFI, ovl.fmt.RIL.r1, 16487 ovl.fmt.RIL.i2); goto ok; 16488 case 0xc204ULL: s390_format_RIL_RU(s390_irgen_SLGFI, ovl.fmt.RIL.r1, 16489 ovl.fmt.RIL.i2); goto ok; 16490 case 0xc205ULL: s390_format_RIL_RU(s390_irgen_SLFI, ovl.fmt.RIL.r1, 16491 ovl.fmt.RIL.i2); goto ok; 16492 case 0xc208ULL: s390_format_RIL_RI(s390_irgen_AGFI, ovl.fmt.RIL.r1, 16493 ovl.fmt.RIL.i2); goto ok; 16494 case 0xc209ULL: s390_format_RIL_RI(s390_irgen_AFI, ovl.fmt.RIL.r1, 16495 ovl.fmt.RIL.i2); goto ok; 16496 case 0xc20aULL: s390_format_RIL_RU(s390_irgen_ALGFI, ovl.fmt.RIL.r1, 16497 ovl.fmt.RIL.i2); goto ok; 16498 case 0xc20bULL: s390_format_RIL_RU(s390_irgen_ALFI, ovl.fmt.RIL.r1, 16499 ovl.fmt.RIL.i2); goto ok; 16500 case 0xc20cULL: s390_format_RIL_RI(s390_irgen_CGFI, ovl.fmt.RIL.r1, 16501 ovl.fmt.RIL.i2); goto ok; 16502 case 0xc20dULL: s390_format_RIL_RI(s390_irgen_CFI, ovl.fmt.RIL.r1, 16503 ovl.fmt.RIL.i2); goto ok; 16504 case 0xc20eULL: s390_format_RIL_RU(s390_irgen_CLGFI, ovl.fmt.RIL.r1, 16505 ovl.fmt.RIL.i2); goto ok; 16506 case 0xc20fULL: s390_format_RIL_RU(s390_irgen_CLFI, ovl.fmt.RIL.r1, 16507 ovl.fmt.RIL.i2); goto ok; 16508 case 0xc402ULL: s390_format_RIL_RP(s390_irgen_LLHRL, ovl.fmt.RIL.r1, 16509 ovl.fmt.RIL.i2); goto ok; 16510 case 0xc404ULL: s390_format_RIL_RP(s390_irgen_LGHRL, ovl.fmt.RIL.r1, 16511 ovl.fmt.RIL.i2); goto ok; 16512 case 0xc405ULL: s390_format_RIL_RP(s390_irgen_LHRL, ovl.fmt.RIL.r1, 16513 ovl.fmt.RIL.i2); goto ok; 16514 case 0xc406ULL: s390_format_RIL_RP(s390_irgen_LLGHRL, ovl.fmt.RIL.r1, 16515 ovl.fmt.RIL.i2); goto ok; 16516 case 0xc407ULL: s390_format_RIL_RP(s390_irgen_STHRL, ovl.fmt.RIL.r1, 16517 ovl.fmt.RIL.i2); goto ok; 16518 case 0xc408ULL: s390_format_RIL_RP(s390_irgen_LGRL, ovl.fmt.RIL.r1, 16519 ovl.fmt.RIL.i2); goto ok; 16520 case 0xc40bULL: s390_format_RIL_RP(s390_irgen_STGRL, ovl.fmt.RIL.r1, 16521 ovl.fmt.RIL.i2); goto ok; 16522 case 0xc40cULL: s390_format_RIL_RP(s390_irgen_LGFRL, ovl.fmt.RIL.r1, 16523 ovl.fmt.RIL.i2); goto ok; 16524 case 0xc40dULL: s390_format_RIL_RP(s390_irgen_LRL, ovl.fmt.RIL.r1, 16525 ovl.fmt.RIL.i2); goto ok; 16526 case 0xc40eULL: s390_format_RIL_RP(s390_irgen_LLGFRL, ovl.fmt.RIL.r1, 16527 ovl.fmt.RIL.i2); goto ok; 16528 case 0xc40fULL: s390_format_RIL_RP(s390_irgen_STRL, ovl.fmt.RIL.r1, 16529 ovl.fmt.RIL.i2); goto ok; 16530 case 0xc600ULL: s390_format_RIL_RP(s390_irgen_EXRL, ovl.fmt.RIL.r1, 16531 ovl.fmt.RIL.i2); goto ok; 16532 case 0xc602ULL: s390_format_RIL_UP(s390_irgen_PFDRL, ovl.fmt.RIL.r1, 16533 ovl.fmt.RIL.i2); goto ok; 16534 case 0xc604ULL: s390_format_RIL_RP(s390_irgen_CGHRL, ovl.fmt.RIL.r1, 16535 ovl.fmt.RIL.i2); goto ok; 16536 case 0xc605ULL: s390_format_RIL_RP(s390_irgen_CHRL, ovl.fmt.RIL.r1, 16537 ovl.fmt.RIL.i2); goto ok; 16538 case 0xc606ULL: s390_format_RIL_RP(s390_irgen_CLGHRL, ovl.fmt.RIL.r1, 16539 ovl.fmt.RIL.i2); goto ok; 16540 case 0xc607ULL: s390_format_RIL_RP(s390_irgen_CLHRL, ovl.fmt.RIL.r1, 16541 ovl.fmt.RIL.i2); goto ok; 16542 case 0xc608ULL: s390_format_RIL_RP(s390_irgen_CGRL, ovl.fmt.RIL.r1, 16543 ovl.fmt.RIL.i2); goto ok; 16544 case 0xc60aULL: s390_format_RIL_RP(s390_irgen_CLGRL, ovl.fmt.RIL.r1, 16545 ovl.fmt.RIL.i2); goto ok; 16546 case 0xc60cULL: s390_format_RIL_RP(s390_irgen_CGFRL, ovl.fmt.RIL.r1, 16547 ovl.fmt.RIL.i2); goto ok; 16548 case 0xc60dULL: s390_format_RIL_RP(s390_irgen_CRL, ovl.fmt.RIL.r1, 16549 ovl.fmt.RIL.i2); goto ok; 16550 case 0xc60eULL: s390_format_RIL_RP(s390_irgen_CLGFRL, ovl.fmt.RIL.r1, 16551 ovl.fmt.RIL.i2); goto ok; 16552 case 0xc60fULL: s390_format_RIL_RP(s390_irgen_CLRL, ovl.fmt.RIL.r1, 16553 ovl.fmt.RIL.i2); goto ok; 16554 case 0xc800ULL: /* MVCOS */ goto unimplemented; 16555 case 0xc801ULL: /* ECTG */ goto unimplemented; 16556 case 0xc802ULL: /* CSST */ goto unimplemented; 16557 case 0xc804ULL: /* LPD */ goto unimplemented; 16558 case 0xc805ULL: /* LPDG */ goto unimplemented; 16559 case 0xcc06ULL: s390_format_RIL_RP(s390_irgen_BRCTH, ovl.fmt.RIL.r1, 16560 ovl.fmt.RIL.i2); goto ok; 16561 case 0xcc08ULL: s390_format_RIL_RI(s390_irgen_AIH, ovl.fmt.RIL.r1, 16562 ovl.fmt.RIL.i2); goto ok; 16563 case 0xcc0aULL: s390_format_RIL_RI(s390_irgen_ALSIH, ovl.fmt.RIL.r1, 16564 ovl.fmt.RIL.i2); goto ok; 16565 case 0xcc0bULL: s390_format_RIL_RI(s390_irgen_ALSIHN, ovl.fmt.RIL.r1, 16566 ovl.fmt.RIL.i2); goto ok; 16567 case 0xcc0dULL: s390_format_RIL_RI(s390_irgen_CIH, ovl.fmt.RIL.r1, 16568 ovl.fmt.RIL.i2); goto ok; 16569 case 0xcc0fULL: s390_format_RIL_RU(s390_irgen_CLIH, ovl.fmt.RIL.r1, 16570 ovl.fmt.RIL.i2); goto ok; 16571 } 16572 16573 switch (((ovl.value >> 16) & 0xff0000000000ULL) >> 40) { 16574 case 0xc5ULL: /* BPRP */ goto unimplemented; 16575 case 0xc7ULL: /* BPP */ goto unimplemented; 16576 case 0xd0ULL: /* TRTR */ goto unimplemented; 16577 case 0xd1ULL: /* MVN */ goto unimplemented; 16578 case 0xd2ULL: s390_format_SS_L0RDRD(s390_irgen_MVC, ovl.fmt.SS.l, 16579 ovl.fmt.SS.b1, ovl.fmt.SS.d1, 16580 ovl.fmt.SS.b2, ovl.fmt.SS.d2); goto ok; 16581 case 0xd3ULL: /* MVZ */ goto unimplemented; 16582 case 0xd4ULL: s390_format_SS_L0RDRD(s390_irgen_NC, ovl.fmt.SS.l, 16583 ovl.fmt.SS.b1, ovl.fmt.SS.d1, 16584 ovl.fmt.SS.b2, ovl.fmt.SS.d2); goto ok; 16585 case 0xd5ULL: s390_format_SS_L0RDRD(s390_irgen_CLC, ovl.fmt.SS.l, 16586 ovl.fmt.SS.b1, ovl.fmt.SS.d1, 16587 ovl.fmt.SS.b2, ovl.fmt.SS.d2); goto ok; 16588 case 0xd6ULL: s390_format_SS_L0RDRD(s390_irgen_OC, ovl.fmt.SS.l, 16589 ovl.fmt.SS.b1, ovl.fmt.SS.d1, 16590 ovl.fmt.SS.b2, ovl.fmt.SS.d2); goto ok; 16591 case 0xd7ULL: 16592 if (ovl.fmt.SS.b1 == ovl.fmt.SS.b2 && ovl.fmt.SS.d1 == ovl.fmt.SS.d2) 16593 s390_irgen_XC_sameloc(ovl.fmt.SS.l, ovl.fmt.SS.b1, ovl.fmt.SS.d1); 16594 else 16595 s390_format_SS_L0RDRD(s390_irgen_XC, ovl.fmt.SS.l, 16596 ovl.fmt.SS.b1, ovl.fmt.SS.d1, 16597 ovl.fmt.SS.b2, ovl.fmt.SS.d2); 16598 goto ok; 16599 case 0xd9ULL: /* MVCK */ goto unimplemented; 16600 case 0xdaULL: /* MVCP */ goto unimplemented; 16601 case 0xdbULL: /* MVCS */ goto unimplemented; 16602 case 0xdcULL: s390_format_SS_L0RDRD(s390_irgen_TR, ovl.fmt.SS.l, 16603 ovl.fmt.SS.b1, ovl.fmt.SS.d1, 16604 ovl.fmt.SS.b2, ovl.fmt.SS.d2); goto ok; 16605 case 0xddULL: /* TRT */ goto unimplemented; 16606 case 0xdeULL: /* ED */ goto unimplemented; 16607 case 0xdfULL: /* EDMK */ goto unimplemented; 16608 case 0xe1ULL: /* PKU */ goto unimplemented; 16609 case 0xe2ULL: /* UNPKU */ goto unimplemented; 16610 case 0xe8ULL: s390_format_SS_L0RDRD(s390_irgen_MVCIN, ovl.fmt.SS.l, 16611 ovl.fmt.SS.b1, ovl.fmt.SS.d1, 16612 ovl.fmt.SS.b2, ovl.fmt.SS.d2); goto ok; 16613 case 0xe9ULL: /* PKA */ goto unimplemented; 16614 case 0xeaULL: /* UNPKA */ goto unimplemented; 16615 case 0xeeULL: /* PLO */ goto unimplemented; 16616 case 0xefULL: /* LMD */ goto unimplemented; 16617 case 0xf0ULL: /* SRP */ goto unimplemented; 16618 case 0xf1ULL: /* MVO */ goto unimplemented; 16619 case 0xf2ULL: /* PACK */ goto unimplemented; 16620 case 0xf3ULL: /* UNPK */ goto unimplemented; 16621 case 0xf8ULL: /* ZAP */ goto unimplemented; 16622 case 0xf9ULL: /* CP */ goto unimplemented; 16623 case 0xfaULL: /* AP */ goto unimplemented; 16624 case 0xfbULL: /* SP */ goto unimplemented; 16625 case 0xfcULL: /* MP */ goto unimplemented; 16626 case 0xfdULL: /* DP */ goto unimplemented; 16627 } 16628 16629 switch (((ovl.value >> 16) & 0xffff00000000ULL) >> 32) { 16630 case 0xe500ULL: /* LASP */ goto unimplemented; 16631 case 0xe501ULL: /* TPROT */ goto unimplemented; 16632 case 0xe502ULL: /* STRAG */ goto unimplemented; 16633 case 0xe50eULL: /* MVCSK */ goto unimplemented; 16634 case 0xe50fULL: /* MVCDK */ goto unimplemented; 16635 case 0xe544ULL: s390_format_SIL_RDI(s390_irgen_MVHHI, ovl.fmt.SIL.b1, 16636 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16637 goto ok; 16638 case 0xe548ULL: s390_format_SIL_RDI(s390_irgen_MVGHI, ovl.fmt.SIL.b1, 16639 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16640 goto ok; 16641 case 0xe54cULL: s390_format_SIL_RDI(s390_irgen_MVHI, ovl.fmt.SIL.b1, 16642 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16643 goto ok; 16644 case 0xe554ULL: s390_format_SIL_RDI(s390_irgen_CHHSI, ovl.fmt.SIL.b1, 16645 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16646 goto ok; 16647 case 0xe555ULL: s390_format_SIL_RDU(s390_irgen_CLHHSI, ovl.fmt.SIL.b1, 16648 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16649 goto ok; 16650 case 0xe558ULL: s390_format_SIL_RDI(s390_irgen_CGHSI, ovl.fmt.SIL.b1, 16651 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16652 goto ok; 16653 case 0xe559ULL: s390_format_SIL_RDU(s390_irgen_CLGHSI, ovl.fmt.SIL.b1, 16654 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16655 goto ok; 16656 case 0xe55cULL: s390_format_SIL_RDI(s390_irgen_CHSI, ovl.fmt.SIL.b1, 16657 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16658 goto ok; 16659 case 0xe55dULL: s390_format_SIL_RDU(s390_irgen_CLFHSI, ovl.fmt.SIL.b1, 16660 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16661 goto ok; 16662 case 0xe560ULL: /* TBEGIN */ goto unimplemented; 16663 case 0xe561ULL: /* TBEGINC */ goto unimplemented; 16664 } 16665 16666 return S390_DECODE_UNKNOWN_INSN; 16667 16668 ok: 16669 return S390_DECODE_OK; 16670 16671 unimplemented: 16672 return S390_DECODE_UNIMPLEMENTED_INSN; 16673 } 16674 16675 /* Handle "special" instructions. */ 16676 static s390_decode_t 16677 s390_decode_special_and_irgen(const UChar *bytes) 16678 { 16679 s390_decode_t status = S390_DECODE_OK; 16680 16681 /* Got a "Special" instruction preamble. Which one is it? */ 16682 if (bytes[0] == 0x18 && bytes[1] == 0x22 /* lr %r2, %r2 */) { 16683 s390_irgen_client_request(); 16684 } else if (bytes[0] == 0x18 && bytes[1] == 0x33 /* lr %r3, %r3 */) { 16685 s390_irgen_guest_NRADDR(); 16686 } else if (bytes[0] == 0x18 && bytes[1] == 0x44 /* lr %r4, %r4 */) { 16687 s390_irgen_call_noredir(); 16688 } else if (bytes[0] == 0x18 && bytes[1] == 0x55 /* lr %r5, %r5 */) { 16689 vex_inject_ir(irsb, Iend_BE); 16690 16691 /* Invalidate the current insn. The reason is that the IRop we're 16692 injecting here can change. In which case the translation has to 16693 be redone. For ease of handling, we simply invalidate all the 16694 time. */ 16695 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_CMSTART), 16696 mkU64(guest_IA_curr_instr))); 16697 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_CMLEN), 16698 mkU64(guest_IA_next_instr - guest_IA_curr_instr))); 16699 vassert(guest_IA_next_instr - guest_IA_curr_instr == 16700 S390_SPECIAL_OP_PREAMBLE_SIZE + S390_SPECIAL_OP_SIZE); 16701 16702 put_IA(mkaddr_expr(guest_IA_next_instr)); 16703 dis_res->whatNext = Dis_StopHere; 16704 dis_res->jk_StopHere = Ijk_InvalICache; 16705 } else { 16706 /* We don't know what it is. */ 16707 return S390_DECODE_UNKNOWN_SPECIAL_INSN; 16708 } 16709 16710 dis_res->len = S390_SPECIAL_OP_PREAMBLE_SIZE + S390_SPECIAL_OP_SIZE; 16711 16712 return status; 16713 } 16714 16715 16716 /* Function returns # bytes that were decoded or 0 in case of failure */ 16717 static UInt 16718 s390_decode_and_irgen(const UChar *bytes, UInt insn_length, DisResult *dres) 16719 { 16720 s390_decode_t status; 16721 16722 dis_res = dres; 16723 16724 /* Spot the 8-byte preamble: 18ff lr r15,r15 16725 1811 lr r1,r1 16726 1822 lr r2,r2 16727 1833 lr r3,r3 */ 16728 if (bytes[ 0] == 0x18 && bytes[ 1] == 0xff && bytes[ 2] == 0x18 && 16729 bytes[ 3] == 0x11 && bytes[ 4] == 0x18 && bytes[ 5] == 0x22 && 16730 bytes[ 6] == 0x18 && bytes[ 7] == 0x33) { 16731 16732 /* Handle special instruction that follows that preamble. */ 16733 if (0) vex_printf("special function handling...\n"); 16734 16735 insn_length = S390_SPECIAL_OP_PREAMBLE_SIZE + S390_SPECIAL_OP_SIZE; 16736 guest_IA_next_instr = guest_IA_curr_instr + insn_length; 16737 16738 status = 16739 s390_decode_special_and_irgen(bytes + S390_SPECIAL_OP_PREAMBLE_SIZE); 16740 } else { 16741 /* Handle normal instructions. */ 16742 switch (insn_length) { 16743 case 2: 16744 status = s390_decode_2byte_and_irgen(bytes); 16745 break; 16746 16747 case 4: 16748 status = s390_decode_4byte_and_irgen(bytes); 16749 break; 16750 16751 case 6: 16752 status = s390_decode_6byte_and_irgen(bytes); 16753 break; 16754 16755 default: 16756 status = S390_DECODE_ERROR; 16757 break; 16758 } 16759 } 16760 /* If next instruction is execute, stop here */ 16761 if (dis_res->whatNext == Dis_Continue && bytes[insn_length] == 0x44) { 16762 put_IA(mkaddr_expr(guest_IA_next_instr)); 16763 dis_res->whatNext = Dis_StopHere; 16764 dis_res->jk_StopHere = Ijk_Boring; 16765 } 16766 16767 if (status == S390_DECODE_OK) return insn_length; /* OK */ 16768 16769 /* Decoding failed somehow */ 16770 if (sigill_diag) { 16771 vex_printf("vex s390->IR: "); 16772 switch (status) { 16773 case S390_DECODE_UNKNOWN_INSN: 16774 vex_printf("unknown insn: "); 16775 break; 16776 16777 case S390_DECODE_UNIMPLEMENTED_INSN: 16778 vex_printf("unimplemented insn: "); 16779 break; 16780 16781 case S390_DECODE_UNKNOWN_SPECIAL_INSN: 16782 vex_printf("unimplemented special insn: "); 16783 break; 16784 16785 case S390_DECODE_ERROR: 16786 vex_printf("decoding error: "); 16787 break; 16788 16789 default: 16790 vpanic("s390_decode_and_irgen"); 16791 } 16792 16793 vex_printf("%02x%02x", bytes[0], bytes[1]); 16794 if (insn_length > 2) { 16795 vex_printf(" %02x%02x", bytes[2], bytes[3]); 16796 } 16797 if (insn_length > 4) { 16798 vex_printf(" %02x%02x", bytes[4], bytes[5]); 16799 } 16800 vex_printf("\n"); 16801 } 16802 16803 return 0; /* Failed */ 16804 } 16805 16806 16807 /* Disassemble a single instruction INSN into IR. */ 16808 static DisResult 16809 disInstr_S390_WRK(const UChar *insn) 16810 { 16811 UChar byte; 16812 UInt insn_length; 16813 DisResult dres; 16814 16815 /* ---------------------------------------------------- */ 16816 /* --- Compute instruction length -- */ 16817 /* ---------------------------------------------------- */ 16818 16819 /* Get the first byte of the insn. */ 16820 byte = insn[0]; 16821 16822 /* The leftmost two bits (0:1) encode the length of the insn in bytes. 16823 00 -> 2 bytes, 01 -> 4 bytes, 10 -> 4 bytes, 11 -> 6 bytes. */ 16824 insn_length = ((((byte >> 6) + 1) >> 1) + 1) << 1; 16825 16826 guest_IA_next_instr = guest_IA_curr_instr + insn_length; 16827 16828 /* ---------------------------------------------------- */ 16829 /* --- Initialise the DisResult data -- */ 16830 /* ---------------------------------------------------- */ 16831 dres.whatNext = Dis_Continue; 16832 dres.len = insn_length; 16833 dres.continueAt = 0; 16834 dres.jk_StopHere = Ijk_INVALID; 16835 dres.hint = Dis_HintNone; 16836 16837 /* fixs390: consider chasing of conditional jumps */ 16838 16839 /* Normal and special instruction handling starts here. */ 16840 if (s390_decode_and_irgen(insn, insn_length, &dres) == 0) { 16841 /* All decode failures end up here. The decoder has already issued an 16842 error message. 16843 Tell the dispatcher that this insn cannot be decoded, and so has 16844 not been executed, and (is currently) the next to be executed. 16845 The insn address in the guest state needs to be set to 16846 guest_IA_curr_instr, otherwise the complaint will report an 16847 incorrect address. */ 16848 put_IA(mkaddr_expr(guest_IA_curr_instr)); 16849 16850 dres.len = 0; 16851 dres.whatNext = Dis_StopHere; 16852 dres.jk_StopHere = Ijk_NoDecode; 16853 dres.continueAt = 0; 16854 } else { 16855 /* Decode success */ 16856 switch (dres.whatNext) { 16857 case Dis_Continue: 16858 put_IA(mkaddr_expr(guest_IA_next_instr)); 16859 break; 16860 case Dis_ResteerU: 16861 case Dis_ResteerC: 16862 put_IA(mkaddr_expr(dres.continueAt)); 16863 break; 16864 case Dis_StopHere: 16865 if (dres.jk_StopHere == Ijk_EmWarn || 16866 dres.jk_StopHere == Ijk_EmFail) { 16867 /* We assume here, that emulation warnings are not given for 16868 insns that transfer control. There is no good way to 16869 do that. */ 16870 put_IA(mkaddr_expr(guest_IA_next_instr)); 16871 } 16872 break; 16873 default: 16874 vpanic("disInstr_S390_WRK"); 16875 } 16876 } 16877 16878 return dres; 16879 } 16880 16881 16882 /*------------------------------------------------------------*/ 16883 /*--- Top-level fn ---*/ 16884 /*------------------------------------------------------------*/ 16885 16886 /* Disassemble a single instruction into IR. The instruction 16887 is located in host memory at &guest_code[delta]. */ 16888 16889 DisResult 16890 disInstr_S390(IRSB *irsb_IN, 16891 Bool (*resteerOkFn)(void *, Addr), 16892 Bool resteerCisOk, 16893 void *callback_opaque, 16894 const UChar *guest_code, 16895 Long delta, 16896 Addr guest_IP, 16897 VexArch guest_arch, 16898 const VexArchInfo *archinfo, 16899 const VexAbiInfo *abiinfo, 16900 VexEndness host_endness, 16901 Bool sigill_diag_IN) 16902 { 16903 vassert(guest_arch == VexArchS390X); 16904 16905 /* The instruction decoder requires a big-endian machine. */ 16906 vassert(host_endness == VexEndnessBE); 16907 16908 /* Set globals (see top of this file) */ 16909 guest_IA_curr_instr = guest_IP; 16910 irsb = irsb_IN; 16911 resteer_fn = resteerOkFn; 16912 resteer_data = callback_opaque; 16913 sigill_diag = sigill_diag_IN; 16914 16915 return disInstr_S390_WRK(guest_code + delta); 16916 } 16917 16918 /*---------------------------------------------------------------*/ 16919 /*--- end guest_s390_toIR.c ---*/ 16920 /*---------------------------------------------------------------*/ 16921