llvm-mc: Diagnose misuse (mix) of defined symbols and labels.
[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 "AsmExpr.h"
17 #include "llvm/MC/MCContext.h"
18 #include "llvm/MC/MCInst.h"
19 #include "llvm/MC/MCStreamer.h"
20 #include "llvm/MC/MCSymbol.h"
21 #include "llvm/Support/SourceMgr.h"
22 #include "llvm/Support/raw_ostream.h"
23 using namespace llvm;
24
25 bool AsmParser::Error(SMLoc L, const char *Msg) {
26   Lexer.PrintMessage(L, Msg);
27   return true;
28 }
29
30 bool AsmParser::TokError(const char *Msg) {
31   Lexer.PrintMessage(Lexer.getLoc(), Msg);
32   return true;
33 }
34
35 bool AsmParser::Run() {
36   // Prime the lexer.
37   Lexer.Lex();
38   
39   while (Lexer.isNot(asmtok::Eof))
40     if (ParseStatement())
41       return true;
42   
43   return false;
44 }
45
46 /// EatToEndOfStatement - Throw away the rest of the line for testing purposes.
47 void AsmParser::EatToEndOfStatement() {
48   while (Lexer.isNot(asmtok::EndOfStatement) &&
49          Lexer.isNot(asmtok::Eof))
50     Lexer.Lex();
51   
52   // Eat EOL.
53   if (Lexer.is(asmtok::EndOfStatement))
54     Lexer.Lex();
55 }
56
57
58 /// ParseParenExpr - Parse a paren expression and return it.
59 /// NOTE: This assumes the leading '(' has already been consumed.
60 ///
61 /// parenexpr ::= expr)
62 ///
63 bool AsmParser::ParseParenExpr(AsmExpr *&Res) {
64   if (ParseExpression(Res)) return true;
65   if (Lexer.isNot(asmtok::RParen))
66     return TokError("expected ')' in parentheses expression");
67   Lexer.Lex();
68   return false;
69 }
70
71 /// ParsePrimaryExpr - Parse a primary expression and return it.
72 ///  primaryexpr ::= (parenexpr
73 ///  primaryexpr ::= symbol
74 ///  primaryexpr ::= number
75 ///  primaryexpr ::= ~,+,- primaryexpr
76 bool AsmParser::ParsePrimaryExpr(AsmExpr *&Res) {
77   switch (Lexer.getKind()) {
78   default:
79     return TokError("unknown token in expression");
80   case asmtok::Exclaim:
81     Lexer.Lex(); // Eat the operator.
82     if (ParsePrimaryExpr(Res))
83       return true;
84     Res = new AsmUnaryExpr(AsmUnaryExpr::LNot, Res);
85     return false;
86   case asmtok::Identifier: {
87     // This is a label, this should be parsed as part of an expression, to
88     // handle things like LFOO+4.
89     MCSymbol *Sym = Ctx.GetOrCreateSymbol(Lexer.getCurStrVal());
90
91     // If this is use of an undefined symbol then mark it external.
92     if (!Sym->getSection() && !Ctx.GetSymbolValue(Sym))
93       Sym->setExternal(true);
94     
95     Res = new AsmSymbolRefExpr(Sym);
96     Lexer.Lex(); // Eat identifier.
97     return false;
98   }
99   case asmtok::IntVal:
100     Res = new AsmConstantExpr(Lexer.getCurIntVal());
101     Lexer.Lex(); // Eat identifier.
102     return false;
103   case asmtok::LParen:
104     Lexer.Lex(); // Eat the '('.
105     return ParseParenExpr(Res);
106   case asmtok::Minus:
107     Lexer.Lex(); // Eat the operator.
108     if (ParsePrimaryExpr(Res))
109       return true;
110     Res = new AsmUnaryExpr(AsmUnaryExpr::Minus, Res);
111     return false;
112   case asmtok::Plus:
113     Lexer.Lex(); // Eat the operator.
114     if (ParsePrimaryExpr(Res))
115       return true;
116     Res = new AsmUnaryExpr(AsmUnaryExpr::Plus, Res);
117     return false;
118   case asmtok::Tilde:
119     Lexer.Lex(); // Eat the operator.
120     if (ParsePrimaryExpr(Res))
121       return true;
122     Res = new AsmUnaryExpr(AsmUnaryExpr::Not, Res);
123     return false;
124   }
125 }
126
127 /// ParseExpression - Parse an expression and return it.
128 /// 
129 ///  expr ::= expr +,- expr          -> lowest.
130 ///  expr ::= expr |,^,&,! expr      -> middle.
131 ///  expr ::= expr *,/,%,<<,>> expr  -> highest.
132 ///  expr ::= primaryexpr
133 ///
134 bool AsmParser::ParseExpression(AsmExpr *&Res) {
135   Res = 0;
136   return ParsePrimaryExpr(Res) ||
137          ParseBinOpRHS(1, Res);
138 }
139
140 bool AsmParser::ParseAbsoluteExpression(int64_t &Res) {
141   AsmExpr *Expr;
142   
143   if (ParseExpression(Expr))
144     return true;
145
146   if (!Expr->EvaluateAsAbsolute(Ctx, Res))
147     return TokError("expected absolute expression");
148
149   return false;
150 }
151
152 static unsigned getBinOpPrecedence(asmtok::TokKind K, 
153                                    AsmBinaryExpr::Opcode &Kind) {
154   switch (K) {
155   default: return 0;    // not a binop.
156
157     // Lowest Precedence: &&, ||
158   case asmtok::AmpAmp:
159     Kind = AsmBinaryExpr::LAnd;
160     return 1;
161   case asmtok::PipePipe:
162     Kind = AsmBinaryExpr::LOr;
163     return 1;
164
165     // Low Precedence: +, -, ==, !=, <>, <, <=, >, >=
166   case asmtok::Plus:
167     Kind = AsmBinaryExpr::Add;
168     return 2;
169   case asmtok::Minus:
170     Kind = AsmBinaryExpr::Sub;
171     return 2;
172   case asmtok::EqualEqual:
173     Kind = AsmBinaryExpr::EQ;
174     return 2;
175   case asmtok::ExclaimEqual:
176   case asmtok::LessGreater:
177     Kind = AsmBinaryExpr::NE;
178     return 2;
179   case asmtok::Less:
180     Kind = AsmBinaryExpr::LT;
181     return 2;
182   case asmtok::LessEqual:
183     Kind = AsmBinaryExpr::LTE;
184     return 2;
185   case asmtok::Greater:
186     Kind = AsmBinaryExpr::GT;
187     return 2;
188   case asmtok::GreaterEqual:
189     Kind = AsmBinaryExpr::GTE;
190     return 2;
191
192     // Intermediate Precedence: |, &, ^
193     //
194     // FIXME: gas seems to support '!' as an infix operator?
195   case asmtok::Pipe:
196     Kind = AsmBinaryExpr::Or;
197     return 3;
198   case asmtok::Caret:
199     Kind = AsmBinaryExpr::Xor;
200     return 3;
201   case asmtok::Amp:
202     Kind = AsmBinaryExpr::And;
203     return 3;
204
205     // Highest Precedence: *, /, %, <<, >>
206   case asmtok::Star:
207     Kind = AsmBinaryExpr::Mul;
208     return 4;
209   case asmtok::Slash:
210     Kind = AsmBinaryExpr::Div;
211     return 4;
212   case asmtok::Percent:
213     Kind = AsmBinaryExpr::Mod;
214     return 4;
215   case asmtok::LessLess:
216     Kind = AsmBinaryExpr::Shl;
217     return 4;
218   case asmtok::GreaterGreater:
219     Kind = AsmBinaryExpr::Shr;
220     return 4;
221   }
222 }
223
224
225 /// ParseBinOpRHS - Parse all binary operators with precedence >= 'Precedence'.
226 /// Res contains the LHS of the expression on input.
227 bool AsmParser::ParseBinOpRHS(unsigned Precedence, AsmExpr *&Res) {
228   while (1) {
229     AsmBinaryExpr::Opcode Kind = AsmBinaryExpr::Add;
230     unsigned TokPrec = getBinOpPrecedence(Lexer.getKind(), Kind);
231     
232     // If the next token is lower precedence than we are allowed to eat, return
233     // successfully with what we ate already.
234     if (TokPrec < Precedence)
235       return false;
236     
237     Lexer.Lex();
238     
239     // Eat the next primary expression.
240     AsmExpr *RHS;
241     if (ParsePrimaryExpr(RHS)) return true;
242     
243     // If BinOp binds less tightly with RHS than the operator after RHS, let
244     // the pending operator take RHS as its LHS.
245     AsmBinaryExpr::Opcode Dummy;
246     unsigned NextTokPrec = getBinOpPrecedence(Lexer.getKind(), Dummy);
247     if (TokPrec < NextTokPrec) {
248       if (ParseBinOpRHS(Precedence+1, RHS)) return true;
249     }
250
251     // Merge LHS and RHS according to operator.
252     Res = new AsmBinaryExpr(Kind, Res, RHS);
253   }
254 }
255
256   
257   
258   
259 /// ParseStatement:
260 ///   ::= EndOfStatement
261 ///   ::= Label* Directive ...Operands... EndOfStatement
262 ///   ::= Label* Identifier OperandList* EndOfStatement
263 bool AsmParser::ParseStatement() {
264   switch (Lexer.getKind()) {
265   default:
266     return TokError("unexpected token at start of statement");
267   case asmtok::EndOfStatement:
268     Lexer.Lex();
269     return false;
270   case asmtok::Identifier:
271     break;
272   // TODO: Recurse on local labels etc.
273   }
274   
275   // If we have an identifier, handle it as the key symbol.
276   SMLoc IDLoc = Lexer.getLoc();
277   const char *IDVal = Lexer.getCurStrVal();
278   
279   // Consume the identifier, see what is after it.
280   switch (Lexer.Lex()) {
281   case asmtok::Colon: {
282     // identifier ':'   -> Label.
283     Lexer.Lex();
284
285     // Diagnose attempt to use a variable as a label.
286     //
287     // FIXME: Diagnostics. Note the location of the definition as a label.
288     // FIXME: This doesn't diagnose assignment to a symbol which has been
289     // implicitly marked as external.
290     MCSymbol *Sym = Ctx.GetOrCreateSymbol(IDVal);
291     if (Sym->getSection())
292       return Error(IDLoc, "invalid symbol redefinition");
293     if (Ctx.GetSymbolValue(Sym))
294       return Error(IDLoc, "symbol already used as assembler variable");
295     
296     // Since we saw a label, create a symbol and emit it.
297     // FIXME: If the label starts with L it is an assembler temporary label.
298     // Why does the client of this api need to know this?
299     Out.EmitLabel(Sym);
300    
301     return ParseStatement();
302   }
303
304   case asmtok::Equal:
305     // identifier '=' ... -> assignment statement
306     Lexer.Lex();
307
308     return ParseAssignment(IDVal, false);
309
310   default: // Normal instruction or directive.
311     break;
312   }
313   
314   // Otherwise, we have a normal instruction or directive.  
315   if (IDVal[0] == '.') {
316     // FIXME: This should be driven based on a hash lookup and callback.
317     if (!strcmp(IDVal, ".section"))
318       return ParseDirectiveDarwinSection();
319     if (!strcmp(IDVal, ".text"))
320       // FIXME: This changes behavior based on the -static flag to the
321       // assembler.
322       return ParseDirectiveSectionSwitch("__TEXT,__text",
323                                          "regular,pure_instructions");
324     if (!strcmp(IDVal, ".const"))
325       return ParseDirectiveSectionSwitch("__TEXT,__const");
326     if (!strcmp(IDVal, ".static_const"))
327       return ParseDirectiveSectionSwitch("__TEXT,__static_const");
328     if (!strcmp(IDVal, ".cstring"))
329       return ParseDirectiveSectionSwitch("__TEXT,__cstring", 
330                                          "cstring_literals");
331     if (!strcmp(IDVal, ".literal4"))
332       return ParseDirectiveSectionSwitch("__TEXT,__literal4", "4byte_literals");
333     if (!strcmp(IDVal, ".literal8"))
334       return ParseDirectiveSectionSwitch("__TEXT,__literal8", "8byte_literals");
335     if (!strcmp(IDVal, ".literal16"))
336       return ParseDirectiveSectionSwitch("__TEXT,__literal16",
337                                          "16byte_literals");
338     if (!strcmp(IDVal, ".constructor"))
339       return ParseDirectiveSectionSwitch("__TEXT,__constructor");
340     if (!strcmp(IDVal, ".destructor"))
341       return ParseDirectiveSectionSwitch("__TEXT,__destructor");
342     if (!strcmp(IDVal, ".fvmlib_init0"))
343       return ParseDirectiveSectionSwitch("__TEXT,__fvmlib_init0");
344     if (!strcmp(IDVal, ".fvmlib_init1"))
345       return ParseDirectiveSectionSwitch("__TEXT,__fvmlib_init1");
346     if (!strcmp(IDVal, ".symbol_stub")) // FIXME: Different on PPC.
347       return ParseDirectiveSectionSwitch("__IMPORT,__jump_table,symbol_stubs",
348                                     "self_modifying_code+pure_instructions,5");
349     // FIXME: .picsymbol_stub on PPC.
350     if (!strcmp(IDVal, ".data"))
351       return ParseDirectiveSectionSwitch("__DATA,__data");
352     if (!strcmp(IDVal, ".static_data"))
353       return ParseDirectiveSectionSwitch("__DATA,__static_data");
354     if (!strcmp(IDVal, ".non_lazy_symbol_pointer"))
355       return ParseDirectiveSectionSwitch("__DATA,__nl_symbol_pointer",
356                                          "non_lazy_symbol_pointers");
357     if (!strcmp(IDVal, ".lazy_symbol_pointer"))
358       return ParseDirectiveSectionSwitch("__DATA,__la_symbol_pointer",
359                                          "lazy_symbol_pointers");
360     if (!strcmp(IDVal, ".dyld"))
361       return ParseDirectiveSectionSwitch("__DATA,__dyld");
362     if (!strcmp(IDVal, ".mod_init_func"))
363       return ParseDirectiveSectionSwitch("__DATA,__mod_init_func",
364                                          "mod_init_funcs");
365     if (!strcmp(IDVal, ".mod_term_func"))
366       return ParseDirectiveSectionSwitch("__DATA,__mod_term_func",
367                                          "mod_term_funcs");
368     if (!strcmp(IDVal, ".const_data"))
369       return ParseDirectiveSectionSwitch("__DATA,__const", "regular");
370     
371     
372     // FIXME: Verify attributes on sections.
373     if (!strcmp(IDVal, ".objc_class"))
374       return ParseDirectiveSectionSwitch("__OBJC,__class");
375     if (!strcmp(IDVal, ".objc_meta_class"))
376       return ParseDirectiveSectionSwitch("__OBJC,__meta_class");
377     if (!strcmp(IDVal, ".objc_cat_cls_meth"))
378       return ParseDirectiveSectionSwitch("__OBJC,__cat_cls_meth");
379     if (!strcmp(IDVal, ".objc_cat_inst_meth"))
380       return ParseDirectiveSectionSwitch("__OBJC,__cat_inst_meth");
381     if (!strcmp(IDVal, ".objc_protocol"))
382       return ParseDirectiveSectionSwitch("__OBJC,__protocol");
383     if (!strcmp(IDVal, ".objc_string_object"))
384       return ParseDirectiveSectionSwitch("__OBJC,__string_object");
385     if (!strcmp(IDVal, ".objc_cls_meth"))
386       return ParseDirectiveSectionSwitch("__OBJC,__cls_meth");
387     if (!strcmp(IDVal, ".objc_inst_meth"))
388       return ParseDirectiveSectionSwitch("__OBJC,__inst_meth");
389     if (!strcmp(IDVal, ".objc_cls_refs"))
390       return ParseDirectiveSectionSwitch("__OBJC,__cls_refs");
391     if (!strcmp(IDVal, ".objc_message_refs"))
392       return ParseDirectiveSectionSwitch("__OBJC,__message_refs");
393     if (!strcmp(IDVal, ".objc_symbols"))
394       return ParseDirectiveSectionSwitch("__OBJC,__symbols");
395     if (!strcmp(IDVal, ".objc_category"))
396       return ParseDirectiveSectionSwitch("__OBJC,__category");
397     if (!strcmp(IDVal, ".objc_class_vars"))
398       return ParseDirectiveSectionSwitch("__OBJC,__class_vars");
399     if (!strcmp(IDVal, ".objc_instance_vars"))
400       return ParseDirectiveSectionSwitch("__OBJC,__instance_vars");
401     if (!strcmp(IDVal, ".objc_module_info"))
402       return ParseDirectiveSectionSwitch("__OBJC,__module_info");
403     if (!strcmp(IDVal, ".objc_class_names"))
404       return ParseDirectiveSectionSwitch("__TEXT,__cstring","cstring_literals");
405     if (!strcmp(IDVal, ".objc_meth_var_types"))
406       return ParseDirectiveSectionSwitch("__TEXT,__cstring","cstring_literals");
407     if (!strcmp(IDVal, ".objc_meth_var_names"))
408       return ParseDirectiveSectionSwitch("__TEXT,__cstring","cstring_literals");
409     if (!strcmp(IDVal, ".objc_selector_strs"))
410       return ParseDirectiveSectionSwitch("__OBJC,__selector_strs");
411     
412     // Assembler features
413     if (!strcmp(IDVal, ".set"))
414       return ParseDirectiveSet();
415
416     // Data directives
417
418     if (!strcmp(IDVal, ".ascii"))
419       return ParseDirectiveAscii(false);
420     if (!strcmp(IDVal, ".asciz"))
421       return ParseDirectiveAscii(true);
422
423     // FIXME: Target hooks for size? Also for "word", "hword".
424     if (!strcmp(IDVal, ".byte"))
425       return ParseDirectiveValue(1);
426     if (!strcmp(IDVal, ".short"))
427       return ParseDirectiveValue(2);
428     if (!strcmp(IDVal, ".long"))
429       return ParseDirectiveValue(4);
430     if (!strcmp(IDVal, ".quad"))
431       return ParseDirectiveValue(8);
432     if (!strcmp(IDVal, ".fill"))
433       return ParseDirectiveFill();
434     if (!strcmp(IDVal, ".org"))
435       return ParseDirectiveOrg();
436     if (!strcmp(IDVal, ".space"))
437       return ParseDirectiveSpace();
438
439     Lexer.PrintMessage(IDLoc, "warning: ignoring directive for now");
440     EatToEndOfStatement();
441     return false;
442   }
443
444   MCInst Inst;
445   if (ParseX86InstOperands(Inst))
446     return true;
447   
448   if (Lexer.isNot(asmtok::EndOfStatement))
449     return TokError("unexpected token in argument list");
450
451   // Eat the end of statement marker.
452   Lexer.Lex();
453   
454   // Instruction is good, process it.
455   outs() << "Found instruction: " << IDVal << " with " << Inst.getNumOperands()
456          << " operands.\n";
457   
458   // Skip to end of line for now.
459   return false;
460 }
461
462 bool AsmParser::ParseAssignment(const char *Name, bool IsDotSet) {
463   // FIXME: Use better location, we should use proper tokens.
464   SMLoc EqualLoc = Lexer.getLoc();
465
466   int64_t Value;
467   if (ParseAbsoluteExpression(Value))
468     return true;
469   
470   if (Lexer.isNot(asmtok::EndOfStatement))
471     return TokError("unexpected token in assignment");
472
473   // Eat the end of statement marker.
474   Lexer.Lex();
475
476   // Diagnose assignment to a label.
477   //
478   // FIXME: Diagnostics. Note the location of the definition as a label.
479   // FIXME: This doesn't diagnose assignment to a symbol which has been
480   // implicitly marked as external.
481   // FIXME: Handle '.'.
482   // FIXME: Diagnose assignment to protected identifier (e.g., register name).
483   MCSymbol *Sym = Ctx.GetOrCreateSymbol(Name);
484   if (Sym->getSection())
485     return Error(EqualLoc, "invalid assignment to symbol emitted as a label");
486   if (Sym->isExternal())
487     return Error(EqualLoc, "invalid assignment to external symbol");
488
489   // Do the assignment.
490   Out.EmitAssignment(Sym, MCValue::get(Value), IsDotSet);
491
492   return false;
493 }
494
495 /// ParseDirectiveSet:
496 ///   ::= .set identifier ',' expression
497 bool AsmParser::ParseDirectiveSet() {
498   if (Lexer.isNot(asmtok::Identifier))
499     return TokError("expected identifier after '.set' directive");
500
501   const char *Name = Lexer.getCurStrVal();
502   
503   if (Lexer.Lex() != asmtok::Comma)
504     return TokError("unexpected token in '.set'");
505   Lexer.Lex();
506
507   return ParseAssignment(Name, true);
508 }
509
510 /// ParseDirectiveSection:
511 ///   ::= .section identifier (',' identifier)*
512 /// FIXME: This should actually parse out the segment, section, attributes and
513 /// sizeof_stub fields.
514 bool AsmParser::ParseDirectiveDarwinSection() {
515   if (Lexer.isNot(asmtok::Identifier))
516     return TokError("expected identifier after '.section' directive");
517   
518   std::string Section = Lexer.getCurStrVal();
519   Lexer.Lex();
520   
521   // Accept a comma separated list of modifiers.
522   while (Lexer.is(asmtok::Comma)) {
523     Lexer.Lex();
524     
525     if (Lexer.isNot(asmtok::Identifier))
526       return TokError("expected identifier in '.section' directive");
527     Section += ',';
528     Section += Lexer.getCurStrVal();
529     Lexer.Lex();
530   }
531   
532   if (Lexer.isNot(asmtok::EndOfStatement))
533     return TokError("unexpected token in '.section' directive");
534   Lexer.Lex();
535
536   Out.SwitchSection(Ctx.GetSection(Section.c_str()));
537   return false;
538 }
539
540 bool AsmParser::ParseDirectiveSectionSwitch(const char *Section,
541                                             const char *Directives) {
542   if (Lexer.isNot(asmtok::EndOfStatement))
543     return TokError("unexpected token in section switching directive");
544   Lexer.Lex();
545   
546   std::string SectionStr = Section;
547   if (Directives && Directives[0]) {
548     SectionStr += ","; 
549     SectionStr += Directives;
550   }
551   
552   Out.SwitchSection(Ctx.GetSection(Section));
553   return false;
554 }
555
556 /// ParseDirectiveAscii:
557 ///   ::= ( .ascii | .asciz ) [ "string" ( , "string" )* ]
558 bool AsmParser::ParseDirectiveAscii(bool ZeroTerminated) {
559   if (Lexer.isNot(asmtok::EndOfStatement)) {
560     for (;;) {
561       if (Lexer.isNot(asmtok::String))
562         return TokError("expected string in '.ascii' or '.asciz' directive");
563       
564       // FIXME: This shouldn't use a const char* + strlen, the string could have
565       // embedded nulls.
566       // FIXME: Should have accessor for getting string contents.
567       const char *Str = Lexer.getCurStrVal();
568       Out.EmitBytes(Str + 1, strlen(Str) - 2);
569       if (ZeroTerminated)
570         Out.EmitBytes("\0", 1);
571       
572       Lexer.Lex();
573       
574       if (Lexer.is(asmtok::EndOfStatement))
575         break;
576
577       if (Lexer.isNot(asmtok::Comma))
578         return TokError("unexpected token in '.ascii' or '.asciz' directive");
579       Lexer.Lex();
580     }
581   }
582
583   Lexer.Lex();
584   return false;
585 }
586
587 /// ParseDirectiveValue
588 ///  ::= (.byte | .short | ... ) [ expression (, expression)* ]
589 bool AsmParser::ParseDirectiveValue(unsigned Size) {
590   if (Lexer.isNot(asmtok::EndOfStatement)) {
591     for (;;) {
592       int64_t Expr;
593       if (ParseAbsoluteExpression(Expr))
594         return true;
595
596       Out.EmitValue(MCValue::get(Expr), Size);
597
598       if (Lexer.is(asmtok::EndOfStatement))
599         break;
600       
601       // FIXME: Improve diagnostic.
602       if (Lexer.isNot(asmtok::Comma))
603         return TokError("unexpected token in directive");
604       Lexer.Lex();
605     }
606   }
607
608   Lexer.Lex();
609   return false;
610 }
611
612 /// ParseDirectiveSpace
613 ///  ::= .space expression [ , expression ]
614 bool AsmParser::ParseDirectiveSpace() {
615   int64_t NumBytes;
616   if (ParseAbsoluteExpression(NumBytes))
617     return true;
618
619   int64_t FillExpr = 0;
620   bool HasFillExpr = false;
621   if (Lexer.isNot(asmtok::EndOfStatement)) {
622     if (Lexer.isNot(asmtok::Comma))
623       return TokError("unexpected token in '.space' directive");
624     Lexer.Lex();
625     
626     if (ParseAbsoluteExpression(FillExpr))
627       return true;
628
629     HasFillExpr = true;
630
631     if (Lexer.isNot(asmtok::EndOfStatement))
632       return TokError("unexpected token in '.space' directive");
633   }
634
635   Lexer.Lex();
636
637   if (NumBytes <= 0)
638     return TokError("invalid number of bytes in '.space' directive");
639
640   // FIXME: Sometimes the fill expr is 'nop' if it isn't supplied, instead of 0.
641   for (uint64_t i = 0, e = NumBytes; i != e; ++i)
642     Out.EmitValue(MCValue::get(FillExpr), 1);
643
644   return false;
645 }
646
647 /// ParseDirectiveFill
648 ///  ::= .fill expression , expression , expression
649 bool AsmParser::ParseDirectiveFill() {
650   int64_t NumValues;
651   if (ParseAbsoluteExpression(NumValues))
652     return true;
653
654   if (Lexer.isNot(asmtok::Comma))
655     return TokError("unexpected token in '.fill' directive");
656   Lexer.Lex();
657   
658   int64_t FillSize;
659   if (ParseAbsoluteExpression(FillSize))
660     return true;
661
662   if (Lexer.isNot(asmtok::Comma))
663     return TokError("unexpected token in '.fill' directive");
664   Lexer.Lex();
665   
666   int64_t FillExpr;
667   if (ParseAbsoluteExpression(FillExpr))
668     return true;
669
670   if (Lexer.isNot(asmtok::EndOfStatement))
671     return TokError("unexpected token in '.fill' directive");
672   
673   Lexer.Lex();
674
675   if (FillSize != 1 && FillSize != 2 && FillSize != 4)
676     return TokError("invalid '.fill' size, expected 1, 2, or 4");
677
678   for (uint64_t i = 0, e = NumValues; i != e; ++i)
679     Out.EmitValue(MCValue::get(FillExpr), FillSize);
680
681   return false;
682 }
683
684 /// ParseDirectiveOrg
685 ///  ::= .org expression [ , expression ]
686 bool AsmParser::ParseDirectiveOrg() {
687   int64_t Offset;
688   if (ParseAbsoluteExpression(Offset))
689     return true;
690
691   // Parse optional fill expression.
692   int64_t FillExpr = 0;
693   if (Lexer.isNot(asmtok::EndOfStatement)) {
694     if (Lexer.isNot(asmtok::Comma))
695       return TokError("unexpected token in '.org' directive");
696     Lexer.Lex();
697     
698     if (ParseAbsoluteExpression(FillExpr))
699       return true;
700
701     if (Lexer.isNot(asmtok::EndOfStatement))
702       return TokError("unexpected token in '.org' directive");
703   }
704
705   Lexer.Lex();
706   
707   Out.EmitValueToOffset(MCValue::get(Offset), FillExpr);
708
709   return false;
710 }