Remove unused pkg dependancy
[platform/upstream/iotivity.git] / service / easy-setup / sampleapp / mediator / linux / richsdk_sample / mediator_cpp.cpp
1 //******************************************************************
2 //
3 // Copyright 2015 Samsung Electronics All Rights Reserved.
4 //
5 //-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
6 //
7 // Licensed under the Apache License, Version 2.0 (the "License");
8 // you may not use this file except in compliance with the License.
9 // You may obtain a copy of the License at
10 //
11 //      http://www.apache.org/licenses/LICENSE-2.0
12 //
13 // Unless required by applicable law or agreed to in writing, software
14 // distributed under the License is distributed on an "AS IS" BASIS,
15 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 // See the License for the specific language governing permissions and
17 // limitations under the License.
18 //
19 //-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
20
21 #include <iostream>
22 #include <condition_variable>
23
24 #include "OCPlatform.h"
25 #include "OCApi.h"
26 #include "OCProvisioningManager.hpp"
27
28 #include "EasySetup.hpp"
29 #include "ESRichCommon.h"
30
31 #define ES_SAMPLE_APP_TAG "ES_SAMPLE_APP_TAG"
32 #define DECLARE_MENU(FUNC, ...) { #FUNC, FUNC }
33
34 #define JSON_DB_PATH "./oic_svr_db_client.dat"
35
36 using namespace OC;
37 using namespace OIC::Service;
38
39 static std::shared_ptr<RemoteEnrollee> remoteEnrollee = nullptr;
40 static std::shared_ptr<OC::OCResource> curResource = nullptr;
41
42 static std::mutex g_discoverymtx;
43 static std::condition_variable g_cond;
44
45 typedef void (*Runner)();
46
47 Runner g_currentRun;
48
49 int processUserInput(int min = std::numeric_limits<int>::min(),
50         int max = std::numeric_limits<int>::max())
51 {
52     assert(min <= max);
53
54     int input;
55
56     std::cin >> input;
57     std::cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
58
59     if (!std::cin.fail() && min <= input && input <= max) return input;
60
61     std::cin.clear();
62     std::cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
63
64     throw std::runtime_error("Invalid Input, please try again");
65 }
66
67 void printConfiguration(EnrolleeConf conf)
68 {
69     cout << "===========================================" << endl;
70     cout << "\tDevice Name : " << conf.getDeviceName() << endl;
71     cout << "\tModel Number : " << conf.getModelNumber() << endl;
72
73     for(auto it : conf.getWiFiModes())
74     {
75         cout << "\tSupported WiFi modes : " << it << endl;
76     }
77
78     cout << "\tSupported WiFi freq : " << static_cast<int>(conf.getWiFiFreq()) << endl;
79     cout << "\tCloud accessibility: " << conf.isCloudAccessible() << endl;
80     cout << "===========================================" << endl;
81 }
82
83 void printStatus(EnrolleeStatus status)
84 {
85     cout << "===========================================" << endl;
86     cout << "\tProvStatus : " << status.getProvStatus() << endl;
87     cout << "\tLastErrCode : " << status.getLastErrCode() << endl;
88     cout << "===========================================" << endl;
89 }
90
91 void provisionSecurityStatusCallback(std::shared_ptr<SecProvisioningStatus> secProvisioningStatus)
92 {
93     if(secProvisioningStatus->getESResult() != ES_OK)
94     {
95       cout << "provisionSecurity is failed." << endl;
96       return;
97     }
98     else
99     {
100       cout << "provisionSecurity is success." << endl;
101       cout << "uuid : " << secProvisioningStatus->getDeviceUUID()<< endl;
102     }
103 }
104
105 void provisionSecurity()
106 {
107     if(!remoteEnrollee)
108     {
109         std::cout << "RemoteEnrollee is null, retry Discovery EnrolleeResource." << endl;
110         return;
111     }
112
113     try
114     {
115         remoteEnrollee->provisionSecurity(provisionSecurityStatusCallback);
116     }
117     catch (OCException &e)
118     {
119         std::cout << "Exception during provisionSecurity call" << e.reason();
120         return;
121     }
122 }
123
124 void getStatusCallback(std::shared_ptr< GetEnrolleeStatus > getEnrolleeStatus)
125 {
126     if(getEnrolleeStatus->getESResult() != ES_OK)
127     {
128       cout << "getStatus is failed." << endl;
129       return;
130     }
131     else
132     {
133       cout << "getStatus is success." << endl;
134       printStatus(getEnrolleeStatus->getEnrolleeStatus());
135     }
136 }
137
138
139 void getStatus()
140 {
141     if(!remoteEnrollee)
142     {
143         std::cout << "RemoteEnrollee is null, retry Discovery EnrolleeResource." << endl;
144         return;
145     }
146
147     try
148     {
149         remoteEnrollee->getStatus(getStatusCallback);
150     }
151     catch (OCException &e)
152     {
153         std::cout << "Exception during getConfiguration call" << e.reason();
154         return;
155     }
156 }
157
158 void getConfigurationCallback(std::shared_ptr< GetConfigurationStatus > getConfigurationStatus)
159 {
160     if(getConfigurationStatus->getESResult() != ES_OK)
161     {
162       cout << "GetConfigurationStatus is failed." << endl;
163       return;
164     }
165     else
166     {
167       cout << "GetConfigurationStatus is success." << endl;
168       printConfiguration(getConfigurationStatus->getEnrolleeConf());
169     }
170 }
171
172 void getConfiguration()
173 {
174     if(!remoteEnrollee)
175     {
176         std::cout << "RemoteEnrollee is null, retry Discovery EnrolleeResource." << endl;
177         return;
178     }
179
180     try
181     {
182         remoteEnrollee->getConfiguration(getConfigurationCallback);
183     }
184     catch (OCException &e)
185     {
186         std::cout << "Exception during getConfiguration call" << e.reason();
187         return;
188     }
189 }
190
191 void deviceProvisioningStatusCallback(std::shared_ptr< DevicePropProvisioningStatus > provStatus)
192 {
193     if(provStatus->getESResult() != ES_OK)
194     {
195       cout << "Device Provisioning is failed." << endl;
196       return;
197     }
198     else
199     {
200       cout << "Device Provisioning is success." << endl;
201     }
202 }
203
204 void provisionDeviceProperty()
205 {
206     if(!remoteEnrollee)
207     {
208         std::cout << "RemoteEnrollee is null, retry Discovery EnrolleeResource." << endl;
209         return;
210     }
211
212     DeviceProp devProp;
213     devProp.setWiFiProp("Iotivity_SSID", "Iotivity_PWD", WPA2_PSK, TKIP_AES);
214     devProp.setDevConfProp("korean", "Korea", "Location");
215
216     try
217     {
218         remoteEnrollee->provisionDeviceProperties(devProp, deviceProvisioningStatusCallback);
219     }
220     catch (OCException &e)
221     {
222         std::cout << "Exception during provisionDeviceProperties call" << e.reason();
223         return;
224     }
225 }
226
227 void cloudProvisioningStatusCallback(std::shared_ptr< CloudPropProvisioningStatus > provStatus)
228 {
229     switch (provStatus->getESResult())
230     {
231         case ES_OK:
232             cout << "Cloud Provisioning is success." << endl;
233             break;
234         case ES_SECURE_RESOURCE_DISCOVERY_FAILURE:
235             cout << "Enrollee is not found in a given network." << endl;
236             break;
237         case ES_ACL_PROVISIONING_FAILURE:
238             cout << "ACL provisioning is failed." << endl;
239             break;
240         case ES_CERT_PROVISIONING_FAILURE:
241             cout << "CERT provisioning is failed." << endl;
242             break;
243         default:
244             cout << "Cloud Provisioning is failed." << endl;
245             break;
246     }
247 }
248
249 void provisionCloudProperty()
250 {
251     if(!remoteEnrollee)
252     {
253         std::cout << "RemoteEnrollee is null, retry Discovery EnrolleeResource." << endl;
254         return;
255     }
256
257     CloudProp cloudProp;
258     cloudProp.setCloudProp("authCode", "authProvider", "ciServer");
259     cloudProp.setCloudID("f002ae8b-c42c-40d3-8b8d-1927c17bd1b3");
260     cloudProp.setCredID(1);
261
262     try
263     {
264         remoteEnrollee->provisionCloudProperties(cloudProp, cloudProvisioningStatusCallback);
265     }
266     catch (OCException &e)
267     {
268         std::cout << "Exception during provisionCloudProperties call" << e.reason();
269         return;
270     }
271 }
272
273 // Callback to found resources
274 void foundResource(std::shared_ptr<OC::OCResource> resource)
275 {
276     std::string resourceURI;
277     std::string hostAddress;
278     try
279     {
280         // Do some operations with resource object.
281         if(resource &&
282            !curResource &&
283            resource->getResourceTypes().at(0) == OC_RSRVD_ES_RES_TYPE_PROV)
284         {
285             std::cout<<"DISCOVERED Resource:"<<std::endl;
286             // Get the resource URI
287             resourceURI = resource->uri();
288             std::cout << "\tURI of the resource: " << resourceURI << std::endl;
289
290             // Get the resource host address
291             hostAddress = resource->host();
292             std::cout << "\tHost address of the resource: " << hostAddress << std::endl;
293
294             // Get the resource types
295             std::cout << "\tList of resource types: " << std::endl;
296             for(auto &resourceTypes : resource->getResourceTypes())
297             {
298                 std::cout << "\t\t" << resourceTypes << std::endl;
299             }
300
301             // Get the resource interfaces
302             std::cout << "\tList of resource interfaces: " << std::endl;
303             for(auto &resourceInterfaces : resource->getResourceInterfaces())
304             {
305                 std::cout << "\t\t" << resourceInterfaces << std::endl;
306             }
307
308             if(curResource == nullptr)
309             {
310                 remoteEnrollee = EasySetup::getInstance()->createRemoteEnrollee(resource);
311                 if(!remoteEnrollee)
312                 {
313                     std::cout << "RemoteEnrollee object is failed for some reasons!" << std::endl;
314                 }
315                 else
316                 {
317                     curResource = resource;
318                     std::cout << "RemoteEnrollee object is successfully created!" << std::endl;
319                     g_cond.notify_all();
320                 }
321             }
322         }
323     }
324     catch(std::exception& e)
325     {
326         std::cerr << "Exception in foundResource: "<< e.what() << std::endl;
327     }
328 }
329
330 void discoveryEnrolleeResource()
331 {
332         try
333         {
334             std::ostringstream requestURI;
335         requestURI << OC_RSRVD_WELL_KNOWN_URI << "?rt=" << OC_RSRVD_ES_RES_TYPE_PROV;
336         OCPlatform::findResource("", requestURI.str(), CT_DEFAULT, &foundResource);
337         std::cout<< "Finding Resource... " <<std::endl;
338
339         std::unique_lock<std::mutex> lck(g_discoverymtx);
340         g_cond.wait_for(lck, std::chrono::seconds(5));
341         }
342         catch (OCException& e)
343         {
344                 std::cout << "Exception in discoveryEnrolleeResource: "<<e.what();
345         }
346 }
347
348 void DisplayMenu()
349 {
350         constexpr int DISCOVERY_ENROLLEE = 1;
351     constexpr int PROVISION_SECURITY = 2;
352     constexpr int GET_STATUS = 3;
353     constexpr int GET_CONFIGURATION = 4;
354     constexpr int PROVISION_DEVICE_PROPERTY = 5;
355     constexpr int PROVISION_CLOUD_PROPERTY = 6;
356
357     std::cout << "========================================================\n";
358     std::cout << DISCOVERY_ENROLLEE << ". Discovery Enrollee Resource \n";
359     std::cout << PROVISION_SECURITY << ". Provision Security to Enrollee  \n";
360     std::cout << GET_STATUS << ". Get Status from Enrollee  \n";
361     std::cout << GET_CONFIGURATION << ". Get Configuration from Enrollee  \n";
362     std::cout << PROVISION_DEVICE_PROPERTY << ". Provision Device Property\n";
363     std::cout << PROVISION_CLOUD_PROPERTY << ". Provision Cloud Property  \n";
364     std::cout << "========================================================\n";
365
366     int selection = processUserInput(DISCOVERY_ENROLLEE, PROVISION_CLOUD_PROPERTY);
367
368     switch (selection)
369     {
370         case DISCOVERY_ENROLLEE:
371             discoveryEnrolleeResource();
372             break;
373         case PROVISION_SECURITY:
374             provisionSecurity();
375             break;
376         case GET_STATUS:
377             getStatus();
378             break;
379         case GET_CONFIGURATION:
380             getConfiguration();
381             break;
382         case PROVISION_DEVICE_PROPERTY:
383             provisionDeviceProperty();
384             break;
385         case PROVISION_CLOUD_PROPERTY:
386             provisionCloudProperty();
387             break;
388         default:
389             break;
390     };
391 }
392
393 static FILE* client_open(const char *UNUSED_PARAM, const char *mode)
394 {
395     (void)UNUSED_PARAM;
396     return fopen(JSON_DB_PATH, mode);
397 }
398
399 int main()
400 {
401     OCPersistentStorage ps {client_open, fread, fwrite, fclose, unlink };
402
403     PlatformConfig config
404     {
405         OC::ServiceType::InProc, ModeType::Both, "0.0.0.0", 0, OC::QualityOfService::HighQos, &ps
406     };
407
408     OCPlatform::Configure(config);
409
410     try
411     {
412 #ifdef __WITH_DTLS__
413         //Initializing the provisioning client stack using the db path provided by the application.
414         OCStackResult result = OCSecure::provisionInit("");
415
416         if (result != OC_STACK_OK)
417         {
418             return -1;
419         }
420 #endif
421     }catch(OCException& e)
422     {
423         std::cout << "Exception in main: "<<e.what();
424     }
425
426     while (true)
427     {
428         try
429         {
430             DisplayMenu();
431         }
432         catch (const std::exception& e)
433         {
434             std::cout << "Exception caught in main " << e.what() << std::endl;
435         }
436     }
437
438     std::cout << "Stopping the client" << std::endl;
439
440     return 0;
441 }
442