xref: /freebsd/contrib/llvm-project/clang/lib/AST/Interp/Opcodes.td (revision db33c6f3ae9d1231087710068ee4ea5398aacca7)
1//===--- Opcodes.td - Opcode defitions for the constexpr VM -----*- C++ -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// Helper file used to generate opcodes, the interpreter and the disassembler.
10//
11//===----------------------------------------------------------------------===//
12
13
14//===----------------------------------------------------------------------===//
15// Types evaluated by the interpreter.
16//===----------------------------------------------------------------------===//
17
18class Type;
19def Bool : Type;
20def Sint8 : Type;
21def Uint8 : Type;
22def Sint16 : Type;
23def Uint16 : Type;
24def Sint32 : Type;
25def Uint32 : Type;
26def Sint64 : Type;
27def Uint64 : Type;
28def IntAP : Type;
29def IntAPS : Type;
30def Float : Type;
31def Ptr : Type;
32def FnPtr : Type;
33def MemberPtr : Type;
34
35//===----------------------------------------------------------------------===//
36// Types transferred to the interpreter.
37//===----------------------------------------------------------------------===//
38
39class ArgType { string Name = ?; bit AsRef = false; }
40def ArgSint8 : ArgType { let Name = "int8_t"; }
41def ArgUint8 : ArgType { let Name = "uint8_t"; }
42def ArgSint16 : ArgType { let Name = "int16_t"; }
43def ArgUint16 : ArgType { let Name = "uint16_t"; }
44def ArgSint32 : ArgType { let Name = "int32_t"; }
45def ArgUint32 : ArgType { let Name = "uint32_t"; }
46def ArgSint64 : ArgType { let Name = "int64_t"; }
47def ArgUint64 : ArgType { let Name = "uint64_t"; }
48def ArgIntAP : ArgType { let Name = "IntegralAP<false>"; let AsRef = true; }
49def ArgIntAPS : ArgType { let Name = "IntegralAP<true>"; let AsRef = true; }
50def ArgFloat : ArgType { let Name = "Floating"; let AsRef = true; }
51def ArgBool : ArgType { let Name = "bool"; }
52
53def ArgFunction : ArgType { let Name = "const Function *"; }
54def ArgRecordDecl : ArgType { let Name = "const RecordDecl *"; }
55def ArgRecordField : ArgType { let Name = "const Record::Field *"; }
56def ArgFltSemantics : ArgType { let Name = "const llvm::fltSemantics *"; }
57def ArgRoundingMode : ArgType { let Name = "llvm::RoundingMode"; }
58def ArgLETD: ArgType { let Name = "const LifetimeExtendedTemporaryDecl *"; }
59def ArgCastKind : ArgType { let Name = "CastKind"; }
60def ArgCallExpr : ArgType { let Name = "const CallExpr *"; }
61def ArgExpr : ArgType { let Name = "const Expr *"; }
62def ArgOffsetOfExpr : ArgType { let Name = "const OffsetOfExpr *"; }
63def ArgDeclRef : ArgType { let Name = "const DeclRefExpr *"; }
64def ArgCCI : ArgType { let Name = "const ComparisonCategoryInfo *"; }
65def ArgDecl : ArgType { let Name = "const Decl*"; }
66def ArgVarDecl : ArgType { let Name = "const VarDecl*"; }
67def ArgDesc : ArgType { let Name = "const Descriptor *"; }
68def ArgPrimType : ArgType { let Name = "PrimType"; }
69def ArgEnumDecl : ArgType { let Name = "const EnumDecl *"; }
70
71//===----------------------------------------------------------------------===//
72// Classes of types instructions operate on.
73//===----------------------------------------------------------------------===//
74
75class TypeClass {
76  list<Type> Types;
77}
78
79def IntegerTypeClass : TypeClass {
80  let Types = [Sint8, Uint8, Sint16, Uint16, Sint32,
81               Uint32, Sint64, Uint64, IntAP, IntAPS];
82}
83
84def FixedSizeIntegralTypeClass : TypeClass {
85  let Types = [Sint8, Uint8, Sint16, Uint16, Sint32,
86               Uint32, Sint64, Uint64, Bool];
87}
88
89def NumberTypeClass : TypeClass {
90  let Types = !listconcat(IntegerTypeClass.Types, [Float]);
91}
92
93def FloatTypeClass : TypeClass {
94  let Types = [Float];
95}
96
97def AluTypeClass : TypeClass {
98  let Types = !listconcat(IntegerTypeClass.Types, [Bool]);
99}
100
101def PtrTypeClass : TypeClass {
102  let Types = [Ptr, FnPtr, MemberPtr];
103}
104
105def BoolTypeClass : TypeClass {
106  let Types = [Bool];
107}
108
109def NonPtrTypeClass : TypeClass {
110  let Types = !listconcat(IntegerTypeClass.Types, [Bool], [Float]);
111}
112
113def AllTypeClass : TypeClass {
114  let Types = !listconcat(AluTypeClass.Types, PtrTypeClass.Types, FloatTypeClass.Types);
115}
116
117def ComparableTypeClass : TypeClass {
118  let Types = !listconcat(AluTypeClass.Types, [Ptr], [Float], [FnPtr]);
119}
120
121class SingletonTypeClass<Type Ty> : TypeClass {
122  let Types = [Ty];
123}
124
125//===----------------------------------------------------------------------===//
126// Record describing all opcodes.
127//===----------------------------------------------------------------------===//
128
129class Opcode {
130  list<TypeClass> Types = [];
131  list<ArgType> Args = [];
132  string Name = "";
133  bit CanReturn = 0;
134  bit ChangesPC = 0;
135  bit HasCustomLink = 0;
136  bit HasCustomEval = 0;
137  bit HasGroup = 0;
138}
139
140class AluOpcode : Opcode {
141  let Types = [AluTypeClass];
142  let HasGroup = 1;
143}
144
145class FloatOpcode : Opcode {
146  let Args = [ArgRoundingMode];
147}
148
149class IntegerOpcode : Opcode {
150  let Types = [IntegerTypeClass];
151  let HasGroup = 1;
152}
153
154//===----------------------------------------------------------------------===//
155// Jump opcodes
156//===----------------------------------------------------------------------===//
157
158class JumpOpcode : Opcode {
159  let Args = [ArgSint32];
160  let ChangesPC = 1;
161  let HasCustomEval = 1;
162}
163
164// [] -> []
165def Jmp : JumpOpcode;
166// [Bool] -> [], jumps if true.
167def Jt : JumpOpcode;
168// [Bool] -> [], jumps if false.
169def Jf : JumpOpcode;
170
171//===----------------------------------------------------------------------===//
172// Returns
173//===----------------------------------------------------------------------===//
174
175// [Value] -> []
176def Ret : Opcode {
177  let Types = [AllTypeClass];
178  let ChangesPC = 1;
179  let CanReturn = 1;
180  let HasGroup = 1;
181  let HasCustomEval = 1;
182}
183// [] -> []
184def RetVoid : Opcode {
185  let CanReturn = 1;
186  let ChangesPC = 1;
187  let HasCustomEval = 1;
188}
189// [Value] -> []
190def RetValue : Opcode {
191  let CanReturn = 1;
192  let ChangesPC = 1;
193  let HasCustomEval = 1;
194}
195// [] -> EXIT
196def NoRet : Opcode {}
197
198
199def Call : Opcode {
200  let Args = [ArgFunction, ArgUint32];
201}
202
203def CallVirt : Opcode {
204  let Args = [ArgFunction, ArgUint32];
205}
206
207def CallBI : Opcode {
208  let Args = [ArgFunction, ArgCallExpr];
209}
210
211def CallPtr : Opcode {
212  let Args = [ArgUint32, ArgCallExpr];
213}
214
215def CallVar : Opcode {
216  let Args = [ArgFunction, ArgUint32];
217}
218
219def OffsetOf : Opcode {
220  let Types = [IntegerTypeClass];
221  let Args = [ArgOffsetOfExpr];
222  let HasGroup = 1;
223}
224
225//===----------------------------------------------------------------------===//
226// Frame management
227//===----------------------------------------------------------------------===//
228
229// [] -> []
230def Destroy : Opcode {
231  let Args = [ArgUint32];
232  let HasCustomEval = 1;
233}
234
235//===----------------------------------------------------------------------===//
236// Constants
237//===----------------------------------------------------------------------===//
238
239class ConstOpcode<Type Ty, ArgType ArgTy> : Opcode {
240  let Types = [SingletonTypeClass<Ty>];
241  let Args = [ArgTy];
242  let Name = "Const";
243}
244
245// [] -> [Integer]
246def ConstSint8 : ConstOpcode<Sint8, ArgSint8>;
247def ConstUint8 : ConstOpcode<Uint8, ArgUint8>;
248def ConstSint16 : ConstOpcode<Sint16, ArgSint16>;
249def ConstUint16 : ConstOpcode<Uint16, ArgUint16>;
250def ConstSint32 : ConstOpcode<Sint32, ArgSint32>;
251def ConstUint32 : ConstOpcode<Uint32, ArgUint32>;
252def ConstSint64 : ConstOpcode<Sint64, ArgSint64>;
253def ConstUint64 : ConstOpcode<Uint64, ArgUint64>;
254def ConstFloat : ConstOpcode<Float, ArgFloat>;
255def constIntAP : ConstOpcode<IntAP, ArgIntAP>;
256def constIntAPS : ConstOpcode<IntAPS, ArgIntAPS>;
257def ConstBool : ConstOpcode<Bool, ArgBool>;
258
259// [] -> [Integer]
260def Zero : Opcode {
261  let Types = [FixedSizeIntegralTypeClass];
262  let HasGroup = 1;
263}
264
265def ZeroIntAP : Opcode {
266  let Args = [ArgUint32];
267}
268
269def ZeroIntAPS : Opcode {
270  let Args = [ArgUint32];
271}
272
273// [] -> [Pointer]
274def Null : Opcode {
275  let Types = [PtrTypeClass];
276  let Args = [ArgDesc];
277  let HasGroup = 1;
278}
279
280//===----------------------------------------------------------------------===//
281// Pointer generation
282//===----------------------------------------------------------------------===//
283class OffsetOpcode : Opcode {
284  let Args = [ArgUint32];
285}
286
287// [] -> [Pointer]
288def GetPtrLocal : OffsetOpcode {
289  bit HasCustomEval = 1;
290}
291// [] -> [Pointer]
292def GetPtrParam : OffsetOpcode;
293// [] -> [Pointer]
294def GetPtrGlobal : OffsetOpcode;
295// [Pointer] -> [Pointer]
296def GetPtrField : OffsetOpcode;
297def GetPtrFieldPop : OffsetOpcode;
298// [Pointer] -> [Pointer]
299def GetPtrActiveField : OffsetOpcode;
300// [] -> [Pointer]
301def GetPtrActiveThisField : OffsetOpcode;
302// [] -> [Pointer]
303def GetPtrThisField : OffsetOpcode;
304// [Pointer] -> [Pointer]
305def GetPtrBase : OffsetOpcode;
306// [Pointer] -> [Pointer]
307def GetPtrBasePop : OffsetOpcode;
308def GetMemberPtrBasePop : Opcode {
309  // Offset of field, which is a base.
310  let Args = [ArgSint32];
311}
312
313
314def FinishInitPop : Opcode;
315def FinishInit    : Opcode;
316
317def GetPtrDerivedPop : Opcode {
318  let Args = [ArgUint32];
319}
320
321// [Pointer] -> [Pointer]
322def GetPtrVirtBasePop : Opcode {
323  // RecordDecl of base class.
324  let Args = [ArgRecordDecl];
325}
326// [] -> [Pointer]
327def GetPtrThisBase : Opcode {
328  // Offset of field, which is a base.
329  let Args = [ArgUint32];
330}
331// [] -> [Pointer]
332def GetPtrThisVirtBase : Opcode {
333  // RecordDecl of base class.
334  let Args = [ArgRecordDecl];
335}
336// [] -> [Pointer]
337def This : Opcode;
338
339// [] -> [Pointer]
340def RVOPtr : Opcode;
341
342// [Pointer] -> [Pointer]
343def NarrowPtr : Opcode;
344// [Pointer] -> [Pointer]
345def ExpandPtr : Opcode;
346// [Pointer, Offset] -> [Pointer]
347def ArrayElemPtr : AluOpcode;
348def ArrayElemPtrPop : AluOpcode;
349
350def ArrayElemPop : Opcode {
351  let Args = [ArgUint32];
352  let Types = [AllTypeClass];
353  let HasGroup = 1;
354}
355
356def ArrayElem : Opcode {
357  let Args = [ArgUint32];
358  let Types = [AllTypeClass];
359  let HasGroup = 1;
360}
361
362def CopyArray : Opcode {
363  let Args = [ArgUint32, ArgUint32, ArgUint32];
364  let Types = [AllTypeClass];
365  let HasGroup = 1;
366}
367
368//===----------------------------------------------------------------------===//
369// Direct field accessors
370//===----------------------------------------------------------------------===//
371
372class AccessOpcode : Opcode {
373  let Types = [AllTypeClass];
374  let Args = [ArgUint32];
375  let HasGroup = 1;
376}
377
378class BitFieldOpcode : Opcode {
379  let Types = [AluTypeClass];
380  let Args = [ArgRecordField];
381  let HasGroup = 1;
382}
383
384// [] -> [Pointer]
385def GetLocal : AccessOpcode { let HasCustomEval = 1; }
386// [] -> [Pointer]
387def SetLocal : AccessOpcode { let HasCustomEval = 1; }
388
389def CheckDecl : Opcode {
390  let Args = [ArgVarDecl];
391}
392
393def CheckEnumValue : Opcode {
394  let Args = [ArgEnumDecl];
395  let Types = [FixedSizeIntegralTypeClass];
396  let HasGroup = 1;
397}
398
399// [] -> [Value]
400def GetGlobal : AccessOpcode;
401def GetGlobalUnchecked : AccessOpcode;
402// [Value] -> []
403def InitGlobal : AccessOpcode;
404// [Value] -> []
405def InitGlobalTemp : AccessOpcode {
406  let Args = [ArgUint32, ArgLETD];
407}
408// [Pointer] -> [Pointer]
409def InitGlobalTempComp : Opcode {
410  let Args = [ArgLETD];
411}
412// [Value] -> []
413def SetGlobal : AccessOpcode;
414
415// [] -> [Value]
416def GetParam : AccessOpcode;
417// [Value] -> []
418def SetParam : AccessOpcode;
419
420// [Pointer] -> [Pointer, Value]
421def GetField : AccessOpcode;
422// [Pointer] -> [Value]
423def GetFieldPop : AccessOpcode;
424// [] -> [Value]
425def GetThisField : AccessOpcode;
426
427// [Pointer, Value] -> [Pointer]
428def SetField : AccessOpcode;
429// [Value] -> []
430def SetThisField : AccessOpcode;
431
432// [Value] -> []
433def InitThisField : AccessOpcode;
434// [Value] -> []
435def InitThisFieldActive : AccessOpcode;
436// [Value] -> []
437def InitThisBitField : Opcode {
438  let Types = [AluTypeClass];
439  let Args = [ArgRecordField, ArgUint32];
440  let HasGroup = 1;
441}
442// [Pointer, Value] -> []
443def InitField : AccessOpcode;
444// [Pointer, Value] -> []
445def InitBitField : BitFieldOpcode;
446// [Pointer, Value] -> []
447def InitFieldActive : AccessOpcode;
448
449//===----------------------------------------------------------------------===//
450// Pointer access
451//===----------------------------------------------------------------------===//
452
453class LoadOpcode : Opcode {
454  let Types = [AllTypeClass];
455  let HasGroup = 1;
456}
457
458// [Pointer] -> [Pointer, Value]
459def Load : LoadOpcode {}
460// [Pointer] -> [Value]
461def LoadPop : LoadOpcode {}
462
463class StoreOpcode : Opcode {
464  let Types = [AllTypeClass];
465  let HasGroup = 1;
466}
467
468class StoreBitFieldOpcode : Opcode {
469  let Types = [AluTypeClass];
470  let HasGroup = 1;
471}
472
473// [Pointer, Value] -> [Pointer]
474def Store : StoreOpcode {}
475// [Pointer, Value] -> []
476def StorePop : StoreOpcode {}
477
478// [Pointer, Value] -> [Pointer]
479def StoreBitField : StoreBitFieldOpcode {}
480// [Pointer, Value] -> []
481def StoreBitFieldPop : StoreBitFieldOpcode {}
482
483// [Pointer, Value] -> []
484def Init : StoreOpcode {}
485def InitPop : StoreOpcode {}
486// [Pointer, Value] -> [Pointer]
487def InitElem : Opcode {
488  let Types = [AllTypeClass];
489  let Args = [ArgUint32];
490  let HasGroup = 1;
491}
492// [Pointer, Value] -> []
493def InitElemPop : Opcode {
494  let Types = [AllTypeClass];
495  let Args = [ArgUint32];
496  let HasGroup = 1;
497}
498
499//===----------------------------------------------------------------------===//
500// Pointer arithmetic.
501//===----------------------------------------------------------------------===//
502
503// [Pointer, Integral] -> [Pointer]
504def AddOffset : AluOpcode;
505// [Pointer, Integral] -> [Pointer]
506def SubOffset : AluOpcode;
507
508// [Pointer, Pointer] -> [Integral]
509def SubPtr : Opcode {
510  let Types = [IntegerTypeClass];
511  let HasGroup = 1;
512}
513
514// [Pointer] -> [Pointer]
515def IncPtr : Opcode;
516// [Pointer] -> [Pointer]
517def DecPtr : Opcode;
518
519//===----------------------------------------------------------------------===//
520// Function pointers.
521//===----------------------------------------------------------------------===//
522def GetFnPtr : Opcode {
523  let Args = [ArgFunction];
524}
525
526def GetIntPtr : Opcode {
527  let Types = [AluTypeClass];
528  let Args = [ArgDesc];
529  let HasGroup = 1;
530}
531
532//===----------------------------------------------------------------------===//
533// Binary operators.
534//===----------------------------------------------------------------------===//
535
536// [Real, Real] -> [Real]
537def Add  : AluOpcode;
538def Addf : FloatOpcode;
539def Sub  : AluOpcode;
540def Subf : FloatOpcode;
541def Mul  : AluOpcode;
542def Mulf : FloatOpcode;
543def Mulc : Opcode {
544  let Types = [NumberTypeClass];
545  let HasGroup = 1;
546}
547def Rem  : IntegerOpcode;
548def Div  : IntegerOpcode;
549def Divf : FloatOpcode;
550def Divc : Opcode {
551  let Types = [NumberTypeClass];
552  let HasGroup = 1;
553}
554
555def BitAnd : IntegerOpcode;
556def BitOr : IntegerOpcode;
557def BitXor : IntegerOpcode;
558
559def Shl : Opcode {
560  let Types = [IntegerTypeClass, IntegerTypeClass];
561  let HasGroup = 1;
562}
563
564def Shr : Opcode {
565  let Types = [IntegerTypeClass, IntegerTypeClass];
566  let HasGroup = 1;
567}
568
569//===----------------------------------------------------------------------===//
570// Unary operators.
571//===----------------------------------------------------------------------===//
572
573// [Real] -> [Real]
574def Inv: Opcode {
575  let Types = [BoolTypeClass];
576  let HasGroup = 1;
577}
578
579// Increment and decrement.
580def Inc: AluOpcode;
581def IncPop : AluOpcode;
582def Dec: AluOpcode;
583def DecPop: AluOpcode;
584
585// Float increment and decrement.
586def Incf: FloatOpcode;
587def IncfPop : FloatOpcode;
588def Decf: FloatOpcode;
589def DecfPop : FloatOpcode;
590
591// [Real] -> [Real]
592def Neg: Opcode {
593  let Types = [NonPtrTypeClass];
594  let HasGroup = 1;
595}
596
597// [Real] -> [Real]
598def Comp: Opcode {
599  let Types = [IntegerTypeClass];
600  let HasGroup = 1;
601}
602
603//===----------------------------------------------------------------------===//
604// Cast, CastFP.
605//===----------------------------------------------------------------------===//
606
607def FromCastTypeClass : TypeClass {
608  let Types = [Uint8, Sint8, Uint16, Sint16, Uint32, Sint32, Uint64, Sint64, Bool, IntAP, IntAPS];
609}
610
611def ToCastTypeClass : TypeClass {
612  let Types = [Uint8, Sint8, Uint16, Sint16, Uint32, Sint32, Uint64, Sint64, Bool];
613}
614
615def Cast: Opcode {
616  let Types = [FromCastTypeClass, ToCastTypeClass];
617  let HasGroup = 1;
618}
619
620def CastFP : Opcode {
621  let Args = [ArgFltSemantics, ArgRoundingMode];
622}
623
624def FixedSizeIntegralTypes : TypeClass {
625  let Types = [Uint8, Sint8, Uint16, Sint16, Uint32, Sint32, Uint64, Sint64, Bool];
626}
627
628def CastAP : Opcode {
629  let Types = [AluTypeClass];
630  let Args = [ArgUint32];
631  let HasGroup = 1;
632}
633
634def CastAPS : Opcode {
635  let Types = [AluTypeClass];
636  let Args = [ArgUint32];
637  let HasGroup = 1;
638}
639
640// Cast an integer to a floating type
641def CastIntegralFloating : Opcode {
642  let Types = [AluTypeClass];
643  let Args = [ArgFltSemantics, ArgRoundingMode];
644  let HasGroup = 1;
645}
646
647// Cast a floating to an integer type
648def CastFloatingIntegral : Opcode {
649  let Types = [FixedSizeIntegralTypes];
650  let Args = [];
651  let HasGroup = 1;
652}
653
654def CastFloatingIntegralAP : Opcode {
655  let Args = [ArgUint32];
656}
657
658def CastFloatingIntegralAPS : Opcode {
659  let Args = [ArgUint32];
660}
661
662def CastPointerIntegral : Opcode {
663  let Types = [FixedSizeIntegralTypeClass];
664  let HasGroup = 1;
665}
666def CastPointerIntegralAP : Opcode {
667  let Args = [ArgUint32];
668}
669def CastPointerIntegralAPS : Opcode {
670  let Args = [ArgUint32];
671}
672def PtrPtrCast : Opcode {
673  let Args = [ArgBool];
674
675}
676
677def DecayPtr : Opcode {
678  let Types = [PtrTypeClass, PtrTypeClass];
679  let HasGroup = 1;
680}
681
682//===----------------------------------------------------------------------===//
683// Comparison opcodes.
684//===----------------------------------------------------------------------===//
685
686class EqualityOpcode : Opcode {
687  let Types = [AllTypeClass];
688  let HasGroup = 1;
689}
690
691def EQ : EqualityOpcode;
692def NE : EqualityOpcode;
693
694class ComparisonOpcode : Opcode {
695  let Types = [ComparableTypeClass];
696  let HasGroup = 1;
697}
698
699def CMP3 : ComparisonOpcode {
700  let Args = [ArgCCI];
701}
702
703def LT : ComparisonOpcode;
704def LE : ComparisonOpcode;
705def GT : ComparisonOpcode;
706def GE : ComparisonOpcode;
707
708//===----------------------------------------------------------------------===//
709// Stack management.
710//===----------------------------------------------------------------------===//
711
712// [Value] -> []
713def Pop : Opcode {
714  let Types = [AllTypeClass];
715  let HasGroup = 1;
716}
717
718// [Value] -> [Value, Value]
719def Dup : Opcode {
720  let Types = [AllTypeClass];
721  let HasGroup = 1;
722}
723
724// [] -> []
725def Invalid : Opcode {}
726def Unsupported : Opcode {}
727def Error : Opcode {}
728def InvalidCast : Opcode {
729  let Args = [ArgCastKind];
730}
731
732def InvalidDeclRef : Opcode {
733  let Args = [ArgDeclRef];
734}
735
736def SizelessVectorElementSize : Opcode;
737
738def Assume : Opcode;
739
740def ArrayDecay : Opcode;
741
742def CheckNonNullArg : Opcode {
743  let Types = [PtrTypeClass];
744  let HasGroup = 1;
745}
746
747def Memcpy : Opcode;
748
749def ToMemberPtr : Opcode;
750def CastMemberPtrPtr : Opcode;
751def GetMemberPtr : Opcode {
752  let Args = [ArgDecl];
753}
754def GetMemberPtrBase : Opcode;
755def GetMemberPtrDecl : Opcode;
756
757//===----------------------------------------------------------------------===//
758// Debugging.
759//===----------------------------------------------------------------------===//
760def Dump : Opcode;
761
762def Alloc : Opcode {
763  let Args = [ArgDesc];
764}
765
766def AllocN : Opcode {
767  let Types = [IntegerTypeClass];
768  let Args = [ArgPrimType, ArgExpr, ArgBool];
769  let HasGroup = 1;
770}
771
772def AllocCN : Opcode {
773  let Types = [IntegerTypeClass];
774  let Args = [ArgDesc, ArgBool];
775  let HasGroup = 1;
776}
777
778def Free : Opcode {
779  let Args = [ArgBool];
780}
781