Skip to content

Commit 15d3bf1

Browse files
committed
SILOptimizer: avoid use-after-free with the name
On Windows at least, the std::string associated with the name of the property would be copy constructed before being passed to the diagnostic engine. The resultant DiagnosticArgument in the InFlightDiagnostic would hold a StringRef to the copy-constructed std::string. However, because the arguments are inalloca'ed on Windows, the copy constructed string would be destructed before the return of the argument. Fortunately, this would result in the standard library overwriting the string and the use-after-free would fail to print the argument. Explicitly construct the StringRef before passing the name to the diagnostic to avoid the use-after-free.
1 parent 6afe77a commit 15d3bf1

File tree

1 file changed

+5
-4
lines changed

1 file changed

+5
-4
lines changed

lib/SILOptimizer/Mandatory/DefiniteInitialization.cpp

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -650,7 +650,8 @@ void LifetimeChecker::noteUninitializedMembers(const DIMemoryUse &Use) {
650650
if (Decl && !Decl->isImplicit())
651651
Loc = SILLocation(Decl);
652652

653-
diagnose(Module, Loc, diag::stored_property_not_initialized, Name);
653+
diagnose(Module, Loc, diag::stored_property_not_initialized,
654+
StringRef(Name));
654655
}
655656
}
656657

@@ -707,7 +708,7 @@ void LifetimeChecker::diagnoseInitError(const DIMemoryUse &Use,
707708
for (unsigned i = 0, e = Use.NumElements; i != e; ++i)
708709
isLet &= TheMemory.isElementLetProperty(i);
709710

710-
diagnose(Module, DiagLoc, DiagMessage, Name, isLet);
711+
diagnose(Module, DiagLoc, DiagMessage, StringRef(Name), isLet);
711712

712713
// As a debugging hack, print the instruction itself if there is no location
713714
// information. This should never happen.
@@ -1164,10 +1165,10 @@ void LifetimeChecker::handleInOutUse(const DIMemoryUse &Use) {
11641165
FD->getName(), /*method*/ 0, PropertyName);
11651166
} else if (isAssignment) {
11661167
diagnose(Module, Use.Inst->getLoc(),
1167-
diag::assignment_to_immutable_value, PropertyName);
1168+
diag::assignment_to_immutable_value, StringRef(PropertyName));
11681169
} else {
11691170
diagnose(Module, Use.Inst->getLoc(),
1170-
diag::immutable_value_passed_inout, PropertyName);
1171+
diag::immutable_value_passed_inout, StringRef(PropertyName));
11711172
}
11721173

11731174
if (auto *Var = dyn_cast<VarDecl>(VD)) {

0 commit comments

Comments
 (0)