[llvm] r198646 - [Mips] TargetStreamer Support for .abicalls and .set pic0.

Jack Carter jack.carter at imgtec.com
Mon Jan 6 15:27:31 PST 2014


Author: jacksprat
Date: Mon Jan  6 17:27:31 2014
New Revision: 198646

URL: http://llvm.org/viewvc/llvm-project?rev=198646&view=rev
Log:
[Mips] TargetStreamer Support for .abicalls and .set pic0.

This patch adds .abicalls and .set pic0 support which
affects the ELF ABI and its flags. In addition the patch uses
a common interface for both the MipsTargetSteamer and
MipsObjectStreamer that both the integrated and standalone
assemblers will use for the output for these directives.

Added:
    llvm/trunk/test/MC/Mips/mips_directives_bad.s
Modified:
    llvm/trunk/lib/Target/Mips/AsmParser/MipsAsmParser.cpp
    llvm/trunk/lib/Target/Mips/MCTargetDesc/MipsMCTargetDesc.cpp
    llvm/trunk/lib/Target/Mips/MCTargetDesc/MipsTargetStreamer.cpp
    llvm/trunk/lib/Target/Mips/MipsAsmPrinter.cpp
    llvm/trunk/lib/Target/Mips/MipsTargetStreamer.h
    llvm/trunk/test/MC/Mips/elf_eflags.ll
    llvm/trunk/test/MC/Mips/elf_eflags.s
    llvm/trunk/test/MC/Mips/mips_directives.s

Modified: llvm/trunk/lib/Target/Mips/AsmParser/MipsAsmParser.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/Mips/AsmParser/MipsAsmParser.cpp?rev=198646&r1=198645&r2=198646&view=diff
==============================================================================
--- llvm/trunk/lib/Target/Mips/AsmParser/MipsAsmParser.cpp (original)
+++ llvm/trunk/lib/Target/Mips/AsmParser/MipsAsmParser.cpp Mon Jan  6 17:27:31 2014
@@ -196,6 +196,7 @@ class MipsAsmParser : public MCTargetAsm
   bool parseDirectiveSet();
   bool parseDirectiveMipsHackStocg();
   bool parseDirectiveMipsHackELFFlags();
+  bool parseDirectiveOption();
 
   bool parseSetAtDirective();
   bool parseSetNoAtDirective();
@@ -2468,6 +2469,35 @@ bool MipsAsmParser::parseDirectiveGpWord
   return false;
 }
 
+bool MipsAsmParser::parseDirectiveOption() {
+  // Get the option token.
+  AsmToken Tok = Parser.getTok();
+  // At the moment only identifiers are supported.
+  if (Tok.isNot(AsmToken::Identifier)) {
+    Error(Parser.getTok().getLoc(), "unexpected token in .option directive");
+    Parser.eatToEndOfStatement();
+    return false;
+  }
+
+  StringRef Option = Tok.getIdentifier();
+
+  if (Option == "pic0") {
+    getTargetStreamer().emitDirectiveOptionPic0();
+    Parser.Lex();
+    if (Parser.getTok().isNot(AsmToken::EndOfStatement)) {
+      Error(Parser.getTok().getLoc(),
+            "unexpected token in .option pic0 directive");
+      Parser.eatToEndOfStatement();
+    }
+    return false;
+  }
+
+  // Unknown option.
+  Warning(Parser.getTok().getLoc(), "unknown option in .option directive");
+  Parser.eatToEndOfStatement();
+  return false;
+}
+
 bool MipsAsmParser::ParseDirective(AsmToken DirectiveID) {
 
   StringRef IDVal = DirectiveID.getString();
@@ -2523,6 +2553,19 @@ bool MipsAsmParser::ParseDirective(AsmTo
   if (IDVal == ".mips_hack_elf_flags")
     return parseDirectiveMipsHackELFFlags();
 
+  if (IDVal == ".option")
+    return parseDirectiveOption();
+
+  if (IDVal == ".abicalls") {
+    getTargetStreamer().emitDirectiveAbiCalls();
+    if (Parser.getTok().isNot(AsmToken::EndOfStatement)) {
+      Error(Parser.getTok().getLoc(), "unexpected token in directive");
+      // Clear line
+      Parser.eatToEndOfStatement();
+    }
+    return false;
+  }
+
   return true;
 }
 

Modified: llvm/trunk/lib/Target/Mips/MCTargetDesc/MipsMCTargetDesc.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/Mips/MCTargetDesc/MipsMCTargetDesc.cpp?rev=198646&r1=198645&r2=198646&view=diff
==============================================================================
--- llvm/trunk/lib/Target/Mips/MCTargetDesc/MipsMCTargetDesc.cpp (original)
+++ llvm/trunk/lib/Target/Mips/MCTargetDesc/MipsMCTargetDesc.cpp Mon Jan  6 17:27:31 2014
@@ -16,7 +16,6 @@
 #include "MipsMCAsmInfo.h"
 #include "MipsTargetStreamer.h"
 #include "llvm/MC/MCCodeGenInfo.h"
-#include "llvm/MC/MCELF.h"
 #include "llvm/MC/MCELFStreamer.h"
 #include "llvm/MC/MCInstrInfo.h"
 #include "llvm/MC/MCRegisterInfo.h"

Modified: llvm/trunk/lib/Target/Mips/MCTargetDesc/MipsTargetStreamer.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/Mips/MCTargetDesc/MipsTargetStreamer.cpp?rev=198646&r1=198645&r2=198646&view=diff
==============================================================================
--- llvm/trunk/lib/Target/Mips/MCTargetDesc/MipsTargetStreamer.cpp (original)
+++ llvm/trunk/lib/Target/Mips/MCTargetDesc/MipsTargetStreamer.cpp Mon Jan  6 17:27:31 2014
@@ -17,13 +17,14 @@
 #include "llvm/Support/CommandLine.h"
 #include "llvm/Support/ErrorHandling.h"
 #include "llvm/Support/FormattedStream.h"
+#include "llvm/Support/ELF.h"
 
 using namespace llvm;
 
 static cl::opt<bool> PrintHackDirectives("print-hack-directives",
                                          cl::init(false), cl::Hidden);
 
-// pin vtable to this file
+// Pin vtable to this file.
 void MipsTargetStreamer::anchor() {}
 
 MipsTargetAsmStreamer::MipsTargetAsmStreamer(formatted_raw_ostream &OS)
@@ -47,6 +48,13 @@ void MipsTargetAsmStreamer::emitMipsHack
   OS << Val;
   OS << '\n';
 }
+void MipsTargetAsmStreamer::emitDirectiveAbiCalls() { OS << "\t.abicalls\n"; }
+void MipsTargetAsmStreamer::emitDirectiveOptionPic0() {
+  OS << "\t.option\tpic0\n";
+}
+
+// This part is for ELF object output.
+MipsTargetELFStreamer::MipsTargetELFStreamer() {}
 
 MCELFStreamer &MipsTargetELFStreamer::getStreamer() {
   return static_cast<MCELFStreamer &>(*Streamer);
@@ -57,7 +65,7 @@ void MipsTargetELFStreamer::emitMipsHack
   MCA.setELFHeaderEFlags(Flags);
 }
 
-// Set a symbol's STO flags
+// Set a symbol's STO flags.
 void MipsTargetELFStreamer::emitMipsHackSTOCG(MCSymbol *Sym, unsigned Val) {
   MCSymbolData &Data = getStreamer().getOrCreateSymbolData(Sym);
   // The "other" values are stored in the last 6 bits of the second byte
@@ -65,3 +73,15 @@ void MipsTargetELFStreamer::emitMipsHack
   // the shift to pack it.
   MCELF::setOther(Data, Val >> 2);
 }
+void MipsTargetELFStreamer::emitDirectiveAbiCalls() {
+  MCAssembler &MCA = getStreamer().getAssembler();
+  unsigned Flags = MCA.getELFHeaderEFlags();
+  Flags |= ELF::EF_MIPS_CPIC;
+  MCA.setELFHeaderEFlags(Flags);
+}
+void MipsTargetELFStreamer::emitDirectiveOptionPic0() {
+  MCAssembler &MCA = getStreamer().getAssembler();
+  unsigned Flags = MCA.getELFHeaderEFlags();
+  Flags &= ~ELF::EF_MIPS_PIC;
+  MCA.setELFHeaderEFlags(Flags);
+}

Modified: llvm/trunk/lib/Target/Mips/MipsAsmPrinter.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/Mips/MipsAsmPrinter.cpp?rev=198646&r1=198645&r2=198646&view=diff
==============================================================================
--- llvm/trunk/lib/Target/Mips/MipsAsmPrinter.cpp (original)
+++ llvm/trunk/lib/Target/Mips/MipsAsmPrinter.cpp Mon Jan  6 17:27:31 2014
@@ -608,12 +608,10 @@ void MipsAsmPrinter::EmitStartOfAsmFile(
 
   // TODO: Need to add -mabicalls and -mno-abicalls flags.
   // Currently we assume that -mabicalls is the default.
-  if (OutStreamer.hasRawTextSupport()) {
-    OutStreamer.EmitRawText(StringRef("\t.abicalls"));
-    Reloc::Model RM = Subtarget->getRelocationModel();
-    if (RM == Reloc::Static && !Subtarget->hasMips64())
-      OutStreamer.EmitRawText(StringRef("\t.option\tpic0"));
-  }
+  getTargetStreamer().emitDirectiveAbiCalls();
+  Reloc::Model RM = Subtarget->getRelocationModel();
+  if (RM == Reloc::Static && !Subtarget->hasMips64())
+    getTargetStreamer().emitDirectiveOptionPic0();
 
   // Tell the assembler which ABI we are using
   if (OutStreamer.hasRawTextSupport())

Modified: llvm/trunk/lib/Target/Mips/MipsTargetStreamer.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/Mips/MipsTargetStreamer.h?rev=198646&r1=198645&r2=198646&view=diff
==============================================================================
--- llvm/trunk/lib/Target/Mips/MipsTargetStreamer.h (original)
+++ llvm/trunk/lib/Target/Mips/MipsTargetStreamer.h Mon Jan  6 17:27:31 2014
@@ -20,6 +20,8 @@ class MipsTargetStreamer : public MCTarg
 public:
   virtual void emitMipsHackELFFlags(unsigned Flags) = 0;
   virtual void emitMipsHackSTOCG(MCSymbol *Sym, unsigned Val) = 0;
+  virtual void emitDirectiveAbiCalls() = 0;
+  virtual void emitDirectiveOptionPic0() = 0;
 };
 
 // This part is for ascii assembly output
@@ -30,15 +32,20 @@ public:
   MipsTargetAsmStreamer(formatted_raw_ostream &OS);
   virtual void emitMipsHackELFFlags(unsigned Flags);
   virtual void emitMipsHackSTOCG(MCSymbol *Sym, unsigned Val);
+  virtual void emitDirectiveAbiCalls();
+  virtual void emitDirectiveOptionPic0();
 };
 
 // This part is for ELF object output
 class MipsTargetELFStreamer : public MipsTargetStreamer {
 public:
   MCELFStreamer &getStreamer();
+  MipsTargetELFStreamer();
+  // FIXME: emitMipsHackELFFlags() will be removed from this class.
   virtual void emitMipsHackELFFlags(unsigned Flags);
   virtual void emitMipsHackSTOCG(MCSymbol *Sym, unsigned Val);
+  virtual void emitDirectiveAbiCalls();
+  virtual void emitDirectiveOptionPic0();
 };
 }
-
 #endif

Modified: llvm/trunk/test/MC/Mips/elf_eflags.ll
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/MC/Mips/elf_eflags.ll?rev=198646&r1=198645&r2=198646&view=diff
==============================================================================
--- llvm/trunk/test/MC/Mips/elf_eflags.ll (original)
+++ llvm/trunk/test/MC/Mips/elf_eflags.ll Mon Jan  6 17:27:31 2014
@@ -29,7 +29,7 @@
 ; RUN: llc -mtriple mipsel-unknown-linux -mcpu=mips64r2 -print-hack-directives %s -o - | FileCheck -check-prefix=CHECK-BE64R2_PIC %s
 
 ; RUN: llc -mtriple mipsel-unknown-linux -mcpu=mips32r2 -mattr=+mips16 -relocation-model=pic -print-hack-directives %s -o - | FileCheck -check-prefix=CHECK-LE32R2-MIPS16 %s
- 
+
 ; 32(R1) bit with NO_REORDER and static
 ; CHECK-BE32: .mips_hack_elf_flags 0x50001005
 ;

Modified: llvm/trunk/test/MC/Mips/elf_eflags.s
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/MC/Mips/elf_eflags.s?rev=198646&r1=198645&r2=198646&view=diff
==============================================================================
--- llvm/trunk/test/MC/Mips/elf_eflags.s (original)
+++ llvm/trunk/test/MC/Mips/elf_eflags.s Mon Jan  6 17:27:31 2014
@@ -1,5 +1,12 @@
 // RUN: llvm-mc -filetype=obj -triple mipsel-unknown-linux %s -o -| llvm-readobj -h | FileCheck %s
+// The initial value will be set at 0x50001003 and
+// we will override that with the negation of 0x2 (option pic0
+// the addition of 0x4 (.abicalls)
 
-        .mips_hack_elf_flags 0x50001005
+        .mips_hack_elf_flags 0x50001003
 
 // CHECK: Flags [ (0x50001005)
+
+        .abicalls
+
+        .option pic0

Modified: llvm/trunk/test/MC/Mips/mips_directives.s
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/MC/Mips/mips_directives.s?rev=198646&r1=198645&r2=198646&view=diff
==============================================================================
--- llvm/trunk/test/MC/Mips/mips_directives.s (original)
+++ llvm/trunk/test/MC/Mips/mips_directives.s Mon Jan  6 17:27:31 2014
@@ -2,8 +2,10 @@
 #
 # CHECK:  .text
 # CHECK:  $BB0_2:
+# CHECK:  .abicalls
 $BB0_2:
   .ent directives_test
+     .abicalls
     .frame    $sp,0,$ra
     .mask     0x00000000,0
     .fmask    0x00000000,0

Added: llvm/trunk/test/MC/Mips/mips_directives_bad.s
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/MC/Mips/mips_directives_bad.s?rev=198646&view=auto
==============================================================================
--- llvm/trunk/test/MC/Mips/mips_directives_bad.s (added)
+++ llvm/trunk/test/MC/Mips/mips_directives_bad.s Mon Jan  6 17:27:31 2014
@@ -0,0 +1,49 @@
+# Error checking for malformed directives
+# RUN: not llvm-mc -triple mips-unknown-unknown %s 2>&1 | FileCheck %s
+
+    .abicalls should have no operands
+# CHECK:    :{{[0-9]+}}:{{[0-9]+}}: error: unexpected token in directive
+# CHECK-NEXT:    .abicalls should have no operands
+# CHECK-NEXT:              ^
+
+# We don't know yet how to represent a list of options
+# pic2 will eventually be legal so we will probably want
+# to change it to something silly.
+
+# Blank option operand
+    .option 
+# CHECK-NEXT:    :{{[0-9]+}}:{{[0-9]+}}: error: unexpected token in .option directive
+# CHECK-NEXT:    .option 
+# CHECK-NEXT:            ^
+
+# Numeric option operand
+    .option 2
+# CHECK-NEXT:    :{{[0-9]+}}:{{[0-9]+}}: error: unexpected token in .option directive
+# CHECK-NEXT:    .option 2
+# CHECK-NEXT:            ^
+
+# Register option operand
+    .option $2
+# CHECK-NEXT:    :{{[0-9]+}}:{{[0-9]+}}: error: unexpected token in .option directive
+# CHECK-NEXT:    .option $2
+# CHECK-NEXT:            ^
+
+    .option WithBadOption
+# CHECK-NEXT:    :{{[0-9]+}}:{{[0-9]+}}: warning: unknown option in .option directive
+# CHECK-NEXT:    .option WithBadOption
+# CHECK-NEXT:            ^
+
+    .option pic0,
+# CHECK-NEXT:    :{{[0-9]+}}:{{[0-9]+}}: error: unexpected token in .option pic0 directive
+# CHECK-NEXT:    .option pic0,
+# CHECK-NEXT:                ^
+
+    .option pic0,pic2
+# CHECK-NEXT:    :{{[0-9]+}}:{{[0-9]+}}: error: unexpected token in .option pic0 directive
+# CHECK-NEXT:    .option pic0,pic2
+# CHECK-NEXT:                ^
+
+    .option pic0 pic2
+# CHECK-NEXT:    :{{[0-9]+}}:{{[0-9]+}}: error: unexpected token in .option pic0 directive
+# CHECK-NEXT:    .option pic0 pic2
+# CHECK-NEXT:                 ^





More information about the llvm-commits mailing list