|
Urbi SDK Remote for C++
2.7.5
|
00001 /* 00002 * Copyright (C) 2006-2011, Gostai S.A.S. 00003 * 00004 * This software is provided "as is" without warranty of any kind, 00005 * either expressed or implied, including but not limited to the 00006 * implied warranties of fitness for a particular purpose. 00007 * 00008 * See the LICENSE file for more information. 00009 */ 00010 00012 00013 #include <urbi/ucontext.hh> 00014 #include <urbi/uobject.hh> 00015 #include <urbi/uvalue.hh> 00016 #include <urbi/uvar.hh> 00017 00018 GD_CATEGORY(Urbi.UVar); 00019 00020 namespace urbi 00021 { 00022 00023 00024 /*-------. 00025 | UVar. | 00026 `-------*/ 00027 UVar::UVar(const std::string& varname, impl::UContextImpl* impl) 00028 : UContext(impl) 00029 , VAR_PROP_INIT 00030 , impl_(0) 00031 , name(varname) 00032 { 00033 __init(); 00034 } 00035 00036 UVar::UVar(UObject& obj, const std::string& varname, impl::UContextImpl* impl) 00037 : UContext(impl) 00038 , VAR_PROP_INIT 00039 , impl_(0) 00040 , name(obj.__name + '.' + varname) 00041 { 00042 __init(); 00043 } 00044 00045 UVar::UVar(const std::string& objname, const std::string& varname, 00046 impl::UContextImpl* impl) 00047 : UContext(impl) 00048 , VAR_PROP_INIT 00049 , impl_(0) 00050 , name(objname + '.' + varname) 00051 { 00052 __init(); 00053 } 00054 00055 UVar::UVar(const UVar& b) 00056 : UContext(b.ctx_) 00057 , VAR_PROP_INIT 00058 , impl_(0) 00059 , name (b.name) 00060 { 00061 __init(); 00062 } 00063 00064 void 00065 UVar::init(const std::string& varname, impl::UContextImpl* ctx) 00066 { 00067 GD_FINFO_DUMP("UVar.init %s", varname); 00068 if (varname == name && ctx == ctx_) 00069 { 00070 GD_FINFO_TRACE("Multiple UVar.init on %s @with same parameters, ignoring", 00071 varname); 00072 return; 00073 } 00074 if (impl_) 00075 { 00076 GD_FINFO_TRACE("UVar.init rebinds from %s to %s", name, varname); 00077 unnotify(); 00078 impl_->clean(); 00079 } 00080 delete impl_; 00081 ctx_ = ctx; 00082 if (!ctx_) 00083 ctx_ = getCurrentContext(); 00084 impl_ = 0; 00085 name = varname; 00086 __init(); 00087 } 00088 00089 bool 00090 UVar::invariant() const 00091 { 00092 if (vardata) 00093 return true; 00094 else 00095 { 00096 // FIXME: this special case should be put in doc. 00097 GD_FERROR ("Unable to locate variable %s in hashtable. " 00098 "UVars being UObject attributes must be bound to be used " 00099 "in UObject C++ code. Use UBindVar. " 00100 "In any other case, this can be a memory problem. " 00101 "Please report bug.", 00102 name); 00103 return false; 00104 } 00105 } 00106 00107 void 00108 UVar::__init() 00109 { 00110 owned = false; 00111 temp = false; 00112 rtp = RTP_DEFAULT; 00113 local = false; 00114 vardata = 0; 00115 if (!impl_) 00116 { 00117 impl_ = ctx_->getVarImpl(); 00118 } 00119 impl_->initialize(this); 00120 } 00121 00122 UVar::~UVar() 00123 { 00124 GD_FINFO_DUMP("~UVar %s", name); 00125 if (impl_) 00126 { 00127 unnotify(); 00128 impl_->clean(); 00129 } 00130 delete impl_; 00131 } 00132 00133 void 00134 UVar::reset(ufloat n) 00135 { 00136 *this = n; 00137 } 00138 00139 std::ostream& 00140 operator<< (std::ostream& o, const UVar& u) 00141 { 00142 return o << "UVar(\"" << u.get_name() << "\" = " << u.val() << ')'; 00143 } 00144 00145 UVar& 00146 uvalue_caster<UVar>::operator() (UValue& v) 00147 { 00148 if (v.type == DATA_VOID) 00149 { 00150 if (!v.storage) 00151 throw std::runtime_error("invalid cast to UVar from void value."); 00152 else 00153 return *((UVar*)v.storage); 00154 } 00155 if (v.type != DATA_STRING) 00156 throw std::runtime_error("invalid cast to UVar from non-string value."); 00157 UVar* var = new UVar(*v.stringValue); 00158 getCurrentContext()->addCleanup(var); 00159 var->set_temp(true); 00160 return *var; 00161 } 00162 00163 UList& 00164 UList::operator=(UVar& v) 00165 { 00166 (*this) = (UList)v.val(); 00167 return *this; 00168 } 00169 00170 libport::utime_t 00171 UVar::timestamp() const 00172 { 00173 check(); 00174 return impl_->timestamp(); 00175 } 00176 00177 void InputPort::init(UObject* owner, const std::string& name, 00178 impl::UContextImpl* ctx) 00179 { 00180 UVar::init(owner->__name, name, ctx); 00181 impl_->setInputPort(true); 00182 } 00183 void InputPort::init(const std::string& owner, const std::string& name, 00184 impl::UContextImpl* ctx) 00185 { 00186 UVar::init(owner, name, ctx); 00187 impl_->setInputPort(true); 00188 } 00189 } // namespace urbi