aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTed Kremenek <kremenek@apple.com>2010-09-09 00:06:07 +0000
committerTed Kremenek <kremenek@apple.com>2010-09-09 00:06:07 +0000
commit90b828aa279542559f655d1af666580288cb1841 (patch)
treedd4c53a6dd2318b884756dc861b7250cf375b12c
parentee7f84d509c6382491673883598eb9ed2d3a6a8b (diff)
Enhance -Wreturn-type to not warn when control-flow is most likely limited by a switch statement explicitly covering
all the cases for an enum value. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@113450 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r--lib/Sema/AnalysisBasedWarnings.cpp14
-rw-r--r--test/Sema/return.c13
2 files changed, 22 insertions, 5 deletions
diff --git a/lib/Sema/AnalysisBasedWarnings.cpp b/lib/Sema/AnalysisBasedWarnings.cpp
index cfebed6a05..a46755bbd9 100644
--- a/lib/Sema/AnalysisBasedWarnings.cpp
+++ b/lib/Sema/AnalysisBasedWarnings.cpp
@@ -108,11 +108,15 @@ static ControlFlowKind CheckFallThrough(AnalysisContext &AC) {
bool HasFakeEdge = false;
bool HasPlainEdge = false;
bool HasAbnormalEdge = false;
- for (CFGBlock::pred_iterator I=cfg->getExit().pred_begin(),
- E = cfg->getExit().pred_end();
- I != E;
- ++I) {
- CFGBlock& B = **I;
+
+ // Ignore default cases that aren't likely to be reachable because all
+ // enums in a switch(X) have explicit case statements.
+ CFGBlock::FilterOptions FO;
+ FO.IgnoreDefaultsWithCoveredEnums = 1;
+
+ for (CFGBlock::filtered_pred_iterator
+ I = cfg->getExit().filtered_pred_start_end(FO); I.hasMore(); ++I) {
+ const CFGBlock& B = **I;
if (!live[B.getBlockID()])
continue;
if (B.size() == 0) {
diff --git a/test/Sema/return.c b/test/Sema/return.c
index 54c340634d..597b50214e 100644
--- a/test/Sema/return.c
+++ b/test/Sema/return.c
@@ -242,3 +242,16 @@ static inline int si_forward() {} // expected-warning{{control reaches end of no
// Test warnings on ignored qualifiers on return types.
const int ignored_c_quals(); // expected-warning{{'const' type qualifier on return type has no effect}}
const volatile int ignored_cv_quals(); // expected-warning{{'const volatile' type qualifiers on return type have no effect}}
+
+// Test that for switch(enum) that if the switch statement covers all the cases
+// that we don't consider that for -Wreturn-type.
+enum Cases { C1, C2, C3, C4 };
+int test_enum_cases(enum Cases C) {
+ switch (C) {
+ case C1: return 1;
+ case C2: return 2;
+ case C4: return 3;
+ case C3: return 4;
+ }
+} // no-warning
+