Skip to content

Commit af37697

Browse files
committed
[Clang importer] Fix the use-after-free with enum info harder.
This is more of rdar://problem/24869070; StringRefs are leaking out of importFullName still, in a DenseMap that can get deallocated. When we cache this data, put them in "permanent" (Swift ASTContext) storage.
1 parent da60535 commit af37697

File tree

3 files changed

+11
-8
lines changed

3 files changed

+11
-8
lines changed

lib/ClangImporter/ImportEnumInfo.cpp

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -167,7 +167,8 @@ static StringRef getCommonPluralPrefix(StringRef singular, StringRef plural) {
167167

168168
/// Determine the prefix to be stripped from the names of the enum constants
169169
/// within the given enum.
170-
void EnumInfo::determineConstantNamePrefix(const clang::EnumDecl *decl) {
170+
void EnumInfo::determineConstantNamePrefix(ASTContext &ctx,
171+
const clang::EnumDecl *decl) {
171172
switch (getKind()) {
172173
case EnumKind::Enum:
173174
case EnumKind::Options:
@@ -281,5 +282,5 @@ void EnumInfo::determineConstantNamePrefix(const clang::EnumDecl *decl) {
281282
commonPrefix = commonPrefix.slice(0, commonWithEnum.size() + delta);
282283
}
283284

284-
constantNamePrefix = commonPrefix;
285+
constantNamePrefix = ctx.AllocateCopy(commonPrefix);
285286
}

lib/ClangImporter/ImportEnumInfo.h

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@
1717
#ifndef SWIFT_CLANG_IMPORT_ENUM_H
1818
#define SWIFT_CLANG_IMPORT_ENUM_H
1919

20+
#include "swift/AST/ASTContext.h"
2021
#include "swift/AST/Decl.h"
2122
#include "clang/AST/Attr.h"
2223
#include "clang/Basic/SourceLocation.h"
@@ -60,7 +61,7 @@ class EnumInfo {
6061

6162
/// The enum's common constant name prefix, which will be stripped from
6263
/// constants
63-
std::string constantNamePrefix = StringRef();
64+
StringRef constantNamePrefix = StringRef();
6465

6566
/// The identifying attribute for specially imported enums
6667
///
@@ -71,9 +72,10 @@ class EnumInfo {
7172
public:
7273
EnumInfo() = default;
7374

74-
EnumInfo(const clang::EnumDecl *decl, clang::Preprocessor &pp) {
75+
EnumInfo(ASTContext &ctx, const clang::EnumDecl *decl,
76+
clang::Preprocessor &pp) {
7577
classifyEnum(decl, pp);
76-
determineConstantNamePrefix(decl);
78+
determineConstantNamePrefix(ctx, decl);
7779
}
7880

7981
EnumKind getKind() const { return kind; }
@@ -92,7 +94,7 @@ class EnumInfo {
9294
}
9395

9496
private:
95-
void determineConstantNamePrefix(const clang::EnumDecl *);
97+
void determineConstantNamePrefix(ASTContext &ctx, const clang::EnumDecl *);
9698
void classifyEnum(const clang::EnumDecl *, clang::Preprocessor &);
9799
};
98100
}

lib/ClangImporter/ImporterImpl.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -497,15 +497,15 @@ class LLVM_LIBRARY_VISIBILITY ClangImporter::Implementation
497497
// If there is no name for linkage, the computation is trivial and we
498498
// wouldn't be able to perform name-based caching anyway.
499499
if (!decl->hasNameForLinkage())
500-
return importer::EnumInfo(decl, preprocessor);
500+
return importer::EnumInfo(SwiftContext, decl, preprocessor);
501501

502502
SmallString<32> keyScratch;
503503
auto key = getEnumInfoKey(decl, keyScratch);
504504
auto known = enumInfos.find(key);
505505
if (known != enumInfos.end())
506506
return known->second;
507507

508-
importer::EnumInfo enumInfo(decl, preprocessor);
508+
importer::EnumInfo enumInfo(SwiftContext, decl, preprocessor);
509509
enumInfos[key] = enumInfo;
510510
return enumInfo;
511511
}

0 commit comments

Comments
 (0)