For PR950:
[oota-llvm.git] / tools / llvm-upgrade / UpgradeParser.y.cvs
1 //===-- UpgradeParser.y - Upgrade parser for llvm assmbly -------*- C++ -*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file was developed by Reid Spencer and is distributed under the
6 // University of Illinois Open Source License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 //  This file implements the bison parser for LLVM 1.9 assembly language.
11 //
12 //===----------------------------------------------------------------------===//
13
14 %{
15 #include "ParserInternals.h"
16 #include <llvm/ADT/StringExtras.h>
17 #include <algorithm>
18 #include <map>
19 #include <utility>
20 #include <iostream>
21 #include <cassert>
22
23 #define YYERROR_VERBOSE 1
24 #define YYINCLUDED_STDLIB_H
25 #define YYDEBUG 1
26
27 int yylex();                       // declaration" of xxx warnings.
28 int yyparse();
29 extern int yydebug;
30
31 static std::string CurFilename;
32 static std::ostream *O = 0;
33 std::istream* LexInput = 0;
34 unsigned SizeOfPointer = 32;
35 static uint64_t unique = 1;
36
37 typedef std::vector<TypeInfo> TypeVector;
38 static TypeVector EnumeratedTypes;
39 typedef std::map<std::string,TypeInfo> TypeMap;
40 static TypeMap NamedTypes;
41 static TypeMap Globals;
42
43 void destroy(ValueList* VL) {
44   while (!VL->empty()) {
45     ValueInfo& VI = VL->back();
46     VI.destroy();
47     VL->pop_back();
48   }
49   delete VL;
50 }
51
52 void UpgradeAssembly(const std::string &infile, std::istream& in, 
53                      std::ostream &out, bool debug)
54 {
55   Upgradelineno = 1; 
56   CurFilename = infile;
57   LexInput = &in;
58   yydebug = debug;
59   O = &out;
60
61   if (yyparse()) {
62     std::cerr << "Parse failed.\n";
63     exit(1);
64   }
65 }
66
67 static void ResolveType(TypeInfo& Ty) {
68   if (Ty.oldTy == UnresolvedTy) {
69     TypeMap::iterator I = NamedTypes.find(*Ty.newTy);
70     if (I != NamedTypes.end()) {
71       Ty.oldTy = I->second.oldTy;
72       Ty.elemTy = I->second.elemTy;
73     } else {
74       std::string msg("Can't resolve type: ");
75       msg += *Ty.newTy;
76       yyerror(msg.c_str());
77     }
78   } else if (Ty.oldTy == NumericTy) {
79     unsigned ref = atoi(&((Ty.newTy->c_str())[1])); // Skip the '\\'
80     if (ref < EnumeratedTypes.size()) {
81       Ty.oldTy = EnumeratedTypes[ref].oldTy;
82       Ty.elemTy = EnumeratedTypes[ref].elemTy;
83     } else {
84       std::string msg("Can't resolve type: ");
85       msg += *Ty.newTy;
86       yyerror(msg.c_str());
87     }
88   }
89   // otherwise its already resolved.
90 }
91
92 static const char* getCastOpcode(
93   std::string& Source, const TypeInfo& SrcTy, const TypeInfo& DstTy) 
94 {
95   unsigned SrcBits = SrcTy.getBitWidth();
96   unsigned DstBits = DstTy.getBitWidth();
97   const char* opcode = "bitcast";
98   // Run through the possibilities ...
99   if (DstTy.isIntegral()) {                        // Casting to integral
100     if (SrcTy.isIntegral()) {                      // Casting from integral
101       if (DstBits < SrcBits)
102         opcode = "trunc";
103       else if (DstBits > SrcBits) {                // its an extension
104         if (SrcTy.isSigned())
105           opcode ="sext";                          // signed -> SEXT
106         else
107           opcode = "zext";                         // unsigned -> ZEXT
108       } else {
109         opcode = "bitcast";                        // Same size, No-op cast
110       }
111     } else if (SrcTy.isFloatingPoint()) {          // Casting from floating pt
112       if (DstTy.isSigned()) 
113         opcode = "fptosi";                         // FP -> sint
114       else
115         opcode = "fptoui";                         // FP -> uint 
116     } else if (SrcTy.isPacked()) {
117       assert(DstBits == SrcTy.getBitWidth() &&
118                "Casting packed to integer of different width");
119         opcode = "bitcast";                        // same size, no-op cast
120     } else {
121       assert(SrcTy.isPointer() &&
122              "Casting from a value that is not first-class type");
123       opcode = "ptrtoint";                         // ptr -> int
124     }
125   } else if (DstTy.isFloatingPoint()) {           // Casting to floating pt
126     if (SrcTy.isIntegral()) {                     // Casting from integral
127       if (SrcTy.isSigned())
128         opcode = "sitofp";                         // sint -> FP
129       else
130         opcode = "uitofp";                         // uint -> FP
131     } else if (SrcTy.isFloatingPoint()) {         // Casting from floating pt
132       if (DstBits < SrcBits) {
133         opcode = "fptrunc";                        // FP -> smaller FP
134       } else if (DstBits > SrcBits) {
135         opcode = "fpext";                          // FP -> larger FP
136       } else  {
137         opcode ="bitcast";                         // same size, no-op cast
138       }
139     } else if (SrcTy.isPacked()) {
140       assert(DstBits == SrcTy.getBitWidth() &&
141              "Casting packed to floating point of different width");
142         opcode = "bitcast";                        // same size, no-op cast
143     } else {
144       assert(0 && "Casting pointer or non-first class to float");
145     }
146   } else if (DstTy.isPacked()) {
147     if (SrcTy.isPacked()) {
148       assert(DstTy.getBitWidth() == SrcTy.getBitWidth() &&
149              "Casting packed to packed of different widths");
150       opcode = "bitcast";                          // packed -> packed
151     } else if (DstTy.getBitWidth() == SrcBits) {
152       opcode = "bitcast";                          // float/int -> packed
153     } else {
154       assert(!"Illegal cast to packed (wrong type or size)");
155     }
156   } else if (DstTy.isPointer()) {
157     if (SrcTy.isPointer()) {
158       opcode = "bitcast";                          // ptr -> ptr
159     } else if (SrcTy.isIntegral()) {
160       opcode = "inttoptr";                         // int -> ptr
161     } else {
162       assert(!"Casting invalid type to pointer");
163     }
164   } else {
165     assert(!"Casting to type that is not first-class");
166   }
167   return opcode;
168 }
169
170 static std::string getCastUpgrade(
171   const std::string& Src, TypeInfo& SrcTy, TypeInfo& DstTy, bool isConst)
172 {
173   std::string Result;
174   std::string Source = Src;
175   if (SrcTy.isFloatingPoint() && DstTy.isPointer()) {
176     // fp -> ptr cast is no longer supported but we must upgrade this
177     // by doing a double cast: fp -> int -> ptr
178     if (isConst)
179       Source = "ulong fptoui(" + Source + " to ulong)";
180     else {
181       *O << "    %cast_upgrade" << unique << " = fptoui " << Source 
182          << " to ulong\n";
183       Source = "ulong %cast_upgrade" + llvm::utostr(unique);
184     }
185     // Update the SrcTy for the getCastOpcode call below
186     SrcTy.destroy();
187     SrcTy.newTy = new std::string("ulong");
188     SrcTy.oldTy = ULongTy;
189   } else if (DstTy.oldTy == BoolTy && SrcTy.oldTy != BoolTy) {
190     // cast ptr %x to  bool was previously defined as setne ptr %x, null
191     // The ptrtoint semantic is to truncate, not compare so we must retain
192     // the original intent by replace the cast with a setne
193     const char* comparator = SrcTy.isPointer() ? ", null" : 
194       (SrcTy.isFloatingPoint() ? ", 0.0" : ", 0");
195     const char* compareOp = SrcTy.isFloatingPoint() ? "fcmp one " : "icmp ne ";
196     if (isConst) { 
197       Result = "(" + Source + comparator + ")";
198       Result = compareOp + Result;
199     } else
200       Result = compareOp + Source + comparator;
201     return Result; // skip cast processing below
202   }
203   ResolveType(SrcTy);
204   ResolveType(DstTy);
205   std::string Opcode(getCastOpcode(Source, SrcTy, DstTy));
206   if (isConst)
207     Result += Opcode + "( " + Source + " to " + *DstTy.newTy + ")";
208   else
209     Result += Opcode + " " + Source + " to " + *DstTy.newTy;
210   return Result;
211 }
212
213 const char* getDivRemOpcode(const std::string& opcode, const TypeInfo& TI) {
214   const char* op = opcode.c_str();
215   TypeInfo Ty = TI;
216   ResolveType(Ty);
217   if (Ty.isPacked())
218     Ty.oldTy = Ty.getElementType();
219   if (opcode == "div")
220     if (Ty.isFloatingPoint())
221       op = "fdiv";
222     else if (Ty.isUnsigned())
223       op = "udiv";
224     else if (Ty.isSigned())
225       op = "sdiv";
226     else
227       yyerror("Invalid type for div instruction");
228   else if (opcode == "rem")
229     if (Ty.isFloatingPoint())
230       op = "frem";
231     else if (Ty.isUnsigned())
232       op = "urem";
233     else if (Ty.isSigned())
234       op = "srem";
235     else
236       yyerror("Invalid type for rem instruction");
237   return op;
238 }
239
240 std::string 
241 getCompareOp(const std::string& setcc, const TypeInfo& TI) {
242   assert(setcc.length() == 5);
243   char cc1 = setcc[3];
244   char cc2 = setcc[4];
245   assert(cc1 == 'e' || cc1 == 'n' || cc1 == 'l' || cc1 == 'g');
246   assert(cc2 == 'q' || cc2 == 'e' || cc2 == 'e' || cc2 == 't');
247   std::string result("xcmp xxx");
248   result[6] = cc1;
249   result[7] = cc2;
250   if (TI.isFloatingPoint()) {
251     result[0] = 'f';
252     result[5] = 'o';
253     if (cc1 == 'n')
254       result[5] = 'u'; // NE maps to unordered
255     else
256       result[5] = 'o'; // everything else maps to ordered
257   } else if (TI.isIntegral() || TI.isPointer()) {
258     result[0] = 'i';
259     if ((cc1 == 'e' && cc2 == 'q') || (cc1 == 'n' && cc2 == 'e'))
260       result.erase(5,1);
261     else if (TI.isSigned())
262       result[5] = 's';
263     else if (TI.isUnsigned() || TI.isPointer() || TI.isBool())
264       result[5] = 'u';
265     else
266       yyerror("Invalid integral type for setcc");
267   }
268   return result;
269 }
270
271 %}
272
273 // %file-prefix="UpgradeParser"
274
275 %union {
276   std::string*    String;
277   TypeInfo        Type;
278   ValueInfo       Value;
279   ConstInfo       Const;
280   ValueList*      ValList;
281 }
282
283 %token <Type>   VOID BOOL SBYTE UBYTE SHORT USHORT INT UINT LONG ULONG
284 %token <Type>   FLOAT DOUBLE LABEL 
285 %token <String> OPAQUE ESINT64VAL EUINT64VAL SINTVAL UINTVAL FPVAL
286 %token <String> NULL_TOK UNDEF ZEROINITIALIZER TRUETOK FALSETOK
287 %token <String> TYPE VAR_ID LABELSTR STRINGCONSTANT
288 %token <String> IMPLEMENTATION BEGINTOK ENDTOK
289 %token <String> DECLARE GLOBAL CONSTANT SECTION VOLATILE
290 %token <String> TO DOTDOTDOT CONST INTERNAL LINKONCE WEAK 
291 %token <String> DLLIMPORT DLLEXPORT EXTERN_WEAK APPENDING
292 %token <String> NOT EXTERNAL TARGET TRIPLE ENDIAN POINTERSIZE LITTLE BIG
293 %token <String> ALIGN UNINITIALIZED
294 %token <String> DEPLIBS CALL TAIL ASM_TOK MODULE SIDEEFFECT
295 %token <String> CC_TOK CCC_TOK CSRETCC_TOK FASTCC_TOK COLDCC_TOK
296 %token <String> X86_STDCALLCC_TOK X86_FASTCALLCC_TOK
297 %token <String> DATALAYOUT
298 %token <String> RET BR SWITCH INVOKE EXCEPT UNWIND UNREACHABLE
299 %token <String> ADD SUB MUL DIV UDIV SDIV FDIV REM UREM SREM FREM AND OR XOR
300 %token <String> SETLE SETGE SETLT SETGT SETEQ SETNE  // Binary Comparators
301 %token <String> ICMP FCMP EQ NE SLT SGT SLE SGE OEQ ONE OLT OGT OLE OGE 
302 %token <String> ORD UNO UEQ UNE ULT UGT ULE UGE
303 %token <String> MALLOC ALLOCA FREE LOAD STORE GETELEMENTPTR
304 %token <String> PHI_TOK SELECT SHL SHR ASHR LSHR VAARG
305 %token <String> EXTRACTELEMENT INSERTELEMENT SHUFFLEVECTOR
306 %token <String> CAST TRUNC ZEXT SEXT FPTRUNC FPEXT FPTOUI FPTOSI UITOFP SITOFP 
307 %token <String> PTRTOINT INTTOPTR BITCAST
308
309 %type <String> OptAssign OptLinkage OptCallingConv OptAlign OptCAlign 
310 %type <String> SectionString OptSection GlobalVarAttributes GlobalVarAttribute
311 %type <String> ArgTypeListI ConstExpr DefinitionList
312 %type <String> ConstPool TargetDefinition LibrariesDefinition LibList OptName
313 %type <String> ArgVal ArgListH ArgList FunctionHeaderH BEGIN FunctionHeader END
314 %type <String> Function FunctionProto BasicBlock TypeListI
315 %type <String> InstructionList BBTerminatorInst JumpTable Inst PHIList
316 %type <String> OptTailCall InstVal OptVolatile Unwind
317 %type <String> MemoryInst SymbolicValueRef OptSideEffect GlobalType
318 %type <String> FnDeclareLinkage BasicBlockList BigOrLittle AsmBlock
319 %type <String> Name ConstValueRef ConstVector External
320 %type <String> ShiftOps SetCondOps LogicalOps ArithmeticOps CastOps
321 %type <String> IPredicates FPredicates
322
323 %type <ValList> ValueRefList ValueRefListE IndexList
324
325 %type <Type> IntType SIntType UIntType FPType TypesV Types 
326 %type <Type> PrimType UpRTypesV UpRTypes
327
328 %type <String> IntVal EInt64Val 
329 %type <Const>  ConstVal
330
331 %type <Value> ValueRef ResolvedVal 
332
333 %start Module
334
335 %%
336
337 // Handle constant integer size restriction and conversion...
338 IntVal : SINTVAL | UINTVAL ;
339 EInt64Val : ESINT64VAL | EUINT64VAL;
340
341 // Operations that are notably excluded from this list include:
342 // RET, BR, & SWITCH because they end basic blocks and are treated specially.
343 ArithmeticOps: ADD | SUB | MUL | DIV | UDIV | SDIV | FDIV 
344              | REM | UREM | SREM | FREM;
345 LogicalOps   : AND | OR | XOR;
346 SetCondOps   : SETLE | SETGE | SETLT | SETGT | SETEQ | SETNE;
347 IPredicates  : EQ | NE | SLT | SGT | SLE | SGE | ULT | UGT | ULE | UGE;
348 FPredicates  : OEQ | ONE | OLT | OGT | OLE | OGE | ORD | UNO | UEQ | UNE
349              | ULT | UGT | ULE | UGE | TRUETOK | FALSETOK;
350 ShiftOps     : SHL | SHR | ASHR | LSHR;
351 CastOps      : TRUNC | ZEXT | SEXT | FPTRUNC | FPEXT | FPTOUI | FPTOSI | 
352                UITOFP | SITOFP | PTRTOINT | INTTOPTR | BITCAST | CAST
353              ;
354
355 // These are some types that allow classification if we only want a particular 
356 // thing... for example, only a signed, unsigned, or integral type.
357 SIntType :  LONG |  INT |  SHORT | SBYTE;
358 UIntType : ULONG | UINT | USHORT | UBYTE;
359 IntType  : SIntType | UIntType;
360 FPType   : FLOAT | DOUBLE;
361
362 // OptAssign - Value producing statements have an optional assignment component
363 OptAssign : Name '=' {
364     $$ = $1;
365   }
366   | /*empty*/ {
367     $$ = new std::string(""); 
368   };
369
370 OptLinkage 
371   : INTERNAL | LINKONCE | WEAK | APPENDING | DLLIMPORT | DLLEXPORT 
372   | EXTERN_WEAK 
373   | /*empty*/   { $$ = new std::string(""); } ;
374
375 OptCallingConv 
376   : CCC_TOK | CSRETCC_TOK | FASTCC_TOK | COLDCC_TOK | X86_STDCALLCC_TOK 
377   | X86_FASTCALLCC_TOK 
378   | CC_TOK EUINT64VAL { 
379     *$1 += *$2; 
380     delete $2;
381     $$ = $1; 
382     }
383   | /*empty*/ { $$ = new std::string(""); } ;
384
385 // OptAlign/OptCAlign - An optional alignment, and an optional alignment with
386 // a comma before it.
387 OptAlign 
388   : /*empty*/        { $$ = new std::string(); }
389   | ALIGN EUINT64VAL { *$1 += " " + *$2; delete $2; $$ = $1; };
390
391 OptCAlign 
392   : /*empty*/            { $$ = new std::string(); } 
393   | ',' ALIGN EUINT64VAL { 
394     $2->insert(0, ", "); 
395     *$2 += " " + *$3;
396     delete $3;
397     $$ = $2;
398   };
399
400 SectionString 
401   : SECTION STRINGCONSTANT { 
402     *$1 += " " + *$2;
403     delete $2;
404     $$ = $1;
405   };
406
407 OptSection : /*empty*/     { $$ = new std::string(); } 
408            | SectionString;
409
410 GlobalVarAttributes 
411     : /* empty */ { $$ = new std::string(); } 
412     | ',' GlobalVarAttribute GlobalVarAttributes  {
413       $2->insert(0, ", ");
414       if (!$3->empty())
415         *$2 += " " + *$3;
416       delete $3;
417       $$ = $2;
418     };
419
420 GlobalVarAttribute 
421     : SectionString 
422     | ALIGN EUINT64VAL {
423       *$1 += " " + *$2;
424       delete $2;
425       $$ = $1;
426     };
427
428 //===----------------------------------------------------------------------===//
429 // Types includes all predefined types... except void, because it can only be
430 // used in specific contexts (function returning void for example).  To have
431 // access to it, a user must explicitly use TypesV.
432 //
433
434 // TypesV includes all of 'Types', but it also includes the void type.
435 TypesV    : Types    | VOID ;
436 UpRTypesV : UpRTypes | VOID ; 
437 Types     : UpRTypes ;
438
439 // Derived types are added later...
440 //
441 PrimType : BOOL | SBYTE | UBYTE | SHORT  | USHORT | INT   | UINT ;
442 PrimType : LONG | ULONG | FLOAT | DOUBLE | LABEL;
443 UpRTypes 
444   : OPAQUE { 
445     $$.newTy = $1; 
446     $$.oldTy = OpaqueTy; 
447   } 
448   | SymbolicValueRef { 
449     $$.newTy = $1;
450     $$.oldTy = UnresolvedTy;
451   }
452   | PrimType { 
453     $$ = $1; 
454   }
455   | '\\' EUINT64VAL {                   // Type UpReference
456     $2->insert(0, "\\");
457     $$.newTy = $2;
458     $$.oldTy = NumericTy;
459   }
460   | UpRTypesV '(' ArgTypeListI ')' {           // Function derived type?
461     *$1.newTy += "( " + *$3 + " )";
462     delete $3;
463     $$.newTy = $1.newTy;
464     $$.oldTy = FunctionTy;
465   }
466   | '[' EUINT64VAL 'x' UpRTypes ']' {          // Sized array type?
467     $2->insert(0,"[ ");
468     *$2 += " x " + *$4.newTy + " ]";
469     delete $4.newTy;
470     $$.newTy = $2;
471     $$.oldTy = ArrayTy;
472     $$.elemTy = $4.oldTy;
473   }
474   | '<' EUINT64VAL 'x' UpRTypes '>' {          // Packed array type?
475     $2->insert(0,"< ");
476     *$2 += " x " + *$4.newTy + " >";
477     delete $4.newTy;
478     $$.newTy = $2;
479     $$.oldTy = PackedTy;
480     $$.elemTy = $4.oldTy;
481   }
482   | '{' TypeListI '}' {                        // Structure type?
483     $2->insert(0, "{ ");
484     *$2 += " }";
485     $$.newTy = $2;
486     $$.oldTy = StructTy;
487   }
488   | '{' '}' {                                  // Empty structure type?
489     $$.newTy = new std::string("{}");
490     $$.oldTy = StructTy;
491   }
492   | UpRTypes '*' {                             // Pointer type?
493     *$1.newTy += '*';
494     $$.elemTy = $1.oldTy;
495     $1.oldTy = PointerTy;
496     $$ = $1;
497   };
498
499 // TypeList - Used for struct declarations and as a basis for function type 
500 // declaration type lists
501 //
502 TypeListI 
503   : UpRTypes {
504     $$ = $1.newTy;
505   }
506   | TypeListI ',' UpRTypes {
507     *$1 += ", " + *$3.newTy;
508     delete $3.newTy;
509     $$ = $1;
510   };
511
512 // ArgTypeList - List of types for a function type declaration...
513 ArgTypeListI 
514   : TypeListI 
515   | TypeListI ',' DOTDOTDOT {
516     *$1 += ", ...";
517     delete $3;
518     $$ = $1;
519   }
520   | DOTDOTDOT {
521     $$ = $1;
522   }
523   | /*empty*/ {
524     $$ = new std::string();
525   };
526
527 // ConstVal - The various declarations that go into the constant pool.  This
528 // production is used ONLY to represent constants that show up AFTER a 'const',
529 // 'constant' or 'global' token at global scope.  Constants that can be inlined
530 // into other expressions (such as integers and constexprs) are handled by the
531 // ResolvedVal, ValueRef and ConstValueRef productions.
532 //
533 ConstVal: Types '[' ConstVector ']' { // Nonempty unsized arr
534     $$.type = $1;
535     $$.cnst = new std::string(*$1.newTy);
536     *$$.cnst += " [ " + *$3 + " ]";
537     delete $3;
538   }
539   | Types '[' ']' {
540     $$.type = $1;
541     $$.cnst = new std::string(*$1.newTy);
542     *$$.cnst += "[ ]";
543   }
544   | Types 'c' STRINGCONSTANT {
545     $$.type = $1;
546     $$.cnst = new std::string(*$1.newTy);
547     *$$.cnst += " c" + *$3;
548     delete $3;
549   }
550   | Types '<' ConstVector '>' { // Nonempty unsized arr
551     $$.type = $1;
552     $$.cnst = new std::string(*$1.newTy);
553     *$$.cnst += " < " + *$3 + " >";
554     delete $3;
555   }
556   | Types '{' ConstVector '}' {
557     $$.type = $1;
558     $$.cnst = new std::string(*$1.newTy);
559     *$$.cnst += " { " + *$3 + " }";
560     delete $3;
561   }
562   | Types '{' '}' {
563     $$.type = $1;
564     $$.cnst = new std::string(*$1.newTy);
565     *$$.cnst += " {}";
566   }
567   | Types NULL_TOK {
568     $$.type = $1;
569     $$.cnst = new std::string(*$1.newTy);
570     *$$.cnst +=  " " + *$2;
571     delete $2;
572   }
573   | Types UNDEF {
574     $$.type = $1;
575     $$.cnst = new std::string(*$1.newTy);
576     *$$.cnst += " " + *$2;
577     delete $2;
578   }
579   | Types SymbolicValueRef {
580     $$.type = $1;
581     $$.cnst = new std::string(*$1.newTy);
582     *$$.cnst += " " + *$2;
583     delete $2;
584   }
585   | Types ConstExpr {
586     $$.type = $1;
587     $$.cnst = new std::string(*$1.newTy);
588     *$$.cnst += " " + *$2;
589     delete $2;
590   }
591   | Types ZEROINITIALIZER {
592     $$.type = $1;
593     $$.cnst = new std::string(*$1.newTy);
594     *$$.cnst += " " + *$2;
595     delete $2;
596   }
597   | SIntType EInt64Val {      // integral constants
598     $$.type = $1;
599     $$.cnst = new std::string(*$1.newTy);
600     *$$.cnst += " " + *$2;
601     delete $2;
602   }
603   | UIntType EUINT64VAL {            // integral constants
604     $$.type = $1;
605     $$.cnst = new std::string(*$1.newTy);
606     *$$.cnst += " " + *$2;
607     delete $2;
608   }
609   | BOOL TRUETOK {                      // Boolean constants
610     $$.type = $1;
611     $$.cnst = new std::string(*$1.newTy);
612     *$$.cnst += " " + *$2;
613     delete $2;
614   }
615   | BOOL FALSETOK {                     // Boolean constants
616     $$.type = $1;
617     $$.cnst = new std::string(*$1.newTy);
618     *$$.cnst += " " + *$2;
619     delete $2;
620   }
621   | FPType FPVAL {                   // Float & Double constants
622     $$.type = $1;
623     $$.cnst = new std::string(*$1.newTy);
624     *$$.cnst += " " + *$2;
625     delete $2;
626   };
627
628
629 ConstExpr: CastOps '(' ConstVal TO Types ')' {
630     std::string source = *$3.cnst;
631     TypeInfo DstTy = $5;
632     ResolveType(DstTy);
633     if (*$1 == "cast") {
634       // Call getCastUpgrade to upgrade the old cast
635       $$ = new std::string(getCastUpgrade(source, $3.type, $5, true));
636     } else {
637       // Nothing to upgrade, just create the cast constant expr
638       $$ = new std::string(*$1);
639       *$$ += "( " + source + " to " + *$5.newTy + ")";
640     }
641     delete $1; $3.destroy(); delete $4; $5.destroy();
642   }
643   | GETELEMENTPTR '(' ConstVal IndexList ')' {
644     *$1 += "(" + *$3.cnst;
645     for (unsigned i = 0; i < $4->size(); ++i) {
646       ValueInfo& VI = (*$4)[i];
647       *$1 += ", " + *VI.val;
648       VI.destroy();
649     }
650     *$1 += ")";
651     $$ = $1;
652     $3.destroy();
653     delete $4;
654   }
655   | SELECT '(' ConstVal ',' ConstVal ',' ConstVal ')' {
656     *$1 += "(" + *$3.cnst + "," + *$5.cnst + "," + *$7.cnst + ")";
657     $3.destroy(); $5.destroy(); $7.destroy();
658     $$ = $1;
659   }
660   | ArithmeticOps '(' ConstVal ',' ConstVal ')' {
661     const char* op = getDivRemOpcode(*$1, $3.type); 
662     $$ = new std::string(op);
663     *$$ += "(" + *$3.cnst + "," + *$5.cnst + ")";
664     delete $1; $3.destroy(); $5.destroy();
665   }
666   | LogicalOps '(' ConstVal ',' ConstVal ')' {
667     *$1 += "(" + *$3.cnst + "," + *$5.cnst + ")";
668     $3.destroy(); $5.destroy();
669     $$ = $1;
670   }
671   | SetCondOps '(' ConstVal ',' ConstVal ')' {
672     *$1 = getCompareOp(*$1, $3.type);
673     *$1 += "(" + *$3.cnst + "," + *$5.cnst + ")";
674     $3.destroy(); $5.destroy();
675     $$ = $1;
676   }
677   | ICMP IPredicates '(' ConstVal ',' ConstVal ')' {
678     *$1 += "(" + *$2 + "," + *$4.cnst + "," + *$6.cnst + ")";
679     delete $2; $4.destroy(); $6.destroy();
680     $$ = $1;
681   }
682   | FCMP FPredicates '(' ConstVal ',' ConstVal ')' {
683     *$1 += "(" + *$2 + "," + *$4.cnst + "," + *$6.cnst + ")";
684     delete $2; $4.destroy(); $6.destroy();
685     $$ = $1;
686   }
687   | ShiftOps '(' ConstVal ',' ConstVal ')' {
688     const char* shiftop = $1->c_str();
689     if (*$1 == "shr")
690       shiftop = ($3.type.isUnsigned()) ? "lshr" : "ashr";
691     $$ = new std::string(shiftop);
692     *$$ += "(" + *$3.cnst + "," + *$5.cnst + ")";
693     delete $1; $3.destroy(); $5.destroy();
694   }
695   | EXTRACTELEMENT '(' ConstVal ',' ConstVal ')' {
696     *$1 += "(" + *$3.cnst + "," + *$5.cnst + ")";
697     $3.destroy(); $5.destroy();
698     $$ = $1;
699   }
700   | INSERTELEMENT '(' ConstVal ',' ConstVal ',' ConstVal ')' {
701     *$1 += "(" + *$3.cnst + "," + *$5.cnst + "," + *$7.cnst + ")";
702     $3.destroy(); $5.destroy(); $7.destroy();
703     $$ = $1;
704   }
705   | SHUFFLEVECTOR '(' ConstVal ',' ConstVal ',' ConstVal ')' {
706     *$1 += "(" + *$3.cnst + "," + *$5.cnst + "," + *$7.cnst + ")";
707     $3.destroy(); $5.destroy(); $7.destroy();
708     $$ = $1;
709   };
710
711
712 // ConstVector - A list of comma separated constants.
713
714 ConstVector 
715   : ConstVector ',' ConstVal {
716     *$1 += ", " + *$3.cnst;
717     $3.destroy();
718     $$ = $1;
719   }
720   | ConstVal { $$ = new std::string(*$1.cnst); $1.destroy(); }
721   ;
722
723
724 // GlobalType - Match either GLOBAL or CONSTANT for global declarations...
725 GlobalType : GLOBAL | CONSTANT ;
726
727
728 //===----------------------------------------------------------------------===//
729 //                             Rules to match Modules
730 //===----------------------------------------------------------------------===//
731
732 // Module rule: Capture the result of parsing the whole file into a result
733 // variable...
734 //
735 Module : DefinitionList {
736 };
737
738 // DefinitionList - Top level definitions
739 //
740 DefinitionList : DefinitionList Function {
741     $$ = 0;
742   } 
743   | DefinitionList FunctionProto {
744     *O << *$2 << "\n";
745     delete $2;
746     $$ = 0;
747   }
748   | DefinitionList MODULE ASM_TOK AsmBlock {
749     *O << "module asm " << " " << *$4 << "\n";
750     $$ = 0;
751   }  
752   | DefinitionList IMPLEMENTATION {
753     *O << "implementation\n";
754     $$ = 0;
755   }
756   | ConstPool { $$ = 0; }
757
758 External : EXTERNAL | UNINITIALIZED { $$ = $1; *$$ = "external"; }
759
760 // ConstPool - Constants with optional names assigned to them.
761 ConstPool : ConstPool OptAssign TYPE TypesV {
762     EnumeratedTypes.push_back($4);
763     if (!$2->empty()) {
764       NamedTypes[*$2].newTy = new std::string(*$4.newTy);
765       NamedTypes[*$2].oldTy = $4.oldTy;
766       NamedTypes[*$2].elemTy = $4.elemTy;
767       *O << *$2 << " = ";
768     }
769     *O << "type " << *$4.newTy << "\n";
770     delete $2; delete $3; $4.destroy();
771     $$ = 0;
772   }
773   | ConstPool FunctionProto {       // Function prototypes can be in const pool
774     *O << *$2 << "\n";
775     delete $2;
776     $$ = 0;
777   }
778   | ConstPool MODULE ASM_TOK AsmBlock {  // Asm blocks can be in the const pool
779     *O << *$2 << " " << *$3 << " " << *$4 << "\n";
780     delete $2; delete $3; delete $4; 
781     $$ = 0;
782   }
783   | ConstPool OptAssign OptLinkage GlobalType ConstVal  GlobalVarAttributes {
784     if (!$2->empty()) {
785       *O << *$2 << " = ";
786       Globals[*$2] = $5.type.clone();
787     }
788     *O << *$3 << " " << *$4 << " " << *$5.cnst << " " << *$6 << "\n";
789     delete $2; delete $3; delete $4; $5.destroy(); delete $6; 
790     $$ = 0;
791   }
792   | ConstPool OptAssign External GlobalType Types  GlobalVarAttributes {
793     if (!$2->empty()) {
794       *O << *$2 << " = ";
795       Globals[*$2] = $5.clone();
796     }
797     *O <<  *$3 << " " << *$4 << " " << *$5.newTy << " " << *$6 << "\n";
798     delete $2; delete $3; delete $4; $5.destroy(); delete $6;
799     $$ = 0;
800   }
801   | ConstPool OptAssign DLLIMPORT GlobalType Types  GlobalVarAttributes {
802     if (!$2->empty()) {
803       *O << *$2 << " = ";
804       Globals[*$2] = $5.clone();
805     }
806     *O << *$3 << " " << *$4 << " " << *$5.newTy << " " << *$6 << "\n";
807     delete $2; delete $3; delete $4; $5.destroy(); delete $6;
808     $$ = 0;
809   }
810   | ConstPool OptAssign EXTERN_WEAK GlobalType Types  GlobalVarAttributes {
811     if (!$2->empty()) {
812       *O << *$2 << " = ";
813       Globals[*$2] = $5.clone();
814     }
815     *O << *$3 << " " << *$4 << " " << *$5.newTy << " " << *$6 << "\n";
816     delete $2; delete $3; delete $4; $5.destroy(); delete $6;
817     $$ = 0;
818   }
819   | ConstPool TARGET TargetDefinition { 
820     *O << *$2 << " " << *$3 << "\n";
821     delete $2; delete $3;
822     $$ = 0;
823   }
824   | ConstPool DEPLIBS '=' LibrariesDefinition {
825     *O << *$2 << " = " << *$4 << "\n";
826     delete $2; delete $4;
827     $$ = 0;
828   }
829   | /* empty: end of list */ { 
830     $$ = 0;
831   };
832
833
834 AsmBlock : STRINGCONSTANT ;
835
836 BigOrLittle : BIG | LITTLE 
837
838 TargetDefinition 
839   : ENDIAN '=' BigOrLittle {
840     *$1 += " = " + *$3;
841     delete $3;
842     $$ = $1;
843   }
844   | POINTERSIZE '=' EUINT64VAL {
845     *$1 += " = " + *$3;
846     if (*$3 == "64")
847       SizeOfPointer = 64;
848     delete $3;
849     $$ = $1;
850   }
851   | TRIPLE '=' STRINGCONSTANT {
852     *$1 += " = " + *$3;
853     delete $3;
854     $$ = $1;
855   }
856   | DATALAYOUT '=' STRINGCONSTANT {
857     *$1 += " = " + *$3;
858     delete $3;
859     $$ = $1;
860   };
861
862 LibrariesDefinition 
863   : '[' LibList ']' {
864     $2->insert(0, "[ ");
865     *$2 += " ]";
866     $$ = $2;
867   };
868
869 LibList 
870   : LibList ',' STRINGCONSTANT {
871     *$1 += ", " + *$3;
872     delete $3;
873     $$ = $1;
874   }
875   | STRINGCONSTANT 
876   | /* empty: end of list */ {
877     $$ = new std::string();
878   };
879
880 //===----------------------------------------------------------------------===//
881 //                       Rules to match Function Headers
882 //===----------------------------------------------------------------------===//
883
884 Name : VAR_ID | STRINGCONSTANT;
885 OptName : Name | /*empty*/ { $$ = new std::string(); };
886
887 ArgVal : Types OptName {
888   $$ = $1.newTy;
889   if (!$2->empty())
890     *$$ += " " + *$2;
891   delete $2;
892 };
893
894 ArgListH : ArgListH ',' ArgVal {
895     *$1 += ", " + *$3;
896     delete $3;
897   }
898   | ArgVal {
899     $$ = $1;
900   };
901
902 ArgList : ArgListH {
903     $$ = $1;
904   }
905   | ArgListH ',' DOTDOTDOT {
906     *$1 += ", ...";
907     $$ = $1;
908     delete $3;
909   }
910   | DOTDOTDOT {
911     $$ = $1;
912   }
913   | /* empty */ { $$ = new std::string(); };
914
915 FunctionHeaderH : OptCallingConv TypesV Name '(' ArgList ')' 
916                   OptSection OptAlign {
917     if (!$1->empty()) {
918       *$1 += " ";
919     }
920     *$1 += *$2.newTy + " " + *$3 + "(" + *$5 + ")";
921     if (!$7->empty()) {
922       *$1 += " " + *$7;
923     }
924     if (!$8->empty()) {
925       *$1 += " " + *$8;
926     }
927     $2.destroy();
928     delete $3;
929     delete $5;
930     delete $7;
931     delete $8;
932     $$ = $1;
933   };
934
935 BEGIN : BEGINTOK { $$ = new std::string("{"); delete $1; }
936   | '{' { $$ = new std::string ("{"); }
937
938 FunctionHeader : OptLinkage FunctionHeaderH BEGIN {
939   if (!$1->empty()) {
940     *O << *$1 << " ";
941   }
942   *O << *$2 << " " << *$3 << "\n";
943   delete $1; delete $2; delete $3;
944   $$ = 0;
945 };
946
947 END : ENDTOK { $$ = new std::string("}"); delete $1; }
948     | '}' { $$ = new std::string("}"); };
949
950 Function : FunctionHeader BasicBlockList END {
951   if ($2)
952     *O << *$2;
953   *O << '\n' << *$3 << "\n";
954   $$ = 0;
955 };
956
957 FnDeclareLinkage
958   : /*default*/ { $$ = new std::string(); }
959   | DLLIMPORT    
960   | EXTERN_WEAK 
961   ;
962   
963 FunctionProto 
964   : DECLARE FnDeclareLinkage FunctionHeaderH { 
965     if (!$2->empty())
966       *$1 += " " + *$2;
967     *$1 += " " + *$3;
968     delete $2;
969     delete $3;
970     $$ = $1;
971   };
972
973 //===----------------------------------------------------------------------===//
974 //                        Rules to match Basic Blocks
975 //===----------------------------------------------------------------------===//
976
977 OptSideEffect : /* empty */ { $$ = new std::string(); }
978   | SIDEEFFECT;
979
980 ConstValueRef 
981   : ESINT64VAL | EUINT64VAL | FPVAL | TRUETOK | FALSETOK | NULL_TOK | UNDEF
982   | ZEROINITIALIZER 
983   | '<' ConstVector '>' { 
984     $2->insert(0, "<");
985     *$2 += ">";
986     $$ = $2;
987   }
988   | ConstExpr 
989   | ASM_TOK OptSideEffect STRINGCONSTANT ',' STRINGCONSTANT {
990     if (!$2->empty()) {
991       *$1 += " " + *$2;
992     }
993     *$1 += " " + *$3 + ", " + *$5;
994     delete $2; delete $3; delete $5;
995     $$ = $1;
996   };
997
998 SymbolicValueRef : IntVal | Name ;
999
1000 // ValueRef - A reference to a definition... either constant or symbolic
1001 ValueRef 
1002   : SymbolicValueRef {
1003     $$.val = $1;
1004     $$.constant = false;
1005     $$.type.newTy = 0;
1006     $$.type.oldTy = UnresolvedTy;
1007   }
1008   | ConstValueRef {
1009     $$.val = $1;
1010     $$.constant = true;
1011     $$.type.newTy = 0;
1012     $$.type.oldTy = UnresolvedTy;
1013   }
1014   ;
1015
1016 // ResolvedVal - a <type> <value> pair.  This is used only in cases where the
1017 // type immediately preceeds the value reference, and allows complex constant
1018 // pool references (for things like: 'ret [2 x int] [ int 12, int 42]')
1019 ResolvedVal : Types ValueRef {
1020     $$ = $2;
1021     $$.type = $1;
1022     $$.val->insert(0, *$1.newTy + " ");
1023   };
1024
1025 BasicBlockList : BasicBlockList BasicBlock {
1026     $$ = 0;
1027   }
1028   | BasicBlock { // Do not allow functions with 0 basic blocks   
1029     $$ = 0;
1030   };
1031
1032
1033 // Basic blocks are terminated by branching instructions: 
1034 // br, br/cc, switch, ret
1035 //
1036 BasicBlock : InstructionList BBTerminatorInst  {
1037     $$ = 0;
1038   };
1039
1040 InstructionList : InstructionList Inst {
1041     *O << "    " << *$2 << "\n";
1042     delete $2;
1043     $$ = 0;
1044   }
1045   | /* empty */ {
1046     $$ = 0;
1047   }
1048   | LABELSTR {
1049     *O << *$1 << "\n";
1050     delete $1;
1051     $$ = 0;
1052   };
1053
1054 Unwind : UNWIND | EXCEPT { $$ = $1; *$$ = "unwind"; }
1055
1056 BBTerminatorInst : RET ResolvedVal {              // Return with a result...
1057     *O << "    " << *$1 << " " << *$2.val << "\n";
1058     delete $1; $2.destroy();
1059     $$ = 0;
1060   }
1061   | RET VOID {                                       // Return with no result...
1062     *O << "    " << *$1 << " " << *$2.newTy << "\n";
1063     delete $1; $2.destroy();
1064     $$ = 0;
1065   }
1066   | BR LABEL ValueRef {                         // Unconditional Branch...
1067     *O << "    " << *$1 << " " << *$2.newTy << " " << *$3.val << "\n";
1068     delete $1; $2.destroy(); $3.destroy();
1069     $$ = 0;
1070   }                                                  // Conditional Branch...
1071   | BR BOOL ValueRef ',' LABEL ValueRef ',' LABEL ValueRef {  
1072     *O << "    " << *$1 << " " << *$2.newTy << " " << *$3.val << ", " 
1073        << *$5.newTy << " " << *$6.val << ", " << *$8.newTy << " " 
1074        << *$9.val << "\n";
1075     delete $1; $2.destroy(); $3.destroy(); $5.destroy(); $6.destroy(); 
1076     $8.destroy(); $9.destroy();
1077     $$ = 0;
1078   }
1079   | SWITCH IntType ValueRef ',' LABEL ValueRef '[' JumpTable ']' {
1080     *O << "    " << *$1 << " " << *$2.newTy << " " << *$3.val << ", " 
1081        << *$5.newTy << " " << *$6.val << " [" << *$8 << " ]\n";
1082     delete $1; $2.destroy(); $3.destroy(); $5.destroy(); $6.destroy(); 
1083     delete $8;
1084     $$ = 0;
1085   }
1086   | SWITCH IntType ValueRef ',' LABEL ValueRef '[' ']' {
1087     *O << "    " << *$1 << " " << *$2.newTy << " " << *$3.val << ", " 
1088        << *$5.newTy << " " << *$6.val << "[]\n";
1089     delete $1; $2.destroy(); $3.destroy(); $5.destroy(); $6.destroy();
1090     $$ = 0;
1091   }
1092   | OptAssign INVOKE OptCallingConv TypesV ValueRef '(' ValueRefListE ')'
1093     TO LABEL ValueRef Unwind LABEL ValueRef {
1094     *O << "    ";
1095     if (!$1->empty())
1096       *O << *$1 << " = ";
1097     *O << *$2 << " " << *$3 << " " << *$4.newTy << " " << *$5.val << " (";
1098     for (unsigned i = 0; i < $7->size(); ++i) {
1099       ValueInfo& VI = (*$7)[i];
1100       *O << *VI.val;
1101       if (i+1 < $7->size())
1102         *O << ", ";
1103       VI.destroy();
1104     }
1105     *O << ") " << *$9 << " " << *$10.newTy << " " << *$11.val << " " 
1106        << *$12 << " " << *$13.newTy << " " << *$14.val << "\n";
1107     delete $1; delete $2; delete $3; $4.destroy(); $5.destroy(); delete $7; 
1108     delete $9; $10.destroy(); $11.destroy(); delete $12; $13.destroy(); 
1109     $14.destroy(); 
1110     $$ = 0;
1111   }
1112   | Unwind {
1113     *O << "    " << *$1 << "\n";
1114     delete $1;
1115     $$ = 0;
1116   }
1117   | UNREACHABLE {
1118     *O << "    " << *$1 << "\n";
1119     delete $1;
1120     $$ = 0;
1121   };
1122
1123 JumpTable : JumpTable IntType ConstValueRef ',' LABEL ValueRef {
1124     *$1 += " " + *$2.newTy + " " + *$3 + ", " + *$5.newTy + " " + *$6.val;
1125     $2.destroy(); delete $3; $5.destroy(); $6.destroy();
1126     $$ = $1;
1127   }
1128   | IntType ConstValueRef ',' LABEL ValueRef {
1129     $2->insert(0, *$1.newTy + " " );
1130     *$2 += ", " + *$4.newTy + " " + *$5.val;
1131     $1.destroy(); $4.destroy(); $5.destroy();
1132     $$ = $2;
1133   };
1134
1135 Inst 
1136   : OptAssign InstVal {
1137     if (!$1->empty())
1138       *$1 += " = ";
1139     *$1 += *$2;
1140     delete $2;
1141     $$ = $1; 
1142   };
1143
1144 PHIList 
1145   : Types '[' ValueRef ',' ValueRef ']' {    // Used for PHI nodes
1146     $3.val->insert(0, *$1.newTy + "[");
1147     *$3.val += "," + *$5.val + "]";
1148     $1.destroy(); $5.destroy();
1149     $$ = new std::string(*$3.val);
1150     $3.destroy();
1151   }
1152   | PHIList ',' '[' ValueRef ',' ValueRef ']' {
1153     *$1 += ", [" + *$4.val + "," + *$6.val + "]";
1154     $4.destroy(); $6.destroy();
1155     $$ = $1;
1156   };
1157
1158
1159 ValueRefList 
1160   : ResolvedVal { 
1161     $$ = new ValueList();
1162     $$->push_back($1);
1163   }
1164   | ValueRefList ',' ResolvedVal {
1165     $1->push_back($3);
1166     $$ = $1;
1167   };
1168
1169 // ValueRefListE - Just like ValueRefList, except that it may also be empty!
1170 ValueRefListE 
1171   : ValueRefList  { $$ = $1; }
1172   | /*empty*/ { $$ = new ValueList(); }
1173   ;
1174
1175 OptTailCall 
1176   : TAIL CALL {
1177     *$1 += " " + *$2;
1178     delete $2;
1179     $$ = $1;
1180   }
1181   | CALL 
1182   ;
1183
1184 InstVal : ArithmeticOps Types ValueRef ',' ValueRef {
1185     const char* op = getDivRemOpcode(*$1, $2); 
1186     $$ = new std::string(op);
1187     *$$ += " " + *$2.newTy + " " + *$3.val + ", " + *$5.val;
1188     delete $1; $2.destroy(); $3.destroy(); $5.destroy();
1189   }
1190   | LogicalOps Types ValueRef ',' ValueRef {
1191     *$1 += " " + *$2.newTy + " " + *$3.val + ", " + *$5.val;
1192     $2.destroy(); $3.destroy(); $5.destroy();
1193     $$ = $1;
1194   }
1195   | SetCondOps Types ValueRef ',' ValueRef {
1196     *$1 = getCompareOp(*$1, $2);
1197     *$1 += " " + *$2.newTy + " " + *$3.val + ", " + *$5.val;
1198     $2.destroy(); $3.destroy(); $5.destroy();
1199     $$ = $1;
1200   }
1201   | ICMP IPredicates Types ValueRef ',' ValueRef ')' {
1202     *$1 += " " + *$2 + " " + *$4.val + "," + *$6.val + ")";
1203     delete $2; $4.destroy(); $6.destroy();
1204     $$ = $1;
1205   }
1206   | FCMP FPredicates Types ValueRef ',' ValueRef ')' {
1207     *$1 += " " + *$2 + " " + *$4.val + "," + *$6.val + ")";
1208     delete $2; $4.destroy(); $6.destroy();
1209     $$ = $1;
1210   }
1211   | NOT ResolvedVal {
1212     *$1 += " " + *$2.val;
1213     $2.destroy();
1214     $$ = $1;
1215   }
1216   | ShiftOps ResolvedVal ',' ResolvedVal {
1217     const char* shiftop = $1->c_str();
1218     if (*$1 == "shr")
1219       shiftop = ($2.type.isUnsigned()) ? "lshr" : "ashr";
1220     $$ = new std::string(shiftop);
1221     *$$ += " " + *$2.val + ", " + *$4.val;
1222     delete $1; $2.destroy(); $4.destroy();
1223   }
1224   | CastOps ResolvedVal TO Types {
1225     std::string source = *$2.val;
1226     TypeInfo SrcTy = $2.type;
1227     TypeInfo DstTy = $4;
1228     ResolveType(DstTy);
1229     $$ = new std::string();
1230     if (*$1 == "cast") {
1231       *$$ +=  getCastUpgrade(source, SrcTy, DstTy, false);
1232     } else {
1233       *$$ += *$1 + " " + source + " to " + *DstTy.newTy;
1234     }
1235     delete $1; $2.destroy();
1236     delete $3; $4.destroy();
1237   }
1238   | SELECT ResolvedVal ',' ResolvedVal ',' ResolvedVal {
1239     *$1 += " " + *$2.val + ", " + *$4.val + ", " + *$6.val;
1240     $2.destroy(); $4.destroy(); $6.destroy();
1241     $$ = $1;
1242   }
1243   | VAARG ResolvedVal ',' Types {
1244     *$1 += " " + *$2.val + ", " + *$4.newTy;
1245     $2.destroy(); $4.destroy();
1246     $$ = $1;
1247   }
1248   | EXTRACTELEMENT ResolvedVal ',' ResolvedVal {
1249     *$1 += " " + *$2.val + ", " + *$4.val;
1250     $2.destroy(); $4.destroy();
1251     $$ = $1;
1252   }
1253   | INSERTELEMENT ResolvedVal ',' ResolvedVal ',' ResolvedVal {
1254     *$1 += " " + *$2.val + ", " + *$4.val + ", " + *$6.val;
1255     $2.destroy(); $4.destroy(); $6.destroy();
1256     $$ = $1;
1257   }
1258   | SHUFFLEVECTOR ResolvedVal ',' ResolvedVal ',' ResolvedVal {
1259     *$1 += " " + *$2.val + ", " + *$4.val + ", " + *$6.val;
1260     $2.destroy(); $4.destroy(); $6.destroy();
1261     $$ = $1;
1262   }
1263   | PHI_TOK PHIList {
1264     *$1 += " " + *$2;
1265     delete $2;
1266     $$ = $1;
1267   }
1268   | OptTailCall OptCallingConv TypesV ValueRef '(' ValueRefListE ')'  {
1269     if (!$2->empty())
1270       *$1 += " " + *$2;
1271     if (!$1->empty())
1272       *$1 += " ";
1273     *$1 += *$3.newTy + " " + *$4.val + "(";
1274     for (unsigned i = 0; i < $6->size(); ++i) {
1275       ValueInfo& VI = (*$6)[i];
1276       *$1 += *VI.val;
1277       if (i+1 < $6->size())
1278         *$1 += ", ";
1279       VI.destroy();
1280     }
1281     *$1 += ")";
1282     delete $2; $3.destroy(); $4.destroy(); delete $6;
1283     $$ = $1;
1284   }
1285   | MemoryInst ;
1286
1287
1288 // IndexList - List of indices for GEP based instructions...
1289 IndexList 
1290   : ',' ValueRefList { $$ = $2; }
1291   | /* empty */ {  $$ = new ValueList(); }
1292   ;
1293
1294 OptVolatile 
1295   : VOLATILE 
1296   | /* empty */ { $$ = new std::string(); }
1297   ;
1298
1299 MemoryInst : MALLOC Types OptCAlign {
1300     *$1 += " " + *$2.newTy;
1301     if (!$3->empty())
1302       *$1 += " " + *$3;
1303     $2.destroy(); delete $3;
1304     $$ = $1;
1305   }
1306   | MALLOC Types ',' UINT ValueRef OptCAlign {
1307     *$1 += " " + *$2.newTy + ", " + *$4.newTy + " " + *$5.val;
1308     if (!$6->empty())
1309       *$1 += " " + *$6;
1310     $2.destroy(); $4.destroy(); $5.destroy(); delete $6;
1311     $$ = $1;
1312   }
1313   | ALLOCA Types OptCAlign {
1314     *$1 += " " + *$2.newTy;
1315     if (!$3->empty())
1316       *$1 += " " + *$3;
1317     $2.destroy(); delete $3;
1318     $$ = $1;
1319   }
1320   | ALLOCA Types ',' UINT ValueRef OptCAlign {
1321     *$1 += " " + *$2.newTy + ", " + *$4.newTy + " " + *$5.val;
1322     if (!$6->empty())
1323       *$1 += " " + *$6;
1324     $2.destroy(); $4.destroy(); $5.destroy(); delete $6;
1325     $$ = $1;
1326   }
1327   | FREE ResolvedVal {
1328     *$1 += " " + *$2.val;
1329     $2.destroy();
1330     $$ = $1;
1331   }
1332   | OptVolatile LOAD Types ValueRef {
1333     if (!$1->empty())
1334       *$1 += " ";
1335     *$1 += *$2 + " " + *$3.newTy + " " + *$4.val;
1336     delete $2; $3.destroy(); $4.destroy();
1337     $$ = $1;
1338   }
1339   | OptVolatile STORE ResolvedVal ',' Types ValueRef {
1340     if (!$1->empty())
1341       *$1 += " ";
1342     *$1 += *$2 + " " + *$3.val + ", " + *$5.newTy + " " + *$6.val;
1343     delete $2; $3.destroy(); $5.destroy(); $6.destroy();
1344     $$ = $1;
1345   }
1346   | GETELEMENTPTR Types ValueRef IndexList {
1347     // Upgrade the indices
1348     for (unsigned i = 0; i < $4->size(); ++i) {
1349       ValueInfo& VI = (*$4)[i];
1350       if (VI.type.isUnsigned() && !VI.isConstant() && 
1351           VI.type.getBitWidth() < 64) {
1352         std::string* old = VI.val;
1353         *O << "    %gep_upgrade" << unique << " = zext " << *old 
1354            << " to ulong\n";
1355         VI.val = new std::string("ulong %gep_upgrade" + llvm::utostr(unique++));
1356         VI.type.oldTy = ULongTy;
1357         delete old;
1358       }
1359     }
1360     *$1 += " " + *$2.newTy + " " + *$3.val;
1361     for (unsigned i = 0; i < $4->size(); ++i) {
1362       ValueInfo& VI = (*$4)[i];
1363       *$1 += ", " + *VI.val;
1364       VI.destroy();
1365     }
1366     $2.destroy(); $3.destroy(); delete $4;
1367     $$ = $1;
1368   };
1369
1370 %%
1371
1372 int yyerror(const char *ErrorMsg) {
1373   std::string where 
1374     = std::string((CurFilename == "-") ? std::string("<stdin>") : CurFilename)
1375                   + ":" + llvm::utostr((unsigned) Upgradelineno) + ": ";
1376   std::string errMsg = std::string(ErrorMsg) + "\n" + where + " while reading ";
1377   if (yychar == YYEMPTY || yychar == 0)
1378     errMsg += "end-of-file.";
1379   else
1380     errMsg += "token: '" + std::string(Upgradetext, Upgradeleng) + "'";
1381   std::cerr << errMsg << '\n';
1382   exit(1);
1383 }