// RUN: %clang_analyze_cc1 %s \ // RUN: -analyzer-checker=core \ // RUN: -analyzer-checker=debug.ExprInspection \ // RUN: 2>&1 | FileCheck %s // In this test we check whether the solver's symbol simplification mechanism // is capable of reaching a fixpoint. This should be done after TWO iterations. void clang_analyzer_printState(); void test(int a, int b, int c, int d) { if (a + b + c != d) return; if (c + b != 0) return; clang_analyzer_printState(); // CHECK: "constraints": [ // CHECK-NEXT: { "symbol": "(((reg_$0) + (reg_$2)) + (reg_$5)) != (reg_$8)", "range": "{ [0, 0] }" }, // CHECK-NEXT: { "symbol": "(reg_$5) + (reg_$2)", "range": "{ [0, 0] }" } // CHECK-NEXT: ], // CHECK-NEXT: "equivalence_classes": [ // CHECK-NEXT: [ "((reg_$0) + (reg_$2)) + (reg_$5)", "reg_$8" ] // CHECK-NEXT: ], // CHECK-NEXT: "disequality_info": null, // Simplification starts here. if (b != 0) return; clang_analyzer_printState(); // CHECK: "constraints": [ // CHECK-NEXT: { "symbol": "(reg_$0) != (reg_$8)", "range": "{ [0, 0] }" }, // CHECK-NEXT: { "symbol": "reg_$2", "range": "{ [0, 0] }" }, // CHECK-NEXT: { "symbol": "reg_$5", "range": "{ [0, 0] }" } // CHECK-NEXT: ], // CHECK-NEXT: "equivalence_classes": [ // CHECK-NEXT: [ "(reg_$0) != (reg_$8)" ], // CHECK-NEXT: [ "reg_$0", "reg_$8" ], // CHECK-NEXT: [ "reg_$5" ] // CHECK-NEXT: ], // CHECK-NEXT: "disequality_info": null, // Keep the symbols and the constraints! alive. (void)(a * b * c * d); return; }