Merge remote-tracking branch 'origin/extended-easysetup'
[platform/upstream/iotivity.git] / service / easy-setup / enrollee / src / resourcehandler.c
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 "resourcehandler.h"
22
23 #include "ocpayload.h"
24 #include "oic_string.h"
25 #include "oic_malloc.h"
26
27 /**
28  * @var ES_RH_TAG
29  * @brief Logging tag for module name.
30  */
31 #define ES_RH_TAG "ES_RH"
32 //-----------------------------------------------------------------------------
33 // Private variables
34 //-----------------------------------------------------------------------------
35
36 /**
37  * @var gProvResource
38  * @brief Structure for holding the Provisioning status and target information required to
39  * connect to the target network
40  */
41 static ProvResource gProvResource;
42 static WiFiResource gWiFiResource;
43 static CloudResource gCloudResource;
44 static DevConfResource gDevConfResource;
45
46 //-----------------------------------------------------------------------------
47 // Private internal function prototypes
48 //-----------------------------------------------------------------------------
49 OCEntityHandlerResult OCEntityHandlerCb(OCEntityHandlerFlag flag, OCEntityHandlerRequest *ehRequest,
50         void *callback);
51 OCEntityHandlerResult ProcessGetRequest(OCEntityHandlerRequest *ehRequest, OCRepPayload** payload);
52 OCEntityHandlerResult ProcessPutRequest(OCEntityHandlerRequest *ehRequest, OCRepPayload** payload);
53 OCEntityHandlerResult ProcessPostRequest(OCEntityHandlerRequest *ehRequest, OCRepPayload** payload);
54 void updateProvResource(OCEntityHandlerRequest* ehRequest, OCRepPayload* input);
55 void updateWiFiResource(OCRepPayload* input);
56 void updateCloudResource(OCRepPayload* input);
57 void updateDevConfResource(OCRepPayload* input);
58 const char *getResult(OCStackResult result);
59
60 ESWiFiCB gWifiRsrcEvtCb = NULL;
61 ESCloudCB gCloudRsrcEvtCb = NULL;
62 ESDevConfCB gDevConfRsrcEvtCb = NULL;
63
64 ESReadUserdataCb gReadUserdataCb = NULL;
65 ESWriteUserdataCb gWriteUserdataCb = NULL;
66
67 ESResult SetCallbackForUserData(ESReadUserdataCb readCb, ESWriteUserdataCb writeCb)
68 {
69     if(!readCb && !writeCb)
70     {
71         OIC_LOG(INFO, ES_RH_TAG, "Both of callbacks for user data are null");
72         return ES_ERROR;
73     }
74     gReadUserdataCb = readCb;
75     gWriteUserdataCb = writeCb;
76     return ES_OK;
77 }
78
79 void RegisterWifiRsrcEventCallBack(ESWiFiCB cb)
80 {
81     gWifiRsrcEvtCb = cb;
82 }
83
84 void RegisterCloudRsrcEventCallBack(ESCloudCB cb)
85 {
86     gCloudRsrcEvtCb = cb;
87 }
88
89 void RegisterDevConfRsrcEventCallBack(ESDevConfCB cb)
90 {
91     gDevConfRsrcEvtCb = cb;
92 }
93
94 void UnRegisterResourceEventCallBack()
95 {
96     if (gWifiRsrcEvtCb)
97     {
98         gWifiRsrcEvtCb = NULL;
99     }
100     if (gCloudRsrcEvtCb)
101     {
102         gCloudRsrcEvtCb = NULL;
103     }
104     if (gDevConfRsrcEvtCb)
105     {
106         gDevConfRsrcEvtCb = NULL;
107     }
108 }
109
110 void GetTargetNetworkInfoFromProvResource(char *name, char *pass)
111 {
112     if (name != NULL && pass != NULL)
113     {
114         OICStrcpy(name, MAX_SSIDLEN, gWiFiResource.ssid);
115         OICStrcpy(pass, MAX_CREDLEN, gWiFiResource.cred);
116     }
117 }
118
119 OCStackResult initProvResource(bool isSecured)
120 {
121     gProvResource.status = ES_STATE_INIT;
122     gProvResource.lastErrCode = ES_ERRCODE_NO_ERROR;
123     OICStrcpy(gProvResource.ocfWebLinks, MAX_WEBLINKLEN, "");
124
125     OCStackResult res = OC_STACK_ERROR;
126     if (isSecured)
127     {
128         res = OCCreateResource(&gProvResource.handle, OC_RSRVD_ES_RES_TYPE_PROV,
129         OC_RSRVD_INTERFACE_DEFAULT,
130         OC_RSRVD_ES_URI_PROV, OCEntityHandlerCb,
131         NULL, OC_DISCOVERABLE | OC_OBSERVABLE | OC_SECURE);
132     }else
133     {
134         res = OCCreateResource(&gProvResource.handle, OC_RSRVD_ES_RES_TYPE_PROV,
135         OC_RSRVD_INTERFACE_DEFAULT,
136         OC_RSRVD_ES_URI_PROV, OCEntityHandlerCb,
137         NULL, OC_DISCOVERABLE | OC_OBSERVABLE);
138     }
139     if(res)
140     {
141         OIC_LOG_V(INFO, ES_RH_TAG, "Created Prov resource with result: %s", getResult(res));
142         return res;
143     }
144
145     res = OCBindResourceInterfaceToResource(gProvResource.handle, OC_RSRVD_INTERFACE_LL);
146     if(res)
147     {
148         OIC_LOG_V(INFO, ES_RH_TAG, "Binding Resource interface with result: %s", getResult(res));
149         return res;
150     }
151     res = OCBindResourceInterfaceToResource(gProvResource.handle, OC_RSRVD_INTERFACE_BATCH);
152     if(res)
153     {
154         OIC_LOG_V(INFO, ES_RH_TAG, "Binding Resource interface with result: %s", getResult(res));
155         return res;
156     }
157
158     OIC_LOG_V(INFO, ES_RH_TAG, "Created Prov resource with result: %s", getResult(res));
159     return res;
160 }
161
162 OCStackResult initWiFiResource(bool isSecured)
163 {
164     OCStackResult res = OC_STACK_ERROR;
165
166     gWiFiResource.supportedFreq = WIFI_BOTH;
167     gWiFiResource.supportedMode[0] = WIFI_11A;
168     gWiFiResource.supportedMode[1] = WIFI_11B;
169     gWiFiResource.supportedMode[2] = WIFI_11G;
170     gWiFiResource.supportedMode[3] = WIFI_11N;
171     gWiFiResource.numMode = 4;
172     gWiFiResource.authType = NONE_AUTH;
173     gWiFiResource.encType = NONE_ENC;
174     OICStrcpy(gWiFiResource.ssid, sizeof(gWiFiResource.ssid), "");
175     OICStrcpy(gWiFiResource.cred, sizeof(gWiFiResource.cred), "");
176
177     if (isSecured)
178     {
179         res = OCCreateResource(&gWiFiResource.handle, OC_RSRVD_ES_RES_TYPE_WIFI,
180         OC_RSRVD_INTERFACE_DEFAULT,
181         OC_RSRVD_ES_URI_WIFI, OCEntityHandlerCb,
182         NULL, OC_DISCOVERABLE | OC_OBSERVABLE | OC_SECURE);
183     }else
184     {
185         res = OCCreateResource(&gWiFiResource.handle, OC_RSRVD_ES_RES_TYPE_WIFI,
186         OC_RSRVD_INTERFACE_DEFAULT,
187         OC_RSRVD_ES_URI_WIFI, OCEntityHandlerCb,
188         NULL, OC_DISCOVERABLE | OC_OBSERVABLE);
189     }
190
191     OIC_LOG_V(INFO, ES_RH_TAG, "Created WiFi resource with result: %s", getResult(res));
192     return res;
193
194 }
195
196 OCStackResult initCloudServerResource(bool isSecured)
197 {
198     OCStackResult res = OC_STACK_ERROR;
199
200     OICStrcpy(gCloudResource.authCode, sizeof(gCloudResource.authCode), "");
201     OICStrcpy(gCloudResource.authProvider, sizeof(gCloudResource.authProvider), "");
202     OICStrcpy(gCloudResource.ciServer, sizeof(gCloudResource.ciServer), "");
203
204     if (isSecured)
205     {
206         res = OCCreateResource(&gCloudResource.handle, OC_RSRVD_ES_RES_TYPE_CLOUDSERVER,
207         OC_RSRVD_INTERFACE_DEFAULT,
208         OC_RSRVD_ES_URI_CLOUDSERVER, OCEntityHandlerCb,
209         NULL, OC_DISCOVERABLE | OC_OBSERVABLE | OC_SECURE);
210     }else
211     {
212         res = OCCreateResource(&gCloudResource.handle, OC_RSRVD_ES_RES_TYPE_CLOUDSERVER,
213         OC_RSRVD_INTERFACE_DEFAULT,
214         OC_RSRVD_ES_URI_CLOUDSERVER, OCEntityHandlerCb,
215         NULL, OC_DISCOVERABLE | OC_OBSERVABLE);
216     }
217
218     OIC_LOG_V(INFO, ES_RH_TAG, "Created CloudServer resource with result: %s", getResult(res));
219     return res;
220
221 }
222
223 OCStackResult initDevConfResource(bool isSecured)
224 {
225     OCStackResult res = OC_STACK_ERROR;
226
227     OICStrcpy(gDevConfResource.devName, sizeof(gDevConfResource.devName), "");
228     OICStrcpy(gDevConfResource.country, sizeof(gDevConfResource.country), "");
229     OICStrcpy(gDevConfResource.language, sizeof(gDevConfResource.language), "");
230
231     if (isSecured)
232     {
233         res = OCCreateResource(&gDevConfResource.handle, OC_RSRVD_ES_RES_TYPE_DEVCONF,
234         OC_RSRVD_INTERFACE_DEFAULT,
235         OC_RSRVD_ES_URI_DEVCONF, OCEntityHandlerCb,
236         NULL, OC_DISCOVERABLE | OC_OBSERVABLE | OC_SECURE);
237     }else
238     {
239         res = OCCreateResource(&gDevConfResource.handle, OC_RSRVD_ES_RES_TYPE_DEVCONF,
240         OC_RSRVD_INTERFACE_DEFAULT,
241         OC_RSRVD_ES_URI_DEVCONF, OCEntityHandlerCb,
242         NULL, OC_DISCOVERABLE | OC_OBSERVABLE);
243     }
244
245     OIC_LOG_V(INFO, ES_RH_TAG, "Created DevConf resource with result: %s", getResult(res));
246     return res;
247
248 }
249
250 void updateProvResource(OCEntityHandlerRequest* ehRequest, OCRepPayload* input)
251 {
252     OIC_LOG_V(INFO, ES_RH_TAG, "gProvResource.status %d", gProvResource.status);
253
254     if(ehRequest->query)
255     {
256         if(strstr(ehRequest->query, OC_RSRVD_INTERFACE_BATCH))
257         {
258         // When Provisioning resource has a POST with BatchInterface
259             updateCloudResource(input);
260             updateWiFiResource(input);
261             updateDevConfResource(input);
262         }
263     }
264 }
265
266 void updateWiFiResource(OCRepPayload* input)
267 {
268     ESWiFiProvData* wiFiData = (ESWiFiProvData*)OICMalloc(sizeof(ESWiFiProvData));
269
270     if(wiFiData == NULL)
271     {
272         OIC_LOG(DEBUG, ES_RH_TAG, "OICMalloc is failed");
273         return ;
274     }
275
276     memset(wiFiData->ssid, 0, MAX_SSIDLEN);
277     memset(wiFiData->pwd, 0, MAX_CREDLEN);
278     wiFiData->authtype = NONE_AUTH;
279     wiFiData->enctype = NONE_AUTH;
280     wiFiData->userdata = NULL;
281
282     char* ssid = NULL;
283     if (OCRepPayloadGetPropString(input, OC_RSRVD_ES_SSID, &ssid))
284     {
285         OICStrcpy(gWiFiResource.ssid, sizeof(gWiFiResource.ssid), ssid);
286         OICStrcpy(wiFiData->ssid, sizeof(wiFiData->ssid), ssid);
287         OIC_LOG_V(INFO, ES_RH_TAG, "gWiFiResource.ssid : %s", gWiFiResource.ssid);
288     }
289
290     char* cred = NULL;
291     if (OCRepPayloadGetPropString(input, OC_RSRVD_ES_CRED, &cred))
292     {
293         OICStrcpy(gWiFiResource.cred, sizeof(gWiFiResource.cred), cred);
294         OICStrcpy(wiFiData->pwd, sizeof(wiFiData->pwd), cred);
295         OIC_LOG_V(INFO, ES_RH_TAG, "gWiFiResource.cred %s", gWiFiResource.cred);
296     }
297
298     int64_t authType = -1;
299     if (OCRepPayloadGetPropInt(input, OC_RSRVD_ES_AUTHTYPE, &authType))
300     {
301         gWiFiResource.authType = authType;
302         wiFiData->authtype = gWiFiResource.authType;
303         OIC_LOG_V(INFO, ES_RH_TAG, "gWiFiResource.authType %u", gWiFiResource.authType);
304     }
305
306     int64_t encType = -1;
307     if (OCRepPayloadGetPropInt(input, OC_RSRVD_ES_ENCTYPE, &encType))
308     {
309         gWiFiResource.encType = encType;
310         wiFiData->enctype = gWiFiResource.encType;
311         OIC_LOG_V(INFO, ES_RH_TAG, "gWiFiResource.encType %u", gWiFiResource.encType);
312     }
313
314     if(gReadUserdataCb)
315     {
316         gReadUserdataCb(input, OC_RSRVD_ES_RES_TYPE_WIFI, &wiFiData->userdata);
317     }
318
319     if(ssid || cred || authType!= -1 || encType != -1)
320     {
321         OIC_LOG(INFO, ES_RH_TAG, "Send WiFiRsrc Callback To ES");
322
323         // TODO : Need to check appropriateness of gWiFiData
324         if(gWifiRsrcEvtCb != NULL)
325         {
326             gWifiRsrcEvtCb(ES_OK, wiFiData);
327         }
328         else
329         {
330             OIC_LOG(ERROR, ES_RH_TAG, "gWifiRsrcEvtCb is NULL");
331         }
332     }
333
334     OICFree(wiFiData);
335 }
336
337 void updateCloudResource(OCRepPayload* input)
338 {
339     ESCloudProvData* cloudData = (ESCloudProvData*)OICMalloc(sizeof(ESCloudProvData));
340
341     if(cloudData == NULL)
342     {
343         OIC_LOG(DEBUG, ES_RH_TAG, "OICMalloc is failed");
344         return;
345     }
346
347     memset(cloudData->authCode, 0, OIC_STRING_MAX_VALUE);
348     memset(cloudData->authProvider, 0, OIC_STRING_MAX_VALUE);
349     memset(cloudData->ciServer, 0, OIC_STRING_MAX_VALUE);
350     cloudData->userdata = NULL;
351
352     char *authCode = NULL;
353     if (OCRepPayloadGetPropString(input, OC_RSRVD_ES_AUTHCODE, &authCode))
354     {
355         OICStrcpy(gCloudResource.authCode, sizeof(gCloudResource.authCode), authCode);
356         OICStrcpy(cloudData->authCode, sizeof(cloudData->authCode), authCode);
357         OIC_LOG_V(INFO, ES_RH_TAG, "gCloudResource.authCode %s", gCloudResource.authCode);
358     }
359
360     char *authProvider = NULL;
361     if (OCRepPayloadGetPropString(input, OC_RSRVD_ES_AUTHPROVIDER, &authProvider))
362     {
363         OICStrcpy(gCloudResource.authProvider, sizeof(gCloudResource.authProvider), authProvider);
364         OICStrcpy(cloudData->authProvider, sizeof(cloudData->authProvider), authProvider);
365         OIC_LOG_V(INFO, ES_RH_TAG, "gCloudResource.authServerUrl %s", gCloudResource.authProvider);
366     }
367
368     char *ciServer = NULL;
369     if (OCRepPayloadGetPropString(input, OC_RSRVD_ES_CISERVER, &ciServer))
370     {
371         OICStrcpy(gCloudResource.ciServer, sizeof(gCloudResource.ciServer), ciServer);
372         OICStrcpy(cloudData->ciServer, sizeof(cloudData->ciServer), ciServer);
373         OIC_LOG_V(INFO, ES_RH_TAG, "gCloudResource.ciServer %s", gCloudResource.ciServer);
374     }
375
376     if(gReadUserdataCb)
377     {
378         gReadUserdataCb(input, OC_RSRVD_ES_RES_TYPE_CLOUDSERVER, &cloudData->userdata);
379     }
380
381     if(authCode || authProvider || ciServer)
382     {
383         OIC_LOG(INFO, ES_RH_TAG, "Send CloudRsrc Callback To ES");
384
385         // TODO : Need to check appropriateness of gCloudData
386         if(gCloudRsrcEvtCb != NULL)
387         {
388             gCloudRsrcEvtCb(ES_OK, cloudData);
389         }
390         else
391         {
392             OIC_LOG(ERROR, ES_RH_TAG, "gCloudRsrcEvtCb is NULL");
393         }
394     }
395
396     OICFree(cloudData);
397 }
398
399 void updateDevConfResource(OCRepPayload* input)
400 {
401     ESDevConfProvData* devConfData = (ESDevConfProvData*)OICMalloc(sizeof(ESDevConfProvData));
402
403     if(devConfData == NULL)
404     {
405         OIC_LOG(DEBUG, ES_RH_TAG, "OICMalloc is failed");
406         return;
407     }
408     memset(devConfData->language, 0, OIC_STRING_MAX_VALUE);
409     memset(devConfData->country, 0, OIC_STRING_MAX_VALUE);
410     devConfData->userdata = NULL;
411
412     char *country = NULL;
413     if (OCRepPayloadGetPropString(input, OC_RSRVD_ES_COUNTRY, &country))
414     {
415         OICStrcpy(gDevConfResource.country, sizeof(gDevConfResource.country), country);
416         OICStrcpy(devConfData->country, sizeof(devConfData->country), country);
417         OIC_LOG_V(INFO, ES_RH_TAG, "gDevConfResource.country %s", gDevConfResource.country);
418     }
419
420     char *language = NULL;
421     if (OCRepPayloadGetPropString(input, OC_RSRVD_ES_LANGUAGE, &language))
422     {
423         OICStrcpy(gDevConfResource.language, sizeof(gDevConfResource.language), language);
424         OICStrcpy(devConfData->language, sizeof(devConfData->language), language);
425         OIC_LOG_V(INFO, ES_RH_TAG, "gDevConfResource.language %s", gDevConfResource.language);
426     }
427
428     if(gReadUserdataCb)
429     {
430         gReadUserdataCb(input, OC_RSRVD_ES_RES_TYPE_DEVCONF, &devConfData->userdata);
431     }
432
433     if(country || language)
434     {
435         OIC_LOG(INFO, ES_RH_TAG, "Send DevConfRsrc Callback To ES");
436
437         // TODO : Need to check appropriateness of gDevConfData
438         if(gDevConfRsrcEvtCb != NULL)
439         {
440             gDevConfRsrcEvtCb(ES_OK, devConfData);
441         }
442         else
443         {
444             OIC_LOG(ERROR, ES_RH_TAG, "gDevConfRsrcEvtCb is NULL");
445         }
446     }
447
448     OICFree(devConfData);
449 }
450
451 OCRepPayload* constructResponseOfWiFi()
452 {
453     OCRepPayload* payload = OCRepPayloadCreate();
454     if (!payload)
455     {
456         OIC_LOG(ERROR, ES_RH_TAG, "Failed to allocate Payload");
457         return NULL;
458     }
459
460     OIC_LOG(INFO, ES_RH_TAG, "constructResponse wifi res");
461     OCRepPayloadSetUri(payload, OC_RSRVD_ES_URI_WIFI);
462
463     size_t dimensions[MAX_REP_ARRAY_DEPTH] = {gWiFiResource.numMode, 0, 0};
464     int64_t *modes_64 = (int64_t *)OICMalloc(gWiFiResource.numMode * sizeof(int64_t));
465     for(int i = 0 ; i < gWiFiResource.numMode ; ++i)
466     {
467         modes_64[i] = gWiFiResource.supportedMode[i];
468     }
469     OCRepPayloadSetIntArray(payload, OC_RSRVD_ES_SUPPORTEDWIFIMODE, (int64_t *)modes_64, dimensions);
470
471     OCRepPayloadSetPropInt(payload, OC_RSRVD_ES_SUPPORTEDWIFIFREQ, gWiFiResource.supportedFreq);
472     OCRepPayloadSetPropString(payload, OC_RSRVD_ES_SSID, gWiFiResource.ssid);
473     OCRepPayloadSetPropString(payload, OC_RSRVD_ES_CRED, gWiFiResource.cred);
474     OCRepPayloadSetPropInt(payload, OC_RSRVD_ES_AUTHTYPE, (int) gWiFiResource.authType);
475     OCRepPayloadSetPropInt(payload, OC_RSRVD_ES_ENCTYPE, (int) gWiFiResource.encType);
476
477     if(gWriteUserdataCb)
478     {
479         gWriteUserdataCb(payload, OC_RSRVD_ES_RES_TYPE_WIFI);
480     }
481
482     return payload;
483 }
484
485 OCRepPayload* constructResponseOfCloud()
486 {
487     OCRepPayload* payload = OCRepPayloadCreate();
488     if (!payload)
489     {
490         OIC_LOG(ERROR, ES_RH_TAG, "Failed to allocate Payload");
491         return NULL;
492     }
493
494     OIC_LOG(INFO, ES_RH_TAG, "constructResponse prov res");
495     OCRepPayloadSetUri(payload, OC_RSRVD_ES_URI_CLOUDSERVER);
496     OCRepPayloadSetPropString(payload, OC_RSRVD_ES_AUTHCODE, gCloudResource.authCode);
497     OCRepPayloadSetPropString(payload, OC_RSRVD_ES_AUTHPROVIDER, gCloudResource.authProvider);
498     OCRepPayloadSetPropString(payload, OC_RSRVD_ES_CISERVER, gCloudResource.ciServer);
499
500     if(gWriteUserdataCb)
501     {
502         gWriteUserdataCb(payload, OC_RSRVD_ES_RES_TYPE_CLOUDSERVER);
503     }
504
505     return payload;
506 }
507
508 OCRepPayload* constructResponseOfDevConf()
509 {
510     OCRepPayload* payload = OCRepPayloadCreate();
511     if (!payload)
512     {
513         OIC_LOG(ERROR, ES_RH_TAG, "Failed to allocate Payload");
514         return NULL;
515     }
516
517     OIC_LOG(INFO, ES_RH_TAG, "constructResponse prov res");
518     OCRepPayloadSetUri(payload, OC_RSRVD_ES_URI_DEVCONF);
519     OCRepPayloadSetPropString(payload, OC_RSRVD_ES_DEVNAME, gDevConfResource.devName);
520     OCRepPayloadSetPropString(payload, OC_RSRVD_ES_LANGUAGE, gDevConfResource.language);
521     OCRepPayloadSetPropString(payload, OC_RSRVD_ES_COUNTRY, gDevConfResource.country);
522
523     if(gWriteUserdataCb)
524     {
525         gWriteUserdataCb(payload, OC_RSRVD_ES_RES_TYPE_DEVCONF);
526     }
527
528     return payload;
529 }
530
531 OCRepPayload* constructResponseOfProv(OCEntityHandlerRequest *ehRequest)
532 {
533     OCRepPayload* payload = OCRepPayloadCreate();
534     if (!payload)
535     {
536         OIC_LOG(ERROR, ES_RH_TAG, "Failed to allocate Payload");
537         return NULL;
538     }
539
540     OIC_LOG(INFO, ES_RH_TAG, "constructResponse prov res");
541     OCRepPayloadSetUri(payload, OC_RSRVD_ES_URI_PROV);
542     OCRepPayloadSetPropInt(payload, OC_RSRVD_ES_PROVSTATUS, gProvResource.status);
543     OCRepPayloadSetPropInt(payload, OC_RSRVD_ES_LAST_ERRORCODE, gProvResource.lastErrCode);
544     OCRepPayloadSetPropString(payload, OC_RSRVD_ES_LINKS, gProvResource.ocfWebLinks);
545
546     if(gWriteUserdataCb)
547     {
548         gWriteUserdataCb(payload, OC_RSRVD_ES_RES_TYPE_PROV);
549     }
550
551     if(ehRequest->query)
552     {
553         if(strstr(ehRequest->query, OC_RSRVD_INTERFACE_BATCH))
554         {// When Provisioning resource has a GET with BatchInterface
555             OCRepPayload* head = payload;
556             OCRepPayload* nextPayload = NULL;
557
558             nextPayload = constructResponseOfWiFi();
559             if(nextPayload != NULL)
560             {
561                 payload->next = nextPayload;
562                 payload = payload->next;
563             }
564
565             nextPayload = constructResponseOfCloud();
566             if(nextPayload != NULL)
567             {
568                 payload->next = nextPayload;
569                 payload = payload->next;
570             }
571
572             nextPayload = constructResponseOfDevConf();
573             if(nextPayload != NULL)
574             {
575                 payload->next = nextPayload;
576                 payload = payload->next;
577             }
578
579             payload = head;
580         }
581     }
582
583     return payload;
584 }
585
586
587 OCStackResult CreateEasySetupResources(bool isSecured, ESResourceMask resourceMask)
588 {
589     OCStackResult res = OC_STACK_ERROR;
590     bool maskFlag = false;
591
592     res = initProvResource(isSecured);
593     if(res != OC_STACK_OK)
594     {
595         // TODO: destroy logic will be added
596         OIC_LOG_V(ERROR, ES_RH_TAG, "initProvResource result: %s", getResult(res));
597
598         return res;
599     }
600
601     if((resourceMask & ES_WIFI_RESOURCE) == ES_WIFI_RESOURCE)
602     {
603         maskFlag = true;
604         res = initWiFiResource(isSecured);
605         if(res != OC_STACK_OK)
606         {
607             OIC_LOG_V(ERROR, ES_RH_TAG, "initWiFiResource result: %s", getResult(res));
608             return res;
609         }
610
611         res = OCBindResource(gProvResource.handle, gWiFiResource.handle);
612         if(res != OC_STACK_OK)
613         {
614             OIC_LOG_V(ERROR, ES_RH_TAG, "Bind WiFiResource result: %s", getResult(res));
615             return res;
616         }
617
618     }
619
620     if((resourceMask & ES_CLOUD_RESOURCE) == ES_CLOUD_RESOURCE)
621     {
622         maskFlag = true;
623         res = initCloudServerResource(isSecured);
624         if(res != OC_STACK_OK)
625         {
626             OIC_LOG_V(ERROR, ES_RH_TAG, "initCloudResource result: %s", getResult(res));
627             return res;
628         }
629
630         res = OCBindResource(gProvResource.handle, gCloudResource.handle);
631         if(res != OC_STACK_OK)
632         {
633             OIC_LOG_V(ERROR, ES_RH_TAG, "Bind CloudResource result: %s", getResult(res));
634             return res;
635         }
636     }
637
638     if((resourceMask & ES_DEVCONF_RESOURCE) == ES_DEVCONF_RESOURCE)
639     {
640         maskFlag = true;
641         res = initDevConfResource(isSecured);
642         if(res != OC_STACK_OK)
643         {
644             OIC_LOG_V(ERROR, ES_RH_TAG, "initDevConf result: %s", getResult(res));
645             return res;
646         }
647
648         res = OCBindResource(gProvResource.handle, gDevConfResource.handle);
649         if(res != OC_STACK_OK)
650         {
651             OIC_LOG_V(ERROR, ES_RH_TAG, "Bind DevConfResource result: %s", getResult(res));
652             return res;
653         }
654     }
655
656
657     if(maskFlag == false)
658     {
659         OIC_LOG_V(ERROR, ES_RH_TAG, "Invalid ResourceMask");
660         return OC_STACK_ERROR;
661
662     }
663
664     OIC_LOG_V(INFO, ES_RH_TAG, "Created all resources with result: %s", getResult(res));
665
666     return res;
667 }
668
669 OCStackResult DeleteProvisioningResource()
670 {
671     OCStackResult res = OCDeleteResource(gProvResource.handle);
672     if (res != OC_STACK_OK)
673     {
674         OIC_LOG_V(INFO, ES_RH_TAG, "Deleting Prov resource error with result: %s", getResult(res));
675     }
676
677     return res;
678 }
679
680 OCStackResult DeleteEasySetupResources()
681 {
682     OCStackResult res = OC_STACK_ERROR;
683     if (gWiFiResource.handle != NULL)
684     {
685         res = OCUnBindResource(gProvResource.handle, gWiFiResource.handle);
686         if(res != OC_STACK_OK)
687         {
688             OIC_LOG_V(ERROR, ES_RH_TAG, "Unbind WiFi resource error with result: %s", getResult(res));
689         }
690     }
691     if (gCloudResource.handle != NULL)
692     {
693         res = OCUnBindResource(gProvResource.handle, gCloudResource.handle);
694         if(res != OC_STACK_OK)
695         {
696             OIC_LOG_V(ERROR, ES_RH_TAG, "Unbind CloudServer resource error with result: %s", getResult(res));
697         }
698     }
699     if (gDevConfResource.handle != NULL)
700     {
701         res = OCUnBindResource(gProvResource.handle, gDevConfResource.handle);
702         if(res != OC_STACK_OK)
703         {
704             OIC_LOG_V(ERROR, ES_RH_TAG, "Unbind DevConf resource error with result: %s", getResult(res));
705         }
706     }
707
708     if (gWiFiResource.handle != NULL)
709     {
710         res = OCDeleteResource(gWiFiResource.handle);
711         if (res != OC_STACK_OK)
712         {
713             OIC_LOG_V(ERROR, ES_RH_TAG, "Deleting WiFi resource error with result: %s", getResult(res));
714         }
715     }
716
717     if(gCloudResource.handle != NULL)
718     {
719         res = OCDeleteResource(gCloudResource.handle);
720         if (res != OC_STACK_OK)
721         {
722             OIC_LOG_V(ERROR, ES_RH_TAG, "Deleting CloudServer resource error with result: %s", getResult(res));
723         }
724     }
725
726     if(gDevConfResource.handle != NULL)
727     {
728         res = OCDeleteResource(gDevConfResource.handle);
729         if (res != OC_STACK_OK)
730         {
731             OIC_LOG_V(ERROR, ES_RH_TAG, "Deleting DevConf resource error with result: %s", getResult(res));
732         }
733     }
734
735     if(gProvResource.handle != NULL)
736     {
737         res = OCDeleteResource(gProvResource.handle);
738         if (res != OC_STACK_OK)
739         {
740             OIC_LOG_V(ERROR, ES_RH_TAG, "Deleting Prov resource error with result: %s", getResult(res));
741         }
742     }
743
744     return res;
745 }
746
747 OCEntityHandlerResult ProcessGetRequest(OCEntityHandlerRequest *ehRequest, OCRepPayload **payload)
748 {
749     OCEntityHandlerResult ehResult = OC_EH_ERROR;
750     if (!ehRequest)
751     {
752         OIC_LOG(ERROR, ES_RH_TAG, "Request is Null");
753         return ehResult;
754     }
755     if (ehRequest->payload && ehRequest->payload->type != PAYLOAD_TYPE_REPRESENTATION)
756     {
757         OIC_LOG(ERROR, ES_RH_TAG, "Incoming payload not a representation");
758         return ehResult;
759     }
760
761     OCRepPayload *getResp = NULL;
762
763     if(ehRequest->resource == gProvResource.handle)
764     {
765         getResp = constructResponseOfProv(ehRequest);
766     }
767     else if(ehRequest->resource == gWiFiResource.handle)
768     {
769         getResp = constructResponseOfWiFi();
770     }
771     else if(ehRequest->resource == gCloudResource.handle)
772     {
773         getResp = constructResponseOfCloud();
774     }
775     else if(ehRequest->resource == gDevConfResource.handle)
776     {
777         getResp = constructResponseOfDevConf();
778     }
779
780     if (!getResp)
781     {
782         OIC_LOG(ERROR, ES_RH_TAG, "constructResponse failed");
783         return OC_EH_ERROR;
784     }
785
786     *payload = getResp;
787     ehResult = OC_EH_OK;
788
789     return ehResult;
790 }
791
792 OCEntityHandlerResult ProcessPostRequest(OCEntityHandlerRequest *ehRequest, OCRepPayload** payload)
793 {
794     OIC_LOG(INFO, ES_RH_TAG, "ProcessPostRequest enter");
795     OCEntityHandlerResult ehResult = OC_EH_ERROR;
796     if (ehRequest->payload && ehRequest->payload->type != PAYLOAD_TYPE_REPRESENTATION)
797     {
798         OIC_LOG(ERROR, ES_RH_TAG, "Incoming payload not a representation");
799         return ehResult;
800     }
801
802     OCRepPayload* input = (OCRepPayload*) (ehRequest->payload);
803     if (!input)
804     {
805         OIC_LOG(ERROR, ES_RH_TAG, "Failed to parse");
806         return ehResult;
807     }
808
809     if(ehRequest->resource == gProvResource.handle)
810     {
811         updateProvResource(ehRequest, input);
812     }
813     else if(ehRequest->resource == gWiFiResource.handle)
814     {
815         updateWiFiResource(input);
816     }
817     else if(ehRequest->resource == gCloudResource.handle)
818     {
819         updateCloudResource(input);
820     }
821     else if(ehRequest->resource == gDevConfResource.handle)
822     {
823         updateDevConfResource(input);
824     }
825
826     OCRepPayload *getResp = NULL;
827     if(ehRequest->resource == gProvResource.handle)
828     {
829         getResp = constructResponseOfProv(ehRequest);
830     }
831     else if(ehRequest->resource == gWiFiResource.handle)
832     {
833         getResp = constructResponseOfWiFi();
834     }
835     else if(ehRequest->resource == gCloudResource.handle)
836     {
837         getResp = constructResponseOfCloud();
838     }
839     else if(ehRequest->resource == gDevConfResource.handle)
840     {
841         getResp = constructResponseOfDevConf();
842     }
843
844     if (!getResp)
845     {
846         OIC_LOG(ERROR, ES_RH_TAG, "constructResponse failed");
847         return OC_EH_ERROR;
848     }
849
850     *payload = getResp;
851     ehResult = OC_EH_OK;
852
853     return ehResult;
854 }
855
856 OCEntityHandlerResult ProcessPutRequest(OCEntityHandlerRequest * ehRequest,
857         OCRepPayload** payload)
858 {
859     (void) ehRequest;
860     (void) payload;
861     OCEntityHandlerResult ehResult = OC_EH_ERROR;
862
863     return ehResult;
864 }
865 /**
866  * This is the entity handler for the registered resource.
867  * This is invoked by OCStack whenever it recevies a request for this resource.
868  */
869 OCEntityHandlerResult OCEntityHandlerCb(OCEntityHandlerFlag flag,
870         OCEntityHandlerRequest* entityHandlerRequest, void *callback)
871 {
872     (void) callback;
873     OCEntityHandlerResult ehRet = OC_EH_OK;
874     OCEntityHandlerResponse response =
875     { 0, 0, OC_EH_ERROR, 0, 0,
876     { },
877     { 0 }, false };
878     OCRepPayload* payload = NULL;
879
880     if (entityHandlerRequest && (flag & OC_REQUEST_FLAG))
881     {
882         if (OC_REST_GET == entityHandlerRequest->method)
883         {
884             OIC_LOG(INFO, ES_RH_TAG, "Received GET request");
885             ehRet = ProcessGetRequest(entityHandlerRequest, &payload);
886         }
887         else if (OC_REST_PUT == entityHandlerRequest->method)
888         {
889             OIC_LOG(INFO, ES_RH_TAG, "Received PUT request");
890
891             //PUT request will be handled in the internal implementation
892             if (gProvResource.handle != NULL)
893             {
894                 ehRet = ProcessPutRequest(entityHandlerRequest, &payload);
895             }
896             else
897             {
898                 OIC_LOG(ERROR, ES_RH_TAG, "Cannot process put");
899                 ehRet = OC_EH_ERROR;
900             }
901         }
902         else if (OC_REST_POST == entityHandlerRequest->method)
903         {
904             OIC_LOG(INFO, ES_RH_TAG, "Received OC_REST_POST from client");
905             if (gProvResource.handle != NULL)
906             {
907                 ehRet = ProcessPostRequest(entityHandlerRequest, &payload);
908             }
909             else
910             {
911                 OIC_LOG(ERROR, ES_RH_TAG, "Cannot process put");
912                 ehRet = OC_EH_ERROR;
913             }
914         }
915
916         if (ehRet == OC_EH_OK)
917         {
918             // Format the response.  Note this requires some info about the request
919             response.requestHandle = entityHandlerRequest->requestHandle;
920             response.resourceHandle = entityHandlerRequest->resource;
921             response.ehResult = ehRet;
922             //response uses OCPaylod while all get,put methodes use OCRepPayload
923             response.payload = (OCPayload*) (payload);
924             response.numSendVendorSpecificHeaderOptions = 0;
925             memset(response.sendVendorSpecificHeaderOptions, 0,
926                     sizeof(response.sendVendorSpecificHeaderOptions));
927             memset(response.resourceUri, 0, sizeof(response.resourceUri));
928             // Indicate that response is NOT in a persistent buffer
929             response.persistentBufferFlag = 0;
930
931             // Send the response
932             if (OCDoResponse(&response) != OC_STACK_OK)
933             {
934                 OIC_LOG(ERROR, ES_RH_TAG, "Error sending response");
935                 ehRet = OC_EH_ERROR;
936             }
937         }
938     }
939
940     return ehRet;
941 }
942
943 OCStackResult SetDeviceProperty(ESDeviceProperty *deviceProperty)
944 {
945     OIC_LOG(INFO, ES_RH_TAG, "SetDeviceProperty IN");
946
947     gWiFiResource.supportedFreq = (deviceProperty->WiFi).freq;
948     OIC_LOG_V(INFO, ES_RH_TAG, "WiFi Freq : %d", gWiFiResource.supportedFreq);
949
950     int modeIdx = 0;
951     while((deviceProperty->WiFi).mode[modeIdx] != WiFi_EOF)
952     {
953         gWiFiResource.supportedMode[modeIdx] = (deviceProperty->WiFi).mode[modeIdx];
954         OIC_LOG_V(INFO, ES_RH_TAG, "WiFi Mode : %d", gWiFiResource.supportedMode[modeIdx]);
955         modeIdx ++;
956     }
957     gWiFiResource.numMode = modeIdx;
958
959     OICStrcpy(gDevConfResource.devName, MAX_DEVICELEN, (deviceProperty->DevConf).deviceName);
960     OIC_LOG_V(INFO, ES_RH_TAG, "Device Name : %s", gDevConfResource.devName);
961
962     OIC_LOG(INFO, ES_RH_TAG, "SetDeviceProperty OUT");
963     return OC_STACK_OK;
964 }
965
966 OCStackResult SetEnrolleeState(ESEnrolleeState esState)
967 {
968     OIC_LOG(INFO, ES_RH_TAG, "SetEnrolleeState IN");
969
970     gProvResource.status = esState;
971     OIC_LOG_V(INFO, ES_RH_TAG, "Enrollee Status : %d", gProvResource.status);
972
973     OIC_LOG(INFO, ES_RH_TAG, "SetEnrolleeState OUT");
974     return OC_STACK_OK;
975 }
976
977 OCStackResult SetEnrolleeErrCode(ESErrorCode esErrCode)
978 {
979     OIC_LOG(INFO, ES_RH_TAG, "SetEnrolleeErrCode IN");
980
981     gProvResource.lastErrCode = esErrCode;
982     OIC_LOG_V(INFO, ES_RH_TAG, "Enrollee ErrorCode : %d", gProvResource.lastErrCode);
983
984     OIC_LOG(INFO, ES_RH_TAG, "SetEnrolleeErrCode OUT");
985     return OC_STACK_OK;
986 }
987
988 const char *getResult(OCStackResult result)
989 {
990     switch (result)
991     {
992         case OC_STACK_OK:
993             return "OC_STACK_OK";
994         case OC_STACK_INVALID_URI:
995             return "OC_STACK_INVALID_URI";
996         case OC_STACK_INVALID_QUERY:
997             return "OC_STACK_INVALID_QUERY";
998         case OC_STACK_INVALID_IP:
999             return "OC_STACK_INVALID_IP";
1000         case OC_STACK_INVALID_PORT:
1001             return "OC_STACK_INVALID_PORT";
1002         case OC_STACK_INVALID_CALLBACK:
1003             return "OC_STACK_INVALID_CALLBACK";
1004         case OC_STACK_INVALID_METHOD:
1005             return "OC_STACK_INVALID_METHOD";
1006         case OC_STACK_NO_MEMORY:
1007             return "OC_STACK_NO_MEMORY";
1008         case OC_STACK_COMM_ERROR:
1009             return "OC_STACK_COMM_ERROR";
1010         case OC_STACK_INVALID_PARAM:
1011             return "OC_STACK_INVALID_PARAM";
1012         case OC_STACK_NOTIMPL:
1013             return "OC_STACK_NOTIMPL";
1014         case OC_STACK_NO_RESOURCE:
1015             return "OC_STACK_NO_RESOURCE";
1016         case OC_STACK_RESOURCE_ERROR:
1017             return "OC_STACK_RESOURCE_ERROR";
1018         case OC_STACK_SLOW_RESOURCE:
1019             return "OC_STACK_SLOW_RESOURCE";
1020         case OC_STACK_NO_OBSERVERS:
1021             return "OC_STACK_NO_OBSERVERS";
1022         case OC_STACK_ERROR:
1023             return "OC_STACK_ERROR";
1024         default:
1025             return "UNKNOWN";
1026     }
1027 }