summaryrefslogtreecommitdiff
path: root/lld/ELF/OutputSections.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'lld/ELF/OutputSections.cpp')
-rw-r--r--lld/ELF/OutputSections.cpp37
1 files changed, 24 insertions, 13 deletions
diff --git a/lld/ELF/OutputSections.cpp b/lld/ELF/OutputSections.cpp
index ea7c96eb676a..6142cb0783ce 100644
--- a/lld/ELF/OutputSections.cpp
+++ b/lld/ELF/OutputSections.cpp
@@ -20,6 +20,7 @@
#include "llvm/Support/MD5.h"
#include "llvm/Support/MathExtras.h"
#include "llvm/Support/SHA1.h"
+#include <regex>
using namespace llvm;
using namespace llvm::dwarf;
@@ -88,7 +89,7 @@ static bool canMergeToProgbits(unsigned type) {
// InputSection post finalizeInputSections(), then you must do the following:
//
// 1. Find or create an InputSectionDescription to hold InputSection.
-// 2. Add the InputSection to the InputSectionDesciption::sections.
+// 2. Add the InputSection to the InputSectionDescription::sections.
// 3. Call commitSection(isec).
void OutputSection::recordSection(InputSectionBase *isec) {
partition = isec->partition;
@@ -271,7 +272,12 @@ template <class ELFT> void OutputSection::maybeCompress() {
// Write section contents to a temporary buffer and compress it.
std::vector<uint8_t> buf(size);
writeTo<ELFT>(buf.data());
- if (Error e = zlib::compress(toStringRef(buf), compressedData))
+ // We chose 1 as the default compression level because it is the fastest. If
+ // -O2 is given, we use level 6 to compress debug info more by ~15%. We found
+ // that level 7 to 9 doesn't make much difference (~1% more compression) while
+ // they take significant amount of time (~2x), so level 6 seems enough.
+ if (Error e = zlib::compress(toStringRef(buf), compressedData,
+ config->optimize >= 2 ? 6 : 1))
fatal("compress failed: " + llvm::toString(std::move(e)));
// Update section headers.
@@ -296,7 +302,7 @@ template <class ELFT> void OutputSection::writeTo(uint8_t *buf) {
if (type == SHT_NOBITS)
return;
- // If -compress-debug-section is specified and if this is a debug seciton,
+ // If -compress-debug-section is specified and if this is a debug section,
// we've already compressed section contents. If that's the case,
// just write it down.
if (!compressedData.empty()) {
@@ -384,18 +390,23 @@ void OutputSection::finalize() {
flags |= SHF_INFO_LINK;
}
-// Returns true if S matches /Filename.?\.o$/.
-static bool isCrtBeginEnd(StringRef s, StringRef filename) {
- if (!s.endswith(".o"))
- return false;
- s = s.drop_back(2);
- if (s.endswith(filename))
- return true;
- return !s.empty() && s.drop_back().endswith(filename);
+// Returns true if S is in one of the many forms the compiler driver may pass
+// crtbegin files.
+//
+// Gcc uses any of crtbegin[<empty>|S|T].o.
+// Clang uses Gcc's plus clang_rt.crtbegin[<empty>|S|T][-<arch>|<empty>].o.
+
+static bool isCrtbegin(StringRef s) {
+ static std::regex re(R"((clang_rt\.)?crtbegin[ST]?(-.*)?\.o)");
+ s = sys::path::filename(s);
+ return std::regex_match(s.begin(), s.end(), re);
}
-static bool isCrtbegin(StringRef s) { return isCrtBeginEnd(s, "crtbegin"); }
-static bool isCrtend(StringRef s) { return isCrtBeginEnd(s, "crtend"); }
+static bool isCrtend(StringRef s) {
+ static std::regex re(R"((clang_rt\.)?crtend[ST]?(-.*)?\.o)");
+ s = sys::path::filename(s);
+ return std::regex_match(s.begin(), s.end(), re);
+}
// .ctors and .dtors are sorted by this priority from highest to lowest.
//