ArrayBounds.ccGo to the documentation of this file.00001
00002
00003 #include "define.h"
00004
00005 #ifdef POLARIS_GNU_PRAGMAS
00006 #pragma implementation
00007 #endif
00008
00009 #include <string.h>
00010
00011 #include "ArrayBounds.h"
00012 #include "BinRep.h"
00013 #include "Collection/Iterator.h"
00014 #include "Collection/List.h"
00015 #include "Collection/Mutator.h"
00016 #include "Expression/Expression.h"
00017 #include "ExprTable.h"
00018
00019 template class TypedCollection<ArrayBounds>;
00020 template class List<ArrayBounds>;
00021 template class Assign<ArrayBounds>;
00022 template ostream & operator << (ostream &, const List<ArrayBounds> &);
00023
00024 template class Iterator<ArrayBounds>;
00025 template class Mutator<ArrayBounds>;
00026
00027 ArrayBounds::ArrayBounds(const BinRep & binstr, ExprTable & exprs)
00028 {
00029 #ifdef CLASS_INSTANCE_REGISTRY
00030 register_instance(ARRAY_BOUNDS, sizeof(ArrayBounds), this);
00031 #endif
00032
00033 _expr_list.make_static_list(2);
00034
00035 for (Iterator<BinRep> iter = binstr.to_set(); iter.valid(); ++iter) {
00036 String field;
00037
00038 iter.current()[0].to_string(field);
00039
00040 if (field == "lb") {
00041 int index = iter.current()[1].to_integer();
00042
00043 _expr_list.modify(LOWER_BOUND, exprs[index]);
00044 }
00045 else if (field == "ub") {
00046 int index = iter.current()[1].to_integer();
00047
00048 _expr_list.modify(UPPER_BOUND, exprs[index]);
00049 }
00050 else {
00051 cerr << "Error: ArrayBounds: Unanticipated format: "
00052 << binstr << "\n";
00053 }
00054 }
00055 }
00056
00057 ArrayBounds::ArrayBounds(Expression * lower, Expression * upper)
00058 {
00059 #ifdef CLASS_INSTANCE_REGISTRY
00060 register_instance(ARRAY_BOUNDS, sizeof(ArrayBounds), this);
00061 #endif
00062
00063 _expr_list.make_static_list(2);
00064
00065 _expr_list.modify(LOWER_BOUND, lower);
00066 _expr_list.modify(UPPER_BOUND, upper);
00067 }
00068
00069 void
00070 ArrayBounds::print(ostream & o) const
00071 {
00072 if (!lower_exists() && upper_exists())
00073 o << upper_guarded();
00074 else if (!lower_exists() && !upper_exists())
00075 o << "*";
00076 else {
00077 if (lower_exists())
00078 o << lower_guarded();
00079 else
00080 o << "*";
00081
00082 o << ":";
00083
00084 if (upper_exists())
00085 o << upper_guarded();
00086 else
00087 o << "*";
00088 }
00089 }
00090
00091 ArrayBounds &
00092 ArrayBounds::operator = (const ArrayBounds & other)
00093 {
00094 _expr_list.modify(LOWER_BOUND,
00095 (other.lower_exists() ? other.lower_guarded().clone() : 0));
00096
00097 _expr_list.modify(UPPER_BOUND,
00098 (other.upper_exists() ? other.upper_guarded().clone() : 0));
00099
00100 return *this;
00101 }
00102
00103 ArrayBounds::~ArrayBounds()
00104 {
00105 #ifdef CLASS_INSTANCE_REGISTRY
00106 unregister_instance(ARRAY_BOUNDS, this);
00107 #endif
00108
00109 _expr_list.clear();
00110 }
00111
00112 int
00113 ArrayBounds::structures_OK() const
00114 {
00115 if (lower_exists()) {
00116 if (!lower_guarded().structures_OK()) {
00117 cerr << "In context of ArrayBounds:\n" << *this << endl;
00118 return 0;
00119 }
00120 }
00121
00122 if (upper_exists()) {
00123 if (!upper_guarded().structures_OK()) {
00124 cerr << "In context of ArrayBounds: " << *this << endl;
00125 return 0;
00126 }
00127 }
00128
00129 return 1;
00130 }
00131
00132 void
00133 ArrayBounds::lower(Expression * expr)
00134 {
00135 _expr_list.modify(LOWER_BOUND, expr);
00136 }
00137
00138 void
00139 ArrayBounds::upper(Expression * expr)
00140 {
00141 _expr_list.modify(UPPER_BOUND, expr);
00142 }
00143
00144 ArrayBounds *
00145 ArrayBounds::clone() const
00146 {
00147 return new ArrayBounds(*this);
00148 }
00149
00150 Listable *
00151 ArrayBounds::listable_clone() const
00152 {
00153 return (Listable *) clone();
00154 }
00155
00156 const Expression &
00157 ArrayBounds::upper_guarded() const
00158 {
00159 p_assert(_expr_list.valid(UPPER_BOUND),
00160 "ArrayBounds::upper_guarded(): upper expression does not exist");
00161
00162 return _expr_list[UPPER_BOUND];
00163 }
00164
00165 Expression &
00166 ArrayBounds::upper_guarded()
00167 {
00168 p_assert(_expr_list.valid(UPPER_BOUND),
00169 "ArrayBounds::upper_guarded(): upper expression does not exist");
00170
00171 return _expr_list[UPPER_BOUND];
00172 }
00173
00174 const Expression &
00175 ArrayBounds::lower_guarded() const
00176 {
00177 p_assert(_expr_list.valid(LOWER_BOUND),
00178 "ArrayBounds::lower_guarded(): lower expression does not exist");
00179
00180 return _expr_list[LOWER_BOUND];
00181 }
00182
00183 Expression &
00184 ArrayBounds::lower_guarded()
00185 {
00186 p_assert(_expr_list.valid(LOWER_BOUND),
00187 "ArrayBounds::lower_guarded(): lower expression does not exist");
00188
00189 return _expr_list[LOWER_BOUND];
00190 }
00191
00192 List<Expression> &
00193 ArrayBounds::arg_list()
00194 {
00195 return _expr_list;
00196 }
00197
00198
00199 ArrayBounds::ArrayBounds(const ArrayBounds & other)
00200 {
00201 #ifdef CLASS_INSTANCE_REGISTRY
00202 register_instance(ARRAY_BOUNDS, sizeof(ArrayBounds), this);
00203 #endif
00204
00205 _expr_list.make_static_list(2);
00206
00207 *this = other;
00208 }
00209
00210 ArrayBounds::ArrayBounds()
00211 {
00212 #ifdef CLASS_INSTANCE_REGISTRY
00213 register_instance(ARRAY_BOUNDS, sizeof(ArrayBounds), this);
00214 #endif
00215
00216 _expr_list.make_static_list(2);
00217 }
00218
00219 int
00220 ArrayBounds::lower_exists() const
00221 {
00222 return _expr_list.valid(LOWER_BOUND);
00223 }
00224
00225 const Expression *
00226 ArrayBounds::lower_ref() const
00227 {
00228 if (lower_exists())
00229 return & _expr_list[LOWER_BOUND];
00230
00231 return 0;
00232 }
00233
00234 Expression *
00235 ArrayBounds::lower_ref()
00236 {
00237 if (lower_exists())
00238 return & _expr_list[LOWER_BOUND];
00239
00240 return 0;
00241 }
00242
00243 int
00244 ArrayBounds::upper_exists() const
00245 {
00246 return _expr_list.valid(UPPER_BOUND);
00247 }
00248
00249 const Expression *
00250 ArrayBounds::upper_ref() const
00251 {
00252 if (upper_exists())
00253 return & _expr_list[UPPER_BOUND];
00254
00255 return 0;
00256
00257 }
00258
00259 Expression *
00260 ArrayBounds::upper_ref()
00261 {
00262 if (upper_exists())
00263 return & _expr_list[UPPER_BOUND];
00264
00265 return 0;
00266
00267 }
00268
00269 ostream &
00270 operator << (ostream & o, const ArrayBounds & bounds)
00271 {
00272 bounds.print(o);
00273 return o;
00274 }
00275
|