diff --git a/include/llvm/MC/MCStreamer.h b/include/llvm/MC/MCStreamer.h index e26b4116bbf..5579186ec9a 100644 --- a/include/llvm/MC/MCStreamer.h +++ b/include/llvm/MC/MCStreamer.h @@ -92,6 +92,8 @@ public: virtual void switchVendor(StringRef Vendor) = 0; virtual void emitAttribute(unsigned Attribute, unsigned Value) = 0; virtual void emitTextAttribute(unsigned Attribute, StringRef String) = 0; + virtual void emitIntTextAttribute(unsigned Attribute, unsigned IntValue, + StringRef StringValue = "") = 0; virtual void emitFPU(unsigned FPU) = 0; virtual void emitArch(unsigned Arch) = 0; virtual void finishAttributeSection() = 0; diff --git a/lib/Target/ARM/ARMAsmPrinter.cpp b/lib/Target/ARM/ARMAsmPrinter.cpp index 296bb0dcee8..a0d2b75c03f 100644 --- a/lib/Target/ARM/ARMAsmPrinter.cpp +++ b/lib/Target/ARM/ARMAsmPrinter.cpp @@ -15,7 +15,6 @@ #define DEBUG_TYPE "asm-printer" #include "ARMAsmPrinter.h" #include "ARM.h" -#include "ARMBuildAttrs.h" #include "ARMConstantPoolValue.h" #include "ARMFPUName.h" #include "ARMMachineFunctionInfo.h" @@ -23,6 +22,7 @@ #include "ARMTargetObjectFile.h" #include "InstPrinter/ARMInstPrinter.h" #include "MCTargetDesc/ARMAddressingModes.h" +#include "MCTargetDesc/ARMBuildAttrs.h" #include "MCTargetDesc/ARMMCExpr.h" #include "llvm/ADT/SetVector.h" #include "llvm/ADT/SmallString.h" diff --git a/lib/Target/ARM/AsmParser/ARMAsmParser.cpp b/lib/Target/ARM/AsmParser/ARMAsmParser.cpp index be148ca7d29..81cad168ae9 100644 --- a/lib/Target/ARM/AsmParser/ARMAsmParser.cpp +++ b/lib/Target/ARM/AsmParser/ARMAsmParser.cpp @@ -7,11 +7,11 @@ // //===----------------------------------------------------------------------===// -#include "ARMBuildAttrs.h" #include "ARMFPUName.h" #include "ARMFeatures.h" #include "llvm/MC/MCTargetAsmParser.h" #include "MCTargetDesc/ARMAddressingModes.h" +#include "MCTargetDesc/ARMBuildAttrs.h" #include "MCTargetDesc/ARMArchName.h" #include "MCTargetDesc/ARMBaseInfo.h" #include "MCTargetDesc/ARMMCExpr.h" @@ -8189,30 +8189,109 @@ bool ARMAsmParser::parseDirectiveArch(SMLoc L) { } /// parseDirectiveEabiAttr -/// ::= .eabi_attribute int, int +/// ::= .eabi_attribute int, int [, "str"] +/// ::= .eabi_attribute Tag_name, int [, "str"] bool ARMAsmParser::parseDirectiveEabiAttr(SMLoc L) { - if (Parser.getTok().isNot(AsmToken::Integer)) { - Error(L, "integer expected"); - return false; + int64_t Tag; + SMLoc TagLoc; + + TagLoc = Parser.getTok().getLoc(); + if (Parser.getTok().is(AsmToken::Identifier)) { + StringRef Name = Parser.getTok().getIdentifier(); + Tag = ARMBuildAttrs::AttrTypeFromString(Name); + if (Tag == -1) { + Error(TagLoc, "attribute name not recognised: " + Name); + Parser.eatToEndOfStatement(); + return false; + } + Parser.Lex(); + } else { + const MCExpr *AttrExpr; + + TagLoc = Parser.getTok().getLoc(); + if (Parser.parseExpression(AttrExpr)) { + Parser.eatToEndOfStatement(); + return false; + } + + const MCConstantExpr *CE = dyn_cast(AttrExpr); + if (!CE) { + Error(TagLoc, "expected numeric constant"); + Parser.eatToEndOfStatement(); + return false; + } + + Tag = CE->getValue(); } - int64_t Tag = Parser.getTok().getIntVal(); - Parser.Lex(); // eat tag integer if (Parser.getTok().isNot(AsmToken::Comma)) { - Error(L, "comma expected"); + Error(Parser.getTok().getLoc(), "comma expected"); + Parser.eatToEndOfStatement(); return false; } Parser.Lex(); // skip comma - L = Parser.getTok().getLoc(); - if (Parser.getTok().isNot(AsmToken::Integer)) { - Error(L, "integer expected"); - return false; - } - int64_t Value = Parser.getTok().getIntVal(); - Parser.Lex(); // eat value integer + StringRef StringValue = ""; + bool IsStringValue = false; - getTargetStreamer().emitAttribute(Tag, Value); + int64_t IntegerValue = 0; + bool IsIntegerValue = false; + + if (Tag == ARMBuildAttrs::CPU_raw_name || Tag == ARMBuildAttrs::CPU_name) + IsStringValue = true; + else if (Tag == ARMBuildAttrs::compatibility) { + IsStringValue = true; + IsIntegerValue = true; + } else if (Tag == ARMBuildAttrs::nodefaults || Tag < 32 || Tag % 2 == 0) + IsIntegerValue = true; + else if (Tag % 2 == 1) + IsStringValue = true; + else + llvm_unreachable("invalid tag type"); + + if (IsIntegerValue) { + const MCExpr *ValueExpr; + SMLoc ValueExprLoc = Parser.getTok().getLoc(); + if (Parser.parseExpression(ValueExpr)) { + Parser.eatToEndOfStatement(); + return false; + } + + const MCConstantExpr *CE = dyn_cast(ValueExpr); + if (!CE) { + Error(ValueExprLoc, "expected numeric constant"); + Parser.eatToEndOfStatement(); + return false; + } + + IntegerValue = CE->getValue(); + } + + if (Tag == ARMBuildAttrs::compatibility) { + if (Parser.getTok().isNot(AsmToken::Comma)) + IsStringValue = false; + else + Parser.Lex(); + } + + if (IsStringValue) { + if (Parser.getTok().isNot(AsmToken::String)) { + Error(Parser.getTok().getLoc(), "bad string constant"); + Parser.eatToEndOfStatement(); + return false; + } + + StringValue = Parser.getTok().getStringContents(); + Parser.Lex(); + } + + if (IsIntegerValue && IsStringValue) { + assert(Tag == ARMBuildAttrs::compatibility); + getTargetStreamer().emitIntTextAttribute(Tag, IntegerValue, StringValue); + } else if (IsIntegerValue) + getTargetStreamer().emitAttribute(Tag, IntegerValue); + else if (IsStringValue) + getTargetStreamer().emitTextAttribute(Tag, StringValue); return false; } diff --git a/lib/Target/ARM/MCTargetDesc/ARMBuildAttrs.cpp b/lib/Target/ARM/MCTargetDesc/ARMBuildAttrs.cpp new file mode 100644 index 00000000000..9bb5072d7dc --- /dev/null +++ b/lib/Target/ARM/MCTargetDesc/ARMBuildAttrs.cpp @@ -0,0 +1,96 @@ +//===-- ARMBuildAttrs.cpp - ARM Build Attributes --------------------------===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#include "ARMBuildAttrs.h" +#include "llvm/ADT/StringRef.h" +#include "llvm/Support/Debug.h" + +using namespace llvm; + +namespace { +const struct { + ARMBuildAttrs::AttrType Attr; + const char *TagName; +} ARMAttributeTags[] = { + { ARMBuildAttrs::File, "Tag_File" }, + { ARMBuildAttrs::Section, "Tag_Section" }, + { ARMBuildAttrs::Symbol, "Tag_Symbol" }, + { ARMBuildAttrs::CPU_raw_name, "Tag_CPU_raw_name" }, + { ARMBuildAttrs::CPU_name, "Tag_CPU_name" }, + { ARMBuildAttrs::CPU_arch, "Tag_CPU_arch" }, + { ARMBuildAttrs::CPU_arch_profile, "Tag_CPU_arch_profile" }, + { ARMBuildAttrs::ARM_ISA_use, "Tag_ARM_ISA_use" }, + { ARMBuildAttrs::THUMB_ISA_use, "Tag_THUMB_ISA_use" }, + { ARMBuildAttrs::FP_arch, "Tag_FP_arch" }, + { ARMBuildAttrs::WMMX_arch, "Tag_WMMX_arch" }, + { ARMBuildAttrs::Advanced_SIMD_arch, "Tag_Advanced_SIMD_arch" }, + { ARMBuildAttrs::PCS_config, "Tag_PCS_config" }, + { ARMBuildAttrs::ABI_PCS_R9_use, "Tag_ABI_PCS_R9_use" }, + { ARMBuildAttrs::ABI_PCS_RW_data, "Tag_ABI_PCS_RW_data" }, + { ARMBuildAttrs::ABI_PCS_RO_data, "Tag_ABI_PCS_RO_data" }, + { ARMBuildAttrs::ABI_PCS_GOT_use, "Tag_ABI_PCS_GOT_use" }, + { ARMBuildAttrs::ABI_PCS_wchar_t, "Tag_ABI_PCS_wchar_t" }, + { ARMBuildAttrs::ABI_FP_rounding, "Tag_ABI_FP_rounding" }, + { ARMBuildAttrs::ABI_FP_denormal, "Tag_ABI_FP_denormal" }, + { ARMBuildAttrs::ABI_FP_exceptions, "Tag_ABI_FP_exceptions" }, + { ARMBuildAttrs::ABI_FP_user_exceptions, "Tag_ABI_FP_user_exceptions" }, + { ARMBuildAttrs::ABI_FP_number_model, "Tag_ABI_FP_number_model" }, + { ARMBuildAttrs::ABI_align8_needed, "Tag_ABI_align8_needed" }, + { ARMBuildAttrs::ABI_align8_preserved, "Tag_ABI_align8_preserved" }, + { ARMBuildAttrs::ABI_enum_size, "Tag_ABI_enum_size" }, + { ARMBuildAttrs::ABI_HardFP_use, "Tag_ABI_HardFP_use" }, + { ARMBuildAttrs::ABI_VFP_args, "Tag_ABI_VFP_args" }, + { ARMBuildAttrs::ABI_WMMX_args, "Tag_ABI_WMMX_args" }, + { ARMBuildAttrs::ABI_optimization_goals, "Tag_ABI_optimization_goals" }, + { ARMBuildAttrs::ABI_FP_optimization_goals, "Tag_ABI_FP_optimization_goals" }, + { ARMBuildAttrs::compatibility, "Tag_compatibility" }, + { ARMBuildAttrs::CPU_unaligned_access, "Tag_CPU_unaligned_access" }, + { ARMBuildAttrs::FP_HP_extension, "Tag_FP_HP_extension" }, + { ARMBuildAttrs::ABI_FP_16bit_format, "Tag_ABI_FP_16bit_format" }, + { ARMBuildAttrs::MPextension_use, "Tag_MPextension_use" }, + { ARMBuildAttrs::DIV_use, "Tag_DIV_use" }, + { ARMBuildAttrs::nodefaults, "Tag_nodefaults" }, + { ARMBuildAttrs::also_compatible_with, "Tag_also_compatible_with" }, + { ARMBuildAttrs::T2EE_use, "Tag_T2EE_use" }, + { ARMBuildAttrs::conformance, "Tag_conformance" }, + { ARMBuildAttrs::Virtualization_use, "Tag_Virtualization_use" }, + + // Legacy Names + { ARMBuildAttrs::FP_arch, "Tag_VFP_arch" }, + { ARMBuildAttrs::ABI_align8_needed, "Tag_ABI_align_needed" }, + { ARMBuildAttrs::ABI_align8_preserved, "Tag_ABI_align_preserved" }, + { ARMBuildAttrs::FP_HP_extension, "Tag_VFP_HP_extension" }, +}; +} + +namespace llvm { +namespace ARMBuildAttrs { +StringRef AttrTypeAsString(unsigned Attr, bool HasTagPrefix) { + return AttrTypeAsString(static_cast(Attr), HasTagPrefix); +} + +StringRef AttrTypeAsString(AttrType Attr, bool HasTagPrefix) { + for (unsigned TI = 0, TE = sizeof(ARMAttributeTags) / sizeof(*ARMAttributeTags); + TI != TE; ++TI) + if (ARMAttributeTags[TI].Attr == Attr) + return ARMAttributeTags[TI].TagName + (HasTagPrefix ? 0 : 4); + return ""; +} + +int AttrTypeFromString(StringRef Tag) { + bool HasTagPrefix = Tag.startswith("Tag_"); + for (unsigned TI = 0, TE = sizeof(ARMAttributeTags) / sizeof(*ARMAttributeTags); + TI != TE; ++TI) + if (StringRef(ARMAttributeTags[TI].TagName + (HasTagPrefix ? 0 : 4)) == Tag) + return ARMAttributeTags[TI].Attr; + return -1; +} +} +} + diff --git a/lib/Target/ARM/ARMBuildAttrs.h b/lib/Target/ARM/MCTargetDesc/ARMBuildAttrs.h similarity index 96% rename from lib/Target/ARM/ARMBuildAttrs.h rename to lib/Target/ARM/MCTargetDesc/ARMBuildAttrs.h index c80659f86d8..98cfecfb71f 100644 --- a/lib/Target/ARM/ARMBuildAttrs.h +++ b/lib/Target/ARM/MCTargetDesc/ARMBuildAttrs.h @@ -16,6 +16,9 @@ #define __TARGET_ARMBUILDATTRS_H__ namespace llvm { + +class StringRef; + namespace ARMBuildAttrs { enum SpecialAttr { @@ -71,6 +74,10 @@ namespace ARMBuildAttrs { MPextension_use_old = 70 }; + StringRef AttrTypeAsString(unsigned Attr, bool HasTagPrefix = true); + StringRef AttrTypeAsString(AttrType Attr, bool HasTagPrefix = true); + int AttrTypeFromString(StringRef Tag); + // Magic numbers for .ARM.attributes enum AttrMagic { Format_Version = 0x41 diff --git a/lib/Target/ARM/MCTargetDesc/ARMELFStreamer.cpp b/lib/Target/ARM/MCTargetDesc/ARMELFStreamer.cpp index 3c0f82fd40f..1fb3beabd9a 100644 --- a/lib/Target/ARM/MCTargetDesc/ARMELFStreamer.cpp +++ b/lib/Target/ARM/MCTargetDesc/ARMELFStreamer.cpp @@ -125,6 +125,8 @@ class ARMTargetAsmStreamer : public ARMTargetStreamer { virtual void switchVendor(StringRef Vendor); virtual void emitAttribute(unsigned Attribute, unsigned Value); virtual void emitTextAttribute(unsigned Attribute, StringRef String); + virtual void emitIntTextAttribute(unsigned Attribute, unsigned IntValue, + StringRef StrinValue); virtual void emitArch(unsigned Arch); virtual void emitFPU(unsigned FPU); virtual void emitInst(uint32_t Inst, char Suffix = '\0'); @@ -182,11 +184,27 @@ void ARMTargetAsmStreamer::emitAttribute(unsigned Attribute, unsigned Value) { void ARMTargetAsmStreamer::emitTextAttribute(unsigned Attribute, StringRef String) { switch (Attribute) { - default: llvm_unreachable("Unsupported Text attribute in ASM Mode"); case ARMBuildAttrs::CPU_name: - OS << "\t.cpu\t" << String.lower() << "\n"; + OS << "\t.cpu\t" << String.lower(); + break; + default: + OS << "\t.eabi_attribute\t" << Attribute << ", \"" << String << "\""; break; } + OS << "\n"; +} +void ARMTargetAsmStreamer::emitIntTextAttribute(unsigned Attribute, + unsigned IntValue, + StringRef StringValue) { + switch (Attribute) { + default: llvm_unreachable("unsupported multi-value attribute in asm mode"); + case ARMBuildAttrs::compatibility: + OS << "\t.eabi_attribute\t" << Attribute << ", " << IntValue; + if (!StringValue.empty()) + OS << ", \"" << StringValue << "\""; + break; + } + OS << "\n"; } void ARMTargetAsmStreamer::emitArch(unsigned Arch) { OS << "\t.arch\t" << GetArchName(Arch) << "\n"; @@ -213,7 +231,8 @@ private: enum { HiddenAttribute = 0, NumericAttribute, - TextAttribute + TextAttribute, + NumericAndTextAttributes } Type; unsigned Tag; unsigned IntValue; @@ -289,6 +308,27 @@ private: Contents.push_back(Item); } + void setAttributeItems(unsigned Attribute, unsigned IntValue, + StringRef StringValue, bool OverwriteExisting) { + // Look for existing attribute item + if (AttributeItem *Item = getAttributeItem(Attribute)) { + if (!OverwriteExisting) + return; + Item->IntValue = IntValue; + Item->StringValue = StringValue; + return; + } + + // Create new attribute item + AttributeItem Item = { + AttributeItem::NumericAndTextAttributes, + Attribute, + IntValue, + StringValue + }; + Contents.push_back(Item); + } + void emitArchDefaultAttributes(); void emitFPUDefaultAttributes(); @@ -307,6 +347,8 @@ private: virtual void switchVendor(StringRef Vendor); virtual void emitAttribute(unsigned Attribute, unsigned Value); virtual void emitTextAttribute(unsigned Attribute, StringRef String); + virtual void emitIntTextAttribute(unsigned Attribute, unsigned IntValue, + StringRef StringValue); virtual void emitArch(unsigned Arch); virtual void emitFPU(unsigned FPU); virtual void emitInst(uint32_t Inst, char Suffix = '\0'); @@ -588,6 +630,12 @@ void ARMTargetELFStreamer::emitTextAttribute(unsigned Attribute, StringRef Value) { setAttributeItem(Attribute, Value, /* OverwriteExisting= */ true); } +void ARMTargetELFStreamer::emitIntTextAttribute(unsigned Attribute, + unsigned IntValue, + StringRef StringValue) { + setAttributeItems(Attribute, IntValue, StringValue, + /* OverwriteExisting= */ true); +} void ARMTargetELFStreamer::emitArch(unsigned Value) { Arch = Value; } @@ -771,6 +819,11 @@ size_t ARMTargetELFStreamer::calculateContentSize() const { Result += getULEBSize(item.Tag); Result += item.StringValue.size() + 1; // string + '\0' break; + case AttributeItem::NumericAndTextAttributes: + Result += getULEBSize(item.Tag); + Result += getULEBSize(item.IntValue); + Result += item.StringValue.size() + 1; // string + '\0'; + break; } } return Result; @@ -841,6 +894,11 @@ void ARMTargetELFStreamer::finishAttributeSection() { Streamer.EmitBytes(item.StringValue.upper()); Streamer.EmitIntValue(0, 1); // '\0' break; + case AttributeItem::NumericAndTextAttributes: + Streamer.EmitULEB128IntValue(item.IntValue); + Streamer.EmitBytes(item.StringValue.upper()); + Streamer.EmitIntValue(0, 1); // '\0' + break; } } diff --git a/lib/Target/ARM/MCTargetDesc/CMakeLists.txt b/lib/Target/ARM/MCTargetDesc/CMakeLists.txt index 162de7d21e2..a65f6ab896e 100644 --- a/lib/Target/ARM/MCTargetDesc/CMakeLists.txt +++ b/lib/Target/ARM/MCTargetDesc/CMakeLists.txt @@ -1,5 +1,6 @@ add_llvm_library(LLVMARMDesc ARMAsmBackend.cpp + ARMBuildAttrs.cpp ARMELFObjectWriter.cpp ARMELFStreamer.cpp ARMMCAsmInfo.cpp diff --git a/test/CodeGen/ARM/build-attributes-encoding.s b/test/CodeGen/ARM/build-attributes-encoding.s index 5ad51b28411..34a1ad38fb1 100644 --- a/test/CodeGen/ARM/build-attributes-encoding.s +++ b/test/CodeGen/ARM/build-attributes-encoding.s @@ -4,7 +4,7 @@ // RUN: | llvm-readobj -s -sd | FileCheck %s // Tag_CPU_name (=5) -.cpu Cortex-A8 +.cpu cortex-a8 // Tag_CPU_arch (=6) .eabi_attribute 6, 10 @@ -61,7 +61,7 @@ .eabi_attribute 110, 160 // Check that tags > 128 are encoded properly -.eabi_attribute 129, 1 +.eabi_attribute 129, "1" .eabi_attribute 250, 1 // CHECK: Section { @@ -71,15 +71,15 @@ // CHECK-NEXT: ] // CHECK-NEXT: Address: 0x0 // CHECK-NEXT: Offset: 0x34 -// CHECK-NEXT: Size: 70 +// CHECK-NEXT: Size: 71 // CHECK-NEXT: Link: 0 // CHECK-NEXT: Info: 0 // CHECK-NEXT: AddressAlignment: 1 // CHECK-NEXT: EntrySize: 0 // CHECK-NEXT: SectionData ( -// CHECK-NEXT: 0000: 41450000 00616561 62690001 3B000000 +// CHECK-NEXT: 0000: 41460000 00616561 62690001 3C000000 // CHECK-NEXT: 0010: 05434F52 5445582D 41380006 0A074108 // CHECK-NEXT: 0020: 0109020A 030C0214 01150117 01180119 // CHECK-NEXT: 0030: 011B001C 0124012A 012C0244 036EA001 -// CHECK-NEXT: 0040: 810101FA 0101 +// CHECK-NEXT: 0040: 81013100 FA0101 // CHECK-NEXT: ) diff --git a/test/MC/ARM/directive-eabi_attribute-2.s b/test/MC/ARM/directive-eabi_attribute-2.s new file mode 100644 index 00000000000..fc8dc6149a5 --- /dev/null +++ b/test/MC/ARM/directive-eabi_attribute-2.s @@ -0,0 +1,91 @@ +@ RUN: llvm-mc -triple armv7-elf -filetype asm -o - %s | FileCheck %s + + .syntax unified + .thumb + + .eabi_attribute Tag_CPU_raw_name, "Cortex-A9" +@ CHECK: .eabi_attribute 4, "Cortex-A9" + .eabi_attribute Tag_CPU_name, "cortex-a9" +@ CHECK: .cpu cortex-a9 + .eabi_attribute Tag_CPU_arch, 10 +@ CHECK: .eabi_attribute 6, 10 + .eabi_attribute Tag_CPU_arch_profile, 'A' +@ CHECK: .eabi_attribute 7, 65 + .eabi_attribute Tag_ARM_ISA_use, 0 +@ CHECK: .eabi_attribute 8, 0 + .eabi_attribute Tag_THUMB_ISA_use, 2 +@ CHECK: .eabi_attribute 9, 2 + .eabi_attribute Tag_FP_arch, 3 +@ CHECK: .eabi_attribute 10, 3 + .eabi_attribute Tag_WMMX_arch, 0 +@ CHECK: .eabi_attribute 11, 0 + .eabi_attribute Tag_Advanced_SIMD_arch, 1 +@ CHECK: .eabi_attribute 12, 1 + .eabi_attribute Tag_PCS_config, 2 +@ CHECK: .eabi_attribute 13, 2 + .eabi_attribute Tag_ABI_PCS_R9_use, 0 +@ CHECK: .eabi_attribute 14, 0 + .eabi_attribute Tag_ABI_PCS_RW_data, 0 +@ CHECK: .eabi_attribute 15, 0 + .eabi_attribute Tag_ABI_PCS_RO_data, 0 +@ CHECK: .eabi_attribute 16, 0 + .eabi_attribute Tag_ABI_PCS_GOT_use, 0 +@ CHECK: .eabi_attribute 17, 0 + .eabi_attribute Tag_ABI_PCS_wchar_t, 4 +@ CHECK: .eabi_attribute 18, 4 + .eabi_attribute Tag_ABI_FP_rounding, 1 +@ CHECK: .eabi_attribute 19, 1 + .eabi_attribute Tag_ABI_FP_denormal, 2 +@ CHECK: .eabi_attribute 20, 2 + .eabi_attribute Tag_ABI_FP_exceptions, 1 +@ CHECK: .eabi_attribute 21, 1 + .eabi_attribute Tag_ABI_FP_user_exceptions, 1 +@ CHECK: .eabi_attribute 22, 1 + .eabi_attribute Tag_ABI_FP_number_model, 3 +@ CHECK: .eabi_attribute 23, 3 + .eabi_attribute Tag_ABI_align8_needed, 1 +@ CHECK: .eabi_attribute 24, 1 + .eabi_attribute Tag_ABI_align8_preserved, 2 +@ CHECK: .eabi_attribute 25, 2 + .eabi_attribute Tag_ABI_enum_size, 3 +@ CHECK: .eabi_attribute 26, 3 + .eabi_attribute Tag_ABI_HardFP_use, 0 +@ CHECK: .eabi_attribute 27, 0 + .eabi_attribute Tag_ABI_VFP_args, 1 +@ CHECK: .eabi_attribute 28, 1 + .eabi_attribute Tag_ABI_WMMX_args, 0 +@ CHECK: .eabi_attribute 29, 0 + .eabi_attribute Tag_ABI_FP_optimization_goals, 1 +@ CHECK: .eabi_attribute 31, 1 + .eabi_attribute Tag_compatibility, 1 +@ CHECK: .eabi_attribute 32, 1 + .eabi_attribute Tag_compatibility, 1, "aeabi" +@ CHECK: .eabi_attribute 32, 1, "aeabi" + .eabi_attribute Tag_CPU_unaligned_access, 0 +@ CHECK: .eabi_attribute 34, 0 + .eabi_attribute Tag_FP_HP_extension, 0 +@ CHECK: .eabi_attribute 36, 0 + .eabi_attribute Tag_ABI_FP_16bit_format, 0 +@ CHECK: .eabi_attribute 38, 0 + .eabi_attribute Tag_MPextension_use, 0 +@ CHECK: .eabi_attribute 42, 0 + .eabi_attribute Tag_DIV_use, 0 +@ CHECK: .eabi_attribute 44, 0 + .eabi_attribute Tag_nodefaults, 0 +@ CHECK: .eabi_attribute 64, 0 + .eabi_attribute Tag_also_compatible_with, "gnu" +@ CHECK: .eabi_attribute 65, "gnu" + .eabi_attribute Tag_T2EE_use, 0 +@ CHECK: .eabi_attribute 66, 0 + .eabi_attribute Tag_conformance, "2.09" +@ CHECK: .eabi_attribute 67, "2.09" + .eabi_attribute Tag_Virtualization_use, 0 +@ CHECK: .eabi_attribute 68, 0 + +@ ===--- GNU AS Compatibility Checks ---=== + + .eabi_attribute 2 * 2 + 1, "cortex-a9" +@ CHECK: .cpu cortex-a9 + .eabi_attribute 2 * 2 + 2, 5 * 2 +@ CHECK: .eabi_attribute 6, 10 + diff --git a/test/MC/ARM/directive-eabi_attribute-diagnostics.s b/test/MC/ARM/directive-eabi_attribute-diagnostics.s new file mode 100644 index 00000000000..d1ae352b25f --- /dev/null +++ b/test/MC/ARM/directive-eabi_attribute-diagnostics.s @@ -0,0 +1,36 @@ +@ RUN: not llvm-mc -triple armv7-elf -filetype asm -o /dev/null %s 2>&1 \ +@ RUN: | FileCheck %s + + .syntax unified + .thumb + + .eabi_attribute Tag_unknown_name, 0 +@ CHECK: error: attribute name not recognised: Tag_unknown_name +@ CHECK: .eabi_attribute Tag_unknown_name +@ CHECK: ^ + + .eabi_attribute [non_constant_expression], 0 +@ CHECK: error: expected numeric constant +@ CHECK: .eabi_attribute [non_constant_expression], 0 +@ CHECK: ^ + + .eabi_attribute 42, "forty two" +@ CHECK: error: expected numeric constant +@ CHECK: .eabi_attribute 42, "forty two" +@ CHECK: ^ + + .eabi_attribute 43, 43 +@ CHECK: error: bad string constant +@ CHECK: .eabi_attribute 43, 43 +@ CHECK: ^ + + .eabi_attribute 0 +@ CHECK: error: comma expected +@ CHECK: .eabi_attribute 0 +@ CHECK: ^ + + .eabi_attribute Tag_MPextension_use_old, 0 +@ CHECK: error: attribute name not recognised: Tag_MPextension_use_old +@ CHECK: .eabi_attribute Tag_MPextension_use_old, 0 +@ CHECK: ^ +