summaryrefslogtreecommitdiffstats
path: root/clang/test/SemaCXX/for-range-examples.cpp
diff options
context:
space:
mode:
authorFaisal Vali <faisalv@yahoo.com>2017-05-15 01:49:19 +0000
committerFaisal Vali <faisalv@yahoo.com>2017-05-15 01:49:19 +0000
commit1ca2d9679ba3493f017e5131451b3f68a708591b (patch)
tree0964a9c0e1ff2d282499ea8d8f9bdfcba721f843 /clang/test/SemaCXX/for-range-examples.cpp
parent54392a20a2761bf45ac486c9df71fe9141d9f44b (diff)
downloadbcm5719-llvm-1ca2d9679ba3493f017e5131451b3f68a708591b.tar.gz
bcm5719-llvm-1ca2d9679ba3493f017e5131451b3f68a708591b.zip
Fix PR32933: crash on lambda capture of VLA
https://bugs.llvm.org/show_bug.cgi?id=32933 Turns out clang wasn't really handling vla's (*) in C++11's for-range entirely correctly. For e.g. This would lead to generation of buggy IR: void foo(int b) { int vla[b]; b = -1; // This store would affect the '__end = vla + b' for (int &c : vla) c = 0; } Additionally, code-gen would get confused when VLA's were reference-captured by lambdas, and then used in a for-range, which would result in an attempt to generate IR for '__end = vla + b' within the lambda's body - without any capture of 'b' - hence the assertion. This patch modifies clang, so that for VLA's it translates the end pointer approximately into: __end = __begin + sizeof(vla)/sizeof(vla->getElementType()) As opposed to the __end = __begin + b; I considered passing a magic value into codegen - or having codegen special case the '__end' variable when it referred to a variably-modified type, but I decided against that approach, because it smelled like I would be increasing a complicated form of coupling, that I think would be even harder to maintain than the above approach (which can easily be optimized (-O1) to refer to the run-time bound that was calculated upon array's creation or copied into the lambda's closure object). (*) why oh why gcc would you enable this by default?! ;) llvm-svn: 303026
Diffstat (limited to 'clang/test/SemaCXX/for-range-examples.cpp')
-rw-r--r--clang/test/SemaCXX/for-range-examples.cpp34
1 files changed, 34 insertions, 0 deletions
diff --git a/clang/test/SemaCXX/for-range-examples.cpp b/clang/test/SemaCXX/for-range-examples.cpp
index 08a9982c637..d6b527ff8a5 100644
--- a/clang/test/SemaCXX/for-range-examples.cpp
+++ b/clang/test/SemaCXX/for-range-examples.cpp
@@ -241,3 +241,37 @@ namespace pr18587 {
}
}
}
+
+namespace PR32933 {
+// https://bugs.llvm.org/show_bug.cgi?id=32933
+void foo ()
+{
+ int b = 1, a[b];
+ a[0] = 0;
+ [&] { for (int c : a) 0; } ();
+}
+
+
+int foo(int b) {
+ int varr[b][(b+=8)];
+ b = 15;
+ [&] {
+ int i = 0;
+ for (auto &c : varr)
+ {
+ c[0] = ++b;
+ }
+ [&] {
+ int i = 0;
+ for (auto &c : varr) {
+ int j = 0;
+ for(auto &c2 : c) {
+ ++j;
+ }
+ ++i;
+ }
+ }();
+ }();
+ return b;
+}
+} \ No newline at end of file
OpenPOWER on IntegriCloud