00001
00002
00003 #ifndef CBZ_CONSTANTS_H
00004 #define CBZ_CONSTANTS_H
00005
00006 #include "pointers.h"
00007
00008 class constantFlowValue : public analysisVal
00009 {
00010 public:
00011
00012 const constant * value;
00013
00014 constantFlowValue()
00015 : value(0)
00016 {}
00017
00018 constantFlowValue(const constant * val)
00019 : value(val)
00020 {}
00021
00022 virtual ~constantFlowValue() { value = 0; }
00023
00024 virtual analysisVal * clone() const {
00025 return new constantFlowValue(*this);
00026 }
00027 };
00028
00029
00030 class constantAnalyzer : public analysisProblem
00031 {
00032 private:
00033
00034 typedef set< constant > constant_set;
00035 typedef constant_set::iterator constant_set_p;
00036
00037 typedef map< memoryDef *, const constant *> memorydef_constant_map;
00038 typedef memorydef_constant_map::iterator memorydef_constant_map_p;
00039
00040 typedef set< procLocation * > change_set;
00041 typedef change_set::iterator change_set_p;
00042
00043 typedef map< exprNode *, const constant * > expr_value_map;
00044 typedef expr_value_map::iterator expr_value_map_p;
00045
00052 TREE constant_set _constants;
00053
00058 memorydef_constant_map _values;
00059
00062 const constant * _top;
00063
00066 const constant * _bottom;
00067
00070 change_set _changes;
00071
00076 expr_value_map _expr_values;
00077
00080 bool _debug;
00081
00082 public:
00083
00086 constantAnalyzer(bool debug = false);
00087
00092 virtual string name() { return string("Constants"); }
00093
00099 void clear();
00100
00103 ~constantAnalyzer();
00104
00107 inline const constant * top() const { return _top; }
00108
00111 inline const constant * bottom() const { return _bottom; }
00112
00115 inline void set_debug(bool new_val) { _debug = new_val; }
00116
00117 protected:
00118
00124 const constant * lookup(const constant & value);
00125
00131 const constant * lookup_flowvalue(memoryDef * def);
00132
00139 bool update_flowvalue(const constant * val, memoryDef * def);
00140
00143 const constant * meet(const constant * one, const constant * two);
00144
00150 const constant * rebuild_flowvalue(pointerValue & pointer);
00151
00156 const constant * get_flowvalue(pointerValue & pointer);
00157
00162 void * set_flowvalue(const constant * val, pointerValue & pointer);
00163
00166 void record_expression(exprNode * expr, const constant * val);
00167
00168 public:
00169
00172 const constant * lookup_expression(exprNode * expr);
00173
00174
00175
00176
00177
00178 virtual void at_id(stmtLocation * current, idNode * id,
00179 pointerValue & value,
00180 bool result_is_a_use);
00181
00182 virtual void at_unary(stmtLocation * current,
00183 unaryNode * unary,
00184 pointerValue & operand,
00185 pointerValue & result,
00186 bool result_is_a_use);
00187
00188 virtual void at_binary(stmtLocation * current,
00189 binaryNode * binary,
00190 pointerValue & left,
00191 pointerValue & right,
00192 pointerValue & result,
00193 bool result_is_a_use);
00194
00195 virtual void at_cast(stmtLocation * current, castNode * cast,
00196 pointerValue & operand,
00197 pointerValue & result,
00198 bool result_is_a_use);
00199
00200 virtual void at_const(stmtLocation * current, constNode * cons,
00201 pointerValue & result,
00202 bool result_is_a_use);
00203
00204
00205
00206 virtual void at_field_access(stmtLocation * current,
00207 binaryNode * binary,
00208 pointerValue & operand,
00209 idNode * field,
00210 pointerValue & result,
00211 bool result_is_a_use);
00212
00213 virtual void at_dereference(stmtLocation * current,
00214 unaryNode * unary,
00215 pointerValue & operand,
00216 pointerValue & result,
00217 bool result_is_a_use);
00218
00219 virtual void at_address(stmtLocation * current,
00220 unaryNode * unary,
00221 pointerValue & operand,
00222 pointerValue & result,
00223 bool result_is_a_use);
00224
00225 virtual void at_index(stmtLocation * current,
00226 binaryNode * binary,
00227 pointerValue & left,
00228 pointerValue & right,
00229 pointerValue & result,
00230 bool result_is_a_use);
00231
00232
00233
00234 virtual void at_assignment(stmtLocation * current,
00235 binaryNode * binary,
00236 pointerValue & left,
00237 pointerValue & right,
00238 pointerValue & result,
00239 bool result_is_a_use,
00240 memoryblock_set & changes);
00241
00242 virtual void at_parameter_pass(Location * current,
00243 pointerValue & left,
00244 pointerValue & right,
00245 pointerValue & result,
00246 memoryblock_set & changes);
00247
00248
00249
00250 virtual void at_return(stmtLocation * stmt,
00251 returnNode * ret,
00252 pointerValue & result,
00253 pointerValue & return_val);
00254
00255
00256
00257 virtual void at_merge(basicblockLocation * where,
00258 memoryBlock * block,
00259 memoryuse_list & phi_uses,
00260 pointerValue & result,
00261 memoryblock_set & changes);
00262
00263
00264
00265 virtual void at_basicblock_entry(basicblockLocation * block,
00266 procedureInfo * info,
00267 pointerValue & initial);
00268
00269 virtual void at_stmt_entry(stmtLocation * stmt,
00270 pointerValue & result);
00271
00272
00273
00274 virtual void at_conservative_procedure_call(stmtLocation * current,
00275 callNode * call,
00276 pointerValue & call_target,
00277 pointervalue_list & arguments,
00278 memoryblock_set & reachable_blocks,
00279 pointerValue & return_val,
00280 memoryblock_set & changes);
00281
00282
00283
00284 void print(ostream & o, const constant * val) {
00285 if (val == _bottom)
00286 o << "(BOTTOM)";
00287 else
00288 if (val == _top)
00289 o << "(TOP)";
00290 else {
00291 constant temp = *val;
00292 o << temp.to_string();
00293 }
00294 }
00295
00296 private:
00297
00300 void record_change(memoryDef * def);
00301
00302
00303 };
00304
00305
00306 class constantsChanger : public Changer
00307 {
00308 public:
00309
00310 static void optimize(unitNode * u,
00311 constantAnalyzer * constants,
00312 bool simplify)
00313 {
00314 constantsChanger ipcc(constants, simplify);
00315 u->change(ipcc);
00316 }
00317
00318 private:
00319
00322 constantAnalyzer * _constants;
00323
00329 bool _simplify;
00330
00333 constantsChanger(constantAnalyzer * constants, bool simplify);
00334
00335 public:
00336
00337 virtual Node * at_expr(exprNode * the_expr, Order ord);
00338 virtual Node * at_if(ifNode * the_if, Order ord);
00339 };
00340
00341 #endif // CBZ_CONSTANTS_H