Sample program showing how to connect GR-PEACH into Watson IoT through mbed Connector and Watson's Connector Bridge
Dependencies: AsciiFont DisplayApp GR-PEACH_video LCD_shield_config LWIPBP3595Interface_STA_for_mbed-os USBDevice
DeviceManager.cpp
00001 /** 00002 * @file DeviceManager.cpp 00003 * @brief mbed CoAP Endpoint Device Management class 00004 * @author Doug Anson 00005 * @version 1.0 00006 * @see 00007 * 00008 * Copyright (c) 2016 00009 * 00010 * Licensed under the Apache License, Version 2.0 (the "License"); 00011 * you may not use this file except in compliance with the License. 00012 * You may obtain a copy of the License at 00013 * 00014 * http://www.apache.org/licenses/LICENSE-2.0 00015 * 00016 * Unless required by applicable law or agreed to in writing, software 00017 * distributed under the License is distributed on an "AS IS" BASIS, 00018 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00019 * See the License for the specific language governing permissions and 00020 * limitations under the License. 00021 */ 00022 00023 // configuration 00024 #include "mbed-connector-interface/mbedConnectorInterface.h" 00025 00026 // BaseClass 00027 #include "mbed-connector-interface/DeviceManager.h" 00028 00029 // Endpoint Class 00030 #include "mbed-connector-interface/ConnectorEndpoint.h" 00031 00032 // Options Builder 00033 #include "mbed-connector-interface/OptionsBuilder.h" 00034 00035 // Device Management Responder 00036 #include "mbed-connector-interface/DeviceManagementResponder.h" 00037 00038 // Constructor 00039 DeviceManager::DeviceManager(const Logger *logger,const void *dm_responder,const char *mfg,const char *dev_type,const char *model,const char *serial,const char *fw_vers,const char *hw_vers,const char *sw_vers) { 00040 // record the data management responder if we have one 00041 this->m_dm_responder = (void *)dm_responder; 00042 00043 // save off for later 00044 this->m_dev_type = (char *)dev_type; 00045 this->m_logger = (Logger *)logger; 00046 this->m_mfg = (char *)mfg; 00047 this->m_model = (char *)model; 00048 this->m_serial = (char *)serial; 00049 this->m_fw_vers = (char *)fw_vers; 00050 this->m_sw_vers = (char *)sw_vers; 00051 this->m_hw_vers = (char *)hw_vers; 00052 00053 // initialize 00054 this->m_device = NULL; 00055 for(int i=0;i<NUM_DEVICE_RESOURCES;++i) { 00056 this->m_dev_res[i] = NULL; 00057 } 00058 for(int i=0;i<NUM_FIRMWARE_RESOURCES;++i) { 00059 this->m_fw_res[i] = NULL; 00060 } 00061 this->m_deregister_resource = NULL; 00062 this->m_endpoint = NULL; 00063 this->m_config = NULL; 00064 this->m_fw_manifest = NULL; 00065 this->m_fw_manifest_length = 0; 00066 this->m_fw_image = NULL; 00067 this->m_fw_image_length = 0; 00068 } 00069 00070 // Copy constructor 00071 DeviceManager::DeviceManager(const DeviceManager &manager) { 00072 for(int i=0;i<NUM_DEVICE_RESOURCES;++i) { 00073 this->m_dev_res[i] = manager.m_dev_res[i]; 00074 } 00075 for(int i=0;i<NUM_FIRMWARE_RESOURCES;++i) { 00076 this->m_fw_res[i] = manager.m_fw_res[i]; 00077 } 00078 this->m_dm_responder = manager.m_dm_responder; 00079 this->m_device = manager.m_device; 00080 this->m_dev_type = manager.m_dev_type; 00081 this->m_logger = manager.m_logger; 00082 this->m_endpoint = manager.m_endpoint; 00083 this->m_config = manager.m_config; 00084 this->m_mfg = manager.m_mfg; 00085 this->m_model = manager.m_model; 00086 this->m_serial = manager.m_serial; 00087 this->m_fw_vers = manager.m_fw_vers; 00088 this->m_sw_vers = manager.m_sw_vers; 00089 this->m_hw_vers = manager.m_hw_vers; 00090 this->m_deregister_resource = manager.m_deregister_resource; 00091 this->m_fw_manifest = this->saveManifest((uint8_t *)manager.m_fw_manifest,manager.m_fw_manifest_length); 00092 this->m_fw_manifest_length = manager.m_fw_manifest_length; 00093 this->m_fw_image = this->saveImage(manager.m_fw_image,manager.m_fw_image_length); 00094 this->m_fw_image_length = manager.m_fw_image_length; 00095 } 00096 00097 // Destructor 00098 DeviceManager::~DeviceManager() { 00099 if (this->m_fw_manifest != NULL) { 00100 free(this->m_fw_manifest); 00101 } 00102 if (this->m_fw_image != NULL) { 00103 free(this->m_fw_image); 00104 } 00105 this->m_fw_manifest = NULL; 00106 this->m_fw_manifest_length = 0; 00107 this->m_fw_image = NULL; 00108 this->m_fw_image_length = 0; 00109 } 00110 00111 // save the fota manifest 00112 char *DeviceManager::saveManifest(uint8_t *manifest,uint32_t manifest_length) { 00113 if (manifest != NULL && manifest_length > 0) { 00114 if (this->m_fw_manifest != NULL) { 00115 free(this->m_fw_manifest); 00116 } 00117 this->m_fw_manifest = (char *)malloc(manifest_length+1); 00118 memset(this->m_fw_manifest,0,manifest_length+1); 00119 memcpy(this->m_fw_manifest,manifest,manifest_length); 00120 this->m_fw_manifest_length = manifest_length; 00121 } 00122 return this->m_fw_manifest; 00123 } 00124 00125 // save the fota image 00126 void *DeviceManager::saveImage(void *image,uint32_t image_length) { 00127 if (image != NULL && image_length > 0) { 00128 if (this->m_fw_image != NULL) { 00129 free(this->m_fw_image); 00130 } 00131 this->m_fw_image = (char *)malloc(image_length); 00132 memset(this->m_fw_image,0,image_length); 00133 memcpy(this->m_fw_image,image,image_length); 00134 } 00135 return this->m_fw_image; 00136 } 00137 00138 // bind the device resources 00139 void DeviceManager::bindDeviceResources() { 00140 // our Endpoint configuration 00141 Connector::OptionsBuilder *cfg = (Connector::OptionsBuilder *)this->m_config; 00142 00143 // establish the default base LWM2M device info resource values 00144 this->m_device = M2MInterfaceFactory::create_device(); 00145 if (this->m_device != NULL) { 00146 this->m_dev_res[0] = this->m_device->create_resource(M2MDevice::Manufacturer,this->m_mfg); // Manufacturer 00147 this->m_dev_res[1] = this->m_device->create_resource(M2MDevice::DeviceType,this->m_dev_type); // Device Type 00148 this->m_dev_res[2] = this->m_device->create_resource(M2MDevice::ModelNumber,this->m_model); // Device Model 00149 this->m_dev_res[3] = this->m_device->create_resource(M2MDevice::SerialNumber,this->m_serial); // Device Serial 00150 this->m_dev_res[4] = this->m_device->create_resource(M2MDevice::FirmwareVersion,this->m_fw_vers); // Firmware Version 00151 this->m_dev_res[5] = this->m_device->create_resource(M2MDevice::HardwareVersion,this->m_hw_vers); // Hardware Version 00152 this->m_dev_res[6] = this->m_device->create_resource(M2MDevice::SoftwareVersion,this->m_sw_vers); // Software Version 00153 this->m_dev_res[7] = this->getDeviceRebootResource(); // Reboot 00154 this->m_dev_res[8] = this->m_device->create_resource(M2MDevice::FactoryReset); // Reset 00155 00156 // set the callback functions for Reboot and Reset 00157 if (this->m_dev_res[7] != NULL) { 00158 this->m_dev_res[7]->set_operation(M2MBase::POST_ALLOWED); 00159 this->m_dev_res[7]->set_execute_function(execute_callback(this,&DeviceManager::process_reboot_action)); 00160 } 00161 if (this->m_dev_res[8] != NULL) { 00162 this->m_dev_res[8]->set_operation(M2MBase::POST_ALLOWED); 00163 this->m_dev_res[8]->set_execute_function(execute_callback(this,&DeviceManager::process_reset_action)); 00164 } 00165 00166 // set the Device Resources Object 00167 if (cfg != NULL) { 00168 cfg->setDeviceResourcesObject(this->m_device); // device resources created under single device object... so just set it 00169 } 00170 } 00171 else { 00172 // unable to create the device object 00173 this->m_logger->logging("DeviceManager::bindDeviceResources(): Unable to create Device Object!"); 00174 } 00175 } 00176 00177 // bind the firmware resources 00178 void DeviceManager::bindFirmwareResources() { 00179 // our Endpoint configuration 00180 Connector::OptionsBuilder *cfg = (Connector::OptionsBuilder *)this->m_config; 00181 00182 // establish the default base LWM2M firmware info resource values 00183 this->m_firmware = M2MInterfaceFactory::create_firmware(); 00184 if (this->m_firmware != NULL) { 00185 // Create our optional resources 00186 this->m_fw_res[0] = this->m_firmware->create_resource(M2MFirmware::PackageName,""); // Package Name 00187 this->m_fw_res[1] = this->m_firmware->create_resource(M2MFirmware::PackageVersion,""); // Package Version 00188 00189 // Get the speciality resources 00190 this->m_fw_res[2] = this->getFirmwareUpdateResource(); 00191 this->m_fw_res[3] = this->getFirmwarePackageResource(); 00192 this->m_fw_res[4] = this->getFirmwarePackageURIResource(); 00193 this->m_fw_res[5] = this->getFirmwareStateResource(); 00194 this->m_fw_res[6] = this->getFirmwareUpdateResultResource(); 00195 00196 // set the callback functions for Update 00197 if (this->m_fw_res[2] != NULL) { 00198 this->m_fw_res[2]->set_operation(M2MBase::POST_ALLOWED); 00199 this->m_fw_res[2]->set_execute_function(execute_callback(this,&DeviceManager::process_firmware_update_action)); 00200 } 00201 00202 // set the Firmware Resources Object 00203 if (cfg != NULL) { 00204 cfg->setFirmwareResourcesObject(this->m_firmware); // firmware resources created under single firmware object... so just set it 00205 } 00206 } 00207 else { 00208 // unable to create the firmware object 00209 this->m_logger->logging("DeviceManager::bindFirmwareResources(): Unable to create Firmware Object!"); 00210 } 00211 } 00212 00213 // bind mbed Cloud resources 00214 void DeviceManager::bindMBEDCloudResources() { 00215 // our Endpoint configuration 00216 Connector::OptionsBuilder *cfg = (Connector::OptionsBuilder *)this->m_config; 00217 00218 // Add mbed Cloud resources here... 00219 00220 // mbed Cloud DeRegistration Resource 00221 this->m_deregister_resource = new DeviceDeRegisterResource(this->m_logger,LWM2M_DREGISTER_OBJ_ID,LWM2M_DEV_DEREGISTER_ID,this->m_dm_responder); 00222 if (this->m_deregister_resource != NULL) { 00223 cfg->addResource(this->m_deregister_resource); // de-registration action resource added 00224 } 00225 } 00226 00227 // setup the Device Manager 00228 void DeviceManager::bind() { 00229 // Bind our Device Resources 00230 this->bindDeviceResources(); 00231 00232 // Bind our Firmware Resources 00233 this->bindFirmwareResources(); 00234 00235 // Bind our mbed Cloud Resources 00236 this->bindMBEDCloudResources(); 00237 } 00238 00239 // process updated values (PUT): The only updatable device management resources are: Firmware::Package, Firmware::PackageURI 00240 void DeviceManager::process(M2MBase *base, M2MBase::BaseType type) { 00241 // DeviceManagementResponder 00242 DeviceManagementResponder *dmr = (DeviceManagementResponder *)this->m_dm_responder; 00243 00244 // PackageURI handler 00245 if (base == this->getFirmwareResource(PackageURI)) { 00246 // PackageURI resource 00247 M2MResource *res = this->getFirmwareResource(PackageURI); 00248 00249 // Save off the manifest 00250 this->saveManifest(res->value(),res->value_length()); 00251 00252 // DEBUG 00253 this->m_logger->logging("DeviceManager::process(PUT): Setting FOTA Manifest: [%s] type: %d length: %d",this->m_fw_manifest,type,this->m_fw_manifest_length); 00254 00255 // Manifest Updated 00256 dmr->setFOTAManifest(this->m_fw_manifest,this->m_fw_manifest_length); 00257 } 00258 00259 // Package handler 00260 if (base == this->getFirmwareResource(Package)) { 00261 // FOTA Image (direct) Updated 00262 M2MResource *res = this->getFirmwareResource(PackageURI); 00263 00264 // DEBUG 00265 this->m_logger->logging("DeviceManager::process(PUT): Setting FOTA Image. Length=%d type: %d",res->value_length(),type); 00266 00267 // FOTA Image updated 00268 dmr->setFOTAImage(res->value(),res->value_length()); 00269 } 00270 } 00271 00272 // Get the Device Reboot Resource from the Device Object 00273 M2MResource *DeviceManager::getDeviceRebootResource() { 00274 if (this->m_device != NULL) { 00275 // Get /3/0/3 00276 return this->getResourceFromObject(this->m_device,0,M2MDevice::Reboot); 00277 } 00278 return NULL; 00279 } 00280 00281 // Get the Firmware Update Resource from the Firmware Object 00282 M2MResource *DeviceManager::getFirmwareUpdateResource() { 00283 if (this->m_firmware != NULL) { 00284 // Get /5/0/2 00285 return this->getResourceFromObject(this->m_firmware,0,M2MFirmware::Update); 00286 } 00287 return NULL; 00288 } 00289 00290 // Get the Firmware Package Resource from the Firmware Object 00291 M2MResource *DeviceManager::getFirmwarePackageResource() { 00292 if (this->m_firmware != NULL) { 00293 // Get /5/0/0 00294 return this->getResourceFromObject(this->m_firmware,0,M2MFirmware::Package); 00295 } 00296 return NULL; 00297 } 00298 00299 // Get the Firmware Package URI Resource from the Firmware Object 00300 M2MResource *DeviceManager::getFirmwarePackageURIResource() { 00301 if (this->m_firmware != NULL) { 00302 // Get /5/0/1 00303 return this->getResourceFromObject(this->m_firmware,0,M2MFirmware::PackageUri); 00304 } 00305 return NULL; 00306 } 00307 00308 // Get the Firmware State Resource from the Firmware Object 00309 M2MResource *DeviceManager::getFirmwareStateResource() { 00310 if (this->m_firmware != NULL) { 00311 // Get /5/0/3 00312 return this->getResourceFromObject(this->m_firmware,0,M2MFirmware::State); 00313 } 00314 return NULL; 00315 } 00316 00317 // Get the Firmware UpdateResult Resource from the Firmware Object 00318 M2MResource *DeviceManager::getFirmwareUpdateResultResource() { 00319 if (this->m_firmware != NULL) { 00320 // Get /5/0/5 00321 return this->getResourceFromObject(this->m_firmware,0,M2MFirmware::UpdateResult); 00322 } 00323 return NULL; 00324 } 00325 // Get a specific resource from a resource object 00326 M2MResource *DeviceManager::getResourceFromObject(M2MObject *obj,int instanceID,int resID) { 00327 if (obj != NULL) { 00328 M2MObjectInstanceList instances = obj->instances(); 00329 if (instances.size() > 0 && instances.size() > instanceID) { 00330 M2MObjectInstance *instance = instances[instanceID]; 00331 if (instance != NULL) { 00332 M2MResourceList resources = instance->resources(); 00333 if (resources.size() > 0 && resources.size() > resID) { 00334 M2MResource *resource = resources[resID]; 00335 return resource; 00336 } 00337 } 00338 } 00339 } 00340 return NULL; 00341 } 00342 00343 // Get the Device Object 00344 M2MDevice *DeviceManager::getDeviceObject() { 00345 return this->m_device; 00346 } 00347 00348 // Get the Firmware Object 00349 M2MFirmware *DeviceManager::getFirmwareObject() { 00350 return this->m_firmware; 00351 } 00352 00353 // extract a specific firmware resource 00354 M2MResource *DeviceManager::getFirmwareResource(FirmwareResources res) { 00355 // indexed optional resources 00356 int index = (int)res; 00357 if (index >= 0 && index <NUM_FIRMWARE_RESOURCES) { 00358 return this->m_fw_res[index]; 00359 } 00360 return NULL; 00361 } 00362 00363 // extract a specific device resource 00364 M2MResource *DeviceManager::getDeviceResource(DeviceResources res) { 00365 // special case: DeRegistration 00366 if (res == DeRegistration){ 00367 return this->m_deregister_resource->getResource(); 00368 } 00369 00370 // indexed optional resources 00371 int index = (int)res; 00372 if (index >= 0 && index <NUM_DEVICE_RESOURCES) { 00373 return this->m_dev_res[index]; 00374 } 00375 return NULL; 00376 } 00377 00378 // Install the device manager into the Connector Endpoint 00379 void DeviceManager::install(const void *endpoint,const void *config) { 00380 // record the configuration 00381 this->m_config = (void *)config; 00382 00383 // record the endpoint 00384 this->m_endpoint = (void *)endpoint; 00385 00386 // set the endpoint type 00387 Connector::OptionsBuilder *cfg = (Connector::OptionsBuilder *)this->m_config; 00388 if (cfg != NULL) { 00389 // set our device type 00390 cfg->setEndpointType(this->m_dev_type); 00391 } 00392 00393 // establish connection to our responder 00394 if (this->m_dm_responder != NULL) { 00395 ((DeviceManagementResponder *)this->m_dm_responder)->setEndpoint(this->m_endpoint); 00396 } 00397 } 00398 00399 // get our device management responder 00400 void *DeviceManager::getResponder() { 00401 return this->m_dm_responder; 00402 } 00403 00404 // process our reboot action 00405 void DeviceManager::process_reboot_action(void *args) { 00406 if (this->m_dm_responder != NULL) { 00407 ((DeviceManagementResponder *)this->m_dm_responder)->rebootDevice(args); 00408 } 00409 else { 00410 // no device management responder instance 00411 this->m_logger->logging("DeviceManager::process_reboot_action: DeviceManagementResponder is NULL. No reboot processed"); 00412 } 00413 } 00414 00415 // process our reset action 00416 void DeviceManager::process_reset_action(void *args) { 00417 if (this->m_dm_responder != NULL) { 00418 ((DeviceManagementResponder *)this->m_dm_responder)->resetDevice(args); 00419 } 00420 else { 00421 // no device management responder instance 00422 this->m_logger->logging("DeviceManager:: process_reset_action: DeviceManagementResponder is NULL. No reset processed"); 00423 } 00424 } 00425 00426 // process our firmware update action 00427 void DeviceManager::process_firmware_update_action(void *args) { 00428 if (this->m_dm_responder != NULL) { 00429 ((DeviceManagementResponder *)this->m_dm_responder)->invokeFOTA(args); 00430 } 00431 else { 00432 // no device management responder instance 00433 this->m_logger->logging("DeviceManager:: process_firmware_update_action: DeviceManagementResponder is NULL. No firmware update action processed"); 00434 } 00435 }
Generated on Thu Jul 14 2022 21:25:54 by 1.7.2