Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
SimpleM2MResource.cpp
00001 // ---------------------------------------------------------------------------- 00002 // Copyright 2016-2017 ARM Ltd. 00003 // 00004 // SPDX-License-Identifier: Apache-2.0 00005 // 00006 // Licensed under the Apache License, Version 2.0 (the "License"); 00007 // you may not use this file except in compliance with the License. 00008 // You may obtain a copy of the License at 00009 // 00010 // http://www.apache.org/licenses/LICENSE-2.0 00011 // 00012 // Unless required by applicable law or agreed to in writing, software 00013 // distributed under the License is distributed on an "AS IS" BASIS, 00014 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00015 // See the License for the specific language governing permissions and 00016 // limitations under the License. 00017 // ---------------------------------------------------------------------------- 00018 00019 #include "mbed-cloud-client/SimpleM2MResource.h" 00020 #include "mbed-trace/mbed_trace.h" 00021 00022 #include <ctype.h> 00023 00024 #include<stdio.h> 00025 00026 #define TRACE_GROUP "mClt" 00027 00028 00029 SimpleM2MResourceBase::SimpleM2MResourceBase() 00030 : _client(NULL), _route("") 00031 { 00032 tr_debug("SimpleM2MResourceBase::SimpleM2MResourceBase()"); 00033 } 00034 00035 SimpleM2MResourceBase::SimpleM2MResourceBase(MbedCloudClient* client, string route) 00036 : _client(client),_route(route) 00037 { 00038 tr_debug("SimpleM2MResourceBase::SimpleM2MResourceBase(), resource name %s\r\n", _route.c_str()); 00039 } 00040 00041 SimpleM2MResourceBase::~SimpleM2MResourceBase() 00042 { 00043 } 00044 00045 bool SimpleM2MResourceBase::define_resource_internal(std::string v, M2MBase::Operation opr, bool observable) 00046 { 00047 tr_debug("SimpleM2MResourceBase::define_resource_internal(), resource name %s!\r\n", _route.c_str()); 00048 00049 vector<string> segments = parse_route(_route.c_str()); 00050 if (segments.size() != 3) { 00051 tr_debug("[SimpleM2MResourceBase] [ERROR] define_resource_internal(), Route needs to have three segments, split by '/' (%s)\r\n", _route.c_str()); 00052 return false; 00053 } 00054 00055 // segments[1] should be one digit and numeric 00056 if (!isdigit(segments.at(1).c_str()[0])) { 00057 tr_debug("[SimpleM2MResourceBase] [ERROR] define_resource_internal(), second route segment should be numeric, but was not (%s)\r\n", _route.c_str()); 00058 return false; 00059 } 00060 00061 int inst_id = atoi(segments.at(1).c_str()); 00062 00063 // Check if object exists 00064 M2MObject* obj; 00065 map<string,M2MObject*>::iterator obj_it = _client->_objects.find(segments[0]) ; 00066 if(obj_it != _client->_objects.end()) { 00067 tr_debug("Found object... %s\r\n", segments.at(0).c_str()); 00068 obj = obj_it->second; 00069 } else { 00070 tr_debug("Create new object... %s\r\n", segments.at(0).c_str()); 00071 obj = M2MInterfaceFactory::create_object(segments.at(0).c_str()); 00072 if (!obj) { 00073 return false; 00074 } 00075 _client->_objects.insert(std::pair<string, M2MObject*>(segments.at(0), obj)); 00076 } 00077 00078 // Check if object instance exists 00079 M2MObjectInstance* inst = obj->object_instance(inst_id); 00080 if(!inst) { 00081 tr_debug("Create new object instance... %s\r\n", segments.at(1).c_str()); 00082 inst = obj->create_object_instance(inst_id); 00083 if(!inst) { 00084 return false; 00085 } 00086 } 00087 00088 // @todo check if the resource exists yet 00089 M2MResource* res = inst->resource(segments.at(2).c_str()); 00090 if(!res) { 00091 res = inst->create_dynamic_resource(segments.at(2).c_str(), "", 00092 M2MResourceInstance::STRING, observable); 00093 if(!res) { 00094 return false; 00095 } 00096 res->set_operation(opr); 00097 res->set_value((uint8_t*)v.c_str(), v.length()); 00098 00099 _client->_resources.insert(pair<string, M2MResource*>(_route, res)); 00100 _client->register_update_callback(_route, this); 00101 } 00102 00103 return true; 00104 } 00105 00106 vector<string> SimpleM2MResourceBase::parse_route(const char* route) 00107 { 00108 string s(route); 00109 vector<string> v; 00110 std::size_t found = s.find_first_of("/"); 00111 00112 while (found!=std::string::npos) { 00113 v.push_back(s.substr(0,found)); 00114 s = s.substr(found+1); 00115 found=s.find_first_of("/"); 00116 if(found == std::string::npos) { 00117 v.push_back(s); 00118 } 00119 } 00120 return v; 00121 } 00122 00123 string SimpleM2MResourceBase::get() const 00124 { 00125 tr_debug("SimpleM2MResourceBase::get() resource (%s)", _route.c_str()); 00126 if (!_client->_resources.count(_route)) { 00127 tr_debug("[SimpleM2MResourceBase] [ERROR] No such route (%s)\r\n", _route.c_str()); 00128 return string(); 00129 } 00130 00131 // otherwise ask mbed Client... 00132 uint8_t* buffIn = NULL; 00133 uint32_t sizeIn; 00134 _client->_resources[_route]->get_value(buffIn, sizeIn); 00135 00136 string s((char*)buffIn, sizeIn); 00137 tr_debug("SimpleM2MResourceBase::get() resource value (%s)", s.c_str()); 00138 free(buffIn); 00139 return s; 00140 } 00141 00142 bool SimpleM2MResourceBase::set(string v) 00143 { 00144 // Potentially set() happens in InterruptContext. That's not good. 00145 tr_debug("SimpleM2MResourceBase::set() resource (%s)", _route.c_str()); 00146 if (!_client->_resources.count(_route)) { 00147 tr_debug("[SimpleM2MResourceBase] [ERROR] No such route (%s)\r\n", _route.c_str()); 00148 return false; 00149 } 00150 00151 if (v.length() == 0) { 00152 _client->_resources[_route]->clear_value(); 00153 } 00154 else { 00155 _client->_resources[_route]->set_value((uint8_t*)v.c_str(), v.length()); 00156 } 00157 00158 return true; 00159 } 00160 00161 bool SimpleM2MResourceBase::set(const int& v) 00162 { 00163 char buffer[20]; 00164 int size = sprintf(buffer,"%d",v); 00165 std::string stringified(buffer,size); 00166 00167 return set(stringified); 00168 } 00169 00170 bool SimpleM2MResourceBase::set_post_function(void(*fn)(void*)) 00171 { 00172 //TODO: Check the resource exists with right operation being set or append the operation into it. 00173 M2MResource *resource = get_resource(); 00174 if(!resource) { 00175 return false; 00176 } 00177 M2MBase::Operation op = resource->operation(); 00178 op = (M2MBase::Operation)(op | M2MBase::POST_ALLOWED); 00179 resource->set_operation(op); 00180 00181 _client->_resources[_route]->set_execute_function(execute_callback_2(fn)); 00182 return true; 00183 } 00184 00185 bool SimpleM2MResourceBase::set_post_function(execute_callback fn) 00186 { 00187 //TODO: Check the resource exists with right operation being set or append the operation into it. 00188 M2MResource *resource = get_resource(); 00189 if(!resource) { 00190 return false; 00191 } 00192 M2MBase::Operation op = resource->operation(); 00193 op = (M2MBase::Operation)(op | M2MBase::POST_ALLOWED); 00194 resource->set_operation(op); 00195 00196 // No clue why this is not working?! It works with class member, but not with static function... 00197 _client->_resources[_route]->set_execute_function(fn); 00198 return true; 00199 } 00200 00201 M2MResource* SimpleM2MResourceBase::get_resource() 00202 { 00203 if (!_client->_resources.count(_route)) { 00204 tr_debug("[SimpleM2MResourceBase] [ERROR] No such route (%s)\r\n", _route.c_str()); 00205 return NULL; 00206 } 00207 return _client->_resources[_route]; 00208 } 00209 00210 SimpleM2MResourceString::SimpleM2MResourceString(MbedCloudClient* client, 00211 const char* route, 00212 string v, 00213 M2MBase::Operation opr, 00214 bool observable, 00215 FP1<void, string> on_update) 00216 : SimpleM2MResourceBase(client,route),_on_update(on_update) 00217 { 00218 tr_debug("SimpleM2MResourceString::SimpleM2MResourceString() creating (%s)\r\n", route); 00219 define_resource_internal(v, opr, observable); 00220 } 00221 00222 SimpleM2MResourceString::SimpleM2MResourceString(MbedCloudClient* client, 00223 const char* route, 00224 string v, 00225 M2MBase::Operation opr, 00226 bool observable, 00227 void(*on_update)(string)) 00228 00229 : SimpleM2MResourceBase(client,route) 00230 { 00231 tr_debug("SimpleM2MResourceString::SimpleM2MResourceString() overloaded creating (%s)\r\n", route); 00232 FP1<void, string> fp; 00233 fp.attach(on_update); 00234 _on_update = fp; 00235 define_resource_internal(v, opr, observable); 00236 } 00237 00238 SimpleM2MResourceString::~SimpleM2MResourceString() 00239 { 00240 } 00241 00242 string SimpleM2MResourceString::operator=(const string& new_value) 00243 { 00244 tr_debug("SimpleM2MResourceString::operator=()"); 00245 set(new_value); 00246 return new_value; 00247 } 00248 00249 SimpleM2MResourceString::operator string() const 00250 { 00251 tr_debug("SimpleM2MResourceString::operator string()"); 00252 string value = get(); 00253 return value; 00254 } 00255 00256 void SimpleM2MResourceString::update() 00257 { 00258 string v = get(); 00259 _on_update(v); 00260 } 00261 00262 SimpleM2MResourceInt::SimpleM2MResourceInt(MbedCloudClient* client, 00263 const char* route, 00264 int v, 00265 M2MBase::Operation opr, 00266 bool observable, 00267 FP1<void, int> on_update) 00268 : SimpleM2MResourceBase(client,route),_on_update(on_update) 00269 { 00270 tr_debug("SimpleM2MResourceInt::SimpleM2MResourceInt() creating (%s)\r\n", route); 00271 char buffer[20]; 00272 int size = sprintf(buffer,"%d",v); 00273 std::string stringified(buffer,size); 00274 define_resource_internal(stringified, opr, observable); 00275 } 00276 00277 SimpleM2MResourceInt::SimpleM2MResourceInt(MbedCloudClient* client, 00278 const char* route, 00279 int v, 00280 M2MBase::Operation opr, 00281 bool observable, 00282 void(*on_update)(int)) 00283 : SimpleM2MResourceBase(client,route) 00284 { 00285 tr_debug("SimpleM2MResourceInt::SimpleM2MResourceInt() overloaded creating (%s)\r\n", route); 00286 FP1<void, int> fp; 00287 fp.attach(on_update); 00288 _on_update = fp; 00289 char buffer[20]; 00290 int size = sprintf(buffer,"%d",v); 00291 std::string stringified(buffer,size); 00292 define_resource_internal(stringified, opr, observable); 00293 } 00294 00295 SimpleM2MResourceInt::~SimpleM2MResourceInt() 00296 { 00297 } 00298 00299 int SimpleM2MResourceInt::operator=(int new_value) 00300 { 00301 set(new_value); 00302 return new_value; 00303 } 00304 00305 SimpleM2MResourceInt::operator int() const 00306 { 00307 string v = get(); 00308 if (v.empty()) return 0; 00309 00310 return atoi((const char*)v.c_str()); 00311 } 00312 00313 void SimpleM2MResourceInt::update() 00314 { 00315 string v = get(); 00316 if (v.empty()) { 00317 _on_update(0); 00318 } else { 00319 _on_update(atoi((const char*)v.c_str())); 00320 } 00321 }
Generated on Tue Jul 12 2022 16:24:20 by
1.7.2