1 //
   2 // Copyright (c) 2003, 2019, Oracle and/or its affiliates. All rights reserved.
   3 // Copyright (c) 2014, 2019, Red Hat, Inc. All rights reserved.
   4 // DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   5 //
   6 // This code is free software; you can redistribute it and/or modify it
   7 // under the terms of the GNU General Public License version 2 only, as
   8 // published by the Free Software Foundation.
   9 //
  10 // This code is distributed in the hope that it will be useful, but WITHOUT
  11 // ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  12 // FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  13 // version 2 for more details (a copy is included in the LICENSE file that
  14 // accompanied this code).
  15 //
  16 // You should have received a copy of the GNU General Public License version
  17 // 2 along with this work; if not, write to the Free Software Foundation,
  18 // Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  19 //
  20 // Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  21 // or visit www.oracle.com if you need additional information or have any
  22 // questions.
  23 //
  24 //
  25 
  26 // AArch64 Architecture Description File
  27 
  28 //----------REGISTER DEFINITION BLOCK------------------------------------------
  29 // This information is used by the matcher and the register allocator to
  30 // describe individual registers and classes of registers within the target
  31 // archtecture.
  32 
  33 register %{
  34 //----------Architecture Description Register Definitions----------------------
  35 // General Registers
  36 // "reg_def"  name ( register save type, C convention save type,
  37 //                   ideal register type, encoding );
  38 // Register Save Types:
  39 //
  40 // NS  = No-Save:       The register allocator assumes that these registers
  41 //                      can be used without saving upon entry to the method, &
  42 //                      that they do not need to be saved at call sites.
  43 //
  44 // SOC = Save-On-Call:  The register allocator assumes that these registers
  45 //                      can be used without saving upon entry to the method,
  46 //                      but that they must be saved at call sites.
  47 //
  48 // SOE = Save-On-Entry: The register allocator assumes that these registers
  49 //                      must be saved before using them upon entry to the
  50 //                      method, but they do not need to be saved at call
  51 //                      sites.
  52 //
  53 // AS  = Always-Save:   The register allocator assumes that these registers
  54 //                      must be saved before using them upon entry to the
  55 //                      method, & that they must be saved at call sites.
  56 //
  57 // Ideal Register Type is used to determine how to save & restore a
  58 // register.  Op_RegI will get spilled with LoadI/StoreI, Op_RegP will get
  59 // spilled with LoadP/StoreP.  If the register supports both, use Op_RegI.
  60 //
  61 // The encoding number is the actual bit-pattern placed into the opcodes.
  62 
  63 // We must define the 64 bit int registers in two 32 bit halves, the
  64 // real lower register and a virtual upper half register. upper halves
  65 // are used by the register allocator but are not actually supplied as
  66 // operands to memory ops.
  67 //
  68 // follow the C1 compiler in making registers
  69 //
  70 //   r0-r7,r10-r26 volatile (caller save)
  71 //   r27-r32 system (no save, no allocate)
  72 //   r8-r9 invisible to the allocator (so we can use them as scratch regs)
  73 //
  74 // as regards Java usage. we don't use any callee save registers
  75 // because this makes it difficult to de-optimise a frame (see comment
  76 // in x86 implementation of Deoptimization::unwind_callee_save_values)
  77 //
  78 
  79 // General Registers
  80 
  81 reg_def R0      ( SOC, SOC, Op_RegI,  0, r0->as_VMReg()         );
  82 reg_def R0_H    ( SOC, SOC, Op_RegI,  0, r0->as_VMReg()->next() );
  83 reg_def R1      ( SOC, SOC, Op_RegI,  1, r1->as_VMReg()         );
  84 reg_def R1_H    ( SOC, SOC, Op_RegI,  1, r1->as_VMReg()->next() );
  85 reg_def R2      ( SOC, SOC, Op_RegI,  2, r2->as_VMReg()         );
  86 reg_def R2_H    ( SOC, SOC, Op_RegI,  2, r2->as_VMReg()->next() );
  87 reg_def R3      ( SOC, SOC, Op_RegI,  3, r3->as_VMReg()         );
  88 reg_def R3_H    ( SOC, SOC, Op_RegI,  3, r3->as_VMReg()->next() );
  89 reg_def R4      ( SOC, SOC, Op_RegI,  4, r4->as_VMReg()         );
  90 reg_def R4_H    ( SOC, SOC, Op_RegI,  4, r4->as_VMReg()->next() );
  91 reg_def R5      ( SOC, SOC, Op_RegI,  5, r5->as_VMReg()         );
  92 reg_def R5_H    ( SOC, SOC, Op_RegI,  5, r5->as_VMReg()->next() );
  93 reg_def R6      ( SOC, SOC, Op_RegI,  6, r6->as_VMReg()         );
  94 reg_def R6_H    ( SOC, SOC, Op_RegI,  6, r6->as_VMReg()->next() );
  95 reg_def R7      ( SOC, SOC, Op_RegI,  7, r7->as_VMReg()         );
  96 reg_def R7_H    ( SOC, SOC, Op_RegI,  7, r7->as_VMReg()->next() );
  97 reg_def R10     ( SOC, SOC, Op_RegI, 10, r10->as_VMReg()        );
  98 reg_def R10_H   ( SOC, SOC, Op_RegI, 10, r10->as_VMReg()->next());
  99 reg_def R11     ( SOC, SOC, Op_RegI, 11, r11->as_VMReg()        );
 100 reg_def R11_H   ( SOC, SOC, Op_RegI, 11, r11->as_VMReg()->next());
 101 reg_def R12     ( SOC, SOC, Op_RegI, 12, r12->as_VMReg()        );
 102 reg_def R12_H   ( SOC, SOC, Op_RegI, 12, r12->as_VMReg()->next());
 103 reg_def R13     ( SOC, SOC, Op_RegI, 13, r13->as_VMReg()        );
 104 reg_def R13_H   ( SOC, SOC, Op_RegI, 13, r13->as_VMReg()->next());
 105 reg_def R14     ( SOC, SOC, Op_RegI, 14, r14->as_VMReg()        );
 106 reg_def R14_H   ( SOC, SOC, Op_RegI, 14, r14->as_VMReg()->next());
 107 reg_def R15     ( SOC, SOC, Op_RegI, 15, r15->as_VMReg()        );
 108 reg_def R15_H   ( SOC, SOC, Op_RegI, 15, r15->as_VMReg()->next());
 109 reg_def R16     ( SOC, SOC, Op_RegI, 16, r16->as_VMReg()        );
 110 reg_def R16_H   ( SOC, SOC, Op_RegI, 16, r16->as_VMReg()->next());
 111 reg_def R17     ( SOC, SOC, Op_RegI, 17, r17->as_VMReg()        );
 112 reg_def R17_H   ( SOC, SOC, Op_RegI, 17, r17->as_VMReg()->next());
 113 reg_def R18     ( SOC, SOC, Op_RegI, 18, r18->as_VMReg()        );
 114 reg_def R18_H   ( SOC, SOC, Op_RegI, 18, r18->as_VMReg()->next());
 115 reg_def R19     ( SOC, SOE, Op_RegI, 19, r19->as_VMReg()        );
 116 reg_def R19_H   ( SOC, SOE, Op_RegI, 19, r19->as_VMReg()->next());
 117 reg_def R20     ( SOC, SOE, Op_RegI, 20, r20->as_VMReg()        ); // caller esp
 118 reg_def R20_H   ( SOC, SOE, Op_RegI, 20, r20->as_VMReg()->next());
 119 reg_def R21     ( SOC, SOE, Op_RegI, 21, r21->as_VMReg()        );
 120 reg_def R21_H   ( SOC, SOE, Op_RegI, 21, r21->as_VMReg()->next());
 121 reg_def R22     ( SOC, SOE, Op_RegI, 22, r22->as_VMReg()        );
 122 reg_def R22_H   ( SOC, SOE, Op_RegI, 22, r22->as_VMReg()->next());
 123 reg_def R23     ( SOC, SOE, Op_RegI, 23, r23->as_VMReg()        );
 124 reg_def R23_H   ( SOC, SOE, Op_RegI, 23, r23->as_VMReg()->next());
 125 reg_def R24     ( SOC, SOE, Op_RegI, 24, r24->as_VMReg()        );
 126 reg_def R24_H   ( SOC, SOE, Op_RegI, 24, r24->as_VMReg()->next());
 127 reg_def R25     ( SOC, SOE, Op_RegI, 25, r25->as_VMReg()        );
 128 reg_def R25_H   ( SOC, SOE, Op_RegI, 25, r25->as_VMReg()->next());
 129 reg_def R26     ( SOC, SOE, Op_RegI, 26, r26->as_VMReg()        );
 130 reg_def R26_H   ( SOC, SOE, Op_RegI, 26, r26->as_VMReg()->next());
 131 reg_def R27     (  NS, SOE, Op_RegI, 27, r27->as_VMReg()        ); // heapbase
 132 reg_def R27_H   (  NS, SOE, Op_RegI, 27, r27->as_VMReg()->next());
 133 reg_def R28     (  NS, SOE, Op_RegI, 28, r28->as_VMReg()        ); // thread
 134 reg_def R28_H   (  NS, SOE, Op_RegI, 28, r28->as_VMReg()->next());
 135 reg_def R29     (  NS,  NS, Op_RegI, 29, r29->as_VMReg()        ); // fp
 136 reg_def R29_H   (  NS,  NS, Op_RegI, 29, r29->as_VMReg()->next());
 137 reg_def R30     (  NS,  NS, Op_RegI, 30, r30->as_VMReg()        ); // lr
 138 reg_def R30_H   (  NS,  NS, Op_RegI, 30, r30->as_VMReg()->next());
 139 reg_def R31     (  NS,  NS, Op_RegI, 31, r31_sp->as_VMReg()     ); // sp
 140 reg_def R31_H   (  NS,  NS, Op_RegI, 31, r31_sp->as_VMReg()->next());
 141 
 142 // ----------------------------
 143 // Float/Double Registers
 144 // ----------------------------
 145 
 146 // Double Registers
 147 
 148 // The rules of ADL require that double registers be defined in pairs.
 149 // Each pair must be two 32-bit values, but not necessarily a pair of
 150 // single float registers. In each pair, ADLC-assigned register numbers
 151 // must be adjacent, with the lower number even. Finally, when the
 152 // CPU stores such a register pair to memory, the word associated with
 153 // the lower ADLC-assigned number must be stored to the lower address.
 154 
 155 // AArch64 has 32 floating-point registers. Each can store a vector of
 156 // single or double precision floating-point values up to 8 * 32
 157 // floats, 4 * 64 bit floats or 2 * 128 bit floats.  We currently only
 158 // use the first float or double element of the vector.
 159 
 160 // for Java use float registers v0-v15 are always save on call whereas
 161 // the platform ABI treats v8-v15 as callee save). float registers
 162 // v16-v31 are SOC as per the platform spec
 163 
 164   reg_def V0   ( SOC, SOC, Op_RegF,  0, v0->as_VMReg()          );
 165   reg_def V0_H ( SOC, SOC, Op_RegF,  0, v0->as_VMReg()->next()  );
 166   reg_def V0_J ( SOC, SOC, Op_RegF,  0, v0->as_VMReg()->next(2) );
 167   reg_def V0_K ( SOC, SOC, Op_RegF,  0, v0->as_VMReg()->next(3) );
 168 
 169   reg_def V1   ( SOC, SOC, Op_RegF,  1, v1->as_VMReg()          );
 170   reg_def V1_H ( SOC, SOC, Op_RegF,  1, v1->as_VMReg()->next()  );
 171   reg_def V1_J ( SOC, SOC, Op_RegF,  1, v1->as_VMReg()->next(2) );
 172   reg_def V1_K ( SOC, SOC, Op_RegF,  1, v1->as_VMReg()->next(3) );
 173 
 174   reg_def V2   ( SOC, SOC, Op_RegF,  2, v2->as_VMReg()          );
 175   reg_def V2_H ( SOC, SOC, Op_RegF,  2, v2->as_VMReg()->next()  );
 176   reg_def V2_J ( SOC, SOC, Op_RegF,  2, v2->as_VMReg()->next(2) );
 177   reg_def V2_K ( SOC, SOC, Op_RegF,  2, v2->as_VMReg()->next(3) );
 178 
 179   reg_def V3   ( SOC, SOC, Op_RegF,  3, v3->as_VMReg()          );
 180   reg_def V3_H ( SOC, SOC, Op_RegF,  3, v3->as_VMReg()->next()  );
 181   reg_def V3_J ( SOC, SOC, Op_RegF,  3, v3->as_VMReg()->next(2) );
 182   reg_def V3_K ( SOC, SOC, Op_RegF,  3, v3->as_VMReg()->next(3) );
 183 
 184   reg_def V4   ( SOC, SOC, Op_RegF,  4, v4->as_VMReg()          );
 185   reg_def V4_H ( SOC, SOC, Op_RegF,  4, v4->as_VMReg()->next()  );
 186   reg_def V4_J ( SOC, SOC, Op_RegF,  4, v4->as_VMReg()->next(2) );
 187   reg_def V4_K ( SOC, SOC, Op_RegF,  4, v4->as_VMReg()->next(3) );
 188 
 189   reg_def V5   ( SOC, SOC, Op_RegF,  5, v5->as_VMReg()          );
 190   reg_def V5_H ( SOC, SOC, Op_RegF,  5, v5->as_VMReg()->next()  );
 191   reg_def V5_J ( SOC, SOC, Op_RegF,  5, v5->as_VMReg()->next(2) );
 192   reg_def V5_K ( SOC, SOC, Op_RegF,  5, v5->as_VMReg()->next(3) );
 193 
 194   reg_def V6   ( SOC, SOC, Op_RegF,  6, v6->as_VMReg()          );
 195   reg_def V6_H ( SOC, SOC, Op_RegF,  6, v6->as_VMReg()->next()  );
 196   reg_def V6_J ( SOC, SOC, Op_RegF,  6, v6->as_VMReg()->next(2) );
 197   reg_def V6_K ( SOC, SOC, Op_RegF,  6, v6->as_VMReg()->next(3) );
 198 
 199   reg_def V7   ( SOC, SOC, Op_RegF,  7, v7->as_VMReg()          );
 200   reg_def V7_H ( SOC, SOC, Op_RegF,  7, v7->as_VMReg()->next()  );
 201   reg_def V7_J ( SOC, SOC, Op_RegF,  7, v7->as_VMReg()->next(2) );
 202   reg_def V7_K ( SOC, SOC, Op_RegF,  7, v7->as_VMReg()->next(3) );
 203 
 204   reg_def V8   ( SOC, SOC, Op_RegF,  8, v8->as_VMReg()          );
 205   reg_def V8_H ( SOC, SOC, Op_RegF,  8, v8->as_VMReg()->next()  );
 206   reg_def V8_J ( SOC, SOC, Op_RegF,  8, v8->as_VMReg()->next(2) );
 207   reg_def V8_K ( SOC, SOC, Op_RegF,  8, v8->as_VMReg()->next(3) );
 208 
 209   reg_def V9   ( SOC, SOC, Op_RegF,  9, v9->as_VMReg()          );
 210   reg_def V9_H ( SOC, SOC, Op_RegF,  9, v9->as_VMReg()->next()  );
 211   reg_def V9_J ( SOC, SOC, Op_RegF,  9, v9->as_VMReg()->next(2) );
 212   reg_def V9_K ( SOC, SOC, Op_RegF,  9, v9->as_VMReg()->next(3) );
 213 
 214   reg_def V10  ( SOC, SOC, Op_RegF, 10, v10->as_VMReg()         );
 215   reg_def V10_H( SOC, SOC, Op_RegF, 10, v10->as_VMReg()->next() );
 216   reg_def V10_J( SOC, SOC, Op_RegF, 10, v10->as_VMReg()->next(2));
 217   reg_def V10_K( SOC, SOC, Op_RegF, 10, v10->as_VMReg()->next(3));
 218 
 219   reg_def V11  ( SOC, SOC, Op_RegF, 11, v11->as_VMReg()         );
 220   reg_def V11_H( SOC, SOC, Op_RegF, 11, v11->as_VMReg()->next() );
 221   reg_def V11_J( SOC, SOC, Op_RegF, 11, v11->as_VMReg()->next(2));
 222   reg_def V11_K( SOC, SOC, Op_RegF, 11, v11->as_VMReg()->next(3));
 223 
 224   reg_def V12  ( SOC, SOC, Op_RegF, 12, v12->as_VMReg()         );
 225   reg_def V12_H( SOC, SOC, Op_RegF, 12, v12->as_VMReg()->next() );
 226   reg_def V12_J( SOC, SOC, Op_RegF, 12, v12->as_VMReg()->next(2));
 227   reg_def V12_K( SOC, SOC, Op_RegF, 12, v12->as_VMReg()->next(3));
 228 
 229   reg_def V13  ( SOC, SOC, Op_RegF, 13, v13->as_VMReg()         );
 230   reg_def V13_H( SOC, SOC, Op_RegF, 13, v13->as_VMReg()->next() );
 231   reg_def V13_J( SOC, SOC, Op_RegF, 13, v13->as_VMReg()->next(2));
 232   reg_def V13_K( SOC, SOC, Op_RegF, 13, v13->as_VMReg()->next(3));
 233 
 234   reg_def V14  ( SOC, SOC, Op_RegF, 14, v14->as_VMReg()         );
 235   reg_def V14_H( SOC, SOC, Op_RegF, 14, v14->as_VMReg()->next() );
 236   reg_def V14_J( SOC, SOC, Op_RegF, 14, v14->as_VMReg()->next(2));
 237   reg_def V14_K( SOC, SOC, Op_RegF, 14, v14->as_VMReg()->next(3));
 238 
 239   reg_def V15  ( SOC, SOC, Op_RegF, 15, v15->as_VMReg()         );
 240   reg_def V15_H( SOC, SOC, Op_RegF, 15, v15->as_VMReg()->next() );
 241   reg_def V15_J( SOC, SOC, Op_RegF, 15, v15->as_VMReg()->next(2));
 242   reg_def V15_K( SOC, SOC, Op_RegF, 15, v15->as_VMReg()->next(3));
 243 
 244   reg_def V16  ( SOC, SOC, Op_RegF, 16, v16->as_VMReg()         );
 245   reg_def V16_H( SOC, SOC, Op_RegF, 16, v16->as_VMReg()->next() );
 246   reg_def V16_J( SOC, SOC, Op_RegF, 16, v16->as_VMReg()->next(2));
 247   reg_def V16_K( SOC, SOC, Op_RegF, 16, v16->as_VMReg()->next(3));
 248 
 249   reg_def V17  ( SOC, SOC, Op_RegF, 17, v17->as_VMReg()         );
 250   reg_def V17_H( SOC, SOC, Op_RegF, 17, v17->as_VMReg()->next() );
 251   reg_def V17_J( SOC, SOC, Op_RegF, 17, v17->as_VMReg()->next(2));
 252   reg_def V17_K( SOC, SOC, Op_RegF, 17, v17->as_VMReg()->next(3));
 253 
 254   reg_def V18  ( SOC, SOC, Op_RegF, 18, v18->as_VMReg()         );
 255   reg_def V18_H( SOC, SOC, Op_RegF, 18, v18->as_VMReg()->next() );
 256   reg_def V18_J( SOC, SOC, Op_RegF, 18, v18->as_VMReg()->next(2));
 257   reg_def V18_K( SOC, SOC, Op_RegF, 18, v18->as_VMReg()->next(3));
 258 
 259   reg_def V19  ( SOC, SOC, Op_RegF, 19, v19->as_VMReg()         );
 260   reg_def V19_H( SOC, SOC, Op_RegF, 19, v19->as_VMReg()->next() );
 261   reg_def V19_J( SOC, SOC, Op_RegF, 19, v19->as_VMReg()->next(2));
 262   reg_def V19_K( SOC, SOC, Op_RegF, 19, v19->as_VMReg()->next(3));
 263 
 264   reg_def V20  ( SOC, SOC, Op_RegF, 20, v20->as_VMReg()         );
 265   reg_def V20_H( SOC, SOC, Op_RegF, 20, v20->as_VMReg()->next() );
 266   reg_def V20_J( SOC, SOC, Op_RegF, 20, v20->as_VMReg()->next(2));
 267   reg_def V20_K( SOC, SOC, Op_RegF, 20, v20->as_VMReg()->next(3));
 268 
 269   reg_def V21  ( SOC, SOC, Op_RegF, 21, v21->as_VMReg()         );
 270   reg_def V21_H( SOC, SOC, Op_RegF, 21, v21->as_VMReg()->next() );
 271   reg_def V21_J( SOC, SOC, Op_RegF, 21, v21->as_VMReg()->next(2));
 272   reg_def V21_K( SOC, SOC, Op_RegF, 21, v21->as_VMReg()->next(3));
 273 
 274   reg_def V22  ( SOC, SOC, Op_RegF, 22, v22->as_VMReg()         );
 275   reg_def V22_H( SOC, SOC, Op_RegF, 22, v22->as_VMReg()->next() );
 276   reg_def V22_J( SOC, SOC, Op_RegF, 22, v22->as_VMReg()->next(2));
 277   reg_def V22_K( SOC, SOC, Op_RegF, 22, v22->as_VMReg()->next(3));
 278 
 279   reg_def V23  ( SOC, SOC, Op_RegF, 23, v23->as_VMReg()         );
 280   reg_def V23_H( SOC, SOC, Op_RegF, 23, v23->as_VMReg()->next() );
 281   reg_def V23_J( SOC, SOC, Op_RegF, 23, v23->as_VMReg()->next(2));
 282   reg_def V23_K( SOC, SOC, Op_RegF, 23, v23->as_VMReg()->next(3));
 283 
 284   reg_def V24  ( SOC, SOC, Op_RegF, 24, v24->as_VMReg()         );
 285   reg_def V24_H( SOC, SOC, Op_RegF, 24, v24->as_VMReg()->next() );
 286   reg_def V24_J( SOC, SOC, Op_RegF, 24, v24->as_VMReg()->next(2));
 287   reg_def V24_K( SOC, SOC, Op_RegF, 24, v24->as_VMReg()->next(3));
 288 
 289   reg_def V25  ( SOC, SOC, Op_RegF, 25, v25->as_VMReg()         );
 290   reg_def V25_H( SOC, SOC, Op_RegF, 25, v25->as_VMReg()->next() );
 291   reg_def V25_J( SOC, SOC, Op_RegF, 25, v25->as_VMReg()->next(2));
 292   reg_def V25_K( SOC, SOC, Op_RegF, 25, v25->as_VMReg()->next(3));
 293 
 294   reg_def V26  ( SOC, SOC, Op_RegF, 26, v26->as_VMReg()         );
 295   reg_def V26_H( SOC, SOC, Op_RegF, 26, v26->as_VMReg()->next() );
 296   reg_def V26_J( SOC, SOC, Op_RegF, 26, v26->as_VMReg()->next(2));
 297   reg_def V26_K( SOC, SOC, Op_RegF, 26, v26->as_VMReg()->next(3));
 298 
 299   reg_def V27  ( SOC, SOC, Op_RegF, 27, v27->as_VMReg()         );
 300   reg_def V27_H( SOC, SOC, Op_RegF, 27, v27->as_VMReg()->next() );
 301   reg_def V27_J( SOC, SOC, Op_RegF, 27, v27->as_VMReg()->next(2));
 302   reg_def V27_K( SOC, SOC, Op_RegF, 27, v27->as_VMReg()->next(3));
 303 
 304   reg_def V28  ( SOC, SOC, Op_RegF, 28, v28->as_VMReg()         );
 305   reg_def V28_H( SOC, SOC, Op_RegF, 28, v28->as_VMReg()->next() );
 306   reg_def V28_J( SOC, SOC, Op_RegF, 28, v28->as_VMReg()->next(2));
 307   reg_def V28_K( SOC, SOC, Op_RegF, 28, v28->as_VMReg()->next(3));
 308 
 309   reg_def V29  ( SOC, SOC, Op_RegF, 29, v29->as_VMReg()         );
 310   reg_def V29_H( SOC, SOC, Op_RegF, 29, v29->as_VMReg()->next() );
 311   reg_def V29_J( SOC, SOC, Op_RegF, 29, v29->as_VMReg()->next(2));
 312   reg_def V29_K( SOC, SOC, Op_RegF, 29, v29->as_VMReg()->next(3));
 313 
 314   reg_def V30  ( SOC, SOC, Op_RegF, 30, v30->as_VMReg()         );
 315   reg_def V30_H( SOC, SOC, Op_RegF, 30, v30->as_VMReg()->next() );
 316   reg_def V30_J( SOC, SOC, Op_RegF, 30, v30->as_VMReg()->next(2));
 317   reg_def V30_K( SOC, SOC, Op_RegF, 30, v30->as_VMReg()->next(3));
 318 
 319   reg_def V31  ( SOC, SOC, Op_RegF, 31, v31->as_VMReg()         );
 320   reg_def V31_H( SOC, SOC, Op_RegF, 31, v31->as_VMReg()->next() );
 321   reg_def V31_J( SOC, SOC, Op_RegF, 31, v31->as_VMReg()->next(2));
 322   reg_def V31_K( SOC, SOC, Op_RegF, 31, v31->as_VMReg()->next(3));
 323 
 324 // ----------------------------
 325 // Special Registers
 326 // ----------------------------
 327 
 328 // the AArch64 CSPR status flag register is not directly acessible as
 329 // instruction operand. the FPSR status flag register is a system
 330 // register which can be written/read using MSR/MRS but again does not
 331 // appear as an operand (a code identifying the FSPR occurs as an
 332 // immediate value in the instruction).
 333 
 334 reg_def RFLAGS(SOC, SOC, 0, 32, VMRegImpl::Bad());
 335 
 336 
 337 // Specify priority of register selection within phases of register
 338 // allocation.  Highest priority is first.  A useful heuristic is to
 339 // give registers a low priority when they are required by machine
 340 // instructions, like EAX and EDX on I486, and choose no-save registers
 341 // before save-on-call, & save-on-call before save-on-entry.  Registers
 342 // which participate in fixed calling sequences should come last.
 343 // Registers which are used as pairs must fall on an even boundary.
 344 
 345 alloc_class chunk0(
 346     // volatiles
 347     R10, R10_H,
 348     R11, R11_H,
 349     R12, R12_H,
 350     R13, R13_H,
 351     R14, R14_H,
 352     R15, R15_H,
 353     R16, R16_H,
 354     R17, R17_H,
 355     R18, R18_H,
 356 
 357     // arg registers
 358     R0, R0_H,
 359     R1, R1_H,
 360     R2, R2_H,
 361     R3, R3_H,
 362     R4, R4_H,
 363     R5, R5_H,
 364     R6, R6_H,
 365     R7, R7_H,
 366 
 367     // non-volatiles
 368     R19, R19_H,
 369     R20, R20_H,
 370     R21, R21_H,
 371     R22, R22_H,
 372     R23, R23_H,
 373     R24, R24_H,
 374     R25, R25_H,
 375     R26, R26_H,
 376 
 377     // non-allocatable registers
 378 
 379     R27, R27_H, // heapbase
 380     R28, R28_H, // thread
 381     R29, R29_H, // fp
 382     R30, R30_H, // lr
 383     R31, R31_H, // sp
 384 );
 385 
 386 alloc_class chunk1(
 387 
 388     // no save
 389     V16, V16_H, V16_J, V16_K,
 390     V17, V17_H, V17_J, V17_K,
 391     V18, V18_H, V18_J, V18_K,
 392     V19, V19_H, V19_J, V19_K,
 393     V20, V20_H, V20_J, V20_K,
 394     V21, V21_H, V21_J, V21_K,
 395     V22, V22_H, V22_J, V22_K,
 396     V23, V23_H, V23_J, V23_K,
 397     V24, V24_H, V24_J, V24_K,
 398     V25, V25_H, V25_J, V25_K,
 399     V26, V26_H, V26_J, V26_K,
 400     V27, V27_H, V27_J, V27_K,
 401     V28, V28_H, V28_J, V28_K,
 402     V29, V29_H, V29_J, V29_K,
 403     V30, V30_H, V30_J, V30_K,
 404     V31, V31_H, V31_J, V31_K,
 405 
 406     // arg registers
 407     V0, V0_H, V0_J, V0_K,
 408     V1, V1_H, V1_J, V1_K,
 409     V2, V2_H, V2_J, V2_K,
 410     V3, V3_H, V3_J, V3_K,
 411     V4, V4_H, V4_J, V4_K,
 412     V5, V5_H, V5_J, V5_K,
 413     V6, V6_H, V6_J, V6_K,
 414     V7, V7_H, V7_J, V7_K,
 415 
 416     // non-volatiles
 417     V8, V8_H, V8_J, V8_K,
 418     V9, V9_H, V9_J, V9_K,
 419     V10, V10_H, V10_J, V10_K,
 420     V11, V11_H, V11_J, V11_K,
 421     V12, V12_H, V12_J, V12_K,
 422     V13, V13_H, V13_J, V13_K,
 423     V14, V14_H, V14_J, V14_K,
 424     V15, V15_H, V15_J, V15_K,
 425 );
 426 
 427 alloc_class chunk2(RFLAGS);
 428 
 429 //----------Architecture Description Register Classes--------------------------
 430 // Several register classes are automatically defined based upon information in
 431 // this architecture description.
 432 // 1) reg_class inline_cache_reg           ( /* as def'd in frame section */ )
 433 // 2) reg_class compiler_method_oop_reg    ( /* as def'd in frame section */ )
 434 // 2) reg_class interpreter_method_oop_reg ( /* as def'd in frame section */ )
 435 // 3) reg_class stack_slots( /* one chunk of stack-based "registers" */ )
 436 //
 437 
 438 // Class for all 32 bit integer registers -- excludes SP which will
 439 // never be used as an integer register
 440 reg_class any_reg32(
 441     R0,
 442     R1,
 443     R2,
 444     R3,
 445     R4,
 446     R5,
 447     R6,
 448     R7,
 449     R10,
 450     R11,
 451     R12,
 452     R13,
 453     R14,
 454     R15,
 455     R16,
 456     R17,
 457     R18,
 458     R19,
 459     R20,
 460     R21,
 461     R22,
 462     R23,
 463     R24,
 464     R25,
 465     R26,
 466     R27,
 467     R28,
 468     R29,
 469     R30
 470 );
 471 
 472 // Singleton class for R0 int register
 473 reg_class int_r0_reg(R0);
 474 
 475 // Singleton class for R2 int register
 476 reg_class int_r2_reg(R2);
 477 
 478 // Singleton class for R3 int register
 479 reg_class int_r3_reg(R3);
 480 
 481 // Singleton class for R4 int register
 482 reg_class int_r4_reg(R4);
 483 
 484 // Class for all long integer registers (including RSP)
 485 reg_class any_reg(
 486     R0, R0_H,
 487     R1, R1_H,
 488     R2, R2_H,
 489     R3, R3_H,
 490     R4, R4_H,
 491     R5, R5_H,
 492     R6, R6_H,
 493     R7, R7_H,
 494     R10, R10_H,
 495     R11, R11_H,
 496     R12, R12_H,
 497     R13, R13_H,
 498     R14, R14_H,
 499     R15, R15_H,
 500     R16, R16_H,
 501     R17, R17_H,
 502     R18, R18_H,
 503     R19, R19_H,
 504     R20, R20_H,
 505     R21, R21_H,
 506     R22, R22_H,
 507     R23, R23_H,
 508     R24, R24_H,
 509     R25, R25_H,
 510     R26, R26_H,
 511     R27, R27_H,
 512     R28, R28_H,
 513     R29, R29_H,
 514     R30, R30_H,
 515     R31, R31_H
 516 );
 517 
 518 // Class for all non-special integer registers
 519 reg_class no_special_reg32_no_fp(
 520     R0,
 521     R1,
 522     R2,
 523     R3,
 524     R4,
 525     R5,
 526     R6,
 527     R7,
 528     R10,
 529     R11,
 530     R12,                        // rmethod
 531     R13,
 532     R14,
 533     R15,
 534     R16,
 535     R17,
 536     R18,
 537     R19,
 538     R20,
 539     R21,
 540     R22,
 541     R23,
 542     R24,
 543     R25,
 544     R26
 545  /* R27, */                     // heapbase
 546  /* R28, */                     // thread
 547  /* R29, */                     // fp
 548  /* R30, */                     // lr
 549  /* R31 */                      // sp
 550 );
 551 
 552 reg_class no_special_reg32_with_fp(
 553     R0,
 554     R1,
 555     R2,
 556     R3,
 557     R4,
 558     R5,
 559     R6,
 560     R7,
 561     R10,
 562     R11,
 563     R12,                        // rmethod
 564     R13,
 565     R14,
 566     R15,
 567     R16,
 568     R17,
 569     R18,
 570     R19,
 571     R20,
 572     R21,
 573     R22,
 574     R23,
 575     R24,
 576     R25,
 577     R26
 578  /* R27, */                     // heapbase
 579  /* R28, */                     // thread
 580     R29,                        // fp
 581  /* R30, */                     // lr
 582  /* R31 */                      // sp
 583 );
 584 
 585 reg_class_dynamic no_special_reg32(no_special_reg32_no_fp, no_special_reg32_with_fp, %{ PreserveFramePointer %});
 586 
 587 // Class for all non-special long integer registers
 588 reg_class no_special_reg_no_fp(
 589     R0, R0_H,
 590     R1, R1_H,
 591     R2, R2_H,
 592     R3, R3_H,
 593     R4, R4_H,
 594     R5, R5_H,
 595     R6, R6_H,
 596     R7, R7_H,
 597     R10, R10_H,
 598     R11, R11_H,
 599     R12, R12_H,                 // rmethod
 600     R13, R13_H,
 601     R14, R14_H,
 602     R15, R15_H,
 603     R16, R16_H,
 604     R17, R17_H,
 605     R18, R18_H,
 606     R19, R19_H,
 607     R20, R20_H,
 608     R21, R21_H,
 609     R22, R22_H,
 610     R23, R23_H,
 611     R24, R24_H,
 612     R25, R25_H,
 613     R26, R26_H,
 614  /* R27, R27_H, */              // heapbase
 615  /* R28, R28_H, */              // thread
 616  /* R29, R29_H, */              // fp
 617  /* R30, R30_H, */              // lr
 618  /* R31, R31_H */               // sp
 619 );
 620 
 621 reg_class no_special_reg_with_fp(
 622     R0, R0_H,
 623     R1, R1_H,
 624     R2, R2_H,
 625     R3, R3_H,
 626     R4, R4_H,
 627     R5, R5_H,
 628     R6, R6_H,
 629     R7, R7_H,
 630     R10, R10_H,
 631     R11, R11_H,
 632     R12, R12_H,                 // rmethod
 633     R13, R13_H,
 634     R14, R14_H,
 635     R15, R15_H,
 636     R16, R16_H,
 637     R17, R17_H,
 638     R18, R18_H,
 639     R19, R19_H,
 640     R20, R20_H,
 641     R21, R21_H,
 642     R22, R22_H,
 643     R23, R23_H,
 644     R24, R24_H,
 645     R25, R25_H,
 646     R26, R26_H,
 647  /* R27, R27_H, */              // heapbase
 648  /* R28, R28_H, */              // thread
 649     R29, R29_H,                 // fp
 650  /* R30, R30_H, */              // lr
 651  /* R31, R31_H */               // sp
 652 );
 653 
 654 reg_class_dynamic no_special_reg(no_special_reg_no_fp, no_special_reg_with_fp, %{ PreserveFramePointer %});
 655 
 656 // Class for 64 bit register r0
 657 reg_class r0_reg(
 658     R0, R0_H
 659 );
 660 
 661 // Class for 64 bit register r1
 662 reg_class r1_reg(
 663     R1, R1_H
 664 );
 665 
 666 // Class for 64 bit register r2
 667 reg_class r2_reg(
 668     R2, R2_H
 669 );
 670 
 671 // Class for 64 bit register r3
 672 reg_class r3_reg(
 673     R3, R3_H
 674 );
 675 
 676 // Class for 64 bit register r4
 677 reg_class r4_reg(
 678     R4, R4_H
 679 );
 680 
 681 // Class for 64 bit register r5
 682 reg_class r5_reg(
 683     R5, R5_H
 684 );
 685 
 686 // Class for 64 bit register r10
 687 reg_class r10_reg(
 688     R10, R10_H
 689 );
 690 
 691 // Class for 64 bit register r11
 692 reg_class r11_reg(
 693     R11, R11_H
 694 );
 695 
 696 // Class for method register
 697 reg_class method_reg(
 698     R12, R12_H
 699 );
 700 
 701 // Class for heapbase register
 702 reg_class heapbase_reg(
 703     R27, R27_H
 704 );
 705 
 706 // Class for thread register
 707 reg_class thread_reg(
 708     R28, R28_H
 709 );
 710 
 711 // Class for frame pointer register
 712 reg_class fp_reg(
 713     R29, R29_H
 714 );
 715 
 716 // Class for link register
 717 reg_class lr_reg(
 718     R30, R30_H
 719 );
 720 
 721 // Class for long sp register
 722 reg_class sp_reg(
 723   R31, R31_H
 724 );
 725 
 726 // Class for all pointer registers
 727 reg_class ptr_reg(
 728     R0, R0_H,
 729     R1, R1_H,
 730     R2, R2_H,
 731     R3, R3_H,
 732     R4, R4_H,
 733     R5, R5_H,
 734     R6, R6_H,
 735     R7, R7_H,
 736     R10, R10_H,
 737     R11, R11_H,
 738     R12, R12_H,
 739     R13, R13_H,
 740     R14, R14_H,
 741     R15, R15_H,
 742     R16, R16_H,
 743     R17, R17_H,
 744     R18, R18_H,
 745     R19, R19_H,
 746     R20, R20_H,
 747     R21, R21_H,
 748     R22, R22_H,
 749     R23, R23_H,
 750     R24, R24_H,
 751     R25, R25_H,
 752     R26, R26_H,
 753     R27, R27_H,
 754     R28, R28_H,
 755     R29, R29_H,
 756     R30, R30_H,
 757     R31, R31_H
 758 );
 759 
 760 // Class for all non_special pointer registers
 761 reg_class no_special_ptr_reg(
 762     R0, R0_H,
 763     R1, R1_H,
 764     R2, R2_H,
 765     R3, R3_H,
 766     R4, R4_H,
 767     R5, R5_H,
 768     R6, R6_H,
 769     R7, R7_H,
 770     R10, R10_H,
 771     R11, R11_H,
 772     R12, R12_H,
 773     R13, R13_H,
 774     R14, R14_H,
 775     R15, R15_H,
 776     R16, R16_H,
 777     R17, R17_H,
 778     R18, R18_H,
 779     R19, R19_H,
 780     R20, R20_H,
 781     R21, R21_H,
 782     R22, R22_H,
 783     R23, R23_H,
 784     R24, R24_H,
 785     R25, R25_H,
 786     R26, R26_H,
 787  /* R27, R27_H, */              // heapbase
 788  /* R28, R28_H, */              // thread
 789  /* R29, R29_H, */              // fp
 790  /* R30, R30_H, */              // lr
 791  /* R31, R31_H */               // sp
 792 );
 793 
 794 // Class for all float registers
 795 reg_class float_reg(
 796     V0,
 797     V1,
 798     V2,
 799     V3,
 800     V4,
 801     V5,
 802     V6,
 803     V7,
 804     V8,
 805     V9,
 806     V10,
 807     V11,
 808     V12,
 809     V13,
 810     V14,
 811     V15,
 812     V16,
 813     V17,
 814     V18,
 815     V19,
 816     V20,
 817     V21,
 818     V22,
 819     V23,
 820     V24,
 821     V25,
 822     V26,
 823     V27,
 824     V28,
 825     V29,
 826     V30,
 827     V31
 828 );
 829 
 830 // Double precision float registers have virtual `high halves' that
 831 // are needed by the allocator.
 832 // Class for all double registers
 833 reg_class double_reg(
 834     V0, V0_H,
 835     V1, V1_H,
 836     V2, V2_H,
 837     V3, V3_H,
 838     V4, V4_H,
 839     V5, V5_H,
 840     V6, V6_H,
 841     V7, V7_H,
 842     V8, V8_H,
 843     V9, V9_H,
 844     V10, V10_H,
 845     V11, V11_H,
 846     V12, V12_H,
 847     V13, V13_H,
 848     V14, V14_H,
 849     V15, V15_H,
 850     V16, V16_H,
 851     V17, V17_H,
 852     V18, V18_H,
 853     V19, V19_H,
 854     V20, V20_H,
 855     V21, V21_H,
 856     V22, V22_H,
 857     V23, V23_H,
 858     V24, V24_H,
 859     V25, V25_H,
 860     V26, V26_H,
 861     V27, V27_H,
 862     V28, V28_H,
 863     V29, V29_H,
 864     V30, V30_H,
 865     V31, V31_H
 866 );
 867 
 868 // Class for all 64bit vector registers
 869 reg_class vectord_reg(
 870     V0, V0_H,
 871     V1, V1_H,
 872     V2, V2_H,
 873     V3, V3_H,
 874     V4, V4_H,
 875     V5, V5_H,
 876     V6, V6_H,
 877     V7, V7_H,
 878     V8, V8_H,
 879     V9, V9_H,
 880     V10, V10_H,
 881     V11, V11_H,
 882     V12, V12_H,
 883     V13, V13_H,
 884     V14, V14_H,
 885     V15, V15_H,
 886     V16, V16_H,
 887     V17, V17_H,
 888     V18, V18_H,
 889     V19, V19_H,
 890     V20, V20_H,
 891     V21, V21_H,
 892     V22, V22_H,
 893     V23, V23_H,
 894     V24, V24_H,
 895     V25, V25_H,
 896     V26, V26_H,
 897     V27, V27_H,
 898     V28, V28_H,
 899     V29, V29_H,
 900     V30, V30_H,
 901     V31, V31_H
 902 );
 903 
 904 // Class for all 128bit vector registers
 905 reg_class vectorx_reg(
 906     V0, V0_H, V0_J, V0_K,
 907     V1, V1_H, V1_J, V1_K,
 908     V2, V2_H, V2_J, V2_K,
 909     V3, V3_H, V3_J, V3_K,
 910     V4, V4_H, V4_J, V4_K,
 911     V5, V5_H, V5_J, V5_K,
 912     V6, V6_H, V6_J, V6_K,
 913     V7, V7_H, V7_J, V7_K,
 914     V8, V8_H, V8_J, V8_K,
 915     V9, V9_H, V9_J, V9_K,
 916     V10, V10_H, V10_J, V10_K,
 917     V11, V11_H, V11_J, V11_K,
 918     V12, V12_H, V12_J, V12_K,
 919     V13, V13_H, V13_J, V13_K,
 920     V14, V14_H, V14_J, V14_K,
 921     V15, V15_H, V15_J, V15_K,
 922     V16, V16_H, V16_J, V16_K,
 923     V17, V17_H, V17_J, V17_K,
 924     V18, V18_H, V18_J, V18_K,
 925     V19, V19_H, V19_J, V19_K,
 926     V20, V20_H, V20_J, V20_K,
 927     V21, V21_H, V21_J, V21_K,
 928     V22, V22_H, V22_J, V22_K,
 929     V23, V23_H, V23_J, V23_K,
 930     V24, V24_H, V24_J, V24_K,
 931     V25, V25_H, V25_J, V25_K,
 932     V26, V26_H, V26_J, V26_K,
 933     V27, V27_H, V27_J, V27_K,
 934     V28, V28_H, V28_J, V28_K,
 935     V29, V29_H, V29_J, V29_K,
 936     V30, V30_H, V30_J, V30_K,
 937     V31, V31_H, V31_J, V31_K
 938 );
 939 
 940 // Class for 128 bit register v0
 941 reg_class v0_reg(
 942     V0, V0_H
 943 );
 944 
 945 // Class for 128 bit register v1
 946 reg_class v1_reg(
 947     V1, V1_H
 948 );
 949 
 950 // Class for 128 bit register v2
 951 reg_class v2_reg(
 952     V2, V2_H
 953 );
 954 
 955 // Class for 128 bit register v3
 956 reg_class v3_reg(
 957     V3, V3_H
 958 );
 959 
 960 // Singleton class for condition codes
 961 reg_class int_flags(RFLAGS);
 962 
 963 %}
 964 
 965 //----------DEFINITION BLOCK---------------------------------------------------
 966 // Define name --> value mappings to inform the ADLC of an integer valued name
 967 // Current support includes integer values in the range [0, 0x7FFFFFFF]
 968 // Format:
 969 //        int_def  <name>         ( <int_value>, <expression>);
 970 // Generated Code in ad_<arch>.hpp
 971 //        #define  <name>   (<expression>)
 972 //        // value == <int_value>
 973 // Generated code in ad_<arch>.cpp adlc_verification()
 974 //        assert( <name> == <int_value>, "Expect (<expression>) to equal <int_value>");
 975 //
 976 
 977 // we follow the ppc-aix port in using a simple cost model which ranks
 978 // register operations as cheap, memory ops as more expensive and
 979 // branches as most expensive. the first two have a low as well as a
 980 // normal cost. huge cost appears to be a way of saying don't do
 981 // something
 982 
 983 definitions %{
 984   // The default cost (of a register move instruction).
 985   int_def INSN_COST            (    100,     100);
 986   int_def BRANCH_COST          (    200,     2 * INSN_COST);
 987   int_def CALL_COST            (    200,     2 * INSN_COST);
 988   int_def VOLATILE_REF_COST    (   1000,     10 * INSN_COST);
 989 %}
 990 
 991 
 992 //----------SOURCE BLOCK-------------------------------------------------------
 993 // This is a block of C++ code which provides values, functions, and
 994 // definitions necessary in the rest of the architecture description
 995 
 996 source_hpp %{
 997 
 998 #include "asm/macroAssembler.hpp"
 999 #include "gc/shared/cardTable.hpp"
1000 #include "gc/shared/cardTableBarrierSet.hpp"
1001 #include "gc/shared/collectedHeap.hpp"
1002 #include "opto/addnode.hpp"
1003 
1004 class CallStubImpl {
1005 
1006   //--------------------------------------------------------------
1007   //---<  Used for optimization in Compile::shorten_branches  >---
1008   //--------------------------------------------------------------
1009 
1010  public:
1011   // Size of call trampoline stub.
1012   static uint size_call_trampoline() {
1013     return 0; // no call trampolines on this platform
1014   }
1015 
1016   // number of relocations needed by a call trampoline stub
1017   static uint reloc_call_trampoline() {
1018     return 0; // no call trampolines on this platform
1019   }
1020 };
1021 
1022 class HandlerImpl {
1023 
1024  public:
1025 
1026   static int emit_exception_handler(CodeBuffer &cbuf);
1027   static int emit_deopt_handler(CodeBuffer& cbuf);
1028 
1029   static uint size_exception_handler() {
1030     return MacroAssembler::far_branch_size();
1031   }
1032 
1033   static uint size_deopt_handler() {
1034     // count one adr and one far branch instruction
1035     return 4 * NativeInstruction::instruction_size;
1036   }
1037 };
1038 
1039  bool is_CAS(int opcode, bool maybe_volatile);
1040 
1041   // predicates controlling emit of ldr<x>/ldar<x> and associated dmb
1042 
1043   bool unnecessary_acquire(const Node *barrier);
1044   bool needs_acquiring_load(const Node *load);
1045 
1046   // predicates controlling emit of str<x>/stlr<x> and associated dmbs
1047 
1048   bool unnecessary_release(const Node *barrier);
1049   bool unnecessary_volatile(const Node *barrier);
1050   bool needs_releasing_store(const Node *store);
1051 
1052   // predicate controlling translation of CompareAndSwapX
1053   bool needs_acquiring_load_exclusive(const Node *load);
1054 
1055   // predicate controlling translation of StoreCM
1056   bool unnecessary_storestore(const Node *storecm);
1057 
1058   // predicate controlling addressing modes
1059   bool size_fits_all_mem_uses(AddPNode* addp, int shift);
1060 %}
1061 
1062 source %{
1063 
1064   // Optimizaton of volatile gets and puts
1065   // -------------------------------------
1066   //
1067   // AArch64 has ldar<x> and stlr<x> instructions which we can safely
1068   // use to implement volatile reads and writes. For a volatile read
1069   // we simply need
1070   //
1071   //   ldar<x>
1072   //
1073   // and for a volatile write we need
1074   //
1075   //   stlr<x>
1076   //
1077   // Alternatively, we can implement them by pairing a normal
1078   // load/store with a memory barrier. For a volatile read we need
1079   //
1080   //   ldr<x>
1081   //   dmb ishld
1082   //
1083   // for a volatile write
1084   //
1085   //   dmb ish
1086   //   str<x>
1087   //   dmb ish
1088   //
1089   // We can also use ldaxr and stlxr to implement compare and swap CAS
1090   // sequences. These are normally translated to an instruction
1091   // sequence like the following
1092   //
1093   //   dmb      ish
1094   // retry:
1095   //   ldxr<x>   rval raddr
1096   //   cmp       rval rold
1097   //   b.ne done
1098   //   stlxr<x>  rval, rnew, rold
1099   //   cbnz      rval retry
1100   // done:
1101   //   cset      r0, eq
1102   //   dmb ishld
1103   //
1104   // Note that the exclusive store is already using an stlxr
1105   // instruction. That is required to ensure visibility to other
1106   // threads of the exclusive write (assuming it succeeds) before that
1107   // of any subsequent writes.
1108   //
1109   // The following instruction sequence is an improvement on the above
1110   //
1111   // retry:
1112   //   ldaxr<x>  rval raddr
1113   //   cmp       rval rold
1114   //   b.ne done
1115   //   stlxr<x>  rval, rnew, rold
1116   //   cbnz      rval retry
1117   // done:
1118   //   cset      r0, eq
1119   //
1120   // We don't need the leading dmb ish since the stlxr guarantees
1121   // visibility of prior writes in the case that the swap is
1122   // successful. Crucially we don't have to worry about the case where
1123   // the swap is not successful since no valid program should be
1124   // relying on visibility of prior changes by the attempting thread
1125   // in the case where the CAS fails.
1126   //
1127   // Similarly, we don't need the trailing dmb ishld if we substitute
1128   // an ldaxr instruction since that will provide all the guarantees we
1129   // require regarding observation of changes made by other threads
1130   // before any change to the CAS address observed by the load.
1131   //
1132   // In order to generate the desired instruction sequence we need to
1133   // be able to identify specific 'signature' ideal graph node
1134   // sequences which i) occur as a translation of a volatile reads or
1135   // writes or CAS operations and ii) do not occur through any other
1136   // translation or graph transformation. We can then provide
1137   // alternative aldc matching rules which translate these node
1138   // sequences to the desired machine code sequences. Selection of the
1139   // alternative rules can be implemented by predicates which identify
1140   // the relevant node sequences.
1141   //
1142   // The ideal graph generator translates a volatile read to the node
1143   // sequence
1144   //
1145   //   LoadX[mo_acquire]
1146   //   MemBarAcquire
1147   //
1148   // As a special case when using the compressed oops optimization we
1149   // may also see this variant
1150   //
1151   //   LoadN[mo_acquire]
1152   //   DecodeN
1153   //   MemBarAcquire
1154   //
1155   // A volatile write is translated to the node sequence
1156   //
1157   //   MemBarRelease
1158   //   StoreX[mo_release] {CardMark}-optional
1159   //   MemBarVolatile
1160   //
1161   // n.b. the above node patterns are generated with a strict
1162   // 'signature' configuration of input and output dependencies (see
1163   // the predicates below for exact details). The card mark may be as
1164   // simple as a few extra nodes or, in a few GC configurations, may
1165   // include more complex control flow between the leading and
1166   // trailing memory barriers. However, whatever the card mark
1167   // configuration these signatures are unique to translated volatile
1168   // reads/stores -- they will not appear as a result of any other
1169   // bytecode translation or inlining nor as a consequence of
1170   // optimizing transforms.
1171   //
1172   // We also want to catch inlined unsafe volatile gets and puts and
1173   // be able to implement them using either ldar<x>/stlr<x> or some
1174   // combination of ldr<x>/stlr<x> and dmb instructions.
1175   //
1176   // Inlined unsafe volatiles puts manifest as a minor variant of the
1177   // normal volatile put node sequence containing an extra cpuorder
1178   // membar
1179   //
1180   //   MemBarRelease
1181   //   MemBarCPUOrder
1182   //   StoreX[mo_release] {CardMark}-optional
1183   //   MemBarCPUOrder
1184   //   MemBarVolatile
1185   //
1186   // n.b. as an aside, a cpuorder membar is not itself subject to
1187   // matching and translation by adlc rules.  However, the rule
1188   // predicates need to detect its presence in order to correctly
1189   // select the desired adlc rules.
1190   //
1191   // Inlined unsafe volatile gets manifest as a slightly different
1192   // node sequence to a normal volatile get because of the
1193   // introduction of some CPUOrder memory barriers to bracket the
1194   // Load. However, but the same basic skeleton of a LoadX feeding a
1195   // MemBarAcquire, possibly thorugh an optional DecodeN, is still
1196   // present
1197   //
1198   //   MemBarCPUOrder
1199   //        ||       \\
1200   //   MemBarCPUOrder LoadX[mo_acquire]
1201   //        ||            |
1202   //        ||       {DecodeN} optional
1203   //        ||       /
1204   //     MemBarAcquire
1205   //
1206   // In this case the acquire membar does not directly depend on the
1207   // load. However, we can be sure that the load is generated from an
1208   // inlined unsafe volatile get if we see it dependent on this unique
1209   // sequence of membar nodes. Similarly, given an acquire membar we
1210   // can know that it was added because of an inlined unsafe volatile
1211   // get if it is fed and feeds a cpuorder membar and if its feed
1212   // membar also feeds an acquiring load.
1213   //
1214   // Finally an inlined (Unsafe) CAS operation is translated to the
1215   // following ideal graph
1216   //
1217   //   MemBarRelease
1218   //   MemBarCPUOrder
1219   //   CompareAndSwapX {CardMark}-optional
1220   //   MemBarCPUOrder
1221   //   MemBarAcquire
1222   //
1223   // So, where we can identify these volatile read and write
1224   // signatures we can choose to plant either of the above two code
1225   // sequences. For a volatile read we can simply plant a normal
1226   // ldr<x> and translate the MemBarAcquire to a dmb. However, we can
1227   // also choose to inhibit translation of the MemBarAcquire and
1228   // inhibit planting of the ldr<x>, instead planting an ldar<x>.
1229   //
1230   // When we recognise a volatile store signature we can choose to
1231   // plant at a dmb ish as a translation for the MemBarRelease, a
1232   // normal str<x> and then a dmb ish for the MemBarVolatile.
1233   // Alternatively, we can inhibit translation of the MemBarRelease
1234   // and MemBarVolatile and instead plant a simple stlr<x>
1235   // instruction.
1236   //
1237   // when we recognise a CAS signature we can choose to plant a dmb
1238   // ish as a translation for the MemBarRelease, the conventional
1239   // macro-instruction sequence for the CompareAndSwap node (which
1240   // uses ldxr<x>) and then a dmb ishld for the MemBarAcquire.
1241   // Alternatively, we can elide generation of the dmb instructions
1242   // and plant the alternative CompareAndSwap macro-instruction
1243   // sequence (which uses ldaxr<x>).
1244   //
1245   // Of course, the above only applies when we see these signature
1246   // configurations. We still want to plant dmb instructions in any
1247   // other cases where we may see a MemBarAcquire, MemBarRelease or
1248   // MemBarVolatile. For example, at the end of a constructor which
1249   // writes final/volatile fields we will see a MemBarRelease
1250   // instruction and this needs a 'dmb ish' lest we risk the
1251   // constructed object being visible without making the
1252   // final/volatile field writes visible.
1253   //
1254   // n.b. the translation rules below which rely on detection of the
1255   // volatile signatures and insert ldar<x> or stlr<x> are failsafe.
1256   // If we see anything other than the signature configurations we
1257   // always just translate the loads and stores to ldr<x> and str<x>
1258   // and translate acquire, release and volatile membars to the
1259   // relevant dmb instructions.
1260   //
1261 
1262   // is_CAS(int opcode, bool maybe_volatile)
1263   //
1264   // return true if opcode is one of the possible CompareAndSwapX
1265   // values otherwise false.
1266 
1267   bool is_CAS(int opcode, bool maybe_volatile)
1268   {
1269     switch(opcode) {
1270       // We handle these
1271     case Op_CompareAndSwapI:
1272     case Op_CompareAndSwapL:
1273     case Op_CompareAndSwapP:
1274     case Op_CompareAndSwapN:
1275     case Op_CompareAndSwapB:
1276     case Op_CompareAndSwapS:
1277     case Op_GetAndSetI:
1278     case Op_GetAndSetL:
1279     case Op_GetAndSetP:
1280     case Op_GetAndSetN:
1281     case Op_GetAndAddI:
1282     case Op_GetAndAddL:
1283       return true;
1284     case Op_CompareAndExchangeI:
1285     case Op_CompareAndExchangeN:
1286     case Op_CompareAndExchangeB:
1287     case Op_CompareAndExchangeS:
1288     case Op_CompareAndExchangeL:
1289     case Op_CompareAndExchangeP:
1290     case Op_WeakCompareAndSwapB:
1291     case Op_WeakCompareAndSwapS:
1292     case Op_WeakCompareAndSwapI:
1293     case Op_WeakCompareAndSwapL:
1294     case Op_WeakCompareAndSwapP:
1295     case Op_WeakCompareAndSwapN:
1296       return maybe_volatile;
1297     default:
1298       return false;
1299     }
1300   }
1301 
1302   // helper to determine the maximum number of Phi nodes we may need to
1303   // traverse when searching from a card mark membar for the merge mem
1304   // feeding a trailing membar or vice versa
1305 
1306 // predicates controlling emit of ldr<x>/ldar<x> and associated dmb
1307 
1308 bool unnecessary_acquire(const Node *barrier)
1309 {
1310   assert(barrier->is_MemBar(), "expecting a membar");
1311 
1312   if (UseBarriersForVolatile) {
1313     // we need to plant a dmb
1314     return false;
1315   }
1316 
1317   MemBarNode* mb = barrier->as_MemBar();
1318 
1319   if (mb->trailing_load()) {
1320     return true;
1321   }
1322 
1323   if (mb->trailing_load_store()) {
1324     Node* load_store = mb->in(MemBarNode::Precedent);
1325     assert(load_store->is_LoadStore(), "unexpected graph shape");
1326     return is_CAS(load_store->Opcode(), true);
1327   }
1328 
1329   return false;
1330 }
1331 
1332 bool needs_acquiring_load(const Node *n)
1333 {
1334   assert(n->is_Load(), "expecting a load");
1335   if (UseBarriersForVolatile) {
1336     // we use a normal load and a dmb
1337     return false;
1338   }
1339 
1340   LoadNode *ld = n->as_Load();
1341 
1342   return ld->is_acquire();
1343 }
1344 
1345 bool unnecessary_release(const Node *n)
1346 {
1347   assert((n->is_MemBar() &&
1348           n->Opcode() == Op_MemBarRelease),
1349          "expecting a release membar");
1350 
1351   if (UseBarriersForVolatile) {
1352     // we need to plant a dmb
1353     return false;
1354   }
1355 
1356   MemBarNode *barrier = n->as_MemBar();
1357   if (!barrier->leading()) {
1358     return false;
1359   } else {
1360     Node* trailing = barrier->trailing_membar();
1361     MemBarNode* trailing_mb = trailing->as_MemBar();
1362     assert(trailing_mb->trailing(), "Not a trailing membar?");
1363     assert(trailing_mb->leading_membar() == n, "inconsistent leading/trailing membars");
1364 
1365     Node* mem = trailing_mb->in(MemBarNode::Precedent);
1366     if (mem->is_Store()) {
1367       assert(mem->as_Store()->is_release(), "");
1368       assert(trailing_mb->Opcode() == Op_MemBarVolatile, "");
1369       return true;
1370     } else {
1371       assert(mem->is_LoadStore(), "");
1372       assert(trailing_mb->Opcode() == Op_MemBarAcquire, "");
1373       return is_CAS(mem->Opcode(), true);
1374     }
1375   }
1376   return false;
1377 }
1378 
1379 bool unnecessary_volatile(const Node *n)
1380 {
1381   // assert n->is_MemBar();
1382   if (UseBarriersForVolatile) {
1383     // we need to plant a dmb
1384     return false;
1385   }
1386 
1387   MemBarNode *mbvol = n->as_MemBar();
1388 
1389   bool release = mbvol->trailing_store();
1390   assert(!release || (mbvol->in(MemBarNode::Precedent)->is_Store() && mbvol->in(MemBarNode::Precedent)->as_Store()->is_release()), "");
1391 #ifdef ASSERT
1392   if (release) {
1393     Node* leading = mbvol->leading_membar();
1394     assert(leading->Opcode() == Op_MemBarRelease, "");
1395     assert(leading->as_MemBar()->leading_store(), "");
1396     assert(leading->as_MemBar()->trailing_membar() == mbvol, "");
1397   }
1398 #endif
1399 
1400   return release;
1401 }
1402 
1403 // predicates controlling emit of str<x>/stlr<x> and associated dmbs
1404 
1405 bool needs_releasing_store(const Node *n)
1406 {
1407   // assert n->is_Store();
1408   if (UseBarriersForVolatile) {
1409     // we use a normal store and dmb combination
1410     return false;
1411   }
1412 
1413   StoreNode *st = n->as_Store();
1414 
1415   return st->trailing_membar() != NULL;
1416 }
1417 
1418 // predicate controlling translation of CAS
1419 //
1420 // returns true if CAS needs to use an acquiring load otherwise false
1421 
1422 bool needs_acquiring_load_exclusive(const Node *n)
1423 {
1424   assert(is_CAS(n->Opcode(), true), "expecting a compare and swap");
1425   if (UseBarriersForVolatile) {
1426     return false;
1427   }
1428 
1429   LoadStoreNode* ldst = n->as_LoadStore();
1430   if (is_CAS(n->Opcode(), false)) {
1431     assert(ldst->trailing_membar() != NULL, "expected trailing membar");
1432   } else {
1433     return ldst->trailing_membar() != NULL;
1434   }
1435 
1436   // so we can just return true here
1437   return true;
1438 }
1439 
1440 // predicate controlling translation of StoreCM
1441 //
1442 // returns true if a StoreStore must precede the card write otherwise
1443 // false
1444 
1445 bool unnecessary_storestore(const Node *storecm)
1446 {
1447   assert(storecm->Opcode()  == Op_StoreCM, "expecting a StoreCM");
1448 
1449   // we need to generate a dmb ishst between an object put and the
1450   // associated card mark when we are using CMS without conditional
1451   // card marking
1452 
1453   if (UseConcMarkSweepGC && !UseCondCardMark) {
1454     return false;
1455   }
1456 
1457   // a storestore is unnecesary in all other cases
1458 
1459   return true;
1460 }
1461 
1462 
1463 #define __ _masm.
1464 
1465 // advance declarations for helper functions to convert register
1466 // indices to register objects
1467 
1468 // the ad file has to provide implementations of certain methods
1469 // expected by the generic code
1470 //
1471 // REQUIRED FUNCTIONALITY
1472 
1473 //=============================================================================
1474 
1475 // !!!!! Special hack to get all types of calls to specify the byte offset
1476 //       from the start of the call to the point where the return address
1477 //       will point.
1478 
1479 int MachCallStaticJavaNode::ret_addr_offset()
1480 {
1481   // call should be a simple bl
1482   int off = 4;
1483   return off;
1484 }
1485 
1486 int MachCallDynamicJavaNode::ret_addr_offset()
1487 {
1488   return 16; // movz, movk, movk, bl
1489 }
1490 
1491 int MachCallRuntimeNode::ret_addr_offset() {
1492   // for generated stubs the call will be
1493   //   far_call(addr)
1494   // for real runtime callouts it will be six instructions
1495   // see aarch64_enc_java_to_runtime
1496   //   adr(rscratch2, retaddr)
1497   //   lea(rscratch1, RuntimeAddress(addr)
1498   //   stp(zr, rscratch2, Address(__ pre(sp, -2 * wordSize)))
1499   //   blr(rscratch1)
1500   CodeBlob *cb = CodeCache::find_blob(_entry_point);
1501   if (cb) {
1502     return MacroAssembler::far_branch_size();
1503   } else {
1504     return 6 * NativeInstruction::instruction_size;
1505   }
1506 }
1507 
1508 // Indicate if the safepoint node needs the polling page as an input
1509 
1510 // the shared code plants the oop data at the start of the generated
1511 // code for the safepoint node and that needs ot be at the load
1512 // instruction itself. so we cannot plant a mov of the safepoint poll
1513 // address followed by a load. setting this to true means the mov is
1514 // scheduled as a prior instruction. that's better for scheduling
1515 // anyway.
1516 
1517 bool SafePointNode::needs_polling_address_input()
1518 {
1519   return true;
1520 }
1521 
1522 //=============================================================================
1523 
1524 #ifndef PRODUCT
1525 void MachBreakpointNode::format(PhaseRegAlloc *ra_, outputStream *st) const {
1526   st->print("BREAKPOINT");
1527 }
1528 #endif
1529 
1530 void MachBreakpointNode::emit(CodeBuffer &cbuf, PhaseRegAlloc *ra_) const {
1531   MacroAssembler _masm(&cbuf);
1532   __ brk(0);
1533 }
1534 
1535 uint MachBreakpointNode::size(PhaseRegAlloc *ra_) const {
1536   return MachNode::size(ra_);
1537 }
1538 
1539 //=============================================================================
1540 
1541 #ifndef PRODUCT
1542   void MachNopNode::format(PhaseRegAlloc*, outputStream* st) const {
1543     st->print("nop \t# %d bytes pad for loops and calls", _count);
1544   }
1545 #endif
1546 
1547   void MachNopNode::emit(CodeBuffer &cbuf, PhaseRegAlloc*) const {
1548     MacroAssembler _masm(&cbuf);
1549     for (int i = 0; i < _count; i++) {
1550       __ nop();
1551     }
1552   }
1553 
1554   uint MachNopNode::size(PhaseRegAlloc*) const {
1555     return _count * NativeInstruction::instruction_size;
1556   }
1557 
1558 //=============================================================================
1559 const RegMask& MachConstantBaseNode::_out_RegMask = RegMask::Empty;
1560 
1561 int Compile::ConstantTable::calculate_table_base_offset() const {
1562   return 0;  // absolute addressing, no offset
1563 }
1564 
1565 bool MachConstantBaseNode::requires_postalloc_expand() const { return false; }
1566 void MachConstantBaseNode::postalloc_expand(GrowableArray <Node *> *nodes, PhaseRegAlloc *ra_) {
1567   ShouldNotReachHere();
1568 }
1569 
1570 void MachConstantBaseNode::emit(CodeBuffer& cbuf, PhaseRegAlloc* ra_) const {
1571   // Empty encoding
1572 }
1573 
1574 uint MachConstantBaseNode::size(PhaseRegAlloc* ra_) const {
1575   return 0;
1576 }
1577 
1578 #ifndef PRODUCT
1579 void MachConstantBaseNode::format(PhaseRegAlloc* ra_, outputStream* st) const {
1580   st->print("-- \t// MachConstantBaseNode (empty encoding)");
1581 }
1582 #endif
1583 
1584 #ifndef PRODUCT
1585 void MachPrologNode::format(PhaseRegAlloc *ra_, outputStream *st) const {
1586   Compile* C = ra_->C;
1587 
1588   int framesize = C->frame_slots() << LogBytesPerInt;
1589 
1590   if (C->need_stack_bang(framesize))
1591     st->print("# stack bang size=%d\n\t", framesize);
1592 
1593   if (framesize < ((1 << 9) + 2 * wordSize)) {
1594     st->print("sub  sp, sp, #%d\n\t", framesize);
1595     st->print("stp  rfp, lr, [sp, #%d]", framesize - 2 * wordSize);
1596     if (PreserveFramePointer) st->print("\n\tadd  rfp, sp, #%d", framesize - 2 * wordSize);
1597   } else {
1598     st->print("stp  lr, rfp, [sp, #%d]!\n\t", -(2 * wordSize));
1599     if (PreserveFramePointer) st->print("mov  rfp, sp\n\t");
1600     st->print("mov  rscratch1, #%d\n\t", framesize - 2 * wordSize);
1601     st->print("sub  sp, sp, rscratch1");
1602   }
1603 }
1604 #endif
1605 
1606 void MachPrologNode::emit(CodeBuffer &cbuf, PhaseRegAlloc *ra_) const {
1607   Compile* C = ra_->C;
1608   MacroAssembler _masm(&cbuf);
1609 
1610   // n.b. frame size includes space for return pc and rfp
1611   const long framesize = C->frame_size_in_bytes();
1612   assert(framesize%(2*wordSize) == 0, "must preserve 2*wordSize alignment");
1613 
1614   // insert a nop at the start of the prolog so we can patch in a
1615   // branch if we need to invalidate the method later
1616   __ nop();
1617 
1618   int bangsize = C->bang_size_in_bytes();
1619   if (C->need_stack_bang(bangsize) && UseStackBanging)
1620     __ generate_stack_overflow_check(bangsize);
1621 
1622   __ build_frame(framesize);
1623 
1624   if (VerifyStackAtCalls) {
1625     Unimplemented();
1626   }
1627 
1628   C->set_frame_complete(cbuf.insts_size());
1629 
1630   if (C->has_mach_constant_base_node()) {
1631     // NOTE: We set the table base offset here because users might be
1632     // emitted before MachConstantBaseNode.
1633     Compile::ConstantTable& constant_table = C->constant_table();
1634     constant_table.set_table_base_offset(constant_table.calculate_table_base_offset());
1635   }
1636 }
1637 
1638 uint MachPrologNode::size(PhaseRegAlloc* ra_) const
1639 {
1640   return MachNode::size(ra_); // too many variables; just compute it
1641                               // the hard way
1642 }
1643 
1644 int MachPrologNode::reloc() const
1645 {
1646   return 0;
1647 }
1648 
1649 //=============================================================================
1650 
1651 #ifndef PRODUCT
1652 void MachEpilogNode::format(PhaseRegAlloc *ra_, outputStream *st) const {
1653   Compile* C = ra_->C;
1654   int framesize = C->frame_slots() << LogBytesPerInt;
1655 
1656   st->print("# pop frame %d\n\t",framesize);
1657 
1658   if (framesize == 0) {
1659     st->print("ldp  lr, rfp, [sp],#%d\n\t", (2 * wordSize));
1660   } else if (framesize < ((1 << 9) + 2 * wordSize)) {
1661     st->print("ldp  lr, rfp, [sp,#%d]\n\t", framesize - 2 * wordSize);
1662     st->print("add  sp, sp, #%d\n\t", framesize);
1663   } else {
1664     st->print("mov  rscratch1, #%d\n\t", framesize - 2 * wordSize);
1665     st->print("add  sp, sp, rscratch1\n\t");
1666     st->print("ldp  lr, rfp, [sp],#%d\n\t", (2 * wordSize));
1667   }
1668 
1669   if (do_polling() && C->is_method_compilation()) {
1670     st->print("# touch polling page\n\t");
1671     st->print("mov  rscratch1, #0x%lx\n\t", p2i(os::get_polling_page()));
1672     st->print("ldr zr, [rscratch1]");
1673   }
1674 }
1675 #endif
1676 
1677 void MachEpilogNode::emit(CodeBuffer &cbuf, PhaseRegAlloc *ra_) const {
1678   Compile* C = ra_->C;
1679   MacroAssembler _masm(&cbuf);
1680   int framesize = C->frame_slots() << LogBytesPerInt;
1681 
1682   __ remove_frame(framesize);
1683 
1684   if (StackReservedPages > 0 && C->has_reserved_stack_access()) {
1685     __ reserved_stack_check();
1686   }
1687 
1688   if (do_polling() && C->is_method_compilation()) {
1689     __ read_polling_page(rscratch1, os::get_polling_page(), relocInfo::poll_return_type);
1690   }
1691 }
1692 
1693 uint MachEpilogNode::size(PhaseRegAlloc *ra_) const {
1694   // Variable size. Determine dynamically.
1695   return MachNode::size(ra_);
1696 }
1697 
1698 int MachEpilogNode::reloc() const {
1699   // Return number of relocatable values contained in this instruction.
1700   return 1; // 1 for polling page.
1701 }
1702 
1703 const Pipeline * MachEpilogNode::pipeline() const {
1704   return MachNode::pipeline_class();
1705 }
1706 
1707 // This method seems to be obsolete. It is declared in machnode.hpp
1708 // and defined in all *.ad files, but it is never called. Should we
1709 // get rid of it?
1710 int MachEpilogNode::safepoint_offset() const {
1711   assert(do_polling(), "no return for this epilog node");
1712   return 4;
1713 }
1714 
1715 //=============================================================================
1716 
1717 // Figure out which register class each belongs in: rc_int, rc_float or
1718 // rc_stack.
1719 enum RC { rc_bad, rc_int, rc_float, rc_stack };
1720 
1721 static enum RC rc_class(OptoReg::Name reg) {
1722 
1723   if (reg == OptoReg::Bad) {
1724     return rc_bad;
1725   }
1726 
1727   // we have 30 int registers * 2 halves
1728   // (rscratch1 and rscratch2 are omitted)
1729 
1730   if (reg < 60) {
1731     return rc_int;
1732   }
1733 
1734   // we have 32 float register * 2 halves
1735   if (reg < 60 + 128) {
1736     return rc_float;
1737   }
1738 
1739   // Between float regs & stack is the flags regs.
1740   assert(OptoReg::is_stack(reg), "blow up if spilling flags");
1741 
1742   return rc_stack;
1743 }
1744 
1745 uint MachSpillCopyNode::implementation(CodeBuffer *cbuf, PhaseRegAlloc *ra_, bool do_size, outputStream *st) const {
1746   Compile* C = ra_->C;
1747 
1748   // Get registers to move.
1749   OptoReg::Name src_hi = ra_->get_reg_second(in(1));
1750   OptoReg::Name src_lo = ra_->get_reg_first(in(1));
1751   OptoReg::Name dst_hi = ra_->get_reg_second(this);
1752   OptoReg::Name dst_lo = ra_->get_reg_first(this);
1753 
1754   enum RC src_hi_rc = rc_class(src_hi);
1755   enum RC src_lo_rc = rc_class(src_lo);
1756   enum RC dst_hi_rc = rc_class(dst_hi);
1757   enum RC dst_lo_rc = rc_class(dst_lo);
1758 
1759   assert(src_lo != OptoReg::Bad && dst_lo != OptoReg::Bad, "must move at least 1 register");
1760 
1761   if (src_hi != OptoReg::Bad) {
1762     assert((src_lo&1)==0 && src_lo+1==src_hi &&
1763            (dst_lo&1)==0 && dst_lo+1==dst_hi,
1764            "expected aligned-adjacent pairs");
1765   }
1766 
1767   if (src_lo == dst_lo && src_hi == dst_hi) {
1768     return 0;            // Self copy, no move.
1769   }
1770 
1771   bool is64 = (src_lo & 1) == 0 && src_lo + 1 == src_hi &&
1772               (dst_lo & 1) == 0 && dst_lo + 1 == dst_hi;
1773   int src_offset = ra_->reg2offset(src_lo);
1774   int dst_offset = ra_->reg2offset(dst_lo);
1775 
1776   if (bottom_type()->isa_vect() != NULL) {
1777     uint ireg = ideal_reg();
1778     assert(ireg == Op_VecD || ireg == Op_VecX, "must be 64 bit or 128 bit vector");
1779     if (cbuf) {
1780       MacroAssembler _masm(cbuf);
1781       assert((src_lo_rc != rc_int && dst_lo_rc != rc_int), "sanity");
1782       if (src_lo_rc == rc_stack && dst_lo_rc == rc_stack) {
1783         // stack->stack
1784         assert((src_offset & 7) == 0 && (dst_offset & 7) == 0, "unaligned stack offset");
1785         if (ireg == Op_VecD) {
1786           __ unspill(rscratch1, true, src_offset);
1787           __ spill(rscratch1, true, dst_offset);
1788         } else {
1789           __ spill_copy128(src_offset, dst_offset);
1790         }
1791       } else if (src_lo_rc == rc_float && dst_lo_rc == rc_float) {
1792         __ mov(as_FloatRegister(Matcher::_regEncode[dst_lo]),
1793                ireg == Op_VecD ? __ T8B : __ T16B,
1794                as_FloatRegister(Matcher::_regEncode[src_lo]));
1795       } else if (src_lo_rc == rc_float && dst_lo_rc == rc_stack) {
1796         __ spill(as_FloatRegister(Matcher::_regEncode[src_lo]),
1797                        ireg == Op_VecD ? __ D : __ Q,
1798                        ra_->reg2offset(dst_lo));
1799       } else if (src_lo_rc == rc_stack && dst_lo_rc == rc_float) {
1800         __ unspill(as_FloatRegister(Matcher::_regEncode[dst_lo]),
1801                        ireg == Op_VecD ? __ D : __ Q,
1802                        ra_->reg2offset(src_lo));
1803       } else {
1804         ShouldNotReachHere();
1805       }
1806     }
1807   } else if (cbuf) {
1808     MacroAssembler _masm(cbuf);
1809     switch (src_lo_rc) {
1810     case rc_int:
1811       if (dst_lo_rc == rc_int) {  // gpr --> gpr copy
1812         if (is64) {
1813             __ mov(as_Register(Matcher::_regEncode[dst_lo]),
1814                    as_Register(Matcher::_regEncode[src_lo]));
1815         } else {
1816             MacroAssembler _masm(cbuf);
1817             __ movw(as_Register(Matcher::_regEncode[dst_lo]),
1818                     as_Register(Matcher::_regEncode[src_lo]));
1819         }
1820       } else if (dst_lo_rc == rc_float) { // gpr --> fpr copy
1821         if (is64) {
1822             __ fmovd(as_FloatRegister(Matcher::_regEncode[dst_lo]),
1823                      as_Register(Matcher::_regEncode[src_lo]));
1824         } else {
1825             __ fmovs(as_FloatRegister(Matcher::_regEncode[dst_lo]),
1826                      as_Register(Matcher::_regEncode[src_lo]));
1827         }
1828       } else {                    // gpr --> stack spill
1829         assert(dst_lo_rc == rc_stack, "spill to bad register class");
1830         __ spill(as_Register(Matcher::_regEncode[src_lo]), is64, dst_offset);
1831       }
1832       break;
1833     case rc_float:
1834       if (dst_lo_rc == rc_int) {  // fpr --> gpr copy
1835         if (is64) {
1836             __ fmovd(as_Register(Matcher::_regEncode[dst_lo]),
1837                      as_FloatRegister(Matcher::_regEncode[src_lo]));
1838         } else {
1839             __ fmovs(as_Register(Matcher::_regEncode[dst_lo]),
1840                      as_FloatRegister(Matcher::_regEncode[src_lo]));
1841         }
1842       } else if (dst_lo_rc == rc_float) { // fpr --> fpr copy
1843           if (cbuf) {
1844             __ fmovd(as_FloatRegister(Matcher::_regEncode[dst_lo]),
1845                      as_FloatRegister(Matcher::_regEncode[src_lo]));
1846         } else {
1847             __ fmovs(as_FloatRegister(Matcher::_regEncode[dst_lo]),
1848                      as_FloatRegister(Matcher::_regEncode[src_lo]));
1849         }
1850       } else {                    // fpr --> stack spill
1851         assert(dst_lo_rc == rc_stack, "spill to bad register class");
1852         __ spill(as_FloatRegister(Matcher::_regEncode[src_lo]),
1853                  is64 ? __ D : __ S, dst_offset);
1854       }
1855       break;
1856     case rc_stack:
1857       if (dst_lo_rc == rc_int) {  // stack --> gpr load
1858         __ unspill(as_Register(Matcher::_regEncode[dst_lo]), is64, src_offset);
1859       } else if (dst_lo_rc == rc_float) { // stack --> fpr load
1860         __ unspill(as_FloatRegister(Matcher::_regEncode[dst_lo]),
1861                    is64 ? __ D : __ S, src_offset);
1862       } else {                    // stack --> stack copy
1863         assert(dst_lo_rc == rc_stack, "spill to bad register class");
1864         __ unspill(rscratch1, is64, src_offset);
1865         __ spill(rscratch1, is64, dst_offset);
1866       }
1867       break;
1868     default:
1869       assert(false, "bad rc_class for spill");
1870       ShouldNotReachHere();
1871     }
1872   }
1873 
1874   if (st) {
1875     st->print("spill ");
1876     if (src_lo_rc == rc_stack) {
1877       st->print("[sp, #%d] -> ", ra_->reg2offset(src_lo));
1878     } else {
1879       st->print("%s -> ", Matcher::regName[src_lo]);
1880     }
1881     if (dst_lo_rc == rc_stack) {
1882       st->print("[sp, #%d]", ra_->reg2offset(dst_lo));
1883     } else {
1884       st->print("%s", Matcher::regName[dst_lo]);
1885     }
1886     if (bottom_type()->isa_vect() != NULL) {
1887       st->print("\t# vector spill size = %d", ideal_reg()==Op_VecD ? 64:128);
1888     } else {
1889       st->print("\t# spill size = %d", is64 ? 64:32);
1890     }
1891   }
1892 
1893   return 0;
1894 
1895 }
1896 
1897 #ifndef PRODUCT
1898 void MachSpillCopyNode::format(PhaseRegAlloc *ra_, outputStream *st) const {
1899   if (!ra_)
1900     st->print("N%d = SpillCopy(N%d)", _idx, in(1)->_idx);
1901   else
1902     implementation(NULL, ra_, false, st);
1903 }
1904 #endif
1905 
1906 void MachSpillCopyNode::emit(CodeBuffer &cbuf, PhaseRegAlloc *ra_) const {
1907   implementation(&cbuf, ra_, false, NULL);
1908 }
1909 
1910 uint MachSpillCopyNode::size(PhaseRegAlloc *ra_) const {
1911   return MachNode::size(ra_);
1912 }
1913 
1914 //=============================================================================
1915 
1916 #ifndef PRODUCT
1917 void BoxLockNode::format(PhaseRegAlloc *ra_, outputStream *st) const {
1918   int offset = ra_->reg2offset(in_RegMask(0).find_first_elem());
1919   int reg = ra_->get_reg_first(this);
1920   st->print("add %s, rsp, #%d]\t# box lock",
1921             Matcher::regName[reg], offset);
1922 }
1923 #endif
1924 
1925 void BoxLockNode::emit(CodeBuffer &cbuf, PhaseRegAlloc *ra_) const {
1926   MacroAssembler _masm(&cbuf);
1927 
1928   int offset = ra_->reg2offset(in_RegMask(0).find_first_elem());
1929   int reg    = ra_->get_encode(this);
1930 
1931   if (Assembler::operand_valid_for_add_sub_immediate(offset)) {
1932     __ add(as_Register(reg), sp, offset);
1933   } else {
1934     ShouldNotReachHere();
1935   }
1936 }
1937 
1938 uint BoxLockNode::size(PhaseRegAlloc *ra_) const {
1939   // BoxLockNode is not a MachNode, so we can't just call MachNode::size(ra_).
1940   return 4;
1941 }
1942 
1943 //=============================================================================
1944 
1945 #ifndef PRODUCT
1946 void MachUEPNode::format(PhaseRegAlloc* ra_, outputStream* st) const
1947 {
1948   st->print_cr("# MachUEPNode");
1949   if (UseCompressedClassPointers) {
1950     st->print_cr("\tldrw rscratch1, j_rarg0 + oopDesc::klass_offset_in_bytes()]\t# compressed klass");
1951     if (Universe::narrow_klass_shift() != 0) {
1952       st->print_cr("\tdecode_klass_not_null rscratch1, rscratch1");
1953     }
1954   } else {
1955    st->print_cr("\tldr rscratch1, j_rarg0 + oopDesc::klass_offset_in_bytes()]\t# compressed klass");
1956   }
1957   st->print_cr("\tcmp r0, rscratch1\t # Inline cache check");
1958   st->print_cr("\tbne, SharedRuntime::_ic_miss_stub");
1959 }
1960 #endif
1961 
1962 void MachUEPNode::emit(CodeBuffer& cbuf, PhaseRegAlloc* ra_) const
1963 {
1964   // This is the unverified entry point.
1965   MacroAssembler _masm(&cbuf);
1966 
1967   __ cmp_klass(j_rarg0, rscratch2, rscratch1);
1968   Label skip;
1969   // TODO
1970   // can we avoid this skip and still use a reloc?
1971   __ br(Assembler::EQ, skip);
1972   __ far_jump(RuntimeAddress(SharedRuntime::get_ic_miss_stub()));
1973   __ bind(skip);
1974 }
1975 
1976 uint MachUEPNode::size(PhaseRegAlloc* ra_) const
1977 {
1978   return MachNode::size(ra_);
1979 }
1980 
1981 // REQUIRED EMIT CODE
1982 
1983 //=============================================================================
1984 
1985 // Emit exception handler code.
1986 int HandlerImpl::emit_exception_handler(CodeBuffer& cbuf)
1987 {
1988   // mov rscratch1 #exception_blob_entry_point
1989   // br rscratch1
1990   // Note that the code buffer's insts_mark is always relative to insts.
1991   // That's why we must use the macroassembler to generate a handler.
1992   MacroAssembler _masm(&cbuf);
1993   address base = __ start_a_stub(size_exception_handler());
1994   if (base == NULL) {
1995     ciEnv::current()->record_failure("CodeCache is full");
1996     return 0;  // CodeBuffer::expand failed
1997   }
1998   int offset = __ offset();
1999   __ far_jump(RuntimeAddress(OptoRuntime::exception_blob()->entry_point()));
2000   assert(__ offset() - offset <= (int) size_exception_handler(), "overflow");
2001   __ end_a_stub();
2002   return offset;
2003 }
2004 
2005 // Emit deopt handler code.
2006 int HandlerImpl::emit_deopt_handler(CodeBuffer& cbuf)
2007 {
2008   // Note that the code buffer's insts_mark is always relative to insts.
2009   // That's why we must use the macroassembler to generate a handler.
2010   MacroAssembler _masm(&cbuf);
2011   address base = __ start_a_stub(size_deopt_handler());
2012   if (base == NULL) {
2013     ciEnv::current()->record_failure("CodeCache is full");
2014     return 0;  // CodeBuffer::expand failed
2015   }
2016   int offset = __ offset();
2017 
2018   __ adr(lr, __ pc());
2019   __ far_jump(RuntimeAddress(SharedRuntime::deopt_blob()->unpack()));
2020 
2021   assert(__ offset() - offset <= (int) size_deopt_handler(), "overflow");
2022   __ end_a_stub();
2023   return offset;
2024 }
2025 
2026 // REQUIRED MATCHER CODE
2027 
2028 //=============================================================================
2029 
2030 const bool Matcher::match_rule_supported(int opcode) {
2031 
2032   switch (opcode) {
2033   default:
2034     break;
2035   }
2036 
2037   if (!has_match_rule(opcode)) {
2038     return false;
2039   }
2040 
2041   return true;  // Per default match rules are supported.
2042 }
2043 
2044 const bool Matcher::match_rule_supported_vector(int opcode, int vlen) {
2045 
2046   // TODO
2047   // identify extra cases that we might want to provide match rules for
2048   // e.g. Op_ vector nodes and other intrinsics while guarding with vlen
2049   bool ret_value = match_rule_supported(opcode);
2050   // Add rules here.
2051 
2052   return ret_value;  // Per default match rules are supported.
2053 }
2054 
2055 const bool Matcher::has_predicated_vectors(void) {
2056   return false;
2057 }
2058 
2059 const int Matcher::float_pressure(int default_pressure_threshold) {
2060   return default_pressure_threshold;
2061 }
2062 
2063 int Matcher::regnum_to_fpu_offset(int regnum)
2064 {
2065   Unimplemented();
2066   return 0;
2067 }
2068 
2069 // Is this branch offset short enough that a short branch can be used?
2070 //
2071 // NOTE: If the platform does not provide any short branch variants, then
2072 //       this method should return false for offset 0.
2073 bool Matcher::is_short_branch_offset(int rule, int br_size, int offset) {
2074   // The passed offset is relative to address of the branch.
2075 
2076   return (-32768 <= offset && offset < 32768);
2077 }
2078 
2079 const bool Matcher::isSimpleConstant64(jlong value) {
2080   // Will one (StoreL ConL) be cheaper than two (StoreI ConI)?.
2081   // Probably always true, even if a temp register is required.
2082   return true;
2083 }
2084 
2085 // true just means we have fast l2f conversion
2086 const bool Matcher::convL2FSupported(void) {
2087   return true;
2088 }
2089 
2090 // Vector width in bytes.
2091 const int Matcher::vector_width_in_bytes(BasicType bt) {
2092   int size = MIN2(16,(int)MaxVectorSize);
2093   // Minimum 2 values in vector
2094   if (size < 2*type2aelembytes(bt)) size = 0;
2095   // But never < 4
2096   if (size < 4) size = 0;
2097   return size;
2098 }
2099 
2100 // Limits on vector size (number of elements) loaded into vector.
2101 const int Matcher::max_vector_size(const BasicType bt) {
2102   return vector_width_in_bytes(bt)/type2aelembytes(bt);
2103 }
2104 const int Matcher::min_vector_size(const BasicType bt) {
2105 //  For the moment limit the vector size to 8 bytes
2106     int size = 8 / type2aelembytes(bt);
2107     if (size < 2) size = 2;
2108     return size;
2109 }
2110 
2111 // Vector ideal reg.
2112 const uint Matcher::vector_ideal_reg(int len) {
2113   switch(len) {
2114     case  8: return Op_VecD;
2115     case 16: return Op_VecX;
2116   }
2117   ShouldNotReachHere();
2118   return 0;
2119 }
2120 
2121 const uint Matcher::vector_shift_count_ideal_reg(int size) {
2122   switch(size) {
2123     case  8: return Op_VecD;
2124     case 16: return Op_VecX;
2125   }
2126   ShouldNotReachHere();
2127   return 0;
2128 }
2129 
2130 // AES support not yet implemented
2131 const bool Matcher::pass_original_key_for_aes() {
2132   return false;
2133 }
2134 
2135 // aarch64 supports misaligned vectors store/load.
2136 const bool Matcher::misaligned_vectors_ok() {
2137   return true;
2138 }
2139 
2140 // false => size gets scaled to BytesPerLong, ok.
2141 const bool Matcher::init_array_count_is_in_bytes = false;
2142 
2143 // Use conditional move (CMOVL)
2144 const int Matcher::long_cmove_cost() {
2145   // long cmoves are no more expensive than int cmoves
2146   return 0;
2147 }
2148 
2149 const int Matcher::float_cmove_cost() {
2150   // float cmoves are no more expensive than int cmoves
2151   return 0;
2152 }
2153 
2154 // Does the CPU require late expand (see block.cpp for description of late expand)?
2155 const bool Matcher::require_postalloc_expand = false;
2156 
2157 // Do we need to mask the count passed to shift instructions or does
2158 // the cpu only look at the lower 5/6 bits anyway?
2159 const bool Matcher::need_masked_shift_count = false;
2160 
2161 // This affects two different things:
2162 //  - how Decode nodes are matched
2163 //  - how ImplicitNullCheck opportunities are recognized
2164 // If true, the matcher will try to remove all Decodes and match them
2165 // (as operands) into nodes. NullChecks are not prepared to deal with
2166 // Decodes by final_graph_reshaping().
2167 // If false, final_graph_reshaping() forces the decode behind the Cmp
2168 // for a NullCheck. The matcher matches the Decode node into a register.
2169 // Implicit_null_check optimization moves the Decode along with the
2170 // memory operation back up before the NullCheck.
2171 bool Matcher::narrow_oop_use_complex_address() {
2172   return Universe::narrow_oop_shift() == 0;
2173 }
2174 
2175 bool Matcher::narrow_klass_use_complex_address() {
2176 // TODO
2177 // decide whether we need to set this to true
2178   return false;
2179 }
2180 
2181 bool Matcher::const_oop_prefer_decode() {
2182   // Prefer ConN+DecodeN over ConP in simple compressed oops mode.
2183   return Universe::narrow_oop_base() == NULL;
2184 }
2185 
2186 bool Matcher::const_klass_prefer_decode() {
2187   // Prefer ConNKlass+DecodeNKlass over ConP in simple compressed klass mode.
2188   return Universe::narrow_klass_base() == NULL;
2189 }
2190 
2191 // Is it better to copy float constants, or load them directly from
2192 // memory?  Intel can load a float constant from a direct address,
2193 // requiring no extra registers.  Most RISCs will have to materialize
2194 // an address into a register first, so they would do better to copy
2195 // the constant from stack.
2196 const bool Matcher::rematerialize_float_constants = false;
2197 
2198 // If CPU can load and store mis-aligned doubles directly then no
2199 // fixup is needed.  Else we split the double into 2 integer pieces
2200 // and move it piece-by-piece.  Only happens when passing doubles into
2201 // C code as the Java calling convention forces doubles to be aligned.
2202 const bool Matcher::misaligned_doubles_ok = true;
2203 
2204 // No-op on amd64
2205 void Matcher::pd_implicit_null_fixup(MachNode *node, uint idx) {
2206   Unimplemented();
2207 }
2208 
2209 // Advertise here if the CPU requires explicit rounding operations to
2210 // implement the UseStrictFP mode.
2211 const bool Matcher::strict_fp_requires_explicit_rounding = false;
2212 
2213 // Are floats converted to double when stored to stack during
2214 // deoptimization?
2215 bool Matcher::float_in_double() { return false; }
2216 
2217 // Do ints take an entire long register or just half?
2218 // The relevant question is how the int is callee-saved:
2219 // the whole long is written but de-opt'ing will have to extract
2220 // the relevant 32 bits.
2221 const bool Matcher::int_in_long = true;
2222 
2223 // Return whether or not this register is ever used as an argument.
2224 // This function is used on startup to build the trampoline stubs in
2225 // generateOptoStub.  Registers not mentioned will be killed by the VM
2226 // call in the trampoline, and arguments in those registers not be
2227 // available to the callee.
2228 bool Matcher::can_be_java_arg(int reg)
2229 {
2230   return
2231     reg ==  R0_num || reg == R0_H_num ||
2232     reg ==  R1_num || reg == R1_H_num ||
2233     reg ==  R2_num || reg == R2_H_num ||
2234     reg ==  R3_num || reg == R3_H_num ||
2235     reg ==  R4_num || reg == R4_H_num ||
2236     reg ==  R5_num || reg == R5_H_num ||
2237     reg ==  R6_num || reg == R6_H_num ||
2238     reg ==  R7_num || reg == R7_H_num ||
2239     reg ==  V0_num || reg == V0_H_num ||
2240     reg ==  V1_num || reg == V1_H_num ||
2241     reg ==  V2_num || reg == V2_H_num ||
2242     reg ==  V3_num || reg == V3_H_num ||
2243     reg ==  V4_num || reg == V4_H_num ||
2244     reg ==  V5_num || reg == V5_H_num ||
2245     reg ==  V6_num || reg == V6_H_num ||
2246     reg ==  V7_num || reg == V7_H_num;
2247 }
2248 
2249 bool Matcher::is_spillable_arg(int reg)
2250 {
2251   return can_be_java_arg(reg);
2252 }
2253 
2254 bool Matcher::use_asm_for_ldiv_by_con(jlong divisor) {
2255   return false;
2256 }
2257 
2258 RegMask Matcher::divI_proj_mask() {
2259   ShouldNotReachHere();
2260   return RegMask();
2261 }
2262 
2263 // Register for MODI projection of divmodI.
2264 RegMask Matcher::modI_proj_mask() {
2265   ShouldNotReachHere();
2266   return RegMask();
2267 }
2268 
2269 // Register for DIVL projection of divmodL.
2270 RegMask Matcher::divL_proj_mask() {
2271   ShouldNotReachHere();
2272   return RegMask();
2273 }
2274 
2275 // Register for MODL projection of divmodL.
2276 RegMask Matcher::modL_proj_mask() {
2277   ShouldNotReachHere();
2278   return RegMask();
2279 }
2280 
2281 const RegMask Matcher::method_handle_invoke_SP_save_mask() {
2282   return FP_REG_mask();
2283 }
2284 
2285 bool size_fits_all_mem_uses(AddPNode* addp, int shift) {
2286   for (DUIterator_Fast imax, i = addp->fast_outs(imax); i < imax; i++) {
2287     Node* u = addp->fast_out(i);
2288     if (u->is_Mem()) {
2289       int opsize = u->as_Mem()->memory_size();
2290       assert(opsize > 0, "unexpected memory operand size");
2291       if (u->as_Mem()->memory_size() != (1<<shift)) {
2292         return false;
2293       }
2294     }
2295   }
2296   return true;
2297 }
2298 
2299 const bool Matcher::convi2l_type_required = false;
2300 
2301 // Should the Matcher clone shifts on addressing modes, expecting them
2302 // to be subsumed into complex addressing expressions or compute them
2303 // into registers?
2304 bool Matcher::clone_address_expressions(AddPNode* m, Matcher::MStack& mstack, VectorSet& address_visited) {
2305   if (clone_base_plus_offset_address(m, mstack, address_visited)) {
2306     return true;
2307   }
2308 
2309   Node *off = m->in(AddPNode::Offset);
2310   if (off->Opcode() == Op_LShiftL && off->in(2)->is_Con() &&
2311       size_fits_all_mem_uses(m, off->in(2)->get_int()) &&
2312       // Are there other uses besides address expressions?
2313       !is_visited(off)) {
2314     address_visited.set(off->_idx); // Flag as address_visited
2315     mstack.push(off->in(2), Visit);
2316     Node *conv = off->in(1);
2317     if (conv->Opcode() == Op_ConvI2L &&
2318         // Are there other uses besides address expressions?
2319         !is_visited(conv)) {
2320       address_visited.set(conv->_idx); // Flag as address_visited
2321       mstack.push(conv->in(1), Pre_Visit);
2322     } else {
2323       mstack.push(conv, Pre_Visit);
2324     }
2325     address_visited.test_set(m->_idx); // Flag as address_visited
2326     mstack.push(m->in(AddPNode::Address), Pre_Visit);
2327     mstack.push(m->in(AddPNode::Base), Pre_Visit);
2328     return true;
2329   } else if (off->Opcode() == Op_ConvI2L &&
2330              // Are there other uses besides address expressions?
2331              !is_visited(off)) {
2332     address_visited.test_set(m->_idx); // Flag as address_visited
2333     address_visited.set(off->_idx); // Flag as address_visited
2334     mstack.push(off->in(1), Pre_Visit);
2335     mstack.push(m->in(AddPNode::Address), Pre_Visit);
2336     mstack.push(m->in(AddPNode::Base), Pre_Visit);
2337     return true;
2338   }
2339   return false;
2340 }
2341 
2342 void Compile::reshape_address(AddPNode* addp) {
2343 }
2344 
2345 
2346 #define MOV_VOLATILE(REG, BASE, INDEX, SCALE, DISP, SCRATCH, INSN)      \
2347   MacroAssembler _masm(&cbuf);                                          \
2348   {                                                                     \
2349     guarantee(INDEX == -1, "mode not permitted for volatile");          \
2350     guarantee(DISP == 0, "mode not permitted for volatile");            \
2351     guarantee(SCALE == 0, "mode not permitted for volatile");           \
2352     __ INSN(REG, as_Register(BASE));                                    \
2353   }
2354 
2355 typedef void (MacroAssembler::* mem_insn)(Register Rt, const Address &adr);
2356 typedef void (MacroAssembler::* mem_float_insn)(FloatRegister Rt, const Address &adr);
2357 typedef void (MacroAssembler::* mem_vector_insn)(FloatRegister Rt,
2358                                   MacroAssembler::SIMD_RegVariant T, const Address &adr);
2359 
2360   // Used for all non-volatile memory accesses.  The use of
2361   // $mem->opcode() to discover whether this pattern uses sign-extended
2362   // offsets is something of a kludge.
2363   static void loadStore(MacroAssembler masm, mem_insn insn,
2364                          Register reg, int opcode,
2365                          Register base, int index, int size, int disp)
2366   {
2367     Address::extend scale;
2368 
2369     // Hooboy, this is fugly.  We need a way to communicate to the
2370     // encoder that the index needs to be sign extended, so we have to
2371     // enumerate all the cases.
2372     switch (opcode) {
2373     case INDINDEXSCALEDI2L:
2374     case INDINDEXSCALEDI2LN:
2375     case INDINDEXI2L:
2376     case INDINDEXI2LN:
2377       scale = Address::sxtw(size);
2378       break;
2379     default:
2380       scale = Address::lsl(size);
2381     }
2382 
2383     if (index == -1) {
2384       (masm.*insn)(reg, Address(base, disp));
2385     } else {
2386       assert(disp == 0, "unsupported address mode: disp = %d", disp);
2387       (masm.*insn)(reg, Address(base, as_Register(index), scale));
2388     }
2389   }
2390 
2391   static void loadStore(MacroAssembler masm, mem_float_insn insn,
2392                          FloatRegister reg, int opcode,
2393                          Register base, int index, int size, int disp)
2394   {
2395     Address::extend scale;
2396 
2397     switch (opcode) {
2398     case INDINDEXSCALEDI2L:
2399     case INDINDEXSCALEDI2LN:
2400       scale = Address::sxtw(size);
2401       break;
2402     default:
2403       scale = Address::lsl(size);
2404     }
2405 
2406      if (index == -1) {
2407       (masm.*insn)(reg, Address(base, disp));
2408     } else {
2409       assert(disp == 0, "unsupported address mode: disp = %d", disp);
2410       (masm.*insn)(reg, Address(base, as_Register(index), scale));
2411     }
2412   }
2413 
2414   static void loadStore(MacroAssembler masm, mem_vector_insn insn,
2415                          FloatRegister reg, MacroAssembler::SIMD_RegVariant T,
2416                          int opcode, Register base, int index, int size, int disp)
2417   {
2418     if (index == -1) {
2419       (masm.*insn)(reg, T, Address(base, disp));
2420     } else {
2421       assert(disp == 0, "unsupported address mode");
2422       (masm.*insn)(reg, T, Address(base, as_Register(index), Address::lsl(size)));
2423     }
2424   }
2425 
2426 %}
2427 
2428 
2429 
2430 //----------ENCODING BLOCK-----------------------------------------------------
2431 // This block specifies the encoding classes used by the compiler to
2432 // output byte streams.  Encoding classes are parameterized macros
2433 // used by Machine Instruction Nodes in order to generate the bit
2434 // encoding of the instruction.  Operands specify their base encoding
2435 // interface with the interface keyword.  There are currently
2436 // supported four interfaces, REG_INTER, CONST_INTER, MEMORY_INTER, &
2437 // COND_INTER.  REG_INTER causes an operand to generate a function
2438 // which returns its register number when queried.  CONST_INTER causes
2439 // an operand to generate a function which returns the value of the
2440 // constant when queried.  MEMORY_INTER causes an operand to generate
2441 // four functions which return the Base Register, the Index Register,
2442 // the Scale Value, and the Offset Value of the operand when queried.
2443 // COND_INTER causes an operand to generate six functions which return
2444 // the encoding code (ie - encoding bits for the instruction)
2445 // associated with each basic boolean condition for a conditional
2446 // instruction.
2447 //
2448 // Instructions specify two basic values for encoding.  Again, a
2449 // function is available to check if the constant displacement is an
2450 // oop. They use the ins_encode keyword to specify their encoding
2451 // classes (which must be a sequence of enc_class names, and their
2452 // parameters, specified in the encoding block), and they use the
2453 // opcode keyword to specify, in order, their primary, secondary, and
2454 // tertiary opcode.  Only the opcode sections which a particular
2455 // instruction needs for encoding need to be specified.
2456 encode %{
2457   // Build emit functions for each basic byte or larger field in the
2458   // intel encoding scheme (opcode, rm, sib, immediate), and call them
2459   // from C++ code in the enc_class source block.  Emit functions will
2460   // live in the main source block for now.  In future, we can
2461   // generalize this by adding a syntax that specifies the sizes of
2462   // fields in an order, so that the adlc can build the emit functions
2463   // automagically
2464 
2465   // catch all for unimplemented encodings
2466   enc_class enc_unimplemented %{
2467     MacroAssembler _masm(&cbuf);
2468     __ unimplemented("C2 catch all");
2469   %}
2470 
2471   // BEGIN Non-volatile memory access
2472 
2473   enc_class aarch64_enc_ldrsbw(iRegI dst, memory mem) %{
2474     Register dst_reg = as_Register($dst$$reg);
2475     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldrsbw, dst_reg, $mem->opcode(),
2476                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2477   %}
2478 
2479   enc_class aarch64_enc_ldrsb(iRegI dst, memory mem) %{
2480     Register dst_reg = as_Register($dst$$reg);
2481     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldrsb, dst_reg, $mem->opcode(),
2482                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2483   %}
2484 
2485   enc_class aarch64_enc_ldrb(iRegI dst, memory mem) %{
2486     Register dst_reg = as_Register($dst$$reg);
2487     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldrb, dst_reg, $mem->opcode(),
2488                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2489   %}
2490 
2491   enc_class aarch64_enc_ldrb(iRegL dst, memory mem) %{
2492     Register dst_reg = as_Register($dst$$reg);
2493     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldrb, dst_reg, $mem->opcode(),
2494                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2495   %}
2496 
2497   enc_class aarch64_enc_ldrshw(iRegI dst, memory mem) %{
2498     Register dst_reg = as_Register($dst$$reg);
2499     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldrshw, dst_reg, $mem->opcode(),
2500                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2501   %}
2502 
2503   enc_class aarch64_enc_ldrsh(iRegI dst, memory mem) %{
2504     Register dst_reg = as_Register($dst$$reg);
2505     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldrsh, dst_reg, $mem->opcode(),
2506                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2507   %}
2508 
2509   enc_class aarch64_enc_ldrh(iRegI dst, memory mem) %{
2510     Register dst_reg = as_Register($dst$$reg);
2511     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldrh, dst_reg, $mem->opcode(),
2512                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2513   %}
2514 
2515   enc_class aarch64_enc_ldrh(iRegL dst, memory mem) %{
2516     Register dst_reg = as_Register($dst$$reg);
2517     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldrh, dst_reg, $mem->opcode(),
2518                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2519   %}
2520 
2521   enc_class aarch64_enc_ldrw(iRegI dst, memory mem) %{
2522     Register dst_reg = as_Register($dst$$reg);
2523     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldrw, dst_reg, $mem->opcode(),
2524                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2525   %}
2526 
2527   enc_class aarch64_enc_ldrw(iRegL dst, memory mem) %{
2528     Register dst_reg = as_Register($dst$$reg);
2529     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldrw, dst_reg, $mem->opcode(),
2530                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2531   %}
2532 
2533   enc_class aarch64_enc_ldrsw(iRegL dst, memory mem) %{
2534     Register dst_reg = as_Register($dst$$reg);
2535     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldrsw, dst_reg, $mem->opcode(),
2536                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2537   %}
2538 
2539   enc_class aarch64_enc_ldr(iRegL dst, memory mem) %{
2540     Register dst_reg = as_Register($dst$$reg);
2541     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldr, dst_reg, $mem->opcode(),
2542                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2543   %}
2544 
2545   enc_class aarch64_enc_ldrs(vRegF dst, memory mem) %{
2546     FloatRegister dst_reg = as_FloatRegister($dst$$reg);
2547     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldrs, dst_reg, $mem->opcode(),
2548                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2549   %}
2550 
2551   enc_class aarch64_enc_ldrd(vRegD dst, memory mem) %{
2552     FloatRegister dst_reg = as_FloatRegister($dst$$reg);
2553     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldrd, dst_reg, $mem->opcode(),
2554                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2555   %}
2556 
2557   enc_class aarch64_enc_ldrvS(vecD dst, memory mem) %{
2558     FloatRegister dst_reg = as_FloatRegister($dst$$reg);
2559     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldr, dst_reg, MacroAssembler::S,
2560        $mem->opcode(), as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2561   %}
2562 
2563   enc_class aarch64_enc_ldrvD(vecD dst, memory mem) %{
2564     FloatRegister dst_reg = as_FloatRegister($dst$$reg);
2565     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldr, dst_reg, MacroAssembler::D,
2566        $mem->opcode(), as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2567   %}
2568 
2569   enc_class aarch64_enc_ldrvQ(vecX dst, memory mem) %{
2570     FloatRegister dst_reg = as_FloatRegister($dst$$reg);
2571     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldr, dst_reg, MacroAssembler::Q,
2572        $mem->opcode(), as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2573   %}
2574 
2575   enc_class aarch64_enc_strb(iRegI src, memory mem) %{
2576     Register src_reg = as_Register($src$$reg);
2577     loadStore(MacroAssembler(&cbuf), &MacroAssembler::strb, src_reg, $mem->opcode(),
2578                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2579   %}
2580 
2581   enc_class aarch64_enc_strb0(memory mem) %{
2582     MacroAssembler _masm(&cbuf);
2583     loadStore(_masm, &MacroAssembler::strb, zr, $mem->opcode(),
2584                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2585   %}
2586 
2587   enc_class aarch64_enc_strb0_ordered(memory mem) %{
2588     MacroAssembler _masm(&cbuf);
2589     __ membar(Assembler::StoreStore);
2590     loadStore(_masm, &MacroAssembler::strb, zr, $mem->opcode(),
2591                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2592   %}
2593 
2594   enc_class aarch64_enc_strh(iRegI src, memory mem) %{
2595     Register src_reg = as_Register($src$$reg);
2596     loadStore(MacroAssembler(&cbuf), &MacroAssembler::strh, src_reg, $mem->opcode(),
2597                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2598   %}
2599 
2600   enc_class aarch64_enc_strh0(memory mem) %{
2601     MacroAssembler _masm(&cbuf);
2602     loadStore(_masm, &MacroAssembler::strh, zr, $mem->opcode(),
2603                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2604   %}
2605 
2606   enc_class aarch64_enc_strw(iRegI src, memory mem) %{
2607     Register src_reg = as_Register($src$$reg);
2608     loadStore(MacroAssembler(&cbuf), &MacroAssembler::strw, src_reg, $mem->opcode(),
2609                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2610   %}
2611 
2612   enc_class aarch64_enc_strw0(memory mem) %{
2613     MacroAssembler _masm(&cbuf);
2614     loadStore(_masm, &MacroAssembler::strw, zr, $mem->opcode(),
2615                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2616   %}
2617 
2618   enc_class aarch64_enc_str(iRegL src, memory mem) %{
2619     Register src_reg = as_Register($src$$reg);
2620     // we sometimes get asked to store the stack pointer into the
2621     // current thread -- we cannot do that directly on AArch64
2622     if (src_reg == r31_sp) {
2623       MacroAssembler _masm(&cbuf);
2624       assert(as_Register($mem$$base) == rthread, "unexpected store for sp");
2625       __ mov(rscratch2, sp);
2626       src_reg = rscratch2;
2627     }
2628     loadStore(MacroAssembler(&cbuf), &MacroAssembler::str, src_reg, $mem->opcode(),
2629                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2630   %}
2631 
2632   enc_class aarch64_enc_str0(memory mem) %{
2633     MacroAssembler _masm(&cbuf);
2634     loadStore(_masm, &MacroAssembler::str, zr, $mem->opcode(),
2635                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2636   %}
2637 
2638   enc_class aarch64_enc_strs(vRegF src, memory mem) %{
2639     FloatRegister src_reg = as_FloatRegister($src$$reg);
2640     loadStore(MacroAssembler(&cbuf), &MacroAssembler::strs, src_reg, $mem->opcode(),
2641                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2642   %}
2643 
2644   enc_class aarch64_enc_strd(vRegD src, memory mem) %{
2645     FloatRegister src_reg = as_FloatRegister($src$$reg);
2646     loadStore(MacroAssembler(&cbuf), &MacroAssembler::strd, src_reg, $mem->opcode(),
2647                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2648   %}
2649 
2650   enc_class aarch64_enc_strvS(vecD src, memory mem) %{
2651     FloatRegister src_reg = as_FloatRegister($src$$reg);
2652     loadStore(MacroAssembler(&cbuf), &MacroAssembler::str, src_reg, MacroAssembler::S,
2653        $mem->opcode(), as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2654   %}
2655 
2656   enc_class aarch64_enc_strvD(vecD src, memory mem) %{
2657     FloatRegister src_reg = as_FloatRegister($src$$reg);
2658     loadStore(MacroAssembler(&cbuf), &MacroAssembler::str, src_reg, MacroAssembler::D,
2659        $mem->opcode(), as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2660   %}
2661 
2662   enc_class aarch64_enc_strvQ(vecX src, memory mem) %{
2663     FloatRegister src_reg = as_FloatRegister($src$$reg);
2664     loadStore(MacroAssembler(&cbuf), &MacroAssembler::str, src_reg, MacroAssembler::Q,
2665        $mem->opcode(), as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
2666   %}
2667 
2668   // END Non-volatile memory access
2669 
2670   // volatile loads and stores
2671 
2672   enc_class aarch64_enc_stlrb(iRegI src, memory mem) %{
2673     MOV_VOLATILE(as_Register($src$$reg), $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2674                  rscratch1, stlrb);
2675   %}
2676 
2677   enc_class aarch64_enc_stlrh(iRegI src, memory mem) %{
2678     MOV_VOLATILE(as_Register($src$$reg), $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2679                  rscratch1, stlrh);
2680   %}
2681 
2682   enc_class aarch64_enc_stlrw(iRegI src, memory mem) %{
2683     MOV_VOLATILE(as_Register($src$$reg), $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2684                  rscratch1, stlrw);
2685   %}
2686 
2687 
2688   enc_class aarch64_enc_ldarsbw(iRegI dst, memory mem) %{
2689     Register dst_reg = as_Register($dst$$reg);
2690     MOV_VOLATILE(dst_reg, $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2691              rscratch1, ldarb);
2692     __ sxtbw(dst_reg, dst_reg);
2693   %}
2694 
2695   enc_class aarch64_enc_ldarsb(iRegL dst, memory mem) %{
2696     Register dst_reg = as_Register($dst$$reg);
2697     MOV_VOLATILE(dst_reg, $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2698              rscratch1, ldarb);
2699     __ sxtb(dst_reg, dst_reg);
2700   %}
2701 
2702   enc_class aarch64_enc_ldarbw(iRegI dst, memory mem) %{
2703     MOV_VOLATILE(as_Register($dst$$reg), $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2704              rscratch1, ldarb);
2705   %}
2706 
2707   enc_class aarch64_enc_ldarb(iRegL dst, memory mem) %{
2708     MOV_VOLATILE(as_Register($dst$$reg), $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2709              rscratch1, ldarb);
2710   %}
2711 
2712   enc_class aarch64_enc_ldarshw(iRegI dst, memory mem) %{
2713     Register dst_reg = as_Register($dst$$reg);
2714     MOV_VOLATILE(dst_reg, $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2715              rscratch1, ldarh);
2716     __ sxthw(dst_reg, dst_reg);
2717   %}
2718 
2719   enc_class aarch64_enc_ldarsh(iRegL dst, memory mem) %{
2720     Register dst_reg = as_Register($dst$$reg);
2721     MOV_VOLATILE(dst_reg, $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2722              rscratch1, ldarh);
2723     __ sxth(dst_reg, dst_reg);
2724   %}
2725 
2726   enc_class aarch64_enc_ldarhw(iRegI dst, memory mem) %{
2727     MOV_VOLATILE(as_Register($dst$$reg), $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2728              rscratch1, ldarh);
2729   %}
2730 
2731   enc_class aarch64_enc_ldarh(iRegL dst, memory mem) %{
2732     MOV_VOLATILE(as_Register($dst$$reg), $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2733              rscratch1, ldarh);
2734   %}
2735 
2736   enc_class aarch64_enc_ldarw(iRegI dst, memory mem) %{
2737     MOV_VOLATILE(as_Register($dst$$reg), $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2738              rscratch1, ldarw);
2739   %}
2740 
2741   enc_class aarch64_enc_ldarw(iRegL dst, memory mem) %{
2742     MOV_VOLATILE(as_Register($dst$$reg), $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2743              rscratch1, ldarw);
2744   %}
2745 
2746   enc_class aarch64_enc_ldar(iRegL dst, memory mem) %{
2747     MOV_VOLATILE(as_Register($dst$$reg), $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2748              rscratch1, ldar);
2749   %}
2750 
2751   enc_class aarch64_enc_fldars(vRegF dst, memory mem) %{
2752     MOV_VOLATILE(rscratch1, $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2753              rscratch1, ldarw);
2754     __ fmovs(as_FloatRegister($dst$$reg), rscratch1);
2755   %}
2756 
2757   enc_class aarch64_enc_fldard(vRegD dst, memory mem) %{
2758     MOV_VOLATILE(rscratch1, $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2759              rscratch1, ldar);
2760     __ fmovd(as_FloatRegister($dst$$reg), rscratch1);
2761   %}
2762 
2763   enc_class aarch64_enc_stlr(iRegL src, memory mem) %{
2764     Register src_reg = as_Register($src$$reg);
2765     // we sometimes get asked to store the stack pointer into the
2766     // current thread -- we cannot do that directly on AArch64
2767     if (src_reg == r31_sp) {
2768         MacroAssembler _masm(&cbuf);
2769       assert(as_Register($mem$$base) == rthread, "unexpected store for sp");
2770       __ mov(rscratch2, sp);
2771       src_reg = rscratch2;
2772     }
2773     MOV_VOLATILE(src_reg, $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2774                  rscratch1, stlr);
2775   %}
2776 
2777   enc_class aarch64_enc_fstlrs(vRegF src, memory mem) %{
2778     {
2779       MacroAssembler _masm(&cbuf);
2780       FloatRegister src_reg = as_FloatRegister($src$$reg);
2781       __ fmovs(rscratch2, src_reg);
2782     }
2783     MOV_VOLATILE(rscratch2, $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2784                  rscratch1, stlrw);
2785   %}
2786 
2787   enc_class aarch64_enc_fstlrd(vRegD src, memory mem) %{
2788     {
2789       MacroAssembler _masm(&cbuf);
2790       FloatRegister src_reg = as_FloatRegister($src$$reg);
2791       __ fmovd(rscratch2, src_reg);
2792     }
2793     MOV_VOLATILE(rscratch2, $mem$$base, $mem$$index, $mem$$scale, $mem$$disp,
2794                  rscratch1, stlr);
2795   %}
2796 
2797   // synchronized read/update encodings
2798 
2799   enc_class aarch64_enc_ldaxr(iRegL dst, memory mem) %{
2800     MacroAssembler _masm(&cbuf);
2801     Register dst_reg = as_Register($dst$$reg);
2802     Register base = as_Register($mem$$base);
2803     int index = $mem$$index;
2804     int scale = $mem$$scale;
2805     int disp = $mem$$disp;
2806     if (index == -1) {
2807        if (disp != 0) {
2808         __ lea(rscratch1, Address(base, disp));
2809         __ ldaxr(dst_reg, rscratch1);
2810       } else {
2811         // TODO
2812         // should we ever get anything other than this case?
2813         __ ldaxr(dst_reg, base);
2814       }
2815     } else {
2816       Register index_reg = as_Register(index);
2817       if (disp == 0) {
2818         __ lea(rscratch1, Address(base, index_reg, Address::lsl(scale)));
2819         __ ldaxr(dst_reg, rscratch1);
2820       } else {
2821         __ lea(rscratch1, Address(base, disp));
2822         __ lea(rscratch1, Address(rscratch1, index_reg, Address::lsl(scale)));
2823         __ ldaxr(dst_reg, rscratch1);
2824       }
2825     }
2826   %}
2827 
2828   enc_class aarch64_enc_stlxr(iRegLNoSp src, memory mem) %{
2829     MacroAssembler _masm(&cbuf);
2830     Register src_reg = as_Register($src$$reg);
2831     Register base = as_Register($mem$$base);
2832     int index = $mem$$index;
2833     int scale = $mem$$scale;
2834     int disp = $mem$$disp;
2835     if (index == -1) {
2836        if (disp != 0) {
2837         __ lea(rscratch2, Address(base, disp));
2838         __ stlxr(rscratch1, src_reg, rscratch2);
2839       } else {
2840         // TODO
2841         // should we ever get anything other than this case?
2842         __ stlxr(rscratch1, src_reg, base);
2843       }
2844     } else {
2845       Register index_reg = as_Register(index);
2846       if (disp == 0) {
2847         __ lea(rscratch2, Address(base, index_reg, Address::lsl(scale)));
2848         __ stlxr(rscratch1, src_reg, rscratch2);
2849       } else {
2850         __ lea(rscratch2, Address(base, disp));
2851         __ lea(rscratch2, Address(rscratch2, index_reg, Address::lsl(scale)));
2852         __ stlxr(rscratch1, src_reg, rscratch2);
2853       }
2854     }
2855     __ cmpw(rscratch1, zr);
2856   %}
2857 
2858   enc_class aarch64_enc_cmpxchg(memory mem, iRegLNoSp oldval, iRegLNoSp newval) %{
2859     MacroAssembler _masm(&cbuf);
2860     guarantee($mem$$index == -1 && $mem$$disp == 0, "impossible encoding");
2861     __ cmpxchg($mem$$base$$Register, $oldval$$Register, $newval$$Register,
2862                Assembler::xword, /*acquire*/ false, /*release*/ true,
2863                /*weak*/ false, noreg);
2864   %}
2865 
2866   enc_class aarch64_enc_cmpxchgw(memory mem, iRegINoSp oldval, iRegINoSp newval) %{
2867     MacroAssembler _masm(&cbuf);
2868     guarantee($mem$$index == -1 && $mem$$disp == 0, "impossible encoding");
2869     __ cmpxchg($mem$$base$$Register, $oldval$$Register, $newval$$Register,
2870                Assembler::word, /*acquire*/ false, /*release*/ true,
2871                /*weak*/ false, noreg);
2872   %}
2873 
2874   enc_class aarch64_enc_cmpxchgs(memory mem, iRegINoSp oldval, iRegINoSp newval) %{
2875     MacroAssembler _masm(&cbuf);
2876     guarantee($mem$$index == -1 && $mem$$disp == 0, "impossible encoding");
2877     __ cmpxchg($mem$$base$$Register, $oldval$$Register, $newval$$Register,
2878                Assembler::halfword, /*acquire*/ false, /*release*/ true,
2879                /*weak*/ false, noreg);
2880   %}
2881 
2882   enc_class aarch64_enc_cmpxchgb(memory mem, iRegINoSp oldval, iRegINoSp newval) %{
2883     MacroAssembler _masm(&cbuf);
2884     guarantee($mem$$index == -1 && $mem$$disp == 0, "impossible encoding");
2885     __ cmpxchg($mem$$base$$Register, $oldval$$Register, $newval$$Register,
2886                Assembler::byte, /*acquire*/ false, /*release*/ true,
2887                /*weak*/ false, noreg);
2888   %}
2889 
2890 
2891   // The only difference between aarch64_enc_cmpxchg and
2892   // aarch64_enc_cmpxchg_acq is that we use load-acquire in the
2893   // CompareAndSwap sequence to serve as a barrier on acquiring a
2894   // lock.
2895   enc_class aarch64_enc_cmpxchg_acq(memory mem, iRegLNoSp oldval, iRegLNoSp newval) %{
2896     MacroAssembler _masm(&cbuf);
2897     guarantee($mem$$index == -1 && $mem$$disp == 0, "impossible encoding");
2898     __ cmpxchg($mem$$base$$Register, $oldval$$Register, $newval$$Register,
2899                Assembler::xword, /*acquire*/ true, /*release*/ true,
2900                /*weak*/ false, noreg);
2901   %}
2902 
2903   enc_class aarch64_enc_cmpxchgw_acq(memory mem, iRegINoSp oldval, iRegINoSp newval) %{
2904     MacroAssembler _masm(&cbuf);
2905     guarantee($mem$$index == -1 && $mem$$disp == 0, "impossible encoding");
2906     __ cmpxchg($mem$$base$$Register, $oldval$$Register, $newval$$Register,
2907                Assembler::word, /*acquire*/ true, /*release*/ true,
2908                /*weak*/ false, noreg);
2909   %}
2910 
2911   enc_class aarch64_enc_cmpxchgs_acq(memory mem, iRegINoSp oldval, iRegINoSp newval) %{
2912     MacroAssembler _masm(&cbuf);
2913     guarantee($mem$$index == -1 && $mem$$disp == 0, "impossible encoding");
2914     __ cmpxchg($mem$$base$$Register, $oldval$$Register, $newval$$Register,
2915                Assembler::halfword, /*acquire*/ true, /*release*/ true,
2916                /*weak*/ false, noreg);
2917   %}
2918 
2919   enc_class aarch64_enc_cmpxchgb_acq(memory mem, iRegINoSp oldval, iRegINoSp newval) %{
2920     MacroAssembler _masm(&cbuf);
2921     guarantee($mem$$index == -1 && $mem$$disp == 0, "impossible encoding");
2922     __ cmpxchg($mem$$base$$Register, $oldval$$Register, $newval$$Register,
2923                Assembler::byte, /*acquire*/ true, /*release*/ true,
2924                /*weak*/ false, noreg);
2925   %}
2926 
2927   // auxiliary used for CompareAndSwapX to set result register
2928   enc_class aarch64_enc_cset_eq(iRegINoSp res) %{
2929     MacroAssembler _masm(&cbuf);
2930     Register res_reg = as_Register($res$$reg);
2931     __ cset(res_reg, Assembler::EQ);
2932   %}
2933 
2934   // prefetch encodings
2935 
2936   enc_class aarch64_enc_prefetchw(memory mem) %{
2937     MacroAssembler _masm(&cbuf);
2938     Register base = as_Register($mem$$base);
2939     int index = $mem$$index;
2940     int scale = $mem$$scale;
2941     int disp = $mem$$disp;
2942     if (index == -1) {
2943       __ prfm(Address(base, disp), PSTL1KEEP);
2944     } else {
2945       Register index_reg = as_Register(index);
2946       if (disp == 0) {
2947         __ prfm(Address(base, index_reg, Address::lsl(scale)), PSTL1KEEP);
2948       } else {
2949         __ lea(rscratch1, Address(base, disp));
2950         __ prfm(Address(rscratch1, index_reg, Address::lsl(scale)), PSTL1KEEP);
2951       }
2952     }
2953   %}
2954 
2955   /// mov envcodings
2956 
2957   enc_class aarch64_enc_movw_imm(iRegI dst, immI src) %{
2958     MacroAssembler _masm(&cbuf);
2959     u_int32_t con = (u_int32_t)$src$$constant;
2960     Register dst_reg = as_Register($dst$$reg);
2961     if (con == 0) {
2962       __ movw(dst_reg, zr);
2963     } else {
2964       __ movw(dst_reg, con);
2965     }
2966   %}
2967 
2968   enc_class aarch64_enc_mov_imm(iRegL dst, immL src) %{
2969     MacroAssembler _masm(&cbuf);
2970     Register dst_reg = as_Register($dst$$reg);
2971     u_int64_t con = (u_int64_t)$src$$constant;
2972     if (con == 0) {
2973       __ mov(dst_reg, zr);
2974     } else {
2975       __ mov(dst_reg, con);
2976     }
2977   %}
2978 
2979   enc_class aarch64_enc_mov_p(iRegP dst, immP src) %{
2980     MacroAssembler _masm(&cbuf);
2981     Register dst_reg = as_Register($dst$$reg);
2982     address con = (address)$src$$constant;
2983     if (con == NULL || con == (address)1) {
2984       ShouldNotReachHere();
2985     } else {
2986       relocInfo::relocType rtype = $src->constant_reloc();
2987       if (rtype == relocInfo::oop_type) {
2988         __ movoop(dst_reg, (jobject)con, /*immediate*/true);
2989       } else if (rtype == relocInfo::metadata_type) {
2990         __ mov_metadata(dst_reg, (Metadata*)con);
2991       } else {
2992         assert(rtype == relocInfo::none, "unexpected reloc type");
2993         if (con < (address)(uintptr_t)os::vm_page_size()) {
2994           __ mov(dst_reg, con);
2995         } else {
2996           unsigned long offset;
2997           __ adrp(dst_reg, con, offset);
2998           __ add(dst_reg, dst_reg, offset);
2999         }
3000       }
3001     }
3002   %}
3003 
3004   enc_class aarch64_enc_mov_p0(iRegP dst, immP0 src) %{
3005     MacroAssembler _masm(&cbuf);
3006     Register dst_reg = as_Register($dst$$reg);
3007     __ mov(dst_reg, zr);
3008   %}
3009 
3010   enc_class aarch64_enc_mov_p1(iRegP dst, immP_1 src) %{
3011     MacroAssembler _masm(&cbuf);
3012     Register dst_reg = as_Register($dst$$reg);
3013     __ mov(dst_reg, (u_int64_t)1);
3014   %}
3015 
3016   enc_class aarch64_enc_mov_poll_page(iRegP dst, immPollPage src) %{
3017     MacroAssembler _masm(&cbuf);
3018     address page = (address)$src$$constant;
3019     Register dst_reg = as_Register($dst$$reg);
3020     unsigned long off;
3021     __ adrp(dst_reg, Address(page, relocInfo::poll_type), off);
3022     assert(off == 0, "assumed offset == 0");
3023   %}
3024 
3025   enc_class aarch64_enc_mov_byte_map_base(iRegP dst, immByteMapBase src) %{
3026     MacroAssembler _masm(&cbuf);
3027     __ load_byte_map_base($dst$$Register);
3028   %}
3029 
3030   enc_class aarch64_enc_mov_n(iRegN dst, immN src) %{
3031     MacroAssembler _masm(&cbuf);
3032     Register dst_reg = as_Register($dst$$reg);
3033     address con = (address)$src$$constant;
3034     if (con == NULL) {
3035       ShouldNotReachHere();
3036     } else {
3037       relocInfo::relocType rtype = $src->constant_reloc();
3038       assert(rtype == relocInfo::oop_type, "unexpected reloc type");
3039       __ set_narrow_oop(dst_reg, (jobject)con);
3040     }
3041   %}
3042 
3043   enc_class aarch64_enc_mov_n0(iRegN dst, immN0 src) %{
3044     MacroAssembler _masm(&cbuf);
3045     Register dst_reg = as_Register($dst$$reg);
3046     __ mov(dst_reg, zr);
3047   %}
3048 
3049   enc_class aarch64_enc_mov_nk(iRegN dst, immNKlass src) %{
3050     MacroAssembler _masm(&cbuf);
3051     Register dst_reg = as_Register($dst$$reg);
3052     address con = (address)$src$$constant;
3053     if (con == NULL) {
3054       ShouldNotReachHere();
3055     } else {
3056       relocInfo::relocType rtype = $src->constant_reloc();
3057       assert(rtype == relocInfo::metadata_type, "unexpected reloc type");
3058       __ set_narrow_klass(dst_reg, (Klass *)con);
3059     }
3060   %}
3061 
3062   // arithmetic encodings
3063 
3064   enc_class aarch64_enc_addsubw_imm(iRegI dst, iRegI src1, immIAddSub src2) %{
3065     MacroAssembler _masm(&cbuf);
3066     Register dst_reg = as_Register($dst$$reg);
3067     Register src_reg = as_Register($src1$$reg);
3068     int32_t con = (int32_t)$src2$$constant;
3069     // add has primary == 0, subtract has primary == 1
3070     if ($primary) { con = -con; }
3071     if (con < 0) {
3072       __ subw(dst_reg, src_reg, -con);
3073     } else {
3074       __ addw(dst_reg, src_reg, con);
3075     }
3076   %}
3077 
3078   enc_class aarch64_enc_addsub_imm(iRegL dst, iRegL src1, immLAddSub src2) %{
3079     MacroAssembler _masm(&cbuf);
3080     Register dst_reg = as_Register($dst$$reg);
3081     Register src_reg = as_Register($src1$$reg);
3082     int32_t con = (int32_t)$src2$$constant;
3083     // add has primary == 0, subtract has primary == 1
3084     if ($primary) { con = -con; }
3085     if (con < 0) {
3086       __ sub(dst_reg, src_reg, -con);
3087     } else {
3088       __ add(dst_reg, src_reg, con);
3089     }
3090   %}
3091 
3092   enc_class aarch64_enc_divw(iRegI dst, iRegI src1, iRegI src2) %{
3093     MacroAssembler _masm(&cbuf);
3094    Register dst_reg = as_Register($dst$$reg);
3095    Register src1_reg = as_Register($src1$$reg);
3096    Register src2_reg = as_Register($src2$$reg);
3097     __ corrected_idivl(dst_reg, src1_reg, src2_reg, false, rscratch1);
3098   %}
3099 
3100   enc_class aarch64_enc_div(iRegI dst, iRegI src1, iRegI src2) %{
3101     MacroAssembler _masm(&cbuf);
3102    Register dst_reg = as_Register($dst$$reg);
3103    Register src1_reg = as_Register($src1$$reg);
3104    Register src2_reg = as_Register($src2$$reg);
3105     __ corrected_idivq(dst_reg, src1_reg, src2_reg, false, rscratch1);
3106   %}
3107 
3108   enc_class aarch64_enc_modw(iRegI dst, iRegI src1, iRegI src2) %{
3109     MacroAssembler _masm(&cbuf);
3110    Register dst_reg = as_Register($dst$$reg);
3111    Register src1_reg = as_Register($src1$$reg);
3112    Register src2_reg = as_Register($src2$$reg);
3113     __ corrected_idivl(dst_reg, src1_reg, src2_reg, true, rscratch1);
3114   %}
3115 
3116   enc_class aarch64_enc_mod(iRegI dst, iRegI src1, iRegI src2) %{
3117     MacroAssembler _masm(&cbuf);
3118    Register dst_reg = as_Register($dst$$reg);
3119    Register src1_reg = as_Register($src1$$reg);
3120    Register src2_reg = as_Register($src2$$reg);
3121     __ corrected_idivq(dst_reg, src1_reg, src2_reg, true, rscratch1);
3122   %}
3123 
3124   // compare instruction encodings
3125 
3126   enc_class aarch64_enc_cmpw(iRegI src1, iRegI src2) %{
3127     MacroAssembler _masm(&cbuf);
3128     Register reg1 = as_Register($src1$$reg);
3129     Register reg2 = as_Register($src2$$reg);
3130     __ cmpw(reg1, reg2);
3131   %}
3132 
3133   enc_class aarch64_enc_cmpw_imm_addsub(iRegI src1, immIAddSub src2) %{
3134     MacroAssembler _masm(&cbuf);
3135     Register reg = as_Register($src1$$reg);
3136     int32_t val = $src2$$constant;
3137     if (val >= 0) {
3138       __ subsw(zr, reg, val);
3139     } else {
3140       __ addsw(zr, reg, -val);
3141     }
3142   %}
3143 
3144   enc_class aarch64_enc_cmpw_imm(iRegI src1, immI src2) %{
3145     MacroAssembler _masm(&cbuf);
3146     Register reg1 = as_Register($src1$$reg);
3147     u_int32_t val = (u_int32_t)$src2$$constant;
3148     __ movw(rscratch1, val);
3149     __ cmpw(reg1, rscratch1);
3150   %}
3151 
3152   enc_class aarch64_enc_cmp(iRegL src1, iRegL src2) %{
3153     MacroAssembler _masm(&cbuf);
3154     Register reg1 = as_Register($src1$$reg);
3155     Register reg2 = as_Register($src2$$reg);
3156     __ cmp(reg1, reg2);
3157   %}
3158 
3159   enc_class aarch64_enc_cmp_imm_addsub(iRegL src1, immL12 src2) %{
3160     MacroAssembler _masm(&cbuf);
3161     Register reg = as_Register($src1$$reg);
3162     int64_t val = $src2$$constant;
3163     if (val >= 0) {
3164       __ subs(zr, reg, val);
3165     } else if (val != -val) {
3166       __ adds(zr, reg, -val);
3167     } else {
3168     // aargh, Long.MIN_VALUE is a special case
3169       __ orr(rscratch1, zr, (u_int64_t)val);
3170       __ subs(zr, reg, rscratch1);
3171     }
3172   %}
3173 
3174   enc_class aarch64_enc_cmp_imm(iRegL src1, immL src2) %{
3175     MacroAssembler _masm(&cbuf);
3176     Register reg1 = as_Register($src1$$reg);
3177     u_int64_t val = (u_int64_t)$src2$$constant;
3178     __ mov(rscratch1, val);
3179     __ cmp(reg1, rscratch1);
3180   %}
3181 
3182   enc_class aarch64_enc_cmpp(iRegP src1, iRegP src2) %{
3183     MacroAssembler _masm(&cbuf);
3184     Register reg1 = as_Register($src1$$reg);
3185     Register reg2 = as_Register($src2$$reg);
3186     __ cmp(reg1, reg2);
3187   %}
3188 
3189   enc_class aarch64_enc_cmpn(iRegN src1, iRegN src2) %{
3190     MacroAssembler _masm(&cbuf);
3191     Register reg1 = as_Register($src1$$reg);
3192     Register reg2 = as_Register($src2$$reg);
3193     __ cmpw(reg1, reg2);
3194   %}
3195 
3196   enc_class aarch64_enc_testp(iRegP src) %{
3197     MacroAssembler _masm(&cbuf);
3198     Register reg = as_Register($src$$reg);
3199     __ cmp(reg, zr);
3200   %}
3201 
3202   enc_class aarch64_enc_testn(iRegN src) %{
3203     MacroAssembler _masm(&cbuf);
3204     Register reg = as_Register($src$$reg);
3205     __ cmpw(reg, zr);
3206   %}
3207 
3208   enc_class aarch64_enc_b(label lbl) %{
3209     MacroAssembler _masm(&cbuf);
3210     Label *L = $lbl$$label;
3211     __ b(*L);
3212   %}
3213 
3214   enc_class aarch64_enc_br_con(cmpOp cmp, label lbl) %{
3215     MacroAssembler _masm(&cbuf);
3216     Label *L = $lbl$$label;
3217     __ br ((Assembler::Condition)$cmp$$cmpcode, *L);
3218   %}
3219 
3220   enc_class aarch64_enc_br_conU(cmpOpU cmp, label lbl) %{
3221     MacroAssembler _masm(&cbuf);
3222     Label *L = $lbl$$label;
3223     __ br ((Assembler::Condition)$cmp$$cmpcode, *L);
3224   %}
3225 
3226   enc_class aarch64_enc_partial_subtype_check(iRegP sub, iRegP super, iRegP temp, iRegP result)
3227   %{
3228      Register sub_reg = as_Register($sub$$reg);
3229      Register super_reg = as_Register($super$$reg);
3230      Register temp_reg = as_Register($temp$$reg);
3231      Register result_reg = as_Register($result$$reg);
3232 
3233      Label miss;
3234      MacroAssembler _masm(&cbuf);
3235      __ check_klass_subtype_slow_path(sub_reg, super_reg, temp_reg, result_reg,
3236                                      NULL, &miss,
3237                                      /*set_cond_codes:*/ true);
3238      if ($primary) {
3239        __ mov(result_reg, zr);
3240      }
3241      __ bind(miss);
3242   %}
3243 
3244   enc_class aarch64_enc_java_static_call(method meth) %{
3245     MacroAssembler _masm(&cbuf);
3246 
3247     address addr = (address)$meth$$method;
3248     address call;
3249     if (!_method) {
3250       // A call to a runtime wrapper, e.g. new, new_typeArray_Java, uncommon_trap.
3251       call = __ trampoline_call(Address(addr, relocInfo::runtime_call_type), &cbuf);
3252     } else {
3253       int method_index = resolved_method_index(cbuf);
3254       RelocationHolder rspec = _optimized_virtual ? opt_virtual_call_Relocation::spec(method_index)
3255                                                   : static_call_Relocation::spec(method_index);
3256       call = __ trampoline_call(Address(addr, rspec), &cbuf);
3257 
3258       // Emit stub for static call
3259       address stub = CompiledStaticCall::emit_to_interp_stub(cbuf);
3260       if (stub == NULL) {
3261         ciEnv::current()->record_failure("CodeCache is full");
3262         return;
3263       }
3264     }
3265     if (call == NULL) {
3266       ciEnv::current()->record_failure("CodeCache is full");
3267       return;
3268     }
3269   %}
3270 
3271   enc_class aarch64_enc_java_dynamic_call(method meth) %{
3272     MacroAssembler _masm(&cbuf);
3273     int method_index = resolved_method_index(cbuf);
3274     address call = __ ic_call((address)$meth$$method, method_index);
3275     if (call == NULL) {
3276       ciEnv::current()->record_failure("CodeCache is full");
3277       return;
3278     }
3279   %}
3280 
3281   enc_class aarch64_enc_call_epilog() %{
3282     MacroAssembler _masm(&cbuf);
3283     if (VerifyStackAtCalls) {
3284       // Check that stack depth is unchanged: find majik cookie on stack
3285       __ call_Unimplemented();
3286     }
3287   %}
3288 
3289   enc_class aarch64_enc_java_to_runtime(method meth) %{
3290     MacroAssembler _masm(&cbuf);
3291 
3292     // some calls to generated routines (arraycopy code) are scheduled
3293     // by C2 as runtime calls. if so we can call them using a br (they
3294     // will be in a reachable segment) otherwise we have to use a blr
3295     // which loads the absolute address into a register.
3296     address entry = (address)$meth$$method;
3297     CodeBlob *cb = CodeCache::find_blob(entry);
3298     if (cb) {
3299       address call = __ trampoline_call(Address(entry, relocInfo::runtime_call_type));
3300       if (call == NULL) {
3301         ciEnv::current()->record_failure("CodeCache is full");
3302         return;
3303       }
3304     } else {
3305       Label retaddr;
3306       __ adr(rscratch2, retaddr);
3307       __ lea(rscratch1, RuntimeAddress(entry));
3308       // Leave a breadcrumb for JavaFrameAnchor::capture_last_Java_pc()
3309       __ stp(zr, rscratch2, Address(__ pre(sp, -2 * wordSize)));
3310       __ blr(rscratch1);
3311       __ bind(retaddr);
3312       __ add(sp, sp, 2 * wordSize);
3313     }
3314   %}
3315 
3316   enc_class aarch64_enc_rethrow() %{
3317     MacroAssembler _masm(&cbuf);
3318     __ far_jump(RuntimeAddress(OptoRuntime::rethrow_stub()));
3319   %}
3320 
3321   enc_class aarch64_enc_ret() %{
3322     MacroAssembler _masm(&cbuf);
3323     __ ret(lr);
3324   %}
3325 
3326   enc_class aarch64_enc_tail_call(iRegP jump_target) %{
3327     MacroAssembler _masm(&cbuf);
3328     Register target_reg = as_Register($jump_target$$reg);
3329     __ br(target_reg);
3330   %}
3331 
3332   enc_class aarch64_enc_tail_jmp(iRegP jump_target) %{
3333     MacroAssembler _masm(&cbuf);
3334     Register target_reg = as_Register($jump_target$$reg);
3335     // exception oop should be in r0
3336     // ret addr has been popped into lr
3337     // callee expects it in r3
3338     __ mov(r3, lr);
3339     __ br(target_reg);
3340   %}
3341 
3342   enc_class aarch64_enc_fast_lock(iRegP object, iRegP box, iRegP tmp, iRegP tmp2) %{
3343     MacroAssembler _masm(&cbuf);
3344     Register oop = as_Register($object$$reg);
3345     Register box = as_Register($box$$reg);
3346     Register disp_hdr = as_Register($tmp$$reg);
3347     Register tmp = as_Register($tmp2$$reg);
3348     Label cont;
3349     Label object_has_monitor;
3350     Label cas_failed;
3351 
3352     assert_different_registers(oop, box, tmp, disp_hdr);
3353 
3354     // Load markOop from object into displaced_header.
3355     __ ldr(disp_hdr, Address(oop, oopDesc::mark_offset_in_bytes()));
3356 
3357     // Always do locking in runtime.
3358     if (EmitSync & 0x01) {
3359       __ cmp(oop, zr);
3360       return;
3361     }
3362 
3363     if (UseBiasedLocking && !UseOptoBiasInlining) {
3364       __ biased_locking_enter(box, oop, disp_hdr, tmp, true, cont);
3365     }
3366 
3367     // Check for existing monitor
3368     if ((EmitSync & 0x02) == 0) {
3369       __ tbnz(disp_hdr, exact_log2(markOopDesc::monitor_value), object_has_monitor);
3370     }
3371 
3372     // Set tmp to be (markOop of object | UNLOCK_VALUE).
3373     __ orr(tmp, disp_hdr, markOopDesc::unlocked_value);
3374 
3375     // Initialize the box. (Must happen before we update the object mark!)
3376     __ str(tmp, Address(box, BasicLock::displaced_header_offset_in_bytes()));
3377 
3378     // Compare object markOop with an unlocked value (tmp) and if
3379     // equal exchange the stack address of our box with object markOop.
3380     // On failure disp_hdr contains the possibly locked markOop.
3381     __ cmpxchg(oop, tmp, box, Assembler::xword, /*acquire*/ true,
3382                /*release*/ true, /*weak*/ false, disp_hdr);
3383     __ br(Assembler::EQ, cont);
3384 
3385     assert(oopDesc::mark_offset_in_bytes() == 0, "offset of _mark is not 0");
3386 
3387     // If the compare-and-exchange succeeded, then we found an unlocked
3388     // object, will have now locked it will continue at label cont
3389 
3390     __ bind(cas_failed);
3391     // We did not see an unlocked object so try the fast recursive case.
3392 
3393     // Check if the owner is self by comparing the value in the
3394     // markOop of object (disp_hdr) with the stack pointer.
3395     __ mov(rscratch1, sp);
3396     __ sub(disp_hdr, disp_hdr, rscratch1);
3397     __ mov(tmp, (address) (~(os::vm_page_size()-1) | (uintptr_t)markOopDesc::lock_mask_in_place));
3398     // If condition is true we are cont and hence we can store 0 as the
3399     // displaced header in the box, which indicates that it is a recursive lock.
3400     __ ands(tmp/*==0?*/, disp_hdr, tmp);   // Sets flags for result
3401     __ str(tmp/*==0, perhaps*/, Address(box, BasicLock::displaced_header_offset_in_bytes()));
3402 
3403     if ((EmitSync & 0x02) == 0) {
3404       __ b(cont);
3405 
3406       // Handle existing monitor.
3407       __ bind(object_has_monitor);
3408       // The object's monitor m is unlocked iff m->owner == NULL,
3409       // otherwise m->owner may contain a thread or a stack address.
3410       //
3411       // Try to CAS m->owner from NULL to current thread.
3412       __ add(tmp, disp_hdr, (ObjectMonitor::owner_offset_in_bytes()-markOopDesc::monitor_value));
3413     __ cmpxchg(tmp, zr, rthread, Assembler::xword, /*acquire*/ true,
3414                /*release*/ true, /*weak*/ false, noreg); // Sets flags for result
3415 
3416       // Store a non-null value into the box to avoid looking like a re-entrant
3417       // lock. The fast-path monitor unlock code checks for
3418       // markOopDesc::monitor_value so use markOopDesc::unused_mark which has the
3419       // relevant bit set, and also matches ObjectSynchronizer::slow_enter.
3420       __ mov(tmp, (address)markOopDesc::unused_mark());
3421       __ str(tmp, Address(box, BasicLock::displaced_header_offset_in_bytes()));
3422     }
3423 
3424     __ bind(cont);
3425     // flag == EQ indicates success
3426     // flag == NE indicates failure
3427   %}
3428 
3429   enc_class aarch64_enc_fast_unlock(iRegP object, iRegP box, iRegP tmp, iRegP tmp2) %{
3430     MacroAssembler _masm(&cbuf);
3431     Register oop = as_Register($object$$reg);
3432     Register box = as_Register($box$$reg);
3433     Register disp_hdr = as_Register($tmp$$reg);
3434     Register tmp = as_Register($tmp2$$reg);
3435     Label cont;
3436     Label object_has_monitor;
3437 
3438     assert_different_registers(oop, box, tmp, disp_hdr);
3439 
3440     // Always do locking in runtime.
3441     if (EmitSync & 0x01) {
3442       __ cmp(oop, zr); // Oop can't be 0 here => always false.
3443       return;
3444     }
3445 
3446     if (UseBiasedLocking && !UseOptoBiasInlining) {
3447       __ biased_locking_exit(oop, tmp, cont);
3448     }
3449 
3450     // Find the lock address and load the displaced header from the stack.
3451     __ ldr(disp_hdr, Address(box, BasicLock::displaced_header_offset_in_bytes()));
3452 
3453     // If the displaced header is 0, we have a recursive unlock.
3454     __ cmp(disp_hdr, zr);
3455     __ br(Assembler::EQ, cont);
3456 
3457     // Handle existing monitor.
3458     if ((EmitSync & 0x02) == 0) {
3459       __ ldr(tmp, Address(oop, oopDesc::mark_offset_in_bytes()));
3460       __ tbnz(disp_hdr, exact_log2(markOopDesc::monitor_value), object_has_monitor);
3461     }
3462 
3463     // Check if it is still a light weight lock, this is is true if we
3464     // see the stack address of the basicLock in the markOop of the
3465     // object.
3466 
3467     __ cmpxchg(oop, box, disp_hdr, Assembler::xword, /*acquire*/ false,
3468                /*release*/ true, /*weak*/ false, tmp);
3469     __ b(cont);
3470 
3471     assert(oopDesc::mark_offset_in_bytes() == 0, "offset of _mark is not 0");
3472 
3473     // Handle existing monitor.
3474     if ((EmitSync & 0x02) == 0) {
3475       __ bind(object_has_monitor);
3476       __ add(tmp, tmp, -markOopDesc::monitor_value); // monitor
3477       __ ldr(rscratch1, Address(tmp, ObjectMonitor::owner_offset_in_bytes()));
3478       __ ldr(disp_hdr, Address(tmp, ObjectMonitor::recursions_offset_in_bytes()));
3479       __ eor(rscratch1, rscratch1, rthread); // Will be 0 if we are the owner.
3480       __ orr(rscratch1, rscratch1, disp_hdr); // Will be 0 if there are 0 recursions
3481       __ cmp(rscratch1, zr); // Sets flags for result
3482       __ br(Assembler::NE, cont);
3483 
3484       __ ldr(rscratch1, Address(tmp, ObjectMonitor::EntryList_offset_in_bytes()));
3485       __ ldr(disp_hdr, Address(tmp, ObjectMonitor::cxq_offset_in_bytes()));
3486       __ orr(rscratch1, rscratch1, disp_hdr); // Will be 0 if both are 0.
3487       __ cmp(rscratch1, zr); // Sets flags for result
3488       __ cbnz(rscratch1, cont);
3489       // need a release store here
3490       __ lea(tmp, Address(tmp, ObjectMonitor::owner_offset_in_bytes()));
3491       __ stlr(zr, tmp); // set unowned
3492     }
3493 
3494     __ bind(cont);
3495     // flag == EQ indicates success
3496     // flag == NE indicates failure
3497   %}
3498 
3499 %}
3500 
3501 //----------FRAME--------------------------------------------------------------
3502 // Definition of frame structure and management information.
3503 //
3504 //  S T A C K   L A Y O U T    Allocators stack-slot number
3505 //                             |   (to get allocators register number
3506 //  G  Owned by    |        |  v    add OptoReg::stack0())
3507 //  r   CALLER     |        |
3508 //  o     |        +--------+      pad to even-align allocators stack-slot
3509 //  w     V        |  pad0  |        numbers; owned by CALLER
3510 //  t   -----------+--------+----> Matcher::_in_arg_limit, unaligned
3511 //  h     ^        |   in   |  5
3512 //        |        |  args  |  4   Holes in incoming args owned by SELF
3513 //  |     |        |        |  3
3514 //  |     |        +--------+
3515 //  V     |        | old out|      Empty on Intel, window on Sparc
3516 //        |    old |preserve|      Must be even aligned.
3517 //        |     SP-+--------+----> Matcher::_old_SP, even aligned
3518 //        |        |   in   |  3   area for Intel ret address
3519 //     Owned by    |preserve|      Empty on Sparc.
3520 //       SELF      +--------+
3521 //        |        |  pad2  |  2   pad to align old SP
3522 //        |        +--------+  1
3523 //        |        | locks  |  0
3524 //        |        +--------+----> OptoReg::stack0(), even aligned
3525 //        |        |  pad1  | 11   pad to align new SP
3526 //        |        +--------+
3527 //        |        |        | 10
3528 //        |        | spills |  9   spills
3529 //        V        |        |  8   (pad0 slot for callee)
3530 //      -----------+--------+----> Matcher::_out_arg_limit, unaligned
3531 //        ^        |  out   |  7
3532 //        |        |  args  |  6   Holes in outgoing args owned by CALLEE
3533 //     Owned by    +--------+
3534 //      CALLEE     | new out|  6   Empty on Intel, window on Sparc
3535 //        |    new |preserve|      Must be even-aligned.
3536 //        |     SP-+--------+----> Matcher::_new_SP, even aligned
3537 //        |        |        |
3538 //
3539 // Note 1: Only region 8-11 is determined by the allocator.  Region 0-5 is
3540 //         known from SELF's arguments and the Java calling convention.
3541 //         Region 6-7 is determined per call site.
3542 // Note 2: If the calling convention leaves holes in the incoming argument
3543 //         area, those holes are owned by SELF.  Holes in the outgoing area
3544 //         are owned by the CALLEE.  Holes should not be nessecary in the
3545 //         incoming area, as the Java calling convention is completely under
3546 //         the control of the AD file.  Doubles can be sorted and packed to
3547 //         avoid holes.  Holes in the outgoing arguments may be nessecary for
3548 //         varargs C calling conventions.
3549 // Note 3: Region 0-3 is even aligned, with pad2 as needed.  Region 3-5 is
3550 //         even aligned with pad0 as needed.
3551 //         Region 6 is even aligned.  Region 6-7 is NOT even aligned;
3552 //           (the latter is true on Intel but is it false on AArch64?)
3553 //         region 6-11 is even aligned; it may be padded out more so that
3554 //         the region from SP to FP meets the minimum stack alignment.
3555 // Note 4: For I2C adapters, the incoming FP may not meet the minimum stack
3556 //         alignment.  Region 11, pad1, may be dynamically extended so that
3557 //         SP meets the minimum alignment.
3558 
3559 frame %{
3560   // What direction does stack grow in (assumed to be same for C & Java)
3561   stack_direction(TOWARDS_LOW);
3562 
3563   // These three registers define part of the calling convention
3564   // between compiled code and the interpreter.
3565 
3566   // Inline Cache Register or methodOop for I2C.
3567   inline_cache_reg(R12);
3568 
3569   // Method Oop Register when calling interpreter.
3570   interpreter_method_oop_reg(R12);
3571 
3572   // Number of stack slots consumed by locking an object
3573   sync_stack_slots(2);
3574 
3575   // Compiled code's Frame Pointer
3576   frame_pointer(R31);
3577 
3578   // Interpreter stores its frame pointer in a register which is
3579   // stored to the stack by I2CAdaptors.
3580   // I2CAdaptors convert from interpreted java to compiled java.
3581   interpreter_frame_pointer(R29);
3582 
3583   // Stack alignment requirement
3584   stack_alignment(StackAlignmentInBytes); // Alignment size in bytes (128-bit -> 16 bytes)
3585 
3586   // Number of stack slots between incoming argument block and the start of
3587   // a new frame.  The PROLOG must add this many slots to the stack.  The
3588   // EPILOG must remove this many slots. aarch64 needs two slots for
3589   // return address and fp.
3590   // TODO think this is correct but check
3591   in_preserve_stack_slots(4);
3592 
3593   // Number of outgoing stack slots killed above the out_preserve_stack_slots
3594   // for calls to C.  Supports the var-args backing area for register parms.
3595   varargs_C_out_slots_killed(frame::arg_reg_save_area_bytes/BytesPerInt);
3596 
3597   // The after-PROLOG location of the return address.  Location of
3598   // return address specifies a type (REG or STACK) and a number
3599   // representing the register number (i.e. - use a register name) or
3600   // stack slot.
3601   // Ret Addr is on stack in slot 0 if no locks or verification or alignment.
3602   // Otherwise, it is above the locks and verification slot and alignment word
3603   // TODO this may well be correct but need to check why that - 2 is there
3604   // ppc port uses 0 but we definitely need to allow for fixed_slots
3605   // which folds in the space used for monitors
3606   return_addr(STACK - 2 +
3607               align_up((Compile::current()->in_preserve_stack_slots() +
3608                         Compile::current()->fixed_slots()),
3609                        stack_alignment_in_slots()));
3610 
3611   // Body of function which returns an integer array locating
3612   // arguments either in registers or in stack slots.  Passed an array
3613   // of ideal registers called "sig" and a "length" count.  Stack-slot
3614   // offsets are based on outgoing arguments, i.e. a CALLER setting up
3615   // arguments for a CALLEE.  Incoming stack arguments are
3616   // automatically biased by the preserve_stack_slots field above.
3617 
3618   calling_convention
3619   %{
3620     // No difference between ingoing/outgoing just pass false
3621     SharedRuntime::java_calling_convention(sig_bt, regs, length, false);
3622   %}
3623 
3624   c_calling_convention
3625   %{
3626     // This is obviously always outgoing
3627     (void) SharedRuntime::c_calling_convention(sig_bt, regs, NULL, length);
3628   %}
3629 
3630   // Location of compiled Java return values.  Same as C for now.
3631   return_value
3632   %{
3633     // TODO do we allow ideal_reg == Op_RegN???
3634     assert(ideal_reg >= Op_RegI && ideal_reg <= Op_RegL,
3635            "only return normal values");
3636 
3637     static const int lo[Op_RegL + 1] = { // enum name
3638       0,                                 // Op_Node
3639       0,                                 // Op_Set
3640       R0_num,                            // Op_RegN
3641       R0_num,                            // Op_RegI
3642       R0_num,                            // Op_RegP
3643       V0_num,                            // Op_RegF
3644       V0_num,                            // Op_RegD
3645       R0_num                             // Op_RegL
3646     };
3647 
3648     static const int hi[Op_RegL + 1] = { // enum name
3649       0,                                 // Op_Node
3650       0,                                 // Op_Set
3651       OptoReg::Bad,                       // Op_RegN
3652       OptoReg::Bad,                      // Op_RegI
3653       R0_H_num,                          // Op_RegP
3654       OptoReg::Bad,                      // Op_RegF
3655       V0_H_num,                          // Op_RegD
3656       R0_H_num                           // Op_RegL
3657     };
3658 
3659     return OptoRegPair(hi[ideal_reg], lo[ideal_reg]);
3660   %}
3661 %}
3662 
3663 //----------ATTRIBUTES---------------------------------------------------------
3664 //----------Operand Attributes-------------------------------------------------
3665 op_attrib op_cost(1);        // Required cost attribute
3666 
3667 //----------Instruction Attributes---------------------------------------------
3668 ins_attrib ins_cost(INSN_COST); // Required cost attribute
3669 ins_attrib ins_size(32);        // Required size attribute (in bits)
3670 ins_attrib ins_short_branch(0); // Required flag: is this instruction
3671                                 // a non-matching short branch variant
3672                                 // of some long branch?
3673 ins_attrib ins_alignment(4);    // Required alignment attribute (must
3674                                 // be a power of 2) specifies the
3675                                 // alignment that some part of the
3676                                 // instruction (not necessarily the
3677                                 // start) requires.  If > 1, a
3678                                 // compute_padding() function must be
3679                                 // provided for the instruction
3680 
3681 //----------OPERANDS-----------------------------------------------------------
3682 // Operand definitions must precede instruction definitions for correct parsing
3683 // in the ADLC because operands constitute user defined types which are used in
3684 // instruction definitions.
3685 
3686 //----------Simple Operands----------------------------------------------------
3687 
3688 // Integer operands 32 bit
3689 // 32 bit immediate
3690 operand immI()
3691 %{
3692   match(ConI);
3693 
3694   op_cost(0);
3695   format %{ %}
3696   interface(CONST_INTER);
3697 %}
3698 
3699 // 32 bit zero
3700 operand immI0()
3701 %{
3702   predicate(n->get_int() == 0);
3703   match(ConI);
3704 
3705   op_cost(0);
3706   format %{ %}
3707   interface(CONST_INTER);
3708 %}
3709 
3710 // 32 bit unit increment
3711 operand immI_1()
3712 %{
3713   predicate(n->get_int() == 1);
3714   match(ConI);
3715 
3716   op_cost(0);
3717   format %{ %}
3718   interface(CONST_INTER);
3719 %}
3720 
3721 // 32 bit unit decrement
3722 operand immI_M1()
3723 %{
3724   predicate(n->get_int() == -1);
3725   match(ConI);
3726 
3727   op_cost(0);
3728   format %{ %}
3729   interface(CONST_INTER);
3730 %}
3731 
3732 // Shift values for add/sub extension shift
3733 operand immIExt()
3734 %{
3735   predicate(0 <= n->get_int() && (n->get_int() <= 4));
3736   match(ConI);
3737 
3738   op_cost(0);
3739   format %{ %}
3740   interface(CONST_INTER);
3741 %}
3742 
3743 operand immI_le_4()
3744 %{
3745   predicate(n->get_int() <= 4);
3746   match(ConI);
3747 
3748   op_cost(0);
3749   format %{ %}
3750   interface(CONST_INTER);
3751 %}
3752 
3753 operand immI_31()
3754 %{
3755   predicate(n->get_int() == 31);
3756   match(ConI);
3757 
3758   op_cost(0);
3759   format %{ %}
3760   interface(CONST_INTER);
3761 %}
3762 
3763 operand immI_8()
3764 %{
3765   predicate(n->get_int() == 8);
3766   match(ConI);
3767 
3768   op_cost(0);
3769   format %{ %}
3770   interface(CONST_INTER);
3771 %}
3772 
3773 operand immI_16()
3774 %{
3775   predicate(n->get_int() == 16);
3776   match(ConI);
3777 
3778   op_cost(0);
3779   format %{ %}
3780   interface(CONST_INTER);
3781 %}
3782 
3783 operand immI_24()
3784 %{
3785   predicate(n->get_int() == 24);
3786   match(ConI);
3787 
3788   op_cost(0);
3789   format %{ %}
3790   interface(CONST_INTER);
3791 %}
3792 
3793 operand immI_32()
3794 %{
3795   predicate(n->get_int() == 32);
3796   match(ConI);
3797 
3798   op_cost(0);
3799   format %{ %}
3800   interface(CONST_INTER);
3801 %}
3802 
3803 operand immI_48()
3804 %{
3805   predicate(n->get_int() == 48);
3806   match(ConI);
3807 
3808   op_cost(0);
3809   format %{ %}
3810   interface(CONST_INTER);
3811 %}
3812 
3813 operand immI_56()
3814 %{
3815   predicate(n->get_int() == 56);
3816   match(ConI);
3817 
3818   op_cost(0);
3819   format %{ %}
3820   interface(CONST_INTER);
3821 %}
3822 
3823 operand immI_63()
3824 %{
3825   predicate(n->get_int() == 63);
3826   match(ConI);
3827 
3828   op_cost(0);
3829   format %{ %}
3830   interface(CONST_INTER);
3831 %}
3832 
3833 operand immI_64()
3834 %{
3835   predicate(n->get_int() == 64);
3836   match(ConI);
3837 
3838   op_cost(0);
3839   format %{ %}
3840   interface(CONST_INTER);
3841 %}
3842 
3843 operand immI_255()
3844 %{
3845   predicate(n->get_int() == 255);
3846   match(ConI);
3847 
3848   op_cost(0);
3849   format %{ %}
3850   interface(CONST_INTER);
3851 %}
3852 
3853 operand immI_65535()
3854 %{
3855   predicate(n->get_int() == 65535);
3856   match(ConI);
3857 
3858   op_cost(0);
3859   format %{ %}
3860   interface(CONST_INTER);
3861 %}
3862 
3863 operand immL_255()
3864 %{
3865   predicate(n->get_long() == 255L);
3866   match(ConL);
3867 
3868   op_cost(0);
3869   format %{ %}
3870   interface(CONST_INTER);
3871 %}
3872 
3873 operand immL_65535()
3874 %{
3875   predicate(n->get_long() == 65535L);
3876   match(ConL);
3877 
3878   op_cost(0);
3879   format %{ %}
3880   interface(CONST_INTER);
3881 %}
3882 
3883 operand immL_4294967295()
3884 %{
3885   predicate(n->get_long() == 4294967295L);
3886   match(ConL);
3887 
3888   op_cost(0);
3889   format %{ %}
3890   interface(CONST_INTER);
3891 %}
3892 
3893 operand immL_bitmask()
3894 %{
3895   predicate(((n->get_long() & 0xc000000000000000l) == 0)
3896             && is_power_of_2(n->get_long() + 1));
3897   match(ConL);
3898 
3899   op_cost(0);
3900   format %{ %}
3901   interface(CONST_INTER);
3902 %}
3903 
3904 operand immI_bitmask()
3905 %{
3906   predicate(((n->get_int() & 0xc0000000) == 0)
3907             && is_power_of_2(n->get_int() + 1));
3908   match(ConI);
3909 
3910   op_cost(0);
3911   format %{ %}
3912   interface(CONST_INTER);
3913 %}
3914 
3915 // Scale values for scaled offset addressing modes (up to long but not quad)
3916 operand immIScale()
3917 %{
3918   predicate(0 <= n->get_int() && (n->get_int() <= 3));
3919   match(ConI);
3920 
3921   op_cost(0);
3922   format %{ %}
3923   interface(CONST_INTER);
3924 %}
3925 
3926 // 26 bit signed offset -- for pc-relative branches
3927 operand immI26()
3928 %{
3929   predicate(((-(1 << 25)) <= n->get_int()) && (n->get_int() < (1 << 25)));
3930   match(ConI);
3931 
3932   op_cost(0);
3933   format %{ %}
3934   interface(CONST_INTER);
3935 %}
3936 
3937 // 19 bit signed offset -- for pc-relative loads
3938 operand immI19()
3939 %{
3940   predicate(((-(1 << 18)) <= n->get_int()) && (n->get_int() < (1 << 18)));
3941   match(ConI);
3942 
3943   op_cost(0);
3944   format %{ %}
3945   interface(CONST_INTER);
3946 %}
3947 
3948 // 12 bit unsigned offset -- for base plus immediate loads
3949 operand immIU12()
3950 %{
3951   predicate((0 <= n->get_int()) && (n->get_int() < (1 << 12)));
3952   match(ConI);
3953 
3954   op_cost(0);
3955   format %{ %}
3956   interface(CONST_INTER);
3957 %}
3958 
3959 operand immLU12()
3960 %{
3961   predicate((0 <= n->get_long()) && (n->get_long() < (1 << 12)));
3962   match(ConL);
3963 
3964   op_cost(0);
3965   format %{ %}
3966   interface(CONST_INTER);
3967 %}
3968 
3969 // Offset for scaled or unscaled immediate loads and stores
3970 operand immIOffset()
3971 %{
3972   predicate(Address::offset_ok_for_immed(n->get_int()));
3973   match(ConI);
3974 
3975   op_cost(0);
3976   format %{ %}
3977   interface(CONST_INTER);
3978 %}
3979 
3980 operand immIOffset4()
3981 %{
3982   predicate(Address::offset_ok_for_immed(n->get_int(), 2));
3983   match(ConI);
3984 
3985   op_cost(0);
3986   format %{ %}
3987   interface(CONST_INTER);
3988 %}
3989 
3990 operand immIOffset8()
3991 %{
3992   predicate(Address::offset_ok_for_immed(n->get_int(), 3));
3993   match(ConI);
3994 
3995   op_cost(0);
3996   format %{ %}
3997   interface(CONST_INTER);
3998 %}
3999 
4000 operand immIOffset16()
4001 %{
4002   predicate(Address::offset_ok_for_immed(n->get_int(), 4));
4003   match(ConI);
4004 
4005   op_cost(0);
4006   format %{ %}
4007   interface(CONST_INTER);
4008 %}
4009 
4010 operand immLoffset()
4011 %{
4012   predicate(Address::offset_ok_for_immed(n->get_long()));
4013   match(ConL);
4014 
4015   op_cost(0);
4016   format %{ %}
4017   interface(CONST_INTER);
4018 %}
4019 
4020 operand immLoffset4()
4021 %{
4022   predicate(Address::offset_ok_for_immed(n->get_long(), 2));
4023   match(ConL);
4024 
4025   op_cost(0);
4026   format %{ %}
4027   interface(CONST_INTER);
4028 %}
4029 
4030 operand immLoffset8()
4031 %{
4032   predicate(Address::offset_ok_for_immed(n->get_long(), 3));
4033   match(ConL);
4034 
4035   op_cost(0);
4036   format %{ %}
4037   interface(CONST_INTER);
4038 %}
4039 
4040 operand immLoffset16()
4041 %{
4042   predicate(Address::offset_ok_for_immed(n->get_long(), 4));
4043   match(ConL);
4044 
4045   op_cost(0);
4046   format %{ %}
4047   interface(CONST_INTER);
4048 %}
4049 
4050 // 32 bit integer valid for add sub immediate
4051 operand immIAddSub()
4052 %{
4053   predicate(Assembler::operand_valid_for_add_sub_immediate((long)n->get_int()));
4054   match(ConI);
4055   op_cost(0);
4056   format %{ %}
4057   interface(CONST_INTER);
4058 %}
4059 
4060 // 32 bit unsigned integer valid for logical immediate
4061 // TODO -- check this is right when e.g the mask is 0x80000000
4062 operand immILog()
4063 %{
4064   predicate(Assembler::operand_valid_for_logical_immediate(/*is32*/true, (unsigned long)n->get_int()));
4065   match(ConI);
4066 
4067   op_cost(0);
4068   format %{ %}
4069   interface(CONST_INTER);
4070 %}
4071 
4072 // Integer operands 64 bit
4073 // 64 bit immediate
4074 operand immL()
4075 %{
4076   match(ConL);
4077 
4078   op_cost(0);
4079   format %{ %}
4080   interface(CONST_INTER);
4081 %}
4082 
4083 // 64 bit zero
4084 operand immL0()
4085 %{
4086   predicate(n->get_long() == 0);
4087   match(ConL);
4088 
4089   op_cost(0);
4090   format %{ %}
4091   interface(CONST_INTER);
4092 %}
4093 
4094 // 64 bit unit increment
4095 operand immL_1()
4096 %{
4097   predicate(n->get_long() == 1);
4098   match(ConL);
4099 
4100   op_cost(0);
4101   format %{ %}
4102   interface(CONST_INTER);
4103 %}
4104 
4105 // 64 bit unit decrement
4106 operand immL_M1()
4107 %{
4108   predicate(n->get_long() == -1);
4109   match(ConL);
4110 
4111   op_cost(0);
4112   format %{ %}
4113   interface(CONST_INTER);
4114 %}
4115 
4116 // 32 bit offset of pc in thread anchor
4117 
4118 operand immL_pc_off()
4119 %{
4120   predicate(n->get_long() == in_bytes(JavaThread::frame_anchor_offset()) +
4121                              in_bytes(JavaFrameAnchor::last_Java_pc_offset()));
4122   match(ConL);
4123 
4124   op_cost(0);
4125   format %{ %}
4126   interface(CONST_INTER);
4127 %}
4128 
4129 // 64 bit integer valid for add sub immediate
4130 operand immLAddSub()
4131 %{
4132   predicate(Assembler::operand_valid_for_add_sub_immediate(n->get_long()));
4133   match(ConL);
4134   op_cost(0);
4135   format %{ %}
4136   interface(CONST_INTER);
4137 %}
4138 
4139 // 64 bit integer valid for logical immediate
4140 operand immLLog()
4141 %{
4142   predicate(Assembler::operand_valid_for_logical_immediate(/*is32*/false, (unsigned long)n->get_long()));
4143   match(ConL);
4144   op_cost(0);
4145   format %{ %}
4146   interface(CONST_INTER);
4147 %}
4148 
4149 // Long Immediate: low 32-bit mask
4150 operand immL_32bits()
4151 %{
4152   predicate(n->get_long() == 0xFFFFFFFFL);
4153   match(ConL);
4154   op_cost(0);
4155   format %{ %}
4156   interface(CONST_INTER);
4157 %}
4158 
4159 // Pointer operands
4160 // Pointer Immediate
4161 operand immP()
4162 %{
4163   match(ConP);
4164 
4165   op_cost(0);
4166   format %{ %}
4167   interface(CONST_INTER);
4168 %}
4169 
4170 // NULL Pointer Immediate
4171 operand immP0()
4172 %{
4173   predicate(n->get_ptr() == 0);
4174   match(ConP);
4175 
4176   op_cost(0);
4177   format %{ %}
4178   interface(CONST_INTER);
4179 %}
4180 
4181 // Pointer Immediate One
4182 // this is used in object initialization (initial object header)
4183 operand immP_1()
4184 %{
4185   predicate(n->get_ptr() == 1);
4186   match(ConP);
4187 
4188   op_cost(0);
4189   format %{ %}
4190   interface(CONST_INTER);
4191 %}
4192 
4193 // Polling Page Pointer Immediate
4194 operand immPollPage()
4195 %{
4196   predicate((address)n->get_ptr() == os::get_polling_page());
4197   match(ConP);
4198 
4199   op_cost(0);
4200   format %{ %}
4201   interface(CONST_INTER);
4202 %}
4203 
4204 // Card Table Byte Map Base
4205 operand immByteMapBase()
4206 %{
4207   // Get base of card map
4208   predicate(BarrierSet::barrier_set()->is_a(BarrierSet::CardTableBarrierSet) &&
4209             (jbyte*)n->get_ptr() == ((CardTableBarrierSet*)(BarrierSet::barrier_set()))->card_table()->byte_map_base());
4210   match(ConP);
4211 
4212   op_cost(0);
4213   format %{ %}
4214   interface(CONST_INTER);
4215 %}
4216 
4217 // Pointer Immediate Minus One
4218 // this is used when we want to write the current PC to the thread anchor
4219 operand immP_M1()
4220 %{
4221   predicate(n->get_ptr() == -1);
4222   match(ConP);
4223 
4224   op_cost(0);
4225   format %{ %}
4226   interface(CONST_INTER);
4227 %}
4228 
4229 // Pointer Immediate Minus Two
4230 // this is used when we want to write the current PC to the thread anchor
4231 operand immP_M2()
4232 %{
4233   predicate(n->get_ptr() == -2);
4234   match(ConP);
4235 
4236   op_cost(0);
4237   format %{ %}
4238   interface(CONST_INTER);
4239 %}
4240 
4241 // Float and Double operands
4242 // Double Immediate
4243 operand immD()
4244 %{
4245   match(ConD);
4246   op_cost(0);
4247   format %{ %}
4248   interface(CONST_INTER);
4249 %}
4250 
4251 // Double Immediate: +0.0d
4252 operand immD0()
4253 %{
4254   predicate(jlong_cast(n->getd()) == 0);
4255   match(ConD);
4256 
4257   op_cost(0);
4258   format %{ %}
4259   interface(CONST_INTER);
4260 %}
4261 
4262 // constant 'double +0.0'.
4263 operand immDPacked()
4264 %{
4265   predicate(Assembler::operand_valid_for_float_immediate(n->getd()));
4266   match(ConD);
4267   op_cost(0);
4268   format %{ %}
4269   interface(CONST_INTER);
4270 %}
4271 
4272 // Float Immediate
4273 operand immF()
4274 %{
4275   match(ConF);
4276   op_cost(0);
4277   format %{ %}
4278   interface(CONST_INTER);
4279 %}
4280 
4281 // Float Immediate: +0.0f.
4282 operand immF0()
4283 %{
4284   predicate(jint_cast(n->getf()) == 0);
4285   match(ConF);
4286 
4287   op_cost(0);
4288   format %{ %}
4289   interface(CONST_INTER);
4290 %}
4291 
4292 //
4293 operand immFPacked()
4294 %{
4295   predicate(Assembler::operand_valid_for_float_immediate((double)n->getf()));
4296   match(ConF);
4297   op_cost(0);
4298   format %{ %}
4299   interface(CONST_INTER);
4300 %}
4301 
4302 // Narrow pointer operands
4303 // Narrow Pointer Immediate
4304 operand immN()
4305 %{
4306   match(ConN);
4307 
4308   op_cost(0);
4309   format %{ %}
4310   interface(CONST_INTER);
4311 %}
4312 
4313 // Narrow NULL Pointer Immediate
4314 operand immN0()
4315 %{
4316   predicate(n->get_narrowcon() == 0);
4317   match(ConN);
4318 
4319   op_cost(0);
4320   format %{ %}
4321   interface(CONST_INTER);
4322 %}
4323 
4324 operand immNKlass()
4325 %{
4326   match(ConNKlass);
4327 
4328   op_cost(0);
4329   format %{ %}
4330   interface(CONST_INTER);
4331 %}
4332 
4333 // Integer 32 bit Register Operands
4334 // Integer 32 bitRegister (excludes SP)
4335 operand iRegI()
4336 %{
4337   constraint(ALLOC_IN_RC(any_reg32));
4338   match(RegI);
4339   match(iRegINoSp);
4340   op_cost(0);
4341   format %{ %}
4342   interface(REG_INTER);
4343 %}
4344 
4345 // Integer 32 bit Register not Special
4346 operand iRegINoSp()
4347 %{
4348   constraint(ALLOC_IN_RC(no_special_reg32));
4349   match(RegI);
4350   op_cost(0);
4351   format %{ %}
4352   interface(REG_INTER);
4353 %}
4354 
4355 // Integer 64 bit Register Operands
4356 // Integer 64 bit Register (includes SP)
4357 operand iRegL()
4358 %{
4359   constraint(ALLOC_IN_RC(any_reg));
4360   match(RegL);
4361   match(iRegLNoSp);
4362   op_cost(0);
4363   format %{ %}
4364   interface(REG_INTER);
4365 %}
4366 
4367 // Integer 64 bit Register not Special
4368 operand iRegLNoSp()
4369 %{
4370   constraint(ALLOC_IN_RC(no_special_reg));
4371   match(RegL);
4372   match(iRegL_R0);
4373   format %{ %}
4374   interface(REG_INTER);
4375 %}
4376 
4377 // Pointer Register Operands
4378 // Pointer Register
4379 operand iRegP()
4380 %{
4381   constraint(ALLOC_IN_RC(ptr_reg));
4382   match(RegP);
4383   match(iRegPNoSp);
4384   match(iRegP_R0);
4385   //match(iRegP_R2);
4386   //match(iRegP_R4);
4387   //match(iRegP_R5);
4388   match(thread_RegP);
4389   op_cost(0);
4390   format %{ %}
4391   interface(REG_INTER);
4392 %}
4393 
4394 // Pointer 64 bit Register not Special
4395 operand iRegPNoSp()
4396 %{
4397   constraint(ALLOC_IN_RC(no_special_ptr_reg));
4398   match(RegP);
4399   // match(iRegP);
4400   // match(iRegP_R0);
4401   // match(iRegP_R2);
4402   // match(iRegP_R4);
4403   // match(iRegP_R5);
4404   // match(thread_RegP);
4405   op_cost(0);
4406   format %{ %}
4407   interface(REG_INTER);
4408 %}
4409 
4410 // Pointer 64 bit Register R0 only
4411 operand iRegP_R0()
4412 %{
4413   constraint(ALLOC_IN_RC(r0_reg));
4414   match(RegP);
4415   // match(iRegP);
4416   match(iRegPNoSp);
4417   op_cost(0);
4418   format %{ %}
4419   interface(REG_INTER);
4420 %}
4421 
4422 // Pointer 64 bit Register R1 only
4423 operand iRegP_R1()
4424 %{
4425   constraint(ALLOC_IN_RC(r1_reg));
4426   match(RegP);
4427   // match(iRegP);
4428   match(iRegPNoSp);
4429   op_cost(0);
4430   format %{ %}
4431   interface(REG_INTER);
4432 %}
4433 
4434 // Pointer 64 bit Register R2 only
4435 operand iRegP_R2()
4436 %{
4437   constraint(ALLOC_IN_RC(r2_reg));
4438   match(RegP);
4439   // match(iRegP);
4440   match(iRegPNoSp);
4441   op_cost(0);
4442   format %{ %}
4443   interface(REG_INTER);
4444 %}
4445 
4446 // Pointer 64 bit Register R3 only
4447 operand iRegP_R3()
4448 %{
4449   constraint(ALLOC_IN_RC(r3_reg));
4450   match(RegP);
4451   // match(iRegP);
4452   match(iRegPNoSp);
4453   op_cost(0);
4454   format %{ %}
4455   interface(REG_INTER);
4456 %}
4457 
4458 // Pointer 64 bit Register R4 only
4459 operand iRegP_R4()
4460 %{
4461   constraint(ALLOC_IN_RC(r4_reg));
4462   match(RegP);
4463   // match(iRegP);
4464   match(iRegPNoSp);
4465   op_cost(0);
4466   format %{ %}
4467   interface(REG_INTER);
4468 %}
4469 
4470 // Pointer 64 bit Register R5 only
4471 operand iRegP_R5()
4472 %{
4473   constraint(ALLOC_IN_RC(r5_reg));
4474   match(RegP);
4475   // match(iRegP);
4476   match(iRegPNoSp);
4477   op_cost(0);
4478   format %{ %}
4479   interface(REG_INTER);
4480 %}
4481 
4482 // Pointer 64 bit Register R10 only
4483 operand iRegP_R10()
4484 %{
4485   constraint(ALLOC_IN_RC(r10_reg));
4486   match(RegP);
4487   // match(iRegP);
4488   match(iRegPNoSp);
4489   op_cost(0);
4490   format %{ %}
4491   interface(REG_INTER);
4492 %}
4493 
4494 // Long 64 bit Register R0 only
4495 operand iRegL_R0()
4496 %{
4497   constraint(ALLOC_IN_RC(r0_reg));
4498   match(RegL);
4499   match(iRegLNoSp);
4500   op_cost(0);
4501   format %{ %}
4502   interface(REG_INTER);
4503 %}
4504 
4505 // Long 64 bit Register R2 only
4506 operand iRegL_R2()
4507 %{
4508   constraint(ALLOC_IN_RC(r2_reg));
4509   match(RegL);
4510   match(iRegLNoSp);
4511   op_cost(0);
4512   format %{ %}
4513   interface(REG_INTER);
4514 %}
4515 
4516 // Long 64 bit Register R3 only
4517 operand iRegL_R3()
4518 %{
4519   constraint(ALLOC_IN_RC(r3_reg));
4520   match(RegL);
4521   match(iRegLNoSp);
4522   op_cost(0);
4523   format %{ %}
4524   interface(REG_INTER);
4525 %}
4526 
4527 // Long 64 bit Register R11 only
4528 operand iRegL_R11()
4529 %{
4530   constraint(ALLOC_IN_RC(r11_reg));
4531   match(RegL);
4532   match(iRegLNoSp);
4533   op_cost(0);
4534   format %{ %}
4535   interface(REG_INTER);
4536 %}
4537 
4538 // Pointer 64 bit Register FP only
4539 operand iRegP_FP()
4540 %{
4541   constraint(ALLOC_IN_RC(fp_reg));
4542   match(RegP);
4543   // match(iRegP);
4544   op_cost(0);
4545   format %{ %}
4546   interface(REG_INTER);
4547 %}
4548 
4549 // Register R0 only
4550 operand iRegI_R0()
4551 %{
4552   constraint(ALLOC_IN_RC(int_r0_reg));
4553   match(RegI);
4554   match(iRegINoSp);
4555   op_cost(0);
4556   format %{ %}
4557   interface(REG_INTER);
4558 %}
4559 
4560 // Register R2 only
4561 operand iRegI_R2()
4562 %{
4563   constraint(ALLOC_IN_RC(int_r2_reg));
4564   match(RegI);
4565   match(iRegINoSp);
4566   op_cost(0);
4567   format %{ %}
4568   interface(REG_INTER);
4569 %}
4570 
4571 // Register R3 only
4572 operand iRegI_R3()
4573 %{
4574   constraint(ALLOC_IN_RC(int_r3_reg));
4575   match(RegI);
4576   match(iRegINoSp);
4577   op_cost(0);
4578   format %{ %}
4579   interface(REG_INTER);
4580 %}
4581 
4582 
4583 // Register R4 only
4584 operand iRegI_R4()
4585 %{
4586   constraint(ALLOC_IN_RC(int_r4_reg));
4587   match(RegI);
4588   match(iRegINoSp);
4589   op_cost(0);
4590   format %{ %}
4591   interface(REG_INTER);
4592 %}
4593 
4594 
4595 // Pointer Register Operands
4596 // Narrow Pointer Register
4597 operand iRegN()
4598 %{
4599   constraint(ALLOC_IN_RC(any_reg32));
4600   match(RegN);
4601   match(iRegNNoSp);
4602   op_cost(0);
4603   format %{ %}
4604   interface(REG_INTER);
4605 %}
4606 
4607 operand iRegN_R0()
4608 %{
4609   constraint(ALLOC_IN_RC(r0_reg));
4610   match(iRegN);
4611   op_cost(0);
4612   format %{ %}
4613   interface(REG_INTER);
4614 %}
4615 
4616 operand iRegN_R2()
4617 %{
4618   constraint(ALLOC_IN_RC(r2_reg));
4619   match(iRegN);
4620   op_cost(0);
4621   format %{ %}
4622   interface(REG_INTER);
4623 %}
4624 
4625 operand iRegN_R3()
4626 %{
4627   constraint(ALLOC_IN_RC(r3_reg));
4628   match(iRegN);
4629   op_cost(0);
4630   format %{ %}
4631   interface(REG_INTER);
4632 %}
4633 
4634 // Integer 64 bit Register not Special
4635 operand iRegNNoSp()
4636 %{
4637   constraint(ALLOC_IN_RC(no_special_reg32));
4638   match(RegN);
4639   op_cost(0);
4640   format %{ %}
4641   interface(REG_INTER);
4642 %}
4643 
4644 // heap base register -- used for encoding immN0
4645 
4646 operand iRegIHeapbase()
4647 %{
4648   constraint(ALLOC_IN_RC(heapbase_reg));
4649   match(RegI);
4650   op_cost(0);
4651   format %{ %}
4652   interface(REG_INTER);
4653 %}
4654 
4655 // Float Register
4656 // Float register operands
4657 operand vRegF()
4658 %{
4659   constraint(ALLOC_IN_RC(float_reg));
4660   match(RegF);
4661 
4662   op_cost(0);
4663   format %{ %}
4664   interface(REG_INTER);
4665 %}
4666 
4667 // Double Register
4668 // Double register operands
4669 operand vRegD()
4670 %{
4671   constraint(ALLOC_IN_RC(double_reg));
4672   match(RegD);
4673 
4674   op_cost(0);
4675   format %{ %}
4676   interface(REG_INTER);
4677 %}
4678 
4679 operand vecD()
4680 %{
4681   constraint(ALLOC_IN_RC(vectord_reg));
4682   match(VecD);
4683 
4684   op_cost(0);
4685   format %{ %}
4686   interface(REG_INTER);
4687 %}
4688 
4689 operand vecX()
4690 %{
4691   constraint(ALLOC_IN_RC(vectorx_reg));
4692   match(VecX);
4693 
4694   op_cost(0);
4695   format %{ %}
4696   interface(REG_INTER);
4697 %}
4698 
4699 operand vRegD_V0()
4700 %{
4701   constraint(ALLOC_IN_RC(v0_reg));
4702   match(RegD);
4703   op_cost(0);
4704   format %{ %}
4705   interface(REG_INTER);
4706 %}
4707 
4708 operand vRegD_V1()
4709 %{
4710   constraint(ALLOC_IN_RC(v1_reg));
4711   match(RegD);
4712   op_cost(0);
4713   format %{ %}
4714   interface(REG_INTER);
4715 %}
4716 
4717 operand vRegD_V2()
4718 %{
4719   constraint(ALLOC_IN_RC(v2_reg));
4720   match(RegD);
4721   op_cost(0);
4722   format %{ %}
4723   interface(REG_INTER);
4724 %}
4725 
4726 operand vRegD_V3()
4727 %{
4728   constraint(ALLOC_IN_RC(v3_reg));
4729   match(RegD);
4730   op_cost(0);
4731   format %{ %}
4732   interface(REG_INTER);
4733 %}
4734 
4735 // Flags register, used as output of signed compare instructions
4736 
4737 // note that on AArch64 we also use this register as the output for
4738 // for floating point compare instructions (CmpF CmpD). this ensures
4739 // that ordered inequality tests use GT, GE, LT or LE none of which
4740 // pass through cases where the result is unordered i.e. one or both
4741 // inputs to the compare is a NaN. this means that the ideal code can
4742 // replace e.g. a GT with an LE and not end up capturing the NaN case
4743 // (where the comparison should always fail). EQ and NE tests are
4744 // always generated in ideal code so that unordered folds into the NE
4745 // case, matching the behaviour of AArch64 NE.
4746 //
4747 // This differs from x86 where the outputs of FP compares use a
4748 // special FP flags registers and where compares based on this
4749 // register are distinguished into ordered inequalities (cmpOpUCF) and
4750 // EQ/NEQ tests (cmpOpUCF2). x86 has to special case the latter tests
4751 // to explicitly handle the unordered case in branches. x86 also has
4752 // to include extra CMoveX rules to accept a cmpOpUCF input.
4753 
4754 operand rFlagsReg()
4755 %{
4756   constraint(ALLOC_IN_RC(int_flags));
4757   match(RegFlags);
4758 
4759   op_cost(0);
4760   format %{ "RFLAGS" %}
4761   interface(REG_INTER);
4762 %}
4763 
4764 // Flags register, used as output of unsigned compare instructions
4765 operand rFlagsRegU()
4766 %{
4767   constraint(ALLOC_IN_RC(int_flags));
4768   match(RegFlags);
4769 
4770   op_cost(0);
4771   format %{ "RFLAGSU" %}
4772   interface(REG_INTER);
4773 %}
4774 
4775 // Special Registers
4776 
4777 // Method Register
4778 operand inline_cache_RegP(iRegP reg)
4779 %{
4780   constraint(ALLOC_IN_RC(method_reg)); // inline_cache_reg
4781   match(reg);
4782   match(iRegPNoSp);
4783   op_cost(0);
4784   format %{ %}
4785   interface(REG_INTER);
4786 %}
4787 
4788 operand interpreter_method_oop_RegP(iRegP reg)
4789 %{
4790   constraint(ALLOC_IN_RC(method_reg)); // interpreter_method_oop_reg
4791   match(reg);
4792   match(iRegPNoSp);
4793   op_cost(0);
4794   format %{ %}
4795   interface(REG_INTER);
4796 %}
4797 
4798 // Thread Register
4799 operand thread_RegP(iRegP reg)
4800 %{
4801   constraint(ALLOC_IN_RC(thread_reg)); // link_reg
4802   match(reg);
4803   op_cost(0);
4804   format %{ %}
4805   interface(REG_INTER);
4806 %}
4807 
4808 operand lr_RegP(iRegP reg)
4809 %{
4810   constraint(ALLOC_IN_RC(lr_reg)); // link_reg
4811   match(reg);
4812   op_cost(0);
4813   format %{ %}
4814   interface(REG_INTER);
4815 %}
4816 
4817 //----------Memory Operands----------------------------------------------------
4818 
4819 operand indirect(iRegP reg)
4820 %{
4821   constraint(ALLOC_IN_RC(ptr_reg));
4822   match(reg);
4823   op_cost(0);
4824   format %{ "[$reg]" %}
4825   interface(MEMORY_INTER) %{
4826     base($reg);
4827     index(0xffffffff);
4828     scale(0x0);
4829     disp(0x0);
4830   %}
4831 %}
4832 
4833 operand indIndexScaledI2L(iRegP reg, iRegI ireg, immIScale scale)
4834 %{
4835   constraint(ALLOC_IN_RC(ptr_reg));
4836   predicate(size_fits_all_mem_uses(n->as_AddP(), n->in(AddPNode::Offset)->in(2)->get_int()));
4837   match(AddP reg (LShiftL (ConvI2L ireg) scale));
4838   op_cost(0);
4839   format %{ "$reg, $ireg sxtw($scale), 0, I2L" %}
4840   interface(MEMORY_INTER) %{
4841     base($reg);
4842     index($ireg);
4843     scale($scale);
4844     disp(0x0);
4845   %}
4846 %}
4847 
4848 operand indIndexScaled(iRegP reg, iRegL lreg, immIScale scale)
4849 %{
4850   constraint(ALLOC_IN_RC(ptr_reg));
4851   predicate(size_fits_all_mem_uses(n->as_AddP(), n->in(AddPNode::Offset)->in(2)->get_int()));
4852   match(AddP reg (LShiftL lreg scale));
4853   op_cost(0);
4854   format %{ "$reg, $lreg lsl($scale)" %}
4855   interface(MEMORY_INTER) %{
4856     base($reg);
4857     index($lreg);
4858     scale($scale);
4859     disp(0x0);
4860   %}
4861 %}
4862 
4863 operand indIndexI2L(iRegP reg, iRegI ireg)
4864 %{
4865   constraint(ALLOC_IN_RC(ptr_reg));
4866   match(AddP reg (ConvI2L ireg));
4867   op_cost(0);
4868   format %{ "$reg, $ireg, 0, I2L" %}
4869   interface(MEMORY_INTER) %{
4870     base($reg);
4871     index($ireg);
4872     scale(0x0);
4873     disp(0x0);
4874   %}
4875 %}
4876 
4877 operand indIndex(iRegP reg, iRegL lreg)
4878 %{
4879   constraint(ALLOC_IN_RC(ptr_reg));
4880   match(AddP reg lreg);
4881   op_cost(0);
4882   format %{ "$reg, $lreg" %}
4883   interface(MEMORY_INTER) %{
4884     base($reg);
4885     index($lreg);
4886     scale(0x0);
4887     disp(0x0);
4888   %}
4889 %}
4890 
4891 operand indOffI(iRegP reg, immIOffset off)
4892 %{
4893   constraint(ALLOC_IN_RC(ptr_reg));
4894   match(AddP reg off);
4895   op_cost(0);
4896   format %{ "[$reg, $off]" %}
4897   interface(MEMORY_INTER) %{
4898     base($reg);
4899     index(0xffffffff);
4900     scale(0x0);
4901     disp($off);
4902   %}
4903 %}
4904 
4905 operand indOffI4(iRegP reg, immIOffset4 off)
4906 %{
4907   constraint(ALLOC_IN_RC(ptr_reg));
4908   match(AddP reg off);
4909   op_cost(0);
4910   format %{ "[$reg, $off]" %}
4911   interface(MEMORY_INTER) %{
4912     base($reg);
4913     index(0xffffffff);
4914     scale(0x0);
4915     disp($off);
4916   %}
4917 %}
4918 
4919 operand indOffI8(iRegP reg, immIOffset8 off)
4920 %{
4921   constraint(ALLOC_IN_RC(ptr_reg));
4922   match(AddP reg off);
4923   op_cost(0);
4924   format %{ "[$reg, $off]" %}
4925   interface(MEMORY_INTER) %{
4926     base($reg);
4927     index(0xffffffff);
4928     scale(0x0);
4929     disp($off);
4930   %}
4931 %}
4932 
4933 operand indOffI16(iRegP reg, immIOffset16 off)
4934 %{
4935   constraint(ALLOC_IN_RC(ptr_reg));
4936   match(AddP reg off);
4937   op_cost(0);
4938   format %{ "[$reg, $off]" %}
4939   interface(MEMORY_INTER) %{
4940     base($reg);
4941     index(0xffffffff);
4942     scale(0x0);
4943     disp($off);
4944   %}
4945 %}
4946 
4947 operand indOffL(iRegP reg, immLoffset off)
4948 %{
4949   constraint(ALLOC_IN_RC(ptr_reg));
4950   match(AddP reg off);
4951   op_cost(0);
4952   format %{ "[$reg, $off]" %}
4953   interface(MEMORY_INTER) %{
4954     base($reg);
4955     index(0xffffffff);
4956     scale(0x0);
4957     disp($off);
4958   %}
4959 %}
4960 
4961 operand indOffL4(iRegP reg, immLoffset4 off)
4962 %{
4963   constraint(ALLOC_IN_RC(ptr_reg));
4964   match(AddP reg off);
4965   op_cost(0);
4966   format %{ "[$reg, $off]" %}
4967   interface(MEMORY_INTER) %{
4968     base($reg);
4969     index(0xffffffff);
4970     scale(0x0);
4971     disp($off);
4972   %}
4973 %}
4974 
4975 operand indOffL8(iRegP reg, immLoffset8 off)
4976 %{
4977   constraint(ALLOC_IN_RC(ptr_reg));
4978   match(AddP reg off);
4979   op_cost(0);
4980   format %{ "[$reg, $off]" %}
4981   interface(MEMORY_INTER) %{
4982     base($reg);
4983     index(0xffffffff);
4984     scale(0x0);
4985     disp($off);
4986   %}
4987 %}
4988 
4989 operand indOffL16(iRegP reg, immLoffset16 off)
4990 %{
4991   constraint(ALLOC_IN_RC(ptr_reg));
4992   match(AddP reg off);
4993   op_cost(0);
4994   format %{ "[$reg, $off]" %}
4995   interface(MEMORY_INTER) %{
4996     base($reg);
4997     index(0xffffffff);
4998     scale(0x0);
4999     disp($off);
5000   %}
5001 %}
5002 
5003 operand indirectN(iRegN reg)
5004 %{
5005   predicate(Universe::narrow_oop_shift() == 0);
5006   constraint(ALLOC_IN_RC(ptr_reg));
5007   match(DecodeN reg);
5008   op_cost(0);
5009   format %{ "[$reg]\t# narrow" %}
5010   interface(MEMORY_INTER) %{
5011     base($reg);
5012     index(0xffffffff);
5013     scale(0x0);
5014     disp(0x0);
5015   %}
5016 %}
5017 
5018 operand indIndexScaledI2LN(iRegN reg, iRegI ireg, immIScale scale)
5019 %{
5020   predicate(Universe::narrow_oop_shift() == 0 && size_fits_all_mem_uses(n->as_AddP(), n->in(AddPNode::Offset)->in(2)->get_int()));
5021   constraint(ALLOC_IN_RC(ptr_reg));
5022   match(AddP (DecodeN reg) (LShiftL (ConvI2L ireg) scale));
5023   op_cost(0);
5024   format %{ "$reg, $ireg sxtw($scale), 0, I2L\t# narrow" %}
5025   interface(MEMORY_INTER) %{
5026     base($reg);
5027     index($ireg);
5028     scale($scale);
5029     disp(0x0);
5030   %}
5031 %}
5032 
5033 operand indIndexScaledN(iRegN reg, iRegL lreg, immIScale scale)
5034 %{
5035   predicate(Universe::narrow_oop_shift() == 0 && size_fits_all_mem_uses(n->as_AddP(), n->in(AddPNode::Offset)->in(2)->get_int()));
5036   constraint(ALLOC_IN_RC(ptr_reg));
5037   match(AddP (DecodeN reg) (LShiftL lreg scale));
5038   op_cost(0);
5039   format %{ "$reg, $lreg lsl($scale)\t# narrow" %}
5040   interface(MEMORY_INTER) %{
5041     base($reg);
5042     index($lreg);
5043     scale($scale);
5044     disp(0x0);
5045   %}
5046 %}
5047 
5048 operand indIndexI2LN(iRegN reg, iRegI ireg)
5049 %{
5050   predicate(Universe::narrow_oop_shift() == 0);
5051   constraint(ALLOC_IN_RC(ptr_reg));
5052   match(AddP (DecodeN reg) (ConvI2L ireg));
5053   op_cost(0);
5054   format %{ "$reg, $ireg, 0, I2L\t# narrow" %}
5055   interface(MEMORY_INTER) %{
5056     base($reg);
5057     index($ireg);
5058     scale(0x0);
5059     disp(0x0);
5060   %}
5061 %}
5062 
5063 operand indIndexN(iRegN reg, iRegL lreg)
5064 %{
5065   predicate(Universe::narrow_oop_shift() == 0);
5066   constraint(ALLOC_IN_RC(ptr_reg));
5067   match(AddP (DecodeN reg) lreg);
5068   op_cost(0);
5069   format %{ "$reg, $lreg\t# narrow" %}
5070   interface(MEMORY_INTER) %{
5071     base($reg);
5072     index($lreg);
5073     scale(0x0);
5074     disp(0x0);
5075   %}
5076 %}
5077 
5078 operand indOffIN(iRegN reg, immIOffset off)
5079 %{
5080   predicate(Universe::narrow_oop_shift() == 0);
5081   constraint(ALLOC_IN_RC(ptr_reg));
5082   match(AddP (DecodeN reg) off);
5083   op_cost(0);
5084   format %{ "[$reg, $off]\t# narrow" %}
5085   interface(MEMORY_INTER) %{
5086     base($reg);
5087     index(0xffffffff);
5088     scale(0x0);
5089     disp($off);
5090   %}
5091 %}
5092 
5093 operand indOffLN(iRegN reg, immLoffset off)
5094 %{
5095   predicate(Universe::narrow_oop_shift() == 0);
5096   constraint(ALLOC_IN_RC(ptr_reg));
5097   match(AddP (DecodeN reg) off);
5098   op_cost(0);
5099   format %{ "[$reg, $off]\t# narrow" %}
5100   interface(MEMORY_INTER) %{
5101     base($reg);
5102     index(0xffffffff);
5103     scale(0x0);
5104     disp($off);
5105   %}
5106 %}
5107 
5108 
5109 
5110 // AArch64 opto stubs need to write to the pc slot in the thread anchor
5111 operand thread_anchor_pc(thread_RegP reg, immL_pc_off off)
5112 %{
5113   constraint(ALLOC_IN_RC(ptr_reg));
5114   match(AddP reg off);
5115   op_cost(0);
5116   format %{ "[$reg, $off]" %}
5117   interface(MEMORY_INTER) %{
5118     base($reg);
5119     index(0xffffffff);
5120     scale(0x0);
5121     disp($off);
5122   %}
5123 %}
5124 
5125 //----------Special Memory Operands--------------------------------------------
5126 // Stack Slot Operand - This operand is used for loading and storing temporary
5127 //                      values on the stack where a match requires a value to
5128 //                      flow through memory.
5129 operand stackSlotP(sRegP reg)
5130 %{
5131   constraint(ALLOC_IN_RC(stack_slots));
5132   op_cost(100);
5133   // No match rule because this operand is only generated in matching
5134   // match(RegP);
5135   format %{ "[$reg]" %}
5136   interface(MEMORY_INTER) %{
5137     base(0x1e);  // RSP
5138     index(0x0);  // No Index
5139     scale(0x0);  // No Scale
5140     disp($reg);  // Stack Offset
5141   %}
5142 %}
5143 
5144 operand stackSlotI(sRegI reg)
5145 %{
5146   constraint(ALLOC_IN_RC(stack_slots));
5147   // No match rule because this operand is only generated in matching
5148   // match(RegI);
5149   format %{ "[$reg]" %}
5150   interface(MEMORY_INTER) %{
5151     base(0x1e);  // RSP
5152     index(0x0);  // No Index
5153     scale(0x0);  // No Scale
5154     disp($reg);  // Stack Offset
5155   %}
5156 %}
5157 
5158 operand stackSlotF(sRegF reg)
5159 %{
5160   constraint(ALLOC_IN_RC(stack_slots));
5161   // No match rule because this operand is only generated in matching
5162   // match(RegF);
5163   format %{ "[$reg]" %}
5164   interface(MEMORY_INTER) %{
5165     base(0x1e);  // RSP
5166     index(0x0);  // No Index
5167     scale(0x0);  // No Scale
5168     disp($reg);  // Stack Offset
5169   %}
5170 %}
5171 
5172 operand stackSlotD(sRegD reg)
5173 %{
5174   constraint(ALLOC_IN_RC(stack_slots));
5175   // No match rule because this operand is only generated in matching
5176   // match(RegD);
5177   format %{ "[$reg]" %}
5178   interface(MEMORY_INTER) %{
5179     base(0x1e);  // RSP
5180     index(0x0);  // No Index
5181     scale(0x0);  // No Scale
5182     disp($reg);  // Stack Offset
5183   %}
5184 %}
5185 
5186 operand stackSlotL(sRegL reg)
5187 %{
5188   constraint(ALLOC_IN_RC(stack_slots));
5189   // No match rule because this operand is only generated in matching
5190   // match(RegL);
5191   format %{ "[$reg]" %}
5192   interface(MEMORY_INTER) %{
5193     base(0x1e);  // RSP
5194     index(0x0);  // No Index
5195     scale(0x0);  // No Scale
5196     disp($reg);  // Stack Offset
5197   %}
5198 %}
5199 
5200 // Operands for expressing Control Flow
5201 // NOTE: Label is a predefined operand which should not be redefined in
5202 //       the AD file. It is generically handled within the ADLC.
5203 
5204 //----------Conditional Branch Operands----------------------------------------
5205 // Comparison Op  - This is the operation of the comparison, and is limited to
5206 //                  the following set of codes:
5207 //                  L (<), LE (<=), G (>), GE (>=), E (==), NE (!=)
5208 //
5209 // Other attributes of the comparison, such as unsignedness, are specified
5210 // by the comparison instruction that sets a condition code flags register.
5211 // That result is represented by a flags operand whose subtype is appropriate
5212 // to the unsignedness (etc.) of the comparison.
5213 //
5214 // Later, the instruction which matches both the Comparison Op (a Bool) and
5215 // the flags (produced by the Cmp) specifies the coding of the comparison op
5216 // by matching a specific subtype of Bool operand below, such as cmpOpU.
5217 
5218 // used for signed integral comparisons and fp comparisons
5219 
5220 operand cmpOp()
5221 %{
5222   match(Bool);
5223 
5224   format %{ "" %}
5225   interface(COND_INTER) %{
5226     equal(0x0, "eq");
5227     not_equal(0x1, "ne");
5228     less(0xb, "lt");
5229     greater_equal(0xa, "ge");
5230     less_equal(0xd, "le");
5231     greater(0xc, "gt");
5232     overflow(0x6, "vs");
5233     no_overflow(0x7, "vc");
5234   %}
5235 %}
5236 
5237 // used for unsigned integral comparisons
5238 
5239 operand cmpOpU()
5240 %{
5241   match(Bool);
5242 
5243   format %{ "" %}
5244   interface(COND_INTER) %{
5245     equal(0x0, "eq");
5246     not_equal(0x1, "ne");
5247     less(0x3, "lo");
5248     greater_equal(0x2, "hs");
5249     less_equal(0x9, "ls");
5250     greater(0x8, "hi");
5251     overflow(0x6, "vs");
5252     no_overflow(0x7, "vc");
5253   %}
5254 %}
5255 
5256 // used for certain integral comparisons which can be
5257 // converted to cbxx or tbxx instructions
5258 
5259 operand cmpOpEqNe()
5260 %{
5261   match(Bool);
5262   match(CmpOp);
5263   op_cost(0);
5264   predicate(n->as_Bool()->_test._test == BoolTest::ne
5265             || n->as_Bool()->_test._test == BoolTest::eq);
5266 
5267   format %{ "" %}
5268   interface(COND_INTER) %{
5269     equal(0x0, "eq");
5270     not_equal(0x1, "ne");
5271     less(0xb, "lt");
5272     greater_equal(0xa, "ge");
5273     less_equal(0xd, "le");
5274     greater(0xc, "gt");
5275     overflow(0x6, "vs");
5276     no_overflow(0x7, "vc");
5277   %}
5278 %}
5279 
5280 // used for certain integral comparisons which can be
5281 // converted to cbxx or tbxx instructions
5282 
5283 operand cmpOpLtGe()
5284 %{
5285   match(Bool);
5286   match(CmpOp);
5287   op_cost(0);
5288 
5289   predicate(n->as_Bool()->_test._test == BoolTest::lt
5290             || n->as_Bool()->_test._test == BoolTest::ge);
5291 
5292   format %{ "" %}
5293   interface(COND_INTER) %{
5294     equal(0x0, "eq");
5295     not_equal(0x1, "ne");
5296     less(0xb, "lt");
5297     greater_equal(0xa, "ge");
5298     less_equal(0xd, "le");
5299     greater(0xc, "gt");
5300     overflow(0x6, "vs");
5301     no_overflow(0x7, "vc");
5302   %}
5303 %}
5304 
5305 // used for certain unsigned integral comparisons which can be
5306 // converted to cbxx or tbxx instructions
5307 
5308 operand cmpOpUEqNeLtGe()
5309 %{
5310   match(Bool);
5311   match(CmpOp);
5312   op_cost(0);
5313 
5314   predicate(n->as_Bool()->_test._test == BoolTest::eq
5315             || n->as_Bool()->_test._test == BoolTest::ne
5316             || n->as_Bool()->_test._test == BoolTest::lt
5317             || n->as_Bool()->_test._test == BoolTest::ge);
5318 
5319   format %{ "" %}
5320   interface(COND_INTER) %{
5321     equal(0x0, "eq");
5322     not_equal(0x1, "ne");
5323     less(0xb, "lt");
5324     greater_equal(0xa, "ge");
5325     less_equal(0xd, "le");
5326     greater(0xc, "gt");
5327     overflow(0x6, "vs");
5328     no_overflow(0x7, "vc");
5329   %}
5330 %}
5331 
5332 // Special operand allowing long args to int ops to be truncated for free
5333 
5334 operand iRegL2I(iRegL reg) %{
5335 
5336   op_cost(0);
5337 
5338   match(ConvL2I reg);
5339 
5340   format %{ "l2i($reg)" %}
5341 
5342   interface(REG_INTER)
5343 %}
5344 
5345 opclass vmem4(indirect, indIndex, indOffI4, indOffL4);
5346 opclass vmem8(indirect, indIndex, indOffI8, indOffL8);
5347 opclass vmem16(indirect, indIndex, indOffI16, indOffL16);
5348 
5349 //----------OPERAND CLASSES----------------------------------------------------
5350 // Operand Classes are groups of operands that are used as to simplify
5351 // instruction definitions by not requiring the AD writer to specify
5352 // separate instructions for every form of operand when the
5353 // instruction accepts multiple operand types with the same basic
5354 // encoding and format. The classic case of this is memory operands.
5355 
5356 // memory is used to define read/write location for load/store
5357 // instruction defs. we can turn a memory op into an Address
5358 
5359 opclass memory(indirect, indIndexScaled, indIndexScaledI2L, indIndexI2L, indIndex, indOffI, indOffL,
5360                indirectN, indIndexScaledN, indIndexScaledI2LN, indIndexI2LN, indIndexN, indOffIN, indOffLN);
5361 
5362 // iRegIorL2I is used for src inputs in rules for 32 bit int (I)
5363 // operations. it allows the src to be either an iRegI or a (ConvL2I
5364 // iRegL). in the latter case the l2i normally planted for a ConvL2I
5365 // can be elided because the 32-bit instruction will just employ the
5366 // lower 32 bits anyway.
5367 //
5368 // n.b. this does not elide all L2I conversions. if the truncated
5369 // value is consumed by more than one operation then the ConvL2I
5370 // cannot be bundled into the consuming nodes so an l2i gets planted
5371 // (actually a movw $dst $src) and the downstream instructions consume
5372 // the result of the l2i as an iRegI input. That's a shame since the
5373 // movw is actually redundant but its not too costly.
5374 
5375 opclass iRegIorL2I(iRegI, iRegL2I);
5376 
5377 //----------PIPELINE-----------------------------------------------------------
5378 // Rules which define the behavior of the target architectures pipeline.
5379 
5380 // For specific pipelines, eg A53, define the stages of that pipeline
5381 //pipe_desc(ISS, EX1, EX2, WR);
5382 #define ISS S0
5383 #define EX1 S1
5384 #define EX2 S2
5385 #define WR  S3
5386 
5387 // Integer ALU reg operation
5388 pipeline %{
5389 
5390 attributes %{
5391   // ARM instructions are of fixed length
5392   fixed_size_instructions;        // Fixed size instructions TODO does
5393   max_instructions_per_bundle = 2;   // A53 = 2, A57 = 4
5394   // ARM instructions come in 32-bit word units
5395   instruction_unit_size = 4;         // An instruction is 4 bytes long
5396   instruction_fetch_unit_size = 64;  // The processor fetches one line
5397   instruction_fetch_units = 1;       // of 64 bytes
5398 
5399   // List of nop instructions
5400   nops( MachNop );
5401 %}
5402 
5403 // We don't use an actual pipeline model so don't care about resources
5404 // or description. we do use pipeline classes to introduce fixed
5405 // latencies
5406 
5407 //----------RESOURCES----------------------------------------------------------
5408 // Resources are the functional units available to the machine
5409 
5410 resources( INS0, INS1, INS01 = INS0 | INS1,
5411            ALU0, ALU1, ALU = ALU0 | ALU1,
5412            MAC,
5413            DIV,
5414            BRANCH,
5415            LDST,
5416            NEON_FP);
5417 
5418 //----------PIPELINE DESCRIPTION-----------------------------------------------
5419 // Pipeline Description specifies the stages in the machine's pipeline
5420 
5421 // Define the pipeline as a generic 6 stage pipeline
5422 pipe_desc(S0, S1, S2, S3, S4, S5);
5423 
5424 //----------PIPELINE CLASSES---------------------------------------------------
5425 // Pipeline Classes describe the stages in which input and output are
5426 // referenced by the hardware pipeline.
5427 
5428 pipe_class fp_dop_reg_reg_s(vRegF dst, vRegF src1, vRegF src2)
5429 %{
5430   single_instruction;
5431   src1   : S1(read);
5432   src2   : S2(read);
5433   dst    : S5(write);
5434   INS01  : ISS;
5435   NEON_FP : S5;
5436 %}
5437 
5438 pipe_class fp_dop_reg_reg_d(vRegD dst, vRegD src1, vRegD src2)
5439 %{
5440   single_instruction;
5441   src1   : S1(read);
5442   src2   : S2(read);
5443   dst    : S5(write);
5444   INS01  : ISS;
5445   NEON_FP : S5;
5446 %}
5447 
5448 pipe_class fp_uop_s(vRegF dst, vRegF src)
5449 %{
5450   single_instruction;
5451   src    : S1(read);
5452   dst    : S5(write);
5453   INS01  : ISS;
5454   NEON_FP : S5;
5455 %}
5456 
5457 pipe_class fp_uop_d(vRegD dst, vRegD src)
5458 %{
5459   single_instruction;
5460   src    : S1(read);
5461   dst    : S5(write);
5462   INS01  : ISS;
5463   NEON_FP : S5;
5464 %}
5465 
5466 pipe_class fp_d2f(vRegF dst, vRegD src)
5467 %{
5468   single_instruction;
5469   src    : S1(read);
5470   dst    : S5(write);
5471   INS01  : ISS;
5472   NEON_FP : S5;
5473 %}
5474 
5475 pipe_class fp_f2d(vRegD dst, vRegF src)
5476 %{
5477   single_instruction;
5478   src    : S1(read);
5479   dst    : S5(write);
5480   INS01  : ISS;
5481   NEON_FP : S5;
5482 %}
5483 
5484 pipe_class fp_f2i(iRegINoSp dst, vRegF src)
5485 %{
5486   single_instruction;
5487   src    : S1(read);
5488   dst    : S5(write);
5489   INS01  : ISS;
5490   NEON_FP : S5;
5491 %}
5492 
5493 pipe_class fp_f2l(iRegLNoSp dst, vRegF src)
5494 %{
5495   single_instruction;
5496   src    : S1(read);
5497   dst    : S5(write);
5498   INS01  : ISS;
5499   NEON_FP : S5;
5500 %}
5501 
5502 pipe_class fp_i2f(vRegF dst, iRegIorL2I src)
5503 %{
5504   single_instruction;
5505   src    : S1(read);
5506   dst    : S5(write);
5507   INS01  : ISS;
5508   NEON_FP : S5;
5509 %}
5510 
5511 pipe_class fp_l2f(vRegF dst, iRegL src)
5512 %{
5513   single_instruction;
5514   src    : S1(read);
5515   dst    : S5(write);
5516   INS01  : ISS;
5517   NEON_FP : S5;
5518 %}
5519 
5520 pipe_class fp_d2i(iRegINoSp dst, vRegD src)
5521 %{
5522   single_instruction;
5523   src    : S1(read);
5524   dst    : S5(write);
5525   INS01  : ISS;
5526   NEON_FP : S5;
5527 %}
5528 
5529 pipe_class fp_d2l(iRegLNoSp dst, vRegD src)
5530 %{
5531   single_instruction;
5532   src    : S1(read);
5533   dst    : S5(write);
5534   INS01  : ISS;
5535   NEON_FP : S5;
5536 %}
5537 
5538 pipe_class fp_i2d(vRegD dst, iRegIorL2I src)
5539 %{
5540   single_instruction;
5541   src    : S1(read);
5542   dst    : S5(write);
5543   INS01  : ISS;
5544   NEON_FP : S5;
5545 %}
5546 
5547 pipe_class fp_l2d(vRegD dst, iRegIorL2I src)
5548 %{
5549   single_instruction;
5550   src    : S1(read);
5551   dst    : S5(write);
5552   INS01  : ISS;
5553   NEON_FP : S5;
5554 %}
5555 
5556 pipe_class fp_div_s(vRegF dst, vRegF src1, vRegF src2)
5557 %{
5558   single_instruction;
5559   src1   : S1(read);
5560   src2   : S2(read);
5561   dst    : S5(write);
5562   INS0   : ISS;
5563   NEON_FP : S5;
5564 %}
5565 
5566 pipe_class fp_div_d(vRegD dst, vRegD src1, vRegD src2)
5567 %{
5568   single_instruction;
5569   src1   : S1(read);
5570   src2   : S2(read);
5571   dst    : S5(write);
5572   INS0   : ISS;
5573   NEON_FP : S5;
5574 %}
5575 
5576 pipe_class fp_cond_reg_reg_s(vRegF dst, vRegF src1, vRegF src2, rFlagsReg cr)
5577 %{
5578   single_instruction;
5579   cr     : S1(read);
5580   src1   : S1(read);
5581   src2   : S1(read);
5582   dst    : S3(write);
5583   INS01  : ISS;
5584   NEON_FP : S3;
5585 %}
5586 
5587 pipe_class fp_cond_reg_reg_d(vRegD dst, vRegD src1, vRegD src2, rFlagsReg cr)
5588 %{
5589   single_instruction;
5590   cr     : S1(read);
5591   src1   : S1(read);
5592   src2   : S1(read);
5593   dst    : S3(write);
5594   INS01  : ISS;
5595   NEON_FP : S3;
5596 %}
5597 
5598 pipe_class fp_imm_s(vRegF dst)
5599 %{
5600   single_instruction;
5601   dst    : S3(write);
5602   INS01  : ISS;
5603   NEON_FP : S3;
5604 %}
5605 
5606 pipe_class fp_imm_d(vRegD dst)
5607 %{
5608   single_instruction;
5609   dst    : S3(write);
5610   INS01  : ISS;
5611   NEON_FP : S3;
5612 %}
5613 
5614 pipe_class fp_load_constant_s(vRegF dst)
5615 %{
5616   single_instruction;
5617   dst    : S4(write);
5618   INS01  : ISS;
5619   NEON_FP : S4;
5620 %}
5621 
5622 pipe_class fp_load_constant_d(vRegD dst)
5623 %{
5624   single_instruction;
5625   dst    : S4(write);
5626   INS01  : ISS;
5627   NEON_FP : S4;
5628 %}
5629 
5630 pipe_class vmul64(vecD dst, vecD src1, vecD src2)
5631 %{
5632   single_instruction;
5633   dst    : S5(write);
5634   src1   : S1(read);
5635   src2   : S1(read);
5636   INS01  : ISS;
5637   NEON_FP : S5;
5638 %}
5639 
5640 pipe_class vmul128(vecX dst, vecX src1, vecX src2)
5641 %{
5642   single_instruction;
5643   dst    : S5(write);
5644   src1   : S1(read);
5645   src2   : S1(read);
5646   INS0   : ISS;
5647   NEON_FP : S5;
5648 %}
5649 
5650 pipe_class vmla64(vecD dst, vecD src1, vecD src2)
5651 %{
5652   single_instruction;
5653   dst    : S5(write);
5654   src1   : S1(read);
5655   src2   : S1(read);
5656   dst    : S1(read);
5657   INS01  : ISS;
5658   NEON_FP : S5;
5659 %}
5660 
5661 pipe_class vmla128(vecX dst, vecX src1, vecX src2)
5662 %{
5663   single_instruction;
5664   dst    : S5(write);
5665   src1   : S1(read);
5666   src2   : S1(read);
5667   dst    : S1(read);
5668   INS0   : ISS;
5669   NEON_FP : S5;
5670 %}
5671 
5672 pipe_class vdop64(vecD dst, vecD src1, vecD src2)
5673 %{
5674   single_instruction;
5675   dst    : S4(write);
5676   src1   : S2(read);
5677   src2   : S2(read);
5678   INS01  : ISS;
5679   NEON_FP : S4;
5680 %}
5681 
5682 pipe_class vdop128(vecX dst, vecX src1, vecX src2)
5683 %{
5684   single_instruction;
5685   dst    : S4(write);
5686   src1   : S2(read);
5687   src2   : S2(read);
5688   INS0   : ISS;
5689   NEON_FP : S4;
5690 %}
5691 
5692 pipe_class vlogical64(vecD dst, vecD src1, vecD src2)
5693 %{
5694   single_instruction;
5695   dst    : S3(write);
5696   src1   : S2(read);
5697   src2   : S2(read);
5698   INS01  : ISS;
5699   NEON_FP : S3;
5700 %}
5701 
5702 pipe_class vlogical128(vecX dst, vecX src1, vecX src2)
5703 %{
5704   single_instruction;
5705   dst    : S3(write);
5706   src1   : S2(read);
5707   src2   : S2(read);
5708   INS0   : ISS;
5709   NEON_FP : S3;
5710 %}
5711 
5712 pipe_class vshift64(vecD dst, vecD src, vecX shift)
5713 %{
5714   single_instruction;
5715   dst    : S3(write);
5716   src    : S1(read);
5717   shift  : S1(read);
5718   INS01  : ISS;
5719   NEON_FP : S3;
5720 %}
5721 
5722 pipe_class vshift128(vecX dst, vecX src, vecX shift)
5723 %{
5724   single_instruction;
5725   dst    : S3(write);
5726   src    : S1(read);
5727   shift  : S1(read);
5728   INS0   : ISS;
5729   NEON_FP : S3;
5730 %}
5731 
5732 pipe_class vshift64_imm(vecD dst, vecD src, immI shift)
5733 %{
5734   single_instruction;
5735   dst    : S3(write);
5736   src    : S1(read);
5737   INS01  : ISS;
5738   NEON_FP : S3;
5739 %}
5740 
5741 pipe_class vshift128_imm(vecX dst, vecX src, immI shift)
5742 %{
5743   single_instruction;
5744   dst    : S3(write);
5745   src    : S1(read);
5746   INS0   : ISS;
5747   NEON_FP : S3;
5748 %}
5749 
5750 pipe_class vdop_fp64(vecD dst, vecD src1, vecD src2)
5751 %{
5752   single_instruction;
5753   dst    : S5(write);
5754   src1   : S1(read);
5755   src2   : S1(read);
5756   INS01  : ISS;
5757   NEON_FP : S5;
5758 %}
5759 
5760 pipe_class vdop_fp128(vecX dst, vecX src1, vecX src2)
5761 %{
5762   single_instruction;
5763   dst    : S5(write);
5764   src1   : S1(read);
5765   src2   : S1(read);
5766   INS0   : ISS;
5767   NEON_FP : S5;
5768 %}
5769 
5770 pipe_class vmuldiv_fp64(vecD dst, vecD src1, vecD src2)
5771 %{
5772   single_instruction;
5773   dst    : S5(write);
5774   src1   : S1(read);
5775   src2   : S1(read);
5776   INS0   : ISS;
5777   NEON_FP : S5;
5778 %}
5779 
5780 pipe_class vmuldiv_fp128(vecX dst, vecX src1, vecX src2)
5781 %{
5782   single_instruction;
5783   dst    : S5(write);
5784   src1   : S1(read);
5785   src2   : S1(read);
5786   INS0   : ISS;
5787   NEON_FP : S5;
5788 %}
5789 
5790 pipe_class vsqrt_fp128(vecX dst, vecX src)
5791 %{
5792   single_instruction;
5793   dst    : S5(write);
5794   src    : S1(read);
5795   INS0   : ISS;
5796   NEON_FP : S5;
5797 %}
5798 
5799 pipe_class vunop_fp64(vecD dst, vecD src)
5800 %{
5801   single_instruction;
5802   dst    : S5(write);
5803   src    : S1(read);
5804   INS01  : ISS;
5805   NEON_FP : S5;
5806 %}
5807 
5808 pipe_class vunop_fp128(vecX dst, vecX src)
5809 %{
5810   single_instruction;
5811   dst    : S5(write);
5812   src    : S1(read);
5813   INS0   : ISS;
5814   NEON_FP : S5;
5815 %}
5816 
5817 pipe_class vdup_reg_reg64(vecD dst, iRegI src)
5818 %{
5819   single_instruction;
5820   dst    : S3(write);
5821   src    : S1(read);
5822   INS01  : ISS;
5823   NEON_FP : S3;
5824 %}
5825 
5826 pipe_class vdup_reg_reg128(vecX dst, iRegI src)
5827 %{
5828   single_instruction;
5829   dst    : S3(write);
5830   src    : S1(read);
5831   INS01  : ISS;
5832   NEON_FP : S3;
5833 %}
5834 
5835 pipe_class vdup_reg_freg64(vecD dst, vRegF src)
5836 %{
5837   single_instruction;
5838   dst    : S3(write);
5839   src    : S1(read);
5840   INS01  : ISS;
5841   NEON_FP : S3;
5842 %}
5843 
5844 pipe_class vdup_reg_freg128(vecX dst, vRegF src)
5845 %{
5846   single_instruction;
5847   dst    : S3(write);
5848   src    : S1(read);
5849   INS01  : ISS;
5850   NEON_FP : S3;
5851 %}
5852 
5853 pipe_class vdup_reg_dreg128(vecX dst, vRegD src)
5854 %{
5855   single_instruction;
5856   dst    : S3(write);
5857   src    : S1(read);
5858   INS01  : ISS;
5859   NEON_FP : S3;
5860 %}
5861 
5862 pipe_class vmovi_reg_imm64(vecD dst)
5863 %{
5864   single_instruction;
5865   dst    : S3(write);
5866   INS01  : ISS;
5867   NEON_FP : S3;
5868 %}
5869 
5870 pipe_class vmovi_reg_imm128(vecX dst)
5871 %{
5872   single_instruction;
5873   dst    : S3(write);
5874   INS0   : ISS;
5875   NEON_FP : S3;
5876 %}
5877 
5878 pipe_class vload_reg_mem64(vecD dst, vmem8 mem)
5879 %{
5880   single_instruction;
5881   dst    : S5(write);
5882   mem    : ISS(read);
5883   INS01  : ISS;
5884   NEON_FP : S3;
5885 %}
5886 
5887 pipe_class vload_reg_mem128(vecX dst, vmem16 mem)
5888 %{
5889   single_instruction;
5890   dst    : S5(write);
5891   mem    : ISS(read);
5892   INS01  : ISS;
5893   NEON_FP : S3;
5894 %}
5895 
5896 pipe_class vstore_reg_mem64(vecD src, vmem8 mem)
5897 %{
5898   single_instruction;
5899   mem    : ISS(read);
5900   src    : S2(read);
5901   INS01  : ISS;
5902   NEON_FP : S3;
5903 %}
5904 
5905 pipe_class vstore_reg_mem128(vecD src, vmem16 mem)
5906 %{
5907   single_instruction;
5908   mem    : ISS(read);
5909   src    : S2(read);
5910   INS01  : ISS;
5911   NEON_FP : S3;
5912 %}
5913 
5914 //------- Integer ALU operations --------------------------
5915 
5916 // Integer ALU reg-reg operation
5917 // Operands needed in EX1, result generated in EX2
5918 // Eg.  ADD     x0, x1, x2
5919 pipe_class ialu_reg_reg(iRegI dst, iRegI src1, iRegI src2)
5920 %{
5921   single_instruction;
5922   dst    : EX2(write);
5923   src1   : EX1(read);
5924   src2   : EX1(read);
5925   INS01  : ISS; // Dual issue as instruction 0 or 1
5926   ALU    : EX2;
5927 %}
5928 
5929 // Integer ALU reg-reg operation with constant shift
5930 // Shifted register must be available in LATE_ISS instead of EX1
5931 // Eg.  ADD     x0, x1, x2, LSL #2
5932 pipe_class ialu_reg_reg_shift(iRegI dst, iRegI src1, iRegI src2, immI shift)
5933 %{
5934   single_instruction;
5935   dst    : EX2(write);
5936   src1   : EX1(read);
5937   src2   : ISS(read);
5938   INS01  : ISS;
5939   ALU    : EX2;
5940 %}
5941 
5942 // Integer ALU reg operation with constant shift
5943 // Eg.  LSL     x0, x1, #shift
5944 pipe_class ialu_reg_shift(iRegI dst, iRegI src1)
5945 %{
5946   single_instruction;
5947   dst    : EX2(write);
5948   src1   : ISS(read);
5949   INS01  : ISS;
5950   ALU    : EX2;
5951 %}
5952 
5953 // Integer ALU reg-reg operation with variable shift
5954 // Both operands must be available in LATE_ISS instead of EX1
5955 // Result is available in EX1 instead of EX2
5956 // Eg.  LSLV    x0, x1, x2
5957 pipe_class ialu_reg_reg_vshift(iRegI dst, iRegI src1, iRegI src2)
5958 %{
5959   single_instruction;
5960   dst    : EX1(write);
5961   src1   : ISS(read);
5962   src2   : ISS(read);
5963   INS01  : ISS;
5964   ALU    : EX1;
5965 %}
5966 
5967 // Integer ALU reg-reg operation with extract
5968 // As for _vshift above, but result generated in EX2
5969 // Eg.  EXTR    x0, x1, x2, #N
5970 pipe_class ialu_reg_reg_extr(iRegI dst, iRegI src1, iRegI src2)
5971 %{
5972   single_instruction;
5973   dst    : EX2(write);
5974   src1   : ISS(read);
5975   src2   : ISS(read);
5976   INS1   : ISS; // Can only dual issue as Instruction 1
5977   ALU    : EX1;
5978 %}
5979 
5980 // Integer ALU reg operation
5981 // Eg.  NEG     x0, x1
5982 pipe_class ialu_reg(iRegI dst, iRegI src)
5983 %{
5984   single_instruction;
5985   dst    : EX2(write);
5986   src    : EX1(read);
5987   INS01  : ISS;
5988   ALU    : EX2;
5989 %}
5990 
5991 // Integer ALU reg mmediate operation
5992 // Eg.  ADD     x0, x1, #N
5993 pipe_class ialu_reg_imm(iRegI dst, iRegI src1)
5994 %{
5995   single_instruction;
5996   dst    : EX2(write);
5997   src1   : EX1(read);
5998   INS01  : ISS;
5999   ALU    : EX2;
6000 %}
6001 
6002 // Integer ALU immediate operation (no source operands)
6003 // Eg.  MOV     x0, #N
6004 pipe_class ialu_imm(iRegI dst)
6005 %{
6006   single_instruction;
6007   dst    : EX1(write);
6008   INS01  : ISS;
6009   ALU    : EX1;
6010 %}
6011 
6012 //------- Compare operation -------------------------------
6013 
6014 // Compare reg-reg
6015 // Eg.  CMP     x0, x1
6016 pipe_class icmp_reg_reg(rFlagsReg cr, iRegI op1, iRegI op2)
6017 %{
6018   single_instruction;
6019 //  fixed_latency(16);
6020   cr     : EX2(write);
6021   op1    : EX1(read);
6022   op2    : EX1(read);
6023   INS01  : ISS;
6024   ALU    : EX2;
6025 %}
6026 
6027 // Compare reg-reg
6028 // Eg.  CMP     x0, #N
6029 pipe_class icmp_reg_imm(rFlagsReg cr, iRegI op1)
6030 %{
6031   single_instruction;
6032 //  fixed_latency(16);
6033   cr     : EX2(write);
6034   op1    : EX1(read);
6035   INS01  : ISS;
6036   ALU    : EX2;
6037 %}
6038 
6039 //------- Conditional instructions ------------------------
6040 
6041 // Conditional no operands
6042 // Eg.  CSINC   x0, zr, zr, <cond>
6043 pipe_class icond_none(iRegI dst, rFlagsReg cr)
6044 %{
6045   single_instruction;
6046   cr     : EX1(read);
6047   dst    : EX2(write);
6048   INS01  : ISS;
6049   ALU    : EX2;
6050 %}
6051 
6052 // Conditional 2 operand
6053 // EG.  CSEL    X0, X1, X2, <cond>
6054 pipe_class icond_reg_reg(iRegI dst, iRegI src1, iRegI src2, rFlagsReg cr)
6055 %{
6056   single_instruction;
6057   cr     : EX1(read);
6058   src1   : EX1(read);
6059   src2   : EX1(read);
6060   dst    : EX2(write);
6061   INS01  : ISS;
6062   ALU    : EX2;
6063 %}
6064 
6065 // Conditional 2 operand
6066 // EG.  CSEL    X0, X1, X2, <cond>
6067 pipe_class icond_reg(iRegI dst, iRegI src, rFlagsReg cr)
6068 %{
6069   single_instruction;
6070   cr     : EX1(read);
6071   src    : EX1(read);
6072   dst    : EX2(write);
6073   INS01  : ISS;
6074   ALU    : EX2;
6075 %}
6076 
6077 //------- Multiply pipeline operations --------------------
6078 
6079 // Multiply reg-reg
6080 // Eg.  MUL     w0, w1, w2
6081 pipe_class imul_reg_reg(iRegI dst, iRegI src1, iRegI src2)
6082 %{
6083   single_instruction;
6084   dst    : WR(write);
6085   src1   : ISS(read);
6086   src2   : ISS(read);
6087   INS01  : ISS;
6088   MAC    : WR;
6089 %}
6090 
6091 // Multiply accumulate
6092 // Eg.  MADD    w0, w1, w2, w3
6093 pipe_class imac_reg_reg(iRegI dst, iRegI src1, iRegI src2, iRegI src3)
6094 %{
6095   single_instruction;
6096   dst    : WR(write);
6097   src1   : ISS(read);
6098   src2   : ISS(read);
6099   src3   : ISS(read);
6100   INS01  : ISS;
6101   MAC    : WR;
6102 %}
6103 
6104 // Eg.  MUL     w0, w1, w2
6105 pipe_class lmul_reg_reg(iRegI dst, iRegI src1, iRegI src2)
6106 %{
6107   single_instruction;
6108   fixed_latency(3); // Maximum latency for 64 bit mul
6109   dst    : WR(write);
6110   src1   : ISS(read);
6111   src2   : ISS(read);
6112   INS01  : ISS;
6113   MAC    : WR;
6114 %}
6115 
6116 // Multiply accumulate
6117 // Eg.  MADD    w0, w1, w2, w3
6118 pipe_class lmac_reg_reg(iRegI dst, iRegI src1, iRegI src2, iRegI src3)
6119 %{
6120   single_instruction;
6121   fixed_latency(3); // Maximum latency for 64 bit mul
6122   dst    : WR(write);
6123   src1   : ISS(read);
6124   src2   : ISS(read);
6125   src3   : ISS(read);
6126   INS01  : ISS;
6127   MAC    : WR;
6128 %}
6129 
6130 //------- Divide pipeline operations --------------------
6131 
6132 // Eg.  SDIV    w0, w1, w2
6133 pipe_class idiv_reg_reg(iRegI dst, iRegI src1, iRegI src2)
6134 %{
6135   single_instruction;
6136   fixed_latency(8); // Maximum latency for 32 bit divide
6137   dst    : WR(write);
6138   src1   : ISS(read);
6139   src2   : ISS(read);
6140   INS0   : ISS; // Can only dual issue as instruction 0
6141   DIV    : WR;
6142 %}
6143 
6144 // Eg.  SDIV    x0, x1, x2
6145 pipe_class ldiv_reg_reg(iRegI dst, iRegI src1, iRegI src2)
6146 %{
6147   single_instruction;
6148   fixed_latency(16); // Maximum latency for 64 bit divide
6149   dst    : WR(write);
6150   src1   : ISS(read);
6151   src2   : ISS(read);
6152   INS0   : ISS; // Can only dual issue as instruction 0
6153   DIV    : WR;
6154 %}
6155 
6156 //------- Load pipeline operations ------------------------
6157 
6158 // Load - prefetch
6159 // Eg.  PFRM    <mem>
6160 pipe_class iload_prefetch(memory mem)
6161 %{
6162   single_instruction;
6163   mem    : ISS(read);
6164   INS01  : ISS;
6165   LDST   : WR;
6166 %}
6167 
6168 // Load - reg, mem
6169 // Eg.  LDR     x0, <mem>
6170 pipe_class iload_reg_mem(iRegI dst, memory mem)
6171 %{
6172   single_instruction;
6173   dst    : WR(write);
6174   mem    : ISS(read);
6175   INS01  : ISS;
6176   LDST   : WR;
6177 %}
6178 
6179 // Load - reg, reg
6180 // Eg.  LDR     x0, [sp, x1]
6181 pipe_class iload_reg_reg(iRegI dst, iRegI src)
6182 %{
6183   single_instruction;
6184   dst    : WR(write);
6185   src    : ISS(read);
6186   INS01  : ISS;
6187   LDST   : WR;
6188 %}
6189 
6190 //------- Store pipeline operations -----------------------
6191 
6192 // Store - zr, mem
6193 // Eg.  STR     zr, <mem>
6194 pipe_class istore_mem(memory mem)
6195 %{
6196   single_instruction;
6197   mem    : ISS(read);
6198   INS01  : ISS;
6199   LDST   : WR;
6200 %}
6201 
6202 // Store - reg, mem
6203 // Eg.  STR     x0, <mem>
6204 pipe_class istore_reg_mem(iRegI src, memory mem)
6205 %{
6206   single_instruction;
6207   mem    : ISS(read);
6208   src    : EX2(read);
6209   INS01  : ISS;
6210   LDST   : WR;
6211 %}
6212 
6213 // Store - reg, reg
6214 // Eg. STR      x0, [sp, x1]
6215 pipe_class istore_reg_reg(iRegI dst, iRegI src)
6216 %{
6217   single_instruction;
6218   dst    : ISS(read);
6219   src    : EX2(read);
6220   INS01  : ISS;
6221   LDST   : WR;
6222 %}
6223 
6224 //------- Store pipeline operations -----------------------
6225 
6226 // Branch
6227 pipe_class pipe_branch()
6228 %{
6229   single_instruction;
6230   INS01  : ISS;
6231   BRANCH : EX1;
6232 %}
6233 
6234 // Conditional branch
6235 pipe_class pipe_branch_cond(rFlagsReg cr)
6236 %{
6237   single_instruction;
6238   cr     : EX1(read);
6239   INS01  : ISS;
6240   BRANCH : EX1;
6241 %}
6242 
6243 // Compare & Branch
6244 // EG.  CBZ/CBNZ
6245 pipe_class pipe_cmp_branch(iRegI op1)
6246 %{
6247   single_instruction;
6248   op1    : EX1(read);
6249   INS01  : ISS;
6250   BRANCH : EX1;
6251 %}
6252 
6253 //------- Synchronisation operations ----------------------
6254 
6255 // Any operation requiring serialization.
6256 // EG.  DMB/Atomic Ops/Load Acquire/Str Release
6257 pipe_class pipe_serial()
6258 %{
6259   single_instruction;
6260   force_serialization;
6261   fixed_latency(16);
6262   INS01  : ISS(2); // Cannot dual issue with any other instruction
6263   LDST   : WR;
6264 %}
6265 
6266 // Generic big/slow expanded idiom - also serialized
6267 pipe_class pipe_slow()
6268 %{
6269   instruction_count(10);
6270   multiple_bundles;
6271   force_serialization;
6272   fixed_latency(16);
6273   INS01  : ISS(2); // Cannot dual issue with any other instruction
6274   LDST   : WR;
6275 %}
6276 
6277 // Empty pipeline class
6278 pipe_class pipe_class_empty()
6279 %{
6280   single_instruction;
6281   fixed_latency(0);
6282 %}
6283 
6284 // Default pipeline class.
6285 pipe_class pipe_class_default()
6286 %{
6287   single_instruction;
6288   fixed_latency(2);
6289 %}
6290 
6291 // Pipeline class for compares.
6292 pipe_class pipe_class_compare()
6293 %{
6294   single_instruction;
6295   fixed_latency(16);
6296 %}
6297 
6298 // Pipeline class for memory operations.
6299 pipe_class pipe_class_memory()
6300 %{
6301   single_instruction;
6302   fixed_latency(16);
6303 %}
6304 
6305 // Pipeline class for call.
6306 pipe_class pipe_class_call()
6307 %{
6308   single_instruction;
6309   fixed_latency(100);
6310 %}
6311 
6312 // Define the class for the Nop node.
6313 define %{
6314    MachNop = pipe_class_empty;
6315 %}
6316 
6317 %}
6318 //----------INSTRUCTIONS-------------------------------------------------------
6319 //
6320 // match      -- States which machine-independent subtree may be replaced
6321 //               by this instruction.
6322 // ins_cost   -- The estimated cost of this instruction is used by instruction
6323 //               selection to identify a minimum cost tree of machine
6324 //               instructions that matches a tree of machine-independent
6325 //               instructions.
6326 // format     -- A string providing the disassembly for this instruction.
6327 //               The value of an instruction's operand may be inserted
6328 //               by referring to it with a '$' prefix.
6329 // opcode     -- Three instruction opcodes may be provided.  These are referred
6330 //               to within an encode class as $primary, $secondary, and $tertiary
6331 //               rrspectively.  The primary opcode is commonly used to
6332 //               indicate the type of machine instruction, while secondary
6333 //               and tertiary are often used for prefix options or addressing
6334 //               modes.
6335 // ins_encode -- A list of encode classes with parameters. The encode class
6336 //               name must have been defined in an 'enc_class' specification
6337 //               in the encode section of the architecture description.
6338 
6339 // ============================================================================
6340 // Memory (Load/Store) Instructions
6341 
6342 // Load Instructions
6343 
6344 // Load Byte (8 bit signed)
6345 instruct loadB(iRegINoSp dst, memory mem)
6346 %{
6347   match(Set dst (LoadB mem));
6348   predicate(!needs_acquiring_load(n));
6349 
6350   ins_cost(4 * INSN_COST);
6351   format %{ "ldrsbw  $dst, $mem\t# byte" %}
6352 
6353   ins_encode(aarch64_enc_ldrsbw(dst, mem));
6354 
6355   ins_pipe(iload_reg_mem);
6356 %}
6357 
6358 // Load Byte (8 bit signed) into long
6359 instruct loadB2L(iRegLNoSp dst, memory mem)
6360 %{
6361   match(Set dst (ConvI2L (LoadB mem)));
6362   predicate(!needs_acquiring_load(n->in(1)));
6363 
6364   ins_cost(4 * INSN_COST);
6365   format %{ "ldrsb  $dst, $mem\t# byte" %}
6366 
6367   ins_encode(aarch64_enc_ldrsb(dst, mem));
6368 
6369   ins_pipe(iload_reg_mem);
6370 %}
6371 
6372 // Load Byte (8 bit unsigned)
6373 instruct loadUB(iRegINoSp dst, memory mem)
6374 %{
6375   match(Set dst (LoadUB mem));
6376   predicate(!needs_acquiring_load(n));
6377 
6378   ins_cost(4 * INSN_COST);
6379   format %{ "ldrbw  $dst, $mem\t# byte" %}
6380 
6381   ins_encode(aarch64_enc_ldrb(dst, mem));
6382 
6383   ins_pipe(iload_reg_mem);
6384 %}
6385 
6386 // Load Byte (8 bit unsigned) into long
6387 instruct loadUB2L(iRegLNoSp dst, memory mem)
6388 %{
6389   match(Set dst (ConvI2L (LoadUB mem)));
6390   predicate(!needs_acquiring_load(n->in(1)));
6391 
6392   ins_cost(4 * INSN_COST);
6393   format %{ "ldrb  $dst, $mem\t# byte" %}
6394 
6395   ins_encode(aarch64_enc_ldrb(dst, mem));
6396 
6397   ins_pipe(iload_reg_mem);
6398 %}
6399 
6400 // Load Short (16 bit signed)
6401 instruct loadS(iRegINoSp dst, memory mem)
6402 %{
6403   match(Set dst (LoadS mem));
6404   predicate(!needs_acquiring_load(n));
6405 
6406   ins_cost(4 * INSN_COST);
6407   format %{ "ldrshw  $dst, $mem\t# short" %}
6408 
6409   ins_encode(aarch64_enc_ldrshw(dst, mem));
6410 
6411   ins_pipe(iload_reg_mem);
6412 %}
6413 
6414 // Load Short (16 bit signed) into long
6415 instruct loadS2L(iRegLNoSp dst, memory mem)
6416 %{
6417   match(Set dst (ConvI2L (LoadS mem)));
6418   predicate(!needs_acquiring_load(n->in(1)));
6419 
6420   ins_cost(4 * INSN_COST);
6421   format %{ "ldrsh  $dst, $mem\t# short" %}
6422 
6423   ins_encode(aarch64_enc_ldrsh(dst, mem));
6424 
6425   ins_pipe(iload_reg_mem);
6426 %}
6427 
6428 // Load Char (16 bit unsigned)
6429 instruct loadUS(iRegINoSp dst, memory mem)
6430 %{
6431   match(Set dst (LoadUS mem));
6432   predicate(!needs_acquiring_load(n));
6433 
6434   ins_cost(4 * INSN_COST);
6435   format %{ "ldrh  $dst, $mem\t# short" %}
6436 
6437   ins_encode(aarch64_enc_ldrh(dst, mem));
6438 
6439   ins_pipe(iload_reg_mem);
6440 %}
6441 
6442 // Load Short/Char (16 bit unsigned) into long
6443 instruct loadUS2L(iRegLNoSp dst, memory mem)
6444 %{
6445   match(Set dst (ConvI2L (LoadUS mem)));
6446   predicate(!needs_acquiring_load(n->in(1)));
6447 
6448   ins_cost(4 * INSN_COST);
6449   format %{ "ldrh  $dst, $mem\t# short" %}
6450 
6451   ins_encode(aarch64_enc_ldrh(dst, mem));
6452 
6453   ins_pipe(iload_reg_mem);
6454 %}
6455 
6456 // Load Integer (32 bit signed)
6457 instruct loadI(iRegINoSp dst, memory mem)
6458 %{
6459   match(Set dst (LoadI mem));
6460   predicate(!needs_acquiring_load(n));
6461 
6462   ins_cost(4 * INSN_COST);
6463   format %{ "ldrw  $dst, $mem\t# int" %}
6464 
6465   ins_encode(aarch64_enc_ldrw(dst, mem));
6466 
6467   ins_pipe(iload_reg_mem);
6468 %}
6469 
6470 // Load Integer (32 bit signed) into long
6471 instruct loadI2L(iRegLNoSp dst, memory mem)
6472 %{
6473   match(Set dst (ConvI2L (LoadI mem)));
6474   predicate(!needs_acquiring_load(n->in(1)));
6475 
6476   ins_cost(4 * INSN_COST);
6477   format %{ "ldrsw  $dst, $mem\t# int" %}
6478 
6479   ins_encode(aarch64_enc_ldrsw(dst, mem));
6480 
6481   ins_pipe(iload_reg_mem);
6482 %}
6483 
6484 // Load Integer (32 bit unsigned) into long
6485 instruct loadUI2L(iRegLNoSp dst, memory mem, immL_32bits mask)
6486 %{
6487   match(Set dst (AndL (ConvI2L (LoadI mem)) mask));
6488   predicate(!needs_acquiring_load(n->in(1)->in(1)->as_Load()));
6489 
6490   ins_cost(4 * INSN_COST);
6491   format %{ "ldrw  $dst, $mem\t# int" %}
6492 
6493   ins_encode(aarch64_enc_ldrw(dst, mem));
6494 
6495   ins_pipe(iload_reg_mem);
6496 %}
6497 
6498 // Load Long (64 bit signed)
6499 instruct loadL(iRegLNoSp dst, memory mem)
6500 %{
6501   match(Set dst (LoadL mem));
6502   predicate(!needs_acquiring_load(n));
6503 
6504   ins_cost(4 * INSN_COST);
6505   format %{ "ldr  $dst, $mem\t# int" %}
6506 
6507   ins_encode(aarch64_enc_ldr(dst, mem));
6508 
6509   ins_pipe(iload_reg_mem);
6510 %}
6511 
6512 // Load Range
6513 instruct loadRange(iRegINoSp dst, memory mem)
6514 %{
6515   match(Set dst (LoadRange mem));
6516 
6517   ins_cost(4 * INSN_COST);
6518   format %{ "ldrw  $dst, $mem\t# range" %}
6519 
6520   ins_encode(aarch64_enc_ldrw(dst, mem));
6521 
6522   ins_pipe(iload_reg_mem);
6523 %}
6524 
6525 // Load Pointer
6526 instruct loadP(iRegPNoSp dst, memory mem)
6527 %{
6528   match(Set dst (LoadP mem));
6529   predicate(!needs_acquiring_load(n));
6530 
6531   ins_cost(4 * INSN_COST);
6532   format %{ "ldr  $dst, $mem\t# ptr" %}
6533 
6534   ins_encode(aarch64_enc_ldr(dst, mem));
6535 
6536   ins_pipe(iload_reg_mem);
6537 %}
6538 
6539 // Load Compressed Pointer
6540 instruct loadN(iRegNNoSp dst, memory mem)
6541 %{
6542   match(Set dst (LoadN mem));
6543   predicate(!needs_acquiring_load(n));
6544 
6545   ins_cost(4 * INSN_COST);
6546   format %{ "ldrw  $dst, $mem\t# compressed ptr" %}
6547 
6548   ins_encode(aarch64_enc_ldrw(dst, mem));
6549 
6550   ins_pipe(iload_reg_mem);
6551 %}
6552 
6553 // Load Klass Pointer
6554 instruct loadKlass(iRegPNoSp dst, memory mem)
6555 %{
6556   match(Set dst (LoadKlass mem));
6557   predicate(!needs_acquiring_load(n));
6558 
6559   ins_cost(4 * INSN_COST);
6560   format %{ "ldr  $dst, $mem\t# class" %}
6561 
6562   ins_encode(aarch64_enc_ldr(dst, mem));
6563 
6564   ins_pipe(iload_reg_mem);
6565 %}
6566 
6567 // Load Narrow Klass Pointer
6568 instruct loadNKlass(iRegNNoSp dst, memory mem)
6569 %{
6570   match(Set dst (LoadNKlass mem));
6571   predicate(!needs_acquiring_load(n));
6572 
6573   ins_cost(4 * INSN_COST);
6574   format %{ "ldrw  $dst, $mem\t# compressed class ptr" %}
6575 
6576   ins_encode(aarch64_enc_ldrw(dst, mem));
6577 
6578   ins_pipe(iload_reg_mem);
6579 %}
6580 
6581 // Load Float
6582 instruct loadF(vRegF dst, memory mem)
6583 %{
6584   match(Set dst (LoadF mem));
6585   predicate(!needs_acquiring_load(n));
6586 
6587   ins_cost(4 * INSN_COST);
6588   format %{ "ldrs  $dst, $mem\t# float" %}
6589 
6590   ins_encode( aarch64_enc_ldrs(dst, mem) );
6591 
6592   ins_pipe(pipe_class_memory);
6593 %}
6594 
6595 // Load Double
6596 instruct loadD(vRegD dst, memory mem)
6597 %{
6598   match(Set dst (LoadD mem));
6599   predicate(!needs_acquiring_load(n));
6600 
6601   ins_cost(4 * INSN_COST);
6602   format %{ "ldrd  $dst, $mem\t# double" %}
6603 
6604   ins_encode( aarch64_enc_ldrd(dst, mem) );
6605 
6606   ins_pipe(pipe_class_memory);
6607 %}
6608 
6609 
6610 // Load Int Constant
6611 instruct loadConI(iRegINoSp dst, immI src)
6612 %{
6613   match(Set dst src);
6614 
6615   ins_cost(INSN_COST);
6616   format %{ "mov $dst, $src\t# int" %}
6617 
6618   ins_encode( aarch64_enc_movw_imm(dst, src) );
6619 
6620   ins_pipe(ialu_imm);
6621 %}
6622 
6623 // Load Long Constant
6624 instruct loadConL(iRegLNoSp dst, immL src)
6625 %{
6626   match(Set dst src);
6627 
6628   ins_cost(INSN_COST);
6629   format %{ "mov $dst, $src\t# long" %}
6630 
6631   ins_encode( aarch64_enc_mov_imm(dst, src) );
6632 
6633   ins_pipe(ialu_imm);
6634 %}
6635 
6636 // Load Pointer Constant
6637 
6638 instruct loadConP(iRegPNoSp dst, immP con)
6639 %{
6640   match(Set dst con);
6641 
6642   ins_cost(INSN_COST * 4);
6643   format %{
6644     "mov  $dst, $con\t# ptr\n\t"
6645   %}
6646 
6647   ins_encode(aarch64_enc_mov_p(dst, con));
6648 
6649   ins_pipe(ialu_imm);
6650 %}
6651 
6652 // Load Null Pointer Constant
6653 
6654 instruct loadConP0(iRegPNoSp dst, immP0 con)
6655 %{
6656   match(Set dst con);
6657 
6658   ins_cost(INSN_COST);
6659   format %{ "mov  $dst, $con\t# NULL ptr" %}
6660 
6661   ins_encode(aarch64_enc_mov_p0(dst, con));
6662 
6663   ins_pipe(ialu_imm);
6664 %}
6665 
6666 // Load Pointer Constant One
6667 
6668 instruct loadConP1(iRegPNoSp dst, immP_1 con)
6669 %{
6670   match(Set dst con);
6671 
6672   ins_cost(INSN_COST);
6673   format %{ "mov  $dst, $con\t# NULL ptr" %}
6674 
6675   ins_encode(aarch64_enc_mov_p1(dst, con));
6676 
6677   ins_pipe(ialu_imm);
6678 %}
6679 
6680 // Load Poll Page Constant
6681 
6682 instruct loadConPollPage(iRegPNoSp dst, immPollPage con)
6683 %{
6684   match(Set dst con);
6685 
6686   ins_cost(INSN_COST);
6687   format %{ "adr  $dst, $con\t# Poll Page Ptr" %}
6688 
6689   ins_encode(aarch64_enc_mov_poll_page(dst, con));
6690 
6691   ins_pipe(ialu_imm);
6692 %}
6693 
6694 // Load Byte Map Base Constant
6695 
6696 instruct loadByteMapBase(iRegPNoSp dst, immByteMapBase con)
6697 %{
6698   match(Set dst con);
6699 
6700   ins_cost(INSN_COST);
6701   format %{ "adr  $dst, $con\t# Byte Map Base" %}
6702 
6703   ins_encode(aarch64_enc_mov_byte_map_base(dst, con));
6704 
6705   ins_pipe(ialu_imm);
6706 %}
6707 
6708 // Load Narrow Pointer Constant
6709 
6710 instruct loadConN(iRegNNoSp dst, immN con)
6711 %{
6712   match(Set dst con);
6713 
6714   ins_cost(INSN_COST * 4);
6715   format %{ "mov  $dst, $con\t# compressed ptr" %}
6716 
6717   ins_encode(aarch64_enc_mov_n(dst, con));
6718 
6719   ins_pipe(ialu_imm);
6720 %}
6721 
6722 // Load Narrow Null Pointer Constant
6723 
6724 instruct loadConN0(iRegNNoSp dst, immN0 con)
6725 %{
6726   match(Set dst con);
6727 
6728   ins_cost(INSN_COST);
6729   format %{ "mov  $dst, $con\t# compressed NULL ptr" %}
6730 
6731   ins_encode(aarch64_enc_mov_n0(dst, con));
6732 
6733   ins_pipe(ialu_imm);
6734 %}
6735 
6736 // Load Narrow Klass Constant
6737 
6738 instruct loadConNKlass(iRegNNoSp dst, immNKlass con)
6739 %{
6740   match(Set dst con);
6741 
6742   ins_cost(INSN_COST);
6743   format %{ "mov  $dst, $con\t# compressed klass ptr" %}
6744 
6745   ins_encode(aarch64_enc_mov_nk(dst, con));
6746 
6747   ins_pipe(ialu_imm);
6748 %}
6749 
6750 // Load Packed Float Constant
6751 
6752 instruct loadConF_packed(vRegF dst, immFPacked con) %{
6753   match(Set dst con);
6754   ins_cost(INSN_COST * 4);
6755   format %{ "fmovs  $dst, $con"%}
6756   ins_encode %{
6757     __ fmovs(as_FloatRegister($dst$$reg), (double)$con$$constant);
6758   %}
6759 
6760   ins_pipe(fp_imm_s);
6761 %}
6762 
6763 // Load Float Constant
6764 
6765 instruct loadConF(vRegF dst, immF con) %{
6766   match(Set dst con);
6767 
6768   ins_cost(INSN_COST * 4);
6769 
6770   format %{
6771     "ldrs $dst, [$constantaddress]\t# load from constant table: float=$con\n\t"
6772   %}
6773 
6774   ins_encode %{
6775     __ ldrs(as_FloatRegister($dst$$reg), $constantaddress($con));
6776   %}
6777 
6778   ins_pipe(fp_load_constant_s);
6779 %}
6780 
6781 // Load Packed Double Constant
6782 
6783 instruct loadConD_packed(vRegD dst, immDPacked con) %{
6784   match(Set dst con);
6785   ins_cost(INSN_COST);
6786   format %{ "fmovd  $dst, $con"%}
6787   ins_encode %{
6788     __ fmovd(as_FloatRegister($dst$$reg), $con$$constant);
6789   %}
6790 
6791   ins_pipe(fp_imm_d);
6792 %}
6793 
6794 // Load Double Constant
6795 
6796 instruct loadConD(vRegD dst, immD con) %{
6797   match(Set dst con);
6798 
6799   ins_cost(INSN_COST * 5);
6800   format %{
6801     "ldrd $dst, [$constantaddress]\t# load from constant table: float=$con\n\t"
6802   %}
6803 
6804   ins_encode %{
6805     __ ldrd(as_FloatRegister($dst$$reg), $constantaddress($con));
6806   %}
6807 
6808   ins_pipe(fp_load_constant_d);
6809 %}
6810 
6811 // Store Instructions
6812 
6813 // Store CMS card-mark Immediate
6814 instruct storeimmCM0(immI0 zero, memory mem)
6815 %{
6816   match(Set mem (StoreCM mem zero));
6817   predicate(unnecessary_storestore(n));
6818 
6819   ins_cost(INSN_COST);
6820   format %{ "storestore (elided)\n\t"
6821             "strb zr, $mem\t# byte" %}
6822 
6823   ins_encode(aarch64_enc_strb0(mem));
6824 
6825   ins_pipe(istore_mem);
6826 %}
6827 
6828 // Store CMS card-mark Immediate with intervening StoreStore
6829 // needed when using CMS with no conditional card marking
6830 instruct storeimmCM0_ordered(immI0 zero, memory mem)
6831 %{
6832   match(Set mem (StoreCM mem zero));
6833 
6834   ins_cost(INSN_COST * 2);
6835   format %{ "storestore\n\t"
6836             "dmb ishst"
6837             "\n\tstrb zr, $mem\t# byte" %}
6838 
6839   ins_encode(aarch64_enc_strb0_ordered(mem));
6840 
6841   ins_pipe(istore_mem);
6842 %}
6843 
6844 // Store Byte
6845 instruct storeB(iRegIorL2I src, memory mem)
6846 %{
6847   match(Set mem (StoreB mem src));
6848   predicate(!needs_releasing_store(n));
6849 
6850   ins_cost(INSN_COST);
6851   format %{ "strb  $src, $mem\t# byte" %}
6852 
6853   ins_encode(aarch64_enc_strb(src, mem));
6854 
6855   ins_pipe(istore_reg_mem);
6856 %}
6857 
6858 
6859 instruct storeimmB0(immI0 zero, memory mem)
6860 %{
6861   match(Set mem (StoreB mem zero));
6862   predicate(!needs_releasing_store(n));
6863 
6864   ins_cost(INSN_COST);
6865   format %{ "strb rscractch2, $mem\t# byte" %}
6866 
6867   ins_encode(aarch64_enc_strb0(mem));
6868 
6869   ins_pipe(istore_mem);
6870 %}
6871 
6872 // Store Char/Short
6873 instruct storeC(iRegIorL2I src, memory mem)
6874 %{
6875   match(Set mem (StoreC mem src));
6876   predicate(!needs_releasing_store(n));
6877 
6878   ins_cost(INSN_COST);
6879   format %{ "strh  $src, $mem\t# short" %}
6880 
6881   ins_encode(aarch64_enc_strh(src, mem));
6882 
6883   ins_pipe(istore_reg_mem);
6884 %}
6885 
6886 instruct storeimmC0(immI0 zero, memory mem)
6887 %{
6888   match(Set mem (StoreC mem zero));
6889   predicate(!needs_releasing_store(n));
6890 
6891   ins_cost(INSN_COST);
6892   format %{ "strh  zr, $mem\t# short" %}
6893 
6894   ins_encode(aarch64_enc_strh0(mem));
6895 
6896   ins_pipe(istore_mem);
6897 %}
6898 
6899 // Store Integer
6900 
6901 instruct storeI(iRegIorL2I src, memory mem)
6902 %{
6903   match(Set mem(StoreI mem src));
6904   predicate(!needs_releasing_store(n));
6905 
6906   ins_cost(INSN_COST);
6907   format %{ "strw  $src, $mem\t# int" %}
6908 
6909   ins_encode(aarch64_enc_strw(src, mem));
6910 
6911   ins_pipe(istore_reg_mem);
6912 %}
6913 
6914 instruct storeimmI0(immI0 zero, memory mem)
6915 %{
6916   match(Set mem(StoreI mem zero));
6917   predicate(!needs_releasing_store(n));
6918 
6919   ins_cost(INSN_COST);
6920   format %{ "strw  zr, $mem\t# int" %}
6921 
6922   ins_encode(aarch64_enc_strw0(mem));
6923 
6924   ins_pipe(istore_mem);
6925 %}
6926 
6927 // Store Long (64 bit signed)
6928 instruct storeL(iRegL src, memory mem)
6929 %{
6930   match(Set mem (StoreL mem src));
6931   predicate(!needs_releasing_store(n));
6932 
6933   ins_cost(INSN_COST);
6934   format %{ "str  $src, $mem\t# int" %}
6935 
6936   ins_encode(aarch64_enc_str(src, mem));
6937 
6938   ins_pipe(istore_reg_mem);
6939 %}
6940 
6941 // Store Long (64 bit signed)
6942 instruct storeimmL0(immL0 zero, memory mem)
6943 %{
6944   match(Set mem (StoreL mem zero));
6945   predicate(!needs_releasing_store(n));
6946 
6947   ins_cost(INSN_COST);
6948   format %{ "str  zr, $mem\t# int" %}
6949 
6950   ins_encode(aarch64_enc_str0(mem));
6951 
6952   ins_pipe(istore_mem);
6953 %}
6954 
6955 // Store Pointer
6956 instruct storeP(iRegP src, memory mem)
6957 %{
6958   match(Set mem (StoreP mem src));
6959   predicate(!needs_releasing_store(n));
6960 
6961   ins_cost(INSN_COST);
6962   format %{ "str  $src, $mem\t# ptr" %}
6963 
6964   ins_encode(aarch64_enc_str(src, mem));
6965 
6966   ins_pipe(istore_reg_mem);
6967 %}
6968 
6969 // Store Pointer
6970 instruct storeimmP0(immP0 zero, memory mem)
6971 %{
6972   match(Set mem (StoreP mem zero));
6973   predicate(!needs_releasing_store(n));
6974 
6975   ins_cost(INSN_COST);
6976   format %{ "str zr, $mem\t# ptr" %}
6977 
6978   ins_encode(aarch64_enc_str0(mem));
6979 
6980   ins_pipe(istore_mem);
6981 %}
6982 
6983 // Store Compressed Pointer
6984 instruct storeN(iRegN src, memory mem)
6985 %{
6986   match(Set mem (StoreN mem src));
6987   predicate(!needs_releasing_store(n));
6988 
6989   ins_cost(INSN_COST);
6990   format %{ "strw  $src, $mem\t# compressed ptr" %}
6991 
6992   ins_encode(aarch64_enc_strw(src, mem));
6993 
6994   ins_pipe(istore_reg_mem);
6995 %}
6996 
6997 instruct storeImmN0(iRegIHeapbase heapbase, immN0 zero, memory mem)
6998 %{
6999   match(Set mem (StoreN mem zero));
7000   predicate(Universe::narrow_oop_base() == NULL &&
7001             Universe::narrow_klass_base() == NULL &&
7002             (!needs_releasing_store(n)));
7003 
7004   ins_cost(INSN_COST);
7005   format %{ "strw  rheapbase, $mem\t# compressed ptr (rheapbase==0)" %}
7006 
7007   ins_encode(aarch64_enc_strw(heapbase, mem));
7008 
7009   ins_pipe(istore_reg_mem);
7010 %}
7011 
7012 // Store Float
7013 instruct storeF(vRegF src, memory mem)
7014 %{
7015   match(Set mem (StoreF mem src));
7016   predicate(!needs_releasing_store(n));
7017 
7018   ins_cost(INSN_COST);
7019   format %{ "strs  $src, $mem\t# float" %}
7020 
7021   ins_encode( aarch64_enc_strs(src, mem) );
7022 
7023   ins_pipe(pipe_class_memory);
7024 %}
7025 
7026 // TODO
7027 // implement storeImmF0 and storeFImmPacked
7028 
7029 // Store Double
7030 instruct storeD(vRegD src, memory mem)
7031 %{
7032   match(Set mem (StoreD mem src));
7033   predicate(!needs_releasing_store(n));
7034 
7035   ins_cost(INSN_COST);
7036   format %{ "strd  $src, $mem\t# double" %}
7037 
7038   ins_encode( aarch64_enc_strd(src, mem) );
7039 
7040   ins_pipe(pipe_class_memory);
7041 %}
7042 
7043 // Store Compressed Klass Pointer
7044 instruct storeNKlass(iRegN src, memory mem)
7045 %{
7046   predicate(!needs_releasing_store(n));
7047   match(Set mem (StoreNKlass mem src));
7048 
7049   ins_cost(INSN_COST);
7050   format %{ "strw  $src, $mem\t# compressed klass ptr" %}
7051 
7052   ins_encode(aarch64_enc_strw(src, mem));
7053 
7054   ins_pipe(istore_reg_mem);
7055 %}
7056 
7057 // TODO
7058 // implement storeImmD0 and storeDImmPacked
7059 
7060 // prefetch instructions
7061 // Must be safe to execute with invalid address (cannot fault).
7062 
7063 instruct prefetchalloc( memory mem ) %{
7064   match(PrefetchAllocation mem);
7065 
7066   ins_cost(INSN_COST);
7067   format %{ "prfm $mem, PSTL1KEEP\t# Prefetch into level 1 cache write keep" %}
7068 
7069   ins_encode( aarch64_enc_prefetchw(mem) );
7070 
7071   ins_pipe(iload_prefetch);
7072 %}
7073 
7074 //  ---------------- volatile loads and stores ----------------
7075 
7076 // Load Byte (8 bit signed)
7077 instruct loadB_volatile(iRegINoSp dst, /* sync_memory*/indirect mem)
7078 %{
7079   match(Set dst (LoadB mem));
7080 
7081   ins_cost(VOLATILE_REF_COST);
7082   format %{ "ldarsb  $dst, $mem\t# byte" %}
7083 
7084   ins_encode(aarch64_enc_ldarsb(dst, mem));
7085 
7086   ins_pipe(pipe_serial);
7087 %}
7088 
7089 // Load Byte (8 bit signed) into long
7090 instruct loadB2L_volatile(iRegLNoSp dst, /* sync_memory*/indirect mem)
7091 %{
7092   match(Set dst (ConvI2L (LoadB mem)));
7093 
7094   ins_cost(VOLATILE_REF_COST);
7095   format %{ "ldarsb  $dst, $mem\t# byte" %}
7096 
7097   ins_encode(aarch64_enc_ldarsb(dst, mem));
7098 
7099   ins_pipe(pipe_serial);
7100 %}
7101 
7102 // Load Byte (8 bit unsigned)
7103 instruct loadUB_volatile(iRegINoSp dst, /* sync_memory*/indirect mem)
7104 %{
7105   match(Set dst (LoadUB mem));
7106 
7107   ins_cost(VOLATILE_REF_COST);
7108   format %{ "ldarb  $dst, $mem\t# byte" %}
7109 
7110   ins_encode(aarch64_enc_ldarb(dst, mem));
7111 
7112   ins_pipe(pipe_serial);
7113 %}
7114 
7115 // Load Byte (8 bit unsigned) into long
7116 instruct loadUB2L_volatile(iRegLNoSp dst, /* sync_memory*/indirect mem)
7117 %{
7118   match(Set dst (ConvI2L (LoadUB mem)));
7119 
7120   ins_cost(VOLATILE_REF_COST);
7121   format %{ "ldarb  $dst, $mem\t# byte" %}
7122 
7123   ins_encode(aarch64_enc_ldarb(dst, mem));
7124 
7125   ins_pipe(pipe_serial);
7126 %}
7127 
7128 // Load Short (16 bit signed)
7129 instruct loadS_volatile(iRegINoSp dst, /* sync_memory*/indirect mem)
7130 %{
7131   match(Set dst (LoadS mem));
7132 
7133   ins_cost(VOLATILE_REF_COST);
7134   format %{ "ldarshw  $dst, $mem\t# short" %}
7135 
7136   ins_encode(aarch64_enc_ldarshw(dst, mem));
7137 
7138   ins_pipe(pipe_serial);
7139 %}
7140 
7141 instruct loadUS_volatile(iRegINoSp dst, /* sync_memory*/indirect mem)
7142 %{
7143   match(Set dst (LoadUS mem));
7144 
7145   ins_cost(VOLATILE_REF_COST);
7146   format %{ "ldarhw  $dst, $mem\t# short" %}
7147 
7148   ins_encode(aarch64_enc_ldarhw(dst, mem));
7149 
7150   ins_pipe(pipe_serial);
7151 %}
7152 
7153 // Load Short/Char (16 bit unsigned) into long
7154 instruct loadUS2L_volatile(iRegLNoSp dst, /* sync_memory*/indirect mem)
7155 %{
7156   match(Set dst (ConvI2L (LoadUS mem)));
7157 
7158   ins_cost(VOLATILE_REF_COST);
7159   format %{ "ldarh  $dst, $mem\t# short" %}
7160 
7161   ins_encode(aarch64_enc_ldarh(dst, mem));
7162 
7163   ins_pipe(pipe_serial);
7164 %}
7165 
7166 // Load Short/Char (16 bit signed) into long
7167 instruct loadS2L_volatile(iRegLNoSp dst, /* sync_memory*/indirect mem)
7168 %{
7169   match(Set dst (ConvI2L (LoadS mem)));
7170 
7171   ins_cost(VOLATILE_REF_COST);
7172   format %{ "ldarh  $dst, $mem\t# short" %}
7173 
7174   ins_encode(aarch64_enc_ldarsh(dst, mem));
7175 
7176   ins_pipe(pipe_serial);
7177 %}
7178 
7179 // Load Integer (32 bit signed)
7180 instruct loadI_volatile(iRegINoSp dst, /* sync_memory*/indirect mem)
7181 %{
7182   match(Set dst (LoadI mem));
7183 
7184   ins_cost(VOLATILE_REF_COST);
7185   format %{ "ldarw  $dst, $mem\t# int" %}
7186 
7187   ins_encode(aarch64_enc_ldarw(dst, mem));
7188 
7189   ins_pipe(pipe_serial);
7190 %}
7191 
7192 // Load Integer (32 bit unsigned) into long
7193 instruct loadUI2L_volatile(iRegLNoSp dst, /* sync_memory*/indirect mem, immL_32bits mask)
7194 %{
7195   match(Set dst (AndL (ConvI2L (LoadI mem)) mask));
7196 
7197   ins_cost(VOLATILE_REF_COST);
7198   format %{ "ldarw  $dst, $mem\t# int" %}
7199 
7200   ins_encode(aarch64_enc_ldarw(dst, mem));
7201 
7202   ins_pipe(pipe_serial);
7203 %}
7204 
7205 // Load Long (64 bit signed)
7206 instruct loadL_volatile(iRegLNoSp dst, /* sync_memory*/indirect mem)
7207 %{
7208   match(Set dst (LoadL mem));
7209 
7210   ins_cost(VOLATILE_REF_COST);
7211   format %{ "ldar  $dst, $mem\t# int" %}
7212 
7213   ins_encode(aarch64_enc_ldar(dst, mem));
7214 
7215   ins_pipe(pipe_serial);
7216 %}
7217 
7218 // Load Pointer
7219 instruct loadP_volatile(iRegPNoSp dst, /* sync_memory*/indirect mem)
7220 %{
7221   match(Set dst (LoadP mem));
7222 
7223   ins_cost(VOLATILE_REF_COST);
7224   format %{ "ldar  $dst, $mem\t# ptr" %}
7225 
7226   ins_encode(aarch64_enc_ldar(dst, mem));
7227 
7228   ins_pipe(pipe_serial);
7229 %}
7230 
7231 // Load Compressed Pointer
7232 instruct loadN_volatile(iRegNNoSp dst, /* sync_memory*/indirect mem)
7233 %{
7234   match(Set dst (LoadN mem));
7235 
7236   ins_cost(VOLATILE_REF_COST);
7237   format %{ "ldarw  $dst, $mem\t# compressed ptr" %}
7238 
7239   ins_encode(aarch64_enc_ldarw(dst, mem));
7240 
7241   ins_pipe(pipe_serial);
7242 %}
7243 
7244 // Load Float
7245 instruct loadF_volatile(vRegF dst, /* sync_memory*/indirect mem)
7246 %{
7247   match(Set dst (LoadF mem));
7248 
7249   ins_cost(VOLATILE_REF_COST);
7250   format %{ "ldars  $dst, $mem\t# float" %}
7251 
7252   ins_encode( aarch64_enc_fldars(dst, mem) );
7253 
7254   ins_pipe(pipe_serial);
7255 %}
7256 
7257 // Load Double
7258 instruct loadD_volatile(vRegD dst, /* sync_memory*/indirect mem)
7259 %{
7260   match(Set dst (LoadD mem));
7261 
7262   ins_cost(VOLATILE_REF_COST);
7263   format %{ "ldard  $dst, $mem\t# double" %}
7264 
7265   ins_encode( aarch64_enc_fldard(dst, mem) );
7266 
7267   ins_pipe(pipe_serial);
7268 %}
7269 
7270 // Store Byte
7271 instruct storeB_volatile(iRegIorL2I src, /* sync_memory*/indirect mem)
7272 %{
7273   match(Set mem (StoreB mem src));
7274 
7275   ins_cost(VOLATILE_REF_COST);
7276   format %{ "stlrb  $src, $mem\t# byte" %}
7277 
7278   ins_encode(aarch64_enc_stlrb(src, mem));
7279 
7280   ins_pipe(pipe_class_memory);
7281 %}
7282 
7283 // Store Char/Short
7284 instruct storeC_volatile(iRegIorL2I src, /* sync_memory*/indirect mem)
7285 %{
7286   match(Set mem (StoreC mem src));
7287 
7288   ins_cost(VOLATILE_REF_COST);
7289   format %{ "stlrh  $src, $mem\t# short" %}
7290 
7291   ins_encode(aarch64_enc_stlrh(src, mem));
7292 
7293   ins_pipe(pipe_class_memory);
7294 %}
7295 
7296 // Store Integer
7297 
7298 instruct storeI_volatile(iRegIorL2I src, /* sync_memory*/indirect mem)
7299 %{
7300   match(Set mem(StoreI mem src));
7301 
7302   ins_cost(VOLATILE_REF_COST);
7303   format %{ "stlrw  $src, $mem\t# int" %}
7304 
7305   ins_encode(aarch64_enc_stlrw(src, mem));
7306 
7307   ins_pipe(pipe_class_memory);
7308 %}
7309 
7310 // Store Long (64 bit signed)
7311 instruct storeL_volatile(iRegL src, /* sync_memory*/indirect mem)
7312 %{
7313   match(Set mem (StoreL mem src));
7314 
7315   ins_cost(VOLATILE_REF_COST);
7316   format %{ "stlr  $src, $mem\t# int" %}
7317 
7318   ins_encode(aarch64_enc_stlr(src, mem));
7319 
7320   ins_pipe(pipe_class_memory);
7321 %}
7322 
7323 // Store Pointer
7324 instruct storeP_volatile(iRegP src, /* sync_memory*/indirect mem)
7325 %{
7326   match(Set mem (StoreP mem src));
7327 
7328   ins_cost(VOLATILE_REF_COST);
7329   format %{ "stlr  $src, $mem\t# ptr" %}
7330 
7331   ins_encode(aarch64_enc_stlr(src, mem));
7332 
7333   ins_pipe(pipe_class_memory);
7334 %}
7335 
7336 // Store Compressed Pointer
7337 instruct storeN_volatile(iRegN src, /* sync_memory*/indirect mem)
7338 %{
7339   match(Set mem (StoreN mem src));
7340 
7341   ins_cost(VOLATILE_REF_COST);
7342   format %{ "stlrw  $src, $mem\t# compressed ptr" %}
7343 
7344   ins_encode(aarch64_enc_stlrw(src, mem));
7345 
7346   ins_pipe(pipe_class_memory);
7347 %}
7348 
7349 // Store Float
7350 instruct storeF_volatile(vRegF src, /* sync_memory*/indirect mem)
7351 %{
7352   match(Set mem (StoreF mem src));
7353 
7354   ins_cost(VOLATILE_REF_COST);
7355   format %{ "stlrs  $src, $mem\t# float" %}
7356 
7357   ins_encode( aarch64_enc_fstlrs(src, mem) );
7358 
7359   ins_pipe(pipe_class_memory);
7360 %}
7361 
7362 // TODO
7363 // implement storeImmF0 and storeFImmPacked
7364 
7365 // Store Double
7366 instruct storeD_volatile(vRegD src, /* sync_memory*/indirect mem)
7367 %{
7368   match(Set mem (StoreD mem src));
7369 
7370   ins_cost(VOLATILE_REF_COST);
7371   format %{ "stlrd  $src, $mem\t# double" %}
7372 
7373   ins_encode( aarch64_enc_fstlrd(src, mem) );
7374 
7375   ins_pipe(pipe_class_memory);
7376 %}
7377 
7378 //  ---------------- end of volatile loads and stores ----------------
7379 
7380 // ============================================================================
7381 // BSWAP Instructions
7382 
7383 instruct bytes_reverse_int(iRegINoSp dst, iRegIorL2I src) %{
7384   match(Set dst (ReverseBytesI src));
7385 
7386   ins_cost(INSN_COST);
7387   format %{ "revw  $dst, $src" %}
7388 
7389   ins_encode %{
7390     __ revw(as_Register($dst$$reg), as_Register($src$$reg));
7391   %}
7392 
7393   ins_pipe(ialu_reg);
7394 %}
7395 
7396 instruct bytes_reverse_long(iRegLNoSp dst, iRegL src) %{
7397   match(Set dst (ReverseBytesL src));
7398 
7399   ins_cost(INSN_COST);
7400   format %{ "rev  $dst, $src" %}
7401 
7402   ins_encode %{
7403     __ rev(as_Register($dst$$reg), as_Register($src$$reg));
7404   %}
7405 
7406   ins_pipe(ialu_reg);
7407 %}
7408 
7409 instruct bytes_reverse_unsigned_short(iRegINoSp dst, iRegIorL2I src) %{
7410   match(Set dst (ReverseBytesUS src));
7411 
7412   ins_cost(INSN_COST);
7413   format %{ "rev16w  $dst, $src" %}
7414 
7415   ins_encode %{
7416     __ rev16w(as_Register($dst$$reg), as_Register($src$$reg));
7417   %}
7418 
7419   ins_pipe(ialu_reg);
7420 %}
7421 
7422 instruct bytes_reverse_short(iRegINoSp dst, iRegIorL2I src) %{
7423   match(Set dst (ReverseBytesS src));
7424 
7425   ins_cost(INSN_COST);
7426   format %{ "rev16w  $dst, $src\n\t"
7427             "sbfmw $dst, $dst, #0, #15" %}
7428 
7429   ins_encode %{
7430     __ rev16w(as_Register($dst$$reg), as_Register($src$$reg));
7431     __ sbfmw(as_Register($dst$$reg), as_Register($dst$$reg), 0U, 15U);
7432   %}
7433 
7434   ins_pipe(ialu_reg);
7435 %}
7436 
7437 // ============================================================================
7438 // Zero Count Instructions
7439 
7440 instruct countLeadingZerosI(iRegINoSp dst, iRegIorL2I src) %{
7441   match(Set dst (CountLeadingZerosI src));
7442 
7443   ins_cost(INSN_COST);
7444   format %{ "clzw  $dst, $src" %}
7445   ins_encode %{
7446     __ clzw(as_Register($dst$$reg), as_Register($src$$reg));
7447   %}
7448 
7449   ins_pipe(ialu_reg);
7450 %}
7451 
7452 instruct countLeadingZerosL(iRegINoSp dst, iRegL src) %{
7453   match(Set dst (CountLeadingZerosL src));
7454 
7455   ins_cost(INSN_COST);
7456   format %{ "clz   $dst, $src" %}
7457   ins_encode %{
7458     __ clz(as_Register($dst$$reg), as_Register($src$$reg));
7459   %}
7460 
7461   ins_pipe(ialu_reg);
7462 %}
7463 
7464 instruct countTrailingZerosI(iRegINoSp dst, iRegIorL2I src) %{
7465   match(Set dst (CountTrailingZerosI src));
7466 
7467   ins_cost(INSN_COST * 2);
7468   format %{ "rbitw  $dst, $src\n\t"
7469             "clzw   $dst, $dst" %}
7470   ins_encode %{
7471     __ rbitw(as_Register($dst$$reg), as_Register($src$$reg));
7472     __ clzw(as_Register($dst$$reg), as_Register($dst$$reg));
7473   %}
7474 
7475   ins_pipe(ialu_reg);
7476 %}
7477 
7478 instruct countTrailingZerosL(iRegINoSp dst, iRegL src) %{
7479   match(Set dst (CountTrailingZerosL src));
7480 
7481   ins_cost(INSN_COST * 2);
7482   format %{ "rbit   $dst, $src\n\t"
7483             "clz    $dst, $dst" %}
7484   ins_encode %{
7485     __ rbit(as_Register($dst$$reg), as_Register($src$$reg));
7486     __ clz(as_Register($dst$$reg), as_Register($dst$$reg));
7487   %}
7488 
7489   ins_pipe(ialu_reg);
7490 %}
7491 
7492 //---------- Population Count Instructions -------------------------------------
7493 //
7494 
7495 instruct popCountI(iRegINoSp dst, iRegIorL2I src, vRegF tmp) %{
7496   predicate(UsePopCountInstruction);
7497   match(Set dst (PopCountI src));
7498   effect(TEMP tmp);
7499   ins_cost(INSN_COST * 13);
7500 
7501   format %{ "movw   $src, $src\n\t"
7502             "mov    $tmp, $src\t# vector (1D)\n\t"
7503             "cnt    $tmp, $tmp\t# vector (8B)\n\t"
7504             "addv   $tmp, $tmp\t# vector (8B)\n\t"
7505             "mov    $dst, $tmp\t# vector (1D)" %}
7506   ins_encode %{
7507     __ movw($src$$Register, $src$$Register); // ensure top 32 bits 0
7508     __ mov($tmp$$FloatRegister, __ T1D, 0, $src$$Register);
7509     __ cnt($tmp$$FloatRegister, __ T8B, $tmp$$FloatRegister);
7510     __ addv($tmp$$FloatRegister, __ T8B, $tmp$$FloatRegister);
7511     __ mov($dst$$Register, $tmp$$FloatRegister, __ T1D, 0);
7512   %}
7513 
7514   ins_pipe(pipe_class_default);
7515 %}
7516 
7517 instruct popCountI_mem(iRegINoSp dst, memory mem, vRegF tmp) %{
7518   predicate(UsePopCountInstruction);
7519   match(Set dst (PopCountI (LoadI mem)));
7520   effect(TEMP tmp);
7521   ins_cost(INSN_COST * 13);
7522 
7523   format %{ "ldrs   $tmp, $mem\n\t"
7524             "cnt    $tmp, $tmp\t# vector (8B)\n\t"
7525             "addv   $tmp, $tmp\t# vector (8B)\n\t"
7526             "mov    $dst, $tmp\t# vector (1D)" %}
7527   ins_encode %{
7528     FloatRegister tmp_reg = as_FloatRegister($tmp$$reg);
7529     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldrs, tmp_reg, $mem->opcode(),
7530                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
7531     __ cnt($tmp$$FloatRegister, __ T8B, $tmp$$FloatRegister);
7532     __ addv($tmp$$FloatRegister, __ T8B, $tmp$$FloatRegister);
7533     __ mov($dst$$Register, $tmp$$FloatRegister, __ T1D, 0);
7534   %}
7535 
7536   ins_pipe(pipe_class_default);
7537 %}
7538 
7539 // Note: Long.bitCount(long) returns an int.
7540 instruct popCountL(iRegINoSp dst, iRegL src, vRegD tmp) %{
7541   predicate(UsePopCountInstruction);
7542   match(Set dst (PopCountL src));
7543   effect(TEMP tmp);
7544   ins_cost(INSN_COST * 13);
7545 
7546   format %{ "mov    $tmp, $src\t# vector (1D)\n\t"
7547             "cnt    $tmp, $tmp\t# vector (8B)\n\t"
7548             "addv   $tmp, $tmp\t# vector (8B)\n\t"
7549             "mov    $dst, $tmp\t# vector (1D)" %}
7550   ins_encode %{
7551     __ mov($tmp$$FloatRegister, __ T1D, 0, $src$$Register);
7552     __ cnt($tmp$$FloatRegister, __ T8B, $tmp$$FloatRegister);
7553     __ addv($tmp$$FloatRegister, __ T8B, $tmp$$FloatRegister);
7554     __ mov($dst$$Register, $tmp$$FloatRegister, __ T1D, 0);
7555   %}
7556 
7557   ins_pipe(pipe_class_default);
7558 %}
7559 
7560 instruct popCountL_mem(iRegINoSp dst, memory mem, vRegD tmp) %{
7561   predicate(UsePopCountInstruction);
7562   match(Set dst (PopCountL (LoadL mem)));
7563   effect(TEMP tmp);
7564   ins_cost(INSN_COST * 13);
7565 
7566   format %{ "ldrd   $tmp, $mem\n\t"
7567             "cnt    $tmp, $tmp\t# vector (8B)\n\t"
7568             "addv   $tmp, $tmp\t# vector (8B)\n\t"
7569             "mov    $dst, $tmp\t# vector (1D)" %}
7570   ins_encode %{
7571     FloatRegister tmp_reg = as_FloatRegister($tmp$$reg);
7572     loadStore(MacroAssembler(&cbuf), &MacroAssembler::ldrd, tmp_reg, $mem->opcode(),
7573                as_Register($mem$$base), $mem$$index, $mem$$scale, $mem$$disp);
7574     __ cnt($tmp$$FloatRegister, __ T8B, $tmp$$FloatRegister);
7575     __ addv($tmp$$FloatRegister, __ T8B, $tmp$$FloatRegister);
7576     __ mov($dst$$Register, $tmp$$FloatRegister, __ T1D, 0);
7577   %}
7578 
7579   ins_pipe(pipe_class_default);
7580 %}
7581 
7582 // ============================================================================
7583 // MemBar Instruction
7584 
7585 instruct load_fence() %{
7586   match(LoadFence);
7587   ins_cost(VOLATILE_REF_COST);
7588 
7589   format %{ "load_fence" %}
7590 
7591   ins_encode %{
7592     __ membar(Assembler::LoadLoad|Assembler::LoadStore);
7593   %}
7594   ins_pipe(pipe_serial);
7595 %}
7596 
7597 instruct unnecessary_membar_acquire() %{
7598   predicate(unnecessary_acquire(n));
7599   match(MemBarAcquire);
7600   ins_cost(0);
7601 
7602   format %{ "membar_acquire (elided)" %}
7603 
7604   ins_encode %{
7605     __ block_comment("membar_acquire (elided)");
7606   %}
7607 
7608   ins_pipe(pipe_class_empty);
7609 %}
7610 
7611 instruct membar_acquire() %{
7612   match(MemBarAcquire);
7613   ins_cost(VOLATILE_REF_COST);
7614 
7615   format %{ "membar_acquire\n\t"
7616             "dmb ish" %}
7617 
7618   ins_encode %{
7619     __ block_comment("membar_acquire");
7620     __ membar(Assembler::LoadLoad|Assembler::LoadStore);
7621   %}
7622 
7623   ins_pipe(pipe_serial);
7624 %}
7625 
7626 
7627 instruct membar_acquire_lock() %{
7628   match(MemBarAcquireLock);
7629   ins_cost(VOLATILE_REF_COST);
7630 
7631   format %{ "membar_acquire_lock (elided)" %}
7632 
7633   ins_encode %{
7634     __ block_comment("membar_acquire_lock (elided)");
7635   %}
7636 
7637   ins_pipe(pipe_serial);
7638 %}
7639 
7640 instruct store_fence() %{
7641   match(StoreFence);
7642   ins_cost(VOLATILE_REF_COST);
7643 
7644   format %{ "store_fence" %}
7645 
7646   ins_encode %{
7647     __ membar(Assembler::LoadStore|Assembler::StoreStore);
7648   %}
7649   ins_pipe(pipe_serial);
7650 %}
7651 
7652 instruct unnecessary_membar_release() %{
7653   predicate(unnecessary_release(n));
7654   match(MemBarRelease);
7655   ins_cost(0);
7656 
7657   format %{ "membar_release (elided)" %}
7658 
7659   ins_encode %{
7660     __ block_comment("membar_release (elided)");
7661   %}
7662   ins_pipe(pipe_serial);
7663 %}
7664 
7665 instruct membar_release() %{
7666   match(MemBarRelease);
7667   ins_cost(VOLATILE_REF_COST);
7668 
7669   format %{ "membar_release\n\t"
7670             "dmb ish" %}
7671 
7672   ins_encode %{
7673     __ block_comment("membar_release");
7674     __ membar(Assembler::LoadStore|Assembler::StoreStore);
7675   %}
7676   ins_pipe(pipe_serial);
7677 %}
7678 
7679 instruct membar_storestore() %{
7680   match(MemBarStoreStore);
7681   ins_cost(VOLATILE_REF_COST);
7682 
7683   format %{ "MEMBAR-store-store" %}
7684 
7685   ins_encode %{
7686     __ membar(Assembler::StoreStore);
7687   %}
7688   ins_pipe(pipe_serial);
7689 %}
7690 
7691 instruct membar_release_lock() %{
7692   match(MemBarReleaseLock);
7693   ins_cost(VOLATILE_REF_COST);
7694 
7695   format %{ "membar_release_lock (elided)" %}
7696 
7697   ins_encode %{
7698     __ block_comment("membar_release_lock (elided)");
7699   %}
7700 
7701   ins_pipe(pipe_serial);
7702 %}
7703 
7704 instruct unnecessary_membar_volatile() %{
7705   predicate(unnecessary_volatile(n));
7706   match(MemBarVolatile);
7707   ins_cost(0);
7708 
7709   format %{ "membar_volatile (elided)" %}
7710 
7711   ins_encode %{
7712     __ block_comment("membar_volatile (elided)");
7713   %}
7714 
7715   ins_pipe(pipe_serial);
7716 %}
7717 
7718 instruct membar_volatile() %{
7719   match(MemBarVolatile);
7720   ins_cost(VOLATILE_REF_COST*100);
7721 
7722   format %{ "membar_volatile\n\t"
7723              "dmb ish"%}
7724 
7725   ins_encode %{
7726     __ block_comment("membar_volatile");
7727     __ membar(Assembler::StoreLoad);
7728   %}
7729 
7730   ins_pipe(pipe_serial);
7731 %}
7732 
7733 // ============================================================================
7734 // Cast/Convert Instructions
7735 
7736 instruct castX2P(iRegPNoSp dst, iRegL src) %{
7737   match(Set dst (CastX2P src));
7738 
7739   ins_cost(INSN_COST);
7740   format %{ "mov $dst, $src\t# long -> ptr" %}
7741 
7742   ins_encode %{
7743     if ($dst$$reg != $src$$reg) {
7744       __ mov(as_Register($dst$$reg), as_Register($src$$reg));
7745     }
7746   %}
7747 
7748   ins_pipe(ialu_reg);
7749 %}
7750 
7751 instruct castP2X(iRegLNoSp dst, iRegP src) %{
7752   match(Set dst (CastP2X src));
7753 
7754   ins_cost(INSN_COST);
7755   format %{ "mov $dst, $src\t# ptr -> long" %}
7756 
7757   ins_encode %{
7758     if ($dst$$reg != $src$$reg) {
7759       __ mov(as_Register($dst$$reg), as_Register($src$$reg));
7760     }
7761   %}
7762 
7763   ins_pipe(ialu_reg);
7764 %}
7765 
7766 // Convert oop into int for vectors alignment masking
7767 instruct convP2I(iRegINoSp dst, iRegP src) %{
7768   match(Set dst (ConvL2I (CastP2X src)));
7769 
7770   ins_cost(INSN_COST);
7771   format %{ "movw $dst, $src\t# ptr -> int" %}
7772   ins_encode %{
7773     __ movw($dst$$Register, $src$$Register);
7774   %}
7775 
7776   ins_pipe(ialu_reg);
7777 %}
7778 
7779 // Convert compressed oop into int for vectors alignment masking
7780 // in case of 32bit oops (heap < 4Gb).
7781 instruct convN2I(iRegINoSp dst, iRegN src)
7782 %{
7783   predicate(Universe::narrow_oop_shift() == 0);
7784   match(Set dst (ConvL2I (CastP2X (DecodeN src))));
7785 
7786   ins_cost(INSN_COST);
7787   format %{ "mov dst, $src\t# compressed ptr -> int" %}
7788   ins_encode %{
7789     __ movw($dst$$Register, $src$$Register);
7790   %}
7791 
7792   ins_pipe(ialu_reg);
7793 %}
7794 
7795 
7796 // Convert oop pointer into compressed form
7797 instruct encodeHeapOop(iRegNNoSp dst, iRegP src, rFlagsReg cr) %{
7798   predicate(n->bottom_type()->make_ptr()->ptr() != TypePtr::NotNull);
7799   match(Set dst (EncodeP src));
7800   effect(KILL cr);
7801   ins_cost(INSN_COST * 3);
7802   format %{ "encode_heap_oop $dst, $src" %}
7803   ins_encode %{
7804     Register s = $src$$Register;
7805     Register d = $dst$$Register;
7806     __ encode_heap_oop(d, s);
7807   %}
7808   ins_pipe(ialu_reg);
7809 %}
7810 
7811 instruct encodeHeapOop_not_null(iRegNNoSp dst, iRegP src, rFlagsReg cr) %{
7812   predicate(n->bottom_type()->make_ptr()->ptr() == TypePtr::NotNull);
7813   match(Set dst (EncodeP src));
7814   ins_cost(INSN_COST * 3);
7815   format %{ "encode_heap_oop_not_null $dst, $src" %}
7816   ins_encode %{
7817     __ encode_heap_oop_not_null($dst$$Register, $src$$Register);
7818   %}
7819   ins_pipe(ialu_reg);
7820 %}
7821 
7822 instruct decodeHeapOop(iRegPNoSp dst, iRegN src, rFlagsReg cr) %{
7823   predicate(n->bottom_type()->is_ptr()->ptr() != TypePtr::NotNull &&
7824             n->bottom_type()->is_ptr()->ptr() != TypePtr::Constant);
7825   match(Set dst (DecodeN src));
7826   ins_cost(INSN_COST * 3);
7827   format %{ "decode_heap_oop $dst, $src" %}
7828   ins_encode %{
7829     Register s = $src$$Register;
7830     Register d = $dst$$Register;
7831     __ decode_heap_oop(d, s);
7832   %}
7833   ins_pipe(ialu_reg);
7834 %}
7835 
7836 instruct decodeHeapOop_not_null(iRegPNoSp dst, iRegN src, rFlagsReg cr) %{
7837   predicate(n->bottom_type()->is_ptr()->ptr() == TypePtr::NotNull ||
7838             n->bottom_type()->is_ptr()->ptr() == TypePtr::Constant);
7839   match(Set dst (DecodeN src));
7840   ins_cost(INSN_COST * 3);
7841   format %{ "decode_heap_oop_not_null $dst, $src" %}
7842   ins_encode %{
7843     Register s = $src$$Register;
7844     Register d = $dst$$Register;
7845     __ decode_heap_oop_not_null(d, s);
7846   %}
7847   ins_pipe(ialu_reg);
7848 %}
7849 
7850 // n.b. AArch64 implementations of encode_klass_not_null and
7851 // decode_klass_not_null do not modify the flags register so, unlike
7852 // Intel, we don't kill CR as a side effect here
7853 
7854 instruct encodeKlass_not_null(iRegNNoSp dst, iRegP src) %{
7855   match(Set dst (EncodePKlass src));
7856 
7857   ins_cost(INSN_COST * 3);
7858   format %{ "encode_klass_not_null $dst,$src" %}
7859 
7860   ins_encode %{
7861     Register src_reg = as_Register($src$$reg);
7862     Register dst_reg = as_Register($dst$$reg);
7863     __ encode_klass_not_null(dst_reg, src_reg);
7864   %}
7865 
7866    ins_pipe(ialu_reg);
7867 %}
7868 
7869 instruct decodeKlass_not_null(iRegPNoSp dst, iRegN src) %{
7870   match(Set dst (DecodeNKlass src));
7871 
7872   ins_cost(INSN_COST * 3);
7873   format %{ "decode_klass_not_null $dst,$src" %}
7874 
7875   ins_encode %{
7876     Register src_reg = as_Register($src$$reg);
7877     Register dst_reg = as_Register($dst$$reg);
7878     if (dst_reg != src_reg) {
7879       __ decode_klass_not_null(dst_reg, src_reg);
7880     } else {
7881       __ decode_klass_not_null(dst_reg);
7882     }
7883   %}
7884 
7885    ins_pipe(ialu_reg);
7886 %}
7887 
7888 instruct checkCastPP(iRegPNoSp dst)
7889 %{
7890   match(Set dst (CheckCastPP dst));
7891 
7892   size(0);
7893   format %{ "# checkcastPP of $dst" %}
7894   ins_encode(/* empty encoding */);
7895   ins_pipe(pipe_class_empty);
7896 %}
7897 
7898 instruct castPP(iRegPNoSp dst)
7899 %{
7900   match(Set dst (CastPP dst));
7901 
7902   size(0);
7903   format %{ "# castPP of $dst" %}
7904   ins_encode(/* empty encoding */);
7905   ins_pipe(pipe_class_empty);
7906 %}
7907 
7908 instruct castII(iRegI dst)
7909 %{
7910   match(Set dst (CastII dst));
7911 
7912   size(0);
7913   format %{ "# castII of $dst" %}
7914   ins_encode(/* empty encoding */);
7915   ins_cost(0);
7916   ins_pipe(pipe_class_empty);
7917 %}
7918 
7919 instruct castLL(iRegL dst)
7920 %{
7921   match(Set dst (CastLL dst));
7922 
7923   size(0);
7924   format %{ "# castLL of $dst" %}
7925   ins_encode(/* empty encoding */);
7926   ins_cost(0);
7927   ins_pipe(pipe_class_empty);
7928 %}
7929 
7930 // ============================================================================
7931 // Atomic operation instructions
7932 //
7933 // Intel and SPARC both implement Ideal Node LoadPLocked and
7934 // Store{PIL}Conditional instructions using a normal load for the
7935 // LoadPLocked and a CAS for the Store{PIL}Conditional.
7936 //
7937 // The ideal code appears only to use LoadPLocked/StorePLocked as a
7938 // pair to lock object allocations from Eden space when not using
7939 // TLABs.
7940 //
7941 // There does not appear to be a Load{IL}Locked Ideal Node and the
7942 // Ideal code appears to use Store{IL}Conditional as an alias for CAS
7943 // and to use StoreIConditional only for 32-bit and StoreLConditional
7944 // only for 64-bit.
7945 //
7946 // We implement LoadPLocked and StorePLocked instructions using,
7947 // respectively the AArch64 hw load-exclusive and store-conditional
7948 // instructions. Whereas we must implement each of
7949 // Store{IL}Conditional using a CAS which employs a pair of
7950 // instructions comprising a load-exclusive followed by a
7951 // store-conditional.
7952 
7953 
7954 // Locked-load (linked load) of the current heap-top
7955 // used when updating the eden heap top
7956 // implemented using ldaxr on AArch64
7957 
7958 instruct loadPLocked(iRegPNoSp dst, indirect mem)
7959 %{
7960   match(Set dst (LoadPLocked mem));
7961 
7962   ins_cost(VOLATILE_REF_COST);
7963 
7964   format %{ "ldaxr $dst, $mem\t# ptr linked acquire" %}
7965 
7966   ins_encode(aarch64_enc_ldaxr(dst, mem));
7967 
7968   ins_pipe(pipe_serial);
7969 %}
7970 
7971 // Conditional-store of the updated heap-top.
7972 // Used during allocation of the shared heap.
7973 // Sets flag (EQ) on success.
7974 // implemented using stlxr on AArch64.
7975 
7976 instruct storePConditional(memory heap_top_ptr, iRegP oldval, iRegP newval, rFlagsReg cr)
7977 %{
7978   match(Set cr (StorePConditional heap_top_ptr (Binary oldval newval)));
7979 
7980   ins_cost(VOLATILE_REF_COST);
7981 
7982  // TODO
7983  // do we need to do a store-conditional release or can we just use a
7984  // plain store-conditional?
7985 
7986   format %{
7987     "stlxr rscratch1, $newval, $heap_top_ptr\t# ptr cond release"
7988     "cmpw rscratch1, zr\t# EQ on successful write"
7989   %}
7990 
7991   ins_encode(aarch64_enc_stlxr(newval, heap_top_ptr));
7992 
7993   ins_pipe(pipe_serial);
7994 %}
7995 
7996 
7997 // storeLConditional is used by PhaseMacroExpand::expand_lock_node
7998 // when attempting to rebias a lock towards the current thread.  We
7999 // must use the acquire form of cmpxchg in order to guarantee acquire
8000 // semantics in this case.
8001 instruct storeLConditional(indirect mem, iRegLNoSp oldval, iRegLNoSp newval, rFlagsReg cr)
8002 %{
8003   match(Set cr (StoreLConditional mem (Binary oldval newval)));
8004 
8005   ins_cost(VOLATILE_REF_COST);
8006 
8007   format %{
8008     "cmpxchg rscratch1, $mem, $oldval, $newval, $mem\t# if $mem == $oldval then $mem <-- $newval"
8009     "cmpw rscratch1, zr\t# EQ on successful write"
8010   %}
8011 
8012   ins_encode(aarch64_enc_cmpxchg_acq(mem, oldval, newval));
8013 
8014   ins_pipe(pipe_slow);
8015 %}
8016 
8017 // storeIConditional also has acquire semantics, for no better reason
8018 // than matching storeLConditional.  At the time of writing this
8019 // comment storeIConditional was not used anywhere by AArch64.
8020 instruct storeIConditional(indirect mem, iRegINoSp oldval, iRegINoSp newval, rFlagsReg cr)
8021 %{
8022   match(Set cr (StoreIConditional mem (Binary oldval newval)));
8023 
8024   ins_cost(VOLATILE_REF_COST);
8025 
8026   format %{
8027     "cmpxchgw rscratch1, $mem, $oldval, $newval, $mem\t# if $mem == $oldval then $mem <-- $newval"
8028     "cmpw rscratch1, zr\t# EQ on successful write"
8029   %}
8030 
8031   ins_encode(aarch64_enc_cmpxchgw_acq(mem, oldval, newval));
8032 
8033   ins_pipe(pipe_slow);
8034 %}
8035 
8036 // standard CompareAndSwapX when we are using barriers
8037 // these have higher priority than the rules selected by a predicate
8038 
8039 // XXX No flag versions for CompareAndSwap{I,L,P,N} because matcher
8040 // can't match them
8041 
8042 instruct compareAndSwapB(iRegINoSp res, indirect mem, iRegINoSp oldval, iRegINoSp newval, rFlagsReg cr) %{
8043 
8044   match(Set res (CompareAndSwapB mem (Binary oldval newval)));
8045   ins_cost(2 * VOLATILE_REF_COST);
8046 
8047   effect(KILL cr);
8048 
8049   format %{
8050     "cmpxchgb $mem, $oldval, $newval\t# (int) if $mem == $oldval then $mem <-- $newval"
8051     "cset $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8052   %}
8053 
8054   ins_encode(aarch64_enc_cmpxchgb(mem, oldval, newval),
8055             aarch64_enc_cset_eq(res));
8056 
8057   ins_pipe(pipe_slow);
8058 %}
8059 
8060 instruct compareAndSwapS(iRegINoSp res, indirect mem, iRegINoSp oldval, iRegINoSp newval, rFlagsReg cr) %{
8061 
8062   match(Set res (CompareAndSwapS mem (Binary oldval newval)));
8063   ins_cost(2 * VOLATILE_REF_COST);
8064 
8065   effect(KILL cr);
8066 
8067   format %{
8068     "cmpxchgs $mem, $oldval, $newval\t# (int) if $mem == $oldval then $mem <-- $newval"
8069     "cset $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8070   %}
8071 
8072   ins_encode(aarch64_enc_cmpxchgs(mem, oldval, newval),
8073             aarch64_enc_cset_eq(res));
8074 
8075   ins_pipe(pipe_slow);
8076 %}
8077 
8078 instruct compareAndSwapI(iRegINoSp res, indirect mem, iRegINoSp oldval, iRegINoSp newval, rFlagsReg cr) %{
8079 
8080   match(Set res (CompareAndSwapI mem (Binary oldval newval)));
8081   ins_cost(2 * VOLATILE_REF_COST);
8082 
8083   effect(KILL cr);
8084 
8085  format %{
8086     "cmpxchgw $mem, $oldval, $newval\t# (int) if $mem == $oldval then $mem <-- $newval"
8087     "cset $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8088  %}
8089 
8090  ins_encode(aarch64_enc_cmpxchgw(mem, oldval, newval),
8091             aarch64_enc_cset_eq(res));
8092 
8093   ins_pipe(pipe_slow);
8094 %}
8095 
8096 instruct compareAndSwapL(iRegINoSp res, indirect mem, iRegLNoSp oldval, iRegLNoSp newval, rFlagsReg cr) %{
8097 
8098   match(Set res (CompareAndSwapL mem (Binary oldval newval)));
8099   ins_cost(2 * VOLATILE_REF_COST);
8100 
8101   effect(KILL cr);
8102 
8103  format %{
8104     "cmpxchg $mem, $oldval, $newval\t# (long) if $mem == $oldval then $mem <-- $newval"
8105     "cset $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8106  %}
8107 
8108  ins_encode(aarch64_enc_cmpxchg(mem, oldval, newval),
8109             aarch64_enc_cset_eq(res));
8110 
8111   ins_pipe(pipe_slow);
8112 %}
8113 
8114 instruct compareAndSwapP(iRegINoSp res, indirect mem, iRegP oldval, iRegP newval, rFlagsReg cr) %{
8115 
8116   match(Set res (CompareAndSwapP mem (Binary oldval newval)));
8117   ins_cost(2 * VOLATILE_REF_COST);
8118 
8119   effect(KILL cr);
8120 
8121  format %{
8122     "cmpxchg $mem, $oldval, $newval\t# (ptr) if $mem == $oldval then $mem <-- $newval"
8123     "cset $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8124  %}
8125 
8126  ins_encode(aarch64_enc_cmpxchg(mem, oldval, newval),
8127             aarch64_enc_cset_eq(res));
8128 
8129   ins_pipe(pipe_slow);
8130 %}
8131 
8132 instruct compareAndSwapN(iRegINoSp res, indirect mem, iRegNNoSp oldval, iRegNNoSp newval, rFlagsReg cr) %{
8133 
8134   match(Set res (CompareAndSwapN mem (Binary oldval newval)));
8135   ins_cost(2 * VOLATILE_REF_COST);
8136 
8137   effect(KILL cr);
8138 
8139  format %{
8140     "cmpxchgw $mem, $oldval, $newval\t# (narrow oop) if $mem == $oldval then $mem <-- $newval"
8141     "cset $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8142  %}
8143 
8144  ins_encode(aarch64_enc_cmpxchgw(mem, oldval, newval),
8145             aarch64_enc_cset_eq(res));
8146 
8147   ins_pipe(pipe_slow);
8148 %}
8149 
8150 // alternative CompareAndSwapX when we are eliding barriers
8151 
8152 instruct compareAndSwapBAcq(iRegINoSp res, indirect mem, iRegINoSp oldval, iRegINoSp newval, rFlagsReg cr) %{
8153 
8154   predicate(needs_acquiring_load_exclusive(n));
8155   match(Set res (CompareAndSwapB mem (Binary oldval newval)));
8156   ins_cost(VOLATILE_REF_COST);
8157 
8158   effect(KILL cr);
8159 
8160   format %{
8161     "cmpxchgb_acq $mem, $oldval, $newval\t# (int) if $mem == $oldval then $mem <-- $newval"
8162     "cset $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8163   %}
8164 
8165   ins_encode(aarch64_enc_cmpxchgb_acq(mem, oldval, newval),
8166             aarch64_enc_cset_eq(res));
8167 
8168   ins_pipe(pipe_slow);
8169 %}
8170 
8171 instruct compareAndSwapSAcq(iRegINoSp res, indirect mem, iRegINoSp oldval, iRegINoSp newval, rFlagsReg cr) %{
8172 
8173   predicate(needs_acquiring_load_exclusive(n));
8174   match(Set res (CompareAndSwapS mem (Binary oldval newval)));
8175   ins_cost(VOLATILE_REF_COST);
8176 
8177   effect(KILL cr);
8178 
8179   format %{
8180     "cmpxchgs_acq $mem, $oldval, $newval\t# (int) if $mem == $oldval then $mem <-- $newval"
8181     "cset $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8182   %}
8183 
8184   ins_encode(aarch64_enc_cmpxchgs_acq(mem, oldval, newval),
8185             aarch64_enc_cset_eq(res));
8186 
8187   ins_pipe(pipe_slow);
8188 %}
8189 
8190 instruct compareAndSwapIAcq(iRegINoSp res, indirect mem, iRegINoSp oldval, iRegINoSp newval, rFlagsReg cr) %{
8191 
8192   predicate(needs_acquiring_load_exclusive(n));
8193   match(Set res (CompareAndSwapI mem (Binary oldval newval)));
8194   ins_cost(VOLATILE_REF_COST);
8195 
8196   effect(KILL cr);
8197 
8198  format %{
8199     "cmpxchgw_acq $mem, $oldval, $newval\t# (int) if $mem == $oldval then $mem <-- $newval"
8200     "cset $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8201  %}
8202 
8203  ins_encode(aarch64_enc_cmpxchgw_acq(mem, oldval, newval),
8204             aarch64_enc_cset_eq(res));
8205 
8206   ins_pipe(pipe_slow);
8207 %}
8208 
8209 instruct compareAndSwapLAcq(iRegINoSp res, indirect mem, iRegLNoSp oldval, iRegLNoSp newval, rFlagsReg cr) %{
8210 
8211   predicate(needs_acquiring_load_exclusive(n));
8212   match(Set res (CompareAndSwapL mem (Binary oldval newval)));
8213   ins_cost(VOLATILE_REF_COST);
8214 
8215   effect(KILL cr);
8216 
8217  format %{
8218     "cmpxchg_acq $mem, $oldval, $newval\t# (long) if $mem == $oldval then $mem <-- $newval"
8219     "cset $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8220  %}
8221 
8222  ins_encode(aarch64_enc_cmpxchg_acq(mem, oldval, newval),
8223             aarch64_enc_cset_eq(res));
8224 
8225   ins_pipe(pipe_slow);
8226 %}
8227 
8228 instruct compareAndSwapPAcq(iRegINoSp res, indirect mem, iRegP oldval, iRegP newval, rFlagsReg cr) %{
8229 
8230   predicate(needs_acquiring_load_exclusive(n));
8231   match(Set res (CompareAndSwapP mem (Binary oldval newval)));
8232   ins_cost(VOLATILE_REF_COST);
8233 
8234   effect(KILL cr);
8235 
8236  format %{
8237     "cmpxchg_acq $mem, $oldval, $newval\t# (ptr) if $mem == $oldval then $mem <-- $newval"
8238     "cset $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8239  %}
8240 
8241  ins_encode(aarch64_enc_cmpxchg_acq(mem, oldval, newval),
8242             aarch64_enc_cset_eq(res));
8243 
8244   ins_pipe(pipe_slow);
8245 %}
8246 
8247 instruct compareAndSwapNAcq(iRegINoSp res, indirect mem, iRegNNoSp oldval, iRegNNoSp newval, rFlagsReg cr) %{
8248 
8249   predicate(needs_acquiring_load_exclusive(n));
8250   match(Set res (CompareAndSwapN mem (Binary oldval newval)));
8251   ins_cost(VOLATILE_REF_COST);
8252 
8253   effect(KILL cr);
8254 
8255  format %{
8256     "cmpxchgw_acq $mem, $oldval, $newval\t# (narrow oop) if $mem == $oldval then $mem <-- $newval"
8257     "cset $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8258  %}
8259 
8260  ins_encode(aarch64_enc_cmpxchgw_acq(mem, oldval, newval),
8261             aarch64_enc_cset_eq(res));
8262 
8263   ins_pipe(pipe_slow);
8264 %}
8265 
8266 
8267 // ---------------------------------------------------------------------
8268 
8269 
8270 // BEGIN This section of the file is automatically generated. Do not edit --------------
8271 
8272 // Sundry CAS operations.  Note that release is always true,
8273 // regardless of the memory ordering of the CAS.  This is because we
8274 // need the volatile case to be sequentially consistent but there is
8275 // no trailing StoreLoad barrier emitted by C2.  Unfortunately we
8276 // can't check the type of memory ordering here, so we always emit a
8277 // STLXR.
8278 
8279 // This section is generated from aarch64_ad_cas.m4
8280 
8281 
8282 
8283 instruct compareAndExchangeB(iRegINoSp res, indirect mem, iRegI oldval, iRegI newval, rFlagsReg cr) %{
8284   match(Set res (CompareAndExchangeB mem (Binary oldval newval)));
8285   ins_cost(2 * VOLATILE_REF_COST);
8286   effect(TEMP_DEF res, KILL cr);
8287   format %{
8288     "cmpxchgb $res = $mem, $oldval, $newval\t# (byte, weak) if $mem == $oldval then $mem <-- $newval"
8289   %}
8290   ins_encode %{
8291     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8292                Assembler::byte, /*acquire*/ false, /*release*/ true,
8293                /*weak*/ false, $res$$Register);
8294     __ sxtbw($res$$Register, $res$$Register);
8295   %}
8296   ins_pipe(pipe_slow);
8297 %}
8298 
8299 instruct compareAndExchangeS(iRegINoSp res, indirect mem, iRegI oldval, iRegI newval, rFlagsReg cr) %{
8300   match(Set res (CompareAndExchangeS mem (Binary oldval newval)));
8301   ins_cost(2 * VOLATILE_REF_COST);
8302   effect(TEMP_DEF res, KILL cr);
8303   format %{
8304     "cmpxchgs $res = $mem, $oldval, $newval\t# (short, weak) if $mem == $oldval then $mem <-- $newval"
8305   %}
8306   ins_encode %{
8307     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8308                Assembler::halfword, /*acquire*/ false, /*release*/ true,
8309                /*weak*/ false, $res$$Register);
8310     __ sxthw($res$$Register, $res$$Register);
8311   %}
8312   ins_pipe(pipe_slow);
8313 %}
8314 
8315 instruct compareAndExchangeI(iRegINoSp res, indirect mem, iRegI oldval, iRegI newval, rFlagsReg cr) %{
8316   match(Set res (CompareAndExchangeI mem (Binary oldval newval)));
8317   ins_cost(2 * VOLATILE_REF_COST);
8318   effect(TEMP_DEF res, KILL cr);
8319   format %{
8320     "cmpxchgw $res = $mem, $oldval, $newval\t# (int, weak) if $mem == $oldval then $mem <-- $newval"
8321   %}
8322   ins_encode %{
8323     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8324                Assembler::word, /*acquire*/ false, /*release*/ true,
8325                /*weak*/ false, $res$$Register);
8326   %}
8327   ins_pipe(pipe_slow);
8328 %}
8329 
8330 instruct compareAndExchangeL(iRegLNoSp res, indirect mem, iRegL oldval, iRegL newval, rFlagsReg cr) %{
8331   match(Set res (CompareAndExchangeL mem (Binary oldval newval)));
8332   ins_cost(2 * VOLATILE_REF_COST);
8333   effect(TEMP_DEF res, KILL cr);
8334   format %{
8335     "cmpxchg $res = $mem, $oldval, $newval\t# (long, weak) if $mem == $oldval then $mem <-- $newval"
8336   %}
8337   ins_encode %{
8338     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8339                Assembler::xword, /*acquire*/ false, /*release*/ true,
8340                /*weak*/ false, $res$$Register);
8341   %}
8342   ins_pipe(pipe_slow);
8343 %}
8344 
8345 instruct compareAndExchangeN(iRegNNoSp res, indirect mem, iRegN oldval, iRegN newval, rFlagsReg cr) %{
8346   match(Set res (CompareAndExchangeN mem (Binary oldval newval)));
8347   ins_cost(2 * VOLATILE_REF_COST);
8348   effect(TEMP_DEF res, KILL cr);
8349   format %{
8350     "cmpxchgw $res = $mem, $oldval, $newval\t# (narrow oop, weak) if $mem == $oldval then $mem <-- $newval"
8351   %}
8352   ins_encode %{
8353     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8354                Assembler::word, /*acquire*/ false, /*release*/ true,
8355                /*weak*/ false, $res$$Register);
8356   %}
8357   ins_pipe(pipe_slow);
8358 %}
8359 
8360 instruct compareAndExchangeP(iRegPNoSp res, indirect mem, iRegP oldval, iRegP newval, rFlagsReg cr) %{
8361   match(Set res (CompareAndExchangeP mem (Binary oldval newval)));
8362   ins_cost(2 * VOLATILE_REF_COST);
8363   effect(TEMP_DEF res, KILL cr);
8364   format %{
8365     "cmpxchg $res = $mem, $oldval, $newval\t# (ptr, weak) if $mem == $oldval then $mem <-- $newval"
8366   %}
8367   ins_encode %{
8368     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8369                Assembler::xword, /*acquire*/ false, /*release*/ true,
8370                /*weak*/ false, $res$$Register);
8371   %}
8372   ins_pipe(pipe_slow);
8373 %}
8374 
8375 instruct compareAndExchangeBAcq(iRegINoSp res, indirect mem, iRegI oldval, iRegI newval, rFlagsReg cr) %{
8376   predicate(needs_acquiring_load_exclusive(n));
8377   match(Set res (CompareAndExchangeB mem (Binary oldval newval)));
8378   ins_cost(VOLATILE_REF_COST);
8379   effect(TEMP_DEF res, KILL cr);
8380   format %{
8381     "cmpxchgb_acq $res = $mem, $oldval, $newval\t# (byte, weak) if $mem == $oldval then $mem <-- $newval"
8382   %}
8383   ins_encode %{
8384     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8385                Assembler::byte, /*acquire*/ true, /*release*/ true,
8386                /*weak*/ false, $res$$Register);
8387     __ sxtbw($res$$Register, $res$$Register);
8388   %}
8389   ins_pipe(pipe_slow);
8390 %}
8391 
8392 instruct compareAndExchangeSAcq(iRegINoSp res, indirect mem, iRegI oldval, iRegI newval, rFlagsReg cr) %{
8393   predicate(needs_acquiring_load_exclusive(n));
8394   match(Set res (CompareAndExchangeS mem (Binary oldval newval)));
8395   ins_cost(VOLATILE_REF_COST);
8396   effect(TEMP_DEF res, KILL cr);
8397   format %{
8398     "cmpxchgs_acq $res = $mem, $oldval, $newval\t# (short, weak) if $mem == $oldval then $mem <-- $newval"
8399   %}
8400   ins_encode %{
8401     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8402                Assembler::halfword, /*acquire*/ true, /*release*/ true,
8403                /*weak*/ false, $res$$Register);
8404     __ sxthw($res$$Register, $res$$Register);
8405   %}
8406   ins_pipe(pipe_slow);
8407 %}
8408 
8409 
8410 instruct compareAndExchangeIAcq(iRegINoSp res, indirect mem, iRegI oldval, iRegI newval, rFlagsReg cr) %{
8411   predicate(needs_acquiring_load_exclusive(n));
8412   match(Set res (CompareAndExchangeI mem (Binary oldval newval)));
8413   ins_cost(VOLATILE_REF_COST);
8414   effect(TEMP_DEF res, KILL cr);
8415   format %{
8416     "cmpxchgw_acq $res = $mem, $oldval, $newval\t# (int, weak) if $mem == $oldval then $mem <-- $newval"
8417   %}
8418   ins_encode %{
8419     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8420                Assembler::word, /*acquire*/ true, /*release*/ true,
8421                /*weak*/ false, $res$$Register);
8422   %}
8423   ins_pipe(pipe_slow);
8424 %}
8425 
8426 instruct compareAndExchangeLAcq(iRegLNoSp res, indirect mem, iRegL oldval, iRegL newval, rFlagsReg cr) %{
8427   predicate(needs_acquiring_load_exclusive(n));
8428   match(Set res (CompareAndExchangeL mem (Binary oldval newval)));
8429   ins_cost(VOLATILE_REF_COST);
8430   effect(TEMP_DEF res, KILL cr);
8431   format %{
8432     "cmpxchg_acq $res = $mem, $oldval, $newval\t# (long, weak) if $mem == $oldval then $mem <-- $newval"
8433   %}
8434   ins_encode %{
8435     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8436                Assembler::xword, /*acquire*/ true, /*release*/ true,
8437                /*weak*/ false, $res$$Register);
8438   %}
8439   ins_pipe(pipe_slow);
8440 %}
8441 
8442 
8443 instruct compareAndExchangeNAcq(iRegNNoSp res, indirect mem, iRegN oldval, iRegN newval, rFlagsReg cr) %{
8444   predicate(needs_acquiring_load_exclusive(n));
8445   match(Set res (CompareAndExchangeN mem (Binary oldval newval)));
8446   ins_cost(VOLATILE_REF_COST);
8447   effect(TEMP_DEF res, KILL cr);
8448   format %{
8449     "cmpxchgw_acq $res = $mem, $oldval, $newval\t# (narrow oop, weak) if $mem == $oldval then $mem <-- $newval"
8450   %}
8451   ins_encode %{
8452     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8453                Assembler::word, /*acquire*/ true, /*release*/ true,
8454                /*weak*/ false, $res$$Register);
8455   %}
8456   ins_pipe(pipe_slow);
8457 %}
8458 
8459 instruct compareAndExchangePAcq(iRegPNoSp res, indirect mem, iRegP oldval, iRegP newval, rFlagsReg cr) %{
8460   predicate(needs_acquiring_load_exclusive(n));
8461   match(Set res (CompareAndExchangeP mem (Binary oldval newval)));
8462   ins_cost(VOLATILE_REF_COST);
8463   effect(TEMP_DEF res, KILL cr);
8464   format %{
8465     "cmpxchg_acq $res = $mem, $oldval, $newval\t# (ptr, weak) if $mem == $oldval then $mem <-- $newval"
8466   %}
8467   ins_encode %{
8468     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8469                Assembler::xword, /*acquire*/ true, /*release*/ true,
8470                /*weak*/ false, $res$$Register);
8471   %}
8472   ins_pipe(pipe_slow);
8473 %}
8474 
8475 instruct weakCompareAndSwapB(iRegINoSp res, indirect mem, iRegI oldval, iRegI newval, rFlagsReg cr) %{
8476   match(Set res (WeakCompareAndSwapB mem (Binary oldval newval)));
8477   ins_cost(2 * VOLATILE_REF_COST);
8478   effect(KILL cr);
8479   format %{
8480     "cmpxchgb $res = $mem, $oldval, $newval\t# (byte, weak) if $mem == $oldval then $mem <-- $newval"
8481     "csetw $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8482   %}
8483   ins_encode %{
8484     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8485                Assembler::byte, /*acquire*/ false, /*release*/ true,
8486                /*weak*/ true, noreg);
8487     __ csetw($res$$Register, Assembler::EQ);
8488   %}
8489   ins_pipe(pipe_slow);
8490 %}
8491 
8492 instruct weakCompareAndSwapS(iRegINoSp res, indirect mem, iRegI oldval, iRegI newval, rFlagsReg cr) %{
8493   match(Set res (WeakCompareAndSwapS mem (Binary oldval newval)));
8494   ins_cost(2 * VOLATILE_REF_COST);
8495   effect(KILL cr);
8496   format %{
8497     "cmpxchgs $res = $mem, $oldval, $newval\t# (short, weak) if $mem == $oldval then $mem <-- $newval"
8498     "csetw $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8499   %}
8500   ins_encode %{
8501     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8502                Assembler::halfword, /*acquire*/ false, /*release*/ true,
8503                /*weak*/ true, noreg);
8504     __ csetw($res$$Register, Assembler::EQ);
8505   %}
8506   ins_pipe(pipe_slow);
8507 %}
8508 
8509 instruct weakCompareAndSwapI(iRegINoSp res, indirect mem, iRegI oldval, iRegI newval, rFlagsReg cr) %{
8510   match(Set res (WeakCompareAndSwapI mem (Binary oldval newval)));
8511   ins_cost(2 * VOLATILE_REF_COST);
8512   effect(KILL cr);
8513   format %{
8514     "cmpxchgw $res = $mem, $oldval, $newval\t# (int, weak) if $mem == $oldval then $mem <-- $newval"
8515     "csetw $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8516   %}
8517   ins_encode %{
8518     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8519                Assembler::word, /*acquire*/ false, /*release*/ true,
8520                /*weak*/ true, noreg);
8521     __ csetw($res$$Register, Assembler::EQ);
8522   %}
8523   ins_pipe(pipe_slow);
8524 %}
8525 
8526 instruct weakCompareAndSwapL(iRegINoSp res, indirect mem, iRegL oldval, iRegL newval, rFlagsReg cr) %{
8527   match(Set res (WeakCompareAndSwapL mem (Binary oldval newval)));
8528   ins_cost(2 * VOLATILE_REF_COST);
8529   effect(KILL cr);
8530   format %{
8531     "cmpxchg $res = $mem, $oldval, $newval\t# (long, weak) if $mem == $oldval then $mem <-- $newval"
8532     "csetw $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8533   %}
8534   ins_encode %{
8535     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8536                Assembler::xword, /*acquire*/ false, /*release*/ true,
8537                /*weak*/ true, noreg);
8538     __ csetw($res$$Register, Assembler::EQ);
8539   %}
8540   ins_pipe(pipe_slow);
8541 %}
8542 
8543 instruct weakCompareAndSwapN(iRegINoSp res, indirect mem, iRegN oldval, iRegN newval, rFlagsReg cr) %{
8544   match(Set res (WeakCompareAndSwapN mem (Binary oldval newval)));
8545   ins_cost(2 * VOLATILE_REF_COST);
8546   effect(KILL cr);
8547   format %{
8548     "cmpxchgw $res = $mem, $oldval, $newval\t# (narrow oop, weak) if $mem == $oldval then $mem <-- $newval"
8549     "csetw $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8550   %}
8551   ins_encode %{
8552     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8553                Assembler::word, /*acquire*/ false, /*release*/ true,
8554                /*weak*/ true, noreg);
8555     __ csetw($res$$Register, Assembler::EQ);
8556   %}
8557   ins_pipe(pipe_slow);
8558 %}
8559 
8560 instruct weakCompareAndSwapP(iRegINoSp res, indirect mem, iRegP oldval, iRegP newval, rFlagsReg cr) %{
8561   match(Set res (WeakCompareAndSwapP mem (Binary oldval newval)));
8562   ins_cost(2 * VOLATILE_REF_COST);
8563   effect(KILL cr);
8564   format %{
8565     "cmpxchg $res = $mem, $oldval, $newval\t# (ptr, weak) if $mem == $oldval then $mem <-- $newval"
8566     "csetw $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8567   %}
8568   ins_encode %{
8569     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8570                Assembler::xword, /*acquire*/ false, /*release*/ true,
8571                /*weak*/ true, noreg);
8572     __ csetw($res$$Register, Assembler::EQ);
8573   %}
8574   ins_pipe(pipe_slow);
8575 %}
8576 
8577 instruct weakCompareAndSwapBAcq(iRegINoSp res, indirect mem, iRegI oldval, iRegI newval, rFlagsReg cr) %{
8578   predicate(needs_acquiring_load_exclusive(n));
8579   match(Set res (WeakCompareAndSwapB mem (Binary oldval newval)));
8580   ins_cost(VOLATILE_REF_COST);
8581   effect(KILL cr);
8582   format %{
8583     "cmpxchgb_acq $res = $mem, $oldval, $newval\t# (byte, weak) if $mem == $oldval then $mem <-- $newval"
8584     "csetw $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8585   %}
8586   ins_encode %{
8587     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8588                Assembler::byte, /*acquire*/ true, /*release*/ true,
8589                /*weak*/ true, noreg);
8590     __ csetw($res$$Register, Assembler::EQ);
8591   %}
8592   ins_pipe(pipe_slow);
8593 %}
8594 
8595 instruct weakCompareAndSwapSAcq(iRegINoSp res, indirect mem, iRegI oldval, iRegI newval, rFlagsReg cr) %{
8596   predicate(needs_acquiring_load_exclusive(n));
8597   match(Set res (WeakCompareAndSwapS mem (Binary oldval newval)));
8598   ins_cost(VOLATILE_REF_COST);
8599   effect(KILL cr);
8600   format %{
8601     "cmpxchgs_acq $res = $mem, $oldval, $newval\t# (short, weak) if $mem == $oldval then $mem <-- $newval"
8602     "csetw $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8603   %}
8604   ins_encode %{
8605     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8606                Assembler::halfword, /*acquire*/ true, /*release*/ true,
8607                /*weak*/ true, noreg);
8608     __ csetw($res$$Register, Assembler::EQ);
8609   %}
8610   ins_pipe(pipe_slow);
8611 %}
8612 
8613 instruct weakCompareAndSwapIAcq(iRegINoSp res, indirect mem, iRegI oldval, iRegI newval, rFlagsReg cr) %{
8614   predicate(needs_acquiring_load_exclusive(n));
8615   match(Set res (WeakCompareAndSwapI mem (Binary oldval newval)));
8616   ins_cost(VOLATILE_REF_COST);
8617   effect(KILL cr);
8618   format %{
8619     "cmpxchgw_acq $res = $mem, $oldval, $newval\t# (int, weak) if $mem == $oldval then $mem <-- $newval"
8620     "csetw $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8621   %}
8622   ins_encode %{
8623     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8624                Assembler::word, /*acquire*/ true, /*release*/ true,
8625                /*weak*/ true, noreg);
8626     __ csetw($res$$Register, Assembler::EQ);
8627   %}
8628   ins_pipe(pipe_slow);
8629 %}
8630 
8631 instruct weakCompareAndSwapLAcq(iRegINoSp res, indirect mem, iRegL oldval, iRegL newval, rFlagsReg cr) %{
8632   predicate(needs_acquiring_load_exclusive(n));
8633   match(Set res (WeakCompareAndSwapL mem (Binary oldval newval)));
8634   ins_cost(VOLATILE_REF_COST);
8635   effect(KILL cr);
8636   format %{
8637     "cmpxchg_acq $res = $mem, $oldval, $newval\t# (long, weak) if $mem == $oldval then $mem <-- $newval"
8638     "csetw $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8639   %}
8640   ins_encode %{
8641     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8642                Assembler::xword, /*acquire*/ true, /*release*/ true,
8643                /*weak*/ true, noreg);
8644     __ csetw($res$$Register, Assembler::EQ);
8645   %}
8646   ins_pipe(pipe_slow);
8647 %}
8648 
8649 instruct weakCompareAndSwapNAcq(iRegINoSp res, indirect mem, iRegN oldval, iRegN newval, rFlagsReg cr) %{
8650   predicate(needs_acquiring_load_exclusive(n));
8651   match(Set res (WeakCompareAndSwapN mem (Binary oldval newval)));
8652   ins_cost(VOLATILE_REF_COST);
8653   effect(KILL cr);
8654   format %{
8655     "cmpxchgw_acq $res = $mem, $oldval, $newval\t# (narrow oop, weak) if $mem == $oldval then $mem <-- $newval"
8656     "csetw $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8657   %}
8658   ins_encode %{
8659     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8660                Assembler::word, /*acquire*/ true, /*release*/ true,
8661                /*weak*/ true, noreg);
8662     __ csetw($res$$Register, Assembler::EQ);
8663   %}
8664   ins_pipe(pipe_slow);
8665 %}
8666 
8667 instruct weakCompareAndSwapPAcq(iRegINoSp res, indirect mem, iRegP oldval, iRegP newval, rFlagsReg cr) %{
8668   predicate(needs_acquiring_load_exclusive(n));
8669   match(Set res (WeakCompareAndSwapP mem (Binary oldval newval)));
8670   ins_cost(VOLATILE_REF_COST);
8671   effect(KILL cr);
8672   format %{
8673     "cmpxchg_acq $res = $mem, $oldval, $newval\t# (ptr, weak) if $mem == $oldval then $mem <-- $newval"
8674     "csetw $res, EQ\t# $res <-- (EQ ? 1 : 0)"
8675   %}
8676   ins_encode %{
8677     __ cmpxchg($mem$$Register, $oldval$$Register, $newval$$Register,
8678                Assembler::xword, /*acquire*/ true, /*release*/ true,
8679                /*weak*/ true, noreg);
8680     __ csetw($res$$Register, Assembler::EQ);
8681   %}
8682   ins_pipe(pipe_slow);
8683 %}
8684 
8685 // END This section of the file is automatically generated. Do not edit --------------
8686 // ---------------------------------------------------------------------
8687 
8688 instruct get_and_setI(indirect mem, iRegI newv, iRegINoSp prev) %{
8689   match(Set prev (GetAndSetI mem newv));
8690   ins_cost(2 * VOLATILE_REF_COST);
8691   format %{ "atomic_xchgw  $prev, $newv, [$mem]" %}
8692   ins_encode %{
8693     __ atomic_xchgw($prev$$Register, $newv$$Register, as_Register($mem$$base));
8694   %}
8695   ins_pipe(pipe_serial);
8696 %}
8697 
8698 instruct get_and_setL(indirect mem, iRegL newv, iRegLNoSp prev) %{
8699   match(Set prev (GetAndSetL mem newv));
8700   ins_cost(2 * VOLATILE_REF_COST);
8701   format %{ "atomic_xchg  $prev, $newv, [$mem]" %}
8702   ins_encode %{
8703     __ atomic_xchg($prev$$Register, $newv$$Register, as_Register($mem$$base));
8704   %}
8705   ins_pipe(pipe_serial);
8706 %}
8707 
8708 instruct get_and_setN(indirect mem, iRegN newv, iRegINoSp prev) %{
8709   match(Set prev (GetAndSetN mem newv));
8710   ins_cost(2 * VOLATILE_REF_COST);
8711   format %{ "atomic_xchgw $prev, $newv, [$mem]" %}
8712   ins_encode %{
8713     __ atomic_xchgw($prev$$Register, $newv$$Register, as_Register($mem$$base));
8714   %}
8715   ins_pipe(pipe_serial);
8716 %}
8717 
8718 instruct get_and_setP(indirect mem, iRegP newv, iRegPNoSp prev) %{
8719   match(Set prev (GetAndSetP mem newv));
8720   ins_cost(2 * VOLATILE_REF_COST);
8721   format %{ "atomic_xchg  $prev, $newv, [$mem]" %}
8722   ins_encode %{
8723     __ atomic_xchg($prev$$Register, $newv$$Register, as_Register($mem$$base));
8724   %}
8725   ins_pipe(pipe_serial);
8726 %}
8727 
8728 instruct get_and_setIAcq(indirect mem, iRegI newv, iRegINoSp prev) %{
8729   predicate(needs_acquiring_load_exclusive(n));
8730   match(Set prev (GetAndSetI mem newv));
8731   ins_cost(VOLATILE_REF_COST);
8732   format %{ "atomic_xchgw_acq  $prev, $newv, [$mem]" %}
8733   ins_encode %{
8734     __ atomic_xchgalw($prev$$Register, $newv$$Register, as_Register($mem$$base));
8735   %}
8736   ins_pipe(pipe_serial);
8737 %}
8738 
8739 instruct get_and_setLAcq(indirect mem, iRegL newv, iRegLNoSp prev) %{
8740   predicate(needs_acquiring_load_exclusive(n));
8741   match(Set prev (GetAndSetL mem newv));
8742   ins_cost(VOLATILE_REF_COST);
8743   format %{ "atomic_xchg_acq  $prev, $newv, [$mem]" %}
8744   ins_encode %{
8745     __ atomic_xchgal($prev$$Register, $newv$$Register, as_Register($mem$$base));
8746   %}
8747   ins_pipe(pipe_serial);
8748 %}
8749 
8750 instruct get_and_setNAcq(indirect mem, iRegN newv, iRegINoSp prev) %{
8751   predicate(needs_acquiring_load_exclusive(n));
8752   match(Set prev (GetAndSetN mem newv));
8753   ins_cost(VOLATILE_REF_COST);
8754   format %{ "atomic_xchgw_acq $prev, $newv, [$mem]" %}
8755   ins_encode %{
8756     __ atomic_xchgalw($prev$$Register, $newv$$Register, as_Register($mem$$base));
8757   %}
8758   ins_pipe(pipe_serial);
8759 %}
8760 
8761 instruct get_and_setPAcq(indirect mem, iRegP newv, iRegPNoSp prev) %{
8762   predicate(needs_acquiring_load_exclusive(n));
8763   match(Set prev (GetAndSetP mem newv));
8764   ins_cost(VOLATILE_REF_COST);
8765   format %{ "atomic_xchg_acq  $prev, $newv, [$mem]" %}
8766   ins_encode %{
8767     __ atomic_xchgal($prev$$Register, $newv$$Register, as_Register($mem$$base));
8768   %}
8769   ins_pipe(pipe_serial);
8770 %}
8771 
8772 
8773 instruct get_and_addL(indirect mem, iRegLNoSp newval, iRegL incr) %{
8774   match(Set newval (GetAndAddL mem incr));
8775   ins_cost(2 * VOLATILE_REF_COST + 1);
8776   format %{ "get_and_addL $newval, [$mem], $incr" %}
8777   ins_encode %{
8778     __ atomic_add($newval$$Register, $incr$$Register, as_Register($mem$$base));
8779   %}
8780   ins_pipe(pipe_serial);
8781 %}
8782 
8783 instruct get_and_addL_no_res(indirect mem, Universe dummy, iRegL incr) %{
8784   predicate(n->as_LoadStore()->result_not_used());
8785   match(Set dummy (GetAndAddL mem incr));
8786   ins_cost(2 * VOLATILE_REF_COST);
8787   format %{ "get_and_addL [$mem], $incr" %}
8788   ins_encode %{
8789     __ atomic_add(noreg, $incr$$Register, as_Register($mem$$base));
8790   %}
8791   ins_pipe(pipe_serial);
8792 %}
8793 
8794 instruct get_and_addLi(indirect mem, iRegLNoSp newval, immLAddSub incr) %{
8795   match(Set newval (GetAndAddL mem incr));
8796   ins_cost(2 * VOLATILE_REF_COST + 1);
8797   format %{ "get_and_addL $newval, [$mem], $incr" %}
8798   ins_encode %{
8799     __ atomic_add($newval$$Register, $incr$$constant, as_Register($mem$$base));
8800   %}
8801   ins_pipe(pipe_serial);
8802 %}
8803 
8804 instruct get_and_addLi_no_res(indirect mem, Universe dummy, immLAddSub incr) %{
8805   predicate(n->as_LoadStore()->result_not_used());
8806   match(Set dummy (GetAndAddL mem incr));
8807   ins_cost(2 * VOLATILE_REF_COST);
8808   format %{ "get_and_addL [$mem], $incr" %}
8809   ins_encode %{
8810     __ atomic_add(noreg, $incr$$constant, as_Register($mem$$base));
8811   %}
8812   ins_pipe(pipe_serial);
8813 %}
8814 
8815 instruct get_and_addI(indirect mem, iRegINoSp newval, iRegIorL2I incr) %{
8816   match(Set newval (GetAndAddI mem incr));
8817   ins_cost(2 * VOLATILE_REF_COST + 1);
8818   format %{ "get_and_addI $newval, [$mem], $incr" %}
8819   ins_encode %{
8820     __ atomic_addw($newval$$Register, $incr$$Register, as_Register($mem$$base));
8821   %}
8822   ins_pipe(pipe_serial);
8823 %}
8824 
8825 instruct get_and_addI_no_res(indirect mem, Universe dummy, iRegIorL2I incr) %{
8826   predicate(n->as_LoadStore()->result_not_used());
8827   match(Set dummy (GetAndAddI mem incr));
8828   ins_cost(2 * VOLATILE_REF_COST);
8829   format %{ "get_and_addI [$mem], $incr" %}
8830   ins_encode %{
8831     __ atomic_addw(noreg, $incr$$Register, as_Register($mem$$base));
8832   %}
8833   ins_pipe(pipe_serial);
8834 %}
8835 
8836 instruct get_and_addIi(indirect mem, iRegINoSp newval, immIAddSub incr) %{
8837   match(Set newval (GetAndAddI mem incr));
8838   ins_cost(2 * VOLATILE_REF_COST + 1);
8839   format %{ "get_and_addI $newval, [$mem], $incr" %}
8840   ins_encode %{
8841     __ atomic_addw($newval$$Register, $incr$$constant, as_Register($mem$$base));
8842   %}
8843   ins_pipe(pipe_serial);
8844 %}
8845 
8846 instruct get_and_addIi_no_res(indirect mem, Universe dummy, immIAddSub incr) %{
8847   predicate(n->as_LoadStore()->result_not_used());
8848   match(Set dummy (GetAndAddI mem incr));
8849   ins_cost(2 * VOLATILE_REF_COST);
8850   format %{ "get_and_addI [$mem], $incr" %}
8851   ins_encode %{
8852     __ atomic_addw(noreg, $incr$$constant, as_Register($mem$$base));
8853   %}
8854   ins_pipe(pipe_serial);
8855 %}
8856 
8857 instruct get_and_addLAcq(indirect mem, iRegLNoSp newval, iRegL incr) %{
8858   predicate(needs_acquiring_load_exclusive(n));
8859   match(Set newval (GetAndAddL mem incr));
8860   ins_cost(VOLATILE_REF_COST + 1);
8861   format %{ "get_and_addL_acq $newval, [$mem], $incr" %}
8862   ins_encode %{
8863     __ atomic_addal($newval$$Register, $incr$$Register, as_Register($mem$$base));
8864   %}
8865   ins_pipe(pipe_serial);
8866 %}
8867 
8868 instruct get_and_addL_no_resAcq(indirect mem, Universe dummy, iRegL incr) %{
8869   predicate(n->as_LoadStore()->result_not_used() && needs_acquiring_load_exclusive(n));
8870   match(Set dummy (GetAndAddL mem incr));
8871   ins_cost(VOLATILE_REF_COST);
8872   format %{ "get_and_addL_acq [$mem], $incr" %}
8873   ins_encode %{
8874     __ atomic_addal(noreg, $incr$$Register, as_Register($mem$$base));
8875   %}
8876   ins_pipe(pipe_serial);
8877 %}
8878 
8879 instruct get_and_addLiAcq(indirect mem, iRegLNoSp newval, immLAddSub incr) %{
8880   predicate(needs_acquiring_load_exclusive(n));
8881   match(Set newval (GetAndAddL mem incr));
8882   ins_cost(VOLATILE_REF_COST + 1);
8883   format %{ "get_and_addL_acq $newval, [$mem], $incr" %}
8884   ins_encode %{
8885     __ atomic_addal($newval$$Register, $incr$$constant, as_Register($mem$$base));
8886   %}
8887   ins_pipe(pipe_serial);
8888 %}
8889 
8890 instruct get_and_addLi_no_resAcq(indirect mem, Universe dummy, immLAddSub incr) %{
8891   predicate(n->as_LoadStore()->result_not_used() && needs_acquiring_load_exclusive(n));
8892   match(Set dummy (GetAndAddL mem incr));
8893   ins_cost(VOLATILE_REF_COST);
8894   format %{ "get_and_addL_acq [$mem], $incr" %}
8895   ins_encode %{
8896     __ atomic_addal(noreg, $incr$$constant, as_Register($mem$$base));
8897   %}
8898   ins_pipe(pipe_serial);
8899 %}
8900 
8901 instruct get_and_addIAcq(indirect mem, iRegINoSp newval, iRegIorL2I incr) %{
8902   predicate(needs_acquiring_load_exclusive(n));
8903   match(Set newval (GetAndAddI mem incr));
8904   ins_cost(VOLATILE_REF_COST + 1);
8905   format %{ "get_and_addI_acq $newval, [$mem], $incr" %}
8906   ins_encode %{
8907     __ atomic_addalw($newval$$Register, $incr$$Register, as_Register($mem$$base));
8908   %}
8909   ins_pipe(pipe_serial);
8910 %}
8911 
8912 instruct get_and_addI_no_resAcq(indirect mem, Universe dummy, iRegIorL2I incr) %{
8913   predicate(n->as_LoadStore()->result_not_used() && needs_acquiring_load_exclusive(n));
8914   match(Set dummy (GetAndAddI mem incr));
8915   ins_cost(VOLATILE_REF_COST);
8916   format %{ "get_and_addI_acq [$mem], $incr" %}
8917   ins_encode %{
8918     __ atomic_addalw(noreg, $incr$$Register, as_Register($mem$$base));
8919   %}
8920   ins_pipe(pipe_serial);
8921 %}
8922 
8923 instruct get_and_addIiAcq(indirect mem, iRegINoSp newval, immIAddSub incr) %{
8924   predicate(needs_acquiring_load_exclusive(n));
8925   match(Set newval (GetAndAddI mem incr));
8926   ins_cost(VOLATILE_REF_COST + 1);
8927   format %{ "get_and_addI_acq $newval, [$mem], $incr" %}
8928   ins_encode %{
8929     __ atomic_addalw($newval$$Register, $incr$$constant, as_Register($mem$$base));
8930   %}
8931   ins_pipe(pipe_serial);
8932 %}
8933 
8934 instruct get_and_addIi_no_resAcq(indirect mem, Universe dummy, immIAddSub incr) %{
8935   predicate(n->as_LoadStore()->result_not_used() && needs_acquiring_load_exclusive(n));
8936   match(Set dummy (GetAndAddI mem incr));
8937   ins_cost(VOLATILE_REF_COST);
8938   format %{ "get_and_addI_acq [$mem], $incr" %}
8939   ins_encode %{
8940     __ atomic_addalw(noreg, $incr$$constant, as_Register($mem$$base));
8941   %}
8942   ins_pipe(pipe_serial);
8943 %}
8944 
8945 // Manifest a CmpL result in an integer register.
8946 // (src1 < src2) ? -1 : ((src1 > src2) ? 1 : 0)
8947 instruct cmpL3_reg_reg(iRegINoSp dst, iRegL src1, iRegL src2, rFlagsReg flags)
8948 %{
8949   match(Set dst (CmpL3 src1 src2));
8950   effect(KILL flags);
8951 
8952   ins_cost(INSN_COST * 6);
8953   format %{
8954       "cmp $src1, $src2"
8955       "csetw $dst, ne"
8956       "cnegw $dst, lt"
8957   %}
8958   // format %{ "CmpL3 $dst, $src1, $src2" %}
8959   ins_encode %{
8960     __ cmp($src1$$Register, $src2$$Register);
8961     __ csetw($dst$$Register, Assembler::NE);
8962     __ cnegw($dst$$Register, $dst$$Register, Assembler::LT);
8963   %}
8964 
8965   ins_pipe(pipe_class_default);
8966 %}
8967 
8968 instruct cmpL3_reg_imm(iRegINoSp dst, iRegL src1, immLAddSub src2, rFlagsReg flags)
8969 %{
8970   match(Set dst (CmpL3 src1 src2));
8971   effect(KILL flags);
8972 
8973   ins_cost(INSN_COST * 6);
8974   format %{
8975       "cmp $src1, $src2"
8976       "csetw $dst, ne"
8977       "cnegw $dst, lt"
8978   %}
8979   ins_encode %{
8980     int32_t con = (int32_t)$src2$$constant;
8981      if (con < 0) {
8982       __ adds(zr, $src1$$Register, -con);
8983     } else {
8984       __ subs(zr, $src1$$Register, con);
8985     }
8986     __ csetw($dst$$Register, Assembler::NE);
8987     __ cnegw($dst$$Register, $dst$$Register, Assembler::LT);
8988   %}
8989 
8990   ins_pipe(pipe_class_default);
8991 %}
8992 
8993 // ============================================================================
8994 // Conditional Move Instructions
8995 
8996 // n.b. we have identical rules for both a signed compare op (cmpOp)
8997 // and an unsigned compare op (cmpOpU). it would be nice if we could
8998 // define an op class which merged both inputs and use it to type the
8999 // argument to a single rule. unfortunatelyt his fails because the
9000 // opclass does not live up to the COND_INTER interface of its
9001 // component operands. When the generic code tries to negate the
9002 // operand it ends up running the generci Machoper::negate method
9003 // which throws a ShouldNotHappen. So, we have to provide two flavours
9004 // of each rule, one for a cmpOp and a second for a cmpOpU (sigh).
9005 
9006 instruct cmovI_reg_reg(cmpOp cmp, rFlagsReg cr, iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2) %{
9007   match(Set dst (CMoveI (Binary cmp cr) (Binary src1 src2)));
9008 
9009   ins_cost(INSN_COST * 2);
9010   format %{ "cselw $dst, $src2, $src1 $cmp\t# signed, int"  %}
9011 
9012   ins_encode %{
9013     __ cselw(as_Register($dst$$reg),
9014              as_Register($src2$$reg),
9015              as_Register($src1$$reg),
9016              (Assembler::Condition)$cmp$$cmpcode);
9017   %}
9018 
9019   ins_pipe(icond_reg_reg);
9020 %}
9021 
9022 instruct cmovUI_reg_reg(cmpOpU cmp, rFlagsRegU cr, iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2) %{
9023   match(Set dst (CMoveI (Binary cmp cr) (Binary src1 src2)));
9024 
9025   ins_cost(INSN_COST * 2);
9026   format %{ "cselw $dst, $src2, $src1 $cmp\t# unsigned, int"  %}
9027 
9028   ins_encode %{
9029     __ cselw(as_Register($dst$$reg),
9030              as_Register($src2$$reg),
9031              as_Register($src1$$reg),
9032              (Assembler::Condition)$cmp$$cmpcode);
9033   %}
9034 
9035   ins_pipe(icond_reg_reg);
9036 %}
9037 
9038 // special cases where one arg is zero
9039 
9040 // n.b. this is selected in preference to the rule above because it
9041 // avoids loading constant 0 into a source register
9042 
9043 // TODO
9044 // we ought only to be able to cull one of these variants as the ideal
9045 // transforms ought always to order the zero consistently (to left/right?)
9046 
9047 instruct cmovI_zero_reg(cmpOp cmp, rFlagsReg cr, iRegINoSp dst, immI0 zero, iRegIorL2I src) %{
9048   match(Set dst (CMoveI (Binary cmp cr) (Binary zero src)));
9049 
9050   ins_cost(INSN_COST * 2);
9051   format %{ "cselw $dst, $src, zr $cmp\t# signed, int"  %}
9052 
9053   ins_encode %{
9054     __ cselw(as_Register($dst$$reg),
9055              as_Register($src$$reg),
9056              zr,
9057              (Assembler::Condition)$cmp$$cmpcode);
9058   %}
9059 
9060   ins_pipe(icond_reg);
9061 %}
9062 
9063 instruct cmovUI_zero_reg(cmpOpU cmp, rFlagsRegU cr, iRegINoSp dst, immI0 zero, iRegIorL2I src) %{
9064   match(Set dst (CMoveI (Binary cmp cr) (Binary zero src)));
9065 
9066   ins_cost(INSN_COST * 2);
9067   format %{ "cselw $dst, $src, zr $cmp\t# unsigned, int"  %}
9068 
9069   ins_encode %{
9070     __ cselw(as_Register($dst$$reg),
9071              as_Register($src$$reg),
9072              zr,
9073              (Assembler::Condition)$cmp$$cmpcode);
9074   %}
9075 
9076   ins_pipe(icond_reg);
9077 %}
9078 
9079 instruct cmovI_reg_zero(cmpOp cmp, rFlagsReg cr, iRegINoSp dst, iRegIorL2I src, immI0 zero) %{
9080   match(Set dst (CMoveI (Binary cmp cr) (Binary src zero)));
9081 
9082   ins_cost(INSN_COST * 2);
9083   format %{ "cselw $dst, zr, $src $cmp\t# signed, int"  %}
9084 
9085   ins_encode %{
9086     __ cselw(as_Register($dst$$reg),
9087              zr,
9088              as_Register($src$$reg),
9089              (Assembler::Condition)$cmp$$cmpcode);
9090   %}
9091 
9092   ins_pipe(icond_reg);
9093 %}
9094 
9095 instruct cmovUI_reg_zero(cmpOpU cmp, rFlagsRegU cr, iRegINoSp dst, iRegIorL2I src, immI0 zero) %{
9096   match(Set dst (CMoveI (Binary cmp cr) (Binary src zero)));
9097 
9098   ins_cost(INSN_COST * 2);
9099   format %{ "cselw $dst, zr, $src $cmp\t# unsigned, int"  %}
9100 
9101   ins_encode %{
9102     __ cselw(as_Register($dst$$reg),
9103              zr,
9104              as_Register($src$$reg),
9105              (Assembler::Condition)$cmp$$cmpcode);
9106   %}
9107 
9108   ins_pipe(icond_reg);
9109 %}
9110 
9111 // special case for creating a boolean 0 or 1
9112 
9113 // n.b. this is selected in preference to the rule above because it
9114 // avoids loading constants 0 and 1 into a source register
9115 
9116 instruct cmovI_reg_zero_one(cmpOp cmp, rFlagsReg cr, iRegINoSp dst, immI0 zero, immI_1 one) %{
9117   match(Set dst (CMoveI (Binary cmp cr) (Binary one zero)));
9118 
9119   ins_cost(INSN_COST * 2);
9120   format %{ "csincw $dst, zr, zr $cmp\t# signed, int"  %}
9121 
9122   ins_encode %{
9123     // equivalently
9124     // cset(as_Register($dst$$reg),
9125     //      negate_condition((Assembler::Condition)$cmp$$cmpcode));
9126     __ csincw(as_Register($dst$$reg),
9127              zr,
9128              zr,
9129              (Assembler::Condition)$cmp$$cmpcode);
9130   %}
9131 
9132   ins_pipe(icond_none);
9133 %}
9134 
9135 instruct cmovUI_reg_zero_one(cmpOpU cmp, rFlagsRegU cr, iRegINoSp dst, immI0 zero, immI_1 one) %{
9136   match(Set dst (CMoveI (Binary cmp cr) (Binary one zero)));
9137 
9138   ins_cost(INSN_COST * 2);
9139   format %{ "csincw $dst, zr, zr $cmp\t# unsigned, int"  %}
9140 
9141   ins_encode %{
9142     // equivalently
9143     // cset(as_Register($dst$$reg),
9144     //      negate_condition((Assembler::Condition)$cmp$$cmpcode));
9145     __ csincw(as_Register($dst$$reg),
9146              zr,
9147              zr,
9148              (Assembler::Condition)$cmp$$cmpcode);
9149   %}
9150 
9151   ins_pipe(icond_none);
9152 %}
9153 
9154 instruct cmovL_reg_reg(cmpOp cmp, rFlagsReg cr, iRegLNoSp dst, iRegL src1, iRegL src2) %{
9155   match(Set dst (CMoveL (Binary cmp cr) (Binary src1 src2)));
9156 
9157   ins_cost(INSN_COST * 2);
9158   format %{ "csel $dst, $src2, $src1 $cmp\t# signed, long"  %}
9159 
9160   ins_encode %{
9161     __ csel(as_Register($dst$$reg),
9162             as_Register($src2$$reg),
9163             as_Register($src1$$reg),
9164             (Assembler::Condition)$cmp$$cmpcode);
9165   %}
9166 
9167   ins_pipe(icond_reg_reg);
9168 %}
9169 
9170 instruct cmovUL_reg_reg(cmpOpU cmp, rFlagsRegU cr, iRegLNoSp dst, iRegL src1, iRegL src2) %{
9171   match(Set dst (CMoveL (Binary cmp cr) (Binary src1 src2)));
9172 
9173   ins_cost(INSN_COST * 2);
9174   format %{ "csel $dst, $src2, $src1 $cmp\t# unsigned, long"  %}
9175 
9176   ins_encode %{
9177     __ csel(as_Register($dst$$reg),
9178             as_Register($src2$$reg),
9179             as_Register($src1$$reg),
9180             (Assembler::Condition)$cmp$$cmpcode);
9181   %}
9182 
9183   ins_pipe(icond_reg_reg);
9184 %}
9185 
9186 // special cases where one arg is zero
9187 
9188 instruct cmovL_reg_zero(cmpOp cmp, rFlagsReg cr, iRegLNoSp dst, iRegL src, immL0 zero) %{
9189   match(Set dst (CMoveL (Binary cmp cr) (Binary src zero)));
9190 
9191   ins_cost(INSN_COST * 2);
9192   format %{ "csel $dst, zr, $src $cmp\t# signed, long"  %}
9193 
9194   ins_encode %{
9195     __ csel(as_Register($dst$$reg),
9196             zr,
9197             as_Register($src$$reg),
9198             (Assembler::Condition)$cmp$$cmpcode);
9199   %}
9200 
9201   ins_pipe(icond_reg);
9202 %}
9203 
9204 instruct cmovUL_reg_zero(cmpOpU cmp, rFlagsRegU cr, iRegLNoSp dst, iRegL src, immL0 zero) %{
9205   match(Set dst (CMoveL (Binary cmp cr) (Binary src zero)));
9206 
9207   ins_cost(INSN_COST * 2);
9208   format %{ "csel $dst, zr, $src $cmp\t# unsigned, long"  %}
9209 
9210   ins_encode %{
9211     __ csel(as_Register($dst$$reg),
9212             zr,
9213             as_Register($src$$reg),
9214             (Assembler::Condition)$cmp$$cmpcode);
9215   %}
9216 
9217   ins_pipe(icond_reg);
9218 %}
9219 
9220 instruct cmovL_zero_reg(cmpOp cmp, rFlagsReg cr, iRegLNoSp dst, immL0 zero, iRegL src) %{
9221   match(Set dst (CMoveL (Binary cmp cr) (Binary zero src)));
9222 
9223   ins_cost(INSN_COST * 2);
9224   format %{ "csel $dst, $src, zr $cmp\t# signed, long"  %}
9225 
9226   ins_encode %{
9227     __ csel(as_Register($dst$$reg),
9228             as_Register($src$$reg),
9229             zr,
9230             (Assembler::Condition)$cmp$$cmpcode);
9231   %}
9232 
9233   ins_pipe(icond_reg);
9234 %}
9235 
9236 instruct cmovUL_zero_reg(cmpOpU cmp, rFlagsRegU cr, iRegLNoSp dst, immL0 zero, iRegL src) %{
9237   match(Set dst (CMoveL (Binary cmp cr) (Binary zero src)));
9238 
9239   ins_cost(INSN_COST * 2);
9240   format %{ "csel $dst, $src, zr $cmp\t# unsigned, long"  %}
9241 
9242   ins_encode %{
9243     __ csel(as_Register($dst$$reg),
9244             as_Register($src$$reg),
9245             zr,
9246             (Assembler::Condition)$cmp$$cmpcode);
9247   %}
9248 
9249   ins_pipe(icond_reg);
9250 %}
9251 
9252 instruct cmovP_reg_reg(cmpOp cmp, rFlagsReg cr, iRegPNoSp dst, iRegP src1, iRegP src2) %{
9253   match(Set dst (CMoveP (Binary cmp cr) (Binary src1 src2)));
9254 
9255   ins_cost(INSN_COST * 2);
9256   format %{ "csel $dst, $src2, $src1 $cmp\t# signed, ptr"  %}
9257 
9258   ins_encode %{
9259     __ csel(as_Register($dst$$reg),
9260             as_Register($src2$$reg),
9261             as_Register($src1$$reg),
9262             (Assembler::Condition)$cmp$$cmpcode);
9263   %}
9264 
9265   ins_pipe(icond_reg_reg);
9266 %}
9267 
9268 instruct cmovUP_reg_reg(cmpOpU cmp, rFlagsRegU cr, iRegPNoSp dst, iRegP src1, iRegP src2) %{
9269   match(Set dst (CMoveP (Binary cmp cr) (Binary src1 src2)));
9270 
9271   ins_cost(INSN_COST * 2);
9272   format %{ "csel $dst, $src2, $src1 $cmp\t# unsigned, ptr"  %}
9273 
9274   ins_encode %{
9275     __ csel(as_Register($dst$$reg),
9276             as_Register($src2$$reg),
9277             as_Register($src1$$reg),
9278             (Assembler::Condition)$cmp$$cmpcode);
9279   %}
9280 
9281   ins_pipe(icond_reg_reg);
9282 %}
9283 
9284 // special cases where one arg is zero
9285 
9286 instruct cmovP_reg_zero(cmpOp cmp, rFlagsReg cr, iRegPNoSp dst, iRegP src, immP0 zero) %{
9287   match(Set dst (CMoveP (Binary cmp cr) (Binary src zero)));
9288 
9289   ins_cost(INSN_COST * 2);
9290   format %{ "csel $dst, zr, $src $cmp\t# signed, ptr"  %}
9291 
9292   ins_encode %{
9293     __ csel(as_Register($dst$$reg),
9294             zr,
9295             as_Register($src$$reg),
9296             (Assembler::Condition)$cmp$$cmpcode);
9297   %}
9298 
9299   ins_pipe(icond_reg);
9300 %}
9301 
9302 instruct cmovUP_reg_zero(cmpOpU cmp, rFlagsRegU cr, iRegPNoSp dst, iRegP src, immP0 zero) %{
9303   match(Set dst (CMoveP (Binary cmp cr) (Binary src zero)));
9304 
9305   ins_cost(INSN_COST * 2);
9306   format %{ "csel $dst, zr, $src $cmp\t# unsigned, ptr"  %}
9307 
9308   ins_encode %{
9309     __ csel(as_Register($dst$$reg),
9310             zr,
9311             as_Register($src$$reg),
9312             (Assembler::Condition)$cmp$$cmpcode);
9313   %}
9314 
9315   ins_pipe(icond_reg);
9316 %}
9317 
9318 instruct cmovP_zero_reg(cmpOp cmp, rFlagsReg cr, iRegPNoSp dst, immP0 zero, iRegP src) %{
9319   match(Set dst (CMoveP (Binary cmp cr) (Binary zero src)));
9320 
9321   ins_cost(INSN_COST * 2);
9322   format %{ "csel $dst, $src, zr $cmp\t# signed, ptr"  %}
9323 
9324   ins_encode %{
9325     __ csel(as_Register($dst$$reg),
9326             as_Register($src$$reg),
9327             zr,
9328             (Assembler::Condition)$cmp$$cmpcode);
9329   %}
9330 
9331   ins_pipe(icond_reg);
9332 %}
9333 
9334 instruct cmovUP_zero_reg(cmpOpU cmp, rFlagsRegU cr, iRegPNoSp dst, immP0 zero, iRegP src) %{
9335   match(Set dst (CMoveP (Binary cmp cr) (Binary zero src)));
9336 
9337   ins_cost(INSN_COST * 2);
9338   format %{ "csel $dst, $src, zr $cmp\t# unsigned, ptr"  %}
9339 
9340   ins_encode %{
9341     __ csel(as_Register($dst$$reg),
9342             as_Register($src$$reg),
9343             zr,
9344             (Assembler::Condition)$cmp$$cmpcode);
9345   %}
9346 
9347   ins_pipe(icond_reg);
9348 %}
9349 
9350 instruct cmovN_reg_reg(cmpOp cmp, rFlagsReg cr, iRegNNoSp dst, iRegN src1, iRegN src2) %{
9351   match(Set dst (CMoveN (Binary cmp cr) (Binary src1 src2)));
9352 
9353   ins_cost(INSN_COST * 2);
9354   format %{ "cselw $dst, $src2, $src1 $cmp\t# signed, compressed ptr"  %}
9355 
9356   ins_encode %{
9357     __ cselw(as_Register($dst$$reg),
9358              as_Register($src2$$reg),
9359              as_Register($src1$$reg),
9360              (Assembler::Condition)$cmp$$cmpcode);
9361   %}
9362 
9363   ins_pipe(icond_reg_reg);
9364 %}
9365 
9366 instruct cmovUN_reg_reg(cmpOpU cmp, rFlagsRegU cr, iRegNNoSp dst, iRegN src1, iRegN src2) %{
9367   match(Set dst (CMoveN (Binary cmp cr) (Binary src1 src2)));
9368 
9369   ins_cost(INSN_COST * 2);
9370   format %{ "cselw $dst, $src2, $src1 $cmp\t# signed, compressed ptr"  %}
9371 
9372   ins_encode %{
9373     __ cselw(as_Register($dst$$reg),
9374              as_Register($src2$$reg),
9375              as_Register($src1$$reg),
9376              (Assembler::Condition)$cmp$$cmpcode);
9377   %}
9378 
9379   ins_pipe(icond_reg_reg);
9380 %}
9381 
9382 // special cases where one arg is zero
9383 
9384 instruct cmovN_reg_zero(cmpOp cmp, rFlagsReg cr, iRegNNoSp dst, iRegN src, immN0 zero) %{
9385   match(Set dst (CMoveN (Binary cmp cr) (Binary src zero)));
9386 
9387   ins_cost(INSN_COST * 2);
9388   format %{ "cselw $dst, zr, $src $cmp\t# signed, compressed ptr"  %}
9389 
9390   ins_encode %{
9391     __ cselw(as_Register($dst$$reg),
9392              zr,
9393              as_Register($src$$reg),
9394              (Assembler::Condition)$cmp$$cmpcode);
9395   %}
9396 
9397   ins_pipe(icond_reg);
9398 %}
9399 
9400 instruct cmovUN_reg_zero(cmpOpU cmp, rFlagsRegU cr, iRegNNoSp dst, iRegN src, immN0 zero) %{
9401   match(Set dst (CMoveN (Binary cmp cr) (Binary src zero)));
9402 
9403   ins_cost(INSN_COST * 2);
9404   format %{ "cselw $dst, zr, $src $cmp\t# unsigned, compressed ptr"  %}
9405 
9406   ins_encode %{
9407     __ cselw(as_Register($dst$$reg),
9408              zr,
9409              as_Register($src$$reg),
9410              (Assembler::Condition)$cmp$$cmpcode);
9411   %}
9412 
9413   ins_pipe(icond_reg);
9414 %}
9415 
9416 instruct cmovN_zero_reg(cmpOp cmp, rFlagsReg cr, iRegNNoSp dst, immN0 zero, iRegN src) %{
9417   match(Set dst (CMoveN (Binary cmp cr) (Binary zero src)));
9418 
9419   ins_cost(INSN_COST * 2);
9420   format %{ "cselw $dst, $src, zr $cmp\t# signed, compressed ptr"  %}
9421 
9422   ins_encode %{
9423     __ cselw(as_Register($dst$$reg),
9424              as_Register($src$$reg),
9425              zr,
9426              (Assembler::Condition)$cmp$$cmpcode);
9427   %}
9428 
9429   ins_pipe(icond_reg);
9430 %}
9431 
9432 instruct cmovUN_zero_reg(cmpOpU cmp, rFlagsRegU cr, iRegNNoSp dst, immN0 zero, iRegN src) %{
9433   match(Set dst (CMoveN (Binary cmp cr) (Binary zero src)));
9434 
9435   ins_cost(INSN_COST * 2);
9436   format %{ "cselw $dst, $src, zr $cmp\t# unsigned, compressed ptr"  %}
9437 
9438   ins_encode %{
9439     __ cselw(as_Register($dst$$reg),
9440              as_Register($src$$reg),
9441              zr,
9442              (Assembler::Condition)$cmp$$cmpcode);
9443   %}
9444 
9445   ins_pipe(icond_reg);
9446 %}
9447 
9448 instruct cmovF_reg(cmpOp cmp, rFlagsReg cr, vRegF dst, vRegF src1,  vRegF src2)
9449 %{
9450   match(Set dst (CMoveF (Binary cmp cr) (Binary src1 src2)));
9451 
9452   ins_cost(INSN_COST * 3);
9453 
9454   format %{ "fcsels $dst, $src1, $src2, $cmp\t# signed cmove float\n\t" %}
9455   ins_encode %{
9456     Assembler::Condition cond = (Assembler::Condition)$cmp$$cmpcode;
9457     __ fcsels(as_FloatRegister($dst$$reg),
9458               as_FloatRegister($src2$$reg),
9459               as_FloatRegister($src1$$reg),
9460               cond);
9461   %}
9462 
9463   ins_pipe(fp_cond_reg_reg_s);
9464 %}
9465 
9466 instruct cmovUF_reg(cmpOpU cmp, rFlagsRegU cr, vRegF dst, vRegF src1,  vRegF src2)
9467 %{
9468   match(Set dst (CMoveF (Binary cmp cr) (Binary src1 src2)));
9469 
9470   ins_cost(INSN_COST * 3);
9471 
9472   format %{ "fcsels $dst, $src1, $src2, $cmp\t# unsigned cmove float\n\t" %}
9473   ins_encode %{
9474     Assembler::Condition cond = (Assembler::Condition)$cmp$$cmpcode;
9475     __ fcsels(as_FloatRegister($dst$$reg),
9476               as_FloatRegister($src2$$reg),
9477               as_FloatRegister($src1$$reg),
9478               cond);
9479   %}
9480 
9481   ins_pipe(fp_cond_reg_reg_s);
9482 %}
9483 
9484 instruct cmovD_reg(cmpOp cmp, rFlagsReg cr, vRegD dst, vRegD src1,  vRegD src2)
9485 %{
9486   match(Set dst (CMoveD (Binary cmp cr) (Binary src1 src2)));
9487 
9488   ins_cost(INSN_COST * 3);
9489 
9490   format %{ "fcseld $dst, $src1, $src2, $cmp\t# signed cmove float\n\t" %}
9491   ins_encode %{
9492     Assembler::Condition cond = (Assembler::Condition)$cmp$$cmpcode;
9493     __ fcseld(as_FloatRegister($dst$$reg),
9494               as_FloatRegister($src2$$reg),
9495               as_FloatRegister($src1$$reg),
9496               cond);
9497   %}
9498 
9499   ins_pipe(fp_cond_reg_reg_d);
9500 %}
9501 
9502 instruct cmovUD_reg(cmpOpU cmp, rFlagsRegU cr, vRegD dst, vRegD src1,  vRegD src2)
9503 %{
9504   match(Set dst (CMoveD (Binary cmp cr) (Binary src1 src2)));
9505 
9506   ins_cost(INSN_COST * 3);
9507 
9508   format %{ "fcseld $dst, $src1, $src2, $cmp\t# unsigned cmove float\n\t" %}
9509   ins_encode %{
9510     Assembler::Condition cond = (Assembler::Condition)$cmp$$cmpcode;
9511     __ fcseld(as_FloatRegister($dst$$reg),
9512               as_FloatRegister($src2$$reg),
9513               as_FloatRegister($src1$$reg),
9514               cond);
9515   %}
9516 
9517   ins_pipe(fp_cond_reg_reg_d);
9518 %}
9519 
9520 // ============================================================================
9521 // Arithmetic Instructions
9522 //
9523 
9524 // Integer Addition
9525 
9526 // TODO
9527 // these currently employ operations which do not set CR and hence are
9528 // not flagged as killing CR but we would like to isolate the cases
9529 // where we want to set flags from those where we don't. need to work
9530 // out how to do that.
9531 
9532 instruct addI_reg_reg(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2) %{
9533   match(Set dst (AddI src1 src2));
9534 
9535   ins_cost(INSN_COST);
9536   format %{ "addw  $dst, $src1, $src2" %}
9537 
9538   ins_encode %{
9539     __ addw(as_Register($dst$$reg),
9540             as_Register($src1$$reg),
9541             as_Register($src2$$reg));
9542   %}
9543 
9544   ins_pipe(ialu_reg_reg);
9545 %}
9546 
9547 instruct addI_reg_imm(iRegINoSp dst, iRegIorL2I src1, immIAddSub src2) %{
9548   match(Set dst (AddI src1 src2));
9549 
9550   ins_cost(INSN_COST);
9551   format %{ "addw $dst, $src1, $src2" %}
9552 
9553   // use opcode to indicate that this is an add not a sub
9554   opcode(0x0);
9555 
9556   ins_encode(aarch64_enc_addsubw_imm(dst, src1, src2));
9557 
9558   ins_pipe(ialu_reg_imm);
9559 %}
9560 
9561 instruct addI_reg_imm_i2l(iRegINoSp dst, iRegL src1, immIAddSub src2) %{
9562   match(Set dst (AddI (ConvL2I src1) src2));
9563 
9564   ins_cost(INSN_COST);
9565   format %{ "addw $dst, $src1, $src2" %}
9566 
9567   // use opcode to indicate that this is an add not a sub
9568   opcode(0x0);
9569 
9570   ins_encode(aarch64_enc_addsubw_imm(dst, src1, src2));
9571 
9572   ins_pipe(ialu_reg_imm);
9573 %}
9574 
9575 // Pointer Addition
9576 instruct addP_reg_reg(iRegPNoSp dst, iRegP src1, iRegL src2) %{
9577   match(Set dst (AddP src1 src2));
9578 
9579   ins_cost(INSN_COST);
9580   format %{ "add $dst, $src1, $src2\t# ptr" %}
9581 
9582   ins_encode %{
9583     __ add(as_Register($dst$$reg),
9584            as_Register($src1$$reg),
9585            as_Register($src2$$reg));
9586   %}
9587 
9588   ins_pipe(ialu_reg_reg);
9589 %}
9590 
9591 instruct addP_reg_reg_ext(iRegPNoSp dst, iRegP src1, iRegIorL2I src2) %{
9592   match(Set dst (AddP src1 (ConvI2L src2)));
9593 
9594   ins_cost(1.9 * INSN_COST);
9595   format %{ "add $dst, $src1, $src2, sxtw\t# ptr" %}
9596 
9597   ins_encode %{
9598     __ add(as_Register($dst$$reg),
9599            as_Register($src1$$reg),
9600            as_Register($src2$$reg), ext::sxtw);
9601   %}
9602 
9603   ins_pipe(ialu_reg_reg);
9604 %}
9605 
9606 instruct addP_reg_reg_lsl(iRegPNoSp dst, iRegP src1, iRegL src2, immIScale scale) %{
9607   match(Set dst (AddP src1 (LShiftL src2 scale)));
9608 
9609   ins_cost(1.9 * INSN_COST);
9610   format %{ "add $dst, $src1, $src2, LShiftL $scale\t# ptr" %}
9611 
9612   ins_encode %{
9613     __ lea(as_Register($dst$$reg),
9614            Address(as_Register($src1$$reg), as_Register($src2$$reg),
9615                    Address::lsl($scale$$constant)));
9616   %}
9617 
9618   ins_pipe(ialu_reg_reg_shift);
9619 %}
9620 
9621 instruct addP_reg_reg_ext_shift(iRegPNoSp dst, iRegP src1, iRegIorL2I src2, immIScale scale) %{
9622   match(Set dst (AddP src1 (LShiftL (ConvI2L src2) scale)));
9623 
9624   ins_cost(1.9 * INSN_COST);
9625   format %{ "add $dst, $src1, $src2, I2L $scale\t# ptr" %}
9626 
9627   ins_encode %{
9628     __ lea(as_Register($dst$$reg),
9629            Address(as_Register($src1$$reg), as_Register($src2$$reg),
9630                    Address::sxtw($scale$$constant)));
9631   %}
9632 
9633   ins_pipe(ialu_reg_reg_shift);
9634 %}
9635 
9636 instruct lshift_ext(iRegLNoSp dst, iRegIorL2I src, immI scale, rFlagsReg cr) %{
9637   match(Set dst (LShiftL (ConvI2L src) scale));
9638 
9639   ins_cost(INSN_COST);
9640   format %{ "sbfiz $dst, $src, $scale & 63, -$scale & 63\t" %}
9641 
9642   ins_encode %{
9643     __ sbfiz(as_Register($dst$$reg),
9644           as_Register($src$$reg),
9645           $scale$$constant & 63, MIN(32, (-$scale$$constant) & 63));
9646   %}
9647 
9648   ins_pipe(ialu_reg_shift);
9649 %}
9650 
9651 // Pointer Immediate Addition
9652 // n.b. this needs to be more expensive than using an indirect memory
9653 // operand
9654 instruct addP_reg_imm(iRegPNoSp dst, iRegP src1, immLAddSub src2) %{
9655   match(Set dst (AddP src1 src2));
9656 
9657   ins_cost(INSN_COST);
9658   format %{ "add $dst, $src1, $src2\t# ptr" %}
9659 
9660   // use opcode to indicate that this is an add not a sub
9661   opcode(0x0);
9662 
9663   ins_encode( aarch64_enc_addsub_imm(dst, src1, src2) );
9664 
9665   ins_pipe(ialu_reg_imm);
9666 %}
9667 
9668 // Long Addition
9669 instruct addL_reg_reg(iRegLNoSp dst, iRegL src1, iRegL src2) %{
9670 
9671   match(Set dst (AddL src1 src2));
9672 
9673   ins_cost(INSN_COST);
9674   format %{ "add  $dst, $src1, $src2" %}
9675 
9676   ins_encode %{
9677     __ add(as_Register($dst$$reg),
9678            as_Register($src1$$reg),
9679            as_Register($src2$$reg));
9680   %}
9681 
9682   ins_pipe(ialu_reg_reg);
9683 %}
9684 
9685 // No constant pool entries requiredLong Immediate Addition.
9686 instruct addL_reg_imm(iRegLNoSp dst, iRegL src1, immLAddSub src2) %{
9687   match(Set dst (AddL src1 src2));
9688 
9689   ins_cost(INSN_COST);
9690   format %{ "add $dst, $src1, $src2" %}
9691 
9692   // use opcode to indicate that this is an add not a sub
9693   opcode(0x0);
9694 
9695   ins_encode( aarch64_enc_addsub_imm(dst, src1, src2) );
9696 
9697   ins_pipe(ialu_reg_imm);
9698 %}
9699 
9700 // Integer Subtraction
9701 instruct subI_reg_reg(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2) %{
9702   match(Set dst (SubI src1 src2));
9703 
9704   ins_cost(INSN_COST);
9705   format %{ "subw  $dst, $src1, $src2" %}
9706 
9707   ins_encode %{
9708     __ subw(as_Register($dst$$reg),
9709             as_Register($src1$$reg),
9710             as_Register($src2$$reg));
9711   %}
9712 
9713   ins_pipe(ialu_reg_reg);
9714 %}
9715 
9716 // Immediate Subtraction
9717 instruct subI_reg_imm(iRegINoSp dst, iRegIorL2I src1, immIAddSub src2) %{
9718   match(Set dst (SubI src1 src2));
9719 
9720   ins_cost(INSN_COST);
9721   format %{ "subw $dst, $src1, $src2" %}
9722 
9723   // use opcode to indicate that this is a sub not an add
9724   opcode(0x1);
9725 
9726   ins_encode(aarch64_enc_addsubw_imm(dst, src1, src2));
9727 
9728   ins_pipe(ialu_reg_imm);
9729 %}
9730 
9731 // Long Subtraction
9732 instruct subL_reg_reg(iRegLNoSp dst, iRegL src1, iRegL src2) %{
9733 
9734   match(Set dst (SubL src1 src2));
9735 
9736   ins_cost(INSN_COST);
9737   format %{ "sub  $dst, $src1, $src2" %}
9738 
9739   ins_encode %{
9740     __ sub(as_Register($dst$$reg),
9741            as_Register($src1$$reg),
9742            as_Register($src2$$reg));
9743   %}
9744 
9745   ins_pipe(ialu_reg_reg);
9746 %}
9747 
9748 // No constant pool entries requiredLong Immediate Subtraction.
9749 instruct subL_reg_imm(iRegLNoSp dst, iRegL src1, immLAddSub src2) %{
9750   match(Set dst (SubL src1 src2));
9751 
9752   ins_cost(INSN_COST);
9753   format %{ "sub$dst, $src1, $src2" %}
9754 
9755   // use opcode to indicate that this is a sub not an add
9756   opcode(0x1);
9757 
9758   ins_encode( aarch64_enc_addsub_imm(dst, src1, src2) );
9759 
9760   ins_pipe(ialu_reg_imm);
9761 %}
9762 
9763 // Integer Negation (special case for sub)
9764 
9765 instruct negI_reg(iRegINoSp dst, iRegIorL2I src, immI0 zero, rFlagsReg cr) %{
9766   match(Set dst (SubI zero src));
9767 
9768   ins_cost(INSN_COST);
9769   format %{ "negw $dst, $src\t# int" %}
9770 
9771   ins_encode %{
9772     __ negw(as_Register($dst$$reg),
9773             as_Register($src$$reg));
9774   %}
9775 
9776   ins_pipe(ialu_reg);
9777 %}
9778 
9779 // Long Negation
9780 
9781 instruct negL_reg(iRegLNoSp dst, iRegL src, immL0 zero, rFlagsReg cr) %{
9782   match(Set dst (SubL zero src));
9783 
9784   ins_cost(INSN_COST);
9785   format %{ "neg $dst, $src\t# long" %}
9786 
9787   ins_encode %{
9788     __ neg(as_Register($dst$$reg),
9789            as_Register($src$$reg));
9790   %}
9791 
9792   ins_pipe(ialu_reg);
9793 %}
9794 
9795 // Integer Multiply
9796 
9797 instruct mulI(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2) %{
9798   match(Set dst (MulI src1 src2));
9799 
9800   ins_cost(INSN_COST * 3);
9801   format %{ "mulw  $dst, $src1, $src2" %}
9802 
9803   ins_encode %{
9804     __ mulw(as_Register($dst$$reg),
9805             as_Register($src1$$reg),
9806             as_Register($src2$$reg));
9807   %}
9808 
9809   ins_pipe(imul_reg_reg);
9810 %}
9811 
9812 instruct smulI(iRegLNoSp dst, iRegIorL2I src1, iRegIorL2I src2) %{
9813   match(Set dst (MulL (ConvI2L src1) (ConvI2L src2)));
9814 
9815   ins_cost(INSN_COST * 3);
9816   format %{ "smull  $dst, $src1, $src2" %}
9817 
9818   ins_encode %{
9819     __ smull(as_Register($dst$$reg),
9820              as_Register($src1$$reg),
9821              as_Register($src2$$reg));
9822   %}
9823 
9824   ins_pipe(imul_reg_reg);
9825 %}
9826 
9827 // Long Multiply
9828 
9829 instruct mulL(iRegLNoSp dst, iRegL src1, iRegL src2) %{
9830   match(Set dst (MulL src1 src2));
9831 
9832   ins_cost(INSN_COST * 5);
9833   format %{ "mul  $dst, $src1, $src2" %}
9834 
9835   ins_encode %{
9836     __ mul(as_Register($dst$$reg),
9837            as_Register($src1$$reg),
9838            as_Register($src2$$reg));
9839   %}
9840 
9841   ins_pipe(lmul_reg_reg);
9842 %}
9843 
9844 instruct mulHiL_rReg(iRegLNoSp dst, iRegL src1, iRegL src2, rFlagsReg cr)
9845 %{
9846   match(Set dst (MulHiL src1 src2));
9847 
9848   ins_cost(INSN_COST * 7);
9849   format %{ "smulh   $dst, $src1, $src2, \t# mulhi" %}
9850 
9851   ins_encode %{
9852     __ smulh(as_Register($dst$$reg),
9853              as_Register($src1$$reg),
9854              as_Register($src2$$reg));
9855   %}
9856 
9857   ins_pipe(lmul_reg_reg);
9858 %}
9859 
9860 // Combined Integer Multiply & Add/Sub
9861 
9862 instruct maddI(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, iRegIorL2I src3) %{
9863   match(Set dst (AddI src3 (MulI src1 src2)));
9864 
9865   ins_cost(INSN_COST * 3);
9866   format %{ "madd  $dst, $src1, $src2, $src3" %}
9867 
9868   ins_encode %{
9869     __ maddw(as_Register($dst$$reg),
9870              as_Register($src1$$reg),
9871              as_Register($src2$$reg),
9872              as_Register($src3$$reg));
9873   %}
9874 
9875   ins_pipe(imac_reg_reg);
9876 %}
9877 
9878 instruct msubI(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, iRegIorL2I src3) %{
9879   match(Set dst (SubI src3 (MulI src1 src2)));
9880 
9881   ins_cost(INSN_COST * 3);
9882   format %{ "msub  $dst, $src1, $src2, $src3" %}
9883 
9884   ins_encode %{
9885     __ msubw(as_Register($dst$$reg),
9886              as_Register($src1$$reg),
9887              as_Register($src2$$reg),
9888              as_Register($src3$$reg));
9889   %}
9890 
9891   ins_pipe(imac_reg_reg);
9892 %}
9893 
9894 // Combined Long Multiply & Add/Sub
9895 
9896 instruct maddL(iRegLNoSp dst, iRegL src1, iRegL src2, iRegL src3) %{
9897   match(Set dst (AddL src3 (MulL src1 src2)));
9898 
9899   ins_cost(INSN_COST * 5);
9900   format %{ "madd  $dst, $src1, $src2, $src3" %}
9901 
9902   ins_encode %{
9903     __ madd(as_Register($dst$$reg),
9904             as_Register($src1$$reg),
9905             as_Register($src2$$reg),
9906             as_Register($src3$$reg));
9907   %}
9908 
9909   ins_pipe(lmac_reg_reg);
9910 %}
9911 
9912 instruct msubL(iRegLNoSp dst, iRegL src1, iRegL src2, iRegL src3) %{
9913   match(Set dst (SubL src3 (MulL src1 src2)));
9914 
9915   ins_cost(INSN_COST * 5);
9916   format %{ "msub  $dst, $src1, $src2, $src3" %}
9917 
9918   ins_encode %{
9919     __ msub(as_Register($dst$$reg),
9920             as_Register($src1$$reg),
9921             as_Register($src2$$reg),
9922             as_Register($src3$$reg));
9923   %}
9924 
9925   ins_pipe(lmac_reg_reg);
9926 %}
9927 
9928 // Integer Divide
9929 
9930 instruct divI(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2) %{
9931   match(Set dst (DivI src1 src2));
9932 
9933   ins_cost(INSN_COST * 19);
9934   format %{ "sdivw  $dst, $src1, $src2" %}
9935 
9936   ins_encode(aarch64_enc_divw(dst, src1, src2));
9937   ins_pipe(idiv_reg_reg);
9938 %}
9939 
9940 instruct signExtract(iRegINoSp dst, iRegIorL2I src1, immI_31 div1, immI_31 div2) %{
9941   match(Set dst (URShiftI (RShiftI src1 div1) div2));
9942   ins_cost(INSN_COST);
9943   format %{ "lsrw $dst, $src1, $div1" %}
9944   ins_encode %{
9945     __ lsrw(as_Register($dst$$reg), as_Register($src1$$reg), 31);
9946   %}
9947   ins_pipe(ialu_reg_shift);
9948 %}
9949 
9950 instruct div2Round(iRegINoSp dst, iRegIorL2I src, immI_31 div1, immI_31 div2) %{
9951   match(Set dst (AddI src (URShiftI (RShiftI src div1) div2)));
9952   ins_cost(INSN_COST);
9953   format %{ "addw $dst, $src, LSR $div1" %}
9954 
9955   ins_encode %{
9956     __ addw(as_Register($dst$$reg),
9957               as_Register($src$$reg),
9958               as_Register($src$$reg),
9959               Assembler::LSR, 31);
9960   %}
9961   ins_pipe(ialu_reg);
9962 %}
9963 
9964 // Long Divide
9965 
9966 instruct divL(iRegLNoSp dst, iRegL src1, iRegL src2) %{
9967   match(Set dst (DivL src1 src2));
9968 
9969   ins_cost(INSN_COST * 35);
9970   format %{ "sdiv   $dst, $src1, $src2" %}
9971 
9972   ins_encode(aarch64_enc_div(dst, src1, src2));
9973   ins_pipe(ldiv_reg_reg);
9974 %}
9975 
9976 instruct signExtractL(iRegLNoSp dst, iRegL src1, immI_63 div1, immI_63 div2) %{
9977   match(Set dst (URShiftL (RShiftL src1 div1) div2));
9978   ins_cost(INSN_COST);
9979   format %{ "lsr $dst, $src1, $div1" %}
9980   ins_encode %{
9981     __ lsr(as_Register($dst$$reg), as_Register($src1$$reg), 63);
9982   %}
9983   ins_pipe(ialu_reg_shift);
9984 %}
9985 
9986 instruct div2RoundL(iRegLNoSp dst, iRegL src, immI_63 div1, immI_63 div2) %{
9987   match(Set dst (AddL src (URShiftL (RShiftL src div1) div2)));
9988   ins_cost(INSN_COST);
9989   format %{ "add $dst, $src, $div1" %}
9990 
9991   ins_encode %{
9992     __ add(as_Register($dst$$reg),
9993               as_Register($src$$reg),
9994               as_Register($src$$reg),
9995               Assembler::LSR, 63);
9996   %}
9997   ins_pipe(ialu_reg);
9998 %}
9999 
10000 // Integer Remainder
10001 
10002 instruct modI(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2) %{
10003   match(Set dst (ModI src1 src2));
10004 
10005   ins_cost(INSN_COST * 22);
10006   format %{ "sdivw  rscratch1, $src1, $src2\n\t"
10007             "msubw($dst, rscratch1, $src2, $src1" %}
10008 
10009   ins_encode(aarch64_enc_modw(dst, src1, src2));
10010   ins_pipe(idiv_reg_reg);
10011 %}
10012 
10013 // Long Remainder
10014 
10015 instruct modL(iRegLNoSp dst, iRegL src1, iRegL src2) %{
10016   match(Set dst (ModL src1 src2));
10017 
10018   ins_cost(INSN_COST * 38);
10019   format %{ "sdiv   rscratch1, $src1, $src2\n"
10020             "msub($dst, rscratch1, $src2, $src1" %}
10021 
10022   ins_encode(aarch64_enc_mod(dst, src1, src2));
10023   ins_pipe(ldiv_reg_reg);
10024 %}
10025 
10026 // Integer Shifts
10027 
10028 // Shift Left Register
10029 instruct lShiftI_reg_reg(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2) %{
10030   match(Set dst (LShiftI src1 src2));
10031 
10032   ins_cost(INSN_COST * 2);
10033   format %{ "lslvw  $dst, $src1, $src2" %}
10034 
10035   ins_encode %{
10036     __ lslvw(as_Register($dst$$reg),
10037              as_Register($src1$$reg),
10038              as_Register($src2$$reg));
10039   %}
10040 
10041   ins_pipe(ialu_reg_reg_vshift);
10042 %}
10043 
10044 // Shift Left Immediate
10045 instruct lShiftI_reg_imm(iRegINoSp dst, iRegIorL2I src1, immI src2) %{
10046   match(Set dst (LShiftI src1 src2));
10047 
10048   ins_cost(INSN_COST);
10049   format %{ "lslw $dst, $src1, ($src2 & 0x1f)" %}
10050 
10051   ins_encode %{
10052     __ lslw(as_Register($dst$$reg),
10053             as_Register($src1$$reg),
10054             $src2$$constant & 0x1f);
10055   %}
10056 
10057   ins_pipe(ialu_reg_shift);
10058 %}
10059 
10060 // Shift Right Logical Register
10061 instruct urShiftI_reg_reg(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2) %{
10062   match(Set dst (URShiftI src1 src2));
10063 
10064   ins_cost(INSN_COST * 2);
10065   format %{ "lsrvw  $dst, $src1, $src2" %}
10066 
10067   ins_encode %{
10068     __ lsrvw(as_Register($dst$$reg),
10069              as_Register($src1$$reg),
10070              as_Register($src2$$reg));
10071   %}
10072 
10073   ins_pipe(ialu_reg_reg_vshift);
10074 %}
10075 
10076 // Shift Right Logical Immediate
10077 instruct urShiftI_reg_imm(iRegINoSp dst, iRegIorL2I src1, immI src2) %{
10078   match(Set dst (URShiftI src1 src2));
10079 
10080   ins_cost(INSN_COST);
10081   format %{ "lsrw $dst, $src1, ($src2 & 0x1f)" %}
10082 
10083   ins_encode %{
10084     __ lsrw(as_Register($dst$$reg),
10085             as_Register($src1$$reg),
10086             $src2$$constant & 0x1f);
10087   %}
10088 
10089   ins_pipe(ialu_reg_shift);
10090 %}
10091 
10092 // Shift Right Arithmetic Register
10093 instruct rShiftI_reg_reg(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2) %{
10094   match(Set dst (RShiftI src1 src2));
10095 
10096   ins_cost(INSN_COST * 2);
10097   format %{ "asrvw  $dst, $src1, $src2" %}
10098 
10099   ins_encode %{
10100     __ asrvw(as_Register($dst$$reg),
10101              as_Register($src1$$reg),
10102              as_Register($src2$$reg));
10103   %}
10104 
10105   ins_pipe(ialu_reg_reg_vshift);
10106 %}
10107 
10108 // Shift Right Arithmetic Immediate
10109 instruct rShiftI_reg_imm(iRegINoSp dst, iRegIorL2I src1, immI src2) %{
10110   match(Set dst (RShiftI src1 src2));
10111 
10112   ins_cost(INSN_COST);
10113   format %{ "asrw $dst, $src1, ($src2 & 0x1f)" %}
10114 
10115   ins_encode %{
10116     __ asrw(as_Register($dst$$reg),
10117             as_Register($src1$$reg),
10118             $src2$$constant & 0x1f);
10119   %}
10120 
10121   ins_pipe(ialu_reg_shift);
10122 %}
10123 
10124 // Combined Int Mask and Right Shift (using UBFM)
10125 // TODO
10126 
10127 // Long Shifts
10128 
10129 // Shift Left Register
10130 instruct lShiftL_reg_reg(iRegLNoSp dst, iRegL src1, iRegIorL2I src2) %{
10131   match(Set dst (LShiftL src1 src2));
10132 
10133   ins_cost(INSN_COST * 2);
10134   format %{ "lslv  $dst, $src1, $src2" %}
10135 
10136   ins_encode %{
10137     __ lslv(as_Register($dst$$reg),
10138             as_Register($src1$$reg),
10139             as_Register($src2$$reg));
10140   %}
10141 
10142   ins_pipe(ialu_reg_reg_vshift);
10143 %}
10144 
10145 // Shift Left Immediate
10146 instruct lShiftL_reg_imm(iRegLNoSp dst, iRegL src1, immI src2) %{
10147   match(Set dst (LShiftL src1 src2));
10148 
10149   ins_cost(INSN_COST);
10150   format %{ "lsl $dst, $src1, ($src2 & 0x3f)" %}
10151 
10152   ins_encode %{
10153     __ lsl(as_Register($dst$$reg),
10154             as_Register($src1$$reg),
10155             $src2$$constant & 0x3f);
10156   %}
10157 
10158   ins_pipe(ialu_reg_shift);
10159 %}
10160 
10161 // Shift Right Logical Register
10162 instruct urShiftL_reg_reg(iRegLNoSp dst, iRegL src1, iRegIorL2I src2) %{
10163   match(Set dst (URShiftL src1 src2));
10164 
10165   ins_cost(INSN_COST * 2);
10166   format %{ "lsrv  $dst, $src1, $src2" %}
10167 
10168   ins_encode %{
10169     __ lsrv(as_Register($dst$$reg),
10170             as_Register($src1$$reg),
10171             as_Register($src2$$reg));
10172   %}
10173 
10174   ins_pipe(ialu_reg_reg_vshift);
10175 %}
10176 
10177 // Shift Right Logical Immediate
10178 instruct urShiftL_reg_imm(iRegLNoSp dst, iRegL src1, immI src2) %{
10179   match(Set dst (URShiftL src1 src2));
10180 
10181   ins_cost(INSN_COST);
10182   format %{ "lsr $dst, $src1, ($src2 & 0x3f)" %}
10183 
10184   ins_encode %{
10185     __ lsr(as_Register($dst$$reg),
10186            as_Register($src1$$reg),
10187            $src2$$constant & 0x3f);
10188   %}
10189 
10190   ins_pipe(ialu_reg_shift);
10191 %}
10192 
10193 // A special-case pattern for card table stores.
10194 instruct urShiftP_reg_imm(iRegLNoSp dst, iRegP src1, immI src2) %{
10195   match(Set dst (URShiftL (CastP2X src1) src2));
10196 
10197   ins_cost(INSN_COST);
10198   format %{ "lsr $dst, p2x($src1), ($src2 & 0x3f)" %}
10199 
10200   ins_encode %{
10201     __ lsr(as_Register($dst$$reg),
10202            as_Register($src1$$reg),
10203            $src2$$constant & 0x3f);
10204   %}
10205 
10206   ins_pipe(ialu_reg_shift);
10207 %}
10208 
10209 // Shift Right Arithmetic Register
10210 instruct rShiftL_reg_reg(iRegLNoSp dst, iRegL src1, iRegIorL2I src2) %{
10211   match(Set dst (RShiftL src1 src2));
10212 
10213   ins_cost(INSN_COST * 2);
10214   format %{ "asrv  $dst, $src1, $src2" %}
10215 
10216   ins_encode %{
10217     __ asrv(as_Register($dst$$reg),
10218             as_Register($src1$$reg),
10219             as_Register($src2$$reg));
10220   %}
10221 
10222   ins_pipe(ialu_reg_reg_vshift);
10223 %}
10224 
10225 // Shift Right Arithmetic Immediate
10226 instruct rShiftL_reg_imm(iRegLNoSp dst, iRegL src1, immI src2) %{
10227   match(Set dst (RShiftL src1 src2));
10228 
10229   ins_cost(INSN_COST);
10230   format %{ "asr $dst, $src1, ($src2 & 0x3f)" %}
10231 
10232   ins_encode %{
10233     __ asr(as_Register($dst$$reg),
10234            as_Register($src1$$reg),
10235            $src2$$constant & 0x3f);
10236   %}
10237 
10238   ins_pipe(ialu_reg_shift);
10239 %}
10240 
10241 // BEGIN This section of the file is automatically generated. Do not edit --------------
10242 
10243 instruct regL_not_reg(iRegLNoSp dst,
10244                          iRegL src1, immL_M1 m1,
10245                          rFlagsReg cr) %{
10246   match(Set dst (XorL src1 m1));
10247   ins_cost(INSN_COST);
10248   format %{ "eon  $dst, $src1, zr" %}
10249 
10250   ins_encode %{
10251     __ eon(as_Register($dst$$reg),
10252               as_Register($src1$$reg),
10253               zr,
10254               Assembler::LSL, 0);
10255   %}
10256 
10257   ins_pipe(ialu_reg);
10258 %}
10259 instruct regI_not_reg(iRegINoSp dst,
10260                          iRegIorL2I src1, immI_M1 m1,
10261                          rFlagsReg cr) %{
10262   match(Set dst (XorI src1 m1));
10263   ins_cost(INSN_COST);
10264   format %{ "eonw  $dst, $src1, zr" %}
10265 
10266   ins_encode %{
10267     __ eonw(as_Register($dst$$reg),
10268               as_Register($src1$$reg),
10269               zr,
10270               Assembler::LSL, 0);
10271   %}
10272 
10273   ins_pipe(ialu_reg);
10274 %}
10275 
10276 instruct AndI_reg_not_reg(iRegINoSp dst,
10277                          iRegIorL2I src1, iRegIorL2I src2, immI_M1 m1,
10278                          rFlagsReg cr) %{
10279   match(Set dst (AndI src1 (XorI src2 m1)));
10280   ins_cost(INSN_COST);
10281   format %{ "bicw  $dst, $src1, $src2" %}
10282 
10283   ins_encode %{
10284     __ bicw(as_Register($dst$$reg),
10285               as_Register($src1$$reg),
10286               as_Register($src2$$reg),
10287               Assembler::LSL, 0);
10288   %}
10289 
10290   ins_pipe(ialu_reg_reg);
10291 %}
10292 
10293 instruct AndL_reg_not_reg(iRegLNoSp dst,
10294                          iRegL src1, iRegL src2, immL_M1 m1,
10295                          rFlagsReg cr) %{
10296   match(Set dst (AndL src1 (XorL src2 m1)));
10297   ins_cost(INSN_COST);
10298   format %{ "bic  $dst, $src1, $src2" %}
10299 
10300   ins_encode %{
10301     __ bic(as_Register($dst$$reg),
10302               as_Register($src1$$reg),
10303               as_Register($src2$$reg),
10304               Assembler::LSL, 0);
10305   %}
10306 
10307   ins_pipe(ialu_reg_reg);
10308 %}
10309 
10310 instruct OrI_reg_not_reg(iRegINoSp dst,
10311                          iRegIorL2I src1, iRegIorL2I src2, immI_M1 m1,
10312                          rFlagsReg cr) %{
10313   match(Set dst (OrI src1 (XorI src2 m1)));
10314   ins_cost(INSN_COST);
10315   format %{ "ornw  $dst, $src1, $src2" %}
10316 
10317   ins_encode %{
10318     __ ornw(as_Register($dst$$reg),
10319               as_Register($src1$$reg),
10320               as_Register($src2$$reg),
10321               Assembler::LSL, 0);
10322   %}
10323 
10324   ins_pipe(ialu_reg_reg);
10325 %}
10326 
10327 instruct OrL_reg_not_reg(iRegLNoSp dst,
10328                          iRegL src1, iRegL src2, immL_M1 m1,
10329                          rFlagsReg cr) %{
10330   match(Set dst (OrL src1 (XorL src2 m1)));
10331   ins_cost(INSN_COST);
10332   format %{ "orn  $dst, $src1, $src2" %}
10333 
10334   ins_encode %{
10335     __ orn(as_Register($dst$$reg),
10336               as_Register($src1$$reg),
10337               as_Register($src2$$reg),
10338               Assembler::LSL, 0);
10339   %}
10340 
10341   ins_pipe(ialu_reg_reg);
10342 %}
10343 
10344 instruct XorI_reg_not_reg(iRegINoSp dst,
10345                          iRegIorL2I src1, iRegIorL2I src2, immI_M1 m1,
10346                          rFlagsReg cr) %{
10347   match(Set dst (XorI m1 (XorI src2 src1)));
10348   ins_cost(INSN_COST);
10349   format %{ "eonw  $dst, $src1, $src2" %}
10350 
10351   ins_encode %{
10352     __ eonw(as_Register($dst$$reg),
10353               as_Register($src1$$reg),
10354               as_Register($src2$$reg),
10355               Assembler::LSL, 0);
10356   %}
10357 
10358   ins_pipe(ialu_reg_reg);
10359 %}
10360 
10361 instruct XorL_reg_not_reg(iRegLNoSp dst,
10362                          iRegL src1, iRegL src2, immL_M1 m1,
10363                          rFlagsReg cr) %{
10364   match(Set dst (XorL m1 (XorL src2 src1)));
10365   ins_cost(INSN_COST);
10366   format %{ "eon  $dst, $src1, $src2" %}
10367 
10368   ins_encode %{
10369     __ eon(as_Register($dst$$reg),
10370               as_Register($src1$$reg),
10371               as_Register($src2$$reg),
10372               Assembler::LSL, 0);
10373   %}
10374 
10375   ins_pipe(ialu_reg_reg);
10376 %}
10377 
10378 instruct AndI_reg_URShift_not_reg(iRegINoSp dst,
10379                          iRegIorL2I src1, iRegIorL2I src2,
10380                          immI src3, immI_M1 src4, rFlagsReg cr) %{
10381   match(Set dst (AndI src1 (XorI(URShiftI src2 src3) src4)));
10382   ins_cost(1.9 * INSN_COST);
10383   format %{ "bicw  $dst, $src1, $src2, LSR $src3" %}
10384 
10385   ins_encode %{
10386     __ bicw(as_Register($dst$$reg),
10387               as_Register($src1$$reg),
10388               as_Register($src2$$reg),
10389               Assembler::LSR,
10390               $src3$$constant & 0x1f);
10391   %}
10392 
10393   ins_pipe(ialu_reg_reg_shift);
10394 %}
10395 
10396 instruct AndL_reg_URShift_not_reg(iRegLNoSp dst,
10397                          iRegL src1, iRegL src2,
10398                          immI src3, immL_M1 src4, rFlagsReg cr) %{
10399   match(Set dst (AndL src1 (XorL(URShiftL src2 src3) src4)));
10400   ins_cost(1.9 * INSN_COST);
10401   format %{ "bic  $dst, $src1, $src2, LSR $src3" %}
10402 
10403   ins_encode %{
10404     __ bic(as_Register($dst$$reg),
10405               as_Register($src1$$reg),
10406               as_Register($src2$$reg),
10407               Assembler::LSR,
10408               $src3$$constant & 0x3f);
10409   %}
10410 
10411   ins_pipe(ialu_reg_reg_shift);
10412 %}
10413 
10414 instruct AndI_reg_RShift_not_reg(iRegINoSp dst,
10415                          iRegIorL2I src1, iRegIorL2I src2,
10416                          immI src3, immI_M1 src4, rFlagsReg cr) %{
10417   match(Set dst (AndI src1 (XorI(RShiftI src2 src3) src4)));
10418   ins_cost(1.9 * INSN_COST);
10419   format %{ "bicw  $dst, $src1, $src2, ASR $src3" %}
10420 
10421   ins_encode %{
10422     __ bicw(as_Register($dst$$reg),
10423               as_Register($src1$$reg),
10424               as_Register($src2$$reg),
10425               Assembler::ASR,
10426               $src3$$constant & 0x1f);
10427   %}
10428 
10429   ins_pipe(ialu_reg_reg_shift);
10430 %}
10431 
10432 instruct AndL_reg_RShift_not_reg(iRegLNoSp dst,
10433                          iRegL src1, iRegL src2,
10434                          immI src3, immL_M1 src4, rFlagsReg cr) %{
10435   match(Set dst (AndL src1 (XorL(RShiftL src2 src3) src4)));
10436   ins_cost(1.9 * INSN_COST);
10437   format %{ "bic  $dst, $src1, $src2, ASR $src3" %}
10438 
10439   ins_encode %{
10440     __ bic(as_Register($dst$$reg),
10441               as_Register($src1$$reg),
10442               as_Register($src2$$reg),
10443               Assembler::ASR,
10444               $src3$$constant & 0x3f);
10445   %}
10446 
10447   ins_pipe(ialu_reg_reg_shift);
10448 %}
10449 
10450 instruct AndI_reg_LShift_not_reg(iRegINoSp dst,
10451                          iRegIorL2I src1, iRegIorL2I src2,
10452                          immI src3, immI_M1 src4, rFlagsReg cr) %{
10453   match(Set dst (AndI src1 (XorI(LShiftI src2 src3) src4)));
10454   ins_cost(1.9 * INSN_COST);
10455   format %{ "bicw  $dst, $src1, $src2, LSL $src3" %}
10456 
10457   ins_encode %{
10458     __ bicw(as_Register($dst$$reg),
10459               as_Register($src1$$reg),
10460               as_Register($src2$$reg),
10461               Assembler::LSL,
10462               $src3$$constant & 0x1f);
10463   %}
10464 
10465   ins_pipe(ialu_reg_reg_shift);
10466 %}
10467 
10468 instruct AndL_reg_LShift_not_reg(iRegLNoSp dst,
10469                          iRegL src1, iRegL src2,
10470                          immI src3, immL_M1 src4, rFlagsReg cr) %{
10471   match(Set dst (AndL src1 (XorL(LShiftL src2 src3) src4)));
10472   ins_cost(1.9 * INSN_COST);
10473   format %{ "bic  $dst, $src1, $src2, LSL $src3" %}
10474 
10475   ins_encode %{
10476     __ bic(as_Register($dst$$reg),
10477               as_Register($src1$$reg),
10478               as_Register($src2$$reg),
10479               Assembler::LSL,
10480               $src3$$constant & 0x3f);
10481   %}
10482 
10483   ins_pipe(ialu_reg_reg_shift);
10484 %}
10485 
10486 instruct XorI_reg_URShift_not_reg(iRegINoSp dst,
10487                          iRegIorL2I src1, iRegIorL2I src2,
10488                          immI src3, immI_M1 src4, rFlagsReg cr) %{
10489   match(Set dst (XorI src4 (XorI(URShiftI src2 src3) src1)));
10490   ins_cost(1.9 * INSN_COST);
10491   format %{ "eonw  $dst, $src1, $src2, LSR $src3" %}
10492 
10493   ins_encode %{
10494     __ eonw(as_Register($dst$$reg),
10495               as_Register($src1$$reg),
10496               as_Register($src2$$reg),
10497               Assembler::LSR,
10498               $src3$$constant & 0x1f);
10499   %}
10500 
10501   ins_pipe(ialu_reg_reg_shift);
10502 %}
10503 
10504 instruct XorL_reg_URShift_not_reg(iRegLNoSp dst,
10505                          iRegL src1, iRegL src2,
10506                          immI src3, immL_M1 src4, rFlagsReg cr) %{
10507   match(Set dst (XorL src4 (XorL(URShiftL src2 src3) src1)));
10508   ins_cost(1.9 * INSN_COST);
10509   format %{ "eon  $dst, $src1, $src2, LSR $src3" %}
10510 
10511   ins_encode %{
10512     __ eon(as_Register($dst$$reg),
10513               as_Register($src1$$reg),
10514               as_Register($src2$$reg),
10515               Assembler::LSR,
10516               $src3$$constant & 0x3f);
10517   %}
10518 
10519   ins_pipe(ialu_reg_reg_shift);
10520 %}
10521 
10522 instruct XorI_reg_RShift_not_reg(iRegINoSp dst,
10523                          iRegIorL2I src1, iRegIorL2I src2,
10524                          immI src3, immI_M1 src4, rFlagsReg cr) %{
10525   match(Set dst (XorI src4 (XorI(RShiftI src2 src3) src1)));
10526   ins_cost(1.9 * INSN_COST);
10527   format %{ "eonw  $dst, $src1, $src2, ASR $src3" %}
10528 
10529   ins_encode %{
10530     __ eonw(as_Register($dst$$reg),
10531               as_Register($src1$$reg),
10532               as_Register($src2$$reg),
10533               Assembler::ASR,
10534               $src3$$constant & 0x1f);
10535   %}
10536 
10537   ins_pipe(ialu_reg_reg_shift);
10538 %}
10539 
10540 instruct XorL_reg_RShift_not_reg(iRegLNoSp dst,
10541                          iRegL src1, iRegL src2,
10542                          immI src3, immL_M1 src4, rFlagsReg cr) %{
10543   match(Set dst (XorL src4 (XorL(RShiftL src2 src3) src1)));
10544   ins_cost(1.9 * INSN_COST);
10545   format %{ "eon  $dst, $src1, $src2, ASR $src3" %}
10546 
10547   ins_encode %{
10548     __ eon(as_Register($dst$$reg),
10549               as_Register($src1$$reg),
10550               as_Register($src2$$reg),
10551               Assembler::ASR,
10552               $src3$$constant & 0x3f);
10553   %}
10554 
10555   ins_pipe(ialu_reg_reg_shift);
10556 %}
10557 
10558 instruct XorI_reg_LShift_not_reg(iRegINoSp dst,
10559                          iRegIorL2I src1, iRegIorL2I src2,
10560                          immI src3, immI_M1 src4, rFlagsReg cr) %{
10561   match(Set dst (XorI src4 (XorI(LShiftI src2 src3) src1)));
10562   ins_cost(1.9 * INSN_COST);
10563   format %{ "eonw  $dst, $src1, $src2, LSL $src3" %}
10564 
10565   ins_encode %{
10566     __ eonw(as_Register($dst$$reg),
10567               as_Register($src1$$reg),
10568               as_Register($src2$$reg),
10569               Assembler::LSL,
10570               $src3$$constant & 0x1f);
10571   %}
10572 
10573   ins_pipe(ialu_reg_reg_shift);
10574 %}
10575 
10576 instruct XorL_reg_LShift_not_reg(iRegLNoSp dst,
10577                          iRegL src1, iRegL src2,
10578                          immI src3, immL_M1 src4, rFlagsReg cr) %{
10579   match(Set dst (XorL src4 (XorL(LShiftL src2 src3) src1)));
10580   ins_cost(1.9 * INSN_COST);
10581   format %{ "eon  $dst, $src1, $src2, LSL $src3" %}
10582 
10583   ins_encode %{
10584     __ eon(as_Register($dst$$reg),
10585               as_Register($src1$$reg),
10586               as_Register($src2$$reg),
10587               Assembler::LSL,
10588               $src3$$constant & 0x3f);
10589   %}
10590 
10591   ins_pipe(ialu_reg_reg_shift);
10592 %}
10593 
10594 instruct OrI_reg_URShift_not_reg(iRegINoSp dst,
10595                          iRegIorL2I src1, iRegIorL2I src2,
10596                          immI src3, immI_M1 src4, rFlagsReg cr) %{
10597   match(Set dst (OrI src1 (XorI(URShiftI src2 src3) src4)));
10598   ins_cost(1.9 * INSN_COST);
10599   format %{ "ornw  $dst, $src1, $src2, LSR $src3" %}
10600 
10601   ins_encode %{
10602     __ ornw(as_Register($dst$$reg),
10603               as_Register($src1$$reg),
10604               as_Register($src2$$reg),
10605               Assembler::LSR,
10606               $src3$$constant & 0x1f);
10607   %}
10608 
10609   ins_pipe(ialu_reg_reg_shift);
10610 %}
10611 
10612 instruct OrL_reg_URShift_not_reg(iRegLNoSp dst,
10613                          iRegL src1, iRegL src2,
10614                          immI src3, immL_M1 src4, rFlagsReg cr) %{
10615   match(Set dst (OrL src1 (XorL(URShiftL src2 src3) src4)));
10616   ins_cost(1.9 * INSN_COST);
10617   format %{ "orn  $dst, $src1, $src2, LSR $src3" %}
10618 
10619   ins_encode %{
10620     __ orn(as_Register($dst$$reg),
10621               as_Register($src1$$reg),
10622               as_Register($src2$$reg),
10623               Assembler::LSR,
10624               $src3$$constant & 0x3f);
10625   %}
10626 
10627   ins_pipe(ialu_reg_reg_shift);
10628 %}
10629 
10630 instruct OrI_reg_RShift_not_reg(iRegINoSp dst,
10631                          iRegIorL2I src1, iRegIorL2I src2,
10632                          immI src3, immI_M1 src4, rFlagsReg cr) %{
10633   match(Set dst (OrI src1 (XorI(RShiftI src2 src3) src4)));
10634   ins_cost(1.9 * INSN_COST);
10635   format %{ "ornw  $dst, $src1, $src2, ASR $src3" %}
10636 
10637   ins_encode %{
10638     __ ornw(as_Register($dst$$reg),
10639               as_Register($src1$$reg),
10640               as_Register($src2$$reg),
10641               Assembler::ASR,
10642               $src3$$constant & 0x1f);
10643   %}
10644 
10645   ins_pipe(ialu_reg_reg_shift);
10646 %}
10647 
10648 instruct OrL_reg_RShift_not_reg(iRegLNoSp dst,
10649                          iRegL src1, iRegL src2,
10650                          immI src3, immL_M1 src4, rFlagsReg cr) %{
10651   match(Set dst (OrL src1 (XorL(RShiftL src2 src3) src4)));
10652   ins_cost(1.9 * INSN_COST);
10653   format %{ "orn  $dst, $src1, $src2, ASR $src3" %}
10654 
10655   ins_encode %{
10656     __ orn(as_Register($dst$$reg),
10657               as_Register($src1$$reg),
10658               as_Register($src2$$reg),
10659               Assembler::ASR,
10660               $src3$$constant & 0x3f);
10661   %}
10662 
10663   ins_pipe(ialu_reg_reg_shift);
10664 %}
10665 
10666 instruct OrI_reg_LShift_not_reg(iRegINoSp dst,
10667                          iRegIorL2I src1, iRegIorL2I src2,
10668                          immI src3, immI_M1 src4, rFlagsReg cr) %{
10669   match(Set dst (OrI src1 (XorI(LShiftI src2 src3) src4)));
10670   ins_cost(1.9 * INSN_COST);
10671   format %{ "ornw  $dst, $src1, $src2, LSL $src3" %}
10672 
10673   ins_encode %{
10674     __ ornw(as_Register($dst$$reg),
10675               as_Register($src1$$reg),
10676               as_Register($src2$$reg),
10677               Assembler::LSL,
10678               $src3$$constant & 0x1f);
10679   %}
10680 
10681   ins_pipe(ialu_reg_reg_shift);
10682 %}
10683 
10684 instruct OrL_reg_LShift_not_reg(iRegLNoSp dst,
10685                          iRegL src1, iRegL src2,
10686                          immI src3, immL_M1 src4, rFlagsReg cr) %{
10687   match(Set dst (OrL src1 (XorL(LShiftL src2 src3) src4)));
10688   ins_cost(1.9 * INSN_COST);
10689   format %{ "orn  $dst, $src1, $src2, LSL $src3" %}
10690 
10691   ins_encode %{
10692     __ orn(as_Register($dst$$reg),
10693               as_Register($src1$$reg),
10694               as_Register($src2$$reg),
10695               Assembler::LSL,
10696               $src3$$constant & 0x3f);
10697   %}
10698 
10699   ins_pipe(ialu_reg_reg_shift);
10700 %}
10701 
10702 instruct AndI_reg_URShift_reg(iRegINoSp dst,
10703                          iRegIorL2I src1, iRegIorL2I src2,
10704                          immI src3, rFlagsReg cr) %{
10705   match(Set dst (AndI src1 (URShiftI src2 src3)));
10706 
10707   ins_cost(1.9 * INSN_COST);
10708   format %{ "andw  $dst, $src1, $src2, LSR $src3" %}
10709 
10710   ins_encode %{
10711     __ andw(as_Register($dst$$reg),
10712               as_Register($src1$$reg),
10713               as_Register($src2$$reg),
10714               Assembler::LSR,
10715               $src3$$constant & 0x1f);
10716   %}
10717 
10718   ins_pipe(ialu_reg_reg_shift);
10719 %}
10720 
10721 instruct AndL_reg_URShift_reg(iRegLNoSp dst,
10722                          iRegL src1, iRegL src2,
10723                          immI src3, rFlagsReg cr) %{
10724   match(Set dst (AndL src1 (URShiftL src2 src3)));
10725 
10726   ins_cost(1.9 * INSN_COST);
10727   format %{ "andr  $dst, $src1, $src2, LSR $src3" %}
10728 
10729   ins_encode %{
10730     __ andr(as_Register($dst$$reg),
10731               as_Register($src1$$reg),
10732               as_Register($src2$$reg),
10733               Assembler::LSR,
10734               $src3$$constant & 0x3f);
10735   %}
10736 
10737   ins_pipe(ialu_reg_reg_shift);
10738 %}
10739 
10740 instruct AndI_reg_RShift_reg(iRegINoSp dst,
10741                          iRegIorL2I src1, iRegIorL2I src2,
10742                          immI src3, rFlagsReg cr) %{
10743   match(Set dst (AndI src1 (RShiftI src2 src3)));
10744 
10745   ins_cost(1.9 * INSN_COST);
10746   format %{ "andw  $dst, $src1, $src2, ASR $src3" %}
10747 
10748   ins_encode %{
10749     __ andw(as_Register($dst$$reg),
10750               as_Register($src1$$reg),
10751               as_Register($src2$$reg),
10752               Assembler::ASR,
10753               $src3$$constant & 0x1f);
10754   %}
10755 
10756   ins_pipe(ialu_reg_reg_shift);
10757 %}
10758 
10759 instruct AndL_reg_RShift_reg(iRegLNoSp dst,
10760                          iRegL src1, iRegL src2,
10761                          immI src3, rFlagsReg cr) %{
10762   match(Set dst (AndL src1 (RShiftL src2 src3)));
10763 
10764   ins_cost(1.9 * INSN_COST);
10765   format %{ "andr  $dst, $src1, $src2, ASR $src3" %}
10766 
10767   ins_encode %{
10768     __ andr(as_Register($dst$$reg),
10769               as_Register($src1$$reg),
10770               as_Register($src2$$reg),
10771               Assembler::ASR,
10772               $src3$$constant & 0x3f);
10773   %}
10774 
10775   ins_pipe(ialu_reg_reg_shift);
10776 %}
10777 
10778 instruct AndI_reg_LShift_reg(iRegINoSp dst,
10779                          iRegIorL2I src1, iRegIorL2I src2,
10780                          immI src3, rFlagsReg cr) %{
10781   match(Set dst (AndI src1 (LShiftI src2 src3)));
10782 
10783   ins_cost(1.9 * INSN_COST);
10784   format %{ "andw  $dst, $src1, $src2, LSL $src3" %}
10785 
10786   ins_encode %{
10787     __ andw(as_Register($dst$$reg),
10788               as_Register($src1$$reg),
10789               as_Register($src2$$reg),
10790               Assembler::LSL,
10791               $src3$$constant & 0x1f);
10792   %}
10793 
10794   ins_pipe(ialu_reg_reg_shift);
10795 %}
10796 
10797 instruct AndL_reg_LShift_reg(iRegLNoSp dst,
10798                          iRegL src1, iRegL src2,
10799                          immI src3, rFlagsReg cr) %{
10800   match(Set dst (AndL src1 (LShiftL src2 src3)));
10801 
10802   ins_cost(1.9 * INSN_COST);
10803   format %{ "andr  $dst, $src1, $src2, LSL $src3" %}
10804 
10805   ins_encode %{
10806     __ andr(as_Register($dst$$reg),
10807               as_Register($src1$$reg),
10808               as_Register($src2$$reg),
10809               Assembler::LSL,
10810               $src3$$constant & 0x3f);
10811   %}
10812 
10813   ins_pipe(ialu_reg_reg_shift);
10814 %}
10815 
10816 instruct XorI_reg_URShift_reg(iRegINoSp dst,
10817                          iRegIorL2I src1, iRegIorL2I src2,
10818                          immI src3, rFlagsReg cr) %{
10819   match(Set dst (XorI src1 (URShiftI src2 src3)));
10820 
10821   ins_cost(1.9 * INSN_COST);
10822   format %{ "eorw  $dst, $src1, $src2, LSR $src3" %}
10823 
10824   ins_encode %{
10825     __ eorw(as_Register($dst$$reg),
10826               as_Register($src1$$reg),
10827               as_Register($src2$$reg),
10828               Assembler::LSR,
10829               $src3$$constant & 0x1f);
10830   %}
10831 
10832   ins_pipe(ialu_reg_reg_shift);
10833 %}
10834 
10835 instruct XorL_reg_URShift_reg(iRegLNoSp dst,
10836                          iRegL src1, iRegL src2,
10837                          immI src3, rFlagsReg cr) %{
10838   match(Set dst (XorL src1 (URShiftL src2 src3)));
10839 
10840   ins_cost(1.9 * INSN_COST);
10841   format %{ "eor  $dst, $src1, $src2, LSR $src3" %}
10842 
10843   ins_encode %{
10844     __ eor(as_Register($dst$$reg),
10845               as_Register($src1$$reg),
10846               as_Register($src2$$reg),
10847               Assembler::LSR,
10848               $src3$$constant & 0x3f);
10849   %}
10850 
10851   ins_pipe(ialu_reg_reg_shift);
10852 %}
10853 
10854 instruct XorI_reg_RShift_reg(iRegINoSp dst,
10855                          iRegIorL2I src1, iRegIorL2I src2,
10856                          immI src3, rFlagsReg cr) %{
10857   match(Set dst (XorI src1 (RShiftI src2 src3)));
10858 
10859   ins_cost(1.9 * INSN_COST);
10860   format %{ "eorw  $dst, $src1, $src2, ASR $src3" %}
10861 
10862   ins_encode %{
10863     __ eorw(as_Register($dst$$reg),
10864               as_Register($src1$$reg),
10865               as_Register($src2$$reg),
10866               Assembler::ASR,
10867               $src3$$constant & 0x1f);
10868   %}
10869 
10870   ins_pipe(ialu_reg_reg_shift);
10871 %}
10872 
10873 instruct XorL_reg_RShift_reg(iRegLNoSp dst,
10874                          iRegL src1, iRegL src2,
10875                          immI src3, rFlagsReg cr) %{
10876   match(Set dst (XorL src1 (RShiftL src2 src3)));
10877 
10878   ins_cost(1.9 * INSN_COST);
10879   format %{ "eor  $dst, $src1, $src2, ASR $src3" %}
10880 
10881   ins_encode %{
10882     __ eor(as_Register($dst$$reg),
10883               as_Register($src1$$reg),
10884               as_Register($src2$$reg),
10885               Assembler::ASR,
10886               $src3$$constant & 0x3f);
10887   %}
10888 
10889   ins_pipe(ialu_reg_reg_shift);
10890 %}
10891 
10892 instruct XorI_reg_LShift_reg(iRegINoSp dst,
10893                          iRegIorL2I src1, iRegIorL2I src2,
10894                          immI src3, rFlagsReg cr) %{
10895   match(Set dst (XorI src1 (LShiftI src2 src3)));
10896 
10897   ins_cost(1.9 * INSN_COST);
10898   format %{ "eorw  $dst, $src1, $src2, LSL $src3" %}
10899 
10900   ins_encode %{
10901     __ eorw(as_Register($dst$$reg),
10902               as_Register($src1$$reg),
10903               as_Register($src2$$reg),
10904               Assembler::LSL,
10905               $src3$$constant & 0x1f);
10906   %}
10907 
10908   ins_pipe(ialu_reg_reg_shift);
10909 %}
10910 
10911 instruct XorL_reg_LShift_reg(iRegLNoSp dst,
10912                          iRegL src1, iRegL src2,
10913                          immI src3, rFlagsReg cr) %{
10914   match(Set dst (XorL src1 (LShiftL src2 src3)));
10915 
10916   ins_cost(1.9 * INSN_COST);
10917   format %{ "eor  $dst, $src1, $src2, LSL $src3" %}
10918 
10919   ins_encode %{
10920     __ eor(as_Register($dst$$reg),
10921               as_Register($src1$$reg),
10922               as_Register($src2$$reg),
10923               Assembler::LSL,
10924               $src3$$constant & 0x3f);
10925   %}
10926 
10927   ins_pipe(ialu_reg_reg_shift);
10928 %}
10929 
10930 instruct OrI_reg_URShift_reg(iRegINoSp dst,
10931                          iRegIorL2I src1, iRegIorL2I src2,
10932                          immI src3, rFlagsReg cr) %{
10933   match(Set dst (OrI src1 (URShiftI src2 src3)));
10934 
10935   ins_cost(1.9 * INSN_COST);
10936   format %{ "orrw  $dst, $src1, $src2, LSR $src3" %}
10937 
10938   ins_encode %{
10939     __ orrw(as_Register($dst$$reg),
10940               as_Register($src1$$reg),
10941               as_Register($src2$$reg),
10942               Assembler::LSR,
10943               $src3$$constant & 0x1f);
10944   %}
10945 
10946   ins_pipe(ialu_reg_reg_shift);
10947 %}
10948 
10949 instruct OrL_reg_URShift_reg(iRegLNoSp dst,
10950                          iRegL src1, iRegL src2,
10951                          immI src3, rFlagsReg cr) %{
10952   match(Set dst (OrL src1 (URShiftL src2 src3)));
10953 
10954   ins_cost(1.9 * INSN_COST);
10955   format %{ "orr  $dst, $src1, $src2, LSR $src3" %}
10956 
10957   ins_encode %{
10958     __ orr(as_Register($dst$$reg),
10959               as_Register($src1$$reg),
10960               as_Register($src2$$reg),
10961               Assembler::LSR,
10962               $src3$$constant & 0x3f);
10963   %}
10964 
10965   ins_pipe(ialu_reg_reg_shift);
10966 %}
10967 
10968 instruct OrI_reg_RShift_reg(iRegINoSp dst,
10969                          iRegIorL2I src1, iRegIorL2I src2,
10970                          immI src3, rFlagsReg cr) %{
10971   match(Set dst (OrI src1 (RShiftI src2 src3)));
10972 
10973   ins_cost(1.9 * INSN_COST);
10974   format %{ "orrw  $dst, $src1, $src2, ASR $src3" %}
10975 
10976   ins_encode %{
10977     __ orrw(as_Register($dst$$reg),
10978               as_Register($src1$$reg),
10979               as_Register($src2$$reg),
10980               Assembler::ASR,
10981               $src3$$constant & 0x1f);
10982   %}
10983 
10984   ins_pipe(ialu_reg_reg_shift);
10985 %}
10986 
10987 instruct OrL_reg_RShift_reg(iRegLNoSp dst,
10988                          iRegL src1, iRegL src2,
10989                          immI src3, rFlagsReg cr) %{
10990   match(Set dst (OrL src1 (RShiftL src2 src3)));
10991 
10992   ins_cost(1.9 * INSN_COST);
10993   format %{ "orr  $dst, $src1, $src2, ASR $src3" %}
10994 
10995   ins_encode %{
10996     __ orr(as_Register($dst$$reg),
10997               as_Register($src1$$reg),
10998               as_Register($src2$$reg),
10999               Assembler::ASR,
11000               $src3$$constant & 0x3f);
11001   %}
11002 
11003   ins_pipe(ialu_reg_reg_shift);
11004 %}
11005 
11006 instruct OrI_reg_LShift_reg(iRegINoSp dst,
11007                          iRegIorL2I src1, iRegIorL2I src2,
11008                          immI src3, rFlagsReg cr) %{
11009   match(Set dst (OrI src1 (LShiftI src2 src3)));
11010 
11011   ins_cost(1.9 * INSN_COST);
11012   format %{ "orrw  $dst, $src1, $src2, LSL $src3" %}
11013 
11014   ins_encode %{
11015     __ orrw(as_Register($dst$$reg),
11016               as_Register($src1$$reg),
11017               as_Register($src2$$reg),
11018               Assembler::LSL,
11019               $src3$$constant & 0x1f);
11020   %}
11021 
11022   ins_pipe(ialu_reg_reg_shift);
11023 %}
11024 
11025 instruct OrL_reg_LShift_reg(iRegLNoSp dst,
11026                          iRegL src1, iRegL src2,
11027                          immI src3, rFlagsReg cr) %{
11028   match(Set dst (OrL src1 (LShiftL src2 src3)));
11029 
11030   ins_cost(1.9 * INSN_COST);
11031   format %{ "orr  $dst, $src1, $src2, LSL $src3" %}
11032 
11033   ins_encode %{
11034     __ orr(as_Register($dst$$reg),
11035               as_Register($src1$$reg),
11036               as_Register($src2$$reg),
11037               Assembler::LSL,
11038               $src3$$constant & 0x3f);
11039   %}
11040 
11041   ins_pipe(ialu_reg_reg_shift);
11042 %}
11043 
11044 instruct AddI_reg_URShift_reg(iRegINoSp dst,
11045                          iRegIorL2I src1, iRegIorL2I src2,
11046                          immI src3, rFlagsReg cr) %{
11047   match(Set dst (AddI src1 (URShiftI src2 src3)));
11048 
11049   ins_cost(1.9 * INSN_COST);
11050   format %{ "addw  $dst, $src1, $src2, LSR $src3" %}
11051 
11052   ins_encode %{
11053     __ addw(as_Register($dst$$reg),
11054               as_Register($src1$$reg),
11055               as_Register($src2$$reg),
11056               Assembler::LSR,
11057               $src3$$constant & 0x1f);
11058   %}
11059 
11060   ins_pipe(ialu_reg_reg_shift);
11061 %}
11062 
11063 instruct AddL_reg_URShift_reg(iRegLNoSp dst,
11064                          iRegL src1, iRegL src2,
11065                          immI src3, rFlagsReg cr) %{
11066   match(Set dst (AddL src1 (URShiftL src2 src3)));
11067 
11068   ins_cost(1.9 * INSN_COST);
11069   format %{ "add  $dst, $src1, $src2, LSR $src3" %}
11070 
11071   ins_encode %{
11072     __ add(as_Register($dst$$reg),
11073               as_Register($src1$$reg),
11074               as_Register($src2$$reg),
11075               Assembler::LSR,
11076               $src3$$constant & 0x3f);
11077   %}
11078 
11079   ins_pipe(ialu_reg_reg_shift);
11080 %}
11081 
11082 instruct AddI_reg_RShift_reg(iRegINoSp dst,
11083                          iRegIorL2I src1, iRegIorL2I src2,
11084                          immI src3, rFlagsReg cr) %{
11085   match(Set dst (AddI src1 (RShiftI src2 src3)));
11086 
11087   ins_cost(1.9 * INSN_COST);
11088   format %{ "addw  $dst, $src1, $src2, ASR $src3" %}
11089 
11090   ins_encode %{
11091     __ addw(as_Register($dst$$reg),
11092               as_Register($src1$$reg),
11093               as_Register($src2$$reg),
11094               Assembler::ASR,
11095               $src3$$constant & 0x1f);
11096   %}
11097 
11098   ins_pipe(ialu_reg_reg_shift);
11099 %}
11100 
11101 instruct AddL_reg_RShift_reg(iRegLNoSp dst,
11102                          iRegL src1, iRegL src2,
11103                          immI src3, rFlagsReg cr) %{
11104   match(Set dst (AddL src1 (RShiftL src2 src3)));
11105 
11106   ins_cost(1.9 * INSN_COST);
11107   format %{ "add  $dst, $src1, $src2, ASR $src3" %}
11108 
11109   ins_encode %{
11110     __ add(as_Register($dst$$reg),
11111               as_Register($src1$$reg),
11112               as_Register($src2$$reg),
11113               Assembler::ASR,
11114               $src3$$constant & 0x3f);
11115   %}
11116 
11117   ins_pipe(ialu_reg_reg_shift);
11118 %}
11119 
11120 instruct AddI_reg_LShift_reg(iRegINoSp dst,
11121                          iRegIorL2I src1, iRegIorL2I src2,
11122                          immI src3, rFlagsReg cr) %{
11123   match(Set dst (AddI src1 (LShiftI src2 src3)));
11124 
11125   ins_cost(1.9 * INSN_COST);
11126   format %{ "addw  $dst, $src1, $src2, LSL $src3" %}
11127 
11128   ins_encode %{
11129     __ addw(as_Register($dst$$reg),
11130               as_Register($src1$$reg),
11131               as_Register($src2$$reg),
11132               Assembler::LSL,
11133               $src3$$constant & 0x1f);
11134   %}
11135 
11136   ins_pipe(ialu_reg_reg_shift);
11137 %}
11138 
11139 instruct AddL_reg_LShift_reg(iRegLNoSp dst,
11140                          iRegL src1, iRegL src2,
11141                          immI src3, rFlagsReg cr) %{
11142   match(Set dst (AddL src1 (LShiftL src2 src3)));
11143 
11144   ins_cost(1.9 * INSN_COST);
11145   format %{ "add  $dst, $src1, $src2, LSL $src3" %}
11146 
11147   ins_encode %{
11148     __ add(as_Register($dst$$reg),
11149               as_Register($src1$$reg),
11150               as_Register($src2$$reg),
11151               Assembler::LSL,
11152               $src3$$constant & 0x3f);
11153   %}
11154 
11155   ins_pipe(ialu_reg_reg_shift);
11156 %}
11157 
11158 instruct SubI_reg_URShift_reg(iRegINoSp dst,
11159                          iRegIorL2I src1, iRegIorL2I src2,
11160                          immI src3, rFlagsReg cr) %{
11161   match(Set dst (SubI src1 (URShiftI src2 src3)));
11162 
11163   ins_cost(1.9 * INSN_COST);
11164   format %{ "subw  $dst, $src1, $src2, LSR $src3" %}
11165 
11166   ins_encode %{
11167     __ subw(as_Register($dst$$reg),
11168               as_Register($src1$$reg),
11169               as_Register($src2$$reg),
11170               Assembler::LSR,
11171               $src3$$constant & 0x1f);
11172   %}
11173 
11174   ins_pipe(ialu_reg_reg_shift);
11175 %}
11176 
11177 instruct SubL_reg_URShift_reg(iRegLNoSp dst,
11178                          iRegL src1, iRegL src2,
11179                          immI src3, rFlagsReg cr) %{
11180   match(Set dst (SubL src1 (URShiftL src2 src3)));
11181 
11182   ins_cost(1.9 * INSN_COST);
11183   format %{ "sub  $dst, $src1, $src2, LSR $src3" %}
11184 
11185   ins_encode %{
11186     __ sub(as_Register($dst$$reg),
11187               as_Register($src1$$reg),
11188               as_Register($src2$$reg),
11189               Assembler::LSR,
11190               $src3$$constant & 0x3f);
11191   %}
11192 
11193   ins_pipe(ialu_reg_reg_shift);
11194 %}
11195 
11196 instruct SubI_reg_RShift_reg(iRegINoSp dst,
11197                          iRegIorL2I src1, iRegIorL2I src2,
11198                          immI src3, rFlagsReg cr) %{
11199   match(Set dst (SubI src1 (RShiftI src2 src3)));
11200 
11201   ins_cost(1.9 * INSN_COST);
11202   format %{ "subw  $dst, $src1, $src2, ASR $src3" %}
11203 
11204   ins_encode %{
11205     __ subw(as_Register($dst$$reg),
11206               as_Register($src1$$reg),
11207               as_Register($src2$$reg),
11208               Assembler::ASR,
11209               $src3$$constant & 0x1f);
11210   %}
11211 
11212   ins_pipe(ialu_reg_reg_shift);
11213 %}
11214 
11215 instruct SubL_reg_RShift_reg(iRegLNoSp dst,
11216                          iRegL src1, iRegL src2,
11217                          immI src3, rFlagsReg cr) %{
11218   match(Set dst (SubL src1 (RShiftL src2 src3)));
11219 
11220   ins_cost(1.9 * INSN_COST);
11221   format %{ "sub  $dst, $src1, $src2, ASR $src3" %}
11222 
11223   ins_encode %{
11224     __ sub(as_Register($dst$$reg),
11225               as_Register($src1$$reg),
11226               as_Register($src2$$reg),
11227               Assembler::ASR,
11228               $src3$$constant & 0x3f);
11229   %}
11230 
11231   ins_pipe(ialu_reg_reg_shift);
11232 %}
11233 
11234 instruct SubI_reg_LShift_reg(iRegINoSp dst,
11235                          iRegIorL2I src1, iRegIorL2I src2,
11236                          immI src3, rFlagsReg cr) %{
11237   match(Set dst (SubI src1 (LShiftI src2 src3)));
11238 
11239   ins_cost(1.9 * INSN_COST);
11240   format %{ "subw  $dst, $src1, $src2, LSL $src3" %}
11241 
11242   ins_encode %{
11243     __ subw(as_Register($dst$$reg),
11244               as_Register($src1$$reg),
11245               as_Register($src2$$reg),
11246               Assembler::LSL,
11247               $src3$$constant & 0x1f);
11248   %}
11249 
11250   ins_pipe(ialu_reg_reg_shift);
11251 %}
11252 
11253 instruct SubL_reg_LShift_reg(iRegLNoSp dst,
11254                          iRegL src1, iRegL src2,
11255                          immI src3, rFlagsReg cr) %{
11256   match(Set dst (SubL src1 (LShiftL src2 src3)));
11257 
11258   ins_cost(1.9 * INSN_COST);
11259   format %{ "sub  $dst, $src1, $src2, LSL $src3" %}
11260 
11261   ins_encode %{
11262     __ sub(as_Register($dst$$reg),
11263               as_Register($src1$$reg),
11264               as_Register($src2$$reg),
11265               Assembler::LSL,
11266               $src3$$constant & 0x3f);
11267   %}
11268 
11269   ins_pipe(ialu_reg_reg_shift);
11270 %}
11271 
11272 
11273 
11274 // Shift Left followed by Shift Right.
11275 // This idiom is used by the compiler for the i2b bytecode etc.
11276 instruct sbfmL(iRegLNoSp dst, iRegL src, immI lshift_count, immI rshift_count)
11277 %{
11278   match(Set dst (RShiftL (LShiftL src lshift_count) rshift_count));
11279   // Make sure we are not going to exceed what sbfm can do.
11280   predicate((unsigned int)n->in(2)->get_int() <= 63
11281             && (unsigned int)n->in(1)->in(2)->get_int() <= 63);
11282 
11283   ins_cost(INSN_COST * 2);
11284   format %{ "sbfm  $dst, $src, $rshift_count - $lshift_count, #63 - $lshift_count" %}
11285   ins_encode %{
11286     int lshift = $lshift_count$$constant, rshift = $rshift_count$$constant;
11287     int s = 63 - lshift;
11288     int r = (rshift - lshift) & 63;
11289     __ sbfm(as_Register($dst$$reg),
11290             as_Register($src$$reg),
11291             r, s);
11292   %}
11293 
11294   ins_pipe(ialu_reg_shift);
11295 %}
11296 
11297 // Shift Left followed by Shift Right.
11298 // This idiom is used by the compiler for the i2b bytecode etc.
11299 instruct sbfmwI(iRegINoSp dst, iRegIorL2I src, immI lshift_count, immI rshift_count)
11300 %{
11301   match(Set dst (RShiftI (LShiftI src lshift_count) rshift_count));
11302   // Make sure we are not going to exceed what sbfmw can do.
11303   predicate((unsigned int)n->in(2)->get_int() <= 31
11304             && (unsigned int)n->in(1)->in(2)->get_int() <= 31);
11305 
11306   ins_cost(INSN_COST * 2);
11307   format %{ "sbfmw  $dst, $src, $rshift_count - $lshift_count, #31 - $lshift_count" %}
11308   ins_encode %{
11309     int lshift = $lshift_count$$constant, rshift = $rshift_count$$constant;
11310     int s = 31 - lshift;
11311     int r = (rshift - lshift) & 31;
11312     __ sbfmw(as_Register($dst$$reg),
11313             as_Register($src$$reg),
11314             r, s);
11315   %}
11316 
11317   ins_pipe(ialu_reg_shift);
11318 %}
11319 
11320 // Shift Left followed by Shift Right.
11321 // This idiom is used by the compiler for the i2b bytecode etc.
11322 instruct ubfmL(iRegLNoSp dst, iRegL src, immI lshift_count, immI rshift_count)
11323 %{
11324   match(Set dst (URShiftL (LShiftL src lshift_count) rshift_count));
11325   // Make sure we are not going to exceed what ubfm can do.
11326   predicate((unsigned int)n->in(2)->get_int() <= 63
11327             && (unsigned int)n->in(1)->in(2)->get_int() <= 63);
11328 
11329   ins_cost(INSN_COST * 2);
11330   format %{ "ubfm  $dst, $src, $rshift_count - $lshift_count, #63 - $lshift_count" %}
11331   ins_encode %{
11332     int lshift = $lshift_count$$constant, rshift = $rshift_count$$constant;
11333     int s = 63 - lshift;
11334     int r = (rshift - lshift) & 63;
11335     __ ubfm(as_Register($dst$$reg),
11336             as_Register($src$$reg),
11337             r, s);
11338   %}
11339 
11340   ins_pipe(ialu_reg_shift);
11341 %}
11342 
11343 // Shift Left followed by Shift Right.
11344 // This idiom is used by the compiler for the i2b bytecode etc.
11345 instruct ubfmwI(iRegINoSp dst, iRegIorL2I src, immI lshift_count, immI rshift_count)
11346 %{
11347   match(Set dst (URShiftI (LShiftI src lshift_count) rshift_count));
11348   // Make sure we are not going to exceed what ubfmw can do.
11349   predicate((unsigned int)n->in(2)->get_int() <= 31
11350             && (unsigned int)n->in(1)->in(2)->get_int() <= 31);
11351 
11352   ins_cost(INSN_COST * 2);
11353   format %{ "ubfmw  $dst, $src, $rshift_count - $lshift_count, #31 - $lshift_count" %}
11354   ins_encode %{
11355     int lshift = $lshift_count$$constant, rshift = $rshift_count$$constant;
11356     int s = 31 - lshift;
11357     int r = (rshift - lshift) & 31;
11358     __ ubfmw(as_Register($dst$$reg),
11359             as_Register($src$$reg),
11360             r, s);
11361   %}
11362 
11363   ins_pipe(ialu_reg_shift);
11364 %}
11365 // Bitfield extract with shift & mask
11366 
11367 instruct ubfxwI(iRegINoSp dst, iRegIorL2I src, immI rshift, immI_bitmask mask)
11368 %{
11369   match(Set dst (AndI (URShiftI src rshift) mask));
11370 
11371   ins_cost(INSN_COST);
11372   format %{ "ubfxw $dst, $src, $rshift, $mask" %}
11373   ins_encode %{
11374     int rshift = $rshift$$constant;
11375     long mask = $mask$$constant;
11376     int width = exact_log2(mask+1);
11377     __ ubfxw(as_Register($dst$$reg),
11378             as_Register($src$$reg), rshift, width);
11379   %}
11380   ins_pipe(ialu_reg_shift);
11381 %}
11382 instruct ubfxL(iRegLNoSp dst, iRegL src, immI rshift, immL_bitmask mask)
11383 %{
11384   match(Set dst (AndL (URShiftL src rshift) mask));
11385 
11386   ins_cost(INSN_COST);
11387   format %{ "ubfx $dst, $src, $rshift, $mask" %}
11388   ins_encode %{
11389     int rshift = $rshift$$constant;
11390     long mask = $mask$$constant;
11391     int width = exact_log2(mask+1);
11392     __ ubfx(as_Register($dst$$reg),
11393             as_Register($src$$reg), rshift, width);
11394   %}
11395   ins_pipe(ialu_reg_shift);
11396 %}
11397 
11398 // We can use ubfx when extending an And with a mask when we know mask
11399 // is positive.  We know that because immI_bitmask guarantees it.
11400 instruct ubfxIConvI2L(iRegLNoSp dst, iRegIorL2I src, immI rshift, immI_bitmask mask)
11401 %{
11402   match(Set dst (ConvI2L (AndI (URShiftI src rshift) mask)));
11403 
11404   ins_cost(INSN_COST * 2);
11405   format %{ "ubfx $dst, $src, $rshift, $mask" %}
11406   ins_encode %{
11407     int rshift = $rshift$$constant;
11408     long mask = $mask$$constant;
11409     int width = exact_log2(mask+1);
11410     __ ubfx(as_Register($dst$$reg),
11411             as_Register($src$$reg), rshift, width);
11412   %}
11413   ins_pipe(ialu_reg_shift);
11414 %}
11415 
11416 // We can use ubfiz when masking by a positive number and then left shifting the result.
11417 // We know that the mask is positive because immI_bitmask guarantees it.
11418 instruct ubfizwI(iRegINoSp dst, iRegIorL2I src, immI lshift, immI_bitmask mask)
11419 %{
11420   match(Set dst (LShiftI (AndI src mask) lshift));
11421   predicate((unsigned int)n->in(2)->get_int() <= 31 &&
11422     (exact_log2(n->in(1)->in(2)->get_int()+1) + (unsigned int)n->in(2)->get_int()) <= (31+1));
11423 
11424   ins_cost(INSN_COST);
11425   format %{ "ubfizw $dst, $src, $lshift, $mask" %}
11426   ins_encode %{
11427     int lshift = $lshift$$constant;
11428     long mask = $mask$$constant;
11429     int width = exact_log2(mask+1);
11430     __ ubfizw(as_Register($dst$$reg),
11431           as_Register($src$$reg), lshift, width);
11432   %}
11433   ins_pipe(ialu_reg_shift);
11434 %}
11435 // We can use ubfiz when masking by a positive number and then left shifting the result.
11436 // We know that the mask is positive because immL_bitmask guarantees it.
11437 instruct ubfizL(iRegLNoSp dst, iRegL src, immI lshift, immL_bitmask mask)
11438 %{
11439   match(Set dst (LShiftL (AndL src mask) lshift));
11440   predicate((unsigned int)n->in(2)->get_int() <= 63 &&
11441     (exact_log2_long(n->in(1)->in(2)->get_long()+1) + (unsigned int)n->in(2)->get_int()) <= (63+1));
11442 
11443   ins_cost(INSN_COST);
11444   format %{ "ubfiz $dst, $src, $lshift, $mask" %}
11445   ins_encode %{
11446     int lshift = $lshift$$constant;
11447     long mask = $mask$$constant;
11448     int width = exact_log2(mask+1);
11449     __ ubfiz(as_Register($dst$$reg),
11450           as_Register($src$$reg), lshift, width);
11451   %}
11452   ins_pipe(ialu_reg_shift);
11453 %}
11454 
11455 // If there is a convert I to L block between and AndI and a LShiftL, we can also match ubfiz
11456 instruct ubfizIConvI2L(iRegLNoSp dst, iRegIorL2I src, immI lshift, immI_bitmask mask)
11457 %{
11458   match(Set dst (LShiftL (ConvI2L(AndI src mask)) lshift));
11459   predicate((unsigned int)n->in(2)->get_int() <= 31 &&
11460     (exact_log2((unsigned int)n->in(1)->in(1)->in(2)->get_int()+1) + (unsigned int)n->in(2)->get_int()) <= 32);
11461 
11462   ins_cost(INSN_COST);
11463   format %{ "ubfiz $dst, $src, $lshift, $mask" %}
11464   ins_encode %{
11465     int lshift = $lshift$$constant;
11466     long mask = $mask$$constant;
11467     int width = exact_log2(mask+1);
11468     __ ubfiz(as_Register($dst$$reg),
11469              as_Register($src$$reg), lshift, width);
11470   %}
11471   ins_pipe(ialu_reg_shift);
11472 %}
11473 
11474 // Rotations
11475 
11476 instruct extrOrL(iRegLNoSp dst, iRegL src1, iRegL src2, immI lshift, immI rshift, rFlagsReg cr)
11477 %{
11478   match(Set dst (OrL (LShiftL src1 lshift) (URShiftL src2 rshift)));
11479   predicate(0 == ((n->in(1)->in(2)->get_int() + n->in(2)->in(2)->get_int()) & 63));
11480 
11481   ins_cost(INSN_COST);
11482   format %{ "extr $dst, $src1, $src2, #$rshift" %}
11483 
11484   ins_encode %{
11485     __ extr(as_Register($dst$$reg), as_Register($src1$$reg), as_Register($src2$$reg),
11486             $rshift$$constant & 63);
11487   %}
11488   ins_pipe(ialu_reg_reg_extr);
11489 %}
11490 
11491 instruct extrOrI(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, immI lshift, immI rshift, rFlagsReg cr)
11492 %{
11493   match(Set dst (OrI (LShiftI src1 lshift) (URShiftI src2 rshift)));
11494   predicate(0 == ((n->in(1)->in(2)->get_int() + n->in(2)->in(2)->get_int()) & 31));
11495 
11496   ins_cost(INSN_COST);
11497   format %{ "extr $dst, $src1, $src2, #$rshift" %}
11498 
11499   ins_encode %{
11500     __ extrw(as_Register($dst$$reg), as_Register($src1$$reg), as_Register($src2$$reg),
11501             $rshift$$constant & 31);
11502   %}
11503   ins_pipe(ialu_reg_reg_extr);
11504 %}
11505 
11506 instruct extrAddL(iRegLNoSp dst, iRegL src1, iRegL src2, immI lshift, immI rshift, rFlagsReg cr)
11507 %{
11508   match(Set dst (AddL (LShiftL src1 lshift) (URShiftL src2 rshift)));
11509   predicate(0 == ((n->in(1)->in(2)->get_int() + n->in(2)->in(2)->get_int()) & 63));
11510 
11511   ins_cost(INSN_COST);
11512   format %{ "extr $dst, $src1, $src2, #$rshift" %}
11513 
11514   ins_encode %{
11515     __ extr(as_Register($dst$$reg), as_Register($src1$$reg), as_Register($src2$$reg),
11516             $rshift$$constant & 63);
11517   %}
11518   ins_pipe(ialu_reg_reg_extr);
11519 %}
11520 
11521 instruct extrAddI(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, immI lshift, immI rshift, rFlagsReg cr)
11522 %{
11523   match(Set dst (AddI (LShiftI src1 lshift) (URShiftI src2 rshift)));
11524   predicate(0 == ((n->in(1)->in(2)->get_int() + n->in(2)->in(2)->get_int()) & 31));
11525 
11526   ins_cost(INSN_COST);
11527   format %{ "extr $dst, $src1, $src2, #$rshift" %}
11528 
11529   ins_encode %{
11530     __ extrw(as_Register($dst$$reg), as_Register($src1$$reg), as_Register($src2$$reg),
11531             $rshift$$constant & 31);
11532   %}
11533   ins_pipe(ialu_reg_reg_extr);
11534 %}
11535 
11536 
11537 // rol expander
11538 
11539 instruct rolL_rReg(iRegLNoSp dst, iRegL src, iRegI shift, rFlagsReg cr)
11540 %{
11541   effect(DEF dst, USE src, USE shift);
11542 
11543   format %{ "rol    $dst, $src, $shift" %}
11544   ins_cost(INSN_COST * 3);
11545   ins_encode %{
11546     __ subw(rscratch1, zr, as_Register($shift$$reg));
11547     __ rorv(as_Register($dst$$reg), as_Register($src$$reg),
11548             rscratch1);
11549     %}
11550   ins_pipe(ialu_reg_reg_vshift);
11551 %}
11552 
11553 // rol expander
11554 
11555 instruct rolI_rReg(iRegINoSp dst, iRegI src, iRegI shift, rFlagsReg cr)
11556 %{
11557   effect(DEF dst, USE src, USE shift);
11558 
11559   format %{ "rol    $dst, $src, $shift" %}
11560   ins_cost(INSN_COST * 3);
11561   ins_encode %{
11562     __ subw(rscratch1, zr, as_Register($shift$$reg));
11563     __ rorvw(as_Register($dst$$reg), as_Register($src$$reg),
11564             rscratch1);
11565     %}
11566   ins_pipe(ialu_reg_reg_vshift);
11567 %}
11568 
11569 instruct rolL_rReg_Var_C_64(iRegLNoSp dst, iRegL src, iRegI shift, immI_64 c_64, rFlagsReg cr)
11570 %{
11571   match(Set dst (OrL (LShiftL src shift) (URShiftL src (SubI c_64 shift))));
11572 
11573   expand %{
11574     rolL_rReg(dst, src, shift, cr);
11575   %}
11576 %}
11577 
11578 instruct rolL_rReg_Var_C0(iRegLNoSp dst, iRegL src, iRegI shift, immI0 c0, rFlagsReg cr)
11579 %{
11580   match(Set dst (OrL (LShiftL src shift) (URShiftL src (SubI c0 shift))));
11581 
11582   expand %{
11583     rolL_rReg(dst, src, shift, cr);
11584   %}
11585 %}
11586 
11587 instruct rolI_rReg_Var_C_32(iRegINoSp dst, iRegI src, iRegI shift, immI_32 c_32, rFlagsReg cr)
11588 %{
11589   match(Set dst (OrI (LShiftI src shift) (URShiftI src (SubI c_32 shift))));
11590 
11591   expand %{
11592     rolI_rReg(dst, src, shift, cr);
11593   %}
11594 %}
11595 
11596 instruct rolI_rReg_Var_C0(iRegINoSp dst, iRegI src, iRegI shift, immI0 c0, rFlagsReg cr)
11597 %{
11598   match(Set dst (OrI (LShiftI src shift) (URShiftI src (SubI c0 shift))));
11599 
11600   expand %{
11601     rolI_rReg(dst, src, shift, cr);
11602   %}
11603 %}
11604 
11605 // ror expander
11606 
11607 instruct rorL_rReg(iRegLNoSp dst, iRegL src, iRegI shift, rFlagsReg cr)
11608 %{
11609   effect(DEF dst, USE src, USE shift);
11610 
11611   format %{ "ror    $dst, $src, $shift" %}
11612   ins_cost(INSN_COST);
11613   ins_encode %{
11614     __ rorv(as_Register($dst$$reg), as_Register($src$$reg),
11615             as_Register($shift$$reg));
11616     %}
11617   ins_pipe(ialu_reg_reg_vshift);
11618 %}
11619 
11620 // ror expander
11621 
11622 instruct rorI_rReg(iRegINoSp dst, iRegI src, iRegI shift, rFlagsReg cr)
11623 %{
11624   effect(DEF dst, USE src, USE shift);
11625 
11626   format %{ "ror    $dst, $src, $shift" %}
11627   ins_cost(INSN_COST);
11628   ins_encode %{
11629     __ rorvw(as_Register($dst$$reg), as_Register($src$$reg),
11630             as_Register($shift$$reg));
11631     %}
11632   ins_pipe(ialu_reg_reg_vshift);
11633 %}
11634 
11635 instruct rorL_rReg_Var_C_64(iRegLNoSp dst, iRegL src, iRegI shift, immI_64 c_64, rFlagsReg cr)
11636 %{
11637   match(Set dst (OrL (URShiftL src shift) (LShiftL src (SubI c_64 shift))));
11638 
11639   expand %{
11640     rorL_rReg(dst, src, shift, cr);
11641   %}
11642 %}
11643 
11644 instruct rorL_rReg_Var_C0(iRegLNoSp dst, iRegL src, iRegI shift, immI0 c0, rFlagsReg cr)
11645 %{
11646   match(Set dst (OrL (URShiftL src shift) (LShiftL src (SubI c0 shift))));
11647 
11648   expand %{
11649     rorL_rReg(dst, src, shift, cr);
11650   %}
11651 %}
11652 
11653 instruct rorI_rReg_Var_C_32(iRegINoSp dst, iRegI src, iRegI shift, immI_32 c_32, rFlagsReg cr)
11654 %{
11655   match(Set dst (OrI (URShiftI src shift) (LShiftI src (SubI c_32 shift))));
11656 
11657   expand %{
11658     rorI_rReg(dst, src, shift, cr);
11659   %}
11660 %}
11661 
11662 instruct rorI_rReg_Var_C0(iRegINoSp dst, iRegI src, iRegI shift, immI0 c0, rFlagsReg cr)
11663 %{
11664   match(Set dst (OrI (URShiftI src shift) (LShiftI src (SubI c0 shift))));
11665 
11666   expand %{
11667     rorI_rReg(dst, src, shift, cr);
11668   %}
11669 %}
11670 
11671 // Add/subtract (extended)
11672 
11673 instruct AddExtI(iRegLNoSp dst, iRegL src1, iRegIorL2I src2, rFlagsReg cr)
11674 %{
11675   match(Set dst (AddL src1 (ConvI2L src2)));
11676   ins_cost(INSN_COST);
11677   format %{ "add  $dst, $src1, $src2, sxtw" %}
11678 
11679    ins_encode %{
11680      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
11681             as_Register($src2$$reg), ext::sxtw);
11682    %}
11683   ins_pipe(ialu_reg_reg);
11684 %};
11685 
11686 instruct SubExtI(iRegLNoSp dst, iRegL src1, iRegIorL2I src2, rFlagsReg cr)
11687 %{
11688   match(Set dst (SubL src1 (ConvI2L src2)));
11689   ins_cost(INSN_COST);
11690   format %{ "sub  $dst, $src1, $src2, sxtw" %}
11691 
11692    ins_encode %{
11693      __ sub(as_Register($dst$$reg), as_Register($src1$$reg),
11694             as_Register($src2$$reg), ext::sxtw);
11695    %}
11696   ins_pipe(ialu_reg_reg);
11697 %};
11698 
11699 
11700 instruct AddExtI_sxth(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, immI_16 lshift, immI_16 rshift, rFlagsReg cr)
11701 %{
11702   match(Set dst (AddI src1 (RShiftI (LShiftI src2 lshift) rshift)));
11703   ins_cost(INSN_COST);
11704   format %{ "add  $dst, $src1, $src2, sxth" %}
11705 
11706    ins_encode %{
11707      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
11708             as_Register($src2$$reg), ext::sxth);
11709    %}
11710   ins_pipe(ialu_reg_reg);
11711 %}
11712 
11713 instruct AddExtI_sxtb(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, immI_24 lshift, immI_24 rshift, rFlagsReg cr)
11714 %{
11715   match(Set dst (AddI src1 (RShiftI (LShiftI src2 lshift) rshift)));
11716   ins_cost(INSN_COST);
11717   format %{ "add  $dst, $src1, $src2, sxtb" %}
11718 
11719    ins_encode %{
11720      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
11721             as_Register($src2$$reg), ext::sxtb);
11722    %}
11723   ins_pipe(ialu_reg_reg);
11724 %}
11725 
11726 instruct AddExtI_uxtb(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, immI_24 lshift, immI_24 rshift, rFlagsReg cr)
11727 %{
11728   match(Set dst (AddI src1 (URShiftI (LShiftI src2 lshift) rshift)));
11729   ins_cost(INSN_COST);
11730   format %{ "add  $dst, $src1, $src2, uxtb" %}
11731 
11732    ins_encode %{
11733      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
11734             as_Register($src2$$reg), ext::uxtb);
11735    %}
11736   ins_pipe(ialu_reg_reg);
11737 %}
11738 
11739 instruct AddExtL_sxth(iRegLNoSp dst, iRegL src1, iRegL src2, immI_48 lshift, immI_48 rshift, rFlagsReg cr)
11740 %{
11741   match(Set dst (AddL src1 (RShiftL (LShiftL src2 lshift) rshift)));
11742   ins_cost(INSN_COST);
11743   format %{ "add  $dst, $src1, $src2, sxth" %}
11744 
11745    ins_encode %{
11746      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
11747             as_Register($src2$$reg), ext::sxth);
11748    %}
11749   ins_pipe(ialu_reg_reg);
11750 %}
11751 
11752 instruct AddExtL_sxtw(iRegLNoSp dst, iRegL src1, iRegL src2, immI_32 lshift, immI_32 rshift, rFlagsReg cr)
11753 %{
11754   match(Set dst (AddL src1 (RShiftL (LShiftL src2 lshift) rshift)));
11755   ins_cost(INSN_COST);
11756   format %{ "add  $dst, $src1, $src2, sxtw" %}
11757 
11758    ins_encode %{
11759      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
11760             as_Register($src2$$reg), ext::sxtw);
11761    %}
11762   ins_pipe(ialu_reg_reg);
11763 %}
11764 
11765 instruct AddExtL_sxtb(iRegLNoSp dst, iRegL src1, iRegL src2, immI_56 lshift, immI_56 rshift, rFlagsReg cr)
11766 %{
11767   match(Set dst (AddL src1 (RShiftL (LShiftL src2 lshift) rshift)));
11768   ins_cost(INSN_COST);
11769   format %{ "add  $dst, $src1, $src2, sxtb" %}
11770 
11771    ins_encode %{
11772      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
11773             as_Register($src2$$reg), ext::sxtb);
11774    %}
11775   ins_pipe(ialu_reg_reg);
11776 %}
11777 
11778 instruct AddExtL_uxtb(iRegLNoSp dst, iRegL src1, iRegL src2, immI_56 lshift, immI_56 rshift, rFlagsReg cr)
11779 %{
11780   match(Set dst (AddL src1 (URShiftL (LShiftL src2 lshift) rshift)));
11781   ins_cost(INSN_COST);
11782   format %{ "add  $dst, $src1, $src2, uxtb" %}
11783 
11784    ins_encode %{
11785      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
11786             as_Register($src2$$reg), ext::uxtb);
11787    %}
11788   ins_pipe(ialu_reg_reg);
11789 %}
11790 
11791 
11792 instruct AddExtI_uxtb_and(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, immI_255 mask, rFlagsReg cr)
11793 %{
11794   match(Set dst (AddI src1 (AndI src2 mask)));
11795   ins_cost(INSN_COST);
11796   format %{ "addw  $dst, $src1, $src2, uxtb" %}
11797 
11798    ins_encode %{
11799      __ addw(as_Register($dst$$reg), as_Register($src1$$reg),
11800             as_Register($src2$$reg), ext::uxtb);
11801    %}
11802   ins_pipe(ialu_reg_reg);
11803 %}
11804 
11805 instruct AddExtI_uxth_and(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, immI_65535 mask, rFlagsReg cr)
11806 %{
11807   match(Set dst (AddI src1 (AndI src2 mask)));
11808   ins_cost(INSN_COST);
11809   format %{ "addw  $dst, $src1, $src2, uxth" %}
11810 
11811    ins_encode %{
11812      __ addw(as_Register($dst$$reg), as_Register($src1$$reg),
11813             as_Register($src2$$reg), ext::uxth);
11814    %}
11815   ins_pipe(ialu_reg_reg);
11816 %}
11817 
11818 instruct AddExtL_uxtb_and(iRegLNoSp dst, iRegL src1, iRegL src2, immL_255 mask, rFlagsReg cr)
11819 %{
11820   match(Set dst (AddL src1 (AndL src2 mask)));
11821   ins_cost(INSN_COST);
11822   format %{ "add  $dst, $src1, $src2, uxtb" %}
11823 
11824    ins_encode %{
11825      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
11826             as_Register($src2$$reg), ext::uxtb);
11827    %}
11828   ins_pipe(ialu_reg_reg);
11829 %}
11830 
11831 instruct AddExtL_uxth_and(iRegLNoSp dst, iRegL src1, iRegL src2, immL_65535 mask, rFlagsReg cr)
11832 %{
11833   match(Set dst (AddL src1 (AndL src2 mask)));
11834   ins_cost(INSN_COST);
11835   format %{ "add  $dst, $src1, $src2, uxth" %}
11836 
11837    ins_encode %{
11838      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
11839             as_Register($src2$$reg), ext::uxth);
11840    %}
11841   ins_pipe(ialu_reg_reg);
11842 %}
11843 
11844 instruct AddExtL_uxtw_and(iRegLNoSp dst, iRegL src1, iRegL src2, immL_4294967295 mask, rFlagsReg cr)
11845 %{
11846   match(Set dst (AddL src1 (AndL src2 mask)));
11847   ins_cost(INSN_COST);
11848   format %{ "add  $dst, $src1, $src2, uxtw" %}
11849 
11850    ins_encode %{
11851      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
11852             as_Register($src2$$reg), ext::uxtw);
11853    %}
11854   ins_pipe(ialu_reg_reg);
11855 %}
11856 
11857 instruct SubExtI_uxtb_and(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, immI_255 mask, rFlagsReg cr)
11858 %{
11859   match(Set dst (SubI src1 (AndI src2 mask)));
11860   ins_cost(INSN_COST);
11861   format %{ "subw  $dst, $src1, $src2, uxtb" %}
11862 
11863    ins_encode %{
11864      __ subw(as_Register($dst$$reg), as_Register($src1$$reg),
11865             as_Register($src2$$reg), ext::uxtb);
11866    %}
11867   ins_pipe(ialu_reg_reg);
11868 %}
11869 
11870 instruct SubExtI_uxth_and(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, immI_65535 mask, rFlagsReg cr)
11871 %{
11872   match(Set dst (SubI src1 (AndI src2 mask)));
11873   ins_cost(INSN_COST);
11874   format %{ "subw  $dst, $src1, $src2, uxth" %}
11875 
11876    ins_encode %{
11877      __ subw(as_Register($dst$$reg), as_Register($src1$$reg),
11878             as_Register($src2$$reg), ext::uxth);
11879    %}
11880   ins_pipe(ialu_reg_reg);
11881 %}
11882 
11883 instruct SubExtL_uxtb_and(iRegLNoSp dst, iRegL src1, iRegL src2, immL_255 mask, rFlagsReg cr)
11884 %{
11885   match(Set dst (SubL src1 (AndL src2 mask)));
11886   ins_cost(INSN_COST);
11887   format %{ "sub  $dst, $src1, $src2, uxtb" %}
11888 
11889    ins_encode %{
11890      __ sub(as_Register($dst$$reg), as_Register($src1$$reg),
11891             as_Register($src2$$reg), ext::uxtb);
11892    %}
11893   ins_pipe(ialu_reg_reg);
11894 %}
11895 
11896 instruct SubExtL_uxth_and(iRegLNoSp dst, iRegL src1, iRegL src2, immL_65535 mask, rFlagsReg cr)
11897 %{
11898   match(Set dst (SubL src1 (AndL src2 mask)));
11899   ins_cost(INSN_COST);
11900   format %{ "sub  $dst, $src1, $src2, uxth" %}
11901 
11902    ins_encode %{
11903      __ sub(as_Register($dst$$reg), as_Register($src1$$reg),
11904             as_Register($src2$$reg), ext::uxth);
11905    %}
11906   ins_pipe(ialu_reg_reg);
11907 %}
11908 
11909 instruct SubExtL_uxtw_and(iRegLNoSp dst, iRegL src1, iRegL src2, immL_4294967295 mask, rFlagsReg cr)
11910 %{
11911   match(Set dst (SubL src1 (AndL src2 mask)));
11912   ins_cost(INSN_COST);
11913   format %{ "sub  $dst, $src1, $src2, uxtw" %}
11914 
11915    ins_encode %{
11916      __ sub(as_Register($dst$$reg), as_Register($src1$$reg),
11917             as_Register($src2$$reg), ext::uxtw);
11918    %}
11919   ins_pipe(ialu_reg_reg);
11920 %}
11921 
11922 
11923 instruct AddExtL_sxtb_shift(iRegLNoSp dst, iRegL src1, iRegL src2, immIExt lshift2, immI_56 lshift1, immI_56 rshift1, rFlagsReg cr)
11924 %{
11925   match(Set dst (AddL src1 (LShiftL (RShiftL (LShiftL src2 lshift1) rshift1) lshift2)));
11926   ins_cost(1.9 * INSN_COST);
11927   format %{ "add  $dst, $src1, $src2, sxtb #lshift2" %}
11928 
11929    ins_encode %{
11930      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
11931             as_Register($src2$$reg), ext::sxtb, ($lshift2$$constant));
11932    %}
11933   ins_pipe(ialu_reg_reg_shift);
11934 %}
11935 
11936 instruct AddExtL_sxth_shift(iRegLNoSp dst, iRegL src1, iRegL src2, immIExt lshift2, immI_48 lshift1, immI_48 rshift1, rFlagsReg cr)
11937 %{
11938   match(Set dst (AddL src1 (LShiftL (RShiftL (LShiftL src2 lshift1) rshift1) lshift2)));
11939   ins_cost(1.9 * INSN_COST);
11940   format %{ "add  $dst, $src1, $src2, sxth #lshift2" %}
11941 
11942    ins_encode %{
11943      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
11944             as_Register($src2$$reg), ext::sxth, ($lshift2$$constant));
11945    %}
11946   ins_pipe(ialu_reg_reg_shift);
11947 %}
11948 
11949 instruct AddExtL_sxtw_shift(iRegLNoSp dst, iRegL src1, iRegL src2, immIExt lshift2, immI_32 lshift1, immI_32 rshift1, rFlagsReg cr)
11950 %{
11951   match(Set dst (AddL src1 (LShiftL (RShiftL (LShiftL src2 lshift1) rshift1) lshift2)));
11952   ins_cost(1.9 * INSN_COST);
11953   format %{ "add  $dst, $src1, $src2, sxtw #lshift2" %}
11954 
11955    ins_encode %{
11956      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
11957             as_Register($src2$$reg), ext::sxtw, ($lshift2$$constant));
11958    %}
11959   ins_pipe(ialu_reg_reg_shift);
11960 %}
11961 
11962 instruct SubExtL_sxtb_shift(iRegLNoSp dst, iRegL src1, iRegL src2, immIExt lshift2, immI_56 lshift1, immI_56 rshift1, rFlagsReg cr)
11963 %{
11964   match(Set dst (SubL src1 (LShiftL (RShiftL (LShiftL src2 lshift1) rshift1) lshift2)));
11965   ins_cost(1.9 * INSN_COST);
11966   format %{ "sub  $dst, $src1, $src2, sxtb #lshift2" %}
11967 
11968    ins_encode %{
11969      __ sub(as_Register($dst$$reg), as_Register($src1$$reg),
11970             as_Register($src2$$reg), ext::sxtb, ($lshift2$$constant));
11971    %}
11972   ins_pipe(ialu_reg_reg_shift);
11973 %}
11974 
11975 instruct SubExtL_sxth_shift(iRegLNoSp dst, iRegL src1, iRegL src2, immIExt lshift2, immI_48 lshift1, immI_48 rshift1, rFlagsReg cr)
11976 %{
11977   match(Set dst (SubL src1 (LShiftL (RShiftL (LShiftL src2 lshift1) rshift1) lshift2)));
11978   ins_cost(1.9 * INSN_COST);
11979   format %{ "sub  $dst, $src1, $src2, sxth #lshift2" %}
11980 
11981    ins_encode %{
11982      __ sub(as_Register($dst$$reg), as_Register($src1$$reg),
11983             as_Register($src2$$reg), ext::sxth, ($lshift2$$constant));
11984    %}
11985   ins_pipe(ialu_reg_reg_shift);
11986 %}
11987 
11988 instruct SubExtL_sxtw_shift(iRegLNoSp dst, iRegL src1, iRegL src2, immIExt lshift2, immI_32 lshift1, immI_32 rshift1, rFlagsReg cr)
11989 %{
11990   match(Set dst (SubL src1 (LShiftL (RShiftL (LShiftL src2 lshift1) rshift1) lshift2)));
11991   ins_cost(1.9 * INSN_COST);
11992   format %{ "sub  $dst, $src1, $src2, sxtw #lshift2" %}
11993 
11994    ins_encode %{
11995      __ sub(as_Register($dst$$reg), as_Register($src1$$reg),
11996             as_Register($src2$$reg), ext::sxtw, ($lshift2$$constant));
11997    %}
11998   ins_pipe(ialu_reg_reg_shift);
11999 %}
12000 
12001 instruct AddExtI_sxtb_shift(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, immIExt lshift2, immI_24 lshift1, immI_24 rshift1, rFlagsReg cr)
12002 %{
12003   match(Set dst (AddI src1 (LShiftI (RShiftI (LShiftI src2 lshift1) rshift1) lshift2)));
12004   ins_cost(1.9 * INSN_COST);
12005   format %{ "addw  $dst, $src1, $src2, sxtb #lshift2" %}
12006 
12007    ins_encode %{
12008      __ addw(as_Register($dst$$reg), as_Register($src1$$reg),
12009             as_Register($src2$$reg), ext::sxtb, ($lshift2$$constant));
12010    %}
12011   ins_pipe(ialu_reg_reg_shift);
12012 %}
12013 
12014 instruct AddExtI_sxth_shift(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, immIExt lshift2, immI_16 lshift1, immI_16 rshift1, rFlagsReg cr)
12015 %{
12016   match(Set dst (AddI src1 (LShiftI (RShiftI (LShiftI src2 lshift1) rshift1) lshift2)));
12017   ins_cost(1.9 * INSN_COST);
12018   format %{ "addw  $dst, $src1, $src2, sxth #lshift2" %}
12019 
12020    ins_encode %{
12021      __ addw(as_Register($dst$$reg), as_Register($src1$$reg),
12022             as_Register($src2$$reg), ext::sxth, ($lshift2$$constant));
12023    %}
12024   ins_pipe(ialu_reg_reg_shift);
12025 %}
12026 
12027 instruct SubExtI_sxtb_shift(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, immIExt lshift2, immI_24 lshift1, immI_24 rshift1, rFlagsReg cr)
12028 %{
12029   match(Set dst (SubI src1 (LShiftI (RShiftI (LShiftI src2 lshift1) rshift1) lshift2)));
12030   ins_cost(1.9 * INSN_COST);
12031   format %{ "subw  $dst, $src1, $src2, sxtb #lshift2" %}
12032 
12033    ins_encode %{
12034      __ subw(as_Register($dst$$reg), as_Register($src1$$reg),
12035             as_Register($src2$$reg), ext::sxtb, ($lshift2$$constant));
12036    %}
12037   ins_pipe(ialu_reg_reg_shift);
12038 %}
12039 
12040 instruct SubExtI_sxth_shift(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, immIExt lshift2, immI_16 lshift1, immI_16 rshift1, rFlagsReg cr)
12041 %{
12042   match(Set dst (SubI src1 (LShiftI (RShiftI (LShiftI src2 lshift1) rshift1) lshift2)));
12043   ins_cost(1.9 * INSN_COST);
12044   format %{ "subw  $dst, $src1, $src2, sxth #lshift2" %}
12045 
12046    ins_encode %{
12047      __ subw(as_Register($dst$$reg), as_Register($src1$$reg),
12048             as_Register($src2$$reg), ext::sxth, ($lshift2$$constant));
12049    %}
12050   ins_pipe(ialu_reg_reg_shift);
12051 %}
12052 
12053 
12054 instruct AddExtI_shift(iRegLNoSp dst, iRegL src1, iRegIorL2I src2, immIExt lshift, rFlagsReg cr)
12055 %{
12056   match(Set dst (AddL src1 (LShiftL (ConvI2L src2) lshift)));
12057   ins_cost(1.9 * INSN_COST);
12058   format %{ "add  $dst, $src1, $src2, sxtw #lshift" %}
12059 
12060    ins_encode %{
12061      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
12062             as_Register($src2$$reg), ext::sxtw, ($lshift$$constant));
12063    %}
12064   ins_pipe(ialu_reg_reg_shift);
12065 %};
12066 
12067 instruct SubExtI_shift(iRegLNoSp dst, iRegL src1, iRegIorL2I src2, immIExt lshift, rFlagsReg cr)
12068 %{
12069   match(Set dst (SubL src1 (LShiftL (ConvI2L src2) lshift)));
12070   ins_cost(1.9 * INSN_COST);
12071   format %{ "sub  $dst, $src1, $src2, sxtw #lshift" %}
12072 
12073    ins_encode %{
12074      __ sub(as_Register($dst$$reg), as_Register($src1$$reg),
12075             as_Register($src2$$reg), ext::sxtw, ($lshift$$constant));
12076    %}
12077   ins_pipe(ialu_reg_reg_shift);
12078 %};
12079 
12080 
12081 instruct AddExtL_uxtb_and_shift(iRegLNoSp dst, iRegL src1, iRegL src2, immL_255 mask, immIExt lshift, rFlagsReg cr)
12082 %{
12083   match(Set dst (AddL src1 (LShiftL (AndL src2 mask) lshift)));
12084   ins_cost(1.9 * INSN_COST);
12085   format %{ "add  $dst, $src1, $src2, uxtb #lshift" %}
12086 
12087    ins_encode %{
12088      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
12089             as_Register($src2$$reg), ext::uxtb, ($lshift$$constant));
12090    %}
12091   ins_pipe(ialu_reg_reg_shift);
12092 %}
12093 
12094 instruct AddExtL_uxth_and_shift(iRegLNoSp dst, iRegL src1, iRegL src2, immL_65535 mask, immIExt lshift, rFlagsReg cr)
12095 %{
12096   match(Set dst (AddL src1 (LShiftL (AndL src2 mask) lshift)));
12097   ins_cost(1.9 * INSN_COST);
12098   format %{ "add  $dst, $src1, $src2, uxth #lshift" %}
12099 
12100    ins_encode %{
12101      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
12102             as_Register($src2$$reg), ext::uxth, ($lshift$$constant));
12103    %}
12104   ins_pipe(ialu_reg_reg_shift);
12105 %}
12106 
12107 instruct AddExtL_uxtw_and_shift(iRegLNoSp dst, iRegL src1, iRegL src2, immL_4294967295 mask, immIExt lshift, rFlagsReg cr)
12108 %{
12109   match(Set dst (AddL src1 (LShiftL (AndL src2 mask) lshift)));
12110   ins_cost(1.9 * INSN_COST);
12111   format %{ "add  $dst, $src1, $src2, uxtw #lshift" %}
12112 
12113    ins_encode %{
12114      __ add(as_Register($dst$$reg), as_Register($src1$$reg),
12115             as_Register($src2$$reg), ext::uxtw, ($lshift$$constant));
12116    %}
12117   ins_pipe(ialu_reg_reg_shift);
12118 %}
12119 
12120 instruct SubExtL_uxtb_and_shift(iRegLNoSp dst, iRegL src1, iRegL src2, immL_255 mask, immIExt lshift, rFlagsReg cr)
12121 %{
12122   match(Set dst (SubL src1 (LShiftL (AndL src2 mask) lshift)));
12123   ins_cost(1.9 * INSN_COST);
12124   format %{ "sub  $dst, $src1, $src2, uxtb #lshift" %}
12125 
12126    ins_encode %{
12127      __ sub(as_Register($dst$$reg), as_Register($src1$$reg),
12128             as_Register($src2$$reg), ext::uxtb, ($lshift$$constant));
12129    %}
12130   ins_pipe(ialu_reg_reg_shift);
12131 %}
12132 
12133 instruct SubExtL_uxth_and_shift(iRegLNoSp dst, iRegL src1, iRegL src2, immL_65535 mask, immIExt lshift, rFlagsReg cr)
12134 %{
12135   match(Set dst (SubL src1 (LShiftL (AndL src2 mask) lshift)));
12136   ins_cost(1.9 * INSN_COST);
12137   format %{ "sub  $dst, $src1, $src2, uxth #lshift" %}
12138 
12139    ins_encode %{
12140      __ sub(as_Register($dst$$reg), as_Register($src1$$reg),
12141             as_Register($src2$$reg), ext::uxth, ($lshift$$constant));
12142    %}
12143   ins_pipe(ialu_reg_reg_shift);
12144 %}
12145 
12146 instruct SubExtL_uxtw_and_shift(iRegLNoSp dst, iRegL src1, iRegL src2, immL_4294967295 mask, immIExt lshift, rFlagsReg cr)
12147 %{
12148   match(Set dst (SubL src1 (LShiftL (AndL src2 mask) lshift)));
12149   ins_cost(1.9 * INSN_COST);
12150   format %{ "sub  $dst, $src1, $src2, uxtw #lshift" %}
12151 
12152    ins_encode %{
12153      __ sub(as_Register($dst$$reg), as_Register($src1$$reg),
12154             as_Register($src2$$reg), ext::uxtw, ($lshift$$constant));
12155    %}
12156   ins_pipe(ialu_reg_reg_shift);
12157 %}
12158 
12159 instruct AddExtI_uxtb_and_shift(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, immI_255 mask, immIExt lshift, rFlagsReg cr)
12160 %{
12161   match(Set dst (AddI src1 (LShiftI (AndI src2 mask) lshift)));
12162   ins_cost(1.9 * INSN_COST);
12163   format %{ "addw  $dst, $src1, $src2, uxtb #lshift" %}
12164 
12165    ins_encode %{
12166      __ addw(as_Register($dst$$reg), as_Register($src1$$reg),
12167             as_Register($src2$$reg), ext::uxtb, ($lshift$$constant));
12168    %}
12169   ins_pipe(ialu_reg_reg_shift);
12170 %}
12171 
12172 instruct AddExtI_uxth_and_shift(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, immI_65535 mask, immIExt lshift, rFlagsReg cr)
12173 %{
12174   match(Set dst (AddI src1 (LShiftI (AndI src2 mask) lshift)));
12175   ins_cost(1.9 * INSN_COST);
12176   format %{ "addw  $dst, $src1, $src2, uxth #lshift" %}
12177 
12178    ins_encode %{
12179      __ addw(as_Register($dst$$reg), as_Register($src1$$reg),
12180             as_Register($src2$$reg), ext::uxth, ($lshift$$constant));
12181    %}
12182   ins_pipe(ialu_reg_reg_shift);
12183 %}
12184 
12185 instruct SubExtI_uxtb_and_shift(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, immI_255 mask, immIExt lshift, rFlagsReg cr)
12186 %{
12187   match(Set dst (SubI src1 (LShiftI (AndI src2 mask) lshift)));
12188   ins_cost(1.9 * INSN_COST);
12189   format %{ "subw  $dst, $src1, $src2, uxtb #lshift" %}
12190 
12191    ins_encode %{
12192      __ subw(as_Register($dst$$reg), as_Register($src1$$reg),
12193             as_Register($src2$$reg), ext::uxtb, ($lshift$$constant));
12194    %}
12195   ins_pipe(ialu_reg_reg_shift);
12196 %}
12197 
12198 instruct SubExtI_uxth_and_shift(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, immI_65535 mask, immIExt lshift, rFlagsReg cr)
12199 %{
12200   match(Set dst (SubI src1 (LShiftI (AndI src2 mask) lshift)));
12201   ins_cost(1.9 * INSN_COST);
12202   format %{ "subw  $dst, $src1, $src2, uxth #lshift" %}
12203 
12204    ins_encode %{
12205      __ subw(as_Register($dst$$reg), as_Register($src1$$reg),
12206             as_Register($src2$$reg), ext::uxth, ($lshift$$constant));
12207    %}
12208   ins_pipe(ialu_reg_reg_shift);
12209 %}
12210 // END This section of the file is automatically generated. Do not edit --------------
12211 
12212 // ============================================================================
12213 // Floating Point Arithmetic Instructions
12214 
12215 instruct addF_reg_reg(vRegF dst, vRegF src1, vRegF src2) %{
12216   match(Set dst (AddF src1 src2));
12217 
12218   ins_cost(INSN_COST * 5);
12219   format %{ "fadds   $dst, $src1, $src2" %}
12220 
12221   ins_encode %{
12222     __ fadds(as_FloatRegister($dst$$reg),
12223              as_FloatRegister($src1$$reg),
12224              as_FloatRegister($src2$$reg));
12225   %}
12226 
12227   ins_pipe(fp_dop_reg_reg_s);
12228 %}
12229 
12230 instruct addD_reg_reg(vRegD dst, vRegD src1, vRegD src2) %{
12231   match(Set dst (AddD src1 src2));
12232 
12233   ins_cost(INSN_COST * 5);
12234   format %{ "faddd   $dst, $src1, $src2" %}
12235 
12236   ins_encode %{
12237     __ faddd(as_FloatRegister($dst$$reg),
12238              as_FloatRegister($src1$$reg),
12239              as_FloatRegister($src2$$reg));
12240   %}
12241 
12242   ins_pipe(fp_dop_reg_reg_d);
12243 %}
12244 
12245 instruct subF_reg_reg(vRegF dst, vRegF src1, vRegF src2) %{
12246   match(Set dst (SubF src1 src2));
12247 
12248   ins_cost(INSN_COST * 5);
12249   format %{ "fsubs   $dst, $src1, $src2" %}
12250 
12251   ins_encode %{
12252     __ fsubs(as_FloatRegister($dst$$reg),
12253              as_FloatRegister($src1$$reg),
12254              as_FloatRegister($src2$$reg));
12255   %}
12256 
12257   ins_pipe(fp_dop_reg_reg_s);
12258 %}
12259 
12260 instruct subD_reg_reg(vRegD dst, vRegD src1, vRegD src2) %{
12261   match(Set dst (SubD src1 src2));
12262 
12263   ins_cost(INSN_COST * 5);
12264   format %{ "fsubd   $dst, $src1, $src2" %}
12265 
12266   ins_encode %{
12267     __ fsubd(as_FloatRegister($dst$$reg),
12268              as_FloatRegister($src1$$reg),
12269              as_FloatRegister($src2$$reg));
12270   %}
12271 
12272   ins_pipe(fp_dop_reg_reg_d);
12273 %}
12274 
12275 instruct mulF_reg_reg(vRegF dst, vRegF src1, vRegF src2) %{
12276   match(Set dst (MulF src1 src2));
12277 
12278   ins_cost(INSN_COST * 6);
12279   format %{ "fmuls   $dst, $src1, $src2" %}
12280 
12281   ins_encode %{
12282     __ fmuls(as_FloatRegister($dst$$reg),
12283              as_FloatRegister($src1$$reg),
12284              as_FloatRegister($src2$$reg));
12285   %}
12286 
12287   ins_pipe(fp_dop_reg_reg_s);
12288 %}
12289 
12290 instruct mulD_reg_reg(vRegD dst, vRegD src1, vRegD src2) %{
12291   match(Set dst (MulD src1 src2));
12292 
12293   ins_cost(INSN_COST * 6);
12294   format %{ "fmuld   $dst, $src1, $src2" %}
12295 
12296   ins_encode %{
12297     __ fmuld(as_FloatRegister($dst$$reg),
12298              as_FloatRegister($src1$$reg),
12299              as_FloatRegister($src2$$reg));
12300   %}
12301 
12302   ins_pipe(fp_dop_reg_reg_d);
12303 %}
12304 
12305 // src1 * src2 + src3
12306 instruct maddF_reg_reg(vRegF dst, vRegF src1, vRegF src2, vRegF src3) %{
12307   predicate(UseFMA);
12308   match(Set dst (FmaF src3 (Binary src1 src2)));
12309 
12310   format %{ "fmadds   $dst, $src1, $src2, $src3" %}
12311 
12312   ins_encode %{
12313     __ fmadds(as_FloatRegister($dst$$reg),
12314              as_FloatRegister($src1$$reg),
12315              as_FloatRegister($src2$$reg),
12316              as_FloatRegister($src3$$reg));
12317   %}
12318 
12319   ins_pipe(pipe_class_default);
12320 %}
12321 
12322 // src1 * src2 + src3
12323 instruct maddD_reg_reg(vRegD dst, vRegD src1, vRegD src2, vRegD src3) %{
12324   predicate(UseFMA);
12325   match(Set dst (FmaD src3 (Binary src1 src2)));
12326 
12327   format %{ "fmaddd   $dst, $src1, $src2, $src3" %}
12328 
12329   ins_encode %{
12330     __ fmaddd(as_FloatRegister($dst$$reg),
12331              as_FloatRegister($src1$$reg),
12332              as_FloatRegister($src2$$reg),
12333              as_FloatRegister($src3$$reg));
12334   %}
12335 
12336   ins_pipe(pipe_class_default);
12337 %}
12338 
12339 // -src1 * src2 + src3
12340 instruct msubF_reg_reg(vRegF dst, vRegF src1, vRegF src2, vRegF src3) %{
12341   predicate(UseFMA);
12342   match(Set dst (FmaF src3 (Binary (NegF src1) src2)));
12343   match(Set dst (FmaF src3 (Binary src1 (NegF src2))));
12344 
12345   format %{ "fmsubs   $dst, $src1, $src2, $src3" %}
12346 
12347   ins_encode %{
12348     __ fmsubs(as_FloatRegister($dst$$reg),
12349               as_FloatRegister($src1$$reg),
12350               as_FloatRegister($src2$$reg),
12351               as_FloatRegister($src3$$reg));
12352   %}
12353 
12354   ins_pipe(pipe_class_default);
12355 %}
12356 
12357 // -src1 * src2 + src3
12358 instruct msubD_reg_reg(vRegD dst, vRegD src1, vRegD src2, vRegD src3) %{
12359   predicate(UseFMA);
12360   match(Set dst (FmaD src3 (Binary (NegD src1) src2)));
12361   match(Set dst (FmaD src3 (Binary src1 (NegD src2))));
12362 
12363   format %{ "fmsubd   $dst, $src1, $src2, $src3" %}
12364 
12365   ins_encode %{
12366     __ fmsubd(as_FloatRegister($dst$$reg),
12367               as_FloatRegister($src1$$reg),
12368               as_FloatRegister($src2$$reg),
12369               as_FloatRegister($src3$$reg));
12370   %}
12371 
12372   ins_pipe(pipe_class_default);
12373 %}
12374 
12375 // -src1 * src2 - src3
12376 instruct mnaddF_reg_reg(vRegF dst, vRegF src1, vRegF src2, vRegF src3) %{
12377   predicate(UseFMA);
12378   match(Set dst (FmaF (NegF src3) (Binary (NegF src1) src2)));
12379   match(Set dst (FmaF (NegF src3) (Binary src1 (NegF src2))));
12380 
12381   format %{ "fnmadds  $dst, $src1, $src2, $src3" %}
12382 
12383   ins_encode %{
12384     __ fnmadds(as_FloatRegister($dst$$reg),
12385                as_FloatRegister($src1$$reg),
12386                as_FloatRegister($src2$$reg),
12387                as_FloatRegister($src3$$reg));
12388   %}
12389 
12390   ins_pipe(pipe_class_default);
12391 %}
12392 
12393 // -src1 * src2 - src3
12394 instruct mnaddD_reg_reg(vRegD dst, vRegD src1, vRegD src2, vRegD src3) %{
12395   predicate(UseFMA);
12396   match(Set dst (FmaD (NegD src3) (Binary (NegD src1) src2)));
12397   match(Set dst (FmaD (NegD src3) (Binary src1 (NegD src2))));
12398 
12399   format %{ "fnmaddd   $dst, $src1, $src2, $src3" %}
12400 
12401   ins_encode %{
12402     __ fnmaddd(as_FloatRegister($dst$$reg),
12403                as_FloatRegister($src1$$reg),
12404                as_FloatRegister($src2$$reg),
12405                as_FloatRegister($src3$$reg));
12406   %}
12407 
12408   ins_pipe(pipe_class_default);
12409 %}
12410 
12411 // src1 * src2 - src3
12412 instruct mnsubF_reg_reg(vRegF dst, vRegF src1, vRegF src2, vRegF src3, immF0 zero) %{
12413   predicate(UseFMA);
12414   match(Set dst (FmaF (NegF src3) (Binary src1 src2)));
12415 
12416   format %{ "fnmsubs  $dst, $src1, $src2, $src3" %}
12417 
12418   ins_encode %{
12419     __ fnmsubs(as_FloatRegister($dst$$reg),
12420                as_FloatRegister($src1$$reg),
12421                as_FloatRegister($src2$$reg),
12422                as_FloatRegister($src3$$reg));
12423   %}
12424 
12425   ins_pipe(pipe_class_default);
12426 %}
12427 
12428 // src1 * src2 - src3
12429 instruct mnsubD_reg_reg(vRegD dst, vRegD src1, vRegD src2, vRegD src3, immD0 zero) %{
12430   predicate(UseFMA);
12431   match(Set dst (FmaD (NegD src3) (Binary src1 src2)));
12432 
12433   format %{ "fnmsubd   $dst, $src1, $src2, $src3" %}
12434 
12435   ins_encode %{
12436   // n.b. insn name should be fnmsubd
12437     __ fnmsub(as_FloatRegister($dst$$reg),
12438               as_FloatRegister($src1$$reg),
12439               as_FloatRegister($src2$$reg),
12440               as_FloatRegister($src3$$reg));
12441   %}
12442 
12443   ins_pipe(pipe_class_default);
12444 %}
12445 
12446 
12447 instruct divF_reg_reg(vRegF dst, vRegF src1, vRegF src2) %{
12448   match(Set dst (DivF src1  src2));
12449 
12450   ins_cost(INSN_COST * 18);
12451   format %{ "fdivs   $dst, $src1, $src2" %}
12452 
12453   ins_encode %{
12454     __ fdivs(as_FloatRegister($dst$$reg),
12455              as_FloatRegister($src1$$reg),
12456              as_FloatRegister($src2$$reg));
12457   %}
12458 
12459   ins_pipe(fp_div_s);
12460 %}
12461 
12462 instruct divD_reg_reg(vRegD dst, vRegD src1, vRegD src2) %{
12463   match(Set dst (DivD src1  src2));
12464 
12465   ins_cost(INSN_COST * 32);
12466   format %{ "fdivd   $dst, $src1, $src2" %}
12467 
12468   ins_encode %{
12469     __ fdivd(as_FloatRegister($dst$$reg),
12470              as_FloatRegister($src1$$reg),
12471              as_FloatRegister($src2$$reg));
12472   %}
12473 
12474   ins_pipe(fp_div_d);
12475 %}
12476 
12477 instruct negF_reg_reg(vRegF dst, vRegF src) %{
12478   match(Set dst (NegF src));
12479 
12480   ins_cost(INSN_COST * 3);
12481   format %{ "fneg   $dst, $src" %}
12482 
12483   ins_encode %{
12484     __ fnegs(as_FloatRegister($dst$$reg),
12485              as_FloatRegister($src$$reg));
12486   %}
12487 
12488   ins_pipe(fp_uop_s);
12489 %}
12490 
12491 instruct negD_reg_reg(vRegD dst, vRegD src) %{
12492   match(Set dst (NegD src));
12493 
12494   ins_cost(INSN_COST * 3);
12495   format %{ "fnegd   $dst, $src" %}
12496 
12497   ins_encode %{
12498     __ fnegd(as_FloatRegister($dst$$reg),
12499              as_FloatRegister($src$$reg));
12500   %}
12501 
12502   ins_pipe(fp_uop_d);
12503 %}
12504 
12505 instruct absF_reg(vRegF dst, vRegF src) %{
12506   match(Set dst (AbsF src));
12507 
12508   ins_cost(INSN_COST * 3);
12509   format %{ "fabss   $dst, $src" %}
12510   ins_encode %{
12511     __ fabss(as_FloatRegister($dst$$reg),
12512              as_FloatRegister($src$$reg));
12513   %}
12514 
12515   ins_pipe(fp_uop_s);
12516 %}
12517 
12518 instruct absD_reg(vRegD dst, vRegD src) %{
12519   match(Set dst (AbsD src));
12520 
12521   ins_cost(INSN_COST * 3);
12522   format %{ "fabsd   $dst, $src" %}
12523   ins_encode %{
12524     __ fabsd(as_FloatRegister($dst$$reg),
12525              as_FloatRegister($src$$reg));
12526   %}
12527 
12528   ins_pipe(fp_uop_d);
12529 %}
12530 
12531 instruct sqrtD_reg(vRegD dst, vRegD src) %{
12532   match(Set dst (SqrtD src));
12533 
12534   ins_cost(INSN_COST * 50);
12535   format %{ "fsqrtd  $dst, $src" %}
12536   ins_encode %{
12537     __ fsqrtd(as_FloatRegister($dst$$reg),
12538              as_FloatRegister($src$$reg));
12539   %}
12540 
12541   ins_pipe(fp_div_s);
12542 %}
12543 
12544 instruct sqrtF_reg(vRegF dst, vRegF src) %{
12545   match(Set dst (ConvD2F (SqrtD (ConvF2D src))));
12546 
12547   ins_cost(INSN_COST * 50);
12548   format %{ "fsqrts  $dst, $src" %}
12549   ins_encode %{
12550     __ fsqrts(as_FloatRegister($dst$$reg),
12551              as_FloatRegister($src$$reg));
12552   %}
12553 
12554   ins_pipe(fp_div_d);
12555 %}
12556 
12557 // ============================================================================
12558 // Logical Instructions
12559 
12560 // Integer Logical Instructions
12561 
12562 // And Instructions
12563 
12564 
12565 instruct andI_reg_reg(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2, rFlagsReg cr) %{
12566   match(Set dst (AndI src1 src2));
12567 
12568   format %{ "andw  $dst, $src1, $src2\t# int" %}
12569 
12570   ins_cost(INSN_COST);
12571   ins_encode %{
12572     __ andw(as_Register($dst$$reg),
12573             as_Register($src1$$reg),
12574             as_Register($src2$$reg));
12575   %}
12576 
12577   ins_pipe(ialu_reg_reg);
12578 %}
12579 
12580 instruct andI_reg_imm(iRegINoSp dst, iRegIorL2I src1, immILog src2, rFlagsReg cr) %{
12581   match(Set dst (AndI src1 src2));
12582 
12583   format %{ "andsw  $dst, $src1, $src2\t# int" %}
12584 
12585   ins_cost(INSN_COST);
12586   ins_encode %{
12587     __ andw(as_Register($dst$$reg),
12588             as_Register($src1$$reg),
12589             (unsigned long)($src2$$constant));
12590   %}
12591 
12592   ins_pipe(ialu_reg_imm);
12593 %}
12594 
12595 // Or Instructions
12596 
12597 instruct orI_reg_reg(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2) %{
12598   match(Set dst (OrI src1 src2));
12599 
12600   format %{ "orrw  $dst, $src1, $src2\t# int" %}
12601 
12602   ins_cost(INSN_COST);
12603   ins_encode %{
12604     __ orrw(as_Register($dst$$reg),
12605             as_Register($src1$$reg),
12606             as_Register($src2$$reg));
12607   %}
12608 
12609   ins_pipe(ialu_reg_reg);
12610 %}
12611 
12612 instruct orI_reg_imm(iRegINoSp dst, iRegIorL2I src1, immILog src2) %{
12613   match(Set dst (OrI src1 src2));
12614 
12615   format %{ "orrw  $dst, $src1, $src2\t# int" %}
12616 
12617   ins_cost(INSN_COST);
12618   ins_encode %{
12619     __ orrw(as_Register($dst$$reg),
12620             as_Register($src1$$reg),
12621             (unsigned long)($src2$$constant));
12622   %}
12623 
12624   ins_pipe(ialu_reg_imm);
12625 %}
12626 
12627 // Xor Instructions
12628 
12629 instruct xorI_reg_reg(iRegINoSp dst, iRegIorL2I src1, iRegIorL2I src2) %{
12630   match(Set dst (XorI src1 src2));
12631 
12632   format %{ "eorw  $dst, $src1, $src2\t# int" %}
12633 
12634   ins_cost(INSN_COST);
12635   ins_encode %{
12636     __ eorw(as_Register($dst$$reg),
12637             as_Register($src1$$reg),
12638             as_Register($src2$$reg));
12639   %}
12640 
12641   ins_pipe(ialu_reg_reg);
12642 %}
12643 
12644 instruct xorI_reg_imm(iRegINoSp dst, iRegIorL2I src1, immILog src2) %{
12645   match(Set dst (XorI src1 src2));
12646 
12647   format %{ "eorw  $dst, $src1, $src2\t# int" %}
12648 
12649   ins_cost(INSN_COST);
12650   ins_encode %{
12651     __ eorw(as_Register($dst$$reg),
12652             as_Register($src1$$reg),
12653             (unsigned long)($src2$$constant));
12654   %}
12655 
12656   ins_pipe(ialu_reg_imm);
12657 %}
12658 
12659 // Long Logical Instructions
12660 // TODO
12661 
12662 instruct andL_reg_reg(iRegLNoSp dst, iRegL src1, iRegL src2, rFlagsReg cr) %{
12663   match(Set dst (AndL src1 src2));
12664 
12665   format %{ "and  $dst, $src1, $src2\t# int" %}
12666 
12667   ins_cost(INSN_COST);
12668   ins_encode %{
12669     __ andr(as_Register($dst$$reg),
12670             as_Register($src1$$reg),
12671             as_Register($src2$$reg));
12672   %}
12673 
12674   ins_pipe(ialu_reg_reg);
12675 %}
12676 
12677 instruct andL_reg_imm(iRegLNoSp dst, iRegL src1, immLLog src2, rFlagsReg cr) %{
12678   match(Set dst (AndL src1 src2));
12679 
12680   format %{ "and  $dst, $src1, $src2\t# int" %}
12681 
12682   ins_cost(INSN_COST);
12683   ins_encode %{
12684     __ andr(as_Register($dst$$reg),
12685             as_Register($src1$$reg),
12686             (unsigned long)($src2$$constant));
12687   %}
12688 
12689   ins_pipe(ialu_reg_imm);
12690 %}
12691 
12692 // Or Instructions
12693 
12694 instruct orL_reg_reg(iRegLNoSp dst, iRegL src1, iRegL src2) %{
12695   match(Set dst (OrL src1 src2));
12696 
12697   format %{ "orr  $dst, $src1, $src2\t# int" %}
12698 
12699   ins_cost(INSN_COST);
12700   ins_encode %{
12701     __ orr(as_Register($dst$$reg),
12702            as_Register($src1$$reg),
12703            as_Register($src2$$reg));
12704   %}
12705 
12706   ins_pipe(ialu_reg_reg);
12707 %}
12708 
12709 instruct orL_reg_imm(iRegLNoSp dst, iRegL src1, immLLog src2) %{
12710   match(Set dst (OrL src1 src2));
12711 
12712   format %{ "orr  $dst, $src1, $src2\t# int" %}
12713 
12714   ins_cost(INSN_COST);
12715   ins_encode %{
12716     __ orr(as_Register($dst$$reg),
12717            as_Register($src1$$reg),
12718            (unsigned long)($src2$$constant));
12719   %}
12720 
12721   ins_pipe(ialu_reg_imm);
12722 %}
12723 
12724 // Xor Instructions
12725 
12726 instruct xorL_reg_reg(iRegLNoSp dst, iRegL src1, iRegL src2) %{
12727   match(Set dst (XorL src1 src2));
12728 
12729   format %{ "eor  $dst, $src1, $src2\t# int" %}
12730 
12731   ins_cost(INSN_COST);
12732   ins_encode %{
12733     __ eor(as_Register($dst$$reg),
12734            as_Register($src1$$reg),
12735            as_Register($src2$$reg));
12736   %}
12737 
12738   ins_pipe(ialu_reg_reg);
12739 %}
12740 
12741 instruct xorL_reg_imm(iRegLNoSp dst, iRegL src1, immLLog src2) %{
12742   match(Set dst (XorL src1 src2));
12743 
12744   ins_cost(INSN_COST);
12745   format %{ "eor  $dst, $src1, $src2\t# int" %}
12746 
12747   ins_encode %{
12748     __ eor(as_Register($dst$$reg),
12749            as_Register($src1$$reg),
12750            (unsigned long)($src2$$constant));
12751   %}
12752 
12753   ins_pipe(ialu_reg_imm);
12754 %}
12755 
12756 instruct convI2L_reg_reg(iRegLNoSp dst, iRegIorL2I src)
12757 %{
12758   match(Set dst (ConvI2L src));
12759 
12760   ins_cost(INSN_COST);
12761   format %{ "sxtw  $dst, $src\t# i2l" %}
12762   ins_encode %{
12763     __ sbfm($dst$$Register, $src$$Register, 0, 31);
12764   %}
12765   ins_pipe(ialu_reg_shift);
12766 %}
12767 
12768 // this pattern occurs in bigmath arithmetic
12769 instruct convUI2L_reg_reg(iRegLNoSp dst, iRegIorL2I src, immL_32bits mask)
12770 %{
12771   match(Set dst (AndL (ConvI2L src) mask));
12772 
12773   ins_cost(INSN_COST);
12774   format %{ "ubfm  $dst, $src, 0, 31\t# ui2l" %}
12775   ins_encode %{
12776     __ ubfm($dst$$Register, $src$$Register, 0, 31);
12777   %}
12778 
12779   ins_pipe(ialu_reg_shift);
12780 %}
12781 
12782 instruct convL2I_reg(iRegINoSp dst, iRegL src) %{
12783   match(Set dst (ConvL2I src));
12784 
12785   ins_cost(INSN_COST);
12786   format %{ "movw  $dst, $src \t// l2i" %}
12787 
12788   ins_encode %{
12789     __ movw(as_Register($dst$$reg), as_Register($src$$reg));
12790   %}
12791 
12792   ins_pipe(ialu_reg);
12793 %}
12794 
12795 instruct convI2B(iRegINoSp dst, iRegIorL2I src, rFlagsReg cr)
12796 %{
12797   match(Set dst (Conv2B src));
12798   effect(KILL cr);
12799 
12800   format %{
12801     "cmpw $src, zr\n\t"
12802     "cset $dst, ne"
12803   %}
12804 
12805   ins_encode %{
12806     __ cmpw(as_Register($src$$reg), zr);
12807     __ cset(as_Register($dst$$reg), Assembler::NE);
12808   %}
12809 
12810   ins_pipe(ialu_reg);
12811 %}
12812 
12813 instruct convP2B(iRegINoSp dst, iRegP src, rFlagsReg cr)
12814 %{
12815   match(Set dst (Conv2B src));
12816   effect(KILL cr);
12817 
12818   format %{
12819     "cmp  $src, zr\n\t"
12820     "cset $dst, ne"
12821   %}
12822 
12823   ins_encode %{
12824     __ cmp(as_Register($src$$reg), zr);
12825     __ cset(as_Register($dst$$reg), Assembler::NE);
12826   %}
12827 
12828   ins_pipe(ialu_reg);
12829 %}
12830 
12831 instruct convD2F_reg(vRegF dst, vRegD src) %{
12832   match(Set dst (ConvD2F src));
12833 
12834   ins_cost(INSN_COST * 5);
12835   format %{ "fcvtd  $dst, $src \t// d2f" %}
12836 
12837   ins_encode %{
12838     __ fcvtd(as_FloatRegister($dst$$reg), as_FloatRegister($src$$reg));
12839   %}
12840 
12841   ins_pipe(fp_d2f);
12842 %}
12843 
12844 instruct convF2D_reg(vRegD dst, vRegF src) %{
12845   match(Set dst (ConvF2D src));
12846 
12847   ins_cost(INSN_COST * 5);
12848   format %{ "fcvts  $dst, $src \t// f2d" %}
12849 
12850   ins_encode %{
12851     __ fcvts(as_FloatRegister($dst$$reg), as_FloatRegister($src$$reg));
12852   %}
12853 
12854   ins_pipe(fp_f2d);
12855 %}
12856 
12857 instruct convF2I_reg_reg(iRegINoSp dst, vRegF src) %{
12858   match(Set dst (ConvF2I src));
12859 
12860   ins_cost(INSN_COST * 5);
12861   format %{ "fcvtzsw  $dst, $src \t// f2i" %}
12862 
12863   ins_encode %{
12864     __ fcvtzsw(as_Register($dst$$reg), as_FloatRegister($src$$reg));
12865   %}
12866 
12867   ins_pipe(fp_f2i);
12868 %}
12869 
12870 instruct convF2L_reg_reg(iRegLNoSp dst, vRegF src) %{
12871   match(Set dst (ConvF2L src));
12872 
12873   ins_cost(INSN_COST * 5);
12874   format %{ "fcvtzs  $dst, $src \t// f2l" %}
12875 
12876   ins_encode %{
12877     __ fcvtzs(as_Register($dst$$reg), as_FloatRegister($src$$reg));
12878   %}
12879 
12880   ins_pipe(fp_f2l);
12881 %}
12882 
12883 instruct convI2F_reg_reg(vRegF dst, iRegIorL2I src) %{
12884   match(Set dst (ConvI2F src));
12885 
12886   ins_cost(INSN_COST * 5);
12887   format %{ "scvtfws  $dst, $src \t// i2f" %}
12888 
12889   ins_encode %{
12890     __ scvtfws(as_FloatRegister($dst$$reg), as_Register($src$$reg));
12891   %}
12892 
12893   ins_pipe(fp_i2f);
12894 %}
12895 
12896 instruct convL2F_reg_reg(vRegF dst, iRegL src) %{
12897   match(Set dst (ConvL2F src));
12898 
12899   ins_cost(INSN_COST * 5);
12900   format %{ "scvtfs  $dst, $src \t// l2f" %}
12901 
12902   ins_encode %{
12903     __ scvtfs(as_FloatRegister($dst$$reg), as_Register($src$$reg));
12904   %}
12905 
12906   ins_pipe(fp_l2f);
12907 %}
12908 
12909 instruct convD2I_reg_reg(iRegINoSp dst, vRegD src) %{
12910   match(Set dst (ConvD2I src));
12911 
12912   ins_cost(INSN_COST * 5);
12913   format %{ "fcvtzdw  $dst, $src \t// d2i" %}
12914 
12915   ins_encode %{
12916     __ fcvtzdw(as_Register($dst$$reg), as_FloatRegister($src$$reg));
12917   %}
12918 
12919   ins_pipe(fp_d2i);
12920 %}
12921 
12922 instruct convD2L_reg_reg(iRegLNoSp dst, vRegD src) %{
12923   match(Set dst (ConvD2L src));
12924 
12925   ins_cost(INSN_COST * 5);
12926   format %{ "fcvtzd  $dst, $src \t// d2l" %}
12927 
12928   ins_encode %{
12929     __ fcvtzd(as_Register($dst$$reg), as_FloatRegister($src$$reg));
12930   %}
12931 
12932   ins_pipe(fp_d2l);
12933 %}
12934 
12935 instruct convI2D_reg_reg(vRegD dst, iRegIorL2I src) %{
12936   match(Set dst (ConvI2D src));
12937 
12938   ins_cost(INSN_COST * 5);
12939   format %{ "scvtfwd  $dst, $src \t// i2d" %}
12940 
12941   ins_encode %{
12942     __ scvtfwd(as_FloatRegister($dst$$reg), as_Register($src$$reg));
12943   %}
12944 
12945   ins_pipe(fp_i2d);
12946 %}
12947 
12948 instruct convL2D_reg_reg(vRegD dst, iRegL src) %{
12949   match(Set dst (ConvL2D src));
12950 
12951   ins_cost(INSN_COST * 5);
12952   format %{ "scvtfd  $dst, $src \t// l2d" %}
12953 
12954   ins_encode %{
12955     __ scvtfd(as_FloatRegister($dst$$reg), as_Register($src$$reg));
12956   %}
12957 
12958   ins_pipe(fp_l2d);
12959 %}
12960 
12961 // stack <-> reg and reg <-> reg shuffles with no conversion
12962 
12963 instruct MoveF2I_stack_reg(iRegINoSp dst, stackSlotF src) %{
12964 
12965   match(Set dst (MoveF2I src));
12966 
12967   effect(DEF dst, USE src);
12968 
12969   ins_cost(4 * INSN_COST);
12970 
12971   format %{ "ldrw $dst, $src\t# MoveF2I_stack_reg" %}
12972 
12973   ins_encode %{
12974     __ ldrw($dst$$Register, Address(sp, $src$$disp));
12975   %}
12976 
12977   ins_pipe(iload_reg_reg);
12978 
12979 %}
12980 
12981 instruct MoveI2F_stack_reg(vRegF dst, stackSlotI src) %{
12982 
12983   match(Set dst (MoveI2F src));
12984 
12985   effect(DEF dst, USE src);
12986 
12987   ins_cost(4 * INSN_COST);
12988 
12989   format %{ "ldrs $dst, $src\t# MoveI2F_stack_reg" %}
12990 
12991   ins_encode %{
12992     __ ldrs(as_FloatRegister($dst$$reg), Address(sp, $src$$disp));
12993   %}
12994 
12995   ins_pipe(pipe_class_memory);
12996 
12997 %}
12998 
12999 instruct MoveD2L_stack_reg(iRegLNoSp dst, stackSlotD src) %{
13000 
13001   match(Set dst (MoveD2L src));
13002 
13003   effect(DEF dst, USE src);
13004 
13005   ins_cost(4 * INSN_COST);
13006 
13007   format %{ "ldr $dst, $src\t# MoveD2L_stack_reg" %}
13008 
13009   ins_encode %{
13010     __ ldr($dst$$Register, Address(sp, $src$$disp));
13011   %}
13012 
13013   ins_pipe(iload_reg_reg);
13014 
13015 %}
13016 
13017 instruct MoveL2D_stack_reg(vRegD dst, stackSlotL src) %{
13018 
13019   match(Set dst (MoveL2D src));
13020 
13021   effect(DEF dst, USE src);
13022 
13023   ins_cost(4 * INSN_COST);
13024 
13025   format %{ "ldrd $dst, $src\t# MoveL2D_stack_reg" %}
13026 
13027   ins_encode %{
13028     __ ldrd(as_FloatRegister($dst$$reg), Address(sp, $src$$disp));
13029   %}
13030 
13031   ins_pipe(pipe_class_memory);
13032 
13033 %}
13034 
13035 instruct MoveF2I_reg_stack(stackSlotI dst, vRegF src) %{
13036 
13037   match(Set dst (MoveF2I src));
13038 
13039   effect(DEF dst, USE src);
13040 
13041   ins_cost(INSN_COST);
13042 
13043   format %{ "strs $src, $dst\t# MoveF2I_reg_stack" %}
13044 
13045   ins_encode %{
13046     __ strs(as_FloatRegister($src$$reg), Address(sp, $dst$$disp));
13047   %}
13048 
13049   ins_pipe(pipe_class_memory);
13050 
13051 %}
13052 
13053 instruct MoveI2F_reg_stack(stackSlotF dst, iRegI src) %{
13054 
13055   match(Set dst (MoveI2F src));
13056 
13057   effect(DEF dst, USE src);
13058 
13059   ins_cost(INSN_COST);
13060 
13061   format %{ "strw $src, $dst\t# MoveI2F_reg_stack" %}
13062 
13063   ins_encode %{
13064     __ strw($src$$Register, Address(sp, $dst$$disp));
13065   %}
13066 
13067   ins_pipe(istore_reg_reg);
13068 
13069 %}
13070 
13071 instruct MoveD2L_reg_stack(stackSlotL dst, vRegD src) %{
13072 
13073   match(Set dst (MoveD2L src));
13074 
13075   effect(DEF dst, USE src);
13076 
13077   ins_cost(INSN_COST);
13078 
13079   format %{ "strd $dst, $src\t# MoveD2L_reg_stack" %}
13080 
13081   ins_encode %{
13082     __ strd(as_FloatRegister($src$$reg), Address(sp, $dst$$disp));
13083   %}
13084 
13085   ins_pipe(pipe_class_memory);
13086 
13087 %}
13088 
13089 instruct MoveL2D_reg_stack(stackSlotD dst, iRegL src) %{
13090 
13091   match(Set dst (MoveL2D src));
13092 
13093   effect(DEF dst, USE src);
13094 
13095   ins_cost(INSN_COST);
13096 
13097   format %{ "str $src, $dst\t# MoveL2D_reg_stack" %}
13098 
13099   ins_encode %{
13100     __ str($src$$Register, Address(sp, $dst$$disp));
13101   %}
13102 
13103   ins_pipe(istore_reg_reg);
13104 
13105 %}
13106 
13107 instruct MoveF2I_reg_reg(iRegINoSp dst, vRegF src) %{
13108 
13109   match(Set dst (MoveF2I src));
13110 
13111   effect(DEF dst, USE src);
13112 
13113   ins_cost(INSN_COST);
13114 
13115   format %{ "fmovs $dst, $src\t# MoveF2I_reg_reg" %}
13116 
13117   ins_encode %{
13118     __ fmovs($dst$$Register, as_FloatRegister($src$$reg));
13119   %}
13120 
13121   ins_pipe(fp_f2i);
13122 
13123 %}
13124 
13125 instruct MoveI2F_reg_reg(vRegF dst, iRegI src) %{
13126 
13127   match(Set dst (MoveI2F src));
13128 
13129   effect(DEF dst, USE src);
13130 
13131   ins_cost(INSN_COST);
13132 
13133   format %{ "fmovs $dst, $src\t# MoveI2F_reg_reg" %}
13134 
13135   ins_encode %{
13136     __ fmovs(as_FloatRegister($dst$$reg), $src$$Register);
13137   %}
13138 
13139   ins_pipe(fp_i2f);
13140 
13141 %}
13142 
13143 instruct MoveD2L_reg_reg(iRegLNoSp dst, vRegD src) %{
13144 
13145   match(Set dst (MoveD2L src));
13146 
13147   effect(DEF dst, USE src);
13148 
13149   ins_cost(INSN_COST);
13150 
13151   format %{ "fmovd $dst, $src\t# MoveD2L_reg_reg" %}
13152 
13153   ins_encode %{
13154     __ fmovd($dst$$Register, as_FloatRegister($src$$reg));
13155   %}
13156 
13157   ins_pipe(fp_d2l);
13158 
13159 %}
13160 
13161 instruct MoveL2D_reg_reg(vRegD dst, iRegL src) %{
13162 
13163   match(Set dst (MoveL2D src));
13164 
13165   effect(DEF dst, USE src);
13166 
13167   ins_cost(INSN_COST);
13168 
13169   format %{ "fmovd $dst, $src\t# MoveL2D_reg_reg" %}
13170 
13171   ins_encode %{
13172     __ fmovd(as_FloatRegister($dst$$reg), $src$$Register);
13173   %}
13174 
13175   ins_pipe(fp_l2d);
13176 
13177 %}
13178 
13179 // ============================================================================
13180 // clearing of an array
13181 
13182 instruct clearArray_reg_reg(iRegL_R11 cnt, iRegP_R10 base, Universe dummy, rFlagsReg cr)
13183 %{
13184   match(Set dummy (ClearArray cnt base));
13185   effect(USE_KILL cnt, USE_KILL base);
13186 
13187   ins_cost(4 * INSN_COST);
13188   format %{ "ClearArray $cnt, $base" %}
13189 
13190   ins_encode %{
13191     __ zero_words($base$$Register, $cnt$$Register);
13192   %}
13193 
13194   ins_pipe(pipe_class_memory);
13195 %}
13196 
13197 instruct clearArray_imm_reg(immL cnt, iRegP_R10 base, Universe dummy, rFlagsReg cr)
13198 %{
13199   predicate((u_int64_t)n->in(2)->get_long()
13200             < (u_int64_t)(BlockZeroingLowLimit >> LogBytesPerWord));
13201   match(Set dummy (ClearArray cnt base));
13202   effect(USE_KILL base);
13203 
13204   ins_cost(4 * INSN_COST);
13205   format %{ "ClearArray $cnt, $base" %}
13206 
13207   ins_encode %{
13208     __ zero_words($base$$Register, (u_int64_t)$cnt$$constant);
13209   %}
13210 
13211   ins_pipe(pipe_class_memory);
13212 %}
13213 
13214 // ============================================================================
13215 // Overflow Math Instructions
13216 
13217 instruct overflowAddI_reg_reg(rFlagsReg cr, iRegIorL2I op1, iRegIorL2I op2)
13218 %{
13219   match(Set cr (OverflowAddI op1 op2));
13220 
13221   format %{ "cmnw  $op1, $op2\t# overflow check int" %}
13222   ins_cost(INSN_COST);
13223   ins_encode %{
13224     __ cmnw($op1$$Register, $op2$$Register);
13225   %}
13226 
13227   ins_pipe(icmp_reg_reg);
13228 %}
13229 
13230 instruct overflowAddI_reg_imm(rFlagsReg cr, iRegIorL2I op1, immIAddSub op2)
13231 %{
13232   match(Set cr (OverflowAddI op1 op2));
13233 
13234   format %{ "cmnw  $op1, $op2\t# overflow check int" %}
13235   ins_cost(INSN_COST);
13236   ins_encode %{
13237     __ cmnw($op1$$Register, $op2$$constant);
13238   %}
13239 
13240   ins_pipe(icmp_reg_imm);
13241 %}
13242 
13243 instruct overflowAddL_reg_reg(rFlagsReg cr, iRegL op1, iRegL op2)
13244 %{
13245   match(Set cr (OverflowAddL op1 op2));
13246 
13247   format %{ "cmn   $op1, $op2\t# overflow check long" %}
13248   ins_cost(INSN_COST);
13249   ins_encode %{
13250     __ cmn($op1$$Register, $op2$$Register);
13251   %}
13252 
13253   ins_pipe(icmp_reg_reg);
13254 %}
13255 
13256 instruct overflowAddL_reg_imm(rFlagsReg cr, iRegL op1, immLAddSub op2)
13257 %{
13258   match(Set cr (OverflowAddL op1 op2));
13259 
13260   format %{ "cmn   $op1, $op2\t# overflow check long" %}
13261   ins_cost(INSN_COST);
13262   ins_encode %{
13263     __ cmn($op1$$Register, $op2$$constant);
13264   %}
13265 
13266   ins_pipe(icmp_reg_imm);
13267 %}
13268 
13269 instruct overflowSubI_reg_reg(rFlagsReg cr, iRegIorL2I op1, iRegIorL2I op2)
13270 %{
13271   match(Set cr (OverflowSubI op1 op2));
13272 
13273   format %{ "cmpw  $op1, $op2\t# overflow check int" %}
13274   ins_cost(INSN_COST);
13275   ins_encode %{
13276     __ cmpw($op1$$Register, $op2$$Register);
13277   %}
13278 
13279   ins_pipe(icmp_reg_reg);
13280 %}
13281 
13282 instruct overflowSubI_reg_imm(rFlagsReg cr, iRegIorL2I op1, immIAddSub op2)
13283 %{
13284   match(Set cr (OverflowSubI op1 op2));
13285 
13286   format %{ "cmpw  $op1, $op2\t# overflow check int" %}
13287   ins_cost(INSN_COST);
13288   ins_encode %{
13289     __ cmpw($op1$$Register, $op2$$constant);
13290   %}
13291 
13292   ins_pipe(icmp_reg_imm);
13293 %}
13294 
13295 instruct overflowSubL_reg_reg(rFlagsReg cr, iRegL op1, iRegL op2)
13296 %{
13297   match(Set cr (OverflowSubL op1 op2));
13298 
13299   format %{ "cmp   $op1, $op2\t# overflow check long" %}
13300   ins_cost(INSN_COST);
13301   ins_encode %{
13302     __ cmp($op1$$Register, $op2$$Register);
13303   %}
13304 
13305   ins_pipe(icmp_reg_reg);
13306 %}
13307 
13308 instruct overflowSubL_reg_imm(rFlagsReg cr, iRegL op1, immLAddSub op2)
13309 %{
13310   match(Set cr (OverflowSubL op1 op2));
13311 
13312   format %{ "cmp   $op1, $op2\t# overflow check long" %}
13313   ins_cost(INSN_COST);
13314   ins_encode %{
13315     __ cmp($op1$$Register, $op2$$constant);
13316   %}
13317 
13318   ins_pipe(icmp_reg_imm);
13319 %}
13320 
13321 instruct overflowNegI_reg(rFlagsReg cr, immI0 zero, iRegIorL2I op1)
13322 %{
13323   match(Set cr (OverflowSubI zero op1));
13324 
13325   format %{ "cmpw  zr, $op1\t# overflow check int" %}
13326   ins_cost(INSN_COST);
13327   ins_encode %{
13328     __ cmpw(zr, $op1$$Register);
13329   %}
13330 
13331   ins_pipe(icmp_reg_imm);
13332 %}
13333 
13334 instruct overflowNegL_reg(rFlagsReg cr, immI0 zero, iRegL op1)
13335 %{
13336   match(Set cr (OverflowSubL zero op1));
13337 
13338   format %{ "cmp   zr, $op1\t# overflow check long" %}
13339   ins_cost(INSN_COST);
13340   ins_encode %{
13341     __ cmp(zr, $op1$$Register);
13342   %}
13343 
13344   ins_pipe(icmp_reg_imm);
13345 %}
13346 
13347 instruct overflowMulI_reg(rFlagsReg cr, iRegIorL2I op1, iRegIorL2I op2)
13348 %{
13349   match(Set cr (OverflowMulI op1 op2));
13350 
13351   format %{ "smull rscratch1, $op1, $op2\t# overflow check int\n\t"
13352             "cmp   rscratch1, rscratch1, sxtw\n\t"
13353             "movw  rscratch1, #0x80000000\n\t"
13354             "cselw rscratch1, rscratch1, zr, NE\n\t"
13355             "cmpw  rscratch1, #1" %}
13356   ins_cost(5 * INSN_COST);
13357   ins_encode %{
13358     __ smull(rscratch1, $op1$$Register, $op2$$Register);
13359     __ subs(zr, rscratch1, rscratch1, ext::sxtw);      // NE => overflow
13360     __ movw(rscratch1, 0x80000000);                    // Develop 0 (EQ),
13361     __ cselw(rscratch1, rscratch1, zr, Assembler::NE); // or 0x80000000 (NE)
13362     __ cmpw(rscratch1, 1);                             // 0x80000000 - 1 => VS
13363   %}
13364 
13365   ins_pipe(pipe_slow);
13366 %}
13367 
13368 instruct overflowMulI_reg_branch(cmpOp cmp, iRegIorL2I op1, iRegIorL2I op2, label labl, rFlagsReg cr)
13369 %{
13370   match(If cmp (OverflowMulI op1 op2));
13371   predicate(n->in(1)->as_Bool()->_test._test == BoolTest::overflow
13372             || n->in(1)->as_Bool()->_test._test == BoolTest::no_overflow);
13373   effect(USE labl, KILL cr);
13374 
13375   format %{ "smull rscratch1, $op1, $op2\t# overflow check int\n\t"
13376             "cmp   rscratch1, rscratch1, sxtw\n\t"
13377             "b$cmp   $labl" %}
13378   ins_cost(3 * INSN_COST); // Branch is rare so treat as INSN_COST
13379   ins_encode %{
13380     Label* L = $labl$$label;
13381     Assembler::Condition cond = (Assembler::Condition)$cmp$$cmpcode;
13382     __ smull(rscratch1, $op1$$Register, $op2$$Register);
13383     __ subs(zr, rscratch1, rscratch1, ext::sxtw);      // NE => overflow
13384     __ br(cond == Assembler::VS ? Assembler::NE : Assembler::EQ, *L);
13385   %}
13386 
13387   ins_pipe(pipe_serial);
13388 %}
13389 
13390 instruct overflowMulL_reg(rFlagsReg cr, iRegL op1, iRegL op2)
13391 %{
13392   match(Set cr (OverflowMulL op1 op2));
13393 
13394   format %{ "mul   rscratch1, $op1, $op2\t#overflow check long\n\t"
13395             "smulh rscratch2, $op1, $op2\n\t"
13396             "cmp   rscratch2, rscratch1, ASR #63\n\t"
13397             "movw  rscratch1, #0x80000000\n\t"
13398             "cselw rscratch1, rscratch1, zr, NE\n\t"
13399             "cmpw  rscratch1, #1" %}
13400   ins_cost(6 * INSN_COST);
13401   ins_encode %{
13402     __ mul(rscratch1, $op1$$Register, $op2$$Register);   // Result bits 0..63
13403     __ smulh(rscratch2, $op1$$Register, $op2$$Register); // Result bits 64..127
13404     __ cmp(rscratch2, rscratch1, Assembler::ASR, 63);    // Top is pure sign ext
13405     __ movw(rscratch1, 0x80000000);                    // Develop 0 (EQ),
13406     __ cselw(rscratch1, rscratch1, zr, Assembler::NE); // or 0x80000000 (NE)
13407     __ cmpw(rscratch1, 1);                             // 0x80000000 - 1 => VS
13408   %}
13409 
13410   ins_pipe(pipe_slow);
13411 %}
13412 
13413 instruct overflowMulL_reg_branch(cmpOp cmp, iRegL op1, iRegL op2, label labl, rFlagsReg cr)
13414 %{
13415   match(If cmp (OverflowMulL op1 op2));
13416   predicate(n->in(1)->as_Bool()->_test._test == BoolTest::overflow
13417             || n->in(1)->as_Bool()->_test._test == BoolTest::no_overflow);
13418   effect(USE labl, KILL cr);
13419 
13420   format %{ "mul   rscratch1, $op1, $op2\t#overflow check long\n\t"
13421             "smulh rscratch2, $op1, $op2\n\t"
13422             "cmp   rscratch2, rscratch1, ASR #63\n\t"
13423             "b$cmp $labl" %}
13424   ins_cost(4 * INSN_COST); // Branch is rare so treat as INSN_COST
13425   ins_encode %{
13426     Label* L = $labl$$label;
13427     Assembler::Condition cond = (Assembler::Condition)$cmp$$cmpcode;
13428     __ mul(rscratch1, $op1$$Register, $op2$$Register);   // Result bits 0..63
13429     __ smulh(rscratch2, $op1$$Register, $op2$$Register); // Result bits 64..127
13430     __ cmp(rscratch2, rscratch1, Assembler::ASR, 63);    // Top is pure sign ext
13431     __ br(cond == Assembler::VS ? Assembler::NE : Assembler::EQ, *L);
13432   %}
13433 
13434   ins_pipe(pipe_serial);
13435 %}
13436 
13437 // ============================================================================
13438 // Compare Instructions
13439 
13440 instruct compI_reg_reg(rFlagsReg cr, iRegI op1, iRegI op2)
13441 %{
13442   match(Set cr (CmpI op1 op2));
13443 
13444   effect(DEF cr, USE op1, USE op2);
13445 
13446   ins_cost(INSN_COST);
13447   format %{ "cmpw  $op1, $op2" %}
13448 
13449   ins_encode(aarch64_enc_cmpw(op1, op2));
13450 
13451   ins_pipe(icmp_reg_reg);
13452 %}
13453 
13454 instruct compI_reg_immI0(rFlagsReg cr, iRegI op1, immI0 zero)
13455 %{
13456   match(Set cr (CmpI op1 zero));
13457 
13458   effect(DEF cr, USE op1);
13459 
13460   ins_cost(INSN_COST);
13461   format %{ "cmpw $op1, 0" %}
13462 
13463   ins_encode(aarch64_enc_cmpw_imm_addsub(op1, zero));
13464 
13465   ins_pipe(icmp_reg_imm);
13466 %}
13467 
13468 instruct compI_reg_immIAddSub(rFlagsReg cr, iRegI op1, immIAddSub op2)
13469 %{
13470   match(Set cr (CmpI op1 op2));
13471 
13472   effect(DEF cr, USE op1);
13473 
13474   ins_cost(INSN_COST);
13475   format %{ "cmpw  $op1, $op2" %}
13476 
13477   ins_encode(aarch64_enc_cmpw_imm_addsub(op1, op2));
13478 
13479   ins_pipe(icmp_reg_imm);
13480 %}
13481 
13482 instruct compI_reg_immI(rFlagsReg cr, iRegI op1, immI op2)
13483 %{
13484   match(Set cr (CmpI op1 op2));
13485 
13486   effect(DEF cr, USE op1);
13487 
13488   ins_cost(INSN_COST * 2);
13489   format %{ "cmpw  $op1, $op2" %}
13490 
13491   ins_encode(aarch64_enc_cmpw_imm(op1, op2));
13492 
13493   ins_pipe(icmp_reg_imm);
13494 %}
13495 
13496 // Unsigned compare Instructions; really, same as signed compare
13497 // except it should only be used to feed an If or a CMovI which takes a
13498 // cmpOpU.
13499 
13500 instruct compU_reg_reg(rFlagsRegU cr, iRegI op1, iRegI op2)
13501 %{
13502   match(Set cr (CmpU op1 op2));
13503 
13504   effect(DEF cr, USE op1, USE op2);
13505 
13506   ins_cost(INSN_COST);
13507   format %{ "cmpw  $op1, $op2\t# unsigned" %}
13508 
13509   ins_encode(aarch64_enc_cmpw(op1, op2));
13510 
13511   ins_pipe(icmp_reg_reg);
13512 %}
13513 
13514 instruct compU_reg_immI0(rFlagsRegU cr, iRegI op1, immI0 zero)
13515 %{
13516   match(Set cr (CmpU op1 zero));
13517 
13518   effect(DEF cr, USE op1);
13519 
13520   ins_cost(INSN_COST);
13521   format %{ "cmpw $op1, #0\t# unsigned" %}
13522 
13523   ins_encode(aarch64_enc_cmpw_imm_addsub(op1, zero));
13524 
13525   ins_pipe(icmp_reg_imm);
13526 %}
13527 
13528 instruct compU_reg_immIAddSub(rFlagsRegU cr, iRegI op1, immIAddSub op2)
13529 %{
13530   match(Set cr (CmpU op1 op2));
13531 
13532   effect(DEF cr, USE op1);
13533 
13534   ins_cost(INSN_COST);
13535   format %{ "cmpw  $op1, $op2\t# unsigned" %}
13536 
13537   ins_encode(aarch64_enc_cmpw_imm_addsub(op1, op2));
13538 
13539   ins_pipe(icmp_reg_imm);
13540 %}
13541 
13542 instruct compU_reg_immI(rFlagsRegU cr, iRegI op1, immI op2)
13543 %{
13544   match(Set cr (CmpU op1 op2));
13545 
13546   effect(DEF cr, USE op1);
13547 
13548   ins_cost(INSN_COST * 2);
13549   format %{ "cmpw  $op1, $op2\t# unsigned" %}
13550 
13551   ins_encode(aarch64_enc_cmpw_imm(op1, op2));
13552 
13553   ins_pipe(icmp_reg_imm);
13554 %}
13555 
13556 instruct compL_reg_reg(rFlagsReg cr, iRegL op1, iRegL op2)
13557 %{
13558   match(Set cr (CmpL op1 op2));
13559 
13560   effect(DEF cr, USE op1, USE op2);
13561 
13562   ins_cost(INSN_COST);
13563   format %{ "cmp  $op1, $op2" %}
13564 
13565   ins_encode(aarch64_enc_cmp(op1, op2));
13566 
13567   ins_pipe(icmp_reg_reg);
13568 %}
13569 
13570 instruct compL_reg_immL0(rFlagsReg cr, iRegL op1, immL0 zero)
13571 %{
13572   match(Set cr (CmpL op1 zero));
13573 
13574   effect(DEF cr, USE op1);
13575 
13576   ins_cost(INSN_COST);
13577   format %{ "tst  $op1" %}
13578 
13579   ins_encode(aarch64_enc_cmp_imm_addsub(op1, zero));
13580 
13581   ins_pipe(icmp_reg_imm);
13582 %}
13583 
13584 instruct compL_reg_immLAddSub(rFlagsReg cr, iRegL op1, immLAddSub op2)
13585 %{
13586   match(Set cr (CmpL op1 op2));
13587 
13588   effect(DEF cr, USE op1);
13589 
13590   ins_cost(INSN_COST);
13591   format %{ "cmp  $op1, $op2" %}
13592 
13593   ins_encode(aarch64_enc_cmp_imm_addsub(op1, op2));
13594 
13595   ins_pipe(icmp_reg_imm);
13596 %}
13597 
13598 instruct compL_reg_immL(rFlagsReg cr, iRegL op1, immL op2)
13599 %{
13600   match(Set cr (CmpL op1 op2));
13601 
13602   effect(DEF cr, USE op1);
13603 
13604   ins_cost(INSN_COST * 2);
13605   format %{ "cmp  $op1, $op2" %}
13606 
13607   ins_encode(aarch64_enc_cmp_imm(op1, op2));
13608 
13609   ins_pipe(icmp_reg_imm);
13610 %}
13611 
13612 instruct compUL_reg_reg(rFlagsRegU cr, iRegL op1, iRegL op2)
13613 %{
13614   match(Set cr (CmpUL op1 op2));
13615 
13616   effect(DEF cr, USE op1, USE op2);
13617 
13618   ins_cost(INSN_COST);
13619   format %{ "cmp  $op1, $op2" %}
13620 
13621   ins_encode(aarch64_enc_cmp(op1, op2));
13622 
13623   ins_pipe(icmp_reg_reg);
13624 %}
13625 
13626 instruct compUL_reg_immL0(rFlagsRegU cr, iRegL op1, immL0 zero)
13627 %{
13628   match(Set cr (CmpUL op1 zero));
13629 
13630   effect(DEF cr, USE op1);
13631 
13632   ins_cost(INSN_COST);
13633   format %{ "tst  $op1" %}
13634 
13635   ins_encode(aarch64_enc_cmp_imm_addsub(op1, zero));
13636 
13637   ins_pipe(icmp_reg_imm);
13638 %}
13639 
13640 instruct compUL_reg_immLAddSub(rFlagsRegU cr, iRegL op1, immLAddSub op2)
13641 %{
13642   match(Set cr (CmpUL op1 op2));
13643 
13644   effect(DEF cr, USE op1);
13645 
13646   ins_cost(INSN_COST);
13647   format %{ "cmp  $op1, $op2" %}
13648 
13649   ins_encode(aarch64_enc_cmp_imm_addsub(op1, op2));
13650 
13651   ins_pipe(icmp_reg_imm);
13652 %}
13653 
13654 instruct compUL_reg_immL(rFlagsRegU cr, iRegL op1, immL op2)
13655 %{
13656   match(Set cr (CmpUL op1 op2));
13657 
13658   effect(DEF cr, USE op1);
13659 
13660   ins_cost(INSN_COST * 2);
13661   format %{ "cmp  $op1, $op2" %}
13662 
13663   ins_encode(aarch64_enc_cmp_imm(op1, op2));
13664 
13665   ins_pipe(icmp_reg_imm);
13666 %}
13667 
13668 instruct compP_reg_reg(rFlagsRegU cr, iRegP op1, iRegP op2)
13669 %{
13670   match(Set cr (CmpP op1 op2));
13671 
13672   effect(DEF cr, USE op1, USE op2);
13673 
13674   ins_cost(INSN_COST);
13675   format %{ "cmp  $op1, $op2\t // ptr" %}
13676 
13677   ins_encode(aarch64_enc_cmpp(op1, op2));
13678 
13679   ins_pipe(icmp_reg_reg);
13680 %}
13681 
13682 instruct compN_reg_reg(rFlagsRegU cr, iRegN op1, iRegN op2)
13683 %{
13684   match(Set cr (CmpN op1 op2));
13685 
13686   effect(DEF cr, USE op1, USE op2);
13687 
13688   ins_cost(INSN_COST);
13689   format %{ "cmp  $op1, $op2\t // compressed ptr" %}
13690 
13691   ins_encode(aarch64_enc_cmpn(op1, op2));
13692 
13693   ins_pipe(icmp_reg_reg);
13694 %}
13695 
13696 instruct testP_reg(rFlagsRegU cr, iRegP op1, immP0 zero)
13697 %{
13698   match(Set cr (CmpP op1 zero));
13699 
13700   effect(DEF cr, USE op1, USE zero);
13701 
13702   ins_cost(INSN_COST);
13703   format %{ "cmp  $op1, 0\t // ptr" %}
13704 
13705   ins_encode(aarch64_enc_testp(op1));
13706 
13707   ins_pipe(icmp_reg_imm);
13708 %}
13709 
13710 instruct testN_reg(rFlagsRegU cr, iRegN op1, immN0 zero)
13711 %{
13712   match(Set cr (CmpN op1 zero));
13713 
13714   effect(DEF cr, USE op1, USE zero);
13715 
13716   ins_cost(INSN_COST);
13717   format %{ "cmp  $op1, 0\t // compressed ptr" %}
13718 
13719   ins_encode(aarch64_enc_testn(op1));
13720 
13721   ins_pipe(icmp_reg_imm);
13722 %}
13723 
13724 // FP comparisons
13725 //
13726 // n.b. CmpF/CmpD set a normal flags reg which then gets compared
13727 // using normal cmpOp. See declaration of rFlagsReg for details.
13728 
13729 instruct compF_reg_reg(rFlagsReg cr, vRegF src1, vRegF src2)
13730 %{
13731   match(Set cr (CmpF src1 src2));
13732 
13733   ins_cost(3 * INSN_COST);
13734   format %{ "fcmps $src1, $src2" %}
13735 
13736   ins_encode %{
13737     __ fcmps(as_FloatRegister($src1$$reg), as_FloatRegister($src2$$reg));
13738   %}
13739 
13740   ins_pipe(pipe_class_compare);
13741 %}
13742 
13743 instruct compF_reg_zero(rFlagsReg cr, vRegF src1, immF0 src2)
13744 %{
13745   match(Set cr (CmpF src1 src2));
13746 
13747   ins_cost(3 * INSN_COST);
13748   format %{ "fcmps $src1, 0.0" %}
13749 
13750   ins_encode %{
13751     __ fcmps(as_FloatRegister($src1$$reg), 0.0);
13752   %}
13753 
13754   ins_pipe(pipe_class_compare);
13755 %}
13756 // FROM HERE
13757 
13758 instruct compD_reg_reg(rFlagsReg cr, vRegD src1, vRegD src2)
13759 %{
13760   match(Set cr (CmpD src1 src2));
13761 
13762   ins_cost(3 * INSN_COST);
13763   format %{ "fcmpd $src1, $src2" %}
13764 
13765   ins_encode %{
13766     __ fcmpd(as_FloatRegister($src1$$reg), as_FloatRegister($src2$$reg));
13767   %}
13768 
13769   ins_pipe(pipe_class_compare);
13770 %}
13771 
13772 instruct compD_reg_zero(rFlagsReg cr, vRegD src1, immD0 src2)
13773 %{
13774   match(Set cr (CmpD src1 src2));
13775 
13776   ins_cost(3 * INSN_COST);
13777   format %{ "fcmpd $src1, 0.0" %}
13778 
13779   ins_encode %{
13780     __ fcmpd(as_FloatRegister($src1$$reg), 0.0);
13781   %}
13782 
13783   ins_pipe(pipe_class_compare);
13784 %}
13785 
13786 instruct compF3_reg_reg(iRegINoSp dst, vRegF src1, vRegF src2, rFlagsReg cr)
13787 %{
13788   match(Set dst (CmpF3 src1 src2));
13789   effect(KILL cr);
13790 
13791   ins_cost(5 * INSN_COST);
13792   format %{ "fcmps $src1, $src2\n\t"
13793             "csinvw($dst, zr, zr, eq\n\t"
13794             "csnegw($dst, $dst, $dst, lt)"
13795   %}
13796 
13797   ins_encode %{
13798     Label done;
13799     FloatRegister s1 = as_FloatRegister($src1$$reg);
13800     FloatRegister s2 = as_FloatRegister($src2$$reg);
13801     Register d = as_Register($dst$$reg);
13802     __ fcmps(s1, s2);
13803     // installs 0 if EQ else -1
13804     __ csinvw(d, zr, zr, Assembler::EQ);
13805     // keeps -1 if less or unordered else installs 1
13806     __ csnegw(d, d, d, Assembler::LT);
13807     __ bind(done);
13808   %}
13809 
13810   ins_pipe(pipe_class_default);
13811 
13812 %}
13813 
13814 instruct compD3_reg_reg(iRegINoSp dst, vRegD src1, vRegD src2, rFlagsReg cr)
13815 %{
13816   match(Set dst (CmpD3 src1 src2));
13817   effect(KILL cr);
13818 
13819   ins_cost(5 * INSN_COST);
13820   format %{ "fcmpd $src1, $src2\n\t"
13821             "csinvw($dst, zr, zr, eq\n\t"
13822             "csnegw($dst, $dst, $dst, lt)"
13823   %}
13824 
13825   ins_encode %{
13826     Label done;
13827     FloatRegister s1 = as_FloatRegister($src1$$reg);
13828     FloatRegister s2 = as_FloatRegister($src2$$reg);
13829     Register d = as_Register($dst$$reg);
13830     __ fcmpd(s1, s2);
13831     // installs 0 if EQ else -1
13832     __ csinvw(d, zr, zr, Assembler::EQ);
13833     // keeps -1 if less or unordered else installs 1
13834     __ csnegw(d, d, d, Assembler::LT);
13835     __ bind(done);
13836   %}
13837   ins_pipe(pipe_class_default);
13838 
13839 %}
13840 
13841 instruct compF3_reg_immF0(iRegINoSp dst, vRegF src1, immF0 zero, rFlagsReg cr)
13842 %{
13843   match(Set dst (CmpF3 src1 zero));
13844   effect(KILL cr);
13845 
13846   ins_cost(5 * INSN_COST);
13847   format %{ "fcmps $src1, 0.0\n\t"
13848             "csinvw($dst, zr, zr, eq\n\t"
13849             "csnegw($dst, $dst, $dst, lt)"
13850   %}
13851 
13852   ins_encode %{
13853     Label done;
13854     FloatRegister s1 = as_FloatRegister($src1$$reg);
13855     Register d = as_Register($dst$$reg);
13856     __ fcmps(s1, 0.0);
13857     // installs 0 if EQ else -1
13858     __ csinvw(d, zr, zr, Assembler::EQ);
13859     // keeps -1 if less or unordered else installs 1
13860     __ csnegw(d, d, d, Assembler::LT);
13861     __ bind(done);
13862   %}
13863 
13864   ins_pipe(pipe_class_default);
13865 
13866 %}
13867 
13868 instruct compD3_reg_immD0(iRegINoSp dst, vRegD src1, immD0 zero, rFlagsReg cr)
13869 %{
13870   match(Set dst (CmpD3 src1 zero));
13871   effect(KILL cr);
13872 
13873   ins_cost(5 * INSN_COST);
13874   format %{ "fcmpd $src1, 0.0\n\t"
13875             "csinvw($dst, zr, zr, eq\n\t"
13876             "csnegw($dst, $dst, $dst, lt)"
13877   %}
13878 
13879   ins_encode %{
13880     Label done;
13881     FloatRegister s1 = as_FloatRegister($src1$$reg);
13882     Register d = as_Register($dst$$reg);
13883     __ fcmpd(s1, 0.0);
13884     // installs 0 if EQ else -1
13885     __ csinvw(d, zr, zr, Assembler::EQ);
13886     // keeps -1 if less or unordered else installs 1
13887     __ csnegw(d, d, d, Assembler::LT);
13888     __ bind(done);
13889   %}
13890   ins_pipe(pipe_class_default);
13891 
13892 %}
13893 
13894 instruct cmpLTMask_reg_reg(iRegINoSp dst, iRegIorL2I p, iRegIorL2I q, rFlagsReg cr)
13895 %{
13896   match(Set dst (CmpLTMask p q));
13897   effect(KILL cr);
13898 
13899   ins_cost(3 * INSN_COST);
13900 
13901   format %{ "cmpw $p, $q\t# cmpLTMask\n\t"
13902             "csetw $dst, lt\n\t"
13903             "subw $dst, zr, $dst"
13904   %}
13905 
13906   ins_encode %{
13907     __ cmpw(as_Register($p$$reg), as_Register($q$$reg));
13908     __ csetw(as_Register($dst$$reg), Assembler::LT);
13909     __ subw(as_Register($dst$$reg), zr, as_Register($dst$$reg));
13910   %}
13911 
13912   ins_pipe(ialu_reg_reg);
13913 %}
13914 
13915 instruct cmpLTMask_reg_zero(iRegINoSp dst, iRegIorL2I src, immI0 zero, rFlagsReg cr)
13916 %{
13917   match(Set dst (CmpLTMask src zero));
13918   effect(KILL cr);
13919 
13920   ins_cost(INSN_COST);
13921 
13922   format %{ "asrw $dst, $src, #31\t# cmpLTMask0" %}
13923 
13924   ins_encode %{
13925     __ asrw(as_Register($dst$$reg), as_Register($src$$reg), 31);
13926   %}
13927 
13928   ins_pipe(ialu_reg_shift);
13929 %}
13930 
13931 // ============================================================================
13932 // Max and Min
13933 
13934 instruct minI_rReg(iRegINoSp dst, iRegI src1, iRegI src2, rFlagsReg cr)
13935 %{
13936   match(Set dst (MinI src1 src2));
13937 
13938   effect(DEF dst, USE src1, USE src2, KILL cr);
13939   size(8);
13940 
13941   ins_cost(INSN_COST * 3);
13942   format %{
13943     "cmpw $src1 $src2\t signed int\n\t"
13944     "cselw $dst, $src1, $src2 lt\t"
13945   %}
13946 
13947   ins_encode %{
13948     __ cmpw(as_Register($src1$$reg),
13949             as_Register($src2$$reg));
13950     __ cselw(as_Register($dst$$reg),
13951              as_Register($src1$$reg),
13952              as_Register($src2$$reg),
13953              Assembler::LT);
13954   %}
13955 
13956   ins_pipe(ialu_reg_reg);
13957 %}
13958 // FROM HERE
13959 
13960 instruct maxI_rReg(iRegINoSp dst, iRegI src1, iRegI src2, rFlagsReg cr)
13961 %{
13962   match(Set dst (MaxI src1 src2));
13963 
13964   effect(DEF dst, USE src1, USE src2, KILL cr);
13965   size(8);
13966 
13967   ins_cost(INSN_COST * 3);
13968   format %{
13969     "cmpw $src1 $src2\t signed int\n\t"
13970     "cselw $dst, $src1, $src2 gt\t"
13971   %}
13972 
13973   ins_encode %{
13974     __ cmpw(as_Register($src1$$reg),
13975             as_Register($src2$$reg));
13976     __ cselw(as_Register($dst$$reg),
13977              as_Register($src1$$reg),
13978              as_Register($src2$$reg),
13979              Assembler::GT);
13980   %}
13981 
13982   ins_pipe(ialu_reg_reg);
13983 %}
13984 
13985 // ============================================================================
13986 // Branch Instructions
13987 
13988 // Direct Branch.
13989 instruct branch(label lbl)
13990 %{
13991   match(Goto);
13992 
13993   effect(USE lbl);
13994 
13995   ins_cost(BRANCH_COST);
13996   format %{ "b  $lbl" %}
13997 
13998   ins_encode(aarch64_enc_b(lbl));
13999 
14000   ins_pipe(pipe_branch);
14001 %}
14002 
14003 // Conditional Near Branch
14004 instruct branchCon(cmpOp cmp, rFlagsReg cr, label lbl)
14005 %{
14006   // Same match rule as `branchConFar'.
14007   match(If cmp cr);
14008 
14009   effect(USE lbl);
14010 
14011   ins_cost(BRANCH_COST);
14012   // If set to 1 this indicates that the current instruction is a
14013   // short variant of a long branch. This avoids using this
14014   // instruction in first-pass matching. It will then only be used in
14015   // the `Shorten_branches' pass.
14016   // ins_short_branch(1);
14017   format %{ "b$cmp  $lbl" %}
14018 
14019   ins_encode(aarch64_enc_br_con(cmp, lbl));
14020 
14021   ins_pipe(pipe_branch_cond);
14022 %}
14023 
14024 // Conditional Near Branch Unsigned
14025 instruct branchConU(cmpOpU cmp, rFlagsRegU cr, label lbl)
14026 %{
14027   // Same match rule as `branchConFar'.
14028   match(If cmp cr);
14029 
14030   effect(USE lbl);
14031 
14032   ins_cost(BRANCH_COST);
14033   // If set to 1 this indicates that the current instruction is a
14034   // short variant of a long branch. This avoids using this
14035   // instruction in first-pass matching. It will then only be used in
14036   // the `Shorten_branches' pass.
14037   // ins_short_branch(1);
14038   format %{ "b$cmp  $lbl\t# unsigned" %}
14039 
14040   ins_encode(aarch64_enc_br_conU(cmp, lbl));
14041 
14042   ins_pipe(pipe_branch_cond);
14043 %}
14044 
14045 // Make use of CBZ and CBNZ.  These instructions, as well as being
14046 // shorter than (cmp; branch), have the additional benefit of not
14047 // killing the flags.
14048 
14049 instruct cmpI_imm0_branch(cmpOpEqNe cmp, iRegIorL2I op1, immI0 op2, label labl, rFlagsReg cr) %{
14050   match(If cmp (CmpI op1 op2));
14051   effect(USE labl);
14052 
14053   ins_cost(BRANCH_COST);
14054   format %{ "cbw$cmp   $op1, $labl" %}
14055   ins_encode %{
14056     Label* L = $labl$$label;
14057     Assembler::Condition cond = (Assembler::Condition)$cmp$$cmpcode;
14058     if (cond == Assembler::EQ)
14059       __ cbzw($op1$$Register, *L);
14060     else
14061       __ cbnzw($op1$$Register, *L);
14062   %}
14063   ins_pipe(pipe_cmp_branch);
14064 %}
14065 
14066 instruct cmpL_imm0_branch(cmpOpEqNe cmp, iRegL op1, immL0 op2, label labl, rFlagsReg cr) %{
14067   match(If cmp (CmpL op1 op2));
14068   effect(USE labl);
14069 
14070   ins_cost(BRANCH_COST);
14071   format %{ "cb$cmp   $op1, $labl" %}
14072   ins_encode %{
14073     Label* L = $labl$$label;
14074     Assembler::Condition cond = (Assembler::Condition)$cmp$$cmpcode;
14075     if (cond == Assembler::EQ)
14076       __ cbz($op1$$Register, *L);
14077     else
14078       __ cbnz($op1$$Register, *L);
14079   %}
14080   ins_pipe(pipe_cmp_branch);
14081 %}
14082 
14083 instruct cmpP_imm0_branch(cmpOpEqNe cmp, iRegP op1, immP0 op2, label labl, rFlagsReg cr) %{
14084   match(If cmp (CmpP op1 op2));
14085   effect(USE labl);
14086 
14087   ins_cost(BRANCH_COST);
14088   format %{ "cb$cmp   $op1, $labl" %}
14089   ins_encode %{
14090     Label* L = $labl$$label;
14091     Assembler::Condition cond = (Assembler::Condition)$cmp$$cmpcode;
14092     if (cond == Assembler::EQ)
14093       __ cbz($op1$$Register, *L);
14094     else
14095       __ cbnz($op1$$Register, *L);
14096   %}
14097   ins_pipe(pipe_cmp_branch);
14098 %}
14099 
14100 instruct cmpN_imm0_branch(cmpOpEqNe cmp, iRegN op1, immN0 op2, label labl, rFlagsReg cr) %{
14101   match(If cmp (CmpN op1 op2));
14102   effect(USE labl);
14103 
14104   ins_cost(BRANCH_COST);
14105   format %{ "cbw$cmp   $op1, $labl" %}
14106   ins_encode %{
14107     Label* L = $labl$$label;
14108     Assembler::Condition cond = (Assembler::Condition)$cmp$$cmpcode;
14109     if (cond == Assembler::EQ)
14110       __ cbzw($op1$$Register, *L);
14111     else
14112       __ cbnzw($op1$$Register, *L);
14113   %}
14114   ins_pipe(pipe_cmp_branch);
14115 %}
14116 
14117 instruct cmpP_narrowOop_imm0_branch(cmpOpEqNe cmp, iRegN oop, immP0 zero, label labl, rFlagsReg cr) %{
14118   match(If cmp (CmpP (DecodeN oop) zero));
14119   effect(USE labl);
14120 
14121   ins_cost(BRANCH_COST);
14122   format %{ "cb$cmp   $oop, $labl" %}
14123   ins_encode %{
14124     Label* L = $labl$$label;
14125     Assembler::Condition cond = (Assembler::Condition)$cmp$$cmpcode;
14126     if (cond == Assembler::EQ)
14127       __ cbzw($oop$$Register, *L);
14128     else
14129       __ cbnzw($oop$$Register, *L);
14130   %}
14131   ins_pipe(pipe_cmp_branch);
14132 %}
14133 
14134 instruct cmpUI_imm0_branch(cmpOpUEqNeLtGe cmp, iRegIorL2I op1, immI0 op2, label labl, rFlagsRegU cr) %{
14135   match(If cmp (CmpU op1 op2));
14136   effect(USE labl);
14137 
14138   ins_cost(BRANCH_COST);
14139   format %{ "cbw$cmp   $op1, $labl" %}
14140   ins_encode %{
14141     Label* L = $labl$$label;
14142     Assembler::Condition cond = (Assembler::Condition)$cmp$$cmpcode;
14143     if (cond == Assembler::EQ || cond == Assembler::LS)
14144       __ cbzw($op1$$Register, *L);
14145     else
14146       __ cbnzw($op1$$Register, *L);
14147   %}
14148   ins_pipe(pipe_cmp_branch);
14149 %}
14150 
14151 instruct cmpUL_imm0_branch(cmpOpUEqNeLtGe cmp, iRegL op1, immL0 op2, label labl, rFlagsRegU cr) %{
14152   match(If cmp (CmpUL op1 op2));
14153   effect(USE labl);
14154 
14155   ins_cost(BRANCH_COST);
14156   format %{ "cb$cmp   $op1, $labl" %}
14157   ins_encode %{
14158     Label* L = $labl$$label;
14159     Assembler::Condition cond = (Assembler::Condition)$cmp$$cmpcode;
14160     if (cond == Assembler::EQ || cond == Assembler::LS)
14161       __ cbz($op1$$Register, *L);
14162     else
14163       __ cbnz($op1$$Register, *L);
14164   %}
14165   ins_pipe(pipe_cmp_branch);
14166 %}
14167 
14168 // Test bit and Branch
14169 
14170 // Patterns for short (< 32KiB) variants
14171 instruct cmpL_branch_sign(cmpOpLtGe cmp, iRegL op1, immL0 op2, label labl) %{
14172   match(If cmp (CmpL op1 op2));
14173   effect(USE labl);
14174 
14175   ins_cost(BRANCH_COST);
14176   format %{ "cb$cmp   $op1, $labl # long" %}
14177   ins_encode %{
14178     Label* L = $labl$$label;
14179     Assembler::Condition cond =
14180       ((Assembler::Condition)$cmp$$cmpcode == Assembler::LT) ? Assembler::NE : Assembler::EQ;
14181     __ tbr(cond, $op1$$Register, 63, *L);
14182   %}
14183   ins_pipe(pipe_cmp_branch);
14184   ins_short_branch(1);
14185 %}
14186 
14187 instruct cmpI_branch_sign(cmpOpLtGe cmp, iRegIorL2I op1, immI0 op2, label labl) %{
14188   match(If cmp (CmpI op1 op2));
14189   effect(USE labl);
14190 
14191   ins_cost(BRANCH_COST);
14192   format %{ "cb$cmp   $op1, $labl # int" %}
14193   ins_encode %{
14194     Label* L = $labl$$label;
14195     Assembler::Condition cond =
14196       ((Assembler::Condition)$cmp$$cmpcode == Assembler::LT) ? Assembler::NE : Assembler::EQ;
14197     __ tbr(cond, $op1$$Register, 31, *L);
14198   %}
14199   ins_pipe(pipe_cmp_branch);
14200   ins_short_branch(1);
14201 %}
14202 
14203 instruct cmpL_branch_bit(cmpOpEqNe cmp, iRegL op1, immL op2, immL0 op3, label labl) %{
14204   match(If cmp (CmpL (AndL op1 op2) op3));
14205   predicate(is_power_of_2(n->in(2)->in(1)->in(2)->get_long()));
14206   effect(USE labl);
14207 
14208   ins_cost(BRANCH_COST);
14209   format %{ "tb$cmp   $op1, $op2, $labl" %}
14210   ins_encode %{
14211     Label* L = $labl$$label;
14212     Assembler::Condition cond = (Assembler::Condition)$cmp$$cmpcode;
14213     int bit = exact_log2($op2$$constant);
14214     __ tbr(cond, $op1$$Register, bit, *L);
14215   %}
14216   ins_pipe(pipe_cmp_branch);
14217   ins_short_branch(1);
14218 %}
14219 
14220 instruct cmpI_branch_bit(cmpOpEqNe cmp, iRegIorL2I op1, immI op2, immI0 op3, label labl) %{
14221   match(If cmp (CmpI (AndI op1 op2) op3));
14222   predicate(is_power_of_2(n->in(2)->in(1)->in(2)->get_int()));
14223   effect(USE labl);
14224 
14225   ins_cost(BRANCH_COST);
14226   format %{ "tb$cmp   $op1, $op2, $labl" %}
14227   ins_encode %{
14228     Label* L = $labl$$label;
14229     Assembler::Condition cond = (Assembler::Condition)$cmp$$cmpcode;
14230     int bit = exact_log2($op2$$constant);
14231     __ tbr(cond, $op1$$Register, bit, *L);
14232   %}
14233   ins_pipe(pipe_cmp_branch);
14234   ins_short_branch(1);
14235 %}
14236 
14237 // And far variants
14238 instruct far_cmpL_branch_sign(cmpOpLtGe cmp, iRegL op1, immL0 op2, label labl) %{
14239   match(If cmp (CmpL op1 op2));
14240   effect(USE labl);
14241 
14242   ins_cost(BRANCH_COST);
14243   format %{ "cb$cmp   $op1, $labl # long" %}
14244   ins_encode %{
14245     Label* L = $labl$$label;
14246     Assembler::Condition cond =
14247       ((Assembler::Condition)$cmp$$cmpcode == Assembler::LT) ? Assembler::NE : Assembler::EQ;
14248     __ tbr(cond, $op1$$Register, 63, *L, /*far*/true);
14249   %}
14250   ins_pipe(pipe_cmp_branch);
14251 %}
14252 
14253 instruct far_cmpI_branch_sign(cmpOpLtGe cmp, iRegIorL2I op1, immI0 op2, label labl) %{
14254   match(If cmp (CmpI op1 op2));
14255   effect(USE labl);
14256 
14257   ins_cost(BRANCH_COST);
14258   format %{ "cb$cmp   $op1, $labl # int" %}
14259   ins_encode %{
14260     Label* L = $labl$$label;
14261     Assembler::Condition cond =
14262       ((Assembler::Condition)$cmp$$cmpcode == Assembler::LT) ? Assembler::NE : Assembler::EQ;
14263     __ tbr(cond, $op1$$Register, 31, *L, /*far*/true);
14264   %}
14265   ins_pipe(pipe_cmp_branch);
14266 %}
14267 
14268 instruct far_cmpL_branch_bit(cmpOpEqNe cmp, iRegL op1, immL op2, immL0 op3, label labl) %{
14269   match(If cmp (CmpL (AndL op1 op2) op3));
14270   predicate(is_power_of_2(n->in(2)->in(1)->in(2)->get_long()));
14271   effect(USE labl);
14272 
14273   ins_cost(BRANCH_COST);
14274   format %{ "tb$cmp   $op1, $op2, $labl" %}
14275   ins_encode %{
14276     Label* L = $labl$$label;
14277     Assembler::Condition cond = (Assembler::Condition)$cmp$$cmpcode;
14278     int bit = exact_log2($op2$$constant);
14279     __ tbr(cond, $op1$$Register, bit, *L, /*far*/true);
14280   %}
14281   ins_pipe(pipe_cmp_branch);
14282 %}
14283 
14284 instruct far_cmpI_branch_bit(cmpOpEqNe cmp, iRegIorL2I op1, immI op2, immI0 op3, label labl) %{
14285   match(If cmp (CmpI (AndI op1 op2) op3));
14286   predicate(is_power_of_2(n->in(2)->in(1)->in(2)->get_int()));
14287   effect(USE labl);
14288 
14289   ins_cost(BRANCH_COST);
14290   format %{ "tb$cmp   $op1, $op2, $labl" %}
14291   ins_encode %{
14292     Label* L = $labl$$label;
14293     Assembler::Condition cond = (Assembler::Condition)$cmp$$cmpcode;
14294     int bit = exact_log2($op2$$constant);
14295     __ tbr(cond, $op1$$Register, bit, *L, /*far*/true);
14296   %}
14297   ins_pipe(pipe_cmp_branch);
14298 %}
14299 
14300 // Test bits
14301 
14302 instruct cmpL_and(cmpOp cmp, iRegL op1, immL op2, immL0 op3, rFlagsReg cr) %{
14303   match(Set cr (CmpL (AndL op1 op2) op3));
14304   predicate(Assembler::operand_valid_for_logical_immediate
14305             (/*is_32*/false, n->in(1)->in(2)->get_long()));
14306 
14307   ins_cost(INSN_COST);
14308   format %{ "tst $op1, $op2 # long" %}
14309   ins_encode %{
14310     __ tst($op1$$Register, $op2$$constant);
14311   %}
14312   ins_pipe(ialu_reg_reg);
14313 %}
14314 
14315 instruct cmpI_and(cmpOp cmp, iRegIorL2I op1, immI op2, immI0 op3, rFlagsReg cr) %{
14316   match(Set cr (CmpI (AndI op1 op2) op3));
14317   predicate(Assembler::operand_valid_for_logical_immediate
14318             (/*is_32*/true, n->in(1)->in(2)->get_int()));
14319 
14320   ins_cost(INSN_COST);
14321   format %{ "tst $op1, $op2 # int" %}
14322   ins_encode %{
14323     __ tstw($op1$$Register, $op2$$constant);
14324   %}
14325   ins_pipe(ialu_reg_reg);
14326 %}
14327 
14328 instruct cmpL_and_reg(cmpOp cmp, iRegL op1, iRegL op2, immL0 op3, rFlagsReg cr) %{
14329   match(Set cr (CmpL (AndL op1 op2) op3));
14330 
14331   ins_cost(INSN_COST);
14332   format %{ "tst $op1, $op2 # long" %}
14333   ins_encode %{
14334     __ tst($op1$$Register, $op2$$Register);
14335   %}
14336   ins_pipe(ialu_reg_reg);
14337 %}
14338 
14339 instruct cmpI_and_reg(cmpOp cmp, iRegIorL2I op1, iRegIorL2I op2, immI0 op3, rFlagsReg cr) %{
14340   match(Set cr (CmpI (AndI op1 op2) op3));
14341 
14342   ins_cost(INSN_COST);
14343   format %{ "tstw $op1, $op2 # int" %}
14344   ins_encode %{
14345     __ tstw($op1$$Register, $op2$$Register);
14346   %}
14347   ins_pipe(ialu_reg_reg);
14348 %}
14349 
14350 
14351 // Conditional Far Branch
14352 // Conditional Far Branch Unsigned
14353 // TODO: fixme
14354 
14355 // counted loop end branch near
14356 instruct branchLoopEnd(cmpOp cmp, rFlagsReg cr, label lbl)
14357 %{
14358   match(CountedLoopEnd cmp cr);
14359 
14360   effect(USE lbl);
14361 
14362   ins_cost(BRANCH_COST);
14363   // short variant.
14364   // ins_short_branch(1);
14365   format %{ "b$cmp $lbl \t// counted loop end" %}
14366 
14367   ins_encode(aarch64_enc_br_con(cmp, lbl));
14368 
14369   ins_pipe(pipe_branch);
14370 %}
14371 
14372 // counted loop end branch near Unsigned
14373 instruct branchLoopEndU(cmpOpU cmp, rFlagsRegU cr, label lbl)
14374 %{
14375   match(CountedLoopEnd cmp cr);
14376 
14377   effect(USE lbl);
14378 
14379   ins_cost(BRANCH_COST);
14380   // short variant.
14381   // ins_short_branch(1);
14382   format %{ "b$cmp $lbl \t// counted loop end unsigned" %}
14383 
14384   ins_encode(aarch64_enc_br_conU(cmp, lbl));
14385 
14386   ins_pipe(pipe_branch);
14387 %}
14388 
14389 // counted loop end branch far
14390 // counted loop end branch far unsigned
14391 // TODO: fixme
14392 
14393 // ============================================================================
14394 // inlined locking and unlocking
14395 
14396 instruct cmpFastLock(rFlagsReg cr, iRegP object, iRegP box, iRegPNoSp tmp, iRegPNoSp tmp2)
14397 %{
14398   match(Set cr (FastLock object box));
14399   effect(TEMP tmp, TEMP tmp2);
14400 
14401   // TODO
14402   // identify correct cost
14403   ins_cost(5 * INSN_COST);
14404   format %{ "fastlock $object,$box\t! kills $tmp,$tmp2" %}
14405 
14406   ins_encode(aarch64_enc_fast_lock(object, box, tmp, tmp2));
14407 
14408   ins_pipe(pipe_serial);
14409 %}
14410 
14411 instruct cmpFastUnlock(rFlagsReg cr, iRegP object, iRegP box, iRegPNoSp tmp, iRegPNoSp tmp2)
14412 %{
14413   match(Set cr (FastUnlock object box));
14414   effect(TEMP tmp, TEMP tmp2);
14415 
14416   ins_cost(5 * INSN_COST);
14417   format %{ "fastunlock $object,$box\t! kills $tmp, $tmp2" %}
14418 
14419   ins_encode(aarch64_enc_fast_unlock(object, box, tmp, tmp2));
14420 
14421   ins_pipe(pipe_serial);
14422 %}
14423 
14424 
14425 // ============================================================================
14426 // Safepoint Instructions
14427 
14428 // TODO
14429 // provide a near and far version of this code
14430 
14431 instruct safePoint(rFlagsReg cr, iRegP poll)
14432 %{
14433   match(SafePoint poll);
14434   effect(KILL cr);
14435 
14436   format %{
14437     "ldrw zr, [$poll]\t# Safepoint: poll for GC"
14438   %}
14439   ins_encode %{
14440     __ read_polling_page(as_Register($poll$$reg), relocInfo::poll_type);
14441   %}
14442   ins_pipe(pipe_serial); // ins_pipe(iload_reg_mem);
14443 %}
14444 
14445 
14446 // ============================================================================
14447 // Procedure Call/Return Instructions
14448 
14449 // Call Java Static Instruction
14450 
14451 instruct CallStaticJavaDirect(method meth)
14452 %{
14453   match(CallStaticJava);
14454 
14455   effect(USE meth);
14456 
14457   ins_cost(CALL_COST);
14458 
14459   format %{ "call,static $meth \t// ==> " %}
14460 
14461   ins_encode( aarch64_enc_java_static_call(meth),
14462               aarch64_enc_call_epilog );
14463 
14464   ins_pipe(pipe_class_call);
14465 %}
14466 
14467 // TO HERE
14468 
14469 // Call Java Dynamic Instruction
14470 instruct CallDynamicJavaDirect(method meth)
14471 %{
14472   match(CallDynamicJava);
14473 
14474   effect(USE meth);
14475 
14476   ins_cost(CALL_COST);
14477 
14478   format %{ "CALL,dynamic $meth \t// ==> " %}
14479 
14480   ins_encode( aarch64_enc_java_dynamic_call(meth),
14481                aarch64_enc_call_epilog );
14482 
14483   ins_pipe(pipe_class_call);
14484 %}
14485 
14486 // Call Runtime Instruction
14487 
14488 instruct CallRuntimeDirect(method meth)
14489 %{
14490   match(CallRuntime);
14491 
14492   effect(USE meth);
14493 
14494   ins_cost(CALL_COST);
14495 
14496   format %{ "CALL, runtime $meth" %}
14497 
14498   ins_encode( aarch64_enc_java_to_runtime(meth) );
14499 
14500   ins_pipe(pipe_class_call);
14501 %}
14502 
14503 // Call Runtime Instruction
14504 
14505 instruct CallLeafDirect(method meth)
14506 %{
14507   match(CallLeaf);
14508 
14509   effect(USE meth);
14510 
14511   ins_cost(CALL_COST);
14512 
14513   format %{ "CALL, runtime leaf $meth" %}
14514 
14515   ins_encode( aarch64_enc_java_to_runtime(meth) );
14516 
14517   ins_pipe(pipe_class_call);
14518 %}
14519 
14520 // Call Runtime Instruction
14521 
14522 instruct CallLeafNoFPDirect(method meth)
14523 %{
14524   match(CallLeafNoFP);
14525 
14526   effect(USE meth);
14527 
14528   ins_cost(CALL_COST);
14529 
14530   format %{ "CALL, runtime leaf nofp $meth" %}
14531 
14532   ins_encode( aarch64_enc_java_to_runtime(meth) );
14533 
14534   ins_pipe(pipe_class_call);
14535 %}
14536 
14537 // Tail Call; Jump from runtime stub to Java code.
14538 // Also known as an 'interprocedural jump'.
14539 // Target of jump will eventually return to caller.
14540 // TailJump below removes the return address.
14541 instruct TailCalljmpInd(iRegPNoSp jump_target, inline_cache_RegP method_oop)
14542 %{
14543   match(TailCall jump_target method_oop);
14544 
14545   ins_cost(CALL_COST);
14546 
14547   format %{ "br $jump_target\t# $method_oop holds method oop" %}
14548 
14549   ins_encode(aarch64_enc_tail_call(jump_target));
14550 
14551   ins_pipe(pipe_class_call);
14552 %}
14553 
14554 instruct TailjmpInd(iRegPNoSp jump_target, iRegP_R0 ex_oop)
14555 %{
14556   match(TailJump jump_target ex_oop);
14557 
14558   ins_cost(CALL_COST);
14559 
14560   format %{ "br $jump_target\t# $ex_oop holds exception oop" %}
14561 
14562   ins_encode(aarch64_enc_tail_jmp(jump_target));
14563 
14564   ins_pipe(pipe_class_call);
14565 %}
14566 
14567 // Create exception oop: created by stack-crawling runtime code.
14568 // Created exception is now available to this handler, and is setup
14569 // just prior to jumping to this handler. No code emitted.
14570 // TODO check
14571 // should ex_oop be in r0? intel uses rax, ppc cannot use r0 so uses rarg1
14572 instruct CreateException(iRegP_R0 ex_oop)
14573 %{
14574   match(Set ex_oop (CreateEx));
14575 
14576   format %{ " -- \t// exception oop; no code emitted" %}
14577 
14578   size(0);
14579 
14580   ins_encode( /*empty*/ );
14581 
14582   ins_pipe(pipe_class_empty);
14583 %}
14584 
14585 // Rethrow exception: The exception oop will come in the first
14586 // argument position. Then JUMP (not call) to the rethrow stub code.
14587 instruct RethrowException() %{
14588   match(Rethrow);
14589   ins_cost(CALL_COST);
14590 
14591   format %{ "b rethrow_stub" %}
14592 
14593   ins_encode( aarch64_enc_rethrow() );
14594 
14595   ins_pipe(pipe_class_call);
14596 %}
14597 
14598 
14599 // Return Instruction
14600 // epilog node loads ret address into lr as part of frame pop
14601 instruct Ret()
14602 %{
14603   match(Return);
14604 
14605   format %{ "ret\t// return register" %}
14606 
14607   ins_encode( aarch64_enc_ret() );
14608 
14609   ins_pipe(pipe_branch);
14610 %}
14611 
14612 // Die now.
14613 instruct ShouldNotReachHere() %{
14614   match(Halt);
14615 
14616   ins_cost(CALL_COST);
14617   format %{ "ShouldNotReachHere" %}
14618 
14619   ins_encode %{
14620     // +1 so NativeInstruction::is_sigill_zombie_not_entrant() doesn't
14621     // return true
14622     __ dpcs1(0xdead + 1);
14623   %}
14624 
14625   ins_pipe(pipe_class_default);
14626 %}
14627 
14628 // ============================================================================
14629 // Partial Subtype Check
14630 //
14631 // superklass array for an instance of the superklass.  Set a hidden
14632 // internal cache on a hit (cache is checked with exposed code in
14633 // gen_subtype_check()).  Return NZ for a miss or zero for a hit.  The
14634 // encoding ALSO sets flags.
14635 
14636 instruct partialSubtypeCheck(iRegP_R4 sub, iRegP_R0 super, iRegP_R2 temp, iRegP_R5 result, rFlagsReg cr)
14637 %{
14638   match(Set result (PartialSubtypeCheck sub super));
14639   effect(KILL cr, KILL temp);
14640 
14641   ins_cost(1100);  // slightly larger than the next version
14642   format %{ "partialSubtypeCheck $result, $sub, $super" %}
14643 
14644   ins_encode(aarch64_enc_partial_subtype_check(sub, super, temp, result));
14645 
14646   opcode(0x1); // Force zero of result reg on hit
14647 
14648   ins_pipe(pipe_class_memory);
14649 %}
14650 
14651 instruct partialSubtypeCheckVsZero(iRegP_R4 sub, iRegP_R0 super, iRegP_R2 temp, iRegP_R5 result, immP0 zero, rFlagsReg cr)
14652 %{
14653   match(Set cr (CmpP (PartialSubtypeCheck sub super) zero));
14654   effect(KILL temp, KILL result);
14655 
14656   ins_cost(1100);  // slightly larger than the next version
14657   format %{ "partialSubtypeCheck $result, $sub, $super == 0" %}
14658 
14659   ins_encode(aarch64_enc_partial_subtype_check(sub, super, temp, result));
14660 
14661   opcode(0x0); // Don't zero result reg on hit
14662 
14663   ins_pipe(pipe_class_memory);
14664 %}
14665 
14666 instruct string_compareU(iRegP_R1 str1, iRegI_R2 cnt1, iRegP_R3 str2, iRegI_R4 cnt2,
14667                         iRegI_R0 result, iRegP_R10 tmp1, iRegL_R11 tmp2, rFlagsReg cr)
14668 %{
14669   predicate(((StrCompNode*)n)->encoding() == StrIntrinsicNode::UU);
14670   match(Set result (StrComp (Binary str1 cnt1) (Binary str2 cnt2)));
14671   effect(KILL tmp1, KILL tmp2, USE_KILL str1, USE_KILL str2, USE_KILL cnt1, USE_KILL cnt2, KILL cr);
14672 
14673   format %{ "String Compare $str1,$cnt1,$str2,$cnt2 -> $result   # KILL $tmp1" %}
14674   ins_encode %{
14675     // Count is in 8-bit bytes; non-Compact chars are 16 bits.
14676     __ string_compare($str1$$Register, $str2$$Register,
14677                       $cnt1$$Register, $cnt2$$Register, $result$$Register,
14678                       $tmp1$$Register, $tmp2$$Register,
14679                       fnoreg, fnoreg, fnoreg, StrIntrinsicNode::UU);
14680   %}
14681   ins_pipe(pipe_class_memory);
14682 %}
14683 
14684 instruct string_compareL(iRegP_R1 str1, iRegI_R2 cnt1, iRegP_R3 str2, iRegI_R4 cnt2,
14685                         iRegI_R0 result, iRegP_R10 tmp1, iRegL_R11 tmp2, rFlagsReg cr)
14686 %{
14687   predicate(((StrCompNode*)n)->encoding() == StrIntrinsicNode::LL);
14688   match(Set result (StrComp (Binary str1 cnt1) (Binary str2 cnt2)));
14689   effect(KILL tmp1, KILL tmp2, USE_KILL str1, USE_KILL str2, USE_KILL cnt1, USE_KILL cnt2, KILL cr);
14690 
14691   format %{ "String Compare $str1,$cnt1,$str2,$cnt2 -> $result   # KILL $tmp1" %}
14692   ins_encode %{
14693     __ string_compare($str1$$Register, $str2$$Register,
14694                       $cnt1$$Register, $cnt2$$Register, $result$$Register,
14695                       $tmp1$$Register, $tmp2$$Register,
14696                       fnoreg, fnoreg, fnoreg, StrIntrinsicNode::LL);
14697   %}
14698   ins_pipe(pipe_class_memory);
14699 %}
14700 
14701 instruct string_compareUL(iRegP_R1 str1, iRegI_R2 cnt1, iRegP_R3 str2, iRegI_R4 cnt2,
14702                         iRegI_R0 result, iRegP_R10 tmp1, iRegL_R11 tmp2,
14703                         vRegD_V0 vtmp1, vRegD_V1 vtmp2, vRegD_V2 vtmp3, rFlagsReg cr)
14704 %{
14705   predicate(((StrCompNode*)n)->encoding() == StrIntrinsicNode::UL);
14706   match(Set result (StrComp (Binary str1 cnt1) (Binary str2 cnt2)));
14707   effect(KILL tmp1, KILL tmp2, KILL vtmp1, KILL vtmp2, KILL vtmp3,
14708          USE_KILL str1, USE_KILL str2, USE_KILL cnt1, USE_KILL cnt2, KILL cr);
14709 
14710   format %{ "String Compare $str1,$cnt1,$str2,$cnt2 -> $result   # KILL $tmp1, $tmp2, $vtmp1, $vtmp2, $vtmp3" %}
14711   ins_encode %{
14712     __ string_compare($str1$$Register, $str2$$Register,
14713                       $cnt1$$Register, $cnt2$$Register, $result$$Register,
14714                       $tmp1$$Register, $tmp2$$Register,
14715                       $vtmp1$$FloatRegister, $vtmp2$$FloatRegister,
14716                       $vtmp3$$FloatRegister, StrIntrinsicNode::UL);
14717   %}
14718   ins_pipe(pipe_class_memory);
14719 %}
14720 
14721 instruct string_compareLU(iRegP_R1 str1, iRegI_R2 cnt1, iRegP_R3 str2, iRegI_R4 cnt2,
14722                         iRegI_R0 result, iRegP_R10 tmp1, iRegL_R11 tmp2,
14723                         vRegD_V0 vtmp1, vRegD_V1 vtmp2, vRegD_V2 vtmp3, rFlagsReg cr)
14724 %{
14725   predicate(((StrCompNode*)n)->encoding() == StrIntrinsicNode::LU);
14726   match(Set result (StrComp (Binary str1 cnt1) (Binary str2 cnt2)));
14727   effect(KILL tmp1, KILL tmp2, KILL vtmp1, KILL vtmp2, KILL vtmp3,
14728          USE_KILL str1, USE_KILL str2, USE_KILL cnt1, USE_KILL cnt2, KILL cr);
14729 
14730   format %{ "String Compare $str1,$cnt1,$str2,$cnt2 -> $result   # KILL $tmp1, $tmp2, $vtmp1, $vtmp2, $vtmp3" %}
14731   ins_encode %{
14732     __ string_compare($str1$$Register, $str2$$Register,
14733                       $cnt1$$Register, $cnt2$$Register, $result$$Register,
14734                       $tmp1$$Register, $tmp2$$Register,
14735                       $vtmp1$$FloatRegister, $vtmp2$$FloatRegister,
14736                       $vtmp3$$FloatRegister,StrIntrinsicNode::LU);
14737   %}
14738   ins_pipe(pipe_class_memory);
14739 %}
14740 
14741 instruct string_indexofUU(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2, iRegI_R2 cnt2,
14742        iRegI_R0 result, iRegINoSp tmp1, iRegINoSp tmp2, iRegINoSp tmp3,
14743        iRegINoSp tmp4, iRegINoSp tmp5, iRegINoSp tmp6, rFlagsReg cr)
14744 %{
14745   predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::UU);
14746   match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 cnt2)));
14747   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt1, USE_KILL cnt2,
14748          TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, TEMP tmp5, TEMP tmp6, KILL cr);
14749   format %{ "String IndexOf $str1,$cnt1,$str2,$cnt2 -> $result (UU)" %}
14750 
14751   ins_encode %{
14752     __ string_indexof($str1$$Register, $str2$$Register,
14753                       $cnt1$$Register, $cnt2$$Register,
14754                       $tmp1$$Register, $tmp2$$Register,
14755                       $tmp3$$Register, $tmp4$$Register,
14756                       $tmp5$$Register, $tmp6$$Register,
14757                       -1, $result$$Register, StrIntrinsicNode::UU);
14758   %}
14759   ins_pipe(pipe_class_memory);
14760 %}
14761 
14762 instruct string_indexofLL(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2, iRegI_R2 cnt2,
14763        iRegI_R0 result, iRegINoSp tmp1, iRegINoSp tmp2, iRegINoSp tmp3,
14764        iRegINoSp tmp4, iRegINoSp tmp5, iRegINoSp tmp6, rFlagsReg cr)
14765 %{
14766   predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::LL);
14767   match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 cnt2)));
14768   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt1, USE_KILL cnt2,
14769          TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, TEMP tmp5, TEMP tmp6, KILL cr);
14770   format %{ "String IndexOf $str1,$cnt1,$str2,$cnt2 -> $result (LL)" %}
14771 
14772   ins_encode %{
14773     __ string_indexof($str1$$Register, $str2$$Register,
14774                       $cnt1$$Register, $cnt2$$Register,
14775                       $tmp1$$Register, $tmp2$$Register,
14776                       $tmp3$$Register, $tmp4$$Register,
14777                       $tmp5$$Register, $tmp6$$Register,
14778                       -1, $result$$Register, StrIntrinsicNode::LL);
14779   %}
14780   ins_pipe(pipe_class_memory);
14781 %}
14782 
14783 instruct string_indexofUL(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2, iRegI_R2 cnt2,
14784        iRegI_R0 result, iRegINoSp tmp1, iRegINoSp tmp2, iRegINoSp tmp3,
14785        iRegINoSp tmp4, iRegINoSp tmp5, iRegINoSp tmp6, rFlagsReg cr)
14786 %{
14787   predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::UL);
14788   match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 cnt2)));
14789   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt1, USE_KILL cnt2,
14790          TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, TEMP tmp5, TEMP tmp6, KILL cr);
14791   format %{ "String IndexOf $str1,$cnt1,$str2,$cnt2 -> $result (UL)" %}
14792 
14793   ins_encode %{
14794     __ string_indexof($str1$$Register, $str2$$Register,
14795                       $cnt1$$Register, $cnt2$$Register,
14796                       $tmp1$$Register, $tmp2$$Register,
14797                       $tmp3$$Register, $tmp4$$Register,
14798                       $tmp5$$Register, $tmp6$$Register,
14799                       -1, $result$$Register, StrIntrinsicNode::UL);
14800   %}
14801   ins_pipe(pipe_class_memory);
14802 %}
14803 
14804 instruct string_indexof_conUU(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2,
14805                  immI_le_4 int_cnt2, iRegI_R0 result, iRegINoSp tmp1, iRegINoSp tmp2,
14806                  iRegINoSp tmp3, iRegINoSp tmp4, rFlagsReg cr)
14807 %{
14808   predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::UU);
14809   match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 int_cnt2)));
14810   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt1,
14811          TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, KILL cr);
14812   format %{ "String IndexOf $str1,$cnt1,$str2,$int_cnt2 -> $result (UU)" %}
14813 
14814   ins_encode %{
14815     int icnt2 = (int)$int_cnt2$$constant;
14816     __ string_indexof($str1$$Register, $str2$$Register,
14817                       $cnt1$$Register, zr,
14818                       $tmp1$$Register, $tmp2$$Register,
14819                       $tmp3$$Register, $tmp4$$Register, zr, zr,
14820                       icnt2, $result$$Register, StrIntrinsicNode::UU);
14821   %}
14822   ins_pipe(pipe_class_memory);
14823 %}
14824 
14825 instruct string_indexof_conLL(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2,
14826                  immI_le_4 int_cnt2, iRegI_R0 result, iRegINoSp tmp1, iRegINoSp tmp2,
14827                  iRegINoSp tmp3, iRegINoSp tmp4, rFlagsReg cr)
14828 %{
14829   predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::LL);
14830   match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 int_cnt2)));
14831   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt1,
14832          TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, KILL cr);
14833   format %{ "String IndexOf $str1,$cnt1,$str2,$int_cnt2 -> $result (LL)" %}
14834 
14835   ins_encode %{
14836     int icnt2 = (int)$int_cnt2$$constant;
14837     __ string_indexof($str1$$Register, $str2$$Register,
14838                       $cnt1$$Register, zr,
14839                       $tmp1$$Register, $tmp2$$Register,
14840                       $tmp3$$Register, $tmp4$$Register, zr, zr,
14841                       icnt2, $result$$Register, StrIntrinsicNode::LL);
14842   %}
14843   ins_pipe(pipe_class_memory);
14844 %}
14845 
14846 instruct string_indexof_conUL(iRegP_R1 str1, iRegI_R4 cnt1, iRegP_R3 str2,
14847                  immI_1 int_cnt2, iRegI_R0 result, iRegINoSp tmp1, iRegINoSp tmp2,
14848                  iRegINoSp tmp3, iRegINoSp tmp4, rFlagsReg cr)
14849 %{
14850   predicate(((StrIndexOfNode*)n)->encoding() == StrIntrinsicNode::UL);
14851   match(Set result (StrIndexOf (Binary str1 cnt1) (Binary str2 int_cnt2)));
14852   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt1,
14853          TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, KILL cr);
14854   format %{ "String IndexOf $str1,$cnt1,$str2,$int_cnt2 -> $result (UL)" %}
14855 
14856   ins_encode %{
14857     int icnt2 = (int)$int_cnt2$$constant;
14858     __ string_indexof($str1$$Register, $str2$$Register,
14859                       $cnt1$$Register, zr,
14860                       $tmp1$$Register, $tmp2$$Register,
14861                       $tmp3$$Register, $tmp4$$Register, zr, zr,
14862                       icnt2, $result$$Register, StrIntrinsicNode::UL);
14863   %}
14864   ins_pipe(pipe_class_memory);
14865 %}
14866 
14867 instruct string_indexofU_char(iRegP_R1 str1, iRegI_R2 cnt1, iRegI_R3 ch,
14868                               iRegI_R0 result, iRegINoSp tmp1, iRegINoSp tmp2,
14869                               iRegINoSp tmp3, rFlagsReg cr)
14870 %{
14871   match(Set result (StrIndexOfChar (Binary str1 cnt1) ch));
14872   effect(USE_KILL str1, USE_KILL cnt1, USE_KILL ch,
14873          TEMP tmp1, TEMP tmp2, TEMP tmp3, KILL cr);
14874 
14875   format %{ "String IndexOf char[] $str1,$cnt1,$ch -> $result" %}
14876 
14877   ins_encode %{
14878     __ string_indexof_char($str1$$Register, $cnt1$$Register, $ch$$Register,
14879                            $result$$Register, $tmp1$$Register, $tmp2$$Register,
14880                            $tmp3$$Register);
14881   %}
14882   ins_pipe(pipe_class_memory);
14883 %}
14884 
14885 instruct string_equalsL(iRegP_R1 str1, iRegP_R3 str2, iRegI_R4 cnt,
14886                         iRegI_R0 result, rFlagsReg cr)
14887 %{
14888   predicate(((StrEqualsNode*)n)->encoding() == StrIntrinsicNode::LL);
14889   match(Set result (StrEquals (Binary str1 str2) cnt));
14890   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt, KILL cr);
14891 
14892   format %{ "String Equals $str1,$str2,$cnt -> $result" %}
14893   ins_encode %{
14894     // Count is in 8-bit bytes; non-Compact chars are 16 bits.
14895     __ string_equals($str1$$Register, $str2$$Register,
14896                      $result$$Register, $cnt$$Register, 1);
14897   %}
14898   ins_pipe(pipe_class_memory);
14899 %}
14900 
14901 instruct string_equalsU(iRegP_R1 str1, iRegP_R3 str2, iRegI_R4 cnt,
14902                         iRegI_R0 result, rFlagsReg cr)
14903 %{
14904   predicate(((StrEqualsNode*)n)->encoding() == StrIntrinsicNode::UU);
14905   match(Set result (StrEquals (Binary str1 str2) cnt));
14906   effect(USE_KILL str1, USE_KILL str2, USE_KILL cnt, KILL cr);
14907 
14908   format %{ "String Equals $str1,$str2,$cnt -> $result" %}
14909   ins_encode %{
14910     // Count is in 8-bit bytes; non-Compact chars are 16 bits.
14911     __ string_equals($str1$$Register, $str2$$Register,
14912                      $result$$Register, $cnt$$Register, 2);
14913   %}
14914   ins_pipe(pipe_class_memory);
14915 %}
14916 
14917 instruct array_equalsB(iRegP_R1 ary1, iRegP_R2 ary2, iRegI_R0 result,
14918                        iRegP_R3 tmp1, iRegP_R4 tmp2, iRegP_R5 tmp3,
14919                        iRegP_R10 tmp, rFlagsReg cr)
14920 %{
14921   predicate(((AryEqNode*)n)->encoding() == StrIntrinsicNode::LL);
14922   match(Set result (AryEq ary1 ary2));
14923   effect(KILL tmp, USE_KILL ary1, USE_KILL ary2, TEMP tmp1, TEMP tmp2, TEMP tmp3, KILL cr);
14924 
14925   format %{ "Array Equals $ary1,ary2 -> $result    // KILL $tmp" %}
14926   ins_encode %{
14927     __ arrays_equals($ary1$$Register, $ary2$$Register,
14928                      $tmp1$$Register, $tmp2$$Register, $tmp3$$Register,
14929                      $result$$Register, $tmp$$Register, 1);
14930     %}
14931   ins_pipe(pipe_class_memory);
14932 %}
14933 
14934 instruct array_equalsC(iRegP_R1 ary1, iRegP_R2 ary2, iRegI_R0 result,
14935                        iRegP_R3 tmp1, iRegP_R4 tmp2, iRegP_R5 tmp3,
14936                        iRegP_R10 tmp, rFlagsReg cr)
14937 %{
14938   predicate(((AryEqNode*)n)->encoding() == StrIntrinsicNode::UU);
14939   match(Set result (AryEq ary1 ary2));
14940   effect(KILL tmp, USE_KILL ary1, USE_KILL ary2, TEMP tmp1, TEMP tmp2, TEMP tmp3, KILL cr);
14941 
14942   format %{ "Array Equals $ary1,ary2 -> $result    // KILL $tmp" %}
14943   ins_encode %{
14944     __ arrays_equals($ary1$$Register, $ary2$$Register,
14945                      $tmp1$$Register, $tmp2$$Register, $tmp3$$Register,
14946                      $result$$Register, $tmp$$Register, 2);
14947   %}
14948   ins_pipe(pipe_class_memory);
14949 %}
14950 
14951 instruct has_negatives(iRegP_R1 ary1, iRegI_R2 len, iRegI_R0 result, rFlagsReg cr)
14952 %{
14953   match(Set result (HasNegatives ary1 len));
14954   effect(USE_KILL ary1, USE_KILL len, KILL cr);
14955   format %{ "has negatives byte[] $ary1,$len -> $result" %}
14956   ins_encode %{
14957     __ has_negatives($ary1$$Register, $len$$Register, $result$$Register);
14958   %}
14959   ins_pipe( pipe_slow );
14960 %}
14961 
14962 // fast char[] to byte[] compression
14963 instruct string_compress(iRegP_R2 src, iRegP_R1 dst, iRegI_R3 len,
14964                          vRegD_V0 tmp1, vRegD_V1 tmp2,
14965                          vRegD_V2 tmp3, vRegD_V3 tmp4,
14966                          iRegI_R0 result, rFlagsReg cr)
14967 %{
14968   match(Set result (StrCompressedCopy src (Binary dst len)));
14969   effect(TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, USE_KILL src, USE_KILL dst, USE_KILL len, KILL cr);
14970 
14971   format %{ "String Compress $src,$dst -> $result    // KILL R1, R2, R3, R4" %}
14972   ins_encode %{
14973     __ char_array_compress($src$$Register, $dst$$Register, $len$$Register,
14974                            $tmp1$$FloatRegister, $tmp2$$FloatRegister,
14975                            $tmp3$$FloatRegister, $tmp4$$FloatRegister,
14976                            $result$$Register);
14977   %}
14978   ins_pipe( pipe_slow );
14979 %}
14980 
14981 // fast byte[] to char[] inflation
14982 instruct string_inflate(Universe dummy, iRegP_R0 src, iRegP_R1 dst, iRegI_R2 len,
14983                         vRegD_V0 tmp1, vRegD_V1 tmp2, vRegD_V2 tmp3, iRegP_R3 tmp4, rFlagsReg cr)
14984 %{
14985   match(Set dummy (StrInflatedCopy src (Binary dst len)));
14986   effect(TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, USE_KILL src, USE_KILL dst, USE_KILL len, KILL cr);
14987 
14988   format %{ "String Inflate $src,$dst    // KILL $tmp1, $tmp2" %}
14989   ins_encode %{
14990     __ byte_array_inflate($src$$Register, $dst$$Register, $len$$Register,
14991                           $tmp1$$FloatRegister, $tmp2$$FloatRegister, $tmp3$$FloatRegister, $tmp4$$Register);
14992   %}
14993   ins_pipe(pipe_class_memory);
14994 %}
14995 
14996 // encode char[] to byte[] in ISO_8859_1
14997 instruct encode_iso_array(iRegP_R2 src, iRegP_R1 dst, iRegI_R3 len,
14998                           vRegD_V0 Vtmp1, vRegD_V1 Vtmp2,
14999                           vRegD_V2 Vtmp3, vRegD_V3 Vtmp4,
15000                           iRegI_R0 result, rFlagsReg cr)
15001 %{
15002   match(Set result (EncodeISOArray src (Binary dst len)));
15003   effect(USE_KILL src, USE_KILL dst, USE_KILL len,
15004          KILL Vtmp1, KILL Vtmp2, KILL Vtmp3, KILL Vtmp4, KILL cr);
15005 
15006   format %{ "Encode array $src,$dst,$len -> $result" %}
15007   ins_encode %{
15008     __ encode_iso_array($src$$Register, $dst$$Register, $len$$Register,
15009          $result$$Register, $Vtmp1$$FloatRegister,  $Vtmp2$$FloatRegister,
15010          $Vtmp3$$FloatRegister,  $Vtmp4$$FloatRegister);
15011   %}
15012   ins_pipe( pipe_class_memory );
15013 %}
15014 
15015 // ============================================================================
15016 // This name is KNOWN by the ADLC and cannot be changed.
15017 // The ADLC forces a 'TypeRawPtr::BOTTOM' output type
15018 // for this guy.
15019 instruct tlsLoadP(thread_RegP dst)
15020 %{
15021   match(Set dst (ThreadLocal));
15022 
15023   ins_cost(0);
15024 
15025   format %{ " -- \t// $dst=Thread::current(), empty" %}
15026 
15027   size(0);
15028 
15029   ins_encode( /*empty*/ );
15030 
15031   ins_pipe(pipe_class_empty);
15032 %}
15033 
15034 // ====================VECTOR INSTRUCTIONS=====================================
15035 
15036 // Load vector (32 bits)
15037 instruct loadV4(vecD dst, vmem4 mem)
15038 %{
15039   predicate(n->as_LoadVector()->memory_size() == 4);
15040   match(Set dst (LoadVector mem));
15041   ins_cost(4 * INSN_COST);
15042   format %{ "ldrs   $dst,$mem\t# vector (32 bits)" %}
15043   ins_encode( aarch64_enc_ldrvS(dst, mem) );
15044   ins_pipe(vload_reg_mem64);
15045 %}
15046 
15047 // Load vector (64 bits)
15048 instruct loadV8(vecD dst, vmem8 mem)
15049 %{
15050   predicate(n->as_LoadVector()->memory_size() == 8);
15051   match(Set dst (LoadVector mem));
15052   ins_cost(4 * INSN_COST);
15053   format %{ "ldrd   $dst,$mem\t# vector (64 bits)" %}
15054   ins_encode( aarch64_enc_ldrvD(dst, mem) );
15055   ins_pipe(vload_reg_mem64);
15056 %}
15057 
15058 // Load Vector (128 bits)
15059 instruct loadV16(vecX dst, vmem16 mem)
15060 %{
15061   predicate(n->as_LoadVector()->memory_size() == 16);
15062   match(Set dst (LoadVector mem));
15063   ins_cost(4 * INSN_COST);
15064   format %{ "ldrq   $dst,$mem\t# vector (128 bits)" %}
15065   ins_encode( aarch64_enc_ldrvQ(dst, mem) );
15066   ins_pipe(vload_reg_mem128);
15067 %}
15068 
15069 // Store Vector (32 bits)
15070 instruct storeV4(vecD src, vmem4 mem)
15071 %{
15072   predicate(n->as_StoreVector()->memory_size() == 4);
15073   match(Set mem (StoreVector mem src));
15074   ins_cost(4 * INSN_COST);
15075   format %{ "strs   $mem,$src\t# vector (32 bits)" %}
15076   ins_encode( aarch64_enc_strvS(src, mem) );
15077   ins_pipe(vstore_reg_mem64);
15078 %}
15079 
15080 // Store Vector (64 bits)
15081 instruct storeV8(vecD src, vmem8 mem)
15082 %{
15083   predicate(n->as_StoreVector()->memory_size() == 8);
15084   match(Set mem (StoreVector mem src));
15085   ins_cost(4 * INSN_COST);
15086   format %{ "strd   $mem,$src\t# vector (64 bits)" %}
15087   ins_encode( aarch64_enc_strvD(src, mem) );
15088   ins_pipe(vstore_reg_mem64);
15089 %}
15090 
15091 // Store Vector (128 bits)
15092 instruct storeV16(vecX src, vmem16 mem)
15093 %{
15094   predicate(n->as_StoreVector()->memory_size() == 16);
15095   match(Set mem (StoreVector mem src));
15096   ins_cost(4 * INSN_COST);
15097   format %{ "strq   $mem,$src\t# vector (128 bits)" %}
15098   ins_encode( aarch64_enc_strvQ(src, mem) );
15099   ins_pipe(vstore_reg_mem128);
15100 %}
15101 
15102 instruct replicate8B(vecD dst, iRegIorL2I src)
15103 %{
15104   predicate(n->as_Vector()->length() == 4 ||
15105             n->as_Vector()->length() == 8);
15106   match(Set dst (ReplicateB src));
15107   ins_cost(INSN_COST);
15108   format %{ "dup  $dst, $src\t# vector (8B)" %}
15109   ins_encode %{
15110     __ dup(as_FloatRegister($dst$$reg), __ T8B, as_Register($src$$reg));
15111   %}
15112   ins_pipe(vdup_reg_reg64);
15113 %}
15114 
15115 instruct replicate16B(vecX dst, iRegIorL2I src)
15116 %{
15117   predicate(n->as_Vector()->length() == 16);
15118   match(Set dst (ReplicateB src));
15119   ins_cost(INSN_COST);
15120   format %{ "dup  $dst, $src\t# vector (16B)" %}
15121   ins_encode %{
15122     __ dup(as_FloatRegister($dst$$reg), __ T16B, as_Register($src$$reg));
15123   %}
15124   ins_pipe(vdup_reg_reg128);
15125 %}
15126 
15127 instruct replicate8B_imm(vecD dst, immI con)
15128 %{
15129   predicate(n->as_Vector()->length() == 4 ||
15130             n->as_Vector()->length() == 8);
15131   match(Set dst (ReplicateB con));
15132   ins_cost(INSN_COST);
15133   format %{ "movi  $dst, $con\t# vector(8B)" %}
15134   ins_encode %{
15135     __ mov(as_FloatRegister($dst$$reg), __ T8B, $con$$constant & 0xff);
15136   %}
15137   ins_pipe(vmovi_reg_imm64);
15138 %}
15139 
15140 instruct replicate16B_imm(vecX dst, immI con)
15141 %{
15142   predicate(n->as_Vector()->length() == 16);
15143   match(Set dst (ReplicateB con));
15144   ins_cost(INSN_COST);
15145   format %{ "movi  $dst, $con\t# vector(16B)" %}
15146   ins_encode %{
15147     __ mov(as_FloatRegister($dst$$reg), __ T16B, $con$$constant & 0xff);
15148   %}
15149   ins_pipe(vmovi_reg_imm128);
15150 %}
15151 
15152 instruct replicate4S(vecD dst, iRegIorL2I src)
15153 %{
15154   predicate(n->as_Vector()->length() == 2 ||
15155             n->as_Vector()->length() == 4);
15156   match(Set dst (ReplicateS src));
15157   ins_cost(INSN_COST);
15158   format %{ "dup  $dst, $src\t# vector (4S)" %}
15159   ins_encode %{
15160     __ dup(as_FloatRegister($dst$$reg), __ T4H, as_Register($src$$reg));
15161   %}
15162   ins_pipe(vdup_reg_reg64);
15163 %}
15164 
15165 instruct replicate8S(vecX dst, iRegIorL2I src)
15166 %{
15167   predicate(n->as_Vector()->length() == 8);
15168   match(Set dst (ReplicateS src));
15169   ins_cost(INSN_COST);
15170   format %{ "dup  $dst, $src\t# vector (8S)" %}
15171   ins_encode %{
15172     __ dup(as_FloatRegister($dst$$reg), __ T8H, as_Register($src$$reg));
15173   %}
15174   ins_pipe(vdup_reg_reg128);
15175 %}
15176 
15177 instruct replicate4S_imm(vecD dst, immI con)
15178 %{
15179   predicate(n->as_Vector()->length() == 2 ||
15180             n->as_Vector()->length() == 4);
15181   match(Set dst (ReplicateS con));
15182   ins_cost(INSN_COST);
15183   format %{ "movi  $dst, $con\t# vector(4H)" %}
15184   ins_encode %{
15185     __ mov(as_FloatRegister($dst$$reg), __ T4H, $con$$constant & 0xffff);
15186   %}
15187   ins_pipe(vmovi_reg_imm64);
15188 %}
15189 
15190 instruct replicate8S_imm(vecX dst, immI con)
15191 %{
15192   predicate(n->as_Vector()->length() == 8);
15193   match(Set dst (ReplicateS con));
15194   ins_cost(INSN_COST);
15195   format %{ "movi  $dst, $con\t# vector(8H)" %}
15196   ins_encode %{
15197     __ mov(as_FloatRegister($dst$$reg), __ T8H, $con$$constant & 0xffff);
15198   %}
15199   ins_pipe(vmovi_reg_imm128);
15200 %}
15201 
15202 instruct replicate2I(vecD dst, iRegIorL2I src)
15203 %{
15204   predicate(n->as_Vector()->length() == 2);
15205   match(Set dst (ReplicateI src));
15206   ins_cost(INSN_COST);
15207   format %{ "dup  $dst, $src\t# vector (2I)" %}
15208   ins_encode %{
15209     __ dup(as_FloatRegister($dst$$reg), __ T2S, as_Register($src$$reg));
15210   %}
15211   ins_pipe(vdup_reg_reg64);
15212 %}
15213 
15214 instruct replicate4I(vecX dst, iRegIorL2I src)
15215 %{
15216   predicate(n->as_Vector()->length() == 4);
15217   match(Set dst (ReplicateI src));
15218   ins_cost(INSN_COST);
15219   format %{ "dup  $dst, $src\t# vector (4I)" %}
15220   ins_encode %{
15221     __ dup(as_FloatRegister($dst$$reg), __ T4S, as_Register($src$$reg));
15222   %}
15223   ins_pipe(vdup_reg_reg128);
15224 %}
15225 
15226 instruct replicate2I_imm(vecD dst, immI con)
15227 %{
15228   predicate(n->as_Vector()->length() == 2);
15229   match(Set dst (ReplicateI con));
15230   ins_cost(INSN_COST);
15231   format %{ "movi  $dst, $con\t# vector(2I)" %}
15232   ins_encode %{
15233     __ mov(as_FloatRegister($dst$$reg), __ T2S, $con$$constant);
15234   %}
15235   ins_pipe(vmovi_reg_imm64);
15236 %}
15237 
15238 instruct replicate4I_imm(vecX dst, immI con)
15239 %{
15240   predicate(n->as_Vector()->length() == 4);
15241   match(Set dst (ReplicateI con));
15242   ins_cost(INSN_COST);
15243   format %{ "movi  $dst, $con\t# vector(4I)" %}
15244   ins_encode %{
15245     __ mov(as_FloatRegister($dst$$reg), __ T4S, $con$$constant);
15246   %}
15247   ins_pipe(vmovi_reg_imm128);
15248 %}
15249 
15250 instruct replicate2L(vecX dst, iRegL src)
15251 %{
15252   predicate(n->as_Vector()->length() == 2);
15253   match(Set dst (ReplicateL src));
15254   ins_cost(INSN_COST);
15255   format %{ "dup  $dst, $src\t# vector (2L)" %}
15256   ins_encode %{
15257     __ dup(as_FloatRegister($dst$$reg), __ T2D, as_Register($src$$reg));
15258   %}
15259   ins_pipe(vdup_reg_reg128);
15260 %}
15261 
15262 instruct replicate2L_zero(vecX dst, immI0 zero)
15263 %{
15264   predicate(n->as_Vector()->length() == 2);
15265   match(Set dst (ReplicateI zero));
15266   ins_cost(INSN_COST);
15267   format %{ "movi  $dst, $zero\t# vector(4I)" %}
15268   ins_encode %{
15269     __ eor(as_FloatRegister($dst$$reg), __ T16B,
15270            as_FloatRegister($dst$$reg),
15271            as_FloatRegister($dst$$reg));
15272   %}
15273   ins_pipe(vmovi_reg_imm128);
15274 %}
15275 
15276 instruct replicate2F(vecD dst, vRegF src)
15277 %{
15278   predicate(n->as_Vector()->length() == 2);
15279   match(Set dst (ReplicateF src));
15280   ins_cost(INSN_COST);
15281   format %{ "dup  $dst, $src\t# vector (2F)" %}
15282   ins_encode %{
15283     __ dup(as_FloatRegister($dst$$reg), __ T2S,
15284            as_FloatRegister($src$$reg));
15285   %}
15286   ins_pipe(vdup_reg_freg64);
15287 %}
15288 
15289 instruct replicate4F(vecX dst, vRegF src)
15290 %{
15291   predicate(n->as_Vector()->length() == 4);
15292   match(Set dst (ReplicateF src));
15293   ins_cost(INSN_COST);
15294   format %{ "dup  $dst, $src\t# vector (4F)" %}
15295   ins_encode %{
15296     __ dup(as_FloatRegister($dst$$reg), __ T4S,
15297            as_FloatRegister($src$$reg));
15298   %}
15299   ins_pipe(vdup_reg_freg128);
15300 %}
15301 
15302 instruct replicate2D(vecX dst, vRegD src)
15303 %{
15304   predicate(n->as_Vector()->length() == 2);
15305   match(Set dst (ReplicateD src));
15306   ins_cost(INSN_COST);
15307   format %{ "dup  $dst, $src\t# vector (2D)" %}
15308   ins_encode %{
15309     __ dup(as_FloatRegister($dst$$reg), __ T2D,
15310            as_FloatRegister($src$$reg));
15311   %}
15312   ins_pipe(vdup_reg_dreg128);
15313 %}
15314 
15315 // ====================REDUCTION ARITHMETIC====================================
15316 
15317 instruct reduce_add2I(iRegINoSp dst, iRegIorL2I src1, vecD src2, iRegINoSp tmp, iRegINoSp tmp2)
15318 %{
15319   match(Set dst (AddReductionVI src1 src2));
15320   ins_cost(INSN_COST);
15321   effect(TEMP tmp, TEMP tmp2);
15322   format %{ "umov  $tmp, $src2, S, 0\n\t"
15323             "umov  $tmp2, $src2, S, 1\n\t"
15324             "addw  $dst, $src1, $tmp\n\t"
15325             "addw  $dst, $dst, $tmp2\t add reduction2i"
15326   %}
15327   ins_encode %{
15328     __ umov($tmp$$Register, as_FloatRegister($src2$$reg), __ S, 0);
15329     __ umov($tmp2$$Register, as_FloatRegister($src2$$reg), __ S, 1);
15330     __ addw($dst$$Register, $src1$$Register, $tmp$$Register);
15331     __ addw($dst$$Register, $dst$$Register, $tmp2$$Register);
15332   %}
15333   ins_pipe(pipe_class_default);
15334 %}
15335 
15336 instruct reduce_add4I(iRegINoSp dst, iRegIorL2I src1, vecX src2, vecX tmp, iRegINoSp tmp2)
15337 %{
15338   match(Set dst (AddReductionVI src1 src2));
15339   ins_cost(INSN_COST);
15340   effect(TEMP tmp, TEMP tmp2);
15341   format %{ "addv  $tmp, T4S, $src2\n\t"
15342             "umov  $tmp2, $tmp, S, 0\n\t"
15343             "addw  $dst, $tmp2, $src1\t add reduction4i"
15344   %}
15345   ins_encode %{
15346     __ addv(as_FloatRegister($tmp$$reg), __ T4S,
15347             as_FloatRegister($src2$$reg));
15348     __ umov($tmp2$$Register, as_FloatRegister($tmp$$reg), __ S, 0);
15349     __ addw($dst$$Register, $tmp2$$Register, $src1$$Register);
15350   %}
15351   ins_pipe(pipe_class_default);
15352 %}
15353 
15354 instruct reduce_mul2I(iRegINoSp dst, iRegIorL2I src1, vecD src2, iRegINoSp tmp)
15355 %{
15356   match(Set dst (MulReductionVI src1 src2));
15357   ins_cost(INSN_COST);
15358   effect(TEMP tmp, TEMP dst);
15359   format %{ "umov  $tmp, $src2, S, 0\n\t"
15360             "mul   $dst, $tmp, $src1\n\t"
15361             "umov  $tmp, $src2, S, 1\n\t"
15362             "mul   $dst, $tmp, $dst\t mul reduction2i\n\t"
15363   %}
15364   ins_encode %{
15365     __ umov($tmp$$Register, as_FloatRegister($src2$$reg), __ S, 0);
15366     __ mul($dst$$Register, $tmp$$Register, $src1$$Register);
15367     __ umov($tmp$$Register, as_FloatRegister($src2$$reg), __ S, 1);
15368     __ mul($dst$$Register, $tmp$$Register, $dst$$Register);
15369   %}
15370   ins_pipe(pipe_class_default);
15371 %}
15372 
15373 instruct reduce_mul4I(iRegINoSp dst, iRegIorL2I src1, vecX src2, vecX tmp, iRegINoSp tmp2)
15374 %{
15375   match(Set dst (MulReductionVI src1 src2));
15376   ins_cost(INSN_COST);
15377   effect(TEMP tmp, TEMP tmp2, TEMP dst);
15378   format %{ "ins   $tmp, $src2, 0, 1\n\t"
15379             "mul   $tmp, $tmp, $src2\n\t"
15380             "umov  $tmp2, $tmp, S, 0\n\t"
15381             "mul   $dst, $tmp2, $src1\n\t"
15382             "umov  $tmp2, $tmp, S, 1\n\t"
15383             "mul   $dst, $tmp2, $dst\t mul reduction4i\n\t"
15384   %}
15385   ins_encode %{
15386     __ ins(as_FloatRegister($tmp$$reg), __ D,
15387            as_FloatRegister($src2$$reg), 0, 1);
15388     __ mulv(as_FloatRegister($tmp$$reg), __ T2S,
15389            as_FloatRegister($tmp$$reg), as_FloatRegister($src2$$reg));
15390     __ umov($tmp2$$Register, as_FloatRegister($tmp$$reg), __ S, 0);
15391     __ mul($dst$$Register, $tmp2$$Register, $src1$$Register);
15392     __ umov($tmp2$$Register, as_FloatRegister($tmp$$reg), __ S, 1);
15393     __ mul($dst$$Register, $tmp2$$Register, $dst$$Register);
15394   %}
15395   ins_pipe(pipe_class_default);
15396 %}
15397 
15398 instruct reduce_add2F(vRegF dst, vRegF src1, vecD src2, vecD tmp)
15399 %{
15400   match(Set dst (AddReductionVF src1 src2));
15401   ins_cost(INSN_COST);
15402   effect(TEMP tmp, TEMP dst);
15403   format %{ "fadds $dst, $src1, $src2\n\t"
15404             "ins   $tmp, S, $src2, 0, 1\n\t"
15405             "fadds $dst, $dst, $tmp\t add reduction2f"
15406   %}
15407   ins_encode %{
15408     __ fadds(as_FloatRegister($dst$$reg),
15409              as_FloatRegister($src1$$reg), as_FloatRegister($src2$$reg));
15410     __ ins(as_FloatRegister($tmp$$reg), __ S,
15411            as_FloatRegister($src2$$reg), 0, 1);
15412     __ fadds(as_FloatRegister($dst$$reg),
15413              as_FloatRegister($dst$$reg), as_FloatRegister($tmp$$reg));
15414   %}
15415   ins_pipe(pipe_class_default);
15416 %}
15417 
15418 instruct reduce_add4F(vRegF dst, vRegF src1, vecX src2, vecX tmp)
15419 %{
15420   match(Set dst (AddReductionVF src1 src2));
15421   ins_cost(INSN_COST);
15422   effect(TEMP tmp, TEMP dst);
15423   format %{ "fadds $dst, $src1, $src2\n\t"
15424             "ins   $tmp, S, $src2, 0, 1\n\t"
15425             "fadds $dst, $dst, $tmp\n\t"
15426             "ins   $tmp, S, $src2, 0, 2\n\t"
15427             "fadds $dst, $dst, $tmp\n\t"
15428             "ins   $tmp, S, $src2, 0, 3\n\t"
15429             "fadds $dst, $dst, $tmp\t add reduction4f"
15430   %}
15431   ins_encode %{
15432     __ fadds(as_FloatRegister($dst$$reg),
15433              as_FloatRegister($src1$$reg), as_FloatRegister($src2$$reg));
15434     __ ins(as_FloatRegister($tmp$$reg), __ S,
15435            as_FloatRegister($src2$$reg), 0, 1);
15436     __ fadds(as_FloatRegister($dst$$reg),
15437              as_FloatRegister($dst$$reg), as_FloatRegister($tmp$$reg));
15438     __ ins(as_FloatRegister($tmp$$reg), __ S,
15439            as_FloatRegister($src2$$reg), 0, 2);
15440     __ fadds(as_FloatRegister($dst$$reg),
15441              as_FloatRegister($dst$$reg), as_FloatRegister($tmp$$reg));
15442     __ ins(as_FloatRegister($tmp$$reg), __ S,
15443            as_FloatRegister($src2$$reg), 0, 3);
15444     __ fadds(as_FloatRegister($dst$$reg),
15445              as_FloatRegister($dst$$reg), as_FloatRegister($tmp$$reg));
15446   %}
15447   ins_pipe(pipe_class_default);
15448 %}
15449 
15450 instruct reduce_mul2F(vRegF dst, vRegF src1, vecD src2, vecD tmp)
15451 %{
15452   match(Set dst (MulReductionVF src1 src2));
15453   ins_cost(INSN_COST);
15454   effect(TEMP tmp, TEMP dst);
15455   format %{ "fmuls $dst, $src1, $src2\n\t"
15456             "ins   $tmp, S, $src2, 0, 1\n\t"
15457             "fmuls $dst, $dst, $tmp\t add reduction4f"
15458   %}
15459   ins_encode %{
15460     __ fmuls(as_FloatRegister($dst$$reg),
15461              as_FloatRegister($src1$$reg), as_FloatRegister($src2$$reg));
15462     __ ins(as_FloatRegister($tmp$$reg), __ S,
15463            as_FloatRegister($src2$$reg), 0, 1);
15464     __ fmuls(as_FloatRegister($dst$$reg),
15465              as_FloatRegister($dst$$reg), as_FloatRegister($tmp$$reg));
15466   %}
15467   ins_pipe(pipe_class_default);
15468 %}
15469 
15470 instruct reduce_mul4F(vRegF dst, vRegF src1, vecX src2, vecX tmp)
15471 %{
15472   match(Set dst (MulReductionVF src1 src2));
15473   ins_cost(INSN_COST);
15474   effect(TEMP tmp, TEMP dst);
15475   format %{ "fmuls $dst, $src1, $src2\n\t"
15476             "ins   $tmp, S, $src2, 0, 1\n\t"
15477             "fmuls $dst, $dst, $tmp\n\t"
15478             "ins   $tmp, S, $src2, 0, 2\n\t"
15479             "fmuls $dst, $dst, $tmp\n\t"
15480             "ins   $tmp, S, $src2, 0, 3\n\t"
15481             "fmuls $dst, $dst, $tmp\t add reduction4f"
15482   %}
15483   ins_encode %{
15484     __ fmuls(as_FloatRegister($dst$$reg),
15485              as_FloatRegister($src1$$reg), as_FloatRegister($src2$$reg));
15486     __ ins(as_FloatRegister($tmp$$reg), __ S,
15487            as_FloatRegister($src2$$reg), 0, 1);
15488     __ fmuls(as_FloatRegister($dst$$reg),
15489              as_FloatRegister($dst$$reg), as_FloatRegister($tmp$$reg));
15490     __ ins(as_FloatRegister($tmp$$reg), __ S,
15491            as_FloatRegister($src2$$reg), 0, 2);
15492     __ fmuls(as_FloatRegister($dst$$reg),
15493              as_FloatRegister($dst$$reg), as_FloatRegister($tmp$$reg));
15494     __ ins(as_FloatRegister($tmp$$reg), __ S,
15495            as_FloatRegister($src2$$reg), 0, 3);
15496     __ fmuls(as_FloatRegister($dst$$reg),
15497              as_FloatRegister($dst$$reg), as_FloatRegister($tmp$$reg));
15498   %}
15499   ins_pipe(pipe_class_default);
15500 %}
15501 
15502 instruct reduce_add2D(vRegD dst, vRegD src1, vecX src2, vecX tmp)
15503 %{
15504   match(Set dst (AddReductionVD src1 src2));
15505   ins_cost(INSN_COST);
15506   effect(TEMP tmp, TEMP dst);
15507   format %{ "faddd $dst, $src1, $src2\n\t"
15508             "ins   $tmp, D, $src2, 0, 1\n\t"
15509             "faddd $dst, $dst, $tmp\t add reduction2d"
15510   %}
15511   ins_encode %{
15512     __ faddd(as_FloatRegister($dst$$reg),
15513              as_FloatRegister($src1$$reg), as_FloatRegister($src2$$reg));
15514     __ ins(as_FloatRegister($tmp$$reg), __ D,
15515            as_FloatRegister($src2$$reg), 0, 1);
15516     __ faddd(as_FloatRegister($dst$$reg),
15517              as_FloatRegister($dst$$reg), as_FloatRegister($tmp$$reg));
15518   %}
15519   ins_pipe(pipe_class_default);
15520 %}
15521 
15522 instruct reduce_mul2D(vRegD dst, vRegD src1, vecX src2, vecX tmp)
15523 %{
15524   match(Set dst (MulReductionVD src1 src2));
15525   ins_cost(INSN_COST);
15526   effect(TEMP tmp, TEMP dst);
15527   format %{ "fmuld $dst, $src1, $src2\n\t"
15528             "ins   $tmp, D, $src2, 0, 1\n\t"
15529             "fmuld $dst, $dst, $tmp\t add reduction2d"
15530   %}
15531   ins_encode %{
15532     __ fmuld(as_FloatRegister($dst$$reg),
15533              as_FloatRegister($src1$$reg), as_FloatRegister($src2$$reg));
15534     __ ins(as_FloatRegister($tmp$$reg), __ D,
15535            as_FloatRegister($src2$$reg), 0, 1);
15536     __ fmuld(as_FloatRegister($dst$$reg),
15537              as_FloatRegister($dst$$reg), as_FloatRegister($tmp$$reg));
15538   %}
15539   ins_pipe(pipe_class_default);
15540 %}
15541 
15542 // ====================VECTOR ARITHMETIC=======================================
15543 
15544 // --------------------------------- ADD --------------------------------------
15545 
15546 instruct vadd8B(vecD dst, vecD src1, vecD src2)
15547 %{
15548   predicate(n->as_Vector()->length() == 4 ||
15549             n->as_Vector()->length() == 8);
15550   match(Set dst (AddVB src1 src2));
15551   ins_cost(INSN_COST);
15552   format %{ "addv  $dst,$src1,$src2\t# vector (8B)" %}
15553   ins_encode %{
15554     __ addv(as_FloatRegister($dst$$reg), __ T8B,
15555             as_FloatRegister($src1$$reg),
15556             as_FloatRegister($src2$$reg));
15557   %}
15558   ins_pipe(vdop64);
15559 %}
15560 
15561 instruct vadd16B(vecX dst, vecX src1, vecX src2)
15562 %{
15563   predicate(n->as_Vector()->length() == 16);
15564   match(Set dst (AddVB src1 src2));
15565   ins_cost(INSN_COST);
15566   format %{ "addv  $dst,$src1,$src2\t# vector (16B)" %}
15567   ins_encode %{
15568     __ addv(as_FloatRegister($dst$$reg), __ T16B,
15569             as_FloatRegister($src1$$reg),
15570             as_FloatRegister($src2$$reg));
15571   %}
15572   ins_pipe(vdop128);
15573 %}
15574 
15575 instruct vadd4S(vecD dst, vecD src1, vecD src2)
15576 %{
15577   predicate(n->as_Vector()->length() == 2 ||
15578             n->as_Vector()->length() == 4);
15579   match(Set dst (AddVS src1 src2));
15580   ins_cost(INSN_COST);
15581   format %{ "addv  $dst,$src1,$src2\t# vector (4H)" %}
15582   ins_encode %{
15583     __ addv(as_FloatRegister($dst$$reg), __ T4H,
15584             as_FloatRegister($src1$$reg),
15585             as_FloatRegister($src2$$reg));
15586   %}
15587   ins_pipe(vdop64);
15588 %}
15589 
15590 instruct vadd8S(vecX dst, vecX src1, vecX src2)
15591 %{
15592   predicate(n->as_Vector()->length() == 8);
15593   match(Set dst (AddVS src1 src2));
15594   ins_cost(INSN_COST);
15595   format %{ "addv  $dst,$src1,$src2\t# vector (8H)" %}
15596   ins_encode %{
15597     __ addv(as_FloatRegister($dst$$reg), __ T8H,
15598             as_FloatRegister($src1$$reg),
15599             as_FloatRegister($src2$$reg));
15600   %}
15601   ins_pipe(vdop128);
15602 %}
15603 
15604 instruct vadd2I(vecD dst, vecD src1, vecD src2)
15605 %{
15606   predicate(n->as_Vector()->length() == 2);
15607   match(Set dst (AddVI src1 src2));
15608   ins_cost(INSN_COST);
15609   format %{ "addv  $dst,$src1,$src2\t# vector (2S)" %}
15610   ins_encode %{
15611     __ addv(as_FloatRegister($dst$$reg), __ T2S,
15612             as_FloatRegister($src1$$reg),
15613             as_FloatRegister($src2$$reg));
15614   %}
15615   ins_pipe(vdop64);
15616 %}
15617 
15618 instruct vadd4I(vecX dst, vecX src1, vecX src2)
15619 %{
15620   predicate(n->as_Vector()->length() == 4);
15621   match(Set dst (AddVI src1 src2));
15622   ins_cost(INSN_COST);
15623   format %{ "addv  $dst,$src1,$src2\t# vector (4S)" %}
15624   ins_encode %{
15625     __ addv(as_FloatRegister($dst$$reg), __ T4S,
15626             as_FloatRegister($src1$$reg),
15627             as_FloatRegister($src2$$reg));
15628   %}
15629   ins_pipe(vdop128);
15630 %}
15631 
15632 instruct vadd2L(vecX dst, vecX src1, vecX src2)
15633 %{
15634   predicate(n->as_Vector()->length() == 2);
15635   match(Set dst (AddVL src1 src2));
15636   ins_cost(INSN_COST);
15637   format %{ "addv  $dst,$src1,$src2\t# vector (2L)" %}
15638   ins_encode %{
15639     __ addv(as_FloatRegister($dst$$reg), __ T2D,
15640             as_FloatRegister($src1$$reg),
15641             as_FloatRegister($src2$$reg));
15642   %}
15643   ins_pipe(vdop128);
15644 %}
15645 
15646 instruct vadd2F(vecD dst, vecD src1, vecD src2)
15647 %{
15648   predicate(n->as_Vector()->length() == 2);
15649   match(Set dst (AddVF src1 src2));
15650   ins_cost(INSN_COST);
15651   format %{ "fadd  $dst,$src1,$src2\t# vector (2S)" %}
15652   ins_encode %{
15653     __ fadd(as_FloatRegister($dst$$reg), __ T2S,
15654             as_FloatRegister($src1$$reg),
15655             as_FloatRegister($src2$$reg));
15656   %}
15657   ins_pipe(vdop_fp64);
15658 %}
15659 
15660 instruct vadd4F(vecX dst, vecX src1, vecX src2)
15661 %{
15662   predicate(n->as_Vector()->length() == 4);
15663   match(Set dst (AddVF src1 src2));
15664   ins_cost(INSN_COST);
15665   format %{ "fadd  $dst,$src1,$src2\t# vector (4S)" %}
15666   ins_encode %{
15667     __ fadd(as_FloatRegister($dst$$reg), __ T4S,
15668             as_FloatRegister($src1$$reg),
15669             as_FloatRegister($src2$$reg));
15670   %}
15671   ins_pipe(vdop_fp128);
15672 %}
15673 
15674 instruct vadd2D(vecX dst, vecX src1, vecX src2)
15675 %{
15676   match(Set dst (AddVD src1 src2));
15677   ins_cost(INSN_COST);
15678   format %{ "fadd  $dst,$src1,$src2\t# vector (2D)" %}
15679   ins_encode %{
15680     __ fadd(as_FloatRegister($dst$$reg), __ T2D,
15681             as_FloatRegister($src1$$reg),
15682             as_FloatRegister($src2$$reg));
15683   %}
15684   ins_pipe(vdop_fp128);
15685 %}
15686 
15687 // --------------------------------- SUB --------------------------------------
15688 
15689 instruct vsub8B(vecD dst, vecD src1, vecD src2)
15690 %{
15691   predicate(n->as_Vector()->length() == 4 ||
15692             n->as_Vector()->length() == 8);
15693   match(Set dst (SubVB src1 src2));
15694   ins_cost(INSN_COST);
15695   format %{ "subv  $dst,$src1,$src2\t# vector (8B)" %}
15696   ins_encode %{
15697     __ subv(as_FloatRegister($dst$$reg), __ T8B,
15698             as_FloatRegister($src1$$reg),
15699             as_FloatRegister($src2$$reg));
15700   %}
15701   ins_pipe(vdop64);
15702 %}
15703 
15704 instruct vsub16B(vecX dst, vecX src1, vecX src2)
15705 %{
15706   predicate(n->as_Vector()->length() == 16);
15707   match(Set dst (SubVB src1 src2));
15708   ins_cost(INSN_COST);
15709   format %{ "subv  $dst,$src1,$src2\t# vector (16B)" %}
15710   ins_encode %{
15711     __ subv(as_FloatRegister($dst$$reg), __ T16B,
15712             as_FloatRegister($src1$$reg),
15713             as_FloatRegister($src2$$reg));
15714   %}
15715   ins_pipe(vdop128);
15716 %}
15717 
15718 instruct vsub4S(vecD dst, vecD src1, vecD src2)
15719 %{
15720   predicate(n->as_Vector()->length() == 2 ||
15721             n->as_Vector()->length() == 4);
15722   match(Set dst (SubVS src1 src2));
15723   ins_cost(INSN_COST);
15724   format %{ "subv  $dst,$src1,$src2\t# vector (4H)" %}
15725   ins_encode %{
15726     __ subv(as_FloatRegister($dst$$reg), __ T4H,
15727             as_FloatRegister($src1$$reg),
15728             as_FloatRegister($src2$$reg));
15729   %}
15730   ins_pipe(vdop64);
15731 %}
15732 
15733 instruct vsub8S(vecX dst, vecX src1, vecX src2)
15734 %{
15735   predicate(n->as_Vector()->length() == 8);
15736   match(Set dst (SubVS src1 src2));
15737   ins_cost(INSN_COST);
15738   format %{ "subv  $dst,$src1,$src2\t# vector (8H)" %}
15739   ins_encode %{
15740     __ subv(as_FloatRegister($dst$$reg), __ T8H,
15741             as_FloatRegister($src1$$reg),
15742             as_FloatRegister($src2$$reg));
15743   %}
15744   ins_pipe(vdop128);
15745 %}
15746 
15747 instruct vsub2I(vecD dst, vecD src1, vecD src2)
15748 %{
15749   predicate(n->as_Vector()->length() == 2);
15750   match(Set dst (SubVI src1 src2));
15751   ins_cost(INSN_COST);
15752   format %{ "subv  $dst,$src1,$src2\t# vector (2S)" %}
15753   ins_encode %{
15754     __ subv(as_FloatRegister($dst$$reg), __ T2S,
15755             as_FloatRegister($src1$$reg),
15756             as_FloatRegister($src2$$reg));
15757   %}
15758   ins_pipe(vdop64);
15759 %}
15760 
15761 instruct vsub4I(vecX dst, vecX src1, vecX src2)
15762 %{
15763   predicate(n->as_Vector()->length() == 4);
15764   match(Set dst (SubVI src1 src2));
15765   ins_cost(INSN_COST);
15766   format %{ "subv  $dst,$src1,$src2\t# vector (4S)" %}
15767   ins_encode %{
15768     __ subv(as_FloatRegister($dst$$reg), __ T4S,
15769             as_FloatRegister($src1$$reg),
15770             as_FloatRegister($src2$$reg));
15771   %}
15772   ins_pipe(vdop128);
15773 %}
15774 
15775 instruct vsub2L(vecX dst, vecX src1, vecX src2)
15776 %{
15777   predicate(n->as_Vector()->length() == 2);
15778   match(Set dst (SubVL src1 src2));
15779   ins_cost(INSN_COST);
15780   format %{ "subv  $dst,$src1,$src2\t# vector (2L)" %}
15781   ins_encode %{
15782     __ subv(as_FloatRegister($dst$$reg), __ T2D,
15783             as_FloatRegister($src1$$reg),
15784             as_FloatRegister($src2$$reg));
15785   %}
15786   ins_pipe(vdop128);
15787 %}
15788 
15789 instruct vsub2F(vecD dst, vecD src1, vecD src2)
15790 %{
15791   predicate(n->as_Vector()->length() == 2);
15792   match(Set dst (SubVF src1 src2));
15793   ins_cost(INSN_COST);
15794   format %{ "fsub  $dst,$src1,$src2\t# vector (2S)" %}
15795   ins_encode %{
15796     __ fsub(as_FloatRegister($dst$$reg), __ T2S,
15797             as_FloatRegister($src1$$reg),
15798             as_FloatRegister($src2$$reg));
15799   %}
15800   ins_pipe(vdop_fp64);
15801 %}
15802 
15803 instruct vsub4F(vecX dst, vecX src1, vecX src2)
15804 %{
15805   predicate(n->as_Vector()->length() == 4);
15806   match(Set dst (SubVF src1 src2));
15807   ins_cost(INSN_COST);
15808   format %{ "fsub  $dst,$src1,$src2\t# vector (4S)" %}
15809   ins_encode %{
15810     __ fsub(as_FloatRegister($dst$$reg), __ T4S,
15811             as_FloatRegister($src1$$reg),
15812             as_FloatRegister($src2$$reg));
15813   %}
15814   ins_pipe(vdop_fp128);
15815 %}
15816 
15817 instruct vsub2D(vecX dst, vecX src1, vecX src2)
15818 %{
15819   predicate(n->as_Vector()->length() == 2);
15820   match(Set dst (SubVD src1 src2));
15821   ins_cost(INSN_COST);
15822   format %{ "fsub  $dst,$src1,$src2\t# vector (2D)" %}
15823   ins_encode %{
15824     __ fsub(as_FloatRegister($dst$$reg), __ T2D,
15825             as_FloatRegister($src1$$reg),
15826             as_FloatRegister($src2$$reg));
15827   %}
15828   ins_pipe(vdop_fp128);
15829 %}
15830 
15831 // --------------------------------- MUL --------------------------------------
15832 
15833 instruct vmul4S(vecD dst, vecD src1, vecD src2)
15834 %{
15835   predicate(n->as_Vector()->length() == 2 ||
15836             n->as_Vector()->length() == 4);
15837   match(Set dst (MulVS src1 src2));
15838   ins_cost(INSN_COST);
15839   format %{ "mulv  $dst,$src1,$src2\t# vector (4H)" %}
15840   ins_encode %{
15841     __ mulv(as_FloatRegister($dst$$reg), __ T4H,
15842             as_FloatRegister($src1$$reg),
15843             as_FloatRegister($src2$$reg));
15844   %}
15845   ins_pipe(vmul64);
15846 %}
15847 
15848 instruct vmul8S(vecX dst, vecX src1, vecX src2)
15849 %{
15850   predicate(n->as_Vector()->length() == 8);
15851   match(Set dst (MulVS src1 src2));
15852   ins_cost(INSN_COST);
15853   format %{ "mulv  $dst,$src1,$src2\t# vector (8H)" %}
15854   ins_encode %{
15855     __ mulv(as_FloatRegister($dst$$reg), __ T8H,
15856             as_FloatRegister($src1$$reg),
15857             as_FloatRegister($src2$$reg));
15858   %}
15859   ins_pipe(vmul128);
15860 %}
15861 
15862 instruct vmul2I(vecD dst, vecD src1, vecD src2)
15863 %{
15864   predicate(n->as_Vector()->length() == 2);
15865   match(Set dst (MulVI src1 src2));
15866   ins_cost(INSN_COST);
15867   format %{ "mulv  $dst,$src1,$src2\t# vector (2S)" %}
15868   ins_encode %{
15869     __ mulv(as_FloatRegister($dst$$reg), __ T2S,
15870             as_FloatRegister($src1$$reg),
15871             as_FloatRegister($src2$$reg));
15872   %}
15873   ins_pipe(vmul64);
15874 %}
15875 
15876 instruct vmul4I(vecX dst, vecX src1, vecX src2)
15877 %{
15878   predicate(n->as_Vector()->length() == 4);
15879   match(Set dst (MulVI src1 src2));
15880   ins_cost(INSN_COST);
15881   format %{ "mulv  $dst,$src1,$src2\t# vector (4S)" %}
15882   ins_encode %{
15883     __ mulv(as_FloatRegister($dst$$reg), __ T4S,
15884             as_FloatRegister($src1$$reg),
15885             as_FloatRegister($src2$$reg));
15886   %}
15887   ins_pipe(vmul128);
15888 %}
15889 
15890 instruct vmul2F(vecD dst, vecD src1, vecD src2)
15891 %{
15892   predicate(n->as_Vector()->length() == 2);
15893   match(Set dst (MulVF src1 src2));
15894   ins_cost(INSN_COST);
15895   format %{ "fmul  $dst,$src1,$src2\t# vector (2S)" %}
15896   ins_encode %{
15897     __ fmul(as_FloatRegister($dst$$reg), __ T2S,
15898             as_FloatRegister($src1$$reg),
15899             as_FloatRegister($src2$$reg));
15900   %}
15901   ins_pipe(vmuldiv_fp64);
15902 %}
15903 
15904 instruct vmul4F(vecX dst, vecX src1, vecX src2)
15905 %{
15906   predicate(n->as_Vector()->length() == 4);
15907   match(Set dst (MulVF src1 src2));
15908   ins_cost(INSN_COST);
15909   format %{ "fmul  $dst,$src1,$src2\t# vector (4S)" %}
15910   ins_encode %{
15911     __ fmul(as_FloatRegister($dst$$reg), __ T4S,
15912             as_FloatRegister($src1$$reg),
15913             as_FloatRegister($src2$$reg));
15914   %}
15915   ins_pipe(vmuldiv_fp128);
15916 %}
15917 
15918 instruct vmul2D(vecX dst, vecX src1, vecX src2)
15919 %{
15920   predicate(n->as_Vector()->length() == 2);
15921   match(Set dst (MulVD src1 src2));
15922   ins_cost(INSN_COST);
15923   format %{ "fmul  $dst,$src1,$src2\t# vector (2D)" %}
15924   ins_encode %{
15925     __ fmul(as_FloatRegister($dst$$reg), __ T2D,
15926             as_FloatRegister($src1$$reg),
15927             as_FloatRegister($src2$$reg));
15928   %}
15929   ins_pipe(vmuldiv_fp128);
15930 %}
15931 
15932 // --------------------------------- MLA --------------------------------------
15933 
15934 instruct vmla4S(vecD dst, vecD src1, vecD src2)
15935 %{
15936   predicate(n->as_Vector()->length() == 2 ||
15937             n->as_Vector()->length() == 4);
15938   match(Set dst (AddVS dst (MulVS src1 src2)));
15939   ins_cost(INSN_COST);
15940   format %{ "mlav  $dst,$src1,$src2\t# vector (4H)" %}
15941   ins_encode %{
15942     __ mlav(as_FloatRegister($dst$$reg), __ T4H,
15943             as_FloatRegister($src1$$reg),
15944             as_FloatRegister($src2$$reg));
15945   %}
15946   ins_pipe(vmla64);
15947 %}
15948 
15949 instruct vmla8S(vecX dst, vecX src1, vecX src2)
15950 %{
15951   predicate(n->as_Vector()->length() == 8);
15952   match(Set dst (AddVS dst (MulVS src1 src2)));
15953   ins_cost(INSN_COST);
15954   format %{ "mlav  $dst,$src1,$src2\t# vector (8H)" %}
15955   ins_encode %{
15956     __ mlav(as_FloatRegister($dst$$reg), __ T8H,
15957             as_FloatRegister($src1$$reg),
15958             as_FloatRegister($src2$$reg));
15959   %}
15960   ins_pipe(vmla128);
15961 %}
15962 
15963 instruct vmla2I(vecD dst, vecD src1, vecD src2)
15964 %{
15965   predicate(n->as_Vector()->length() == 2);
15966   match(Set dst (AddVI dst (MulVI src1 src2)));
15967   ins_cost(INSN_COST);
15968   format %{ "mlav  $dst,$src1,$src2\t# vector (2S)" %}
15969   ins_encode %{
15970     __ mlav(as_FloatRegister($dst$$reg), __ T2S,
15971             as_FloatRegister($src1$$reg),
15972             as_FloatRegister($src2$$reg));
15973   %}
15974   ins_pipe(vmla64);
15975 %}
15976 
15977 instruct vmla4I(vecX dst, vecX src1, vecX src2)
15978 %{
15979   predicate(n->as_Vector()->length() == 4);
15980   match(Set dst (AddVI dst (MulVI src1 src2)));
15981   ins_cost(INSN_COST);
15982   format %{ "mlav  $dst,$src1,$src2\t# vector (4S)" %}
15983   ins_encode %{
15984     __ mlav(as_FloatRegister($dst$$reg), __ T4S,
15985             as_FloatRegister($src1$$reg),
15986             as_FloatRegister($src2$$reg));
15987   %}
15988   ins_pipe(vmla128);
15989 %}
15990 
15991 // dst + src1 * src2
15992 instruct vmla2F(vecD dst, vecD src1, vecD src2) %{
15993   predicate(UseFMA && n->as_Vector()->length() == 2);
15994   match(Set dst (FmaVF  dst (Binary src1 src2)));
15995   format %{ "fmla  $dst,$src1,$src2\t# vector (2S)" %}
15996   ins_cost(INSN_COST);
15997   ins_encode %{
15998     __ fmla(as_FloatRegister($dst$$reg), __ T2S,
15999             as_FloatRegister($src1$$reg),
16000             as_FloatRegister($src2$$reg));
16001   %}
16002   ins_pipe(vmuldiv_fp64);
16003 %}
16004 
16005 // dst + src1 * src2
16006 instruct vmla4F(vecX dst, vecX src1, vecX src2) %{
16007   predicate(UseFMA && n->as_Vector()->length() == 4);
16008   match(Set dst (FmaVF  dst (Binary src1 src2)));
16009   format %{ "fmla  $dst,$src1,$src2\t# vector (4S)" %}
16010   ins_cost(INSN_COST);
16011   ins_encode %{
16012     __ fmla(as_FloatRegister($dst$$reg), __ T4S,
16013             as_FloatRegister($src1$$reg),
16014             as_FloatRegister($src2$$reg));
16015   %}
16016   ins_pipe(vmuldiv_fp128);
16017 %}
16018 
16019 // dst + src1 * src2
16020 instruct vmla2D(vecX dst, vecX src1, vecX src2) %{
16021   predicate(UseFMA && n->as_Vector()->length() == 2);
16022   match(Set dst (FmaVD  dst (Binary src1 src2)));
16023   format %{ "fmla  $dst,$src1,$src2\t# vector (2D)" %}
16024   ins_cost(INSN_COST);
16025   ins_encode %{
16026     __ fmla(as_FloatRegister($dst$$reg), __ T2D,
16027             as_FloatRegister($src1$$reg),
16028             as_FloatRegister($src2$$reg));
16029   %}
16030   ins_pipe(vmuldiv_fp128);
16031 %}
16032 
16033 // --------------------------------- MLS --------------------------------------
16034 
16035 instruct vmls4S(vecD dst, vecD src1, vecD src2)
16036 %{
16037   predicate(n->as_Vector()->length() == 2 ||
16038             n->as_Vector()->length() == 4);
16039   match(Set dst (SubVS dst (MulVS src1 src2)));
16040   ins_cost(INSN_COST);
16041   format %{ "mlsv  $dst,$src1,$src2\t# vector (4H)" %}
16042   ins_encode %{
16043     __ mlsv(as_FloatRegister($dst$$reg), __ T4H,
16044             as_FloatRegister($src1$$reg),
16045             as_FloatRegister($src2$$reg));
16046   %}
16047   ins_pipe(vmla64);
16048 %}
16049 
16050 instruct vmls8S(vecX dst, vecX src1, vecX src2)
16051 %{
16052   predicate(n->as_Vector()->length() == 8);
16053   match(Set dst (SubVS dst (MulVS src1 src2)));
16054   ins_cost(INSN_COST);
16055   format %{ "mlsv  $dst,$src1,$src2\t# vector (8H)" %}
16056   ins_encode %{
16057     __ mlsv(as_FloatRegister($dst$$reg), __ T8H,
16058             as_FloatRegister($src1$$reg),
16059             as_FloatRegister($src2$$reg));
16060   %}
16061   ins_pipe(vmla128);
16062 %}
16063 
16064 instruct vmls2I(vecD dst, vecD src1, vecD src2)
16065 %{
16066   predicate(n->as_Vector()->length() == 2);
16067   match(Set dst (SubVI dst (MulVI src1 src2)));
16068   ins_cost(INSN_COST);
16069   format %{ "mlsv  $dst,$src1,$src2\t# vector (2S)" %}
16070   ins_encode %{
16071     __ mlsv(as_FloatRegister($dst$$reg), __ T2S,
16072             as_FloatRegister($src1$$reg),
16073             as_FloatRegister($src2$$reg));
16074   %}
16075   ins_pipe(vmla64);
16076 %}
16077 
16078 instruct vmls4I(vecX dst, vecX src1, vecX src2)
16079 %{
16080   predicate(n->as_Vector()->length() == 4);
16081   match(Set dst (SubVI dst (MulVI src1 src2)));
16082   ins_cost(INSN_COST);
16083   format %{ "mlsv  $dst,$src1,$src2\t# vector (4S)" %}
16084   ins_encode %{
16085     __ mlsv(as_FloatRegister($dst$$reg), __ T4S,
16086             as_FloatRegister($src1$$reg),
16087             as_FloatRegister($src2$$reg));
16088   %}
16089   ins_pipe(vmla128);
16090 %}
16091 
16092 // dst - src1 * src2
16093 instruct vmls2F(vecD dst, vecD src1, vecD src2) %{
16094   predicate(UseFMA && n->as_Vector()->length() == 2);
16095   match(Set dst (FmaVF  dst (Binary (NegVF src1) src2)));
16096   match(Set dst (FmaVF  dst (Binary src1 (NegVF src2))));
16097   format %{ "fmls  $dst,$src1,$src2\t# vector (2S)" %}
16098   ins_cost(INSN_COST);
16099   ins_encode %{
16100     __ fmls(as_FloatRegister($dst$$reg), __ T2S,
16101             as_FloatRegister($src1$$reg),
16102             as_FloatRegister($src2$$reg));
16103   %}
16104   ins_pipe(vmuldiv_fp64);
16105 %}
16106 
16107 // dst - src1 * src2
16108 instruct vmls4F(vecX dst, vecX src1, vecX src2) %{
16109   predicate(UseFMA && n->as_Vector()->length() == 4);
16110   match(Set dst (FmaVF  dst (Binary (NegVF src1) src2)));
16111   match(Set dst (FmaVF  dst (Binary src1 (NegVF src2))));
16112   format %{ "fmls  $dst,$src1,$src2\t# vector (4S)" %}
16113   ins_cost(INSN_COST);
16114   ins_encode %{
16115     __ fmls(as_FloatRegister($dst$$reg), __ T4S,
16116             as_FloatRegister($src1$$reg),
16117             as_FloatRegister($src2$$reg));
16118   %}
16119   ins_pipe(vmuldiv_fp128);
16120 %}
16121 
16122 // dst - src1 * src2
16123 instruct vmls2D(vecX dst, vecX src1, vecX src2) %{
16124   predicate(UseFMA && n->as_Vector()->length() == 2);
16125   match(Set dst (FmaVD  dst (Binary (NegVD src1) src2)));
16126   match(Set dst (FmaVD  dst (Binary src1 (NegVD src2))));
16127   format %{ "fmls  $dst,$src1,$src2\t# vector (2D)" %}
16128   ins_cost(INSN_COST);
16129   ins_encode %{
16130     __ fmls(as_FloatRegister($dst$$reg), __ T2D,
16131             as_FloatRegister($src1$$reg),
16132             as_FloatRegister($src2$$reg));
16133   %}
16134   ins_pipe(vmuldiv_fp128);
16135 %}
16136 
16137 // --------------------------------- DIV --------------------------------------
16138 
16139 instruct vdiv2F(vecD dst, vecD src1, vecD src2)
16140 %{
16141   predicate(n->as_Vector()->length() == 2);
16142   match(Set dst (DivVF src1 src2));
16143   ins_cost(INSN_COST);
16144   format %{ "fdiv  $dst,$src1,$src2\t# vector (2S)" %}
16145   ins_encode %{
16146     __ fdiv(as_FloatRegister($dst$$reg), __ T2S,
16147             as_FloatRegister($src1$$reg),
16148             as_FloatRegister($src2$$reg));
16149   %}
16150   ins_pipe(vmuldiv_fp64);
16151 %}
16152 
16153 instruct vdiv4F(vecX dst, vecX src1, vecX src2)
16154 %{
16155   predicate(n->as_Vector()->length() == 4);
16156   match(Set dst (DivVF src1 src2));
16157   ins_cost(INSN_COST);
16158   format %{ "fdiv  $dst,$src1,$src2\t# vector (4S)" %}
16159   ins_encode %{
16160     __ fdiv(as_FloatRegister($dst$$reg), __ T4S,
16161             as_FloatRegister($src1$$reg),
16162             as_FloatRegister($src2$$reg));
16163   %}
16164   ins_pipe(vmuldiv_fp128);
16165 %}
16166 
16167 instruct vdiv2D(vecX dst, vecX src1, vecX src2)
16168 %{
16169   predicate(n->as_Vector()->length() == 2);
16170   match(Set dst (DivVD src1 src2));
16171   ins_cost(INSN_COST);
16172   format %{ "fdiv  $dst,$src1,$src2\t# vector (2D)" %}
16173   ins_encode %{
16174     __ fdiv(as_FloatRegister($dst$$reg), __ T2D,
16175             as_FloatRegister($src1$$reg),
16176             as_FloatRegister($src2$$reg));
16177   %}
16178   ins_pipe(vmuldiv_fp128);
16179 %}
16180 
16181 // --------------------------------- SQRT -------------------------------------
16182 
16183 instruct vsqrt2D(vecX dst, vecX src)
16184 %{
16185   predicate(n->as_Vector()->length() == 2);
16186   match(Set dst (SqrtVD src));
16187   format %{ "fsqrt  $dst, $src\t# vector (2D)" %}
16188   ins_encode %{
16189     __ fsqrt(as_FloatRegister($dst$$reg), __ T2D,
16190              as_FloatRegister($src$$reg));
16191   %}
16192   ins_pipe(vsqrt_fp128);
16193 %}
16194 
16195 // --------------------------------- ABS --------------------------------------
16196 
16197 instruct vabs2F(vecD dst, vecD src)
16198 %{
16199   predicate(n->as_Vector()->length() == 2);
16200   match(Set dst (AbsVF src));
16201   ins_cost(INSN_COST * 3);
16202   format %{ "fabs  $dst,$src\t# vector (2S)" %}
16203   ins_encode %{
16204     __ fabs(as_FloatRegister($dst$$reg), __ T2S,
16205             as_FloatRegister($src$$reg));
16206   %}
16207   ins_pipe(vunop_fp64);
16208 %}
16209 
16210 instruct vabs4F(vecX dst, vecX src)
16211 %{
16212   predicate(n->as_Vector()->length() == 4);
16213   match(Set dst (AbsVF src));
16214   ins_cost(INSN_COST * 3);
16215   format %{ "fabs  $dst,$src\t# vector (4S)" %}
16216   ins_encode %{
16217     __ fabs(as_FloatRegister($dst$$reg), __ T4S,
16218             as_FloatRegister($src$$reg));
16219   %}
16220   ins_pipe(vunop_fp128);
16221 %}
16222 
16223 instruct vabs2D(vecX dst, vecX src)
16224 %{
16225   predicate(n->as_Vector()->length() == 2);
16226   match(Set dst (AbsVD src));
16227   ins_cost(INSN_COST * 3);
16228   format %{ "fabs  $dst,$src\t# vector (2D)" %}
16229   ins_encode %{
16230     __ fabs(as_FloatRegister($dst$$reg), __ T2D,
16231             as_FloatRegister($src$$reg));
16232   %}
16233   ins_pipe(vunop_fp128);
16234 %}
16235 
16236 // --------------------------------- NEG --------------------------------------
16237 
16238 instruct vneg2F(vecD dst, vecD src)
16239 %{
16240   predicate(n->as_Vector()->length() == 2);
16241   match(Set dst (NegVF src));
16242   ins_cost(INSN_COST * 3);
16243   format %{ "fneg  $dst,$src\t# vector (2S)" %}
16244   ins_encode %{
16245     __ fneg(as_FloatRegister($dst$$reg), __ T2S,
16246             as_FloatRegister($src$$reg));
16247   %}
16248   ins_pipe(vunop_fp64);
16249 %}
16250 
16251 instruct vneg4F(vecX dst, vecX src)
16252 %{
16253   predicate(n->as_Vector()->length() == 4);
16254   match(Set dst (NegVF src));
16255   ins_cost(INSN_COST * 3);
16256   format %{ "fneg  $dst,$src\t# vector (4S)" %}
16257   ins_encode %{
16258     __ fneg(as_FloatRegister($dst$$reg), __ T4S,
16259             as_FloatRegister($src$$reg));
16260   %}
16261   ins_pipe(vunop_fp128);
16262 %}
16263 
16264 instruct vneg2D(vecX dst, vecX src)
16265 %{
16266   predicate(n->as_Vector()->length() == 2);
16267   match(Set dst (NegVD src));
16268   ins_cost(INSN_COST * 3);
16269   format %{ "fneg  $dst,$src\t# vector (2D)" %}
16270   ins_encode %{
16271     __ fneg(as_FloatRegister($dst$$reg), __ T2D,
16272             as_FloatRegister($src$$reg));
16273   %}
16274   ins_pipe(vunop_fp128);
16275 %}
16276 
16277 // --------------------------------- AND --------------------------------------
16278 
16279 instruct vand8B(vecD dst, vecD src1, vecD src2)
16280 %{
16281   predicate(n->as_Vector()->length_in_bytes() == 4 ||
16282             n->as_Vector()->length_in_bytes() == 8);
16283   match(Set dst (AndV src1 src2));
16284   ins_cost(INSN_COST);
16285   format %{ "and  $dst,$src1,$src2\t# vector (8B)" %}
16286   ins_encode %{
16287     __ andr(as_FloatRegister($dst$$reg), __ T8B,
16288             as_FloatRegister($src1$$reg),
16289             as_FloatRegister($src2$$reg));
16290   %}
16291   ins_pipe(vlogical64);
16292 %}
16293 
16294 instruct vand16B(vecX dst, vecX src1, vecX src2)
16295 %{
16296   predicate(n->as_Vector()->length_in_bytes() == 16);
16297   match(Set dst (AndV src1 src2));
16298   ins_cost(INSN_COST);
16299   format %{ "and  $dst,$src1,$src2\t# vector (16B)" %}
16300   ins_encode %{
16301     __ andr(as_FloatRegister($dst$$reg), __ T16B,
16302             as_FloatRegister($src1$$reg),
16303             as_FloatRegister($src2$$reg));
16304   %}
16305   ins_pipe(vlogical128);
16306 %}
16307 
16308 // --------------------------------- OR ---------------------------------------
16309 
16310 instruct vor8B(vecD dst, vecD src1, vecD src2)
16311 %{
16312   predicate(n->as_Vector()->length_in_bytes() == 4 ||
16313             n->as_Vector()->length_in_bytes() == 8);
16314   match(Set dst (OrV src1 src2));
16315   ins_cost(INSN_COST);
16316   format %{ "and  $dst,$src1,$src2\t# vector (8B)" %}
16317   ins_encode %{
16318     __ orr(as_FloatRegister($dst$$reg), __ T8B,
16319             as_FloatRegister($src1$$reg),
16320             as_FloatRegister($src2$$reg));
16321   %}
16322   ins_pipe(vlogical64);
16323 %}
16324 
16325 instruct vor16B(vecX dst, vecX src1, vecX src2)
16326 %{
16327   predicate(n->as_Vector()->length_in_bytes() == 16);
16328   match(Set dst (OrV src1 src2));
16329   ins_cost(INSN_COST);
16330   format %{ "orr  $dst,$src1,$src2\t# vector (16B)" %}
16331   ins_encode %{
16332     __ orr(as_FloatRegister($dst$$reg), __ T16B,
16333             as_FloatRegister($src1$$reg),
16334             as_FloatRegister($src2$$reg));
16335   %}
16336   ins_pipe(vlogical128);
16337 %}
16338 
16339 // --------------------------------- XOR --------------------------------------
16340 
16341 instruct vxor8B(vecD dst, vecD src1, vecD src2)
16342 %{
16343   predicate(n->as_Vector()->length_in_bytes() == 4 ||
16344             n->as_Vector()->length_in_bytes() == 8);
16345   match(Set dst (XorV src1 src2));
16346   ins_cost(INSN_COST);
16347   format %{ "xor  $dst,$src1,$src2\t# vector (8B)" %}
16348   ins_encode %{
16349     __ eor(as_FloatRegister($dst$$reg), __ T8B,
16350             as_FloatRegister($src1$$reg),
16351             as_FloatRegister($src2$$reg));
16352   %}
16353   ins_pipe(vlogical64);
16354 %}
16355 
16356 instruct vxor16B(vecX dst, vecX src1, vecX src2)
16357 %{
16358   predicate(n->as_Vector()->length_in_bytes() == 16);
16359   match(Set dst (XorV src1 src2));
16360   ins_cost(INSN_COST);
16361   format %{ "xor  $dst,$src1,$src2\t# vector (16B)" %}
16362   ins_encode %{
16363     __ eor(as_FloatRegister($dst$$reg), __ T16B,
16364             as_FloatRegister($src1$$reg),
16365             as_FloatRegister($src2$$reg));
16366   %}
16367   ins_pipe(vlogical128);
16368 %}
16369 
16370 // ------------------------------ Shift ---------------------------------------
16371 instruct vshiftcnt8B(vecD dst, iRegIorL2I cnt) %{
16372   predicate(n->as_Vector()->length_in_bytes() == 8);
16373   match(Set dst (LShiftCntV cnt));
16374   match(Set dst (RShiftCntV cnt));
16375   format %{ "dup  $dst, $cnt\t# shift count vector (8B)" %}
16376   ins_encode %{
16377     __ dup(as_FloatRegister($dst$$reg), __ T8B, as_Register($cnt$$reg));
16378   %}
16379   ins_pipe(vdup_reg_reg64);
16380 %}
16381 
16382 instruct vshiftcnt16B(vecX dst, iRegIorL2I cnt) %{
16383   predicate(n->as_Vector()->length_in_bytes() == 16);
16384   match(Set dst (LShiftCntV cnt));
16385   match(Set dst (RShiftCntV cnt));
16386   format %{ "dup  $dst, $cnt\t# shift count vector (16B)" %}
16387   ins_encode %{
16388     __ dup(as_FloatRegister($dst$$reg), __ T16B, as_Register($cnt$$reg));
16389   %}
16390   ins_pipe(vdup_reg_reg128);
16391 %}
16392 
16393 instruct vsll8B(vecD dst, vecD src, vecD shift) %{
16394   predicate(n->as_Vector()->length() == 4 ||
16395             n->as_Vector()->length() == 8);
16396   match(Set dst (LShiftVB src shift));
16397   ins_cost(INSN_COST);
16398   format %{ "sshl  $dst,$src,$shift\t# vector (8B)" %}
16399   ins_encode %{
16400     __ sshl(as_FloatRegister($dst$$reg), __ T8B,
16401             as_FloatRegister($src$$reg),
16402             as_FloatRegister($shift$$reg));
16403   %}
16404   ins_pipe(vshift64);
16405 %}
16406 
16407 instruct vsll16B(vecX dst, vecX src, vecX shift) %{
16408   predicate(n->as_Vector()->length() == 16);
16409   match(Set dst (LShiftVB src shift));
16410   ins_cost(INSN_COST);
16411   format %{ "sshl  $dst,$src,$shift\t# vector (16B)" %}
16412   ins_encode %{
16413     __ sshl(as_FloatRegister($dst$$reg), __ T16B,
16414             as_FloatRegister($src$$reg),
16415             as_FloatRegister($shift$$reg));
16416   %}
16417   ins_pipe(vshift128);
16418 %}
16419 
16420 // Right shifts with vector shift count on aarch64 SIMD are implemented
16421 // as left shift by negative shift count.
16422 // There are two cases for vector shift count.
16423 //
16424 // Case 1: The vector shift count is from replication.
16425 //        |            |
16426 //    LoadVector  RShiftCntV
16427 //        |       /
16428 //     RShiftVI
16429 // Note: In inner loop, multiple neg instructions are used, which can be
16430 // moved to outer loop and merge into one neg instruction.
16431 //
16432 // Case 2: The vector shift count is from loading.
16433 // This case isn't supported by middle-end now. But it's supported by
16434 // panama/vectorIntrinsics(JEP 338: Vector API).
16435 //        |            |
16436 //    LoadVector  LoadVector
16437 //        |       /
16438 //     RShiftVI
16439 //
16440 
16441 instruct vsra8B(vecD dst, vecD src, vecD shift, vecD tmp) %{
16442   predicate(n->as_Vector()->length() == 4 ||
16443             n->as_Vector()->length() == 8);
16444   match(Set dst (RShiftVB src shift));
16445   ins_cost(INSN_COST);
16446   effect(TEMP tmp);
16447   format %{ "negr  $tmp,$shift\t"
16448             "sshl  $dst,$src,$tmp\t# vector (8B)" %}
16449   ins_encode %{
16450     __ negr(as_FloatRegister($tmp$$reg), __ T8B,
16451             as_FloatRegister($shift$$reg));
16452     __ sshl(as_FloatRegister($dst$$reg), __ T8B,
16453             as_FloatRegister($src$$reg),
16454             as_FloatRegister($tmp$$reg));
16455   %}
16456   ins_pipe(vshift64);
16457 %}
16458 
16459 instruct vsra16B(vecX dst, vecX src, vecX shift, vecX tmp) %{
16460   predicate(n->as_Vector()->length() == 16);
16461   match(Set dst (RShiftVB src shift));
16462   ins_cost(INSN_COST);
16463   effect(TEMP tmp);
16464   format %{ "negr  $tmp,$shift\t"
16465             "sshl  $dst,$src,$tmp\t# vector (16B)" %}
16466   ins_encode %{
16467     __ negr(as_FloatRegister($tmp$$reg), __ T16B,
16468             as_FloatRegister($shift$$reg));
16469     __ sshl(as_FloatRegister($dst$$reg), __ T16B,
16470             as_FloatRegister($src$$reg),
16471             as_FloatRegister($tmp$$reg));
16472   %}
16473   ins_pipe(vshift128);
16474 %}
16475 
16476 instruct vsrl8B(vecD dst, vecD src, vecD shift, vecD tmp) %{
16477   predicate(n->as_Vector()->length() == 4 ||
16478             n->as_Vector()->length() == 8);
16479   match(Set dst (URShiftVB src shift));
16480   ins_cost(INSN_COST);
16481   effect(TEMP tmp);
16482   format %{ "negr  $tmp,$shift\t"
16483             "ushl  $dst,$src,$tmp\t# vector (8B)" %}
16484   ins_encode %{
16485     __ negr(as_FloatRegister($tmp$$reg), __ T8B,
16486             as_FloatRegister($shift$$reg));
16487     __ ushl(as_FloatRegister($dst$$reg), __ T8B,
16488             as_FloatRegister($src$$reg),
16489             as_FloatRegister($tmp$$reg));
16490   %}
16491   ins_pipe(vshift64);
16492 %}
16493 
16494 instruct vsrl16B(vecX dst, vecX src, vecX shift, vecX tmp) %{
16495   predicate(n->as_Vector()->length() == 16);
16496   match(Set dst (URShiftVB src shift));
16497   ins_cost(INSN_COST);
16498   effect(TEMP tmp);
16499   format %{ "negr  $tmp,$shift\t"
16500             "ushl  $dst,$src,$tmp\t# vector (16B)" %}
16501   ins_encode %{
16502     __ negr(as_FloatRegister($tmp$$reg), __ T16B,
16503             as_FloatRegister($shift$$reg));
16504     __ ushl(as_FloatRegister($dst$$reg), __ T16B,
16505             as_FloatRegister($src$$reg),
16506             as_FloatRegister($tmp$$reg));
16507   %}
16508   ins_pipe(vshift128);
16509 %}
16510 
16511 instruct vsll8B_imm(vecD dst, vecD src, immI shift) %{
16512   predicate(n->as_Vector()->length() == 4 ||
16513             n->as_Vector()->length() == 8);
16514   match(Set dst (LShiftVB src shift));
16515   ins_cost(INSN_COST);
16516   format %{ "shl    $dst, $src, $shift\t# vector (8B)" %}
16517   ins_encode %{
16518     int sh = (int)$shift$$constant;
16519     if (sh >= 8) {
16520       __ eor(as_FloatRegister($dst$$reg), __ T8B,
16521              as_FloatRegister($src$$reg),
16522              as_FloatRegister($src$$reg));
16523     } else {
16524       __ shl(as_FloatRegister($dst$$reg), __ T8B,
16525              as_FloatRegister($src$$reg), sh);
16526     }
16527   %}
16528   ins_pipe(vshift64_imm);
16529 %}
16530 
16531 instruct vsll16B_imm(vecX dst, vecX src, immI shift) %{
16532   predicate(n->as_Vector()->length() == 16);
16533   match(Set dst (LShiftVB src shift));
16534   ins_cost(INSN_COST);
16535   format %{ "shl    $dst, $src, $shift\t# vector (16B)" %}
16536   ins_encode %{
16537     int sh = (int)$shift$$constant;
16538     if (sh >= 8) {
16539       __ eor(as_FloatRegister($dst$$reg), __ T16B,
16540              as_FloatRegister($src$$reg),
16541              as_FloatRegister($src$$reg));
16542     } else {
16543       __ shl(as_FloatRegister($dst$$reg), __ T16B,
16544              as_FloatRegister($src$$reg), sh);
16545     }
16546   %}
16547   ins_pipe(vshift128_imm);
16548 %}
16549 
16550 instruct vsra8B_imm(vecD dst, vecD src, immI shift) %{
16551   predicate(n->as_Vector()->length() == 4 ||
16552             n->as_Vector()->length() == 8);
16553   match(Set dst (RShiftVB src shift));
16554   ins_cost(INSN_COST);
16555   format %{ "sshr    $dst, $src, $shift\t# vector (8B)" %}
16556   ins_encode %{
16557     int sh = (int)$shift$$constant;
16558     if (sh >= 8) sh = 7;
16559     __ sshr(as_FloatRegister($dst$$reg), __ T8B,
16560            as_FloatRegister($src$$reg), sh);
16561   %}
16562   ins_pipe(vshift64_imm);
16563 %}
16564 
16565 instruct vsra16B_imm(vecX dst, vecX src, immI shift) %{
16566   predicate(n->as_Vector()->length() == 16);
16567   match(Set dst (RShiftVB src shift));
16568   ins_cost(INSN_COST);
16569   format %{ "sshr    $dst, $src, $shift\t# vector (16B)" %}
16570   ins_encode %{
16571     int sh = (int)$shift$$constant;
16572     if (sh >= 8) sh = 7;
16573     __ sshr(as_FloatRegister($dst$$reg), __ T16B,
16574            as_FloatRegister($src$$reg), sh);
16575   %}
16576   ins_pipe(vshift128_imm);
16577 %}
16578 
16579 instruct vsrl8B_imm(vecD dst, vecD src, immI shift) %{
16580   predicate(n->as_Vector()->length() == 4 ||
16581             n->as_Vector()->length() == 8);
16582   match(Set dst (URShiftVB src shift));
16583   ins_cost(INSN_COST);
16584   format %{ "ushr    $dst, $src, $shift\t# vector (8B)" %}
16585   ins_encode %{
16586     int sh = (int)$shift$$constant;
16587     if (sh >= 8) {
16588       __ eor(as_FloatRegister($dst$$reg), __ T8B,
16589              as_FloatRegister($src$$reg),
16590              as_FloatRegister($src$$reg));
16591     } else {
16592       __ ushr(as_FloatRegister($dst$$reg), __ T8B,
16593              as_FloatRegister($src$$reg), sh);
16594     }
16595   %}
16596   ins_pipe(vshift64_imm);
16597 %}
16598 
16599 instruct vsrl16B_imm(vecX dst, vecX src, immI shift) %{
16600   predicate(n->as_Vector()->length() == 16);
16601   match(Set dst (URShiftVB src shift));
16602   ins_cost(INSN_COST);
16603   format %{ "ushr    $dst, $src, $shift\t# vector (16B)" %}
16604   ins_encode %{
16605     int sh = (int)$shift$$constant;
16606     if (sh >= 8) {
16607       __ eor(as_FloatRegister($dst$$reg), __ T16B,
16608              as_FloatRegister($src$$reg),
16609              as_FloatRegister($src$$reg));
16610     } else {
16611       __ ushr(as_FloatRegister($dst$$reg), __ T16B,
16612              as_FloatRegister($src$$reg), sh);
16613     }
16614   %}
16615   ins_pipe(vshift128_imm);
16616 %}
16617 
16618 instruct vsll4S(vecD dst, vecD src, vecD shift) %{
16619   predicate(n->as_Vector()->length() == 2 ||
16620             n->as_Vector()->length() == 4);
16621   match(Set dst (LShiftVS src shift));
16622   ins_cost(INSN_COST);
16623   format %{ "sshl  $dst,$src,$shift\t# vector (4H)" %}
16624   ins_encode %{
16625     __ sshl(as_FloatRegister($dst$$reg), __ T4H,
16626             as_FloatRegister($src$$reg),
16627             as_FloatRegister($shift$$reg));
16628   %}
16629   ins_pipe(vshift64);
16630 %}
16631 
16632 instruct vsll8S(vecX dst, vecX src, vecX shift) %{
16633   predicate(n->as_Vector()->length() == 8);
16634   match(Set dst (LShiftVS src shift));
16635   ins_cost(INSN_COST);
16636   format %{ "sshl  $dst,$src,$shift\t# vector (8H)" %}
16637   ins_encode %{
16638     __ sshl(as_FloatRegister($dst$$reg), __ T8H,
16639             as_FloatRegister($src$$reg),
16640             as_FloatRegister($shift$$reg));
16641   %}
16642   ins_pipe(vshift128);
16643 %}
16644 
16645 instruct vsra4S(vecD dst, vecD src, vecD shift, vecD tmp) %{
16646   predicate(n->as_Vector()->length() == 2 ||
16647             n->as_Vector()->length() == 4);
16648   match(Set dst (RShiftVS src shift));
16649   ins_cost(INSN_COST);
16650   effect(TEMP tmp);
16651   format %{ "negr  $tmp,$shift\t"
16652             "sshl  $dst,$src,$tmp\t# vector (4H)" %}
16653   ins_encode %{
16654     __ negr(as_FloatRegister($tmp$$reg), __ T8B,
16655             as_FloatRegister($shift$$reg));
16656     __ sshl(as_FloatRegister($dst$$reg), __ T4H,
16657             as_FloatRegister($src$$reg),
16658             as_FloatRegister($tmp$$reg));
16659   %}
16660   ins_pipe(vshift64);
16661 %}
16662 
16663 instruct vsra8S(vecX dst, vecX src, vecX shift, vecX tmp) %{
16664   predicate(n->as_Vector()->length() == 8);
16665   match(Set dst (RShiftVS src shift));
16666   ins_cost(INSN_COST);
16667   effect(TEMP tmp);
16668   format %{ "negr  $tmp,$shift\t"
16669             "sshl  $dst,$src,$tmp\t# vector (8H)" %}
16670   ins_encode %{
16671     __ negr(as_FloatRegister($tmp$$reg), __ T16B,
16672             as_FloatRegister($shift$$reg));
16673     __ sshl(as_FloatRegister($dst$$reg), __ T8H,
16674             as_FloatRegister($src$$reg),
16675             as_FloatRegister($tmp$$reg));
16676   %}
16677   ins_pipe(vshift128);
16678 %}
16679 
16680 instruct vsrl4S(vecD dst, vecD src, vecD shift, vecD tmp) %{
16681   predicate(n->as_Vector()->length() == 2 ||
16682             n->as_Vector()->length() == 4);
16683   match(Set dst (URShiftVS src shift));
16684   ins_cost(INSN_COST);
16685   effect(TEMP tmp);
16686   format %{ "negr  $tmp,$shift\t"
16687             "ushl  $dst,$src,$tmp\t# vector (4H)" %}
16688   ins_encode %{
16689     __ negr(as_FloatRegister($tmp$$reg), __ T8B,
16690             as_FloatRegister($shift$$reg));
16691     __ ushl(as_FloatRegister($dst$$reg), __ T4H,
16692             as_FloatRegister($src$$reg),
16693             as_FloatRegister($tmp$$reg));
16694   %}
16695   ins_pipe(vshift64);
16696 %}
16697 
16698 instruct vsrl8S(vecX dst, vecX src, vecX shift, vecX tmp) %{
16699   predicate(n->as_Vector()->length() == 8);
16700   match(Set dst (URShiftVS src shift));
16701   ins_cost(INSN_COST);
16702   effect(TEMP tmp);
16703   format %{ "negr  $tmp,$shift\t"
16704             "ushl  $dst,$src,$tmp\t# vector (8H)" %}
16705   ins_encode %{
16706     __ negr(as_FloatRegister($tmp$$reg), __ T16B,
16707             as_FloatRegister($shift$$reg));
16708     __ ushl(as_FloatRegister($dst$$reg), __ T8H,
16709             as_FloatRegister($src$$reg),
16710             as_FloatRegister($tmp$$reg));
16711   %}
16712   ins_pipe(vshift128);
16713 %}
16714 
16715 instruct vsll4S_imm(vecD dst, vecD src, immI shift) %{
16716   predicate(n->as_Vector()->length() == 2 ||
16717             n->as_Vector()->length() == 4);
16718   match(Set dst (LShiftVS src shift));
16719   ins_cost(INSN_COST);
16720   format %{ "shl    $dst, $src, $shift\t# vector (4H)" %}
16721   ins_encode %{
16722     int sh = (int)$shift$$constant;
16723     if (sh >= 16) {
16724       __ eor(as_FloatRegister($dst$$reg), __ T8B,
16725              as_FloatRegister($src$$reg),
16726              as_FloatRegister($src$$reg));
16727     } else {
16728       __ shl(as_FloatRegister($dst$$reg), __ T4H,
16729              as_FloatRegister($src$$reg), sh);
16730     }
16731   %}
16732   ins_pipe(vshift64_imm);
16733 %}
16734 
16735 instruct vsll8S_imm(vecX dst, vecX src, immI shift) %{
16736   predicate(n->as_Vector()->length() == 8);
16737   match(Set dst (LShiftVS src shift));
16738   ins_cost(INSN_COST);
16739   format %{ "shl    $dst, $src, $shift\t# vector (8H)" %}
16740   ins_encode %{
16741     int sh = (int)$shift$$constant;
16742     if (sh >= 16) {
16743       __ eor(as_FloatRegister($dst$$reg), __ T16B,
16744              as_FloatRegister($src$$reg),
16745              as_FloatRegister($src$$reg));
16746     } else {
16747       __ shl(as_FloatRegister($dst$$reg), __ T8H,
16748              as_FloatRegister($src$$reg), sh);
16749     }
16750   %}
16751   ins_pipe(vshift128_imm);
16752 %}
16753 
16754 instruct vsra4S_imm(vecD dst, vecD src, immI shift) %{
16755   predicate(n->as_Vector()->length() == 2 ||
16756             n->as_Vector()->length() == 4);
16757   match(Set dst (RShiftVS src shift));
16758   ins_cost(INSN_COST);
16759   format %{ "sshr    $dst, $src, $shift\t# vector (4H)" %}
16760   ins_encode %{
16761     int sh = (int)$shift$$constant;
16762     if (sh >= 16) sh = 15;
16763     __ sshr(as_FloatRegister($dst$$reg), __ T4H,
16764            as_FloatRegister($src$$reg), sh);
16765   %}
16766   ins_pipe(vshift64_imm);
16767 %}
16768 
16769 instruct vsra8S_imm(vecX dst, vecX src, immI shift) %{
16770   predicate(n->as_Vector()->length() == 8);
16771   match(Set dst (RShiftVS src shift));
16772   ins_cost(INSN_COST);
16773   format %{ "sshr    $dst, $src, $shift\t# vector (8H)" %}
16774   ins_encode %{
16775     int sh = (int)$shift$$constant;
16776     if (sh >= 16) sh = 15;
16777     __ sshr(as_FloatRegister($dst$$reg), __ T8H,
16778            as_FloatRegister($src$$reg), sh);
16779   %}
16780   ins_pipe(vshift128_imm);
16781 %}
16782 
16783 instruct vsrl4S_imm(vecD dst, vecD src, immI shift) %{
16784   predicate(n->as_Vector()->length() == 2 ||
16785             n->as_Vector()->length() == 4);
16786   match(Set dst (URShiftVS src shift));
16787   ins_cost(INSN_COST);
16788   format %{ "ushr    $dst, $src, $shift\t# vector (4H)" %}
16789   ins_encode %{
16790     int sh = (int)$shift$$constant;
16791     if (sh >= 16) {
16792       __ eor(as_FloatRegister($dst$$reg), __ T8B,
16793              as_FloatRegister($src$$reg),
16794              as_FloatRegister($src$$reg));
16795     } else {
16796       __ ushr(as_FloatRegister($dst$$reg), __ T4H,
16797              as_FloatRegister($src$$reg), sh);
16798     }
16799   %}
16800   ins_pipe(vshift64_imm);
16801 %}
16802 
16803 instruct vsrl8S_imm(vecX dst, vecX src, immI shift) %{
16804   predicate(n->as_Vector()->length() == 8);
16805   match(Set dst (URShiftVS src shift));
16806   ins_cost(INSN_COST);
16807   format %{ "ushr    $dst, $src, $shift\t# vector (8H)" %}
16808   ins_encode %{
16809     int sh = (int)$shift$$constant;
16810     if (sh >= 16) {
16811       __ eor(as_FloatRegister($dst$$reg), __ T16B,
16812              as_FloatRegister($src$$reg),
16813              as_FloatRegister($src$$reg));
16814     } else {
16815       __ ushr(as_FloatRegister($dst$$reg), __ T8H,
16816              as_FloatRegister($src$$reg), sh);
16817     }
16818   %}
16819   ins_pipe(vshift128_imm);
16820 %}
16821 
16822 instruct vsll2I(vecD dst, vecD src, vecD shift) %{
16823   predicate(n->as_Vector()->length() == 2);
16824   match(Set dst (LShiftVI src shift));
16825   ins_cost(INSN_COST);
16826   format %{ "sshl  $dst,$src,$shift\t# vector (2S)" %}
16827   ins_encode %{
16828     __ sshl(as_FloatRegister($dst$$reg), __ T2S,
16829             as_FloatRegister($src$$reg),
16830             as_FloatRegister($shift$$reg));
16831   %}
16832   ins_pipe(vshift64);
16833 %}
16834 
16835 instruct vsll4I(vecX dst, vecX src, vecX shift) %{
16836   predicate(n->as_Vector()->length() == 4);
16837   match(Set dst (LShiftVI src shift));
16838   ins_cost(INSN_COST);
16839   format %{ "sshl  $dst,$src,$shift\t# vector (4S)" %}
16840   ins_encode %{
16841     __ sshl(as_FloatRegister($dst$$reg), __ T4S,
16842             as_FloatRegister($src$$reg),
16843             as_FloatRegister($shift$$reg));
16844   %}
16845   ins_pipe(vshift128);
16846 %}
16847 
16848 instruct vsra2I(vecD dst, vecD src, vecD shift, vecD tmp) %{
16849   predicate(n->as_Vector()->length() == 2);
16850   match(Set dst (RShiftVI src shift));
16851   ins_cost(INSN_COST);
16852   effect(TEMP tmp);
16853   format %{ "negr  $tmp,$shift\t"
16854             "sshl  $dst,$src,$tmp\t# vector (2S)" %}
16855   ins_encode %{
16856     __ negr(as_FloatRegister($tmp$$reg), __ T8B,
16857             as_FloatRegister($shift$$reg));
16858     __ sshl(as_FloatRegister($dst$$reg), __ T2S,
16859             as_FloatRegister($src$$reg),
16860             as_FloatRegister($tmp$$reg));
16861   %}
16862   ins_pipe(vshift64);
16863 %}
16864 
16865 instruct vsra4I(vecX dst, vecX src, vecX shift, vecX tmp) %{
16866   predicate(n->as_Vector()->length() == 4);
16867   match(Set dst (RShiftVI src shift));
16868   ins_cost(INSN_COST);
16869   effect(TEMP tmp);
16870   format %{ "negr  $tmp,$shift\t"
16871             "sshl  $dst,$src,$tmp\t# vector (4S)" %}
16872   ins_encode %{
16873     __ negr(as_FloatRegister($tmp$$reg), __ T16B,
16874             as_FloatRegister($shift$$reg));
16875     __ sshl(as_FloatRegister($dst$$reg), __ T4S,
16876             as_FloatRegister($src$$reg),
16877             as_FloatRegister($tmp$$reg));
16878   %}
16879   ins_pipe(vshift128);
16880 %}
16881 
16882 instruct vsrl2I(vecD dst, vecD src, vecD shift, vecD tmp) %{
16883   predicate(n->as_Vector()->length() == 2);
16884   match(Set dst (URShiftVI src shift));
16885   ins_cost(INSN_COST);
16886   effect(TEMP tmp);
16887   format %{ "negr  $tmp,$shift\t"
16888             "ushl  $dst,$src,$tmp\t# vector (2S)" %}
16889   ins_encode %{
16890     __ negr(as_FloatRegister($tmp$$reg), __ T8B,
16891             as_FloatRegister($shift$$reg));
16892     __ ushl(as_FloatRegister($dst$$reg), __ T2S,
16893             as_FloatRegister($src$$reg),
16894             as_FloatRegister($tmp$$reg));
16895   %}
16896   ins_pipe(vshift64);
16897 %}
16898 
16899 instruct vsrl4I(vecX dst, vecX src, vecX shift, vecX tmp) %{
16900   predicate(n->as_Vector()->length() == 4);
16901   match(Set dst (URShiftVI src shift));
16902   ins_cost(INSN_COST);
16903   effect(TEMP tmp);
16904   format %{ "negr  $tmp,$shift\t"
16905             "ushl  $dst,$src,$tmp\t# vector (4S)" %}
16906   ins_encode %{
16907     __ negr(as_FloatRegister($tmp$$reg), __ T16B,
16908             as_FloatRegister($shift$$reg));
16909     __ ushl(as_FloatRegister($dst$$reg), __ T4S,
16910             as_FloatRegister($src$$reg),
16911             as_FloatRegister($tmp$$reg));
16912   %}
16913   ins_pipe(vshift128);
16914 %}
16915 
16916 instruct vsll2I_imm(vecD dst, vecD src, immI shift) %{
16917   predicate(n->as_Vector()->length() == 2);
16918   match(Set dst (LShiftVI src shift));
16919   ins_cost(INSN_COST);
16920   format %{ "shl    $dst, $src, $shift\t# vector (2S)" %}
16921   ins_encode %{
16922     __ shl(as_FloatRegister($dst$$reg), __ T2S,
16923            as_FloatRegister($src$$reg),
16924            (int)$shift$$constant);
16925   %}
16926   ins_pipe(vshift64_imm);
16927 %}
16928 
16929 instruct vsll4I_imm(vecX dst, vecX src, immI shift) %{
16930   predicate(n->as_Vector()->length() == 4);
16931   match(Set dst (LShiftVI src shift));
16932   ins_cost(INSN_COST);
16933   format %{ "shl    $dst, $src, $shift\t# vector (4S)" %}
16934   ins_encode %{
16935     __ shl(as_FloatRegister($dst$$reg), __ T4S,
16936            as_FloatRegister($src$$reg),
16937            (int)$shift$$constant);
16938   %}
16939   ins_pipe(vshift128_imm);
16940 %}
16941 
16942 instruct vsra2I_imm(vecD dst, vecD src, immI shift) %{
16943   predicate(n->as_Vector()->length() == 2);
16944   match(Set dst (RShiftVI src shift));
16945   ins_cost(INSN_COST);
16946   format %{ "sshr    $dst, $src, $shift\t# vector (2S)" %}
16947   ins_encode %{
16948     __ sshr(as_FloatRegister($dst$$reg), __ T2S,
16949             as_FloatRegister($src$$reg),
16950             (int)$shift$$constant);
16951   %}
16952   ins_pipe(vshift64_imm);
16953 %}
16954 
16955 instruct vsra4I_imm(vecX dst, vecX src, immI shift) %{
16956   predicate(n->as_Vector()->length() == 4);
16957   match(Set dst (RShiftVI src shift));
16958   ins_cost(INSN_COST);
16959   format %{ "sshr    $dst, $src, $shift\t# vector (4S)" %}
16960   ins_encode %{
16961     __ sshr(as_FloatRegister($dst$$reg), __ T4S,
16962             as_FloatRegister($src$$reg),
16963             (int)$shift$$constant);
16964   %}
16965   ins_pipe(vshift128_imm);
16966 %}
16967 
16968 instruct vsrl2I_imm(vecD dst, vecD src, immI shift) %{
16969   predicate(n->as_Vector()->length() == 2);
16970   match(Set dst (URShiftVI src shift));
16971   ins_cost(INSN_COST);
16972   format %{ "ushr    $dst, $src, $shift\t# vector (2S)" %}
16973   ins_encode %{
16974     __ ushr(as_FloatRegister($dst$$reg), __ T2S,
16975             as_FloatRegister($src$$reg),
16976             (int)$shift$$constant);
16977   %}
16978   ins_pipe(vshift64_imm);
16979 %}
16980 
16981 instruct vsrl4I_imm(vecX dst, vecX src, immI shift) %{
16982   predicate(n->as_Vector()->length() == 4);
16983   match(Set dst (URShiftVI src shift));
16984   ins_cost(INSN_COST);
16985   format %{ "ushr    $dst, $src, $shift\t# vector (4S)" %}
16986   ins_encode %{
16987     __ ushr(as_FloatRegister($dst$$reg), __ T4S,
16988             as_FloatRegister($src$$reg),
16989             (int)$shift$$constant);
16990   %}
16991   ins_pipe(vshift128_imm);
16992 %}
16993 
16994 instruct vsll2L(vecX dst, vecX src, vecX shift) %{
16995   predicate(n->as_Vector()->length() == 2);
16996   match(Set dst (LShiftVL src shift));
16997   ins_cost(INSN_COST);
16998   format %{ "sshl  $dst,$src,$shift\t# vector (2D)" %}
16999   ins_encode %{
17000     __ sshl(as_FloatRegister($dst$$reg), __ T2D,
17001             as_FloatRegister($src$$reg),
17002             as_FloatRegister($shift$$reg));
17003   %}
17004   ins_pipe(vshift128);
17005 %}
17006 
17007 instruct vsra2L(vecX dst, vecX src, vecX shift, vecX tmp) %{
17008   predicate(n->as_Vector()->length() == 2);
17009   match(Set dst (RShiftVL src shift));
17010   ins_cost(INSN_COST);
17011   effect(TEMP tmp);
17012   format %{ "negr  $tmp,$shift\t"
17013             "sshl  $dst,$src,$tmp\t# vector (2D)" %}
17014   ins_encode %{
17015     __ negr(as_FloatRegister($tmp$$reg), __ T16B,
17016             as_FloatRegister($shift$$reg));
17017     __ sshl(as_FloatRegister($dst$$reg), __ T2D,
17018             as_FloatRegister($src$$reg),
17019             as_FloatRegister($tmp$$reg));
17020   %}
17021   ins_pipe(vshift128);
17022 %}
17023 
17024 instruct vsrl2L(vecX dst, vecX src, vecX shift, vecX tmp) %{
17025   predicate(n->as_Vector()->length() == 2);
17026   match(Set dst (URShiftVL src shift));
17027   ins_cost(INSN_COST);
17028   effect(TEMP tmp);
17029   format %{ "negr  $tmp,$shift\t"
17030             "ushl  $dst,$src,$tmp\t# vector (2D)" %}
17031   ins_encode %{
17032     __ negr(as_FloatRegister($tmp$$reg), __ T16B,
17033             as_FloatRegister($shift$$reg));
17034     __ ushl(as_FloatRegister($dst$$reg), __ T2D,
17035             as_FloatRegister($src$$reg),
17036             as_FloatRegister($tmp$$reg));
17037   %}
17038   ins_pipe(vshift128);
17039 %}
17040 
17041 instruct vsll2L_imm(vecX dst, vecX src, immI shift) %{
17042   predicate(n->as_Vector()->length() == 2);
17043   match(Set dst (LShiftVL src shift));
17044   ins_cost(INSN_COST);
17045   format %{ "shl    $dst, $src, $shift\t# vector (2D)" %}
17046   ins_encode %{
17047     __ shl(as_FloatRegister($dst$$reg), __ T2D,
17048            as_FloatRegister($src$$reg),
17049            (int)$shift$$constant);
17050   %}
17051   ins_pipe(vshift128_imm);
17052 %}
17053 
17054 instruct vsra2L_imm(vecX dst, vecX src, immI shift) %{
17055   predicate(n->as_Vector()->length() == 2);
17056   match(Set dst (RShiftVL src shift));
17057   ins_cost(INSN_COST);
17058   format %{ "sshr    $dst, $src, $shift\t# vector (2D)" %}
17059   ins_encode %{
17060     __ sshr(as_FloatRegister($dst$$reg), __ T2D,
17061             as_FloatRegister($src$$reg),
17062             (int)$shift$$constant);
17063   %}
17064   ins_pipe(vshift128_imm);
17065 %}
17066 
17067 instruct vsrl2L_imm(vecX dst, vecX src, immI shift) %{
17068   predicate(n->as_Vector()->length() == 2);
17069   match(Set dst (URShiftVL src shift));
17070   ins_cost(INSN_COST);
17071   format %{ "ushr    $dst, $src, $shift\t# vector (2D)" %}
17072   ins_encode %{
17073     __ ushr(as_FloatRegister($dst$$reg), __ T2D,
17074             as_FloatRegister($src$$reg),
17075             (int)$shift$$constant);
17076   %}
17077   ins_pipe(vshift128_imm);
17078 %}
17079 
17080 //----------PEEPHOLE RULES-----------------------------------------------------
17081 // These must follow all instruction definitions as they use the names
17082 // defined in the instructions definitions.
17083 //
17084 // peepmatch ( root_instr_name [preceding_instruction]* );
17085 //
17086 // peepconstraint %{
17087 // (instruction_number.operand_name relational_op instruction_number.operand_name
17088 //  [, ...] );
17089 // // instruction numbers are zero-based using left to right order in peepmatch
17090 //
17091 // peepreplace ( instr_name  ( [instruction_number.operand_name]* ) );
17092 // // provide an instruction_number.operand_name for each operand that appears
17093 // // in the replacement instruction's match rule
17094 //
17095 // ---------VM FLAGS---------------------------------------------------------
17096 //
17097 // All peephole optimizations can be turned off using -XX:-OptoPeephole
17098 //
17099 // Each peephole rule is given an identifying number starting with zero and
17100 // increasing by one in the order seen by the parser.  An individual peephole
17101 // can be enabled, and all others disabled, by using -XX:OptoPeepholeAt=#
17102 // on the command-line.
17103 //
17104 // ---------CURRENT LIMITATIONS----------------------------------------------
17105 //
17106 // Only match adjacent instructions in same basic block
17107 // Only equality constraints
17108 // Only constraints between operands, not (0.dest_reg == RAX_enc)
17109 // Only one replacement instruction
17110 //
17111 // ---------EXAMPLE----------------------------------------------------------
17112 //
17113 // // pertinent parts of existing instructions in architecture description
17114 // instruct movI(iRegINoSp dst, iRegI src)
17115 // %{
17116 //   match(Set dst (CopyI src));
17117 // %}
17118 //
17119 // instruct incI_iReg(iRegINoSp dst, immI1 src, rFlagsReg cr)
17120 // %{
17121 //   match(Set dst (AddI dst src));
17122 //   effect(KILL cr);
17123 // %}
17124 //
17125 // // Change (inc mov) to lea
17126 // peephole %{
17127 //   // increment preceeded by register-register move
17128 //   peepmatch ( incI_iReg movI );
17129 //   // require that the destination register of the increment
17130 //   // match the destination register of the move
17131 //   peepconstraint ( 0.dst == 1.dst );
17132 //   // construct a replacement instruction that sets
17133 //   // the destination to ( move's source register + one )
17134 //   peepreplace ( leaI_iReg_immI( 0.dst 1.src 0.src ) );
17135 // %}
17136 //
17137 
17138 // Implementation no longer uses movX instructions since
17139 // machine-independent system no longer uses CopyX nodes.
17140 //
17141 // peephole
17142 // %{
17143 //   peepmatch (incI_iReg movI);
17144 //   peepconstraint (0.dst == 1.dst);
17145 //   peepreplace (leaI_iReg_immI(0.dst 1.src 0.src));
17146 // %}
17147 
17148 // peephole
17149 // %{
17150 //   peepmatch (decI_iReg movI);
17151 //   peepconstraint (0.dst == 1.dst);
17152 //   peepreplace (leaI_iReg_immI(0.dst 1.src 0.src));
17153 // %}
17154 
17155 // peephole
17156 // %{
17157 //   peepmatch (addI_iReg_imm movI);
17158 //   peepconstraint (0.dst == 1.dst);
17159 //   peepreplace (leaI_iReg_immI(0.dst 1.src 0.src));
17160 // %}
17161 
17162 // peephole
17163 // %{
17164 //   peepmatch (incL_iReg movL);
17165 //   peepconstraint (0.dst == 1.dst);
17166 //   peepreplace (leaL_iReg_immL(0.dst 1.src 0.src));
17167 // %}
17168 
17169 // peephole
17170 // %{
17171 //   peepmatch (decL_iReg movL);
17172 //   peepconstraint (0.dst == 1.dst);
17173 //   peepreplace (leaL_iReg_immL(0.dst 1.src 0.src));
17174 // %}
17175 
17176 // peephole
17177 // %{
17178 //   peepmatch (addL_iReg_imm movL);
17179 //   peepconstraint (0.dst == 1.dst);
17180 //   peepreplace (leaL_iReg_immL(0.dst 1.src 0.src));
17181 // %}
17182 
17183 // peephole
17184 // %{
17185 //   peepmatch (addP_iReg_imm movP);
17186 //   peepconstraint (0.dst == 1.dst);
17187 //   peepreplace (leaP_iReg_imm(0.dst 1.src 0.src));
17188 // %}
17189 
17190 // // Change load of spilled value to only a spill
17191 // instruct storeI(memory mem, iRegI src)
17192 // %{
17193 //   match(Set mem (StoreI mem src));
17194 // %}
17195 //
17196 // instruct loadI(iRegINoSp dst, memory mem)
17197 // %{
17198 //   match(Set dst (LoadI mem));
17199 // %}
17200 //
17201 
17202 //----------SMARTSPILL RULES---------------------------------------------------
17203 // These must follow all instruction definitions as they use the names
17204 // defined in the instructions definitions.
17205 
17206 // Local Variables:
17207 // mode: c++
17208 // End: