replace : iotivity -> iotivity-sec
[platform/upstream/iotivity.git] / resource / csdk / security / provisioning / sample / cloud / cloudCommon.c
1 //******************************************************************
2 //
3 // Copyright 2016 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 #include <stdio.h>
21 #include <stdlib.h>
22 #include <string.h>
23 #include <pthread.h>
24
25 #include "ocstack.h"
26 #include "logger.h"
27 #include "octhread.h"
28 #include "cathreadpool.h"
29 #include "ocpayload.h"
30 #include "payload_logging.h"
31 #include "aclresource.h"
32 #include "crlresource.h"
33 #include "ocprovisioningmanager.h"
34 #include "casecurityinterface.h"
35 #include "mbedtls/ssl_ciphersuites.h"
36 #include "pkix_interface.h"
37 #include "../hw_emul/hw_interface.h"
38
39 #include "utils.h"
40 #include "cloudAuth.h"
41 #include "cloudCommon.h"
42 #include "cloudWrapper.h"
43 #include "cloudDiscovery.h"
44
45 #ifdef __unix__
46 #include <unistd.h> //for unlink
47 #endif
48
49 #define TAG "cloudCommon"
50
51 #define DEFAULT_HOST            "10.113.68.85"//"127.0.0.1"
52 #define DEFAULT_PORT            OC_MULTICAST_PORT
53 #define DEFAULT_AUTH_PROVIDER   "github"
54 #define DEFAULT_DB_FILE         "./cloud.dat"
55 #define DEFAULT_RESPONSE_WAIT_TIME (10 * 1000000) //10s
56
57 #define GITHUB_AUTH_LINK        "https://github.com/login?return_to=%2Flogin%2Foauth%2Fauthorize%3Fclient_id%3Dea9c18f540323b0213d0%26redirect_uri%3Dhttp%253A%252F%252Fwww.example.com%252Foauth_callback%252F"
58
59 #define CLIENT_ONLY(mode)       if (OC_SERVER == (mode)) { wrongRequest(); sendDataToServer = false; break; }
60
61 static bool fExit = false;
62
63 static ca_thread_pool_t g_threadPoolHandle = NULL;
64 static OCDevAddr endPoint;
65 static char token[1024] = "";
66 static char authProvider[1024] = DEFAULT_AUTH_PROVIDER;
67 static char *fname = DEFAULT_DB_FILE;
68 static uint64_t timeout;
69 static uint16_t g_credId = 0;
70
71 static oc_cond cond;
72 static oc_mutex mutex;
73
74 typedef enum {
75     SIGN_UP       = 1,
76     SIGN_IN       = 2,
77     SIGN_OUT      = 3,
78
79     HOST          = 4,
80     PORT          = 5,
81     DB_FILE       = 6,
82     AUTH_PROVIDER = 7,
83     USE_RSA = 8,
84     SAVE_TRUST_CERT = 9,
85     USE_SECURE_CONN = 10,
86     CONFIG_SELF_OWNERSHIP = 11,
87     SECURE_STORAGE_HW_EMULATION = 12,
88
89     DISCOVERY     = 13,
90     GET           = 14,
91     PUT           = 15,
92     POST          = 16,
93
94     CSR_SIGN      = 19,
95
96     CRL_GET       = 20,
97     CRL_POST      = 21,
98
99     ACL_ID_CREATE = 30,
100     ACL_ID_GET_BY_DEVICE = 31,
101     ACL_ID_DELETE = 32,
102
103     ACL_INDIVIDUAL_GET_INFO = 40,
104     ACL_INDIVIDUAL_UPDATE_ACE = 41,
105     ACL_INDIVIDUAL_UPDATE = 42,
106     ACL_INDIVIDUAL_DELETE = 43,
107     ACL_INDIVIDUAL_DELETE_ACE = 44,
108
109     ACL_GROUP_CREATE = 50,
110     ACL_GROUP_FIND   = 51,
111     ACL_GROUP_JOIN   = 52,
112     ACL_GROUP_OBSERVE= 53,
113     ACL_GROUP_DELETE = 54,
114
115     ACL_GROUP_SHARE_DEVICE  = 60,
116     ACL_GROUP_DELETE_DEVICE  = 61,
117     ACL_GROUP_GET_INFO  = 62,
118
119     ACL_POLICY_CHECK_REQUEST = 70,
120
121     ACL_GROUP_INVITE_USER = 80,
122     ACL_GROUP_GET_INVITE  = 81,
123     ACL_GROUP_DELETE_INVITE  = 82,
124     ACL_GROUP_CANCEL_INVITE  = 83,
125
126     EXIT          = 99
127 }CloudRequest;
128
129 static void printMenu(OCMode mode)
130 {
131     char *title = "Client";
132     if (OC_SERVER == mode)
133     {
134         title = "Server";
135     }
136     printf("************************************************************\n");
137     printf("****************** Cloud %s Requests *******************\n", title);
138     printf("************************************************************\n");
139     printf("** AUTHORIZATION\n");
140     printf("** %d - Sign Up request\n", SIGN_UP);
141     printf("** %d - Sign In request\n", SIGN_IN);
142     printf("** %d - Sign Out request\n", SIGN_OUT);
143
144     printf("** SETTINGS \n");
145     printf("** %d - Change default host\n", HOST);
146     printf("** %d - Change default port\n", PORT);
147     printf("** %d - Change default database filename\n", DB_FILE);
148     printf("** %d - Change default auth provider\n", AUTH_PROVIDER);
149     printf("** %d - Change TLS cipher suite (ECDSA/RSA)\n", USE_RSA);
150     printf("** %d - Save Trust Cert. Chain into Cred of SVR\n", SAVE_TRUST_CERT);
151     printf("** %d - Change Protocol type (CoAP/CoAPs)\n", USE_SECURE_CONN);
152     printf("** %d - Configure SVRdb as Self-OwnerShip\n", CONFIG_SELF_OWNERSHIP);
153     printf("** %d - Configure Secure Storage HW Emulation\n", SECURE_STORAGE_HW_EMULATION);
154
155     if (OC_CLIENT == mode)
156     {
157         printf("** DISCOVERY\n");
158         printf("** %d - Start Discovery\n", DISCOVERY);
159         printf("** %d - Get Request\n", GET);
160         printf("** %d - Put Request\n", PUT);
161         printf("** %d - Post Request\n", POST);
162     }
163
164     printf("** CERTIFICATE REQUEST\n");
165     printf("** %d - Certificate Request\n", CSR_SIGN);
166
167     printf("** CRL\n");
168     printf("** %d - CRL GET Request\n", CRL_GET);
169     printf("** %d - CRL POST Request\n", CRL_POST);
170
171     printf("** ACL MANAGER\n");
172     printf("** %d - ACL id create Request\n", ACL_ID_CREATE);
173     printf("** %d - ACL id retrieve by device Request\n", ACL_ID_GET_BY_DEVICE);
174     printf("** %d - ACL id delete Request\n", ACL_ID_DELETE);
175
176     printf("** ACL INDIVIDUAL\n");
177     printf("** %d - ACL individual get info Request\n", ACL_INDIVIDUAL_GET_INFO);
178     printf("** %d - ACL individual update ACE Request\n", ACL_INDIVIDUAL_UPDATE_ACE);
179     printf("** %d - ACL individual update Request\n", ACL_INDIVIDUAL_UPDATE);
180     printf("** %d - ACL individual delete Request\n", ACL_INDIVIDUAL_DELETE);
181     printf("** %d - ACL individual delete ACE Request\n", ACL_INDIVIDUAL_DELETE_ACE);
182
183     printf("** ACL GROUP MANAGER\n");
184     printf("** %d - ACL Create Group Request\n", ACL_GROUP_CREATE);
185     printf("** %d - ACL Find Group Request\n", ACL_GROUP_FIND);
186     printf("** %d - ACL Join to invited Group Request\n", ACL_GROUP_JOIN);
187     printf("** %d - ACL Observe Group Request\n", ACL_GROUP_OBSERVE);
188     printf("** %d - ACL Delete Group Request\n", ACL_GROUP_DELETE);
189
190     printf("** ACL INDIVIDUAL GROUP\n");
191     printf("** %d - ACL Share device into Group Request\n", ACL_GROUP_SHARE_DEVICE);
192     printf("** %d - ACL Delete device from Group Request\n", ACL_GROUP_DELETE_DEVICE);
193     printf("** %d - ACL Get Group Info Request\n", ACL_GROUP_GET_INFO);
194
195     printf("** ACL POLICY ENFORCEMENT\n");
196     printf("** %d - ACL Check Permissions Request\n", ACL_POLICY_CHECK_REQUEST);
197
198     printf("** ACL MEMBER INVITATION\n");
199     printf("** %d - ACL Invite user to group Request\n", ACL_GROUP_INVITE_USER);
200     printf("** %d - ACL Retrieve invitation Request\n", ACL_GROUP_GET_INVITE);
201     printf("** %d - ACL Delete invitation Request\n", ACL_GROUP_DELETE_INVITE);
202     printf("** %d - ACL Cancel invitation Request\n", ACL_GROUP_CANCEL_INVITE);
203
204     printf("** EXIT\n");
205     printf("** %d - Exit cloud %s\n", EXIT, title);
206     printf("************************************************************\n");
207 }
208
209 void unlockMenu(void *data)
210 {
211     OICFree(data);
212
213     if (!fExit)
214     {
215         oc_mutex_lock(mutex);
216         oc_cond_signal(cond);
217         oc_mutex_unlock(mutex);
218     }
219 }
220
221 /**
222  * This is default callback to all requests
223  * Used to sync with main menu
224  *
225  * @param[in] ctx          context
226  * @param[in] result       result
227  * @param[in] data         data
228  */
229 static void handleCB(void* ctx, OCStackResult result, void* data)
230 {
231     OC_UNUSED(ctx);
232     OC_UNUSED(data);
233
234     OIC_LOG_V(INFO, TAG, "%s: Received result = %d", __func__, result);
235
236     unlockMenu(NULL);
237 }
238
239 /**
240  * This function prints Acl id and calls default callback function handleCB()
241  *
242  * @param[in] ctx          context
243  * @param[in] result       result
244  * @param[in] aclId        acl id
245  */
246 static void handleAclIdCB(void* ctx, OCStackResult result, void* aclId)
247 {
248     OIC_LOG_V(INFO, TAG, "Received Acl id = %s", (char *)aclId);
249     handleCB(ctx, result, aclId);
250     OICFree(aclId);
251 }
252
253 /**
254  * This function prints group id and calls default callback function handleCB()
255  *
256  * @param[in] ctx          context
257  * @param[in] result       result
258  * @param[in] groupId      group id
259  */
260 static void handleAclCreateGroupCB(void* ctx, OCStackResult result, void* groupId)
261 {
262     OIC_LOG_V(INFO, TAG, "Received gid = %s", (char *)groupId);
263     handleCB(ctx, result, groupId);
264     OICFree(groupId);
265 }
266
267 /**
268  * This function prints group policy and calls default callback function handleCB()
269  *
270  * @param[in] ctx          context
271  * @param[in] result       result
272  * @param[in] gp           group policy
273  */
274 static void handleAclPolicyCheckCB(void* ctx, OCStackResult result, void* gp)
275 {
276     OIC_LOG_V(INFO, TAG, "Received gp = %s", (char *)gp);
277     handleCB(ctx, result, gp);
278     OICFree(gp);
279 }
280
281 /**
282  * This function prints received acl and calls default callback function handleCB()
283  *
284  * @param[in] ctx          context
285  * @param[in] result       result
286  * @param[in] acl          acl
287  */
288 static void handleAclIndividualGetInfoCB(void* ctx, OCStackResult result, void* acl)
289 {
290     printACL((OicSecAcl_t* )acl);
291     handleCB(ctx, result, acl);
292     //can't delete acl here because its ACE's were added to gAcl
293     //TODO: changes in aclresources.c required to fix that
294 }
295
296 /**
297  * This function prints received group id list and calls default callback function handleCB()
298  *
299  * @param[in] ctx          context
300  * @param[in] result       result
301  * @param[in] gidList      group id list
302  */
303 static void handleAclFindMyGroupCB(void* ctx, OCStackResult result, void* gidList)
304 {
305     printStringArray((stringArray_t *)gidList);
306     handleCB(ctx, result, gidList);
307     clearStringArray((stringArray_t *)gidList);
308 }
309
310 /**
311  * This function prints received acl and calls default callback function handleCB()
312  *
313  * @param[in] ctx          context
314  * @param[in] result       result
315  * @param[in] crl          crl
316  */
317 static void handleGetCrlCB(void* ctx, OCStackResult result, void* crl)
318 {
319     printCrl((OicSecCrl_t *)crl);
320     handleCB(ctx, result, crl);
321     DeleteCrl((OicSecCrl_t *)crl);
322 }
323
324 /**
325  * This function prints received invitation response and calls default callback function handleCB()
326  *
327  * @param[in] ctx          context
328  * @param[in] result       result
329  * @param[in] invite       invitation response (it has inviteResponse_t* type)
330  */
331 static void handleAclGetInvitationCB(void* ctx, OCStackResult result, void* invite)
332 {
333     printInviteResponse((inviteResponse_t *)invite);
334     handleCB(ctx, result, invite);
335     clearInviteResponse((inviteResponse_t *)invite);
336     OICFree(invite);
337 }
338
339 static OCStackResult saveTrustCert(void)
340 {
341     OCStackResult res = OC_STACK_ERROR;
342     OIC_LOG(INFO, TAG, "Save Trust Cert. Chain into Cred of SVR");
343
344     OCByteString trustCertChainArray = {0, 0};
345     const char *filename = "rootca.crt";
346
347     if (!readFile(filename, &trustCertChainArray))
348     {
349         OIC_LOG_V(ERROR, TAG, "Can't read %s file", filename);
350         OICFree(trustCertChainArray.bytes);
351         return OC_STACK_ERROR;
352     }
353     OIC_LOG_BUFFER(DEBUG, TAG, trustCertChainArray.bytes, trustCertChainArray.len);
354
355     res = OCSaveTrustCertChain(trustCertChainArray.bytes, trustCertChainArray.len, OIC_ENCODING_PEM,&g_credId);
356
357     if (OC_STACK_OK != res)
358     {
359         OIC_LOG(ERROR, TAG, "OCSaveTrustCertChain API error");
360     }
361     else
362     {
363         OIC_LOG_V(INFO, TAG, "CredId of Saved Trust Cert. Chain into Cred of SVR : %d.\n", g_credId);
364     }
365     OICFree(trustCertChainArray.bytes);
366
367     return res;
368 }
369
370 static OCStackResult configSelfOwnership(void)
371 {
372     OCStackResult res = OC_STACK_ERROR;
373     OIC_LOG(INFO, TAG, "Configures SVR DB as self-ownership.");
374
375     res = OCConfigSelfOwnership();
376
377     if (OC_STACK_OK != res)
378     {
379         OIC_LOG(ERROR, TAG, "OCConfigSelfOwnership API error. Please check SVR DB");
380     }
381     else
382     {
383         OIC_LOG(INFO, TAG, "Success to configures SVR DB as self-ownership");
384     }
385
386     return res;
387 }
388
389 static void configSecureStorageHwEmulation()
390 {
391     OIC_LOG(INFO, TAG, "Enable Secure Storage HW Emulation");
392
393     printf("         Enter Own Certificate File Path[~4095]: ");
394     char cert_filepath[4096] = {0,};
395     for(int ret=0; 1!=ret; )
396     {
397         ret = scanf("%255s", cert_filepath);
398         for( ; 0x20<=getchar(); );  // for removing overflow garbages
399                                     // '0x20<=code' is character region
400     }
401
402     printf("         Enter Private Key File Path[~4095]: ");
403     char key_filepath[4096] = {0,};
404     for(int ret=0; 1!=ret; )
405     {
406         ret = scanf("%255s", key_filepath);
407         for( ; 0x20<=getchar(); );  // for removing overflow garbages
408                                     // '0x20<=code' is character region
409     }
410
411     printf("         Enter Password for Key Password[~31][Press (Enter) to not set]: ");
412     char pwd[32] = {0,};
413     for(int i=0; i < 31; i++)
414     {
415         pwd[i] = (char)getchar();
416         if (0x20 <= pwd[i])
417         {
418             pwd[i--] = '\0';
419             continue;
420         }
421         if (0x0A == pwd[i])
422         {
423             pwd[i] = '\0';
424             break;
425         }
426     }
427
428     if (0 != SSemulSetCertkeyFilepath(cert_filepath, key_filepath, pwd))
429     {
430         OIC_LOG(ERROR, TAG, "    Fail to set cert/key file path");
431         return;
432     }
433
434     if (0 != SetHwPkixCallbacks(HWGetKeyContext,
435                                                   HWFreeKeyContext,
436                                                   HWGetOwnCertificateChain,
437                                                   HWSetupPkContext))
438     {
439         OIC_LOG(ERROR, TAG, "    Fail to regist HW Pkix Callbacks");
440         return;
441     }
442     OIC_LOG(INFO, TAG, "    Success to regist HW Pkix Callbacks");
443 }
444
445 static void wrongRequest()
446 {
447     printf(">> Entered Wrong Menu Number. Please Enter Again\n\n");
448 }
449
450 static void userRequests(void *data)
451 {
452     if (NULL == data)
453     {
454         OIC_LOG(ERROR, TAG, "Received NULL data");
455         return;
456     }
457
458     OCMode mode = *(OCMode*)data;
459
460     memset(&endPoint, 0, sizeof(endPoint));
461     strncpy(endPoint.addr, DEFAULT_HOST, sizeof(endPoint.addr));
462     endPoint.port = DEFAULT_PORT;
463
464     mutex = oc_mutex_new();
465     cond = oc_cond_new();
466
467     while (false == fExit)
468     {
469         OCStackResult res = OC_STACK_ERROR;
470         bool sendDataToServer = true;
471         timeout = DEFAULT_RESPONSE_WAIT_TIME;
472         //startup report
473         printf("-----------------------------------------------------------\n");
474         printf("Connecting to: %s:%d\n", endPoint.addr, endPoint.port);
475         printf("via auth provider: %s\n", authProvider);
476         printf("srv file: %s\n", fname);
477         printf("CoAP prefix: %s\n", DEFAULT_PREFIX);
478         printf("-----------------------------------------------------------\n");
479
480         printMenu(mode);
481
482         int request = 0;
483         readInteger(&request, "Menu number", "see above");
484
485         switch (request)
486         {
487         case SIGN_UP:
488             if (0 == strncmp(authProvider, DEFAULT_AUTH_PROVIDER, sizeof(authProvider)))
489             {
490                 printf("Paste to browser %s and get auth code\n", GITHUB_AUTH_LINK);
491             }
492             readString(token, sizeof(token), "auth token", "check link above");
493             res = CloudSignUp(&endPoint, authProvider, token);
494             break;
495         case SIGN_IN:
496             res = CloudSignIn(&endPoint);
497             break;
498         case SIGN_OUT:
499             res = CloudSignOut(&endPoint);
500             break;
501         case HOST:
502             readString(endPoint.addr, sizeof(endPoint.addr), "host ip address", DEFAULT_HOST);
503             sendDataToServer = false;
504             break;
505         case PORT:
506         {
507             char example[8];
508             snprintf(example, sizeof(example), "%d", DEFAULT_PORT);
509             int tmp = 0;
510             readInteger(&tmp, "port number", example);
511             endPoint.port = tmp;
512             sendDataToServer = false;
513         }
514         break;
515         case CRL_GET:
516             res = OCWrapperGetCRL(&endPoint, handleGetCrlCB);
517             break;
518         case CRL_POST:
519             res = OCWrapperPostCRL(&endPoint, handleCB);
520             break;
521         case ACL_GROUP_CREATE:
522             res = OCWrapperAclCreateGroup(&endPoint, handleAclCreateGroupCB);
523             break;
524         case ACL_GROUP_FIND:
525             res = OCWrapperAclFindMyGroup(&endPoint, handleAclFindMyGroupCB);
526             break;
527         case ACL_GROUP_DELETE:
528             res = OCWrapperAclDeleteGroup(&endPoint, handleCB);
529             break;
530         case ACL_GROUP_JOIN:
531             res = OCWrapperAclJoinToInvitedGroup(&endPoint, handleCB);
532             break;
533         case ACL_GROUP_OBSERVE:
534             res = OCWrapperAclObserveGroup(&endPoint, handleCB);
535             break;
536         case ACL_GROUP_SHARE_DEVICE:
537             res = OCWrapperAclShareDeviceIntoGroup(&endPoint, handleCB);
538             break;
539         case ACL_GROUP_DELETE_DEVICE:
540             res = OCWrapperAclDeleteDeviceFromGroup(&endPoint, handleCB);
541             break;
542         case ACL_GROUP_GET_INFO:
543             res = OCWrapperAclGroupGetInfo(&endPoint, handleCB);
544             break;
545         case ACL_GROUP_INVITE_USER:
546             res = OCWrapperAclInviteUser(&endPoint, handleCB);
547             break;
548         case ACL_GROUP_GET_INVITE:
549             res = OCWrapperAclGetInvitation(&endPoint, handleAclGetInvitationCB);
550             break;
551         case ACL_GROUP_DELETE_INVITE:
552             res = OCWrapperAclDeleteInvitation(&endPoint, handleCB);
553             break;
554         case ACL_GROUP_CANCEL_INVITE:
555             res = OCWrapperAclCancelInvitation(&endPoint, handleCB);
556             break;
557         case ACL_POLICY_CHECK_REQUEST:
558             res = OCWrapperAclPolicyCheck(&endPoint, handleAclPolicyCheckCB);
559             break;
560         case ACL_ID_GET_BY_DEVICE:
561             res = OCWrapperAclIdGetByDevice(&endPoint, handleAclIdCB);
562             break;
563         case ACL_ID_CREATE:
564             res = OCWrapperAclIdCreate(&endPoint, handleAclIdCB);
565             break;
566         case ACL_ID_DELETE:
567             res = OCWrapperAclIdDelete(&endPoint, handleCB);
568             break;
569         case ACL_INDIVIDUAL_GET_INFO:
570             res = OCWrapperAclIndividualGetInfo(&endPoint, handleAclIndividualGetInfoCB);
571             break;
572         case ACL_INDIVIDUAL_UPDATE_ACE:
573             res = OCWrapperAclIndividualUpdateAce(&endPoint, handleCB);
574             break;
575         case ACL_INDIVIDUAL_UPDATE:
576             res = OCWrapperAclIndividualUpdate(&endPoint, handleCB);
577             break;
578         case ACL_INDIVIDUAL_DELETE:
579             res = OCWrapperAclIndividualDelete(&endPoint, handleCB);
580             break;
581         case ACL_INDIVIDUAL_DELETE_ACE:
582             res = OCWrapperAclIndividualDeleteAce(&endPoint, handleCB);
583             break;
584         case CSR_SIGN:
585             res = OCWrapperCertificateIssueRequest(&endPoint, handleCB);
586             break;
587         case DISCOVERY:
588             CLIENT_ONLY(mode);
589             res = InitDiscovery();
590             break;
591         case GET:
592             CLIENT_ONLY(mode);
593             res = InitRequest(OC_REST_GET);
594             break;
595         case PUT:
596             CLIENT_ONLY(mode);
597             res= InitRequest(OC_REST_PUT);
598             break;
599         case POST:
600             CLIENT_ONLY(mode);
601             res= InitRequest(OC_REST_POST);
602             break;
603         case USE_RSA:
604         {
605             int tmp = 0;
606             readInteger(&tmp, "Select Cipher Suite", "0 - ECDSA, other - RSA");
607             uint16_t cipher = tmp? MBEDTLS_TLS_RSA_WITH_AES_128_GCM_SHA256:
608                                    MBEDTLS_TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8;
609             if (CA_STATUS_OK != CASelectCipherSuite(cipher, CA_ADAPTER_TCP))
610             {
611                 OIC_LOG(ERROR, TAG, "CASelectCipherSuite returned an error");
612             }
613             sendDataToServer = false;
614         }
615             break;
616         case SAVE_TRUST_CERT:
617             saveTrustCert();
618             sendDataToServer = false;
619             break;
620         case USE_SECURE_CONN:
621         {
622             int tmp = 0;
623             readInteger(&tmp, "CoAP protocol type", "0 - non-secure, 1 - secure");
624             setCoapPrefix(0 == tmp ? false : true);
625             sendDataToServer = false;
626         }
627             break;
628         case CONFIG_SELF_OWNERSHIP:
629             configSelfOwnership();
630             sendDataToServer = false;
631             break;
632         case SECURE_STORAGE_HW_EMULATION:
633             configSecureStorageHwEmulation();
634             sendDataToServer = false;
635             break;
636         case EXIT:
637             oc_mutex_free(mutex);
638             oc_cond_free(cond);
639             fExit = true;
640             sendDataToServer = false;
641             break;
642         default:
643             wrongRequest();
644             sendDataToServer = false;
645             break;
646         }
647
648         //if requests were sent then wait response
649         if (sendDataToServer)
650         {
651             if (OC_STACK_OK == res)
652             {
653                 oc_mutex_lock(mutex);
654                 oc_cond_wait_for(cond, mutex, timeout);
655                 oc_mutex_unlock(mutex);
656             }
657             else
658             {
659                 OIC_LOG_V(ERROR, TAG, "Request returned an error %d", res);
660             }
661         }
662     }
663 }
664
665 FILE* server_fopen(const char *path, const char *mode)
666 {
667     OC_UNUSED(path);
668     return fopen(fname, mode);
669 }
670
671 /**
672  * Check file accessibility
673  *
674  * @param[in] name        file path
675  * @return true           if check was successful
676  */
677 static bool checkConfig(const char *name)
678 {
679     FILE* file = fopen(name, "rb");
680
681     if (file)
682     {
683         fclose(file);
684         return true;
685     }
686     return false;
687 }
688
689 static void printUsage(char *name)
690 {
691     printf("Wrong arguments count!\n");
692     printf("Usage : %s <database_filename>\n", name);
693     printf("Examples : 1) %s 2) %s cloud.dat\n", name, name);
694 }
695
696 bool parseCommandLineArguments(int argc, char *argv[])
697 {
698     bool result = true;
699     if (2 == argc)
700     {
701         fname = argv[1];
702
703         if (!checkConfig(fname))
704         {
705             OIC_LOG_V(ERROR, TAG, "Can't open database file %s, exit!", fname);
706             result = false;
707         }
708     }
709     else if (argc > 2)
710     {
711         printUsage(argv[0]);
712         result = false;
713     }
714     return result;
715 }
716
717 OCStackResult initPersistentStorage()
718 {
719     //Initialize Persistent Storage for SVR database
720     static OCPersistentStorage ps = {server_fopen, fread, fwrite, fclose, unlink, NULL, NULL};
721
722     return OCRegisterPersistentStorageHandler(&ps);
723 }
724
725 OCStackResult startRequestsThread(OCMode *mode)
726 {
727     CAResult_t res = ca_thread_pool_init(1, &g_threadPoolHandle);
728     if (CA_STATUS_OK != res)
729     {
730         OIC_LOG(ERROR, TAG, "thread pool initialize error.");
731         return res;
732     }
733
734     res = ca_thread_pool_add_task(g_threadPoolHandle, userRequests, mode, NULL);
735     if (CA_STATUS_OK != res)
736     {
737         OIC_LOG(ERROR, TAG, "thread pool add task error.");
738         ca_thread_pool_free(g_threadPoolHandle);
739     }
740     return res;
741 }
742
743 OCStackResult initProcess(OCMode mode)
744 {
745     return OCInit(NULL, 0, mode);
746 }
747
748 void startProcess()
749 {
750     struct timespec timeout;
751     timeout.tv_sec  = 0;
752     timeout.tv_nsec = 100000000L;
753
754     while(false == fExit)
755     {
756         if (OCProcess() != OC_STACK_OK)
757         {
758             OIC_LOG(ERROR, TAG,"OCProcess process error, exit\n");
759             break;
760         }
761         nanosleep(&timeout, NULL);
762     }
763
764     if (OCStop() != OC_STACK_OK)
765     {
766         OIC_LOG(ERROR, TAG, "OCStop process error\n");
767     }
768 }
769
770 void freeThreadResources()
771 {
772     if (g_threadPoolHandle)
773     {
774         ca_thread_pool_free(g_threadPoolHandle);
775     }
776 }