00001
00002
00003 #ifndef expr_result_h
00004 #define expr_result_h
00005
00006 #include <ptree.h>
00007 #include "annotation.h"
00008 #include "type_rep.h"
00009
00010
00011
00012
00013
00014
00015 class Function_symbol;
00021 struct Expr_result {
00022 struct Dummy;
00023 enum Kind {
00024 k_RValue,
00025 k_LValue,
00026 k_Function,
00027 k_BoundMember,
00028 k_BoundPMF
00029 };
00030
00031 private:
00032 Ptree* tree;
00033 Type type;
00034 Function_symbol* symbol;
00035 Kind kind;
00036 Ptree* obj_tree;
00037 public:
00038 Ptree* get_tree() const { return tree; }
00039 const Type& get_type() const { return type; }
00040 Function_symbol* get_function() const { return symbol; }
00041 Kind get_kind() const { return kind; }
00042 Ptree* get_object() const { return obj_tree; }
00043
00044 bool is_function() const { return kind == k_Function; }
00045 bool is_bound_member() const { return kind == k_BoundMember || kind == k_BoundPMF; }
00046 bool is_bound_pmf() const { return kind == k_BoundPMF; }
00047
00048 void set_kind(Kind k) { kind = k; }
00049 void set_tree(Ptree* t) { tree = t; }
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071
00072 Expr_result() : tree(0), type(), symbol(), obj_tree(0) { }
00073 Expr_result(Dummy*) : tree(0), type(), symbol(), obj_tree(0) { }
00074
00075
00076 template<class T>
00077 Expr_result(Annotated<T>* tree, Kind k)
00078 : tree(tree), type(tree->get_type()), symbol(0), kind(k), obj_tree(0)
00079 { assert(type.is_valid()); }
00080
00081 Expr_result(Ptree* tree, Type t, Kind k)
00082 : tree(tree), type(t), symbol(0), kind(k), obj_tree(0)
00083 { assert(type.is_valid()); }
00084
00085
00086 template<class T>
00087 Expr_result(Annotated<T>* tree, Function_symbol* sym)
00088 : tree(tree), type(), symbol(sym), kind(k_Function), obj_tree(0) { }
00089
00090
00091 Expr_result(Ptree* object, Ptree* function, Function_symbol* sym)
00092 : tree(function), type(), symbol(sym), kind(k_BoundMember), obj_tree(object) { }
00093
00094 Expr_result(Ptree* object, Ptree* function, Type t)
00095 : tree(function), type(t), symbol(0), kind(k_BoundPMF), obj_tree(object) { }
00096
00097 public:
00099 bool is_lvalue() const;
00100
00101 bool is_value() const;
00102
00103 void convert_to(Type t);
00104
00105 void convert_to_qual(Type t);
00106
00107 void set_value(Ptree* value, Type t);
00108
00110 void convert_to_rvalue();
00111
00113 void convert_to_pointer();
00114
00116 void convert_to_fpointer();
00117
00119 void do_integral_promotions();
00120
00121
00122
00124 void convert_to_bool();
00125
00127 void adjust_reference();
00128
00131 void do_std_conversions();
00132
00133 bool is_modifyable_lvalue() const;
00134
00136 bool is_npc() const;
00137 };
00138
00139
00140
00141
00142
00143
00144
00146 inline bool
00147 Expr_result::is_lvalue() const
00148 {
00149 return kind == k_LValue;
00150 }
00151
00152
00153 inline bool
00154 Expr_result::is_value() const
00155 {
00156 return kind == k_LValue || kind == k_RValue;
00157 }
00158
00159
00160 inline void
00161 Expr_result::convert_to(Type t)
00162 {
00163 assert(t.is_valid() && !t.is_class_type());
00164 if (t != type) {
00165 set_value(make_cast_expr(tree, t), t);
00166 }
00167 }
00168
00169
00170 inline void
00171 Expr_result::convert_to_qual(Type t)
00172 {
00173 assert(t.is_valid() && t.is_same_unqualified_type(type));
00174 if (t != type)
00175 set_value(make_cast_expr_unchecked(tree, t), t);
00176 }
00177
00178
00180 inline void
00181 Expr_result::do_integral_promotions()
00182 {
00183 convert_to_rvalue();
00184 convert_to(type.get_promoted_integer());
00185 }
00186
00187 #endif // expr_result_h