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-2015 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_BRCTG(UChar r1, UShort i2) 3835 { 3836 put_gpr_dw0(r1, binop(Iop_Sub64, get_gpr_dw0(r1), mkU64(1))); 3837 if_condition_goto(binop(Iop_CmpNE64, get_gpr_dw0(r1), mkU64(0)), 3838 guest_IA_curr_instr + ((ULong)(Long)(Short)i2 << 1)); 3839 3840 return "brctg"; 3841 } 3842 3843 static const HChar * 3844 s390_irgen_BRXH(UChar r1, UChar r3, UShort i2) 3845 { 3846 IRTemp value = newTemp(Ity_I32); 3847 3848 assign(value, get_gpr_w1(r3 | 1)); 3849 put_gpr_w1(r1, binop(Iop_Add32, get_gpr_w1(r1), get_gpr_w1(r3))); 3850 if_condition_goto(binop(Iop_CmpLT32S, mkexpr(value), get_gpr_w1(r1)), 3851 guest_IA_curr_instr + ((ULong)(Long)(Short)i2 << 1)); 3852 3853 return "brxh"; 3854 } 3855 3856 static const HChar * 3857 s390_irgen_BRXHG(UChar r1, UChar r3, UShort i2) 3858 { 3859 IRTemp value = newTemp(Ity_I64); 3860 3861 assign(value, get_gpr_dw0(r3 | 1)); 3862 put_gpr_dw0(r1, binop(Iop_Add64, get_gpr_dw0(r1), get_gpr_dw0(r3))); 3863 if_condition_goto(binop(Iop_CmpLT64S, mkexpr(value), get_gpr_dw0(r1)), 3864 guest_IA_curr_instr + ((ULong)(Long)(Short)i2 << 1)); 3865 3866 return "brxhg"; 3867 } 3868 3869 static const HChar * 3870 s390_irgen_BRXLE(UChar r1, UChar r3, UShort i2) 3871 { 3872 IRTemp value = newTemp(Ity_I32); 3873 3874 assign(value, get_gpr_w1(r3 | 1)); 3875 put_gpr_w1(r1, binop(Iop_Add32, get_gpr_w1(r1), get_gpr_w1(r3))); 3876 if_condition_goto(binop(Iop_CmpLE32S, get_gpr_w1(r1), mkexpr(value)), 3877 guest_IA_curr_instr + ((ULong)(Long)(Short)i2 << 1)); 3878 3879 return "brxle"; 3880 } 3881 3882 static const HChar * 3883 s390_irgen_BRXLG(UChar r1, UChar r3, UShort i2) 3884 { 3885 IRTemp value = newTemp(Ity_I64); 3886 3887 assign(value, get_gpr_dw0(r3 | 1)); 3888 put_gpr_dw0(r1, binop(Iop_Add64, get_gpr_dw0(r1), get_gpr_dw0(r3))); 3889 if_condition_goto(binop(Iop_CmpLE64S, get_gpr_dw0(r1), mkexpr(value)), 3890 guest_IA_curr_instr + ((ULong)(Long)(Short)i2 << 1)); 3891 3892 return "brxlg"; 3893 } 3894 3895 static const HChar * 3896 s390_irgen_CR(UChar r1, UChar r2) 3897 { 3898 IRTemp op1 = newTemp(Ity_I32); 3899 IRTemp op2 = newTemp(Ity_I32); 3900 3901 assign(op1, get_gpr_w1(r1)); 3902 assign(op2, get_gpr_w1(r2)); 3903 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 3904 3905 return "cr"; 3906 } 3907 3908 static const HChar * 3909 s390_irgen_CGR(UChar r1, UChar r2) 3910 { 3911 IRTemp op1 = newTemp(Ity_I64); 3912 IRTemp op2 = newTemp(Ity_I64); 3913 3914 assign(op1, get_gpr_dw0(r1)); 3915 assign(op2, get_gpr_dw0(r2)); 3916 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 3917 3918 return "cgr"; 3919 } 3920 3921 static const HChar * 3922 s390_irgen_CGFR(UChar r1, UChar r2) 3923 { 3924 IRTemp op1 = newTemp(Ity_I64); 3925 IRTemp op2 = newTemp(Ity_I64); 3926 3927 assign(op1, get_gpr_dw0(r1)); 3928 assign(op2, unop(Iop_32Sto64, get_gpr_w1(r2))); 3929 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 3930 3931 return "cgfr"; 3932 } 3933 3934 static const HChar * 3935 s390_irgen_C(UChar r1, IRTemp op2addr) 3936 { 3937 IRTemp op1 = newTemp(Ity_I32); 3938 IRTemp op2 = newTemp(Ity_I32); 3939 3940 assign(op1, get_gpr_w1(r1)); 3941 assign(op2, load(Ity_I32, mkexpr(op2addr))); 3942 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 3943 3944 return "c"; 3945 } 3946 3947 static const HChar * 3948 s390_irgen_CY(UChar r1, IRTemp op2addr) 3949 { 3950 IRTemp op1 = newTemp(Ity_I32); 3951 IRTemp op2 = newTemp(Ity_I32); 3952 3953 assign(op1, get_gpr_w1(r1)); 3954 assign(op2, load(Ity_I32, mkexpr(op2addr))); 3955 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 3956 3957 return "cy"; 3958 } 3959 3960 static const HChar * 3961 s390_irgen_CG(UChar r1, IRTemp op2addr) 3962 { 3963 IRTemp op1 = newTemp(Ity_I64); 3964 IRTemp op2 = newTemp(Ity_I64); 3965 3966 assign(op1, get_gpr_dw0(r1)); 3967 assign(op2, load(Ity_I64, mkexpr(op2addr))); 3968 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 3969 3970 return "cg"; 3971 } 3972 3973 static const HChar * 3974 s390_irgen_CGF(UChar r1, IRTemp op2addr) 3975 { 3976 IRTemp op1 = newTemp(Ity_I64); 3977 IRTemp op2 = newTemp(Ity_I64); 3978 3979 assign(op1, get_gpr_dw0(r1)); 3980 assign(op2, unop(Iop_32Sto64, load(Ity_I32, mkexpr(op2addr)))); 3981 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 3982 3983 return "cgf"; 3984 } 3985 3986 static const HChar * 3987 s390_irgen_CFI(UChar r1, UInt i2) 3988 { 3989 IRTemp op1 = newTemp(Ity_I32); 3990 Int op2; 3991 3992 assign(op1, get_gpr_w1(r1)); 3993 op2 = (Int)i2; 3994 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, mktemp(Ity_I32, 3995 mkU32((UInt)op2))); 3996 3997 return "cfi"; 3998 } 3999 4000 static const HChar * 4001 s390_irgen_CGFI(UChar r1, UInt i2) 4002 { 4003 IRTemp op1 = newTemp(Ity_I64); 4004 Long op2; 4005 4006 assign(op1, get_gpr_dw0(r1)); 4007 op2 = (Long)(Int)i2; 4008 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, mktemp(Ity_I64, 4009 mkU64((ULong)op2))); 4010 4011 return "cgfi"; 4012 } 4013 4014 static const HChar * 4015 s390_irgen_CRL(UChar r1, UInt i2) 4016 { 4017 IRTemp op1 = newTemp(Ity_I32); 4018 IRTemp op2 = newTemp(Ity_I32); 4019 4020 assign(op1, get_gpr_w1(r1)); 4021 assign(op2, load(Ity_I32, mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int) 4022 i2 << 1)))); 4023 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4024 4025 return "crl"; 4026 } 4027 4028 static const HChar * 4029 s390_irgen_CGRL(UChar r1, UInt i2) 4030 { 4031 IRTemp op1 = newTemp(Ity_I64); 4032 IRTemp op2 = newTemp(Ity_I64); 4033 4034 assign(op1, get_gpr_dw0(r1)); 4035 assign(op2, load(Ity_I64, mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int) 4036 i2 << 1)))); 4037 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4038 4039 return "cgrl"; 4040 } 4041 4042 static const HChar * 4043 s390_irgen_CGFRL(UChar r1, UInt i2) 4044 { 4045 IRTemp op1 = newTemp(Ity_I64); 4046 IRTemp op2 = newTemp(Ity_I64); 4047 4048 assign(op1, get_gpr_dw0(r1)); 4049 assign(op2, unop(Iop_32Sto64, load(Ity_I32, mkU64(guest_IA_curr_instr + 4050 ((ULong)(Long)(Int)i2 << 1))))); 4051 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4052 4053 return "cgfrl"; 4054 } 4055 4056 static const HChar * 4057 s390_irgen_CRB(UChar r1, UChar r2, UChar m3, IRTemp op4addr) 4058 { 4059 IRTemp op1 = newTemp(Ity_I32); 4060 IRTemp op2 = newTemp(Ity_I32); 4061 IRTemp cond = newTemp(Ity_I32); 4062 4063 if (m3 == 0) { 4064 } else { 4065 if (m3 == 14) { 4066 always_goto(mkexpr(op4addr)); 4067 } else { 4068 assign(op1, get_gpr_w1(r1)); 4069 assign(op2, get_gpr_w1(r2)); 4070 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_SIGNED_COMPARE, 4071 op1, op2)); 4072 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), 4073 mkU32(0)), mkexpr(op4addr)); 4074 } 4075 } 4076 4077 return "crb"; 4078 } 4079 4080 static const HChar * 4081 s390_irgen_CGRB(UChar r1, UChar r2, UChar m3, IRTemp op4addr) 4082 { 4083 IRTemp op1 = newTemp(Ity_I64); 4084 IRTemp op2 = newTemp(Ity_I64); 4085 IRTemp cond = newTemp(Ity_I32); 4086 4087 if (m3 == 0) { 4088 } else { 4089 if (m3 == 14) { 4090 always_goto(mkexpr(op4addr)); 4091 } else { 4092 assign(op1, get_gpr_dw0(r1)); 4093 assign(op2, get_gpr_dw0(r2)); 4094 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_SIGNED_COMPARE, 4095 op1, op2)); 4096 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), 4097 mkU32(0)), mkexpr(op4addr)); 4098 } 4099 } 4100 4101 return "cgrb"; 4102 } 4103 4104 static const HChar * 4105 s390_irgen_CRJ(UChar r1, UChar r2, UShort i4, UChar m3) 4106 { 4107 IRTemp op1 = newTemp(Ity_I32); 4108 IRTemp op2 = newTemp(Ity_I32); 4109 IRTemp cond = newTemp(Ity_I32); 4110 4111 if (m3 == 0) { 4112 } else { 4113 if (m3 == 14) { 4114 always_goto_and_chase( 4115 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4116 } else { 4117 assign(op1, get_gpr_w1(r1)); 4118 assign(op2, get_gpr_w1(r2)); 4119 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_SIGNED_COMPARE, 4120 op1, op2)); 4121 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4122 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4123 4124 } 4125 } 4126 4127 return "crj"; 4128 } 4129 4130 static const HChar * 4131 s390_irgen_CGRJ(UChar r1, UChar r2, UShort i4, UChar m3) 4132 { 4133 IRTemp op1 = newTemp(Ity_I64); 4134 IRTemp op2 = newTemp(Ity_I64); 4135 IRTemp cond = newTemp(Ity_I32); 4136 4137 if (m3 == 0) { 4138 } else { 4139 if (m3 == 14) { 4140 always_goto_and_chase( 4141 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4142 } else { 4143 assign(op1, get_gpr_dw0(r1)); 4144 assign(op2, get_gpr_dw0(r2)); 4145 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_SIGNED_COMPARE, 4146 op1, op2)); 4147 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4148 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4149 4150 } 4151 } 4152 4153 return "cgrj"; 4154 } 4155 4156 static const HChar * 4157 s390_irgen_CIB(UChar r1, UChar m3, UChar i2, IRTemp op4addr) 4158 { 4159 IRTemp op1 = newTemp(Ity_I32); 4160 Int op2; 4161 IRTemp cond = newTemp(Ity_I32); 4162 4163 if (m3 == 0) { 4164 } else { 4165 if (m3 == 14) { 4166 always_goto(mkexpr(op4addr)); 4167 } else { 4168 assign(op1, get_gpr_w1(r1)); 4169 op2 = (Int)(Char)i2; 4170 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_SIGNED_COMPARE, op1, 4171 mktemp(Ity_I32, mkU32((UInt)op2)))); 4172 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4173 mkexpr(op4addr)); 4174 } 4175 } 4176 4177 return "cib"; 4178 } 4179 4180 static const HChar * 4181 s390_irgen_CGIB(UChar r1, UChar m3, UChar i2, IRTemp op4addr) 4182 { 4183 IRTemp op1 = newTemp(Ity_I64); 4184 Long op2; 4185 IRTemp cond = newTemp(Ity_I32); 4186 4187 if (m3 == 0) { 4188 } else { 4189 if (m3 == 14) { 4190 always_goto(mkexpr(op4addr)); 4191 } else { 4192 assign(op1, get_gpr_dw0(r1)); 4193 op2 = (Long)(Char)i2; 4194 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_SIGNED_COMPARE, op1, 4195 mktemp(Ity_I64, mkU64((ULong)op2)))); 4196 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4197 mkexpr(op4addr)); 4198 } 4199 } 4200 4201 return "cgib"; 4202 } 4203 4204 static const HChar * 4205 s390_irgen_CIJ(UChar r1, UChar m3, UShort i4, UChar i2) 4206 { 4207 IRTemp op1 = newTemp(Ity_I32); 4208 Int op2; 4209 IRTemp cond = newTemp(Ity_I32); 4210 4211 if (m3 == 0) { 4212 } else { 4213 if (m3 == 14) { 4214 always_goto_and_chase(guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4215 } else { 4216 assign(op1, get_gpr_w1(r1)); 4217 op2 = (Int)(Char)i2; 4218 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_SIGNED_COMPARE, op1, 4219 mktemp(Ity_I32, mkU32((UInt)op2)))); 4220 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4221 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4222 4223 } 4224 } 4225 4226 return "cij"; 4227 } 4228 4229 static const HChar * 4230 s390_irgen_CGIJ(UChar r1, UChar m3, UShort i4, UChar i2) 4231 { 4232 IRTemp op1 = newTemp(Ity_I64); 4233 Long op2; 4234 IRTemp cond = newTemp(Ity_I32); 4235 4236 if (m3 == 0) { 4237 } else { 4238 if (m3 == 14) { 4239 always_goto_and_chase(guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4240 } else { 4241 assign(op1, get_gpr_dw0(r1)); 4242 op2 = (Long)(Char)i2; 4243 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_SIGNED_COMPARE, op1, 4244 mktemp(Ity_I64, mkU64((ULong)op2)))); 4245 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4246 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4247 4248 } 4249 } 4250 4251 return "cgij"; 4252 } 4253 4254 static const HChar * 4255 s390_irgen_CH(UChar r1, IRTemp op2addr) 4256 { 4257 IRTemp op1 = newTemp(Ity_I32); 4258 IRTemp op2 = newTemp(Ity_I32); 4259 4260 assign(op1, get_gpr_w1(r1)); 4261 assign(op2, unop(Iop_16Sto32, load(Ity_I16, mkexpr(op2addr)))); 4262 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4263 4264 return "ch"; 4265 } 4266 4267 static const HChar * 4268 s390_irgen_CHY(UChar r1, IRTemp op2addr) 4269 { 4270 IRTemp op1 = newTemp(Ity_I32); 4271 IRTemp op2 = newTemp(Ity_I32); 4272 4273 assign(op1, get_gpr_w1(r1)); 4274 assign(op2, unop(Iop_16Sto32, load(Ity_I16, mkexpr(op2addr)))); 4275 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4276 4277 return "chy"; 4278 } 4279 4280 static const HChar * 4281 s390_irgen_CGH(UChar r1, IRTemp op2addr) 4282 { 4283 IRTemp op1 = newTemp(Ity_I64); 4284 IRTemp op2 = newTemp(Ity_I64); 4285 4286 assign(op1, get_gpr_dw0(r1)); 4287 assign(op2, unop(Iop_16Sto64, load(Ity_I16, mkexpr(op2addr)))); 4288 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4289 4290 return "cgh"; 4291 } 4292 4293 static const HChar * 4294 s390_irgen_CHI(UChar r1, UShort i2) 4295 { 4296 IRTemp op1 = newTemp(Ity_I32); 4297 Int op2; 4298 4299 assign(op1, get_gpr_w1(r1)); 4300 op2 = (Int)(Short)i2; 4301 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, mktemp(Ity_I32, 4302 mkU32((UInt)op2))); 4303 4304 return "chi"; 4305 } 4306 4307 static const HChar * 4308 s390_irgen_CGHI(UChar r1, UShort i2) 4309 { 4310 IRTemp op1 = newTemp(Ity_I64); 4311 Long op2; 4312 4313 assign(op1, get_gpr_dw0(r1)); 4314 op2 = (Long)(Short)i2; 4315 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, mktemp(Ity_I64, 4316 mkU64((ULong)op2))); 4317 4318 return "cghi"; 4319 } 4320 4321 static const HChar * 4322 s390_irgen_CHHSI(UShort i2, IRTemp op1addr) 4323 { 4324 IRTemp op1 = newTemp(Ity_I16); 4325 Short op2; 4326 4327 assign(op1, load(Ity_I16, mkexpr(op1addr))); 4328 op2 = (Short)i2; 4329 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, mktemp(Ity_I16, 4330 mkU16((UShort)op2))); 4331 4332 return "chhsi"; 4333 } 4334 4335 static const HChar * 4336 s390_irgen_CHSI(UShort i2, IRTemp op1addr) 4337 { 4338 IRTemp op1 = newTemp(Ity_I32); 4339 Int op2; 4340 4341 assign(op1, load(Ity_I32, mkexpr(op1addr))); 4342 op2 = (Int)(Short)i2; 4343 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, mktemp(Ity_I32, 4344 mkU32((UInt)op2))); 4345 4346 return "chsi"; 4347 } 4348 4349 static const HChar * 4350 s390_irgen_CGHSI(UShort i2, IRTemp op1addr) 4351 { 4352 IRTemp op1 = newTemp(Ity_I64); 4353 Long op2; 4354 4355 assign(op1, load(Ity_I64, mkexpr(op1addr))); 4356 op2 = (Long)(Short)i2; 4357 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, mktemp(Ity_I64, 4358 mkU64((ULong)op2))); 4359 4360 return "cghsi"; 4361 } 4362 4363 static const HChar * 4364 s390_irgen_CHRL(UChar r1, UInt i2) 4365 { 4366 IRTemp op1 = newTemp(Ity_I32); 4367 IRTemp op2 = newTemp(Ity_I32); 4368 4369 assign(op1, get_gpr_w1(r1)); 4370 assign(op2, unop(Iop_16Sto32, load(Ity_I16, mkU64(guest_IA_curr_instr + 4371 ((ULong)(Long)(Int)i2 << 1))))); 4372 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4373 4374 return "chrl"; 4375 } 4376 4377 static const HChar * 4378 s390_irgen_CGHRL(UChar r1, UInt i2) 4379 { 4380 IRTemp op1 = newTemp(Ity_I64); 4381 IRTemp op2 = newTemp(Ity_I64); 4382 4383 assign(op1, get_gpr_dw0(r1)); 4384 assign(op2, unop(Iop_16Sto64, load(Ity_I16, mkU64(guest_IA_curr_instr + 4385 ((ULong)(Long)(Int)i2 << 1))))); 4386 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4387 4388 return "cghrl"; 4389 } 4390 4391 static const HChar * 4392 s390_irgen_CHHR(UChar r1, UChar r2) 4393 { 4394 IRTemp op1 = newTemp(Ity_I32); 4395 IRTemp op2 = newTemp(Ity_I32); 4396 4397 assign(op1, get_gpr_w0(r1)); 4398 assign(op2, get_gpr_w0(r2)); 4399 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4400 4401 return "chhr"; 4402 } 4403 4404 static const HChar * 4405 s390_irgen_CHLR(UChar r1, UChar r2) 4406 { 4407 IRTemp op1 = newTemp(Ity_I32); 4408 IRTemp op2 = newTemp(Ity_I32); 4409 4410 assign(op1, get_gpr_w0(r1)); 4411 assign(op2, get_gpr_w1(r2)); 4412 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4413 4414 return "chlr"; 4415 } 4416 4417 static const HChar * 4418 s390_irgen_CHF(UChar r1, IRTemp op2addr) 4419 { 4420 IRTemp op1 = newTemp(Ity_I32); 4421 IRTemp op2 = newTemp(Ity_I32); 4422 4423 assign(op1, get_gpr_w0(r1)); 4424 assign(op2, load(Ity_I32, mkexpr(op2addr))); 4425 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, op2); 4426 4427 return "chf"; 4428 } 4429 4430 static const HChar * 4431 s390_irgen_CIH(UChar r1, UInt i2) 4432 { 4433 IRTemp op1 = newTemp(Ity_I32); 4434 Int op2; 4435 4436 assign(op1, get_gpr_w0(r1)); 4437 op2 = (Int)i2; 4438 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_COMPARE, op1, mktemp(Ity_I32, 4439 mkU32((UInt)op2))); 4440 4441 return "cih"; 4442 } 4443 4444 static const HChar * 4445 s390_irgen_CLR(UChar r1, UChar r2) 4446 { 4447 IRTemp op1 = newTemp(Ity_I32); 4448 IRTemp op2 = newTemp(Ity_I32); 4449 4450 assign(op1, get_gpr_w1(r1)); 4451 assign(op2, get_gpr_w1(r2)); 4452 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4453 4454 return "clr"; 4455 } 4456 4457 static const HChar * 4458 s390_irgen_CLGR(UChar r1, UChar r2) 4459 { 4460 IRTemp op1 = newTemp(Ity_I64); 4461 IRTemp op2 = newTemp(Ity_I64); 4462 4463 assign(op1, get_gpr_dw0(r1)); 4464 assign(op2, get_gpr_dw0(r2)); 4465 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4466 4467 return "clgr"; 4468 } 4469 4470 static const HChar * 4471 s390_irgen_CLGFR(UChar r1, UChar r2) 4472 { 4473 IRTemp op1 = newTemp(Ity_I64); 4474 IRTemp op2 = newTemp(Ity_I64); 4475 4476 assign(op1, get_gpr_dw0(r1)); 4477 assign(op2, unop(Iop_32Uto64, get_gpr_w1(r2))); 4478 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4479 4480 return "clgfr"; 4481 } 4482 4483 static const HChar * 4484 s390_irgen_CL(UChar r1, IRTemp op2addr) 4485 { 4486 IRTemp op1 = newTemp(Ity_I32); 4487 IRTemp op2 = newTemp(Ity_I32); 4488 4489 assign(op1, get_gpr_w1(r1)); 4490 assign(op2, load(Ity_I32, mkexpr(op2addr))); 4491 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4492 4493 return "cl"; 4494 } 4495 4496 static const HChar * 4497 s390_irgen_CLY(UChar r1, IRTemp op2addr) 4498 { 4499 IRTemp op1 = newTemp(Ity_I32); 4500 IRTemp op2 = newTemp(Ity_I32); 4501 4502 assign(op1, get_gpr_w1(r1)); 4503 assign(op2, load(Ity_I32, mkexpr(op2addr))); 4504 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4505 4506 return "cly"; 4507 } 4508 4509 static const HChar * 4510 s390_irgen_CLG(UChar r1, IRTemp op2addr) 4511 { 4512 IRTemp op1 = newTemp(Ity_I64); 4513 IRTemp op2 = newTemp(Ity_I64); 4514 4515 assign(op1, get_gpr_dw0(r1)); 4516 assign(op2, load(Ity_I64, mkexpr(op2addr))); 4517 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4518 4519 return "clg"; 4520 } 4521 4522 static const HChar * 4523 s390_irgen_CLGF(UChar r1, IRTemp op2addr) 4524 { 4525 IRTemp op1 = newTemp(Ity_I64); 4526 IRTemp op2 = newTemp(Ity_I64); 4527 4528 assign(op1, get_gpr_dw0(r1)); 4529 assign(op2, unop(Iop_32Uto64, load(Ity_I32, mkexpr(op2addr)))); 4530 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4531 4532 return "clgf"; 4533 } 4534 4535 static const HChar * 4536 s390_irgen_CLFI(UChar r1, UInt i2) 4537 { 4538 IRTemp op1 = newTemp(Ity_I32); 4539 UInt op2; 4540 4541 assign(op1, get_gpr_w1(r1)); 4542 op2 = i2; 4543 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, mktemp(Ity_I32, 4544 mkU32(op2))); 4545 4546 return "clfi"; 4547 } 4548 4549 static const HChar * 4550 s390_irgen_CLGFI(UChar r1, UInt i2) 4551 { 4552 IRTemp op1 = newTemp(Ity_I64); 4553 ULong op2; 4554 4555 assign(op1, get_gpr_dw0(r1)); 4556 op2 = (ULong)i2; 4557 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, mktemp(Ity_I64, 4558 mkU64(op2))); 4559 4560 return "clgfi"; 4561 } 4562 4563 static const HChar * 4564 s390_irgen_CLI(UChar i2, IRTemp op1addr) 4565 { 4566 IRTemp op1 = newTemp(Ity_I8); 4567 UChar op2; 4568 4569 assign(op1, load(Ity_I8, mkexpr(op1addr))); 4570 op2 = i2; 4571 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, mktemp(Ity_I8, 4572 mkU8(op2))); 4573 4574 return "cli"; 4575 } 4576 4577 static const HChar * 4578 s390_irgen_CLIY(UChar i2, IRTemp op1addr) 4579 { 4580 IRTemp op1 = newTemp(Ity_I8); 4581 UChar op2; 4582 4583 assign(op1, load(Ity_I8, mkexpr(op1addr))); 4584 op2 = i2; 4585 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, mktemp(Ity_I8, 4586 mkU8(op2))); 4587 4588 return "cliy"; 4589 } 4590 4591 static const HChar * 4592 s390_irgen_CLFHSI(UShort i2, IRTemp op1addr) 4593 { 4594 IRTemp op1 = newTemp(Ity_I32); 4595 UInt op2; 4596 4597 assign(op1, load(Ity_I32, mkexpr(op1addr))); 4598 op2 = (UInt)i2; 4599 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, mktemp(Ity_I32, 4600 mkU32(op2))); 4601 4602 return "clfhsi"; 4603 } 4604 4605 static const HChar * 4606 s390_irgen_CLGHSI(UShort i2, IRTemp op1addr) 4607 { 4608 IRTemp op1 = newTemp(Ity_I64); 4609 ULong op2; 4610 4611 assign(op1, load(Ity_I64, mkexpr(op1addr))); 4612 op2 = (ULong)i2; 4613 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, mktemp(Ity_I64, 4614 mkU64(op2))); 4615 4616 return "clghsi"; 4617 } 4618 4619 static const HChar * 4620 s390_irgen_CLHHSI(UShort i2, IRTemp op1addr) 4621 { 4622 IRTemp op1 = newTemp(Ity_I16); 4623 UShort op2; 4624 4625 assign(op1, load(Ity_I16, mkexpr(op1addr))); 4626 op2 = i2; 4627 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, mktemp(Ity_I16, 4628 mkU16(op2))); 4629 4630 return "clhhsi"; 4631 } 4632 4633 static const HChar * 4634 s390_irgen_CLRL(UChar r1, UInt i2) 4635 { 4636 IRTemp op1 = newTemp(Ity_I32); 4637 IRTemp op2 = newTemp(Ity_I32); 4638 4639 assign(op1, get_gpr_w1(r1)); 4640 assign(op2, load(Ity_I32, mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int) 4641 i2 << 1)))); 4642 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4643 4644 return "clrl"; 4645 } 4646 4647 static const HChar * 4648 s390_irgen_CLGRL(UChar r1, UInt i2) 4649 { 4650 IRTemp op1 = newTemp(Ity_I64); 4651 IRTemp op2 = newTemp(Ity_I64); 4652 4653 assign(op1, get_gpr_dw0(r1)); 4654 assign(op2, load(Ity_I64, mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int) 4655 i2 << 1)))); 4656 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4657 4658 return "clgrl"; 4659 } 4660 4661 static const HChar * 4662 s390_irgen_CLGFRL(UChar r1, UInt i2) 4663 { 4664 IRTemp op1 = newTemp(Ity_I64); 4665 IRTemp op2 = newTemp(Ity_I64); 4666 4667 assign(op1, get_gpr_dw0(r1)); 4668 assign(op2, unop(Iop_32Uto64, load(Ity_I32, mkU64(guest_IA_curr_instr + 4669 ((ULong)(Long)(Int)i2 << 1))))); 4670 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4671 4672 return "clgfrl"; 4673 } 4674 4675 static const HChar * 4676 s390_irgen_CLHRL(UChar r1, UInt i2) 4677 { 4678 IRTemp op1 = newTemp(Ity_I32); 4679 IRTemp op2 = newTemp(Ity_I32); 4680 4681 assign(op1, get_gpr_w1(r1)); 4682 assign(op2, unop(Iop_16Uto32, load(Ity_I16, mkU64(guest_IA_curr_instr + 4683 ((ULong)(Long)(Int)i2 << 1))))); 4684 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4685 4686 return "clhrl"; 4687 } 4688 4689 static const HChar * 4690 s390_irgen_CLGHRL(UChar r1, UInt i2) 4691 { 4692 IRTemp op1 = newTemp(Ity_I64); 4693 IRTemp op2 = newTemp(Ity_I64); 4694 4695 assign(op1, get_gpr_dw0(r1)); 4696 assign(op2, unop(Iop_16Uto64, load(Ity_I16, mkU64(guest_IA_curr_instr + 4697 ((ULong)(Long)(Int)i2 << 1))))); 4698 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4699 4700 return "clghrl"; 4701 } 4702 4703 static const HChar * 4704 s390_irgen_CLRB(UChar r1, UChar r2, UChar m3, IRTemp op4addr) 4705 { 4706 IRTemp op1 = newTemp(Ity_I32); 4707 IRTemp op2 = newTemp(Ity_I32); 4708 IRTemp cond = newTemp(Ity_I32); 4709 4710 if (m3 == 0) { 4711 } else { 4712 if (m3 == 14) { 4713 always_goto(mkexpr(op4addr)); 4714 } else { 4715 assign(op1, get_gpr_w1(r1)); 4716 assign(op2, get_gpr_w1(r2)); 4717 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_UNSIGNED_COMPARE, 4718 op1, op2)); 4719 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4720 mkexpr(op4addr)); 4721 } 4722 } 4723 4724 return "clrb"; 4725 } 4726 4727 static const HChar * 4728 s390_irgen_CLGRB(UChar r1, UChar r2, UChar m3, IRTemp op4addr) 4729 { 4730 IRTemp op1 = newTemp(Ity_I64); 4731 IRTemp op2 = newTemp(Ity_I64); 4732 IRTemp cond = newTemp(Ity_I32); 4733 4734 if (m3 == 0) { 4735 } else { 4736 if (m3 == 14) { 4737 always_goto(mkexpr(op4addr)); 4738 } else { 4739 assign(op1, get_gpr_dw0(r1)); 4740 assign(op2, get_gpr_dw0(r2)); 4741 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_UNSIGNED_COMPARE, 4742 op1, op2)); 4743 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4744 mkexpr(op4addr)); 4745 } 4746 } 4747 4748 return "clgrb"; 4749 } 4750 4751 static const HChar * 4752 s390_irgen_CLRJ(UChar r1, UChar r2, UShort i4, UChar m3) 4753 { 4754 IRTemp op1 = newTemp(Ity_I32); 4755 IRTemp op2 = newTemp(Ity_I32); 4756 IRTemp cond = newTemp(Ity_I32); 4757 4758 if (m3 == 0) { 4759 } else { 4760 if (m3 == 14) { 4761 always_goto_and_chase(guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4762 } else { 4763 assign(op1, get_gpr_w1(r1)); 4764 assign(op2, get_gpr_w1(r2)); 4765 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_UNSIGNED_COMPARE, 4766 op1, op2)); 4767 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4768 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4769 4770 } 4771 } 4772 4773 return "clrj"; 4774 } 4775 4776 static const HChar * 4777 s390_irgen_CLGRJ(UChar r1, UChar r2, UShort i4, UChar m3) 4778 { 4779 IRTemp op1 = newTemp(Ity_I64); 4780 IRTemp op2 = newTemp(Ity_I64); 4781 IRTemp cond = newTemp(Ity_I32); 4782 4783 if (m3 == 0) { 4784 } else { 4785 if (m3 == 14) { 4786 always_goto_and_chase(guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4787 } else { 4788 assign(op1, get_gpr_dw0(r1)); 4789 assign(op2, get_gpr_dw0(r2)); 4790 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_UNSIGNED_COMPARE, 4791 op1, op2)); 4792 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4793 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4794 4795 } 4796 } 4797 4798 return "clgrj"; 4799 } 4800 4801 static const HChar * 4802 s390_irgen_CLIB(UChar r1, UChar m3, UChar i2, IRTemp op4addr) 4803 { 4804 IRTemp op1 = newTemp(Ity_I32); 4805 UInt op2; 4806 IRTemp cond = newTemp(Ity_I32); 4807 4808 if (m3 == 0) { 4809 } else { 4810 if (m3 == 14) { 4811 always_goto(mkexpr(op4addr)); 4812 } else { 4813 assign(op1, get_gpr_w1(r1)); 4814 op2 = (UInt)i2; 4815 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_UNSIGNED_COMPARE, op1, 4816 mktemp(Ity_I32, mkU32(op2)))); 4817 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4818 mkexpr(op4addr)); 4819 } 4820 } 4821 4822 return "clib"; 4823 } 4824 4825 static const HChar * 4826 s390_irgen_CLGIB(UChar r1, UChar m3, UChar i2, IRTemp op4addr) 4827 { 4828 IRTemp op1 = newTemp(Ity_I64); 4829 ULong op2; 4830 IRTemp cond = newTemp(Ity_I32); 4831 4832 if (m3 == 0) { 4833 } else { 4834 if (m3 == 14) { 4835 always_goto(mkexpr(op4addr)); 4836 } else { 4837 assign(op1, get_gpr_dw0(r1)); 4838 op2 = (ULong)i2; 4839 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_UNSIGNED_COMPARE, op1, 4840 mktemp(Ity_I64, mkU64(op2)))); 4841 if_condition_goto_computed(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4842 mkexpr(op4addr)); 4843 } 4844 } 4845 4846 return "clgib"; 4847 } 4848 4849 static const HChar * 4850 s390_irgen_CLIJ(UChar r1, UChar m3, UShort i4, UChar i2) 4851 { 4852 IRTemp op1 = newTemp(Ity_I32); 4853 UInt op2; 4854 IRTemp cond = newTemp(Ity_I32); 4855 4856 if (m3 == 0) { 4857 } else { 4858 if (m3 == 14) { 4859 always_goto_and_chase(guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4860 } else { 4861 assign(op1, get_gpr_w1(r1)); 4862 op2 = (UInt)i2; 4863 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_UNSIGNED_COMPARE, op1, 4864 mktemp(Ity_I32, mkU32(op2)))); 4865 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4866 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4867 4868 } 4869 } 4870 4871 return "clij"; 4872 } 4873 4874 static const HChar * 4875 s390_irgen_CLGIJ(UChar r1, UChar m3, UShort i4, UChar i2) 4876 { 4877 IRTemp op1 = newTemp(Ity_I64); 4878 ULong op2; 4879 IRTemp cond = newTemp(Ity_I32); 4880 4881 if (m3 == 0) { 4882 } else { 4883 if (m3 == 14) { 4884 always_goto_and_chase(guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4885 } else { 4886 assign(op1, get_gpr_dw0(r1)); 4887 op2 = (ULong)i2; 4888 assign(cond, s390_call_calculate_icc(m3, S390_CC_OP_UNSIGNED_COMPARE, op1, 4889 mktemp(Ity_I64, mkU64(op2)))); 4890 if_condition_goto(binop(Iop_CmpNE32, mkexpr(cond), mkU32(0)), 4891 guest_IA_curr_instr + ((ULong)(Long)(Short)i4 << 1)); 4892 4893 } 4894 } 4895 4896 return "clgij"; 4897 } 4898 4899 static const HChar * 4900 s390_irgen_CLM(UChar r1, UChar r3, IRTemp op2addr) 4901 { 4902 IRTemp op1 = newTemp(Ity_I32); 4903 IRTemp op2 = newTemp(Ity_I32); 4904 IRTemp b0 = newTemp(Ity_I32); 4905 IRTemp b1 = newTemp(Ity_I32); 4906 IRTemp b2 = newTemp(Ity_I32); 4907 IRTemp b3 = newTemp(Ity_I32); 4908 IRTemp c0 = newTemp(Ity_I32); 4909 IRTemp c1 = newTemp(Ity_I32); 4910 IRTemp c2 = newTemp(Ity_I32); 4911 IRTemp c3 = newTemp(Ity_I32); 4912 UChar n; 4913 4914 n = 0; 4915 if ((r3 & 8) != 0) { 4916 assign(b0, unop(Iop_8Uto32, get_gpr_b4(r1))); 4917 assign(c0, unop(Iop_8Uto32, load(Ity_I8, mkexpr(op2addr)))); 4918 n = n + 1; 4919 } else { 4920 assign(b0, mkU32(0)); 4921 assign(c0, mkU32(0)); 4922 } 4923 if ((r3 & 4) != 0) { 4924 assign(b1, unop(Iop_8Uto32, get_gpr_b5(r1))); 4925 assign(c1, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 4926 mkU64(n))))); 4927 n = n + 1; 4928 } else { 4929 assign(b1, mkU32(0)); 4930 assign(c1, mkU32(0)); 4931 } 4932 if ((r3 & 2) != 0) { 4933 assign(b2, unop(Iop_8Uto32, get_gpr_b6(r1))); 4934 assign(c2, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 4935 mkU64(n))))); 4936 n = n + 1; 4937 } else { 4938 assign(b2, mkU32(0)); 4939 assign(c2, mkU32(0)); 4940 } 4941 if ((r3 & 1) != 0) { 4942 assign(b3, unop(Iop_8Uto32, get_gpr_b7(r1))); 4943 assign(c3, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 4944 mkU64(n))))); 4945 n = n + 1; 4946 } else { 4947 assign(b3, mkU32(0)); 4948 assign(c3, mkU32(0)); 4949 } 4950 assign(op1, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Shl32, 4951 mkexpr(b0), mkU8(24)), binop(Iop_Shl32, mkexpr(b1), mkU8(16))), 4952 binop(Iop_Shl32, mkexpr(b2), mkU8(8))), mkexpr(b3))); 4953 assign(op2, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Shl32, 4954 mkexpr(c0), mkU8(24)), binop(Iop_Shl32, mkexpr(c1), mkU8(16))), 4955 binop(Iop_Shl32, mkexpr(c2), mkU8(8))), mkexpr(c3))); 4956 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 4957 4958 return "clm"; 4959 } 4960 4961 static const HChar * 4962 s390_irgen_CLMY(UChar r1, UChar r3, IRTemp op2addr) 4963 { 4964 IRTemp op1 = newTemp(Ity_I32); 4965 IRTemp op2 = newTemp(Ity_I32); 4966 IRTemp b0 = newTemp(Ity_I32); 4967 IRTemp b1 = newTemp(Ity_I32); 4968 IRTemp b2 = newTemp(Ity_I32); 4969 IRTemp b3 = newTemp(Ity_I32); 4970 IRTemp c0 = newTemp(Ity_I32); 4971 IRTemp c1 = newTemp(Ity_I32); 4972 IRTemp c2 = newTemp(Ity_I32); 4973 IRTemp c3 = newTemp(Ity_I32); 4974 UChar n; 4975 4976 n = 0; 4977 if ((r3 & 8) != 0) { 4978 assign(b0, unop(Iop_8Uto32, get_gpr_b4(r1))); 4979 assign(c0, unop(Iop_8Uto32, load(Ity_I8, mkexpr(op2addr)))); 4980 n = n + 1; 4981 } else { 4982 assign(b0, mkU32(0)); 4983 assign(c0, mkU32(0)); 4984 } 4985 if ((r3 & 4) != 0) { 4986 assign(b1, unop(Iop_8Uto32, get_gpr_b5(r1))); 4987 assign(c1, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 4988 mkU64(n))))); 4989 n = n + 1; 4990 } else { 4991 assign(b1, mkU32(0)); 4992 assign(c1, mkU32(0)); 4993 } 4994 if ((r3 & 2) != 0) { 4995 assign(b2, unop(Iop_8Uto32, get_gpr_b6(r1))); 4996 assign(c2, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 4997 mkU64(n))))); 4998 n = n + 1; 4999 } else { 5000 assign(b2, mkU32(0)); 5001 assign(c2, mkU32(0)); 5002 } 5003 if ((r3 & 1) != 0) { 5004 assign(b3, unop(Iop_8Uto32, get_gpr_b7(r1))); 5005 assign(c3, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 5006 mkU64(n))))); 5007 n = n + 1; 5008 } else { 5009 assign(b3, mkU32(0)); 5010 assign(c3, mkU32(0)); 5011 } 5012 assign(op1, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Shl32, 5013 mkexpr(b0), mkU8(24)), binop(Iop_Shl32, mkexpr(b1), mkU8(16))), 5014 binop(Iop_Shl32, mkexpr(b2), mkU8(8))), mkexpr(b3))); 5015 assign(op2, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Shl32, 5016 mkexpr(c0), mkU8(24)), binop(Iop_Shl32, mkexpr(c1), mkU8(16))), 5017 binop(Iop_Shl32, mkexpr(c2), mkU8(8))), mkexpr(c3))); 5018 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 5019 5020 return "clmy"; 5021 } 5022 5023 static const HChar * 5024 s390_irgen_CLMH(UChar r1, UChar r3, IRTemp op2addr) 5025 { 5026 IRTemp op1 = newTemp(Ity_I32); 5027 IRTemp op2 = newTemp(Ity_I32); 5028 IRTemp b0 = newTemp(Ity_I32); 5029 IRTemp b1 = newTemp(Ity_I32); 5030 IRTemp b2 = newTemp(Ity_I32); 5031 IRTemp b3 = newTemp(Ity_I32); 5032 IRTemp c0 = newTemp(Ity_I32); 5033 IRTemp c1 = newTemp(Ity_I32); 5034 IRTemp c2 = newTemp(Ity_I32); 5035 IRTemp c3 = newTemp(Ity_I32); 5036 UChar n; 5037 5038 n = 0; 5039 if ((r3 & 8) != 0) { 5040 assign(b0, unop(Iop_8Uto32, get_gpr_b0(r1))); 5041 assign(c0, unop(Iop_8Uto32, load(Ity_I8, mkexpr(op2addr)))); 5042 n = n + 1; 5043 } else { 5044 assign(b0, mkU32(0)); 5045 assign(c0, mkU32(0)); 5046 } 5047 if ((r3 & 4) != 0) { 5048 assign(b1, unop(Iop_8Uto32, get_gpr_b1(r1))); 5049 assign(c1, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 5050 mkU64(n))))); 5051 n = n + 1; 5052 } else { 5053 assign(b1, mkU32(0)); 5054 assign(c1, mkU32(0)); 5055 } 5056 if ((r3 & 2) != 0) { 5057 assign(b2, unop(Iop_8Uto32, get_gpr_b2(r1))); 5058 assign(c2, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 5059 mkU64(n))))); 5060 n = n + 1; 5061 } else { 5062 assign(b2, mkU32(0)); 5063 assign(c2, mkU32(0)); 5064 } 5065 if ((r3 & 1) != 0) { 5066 assign(b3, unop(Iop_8Uto32, get_gpr_b3(r1))); 5067 assign(c3, unop(Iop_8Uto32, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), 5068 mkU64(n))))); 5069 n = n + 1; 5070 } else { 5071 assign(b3, mkU32(0)); 5072 assign(c3, mkU32(0)); 5073 } 5074 assign(op1, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Shl32, 5075 mkexpr(b0), mkU8(24)), binop(Iop_Shl32, mkexpr(b1), mkU8(16))), 5076 binop(Iop_Shl32, mkexpr(b2), mkU8(8))), mkexpr(b3))); 5077 assign(op2, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Or32, binop(Iop_Shl32, 5078 mkexpr(c0), mkU8(24)), binop(Iop_Shl32, mkexpr(c1), mkU8(16))), 5079 binop(Iop_Shl32, mkexpr(c2), mkU8(8))), mkexpr(c3))); 5080 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 5081 5082 return "clmh"; 5083 } 5084 5085 static const HChar * 5086 s390_irgen_CLHHR(UChar r1, UChar r2) 5087 { 5088 IRTemp op1 = newTemp(Ity_I32); 5089 IRTemp op2 = newTemp(Ity_I32); 5090 5091 assign(op1, get_gpr_w0(r1)); 5092 assign(op2, get_gpr_w0(r2)); 5093 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 5094 5095 return "clhhr"; 5096 } 5097 5098 static const HChar * 5099 s390_irgen_CLHLR(UChar r1, UChar r2) 5100 { 5101 IRTemp op1 = newTemp(Ity_I32); 5102 IRTemp op2 = newTemp(Ity_I32); 5103 5104 assign(op1, get_gpr_w0(r1)); 5105 assign(op2, get_gpr_w1(r2)); 5106 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 5107 5108 return "clhlr"; 5109 } 5110 5111 static const HChar * 5112 s390_irgen_CLHF(UChar r1, IRTemp op2addr) 5113 { 5114 IRTemp op1 = newTemp(Ity_I32); 5115 IRTemp op2 = newTemp(Ity_I32); 5116 5117 assign(op1, get_gpr_w0(r1)); 5118 assign(op2, load(Ity_I32, mkexpr(op2addr))); 5119 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, op2); 5120 5121 return "clhf"; 5122 } 5123 5124 static const HChar * 5125 s390_irgen_CLIH(UChar r1, UInt i2) 5126 { 5127 IRTemp op1 = newTemp(Ity_I32); 5128 UInt op2; 5129 5130 assign(op1, get_gpr_w0(r1)); 5131 op2 = i2; 5132 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_COMPARE, op1, mktemp(Ity_I32, 5133 mkU32(op2))); 5134 5135 return "clih"; 5136 } 5137 5138 static const HChar * 5139 s390_irgen_CPYA(UChar r1, UChar r2) 5140 { 5141 put_ar_w0(r1, get_ar_w0(r2)); 5142 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 5143 s390_disasm(ENC3(MNM, AR, AR), "cpya", r1, r2); 5144 5145 return "cpya"; 5146 } 5147 5148 static const HChar * 5149 s390_irgen_XR(UChar r1, UChar r2) 5150 { 5151 IRTemp op1 = newTemp(Ity_I32); 5152 IRTemp op2 = newTemp(Ity_I32); 5153 IRTemp result = newTemp(Ity_I32); 5154 5155 if (r1 == r2) { 5156 assign(result, mkU32(0)); 5157 } else { 5158 assign(op1, get_gpr_w1(r1)); 5159 assign(op2, get_gpr_w1(r2)); 5160 assign(result, binop(Iop_Xor32, mkexpr(op1), mkexpr(op2))); 5161 } 5162 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5163 put_gpr_w1(r1, mkexpr(result)); 5164 5165 return "xr"; 5166 } 5167 5168 static const HChar * 5169 s390_irgen_XGR(UChar r1, UChar r2) 5170 { 5171 IRTemp op1 = newTemp(Ity_I64); 5172 IRTemp op2 = newTemp(Ity_I64); 5173 IRTemp result = newTemp(Ity_I64); 5174 5175 if (r1 == r2) { 5176 assign(result, mkU64(0)); 5177 } else { 5178 assign(op1, get_gpr_dw0(r1)); 5179 assign(op2, get_gpr_dw0(r2)); 5180 assign(result, binop(Iop_Xor64, mkexpr(op1), mkexpr(op2))); 5181 } 5182 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5183 put_gpr_dw0(r1, mkexpr(result)); 5184 5185 return "xgr"; 5186 } 5187 5188 static const HChar * 5189 s390_irgen_XRK(UChar r3, UChar r1, UChar r2) 5190 { 5191 IRTemp op2 = newTemp(Ity_I32); 5192 IRTemp op3 = newTemp(Ity_I32); 5193 IRTemp result = newTemp(Ity_I32); 5194 5195 assign(op2, get_gpr_w1(r2)); 5196 assign(op3, get_gpr_w1(r3)); 5197 assign(result, binop(Iop_Xor32, mkexpr(op2), mkexpr(op3))); 5198 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5199 put_gpr_w1(r1, mkexpr(result)); 5200 5201 return "xrk"; 5202 } 5203 5204 static const HChar * 5205 s390_irgen_XGRK(UChar r3, UChar r1, UChar r2) 5206 { 5207 IRTemp op2 = newTemp(Ity_I64); 5208 IRTemp op3 = newTemp(Ity_I64); 5209 IRTemp result = newTemp(Ity_I64); 5210 5211 assign(op2, get_gpr_dw0(r2)); 5212 assign(op3, get_gpr_dw0(r3)); 5213 assign(result, binop(Iop_Xor64, mkexpr(op2), mkexpr(op3))); 5214 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5215 put_gpr_dw0(r1, mkexpr(result)); 5216 5217 return "xgrk"; 5218 } 5219 5220 static const HChar * 5221 s390_irgen_X(UChar r1, IRTemp op2addr) 5222 { 5223 IRTemp op1 = newTemp(Ity_I32); 5224 IRTemp op2 = newTemp(Ity_I32); 5225 IRTemp result = newTemp(Ity_I32); 5226 5227 assign(op1, get_gpr_w1(r1)); 5228 assign(op2, load(Ity_I32, mkexpr(op2addr))); 5229 assign(result, binop(Iop_Xor32, mkexpr(op1), mkexpr(op2))); 5230 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5231 put_gpr_w1(r1, mkexpr(result)); 5232 5233 return "x"; 5234 } 5235 5236 static const HChar * 5237 s390_irgen_XY(UChar r1, IRTemp op2addr) 5238 { 5239 IRTemp op1 = newTemp(Ity_I32); 5240 IRTemp op2 = newTemp(Ity_I32); 5241 IRTemp result = newTemp(Ity_I32); 5242 5243 assign(op1, get_gpr_w1(r1)); 5244 assign(op2, load(Ity_I32, mkexpr(op2addr))); 5245 assign(result, binop(Iop_Xor32, mkexpr(op1), mkexpr(op2))); 5246 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5247 put_gpr_w1(r1, mkexpr(result)); 5248 5249 return "xy"; 5250 } 5251 5252 static const HChar * 5253 s390_irgen_XG(UChar r1, IRTemp op2addr) 5254 { 5255 IRTemp op1 = newTemp(Ity_I64); 5256 IRTemp op2 = newTemp(Ity_I64); 5257 IRTemp result = newTemp(Ity_I64); 5258 5259 assign(op1, get_gpr_dw0(r1)); 5260 assign(op2, load(Ity_I64, mkexpr(op2addr))); 5261 assign(result, binop(Iop_Xor64, mkexpr(op1), mkexpr(op2))); 5262 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5263 put_gpr_dw0(r1, mkexpr(result)); 5264 5265 return "xg"; 5266 } 5267 5268 static const HChar * 5269 s390_irgen_XI(UChar i2, IRTemp op1addr) 5270 { 5271 IRTemp op1 = newTemp(Ity_I8); 5272 UChar op2; 5273 IRTemp result = newTemp(Ity_I8); 5274 5275 assign(op1, load(Ity_I8, mkexpr(op1addr))); 5276 op2 = i2; 5277 assign(result, binop(Iop_Xor8, mkexpr(op1), mkU8(op2))); 5278 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5279 store(mkexpr(op1addr), mkexpr(result)); 5280 5281 return "xi"; 5282 } 5283 5284 static const HChar * 5285 s390_irgen_XIY(UChar i2, IRTemp op1addr) 5286 { 5287 IRTemp op1 = newTemp(Ity_I8); 5288 UChar op2; 5289 IRTemp result = newTemp(Ity_I8); 5290 5291 assign(op1, load(Ity_I8, mkexpr(op1addr))); 5292 op2 = i2; 5293 assign(result, binop(Iop_Xor8, mkexpr(op1), mkU8(op2))); 5294 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5295 store(mkexpr(op1addr), mkexpr(result)); 5296 5297 return "xiy"; 5298 } 5299 5300 static const HChar * 5301 s390_irgen_XIHF(UChar r1, UInt i2) 5302 { 5303 IRTemp op1 = newTemp(Ity_I32); 5304 UInt op2; 5305 IRTemp result = newTemp(Ity_I32); 5306 5307 assign(op1, get_gpr_w0(r1)); 5308 op2 = i2; 5309 assign(result, binop(Iop_Xor32, mkexpr(op1), mkU32(op2))); 5310 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5311 put_gpr_w0(r1, mkexpr(result)); 5312 5313 return "xihf"; 5314 } 5315 5316 static const HChar * 5317 s390_irgen_XILF(UChar r1, UInt i2) 5318 { 5319 IRTemp op1 = newTemp(Ity_I32); 5320 UInt op2; 5321 IRTemp result = newTemp(Ity_I32); 5322 5323 assign(op1, get_gpr_w1(r1)); 5324 op2 = i2; 5325 assign(result, binop(Iop_Xor32, mkexpr(op1), mkU32(op2))); 5326 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5327 put_gpr_w1(r1, mkexpr(result)); 5328 5329 return "xilf"; 5330 } 5331 5332 static const HChar * 5333 s390_irgen_EAR(UChar r1, UChar r2) 5334 { 5335 put_gpr_w1(r1, get_ar_w0(r2)); 5336 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 5337 s390_disasm(ENC3(MNM, GPR, AR), "ear", r1, r2); 5338 5339 return "ear"; 5340 } 5341 5342 static const HChar * 5343 s390_irgen_IC(UChar r1, IRTemp op2addr) 5344 { 5345 put_gpr_b7(r1, load(Ity_I8, mkexpr(op2addr))); 5346 5347 return "ic"; 5348 } 5349 5350 static const HChar * 5351 s390_irgen_ICY(UChar r1, IRTemp op2addr) 5352 { 5353 put_gpr_b7(r1, load(Ity_I8, mkexpr(op2addr))); 5354 5355 return "icy"; 5356 } 5357 5358 static const HChar * 5359 s390_irgen_ICM(UChar r1, UChar r3, IRTemp op2addr) 5360 { 5361 UChar n; 5362 IRTemp result = newTemp(Ity_I32); 5363 UInt mask; 5364 5365 n = 0; 5366 mask = (UInt)r3; 5367 if ((mask & 8) != 0) { 5368 put_gpr_b4(r1, load(Ity_I8, mkexpr(op2addr))); 5369 n = n + 1; 5370 } 5371 if ((mask & 4) != 0) { 5372 put_gpr_b5(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5373 5374 n = n + 1; 5375 } 5376 if ((mask & 2) != 0) { 5377 put_gpr_b6(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5378 5379 n = n + 1; 5380 } 5381 if ((mask & 1) != 0) { 5382 put_gpr_b7(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5383 5384 n = n + 1; 5385 } 5386 assign(result, get_gpr_w1(r1)); 5387 s390_cc_thunk_putZZ(S390_CC_OP_INSERT_CHAR_MASK_32, result, mktemp(Ity_I32, 5388 mkU32(mask))); 5389 5390 return "icm"; 5391 } 5392 5393 static const HChar * 5394 s390_irgen_ICMY(UChar r1, UChar r3, IRTemp op2addr) 5395 { 5396 UChar n; 5397 IRTemp result = newTemp(Ity_I32); 5398 UInt mask; 5399 5400 n = 0; 5401 mask = (UInt)r3; 5402 if ((mask & 8) != 0) { 5403 put_gpr_b4(r1, load(Ity_I8, mkexpr(op2addr))); 5404 n = n + 1; 5405 } 5406 if ((mask & 4) != 0) { 5407 put_gpr_b5(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5408 5409 n = n + 1; 5410 } 5411 if ((mask & 2) != 0) { 5412 put_gpr_b6(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5413 5414 n = n + 1; 5415 } 5416 if ((mask & 1) != 0) { 5417 put_gpr_b7(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5418 5419 n = n + 1; 5420 } 5421 assign(result, get_gpr_w1(r1)); 5422 s390_cc_thunk_putZZ(S390_CC_OP_INSERT_CHAR_MASK_32, result, mktemp(Ity_I32, 5423 mkU32(mask))); 5424 5425 return "icmy"; 5426 } 5427 5428 static const HChar * 5429 s390_irgen_ICMH(UChar r1, UChar r3, IRTemp op2addr) 5430 { 5431 UChar n; 5432 IRTemp result = newTemp(Ity_I32); 5433 UInt mask; 5434 5435 n = 0; 5436 mask = (UInt)r3; 5437 if ((mask & 8) != 0) { 5438 put_gpr_b0(r1, load(Ity_I8, mkexpr(op2addr))); 5439 n = n + 1; 5440 } 5441 if ((mask & 4) != 0) { 5442 put_gpr_b1(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5443 5444 n = n + 1; 5445 } 5446 if ((mask & 2) != 0) { 5447 put_gpr_b2(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5448 5449 n = n + 1; 5450 } 5451 if ((mask & 1) != 0) { 5452 put_gpr_b3(r1, load(Ity_I8, binop(Iop_Add64, mkexpr(op2addr), mkU64(n)))); 5453 5454 n = n + 1; 5455 } 5456 assign(result, get_gpr_w0(r1)); 5457 s390_cc_thunk_putZZ(S390_CC_OP_INSERT_CHAR_MASK_32, result, mktemp(Ity_I32, 5458 mkU32(mask))); 5459 5460 return "icmh"; 5461 } 5462 5463 static const HChar * 5464 s390_irgen_IIHF(UChar r1, UInt i2) 5465 { 5466 put_gpr_w0(r1, mkU32(i2)); 5467 5468 return "iihf"; 5469 } 5470 5471 static const HChar * 5472 s390_irgen_IIHH(UChar r1, UShort i2) 5473 { 5474 put_gpr_hw0(r1, mkU16(i2)); 5475 5476 return "iihh"; 5477 } 5478 5479 static const HChar * 5480 s390_irgen_IIHL(UChar r1, UShort i2) 5481 { 5482 put_gpr_hw1(r1, mkU16(i2)); 5483 5484 return "iihl"; 5485 } 5486 5487 static const HChar * 5488 s390_irgen_IILF(UChar r1, UInt i2) 5489 { 5490 put_gpr_w1(r1, mkU32(i2)); 5491 5492 return "iilf"; 5493 } 5494 5495 static const HChar * 5496 s390_irgen_IILH(UChar r1, UShort i2) 5497 { 5498 put_gpr_hw2(r1, mkU16(i2)); 5499 5500 return "iilh"; 5501 } 5502 5503 static const HChar * 5504 s390_irgen_IILL(UChar r1, UShort i2) 5505 { 5506 put_gpr_hw3(r1, mkU16(i2)); 5507 5508 return "iill"; 5509 } 5510 5511 static const HChar * 5512 s390_irgen_LR(UChar r1, UChar r2) 5513 { 5514 put_gpr_w1(r1, get_gpr_w1(r2)); 5515 5516 return "lr"; 5517 } 5518 5519 static const HChar * 5520 s390_irgen_LGR(UChar r1, UChar r2) 5521 { 5522 put_gpr_dw0(r1, get_gpr_dw0(r2)); 5523 5524 return "lgr"; 5525 } 5526 5527 static const HChar * 5528 s390_irgen_LGFR(UChar r1, UChar r2) 5529 { 5530 put_gpr_dw0(r1, unop(Iop_32Sto64, get_gpr_w1(r2))); 5531 5532 return "lgfr"; 5533 } 5534 5535 static const HChar * 5536 s390_irgen_L(UChar r1, IRTemp op2addr) 5537 { 5538 put_gpr_w1(r1, load(Ity_I32, mkexpr(op2addr))); 5539 5540 return "l"; 5541 } 5542 5543 static const HChar * 5544 s390_irgen_LY(UChar r1, IRTemp op2addr) 5545 { 5546 put_gpr_w1(r1, load(Ity_I32, mkexpr(op2addr))); 5547 5548 return "ly"; 5549 } 5550 5551 static const HChar * 5552 s390_irgen_LG(UChar r1, IRTemp op2addr) 5553 { 5554 put_gpr_dw0(r1, load(Ity_I64, mkexpr(op2addr))); 5555 5556 return "lg"; 5557 } 5558 5559 static const HChar * 5560 s390_irgen_LGF(UChar r1, IRTemp op2addr) 5561 { 5562 put_gpr_dw0(r1, unop(Iop_32Sto64, load(Ity_I32, mkexpr(op2addr)))); 5563 5564 return "lgf"; 5565 } 5566 5567 static const HChar * 5568 s390_irgen_LGFI(UChar r1, UInt i2) 5569 { 5570 put_gpr_dw0(r1, mkU64((ULong)(Long)(Int)i2)); 5571 5572 return "lgfi"; 5573 } 5574 5575 static const HChar * 5576 s390_irgen_LRL(UChar r1, UInt i2) 5577 { 5578 put_gpr_w1(r1, load(Ity_I32, mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int) 5579 i2 << 1)))); 5580 5581 return "lrl"; 5582 } 5583 5584 static const HChar * 5585 s390_irgen_LGRL(UChar r1, UInt i2) 5586 { 5587 put_gpr_dw0(r1, load(Ity_I64, mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int) 5588 i2 << 1)))); 5589 5590 return "lgrl"; 5591 } 5592 5593 static const HChar * 5594 s390_irgen_LGFRL(UChar r1, UInt i2) 5595 { 5596 put_gpr_dw0(r1, unop(Iop_32Sto64, load(Ity_I32, mkU64(guest_IA_curr_instr + 5597 ((ULong)(Long)(Int)i2 << 1))))); 5598 5599 return "lgfrl"; 5600 } 5601 5602 static const HChar * 5603 s390_irgen_LA(UChar r1, IRTemp op2addr) 5604 { 5605 put_gpr_dw0(r1, mkexpr(op2addr)); 5606 5607 return "la"; 5608 } 5609 5610 static const HChar * 5611 s390_irgen_LAY(UChar r1, IRTemp op2addr) 5612 { 5613 put_gpr_dw0(r1, mkexpr(op2addr)); 5614 5615 return "lay"; 5616 } 5617 5618 static const HChar * 5619 s390_irgen_LAE(UChar r1, IRTemp op2addr) 5620 { 5621 put_gpr_dw0(r1, mkexpr(op2addr)); 5622 5623 return "lae"; 5624 } 5625 5626 static const HChar * 5627 s390_irgen_LAEY(UChar r1, IRTemp op2addr) 5628 { 5629 put_gpr_dw0(r1, mkexpr(op2addr)); 5630 5631 return "laey"; 5632 } 5633 5634 static const HChar * 5635 s390_irgen_LARL(UChar r1, UInt i2) 5636 { 5637 put_gpr_dw0(r1, mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int)i2 << 1))); 5638 5639 return "larl"; 5640 } 5641 5642 /* The IR representation of LAA and friends is an approximation of what 5643 happens natively. Essentially a loop containing a compare-and-swap is 5644 constructed which will iterate until the CAS succeeds. As a consequence, 5645 instrumenters may see more memory accesses than happen natively. See also 5646 discussion here: https://bugs.kde.org/show_bug.cgi?id=306035 */ 5647 static void 5648 s390_irgen_load_and_add32(UChar r1, UChar r3, IRTemp op2addr, Bool is_signed) 5649 { 5650 IRCAS *cas; 5651 IRTemp old_mem = newTemp(Ity_I32); 5652 IRTemp op2 = newTemp(Ity_I32); 5653 IRTemp op3 = newTemp(Ity_I32); 5654 IRTemp result = newTemp(Ity_I32); 5655 5656 assign(op2, load(Ity_I32, mkexpr(op2addr))); 5657 assign(op3, get_gpr_w1(r3)); 5658 assign(result, binop(Iop_Add32, mkexpr(op2), mkexpr(op3))); 5659 5660 /* Place the addition of second operand and third operand at the 5661 second-operand location everytime */ 5662 cas = mkIRCAS(IRTemp_INVALID, old_mem, 5663 Iend_BE, mkexpr(op2addr), 5664 NULL, mkexpr(op2), /* expected value */ 5665 NULL, mkexpr(result) /* new value */); 5666 stmt(IRStmt_CAS(cas)); 5667 5668 /* Set CC according to 32-bit addition */ 5669 if (is_signed) { 5670 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_32, op2, op3); 5671 } else { 5672 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_32, op2, op3); 5673 } 5674 5675 /* If old_mem contains the expected value, then the CAS succeeded. 5676 Otherwise, it did not */ 5677 yield_if(binop(Iop_CmpNE32, mkexpr(old_mem), mkexpr(op2))); 5678 put_gpr_w1(r1, mkexpr(old_mem)); 5679 } 5680 5681 static void 5682 s390_irgen_load_and_add64(UChar r1, UChar r3, IRTemp op2addr, Bool is_signed) 5683 { 5684 IRCAS *cas; 5685 IRTemp old_mem = newTemp(Ity_I64); 5686 IRTemp op2 = newTemp(Ity_I64); 5687 IRTemp op3 = newTemp(Ity_I64); 5688 IRTemp result = newTemp(Ity_I64); 5689 5690 assign(op2, load(Ity_I64, mkexpr(op2addr))); 5691 assign(op3, get_gpr_dw0(r3)); 5692 assign(result, binop(Iop_Add64, mkexpr(op2), mkexpr(op3))); 5693 5694 /* Place the addition of second operand and third operand at the 5695 second-operand location everytime */ 5696 cas = mkIRCAS(IRTemp_INVALID, old_mem, 5697 Iend_BE, mkexpr(op2addr), 5698 NULL, mkexpr(op2), /* expected value */ 5699 NULL, mkexpr(result) /* new value */); 5700 stmt(IRStmt_CAS(cas)); 5701 5702 /* Set CC according to 64-bit addition */ 5703 if (is_signed) { 5704 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_ADD_64, op2, op3); 5705 } else { 5706 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_ADD_64, op2, op3); 5707 } 5708 5709 /* If old_mem contains the expected value, then the CAS succeeded. 5710 Otherwise, it did not */ 5711 yield_if(binop(Iop_CmpNE64, mkexpr(old_mem), mkexpr(op2))); 5712 put_gpr_dw0(r1, mkexpr(old_mem)); 5713 } 5714 5715 static void 5716 s390_irgen_load_and_bitwise32(UChar r1, UChar r3, IRTemp op2addr, IROp op) 5717 { 5718 IRCAS *cas; 5719 IRTemp old_mem = newTemp(Ity_I32); 5720 IRTemp op2 = newTemp(Ity_I32); 5721 IRTemp op3 = newTemp(Ity_I32); 5722 IRTemp result = newTemp(Ity_I32); 5723 5724 assign(op2, load(Ity_I32, mkexpr(op2addr))); 5725 assign(op3, get_gpr_w1(r3)); 5726 assign(result, binop(op, mkexpr(op2), mkexpr(op3))); 5727 5728 /* Place the addition of second operand and third operand at the 5729 second-operand location everytime */ 5730 cas = mkIRCAS(IRTemp_INVALID, old_mem, 5731 Iend_BE, mkexpr(op2addr), 5732 NULL, mkexpr(op2), /* expected value */ 5733 NULL, mkexpr(result) /* new value */); 5734 stmt(IRStmt_CAS(cas)); 5735 5736 /* Set CC according to bitwise operation */ 5737 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5738 5739 /* If old_mem contains the expected value, then the CAS succeeded. 5740 Otherwise, it did not */ 5741 yield_if(binop(Iop_CmpNE32, mkexpr(old_mem), mkexpr(op2))); 5742 put_gpr_w1(r1, mkexpr(old_mem)); 5743 } 5744 5745 static void 5746 s390_irgen_load_and_bitwise64(UChar r1, UChar r3, IRTemp op2addr, IROp op) 5747 { 5748 IRCAS *cas; 5749 IRTemp old_mem = newTemp(Ity_I64); 5750 IRTemp op2 = newTemp(Ity_I64); 5751 IRTemp op3 = newTemp(Ity_I64); 5752 IRTemp result = newTemp(Ity_I64); 5753 5754 assign(op2, load(Ity_I64, mkexpr(op2addr))); 5755 assign(op3, get_gpr_dw0(r3)); 5756 assign(result, binop(op, mkexpr(op2), mkexpr(op3))); 5757 5758 /* Place the addition of second operand and third operand at the 5759 second-operand location everytime */ 5760 cas = mkIRCAS(IRTemp_INVALID, old_mem, 5761 Iend_BE, mkexpr(op2addr), 5762 NULL, mkexpr(op2), /* expected value */ 5763 NULL, mkexpr(result) /* new value */); 5764 stmt(IRStmt_CAS(cas)); 5765 5766 /* Set CC according to bitwise operation */ 5767 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 5768 5769 /* If old_mem contains the expected value, then the CAS succeeded. 5770 Otherwise, it did not */ 5771 yield_if(binop(Iop_CmpNE64, mkexpr(old_mem), mkexpr(op2))); 5772 put_gpr_dw0(r1, mkexpr(old_mem)); 5773 } 5774 5775 static const HChar * 5776 s390_irgen_LAA(UChar r1, UChar r3, IRTemp op2addr) 5777 { 5778 s390_irgen_load_and_add32(r1, r3, op2addr, True /* is_signed */); 5779 5780 return "laa"; 5781 } 5782 5783 static const HChar * 5784 s390_irgen_LAAG(UChar r1, UChar r3, IRTemp op2addr) 5785 { 5786 s390_irgen_load_and_add64(r1, r3, op2addr, True /* is_signed */); 5787 5788 return "laag"; 5789 } 5790 5791 static const HChar * 5792 s390_irgen_LAAL(UChar r1, UChar r3, IRTemp op2addr) 5793 { 5794 s390_irgen_load_and_add32(r1, r3, op2addr, False /* is_signed */); 5795 5796 return "laal"; 5797 } 5798 5799 static const HChar * 5800 s390_irgen_LAALG(UChar r1, UChar r3, IRTemp op2addr) 5801 { 5802 s390_irgen_load_and_add64(r1, r3, op2addr, False /* is_signed */); 5803 5804 return "laalg"; 5805 } 5806 5807 static const HChar * 5808 s390_irgen_LAN(UChar r1, UChar r3, IRTemp op2addr) 5809 { 5810 s390_irgen_load_and_bitwise32(r1, r3, op2addr, Iop_And32); 5811 5812 return "lan"; 5813 } 5814 5815 static const HChar * 5816 s390_irgen_LANG(UChar r1, UChar r3, IRTemp op2addr) 5817 { 5818 s390_irgen_load_and_bitwise64(r1, r3, op2addr, Iop_And64); 5819 5820 return "lang"; 5821 } 5822 5823 static const HChar * 5824 s390_irgen_LAX(UChar r1, UChar r3, IRTemp op2addr) 5825 { 5826 s390_irgen_load_and_bitwise32(r1, r3, op2addr, Iop_Xor32); 5827 5828 return "lax"; 5829 } 5830 5831 static const HChar * 5832 s390_irgen_LAXG(UChar r1, UChar r3, IRTemp op2addr) 5833 { 5834 s390_irgen_load_and_bitwise64(r1, r3, op2addr, Iop_Xor64); 5835 5836 return "laxg"; 5837 } 5838 5839 static const HChar * 5840 s390_irgen_LAO(UChar r1, UChar r3, IRTemp op2addr) 5841 { 5842 s390_irgen_load_and_bitwise32(r1, r3, op2addr, Iop_Or32); 5843 5844 return "lao"; 5845 } 5846 5847 static const HChar * 5848 s390_irgen_LAOG(UChar r1, UChar r3, IRTemp op2addr) 5849 { 5850 s390_irgen_load_and_bitwise64(r1, r3, op2addr, Iop_Or64); 5851 5852 return "laog"; 5853 } 5854 5855 static const HChar * 5856 s390_irgen_LTR(UChar r1, UChar r2) 5857 { 5858 IRTemp op2 = newTemp(Ity_I32); 5859 5860 assign(op2, get_gpr_w1(r2)); 5861 put_gpr_w1(r1, mkexpr(op2)); 5862 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, op2); 5863 5864 return "ltr"; 5865 } 5866 5867 static const HChar * 5868 s390_irgen_LTGR(UChar r1, UChar r2) 5869 { 5870 IRTemp op2 = newTemp(Ity_I64); 5871 5872 assign(op2, get_gpr_dw0(r2)); 5873 put_gpr_dw0(r1, mkexpr(op2)); 5874 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, op2); 5875 5876 return "ltgr"; 5877 } 5878 5879 static const HChar * 5880 s390_irgen_LTGFR(UChar r1, UChar r2) 5881 { 5882 IRTemp op2 = newTemp(Ity_I64); 5883 5884 assign(op2, unop(Iop_32Sto64, get_gpr_w1(r2))); 5885 put_gpr_dw0(r1, mkexpr(op2)); 5886 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, op2); 5887 5888 return "ltgfr"; 5889 } 5890 5891 static const HChar * 5892 s390_irgen_LT(UChar r1, IRTemp op2addr) 5893 { 5894 IRTemp op2 = newTemp(Ity_I32); 5895 5896 assign(op2, load(Ity_I32, mkexpr(op2addr))); 5897 put_gpr_w1(r1, mkexpr(op2)); 5898 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, op2); 5899 5900 return "lt"; 5901 } 5902 5903 static const HChar * 5904 s390_irgen_LTG(UChar r1, IRTemp op2addr) 5905 { 5906 IRTemp op2 = newTemp(Ity_I64); 5907 5908 assign(op2, load(Ity_I64, mkexpr(op2addr))); 5909 put_gpr_dw0(r1, mkexpr(op2)); 5910 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, op2); 5911 5912 return "ltg"; 5913 } 5914 5915 static const HChar * 5916 s390_irgen_LTGF(UChar r1, IRTemp op2addr) 5917 { 5918 IRTemp op2 = newTemp(Ity_I64); 5919 5920 assign(op2, unop(Iop_32Sto64, load(Ity_I32, mkexpr(op2addr)))); 5921 put_gpr_dw0(r1, mkexpr(op2)); 5922 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, op2); 5923 5924 return "ltgf"; 5925 } 5926 5927 static const HChar * 5928 s390_irgen_LBR(UChar r1, UChar r2) 5929 { 5930 put_gpr_w1(r1, unop(Iop_8Sto32, get_gpr_b7(r2))); 5931 5932 return "lbr"; 5933 } 5934 5935 static const HChar * 5936 s390_irgen_LGBR(UChar r1, UChar r2) 5937 { 5938 put_gpr_dw0(r1, unop(Iop_8Sto64, get_gpr_b7(r2))); 5939 5940 return "lgbr"; 5941 } 5942 5943 static const HChar * 5944 s390_irgen_LB(UChar r1, IRTemp op2addr) 5945 { 5946 put_gpr_w1(r1, unop(Iop_8Sto32, load(Ity_I8, mkexpr(op2addr)))); 5947 5948 return "lb"; 5949 } 5950 5951 static const HChar * 5952 s390_irgen_LGB(UChar r1, IRTemp op2addr) 5953 { 5954 put_gpr_dw0(r1, unop(Iop_8Sto64, load(Ity_I8, mkexpr(op2addr)))); 5955 5956 return "lgb"; 5957 } 5958 5959 static const HChar * 5960 s390_irgen_LBH(UChar r1, IRTemp op2addr) 5961 { 5962 put_gpr_w0(r1, unop(Iop_8Sto32, load(Ity_I8, mkexpr(op2addr)))); 5963 5964 return "lbh"; 5965 } 5966 5967 static const HChar * 5968 s390_irgen_LCR(UChar r1, UChar r2) 5969 { 5970 Int op1; 5971 IRTemp op2 = newTemp(Ity_I32); 5972 IRTemp result = newTemp(Ity_I32); 5973 5974 op1 = 0; 5975 assign(op2, get_gpr_w1(r2)); 5976 assign(result, binop(Iop_Sub32, mkU32((UInt)op1), mkexpr(op2))); 5977 put_gpr_w1(r1, mkexpr(result)); 5978 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, mktemp(Ity_I32, mkU32((UInt) 5979 op1)), op2); 5980 5981 return "lcr"; 5982 } 5983 5984 static const HChar * 5985 s390_irgen_LCGR(UChar r1, UChar r2) 5986 { 5987 Long op1; 5988 IRTemp op2 = newTemp(Ity_I64); 5989 IRTemp result = newTemp(Ity_I64); 5990 5991 op1 = 0ULL; 5992 assign(op2, get_gpr_dw0(r2)); 5993 assign(result, binop(Iop_Sub64, mkU64((ULong)op1), mkexpr(op2))); 5994 put_gpr_dw0(r1, mkexpr(result)); 5995 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_64, mktemp(Ity_I64, mkU64((ULong) 5996 op1)), op2); 5997 5998 return "lcgr"; 5999 } 6000 6001 static const HChar * 6002 s390_irgen_LCGFR(UChar r1, UChar r2) 6003 { 6004 Long op1; 6005 IRTemp op2 = newTemp(Ity_I64); 6006 IRTemp result = newTemp(Ity_I64); 6007 6008 op1 = 0ULL; 6009 assign(op2, unop(Iop_32Sto64, get_gpr_w1(r2))); 6010 assign(result, binop(Iop_Sub64, mkU64((ULong)op1), mkexpr(op2))); 6011 put_gpr_dw0(r1, mkexpr(result)); 6012 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_64, mktemp(Ity_I64, mkU64((ULong) 6013 op1)), op2); 6014 6015 return "lcgfr"; 6016 } 6017 6018 static const HChar * 6019 s390_irgen_LHR(UChar r1, UChar r2) 6020 { 6021 put_gpr_w1(r1, unop(Iop_16Sto32, get_gpr_hw3(r2))); 6022 6023 return "lhr"; 6024 } 6025 6026 static const HChar * 6027 s390_irgen_LGHR(UChar r1, UChar r2) 6028 { 6029 put_gpr_dw0(r1, unop(Iop_16Sto64, get_gpr_hw3(r2))); 6030 6031 return "lghr"; 6032 } 6033 6034 static const HChar * 6035 s390_irgen_LH(UChar r1, IRTemp op2addr) 6036 { 6037 put_gpr_w1(r1, unop(Iop_16Sto32, load(Ity_I16, mkexpr(op2addr)))); 6038 6039 return "lh"; 6040 } 6041 6042 static const HChar * 6043 s390_irgen_LHY(UChar r1, IRTemp op2addr) 6044 { 6045 put_gpr_w1(r1, unop(Iop_16Sto32, load(Ity_I16, mkexpr(op2addr)))); 6046 6047 return "lhy"; 6048 } 6049 6050 static const HChar * 6051 s390_irgen_LGH(UChar r1, IRTemp op2addr) 6052 { 6053 put_gpr_dw0(r1, unop(Iop_16Sto64, load(Ity_I16, mkexpr(op2addr)))); 6054 6055 return "lgh"; 6056 } 6057 6058 static const HChar * 6059 s390_irgen_LHI(UChar r1, UShort i2) 6060 { 6061 put_gpr_w1(r1, mkU32((UInt)(Int)(Short)i2)); 6062 6063 return "lhi"; 6064 } 6065 6066 static const HChar * 6067 s390_irgen_LGHI(UChar r1, UShort i2) 6068 { 6069 put_gpr_dw0(r1, mkU64((ULong)(Long)(Short)i2)); 6070 6071 return "lghi"; 6072 } 6073 6074 static const HChar * 6075 s390_irgen_LHRL(UChar r1, UInt i2) 6076 { 6077 put_gpr_w1(r1, unop(Iop_16Sto32, load(Ity_I16, mkU64(guest_IA_curr_instr + 6078 ((ULong)(Long)(Int)i2 << 1))))); 6079 6080 return "lhrl"; 6081 } 6082 6083 static const HChar * 6084 s390_irgen_LGHRL(UChar r1, UInt i2) 6085 { 6086 put_gpr_dw0(r1, unop(Iop_16Sto64, load(Ity_I16, mkU64(guest_IA_curr_instr + 6087 ((ULong)(Long)(Int)i2 << 1))))); 6088 6089 return "lghrl"; 6090 } 6091 6092 static const HChar * 6093 s390_irgen_LHH(UChar r1, IRTemp op2addr) 6094 { 6095 put_gpr_w0(r1, unop(Iop_16Sto32, load(Ity_I16, mkexpr(op2addr)))); 6096 6097 return "lhh"; 6098 } 6099 6100 static const HChar * 6101 s390_irgen_LFH(UChar r1, IRTemp op2addr) 6102 { 6103 put_gpr_w0(r1, load(Ity_I32, mkexpr(op2addr))); 6104 6105 return "lfh"; 6106 } 6107 6108 static const HChar * 6109 s390_irgen_LLGFR(UChar r1, UChar r2) 6110 { 6111 put_gpr_dw0(r1, unop(Iop_32Uto64, get_gpr_w1(r2))); 6112 6113 return "llgfr"; 6114 } 6115 6116 static const HChar * 6117 s390_irgen_LLGF(UChar r1, IRTemp op2addr) 6118 { 6119 put_gpr_dw0(r1, unop(Iop_32Uto64, load(Ity_I32, mkexpr(op2addr)))); 6120 6121 return "llgf"; 6122 } 6123 6124 static const HChar * 6125 s390_irgen_LLGFRL(UChar r1, UInt i2) 6126 { 6127 put_gpr_dw0(r1, unop(Iop_32Uto64, load(Ity_I32, mkU64(guest_IA_curr_instr + 6128 ((ULong)(Long)(Int)i2 << 1))))); 6129 6130 return "llgfrl"; 6131 } 6132 6133 static const HChar * 6134 s390_irgen_LLCR(UChar r1, UChar r2) 6135 { 6136 put_gpr_w1(r1, unop(Iop_8Uto32, get_gpr_b7(r2))); 6137 6138 return "llcr"; 6139 } 6140 6141 static const HChar * 6142 s390_irgen_LLGCR(UChar r1, UChar r2) 6143 { 6144 put_gpr_dw0(r1, unop(Iop_8Uto64, get_gpr_b7(r2))); 6145 6146 return "llgcr"; 6147 } 6148 6149 static const HChar * 6150 s390_irgen_LLC(UChar r1, IRTemp op2addr) 6151 { 6152 put_gpr_w1(r1, unop(Iop_8Uto32, load(Ity_I8, mkexpr(op2addr)))); 6153 6154 return "llc"; 6155 } 6156 6157 static const HChar * 6158 s390_irgen_LLGC(UChar r1, IRTemp op2addr) 6159 { 6160 put_gpr_dw0(r1, unop(Iop_8Uto64, load(Ity_I8, mkexpr(op2addr)))); 6161 6162 return "llgc"; 6163 } 6164 6165 static const HChar * 6166 s390_irgen_LLCH(UChar r1, IRTemp op2addr) 6167 { 6168 put_gpr_w0(r1, unop(Iop_8Uto32, load(Ity_I8, mkexpr(op2addr)))); 6169 6170 return "llch"; 6171 } 6172 6173 static const HChar * 6174 s390_irgen_LLHR(UChar r1, UChar r2) 6175 { 6176 put_gpr_w1(r1, unop(Iop_16Uto32, get_gpr_hw3(r2))); 6177 6178 return "llhr"; 6179 } 6180 6181 static const HChar * 6182 s390_irgen_LLGHR(UChar r1, UChar r2) 6183 { 6184 put_gpr_dw0(r1, unop(Iop_16Uto64, get_gpr_hw3(r2))); 6185 6186 return "llghr"; 6187 } 6188 6189 static const HChar * 6190 s390_irgen_LLH(UChar r1, IRTemp op2addr) 6191 { 6192 put_gpr_w1(r1, unop(Iop_16Uto32, load(Ity_I16, mkexpr(op2addr)))); 6193 6194 return "llh"; 6195 } 6196 6197 static const HChar * 6198 s390_irgen_LLGH(UChar r1, IRTemp op2addr) 6199 { 6200 put_gpr_dw0(r1, unop(Iop_16Uto64, load(Ity_I16, mkexpr(op2addr)))); 6201 6202 return "llgh"; 6203 } 6204 6205 static const HChar * 6206 s390_irgen_LLHRL(UChar r1, UInt i2) 6207 { 6208 put_gpr_w1(r1, unop(Iop_16Uto32, load(Ity_I16, mkU64(guest_IA_curr_instr + 6209 ((ULong)(Long)(Int)i2 << 1))))); 6210 6211 return "llhrl"; 6212 } 6213 6214 static const HChar * 6215 s390_irgen_LLGHRL(UChar r1, UInt i2) 6216 { 6217 put_gpr_dw0(r1, unop(Iop_16Uto64, load(Ity_I16, mkU64(guest_IA_curr_instr + 6218 ((ULong)(Long)(Int)i2 << 1))))); 6219 6220 return "llghrl"; 6221 } 6222 6223 static const HChar * 6224 s390_irgen_LLHH(UChar r1, IRTemp op2addr) 6225 { 6226 put_gpr_w0(r1, unop(Iop_16Uto32, load(Ity_I16, mkexpr(op2addr)))); 6227 6228 return "llhh"; 6229 } 6230 6231 static const HChar * 6232 s390_irgen_LLIHF(UChar r1, UInt i2) 6233 { 6234 put_gpr_dw0(r1, mkU64(((ULong)i2) << 32)); 6235 6236 return "llihf"; 6237 } 6238 6239 static const HChar * 6240 s390_irgen_LLIHH(UChar r1, UShort i2) 6241 { 6242 put_gpr_dw0(r1, mkU64(((ULong)i2) << 48)); 6243 6244 return "llihh"; 6245 } 6246 6247 static const HChar * 6248 s390_irgen_LLIHL(UChar r1, UShort i2) 6249 { 6250 put_gpr_dw0(r1, mkU64(((ULong)i2) << 32)); 6251 6252 return "llihl"; 6253 } 6254 6255 static const HChar * 6256 s390_irgen_LLILF(UChar r1, UInt i2) 6257 { 6258 put_gpr_dw0(r1, mkU64(i2)); 6259 6260 return "llilf"; 6261 } 6262 6263 static const HChar * 6264 s390_irgen_LLILH(UChar r1, UShort i2) 6265 { 6266 put_gpr_dw0(r1, mkU64(((ULong)i2) << 16)); 6267 6268 return "llilh"; 6269 } 6270 6271 static const HChar * 6272 s390_irgen_LLILL(UChar r1, UShort i2) 6273 { 6274 put_gpr_dw0(r1, mkU64(i2)); 6275 6276 return "llill"; 6277 } 6278 6279 static const HChar * 6280 s390_irgen_LLGTR(UChar r1, UChar r2) 6281 { 6282 put_gpr_dw0(r1, unop(Iop_32Uto64, binop(Iop_And32, get_gpr_w1(r2), 6283 mkU32(2147483647)))); 6284 6285 return "llgtr"; 6286 } 6287 6288 static const HChar * 6289 s390_irgen_LLGT(UChar r1, IRTemp op2addr) 6290 { 6291 put_gpr_dw0(r1, unop(Iop_32Uto64, binop(Iop_And32, load(Ity_I32, 6292 mkexpr(op2addr)), mkU32(2147483647)))); 6293 6294 return "llgt"; 6295 } 6296 6297 static const HChar * 6298 s390_irgen_LNR(UChar r1, UChar r2) 6299 { 6300 IRTemp op2 = newTemp(Ity_I32); 6301 IRTemp result = newTemp(Ity_I32); 6302 6303 assign(op2, get_gpr_w1(r2)); 6304 assign(result, mkite(binop(Iop_CmpLE32S, mkexpr(op2), mkU32(0)), mkexpr(op2), 6305 binop(Iop_Sub32, mkU32(0), mkexpr(op2)))); 6306 put_gpr_w1(r1, mkexpr(result)); 6307 s390_cc_thunk_putS(S390_CC_OP_BITWISE, result); 6308 6309 return "lnr"; 6310 } 6311 6312 static const HChar * 6313 s390_irgen_LNGR(UChar r1, UChar r2) 6314 { 6315 IRTemp op2 = newTemp(Ity_I64); 6316 IRTemp result = newTemp(Ity_I64); 6317 6318 assign(op2, get_gpr_dw0(r2)); 6319 assign(result, mkite(binop(Iop_CmpLE64S, mkexpr(op2), mkU64(0)), mkexpr(op2), 6320 binop(Iop_Sub64, mkU64(0), mkexpr(op2)))); 6321 put_gpr_dw0(r1, mkexpr(result)); 6322 s390_cc_thunk_putS(S390_CC_OP_BITWISE, result); 6323 6324 return "lngr"; 6325 } 6326 6327 static const HChar * 6328 s390_irgen_LNGFR(UChar r1, UChar r2 __attribute__((unused))) 6329 { 6330 IRTemp op2 = newTemp(Ity_I64); 6331 IRTemp result = newTemp(Ity_I64); 6332 6333 assign(op2, unop(Iop_32Sto64, get_gpr_w1(r1))); 6334 assign(result, mkite(binop(Iop_CmpLE64S, mkexpr(op2), mkU64(0)), mkexpr(op2), 6335 binop(Iop_Sub64, mkU64(0), mkexpr(op2)))); 6336 put_gpr_dw0(r1, mkexpr(result)); 6337 s390_cc_thunk_putS(S390_CC_OP_BITWISE, result); 6338 6339 return "lngfr"; 6340 } 6341 6342 static const HChar * 6343 s390_irgen_LOCR(UChar m3, UChar r1, UChar r2) 6344 { 6345 next_insn_if(binop(Iop_CmpEQ32, s390_call_calculate_cond(m3), mkU32(0))); 6346 put_gpr_w1(r1, get_gpr_w1(r2)); 6347 6348 return "locr"; 6349 } 6350 6351 static const HChar * 6352 s390_irgen_LOCGR(UChar m3, UChar r1, UChar r2) 6353 { 6354 next_insn_if(binop(Iop_CmpEQ32, s390_call_calculate_cond(m3), mkU32(0))); 6355 put_gpr_dw0(r1, get_gpr_dw0(r2)); 6356 6357 return "locgr"; 6358 } 6359 6360 static const HChar * 6361 s390_irgen_LOC(UChar r1, IRTemp op2addr) 6362 { 6363 /* condition is checked in format handler */ 6364 put_gpr_w1(r1, load(Ity_I32, mkexpr(op2addr))); 6365 6366 return "loc"; 6367 } 6368 6369 static const HChar * 6370 s390_irgen_LOCG(UChar r1, IRTemp op2addr) 6371 { 6372 /* condition is checked in format handler */ 6373 put_gpr_dw0(r1, load(Ity_I64, mkexpr(op2addr))); 6374 6375 return "locg"; 6376 } 6377 6378 static const HChar * 6379 s390_irgen_LPQ(UChar r1, IRTemp op2addr) 6380 { 6381 put_gpr_dw0(r1, load(Ity_I64, mkexpr(op2addr))); 6382 put_gpr_dw0(r1 + 1, load(Ity_I64, binop(Iop_Add64, mkexpr(op2addr), mkU64(8)) 6383 )); 6384 6385 return "lpq"; 6386 } 6387 6388 static const HChar * 6389 s390_irgen_LPR(UChar r1, UChar r2) 6390 { 6391 IRTemp op2 = newTemp(Ity_I32); 6392 IRTemp result = newTemp(Ity_I32); 6393 6394 assign(op2, get_gpr_w1(r2)); 6395 assign(result, mkite(binop(Iop_CmpLT32S, mkexpr(op2), mkU32(0)), 6396 binop(Iop_Sub32, mkU32(0), mkexpr(op2)), mkexpr(op2))); 6397 put_gpr_w1(r1, mkexpr(result)); 6398 s390_cc_thunk_putS(S390_CC_OP_LOAD_POSITIVE_32, op2); 6399 6400 return "lpr"; 6401 } 6402 6403 static const HChar * 6404 s390_irgen_LPGR(UChar r1, UChar r2) 6405 { 6406 IRTemp op2 = newTemp(Ity_I64); 6407 IRTemp result = newTemp(Ity_I64); 6408 6409 assign(op2, get_gpr_dw0(r2)); 6410 assign(result, mkite(binop(Iop_CmpLT64S, mkexpr(op2), mkU64(0)), 6411 binop(Iop_Sub64, mkU64(0), mkexpr(op2)), mkexpr(op2))); 6412 put_gpr_dw0(r1, mkexpr(result)); 6413 s390_cc_thunk_putS(S390_CC_OP_LOAD_POSITIVE_64, op2); 6414 6415 return "lpgr"; 6416 } 6417 6418 static const HChar * 6419 s390_irgen_LPGFR(UChar r1, UChar r2) 6420 { 6421 IRTemp op2 = newTemp(Ity_I64); 6422 IRTemp result = newTemp(Ity_I64); 6423 6424 assign(op2, unop(Iop_32Sto64, get_gpr_w1(r2))); 6425 assign(result, mkite(binop(Iop_CmpLT64S, mkexpr(op2), mkU64(0)), 6426 binop(Iop_Sub64, mkU64(0), mkexpr(op2)), mkexpr(op2))); 6427 put_gpr_dw0(r1, mkexpr(result)); 6428 s390_cc_thunk_putS(S390_CC_OP_LOAD_POSITIVE_64, op2); 6429 6430 return "lpgfr"; 6431 } 6432 6433 static const HChar * 6434 s390_irgen_LRVR(UChar r1, UChar r2) 6435 { 6436 IRTemp b0 = newTemp(Ity_I8); 6437 IRTemp b1 = newTemp(Ity_I8); 6438 IRTemp b2 = newTemp(Ity_I8); 6439 IRTemp b3 = newTemp(Ity_I8); 6440 6441 assign(b3, get_gpr_b7(r2)); 6442 assign(b2, get_gpr_b6(r2)); 6443 assign(b1, get_gpr_b5(r2)); 6444 assign(b0, get_gpr_b4(r2)); 6445 put_gpr_b4(r1, mkexpr(b3)); 6446 put_gpr_b5(r1, mkexpr(b2)); 6447 put_gpr_b6(r1, mkexpr(b1)); 6448 put_gpr_b7(r1, mkexpr(b0)); 6449 6450 return "lrvr"; 6451 } 6452 6453 static const HChar * 6454 s390_irgen_LRVGR(UChar r1, UChar r2) 6455 { 6456 IRTemp b0 = newTemp(Ity_I8); 6457 IRTemp b1 = newTemp(Ity_I8); 6458 IRTemp b2 = newTemp(Ity_I8); 6459 IRTemp b3 = newTemp(Ity_I8); 6460 IRTemp b4 = newTemp(Ity_I8); 6461 IRTemp b5 = newTemp(Ity_I8); 6462 IRTemp b6 = newTemp(Ity_I8); 6463 IRTemp b7 = newTemp(Ity_I8); 6464 6465 assign(b7, get_gpr_b7(r2)); 6466 assign(b6, get_gpr_b6(r2)); 6467 assign(b5, get_gpr_b5(r2)); 6468 assign(b4, get_gpr_b4(r2)); 6469 assign(b3, get_gpr_b3(r2)); 6470 assign(b2, get_gpr_b2(r2)); 6471 assign(b1, get_gpr_b1(r2)); 6472 assign(b0, get_gpr_b0(r2)); 6473 put_gpr_b0(r1, mkexpr(b7)); 6474 put_gpr_b1(r1, mkexpr(b6)); 6475 put_gpr_b2(r1, mkexpr(b5)); 6476 put_gpr_b3(r1, mkexpr(b4)); 6477 put_gpr_b4(r1, mkexpr(b3)); 6478 put_gpr_b5(r1, mkexpr(b2)); 6479 put_gpr_b6(r1, mkexpr(b1)); 6480 put_gpr_b7(r1, mkexpr(b0)); 6481 6482 return "lrvgr"; 6483 } 6484 6485 static const HChar * 6486 s390_irgen_LRVH(UChar r1, IRTemp op2addr) 6487 { 6488 IRTemp op2 = newTemp(Ity_I16); 6489 6490 assign(op2, load(Ity_I16, mkexpr(op2addr))); 6491 put_gpr_b6(r1, unop(Iop_16to8, mkexpr(op2))); 6492 put_gpr_b7(r1, unop(Iop_16HIto8, mkexpr(op2))); 6493 6494 return "lrvh"; 6495 } 6496 6497 static const HChar * 6498 s390_irgen_LRV(UChar r1, IRTemp op2addr) 6499 { 6500 IRTemp op2 = newTemp(Ity_I32); 6501 6502 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6503 put_gpr_b4(r1, unop(Iop_32to8, binop(Iop_And32, mkexpr(op2), mkU32(255)))); 6504 put_gpr_b5(r1, unop(Iop_32to8, binop(Iop_And32, binop(Iop_Shr32, mkexpr(op2), 6505 mkU8(8)), mkU32(255)))); 6506 put_gpr_b6(r1, unop(Iop_32to8, binop(Iop_And32, binop(Iop_Shr32, mkexpr(op2), 6507 mkU8(16)), mkU32(255)))); 6508 put_gpr_b7(r1, unop(Iop_32to8, binop(Iop_And32, binop(Iop_Shr32, mkexpr(op2), 6509 mkU8(24)), mkU32(255)))); 6510 6511 return "lrv"; 6512 } 6513 6514 static const HChar * 6515 s390_irgen_LRVG(UChar r1, IRTemp op2addr) 6516 { 6517 IRTemp op2 = newTemp(Ity_I64); 6518 6519 assign(op2, load(Ity_I64, mkexpr(op2addr))); 6520 put_gpr_b0(r1, unop(Iop_64to8, binop(Iop_And64, mkexpr(op2), mkU64(255)))); 6521 put_gpr_b1(r1, unop(Iop_64to8, binop(Iop_And64, binop(Iop_Shr64, mkexpr(op2), 6522 mkU8(8)), mkU64(255)))); 6523 put_gpr_b2(r1, unop(Iop_64to8, binop(Iop_And64, binop(Iop_Shr64, mkexpr(op2), 6524 mkU8(16)), mkU64(255)))); 6525 put_gpr_b3(r1, unop(Iop_64to8, binop(Iop_And64, binop(Iop_Shr64, mkexpr(op2), 6526 mkU8(24)), mkU64(255)))); 6527 put_gpr_b4(r1, unop(Iop_64to8, binop(Iop_And64, binop(Iop_Shr64, mkexpr(op2), 6528 mkU8(32)), mkU64(255)))); 6529 put_gpr_b5(r1, unop(Iop_64to8, binop(Iop_And64, binop(Iop_Shr64, mkexpr(op2), 6530 mkU8(40)), mkU64(255)))); 6531 put_gpr_b6(r1, unop(Iop_64to8, binop(Iop_And64, binop(Iop_Shr64, mkexpr(op2), 6532 mkU8(48)), mkU64(255)))); 6533 put_gpr_b7(r1, unop(Iop_64to8, binop(Iop_And64, binop(Iop_Shr64, mkexpr(op2), 6534 mkU8(56)), mkU64(255)))); 6535 6536 return "lrvg"; 6537 } 6538 6539 static const HChar * 6540 s390_irgen_MVHHI(UShort i2, IRTemp op1addr) 6541 { 6542 store(mkexpr(op1addr), mkU16(i2)); 6543 6544 return "mvhhi"; 6545 } 6546 6547 static const HChar * 6548 s390_irgen_MVHI(UShort i2, IRTemp op1addr) 6549 { 6550 store(mkexpr(op1addr), mkU32((UInt)(Int)(Short)i2)); 6551 6552 return "mvhi"; 6553 } 6554 6555 static const HChar * 6556 s390_irgen_MVGHI(UShort i2, IRTemp op1addr) 6557 { 6558 store(mkexpr(op1addr), mkU64((ULong)(Long)(Short)i2)); 6559 6560 return "mvghi"; 6561 } 6562 6563 static const HChar * 6564 s390_irgen_MVI(UChar i2, IRTemp op1addr) 6565 { 6566 store(mkexpr(op1addr), mkU8(i2)); 6567 6568 return "mvi"; 6569 } 6570 6571 static const HChar * 6572 s390_irgen_MVIY(UChar i2, IRTemp op1addr) 6573 { 6574 store(mkexpr(op1addr), mkU8(i2)); 6575 6576 return "mviy"; 6577 } 6578 6579 static const HChar * 6580 s390_irgen_MR(UChar r1, UChar r2) 6581 { 6582 IRTemp op1 = newTemp(Ity_I32); 6583 IRTemp op2 = newTemp(Ity_I32); 6584 IRTemp result = newTemp(Ity_I64); 6585 6586 assign(op1, get_gpr_w1(r1 + 1)); 6587 assign(op2, get_gpr_w1(r2)); 6588 assign(result, binop(Iop_MullS32, mkexpr(op1), mkexpr(op2))); 6589 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 6590 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 6591 6592 return "mr"; 6593 } 6594 6595 static const HChar * 6596 s390_irgen_M(UChar r1, IRTemp op2addr) 6597 { 6598 IRTemp op1 = newTemp(Ity_I32); 6599 IRTemp op2 = newTemp(Ity_I32); 6600 IRTemp result = newTemp(Ity_I64); 6601 6602 assign(op1, get_gpr_w1(r1 + 1)); 6603 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6604 assign(result, binop(Iop_MullS32, mkexpr(op1), mkexpr(op2))); 6605 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 6606 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 6607 6608 return "m"; 6609 } 6610 6611 static const HChar * 6612 s390_irgen_MFY(UChar r1, IRTemp op2addr) 6613 { 6614 IRTemp op1 = newTemp(Ity_I32); 6615 IRTemp op2 = newTemp(Ity_I32); 6616 IRTemp result = newTemp(Ity_I64); 6617 6618 assign(op1, get_gpr_w1(r1 + 1)); 6619 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6620 assign(result, binop(Iop_MullS32, mkexpr(op1), mkexpr(op2))); 6621 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 6622 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 6623 6624 return "mfy"; 6625 } 6626 6627 static const HChar * 6628 s390_irgen_MH(UChar r1, IRTemp op2addr) 6629 { 6630 IRTemp op1 = newTemp(Ity_I32); 6631 IRTemp op2 = newTemp(Ity_I16); 6632 IRTemp result = newTemp(Ity_I64); 6633 6634 assign(op1, get_gpr_w1(r1)); 6635 assign(op2, load(Ity_I16, mkexpr(op2addr))); 6636 assign(result, binop(Iop_MullS32, mkexpr(op1), unop(Iop_16Sto32, mkexpr(op2)) 6637 )); 6638 put_gpr_w1(r1, unop(Iop_64to32, mkexpr(result))); 6639 6640 return "mh"; 6641 } 6642 6643 static const HChar * 6644 s390_irgen_MHY(UChar r1, IRTemp op2addr) 6645 { 6646 IRTemp op1 = newTemp(Ity_I32); 6647 IRTemp op2 = newTemp(Ity_I16); 6648 IRTemp result = newTemp(Ity_I64); 6649 6650 assign(op1, get_gpr_w1(r1)); 6651 assign(op2, load(Ity_I16, mkexpr(op2addr))); 6652 assign(result, binop(Iop_MullS32, mkexpr(op1), unop(Iop_16Sto32, mkexpr(op2)) 6653 )); 6654 put_gpr_w1(r1, unop(Iop_64to32, mkexpr(result))); 6655 6656 return "mhy"; 6657 } 6658 6659 static const HChar * 6660 s390_irgen_MHI(UChar r1, UShort i2) 6661 { 6662 IRTemp op1 = newTemp(Ity_I32); 6663 Short op2; 6664 IRTemp result = newTemp(Ity_I64); 6665 6666 assign(op1, get_gpr_w1(r1)); 6667 op2 = (Short)i2; 6668 assign(result, binop(Iop_MullS32, mkexpr(op1), unop(Iop_16Sto32, 6669 mkU16((UShort)op2)))); 6670 put_gpr_w1(r1, unop(Iop_64to32, mkexpr(result))); 6671 6672 return "mhi"; 6673 } 6674 6675 static const HChar * 6676 s390_irgen_MGHI(UChar r1, UShort i2) 6677 { 6678 IRTemp op1 = newTemp(Ity_I64); 6679 Short op2; 6680 IRTemp result = newTemp(Ity_I128); 6681 6682 assign(op1, get_gpr_dw0(r1)); 6683 op2 = (Short)i2; 6684 assign(result, binop(Iop_MullS64, mkexpr(op1), unop(Iop_16Sto64, 6685 mkU16((UShort)op2)))); 6686 put_gpr_dw0(r1, unop(Iop_128to64, mkexpr(result))); 6687 6688 return "mghi"; 6689 } 6690 6691 static const HChar * 6692 s390_irgen_MLR(UChar r1, UChar r2) 6693 { 6694 IRTemp op1 = newTemp(Ity_I32); 6695 IRTemp op2 = newTemp(Ity_I32); 6696 IRTemp result = newTemp(Ity_I64); 6697 6698 assign(op1, get_gpr_w1(r1 + 1)); 6699 assign(op2, get_gpr_w1(r2)); 6700 assign(result, binop(Iop_MullU32, mkexpr(op1), mkexpr(op2))); 6701 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 6702 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 6703 6704 return "mlr"; 6705 } 6706 6707 static const HChar * 6708 s390_irgen_MLGR(UChar r1, UChar r2) 6709 { 6710 IRTemp op1 = newTemp(Ity_I64); 6711 IRTemp op2 = newTemp(Ity_I64); 6712 IRTemp result = newTemp(Ity_I128); 6713 6714 assign(op1, get_gpr_dw0(r1 + 1)); 6715 assign(op2, get_gpr_dw0(r2)); 6716 assign(result, binop(Iop_MullU64, mkexpr(op1), mkexpr(op2))); 6717 put_gpr_dw0(r1, unop(Iop_128HIto64, mkexpr(result))); 6718 put_gpr_dw0(r1 + 1, unop(Iop_128to64, mkexpr(result))); 6719 6720 return "mlgr"; 6721 } 6722 6723 static const HChar * 6724 s390_irgen_ML(UChar r1, IRTemp op2addr) 6725 { 6726 IRTemp op1 = newTemp(Ity_I32); 6727 IRTemp op2 = newTemp(Ity_I32); 6728 IRTemp result = newTemp(Ity_I64); 6729 6730 assign(op1, get_gpr_w1(r1 + 1)); 6731 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6732 assign(result, binop(Iop_MullU32, mkexpr(op1), mkexpr(op2))); 6733 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 6734 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 6735 6736 return "ml"; 6737 } 6738 6739 static const HChar * 6740 s390_irgen_MLG(UChar r1, IRTemp op2addr) 6741 { 6742 IRTemp op1 = newTemp(Ity_I64); 6743 IRTemp op2 = newTemp(Ity_I64); 6744 IRTemp result = newTemp(Ity_I128); 6745 6746 assign(op1, get_gpr_dw0(r1 + 1)); 6747 assign(op2, load(Ity_I64, mkexpr(op2addr))); 6748 assign(result, binop(Iop_MullU64, mkexpr(op1), mkexpr(op2))); 6749 put_gpr_dw0(r1, unop(Iop_128HIto64, mkexpr(result))); 6750 put_gpr_dw0(r1 + 1, unop(Iop_128to64, mkexpr(result))); 6751 6752 return "mlg"; 6753 } 6754 6755 static const HChar * 6756 s390_irgen_MSR(UChar r1, UChar r2) 6757 { 6758 IRTemp op1 = newTemp(Ity_I32); 6759 IRTemp op2 = newTemp(Ity_I32); 6760 IRTemp result = newTemp(Ity_I64); 6761 6762 assign(op1, get_gpr_w1(r1)); 6763 assign(op2, get_gpr_w1(r2)); 6764 assign(result, binop(Iop_MullS32, mkexpr(op1), mkexpr(op2))); 6765 put_gpr_w1(r1, unop(Iop_64to32, mkexpr(result))); 6766 6767 return "msr"; 6768 } 6769 6770 static const HChar * 6771 s390_irgen_MSGR(UChar r1, UChar r2) 6772 { 6773 IRTemp op1 = newTemp(Ity_I64); 6774 IRTemp op2 = newTemp(Ity_I64); 6775 IRTemp result = newTemp(Ity_I128); 6776 6777 assign(op1, get_gpr_dw0(r1)); 6778 assign(op2, get_gpr_dw0(r2)); 6779 assign(result, binop(Iop_MullS64, mkexpr(op1), mkexpr(op2))); 6780 put_gpr_dw0(r1, unop(Iop_128to64, mkexpr(result))); 6781 6782 return "msgr"; 6783 } 6784 6785 static const HChar * 6786 s390_irgen_MSGFR(UChar r1, UChar r2) 6787 { 6788 IRTemp op1 = newTemp(Ity_I64); 6789 IRTemp op2 = newTemp(Ity_I32); 6790 IRTemp result = newTemp(Ity_I128); 6791 6792 assign(op1, get_gpr_dw0(r1)); 6793 assign(op2, get_gpr_w1(r2)); 6794 assign(result, binop(Iop_MullS64, mkexpr(op1), unop(Iop_32Sto64, mkexpr(op2)) 6795 )); 6796 put_gpr_dw0(r1, unop(Iop_128to64, mkexpr(result))); 6797 6798 return "msgfr"; 6799 } 6800 6801 static const HChar * 6802 s390_irgen_MS(UChar r1, IRTemp op2addr) 6803 { 6804 IRTemp op1 = newTemp(Ity_I32); 6805 IRTemp op2 = newTemp(Ity_I32); 6806 IRTemp result = newTemp(Ity_I64); 6807 6808 assign(op1, get_gpr_w1(r1)); 6809 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6810 assign(result, binop(Iop_MullS32, mkexpr(op1), mkexpr(op2))); 6811 put_gpr_w1(r1, unop(Iop_64to32, mkexpr(result))); 6812 6813 return "ms"; 6814 } 6815 6816 static const HChar * 6817 s390_irgen_MSY(UChar r1, IRTemp op2addr) 6818 { 6819 IRTemp op1 = newTemp(Ity_I32); 6820 IRTemp op2 = newTemp(Ity_I32); 6821 IRTemp result = newTemp(Ity_I64); 6822 6823 assign(op1, get_gpr_w1(r1)); 6824 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6825 assign(result, binop(Iop_MullS32, mkexpr(op1), mkexpr(op2))); 6826 put_gpr_w1(r1, unop(Iop_64to32, mkexpr(result))); 6827 6828 return "msy"; 6829 } 6830 6831 static const HChar * 6832 s390_irgen_MSG(UChar r1, IRTemp op2addr) 6833 { 6834 IRTemp op1 = newTemp(Ity_I64); 6835 IRTemp op2 = newTemp(Ity_I64); 6836 IRTemp result = newTemp(Ity_I128); 6837 6838 assign(op1, get_gpr_dw0(r1)); 6839 assign(op2, load(Ity_I64, mkexpr(op2addr))); 6840 assign(result, binop(Iop_MullS64, mkexpr(op1), mkexpr(op2))); 6841 put_gpr_dw0(r1, unop(Iop_128to64, mkexpr(result))); 6842 6843 return "msg"; 6844 } 6845 6846 static const HChar * 6847 s390_irgen_MSGF(UChar r1, IRTemp op2addr) 6848 { 6849 IRTemp op1 = newTemp(Ity_I64); 6850 IRTemp op2 = newTemp(Ity_I32); 6851 IRTemp result = newTemp(Ity_I128); 6852 6853 assign(op1, get_gpr_dw0(r1)); 6854 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6855 assign(result, binop(Iop_MullS64, mkexpr(op1), unop(Iop_32Sto64, mkexpr(op2)) 6856 )); 6857 put_gpr_dw0(r1, unop(Iop_128to64, mkexpr(result))); 6858 6859 return "msgf"; 6860 } 6861 6862 static const HChar * 6863 s390_irgen_MSFI(UChar r1, UInt i2) 6864 { 6865 IRTemp op1 = newTemp(Ity_I32); 6866 Int op2; 6867 IRTemp result = newTemp(Ity_I64); 6868 6869 assign(op1, get_gpr_w1(r1)); 6870 op2 = (Int)i2; 6871 assign(result, binop(Iop_MullS32, mkexpr(op1), mkU32((UInt)op2))); 6872 put_gpr_w1(r1, unop(Iop_64to32, mkexpr(result))); 6873 6874 return "msfi"; 6875 } 6876 6877 static const HChar * 6878 s390_irgen_MSGFI(UChar r1, UInt i2) 6879 { 6880 IRTemp op1 = newTemp(Ity_I64); 6881 Int op2; 6882 IRTemp result = newTemp(Ity_I128); 6883 6884 assign(op1, get_gpr_dw0(r1)); 6885 op2 = (Int)i2; 6886 assign(result, binop(Iop_MullS64, mkexpr(op1), unop(Iop_32Sto64, mkU32((UInt) 6887 op2)))); 6888 put_gpr_dw0(r1, unop(Iop_128to64, mkexpr(result))); 6889 6890 return "msgfi"; 6891 } 6892 6893 static const HChar * 6894 s390_irgen_OR(UChar r1, UChar r2) 6895 { 6896 IRTemp op1 = newTemp(Ity_I32); 6897 IRTemp op2 = newTemp(Ity_I32); 6898 IRTemp result = newTemp(Ity_I32); 6899 6900 assign(op1, get_gpr_w1(r1)); 6901 assign(op2, get_gpr_w1(r2)); 6902 assign(result, binop(Iop_Or32, mkexpr(op1), mkexpr(op2))); 6903 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 6904 put_gpr_w1(r1, mkexpr(result)); 6905 6906 return "or"; 6907 } 6908 6909 static const HChar * 6910 s390_irgen_OGR(UChar r1, UChar r2) 6911 { 6912 IRTemp op1 = newTemp(Ity_I64); 6913 IRTemp op2 = newTemp(Ity_I64); 6914 IRTemp result = newTemp(Ity_I64); 6915 6916 assign(op1, get_gpr_dw0(r1)); 6917 assign(op2, get_gpr_dw0(r2)); 6918 assign(result, binop(Iop_Or64, mkexpr(op1), mkexpr(op2))); 6919 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 6920 put_gpr_dw0(r1, mkexpr(result)); 6921 6922 return "ogr"; 6923 } 6924 6925 static const HChar * 6926 s390_irgen_ORK(UChar r3, UChar r1, UChar r2) 6927 { 6928 IRTemp op2 = newTemp(Ity_I32); 6929 IRTemp op3 = newTemp(Ity_I32); 6930 IRTemp result = newTemp(Ity_I32); 6931 6932 assign(op2, get_gpr_w1(r2)); 6933 assign(op3, get_gpr_w1(r3)); 6934 assign(result, binop(Iop_Or32, mkexpr(op2), mkexpr(op3))); 6935 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 6936 put_gpr_w1(r1, mkexpr(result)); 6937 6938 return "ork"; 6939 } 6940 6941 static const HChar * 6942 s390_irgen_OGRK(UChar r3, UChar r1, UChar r2) 6943 { 6944 IRTemp op2 = newTemp(Ity_I64); 6945 IRTemp op3 = newTemp(Ity_I64); 6946 IRTemp result = newTemp(Ity_I64); 6947 6948 assign(op2, get_gpr_dw0(r2)); 6949 assign(op3, get_gpr_dw0(r3)); 6950 assign(result, binop(Iop_Or64, mkexpr(op2), mkexpr(op3))); 6951 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 6952 put_gpr_dw0(r1, mkexpr(result)); 6953 6954 return "ogrk"; 6955 } 6956 6957 static const HChar * 6958 s390_irgen_O(UChar r1, IRTemp op2addr) 6959 { 6960 IRTemp op1 = newTemp(Ity_I32); 6961 IRTemp op2 = newTemp(Ity_I32); 6962 IRTemp result = newTemp(Ity_I32); 6963 6964 assign(op1, get_gpr_w1(r1)); 6965 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6966 assign(result, binop(Iop_Or32, mkexpr(op1), mkexpr(op2))); 6967 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 6968 put_gpr_w1(r1, mkexpr(result)); 6969 6970 return "o"; 6971 } 6972 6973 static const HChar * 6974 s390_irgen_OY(UChar r1, IRTemp op2addr) 6975 { 6976 IRTemp op1 = newTemp(Ity_I32); 6977 IRTemp op2 = newTemp(Ity_I32); 6978 IRTemp result = newTemp(Ity_I32); 6979 6980 assign(op1, get_gpr_w1(r1)); 6981 assign(op2, load(Ity_I32, mkexpr(op2addr))); 6982 assign(result, binop(Iop_Or32, mkexpr(op1), mkexpr(op2))); 6983 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 6984 put_gpr_w1(r1, mkexpr(result)); 6985 6986 return "oy"; 6987 } 6988 6989 static const HChar * 6990 s390_irgen_OG(UChar r1, IRTemp op2addr) 6991 { 6992 IRTemp op1 = newTemp(Ity_I64); 6993 IRTemp op2 = newTemp(Ity_I64); 6994 IRTemp result = newTemp(Ity_I64); 6995 6996 assign(op1, get_gpr_dw0(r1)); 6997 assign(op2, load(Ity_I64, mkexpr(op2addr))); 6998 assign(result, binop(Iop_Or64, mkexpr(op1), mkexpr(op2))); 6999 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7000 put_gpr_dw0(r1, mkexpr(result)); 7001 7002 return "og"; 7003 } 7004 7005 static const HChar * 7006 s390_irgen_OI(UChar i2, IRTemp op1addr) 7007 { 7008 IRTemp op1 = newTemp(Ity_I8); 7009 UChar op2; 7010 IRTemp result = newTemp(Ity_I8); 7011 7012 assign(op1, load(Ity_I8, mkexpr(op1addr))); 7013 op2 = i2; 7014 assign(result, binop(Iop_Or8, mkexpr(op1), mkU8(op2))); 7015 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7016 store(mkexpr(op1addr), mkexpr(result)); 7017 7018 return "oi"; 7019 } 7020 7021 static const HChar * 7022 s390_irgen_OIY(UChar i2, IRTemp op1addr) 7023 { 7024 IRTemp op1 = newTemp(Ity_I8); 7025 UChar op2; 7026 IRTemp result = newTemp(Ity_I8); 7027 7028 assign(op1, load(Ity_I8, mkexpr(op1addr))); 7029 op2 = i2; 7030 assign(result, binop(Iop_Or8, mkexpr(op1), mkU8(op2))); 7031 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7032 store(mkexpr(op1addr), mkexpr(result)); 7033 7034 return "oiy"; 7035 } 7036 7037 static const HChar * 7038 s390_irgen_OIHF(UChar r1, UInt i2) 7039 { 7040 IRTemp op1 = newTemp(Ity_I32); 7041 UInt op2; 7042 IRTemp result = newTemp(Ity_I32); 7043 7044 assign(op1, get_gpr_w0(r1)); 7045 op2 = i2; 7046 assign(result, binop(Iop_Or32, mkexpr(op1), mkU32(op2))); 7047 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7048 put_gpr_w0(r1, mkexpr(result)); 7049 7050 return "oihf"; 7051 } 7052 7053 static const HChar * 7054 s390_irgen_OIHH(UChar r1, UShort i2) 7055 { 7056 IRTemp op1 = newTemp(Ity_I16); 7057 UShort op2; 7058 IRTemp result = newTemp(Ity_I16); 7059 7060 assign(op1, get_gpr_hw0(r1)); 7061 op2 = i2; 7062 assign(result, binop(Iop_Or16, mkexpr(op1), mkU16(op2))); 7063 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7064 put_gpr_hw0(r1, mkexpr(result)); 7065 7066 return "oihh"; 7067 } 7068 7069 static const HChar * 7070 s390_irgen_OIHL(UChar r1, UShort i2) 7071 { 7072 IRTemp op1 = newTemp(Ity_I16); 7073 UShort op2; 7074 IRTemp result = newTemp(Ity_I16); 7075 7076 assign(op1, get_gpr_hw1(r1)); 7077 op2 = i2; 7078 assign(result, binop(Iop_Or16, mkexpr(op1), mkU16(op2))); 7079 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7080 put_gpr_hw1(r1, mkexpr(result)); 7081 7082 return "oihl"; 7083 } 7084 7085 static const HChar * 7086 s390_irgen_OILF(UChar r1, UInt i2) 7087 { 7088 IRTemp op1 = newTemp(Ity_I32); 7089 UInt op2; 7090 IRTemp result = newTemp(Ity_I32); 7091 7092 assign(op1, get_gpr_w1(r1)); 7093 op2 = i2; 7094 assign(result, binop(Iop_Or32, mkexpr(op1), mkU32(op2))); 7095 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7096 put_gpr_w1(r1, mkexpr(result)); 7097 7098 return "oilf"; 7099 } 7100 7101 static const HChar * 7102 s390_irgen_OILH(UChar r1, UShort i2) 7103 { 7104 IRTemp op1 = newTemp(Ity_I16); 7105 UShort op2; 7106 IRTemp result = newTemp(Ity_I16); 7107 7108 assign(op1, get_gpr_hw2(r1)); 7109 op2 = i2; 7110 assign(result, binop(Iop_Or16, mkexpr(op1), mkU16(op2))); 7111 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7112 put_gpr_hw2(r1, mkexpr(result)); 7113 7114 return "oilh"; 7115 } 7116 7117 static const HChar * 7118 s390_irgen_OILL(UChar r1, UShort i2) 7119 { 7120 IRTemp op1 = newTemp(Ity_I16); 7121 UShort op2; 7122 IRTemp result = newTemp(Ity_I16); 7123 7124 assign(op1, get_gpr_hw3(r1)); 7125 op2 = i2; 7126 assign(result, binop(Iop_Or16, mkexpr(op1), mkU16(op2))); 7127 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7128 put_gpr_hw3(r1, mkexpr(result)); 7129 7130 return "oill"; 7131 } 7132 7133 static const HChar * 7134 s390_irgen_PFD(void) 7135 { 7136 7137 return "pfd"; 7138 } 7139 7140 static const HChar * 7141 s390_irgen_PFDRL(void) 7142 { 7143 7144 return "pfdrl"; 7145 } 7146 7147 static IRExpr * 7148 get_rounding_mode_from_gr0(void) 7149 { 7150 IRTemp rm_bits = newTemp(Ity_I32); 7151 IRExpr *s390rm; 7152 IRExpr *irrm; 7153 7154 /* The dfp/bfp rounding mode is stored in bits [60:63] of GR 0 7155 when PFPO insn is called. So, extract the bits at [60:63] */ 7156 assign(rm_bits, binop(Iop_And32, get_gpr_w1(0), mkU32(0xf))); 7157 s390rm = mkexpr(rm_bits); 7158 irrm = mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0x1)), 7159 mkexpr(encode_bfp_rounding_mode( S390_BFP_ROUND_PER_FPC)), 7160 mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0x8)), 7161 mkexpr(encode_dfp_rounding_mode(S390_DFP_ROUND_NEAREST_EVEN_8)), 7162 mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0x9)), 7163 mkexpr(encode_dfp_rounding_mode(S390_DFP_ROUND_ZERO_9)), 7164 mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0xa)), 7165 mkexpr(encode_dfp_rounding_mode(S390_DFP_ROUND_POSINF_10)), 7166 mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0xb)), 7167 mkexpr(encode_dfp_rounding_mode(S390_DFP_ROUND_NEGINF_11)), 7168 mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0xc)), 7169 mkexpr(encode_dfp_rounding_mode( 7170 S390_DFP_ROUND_NEAREST_TIE_AWAY_0_12)), 7171 mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0xd)), 7172 mkexpr(encode_dfp_rounding_mode( 7173 S390_DFP_ROUND_NEAREST_TIE_TOWARD_0)), 7174 mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0xe)), 7175 mkexpr(encode_dfp_rounding_mode( 7176 S390_DFP_ROUND_AWAY_0)), 7177 mkite(binop(Iop_CmpEQ32, s390rm, mkU32(0xf)), 7178 mkexpr(encode_dfp_rounding_mode( 7179 S390_DFP_ROUND_PREPARE_SHORT_15)), 7180 /* if rounding mode is 0 or invalid (2-7) 7181 set S390_DFP_ROUND_PER_FPC_0 */ 7182 mkexpr(encode_dfp_rounding_mode( 7183 S390_DFP_ROUND_PER_FPC_0))))))))))); 7184 7185 return irrm; 7186 } 7187 7188 static IRExpr * 7189 s390_call_pfpo_helper(IRExpr *gr0) 7190 { 7191 IRExpr **args, *call; 7192 7193 args = mkIRExprVec_1(gr0); 7194 call = mkIRExprCCall(Ity_I32, 0 /*regparm*/, 7195 "s390_do_pfpo", &s390_do_pfpo, args); 7196 /* Nothing is excluded from definedness checking. */ 7197 call->Iex.CCall.cee->mcx_mask = 0; 7198 7199 return call; 7200 } 7201 7202 static const HChar * 7203 s390_irgen_PFPO(void) 7204 { 7205 IRTemp gr0 = newTemp(Ity_I32); /* word 1 [32:63] of GR 0 */ 7206 IRTemp test_bit = newTemp(Ity_I32); /* bit 32 of GR 0 - test validity */ 7207 IRTemp fn = newTemp(Ity_I32); /* [33:55] of GR 0 - function code */ 7208 IRTemp ef = newTemp(Ity_I32); /* Emulation Failure */ 7209 IRTemp src1 = newTemp(Ity_F32); 7210 IRTemp dst1 = newTemp(Ity_D32); 7211 IRTemp src2 = newTemp(Ity_F32); 7212 IRTemp dst2 = newTemp(Ity_D64); 7213 IRTemp src3 = newTemp(Ity_F32); 7214 IRTemp dst3 = newTemp(Ity_D128); 7215 IRTemp src4 = newTemp(Ity_F64); 7216 IRTemp dst4 = newTemp(Ity_D32); 7217 IRTemp src5 = newTemp(Ity_F64); 7218 IRTemp dst5 = newTemp(Ity_D64); 7219 IRTemp src6 = newTemp(Ity_F64); 7220 IRTemp dst6 = newTemp(Ity_D128); 7221 IRTemp src7 = newTemp(Ity_F128); 7222 IRTemp dst7 = newTemp(Ity_D32); 7223 IRTemp src8 = newTemp(Ity_F128); 7224 IRTemp dst8 = newTemp(Ity_D64); 7225 IRTemp src9 = newTemp(Ity_F128); 7226 IRTemp dst9 = newTemp(Ity_D128); 7227 IRTemp src10 = newTemp(Ity_D32); 7228 IRTemp dst10 = newTemp(Ity_F32); 7229 IRTemp src11 = newTemp(Ity_D32); 7230 IRTemp dst11 = newTemp(Ity_F64); 7231 IRTemp src12 = newTemp(Ity_D32); 7232 IRTemp dst12 = newTemp(Ity_F128); 7233 IRTemp src13 = newTemp(Ity_D64); 7234 IRTemp dst13 = newTemp(Ity_F32); 7235 IRTemp src14 = newTemp(Ity_D64); 7236 IRTemp dst14 = newTemp(Ity_F64); 7237 IRTemp src15 = newTemp(Ity_D64); 7238 IRTemp dst15 = newTemp(Ity_F128); 7239 IRTemp src16 = newTemp(Ity_D128); 7240 IRTemp dst16 = newTemp(Ity_F32); 7241 IRTemp src17 = newTemp(Ity_D128); 7242 IRTemp dst17 = newTemp(Ity_F64); 7243 IRTemp src18 = newTemp(Ity_D128); 7244 IRTemp dst18 = newTemp(Ity_F128); 7245 IRExpr *irrm; 7246 7247 if (! s390_host_has_pfpo) { 7248 emulation_failure(EmFail_S390X_pfpo); 7249 goto done; 7250 } 7251 7252 assign(gr0, get_gpr_w1(0)); 7253 /* get function code */ 7254 assign(fn, binop(Iop_And32, binop(Iop_Shr32, mkexpr(gr0), mkU8(8)), 7255 mkU32(0x7fffff))); 7256 /* get validity test bit */ 7257 assign(test_bit, binop(Iop_And32, binop(Iop_Shr32, mkexpr(gr0), mkU8(31)), 7258 mkU32(0x1))); 7259 irrm = get_rounding_mode_from_gr0(); 7260 7261 /* test_bit is 1 */ 7262 assign(src1, get_fpr_w0(4)); /* get source from FPR 4,6 */ 7263 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_64, src1, gr0); 7264 7265 /* Return code set in GR1 is usually 0. Non-zero value is set only 7266 when exceptions are raised. See Programming Notes point 5 in the 7267 instrcution description of pfpo in POP. Since valgrind does not 7268 model exception, it might be safe to just set 0 to GR 1. */ 7269 put_gpr_w1(1, mkU32(0x0)); 7270 next_insn_if(binop(Iop_CmpEQ32, mkexpr(test_bit), mkU32(0x1))); 7271 7272 /* Check validity of function code in GR 0 */ 7273 assign(ef, s390_call_pfpo_helper(unop(Iop_32Uto64, mkexpr(gr0)))); 7274 emulation_failure_with_expr(mkexpr(ef)); 7275 7276 stmt( 7277 IRStmt_Exit( 7278 binop(Iop_CmpNE32, mkexpr(ef), mkU32(EmNote_NONE)), 7279 Ijk_EmFail, 7280 IRConst_U64(guest_IA_next_instr), 7281 S390X_GUEST_OFFSET(guest_IA) 7282 ) 7283 ); 7284 7285 /* F32 -> D32 */ 7286 /* get source from FPR 4,6 - already set in src1 */ 7287 assign(dst1, binop(Iop_F32toD32, irrm, mkexpr(src1))); 7288 put_dpr_w0(0, mkexpr(dst1)); /* put the result in FPR 0,2 */ 7289 put_gpr_w1(1, mkU32(0x0)); 7290 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_32, src1, gr0); 7291 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F32_TO_D32))); 7292 7293 /* F32 -> D64 */ 7294 assign(src2, get_fpr_w0(4)); /* get source from FPR 4,6 */ 7295 assign(dst2, binop(Iop_F32toD64, irrm, mkexpr(src2))); 7296 put_dpr_dw0(0, mkexpr(dst2)); /* put the result in FPR 0,2 */ 7297 put_gpr_w1(1, mkU32(0x0)); 7298 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_32, src2, gr0); 7299 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F32_TO_D64))); 7300 7301 /* F32 -> D128 */ 7302 assign(src3, get_fpr_w0(4)); /* get source from FPR 4,6 */ 7303 assign(dst3, binop(Iop_F32toD128, irrm, mkexpr(src3))); 7304 put_dpr_pair(0, mkexpr(dst3)); /* put the result in FPR 0,2 */ 7305 put_gpr_w1(1, mkU32(0x0)); 7306 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_32, src3, gr0); 7307 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F32_TO_D128))); 7308 7309 /* F64 -> D32 */ 7310 assign(src4, get_fpr_dw0(4)); /* get source from FPR 4,6 */ 7311 assign(dst4, binop(Iop_F64toD32, irrm, mkexpr(src4))); 7312 put_dpr_w0(0, mkexpr(dst4)); /* put the result in FPR 0,2 */ 7313 put_gpr_w1(1, mkU32(0x0)); 7314 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_64, src4, gr0); 7315 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F64_TO_D32))); 7316 7317 /* F64 -> D64 */ 7318 assign(src5, get_fpr_dw0(4)); /* get source from FPR 4,6 */ 7319 assign(dst5, binop(Iop_F64toD64, irrm, mkexpr(src5))); 7320 put_dpr_dw0(0, mkexpr(dst5)); /* put the result in FPR 0,2 */ 7321 put_gpr_w1(1, mkU32(0x0)); 7322 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_64, src5, gr0); 7323 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F64_TO_D64))); 7324 7325 /* F64 -> D128 */ 7326 assign(src6, get_fpr_dw0(4)); /* get source from FPR 4,6 */ 7327 assign(dst6, binop(Iop_F64toD128, irrm, mkexpr(src6))); 7328 put_dpr_pair(0, mkexpr(dst6)); /* put the result in FPR 0,2 */ 7329 put_gpr_w1(1, mkU32(0x0)); 7330 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_64, src6, gr0); 7331 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F64_TO_D128))); 7332 7333 /* F128 -> D32 */ 7334 assign(src7, get_fpr_pair(4)); /* get source from FPR 4,6 */ 7335 assign(dst7, binop(Iop_F128toD32, irrm, mkexpr(src7))); 7336 put_dpr_w0(0, mkexpr(dst7)); /* put the result in FPR 0,2 */ 7337 put_gpr_w1(1, mkU32(0x0)); 7338 s390_cc_thunk_put1f128Z(S390_CC_OP_PFPO_128, src7, gr0); 7339 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F128_TO_D32))); 7340 7341 /* F128 -> D64 */ 7342 assign(src8, get_fpr_pair(4)); /* get source from FPR 4,6 */ 7343 assign(dst8, binop(Iop_F128toD64, irrm, mkexpr(src8))); 7344 put_dpr_dw0(0, mkexpr(dst8)); /* put the result in FPR 0,2 */ 7345 put_gpr_w1(1, mkU32(0x0)); 7346 s390_cc_thunk_put1f128Z(S390_CC_OP_PFPO_128, src8, gr0); 7347 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F128_TO_D64))); 7348 7349 /* F128 -> D128 */ 7350 assign(src9, get_fpr_pair(4)); /* get source from FPR 4,6 */ 7351 assign(dst9, binop(Iop_F128toD128, irrm, mkexpr(src9))); 7352 put_dpr_pair(0, mkexpr(dst9)); /* put the result in FPR 0,2 */ 7353 put_gpr_w1(1, mkU32(0x0)); 7354 s390_cc_thunk_put1f128Z(S390_CC_OP_PFPO_128, src9, gr0); 7355 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_F128_TO_D128))); 7356 7357 /* D32 -> F32 */ 7358 assign(src10, get_dpr_w0(4)); /* get source from FPR 4,6 */ 7359 assign(dst10, binop(Iop_D32toF32, irrm, mkexpr(src10))); 7360 put_fpr_w0(0, mkexpr(dst10)); /* put the result in FPR 0,2 */ 7361 put_gpr_w1(1, mkU32(0x0)); 7362 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_32, src10, gr0); 7363 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D32_TO_F32))); 7364 7365 /* D32 -> F64 */ 7366 assign(src11, get_dpr_w0(4)); /* get source from FPR 4,6 */ 7367 assign(dst11, binop(Iop_D32toF64, irrm, mkexpr(src11))); 7368 put_fpr_dw0(0, mkexpr(dst11)); /* put the result in FPR 0,2 */ 7369 put_gpr_w1(1, mkU32(0x0)); 7370 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_32, src11, gr0); 7371 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D32_TO_F64))); 7372 7373 /* D32 -> F128 */ 7374 assign(src12, get_dpr_w0(4)); /* get source from FPR 4,6 */ 7375 assign(dst12, binop(Iop_D32toF128, irrm, mkexpr(src12))); 7376 put_fpr_pair(0, mkexpr(dst12)); /* put the result in FPR 0,2 */ 7377 put_gpr_w1(1, mkU32(0x0)); 7378 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_32, src12, gr0); 7379 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D32_TO_F128))); 7380 7381 /* D64 -> F32 */ 7382 assign(src13, get_dpr_dw0(4)); /* get source from FPR 4,6 */ 7383 assign(dst13, binop(Iop_D64toF32, irrm, mkexpr(src13))); 7384 put_fpr_w0(0, mkexpr(dst13)); /* put the result in FPR 0,2 */ 7385 put_gpr_w1(1, mkU32(0x0)); 7386 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_64, src13, gr0); 7387 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D64_TO_F32))); 7388 7389 /* D64 -> F64 */ 7390 assign(src14, get_dpr_dw0(4)); /* get source from FPR 4,6 */ 7391 assign(dst14, binop(Iop_D64toF64, irrm, mkexpr(src14))); 7392 put_fpr_dw0(0, mkexpr(dst14)); /* put the result in FPR 0,2 */ 7393 put_gpr_w1(1, mkU32(0x0)); 7394 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_64, src14, gr0); 7395 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D64_TO_F64))); 7396 7397 /* D64 -> F128 */ 7398 assign(src15, get_dpr_dw0(4)); /* get source from FPR 4,6 */ 7399 assign(dst15, binop(Iop_D64toF128, irrm, mkexpr(src15))); 7400 put_fpr_pair(0, mkexpr(dst15)); /* put the result in FPR 0,2 */ 7401 put_gpr_w1(1, mkU32(0x0)); 7402 s390_cc_thunk_putFZ(S390_CC_OP_PFPO_64, src15, gr0); 7403 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D64_TO_F128))); 7404 7405 /* D128 -> F32 */ 7406 assign(src16, get_dpr_pair(4)); /* get source from FPR 4,6 */ 7407 assign(dst16, binop(Iop_D128toF32, irrm, mkexpr(src16))); 7408 put_fpr_w0(0, mkexpr(dst16)); /* put the result in FPR 0,2 */ 7409 put_gpr_w1(1, mkU32(0x0)); 7410 s390_cc_thunk_put1d128Z(S390_CC_OP_PFPO_128, src16, gr0); 7411 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D128_TO_F32))); 7412 7413 /* D128 -> F64 */ 7414 assign(src17, get_dpr_pair(4)); /* get source from FPR 4,6 */ 7415 assign(dst17, binop(Iop_D128toF64, irrm, mkexpr(src17))); 7416 put_fpr_dw0(0, mkexpr(dst17)); /* put the result in FPR 0,2 */ 7417 put_gpr_w1(1, mkU32(0x0)); 7418 s390_cc_thunk_put1d128Z(S390_CC_OP_PFPO_128, src17, gr0); 7419 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D128_TO_F64))); 7420 7421 /* D128 -> F128 */ 7422 assign(src18, get_dpr_pair(4)); /* get source from FPR 4,6 */ 7423 assign(dst18, binop(Iop_D128toF128, irrm, mkexpr(src18))); 7424 put_fpr_pair(0, mkexpr(dst18)); /* put the result in FPR 0,2 */ 7425 put_gpr_w1(1, mkU32(0x0)); 7426 s390_cc_thunk_put1d128Z(S390_CC_OP_PFPO_128, src18, gr0); 7427 next_insn_if(binop(Iop_CmpEQ32, mkexpr(fn), mkU32(S390_PFPO_D128_TO_F128))); 7428 7429 done: 7430 return "pfpo"; 7431 } 7432 7433 static const HChar * 7434 s390_irgen_RLL(UChar r1, UChar r3, IRTemp op2addr) 7435 { 7436 IRTemp amount = newTemp(Ity_I64); 7437 IRTemp op = newTemp(Ity_I32); 7438 7439 assign(amount, binop(Iop_And64, mkexpr(op2addr), mkU64(31))); 7440 assign(op, get_gpr_w1(r3)); 7441 put_gpr_w1(r1, binop(Iop_Or32, binop(Iop_Shl32, mkexpr(op), unop(Iop_64to8, 7442 mkexpr(amount))), binop(Iop_Shr32, mkexpr(op), unop(Iop_64to8, 7443 binop(Iop_Sub64, mkU64(32), mkexpr(amount)))))); 7444 7445 return "rll"; 7446 } 7447 7448 static const HChar * 7449 s390_irgen_RLLG(UChar r1, UChar r3, IRTemp op2addr) 7450 { 7451 IRTemp amount = newTemp(Ity_I64); 7452 IRTemp op = newTemp(Ity_I64); 7453 7454 assign(amount, binop(Iop_And64, mkexpr(op2addr), mkU64(63))); 7455 assign(op, get_gpr_dw0(r3)); 7456 put_gpr_dw0(r1, binop(Iop_Or64, binop(Iop_Shl64, mkexpr(op), unop(Iop_64to8, 7457 mkexpr(amount))), binop(Iop_Shr64, mkexpr(op), unop(Iop_64to8, 7458 binop(Iop_Sub64, mkU64(64), mkexpr(amount)))))); 7459 7460 return "rllg"; 7461 } 7462 7463 static const HChar * 7464 s390_irgen_RNSBG(UChar r1, UChar r2, UChar i3, UChar i4, UChar i5) 7465 { 7466 UChar from; 7467 UChar to; 7468 UChar rot; 7469 UChar t_bit; 7470 ULong mask; 7471 ULong maskc; 7472 IRTemp result = newTemp(Ity_I64); 7473 IRTemp op2 = newTemp(Ity_I64); 7474 7475 from = i3 & 63; 7476 to = i4 & 63; 7477 rot = i5 & 63; 7478 t_bit = i3 & 128; 7479 assign(op2, rot == 0 ? get_gpr_dw0(r2) : binop(Iop_Or64, binop(Iop_Shl64, 7480 get_gpr_dw0(r2), mkU8(rot)), binop(Iop_Shr64, get_gpr_dw0(r2), 7481 mkU8(64 - rot)))); 7482 if (from <= to) { 7483 mask = ~0ULL; 7484 mask = (mask >> from) & (mask << (63 - to)); 7485 maskc = ~mask; 7486 } else { 7487 maskc = ~0ULL; 7488 maskc = (maskc >> (to + 1)) & (maskc << (64 - from)); 7489 mask = ~maskc; 7490 } 7491 assign(result, binop(Iop_And64, binop(Iop_And64, get_gpr_dw0(r1), mkexpr(op2) 7492 ), mkU64(mask))); 7493 if (t_bit == 0) { 7494 put_gpr_dw0(r1, binop(Iop_Or64, binop(Iop_And64, get_gpr_dw0(r1), 7495 mkU64(maskc)), mkexpr(result))); 7496 } 7497 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7498 7499 return "rnsbg"; 7500 } 7501 7502 static const HChar * 7503 s390_irgen_RXSBG(UChar r1, UChar r2, UChar i3, UChar i4, UChar i5) 7504 { 7505 UChar from; 7506 UChar to; 7507 UChar rot; 7508 UChar t_bit; 7509 ULong mask; 7510 ULong maskc; 7511 IRTemp result = newTemp(Ity_I64); 7512 IRTemp op2 = newTemp(Ity_I64); 7513 7514 from = i3 & 63; 7515 to = i4 & 63; 7516 rot = i5 & 63; 7517 t_bit = i3 & 128; 7518 assign(op2, rot == 0 ? get_gpr_dw0(r2) : binop(Iop_Or64, binop(Iop_Shl64, 7519 get_gpr_dw0(r2), mkU8(rot)), binop(Iop_Shr64, get_gpr_dw0(r2), 7520 mkU8(64 - rot)))); 7521 if (from <= to) { 7522 mask = ~0ULL; 7523 mask = (mask >> from) & (mask << (63 - to)); 7524 maskc = ~mask; 7525 } else { 7526 maskc = ~0ULL; 7527 maskc = (maskc >> (to + 1)) & (maskc << (64 - from)); 7528 mask = ~maskc; 7529 } 7530 assign(result, binop(Iop_And64, binop(Iop_Xor64, get_gpr_dw0(r1), mkexpr(op2) 7531 ), mkU64(mask))); 7532 if (t_bit == 0) { 7533 put_gpr_dw0(r1, binop(Iop_Or64, binop(Iop_And64, get_gpr_dw0(r1), 7534 mkU64(maskc)), mkexpr(result))); 7535 } 7536 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7537 7538 return "rxsbg"; 7539 } 7540 7541 static const HChar * 7542 s390_irgen_ROSBG(UChar r1, UChar r2, UChar i3, UChar i4, UChar i5) 7543 { 7544 UChar from; 7545 UChar to; 7546 UChar rot; 7547 UChar t_bit; 7548 ULong mask; 7549 ULong maskc; 7550 IRTemp result = newTemp(Ity_I64); 7551 IRTemp op2 = newTemp(Ity_I64); 7552 7553 from = i3 & 63; 7554 to = i4 & 63; 7555 rot = i5 & 63; 7556 t_bit = i3 & 128; 7557 assign(op2, rot == 0 ? get_gpr_dw0(r2) : binop(Iop_Or64, binop(Iop_Shl64, 7558 get_gpr_dw0(r2), mkU8(rot)), binop(Iop_Shr64, get_gpr_dw0(r2), 7559 mkU8(64 - rot)))); 7560 if (from <= to) { 7561 mask = ~0ULL; 7562 mask = (mask >> from) & (mask << (63 - to)); 7563 maskc = ~mask; 7564 } else { 7565 maskc = ~0ULL; 7566 maskc = (maskc >> (to + 1)) & (maskc << (64 - from)); 7567 mask = ~maskc; 7568 } 7569 assign(result, binop(Iop_And64, binop(Iop_Or64, get_gpr_dw0(r1), mkexpr(op2) 7570 ), mkU64(mask))); 7571 if (t_bit == 0) { 7572 put_gpr_dw0(r1, binop(Iop_Or64, binop(Iop_And64, get_gpr_dw0(r1), 7573 mkU64(maskc)), mkexpr(result))); 7574 } 7575 s390_cc_thunk_putZ(S390_CC_OP_BITWISE, result); 7576 7577 return "rosbg"; 7578 } 7579 7580 static const HChar * 7581 s390_irgen_RISBG(UChar r1, UChar r2, UChar i3, UChar i4, UChar i5) 7582 { 7583 UChar from; 7584 UChar to; 7585 UChar rot; 7586 UChar z_bit; 7587 ULong mask; 7588 ULong maskc; 7589 IRTemp op2 = newTemp(Ity_I64); 7590 IRTemp result = newTemp(Ity_I64); 7591 7592 from = i3 & 63; 7593 to = i4 & 63; 7594 rot = i5 & 63; 7595 z_bit = i4 & 128; 7596 assign(op2, rot == 0 ? get_gpr_dw0(r2) : binop(Iop_Or64, binop(Iop_Shl64, 7597 get_gpr_dw0(r2), mkU8(rot)), binop(Iop_Shr64, get_gpr_dw0(r2), 7598 mkU8(64 - rot)))); 7599 if (from <= to) { 7600 mask = ~0ULL; 7601 mask = (mask >> from) & (mask << (63 - to)); 7602 maskc = ~mask; 7603 } else { 7604 maskc = ~0ULL; 7605 maskc = (maskc >> (to + 1)) & (maskc << (64 - from)); 7606 mask = ~maskc; 7607 } 7608 if (z_bit == 0) { 7609 put_gpr_dw0(r1, binop(Iop_Or64, binop(Iop_And64, get_gpr_dw0(r1), 7610 mkU64(maskc)), binop(Iop_And64, mkexpr(op2), mkU64(mask)))); 7611 } else { 7612 put_gpr_dw0(r1, binop(Iop_And64, mkexpr(op2), mkU64(mask))); 7613 } 7614 assign(result, get_gpr_dw0(r1)); 7615 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, result); 7616 7617 return "risbg"; 7618 } 7619 7620 static const HChar * 7621 s390_irgen_SAR(UChar r1, UChar r2) 7622 { 7623 put_ar_w0(r1, get_gpr_w1(r2)); 7624 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 7625 s390_disasm(ENC3(MNM, AR, GPR), "sar", r1, r2); 7626 7627 return "sar"; 7628 } 7629 7630 static const HChar * 7631 s390_irgen_SLDA(UChar r1, IRTemp op2addr) 7632 { 7633 IRTemp p1 = newTemp(Ity_I64); 7634 IRTemp p2 = newTemp(Ity_I64); 7635 IRTemp op = newTemp(Ity_I64); 7636 IRTemp result = newTemp(Ity_I64); 7637 ULong sign_mask; 7638 IRTemp shift_amount = newTemp(Ity_I64); 7639 7640 assign(p1, unop(Iop_32Uto64, get_gpr_w1(r1))); 7641 assign(p2, unop(Iop_32Uto64, get_gpr_w1(r1 + 1))); 7642 assign(op, binop(Iop_Or64, binop(Iop_Shl64, mkexpr(p1), mkU8(32)), mkexpr(p2) 7643 )); 7644 sign_mask = 1ULL << 63; 7645 assign(shift_amount, binop(Iop_And64, mkexpr(op2addr), mkU64(63))); 7646 assign(result, binop(Iop_Or64, binop(Iop_And64, binop(Iop_Shl64, mkexpr(op), 7647 unop(Iop_64to8, mkexpr(shift_amount))), mkU64(~sign_mask)), 7648 binop(Iop_And64, mkexpr(op), mkU64(sign_mask)))); 7649 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 7650 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 7651 s390_cc_thunk_putZZ(S390_CC_OP_SHIFT_LEFT_64, op, shift_amount); 7652 7653 return "slda"; 7654 } 7655 7656 static const HChar * 7657 s390_irgen_SLDL(UChar r1, IRTemp op2addr) 7658 { 7659 IRTemp p1 = newTemp(Ity_I64); 7660 IRTemp p2 = newTemp(Ity_I64); 7661 IRTemp result = newTemp(Ity_I64); 7662 7663 assign(p1, unop(Iop_32Uto64, get_gpr_w1(r1))); 7664 assign(p2, unop(Iop_32Uto64, get_gpr_w1(r1 + 1))); 7665 assign(result, binop(Iop_Shl64, binop(Iop_Or64, binop(Iop_Shl64, mkexpr(p1), 7666 mkU8(32)), mkexpr(p2)), unop(Iop_64to8, binop(Iop_And64, 7667 mkexpr(op2addr), mkU64(63))))); 7668 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 7669 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 7670 7671 return "sldl"; 7672 } 7673 7674 static const HChar * 7675 s390_irgen_SLA(UChar r1, IRTemp op2addr) 7676 { 7677 IRTemp uop = newTemp(Ity_I32); 7678 IRTemp result = newTemp(Ity_I32); 7679 UInt sign_mask; 7680 IRTemp shift_amount = newTemp(Ity_I64); 7681 IRTemp op = newTemp(Ity_I32); 7682 7683 assign(op, get_gpr_w1(r1)); 7684 assign(uop, get_gpr_w1(r1)); 7685 sign_mask = 2147483648U; 7686 assign(shift_amount, binop(Iop_And64, mkexpr(op2addr), mkU64(63))); 7687 assign(result, binop(Iop_Or32, binop(Iop_And32, binop(Iop_Shl32, mkexpr(uop), 7688 unop(Iop_64to8, mkexpr(shift_amount))), mkU32(~sign_mask)), 7689 binop(Iop_And32, mkexpr(uop), mkU32(sign_mask)))); 7690 put_gpr_w1(r1, mkexpr(result)); 7691 s390_cc_thunk_putZZ(S390_CC_OP_SHIFT_LEFT_32, op, shift_amount); 7692 7693 return "sla"; 7694 } 7695 7696 static const HChar * 7697 s390_irgen_SLAK(UChar r1, UChar r3, IRTemp op2addr) 7698 { 7699 IRTemp uop = newTemp(Ity_I32); 7700 IRTemp result = newTemp(Ity_I32); 7701 UInt sign_mask; 7702 IRTemp shift_amount = newTemp(Ity_I64); 7703 IRTemp op = newTemp(Ity_I32); 7704 7705 assign(op, get_gpr_w1(r3)); 7706 assign(uop, get_gpr_w1(r3)); 7707 sign_mask = 2147483648U; 7708 assign(shift_amount, binop(Iop_And64, mkexpr(op2addr), mkU64(63))); 7709 assign(result, binop(Iop_Or32, binop(Iop_And32, binop(Iop_Shl32, mkexpr(uop), 7710 unop(Iop_64to8, mkexpr(shift_amount))), mkU32(~sign_mask)), 7711 binop(Iop_And32, mkexpr(uop), mkU32(sign_mask)))); 7712 put_gpr_w1(r1, mkexpr(result)); 7713 s390_cc_thunk_putZZ(S390_CC_OP_SHIFT_LEFT_32, op, shift_amount); 7714 7715 return "slak"; 7716 } 7717 7718 static const HChar * 7719 s390_irgen_SLAG(UChar r1, UChar r3, IRTemp op2addr) 7720 { 7721 IRTemp uop = newTemp(Ity_I64); 7722 IRTemp result = newTemp(Ity_I64); 7723 ULong sign_mask; 7724 IRTemp shift_amount = newTemp(Ity_I64); 7725 IRTemp op = newTemp(Ity_I64); 7726 7727 assign(op, get_gpr_dw0(r3)); 7728 assign(uop, get_gpr_dw0(r3)); 7729 sign_mask = 9223372036854775808ULL; 7730 assign(shift_amount, binop(Iop_And64, mkexpr(op2addr), mkU64(63))); 7731 assign(result, binop(Iop_Or64, binop(Iop_And64, binop(Iop_Shl64, mkexpr(uop), 7732 unop(Iop_64to8, mkexpr(shift_amount))), mkU64(~sign_mask)), 7733 binop(Iop_And64, mkexpr(uop), mkU64(sign_mask)))); 7734 put_gpr_dw0(r1, mkexpr(result)); 7735 s390_cc_thunk_putZZ(S390_CC_OP_SHIFT_LEFT_64, op, shift_amount); 7736 7737 return "slag"; 7738 } 7739 7740 static const HChar * 7741 s390_irgen_SLL(UChar r1, IRTemp op2addr) 7742 { 7743 put_gpr_w1(r1, binop(Iop_Shl32, get_gpr_w1(r1), unop(Iop_64to8, 7744 binop(Iop_And64, mkexpr(op2addr), mkU64(63))))); 7745 7746 return "sll"; 7747 } 7748 7749 static const HChar * 7750 s390_irgen_SLLK(UChar r1, UChar r3, IRTemp op2addr) 7751 { 7752 put_gpr_w1(r1, binop(Iop_Shl32, get_gpr_w1(r3), unop(Iop_64to8, 7753 binop(Iop_And64, mkexpr(op2addr), mkU64(63))))); 7754 7755 return "sllk"; 7756 } 7757 7758 static const HChar * 7759 s390_irgen_SLLG(UChar r1, UChar r3, IRTemp op2addr) 7760 { 7761 put_gpr_dw0(r1, binop(Iop_Shl64, get_gpr_dw0(r3), unop(Iop_64to8, 7762 binop(Iop_And64, mkexpr(op2addr), mkU64(63))))); 7763 7764 return "sllg"; 7765 } 7766 7767 static const HChar * 7768 s390_irgen_SRDA(UChar r1, IRTemp op2addr) 7769 { 7770 IRTemp p1 = newTemp(Ity_I64); 7771 IRTemp p2 = newTemp(Ity_I64); 7772 IRTemp result = newTemp(Ity_I64); 7773 7774 assign(p1, unop(Iop_32Uto64, get_gpr_w1(r1))); 7775 assign(p2, unop(Iop_32Uto64, get_gpr_w1(r1 + 1))); 7776 assign(result, binop(Iop_Sar64, binop(Iop_Or64, binop(Iop_Shl64, mkexpr(p1), 7777 mkU8(32)), mkexpr(p2)), unop(Iop_64to8, binop(Iop_And64, 7778 mkexpr(op2addr), mkU64(63))))); 7779 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 7780 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 7781 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, result); 7782 7783 return "srda"; 7784 } 7785 7786 static const HChar * 7787 s390_irgen_SRDL(UChar r1, IRTemp op2addr) 7788 { 7789 IRTemp p1 = newTemp(Ity_I64); 7790 IRTemp p2 = newTemp(Ity_I64); 7791 IRTemp result = newTemp(Ity_I64); 7792 7793 assign(p1, unop(Iop_32Uto64, get_gpr_w1(r1))); 7794 assign(p2, unop(Iop_32Uto64, get_gpr_w1(r1 + 1))); 7795 assign(result, binop(Iop_Shr64, binop(Iop_Or64, binop(Iop_Shl64, mkexpr(p1), 7796 mkU8(32)), mkexpr(p2)), unop(Iop_64to8, binop(Iop_And64, 7797 mkexpr(op2addr), mkU64(63))))); 7798 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); 7799 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); 7800 7801 return "srdl"; 7802 } 7803 7804 static const HChar * 7805 s390_irgen_SRA(UChar r1, IRTemp op2addr) 7806 { 7807 IRTemp result = newTemp(Ity_I32); 7808 IRTemp op = newTemp(Ity_I32); 7809 7810 assign(op, get_gpr_w1(r1)); 7811 assign(result, binop(Iop_Sar32, mkexpr(op), unop(Iop_64to8, binop(Iop_And64, 7812 mkexpr(op2addr), mkU64(63))))); 7813 put_gpr_w1(r1, mkexpr(result)); 7814 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, result); 7815 7816 return "sra"; 7817 } 7818 7819 static const HChar * 7820 s390_irgen_SRAK(UChar r1, UChar r3, IRTemp op2addr) 7821 { 7822 IRTemp result = newTemp(Ity_I32); 7823 IRTemp op = newTemp(Ity_I32); 7824 7825 assign(op, get_gpr_w1(r3)); 7826 assign(result, binop(Iop_Sar32, mkexpr(op), unop(Iop_64to8, binop(Iop_And64, 7827 mkexpr(op2addr), mkU64(63))))); 7828 put_gpr_w1(r1, mkexpr(result)); 7829 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, result); 7830 7831 return "srak"; 7832 } 7833 7834 static const HChar * 7835 s390_irgen_SRAG(UChar r1, UChar r3, IRTemp op2addr) 7836 { 7837 IRTemp result = newTemp(Ity_I64); 7838 IRTemp op = newTemp(Ity_I64); 7839 7840 assign(op, get_gpr_dw0(r3)); 7841 assign(result, binop(Iop_Sar64, mkexpr(op), unop(Iop_64to8, binop(Iop_And64, 7842 mkexpr(op2addr), mkU64(63))))); 7843 put_gpr_dw0(r1, mkexpr(result)); 7844 s390_cc_thunk_putS(S390_CC_OP_LOAD_AND_TEST, result); 7845 7846 return "srag"; 7847 } 7848 7849 static const HChar * 7850 s390_irgen_SRL(UChar r1, IRTemp op2addr) 7851 { 7852 IRTemp op = newTemp(Ity_I32); 7853 7854 assign(op, get_gpr_w1(r1)); 7855 put_gpr_w1(r1, binop(Iop_Shr32, mkexpr(op), unop(Iop_64to8, binop(Iop_And64, 7856 mkexpr(op2addr), mkU64(63))))); 7857 7858 return "srl"; 7859 } 7860 7861 static const HChar * 7862 s390_irgen_SRLK(UChar r1, UChar r3, IRTemp op2addr) 7863 { 7864 IRTemp op = newTemp(Ity_I32); 7865 7866 assign(op, get_gpr_w1(r3)); 7867 put_gpr_w1(r1, binop(Iop_Shr32, mkexpr(op), unop(Iop_64to8, binop(Iop_And64, 7868 mkexpr(op2addr), mkU64(63))))); 7869 7870 return "srlk"; 7871 } 7872 7873 static const HChar * 7874 s390_irgen_SRLG(UChar r1, UChar r3, IRTemp op2addr) 7875 { 7876 IRTemp op = newTemp(Ity_I64); 7877 7878 assign(op, get_gpr_dw0(r3)); 7879 put_gpr_dw0(r1, binop(Iop_Shr64, mkexpr(op), unop(Iop_64to8, binop(Iop_And64, 7880 mkexpr(op2addr), mkU64(63))))); 7881 7882 return "srlg"; 7883 } 7884 7885 static const HChar * 7886 s390_irgen_ST(UChar r1, IRTemp op2addr) 7887 { 7888 store(mkexpr(op2addr), get_gpr_w1(r1)); 7889 7890 return "st"; 7891 } 7892 7893 static const HChar * 7894 s390_irgen_STY(UChar r1, IRTemp op2addr) 7895 { 7896 store(mkexpr(op2addr), get_gpr_w1(r1)); 7897 7898 return "sty"; 7899 } 7900 7901 static const HChar * 7902 s390_irgen_STG(UChar r1, IRTemp op2addr) 7903 { 7904 store(mkexpr(op2addr), get_gpr_dw0(r1)); 7905 7906 return "stg"; 7907 } 7908 7909 static const HChar * 7910 s390_irgen_STRL(UChar r1, UInt i2) 7911 { 7912 store(mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int)i2 << 1)), 7913 get_gpr_w1(r1)); 7914 7915 return "strl"; 7916 } 7917 7918 static const HChar * 7919 s390_irgen_STGRL(UChar r1, UInt i2) 7920 { 7921 store(mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int)i2 << 1)), 7922 get_gpr_dw0(r1)); 7923 7924 return "stgrl"; 7925 } 7926 7927 static const HChar * 7928 s390_irgen_STC(UChar r1, IRTemp op2addr) 7929 { 7930 store(mkexpr(op2addr), get_gpr_b7(r1)); 7931 7932 return "stc"; 7933 } 7934 7935 static const HChar * 7936 s390_irgen_STCY(UChar r1, IRTemp op2addr) 7937 { 7938 store(mkexpr(op2addr), get_gpr_b7(r1)); 7939 7940 return "stcy"; 7941 } 7942 7943 static const HChar * 7944 s390_irgen_STCH(UChar r1, IRTemp op2addr) 7945 { 7946 store(mkexpr(op2addr), get_gpr_b3(r1)); 7947 7948 return "stch"; 7949 } 7950 7951 static const HChar * 7952 s390_irgen_STCM(UChar r1, UChar r3, IRTemp op2addr) 7953 { 7954 UChar mask; 7955 UChar n; 7956 7957 mask = (UChar)r3; 7958 n = 0; 7959 if ((mask & 8) != 0) { 7960 store(mkexpr(op2addr), get_gpr_b4(r1)); 7961 n = n + 1; 7962 } 7963 if ((mask & 4) != 0) { 7964 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b5(r1)); 7965 n = n + 1; 7966 } 7967 if ((mask & 2) != 0) { 7968 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b6(r1)); 7969 n = n + 1; 7970 } 7971 if ((mask & 1) != 0) { 7972 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b7(r1)); 7973 } 7974 7975 return "stcm"; 7976 } 7977 7978 static const HChar * 7979 s390_irgen_STCMY(UChar r1, UChar r3, IRTemp op2addr) 7980 { 7981 UChar mask; 7982 UChar n; 7983 7984 mask = (UChar)r3; 7985 n = 0; 7986 if ((mask & 8) != 0) { 7987 store(mkexpr(op2addr), get_gpr_b4(r1)); 7988 n = n + 1; 7989 } 7990 if ((mask & 4) != 0) { 7991 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b5(r1)); 7992 n = n + 1; 7993 } 7994 if ((mask & 2) != 0) { 7995 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b6(r1)); 7996 n = n + 1; 7997 } 7998 if ((mask & 1) != 0) { 7999 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b7(r1)); 8000 } 8001 8002 return "stcmy"; 8003 } 8004 8005 static const HChar * 8006 s390_irgen_STCMH(UChar r1, UChar r3, IRTemp op2addr) 8007 { 8008 UChar mask; 8009 UChar n; 8010 8011 mask = (UChar)r3; 8012 n = 0; 8013 if ((mask & 8) != 0) { 8014 store(mkexpr(op2addr), get_gpr_b0(r1)); 8015 n = n + 1; 8016 } 8017 if ((mask & 4) != 0) { 8018 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b1(r1)); 8019 n = n + 1; 8020 } 8021 if ((mask & 2) != 0) { 8022 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b2(r1)); 8023 n = n + 1; 8024 } 8025 if ((mask & 1) != 0) { 8026 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(n)), get_gpr_b3(r1)); 8027 } 8028 8029 return "stcmh"; 8030 } 8031 8032 static const HChar * 8033 s390_irgen_STH(UChar r1, IRTemp op2addr) 8034 { 8035 store(mkexpr(op2addr), get_gpr_hw3(r1)); 8036 8037 return "sth"; 8038 } 8039 8040 static const HChar * 8041 s390_irgen_STHY(UChar r1, IRTemp op2addr) 8042 { 8043 store(mkexpr(op2addr), get_gpr_hw3(r1)); 8044 8045 return "sthy"; 8046 } 8047 8048 static const HChar * 8049 s390_irgen_STHRL(UChar r1, UInt i2) 8050 { 8051 store(mkU64(guest_IA_curr_instr + ((ULong)(Long)(Int)i2 << 1)), 8052 get_gpr_hw3(r1)); 8053 8054 return "sthrl"; 8055 } 8056 8057 static const HChar * 8058 s390_irgen_STHH(UChar r1, IRTemp op2addr) 8059 { 8060 store(mkexpr(op2addr), get_gpr_hw1(r1)); 8061 8062 return "sthh"; 8063 } 8064 8065 static const HChar * 8066 s390_irgen_STFH(UChar r1, IRTemp op2addr) 8067 { 8068 store(mkexpr(op2addr), get_gpr_w0(r1)); 8069 8070 return "stfh"; 8071 } 8072 8073 static const HChar * 8074 s390_irgen_STOC(UChar r1, IRTemp op2addr) 8075 { 8076 /* condition is checked in format handler */ 8077 store(mkexpr(op2addr), get_gpr_w1(r1)); 8078 8079 return "stoc"; 8080 } 8081 8082 static const HChar * 8083 s390_irgen_STOCG(UChar r1, IRTemp op2addr) 8084 { 8085 /* condition is checked in format handler */ 8086 store(mkexpr(op2addr), get_gpr_dw0(r1)); 8087 8088 return "stocg"; 8089 } 8090 8091 static const HChar * 8092 s390_irgen_STPQ(UChar r1, IRTemp op2addr) 8093 { 8094 store(mkexpr(op2addr), get_gpr_dw0(r1)); 8095 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(8)), get_gpr_dw0(r1 + 1)); 8096 8097 return "stpq"; 8098 } 8099 8100 static const HChar * 8101 s390_irgen_STRVH(UChar r1, IRTemp op2addr) 8102 { 8103 store(mkexpr(op2addr), get_gpr_b7(r1)); 8104 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(1)), get_gpr_b6(r1)); 8105 8106 return "strvh"; 8107 } 8108 8109 static const HChar * 8110 s390_irgen_STRV(UChar r1, IRTemp op2addr) 8111 { 8112 store(mkexpr(op2addr), get_gpr_b7(r1)); 8113 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(1)), get_gpr_b6(r1)); 8114 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(2)), get_gpr_b5(r1)); 8115 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(3)), get_gpr_b4(r1)); 8116 8117 return "strv"; 8118 } 8119 8120 static const HChar * 8121 s390_irgen_STRVG(UChar r1, IRTemp op2addr) 8122 { 8123 store(mkexpr(op2addr), get_gpr_b7(r1)); 8124 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(1)), get_gpr_b6(r1)); 8125 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(2)), get_gpr_b5(r1)); 8126 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(3)), get_gpr_b4(r1)); 8127 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(4)), get_gpr_b3(r1)); 8128 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(5)), get_gpr_b2(r1)); 8129 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(6)), get_gpr_b1(r1)); 8130 store(binop(Iop_Add64, mkexpr(op2addr), mkU64(7)), get_gpr_b0(r1)); 8131 8132 return "strvg"; 8133 } 8134 8135 static const HChar * 8136 s390_irgen_SR(UChar r1, UChar r2) 8137 { 8138 IRTemp op1 = newTemp(Ity_I32); 8139 IRTemp op2 = newTemp(Ity_I32); 8140 IRTemp result = newTemp(Ity_I32); 8141 8142 assign(op1, get_gpr_w1(r1)); 8143 assign(op2, get_gpr_w1(r2)); 8144 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2))); 8145 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, op1, op2); 8146 put_gpr_w1(r1, mkexpr(result)); 8147 8148 return "sr"; 8149 } 8150 8151 static const HChar * 8152 s390_irgen_SGR(UChar r1, UChar r2) 8153 { 8154 IRTemp op1 = newTemp(Ity_I64); 8155 IRTemp op2 = newTemp(Ity_I64); 8156 IRTemp result = newTemp(Ity_I64); 8157 8158 assign(op1, get_gpr_dw0(r1)); 8159 assign(op2, get_gpr_dw0(r2)); 8160 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2))); 8161 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_64, op1, op2); 8162 put_gpr_dw0(r1, mkexpr(result)); 8163 8164 return "sgr"; 8165 } 8166 8167 static const HChar * 8168 s390_irgen_SGFR(UChar r1, UChar r2) 8169 { 8170 IRTemp op1 = newTemp(Ity_I64); 8171 IRTemp op2 = newTemp(Ity_I64); 8172 IRTemp result = newTemp(Ity_I64); 8173 8174 assign(op1, get_gpr_dw0(r1)); 8175 assign(op2, unop(Iop_32Sto64, get_gpr_w1(r2))); 8176 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2))); 8177 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_64, op1, op2); 8178 put_gpr_dw0(r1, mkexpr(result)); 8179 8180 return "sgfr"; 8181 } 8182 8183 static const HChar * 8184 s390_irgen_SRK(UChar r3, UChar r1, UChar r2) 8185 { 8186 IRTemp op2 = newTemp(Ity_I32); 8187 IRTemp op3 = newTemp(Ity_I32); 8188 IRTemp result = newTemp(Ity_I32); 8189 8190 assign(op2, get_gpr_w1(r2)); 8191 assign(op3, get_gpr_w1(r3)); 8192 assign(result, binop(Iop_Sub32, mkexpr(op2), mkexpr(op3))); 8193 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, op2, op3); 8194 put_gpr_w1(r1, mkexpr(result)); 8195 8196 return "srk"; 8197 } 8198 8199 static const HChar * 8200 s390_irgen_SGRK(UChar r3, UChar r1, UChar r2) 8201 { 8202 IRTemp op2 = newTemp(Ity_I64); 8203 IRTemp op3 = newTemp(Ity_I64); 8204 IRTemp result = newTemp(Ity_I64); 8205 8206 assign(op2, get_gpr_dw0(r2)); 8207 assign(op3, get_gpr_dw0(r3)); 8208 assign(result, binop(Iop_Sub64, mkexpr(op2), mkexpr(op3))); 8209 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_64, op2, op3); 8210 put_gpr_dw0(r1, mkexpr(result)); 8211 8212 return "sgrk"; 8213 } 8214 8215 static const HChar * 8216 s390_irgen_S(UChar r1, IRTemp op2addr) 8217 { 8218 IRTemp op1 = newTemp(Ity_I32); 8219 IRTemp op2 = newTemp(Ity_I32); 8220 IRTemp result = newTemp(Ity_I32); 8221 8222 assign(op1, get_gpr_w1(r1)); 8223 assign(op2, load(Ity_I32, mkexpr(op2addr))); 8224 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2))); 8225 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, op1, op2); 8226 put_gpr_w1(r1, mkexpr(result)); 8227 8228 return "s"; 8229 } 8230 8231 static const HChar * 8232 s390_irgen_SY(UChar r1, IRTemp op2addr) 8233 { 8234 IRTemp op1 = newTemp(Ity_I32); 8235 IRTemp op2 = newTemp(Ity_I32); 8236 IRTemp result = newTemp(Ity_I32); 8237 8238 assign(op1, get_gpr_w1(r1)); 8239 assign(op2, load(Ity_I32, mkexpr(op2addr))); 8240 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2))); 8241 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, op1, op2); 8242 put_gpr_w1(r1, mkexpr(result)); 8243 8244 return "sy"; 8245 } 8246 8247 static const HChar * 8248 s390_irgen_SG(UChar r1, IRTemp op2addr) 8249 { 8250 IRTemp op1 = newTemp(Ity_I64); 8251 IRTemp op2 = newTemp(Ity_I64); 8252 IRTemp result = newTemp(Ity_I64); 8253 8254 assign(op1, get_gpr_dw0(r1)); 8255 assign(op2, load(Ity_I64, mkexpr(op2addr))); 8256 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2))); 8257 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_64, op1, op2); 8258 put_gpr_dw0(r1, mkexpr(result)); 8259 8260 return "sg"; 8261 } 8262 8263 static const HChar * 8264 s390_irgen_SGF(UChar r1, IRTemp op2addr) 8265 { 8266 IRTemp op1 = newTemp(Ity_I64); 8267 IRTemp op2 = newTemp(Ity_I64); 8268 IRTemp result = newTemp(Ity_I64); 8269 8270 assign(op1, get_gpr_dw0(r1)); 8271 assign(op2, unop(Iop_32Sto64, load(Ity_I32, mkexpr(op2addr)))); 8272 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2))); 8273 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_64, op1, op2); 8274 put_gpr_dw0(r1, mkexpr(result)); 8275 8276 return "sgf"; 8277 } 8278 8279 static const HChar * 8280 s390_irgen_SH(UChar r1, IRTemp op2addr) 8281 { 8282 IRTemp op1 = newTemp(Ity_I32); 8283 IRTemp op2 = newTemp(Ity_I32); 8284 IRTemp result = newTemp(Ity_I32); 8285 8286 assign(op1, get_gpr_w1(r1)); 8287 assign(op2, unop(Iop_16Sto32, load(Ity_I16, mkexpr(op2addr)))); 8288 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2))); 8289 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, op1, op2); 8290 put_gpr_w1(r1, mkexpr(result)); 8291 8292 return "sh"; 8293 } 8294 8295 static const HChar * 8296 s390_irgen_SHY(UChar r1, IRTemp op2addr) 8297 { 8298 IRTemp op1 = newTemp(Ity_I32); 8299 IRTemp op2 = newTemp(Ity_I32); 8300 IRTemp result = newTemp(Ity_I32); 8301 8302 assign(op1, get_gpr_w1(r1)); 8303 assign(op2, unop(Iop_16Sto32, load(Ity_I16, mkexpr(op2addr)))); 8304 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2))); 8305 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, op1, op2); 8306 put_gpr_w1(r1, mkexpr(result)); 8307 8308 return "shy"; 8309 } 8310 8311 static const HChar * 8312 s390_irgen_SHHHR(UChar r3 __attribute__((unused)), UChar r1, UChar r2) 8313 { 8314 IRTemp op2 = newTemp(Ity_I32); 8315 IRTemp op3 = newTemp(Ity_I32); 8316 IRTemp result = newTemp(Ity_I32); 8317 8318 assign(op2, get_gpr_w0(r1)); 8319 assign(op3, get_gpr_w0(r2)); 8320 assign(result, binop(Iop_Sub32, mkexpr(op2), mkexpr(op3))); 8321 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, op2, op3); 8322 put_gpr_w0(r1, mkexpr(result)); 8323 8324 return "shhhr"; 8325 } 8326 8327 static const HChar * 8328 s390_irgen_SHHLR(UChar r3 __attribute__((unused)), UChar r1, UChar r2) 8329 { 8330 IRTemp op2 = newTemp(Ity_I32); 8331 IRTemp op3 = newTemp(Ity_I32); 8332 IRTemp result = newTemp(Ity_I32); 8333 8334 assign(op2, get_gpr_w0(r1)); 8335 assign(op3, get_gpr_w1(r2)); 8336 assign(result, binop(Iop_Sub32, mkexpr(op2), mkexpr(op3))); 8337 s390_cc_thunk_putSS(S390_CC_OP_SIGNED_SUB_32, op2, op3); 8338 put_gpr_w0(r1, mkexpr(result)); 8339 8340 return "shhlr"; 8341 } 8342 8343 static const HChar * 8344 s390_irgen_SLR(UChar r1, UChar r2) 8345 { 8346 IRTemp op1 = newTemp(Ity_I32); 8347 IRTemp op2 = newTemp(Ity_I32); 8348 IRTemp result = newTemp(Ity_I32); 8349 8350 assign(op1, get_gpr_w1(r1)); 8351 assign(op2, get_gpr_w1(r2)); 8352 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2))); 8353 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_32, op1, op2); 8354 put_gpr_w1(r1, mkexpr(result)); 8355 8356 return "slr"; 8357 } 8358 8359 static const HChar * 8360 s390_irgen_SLGR(UChar r1, UChar r2) 8361 { 8362 IRTemp op1 = newTemp(Ity_I64); 8363 IRTemp op2 = newTemp(Ity_I64); 8364 IRTemp result = newTemp(Ity_I64); 8365 8366 assign(op1, get_gpr_dw0(r1)); 8367 assign(op2, get_gpr_dw0(r2)); 8368 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2))); 8369 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_64, op1, op2); 8370 put_gpr_dw0(r1, mkexpr(result)); 8371 8372 return "slgr"; 8373 } 8374 8375 static const HChar * 8376 s390_irgen_SLGFR(UChar r1, UChar r2) 8377 { 8378 IRTemp op1 = newTemp(Ity_I64); 8379 IRTemp op2 = newTemp(Ity_I64); 8380 IRTemp result = newTemp(Ity_I64); 8381 8382 assign(op1, get_gpr_dw0(r1)); 8383 assign(op2, unop(Iop_32Uto64, get_gpr_w1(r2))); 8384 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2))); 8385 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_64, op1, op2); 8386 put_gpr_dw0(r1, mkexpr(result)); 8387 8388 return "slgfr"; 8389 } 8390 8391 static const HChar * 8392 s390_irgen_SLRK(UChar r3, UChar r1, UChar r2) 8393 { 8394 IRTemp op2 = newTemp(Ity_I32); 8395 IRTemp op3 = newTemp(Ity_I32); 8396 IRTemp result = newTemp(Ity_I32); 8397 8398 assign(op2, get_gpr_w1(r2)); 8399 assign(op3, get_gpr_w1(r3)); 8400 assign(result, binop(Iop_Sub32, mkexpr(op2), mkexpr(op3))); 8401 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_32, op2, op3); 8402 put_gpr_w1(r1, mkexpr(result)); 8403 8404 return "slrk"; 8405 } 8406 8407 static const HChar * 8408 s390_irgen_SLGRK(UChar r3, UChar r1, UChar r2) 8409 { 8410 IRTemp op2 = newTemp(Ity_I64); 8411 IRTemp op3 = newTemp(Ity_I64); 8412 IRTemp result = newTemp(Ity_I64); 8413 8414 assign(op2, get_gpr_dw0(r2)); 8415 assign(op3, get_gpr_dw0(r3)); 8416 assign(result, binop(Iop_Sub64, mkexpr(op2), mkexpr(op3))); 8417 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_64, op2, op3); 8418 put_gpr_dw0(r1, mkexpr(result)); 8419 8420 return "slgrk"; 8421 } 8422 8423 static const HChar * 8424 s390_irgen_SL(UChar r1, IRTemp op2addr) 8425 { 8426 IRTemp op1 = newTemp(Ity_I32); 8427 IRTemp op2 = newTemp(Ity_I32); 8428 IRTemp result = newTemp(Ity_I32); 8429 8430 assign(op1, get_gpr_w1(r1)); 8431 assign(op2, load(Ity_I32, mkexpr(op2addr))); 8432 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2))); 8433 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_32, op1, op2); 8434 put_gpr_w1(r1, mkexpr(result)); 8435 8436 return "sl"; 8437 } 8438 8439 static const HChar * 8440 s390_irgen_SLY(UChar r1, IRTemp op2addr) 8441 { 8442 IRTemp op1 = newTemp(Ity_I32); 8443 IRTemp op2 = newTemp(Ity_I32); 8444 IRTemp result = newTemp(Ity_I32); 8445 8446 assign(op1, get_gpr_w1(r1)); 8447 assign(op2, load(Ity_I32, mkexpr(op2addr))); 8448 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2))); 8449 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_32, op1, op2); 8450 put_gpr_w1(r1, mkexpr(result)); 8451 8452 return "sly"; 8453 } 8454 8455 static const HChar * 8456 s390_irgen_SLG(UChar r1, IRTemp op2addr) 8457 { 8458 IRTemp op1 = newTemp(Ity_I64); 8459 IRTemp op2 = newTemp(Ity_I64); 8460 IRTemp result = newTemp(Ity_I64); 8461 8462 assign(op1, get_gpr_dw0(r1)); 8463 assign(op2, load(Ity_I64, mkexpr(op2addr))); 8464 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2))); 8465 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_64, op1, op2); 8466 put_gpr_dw0(r1, mkexpr(result)); 8467 8468 return "slg"; 8469 } 8470 8471 static const HChar * 8472 s390_irgen_SLGF(UChar r1, IRTemp op2addr) 8473 { 8474 IRTemp op1 = newTemp(Ity_I64); 8475 IRTemp op2 = newTemp(Ity_I64); 8476 IRTemp result = newTemp(Ity_I64); 8477 8478 assign(op1, get_gpr_dw0(r1)); 8479 assign(op2, unop(Iop_32Uto64, load(Ity_I32, mkexpr(op2addr)))); 8480 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2))); 8481 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_64, op1, op2); 8482 put_gpr_dw0(r1, mkexpr(result)); 8483 8484 return "slgf"; 8485 } 8486 8487 static const HChar * 8488 s390_irgen_SLFI(UChar r1, UInt i2) 8489 { 8490 IRTemp op1 = newTemp(Ity_I32); 8491 UInt op2; 8492 IRTemp result = newTemp(Ity_I32); 8493 8494 assign(op1, get_gpr_w1(r1)); 8495 op2 = i2; 8496 assign(result, binop(Iop_Sub32, mkexpr(op1), mkU32(op2))); 8497 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_32, op1, mktemp(Ity_I32, 8498 mkU32(op2))); 8499 put_gpr_w1(r1, mkexpr(result)); 8500 8501 return "slfi"; 8502 } 8503 8504 static const HChar * 8505 s390_irgen_SLGFI(UChar r1, UInt i2) 8506 { 8507 IRTemp op1 = newTemp(Ity_I64); 8508 ULong op2; 8509 IRTemp result = newTemp(Ity_I64); 8510 8511 assign(op1, get_gpr_dw0(r1)); 8512 op2 = (ULong)i2; 8513 assign(result, binop(Iop_Sub64, mkexpr(op1), mkU64(op2))); 8514 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_64, op1, mktemp(Ity_I64, 8515 mkU64(op2))); 8516 put_gpr_dw0(r1, mkexpr(result)); 8517 8518 return "slgfi"; 8519 } 8520 8521 static const HChar * 8522 s390_irgen_SLHHHR(UChar r3 __attribute__((unused)), UChar r1, UChar r2) 8523 { 8524 IRTemp op2 = newTemp(Ity_I32); 8525 IRTemp op3 = newTemp(Ity_I32); 8526 IRTemp result = newTemp(Ity_I32); 8527 8528 assign(op2, get_gpr_w0(r1)); 8529 assign(op3, get_gpr_w0(r2)); 8530 assign(result, binop(Iop_Sub32, mkexpr(op2), mkexpr(op3))); 8531 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_32, op2, op3); 8532 put_gpr_w0(r1, mkexpr(result)); 8533 8534 return "slhhhr"; 8535 } 8536 8537 static const HChar * 8538 s390_irgen_SLHHLR(UChar r3 __attribute__((unused)), UChar r1, UChar r2) 8539 { 8540 IRTemp op2 = newTemp(Ity_I32); 8541 IRTemp op3 = newTemp(Ity_I32); 8542 IRTemp result = newTemp(Ity_I32); 8543 8544 assign(op2, get_gpr_w0(r1)); 8545 assign(op3, get_gpr_w1(r2)); 8546 assign(result, binop(Iop_Sub32, mkexpr(op2), mkexpr(op3))); 8547 s390_cc_thunk_putZZ(S390_CC_OP_UNSIGNED_SUB_32, op2, op3); 8548 put_gpr_w0(r1, mkexpr(result)); 8549 8550 return "slhhlr"; 8551 } 8552 8553 static const HChar * 8554 s390_irgen_SLBR(UChar r1, UChar r2) 8555 { 8556 IRTemp op1 = newTemp(Ity_I32); 8557 IRTemp op2 = newTemp(Ity_I32); 8558 IRTemp result = newTemp(Ity_I32); 8559 IRTemp borrow_in = newTemp(Ity_I32); 8560 8561 assign(op1, get_gpr_w1(r1)); 8562 assign(op2, get_gpr_w1(r2)); 8563 assign(borrow_in, binop(Iop_Sub32, mkU32(1), binop(Iop_Shr32, 8564 s390_call_calculate_cc(), mkU8(1)))); 8565 assign(result, binop(Iop_Sub32, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2)), 8566 mkexpr(borrow_in))); 8567 s390_cc_thunk_putZZZ(S390_CC_OP_UNSIGNED_SUBB_32, op1, op2, borrow_in); 8568 put_gpr_w1(r1, mkexpr(result)); 8569 8570 return "slbr"; 8571 } 8572 8573 static const HChar * 8574 s390_irgen_SLBGR(UChar r1, UChar r2) 8575 { 8576 IRTemp op1 = newTemp(Ity_I64); 8577 IRTemp op2 = newTemp(Ity_I64); 8578 IRTemp result = newTemp(Ity_I64); 8579 IRTemp borrow_in = newTemp(Ity_I64); 8580 8581 assign(op1, get_gpr_dw0(r1)); 8582 assign(op2, get_gpr_dw0(r2)); 8583 assign(borrow_in, unop(Iop_32Uto64, binop(Iop_Sub32, mkU32(1), 8584 binop(Iop_Shr32, s390_call_calculate_cc(), mkU8(1))))); 8585 assign(result, binop(Iop_Sub64, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2)), 8586 mkexpr(borrow_in))); 8587 s390_cc_thunk_putZZZ(S390_CC_OP_UNSIGNED_SUBB_64, op1, op2, borrow_in); 8588 put_gpr_dw0(r1, mkexpr(result)); 8589 8590 return "slbgr"; 8591 } 8592 8593 static const HChar * 8594 s390_irgen_SLB(UChar r1, IRTemp op2addr) 8595 { 8596 IRTemp op1 = newTemp(Ity_I32); 8597 IRTemp op2 = newTemp(Ity_I32); 8598 IRTemp result = newTemp(Ity_I32); 8599 IRTemp borrow_in = newTemp(Ity_I32); 8600 8601 assign(op1, get_gpr_w1(r1)); 8602 assign(op2, load(Ity_I32, mkexpr(op2addr))); 8603 assign(borrow_in, binop(Iop_Sub32, mkU32(1), binop(Iop_Shr32, 8604 s390_call_calculate_cc(), mkU8(1)))); 8605 assign(result, binop(Iop_Sub32, binop(Iop_Sub32, mkexpr(op1), mkexpr(op2)), 8606 mkexpr(borrow_in))); 8607 s390_cc_thunk_putZZZ(S390_CC_OP_UNSIGNED_SUBB_32, op1, op2, borrow_in); 8608 put_gpr_w1(r1, mkexpr(result)); 8609 8610 return "slb"; 8611 } 8612 8613 static const HChar * 8614 s390_irgen_SLBG(UChar r1, IRTemp op2addr) 8615 { 8616 IRTemp op1 = newTemp(Ity_I64); 8617 IRTemp op2 = newTemp(Ity_I64); 8618 IRTemp result = newTemp(Ity_I64); 8619 IRTemp borrow_in = newTemp(Ity_I64); 8620 8621 assign(op1, get_gpr_dw0(r1)); 8622 assign(op2, load(Ity_I64, mkexpr(op2addr))); 8623 assign(borrow_in, unop(Iop_32Uto64, binop(Iop_Sub32, mkU32(1), 8624 binop(Iop_Shr32, s390_call_calculate_cc(), mkU8(1))))); 8625 assign(result, binop(Iop_Sub64, binop(Iop_Sub64, mkexpr(op1), mkexpr(op2)), 8626 mkexpr(borrow_in))); 8627 s390_cc_thunk_putZZZ(S390_CC_OP_UNSIGNED_SUBB_64, op1, op2, borrow_in); 8628 put_gpr_dw0(r1, mkexpr(result)); 8629 8630 return "slbg"; 8631 } 8632 8633 static const HChar * 8634 s390_irgen_SVC(UChar i) 8635 { 8636 IRTemp sysno = newTemp(Ity_I64); 8637 8638 if (i != 0) { 8639 assign(sysno, mkU64(i)); 8640 } else { 8641 assign(sysno, unop(Iop_32Uto64, get_gpr_w1(1))); 8642 } 8643 system_call(mkexpr(sysno)); 8644 8645 return "svc"; 8646 } 8647 8648 static const HChar * 8649 s390_irgen_TM(UChar i2, IRTemp op1addr) 8650 { 8651 UChar mask; 8652 IRTemp value = newTemp(Ity_I8); 8653 8654 mask = i2; 8655 assign(value, load(Ity_I8, mkexpr(op1addr))); 8656 s390_cc_thunk_putZZ(S390_CC_OP_TEST_UNDER_MASK_8, value, mktemp(Ity_I8, 8657 mkU8(mask))); 8658 8659 return "tm"; 8660 } 8661 8662 static const HChar * 8663 s390_irgen_TMY(UChar i2, IRTemp op1addr) 8664 { 8665 UChar mask; 8666 IRTemp value = newTemp(Ity_I8); 8667 8668 mask = i2; 8669 assign(value, load(Ity_I8, mkexpr(op1addr))); 8670 s390_cc_thunk_putZZ(S390_CC_OP_TEST_UNDER_MASK_8, value, mktemp(Ity_I8, 8671 mkU8(mask))); 8672 8673 return "tmy"; 8674 } 8675 8676 static const HChar * 8677 s390_irgen_TMHH(UChar r1, UShort i2) 8678 { 8679 UShort mask; 8680 IRTemp value = newTemp(Ity_I16); 8681 8682 mask = i2; 8683 assign(value, get_gpr_hw0(r1)); 8684 s390_cc_thunk_putZZ(S390_CC_OP_TEST_UNDER_MASK_16, value, mktemp(Ity_I16, 8685 mkU16(mask))); 8686 8687 return "tmhh"; 8688 } 8689 8690 static const HChar * 8691 s390_irgen_TMHL(UChar r1, UShort i2) 8692 { 8693 UShort mask; 8694 IRTemp value = newTemp(Ity_I16); 8695 8696 mask = i2; 8697 assign(value, get_gpr_hw1(r1)); 8698 s390_cc_thunk_putZZ(S390_CC_OP_TEST_UNDER_MASK_16, value, mktemp(Ity_I16, 8699 mkU16(mask))); 8700 8701 return "tmhl"; 8702 } 8703 8704 static const HChar * 8705 s390_irgen_TMLH(UChar r1, UShort i2) 8706 { 8707 UShort mask; 8708 IRTemp value = newTemp(Ity_I16); 8709 8710 mask = i2; 8711 assign(value, get_gpr_hw2(r1)); 8712 s390_cc_thunk_putZZ(S390_CC_OP_TEST_UNDER_MASK_16, value, mktemp(Ity_I16, 8713 mkU16(mask))); 8714 8715 return "tmlh"; 8716 } 8717 8718 static const HChar * 8719 s390_irgen_TMLL(UChar r1, UShort i2) 8720 { 8721 UShort mask; 8722 IRTemp value = newTemp(Ity_I16); 8723 8724 mask = i2; 8725 assign(value, get_gpr_hw3(r1)); 8726 s390_cc_thunk_putZZ(S390_CC_OP_TEST_UNDER_MASK_16, value, mktemp(Ity_I16, 8727 mkU16(mask))); 8728 8729 return "tmll"; 8730 } 8731 8732 static const HChar * 8733 s390_irgen_EFPC(UChar r1) 8734 { 8735 put_gpr_w1(r1, get_fpc_w0()); 8736 8737 return "efpc"; 8738 } 8739 8740 static const HChar * 8741 s390_irgen_LER(UChar r1, UChar r2) 8742 { 8743 put_fpr_w0(r1, get_fpr_w0(r2)); 8744 8745 return "ler"; 8746 } 8747 8748 static const HChar * 8749 s390_irgen_LDR(UChar r1, UChar r2) 8750 { 8751 put_fpr_dw0(r1, get_fpr_dw0(r2)); 8752 8753 return "ldr"; 8754 } 8755 8756 static const HChar * 8757 s390_irgen_LXR(UChar r1, UChar r2) 8758 { 8759 put_fpr_dw0(r1, get_fpr_dw0(r2)); 8760 put_fpr_dw0(r1 + 2, get_fpr_dw0(r2 + 2)); 8761 8762 return "lxr"; 8763 } 8764 8765 static const HChar * 8766 s390_irgen_LE(UChar r1, IRTemp op2addr) 8767 { 8768 put_fpr_w0(r1, load(Ity_F32, mkexpr(op2addr))); 8769 8770 return "le"; 8771 } 8772 8773 static const HChar * 8774 s390_irgen_LD(UChar r1, IRTemp op2addr) 8775 { 8776 put_fpr_dw0(r1, load(Ity_F64, mkexpr(op2addr))); 8777 8778 return "ld"; 8779 } 8780 8781 static const HChar * 8782 s390_irgen_LEY(UChar r1, IRTemp op2addr) 8783 { 8784 put_fpr_w0(r1, load(Ity_F32, mkexpr(op2addr))); 8785 8786 return "ley"; 8787 } 8788 8789 static const HChar * 8790 s390_irgen_LDY(UChar r1, IRTemp op2addr) 8791 { 8792 put_fpr_dw0(r1, load(Ity_F64, mkexpr(op2addr))); 8793 8794 return "ldy"; 8795 } 8796 8797 static const HChar * 8798 s390_irgen_LFPC(IRTemp op2addr) 8799 { 8800 put_fpc_w0(load(Ity_I32, mkexpr(op2addr))); 8801 8802 return "lfpc"; 8803 } 8804 8805 static const HChar * 8806 s390_irgen_LZER(UChar r1) 8807 { 8808 put_fpr_w0(r1, mkF32i(0x0)); 8809 8810 return "lzer"; 8811 } 8812 8813 static const HChar * 8814 s390_irgen_LZDR(UChar r1) 8815 { 8816 put_fpr_dw0(r1, mkF64i(0x0)); 8817 8818 return "lzdr"; 8819 } 8820 8821 static const HChar * 8822 s390_irgen_LZXR(UChar r1) 8823 { 8824 put_fpr_dw0(r1, mkF64i(0x0)); 8825 put_fpr_dw0(r1 + 2, mkF64i(0x0)); 8826 8827 return "lzxr"; 8828 } 8829 8830 static const HChar * 8831 s390_irgen_SRNM(IRTemp op2addr) 8832 { 8833 UInt input_mask, fpc_mask; 8834 8835 input_mask = 3; 8836 fpc_mask = s390_host_has_fpext ? 7 : 3; 8837 8838 put_fpc_w0(binop(Iop_Or32, 8839 binop(Iop_And32, get_fpc_w0(), mkU32(~fpc_mask)), 8840 binop(Iop_And32, unop(Iop_64to32, mkexpr(op2addr)), 8841 mkU32(input_mask)))); 8842 return "srnm"; 8843 } 8844 8845 static const HChar * 8846 s390_irgen_SRNMB(IRTemp op2addr) 8847 { 8848 UInt input_mask, fpc_mask; 8849 8850 input_mask = 7; 8851 fpc_mask = 7; 8852 8853 put_fpc_w0(binop(Iop_Or32, 8854 binop(Iop_And32, get_fpc_w0(), mkU32(~fpc_mask)), 8855 binop(Iop_And32, unop(Iop_64to32, mkexpr(op2addr)), 8856 mkU32(input_mask)))); 8857 return "srnmb"; 8858 } 8859 8860 static void 8861 s390_irgen_srnmb_wrapper(UChar b2, UShort d2) 8862 { 8863 if (b2 == 0) { /* This is the typical case */ 8864 if (d2 > 3) { 8865 if (s390_host_has_fpext && d2 == 7) { 8866 /* ok */ 8867 } else { 8868 emulation_warning(EmWarn_S390X_invalid_rounding); 8869 d2 = S390_FPC_BFP_ROUND_NEAREST_EVEN; 8870 } 8871 } 8872 } 8873 8874 s390_format_S_RD(s390_irgen_SRNMB, b2, d2); 8875 } 8876 8877 /* Wrapper to validate the parameter as in SRNMB is not required, as all 8878 the 8 values in op2addr[61:63] correspond to a valid DFP rounding mode */ 8879 static const HChar * 8880 s390_irgen_SRNMT(IRTemp op2addr) 8881 { 8882 UInt input_mask, fpc_mask; 8883 8884 input_mask = 7; 8885 fpc_mask = 0x70; 8886 8887 /* fpc[25:27] <- op2addr[61:63] 8888 fpc = (fpc & ~(0x70)) | ((op2addr & 7) << 4) */ 8889 put_fpc_w0(binop(Iop_Or32, binop(Iop_And32, get_fpc_w0(), mkU32(~fpc_mask)), 8890 binop(Iop_Shl32, binop(Iop_And32, 8891 unop(Iop_64to32, mkexpr(op2addr)), 8892 mkU32(input_mask)), mkU8(4)))); 8893 return "srnmt"; 8894 } 8895 8896 8897 static const HChar * 8898 s390_irgen_SFPC(UChar r1) 8899 { 8900 put_fpc_w0(get_gpr_w1(r1)); 8901 8902 return "sfpc"; 8903 } 8904 8905 static const HChar * 8906 s390_irgen_STE(UChar r1, IRTemp op2addr) 8907 { 8908 store(mkexpr(op2addr), get_fpr_w0(r1)); 8909 8910 return "ste"; 8911 } 8912 8913 static const HChar * 8914 s390_irgen_STD(UChar r1, IRTemp op2addr) 8915 { 8916 store(mkexpr(op2addr), get_fpr_dw0(r1)); 8917 8918 return "std"; 8919 } 8920 8921 static const HChar * 8922 s390_irgen_STEY(UChar r1, IRTemp op2addr) 8923 { 8924 store(mkexpr(op2addr), get_fpr_w0(r1)); 8925 8926 return "stey"; 8927 } 8928 8929 static const HChar * 8930 s390_irgen_STDY(UChar r1, IRTemp op2addr) 8931 { 8932 store(mkexpr(op2addr), get_fpr_dw0(r1)); 8933 8934 return "stdy"; 8935 } 8936 8937 static const HChar * 8938 s390_irgen_STFPC(IRTemp op2addr) 8939 { 8940 store(mkexpr(op2addr), get_fpc_w0()); 8941 8942 return "stfpc"; 8943 } 8944 8945 static const HChar * 8946 s390_irgen_AEBR(UChar r1, UChar r2) 8947 { 8948 IRTemp op1 = newTemp(Ity_F32); 8949 IRTemp op2 = newTemp(Ity_F32); 8950 IRTemp result = newTemp(Ity_F32); 8951 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 8952 8953 assign(op1, get_fpr_w0(r1)); 8954 assign(op2, get_fpr_w0(r2)); 8955 assign(result, triop(Iop_AddF32, mkexpr(rounding_mode), mkexpr(op1), 8956 mkexpr(op2))); 8957 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_32, result); 8958 put_fpr_w0(r1, mkexpr(result)); 8959 8960 return "aebr"; 8961 } 8962 8963 static const HChar * 8964 s390_irgen_ADBR(UChar r1, UChar r2) 8965 { 8966 IRTemp op1 = newTemp(Ity_F64); 8967 IRTemp op2 = newTemp(Ity_F64); 8968 IRTemp result = newTemp(Ity_F64); 8969 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 8970 8971 assign(op1, get_fpr_dw0(r1)); 8972 assign(op2, get_fpr_dw0(r2)); 8973 assign(result, triop(Iop_AddF64, mkexpr(rounding_mode), mkexpr(op1), 8974 mkexpr(op2))); 8975 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_64, result); 8976 put_fpr_dw0(r1, mkexpr(result)); 8977 8978 return "adbr"; 8979 } 8980 8981 static const HChar * 8982 s390_irgen_AEB(UChar r1, IRTemp op2addr) 8983 { 8984 IRTemp op1 = newTemp(Ity_F32); 8985 IRTemp op2 = newTemp(Ity_F32); 8986 IRTemp result = newTemp(Ity_F32); 8987 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 8988 8989 assign(op1, get_fpr_w0(r1)); 8990 assign(op2, load(Ity_F32, mkexpr(op2addr))); 8991 assign(result, triop(Iop_AddF32, mkexpr(rounding_mode), mkexpr(op1), 8992 mkexpr(op2))); 8993 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_32, result); 8994 put_fpr_w0(r1, mkexpr(result)); 8995 8996 return "aeb"; 8997 } 8998 8999 static const HChar * 9000 s390_irgen_ADB(UChar r1, IRTemp op2addr) 9001 { 9002 IRTemp op1 = newTemp(Ity_F64); 9003 IRTemp op2 = newTemp(Ity_F64); 9004 IRTemp result = newTemp(Ity_F64); 9005 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9006 9007 assign(op1, get_fpr_dw0(r1)); 9008 assign(op2, load(Ity_F64, mkexpr(op2addr))); 9009 assign(result, triop(Iop_AddF64, mkexpr(rounding_mode), mkexpr(op1), 9010 mkexpr(op2))); 9011 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_64, result); 9012 put_fpr_dw0(r1, mkexpr(result)); 9013 9014 return "adb"; 9015 } 9016 9017 static const HChar * 9018 s390_irgen_CEFBR(UChar m3, UChar m4 __attribute__((unused)), 9019 UChar r1, UChar r2) 9020 { 9021 if (! s390_host_has_fpext && m3 != S390_BFP_ROUND_PER_FPC) { 9022 emulation_warning(EmWarn_S390X_fpext_rounding); 9023 m3 = S390_BFP_ROUND_PER_FPC; 9024 } 9025 IRTemp op2 = newTemp(Ity_I32); 9026 9027 assign(op2, get_gpr_w1(r2)); 9028 put_fpr_w0(r1, binop(Iop_I32StoF32, mkexpr(encode_bfp_rounding_mode(m3)), 9029 mkexpr(op2))); 9030 9031 return "cefbr"; 9032 } 9033 9034 static const HChar * 9035 s390_irgen_CDFBR(UChar m3 __attribute__((unused)), 9036 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 9037 { 9038 IRTemp op2 = newTemp(Ity_I32); 9039 9040 assign(op2, get_gpr_w1(r2)); 9041 put_fpr_dw0(r1, unop(Iop_I32StoF64, mkexpr(op2))); 9042 9043 return "cdfbr"; 9044 } 9045 9046 static const HChar * 9047 s390_irgen_CEGBR(UChar m3, UChar m4 __attribute__((unused)), 9048 UChar r1, UChar r2) 9049 { 9050 if (! s390_host_has_fpext && m3 != S390_BFP_ROUND_PER_FPC) { 9051 emulation_warning(EmWarn_S390X_fpext_rounding); 9052 m3 = S390_BFP_ROUND_PER_FPC; 9053 } 9054 IRTemp op2 = newTemp(Ity_I64); 9055 9056 assign(op2, get_gpr_dw0(r2)); 9057 put_fpr_w0(r1, binop(Iop_I64StoF32, mkexpr(encode_bfp_rounding_mode(m3)), 9058 mkexpr(op2))); 9059 9060 return "cegbr"; 9061 } 9062 9063 static const HChar * 9064 s390_irgen_CDGBR(UChar m3, UChar m4 __attribute__((unused)), 9065 UChar r1, UChar r2) 9066 { 9067 if (! s390_host_has_fpext && m3 != S390_BFP_ROUND_PER_FPC) { 9068 emulation_warning(EmWarn_S390X_fpext_rounding); 9069 m3 = S390_BFP_ROUND_PER_FPC; 9070 } 9071 IRTemp op2 = newTemp(Ity_I64); 9072 9073 assign(op2, get_gpr_dw0(r2)); 9074 put_fpr_dw0(r1, binop(Iop_I64StoF64, mkexpr(encode_bfp_rounding_mode(m3)), 9075 mkexpr(op2))); 9076 9077 return "cdgbr"; 9078 } 9079 9080 static const HChar * 9081 s390_irgen_CELFBR(UChar m3, UChar m4 __attribute__((unused)), 9082 UChar r1, UChar r2) 9083 { 9084 if (! s390_host_has_fpext) { 9085 emulation_failure(EmFail_S390X_fpext); 9086 } else { 9087 IRTemp op2 = newTemp(Ity_I32); 9088 9089 assign(op2, get_gpr_w1(r2)); 9090 put_fpr_w0(r1, binop(Iop_I32UtoF32, mkexpr(encode_bfp_rounding_mode(m3)), 9091 mkexpr(op2))); 9092 } 9093 return "celfbr"; 9094 } 9095 9096 static const HChar * 9097 s390_irgen_CDLFBR(UChar m3 __attribute__((unused)), 9098 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 9099 { 9100 if (! s390_host_has_fpext) { 9101 emulation_failure(EmFail_S390X_fpext); 9102 } else { 9103 IRTemp op2 = newTemp(Ity_I32); 9104 9105 assign(op2, get_gpr_w1(r2)); 9106 put_fpr_dw0(r1, unop(Iop_I32UtoF64, mkexpr(op2))); 9107 } 9108 return "cdlfbr"; 9109 } 9110 9111 static const HChar * 9112 s390_irgen_CELGBR(UChar m3, UChar m4 __attribute__((unused)), 9113 UChar r1, UChar r2) 9114 { 9115 if (! s390_host_has_fpext) { 9116 emulation_failure(EmFail_S390X_fpext); 9117 } else { 9118 IRTemp op2 = newTemp(Ity_I64); 9119 9120 assign(op2, get_gpr_dw0(r2)); 9121 put_fpr_w0(r1, binop(Iop_I64UtoF32, mkexpr(encode_bfp_rounding_mode(m3)), 9122 mkexpr(op2))); 9123 } 9124 return "celgbr"; 9125 } 9126 9127 static const HChar * 9128 s390_irgen_CDLGBR(UChar m3, UChar m4 __attribute__((unused)), 9129 UChar r1, UChar r2) 9130 { 9131 if (! s390_host_has_fpext) { 9132 emulation_failure(EmFail_S390X_fpext); 9133 } else { 9134 IRTemp op2 = newTemp(Ity_I64); 9135 9136 assign(op2, get_gpr_dw0(r2)); 9137 put_fpr_dw0(r1, binop(Iop_I64UtoF64, 9138 mkexpr(encode_bfp_rounding_mode(m3)), 9139 mkexpr(op2))); 9140 } 9141 return "cdlgbr"; 9142 } 9143 9144 static const HChar * 9145 s390_irgen_CLFEBR(UChar m3, UChar m4 __attribute__((unused)), 9146 UChar r1, UChar r2) 9147 { 9148 if (! s390_host_has_fpext) { 9149 emulation_failure(EmFail_S390X_fpext); 9150 } else { 9151 IRTemp op = newTemp(Ity_F32); 9152 IRTemp result = newTemp(Ity_I32); 9153 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 9154 9155 assign(op, get_fpr_w0(r2)); 9156 assign(result, binop(Iop_F32toI32U, mkexpr(rounding_mode), 9157 mkexpr(op))); 9158 put_gpr_w1(r1, mkexpr(result)); 9159 s390_cc_thunk_putFZ(S390_CC_OP_BFP_32_TO_UINT_32, op, rounding_mode); 9160 } 9161 return "clfebr"; 9162 } 9163 9164 static const HChar * 9165 s390_irgen_CLFDBR(UChar m3, UChar m4 __attribute__((unused)), 9166 UChar r1, UChar r2) 9167 { 9168 if (! s390_host_has_fpext) { 9169 emulation_failure(EmFail_S390X_fpext); 9170 } else { 9171 IRTemp op = newTemp(Ity_F64); 9172 IRTemp result = newTemp(Ity_I32); 9173 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 9174 9175 assign(op, get_fpr_dw0(r2)); 9176 assign(result, binop(Iop_F64toI32U, mkexpr(rounding_mode), 9177 mkexpr(op))); 9178 put_gpr_w1(r1, mkexpr(result)); 9179 s390_cc_thunk_putFZ(S390_CC_OP_BFP_64_TO_UINT_32, op, rounding_mode); 9180 } 9181 return "clfdbr"; 9182 } 9183 9184 static const HChar * 9185 s390_irgen_CLGEBR(UChar m3, UChar m4 __attribute__((unused)), 9186 UChar r1, UChar r2) 9187 { 9188 if (! s390_host_has_fpext) { 9189 emulation_failure(EmFail_S390X_fpext); 9190 } else { 9191 IRTemp op = newTemp(Ity_F32); 9192 IRTemp result = newTemp(Ity_I64); 9193 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 9194 9195 assign(op, get_fpr_w0(r2)); 9196 assign(result, binop(Iop_F32toI64U, mkexpr(rounding_mode), 9197 mkexpr(op))); 9198 put_gpr_dw0(r1, mkexpr(result)); 9199 s390_cc_thunk_putFZ(S390_CC_OP_BFP_32_TO_UINT_64, op, rounding_mode); 9200 } 9201 return "clgebr"; 9202 } 9203 9204 static const HChar * 9205 s390_irgen_CLGDBR(UChar m3, UChar m4 __attribute__((unused)), 9206 UChar r1, UChar r2) 9207 { 9208 if (! s390_host_has_fpext) { 9209 emulation_failure(EmFail_S390X_fpext); 9210 } else { 9211 IRTemp op = newTemp(Ity_F64); 9212 IRTemp result = newTemp(Ity_I64); 9213 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 9214 9215 assign(op, get_fpr_dw0(r2)); 9216 assign(result, binop(Iop_F64toI64U, mkexpr(rounding_mode), 9217 mkexpr(op))); 9218 put_gpr_dw0(r1, mkexpr(result)); 9219 s390_cc_thunk_putFZ(S390_CC_OP_BFP_64_TO_UINT_64, op, rounding_mode); 9220 } 9221 return "clgdbr"; 9222 } 9223 9224 static const HChar * 9225 s390_irgen_CFEBR(UChar m3, UChar m4 __attribute__((unused)), 9226 UChar r1, UChar r2) 9227 { 9228 IRTemp op = newTemp(Ity_F32); 9229 IRTemp result = newTemp(Ity_I32); 9230 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 9231 9232 assign(op, get_fpr_w0(r2)); 9233 assign(result, binop(Iop_F32toI32S, mkexpr(rounding_mode), 9234 mkexpr(op))); 9235 put_gpr_w1(r1, mkexpr(result)); 9236 s390_cc_thunk_putFZ(S390_CC_OP_BFP_32_TO_INT_32, op, rounding_mode); 9237 9238 return "cfebr"; 9239 } 9240 9241 static const HChar * 9242 s390_irgen_CFDBR(UChar m3, UChar m4 __attribute__((unused)), 9243 UChar r1, UChar r2) 9244 { 9245 IRTemp op = newTemp(Ity_F64); 9246 IRTemp result = newTemp(Ity_I32); 9247 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 9248 9249 assign(op, get_fpr_dw0(r2)); 9250 assign(result, binop(Iop_F64toI32S, mkexpr(rounding_mode), 9251 mkexpr(op))); 9252 put_gpr_w1(r1, mkexpr(result)); 9253 s390_cc_thunk_putFZ(S390_CC_OP_BFP_64_TO_INT_32, op, rounding_mode); 9254 9255 return "cfdbr"; 9256 } 9257 9258 static const HChar * 9259 s390_irgen_CGEBR(UChar m3, UChar m4 __attribute__((unused)), 9260 UChar r1, UChar r2) 9261 { 9262 IRTemp op = newTemp(Ity_F32); 9263 IRTemp result = newTemp(Ity_I64); 9264 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 9265 9266 assign(op, get_fpr_w0(r2)); 9267 assign(result, binop(Iop_F32toI64S, mkexpr(rounding_mode), 9268 mkexpr(op))); 9269 put_gpr_dw0(r1, mkexpr(result)); 9270 s390_cc_thunk_putFZ(S390_CC_OP_BFP_32_TO_INT_64, op, rounding_mode); 9271 9272 return "cgebr"; 9273 } 9274 9275 static const HChar * 9276 s390_irgen_CGDBR(UChar m3, UChar m4 __attribute__((unused)), 9277 UChar r1, UChar r2) 9278 { 9279 IRTemp op = newTemp(Ity_F64); 9280 IRTemp result = newTemp(Ity_I64); 9281 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 9282 9283 assign(op, get_fpr_dw0(r2)); 9284 assign(result, binop(Iop_F64toI64S, mkexpr(rounding_mode), 9285 mkexpr(op))); 9286 put_gpr_dw0(r1, mkexpr(result)); 9287 s390_cc_thunk_putFZ(S390_CC_OP_BFP_64_TO_INT_64, op, rounding_mode); 9288 9289 return "cgdbr"; 9290 } 9291 9292 static const HChar * 9293 s390_irgen_DEBR(UChar r1, UChar r2) 9294 { 9295 IRTemp op1 = newTemp(Ity_F32); 9296 IRTemp op2 = newTemp(Ity_F32); 9297 IRTemp result = newTemp(Ity_F32); 9298 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9299 9300 assign(op1, get_fpr_w0(r1)); 9301 assign(op2, get_fpr_w0(r2)); 9302 assign(result, triop(Iop_DivF32, mkexpr(rounding_mode), mkexpr(op1), 9303 mkexpr(op2))); 9304 put_fpr_w0(r1, mkexpr(result)); 9305 9306 return "debr"; 9307 } 9308 9309 static const HChar * 9310 s390_irgen_DDBR(UChar r1, UChar r2) 9311 { 9312 IRTemp op1 = newTemp(Ity_F64); 9313 IRTemp op2 = newTemp(Ity_F64); 9314 IRTemp result = newTemp(Ity_F64); 9315 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9316 9317 assign(op1, get_fpr_dw0(r1)); 9318 assign(op2, get_fpr_dw0(r2)); 9319 assign(result, triop(Iop_DivF64, mkexpr(rounding_mode), mkexpr(op1), 9320 mkexpr(op2))); 9321 put_fpr_dw0(r1, mkexpr(result)); 9322 9323 return "ddbr"; 9324 } 9325 9326 static const HChar * 9327 s390_irgen_DEB(UChar r1, IRTemp op2addr) 9328 { 9329 IRTemp op1 = newTemp(Ity_F32); 9330 IRTemp op2 = newTemp(Ity_F32); 9331 IRTemp result = newTemp(Ity_F32); 9332 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9333 9334 assign(op1, get_fpr_w0(r1)); 9335 assign(op2, load(Ity_F32, mkexpr(op2addr))); 9336 assign(result, triop(Iop_DivF32, mkexpr(rounding_mode), mkexpr(op1), 9337 mkexpr(op2))); 9338 put_fpr_w0(r1, mkexpr(result)); 9339 9340 return "deb"; 9341 } 9342 9343 static const HChar * 9344 s390_irgen_DDB(UChar r1, IRTemp op2addr) 9345 { 9346 IRTemp op1 = newTemp(Ity_F64); 9347 IRTemp op2 = newTemp(Ity_F64); 9348 IRTemp result = newTemp(Ity_F64); 9349 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9350 9351 assign(op1, get_fpr_dw0(r1)); 9352 assign(op2, load(Ity_F64, mkexpr(op2addr))); 9353 assign(result, triop(Iop_DivF64, mkexpr(rounding_mode), mkexpr(op1), 9354 mkexpr(op2))); 9355 put_fpr_dw0(r1, mkexpr(result)); 9356 9357 return "ddb"; 9358 } 9359 9360 static const HChar * 9361 s390_irgen_LTEBR(UChar r1, UChar r2) 9362 { 9363 IRTemp result = newTemp(Ity_F32); 9364 9365 assign(result, get_fpr_w0(r2)); 9366 put_fpr_w0(r1, mkexpr(result)); 9367 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_32, result); 9368 9369 return "ltebr"; 9370 } 9371 9372 static const HChar * 9373 s390_irgen_LTDBR(UChar r1, UChar r2) 9374 { 9375 IRTemp result = newTemp(Ity_F64); 9376 9377 assign(result, get_fpr_dw0(r2)); 9378 put_fpr_dw0(r1, mkexpr(result)); 9379 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_64, result); 9380 9381 return "ltdbr"; 9382 } 9383 9384 static const HChar * 9385 s390_irgen_LCEBR(UChar r1, UChar r2) 9386 { 9387 IRTemp result = newTemp(Ity_F32); 9388 9389 assign(result, unop(Iop_NegF32, get_fpr_w0(r2))); 9390 put_fpr_w0(r1, mkexpr(result)); 9391 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_32, result); 9392 9393 return "lcebr"; 9394 } 9395 9396 static const HChar * 9397 s390_irgen_LCDBR(UChar r1, UChar r2) 9398 { 9399 IRTemp result = newTemp(Ity_F64); 9400 9401 assign(result, unop(Iop_NegF64, get_fpr_dw0(r2))); 9402 put_fpr_dw0(r1, mkexpr(result)); 9403 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_64, result); 9404 9405 return "lcdbr"; 9406 } 9407 9408 static const HChar * 9409 s390_irgen_LDEBR(UChar r1, UChar r2) 9410 { 9411 IRTemp op = newTemp(Ity_F32); 9412 9413 assign(op, get_fpr_w0(r2)); 9414 put_fpr_dw0(r1, unop(Iop_F32toF64, mkexpr(op))); 9415 9416 return "ldebr"; 9417 } 9418 9419 static const HChar * 9420 s390_irgen_LDEB(UChar r1, IRTemp op2addr) 9421 { 9422 IRTemp op = newTemp(Ity_F32); 9423 9424 assign(op, load(Ity_F32, mkexpr(op2addr))); 9425 put_fpr_dw0(r1, unop(Iop_F32toF64, mkexpr(op))); 9426 9427 return "ldeb"; 9428 } 9429 9430 static const HChar * 9431 s390_irgen_LEDBR(UChar m3, UChar m4 __attribute__((unused)), 9432 UChar r1, UChar r2) 9433 { 9434 if (! s390_host_has_fpext && m3 != S390_BFP_ROUND_PER_FPC) { 9435 emulation_warning(EmWarn_S390X_fpext_rounding); 9436 m3 = S390_BFP_ROUND_PER_FPC; 9437 } 9438 IRTemp op = newTemp(Ity_F64); 9439 9440 assign(op, get_fpr_dw0(r2)); 9441 put_fpr_w0(r1, binop(Iop_F64toF32, mkexpr(encode_bfp_rounding_mode(m3)), 9442 mkexpr(op))); 9443 9444 return "ledbr"; 9445 } 9446 9447 static const HChar * 9448 s390_irgen_MEEBR(UChar r1, UChar r2) 9449 { 9450 IRTemp op1 = newTemp(Ity_F32); 9451 IRTemp op2 = newTemp(Ity_F32); 9452 IRTemp result = newTemp(Ity_F32); 9453 IRRoundingMode rounding_mode = 9454 encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9455 9456 assign(op1, get_fpr_w0(r1)); 9457 assign(op2, get_fpr_w0(r2)); 9458 assign(result, triop(Iop_MulF32, mkexpr(rounding_mode), mkexpr(op1), 9459 mkexpr(op2))); 9460 put_fpr_w0(r1, mkexpr(result)); 9461 9462 return "meebr"; 9463 } 9464 9465 static const HChar * 9466 s390_irgen_MDBR(UChar r1, UChar r2) 9467 { 9468 IRTemp op1 = newTemp(Ity_F64); 9469 IRTemp op2 = newTemp(Ity_F64); 9470 IRTemp result = newTemp(Ity_F64); 9471 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9472 9473 assign(op1, get_fpr_dw0(r1)); 9474 assign(op2, get_fpr_dw0(r2)); 9475 assign(result, triop(Iop_MulF64, mkexpr(rounding_mode), mkexpr(op1), 9476 mkexpr(op2))); 9477 put_fpr_dw0(r1, mkexpr(result)); 9478 9479 return "mdbr"; 9480 } 9481 9482 static const HChar * 9483 s390_irgen_MEEB(UChar r1, IRTemp op2addr) 9484 { 9485 IRTemp op1 = newTemp(Ity_F32); 9486 IRTemp op2 = newTemp(Ity_F32); 9487 IRTemp result = newTemp(Ity_F32); 9488 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9489 9490 assign(op1, get_fpr_w0(r1)); 9491 assign(op2, load(Ity_F32, mkexpr(op2addr))); 9492 assign(result, triop(Iop_MulF32, mkexpr(rounding_mode), mkexpr(op1), 9493 mkexpr(op2))); 9494 put_fpr_w0(r1, mkexpr(result)); 9495 9496 return "meeb"; 9497 } 9498 9499 static const HChar * 9500 s390_irgen_MDB(UChar r1, IRTemp op2addr) 9501 { 9502 IRTemp op1 = newTemp(Ity_F64); 9503 IRTemp op2 = newTemp(Ity_F64); 9504 IRTemp result = newTemp(Ity_F64); 9505 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9506 9507 assign(op1, get_fpr_dw0(r1)); 9508 assign(op2, load(Ity_F64, mkexpr(op2addr))); 9509 assign(result, triop(Iop_MulF64, mkexpr(rounding_mode), mkexpr(op1), 9510 mkexpr(op2))); 9511 put_fpr_dw0(r1, mkexpr(result)); 9512 9513 return "mdb"; 9514 } 9515 9516 static const HChar * 9517 s390_irgen_SEBR(UChar r1, UChar r2) 9518 { 9519 IRTemp op1 = newTemp(Ity_F32); 9520 IRTemp op2 = newTemp(Ity_F32); 9521 IRTemp result = newTemp(Ity_F32); 9522 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9523 9524 assign(op1, get_fpr_w0(r1)); 9525 assign(op2, get_fpr_w0(r2)); 9526 assign(result, triop(Iop_SubF32, mkexpr(rounding_mode), mkexpr(op1), 9527 mkexpr(op2))); 9528 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_32, result); 9529 put_fpr_w0(r1, mkexpr(result)); 9530 9531 return "sebr"; 9532 } 9533 9534 static const HChar * 9535 s390_irgen_SDBR(UChar r1, UChar r2) 9536 { 9537 IRTemp op1 = newTemp(Ity_F64); 9538 IRTemp op2 = newTemp(Ity_F64); 9539 IRTemp result = newTemp(Ity_F64); 9540 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9541 9542 assign(op1, get_fpr_dw0(r1)); 9543 assign(op2, get_fpr_dw0(r2)); 9544 assign(result, triop(Iop_SubF64, mkexpr(rounding_mode), mkexpr(op1), 9545 mkexpr(op2))); 9546 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_64, result); 9547 put_fpr_dw0(r1, mkexpr(result)); 9548 9549 return "sdbr"; 9550 } 9551 9552 static const HChar * 9553 s390_irgen_SEB(UChar r1, IRTemp op2addr) 9554 { 9555 IRTemp op1 = newTemp(Ity_F32); 9556 IRTemp op2 = newTemp(Ity_F32); 9557 IRTemp result = newTemp(Ity_F32); 9558 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9559 9560 assign(op1, get_fpr_w0(r1)); 9561 assign(op2, load(Ity_F32, mkexpr(op2addr))); 9562 assign(result, triop(Iop_SubF32, mkexpr(rounding_mode), mkexpr(op1), 9563 mkexpr(op2))); 9564 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_32, result); 9565 put_fpr_w0(r1, mkexpr(result)); 9566 9567 return "seb"; 9568 } 9569 9570 static const HChar * 9571 s390_irgen_SDB(UChar r1, IRTemp op2addr) 9572 { 9573 IRTemp op1 = newTemp(Ity_F64); 9574 IRTemp op2 = newTemp(Ity_F64); 9575 IRTemp result = newTemp(Ity_F64); 9576 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 9577 9578 assign(op1, get_fpr_dw0(r1)); 9579 assign(op2, load(Ity_F64, mkexpr(op2addr))); 9580 assign(result, triop(Iop_SubF64, mkexpr(rounding_mode), mkexpr(op1), 9581 mkexpr(op2))); 9582 s390_cc_thunk_putF(S390_CC_OP_BFP_RESULT_64, result); 9583 put_fpr_dw0(r1, mkexpr(result)); 9584 9585 return "sdb"; 9586 } 9587 9588 static const HChar * 9589 s390_irgen_ADTRA(UChar r3, UChar m4, UChar r1, UChar r2) 9590 { 9591 if (! s390_host_has_dfp) { 9592 emulation_failure(EmFail_S390X_DFP_insn); 9593 } else { 9594 IRTemp op1 = newTemp(Ity_D64); 9595 IRTemp op2 = newTemp(Ity_D64); 9596 IRTemp result = newTemp(Ity_D64); 9597 IRTemp rounding_mode; 9598 9599 if (! s390_host_has_fpext && m4 != S390_DFP_ROUND_PER_FPC_0) { 9600 emulation_warning(EmWarn_S390X_fpext_rounding); 9601 m4 = S390_DFP_ROUND_PER_FPC_0; 9602 } 9603 9604 rounding_mode = encode_dfp_rounding_mode(m4); 9605 assign(op1, get_dpr_dw0(r2)); 9606 assign(op2, get_dpr_dw0(r3)); 9607 assign(result, triop(Iop_AddD64, mkexpr(rounding_mode), mkexpr(op1), 9608 mkexpr(op2))); 9609 s390_cc_thunk_putF(S390_CC_OP_DFP_RESULT_64, result); 9610 put_dpr_dw0(r1, mkexpr(result)); 9611 } 9612 return (m4 == 0) ? "adtr" : "adtra"; 9613 } 9614 9615 static const HChar * 9616 s390_irgen_AXTRA(UChar r3, UChar m4, UChar r1, UChar r2) 9617 { 9618 if (! s390_host_has_dfp) { 9619 emulation_failure(EmFail_S390X_DFP_insn); 9620 } else { 9621 IRTemp op1 = newTemp(Ity_D128); 9622 IRTemp op2 = newTemp(Ity_D128); 9623 IRTemp result = newTemp(Ity_D128); 9624 IRTemp rounding_mode; 9625 9626 if (! s390_host_has_fpext && m4 != S390_DFP_ROUND_PER_FPC_0) { 9627 emulation_warning(EmWarn_S390X_fpext_rounding); 9628 m4 = S390_DFP_ROUND_PER_FPC_0; 9629 } 9630 9631 rounding_mode = encode_dfp_rounding_mode(m4); 9632 assign(op1, get_dpr_pair(r2)); 9633 assign(op2, get_dpr_pair(r3)); 9634 assign(result, triop(Iop_AddD128, mkexpr(rounding_mode), mkexpr(op1), 9635 mkexpr(op2))); 9636 put_dpr_pair(r1, mkexpr(result)); 9637 9638 s390_cc_thunk_put1d128(S390_CC_OP_DFP_RESULT_128, result); 9639 } 9640 return (m4 == 0) ? "axtr" : "axtra"; 9641 } 9642 9643 static const HChar * 9644 s390_irgen_CDTR(UChar r1, UChar r2) 9645 { 9646 IRTemp op1 = newTemp(Ity_D64); 9647 IRTemp op2 = newTemp(Ity_D64); 9648 IRTemp cc_vex = newTemp(Ity_I32); 9649 IRTemp cc_s390 = newTemp(Ity_I32); 9650 9651 assign(op1, get_dpr_dw0(r1)); 9652 assign(op2, get_dpr_dw0(r2)); 9653 assign(cc_vex, binop(Iop_CmpD64, mkexpr(op1), mkexpr(op2))); 9654 9655 assign(cc_s390, convert_vex_dfpcc_to_s390(cc_vex)); 9656 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 9657 9658 return "cdtr"; 9659 } 9660 9661 static const HChar * 9662 s390_irgen_CXTR(UChar r1, UChar r2) 9663 { 9664 IRTemp op1 = newTemp(Ity_D128); 9665 IRTemp op2 = newTemp(Ity_D128); 9666 IRTemp cc_vex = newTemp(Ity_I32); 9667 IRTemp cc_s390 = newTemp(Ity_I32); 9668 9669 assign(op1, get_dpr_pair(r1)); 9670 assign(op2, get_dpr_pair(r2)); 9671 assign(cc_vex, binop(Iop_CmpD128, mkexpr(op1), mkexpr(op2))); 9672 9673 assign(cc_s390, convert_vex_dfpcc_to_s390(cc_vex)); 9674 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 9675 9676 return "cxtr"; 9677 } 9678 9679 static const HChar * 9680 s390_irgen_CDFTR(UChar m3 __attribute__((unused)), 9681 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 9682 { 9683 if (! s390_host_has_dfp) { 9684 emulation_failure(EmFail_S390X_DFP_insn); 9685 } else { 9686 if (! s390_host_has_fpext) { 9687 emulation_failure(EmFail_S390X_fpext); 9688 } else { 9689 IRTemp op2 = newTemp(Ity_I32); 9690 9691 assign(op2, get_gpr_w1(r2)); 9692 put_dpr_dw0(r1, unop(Iop_I32StoD64, mkexpr(op2))); 9693 } 9694 } 9695 return "cdftr"; 9696 } 9697 9698 static const HChar * 9699 s390_irgen_CXFTR(UChar m3 __attribute__((unused)), 9700 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 9701 { 9702 if (! s390_host_has_dfp) { 9703 emulation_failure(EmFail_S390X_DFP_insn); 9704 } else { 9705 if (! s390_host_has_fpext) { 9706 emulation_failure(EmFail_S390X_fpext); 9707 } else { 9708 IRTemp op2 = newTemp(Ity_I32); 9709 9710 assign(op2, get_gpr_w1(r2)); 9711 put_dpr_pair(r1, unop(Iop_I32StoD128, mkexpr(op2))); 9712 } 9713 } 9714 return "cxftr"; 9715 } 9716 9717 static const HChar * 9718 s390_irgen_CDGTRA(UChar m3, UChar m4 __attribute__((unused)), 9719 UChar r1, UChar r2) 9720 { 9721 if (! s390_host_has_dfp) { 9722 emulation_failure(EmFail_S390X_DFP_insn); 9723 } else { 9724 IRTemp op2 = newTemp(Ity_I64); 9725 9726 if (! s390_host_has_fpext && m3 != S390_DFP_ROUND_PER_FPC_0) { 9727 emulation_warning(EmWarn_S390X_fpext_rounding); 9728 m3 = S390_DFP_ROUND_PER_FPC_0; 9729 } 9730 9731 assign(op2, get_gpr_dw0(r2)); 9732 put_dpr_dw0(r1, binop(Iop_I64StoD64, mkexpr(encode_dfp_rounding_mode(m3)), 9733 mkexpr(op2))); 9734 } 9735 return (m3 == 0) ? "cdgtr" : "cdgtra"; 9736 } 9737 9738 static const HChar * 9739 s390_irgen_CXGTR(UChar m3 __attribute__((unused)), 9740 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 9741 { 9742 if (! s390_host_has_dfp) { 9743 emulation_failure(EmFail_S390X_DFP_insn); 9744 } else { 9745 IRTemp op2 = newTemp(Ity_I64); 9746 9747 /* No emulation warning here about an non-zero m3 on hosts without 9748 floating point extension facility. No rounding is performed */ 9749 9750 assign(op2, get_gpr_dw0(r2)); 9751 put_dpr_pair(r1, unop(Iop_I64StoD128, mkexpr(op2))); 9752 } 9753 return "cxgtr"; 9754 } 9755 9756 static const HChar * 9757 s390_irgen_CDLFTR(UChar m3 __attribute__((unused)), 9758 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 9759 { 9760 if (! s390_host_has_dfp) { 9761 emulation_failure(EmFail_S390X_DFP_insn); 9762 } else { 9763 if (! s390_host_has_fpext) { 9764 emulation_failure(EmFail_S390X_fpext); 9765 } else { 9766 IRTemp op2 = newTemp(Ity_I32); 9767 9768 assign(op2, get_gpr_w1(r2)); 9769 put_dpr_dw0(r1, unop(Iop_I32UtoD64, mkexpr(op2))); 9770 } 9771 } 9772 return "cdlftr"; 9773 } 9774 9775 static const HChar * 9776 s390_irgen_CXLFTR(UChar m3 __attribute__((unused)), 9777 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 9778 { 9779 if (! s390_host_has_dfp) { 9780 emulation_failure(EmFail_S390X_DFP_insn); 9781 } else { 9782 if (! s390_host_has_fpext) { 9783 emulation_failure(EmFail_S390X_fpext); 9784 } else { 9785 IRTemp op2 = newTemp(Ity_I32); 9786 9787 assign(op2, get_gpr_w1(r2)); 9788 put_dpr_pair(r1, unop(Iop_I32UtoD128, mkexpr(op2))); 9789 } 9790 } 9791 return "cxlftr"; 9792 } 9793 9794 static const HChar * 9795 s390_irgen_CDLGTR(UChar m3, UChar m4 __attribute__((unused)), 9796 UChar r1, UChar r2) 9797 { 9798 if (! s390_host_has_dfp) { 9799 emulation_failure(EmFail_S390X_DFP_insn); 9800 } else { 9801 if (! s390_host_has_fpext) { 9802 emulation_failure(EmFail_S390X_fpext); 9803 } else { 9804 IRTemp op2 = newTemp(Ity_I64); 9805 9806 assign(op2, get_gpr_dw0(r2)); 9807 put_dpr_dw0(r1, binop(Iop_I64UtoD64, 9808 mkexpr(encode_dfp_rounding_mode(m3)), 9809 mkexpr(op2))); 9810 } 9811 } 9812 return "cdlgtr"; 9813 } 9814 9815 static const HChar * 9816 s390_irgen_CXLGTR(UChar m3 __attribute__((unused)), 9817 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 9818 { 9819 if (! s390_host_has_dfp) { 9820 emulation_failure(EmFail_S390X_DFP_insn); 9821 } else { 9822 if (! s390_host_has_fpext) { 9823 emulation_failure(EmFail_S390X_fpext); 9824 } else { 9825 IRTemp op2 = newTemp(Ity_I64); 9826 9827 assign(op2, get_gpr_dw0(r2)); 9828 put_dpr_pair(r1, unop(Iop_I64UtoD128, mkexpr(op2))); 9829 } 9830 } 9831 return "cxlgtr"; 9832 } 9833 9834 static const HChar * 9835 s390_irgen_CFDTR(UChar m3, UChar m4 __attribute__((unused)), 9836 UChar r1, UChar r2) 9837 { 9838 if (! s390_host_has_dfp) { 9839 emulation_failure(EmFail_S390X_DFP_insn); 9840 } else { 9841 if (! s390_host_has_fpext) { 9842 emulation_failure(EmFail_S390X_fpext); 9843 } else { 9844 IRTemp op = newTemp(Ity_D64); 9845 IRTemp result = newTemp(Ity_I32); 9846 IRTemp rounding_mode = encode_dfp_rounding_mode(m3); 9847 9848 assign(op, get_dpr_dw0(r2)); 9849 assign(result, binop(Iop_D64toI32S, mkexpr(rounding_mode), 9850 mkexpr(op))); 9851 put_gpr_w1(r1, mkexpr(result)); 9852 s390_cc_thunk_putFZ(S390_CC_OP_DFP_64_TO_INT_32, op, rounding_mode); 9853 } 9854 } 9855 return "cfdtr"; 9856 } 9857 9858 static const HChar * 9859 s390_irgen_CFXTR(UChar m3, UChar m4 __attribute__((unused)), 9860 UChar r1, UChar r2) 9861 { 9862 if (! s390_host_has_dfp) { 9863 emulation_failure(EmFail_S390X_DFP_insn); 9864 } else { 9865 if (! s390_host_has_fpext) { 9866 emulation_failure(EmFail_S390X_fpext); 9867 } else { 9868 IRTemp op = newTemp(Ity_D128); 9869 IRTemp result = newTemp(Ity_I32); 9870 IRTemp rounding_mode = encode_dfp_rounding_mode(m3); 9871 9872 assign(op, get_dpr_pair(r2)); 9873 assign(result, binop(Iop_D128toI32S, mkexpr(rounding_mode), 9874 mkexpr(op))); 9875 put_gpr_w1(r1, mkexpr(result)); 9876 s390_cc_thunk_put1d128Z(S390_CC_OP_DFP_128_TO_INT_32, op, 9877 rounding_mode); 9878 } 9879 } 9880 return "cfxtr"; 9881 } 9882 9883 static const HChar * 9884 s390_irgen_CGDTR(UChar m3, UChar m4 __attribute__((unused)), 9885 UChar r1, UChar r2) 9886 { 9887 if (! s390_host_has_dfp) { 9888 emulation_failure(EmFail_S390X_DFP_insn); 9889 } else { 9890 IRTemp op = newTemp(Ity_D64); 9891 IRTemp rounding_mode = encode_dfp_rounding_mode(m3); 9892 9893 /* If fpext is not installed and m3 is in 1:7, 9894 rounding mode performed is unpredictable */ 9895 if (! s390_host_has_fpext && m3 > 0 && m3 < 8) { 9896 emulation_warning(EmWarn_S390X_fpext_rounding); 9897 m3 = S390_DFP_ROUND_PER_FPC_0; 9898 } 9899 9900 assign(op, get_dpr_dw0(r2)); 9901 put_gpr_dw0(r1, binop(Iop_D64toI64S, mkexpr(rounding_mode), mkexpr(op))); 9902 s390_cc_thunk_putFZ(S390_CC_OP_DFP_64_TO_INT_64, op, rounding_mode); 9903 } 9904 return "cgdtr"; 9905 } 9906 9907 static const HChar * 9908 s390_irgen_CGXTR(UChar m3, UChar m4 __attribute__((unused)), 9909 UChar r1, UChar r2) 9910 { 9911 if (! s390_host_has_dfp) { 9912 emulation_failure(EmFail_S390X_DFP_insn); 9913 } else { 9914 IRTemp op = newTemp(Ity_D128); 9915 IRTemp rounding_mode = encode_dfp_rounding_mode(m3); 9916 9917 /* If fpext is not installed and m3 is in 1:7, 9918 rounding mode performed is unpredictable */ 9919 if (! s390_host_has_fpext && m3 > 0 && m3 < 8) { 9920 emulation_warning(EmWarn_S390X_fpext_rounding); 9921 m3 = S390_DFP_ROUND_PER_FPC_0; 9922 } 9923 assign(op, get_dpr_pair(r2)); 9924 put_gpr_dw0(r1, binop(Iop_D128toI64S, mkexpr(rounding_mode), mkexpr(op))); 9925 s390_cc_thunk_put1d128Z(S390_CC_OP_DFP_128_TO_INT_64, op, rounding_mode); 9926 } 9927 return "cgxtr"; 9928 } 9929 9930 static const HChar * 9931 s390_irgen_CEDTR(UChar r1, UChar r2) 9932 { 9933 if (! s390_host_has_dfp) { 9934 emulation_failure(EmFail_S390X_DFP_insn); 9935 } else { 9936 IRTemp op1 = newTemp(Ity_D64); 9937 IRTemp op2 = newTemp(Ity_D64); 9938 IRTemp cc_vex = newTemp(Ity_I32); 9939 IRTemp cc_s390 = newTemp(Ity_I32); 9940 9941 assign(op1, get_dpr_dw0(r1)); 9942 assign(op2, get_dpr_dw0(r2)); 9943 assign(cc_vex, binop(Iop_CmpExpD64, mkexpr(op1), mkexpr(op2))); 9944 9945 assign(cc_s390, convert_vex_dfpcc_to_s390(cc_vex)); 9946 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 9947 } 9948 return "cedtr"; 9949 } 9950 9951 static const HChar * 9952 s390_irgen_CEXTR(UChar r1, UChar r2) 9953 { 9954 if (! s390_host_has_dfp) { 9955 emulation_failure(EmFail_S390X_DFP_insn); 9956 } else { 9957 IRTemp op1 = newTemp(Ity_D128); 9958 IRTemp op2 = newTemp(Ity_D128); 9959 IRTemp cc_vex = newTemp(Ity_I32); 9960 IRTemp cc_s390 = newTemp(Ity_I32); 9961 9962 assign(op1, get_dpr_pair(r1)); 9963 assign(op2, get_dpr_pair(r2)); 9964 assign(cc_vex, binop(Iop_CmpExpD128, mkexpr(op1), mkexpr(op2))); 9965 9966 assign(cc_s390, convert_vex_dfpcc_to_s390(cc_vex)); 9967 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 9968 } 9969 return "cextr"; 9970 } 9971 9972 static const HChar * 9973 s390_irgen_CLFDTR(UChar m3, UChar m4 __attribute__((unused)), 9974 UChar r1, UChar r2) 9975 { 9976 if (! s390_host_has_dfp) { 9977 emulation_failure(EmFail_S390X_DFP_insn); 9978 } else { 9979 if (! s390_host_has_fpext) { 9980 emulation_failure(EmFail_S390X_fpext); 9981 } else { 9982 IRTemp op = newTemp(Ity_D64); 9983 IRTemp result = newTemp(Ity_I32); 9984 IRTemp rounding_mode = encode_dfp_rounding_mode(m3); 9985 9986 assign(op, get_dpr_dw0(r2)); 9987 assign(result, binop(Iop_D64toI32U, mkexpr(rounding_mode), 9988 mkexpr(op))); 9989 put_gpr_w1(r1, mkexpr(result)); 9990 s390_cc_thunk_putFZ(S390_CC_OP_DFP_64_TO_UINT_32, op, rounding_mode); 9991 } 9992 } 9993 return "clfdtr"; 9994 } 9995 9996 static const HChar * 9997 s390_irgen_CLFXTR(UChar m3, UChar m4 __attribute__((unused)), 9998 UChar r1, UChar r2) 9999 { 10000 if (! s390_host_has_dfp) { 10001 emulation_failure(EmFail_S390X_DFP_insn); 10002 } else { 10003 if (! s390_host_has_fpext) { 10004 emulation_failure(EmFail_S390X_fpext); 10005 } else { 10006 IRTemp op = newTemp(Ity_D128); 10007 IRTemp result = newTemp(Ity_I32); 10008 IRTemp rounding_mode = encode_dfp_rounding_mode(m3); 10009 10010 assign(op, get_dpr_pair(r2)); 10011 assign(result, binop(Iop_D128toI32U, mkexpr(rounding_mode), 10012 mkexpr(op))); 10013 put_gpr_w1(r1, mkexpr(result)); 10014 s390_cc_thunk_put1d128Z(S390_CC_OP_DFP_128_TO_UINT_32, op, 10015 rounding_mode); 10016 } 10017 } 10018 return "clfxtr"; 10019 } 10020 10021 static const HChar * 10022 s390_irgen_CLGDTR(UChar m3, UChar m4 __attribute__((unused)), 10023 UChar r1, UChar r2) 10024 { 10025 if (! s390_host_has_dfp) { 10026 emulation_failure(EmFail_S390X_DFP_insn); 10027 } else { 10028 if (! s390_host_has_fpext) { 10029 emulation_failure(EmFail_S390X_fpext); 10030 } else { 10031 IRTemp op = newTemp(Ity_D64); 10032 IRTemp result = newTemp(Ity_I64); 10033 IRTemp rounding_mode = encode_dfp_rounding_mode(m3); 10034 10035 assign(op, get_dpr_dw0(r2)); 10036 assign(result, binop(Iop_D64toI64U, mkexpr(rounding_mode), 10037 mkexpr(op))); 10038 put_gpr_dw0(r1, mkexpr(result)); 10039 s390_cc_thunk_putFZ(S390_CC_OP_DFP_64_TO_UINT_64, op, rounding_mode); 10040 } 10041 } 10042 return "clgdtr"; 10043 } 10044 10045 static const HChar * 10046 s390_irgen_CLGXTR(UChar m3, UChar m4 __attribute__((unused)), 10047 UChar r1, UChar r2) 10048 { 10049 if (! s390_host_has_dfp) { 10050 emulation_failure(EmFail_S390X_DFP_insn); 10051 } else { 10052 if (! s390_host_has_fpext) { 10053 emulation_failure(EmFail_S390X_fpext); 10054 } else { 10055 IRTemp op = newTemp(Ity_D128); 10056 IRTemp result = newTemp(Ity_I64); 10057 IRTemp rounding_mode = encode_dfp_rounding_mode(m3); 10058 10059 assign(op, get_dpr_pair(r2)); 10060 assign(result, binop(Iop_D128toI64U, mkexpr(rounding_mode), 10061 mkexpr(op))); 10062 put_gpr_dw0(r1, mkexpr(result)); 10063 s390_cc_thunk_put1d128Z(S390_CC_OP_DFP_128_TO_UINT_64, op, 10064 rounding_mode); 10065 } 10066 } 10067 return "clgxtr"; 10068 } 10069 10070 static const HChar * 10071 s390_irgen_DDTRA(UChar r3, UChar m4, UChar r1, UChar r2) 10072 { 10073 if (! s390_host_has_dfp) { 10074 emulation_failure(EmFail_S390X_DFP_insn); 10075 } else { 10076 IRTemp op1 = newTemp(Ity_D64); 10077 IRTemp op2 = newTemp(Ity_D64); 10078 IRTemp result = newTemp(Ity_D64); 10079 IRTemp rounding_mode; 10080 10081 if (! s390_host_has_fpext && m4 != S390_DFP_ROUND_PER_FPC_0) { 10082 emulation_warning(EmWarn_S390X_fpext_rounding); 10083 m4 = S390_DFP_ROUND_PER_FPC_0; 10084 } 10085 10086 rounding_mode = encode_dfp_rounding_mode(m4); 10087 assign(op1, get_dpr_dw0(r2)); 10088 assign(op2, get_dpr_dw0(r3)); 10089 assign(result, triop(Iop_DivD64, mkexpr(rounding_mode), mkexpr(op1), 10090 mkexpr(op2))); 10091 put_dpr_dw0(r1, mkexpr(result)); 10092 } 10093 return (m4 == 0) ? "ddtr" : "ddtra"; 10094 } 10095 10096 static const HChar * 10097 s390_irgen_DXTRA(UChar r3, UChar m4, UChar r1, UChar r2) 10098 { 10099 if (! s390_host_has_dfp) { 10100 emulation_failure(EmFail_S390X_DFP_insn); 10101 } else { 10102 IRTemp op1 = newTemp(Ity_D128); 10103 IRTemp op2 = newTemp(Ity_D128); 10104 IRTemp result = newTemp(Ity_D128); 10105 IRTemp rounding_mode; 10106 10107 if (! s390_host_has_fpext && m4 != S390_DFP_ROUND_PER_FPC_0) { 10108 emulation_warning(EmWarn_S390X_fpext_rounding); 10109 m4 = S390_DFP_ROUND_PER_FPC_0; 10110 } 10111 10112 rounding_mode = encode_dfp_rounding_mode(m4); 10113 assign(op1, get_dpr_pair(r2)); 10114 assign(op2, get_dpr_pair(r3)); 10115 assign(result, triop(Iop_DivD128, mkexpr(rounding_mode), mkexpr(op1), 10116 mkexpr(op2))); 10117 put_dpr_pair(r1, mkexpr(result)); 10118 } 10119 return (m4 == 0) ? "dxtr" : "dxtra"; 10120 } 10121 10122 static const HChar * 10123 s390_irgen_EEDTR(UChar r1, UChar r2) 10124 { 10125 if (! s390_host_has_dfp) { 10126 emulation_failure(EmFail_S390X_DFP_insn); 10127 } else { 10128 put_gpr_dw0(r1, unop(Iop_ExtractExpD64, get_dpr_dw0(r2))); 10129 } 10130 return "eedtr"; 10131 } 10132 10133 static const HChar * 10134 s390_irgen_EEXTR(UChar r1, UChar r2) 10135 { 10136 if (! s390_host_has_dfp) { 10137 emulation_failure(EmFail_S390X_DFP_insn); 10138 } else { 10139 put_gpr_dw0(r1, unop(Iop_ExtractExpD128, get_dpr_pair(r2))); 10140 } 10141 return "eextr"; 10142 } 10143 10144 static const HChar * 10145 s390_irgen_ESDTR(UChar r1, UChar r2) 10146 { 10147 if (! s390_host_has_dfp) { 10148 emulation_failure(EmFail_S390X_DFP_insn); 10149 } else { 10150 put_gpr_dw0(r1, unop(Iop_ExtractSigD64, get_dpr_dw0(r2))); 10151 } 10152 return "esdtr"; 10153 } 10154 10155 static const HChar * 10156 s390_irgen_ESXTR(UChar r1, UChar r2) 10157 { 10158 if (! s390_host_has_dfp) { 10159 emulation_failure(EmFail_S390X_DFP_insn); 10160 } else { 10161 put_gpr_dw0(r1, unop(Iop_ExtractSigD128, get_dpr_pair(r2))); 10162 } 10163 return "esxtr"; 10164 } 10165 10166 static const HChar * 10167 s390_irgen_IEDTR(UChar r3, UChar r1, UChar r2) 10168 { 10169 if (! s390_host_has_dfp) { 10170 emulation_failure(EmFail_S390X_DFP_insn); 10171 } else { 10172 IRTemp op1 = newTemp(Ity_I64); 10173 IRTemp op2 = newTemp(Ity_D64); 10174 IRTemp result = newTemp(Ity_D64); 10175 10176 assign(op1, get_gpr_dw0(r2)); 10177 assign(op2, get_dpr_dw0(r3)); 10178 assign(result, binop(Iop_InsertExpD64, mkexpr(op1), mkexpr(op2))); 10179 put_dpr_dw0(r1, mkexpr(result)); 10180 } 10181 return "iedtr"; 10182 } 10183 10184 static const HChar * 10185 s390_irgen_IEXTR(UChar r3, UChar r1, UChar r2) 10186 { 10187 if (! s390_host_has_dfp) { 10188 emulation_failure(EmFail_S390X_DFP_insn); 10189 } else { 10190 IRTemp op1 = newTemp(Ity_I64); 10191 IRTemp op2 = newTemp(Ity_D128); 10192 IRTemp result = newTemp(Ity_D128); 10193 10194 assign(op1, get_gpr_dw0(r2)); 10195 assign(op2, get_dpr_pair(r3)); 10196 assign(result, binop(Iop_InsertExpD128, mkexpr(op1), mkexpr(op2))); 10197 put_dpr_pair(r1, mkexpr(result)); 10198 } 10199 return "iextr"; 10200 } 10201 10202 static const HChar * 10203 s390_irgen_LDETR(UChar m4 __attribute__((unused)), UChar r1, UChar r2) 10204 { 10205 if (! s390_host_has_dfp) { 10206 emulation_failure(EmFail_S390X_DFP_insn); 10207 } else { 10208 IRTemp op = newTemp(Ity_D32); 10209 10210 assign(op, get_dpr_w0(r2)); 10211 put_dpr_dw0(r1, unop(Iop_D32toD64, mkexpr(op))); 10212 } 10213 return "ldetr"; 10214 } 10215 10216 static const HChar * 10217 s390_irgen_LXDTR(UChar m4 __attribute__((unused)), UChar r1, UChar r2) 10218 { 10219 IRTemp op = newTemp(Ity_D64); 10220 10221 assign(op, get_dpr_dw0(r2)); 10222 put_dpr_pair(r1, unop(Iop_D64toD128, mkexpr(op))); 10223 10224 return "lxdtr"; 10225 } 10226 10227 static const HChar * 10228 s390_irgen_LDXTR(UChar m3, UChar m4 __attribute__((unused)), 10229 UChar r1, UChar r2) 10230 { 10231 if (! s390_host_has_dfp) { 10232 emulation_failure(EmFail_S390X_DFP_insn); 10233 } else { 10234 /* If fpext is not installed and m3 is in 1:7, 10235 rounding mode performed is unpredictable */ 10236 if (! s390_host_has_fpext && m3 > 0 && m3 < 8) { 10237 emulation_warning(EmWarn_S390X_fpext_rounding); 10238 m3 = S390_DFP_ROUND_PER_FPC_0; 10239 } 10240 IRTemp result = newTemp(Ity_D64); 10241 10242 assign(result, binop(Iop_D128toD64, mkexpr(encode_dfp_rounding_mode(m3)), 10243 get_dpr_pair(r2))); 10244 put_dpr_dw0(r1, mkexpr(result)); 10245 } 10246 return "ldxtr"; 10247 } 10248 10249 static const HChar * 10250 s390_irgen_LEDTR(UChar m3, UChar m4 __attribute__((unused)), 10251 UChar r1, UChar r2) 10252 { 10253 if (! s390_host_has_dfp) { 10254 emulation_failure(EmFail_S390X_DFP_insn); 10255 } else { 10256 /* If fpext is not installed and m3 is in 1:7, 10257 rounding mode performed is unpredictable */ 10258 if (! s390_host_has_fpext && m3 > 0 && m3 < 8) { 10259 emulation_warning(EmWarn_S390X_fpext_rounding); 10260 m3 = S390_DFP_ROUND_PER_FPC_0; 10261 } 10262 IRTemp op = newTemp(Ity_D64); 10263 10264 assign(op, get_dpr_dw0(r2)); 10265 put_dpr_w0(r1, binop(Iop_D64toD32, mkexpr(encode_dfp_rounding_mode(m3)), 10266 mkexpr(op))); 10267 } 10268 return "ledtr"; 10269 } 10270 10271 static const HChar * 10272 s390_irgen_LTDTR(UChar r1, UChar r2) 10273 { 10274 IRTemp result = newTemp(Ity_D64); 10275 10276 assign(result, get_dpr_dw0(r2)); 10277 put_dpr_dw0(r1, mkexpr(result)); 10278 s390_cc_thunk_putF(S390_CC_OP_DFP_RESULT_64, result); 10279 10280 return "ltdtr"; 10281 } 10282 10283 static const HChar * 10284 s390_irgen_LTXTR(UChar r1, UChar r2) 10285 { 10286 IRTemp result = newTemp(Ity_D128); 10287 10288 assign(result, get_dpr_pair(r2)); 10289 put_dpr_pair(r1, mkexpr(result)); 10290 s390_cc_thunk_put1d128(S390_CC_OP_DFP_RESULT_128, result); 10291 10292 return "ltxtr"; 10293 } 10294 10295 static const HChar * 10296 s390_irgen_MDTRA(UChar r3, UChar m4, UChar r1, UChar r2) 10297 { 10298 if (! s390_host_has_dfp) { 10299 emulation_failure(EmFail_S390X_DFP_insn); 10300 } else { 10301 IRTemp op1 = newTemp(Ity_D64); 10302 IRTemp op2 = newTemp(Ity_D64); 10303 IRTemp result = newTemp(Ity_D64); 10304 IRTemp rounding_mode; 10305 10306 if (! s390_host_has_fpext && m4 != S390_DFP_ROUND_PER_FPC_0) { 10307 emulation_warning(EmWarn_S390X_fpext_rounding); 10308 m4 = S390_DFP_ROUND_PER_FPC_0; 10309 } 10310 10311 rounding_mode = encode_dfp_rounding_mode(m4); 10312 assign(op1, get_dpr_dw0(r2)); 10313 assign(op2, get_dpr_dw0(r3)); 10314 assign(result, triop(Iop_MulD64, mkexpr(rounding_mode), mkexpr(op1), 10315 mkexpr(op2))); 10316 put_dpr_dw0(r1, mkexpr(result)); 10317 } 10318 return (m4 == 0) ? "mdtr" : "mdtra"; 10319 } 10320 10321 static const HChar * 10322 s390_irgen_MXTRA(UChar r3, UChar m4, UChar r1, UChar r2) 10323 { 10324 if (! s390_host_has_dfp) { 10325 emulation_failure(EmFail_S390X_DFP_insn); 10326 } else { 10327 IRTemp op1 = newTemp(Ity_D128); 10328 IRTemp op2 = newTemp(Ity_D128); 10329 IRTemp result = newTemp(Ity_D128); 10330 IRTemp rounding_mode; 10331 10332 if (! s390_host_has_fpext && m4 != S390_DFP_ROUND_PER_FPC_0) { 10333 emulation_warning(EmWarn_S390X_fpext_rounding); 10334 m4 = S390_DFP_ROUND_PER_FPC_0; 10335 } 10336 10337 rounding_mode = encode_dfp_rounding_mode(m4); 10338 assign(op1, get_dpr_pair(r2)); 10339 assign(op2, get_dpr_pair(r3)); 10340 assign(result, triop(Iop_MulD128, mkexpr(rounding_mode), mkexpr(op1), 10341 mkexpr(op2))); 10342 put_dpr_pair(r1, mkexpr(result)); 10343 } 10344 return (m4 == 0) ? "mxtr" : "mxtra"; 10345 } 10346 10347 static const HChar * 10348 s390_irgen_QADTR(UChar r3, UChar m4, UChar r1, UChar r2) 10349 { 10350 if (! s390_host_has_dfp) { 10351 emulation_failure(EmFail_S390X_DFP_insn); 10352 } else { 10353 IRTemp op1 = newTemp(Ity_D64); 10354 IRTemp op2 = newTemp(Ity_D64); 10355 IRTemp result = newTemp(Ity_D64); 10356 IRTemp rounding_mode; 10357 10358 /* If fpext is not installed and m4 is in 1:7, 10359 rounding mode performed is unpredictable */ 10360 if (! s390_host_has_fpext && m4 > 0 && m4 < 8) { 10361 emulation_warning(EmWarn_S390X_fpext_rounding); 10362 m4 = S390_DFP_ROUND_PER_FPC_0; 10363 } 10364 10365 rounding_mode = encode_dfp_rounding_mode(m4); 10366 assign(op1, get_dpr_dw0(r2)); 10367 assign(op2, get_dpr_dw0(r3)); 10368 assign(result, triop(Iop_QuantizeD64, mkexpr(rounding_mode), mkexpr(op1), 10369 mkexpr(op2))); 10370 put_dpr_dw0(r1, mkexpr(result)); 10371 } 10372 return "qadtr"; 10373 } 10374 10375 static const HChar * 10376 s390_irgen_QAXTR(UChar r3, UChar m4, UChar r1, UChar r2) 10377 { 10378 if (! s390_host_has_dfp) { 10379 emulation_failure(EmFail_S390X_DFP_insn); 10380 } else { 10381 IRTemp op1 = newTemp(Ity_D128); 10382 IRTemp op2 = newTemp(Ity_D128); 10383 IRTemp result = newTemp(Ity_D128); 10384 IRTemp rounding_mode; 10385 10386 /* If fpext is not installed and m4 is in 1:7, 10387 rounding mode performed is unpredictable */ 10388 if (! s390_host_has_fpext && m4 > 0 && m4 < 8) { 10389 emulation_warning(EmWarn_S390X_fpext_rounding); 10390 m4 = S390_DFP_ROUND_PER_FPC_0; 10391 } 10392 10393 rounding_mode = encode_dfp_rounding_mode(m4); 10394 assign(op1, get_dpr_pair(r2)); 10395 assign(op2, get_dpr_pair(r3)); 10396 assign(result, triop(Iop_QuantizeD128, mkexpr(rounding_mode), mkexpr(op1), 10397 mkexpr(op2))); 10398 put_dpr_pair(r1, mkexpr(result)); 10399 } 10400 return "qaxtr"; 10401 } 10402 10403 static const HChar * 10404 s390_irgen_RRDTR(UChar r3, UChar m4, UChar r1, UChar r2) 10405 { 10406 if (! s390_host_has_dfp) { 10407 emulation_failure(EmFail_S390X_DFP_insn); 10408 } else { 10409 IRTemp op1 = newTemp(Ity_I8); 10410 IRTemp op2 = newTemp(Ity_D64); 10411 IRTemp result = newTemp(Ity_D64); 10412 IRTemp rounding_mode; 10413 10414 /* If fpext is not installed and m4 is in 1:7, 10415 rounding mode performed is unpredictable */ 10416 if (! s390_host_has_fpext && m4 > 0 && m4 < 8) { 10417 emulation_warning(EmWarn_S390X_fpext_rounding); 10418 m4 = S390_DFP_ROUND_PER_FPC_0; 10419 } 10420 10421 rounding_mode = encode_dfp_rounding_mode(m4); 10422 assign(op1, get_gpr_b7(r2)); 10423 assign(op2, get_dpr_dw0(r3)); 10424 assign(result, triop(Iop_SignificanceRoundD64, mkexpr(rounding_mode), 10425 mkexpr(op1), mkexpr(op2))); 10426 put_dpr_dw0(r1, mkexpr(result)); 10427 } 10428 return "rrdtr"; 10429 } 10430 10431 static const HChar * 10432 s390_irgen_RRXTR(UChar r3, UChar m4, UChar r1, UChar r2) 10433 { 10434 if (! s390_host_has_dfp) { 10435 emulation_failure(EmFail_S390X_DFP_insn); 10436 } else { 10437 IRTemp op1 = newTemp(Ity_I8); 10438 IRTemp op2 = newTemp(Ity_D128); 10439 IRTemp result = newTemp(Ity_D128); 10440 IRTemp rounding_mode; 10441 10442 /* If fpext is not installed and m4 is in 1:7, 10443 rounding mode performed is unpredictable */ 10444 if (! s390_host_has_fpext && m4 > 0 && m4 < 8) { 10445 emulation_warning(EmWarn_S390X_fpext_rounding); 10446 m4 = S390_DFP_ROUND_PER_FPC_0; 10447 } 10448 10449 rounding_mode = encode_dfp_rounding_mode(m4); 10450 assign(op1, get_gpr_b7(r2)); 10451 assign(op2, get_dpr_pair(r3)); 10452 assign(result, triop(Iop_SignificanceRoundD128, mkexpr(rounding_mode), 10453 mkexpr(op1), mkexpr(op2))); 10454 put_dpr_pair(r1, mkexpr(result)); 10455 } 10456 return "rrxtr"; 10457 } 10458 10459 static const HChar * 10460 s390_irgen_SDTRA(UChar r3, UChar m4, UChar r1, UChar r2) 10461 { 10462 if (! s390_host_has_dfp) { 10463 emulation_failure(EmFail_S390X_DFP_insn); 10464 } else { 10465 IRTemp op1 = newTemp(Ity_D64); 10466 IRTemp op2 = newTemp(Ity_D64); 10467 IRTemp result = newTemp(Ity_D64); 10468 IRTemp rounding_mode; 10469 10470 if (! s390_host_has_fpext && m4 != S390_DFP_ROUND_PER_FPC_0) { 10471 emulation_warning(EmWarn_S390X_fpext_rounding); 10472 m4 = S390_DFP_ROUND_PER_FPC_0; 10473 } 10474 10475 rounding_mode = encode_dfp_rounding_mode(m4); 10476 assign(op1, get_dpr_dw0(r2)); 10477 assign(op2, get_dpr_dw0(r3)); 10478 assign(result, triop(Iop_SubD64, mkexpr(rounding_mode), mkexpr(op1), 10479 mkexpr(op2))); 10480 s390_cc_thunk_putF(S390_CC_OP_DFP_RESULT_64, result); 10481 put_dpr_dw0(r1, mkexpr(result)); 10482 } 10483 return (m4 == 0) ? "sdtr" : "sdtra"; 10484 } 10485 10486 static const HChar * 10487 s390_irgen_SXTRA(UChar r3, UChar m4, UChar r1, UChar r2) 10488 { 10489 if (! s390_host_has_dfp) { 10490 emulation_failure(EmFail_S390X_DFP_insn); 10491 } else { 10492 IRTemp op1 = newTemp(Ity_D128); 10493 IRTemp op2 = newTemp(Ity_D128); 10494 IRTemp result = newTemp(Ity_D128); 10495 IRTemp rounding_mode; 10496 10497 if (! s390_host_has_fpext && m4 != S390_DFP_ROUND_PER_FPC_0) { 10498 emulation_warning(EmWarn_S390X_fpext_rounding); 10499 m4 = S390_DFP_ROUND_PER_FPC_0; 10500 } 10501 10502 rounding_mode = encode_dfp_rounding_mode(m4); 10503 assign(op1, get_dpr_pair(r2)); 10504 assign(op2, get_dpr_pair(r3)); 10505 assign(result, triop(Iop_SubD128, mkexpr(rounding_mode), mkexpr(op1), 10506 mkexpr(op2))); 10507 put_dpr_pair(r1, mkexpr(result)); 10508 10509 s390_cc_thunk_put1d128(S390_CC_OP_DFP_RESULT_128, result); 10510 } 10511 return (m4 == 0) ? "sxtr" : "sxtra"; 10512 } 10513 10514 static const HChar * 10515 s390_irgen_SLDT(UChar r3, IRTemp op2addr, UChar r1) 10516 { 10517 if (! s390_host_has_dfp) { 10518 emulation_failure(EmFail_S390X_DFP_insn); 10519 } else { 10520 IRTemp op = newTemp(Ity_D64); 10521 10522 assign(op, get_dpr_dw0(r3)); 10523 put_dpr_dw0(r1, binop(Iop_ShlD64, mkexpr(op), 10524 unop(Iop_64to8, binop(Iop_And64, mkexpr(op2addr), 10525 mkU64(63))))); 10526 } 10527 return "sldt"; 10528 } 10529 10530 static const HChar * 10531 s390_irgen_SLXT(UChar r3, IRTemp op2addr, UChar r1) 10532 { 10533 if (! s390_host_has_dfp) { 10534 emulation_failure(EmFail_S390X_DFP_insn); 10535 } else { 10536 IRTemp op = newTemp(Ity_D128); 10537 10538 assign(op, get_dpr_pair(r3)); 10539 put_dpr_pair(r1, binop(Iop_ShlD128, mkexpr(op), 10540 unop(Iop_64to8, binop(Iop_And64, mkexpr(op2addr), 10541 mkU64(63))))); 10542 } 10543 return "slxt"; 10544 } 10545 10546 static const HChar * 10547 s390_irgen_SRDT(UChar r3, IRTemp op2addr, UChar r1) 10548 { 10549 if (! s390_host_has_dfp) { 10550 emulation_failure(EmFail_S390X_DFP_insn); 10551 } else { 10552 IRTemp op = newTemp(Ity_D64); 10553 10554 assign(op, get_dpr_dw0(r3)); 10555 put_dpr_dw0(r1, binop(Iop_ShrD64, mkexpr(op), 10556 unop(Iop_64to8, binop(Iop_And64, mkexpr(op2addr), 10557 mkU64(63))))); 10558 } 10559 return "srdt"; 10560 } 10561 10562 static const HChar * 10563 s390_irgen_SRXT(UChar r3, IRTemp op2addr, UChar r1) 10564 { 10565 if (! s390_host_has_dfp) { 10566 emulation_failure(EmFail_S390X_DFP_insn); 10567 } else { 10568 IRTemp op = newTemp(Ity_D128); 10569 10570 assign(op, get_dpr_pair(r3)); 10571 put_dpr_pair(r1, binop(Iop_ShrD128, mkexpr(op), 10572 unop(Iop_64to8, binop(Iop_And64, mkexpr(op2addr), 10573 mkU64(63))))); 10574 } 10575 return "srxt"; 10576 } 10577 10578 static const HChar * 10579 s390_irgen_TDCET(UChar r1, IRTemp op2addr) 10580 { 10581 if (! s390_host_has_dfp) { 10582 emulation_failure(EmFail_S390X_DFP_insn); 10583 } else { 10584 IRTemp value = newTemp(Ity_D32); 10585 10586 assign(value, get_dpr_w0(r1)); 10587 10588 s390_cc_thunk_putFZ(S390_CC_OP_DFP_TDC_32, value, op2addr); 10589 } 10590 return "tdcet"; 10591 } 10592 10593 static const HChar * 10594 s390_irgen_TDCDT(UChar r1, IRTemp op2addr) 10595 { 10596 if (! s390_host_has_dfp) { 10597 emulation_failure(EmFail_S390X_DFP_insn); 10598 } else { 10599 IRTemp value = newTemp(Ity_D64); 10600 10601 assign(value, get_dpr_dw0(r1)); 10602 10603 s390_cc_thunk_putFZ(S390_CC_OP_DFP_TDC_64, value, op2addr); 10604 } 10605 return "tdcdt"; 10606 } 10607 10608 static const HChar * 10609 s390_irgen_TDCXT(UChar r1, IRTemp op2addr) 10610 { 10611 if (! s390_host_has_dfp) { 10612 emulation_failure(EmFail_S390X_DFP_insn); 10613 } else { 10614 IRTemp value = newTemp(Ity_D128); 10615 10616 assign(value, get_dpr_pair(r1)); 10617 10618 s390_cc_thunk_put1d128Z(S390_CC_OP_DFP_TDC_128, value, op2addr); 10619 } 10620 return "tdcxt"; 10621 } 10622 10623 static const HChar * 10624 s390_irgen_TDGET(UChar r1, IRTemp op2addr) 10625 { 10626 if (! s390_host_has_dfp) { 10627 emulation_failure(EmFail_S390X_DFP_insn); 10628 } else { 10629 IRTemp value = newTemp(Ity_D32); 10630 10631 assign(value, get_dpr_w0(r1)); 10632 10633 s390_cc_thunk_putFZ(S390_CC_OP_DFP_TDG_32, value, op2addr); 10634 } 10635 return "tdget"; 10636 } 10637 10638 static const HChar * 10639 s390_irgen_TDGDT(UChar r1, IRTemp op2addr) 10640 { 10641 if (! s390_host_has_dfp) { 10642 emulation_failure(EmFail_S390X_DFP_insn); 10643 } else { 10644 IRTemp value = newTemp(Ity_D64); 10645 10646 assign(value, get_dpr_dw0(r1)); 10647 10648 s390_cc_thunk_putFZ(S390_CC_OP_DFP_TDG_64, value, op2addr); 10649 } 10650 return "tdgdt"; 10651 } 10652 10653 static const HChar * 10654 s390_irgen_TDGXT(UChar r1, IRTemp op2addr) 10655 { 10656 if (! s390_host_has_dfp) { 10657 emulation_failure(EmFail_S390X_DFP_insn); 10658 } else { 10659 IRTemp value = newTemp(Ity_D128); 10660 10661 assign(value, get_dpr_pair(r1)); 10662 10663 s390_cc_thunk_put1d128Z(S390_CC_OP_DFP_TDG_128, value, op2addr); 10664 } 10665 return "tdgxt"; 10666 } 10667 10668 static const HChar * 10669 s390_irgen_CLC(UChar length, IRTemp start1, IRTemp start2) 10670 { 10671 IRTemp len = newTemp(Ity_I64); 10672 10673 assign(len, mkU64(length)); 10674 s390_irgen_CLC_EX(len, start1, start2); 10675 10676 return "clc"; 10677 } 10678 10679 static const HChar * 10680 s390_irgen_CLCL(UChar r1, UChar r2) 10681 { 10682 IRTemp addr1 = newTemp(Ity_I64); 10683 IRTemp addr2 = newTemp(Ity_I64); 10684 IRTemp addr1_load = newTemp(Ity_I64); 10685 IRTemp addr2_load = newTemp(Ity_I64); 10686 IRTemp len1 = newTemp(Ity_I32); 10687 IRTemp len2 = newTemp(Ity_I32); 10688 IRTemp r1p1 = newTemp(Ity_I32); /* contents of r1 + 1 */ 10689 IRTemp r2p1 = newTemp(Ity_I32); /* contents of r2 + 1 */ 10690 IRTemp single1 = newTemp(Ity_I8); 10691 IRTemp single2 = newTemp(Ity_I8); 10692 IRTemp pad = newTemp(Ity_I8); 10693 10694 assign(addr1, get_gpr_dw0(r1)); 10695 assign(r1p1, get_gpr_w1(r1 + 1)); 10696 assign(len1, binop(Iop_And32, mkexpr(r1p1), mkU32(0x00ffffff))); 10697 assign(addr2, get_gpr_dw0(r2)); 10698 assign(r2p1, get_gpr_w1(r2 + 1)); 10699 assign(len2, binop(Iop_And32, mkexpr(r2p1), mkU32(0x00ffffff))); 10700 assign(pad, get_gpr_b4(r2 + 1)); 10701 10702 /* len1 == 0 and len2 == 0? Exit */ 10703 s390_cc_set(0); 10704 next_insn_if(binop(Iop_CmpEQ32, binop(Iop_Or32, mkexpr(len1), 10705 mkexpr(len2)), mkU32(0))); 10706 10707 /* Because mkite evaluates both the then-clause and the else-clause 10708 we cannot load directly from addr1 here. If len1 is 0, then adddr1 10709 may be NULL and loading from there would segfault. So we provide a 10710 valid dummy address in that case. Loading from there does no harm and 10711 the value will be discarded at runtime. */ 10712 assign(addr1_load, 10713 mkite(binop(Iop_CmpEQ32, mkexpr(len1), mkU32(0)), 10714 mkU64(guest_IA_curr_instr), mkexpr(addr1))); 10715 assign(single1, 10716 mkite(binop(Iop_CmpEQ32, mkexpr(len1), mkU32(0)), 10717 mkexpr(pad), load(Ity_I8, mkexpr(addr1_load)))); 10718 10719 assign(addr2_load, 10720 mkite(binop(Iop_CmpEQ32, mkexpr(len2), mkU32(0)), 10721 mkU64(guest_IA_curr_instr), mkexpr(addr2))); 10722 assign(single2, 10723 mkite(binop(Iop_CmpEQ32, mkexpr(len2), mkU32(0)), 10724 mkexpr(pad), load(Ity_I8, mkexpr(addr2_load)))); 10725 10726 s390_cc_thunk_put2(S390_CC_OP_UNSIGNED_COMPARE, single1, single2, False); 10727 /* Fields differ ? */ 10728 next_insn_if(binop(Iop_CmpNE8, mkexpr(single1), mkexpr(single2))); 10729 10730 /* Update len1 and addr1, unless len1 == 0. */ 10731 put_gpr_dw0(r1, 10732 mkite(binop(Iop_CmpEQ32, mkexpr(len1), mkU32(0)), 10733 mkexpr(addr1), 10734 binop(Iop_Add64, mkexpr(addr1), mkU64(1)))); 10735 10736 /* When updating len1 we must not modify bits (r1+1)[0:39] */ 10737 put_gpr_w1(r1 + 1, 10738 mkite(binop(Iop_CmpEQ32, mkexpr(len1), mkU32(0)), 10739 binop(Iop_And32, mkexpr(r1p1), mkU32(0xFF000000u)), 10740 binop(Iop_Sub32, mkexpr(r1p1), mkU32(1)))); 10741 10742 /* Update len2 and addr2, unless len2 == 0. */ 10743 put_gpr_dw0(r2, 10744 mkite(binop(Iop_CmpEQ32, mkexpr(len2), mkU32(0)), 10745 mkexpr(addr2), 10746 binop(Iop_Add64, mkexpr(addr2), mkU64(1)))); 10747 10748 /* When updating len2 we must not modify bits (r2+1)[0:39] */ 10749 put_gpr_w1(r2 + 1, 10750 mkite(binop(Iop_CmpEQ32, mkexpr(len2), mkU32(0)), 10751 binop(Iop_And32, mkexpr(r2p1), mkU32(0xFF000000u)), 10752 binop(Iop_Sub32, mkexpr(r2p1), mkU32(1)))); 10753 10754 iterate(); 10755 10756 return "clcl"; 10757 } 10758 10759 static const HChar * 10760 s390_irgen_CLCLE(UChar r1, UChar r3, IRTemp pad2) 10761 { 10762 IRTemp addr1, addr3, addr1_load, addr3_load, len1, len3, single1, single3; 10763 10764 addr1 = newTemp(Ity_I64); 10765 addr3 = newTemp(Ity_I64); 10766 addr1_load = newTemp(Ity_I64); 10767 addr3_load = newTemp(Ity_I64); 10768 len1 = newTemp(Ity_I64); 10769 len3 = newTemp(Ity_I64); 10770 single1 = newTemp(Ity_I8); 10771 single3 = newTemp(Ity_I8); 10772 10773 assign(addr1, get_gpr_dw0(r1)); 10774 assign(len1, get_gpr_dw0(r1 + 1)); 10775 assign(addr3, get_gpr_dw0(r3)); 10776 assign(len3, get_gpr_dw0(r3 + 1)); 10777 10778 /* len1 == 0 and len3 == 0? Exit */ 10779 s390_cc_set(0); 10780 next_insn_if(binop(Iop_CmpEQ64,binop(Iop_Or64, mkexpr(len1), 10781 mkexpr(len3)), mkU64(0))); 10782 10783 /* A mux requires both ways to be possible. This is a way to prevent clcle 10784 from reading from addr1 if it should read from the pad. Since the pad 10785 has no address, just read from the instruction, we discard that anyway */ 10786 assign(addr1_load, 10787 mkite(binop(Iop_CmpEQ64, mkexpr(len1), mkU64(0)), 10788 mkU64(guest_IA_curr_instr), mkexpr(addr1))); 10789 10790 /* same for addr3 */ 10791 assign(addr3_load, 10792 mkite(binop(Iop_CmpEQ64, mkexpr(len3), mkU64(0)), 10793 mkU64(guest_IA_curr_instr), mkexpr(addr3))); 10794 10795 assign(single1, 10796 mkite(binop(Iop_CmpEQ64, mkexpr(len1), mkU64(0)), 10797 unop(Iop_64to8, mkexpr(pad2)), 10798 load(Ity_I8, mkexpr(addr1_load)))); 10799 10800 assign(single3, 10801 mkite(binop(Iop_CmpEQ64, mkexpr(len3), mkU64(0)), 10802 unop(Iop_64to8, mkexpr(pad2)), 10803 load(Ity_I8, mkexpr(addr3_load)))); 10804 10805 s390_cc_thunk_put2(S390_CC_OP_UNSIGNED_COMPARE, single1, single3, False); 10806 /* Both fields differ ? */ 10807 next_insn_if(binop(Iop_CmpNE8, mkexpr(single1), mkexpr(single3))); 10808 10809 /* If a length in 0 we must not change this length and the address */ 10810 put_gpr_dw0(r1, 10811 mkite(binop(Iop_CmpEQ64, mkexpr(len1), mkU64(0)), 10812 mkexpr(addr1), 10813 binop(Iop_Add64, mkexpr(addr1), mkU64(1)))); 10814 10815 put_gpr_dw0(r1 + 1, 10816 mkite(binop(Iop_CmpEQ64, mkexpr(len1), mkU64(0)), 10817 mkU64(0), binop(Iop_Sub64, mkexpr(len1), mkU64(1)))); 10818 10819 put_gpr_dw0(r3, 10820 mkite(binop(Iop_CmpEQ64, mkexpr(len3), mkU64(0)), 10821 mkexpr(addr3), 10822 binop(Iop_Add64, mkexpr(addr3), mkU64(1)))); 10823 10824 put_gpr_dw0(r3 + 1, 10825 mkite(binop(Iop_CmpEQ64, mkexpr(len3), mkU64(0)), 10826 mkU64(0), binop(Iop_Sub64, mkexpr(len3), mkU64(1)))); 10827 10828 iterate(); 10829 10830 return "clcle"; 10831 } 10832 10833 10834 static void 10835 s390_irgen_XC_EX(IRTemp length, IRTemp start1, IRTemp start2) 10836 { 10837 s390_irgen_xonc(Iop_Xor8, length, start1, start2); 10838 } 10839 10840 10841 static void 10842 s390_irgen_NC_EX(IRTemp length, IRTemp start1, IRTemp start2) 10843 { 10844 s390_irgen_xonc(Iop_And8, length, start1, start2); 10845 } 10846 10847 10848 static void 10849 s390_irgen_OC_EX(IRTemp length, IRTemp start1, IRTemp start2) 10850 { 10851 s390_irgen_xonc(Iop_Or8, length, start1, start2); 10852 } 10853 10854 10855 static void 10856 s390_irgen_CLC_EX(IRTemp length, IRTemp start1, IRTemp start2) 10857 { 10858 IRTemp current1 = newTemp(Ity_I8); 10859 IRTemp current2 = newTemp(Ity_I8); 10860 IRTemp counter = newTemp(Ity_I64); 10861 10862 assign(counter, get_counter_dw0()); 10863 put_counter_dw0(mkU64(0)); 10864 10865 assign(current1, load(Ity_I8, binop(Iop_Add64, mkexpr(start1), 10866 mkexpr(counter)))); 10867 assign(current2, load(Ity_I8, binop(Iop_Add64, mkexpr(start2), 10868 mkexpr(counter)))); 10869 s390_cc_thunk_put2(S390_CC_OP_UNSIGNED_COMPARE, current1, current2, 10870 False); 10871 10872 /* Both fields differ ? */ 10873 next_insn_if(binop(Iop_CmpNE8, mkexpr(current1), mkexpr(current2))); 10874 10875 /* Check for end of field */ 10876 put_counter_dw0(binop(Iop_Add64, mkexpr(counter), mkU64(1))); 10877 iterate_if(binop(Iop_CmpNE64, mkexpr(counter), mkexpr(length))); 10878 put_counter_dw0(mkU64(0)); 10879 } 10880 10881 static void 10882 s390_irgen_MVC_EX(IRTemp length, IRTemp start1, IRTemp start2) 10883 { 10884 IRTemp counter = newTemp(Ity_I64); 10885 10886 assign(counter, get_counter_dw0()); 10887 10888 store(binop(Iop_Add64, mkexpr(start1), mkexpr(counter)), 10889 load(Ity_I8, binop(Iop_Add64, mkexpr(start2), mkexpr(counter)))); 10890 10891 /* Check for end of field */ 10892 put_counter_dw0(binop(Iop_Add64, mkexpr(counter), mkU64(1))); 10893 iterate_if(binop(Iop_CmpNE64, mkexpr(counter), mkexpr(length))); 10894 put_counter_dw0(mkU64(0)); 10895 } 10896 10897 static void 10898 s390_irgen_TR_EX(IRTemp length, IRTemp start1, IRTemp start2) 10899 { 10900 IRTemp op = newTemp(Ity_I8); 10901 IRTemp op1 = newTemp(Ity_I8); 10902 IRTemp result = newTemp(Ity_I64); 10903 IRTemp counter = newTemp(Ity_I64); 10904 10905 assign(counter, get_counter_dw0()); 10906 10907 assign(op, load(Ity_I8, binop(Iop_Add64, mkexpr(start1), mkexpr(counter)))); 10908 10909 assign(result, binop(Iop_Add64, unop(Iop_8Uto64, mkexpr(op)), mkexpr(start2))); 10910 10911 assign(op1, load(Ity_I8, mkexpr(result))); 10912 store(binop(Iop_Add64, mkexpr(start1), mkexpr(counter)), mkexpr(op1)); 10913 10914 put_counter_dw0(binop(Iop_Add64, mkexpr(counter), mkU64(1))); 10915 iterate_if(binop(Iop_CmpNE64, mkexpr(counter), mkexpr(length))); 10916 put_counter_dw0(mkU64(0)); 10917 } 10918 10919 10920 static void 10921 s390_irgen_EX_SS(UChar r, IRTemp addr2, 10922 void (*irgen)(IRTemp length, IRTemp start1, IRTemp start2), 10923 UInt lensize) 10924 { 10925 struct SS { 10926 unsigned int op : 8; 10927 unsigned int l : 8; 10928 unsigned int b1 : 4; 10929 unsigned int d1 : 12; 10930 unsigned int b2 : 4; 10931 unsigned int d2 : 12; 10932 }; 10933 union { 10934 struct SS dec; 10935 unsigned long bytes; 10936 } ss; 10937 IRTemp cond; 10938 IRDirty *d; 10939 IRTemp torun; 10940 10941 IRTemp start1 = newTemp(Ity_I64); 10942 IRTemp start2 = newTemp(Ity_I64); 10943 IRTemp len = newTemp(lensize == 64 ? Ity_I64 : Ity_I32); 10944 cond = newTemp(Ity_I1); 10945 torun = newTemp(Ity_I64); 10946 10947 assign(torun, load(Ity_I64, mkexpr(addr2))); 10948 /* Start with a check that the saved code is still correct */ 10949 assign(cond, binop(Iop_CmpNE64, mkexpr(torun), mkU64(last_execute_target))); 10950 /* If not, save the new value */ 10951 d = unsafeIRDirty_0_N (0, "s390x_dirtyhelper_EX", &s390x_dirtyhelper_EX, 10952 mkIRExprVec_1(mkexpr(torun))); 10953 d->guard = mkexpr(cond); 10954 stmt(IRStmt_Dirty(d)); 10955 10956 /* and restart */ 10957 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_CMSTART), 10958 mkU64(guest_IA_curr_instr))); 10959 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_CMLEN), mkU64(4))); 10960 restart_if(mkexpr(cond)); 10961 10962 ss.bytes = last_execute_target; 10963 assign(start1, binop(Iop_Add64, mkU64(ss.dec.d1), 10964 ss.dec.b1 != 0 ? get_gpr_dw0(ss.dec.b1) : mkU64(0))); 10965 assign(start2, binop(Iop_Add64, mkU64(ss.dec.d2), 10966 ss.dec.b2 != 0 ? get_gpr_dw0(ss.dec.b2) : mkU64(0))); 10967 assign(len, unop(lensize == 64 ? Iop_8Uto64 : Iop_8Uto32, binop(Iop_Or8, 10968 r != 0 ? get_gpr_b7(r): mkU8(0), mkU8(ss.dec.l)))); 10969 irgen(len, start1, start2); 10970 10971 last_execute_target = 0; 10972 } 10973 10974 static const HChar * 10975 s390_irgen_EX(UChar r1, IRTemp addr2) 10976 { 10977 switch(last_execute_target & 0xff00000000000000ULL) { 10978 case 0: 10979 { 10980 /* no code information yet */ 10981 IRDirty *d; 10982 10983 /* so safe the code... */ 10984 d = unsafeIRDirty_0_N (0, "s390x_dirtyhelper_EX", &s390x_dirtyhelper_EX, 10985 mkIRExprVec_1(load(Ity_I64, mkexpr(addr2)))); 10986 stmt(IRStmt_Dirty(d)); 10987 /* and restart */ 10988 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_CMSTART), 10989 mkU64(guest_IA_curr_instr))); 10990 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_CMLEN), mkU64(4))); 10991 restart_if(IRExpr_Const(IRConst_U1(True))); 10992 10993 /* we know that this will be invalidated */ 10994 put_IA(mkaddr_expr(guest_IA_next_instr)); 10995 dis_res->whatNext = Dis_StopHere; 10996 dis_res->jk_StopHere = Ijk_InvalICache; 10997 break; 10998 } 10999 11000 case 0xd200000000000000ULL: 11001 /* special case MVC */ 11002 s390_irgen_EX_SS(r1, addr2, s390_irgen_MVC_EX, 64); 11003 return "ex@mvc"; 11004 11005 case 0xd500000000000000ULL: 11006 /* special case CLC */ 11007 s390_irgen_EX_SS(r1, addr2, s390_irgen_CLC_EX, 64); 11008 return "ex@clc"; 11009 11010 case 0xd700000000000000ULL: 11011 /* special case XC */ 11012 s390_irgen_EX_SS(r1, addr2, s390_irgen_XC_EX, 32); 11013 return "ex@xc"; 11014 11015 case 0xd600000000000000ULL: 11016 /* special case OC */ 11017 s390_irgen_EX_SS(r1, addr2, s390_irgen_OC_EX, 32); 11018 return "ex@oc"; 11019 11020 case 0xd400000000000000ULL: 11021 /* special case NC */ 11022 s390_irgen_EX_SS(r1, addr2, s390_irgen_NC_EX, 32); 11023 return "ex@nc"; 11024 11025 case 0xdc00000000000000ULL: 11026 /* special case TR */ 11027 s390_irgen_EX_SS(r1, addr2, s390_irgen_TR_EX, 64); 11028 return "ex@tr"; 11029 11030 default: 11031 { 11032 /* everything else will get a self checking prefix that also checks the 11033 register content */ 11034 IRDirty *d; 11035 UChar *bytes; 11036 IRTemp cond; 11037 IRTemp orperand; 11038 IRTemp torun; 11039 11040 cond = newTemp(Ity_I1); 11041 orperand = newTemp(Ity_I64); 11042 torun = newTemp(Ity_I64); 11043 11044 if (r1 == 0) 11045 assign(orperand, mkU64(0)); 11046 else 11047 assign(orperand, unop(Iop_8Uto64,get_gpr_b7(r1))); 11048 /* This code is going to be translated */ 11049 assign(torun, binop(Iop_Or64, load(Ity_I64, mkexpr(addr2)), 11050 binop(Iop_Shl64, mkexpr(orperand), mkU8(48)))); 11051 11052 /* Start with a check that saved code is still correct */ 11053 assign(cond, binop(Iop_CmpNE64, mkexpr(torun), 11054 mkU64(last_execute_target))); 11055 /* If not, save the new value */ 11056 d = unsafeIRDirty_0_N (0, "s390x_dirtyhelper_EX", &s390x_dirtyhelper_EX, 11057 mkIRExprVec_1(mkexpr(torun))); 11058 d->guard = mkexpr(cond); 11059 stmt(IRStmt_Dirty(d)); 11060 11061 /* and restart */ 11062 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_CMSTART), mkU64(guest_IA_curr_instr))); 11063 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_CMLEN), mkU64(4))); 11064 restart_if(mkexpr(cond)); 11065 11066 /* Now comes the actual translation */ 11067 bytes = (UChar *) &last_execute_target; 11068 s390_decode_and_irgen(bytes, ((((bytes[0] >> 6) + 1) >> 1) + 1) << 1, 11069 dis_res); 11070 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 11071 vex_printf(" which was executed by\n"); 11072 /* dont make useless translations in the next execute */ 11073 last_execute_target = 0; 11074 } 11075 } 11076 return "ex"; 11077 } 11078 11079 static const HChar * 11080 s390_irgen_EXRL(UChar r1, UInt offset) 11081 { 11082 IRTemp addr = newTemp(Ity_I64); 11083 /* we might save one round trip because we know the target */ 11084 if (!last_execute_target) 11085 last_execute_target = *(ULong *)(HWord) 11086 (guest_IA_curr_instr + offset * 2UL); 11087 assign(addr, mkU64(guest_IA_curr_instr + offset * 2UL)); 11088 s390_irgen_EX(r1, addr); 11089 return "exrl"; 11090 } 11091 11092 static const HChar * 11093 s390_irgen_IPM(UChar r1) 11094 { 11095 // As long as we dont support SPM, lets just assume 0 as program mask 11096 put_gpr_b4(r1, unop(Iop_32to8, binop(Iop_Or32, mkU32(0 /* program mask */), 11097 binop(Iop_Shl32, s390_call_calculate_cc(), mkU8(4))))); 11098 11099 return "ipm"; 11100 } 11101 11102 11103 static const HChar * 11104 s390_irgen_SRST(UChar r1, UChar r2) 11105 { 11106 IRTemp address = newTemp(Ity_I64); 11107 IRTemp next = newTemp(Ity_I64); 11108 IRTemp delim = newTemp(Ity_I8); 11109 IRTemp counter = newTemp(Ity_I64); 11110 IRTemp byte = newTemp(Ity_I8); 11111 11112 assign(address, get_gpr_dw0(r2)); 11113 assign(next, get_gpr_dw0(r1)); 11114 11115 assign(counter, get_counter_dw0()); 11116 put_counter_dw0(mkU64(0)); 11117 11118 // start = next? CC=2 and out r1 and r2 unchanged 11119 s390_cc_set(2); 11120 put_gpr_dw0(r2, binop(Iop_Sub64, mkexpr(address), mkexpr(counter))); 11121 next_insn_if(binop(Iop_CmpEQ64, mkexpr(address), mkexpr(next))); 11122 11123 assign(byte, load(Ity_I8, mkexpr(address))); 11124 assign(delim, get_gpr_b7(0)); 11125 11126 // byte = delim? CC=1, R1=address 11127 s390_cc_set(1); 11128 put_gpr_dw0(r1, mkexpr(address)); 11129 next_insn_if(binop(Iop_CmpEQ8, mkexpr(delim), mkexpr(byte))); 11130 11131 // else: all equal, no end yet, loop 11132 put_counter_dw0(binop(Iop_Add64, mkexpr(counter), mkU64(1))); 11133 put_gpr_dw0(r1, mkexpr(next)); 11134 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(address), mkU64(1))); 11135 11136 iterate(); 11137 11138 return "srst"; 11139 } 11140 11141 static const HChar * 11142 s390_irgen_CLST(UChar r1, UChar r2) 11143 { 11144 IRTemp address1 = newTemp(Ity_I64); 11145 IRTemp address2 = newTemp(Ity_I64); 11146 IRTemp end = newTemp(Ity_I8); 11147 IRTemp counter = newTemp(Ity_I64); 11148 IRTemp byte1 = newTemp(Ity_I8); 11149 IRTemp byte2 = newTemp(Ity_I8); 11150 11151 assign(address1, get_gpr_dw0(r1)); 11152 assign(address2, get_gpr_dw0(r2)); 11153 assign(end, get_gpr_b7(0)); 11154 assign(counter, get_counter_dw0()); 11155 put_counter_dw0(mkU64(0)); 11156 assign(byte1, load(Ity_I8, mkexpr(address1))); 11157 assign(byte2, load(Ity_I8, mkexpr(address2))); 11158 11159 // end in both? all equal, reset r1 and r2 to start values 11160 s390_cc_set(0); 11161 put_gpr_dw0(r1, binop(Iop_Sub64, mkexpr(address1), mkexpr(counter))); 11162 put_gpr_dw0(r2, binop(Iop_Sub64, mkexpr(address2), mkexpr(counter))); 11163 next_insn_if(binop(Iop_CmpEQ8, mkU8(0), 11164 binop(Iop_Or8, 11165 binop(Iop_Xor8, mkexpr(byte1), mkexpr(end)), 11166 binop(Iop_Xor8, mkexpr(byte2), mkexpr(end))))); 11167 11168 put_gpr_dw0(r1, mkexpr(address1)); 11169 put_gpr_dw0(r2, mkexpr(address2)); 11170 11171 // End found in string1 11172 s390_cc_set(1); 11173 next_insn_if(binop(Iop_CmpEQ8, mkexpr(end), mkexpr(byte1))); 11174 11175 // End found in string2 11176 s390_cc_set(2); 11177 next_insn_if(binop(Iop_CmpEQ8, mkexpr(end), mkexpr(byte2))); 11178 11179 // string1 < string2 11180 s390_cc_set(1); 11181 next_insn_if(binop(Iop_CmpLT32U, unop(Iop_8Uto32, mkexpr(byte1)), 11182 unop(Iop_8Uto32, mkexpr(byte2)))); 11183 11184 // string2 < string1 11185 s390_cc_set(2); 11186 next_insn_if(binop(Iop_CmpLT32U, unop(Iop_8Uto32, mkexpr(byte2)), 11187 unop(Iop_8Uto32, mkexpr(byte1)))); 11188 11189 // else: all equal, no end yet, loop 11190 put_counter_dw0(binop(Iop_Add64, mkexpr(counter), mkU64(1))); 11191 put_gpr_dw0(r1, binop(Iop_Add64, get_gpr_dw0(r1), mkU64(1))); 11192 put_gpr_dw0(r2, binop(Iop_Add64, get_gpr_dw0(r2), mkU64(1))); 11193 11194 iterate(); 11195 11196 return "clst"; 11197 } 11198 11199 static void 11200 s390_irgen_load_multiple_32bit(UChar r1, UChar r3, IRTemp op2addr) 11201 { 11202 UChar reg; 11203 IRTemp addr = newTemp(Ity_I64); 11204 11205 assign(addr, mkexpr(op2addr)); 11206 reg = r1; 11207 do { 11208 IRTemp old = addr; 11209 11210 reg %= 16; 11211 put_gpr_w1(reg, load(Ity_I32, mkexpr(addr))); 11212 addr = newTemp(Ity_I64); 11213 assign(addr, binop(Iop_Add64, mkexpr(old), mkU64(4))); 11214 reg++; 11215 } while (reg != (r3 + 1)); 11216 } 11217 11218 static const HChar * 11219 s390_irgen_LM(UChar r1, UChar r3, IRTemp op2addr) 11220 { 11221 s390_irgen_load_multiple_32bit(r1, r3, op2addr); 11222 11223 return "lm"; 11224 } 11225 11226 static const HChar * 11227 s390_irgen_LMY(UChar r1, UChar r3, IRTemp op2addr) 11228 { 11229 s390_irgen_load_multiple_32bit(r1, r3, op2addr); 11230 11231 return "lmy"; 11232 } 11233 11234 static const HChar * 11235 s390_irgen_LMH(UChar r1, UChar r3, IRTemp op2addr) 11236 { 11237 UChar reg; 11238 IRTemp addr = newTemp(Ity_I64); 11239 11240 assign(addr, mkexpr(op2addr)); 11241 reg = r1; 11242 do { 11243 IRTemp old = addr; 11244 11245 reg %= 16; 11246 put_gpr_w0(reg, load(Ity_I32, mkexpr(addr))); 11247 addr = newTemp(Ity_I64); 11248 assign(addr, binop(Iop_Add64, mkexpr(old), mkU64(4))); 11249 reg++; 11250 } while (reg != (r3 + 1)); 11251 11252 return "lmh"; 11253 } 11254 11255 static const HChar * 11256 s390_irgen_LMG(UChar r1, UChar r3, IRTemp op2addr) 11257 { 11258 UChar reg; 11259 IRTemp addr = newTemp(Ity_I64); 11260 11261 assign(addr, mkexpr(op2addr)); 11262 reg = r1; 11263 do { 11264 IRTemp old = addr; 11265 11266 reg %= 16; 11267 put_gpr_dw0(reg, load(Ity_I64, mkexpr(addr))); 11268 addr = newTemp(Ity_I64); 11269 assign(addr, binop(Iop_Add64, mkexpr(old), mkU64(8))); 11270 reg++; 11271 } while (reg != (r3 + 1)); 11272 11273 return "lmg"; 11274 } 11275 11276 static void 11277 s390_irgen_store_multiple_32bit(UChar r1, UChar r3, IRTemp op2addr) 11278 { 11279 UChar reg; 11280 IRTemp addr = newTemp(Ity_I64); 11281 11282 assign(addr, mkexpr(op2addr)); 11283 reg = r1; 11284 do { 11285 IRTemp old = addr; 11286 11287 reg %= 16; 11288 store(mkexpr(addr), get_gpr_w1(reg)); 11289 addr = newTemp(Ity_I64); 11290 assign(addr, binop(Iop_Add64, mkexpr(old), mkU64(4))); 11291 reg++; 11292 } while( reg != (r3 + 1)); 11293 } 11294 11295 static const HChar * 11296 s390_irgen_STM(UChar r1, UChar r3, IRTemp op2addr) 11297 { 11298 s390_irgen_store_multiple_32bit(r1, r3, op2addr); 11299 11300 return "stm"; 11301 } 11302 11303 static const HChar * 11304 s390_irgen_STMY(UChar r1, UChar r3, IRTemp op2addr) 11305 { 11306 s390_irgen_store_multiple_32bit(r1, r3, op2addr); 11307 11308 return "stmy"; 11309 } 11310 11311 static const HChar * 11312 s390_irgen_STMH(UChar r1, UChar r3, IRTemp op2addr) 11313 { 11314 UChar reg; 11315 IRTemp addr = newTemp(Ity_I64); 11316 11317 assign(addr, mkexpr(op2addr)); 11318 reg = r1; 11319 do { 11320 IRTemp old = addr; 11321 11322 reg %= 16; 11323 store(mkexpr(addr), get_gpr_w0(reg)); 11324 addr = newTemp(Ity_I64); 11325 assign(addr, binop(Iop_Add64, mkexpr(old), mkU64(4))); 11326 reg++; 11327 } while( reg != (r3 + 1)); 11328 11329 return "stmh"; 11330 } 11331 11332 static const HChar * 11333 s390_irgen_STMG(UChar r1, UChar r3, IRTemp op2addr) 11334 { 11335 UChar reg; 11336 IRTemp addr = newTemp(Ity_I64); 11337 11338 assign(addr, mkexpr(op2addr)); 11339 reg = r1; 11340 do { 11341 IRTemp old = addr; 11342 11343 reg %= 16; 11344 store(mkexpr(addr), get_gpr_dw0(reg)); 11345 addr = newTemp(Ity_I64); 11346 assign(addr, binop(Iop_Add64, mkexpr(old), mkU64(8))); 11347 reg++; 11348 } while( reg != (r3 + 1)); 11349 11350 return "stmg"; 11351 } 11352 11353 static void 11354 s390_irgen_xonc(IROp op, IRTemp length, IRTemp start1, IRTemp start2) 11355 { 11356 IRTemp old1 = newTemp(Ity_I8); 11357 IRTemp old2 = newTemp(Ity_I8); 11358 IRTemp new1 = newTemp(Ity_I8); 11359 IRTemp counter = newTemp(Ity_I32); 11360 IRTemp addr1 = newTemp(Ity_I64); 11361 11362 assign(counter, get_counter_w0()); 11363 11364 assign(addr1, binop(Iop_Add64, mkexpr(start1), 11365 unop(Iop_32Uto64, mkexpr(counter)))); 11366 11367 assign(old1, load(Ity_I8, mkexpr(addr1))); 11368 assign(old2, load(Ity_I8, binop(Iop_Add64, mkexpr(start2), 11369 unop(Iop_32Uto64,mkexpr(counter))))); 11370 assign(new1, binop(op, mkexpr(old1), mkexpr(old2))); 11371 11372 /* Special case: xc is used to zero memory */ 11373 if (op == Iop_Xor8) { 11374 store(mkexpr(addr1), 11375 mkite(binop(Iop_CmpEQ64, mkexpr(start1), mkexpr(start2)), 11376 mkU8(0), mkexpr(new1))); 11377 } else 11378 store(mkexpr(addr1), mkexpr(new1)); 11379 put_counter_w1(binop(Iop_Or32, unop(Iop_8Uto32, mkexpr(new1)), 11380 get_counter_w1())); 11381 11382 /* Check for end of field */ 11383 put_counter_w0(binop(Iop_Add32, mkexpr(counter), mkU32(1))); 11384 iterate_if(binop(Iop_CmpNE32, mkexpr(counter), mkexpr(length))); 11385 s390_cc_thunk_put1(S390_CC_OP_BITWISE, mktemp(Ity_I32, get_counter_w1()), 11386 False); 11387 put_counter_dw0(mkU64(0)); 11388 } 11389 11390 static const HChar * 11391 s390_irgen_XC(UChar length, IRTemp start1, IRTemp start2) 11392 { 11393 IRTemp len = newTemp(Ity_I32); 11394 11395 assign(len, mkU32(length)); 11396 s390_irgen_xonc(Iop_Xor8, len, start1, start2); 11397 11398 return "xc"; 11399 } 11400 11401 static void 11402 s390_irgen_XC_sameloc(UChar length, UChar b, UShort d) 11403 { 11404 IRTemp counter = newTemp(Ity_I32); 11405 IRTemp start = newTemp(Ity_I64); 11406 IRTemp addr = newTemp(Ity_I64); 11407 11408 assign(start, 11409 binop(Iop_Add64, mkU64(d), b != 0 ? get_gpr_dw0(b) : mkU64(0))); 11410 11411 if (length < 8) { 11412 UInt i; 11413 11414 for (i = 0; i <= length; ++i) { 11415 store(binop(Iop_Add64, mkexpr(start), mkU64(i)), mkU8(0)); 11416 } 11417 } else { 11418 assign(counter, get_counter_w0()); 11419 11420 assign(addr, binop(Iop_Add64, mkexpr(start), 11421 unop(Iop_32Uto64, mkexpr(counter)))); 11422 11423 store(mkexpr(addr), mkU8(0)); 11424 11425 /* Check for end of field */ 11426 put_counter_w0(binop(Iop_Add32, mkexpr(counter), mkU32(1))); 11427 iterate_if(binop(Iop_CmpNE32, mkexpr(counter), mkU32(length))); 11428 11429 /* Reset counter */ 11430 put_counter_dw0(mkU64(0)); 11431 } 11432 11433 s390_cc_thunk_put1(S390_CC_OP_BITWISE, mktemp(Ity_I32, mkU32(0)), False); 11434 11435 if (UNLIKELY(vex_traceflags & VEX_TRACE_FE)) 11436 s390_disasm(ENC3(MNM, UDLB, UDXB), "xc", d, length, b, d, 0, b); 11437 } 11438 11439 static const HChar * 11440 s390_irgen_NC(UChar length, IRTemp start1, IRTemp start2) 11441 { 11442 IRTemp len = newTemp(Ity_I32); 11443 11444 assign(len, mkU32(length)); 11445 s390_irgen_xonc(Iop_And8, len, start1, start2); 11446 11447 return "nc"; 11448 } 11449 11450 static const HChar * 11451 s390_irgen_OC(UChar length, IRTemp start1, IRTemp start2) 11452 { 11453 IRTemp len = newTemp(Ity_I32); 11454 11455 assign(len, mkU32(length)); 11456 s390_irgen_xonc(Iop_Or8, len, start1, start2); 11457 11458 return "oc"; 11459 } 11460 11461 11462 static const HChar * 11463 s390_irgen_MVC(UChar length, IRTemp start1, IRTemp start2) 11464 { 11465 IRTemp len = newTemp(Ity_I64); 11466 11467 assign(len, mkU64(length)); 11468 s390_irgen_MVC_EX(len, start1, start2); 11469 11470 return "mvc"; 11471 } 11472 11473 static const HChar * 11474 s390_irgen_MVCL(UChar r1, UChar r2) 11475 { 11476 IRTemp addr1 = newTemp(Ity_I64); 11477 IRTemp addr2 = newTemp(Ity_I64); 11478 IRTemp addr2_load = newTemp(Ity_I64); 11479 IRTemp r1p1 = newTemp(Ity_I32); /* contents of r1 + 1 */ 11480 IRTemp r2p1 = newTemp(Ity_I32); /* contents of r2 + 1 */ 11481 IRTemp len1 = newTemp(Ity_I32); 11482 IRTemp len2 = newTemp(Ity_I32); 11483 IRTemp pad = newTemp(Ity_I8); 11484 IRTemp single = newTemp(Ity_I8); 11485 11486 assign(addr1, get_gpr_dw0(r1)); 11487 assign(r1p1, get_gpr_w1(r1 + 1)); 11488 assign(len1, binop(Iop_And32, mkexpr(r1p1), mkU32(0x00ffffff))); 11489 assign(addr2, get_gpr_dw0(r2)); 11490 assign(r2p1, get_gpr_w1(r2 + 1)); 11491 assign(len2, binop(Iop_And32, mkexpr(r2p1), mkU32(0x00ffffff))); 11492 assign(pad, get_gpr_b4(r2 + 1)); 11493 11494 /* len1 == 0 ? */ 11495 s390_cc_thunk_put2(S390_CC_OP_UNSIGNED_COMPARE, len1, len2, False); 11496 next_insn_if(binop(Iop_CmpEQ32, mkexpr(len1), mkU32(0))); 11497 11498 /* Check for destructive overlap: 11499 addr1 > addr2 && addr2 + len1 > addr1 && (addr2 + len2) > addr1 */ 11500 s390_cc_set(3); 11501 IRTemp cond1 = newTemp(Ity_I32); 11502 assign(cond1, unop(Iop_1Uto32, 11503 binop(Iop_CmpLT64U, mkexpr(addr2), mkexpr(addr1)))); 11504 IRTemp cond2 = newTemp(Ity_I32); 11505 assign(cond2, unop(Iop_1Uto32, 11506 binop(Iop_CmpLT64U, mkexpr(addr1), 11507 binop(Iop_Add64, mkexpr(addr2), 11508 unop(Iop_32Uto64, mkexpr(len1)))))); 11509 IRTemp cond3 = newTemp(Ity_I32); 11510 assign(cond3, unop(Iop_1Uto32, 11511 binop(Iop_CmpLT64U, 11512 mkexpr(addr1), 11513 binop(Iop_Add64, mkexpr(addr2), 11514 unop(Iop_32Uto64, mkexpr(len2)))))); 11515 11516 next_insn_if(binop(Iop_CmpEQ32, 11517 binop(Iop_And32, 11518 binop(Iop_And32, mkexpr(cond1), mkexpr(cond2)), 11519 mkexpr(cond3)), 11520 mkU32(1))); 11521 11522 /* See s390_irgen_CLCL for explanation why we cannot load directly 11523 and need two steps. */ 11524 assign(addr2_load, 11525 mkite(binop(Iop_CmpEQ32, mkexpr(len2), mkU32(0)), 11526 mkU64(guest_IA_curr_instr), mkexpr(addr2))); 11527 assign(single, 11528 mkite(binop(Iop_CmpEQ32, mkexpr(len2), mkU32(0)), 11529 mkexpr(pad), load(Ity_I8, mkexpr(addr2_load)))); 11530 11531 store(mkexpr(addr1), mkexpr(single)); 11532 11533 /* Update addr1 and len1 */ 11534 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(addr1), mkU64(1))); 11535 put_gpr_w1(r1 + 1, binop(Iop_Sub32, mkexpr(r1p1), mkU32(1))); 11536 11537 /* Update addr2 and len2 */ 11538 put_gpr_dw0(r2, 11539 mkite(binop(Iop_CmpEQ32, mkexpr(len2), mkU32(0)), 11540 mkexpr(addr2), 11541 binop(Iop_Add64, mkexpr(addr2), mkU64(1)))); 11542 11543 /* When updating len2 we must not modify bits (r2+1)[0:39] */ 11544 put_gpr_w1(r2 + 1, 11545 mkite(binop(Iop_CmpEQ32, mkexpr(len2), mkU32(0)), 11546 binop(Iop_And32, mkexpr(r2p1), mkU32(0xFF000000u)), 11547 binop(Iop_Sub32, mkexpr(r2p1), mkU32(1)))); 11548 11549 s390_cc_thunk_put2(S390_CC_OP_UNSIGNED_COMPARE, len1, len2, False); 11550 iterate_if(binop(Iop_CmpNE32, mkexpr(len1), mkU32(1))); 11551 11552 return "mvcl"; 11553 } 11554 11555 11556 static const HChar * 11557 s390_irgen_MVCLE(UChar r1, UChar r3, IRTemp pad2) 11558 { 11559 IRTemp addr1, addr3, addr3_load, len1, len3, single; 11560 11561 addr1 = newTemp(Ity_I64); 11562 addr3 = newTemp(Ity_I64); 11563 addr3_load = newTemp(Ity_I64); 11564 len1 = newTemp(Ity_I64); 11565 len3 = newTemp(Ity_I64); 11566 single = newTemp(Ity_I8); 11567 11568 assign(addr1, get_gpr_dw0(r1)); 11569 assign(len1, get_gpr_dw0(r1 + 1)); 11570 assign(addr3, get_gpr_dw0(r3)); 11571 assign(len3, get_gpr_dw0(r3 + 1)); 11572 11573 // len1 == 0 ? 11574 s390_cc_thunk_put2(S390_CC_OP_UNSIGNED_COMPARE, len1, len3, False); 11575 next_insn_if(binop(Iop_CmpEQ64,mkexpr(len1), mkU64(0))); 11576 11577 /* This is a hack to prevent mvcle from reading from addr3 if it 11578 should read from the pad. Since the pad has no address, just 11579 read from the instruction, we discard that anyway */ 11580 assign(addr3_load, 11581 mkite(binop(Iop_CmpEQ64, mkexpr(len3), mkU64(0)), 11582 mkU64(guest_IA_curr_instr), mkexpr(addr3))); 11583 11584 assign(single, 11585 mkite(binop(Iop_CmpEQ64, mkexpr(len3), mkU64(0)), 11586 unop(Iop_64to8, mkexpr(pad2)), 11587 load(Ity_I8, mkexpr(addr3_load)))); 11588 store(mkexpr(addr1), mkexpr(single)); 11589 11590 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(addr1), mkU64(1))); 11591 11592 put_gpr_dw0(r1 + 1, binop(Iop_Sub64, mkexpr(len1), mkU64(1))); 11593 11594 put_gpr_dw0(r3, 11595 mkite(binop(Iop_CmpEQ64, mkexpr(len3), mkU64(0)), 11596 mkexpr(addr3), 11597 binop(Iop_Add64, mkexpr(addr3), mkU64(1)))); 11598 11599 put_gpr_dw0(r3 + 1, 11600 mkite(binop(Iop_CmpEQ64, mkexpr(len3), mkU64(0)), 11601 mkU64(0), binop(Iop_Sub64, mkexpr(len3), mkU64(1)))); 11602 11603 s390_cc_thunk_put2(S390_CC_OP_UNSIGNED_COMPARE, len1, len3, False); 11604 iterate_if(binop(Iop_CmpNE64, mkexpr(len1), mkU64(1))); 11605 11606 return "mvcle"; 11607 } 11608 11609 static const HChar * 11610 s390_irgen_MVST(UChar r1, UChar r2) 11611 { 11612 IRTemp addr1 = newTemp(Ity_I64); 11613 IRTemp addr2 = newTemp(Ity_I64); 11614 IRTemp end = newTemp(Ity_I8); 11615 IRTemp byte = newTemp(Ity_I8); 11616 IRTemp counter = newTemp(Ity_I64); 11617 11618 assign(addr1, get_gpr_dw0(r1)); 11619 assign(addr2, get_gpr_dw0(r2)); 11620 assign(counter, get_counter_dw0()); 11621 assign(end, get_gpr_b7(0)); 11622 assign(byte, load(Ity_I8, binop(Iop_Add64, mkexpr(addr2),mkexpr(counter)))); 11623 store(binop(Iop_Add64,mkexpr(addr1),mkexpr(counter)), mkexpr(byte)); 11624 11625 // We use unlimited as cpu-determined number 11626 put_counter_dw0(binop(Iop_Add64, mkexpr(counter), mkU64(1))); 11627 iterate_if(binop(Iop_CmpNE8, mkexpr(end), mkexpr(byte))); 11628 11629 // and always set cc=1 at the end + update r1 11630 s390_cc_set(1); 11631 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(addr1), mkexpr(counter))); 11632 put_counter_dw0(mkU64(0)); 11633 11634 return "mvst"; 11635 } 11636 11637 static void 11638 s390_irgen_divide_64to32(IROp op, UChar r1, IRTemp op2) 11639 { 11640 IRTemp op1 = newTemp(Ity_I64); 11641 IRTemp result = newTemp(Ity_I64); 11642 11643 assign(op1, binop(Iop_32HLto64, 11644 get_gpr_w1(r1), // high 32 bits 11645 get_gpr_w1(r1 + 1))); // low 32 bits 11646 assign(result, binop(op, mkexpr(op1), mkexpr(op2))); 11647 put_gpr_w1(r1, unop(Iop_64HIto32, mkexpr(result))); // remainder 11648 put_gpr_w1(r1 + 1, unop(Iop_64to32, mkexpr(result))); // quotient 11649 } 11650 11651 static void 11652 s390_irgen_divide_128to64(IROp op, UChar r1, IRTemp op2) 11653 { 11654 IRTemp op1 = newTemp(Ity_I128); 11655 IRTemp result = newTemp(Ity_I128); 11656 11657 assign(op1, binop(Iop_64HLto128, 11658 get_gpr_dw0(r1), // high 64 bits 11659 get_gpr_dw0(r1 + 1))); // low 64 bits 11660 assign(result, binop(op, mkexpr(op1), mkexpr(op2))); 11661 put_gpr_dw0(r1, unop(Iop_128HIto64, mkexpr(result))); // remainder 11662 put_gpr_dw0(r1 + 1, unop(Iop_128to64, mkexpr(result))); // quotient 11663 } 11664 11665 static void 11666 s390_irgen_divide_64to64(IROp op, UChar r1, IRTemp op2) 11667 { 11668 IRTemp op1 = newTemp(Ity_I64); 11669 IRTemp result = newTemp(Ity_I128); 11670 11671 assign(op1, get_gpr_dw0(r1 + 1)); 11672 assign(result, binop(op, mkexpr(op1), mkexpr(op2))); 11673 put_gpr_dw0(r1, unop(Iop_128HIto64, mkexpr(result))); // remainder 11674 put_gpr_dw0(r1 + 1, unop(Iop_128to64, mkexpr(result))); // quotient 11675 } 11676 11677 static const HChar * 11678 s390_irgen_DR(UChar r1, UChar r2) 11679 { 11680 IRTemp op2 = newTemp(Ity_I32); 11681 11682 assign(op2, get_gpr_w1(r2)); 11683 11684 s390_irgen_divide_64to32(Iop_DivModS64to32, r1, op2); 11685 11686 return "dr"; 11687 } 11688 11689 static const HChar * 11690 s390_irgen_D(UChar r1, IRTemp op2addr) 11691 { 11692 IRTemp op2 = newTemp(Ity_I32); 11693 11694 assign(op2, load(Ity_I32, mkexpr(op2addr))); 11695 11696 s390_irgen_divide_64to32(Iop_DivModS64to32, r1, op2); 11697 11698 return "d"; 11699 } 11700 11701 static const HChar * 11702 s390_irgen_DLR(UChar r1, UChar r2) 11703 { 11704 IRTemp op2 = newTemp(Ity_I32); 11705 11706 assign(op2, get_gpr_w1(r2)); 11707 11708 s390_irgen_divide_64to32(Iop_DivModU64to32, r1, op2); 11709 11710 return "dlr"; 11711 } 11712 11713 static const HChar * 11714 s390_irgen_DL(UChar r1, IRTemp op2addr) 11715 { 11716 IRTemp op2 = newTemp(Ity_I32); 11717 11718 assign(op2, load(Ity_I32, mkexpr(op2addr))); 11719 11720 s390_irgen_divide_64to32(Iop_DivModU64to32, r1, op2); 11721 11722 return "dl"; 11723 } 11724 11725 static const HChar * 11726 s390_irgen_DLG(UChar r1, IRTemp op2addr) 11727 { 11728 IRTemp op2 = newTemp(Ity_I64); 11729 11730 assign(op2, load(Ity_I64, mkexpr(op2addr))); 11731 11732 s390_irgen_divide_128to64(Iop_DivModU128to64, r1, op2); 11733 11734 return "dlg"; 11735 } 11736 11737 static const HChar * 11738 s390_irgen_DLGR(UChar r1, UChar r2) 11739 { 11740 IRTemp op2 = newTemp(Ity_I64); 11741 11742 assign(op2, get_gpr_dw0(r2)); 11743 11744 s390_irgen_divide_128to64(Iop_DivModU128to64, r1, op2); 11745 11746 return "dlgr"; 11747 } 11748 11749 static const HChar * 11750 s390_irgen_DSGR(UChar r1, UChar r2) 11751 { 11752 IRTemp op2 = newTemp(Ity_I64); 11753 11754 assign(op2, get_gpr_dw0(r2)); 11755 11756 s390_irgen_divide_64to64(Iop_DivModS64to64, r1, op2); 11757 11758 return "dsgr"; 11759 } 11760 11761 static const HChar * 11762 s390_irgen_DSG(UChar r1, IRTemp op2addr) 11763 { 11764 IRTemp op2 = newTemp(Ity_I64); 11765 11766 assign(op2, load(Ity_I64, mkexpr(op2addr))); 11767 11768 s390_irgen_divide_64to64(Iop_DivModS64to64, r1, op2); 11769 11770 return "dsg"; 11771 } 11772 11773 static const HChar * 11774 s390_irgen_DSGFR(UChar r1, UChar r2) 11775 { 11776 IRTemp op2 = newTemp(Ity_I64); 11777 11778 assign(op2, unop(Iop_32Sto64, get_gpr_w1(r2))); 11779 11780 s390_irgen_divide_64to64(Iop_DivModS64to64, r1, op2); 11781 11782 return "dsgfr"; 11783 } 11784 11785 static const HChar * 11786 s390_irgen_DSGF(UChar r1, IRTemp op2addr) 11787 { 11788 IRTemp op2 = newTemp(Ity_I64); 11789 11790 assign(op2, unop(Iop_32Sto64, load(Ity_I32, mkexpr(op2addr)))); 11791 11792 s390_irgen_divide_64to64(Iop_DivModS64to64, r1, op2); 11793 11794 return "dsgf"; 11795 } 11796 11797 static void 11798 s390_irgen_load_ar_multiple(UChar r1, UChar r3, IRTemp op2addr) 11799 { 11800 UChar reg; 11801 IRTemp addr = newTemp(Ity_I64); 11802 11803 assign(addr, mkexpr(op2addr)); 11804 reg = r1; 11805 do { 11806 IRTemp old = addr; 11807 11808 reg %= 16; 11809 put_ar_w0(reg, load(Ity_I32, mkexpr(addr))); 11810 addr = newTemp(Ity_I64); 11811 assign(addr, binop(Iop_Add64, mkexpr(old), mkU64(4))); 11812 reg++; 11813 } while (reg != (r3 + 1)); 11814 } 11815 11816 static const HChar * 11817 s390_irgen_LAM(UChar r1, UChar r3, IRTemp op2addr) 11818 { 11819 s390_irgen_load_ar_multiple(r1, r3, op2addr); 11820 11821 return "lam"; 11822 } 11823 11824 static const HChar * 11825 s390_irgen_LAMY(UChar r1, UChar r3, IRTemp op2addr) 11826 { 11827 s390_irgen_load_ar_multiple(r1, r3, op2addr); 11828 11829 return "lamy"; 11830 } 11831 11832 static void 11833 s390_irgen_store_ar_multiple(UChar r1, UChar r3, IRTemp op2addr) 11834 { 11835 UChar reg; 11836 IRTemp addr = newTemp(Ity_I64); 11837 11838 assign(addr, mkexpr(op2addr)); 11839 reg = r1; 11840 do { 11841 IRTemp old = addr; 11842 11843 reg %= 16; 11844 store(mkexpr(addr), get_ar_w0(reg)); 11845 addr = newTemp(Ity_I64); 11846 assign(addr, binop(Iop_Add64, mkexpr(old), mkU64(4))); 11847 reg++; 11848 } while (reg != (r3 + 1)); 11849 } 11850 11851 static const HChar * 11852 s390_irgen_STAM(UChar r1, UChar r3, IRTemp op2addr) 11853 { 11854 s390_irgen_store_ar_multiple(r1, r3, op2addr); 11855 11856 return "stam"; 11857 } 11858 11859 static const HChar * 11860 s390_irgen_STAMY(UChar r1, UChar r3, IRTemp op2addr) 11861 { 11862 s390_irgen_store_ar_multiple(r1, r3, op2addr); 11863 11864 return "stamy"; 11865 } 11866 11867 11868 /* Implementation for 32-bit compare-and-swap */ 11869 static void 11870 s390_irgen_cas_32(UChar r1, UChar r3, IRTemp op2addr) 11871 { 11872 IRCAS *cas; 11873 IRTemp op1 = newTemp(Ity_I32); 11874 IRTemp old_mem = newTemp(Ity_I32); 11875 IRTemp op3 = newTemp(Ity_I32); 11876 IRTemp result = newTemp(Ity_I32); 11877 IRTemp nequal = newTemp(Ity_I1); 11878 11879 assign(op1, get_gpr_w1(r1)); 11880 assign(op3, get_gpr_w1(r3)); 11881 11882 /* The first and second operands are compared. If they are equal, 11883 the third operand is stored at the second- operand location. */ 11884 cas = mkIRCAS(IRTemp_INVALID, old_mem, 11885 Iend_BE, mkexpr(op2addr), 11886 NULL, mkexpr(op1), /* expected value */ 11887 NULL, mkexpr(op3) /* new value */); 11888 stmt(IRStmt_CAS(cas)); 11889 11890 /* Set CC. Operands compared equal -> 0, else 1. */ 11891 assign(result, binop(Iop_Sub32, mkexpr(op1), mkexpr(old_mem))); 11892 s390_cc_thunk_put1(S390_CC_OP_BITWISE, result, False); 11893 11894 /* If operands were equal (cc == 0) just store the old value op1 in r1. 11895 Otherwise, store the old_value from memory in r1 and yield. */ 11896 assign(nequal, binop(Iop_CmpNE32, s390_call_calculate_cc(), mkU32(0))); 11897 put_gpr_w1(r1, mkite(mkexpr(nequal), mkexpr(old_mem), mkexpr(op1))); 11898 yield_if(mkexpr(nequal)); 11899 } 11900 11901 static const HChar * 11902 s390_irgen_CS(UChar r1, UChar r3, IRTemp op2addr) 11903 { 11904 s390_irgen_cas_32(r1, r3, op2addr); 11905 11906 return "cs"; 11907 } 11908 11909 static const HChar * 11910 s390_irgen_CSY(UChar r1, UChar r3, IRTemp op2addr) 11911 { 11912 s390_irgen_cas_32(r1, r3, op2addr); 11913 11914 return "csy"; 11915 } 11916 11917 static const HChar * 11918 s390_irgen_CSG(UChar r1, UChar r3, IRTemp op2addr) 11919 { 11920 IRCAS *cas; 11921 IRTemp op1 = newTemp(Ity_I64); 11922 IRTemp old_mem = newTemp(Ity_I64); 11923 IRTemp op3 = newTemp(Ity_I64); 11924 IRTemp result = newTemp(Ity_I64); 11925 IRTemp nequal = newTemp(Ity_I1); 11926 11927 assign(op1, get_gpr_dw0(r1)); 11928 assign(op3, get_gpr_dw0(r3)); 11929 11930 /* The first and second operands are compared. If they are equal, 11931 the third operand is stored at the second- operand location. */ 11932 cas = mkIRCAS(IRTemp_INVALID, old_mem, 11933 Iend_BE, mkexpr(op2addr), 11934 NULL, mkexpr(op1), /* expected value */ 11935 NULL, mkexpr(op3) /* new value */); 11936 stmt(IRStmt_CAS(cas)); 11937 11938 /* Set CC. Operands compared equal -> 0, else 1. */ 11939 assign(result, binop(Iop_Sub64, mkexpr(op1), mkexpr(old_mem))); 11940 s390_cc_thunk_put1(S390_CC_OP_BITWISE, result, False); 11941 11942 /* If operands were equal (cc == 0) just store the old value op1 in r1. 11943 Otherwise, store the old_value from memory in r1 and yield. */ 11944 assign(nequal, binop(Iop_CmpNE32, s390_call_calculate_cc(), mkU32(0))); 11945 put_gpr_dw0(r1, mkite(mkexpr(nequal), mkexpr(old_mem), mkexpr(op1))); 11946 yield_if(mkexpr(nequal)); 11947 11948 return "csg"; 11949 } 11950 11951 /* Implementation for 32-bit compare-double-and-swap */ 11952 static void 11953 s390_irgen_cdas_32(UChar r1, UChar r3, IRTemp op2addr) 11954 { 11955 IRCAS *cas; 11956 IRTemp op1_high = newTemp(Ity_I32); 11957 IRTemp op1_low = newTemp(Ity_I32); 11958 IRTemp old_mem_high = newTemp(Ity_I32); 11959 IRTemp old_mem_low = newTemp(Ity_I32); 11960 IRTemp op3_high = newTemp(Ity_I32); 11961 IRTemp op3_low = newTemp(Ity_I32); 11962 IRTemp result = newTemp(Ity_I32); 11963 IRTemp nequal = newTemp(Ity_I1); 11964 11965 assign(op1_high, get_gpr_w1(r1)); 11966 assign(op1_low, get_gpr_w1(r1+1)); 11967 assign(op3_high, get_gpr_w1(r3)); 11968 assign(op3_low, get_gpr_w1(r3+1)); 11969 11970 /* The first and second operands are compared. If they are equal, 11971 the third operand is stored at the second-operand location. */ 11972 cas = mkIRCAS(old_mem_high, old_mem_low, 11973 Iend_BE, mkexpr(op2addr), 11974 mkexpr(op1_high), mkexpr(op1_low), /* expected value */ 11975 mkexpr(op3_high), mkexpr(op3_low) /* new value */); 11976 stmt(IRStmt_CAS(cas)); 11977 11978 /* Set CC. Operands compared equal -> 0, else 1. */ 11979 assign(result, unop(Iop_1Uto32, 11980 binop(Iop_CmpNE32, 11981 binop(Iop_Or32, 11982 binop(Iop_Xor32, mkexpr(op1_high), mkexpr(old_mem_high)), 11983 binop(Iop_Xor32, mkexpr(op1_low), mkexpr(old_mem_low))), 11984 mkU32(0)))); 11985 11986 s390_cc_thunk_put1(S390_CC_OP_BITWISE, result, False); 11987 11988 /* If operands were equal (cc == 0) just store the old value op1 in r1. 11989 Otherwise, store the old_value from memory in r1 and yield. */ 11990 assign(nequal, binop(Iop_CmpNE32, s390_call_calculate_cc(), mkU32(0))); 11991 put_gpr_w1(r1, mkite(mkexpr(nequal), mkexpr(old_mem_high), mkexpr(op1_high))); 11992 put_gpr_w1(r1+1, mkite(mkexpr(nequal), mkexpr(old_mem_low), mkexpr(op1_low))); 11993 yield_if(mkexpr(nequal)); 11994 } 11995 11996 static const HChar * 11997 s390_irgen_CDS(UChar r1, UChar r3, IRTemp op2addr) 11998 { 11999 s390_irgen_cdas_32(r1, r3, op2addr); 12000 12001 return "cds"; 12002 } 12003 12004 static const HChar * 12005 s390_irgen_CDSY(UChar r1, UChar r3, IRTemp op2addr) 12006 { 12007 s390_irgen_cdas_32(r1, r3, op2addr); 12008 12009 return "cdsy"; 12010 } 12011 12012 static const HChar * 12013 s390_irgen_CDSG(UChar r1, UChar r3, IRTemp op2addr) 12014 { 12015 IRCAS *cas; 12016 IRTemp op1_high = newTemp(Ity_I64); 12017 IRTemp op1_low = newTemp(Ity_I64); 12018 IRTemp old_mem_high = newTemp(Ity_I64); 12019 IRTemp old_mem_low = newTemp(Ity_I64); 12020 IRTemp op3_high = newTemp(Ity_I64); 12021 IRTemp op3_low = newTemp(Ity_I64); 12022 IRTemp result = newTemp(Ity_I64); 12023 IRTemp nequal = newTemp(Ity_I1); 12024 12025 assign(op1_high, get_gpr_dw0(r1)); 12026 assign(op1_low, get_gpr_dw0(r1+1)); 12027 assign(op3_high, get_gpr_dw0(r3)); 12028 assign(op3_low, get_gpr_dw0(r3+1)); 12029 12030 /* The first and second operands are compared. If they are equal, 12031 the third operand is stored at the second-operand location. */ 12032 cas = mkIRCAS(old_mem_high, old_mem_low, 12033 Iend_BE, mkexpr(op2addr), 12034 mkexpr(op1_high), mkexpr(op1_low), /* expected value */ 12035 mkexpr(op3_high), mkexpr(op3_low) /* new value */); 12036 stmt(IRStmt_CAS(cas)); 12037 12038 /* Set CC. Operands compared equal -> 0, else 1. */ 12039 assign(result, unop(Iop_1Uto64, 12040 binop(Iop_CmpNE64, 12041 binop(Iop_Or64, 12042 binop(Iop_Xor64, mkexpr(op1_high), mkexpr(old_mem_high)), 12043 binop(Iop_Xor64, mkexpr(op1_low), mkexpr(old_mem_low))), 12044 mkU64(0)))); 12045 12046 s390_cc_thunk_put1(S390_CC_OP_BITWISE, result, False); 12047 12048 /* If operands were equal (cc == 0) just store the old value op1 in r1. 12049 Otherwise, store the old_value from memory in r1 and yield. */ 12050 assign(nequal, binop(Iop_CmpNE32, s390_call_calculate_cc(), mkU32(0))); 12051 put_gpr_dw0(r1, mkite(mkexpr(nequal), mkexpr(old_mem_high), mkexpr(op1_high))); 12052 put_gpr_dw0(r1+1, mkite(mkexpr(nequal), mkexpr(old_mem_low), mkexpr(op1_low))); 12053 yield_if(mkexpr(nequal)); 12054 12055 return "cdsg"; 12056 } 12057 12058 12059 /* Binary floating point */ 12060 12061 static const HChar * 12062 s390_irgen_AXBR(UChar r1, UChar r2) 12063 { 12064 IRTemp op1 = newTemp(Ity_F128); 12065 IRTemp op2 = newTemp(Ity_F128); 12066 IRTemp result = newTemp(Ity_F128); 12067 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12068 12069 assign(op1, get_fpr_pair(r1)); 12070 assign(op2, get_fpr_pair(r2)); 12071 assign(result, triop(Iop_AddF128, mkexpr(rounding_mode), mkexpr(op1), 12072 mkexpr(op2))); 12073 put_fpr_pair(r1, mkexpr(result)); 12074 12075 s390_cc_thunk_put1f128(S390_CC_OP_BFP_RESULT_128, result); 12076 12077 return "axbr"; 12078 } 12079 12080 static const HChar * 12081 s390_irgen_CEBR(UChar r1, UChar r2) 12082 { 12083 IRTemp op1 = newTemp(Ity_F32); 12084 IRTemp op2 = newTemp(Ity_F32); 12085 IRTemp cc_vex = newTemp(Ity_I32); 12086 IRTemp cc_s390 = newTemp(Ity_I32); 12087 12088 assign(op1, get_fpr_w0(r1)); 12089 assign(op2, get_fpr_w0(r2)); 12090 assign(cc_vex, binop(Iop_CmpF32, mkexpr(op1), mkexpr(op2))); 12091 12092 assign(cc_s390, convert_vex_bfpcc_to_s390(cc_vex)); 12093 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 12094 12095 return "cebr"; 12096 } 12097 12098 static const HChar * 12099 s390_irgen_CDBR(UChar r1, UChar r2) 12100 { 12101 IRTemp op1 = newTemp(Ity_F64); 12102 IRTemp op2 = newTemp(Ity_F64); 12103 IRTemp cc_vex = newTemp(Ity_I32); 12104 IRTemp cc_s390 = newTemp(Ity_I32); 12105 12106 assign(op1, get_fpr_dw0(r1)); 12107 assign(op2, get_fpr_dw0(r2)); 12108 assign(cc_vex, binop(Iop_CmpF64, mkexpr(op1), mkexpr(op2))); 12109 12110 assign(cc_s390, convert_vex_bfpcc_to_s390(cc_vex)); 12111 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 12112 12113 return "cdbr"; 12114 } 12115 12116 static const HChar * 12117 s390_irgen_CXBR(UChar r1, UChar r2) 12118 { 12119 IRTemp op1 = newTemp(Ity_F128); 12120 IRTemp op2 = newTemp(Ity_F128); 12121 IRTemp cc_vex = newTemp(Ity_I32); 12122 IRTemp cc_s390 = newTemp(Ity_I32); 12123 12124 assign(op1, get_fpr_pair(r1)); 12125 assign(op2, get_fpr_pair(r2)); 12126 assign(cc_vex, binop(Iop_CmpF128, mkexpr(op1), mkexpr(op2))); 12127 12128 assign(cc_s390, convert_vex_bfpcc_to_s390(cc_vex)); 12129 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 12130 12131 return "cxbr"; 12132 } 12133 12134 static const HChar * 12135 s390_irgen_CEB(UChar r1, IRTemp op2addr) 12136 { 12137 IRTemp op1 = newTemp(Ity_F32); 12138 IRTemp op2 = newTemp(Ity_F32); 12139 IRTemp cc_vex = newTemp(Ity_I32); 12140 IRTemp cc_s390 = newTemp(Ity_I32); 12141 12142 assign(op1, get_fpr_w0(r1)); 12143 assign(op2, load(Ity_F32, mkexpr(op2addr))); 12144 assign(cc_vex, binop(Iop_CmpF32, mkexpr(op1), mkexpr(op2))); 12145 12146 assign(cc_s390, convert_vex_bfpcc_to_s390(cc_vex)); 12147 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 12148 12149 return "ceb"; 12150 } 12151 12152 static const HChar * 12153 s390_irgen_CDB(UChar r1, IRTemp op2addr) 12154 { 12155 IRTemp op1 = newTemp(Ity_F64); 12156 IRTemp op2 = newTemp(Ity_F64); 12157 IRTemp cc_vex = newTemp(Ity_I32); 12158 IRTemp cc_s390 = newTemp(Ity_I32); 12159 12160 assign(op1, get_fpr_dw0(r1)); 12161 assign(op2, load(Ity_F64, mkexpr(op2addr))); 12162 assign(cc_vex, binop(Iop_CmpF64, mkexpr(op1), mkexpr(op2))); 12163 12164 assign(cc_s390, convert_vex_bfpcc_to_s390(cc_vex)); 12165 s390_cc_thunk_put1(S390_CC_OP_SET, cc_s390, False); 12166 12167 return "cdb"; 12168 } 12169 12170 static const HChar * 12171 s390_irgen_CXFBR(UChar m3 __attribute__((unused)), 12172 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 12173 { 12174 IRTemp op2 = newTemp(Ity_I32); 12175 12176 assign(op2, get_gpr_w1(r2)); 12177 put_fpr_pair(r1, unop(Iop_I32StoF128, mkexpr(op2))); 12178 12179 return "cxfbr"; 12180 } 12181 12182 static const HChar * 12183 s390_irgen_CXLFBR(UChar m3 __attribute__((unused)), 12184 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 12185 { 12186 if (! s390_host_has_fpext) { 12187 emulation_failure(EmFail_S390X_fpext); 12188 } else { 12189 IRTemp op2 = newTemp(Ity_I32); 12190 12191 assign(op2, get_gpr_w1(r2)); 12192 put_fpr_pair(r1, unop(Iop_I32UtoF128, mkexpr(op2))); 12193 } 12194 return "cxlfbr"; 12195 } 12196 12197 12198 static const HChar * 12199 s390_irgen_CXGBR(UChar m3 __attribute__((unused)), 12200 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 12201 { 12202 IRTemp op2 = newTemp(Ity_I64); 12203 12204 assign(op2, get_gpr_dw0(r2)); 12205 put_fpr_pair(r1, unop(Iop_I64StoF128, mkexpr(op2))); 12206 12207 return "cxgbr"; 12208 } 12209 12210 static const HChar * 12211 s390_irgen_CXLGBR(UChar m3 __attribute__((unused)), 12212 UChar m4 __attribute__((unused)), UChar r1, UChar r2) 12213 { 12214 if (! s390_host_has_fpext) { 12215 emulation_failure(EmFail_S390X_fpext); 12216 } else { 12217 IRTemp op2 = newTemp(Ity_I64); 12218 12219 assign(op2, get_gpr_dw0(r2)); 12220 put_fpr_pair(r1, unop(Iop_I64UtoF128, mkexpr(op2))); 12221 } 12222 return "cxlgbr"; 12223 } 12224 12225 static const HChar * 12226 s390_irgen_CFXBR(UChar m3, UChar m4 __attribute__((unused)), 12227 UChar r1, UChar r2) 12228 { 12229 IRTemp op = newTemp(Ity_F128); 12230 IRTemp result = newTemp(Ity_I32); 12231 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 12232 12233 assign(op, get_fpr_pair(r2)); 12234 assign(result, binop(Iop_F128toI32S, mkexpr(rounding_mode), 12235 mkexpr(op))); 12236 put_gpr_w1(r1, mkexpr(result)); 12237 s390_cc_thunk_put1f128Z(S390_CC_OP_BFP_128_TO_INT_32, op, rounding_mode); 12238 12239 return "cfxbr"; 12240 } 12241 12242 static const HChar * 12243 s390_irgen_CLFXBR(UChar m3, UChar m4 __attribute__((unused)), 12244 UChar r1, UChar r2) 12245 { 12246 if (! s390_host_has_fpext) { 12247 emulation_failure(EmFail_S390X_fpext); 12248 } else { 12249 IRTemp op = newTemp(Ity_F128); 12250 IRTemp result = newTemp(Ity_I32); 12251 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 12252 12253 assign(op, get_fpr_pair(r2)); 12254 assign(result, binop(Iop_F128toI32U, mkexpr(rounding_mode), 12255 mkexpr(op))); 12256 put_gpr_w1(r1, mkexpr(result)); 12257 s390_cc_thunk_put1f128Z(S390_CC_OP_BFP_128_TO_UINT_32, op, rounding_mode); 12258 } 12259 return "clfxbr"; 12260 } 12261 12262 12263 static const HChar * 12264 s390_irgen_CGXBR(UChar m3, UChar m4 __attribute__((unused)), 12265 UChar r1, UChar r2) 12266 { 12267 IRTemp op = newTemp(Ity_F128); 12268 IRTemp result = newTemp(Ity_I64); 12269 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 12270 12271 assign(op, get_fpr_pair(r2)); 12272 assign(result, binop(Iop_F128toI64S, mkexpr(rounding_mode), 12273 mkexpr(op))); 12274 put_gpr_dw0(r1, mkexpr(result)); 12275 s390_cc_thunk_put1f128Z(S390_CC_OP_BFP_128_TO_INT_64, op, rounding_mode); 12276 12277 return "cgxbr"; 12278 } 12279 12280 static const HChar * 12281 s390_irgen_CLGXBR(UChar m3, UChar m4 __attribute__((unused)), 12282 UChar r1, UChar r2) 12283 { 12284 if (! s390_host_has_fpext) { 12285 emulation_failure(EmFail_S390X_fpext); 12286 } else { 12287 IRTemp op = newTemp(Ity_F128); 12288 IRTemp result = newTemp(Ity_I64); 12289 IRTemp rounding_mode = encode_bfp_rounding_mode(m3); 12290 12291 assign(op, get_fpr_pair(r2)); 12292 assign(result, binop(Iop_F128toI64U, mkexpr(rounding_mode), 12293 mkexpr(op))); 12294 put_gpr_dw0(r1, mkexpr(result)); 12295 s390_cc_thunk_put1f128Z(S390_CC_OP_BFP_128_TO_UINT_64, op, 12296 rounding_mode); 12297 } 12298 return "clgxbr"; 12299 } 12300 12301 static const HChar * 12302 s390_irgen_DXBR(UChar r1, UChar r2) 12303 { 12304 IRTemp op1 = newTemp(Ity_F128); 12305 IRTemp op2 = newTemp(Ity_F128); 12306 IRTemp result = newTemp(Ity_F128); 12307 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12308 12309 assign(op1, get_fpr_pair(r1)); 12310 assign(op2, get_fpr_pair(r2)); 12311 assign(result, triop(Iop_DivF128, mkexpr(rounding_mode), mkexpr(op1), 12312 mkexpr(op2))); 12313 put_fpr_pair(r1, mkexpr(result)); 12314 12315 return "dxbr"; 12316 } 12317 12318 static const HChar * 12319 s390_irgen_LTXBR(UChar r1, UChar r2) 12320 { 12321 IRTemp result = newTemp(Ity_F128); 12322 12323 assign(result, get_fpr_pair(r2)); 12324 put_fpr_pair(r1, mkexpr(result)); 12325 s390_cc_thunk_put1f128(S390_CC_OP_BFP_RESULT_128, result); 12326 12327 return "ltxbr"; 12328 } 12329 12330 static const HChar * 12331 s390_irgen_LCXBR(UChar r1, UChar r2) 12332 { 12333 IRTemp result = newTemp(Ity_F128); 12334 12335 assign(result, unop(Iop_NegF128, get_fpr_pair(r2))); 12336 put_fpr_pair(r1, mkexpr(result)); 12337 s390_cc_thunk_put1f128(S390_CC_OP_BFP_RESULT_128, result); 12338 12339 return "lcxbr"; 12340 } 12341 12342 static const HChar * 12343 s390_irgen_LXDBR(UChar r1, UChar r2) 12344 { 12345 IRTemp op = newTemp(Ity_F64); 12346 12347 assign(op, get_fpr_dw0(r2)); 12348 put_fpr_pair(r1, unop(Iop_F64toF128, mkexpr(op))); 12349 12350 return "lxdbr"; 12351 } 12352 12353 static const HChar * 12354 s390_irgen_LXEBR(UChar r1, UChar r2) 12355 { 12356 IRTemp op = newTemp(Ity_F32); 12357 12358 assign(op, get_fpr_w0(r2)); 12359 put_fpr_pair(r1, unop(Iop_F32toF128, mkexpr(op))); 12360 12361 return "lxebr"; 12362 } 12363 12364 static const HChar * 12365 s390_irgen_LXDB(UChar r1, IRTemp op2addr) 12366 { 12367 IRTemp op = newTemp(Ity_F64); 12368 12369 assign(op, load(Ity_F64, mkexpr(op2addr))); 12370 put_fpr_pair(r1, unop(Iop_F64toF128, mkexpr(op))); 12371 12372 return "lxdb"; 12373 } 12374 12375 static const HChar * 12376 s390_irgen_LXEB(UChar r1, IRTemp op2addr) 12377 { 12378 IRTemp op = newTemp(Ity_F32); 12379 12380 assign(op, load(Ity_F32, mkexpr(op2addr))); 12381 put_fpr_pair(r1, unop(Iop_F32toF128, mkexpr(op))); 12382 12383 return "lxeb"; 12384 } 12385 12386 static const HChar * 12387 s390_irgen_FIEBRA(UChar m3, UChar m4 __attribute__((unused)), 12388 UChar r1, UChar r2) 12389 { 12390 IRTemp result = newTemp(Ity_F32); 12391 12392 assign(result, binop(Iop_RoundF32toInt, mkexpr(encode_bfp_rounding_mode(m3)), 12393 get_fpr_w0(r2))); 12394 put_fpr_w0(r1, mkexpr(result)); 12395 12396 return "fiebra"; 12397 } 12398 12399 static const HChar * 12400 s390_irgen_FIDBRA(UChar m3, UChar m4 __attribute__((unused)), 12401 UChar r1, UChar r2) 12402 { 12403 IRTemp result = newTemp(Ity_F64); 12404 12405 assign(result, binop(Iop_RoundF64toInt, mkexpr(encode_bfp_rounding_mode(m3)), 12406 get_fpr_dw0(r2))); 12407 put_fpr_dw0(r1, mkexpr(result)); 12408 12409 return "fidbra"; 12410 } 12411 12412 static const HChar * 12413 s390_irgen_FIXBRA(UChar m3, UChar m4 __attribute__((unused)), 12414 UChar r1, UChar r2) 12415 { 12416 IRTemp result = newTemp(Ity_F128); 12417 12418 assign(result, binop(Iop_RoundF128toInt, mkexpr(encode_bfp_rounding_mode(m3)), 12419 get_fpr_pair(r2))); 12420 put_fpr_pair(r1, mkexpr(result)); 12421 12422 return "fixbra"; 12423 } 12424 12425 static const HChar * 12426 s390_irgen_LNEBR(UChar r1, UChar r2) 12427 { 12428 IRTemp result = newTemp(Ity_F32); 12429 12430 assign(result, unop(Iop_NegF32, unop(Iop_AbsF32, get_fpr_w0(r2)))); 12431 put_fpr_w0(r1, mkexpr(result)); 12432 s390_cc_thunk_put1f(S390_CC_OP_BFP_RESULT_32, result); 12433 12434 return "lnebr"; 12435 } 12436 12437 static const HChar * 12438 s390_irgen_LNDBR(UChar r1, UChar r2) 12439 { 12440 IRTemp result = newTemp(Ity_F64); 12441 12442 assign(result, unop(Iop_NegF64, unop(Iop_AbsF64, get_fpr_dw0(r2)))); 12443 put_fpr_dw0(r1, mkexpr(result)); 12444 s390_cc_thunk_put1f(S390_CC_OP_BFP_RESULT_64, result); 12445 12446 return "lndbr"; 12447 } 12448 12449 static const HChar * 12450 s390_irgen_LNXBR(UChar r1, UChar r2) 12451 { 12452 IRTemp result = newTemp(Ity_F128); 12453 12454 assign(result, unop(Iop_NegF128, unop(Iop_AbsF128, get_fpr_pair(r2)))); 12455 put_fpr_pair(r1, mkexpr(result)); 12456 s390_cc_thunk_put1f128(S390_CC_OP_BFP_RESULT_128, result); 12457 12458 return "lnxbr"; 12459 } 12460 12461 static const HChar * 12462 s390_irgen_LPEBR(UChar r1, UChar r2) 12463 { 12464 IRTemp result = newTemp(Ity_F32); 12465 12466 assign(result, unop(Iop_AbsF32, get_fpr_w0(r2))); 12467 put_fpr_w0(r1, mkexpr(result)); 12468 s390_cc_thunk_put1f(S390_CC_OP_BFP_RESULT_32, result); 12469 12470 return "lpebr"; 12471 } 12472 12473 static const HChar * 12474 s390_irgen_LPDBR(UChar r1, UChar r2) 12475 { 12476 IRTemp result = newTemp(Ity_F64); 12477 12478 assign(result, unop(Iop_AbsF64, get_fpr_dw0(r2))); 12479 put_fpr_dw0(r1, mkexpr(result)); 12480 s390_cc_thunk_put1f(S390_CC_OP_BFP_RESULT_64, result); 12481 12482 return "lpdbr"; 12483 } 12484 12485 static const HChar * 12486 s390_irgen_LPXBR(UChar r1, UChar r2) 12487 { 12488 IRTemp result = newTemp(Ity_F128); 12489 12490 assign(result, unop(Iop_AbsF128, get_fpr_pair(r2))); 12491 put_fpr_pair(r1, mkexpr(result)); 12492 s390_cc_thunk_put1f128(S390_CC_OP_BFP_RESULT_128, result); 12493 12494 return "lpxbr"; 12495 } 12496 12497 static const HChar * 12498 s390_irgen_LDXBR(UChar m3, UChar m4 __attribute__((unused)), 12499 UChar r1, UChar r2) 12500 { 12501 if (! s390_host_has_fpext && m3 != S390_BFP_ROUND_PER_FPC) { 12502 emulation_warning(EmWarn_S390X_fpext_rounding); 12503 m3 = S390_BFP_ROUND_PER_FPC; 12504 } 12505 IRTemp result = newTemp(Ity_F64); 12506 12507 assign(result, binop(Iop_F128toF64, mkexpr(encode_bfp_rounding_mode(m3)), 12508 get_fpr_pair(r2))); 12509 put_fpr_dw0(r1, mkexpr(result)); 12510 12511 return "ldxbr"; 12512 } 12513 12514 static const HChar * 12515 s390_irgen_LEXBR(UChar m3, UChar m4 __attribute__((unused)), 12516 UChar r1, UChar r2) 12517 { 12518 if (! s390_host_has_fpext && m3 != S390_BFP_ROUND_PER_FPC) { 12519 emulation_warning(EmWarn_S390X_fpext_rounding); 12520 m3 = S390_BFP_ROUND_PER_FPC; 12521 } 12522 IRTemp result = newTemp(Ity_F32); 12523 12524 assign(result, binop(Iop_F128toF32, mkexpr(encode_bfp_rounding_mode(m3)), 12525 get_fpr_pair(r2))); 12526 put_fpr_w0(r1, mkexpr(result)); 12527 12528 return "lexbr"; 12529 } 12530 12531 static const HChar * 12532 s390_irgen_MXBR(UChar r1, UChar r2) 12533 { 12534 IRTemp op1 = newTemp(Ity_F128); 12535 IRTemp op2 = newTemp(Ity_F128); 12536 IRTemp result = newTemp(Ity_F128); 12537 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12538 12539 assign(op1, get_fpr_pair(r1)); 12540 assign(op2, get_fpr_pair(r2)); 12541 assign(result, triop(Iop_MulF128, mkexpr(rounding_mode), mkexpr(op1), 12542 mkexpr(op2))); 12543 put_fpr_pair(r1, mkexpr(result)); 12544 12545 return "mxbr"; 12546 } 12547 12548 static const HChar * 12549 s390_irgen_MAEBR(UChar r1, UChar r3, UChar r2) 12550 { 12551 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12552 12553 put_fpr_w0(r1, qop(Iop_MAddF32, mkexpr(rounding_mode), 12554 get_fpr_w0(r3), get_fpr_w0(r2), get_fpr_w0(r1))); 12555 12556 return "maebr"; 12557 } 12558 12559 static const HChar * 12560 s390_irgen_MADBR(UChar r1, UChar r3, UChar r2) 12561 { 12562 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12563 12564 put_fpr_dw0(r1, qop(Iop_MAddF64, mkexpr(rounding_mode), 12565 get_fpr_dw0(r3), get_fpr_dw0(r2), get_fpr_dw0(r1))); 12566 12567 return "madbr"; 12568 } 12569 12570 static const HChar * 12571 s390_irgen_MAEB(UChar r3, IRTemp op2addr, UChar r1) 12572 { 12573 IRExpr *op2 = load(Ity_F32, mkexpr(op2addr)); 12574 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12575 12576 put_fpr_w0(r1, qop(Iop_MAddF32, mkexpr(rounding_mode), 12577 get_fpr_w0(r3), op2, get_fpr_w0(r1))); 12578 12579 return "maeb"; 12580 } 12581 12582 static const HChar * 12583 s390_irgen_MADB(UChar r3, IRTemp op2addr, UChar r1) 12584 { 12585 IRExpr *op2 = load(Ity_F64, mkexpr(op2addr)); 12586 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12587 12588 put_fpr_dw0(r1, qop(Iop_MAddF64, mkexpr(rounding_mode), 12589 get_fpr_dw0(r3), op2, get_fpr_dw0(r1))); 12590 12591 return "madb"; 12592 } 12593 12594 static const HChar * 12595 s390_irgen_MSEBR(UChar r1, UChar r3, UChar r2) 12596 { 12597 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12598 12599 put_fpr_w0(r1, qop(Iop_MSubF32, mkexpr(rounding_mode), 12600 get_fpr_w0(r3), get_fpr_w0(r2), get_fpr_w0(r1))); 12601 12602 return "msebr"; 12603 } 12604 12605 static const HChar * 12606 s390_irgen_MSDBR(UChar r1, UChar r3, UChar r2) 12607 { 12608 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12609 12610 put_fpr_dw0(r1, qop(Iop_MSubF64, mkexpr(rounding_mode), 12611 get_fpr_dw0(r3), get_fpr_dw0(r2), get_fpr_dw0(r1))); 12612 12613 return "msdbr"; 12614 } 12615 12616 static const HChar * 12617 s390_irgen_MSEB(UChar r3, IRTemp op2addr, UChar r1) 12618 { 12619 IRExpr *op2 = load(Ity_F32, mkexpr(op2addr)); 12620 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12621 12622 put_fpr_w0(r1, qop(Iop_MSubF32, mkexpr(rounding_mode), 12623 get_fpr_w0(r3), op2, get_fpr_w0(r1))); 12624 12625 return "mseb"; 12626 } 12627 12628 static const HChar * 12629 s390_irgen_MSDB(UChar r3, IRTemp op2addr, UChar r1) 12630 { 12631 IRExpr *op2 = load(Ity_F64, mkexpr(op2addr)); 12632 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12633 12634 put_fpr_dw0(r1, qop(Iop_MSubF64, mkexpr(rounding_mode), 12635 get_fpr_dw0(r3), op2, get_fpr_dw0(r1))); 12636 12637 return "msdb"; 12638 } 12639 12640 static const HChar * 12641 s390_irgen_SQEBR(UChar r1, UChar r2) 12642 { 12643 IRTemp result = newTemp(Ity_F32); 12644 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12645 12646 assign(result, binop(Iop_SqrtF32, mkexpr(rounding_mode), get_fpr_w0(r2))); 12647 put_fpr_w0(r1, mkexpr(result)); 12648 12649 return "sqebr"; 12650 } 12651 12652 static const HChar * 12653 s390_irgen_SQDBR(UChar r1, UChar r2) 12654 { 12655 IRTemp result = newTemp(Ity_F64); 12656 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12657 12658 assign(result, binop(Iop_SqrtF64, mkexpr(rounding_mode), get_fpr_dw0(r2))); 12659 put_fpr_dw0(r1, mkexpr(result)); 12660 12661 return "sqdbr"; 12662 } 12663 12664 static const HChar * 12665 s390_irgen_SQXBR(UChar r1, UChar r2) 12666 { 12667 IRTemp result = newTemp(Ity_F128); 12668 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12669 12670 assign(result, binop(Iop_SqrtF128, mkexpr(rounding_mode), 12671 get_fpr_pair(r2))); 12672 put_fpr_pair(r1, mkexpr(result)); 12673 12674 return "sqxbr"; 12675 } 12676 12677 static const HChar * 12678 s390_irgen_SQEB(UChar r1, IRTemp op2addr) 12679 { 12680 IRTemp op = newTemp(Ity_F32); 12681 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12682 12683 assign(op, load(Ity_F32, mkexpr(op2addr))); 12684 put_fpr_w0(r1, binop(Iop_SqrtF32, mkexpr(rounding_mode), mkexpr(op))); 12685 12686 return "sqeb"; 12687 } 12688 12689 static const HChar * 12690 s390_irgen_SQDB(UChar r1, IRTemp op2addr) 12691 { 12692 IRTemp op = newTemp(Ity_F64); 12693 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12694 12695 assign(op, load(Ity_F64, mkexpr(op2addr))); 12696 put_fpr_dw0(r1, binop(Iop_SqrtF64, mkexpr(rounding_mode), mkexpr(op))); 12697 12698 return "sqdb"; 12699 } 12700 12701 static const HChar * 12702 s390_irgen_SXBR(UChar r1, UChar r2) 12703 { 12704 IRTemp op1 = newTemp(Ity_F128); 12705 IRTemp op2 = newTemp(Ity_F128); 12706 IRTemp result = newTemp(Ity_F128); 12707 IRTemp rounding_mode = encode_bfp_rounding_mode(S390_BFP_ROUND_PER_FPC); 12708 12709 assign(op1, get_fpr_pair(r1)); 12710 assign(op2, get_fpr_pair(r2)); 12711 assign(result, triop(Iop_SubF128, mkexpr(rounding_mode), mkexpr(op1), 12712 mkexpr(op2))); 12713 put_fpr_pair(r1, mkexpr(result)); 12714 s390_cc_thunk_put1f128(S390_CC_OP_BFP_RESULT_128, result); 12715 12716 return "sxbr"; 12717 } 12718 12719 static const HChar * 12720 s390_irgen_TCEB(UChar r1, IRTemp op2addr) 12721 { 12722 IRTemp value = newTemp(Ity_F32); 12723 12724 assign(value, get_fpr_w0(r1)); 12725 12726 s390_cc_thunk_putFZ(S390_CC_OP_BFP_TDC_32, value, op2addr); 12727 12728 return "tceb"; 12729 } 12730 12731 static const HChar * 12732 s390_irgen_TCDB(UChar r1, IRTemp op2addr) 12733 { 12734 IRTemp value = newTemp(Ity_F64); 12735 12736 assign(value, get_fpr_dw0(r1)); 12737 12738 s390_cc_thunk_putFZ(S390_CC_OP_BFP_TDC_64, value, op2addr); 12739 12740 return "tcdb"; 12741 } 12742 12743 static const HChar * 12744 s390_irgen_TCXB(UChar r1, IRTemp op2addr) 12745 { 12746 IRTemp value = newTemp(Ity_F128); 12747 12748 assign(value, get_fpr_pair(r1)); 12749 12750 s390_cc_thunk_put1f128Z(S390_CC_OP_BFP_TDC_128, value, op2addr); 12751 12752 return "tcxb"; 12753 } 12754 12755 static const HChar * 12756 s390_irgen_LCDFR(UChar r1, UChar r2) 12757 { 12758 IRTemp result = newTemp(Ity_F64); 12759 12760 assign(result, unop(Iop_NegF64, get_fpr_dw0(r2))); 12761 put_fpr_dw0(r1, mkexpr(result)); 12762 12763 return "lcdfr"; 12764 } 12765 12766 static const HChar * 12767 s390_irgen_LNDFR(UChar r1, UChar r2) 12768 { 12769 IRTemp result = newTemp(Ity_F64); 12770 12771 assign(result, unop(Iop_NegF64, unop(Iop_AbsF64, get_fpr_dw0(r2)))); 12772 put_fpr_dw0(r1, mkexpr(result)); 12773 12774 return "lndfr"; 12775 } 12776 12777 static const HChar * 12778 s390_irgen_LPDFR(UChar r1, UChar r2) 12779 { 12780 IRTemp result = newTemp(Ity_F64); 12781 12782 assign(result, unop(Iop_AbsF64, get_fpr_dw0(r2))); 12783 put_fpr_dw0(r1, mkexpr(result)); 12784 12785 return "lpdfr"; 12786 } 12787 12788 static const HChar * 12789 s390_irgen_LDGR(UChar r1, UChar r2) 12790 { 12791 put_fpr_dw0(r1, unop(Iop_ReinterpI64asF64, get_gpr_dw0(r2))); 12792 12793 return "ldgr"; 12794 } 12795 12796 static const HChar * 12797 s390_irgen_LGDR(UChar r1, UChar r2) 12798 { 12799 put_gpr_dw0(r1, unop(Iop_ReinterpF64asI64, get_fpr_dw0(r2))); 12800 12801 return "lgdr"; 12802 } 12803 12804 12805 static const HChar * 12806 s390_irgen_CPSDR(UChar r3, UChar r1, UChar r2) 12807 { 12808 IRTemp sign = newTemp(Ity_I64); 12809 IRTemp value = newTemp(Ity_I64); 12810 12811 assign(sign, binop(Iop_And64, unop(Iop_ReinterpF64asI64, get_fpr_dw0(r3)), 12812 mkU64(1ULL << 63))); 12813 assign(value, binop(Iop_And64, unop(Iop_ReinterpF64asI64, get_fpr_dw0(r2)), 12814 mkU64((1ULL << 63) - 1))); 12815 put_fpr_dw0(r1, unop(Iop_ReinterpI64asF64, binop(Iop_Or64, mkexpr(value), 12816 mkexpr(sign)))); 12817 12818 return "cpsdr"; 12819 } 12820 12821 12822 static IRExpr * 12823 s390_call_cvb(IRExpr *in) 12824 { 12825 IRExpr **args, *call; 12826 12827 args = mkIRExprVec_1(in); 12828 call = mkIRExprCCall(Ity_I32, 0 /*regparm*/, 12829 "s390_do_cvb", &s390_do_cvb, args); 12830 12831 /* Nothing is excluded from definedness checking. */ 12832 call->Iex.CCall.cee->mcx_mask = 0; 12833 12834 return call; 12835 } 12836 12837 static const HChar * 12838 s390_irgen_CVB(UChar r1, IRTemp op2addr) 12839 { 12840 put_gpr_w1(r1, s390_call_cvb(load(Ity_I64, mkexpr(op2addr)))); 12841 12842 return "cvb"; 12843 } 12844 12845 static const HChar * 12846 s390_irgen_CVBY(UChar r1, IRTemp op2addr) 12847 { 12848 put_gpr_w1(r1, s390_call_cvb(load(Ity_I64, mkexpr(op2addr)))); 12849 12850 return "cvby"; 12851 } 12852 12853 12854 static IRExpr * 12855 s390_call_cvd(IRExpr *in) 12856 { 12857 IRExpr **args, *call; 12858 12859 args = mkIRExprVec_1(in); 12860 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, 12861 "s390_do_cvd", &s390_do_cvd, args); 12862 12863 /* Nothing is excluded from definedness checking. */ 12864 call->Iex.CCall.cee->mcx_mask = 0; 12865 12866 return call; 12867 } 12868 12869 static const HChar * 12870 s390_irgen_CVD(UChar r1, IRTemp op2addr) 12871 { 12872 store(mkexpr(op2addr), s390_call_cvd(unop(Iop_32Uto64, get_gpr_w1(r1)))); 12873 12874 return "cvd"; 12875 } 12876 12877 static const HChar * 12878 s390_irgen_CVDY(UChar r1, IRTemp op2addr) 12879 { 12880 store(mkexpr(op2addr), s390_call_cvd(get_gpr_w1(r1))); 12881 12882 return "cvdy"; 12883 } 12884 12885 static const HChar * 12886 s390_irgen_FLOGR(UChar r1, UChar r2) 12887 { 12888 IRTemp input = newTemp(Ity_I64); 12889 IRTemp not_zero = newTemp(Ity_I64); 12890 IRTemp tmpnum = newTemp(Ity_I64); 12891 IRTemp num = newTemp(Ity_I64); 12892 IRTemp shift_amount = newTemp(Ity_I8); 12893 12894 /* We use the "count leading zeroes" operator because the number of 12895 leading zeroes is identical with the bit position of the first '1' bit. 12896 However, that operator does not work when the input value is zero. 12897 Therefore, we set the LSB of the input value to 1 and use Clz64 on 12898 the modified value. If input == 0, then the result is 64. Otherwise, 12899 the result of Clz64 is what we want. */ 12900 12901 assign(input, get_gpr_dw0(r2)); 12902 assign(not_zero, binop(Iop_Or64, mkexpr(input), mkU64(1))); 12903 assign(tmpnum, unop(Iop_Clz64, mkexpr(not_zero))); 12904 12905 /* num = (input == 0) ? 64 : tmpnum */ 12906 assign(num, mkite(binop(Iop_CmpEQ64, mkexpr(input), mkU64(0)), 12907 /* == 0 */ mkU64(64), 12908 /* != 0 */ mkexpr(tmpnum))); 12909 12910 put_gpr_dw0(r1, mkexpr(num)); 12911 12912 /* Set the leftmost '1' bit of the input value to zero. The general scheme 12913 is to first shift the input value by NUM + 1 bits to the left which 12914 causes the leftmost '1' bit to disappear. Then we shift logically to 12915 the right by NUM + 1 bits. Because the semantics of Iop_Shl64 and 12916 Iop_Shr64 are undefined if the shift-amount is greater than or equal to 12917 the width of the value-to-be-shifted, we need to special case 12918 NUM + 1 >= 64. This is equivalent to INPUT != 0 && INPUT != 1. 12919 For both such INPUT values the result will be 0. */ 12920 12921 assign(shift_amount, unop(Iop_64to8, binop(Iop_Add64, mkexpr(num), 12922 mkU64(1)))); 12923 12924 put_gpr_dw0(r1 + 1, 12925 mkite(binop(Iop_CmpLE64U, mkexpr(input), mkU64(1)), 12926 /* == 0 || == 1*/ mkU64(0), 12927 /* otherwise */ 12928 binop(Iop_Shr64, 12929 binop(Iop_Shl64, mkexpr(input), 12930 mkexpr(shift_amount)), 12931 mkexpr(shift_amount)))); 12932 12933 /* Compare the original value as an unsigned integer with 0. */ 12934 s390_cc_thunk_put2(S390_CC_OP_UNSIGNED_COMPARE, input, 12935 mktemp(Ity_I64, mkU64(0)), False); 12936 12937 return "flogr"; 12938 } 12939 12940 static const HChar * 12941 s390_irgen_STCK(IRTemp op2addr) 12942 { 12943 IRDirty *d; 12944 IRTemp cc = newTemp(Ity_I64); 12945 12946 d = unsafeIRDirty_1_N(cc, 0, "s390x_dirtyhelper_STCK", 12947 &s390x_dirtyhelper_STCK, 12948 mkIRExprVec_1(mkexpr(op2addr))); 12949 d->mFx = Ifx_Write; 12950 d->mAddr = mkexpr(op2addr); 12951 d->mSize = 8; 12952 stmt(IRStmt_Dirty(d)); 12953 s390_cc_thunk_fill(mkU64(S390_CC_OP_SET), 12954 mkexpr(cc), mkU64(0), mkU64(0)); 12955 return "stck"; 12956 } 12957 12958 static const HChar * 12959 s390_irgen_STCKF(IRTemp op2addr) 12960 { 12961 if (! s390_host_has_stckf) { 12962 emulation_failure(EmFail_S390X_stckf); 12963 } else { 12964 IRTemp cc = newTemp(Ity_I64); 12965 12966 IRDirty *d = unsafeIRDirty_1_N(cc, 0, "s390x_dirtyhelper_STCKF", 12967 &s390x_dirtyhelper_STCKF, 12968 mkIRExprVec_1(mkexpr(op2addr))); 12969 d->mFx = Ifx_Write; 12970 d->mAddr = mkexpr(op2addr); 12971 d->mSize = 8; 12972 stmt(IRStmt_Dirty(d)); 12973 s390_cc_thunk_fill(mkU64(S390_CC_OP_SET), 12974 mkexpr(cc), mkU64(0), mkU64(0)); 12975 } 12976 return "stckf"; 12977 } 12978 12979 static const HChar * 12980 s390_irgen_STCKE(IRTemp op2addr) 12981 { 12982 IRDirty *d; 12983 IRTemp cc = newTemp(Ity_I64); 12984 12985 d = unsafeIRDirty_1_N(cc, 0, "s390x_dirtyhelper_STCKE", 12986 &s390x_dirtyhelper_STCKE, 12987 mkIRExprVec_1(mkexpr(op2addr))); 12988 d->mFx = Ifx_Write; 12989 d->mAddr = mkexpr(op2addr); 12990 d->mSize = 16; 12991 stmt(IRStmt_Dirty(d)); 12992 s390_cc_thunk_fill(mkU64(S390_CC_OP_SET), 12993 mkexpr(cc), mkU64(0), mkU64(0)); 12994 return "stcke"; 12995 } 12996 12997 static const HChar * 12998 s390_irgen_STFLE(IRTemp op2addr) 12999 { 13000 if (! s390_host_has_stfle) { 13001 emulation_failure(EmFail_S390X_stfle); 13002 return "stfle"; 13003 } 13004 13005 IRDirty *d; 13006 IRTemp cc = newTemp(Ity_I64); 13007 13008 /* IRExpr_BBPTR() => Need to pass pointer to guest state to helper */ 13009 d = unsafeIRDirty_1_N(cc, 0, "s390x_dirtyhelper_STFLE", 13010 &s390x_dirtyhelper_STFLE, 13011 mkIRExprVec_2(IRExpr_BBPTR(), mkexpr(op2addr))); 13012 13013 d->nFxState = 1; 13014 vex_bzero(&d->fxState, sizeof(d->fxState)); 13015 13016 d->fxState[0].fx = Ifx_Modify; /* read then write */ 13017 d->fxState[0].offset = S390X_GUEST_OFFSET(guest_r0); 13018 d->fxState[0].size = sizeof(ULong); 13019 13020 d->mAddr = mkexpr(op2addr); 13021 /* Pretend all double words are written */ 13022 d->mSize = S390_NUM_FACILITY_DW * sizeof(ULong); 13023 d->mFx = Ifx_Write; 13024 13025 stmt(IRStmt_Dirty(d)); 13026 13027 s390_cc_thunk_fill(mkU64(S390_CC_OP_SET), mkexpr(cc), mkU64(0), mkU64(0)); 13028 13029 return "stfle"; 13030 } 13031 13032 static const HChar * 13033 s390_irgen_CKSM(UChar r1,UChar r2) 13034 { 13035 IRTemp addr = newTemp(Ity_I64); 13036 IRTemp op = newTemp(Ity_I32); 13037 IRTemp len = newTemp(Ity_I64); 13038 IRTemp oldval = newTemp(Ity_I32); 13039 IRTemp mask = newTemp(Ity_I32); 13040 IRTemp newop = newTemp(Ity_I32); 13041 IRTemp result = newTemp(Ity_I32); 13042 IRTemp result1 = newTemp(Ity_I32); 13043 IRTemp inc = newTemp(Ity_I64); 13044 13045 assign(oldval, get_gpr_w1(r1)); 13046 assign(addr, get_gpr_dw0(r2)); 13047 assign(len, get_gpr_dw0(r2+1)); 13048 13049 /* Condition code is always zero. */ 13050 s390_cc_set(0); 13051 13052 /* If length is zero, there is no need to calculate the checksum */ 13053 next_insn_if(binop(Iop_CmpEQ64, mkexpr(len), mkU64(0))); 13054 13055 /* Assiging the increment variable to adjust address and length 13056 later on. */ 13057 assign(inc, mkite(binop(Iop_CmpLT64U, mkexpr(len), mkU64(4)), 13058 mkexpr(len), mkU64(4))); 13059 13060 /* If length < 4 the final 4-byte 2nd operand value is computed by 13061 appending the remaining bytes to the right with 0. This is done 13062 by AND'ing the 4 bytes loaded from memory with an appropriate 13063 mask. If length >= 4, that mask is simply 0xffffffff. */ 13064 13065 assign(mask, mkite(binop(Iop_CmpLT64U, mkexpr(len), mkU64(4)), 13066 /* Mask computation when len < 4: 13067 0xffffffff << (32 - (len % 4)*8) */ 13068 binop(Iop_Shl32, mkU32(0xffffffff), 13069 unop(Iop_32to8, 13070 binop(Iop_Sub32, mkU32(32), 13071 binop(Iop_Shl32, 13072 unop(Iop_64to32, 13073 binop(Iop_And64, 13074 mkexpr(len), mkU64(3))), 13075 mkU8(3))))), 13076 mkU32(0xffffffff))); 13077 13078 assign(op, load(Ity_I32, mkexpr(addr))); 13079 assign(newop, binop(Iop_And32, mkexpr(op), mkexpr(mask))); 13080 assign(result, binop(Iop_Add32, mkexpr(newop), mkexpr(oldval))); 13081 13082 /* Checking for carry */ 13083 assign(result1, mkite(binop(Iop_CmpLT32U, mkexpr(result), mkexpr(newop)), 13084 binop(Iop_Add32, mkexpr(result), mkU32(1)), 13085 mkexpr(result))); 13086 13087 put_gpr_w1(r1, mkexpr(result1)); 13088 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(addr), mkexpr(inc))); 13089 put_gpr_dw0(r2+1, binop(Iop_Sub64, mkexpr(len), mkexpr(inc))); 13090 13091 iterate_if(binop(Iop_CmpNE64, mkexpr(len), mkU64(0))); 13092 13093 return "cksm"; 13094 } 13095 13096 static const HChar * 13097 s390_irgen_TROO(UChar m3, UChar r1, UChar r2) 13098 { 13099 IRTemp src_addr, des_addr, tab_addr, src_len, test_byte; 13100 src_addr = newTemp(Ity_I64); 13101 des_addr = newTemp(Ity_I64); 13102 tab_addr = newTemp(Ity_I64); 13103 test_byte = newTemp(Ity_I8); 13104 src_len = newTemp(Ity_I64); 13105 13106 assign(src_addr, get_gpr_dw0(r2)); 13107 assign(des_addr, get_gpr_dw0(r1)); 13108 assign(tab_addr, get_gpr_dw0(1)); 13109 assign(src_len, get_gpr_dw0(r1+1)); 13110 assign(test_byte, get_gpr_b7(0)); 13111 13112 IRTemp op = newTemp(Ity_I8); 13113 IRTemp op1 = newTemp(Ity_I8); 13114 IRTemp result = newTemp(Ity_I64); 13115 13116 /* End of source string? We're done; proceed to next insn */ 13117 s390_cc_set(0); 13118 next_insn_if(binop(Iop_CmpEQ64, mkexpr(src_len), mkU64(0))); 13119 13120 /* Load character from source string, index translation table and 13121 store translated character in op1. */ 13122 assign(op, load(Ity_I8, mkexpr(src_addr))); 13123 13124 assign(result, binop(Iop_Add64, unop(Iop_8Uto64, mkexpr(op)), 13125 mkexpr(tab_addr))); 13126 assign(op1, load(Ity_I8, mkexpr(result))); 13127 13128 if (! s390_host_has_etf2 || (m3 & 0x1) == 0) { 13129 s390_cc_set(1); 13130 next_insn_if(binop(Iop_CmpEQ8, mkexpr(op1), mkexpr(test_byte))); 13131 } 13132 store(get_gpr_dw0(r1), mkexpr(op1)); 13133 13134 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(des_addr), mkU64(1))); 13135 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(src_addr), mkU64(1))); 13136 put_gpr_dw0(r1+1, binop(Iop_Sub64, mkexpr(src_len), mkU64(1))); 13137 13138 iterate(); 13139 13140 return "troo"; 13141 } 13142 13143 static const HChar * 13144 s390_irgen_TRTO(UChar m3, UChar r1, UChar r2) 13145 { 13146 IRTemp src_addr, des_addr, tab_addr, src_len, test_byte; 13147 src_addr = newTemp(Ity_I64); 13148 des_addr = newTemp(Ity_I64); 13149 tab_addr = newTemp(Ity_I64); 13150 test_byte = newTemp(Ity_I8); 13151 src_len = newTemp(Ity_I64); 13152 13153 assign(src_addr, get_gpr_dw0(r2)); 13154 assign(des_addr, get_gpr_dw0(r1)); 13155 assign(tab_addr, get_gpr_dw0(1)); 13156 assign(src_len, get_gpr_dw0(r1+1)); 13157 assign(test_byte, get_gpr_b7(0)); 13158 13159 IRTemp op = newTemp(Ity_I16); 13160 IRTemp op1 = newTemp(Ity_I8); 13161 IRTemp result = newTemp(Ity_I64); 13162 13163 /* End of source string? We're done; proceed to next insn */ 13164 s390_cc_set(0); 13165 next_insn_if(binop(Iop_CmpEQ64, mkexpr(src_len), mkU64(0))); 13166 13167 /* Load character from source string, index translation table and 13168 store translated character in op1. */ 13169 assign(op, load(Ity_I16, mkexpr(src_addr))); 13170 13171 assign(result, binop(Iop_Add64, unop(Iop_16Uto64, mkexpr(op)), 13172 mkexpr(tab_addr))); 13173 13174 assign(op1, load(Ity_I8, mkexpr(result))); 13175 13176 if (! s390_host_has_etf2 || (m3 & 0x1) == 0) { 13177 s390_cc_set(1); 13178 next_insn_if(binop(Iop_CmpEQ8, mkexpr(op1), mkexpr(test_byte))); 13179 } 13180 store(get_gpr_dw0(r1), mkexpr(op1)); 13181 13182 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(src_addr), mkU64(2))); 13183 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(des_addr), mkU64(1))); 13184 put_gpr_dw0(r1+1, binop(Iop_Sub64, mkexpr(src_len), mkU64(2))); 13185 13186 iterate(); 13187 13188 return "trto"; 13189 } 13190 13191 static const HChar * 13192 s390_irgen_TROT(UChar m3, UChar r1, UChar r2) 13193 { 13194 IRTemp src_addr, des_addr, tab_addr, src_len, test_byte; 13195 src_addr = newTemp(Ity_I64); 13196 des_addr = newTemp(Ity_I64); 13197 tab_addr = newTemp(Ity_I64); 13198 test_byte = newTemp(Ity_I16); 13199 src_len = newTemp(Ity_I64); 13200 13201 assign(src_addr, get_gpr_dw0(r2)); 13202 assign(des_addr, get_gpr_dw0(r1)); 13203 assign(tab_addr, get_gpr_dw0(1)); 13204 assign(src_len, get_gpr_dw0(r1+1)); 13205 assign(test_byte, get_gpr_hw3(0)); 13206 13207 IRTemp op = newTemp(Ity_I8); 13208 IRTemp op1 = newTemp(Ity_I16); 13209 IRTemp result = newTemp(Ity_I64); 13210 13211 /* End of source string? We're done; proceed to next insn */ 13212 s390_cc_set(0); 13213 next_insn_if(binop(Iop_CmpEQ64, mkexpr(src_len), mkU64(0))); 13214 13215 /* Load character from source string, index translation table and 13216 store translated character in op1. */ 13217 assign(op, binop(Iop_Shl8, load(Ity_I8, mkexpr(src_addr)), mkU8(1))); 13218 13219 assign(result, binop(Iop_Add64, unop(Iop_8Uto64, mkexpr(op)), 13220 mkexpr(tab_addr))); 13221 assign(op1, load(Ity_I16, mkexpr(result))); 13222 13223 if (! s390_host_has_etf2 || (m3 & 0x1) == 0) { 13224 s390_cc_set(1); 13225 next_insn_if(binop(Iop_CmpEQ16, mkexpr(op1), mkexpr(test_byte))); 13226 } 13227 store(get_gpr_dw0(r1), mkexpr(op1)); 13228 13229 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(src_addr), mkU64(1))); 13230 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(des_addr), mkU64(2))); 13231 put_gpr_dw0(r1+1, binop(Iop_Sub64, mkexpr(src_len), mkU64(1))); 13232 13233 iterate(); 13234 13235 return "trot"; 13236 } 13237 13238 static const HChar * 13239 s390_irgen_TRTT(UChar m3, UChar r1, UChar r2) 13240 { 13241 IRTemp src_addr, des_addr, tab_addr, src_len, test_byte; 13242 src_addr = newTemp(Ity_I64); 13243 des_addr = newTemp(Ity_I64); 13244 tab_addr = newTemp(Ity_I64); 13245 test_byte = newTemp(Ity_I16); 13246 src_len = newTemp(Ity_I64); 13247 13248 assign(src_addr, get_gpr_dw0(r2)); 13249 assign(des_addr, get_gpr_dw0(r1)); 13250 assign(tab_addr, get_gpr_dw0(1)); 13251 assign(src_len, get_gpr_dw0(r1+1)); 13252 assign(test_byte, get_gpr_hw3(0)); 13253 13254 IRTemp op = newTemp(Ity_I16); 13255 IRTemp op1 = newTemp(Ity_I16); 13256 IRTemp result = newTemp(Ity_I64); 13257 13258 /* End of source string? We're done; proceed to next insn */ 13259 s390_cc_set(0); 13260 next_insn_if(binop(Iop_CmpEQ64, mkexpr(src_len), mkU64(0))); 13261 13262 /* Load character from source string, index translation table and 13263 store translated character in op1. */ 13264 assign(op, binop(Iop_Shl16, load(Ity_I16, mkexpr(src_addr)), mkU8(1))); 13265 13266 assign(result, binop(Iop_Add64, unop(Iop_16Uto64, mkexpr(op)), 13267 mkexpr(tab_addr))); 13268 assign(op1, load(Ity_I16, mkexpr(result))); 13269 13270 if (! s390_host_has_etf2 || (m3 & 0x1) == 0) { 13271 s390_cc_set(1); 13272 next_insn_if(binop(Iop_CmpEQ16, mkexpr(op1), mkexpr(test_byte))); 13273 } 13274 13275 store(get_gpr_dw0(r1), mkexpr(op1)); 13276 13277 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(src_addr), mkU64(2))); 13278 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(des_addr), mkU64(2))); 13279 put_gpr_dw0(r1+1, binop(Iop_Sub64, mkexpr(src_len), mkU64(2))); 13280 13281 iterate(); 13282 13283 return "trtt"; 13284 } 13285 13286 static const HChar * 13287 s390_irgen_TR(UChar length, IRTemp start1, IRTemp start2) 13288 { 13289 IRTemp len = newTemp(Ity_I64); 13290 13291 assign(len, mkU64(length)); 13292 s390_irgen_TR_EX(len, start1, start2); 13293 13294 return "tr"; 13295 } 13296 13297 static const HChar * 13298 s390_irgen_TRE(UChar r1,UChar r2) 13299 { 13300 IRTemp src_addr, tab_addr, src_len, test_byte; 13301 src_addr = newTemp(Ity_I64); 13302 tab_addr = newTemp(Ity_I64); 13303 src_len = newTemp(Ity_I64); 13304 test_byte = newTemp(Ity_I8); 13305 13306 assign(src_addr, get_gpr_dw0(r1)); 13307 assign(src_len, get_gpr_dw0(r1+1)); 13308 assign(tab_addr, get_gpr_dw0(r2)); 13309 assign(test_byte, get_gpr_b7(0)); 13310 13311 IRTemp op = newTemp(Ity_I8); 13312 IRTemp op1 = newTemp(Ity_I8); 13313 IRTemp result = newTemp(Ity_I64); 13314 13315 /* End of source string? We're done; proceed to next insn */ 13316 s390_cc_set(0); 13317 next_insn_if(binop(Iop_CmpEQ64, mkexpr(src_len), mkU64(0))); 13318 13319 /* Load character from source string and compare with test byte */ 13320 assign(op, load(Ity_I8, mkexpr(src_addr))); 13321 13322 s390_cc_set(1); 13323 next_insn_if(binop(Iop_CmpEQ8, mkexpr(op), mkexpr(test_byte))); 13324 13325 assign(result, binop(Iop_Add64, unop(Iop_8Uto64, mkexpr(op)), 13326 mkexpr(tab_addr))); 13327 13328 assign(op1, load(Ity_I8, mkexpr(result))); 13329 13330 store(get_gpr_dw0(r1), mkexpr(op1)); 13331 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(src_addr), mkU64(1))); 13332 put_gpr_dw0(r1+1, binop(Iop_Sub64, mkexpr(src_len), mkU64(1))); 13333 13334 iterate(); 13335 13336 return "tre"; 13337 } 13338 13339 static IRExpr * 13340 s390_call_cu21(IRExpr *srcval, IRExpr *low_surrogate) 13341 { 13342 IRExpr **args, *call; 13343 args = mkIRExprVec_2(srcval, low_surrogate); 13344 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, 13345 "s390_do_cu21", &s390_do_cu21, args); 13346 13347 /* Nothing is excluded from definedness checking. */ 13348 call->Iex.CCall.cee->mcx_mask = 0; 13349 13350 return call; 13351 } 13352 13353 static const HChar * 13354 s390_irgen_CU21(UChar m3, UChar r1, UChar r2) 13355 { 13356 IRTemp addr1 = newTemp(Ity_I64); 13357 IRTemp addr2 = newTemp(Ity_I64); 13358 IRTemp len1 = newTemp(Ity_I64); 13359 IRTemp len2 = newTemp(Ity_I64); 13360 13361 assign(addr1, get_gpr_dw0(r1)); 13362 assign(addr2, get_gpr_dw0(r2)); 13363 assign(len1, get_gpr_dw0(r1 + 1)); 13364 assign(len2, get_gpr_dw0(r2 + 1)); 13365 13366 /* We're processing the 2nd operand 2 bytes at a time. Therefore, if 13367 there are less than 2 bytes left, then the 2nd operand is exhausted 13368 and we're done here. cc = 0 */ 13369 s390_cc_set(0); 13370 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len2), mkU64(2))); 13371 13372 /* There are at least two bytes there. Read them. */ 13373 IRTemp srcval = newTemp(Ity_I32); 13374 assign(srcval, unop(Iop_16Uto32, load(Ity_I16, mkexpr(addr2)))); 13375 13376 /* Find out whether this is a high surrogate. I.e. SRCVAL lies 13377 inside the interval [0xd800 - 0xdbff] */ 13378 IRTemp is_high_surrogate = newTemp(Ity_I32); 13379 IRExpr *flag1 = mkite(binop(Iop_CmpLE32U, mkU32(0xd800), mkexpr(srcval)), 13380 mkU32(1), mkU32(0)); 13381 IRExpr *flag2 = mkite(binop(Iop_CmpLE32U, mkexpr(srcval), mkU32(0xdbff)), 13382 mkU32(1), mkU32(0)); 13383 assign(is_high_surrogate, binop(Iop_And32, flag1, flag2)); 13384 13385 /* If SRCVAL is a high surrogate and there are less than 4 bytes left, 13386 then the 2nd operand is exhausted and we're done here. cc = 0 */ 13387 IRExpr *not_enough_bytes = 13388 mkite(binop(Iop_CmpLT64U, mkexpr(len2), mkU64(4)), mkU32(1), mkU32(0)); 13389 13390 next_insn_if(binop(Iop_CmpEQ32, 13391 binop(Iop_And32, mkexpr(is_high_surrogate), 13392 not_enough_bytes), mkU32(1))); 13393 13394 /* The 2nd operand is not exhausted. If the first 2 bytes are a high 13395 surrogate, read the next two bytes (low surrogate). */ 13396 IRTemp low_surrogate = newTemp(Ity_I32); 13397 IRExpr *low_surrogate_addr = binop(Iop_Add64, mkexpr(addr2), mkU64(2)); 13398 13399 assign(low_surrogate, 13400 mkite(binop(Iop_CmpEQ32, mkexpr(is_high_surrogate), mkU32(1)), 13401 unop(Iop_16Uto32, load(Ity_I16, low_surrogate_addr)), 13402 mkU32(0))); // any value is fine; it will not be used 13403 13404 /* Call the helper */ 13405 IRTemp retval = newTemp(Ity_I64); 13406 assign(retval, s390_call_cu21(unop(Iop_32Uto64, mkexpr(srcval)), 13407 unop(Iop_32Uto64, mkexpr(low_surrogate)))); 13408 13409 /* Before we can test whether the 1st operand is exhausted we need to 13410 test for an invalid low surrogate. Because cc=2 outranks cc=1. */ 13411 if (s390_host_has_etf3 && (m3 & 0x1) == 1) { 13412 IRExpr *invalid_low_surrogate = 13413 binop(Iop_And64, mkexpr(retval), mkU64(0xff)); 13414 13415 s390_cc_set(2); 13416 next_insn_if(binop(Iop_CmpEQ64, invalid_low_surrogate, mkU64(1))); 13417 } 13418 13419 /* Now test whether the 1st operand is exhausted */ 13420 IRTemp num_bytes = newTemp(Ity_I64); 13421 assign(num_bytes, binop(Iop_And64, 13422 binop(Iop_Shr64, mkexpr(retval), mkU8(8)), 13423 mkU64(0xff))); 13424 s390_cc_set(1); 13425 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len1), mkexpr(num_bytes))); 13426 13427 /* Extract the bytes to be stored at addr1 */ 13428 IRTemp data = newTemp(Ity_I64); 13429 assign(data, binop(Iop_Shr64, mkexpr(retval), mkU8(16))); 13430 13431 /* To store the bytes construct 4 dirty helper calls. The helper calls 13432 are guarded (num_bytes == 1, num_bytes == 2, etc) such that only 13433 one of them will be called at runtime. */ 13434 UInt i; 13435 for (i = 1; i <= 4; ++i) { 13436 IRDirty *d; 13437 13438 d = unsafeIRDirty_0_N(0 /* regparms */, "s390x_dirtyhelper_CUxy", 13439 &s390x_dirtyhelper_CUxy, 13440 mkIRExprVec_3(mkexpr(addr1), mkexpr(data), 13441 mkexpr(num_bytes))); 13442 d->guard = binop(Iop_CmpEQ64, mkexpr(num_bytes), mkU64(i)); 13443 d->mFx = Ifx_Write; 13444 d->mAddr = mkexpr(addr1); 13445 d->mSize = i; 13446 stmt(IRStmt_Dirty(d)); 13447 } 13448 13449 /* Update source address and length */ 13450 IRTemp num_src_bytes = newTemp(Ity_I64); 13451 assign(num_src_bytes, 13452 mkite(binop(Iop_CmpEQ32, mkexpr(is_high_surrogate), mkU32(1)), 13453 mkU64(4), mkU64(2))); 13454 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(addr2), mkexpr(num_src_bytes))); 13455 put_gpr_dw0(r2 + 1, binop(Iop_Sub64, mkexpr(len2), mkexpr(num_src_bytes))); 13456 13457 /* Update destination address and length */ 13458 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(addr1), mkexpr(num_bytes))); 13459 put_gpr_dw0(r1 + 1, binop(Iop_Sub64, mkexpr(len1), mkexpr(num_bytes))); 13460 13461 iterate(); 13462 13463 return "cu21"; 13464 } 13465 13466 static IRExpr * 13467 s390_call_cu24(IRExpr *srcval, IRExpr *low_surrogate) 13468 { 13469 IRExpr **args, *call; 13470 args = mkIRExprVec_2(srcval, low_surrogate); 13471 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, 13472 "s390_do_cu24", &s390_do_cu24, args); 13473 13474 /* Nothing is excluded from definedness checking. */ 13475 call->Iex.CCall.cee->mcx_mask = 0; 13476 13477 return call; 13478 } 13479 13480 static const HChar * 13481 s390_irgen_CU24(UChar m3, UChar r1, UChar r2) 13482 { 13483 IRTemp addr1 = newTemp(Ity_I64); 13484 IRTemp addr2 = newTemp(Ity_I64); 13485 IRTemp len1 = newTemp(Ity_I64); 13486 IRTemp len2 = newTemp(Ity_I64); 13487 13488 assign(addr1, get_gpr_dw0(r1)); 13489 assign(addr2, get_gpr_dw0(r2)); 13490 assign(len1, get_gpr_dw0(r1 + 1)); 13491 assign(len2, get_gpr_dw0(r2 + 1)); 13492 13493 /* We're processing the 2nd operand 2 bytes at a time. Therefore, if 13494 there are less than 2 bytes left, then the 2nd operand is exhausted 13495 and we're done here. cc = 0 */ 13496 s390_cc_set(0); 13497 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len2), mkU64(2))); 13498 13499 /* There are at least two bytes there. Read them. */ 13500 IRTemp srcval = newTemp(Ity_I32); 13501 assign(srcval, unop(Iop_16Uto32, load(Ity_I16, mkexpr(addr2)))); 13502 13503 /* Find out whether this is a high surrogate. I.e. SRCVAL lies 13504 inside the interval [0xd800 - 0xdbff] */ 13505 IRTemp is_high_surrogate = newTemp(Ity_I32); 13506 IRExpr *flag1 = mkite(binop(Iop_CmpLE32U, mkU32(0xd800), mkexpr(srcval)), 13507 mkU32(1), mkU32(0)); 13508 IRExpr *flag2 = mkite(binop(Iop_CmpLE32U, mkexpr(srcval), mkU32(0xdbff)), 13509 mkU32(1), mkU32(0)); 13510 assign(is_high_surrogate, binop(Iop_And32, flag1, flag2)); 13511 13512 /* If SRCVAL is a high surrogate and there are less than 4 bytes left, 13513 then the 2nd operand is exhausted and we're done here. cc = 0 */ 13514 IRExpr *not_enough_bytes = 13515 mkite(binop(Iop_CmpLT64U, mkexpr(len2), mkU64(4)), mkU32(1), mkU32(0)); 13516 13517 next_insn_if(binop(Iop_CmpEQ32, 13518 binop(Iop_And32, mkexpr(is_high_surrogate), 13519 not_enough_bytes), 13520 mkU32(1))); 13521 13522 /* The 2nd operand is not exhausted. If the first 2 bytes are a high 13523 surrogate, read the next two bytes (low surrogate). */ 13524 IRTemp low_surrogate = newTemp(Ity_I32); 13525 IRExpr *low_surrogate_addr = binop(Iop_Add64, mkexpr(addr2), mkU64(2)); 13526 13527 assign(low_surrogate, 13528 mkite(binop(Iop_CmpEQ32, mkexpr(is_high_surrogate), mkU32(1)), 13529 unop(Iop_16Uto32, load(Ity_I16, low_surrogate_addr)), 13530 mkU32(0))); // any value is fine; it will not be used 13531 13532 /* Call the helper */ 13533 IRTemp retval = newTemp(Ity_I64); 13534 assign(retval, s390_call_cu24(unop(Iop_32Uto64, mkexpr(srcval)), 13535 unop(Iop_32Uto64, mkexpr(low_surrogate)))); 13536 13537 /* Before we can test whether the 1st operand is exhausted we need to 13538 test for an invalid low surrogate. Because cc=2 outranks cc=1. */ 13539 if (s390_host_has_etf3 && (m3 & 0x1) == 1) { 13540 IRExpr *invalid_low_surrogate = 13541 binop(Iop_And64, mkexpr(retval), mkU64(0xff)); 13542 13543 s390_cc_set(2); 13544 next_insn_if(binop(Iop_CmpEQ64, invalid_low_surrogate, mkU64(1))); 13545 } 13546 13547 /* Now test whether the 1st operand is exhausted */ 13548 s390_cc_set(1); 13549 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len1), mkU64(4))); 13550 13551 /* Extract the bytes to be stored at addr1 */ 13552 IRExpr *data = unop(Iop_64to32, binop(Iop_Shr64, mkexpr(retval), mkU8(8))); 13553 13554 store(mkexpr(addr1), data); 13555 13556 /* Update source address and length */ 13557 IRTemp num_src_bytes = newTemp(Ity_I64); 13558 assign(num_src_bytes, 13559 mkite(binop(Iop_CmpEQ32, mkexpr(is_high_surrogate), mkU32(1)), 13560 mkU64(4), mkU64(2))); 13561 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(addr2), mkexpr(num_src_bytes))); 13562 put_gpr_dw0(r2 + 1, binop(Iop_Sub64, mkexpr(len2), mkexpr(num_src_bytes))); 13563 13564 /* Update destination address and length */ 13565 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(addr1), mkU64(4))); 13566 put_gpr_dw0(r1 + 1, binop(Iop_Sub64, mkexpr(len1), mkU64(4))); 13567 13568 iterate(); 13569 13570 return "cu24"; 13571 } 13572 13573 static IRExpr * 13574 s390_call_cu42(IRExpr *srcval) 13575 { 13576 IRExpr **args, *call; 13577 args = mkIRExprVec_1(srcval); 13578 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, 13579 "s390_do_cu42", &s390_do_cu42, args); 13580 13581 /* Nothing is excluded from definedness checking. */ 13582 call->Iex.CCall.cee->mcx_mask = 0; 13583 13584 return call; 13585 } 13586 13587 static const HChar * 13588 s390_irgen_CU42(UChar r1, UChar r2) 13589 { 13590 IRTemp addr1 = newTemp(Ity_I64); 13591 IRTemp addr2 = newTemp(Ity_I64); 13592 IRTemp len1 = newTemp(Ity_I64); 13593 IRTemp len2 = newTemp(Ity_I64); 13594 13595 assign(addr1, get_gpr_dw0(r1)); 13596 assign(addr2, get_gpr_dw0(r2)); 13597 assign(len1, get_gpr_dw0(r1 + 1)); 13598 assign(len2, get_gpr_dw0(r2 + 1)); 13599 13600 /* We're processing the 2nd operand 4 bytes at a time. Therefore, if 13601 there are less than 4 bytes left, then the 2nd operand is exhausted 13602 and we're done here. cc = 0 */ 13603 s390_cc_set(0); 13604 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len2), mkU64(4))); 13605 13606 /* Read the 2nd operand. */ 13607 IRTemp srcval = newTemp(Ity_I32); 13608 assign(srcval, load(Ity_I32, mkexpr(addr2))); 13609 13610 /* Call the helper */ 13611 IRTemp retval = newTemp(Ity_I64); 13612 assign(retval, s390_call_cu42(unop(Iop_32Uto64, mkexpr(srcval)))); 13613 13614 /* If the UTF-32 character was invalid, set cc=2 and we're done. 13615 cc=2 outranks cc=1 (1st operand exhausted) */ 13616 IRExpr *invalid_character = binop(Iop_And64, mkexpr(retval), mkU64(0xff)); 13617 13618 s390_cc_set(2); 13619 next_insn_if(binop(Iop_CmpEQ64, invalid_character, mkU64(1))); 13620 13621 /* Now test whether the 1st operand is exhausted */ 13622 IRTemp num_bytes = newTemp(Ity_I64); 13623 assign(num_bytes, binop(Iop_And64, 13624 binop(Iop_Shr64, mkexpr(retval), mkU8(8)), 13625 mkU64(0xff))); 13626 s390_cc_set(1); 13627 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len1), mkexpr(num_bytes))); 13628 13629 /* Extract the bytes to be stored at addr1 */ 13630 IRTemp data = newTemp(Ity_I64); 13631 assign(data, binop(Iop_Shr64, mkexpr(retval), mkU8(16))); 13632 13633 /* To store the bytes construct 2 dirty helper calls. The helper calls 13634 are guarded (num_bytes == 2 and num_bytes == 4, respectively) such 13635 that only one of them will be called at runtime. */ 13636 13637 Int i; 13638 for (i = 2; i <= 4; ++i) { 13639 IRDirty *d; 13640 13641 if (i == 3) continue; // skip this one 13642 13643 d = unsafeIRDirty_0_N(0 /* regparms */, "s390x_dirtyhelper_CUxy", 13644 &s390x_dirtyhelper_CUxy, 13645 mkIRExprVec_3(mkexpr(addr1), mkexpr(data), 13646 mkexpr(num_bytes))); 13647 d->guard = binop(Iop_CmpEQ64, mkexpr(num_bytes), mkU64(i)); 13648 d->mFx = Ifx_Write; 13649 d->mAddr = mkexpr(addr1); 13650 d->mSize = i; 13651 stmt(IRStmt_Dirty(d)); 13652 } 13653 13654 /* Update source address and length */ 13655 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(addr2), mkU64(4))); 13656 put_gpr_dw0(r2 + 1, binop(Iop_Sub64, mkexpr(len2), mkU64(4))); 13657 13658 /* Update destination address and length */ 13659 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(addr1), mkexpr(num_bytes))); 13660 put_gpr_dw0(r1 + 1, binop(Iop_Sub64, mkexpr(len1), mkexpr(num_bytes))); 13661 13662 iterate(); 13663 13664 return "cu42"; 13665 } 13666 13667 static IRExpr * 13668 s390_call_cu41(IRExpr *srcval) 13669 { 13670 IRExpr **args, *call; 13671 args = mkIRExprVec_1(srcval); 13672 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, 13673 "s390_do_cu41", &s390_do_cu41, args); 13674 13675 /* Nothing is excluded from definedness checking. */ 13676 call->Iex.CCall.cee->mcx_mask = 0; 13677 13678 return call; 13679 } 13680 13681 static const HChar * 13682 s390_irgen_CU41(UChar r1, UChar r2) 13683 { 13684 IRTemp addr1 = newTemp(Ity_I64); 13685 IRTemp addr2 = newTemp(Ity_I64); 13686 IRTemp len1 = newTemp(Ity_I64); 13687 IRTemp len2 = newTemp(Ity_I64); 13688 13689 assign(addr1, get_gpr_dw0(r1)); 13690 assign(addr2, get_gpr_dw0(r2)); 13691 assign(len1, get_gpr_dw0(r1 + 1)); 13692 assign(len2, get_gpr_dw0(r2 + 1)); 13693 13694 /* We're processing the 2nd operand 4 bytes at a time. Therefore, if 13695 there are less than 4 bytes left, then the 2nd operand is exhausted 13696 and we're done here. cc = 0 */ 13697 s390_cc_set(0); 13698 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len2), mkU64(4))); 13699 13700 /* Read the 2nd operand. */ 13701 IRTemp srcval = newTemp(Ity_I32); 13702 assign(srcval, load(Ity_I32, mkexpr(addr2))); 13703 13704 /* Call the helper */ 13705 IRTemp retval = newTemp(Ity_I64); 13706 assign(retval, s390_call_cu41(unop(Iop_32Uto64, mkexpr(srcval)))); 13707 13708 /* If the UTF-32 character was invalid, set cc=2 and we're done. 13709 cc=2 outranks cc=1 (1st operand exhausted) */ 13710 IRExpr *invalid_character = binop(Iop_And64, mkexpr(retval), mkU64(0xff)); 13711 13712 s390_cc_set(2); 13713 next_insn_if(binop(Iop_CmpEQ64, invalid_character, mkU64(1))); 13714 13715 /* Now test whether the 1st operand is exhausted */ 13716 IRTemp num_bytes = newTemp(Ity_I64); 13717 assign(num_bytes, binop(Iop_And64, 13718 binop(Iop_Shr64, mkexpr(retval), mkU8(8)), 13719 mkU64(0xff))); 13720 s390_cc_set(1); 13721 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len1), mkexpr(num_bytes))); 13722 13723 /* Extract the bytes to be stored at addr1 */ 13724 IRTemp data = newTemp(Ity_I64); 13725 assign(data, binop(Iop_Shr64, mkexpr(retval), mkU8(16))); 13726 13727 /* To store the bytes construct 4 dirty helper calls. The helper calls 13728 are guarded (num_bytes == 1, num_bytes == 2, etc) such that only 13729 one of them will be called at runtime. */ 13730 UInt i; 13731 for (i = 1; i <= 4; ++i) { 13732 IRDirty *d; 13733 13734 d = unsafeIRDirty_0_N(0 /* regparms */, "s390x_dirtyhelper_CUxy", 13735 &s390x_dirtyhelper_CUxy, 13736 mkIRExprVec_3(mkexpr(addr1), mkexpr(data), 13737 mkexpr(num_bytes))); 13738 d->guard = binop(Iop_CmpEQ64, mkexpr(num_bytes), mkU64(i)); 13739 d->mFx = Ifx_Write; 13740 d->mAddr = mkexpr(addr1); 13741 d->mSize = i; 13742 stmt(IRStmt_Dirty(d)); 13743 } 13744 13745 /* Update source address and length */ 13746 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(addr2), mkU64(4))); 13747 put_gpr_dw0(r2 + 1, binop(Iop_Sub64, mkexpr(len2), mkU64(4))); 13748 13749 /* Update destination address and length */ 13750 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(addr1), mkexpr(num_bytes))); 13751 put_gpr_dw0(r1 + 1, binop(Iop_Sub64, mkexpr(len1), mkexpr(num_bytes))); 13752 13753 iterate(); 13754 13755 return "cu41"; 13756 } 13757 13758 static IRExpr * 13759 s390_call_cu12_cu14_helper1(IRExpr *byte1, IRExpr *etf3_and_m3_is_1) 13760 { 13761 IRExpr **args, *call; 13762 args = mkIRExprVec_2(byte1, etf3_and_m3_is_1); 13763 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, "s390_do_cu12_cu14_helper1", 13764 &s390_do_cu12_cu14_helper1, args); 13765 13766 /* Nothing is excluded from definedness checking. */ 13767 call->Iex.CCall.cee->mcx_mask = 0; 13768 13769 return call; 13770 } 13771 13772 static IRExpr * 13773 s390_call_cu12_helper2(IRExpr *byte1, IRExpr *byte2, IRExpr *byte3, 13774 IRExpr *byte4, IRExpr *stuff) 13775 { 13776 IRExpr **args, *call; 13777 args = mkIRExprVec_5(byte1, byte2, byte3, byte4, stuff); 13778 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, 13779 "s390_do_cu12_helper2", &s390_do_cu12_helper2, args); 13780 13781 /* Nothing is excluded from definedness checking. */ 13782 call->Iex.CCall.cee->mcx_mask = 0; 13783 13784 return call; 13785 } 13786 13787 static IRExpr * 13788 s390_call_cu14_helper2(IRExpr *byte1, IRExpr *byte2, IRExpr *byte3, 13789 IRExpr *byte4, IRExpr *stuff) 13790 { 13791 IRExpr **args, *call; 13792 args = mkIRExprVec_5(byte1, byte2, byte3, byte4, stuff); 13793 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, 13794 "s390_do_cu14_helper2", &s390_do_cu14_helper2, args); 13795 13796 /* Nothing is excluded from definedness checking. */ 13797 call->Iex.CCall.cee->mcx_mask = 0; 13798 13799 return call; 13800 } 13801 13802 static void 13803 s390_irgen_cu12_cu14(UChar m3, UChar r1, UChar r2, Bool is_cu12) 13804 { 13805 IRTemp addr1 = newTemp(Ity_I64); 13806 IRTemp addr2 = newTemp(Ity_I64); 13807 IRTemp len1 = newTemp(Ity_I64); 13808 IRTemp len2 = newTemp(Ity_I64); 13809 13810 assign(addr1, get_gpr_dw0(r1)); 13811 assign(addr2, get_gpr_dw0(r2)); 13812 assign(len1, get_gpr_dw0(r1 + 1)); 13813 assign(len2, get_gpr_dw0(r2 + 1)); 13814 13815 UInt extended_checking = s390_host_has_etf3 && (m3 & 0x1) == 1; 13816 13817 /* We're processing the 2nd operand 1 byte at a time. Therefore, if 13818 there is less than 1 byte left, then the 2nd operand is exhausted 13819 and we're done here. cc = 0 */ 13820 s390_cc_set(0); 13821 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len2), mkU64(1))); 13822 13823 /* There is at least one byte there. Read it. */ 13824 IRTemp byte1 = newTemp(Ity_I64); 13825 assign(byte1, unop(Iop_8Uto64, load(Ity_I8, mkexpr(addr2)))); 13826 13827 /* Call the helper to get number of bytes and invalid byte indicator */ 13828 IRTemp retval1 = newTemp(Ity_I64); 13829 assign(retval1, s390_call_cu12_cu14_helper1(mkexpr(byte1), 13830 mkU64(extended_checking))); 13831 13832 /* Check for invalid 1st byte */ 13833 IRExpr *is_invalid = unop(Iop_64to1, mkexpr(retval1)); 13834 s390_cc_set(2); 13835 next_insn_if(is_invalid); 13836 13837 /* How many bytes do we have to read? */ 13838 IRTemp num_src_bytes = newTemp(Ity_I64); 13839 assign(num_src_bytes, binop(Iop_Shr64, mkexpr(retval1), mkU8(8))); 13840 13841 /* Now test whether the 2nd operand is exhausted */ 13842 s390_cc_set(0); 13843 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len2), mkexpr(num_src_bytes))); 13844 13845 /* Read the remaining bytes */ 13846 IRExpr *cond, *addr, *byte2, *byte3, *byte4; 13847 13848 cond = binop(Iop_CmpLE64U, mkU64(2), mkexpr(num_src_bytes)); 13849 addr = binop(Iop_Add64, mkexpr(addr2), mkU64(1)); 13850 byte2 = mkite(cond, unop(Iop_8Uto64, load(Ity_I8, addr)), mkU64(0)); 13851 cond = binop(Iop_CmpLE64U, mkU64(3), mkexpr(num_src_bytes)); 13852 addr = binop(Iop_Add64, mkexpr(addr2), mkU64(2)); 13853 byte3 = mkite(cond, unop(Iop_8Uto64, load(Ity_I8, addr)), mkU64(0)); 13854 cond = binop(Iop_CmpLE64U, mkU64(4), mkexpr(num_src_bytes)); 13855 addr = binop(Iop_Add64, mkexpr(addr2), mkU64(3)); 13856 byte4 = mkite(cond, unop(Iop_8Uto64, load(Ity_I8, addr)), mkU64(0)); 13857 13858 /* Call the helper to get the converted value and invalid byte indicator. 13859 We can pass at most 5 arguments; therefore some encoding is needed 13860 here */ 13861 IRExpr *stuff = binop(Iop_Or64, 13862 binop(Iop_Shl64, mkexpr(num_src_bytes), mkU8(1)), 13863 mkU64(extended_checking)); 13864 IRTemp retval2 = newTemp(Ity_I64); 13865 13866 if (is_cu12) { 13867 assign(retval2, s390_call_cu12_helper2(mkexpr(byte1), byte2, byte3, 13868 byte4, stuff)); 13869 } else { 13870 assign(retval2, s390_call_cu14_helper2(mkexpr(byte1), byte2, byte3, 13871 byte4, stuff)); 13872 } 13873 13874 /* Check for invalid character */ 13875 s390_cc_set(2); 13876 is_invalid = unop(Iop_64to1, mkexpr(retval2)); 13877 next_insn_if(is_invalid); 13878 13879 /* Now test whether the 1st operand is exhausted */ 13880 IRTemp num_bytes = newTemp(Ity_I64); 13881 assign(num_bytes, binop(Iop_And64, 13882 binop(Iop_Shr64, mkexpr(retval2), mkU8(8)), 13883 mkU64(0xff))); 13884 s390_cc_set(1); 13885 next_insn_if(binop(Iop_CmpLT64U, mkexpr(len1), mkexpr(num_bytes))); 13886 13887 /* Extract the bytes to be stored at addr1 */ 13888 IRTemp data = newTemp(Ity_I64); 13889 assign(data, binop(Iop_Shr64, mkexpr(retval2), mkU8(16))); 13890 13891 if (is_cu12) { 13892 /* To store the bytes construct 2 dirty helper calls. The helper calls 13893 are guarded (num_bytes == 2 and num_bytes == 4, respectively) such 13894 that only one of them will be called at runtime. */ 13895 13896 Int i; 13897 for (i = 2; i <= 4; ++i) { 13898 IRDirty *d; 13899 13900 if (i == 3) continue; // skip this one 13901 13902 d = unsafeIRDirty_0_N(0 /* regparms */, "s390x_dirtyhelper_CUxy", 13903 &s390x_dirtyhelper_CUxy, 13904 mkIRExprVec_3(mkexpr(addr1), mkexpr(data), 13905 mkexpr(num_bytes))); 13906 d->guard = binop(Iop_CmpEQ64, mkexpr(num_bytes), mkU64(i)); 13907 d->mFx = Ifx_Write; 13908 d->mAddr = mkexpr(addr1); 13909 d->mSize = i; 13910 stmt(IRStmt_Dirty(d)); 13911 } 13912 } else { 13913 // cu14 13914 store(mkexpr(addr1), unop(Iop_64to32, mkexpr(data))); 13915 } 13916 13917 /* Update source address and length */ 13918 put_gpr_dw0(r2, binop(Iop_Add64, mkexpr(addr2), mkexpr(num_src_bytes))); 13919 put_gpr_dw0(r2 + 1, binop(Iop_Sub64, mkexpr(len2), mkexpr(num_src_bytes))); 13920 13921 /* Update destination address and length */ 13922 put_gpr_dw0(r1, binop(Iop_Add64, mkexpr(addr1), mkexpr(num_bytes))); 13923 put_gpr_dw0(r1 + 1, binop(Iop_Sub64, mkexpr(len1), mkexpr(num_bytes))); 13924 13925 iterate(); 13926 } 13927 13928 static const HChar * 13929 s390_irgen_CU12(UChar m3, UChar r1, UChar r2) 13930 { 13931 s390_irgen_cu12_cu14(m3, r1, r2, /* is_cu12 = */ 1); 13932 13933 return "cu12"; 13934 } 13935 13936 static const HChar * 13937 s390_irgen_CU14(UChar m3, UChar r1, UChar r2) 13938 { 13939 s390_irgen_cu12_cu14(m3, r1, r2, /* is_cu12 = */ 0); 13940 13941 return "cu14"; 13942 } 13943 13944 static IRExpr * 13945 s390_call_ecag(IRExpr *op2addr) 13946 { 13947 IRExpr **args, *call; 13948 13949 args = mkIRExprVec_1(op2addr); 13950 call = mkIRExprCCall(Ity_I64, 0 /*regparm*/, 13951 "s390_do_ecag", &s390_do_ecag, args); 13952 13953 /* Nothing is excluded from definedness checking. */ 13954 call->Iex.CCall.cee->mcx_mask = 0; 13955 13956 return call; 13957 } 13958 13959 static const HChar * 13960 s390_irgen_ECAG(UChar r1, UChar r3 __attribute__((unused)), IRTemp op2addr) 13961 { 13962 if (! s390_host_has_gie) { 13963 emulation_failure(EmFail_S390X_ecag); 13964 } else { 13965 put_gpr_dw0(r1, s390_call_ecag(mkexpr(op2addr))); 13966 } 13967 13968 return "ecag"; 13969 } 13970 13971 13972 /* New insns are added here. 13973 If an insn is contingent on a facility being installed also 13974 check whether the list of supported facilities in function 13975 s390x_dirtyhelper_STFLE needs updating */ 13976 13977 /*------------------------------------------------------------*/ 13978 /*--- Build IR for special instructions ---*/ 13979 /*------------------------------------------------------------*/ 13980 13981 static void 13982 s390_irgen_client_request(void) 13983 { 13984 if (0) 13985 vex_printf("%%R3 = client_request ( %%R2 )\n"); 13986 13987 Addr64 next = guest_IA_curr_instr + S390_SPECIAL_OP_PREAMBLE_SIZE 13988 + S390_SPECIAL_OP_SIZE; 13989 13990 dis_res->jk_StopHere = Ijk_ClientReq; 13991 dis_res->whatNext = Dis_StopHere; 13992 13993 put_IA(mkaddr_expr(next)); 13994 } 13995 13996 static void 13997 s390_irgen_guest_NRADDR(void) 13998 { 13999 if (0) 14000 vex_printf("%%R3 = guest_NRADDR\n"); 14001 14002 put_gpr_dw0(3, IRExpr_Get(S390X_GUEST_OFFSET(guest_NRADDR), Ity_I64)); 14003 } 14004 14005 static void 14006 s390_irgen_call_noredir(void) 14007 { 14008 Addr64 next = guest_IA_curr_instr + S390_SPECIAL_OP_PREAMBLE_SIZE 14009 + S390_SPECIAL_OP_SIZE; 14010 14011 /* Continue after special op */ 14012 put_gpr_dw0(14, mkaddr_expr(next)); 14013 14014 /* The address is in REG1, all parameters are in the right (guest) places */ 14015 put_IA(get_gpr_dw0(1)); 14016 14017 dis_res->whatNext = Dis_StopHere; 14018 dis_res->jk_StopHere = Ijk_NoRedir; 14019 } 14020 14021 /* Force proper alignment for the structures below. */ 14022 #pragma pack(1) 14023 14024 14025 static s390_decode_t 14026 s390_decode_2byte_and_irgen(const UChar *bytes) 14027 { 14028 typedef union { 14029 struct { 14030 unsigned int op : 16; 14031 } E; 14032 struct { 14033 unsigned int op : 8; 14034 unsigned int i : 8; 14035 } I; 14036 struct { 14037 unsigned int op : 8; 14038 unsigned int r1 : 4; 14039 unsigned int r2 : 4; 14040 } RR; 14041 } formats; 14042 union { 14043 formats fmt; 14044 UShort value; 14045 } ovl; 14046 14047 vassert(sizeof(formats) == 2); 14048 14049 ((UChar *)(&ovl.value))[0] = bytes[0]; 14050 ((UChar *)(&ovl.value))[1] = bytes[1]; 14051 14052 switch (ovl.value & 0xffff) { 14053 case 0x0101: /* PR */ goto unimplemented; 14054 case 0x0102: /* UPT */ goto unimplemented; 14055 case 0x0104: /* PTFF */ goto unimplemented; 14056 case 0x0107: /* SCKPF */ goto unimplemented; 14057 case 0x010a: s390_format_E(s390_irgen_PFPO); goto ok; 14058 case 0x010b: /* TAM */ goto unimplemented; 14059 case 0x010c: /* SAM24 */ goto unimplemented; 14060 case 0x010d: /* SAM31 */ goto unimplemented; 14061 case 0x010e: /* SAM64 */ goto unimplemented; 14062 case 0x01ff: /* TRAP2 */ goto unimplemented; 14063 } 14064 14065 switch ((ovl.value & 0xff00) >> 8) { 14066 case 0x04: /* SPM */ goto unimplemented; 14067 case 0x05: /* BALR */ goto unimplemented; 14068 case 0x06: s390_format_RR_RR(s390_irgen_BCTR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14069 goto ok; 14070 case 0x07: s390_format_RR(s390_irgen_BCR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14071 goto ok; 14072 case 0x0a: s390_format_I(s390_irgen_SVC, ovl.fmt.I.i); goto ok; 14073 case 0x0b: /* BSM */ goto unimplemented; 14074 case 0x0c: /* BASSM */ goto unimplemented; 14075 case 0x0d: s390_format_RR_RR(s390_irgen_BASR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14076 goto ok; 14077 case 0x0e: s390_format_RR(s390_irgen_MVCL, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14078 goto ok; 14079 case 0x0f: s390_format_RR(s390_irgen_CLCL, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14080 goto ok; 14081 case 0x10: s390_format_RR_RR(s390_irgen_LPR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14082 goto ok; 14083 case 0x11: s390_format_RR_RR(s390_irgen_LNR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14084 goto ok; 14085 case 0x12: s390_format_RR_RR(s390_irgen_LTR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14086 goto ok; 14087 case 0x13: s390_format_RR_RR(s390_irgen_LCR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14088 goto ok; 14089 case 0x14: s390_format_RR_RR(s390_irgen_NR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14090 goto ok; 14091 case 0x15: s390_format_RR_RR(s390_irgen_CLR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14092 goto ok; 14093 case 0x16: s390_format_RR_RR(s390_irgen_OR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14094 goto ok; 14095 case 0x17: s390_format_RR_RR(s390_irgen_XR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14096 goto ok; 14097 case 0x18: s390_format_RR_RR(s390_irgen_LR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14098 goto ok; 14099 case 0x19: s390_format_RR_RR(s390_irgen_CR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14100 goto ok; 14101 case 0x1a: s390_format_RR_RR(s390_irgen_AR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14102 goto ok; 14103 case 0x1b: s390_format_RR_RR(s390_irgen_SR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14104 goto ok; 14105 case 0x1c: s390_format_RR_RR(s390_irgen_MR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14106 goto ok; 14107 case 0x1d: s390_format_RR_RR(s390_irgen_DR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14108 goto ok; 14109 case 0x1e: s390_format_RR_RR(s390_irgen_ALR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14110 goto ok; 14111 case 0x1f: s390_format_RR_RR(s390_irgen_SLR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14112 goto ok; 14113 case 0x20: /* LPDR */ goto unimplemented; 14114 case 0x21: /* LNDR */ goto unimplemented; 14115 case 0x22: /* LTDR */ goto unimplemented; 14116 case 0x23: /* LCDR */ goto unimplemented; 14117 case 0x24: /* HDR */ goto unimplemented; 14118 case 0x25: /* LDXR */ goto unimplemented; 14119 case 0x26: /* MXR */ goto unimplemented; 14120 case 0x27: /* MXDR */ goto unimplemented; 14121 case 0x28: s390_format_RR_FF(s390_irgen_LDR, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14122 goto ok; 14123 case 0x29: /* CDR */ goto unimplemented; 14124 case 0x2a: /* ADR */ goto unimplemented; 14125 case 0x2b: /* SDR */ goto unimplemented; 14126 case 0x2c: /* MDR */ goto unimplemented; 14127 case 0x2d: /* DDR */ goto unimplemented; 14128 case 0x2e: /* AWR */ goto unimplemented; 14129 case 0x2f: /* SWR */ goto unimplemented; 14130 case 0x30: /* LPER */ goto unimplemented; 14131 case 0x31: /* LNER */ goto unimplemented; 14132 case 0x32: /* LTER */ goto unimplemented; 14133 case 0x33: /* LCER */ goto unimplemented; 14134 case 0x34: /* HER */ goto unimplemented; 14135 case 0x35: /* LEDR */ goto unimplemented; 14136 case 0x36: /* AXR */ goto unimplemented; 14137 case 0x37: /* SXR */ goto unimplemented; 14138 case 0x38: s390_format_RR_FF(s390_irgen_LER, ovl.fmt.RR.r1, ovl.fmt.RR.r2); 14139 goto ok; 14140 case 0x39: /* CER */ goto unimplemented; 14141 case 0x3a: /* AER */ goto unimplemented; 14142 case 0x3b: /* SER */ goto unimplemented; 14143 case 0x3c: /* MDER */ goto unimplemented; 14144 case 0x3d: /* DER */ goto unimplemented; 14145 case 0x3e: /* AUR */ goto unimplemented; 14146 case 0x3f: /* SUR */ goto unimplemented; 14147 } 14148 14149 return S390_DECODE_UNKNOWN_INSN; 14150 14151 ok: 14152 return S390_DECODE_OK; 14153 14154 unimplemented: 14155 return S390_DECODE_UNIMPLEMENTED_INSN; 14156 } 14157 14158 static s390_decode_t 14159 s390_decode_4byte_and_irgen(const UChar *bytes) 14160 { 14161 typedef union { 14162 struct { 14163 unsigned int op1 : 8; 14164 unsigned int r1 : 4; 14165 unsigned int op2 : 4; 14166 unsigned int i2 : 16; 14167 } RI; 14168 struct { 14169 unsigned int op : 16; 14170 unsigned int : 8; 14171 unsigned int r1 : 4; 14172 unsigned int r2 : 4; 14173 } RRE; 14174 struct { 14175 unsigned int op : 16; 14176 unsigned int r1 : 4; 14177 unsigned int : 4; 14178 unsigned int r3 : 4; 14179 unsigned int r2 : 4; 14180 } RRF; 14181 struct { 14182 unsigned int op : 16; 14183 unsigned int m3 : 4; 14184 unsigned int m4 : 4; 14185 unsigned int r1 : 4; 14186 unsigned int r2 : 4; 14187 } RRF2; 14188 struct { 14189 unsigned int op : 16; 14190 unsigned int r3 : 4; 14191 unsigned int : 4; 14192 unsigned int r1 : 4; 14193 unsigned int r2 : 4; 14194 } RRF3; 14195 struct { 14196 unsigned int op : 16; 14197 unsigned int r3 : 4; 14198 unsigned int : 4; 14199 unsigned int r1 : 4; 14200 unsigned int r2 : 4; 14201 } RRR; 14202 struct { 14203 unsigned int op : 16; 14204 unsigned int r3 : 4; 14205 unsigned int m4 : 4; 14206 unsigned int r1 : 4; 14207 unsigned int r2 : 4; 14208 } RRF4; 14209 struct { 14210 unsigned int op : 16; 14211 unsigned int : 4; 14212 unsigned int m4 : 4; 14213 unsigned int r1 : 4; 14214 unsigned int r2 : 4; 14215 } RRF5; 14216 struct { 14217 unsigned int op : 8; 14218 unsigned int r1 : 4; 14219 unsigned int r3 : 4; 14220 unsigned int b2 : 4; 14221 unsigned int d2 : 12; 14222 } RS; 14223 struct { 14224 unsigned int op : 8; 14225 unsigned int r1 : 4; 14226 unsigned int r3 : 4; 14227 unsigned int i2 : 16; 14228 } RSI; 14229 struct { 14230 unsigned int op : 8; 14231 unsigned int r1 : 4; 14232 unsigned int x2 : 4; 14233 unsigned int b2 : 4; 14234 unsigned int d2 : 12; 14235 } RX; 14236 struct { 14237 unsigned int op : 16; 14238 unsigned int b2 : 4; 14239 unsigned int d2 : 12; 14240 } S; 14241 struct { 14242 unsigned int op : 8; 14243 unsigned int i2 : 8; 14244 unsigned int b1 : 4; 14245 unsigned int d1 : 12; 14246 } SI; 14247 } formats; 14248 union { 14249 formats fmt; 14250 UInt value; 14251 } ovl; 14252 14253 vassert(sizeof(formats) == 4); 14254 14255 ((UChar *)(&ovl.value))[0] = bytes[0]; 14256 ((UChar *)(&ovl.value))[1] = bytes[1]; 14257 ((UChar *)(&ovl.value))[2] = bytes[2]; 14258 ((UChar *)(&ovl.value))[3] = bytes[3]; 14259 14260 switch ((ovl.value & 0xff0f0000) >> 16) { 14261 case 0xa500: s390_format_RI_RU(s390_irgen_IIHH, ovl.fmt.RI.r1, 14262 ovl.fmt.RI.i2); goto ok; 14263 case 0xa501: s390_format_RI_RU(s390_irgen_IIHL, ovl.fmt.RI.r1, 14264 ovl.fmt.RI.i2); goto ok; 14265 case 0xa502: s390_format_RI_RU(s390_irgen_IILH, ovl.fmt.RI.r1, 14266 ovl.fmt.RI.i2); goto ok; 14267 case 0xa503: s390_format_RI_RU(s390_irgen_IILL, ovl.fmt.RI.r1, 14268 ovl.fmt.RI.i2); goto ok; 14269 case 0xa504: s390_format_RI_RU(s390_irgen_NIHH, ovl.fmt.RI.r1, 14270 ovl.fmt.RI.i2); goto ok; 14271 case 0xa505: s390_format_RI_RU(s390_irgen_NIHL, ovl.fmt.RI.r1, 14272 ovl.fmt.RI.i2); goto ok; 14273 case 0xa506: s390_format_RI_RU(s390_irgen_NILH, ovl.fmt.RI.r1, 14274 ovl.fmt.RI.i2); goto ok; 14275 case 0xa507: s390_format_RI_RU(s390_irgen_NILL, ovl.fmt.RI.r1, 14276 ovl.fmt.RI.i2); goto ok; 14277 case 0xa508: s390_format_RI_RU(s390_irgen_OIHH, ovl.fmt.RI.r1, 14278 ovl.fmt.RI.i2); goto ok; 14279 case 0xa509: s390_format_RI_RU(s390_irgen_OIHL, ovl.fmt.RI.r1, 14280 ovl.fmt.RI.i2); goto ok; 14281 case 0xa50a: s390_format_RI_RU(s390_irgen_OILH, ovl.fmt.RI.r1, 14282 ovl.fmt.RI.i2); goto ok; 14283 case 0xa50b: s390_format_RI_RU(s390_irgen_OILL, ovl.fmt.RI.r1, 14284 ovl.fmt.RI.i2); goto ok; 14285 case 0xa50c: s390_format_RI_RU(s390_irgen_LLIHH, ovl.fmt.RI.r1, 14286 ovl.fmt.RI.i2); goto ok; 14287 case 0xa50d: s390_format_RI_RU(s390_irgen_LLIHL, ovl.fmt.RI.r1, 14288 ovl.fmt.RI.i2); goto ok; 14289 case 0xa50e: s390_format_RI_RU(s390_irgen_LLILH, ovl.fmt.RI.r1, 14290 ovl.fmt.RI.i2); goto ok; 14291 case 0xa50f: s390_format_RI_RU(s390_irgen_LLILL, ovl.fmt.RI.r1, 14292 ovl.fmt.RI.i2); goto ok; 14293 case 0xa700: s390_format_RI_RU(s390_irgen_TMLH, ovl.fmt.RI.r1, 14294 ovl.fmt.RI.i2); goto ok; 14295 case 0xa701: s390_format_RI_RU(s390_irgen_TMLL, ovl.fmt.RI.r1, 14296 ovl.fmt.RI.i2); goto ok; 14297 case 0xa702: s390_format_RI_RU(s390_irgen_TMHH, ovl.fmt.RI.r1, 14298 ovl.fmt.RI.i2); goto ok; 14299 case 0xa703: s390_format_RI_RU(s390_irgen_TMHL, ovl.fmt.RI.r1, 14300 ovl.fmt.RI.i2); goto ok; 14301 case 0xa704: s390_format_RI(s390_irgen_BRC, ovl.fmt.RI.r1, ovl.fmt.RI.i2); 14302 goto ok; 14303 case 0xa705: s390_format_RI_RP(s390_irgen_BRAS, ovl.fmt.RI.r1, 14304 ovl.fmt.RI.i2); goto ok; 14305 case 0xa706: s390_format_RI_RP(s390_irgen_BRCT, ovl.fmt.RI.r1, 14306 ovl.fmt.RI.i2); goto ok; 14307 case 0xa707: s390_format_RI_RP(s390_irgen_BRCTG, ovl.fmt.RI.r1, 14308 ovl.fmt.RI.i2); goto ok; 14309 case 0xa708: s390_format_RI_RI(s390_irgen_LHI, ovl.fmt.RI.r1, ovl.fmt.RI.i2); 14310 goto ok; 14311 case 0xa709: s390_format_RI_RI(s390_irgen_LGHI, ovl.fmt.RI.r1, 14312 ovl.fmt.RI.i2); goto ok; 14313 case 0xa70a: s390_format_RI_RI(s390_irgen_AHI, ovl.fmt.RI.r1, ovl.fmt.RI.i2); 14314 goto ok; 14315 case 0xa70b: s390_format_RI_RI(s390_irgen_AGHI, ovl.fmt.RI.r1, 14316 ovl.fmt.RI.i2); goto ok; 14317 case 0xa70c: s390_format_RI_RI(s390_irgen_MHI, ovl.fmt.RI.r1, ovl.fmt.RI.i2); 14318 goto ok; 14319 case 0xa70d: s390_format_RI_RI(s390_irgen_MGHI, ovl.fmt.RI.r1, 14320 ovl.fmt.RI.i2); goto ok; 14321 case 0xa70e: s390_format_RI_RI(s390_irgen_CHI, ovl.fmt.RI.r1, ovl.fmt.RI.i2); 14322 goto ok; 14323 case 0xa70f: s390_format_RI_RI(s390_irgen_CGHI, ovl.fmt.RI.r1, 14324 ovl.fmt.RI.i2); goto ok; 14325 } 14326 14327 switch ((ovl.value & 0xffff0000) >> 16) { 14328 case 0x8000: /* SSM */ goto unimplemented; 14329 case 0x8200: /* LPSW */ goto unimplemented; 14330 case 0x9300: /* TS */ goto unimplemented; 14331 case 0xb202: /* STIDP */ goto unimplemented; 14332 case 0xb204: /* SCK */ goto unimplemented; 14333 case 0xb205: s390_format_S_RD(s390_irgen_STCK, ovl.fmt.S.b2, ovl.fmt.S.d2); 14334 goto ok; 14335 case 0xb206: /* SCKC */ goto unimplemented; 14336 case 0xb207: /* STCKC */ goto unimplemented; 14337 case 0xb208: /* SPT */ goto unimplemented; 14338 case 0xb209: /* STPT */ goto unimplemented; 14339 case 0xb20a: /* SPKA */ goto unimplemented; 14340 case 0xb20b: /* IPK */ goto unimplemented; 14341 case 0xb20d: /* PTLB */ goto unimplemented; 14342 case 0xb210: /* SPX */ goto unimplemented; 14343 case 0xb211: /* STPX */ goto unimplemented; 14344 case 0xb212: /* STAP */ goto unimplemented; 14345 case 0xb214: /* SIE */ goto unimplemented; 14346 case 0xb218: /* PC */ goto unimplemented; 14347 case 0xb219: /* SAC */ goto unimplemented; 14348 case 0xb21a: /* CFC */ goto unimplemented; 14349 case 0xb221: /* IPTE */ goto unimplemented; 14350 case 0xb222: s390_format_RRE_R0(s390_irgen_IPM, ovl.fmt.RRE.r1); goto ok; 14351 case 0xb223: /* IVSK */ goto unimplemented; 14352 case 0xb224: /* IAC */ goto unimplemented; 14353 case 0xb225: /* SSAR */ goto unimplemented; 14354 case 0xb226: /* EPAR */ goto unimplemented; 14355 case 0xb227: /* ESAR */ goto unimplemented; 14356 case 0xb228: /* PT */ goto unimplemented; 14357 case 0xb229: /* ISKE */ goto unimplemented; 14358 case 0xb22a: /* RRBE */ goto unimplemented; 14359 case 0xb22b: /* SSKE */ goto unimplemented; 14360 case 0xb22c: /* TB */ goto unimplemented; 14361 case 0xb22d: /* DXR */ goto unimplemented; 14362 case 0xb22e: /* PGIN */ goto unimplemented; 14363 case 0xb22f: /* PGOUT */ goto unimplemented; 14364 case 0xb230: /* CSCH */ goto unimplemented; 14365 case 0xb231: /* HSCH */ goto unimplemented; 14366 case 0xb232: /* MSCH */ goto unimplemented; 14367 case 0xb233: /* SSCH */ goto unimplemented; 14368 case 0xb234: /* STSCH */ goto unimplemented; 14369 case 0xb235: /* TSCH */ goto unimplemented; 14370 case 0xb236: /* TPI */ goto unimplemented; 14371 case 0xb237: /* SAL */ goto unimplemented; 14372 case 0xb238: /* RSCH */ goto unimplemented; 14373 case 0xb239: /* STCRW */ goto unimplemented; 14374 case 0xb23a: /* STCPS */ goto unimplemented; 14375 case 0xb23b: /* RCHP */ goto unimplemented; 14376 case 0xb23c: /* SCHM */ goto unimplemented; 14377 case 0xb240: /* BAKR */ goto unimplemented; 14378 case 0xb241: s390_format_RRE(s390_irgen_CKSM, ovl.fmt.RRE.r1, 14379 ovl.fmt.RRE.r2); goto ok; 14380 case 0xb244: /* SQDR */ goto unimplemented; 14381 case 0xb245: /* SQER */ goto unimplemented; 14382 case 0xb246: /* STURA */ goto unimplemented; 14383 case 0xb247: /* MSTA */ goto unimplemented; 14384 case 0xb248: /* PALB */ goto unimplemented; 14385 case 0xb249: /* EREG */ goto unimplemented; 14386 case 0xb24a: /* ESTA */ goto unimplemented; 14387 case 0xb24b: /* LURA */ goto unimplemented; 14388 case 0xb24c: /* TAR */ goto unimplemented; 14389 case 0xb24d: s390_format_RRE(s390_irgen_CPYA, ovl.fmt.RRE.r1, 14390 ovl.fmt.RRE.r2); goto ok; 14391 case 0xb24e: s390_format_RRE(s390_irgen_SAR, ovl.fmt.RRE.r1, ovl.fmt.RRE.r2); 14392 goto ok; 14393 case 0xb24f: s390_format_RRE(s390_irgen_EAR, ovl.fmt.RRE.r1, ovl.fmt.RRE.r2); 14394 goto ok; 14395 case 0xb250: /* CSP */ goto unimplemented; 14396 case 0xb252: s390_format_RRE_RR(s390_irgen_MSR, ovl.fmt.RRE.r1, 14397 ovl.fmt.RRE.r2); goto ok; 14398 case 0xb254: /* MVPG */ goto unimplemented; 14399 case 0xb255: s390_format_RRE_RR(s390_irgen_MVST, ovl.fmt.RRE.r1, 14400 ovl.fmt.RRE.r2); goto ok; 14401 case 0xb257: /* CUSE */ goto unimplemented; 14402 case 0xb258: /* BSG */ goto unimplemented; 14403 case 0xb25a: /* BSA */ goto unimplemented; 14404 case 0xb25d: s390_format_RRE_RR(s390_irgen_CLST, ovl.fmt.RRE.r1, 14405 ovl.fmt.RRE.r2); goto ok; 14406 case 0xb25e: s390_format_RRE_RR(s390_irgen_SRST, ovl.fmt.RRE.r1, 14407 ovl.fmt.RRE.r2); goto ok; 14408 case 0xb263: /* CMPSC */ goto unimplemented; 14409 case 0xb274: /* SIGA */ goto unimplemented; 14410 case 0xb276: /* XSCH */ goto unimplemented; 14411 case 0xb277: /* RP */ goto unimplemented; 14412 case 0xb278: s390_format_S_RD(s390_irgen_STCKE, ovl.fmt.S.b2, ovl.fmt.S.d2);goto ok; 14413 case 0xb279: /* SACF */ goto unimplemented; 14414 case 0xb27c: s390_format_S_RD(s390_irgen_STCKF, ovl.fmt.S.b2, ovl.fmt.S.d2);goto ok; 14415 case 0xb27d: /* STSI */ goto unimplemented; 14416 case 0xb280: /* LPP */ goto unimplemented; 14417 case 0xb284: /* LCCTL */ goto unimplemented; 14418 case 0xb285: /* LPCTL */ goto unimplemented; 14419 case 0xb286: /* QSI */ goto unimplemented; 14420 case 0xb287: /* LSCTL */ goto unimplemented; 14421 case 0xb28e: /* QCTRI */ goto unimplemented; 14422 case 0xb299: s390_format_S_RD(s390_irgen_SRNM, ovl.fmt.S.b2, ovl.fmt.S.d2); 14423 goto ok; 14424 case 0xb29c: s390_format_S_RD(s390_irgen_STFPC, ovl.fmt.S.b2, ovl.fmt.S.d2); 14425 goto ok; 14426 case 0xb29d: s390_format_S_RD(s390_irgen_LFPC, ovl.fmt.S.b2, ovl.fmt.S.d2); 14427 goto ok; 14428 case 0xb2a5: s390_format_RRE_FF(s390_irgen_TRE, ovl.fmt.RRE.r1, ovl.fmt.RRE.r2); goto ok; 14429 case 0xb2a6: s390_format_RRF_M0RERE(s390_irgen_CU21, ovl.fmt.RRF3.r3, 14430 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); 14431 goto ok; 14432 case 0xb2a7: s390_format_RRF_M0RERE(s390_irgen_CU12, ovl.fmt.RRF3.r3, 14433 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); 14434 goto ok; 14435 case 0xb2b0: s390_format_S_RD(s390_irgen_STFLE, ovl.fmt.S.b2, ovl.fmt.S.d2); 14436 goto ok; 14437 case 0xb2b1: /* STFL */ goto unimplemented; 14438 case 0xb2b2: /* LPSWE */ goto unimplemented; 14439 case 0xb2b8: s390_irgen_srnmb_wrapper(ovl.fmt.S.b2, ovl.fmt.S.d2); 14440 goto ok; 14441 case 0xb2b9: s390_format_S_RD(s390_irgen_SRNMT, ovl.fmt.S.b2, ovl.fmt.S.d2); 14442 goto ok; 14443 case 0xb2bd: /* LFAS */ goto unimplemented; 14444 case 0xb2e0: /* SCCTR */ goto unimplemented; 14445 case 0xb2e1: /* SPCTR */ goto unimplemented; 14446 case 0xb2e4: /* ECCTR */ goto unimplemented; 14447 case 0xb2e5: /* EPCTR */ goto unimplemented; 14448 case 0xb2e8: /* PPA */ goto unimplemented; 14449 case 0xb2ec: /* ETND */ goto unimplemented; 14450 case 0xb2ed: /* ECPGA */ goto unimplemented; 14451 case 0xb2f8: /* TEND */ goto unimplemented; 14452 case 0xb2fa: /* NIAI */ goto unimplemented; 14453 case 0xb2fc: /* TABORT */ goto unimplemented; 14454 case 0xb2ff: /* TRAP4 */ goto unimplemented; 14455 case 0xb300: s390_format_RRE_FF(s390_irgen_LPEBR, ovl.fmt.RRE.r1, 14456 ovl.fmt.RRE.r2); goto ok; 14457 case 0xb301: s390_format_RRE_FF(s390_irgen_LNEBR, ovl.fmt.RRE.r1, 14458 ovl.fmt.RRE.r2); goto ok; 14459 case 0xb302: s390_format_RRE_FF(s390_irgen_LTEBR, ovl.fmt.RRE.r1, 14460 ovl.fmt.RRE.r2); goto ok; 14461 case 0xb303: s390_format_RRE_FF(s390_irgen_LCEBR, ovl.fmt.RRE.r1, 14462 ovl.fmt.RRE.r2); goto ok; 14463 case 0xb304: s390_format_RRE_FF(s390_irgen_LDEBR, ovl.fmt.RRE.r1, 14464 ovl.fmt.RRE.r2); goto ok; 14465 case 0xb305: s390_format_RRE_FF(s390_irgen_LXDBR, ovl.fmt.RRE.r1, 14466 ovl.fmt.RRE.r2); goto ok; 14467 case 0xb306: s390_format_RRE_FF(s390_irgen_LXEBR, ovl.fmt.RRE.r1, 14468 ovl.fmt.RRE.r2); goto ok; 14469 case 0xb307: /* MXDBR */ goto unimplemented; 14470 case 0xb308: /* KEBR */ goto unimplemented; 14471 case 0xb309: s390_format_RRE_FF(s390_irgen_CEBR, ovl.fmt.RRE.r1, 14472 ovl.fmt.RRE.r2); goto ok; 14473 case 0xb30a: s390_format_RRE_FF(s390_irgen_AEBR, ovl.fmt.RRE.r1, 14474 ovl.fmt.RRE.r2); goto ok; 14475 case 0xb30b: s390_format_RRE_FF(s390_irgen_SEBR, ovl.fmt.RRE.r1, 14476 ovl.fmt.RRE.r2); goto ok; 14477 case 0xb30c: /* MDEBR */ goto unimplemented; 14478 case 0xb30d: s390_format_RRE_FF(s390_irgen_DEBR, ovl.fmt.RRE.r1, 14479 ovl.fmt.RRE.r2); goto ok; 14480 case 0xb30e: s390_format_RRF_F0FF(s390_irgen_MAEBR, ovl.fmt.RRF.r1, 14481 ovl.fmt.RRF.r3, ovl.fmt.RRF.r2); goto ok; 14482 case 0xb30f: s390_format_RRF_F0FF(s390_irgen_MSEBR, ovl.fmt.RRF.r1, 14483 ovl.fmt.RRF.r3, ovl.fmt.RRF.r2); goto ok; 14484 case 0xb310: s390_format_RRE_FF(s390_irgen_LPDBR, ovl.fmt.RRE.r1, 14485 ovl.fmt.RRE.r2); goto ok; 14486 case 0xb311: s390_format_RRE_FF(s390_irgen_LNDBR, ovl.fmt.RRE.r1, 14487 ovl.fmt.RRE.r2); goto ok; 14488 case 0xb312: s390_format_RRE_FF(s390_irgen_LTDBR, ovl.fmt.RRE.r1, 14489 ovl.fmt.RRE.r2); goto ok; 14490 case 0xb313: s390_format_RRE_FF(s390_irgen_LCDBR, ovl.fmt.RRE.r1, 14491 ovl.fmt.RRE.r2); goto ok; 14492 case 0xb314: s390_format_RRE_FF(s390_irgen_SQEBR, ovl.fmt.RRE.r1, 14493 ovl.fmt.RRE.r2); goto ok; 14494 case 0xb315: s390_format_RRE_FF(s390_irgen_SQDBR, ovl.fmt.RRE.r1, 14495 ovl.fmt.RRE.r2); goto ok; 14496 case 0xb316: s390_format_RRE_FF(s390_irgen_SQXBR, ovl.fmt.RRE.r1, 14497 ovl.fmt.RRE.r2); goto ok; 14498 case 0xb317: s390_format_RRE_FF(s390_irgen_MEEBR, ovl.fmt.RRE.r1, 14499 ovl.fmt.RRE.r2); goto ok; 14500 case 0xb318: /* KDBR */ goto unimplemented; 14501 case 0xb319: s390_format_RRE_FF(s390_irgen_CDBR, ovl.fmt.RRE.r1, 14502 ovl.fmt.RRE.r2); goto ok; 14503 case 0xb31a: s390_format_RRE_FF(s390_irgen_ADBR, ovl.fmt.RRE.r1, 14504 ovl.fmt.RRE.r2); goto ok; 14505 case 0xb31b: s390_format_RRE_FF(s390_irgen_SDBR, ovl.fmt.RRE.r1, 14506 ovl.fmt.RRE.r2); goto ok; 14507 case 0xb31c: s390_format_RRE_FF(s390_irgen_MDBR, ovl.fmt.RRE.r1, 14508 ovl.fmt.RRE.r2); goto ok; 14509 case 0xb31d: s390_format_RRE_FF(s390_irgen_DDBR, ovl.fmt.RRE.r1, 14510 ovl.fmt.RRE.r2); goto ok; 14511 case 0xb31e: s390_format_RRF_F0FF(s390_irgen_MADBR, ovl.fmt.RRF.r1, 14512 ovl.fmt.RRF.r3, ovl.fmt.RRF.r2); goto ok; 14513 case 0xb31f: s390_format_RRF_F0FF(s390_irgen_MSDBR, ovl.fmt.RRF.r1, 14514 ovl.fmt.RRF.r3, ovl.fmt.RRF.r2); goto ok; 14515 case 0xb324: /* LDER */ goto unimplemented; 14516 case 0xb325: /* LXDR */ goto unimplemented; 14517 case 0xb326: /* LXER */ goto unimplemented; 14518 case 0xb32e: /* MAER */ goto unimplemented; 14519 case 0xb32f: /* MSER */ goto unimplemented; 14520 case 0xb336: /* SQXR */ goto unimplemented; 14521 case 0xb337: /* MEER */ goto unimplemented; 14522 case 0xb338: /* MAYLR */ goto unimplemented; 14523 case 0xb339: /* MYLR */ goto unimplemented; 14524 case 0xb33a: /* MAYR */ goto unimplemented; 14525 case 0xb33b: /* MYR */ goto unimplemented; 14526 case 0xb33c: /* MAYHR */ goto unimplemented; 14527 case 0xb33d: /* MYHR */ goto unimplemented; 14528 case 0xb33e: /* MADR */ goto unimplemented; 14529 case 0xb33f: /* MSDR */ goto unimplemented; 14530 case 0xb340: s390_format_RRE_FF(s390_irgen_LPXBR, ovl.fmt.RRE.r1, 14531 ovl.fmt.RRE.r2); goto ok; 14532 case 0xb341: s390_format_RRE_FF(s390_irgen_LNXBR, ovl.fmt.RRE.r1, 14533 ovl.fmt.RRE.r2); goto ok; 14534 case 0xb342: s390_format_RRE_FF(s390_irgen_LTXBR, ovl.fmt.RRE.r1, 14535 ovl.fmt.RRE.r2); goto ok; 14536 case 0xb343: s390_format_RRE_FF(s390_irgen_LCXBR, ovl.fmt.RRE.r1, 14537 ovl.fmt.RRE.r2); goto ok; 14538 case 0xb344: s390_format_RRF_UUFF(s390_irgen_LEDBR, ovl.fmt.RRF2.m3, 14539 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14540 ovl.fmt.RRF2.r2); goto ok; 14541 case 0xb345: s390_format_RRF_UUFF(s390_irgen_LDXBR, ovl.fmt.RRF2.m3, 14542 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14543 ovl.fmt.RRF2.r2); goto ok; 14544 case 0xb346: s390_format_RRF_UUFF(s390_irgen_LEXBR, ovl.fmt.RRF2.m3, 14545 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14546 ovl.fmt.RRF2.r2); goto ok; 14547 case 0xb347: s390_format_RRF_UUFF(s390_irgen_FIXBRA, ovl.fmt.RRF2.m3, 14548 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14549 ovl.fmt.RRF2.r2); goto ok; 14550 case 0xb348: /* KXBR */ goto unimplemented; 14551 case 0xb349: s390_format_RRE_FF(s390_irgen_CXBR, ovl.fmt.RRE.r1, 14552 ovl.fmt.RRE.r2); goto ok; 14553 case 0xb34a: s390_format_RRE_FF(s390_irgen_AXBR, ovl.fmt.RRE.r1, 14554 ovl.fmt.RRE.r2); goto ok; 14555 case 0xb34b: s390_format_RRE_FF(s390_irgen_SXBR, ovl.fmt.RRE.r1, 14556 ovl.fmt.RRE.r2); goto ok; 14557 case 0xb34c: s390_format_RRE_FF(s390_irgen_MXBR, ovl.fmt.RRE.r1, 14558 ovl.fmt.RRE.r2); goto ok; 14559 case 0xb34d: s390_format_RRE_FF(s390_irgen_DXBR, ovl.fmt.RRE.r1, 14560 ovl.fmt.RRE.r2); goto ok; 14561 case 0xb350: /* TBEDR */ goto unimplemented; 14562 case 0xb351: /* TBDR */ goto unimplemented; 14563 case 0xb353: /* DIEBR */ goto unimplemented; 14564 case 0xb357: s390_format_RRF_UUFF(s390_irgen_FIEBRA, ovl.fmt.RRF2.m3, 14565 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14566 ovl.fmt.RRF2.r2); goto ok; 14567 case 0xb358: /* THDER */ goto unimplemented; 14568 case 0xb359: /* THDR */ goto unimplemented; 14569 case 0xb35b: /* DIDBR */ goto unimplemented; 14570 case 0xb35f: s390_format_RRF_UUFF(s390_irgen_FIDBRA, ovl.fmt.RRF2.m3, 14571 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14572 ovl.fmt.RRF2.r2); goto ok; 14573 case 0xb360: /* LPXR */ goto unimplemented; 14574 case 0xb361: /* LNXR */ goto unimplemented; 14575 case 0xb362: /* LTXR */ goto unimplemented; 14576 case 0xb363: /* LCXR */ goto unimplemented; 14577 case 0xb365: s390_format_RRE_FF(s390_irgen_LXR, ovl.fmt.RRE.r1, 14578 ovl.fmt.RRE.r2); goto ok; 14579 case 0xb366: /* LEXR */ goto unimplemented; 14580 case 0xb367: /* FIXR */ goto unimplemented; 14581 case 0xb369: /* CXR */ goto unimplemented; 14582 case 0xb370: s390_format_RRE_FF(s390_irgen_LPDFR, ovl.fmt.RRE.r1, 14583 ovl.fmt.RRE.r2); goto ok; 14584 case 0xb371: s390_format_RRE_FF(s390_irgen_LNDFR, ovl.fmt.RRE.r1, 14585 ovl.fmt.RRE.r2); goto ok; 14586 case 0xb372: s390_format_RRF_F0FF2(s390_irgen_CPSDR, ovl.fmt.RRF3.r3, 14587 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); 14588 goto ok; 14589 case 0xb373: s390_format_RRE_FF(s390_irgen_LCDFR, ovl.fmt.RRE.r1, 14590 ovl.fmt.RRE.r2); goto ok; 14591 case 0xb374: s390_format_RRE_F0(s390_irgen_LZER, ovl.fmt.RRE.r1); goto ok; 14592 case 0xb375: s390_format_RRE_F0(s390_irgen_LZDR, ovl.fmt.RRE.r1); goto ok; 14593 case 0xb376: s390_format_RRE_F0(s390_irgen_LZXR, ovl.fmt.RRE.r1); goto ok; 14594 case 0xb377: /* FIER */ goto unimplemented; 14595 case 0xb37f: /* FIDR */ goto unimplemented; 14596 case 0xb384: s390_format_RRE_R0(s390_irgen_SFPC, ovl.fmt.RRE.r1); goto ok; 14597 case 0xb385: /* SFASR */ goto unimplemented; 14598 case 0xb38c: s390_format_RRE_R0(s390_irgen_EFPC, ovl.fmt.RRE.r1); goto ok; 14599 case 0xb390: s390_format_RRF_UUFR(s390_irgen_CELFBR, ovl.fmt.RRF2.m3, 14600 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14601 ovl.fmt.RRF2.r2); goto ok; 14602 case 0xb391: s390_format_RRF_UUFR(s390_irgen_CDLFBR, ovl.fmt.RRF2.m3, 14603 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14604 ovl.fmt.RRF2.r2); goto ok; 14605 case 0xb392: s390_format_RRF_UUFR(s390_irgen_CXLFBR, ovl.fmt.RRF2.m3, 14606 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14607 ovl.fmt.RRF2.r2); goto ok; 14608 case 0xb394: s390_format_RRF_UUFR(s390_irgen_CEFBR, ovl.fmt.RRF2.m3, 14609 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14610 ovl.fmt.RRF2.r2); goto ok; 14611 case 0xb395: s390_format_RRF_UUFR(s390_irgen_CDFBR, ovl.fmt.RRF2.m3, 14612 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14613 ovl.fmt.RRF2.r2); goto ok; 14614 case 0xb396: s390_format_RRF_UUFR(s390_irgen_CXFBR, ovl.fmt.RRF2.m3, 14615 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14616 ovl.fmt.RRF2.r2); goto ok; 14617 case 0xb398: s390_format_RRF_UURF(s390_irgen_CFEBR, ovl.fmt.RRF2.m3, 14618 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14619 ovl.fmt.RRF2.r2); goto ok; 14620 case 0xb399: s390_format_RRF_UURF(s390_irgen_CFDBR, ovl.fmt.RRF2.m3, 14621 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14622 ovl.fmt.RRF2.r2); goto ok; 14623 case 0xb39a: s390_format_RRF_UURF(s390_irgen_CFXBR, ovl.fmt.RRF2.m3, 14624 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14625 ovl.fmt.RRF2.r2); goto ok; 14626 case 0xb39c: s390_format_RRF_UURF(s390_irgen_CLFEBR, ovl.fmt.RRF2.m3, 14627 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14628 ovl.fmt.RRF2.r2); goto ok; 14629 case 0xb39d: s390_format_RRF_UURF(s390_irgen_CLFDBR, ovl.fmt.RRF2.m3, 14630 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14631 ovl.fmt.RRF2.r2); goto ok; 14632 case 0xb39e: s390_format_RRF_UURF(s390_irgen_CLFXBR, ovl.fmt.RRF2.m3, 14633 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14634 ovl.fmt.RRF2.r2); goto ok; 14635 case 0xb3a0: s390_format_RRF_UUFR(s390_irgen_CELGBR, ovl.fmt.RRF2.m3, 14636 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14637 ovl.fmt.RRF2.r2); goto ok; 14638 case 0xb3a1: s390_format_RRF_UUFR(s390_irgen_CDLGBR, ovl.fmt.RRF2.m3, 14639 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14640 ovl.fmt.RRF2.r2); goto ok; 14641 case 0xb3a2: s390_format_RRF_UUFR(s390_irgen_CXLGBR, ovl.fmt.RRF2.m3, 14642 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14643 ovl.fmt.RRF2.r2); goto ok; 14644 case 0xb3a4: s390_format_RRF_UUFR(s390_irgen_CEGBR, ovl.fmt.RRF2.m3, 14645 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14646 ovl.fmt.RRF2.r2); goto ok; 14647 case 0xb3a5: s390_format_RRF_UUFR(s390_irgen_CDGBR, ovl.fmt.RRF2.m3, 14648 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14649 ovl.fmt.RRF2.r2); goto ok; 14650 case 0xb3a6: s390_format_RRF_UUFR(s390_irgen_CXGBR, ovl.fmt.RRF2.m3, 14651 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14652 ovl.fmt.RRF2.r2); goto ok; 14653 case 0xb3a8: s390_format_RRF_UURF(s390_irgen_CGEBR, ovl.fmt.RRF2.m3, 14654 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14655 ovl.fmt.RRF2.r2); goto ok; 14656 case 0xb3a9: s390_format_RRF_UURF(s390_irgen_CGDBR, ovl.fmt.RRF2.m3, 14657 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14658 ovl.fmt.RRF2.r2); goto ok; 14659 case 0xb3aa: s390_format_RRF_UURF(s390_irgen_CGXBR, ovl.fmt.RRF2.m3, 14660 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14661 ovl.fmt.RRF2.r2); goto ok; 14662 case 0xb3ac: s390_format_RRF_UURF(s390_irgen_CLGEBR, ovl.fmt.RRF2.m3, 14663 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14664 ovl.fmt.RRF2.r2); goto ok; 14665 case 0xb3ad: s390_format_RRF_UURF(s390_irgen_CLGDBR, ovl.fmt.RRF2.m3, 14666 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14667 ovl.fmt.RRF2.r2); goto ok; 14668 case 0xb3ae: s390_format_RRF_UURF(s390_irgen_CLGXBR, ovl.fmt.RRF2.m3, 14669 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14670 ovl.fmt.RRF2.r2); goto ok; 14671 case 0xb3b4: /* CEFR */ goto unimplemented; 14672 case 0xb3b5: /* CDFR */ goto unimplemented; 14673 case 0xb3b6: /* CXFR */ goto unimplemented; 14674 case 0xb3b8: /* CFER */ goto unimplemented; 14675 case 0xb3b9: /* CFDR */ goto unimplemented; 14676 case 0xb3ba: /* CFXR */ goto unimplemented; 14677 case 0xb3c1: s390_format_RRE_FR(s390_irgen_LDGR, ovl.fmt.RRE.r1, 14678 ovl.fmt.RRE.r2); goto ok; 14679 case 0xb3c4: /* CEGR */ goto unimplemented; 14680 case 0xb3c5: /* CDGR */ goto unimplemented; 14681 case 0xb3c6: /* CXGR */ goto unimplemented; 14682 case 0xb3c8: /* CGER */ goto unimplemented; 14683 case 0xb3c9: /* CGDR */ goto unimplemented; 14684 case 0xb3ca: /* CGXR */ goto unimplemented; 14685 case 0xb3cd: s390_format_RRE_RF(s390_irgen_LGDR, ovl.fmt.RRE.r1, 14686 ovl.fmt.RRE.r2); goto ok; 14687 case 0xb3d0: s390_format_RRF_FUFF2(s390_irgen_MDTRA, ovl.fmt.RRF4.r3, 14688 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14689 ovl.fmt.RRF4.r2); goto ok; 14690 case 0xb3d1: s390_format_RRF_FUFF2(s390_irgen_DDTRA, ovl.fmt.RRF4.r3, 14691 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14692 ovl.fmt.RRF4.r2); goto ok; 14693 case 0xb3d2: s390_format_RRF_FUFF2(s390_irgen_ADTRA, ovl.fmt.RRF4.r3, 14694 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14695 ovl.fmt.RRF4.r2); goto ok; 14696 case 0xb3d3: s390_format_RRF_FUFF2(s390_irgen_SDTRA, ovl.fmt.RRF4.r3, 14697 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14698 ovl.fmt.RRF4.r2); goto ok; 14699 case 0xb3d4: s390_format_RRF_0UFF(s390_irgen_LDETR, ovl.fmt.RRF5.m4, 14700 ovl.fmt.RRF5.r1, ovl.fmt.RRF5.r2); goto ok; 14701 case 0xb3d5: s390_format_RRF_UUFF(s390_irgen_LEDTR, ovl.fmt.RRF2.m3, 14702 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14703 ovl.fmt.RRF2.r2); goto ok; 14704 case 0xb3d6: s390_format_RRE_FF(s390_irgen_LTDTR, ovl.fmt.RRE.r1, 14705 ovl.fmt.RRE.r2); goto ok; 14706 case 0xb3d7: /* FIDTR */ goto unimplemented; 14707 case 0xb3d8: s390_format_RRF_FUFF2(s390_irgen_MXTRA, ovl.fmt.RRF4.r3, 14708 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14709 ovl.fmt.RRF4.r2); goto ok; 14710 case 0xb3d9: s390_format_RRF_FUFF2(s390_irgen_DXTRA, ovl.fmt.RRF4.r3, 14711 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14712 ovl.fmt.RRF4.r2); goto ok; 14713 case 0xb3da: s390_format_RRF_FUFF2(s390_irgen_AXTRA, ovl.fmt.RRF4.r3, 14714 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14715 ovl.fmt.RRF4.r2); goto ok; 14716 case 0xb3db: s390_format_RRF_FUFF2(s390_irgen_SXTRA, ovl.fmt.RRF4.r3, 14717 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14718 ovl.fmt.RRF4.r2); goto ok; 14719 case 0xb3dc: s390_format_RRF_0UFF(s390_irgen_LXDTR, ovl.fmt.RRF5.m4, 14720 ovl.fmt.RRF5.r1, ovl.fmt.RRF5.r2); goto ok; 14721 case 0xb3dd: s390_format_RRF_UUFF(s390_irgen_LDXTR, ovl.fmt.RRF2.m3, 14722 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14723 ovl.fmt.RRF2.r2); goto ok; 14724 case 0xb3de: s390_format_RRE_FF(s390_irgen_LTXTR, ovl.fmt.RRE.r1, 14725 ovl.fmt.RRE.r2); goto ok; 14726 case 0xb3df: /* FIXTR */ goto unimplemented; 14727 case 0xb3e0: /* KDTR */ goto unimplemented; 14728 case 0xb3e1: s390_format_RRF_UURF(s390_irgen_CGDTR, ovl.fmt.RRF2.m3, 14729 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14730 ovl.fmt.RRF2.r2); goto ok; 14731 case 0xb3e2: /* CUDTR */ goto unimplemented; 14732 case 0xb3e3: /* CSDTR */ goto unimplemented; 14733 case 0xb3e4: s390_format_RRE_FF(s390_irgen_CDTR, ovl.fmt.RRE.r1, 14734 ovl.fmt.RRE.r2); goto ok; 14735 case 0xb3e5: s390_format_RRE_RF(s390_irgen_EEDTR, ovl.fmt.RRE.r1, 14736 ovl.fmt.RRE.r2); goto ok; 14737 case 0xb3e7: s390_format_RRE_RF(s390_irgen_ESDTR, ovl.fmt.RRE.r1, 14738 ovl.fmt.RRE.r2); goto ok; 14739 case 0xb3e8: /* KXTR */ goto unimplemented; 14740 case 0xb3e9: s390_format_RRF_UURF(s390_irgen_CGXTR, ovl.fmt.RRF2.m3, 14741 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14742 ovl.fmt.RRF2.r2); goto ok; 14743 case 0xb3ea: /* CUXTR */ goto unimplemented; 14744 case 0xb3eb: /* CSXTR */ goto unimplemented; 14745 case 0xb3ec: s390_format_RRE_FF(s390_irgen_CXTR, ovl.fmt.RRE.r1, 14746 ovl.fmt.RRE.r2); goto ok; 14747 case 0xb3ed: s390_format_RRE_RF(s390_irgen_EEXTR, ovl.fmt.RRE.r1, 14748 ovl.fmt.RRE.r2); goto ok; 14749 case 0xb3ef: s390_format_RRE_RF(s390_irgen_ESXTR, ovl.fmt.RRE.r1, 14750 ovl.fmt.RRE.r2); goto ok; 14751 case 0xb3f1: s390_format_RRF_UUFR(s390_irgen_CDGTRA, ovl.fmt.RRF2.m3, 14752 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14753 ovl.fmt.RRF2.r2); goto ok; 14754 case 0xb3f2: /* CDUTR */ goto unimplemented; 14755 case 0xb3f3: /* CDSTR */ goto unimplemented; 14756 case 0xb3f4: s390_format_RRE_FF(s390_irgen_CEDTR, ovl.fmt.RRE.r1, 14757 ovl.fmt.RRE.r2); goto ok; 14758 case 0xb3f5: s390_format_RRF_FUFF(s390_irgen_QADTR, ovl.fmt.RRF4.r3, 14759 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14760 ovl.fmt.RRF4.r2); goto ok; 14761 case 0xb3f6: s390_format_RRF_F0FR(s390_irgen_IEDTR, ovl.fmt.RRF3.r3, 14762 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); goto ok; 14763 case 0xb3f7: s390_format_RRF_FFRU(s390_irgen_RRDTR, ovl.fmt.RRF4.r3, 14764 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14765 ovl.fmt.RRF4.r2); goto ok; 14766 case 0xb3f9: s390_format_RRF_UUFR(s390_irgen_CXGTR, ovl.fmt.RRF2.m3, 14767 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14768 ovl.fmt.RRF2.r2); goto ok; 14769 case 0xb3fa: /* CXUTR */ goto unimplemented; 14770 case 0xb3fb: /* CXSTR */ goto unimplemented; 14771 case 0xb3fc: s390_format_RRE_FF(s390_irgen_CEXTR, ovl.fmt.RRE.r1, 14772 ovl.fmt.RRE.r2); goto ok; 14773 case 0xb3fd: s390_format_RRF_FUFF(s390_irgen_QAXTR, ovl.fmt.RRF4.r3, 14774 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14775 ovl.fmt.RRF4.r2); goto ok; 14776 case 0xb3fe: s390_format_RRF_F0FR(s390_irgen_IEXTR, ovl.fmt.RRF3.r3, 14777 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); goto ok; 14778 case 0xb3ff: s390_format_RRF_FFRU(s390_irgen_RRXTR, ovl.fmt.RRF4.r3, 14779 ovl.fmt.RRF4.m4, ovl.fmt.RRF4.r1, 14780 ovl.fmt.RRF4.r2); goto ok; 14781 case 0xb900: s390_format_RRE_RR(s390_irgen_LPGR, ovl.fmt.RRE.r1, 14782 ovl.fmt.RRE.r2); goto ok; 14783 case 0xb901: s390_format_RRE_RR(s390_irgen_LNGR, ovl.fmt.RRE.r1, 14784 ovl.fmt.RRE.r2); goto ok; 14785 case 0xb902: s390_format_RRE_RR(s390_irgen_LTGR, ovl.fmt.RRE.r1, 14786 ovl.fmt.RRE.r2); goto ok; 14787 case 0xb903: s390_format_RRE_RR(s390_irgen_LCGR, ovl.fmt.RRE.r1, 14788 ovl.fmt.RRE.r2); goto ok; 14789 case 0xb904: s390_format_RRE_RR(s390_irgen_LGR, ovl.fmt.RRE.r1, 14790 ovl.fmt.RRE.r2); goto ok; 14791 case 0xb905: /* LURAG */ goto unimplemented; 14792 case 0xb906: s390_format_RRE_RR(s390_irgen_LGBR, ovl.fmt.RRE.r1, 14793 ovl.fmt.RRE.r2); goto ok; 14794 case 0xb907: s390_format_RRE_RR(s390_irgen_LGHR, ovl.fmt.RRE.r1, 14795 ovl.fmt.RRE.r2); goto ok; 14796 case 0xb908: s390_format_RRE_RR(s390_irgen_AGR, ovl.fmt.RRE.r1, 14797 ovl.fmt.RRE.r2); goto ok; 14798 case 0xb909: s390_format_RRE_RR(s390_irgen_SGR, ovl.fmt.RRE.r1, 14799 ovl.fmt.RRE.r2); goto ok; 14800 case 0xb90a: s390_format_RRE_RR(s390_irgen_ALGR, ovl.fmt.RRE.r1, 14801 ovl.fmt.RRE.r2); goto ok; 14802 case 0xb90b: s390_format_RRE_RR(s390_irgen_SLGR, ovl.fmt.RRE.r1, 14803 ovl.fmt.RRE.r2); goto ok; 14804 case 0xb90c: s390_format_RRE_RR(s390_irgen_MSGR, ovl.fmt.RRE.r1, 14805 ovl.fmt.RRE.r2); goto ok; 14806 case 0xb90d: s390_format_RRE_RR(s390_irgen_DSGR, ovl.fmt.RRE.r1, 14807 ovl.fmt.RRE.r2); goto ok; 14808 case 0xb90e: /* EREGG */ goto unimplemented; 14809 case 0xb90f: s390_format_RRE_RR(s390_irgen_LRVGR, ovl.fmt.RRE.r1, 14810 ovl.fmt.RRE.r2); goto ok; 14811 case 0xb910: s390_format_RRE_RR(s390_irgen_LPGFR, ovl.fmt.RRE.r1, 14812 ovl.fmt.RRE.r2); goto ok; 14813 case 0xb911: s390_format_RRE_RR(s390_irgen_LNGFR, ovl.fmt.RRE.r1, 14814 ovl.fmt.RRE.r2); goto ok; 14815 case 0xb912: s390_format_RRE_RR(s390_irgen_LTGFR, ovl.fmt.RRE.r1, 14816 ovl.fmt.RRE.r2); goto ok; 14817 case 0xb913: s390_format_RRE_RR(s390_irgen_LCGFR, ovl.fmt.RRE.r1, 14818 ovl.fmt.RRE.r2); goto ok; 14819 case 0xb914: s390_format_RRE_RR(s390_irgen_LGFR, ovl.fmt.RRE.r1, 14820 ovl.fmt.RRE.r2); goto ok; 14821 case 0xb916: s390_format_RRE_RR(s390_irgen_LLGFR, ovl.fmt.RRE.r1, 14822 ovl.fmt.RRE.r2); goto ok; 14823 case 0xb917: s390_format_RRE_RR(s390_irgen_LLGTR, ovl.fmt.RRE.r1, 14824 ovl.fmt.RRE.r2); goto ok; 14825 case 0xb918: s390_format_RRE_RR(s390_irgen_AGFR, ovl.fmt.RRE.r1, 14826 ovl.fmt.RRE.r2); goto ok; 14827 case 0xb919: s390_format_RRE_RR(s390_irgen_SGFR, ovl.fmt.RRE.r1, 14828 ovl.fmt.RRE.r2); goto ok; 14829 case 0xb91a: s390_format_RRE_RR(s390_irgen_ALGFR, ovl.fmt.RRE.r1, 14830 ovl.fmt.RRE.r2); goto ok; 14831 case 0xb91b: s390_format_RRE_RR(s390_irgen_SLGFR, ovl.fmt.RRE.r1, 14832 ovl.fmt.RRE.r2); goto ok; 14833 case 0xb91c: s390_format_RRE_RR(s390_irgen_MSGFR, ovl.fmt.RRE.r1, 14834 ovl.fmt.RRE.r2); goto ok; 14835 case 0xb91d: s390_format_RRE_RR(s390_irgen_DSGFR, ovl.fmt.RRE.r1, 14836 ovl.fmt.RRE.r2); goto ok; 14837 case 0xb91e: /* KMAC */ goto unimplemented; 14838 case 0xb91f: s390_format_RRE_RR(s390_irgen_LRVR, ovl.fmt.RRE.r1, 14839 ovl.fmt.RRE.r2); goto ok; 14840 case 0xb920: s390_format_RRE_RR(s390_irgen_CGR, ovl.fmt.RRE.r1, 14841 ovl.fmt.RRE.r2); goto ok; 14842 case 0xb921: s390_format_RRE_RR(s390_irgen_CLGR, ovl.fmt.RRE.r1, 14843 ovl.fmt.RRE.r2); goto ok; 14844 case 0xb925: /* STURG */ goto unimplemented; 14845 case 0xb926: s390_format_RRE_RR(s390_irgen_LBR, ovl.fmt.RRE.r1, 14846 ovl.fmt.RRE.r2); goto ok; 14847 case 0xb927: s390_format_RRE_RR(s390_irgen_LHR, ovl.fmt.RRE.r1, 14848 ovl.fmt.RRE.r2); goto ok; 14849 case 0xb928: /* PCKMO */ goto unimplemented; 14850 case 0xb92a: /* KMF */ goto unimplemented; 14851 case 0xb92b: /* KMO */ goto unimplemented; 14852 case 0xb92c: /* PCC */ goto unimplemented; 14853 case 0xb92d: /* KMCTR */ goto unimplemented; 14854 case 0xb92e: /* KM */ goto unimplemented; 14855 case 0xb92f: /* KMC */ goto unimplemented; 14856 case 0xb930: s390_format_RRE_RR(s390_irgen_CGFR, ovl.fmt.RRE.r1, 14857 ovl.fmt.RRE.r2); goto ok; 14858 case 0xb931: s390_format_RRE_RR(s390_irgen_CLGFR, ovl.fmt.RRE.r1, 14859 ovl.fmt.RRE.r2); goto ok; 14860 case 0xb93e: /* KIMD */ goto unimplemented; 14861 case 0xb93f: /* KLMD */ goto unimplemented; 14862 case 0xb941: s390_format_RRF_UURF(s390_irgen_CFDTR, ovl.fmt.RRF2.m3, 14863 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14864 ovl.fmt.RRF2.r2); goto ok; 14865 case 0xb942: s390_format_RRF_UURF(s390_irgen_CLGDTR, ovl.fmt.RRF2.m3, 14866 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14867 ovl.fmt.RRF2.r2); goto ok; 14868 case 0xb943: s390_format_RRF_UURF(s390_irgen_CLFDTR, ovl.fmt.RRF2.m3, 14869 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14870 ovl.fmt.RRF2.r2); goto ok; 14871 case 0xb946: s390_format_RRE_RR(s390_irgen_BCTGR, ovl.fmt.RRE.r1, 14872 ovl.fmt.RRE.r2); goto ok; 14873 case 0xb949: s390_format_RRF_UURF(s390_irgen_CFXTR, ovl.fmt.RRF2.m3, 14874 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14875 ovl.fmt.RRF2.r2); goto ok; 14876 case 0xb94a: s390_format_RRF_UURF(s390_irgen_CLGXTR, ovl.fmt.RRF2.m3, 14877 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14878 ovl.fmt.RRF2.r2); goto ok; 14879 case 0xb94b: s390_format_RRF_UURF(s390_irgen_CLFXTR, ovl.fmt.RRF2.m3, 14880 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14881 ovl.fmt.RRF2.r2); goto ok; 14882 case 0xb951: s390_format_RRF_UUFR(s390_irgen_CDFTR, ovl.fmt.RRF2.m3, 14883 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14884 ovl.fmt.RRF2.r2); goto ok; 14885 case 0xb952: s390_format_RRF_UUFR(s390_irgen_CDLGTR, ovl.fmt.RRF2.m3, 14886 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14887 ovl.fmt.RRF2.r2); goto ok; 14888 case 0xb953: s390_format_RRF_UUFR(s390_irgen_CDLFTR, ovl.fmt.RRF2.m3, 14889 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14890 ovl.fmt.RRF2.r2); goto ok; 14891 case 0xb959: s390_format_RRF_UUFR(s390_irgen_CXFTR, ovl.fmt.RRF2.m3, 14892 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14893 ovl.fmt.RRF2.r2); goto ok; 14894 case 0xb95a: s390_format_RRF_UUFR(s390_irgen_CXLGTR, ovl.fmt.RRF2.m3, 14895 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14896 ovl.fmt.RRF2.r2); goto ok; 14897 case 0xb95b: s390_format_RRF_UUFR(s390_irgen_CXLFTR, ovl.fmt.RRF2.m3, 14898 ovl.fmt.RRF2.m4, ovl.fmt.RRF2.r1, 14899 ovl.fmt.RRF2.r2); goto ok; 14900 case 0xb960: /* CGRT */ goto unimplemented; 14901 case 0xb961: /* CLGRT */ goto unimplemented; 14902 case 0xb972: /* CRT */ goto unimplemented; 14903 case 0xb973: /* CLRT */ goto unimplemented; 14904 case 0xb980: s390_format_RRE_RR(s390_irgen_NGR, ovl.fmt.RRE.r1, 14905 ovl.fmt.RRE.r2); goto ok; 14906 case 0xb981: s390_format_RRE_RR(s390_irgen_OGR, ovl.fmt.RRE.r1, 14907 ovl.fmt.RRE.r2); goto ok; 14908 case 0xb982: s390_format_RRE_RR(s390_irgen_XGR, ovl.fmt.RRE.r1, 14909 ovl.fmt.RRE.r2); goto ok; 14910 case 0xb983: s390_format_RRE_RR(s390_irgen_FLOGR, ovl.fmt.RRE.r1, 14911 ovl.fmt.RRE.r2); goto ok; 14912 case 0xb984: s390_format_RRE_RR(s390_irgen_LLGCR, ovl.fmt.RRE.r1, 14913 ovl.fmt.RRE.r2); goto ok; 14914 case 0xb985: s390_format_RRE_RR(s390_irgen_LLGHR, ovl.fmt.RRE.r1, 14915 ovl.fmt.RRE.r2); goto ok; 14916 case 0xb986: s390_format_RRE_RR(s390_irgen_MLGR, ovl.fmt.RRE.r1, 14917 ovl.fmt.RRE.r2); goto ok; 14918 case 0xb987: s390_format_RRE_RR(s390_irgen_DLGR, ovl.fmt.RRE.r1, 14919 ovl.fmt.RRE.r2); goto ok; 14920 case 0xb988: s390_format_RRE_RR(s390_irgen_ALCGR, ovl.fmt.RRE.r1, 14921 ovl.fmt.RRE.r2); goto ok; 14922 case 0xb989: s390_format_RRE_RR(s390_irgen_SLBGR, ovl.fmt.RRE.r1, 14923 ovl.fmt.RRE.r2); goto ok; 14924 case 0xb98a: /* CSPG */ goto unimplemented; 14925 case 0xb98d: /* EPSW */ goto unimplemented; 14926 case 0xb98e: /* IDTE */ goto unimplemented; 14927 case 0xb98f: /* CRDTE */ goto unimplemented; 14928 case 0xb990: s390_format_RRF_M0RERE(s390_irgen_TRTT, ovl.fmt.RRF3.r3, 14929 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); goto ok; 14930 case 0xb991: s390_format_RRF_M0RERE(s390_irgen_TRTO, ovl.fmt.RRF3.r3, 14931 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); goto ok; 14932 case 0xb992: s390_format_RRF_M0RERE(s390_irgen_TROT, ovl.fmt.RRF3.r3, 14933 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); goto ok; 14934 case 0xb993: s390_format_RRF_M0RERE(s390_irgen_TROO, ovl.fmt.RRF3.r3, 14935 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); goto ok; 14936 case 0xb994: s390_format_RRE_RR(s390_irgen_LLCR, ovl.fmt.RRE.r1, 14937 ovl.fmt.RRE.r2); goto ok; 14938 case 0xb995: s390_format_RRE_RR(s390_irgen_LLHR, ovl.fmt.RRE.r1, 14939 ovl.fmt.RRE.r2); goto ok; 14940 case 0xb996: s390_format_RRE_RR(s390_irgen_MLR, ovl.fmt.RRE.r1, 14941 ovl.fmt.RRE.r2); goto ok; 14942 case 0xb997: s390_format_RRE_RR(s390_irgen_DLR, ovl.fmt.RRE.r1, 14943 ovl.fmt.RRE.r2); goto ok; 14944 case 0xb998: s390_format_RRE_RR(s390_irgen_ALCR, ovl.fmt.RRE.r1, 14945 ovl.fmt.RRE.r2); goto ok; 14946 case 0xb999: s390_format_RRE_RR(s390_irgen_SLBR, ovl.fmt.RRE.r1, 14947 ovl.fmt.RRE.r2); goto ok; 14948 case 0xb99a: /* EPAIR */ goto unimplemented; 14949 case 0xb99b: /* ESAIR */ goto unimplemented; 14950 case 0xb99d: /* ESEA */ goto unimplemented; 14951 case 0xb99e: /* PTI */ goto unimplemented; 14952 case 0xb99f: /* SSAIR */ goto unimplemented; 14953 case 0xb9a2: /* PTF */ goto unimplemented; 14954 case 0xb9aa: /* LPTEA */ goto unimplemented; 14955 case 0xb9ae: /* RRBM */ goto unimplemented; 14956 case 0xb9af: /* PFMF */ goto unimplemented; 14957 case 0xb9b0: s390_format_RRF_M0RERE(s390_irgen_CU14, ovl.fmt.RRF3.r3, 14958 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); 14959 goto ok; 14960 case 0xb9b1: s390_format_RRF_M0RERE(s390_irgen_CU24, ovl.fmt.RRF3.r3, 14961 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2); 14962 goto ok; 14963 case 0xb9b2: s390_format_RRE_RR(s390_irgen_CU41, ovl.fmt.RRE.r1, 14964 ovl.fmt.RRE.r2); goto ok; 14965 case 0xb9b3: s390_format_RRE_RR(s390_irgen_CU42, ovl.fmt.RRE.r1, 14966 ovl.fmt.RRE.r2); goto ok; 14967 case 0xb9bd: /* TRTRE */ goto unimplemented; 14968 case 0xb9be: /* SRSTU */ goto unimplemented; 14969 case 0xb9bf: /* TRTE */ goto unimplemented; 14970 case 0xb9c8: s390_format_RRF_R0RR2(s390_irgen_AHHHR, ovl.fmt.RRF4.r3, 14971 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 14972 goto ok; 14973 case 0xb9c9: s390_format_RRF_R0RR2(s390_irgen_SHHHR, ovl.fmt.RRF4.r3, 14974 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 14975 goto ok; 14976 case 0xb9ca: s390_format_RRF_R0RR2(s390_irgen_ALHHHR, ovl.fmt.RRF4.r3, 14977 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 14978 goto ok; 14979 case 0xb9cb: s390_format_RRF_R0RR2(s390_irgen_SLHHHR, ovl.fmt.RRF4.r3, 14980 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 14981 goto ok; 14982 case 0xb9cd: s390_format_RRE_RR(s390_irgen_CHHR, ovl.fmt.RRE.r1, 14983 ovl.fmt.RRE.r2); goto ok; 14984 case 0xb9cf: s390_format_RRE_RR(s390_irgen_CLHHR, ovl.fmt.RRE.r1, 14985 ovl.fmt.RRE.r2); goto ok; 14986 case 0xb9d8: s390_format_RRF_R0RR2(s390_irgen_AHHLR, ovl.fmt.RRF4.r3, 14987 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 14988 goto ok; 14989 case 0xb9d9: s390_format_RRF_R0RR2(s390_irgen_SHHLR, ovl.fmt.RRF4.r3, 14990 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 14991 goto ok; 14992 case 0xb9da: s390_format_RRF_R0RR2(s390_irgen_ALHHLR, ovl.fmt.RRF4.r3, 14993 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 14994 goto ok; 14995 case 0xb9db: s390_format_RRF_R0RR2(s390_irgen_SLHHLR, ovl.fmt.RRF4.r3, 14996 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 14997 goto ok; 14998 case 0xb9dd: s390_format_RRE_RR(s390_irgen_CHLR, ovl.fmt.RRE.r1, 14999 ovl.fmt.RRE.r2); goto ok; 15000 case 0xb9df: s390_format_RRE_RR(s390_irgen_CLHLR, ovl.fmt.RRE.r1, 15001 ovl.fmt.RRE.r2); goto ok; 15002 case 0xb9e1: /* POPCNT */ goto unimplemented; 15003 case 0xb9e2: s390_format_RRF_U0RR(s390_irgen_LOCGR, ovl.fmt.RRF3.r3, 15004 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2, 15005 S390_XMNM_LOCGR); goto ok; 15006 case 0xb9e4: s390_format_RRF_R0RR2(s390_irgen_NGRK, ovl.fmt.RRF4.r3, 15007 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15008 goto ok; 15009 case 0xb9e6: s390_format_RRF_R0RR2(s390_irgen_OGRK, ovl.fmt.RRF4.r3, 15010 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15011 goto ok; 15012 case 0xb9e7: s390_format_RRF_R0RR2(s390_irgen_XGRK, ovl.fmt.RRF4.r3, 15013 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15014 goto ok; 15015 case 0xb9e8: s390_format_RRF_R0RR2(s390_irgen_AGRK, ovl.fmt.RRF4.r3, 15016 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15017 goto ok; 15018 case 0xb9e9: s390_format_RRF_R0RR2(s390_irgen_SGRK, ovl.fmt.RRF4.r3, 15019 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15020 goto ok; 15021 case 0xb9ea: s390_format_RRF_R0RR2(s390_irgen_ALGRK, ovl.fmt.RRF4.r3, 15022 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15023 goto ok; 15024 case 0xb9eb: s390_format_RRF_R0RR2(s390_irgen_SLGRK, ovl.fmt.RRF4.r3, 15025 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15026 goto ok; 15027 case 0xb9f2: s390_format_RRF_U0RR(s390_irgen_LOCR, ovl.fmt.RRF3.r3, 15028 ovl.fmt.RRF3.r1, ovl.fmt.RRF3.r2, 15029 S390_XMNM_LOCR); goto ok; 15030 case 0xb9f4: s390_format_RRF_R0RR2(s390_irgen_NRK, ovl.fmt.RRF4.r3, 15031 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15032 goto ok; 15033 case 0xb9f6: s390_format_RRF_R0RR2(s390_irgen_ORK, ovl.fmt.RRF4.r3, 15034 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15035 goto ok; 15036 case 0xb9f7: s390_format_RRF_R0RR2(s390_irgen_XRK, ovl.fmt.RRF4.r3, 15037 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15038 goto ok; 15039 case 0xb9f8: s390_format_RRF_R0RR2(s390_irgen_ARK, ovl.fmt.RRF4.r3, 15040 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15041 goto ok; 15042 case 0xb9f9: s390_format_RRF_R0RR2(s390_irgen_SRK, ovl.fmt.RRF4.r3, 15043 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15044 goto ok; 15045 case 0xb9fa: s390_format_RRF_R0RR2(s390_irgen_ALRK, ovl.fmt.RRF4.r3, 15046 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15047 goto ok; 15048 case 0xb9fb: s390_format_RRF_R0RR2(s390_irgen_SLRK, ovl.fmt.RRF4.r3, 15049 ovl.fmt.RRF4.r1, ovl.fmt.RRF4.r2); 15050 goto ok; 15051 } 15052 15053 switch ((ovl.value & 0xff000000) >> 24) { 15054 case 0x40: s390_format_RX_RRRD(s390_irgen_STH, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15055 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15056 case 0x41: s390_format_RX_RRRD(s390_irgen_LA, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15057 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15058 case 0x42: s390_format_RX_RRRD(s390_irgen_STC, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15059 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15060 case 0x43: s390_format_RX_RRRD(s390_irgen_IC, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15061 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15062 case 0x44: s390_format_RX_RRRD(s390_irgen_EX, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15063 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15064 case 0x45: /* BAL */ goto unimplemented; 15065 case 0x46: s390_format_RX_RRRD(s390_irgen_BCT, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15066 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15067 case 0x47: s390_format_RX(s390_irgen_BC, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15068 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15069 case 0x48: s390_format_RX_RRRD(s390_irgen_LH, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15070 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15071 case 0x49: s390_format_RX_RRRD(s390_irgen_CH, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15072 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15073 case 0x4a: s390_format_RX_RRRD(s390_irgen_AH, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15074 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15075 case 0x4b: s390_format_RX_RRRD(s390_irgen_SH, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15076 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15077 case 0x4c: s390_format_RX_RRRD(s390_irgen_MH, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15078 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15079 case 0x4d: s390_format_RX_RRRD(s390_irgen_BAS, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15080 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15081 case 0x4e: s390_format_RX_RRRD(s390_irgen_CVD, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15082 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15083 case 0x4f: s390_format_RX_RRRD(s390_irgen_CVB, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15084 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15085 case 0x50: s390_format_RX_RRRD(s390_irgen_ST, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15086 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15087 case 0x51: s390_format_RX_RRRD(s390_irgen_LAE, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15088 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15089 case 0x54: s390_format_RX_RRRD(s390_irgen_N, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15090 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15091 case 0x55: s390_format_RX_RRRD(s390_irgen_CL, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15092 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15093 case 0x56: s390_format_RX_RRRD(s390_irgen_O, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15094 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15095 case 0x57: s390_format_RX_RRRD(s390_irgen_X, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15096 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15097 case 0x58: s390_format_RX_RRRD(s390_irgen_L, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15098 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15099 case 0x59: s390_format_RX_RRRD(s390_irgen_C, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15100 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15101 case 0x5a: s390_format_RX_RRRD(s390_irgen_A, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15102 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15103 case 0x5b: s390_format_RX_RRRD(s390_irgen_S, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15104 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15105 case 0x5c: s390_format_RX_RRRD(s390_irgen_M, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15106 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15107 case 0x5d: s390_format_RX_RRRD(s390_irgen_D, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15108 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15109 case 0x5e: s390_format_RX_RRRD(s390_irgen_AL, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15110 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15111 case 0x5f: s390_format_RX_RRRD(s390_irgen_SL, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15112 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15113 case 0x60: s390_format_RX_FRRD(s390_irgen_STD, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15114 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15115 case 0x67: /* MXD */ goto unimplemented; 15116 case 0x68: s390_format_RX_FRRD(s390_irgen_LD, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15117 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15118 case 0x69: /* CD */ goto unimplemented; 15119 case 0x6a: /* AD */ goto unimplemented; 15120 case 0x6b: /* SD */ goto unimplemented; 15121 case 0x6c: /* MD */ goto unimplemented; 15122 case 0x6d: /* DD */ goto unimplemented; 15123 case 0x6e: /* AW */ goto unimplemented; 15124 case 0x6f: /* SW */ goto unimplemented; 15125 case 0x70: s390_format_RX_FRRD(s390_irgen_STE, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15126 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15127 case 0x71: s390_format_RX_RRRD(s390_irgen_MS, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15128 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15129 case 0x78: s390_format_RX_FRRD(s390_irgen_LE, ovl.fmt.RX.r1, ovl.fmt.RX.x2, 15130 ovl.fmt.RX.b2, ovl.fmt.RX.d2); goto ok; 15131 case 0x79: /* CE */ goto unimplemented; 15132 case 0x7a: /* AE */ goto unimplemented; 15133 case 0x7b: /* SE */ goto unimplemented; 15134 case 0x7c: /* MDE */ goto unimplemented; 15135 case 0x7d: /* DE */ goto unimplemented; 15136 case 0x7e: /* AU */ goto unimplemented; 15137 case 0x7f: /* SU */ goto unimplemented; 15138 case 0x83: /* DIAG */ goto unimplemented; 15139 case 0x84: s390_format_RSI_RRP(s390_irgen_BRXH, ovl.fmt.RSI.r1, 15140 ovl.fmt.RSI.r3, ovl.fmt.RSI.i2); goto ok; 15141 case 0x85: s390_format_RSI_RRP(s390_irgen_BRXLE, ovl.fmt.RSI.r1, 15142 ovl.fmt.RSI.r3, ovl.fmt.RSI.i2); goto ok; 15143 case 0x86: s390_format_RS_RRRD(s390_irgen_BXH, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15144 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15145 case 0x87: s390_format_RS_RRRD(s390_irgen_BXLE, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15146 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15147 case 0x88: s390_format_RS_R0RD(s390_irgen_SRL, ovl.fmt.RS.r1, ovl.fmt.RS.b2, 15148 ovl.fmt.RS.d2); goto ok; 15149 case 0x89: s390_format_RS_R0RD(s390_irgen_SLL, ovl.fmt.RS.r1, ovl.fmt.RS.b2, 15150 ovl.fmt.RS.d2); goto ok; 15151 case 0x8a: s390_format_RS_R0RD(s390_irgen_SRA, ovl.fmt.RS.r1, ovl.fmt.RS.b2, 15152 ovl.fmt.RS.d2); goto ok; 15153 case 0x8b: s390_format_RS_R0RD(s390_irgen_SLA, ovl.fmt.RS.r1, ovl.fmt.RS.b2, 15154 ovl.fmt.RS.d2); goto ok; 15155 case 0x8c: s390_format_RS_R0RD(s390_irgen_SRDL, ovl.fmt.RS.r1, ovl.fmt.RS.b2, 15156 ovl.fmt.RS.d2); goto ok; 15157 case 0x8d: s390_format_RS_R0RD(s390_irgen_SLDL, ovl.fmt.RS.r1, ovl.fmt.RS.b2, 15158 ovl.fmt.RS.d2); goto ok; 15159 case 0x8e: s390_format_RS_R0RD(s390_irgen_SRDA, ovl.fmt.RS.r1, ovl.fmt.RS.b2, 15160 ovl.fmt.RS.d2); goto ok; 15161 case 0x8f: s390_format_RS_R0RD(s390_irgen_SLDA, ovl.fmt.RS.r1, ovl.fmt.RS.b2, 15162 ovl.fmt.RS.d2); goto ok; 15163 case 0x90: s390_format_RS_RRRD(s390_irgen_STM, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15164 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15165 case 0x91: s390_format_SI_URD(s390_irgen_TM, ovl.fmt.SI.i2, ovl.fmt.SI.b1, 15166 ovl.fmt.SI.d1); goto ok; 15167 case 0x92: s390_format_SI_URD(s390_irgen_MVI, ovl.fmt.SI.i2, ovl.fmt.SI.b1, 15168 ovl.fmt.SI.d1); goto ok; 15169 case 0x94: s390_format_SI_URD(s390_irgen_NI, ovl.fmt.SI.i2, ovl.fmt.SI.b1, 15170 ovl.fmt.SI.d1); goto ok; 15171 case 0x95: s390_format_SI_URD(s390_irgen_CLI, ovl.fmt.SI.i2, ovl.fmt.SI.b1, 15172 ovl.fmt.SI.d1); goto ok; 15173 case 0x96: s390_format_SI_URD(s390_irgen_OI, ovl.fmt.SI.i2, ovl.fmt.SI.b1, 15174 ovl.fmt.SI.d1); goto ok; 15175 case 0x97: s390_format_SI_URD(s390_irgen_XI, ovl.fmt.SI.i2, ovl.fmt.SI.b1, 15176 ovl.fmt.SI.d1); goto ok; 15177 case 0x98: s390_format_RS_RRRD(s390_irgen_LM, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15178 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15179 case 0x99: /* TRACE */ goto unimplemented; 15180 case 0x9a: s390_format_RS_AARD(s390_irgen_LAM, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15181 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15182 case 0x9b: s390_format_RS_AARD(s390_irgen_STAM, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15183 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15184 case 0xa8: s390_format_RS_RRRD(s390_irgen_MVCLE, ovl.fmt.RS.r1, 15185 ovl.fmt.RS.r3, ovl.fmt.RS.b2, ovl.fmt.RS.d2); 15186 goto ok; 15187 case 0xa9: s390_format_RS_RRRD(s390_irgen_CLCLE, ovl.fmt.RS.r1, 15188 ovl.fmt.RS.r3, ovl.fmt.RS.b2, ovl.fmt.RS.d2); 15189 goto ok; 15190 case 0xac: /* STNSM */ goto unimplemented; 15191 case 0xad: /* STOSM */ goto unimplemented; 15192 case 0xae: /* SIGP */ goto unimplemented; 15193 case 0xaf: /* MC */ goto unimplemented; 15194 case 0xb1: /* LRA */ goto unimplemented; 15195 case 0xb6: /* STCTL */ goto unimplemented; 15196 case 0xb7: /* LCTL */ goto unimplemented; 15197 case 0xba: s390_format_RS_RRRD(s390_irgen_CS, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15198 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15199 case 0xbb: s390_format_RS_RRRD(s390_irgen_CDS, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15200 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15201 case 0xbd: s390_format_RS_RURD(s390_irgen_CLM, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15202 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15203 case 0xbe: s390_format_RS_RURD(s390_irgen_STCM, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15204 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15205 case 0xbf: s390_format_RS_RURD(s390_irgen_ICM, ovl.fmt.RS.r1, ovl.fmt.RS.r3, 15206 ovl.fmt.RS.b2, ovl.fmt.RS.d2); goto ok; 15207 } 15208 15209 return S390_DECODE_UNKNOWN_INSN; 15210 15211 ok: 15212 return S390_DECODE_OK; 15213 15214 unimplemented: 15215 return S390_DECODE_UNIMPLEMENTED_INSN; 15216 } 15217 15218 static s390_decode_t 15219 s390_decode_6byte_and_irgen(const UChar *bytes) 15220 { 15221 typedef union { 15222 struct { 15223 unsigned int op1 : 8; 15224 unsigned int r1 : 4; 15225 unsigned int r3 : 4; 15226 unsigned int i2 : 16; 15227 unsigned int : 8; 15228 unsigned int op2 : 8; 15229 } RIE; 15230 struct { 15231 unsigned int op1 : 8; 15232 unsigned int r1 : 4; 15233 unsigned int r2 : 4; 15234 unsigned int i3 : 8; 15235 unsigned int i4 : 8; 15236 unsigned int i5 : 8; 15237 unsigned int op2 : 8; 15238 } RIE_RRUUU; 15239 struct { 15240 unsigned int op1 : 8; 15241 unsigned int r1 : 4; 15242 unsigned int : 4; 15243 unsigned int i2 : 16; 15244 unsigned int m3 : 4; 15245 unsigned int : 4; 15246 unsigned int op2 : 8; 15247 } RIEv1; 15248 struct { 15249 unsigned int op1 : 8; 15250 unsigned int r1 : 4; 15251 unsigned int r2 : 4; 15252 unsigned int i4 : 16; 15253 unsigned int m3 : 4; 15254 unsigned int : 4; 15255 unsigned int op2 : 8; 15256 } RIE_RRPU; 15257 struct { 15258 unsigned int op1 : 8; 15259 unsigned int r1 : 4; 15260 unsigned int m3 : 4; 15261 unsigned int i4 : 16; 15262 unsigned int i2 : 8; 15263 unsigned int op2 : 8; 15264 } RIEv3; 15265 struct { 15266 unsigned int op1 : 8; 15267 unsigned int r1 : 4; 15268 unsigned int op2 : 4; 15269 unsigned int i2 : 32; 15270 } RIL; 15271 struct { 15272 unsigned int op1 : 8; 15273 unsigned int r1 : 4; 15274 unsigned int m3 : 4; 15275 unsigned int b4 : 4; 15276 unsigned int d4 : 12; 15277 unsigned int i2 : 8; 15278 unsigned int op2 : 8; 15279 } RIS; 15280 struct { 15281 unsigned int op1 : 8; 15282 unsigned int r1 : 4; 15283 unsigned int r2 : 4; 15284 unsigned int b4 : 4; 15285 unsigned int d4 : 12; 15286 unsigned int m3 : 4; 15287 unsigned int : 4; 15288 unsigned int op2 : 8; 15289 } RRS; 15290 struct { 15291 unsigned int op1 : 8; 15292 unsigned int l1 : 4; 15293 unsigned int : 4; 15294 unsigned int b1 : 4; 15295 unsigned int d1 : 12; 15296 unsigned int : 8; 15297 unsigned int op2 : 8; 15298 } RSL; 15299 struct { 15300 unsigned int op1 : 8; 15301 unsigned int r1 : 4; 15302 unsigned int r3 : 4; 15303 unsigned int b2 : 4; 15304 unsigned int dl2 : 12; 15305 unsigned int dh2 : 8; 15306 unsigned int op2 : 8; 15307 } RSY; 15308 struct { 15309 unsigned int op1 : 8; 15310 unsigned int r1 : 4; 15311 unsigned int x2 : 4; 15312 unsigned int b2 : 4; 15313 unsigned int d2 : 12; 15314 unsigned int : 8; 15315 unsigned int op2 : 8; 15316 } RXE; 15317 struct { 15318 unsigned int op1 : 8; 15319 unsigned int r3 : 4; 15320 unsigned int x2 : 4; 15321 unsigned int b2 : 4; 15322 unsigned int d2 : 12; 15323 unsigned int r1 : 4; 15324 unsigned int : 4; 15325 unsigned int op2 : 8; 15326 } RXF; 15327 struct { 15328 unsigned int op1 : 8; 15329 unsigned int r1 : 4; 15330 unsigned int x2 : 4; 15331 unsigned int b2 : 4; 15332 unsigned int dl2 : 12; 15333 unsigned int dh2 : 8; 15334 unsigned int op2 : 8; 15335 } RXY; 15336 struct { 15337 unsigned int op1 : 8; 15338 unsigned int i2 : 8; 15339 unsigned int b1 : 4; 15340 unsigned int dl1 : 12; 15341 unsigned int dh1 : 8; 15342 unsigned int op2 : 8; 15343 } SIY; 15344 struct { 15345 unsigned int op : 8; 15346 unsigned int l : 8; 15347 unsigned int b1 : 4; 15348 unsigned int d1 : 12; 15349 unsigned int b2 : 4; 15350 unsigned int d2 : 12; 15351 } SS; 15352 struct { 15353 unsigned int op : 8; 15354 unsigned int l1 : 4; 15355 unsigned int l2 : 4; 15356 unsigned int b1 : 4; 15357 unsigned int d1 : 12; 15358 unsigned int b2 : 4; 15359 unsigned int d2 : 12; 15360 } SS_LLRDRD; 15361 struct { 15362 unsigned int op : 8; 15363 unsigned int r1 : 4; 15364 unsigned int r3 : 4; 15365 unsigned int b2 : 4; 15366 unsigned int d2 : 12; 15367 unsigned int b4 : 4; 15368 unsigned int d4 : 12; 15369 } SS_RRRDRD2; 15370 struct { 15371 unsigned int op : 16; 15372 unsigned int b1 : 4; 15373 unsigned int d1 : 12; 15374 unsigned int b2 : 4; 15375 unsigned int d2 : 12; 15376 } SSE; 15377 struct { 15378 unsigned int op1 : 8; 15379 unsigned int r3 : 4; 15380 unsigned int op2 : 4; 15381 unsigned int b1 : 4; 15382 unsigned int d1 : 12; 15383 unsigned int b2 : 4; 15384 unsigned int d2 : 12; 15385 } SSF; 15386 struct { 15387 unsigned int op : 16; 15388 unsigned int b1 : 4; 15389 unsigned int d1 : 12; 15390 unsigned int i2 : 16; 15391 } SIL; 15392 } formats; 15393 union { 15394 formats fmt; 15395 ULong value; 15396 } ovl; 15397 15398 vassert(sizeof(formats) == 6); 15399 15400 ((UChar *)(&ovl.value))[0] = bytes[0]; 15401 ((UChar *)(&ovl.value))[1] = bytes[1]; 15402 ((UChar *)(&ovl.value))[2] = bytes[2]; 15403 ((UChar *)(&ovl.value))[3] = bytes[3]; 15404 ((UChar *)(&ovl.value))[4] = bytes[4]; 15405 ((UChar *)(&ovl.value))[5] = bytes[5]; 15406 ((UChar *)(&ovl.value))[6] = 0x0; 15407 ((UChar *)(&ovl.value))[7] = 0x0; 15408 15409 switch ((ovl.value >> 16) & 0xff00000000ffULL) { 15410 case 0xe30000000002ULL: s390_format_RXY_RRRD(s390_irgen_LTG, ovl.fmt.RXY.r1, 15411 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15412 ovl.fmt.RXY.dl2, 15413 ovl.fmt.RXY.dh2); goto ok; 15414 case 0xe30000000003ULL: /* LRAG */ goto unimplemented; 15415 case 0xe30000000004ULL: s390_format_RXY_RRRD(s390_irgen_LG, ovl.fmt.RXY.r1, 15416 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15417 ovl.fmt.RXY.dl2, 15418 ovl.fmt.RXY.dh2); goto ok; 15419 case 0xe30000000006ULL: s390_format_RXY_RRRD(s390_irgen_CVBY, ovl.fmt.RXY.r1, 15420 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15421 ovl.fmt.RXY.dl2, 15422 ovl.fmt.RXY.dh2); goto ok; 15423 case 0xe30000000008ULL: s390_format_RXY_RRRD(s390_irgen_AG, ovl.fmt.RXY.r1, 15424 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15425 ovl.fmt.RXY.dl2, 15426 ovl.fmt.RXY.dh2); goto ok; 15427 case 0xe30000000009ULL: s390_format_RXY_RRRD(s390_irgen_SG, ovl.fmt.RXY.r1, 15428 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15429 ovl.fmt.RXY.dl2, 15430 ovl.fmt.RXY.dh2); goto ok; 15431 case 0xe3000000000aULL: s390_format_RXY_RRRD(s390_irgen_ALG, ovl.fmt.RXY.r1, 15432 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15433 ovl.fmt.RXY.dl2, 15434 ovl.fmt.RXY.dh2); goto ok; 15435 case 0xe3000000000bULL: s390_format_RXY_RRRD(s390_irgen_SLG, ovl.fmt.RXY.r1, 15436 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15437 ovl.fmt.RXY.dl2, 15438 ovl.fmt.RXY.dh2); goto ok; 15439 case 0xe3000000000cULL: s390_format_RXY_RRRD(s390_irgen_MSG, ovl.fmt.RXY.r1, 15440 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15441 ovl.fmt.RXY.dl2, 15442 ovl.fmt.RXY.dh2); goto ok; 15443 case 0xe3000000000dULL: s390_format_RXY_RRRD(s390_irgen_DSG, ovl.fmt.RXY.r1, 15444 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15445 ovl.fmt.RXY.dl2, 15446 ovl.fmt.RXY.dh2); goto ok; 15447 case 0xe3000000000eULL: /* CVBG */ goto unimplemented; 15448 case 0xe3000000000fULL: s390_format_RXY_RRRD(s390_irgen_LRVG, ovl.fmt.RXY.r1, 15449 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15450 ovl.fmt.RXY.dl2, 15451 ovl.fmt.RXY.dh2); goto ok; 15452 case 0xe30000000012ULL: s390_format_RXY_RRRD(s390_irgen_LT, ovl.fmt.RXY.r1, 15453 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15454 ovl.fmt.RXY.dl2, 15455 ovl.fmt.RXY.dh2); goto ok; 15456 case 0xe30000000013ULL: /* LRAY */ goto unimplemented; 15457 case 0xe30000000014ULL: s390_format_RXY_RRRD(s390_irgen_LGF, ovl.fmt.RXY.r1, 15458 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15459 ovl.fmt.RXY.dl2, 15460 ovl.fmt.RXY.dh2); goto ok; 15461 case 0xe30000000015ULL: s390_format_RXY_RRRD(s390_irgen_LGH, ovl.fmt.RXY.r1, 15462 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15463 ovl.fmt.RXY.dl2, 15464 ovl.fmt.RXY.dh2); goto ok; 15465 case 0xe30000000016ULL: s390_format_RXY_RRRD(s390_irgen_LLGF, ovl.fmt.RXY.r1, 15466 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15467 ovl.fmt.RXY.dl2, 15468 ovl.fmt.RXY.dh2); goto ok; 15469 case 0xe30000000017ULL: s390_format_RXY_RRRD(s390_irgen_LLGT, ovl.fmt.RXY.r1, 15470 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15471 ovl.fmt.RXY.dl2, 15472 ovl.fmt.RXY.dh2); goto ok; 15473 case 0xe30000000018ULL: s390_format_RXY_RRRD(s390_irgen_AGF, ovl.fmt.RXY.r1, 15474 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15475 ovl.fmt.RXY.dl2, 15476 ovl.fmt.RXY.dh2); goto ok; 15477 case 0xe30000000019ULL: s390_format_RXY_RRRD(s390_irgen_SGF, ovl.fmt.RXY.r1, 15478 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15479 ovl.fmt.RXY.dl2, 15480 ovl.fmt.RXY.dh2); goto ok; 15481 case 0xe3000000001aULL: s390_format_RXY_RRRD(s390_irgen_ALGF, ovl.fmt.RXY.r1, 15482 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15483 ovl.fmt.RXY.dl2, 15484 ovl.fmt.RXY.dh2); goto ok; 15485 case 0xe3000000001bULL: s390_format_RXY_RRRD(s390_irgen_SLGF, ovl.fmt.RXY.r1, 15486 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15487 ovl.fmt.RXY.dl2, 15488 ovl.fmt.RXY.dh2); goto ok; 15489 case 0xe3000000001cULL: s390_format_RXY_RRRD(s390_irgen_MSGF, ovl.fmt.RXY.r1, 15490 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15491 ovl.fmt.RXY.dl2, 15492 ovl.fmt.RXY.dh2); goto ok; 15493 case 0xe3000000001dULL: s390_format_RXY_RRRD(s390_irgen_DSGF, ovl.fmt.RXY.r1, 15494 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15495 ovl.fmt.RXY.dl2, 15496 ovl.fmt.RXY.dh2); goto ok; 15497 case 0xe3000000001eULL: s390_format_RXY_RRRD(s390_irgen_LRV, ovl.fmt.RXY.r1, 15498 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15499 ovl.fmt.RXY.dl2, 15500 ovl.fmt.RXY.dh2); goto ok; 15501 case 0xe3000000001fULL: s390_format_RXY_RRRD(s390_irgen_LRVH, ovl.fmt.RXY.r1, 15502 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15503 ovl.fmt.RXY.dl2, 15504 ovl.fmt.RXY.dh2); goto ok; 15505 case 0xe30000000020ULL: s390_format_RXY_RRRD(s390_irgen_CG, ovl.fmt.RXY.r1, 15506 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15507 ovl.fmt.RXY.dl2, 15508 ovl.fmt.RXY.dh2); goto ok; 15509 case 0xe30000000021ULL: s390_format_RXY_RRRD(s390_irgen_CLG, ovl.fmt.RXY.r1, 15510 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15511 ovl.fmt.RXY.dl2, 15512 ovl.fmt.RXY.dh2); goto ok; 15513 case 0xe30000000024ULL: s390_format_RXY_RRRD(s390_irgen_STG, ovl.fmt.RXY.r1, 15514 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15515 ovl.fmt.RXY.dl2, 15516 ovl.fmt.RXY.dh2); goto ok; 15517 case 0xe30000000025ULL: /* NTSTG */ goto unimplemented; 15518 case 0xe30000000026ULL: s390_format_RXY_RRRD(s390_irgen_CVDY, ovl.fmt.RXY.r1, 15519 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15520 ovl.fmt.RXY.dl2, 15521 ovl.fmt.RXY.dh2); goto ok; 15522 case 0xe3000000002eULL: /* CVDG */ goto unimplemented; 15523 case 0xe3000000002fULL: s390_format_RXY_RRRD(s390_irgen_STRVG, 15524 ovl.fmt.RXY.r1, ovl.fmt.RXY.x2, 15525 ovl.fmt.RXY.b2, ovl.fmt.RXY.dl2, 15526 ovl.fmt.RXY.dh2); goto ok; 15527 case 0xe30000000030ULL: s390_format_RXY_RRRD(s390_irgen_CGF, ovl.fmt.RXY.r1, 15528 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15529 ovl.fmt.RXY.dl2, 15530 ovl.fmt.RXY.dh2); goto ok; 15531 case 0xe30000000031ULL: s390_format_RXY_RRRD(s390_irgen_CLGF, ovl.fmt.RXY.r1, 15532 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15533 ovl.fmt.RXY.dl2, 15534 ovl.fmt.RXY.dh2); goto ok; 15535 case 0xe30000000032ULL: s390_format_RXY_RRRD(s390_irgen_LTGF, ovl.fmt.RXY.r1, 15536 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15537 ovl.fmt.RXY.dl2, 15538 ovl.fmt.RXY.dh2); goto ok; 15539 case 0xe30000000034ULL: s390_format_RXY_RRRD(s390_irgen_CGH, ovl.fmt.RXY.r1, 15540 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15541 ovl.fmt.RXY.dl2, 15542 ovl.fmt.RXY.dh2); goto ok; 15543 case 0xe30000000036ULL: s390_format_RXY_URRD(s390_irgen_PFD, ovl.fmt.RXY.r1, 15544 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15545 ovl.fmt.RXY.dl2, 15546 ovl.fmt.RXY.dh2); goto ok; 15547 case 0xe3000000003eULL: s390_format_RXY_RRRD(s390_irgen_STRV, ovl.fmt.RXY.r1, 15548 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15549 ovl.fmt.RXY.dl2, 15550 ovl.fmt.RXY.dh2); goto ok; 15551 case 0xe3000000003fULL: s390_format_RXY_RRRD(s390_irgen_STRVH, 15552 ovl.fmt.RXY.r1, ovl.fmt.RXY.x2, 15553 ovl.fmt.RXY.b2, ovl.fmt.RXY.dl2, 15554 ovl.fmt.RXY.dh2); goto ok; 15555 case 0xe30000000046ULL: s390_format_RXY_RRRD(s390_irgen_BCTG, ovl.fmt.RXY.r1, 15556 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15557 ovl.fmt.RXY.dl2, 15558 ovl.fmt.RXY.dh2); goto ok; 15559 case 0xe30000000050ULL: s390_format_RXY_RRRD(s390_irgen_STY, ovl.fmt.RXY.r1, 15560 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15561 ovl.fmt.RXY.dl2, 15562 ovl.fmt.RXY.dh2); goto ok; 15563 case 0xe30000000051ULL: s390_format_RXY_RRRD(s390_irgen_MSY, ovl.fmt.RXY.r1, 15564 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15565 ovl.fmt.RXY.dl2, 15566 ovl.fmt.RXY.dh2); goto ok; 15567 case 0xe30000000054ULL: s390_format_RXY_RRRD(s390_irgen_NY, ovl.fmt.RXY.r1, 15568 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15569 ovl.fmt.RXY.dl2, 15570 ovl.fmt.RXY.dh2); goto ok; 15571 case 0xe30000000055ULL: s390_format_RXY_RRRD(s390_irgen_CLY, ovl.fmt.RXY.r1, 15572 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15573 ovl.fmt.RXY.dl2, 15574 ovl.fmt.RXY.dh2); goto ok; 15575 case 0xe30000000056ULL: s390_format_RXY_RRRD(s390_irgen_OY, ovl.fmt.RXY.r1, 15576 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15577 ovl.fmt.RXY.dl2, 15578 ovl.fmt.RXY.dh2); goto ok; 15579 case 0xe30000000057ULL: s390_format_RXY_RRRD(s390_irgen_XY, 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 0xe30000000058ULL: s390_format_RXY_RRRD(s390_irgen_LY, ovl.fmt.RXY.r1, 15584 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15585 ovl.fmt.RXY.dl2, 15586 ovl.fmt.RXY.dh2); goto ok; 15587 case 0xe30000000059ULL: s390_format_RXY_RRRD(s390_irgen_CY, ovl.fmt.RXY.r1, 15588 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15589 ovl.fmt.RXY.dl2, 15590 ovl.fmt.RXY.dh2); goto ok; 15591 case 0xe3000000005aULL: s390_format_RXY_RRRD(s390_irgen_AY, ovl.fmt.RXY.r1, 15592 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15593 ovl.fmt.RXY.dl2, 15594 ovl.fmt.RXY.dh2); goto ok; 15595 case 0xe3000000005bULL: s390_format_RXY_RRRD(s390_irgen_SY, ovl.fmt.RXY.r1, 15596 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15597 ovl.fmt.RXY.dl2, 15598 ovl.fmt.RXY.dh2); goto ok; 15599 case 0xe3000000005cULL: s390_format_RXY_RRRD(s390_irgen_MFY, ovl.fmt.RXY.r1, 15600 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15601 ovl.fmt.RXY.dl2, 15602 ovl.fmt.RXY.dh2); goto ok; 15603 case 0xe3000000005eULL: s390_format_RXY_RRRD(s390_irgen_ALY, ovl.fmt.RXY.r1, 15604 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15605 ovl.fmt.RXY.dl2, 15606 ovl.fmt.RXY.dh2); goto ok; 15607 case 0xe3000000005fULL: s390_format_RXY_RRRD(s390_irgen_SLY, ovl.fmt.RXY.r1, 15608 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15609 ovl.fmt.RXY.dl2, 15610 ovl.fmt.RXY.dh2); goto ok; 15611 case 0xe30000000070ULL: s390_format_RXY_RRRD(s390_irgen_STHY, ovl.fmt.RXY.r1, 15612 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15613 ovl.fmt.RXY.dl2, 15614 ovl.fmt.RXY.dh2); goto ok; 15615 case 0xe30000000071ULL: s390_format_RXY_RRRD(s390_irgen_LAY, ovl.fmt.RXY.r1, 15616 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15617 ovl.fmt.RXY.dl2, 15618 ovl.fmt.RXY.dh2); goto ok; 15619 case 0xe30000000072ULL: s390_format_RXY_RRRD(s390_irgen_STCY, ovl.fmt.RXY.r1, 15620 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15621 ovl.fmt.RXY.dl2, 15622 ovl.fmt.RXY.dh2); goto ok; 15623 case 0xe30000000073ULL: s390_format_RXY_RRRD(s390_irgen_ICY, ovl.fmt.RXY.r1, 15624 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15625 ovl.fmt.RXY.dl2, 15626 ovl.fmt.RXY.dh2); goto ok; 15627 case 0xe30000000075ULL: s390_format_RXY_RRRD(s390_irgen_LAEY, ovl.fmt.RXY.r1, 15628 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15629 ovl.fmt.RXY.dl2, 15630 ovl.fmt.RXY.dh2); goto ok; 15631 case 0xe30000000076ULL: s390_format_RXY_RRRD(s390_irgen_LB, ovl.fmt.RXY.r1, 15632 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15633 ovl.fmt.RXY.dl2, 15634 ovl.fmt.RXY.dh2); goto ok; 15635 case 0xe30000000077ULL: s390_format_RXY_RRRD(s390_irgen_LGB, ovl.fmt.RXY.r1, 15636 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15637 ovl.fmt.RXY.dl2, 15638 ovl.fmt.RXY.dh2); goto ok; 15639 case 0xe30000000078ULL: s390_format_RXY_RRRD(s390_irgen_LHY, ovl.fmt.RXY.r1, 15640 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15641 ovl.fmt.RXY.dl2, 15642 ovl.fmt.RXY.dh2); goto ok; 15643 case 0xe30000000079ULL: s390_format_RXY_RRRD(s390_irgen_CHY, ovl.fmt.RXY.r1, 15644 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15645 ovl.fmt.RXY.dl2, 15646 ovl.fmt.RXY.dh2); goto ok; 15647 case 0xe3000000007aULL: s390_format_RXY_RRRD(s390_irgen_AHY, ovl.fmt.RXY.r1, 15648 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15649 ovl.fmt.RXY.dl2, 15650 ovl.fmt.RXY.dh2); goto ok; 15651 case 0xe3000000007bULL: s390_format_RXY_RRRD(s390_irgen_SHY, ovl.fmt.RXY.r1, 15652 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15653 ovl.fmt.RXY.dl2, 15654 ovl.fmt.RXY.dh2); goto ok; 15655 case 0xe3000000007cULL: s390_format_RXY_RRRD(s390_irgen_MHY, ovl.fmt.RXY.r1, 15656 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15657 ovl.fmt.RXY.dl2, 15658 ovl.fmt.RXY.dh2); goto ok; 15659 case 0xe30000000080ULL: s390_format_RXY_RRRD(s390_irgen_NG, ovl.fmt.RXY.r1, 15660 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15661 ovl.fmt.RXY.dl2, 15662 ovl.fmt.RXY.dh2); goto ok; 15663 case 0xe30000000081ULL: s390_format_RXY_RRRD(s390_irgen_OG, ovl.fmt.RXY.r1, 15664 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15665 ovl.fmt.RXY.dl2, 15666 ovl.fmt.RXY.dh2); goto ok; 15667 case 0xe30000000082ULL: s390_format_RXY_RRRD(s390_irgen_XG, ovl.fmt.RXY.r1, 15668 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15669 ovl.fmt.RXY.dl2, 15670 ovl.fmt.RXY.dh2); goto ok; 15671 case 0xe30000000085ULL: /* LGAT */ goto unimplemented; 15672 case 0xe30000000086ULL: s390_format_RXY_RRRD(s390_irgen_MLG, ovl.fmt.RXY.r1, 15673 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15674 ovl.fmt.RXY.dl2, 15675 ovl.fmt.RXY.dh2); goto ok; 15676 case 0xe30000000087ULL: s390_format_RXY_RRRD(s390_irgen_DLG, ovl.fmt.RXY.r1, 15677 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15678 ovl.fmt.RXY.dl2, 15679 ovl.fmt.RXY.dh2); goto ok; 15680 case 0xe30000000088ULL: s390_format_RXY_RRRD(s390_irgen_ALCG, ovl.fmt.RXY.r1, 15681 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15682 ovl.fmt.RXY.dl2, 15683 ovl.fmt.RXY.dh2); goto ok; 15684 case 0xe30000000089ULL: s390_format_RXY_RRRD(s390_irgen_SLBG, ovl.fmt.RXY.r1, 15685 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15686 ovl.fmt.RXY.dl2, 15687 ovl.fmt.RXY.dh2); goto ok; 15688 case 0xe3000000008eULL: s390_format_RXY_RRRD(s390_irgen_STPQ, ovl.fmt.RXY.r1, 15689 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15690 ovl.fmt.RXY.dl2, 15691 ovl.fmt.RXY.dh2); goto ok; 15692 case 0xe3000000008fULL: s390_format_RXY_RRRD(s390_irgen_LPQ, ovl.fmt.RXY.r1, 15693 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15694 ovl.fmt.RXY.dl2, 15695 ovl.fmt.RXY.dh2); goto ok; 15696 case 0xe30000000090ULL: s390_format_RXY_RRRD(s390_irgen_LLGC, 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 0xe30000000091ULL: s390_format_RXY_RRRD(s390_irgen_LLGH, 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 0xe30000000094ULL: s390_format_RXY_RRRD(s390_irgen_LLC, 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 0xe30000000095ULL: s390_format_RXY_RRRD(s390_irgen_LLH, 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 0xe30000000096ULL: s390_format_RXY_RRRD(s390_irgen_ML, 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 0xe30000000097ULL: s390_format_RXY_RRRD(s390_irgen_DL, 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 0xe30000000098ULL: s390_format_RXY_RRRD(s390_irgen_ALC, ovl.fmt.RXY.r1, 15721 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15722 ovl.fmt.RXY.dl2, 15723 ovl.fmt.RXY.dh2); goto ok; 15724 case 0xe30000000099ULL: s390_format_RXY_RRRD(s390_irgen_SLB, 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 0xe3000000009cULL: /* LLGTAT */ goto unimplemented; 15729 case 0xe3000000009dULL: /* LLGFAT */ goto unimplemented; 15730 case 0xe3000000009fULL: /* LAT */ goto unimplemented; 15731 case 0xe300000000c0ULL: s390_format_RXY_RRRD(s390_irgen_LBH, ovl.fmt.RXY.r1, 15732 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15733 ovl.fmt.RXY.dl2, 15734 ovl.fmt.RXY.dh2); goto ok; 15735 case 0xe300000000c2ULL: s390_format_RXY_RRRD(s390_irgen_LLCH, ovl.fmt.RXY.r1, 15736 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15737 ovl.fmt.RXY.dl2, 15738 ovl.fmt.RXY.dh2); goto ok; 15739 case 0xe300000000c3ULL: s390_format_RXY_RRRD(s390_irgen_STCH, ovl.fmt.RXY.r1, 15740 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15741 ovl.fmt.RXY.dl2, 15742 ovl.fmt.RXY.dh2); goto ok; 15743 case 0xe300000000c4ULL: s390_format_RXY_RRRD(s390_irgen_LHH, ovl.fmt.RXY.r1, 15744 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15745 ovl.fmt.RXY.dl2, 15746 ovl.fmt.RXY.dh2); goto ok; 15747 case 0xe300000000c6ULL: s390_format_RXY_RRRD(s390_irgen_LLHH, ovl.fmt.RXY.r1, 15748 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15749 ovl.fmt.RXY.dl2, 15750 ovl.fmt.RXY.dh2); goto ok; 15751 case 0xe300000000c7ULL: s390_format_RXY_RRRD(s390_irgen_STHH, ovl.fmt.RXY.r1, 15752 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 15753 ovl.fmt.RXY.dl2, 15754 ovl.fmt.RXY.dh2); goto ok; 15755 case 0xe300000000c8ULL: /* LFHAT */ goto unimplemented; 15756 case 0xe300000000caULL: s390_format_RXY_RRRD(s390_irgen_LFH, 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 0xe300000000cbULL: s390_format_RXY_RRRD(s390_irgen_STFH, 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 0xe300000000cdULL: s390_format_RXY_RRRD(s390_irgen_CHF, 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 0xe300000000cfULL: s390_format_RXY_RRRD(s390_irgen_CLHF, 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 0xeb0000000004ULL: s390_format_RSY_RRRD(s390_irgen_LMG, ovl.fmt.RSY.r1, 15773 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15774 ovl.fmt.RSY.dl2, 15775 ovl.fmt.RSY.dh2); goto ok; 15776 case 0xeb000000000aULL: s390_format_RSY_RRRD(s390_irgen_SRAG, ovl.fmt.RSY.r1, 15777 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15778 ovl.fmt.RSY.dl2, 15779 ovl.fmt.RSY.dh2); goto ok; 15780 case 0xeb000000000bULL: s390_format_RSY_RRRD(s390_irgen_SLAG, ovl.fmt.RSY.r1, 15781 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15782 ovl.fmt.RSY.dl2, 15783 ovl.fmt.RSY.dh2); goto ok; 15784 case 0xeb000000000cULL: s390_format_RSY_RRRD(s390_irgen_SRLG, ovl.fmt.RSY.r1, 15785 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15786 ovl.fmt.RSY.dl2, 15787 ovl.fmt.RSY.dh2); goto ok; 15788 case 0xeb000000000dULL: s390_format_RSY_RRRD(s390_irgen_SLLG, ovl.fmt.RSY.r1, 15789 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15790 ovl.fmt.RSY.dl2, 15791 ovl.fmt.RSY.dh2); goto ok; 15792 case 0xeb000000000fULL: /* TRACG */ goto unimplemented; 15793 case 0xeb0000000014ULL: s390_format_RSY_RRRD(s390_irgen_CSY, ovl.fmt.RSY.r1, 15794 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15795 ovl.fmt.RSY.dl2, 15796 ovl.fmt.RSY.dh2); goto ok; 15797 case 0xeb000000001cULL: s390_format_RSY_RRRD(s390_irgen_RLLG, ovl.fmt.RSY.r1, 15798 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15799 ovl.fmt.RSY.dl2, 15800 ovl.fmt.RSY.dh2); goto ok; 15801 case 0xeb000000001dULL: s390_format_RSY_RRRD(s390_irgen_RLL, ovl.fmt.RSY.r1, 15802 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15803 ovl.fmt.RSY.dl2, 15804 ovl.fmt.RSY.dh2); goto ok; 15805 case 0xeb0000000020ULL: s390_format_RSY_RURD(s390_irgen_CLMH, ovl.fmt.RSY.r1, 15806 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15807 ovl.fmt.RSY.dl2, 15808 ovl.fmt.RSY.dh2); goto ok; 15809 case 0xeb0000000021ULL: s390_format_RSY_RURD(s390_irgen_CLMY, ovl.fmt.RSY.r1, 15810 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15811 ovl.fmt.RSY.dl2, 15812 ovl.fmt.RSY.dh2); goto ok; 15813 case 0xeb0000000023ULL: /* CLT */ goto unimplemented; 15814 case 0xeb0000000024ULL: s390_format_RSY_RRRD(s390_irgen_STMG, ovl.fmt.RSY.r1, 15815 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15816 ovl.fmt.RSY.dl2, 15817 ovl.fmt.RSY.dh2); goto ok; 15818 case 0xeb0000000025ULL: /* STCTG */ goto unimplemented; 15819 case 0xeb0000000026ULL: s390_format_RSY_RRRD(s390_irgen_STMH, ovl.fmt.RSY.r1, 15820 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15821 ovl.fmt.RSY.dl2, 15822 ovl.fmt.RSY.dh2); goto ok; 15823 case 0xeb000000002bULL: /* CLGT */ goto unimplemented; 15824 case 0xeb000000002cULL: s390_format_RSY_RURD(s390_irgen_STCMH, 15825 ovl.fmt.RSY.r1, ovl.fmt.RSY.r3, 15826 ovl.fmt.RSY.b2, ovl.fmt.RSY.dl2, 15827 ovl.fmt.RSY.dh2); goto ok; 15828 case 0xeb000000002dULL: s390_format_RSY_RURD(s390_irgen_STCMY, 15829 ovl.fmt.RSY.r1, ovl.fmt.RSY.r3, 15830 ovl.fmt.RSY.b2, ovl.fmt.RSY.dl2, 15831 ovl.fmt.RSY.dh2); goto ok; 15832 case 0xeb000000002fULL: /* LCTLG */ goto unimplemented; 15833 case 0xeb0000000030ULL: s390_format_RSY_RRRD(s390_irgen_CSG, ovl.fmt.RSY.r1, 15834 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15835 ovl.fmt.RSY.dl2, 15836 ovl.fmt.RSY.dh2); goto ok; 15837 case 0xeb0000000031ULL: s390_format_RSY_RRRD(s390_irgen_CDSY, ovl.fmt.RSY.r1, 15838 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15839 ovl.fmt.RSY.dl2, 15840 ovl.fmt.RSY.dh2); goto ok; 15841 case 0xeb000000003eULL: s390_format_RSY_RRRD(s390_irgen_CDSG, ovl.fmt.RSY.r1, 15842 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15843 ovl.fmt.RSY.dl2, 15844 ovl.fmt.RSY.dh2); goto ok; 15845 case 0xeb0000000044ULL: s390_format_RSY_RRRD(s390_irgen_BXHG, ovl.fmt.RSY.r1, 15846 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15847 ovl.fmt.RSY.dl2, 15848 ovl.fmt.RSY.dh2); goto ok; 15849 case 0xeb0000000045ULL: s390_format_RSY_RRRD(s390_irgen_BXLEG, 15850 ovl.fmt.RSY.r1, ovl.fmt.RSY.r3, 15851 ovl.fmt.RSY.b2, ovl.fmt.RSY.dl2, 15852 ovl.fmt.RSY.dh2); goto ok; 15853 case 0xeb000000004cULL: s390_format_RSY_RRRD(s390_irgen_ECAG, ovl.fmt.RSY.r1, 15854 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15855 ovl.fmt.RSY.dl2, 15856 ovl.fmt.RSY.dh2); goto ok; 15857 case 0xeb0000000051ULL: s390_format_SIY_URD(s390_irgen_TMY, ovl.fmt.SIY.i2, 15858 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 15859 ovl.fmt.SIY.dh1); goto ok; 15860 case 0xeb0000000052ULL: s390_format_SIY_URD(s390_irgen_MVIY, ovl.fmt.SIY.i2, 15861 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 15862 ovl.fmt.SIY.dh1); goto ok; 15863 case 0xeb0000000054ULL: s390_format_SIY_URD(s390_irgen_NIY, ovl.fmt.SIY.i2, 15864 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 15865 ovl.fmt.SIY.dh1); goto ok; 15866 case 0xeb0000000055ULL: s390_format_SIY_URD(s390_irgen_CLIY, ovl.fmt.SIY.i2, 15867 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 15868 ovl.fmt.SIY.dh1); goto ok; 15869 case 0xeb0000000056ULL: s390_format_SIY_URD(s390_irgen_OIY, ovl.fmt.SIY.i2, 15870 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 15871 ovl.fmt.SIY.dh1); goto ok; 15872 case 0xeb0000000057ULL: s390_format_SIY_URD(s390_irgen_XIY, ovl.fmt.SIY.i2, 15873 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 15874 ovl.fmt.SIY.dh1); goto ok; 15875 case 0xeb000000006aULL: s390_format_SIY_IRD(s390_irgen_ASI, ovl.fmt.SIY.i2, 15876 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 15877 ovl.fmt.SIY.dh1); goto ok; 15878 case 0xeb000000006eULL: s390_format_SIY_IRD(s390_irgen_ALSI, ovl.fmt.SIY.i2, 15879 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 15880 ovl.fmt.SIY.dh1); goto ok; 15881 case 0xeb000000007aULL: s390_format_SIY_IRD(s390_irgen_AGSI, ovl.fmt.SIY.i2, 15882 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 15883 ovl.fmt.SIY.dh1); goto ok; 15884 case 0xeb000000007eULL: s390_format_SIY_IRD(s390_irgen_ALGSI, ovl.fmt.SIY.i2, 15885 ovl.fmt.SIY.b1, ovl.fmt.SIY.dl1, 15886 ovl.fmt.SIY.dh1); goto ok; 15887 case 0xeb0000000080ULL: s390_format_RSY_RURD(s390_irgen_ICMH, ovl.fmt.RSY.r1, 15888 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15889 ovl.fmt.RSY.dl2, 15890 ovl.fmt.RSY.dh2); goto ok; 15891 case 0xeb0000000081ULL: s390_format_RSY_RURD(s390_irgen_ICMY, ovl.fmt.RSY.r1, 15892 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15893 ovl.fmt.RSY.dl2, 15894 ovl.fmt.RSY.dh2); goto ok; 15895 case 0xeb000000008eULL: /* MVCLU */ goto unimplemented; 15896 case 0xeb000000008fULL: /* CLCLU */ goto unimplemented; 15897 case 0xeb0000000090ULL: s390_format_RSY_RRRD(s390_irgen_STMY, ovl.fmt.RSY.r1, 15898 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15899 ovl.fmt.RSY.dl2, 15900 ovl.fmt.RSY.dh2); goto ok; 15901 case 0xeb0000000096ULL: s390_format_RSY_RRRD(s390_irgen_LMH, ovl.fmt.RSY.r1, 15902 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15903 ovl.fmt.RSY.dl2, 15904 ovl.fmt.RSY.dh2); goto ok; 15905 case 0xeb0000000098ULL: s390_format_RSY_RRRD(s390_irgen_LMY, ovl.fmt.RSY.r1, 15906 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15907 ovl.fmt.RSY.dl2, 15908 ovl.fmt.RSY.dh2); goto ok; 15909 case 0xeb000000009aULL: s390_format_RSY_AARD(s390_irgen_LAMY, ovl.fmt.RSY.r1, 15910 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15911 ovl.fmt.RSY.dl2, 15912 ovl.fmt.RSY.dh2); goto ok; 15913 case 0xeb000000009bULL: s390_format_RSY_AARD(s390_irgen_STAMY, 15914 ovl.fmt.RSY.r1, ovl.fmt.RSY.r3, 15915 ovl.fmt.RSY.b2, ovl.fmt.RSY.dl2, 15916 ovl.fmt.RSY.dh2); goto ok; 15917 case 0xeb00000000c0ULL: /* TP */ goto unimplemented; 15918 case 0xeb00000000dcULL: s390_format_RSY_RRRD(s390_irgen_SRAK, ovl.fmt.RSY.r1, 15919 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15920 ovl.fmt.RSY.dl2, 15921 ovl.fmt.RSY.dh2); goto ok; 15922 case 0xeb00000000ddULL: s390_format_RSY_RRRD(s390_irgen_SLAK, ovl.fmt.RSY.r1, 15923 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15924 ovl.fmt.RSY.dl2, 15925 ovl.fmt.RSY.dh2); goto ok; 15926 case 0xeb00000000deULL: s390_format_RSY_RRRD(s390_irgen_SRLK, ovl.fmt.RSY.r1, 15927 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15928 ovl.fmt.RSY.dl2, 15929 ovl.fmt.RSY.dh2); goto ok; 15930 case 0xeb00000000dfULL: s390_format_RSY_RRRD(s390_irgen_SLLK, ovl.fmt.RSY.r1, 15931 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15932 ovl.fmt.RSY.dl2, 15933 ovl.fmt.RSY.dh2); goto ok; 15934 case 0xeb00000000e2ULL: s390_format_RSY_RDRM(s390_irgen_LOCG, ovl.fmt.RSY.r1, 15935 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15936 ovl.fmt.RSY.dl2, 15937 ovl.fmt.RSY.dh2, 15938 S390_XMNM_LOCG); goto ok; 15939 case 0xeb00000000e3ULL: s390_format_RSY_RDRM(s390_irgen_STOCG, 15940 ovl.fmt.RSY.r1, ovl.fmt.RSY.r3, 15941 ovl.fmt.RSY.b2, ovl.fmt.RSY.dl2, 15942 ovl.fmt.RSY.dh2, 15943 S390_XMNM_STOCG); goto ok; 15944 case 0xeb00000000e4ULL: s390_format_RSY_RRRD(s390_irgen_LANG, ovl.fmt.RSY.r1, 15945 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15946 ovl.fmt.RSY.dl2, 15947 ovl.fmt.RSY.dh2); goto ok; 15948 case 0xeb00000000e6ULL: s390_format_RSY_RRRD(s390_irgen_LAOG, ovl.fmt.RSY.r1, 15949 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15950 ovl.fmt.RSY.dl2, 15951 ovl.fmt.RSY.dh2); goto ok; 15952 case 0xeb00000000e7ULL: s390_format_RSY_RRRD(s390_irgen_LAXG, ovl.fmt.RSY.r1, 15953 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15954 ovl.fmt.RSY.dl2, 15955 ovl.fmt.RSY.dh2); goto ok; 15956 case 0xeb00000000e8ULL: s390_format_RSY_RRRD(s390_irgen_LAAG, ovl.fmt.RSY.r1, 15957 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15958 ovl.fmt.RSY.dl2, 15959 ovl.fmt.RSY.dh2); goto ok; 15960 case 0xeb00000000eaULL: s390_format_RSY_RRRD(s390_irgen_LAALG, 15961 ovl.fmt.RSY.r1, ovl.fmt.RSY.r3, 15962 ovl.fmt.RSY.b2, ovl.fmt.RSY.dl2, 15963 ovl.fmt.RSY.dh2); goto ok; 15964 case 0xeb00000000f2ULL: s390_format_RSY_RDRM(s390_irgen_LOC, ovl.fmt.RSY.r1, 15965 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15966 ovl.fmt.RSY.dl2, 15967 ovl.fmt.RSY.dh2, S390_XMNM_LOC); 15968 goto ok; 15969 case 0xeb00000000f3ULL: s390_format_RSY_RDRM(s390_irgen_STOC, ovl.fmt.RSY.r1, 15970 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15971 ovl.fmt.RSY.dl2, 15972 ovl.fmt.RSY.dh2, 15973 S390_XMNM_STOC); goto ok; 15974 case 0xeb00000000f4ULL: s390_format_RSY_RRRD(s390_irgen_LAN, 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 0xeb00000000f6ULL: s390_format_RSY_RRRD(s390_irgen_LAO, 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 0xeb00000000f7ULL: s390_format_RSY_RRRD(s390_irgen_LAX, ovl.fmt.RSY.r1, 15983 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15984 ovl.fmt.RSY.dl2, 15985 ovl.fmt.RSY.dh2); goto ok; 15986 case 0xeb00000000f8ULL: s390_format_RSY_RRRD(s390_irgen_LAA, ovl.fmt.RSY.r1, 15987 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15988 ovl.fmt.RSY.dl2, 15989 ovl.fmt.RSY.dh2); goto ok; 15990 case 0xeb00000000faULL: s390_format_RSY_RRRD(s390_irgen_LAAL, ovl.fmt.RSY.r1, 15991 ovl.fmt.RSY.r3, ovl.fmt.RSY.b2, 15992 ovl.fmt.RSY.dl2, 15993 ovl.fmt.RSY.dh2); goto ok; 15994 case 0xec0000000044ULL: s390_format_RIE_RRP(s390_irgen_BRXHG, ovl.fmt.RIE.r1, 15995 ovl.fmt.RIE.r3, ovl.fmt.RIE.i2); 15996 goto ok; 15997 case 0xec0000000045ULL: s390_format_RIE_RRP(s390_irgen_BRXLG, ovl.fmt.RIE.r1, 15998 ovl.fmt.RIE.r3, ovl.fmt.RIE.i2); 15999 goto ok; 16000 case 0xec0000000051ULL: /* RISBLG */ goto unimplemented; 16001 case 0xec0000000054ULL: s390_format_RIE_RRUUU(s390_irgen_RNSBG, 16002 ovl.fmt.RIE_RRUUU.r1, 16003 ovl.fmt.RIE_RRUUU.r2, 16004 ovl.fmt.RIE_RRUUU.i3, 16005 ovl.fmt.RIE_RRUUU.i4, 16006 ovl.fmt.RIE_RRUUU.i5); 16007 goto ok; 16008 case 0xec0000000055ULL: s390_format_RIE_RRUUU(s390_irgen_RISBG, 16009 ovl.fmt.RIE_RRUUU.r1, 16010 ovl.fmt.RIE_RRUUU.r2, 16011 ovl.fmt.RIE_RRUUU.i3, 16012 ovl.fmt.RIE_RRUUU.i4, 16013 ovl.fmt.RIE_RRUUU.i5); 16014 goto ok; 16015 case 0xec0000000056ULL: s390_format_RIE_RRUUU(s390_irgen_ROSBG, 16016 ovl.fmt.RIE_RRUUU.r1, 16017 ovl.fmt.RIE_RRUUU.r2, 16018 ovl.fmt.RIE_RRUUU.i3, 16019 ovl.fmt.RIE_RRUUU.i4, 16020 ovl.fmt.RIE_RRUUU.i5); 16021 goto ok; 16022 case 0xec0000000057ULL: s390_format_RIE_RRUUU(s390_irgen_RXSBG, 16023 ovl.fmt.RIE_RRUUU.r1, 16024 ovl.fmt.RIE_RRUUU.r2, 16025 ovl.fmt.RIE_RRUUU.i3, 16026 ovl.fmt.RIE_RRUUU.i4, 16027 ovl.fmt.RIE_RRUUU.i5); 16028 goto ok; 16029 case 0xec0000000059ULL: /* RISBGN */ goto unimplemented; 16030 case 0xec000000005dULL: /* RISBHG */ goto unimplemented; 16031 case 0xec0000000064ULL: s390_format_RIE_RRPU(s390_irgen_CGRJ, 16032 ovl.fmt.RIE_RRPU.r1, 16033 ovl.fmt.RIE_RRPU.r2, 16034 ovl.fmt.RIE_RRPU.i4, 16035 ovl.fmt.RIE_RRPU.m3); goto ok; 16036 case 0xec0000000065ULL: s390_format_RIE_RRPU(s390_irgen_CLGRJ, 16037 ovl.fmt.RIE_RRPU.r1, 16038 ovl.fmt.RIE_RRPU.r2, 16039 ovl.fmt.RIE_RRPU.i4, 16040 ovl.fmt.RIE_RRPU.m3); goto ok; 16041 case 0xec0000000070ULL: /* CGIT */ goto unimplemented; 16042 case 0xec0000000071ULL: /* CLGIT */ goto unimplemented; 16043 case 0xec0000000072ULL: /* CIT */ goto unimplemented; 16044 case 0xec0000000073ULL: /* CLFIT */ goto unimplemented; 16045 case 0xec0000000076ULL: s390_format_RIE_RRPU(s390_irgen_CRJ, 16046 ovl.fmt.RIE_RRPU.r1, 16047 ovl.fmt.RIE_RRPU.r2, 16048 ovl.fmt.RIE_RRPU.i4, 16049 ovl.fmt.RIE_RRPU.m3); goto ok; 16050 case 0xec0000000077ULL: s390_format_RIE_RRPU(s390_irgen_CLRJ, 16051 ovl.fmt.RIE_RRPU.r1, 16052 ovl.fmt.RIE_RRPU.r2, 16053 ovl.fmt.RIE_RRPU.i4, 16054 ovl.fmt.RIE_RRPU.m3); goto ok; 16055 case 0xec000000007cULL: s390_format_RIE_RUPI(s390_irgen_CGIJ, 16056 ovl.fmt.RIEv3.r1, 16057 ovl.fmt.RIEv3.m3, 16058 ovl.fmt.RIEv3.i4, 16059 ovl.fmt.RIEv3.i2); goto ok; 16060 case 0xec000000007dULL: s390_format_RIE_RUPU(s390_irgen_CLGIJ, 16061 ovl.fmt.RIEv3.r1, 16062 ovl.fmt.RIEv3.m3, 16063 ovl.fmt.RIEv3.i4, 16064 ovl.fmt.RIEv3.i2); goto ok; 16065 case 0xec000000007eULL: s390_format_RIE_RUPI(s390_irgen_CIJ, 16066 ovl.fmt.RIEv3.r1, 16067 ovl.fmt.RIEv3.m3, 16068 ovl.fmt.RIEv3.i4, 16069 ovl.fmt.RIEv3.i2); goto ok; 16070 case 0xec000000007fULL: s390_format_RIE_RUPU(s390_irgen_CLIJ, 16071 ovl.fmt.RIEv3.r1, 16072 ovl.fmt.RIEv3.m3, 16073 ovl.fmt.RIEv3.i4, 16074 ovl.fmt.RIEv3.i2); goto ok; 16075 case 0xec00000000d8ULL: s390_format_RIE_RRI0(s390_irgen_AHIK, ovl.fmt.RIE.r1, 16076 ovl.fmt.RIE.r3, ovl.fmt.RIE.i2); 16077 goto ok; 16078 case 0xec00000000d9ULL: s390_format_RIE_RRI0(s390_irgen_AGHIK, 16079 ovl.fmt.RIE.r1, ovl.fmt.RIE.r3, 16080 ovl.fmt.RIE.i2); goto ok; 16081 case 0xec00000000daULL: s390_format_RIE_RRI0(s390_irgen_ALHSIK, 16082 ovl.fmt.RIE.r1, ovl.fmt.RIE.r3, 16083 ovl.fmt.RIE.i2); goto ok; 16084 case 0xec00000000dbULL: s390_format_RIE_RRI0(s390_irgen_ALGHSIK, 16085 ovl.fmt.RIE.r1, ovl.fmt.RIE.r3, 16086 ovl.fmt.RIE.i2); goto ok; 16087 case 0xec00000000e4ULL: s390_format_RRS(s390_irgen_CGRB, ovl.fmt.RRS.r1, 16088 ovl.fmt.RRS.r2, ovl.fmt.RRS.b4, 16089 ovl.fmt.RRS.d4, ovl.fmt.RRS.m3); 16090 goto ok; 16091 case 0xec00000000e5ULL: s390_format_RRS(s390_irgen_CLGRB, ovl.fmt.RRS.r1, 16092 ovl.fmt.RRS.r2, ovl.fmt.RRS.b4, 16093 ovl.fmt.RRS.d4, ovl.fmt.RRS.m3); 16094 goto ok; 16095 case 0xec00000000f6ULL: s390_format_RRS(s390_irgen_CRB, ovl.fmt.RRS.r1, 16096 ovl.fmt.RRS.r2, ovl.fmt.RRS.b4, 16097 ovl.fmt.RRS.d4, ovl.fmt.RRS.m3); 16098 goto ok; 16099 case 0xec00000000f7ULL: s390_format_RRS(s390_irgen_CLRB, ovl.fmt.RRS.r1, 16100 ovl.fmt.RRS.r2, ovl.fmt.RRS.b4, 16101 ovl.fmt.RRS.d4, ovl.fmt.RRS.m3); 16102 goto ok; 16103 case 0xec00000000fcULL: s390_format_RIS_RURDI(s390_irgen_CGIB, 16104 ovl.fmt.RIS.r1, ovl.fmt.RIS.m3, 16105 ovl.fmt.RIS.b4, ovl.fmt.RIS.d4, 16106 ovl.fmt.RIS.i2); goto ok; 16107 case 0xec00000000fdULL: s390_format_RIS_RURDU(s390_irgen_CLGIB, 16108 ovl.fmt.RIS.r1, ovl.fmt.RIS.m3, 16109 ovl.fmt.RIS.b4, ovl.fmt.RIS.d4, 16110 ovl.fmt.RIS.i2); goto ok; 16111 case 0xec00000000feULL: s390_format_RIS_RURDI(s390_irgen_CIB, ovl.fmt.RIS.r1, 16112 ovl.fmt.RIS.m3, ovl.fmt.RIS.b4, 16113 ovl.fmt.RIS.d4, 16114 ovl.fmt.RIS.i2); goto ok; 16115 case 0xec00000000ffULL: s390_format_RIS_RURDU(s390_irgen_CLIB, 16116 ovl.fmt.RIS.r1, ovl.fmt.RIS.m3, 16117 ovl.fmt.RIS.b4, ovl.fmt.RIS.d4, 16118 ovl.fmt.RIS.i2); goto ok; 16119 case 0xed0000000004ULL: s390_format_RXE_FRRD(s390_irgen_LDEB, ovl.fmt.RXE.r1, 16120 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16121 ovl.fmt.RXE.d2); goto ok; 16122 case 0xed0000000005ULL: s390_format_RXE_FRRD(s390_irgen_LXDB, ovl.fmt.RXE.r1, 16123 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16124 ovl.fmt.RXE.d2); goto ok; 16125 case 0xed0000000006ULL: s390_format_RXE_FRRD(s390_irgen_LXEB, ovl.fmt.RXE.r1, 16126 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16127 ovl.fmt.RXE.d2); goto ok; 16128 case 0xed0000000007ULL: /* MXDB */ goto unimplemented; 16129 case 0xed0000000008ULL: /* KEB */ goto unimplemented; 16130 case 0xed0000000009ULL: s390_format_RXE_FRRD(s390_irgen_CEB, ovl.fmt.RXE.r1, 16131 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16132 ovl.fmt.RXE.d2); goto ok; 16133 case 0xed000000000aULL: s390_format_RXE_FRRD(s390_irgen_AEB, ovl.fmt.RXE.r1, 16134 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16135 ovl.fmt.RXE.d2); goto ok; 16136 case 0xed000000000bULL: s390_format_RXE_FRRD(s390_irgen_SEB, ovl.fmt.RXE.r1, 16137 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16138 ovl.fmt.RXE.d2); goto ok; 16139 case 0xed000000000cULL: /* MDEB */ goto unimplemented; 16140 case 0xed000000000dULL: s390_format_RXE_FRRD(s390_irgen_DEB, ovl.fmt.RXE.r1, 16141 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16142 ovl.fmt.RXE.d2); goto ok; 16143 case 0xed000000000eULL: s390_format_RXF_FRRDF(s390_irgen_MAEB, 16144 ovl.fmt.RXF.r3, ovl.fmt.RXF.x2, 16145 ovl.fmt.RXF.b2, ovl.fmt.RXF.d2, 16146 ovl.fmt.RXF.r1); goto ok; 16147 case 0xed000000000fULL: s390_format_RXF_FRRDF(s390_irgen_MSEB, 16148 ovl.fmt.RXF.r3, ovl.fmt.RXF.x2, 16149 ovl.fmt.RXF.b2, ovl.fmt.RXF.d2, 16150 ovl.fmt.RXF.r1); goto ok; 16151 case 0xed0000000010ULL: s390_format_RXE_FRRD(s390_irgen_TCEB, ovl.fmt.RXE.r1, 16152 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16153 ovl.fmt.RXE.d2); goto ok; 16154 case 0xed0000000011ULL: s390_format_RXE_FRRD(s390_irgen_TCDB, ovl.fmt.RXE.r1, 16155 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16156 ovl.fmt.RXE.d2); goto ok; 16157 case 0xed0000000012ULL: s390_format_RXE_FRRD(s390_irgen_TCXB, ovl.fmt.RXE.r1, 16158 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16159 ovl.fmt.RXE.d2); goto ok; 16160 case 0xed0000000014ULL: s390_format_RXE_FRRD(s390_irgen_SQEB, ovl.fmt.RXE.r1, 16161 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16162 ovl.fmt.RXE.d2); goto ok; 16163 case 0xed0000000015ULL: s390_format_RXE_FRRD(s390_irgen_SQDB, ovl.fmt.RXE.r1, 16164 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16165 ovl.fmt.RXE.d2); goto ok; 16166 case 0xed0000000017ULL: s390_format_RXE_FRRD(s390_irgen_MEEB, ovl.fmt.RXE.r1, 16167 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16168 ovl.fmt.RXE.d2); goto ok; 16169 case 0xed0000000018ULL: /* KDB */ goto unimplemented; 16170 case 0xed0000000019ULL: s390_format_RXE_FRRD(s390_irgen_CDB, ovl.fmt.RXE.r1, 16171 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16172 ovl.fmt.RXE.d2); goto ok; 16173 case 0xed000000001aULL: s390_format_RXE_FRRD(s390_irgen_ADB, ovl.fmt.RXE.r1, 16174 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16175 ovl.fmt.RXE.d2); goto ok; 16176 case 0xed000000001bULL: s390_format_RXE_FRRD(s390_irgen_SDB, ovl.fmt.RXE.r1, 16177 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16178 ovl.fmt.RXE.d2); goto ok; 16179 case 0xed000000001cULL: s390_format_RXE_FRRD(s390_irgen_MDB, ovl.fmt.RXE.r1, 16180 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16181 ovl.fmt.RXE.d2); goto ok; 16182 case 0xed000000001dULL: s390_format_RXE_FRRD(s390_irgen_DDB, ovl.fmt.RXE.r1, 16183 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16184 ovl.fmt.RXE.d2); goto ok; 16185 case 0xed000000001eULL: s390_format_RXF_FRRDF(s390_irgen_MADB, 16186 ovl.fmt.RXF.r3, ovl.fmt.RXF.x2, 16187 ovl.fmt.RXF.b2, ovl.fmt.RXF.d2, 16188 ovl.fmt.RXF.r1); goto ok; 16189 case 0xed000000001fULL: s390_format_RXF_FRRDF(s390_irgen_MSDB, 16190 ovl.fmt.RXF.r3, ovl.fmt.RXF.x2, 16191 ovl.fmt.RXF.b2, ovl.fmt.RXF.d2, 16192 ovl.fmt.RXF.r1); goto ok; 16193 case 0xed0000000024ULL: /* LDE */ goto unimplemented; 16194 case 0xed0000000025ULL: /* LXD */ goto unimplemented; 16195 case 0xed0000000026ULL: /* LXE */ goto unimplemented; 16196 case 0xed000000002eULL: /* MAE */ goto unimplemented; 16197 case 0xed000000002fULL: /* MSE */ goto unimplemented; 16198 case 0xed0000000034ULL: /* SQE */ goto unimplemented; 16199 case 0xed0000000035ULL: /* SQD */ goto unimplemented; 16200 case 0xed0000000037ULL: /* MEE */ goto unimplemented; 16201 case 0xed0000000038ULL: /* MAYL */ goto unimplemented; 16202 case 0xed0000000039ULL: /* MYL */ goto unimplemented; 16203 case 0xed000000003aULL: /* MAY */ goto unimplemented; 16204 case 0xed000000003bULL: /* MY */ goto unimplemented; 16205 case 0xed000000003cULL: /* MAYH */ goto unimplemented; 16206 case 0xed000000003dULL: /* MYH */ goto unimplemented; 16207 case 0xed000000003eULL: /* MAD */ goto unimplemented; 16208 case 0xed000000003fULL: /* MSD */ goto unimplemented; 16209 case 0xed0000000040ULL: s390_format_RXF_FRRDF(s390_irgen_SLDT, 16210 ovl.fmt.RXF.r3, ovl.fmt.RXF.x2, 16211 ovl.fmt.RXF.b2, ovl.fmt.RXF.d2, 16212 ovl.fmt.RXF.r1); goto ok; 16213 case 0xed0000000041ULL: s390_format_RXF_FRRDF(s390_irgen_SRDT, 16214 ovl.fmt.RXF.r3, ovl.fmt.RXF.x2, 16215 ovl.fmt.RXF.b2, ovl.fmt.RXF.d2, 16216 ovl.fmt.RXF.r1); goto ok; 16217 case 0xed0000000048ULL: s390_format_RXF_FRRDF(s390_irgen_SLXT, 16218 ovl.fmt.RXF.r3, ovl.fmt.RXF.x2, 16219 ovl.fmt.RXF.b2, ovl.fmt.RXF.d2, 16220 ovl.fmt.RXF.r1); goto ok; 16221 case 0xed0000000049ULL: s390_format_RXF_FRRDF(s390_irgen_SRXT, 16222 ovl.fmt.RXF.r3, ovl.fmt.RXF.x2, 16223 ovl.fmt.RXF.b2, ovl.fmt.RXF.d2, 16224 ovl.fmt.RXF.r1); goto ok; 16225 case 0xed0000000050ULL: s390_format_RXE_FRRD(s390_irgen_TDCET, ovl.fmt.RXE.r1, 16226 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16227 ovl.fmt.RXE.d2); goto ok; 16228 case 0xed0000000051ULL: s390_format_RXE_FRRD(s390_irgen_TDGET, ovl.fmt.RXE.r1, 16229 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16230 ovl.fmt.RXE.d2); goto ok; 16231 case 0xed0000000054ULL: s390_format_RXE_FRRD(s390_irgen_TDCDT, ovl.fmt.RXE.r1, 16232 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16233 ovl.fmt.RXE.d2); goto ok; 16234 case 0xed0000000055ULL: s390_format_RXE_FRRD(s390_irgen_TDGDT, ovl.fmt.RXE.r1, 16235 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16236 ovl.fmt.RXE.d2); goto ok; 16237 case 0xed0000000058ULL: s390_format_RXE_FRRD(s390_irgen_TDCXT, ovl.fmt.RXE.r1, 16238 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16239 ovl.fmt.RXE.d2); goto ok; 16240 case 0xed0000000059ULL: s390_format_RXE_FRRD(s390_irgen_TDGXT, ovl.fmt.RXE.r1, 16241 ovl.fmt.RXE.x2, ovl.fmt.RXE.b2, 16242 ovl.fmt.RXE.d2); goto ok; 16243 case 0xed0000000064ULL: s390_format_RXY_FRRD(s390_irgen_LEY, ovl.fmt.RXY.r1, 16244 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 16245 ovl.fmt.RXY.dl2, 16246 ovl.fmt.RXY.dh2); goto ok; 16247 case 0xed0000000065ULL: s390_format_RXY_FRRD(s390_irgen_LDY, ovl.fmt.RXY.r1, 16248 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 16249 ovl.fmt.RXY.dl2, 16250 ovl.fmt.RXY.dh2); goto ok; 16251 case 0xed0000000066ULL: s390_format_RXY_FRRD(s390_irgen_STEY, ovl.fmt.RXY.r1, 16252 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 16253 ovl.fmt.RXY.dl2, 16254 ovl.fmt.RXY.dh2); goto ok; 16255 case 0xed0000000067ULL: s390_format_RXY_FRRD(s390_irgen_STDY, ovl.fmt.RXY.r1, 16256 ovl.fmt.RXY.x2, ovl.fmt.RXY.b2, 16257 ovl.fmt.RXY.dl2, 16258 ovl.fmt.RXY.dh2); goto ok; 16259 case 0xed00000000a8ULL: /* CZDT */ goto unimplemented; 16260 case 0xed00000000a9ULL: /* CZXT */ goto unimplemented; 16261 case 0xed00000000aaULL: /* CDZT */ goto unimplemented; 16262 case 0xed00000000abULL: /* CXZT */ goto unimplemented; 16263 } 16264 16265 switch (((ovl.value >> 16) & 0xff0f00000000ULL) >> 32) { 16266 case 0xc000ULL: s390_format_RIL_RP(s390_irgen_LARL, ovl.fmt.RIL.r1, 16267 ovl.fmt.RIL.i2); goto ok; 16268 case 0xc001ULL: s390_format_RIL_RI(s390_irgen_LGFI, ovl.fmt.RIL.r1, 16269 ovl.fmt.RIL.i2); goto ok; 16270 case 0xc004ULL: s390_format_RIL(s390_irgen_BRCL, ovl.fmt.RIL.r1, 16271 ovl.fmt.RIL.i2); goto ok; 16272 case 0xc005ULL: s390_format_RIL_RP(s390_irgen_BRASL, ovl.fmt.RIL.r1, 16273 ovl.fmt.RIL.i2); goto ok; 16274 case 0xc006ULL: s390_format_RIL_RU(s390_irgen_XIHF, ovl.fmt.RIL.r1, 16275 ovl.fmt.RIL.i2); goto ok; 16276 case 0xc007ULL: s390_format_RIL_RU(s390_irgen_XILF, ovl.fmt.RIL.r1, 16277 ovl.fmt.RIL.i2); goto ok; 16278 case 0xc008ULL: s390_format_RIL_RU(s390_irgen_IIHF, ovl.fmt.RIL.r1, 16279 ovl.fmt.RIL.i2); goto ok; 16280 case 0xc009ULL: s390_format_RIL_RU(s390_irgen_IILF, ovl.fmt.RIL.r1, 16281 ovl.fmt.RIL.i2); goto ok; 16282 case 0xc00aULL: s390_format_RIL_RU(s390_irgen_NIHF, ovl.fmt.RIL.r1, 16283 ovl.fmt.RIL.i2); goto ok; 16284 case 0xc00bULL: s390_format_RIL_RU(s390_irgen_NILF, ovl.fmt.RIL.r1, 16285 ovl.fmt.RIL.i2); goto ok; 16286 case 0xc00cULL: s390_format_RIL_RU(s390_irgen_OIHF, ovl.fmt.RIL.r1, 16287 ovl.fmt.RIL.i2); goto ok; 16288 case 0xc00dULL: s390_format_RIL_RU(s390_irgen_OILF, ovl.fmt.RIL.r1, 16289 ovl.fmt.RIL.i2); goto ok; 16290 case 0xc00eULL: s390_format_RIL_RU(s390_irgen_LLIHF, ovl.fmt.RIL.r1, 16291 ovl.fmt.RIL.i2); goto ok; 16292 case 0xc00fULL: s390_format_RIL_RU(s390_irgen_LLILF, ovl.fmt.RIL.r1, 16293 ovl.fmt.RIL.i2); goto ok; 16294 case 0xc200ULL: s390_format_RIL_RI(s390_irgen_MSGFI, ovl.fmt.RIL.r1, 16295 ovl.fmt.RIL.i2); goto ok; 16296 case 0xc201ULL: s390_format_RIL_RI(s390_irgen_MSFI, ovl.fmt.RIL.r1, 16297 ovl.fmt.RIL.i2); goto ok; 16298 case 0xc204ULL: s390_format_RIL_RU(s390_irgen_SLGFI, ovl.fmt.RIL.r1, 16299 ovl.fmt.RIL.i2); goto ok; 16300 case 0xc205ULL: s390_format_RIL_RU(s390_irgen_SLFI, ovl.fmt.RIL.r1, 16301 ovl.fmt.RIL.i2); goto ok; 16302 case 0xc208ULL: s390_format_RIL_RI(s390_irgen_AGFI, ovl.fmt.RIL.r1, 16303 ovl.fmt.RIL.i2); goto ok; 16304 case 0xc209ULL: s390_format_RIL_RI(s390_irgen_AFI, ovl.fmt.RIL.r1, 16305 ovl.fmt.RIL.i2); goto ok; 16306 case 0xc20aULL: s390_format_RIL_RU(s390_irgen_ALGFI, ovl.fmt.RIL.r1, 16307 ovl.fmt.RIL.i2); goto ok; 16308 case 0xc20bULL: s390_format_RIL_RU(s390_irgen_ALFI, ovl.fmt.RIL.r1, 16309 ovl.fmt.RIL.i2); goto ok; 16310 case 0xc20cULL: s390_format_RIL_RI(s390_irgen_CGFI, ovl.fmt.RIL.r1, 16311 ovl.fmt.RIL.i2); goto ok; 16312 case 0xc20dULL: s390_format_RIL_RI(s390_irgen_CFI, ovl.fmt.RIL.r1, 16313 ovl.fmt.RIL.i2); goto ok; 16314 case 0xc20eULL: s390_format_RIL_RU(s390_irgen_CLGFI, ovl.fmt.RIL.r1, 16315 ovl.fmt.RIL.i2); goto ok; 16316 case 0xc20fULL: s390_format_RIL_RU(s390_irgen_CLFI, ovl.fmt.RIL.r1, 16317 ovl.fmt.RIL.i2); goto ok; 16318 case 0xc402ULL: s390_format_RIL_RP(s390_irgen_LLHRL, ovl.fmt.RIL.r1, 16319 ovl.fmt.RIL.i2); goto ok; 16320 case 0xc404ULL: s390_format_RIL_RP(s390_irgen_LGHRL, ovl.fmt.RIL.r1, 16321 ovl.fmt.RIL.i2); goto ok; 16322 case 0xc405ULL: s390_format_RIL_RP(s390_irgen_LHRL, ovl.fmt.RIL.r1, 16323 ovl.fmt.RIL.i2); goto ok; 16324 case 0xc406ULL: s390_format_RIL_RP(s390_irgen_LLGHRL, ovl.fmt.RIL.r1, 16325 ovl.fmt.RIL.i2); goto ok; 16326 case 0xc407ULL: s390_format_RIL_RP(s390_irgen_STHRL, ovl.fmt.RIL.r1, 16327 ovl.fmt.RIL.i2); goto ok; 16328 case 0xc408ULL: s390_format_RIL_RP(s390_irgen_LGRL, ovl.fmt.RIL.r1, 16329 ovl.fmt.RIL.i2); goto ok; 16330 case 0xc40bULL: s390_format_RIL_RP(s390_irgen_STGRL, ovl.fmt.RIL.r1, 16331 ovl.fmt.RIL.i2); goto ok; 16332 case 0xc40cULL: s390_format_RIL_RP(s390_irgen_LGFRL, ovl.fmt.RIL.r1, 16333 ovl.fmt.RIL.i2); goto ok; 16334 case 0xc40dULL: s390_format_RIL_RP(s390_irgen_LRL, ovl.fmt.RIL.r1, 16335 ovl.fmt.RIL.i2); goto ok; 16336 case 0xc40eULL: s390_format_RIL_RP(s390_irgen_LLGFRL, ovl.fmt.RIL.r1, 16337 ovl.fmt.RIL.i2); goto ok; 16338 case 0xc40fULL: s390_format_RIL_RP(s390_irgen_STRL, ovl.fmt.RIL.r1, 16339 ovl.fmt.RIL.i2); goto ok; 16340 case 0xc600ULL: s390_format_RIL_RP(s390_irgen_EXRL, ovl.fmt.RIL.r1, 16341 ovl.fmt.RIL.i2); goto ok; 16342 case 0xc602ULL: s390_format_RIL_UP(s390_irgen_PFDRL, ovl.fmt.RIL.r1, 16343 ovl.fmt.RIL.i2); goto ok; 16344 case 0xc604ULL: s390_format_RIL_RP(s390_irgen_CGHRL, ovl.fmt.RIL.r1, 16345 ovl.fmt.RIL.i2); goto ok; 16346 case 0xc605ULL: s390_format_RIL_RP(s390_irgen_CHRL, ovl.fmt.RIL.r1, 16347 ovl.fmt.RIL.i2); goto ok; 16348 case 0xc606ULL: s390_format_RIL_RP(s390_irgen_CLGHRL, ovl.fmt.RIL.r1, 16349 ovl.fmt.RIL.i2); goto ok; 16350 case 0xc607ULL: s390_format_RIL_RP(s390_irgen_CLHRL, ovl.fmt.RIL.r1, 16351 ovl.fmt.RIL.i2); goto ok; 16352 case 0xc608ULL: s390_format_RIL_RP(s390_irgen_CGRL, ovl.fmt.RIL.r1, 16353 ovl.fmt.RIL.i2); goto ok; 16354 case 0xc60aULL: s390_format_RIL_RP(s390_irgen_CLGRL, ovl.fmt.RIL.r1, 16355 ovl.fmt.RIL.i2); goto ok; 16356 case 0xc60cULL: s390_format_RIL_RP(s390_irgen_CGFRL, ovl.fmt.RIL.r1, 16357 ovl.fmt.RIL.i2); goto ok; 16358 case 0xc60dULL: s390_format_RIL_RP(s390_irgen_CRL, ovl.fmt.RIL.r1, 16359 ovl.fmt.RIL.i2); goto ok; 16360 case 0xc60eULL: s390_format_RIL_RP(s390_irgen_CLGFRL, ovl.fmt.RIL.r1, 16361 ovl.fmt.RIL.i2); goto ok; 16362 case 0xc60fULL: s390_format_RIL_RP(s390_irgen_CLRL, ovl.fmt.RIL.r1, 16363 ovl.fmt.RIL.i2); goto ok; 16364 case 0xc800ULL: /* MVCOS */ goto unimplemented; 16365 case 0xc801ULL: /* ECTG */ goto unimplemented; 16366 case 0xc802ULL: /* CSST */ goto unimplemented; 16367 case 0xc804ULL: /* LPD */ goto unimplemented; 16368 case 0xc805ULL: /* LPDG */ goto unimplemented; 16369 case 0xcc06ULL: /* BRCTH */ goto unimplemented; 16370 case 0xcc08ULL: s390_format_RIL_RI(s390_irgen_AIH, ovl.fmt.RIL.r1, 16371 ovl.fmt.RIL.i2); goto ok; 16372 case 0xcc0aULL: s390_format_RIL_RI(s390_irgen_ALSIH, ovl.fmt.RIL.r1, 16373 ovl.fmt.RIL.i2); goto ok; 16374 case 0xcc0bULL: s390_format_RIL_RI(s390_irgen_ALSIHN, ovl.fmt.RIL.r1, 16375 ovl.fmt.RIL.i2); goto ok; 16376 case 0xcc0dULL: s390_format_RIL_RI(s390_irgen_CIH, ovl.fmt.RIL.r1, 16377 ovl.fmt.RIL.i2); goto ok; 16378 case 0xcc0fULL: s390_format_RIL_RU(s390_irgen_CLIH, ovl.fmt.RIL.r1, 16379 ovl.fmt.RIL.i2); goto ok; 16380 } 16381 16382 switch (((ovl.value >> 16) & 0xff0000000000ULL) >> 40) { 16383 case 0xc5ULL: /* BPRP */ goto unimplemented; 16384 case 0xc7ULL: /* BPP */ goto unimplemented; 16385 case 0xd0ULL: /* TRTR */ goto unimplemented; 16386 case 0xd1ULL: /* MVN */ goto unimplemented; 16387 case 0xd2ULL: s390_format_SS_L0RDRD(s390_irgen_MVC, ovl.fmt.SS.l, 16388 ovl.fmt.SS.b1, ovl.fmt.SS.d1, 16389 ovl.fmt.SS.b2, ovl.fmt.SS.d2); goto ok; 16390 case 0xd3ULL: /* MVZ */ goto unimplemented; 16391 case 0xd4ULL: s390_format_SS_L0RDRD(s390_irgen_NC, ovl.fmt.SS.l, 16392 ovl.fmt.SS.b1, ovl.fmt.SS.d1, 16393 ovl.fmt.SS.b2, ovl.fmt.SS.d2); goto ok; 16394 case 0xd5ULL: s390_format_SS_L0RDRD(s390_irgen_CLC, ovl.fmt.SS.l, 16395 ovl.fmt.SS.b1, ovl.fmt.SS.d1, 16396 ovl.fmt.SS.b2, ovl.fmt.SS.d2); goto ok; 16397 case 0xd6ULL: s390_format_SS_L0RDRD(s390_irgen_OC, ovl.fmt.SS.l, 16398 ovl.fmt.SS.b1, ovl.fmt.SS.d1, 16399 ovl.fmt.SS.b2, ovl.fmt.SS.d2); goto ok; 16400 case 0xd7ULL: 16401 if (ovl.fmt.SS.b1 == ovl.fmt.SS.b2 && ovl.fmt.SS.d1 == ovl.fmt.SS.d2) 16402 s390_irgen_XC_sameloc(ovl.fmt.SS.l, ovl.fmt.SS.b1, ovl.fmt.SS.d1); 16403 else 16404 s390_format_SS_L0RDRD(s390_irgen_XC, ovl.fmt.SS.l, 16405 ovl.fmt.SS.b1, ovl.fmt.SS.d1, 16406 ovl.fmt.SS.b2, ovl.fmt.SS.d2); 16407 goto ok; 16408 case 0xd9ULL: /* MVCK */ goto unimplemented; 16409 case 0xdaULL: /* MVCP */ goto unimplemented; 16410 case 0xdbULL: /* MVCS */ goto unimplemented; 16411 case 0xdcULL: s390_format_SS_L0RDRD(s390_irgen_TR, ovl.fmt.SS.l, 16412 ovl.fmt.SS.b1, ovl.fmt.SS.d1, 16413 ovl.fmt.SS.b2, ovl.fmt.SS.d2); goto ok; 16414 case 0xddULL: /* TRT */ goto unimplemented; 16415 case 0xdeULL: /* ED */ goto unimplemented; 16416 case 0xdfULL: /* EDMK */ goto unimplemented; 16417 case 0xe1ULL: /* PKU */ goto unimplemented; 16418 case 0xe2ULL: /* UNPKU */ goto unimplemented; 16419 case 0xe8ULL: /* MVCIN */ goto unimplemented; 16420 case 0xe9ULL: /* PKA */ goto unimplemented; 16421 case 0xeaULL: /* UNPKA */ goto unimplemented; 16422 case 0xeeULL: /* PLO */ goto unimplemented; 16423 case 0xefULL: /* LMD */ goto unimplemented; 16424 case 0xf0ULL: /* SRP */ goto unimplemented; 16425 case 0xf1ULL: /* MVO */ goto unimplemented; 16426 case 0xf2ULL: /* PACK */ goto unimplemented; 16427 case 0xf3ULL: /* UNPK */ goto unimplemented; 16428 case 0xf8ULL: /* ZAP */ goto unimplemented; 16429 case 0xf9ULL: /* CP */ goto unimplemented; 16430 case 0xfaULL: /* AP */ goto unimplemented; 16431 case 0xfbULL: /* SP */ goto unimplemented; 16432 case 0xfcULL: /* MP */ goto unimplemented; 16433 case 0xfdULL: /* DP */ goto unimplemented; 16434 } 16435 16436 switch (((ovl.value >> 16) & 0xffff00000000ULL) >> 32) { 16437 case 0xe500ULL: /* LASP */ goto unimplemented; 16438 case 0xe501ULL: /* TPROT */ goto unimplemented; 16439 case 0xe502ULL: /* STRAG */ goto unimplemented; 16440 case 0xe50eULL: /* MVCSK */ goto unimplemented; 16441 case 0xe50fULL: /* MVCDK */ goto unimplemented; 16442 case 0xe544ULL: s390_format_SIL_RDI(s390_irgen_MVHHI, ovl.fmt.SIL.b1, 16443 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16444 goto ok; 16445 case 0xe548ULL: s390_format_SIL_RDI(s390_irgen_MVGHI, ovl.fmt.SIL.b1, 16446 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16447 goto ok; 16448 case 0xe54cULL: s390_format_SIL_RDI(s390_irgen_MVHI, ovl.fmt.SIL.b1, 16449 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16450 goto ok; 16451 case 0xe554ULL: s390_format_SIL_RDI(s390_irgen_CHHSI, ovl.fmt.SIL.b1, 16452 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16453 goto ok; 16454 case 0xe555ULL: s390_format_SIL_RDU(s390_irgen_CLHHSI, ovl.fmt.SIL.b1, 16455 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16456 goto ok; 16457 case 0xe558ULL: s390_format_SIL_RDI(s390_irgen_CGHSI, ovl.fmt.SIL.b1, 16458 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16459 goto ok; 16460 case 0xe559ULL: s390_format_SIL_RDU(s390_irgen_CLGHSI, ovl.fmt.SIL.b1, 16461 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16462 goto ok; 16463 case 0xe55cULL: s390_format_SIL_RDI(s390_irgen_CHSI, ovl.fmt.SIL.b1, 16464 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16465 goto ok; 16466 case 0xe55dULL: s390_format_SIL_RDU(s390_irgen_CLFHSI, ovl.fmt.SIL.b1, 16467 ovl.fmt.SIL.d1, ovl.fmt.SIL.i2); 16468 goto ok; 16469 case 0xe560ULL: /* TBEGIN */ goto unimplemented; 16470 case 0xe561ULL: /* TBEGINC */ goto unimplemented; 16471 } 16472 16473 return S390_DECODE_UNKNOWN_INSN; 16474 16475 ok: 16476 return S390_DECODE_OK; 16477 16478 unimplemented: 16479 return S390_DECODE_UNIMPLEMENTED_INSN; 16480 } 16481 16482 /* Handle "special" instructions. */ 16483 static s390_decode_t 16484 s390_decode_special_and_irgen(const UChar *bytes) 16485 { 16486 s390_decode_t status = S390_DECODE_OK; 16487 16488 /* Got a "Special" instruction preamble. Which one is it? */ 16489 if (bytes[0] == 0x18 && bytes[1] == 0x22 /* lr %r2, %r2 */) { 16490 s390_irgen_client_request(); 16491 } else if (bytes[0] == 0x18 && bytes[1] == 0x33 /* lr %r3, %r3 */) { 16492 s390_irgen_guest_NRADDR(); 16493 } else if (bytes[0] == 0x18 && bytes[1] == 0x44 /* lr %r4, %r4 */) { 16494 s390_irgen_call_noredir(); 16495 } else if (bytes[0] == 0x18 && bytes[1] == 0x55 /* lr %r5, %r5 */) { 16496 vex_inject_ir(irsb, Iend_BE); 16497 16498 /* Invalidate the current insn. The reason is that the IRop we're 16499 injecting here can change. In which case the translation has to 16500 be redone. For ease of handling, we simply invalidate all the 16501 time. */ 16502 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_CMSTART), 16503 mkU64(guest_IA_curr_instr))); 16504 stmt(IRStmt_Put(S390X_GUEST_OFFSET(guest_CMLEN), 16505 mkU64(guest_IA_next_instr - guest_IA_curr_instr))); 16506 vassert(guest_IA_next_instr - guest_IA_curr_instr == 16507 S390_SPECIAL_OP_PREAMBLE_SIZE + S390_SPECIAL_OP_SIZE); 16508 16509 put_IA(mkaddr_expr(guest_IA_next_instr)); 16510 dis_res->whatNext = Dis_StopHere; 16511 dis_res->jk_StopHere = Ijk_InvalICache; 16512 } else { 16513 /* We don't know what it is. */ 16514 return S390_DECODE_UNKNOWN_SPECIAL_INSN; 16515 } 16516 16517 dis_res->len = S390_SPECIAL_OP_PREAMBLE_SIZE + S390_SPECIAL_OP_SIZE; 16518 16519 return status; 16520 } 16521 16522 16523 /* Function returns # bytes that were decoded or 0 in case of failure */ 16524 static UInt 16525 s390_decode_and_irgen(const UChar *bytes, UInt insn_length, DisResult *dres) 16526 { 16527 s390_decode_t status; 16528 16529 dis_res = dres; 16530 16531 /* Spot the 8-byte preamble: 18ff lr r15,r15 16532 1811 lr r1,r1 16533 1822 lr r2,r2 16534 1833 lr r3,r3 */ 16535 if (bytes[ 0] == 0x18 && bytes[ 1] == 0xff && bytes[ 2] == 0x18 && 16536 bytes[ 3] == 0x11 && bytes[ 4] == 0x18 && bytes[ 5] == 0x22 && 16537 bytes[ 6] == 0x18 && bytes[ 7] == 0x33) { 16538 16539 /* Handle special instruction that follows that preamble. */ 16540 if (0) vex_printf("special function handling...\n"); 16541 16542 insn_length = S390_SPECIAL_OP_PREAMBLE_SIZE + S390_SPECIAL_OP_SIZE; 16543 guest_IA_next_instr = guest_IA_curr_instr + insn_length; 16544 16545 status = 16546 s390_decode_special_and_irgen(bytes + S390_SPECIAL_OP_PREAMBLE_SIZE); 16547 } else { 16548 /* Handle normal instructions. */ 16549 switch (insn_length) { 16550 case 2: 16551 status = s390_decode_2byte_and_irgen(bytes); 16552 break; 16553 16554 case 4: 16555 status = s390_decode_4byte_and_irgen(bytes); 16556 break; 16557 16558 case 6: 16559 status = s390_decode_6byte_and_irgen(bytes); 16560 break; 16561 16562 default: 16563 status = S390_DECODE_ERROR; 16564 break; 16565 } 16566 } 16567 /* If next instruction is execute, stop here */ 16568 if (dis_res->whatNext == Dis_Continue && bytes[insn_length] == 0x44) { 16569 put_IA(mkaddr_expr(guest_IA_next_instr)); 16570 dis_res->whatNext = Dis_StopHere; 16571 dis_res->jk_StopHere = Ijk_Boring; 16572 } 16573 16574 if (status == S390_DECODE_OK) return insn_length; /* OK */ 16575 16576 /* Decoding failed somehow */ 16577 if (sigill_diag) { 16578 vex_printf("vex s390->IR: "); 16579 switch (status) { 16580 case S390_DECODE_UNKNOWN_INSN: 16581 vex_printf("unknown insn: "); 16582 break; 16583 16584 case S390_DECODE_UNIMPLEMENTED_INSN: 16585 vex_printf("unimplemented insn: "); 16586 break; 16587 16588 case S390_DECODE_UNKNOWN_SPECIAL_INSN: 16589 vex_printf("unimplemented special insn: "); 16590 break; 16591 16592 case S390_DECODE_ERROR: 16593 vex_printf("decoding error: "); 16594 break; 16595 16596 default: 16597 vpanic("s390_decode_and_irgen"); 16598 } 16599 16600 vex_printf("%02x%02x", bytes[0], bytes[1]); 16601 if (insn_length > 2) { 16602 vex_printf(" %02x%02x", bytes[2], bytes[3]); 16603 } 16604 if (insn_length > 4) { 16605 vex_printf(" %02x%02x", bytes[4], bytes[5]); 16606 } 16607 vex_printf("\n"); 16608 } 16609 16610 return 0; /* Failed */ 16611 } 16612 16613 16614 /* Disassemble a single instruction INSN into IR. */ 16615 static DisResult 16616 disInstr_S390_WRK(const UChar *insn) 16617 { 16618 UChar byte; 16619 UInt insn_length; 16620 DisResult dres; 16621 16622 /* ---------------------------------------------------- */ 16623 /* --- Compute instruction length -- */ 16624 /* ---------------------------------------------------- */ 16625 16626 /* Get the first byte of the insn. */ 16627 byte = insn[0]; 16628 16629 /* The leftmost two bits (0:1) encode the length of the insn in bytes. 16630 00 -> 2 bytes, 01 -> 4 bytes, 10 -> 4 bytes, 11 -> 6 bytes. */ 16631 insn_length = ((((byte >> 6) + 1) >> 1) + 1) << 1; 16632 16633 guest_IA_next_instr = guest_IA_curr_instr + insn_length; 16634 16635 /* ---------------------------------------------------- */ 16636 /* --- Initialise the DisResult data -- */ 16637 /* ---------------------------------------------------- */ 16638 dres.whatNext = Dis_Continue; 16639 dres.len = insn_length; 16640 dres.continueAt = 0; 16641 dres.jk_StopHere = Ijk_INVALID; 16642 16643 /* fixs390: consider chasing of conditional jumps */ 16644 16645 /* Normal and special instruction handling starts here. */ 16646 if (s390_decode_and_irgen(insn, insn_length, &dres) == 0) { 16647 /* All decode failures end up here. The decoder has already issued an 16648 error message. 16649 Tell the dispatcher that this insn cannot be decoded, and so has 16650 not been executed, and (is currently) the next to be executed. 16651 The insn address in the guest state needs to be set to 16652 guest_IA_curr_instr, otherwise the complaint will report an 16653 incorrect address. */ 16654 put_IA(mkaddr_expr(guest_IA_curr_instr)); 16655 16656 dres.len = 0; 16657 dres.whatNext = Dis_StopHere; 16658 dres.jk_StopHere = Ijk_NoDecode; 16659 dres.continueAt = 0; 16660 } else { 16661 /* Decode success */ 16662 switch (dres.whatNext) { 16663 case Dis_Continue: 16664 put_IA(mkaddr_expr(guest_IA_next_instr)); 16665 break; 16666 case Dis_ResteerU: 16667 case Dis_ResteerC: 16668 put_IA(mkaddr_expr(dres.continueAt)); 16669 break; 16670 case Dis_StopHere: 16671 if (dres.jk_StopHere == Ijk_EmWarn || 16672 dres.jk_StopHere == Ijk_EmFail) { 16673 /* We assume here, that emulation warnings are not given for 16674 insns that transfer control. There is no good way to 16675 do that. */ 16676 put_IA(mkaddr_expr(guest_IA_next_instr)); 16677 } 16678 break; 16679 default: 16680 vpanic("disInstr_S390_WRK"); 16681 } 16682 } 16683 16684 return dres; 16685 } 16686 16687 16688 /*------------------------------------------------------------*/ 16689 /*--- Top-level fn ---*/ 16690 /*------------------------------------------------------------*/ 16691 16692 /* Disassemble a single instruction into IR. The instruction 16693 is located in host memory at &guest_code[delta]. */ 16694 16695 DisResult 16696 disInstr_S390(IRSB *irsb_IN, 16697 Bool (*resteerOkFn)(void *, Addr), 16698 Bool resteerCisOk, 16699 void *callback_opaque, 16700 const UChar *guest_code, 16701 Long delta, 16702 Addr guest_IP, 16703 VexArch guest_arch, 16704 const VexArchInfo *archinfo, 16705 const VexAbiInfo *abiinfo, 16706 VexEndness host_endness, 16707 Bool sigill_diag_IN) 16708 { 16709 vassert(guest_arch == VexArchS390X); 16710 16711 /* The instruction decoder requires a big-endian machine. */ 16712 vassert(host_endness == VexEndnessBE); 16713 16714 /* Set globals (see top of this file) */ 16715 guest_IA_curr_instr = guest_IP; 16716 irsb = irsb_IN; 16717 resteer_fn = resteerOkFn; 16718 resteer_data = callback_opaque; 16719 sigill_diag = sigill_diag_IN; 16720 16721 return disInstr_S390_WRK(guest_code + delta); 16722 } 16723 16724 /*---------------------------------------------------------------*/ 16725 /*--- end guest_s390_toIR.c ---*/ 16726 /*---------------------------------------------------------------*/ 16727