diff options
author | Richard Smith <richard-llvm@metafoo.co.uk> | 2012-03-10 00:28:11 +0000 |
---|---|---|
committer | Richard Smith <richard-llvm@metafoo.co.uk> | 2012-03-10 00:28:11 +0000 |
commit | 0069b84c2aa7cc39263e85997b7cb1ed0b132ccd (patch) | |
tree | 0a1829e841beb468d9a25fc474a8b9b5b662be56 /lib/AST/ExprConstant.cpp | |
parent | 97c1fd651c24638a4989b4e1f8eb2e629c2073d1 (diff) |
Assign APValues by swapping from a temporary. Removes a bunch of unnecessary
copy-construction, which Daniel Dunbar reports as giving a 0.75% speedup on
403.gcc/combine.c. The performance differences on my constexpr torture tests
are below the noise floor.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@152455 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/AST/ExprConstant.cpp')
-rw-r--r-- | lib/AST/ExprConstant.cpp | 10 |
1 files changed, 8 insertions, 2 deletions
diff --git a/lib/AST/ExprConstant.cpp b/lib/AST/ExprConstant.cpp index 5f9b0501b2..97c906c407 100644 --- a/lib/AST/ExprConstant.cpp +++ b/lib/AST/ExprConstant.cpp @@ -1518,7 +1518,7 @@ static bool ExtractSubobject(EvalInfo &Info, const Expr *E, // This object might be initialized later. return false; - const APValue *O = &Obj; + APValue *O = &Obj; // Walk the designator's path to find the subobject. for (unsigned I = 0, N = Sub.Entries.size(); I != N; ++I) { if (ObjType->isArrayType()) { @@ -1616,7 +1616,13 @@ static bool ExtractSubobject(EvalInfo &Info, const Expr *E, } } - Obj = APValue(*O); + // This may look super-stupid, but it serves an important purpose: if we just + // swapped Obj and *O, we'd create an object which had itself as a subobject. + // To avoid the leak, we ensure that Tmp ends up owning the original complete + // object, which is destroyed by Tmp's destructor. + APValue Tmp; + O->swap(Tmp); + Obj.swap(Tmp); return true; } |