Source file src/cmd/internal/obj/loong64/asm.go

     1  // Copyright 2022 The Go Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  package loong64
     6  
     7  import (
     8  	"cmd/internal/obj"
     9  	"cmd/internal/objabi"
    10  	"fmt"
    11  	"log"
    12  	"math/bits"
    13  	"slices"
    14  )
    15  
    16  // ctxt0 holds state while assembling a single function.
    17  // Each function gets a fresh ctxt0.
    18  // This allows for multiple functions to be safely concurrently assembled.
    19  type ctxt0 struct {
    20  	ctxt       *obj.Link
    21  	newprog    obj.ProgAlloc
    22  	cursym     *obj.LSym
    23  	autosize   int32
    24  	instoffset int64
    25  	pc         int64
    26  }
    27  
    28  // Instruction layout.
    29  
    30  const (
    31  	FuncAlign = 4
    32  	loopAlign = 16
    33  )
    34  
    35  type Optab struct {
    36  	as    obj.As
    37  	from1 uint8
    38  	reg   uint8
    39  	from3 uint8
    40  	to1   uint8
    41  	to2   uint8
    42  	type_ int8
    43  	size  int8
    44  	param int16
    45  	flag  uint8
    46  }
    47  
    48  const (
    49  	NOTUSETMP = 1 << iota // p expands to multiple instructions, but does NOT use REGTMP
    50  
    51  	// branchLoopHead marks loop entry.
    52  	// Used to insert padding for under-aligned loops.
    53  	branchLoopHead
    54  )
    55  
    56  var optab = []Optab{
    57  	{obj.ATEXT, C_ADDR, C_NONE, C_NONE, C_TEXTSIZE, C_NONE, 0, 0, 0, 0},
    58  
    59  	{AMOVW, C_REG, C_NONE, C_NONE, C_REG, C_NONE, 1, 4, 0, 0},
    60  	{AMOVV, C_REG, C_NONE, C_NONE, C_REG, C_NONE, 1, 4, 0, 0},
    61  	{AMOVB, C_REG, C_NONE, C_NONE, C_REG, C_NONE, 12, 4, 0, 0},
    62  	{AMOVBU, C_REG, C_NONE, C_NONE, C_REG, C_NONE, 12, 4, 0, 0},
    63  	{AMOVWU, C_REG, C_NONE, C_NONE, C_REG, C_NONE, 12, 4, 0, 0},
    64  
    65  	{ASUB, C_REG, C_REG, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    66  	{ASUBV, C_REG, C_REG, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    67  	{AADD, C_REG, C_REG, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    68  	{AADDV, C_REG, C_REG, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    69  	{AAND, C_REG, C_REG, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    70  	{ASUB, C_REG, C_NONE, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    71  	{ASUBV, C_REG, C_NONE, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    72  	{AADD, C_REG, C_NONE, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    73  	{AADDV, C_REG, C_NONE, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    74  	{AAND, C_REG, C_NONE, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    75  	{ANEGW, C_REG, C_NONE, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    76  	{ANEGV, C_REG, C_NONE, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    77  	{AMASKEQZ, C_REG, C_REG, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    78  	{ASLL, C_REG, C_NONE, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    79  	{ASLL, C_REG, C_REG, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    80  	{ASLLV, C_REG, C_NONE, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    81  	{ASLLV, C_REG, C_REG, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    82  	{AMUL, C_REG, C_NONE, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    83  	{AMUL, C_REG, C_REG, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    84  	{AMULV, C_REG, C_NONE, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    85  	{AMULV, C_REG, C_REG, C_NONE, C_REG, C_NONE, 2, 4, 0, 0},
    86  	{AADDF, C_FREG, C_NONE, C_NONE, C_FREG, C_NONE, 2, 4, 0, 0},
    87  	{AADDF, C_FREG, C_FREG, C_NONE, C_FREG, C_NONE, 2, 4, 0, 0},
    88  	{ACMPEQF, C_FREG, C_FREG, C_NONE, C_FCCREG, C_NONE, 2, 4, 0, 0},
    89  
    90  	{AVSEQB, C_VREG, C_VREG, C_NONE, C_VREG, C_NONE, 2, 4, 0, 0},
    91  	{AXVSEQB, C_XREG, C_XREG, C_NONE, C_XREG, C_NONE, 2, 4, 0, 0},
    92  	{AVSEQB, C_S5CON, C_VREG, C_NONE, C_VREG, C_NONE, 22, 4, 0, 0},
    93  	{AXVSEQB, C_S5CON, C_XREG, C_NONE, C_XREG, C_NONE, 22, 4, 0, 0},
    94  	{AVANDV, C_VREG, C_VREG, C_NONE, C_VREG, C_NONE, 2, 4, 0, 0},
    95  	{AVANDV, C_VREG, C_NONE, C_NONE, C_VREG, C_NONE, 2, 4, 0, 0},
    96  	{AXVANDV, C_XREG, C_XREG, C_NONE, C_XREG, C_NONE, 2, 4, 0, 0},
    97  	{AXVANDV, C_XREG, C_NONE, C_NONE, C_XREG, C_NONE, 2, 4, 0, 0},
    98  	{AVANDB, C_U8CON, C_VREG, C_NONE, C_VREG, C_NONE, 23, 4, 0, 0},
    99  	{AVANDB, C_U8CON, C_NONE, C_NONE, C_VREG, C_NONE, 23, 4, 0, 0},
   100  	{AXVANDB, C_U8CON, C_XREG, C_NONE, C_XREG, C_NONE, 23, 4, 0, 0},
   101  	{AXVANDB, C_U8CON, C_NONE, C_NONE, C_XREG, C_NONE, 23, 4, 0, 0},
   102  
   103  	{AVADDB, C_VREG, C_VREG, C_NONE, C_VREG, C_NONE, 2, 4, 0, 0},
   104  	{AVADDB, C_VREG, C_NONE, C_NONE, C_VREG, C_NONE, 2, 4, 0, 0},
   105  	{AXVADDB, C_XREG, C_XREG, C_NONE, C_XREG, C_NONE, 2, 4, 0, 0},
   106  	{AXVADDB, C_XREG, C_NONE, C_NONE, C_XREG, C_NONE, 2, 4, 0, 0},
   107  
   108  	{AVSLLB, C_VREG, C_VREG, C_NONE, C_VREG, C_NONE, 2, 4, 0, 0},
   109  	{AVSLLB, C_VREG, C_NONE, C_NONE, C_VREG, C_NONE, 2, 4, 0, 0},
   110  	{AXVSLLB, C_XREG, C_XREG, C_NONE, C_XREG, C_NONE, 2, 4, 0, 0},
   111  	{AXVSLLB, C_XREG, C_NONE, C_NONE, C_XREG, C_NONE, 2, 4, 0, 0},
   112  	{AVSLLB, C_U3CON, C_VREG, C_NONE, C_VREG, C_NONE, 13, 4, 0, 0},
   113  	{AXVSLLB, C_U3CON, C_XREG, C_NONE, C_XREG, C_NONE, 13, 4, 0, 0},
   114  	{AVSLLB, C_U3CON, C_NONE, C_NONE, C_VREG, C_NONE, 13, 4, 0, 0},
   115  	{AXVSLLB, C_U3CON, C_NONE, C_NONE, C_XREG, C_NONE, 13, 4, 0, 0},
   116  
   117  	{AVSLLH, C_VREG, C_VREG, C_NONE, C_VREG, C_NONE, 2, 4, 0, 0},
   118  	{AVSLLH, C_VREG, C_NONE, C_NONE, C_VREG, C_NONE, 2, 4, 0, 0},
   119  	{AXVSLLH, C_XREG, C_XREG, C_NONE, C_XREG, C_NONE, 2, 4, 0, 0},
   120  	{AXVSLLH, C_XREG, C_NONE, C_NONE, C_XREG, C_NONE, 2, 4, 0, 0},
   121  	{AVSLLH, C_U4CON, C_VREG, C_NONE, C_VREG, C_NONE, 14, 4, 0, 0},
   122  	{AXVSLLH, C_U4CON, C_XREG, C_NONE, C_XREG, C_NONE, 14, 4, 0, 0},
   123  	{AVSLLH, C_U4CON, C_NONE, C_NONE, C_VREG, C_NONE, 14, 4, 0, 0},
   124  	{AXVSLLH, C_U4CON, C_NONE, C_NONE, C_XREG, C_NONE, 14, 4, 0, 0},
   125  
   126  	{AVSLLW, C_VREG, C_VREG, C_NONE, C_VREG, C_NONE, 2, 4, 0, 0},
   127  	{AVSLLW, C_VREG, C_NONE, C_NONE, C_VREG, C_NONE, 2, 4, 0, 0},
   128  	{AXVSLLW, C_XREG, C_XREG, C_NONE, C_XREG, C_NONE, 2, 4, 0, 0},
   129  	{AXVSLLW, C_XREG, C_NONE, C_NONE, C_XREG, C_NONE, 2, 4, 0, 0},
   130  	{AVSLLW, C_U5CON, C_VREG, C_NONE, C_VREG, C_NONE, 31, 4, 0, 0},
   131  	{AXVSLLW, C_U5CON, C_XREG, C_NONE, C_XREG, C_NONE, 31, 4, 0, 0},
   132  	{AVSLLW, C_U5CON, C_NONE, C_NONE, C_VREG, C_NONE, 31, 4, 0, 0},
   133  	{AXVSLLW, C_U5CON, C_NONE, C_NONE, C_XREG, C_NONE, 31, 4, 0, 0},
   134  
   135  	{AVSLLV, C_VREG, C_VREG, C_NONE, C_VREG, C_NONE, 2, 4, 0, 0},
   136  	{AVSLLV, C_VREG, C_NONE, C_NONE, C_VREG, C_NONE, 2, 4, 0, 0},
   137  	{AXVSLLV, C_XREG, C_XREG, C_NONE, C_XREG, C_NONE, 2, 4, 0, 0},
   138  	{AXVSLLV, C_XREG, C_NONE, C_NONE, C_XREG, C_NONE, 2, 4, 0, 0},
   139  	{AVSLLV, C_U6CON, C_VREG, C_NONE, C_VREG, C_NONE, 32, 4, 0, 0},
   140  	{AXVSLLV, C_U6CON, C_XREG, C_NONE, C_XREG, C_NONE, 32, 4, 0, 0},
   141  	{AVSLLV, C_U6CON, C_NONE, C_NONE, C_VREG, C_NONE, 32, 4, 0, 0},
   142  	{AXVSLLV, C_U6CON, C_NONE, C_NONE, C_XREG, C_NONE, 32, 4, 0, 0},
   143  
   144  	{ACLOW, C_REG, C_NONE, C_NONE, C_REG, C_NONE, 9, 4, 0, 0},
   145  	{AABSF, C_FREG, C_NONE, C_NONE, C_FREG, C_NONE, 9, 4, 0, 0},
   146  	{AMOVVF, C_FREG, C_NONE, C_NONE, C_FREG, C_NONE, 9, 4, 0, 0},
   147  	{AMOVF, C_FREG, C_NONE, C_NONE, C_FREG, C_NONE, 9, 4, 0, 0},
   148  	{AMOVD, C_FREG, C_NONE, C_NONE, C_FREG, C_NONE, 9, 4, 0, 0},
   149  	{AVPCNTB, C_VREG, C_NONE, C_NONE, C_VREG, C_NONE, 9, 4, 0, 0},
   150  	{AXVPCNTB, C_XREG, C_NONE, C_NONE, C_XREG, C_NONE, 9, 4, 0, 0},
   151  	{AVSETEQV, C_VREG, C_NONE, C_NONE, C_FCCREG, C_NONE, 9, 4, 0, 0},
   152  	{AXVSETEQV, C_XREG, C_NONE, C_NONE, C_FCCREG, C_NONE, 9, 4, 0, 0},
   153  
   154  	{AFMADDF, C_FREG, C_FREG, C_NONE, C_FREG, C_NONE, 37, 4, 0, 0},
   155  	{AFMADDF, C_FREG, C_FREG, C_FREG, C_FREG, C_NONE, 37, 4, 0, 0},
   156  
   157  	{AMOVW, C_REG, C_NONE, C_NONE, C_SAUTO, C_NONE, 7, 4, REGSP, 0},
   158  	{AMOVWU, C_REG, C_NONE, C_NONE, C_SAUTO, C_NONE, 7, 4, REGSP, 0},
   159  	{AMOVV, C_REG, C_NONE, C_NONE, C_SAUTO, C_NONE, 7, 4, REGSP, 0},
   160  	{AMOVB, C_REG, C_NONE, C_NONE, C_SAUTO, C_NONE, 7, 4, REGSP, 0},
   161  	{AMOVBU, C_REG, C_NONE, C_NONE, C_SAUTO, C_NONE, 7, 4, REGSP, 0},
   162  	{AMOVW, C_REG, C_NONE, C_NONE, C_SOREG, C_NONE, 7, 4, REGZERO, 0},
   163  	{AMOVWU, C_REG, C_NONE, C_NONE, C_SOREG, C_NONE, 7, 4, REGZERO, 0},
   164  	{AMOVV, C_REG, C_NONE, C_NONE, C_SOREG, C_NONE, 7, 4, REGZERO, 0},
   165  	{AMOVB, C_REG, C_NONE, C_NONE, C_SOREG, C_NONE, 7, 4, REGZERO, 0},
   166  	{AMOVBU, C_REG, C_NONE, C_NONE, C_SOREG, C_NONE, 7, 4, REGZERO, 0},
   167  	{AVMOVQ, C_VREG, C_NONE, C_NONE, C_SOREG, C_NONE, 7, 4, REGZERO, 0},
   168  	{AXVMOVQ, C_XREG, C_NONE, C_NONE, C_SOREG, C_NONE, 7, 4, REGZERO, 0},
   169  	{AVMOVQ, C_VREG, C_NONE, C_NONE, C_SAUTO, C_NONE, 7, 4, REGZERO, 0},
   170  	{AXVMOVQ, C_XREG, C_NONE, C_NONE, C_SAUTO, C_NONE, 7, 4, REGZERO, 0},
   171  	{ASC, C_REG, C_NONE, C_NONE, C_SOREG, C_NONE, 7, 4, REGZERO, 0},
   172  	{ASCV, C_REG, C_NONE, C_NONE, C_SOREG, C_NONE, 7, 4, REGZERO, 0},
   173  
   174  	{AMOVW, C_SAUTO, C_NONE, C_NONE, C_REG, C_NONE, 8, 4, REGSP, 0},
   175  	{AMOVWU, C_SAUTO, C_NONE, C_NONE, C_REG, C_NONE, 8, 4, REGSP, 0},
   176  	{AMOVV, C_SAUTO, C_NONE, C_NONE, C_REG, C_NONE, 8, 4, REGSP, 0},
   177  	{AMOVB, C_SAUTO, C_NONE, C_NONE, C_REG, C_NONE, 8, 4, REGSP, 0},
   178  	{AMOVBU, C_SAUTO, C_NONE, C_NONE, C_REG, C_NONE, 8, 4, REGSP, 0},
   179  	{AMOVW, C_SOREG, C_NONE, C_NONE, C_REG, C_NONE, 8, 4, REGZERO, 0},
   180  	{AMOVWU, C_SOREG, C_NONE, C_NONE, C_REG, C_NONE, 8, 4, REGZERO, 0},
   181  	{AMOVV, C_SOREG, C_NONE, C_NONE, C_REG, C_NONE, 8, 4, REGZERO, 0},
   182  	{AMOVB, C_SOREG, C_NONE, C_NONE, C_REG, C_NONE, 8, 4, REGZERO, 0},
   183  	{AMOVBU, C_SOREG, C_NONE, C_NONE, C_REG, C_NONE, 8, 4, REGZERO, 0},
   184  	{AVMOVQ, C_SOREG, C_NONE, C_NONE, C_VREG, C_NONE, 8, 4, REGZERO, 0},
   185  	{AXVMOVQ, C_SOREG, C_NONE, C_NONE, C_XREG, C_NONE, 8, 4, REGZERO, 0},
   186  	{AVMOVQ, C_SAUTO, C_NONE, C_NONE, C_VREG, C_NONE, 8, 4, REGZERO, 0},
   187  	{AXVMOVQ, C_SAUTO, C_NONE, C_NONE, C_XREG, C_NONE, 8, 4, REGZERO, 0},
   188  	{ALL, C_SOREG, C_NONE, C_NONE, C_REG, C_NONE, 8, 4, REGZERO, 0},
   189  	{ALLV, C_SOREG, C_NONE, C_NONE, C_REG, C_NONE, 8, 4, REGZERO, 0},
   190  
   191  	{AMOVW, C_REG, C_NONE, C_NONE, C_LAUTO, C_NONE, 35, 12, REGSP, 0},
   192  	{AMOVWU, C_REG, C_NONE, C_NONE, C_LAUTO, C_NONE, 35, 12, REGSP, 0},
   193  	{AMOVV, C_REG, C_NONE, C_NONE, C_LAUTO, C_NONE, 35, 12, REGSP, 0},
   194  	{AMOVB, C_REG, C_NONE, C_NONE, C_LAUTO, C_NONE, 35, 12, REGSP, 0},
   195  	{AMOVBU, C_REG, C_NONE, C_NONE, C_LAUTO, C_NONE, 35, 12, REGSP, 0},
   196  	{AMOVW, C_REG, C_NONE, C_NONE, C_LOREG, C_NONE, 35, 12, REGZERO, 0},
   197  	{AMOVWU, C_REG, C_NONE, C_NONE, C_LOREG, C_NONE, 35, 12, REGZERO, 0},
   198  	{AMOVV, C_REG, C_NONE, C_NONE, C_LOREG, C_NONE, 35, 12, REGZERO, 0},
   199  	{AMOVB, C_REG, C_NONE, C_NONE, C_LOREG, C_NONE, 35, 12, REGZERO, 0},
   200  	{AMOVBU, C_REG, C_NONE, C_NONE, C_LOREG, C_NONE, 35, 12, REGZERO, 0},
   201  	{ASC, C_REG, C_NONE, C_NONE, C_LOREG, C_NONE, 35, 12, REGZERO, 0},
   202  	{AMOVW, C_REG, C_NONE, C_NONE, C_ADDR, C_NONE, 50, 8, 0, 0},
   203  	{AMOVWU, C_REG, C_NONE, C_NONE, C_ADDR, C_NONE, 50, 8, 0, 0},
   204  	{AMOVV, C_REG, C_NONE, C_NONE, C_ADDR, C_NONE, 50, 8, 0, 0},
   205  	{AMOVB, C_REG, C_NONE, C_NONE, C_ADDR, C_NONE, 50, 8, 0, 0},
   206  	{AMOVBU, C_REG, C_NONE, C_NONE, C_ADDR, C_NONE, 50, 8, 0, 0},
   207  	{AMOVW, C_REG, C_NONE, C_NONE, C_TLS_LE, C_NONE, 53, 16, 0, 0},
   208  	{AMOVWU, C_REG, C_NONE, C_NONE, C_TLS_LE, C_NONE, 53, 16, 0, 0},
   209  	{AMOVV, C_REG, C_NONE, C_NONE, C_TLS_LE, C_NONE, 53, 16, 0, 0},
   210  	{AMOVB, C_REG, C_NONE, C_NONE, C_TLS_LE, C_NONE, 53, 16, 0, 0},
   211  	{AMOVBU, C_REG, C_NONE, C_NONE, C_TLS_LE, C_NONE, 53, 16, 0, 0},
   212  
   213  	{AMOVW, C_LAUTO, C_NONE, C_NONE, C_REG, C_NONE, 36, 12, REGSP, 0},
   214  	{AMOVWU, C_LAUTO, C_NONE, C_NONE, C_REG, C_NONE, 36, 12, REGSP, 0},
   215  	{AMOVV, C_LAUTO, C_NONE, C_NONE, C_REG, C_NONE, 36, 12, REGSP, 0},
   216  	{AMOVB, C_LAUTO, C_NONE, C_NONE, C_REG, C_NONE, 36, 12, REGSP, 0},
   217  	{AMOVBU, C_LAUTO, C_NONE, C_NONE, C_REG, C_NONE, 36, 12, REGSP, 0},
   218  	{AMOVW, C_LOREG, C_NONE, C_NONE, C_REG, C_NONE, 36, 12, REGZERO, 0},
   219  	{AMOVWU, C_LOREG, C_NONE, C_NONE, C_REG, C_NONE, 36, 12, REGZERO, 0},
   220  	{AMOVV, C_LOREG, C_NONE, C_NONE, C_REG, C_NONE, 36, 12, REGZERO, 0},
   221  	{AMOVB, C_LOREG, C_NONE, C_NONE, C_REG, C_NONE, 36, 12, REGZERO, 0},
   222  	{AMOVBU, C_LOREG, C_NONE, C_NONE, C_REG, C_NONE, 36, 12, REGZERO, 0},
   223  	{AMOVW, C_ADDR, C_NONE, C_NONE, C_REG, C_NONE, 51, 8, 0, 0},
   224  	{AMOVWU, C_ADDR, C_NONE, C_NONE, C_REG, C_NONE, 51, 8, 0, 0},
   225  	{AMOVV, C_ADDR, C_NONE, C_NONE, C_REG, C_NONE, 51, 8, 0, 0},
   226  	{AMOVB, C_ADDR, C_NONE, C_NONE, C_REG, C_NONE, 51, 8, 0, 0},
   227  	{AMOVBU, C_ADDR, C_NONE, C_NONE, C_REG, C_NONE, 51, 8, 0, 0},
   228  	{AMOVW, C_TLS_LE, C_NONE, C_NONE, C_REG, C_NONE, 54, 16, 0, 0},
   229  	{AMOVWU, C_TLS_LE, C_NONE, C_NONE, C_REG, C_NONE, 54, 16, 0, 0},
   230  	{AMOVV, C_TLS_LE, C_NONE, C_NONE, C_REG, C_NONE, 54, 16, 0, 0},
   231  	{AMOVB, C_TLS_LE, C_NONE, C_NONE, C_REG, C_NONE, 54, 16, 0, 0},
   232  	{AMOVBU, C_TLS_LE, C_NONE, C_NONE, C_REG, C_NONE, 54, 16, 0, 0},
   233  
   234  	{AMOVW, C_SACON, C_NONE, C_NONE, C_REG, C_NONE, 3, 4, REGSP, 0},
   235  	{AMOVV, C_SACON, C_NONE, C_NONE, C_REG, C_NONE, 3, 4, REGSP, 0},
   236  	{AMOVW, C_EXTADDR, C_NONE, C_NONE, C_REG, C_NONE, 52, 8, 0, NOTUSETMP},
   237  	{AMOVV, C_EXTADDR, C_NONE, C_NONE, C_REG, C_NONE, 52, 8, 0, NOTUSETMP},
   238  
   239  	{AMOVW, C_LACON, C_NONE, C_NONE, C_REG, C_NONE, 27, 12, REGSP, 0},
   240  	{AMOVV, C_LACON, C_NONE, C_NONE, C_REG, C_NONE, 27, 12, REGSP, 0},
   241  	{AMOVW, C_12CON, C_NONE, C_NONE, C_REG, C_NONE, 3, 4, REGZERO, 0},
   242  	{AMOVV, C_12CON, C_NONE, C_NONE, C_REG, C_NONE, 3, 4, REGZERO, 0},
   243  
   244  	{AMOVW, C_32CON20_0, C_NONE, C_NONE, C_REG, C_NONE, 25, 4, 0, 0},
   245  	{AMOVV, C_32CON20_0, C_NONE, C_NONE, C_REG, C_NONE, 25, 4, 0, 0},
   246  	{AMOVW, C_32CON, C_NONE, C_NONE, C_REG, C_NONE, 19, 8, 0, NOTUSETMP},
   247  	{AMOVV, C_32CON, C_NONE, C_NONE, C_REG, C_NONE, 19, 8, 0, NOTUSETMP},
   248  	{AMOVV, C_DCON12_0, C_NONE, C_NONE, C_REG, C_NONE, 67, 4, 0, NOTUSETMP},
   249  	{AMOVV, C_DCON12_20S, C_NONE, C_NONE, C_REG, C_NONE, 68, 8, 0, NOTUSETMP},
   250  	{AMOVV, C_DCON32_12S, C_NONE, C_NONE, C_REG, C_NONE, 69, 12, 0, NOTUSETMP},
   251  	{AMOVV, C_DCON, C_NONE, C_NONE, C_REG, C_NONE, 59, 16, 0, NOTUSETMP},
   252  
   253  	{AADD, C_US12CON, C_REG, C_NONE, C_REG, C_NONE, 4, 4, 0, 0},
   254  	{AADD, C_US12CON, C_NONE, C_NONE, C_REG, C_NONE, 4, 4, 0, 0},
   255  	{AADD, C_U12CON, C_REG, C_NONE, C_REG, C_NONE, 10, 8, 0, 0},
   256  	{AADD, C_U12CON, C_NONE, C_NONE, C_REG, C_NONE, 10, 8, 0, 0},
   257  
   258  	{AADDV, C_US12CON, C_REG, C_NONE, C_REG, C_NONE, 4, 4, 0, 0},
   259  	{AADDV, C_US12CON, C_NONE, C_NONE, C_REG, C_NONE, 4, 4, 0, 0},
   260  	{AADDV, C_U12CON, C_REG, C_NONE, C_REG, C_NONE, 10, 8, 0, 0},
   261  	{AADDV, C_U12CON, C_NONE, C_NONE, C_REG, C_NONE, 10, 8, 0, 0},
   262  
   263  	{AAND, C_UU12CON, C_REG, C_NONE, C_REG, C_NONE, 4, 4, 0, 0},
   264  	{AAND, C_UU12CON, C_NONE, C_NONE, C_REG, C_NONE, 4, 4, 0, 0},
   265  	{AAND, C_S12CON, C_REG, C_NONE, C_REG, C_NONE, 10, 8, 0, 0},
   266  	{AAND, C_S12CON, C_NONE, C_NONE, C_REG, C_NONE, 10, 8, 0, 0},
   267  
   268  	{AADD, C_32CON20_0, C_REG, C_NONE, C_REG, C_NONE, 26, 8, 0, 0},
   269  	{AADD, C_32CON20_0, C_NONE, C_NONE, C_REG, C_NONE, 26, 8, 0, 0},
   270  	{AADDV, C_32CON20_0, C_REG, C_NONE, C_REG, C_NONE, 26, 8, 0, 0},
   271  	{AADDV, C_32CON20_0, C_NONE, C_NONE, C_REG, C_NONE, 26, 8, 0, 0},
   272  	{AAND, C_32CON20_0, C_REG, C_NONE, C_REG, C_NONE, 26, 8, 0, 0},
   273  	{AAND, C_32CON20_0, C_NONE, C_NONE, C_REG, C_NONE, 26, 8, 0, 0},
   274  
   275  	{AADD, C_32CON, C_NONE, C_NONE, C_REG, C_NONE, 24, 12, 0, 0},
   276  	{AADDV, C_32CON, C_NONE, C_NONE, C_REG, C_NONE, 24, 12, 0, 0},
   277  	{AAND, C_32CON, C_NONE, C_NONE, C_REG, C_NONE, 24, 12, 0, 0},
   278  	{AADD, C_32CON, C_REG, C_NONE, C_REG, C_NONE, 24, 12, 0, 0},
   279  	{AADDV, C_32CON, C_REG, C_NONE, C_REG, C_NONE, 24, 12, 0, 0},
   280  	{AAND, C_32CON, C_REG, C_NONE, C_REG, C_NONE, 24, 12, 0, 0},
   281  
   282  	{AADDV, C_DCON, C_NONE, C_NONE, C_REG, C_NONE, 60, 20, 0, 0},
   283  	{AADDV, C_DCON, C_REG, C_NONE, C_REG, C_NONE, 60, 20, 0, 0},
   284  	{AAND, C_DCON, C_NONE, C_NONE, C_REG, C_NONE, 60, 20, 0, 0},
   285  	{AAND, C_DCON, C_REG, C_NONE, C_REG, C_NONE, 60, 20, 0, 0},
   286  	{AADDV, C_DCON12_0, C_NONE, C_NONE, C_REG, C_NONE, 70, 8, 0, 0},
   287  	{AADDV, C_DCON12_0, C_REG, C_NONE, C_REG, C_NONE, 70, 8, 0, 0},
   288  	{AAND, C_DCON12_0, C_NONE, C_NONE, C_REG, C_NONE, 70, 8, 0, 0},
   289  	{AAND, C_DCON12_0, C_REG, C_NONE, C_REG, C_NONE, 70, 8, 0, 0},
   290  	{AADDV, C_DCON12_20S, C_NONE, C_NONE, C_REG, C_NONE, 71, 12, 0, 0},
   291  	{AADDV, C_DCON12_20S, C_REG, C_NONE, C_REG, C_NONE, 71, 12, 0, 0},
   292  	{AAND, C_DCON12_20S, C_NONE, C_NONE, C_REG, C_NONE, 71, 12, 0, 0},
   293  	{AAND, C_DCON12_20S, C_REG, C_NONE, C_REG, C_NONE, 71, 12, 0, 0},
   294  	{AADDV, C_DCON32_12S, C_NONE, C_NONE, C_REG, C_NONE, 72, 16, 0, 0},
   295  	{AADDV, C_DCON32_12S, C_REG, C_NONE, C_REG, C_NONE, 72, 16, 0, 0},
   296  	{AAND, C_DCON32_12S, C_NONE, C_NONE, C_REG, C_NONE, 72, 16, 0, 0},
   297  	{AAND, C_DCON32_12S, C_REG, C_NONE, C_REG, C_NONE, 72, 16, 0, 0},
   298  
   299  	{ASLL, C_U5CON, C_REG, C_NONE, C_REG, C_NONE, 16, 4, 0, 0},
   300  	{ASLL, C_U5CON, C_NONE, C_NONE, C_REG, C_NONE, 16, 4, 0, 0},
   301  
   302  	{ASLLV, C_U6CON, C_REG, C_NONE, C_REG, C_NONE, 16, 4, 0, 0},
   303  	{ASLLV, C_U6CON, C_NONE, C_NONE, C_REG, C_NONE, 16, 4, 0, 0},
   304  
   305  	{ABSTRPICKW, C_U6CON, C_REG, C_U6CON, C_REG, C_NONE, 17, 4, 0, 0},
   306  	{ABSTRPICKW, C_U6CON, C_REG, C_ZCON, C_REG, C_NONE, 17, 4, 0, 0},
   307  	{ABSTRPICKW, C_ZCON, C_REG, C_ZCON, C_REG, C_NONE, 17, 4, 0, 0},
   308  
   309  	{ASYSCALL, C_NONE, C_NONE, C_NONE, C_NONE, C_NONE, 5, 4, 0, 0},
   310  	{ASYSCALL, C_U15CON, C_NONE, C_NONE, C_NONE, C_NONE, 5, 4, 0, 0},
   311  
   312  	{ABEQ, C_REG, C_REG, C_NONE, C_BRAN, C_NONE, 6, 4, 0, 0},
   313  	{ABEQ, C_REG, C_NONE, C_NONE, C_BRAN, C_NONE, 6, 4, 0, 0},
   314  	{ABLEZ, C_REG, C_NONE, C_NONE, C_BRAN, C_NONE, 6, 4, 0, 0},
   315  	{ABFPT, C_NONE, C_NONE, C_NONE, C_BRAN, C_NONE, 6, 4, 0, 0},
   316  	{ABFPT, C_FCCREG, C_NONE, C_NONE, C_BRAN, C_NONE, 6, 4, 0, 0},
   317  
   318  	{AJMP, C_NONE, C_NONE, C_NONE, C_BRAN, C_NONE, 11, 4, 0, 0}, // b
   319  	{AJAL, C_NONE, C_NONE, C_NONE, C_BRAN, C_NONE, 11, 4, 0, 0}, // bl
   320  
   321  	{AJMP, C_NONE, C_NONE, C_NONE, C_ZOREG, C_NONE, 18, 4, REGZERO, 0}, // jirl r0, rj, 0
   322  	{AJAL, C_NONE, C_NONE, C_NONE, C_ZOREG, C_NONE, 18, 4, REGLINK, 0}, // jirl r1, rj, 0
   323  
   324  	{AMOVF, C_SAUTO, C_NONE, C_NONE, C_FREG, C_NONE, 28, 4, REGSP, 0},
   325  	{AMOVD, C_SAUTO, C_NONE, C_NONE, C_FREG, C_NONE, 28, 4, REGSP, 0},
   326  	{AMOVF, C_SOREG, C_NONE, C_NONE, C_FREG, C_NONE, 28, 4, REGZERO, 0},
   327  	{AMOVD, C_SOREG, C_NONE, C_NONE, C_FREG, C_NONE, 28, 4, REGZERO, 0},
   328  
   329  	{AMOVF, C_LAUTO, C_NONE, C_NONE, C_FREG, C_NONE, 28, 12, REGSP, 0},
   330  	{AMOVD, C_LAUTO, C_NONE, C_NONE, C_FREG, C_NONE, 28, 12, REGSP, 0},
   331  	{AMOVF, C_LOREG, C_NONE, C_NONE, C_FREG, C_NONE, 28, 12, REGZERO, 0},
   332  	{AMOVD, C_LOREG, C_NONE, C_NONE, C_FREG, C_NONE, 28, 12, REGZERO, 0},
   333  	{AMOVF, C_ADDR, C_NONE, C_NONE, C_FREG, C_NONE, 51, 8, 0, 0},
   334  	{AMOVD, C_ADDR, C_NONE, C_NONE, C_FREG, C_NONE, 51, 8, 0, 0},
   335  
   336  	{AMOVF, C_FREG, C_NONE, C_NONE, C_SAUTO, C_NONE, 29, 4, REGSP, 0},
   337  	{AMOVD, C_FREG, C_NONE, C_NONE, C_SAUTO, C_NONE, 29, 4, REGSP, 0},
   338  	{AMOVF, C_FREG, C_NONE, C_NONE, C_SOREG, C_NONE, 29, 4, REGZERO, 0},
   339  	{AMOVD, C_FREG, C_NONE, C_NONE, C_SOREG, C_NONE, 29, 4, REGZERO, 0},
   340  
   341  	{AMOVF, C_FREG, C_NONE, C_NONE, C_LAUTO, C_NONE, 29, 12, REGSP, 0},
   342  	{AMOVD, C_FREG, C_NONE, C_NONE, C_LAUTO, C_NONE, 29, 12, REGSP, 0},
   343  	{AMOVF, C_FREG, C_NONE, C_NONE, C_LOREG, C_NONE, 29, 12, REGZERO, 0},
   344  	{AMOVD, C_FREG, C_NONE, C_NONE, C_LOREG, C_NONE, 29, 12, REGZERO, 0},
   345  	{AMOVF, C_FREG, C_NONE, C_NONE, C_ADDR, C_NONE, 50, 8, 0, 0},
   346  	{AMOVD, C_FREG, C_NONE, C_NONE, C_ADDR, C_NONE, 50, 8, 0, 0},
   347  
   348  	{AMOVW, C_REG, C_NONE, C_NONE, C_FREG, C_NONE, 30, 4, 0, 0},
   349  	{AMOVV, C_REG, C_NONE, C_NONE, C_FREG, C_NONE, 30, 4, 0, 0},
   350  	{AMOVW, C_FREG, C_NONE, C_NONE, C_REG, C_NONE, 30, 4, 0, 0},
   351  	{AMOVV, C_FREG, C_NONE, C_NONE, C_REG, C_NONE, 30, 4, 0, 0},
   352  	{AMOVV, C_FCCREG, C_NONE, C_NONE, C_REG, C_NONE, 30, 4, 0, 0},
   353  	{AMOVV, C_FCSRREG, C_NONE, C_NONE, C_REG, C_NONE, 30, 4, 0, 0},
   354  	{AMOVV, C_REG, C_NONE, C_NONE, C_FCCREG, C_NONE, 30, 4, 0, 0},
   355  	{AMOVV, C_REG, C_NONE, C_NONE, C_FCSRREG, C_NONE, 30, 4, 0, 0},
   356  	{AMOVV, C_FREG, C_NONE, C_NONE, C_FCCREG, C_NONE, 30, 4, 0, 0},
   357  	{AMOVV, C_FCCREG, C_NONE, C_NONE, C_FREG, C_NONE, 30, 4, 0, 0},
   358  
   359  	{AMOVW, C_12CON, C_NONE, C_NONE, C_FREG, C_NONE, 34, 8, 0, 0},
   360  
   361  	{AMOVB, C_REG, C_NONE, C_NONE, C_TLS_IE, C_NONE, 56, 16, 0, 0},
   362  	{AMOVW, C_REG, C_NONE, C_NONE, C_TLS_IE, C_NONE, 56, 16, 0, 0},
   363  	{AMOVV, C_REG, C_NONE, C_NONE, C_TLS_IE, C_NONE, 56, 16, 0, 0},
   364  	{AMOVBU, C_REG, C_NONE, C_NONE, C_TLS_IE, C_NONE, 56, 16, 0, 0},
   365  	{AMOVWU, C_REG, C_NONE, C_NONE, C_TLS_IE, C_NONE, 56, 16, 0, 0},
   366  
   367  	{AMOVB, C_TLS_IE, C_NONE, C_NONE, C_REG, C_NONE, 57, 16, 0, 0},
   368  	{AMOVW, C_TLS_IE, C_NONE, C_NONE, C_REG, C_NONE, 57, 16, 0, 0},
   369  	{AMOVV, C_TLS_IE, C_NONE, C_NONE, C_REG, C_NONE, 57, 16, 0, 0},
   370  	{AMOVBU, C_TLS_IE, C_NONE, C_NONE, C_REG, C_NONE, 57, 16, 0, 0},
   371  	{AMOVWU, C_TLS_IE, C_NONE, C_NONE, C_REG, C_NONE, 57, 16, 0, 0},
   372  
   373  	{AWORD, C_32CON, C_NONE, C_NONE, C_NONE, C_NONE, 38, 4, 0, 0},
   374  	{AWORD, C_DCON, C_NONE, C_NONE, C_NONE, C_NONE, 61, 4, 0, 0},
   375  
   376  	{AMOVV, C_GOTADDR, C_NONE, C_NONE, C_REG, C_NONE, 65, 8, 0, 0},
   377  
   378  	{ATEQ, C_US12CON, C_REG, C_NONE, C_REG, C_NONE, 15, 8, 0, 0},
   379  	{ATEQ, C_US12CON, C_NONE, C_NONE, C_REG, C_NONE, 15, 8, 0, 0},
   380  
   381  	{ARDTIMELW, C_NONE, C_NONE, C_NONE, C_REG, C_REG, 62, 4, 0, 0},
   382  	{AAMSWAPW, C_REG, C_NONE, C_NONE, C_ZOREG, C_REG, 66, 4, 0, 0},
   383  	{ANOOP, C_NONE, C_NONE, C_NONE, C_NONE, C_NONE, 49, 4, 0, 0},
   384  
   385  	/* store with extended register offset */
   386  	{AMOVB, C_REG, C_NONE, C_NONE, C_ROFF, C_NONE, 20, 4, 0, 0},
   387  	{AMOVW, C_REG, C_NONE, C_NONE, C_ROFF, C_NONE, 20, 4, 0, 0},
   388  	{AMOVV, C_REG, C_NONE, C_NONE, C_ROFF, C_NONE, 20, 4, 0, 0},
   389  	{AMOVF, C_FREG, C_NONE, C_NONE, C_ROFF, C_NONE, 20, 4, 0, 0},
   390  	{AMOVD, C_FREG, C_NONE, C_NONE, C_ROFF, C_NONE, 20, 4, 0, 0},
   391  	{AVMOVQ, C_VREG, C_NONE, C_NONE, C_ROFF, C_NONE, 20, 4, 0, 0},
   392  	{AXVMOVQ, C_XREG, C_NONE, C_NONE, C_ROFF, C_NONE, 20, 4, 0, 0},
   393  
   394  	/* load with extended register offset */
   395  	{AMOVB, C_ROFF, C_NONE, C_NONE, C_REG, C_NONE, 21, 4, 0, 0},
   396  	{AMOVBU, C_ROFF, C_NONE, C_NONE, C_REG, C_NONE, 21, 4, 0, 0},
   397  	{AMOVW, C_ROFF, C_NONE, C_NONE, C_REG, C_NONE, 21, 4, 0, 0},
   398  	{AMOVWU, C_ROFF, C_NONE, C_NONE, C_REG, C_NONE, 21, 4, 0, 0},
   399  	{AMOVV, C_ROFF, C_NONE, C_NONE, C_REG, C_NONE, 21, 4, 0, 0},
   400  	{AMOVF, C_ROFF, C_NONE, C_NONE, C_FREG, C_NONE, 21, 4, 0, 0},
   401  	{AMOVD, C_ROFF, C_NONE, C_NONE, C_FREG, C_NONE, 21, 4, 0, 0},
   402  	{AVMOVQ, C_ROFF, C_NONE, C_NONE, C_VREG, C_NONE, 21, 4, 0, 0},
   403  	{AXVMOVQ, C_ROFF, C_NONE, C_NONE, C_XREG, C_NONE, 21, 4, 0, 0},
   404  
   405  	{AVMOVQ, C_REG, C_NONE, C_NONE, C_ELEM, C_NONE, 39, 4, 0, 0},
   406  	{AVMOVQ, C_ELEM, C_NONE, C_NONE, C_REG, C_NONE, 40, 4, 0, 0},
   407  	{AXVMOVQ, C_REG, C_NONE, C_NONE, C_ELEM, C_NONE, 39, 4, 0, 0},
   408  	{AXVMOVQ, C_ELEM, C_NONE, C_NONE, C_REG, C_NONE, 40, 4, 0, 0},
   409  
   410  	{AXVMOVQ, C_XREG, C_NONE, C_NONE, C_ELEM, C_NONE, 43, 4, 0, 0},
   411  	{AXVMOVQ, C_ELEM, C_NONE, C_NONE, C_XREG, C_NONE, 44, 4, 0, 0},
   412  
   413  	{AVMOVQ, C_REG, C_NONE, C_NONE, C_ARNG, C_NONE, 41, 4, 0, 0},
   414  	{AXVMOVQ, C_REG, C_NONE, C_NONE, C_ARNG, C_NONE, 41, 4, 0, 0},
   415  	{AXVMOVQ, C_XREG, C_NONE, C_NONE, C_ARNG, C_NONE, 42, 4, 0, 0},
   416  
   417  	{AVMOVQ, C_ELEM, C_NONE, C_NONE, C_ARNG, C_NONE, 45, 4, 0, 0},
   418  
   419  	{APRELD, C_SOREG, C_U5CON, C_NONE, C_NONE, C_NONE, 46, 4, 0, 0},
   420  	{APRELDX, C_SOREG, C_DCON, C_U5CON, C_NONE, C_NONE, 47, 20, 0, 0},
   421  
   422  	{obj.APCALIGN, C_U12CON, C_NONE, C_NONE, C_NONE, C_NONE, 0, 0, 0, 0},
   423  	{obj.APCDATA, C_32CON, C_NONE, C_NONE, C_32CON, C_NONE, 0, 0, 0, 0},
   424  	{obj.APCDATA, C_DCON, C_NONE, C_NONE, C_DCON, C_NONE, 0, 0, 0, 0},
   425  	{obj.AFUNCDATA, C_U12CON, C_NONE, C_NONE, C_ADDR, C_NONE, 0, 0, 0, 0},
   426  	{obj.ANOP, C_NONE, C_NONE, C_NONE, C_NONE, C_NONE, 0, 0, 0, 0},
   427  	{obj.ANOP, C_32CON, C_NONE, C_NONE, C_NONE, C_NONE, 0, 0, 0, 0}, // nop variants, see #40689
   428  	{obj.ANOP, C_DCON, C_NONE, C_NONE, C_NONE, C_NONE, 0, 0, 0, 0},  // nop variants, see #40689
   429  	{obj.ANOP, C_REG, C_NONE, C_NONE, C_NONE, C_NONE, 0, 0, 0, 0},
   430  	{obj.ANOP, C_FREG, C_NONE, C_NONE, C_NONE, C_NONE, 0, 0, 0, 0},
   431  	{obj.ADUFFZERO, C_NONE, C_NONE, C_NONE, C_BRAN, C_NONE, 11, 4, 0, 0}, // same as AJMP
   432  	{obj.ADUFFCOPY, C_NONE, C_NONE, C_NONE, C_BRAN, C_NONE, 11, 4, 0, 0}, // same as AJMP
   433  
   434  	{obj.AXXX, C_NONE, C_NONE, C_NONE, C_NONE, C_NONE, 0, 4, 0, 0},
   435  }
   436  
   437  var atomicInst = map[obj.As]uint32{
   438  	AAMSWAPB:   0x070B8 << 15, // amswap.b
   439  	AAMSWAPH:   0x070B9 << 15, // amswap.h
   440  	AAMSWAPW:   0x070C0 << 15, // amswap.w
   441  	AAMSWAPV:   0x070C1 << 15, // amswap.d
   442  	AAMCASB:    0x070B0 << 15, // amcas.b
   443  	AAMCASH:    0x070B1 << 15, // amcas.h
   444  	AAMCASW:    0x070B2 << 15, // amcas.w
   445  	AAMCASV:    0x070B3 << 15, // amcas.d
   446  	AAMADDW:    0x070C2 << 15, // amadd.w
   447  	AAMADDV:    0x070C3 << 15, // amadd.d
   448  	AAMANDW:    0x070C4 << 15, // amand.w
   449  	AAMANDV:    0x070C5 << 15, // amand.d
   450  	AAMORW:     0x070C6 << 15, // amor.w
   451  	AAMORV:     0x070C7 << 15, // amor.d
   452  	AAMXORW:    0x070C8 << 15, // amxor.w
   453  	AAMXORV:    0x070C9 << 15, // amxor.d
   454  	AAMMAXW:    0x070CA << 15, // ammax.w
   455  	AAMMAXV:    0x070CB << 15, // ammax.d
   456  	AAMMINW:    0x070CC << 15, // ammin.w
   457  	AAMMINV:    0x070CD << 15, // ammin.d
   458  	AAMMAXWU:   0x070CE << 15, // ammax.wu
   459  	AAMMAXVU:   0x070CF << 15, // ammax.du
   460  	AAMMINWU:   0x070D0 << 15, // ammin.wu
   461  	AAMMINVU:   0x070D1 << 15, // ammin.du
   462  	AAMSWAPDBB: 0x070BC << 15, // amswap_db.b
   463  	AAMSWAPDBH: 0x070BD << 15, // amswap_db.h
   464  	AAMSWAPDBW: 0x070D2 << 15, // amswap_db.w
   465  	AAMSWAPDBV: 0x070D3 << 15, // amswap_db.d
   466  	AAMCASDBB:  0x070B4 << 15, // amcas_db.b
   467  	AAMCASDBH:  0x070B5 << 15, // amcas_db.h
   468  	AAMCASDBW:  0x070B6 << 15, // amcas_db.w
   469  	AAMCASDBV:  0x070B7 << 15, // amcas_db.d
   470  	AAMADDDBW:  0x070D4 << 15, // amadd_db.w
   471  	AAMADDDBV:  0x070D5 << 15, // amadd_db.d
   472  	AAMANDDBW:  0x070D6 << 15, // amand_db.w
   473  	AAMANDDBV:  0x070D7 << 15, // amand_db.d
   474  	AAMORDBW:   0x070D8 << 15, // amor_db.w
   475  	AAMORDBV:   0x070D9 << 15, // amor_db.d
   476  	AAMXORDBW:  0x070DA << 15, // amxor_db.w
   477  	AAMXORDBV:  0x070DB << 15, // amxor_db.d
   478  	AAMMAXDBW:  0x070DC << 15, // ammax_db.w
   479  	AAMMAXDBV:  0x070DD << 15, // ammax_db.d
   480  	AAMMINDBW:  0x070DE << 15, // ammin_db.w
   481  	AAMMINDBV:  0x070DF << 15, // ammin_db.d
   482  	AAMMAXDBWU: 0x070E0 << 15, // ammax_db.wu
   483  	AAMMAXDBVU: 0x070E1 << 15, // ammax_db.du
   484  	AAMMINDBWU: 0x070E2 << 15, // ammin_db.wu
   485  	AAMMINDBVU: 0x070E3 << 15, // ammin_db.du
   486  }
   487  
   488  func IsAtomicInst(as obj.As) bool {
   489  	_, ok := atomicInst[as]
   490  
   491  	return ok
   492  }
   493  
   494  // pcAlignPadLength returns the number of bytes required to align pc to alignedValue,
   495  // reporting an error if alignedValue is not a power of two or is out of range.
   496  func pcAlignPadLength(ctxt *obj.Link, pc int64, alignedValue int64) int {
   497  	if !((alignedValue&(alignedValue-1) == 0) && 8 <= alignedValue && alignedValue <= 2048) {
   498  		ctxt.Diag("alignment value of an instruction must be a power of two and in the range [8, 2048], got %d\n", alignedValue)
   499  	}
   500  	return int(-pc & (alignedValue - 1))
   501  }
   502  
   503  var oprange [ALAST & obj.AMask][]Optab
   504  
   505  var xcmp [C_NCLASS][C_NCLASS]bool
   506  
   507  func span0(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
   508  	if ctxt.Retpoline {
   509  		ctxt.Diag("-spectre=ret not supported on loong64")
   510  		ctxt.Retpoline = false // don't keep printing
   511  	}
   512  
   513  	p := cursym.Func().Text
   514  	if p == nil || p.Link == nil { // handle external functions and ELF section symbols
   515  		return
   516  	}
   517  
   518  	c := ctxt0{ctxt: ctxt, newprog: newprog, cursym: cursym, autosize: int32(p.To.Offset + ctxt.Arch.FixedFrameSize)}
   519  
   520  	if oprange[AOR&obj.AMask] == nil {
   521  		c.ctxt.Diag("loong64 ops not initialized, call loong64.buildop first")
   522  	}
   523  
   524  	pc := int64(0)
   525  	p.Pc = pc
   526  
   527  	var m int
   528  	var o *Optab
   529  	for p = p.Link; p != nil; p = p.Link {
   530  		p.Pc = pc
   531  		o = c.oplook(p)
   532  		m = int(o.size)
   533  		if m == 0 {
   534  			switch p.As {
   535  			case obj.APCALIGN:
   536  				alignedValue := p.From.Offset
   537  				m = pcAlignPadLength(ctxt, pc, alignedValue)
   538  				// Update the current text symbol alignment value.
   539  				if int32(alignedValue) > cursym.Func().Align {
   540  					cursym.Func().Align = int32(alignedValue)
   541  				}
   542  				break
   543  			case obj.ANOP, obj.AFUNCDATA, obj.APCDATA:
   544  				continue
   545  			default:
   546  				c.ctxt.Diag("zero-width instruction\n%v", p)
   547  			}
   548  		}
   549  
   550  		pc += int64(m)
   551  	}
   552  
   553  	c.cursym.Size = pc
   554  
   555  	// mark loop entry instructions for padding
   556  	// loop entrances are defined as targets of backward branches
   557  	for p = c.cursym.Func().Text.Link; p != nil; p = p.Link {
   558  		if q := p.To.Target(); q != nil && q.Pc < p.Pc {
   559  			q.Mark |= branchLoopHead
   560  		}
   561  	}
   562  
   563  	// Run these passes until convergence.
   564  	for {
   565  		rescan := false
   566  		pc = 0
   567  		prev := c.cursym.Func().Text
   568  		for p = prev.Link; p != nil; prev, p = p, p.Link {
   569  			p.Pc = pc
   570  			o = c.oplook(p)
   571  
   572  			// Prepend a PCALIGN $loopAlign to each of the loop heads
   573  			// that need padding, if not already done so (because this
   574  			// pass may execute more than once).
   575  			//
   576  			// This needs to come before any pass that look at pc,
   577  			// because pc will be adjusted if padding happens.
   578  			if p.Mark&branchLoopHead != 0 && pc&(loopAlign-1) != 0 &&
   579  				!(prev.As == obj.APCALIGN && prev.From.Offset >= loopAlign) {
   580  				q := c.newprog()
   581  				prev.Link = q
   582  				q.Link = p
   583  				q.Pc = pc
   584  				q.As = obj.APCALIGN
   585  				q.From.Type = obj.TYPE_CONST
   586  				q.From.Offset = loopAlign
   587  				// Don't associate the synthesized PCALIGN with
   588  				// the original source position, for deterministic
   589  				// mapping between source and corresponding asm.
   590  				// q.Pos = p.Pos
   591  
   592  				// Manually make the PCALIGN come into effect,
   593  				// since this loop iteration is for p.
   594  				pc += int64(pcAlignPadLength(ctxt, pc, loopAlign))
   595  				p.Pc = pc
   596  				rescan = true
   597  			}
   598  
   599  			// very large conditional branches
   600  			//
   601  			// if any procedure is large enough to generate a large SBRA branch, then
   602  			// generate extra passes putting branches around jmps to fix. this is rare.
   603  			if o.type_ == 6 && p.To.Target() != nil {
   604  				otxt := p.To.Target().Pc - pc
   605  
   606  				// On loong64, the immediate value field of the conditional branch instructions
   607  				// BFPT and BFPT is 21 bits, and the others are 16 bits. The jump target address
   608  				// is to logically shift the immediate value in the instruction code to the left
   609  				// by 2 bits and then sign extend.
   610  				bound := int64(1 << (18 - 1))
   611  
   612  				switch p.As {
   613  				case ABFPT, ABFPF:
   614  					bound = int64(1 << (23 - 1))
   615  				}
   616  
   617  				if otxt < -bound || otxt >= bound {
   618  					q := c.newprog()
   619  					q.Link = p.Link
   620  					p.Link = q
   621  					q.As = AJMP
   622  					q.Pos = p.Pos
   623  					q.To.Type = obj.TYPE_BRANCH
   624  					q.To.SetTarget(p.To.Target())
   625  					p.To.SetTarget(q)
   626  					q = c.newprog()
   627  					q.Link = p.Link
   628  					p.Link = q
   629  					q.As = AJMP
   630  					q.Pos = p.Pos
   631  					q.To.Type = obj.TYPE_BRANCH
   632  					q.To.SetTarget(q.Link.Link)
   633  					rescan = true
   634  				}
   635  			}
   636  
   637  			m = int(o.size)
   638  			if m == 0 {
   639  				switch p.As {
   640  				case obj.APCALIGN:
   641  					alignedValue := p.From.Offset
   642  					m = pcAlignPadLength(ctxt, pc, alignedValue)
   643  					break
   644  				case obj.ANOP, obj.AFUNCDATA, obj.APCDATA:
   645  					continue
   646  				default:
   647  					c.ctxt.Diag("zero-width instruction\n%v", p)
   648  				}
   649  			}
   650  
   651  			pc += int64(m)
   652  		}
   653  
   654  		c.cursym.Size = pc
   655  
   656  		if !rescan {
   657  			break
   658  		}
   659  	}
   660  
   661  	pc += -pc & (FuncAlign - 1)
   662  	c.cursym.Size = pc
   663  
   664  	// lay out the code, emitting code and data relocations.
   665  
   666  	c.cursym.Grow(c.cursym.Size)
   667  
   668  	bp := c.cursym.P
   669  	var i int32
   670  	var out [5]uint32
   671  	for p := c.cursym.Func().Text.Link; p != nil; p = p.Link {
   672  		c.pc = p.Pc
   673  		o = c.oplook(p)
   674  		if int(o.size) > 4*len(out) {
   675  			log.Fatalf("out array in span0 is too small, need at least %d for %v", o.size/4, p)
   676  		}
   677  		if p.As == obj.APCALIGN {
   678  			alignedValue := p.From.Offset
   679  			v := pcAlignPadLength(c.ctxt, p.Pc, alignedValue)
   680  			for i = 0; i < int32(v/4); i++ {
   681  				// emit ANOOP instruction by the padding size
   682  				c.ctxt.Arch.ByteOrder.PutUint32(bp, OP_12IRR(c.opirr(AAND), 0, 0, 0))
   683  				bp = bp[4:]
   684  			}
   685  			continue
   686  		}
   687  		c.asmout(p, o, out[:])
   688  		for i = 0; i < int32(o.size/4); i++ {
   689  			c.ctxt.Arch.ByteOrder.PutUint32(bp, out[i])
   690  			bp = bp[4:]
   691  		}
   692  	}
   693  
   694  	// Mark nonpreemptible instruction sequences.
   695  	// We use REGTMP as a scratch register during call injection,
   696  	// so instruction sequences that use REGTMP are unsafe to
   697  	// preempt asynchronously.
   698  	obj.MarkUnsafePoints(c.ctxt, c.cursym.Func().Text, c.newprog, c.isUnsafePoint, c.isRestartable)
   699  }
   700  
   701  // isUnsafePoint returns whether p is an unsafe point.
   702  func (c *ctxt0) isUnsafePoint(p *obj.Prog) bool {
   703  	// If p explicitly uses REGTMP, it's unsafe to preempt, because the
   704  	// preemption sequence clobbers REGTMP.
   705  	return p.From.Reg == REGTMP || p.To.Reg == REGTMP || p.Reg == REGTMP
   706  }
   707  
   708  // isRestartable returns whether p is a multi-instruction sequence that,
   709  // if preempted, can be restarted.
   710  func (c *ctxt0) isRestartable(p *obj.Prog) bool {
   711  	if c.isUnsafePoint(p) {
   712  		return false
   713  	}
   714  	// If p is a multi-instruction sequence with uses REGTMP inserted by
   715  	// the assembler in order to materialize a large constant/offset, we
   716  	// can restart p (at the start of the instruction sequence), recompute
   717  	// the content of REGTMP, upon async preemption. Currently, all cases
   718  	// of assembler-inserted REGTMP fall into this category.
   719  	// If p doesn't use REGTMP, it can be simply preempted, so we don't
   720  	// mark it.
   721  	o := c.oplook(p)
   722  	return o.size > 4 && o.flag&NOTUSETMP == 0
   723  }
   724  
   725  func isint32(v int64) bool {
   726  	return int64(int32(v)) == v
   727  }
   728  
   729  func isuint32(v uint64) bool {
   730  	return uint64(uint32(v)) == v
   731  }
   732  
   733  func (c *ctxt0) aclass(a *obj.Addr) int {
   734  	switch a.Type {
   735  	case obj.TYPE_NONE:
   736  		return C_NONE
   737  
   738  	case obj.TYPE_REG:
   739  		return c.rclass(a.Reg)
   740  
   741  	case obj.TYPE_MEM:
   742  		switch a.Name {
   743  		case obj.NAME_EXTERN,
   744  			obj.NAME_STATIC:
   745  			if a.Sym == nil {
   746  				break
   747  			}
   748  			c.instoffset = a.Offset
   749  			if a.Sym.Type == objabi.STLSBSS {
   750  				if c.ctxt.Flag_shared {
   751  					return C_TLS_IE
   752  				} else {
   753  					return C_TLS_LE
   754  				}
   755  			}
   756  			return C_ADDR
   757  
   758  		case obj.NAME_AUTO:
   759  			if a.Reg == REGSP {
   760  				// unset base register for better printing, since
   761  				// a.Offset is still relative to pseudo-SP.
   762  				a.Reg = obj.REG_NONE
   763  			}
   764  			c.instoffset = int64(c.autosize) + a.Offset
   765  			if c.instoffset >= -BIG && c.instoffset < BIG {
   766  				return C_SAUTO
   767  			}
   768  			return C_LAUTO
   769  
   770  		case obj.NAME_PARAM:
   771  			if a.Reg == REGSP {
   772  				// unset base register for better printing, since
   773  				// a.Offset is still relative to pseudo-FP.
   774  				a.Reg = obj.REG_NONE
   775  			}
   776  			c.instoffset = int64(c.autosize) + a.Offset + c.ctxt.Arch.FixedFrameSize
   777  			if c.instoffset >= -BIG && c.instoffset < BIG {
   778  				return C_SAUTO
   779  			}
   780  			return C_LAUTO
   781  
   782  		case obj.NAME_NONE:
   783  			if a.Index != 0 {
   784  				if a.Offset != 0 {
   785  					return C_GOK
   786  				}
   787  				// register offset
   788  				return C_ROFF
   789  			}
   790  
   791  			c.instoffset = a.Offset
   792  			if c.instoffset == 0 {
   793  				return C_ZOREG
   794  			}
   795  			if c.instoffset >= -BIG && c.instoffset < BIG {
   796  				return C_SOREG
   797  			}
   798  			return C_LOREG
   799  
   800  		case obj.NAME_GOTREF:
   801  			return C_GOTADDR
   802  		}
   803  
   804  		return C_GOK
   805  
   806  	case obj.TYPE_TEXTSIZE:
   807  		return C_TEXTSIZE
   808  
   809  	case obj.TYPE_CONST,
   810  		obj.TYPE_ADDR:
   811  		switch a.Name {
   812  		case obj.NAME_NONE:
   813  			c.instoffset = a.Offset
   814  			if a.Reg != 0 {
   815  				if -BIG <= c.instoffset && c.instoffset <= BIG {
   816  					return C_SACON
   817  				}
   818  				if isint32(c.instoffset) {
   819  					return C_LACON
   820  				}
   821  				return C_DACON
   822  			}
   823  
   824  		case obj.NAME_EXTERN,
   825  			obj.NAME_STATIC:
   826  			s := a.Sym
   827  			if s == nil {
   828  				return C_GOK
   829  			}
   830  
   831  			c.instoffset = a.Offset
   832  			if s.Type == objabi.STLSBSS {
   833  				c.ctxt.Diag("taking address of TLS variable is not supported")
   834  			}
   835  			return C_EXTADDR
   836  
   837  		case obj.NAME_AUTO:
   838  			if a.Reg == REGSP {
   839  				// unset base register for better printing, since
   840  				// a.Offset is still relative to pseudo-SP.
   841  				a.Reg = obj.REG_NONE
   842  			}
   843  			c.instoffset = int64(c.autosize) + a.Offset
   844  			if c.instoffset >= -BIG && c.instoffset < BIG {
   845  				return C_SACON
   846  			}
   847  			return C_LACON
   848  
   849  		case obj.NAME_PARAM:
   850  			if a.Reg == REGSP {
   851  				// unset base register for better printing, since
   852  				// a.Offset is still relative to pseudo-FP.
   853  				a.Reg = obj.REG_NONE
   854  			}
   855  			c.instoffset = int64(c.autosize) + a.Offset + c.ctxt.Arch.FixedFrameSize
   856  			if c.instoffset >= -BIG && c.instoffset < BIG {
   857  				return C_SACON
   858  			}
   859  			return C_LACON
   860  
   861  		default:
   862  			return C_GOK
   863  		}
   864  
   865  		if c.instoffset != int64(int32(c.instoffset)) {
   866  			return dconClass(c.instoffset)
   867  		}
   868  
   869  		if c.instoffset >= 0 {
   870  			sbits := bits.Len64(uint64(c.instoffset))
   871  			switch {
   872  			case sbits <= 8:
   873  				return C_ZCON + sbits
   874  			case sbits <= 12:
   875  				if c.instoffset <= 0x7ff {
   876  					return C_US12CON
   877  				}
   878  				return C_U12CON
   879  			case sbits <= 13:
   880  				if c.instoffset&0xfff == 0 {
   881  					return C_U13CON20_0
   882  				}
   883  				return C_U13CON
   884  			case sbits <= 15:
   885  				if c.instoffset&0xfff == 0 {
   886  					return C_U15CON20_0
   887  				}
   888  				return C_U15CON
   889  			}
   890  		} else {
   891  			sbits := bits.Len64(uint64(^c.instoffset))
   892  			switch {
   893  			case sbits < 5:
   894  				return C_S5CON
   895  			case sbits < 12:
   896  				return C_S12CON
   897  			case sbits < 13:
   898  				if c.instoffset&0xfff == 0 {
   899  					return C_S13CON20_0
   900  				}
   901  				return C_S13CON
   902  			}
   903  		}
   904  
   905  		if c.instoffset&0xfff == 0 {
   906  			return C_32CON20_0
   907  		}
   908  		return C_32CON
   909  
   910  	case obj.TYPE_BRANCH:
   911  		return C_BRAN
   912  	}
   913  
   914  	return C_GOK
   915  }
   916  
   917  // The constants here define the data characteristics within the bit field range.
   918  //
   919  //	ALL1: The data in the bit field is all 1
   920  //	ALL0: The data in the bit field is all 0
   921  //	ST1: The data in the bit field starts with 1, but not all 1
   922  //	ST0: The data in the bit field starts with 0, but not all 0
   923  const (
   924  	ALL1 = iota
   925  	ALL0
   926  	ST1
   927  	ST0
   928  )
   929  
   930  // mask returns the mask of the specified bit field, which is used to help determine
   931  // the data characteristics of the immediate value at the specified bit.
   932  func mask(suf int8, len int8) (uint64, uint64) {
   933  	if len == 12 {
   934  		if suf == 0 {
   935  			return 0xfff, 0x800
   936  		} else { // suf == 52
   937  			return 0xfff0000000000000, 0x8000000000000000
   938  		}
   939  	} else { // len == 20
   940  		if suf == 12 {
   941  			return 0xfffff000, 0x80000000
   942  		} else { // suf == 32
   943  			return 0xfffff00000000, 0x8000000000000
   944  		}
   945  	}
   946  }
   947  
   948  // bitField return a number represent status of val in bit field
   949  //
   950  //	suf: The starting bit of the bit field
   951  //	len: The length of the bit field
   952  func bitField(val int64, suf int8, len int8) int8 {
   953  	mask1, mask2 := mask(suf, len)
   954  	if uint64(val)&mask1 == mask1 {
   955  		return ALL1
   956  	} else if uint64(val)&mask1 == 0x0 {
   957  		return ALL0
   958  	} else if uint64(val)&mask2 == mask2 {
   959  		return ST1
   960  	} else {
   961  		return ST0
   962  	}
   963  }
   964  
   965  // Loading an immediate value larger than 32 bits requires four instructions
   966  // on loong64 (lu12i.w + ori + lu32i.d + lu52i.d), but in some special cases,
   967  // we can use the sign extension and zero extension features of the instruction
   968  // to fill in the high-order data (all 0 or all 1), which can save one to
   969  // three instructions.
   970  //
   971  //	| 63 ~ 52 | 51 ~ 32 | 31 ~ 12 | 11 ~ 0 |
   972  //	| lu52i.d | lu32i.d | lu12i.w |   ori  |
   973  func dconClass(offset int64) int {
   974  	tzb := bits.TrailingZeros64(uint64(offset))
   975  	hi12 := bitField(offset, 52, 12)
   976  	hi20 := bitField(offset, 32, 20)
   977  	lo20 := bitField(offset, 12, 20)
   978  	lo12 := bitField(offset, 0, 12)
   979  	if tzb >= 52 {
   980  		return C_DCON12_0 // lu52i.d
   981  	}
   982  	if tzb >= 32 {
   983  		if ((hi20 == ALL1 || hi20 == ST1) && hi12 == ALL1) || ((hi20 == ALL0 || hi20 == ST0) && hi12 == ALL0) {
   984  			return C_DCON20S_0 // addi.w + lu32i.d
   985  		}
   986  		return C_DCON32_0 // addi.w + lu32i.d + lu52i.d
   987  	}
   988  	if tzb >= 12 {
   989  		if lo20 == ST1 || lo20 == ALL1 {
   990  			if hi20 == ALL1 {
   991  				return C_DCON12_20S // lu12i.w + lu52i.d
   992  			}
   993  			if (hi20 == ST1 && hi12 == ALL1) || ((hi20 == ST0 || hi20 == ALL0) && hi12 == ALL0) {
   994  				return C_DCON20S_20 // lu12i.w + lu32i.d
   995  			}
   996  			return C_DCON32_20 // lu12i.w + lu32i.d + lu52i.d
   997  		}
   998  		if hi20 == ALL0 {
   999  			return C_DCON12_20S // lu12i.w + lu52i.d
  1000  		}
  1001  		if (hi20 == ST0 && hi12 == ALL0) || ((hi20 == ST1 || hi20 == ALL1) && hi12 == ALL1) {
  1002  			return C_DCON20S_20 // lu12i.w + lu32i.d
  1003  		}
  1004  		return C_DCON32_20 // lu12i.w + lu32i.d + lu52i.d
  1005  	}
  1006  	if lo12 == ST1 || lo12 == ALL1 {
  1007  		if lo20 == ALL1 {
  1008  			if hi20 == ALL1 {
  1009  				return C_DCON12_12S // addi.d + lu52i.d
  1010  			}
  1011  			if (hi20 == ST1 && hi12 == ALL1) || ((hi20 == ST0 || hi20 == ALL0) && hi12 == ALL0) {
  1012  				return C_DCON20S_12S // addi.w + lu32i.d
  1013  			}
  1014  			return C_DCON32_12S // addi.w + lu32i.d + lu52i.d
  1015  		}
  1016  		if lo20 == ST1 {
  1017  			if hi20 == ALL1 {
  1018  
  1019  				return C_DCON12_32S // lu12i.w + ori + lu52i.d
  1020  			}
  1021  			if (hi20 == ST1 && hi12 == ALL1) || ((hi20 == ST0 || hi20 == ALL0) && hi12 == ALL0) {
  1022  				return C_DCON20S_32 // lu12i.w + ori + lu32i.d
  1023  			}
  1024  			return C_DCON // lu12i.w + ori + lu32i.d + lu52i.d
  1025  		}
  1026  		if lo20 == ALL0 {
  1027  			if hi20 == ALL0 {
  1028  				return C_DCON12_12U // ori + lu52i.d
  1029  			}
  1030  			if ((hi20 == ST1 || hi20 == ALL1) && hi12 == ALL1) || (hi20 == ST0 && hi12 == ALL0) {
  1031  				return C_DCON20S_12U // ori + lu32i.d
  1032  			}
  1033  			return C_DCON32_12U // ori + lu32i.d + lu52i.d
  1034  		}
  1035  		if hi20 == ALL0 {
  1036  			return C_DCON12_32S // lu12i.w + ori + lu52i.d
  1037  		}
  1038  		if ((hi20 == ST1 || hi20 == ALL1) && hi12 == ALL1) || (hi20 == ST0 && hi12 == ALL0) {
  1039  			return C_DCON20S_32 // lu12i.w + ori + lu32i.d
  1040  		}
  1041  		return C_DCON // lu12i.w + ori + lu32i.d + lu52i.d
  1042  	}
  1043  	if lo20 == ALL0 {
  1044  		if hi20 == ALL0 {
  1045  			return C_DCON12_12U // ori + lu52i.d
  1046  		}
  1047  		if ((hi20 == ST1 || hi20 == ALL1) && hi12 == ALL1) || (hi20 == ST0 && hi12 == ALL0) {
  1048  			return C_DCON20S_12U // ori + lu32i.d
  1049  		}
  1050  		return C_DCON32_12U // ori + lu32i.d + lu52i.d
  1051  	}
  1052  	if lo20 == ST1 || lo20 == ALL1 {
  1053  		if hi20 == ALL1 {
  1054  			return C_DCON12_32S // lu12i.w + ori + lu52i.d
  1055  		}
  1056  		if (hi20 == ST1 && hi12 == ALL1) || ((hi20 == ST0 || hi20 == ALL0) && hi12 == ALL0) {
  1057  			return C_DCON20S_32 // lu12i.w + ori + lu32i.d
  1058  		}
  1059  		return C_DCON
  1060  	}
  1061  	if hi20 == ALL0 {
  1062  		return C_DCON12_32S // lu12i.w + ori + lu52i.d
  1063  	}
  1064  	if ((hi20 == ST1 || hi20 == ALL1) && hi12 == ALL1) || (hi20 == ST0 && hi12 == ALL0) {
  1065  		return C_DCON20S_32 // lu12i.w + ori + lu32i.d
  1066  	}
  1067  	return C_DCON
  1068  }
  1069  
  1070  // In Loong64,there are 8 CFRs, denoted as fcc0-fcc7.
  1071  // There are 4 FCSRs, denoted as fcsr0-fcsr3.
  1072  func (c *ctxt0) rclass(r int16) int {
  1073  	switch {
  1074  	case REG_R0 <= r && r <= REG_R31:
  1075  		return C_REG
  1076  	case REG_F0 <= r && r <= REG_F31:
  1077  		return C_FREG
  1078  	case REG_FCC0 <= r && r <= REG_FCC7:
  1079  		return C_FCCREG
  1080  	case REG_FCSR0 <= r && r <= REG_FCSR3:
  1081  		return C_FCSRREG
  1082  	case REG_V0 <= r && r <= REG_V31:
  1083  		return C_VREG
  1084  	case REG_X0 <= r && r <= REG_X31:
  1085  		return C_XREG
  1086  	case r >= REG_ARNG && r < REG_ELEM:
  1087  		return C_ARNG
  1088  	case r >= REG_ELEM && r < REG_ELEM_END:
  1089  		return C_ELEM
  1090  	}
  1091  
  1092  	return C_GOK
  1093  }
  1094  
  1095  func oclass(a *obj.Addr) int {
  1096  	return int(a.Class) - 1
  1097  }
  1098  
  1099  func prasm(p *obj.Prog) {
  1100  	fmt.Printf("%v\n", p)
  1101  }
  1102  
  1103  func (c *ctxt0) oplook(p *obj.Prog) *Optab {
  1104  	if oprange[AOR&obj.AMask] == nil {
  1105  		c.ctxt.Diag("loong64 ops not initialized, call loong64.buildop first")
  1106  	}
  1107  
  1108  	restArgsIndex := 0
  1109  	restArgsLen := len(p.RestArgs)
  1110  	if restArgsLen > 2 {
  1111  		c.ctxt.Diag("too many RestArgs: got %v, maximum is 2\n", restArgsLen)
  1112  		return nil
  1113  	}
  1114  
  1115  	restArgsv := [2]int{C_NONE + 1, C_NONE + 1}
  1116  	for i, ap := range p.RestArgs {
  1117  		restArgsv[i] = int(ap.Addr.Class)
  1118  		if restArgsv[i] == 0 {
  1119  			restArgsv[i] = c.aclass(&ap.Addr) + 1
  1120  			ap.Addr.Class = int8(restArgsv[i])
  1121  		}
  1122  	}
  1123  
  1124  	a1 := int(p.Optab)
  1125  	if a1 != 0 {
  1126  		return &optab[a1-1]
  1127  	}
  1128  
  1129  	// first source operand
  1130  	a1 = int(p.From.Class)
  1131  	if a1 == 0 {
  1132  		a1 = c.aclass(&p.From) + 1
  1133  		p.From.Class = int8(a1)
  1134  	}
  1135  	a1--
  1136  
  1137  	// first destination operand
  1138  	a4 := int(p.To.Class)
  1139  	if a4 == 0 {
  1140  		a4 = c.aclass(&p.To) + 1
  1141  		p.To.Class = int8(a4)
  1142  	}
  1143  	a4--
  1144  
  1145  	// 2nd source operand
  1146  	a2 := C_NONE
  1147  	if p.Reg != 0 {
  1148  		a2 = c.rclass(p.Reg)
  1149  	} else if restArgsLen > 0 {
  1150  		a2 = restArgsv[restArgsIndex] - 1
  1151  		restArgsIndex++
  1152  	}
  1153  
  1154  	// 2nd destination operand
  1155  	a5 := C_NONE
  1156  	if p.RegTo2 != 0 {
  1157  		a5 = C_REG
  1158  	}
  1159  
  1160  	// 3rd source operand
  1161  	a3 := C_NONE
  1162  	if restArgsLen > 0 && restArgsIndex < restArgsLen {
  1163  		a3 = restArgsv[restArgsIndex] - 1
  1164  		restArgsIndex++
  1165  	}
  1166  
  1167  	ops := oprange[p.As&obj.AMask]
  1168  	c1 := &xcmp[a1]
  1169  	c2 := &xcmp[a2]
  1170  	c3 := &xcmp[a3]
  1171  	c4 := &xcmp[a4]
  1172  	c5 := &xcmp[a5]
  1173  	for i := range ops {
  1174  		op := &ops[i]
  1175  		if c1[op.from1] && c2[op.reg] && c3[op.from3] && c4[op.to1] && c5[op.to2] {
  1176  			p.Optab = uint16(cap(optab) - cap(ops) + i + 1)
  1177  			return op
  1178  		}
  1179  	}
  1180  
  1181  	c.ctxt.Diag("illegal combination %v %v %v %v %v %v", p.As, DRconv(a1), DRconv(a2), DRconv(a3), DRconv(a4), DRconv(a5))
  1182  	prasm(p)
  1183  	// Turn illegal instruction into an UNDEF, avoid crashing in asmout.
  1184  	return &Optab{obj.AUNDEF, C_NONE, C_NONE, C_NONE, C_NONE, C_NONE, 49, 4, 0, 0}
  1185  }
  1186  
  1187  func cmp(a int, b int) bool {
  1188  	if a == b {
  1189  		return true
  1190  	}
  1191  	switch a {
  1192  	case C_DCON:
  1193  		return cmp(C_32CON, b) || cmp(C_DCON12_20S, b) || cmp(C_DCON32_12S, b) || b == C_DCON12_0
  1194  	case C_32CON:
  1195  		return cmp(C_32CON20_0, b) || cmp(C_U15CON, b) || cmp(C_13CON, b) || cmp(C_12CON, b)
  1196  	case C_32CON20_0:
  1197  		return b == C_U15CON20_0 || b == C_U13CON20_0 || b == C_S13CON20_0 || b == C_ZCON
  1198  	case C_U15CON:
  1199  		return cmp(C_U12CON, b) || b == C_U15CON20_0 || b == C_U13CON20_0 || b == C_U13CON
  1200  	case C_13CON:
  1201  		return cmp(C_U13CON, b) || cmp(C_S13CON, b)
  1202  	case C_U13CON:
  1203  		return cmp(C_12CON, b) || b == C_U13CON20_0
  1204  	case C_S13CON:
  1205  		return cmp(C_12CON, b) || b == C_S13CON20_0
  1206  	case C_12CON:
  1207  		return cmp(C_U12CON, b) || cmp(C_S12CON, b)
  1208  	case C_UU12CON:
  1209  		return cmp(C_U12CON, b)
  1210  	case C_U12CON:
  1211  		return cmp(C_U8CON, b) || b == C_US12CON
  1212  	case C_U8CON:
  1213  		return cmp(C_U7CON, b)
  1214  	case C_U7CON:
  1215  		return cmp(C_U6CON, b)
  1216  	case C_U6CON:
  1217  		return cmp(C_U5CON, b)
  1218  	case C_U5CON:
  1219  		return cmp(C_U4CON, b)
  1220  	case C_U4CON:
  1221  		return cmp(C_U3CON, b)
  1222  	case C_U3CON:
  1223  		return cmp(C_U2CON, b)
  1224  	case C_U2CON:
  1225  		return cmp(C_U1CON, b)
  1226  	case C_U1CON:
  1227  		return cmp(C_ZCON, b)
  1228  	case C_US12CON:
  1229  		return cmp(C_S12CON, b)
  1230  	case C_S12CON:
  1231  		return cmp(C_S5CON, b) || cmp(C_U8CON, b) || b == C_US12CON
  1232  	case C_S5CON:
  1233  		return cmp(C_ZCON, b) || cmp(C_U4CON, b)
  1234  
  1235  	case C_DCON12_20S:
  1236  		if b == C_DCON20S_20 || b == C_DCON12_12S ||
  1237  			b == C_DCON20S_12S || b == C_DCON12_12U ||
  1238  			b == C_DCON20S_12U || b == C_DCON20S_0 {
  1239  			return true
  1240  		}
  1241  
  1242  	case C_DCON32_12S:
  1243  		if b == C_DCON32_20 || b == C_DCON12_32S ||
  1244  			b == C_DCON20S_32 || b == C_DCON32_12U ||
  1245  			b == C_DCON32_0 {
  1246  			return true
  1247  		}
  1248  
  1249  	case C_LACON:
  1250  		return b == C_SACON
  1251  
  1252  	case C_LAUTO:
  1253  		return b == C_SAUTO
  1254  
  1255  	case C_REG:
  1256  		return b == C_ZCON
  1257  
  1258  	case C_LOREG:
  1259  		return b == C_ZOREG || b == C_SOREG
  1260  
  1261  	case C_SOREG:
  1262  		return b == C_ZOREG
  1263  	}
  1264  
  1265  	return false
  1266  }
  1267  
  1268  func ocmp(p1, p2 Optab) int {
  1269  	if p1.as != p2.as {
  1270  		return int(p1.as) - int(p2.as)
  1271  	}
  1272  	if p1.from1 != p2.from1 {
  1273  		return int(p1.from1) - int(p2.from1)
  1274  	}
  1275  	if p1.reg != p2.reg {
  1276  		return int(p1.reg) - int(p2.reg)
  1277  	}
  1278  	if p1.to1 != p2.to1 {
  1279  		return int(p1.to1) - int(p2.to1)
  1280  	}
  1281  	return 0
  1282  }
  1283  
  1284  func opset(a, b0 obj.As) {
  1285  	oprange[a&obj.AMask] = oprange[b0]
  1286  }
  1287  
  1288  func buildop(ctxt *obj.Link) {
  1289  	if ctxt.DiagFunc == nil {
  1290  		ctxt.DiagFunc = func(format string, args ...interface{}) {
  1291  			log.Printf(format, args...)
  1292  		}
  1293  	}
  1294  
  1295  	if oprange[AOR&obj.AMask] != nil {
  1296  		// Already initialized; stop now.
  1297  		// This happens in the cmd/asm tests,
  1298  		// each of which re-initializes the arch.
  1299  		return
  1300  	}
  1301  
  1302  	var n int
  1303  
  1304  	for i := 0; i < C_NCLASS; i++ {
  1305  		for n = 0; n < C_NCLASS; n++ {
  1306  			if cmp(n, i) {
  1307  				xcmp[i][n] = true
  1308  			}
  1309  		}
  1310  	}
  1311  	for n = 0; optab[n].as != obj.AXXX; n++ {
  1312  	}
  1313  	slices.SortFunc(optab[:n], ocmp)
  1314  	for i := 0; i < n; i++ {
  1315  		r := optab[i].as
  1316  		r0 := r & obj.AMask
  1317  		start := i
  1318  		for optab[i].as == r {
  1319  			i++
  1320  		}
  1321  		oprange[r0] = optab[start:i]
  1322  		i--
  1323  
  1324  		switch r {
  1325  		default:
  1326  			ctxt.Diag("unknown op in build: %v", r)
  1327  			ctxt.DiagFlush()
  1328  			log.Fatalf("bad code")
  1329  
  1330  		case AABSF:
  1331  			opset(AMOVFD, r0)
  1332  			opset(AMOVDF, r0)
  1333  			opset(AMOVWF, r0)
  1334  			opset(AMOVFW, r0)
  1335  			opset(AMOVWD, r0)
  1336  			opset(AMOVDW, r0)
  1337  			opset(ANEGF, r0)
  1338  			opset(ANEGD, r0)
  1339  			opset(AABSD, r0)
  1340  			opset(ATRUNCDW, r0)
  1341  			opset(ATRUNCFW, r0)
  1342  			opset(ASQRTF, r0)
  1343  			opset(ASQRTD, r0)
  1344  			opset(AFCLASSF, r0)
  1345  			opset(AFCLASSD, r0)
  1346  			opset(AFLOGBF, r0)
  1347  			opset(AFLOGBD, r0)
  1348  
  1349  		case AMOVVF:
  1350  			opset(AMOVVD, r0)
  1351  			opset(AMOVFV, r0)
  1352  			opset(AMOVDV, r0)
  1353  			opset(ATRUNCDV, r0)
  1354  			opset(ATRUNCFV, r0)
  1355  			opset(AFFINTFW, r0)
  1356  			opset(AFFINTFV, r0)
  1357  			opset(AFFINTDW, r0)
  1358  			opset(AFFINTDV, r0)
  1359  			opset(AFTINTWF, r0)
  1360  			opset(AFTINTWD, r0)
  1361  			opset(AFTINTVF, r0)
  1362  			opset(AFTINTVD, r0)
  1363  			opset(AFTINTRPWF, r0)
  1364  			opset(AFTINTRPWD, r0)
  1365  			opset(AFTINTRPVF, r0)
  1366  			opset(AFTINTRPVD, r0)
  1367  			opset(AFTINTRMWF, r0)
  1368  			opset(AFTINTRMWD, r0)
  1369  			opset(AFTINTRMVF, r0)
  1370  			opset(AFTINTRMVD, r0)
  1371  			opset(AFTINTRZWF, r0)
  1372  			opset(AFTINTRZWD, r0)
  1373  			opset(AFTINTRZVF, r0)
  1374  			opset(AFTINTRZVD, r0)
  1375  			opset(AFTINTRNEWF, r0)
  1376  			opset(AFTINTRNEWD, r0)
  1377  			opset(AFTINTRNEVF, r0)
  1378  			opset(AFTINTRNEVD, r0)
  1379  
  1380  		case AADD:
  1381  			opset(ASGT, r0)
  1382  			opset(ASGTU, r0)
  1383  			opset(AADDU, r0)
  1384  
  1385  		case AADDV:
  1386  			opset(AADDVU, r0)
  1387  
  1388  		case AADDF:
  1389  			opset(ADIVF, r0)
  1390  			opset(ADIVD, r0)
  1391  			opset(AMULF, r0)
  1392  			opset(AMULD, r0)
  1393  			opset(ASUBF, r0)
  1394  			opset(ASUBD, r0)
  1395  			opset(AADDD, r0)
  1396  			opset(AFMINF, r0)
  1397  			opset(AFMIND, r0)
  1398  			opset(AFMAXF, r0)
  1399  			opset(AFMAXD, r0)
  1400  			opset(AFCOPYSGF, r0)
  1401  			opset(AFCOPYSGD, r0)
  1402  			opset(AFSCALEBF, r0)
  1403  			opset(AFSCALEBD, r0)
  1404  			opset(AFMAXAF, r0)
  1405  			opset(AFMAXAD, r0)
  1406  			opset(AFMINAF, r0)
  1407  			opset(AFMINAD, r0)
  1408  
  1409  		case AFMADDF:
  1410  			opset(AFMADDD, r0)
  1411  			opset(AFMSUBF, r0)
  1412  			opset(AFMSUBD, r0)
  1413  			opset(AFNMADDF, r0)
  1414  			opset(AFNMADDD, r0)
  1415  			opset(AFNMSUBF, r0)
  1416  			opset(AFNMSUBD, r0)
  1417  
  1418  		case AAND:
  1419  			opset(AOR, r0)
  1420  			opset(AXOR, r0)
  1421  			opset(AORN, r0)
  1422  			opset(AANDN, r0)
  1423  
  1424  		case ABEQ:
  1425  			opset(ABNE, r0)
  1426  			opset(ABLT, r0)
  1427  			opset(ABGE, r0)
  1428  			opset(ABGEU, r0)
  1429  			opset(ABLTU, r0)
  1430  
  1431  		case ABLEZ:
  1432  			opset(ABGEZ, r0)
  1433  			opset(ABLTZ, r0)
  1434  			opset(ABGTZ, r0)
  1435  
  1436  		case AMOVB:
  1437  			opset(AMOVH, r0)
  1438  
  1439  		case AMOVBU:
  1440  			opset(AMOVHU, r0)
  1441  
  1442  		case AMUL:
  1443  			opset(AMULU, r0)
  1444  			opset(AMULH, r0)
  1445  			opset(AMULHU, r0)
  1446  			opset(AREM, r0)
  1447  			opset(AREMU, r0)
  1448  			opset(ADIV, r0)
  1449  			opset(ADIVU, r0)
  1450  
  1451  		case AMULV:
  1452  			opset(AMULVU, r0)
  1453  			opset(AMULHV, r0)
  1454  			opset(AMULHVU, r0)
  1455  			opset(AREMV, r0)
  1456  			opset(AREMVU, r0)
  1457  			opset(ADIVV, r0)
  1458  			opset(ADIVVU, r0)
  1459  
  1460  		case ASLL:
  1461  			opset(ASRL, r0)
  1462  			opset(ASRA, r0)
  1463  			opset(AROTR, r0)
  1464  
  1465  		case ASLLV:
  1466  			opset(ASRAV, r0)
  1467  			opset(ASRLV, r0)
  1468  			opset(AROTRV, r0)
  1469  
  1470  		case ABSTRPICKW:
  1471  			opset(ABSTRPICKV, r0)
  1472  			opset(ABSTRINSW, r0)
  1473  			opset(ABSTRINSV, r0)
  1474  
  1475  		case ASUB:
  1476  			opset(ASUBU, r0)
  1477  			opset(ANOR, r0)
  1478  
  1479  		case ASUBV:
  1480  			opset(ASUBVU, r0)
  1481  
  1482  		case ASYSCALL:
  1483  			opset(ADBAR, r0)
  1484  			opset(ABREAK, r0)
  1485  
  1486  		case ACMPEQF:
  1487  			opset(ACMPGTF, r0)
  1488  			opset(ACMPGTD, r0)
  1489  			opset(ACMPGEF, r0)
  1490  			opset(ACMPGED, r0)
  1491  			opset(ACMPEQD, r0)
  1492  
  1493  		case ABFPT:
  1494  			opset(ABFPF, r0)
  1495  
  1496  		case AMOVW,
  1497  			AMOVD,
  1498  			AMOVF,
  1499  			AMOVV,
  1500  			ARFE,
  1501  			AJAL,
  1502  			AJMP,
  1503  			AMOVWU,
  1504  			AVMOVQ,
  1505  			AXVMOVQ,
  1506  			ALL,
  1507  			ALLV,
  1508  			ASC,
  1509  			ASCV,
  1510  			ANEGW,
  1511  			ANEGV,
  1512  			AWORD,
  1513  			APRELD,
  1514  			APRELDX,
  1515  			obj.ANOP,
  1516  			obj.ATEXT,
  1517  			obj.AFUNCDATA,
  1518  			obj.APCALIGN,
  1519  			obj.APCDATA,
  1520  			obj.ADUFFZERO,
  1521  			obj.ADUFFCOPY:
  1522  			break
  1523  
  1524  		case ARDTIMELW:
  1525  			opset(ARDTIMEHW, r0)
  1526  			opset(ARDTIMED, r0)
  1527  
  1528  		case ACLOW:
  1529  			opset(ACLZW, r0)
  1530  			opset(ACTOW, r0)
  1531  			opset(ACTZW, r0)
  1532  			opset(ACLOV, r0)
  1533  			opset(ACLZV, r0)
  1534  			opset(ACTOV, r0)
  1535  			opset(ACTZV, r0)
  1536  			opset(AREVB2H, r0)
  1537  			opset(AREVB4H, r0)
  1538  			opset(AREVB2W, r0)
  1539  			opset(AREVBV, r0)
  1540  			opset(AREVH2W, r0)
  1541  			opset(AREVHV, r0)
  1542  			opset(ABITREV4B, r0)
  1543  			opset(ABITREV8B, r0)
  1544  			opset(ABITREVW, r0)
  1545  			opset(ABITREVV, r0)
  1546  			opset(AEXTWB, r0)
  1547  			opset(AEXTWH, r0)
  1548  			opset(ACPUCFG, r0)
  1549  
  1550  		case ATEQ:
  1551  			opset(ATNE, r0)
  1552  
  1553  		case AMASKEQZ:
  1554  			opset(AMASKNEZ, r0)
  1555  			opset(ACRCWBW, r0)
  1556  			opset(ACRCWHW, r0)
  1557  			opset(ACRCWWW, r0)
  1558  			opset(ACRCWVW, r0)
  1559  			opset(ACRCCWBW, r0)
  1560  			opset(ACRCCWHW, r0)
  1561  			opset(ACRCCWWW, r0)
  1562  			opset(ACRCCWVW, r0)
  1563  
  1564  		case ANOOP:
  1565  			opset(obj.AUNDEF, r0)
  1566  
  1567  		case AAMSWAPW:
  1568  			for i := range atomicInst {
  1569  				if i == AAMSWAPW {
  1570  					continue
  1571  				}
  1572  				opset(i, r0)
  1573  			}
  1574  
  1575  		case AVSEQB:
  1576  			opset(AVSEQH, r0)
  1577  			opset(AVSEQW, r0)
  1578  			opset(AVSEQV, r0)
  1579  			opset(AVILVLB, r0)
  1580  			opset(AVILVLH, r0)
  1581  			opset(AVILVLW, r0)
  1582  			opset(AVILVLV, r0)
  1583  			opset(AVILVHB, r0)
  1584  			opset(AVILVHH, r0)
  1585  			opset(AVILVHW, r0)
  1586  			opset(AVILVHV, r0)
  1587  			opset(AVMULB, r0)
  1588  			opset(AVMULH, r0)
  1589  			opset(AVMULW, r0)
  1590  			opset(AVMULV, r0)
  1591  			opset(AVMUHB, r0)
  1592  			opset(AVMUHH, r0)
  1593  			opset(AVMUHW, r0)
  1594  			opset(AVMUHV, r0)
  1595  			opset(AVMUHBU, r0)
  1596  			opset(AVMUHHU, r0)
  1597  			opset(AVMUHWU, r0)
  1598  			opset(AVMUHVU, r0)
  1599  			opset(AVDIVB, r0)
  1600  			opset(AVDIVH, r0)
  1601  			opset(AVDIVW, r0)
  1602  			opset(AVDIVV, r0)
  1603  			opset(AVMODB, r0)
  1604  			opset(AVMODH, r0)
  1605  			opset(AVMODW, r0)
  1606  			opset(AVMODV, r0)
  1607  			opset(AVDIVBU, r0)
  1608  			opset(AVDIVHU, r0)
  1609  			opset(AVDIVWU, r0)
  1610  			opset(AVDIVVU, r0)
  1611  			opset(AVMODBU, r0)
  1612  			opset(AVMODHU, r0)
  1613  			opset(AVMODWU, r0)
  1614  			opset(AVMODVU, r0)
  1615  			opset(AVMULWEVHB, r0)
  1616  			opset(AVMULWEVWH, r0)
  1617  			opset(AVMULWEVVW, r0)
  1618  			opset(AVMULWEVQV, r0)
  1619  			opset(AVMULWODHB, r0)
  1620  			opset(AVMULWODWH, r0)
  1621  			opset(AVMULWODVW, r0)
  1622  			opset(AVMULWODQV, r0)
  1623  			opset(AVMULWEVHBU, r0)
  1624  			opset(AVMULWEVWHU, r0)
  1625  			opset(AVMULWEVVWU, r0)
  1626  			opset(AVMULWEVQVU, r0)
  1627  			opset(AVMULWODHBU, r0)
  1628  			opset(AVMULWODWHU, r0)
  1629  			opset(AVMULWODVWU, r0)
  1630  			opset(AVMULWODQVU, r0)
  1631  			opset(AVMULWEVHBUB, r0)
  1632  			opset(AVMULWEVWHUH, r0)
  1633  			opset(AVMULWEVVWUW, r0)
  1634  			opset(AVMULWEVQVUV, r0)
  1635  			opset(AVMULWODHBUB, r0)
  1636  			opset(AVMULWODWHUH, r0)
  1637  			opset(AVMULWODVWUW, r0)
  1638  			opset(AVMULWODQVUV, r0)
  1639  			opset(AVADDF, r0)
  1640  			opset(AVADDD, r0)
  1641  			opset(AVSUBF, r0)
  1642  			opset(AVSUBD, r0)
  1643  			opset(AVMULF, r0)
  1644  			opset(AVMULD, r0)
  1645  			opset(AVDIVF, r0)
  1646  			opset(AVDIVD, r0)
  1647  
  1648  		case AXVSEQB:
  1649  			opset(AXVSEQH, r0)
  1650  			opset(AXVSEQW, r0)
  1651  			opset(AXVSEQV, r0)
  1652  			opset(AXVILVLB, r0)
  1653  			opset(AXVILVLH, r0)
  1654  			opset(AXVILVLW, r0)
  1655  			opset(AXVILVLV, r0)
  1656  			opset(AXVILVHB, r0)
  1657  			opset(AXVILVHH, r0)
  1658  			opset(AXVILVHW, r0)
  1659  			opset(AXVILVHV, r0)
  1660  			opset(AXVMULB, r0)
  1661  			opset(AXVMULH, r0)
  1662  			opset(AXVMULW, r0)
  1663  			opset(AXVMULV, r0)
  1664  			opset(AXVMUHB, r0)
  1665  			opset(AXVMUHH, r0)
  1666  			opset(AXVMUHW, r0)
  1667  			opset(AXVMUHV, r0)
  1668  			opset(AXVMUHBU, r0)
  1669  			opset(AXVMUHHU, r0)
  1670  			opset(AXVMUHWU, r0)
  1671  			opset(AXVMUHVU, r0)
  1672  			opset(AXVDIVB, r0)
  1673  			opset(AXVDIVH, r0)
  1674  			opset(AXVDIVW, r0)
  1675  			opset(AXVDIVV, r0)
  1676  			opset(AXVMODB, r0)
  1677  			opset(AXVMODH, r0)
  1678  			opset(AXVMODW, r0)
  1679  			opset(AXVMODV, r0)
  1680  			opset(AXVDIVBU, r0)
  1681  			opset(AXVDIVHU, r0)
  1682  			opset(AXVDIVWU, r0)
  1683  			opset(AXVDIVVU, r0)
  1684  			opset(AXVMODBU, r0)
  1685  			opset(AXVMODHU, r0)
  1686  			opset(AXVMODWU, r0)
  1687  			opset(AXVMODVU, r0)
  1688  			opset(AXVMULWEVHB, r0)
  1689  			opset(AXVMULWEVWH, r0)
  1690  			opset(AXVMULWEVVW, r0)
  1691  			opset(AXVMULWEVQV, r0)
  1692  			opset(AXVMULWODHB, r0)
  1693  			opset(AXVMULWODWH, r0)
  1694  			opset(AXVMULWODVW, r0)
  1695  			opset(AXVMULWODQV, r0)
  1696  			opset(AXVMULWEVHBU, r0)
  1697  			opset(AXVMULWEVWHU, r0)
  1698  			opset(AXVMULWEVVWU, r0)
  1699  			opset(AXVMULWEVQVU, r0)
  1700  			opset(AXVMULWODHBU, r0)
  1701  			opset(AXVMULWODWHU, r0)
  1702  			opset(AXVMULWODVWU, r0)
  1703  			opset(AXVMULWODQVU, r0)
  1704  			opset(AXVMULWEVHBUB, r0)
  1705  			opset(AXVMULWEVWHUH, r0)
  1706  			opset(AXVMULWEVVWUW, r0)
  1707  			opset(AXVMULWEVQVUV, r0)
  1708  			opset(AXVMULWODHBUB, r0)
  1709  			opset(AXVMULWODWHUH, r0)
  1710  			opset(AXVMULWODVWUW, r0)
  1711  			opset(AXVMULWODQVUV, r0)
  1712  			opset(AXVADDF, r0)
  1713  			opset(AXVADDD, r0)
  1714  			opset(AXVSUBF, r0)
  1715  			opset(AXVSUBD, r0)
  1716  			opset(AXVMULF, r0)
  1717  			opset(AXVMULD, r0)
  1718  			opset(AXVDIVF, r0)
  1719  			opset(AXVDIVD, r0)
  1720  
  1721  		case AVANDB:
  1722  			opset(AVORB, r0)
  1723  			opset(AVXORB, r0)
  1724  			opset(AVNORB, r0)
  1725  			opset(AVSHUF4IB, r0)
  1726  			opset(AVSHUF4IH, r0)
  1727  			opset(AVSHUF4IW, r0)
  1728  			opset(AVSHUF4IV, r0)
  1729  
  1730  		case AXVANDB:
  1731  			opset(AXVORB, r0)
  1732  			opset(AXVXORB, r0)
  1733  			opset(AXVNORB, r0)
  1734  			opset(AXVSHUF4IB, r0)
  1735  			opset(AXVSHUF4IH, r0)
  1736  			opset(AXVSHUF4IW, r0)
  1737  			opset(AXVSHUF4IV, r0)
  1738  
  1739  		case AVANDV:
  1740  			opset(AVORV, r0)
  1741  			opset(AVXORV, r0)
  1742  			opset(AVNORV, r0)
  1743  			opset(AVANDNV, r0)
  1744  			opset(AVORNV, r0)
  1745  
  1746  		case AXVANDV:
  1747  			opset(AXVORV, r0)
  1748  			opset(AXVXORV, r0)
  1749  			opset(AXVNORV, r0)
  1750  			opset(AXVANDNV, r0)
  1751  			opset(AXVORNV, r0)
  1752  
  1753  		case AVPCNTB:
  1754  			opset(AVPCNTH, r0)
  1755  			opset(AVPCNTW, r0)
  1756  			opset(AVPCNTV, r0)
  1757  			opset(AVFSQRTF, r0)
  1758  			opset(AVFSQRTD, r0)
  1759  			opset(AVFRECIPF, r0)
  1760  			opset(AVFRECIPD, r0)
  1761  			opset(AVFRSQRTF, r0)
  1762  			opset(AVFRSQRTD, r0)
  1763  			opset(AVNEGB, r0)
  1764  			opset(AVNEGH, r0)
  1765  			opset(AVNEGW, r0)
  1766  			opset(AVNEGV, r0)
  1767  			opset(AVFRINTRNEF, r0)
  1768  			opset(AVFRINTRNED, r0)
  1769  			opset(AVFRINTRZF, r0)
  1770  			opset(AVFRINTRZD, r0)
  1771  			opset(AVFRINTRPF, r0)
  1772  			opset(AVFRINTRPD, r0)
  1773  			opset(AVFRINTRMF, r0)
  1774  			opset(AVFRINTRMD, r0)
  1775  			opset(AVFRINTF, r0)
  1776  			opset(AVFRINTD, r0)
  1777  			opset(AVFCLASSF, r0)
  1778  			opset(AVFCLASSD, r0)
  1779  
  1780  		case AXVPCNTB:
  1781  			opset(AXVPCNTH, r0)
  1782  			opset(AXVPCNTW, r0)
  1783  			opset(AXVPCNTV, r0)
  1784  			opset(AXVFSQRTF, r0)
  1785  			opset(AXVFSQRTD, r0)
  1786  			opset(AXVFRECIPF, r0)
  1787  			opset(AXVFRECIPD, r0)
  1788  			opset(AXVFRSQRTF, r0)
  1789  			opset(AXVFRSQRTD, r0)
  1790  			opset(AXVNEGB, r0)
  1791  			opset(AXVNEGH, r0)
  1792  			opset(AXVNEGW, r0)
  1793  			opset(AXVNEGV, r0)
  1794  			opset(AXVFRINTRNEF, r0)
  1795  			opset(AXVFRINTRNED, r0)
  1796  			opset(AXVFRINTRZF, r0)
  1797  			opset(AXVFRINTRZD, r0)
  1798  			opset(AXVFRINTRPF, r0)
  1799  			opset(AXVFRINTRPD, r0)
  1800  			opset(AXVFRINTRMF, r0)
  1801  			opset(AXVFRINTRMD, r0)
  1802  			opset(AXVFRINTF, r0)
  1803  			opset(AXVFRINTD, r0)
  1804  			opset(AXVFCLASSF, r0)
  1805  			opset(AXVFCLASSD, r0)
  1806  
  1807  		case AVADDB:
  1808  			opset(AVADDH, r0)
  1809  			opset(AVADDW, r0)
  1810  			opset(AVADDV, r0)
  1811  			opset(AVADDQ, r0)
  1812  			opset(AVSUBB, r0)
  1813  			opset(AVSUBH, r0)
  1814  			opset(AVSUBW, r0)
  1815  			opset(AVSUBV, r0)
  1816  			opset(AVSUBQ, r0)
  1817  
  1818  		case AXVADDB:
  1819  			opset(AXVADDH, r0)
  1820  			opset(AXVADDW, r0)
  1821  			opset(AXVADDV, r0)
  1822  			opset(AXVADDQ, r0)
  1823  			opset(AXVSUBB, r0)
  1824  			opset(AXVSUBH, r0)
  1825  			opset(AXVSUBW, r0)
  1826  			opset(AXVSUBV, r0)
  1827  			opset(AXVSUBQ, r0)
  1828  
  1829  		case AVSLLB:
  1830  			opset(AVSRLB, r0)
  1831  			opset(AVSRAB, r0)
  1832  			opset(AVROTRB, r0)
  1833  
  1834  		case AXVSLLB:
  1835  			opset(AXVSRLB, r0)
  1836  			opset(AXVSRAB, r0)
  1837  			opset(AXVROTRB, r0)
  1838  
  1839  		case AVSLLH:
  1840  			opset(AVSRLH, r0)
  1841  			opset(AVSRAH, r0)
  1842  			opset(AVROTRH, r0)
  1843  
  1844  		case AXVSLLH:
  1845  			opset(AXVSRLH, r0)
  1846  			opset(AXVSRAH, r0)
  1847  			opset(AXVROTRH, r0)
  1848  
  1849  		case AVSLLW:
  1850  			opset(AVSRLW, r0)
  1851  			opset(AVSRAW, r0)
  1852  			opset(AVROTRW, r0)
  1853  			opset(AVADDBU, r0)
  1854  			opset(AVADDHU, r0)
  1855  			opset(AVADDWU, r0)
  1856  			opset(AVADDVU, r0)
  1857  			opset(AVSUBBU, r0)
  1858  			opset(AVSUBHU, r0)
  1859  			opset(AVSUBWU, r0)
  1860  			opset(AVSUBVU, r0)
  1861  
  1862  		case AXVSLLW:
  1863  			opset(AXVSRLW, r0)
  1864  			opset(AXVSRAW, r0)
  1865  			opset(AXVROTRW, r0)
  1866  			opset(AXVADDBU, r0)
  1867  			opset(AXVADDHU, r0)
  1868  			opset(AXVADDWU, r0)
  1869  			opset(AXVADDVU, r0)
  1870  			opset(AXVSUBBU, r0)
  1871  			opset(AXVSUBHU, r0)
  1872  			opset(AXVSUBWU, r0)
  1873  			opset(AXVSUBVU, r0)
  1874  
  1875  		case AVSLLV:
  1876  			opset(AVSRLV, r0)
  1877  			opset(AVSRAV, r0)
  1878  			opset(AVROTRV, r0)
  1879  
  1880  		case AXVSLLV:
  1881  			opset(AXVSRLV, r0)
  1882  			opset(AXVSRAV, r0)
  1883  			opset(AXVROTRV, r0)
  1884  
  1885  		case AVSETEQV:
  1886  			opset(AVSETNEV, r0)
  1887  			opset(AVSETANYEQB, r0)
  1888  			opset(AVSETANYEQH, r0)
  1889  			opset(AVSETANYEQW, r0)
  1890  			opset(AVSETANYEQV, r0)
  1891  			opset(AVSETALLNEB, r0)
  1892  			opset(AVSETALLNEH, r0)
  1893  			opset(AVSETALLNEW, r0)
  1894  			opset(AVSETALLNEV, r0)
  1895  
  1896  		case AXVSETEQV:
  1897  			opset(AXVSETNEV, r0)
  1898  			opset(AXVSETANYEQB, r0)
  1899  			opset(AXVSETANYEQH, r0)
  1900  			opset(AXVSETANYEQW, r0)
  1901  			opset(AXVSETANYEQV, r0)
  1902  			opset(AXVSETALLNEB, r0)
  1903  			opset(AXVSETALLNEH, r0)
  1904  			opset(AXVSETALLNEW, r0)
  1905  			opset(AXVSETALLNEV, r0)
  1906  
  1907  		}
  1908  	}
  1909  }
  1910  
  1911  func OP_RRRR(op uint32, r1 uint32, r2 uint32, r3 uint32, r4 uint32) uint32 {
  1912  	return op | (r1&0x1F)<<15 | (r2&0x1F)<<10 | (r3&0x1F)<<5 | (r4 & 0x1F)
  1913  }
  1914  
  1915  // r1 -> rk
  1916  // r2 -> rj
  1917  // r3 -> rd
  1918  func OP_RRR(op uint32, r1 uint32, r2 uint32, r3 uint32) uint32 {
  1919  	return op | (r1&0x1F)<<10 | (r2&0x1F)<<5 | (r3&0x1F)<<0
  1920  }
  1921  
  1922  // r2 -> rj
  1923  // r3 -> rd
  1924  func OP_RR(op uint32, r2 uint32, r3 uint32) uint32 {
  1925  	return op | (r2&0x1F)<<5 | (r3&0x1F)<<0
  1926  }
  1927  
  1928  func OP_16IR_5I(op uint32, i uint32, r2 uint32) uint32 {
  1929  	return op | (i&0xFFFF)<<10 | (r2&0x1F)<<5 | ((i >> 16) & 0x1F)
  1930  }
  1931  
  1932  func OP_16IRR(op uint32, i uint32, r2 uint32, r3 uint32) uint32 {
  1933  	return op | (i&0xFFFF)<<10 | (r2&0x1F)<<5 | (r3&0x1F)<<0
  1934  }
  1935  
  1936  func OP_12IR_5I(op uint32, i1 uint32, r2 uint32, i2 uint32) uint32 {
  1937  	return op | (i1&0xFFF)<<10 | (r2&0x1F)<<5 | (i2&0x1F)<<0
  1938  }
  1939  
  1940  func OP_12IRR(op uint32, i uint32, r2 uint32, r3 uint32) uint32 {
  1941  	return op | (i&0xFFF)<<10 | (r2&0x1F)<<5 | (r3&0x1F)<<0
  1942  }
  1943  
  1944  func OP_8IRR(op uint32, i uint32, r2 uint32, r3 uint32) uint32 {
  1945  	return op | (i&0xFF)<<10 | (r2&0x1F)<<5 | (r3&0x1F)<<0
  1946  }
  1947  
  1948  func OP_6IRR(op uint32, i uint32, r2 uint32, r3 uint32) uint32 {
  1949  	return op | (i&0x3F)<<10 | (r2&0x1F)<<5 | (r3&0x1F)<<0
  1950  }
  1951  
  1952  func OP_5IRR(op uint32, i uint32, r2 uint32, r3 uint32) uint32 {
  1953  	return op | (i&0x1F)<<10 | (r2&0x1F)<<5 | (r3&0x1F)<<0
  1954  }
  1955  
  1956  func OP_4IRR(op uint32, i uint32, r2 uint32, r3 uint32) uint32 {
  1957  	return op | (i&0xF)<<10 | (r2&0x1F)<<5 | (r3&0x1F)<<0
  1958  }
  1959  
  1960  func OP_3IRR(op uint32, i uint32, r2 uint32, r3 uint32) uint32 {
  1961  	return op | (i&0x7)<<10 | (r2&0x1F)<<5 | (r3&0x1F)<<0
  1962  }
  1963  
  1964  func OP_IR(op uint32, i uint32, r2 uint32) uint32 {
  1965  	return op | (i&0xFFFFF)<<5 | (r2&0x1F)<<0 // ui20, rd5
  1966  }
  1967  
  1968  func OP_15I(op uint32, i uint32) uint32 {
  1969  	return op | (i&0x7FFF)<<0
  1970  }
  1971  
  1972  // i1 -> msb
  1973  // r2 -> rj
  1974  // i3 -> lsb
  1975  // r4 -> rd
  1976  func OP_IRIR(op uint32, i1 uint32, r2 uint32, i3 uint32, r4 uint32) uint32 {
  1977  	return op | (i1 << 16) | (r2&0x1F)<<5 | (i3 << 10) | (r4&0x1F)<<0
  1978  }
  1979  
  1980  // Encoding for the 'b' or 'bl' instruction.
  1981  func OP_B_BL(op uint32, i uint32) uint32 {
  1982  	return op | ((i & 0xFFFF) << 10) | ((i >> 16) & 0x3FF)
  1983  }
  1984  
  1985  func (c *ctxt0) asmout(p *obj.Prog, o *Optab, out []uint32) {
  1986  	o1 := uint32(0)
  1987  	o2 := uint32(0)
  1988  	o3 := uint32(0)
  1989  	o4 := uint32(0)
  1990  	o5 := uint32(0)
  1991  
  1992  	add := AADDU
  1993  	add = AADDVU
  1994  
  1995  	switch o.type_ {
  1996  	default:
  1997  		c.ctxt.Diag("unknown type %d %v", o.type_)
  1998  		prasm(p)
  1999  
  2000  	case 0: // pseudo ops
  2001  		break
  2002  
  2003  	case 1: // mov r1,r2 ==> OR r1,r0,r2
  2004  		a := AOR
  2005  		if p.As == AMOVW {
  2006  			a = ASLL
  2007  		}
  2008  		o1 = OP_RRR(c.oprrr(a), uint32(REGZERO), uint32(p.From.Reg), uint32(p.To.Reg))
  2009  
  2010  	case 2: // add/sub r1,[r2],r3
  2011  		r := int(p.Reg)
  2012  		if p.As == ANEGW || p.As == ANEGV {
  2013  			r = REGZERO
  2014  		}
  2015  		if r == 0 {
  2016  			r = int(p.To.Reg)
  2017  		}
  2018  		o1 = OP_RRR(c.oprrr(p.As), uint32(p.From.Reg), uint32(r), uint32(p.To.Reg))
  2019  
  2020  	case 3: // mov $soreg, r ==> or/add $i,o,r
  2021  		v := c.regoff(&p.From)
  2022  
  2023  		r := int(p.From.Reg)
  2024  		if r == 0 {
  2025  			r = int(o.param)
  2026  		}
  2027  		a := add
  2028  		if o.from1 == C_12CON && v > 0 {
  2029  			a = AOR
  2030  		}
  2031  
  2032  		o1 = OP_12IRR(c.opirr(a), uint32(v), uint32(r), uint32(p.To.Reg))
  2033  
  2034  	case 4: // add $scon,[r1],r2
  2035  		v := c.regoff(&p.From)
  2036  		r := int(p.Reg)
  2037  		if r == 0 {
  2038  			r = int(p.To.Reg)
  2039  		}
  2040  		o1 = OP_12IRR(c.opirr(p.As), uint32(v), uint32(r), uint32(p.To.Reg))
  2041  
  2042  	case 5: // syscall
  2043  		v := c.regoff(&p.From)
  2044  		o1 = OP_15I(c.opi(p.As), uint32(v))
  2045  
  2046  	case 6: // beq r1,[r2],sbra
  2047  		v := int32(0)
  2048  		if p.To.Target() != nil {
  2049  			v = int32(p.To.Target().Pc-p.Pc) >> 2
  2050  		}
  2051  		as, rd, rj, width := p.As, p.Reg, p.From.Reg, 16
  2052  		switch as {
  2053  		case ABGTZ, ABLEZ:
  2054  			rd, rj = rj, rd
  2055  		case ABFPT, ABFPF:
  2056  			width = 21
  2057  			// FCC0 is the implicit source operand, now that we
  2058  			// don't register-allocate from the FCC bank.
  2059  			if rj == 0 {
  2060  				rj = REG_FCC0
  2061  			}
  2062  		case ABEQ, ABNE:
  2063  			if rd == 0 || rd == REGZERO || rj == REGZERO {
  2064  				// BEQZ/BNEZ can be encoded with 21-bit offsets.
  2065  				width = 21
  2066  				as = -as
  2067  				if rj == 0 || rj == REGZERO {
  2068  					rj = rd
  2069  				}
  2070  			}
  2071  		}
  2072  		switch width {
  2073  		case 21:
  2074  			if (v<<11)>>11 != v {
  2075  				c.ctxt.Diag("21 bit-width, short branch too far\n%v", p)
  2076  			}
  2077  			o1 = OP_16IR_5I(c.opirr(as), uint32(v), uint32(rj))
  2078  		case 16:
  2079  			if (v<<16)>>16 != v {
  2080  				c.ctxt.Diag("16 bit-width, short branch too far\n%v", p)
  2081  			}
  2082  			o1 = OP_16IRR(c.opirr(as), uint32(v), uint32(rj), uint32(rd))
  2083  		default:
  2084  			c.ctxt.Diag("unexpected branch encoding\n%v", p)
  2085  		}
  2086  
  2087  	case 7: // mov r, soreg
  2088  		r := int(p.To.Reg)
  2089  		if r == 0 {
  2090  			r = int(o.param)
  2091  		}
  2092  		v := c.regoff(&p.To)
  2093  		o1 = OP_12IRR(c.opirr(p.As), uint32(v), uint32(r), uint32(p.From.Reg))
  2094  
  2095  	case 8: // mov soreg, r
  2096  		r := int(p.From.Reg)
  2097  		if r == 0 {
  2098  			r = int(o.param)
  2099  		}
  2100  		v := c.regoff(&p.From)
  2101  		o1 = OP_12IRR(c.opirr(-p.As), uint32(v), uint32(r), uint32(p.To.Reg))
  2102  
  2103  	case 9: // sll r1,[r2],r3
  2104  		o1 = OP_RR(c.oprr(p.As), uint32(p.From.Reg), uint32(p.To.Reg))
  2105  
  2106  	case 10: // add $con,[r1],r2 ==> mov $con, t; add t,[r1],r2
  2107  		v := c.regoff(&p.From)
  2108  		a := AOR
  2109  		if v < 0 {
  2110  			a = AADDU
  2111  		}
  2112  		o1 = OP_12IRR(c.opirr(a), uint32(v), uint32(0), uint32(REGTMP))
  2113  		r := int(p.Reg)
  2114  		if r == 0 {
  2115  			r = int(p.To.Reg)
  2116  		}
  2117  		o2 = OP_RRR(c.oprrr(p.As), uint32(REGTMP), uint32(r), uint32(p.To.Reg))
  2118  
  2119  	case 11: // jmp lbra
  2120  		v := int32(0)
  2121  		if p.To.Target() != nil {
  2122  			v = int32(p.To.Target().Pc-p.Pc) >> 2
  2123  		}
  2124  		o1 = OP_B_BL(c.opirr(p.As), uint32(v))
  2125  		if p.To.Sym != nil {
  2126  			c.cursym.AddRel(c.ctxt, obj.Reloc{
  2127  				Type: objabi.R_CALLLOONG64,
  2128  				Off:  int32(c.pc),
  2129  				Siz:  4,
  2130  				Sym:  p.To.Sym,
  2131  				Add:  p.To.Offset,
  2132  			})
  2133  		}
  2134  
  2135  	case 12: // movbs r,r
  2136  		switch p.As {
  2137  		case AMOVB:
  2138  			o1 = OP_RR(c.oprr(AEXTWB), uint32(p.From.Reg), uint32(p.To.Reg))
  2139  		case AMOVH:
  2140  			o1 = OP_RR(c.oprr(AEXTWH), uint32(p.From.Reg), uint32(p.To.Reg))
  2141  		case AMOVBU:
  2142  			o1 = OP_12IRR(c.opirr(AAND), uint32(0xff), uint32(p.From.Reg), uint32(p.To.Reg))
  2143  		case AMOVHU:
  2144  			o1 = OP_IRIR(c.opirir(ABSTRPICKV), 15, uint32(p.From.Reg), 0, uint32(p.To.Reg))
  2145  		case AMOVWU:
  2146  			o1 = OP_IRIR(c.opirir(ABSTRPICKV), 31, uint32(p.From.Reg), 0, uint32(p.To.Reg))
  2147  		default:
  2148  			c.ctxt.Diag("unexpected encoding\n%v", p)
  2149  		}
  2150  
  2151  	case 13: // vsll $ui3, [vr1], vr2
  2152  		v := c.regoff(&p.From)
  2153  		r := int(p.Reg)
  2154  		if r == 0 {
  2155  			r = int(p.To.Reg)
  2156  		}
  2157  		o1 = OP_3IRR(c.opirr(p.As), uint32(v), uint32(r), uint32(p.To.Reg))
  2158  
  2159  	case 14: // vsll $ui4, [vr1], vr2
  2160  		v := c.regoff(&p.From)
  2161  		r := int(p.Reg)
  2162  		if r == 0 {
  2163  			r = int(p.To.Reg)
  2164  		}
  2165  		o1 = OP_4IRR(c.opirr(p.As), uint32(v), uint32(r), uint32(p.To.Reg))
  2166  
  2167  	case 15: // teq $c r,r
  2168  		v := c.regoff(&p.From)
  2169  		r := int(p.Reg)
  2170  		if r == 0 {
  2171  			r = REGZERO
  2172  		}
  2173  		/*
  2174  			teq c, r1, r2
  2175  			fallthrough
  2176  			==>
  2177  			bne r1, r2, 2
  2178  			break c
  2179  			fallthrough
  2180  		*/
  2181  		if p.As == ATEQ {
  2182  			o1 = OP_16IRR(c.opirr(ABNE), uint32(2), uint32(r), uint32(p.To.Reg))
  2183  		} else { // ATNE
  2184  			o1 = OP_16IRR(c.opirr(ABEQ), uint32(2), uint32(r), uint32(p.To.Reg))
  2185  		}
  2186  		o2 = OP_15I(c.opi(ABREAK), uint32(v))
  2187  
  2188  	case 16: // sll $c,[r1],r2
  2189  		v := c.regoff(&p.From)
  2190  		r := int(p.Reg)
  2191  		if r == 0 {
  2192  			r = int(p.To.Reg)
  2193  		}
  2194  
  2195  		// instruction ending with V:6-digit immediate, others:5-digit immediate
  2196  		if v >= 32 && vshift(p.As) {
  2197  			o1 = OP_16IRR(c.opirr(p.As), uint32(v)&0x3f, uint32(r), uint32(p.To.Reg))
  2198  		} else {
  2199  			o1 = OP_16IRR(c.opirr(p.As), uint32(v)&0x1f, uint32(r), uint32(p.To.Reg))
  2200  		}
  2201  
  2202  	case 17: // bstrpickw $msbw, r1, $lsbw, r2
  2203  		rd, rj := p.To.Reg, p.Reg
  2204  		if rj == obj.REG_NONE {
  2205  			rj = rd
  2206  		}
  2207  		msb, lsb := p.From.Offset, p.GetFrom3().Offset
  2208  
  2209  		// check the range of msb and lsb
  2210  		var b uint32
  2211  		if p.As == ABSTRPICKW || p.As == ABSTRINSW {
  2212  			b = 32
  2213  		} else {
  2214  			b = 64
  2215  		}
  2216  		if lsb < 0 || uint32(lsb) >= b || msb < 0 || uint32(msb) >= b || uint32(lsb) > uint32(msb) {
  2217  			c.ctxt.Diag("illegal bit number\n%v", p)
  2218  		}
  2219  
  2220  		o1 = OP_IRIR(c.opirir(p.As), uint32(msb), uint32(rj), uint32(lsb), uint32(rd))
  2221  
  2222  	case 18: // jmp [r1],0(r2)
  2223  		r := int(p.Reg)
  2224  		if r == 0 {
  2225  			r = int(o.param)
  2226  		}
  2227  		o1 = OP_RRR(c.oprrr(p.As), uint32(0), uint32(p.To.Reg), uint32(r))
  2228  		if p.As == obj.ACALL {
  2229  			c.cursym.AddRel(c.ctxt, obj.Reloc{
  2230  				Type: objabi.R_CALLIND,
  2231  				Off:  int32(c.pc),
  2232  			})
  2233  		}
  2234  
  2235  	case 19: // mov $lcon,r
  2236  		// NOTE: this case does not use REGTMP. If it ever does,
  2237  		// remove the NOTUSETMP flag in optab.
  2238  		v := c.regoff(&p.From)
  2239  		o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(p.To.Reg))
  2240  		o2 = OP_12IRR(c.opirr(AOR), uint32(v), uint32(p.To.Reg), uint32(p.To.Reg))
  2241  
  2242  	case 20: // mov Rsrc, (Rbase)(Roff)
  2243  		o1 = OP_RRR(c.oprrr(p.As), uint32(p.To.Index), uint32(p.To.Reg), uint32(p.From.Reg))
  2244  
  2245  	case 21: // mov (Rbase)(Roff), Rdst
  2246  		o1 = OP_RRR(c.oprrr(-p.As), uint32(p.From.Index), uint32(p.From.Reg), uint32(p.To.Reg))
  2247  
  2248  	case 22: // add $si5,[r1],r2
  2249  		v := c.regoff(&p.From)
  2250  		r := int(p.Reg)
  2251  		if r == 0 {
  2252  			r = int(p.To.Reg)
  2253  		}
  2254  
  2255  		o1 = OP_5IRR(c.opirr(p.As), uint32(v), uint32(r), uint32(p.To.Reg))
  2256  
  2257  	case 23: // add $ui8,[r1],r2
  2258  		v := c.regoff(&p.From)
  2259  		r := int(p.Reg)
  2260  		if r == 0 {
  2261  			r = int(p.To.Reg)
  2262  		}
  2263  
  2264  		// the operand range available for instructions VSHUF4IV and XVSHUF4IV is [0, 15]
  2265  		if p.As == AVSHUF4IV || p.As == AXVSHUF4IV {
  2266  			operand := uint32(v)
  2267  			c.checkoperand(p, operand, 15)
  2268  		}
  2269  
  2270  		o1 = OP_8IRR(c.opirr(p.As), uint32(v), uint32(r), uint32(p.To.Reg))
  2271  
  2272  	case 24: // add $lcon,r1,r2
  2273  		v := c.regoff(&p.From)
  2274  		o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(REGTMP))
  2275  		o2 = OP_12IRR(c.opirr(AOR), uint32(v), uint32(REGTMP), uint32(REGTMP))
  2276  		r := int(p.Reg)
  2277  		if r == 0 {
  2278  			r = int(p.To.Reg)
  2279  		}
  2280  		o3 = OP_RRR(c.oprrr(p.As), uint32(REGTMP), uint32(r), uint32(p.To.Reg))
  2281  
  2282  	case 25: // mov $ucon,r
  2283  		v := c.regoff(&p.From)
  2284  		o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(p.To.Reg))
  2285  
  2286  	case 26: // add/and $ucon,[r1],r2
  2287  		v := c.regoff(&p.From)
  2288  		o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(REGTMP))
  2289  		r := int(p.Reg)
  2290  		if r == 0 {
  2291  			r = int(p.To.Reg)
  2292  		}
  2293  		o2 = OP_RRR(c.oprrr(p.As), uint32(REGTMP), uint32(r), uint32(p.To.Reg))
  2294  
  2295  	case 27: // mov $lsext/auto/oreg,r
  2296  		v := c.regoff(&p.From)
  2297  		o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(REGTMP))
  2298  		o2 = OP_12IRR(c.opirr(AOR), uint32(v), uint32(REGTMP), uint32(REGTMP))
  2299  		r := int(p.From.Reg)
  2300  		if r == 0 {
  2301  			r = int(o.param)
  2302  		}
  2303  		o3 = OP_RRR(c.oprrr(add), uint32(REGTMP), uint32(r), uint32(p.To.Reg))
  2304  
  2305  	case 28: // mov [sl]ext/auto/oreg,fr
  2306  		v := c.regoff(&p.From)
  2307  		r := int(p.From.Reg)
  2308  		if r == 0 {
  2309  			r = int(o.param)
  2310  		}
  2311  		switch o.size {
  2312  		case 12:
  2313  			o1 = OP_IR(c.opir(ALU12IW), uint32((v+1<<11)>>12), uint32(REGTMP))
  2314  			o2 = OP_RRR(c.oprrr(add), uint32(r), uint32(REGTMP), uint32(REGTMP))
  2315  			o3 = OP_12IRR(c.opirr(-p.As), uint32(v), uint32(REGTMP), uint32(p.To.Reg))
  2316  
  2317  		case 4:
  2318  			o1 = OP_12IRR(c.opirr(-p.As), uint32(v), uint32(r), uint32(p.To.Reg))
  2319  		}
  2320  
  2321  	case 29: // mov fr,[sl]ext/auto/oreg
  2322  		v := c.regoff(&p.To)
  2323  		r := int(p.To.Reg)
  2324  		if r == 0 {
  2325  			r = int(o.param)
  2326  		}
  2327  		switch o.size {
  2328  		case 12:
  2329  			o1 = OP_IR(c.opir(ALU12IW), uint32((v+1<<11)>>12), uint32(REGTMP))
  2330  			o2 = OP_RRR(c.oprrr(add), uint32(r), uint32(REGTMP), uint32(REGTMP))
  2331  			o3 = OP_12IRR(c.opirr(p.As), uint32(v), uint32(REGTMP), uint32(p.From.Reg))
  2332  
  2333  		case 4:
  2334  			o1 = OP_12IRR(c.opirr(p.As), uint32(v), uint32(r), uint32(p.From.Reg))
  2335  		}
  2336  
  2337  	case 30: // mov gr/fr/fcc/fcsr, fr/fcc/fcsr/gr
  2338  		a := c.specialFpMovInst(p.As, oclass(&p.From), oclass(&p.To))
  2339  		o1 = OP_RR(a, uint32(p.From.Reg), uint32(p.To.Reg))
  2340  
  2341  	case 31: // vsll $ui5, [vr1], vr2
  2342  		v := c.regoff(&p.From)
  2343  		r := int(p.Reg)
  2344  		if r == 0 {
  2345  			r = int(p.To.Reg)
  2346  		}
  2347  		o1 = OP_5IRR(c.opirr(p.As), uint32(v), uint32(r), uint32(p.To.Reg))
  2348  
  2349  	case 32: // vsll $ui6, [vr1], vr2
  2350  		v := c.regoff(&p.From)
  2351  		r := int(p.Reg)
  2352  		if r == 0 {
  2353  			r = int(p.To.Reg)
  2354  		}
  2355  		o1 = OP_6IRR(c.opirr(p.As), uint32(v), uint32(r), uint32(p.To.Reg))
  2356  
  2357  	case 34: // mov $con,fr
  2358  		v := c.regoff(&p.From)
  2359  		a := AADDU
  2360  		if v > 0 {
  2361  			a = AOR
  2362  		}
  2363  		a2 := c.specialFpMovInst(p.As, C_REG, oclass(&p.To))
  2364  		o1 = OP_12IRR(c.opirr(a), uint32(v), uint32(0), uint32(REGTMP))
  2365  		o2 = OP_RR(a2, uint32(REGTMP), uint32(p.To.Reg))
  2366  
  2367  	case 35: // mov r,lext/auto/oreg
  2368  		v := c.regoff(&p.To)
  2369  		r := int(p.To.Reg)
  2370  		if r == 0 {
  2371  			r = int(o.param)
  2372  		}
  2373  		o1 = OP_IR(c.opir(ALU12IW), uint32((v+1<<11)>>12), uint32(REGTMP))
  2374  		o2 = OP_RRR(c.oprrr(add), uint32(r), uint32(REGTMP), uint32(REGTMP))
  2375  		o3 = OP_12IRR(c.opirr(p.As), uint32(v), uint32(REGTMP), uint32(p.From.Reg))
  2376  
  2377  	case 36: // mov lext/auto/oreg,r
  2378  		v := c.regoff(&p.From)
  2379  		r := int(p.From.Reg)
  2380  		if r == 0 {
  2381  			r = int(o.param)
  2382  		}
  2383  		o1 = OP_IR(c.opir(ALU12IW), uint32((v+1<<11)>>12), uint32(REGTMP))
  2384  		o2 = OP_RRR(c.oprrr(add), uint32(r), uint32(REGTMP), uint32(REGTMP))
  2385  		o3 = OP_12IRR(c.opirr(-p.As), uint32(v), uint32(REGTMP), uint32(p.To.Reg))
  2386  
  2387  	case 37: // fmadd r1, r2, [r3], r4
  2388  		r := int(p.To.Reg)
  2389  		if len(p.RestArgs) > 0 {
  2390  			r = int(p.GetFrom3().Reg)
  2391  		}
  2392  		o1 = OP_RRRR(c.oprrrr(p.As), uint32(p.From.Reg), uint32(p.Reg), uint32(r), uint32(p.To.Reg))
  2393  
  2394  	case 38: // word
  2395  		o1 = uint32(c.regoff(&p.From))
  2396  
  2397  	case 39: // vmov Rn, Vd.<T>[index]
  2398  		v, m := c.specialLsxMovInst(p.As, p.From.Reg, p.To.Reg)
  2399  		if v == 0 {
  2400  			c.ctxt.Diag("illegal arng type combination: %v\n", p)
  2401  		}
  2402  
  2403  		Rj := uint32(p.From.Reg & EXT_REG_MASK)
  2404  		Vd := uint32(p.To.Reg & EXT_REG_MASK)
  2405  		index := uint32(p.To.Index)
  2406  		c.checkindex(p, index, m)
  2407  		o1 = v | (index << 10) | (Rj << 5) | Vd
  2408  
  2409  	case 40: // vmov Vd.<T>[index], Rn
  2410  		v, m := c.specialLsxMovInst(p.As, p.From.Reg, p.To.Reg)
  2411  		if v == 0 {
  2412  			c.ctxt.Diag("illegal arng type combination: %v\n", p)
  2413  		}
  2414  
  2415  		Vj := uint32(p.From.Reg & EXT_REG_MASK)
  2416  		Rd := uint32(p.To.Reg & EXT_REG_MASK)
  2417  		index := uint32(p.From.Index)
  2418  		c.checkindex(p, index, m)
  2419  		o1 = v | (index << 10) | (Vj << 5) | Rd
  2420  
  2421  	case 41: // vmov Rn, Vd.<T>
  2422  		v, _ := c.specialLsxMovInst(p.As, p.From.Reg, p.To.Reg)
  2423  		if v == 0 {
  2424  			c.ctxt.Diag("illegal arng type combination: %v\n", p)
  2425  		}
  2426  
  2427  		Rj := uint32(p.From.Reg & EXT_REG_MASK)
  2428  		Vd := uint32(p.To.Reg & EXT_REG_MASK)
  2429  		o1 = v | (Rj << 5) | Vd
  2430  
  2431  	case 42: // vmov  xj, xd.<T>
  2432  		v, _ := c.specialLsxMovInst(p.As, p.From.Reg, p.To.Reg)
  2433  		if v == 0 {
  2434  			c.ctxt.Diag("illegal arng type combination: %v\n", p)
  2435  		}
  2436  
  2437  		Xj := uint32(p.From.Reg & EXT_REG_MASK)
  2438  		Xd := uint32(p.To.Reg & EXT_REG_MASK)
  2439  		o1 = v | (Xj << 5) | Xd
  2440  
  2441  	case 43: // vmov  xj, xd.<T>[index]
  2442  		v, m := c.specialLsxMovInst(p.As, p.From.Reg, p.To.Reg)
  2443  		if v == 0 {
  2444  			c.ctxt.Diag("illegal arng type combination: %v\n", p)
  2445  		}
  2446  
  2447  		Xj := uint32(p.From.Reg & EXT_REG_MASK)
  2448  		Xd := uint32(p.To.Reg & EXT_REG_MASK)
  2449  		index := uint32(p.To.Index)
  2450  		c.checkindex(p, index, m)
  2451  		o1 = v | (index << 10) | (Xj << 5) | Xd
  2452  
  2453  	case 44: // vmov  xj.<T>[index], xd
  2454  		v, m := c.specialLsxMovInst(p.As, p.From.Reg, p.To.Reg)
  2455  		if v == 0 {
  2456  			c.ctxt.Diag("illegal arng type combination: %v\n", p)
  2457  		}
  2458  
  2459  		Xj := uint32(p.From.Reg & EXT_REG_MASK)
  2460  		Xd := uint32(p.To.Reg & EXT_REG_MASK)
  2461  		index := uint32(p.From.Index)
  2462  		c.checkindex(p, index, m)
  2463  		o1 = v | (index << 10) | (Xj << 5) | Xd
  2464  
  2465  	case 45: // vmov  vj.<T>[index], vd.<T>
  2466  		v, m := c.specialLsxMovInst(p.As, p.From.Reg, p.To.Reg)
  2467  		if v == 0 {
  2468  			c.ctxt.Diag("illegal arng type combination: %v\n", p)
  2469  		}
  2470  
  2471  		vj := uint32(p.From.Reg & EXT_REG_MASK)
  2472  		vd := uint32(p.To.Reg & EXT_REG_MASK)
  2473  		index := uint32(p.From.Index)
  2474  		c.checkindex(p, index, m)
  2475  		o1 = v | (index << 10) | (vj << 5) | vd
  2476  
  2477  	case 46: // preld  offset(Rbase), $hint
  2478  		offs := c.regoff(&p.From)
  2479  		hint := p.GetFrom3().Offset
  2480  		o1 = OP_12IR_5I(c.opiir(p.As), uint32(offs), uint32(p.From.Reg), uint32(hint))
  2481  
  2482  	case 47: // preldx offset(Rbase), $n, $hint
  2483  		offs := c.regoff(&p.From)
  2484  		hint := p.RestArgs[1].Offset
  2485  		n := uint64(p.GetFrom3().Offset)
  2486  
  2487  		addrSeq := (n >> 0) & 0x1
  2488  		blkSize := (n >> 1) & 0x7ff
  2489  		blkNums := (n >> 12) & 0x1ff
  2490  		stride := (n >> 21) & 0xffff
  2491  
  2492  		if blkSize > 1024 {
  2493  			c.ctxt.Diag("%v: block_size amount out of range[16, 1024]: %v\n", p, blkSize)
  2494  		}
  2495  
  2496  		if blkNums > 256 {
  2497  			c.ctxt.Diag("%v: block_nums amount out of range[1, 256]: %v\n", p, blkSize)
  2498  		}
  2499  
  2500  		v := (uint64(offs) & 0xffff)
  2501  		v += addrSeq << 16
  2502  		v += ((blkSize / 16) - 1) << 20
  2503  		v += (blkNums - 1) << 32
  2504  		v += stride << 44
  2505  
  2506  		o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(REGTMP))
  2507  		o2 = OP_12IRR(c.opirr(AOR), uint32(v), uint32(REGTMP), uint32(REGTMP))
  2508  		o3 = OP_IR(c.opir(ALU32ID), uint32(v>>32), uint32(REGTMP))
  2509  		o4 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(REGTMP), uint32(REGTMP))
  2510  		o5 = OP_5IRR(c.opirr(p.As), uint32(REGTMP), uint32(p.From.Reg), uint32(hint))
  2511  
  2512  	case 49:
  2513  		if p.As == ANOOP {
  2514  			// andi r0, r0, 0
  2515  			o1 = OP_12IRR(c.opirr(AAND), 0, 0, 0)
  2516  		} else {
  2517  			// undef
  2518  			o1 = OP_15I(c.opi(ABREAK), 0)
  2519  		}
  2520  
  2521  	// relocation operations
  2522  	case 50: // mov r,addr ==> pcalau12i + sw
  2523  		o1 = OP_IR(c.opir(APCALAU12I), uint32(0), uint32(REGTMP))
  2524  		c.cursym.AddRel(c.ctxt, obj.Reloc{
  2525  			Type: objabi.R_LOONG64_ADDR_HI,
  2526  			Off:  int32(c.pc),
  2527  			Siz:  4,
  2528  			Sym:  p.To.Sym,
  2529  			Add:  p.To.Offset,
  2530  		})
  2531  		o2 = OP_12IRR(c.opirr(p.As), uint32(0), uint32(REGTMP), uint32(p.From.Reg))
  2532  		c.cursym.AddRel(c.ctxt, obj.Reloc{
  2533  			Type: objabi.R_LOONG64_ADDR_LO,
  2534  			Off:  int32(c.pc + 4),
  2535  			Siz:  4,
  2536  			Sym:  p.To.Sym,
  2537  			Add:  p.To.Offset,
  2538  		})
  2539  
  2540  	case 51: // mov addr,r ==> pcalau12i + lw
  2541  		o1 = OP_IR(c.opir(APCALAU12I), uint32(0), uint32(REGTMP))
  2542  		c.cursym.AddRel(c.ctxt, obj.Reloc{
  2543  			Type: objabi.R_LOONG64_ADDR_HI,
  2544  			Off:  int32(c.pc),
  2545  			Siz:  4,
  2546  			Sym:  p.From.Sym,
  2547  			Add:  p.From.Offset,
  2548  		})
  2549  		o2 = OP_12IRR(c.opirr(-p.As), uint32(0), uint32(REGTMP), uint32(p.To.Reg))
  2550  		c.cursym.AddRel(c.ctxt, obj.Reloc{
  2551  			Type: objabi.R_LOONG64_ADDR_LO,
  2552  			Off:  int32(c.pc + 4),
  2553  			Siz:  4,
  2554  			Sym:  p.From.Sym,
  2555  			Add:  p.From.Offset,
  2556  		})
  2557  
  2558  	case 52: // mov $ext, r
  2559  		// NOTE: this case does not use REGTMP. If it ever does,
  2560  		// remove the NOTUSETMP flag in optab.
  2561  		o1 = OP_IR(c.opir(APCALAU12I), uint32(0), uint32(p.To.Reg))
  2562  		c.cursym.AddRel(c.ctxt, obj.Reloc{
  2563  			Type: objabi.R_LOONG64_ADDR_HI,
  2564  			Off:  int32(c.pc),
  2565  			Siz:  4,
  2566  			Sym:  p.From.Sym,
  2567  			Add:  p.From.Offset,
  2568  		})
  2569  		o2 = OP_12IRR(c.opirr(add), uint32(0), uint32(p.To.Reg), uint32(p.To.Reg))
  2570  		c.cursym.AddRel(c.ctxt, obj.Reloc{
  2571  			Type: objabi.R_LOONG64_ADDR_LO,
  2572  			Off:  int32(c.pc + 4),
  2573  			Siz:  4,
  2574  			Sym:  p.From.Sym,
  2575  			Add:  p.From.Offset,
  2576  		})
  2577  
  2578  	case 53: // mov r, tlsvar ==>  lu12i.w + ori + add r2, regtmp + sw o(regtmp)
  2579  		// NOTE: this case does not use REGTMP. If it ever does,
  2580  		// remove the NOTUSETMP flag in optab.
  2581  		o1 = OP_IR(c.opir(ALU12IW), uint32(0), uint32(REGTMP))
  2582  		c.cursym.AddRel(c.ctxt, obj.Reloc{
  2583  			Type: objabi.R_LOONG64_TLS_LE_HI,
  2584  			Off:  int32(c.pc),
  2585  			Siz:  4,
  2586  			Sym:  p.To.Sym,
  2587  			Add:  p.To.Offset,
  2588  		})
  2589  		o2 = OP_12IRR(c.opirr(AOR), uint32(0), uint32(REGTMP), uint32(REGTMP))
  2590  		c.cursym.AddRel(c.ctxt, obj.Reloc{
  2591  			Type: objabi.R_LOONG64_TLS_LE_LO,
  2592  			Off:  int32(c.pc + 4),
  2593  			Siz:  4,
  2594  			Sym:  p.To.Sym,
  2595  			Add:  p.To.Offset,
  2596  		})
  2597  		o3 = OP_RRR(c.oprrr(AADDV), uint32(REG_R2), uint32(REGTMP), uint32(REGTMP))
  2598  		o4 = OP_12IRR(c.opirr(p.As), uint32(0), uint32(REGTMP), uint32(p.From.Reg))
  2599  
  2600  	case 54: // lu12i.w + ori + add r2, regtmp + lw o(regtmp)
  2601  		// NOTE: this case does not use REGTMP. If it ever does,
  2602  		// remove the NOTUSETMP flag in optab.
  2603  		o1 = OP_IR(c.opir(ALU12IW), uint32(0), uint32(REGTMP))
  2604  		c.cursym.AddRel(c.ctxt, obj.Reloc{
  2605  			Type: objabi.R_LOONG64_TLS_LE_HI,
  2606  			Off:  int32(c.pc),
  2607  			Siz:  4,
  2608  			Sym:  p.From.Sym,
  2609  			Add:  p.From.Offset,
  2610  		})
  2611  		o2 = OP_12IRR(c.opirr(AOR), uint32(0), uint32(REGTMP), uint32(REGTMP))
  2612  		c.cursym.AddRel(c.ctxt, obj.Reloc{
  2613  			Type: objabi.R_LOONG64_TLS_LE_LO,
  2614  			Off:  int32(c.pc + 4),
  2615  			Siz:  4,
  2616  			Sym:  p.From.Sym,
  2617  			Add:  p.From.Offset,
  2618  		})
  2619  		o3 = OP_RRR(c.oprrr(AADDV), uint32(REG_R2), uint32(REGTMP), uint32(REGTMP))
  2620  		o4 = OP_12IRR(c.opirr(-p.As), uint32(0), uint32(REGTMP), uint32(p.To.Reg))
  2621  
  2622  	case 56: // mov r, tlsvar IE model ==> (pcalau12i + ld.d)tlsvar@got + add.d + st.d
  2623  		o1 = OP_IR(c.opir(APCALAU12I), uint32(0), uint32(REGTMP))
  2624  		c.cursym.AddRel(c.ctxt, obj.Reloc{
  2625  			Type: objabi.R_LOONG64_TLS_IE_HI,
  2626  			Off:  int32(c.pc),
  2627  			Siz:  4,
  2628  			Sym:  p.To.Sym,
  2629  		})
  2630  		o2 = OP_12IRR(c.opirr(-p.As), uint32(0), uint32(REGTMP), uint32(REGTMP))
  2631  		c.cursym.AddRel(c.ctxt, obj.Reloc{
  2632  			Type: objabi.R_LOONG64_TLS_IE_LO,
  2633  			Off:  int32(c.pc + 4),
  2634  			Siz:  4,
  2635  			Sym:  p.To.Sym,
  2636  		})
  2637  		o3 = OP_RRR(c.oprrr(AADDVU), uint32(REGTMP), uint32(REG_R2), uint32(REGTMP))
  2638  		o4 = OP_12IRR(c.opirr(p.As), uint32(0), uint32(REGTMP), uint32(p.From.Reg))
  2639  
  2640  	case 57: // mov tlsvar, r IE model ==> (pcalau12i + ld.d)tlsvar@got + add.d + ld.d
  2641  		o1 = OP_IR(c.opir(APCALAU12I), uint32(0), uint32(REGTMP))
  2642  		c.cursym.AddRel(c.ctxt, obj.Reloc{
  2643  			Type: objabi.R_LOONG64_TLS_IE_HI,
  2644  			Off:  int32(c.pc),
  2645  			Siz:  4,
  2646  			Sym:  p.From.Sym,
  2647  		})
  2648  		o2 = OP_12IRR(c.opirr(-p.As), uint32(0), uint32(REGTMP), uint32(REGTMP))
  2649  		c.cursym.AddRel(c.ctxt, obj.Reloc{
  2650  			Type: objabi.R_LOONG64_TLS_IE_LO,
  2651  			Off:  int32(c.pc + 4),
  2652  			Siz:  4,
  2653  			Sym:  p.From.Sym,
  2654  		})
  2655  		o3 = OP_RRR(c.oprrr(AADDVU), uint32(REGTMP), uint32(REG_R2), uint32(REGTMP))
  2656  		o4 = OP_12IRR(c.opirr(-p.As), uint32(0), uint32(REGTMP), uint32(p.To.Reg))
  2657  
  2658  	case 59: // mov $dcon,r
  2659  		// NOTE: this case does not use REGTMP. If it ever does,
  2660  		// remove the NOTUSETMP flag in optab.
  2661  		v := c.vregoff(&p.From)
  2662  		o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(p.To.Reg))
  2663  		o2 = OP_12IRR(c.opirr(AOR), uint32(v), uint32(p.To.Reg), uint32(p.To.Reg))
  2664  		o3 = OP_IR(c.opir(ALU32ID), uint32(v>>32), uint32(p.To.Reg))
  2665  		o4 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(p.To.Reg), uint32(p.To.Reg))
  2666  
  2667  	case 60: // add $dcon,r1,r2
  2668  		v := c.vregoff(&p.From)
  2669  		o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(REGTMP))
  2670  		o2 = OP_12IRR(c.opirr(AOR), uint32(v), uint32(REGTMP), uint32(REGTMP))
  2671  		o3 = OP_IR(c.opir(ALU32ID), uint32(v>>32), uint32(REGTMP))
  2672  		o4 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(REGTMP), uint32(REGTMP))
  2673  		r := int(p.Reg)
  2674  		if r == 0 {
  2675  			r = int(p.To.Reg)
  2676  		}
  2677  		o5 = OP_RRR(c.oprrr(p.As), uint32(REGTMP), uint32(r), uint32(p.To.Reg))
  2678  
  2679  	case 61: // word C_DCON
  2680  		o1 = uint32(c.vregoff(&p.From))
  2681  		o2 = uint32(c.vregoff(&p.From) >> 32)
  2682  
  2683  	case 62: // rdtimex rd, rj
  2684  		o1 = OP_RR(c.oprr(p.As), uint32(p.To.Reg), uint32(p.RegTo2))
  2685  
  2686  	case 65: // mov sym@GOT, r ==> pcalau12i + ld.d
  2687  		o1 = OP_IR(c.opir(APCALAU12I), uint32(0), uint32(p.To.Reg))
  2688  		c.cursym.AddRel(c.ctxt, obj.Reloc{
  2689  			Type: objabi.R_LOONG64_GOT_HI,
  2690  			Off:  int32(c.pc),
  2691  			Siz:  4,
  2692  			Sym:  p.From.Sym,
  2693  		})
  2694  		o2 = OP_12IRR(c.opirr(-p.As), uint32(0), uint32(p.To.Reg), uint32(p.To.Reg))
  2695  		c.cursym.AddRel(c.ctxt, obj.Reloc{
  2696  			Type: objabi.R_LOONG64_GOT_LO,
  2697  			Off:  int32(c.pc + 4),
  2698  			Siz:  4,
  2699  			Sym:  p.From.Sym,
  2700  		})
  2701  
  2702  	case 66: // am* From, To, RegTo2 ==> am* RegTo2, From, To
  2703  		rk := p.From.Reg
  2704  		rj := p.To.Reg
  2705  		rd := p.RegTo2
  2706  
  2707  		// See section 2.2.7.1 of https://loongson.github.io/LoongArch-Documentation/LoongArch-Vol1-EN.html
  2708  		// for the register usage constraints.
  2709  		if rd == rj || rd == rk {
  2710  			c.ctxt.Diag("illegal register combination: %v\n", p)
  2711  		}
  2712  		o1 = OP_RRR(atomicInst[p.As], uint32(rk), uint32(rj), uint32(rd))
  2713  
  2714  	case 67: // mov $dcon12_0, r
  2715  		v := c.vregoff(&p.From)
  2716  		o1 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(0), uint32(p.To.Reg))
  2717  
  2718  	case 68: // mov $dcon12_20S, r
  2719  		v := c.vregoff(&p.From)
  2720  		contype := c.aclass(&p.From)
  2721  		switch contype {
  2722  		default: // C_DCON12_20S
  2723  			o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(p.To.Reg))
  2724  			o2 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(p.To.Reg), uint32(p.To.Reg))
  2725  		case C_DCON20S_20:
  2726  			o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(p.To.Reg))
  2727  			o2 = OP_IR(c.opir(ALU32ID), uint32(v>>32), uint32(p.To.Reg))
  2728  		case C_DCON12_12S:
  2729  			o1 = OP_12IRR(c.opirr(AADDV), uint32(v), uint32(0), uint32(p.To.Reg))
  2730  			o2 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(p.To.Reg), uint32(p.To.Reg))
  2731  		case C_DCON20S_12S, C_DCON20S_0:
  2732  			o1 = OP_12IRR(c.opirr(AADD), uint32(v), uint32(0), uint32(p.To.Reg))
  2733  			o2 = OP_IR(c.opir(ALU32ID), uint32(v>>32), uint32(p.To.Reg))
  2734  		case C_DCON12_12U:
  2735  			o1 = OP_12IRR(c.opirr(AOR), uint32(v), uint32(0), uint32(p.To.Reg))
  2736  			o2 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(p.To.Reg), uint32(p.To.Reg))
  2737  		case C_DCON20S_12U:
  2738  			o1 = OP_12IRR(c.opirr(AOR), uint32(v), uint32(0), uint32(p.To.Reg))
  2739  			o2 = OP_IR(c.opir(ALU32ID), uint32(v>>32), uint32(p.To.Reg))
  2740  		}
  2741  
  2742  	case 69: // mov $dcon32_12S, r
  2743  		v := c.vregoff(&p.From)
  2744  		contype := c.aclass(&p.From)
  2745  		switch contype {
  2746  		default: // C_DCON32_12S, C_DCON32_0
  2747  			o1 = OP_12IRR(c.opirr(AADD), uint32(v), uint32(0), uint32(p.To.Reg))
  2748  			o2 = OP_IR(c.opir(ALU32ID), uint32(v>>32), uint32(p.To.Reg))
  2749  			o3 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(p.To.Reg), uint32(p.To.Reg))
  2750  		case C_DCON32_20:
  2751  			o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(p.To.Reg))
  2752  			o2 = OP_IR(c.opir(ALU32ID), uint32(v>>32), uint32(p.To.Reg))
  2753  			o3 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(p.To.Reg), uint32(p.To.Reg))
  2754  		case C_DCON12_32S:
  2755  			o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(p.To.Reg))
  2756  			o2 = OP_12IRR(c.opirr(AOR), uint32(v), uint32(p.To.Reg), uint32(p.To.Reg))
  2757  			o3 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(p.To.Reg), uint32(p.To.Reg))
  2758  		case C_DCON20S_32:
  2759  			o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(p.To.Reg))
  2760  			o2 = OP_12IRR(c.opirr(AOR), uint32(v), uint32(p.To.Reg), uint32(p.To.Reg))
  2761  			o3 = OP_IR(c.opir(ALU32ID), uint32(v>>32), uint32(p.To.Reg))
  2762  		case C_DCON32_12U:
  2763  			o1 = OP_12IRR(c.opirr(AOR), uint32(v), uint32(0), uint32(p.To.Reg))
  2764  			o2 = OP_IR(c.opir(ALU32ID), uint32(v>>32), uint32(p.To.Reg))
  2765  			o3 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(p.To.Reg), uint32(p.To.Reg))
  2766  		}
  2767  
  2768  	case 70: // add $dcon12_0,[r1],r2
  2769  		v := c.vregoff(&p.From)
  2770  		r := int(p.Reg)
  2771  		if r == 0 {
  2772  			r = int(p.To.Reg)
  2773  		}
  2774  		o1 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(0), uint32(REGTMP))
  2775  		o2 = OP_RRR(c.oprrr(p.As), uint32(REGTMP), uint32(r), uint32(p.To.Reg))
  2776  
  2777  	case 71: // add $dcon12_20S,[r1],r2
  2778  		v := c.vregoff(&p.From)
  2779  		r := int(p.Reg)
  2780  		if r == 0 {
  2781  			r = int(p.To.Reg)
  2782  		}
  2783  		contype := c.aclass(&p.From)
  2784  		switch contype {
  2785  		default: // C_DCON12_20S
  2786  			o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(REGTMP))
  2787  			o2 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(REGTMP), uint32(REGTMP))
  2788  		case C_DCON20S_20:
  2789  			o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(REGTMP))
  2790  			o2 = OP_IR(c.opir(ALU32ID), uint32(v>>32), uint32(REGTMP))
  2791  		case C_DCON12_12S:
  2792  			o1 = OP_12IRR(c.opirr(AADDV), uint32(v), uint32(0), uint32(REGTMP))
  2793  			o2 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(REGTMP), uint32(REGTMP))
  2794  		case C_DCON20S_12S, C_DCON20S_0:
  2795  			o1 = OP_12IRR(c.opirr(AADD), uint32(v), uint32(0), uint32(REGTMP))
  2796  			o2 = OP_IR(c.opir(ALU32ID), uint32(v>>32), uint32(REGTMP))
  2797  		case C_DCON12_12U:
  2798  			o1 = OP_12IRR(c.opirr(AOR), uint32(v), uint32(0), uint32(REGTMP))
  2799  			o2 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(REGTMP), uint32(REGTMP))
  2800  		case C_DCON20S_12U:
  2801  			o1 = OP_12IRR(c.opirr(AOR), uint32(v), uint32(0), uint32(REGTMP))
  2802  			o2 = OP_IR(c.opir(ALU32ID), uint32(v>>32), uint32(REGTMP))
  2803  		}
  2804  		o3 = OP_RRR(c.oprrr(p.As), uint32(REGTMP), uint32(r), uint32(p.To.Reg))
  2805  
  2806  	case 72: // add $dcon32_12S,[r1],r2
  2807  		v := c.vregoff(&p.From)
  2808  		r := int(p.Reg)
  2809  		if r == 0 {
  2810  			r = int(p.To.Reg)
  2811  		}
  2812  		contype := c.aclass(&p.From)
  2813  		switch contype {
  2814  		default: // C_DCON32_12S, C_DCON32_0
  2815  			o1 = OP_12IRR(c.opirr(AADD), uint32(v), uint32(0), uint32(REGTMP))
  2816  			o2 = OP_IR(c.opir(ALU32ID), uint32(v>>32), uint32(REGTMP))
  2817  			o3 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(REGTMP), uint32(REGTMP))
  2818  		case C_DCON32_20:
  2819  			o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(REGTMP))
  2820  			o2 = OP_IR(c.opir(ALU32ID), uint32(v>>32), uint32(REGTMP))
  2821  			o3 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(REGTMP), uint32(REGTMP))
  2822  		case C_DCON12_32S:
  2823  			o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(REGTMP))
  2824  			o2 = OP_12IRR(c.opirr(AOR), uint32(v), uint32(REGTMP), uint32(REGTMP))
  2825  			o3 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(REGTMP), uint32(REGTMP))
  2826  		case C_DCON20S_32:
  2827  			o1 = OP_IR(c.opir(ALU12IW), uint32(v>>12), uint32(REGTMP))
  2828  			o2 = OP_12IRR(c.opirr(AOR), uint32(v), uint32(REGTMP), uint32(REGTMP))
  2829  			o3 = OP_IR(c.opir(ALU32ID), uint32(v>>32), uint32(REGTMP))
  2830  		case C_DCON32_12U:
  2831  			o1 = OP_12IRR(c.opirr(AOR), uint32(v), uint32(0), uint32(REGTMP))
  2832  			o2 = OP_IR(c.opir(ALU32ID), uint32(v>>32), uint32(REGTMP))
  2833  			o3 = OP_12IRR(c.opirr(ALU52ID), uint32(v>>52), uint32(REGTMP), uint32(REGTMP))
  2834  		}
  2835  		o4 = OP_RRR(c.oprrr(p.As), uint32(REGTMP), uint32(r), uint32(p.To.Reg))
  2836  	}
  2837  
  2838  	out[0] = o1
  2839  	out[1] = o2
  2840  	out[2] = o3
  2841  	out[3] = o4
  2842  	out[4] = o5
  2843  }
  2844  
  2845  // checkoperand checks if operand >= 0 && operand <= maxoperand
  2846  func (c *ctxt0) checkoperand(p *obj.Prog, operand uint32, mask uint32) {
  2847  	if (operand & ^mask) != 0 {
  2848  		c.ctxt.Diag("operand out of range 0 to %d: %v", mask, p)
  2849  	}
  2850  }
  2851  
  2852  // checkindex checks if index >= 0 && index <= maxindex
  2853  func (c *ctxt0) checkindex(p *obj.Prog, index uint32, mask uint32) {
  2854  	if (index & ^mask) != 0 {
  2855  		c.ctxt.Diag("register element index out of range 0 to %d: %v", mask, p)
  2856  	}
  2857  }
  2858  
  2859  func (c *ctxt0) vregoff(a *obj.Addr) int64 {
  2860  	c.instoffset = 0
  2861  	c.aclass(a)
  2862  	return c.instoffset
  2863  }
  2864  
  2865  func (c *ctxt0) regoff(a *obj.Addr) int32 {
  2866  	return int32(c.vregoff(a))
  2867  }
  2868  
  2869  func (c *ctxt0) oprrrr(a obj.As) uint32 {
  2870  	switch a {
  2871  	case AFMADDF:
  2872  		return 0x81 << 20 // fmadd.s
  2873  	case AFMADDD:
  2874  		return 0x82 << 20 // fmadd.d
  2875  	case AFMSUBF:
  2876  		return 0x85 << 20 // fmsub.s
  2877  	case AFMSUBD:
  2878  		return 0x86 << 20 // fmsub.d
  2879  	case AFNMADDF:
  2880  		return 0x89 << 20 // fnmadd.f
  2881  	case AFNMADDD:
  2882  		return 0x8a << 20 // fnmadd.d
  2883  	case AFNMSUBF:
  2884  		return 0x8d << 20 // fnmsub.s
  2885  	case AFNMSUBD:
  2886  		return 0x8e << 20 // fnmsub.d
  2887  	}
  2888  
  2889  	c.ctxt.Diag("bad rrrr opcode %v", a)
  2890  	return 0
  2891  }
  2892  
  2893  func (c *ctxt0) oprrr(a obj.As) uint32 {
  2894  	switch a {
  2895  	case AADD:
  2896  		return 0x20 << 15
  2897  	case AADDU:
  2898  		return 0x20 << 15
  2899  	case ASGT:
  2900  		return 0x24 << 15 // SLT
  2901  	case ASGTU:
  2902  		return 0x25 << 15 // SLTU
  2903  	case AMASKEQZ:
  2904  		return 0x26 << 15
  2905  	case AMASKNEZ:
  2906  		return 0x27 << 15
  2907  	case AAND:
  2908  		return 0x29 << 15
  2909  	case AOR:
  2910  		return 0x2a << 15
  2911  	case AXOR:
  2912  		return 0x2b << 15
  2913  	case AORN:
  2914  		return 0x2c << 15 // orn
  2915  	case AANDN:
  2916  		return 0x2d << 15 // andn
  2917  	case ASUB:
  2918  		return 0x22 << 15
  2919  	case ASUBU, ANEGW:
  2920  		return 0x22 << 15
  2921  	case ANOR:
  2922  		return 0x28 << 15
  2923  	case ASLL:
  2924  		return 0x2e << 15
  2925  	case ASRL:
  2926  		return 0x2f << 15
  2927  	case ASRA:
  2928  		return 0x30 << 15
  2929  	case AROTR:
  2930  		return 0x36 << 15
  2931  	case ASLLV:
  2932  		return 0x31 << 15
  2933  	case ASRLV:
  2934  		return 0x32 << 15
  2935  	case ASRAV:
  2936  		return 0x33 << 15
  2937  	case AROTRV:
  2938  		return 0x37 << 15
  2939  	case AADDV:
  2940  		return 0x21 << 15
  2941  	case AADDVU:
  2942  		return 0x21 << 15
  2943  	case ASUBV:
  2944  		return 0x23 << 15
  2945  	case ASUBVU, ANEGV:
  2946  		return 0x23 << 15
  2947  
  2948  	case AMUL:
  2949  		return 0x38 << 15 // mul.w
  2950  	case AMULU:
  2951  		return 0x38 << 15 // mul.w
  2952  	case AMULH:
  2953  		return 0x39 << 15 // mulh.w
  2954  	case AMULHU:
  2955  		return 0x3a << 15 // mulhu.w
  2956  	case AMULV:
  2957  		return 0x3b << 15 // mul.d
  2958  	case AMULVU:
  2959  		return 0x3b << 15 // mul.d
  2960  	case AMULHV:
  2961  		return 0x3c << 15 // mulh.d
  2962  	case AMULHVU:
  2963  		return 0x3d << 15 // mulhu.d
  2964  	case ADIV:
  2965  		return 0x40 << 15 // div.w
  2966  	case ADIVU:
  2967  		return 0x42 << 15 // div.wu
  2968  	case ADIVV:
  2969  		return 0x44 << 15 // div.d
  2970  	case ADIVVU:
  2971  		return 0x46 << 15 // div.du
  2972  	case AREM:
  2973  		return 0x41 << 15 // mod.w
  2974  	case AREMU:
  2975  		return 0x43 << 15 // mod.wu
  2976  	case AREMV:
  2977  		return 0x45 << 15 // mod.d
  2978  	case AREMVU:
  2979  		return 0x47 << 15 // mod.du
  2980  	case ACRCWBW:
  2981  		return 0x48 << 15 // crc.w.b.w
  2982  	case ACRCWHW:
  2983  		return 0x49 << 15 // crc.w.h.w
  2984  	case ACRCWWW:
  2985  		return 0x4a << 15 // crc.w.w.w
  2986  	case ACRCWVW:
  2987  		return 0x4b << 15 // crc.w.d.w
  2988  	case ACRCCWBW:
  2989  		return 0x4c << 15 // crcc.w.b.w
  2990  	case ACRCCWHW:
  2991  		return 0x4d << 15 // crcc.w.h.w
  2992  	case ACRCCWWW:
  2993  		return 0x4e << 15 // crcc.w.w.w
  2994  	case ACRCCWVW:
  2995  		return 0x4f << 15 // crcc.w.d.w
  2996  	case AJMP:
  2997  		return 0x13 << 26 // jirl r0, rj, 0
  2998  	case AJAL:
  2999  		return (0x13 << 26) | 1 // jirl r1, rj, 0
  3000  
  3001  	case ADIVF:
  3002  		return 0x20d << 15
  3003  	case ADIVD:
  3004  		return 0x20e << 15
  3005  	case AMULF:
  3006  		return 0x209 << 15
  3007  	case AMULD:
  3008  		return 0x20a << 15
  3009  	case ASUBF:
  3010  		return 0x205 << 15
  3011  	case ASUBD:
  3012  		return 0x206 << 15
  3013  	case AADDF:
  3014  		return 0x201 << 15
  3015  	case AADDD:
  3016  		return 0x202 << 15
  3017  	case ACMPEQF:
  3018  		return 0x0c1<<20 | 0x4<<15 // FCMP.CEQ.S
  3019  	case ACMPEQD:
  3020  		return 0x0c2<<20 | 0x4<<15 // FCMP.CEQ.D
  3021  	case ACMPGED:
  3022  		return 0x0c2<<20 | 0x7<<15 // FCMP.SLE.D
  3023  	case ACMPGEF:
  3024  		return 0x0c1<<20 | 0x7<<15 // FCMP.SLE.S
  3025  	case ACMPGTD:
  3026  		return 0x0c2<<20 | 0x3<<15 // FCMP.SLT.D
  3027  	case ACMPGTF:
  3028  		return 0x0c1<<20 | 0x3<<15 // FCMP.SLT.S
  3029  	case AFMINF:
  3030  		return 0x215 << 15 // fmin.s
  3031  	case AFMIND:
  3032  		return 0x216 << 15 // fmin.d
  3033  	case AFMAXF:
  3034  		return 0x211 << 15 // fmax.s
  3035  	case AFMAXD:
  3036  		return 0x212 << 15 // fmax.d
  3037  	case AFMAXAF:
  3038  		return 0x219 << 15 // fmaxa.s
  3039  	case AFMAXAD:
  3040  		return 0x21a << 15 // fmaxa.d
  3041  	case AFMINAF:
  3042  		return 0x21d << 15 // fmina.s
  3043  	case AFMINAD:
  3044  		return 0x21e << 15 // fmina.d
  3045  	case AFSCALEBF:
  3046  		return 0x221 << 15 // fscaleb.s
  3047  	case AFSCALEBD:
  3048  		return 0x222 << 15 // fscaleb.d
  3049  	case AFCOPYSGF:
  3050  		return 0x225 << 15 // fcopysign.s
  3051  	case AFCOPYSGD:
  3052  		return 0x226 << 15 // fcopysign.d
  3053  	case -AMOVB:
  3054  		return 0x07000 << 15 // ldx.b
  3055  	case -AMOVH:
  3056  		return 0x07008 << 15 // ldx.h
  3057  	case -AMOVW:
  3058  		return 0x07010 << 15 // ldx.w
  3059  	case -AMOVV:
  3060  		return 0x07018 << 15 // ldx.d
  3061  	case -AMOVBU:
  3062  		return 0x07040 << 15 // ldx.bu
  3063  	case -AMOVHU:
  3064  		return 0x07048 << 15 // ldx.hu
  3065  	case -AMOVWU:
  3066  		return 0x07050 << 15 // ldx.wu
  3067  	case AMOVB:
  3068  		return 0x07020 << 15 // stx.b
  3069  	case AMOVH:
  3070  		return 0x07028 << 15 // stx.h
  3071  	case AMOVW:
  3072  		return 0x07030 << 15 // stx.w
  3073  	case AMOVV:
  3074  		return 0x07038 << 15 // stx.d
  3075  	case -AMOVF:
  3076  		return 0x07060 << 15 // fldx.s
  3077  	case -AMOVD:
  3078  		return 0x07068 << 15 // fldx.d
  3079  	case AMOVF:
  3080  		return 0x07070 << 15 // fstx.s
  3081  	case AMOVD:
  3082  		return 0x07078 << 15 // fstx.d
  3083  	case -AVMOVQ:
  3084  		return 0x07080 << 15 // vldx
  3085  	case -AXVMOVQ:
  3086  		return 0x07090 << 15 // xvldx
  3087  	case AVMOVQ:
  3088  		return 0x07088 << 15 // vstx
  3089  	case AXVMOVQ:
  3090  		return 0x07098 << 15 // xvstx
  3091  	case AVSEQB:
  3092  		return 0x0e000 << 15 // vseq.b
  3093  	case AXVSEQB:
  3094  		return 0x0e800 << 15 // xvseq.b
  3095  	case AVSEQH:
  3096  		return 0x0e001 << 15 // vseq.h
  3097  	case AXVSEQH:
  3098  		return 0x0e801 << 15 // xvseq.h
  3099  	case AVSEQW:
  3100  		return 0x0e002 << 15 // vseq.w
  3101  	case AXVSEQW:
  3102  		return 0x0e802 << 15 // xvseq.w
  3103  	case AVSEQV:
  3104  		return 0x0e003 << 15 // vseq.d
  3105  	case AXVSEQV:
  3106  		return 0x0e803 << 15 // xvseq.d
  3107  	case AVANDV:
  3108  		return 0x0E24C << 15 // vand.v
  3109  	case AVORV:
  3110  		return 0x0E24D << 15 // vor.v
  3111  	case AVXORV:
  3112  		return 0x0E24E << 15 // vxor.v
  3113  	case AVNORV:
  3114  		return 0x0E24F << 15 // vnor.v
  3115  	case AVANDNV:
  3116  		return 0x0E250 << 15 // vandn.v
  3117  	case AVORNV:
  3118  		return 0x0E251 << 15 // vorn.v
  3119  	case AXVANDV:
  3120  		return 0x0EA4C << 15 // xvand.v
  3121  	case AXVORV:
  3122  		return 0x0EA4D << 15 // xvor.v
  3123  	case AXVXORV:
  3124  		return 0x0EA4E << 15 // xvxor.v
  3125  	case AXVNORV:
  3126  		return 0x0EA4F << 15 // xvnor.v
  3127  	case AXVANDNV:
  3128  		return 0x0EA50 << 15 // xvandn.v
  3129  	case AXVORNV:
  3130  		return 0x0EA51 << 15 // xvorn.v
  3131  	case AVDIVB:
  3132  		return 0xe1c0 << 15 // vdiv.b
  3133  	case AVDIVH:
  3134  		return 0xe1c1 << 15 // vdiv.h
  3135  	case AVDIVW:
  3136  		return 0xe1c2 << 15 // vdiv.w
  3137  	case AVDIVV:
  3138  		return 0xe1c3 << 15 // vdiv.d
  3139  	case AVMODB:
  3140  		return 0xe1c4 << 15 // vmod.b
  3141  	case AVMODH:
  3142  		return 0xe1c5 << 15 // vmod.h
  3143  	case AVMODW:
  3144  		return 0xe1c6 << 15 // vmod.w
  3145  	case AVMODV:
  3146  		return 0xe1c7 << 15 // vmod.d
  3147  	case AVDIVBU:
  3148  		return 0xe1c8 << 15 // vdiv.bu
  3149  	case AVDIVHU:
  3150  		return 0xe1c9 << 15 // vdiv.hu
  3151  	case AVDIVWU:
  3152  		return 0xe1ca << 15 // vdiv.wu
  3153  	case AVDIVVU:
  3154  		return 0xe1cb << 15 // vdiv.du
  3155  	case AVMODBU:
  3156  		return 0xe1cc << 15 // vmod.bu
  3157  	case AVMODHU:
  3158  		return 0xe1cd << 15 // vmod.hu
  3159  	case AVMODWU:
  3160  		return 0xe1ce << 15 // vmod.wu
  3161  	case AVMODVU:
  3162  		return 0xe1cf << 15 // vmod.du
  3163  	case AXVDIVB:
  3164  		return 0xe9c0 << 15 // xvdiv.b
  3165  	case AXVDIVH:
  3166  		return 0xe9c1 << 15 // xvdiv.h
  3167  	case AXVDIVW:
  3168  		return 0xe9c2 << 15 // xvdiv.w
  3169  	case AXVDIVV:
  3170  		return 0xe9c3 << 15 // xvdiv.d
  3171  	case AXVMODB:
  3172  		return 0xe9c4 << 15 // xvmod.b
  3173  	case AXVMODH:
  3174  		return 0xe9c5 << 15 // xvmod.h
  3175  	case AXVMODW:
  3176  		return 0xe9c6 << 15 // xvmod.w
  3177  	case AXVMODV:
  3178  		return 0xe9c7 << 15 // xvmod.d
  3179  	case AXVDIVBU:
  3180  		return 0xe9c8 << 15 // xvdiv.bu
  3181  	case AXVDIVHU:
  3182  		return 0xe9c9 << 15 // xvdiv.hu
  3183  	case AXVDIVWU:
  3184  		return 0xe9ca << 15 // xvdiv.wu
  3185  	case AXVDIVVU:
  3186  		return 0xe9cb << 15 // xvdiv.du
  3187  	case AXVMODBU:
  3188  		return 0xe9cc << 15 // xvmod.bu
  3189  	case AXVMODHU:
  3190  		return 0xe9cd << 15 // xvmod.hu
  3191  	case AXVMODWU:
  3192  		return 0xe9ce << 15 // xvmod.wu
  3193  	case AXVMODVU:
  3194  		return 0xe9cf << 15 // xvmod.du
  3195  	case AVMULWEVHB:
  3196  		return 0xe120 << 15 // vmulwev.h.b
  3197  	case AVMULWEVWH:
  3198  		return 0xe121 << 15 // vmulwev.w.h
  3199  	case AVMULWEVVW:
  3200  		return 0xe122 << 15 // vmulwev.d.w
  3201  	case AVMULWEVQV:
  3202  		return 0xe123 << 15 // vmulwev.q.d
  3203  	case AVMULWODHB:
  3204  		return 0xe124 << 15 // vmulwod.h.b
  3205  	case AVMULWODWH:
  3206  		return 0xe125 << 15 // vmulwod.w.h
  3207  	case AVMULWODVW:
  3208  		return 0xe126 << 15 // vmulwod.d.w
  3209  	case AVMULWODQV:
  3210  		return 0xe127 << 15 // vmulwod.q.d
  3211  	case AVMULWEVHBU:
  3212  		return 0xe130 << 15 // vmulwev.h.bu
  3213  	case AVMULWEVWHU:
  3214  		return 0xe131 << 15 // vmulwev.w.hu
  3215  	case AVMULWEVVWU:
  3216  		return 0xe132 << 15 // vmulwev.d.wu
  3217  	case AVMULWEVQVU:
  3218  		return 0xe133 << 15 // vmulwev.q.du
  3219  	case AVMULWODHBU:
  3220  		return 0xe134 << 15 // vmulwod.h.bu
  3221  	case AVMULWODWHU:
  3222  		return 0xe135 << 15 // vmulwod.w.hu
  3223  	case AVMULWODVWU:
  3224  		return 0xe136 << 15 // vmulwod.d.wu
  3225  	case AVMULWODQVU:
  3226  		return 0xe137 << 15 // vmulwod.q.du
  3227  	case AVMULWEVHBUB:
  3228  		return 0xe140 << 15 // vmulwev.h.bu.b
  3229  	case AVMULWEVWHUH:
  3230  		return 0xe141 << 15 // vmulwev.w.hu.h
  3231  	case AVMULWEVVWUW:
  3232  		return 0xe142 << 15 // vmulwev.d.wu.w
  3233  	case AVMULWEVQVUV:
  3234  		return 0xe143 << 15 // vmulwev.q.du.d
  3235  	case AVMULWODHBUB:
  3236  		return 0xe144 << 15 // vmulwod.h.bu.b
  3237  	case AVMULWODWHUH:
  3238  		return 0xe145 << 15 // vmulwod.w.hu.h
  3239  	case AVMULWODVWUW:
  3240  		return 0xe146 << 15 // vmulwod.d.wu.w
  3241  	case AVMULWODQVUV:
  3242  		return 0xe147 << 15 // vmulwod.q.du.d
  3243  	case AXVMULWEVHB:
  3244  		return 0xe920 << 15 // xvmulwev.h.b
  3245  	case AXVMULWEVWH:
  3246  		return 0xe921 << 15 // xvmulwev.w.h
  3247  	case AXVMULWEVVW:
  3248  		return 0xe922 << 15 // xvmulwev.d.w
  3249  	case AXVMULWEVQV:
  3250  		return 0xe923 << 15 // xvmulwev.q.d
  3251  	case AXVMULWODHB:
  3252  		return 0xe924 << 15 // xvmulwod.h.b
  3253  	case AXVMULWODWH:
  3254  		return 0xe925 << 15 // xvmulwod.w.h
  3255  	case AXVMULWODVW:
  3256  		return 0xe926 << 15 // xvmulwod.d.w
  3257  	case AXVMULWODQV:
  3258  		return 0xe927 << 15 // xvmulwod.q.d
  3259  	case AXVMULWEVHBU:
  3260  		return 0xe930 << 15 // xvmulwev.h.bu
  3261  	case AXVMULWEVWHU:
  3262  		return 0xe931 << 15 // xvmulwev.w.hu
  3263  	case AXVMULWEVVWU:
  3264  		return 0xe932 << 15 // xvmulwev.d.wu
  3265  	case AXVMULWEVQVU:
  3266  		return 0xe933 << 15 // xvmulwev.q.du
  3267  	case AXVMULWODHBU:
  3268  		return 0xe934 << 15 // xvmulwod.h.bu
  3269  	case AXVMULWODWHU:
  3270  		return 0xe935 << 15 // xvmulwod.w.hu
  3271  	case AXVMULWODVWU:
  3272  		return 0xe936 << 15 // xvmulwod.d.wu
  3273  	case AXVMULWODQVU:
  3274  		return 0xe937 << 15 // xvmulwod.q.du
  3275  	case AXVMULWEVHBUB:
  3276  		return 0xe940 << 15 // xvmulwev.h.bu.b
  3277  	case AXVMULWEVWHUH:
  3278  		return 0xe941 << 15 // xvmulwev.w.hu.h
  3279  	case AXVMULWEVVWUW:
  3280  		return 0xe942 << 15 // xvmulwev.d.wu.w
  3281  	case AXVMULWEVQVUV:
  3282  		return 0xe943 << 15 // xvmulwev.q.du.d
  3283  	case AXVMULWODHBUB:
  3284  		return 0xe944 << 15 // xvmulwod.h.bu.b
  3285  	case AXVMULWODWHUH:
  3286  		return 0xe945 << 15 // xvmulwod.w.hu.h
  3287  	case AXVMULWODVWUW:
  3288  		return 0xe946 << 15 // xvmulwod.d.wu.w
  3289  	case AXVMULWODQVUV:
  3290  		return 0xe947 << 15 // xvmulwod.q.du.d
  3291  	case AVSLLB:
  3292  		return 0xe1d0 << 15 // vsll.b
  3293  	case AVSLLH:
  3294  		return 0xe1d1 << 15 // vsll.h
  3295  	case AVSLLW:
  3296  		return 0xe1d2 << 15 // vsll.w
  3297  	case AVSLLV:
  3298  		return 0xe1d3 << 15 // vsll.d
  3299  	case AVSRLB:
  3300  		return 0xe1d4 << 15 // vsrl.b
  3301  	case AVSRLH:
  3302  		return 0xe1d5 << 15 // vsrl.h
  3303  	case AVSRLW:
  3304  		return 0xe1d6 << 15 // vsrl.w
  3305  	case AVSRLV:
  3306  		return 0xe1d7 << 15 // vsrl.d
  3307  	case AVSRAB:
  3308  		return 0xe1d8 << 15 // vsra.b
  3309  	case AVSRAH:
  3310  		return 0xe1d9 << 15 // vsra.h
  3311  	case AVSRAW:
  3312  		return 0xe1da << 15 // vsra.w
  3313  	case AVSRAV:
  3314  		return 0xe1db << 15 // vsra.d
  3315  	case AVROTRB:
  3316  		return 0xe1dc << 15 // vrotr.b
  3317  	case AVROTRH:
  3318  		return 0xe1dd << 15 // vrotr.h
  3319  	case AVROTRW:
  3320  		return 0xe1de << 15 // vrotr.w
  3321  	case AVROTRV:
  3322  		return 0xe1df << 15 // vrotr.d
  3323  	case AXVSLLB:
  3324  		return 0xe9d0 << 15 // xvsll.b
  3325  	case AXVSLLH:
  3326  		return 0xe9d1 << 15 // xvsll.h
  3327  	case AXVSLLW:
  3328  		return 0xe9d2 << 15 // xvsll.w
  3329  	case AXVSLLV:
  3330  		return 0xe9d3 << 15 // xvsll.d
  3331  	case AXVSRLB:
  3332  		return 0xe9d4 << 15 // xvsrl.b
  3333  	case AXVSRLH:
  3334  		return 0xe9d5 << 15 // xvsrl.h
  3335  	case AXVSRLW:
  3336  		return 0xe9d6 << 15 // xvsrl.w
  3337  	case AXVSRLV:
  3338  		return 0xe9d7 << 15 // xvsrl.d
  3339  	case AXVSRAB:
  3340  		return 0xe9d8 << 15 // xvsra.b
  3341  	case AXVSRAH:
  3342  		return 0xe9d9 << 15 // xvsra.h
  3343  	case AXVSRAW:
  3344  		return 0xe9da << 15 // xvsra.w
  3345  	case AXVSRAV:
  3346  		return 0xe9db << 15 // xvsra.d
  3347  	case AXVROTRB:
  3348  		return 0xe9dc << 15 // xvrotr.b
  3349  	case AXVROTRH:
  3350  		return 0xe9dd << 15 // xvrotr.h
  3351  	case AXVROTRW:
  3352  		return 0xe9de << 15 // xvrotr.w
  3353  	case AXVROTRV:
  3354  		return 0xe9df << 15 // xvrotr.d
  3355  	case AVADDB:
  3356  		return 0xe014 << 15 // vadd.b
  3357  	case AVADDH:
  3358  		return 0xe015 << 15 // vadd.h
  3359  	case AVADDW:
  3360  		return 0xe016 << 15 // vadd.w
  3361  	case AVADDV:
  3362  		return 0xe017 << 15 // vadd.d
  3363  	case AVADDQ:
  3364  		return 0xe25a << 15 // vadd.q
  3365  	case AVSUBB:
  3366  		return 0xe018 << 15 // vsub.b
  3367  	case AVSUBH:
  3368  		return 0xe019 << 15 // vsub.h
  3369  	case AVSUBW:
  3370  		return 0xe01a << 15 // vsub.w
  3371  	case AVSUBV:
  3372  		return 0xe01b << 15 // vsub.d
  3373  	case AVSUBQ:
  3374  		return 0xe25b << 15 // vsub.q
  3375  	case AXVADDB:
  3376  		return 0xe814 << 15 // xvadd.b
  3377  	case AXVADDH:
  3378  		return 0xe815 << 15 // xvadd.h
  3379  	case AXVADDW:
  3380  		return 0xe816 << 15 // xvadd.w
  3381  	case AXVADDV:
  3382  		return 0xe817 << 15 // xvadd.d
  3383  	case AXVADDQ:
  3384  		return 0xea5a << 15 // xvadd.q
  3385  	case AXVSUBB:
  3386  		return 0xe818 << 15 // xvsub.b
  3387  	case AXVSUBH:
  3388  		return 0xe819 << 15 // xvsub.h
  3389  	case AXVSUBW:
  3390  		return 0xe81a << 15 // xvsub.w
  3391  	case AXVSUBV:
  3392  		return 0xe81b << 15 // xvsub.d
  3393  	case AXVSUBQ:
  3394  		return 0xea5b << 15 // xvsub.q
  3395  	case AVILVLB:
  3396  		return 0xe234 << 15 // vilvl.b
  3397  	case AVILVLH:
  3398  		return 0xe235 << 15 // vilvl.h
  3399  	case AVILVLW:
  3400  		return 0xe236 << 15 // vilvl.w
  3401  	case AVILVLV:
  3402  		return 0xe237 << 15 // vilvl.d
  3403  	case AVILVHB:
  3404  		return 0xe238 << 15 // vilvh.b
  3405  	case AVILVHH:
  3406  		return 0xe239 << 15 // vilvh.h
  3407  	case AVILVHW:
  3408  		return 0xe23a << 15 // vilvh.w
  3409  	case AVILVHV:
  3410  		return 0xe23b << 15 // vilvh.d
  3411  	case AXVILVLB:
  3412  		return 0xea34 << 15 // xvilvl.b
  3413  	case AXVILVLH:
  3414  		return 0xea35 << 15 // xvilvl.h
  3415  	case AXVILVLW:
  3416  		return 0xea36 << 15 // xvilvl.w
  3417  	case AXVILVLV:
  3418  		return 0xea37 << 15 // xvilvl.d
  3419  	case AXVILVHB:
  3420  		return 0xea38 << 15 // xvilvh.b
  3421  	case AXVILVHH:
  3422  		return 0xea39 << 15 // xvilvh.h
  3423  	case AXVILVHW:
  3424  		return 0xea3a << 15 // xvilvh.w
  3425  	case AXVILVHV:
  3426  		return 0xea3b << 15 // xvilvh.d
  3427  	case AVMULB:
  3428  		return 0xe108 << 15 // vmul.b
  3429  	case AVMULH:
  3430  		return 0xe109 << 15 // vmul.h
  3431  	case AVMULW:
  3432  		return 0xe10a << 15 // vmul.w
  3433  	case AVMULV:
  3434  		return 0xe10b << 15 // vmul.d
  3435  	case AVMUHB:
  3436  		return 0xe10c << 15 // vmuh.b
  3437  	case AVMUHH:
  3438  		return 0xe10d << 15 // vmuh.h
  3439  	case AVMUHW:
  3440  		return 0xe10e << 15 // vmuh.w
  3441  	case AVMUHV:
  3442  		return 0xe10f << 15 // vmuh.d
  3443  	case AVMUHBU:
  3444  		return 0xe110 << 15 // vmuh.bu
  3445  	case AVMUHHU:
  3446  		return 0xe111 << 15 // vmuh.hu
  3447  	case AVMUHWU:
  3448  		return 0xe112 << 15 // vmuh.wu
  3449  	case AVMUHVU:
  3450  		return 0xe113 << 15 // vmuh.du
  3451  	case AXVMULB:
  3452  		return 0xe908 << 15 // xvmul.b
  3453  	case AXVMULH:
  3454  		return 0xe909 << 15 // xvmul.h
  3455  	case AXVMULW:
  3456  		return 0xe90a << 15 // xvmul.w
  3457  	case AXVMULV:
  3458  		return 0xe90b << 15 // xvmul.d
  3459  	case AXVMUHB:
  3460  		return 0xe90c << 15 // xvmuh.b
  3461  	case AXVMUHH:
  3462  		return 0xe90d << 15 // xvmuh.h
  3463  	case AXVMUHW:
  3464  		return 0xe90e << 15 // xvmuh.w
  3465  	case AXVMUHV:
  3466  		return 0xe90f << 15 // xvmuh.d
  3467  	case AXVMUHBU:
  3468  		return 0xe910 << 15 // xvmuh.bu
  3469  	case AXVMUHHU:
  3470  		return 0xe911 << 15 // xvmuh.hu
  3471  	case AXVMUHWU:
  3472  		return 0xe912 << 15 // xvmuh.wu
  3473  	case AXVMUHVU:
  3474  		return 0xe913 << 15 // xvmuh.du
  3475  	case AVADDF:
  3476  		return 0xe261 << 15 // vfadd.s
  3477  	case AVADDD:
  3478  		return 0xe262 << 15 // vfadd.d
  3479  	case AVSUBF:
  3480  		return 0xe265 << 15 // vfsub.s
  3481  	case AVSUBD:
  3482  		return 0xe266 << 15 // vfsub.d
  3483  	case AVMULF:
  3484  		return 0xe271 << 15 // vfmul.s
  3485  	case AVMULD:
  3486  		return 0xe272 << 15 // vfmul.d
  3487  	case AVDIVF:
  3488  		return 0xe275 << 15 // vfdiv.s
  3489  	case AVDIVD:
  3490  		return 0xe276 << 15 // vfdiv.d
  3491  	case AXVADDF:
  3492  		return 0xea61 << 15 // xvfadd.s
  3493  	case AXVADDD:
  3494  		return 0xea62 << 15 // xvfadd.d
  3495  	case AXVSUBF:
  3496  		return 0xea65 << 15 // xvfsub.s
  3497  	case AXVSUBD:
  3498  		return 0xea66 << 15 // xvfsub.d
  3499  	case AXVMULF:
  3500  		return 0xea71 << 15 // xvfmul.s
  3501  	case AXVMULD:
  3502  		return 0xea72 << 15 // xvfmul.d
  3503  	case AXVDIVF:
  3504  		return 0xea75 << 15 // xvfdiv.s
  3505  	case AXVDIVD:
  3506  		return 0xea76 << 15 // xvfdiv.d
  3507  	}
  3508  
  3509  	if a < 0 {
  3510  		c.ctxt.Diag("bad rrr opcode -%v", -a)
  3511  	} else {
  3512  		c.ctxt.Diag("bad rrr opcode %v", a)
  3513  	}
  3514  	return 0
  3515  }
  3516  
  3517  func (c *ctxt0) oprr(a obj.As) uint32 {
  3518  	switch a {
  3519  	case ACLOW:
  3520  		return 0x4 << 10 // clo.w
  3521  	case ACLZW:
  3522  		return 0x5 << 10 // clz.w
  3523  	case ACTOW:
  3524  		return 0x6 << 10 // cto.w
  3525  	case ACTZW:
  3526  		return 0x7 << 10 // ctz.w
  3527  	case ACLOV:
  3528  		return 0x8 << 10 // clo.d
  3529  	case ACLZV:
  3530  		return 0x9 << 10 // clz.d
  3531  	case ACTOV:
  3532  		return 0xa << 10 // cto.d
  3533  	case ACTZV:
  3534  		return 0xb << 10 // ctz.d
  3535  	case AREVB2H:
  3536  		return 0xc << 10 // revb.2h
  3537  	case AREVB4H:
  3538  		return 0xd << 10 // revb.4h
  3539  	case AREVB2W:
  3540  		return 0xe << 10 // revb.2w
  3541  	case AREVBV:
  3542  		return 0xf << 10 // revb.d
  3543  	case AREVH2W:
  3544  		return 0x10 << 10 // revh.2w
  3545  	case AREVHV:
  3546  		return 0x11 << 10 // revh.d
  3547  	case ABITREV4B:
  3548  		return 0x12 << 10 // bitrev.4b
  3549  	case ABITREV8B:
  3550  		return 0x13 << 10 // bitrev.8b
  3551  	case ABITREVW:
  3552  		return 0x14 << 10 // bitrev.w
  3553  	case ABITREVV:
  3554  		return 0x15 << 10 // bitrev.d
  3555  	case AEXTWH:
  3556  		return 0x16 << 10 // ext.w.h
  3557  	case AEXTWB:
  3558  		return 0x17 << 10 // ext.w.h
  3559  	case ACPUCFG:
  3560  		return 0x1b << 10
  3561  	case ARDTIMELW:
  3562  		return 0x18 << 10
  3563  	case ARDTIMEHW:
  3564  		return 0x19 << 10
  3565  	case ARDTIMED:
  3566  		return 0x1a << 10
  3567  	case ATRUNCFV:
  3568  		return 0x46a9 << 10
  3569  	case ATRUNCDV:
  3570  		return 0x46aa << 10
  3571  	case ATRUNCFW:
  3572  		return 0x46a1 << 10
  3573  	case ATRUNCDW:
  3574  		return 0x46a2 << 10
  3575  	case AMOVFV:
  3576  		return 0x46c9 << 10
  3577  	case AMOVDV:
  3578  		return 0x46ca << 10
  3579  	case AMOVVF:
  3580  		return 0x4746 << 10
  3581  	case AMOVVD:
  3582  		return 0x474a << 10
  3583  	case AMOVFW:
  3584  		return 0x46c1 << 10
  3585  	case AMOVDW:
  3586  		return 0x46c2 << 10
  3587  	case AMOVWF:
  3588  		return 0x4744 << 10
  3589  	case AMOVDF:
  3590  		return 0x4646 << 10
  3591  	case AMOVWD:
  3592  		return 0x4748 << 10
  3593  	case AMOVFD:
  3594  		return 0x4649 << 10
  3595  	case AABSF:
  3596  		return 0x4501 << 10
  3597  	case AABSD:
  3598  		return 0x4502 << 10
  3599  	case AMOVF:
  3600  		return 0x4525 << 10
  3601  	case AMOVD:
  3602  		return 0x4526 << 10
  3603  	case ANEGF:
  3604  		return 0x4505 << 10
  3605  	case ANEGD:
  3606  		return 0x4506 << 10
  3607  	case ASQRTF:
  3608  		return 0x4511 << 10
  3609  	case ASQRTD:
  3610  		return 0x4512 << 10
  3611  	case AFLOGBF:
  3612  		return 0x4509 << 10 // flogb.s
  3613  	case AFLOGBD:
  3614  		return 0x450a << 10 // flogb.d
  3615  	case AFCLASSF:
  3616  		return 0x450d << 10 // fclass.s
  3617  	case AFCLASSD:
  3618  		return 0x450e << 10 // fclass.d
  3619  	case AFFINTFW:
  3620  		return 0x4744 << 10 // ffint.s.w
  3621  	case AFFINTFV:
  3622  		return 0x4746 << 10 // ffint.s.l
  3623  	case AFFINTDW:
  3624  		return 0x4748 << 10 // ffint.d.w
  3625  	case AFFINTDV:
  3626  		return 0x474a << 10 // ffint.d.l
  3627  	case AFTINTWF:
  3628  		return 0x46c1 << 10 // ftint.w.s
  3629  	case AFTINTWD:
  3630  		return 0x46c2 << 10 // ftint.w.d
  3631  	case AFTINTVF:
  3632  		return 0x46c9 << 10 // ftint.l.s
  3633  	case AFTINTVD:
  3634  		return 0x46ca << 10 // ftint.l.d
  3635  	case AFTINTRMWF:
  3636  		return 0x4681 << 10 // ftintrm.w.s
  3637  	case AFTINTRMWD:
  3638  		return 0x4682 << 10 // ftintrm.w.d
  3639  	case AFTINTRMVF:
  3640  		return 0x4689 << 10 // ftintrm.l.s
  3641  	case AFTINTRMVD:
  3642  		return 0x468a << 10 // ftintrm.l.d
  3643  	case AFTINTRPWF:
  3644  		return 0x4691 << 10 // ftintrp.w.s
  3645  	case AFTINTRPWD:
  3646  		return 0x4692 << 10 // ftintrp.w.d
  3647  	case AFTINTRPVF:
  3648  		return 0x4699 << 10 // ftintrp.l.s
  3649  	case AFTINTRPVD:
  3650  		return 0x469a << 10 // ftintrp.l.d
  3651  	case AFTINTRZWF:
  3652  		return 0x46a1 << 10 // ftintrz.w.s
  3653  	case AFTINTRZWD:
  3654  		return 0x46a2 << 10 // ftintrz.w.d
  3655  	case AFTINTRZVF:
  3656  		return 0x46a9 << 10 // ftintrz.l.s
  3657  	case AFTINTRZVD:
  3658  		return 0x46aa << 10 // ftintrz.l.d
  3659  	case AFTINTRNEWF:
  3660  		return 0x46b1 << 10 // ftintrne.w.s
  3661  	case AFTINTRNEWD:
  3662  		return 0x46b2 << 10 // ftintrne.w.d
  3663  	case AFTINTRNEVF:
  3664  		return 0x46b9 << 10 // ftintrne.l.s
  3665  	case AFTINTRNEVD:
  3666  		return 0x46ba << 10 // ftintrne.l.d
  3667  	case AVPCNTB:
  3668  		return 0x1ca708 << 10 // vpcnt.b
  3669  	case AVPCNTH:
  3670  		return 0x1ca709 << 10 // vpcnt.h
  3671  	case AVPCNTW:
  3672  		return 0x1ca70a << 10 // vpcnt.w
  3673  	case AVPCNTV:
  3674  		return 0x1ca70b << 10 // vpcnt.v
  3675  	case AXVPCNTB:
  3676  		return 0x1da708 << 10 // xvpcnt.b
  3677  	case AXVPCNTH:
  3678  		return 0x1da709 << 10 // xvpcnt.h
  3679  	case AXVPCNTW:
  3680  		return 0x1da70a << 10 // xvpcnt.w
  3681  	case AXVPCNTV:
  3682  		return 0x1da70b << 10 // xvpcnt.v
  3683  	case AVFSQRTF:
  3684  		return 0x1ca739 << 10 // vfsqrt.s
  3685  	case AVFSQRTD:
  3686  		return 0x1ca73a << 10 // vfsqrt.d
  3687  	case AVFRECIPF:
  3688  		return 0x1ca73d << 10 // vfrecip.s
  3689  	case AVFRECIPD:
  3690  		return 0x1ca73e << 10 // vfrecip.d
  3691  	case AVFRSQRTF:
  3692  		return 0x1ca741 << 10 // vfrsqrt.s
  3693  	case AVFRSQRTD:
  3694  		return 0x1ca742 << 10 // vfrsqrt.d
  3695  	case AXVFSQRTF:
  3696  		return 0x1da739 << 10 // xvfsqrt.s
  3697  	case AXVFSQRTD:
  3698  		return 0x1da73a << 10 // xvfsqrt.d
  3699  	case AXVFRECIPF:
  3700  		return 0x1da73d << 10 // xvfrecip.s
  3701  	case AXVFRECIPD:
  3702  		return 0x1da73e << 10 // xvfrecip.d
  3703  	case AXVFRSQRTF:
  3704  		return 0x1da741 << 10 // xvfrsqrt.s
  3705  	case AXVFRSQRTD:
  3706  		return 0x1da742 << 10 // xvfrsqrt.d
  3707  	case AVNEGB:
  3708  		return 0x1ca70c << 10 // vneg.b
  3709  	case AVNEGH:
  3710  		return 0x1ca70d << 10 // vneg.h
  3711  	case AVNEGW:
  3712  		return 0x1ca70e << 10 // vneg.w
  3713  	case AVNEGV:
  3714  		return 0x1ca70f << 10 // vneg.d
  3715  	case AXVNEGB:
  3716  		return 0x1da70c << 10 // xvneg.b
  3717  	case AXVNEGH:
  3718  		return 0x1da70d << 10 // xvneg.h
  3719  	case AXVNEGW:
  3720  		return 0x1da70e << 10 // xvneg.w
  3721  	case AXVNEGV:
  3722  		return 0x1da70f << 10 // xvneg.d
  3723  	case AVFRINTRNEF:
  3724  		return 0x1ca75d << 10 // vfrintrne.s
  3725  	case AVFRINTRNED:
  3726  		return 0x1ca75e << 10 // vfrintrne.d
  3727  	case AVFRINTRZF:
  3728  		return 0x1ca759 << 10 // vfrintrz.s
  3729  	case AVFRINTRZD:
  3730  		return 0x1ca75a << 10 // vfrintrz.d
  3731  	case AVFRINTRPF:
  3732  		return 0x1ca755 << 10 // vfrintrp.s
  3733  	case AVFRINTRPD:
  3734  		return 0x1ca756 << 10 // vfrintrp.d
  3735  	case AVFRINTRMF:
  3736  		return 0x1ca751 << 10 // vfrintrm.s
  3737  	case AVFRINTRMD:
  3738  		return 0x1ca752 << 10 // vfrintrm.d
  3739  	case AVFRINTF:
  3740  		return 0x1ca74d << 10 // vfrint.s
  3741  	case AVFRINTD:
  3742  		return 0x1ca74e << 10 // vfrint.d
  3743  	case AXVFRINTRNEF:
  3744  		return 0x1da75d << 10 // xvfrintrne.s
  3745  	case AXVFRINTRNED:
  3746  		return 0x1da75e << 10 // xvfrintrne.d
  3747  	case AXVFRINTRZF:
  3748  		return 0x1da759 << 10 // xvfrintrz.s
  3749  	case AXVFRINTRZD:
  3750  		return 0x1da75a << 10 // xvfrintrz.d
  3751  	case AXVFRINTRPF:
  3752  		return 0x1da755 << 10 // xvfrintrp.s
  3753  	case AXVFRINTRPD:
  3754  		return 0x1da756 << 10 // xvfrintrp.d
  3755  	case AXVFRINTRMF:
  3756  		return 0x1da751 << 10 // xvfrintrm.s
  3757  	case AXVFRINTRMD:
  3758  		return 0x1da752 << 10 // xvfrintrm.d
  3759  	case AXVFRINTF:
  3760  		return 0x1da74d << 10 // xvfrint.s
  3761  	case AXVFRINTD:
  3762  		return 0x1da74e << 10 // xvfrint.d
  3763  	case AVFCLASSF:
  3764  		return 0x1ca735 << 10 // vfclass.s
  3765  	case AVFCLASSD:
  3766  		return 0x1ca736 << 10 // vfclass.d
  3767  	case AXVFCLASSF:
  3768  		return 0x1da735 << 10 // xvfclass.s
  3769  	case AXVFCLASSD:
  3770  		return 0x1da736 << 10 // xvfclass.d
  3771  	case AVSETEQV:
  3772  		return 0x1ca726<<10 | 0x0<<3 // vseteqz.v
  3773  	case AVSETNEV:
  3774  		return 0x1ca727<<10 | 0x0<<3 // vsetnez.v
  3775  	case AVSETANYEQB:
  3776  		return 0x1ca728<<10 | 0x0<<3 // vsetanyeqz.b
  3777  	case AVSETANYEQH:
  3778  		return 0x1ca729<<10 | 0x0<<3 // vsetanyeqz.h
  3779  	case AVSETANYEQW:
  3780  		return 0x1ca72a<<10 | 0x0<<3 // vsetanyeqz.w
  3781  	case AVSETANYEQV:
  3782  		return 0x1ca72b<<10 | 0x0<<3 // vsetanyeqz.d
  3783  	case AVSETALLNEB:
  3784  		return 0x1ca72c<<10 | 0x0<<3 // vsetallnez.b
  3785  	case AVSETALLNEH:
  3786  		return 0x1ca72d<<10 | 0x0<<3 // vsetallnez.h
  3787  	case AVSETALLNEW:
  3788  		return 0x1ca72e<<10 | 0x0<<3 // vsetallnez.w
  3789  	case AVSETALLNEV:
  3790  		return 0x1ca72f<<10 | 0x0<<3 // vsetallnez.d
  3791  	case AXVSETEQV:
  3792  		return 0x1da726<<10 | 0x0<<3 // xvseteqz.v
  3793  	case AXVSETNEV:
  3794  		return 0x1da727<<10 | 0x0<<3 // xvsetnez.v
  3795  	case AXVSETANYEQB:
  3796  		return 0x1da728<<10 | 0x0<<3 // xvsetanyeqz.b
  3797  	case AXVSETANYEQH:
  3798  		return 0x1da729<<10 | 0x0<<3 // xvsetanyeqz.h
  3799  	case AXVSETANYEQW:
  3800  		return 0x1da72a<<10 | 0x0<<3 // xvsetanyeqz.w
  3801  	case AXVSETANYEQV:
  3802  		return 0x1da72b<<10 | 0x0<<3 // xvsetanyeqz.d
  3803  	case AXVSETALLNEB:
  3804  		return 0x1da72c<<10 | 0x0<<3 // xvsetallnez.b
  3805  	case AXVSETALLNEH:
  3806  		return 0x1da72d<<10 | 0x0<<3 // xvsetallnez.h
  3807  	case AXVSETALLNEW:
  3808  		return 0x1da72e<<10 | 0x0<<3 // xvsetallnez.w
  3809  	case AXVSETALLNEV:
  3810  		return 0x1da72f<<10 | 0x0<<3 // xvsetallnez.d
  3811  	}
  3812  
  3813  	c.ctxt.Diag("bad rr opcode %v", a)
  3814  	return 0
  3815  }
  3816  
  3817  func (c *ctxt0) opi(a obj.As) uint32 {
  3818  	switch a {
  3819  	case ASYSCALL:
  3820  		return 0x56 << 15
  3821  	case ABREAK:
  3822  		return 0x54 << 15
  3823  	case ADBAR:
  3824  		return 0x70e4 << 15
  3825  	}
  3826  
  3827  	c.ctxt.Diag("bad ic opcode %v", a)
  3828  
  3829  	return 0
  3830  }
  3831  
  3832  func (c *ctxt0) opir(a obj.As) uint32 {
  3833  	switch a {
  3834  	case ALU12IW:
  3835  		return 0x0a << 25
  3836  	case ALU32ID:
  3837  		return 0x0b << 25
  3838  	case APCALAU12I:
  3839  		return 0x0d << 25
  3840  	case APCADDU12I:
  3841  		return 0x0e << 25
  3842  	}
  3843  	return 0
  3844  }
  3845  
  3846  func (c *ctxt0) opirr(a obj.As) uint32 {
  3847  	switch a {
  3848  	case AADD, AADDU:
  3849  		return 0x00a << 22
  3850  	case ASGT:
  3851  		return 0x008 << 22
  3852  	case ASGTU:
  3853  		return 0x009 << 22
  3854  	case AAND:
  3855  		return 0x00d << 22
  3856  	case AOR:
  3857  		return 0x00e << 22
  3858  	case ALU52ID:
  3859  		return 0x00c << 22
  3860  	case AXOR:
  3861  		return 0x00f << 22
  3862  	case ASLL:
  3863  		return 0x00081 << 15
  3864  	case ASRL:
  3865  		return 0x00089 << 15
  3866  	case ASRA:
  3867  		return 0x00091 << 15
  3868  	case AROTR:
  3869  		return 0x00099 << 15
  3870  	case AADDV:
  3871  		return 0x00b << 22
  3872  	case AADDVU:
  3873  		return 0x00b << 22
  3874  
  3875  	case AJMP:
  3876  		return 0x14 << 26
  3877  	case AJAL,
  3878  		obj.ADUFFZERO,
  3879  		obj.ADUFFCOPY:
  3880  		return 0x15 << 26
  3881  
  3882  	case AJIRL:
  3883  		return 0x13 << 26
  3884  	case ABLTU:
  3885  		return 0x1a << 26
  3886  	case ABLT, ABLTZ, ABGTZ:
  3887  		return 0x18 << 26
  3888  	case ABGEU:
  3889  		return 0x1b << 26
  3890  	case ABGE, ABGEZ, ABLEZ:
  3891  		return 0x19 << 26
  3892  	case -ABEQ: // beqz
  3893  		return 0x10 << 26
  3894  	case -ABNE: // bnez
  3895  		return 0x11 << 26
  3896  	case ABEQ:
  3897  		return 0x16 << 26
  3898  	case ABNE:
  3899  		return 0x17 << 26
  3900  	case ABFPT:
  3901  		return 0x12<<26 | 0x1<<8
  3902  	case ABFPF:
  3903  		return 0x12<<26 | 0x0<<8
  3904  	case APRELDX:
  3905  		return 0x07058 << 15 // preldx
  3906  	case AMOVB,
  3907  		AMOVBU:
  3908  		return 0x0a4 << 22
  3909  	case AMOVH,
  3910  		AMOVHU:
  3911  		return 0x0a5 << 22
  3912  	case AMOVW,
  3913  		AMOVWU:
  3914  		return 0x0a6 << 22
  3915  	case AMOVV:
  3916  		return 0x0a7 << 22
  3917  	case AMOVF:
  3918  		return 0x0ad << 22
  3919  	case AMOVD:
  3920  		return 0x0af << 22
  3921  	case -AMOVB:
  3922  		return 0x0a0 << 22
  3923  	case -AMOVBU:
  3924  		return 0x0a8 << 22
  3925  	case -AMOVH:
  3926  		return 0x0a1 << 22
  3927  	case -AMOVHU:
  3928  		return 0x0a9 << 22
  3929  	case -AMOVW:
  3930  		return 0x0a2 << 22
  3931  	case -AMOVWU:
  3932  		return 0x0aa << 22
  3933  	case -AMOVV:
  3934  		return 0x0a3 << 22
  3935  	case -AMOVF:
  3936  		return 0x0ac << 22
  3937  	case -AMOVD:
  3938  		return 0x0ae << 22
  3939  	case -AVMOVQ:
  3940  		return 0x0b0 << 22 // vld
  3941  	case -AXVMOVQ:
  3942  		return 0x0b2 << 22 // xvld
  3943  	case AVMOVQ:
  3944  		return 0x0b1 << 22 // vst
  3945  	case AXVMOVQ:
  3946  		return 0x0b3 << 22 // xvst
  3947  	case ASLLV:
  3948  		return 0x0041 << 16
  3949  	case ASRLV:
  3950  		return 0x0045 << 16
  3951  	case ASRAV:
  3952  		return 0x0049 << 16
  3953  	case AROTRV:
  3954  		return 0x004d << 16
  3955  	case -ALL:
  3956  		return 0x020 << 24
  3957  	case -ALLV:
  3958  		return 0x022 << 24
  3959  	case ASC:
  3960  		return 0x021 << 24
  3961  	case ASCV:
  3962  		return 0x023 << 24
  3963  	case AVANDB:
  3964  		return 0x1CF4 << 18 // vandi.b
  3965  	case AVORB:
  3966  		return 0x1CF5 << 18 // vori.b
  3967  	case AVXORB:
  3968  		return 0x1CF6 << 18 // xori.b
  3969  	case AVNORB:
  3970  		return 0x1CF7 << 18 // xnori.b
  3971  	case AXVANDB:
  3972  		return 0x1DF4 << 18 // xvandi.b
  3973  	case AXVORB:
  3974  		return 0x1DF5 << 18 // xvori.b
  3975  	case AXVXORB:
  3976  		return 0x1DF6 << 18 // xvxori.b
  3977  	case AXVNORB:
  3978  		return 0x1DF7 << 18 // xvnor.b
  3979  	case AVSEQB:
  3980  		return 0x0E500 << 15 //vseqi.b
  3981  	case AVSEQH:
  3982  		return 0x0E501 << 15 // vseqi.h
  3983  	case AVSEQW:
  3984  		return 0x0E502 << 15 //vseqi.w
  3985  	case AVSEQV:
  3986  		return 0x0E503 << 15 //vseqi.d
  3987  	case AXVSEQB:
  3988  		return 0x0ED00 << 15 //xvseqi.b
  3989  	case AXVSEQH:
  3990  		return 0x0ED01 << 15 // xvseqi.h
  3991  	case AXVSEQW:
  3992  		return 0x0ED02 << 15 // xvseqi.w
  3993  	case AXVSEQV:
  3994  		return 0x0ED03 << 15 // xvseqi.d
  3995  	case AVROTRB:
  3996  		return 0x1ca8<<18 | 0x1<<13 // vrotri.b
  3997  	case AVROTRH:
  3998  		return 0x1ca8<<18 | 0x1<<14 // vrotri.h
  3999  	case AVROTRW:
  4000  		return 0x1ca8<<18 | 0x1<<15 // vrotri.w
  4001  	case AVROTRV:
  4002  		return 0x1ca8<<18 | 0x1<<16 // vrotri.d
  4003  	case AXVROTRB:
  4004  		return 0x1da8<<18 | 0x1<<13 // xvrotri.b
  4005  	case AXVROTRH:
  4006  		return 0x1da8<<18 | 0x1<<14 // xvrotri.h
  4007  	case AXVROTRW:
  4008  		return 0x1da8<<18 | 0x1<<15 // xvrotri.w
  4009  	case AXVROTRV:
  4010  		return 0x1da8<<18 | 0x1<<16 // xvrotri.d
  4011  	case AVSLLB:
  4012  		return 0x1ccb<<18 | 0x1<<13 // vslli.b
  4013  	case AVSLLH:
  4014  		return 0x1ccb<<18 | 0x1<<14 // vslli.h
  4015  	case AVSLLW:
  4016  		return 0x1ccb<<18 | 0x1<<15 // vslli.w
  4017  	case AVSLLV:
  4018  		return 0x1ccb<<18 | 0x1<<16 // vslli.d
  4019  	case AVSRLB:
  4020  		return 0x1ccc<<18 | 0x1<<13 // vsrli.b
  4021  	case AVSRLH:
  4022  		return 0x1ccc<<18 | 0x1<<14 // vsrli.h
  4023  	case AVSRLW:
  4024  		return 0x1ccc<<18 | 0x1<<15 // vsrli.w
  4025  	case AVSRLV:
  4026  		return 0x1ccc<<18 | 0x1<<16 // vsrli.d
  4027  	case AVSRAB:
  4028  		return 0x1ccd<<18 | 0x1<<13 // vsrai.b
  4029  	case AVSRAH:
  4030  		return 0x1ccd<<18 | 0x1<<14 // vsrai.h
  4031  	case AVSRAW:
  4032  		return 0x1ccd<<18 | 0x1<<15 // vsrai.w
  4033  	case AVSRAV:
  4034  		return 0x1ccd<<18 | 0x1<<16 // vsrai.d
  4035  	case AXVSLLB:
  4036  		return 0x1dcb<<18 | 0x1<<13 // xvslli.b
  4037  	case AXVSLLH:
  4038  		return 0x1dcb<<18 | 0x1<<14 // xvslli.h
  4039  	case AXVSLLW:
  4040  		return 0x1dcb<<18 | 0x1<<15 // xvslli.w
  4041  	case AXVSLLV:
  4042  		return 0x1dcb<<18 | 0x1<<16 // xvslli.d
  4043  	case AXVSRLB:
  4044  		return 0x1dcc<<18 | 0x1<<13 // xvsrli.b
  4045  	case AXVSRLH:
  4046  		return 0x1dcc<<18 | 0x1<<14 // xvsrli.h
  4047  	case AXVSRLW:
  4048  		return 0x1dcc<<18 | 0x1<<15 // xvsrli.w
  4049  	case AXVSRLV:
  4050  		return 0x1dcc<<18 | 0x1<<16 // xvsrli.d
  4051  	case AXVSRAB:
  4052  		return 0x1dcd<<18 | 0x1<<13 // xvsrai.b
  4053  	case AXVSRAH:
  4054  		return 0x1dcd<<18 | 0x1<<14 // xvsrai.h
  4055  	case AXVSRAW:
  4056  		return 0x1dcd<<18 | 0x1<<15 // xvsrai.w
  4057  	case AXVSRAV:
  4058  		return 0x1dcd<<18 | 0x1<<16 // xvsrai.d
  4059  	case AVADDBU:
  4060  		return 0xe514 << 15 // vaddi.bu
  4061  	case AVADDHU:
  4062  		return 0xe515 << 15 // vaddi.hu
  4063  	case AVADDWU:
  4064  		return 0xe516 << 15 // vaddi.wu
  4065  	case AVADDVU:
  4066  		return 0xe517 << 15 // vaddi.du
  4067  	case AVSUBBU:
  4068  		return 0xe518 << 15 // vsubi.bu
  4069  	case AVSUBHU:
  4070  		return 0xe519 << 15 // vsubi.hu
  4071  	case AVSUBWU:
  4072  		return 0xe51a << 15 // vsubi.wu
  4073  	case AVSUBVU:
  4074  		return 0xe51b << 15 // vsubi.du
  4075  	case AXVADDBU:
  4076  		return 0xed14 << 15 // xvaddi.bu
  4077  	case AXVADDHU:
  4078  		return 0xed15 << 15 // xvaddi.hu
  4079  	case AXVADDWU:
  4080  		return 0xed16 << 15 // xvaddi.wu
  4081  	case AXVADDVU:
  4082  		return 0xed17 << 15 // xvaddi.du
  4083  	case AXVSUBBU:
  4084  		return 0xed18 << 15 // xvsubi.bu
  4085  	case AXVSUBHU:
  4086  		return 0xed19 << 15 // xvsubi.hu
  4087  	case AXVSUBWU:
  4088  		return 0xed1a << 15 // xvsubi.wu
  4089  	case AXVSUBVU:
  4090  		return 0xed1b << 15 // xvsubi.du
  4091  	case AVSHUF4IB:
  4092  		return 0x1ce4 << 18 // vshuf4i.b
  4093  	case AVSHUF4IH:
  4094  		return 0x1ce5 << 18 // vshuf4i.h
  4095  	case AVSHUF4IW:
  4096  		return 0x1ce6 << 18 // vshuf4i.w
  4097  	case AVSHUF4IV:
  4098  		return 0x1ce7 << 18 // vshuf4i.d
  4099  	case AXVSHUF4IB:
  4100  		return 0x1de4 << 18 // xvshuf4i.b
  4101  	case AXVSHUF4IH:
  4102  		return 0x1de5 << 18 // xvshuf4i.h
  4103  	case AXVSHUF4IW:
  4104  		return 0x1de6 << 18 // xvshuf4i.w
  4105  	case AXVSHUF4IV:
  4106  		return 0x1de7 << 18 // xvshuf4i.d
  4107  	}
  4108  
  4109  	if a < 0 {
  4110  		c.ctxt.Diag("bad irr opcode -%v", -a)
  4111  	} else {
  4112  		c.ctxt.Diag("bad irr opcode %v", a)
  4113  	}
  4114  	return 0
  4115  }
  4116  
  4117  func (c *ctxt0) opirir(a obj.As) uint32 {
  4118  	switch a {
  4119  	case ABSTRINSW:
  4120  		return 0x3<<21 | 0x0<<15 // bstrins.w
  4121  	case ABSTRINSV:
  4122  		return 0x2 << 22 // bstrins.d
  4123  	case ABSTRPICKW:
  4124  		return 0x3<<21 | 0x1<<15 // bstrpick.w
  4125  	case ABSTRPICKV:
  4126  		return 0x3 << 22 // bstrpick.d
  4127  	}
  4128  
  4129  	return 0
  4130  }
  4131  
  4132  func (c *ctxt0) opiir(a obj.As) uint32 {
  4133  	switch a {
  4134  	case APRELD:
  4135  		return 0x0AB << 22 // preld
  4136  	}
  4137  
  4138  	return 0
  4139  }
  4140  
  4141  func (c *ctxt0) specialFpMovInst(a obj.As, fclass int, tclass int) uint32 {
  4142  	switch a {
  4143  	case AMOVV:
  4144  		switch fclass {
  4145  		case C_REG:
  4146  			switch tclass {
  4147  			case C_FREG:
  4148  				return 0x452a << 10 // movgr2fr.d
  4149  			case C_FCCREG:
  4150  				return 0x4536 << 10 // movgr2cf
  4151  			case C_FCSRREG:
  4152  				return 0x4530 << 10 // movgr2fcsr
  4153  			}
  4154  		case C_FREG:
  4155  			switch tclass {
  4156  			case C_REG:
  4157  				return 0x452e << 10 // movfr2gr.d
  4158  			case C_FCCREG:
  4159  				return 0x4534 << 10 // movfr2cf
  4160  			}
  4161  		case C_FCCREG:
  4162  			switch tclass {
  4163  			case C_REG:
  4164  				return 0x4537 << 10 // movcf2gr
  4165  			case C_FREG:
  4166  				return 0x4535 << 10 // movcf2fr
  4167  			}
  4168  		case C_FCSRREG:
  4169  			switch tclass {
  4170  			case C_REG:
  4171  				return 0x4532 << 10 // movfcsr2gr
  4172  			}
  4173  		}
  4174  
  4175  	case AMOVW:
  4176  		switch fclass {
  4177  		case C_REG:
  4178  			switch tclass {
  4179  			case C_FREG:
  4180  				return 0x4529 << 10 // movgr2fr.w
  4181  			}
  4182  		case C_FREG:
  4183  			switch tclass {
  4184  			case C_REG:
  4185  				return 0x452d << 10 // movfr2gr.s
  4186  			}
  4187  		}
  4188  	}
  4189  
  4190  	c.ctxt.Diag("bad class combination: %s %s,%s\n", a, fclass, tclass)
  4191  
  4192  	return 0
  4193  }
  4194  
  4195  func (c *ctxt0) specialLsxMovInst(a obj.As, fReg, tReg int16) (op_code, index_mask uint32) {
  4196  	farng := (fReg >> EXT_TYPE_SHIFT) & EXT_TYPE_MASK
  4197  	tarng := (tReg >> EXT_TYPE_SHIFT) & EXT_TYPE_MASK
  4198  	fclass := c.rclass(fReg)
  4199  	tclass := c.rclass(tReg)
  4200  
  4201  	switch fclass | (tclass << 16) {
  4202  	case C_REG | (C_ELEM << 16):
  4203  		// vmov Rn, Vd.<T>[index]
  4204  		switch a {
  4205  		case AVMOVQ:
  4206  			switch tarng {
  4207  			case ARNG_B:
  4208  				return (0x01CBAE << 14), 0xf // vinsgr2vr.b
  4209  			case ARNG_H:
  4210  				return (0x03975E << 13), 0x7 // vinsgr2vr.h
  4211  			case ARNG_W:
  4212  				return (0x072EBE << 12), 0x3 // vinsgr2vr.w
  4213  			case ARNG_V:
  4214  				return (0x0E5D7E << 11), 0x1 // vinsgr2vr.d
  4215  			}
  4216  		case AXVMOVQ:
  4217  			switch tarng {
  4218  			case ARNG_W:
  4219  				return (0x03B75E << 13), 0x7 // xvinsgr2vr.w
  4220  			case ARNG_V:
  4221  				return (0x076EBE << 12), 0x3 // xvinsgr2vr.d
  4222  			}
  4223  		}
  4224  
  4225  	case C_ELEM | (C_REG << 16):
  4226  		// vmov Vd.<T>[index], Rn
  4227  		switch a {
  4228  		case AVMOVQ:
  4229  			switch farng {
  4230  			case ARNG_B:
  4231  				return (0x01CBBE << 14), 0xf // vpickve2gr.b
  4232  			case ARNG_H:
  4233  				return (0x03977E << 13), 0x7 // vpickve2gr.h
  4234  			case ARNG_W:
  4235  				return (0x072EFE << 12), 0x3 // vpickve2gr.w
  4236  			case ARNG_V:
  4237  				return (0x0E5DFE << 11), 0x1 // vpickve2gr.d
  4238  			case ARNG_BU:
  4239  				return (0x01CBCE << 14), 0xf // vpickve2gr.bu
  4240  			case ARNG_HU:
  4241  				return (0x03979E << 13), 0x7 // vpickve2gr.hu
  4242  			case ARNG_WU:
  4243  				return (0x072F3E << 12), 0x3 // vpickve2gr.wu
  4244  			case ARNG_VU:
  4245  				return (0x0E5E7E << 11), 0x1 // vpickve2gr.du
  4246  			}
  4247  		case AXVMOVQ:
  4248  			switch farng {
  4249  			case ARNG_W:
  4250  				return (0x03B77E << 13), 0x7 // xvpickve2gr.w
  4251  			case ARNG_V:
  4252  				return (0x076EFE << 12), 0x3 // xvpickve2gr.d
  4253  			case ARNG_WU:
  4254  				return (0x03B79E << 13), 0x7 // xvpickve2gr.wu
  4255  			case ARNG_VU:
  4256  				return (0x076F3E << 12), 0x3 // xvpickve2gr.du
  4257  			}
  4258  		}
  4259  
  4260  	case C_REG | (C_ARNG << 16):
  4261  		// vmov Rn, Vd.<T>
  4262  		switch a {
  4263  		case AVMOVQ:
  4264  			switch tarng {
  4265  			case ARNG_16B:
  4266  				return (0x1CA7C0 << 10), 0x0 // vreplgr2vr.b
  4267  			case ARNG_8H:
  4268  				return (0x1CA7C1 << 10), 0x0 // vreplgr2vr.h
  4269  			case ARNG_4W:
  4270  				return (0x1CA7C2 << 10), 0x0 // vreplgr2vr.w
  4271  			case ARNG_2V:
  4272  				return (0x1CA7C3 << 10), 0x0 // vreplgr2vr.d
  4273  			}
  4274  		case AXVMOVQ:
  4275  			switch tarng {
  4276  			case ARNG_32B:
  4277  				return (0x1DA7C0 << 10), 0x0 // xvreplgr2vr.b
  4278  			case ARNG_16H:
  4279  				return (0x1DA7C1 << 10), 0x0 // xvreplgr2vr.h
  4280  			case ARNG_8W:
  4281  				return (0x1DA7C2 << 10), 0x0 // xvreplgr2vr.w
  4282  			case ARNG_4V:
  4283  				return (0x1DA7C3 << 10), 0x0 // xvreplgr2vr.d
  4284  			}
  4285  		}
  4286  
  4287  	case C_XREG | (C_ARNG << 16):
  4288  		// vmov  xj, xd.<T>
  4289  		switch a {
  4290  		case AVMOVQ:
  4291  			return 0, 0 // unsupported op
  4292  		case AXVMOVQ:
  4293  			switch tarng {
  4294  			case ARNG_32B:
  4295  				return (0x1DC1C0 << 10), 0x0 // xvreplve0.b
  4296  			case ARNG_16H:
  4297  				return (0x1DC1E0 << 10), 0x0 // xvreplve0.h
  4298  			case ARNG_8W:
  4299  				return (0x1DC1F0 << 10), 0x0 // xvreplve0.w
  4300  			case ARNG_4V:
  4301  				return (0x1DC1F8 << 10), 0x0 // xvreplve0.d
  4302  			case ARNG_2Q:
  4303  				return (0x1DC1FC << 10), 0x0 // xvreplve0.q
  4304  			}
  4305  		}
  4306  
  4307  	case C_XREG | (C_ELEM << 16):
  4308  		// vmov  xj, xd.<T>[index]
  4309  		switch a {
  4310  		case AVMOVQ:
  4311  			return 0, 0 // unsupported op
  4312  		case AXVMOVQ:
  4313  			switch tarng {
  4314  			case ARNG_W:
  4315  				return (0x03B7FE << 13), 0x7 // xvinsve0.w
  4316  			case ARNG_V:
  4317  				return (0x076FFE << 12), 0x3 // xvinsve0.d
  4318  			}
  4319  		}
  4320  
  4321  	case C_ELEM | (C_XREG << 16):
  4322  		// vmov  xj.<T>[index], xd
  4323  		switch a {
  4324  		case AVMOVQ:
  4325  			return 0, 0 // unsupported op
  4326  		case AXVMOVQ:
  4327  			switch farng {
  4328  			case ARNG_W:
  4329  				return (0x03B81E << 13), 0x7 // xvpickve.w
  4330  			case ARNG_V:
  4331  				return (0x07703E << 12), 0x3 // xvpickve.d
  4332  			}
  4333  		}
  4334  
  4335  	case C_ELEM | (C_ARNG << 16):
  4336  		// vmov  vj.<T>[index], vd.<T>
  4337  		switch a {
  4338  		case AVMOVQ:
  4339  			switch int32(farng) | (int32(tarng) << 16) {
  4340  			case int32(ARNG_B) | (int32(ARNG_16B) << 16):
  4341  				return (0x01CBDE << 14), 0xf // vreplvei.b
  4342  			case int32(ARNG_H) | (int32(ARNG_8H) << 16):
  4343  				return (0x0397BE << 13), 0x7 // vreplvei.h
  4344  			case int32(ARNG_W) | (int32(ARNG_4W) << 16):
  4345  				return (0x072F7E << 12), 0x3 // vreplvei.w
  4346  			case int32(ARNG_V) | (int32(ARNG_2V) << 16):
  4347  				return (0x0E5EFE << 11), 0x1 // vreplvei.d
  4348  			}
  4349  		case AXVMOVQ:
  4350  			return 0, 0 // unsupported op
  4351  		}
  4352  	}
  4353  
  4354  	return 0, 0
  4355  }
  4356  
  4357  func vshift(a obj.As) bool {
  4358  	switch a {
  4359  	case ASLLV,
  4360  		ASRLV,
  4361  		ASRAV,
  4362  		AROTRV:
  4363  		return true
  4364  	}
  4365  	return false
  4366  }
  4367  

View as plain text