[PATCH] AST: Mangle reference temporaries reliably

Richard Smith richard at metafoo.co.uk
Wed Apr 30 19:02:12 PDT 2014


================
Comment at: include/clang/Sema/Initialization.h:424
@@ -420,1 +423,3 @@
 
+  unsigned &getManglingNumber() const { return ManglingNumber; }
+
----------------
Maybe make this allocate a mangling number and return it, rather than returning a reference to the member?

================
Comment at: lib/Sema/SemaInit.cpp:5381
@@ -5381,1 +5380,3 @@
+static void performLifetimeExtension(Expr *Init, const ValueDecl *ExtendingD,
+                                     unsigned &ManglingNumber);
 
----------------
Maybe pass the `ExtendingEntity *` into here instead of its decl and a reference to its mangling number?

================
Comment at: lib/Sema/SemaInit.cpp:5791-5808
@@ -5780,13 +5790,20 @@
       // entity's lifetime.
-      const ValueDecl *ExtendingDecl =
-          getDeclForTemporaryLifetimeExtension(Entity);
-      if (ExtendingDecl) {
-        performLifetimeExtension(CurInit.get(), ExtendingDecl);
+      const InitializedEntity *ExtendingEntity =
+          getEntityForTemporaryLifetimeExtension(&Entity);
+      if (ExtendingEntity) {
+        unsigned &ExtendingEntityManglingNumber =
+            ExtendingEntity->getManglingNumber();
+        ManglingNumber = ExtendingEntityManglingNumber++;
+
+        ExtendingDecl = ExtendingEntity->getDecl();
+        performLifetimeExtension(CurInit.get(), ExtendingDecl,
+                                 ExtendingEntityManglingNumber);
         warnOnLifetimeExtension(S, Entity, CurInit.get(), false, ExtendingDecl);
       }
 
       // Materialize the temporary into memory.
       MaterializeTemporaryExpr *MTE = new (S.Context) MaterializeTemporaryExpr(
           Entity.getType().getNonReferenceType(), CurInit.get(),
-          Entity.getType()->isLValueReferenceType(), ExtendingDecl);
+          Entity.getType()->isLValueReferenceType(), ExtendingDecl,
+          ManglingNumber);
 
----------------
You could reorder these to first create the `MTE` and then `performReferenceExtension` on it, and avoid the special-casing of the `ManglingNumber` here:

    auto *MTE = new (S.Context) MaterializeTemporaryExpr(... /*no extending decl or mangling number*/ ...);
    if (auto *ExtendingEntity = getEntityForTemporaryLifetimeExtension(&Entity)) {
      performReferenceExtension(MTE, ExtendingEntity);
      warnOnLifetimeExtension(...);
    }

================
Comment at: lib/Sema/SemaInit.cpp:6196-6218
@@ -6178,15 +6195,25 @@
 
+      unsigned ManglingNumber = 1;
+      const ValueDecl *ExtendingDecl = nullptr;
+
       // Maybe lifetime-extend the array temporary's subobjects to match the
       // entity's lifetime.
-      const ValueDecl *ExtendingDecl =
-          getDeclForTemporaryLifetimeExtension(Entity);
-      if (ExtendingDecl) {
-        performLifetimeExtension(CurInit.get(), ExtendingDecl);
+      const InitializedEntity *ExtendingEntity =
+          getEntityForTemporaryLifetimeExtension(&Entity);
+      if (ExtendingEntity) {
+        unsigned &ExtendingEntityManglingNumber =
+            ExtendingEntity->getManglingNumber();
+        ManglingNumber = ExtendingEntityManglingNumber++;
+
+        ExtendingDecl = ExtendingEntity->getDecl();
+        performLifetimeExtension(CurInit.get(), ExtendingDecl,
+                                 ExtendingEntityManglingNumber);
         warnOnLifetimeExtension(S, Entity, CurInit.get(), true, ExtendingDecl);
       }
 
       // Materialize the temporary into memory.
       MaterializeTemporaryExpr *MTE = new (S.Context)
           MaterializeTemporaryExpr(CurInit.get()->getType(), CurInit.get(),
-                                   /*lvalue reference*/ false, ExtendingDecl);
+                                   /*BoundToLvalueReference=*/false,
+                                   ExtendingDecl, ManglingNumber);
 
----------------
Likewise here.

http://reviews.llvm.org/D3554






More information about the cfe-commits mailing list