[lld] 3fe5c3b - [lld-macho] Fix use-after-free in loadDylib()
Jez Ng via llvm-commits
llvm-commits at lists.llvm.org
Fri Apr 23 15:05:59 PDT 2021
Author: Jez Ng
Date: 2021-04-23T18:05:49-04:00
New Revision: 3fe5c3b0189f51868493bbbc6768ef3afbdfb492
URL: https://github.com/llvm/llvm-project/commit/3fe5c3b0189f51868493bbbc6768ef3afbdfb492
DIFF: https://github.com/llvm/llvm-project/commit/3fe5c3b0189f51868493bbbc6768ef3afbdfb492.diff
LOG: [lld-macho] Fix use-after-free in loadDylib()
We were taking a reference to a value in `loadedDylibs`, which in turn
called `make<DylibFile>()`, which could then recursively call
`loadDylibs`, which would then potentially resize `loadedDylibs` and
invalidate that reference.
Fixes PR50101.
Reviewed By: #lld-macho, oontvoo
Differential Revision: https://reviews.llvm.org/D101175
Added:
Modified:
lld/MachO/DriverUtils.cpp
lld/MachO/InputFiles.h
Removed:
################################################################################
diff --git a/lld/MachO/DriverUtils.cpp b/lld/MachO/DriverUtils.cpp
index bbbc339c3177..e0f6a353c03e 100644
--- a/lld/MachO/DriverUtils.cpp
+++ b/lld/MachO/DriverUtils.cpp
@@ -188,8 +188,8 @@ static DenseMap<CachedHashStringRef, DylibFile *> loadedDylibs;
Optional<DylibFile *> macho::loadDylib(MemoryBufferRef mbref,
DylibFile *umbrella,
bool isBundleLoader) {
- StringRef path = mbref.getBufferIdentifier();
- DylibFile *&file = loadedDylibs[CachedHashStringRef(path)];
+ CachedHashStringRef path(mbref.getBufferIdentifier());
+ DylibFile *file = loadedDylibs[path];
if (file)
return file;
@@ -209,6 +209,11 @@ Optional<DylibFile *> macho::loadDylib(MemoryBufferRef mbref,
magic == file_magic::macho_bundle);
file = make<DylibFile>(mbref, umbrella, isBundleLoader);
}
+ // Note that DylibFile's ctor may recursively invoke loadDylib(), which can
+ // cause loadedDylibs to get resized and its iterators invalidated. As such,
+ // we redo the key lookup here instead of caching an iterator from our earlier
+ // lookup at the start of the function.
+ loadedDylibs[path] = file;
return file;
}
diff --git a/lld/MachO/InputFiles.h b/lld/MachO/InputFiles.h
index 4db93bec8611..066d4506644c 100644
--- a/lld/MachO/InputFiles.h
+++ b/lld/MachO/InputFiles.h
@@ -160,7 +160,7 @@ class DylibFile : public InputFile {
bool isBundleLoader;
private:
- template <class LP> void parse(DylibFile *umbrella = nullptr);
+ template <class LP> void parse(DylibFile *umbrella);
};
// .a file
More information about the llvm-commits
mailing list