[llvm] r193524 - [arm] Implement eabi_attribute, cpu, and fpu directives.

Rafael EspĂ­ndola rafael.espindola at gmail.com
Mon Oct 28 11:06:44 PDT 2013


Thanks !

On Monday, October 28, 2013, Logan Chien wrote:

> Author: logan
> Date: Mon Oct 28 12:51:12 2013
> New Revision: 193524
>
> URL: http://llvm.org/viewvc/llvm-project?rev=193524&view=rev
> Log:
> [arm] Implement eabi_attribute, cpu, and fpu directives.
>
> This commit allows the ARM integrated assembler to parse
> and assemble the code with .eabi_attribute, .cpu, and
> .fpu directives.
>
> To implement the feature, this commit moves the code from
> AttrEmitter to ARMTargetStreamers, and several new test
> cases related to cortex-m4, cortex-r5, and cortex-a15 are
> added.
>
> Besides, this commit also change the Subtarget->isFPOnlySP()
> to Subtarget->hasD16() to match the usage of .fpu directive.
>
> This commit changes the test cases:
>
> * Several .eabi_attribute directives in
>   2010-09-29-mc-asm-header-test.ll are removed because the .fpu
>   directive already cover the functionality.
>
> * In the Cortex-A15 test case, the value for
>   Tag_Advanced_SIMD_arch has be changed from 1 to 2,
>   which is more precise.
>
>
> Added:
>     llvm/trunk/lib/Target/ARM/ARMFPUName.def
>     llvm/trunk/lib/Target/ARM/ARMFPUName.h
>     llvm/trunk/test/MC/ARM/directive-cpu.s
>     llvm/trunk/test/MC/ARM/directive-eabi_attribute.s
>     llvm/trunk/test/MC/ARM/directive-fpu-multiple.s
>     llvm/trunk/test/MC/ARM/directive-fpu.s
> Modified:
>     llvm/trunk/include/llvm/MC/MCStreamer.h
>     llvm/trunk/lib/Target/ARM/ARM.td
>     llvm/trunk/lib/Target/ARM/ARMAsmPrinter.cpp
>     llvm/trunk/lib/Target/ARM/ARMBuildAttrs.h
>     llvm/trunk/lib/Target/ARM/AsmParser/ARMAsmParser.cpp
>     llvm/trunk/lib/Target/ARM/MCTargetDesc/ARMELFStreamer.cpp
>     llvm/trunk/test/CodeGen/ARM/2010-09-29-mc-asm-header-test.ll
>     llvm/trunk/test/CodeGen/ARM/2010-10-19-mc-elf-objheader.ll
>
> Modified: llvm/trunk/include/llvm/MC/MCStreamer.h
> URL:
> http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/MC/MCStreamer.h?rev=193524&r1=193523&r2=193524&view=diff
>
> ==============================================================================
> --- llvm/trunk/include/llvm/MC/MCStreamer.h (original)
> +++ llvm/trunk/include/llvm/MC/MCStreamer.h Mon Oct 28 12:51:12 2013
> @@ -87,6 +87,12 @@ public:
>    virtual void emitPad(int64_t Offset) = 0;
>    virtual void emitRegSave(const SmallVectorImpl<unsigned> &RegList,
>                             bool isVector) = 0;
> +
> +  virtual void switchVendor(StringRef Vendor) = 0;
> +  virtual void emitAttribute(unsigned Attribute, unsigned Value) = 0;
> +  virtual void emitTextAttribute(unsigned Attribute, StringRef String) =
> 0;
> +  virtual void emitFPU(unsigned FPU) = 0;
> +  virtual void finishAttributeSection() = 0;
>  };
>
>  /// MCStreamer - Streaming machine code generation interface.  This
> interface
>
> Modified: llvm/trunk/lib/Target/ARM/ARM.td
> URL:
> http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/ARM/ARM.td?rev=193524&r1=193523&r2=193524&view=diff
>
> ==============================================================================
> --- llvm/trunk/lib/Target/ARM/ARM.td (original)
> +++ llvm/trunk/lib/Target/ARM/ARM.td Mon Oct 28 12:51:12 2013
> @@ -309,7 +309,7 @@ def : ProcessorModel<"cortex-r5",   Cort
>                                      [ProcR5, HasV7Ops, FeatureDB,
>                                       FeatureVFP3, FeatureDSPThumb2,
>                                       FeatureHasRAS, FeatureVFPOnlySP,
> -                                     FeatureRClass]>;
> +                                     FeatureD16, FeatureRClass]>;
>
>  // V7M Processors.
>  def : ProcNoItin<"cortex-m3",       [HasV7Ops,
> @@ -321,7 +321,8 @@ def : ProcNoItin<"cortex-m4",       [Has
>                                       FeatureThumb2, FeatureNoARM,
> FeatureDB,
>                                       FeatureHWDiv, FeatureDSPThumb2,
>                                       FeatureT2XtPk, FeatureVFP4,
> -                                     FeatureVFPOnlySP, FeatureMClass]>;
> +                                     FeatureVFPOnlySP, FeatureD16,
> +                                     FeatureMClass]>;
>
>  // Swift uArch Processors.
>  def : ProcessorModel<"swift",       SwiftModel,
>
> Modified: llvm/trunk/lib/Target/ARM/ARMAsmPrinter.cpp
> URL:
> http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/ARM/ARMAsmPrinter.cpp?rev=193524&r1=193523&r2=193524&view=diff
>
> ==============================================================================
> --- llvm/trunk/lib/Target/ARM/ARMAsmPrinter.cpp (original)
> +++ llvm/trunk/lib/Target/ARM/ARMAsmPrinter.cpp Mon Oct 28 12:51:12 2013
> @@ -17,6 +17,7 @@
>  #include "ARM.h"
>  #include "ARMBuildAttrs.h"
>  #include "ARMConstantPoolValue.h"
> +#include "ARMFPUName.h"
>  #include "ARMMachineFunctionInfo.h"
>  #include "ARMTargetMachine.h"
>  #include "ARMTargetObjectFile.h"
> @@ -55,164 +56,6 @@
>  #include <cctype>
>  using namespace llvm;
>
> -namespace {
> -
> -  // Per section and per symbol attributes are not supported.
> -  // To implement them we would need the ability to delay this emission
> -  // until the assembly file is fully parsed/generated as only then do we
> -  // know the symbol and section numbers.
> -  class AttributeEmitter {
> -  public:
> -    virtual void MaybeSwitchVendor(StringRef Vendor) = 0;
> -    virtual void EmitAttribute(unsigned Attribute, unsigned Value) = 0;
> -    virtual void EmitTextAttribute(unsigned Attribute, StringRef String)
> = 0;
> -    virtual void Finish() = 0;
> -    virtual ~AttributeEmitter() {}
> -  };
> -
> -  class AsmAttributeEmitter : public AttributeEmitter {
> -    MCStreamer &Streamer;
> -
> -  public:
> -    AsmAttributeEmitter(MCStreamer &Streamer_) : Streamer(Streamer_) {}
> -    void MaybeSwitchVendor(StringRef Vendor) { }
> -
> -    void EmitAttribute(unsigned Attribute, unsigned Value) {
> -      Streamer.EmitRawText("\t.eabi_attribute " +
> -                           Twine(Attribute) + ", " + Twine(Value));
> -    }
> -
> -    void EmitTextAttribute(unsigned Attribute, StringRef String) {
> -      switch (Attribute) {
> -      default: llvm_unreachable("Unsupported Text attribute in ASM Mode");
> -      case ARMBuildAttrs::CPU_name:
> -        Streamer.EmitRawText(StringRef("\t.cpu ") + String.lower());
> -        break;
> -      /* GAS requires .fpu to be emitted regardless of EABI attribute */
> -      case ARMBuildAttrs::Advanced_SIMD_arch:
> -      case ARMBuildAttrs::VFP_arch:
> -        Streamer.EmitRawText(StringRef("\t.fpu ") + String.lower());
> -        break;
> -      }
> -    }
> -    void Finish() { }
> -  };
> -
> -  class ObjectAttributeEmitter : public AttributeEmitter {
> -    // This structure holds all attributes, accounting for
> -    // their string/numeric value, so we can later emmit them
> -    // in declaration order, keeping all in the same vector
> -    struct AttributeItemType {
> -      enum {
> -        HiddenAttribute = 0,
> -        NumericAttribute,
> -        TextAttribute
> -      } Type;
> -      unsigned Tag;
> -      unsigned IntValue;
> -      StringRef StringValue;
> -    };
> -
> -    MCObjectStreamer &Streamer;
> -    StringRef CurrentVendor;
> -    SmallVector<AttributeItemType, 64> Contents;
> -
> -    // Account for the ULEB/String size of each item,
> -    // not just the number of items
> -    size_t ContentsSize;
> -    // FIXME: this should be in a more generic place, but
> -    // getULEBSize() is in MCAsmInfo and will be moved to MCDwarf
> -    size_t getULEBSize(int Value) {
> -      size_t Size = 0;
> -      do {
> -        Value >>= 7;
> -        Size += sizeof(int8_t); // Is this really necessary?
> -      } while (Value);
> -      return Size;
> -    }
> -
> -  public:
> -    ObjectAttributeEmitter(MCObjectStreamer &Streamer_) :
> -      Streamer(Streamer_), CurrentVendor(""), ContentsSize(0) { }
> -
> -    void MaybeSwitchVendor(StringRef Vendor) {
> -      assert(!Vendor.empty() && "Vendor cannot be empty.");
> -
> -      if (CurrentVendor.empty())
> -        CurrentVendor = Vendor;
> -      else if (CurrentVendor == Vendor)
> -        return;
> -      else
> -        Finish();
> -
> -      CurrentVendor = Vendor;
> -
> -      assert(Contents.size() == 0);
> -    }
> -
> -    void EmitAttribute(unsigned Attribute, unsigned Value) {
> -      AttributeItemType attr = {
> -        AttributeItemType::NumericAttribute,
> -        Attribute,
> -        Value,
> -        StringRef("")
> -      };
> -      ContentsSize += getULEBSize(Attribute);
> -      ContentsSize += getULEBSize(Value);
> -      Contents.push_back(attr);
> -    }
> -
> -    void EmitTextAttribute(unsigned Attribute, StringRef String) {
> -      AttributeItemType attr = {
> -        AttributeItemType::TextAttribute,
> -        Attribute,
> -        0,
> -        String
> -      };
> -      ContentsSize += getULEBSize(Attribute);
> -      // String + \0
> -      ContentsSize += String.size()+1;
> -
> -      Contents.push_back(attr);
> -    }
> -
> -    void Finish() {
> -      // Vendor size + Vendor name + '\0'
> -      const size_t VendorHeaderSize = 4 + CurrentVendor.size() + 1;
> -
> -      // Tag + Tag Size
> -      const size_t TagHeaderSize = 1 + 4;
> -
> -      Streamer.EmitIntValue(VendorHeaderSize + TagHeaderSize +
> ContentsSize, 4);
> -      Streamer.EmitBytes(CurrentVendor);
> -      Streamer.EmitIntValue(0, 1); // '\0'
> -
> -      Streamer.EmitIntValue(ARMBuildAttrs::File, 1);
> -      Streamer.EmitIntValue(TagHeaderSize + ContentsSize, 4);
> -
> -      // Size should have been accounted for already, now
> -      // emit each field as its type (ULEB or String)
> -      for (unsigned int i=0; i<Contents.size(); ++i) {
> -        AttributeItemType item = Contents[i];
> -        Streamer.EmitULEB128IntValue(item.Tag);
> -        switch (item.Type) {
> -        default: llvm_unreachable("Invalid attribute type");
> -        case AttributeItemType::NumericAttribute:
> -          Streamer.EmitULEB128IntValue(item.IntValue);
> -          break;
> -        case AttributeItemType::TextAttribute:
> -          Streamer.EmitBytes(item.StringValue.upper());
> -          Streamer.EmitIntValue(0, 1); // '\0'
> -          break;
> -        }
> -      }
> -
> -      Contents.clear();
> -    }
> -  };
> -
> -} // end of anonymous namespace
> -
>  /// EmitDwarfRegOp - Emit dwarf register operation.
>  void ARMAsmPrinter::EmitDwarfRegOp(const MachineLocation &MLoc,
>                                     bool Indirect) const {
> @@ -768,149 +611,102 @@ static ARMBuildAttrs::CPUArch getArchFor
>  }
>
>  void ARMAsmPrinter::emitAttributes() {
> +  MCTargetStreamer &TS = OutStreamer.getTargetStreamer();
> +  ARMTargetStreamer &ATS = static_cast<ARMTargetStreamer &>(TS);
>
> -  emitARMAttributeSection();
> -
> -  /* GAS expect .fpu to be emitted, regardless of VFP build attribute */
> -  bool emitFPU = false;
> -  AttributeEmitter *AttrEmitter;
> -  if (OutStreamer.hasRawTextSupport()) {
> -    AttrEmitter = new AsmAttributeEmitter(OutStreamer);
> -    emitFPU = true;
> -  } else {
> -    MCObjectStreamer &O = static_cast<MCObjectStreamer&>(OutStreamer);
> -    AttrEmitter = new ObjectAttributeEmitter(O);
> -  }
> -
> -  AttrEmitter->MaybeSwitchVendor("aeabi");
> +  ATS.switchVendor("aeabi");
>
>    std::string CPUString = Subtarget->getCPUString();
>
>    if (CPUString != "generic")
> -    AttrEmitter->EmitTextAttribute(ARMBuildAttrs::CPU_name, CPUString);
> +    ATS.emitTextAttribute(ARMBuildAttrs::CPU_name, CPUString);
>
> -  AttrEmitter->EmitAttribute(ARMBuildAttrs::CPU_arch,
> -                             getArchForCPU(CPUString, Subtarget));
> +  ATS.emitAttribute(ARMBuildAttrs::CPU_arch,
> +                    getArchForCPU(CPUString, Subtarget));
>
>    if (Subtarget->isAClass()) {
> -    AttrEmitter->EmitAttribute(ARMBuildAttrs::CPU_arch_profile,
> -                               ARMBuildAttrs::ApplicationProfile);
> +    ATS.emitAttribute(ARMBuildAttrs::CPU_arch_profile,
> +                      ARMBuildAttrs::ApplicationProfile);
>    } else if (Subtarget->isRClass()) {
> -    AttrEmitter->EmitAttribute(ARMBuildAttrs::CPU_arch_profile,
> -                               ARMBuildAttrs::RealTimeProfile);
> +    ATS.emitAttribute(ARMBuildAttrs::CPU_arch_profile,
> +                      ARMBuildAttrs::RealTimeProfile);
>    } else if (Subtarget->isMClass()){
> -    AttrEmitter->EmitAttribute(ARMBuildAttrs::CPU_arch_profile,
> -                               ARMBuildAttrs::MicroControllerProfile);
> +    ATS.emitAttribute(ARMBuildAttrs::CPU_arch_profile,
> +                      ARMBuildAttrs::MicroControllerProfile);
>    }
>
> -  AttrEmitter->EmitAttribute(ARMBuildAttrs::ARM_ISA_use,
> Subtarget->hasARMOps() ?
> -                           ARMBuildAttrs::Allowed :
> ARMBuildAttrs::Not_Allowed);
> +  ATS.emitAttribute(ARMBuildAttrs::ARM_ISA_use, Subtarget->hasARMOps() ?
> +                      ARMBuildAttrs::Allowed :
> ARMBuildAttrs::Not_Allowed);
>    if (Subtarget->isThumb1Only()) {
> -    AttrEmitter->EmitAttribute(ARMBuildAttrs::THUMB_ISA_use,
> -                               ARMBuildAttrs::Allowed);
> +    ATS.emitAttribute(ARMBuildAttrs::
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20131028/beb2d4b7/attachment.html>


More information about the llvm-commits mailing list