 |
|
 |
|
| Files: |
1 |
|
Branches Taken: |
37.3% |
19 / 51 |
| Generated: |
2009-05-17 22:47 |
|
Branches Executed: |
100.0% |
51 / 51 |
| |
|
Line Coverage: |
49.1% |
28 / 57 |
| |
 |
|
 |
1 : /* -*- mode: c++; c-basic-offset: 2; -*- */
2 :
3 : #include "Executor.h"
4 :
5 : #include "klee/Expr.h"
6 : #include "klee/Interpreter.h"
7 : #include "klee/Machine.h"
8 : #include "klee/Solver.h"
9 :
10 : #include "klee/Internal/Module/KModule.h"
11 :
12 : #include "llvm/Constants.h"
13 : #include "llvm/Function.h"
14 : #include "llvm/Instructions.h"
15 : #include "llvm/Module.h"
16 : #include "llvm/ModuleProvider.h"
17 : #include "llvm/Support/CallSite.h"
18 : #include "llvm/Support/GetElementPtrTypeIterator.h"
19 : #include "llvm/Support/Streams.h"
20 : #include "llvm/Target/TargetData.h"
21 : #include <iostream>
22 : #include <cassert>
23 :
24 : using namespace klee;
25 : using namespace llvm;
26 :
27 : namespace klee {
28 :
29 : ref<Expr>
30 16967: Executor::evalConstantExpr(llvm::ConstantExpr *ce, MemoryObject **referent) {
31 33934: const llvm::Type *type = ce->getType();
32 :
33 : ref<Expr> op1(0,Expr::Bool), op2(0,Expr::Bool), op3(0,Expr::Bool);
34 16967: int numOperands = ce->getNumOperands();
35 :
16967: branch 0 taken
0: branch 1 not taken
36 16967: if(!referent) {
16967: branch 0 taken
0: branch 1 not taken
37 16967: if (numOperands > 0) op1 = evalConstant(ce->getOperand(0));
4888: branch 0 taken
12079: branch 1 taken
38 16967: if (numOperands > 1) op2 = evalConstant(ce->getOperand(1));
4882: branch 0 taken
12085: branch 1 taken
39 16967: if (numOperands > 2) op3 = evalConstant(ce->getOperand(2));
40 : } else {
41 : #ifdef KLEE_TRACK_REFERENTS
42 : MemoryObject *op1Ref = 0, *op2Ref = 0, *op3Ref = 0;
43 : if (numOperands > 0) op1 = evalConstant(ce->getOperand(0), &op1Ref);
44 : if (numOperands > 1) op2 = evalConstant(ce->getOperand(1), &op2Ref);
45 : if (numOperands > 2) op3 = evalConstant(ce->getOperand(2), &op3Ref);
46 : switch(ce->getOpcode()) {
47 : case Instruction::Add:
48 : case Instruction::Sub:
49 : *referent = selectReferent(op1Ref, op2Ref);
50 : break;
51 : case Instruction::BitCast:
52 : case Instruction::IntToPtr:
53 : case Instruction::PtrToInt:
54 : case Instruction::GetElementPtr:
55 : *referent = op1Ref;
56 : break;
57 : case Instruction::Select:
58 : *referent = selectReferent(op2Ref, op3Ref);
59 : break;
60 : default:
61 : break;
62 : }
63 : #else
64 0: assert(0 && "Should not be tracking!");
65 : #endif
66 : }
67 :
0: branch 0 not taken
0: branch 1 not taken
0: branch 2 not taken
4: branch 3 taken
0: branch 4 not taken
0: branch 5 not taken
0: branch 6 not taken
0: branch 7 not taken
0: branch 8 not taken
0: branch 9 not taken
0: branch 10 not taken
0: branch 11 not taken
0: branch 12 not taken
0: branch 13 not taken
0: branch 14 not taken
0: branch 15 not taken
12066: branch 16 taken
5: branch 17 taken
8: branch 18 taken
4882: branch 19 taken
2: branch 20 taken
0: branch 21 not taken
0: branch 22 not taken
0: branch 23 not taken
68 16967: switch (ce->getOpcode()) {
69 : case Instruction::Trunc: return ExtractExpr::createByteOff(op1,
70 : 0,
71 0: Expr::getWidthForLLVMType(type));
72 : case Instruction::ZExt: return ZExtExpr::create(op1,
73 0: Expr::getWidthForLLVMType(type));
74 : case Instruction::SExt: return SExtExpr::create(op1,
75 0: Expr::getWidthForLLVMType(type));
76 4: case Instruction::Add: return AddExpr::create(op1, op2);
77 0: case Instruction::Sub: return SubExpr::create(op1, op2);
78 0: case Instruction::Mul: return MulExpr::create(op1, op2);
79 0: case Instruction::SDiv: return SDivExpr::create(op1, op2);
80 0: case Instruction::UDiv: return UDivExpr::create(op1, op2);
81 0: case Instruction::SRem: return SRemExpr::create(op1, op2);
82 0: case Instruction::URem: return URemExpr::create(op1, op2);
83 0: case Instruction::And: return AndExpr::create(op1, op2);
84 0: case Instruction::Or: return OrExpr::create(op1, op2);
85 0: case Instruction::Xor: return XorExpr::create(op1, op2);
86 0: case Instruction::Shl: return ShlExpr::create(op1, op2);
87 0: case Instruction::LShr: return LShrExpr::create(op1, op2);
88 0: case Instruction::AShr: return AShrExpr::create(op1, op2);
89 12066: case Instruction::BitCast: return op1;
90 :
91 : case Instruction::IntToPtr: {
92 5: return ZExtExpr::create(op1, Expr::getWidthForLLVMType(type));
93 : }
94 :
95 : case Instruction::PtrToInt: {
96 8: return ZExtExpr::create(op1, Expr::getWidthForLLVMType(type));
97 : }
98 :
99 : case Instruction::GetElementPtr: {
100 : ref<Expr> base = op1;
101 :
102 : #if 0
103 : // XXX: we have a base, but lost the object? how does that work?
104 : if(referent) {
105 : if (const GlobalValue *gv = dyn_cast<GlobalValue>(ce->getOperand(0))) {
106 : assert(*referent && "don't have referent?");
107 : let(mt, globalObjects.find(gv));
108 : assert(mt != globalObjects.end());
109 : *referent = mt->second;
110 : cerr << "XXX: Have a global object!\n";
111 : } else
112 : cerr << "XXX: not a global, where is base?? :" << *base << "\n";
113 : }
114 : #endif
115 :
9795: branch 1 taken
4882: branch 2 taken
116 34236: for (gep_type_iterator ii = gep_type_begin(ce), ie = gep_type_end(ce);
117 : ii != ie; ++ii) {
118 : ref<Expr> addend(0, kMachinePointerType);
119 :
60: branch 0 taken
9735: branch 1 taken
120 19590: if (const StructType *st = dyn_cast<StructType>(*ii)) {
121 60: const StructLayout *sl = kmodule->targetData->getStructLayout(st);
122 60: const ConstantInt *ci = cast<ConstantInt>(ii.getOperand());
123 :
124 : addend = Expr::createPointer(sl->getElementOffset((unsigned)
125 60: ci->getZExtValue()));
126 : } else {
127 9735: const SequentialType *st = cast<SequentialType>(*ii);
128 9735: ref<Expr> index = evalConstant(cast<Constant>(ii.getOperand()));
129 19470: unsigned elementSize = kmodule->targetData->getTypeStoreSize(st->getElementType());
130 :
131 9735: index = Expr::createCoerceToPointerType(index);
132 : addend = MulExpr::create(index,
133 9735: Expr::createPointer(elementSize));
134 : }
135 :
136 9795: base = AddExpr::create(base, addend);
137 : }
138 :
139 9764: return base;
140 : }
141 :
142 : case Instruction::ICmp: {
0: branch 1 not taken
2: branch 2 taken
0: branch 3 not taken
0: branch 4 not taken
0: branch 5 not taken
0: branch 6 not taken
0: branch 7 not taken
0: branch 8 not taken
0: branch 9 not taken
0: branch 10 not taken
0: branch 11 not taken
143 2: switch(ce->getPredicate()) {
144 0: case ICmpInst::ICMP_EQ: return EqExpr::create(op1, op2);
145 2: case ICmpInst::ICMP_NE: return NeExpr::create(op1, op2);
146 0: case ICmpInst::ICMP_UGT: return UgtExpr::create(op1, op2);
147 0: case ICmpInst::ICMP_UGE: return UgeExpr::create(op1, op2);
148 0: case ICmpInst::ICMP_ULT: return UltExpr::create(op1, op2);
149 0: case ICmpInst::ICMP_ULE: return UleExpr::create(op1, op2);
150 0: case ICmpInst::ICMP_SGT: return SgtExpr::create(op1, op2);
151 0: case ICmpInst::ICMP_SGE: return SgeExpr::create(op1, op2);
152 0: case ICmpInst::ICMP_SLT: return SltExpr::create(op1, op2);
153 0: case ICmpInst::ICMP_SLE: return SleExpr::create(op1, op2);
154 : default:
155 0: assert(0 && "unhandled ICmp predicate");
156 : }
157 : }
158 :
159 : case Instruction::Select: {
160 0: return SelectExpr::create(op1, op2, op3);
161 : }
162 :
163 : case Instruction::FDiv:
164 : case Instruction::FRem:
165 : case Instruction::FPTrunc:
166 : case Instruction::FPExt:
167 : case Instruction::UIToFP:
168 : case Instruction::SIToFP:
169 : case Instruction::FPToUI:
170 : case Instruction::FPToSI:
171 : case Instruction::FCmp:
172 0: assert(0 && "floating point ConstantExprs unsupported");
173 :
174 : default :
175 0: assert(0 && "unknown ConstantExpr type");
176 16967: }
177 : }
178 :
103: branch 0 taken
0: branch 1 not taken
103: branch 2 taken
0: branch 3 not taken
179 206: }
Generated: 2009-05-17 22:47 by zcov