http://flic.kr/p/ohtmj Whitebox Testing
SWEBOK Knowledge Areas Software Requirements Software Design Software Construction Software Testing Software Maintenance Software Configuration Management Software Engineering Management Software Engineering Process Software Engineering Models and Methods Software Quality Software Engineering Professional Practice Software Engineering Economics Computing Foundations Mathematical Foundations Engineering Foundations Today’s topic
Recall: Common approaches for choosing test cases Blackbox testing: Choose based on module’s possible inputs and outputs Do not use code Often test boundary cases White-box testing: Uses internal logic to choose tests Different levels of code coverage Aka glass box testing, clear box testing Regression testing: Keep tests that reveal old bugs Rationale: “Fixed” bugs come back!
Criteria for choosing test cases: Coverage Measures Degree to which the source code of a program is tested by a test suite Examples: Statement coverage Condition coverage Path coverage Some examples will clarify, but first…
Control Flow Graphs – Frequently used to calculate coverage int foo(int x, int y) { int z = 0; if ((x>0) && (y>0)) { z = x; } return z; Basic blocks: straight-line pieces of code without any jumps or jump targets return z; z = x; int z = 0; if ((x>0) && (y>0)) { true false Jumps: control branches
Statement Coverage Set of test cases such that… Each program statement (line or basic block) is executed at least once
Define a test suite that provides statement coverage for this code return z; z = x; int z = 0; if ((x>0) && (y>0)) { true false Control Flow Graph int foo(int x, int y) { int z = 0; if ((x>0) && (y>0)) { z = x; } return z; ✔ ✔ input expected x y ✔ 1
Now try this code… Control Flow Graph F T T F T F public int bar(int x) { int result=0; if (x < 69) { if (x % 2 == 0) { result = x/2; } else { result = x*2; } } else if (x > 6969) { x = 69; x = 6969; return result; Control Flow Graph int result=0; result = x*2; F T x < 69 x % 2 == 0 T F result = x/2; T x > 6969 x = 69; F return result; x = 6969;
✔ ✔ ✔ ✔ ✔ ✔ ✔ ✔ ✔ Now try this code… Input (x) expected 1 2 2 1 6970 Control Flow Graph 70 6969 ✔ ✔ int result=0; result = x*2; ✔ ✔ F T x < 69 x % 2 == 0 T ✔ F result = x/2; ✔ ✔ T x > 6969 x = 69; ✔ F return result; ✔ x = 6969;
Condition Coverage Set of test cases such that… Each boolean expression (in control structures) evaluates to true at least once and to false at least once
✔ ✔ Define a test suite that provides condition coverage for this code return z; z = x; int z = 0; if ((x>0) && (y>0)) { true false Control Flow Graph int foo(int x, int y) { int z = 0; if ((x>0) && (y>0)) { z = x; } return z; ✔ ✔ input expected x y 1
Now try this code… Control Flow Graph F T T F T F public int bar(int x) { int result=0; if (x < 69) { if (x % 2 == 0) { result = x/2; } else { result = x*2; } } else if (x > 6969) { x = 69; x = 6969; return result; Control Flow Graph int result=0; result = x*2; F T x < 69 x % 2 == 0 T F result = x/2; T x > 6969 x = 69; F return result; x = 6969;
✔ ✔ ✔ ✔ ✔ ✔ Now try this code… Input (x) expected 1 2 2 1 6970 69 Control Flow Graph 70 6969 int result=0; result = x*2; ✔ ✔ F T x < 69 x % 2 == 0 ✔ T ✔ F result = x/2; ✔ T x > 6969 x = 69; ✔ F return result; x = 6969;
Path Coverage Set of test cases such that… Each possible path through a program’s control flow graph is taken at least once
✔ ✔ Define a test suite that provides path coverage for this code return z; z = x; int z = 0; if ((x>0) && (y>0)) { true false Control Flow Graph int foo(int x, int y) { int z = 0; if ((x>0) && (y>0)) { z = x; } return z; (a) (b) (c) input expected x y 1 Paths: a , b c ✔ ✔
Now try this code… Control Flow Graph F T T F T F public int bar(int x) { int result=0; if (x < 69) { if (x % 2 == 0) { result = x/2; } else { result = x*2; } } else if (x > 6969) { x = 69; x = 6969; return result; Control Flow Graph int result=0; result = x*2; F T x < 69 x % 2 == 0 T F result = x/2; T x > 6969 x = 69; F return result; x = 6969;
✔ ✔ ✔ ✔ Now try this code… Input (x) expected 1 2 2 1 6970 69 70 6969 Control Flow Graph int result=0; (a) (b) (c) (d) (f) (e) (g) (h) (i) (j) (k) result = x*2; F T x < 69 Paths: a , d , f , h a , d , g , i a , b , e , j a , b , c , k x % 2 == 0 ✔ T ✔ F result = x/2; ✔ ✔ T x > 6969 x = 69; F return result; x = 6969;
BONUS QUESTION
Draw a control flow graph Define test suites that provide: Given this code Draw a control flow graph Define test suites that provide: Statement coverage Condition coverage Path coverage int myF(int x, int y) { while (x > 10) { x = x – 10; if (x == 10) { break; } if (y < 20 && x%2 == 0) { y = y + 20; } else { y = y – 20; return 2*x + y;
Here’s the CFG F T F T F T int myF(int x, int y) { while (x > 10) { x = x – 10; if (x == 10) { break; } if (y < 20 && x%2 == 0) { y = y + 20; } else { y = y – 20; return 2*x + y; while (x > 10) F T x = x – 10; if (x == 10) F T break; if (y < 20 && x%2 == 0) F T y = y – 20; y = y + 20; Here’s the CFG return 2*x + y;