From 2953224d644236783d4f2487b9777803cc5e7111 Mon Sep 17 00:00:00 2001 From: Simon Atanasyan Date: Fri, 10 Mar 2017 08:22:13 +0000 Subject: [PATCH] [MC] Accept a numeric value as an ELF section header's type GAS supports specification of section header's type using a numeric value [1]. This patch brings the same functionality to LLVM. That allows to setup some target-specific section types belong to the SHT_LOPROC - SHT_HIPROC range. If we attempt to print unknown section type, MCSectionELF class shows an error message. It's better than print sole '@' sign without any section type name. In case of MIPS, example of such section's type is SHT_MIPS_DWARF. Without the patch we will have to implement some workarounds in probably not-MIPS-specific part of code base to convert SHT_MIPS_DWARF to the @progbits while printing assembly and to assign SHT_MIPS_DWARF for @progbits sections named .debug_* if we encounter such section in an input assembly. [1] https://sourceware.org/binutils/docs/as/Section.html Differential Revision: https://reviews.llvm.org/D29719 llvm-svn: 297446 --- llvm/lib/MC/MCParser/ELFAsmParser.cpp | 7 +++++-- llvm/lib/MC/MCSectionELF.cpp | 4 ++++ .../MC/ELF/section-numeric-invalid-type.s | 14 +++++++++++++ llvm/test/MC/ELF/section-numeric-type.s | 20 +++++++++++++++++++ 4 files changed, 43 insertions(+), 2 deletions(-) create mode 100644 llvm/test/MC/ELF/section-numeric-invalid-type.s create mode 100644 llvm/test/MC/ELF/section-numeric-type.s diff --git a/llvm/lib/MC/MCParser/ELFAsmParser.cpp b/llvm/lib/MC/MCParser/ELFAsmParser.cpp index fff081f04455..8838f16d60ac 100644 --- a/llvm/lib/MC/MCParser/ELFAsmParser.cpp +++ b/llvm/lib/MC/MCParser/ELFAsmParser.cpp @@ -395,7 +395,10 @@ bool ELFAsmParser::maybeParseSectionType(StringRef &TypeName) { return TokError("expected '@', '%' or \"\""); if (!L.is(AsmToken::String)) Lex(); - if (getParser().parseIdentifier(TypeName)) + if (L.is(AsmToken::Integer)) { + TypeName = getTok().getString(); + Lex(); + } else if (getParser().parseIdentifier(TypeName)) return TokError("expected identifier in directive"); return false; } @@ -580,7 +583,7 @@ EndStmt: Type = ELF::SHT_NOTE; else if (TypeName == "unwind") Type = ELF::SHT_X86_64_UNWIND; - else + else if (TypeName.getAsInteger(0, Type)) return TokError("unknown section type"); } diff --git a/llvm/lib/MC/MCSectionELF.cpp b/llvm/lib/MC/MCSectionELF.cpp index fdd9239a0f1a..c73fafe151b0 100644 --- a/llvm/lib/MC/MCSectionELF.cpp +++ b/llvm/lib/MC/MCSectionELF.cpp @@ -12,6 +12,7 @@ #include "llvm/MC/MCExpr.h" #include "llvm/MC/MCSectionELF.h" #include "llvm/Support/ELF.h" +#include "llvm/Support/ErrorHandling.h" #include "llvm/Support/raw_ostream.h" #include @@ -140,6 +141,9 @@ void MCSectionELF::PrintSwitchToSection(const MCAsmInfo &MAI, const Triple &T, OS << "progbits"; else if (Type == ELF::SHT_X86_64_UNWIND) OS << "unwind"; + else + report_fatal_error("unsupported type 0x" + Twine::utohexstr(Type) + + " for section " + getSectionName()); if (EntrySize) { assert(Flags & ELF::SHF_MERGE); diff --git a/llvm/test/MC/ELF/section-numeric-invalid-type.s b/llvm/test/MC/ELF/section-numeric-invalid-type.s new file mode 100644 index 000000000000..3ae071bc7c13 --- /dev/null +++ b/llvm/test/MC/ELF/section-numeric-invalid-type.s @@ -0,0 +1,14 @@ +// RUN: llvm-mc -filetype=obj -triple=x86_64-pc-linux-gnu %s -o - \ +// RUN: | llvm-readobj -s -t | FileCheck --check-prefix=OBJ %s + +// RUN: not llvm-mc -filetype=asm -triple=x86_64-pc-linux-gnu %s -o - 2>&1 \ +// RUN: | FileCheck --check-prefix=ASM %s + + .section .sec,"a",@0x7fffffff + +// OBJ: Section { +// OBJ: Name: .sec +// OBJ-NEXT: Type: (0x7FFFFFFF) +// OBJ: } + +// ASM: unsupported type 0x7fffffff for section .sec diff --git a/llvm/test/MC/ELF/section-numeric-type.s b/llvm/test/MC/ELF/section-numeric-type.s new file mode 100644 index 000000000000..2e51bd4eb187 --- /dev/null +++ b/llvm/test/MC/ELF/section-numeric-type.s @@ -0,0 +1,20 @@ +// RUN: llvm-mc -filetype=obj -triple=x86_64-pc-linux-gnu %s -o - \ +// RUN: | llvm-readobj -s -t | FileCheck --check-prefix=OBJ %s + +// RUN: llvm-mc -filetype=asm -triple=x86_64-pc-linux-gnu %s -o - \ +// RUN: | FileCheck --check-prefix=ASM %s + + .section .sec1,"a",@0x70000001 + .section .sec2,"a",@1879048193 + +// OBJ: Section { +// OBJ: Name: .sec1 +// OBJ-NEXT: Type: SHT_X86_64_UNWIND (0x70000001) +// OBJ: } +// OBJ: Section { +// OBJ: Name: .sec2 +// OBJ-NEXT: Type: SHT_X86_64_UNWIND (0x70000001) +// OBJ: } + +// ASM: .section .sec1,"a",@unwind +// ASM: .section .sec2,"a",@unwind -- GitLab