6f002e1cb38f73e6921878e381f19333aebb29aa
[oota-llvm.git] / tools / llvm-mc / AsmParser.cpp
1 //===- AsmParser.cpp - Parser for Assembly Files --------------------------===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // This class implements the parser for assembly files.
11 //
12 //===----------------------------------------------------------------------===//
13
14 #include "AsmParser.h"
15
16 #include "llvm/ADT/SmallString.h"
17 #include "llvm/ADT/Twine.h"
18 #include "llvm/MC/MCContext.h"
19 #include "llvm/MC/MCExpr.h"
20 #include "llvm/MC/MCInst.h"
21 #include "llvm/MC/MCSectionMachO.h"
22 #include "llvm/MC/MCStreamer.h"
23 #include "llvm/MC/MCSymbol.h"
24 #include "llvm/Support/SourceMgr.h"
25 #include "llvm/Support/raw_ostream.h"
26 #include "llvm/Target/TargetAsmParser.h"
27 using namespace llvm;
28
29 // Mach-O section uniquing.
30 //
31 // FIXME: Figure out where this should live, it should be shared by
32 // TargetLoweringObjectFile.
33 typedef StringMap<const MCSectionMachO*> MachOUniqueMapTy;
34
35 AsmParser::~AsmParser() {
36   // If we have the MachO uniquing map, free it.
37   delete (MachOUniqueMapTy*)SectionUniquingMap;
38 }
39
40 const MCSection *AsmParser::getMachOSection(const StringRef &Segment,
41                                             const StringRef &Section,
42                                             unsigned TypeAndAttributes,
43                                             unsigned Reserved2,
44                                             SectionKind Kind) const {
45   // We unique sections by their segment/section pair.  The returned section
46   // may not have the same flags as the requested section, if so this should be
47   // diagnosed by the client as an error.
48   
49   // Create the map if it doesn't already exist.
50   if (SectionUniquingMap == 0)
51     SectionUniquingMap = new MachOUniqueMapTy();
52   MachOUniqueMapTy &Map = *(MachOUniqueMapTy*)SectionUniquingMap;
53   
54   // Form the name to look up.
55   SmallString<64> Name;
56   Name += Segment;
57   Name.push_back(',');
58   Name += Section;
59
60   // Do the lookup, if we have a hit, return it.
61   const MCSectionMachO *&Entry = Map[Name.str()];
62
63   // FIXME: This should validate the type and attributes.
64   if (Entry) return Entry;
65
66   // Otherwise, return a new section.
67   return Entry = MCSectionMachO::Create(Segment, Section, TypeAndAttributes,
68                                         Reserved2, Kind, Ctx);
69 }
70
71 void AsmParser::Warning(SMLoc L, const Twine &Msg) {
72   Lexer.PrintMessage(L, Msg.str(), "warning");
73 }
74
75 bool AsmParser::Error(SMLoc L, const Twine &Msg) {
76   Lexer.PrintMessage(L, Msg.str(), "error");
77   return true;
78 }
79
80 bool AsmParser::TokError(const char *Msg) {
81   Lexer.PrintMessage(Lexer.getLoc(), Msg, "error");
82   return true;
83 }
84
85 bool AsmParser::Run() {
86   // Create the initial section.
87   //
88   // FIXME: Support -n.
89   // FIXME: Target hook & command line option for initial section.
90   Out.SwitchSection(getMachOSection("__TEXT", "__text",
91                                     MCSectionMachO::S_ATTR_PURE_INSTRUCTIONS,
92                                     0, SectionKind()));
93
94
95   // Prime the lexer.
96   Lexer.Lex();
97   
98   bool HadError = false;
99   
100   AsmCond StartingCondState = TheCondState;
101
102   // While we have input, parse each statement.
103   while (Lexer.isNot(AsmToken::Eof)) {
104     // Handle conditional assembly here before calling ParseStatement()
105     if (Lexer.getKind() == AsmToken::Identifier) {
106       // If we have an identifier, handle it as the key symbol.
107       AsmToken ID = Lexer.getTok();
108       SMLoc IDLoc = ID.getLoc();
109       StringRef IDVal = ID.getString();
110
111       if (IDVal == ".if" ||
112           IDVal == ".elseif" ||
113           IDVal == ".else" ||
114           IDVal == ".endif") {
115         if (!ParseConditionalAssemblyDirectives(IDVal, IDLoc))
116           continue;
117         HadError = true;
118         EatToEndOfStatement();
119         continue;
120       }
121     }
122     if (TheCondState.Ignore) {
123       EatToEndOfStatement();
124       continue;
125     }
126
127     if (!ParseStatement()) continue;
128   
129     // We had an error, remember it and recover by skipping to the next line.
130     HadError = true;
131     EatToEndOfStatement();
132   }
133
134   if (TheCondState.TheCond != StartingCondState.TheCond ||
135       TheCondState.Ignore != StartingCondState.Ignore)
136     return TokError("unmatched .ifs or .elses");
137   
138   if (!HadError)  
139     Out.Finish();
140
141   return HadError;
142 }
143
144 /// ParseConditionalAssemblyDirectives - parse the conditional assembly
145 /// directives
146 bool AsmParser::ParseConditionalAssemblyDirectives(StringRef Directive,
147                                                    SMLoc DirectiveLoc) {
148   if (Directive == ".if")
149     return ParseDirectiveIf(DirectiveLoc);
150   if (Directive == ".elseif")
151     return ParseDirectiveElseIf(DirectiveLoc);
152   if (Directive == ".else")
153     return ParseDirectiveElse(DirectiveLoc);
154   if (Directive == ".endif")
155     return ParseDirectiveEndIf(DirectiveLoc);
156   return true;
157 }
158
159 /// EatToEndOfStatement - Throw away the rest of the line for testing purposes.
160 void AsmParser::EatToEndOfStatement() {
161   while (Lexer.isNot(AsmToken::EndOfStatement) &&
162          Lexer.isNot(AsmToken::Eof))
163     Lexer.Lex();
164   
165   // Eat EOL.
166   if (Lexer.is(AsmToken::EndOfStatement))
167     Lexer.Lex();
168 }
169
170
171 /// ParseParenExpr - Parse a paren expression and return it.
172 /// NOTE: This assumes the leading '(' has already been consumed.
173 ///
174 /// parenexpr ::= expr)
175 ///
176 bool AsmParser::ParseParenExpr(const MCExpr *&Res) {
177   if (ParseExpression(Res)) return true;
178   if (Lexer.isNot(AsmToken::RParen))
179     return TokError("expected ')' in parentheses expression");
180   Lexer.Lex();
181   return false;
182 }
183
184 MCSymbol *AsmParser::CreateSymbol(StringRef Name) {
185   if (MCSymbol *S = Ctx.LookupSymbol(Name))
186     return S;
187
188   // If the label starts with L it is an assembler temporary label.
189   if (Name.startswith("L"))
190     return Ctx.CreateTemporarySymbol(Name);
191
192   return Ctx.CreateSymbol(Name);
193 }
194
195 /// ParsePrimaryExpr - Parse a primary expression and return it.
196 ///  primaryexpr ::= (parenexpr
197 ///  primaryexpr ::= symbol
198 ///  primaryexpr ::= number
199 ///  primaryexpr ::= ~,+,- primaryexpr
200 bool AsmParser::ParsePrimaryExpr(const MCExpr *&Res) {
201   switch (Lexer.getKind()) {
202   default:
203     return TokError("unknown token in expression");
204   case AsmToken::Exclaim:
205     Lexer.Lex(); // Eat the operator.
206     if (ParsePrimaryExpr(Res))
207       return true;
208     Res = MCUnaryExpr::CreateLNot(Res, Ctx);
209     return false;
210   case AsmToken::String:
211   case AsmToken::Identifier: {
212     // This is a label, this should be parsed as part of an expression, to
213     // handle things like LFOO+4.
214     MCSymbol *Sym = CreateSymbol(Lexer.getTok().getIdentifier());
215     
216     Res = MCSymbolRefExpr::Create(Sym, Ctx);
217     Lexer.Lex(); // Eat identifier.
218     return false;
219   }
220   case AsmToken::Integer:
221     Res = MCConstantExpr::Create(Lexer.getTok().getIntVal(), Ctx);
222     Lexer.Lex(); // Eat token.
223     return false;
224   case AsmToken::LParen:
225     Lexer.Lex(); // Eat the '('.
226     return ParseParenExpr(Res);
227   case AsmToken::Minus:
228     Lexer.Lex(); // Eat the operator.
229     if (ParsePrimaryExpr(Res))
230       return true;
231     Res = MCUnaryExpr::CreateMinus(Res, Ctx);
232     return false;
233   case AsmToken::Plus:
234     Lexer.Lex(); // Eat the operator.
235     if (ParsePrimaryExpr(Res))
236       return true;
237     Res = MCUnaryExpr::CreatePlus(Res, Ctx);
238     return false;
239   case AsmToken::Tilde:
240     Lexer.Lex(); // Eat the operator.
241     if (ParsePrimaryExpr(Res))
242       return true;
243     Res = MCUnaryExpr::CreateNot(Res, Ctx);
244     return false;
245   }
246 }
247
248 /// ParseExpression - Parse an expression and return it.
249 /// 
250 ///  expr ::= expr +,- expr          -> lowest.
251 ///  expr ::= expr |,^,&,! expr      -> middle.
252 ///  expr ::= expr *,/,%,<<,>> expr  -> highest.
253 ///  expr ::= primaryexpr
254 ///
255 bool AsmParser::ParseExpression(const MCExpr *&Res) {
256   Res = 0;
257   return ParsePrimaryExpr(Res) ||
258          ParseBinOpRHS(1, Res);
259 }
260
261 bool AsmParser::ParseAbsoluteExpression(int64_t &Res) {
262   const MCExpr *Expr;
263   
264   SMLoc StartLoc = Lexer.getLoc();
265   if (ParseExpression(Expr))
266     return true;
267
268   if (!Expr->EvaluateAsAbsolute(Ctx, Res))
269     return Error(StartLoc, "expected absolute expression");
270
271   return false;
272 }
273
274 bool AsmParser::ParseRelocatableExpression(MCValue &Res) {
275   const MCExpr *Expr;
276   
277   SMLoc StartLoc = Lexer.getLoc();
278   if (ParseExpression(Expr))
279     return true;
280
281   if (!Expr->EvaluateAsRelocatable(Ctx, Res))
282     return Error(StartLoc, "expected relocatable expression");
283
284   return false;
285 }
286
287 bool AsmParser::ParseParenRelocatableExpression(MCValue &Res) {
288   const MCExpr *Expr;
289   
290   SMLoc StartLoc = Lexer.getLoc();
291   if (ParseParenExpr(Expr))
292     return true;
293
294   if (!Expr->EvaluateAsRelocatable(Ctx, Res))
295     return Error(StartLoc, "expected relocatable expression");
296
297   return false;
298 }
299
300 static unsigned getBinOpPrecedence(AsmToken::TokenKind K, 
301                                    MCBinaryExpr::Opcode &Kind) {
302   switch (K) {
303   default: return 0;    // not a binop.
304
305     // Lowest Precedence: &&, ||
306   case AsmToken::AmpAmp:
307     Kind = MCBinaryExpr::LAnd;
308     return 1;
309   case AsmToken::PipePipe:
310     Kind = MCBinaryExpr::LOr;
311     return 1;
312
313     // Low Precedence: +, -, ==, !=, <>, <, <=, >, >=
314   case AsmToken::Plus:
315     Kind = MCBinaryExpr::Add;
316     return 2;
317   case AsmToken::Minus:
318     Kind = MCBinaryExpr::Sub;
319     return 2;
320   case AsmToken::EqualEqual:
321     Kind = MCBinaryExpr::EQ;
322     return 2;
323   case AsmToken::ExclaimEqual:
324   case AsmToken::LessGreater:
325     Kind = MCBinaryExpr::NE;
326     return 2;
327   case AsmToken::Less:
328     Kind = MCBinaryExpr::LT;
329     return 2;
330   case AsmToken::LessEqual:
331     Kind = MCBinaryExpr::LTE;
332     return 2;
333   case AsmToken::Greater:
334     Kind = MCBinaryExpr::GT;
335     return 2;
336   case AsmToken::GreaterEqual:
337     Kind = MCBinaryExpr::GTE;
338     return 2;
339
340     // Intermediate Precedence: |, &, ^
341     //
342     // FIXME: gas seems to support '!' as an infix operator?
343   case AsmToken::Pipe:
344     Kind = MCBinaryExpr::Or;
345     return 3;
346   case AsmToken::Caret:
347     Kind = MCBinaryExpr::Xor;
348     return 3;
349   case AsmToken::Amp:
350     Kind = MCBinaryExpr::And;
351     return 3;
352
353     // Highest Precedence: *, /, %, <<, >>
354   case AsmToken::Star:
355     Kind = MCBinaryExpr::Mul;
356     return 4;
357   case AsmToken::Slash:
358     Kind = MCBinaryExpr::Div;
359     return 4;
360   case AsmToken::Percent:
361     Kind = MCBinaryExpr::Mod;
362     return 4;
363   case AsmToken::LessLess:
364     Kind = MCBinaryExpr::Shl;
365     return 4;
366   case AsmToken::GreaterGreater:
367     Kind = MCBinaryExpr::Shr;
368     return 4;
369   }
370 }
371
372
373 /// ParseBinOpRHS - Parse all binary operators with precedence >= 'Precedence'.
374 /// Res contains the LHS of the expression on input.
375 bool AsmParser::ParseBinOpRHS(unsigned Precedence, const MCExpr *&Res) {
376   while (1) {
377     MCBinaryExpr::Opcode Kind = MCBinaryExpr::Add;
378     unsigned TokPrec = getBinOpPrecedence(Lexer.getKind(), Kind);
379     
380     // If the next token is lower precedence than we are allowed to eat, return
381     // successfully with what we ate already.
382     if (TokPrec < Precedence)
383       return false;
384     
385     Lexer.Lex();
386     
387     // Eat the next primary expression.
388     const MCExpr *RHS;
389     if (ParsePrimaryExpr(RHS)) return true;
390     
391     // If BinOp binds less tightly with RHS than the operator after RHS, let
392     // the pending operator take RHS as its LHS.
393     MCBinaryExpr::Opcode Dummy;
394     unsigned NextTokPrec = getBinOpPrecedence(Lexer.getKind(), Dummy);
395     if (TokPrec < NextTokPrec) {
396       if (ParseBinOpRHS(Precedence+1, RHS)) return true;
397     }
398
399     // Merge LHS and RHS according to operator.
400     Res = MCBinaryExpr::Create(Kind, Res, RHS, Ctx);
401   }
402 }
403
404   
405   
406   
407 /// ParseStatement:
408 ///   ::= EndOfStatement
409 ///   ::= Label* Directive ...Operands... EndOfStatement
410 ///   ::= Label* Identifier OperandList* EndOfStatement
411 bool AsmParser::ParseStatement() {
412   if (Lexer.is(AsmToken::EndOfStatement)) {
413     Lexer.Lex();
414     return false;
415   }
416
417   // Statements always start with an identifier.
418   AsmToken ID = Lexer.getTok();
419   SMLoc IDLoc = ID.getLoc();
420   StringRef IDVal;
421   if (ParseIdentifier(IDVal))
422     return TokError("unexpected token at start of statement");
423
424   // FIXME: Recurse on local labels?
425
426   // See what kind of statement we have.
427   switch (Lexer.getKind()) {
428   case AsmToken::Colon: {
429     // identifier ':'   -> Label.
430     Lexer.Lex();
431
432     // Diagnose attempt to use a variable as a label.
433     //
434     // FIXME: Diagnostics. Note the location of the definition as a label.
435     // FIXME: This doesn't diagnose assignment to a symbol which has been
436     // implicitly marked as external.
437     MCSymbol *Sym = CreateSymbol(IDVal);
438     if (!Sym->isUndefined())
439       return Error(IDLoc, "invalid symbol redefinition");
440     
441     // Emit the label.
442     Out.EmitLabel(Sym);
443    
444     return ParseStatement();
445   }
446
447   case AsmToken::Equal:
448     // identifier '=' ... -> assignment statement
449     Lexer.Lex();
450
451     return ParseAssignment(IDVal, false);
452
453   default: // Normal instruction or directive.
454     break;
455   }
456   
457   // Otherwise, we have a normal instruction or directive.  
458   if (IDVal[0] == '.') {
459     // FIXME: This should be driven based on a hash lookup and callback.
460     if (IDVal == ".section")
461       return ParseDirectiveDarwinSection();
462     if (IDVal == ".text")
463       // FIXME: This changes behavior based on the -static flag to the
464       // assembler.
465       return ParseDirectiveSectionSwitch("__TEXT", "__text",
466                                      MCSectionMachO::S_ATTR_PURE_INSTRUCTIONS);
467     if (IDVal == ".const")
468       return ParseDirectiveSectionSwitch("__TEXT", "__const");
469     if (IDVal == ".static_const")
470       return ParseDirectiveSectionSwitch("__TEXT", "__static_const");
471     if (IDVal == ".cstring")
472       return ParseDirectiveSectionSwitch("__TEXT","__cstring", 
473                                          MCSectionMachO::S_CSTRING_LITERALS);
474     if (IDVal == ".literal4")
475       return ParseDirectiveSectionSwitch("__TEXT", "__literal4",
476                                          MCSectionMachO::S_4BYTE_LITERALS,
477                                          4);
478     if (IDVal == ".literal8")
479       return ParseDirectiveSectionSwitch("__TEXT", "__literal8",
480                                          MCSectionMachO::S_8BYTE_LITERALS,
481                                          8);
482     if (IDVal == ".literal16")
483       return ParseDirectiveSectionSwitch("__TEXT","__literal16",
484                                          MCSectionMachO::S_16BYTE_LITERALS,
485                                          16);
486     if (IDVal == ".constructor")
487       return ParseDirectiveSectionSwitch("__TEXT","__constructor");
488     if (IDVal == ".destructor")
489       return ParseDirectiveSectionSwitch("__TEXT","__destructor");
490     if (IDVal == ".fvmlib_init0")
491       return ParseDirectiveSectionSwitch("__TEXT","__fvmlib_init0");
492     if (IDVal == ".fvmlib_init1")
493       return ParseDirectiveSectionSwitch("__TEXT","__fvmlib_init1");
494
495     // FIXME: The assembler manual claims that this has the self modify code
496     // flag, at least on x86-32, but that does not appear to be correct.
497     if (IDVal == ".symbol_stub")
498       return ParseDirectiveSectionSwitch("__TEXT","__symbol_stub",
499                                          MCSectionMachO::S_SYMBOL_STUBS |
500                                        MCSectionMachO::S_ATTR_PURE_INSTRUCTIONS,
501                                           // FIXME: Different on PPC and ARM.
502                                          0, 16);
503     // FIXME: PowerPC only?
504     if (IDVal == ".picsymbol_stub")
505       return ParseDirectiveSectionSwitch("__TEXT","__picsymbol_stub",
506                                          MCSectionMachO::S_SYMBOL_STUBS |
507                                        MCSectionMachO::S_ATTR_PURE_INSTRUCTIONS,
508                                          0, 26);
509     if (IDVal == ".data")
510       return ParseDirectiveSectionSwitch("__DATA", "__data");
511     if (IDVal == ".static_data")
512       return ParseDirectiveSectionSwitch("__DATA", "__static_data");
513
514     // FIXME: The section names of these two are misspelled in the assembler
515     // manual.
516     if (IDVal == ".non_lazy_symbol_pointer")
517       return ParseDirectiveSectionSwitch("__DATA", "__nl_symbol_ptr",
518                                      MCSectionMachO::S_NON_LAZY_SYMBOL_POINTERS,
519                                          4);
520     if (IDVal == ".lazy_symbol_pointer")
521       return ParseDirectiveSectionSwitch("__DATA", "__la_symbol_ptr",
522                                          MCSectionMachO::S_LAZY_SYMBOL_POINTERS,
523                                          4);
524
525     if (IDVal == ".dyld")
526       return ParseDirectiveSectionSwitch("__DATA", "__dyld");
527     if (IDVal == ".mod_init_func")
528       return ParseDirectiveSectionSwitch("__DATA", "__mod_init_func",
529                                        MCSectionMachO::S_MOD_INIT_FUNC_POINTERS,
530                                          4);
531     if (IDVal == ".mod_term_func")
532       return ParseDirectiveSectionSwitch("__DATA", "__mod_term_func",
533                                        MCSectionMachO::S_MOD_TERM_FUNC_POINTERS,
534                                          4);
535     if (IDVal == ".const_data")
536       return ParseDirectiveSectionSwitch("__DATA", "__const");
537     
538     
539     if (IDVal == ".objc_class")
540       return ParseDirectiveSectionSwitch("__OBJC", "__class", 
541                                          MCSectionMachO::S_ATTR_NO_DEAD_STRIP);
542     if (IDVal == ".objc_meta_class")
543       return ParseDirectiveSectionSwitch("__OBJC", "__meta_class",
544                                          MCSectionMachO::S_ATTR_NO_DEAD_STRIP);
545     if (IDVal == ".objc_cat_cls_meth")
546       return ParseDirectiveSectionSwitch("__OBJC", "__cat_cls_meth",
547                                          MCSectionMachO::S_ATTR_NO_DEAD_STRIP);
548     if (IDVal == ".objc_cat_inst_meth")
549       return ParseDirectiveSectionSwitch("__OBJC", "__cat_inst_meth",
550                                          MCSectionMachO::S_ATTR_NO_DEAD_STRIP);
551     if (IDVal == ".objc_protocol")
552       return ParseDirectiveSectionSwitch("__OBJC", "__protocol",
553                                          MCSectionMachO::S_ATTR_NO_DEAD_STRIP);
554     if (IDVal == ".objc_string_object")
555       return ParseDirectiveSectionSwitch("__OBJC", "__string_object",
556                                          MCSectionMachO::S_ATTR_NO_DEAD_STRIP);
557     if (IDVal == ".objc_cls_meth")
558       return ParseDirectiveSectionSwitch("__OBJC", "__cls_meth",
559                                          MCSectionMachO::S_ATTR_NO_DEAD_STRIP);
560     if (IDVal == ".objc_inst_meth")
561       return ParseDirectiveSectionSwitch("__OBJC", "__inst_meth",
562                                          MCSectionMachO::S_ATTR_NO_DEAD_STRIP);
563     if (IDVal == ".objc_cls_refs")
564       return ParseDirectiveSectionSwitch("__OBJC", "__cls_refs",
565                                          MCSectionMachO::S_ATTR_NO_DEAD_STRIP |
566                                          MCSectionMachO::S_LITERAL_POINTERS,
567                                          4);
568     if (IDVal == ".objc_message_refs")
569       return ParseDirectiveSectionSwitch("__OBJC", "__message_refs",
570                                          MCSectionMachO::S_ATTR_NO_DEAD_STRIP |
571                                          MCSectionMachO::S_LITERAL_POINTERS,
572                                          4);
573     if (IDVal == ".objc_symbols")
574       return ParseDirectiveSectionSwitch("__OBJC", "__symbols",
575                                          MCSectionMachO::S_ATTR_NO_DEAD_STRIP);
576     if (IDVal == ".objc_category")
577       return ParseDirectiveSectionSwitch("__OBJC", "__category",
578                                          MCSectionMachO::S_ATTR_NO_DEAD_STRIP);
579     if (IDVal == ".objc_class_vars")
580       return ParseDirectiveSectionSwitch("__OBJC", "__class_vars",
581                                          MCSectionMachO::S_ATTR_NO_DEAD_STRIP);
582     if (IDVal == ".objc_instance_vars")
583       return ParseDirectiveSectionSwitch("__OBJC", "__instance_vars",
584                                          MCSectionMachO::S_ATTR_NO_DEAD_STRIP);
585     if (IDVal == ".objc_module_info")
586       return ParseDirectiveSectionSwitch("__OBJC", "__module_info",
587                                          MCSectionMachO::S_ATTR_NO_DEAD_STRIP);
588     if (IDVal == ".objc_class_names")
589       return ParseDirectiveSectionSwitch("__TEXT", "__cstring",
590                                          MCSectionMachO::S_CSTRING_LITERALS);
591     if (IDVal == ".objc_meth_var_types")
592       return ParseDirectiveSectionSwitch("__TEXT", "__cstring",
593                                          MCSectionMachO::S_CSTRING_LITERALS);
594     if (IDVal == ".objc_meth_var_names")
595       return ParseDirectiveSectionSwitch("__TEXT", "__cstring",
596                                          MCSectionMachO::S_CSTRING_LITERALS);
597     if (IDVal == ".objc_selector_strs")
598       return ParseDirectiveSectionSwitch("__OBJC", "__selector_strs",
599                                          MCSectionMachO::S_CSTRING_LITERALS);
600     
601     // Assembler features
602     if (IDVal == ".set")
603       return ParseDirectiveSet();
604
605     // Data directives
606
607     if (IDVal == ".ascii")
608       return ParseDirectiveAscii(false);
609     if (IDVal == ".asciz")
610       return ParseDirectiveAscii(true);
611
612     // FIXME: Target hooks for size? Also for "word", "hword".
613     if (IDVal == ".byte")
614       return ParseDirectiveValue(1);
615     if (IDVal == ".short" || IDVal == ".word")
616       return ParseDirectiveValue(2);
617     if (IDVal == ".long")
618       return ParseDirectiveValue(4);
619     if (IDVal == ".quad")
620       return ParseDirectiveValue(8);
621
622     // FIXME: Target hooks for IsPow2.
623     if (IDVal == ".align")
624       return ParseDirectiveAlign(/*IsPow2=*/true, /*ExprSize=*/1);
625     if (IDVal == ".align32")
626       return ParseDirectiveAlign(/*IsPow2=*/true, /*ExprSize=*/4);
627     if (IDVal == ".balign")
628       return ParseDirectiveAlign(/*IsPow2=*/false, /*ExprSize=*/1);
629     if (IDVal == ".balignw")
630       return ParseDirectiveAlign(/*IsPow2=*/false, /*ExprSize=*/2);
631     if (IDVal == ".balignl")
632       return ParseDirectiveAlign(/*IsPow2=*/false, /*ExprSize=*/4);
633     if (IDVal == ".p2align")
634       return ParseDirectiveAlign(/*IsPow2=*/true, /*ExprSize=*/1);
635     if (IDVal == ".p2alignw")
636       return ParseDirectiveAlign(/*IsPow2=*/true, /*ExprSize=*/2);
637     if (IDVal == ".p2alignl")
638       return ParseDirectiveAlign(/*IsPow2=*/true, /*ExprSize=*/4);
639
640     if (IDVal == ".org")
641       return ParseDirectiveOrg();
642
643     if (IDVal == ".fill")
644       return ParseDirectiveFill();
645     if (IDVal == ".space")
646       return ParseDirectiveSpace();
647
648     // Symbol attribute directives
649
650     if (IDVal == ".globl" || IDVal == ".global")
651       return ParseDirectiveSymbolAttribute(MCStreamer::Global);
652     if (IDVal == ".hidden")
653       return ParseDirectiveSymbolAttribute(MCStreamer::Hidden);
654     if (IDVal == ".indirect_symbol")
655       return ParseDirectiveSymbolAttribute(MCStreamer::IndirectSymbol);
656     if (IDVal == ".internal")
657       return ParseDirectiveSymbolAttribute(MCStreamer::Internal);
658     if (IDVal == ".lazy_reference")
659       return ParseDirectiveSymbolAttribute(MCStreamer::LazyReference);
660     if (IDVal == ".no_dead_strip")
661       return ParseDirectiveSymbolAttribute(MCStreamer::NoDeadStrip);
662     if (IDVal == ".private_extern")
663       return ParseDirectiveSymbolAttribute(MCStreamer::PrivateExtern);
664     if (IDVal == ".protected")
665       return ParseDirectiveSymbolAttribute(MCStreamer::Protected);
666     if (IDVal == ".reference")
667       return ParseDirectiveSymbolAttribute(MCStreamer::Reference);
668     if (IDVal == ".weak")
669       return ParseDirectiveSymbolAttribute(MCStreamer::Weak);
670     if (IDVal == ".weak_definition")
671       return ParseDirectiveSymbolAttribute(MCStreamer::WeakDefinition);
672     if (IDVal == ".weak_reference")
673       return ParseDirectiveSymbolAttribute(MCStreamer::WeakReference);
674
675     if (IDVal == ".comm")
676       return ParseDirectiveComm(/*IsLocal=*/false);
677     if (IDVal == ".lcomm")
678       return ParseDirectiveComm(/*IsLocal=*/true);
679     if (IDVal == ".zerofill")
680       return ParseDirectiveDarwinZerofill();
681     if (IDVal == ".desc")
682       return ParseDirectiveDarwinSymbolDesc();
683     if (IDVal == ".lsym")
684       return ParseDirectiveDarwinLsym();
685
686     if (IDVal == ".subsections_via_symbols")
687       return ParseDirectiveDarwinSubsectionsViaSymbols();
688     if (IDVal == ".abort")
689       return ParseDirectiveAbort();
690     if (IDVal == ".include")
691       return ParseDirectiveInclude();
692     if (IDVal == ".dump")
693       return ParseDirectiveDarwinDumpOrLoad(IDLoc, /*IsDump=*/true);
694     if (IDVal == ".load")
695       return ParseDirectiveDarwinDumpOrLoad(IDLoc, /*IsLoad=*/false);
696
697     // Debugging directives
698
699     if (IDVal == ".file")
700       return ParseDirectiveFile(IDLoc);
701     if (IDVal == ".line")
702       return ParseDirectiveLine(IDLoc);
703     if (IDVal == ".loc")
704       return ParseDirectiveLoc(IDLoc);
705
706     Warning(IDLoc, "ignoring directive for now");
707     EatToEndOfStatement();
708     return false;
709   }
710
711   MCInst Inst;
712   if (getTargetParser().ParseInstruction(IDVal, Inst))
713     return true;
714   
715   if (Lexer.isNot(AsmToken::EndOfStatement))
716     return TokError("unexpected token in argument list");
717
718   // Eat the end of statement marker.
719   Lexer.Lex();
720   
721   // Instruction is good, process it.
722   Out.EmitInstruction(Inst);
723   
724   // Skip to end of line for now.
725   return false;
726 }
727
728 bool AsmParser::ParseAssignment(const StringRef &Name, bool IsDotSet) {
729   // FIXME: Use better location, we should use proper tokens.
730   SMLoc EqualLoc = Lexer.getLoc();
731
732   MCValue Value;
733   if (ParseRelocatableExpression(Value))
734     return true;
735   
736   if (Lexer.isNot(AsmToken::EndOfStatement))
737     return TokError("unexpected token in assignment");
738
739   // Eat the end of statement marker.
740   Lexer.Lex();
741
742   // Diagnose assignment to a label.
743   //
744   // FIXME: Diagnostics. Note the location of the definition as a label.
745   // FIXME: Handle '.'.
746   // FIXME: Diagnose assignment to protected identifier (e.g., register name).
747   MCSymbol *Sym = CreateSymbol(Name);
748   if (!Sym->isUndefined() && !Sym->isAbsolute())
749     return Error(EqualLoc, "symbol has already been defined");
750
751   // Do the assignment.
752   Out.EmitAssignment(Sym, Value, IsDotSet);
753
754   return false;
755 }
756
757 /// ParseIdentifier:
758 ///   ::= identifier
759 ///   ::= string
760 bool AsmParser::ParseIdentifier(StringRef &Res) {
761   if (Lexer.isNot(AsmToken::Identifier) &&
762       Lexer.isNot(AsmToken::String))
763     return true;
764
765   Res = Lexer.getTok().getIdentifier();
766
767   Lexer.Lex(); // Consume the identifier token.
768
769   return false;
770 }
771
772 /// ParseDirectiveSet:
773 ///   ::= .set identifier ',' expression
774 bool AsmParser::ParseDirectiveSet() {
775   StringRef Name;
776
777   if (ParseIdentifier(Name))
778     return TokError("expected identifier after '.set' directive");
779   
780   if (Lexer.isNot(AsmToken::Comma))
781     return TokError("unexpected token in '.set'");
782   Lexer.Lex();
783
784   return ParseAssignment(Name, true);
785 }
786
787 /// ParseDirectiveSection:
788 ///   ::= .section identifier (',' identifier)*
789 /// FIXME: This should actually parse out the segment, section, attributes and
790 /// sizeof_stub fields.
791 bool AsmParser::ParseDirectiveDarwinSection() {
792   SMLoc Loc = Lexer.getLoc();
793
794   StringRef SectionName;
795   if (ParseIdentifier(SectionName))
796     return Error(Loc, "expected identifier after '.section' directive");
797
798   // Verify there is a following comma.
799   if (!Lexer.is(AsmToken::Comma))
800     return TokError("unexpected token in '.section' directive");
801
802   std::string SectionSpec = SectionName;
803   SectionSpec += ",";
804
805   // Add all the tokens until the end of the line, ParseSectionSpecifier will
806   // handle this.
807   StringRef EOL = Lexer.LexUntilEndOfStatement();
808   SectionSpec.append(EOL.begin(), EOL.end());
809
810   Lexer.Lex();
811   if (Lexer.isNot(AsmToken::EndOfStatement))
812     return TokError("unexpected token in '.section' directive");
813   Lexer.Lex();
814
815
816   StringRef Segment, Section;
817   unsigned TAA, StubSize;
818   std::string ErrorStr = 
819     MCSectionMachO::ParseSectionSpecifier(SectionSpec, Segment, Section,
820                                           TAA, StubSize);
821   
822   if (!ErrorStr.empty())
823     return Error(Loc, ErrorStr.c_str());
824   
825   // FIXME: Arch specific.
826   Out.SwitchSection(getMachOSection(Segment, Section, TAA, StubSize,
827                                     SectionKind()));
828   return false;
829 }
830
831 /// ParseDirectiveSectionSwitch - 
832 bool AsmParser::ParseDirectiveSectionSwitch(const char *Segment,
833                                             const char *Section,
834                                             unsigned TAA, unsigned Align,
835                                             unsigned StubSize) {
836   if (Lexer.isNot(AsmToken::EndOfStatement))
837     return TokError("unexpected token in section switching directive");
838   Lexer.Lex();
839   
840   // FIXME: Arch specific.
841   Out.SwitchSection(getMachOSection(Segment, Section, TAA, StubSize,
842                                     SectionKind()));
843
844   // Set the implicit alignment, if any.
845   //
846   // FIXME: This isn't really what 'as' does; I think it just uses the implicit
847   // alignment on the section (e.g., if one manually inserts bytes into the
848   // section, then just issueing the section switch directive will not realign
849   // the section. However, this is arguably more reasonable behavior, and there
850   // is no good reason for someone to intentionally emit incorrectly sized
851   // values into the implicitly aligned sections.
852   if (Align)
853     Out.EmitValueToAlignment(Align, 0, 1, 0);
854
855   return false;
856 }
857
858 bool AsmParser::ParseEscapedString(std::string &Data) {
859   assert(Lexer.is(AsmToken::String) && "Unexpected current token!");
860
861   Data = "";
862   StringRef Str = Lexer.getTok().getStringContents();
863   for (unsigned i = 0, e = Str.size(); i != e; ++i) {
864     if (Str[i] != '\\') {
865       Data += Str[i];
866       continue;
867     }
868
869     // Recognize escaped characters. Note that this escape semantics currently
870     // loosely follows Darwin 'as'. Notably, it doesn't support hex escapes.
871     ++i;
872     if (i == e)
873       return TokError("unexpected backslash at end of string");
874
875     // Recognize octal sequences.
876     if ((unsigned) (Str[i] - '0') <= 7) {
877       // Consume up to three octal characters.
878       unsigned Value = Str[i] - '0';
879
880       if (i + 1 != e && ((unsigned) (Str[i + 1] - '0')) <= 7) {
881         ++i;
882         Value = Value * 8 + (Str[i] - '0');
883
884         if (i + 1 != e && ((unsigned) (Str[i + 1] - '0')) <= 7) {
885           ++i;
886           Value = Value * 8 + (Str[i] - '0');
887         }
888       }
889
890       if (Value > 255)
891         return TokError("invalid octal escape sequence (out of range)");
892
893       Data += (unsigned char) Value;
894       continue;
895     }
896
897     // Otherwise recognize individual escapes.
898     switch (Str[i]) {
899     default:
900       // Just reject invalid escape sequences for now.
901       return TokError("invalid escape sequence (unrecognized character)");
902
903     case 'b': Data += '\b'; break;
904     case 'f': Data += '\f'; break;
905     case 'n': Data += '\n'; break;
906     case 'r': Data += '\r'; break;
907     case 't': Data += '\t'; break;
908     case '"': Data += '"'; break;
909     case '\\': Data += '\\'; break;
910     }
911   }
912
913   return false;
914 }
915
916 /// ParseDirectiveAscii:
917 ///   ::= ( .ascii | .asciz ) [ "string" ( , "string" )* ]
918 bool AsmParser::ParseDirectiveAscii(bool ZeroTerminated) {
919   if (Lexer.isNot(AsmToken::EndOfStatement)) {
920     for (;;) {
921       if (Lexer.isNot(AsmToken::String))
922         return TokError("expected string in '.ascii' or '.asciz' directive");
923       
924       std::string Data;
925       if (ParseEscapedString(Data))
926         return true;
927       
928       Out.EmitBytes(Data);
929       if (ZeroTerminated)
930         Out.EmitBytes(StringRef("\0", 1));
931       
932       Lexer.Lex();
933       
934       if (Lexer.is(AsmToken::EndOfStatement))
935         break;
936
937       if (Lexer.isNot(AsmToken::Comma))
938         return TokError("unexpected token in '.ascii' or '.asciz' directive");
939       Lexer.Lex();
940     }
941   }
942
943   Lexer.Lex();
944   return false;
945 }
946
947 /// ParseDirectiveValue
948 ///  ::= (.byte | .short | ... ) [ expression (, expression)* ]
949 bool AsmParser::ParseDirectiveValue(unsigned Size) {
950   if (Lexer.isNot(AsmToken::EndOfStatement)) {
951     for (;;) {
952       MCValue Expr;
953       if (ParseRelocatableExpression(Expr))
954         return true;
955
956       Out.EmitValue(Expr, Size);
957
958       if (Lexer.is(AsmToken::EndOfStatement))
959         break;
960       
961       // FIXME: Improve diagnostic.
962       if (Lexer.isNot(AsmToken::Comma))
963         return TokError("unexpected token in directive");
964       Lexer.Lex();
965     }
966   }
967
968   Lexer.Lex();
969   return false;
970 }
971
972 /// ParseDirectiveSpace
973 ///  ::= .space expression [ , expression ]
974 bool AsmParser::ParseDirectiveSpace() {
975   int64_t NumBytes;
976   if (ParseAbsoluteExpression(NumBytes))
977     return true;
978
979   int64_t FillExpr = 0;
980   bool HasFillExpr = false;
981   if (Lexer.isNot(AsmToken::EndOfStatement)) {
982     if (Lexer.isNot(AsmToken::Comma))
983       return TokError("unexpected token in '.space' directive");
984     Lexer.Lex();
985     
986     if (ParseAbsoluteExpression(FillExpr))
987       return true;
988
989     HasFillExpr = true;
990
991     if (Lexer.isNot(AsmToken::EndOfStatement))
992       return TokError("unexpected token in '.space' directive");
993   }
994
995   Lexer.Lex();
996
997   if (NumBytes <= 0)
998     return TokError("invalid number of bytes in '.space' directive");
999
1000   // FIXME: Sometimes the fill expr is 'nop' if it isn't supplied, instead of 0.
1001   for (uint64_t i = 0, e = NumBytes; i != e; ++i)
1002     Out.EmitValue(MCValue::get(FillExpr), 1);
1003
1004   return false;
1005 }
1006
1007 /// ParseDirectiveFill
1008 ///  ::= .fill expression , expression , expression
1009 bool AsmParser::ParseDirectiveFill() {
1010   int64_t NumValues;
1011   if (ParseAbsoluteExpression(NumValues))
1012     return true;
1013
1014   if (Lexer.isNot(AsmToken::Comma))
1015     return TokError("unexpected token in '.fill' directive");
1016   Lexer.Lex();
1017   
1018   int64_t FillSize;
1019   if (ParseAbsoluteExpression(FillSize))
1020     return true;
1021
1022   if (Lexer.isNot(AsmToken::Comma))
1023     return TokError("unexpected token in '.fill' directive");
1024   Lexer.Lex();
1025   
1026   int64_t FillExpr;
1027   if (ParseAbsoluteExpression(FillExpr))
1028     return true;
1029
1030   if (Lexer.isNot(AsmToken::EndOfStatement))
1031     return TokError("unexpected token in '.fill' directive");
1032   
1033   Lexer.Lex();
1034
1035   if (FillSize != 1 && FillSize != 2 && FillSize != 4 && FillSize != 8)
1036     return TokError("invalid '.fill' size, expected 1, 2, 4, or 8");
1037
1038   for (uint64_t i = 0, e = NumValues; i != e; ++i)
1039     Out.EmitValue(MCValue::get(FillExpr), FillSize);
1040
1041   return false;
1042 }
1043
1044 /// ParseDirectiveOrg
1045 ///  ::= .org expression [ , expression ]
1046 bool AsmParser::ParseDirectiveOrg() {
1047   MCValue Offset;
1048   if (ParseRelocatableExpression(Offset))
1049     return true;
1050
1051   // Parse optional fill expression.
1052   int64_t FillExpr = 0;
1053   if (Lexer.isNot(AsmToken::EndOfStatement)) {
1054     if (Lexer.isNot(AsmToken::Comma))
1055       return TokError("unexpected token in '.org' directive");
1056     Lexer.Lex();
1057     
1058     if (ParseAbsoluteExpression(FillExpr))
1059       return true;
1060
1061     if (Lexer.isNot(AsmToken::EndOfStatement))
1062       return TokError("unexpected token in '.org' directive");
1063   }
1064
1065   Lexer.Lex();
1066
1067   // FIXME: Only limited forms of relocatable expressions are accepted here, it
1068   // has to be relative to the current section.
1069   Out.EmitValueToOffset(Offset, FillExpr);
1070
1071   return false;
1072 }
1073
1074 /// ParseDirectiveAlign
1075 ///  ::= {.align, ...} expression [ , expression [ , expression ]]
1076 bool AsmParser::ParseDirectiveAlign(bool IsPow2, unsigned ValueSize) {
1077   SMLoc AlignmentLoc = Lexer.getLoc();
1078   int64_t Alignment;
1079   if (ParseAbsoluteExpression(Alignment))
1080     return true;
1081
1082   SMLoc MaxBytesLoc;
1083   bool HasFillExpr = false;
1084   int64_t FillExpr = 0;
1085   int64_t MaxBytesToFill = 0;
1086   if (Lexer.isNot(AsmToken::EndOfStatement)) {
1087     if (Lexer.isNot(AsmToken::Comma))
1088       return TokError("unexpected token in directive");
1089     Lexer.Lex();
1090
1091     // The fill expression can be omitted while specifying a maximum number of
1092     // alignment bytes, e.g:
1093     //  .align 3,,4
1094     if (Lexer.isNot(AsmToken::Comma)) {
1095       HasFillExpr = true;
1096       if (ParseAbsoluteExpression(FillExpr))
1097         return true;
1098     }
1099
1100     if (Lexer.isNot(AsmToken::EndOfStatement)) {
1101       if (Lexer.isNot(AsmToken::Comma))
1102         return TokError("unexpected token in directive");
1103       Lexer.Lex();
1104
1105       MaxBytesLoc = Lexer.getLoc();
1106       if (ParseAbsoluteExpression(MaxBytesToFill))
1107         return true;
1108       
1109       if (Lexer.isNot(AsmToken::EndOfStatement))
1110         return TokError("unexpected token in directive");
1111     }
1112   }
1113
1114   Lexer.Lex();
1115
1116   if (!HasFillExpr) {
1117     // FIXME: Sometimes fill with nop.
1118     FillExpr = 0;
1119   }
1120
1121   // Compute alignment in bytes.
1122   if (IsPow2) {
1123     // FIXME: Diagnose overflow.
1124     if (Alignment >= 32) {
1125       Error(AlignmentLoc, "invalid alignment value");
1126       Alignment = 31;
1127     }
1128
1129     Alignment = 1 << Alignment;
1130   }
1131
1132   // Diagnose non-sensical max bytes to align.
1133   if (MaxBytesLoc.isValid()) {
1134     if (MaxBytesToFill < 1) {
1135       Error(MaxBytesLoc, "alignment directive can never be satisfied in this "
1136             "many bytes, ignoring maximum bytes expression");
1137       MaxBytesToFill = 0;
1138     }
1139
1140     if (MaxBytesToFill >= Alignment) {
1141       Warning(MaxBytesLoc, "maximum bytes expression exceeds alignment and "
1142               "has no effect");
1143       MaxBytesToFill = 0;
1144     }
1145   }
1146
1147   // FIXME: Target specific behavior about how the "extra" bytes are filled.
1148   Out.EmitValueToAlignment(Alignment, FillExpr, ValueSize, MaxBytesToFill);
1149
1150   return false;
1151 }
1152
1153 /// ParseDirectiveSymbolAttribute
1154 ///  ::= { ".globl", ".weak", ... } [ identifier ( , identifier )* ]
1155 bool AsmParser::ParseDirectiveSymbolAttribute(MCStreamer::SymbolAttr Attr) {
1156   if (Lexer.isNot(AsmToken::EndOfStatement)) {
1157     for (;;) {
1158       StringRef Name;
1159
1160       if (ParseIdentifier(Name))
1161         return TokError("expected identifier in directive");
1162       
1163       MCSymbol *Sym = CreateSymbol(Name);
1164
1165       Out.EmitSymbolAttribute(Sym, Attr);
1166
1167       if (Lexer.is(AsmToken::EndOfStatement))
1168         break;
1169
1170       if (Lexer.isNot(AsmToken::Comma))
1171         return TokError("unexpected token in directive");
1172       Lexer.Lex();
1173     }
1174   }
1175
1176   Lexer.Lex();
1177   return false;  
1178 }
1179
1180 /// ParseDirectiveDarwinSymbolDesc
1181 ///  ::= .desc identifier , expression
1182 bool AsmParser::ParseDirectiveDarwinSymbolDesc() {
1183   StringRef Name;
1184   if (ParseIdentifier(Name))
1185     return TokError("expected identifier in directive");
1186   
1187   // Handle the identifier as the key symbol.
1188   MCSymbol *Sym = CreateSymbol(Name);
1189
1190   if (Lexer.isNot(AsmToken::Comma))
1191     return TokError("unexpected token in '.desc' directive");
1192   Lexer.Lex();
1193
1194   SMLoc DescLoc = Lexer.getLoc();
1195   int64_t DescValue;
1196   if (ParseAbsoluteExpression(DescValue))
1197     return true;
1198
1199   if (Lexer.isNot(AsmToken::EndOfStatement))
1200     return TokError("unexpected token in '.desc' directive");
1201   
1202   Lexer.Lex();
1203
1204   // Set the n_desc field of this Symbol to this DescValue
1205   Out.EmitSymbolDesc(Sym, DescValue);
1206
1207   return false;
1208 }
1209
1210 /// ParseDirectiveComm
1211 ///  ::= ( .comm | .lcomm ) identifier , size_expression [ , align_expression ]
1212 bool AsmParser::ParseDirectiveComm(bool IsLocal) {
1213   SMLoc IDLoc = Lexer.getLoc();
1214   StringRef Name;
1215   if (ParseIdentifier(Name))
1216     return TokError("expected identifier in directive");
1217   
1218   // Handle the identifier as the key symbol.
1219   MCSymbol *Sym = CreateSymbol(Name);
1220
1221   if (Lexer.isNot(AsmToken::Comma))
1222     return TokError("unexpected token in directive");
1223   Lexer.Lex();
1224
1225   int64_t Size;
1226   SMLoc SizeLoc = Lexer.getLoc();
1227   if (ParseAbsoluteExpression(Size))
1228     return true;
1229
1230   int64_t Pow2Alignment = 0;
1231   SMLoc Pow2AlignmentLoc;
1232   if (Lexer.is(AsmToken::Comma)) {
1233     Lexer.Lex();
1234     Pow2AlignmentLoc = Lexer.getLoc();
1235     if (ParseAbsoluteExpression(Pow2Alignment))
1236       return true;
1237   }
1238   
1239   if (Lexer.isNot(AsmToken::EndOfStatement))
1240     return TokError("unexpected token in '.comm' or '.lcomm' directive");
1241   
1242   Lexer.Lex();
1243
1244   // NOTE: a size of zero for a .comm should create a undefined symbol
1245   // but a size of .lcomm creates a bss symbol of size zero.
1246   if (Size < 0)
1247     return Error(SizeLoc, "invalid '.comm' or '.lcomm' directive size, can't "
1248                  "be less than zero");
1249
1250   // NOTE: The alignment in the directive is a power of 2 value, the assember
1251   // may internally end up wanting an alignment in bytes.
1252   // FIXME: Diagnose overflow.
1253   if (Pow2Alignment < 0)
1254     return Error(Pow2AlignmentLoc, "invalid '.comm' or '.lcomm' directive "
1255                  "alignment, can't be less than zero");
1256
1257   if (!Sym->isUndefined())
1258     return Error(IDLoc, "invalid symbol redefinition");
1259
1260   // '.lcomm' is equivalent to '.zerofill'.
1261   // Create the Symbol as a common or local common with Size and Pow2Alignment
1262   if (IsLocal) {
1263     Out.EmitZerofill(getMachOSection("__DATA", "__bss",
1264                                      MCSectionMachO::S_ZEROFILL, 0,
1265                                      SectionKind()),
1266                      Sym, Size, 1 << Pow2Alignment);
1267     return false;
1268   }
1269
1270   Out.EmitCommonSymbol(Sym, Size, 1 << Pow2Alignment);
1271   return false;
1272 }
1273
1274 /// ParseDirectiveDarwinZerofill
1275 ///  ::= .zerofill segname , sectname [, identifier , size_expression [
1276 ///      , align_expression ]]
1277 bool AsmParser::ParseDirectiveDarwinZerofill() {
1278   // FIXME: Handle quoted names here.
1279
1280   if (Lexer.isNot(AsmToken::Identifier))
1281     return TokError("expected segment name after '.zerofill' directive");
1282   StringRef Segment = Lexer.getTok().getString();
1283   Lexer.Lex();
1284
1285   if (Lexer.isNot(AsmToken::Comma))
1286     return TokError("unexpected token in directive");
1287   Lexer.Lex();
1288  
1289   if (Lexer.isNot(AsmToken::Identifier))
1290     return TokError("expected section name after comma in '.zerofill' "
1291                     "directive");
1292   StringRef Section = Lexer.getTok().getString();
1293   Lexer.Lex();
1294
1295   // If this is the end of the line all that was wanted was to create the
1296   // the section but with no symbol.
1297   if (Lexer.is(AsmToken::EndOfStatement)) {
1298     // Create the zerofill section but no symbol
1299     Out.EmitZerofill(getMachOSection(Segment, Section,
1300                                      MCSectionMachO::S_ZEROFILL, 0,
1301                                      SectionKind()));
1302     return false;
1303   }
1304
1305   if (Lexer.isNot(AsmToken::Comma))
1306     return TokError("unexpected token in directive");
1307   Lexer.Lex();
1308
1309   if (Lexer.isNot(AsmToken::Identifier))
1310     return TokError("expected identifier in directive");
1311   
1312   // handle the identifier as the key symbol.
1313   SMLoc IDLoc = Lexer.getLoc();
1314   MCSymbol *Sym = CreateSymbol(Lexer.getTok().getString());
1315   Lexer.Lex();
1316
1317   if (Lexer.isNot(AsmToken::Comma))
1318     return TokError("unexpected token in directive");
1319   Lexer.Lex();
1320
1321   int64_t Size;
1322   SMLoc SizeLoc = Lexer.getLoc();
1323   if (ParseAbsoluteExpression(Size))
1324     return true;
1325
1326   int64_t Pow2Alignment = 0;
1327   SMLoc Pow2AlignmentLoc;
1328   if (Lexer.is(AsmToken::Comma)) {
1329     Lexer.Lex();
1330     Pow2AlignmentLoc = Lexer.getLoc();
1331     if (ParseAbsoluteExpression(Pow2Alignment))
1332       return true;
1333   }
1334   
1335   if (Lexer.isNot(AsmToken::EndOfStatement))
1336     return TokError("unexpected token in '.zerofill' directive");
1337   
1338   Lexer.Lex();
1339
1340   if (Size < 0)
1341     return Error(SizeLoc, "invalid '.zerofill' directive size, can't be less "
1342                  "than zero");
1343
1344   // NOTE: The alignment in the directive is a power of 2 value, the assember
1345   // may internally end up wanting an alignment in bytes.
1346   // FIXME: Diagnose overflow.
1347   if (Pow2Alignment < 0)
1348     return Error(Pow2AlignmentLoc, "invalid '.zerofill' directive alignment, "
1349                  "can't be less than zero");
1350
1351   if (!Sym->isUndefined())
1352     return Error(IDLoc, "invalid symbol redefinition");
1353
1354   // Create the zerofill Symbol with Size and Pow2Alignment
1355   //
1356   // FIXME: Arch specific.
1357   Out.EmitZerofill(getMachOSection(Segment, Section,
1358                                  MCSectionMachO::S_ZEROFILL, 0,
1359                                  SectionKind()),
1360                    Sym, Size, 1 << Pow2Alignment);
1361
1362   return false;
1363 }
1364
1365 /// ParseDirectiveDarwinSubsectionsViaSymbols
1366 ///  ::= .subsections_via_symbols
1367 bool AsmParser::ParseDirectiveDarwinSubsectionsViaSymbols() {
1368   if (Lexer.isNot(AsmToken::EndOfStatement))
1369     return TokError("unexpected token in '.subsections_via_symbols' directive");
1370   
1371   Lexer.Lex();
1372
1373   Out.EmitAssemblerFlag(MCStreamer::SubsectionsViaSymbols);
1374
1375   return false;
1376 }
1377
1378 /// ParseDirectiveAbort
1379 ///  ::= .abort [ "abort_string" ]
1380 bool AsmParser::ParseDirectiveAbort() {
1381   // FIXME: Use loc from directive.
1382   SMLoc Loc = Lexer.getLoc();
1383
1384   StringRef Str = "";
1385   if (Lexer.isNot(AsmToken::EndOfStatement)) {
1386     if (Lexer.isNot(AsmToken::String))
1387       return TokError("expected string in '.abort' directive");
1388     
1389     Str = Lexer.getTok().getString();
1390
1391     Lexer.Lex();
1392   }
1393
1394   if (Lexer.isNot(AsmToken::EndOfStatement))
1395     return TokError("unexpected token in '.abort' directive");
1396   
1397   Lexer.Lex();
1398
1399   // FIXME: Handle here.
1400   if (Str.empty())
1401     Error(Loc, ".abort detected. Assembly stopping.");
1402   else
1403     Error(Loc, ".abort '" + Str + "' detected. Assembly stopping.");
1404
1405   return false;
1406 }
1407
1408 /// ParseDirectiveLsym
1409 ///  ::= .lsym identifier , expression
1410 bool AsmParser::ParseDirectiveDarwinLsym() {
1411   StringRef Name;
1412   if (ParseIdentifier(Name))
1413     return TokError("expected identifier in directive");
1414   
1415   // Handle the identifier as the key symbol.
1416   MCSymbol *Sym = CreateSymbol(Name);
1417
1418   if (Lexer.isNot(AsmToken::Comma))
1419     return TokError("unexpected token in '.lsym' directive");
1420   Lexer.Lex();
1421
1422   MCValue Expr;
1423   if (ParseRelocatableExpression(Expr))
1424     return true;
1425
1426   if (Lexer.isNot(AsmToken::EndOfStatement))
1427     return TokError("unexpected token in '.lsym' directive");
1428   
1429   Lexer.Lex();
1430
1431   // We don't currently support this directive.
1432   //
1433   // FIXME: Diagnostic location!
1434   (void) Sym;
1435   return TokError("directive '.lsym' is unsupported");
1436 }
1437
1438 /// ParseDirectiveInclude
1439 ///  ::= .include "filename"
1440 bool AsmParser::ParseDirectiveInclude() {
1441   if (Lexer.isNot(AsmToken::String))
1442     return TokError("expected string in '.include' directive");
1443   
1444   std::string Filename = Lexer.getTok().getString();
1445   SMLoc IncludeLoc = Lexer.getLoc();
1446   Lexer.Lex();
1447
1448   if (Lexer.isNot(AsmToken::EndOfStatement))
1449     return TokError("unexpected token in '.include' directive");
1450   
1451   // Strip the quotes.
1452   Filename = Filename.substr(1, Filename.size()-2);
1453   
1454   // Attempt to switch the lexer to the included file before consuming the end
1455   // of statement to avoid losing it when we switch.
1456   if (Lexer.EnterIncludeFile(Filename)) {
1457     Lexer.PrintMessage(IncludeLoc,
1458                        "Could not find include file '" + Filename + "'",
1459                        "error");
1460     return true;
1461   }
1462
1463   return false;
1464 }
1465
1466 /// ParseDirectiveDarwinDumpOrLoad
1467 ///  ::= ( .dump | .load ) "filename"
1468 bool AsmParser::ParseDirectiveDarwinDumpOrLoad(SMLoc IDLoc, bool IsDump) {
1469   if (Lexer.isNot(AsmToken::String))
1470     return TokError("expected string in '.dump' or '.load' directive");
1471   
1472   Lexer.Lex();
1473
1474   if (Lexer.isNot(AsmToken::EndOfStatement))
1475     return TokError("unexpected token in '.dump' or '.load' directive");
1476   
1477   Lexer.Lex();
1478
1479   // FIXME: If/when .dump and .load are implemented they will be done in the
1480   // the assembly parser and not have any need for an MCStreamer API.
1481   if (IsDump)
1482     Warning(IDLoc, "ignoring directive .dump for now");
1483   else
1484     Warning(IDLoc, "ignoring directive .load for now");
1485
1486   return false;
1487 }
1488
1489 /// ParseDirectiveIf
1490 /// ::= .if expression
1491 bool AsmParser::ParseDirectiveIf(SMLoc DirectiveLoc) {
1492   // Consume the identifier that was the .if directive
1493   Lexer.Lex();
1494
1495   TheCondStack.push_back(TheCondState);
1496   TheCondState.TheCond = AsmCond::IfCond;
1497   if(TheCondState.Ignore) {
1498     EatToEndOfStatement();
1499   }
1500   else {
1501     int64_t ExprValue;
1502     if (ParseAbsoluteExpression(ExprValue))
1503       return true;
1504
1505     if (Lexer.isNot(AsmToken::EndOfStatement))
1506       return TokError("unexpected token in '.if' directive");
1507     
1508     Lexer.Lex();
1509
1510     TheCondState.CondMet = ExprValue;
1511     TheCondState.Ignore = !TheCondState.CondMet;
1512   }
1513
1514   return false;
1515 }
1516
1517 /// ParseDirectiveElseIf
1518 /// ::= .elseif expression
1519 bool AsmParser::ParseDirectiveElseIf(SMLoc DirectiveLoc) {
1520   if (TheCondState.TheCond != AsmCond::IfCond &&
1521       TheCondState.TheCond != AsmCond::ElseIfCond)
1522       Error(DirectiveLoc, "Encountered a .elseif that doesn't follow a .if or "
1523                           " an .elseif");
1524   TheCondState.TheCond = AsmCond::ElseIfCond;
1525
1526   // Consume the identifier that was the .elseif directive
1527   Lexer.Lex();
1528
1529   bool LastIgnoreState = false;
1530   if (!TheCondStack.empty())
1531       LastIgnoreState = TheCondStack.back().Ignore;
1532   if (LastIgnoreState || TheCondState.CondMet) {
1533     TheCondState.Ignore = true;
1534     EatToEndOfStatement();
1535   }
1536   else {
1537     int64_t ExprValue;
1538     if (ParseAbsoluteExpression(ExprValue))
1539       return true;
1540
1541     if (Lexer.isNot(AsmToken::EndOfStatement))
1542       return TokError("unexpected token in '.elseif' directive");
1543     
1544     Lexer.Lex();
1545     TheCondState.CondMet = ExprValue;
1546     TheCondState.Ignore = !TheCondState.CondMet;
1547   }
1548
1549   return false;
1550 }
1551
1552 /// ParseDirectiveElse
1553 /// ::= .else
1554 bool AsmParser::ParseDirectiveElse(SMLoc DirectiveLoc) {
1555   // Consume the identifier that was the .else directive
1556   Lexer.Lex();
1557
1558   if (Lexer.isNot(AsmToken::EndOfStatement))
1559     return TokError("unexpected token in '.else' directive");
1560   
1561   Lexer.Lex();
1562
1563   if (TheCondState.TheCond != AsmCond::IfCond &&
1564       TheCondState.TheCond != AsmCond::ElseIfCond)
1565       Error(DirectiveLoc, "Encountered a .else that doesn't follow a .if or an "
1566                           ".elseif");
1567   TheCondState.TheCond = AsmCond::ElseCond;
1568   bool LastIgnoreState = false;
1569   if (!TheCondStack.empty())
1570     LastIgnoreState = TheCondStack.back().Ignore;
1571   if (LastIgnoreState || TheCondState.CondMet)
1572     TheCondState.Ignore = true;
1573   else
1574     TheCondState.Ignore = false;
1575
1576   return false;
1577 }
1578
1579 /// ParseDirectiveEndIf
1580 /// ::= .endif
1581 bool AsmParser::ParseDirectiveEndIf(SMLoc DirectiveLoc) {
1582   // Consume the identifier that was the .endif directive
1583   Lexer.Lex();
1584
1585   if (Lexer.isNot(AsmToken::EndOfStatement))
1586     return TokError("unexpected token in '.endif' directive");
1587   
1588   Lexer.Lex();
1589
1590   if ((TheCondState.TheCond == AsmCond::NoCond) ||
1591       TheCondStack.empty())
1592     Error(DirectiveLoc, "Encountered a .endif that doesn't follow a .if or "
1593                         ".else");
1594   if (!TheCondStack.empty()) {
1595     TheCondState = TheCondStack.back();
1596     TheCondStack.pop_back();
1597   }
1598
1599   return false;
1600 }
1601
1602 /// ParseDirectiveFile
1603 /// ::= .file [number] string
1604 bool AsmParser::ParseDirectiveFile(SMLoc DirectiveLoc) {
1605   // FIXME: I'm not sure what this is.
1606   int64_t FileNumber = -1;
1607   if (Lexer.is(AsmToken::Integer)) {
1608     FileNumber = Lexer.getTok().getIntVal();
1609     Lexer.Lex();
1610     
1611     if (FileNumber < 1)
1612       return TokError("file number less than one");
1613   }
1614
1615   if (Lexer.isNot(AsmToken::String))
1616     return TokError("unexpected token in '.file' directive");
1617   
1618   StringRef FileName = Lexer.getTok().getString();
1619   Lexer.Lex();
1620
1621   if (Lexer.isNot(AsmToken::EndOfStatement))
1622     return TokError("unexpected token in '.file' directive");
1623
1624   // FIXME: Do something with the .file.
1625
1626   return false;
1627 }
1628
1629 /// ParseDirectiveLine
1630 /// ::= .line [number]
1631 bool AsmParser::ParseDirectiveLine(SMLoc DirectiveLoc) {
1632   if (Lexer.isNot(AsmToken::EndOfStatement)) {
1633     if (Lexer.isNot(AsmToken::Integer))
1634       return TokError("unexpected token in '.line' directive");
1635
1636     int64_t LineNumber = Lexer.getTok().getIntVal();
1637     (void) LineNumber;
1638     Lexer.Lex();
1639
1640     // FIXME: Do something with the .line.
1641   }
1642
1643   if (Lexer.isNot(AsmToken::EndOfStatement))
1644     return TokError("unexpected token in '.file' directive");
1645
1646   return false;
1647 }
1648
1649
1650 /// ParseDirectiveLoc
1651 /// ::= .loc number [number [number]]
1652 bool AsmParser::ParseDirectiveLoc(SMLoc DirectiveLoc) {
1653   if (Lexer.isNot(AsmToken::Integer))
1654     return TokError("unexpected token in '.loc' directive");
1655
1656   // FIXME: What are these fields?
1657   int64_t FileNumber = Lexer.getTok().getIntVal();
1658   (void) FileNumber;
1659   // FIXME: Validate file.
1660
1661   Lexer.Lex();
1662   if (Lexer.isNot(AsmToken::EndOfStatement)) {
1663     if (Lexer.isNot(AsmToken::Integer))
1664       return TokError("unexpected token in '.loc' directive");
1665
1666     int64_t Param2 = Lexer.getTok().getIntVal();
1667     (void) Param2;
1668     Lexer.Lex();
1669
1670     if (Lexer.isNot(AsmToken::EndOfStatement)) {
1671       if (Lexer.isNot(AsmToken::Integer))
1672         return TokError("unexpected token in '.loc' directive");
1673
1674       int64_t Param3 = Lexer.getTok().getIntVal();
1675       (void) Param3;
1676       Lexer.Lex();
1677
1678       // FIXME: Do something with the .loc.
1679     }
1680   }
1681
1682   if (Lexer.isNot(AsmToken::EndOfStatement))
1683     return TokError("unexpected token in '.file' directive");
1684
1685   return false;
1686 }
1687