From 896353d6638cf4c3eb6c00e29f0b9139ebbcd441 Mon Sep 17 00:00:00 2001 From: Benjamin Kramer Date: Tue, 23 Jun 2015 15:28:10 +0000 Subject: [PATCH] [Option] Plug a leak when move-assigning an InputArgList. The class has a non-trivial dtor so we have to clean up before we move in new members. Remove misleading comment as a default move assignment operator will never be synthesized for this class. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@240417 91177308-0d34-0410-b5e6-96231b3b80d8 --- include/llvm/Option/ArgList.h | 8 +++++--- lib/Option/ArgList.cpp | 12 ++++++------ 2 files changed, 11 insertions(+), 9 deletions(-) diff --git a/include/llvm/Option/ArgList.h b/include/llvm/Option/ArgList.h index e29cf24661a..ef4005761b7 100644 --- a/include/llvm/Option/ArgList.h +++ b/include/llvm/Option/ArgList.h @@ -325,22 +325,24 @@ private: /// The number of original input argument strings. unsigned NumInputArgStrings; + /// Release allocated arguments. + void releaseMemory(); + public: InputArgList(const char* const *ArgBegin, const char* const *ArgEnd); - // Default move operations implemented for the convenience of MSVC. Nothing - // special here. InputArgList(InputArgList &&RHS) : ArgList(std::move(RHS)), ArgStrings(std::move(RHS.ArgStrings)), SynthesizedStrings(std::move(RHS.SynthesizedStrings)), NumInputArgStrings(RHS.NumInputArgStrings) {} InputArgList &operator=(InputArgList &&RHS) { + releaseMemory(); ArgList::operator=(std::move(RHS)); ArgStrings = std::move(RHS.ArgStrings); SynthesizedStrings = std::move(RHS.SynthesizedStrings); NumInputArgStrings = RHS.NumInputArgStrings; return *this; } - ~InputArgList(); + ~InputArgList() { releaseMemory(); } const char *getArgString(unsigned Index) const override { return ArgStrings[Index]; diff --git a/lib/Option/ArgList.cpp b/lib/Option/ArgList.cpp index e29b62f74dc..a74ead6b358 100644 --- a/lib/Option/ArgList.cpp +++ b/lib/Option/ArgList.cpp @@ -315,18 +315,18 @@ const char *ArgList::GetOrMakeJoinedArgString(unsigned Index, // +void InputArgList::releaseMemory() { + // An InputArgList always owns its arguments. + for (Arg *A : *this) + delete A; +} + InputArgList::InputArgList(const char* const *ArgBegin, const char* const *ArgEnd) : NumInputArgStrings(ArgEnd - ArgBegin) { ArgStrings.append(ArgBegin, ArgEnd); } -InputArgList::~InputArgList() { - // An InputArgList always owns its arguments. - for (iterator it = begin(), ie = end(); it != ie; ++it) - delete *it; -} - unsigned InputArgList::MakeIndex(StringRef String0) const { unsigned Index = ArgStrings.size();