Simple interface for Mbed Cloud Client
Embed:
(wiki syntax)
Show/hide line numbers
m2msecurity.cpp
00001 /* 00002 * Copyright (c) 2015 ARM Limited. All rights reserved. 00003 * SPDX-License-Identifier: Apache-2.0 00004 * Licensed under the Apache License, Version 2.0 (the License); you may 00005 * not use this file except in compliance with the License. 00006 * You may obtain a copy of the License at 00007 * 00008 * http://www.apache.org/licenses/LICENSE-2.0 00009 * 00010 * Unless required by applicable law or agreed to in writing, software 00011 * distributed under the License is distributed on an AS IS BASIS, WITHOUT 00012 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00013 * See the License for the specific language governing permissions and 00014 * limitations under the License. 00015 */ 00016 #include "mbed-client/m2msecurity.h" 00017 #include "mbed-client/m2mconstants.h" 00018 #include "mbed-client/m2mobject.h" 00019 #include "mbed-client/m2mobjectinstance.h" 00020 #include "mbed-client/m2mresource.h" 00021 #include "mbed-client/m2mstring.h" 00022 #include "mbed-trace/mbed_trace.h" 00023 00024 #include <stdlib.h> 00025 00026 #define TRACE_GROUP "mClt" 00027 00028 #define BUFFER_SIZE 21 00029 00030 // Default instance id's that server uses 00031 #define DEFAULT_M2M_INSTANCE 0 00032 #define DEFAULT_BOOTSTRAP_INSTANCE 1 00033 00034 M2MSecurity* M2MSecurity::_instance = NULL; 00035 00036 M2MSecurity* M2MSecurity::get_instance() 00037 { 00038 if (_instance == NULL) { 00039 _instance = new M2MSecurity(M2MServer); 00040 } 00041 return _instance; 00042 } 00043 00044 void M2MSecurity::delete_instance() 00045 { 00046 delete _instance; 00047 _instance = NULL; 00048 } 00049 00050 00051 M2MSecurity::M2MSecurity(ServerType ser_type) 00052 : M2MObject(M2M_SECURITY_ID, stringdup(M2M_SECURITY_ID)) 00053 { 00054 } 00055 00056 M2MSecurity::~M2MSecurity() 00057 { 00058 } 00059 00060 M2MObjectInstance* M2MSecurity::create_object_instance(ServerType server_type) 00061 { 00062 uint16_t instance_id = DEFAULT_M2M_INSTANCE; 00063 if (server_type == Bootstrap) { 00064 instance_id = DEFAULT_BOOTSTRAP_INSTANCE; 00065 } 00066 00067 M2MObjectInstance *server_instance = M2MObject::object_instance(instance_id); 00068 if (server_instance != NULL) { 00069 // Instance already exists, return NULL 00070 return NULL; 00071 } 00072 00073 server_instance = M2MObject::create_object_instance(instance_id); 00074 if (server_instance) { 00075 M2MResource* res = server_instance->create_dynamic_resource(SECURITY_M2M_SERVER_URI, 00076 OMA_RESOURCE_TYPE, 00077 M2MResourceInstance::STRING, 00078 false); 00079 if (res) { 00080 res->set_operation(M2MBase::NOT_ALLOWED); 00081 } 00082 res = server_instance->create_dynamic_resource(SECURITY_BOOTSTRAP_SERVER, 00083 OMA_RESOURCE_TYPE, 00084 M2MResourceInstance::BOOLEAN, 00085 false); 00086 if (res) { 00087 res->set_operation(M2MBase::NOT_ALLOWED); 00088 res->set_value((int)server_type); 00089 } 00090 res = server_instance->create_dynamic_resource(SECURITY_SECURITY_MODE, 00091 OMA_RESOURCE_TYPE, 00092 M2MResourceInstance::INTEGER, 00093 false); 00094 if (res) { 00095 res->set_operation(M2MBase::NOT_ALLOWED); 00096 } 00097 res = server_instance->create_dynamic_resource(SECURITY_PUBLIC_KEY, 00098 OMA_RESOURCE_TYPE, 00099 M2MResourceInstance::OPAQUE, 00100 false); 00101 if (res) { 00102 res->set_operation(M2MBase::NOT_ALLOWED); 00103 } 00104 res = server_instance->create_dynamic_resource(SECURITY_SERVER_PUBLIC_KEY, 00105 OMA_RESOURCE_TYPE, 00106 M2MResourceInstance::OPAQUE, 00107 false); 00108 if (res) { 00109 res->set_operation(M2MBase::NOT_ALLOWED); 00110 } 00111 res = server_instance->create_dynamic_resource(SECURITY_SECRET_KEY, 00112 OMA_RESOURCE_TYPE, 00113 M2MResourceInstance::OPAQUE, 00114 false); 00115 if (res) { 00116 res->set_operation(M2MBase::NOT_ALLOWED); 00117 } 00118 if (M2MSecurity::M2MServer == server_type) { 00119 res = server_instance->create_dynamic_resource(SECURITY_SHORT_SERVER_ID, 00120 OMA_RESOURCE_TYPE, 00121 M2MResourceInstance::INTEGER, 00122 false); 00123 if (res) { 00124 res->set_operation(M2MBase::NOT_ALLOWED); 00125 } 00126 } 00127 } 00128 return server_instance; 00129 } 00130 00131 void M2MSecurity::remove_security_instances() 00132 { 00133 int32_t instance_id = _instance->get_security_instance_id(M2MSecurity::Bootstrap); 00134 if (instance_id >= 0) { 00135 _instance->remove_object_instance(instance_id); 00136 } 00137 instance_id = _instance->get_security_instance_id(M2MSecurity::M2MServer); 00138 if (instance_id >= 0) { 00139 _instance->remove_object_instance(instance_id); 00140 } 00141 } 00142 00143 M2MResource* M2MSecurity::create_resource(SecurityResource resource, uint32_t value, uint16_t instance_id) 00144 { 00145 M2MResource* res = NULL; 00146 M2MObjectInstance *server_instance = M2MObject::object_instance(instance_id); 00147 if (server_instance == NULL) { 00148 return NULL; 00149 } 00150 00151 const char* security_id_ptr = ""; 00152 if (!is_resource_present(resource, instance_id)) { 00153 switch(resource) { 00154 case SMSSecurityMode: 00155 security_id_ptr = SECURITY_SMS_SECURITY_MODE; 00156 break; 00157 case M2MServerSMSNumber: 00158 security_id_ptr = SECURITY_M2M_SERVER_SMS_NUMBER; 00159 break; 00160 case ShortServerID: 00161 security_id_ptr = SECURITY_SHORT_SERVER_ID; 00162 break; 00163 case ClientHoldOffTime: 00164 security_id_ptr = SECURITY_CLIENT_HOLD_OFF_TIME; 00165 break; 00166 default: 00167 break; 00168 } 00169 } 00170 00171 const String security_id(security_id_ptr); 00172 00173 if (!security_id.empty()) { 00174 if (server_instance) { 00175 res = server_instance->create_dynamic_resource(security_id,OMA_RESOURCE_TYPE, 00176 M2MResourceInstance::INTEGER, 00177 false); 00178 00179 if (res) { 00180 res->set_operation(M2MBase::NOT_ALLOWED); 00181 res->set_value(value); 00182 } 00183 } 00184 } 00185 return res; 00186 } 00187 00188 bool M2MSecurity::delete_resource(SecurityResource resource, uint16_t instance_id) 00189 { 00190 bool success = false; 00191 const char* security_id_ptr; 00192 M2MObjectInstance *server_instance = M2MObject::object_instance(instance_id); 00193 if (server_instance == NULL) { 00194 return NULL; 00195 } 00196 switch(resource) { 00197 case SMSSecurityMode: 00198 security_id_ptr = SECURITY_SMS_SECURITY_MODE; 00199 break; 00200 case M2MServerSMSNumber: 00201 security_id_ptr = SECURITY_M2M_SERVER_SMS_NUMBER; 00202 break; 00203 case ShortServerID: 00204 if (M2MSecurity::Bootstrap == server_type(instance_id)) { 00205 security_id_ptr = SECURITY_SHORT_SERVER_ID; 00206 } else { 00207 security_id_ptr = NULL; 00208 } 00209 break; 00210 case ClientHoldOffTime: 00211 security_id_ptr = SECURITY_CLIENT_HOLD_OFF_TIME; 00212 break; 00213 default: 00214 // Others are mandatory resources hence cannot be deleted. 00215 security_id_ptr = NULL; 00216 break; 00217 } 00218 00219 if (security_id_ptr) { 00220 if (server_instance) { 00221 success = server_instance->remove_resource(security_id_ptr); 00222 } 00223 } 00224 return success; 00225 } 00226 00227 bool M2MSecurity::set_resource_value(SecurityResource resource, 00228 const String &value, 00229 uint16_t instance_id) 00230 { 00231 bool success = false; 00232 if (M2MSecurity::M2MServerUri == resource) { 00233 M2MResource* res = get_resource(resource, instance_id); 00234 if (res) { 00235 success = res->set_value((const uint8_t*)value.c_str(),(uint32_t)value.length()); 00236 } 00237 } 00238 return success; 00239 } 00240 00241 bool M2MSecurity::set_resource_value(SecurityResource resource, 00242 uint32_t value, 00243 uint16_t instance_id) 00244 { 00245 bool success = false; 00246 M2MResource* res = get_resource(resource, instance_id); 00247 if (res) { 00248 if (M2MSecurity::SecurityMode == resource || 00249 M2MSecurity::SMSSecurityMode == resource || 00250 M2MSecurity::M2MServerSMSNumber == resource || 00251 M2MSecurity::ShortServerID == resource || 00252 M2MSecurity::BootstrapServer == resource || 00253 M2MSecurity::ClientHoldOffTime == resource) { 00254 success = res->set_value(value); 00255 00256 } 00257 } 00258 return success; 00259 } 00260 00261 bool M2MSecurity::set_resource_value(SecurityResource resource, 00262 const uint8_t *value, 00263 const uint16_t length, 00264 uint16_t instance_id) 00265 { 00266 bool success = false; 00267 M2MResource* res = get_resource(resource, instance_id); 00268 if (res) { 00269 if (M2MSecurity::PublicKey == resource || 00270 M2MSecurity::ServerPublicKey == resource || 00271 M2MSecurity::Secretkey == resource || 00272 M2MSecurity::M2MServerUri == resource) { 00273 success = res->set_value(value,length); 00274 } 00275 } 00276 return success; 00277 } 00278 00279 String M2MSecurity::resource_value_string(SecurityResource resource, uint16_t instance_id) const 00280 { 00281 String value = ""; 00282 M2MResource* res = get_resource(resource, instance_id); 00283 if (res) { 00284 if (M2MSecurity::M2MServerUri == resource) { 00285 value = res->get_value_string(); 00286 } 00287 } 00288 return value; 00289 } 00290 00291 uint32_t M2MSecurity::resource_value_buffer(SecurityResource resource, 00292 uint8_t *&data, 00293 uint16_t instance_id) const 00294 { 00295 uint32_t size = 0; 00296 M2MResource* res = get_resource(resource, instance_id); 00297 if (res) { 00298 if (M2MSecurity::PublicKey == resource || 00299 M2MSecurity::ServerPublicKey == resource || 00300 M2MSecurity::Secretkey == resource) { 00301 res->get_value(data,size); 00302 } 00303 } 00304 return size; 00305 } 00306 00307 uint32_t M2MSecurity::resource_value_buffer(SecurityResource resource, 00308 const uint8_t *&data, 00309 uint16_t instance_id) const 00310 { 00311 uint32_t size = 0; 00312 M2MResource* res = get_resource(resource, instance_id); 00313 if (res) { 00314 if (M2MSecurity::PublicKey == resource || 00315 M2MSecurity::ServerPublicKey == resource || 00316 M2MSecurity::Secretkey == resource) { 00317 data = res->value(); 00318 size = res->value_length(); 00319 } 00320 } 00321 return size; 00322 } 00323 00324 00325 uint32_t M2MSecurity::resource_value_int(SecurityResource resource, uint16_t instance_id) const 00326 { 00327 uint32_t value = 0; 00328 M2MResource* res = get_resource(resource, instance_id); 00329 if (res) { 00330 if (M2MSecurity::SecurityMode == resource || 00331 M2MSecurity::SMSSecurityMode == resource || 00332 M2MSecurity::M2MServerSMSNumber == resource || 00333 M2MSecurity::ShortServerID == resource || 00334 M2MSecurity::BootstrapServer == resource || 00335 M2MSecurity::ClientHoldOffTime == resource) { 00336 // note: the value may be 32bit int on 32b archs. 00337 value = res->get_value_int(); 00338 } 00339 } 00340 return value; 00341 } 00342 00343 bool M2MSecurity::is_resource_present(SecurityResource resource, uint16_t instance_id) const 00344 { 00345 bool success = false; 00346 M2MResource *res = get_resource(resource, instance_id); 00347 if (res) { 00348 success = true; 00349 } 00350 return success; 00351 } 00352 00353 uint16_t M2MSecurity::total_resource_count(uint16_t instance_id) const 00354 { 00355 uint16_t count = 0; 00356 M2MObjectInstance *server_instance = M2MObject::object_instance(instance_id); 00357 if (server_instance) { 00358 count = server_instance->resources().size(); 00359 } 00360 return count; 00361 } 00362 00363 M2MSecurity::ServerType M2MSecurity::server_type(uint16_t instance_id) const 00364 { 00365 uint32_t sec_mode = resource_value_int(M2MSecurity::BootstrapServer, instance_id); 00366 M2MSecurity::ServerType type = M2MSecurity::M2MServer; 00367 if (sec_mode == 1) { 00368 type = M2MSecurity::Bootstrap; 00369 } 00370 return type; 00371 } 00372 00373 M2MResource* M2MSecurity::get_resource(SecurityResource res, uint16_t instance_id) const 00374 { 00375 M2MResource* res_object = NULL; 00376 M2MObjectInstance *server_instance = M2MObject::object_instance(instance_id); 00377 if (server_instance == NULL) { 00378 return NULL; 00379 } 00380 00381 if (server_instance) { 00382 const char* res_name_ptr = NULL; 00383 switch(res) { 00384 case M2MServerUri: 00385 res_name_ptr = SECURITY_M2M_SERVER_URI; 00386 break; 00387 case BootstrapServer: 00388 res_name_ptr = SECURITY_BOOTSTRAP_SERVER; 00389 break; 00390 case SecurityMode: 00391 res_name_ptr = SECURITY_SECURITY_MODE; 00392 break; 00393 case PublicKey: 00394 res_name_ptr = SECURITY_PUBLIC_KEY; 00395 break; 00396 case ServerPublicKey: 00397 res_name_ptr = SECURITY_SERVER_PUBLIC_KEY; 00398 break; 00399 case Secretkey: 00400 res_name_ptr = SECURITY_SECRET_KEY; 00401 break; 00402 case SMSSecurityMode: 00403 res_name_ptr = SECURITY_SMS_SECURITY_MODE; 00404 break; 00405 case SMSBindingKey: 00406 res_name_ptr = SECURITY_SMS_BINDING_KEY; 00407 break; 00408 case SMSBindingSecretKey: 00409 res_name_ptr = SECURITY_SMS_BINDING_SECRET_KEY; 00410 break; 00411 case M2MServerSMSNumber: 00412 res_name_ptr = SECURITY_M2M_SERVER_SMS_NUMBER; 00413 break; 00414 case ShortServerID: 00415 res_name_ptr = SECURITY_SHORT_SERVER_ID; 00416 break; 00417 case ClientHoldOffTime: 00418 res_name_ptr = SECURITY_CLIENT_HOLD_OFF_TIME; 00419 break; 00420 } 00421 00422 if (res_name_ptr) { 00423 res_object = server_instance->resource(res_name_ptr); 00424 } 00425 } 00426 return res_object; 00427 } 00428 00429 void M2MSecurity::clear_resources(uint16_t instance_id) 00430 { 00431 for(int i = 0; i <= M2MSecurity::ClientHoldOffTime; i++) { 00432 M2MResource *res = get_resource((SecurityResource) i, instance_id); 00433 if (res) { 00434 res->clear_value(); 00435 } 00436 } 00437 } 00438 00439 int32_t M2MSecurity::get_security_instance_id(ServerType ser_type) const 00440 { 00441 M2MObjectInstanceList::const_iterator it; 00442 M2MObjectInstanceList insts = instances(); 00443 it = insts.begin(); 00444 int32_t instance_id = -1; 00445 for ( ; it != insts.end(); it++ ) { 00446 uint16_t id = (*it)->instance_id(); 00447 if (server_type(id) == ser_type) { 00448 instance_id = id; 00449 break; 00450 } 00451 } 00452 return instance_id; 00453 }
Generated on Tue Jul 12 2022 19:01:35 by 1.7.2