OSDN Git Service

PR c++/51459
authorjason <jason@138bc75d-0d04-0410-961f-82ee72b054a4>
Thu, 8 Dec 2011 22:28:29 +0000 (22:28 +0000)
committerjason <jason@138bc75d-0d04-0410-961f-82ee72b054a4>
Thu, 8 Dec 2011 22:28:29 +0000 (22:28 +0000)
* pt.c (tsubst_expr) [DECL_EXPR]: Handle capture proxies properly.
* semantics.c (insert_capture_proxy): No longer static.
* cp-tree.h: Declare it.

git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@182141 138bc75d-0d04-0410-961f-82ee72b054a4

gcc/cp/ChangeLog
gcc/cp/cp-tree.h
gcc/cp/pt.c
gcc/cp/semantics.c
gcc/testsuite/ChangeLog
gcc/testsuite/g++.dg/cpp0x/lambda/lambda-template4.C [new file with mode: 0644]

index ebb636e..70a93bd 100644 (file)
@@ -1,3 +1,10 @@
+2011-12-08  Jason Merrill  <jason@redhat.com>
+
+       PR c++/51459
+       * pt.c (tsubst_expr) [DECL_EXPR]: Handle capture proxies properly.
+       * semantics.c (insert_capture_proxy): No longer static.
+       * cp-tree.h: Declare it.
+
 2011-12-07  Jakub Jelinek  <jakub@redhat.com>
 
        PR c++/51401
index dccf485..87cb8b6 100644 (file)
@@ -5593,6 +5593,7 @@ extern void apply_lambda_return_type            (tree, tree);
 extern tree add_capture                         (tree, tree, tree, bool, bool);
 extern tree add_default_capture                 (tree, tree, tree);
 extern tree build_capture_proxy                        (tree);
+extern void insert_capture_proxy               (tree);
 extern void insert_pending_capture_proxies     (void);
 extern bool is_capture_proxy                   (tree);
 extern bool is_normal_capture_proxy             (tree);
index 7603c11..296cd54 100644 (file)
@@ -12810,6 +12810,11 @@ tsubst_expr (tree t, tree args, tsubst_flags_t complain, tree in_decl,
                    && ANON_AGGR_TYPE_P (TREE_TYPE (decl)))
                  /* Anonymous aggregates are a special case.  */
                  finish_anon_union (decl);
+               else if (is_capture_proxy (DECL_EXPR_DECL (t)))
+                 {
+                   DECL_CONTEXT (decl) = current_function_decl;
+                   insert_capture_proxy (decl);
+                 }
                else
                  {
                    int const_init = false;
index 9a1043a..2dab6a7 100644 (file)
@@ -8804,7 +8804,7 @@ is_normal_capture_proxy (tree decl)
 /* VAR is a capture proxy created by build_capture_proxy; add it to the
    current function, which is the operator() for the appropriate lambda.  */
 
-static inline void
+void
 insert_capture_proxy (tree var)
 {
   cp_binding_level *b;
index ed2428d..5c97305 100644 (file)
@@ -1,3 +1,8 @@
+2011-12-08  Jason Merrill  <jason@redhat.com>
+
+       PR c++/51459
+       * g++.dg/cpp0x/lambda/lambda-template4.C: New.
+
 2011-12-08  Jakub Jelinek  <jakub@redhat.com>
 
        PR tree-optimization/51466
diff --git a/gcc/testsuite/g++.dg/cpp0x/lambda/lambda-template4.C b/gcc/testsuite/g++.dg/cpp0x/lambda/lambda-template4.C
new file mode 100644 (file)
index 0000000..a65727a
--- /dev/null
@@ -0,0 +1,42 @@
+// PR c++/51459
+// { dg-do run { target c++11 } }
+
+struct func {
+    virtual ~func() { }
+    virtual void operator()() const = 0;
+    virtual func* clone() const = 0;
+};
+
+template<typename T>
+struct funcimpl : func {
+    explicit funcimpl(T t) : t(t) { }
+    void operator()() const { t(); }
+    func* clone() const { return new funcimpl(*this); }
+    T t;
+};
+
+struct function
+{
+    func* p;
+
+    template<typename T>
+        function(T t) : p(new funcimpl<T>(t)) { }
+
+    ~function() { delete p; }
+
+    function(const function& f) : p(f.p->clone()) { }
+
+    function& operator=(const function& ) = delete;
+
+    void operator()() const { (*p)(); }
+};
+
+template <typename F>
+function animate(F f) { return [=]{ f(); }; }
+
+int main()
+{
+  function linear1 = []{};
+  function av(animate(linear1));
+  av();
+}