/ src / Ryujinx.Graphics.Shader / Translation / EmitterContextInsts.cs
EmitterContextInsts.cs
   1  using Ryujinx.Graphics.Shader.IntermediateRepresentation;
   2  using System;
   3  
   4  using static Ryujinx.Graphics.Shader.IntermediateRepresentation.OperandHelper;
   5  
   6  namespace Ryujinx.Graphics.Shader.Translation
   7  {
   8      static class EmitterContextInsts
   9      {
  10          public static Operand AtomicAdd(this EmitterContext context, StorageKind storageKind, Operand a, Operand b, Operand c)
  11          {
  12              return context.Add(Instruction.AtomicAdd, storageKind, Local(), a, b, c);
  13          }
  14  
  15          public static Operand AtomicAnd(this EmitterContext context, StorageKind storageKind, Operand a, Operand b, Operand c)
  16          {
  17              return context.Add(Instruction.AtomicAnd, storageKind, Local(), a, b, c);
  18          }
  19  
  20          public static Operand AtomicCompareAndSwap(this EmitterContext context, StorageKind storageKind, Operand a, Operand b, Operand c, Operand d)
  21          {
  22              return context.Add(Instruction.AtomicCompareAndSwap, storageKind, Local(), a, b, c, d);
  23          }
  24  
  25          public static Operand AtomicMaxS32(this EmitterContext context, StorageKind storageKind, Operand a, Operand b, Operand c)
  26          {
  27              return context.Add(Instruction.AtomicMaxS32, storageKind, Local(), a, b, c);
  28          }
  29  
  30          public static Operand AtomicMaxU32(this EmitterContext context, StorageKind storageKind, Operand a, Operand b, Operand c)
  31          {
  32              return context.Add(Instruction.AtomicMaxU32, storageKind, Local(), a, b, c);
  33          }
  34  
  35          public static Operand AtomicMinS32(this EmitterContext context, StorageKind storageKind, Operand a, Operand b, Operand c)
  36          {
  37              return context.Add(Instruction.AtomicMinS32, storageKind, Local(), a, b, c);
  38          }
  39  
  40          public static Operand AtomicMinU32(this EmitterContext context, StorageKind storageKind, Operand a, Operand b, Operand c)
  41          {
  42              return context.Add(Instruction.AtomicMinU32, storageKind, Local(), a, b, c);
  43          }
  44  
  45          public static Operand AtomicOr(this EmitterContext context, StorageKind storageKind, Operand a, Operand b, Operand c)
  46          {
  47              return context.Add(Instruction.AtomicOr, storageKind, Local(), a, b, c);
  48          }
  49  
  50          public static Operand AtomicSwap(this EmitterContext context, StorageKind storageKind, Operand a, Operand b, Operand c)
  51          {
  52              return context.Add(Instruction.AtomicSwap, storageKind, Local(), a, b, c);
  53          }
  54  
  55          public static Operand AtomicXor(this EmitterContext context, StorageKind storageKind, Operand a, Operand b, Operand c)
  56          {
  57              return context.Add(Instruction.AtomicXor, storageKind, Local(), a, b, c);
  58          }
  59  
  60          public static Operand AtomicAdd(this EmitterContext context, StorageKind storageKind, int binding, Operand e0, Operand e1, Operand value)
  61          {
  62              return context.Add(Instruction.AtomicAdd, storageKind, Local(), Const(binding), e0, e1, value);
  63          }
  64  
  65          public static Operand AtomicAnd(this EmitterContext context, StorageKind storageKind, int binding, Operand e0, Operand e1, Operand value)
  66          {
  67              return context.Add(Instruction.AtomicAnd, storageKind, Local(), Const(binding), e0, e1, value);
  68          }
  69  
  70          public static Operand AtomicCompareAndSwap(this EmitterContext context, StorageKind storageKind, int binding, Operand e0, Operand compare, Operand value)
  71          {
  72              return context.Add(Instruction.AtomicCompareAndSwap, storageKind, Local(), Const(binding), e0, compare, value);
  73          }
  74  
  75          public static Operand AtomicCompareAndSwap(this EmitterContext context, StorageKind storageKind, int binding, Operand e0, Operand e1, Operand compare, Operand value)
  76          {
  77              return context.Add(Instruction.AtomicCompareAndSwap, storageKind, Local(), Const(binding), e0, e1, compare, value);
  78          }
  79  
  80          public static Operand AtomicMaxS32(this EmitterContext context, StorageKind storageKind, int binding, Operand e0, Operand e1, Operand value)
  81          {
  82              return context.Add(Instruction.AtomicMaxS32, storageKind, Local(), Const(binding), e0, e1, value);
  83          }
  84  
  85          public static Operand AtomicMaxU32(this EmitterContext context, StorageKind storageKind, int binding, Operand e0, Operand e1, Operand value)
  86          {
  87              return context.Add(Instruction.AtomicMaxU32, storageKind, Local(), Const(binding), e0, e1, value);
  88          }
  89  
  90          public static Operand AtomicMinS32(this EmitterContext context, StorageKind storageKind, int binding, Operand e0, Operand e1, Operand value)
  91          {
  92              return context.Add(Instruction.AtomicMinS32, storageKind, Local(), Const(binding), e0, e1, value);
  93          }
  94  
  95          public static Operand AtomicMinU32(this EmitterContext context, StorageKind storageKind, int binding, Operand e0, Operand e1, Operand value)
  96          {
  97              return context.Add(Instruction.AtomicMinU32, storageKind, Local(), Const(binding), e0, e1, value);
  98          }
  99  
 100          public static Operand AtomicOr(this EmitterContext context, StorageKind storageKind, int binding, Operand e0, Operand e1, Operand value)
 101          {
 102              return context.Add(Instruction.AtomicOr, storageKind, Local(), Const(binding), e0, e1, value);
 103          }
 104  
 105          public static Operand AtomicSwap(this EmitterContext context, StorageKind storageKind, int binding, Operand e0, Operand e1, Operand value)
 106          {
 107              return context.Add(Instruction.AtomicSwap, storageKind, Local(), Const(binding), e0, e1, value);
 108          }
 109  
 110          public static Operand AtomicXor(this EmitterContext context, StorageKind storageKind, int binding, Operand e0, Operand e1, Operand value)
 111          {
 112              return context.Add(Instruction.AtomicXor, storageKind, Local(), Const(binding), e0, e1, value);
 113          }
 114  
 115          public static Operand Ballot(this EmitterContext context, Operand a, int index)
 116          {
 117              Operand dest = Local();
 118  
 119              context.Add(new Operation(Instruction.Ballot, index, dest, a));
 120  
 121              return dest;
 122          }
 123  
 124          public static Operand Barrier(this EmitterContext context)
 125          {
 126              return context.Add(Instruction.Barrier);
 127          }
 128  
 129          public static Operand BitCount(this EmitterContext context, Operand a)
 130          {
 131              return context.Add(Instruction.BitCount, Local(), a);
 132          }
 133  
 134          public static Operand BitfieldExtractS32(this EmitterContext context, Operand a, Operand b, Operand c)
 135          {
 136              return context.Add(Instruction.BitfieldExtractS32, Local(), a, b, c);
 137          }
 138  
 139          public static Operand BitfieldExtractU32(this EmitterContext context, Operand a, Operand b, Operand c)
 140          {
 141              return context.Add(Instruction.BitfieldExtractU32, Local(), a, b, c);
 142          }
 143  
 144          public static Operand BitfieldInsert(this EmitterContext context, Operand a, Operand b, Operand c, Operand d)
 145          {
 146              return context.Add(Instruction.BitfieldInsert, Local(), a, b, c, d);
 147          }
 148  
 149          public static Operand BitfieldReverse(this EmitterContext context, Operand a)
 150          {
 151              return context.Add(Instruction.BitfieldReverse, Local(), a);
 152          }
 153  
 154          public static Operand BitwiseAnd(this EmitterContext context, Operand a, Operand b)
 155          {
 156              return context.Add(Instruction.BitwiseAnd, Local(), a, b);
 157          }
 158  
 159          public static Operand BitwiseExclusiveOr(this EmitterContext context, Operand a, Operand b)
 160          {
 161              return context.Add(Instruction.BitwiseExclusiveOr, Local(), a, b);
 162          }
 163  
 164          public static Operand BitwiseNot(this EmitterContext context, Operand a, bool invert)
 165          {
 166              if (invert)
 167              {
 168                  a = context.BitwiseNot(a);
 169              }
 170  
 171              return a;
 172          }
 173  
 174          public static Operand BitwiseNot(this EmitterContext context, Operand a)
 175          {
 176              return context.Add(Instruction.BitwiseNot, Local(), a);
 177          }
 178  
 179          public static Operand BitwiseOr(this EmitterContext context, Operand a, Operand b)
 180          {
 181              return context.Add(Instruction.BitwiseOr, Local(), a, b);
 182          }
 183  
 184          public static Operand Branch(this EmitterContext context, Operand d)
 185          {
 186              return context.Add(Instruction.Branch, d);
 187          }
 188  
 189          public static Operand BranchIfFalse(this EmitterContext context, Operand d, Operand a)
 190          {
 191              return context.Add(Instruction.BranchIfFalse, d, a);
 192          }
 193  
 194          public static Operand BranchIfTrue(this EmitterContext context, Operand d, Operand a)
 195          {
 196              return context.Add(Instruction.BranchIfTrue, d, a);
 197          }
 198  
 199          public static Operand Call(this EmitterContext context, int funcId, bool returns, params Operand[] args)
 200          {
 201              Operand[] args2 = new Operand[args.Length + 1];
 202  
 203              args2[0] = Const(funcId);
 204              args.CopyTo(args2, 1);
 205  
 206              return context.Add(Instruction.Call, returns ? Local() : null, args2);
 207          }
 208  
 209          public static Operand ConditionalSelect(this EmitterContext context, Operand a, Operand b, Operand c)
 210          {
 211              return context.Add(Instruction.ConditionalSelect, Local(), a, b, c);
 212          }
 213  
 214          public static Operand Copy(this EmitterContext context, Operand a)
 215          {
 216              return context.Add(Instruction.Copy, Local(), a);
 217          }
 218  
 219          public static void Copy(this EmitterContext context, Operand d, Operand a)
 220          {
 221              if (d.Type == OperandType.Constant)
 222              {
 223                  return;
 224              }
 225  
 226              context.Add(Instruction.Copy, d, a);
 227          }
 228  
 229          public static Operand Discard(this EmitterContext context)
 230          {
 231              return context.Add(Instruction.Discard);
 232          }
 233  
 234          public static Operand EmitVertex(this EmitterContext context)
 235          {
 236              return context.Add(Instruction.EmitVertex);
 237          }
 238  
 239          public static Operand EndPrimitive(this EmitterContext context)
 240          {
 241              return context.Add(Instruction.EndPrimitive);
 242          }
 243  
 244          public static Operand FindLSB(this EmitterContext context, Operand a)
 245          {
 246              return context.Add(Instruction.FindLSB, Local(), a);
 247          }
 248  
 249          public static Operand FindMSBS32(this EmitterContext context, Operand a)
 250          {
 251              return context.Add(Instruction.FindMSBS32, Local(), a);
 252          }
 253  
 254          public static Operand FindMSBU32(this EmitterContext context, Operand a)
 255          {
 256              return context.Add(Instruction.FindMSBU32, Local(), a);
 257          }
 258  
 259          public static Operand FP32ConvertToFP64(this EmitterContext context, Operand a)
 260          {
 261              return context.Add(Instruction.ConvertFP32ToFP64, Local(), a);
 262          }
 263  
 264          public static Operand FP64ConvertToFP32(this EmitterContext context, Operand a)
 265          {
 266              return context.Add(Instruction.ConvertFP64ToFP32, Local(), a);
 267          }
 268  
 269          public static Operand FPAbsNeg(this EmitterContext context, Operand a, bool abs, bool neg, Instruction fpType = Instruction.FP32)
 270          {
 271              return context.FPNegate(context.FPAbsolute(a, abs, fpType), neg, fpType);
 272          }
 273  
 274          public static Operand FPAbsolute(this EmitterContext context, Operand a, bool abs, Instruction fpType = Instruction.FP32)
 275          {
 276              if (abs)
 277              {
 278                  a = context.FPAbsolute(a, fpType);
 279              }
 280  
 281              return a;
 282          }
 283  
 284          public static Operand FPAbsolute(this EmitterContext context, Operand a, Instruction fpType = Instruction.FP32)
 285          {
 286              return context.Add(fpType | Instruction.Absolute, Local(), a);
 287          }
 288  
 289          public static Operand FPAdd(this EmitterContext context, Operand a, Operand b, Instruction fpType = Instruction.FP32)
 290          {
 291              return context.Add(fpType | Instruction.Add, Local(), a, b);
 292          }
 293  
 294          public static Operand FPCeiling(this EmitterContext context, Operand a, Instruction fpType = Instruction.FP32)
 295          {
 296              return context.Add(fpType | Instruction.Ceiling, Local(), a);
 297          }
 298  
 299          public static Operand FPCompareEqual(this EmitterContext context, Operand a, Operand b, Instruction fpType = Instruction.FP32)
 300          {
 301              return context.Add(fpType | Instruction.CompareEqual, Local(), a, b);
 302          }
 303  
 304          public static Operand FPCompareLess(this EmitterContext context, Operand a, Operand b, Instruction fpType = Instruction.FP32)
 305          {
 306              return context.Add(fpType | Instruction.CompareLess, Local(), a, b);
 307          }
 308  
 309          public static Operand FP32ConvertToS32(this EmitterContext context, Operand a)
 310          {
 311              return context.Add(Instruction.ConvertFP32ToS32, Local(), a);
 312          }
 313  
 314          public static Operand FP32ConvertToU32(this EmitterContext context, Operand a)
 315          {
 316              return context.Add(Instruction.ConvertFP32ToU32, Local(), a);
 317          }
 318  
 319          public static Operand FP64ConvertToS32(this EmitterContext context, Operand a)
 320          {
 321              return context.Add(Instruction.ConvertFP64ToS32, Local(), a);
 322          }
 323  
 324          public static Operand FP64ConvertToU32(this EmitterContext context, Operand a)
 325          {
 326              return context.Add(Instruction.ConvertFP64ToU32, Local(), a);
 327          }
 328  
 329          public static Operand FPCosine(this EmitterContext context, Operand a)
 330          {
 331              return context.Add(Instruction.FP32 | Instruction.Cosine, Local(), a);
 332          }
 333  
 334          public static Operand FPDivide(this EmitterContext context, Operand a, Operand b, Instruction fpType = Instruction.FP32)
 335          {
 336              return context.Add(fpType | Instruction.Divide, Local(), a, b);
 337          }
 338  
 339          public static Operand FPExponentB2(this EmitterContext context, Operand a)
 340          {
 341              return context.Add(Instruction.FP32 | Instruction.ExponentB2, Local(), a);
 342          }
 343  
 344          public static Operand FPFloor(this EmitterContext context, Operand a, Instruction fpType = Instruction.FP32)
 345          {
 346              return context.Add(fpType | Instruction.Floor, Local(), a);
 347          }
 348  
 349          public static Operand FPFusedMultiplyAdd(this EmitterContext context, Operand a, Operand b, Operand c, Instruction fpType = Instruction.FP32)
 350          {
 351              return context.Add(fpType | Instruction.FusedMultiplyAdd, Local(), a, b, c);
 352          }
 353  
 354          public static Operand FPLogarithmB2(this EmitterContext context, Operand a)
 355          {
 356              return context.Add(Instruction.FP32 | Instruction.LogarithmB2, Local(), a);
 357          }
 358  
 359          public static Operand FPMaximum(this EmitterContext context, Operand a, Operand b, Instruction fpType = Instruction.FP32)
 360          {
 361              return context.Add(fpType | Instruction.Maximum, Local(), a, b);
 362          }
 363  
 364          public static Operand FPMinimum(this EmitterContext context, Operand a, Operand b, Instruction fpType = Instruction.FP32)
 365          {
 366              return context.Add(fpType | Instruction.Minimum, Local(), a, b);
 367          }
 368  
 369          public static Operand FPModulo(this EmitterContext context, Operand a, Operand b, Instruction fpType = Instruction.FP32)
 370          {
 371              return context.Add(fpType | Instruction.Modulo, Local(), a, b);
 372          }
 373  
 374          public static Operand FPMultiply(this EmitterContext context, Operand a, Operand b, Instruction fpType = Instruction.FP32)
 375          {
 376              return context.Add(fpType | Instruction.Multiply, Local(), a, b);
 377          }
 378  
 379          public static Operand FPNegate(this EmitterContext context, Operand a, bool neg, Instruction fpType = Instruction.FP32)
 380          {
 381              if (neg)
 382              {
 383                  a = context.FPNegate(a, fpType);
 384              }
 385  
 386              return a;
 387          }
 388  
 389          public static Operand FPNegate(this EmitterContext context, Operand a, Instruction fpType = Instruction.FP32)
 390          {
 391              return context.Add(fpType | Instruction.Negate, Local(), a);
 392          }
 393  
 394          public static Operand FPReciprocal(this EmitterContext context, Operand a, Instruction fpType = Instruction.FP32)
 395          {
 396              return context.FPDivide(fpType == Instruction.FP64 ? context.PackDouble2x32(1.0) : ConstF(1), a, fpType);
 397          }
 398  
 399          public static Operand FPReciprocalSquareRoot(this EmitterContext context, Operand a, Instruction fpType = Instruction.FP32)
 400          {
 401              return context.Add(fpType | Instruction.ReciprocalSquareRoot, Local(), a);
 402          }
 403  
 404          public static Operand FPRound(this EmitterContext context, Operand a, Instruction fpType = Instruction.FP32)
 405          {
 406              return context.Add(fpType | Instruction.Round, Local(), a);
 407          }
 408  
 409          public static Operand FPSaturate(this EmitterContext context, Operand a, bool sat, Instruction fpType = Instruction.FP32)
 410          {
 411              if (sat)
 412              {
 413                  a = context.FPSaturate(a, fpType);
 414              }
 415  
 416              return a;
 417          }
 418  
 419          public static Operand FPSaturate(this EmitterContext context, Operand a, Instruction fpType = Instruction.FP32)
 420          {
 421              return fpType == Instruction.FP64
 422                  ? context.Add(fpType | Instruction.Clamp, Local(), a, context.PackDouble2x32(0.0), context.PackDouble2x32(1.0))
 423                  : context.Add(fpType | Instruction.Clamp, Local(), a, ConstF(0), ConstF(1));
 424          }
 425  
 426          public static Operand FPSine(this EmitterContext context, Operand a)
 427          {
 428              return context.Add(Instruction.FP32 | Instruction.Sine, Local(), a);
 429          }
 430  
 431          public static Operand FPSquareRoot(this EmitterContext context, Operand a)
 432          {
 433              return context.Add(Instruction.FP32 | Instruction.SquareRoot, Local(), a);
 434          }
 435  
 436          public static Operand FPSubtract(this EmitterContext context, Operand a, Operand b, Instruction fpType = Instruction.FP32)
 437          {
 438              return context.Add(fpType | Instruction.Subtract, Local(), a, b);
 439          }
 440  
 441          public static Operand FPTruncate(this EmitterContext context, Operand a, Instruction fpType = Instruction.FP32)
 442          {
 443              return context.Add(fpType | Instruction.Truncate, Local(), a);
 444          }
 445  
 446          public static Operand FPSwizzleAdd(this EmitterContext context, Operand a, Operand b, int mask)
 447          {
 448              return context.Add(Instruction.SwizzleAdd, Local(), a, b, Const(mask));
 449          }
 450  
 451          public static void FSIBegin(this EmitterContext context)
 452          {
 453              context.Add(Instruction.FSIBegin);
 454          }
 455  
 456          public static void FSIEnd(this EmitterContext context)
 457          {
 458              context.Add(Instruction.FSIEnd);
 459          }
 460  
 461          public static Operand GroupMemoryBarrier(this EmitterContext context)
 462          {
 463              return context.Add(Instruction.GroupMemoryBarrier);
 464          }
 465  
 466          public static Operand IAbsNeg(this EmitterContext context, Operand a, bool abs, bool neg)
 467          {
 468              return context.INegate(context.IAbsolute(a, abs), neg);
 469          }
 470  
 471          public static Operand IAbsolute(this EmitterContext context, Operand a, bool abs)
 472          {
 473              if (abs)
 474              {
 475                  a = context.IAbsolute(a);
 476              }
 477  
 478              return a;
 479          }
 480  
 481          public static Operand IAbsolute(this EmitterContext context, Operand a)
 482          {
 483              return context.Add(Instruction.Absolute, Local(), a);
 484          }
 485  
 486          public static Operand IAdd(this EmitterContext context, Operand a, Operand b)
 487          {
 488              return context.Add(Instruction.Add, Local(), a, b);
 489          }
 490  
 491          public static Operand IClampS32(this EmitterContext context, Operand a, Operand b, Operand c)
 492          {
 493              return context.Add(Instruction.Clamp, Local(), a, b, c);
 494          }
 495  
 496          public static Operand IClampU32(this EmitterContext context, Operand a, Operand b, Operand c)
 497          {
 498              return context.Add(Instruction.ClampU32, Local(), a, b, c);
 499          }
 500  
 501          public static Operand ICompareEqual(this EmitterContext context, Operand a, Operand b)
 502          {
 503              return context.Add(Instruction.CompareEqual, Local(), a, b);
 504          }
 505  
 506          public static Operand ICompareGreater(this EmitterContext context, Operand a, Operand b)
 507          {
 508              return context.Add(Instruction.CompareGreater, Local(), a, b);
 509          }
 510  
 511          public static Operand ICompareGreaterOrEqual(this EmitterContext context, Operand a, Operand b)
 512          {
 513              return context.Add(Instruction.CompareGreaterOrEqual, Local(), a, b);
 514          }
 515  
 516          public static Operand ICompareGreaterOrEqualUnsigned(this EmitterContext context, Operand a, Operand b)
 517          {
 518              return context.Add(Instruction.CompareGreaterOrEqualU32, Local(), a, b);
 519          }
 520  
 521          public static Operand ICompareGreaterUnsigned(this EmitterContext context, Operand a, Operand b)
 522          {
 523              return context.Add(Instruction.CompareGreaterU32, Local(), a, b);
 524          }
 525  
 526          public static Operand ICompareLess(this EmitterContext context, Operand a, Operand b)
 527          {
 528              return context.Add(Instruction.CompareLess, Local(), a, b);
 529          }
 530  
 531          public static Operand ICompareLessOrEqual(this EmitterContext context, Operand a, Operand b)
 532          {
 533              return context.Add(Instruction.CompareLessOrEqual, Local(), a, b);
 534          }
 535  
 536          public static Operand ICompareLessOrEqualUnsigned(this EmitterContext context, Operand a, Operand b)
 537          {
 538              return context.Add(Instruction.CompareLessOrEqualU32, Local(), a, b);
 539          }
 540  
 541          public static Operand ICompareLessUnsigned(this EmitterContext context, Operand a, Operand b)
 542          {
 543              return context.Add(Instruction.CompareLessU32, Local(), a, b);
 544          }
 545  
 546          public static Operand ICompareNotEqual(this EmitterContext context, Operand a, Operand b)
 547          {
 548              return context.Add(Instruction.CompareNotEqual, Local(), a, b);
 549          }
 550  
 551          public static Operand IConvertS32ToFP32(this EmitterContext context, Operand a)
 552          {
 553              return context.Add(Instruction.ConvertS32ToFP32, Local(), a);
 554          }
 555  
 556          public static Operand IConvertS32ToFP64(this EmitterContext context, Operand a)
 557          {
 558              return context.Add(Instruction.ConvertS32ToFP64, Local(), a);
 559          }
 560  
 561          public static Operand IConvertU32ToFP32(this EmitterContext context, Operand a)
 562          {
 563              return context.Add(Instruction.ConvertU32ToFP32, Local(), a);
 564          }
 565  
 566          public static Operand IConvertU32ToFP64(this EmitterContext context, Operand a)
 567          {
 568              return context.Add(Instruction.ConvertU32ToFP64, Local(), a);
 569          }
 570  
 571          public static Operand IMaximumS32(this EmitterContext context, Operand a, Operand b)
 572          {
 573              return context.Add(Instruction.Maximum, Local(), a, b);
 574          }
 575  
 576          public static Operand IMaximumU32(this EmitterContext context, Operand a, Operand b)
 577          {
 578              return context.Add(Instruction.MaximumU32, Local(), a, b);
 579          }
 580  
 581          public static Operand IMinimumS32(this EmitterContext context, Operand a, Operand b)
 582          {
 583              return context.Add(Instruction.Minimum, Local(), a, b);
 584          }
 585  
 586          public static Operand IMinimumU32(this EmitterContext context, Operand a, Operand b)
 587          {
 588              return context.Add(Instruction.MinimumU32, Local(), a, b);
 589          }
 590  
 591          public static Operand IMultiply(this EmitterContext context, Operand a, Operand b)
 592          {
 593              return context.Add(Instruction.Multiply, Local(), a, b);
 594          }
 595  
 596          public static Operand INegate(this EmitterContext context, Operand a, bool neg)
 597          {
 598              if (neg)
 599              {
 600                  a = context.INegate(a);
 601              }
 602  
 603              return a;
 604          }
 605  
 606          public static Operand INegate(this EmitterContext context, Operand a)
 607          {
 608              return context.Add(Instruction.Negate, Local(), a);
 609          }
 610  
 611          public static Operand ISubtract(this EmitterContext context, Operand a, Operand b)
 612          {
 613              return context.Add(Instruction.Subtract, Local(), a, b);
 614          }
 615  
 616          public static Operand ImageAtomic(
 617              this EmitterContext context,
 618              SamplerType type,
 619              TextureFormat format,
 620              TextureFlags flags,
 621              SetBindingPair setAndBinding,
 622              Operand[] sources)
 623          {
 624              Operand dest = Local();
 625  
 626              context.Add(new TextureOperation(
 627                  Instruction.ImageAtomic,
 628                  type,
 629                  format,
 630                  flags,
 631                  setAndBinding.SetIndex,
 632                  setAndBinding.Binding,
 633                  0,
 634                  new[] { dest },
 635                  sources));
 636  
 637              return dest;
 638          }
 639  
 640          public static void ImageLoad(
 641              this EmitterContext context,
 642              SamplerType type,
 643              TextureFormat format,
 644              TextureFlags flags,
 645              SetBindingPair setAndBinding,
 646              int compMask,
 647              Operand[] dests,
 648              Operand[] sources)
 649          {
 650              context.Add(new TextureOperation(
 651                  Instruction.ImageLoad,
 652                  type,
 653                  format,
 654                  flags,
 655                  setAndBinding.SetIndex,
 656                  setAndBinding.Binding,
 657                  compMask,
 658                  dests,
 659                  sources));
 660          }
 661  
 662          public static void ImageStore(
 663              this EmitterContext context,
 664              SamplerType type,
 665              TextureFormat format,
 666              TextureFlags flags,
 667              SetBindingPair setAndBinding,
 668              Operand[] sources)
 669          {
 670              context.Add(new TextureOperation(
 671                  Instruction.ImageStore,
 672                  type,
 673                  format,
 674                  flags,
 675                  setAndBinding.SetIndex,
 676                  setAndBinding.Binding,
 677                  0,
 678                  null,
 679                  sources));
 680          }
 681  
 682          public static Operand IsNan(this EmitterContext context, Operand a, Instruction fpType = Instruction.FP32)
 683          {
 684              return context.Add(fpType | Instruction.IsNan, Local(), a);
 685          }
 686  
 687          public static Operand Load(this EmitterContext context, StorageKind storageKind, Operand e0, Operand e1)
 688          {
 689              return context.Add(Instruction.Load, storageKind, Local(), e0, e1);
 690          }
 691  
 692          public static Operand Load(this EmitterContext context, StorageKind storageKind, int binding)
 693          {
 694              return context.Add(Instruction.Load, storageKind, Local(), Const(binding));
 695          }
 696  
 697          public static Operand Load(this EmitterContext context, StorageKind storageKind, int binding, Operand e0)
 698          {
 699              return context.Add(Instruction.Load, storageKind, Local(), Const(binding), e0);
 700          }
 701  
 702          public static Operand Load(this EmitterContext context, StorageKind storageKind, int binding, Operand e0, Operand e1)
 703          {
 704              return context.Add(Instruction.Load, storageKind, Local(), Const(binding), e0, e1);
 705          }
 706  
 707          public static Operand Load(this EmitterContext context, StorageKind storageKind, int binding, Operand e0, Operand e1, Operand e2)
 708          {
 709              return context.Add(Instruction.Load, storageKind, Local(), Const(binding), e0, e1, e2);
 710          }
 711  
 712          public static Operand Load(this EmitterContext context, StorageKind storageKind, IoVariable ioVariable, Operand primVertex = null)
 713          {
 714              return primVertex != null
 715                  ? context.Load(storageKind, (int)ioVariable, primVertex)
 716                  : context.Load(storageKind, (int)ioVariable);
 717          }
 718  
 719          public static Operand Load(
 720              this EmitterContext context,
 721              StorageKind storageKind,
 722              IoVariable ioVariable,
 723              Operand primVertex,
 724              Operand elemIndex)
 725          {
 726              return primVertex != null
 727                  ? context.Load(storageKind, (int)ioVariable, primVertex, elemIndex)
 728                  : context.Load(storageKind, (int)ioVariable, elemIndex);
 729          }
 730  
 731          public static Operand Load(
 732              this EmitterContext context,
 733              StorageKind storageKind,
 734              IoVariable ioVariable,
 735              Operand primVertex,
 736              Operand arrayIndex,
 737              Operand elemIndex)
 738          {
 739              return primVertex != null
 740                  ? context.Load(storageKind, (int)ioVariable, primVertex, arrayIndex, elemIndex)
 741                  : context.Load(storageKind, (int)ioVariable, arrayIndex, elemIndex);
 742          }
 743  
 744          public static Operand Lod(
 745              this EmitterContext context,
 746              SamplerType type,
 747              TextureFlags flags,
 748              SetBindingPair setAndBinding,
 749              int compIndex,
 750              Operand[] sources)
 751          {
 752              Operand dest = Local();
 753  
 754              context.Add(new TextureOperation(
 755                  Instruction.Lod,
 756                  type,
 757                  TextureFormat.Unknown,
 758                  flags,
 759                  setAndBinding.SetIndex,
 760                  setAndBinding.Binding,
 761                  compIndex,
 762                  new[] { dest },
 763                  sources));
 764  
 765              return dest;
 766          }
 767  
 768          public static Operand MemoryBarrier(this EmitterContext context)
 769          {
 770              return context.Add(Instruction.MemoryBarrier);
 771          }
 772  
 773          public static Operand MultiplyHighS32(this EmitterContext context, Operand a, Operand b)
 774          {
 775              return context.Add(Instruction.MultiplyHighS32, Local(), a, b);
 776          }
 777  
 778          public static Operand MultiplyHighU32(this EmitterContext context, Operand a, Operand b)
 779          {
 780              return context.Add(Instruction.MultiplyHighU32, Local(), a, b);
 781          }
 782  
 783          public static Operand PackDouble2x32(this EmitterContext context, double value)
 784          {
 785              long valueAsLong = BitConverter.DoubleToInt64Bits(value);
 786  
 787              return context.Add(Instruction.PackDouble2x32, Local(), Const((int)valueAsLong), Const((int)(valueAsLong >> 32)));
 788          }
 789  
 790          public static Operand PackDouble2x32(this EmitterContext context, Operand a, Operand b)
 791          {
 792              return context.Add(Instruction.PackDouble2x32, Local(), a, b);
 793          }
 794  
 795          public static Operand PackHalf2x16(this EmitterContext context, Operand a, Operand b)
 796          {
 797              return context.Add(Instruction.PackHalf2x16, Local(), a, b);
 798          }
 799  
 800          public static void Return(this EmitterContext context)
 801          {
 802              context.Add(Instruction.Return);
 803          }
 804  
 805          public static void Return(this EmitterContext context, Operand returnValue)
 806          {
 807              context.Add(Instruction.Return, null, returnValue);
 808          }
 809  
 810          public static Operand ShiftLeft(this EmitterContext context, Operand a, Operand b)
 811          {
 812              return context.Add(Instruction.ShiftLeft, Local(), a, b);
 813          }
 814  
 815          public static Operand ShiftRightS32(this EmitterContext context, Operand a, Operand b)
 816          {
 817              return context.Add(Instruction.ShiftRightS32, Local(), a, b);
 818          }
 819  
 820          public static Operand ShiftRightU32(this EmitterContext context, Operand a, Operand b)
 821          {
 822              return context.Add(Instruction.ShiftRightU32, Local(), a, b);
 823          }
 824  
 825          public static Operand Shuffle(this EmitterContext context, Operand a, Operand b)
 826          {
 827              return context.Add(Instruction.Shuffle, Local(), a, b);
 828          }
 829  
 830          public static (Operand, Operand) Shuffle(this EmitterContext context, Operand a, Operand b, Operand c)
 831          {
 832              return context.Add(Instruction.Shuffle, (Local(), Local()), a, b, c);
 833          }
 834  
 835          public static Operand ShuffleDown(this EmitterContext context, Operand a, Operand b)
 836          {
 837              return context.Add(Instruction.ShuffleDown, Local(), a, b);
 838          }
 839  
 840          public static (Operand, Operand) ShuffleDown(this EmitterContext context, Operand a, Operand b, Operand c)
 841          {
 842              return context.Add(Instruction.ShuffleDown, (Local(), Local()), a, b, c);
 843          }
 844  
 845          public static Operand ShuffleUp(this EmitterContext context, Operand a, Operand b)
 846          {
 847              return context.Add(Instruction.ShuffleUp, Local(), a, b);
 848          }
 849  
 850          public static (Operand, Operand) ShuffleUp(this EmitterContext context, Operand a, Operand b, Operand c)
 851          {
 852              return context.Add(Instruction.ShuffleUp, (Local(), Local()), a, b, c);
 853          }
 854  
 855          public static Operand ShuffleXor(this EmitterContext context, Operand a, Operand b)
 856          {
 857              return context.Add(Instruction.ShuffleXor, Local(), a, b);
 858          }
 859  
 860          public static (Operand, Operand) ShuffleXor(this EmitterContext context, Operand a, Operand b, Operand c)
 861          {
 862              return context.Add(Instruction.ShuffleXor, (Local(), Local()), a, b, c);
 863          }
 864  
 865          public static Operand Store(this EmitterContext context, StorageKind storageKind, Operand e0, Operand e1, Operand value)
 866          {
 867              return context.Add(Instruction.Store, storageKind, null, e0, e1, value);
 868          }
 869  
 870          public static Operand Store(this EmitterContext context, StorageKind storageKind, int binding, Operand value)
 871          {
 872              return context.Add(Instruction.Store, storageKind, null, Const(binding), value);
 873          }
 874  
 875          public static Operand Store(this EmitterContext context, StorageKind storageKind, int binding, Operand e0, Operand value)
 876          {
 877              return context.Add(Instruction.Store, storageKind, null, Const(binding), e0, value);
 878          }
 879  
 880          public static Operand Store(this EmitterContext context, StorageKind storageKind, int binding, Operand e0, Operand e1, Operand value)
 881          {
 882              return context.Add(Instruction.Store, storageKind, null, Const(binding), e0, e1, value);
 883          }
 884  
 885          public static Operand Store(
 886              this EmitterContext context,
 887              StorageKind storageKind,
 888              IoVariable ioVariable,
 889              Operand invocationId,
 890              Operand value)
 891          {
 892              return invocationId != null
 893                  ? context.Add(Instruction.Store, storageKind, null, Const((int)ioVariable), invocationId, value)
 894                  : context.Add(Instruction.Store, storageKind, null, Const((int)ioVariable), value);
 895          }
 896  
 897          public static Operand Store(
 898              this EmitterContext context,
 899              StorageKind storageKind,
 900              IoVariable ioVariable,
 901              Operand invocationId,
 902              Operand elemIndex,
 903              Operand value)
 904          {
 905              return invocationId != null
 906                  ? context.Add(Instruction.Store, storageKind, null, Const((int)ioVariable), invocationId, elemIndex, value)
 907                  : context.Add(Instruction.Store, storageKind, null, Const((int)ioVariable), elemIndex, value);
 908          }
 909  
 910          public static Operand Store(
 911              this EmitterContext context,
 912              StorageKind storageKind,
 913              IoVariable ioVariable,
 914              Operand invocationId,
 915              Operand arrayIndex,
 916              Operand elemIndex,
 917              Operand value)
 918          {
 919              return invocationId != null
 920                  ? context.Add(Instruction.Store, storageKind, null, Const((int)ioVariable), invocationId, arrayIndex, elemIndex, value)
 921                  : context.Add(Instruction.Store, storageKind, null, Const((int)ioVariable), arrayIndex, elemIndex, value);
 922          }
 923  
 924          public static void TextureSample(
 925              this EmitterContext context,
 926              SamplerType type,
 927              TextureFlags flags,
 928              SetBindingPair setAndBinding,
 929              int compMask,
 930              Operand[] dests,
 931              Operand[] sources)
 932          {
 933              context.Add(new TextureOperation(
 934                  Instruction.TextureSample,
 935                  type,
 936                  TextureFormat.Unknown,
 937                  flags,
 938                  setAndBinding.SetIndex,
 939                  setAndBinding.Binding,
 940                  compMask,
 941                  dests,
 942                  sources));
 943          }
 944  
 945          public static Operand TextureQuerySamples(
 946              this EmitterContext context,
 947              SamplerType type,
 948              TextureFlags flags,
 949              SetBindingPair setAndBinding,
 950              Operand[] sources)
 951          {
 952              Operand dest = Local();
 953  
 954              context.Add(new TextureOperation(
 955                  Instruction.TextureQuerySamples,
 956                  type,
 957                  TextureFormat.Unknown,
 958                  flags,
 959                  setAndBinding.SetIndex,
 960                  setAndBinding.Binding,
 961                  0,
 962                  new[] { dest },
 963                  sources));
 964  
 965              return dest;
 966          }
 967  
 968          public static Operand TextureQuerySize(
 969              this EmitterContext context,
 970              SamplerType type,
 971              TextureFlags flags,
 972              SetBindingPair setAndBinding,
 973              int compIndex,
 974              Operand[] sources)
 975          {
 976              Operand dest = Local();
 977  
 978              context.Add(new TextureOperation(
 979                  Instruction.TextureQuerySize,
 980                  type,
 981                  TextureFormat.Unknown,
 982                  flags,
 983                  setAndBinding.SetIndex,
 984                  setAndBinding.Binding,
 985                  compIndex,
 986                  new[] { dest },
 987                  sources));
 988  
 989              return dest;
 990          }
 991  
 992          public static Operand UnpackDouble2x32High(this EmitterContext context, Operand a)
 993          {
 994              return UnpackDouble2x32(context, a, 1);
 995          }
 996  
 997          public static Operand UnpackDouble2x32Low(this EmitterContext context, Operand a)
 998          {
 999              return UnpackDouble2x32(context, a, 0);
1000          }
1001  
1002          private static Operand UnpackDouble2x32(this EmitterContext context, Operand a, int index)
1003          {
1004              Operand dest = Local();
1005  
1006              context.Add(new Operation(Instruction.UnpackDouble2x32, index, dest, a));
1007  
1008              return dest;
1009          }
1010  
1011          public static Operand UnpackHalf2x16High(this EmitterContext context, Operand a)
1012          {
1013              return UnpackHalf2x16(context, a, 1);
1014          }
1015  
1016          public static Operand UnpackHalf2x16Low(this EmitterContext context, Operand a)
1017          {
1018              return UnpackHalf2x16(context, a, 0);
1019          }
1020  
1021          private static Operand UnpackHalf2x16(this EmitterContext context, Operand a, int index)
1022          {
1023              Operand dest = Local();
1024  
1025              context.Add(new Operation(Instruction.UnpackHalf2x16, index, dest, a));
1026  
1027              return dest;
1028          }
1029  
1030          public static Operand VoteAll(this EmitterContext context, Operand a)
1031          {
1032              return context.Add(Instruction.VoteAll, Local(), a);
1033          }
1034  
1035          public static Operand VoteAllEqual(this EmitterContext context, Operand a)
1036          {
1037              return context.Add(Instruction.VoteAllEqual, Local(), a);
1038          }
1039  
1040          public static Operand VoteAny(this EmitterContext context, Operand a)
1041          {
1042              return context.Add(Instruction.VoteAny, Local(), a);
1043          }
1044      }
1045  }