e6707e2cf861b9866e1ca0ef4b8e269becf2cb21
[platform/upstream/iotivity.git] / resource / csdk / connectivity / samples / android / sample_service / jni / ResourceModel.c
1 #include <jni.h>
2 #include <android/log.h>
3 #include <stdio.h>
4 #include <dlfcn.h>
5 #include <stdlib.h>
6 #include <string.h>
7
8 #include <../../../../api/cainterface.h>
9 #include <../../../../api/cacommon.h>
10 #include "com_iotivity_service_RMInterface.h"
11
12 #define  LOG_TAG   "JNI_INTERFACE_SAMPLE"
13 #define  LOGI(...) __android_log_print(ANDROID_LOG_INFO, LOG_TAG, __VA_ARGS__)
14 #define  LOGE(...) __android_log_print(ANDROID_LOG_ERROR, LOG_TAG, __VA_ARGS__)
15
16 /**
17  * @def RS_IDENTITY
18  * @brief
19  */
20 #define IDENTITY     ("1111111111111111")
21 /* @def RS_CLIENT_PSK
22  * @brief
23  */
24 #define RS_CLIENT_PSK   ("AAAAAAAAAAAAAAAA")
25
26 int gReceived;
27 CABool_t gLocalUnicastPort;
28 CABool_t gLocalSecurePort;
29
30 void request_handler(const CARemoteEndpoint_t* object, const CARequestInfo_t* requestInfo);
31 void response_handler(const CARemoteEndpoint_t* object, const CAResponseInfo_t* responseInfo);
32 void send_response(const CARemoteEndpoint_t* endpoint, CAToken_t request_token);
33 void get_resource_uri(char *URI, char *resourceURI, int length);
34 int get_secure_information(CAPayload_t payLoad);
35 CAResult_t get_network_type(int selectedNetwork);
36 void callback(char *subject, char *receivedData);
37
38 CAConnectivityType_t gSelectedNwType;
39 static CAToken_t gLastRequestToken = NULL;
40 static const char *gSecureInfoData = "{\"oc\":[{\"href\":\"%s\",\"prop\":{\"rt\":[\"core.led\"],"
41                                      "\"if\":[\"oc.mi.def\"],\"obs\":1,\"sec\":1,\"port\":%d}}]}";
42 static const char *gNormalInfoData = "{\"oc\":[{\"href\":\"%s\",\"prop\":{\"rt\":[\"core.led\"],"
43                                      "\"if\":[\"oc.mi.def\"],\"obs\":1}}]}";
44
45 static jobject gResponseListenerObject = NULL;
46 extern JavaVM *g_jvm;
47
48 static CARemoteEndpoint_t* clientEndpoint =NULL;
49 static CAToken_t clientToken;
50
51 // init
52 JNIEXPORT void JNICALL Java_com_iotivity_service_RMInterface_setNativeResponseListener(JNIEnv *env, jobject obj, jobject listener){
53     LOGI("setNativeResponseListener");
54     gResponseListenerObject = (*env)->NewGlobalRef(env, obj);
55 }
56
57 #ifdef __WITH_DTLS__
58 static OCDtlsPskCredsBlob *pskCredsBlob = NULL;
59
60 void clearDtlsCredentialInfo()
61 {
62     printf("clearDtlsCredentialInfo IN\n");
63     if (pskCredsBlob)
64     {
65         // Initialize sensitive data to zeroes before freeing.
66         memset(pskCredsBlob->creds, 0, sizeof(OCDtlsPskCredsBlob)*(pskCredsBlob->num));
67         free(pskCredsBlob->creds);
68
69         memset(pskCredsBlob, 0, sizeof(OCDtlsPskCredsBlob));
70         free(pskCredsBlob);
71         pskCredsBlob = NULL;
72     }
73     printf("clearDtlsCredentialInfo OUT\n");
74 }
75
76 // Internal API. Invoked by OC stack to retrieve credentials from this module
77 void CAGetDtlsPskCredentials(OCDtlsPskCredsBlob **credInfo)
78 {
79     printf("CAGetDtlsPskCredentials IN\n");
80
81     *credInfo = pskCredsBlob;
82
83     printf("CAGetDtlsPskCredentials OUT\n");
84 }
85
86 int32_t SetCredentials()
87 {
88     printf("SetCredentials IN\n");
89     pskCredsBlob = (OCDtlsPskCredsBlob *)malloc(sizeof(OCDtlsPskCredsBlob));
90
91     memset(pskCredsBlob, 0x0, sizeof(OCDtlsPskCredsBlob));
92     memcpy(pskCredsBlob->rsIdentity, IDENTITY, DTLS_PSK_ID_LEN);
93
94     pskCredsBlob->num = 1;
95
96     pskCredsBlob->creds = (OCDtlsPskCredsBlob *)malloc(sizeof(OCDtlsPskCredsBlob) *(pskCredsBlob->num));
97
98     memcpy(pskCredsBlob->creds[0].clientIdentity, IDENTITY, DTLS_PSK_ID_LEN);
99     memcpy(pskCredsBlob->creds[0].rsClientPsk, RS_CLIENT_PSK, DTLS_PSK_PSK_LEN);
100
101     printf("SetCredentials OUT\n");
102     return 1;
103 }
104 #endif
105
106 JNIEXPORT jint JNI_OnLoad(JavaVM *jvm, void *reserved)
107 {
108     printf("JNI_OnLoad");
109
110     JNIEnv* env;
111     if((*jvm)->GetEnv(jvm, (void**)&env, JNI_VERSION_1_6) != JNI_OK)
112     {
113         return -1;
114     }
115     g_jvm = jvm;  /* cache the JavaVM pointer */
116
117     CANativeJNISetJavaVM(g_jvm);
118
119     return JNI_VERSION_1_6;
120 }
121
122 void JNI_OnUnload(JavaVM *jvm, void *reserved)
123 {
124     printf("JNI_OnUnload");
125
126     JNIEnv* env;
127     if((*jvm)->GetEnv(jvm, (void**)&env, JNI_VERSION_1_6) != JNI_OK)
128     {
129         return;
130     }
131     g_jvm = 0;
132     return;
133 }
134
135 JNIEXPORT void JNICALL Java_com_iotivity_service_RMInterface_RMInitialize
136   (JNIEnv *env, jobject obj, jobject context)
137 {
138     LOGI("RMInitialize");
139
140     //Currently set context for Android Platform
141     CANativeJNISetContext(env, context);
142
143     CAResult_t res;
144
145 #ifdef __WITH_DTLS__
146     if (SetCredentials() == 0)
147     {
148         printf("SetCredentials failed\n");
149     }
150
151     res = CARegisterDTLSCredentialsHandler(CAGetDtlsPskCredentials);
152     if(res != CA_STATUS_OK)
153     {
154         printf("Set credential handler fail\n");
155     }
156 #endif
157
158     if(CA_STATUS_OK != CAInitialize())
159     {
160         LOGI("Could not Initialize");
161     }
162 }
163
164 JNIEXPORT void JNICALL Java_com_iotivity_service_RMInterface_RMTerminate(JNIEnv *env, jobject obj)
165 {
166     LOGI("RMTerminate");
167
168     CATerminate();
169 }
170
171 JNIEXPORT void JNICALL Java_com_iotivity_service_RMInterface_RMStartListeningServer(JNIEnv *env,
172     jobject obj)
173 {
174     LOGI("RMStartListeningServer");
175
176     if(CA_STATUS_OK != CAStartListeningServer())
177     {
178         LOGI("Could not start Listening server");
179     }
180 }
181
182 JNIEXPORT void JNICALL Java_com_iotivity_service_RMInterface_RMStartDiscoveryServer(JNIEnv *env,
183     jobject obj)
184 {
185     LOGI("RMStartDiscoveryServer");
186
187     if(CA_STATUS_OK != CAStartDiscoveryServer())
188     {
189         LOGI("Could not start discovery server");
190     }
191 }
192
193 JNIEXPORT void JNICALL Java_com_iotivity_service_RMInterface_RMRegisterHandler(JNIEnv *env,
194     jobject obj)
195 {
196     LOGI("RMRegisterHandler");
197
198     CARegisterHandler(request_handler, response_handler);
199 }
200
201 JNIEXPORT void JNICALL Java_com_iotivity_service_RMInterface_RMFindResource(JNIEnv *env, jobject obj,
202     jstring uri)
203 {
204     const char* strUri = (*env)->GetStringUTFChars(env, uri, NULL);
205     LOGI("RMFindResource - %s", strUri);
206
207     // create token
208     CAToken_t token = NULL;
209     CAResult_t res = CAGenerateToken(&token);
210     if (res != CA_STATUS_OK)
211     {
212         printf("token generate error!!\n");
213         token = NULL;
214     }
215
216     LOGI("generated token %s\n", (token != NULL) ? token : "");
217
218     if(CA_STATUS_OK != CAFindResource((const CAURI_t)strUri, token))
219     {
220         LOGI("Could not find resource");
221     }
222     else
223     {
224         LOGI("find resource to %s URI", strUri);
225         gLastRequestToken = token;
226     }
227 }
228
229 JNIEXPORT void JNICALL Java_com_iotivity_service_RMInterface_RMSendRequest(JNIEnv *env, jobject obj,
230     jstring uri, jstring payload, jint selectedNetwork, jint isSecured, jint msgType)
231 {
232     const char* strUri = (*env)->GetStringUTFChars(env, uri, NULL);
233     LOGI("RMSendRequest - %s", strUri);
234
235     CAResult_t res;
236
237     LOGI("selectedNetwork - %d", selectedNetwork);
238     res = get_network_type(selectedNetwork);
239     if (res != CA_STATUS_OK)
240     {
241         return;
242     }
243
244     //create remote endpoint
245     CARemoteEndpoint_t* endpoint = NULL;
246
247     if(CA_STATUS_OK != CACreateRemoteEndpoint((const CAURI_t)strUri, gSelectedNwType, &endpoint))
248     {
249         LOGI("Could not create remote end point");
250         CADestroyRemoteEndpoint(endpoint);
251         return;
252     }
253
254     CAMessageType_t messageType = msgType;
255
256     // create token
257     CAToken_t token = NULL;
258     res = CAGenerateToken(&token);
259     if (res != CA_STATUS_OK)
260     {
261         printf("token generate error!!\n");
262         token = NULL;
263     }
264
265     char resourceURI[15] = {0};
266
267     get_resource_uri((const CAURI_t)strUri, resourceURI, 14);
268
269     CAInfo_t requestData;
270     memset(&requestData, 0, sizeof(CAInfo_t));
271     requestData.token = token;
272
273     const char* strPayload = (*env)->GetStringUTFChars(env, payload, NULL);
274     if (isSecured == 1)
275     {
276         int length = strlen(gSecureInfoData) + strlen(resourceURI) + 1;
277         requestData.payload = (CAPayload_t) malloc(length);
278         sprintf(requestData.payload, gSecureInfoData, resourceURI, gLocalSecurePort);
279     }
280     else
281     {
282         int length = strlen(strPayload) + strlen(resourceURI) + 1;
283         requestData.payload = (CAPayload_t) malloc(length);
284         sprintf(requestData.payload, strPayload, resourceURI);
285     }
286
287     requestData.type = messageType;
288
289     CARequestInfo_t requestInfo;
290     memset(&requestInfo, 0, sizeof(CARequestInfo_t));
291     requestInfo.method = CA_GET;
292     requestInfo.info = requestData;
293
294     // send request
295     if(CA_STATUS_OK != CASendRequest(endpoint, &requestInfo))
296     {
297         LOGI("Could not send request");
298     }
299
300     // destroy token
301     if (token != NULL)
302     {
303         CADestroyToken(token);
304     }
305
306     // destroy remote endpoint
307     if (endpoint != NULL)
308     {
309         CADestroyRemoteEndpoint(endpoint);
310     }
311 }
312
313 JNIEXPORT void JNICALL Java_com_iotivity_service_RMInterface_RMSendResponse(JNIEnv *env,
314     jobject obj, jint selectedNetwork, jint isSecured, jint msgType, jint responseValue)
315 {
316     LOGI("RMSendResponse");
317
318     CAResult_t res;
319
320     LOGI("selectedNetwork - %d", selectedNetwork);
321
322     res = get_network_type(selectedNetwork);
323     if (res != CA_STATUS_OK)
324     {
325         LOGI("Not supported network type");
326         return;
327     }
328
329     if (clientEndpoint == NULL)
330     {
331         LOGI("No Request received");
332         return;
333     }
334
335     CAMessageType_t messageType = msgType;
336
337     CAInfo_t responseData;
338     memset(&responseData, 0, sizeof(CAInfo_t));
339     responseData.token = clientToken;
340
341     if (isSecured == 1)
342     {
343         int length = strlen(gSecureInfoData) + strlen(clientEndpoint->resourceUri) + 1;
344         responseData.payload = (CAPayload_t) malloc(length);
345         sprintf(responseData.payload, gSecureInfoData, clientEndpoint->resourceUri, gLocalSecurePort);
346     }
347     else
348     {
349         int length = strlen("sendResponse Payload") + strlen(clientEndpoint->resourceUri) + 1;
350         responseData.payload = (CAPayload_t) malloc(length);
351         sprintf(responseData.payload, gNormalInfoData, clientEndpoint->resourceUri);
352     }
353
354     responseData.type = messageType;
355
356     CAResponseInfo_t responseInfo;
357     memset(&responseInfo, 0, sizeof(CAResponseInfo_t));
358     responseInfo.result = responseValue;
359     responseInfo.info = responseData;
360
361     // send request
362     if(CA_STATUS_OK != CASendResponse(clientEndpoint, &responseInfo))
363     {
364         LOGI("Could not send response");
365     }
366
367     // destroy token
368     if (clientToken != NULL)
369     {
370         CADestroyToken(clientToken);
371     }
372
373     // destroy remote endpoint
374     if (clientEndpoint != NULL)
375     {
376         CADestroyRemoteEndpoint(clientEndpoint);
377     }
378
379 }
380
381 JNIEXPORT void JNICALL Java_com_iotivity_service_RMInterface_RMAdvertiseResource(JNIEnv *env,
382     jobject obj, jstring uri, jint selectedNetwork)
383 {
384     LOGI("RMAdvertiseResource");
385
386     const char* strUri = (*env)->GetStringUTFChars(env, uri, NULL);
387
388     int optionNum = 2;
389
390     CAHeaderOption_t *headerOpt;
391     headerOpt = (CAHeaderOption_t*) malloc(sizeof(CAHeaderOption_t) * optionNum);
392     if (NULL == headerOpt)
393     {
394         printf("Memory allocation failed!\n");
395         return;
396     }
397     memset(headerOpt, 0, sizeof(CAHeaderOption_t) * optionNum);
398
399     char* tmpOptionData1 = "Hello";
400     headerOpt[0].optionID = 3000;
401     memcpy(headerOpt[0].optionData, tmpOptionData1, strlen(tmpOptionData1));
402     headerOpt[0].optionLength = (uint16_t) strlen(tmpOptionData1);
403
404     char* tmpOptionData2 = "World";
405     headerOpt[1].optionID = 3001;
406     memcpy(headerOpt[1].optionData, tmpOptionData2, strlen(tmpOptionData2));
407     headerOpt[1].optionLength = (uint16_t) strlen(tmpOptionData2);
408
409     // create token
410     CAToken_t token = NULL;
411     CAResult_t res = CAGenerateToken(&token);
412     if (res != CA_STATUS_OK)
413     {
414         LOGI("token generate error!");
415         token = NULL;
416     }
417
418     CAAdvertiseResource((const CAURI_t)strUri, token, headerOpt, (uint8_t) optionNum);
419
420     free(headerOpt);
421 }
422
423 JNIEXPORT void JNICALL Java_com_iotivity_service_RMInterface_RMSendNotification(JNIEnv *env,
424     jobject obj, jstring uri, jstring payload, jint selectedNetwork, jint isSecured)
425 {
426     const char* strUri = (*env)->GetStringUTFChars(env, uri, NULL);
427     LOGI("RMSendNotification - %s", strUri);
428
429     CAResult_t res;
430
431     LOGI("selectedNetwork - %d", selectedNetwork);
432
433     res = get_network_type(selectedNetwork);
434     if (res != CA_STATUS_OK)
435     {
436         LOGI("Not supported network type");
437         return;
438     }
439
440     //create remote endpoint
441     CARemoteEndpoint_t* endpoint = NULL;
442
443     if(CA_STATUS_OK != CACreateRemoteEndpoint((const CAURI_t)strUri, gSelectedNwType, &endpoint))
444     {
445         LOGI("Could not create remote end point");
446         CADestroyRemoteEndpoint(endpoint);
447         return;
448     }
449
450     CAMessageType_t messageType = CA_MSG_NONCONFIRM;
451
452     // create token
453     CAToken_t token = NULL;
454     res = CAGenerateToken(&token);
455     if (res != CA_STATUS_OK)
456     {
457         LOGI("token generate error!");
458         token = NULL;
459     }
460
461     char resourceURI[15] = {0};
462
463     get_resource_uri((const CAURI_t)strUri, resourceURI, 14);
464
465     CAInfo_t responseData;
466     memset(&responseData, 0, sizeof(CAInfo_t));
467     responseData.token = token;
468
469     const char* strPayload = (*env)->GetStringUTFChars(env, payload, NULL);
470     if (isSecured == 1)
471     {
472         int length = strlen(gSecureInfoData) + strlen(resourceURI) + 1;
473         responseData.payload = (CAPayload_t) malloc(length);
474         sprintf(responseData.payload, gSecureInfoData, resourceURI, gLocalSecurePort);
475     }
476     else
477     {
478         int length = strlen(strPayload) + strlen(resourceURI) + 1;
479         responseData.payload = (CAPayload_t) malloc(length);
480         sprintf(responseData.payload, strPayload, resourceURI);
481     }
482
483     responseData.type = messageType;
484
485     CAResponseInfo_t responseInfo;
486     memset(&responseInfo, 0, sizeof(CAResponseInfo_t));
487     responseInfo.result = CA_SUCCESS;
488     responseInfo.info = responseData;
489
490     // send request
491     if(CA_STATUS_OK != CASendNotification(endpoint, &responseInfo))
492     {
493         LOGI("Could not send notification");
494     }
495
496     LOGI("Send Notification");
497
498     // destroy token
499     if (token != NULL)
500     {
501         CADestroyToken(token);
502     }
503
504     // destroy remote endpoint
505     if (endpoint != NULL)
506     {
507         CADestroyRemoteEndpoint(endpoint);
508     }
509 }
510
511 JNIEXPORT void JNICALL Java_com_iotivity_service_RMInterface_RMSelectNetwork(JNIEnv *env, jobject obj,
512     jint networkType)
513 {
514     LOGI("RMSelectNetwork Type : %d", networkType);
515
516     if(CA_STATUS_OK != CASelectNetwork(networkType))
517     {
518         LOGI("Could not select network");
519     }
520 }
521
522 JNIEXPORT void JNICALL Java_com_iotivity_service_RMInterface_RMHandleRequestResponse(JNIEnv *env,
523     jobject obj)
524 {
525     LOGI("RMHandleRequestResponse");
526
527     if(CA_STATUS_OK != CAHandleRequestResponse())
528     {
529         LOGI("Could not handle request and response");
530     }
531 }
532
533 void request_handler(const CARemoteEndpoint_t* object, const CARequestInfo_t* requestInfo)
534 {
535
536     char *cloneUri = NULL;
537     char *cloneRemoteAddress = NULL;
538     char *clonePayload = NULL;
539     char *cloneOptionData = NULL;
540     uint32_t len = 0;
541
542     if (!object)
543     {
544         LOGI("Remote endpoint is NULL!");
545         return;
546     }
547
548     if (!requestInfo)
549     {
550         LOGI("Request info is NULL!");
551         return;
552     }
553
554     LOGI("##########received request from remote device #############\n");
555     LOGI("Uri: %s\n", object->resourceUri);
556     LOGI("Remote Address: %s\n", object->addressInfo.IP.ipAddress);
557     LOGI("Data: %s\n", requestInfo->info.payload);
558     LOGI("Token: %s\n", requestInfo->info.token);
559     LOGI("Code: %d\n", requestInfo->method);
560
561     if (NULL != gResponseListenerObject)
562     {
563         callback("received request from remote device", "#######");
564
565         if (object->resourceUri != NULL)
566         {
567             len = strlen(object->resourceUri);
568             cloneUri = (char *) OICMalloc(sizeof(char) * (len + 1));
569
570             if (cloneUri == NULL)
571             {
572                 LOGI("CACloneRemoteEndpoint Out of memory");
573                 return;
574             }
575
576             memset(cloneUri, 0, sizeof(char) * (len + 1));
577             strncpy(cloneUri, object->resourceUri, len);
578
579             callback("Uri: ", cloneUri);
580             free(cloneUri);
581         }
582
583         len = strlen(object->addressInfo.IP.ipAddress);
584         cloneRemoteAddress = (char *) OICMalloc(sizeof(char) * (len + 1));
585
586         if (cloneRemoteAddress == NULL)
587         {
588             LOGI("CACloneRemoteEndpoint Out of memory");
589             return;
590         }
591
592         memset(cloneRemoteAddress, 0, sizeof(char) * (len + 1));
593         strncpy(cloneRemoteAddress, object->addressInfo.IP.ipAddress, len);
594
595         callback("Remote Address: ", cloneRemoteAddress);
596         free(cloneRemoteAddress);
597
598
599         if(requestInfo->info.payload != NULL)
600         {
601             len = strlen(requestInfo->info.payload);
602             clonePayload = (char *) OICMalloc(sizeof(char) * (len + 1));
603
604             if (clonePayload == NULL)
605             {
606                 LOGI("CACloneRemoteEndpoint Out of memory");
607                 return;
608             }
609
610             memset(clonePayload, 0, sizeof(char) * (len + 1));
611             strncpy(clonePayload, requestInfo->info.payload, len);
612
613             callback("Data: ", clonePayload);
614             free(clonePayload);
615         }
616     }
617
618     if (gLastRequestToken != NULL && requestInfo->info.token != NULL
619         && (strcmp((char *)gLastRequestToken, requestInfo->info.token) == 0))
620     {
621         LOGI("token is same. received request of it's own. skip.. \n");
622         return;
623     }
624
625     if (requestInfo->info.options)
626     {
627         uint32_t len = requestInfo->info.numOptions;
628         uint32_t i;
629
630         LOGI("Option count: %d\n", requestInfo->info.numOptions);
631
632         for (i = 0; i < len; i++)
633         {
634             LOGI("Option %d\n", i + 1);
635             LOGI("ID : %d\n", requestInfo->info.options[i].optionID);
636             LOGI("Data[%d]: %s\n", requestInfo->info.options[i].optionLength,
637                    requestInfo->info.options[i].optionData);
638
639             if (NULL != gResponseListenerObject)
640             {
641                 char optionInfo[1024] = {0,};
642                 sprintf(optionInfo, "Num[%d] - ID : %d, Option Length : %d", i+1,
643                         requestInfo->info.options[i].optionID, requestInfo->info.options[i].optionLength);
644
645                 callback("Option info: ", optionInfo);
646
647                 if (requestInfo->info.options[i].optionData != NULL)
648                 {
649                     uint32_t optionDataLen = strlen(requestInfo->info.options[i].optionData);
650                     cloneOptionData = (char *) OICMalloc(sizeof(char) * (optionDataLen + 1));
651
652                     if (cloneOptionData == NULL)
653                     {
654                         LOGI("CACloneRemoteEndpoint Out of memory");
655                         return;
656                     }
657
658                     memset(cloneOptionData, 0, sizeof(char) * (optionDataLen + 1));
659                     strncpy(cloneOptionData, requestInfo->info.options[i].optionData, optionDataLen);
660
661                     callback("Option Data: ", cloneOptionData);
662                     free(cloneOptionData);
663                 }
664             }
665         }
666     }
667
668     printf("############################################################\n");
669
670     //Check if this has secure communication information
671     if (requestInfo->info.payload && object->resourceUri)
672     {
673         int securePort = get_secure_information(requestInfo->info.payload);
674         if (0 < securePort) //Set the remote endpoint secure details and send response
675         {
676             LOGI("This is secure resource...\n");
677             char *uri = NULL;
678             int length = 0;
679
680             length = 8; //length of "coaps://"
681             length += strlen(object->addressInfo.IP.ipAddress) + 5; // length of "ipaddress:port"
682             length += strlen(object->resourceUri) + 1;
683
684             uri = calloc(1,sizeof(char)*length);
685             if (!uri)
686             {
687                 printf("Failed to create new uri\n");
688                 return;
689             }
690             sprintf(uri,"coaps://%s:%d/%s",object->addressInfo.IP.ipAddress,
691                       securePort, object->resourceUri);
692
693             CARemoteEndpoint_t *endpoint = NULL;
694             if (CA_STATUS_OK != CACreateRemoteEndpoint(uri, object->connectivityType, &endpoint))
695             {
696                 LOGI("Failed to create duplicate of remote endpoint!\n");
697                 return;
698             }
699             endpoint->isSecured = CA_TRUE;
700             object = endpoint;
701         }
702     }
703
704     gReceived = 1;
705
706     clientEndpoint = object;
707     clientToken = requestInfo->info.token;
708 }
709
710 void response_handler(const CARemoteEndpoint_t* object, const CAResponseInfo_t* responseInfo)
711 {
712
713     char *cloneUri = NULL;
714     char *cloneRemoteAddress = NULL;
715     char *clonePayload = NULL;
716     char *cloneOptionData = NULL;
717     uint32_t len = 0;
718
719     LOGI("##########Received response from remote device #############\n");
720     LOGI("Uri: %s\n", object->resourceUri);
721     LOGI("Remote Address: %s\n", object->addressInfo.IP.ipAddress);
722     LOGI("response result: %d\n", responseInfo->result);
723     LOGI("Data: %s\n", responseInfo->info.payload);
724     LOGI("Token: %s\n", responseInfo->info.token);
725     LOGI("Code: %d\n", responseInfo->result);
726
727     if (NULL != gResponseListenerObject)
728     {
729         if (object->resourceUri != NULL)
730         {
731             len = strlen(object->resourceUri);
732             cloneUri = (char *) OICMalloc(sizeof(char) * (len + 1));
733
734             if (cloneUri == NULL)
735             {
736                 LOGI("CACloneRemoteEndpoint Out of memory");
737                 return;
738             }
739
740             memset(cloneUri, 0, sizeof(char) * (len + 1));
741             strncpy(cloneUri, object->resourceUri, len);
742
743             callback("Uri: ", cloneUri);
744             free(cloneUri);
745         }
746
747         len = strlen(object->addressInfo.IP.ipAddress);
748         cloneRemoteAddress = (char *) OICMalloc(sizeof(char) * (len + 1));
749
750         if (cloneRemoteAddress == NULL)
751         {
752             LOGI("CACloneRemoteEndpoint Out of memory");
753             return;
754         }
755
756         memset(cloneRemoteAddress, 0, sizeof(char) * (len + 1));
757         strncpy(cloneRemoteAddress, object->addressInfo.IP.ipAddress, len);
758
759         callback("Remote Address: ", cloneRemoteAddress);
760         free(cloneRemoteAddress);
761
762
763         if(responseInfo->info.payload != NULL)
764         {
765             len = strlen(responseInfo->info.payload);
766             clonePayload = (char *) OICMalloc(sizeof(char) * (len + 1));
767
768             if (clonePayload == NULL)
769             {
770                 LOGI("CACloneRemoteEndpoint Out of memory");
771                 return;
772             }
773
774             memset(clonePayload, 0, sizeof(char) * (len + 1));
775             strncpy(clonePayload, responseInfo->info.payload, len);
776
777             callback("Data: ", clonePayload);
778             free(clonePayload);
779         }
780     }
781
782     if (responseInfo->info.options)
783     {
784         uint32_t len = responseInfo->info.numOptions;
785         uint32_t i;
786         for (i = 0; i < len; i++)
787         {
788             LOGI("Option %d\n", i + 1);
789             LOGI("ID : %d\n", responseInfo->info.options[i].optionID);
790             LOGI("Data[%d]: %s\n", responseInfo->info.options[i].optionLength,
791                       responseInfo->info.options[i].optionData);
792
793             if (NULL != gResponseListenerObject)
794             {
795                 char optionInfo[1024] = {0,};
796                 sprintf(optionInfo, "Num[%d] - ID : %d, Option Length : %d", i+1,
797                         responseInfo->info.options[i].optionID,
798                         responseInfo->info.options[i].optionLength);
799
800                 callback("Option info: ", optionInfo);
801
802                 if (responseInfo->info.options[i].optionData != NULL)
803                 {
804                     uint32_t optionDataLen = strlen(responseInfo->info.options[i].optionData);
805                     cloneOptionData = (char *) OICMalloc(sizeof(char) * (optionDataLen + 1));
806
807                     if (cloneOptionData == NULL)
808                     {
809                         LOGI("CACloneRemoteEndpoint Out of memory");
810                         return;
811                     }
812                     memset(cloneOptionData, 0, sizeof(char) * (optionDataLen + 1));
813                     strncpy(cloneOptionData, responseInfo->info.options[i].optionData, optionDataLen);
814                     callback("Option Data: ", cloneOptionData);
815                     free(cloneOptionData);
816                 }
817             }
818         }
819     }
820     LOGI("############################################################\n");
821     gReceived = 1;
822
823     //Check if this has secure communication information
824     if (responseInfo->info.payload)
825     {
826         int securePort = get_secure_information(responseInfo->info.payload);
827         if (0 < securePort) //Set the remote endpoint secure details and send response
828         {
829             LOGI("This is secure resource...\n");
830         }
831     }
832 }
833
834 void get_resource_uri(char *URI, char *resourceURI, int length)
835 {
836     char *startPos = URI;
837     char *temp = NULL;
838     if (NULL != (temp = strstr(URI, "://")))
839     {
840         startPos = strchr(temp + 3, '/');
841         if (!startPos)
842         {
843             printf("Resource URI is missing\n");
844             return;
845         }
846     }
847
848     char *endPos = strchr(startPos, '?');
849     if (!endPos)
850     {
851         endPos = URI + strlen(URI);
852     }
853     endPos -= 1;
854
855     if (endPos - startPos <= length)
856         memcpy(resourceURI, startPos + 1, endPos - startPos);
857
858     printf("URI: %s, ResourceURI:%s\n", URI, resourceURI);
859 }
860
861 int get_secure_information(CAPayload_t payLoad)
862 {
863     printf("entering get_secure_information\n");
864
865     if (!payLoad)
866     {
867         printf("Payload is NULL\n");
868         return -1;
869     }
870
871     char *subString = NULL;
872     if (NULL == (subString = strstr(payLoad, "\"sec\":1")))
873     {
874         printf("This is not secure resource\n");
875         return -1;
876     }
877
878     if (NULL == (subString = strstr(payLoad, "\"port\":")))
879     {
880         printf("This secure resource does not have port information\n");
881         return -1;
882     }
883
884     char *startPos = strstr(subString, ":");
885     if (!startPos)
886     {
887         printf("Parsing failed !\n");
888         return -1;
889     }
890
891     char *endPos = strstr(startPos, "}");
892     if (!endPos)
893     {
894         printf("Parsing failed !\n");
895         return -1;
896     }
897
898     char portStr[4] = {0};
899     memcpy(portStr, startPos + 1, (endPos-1) - startPos);
900
901     printf("secured port is: %s\n", portStr);
902     return atoi(portStr);
903 }
904
905 CAResult_t get_network_type(int selectedNetwork)
906 {
907
908     int number = selectedNetwork;
909
910     if (!(number & 0xf))
911     {
912         return CA_NOT_SUPPORTED;
913     }
914     if (number & CA_ETHERNET)
915     {
916         gSelectedNwType = CA_ETHERNET;
917         return CA_STATUS_OK;
918     }
919     if (number & CA_WIFI)
920     {
921         gSelectedNwType = CA_WIFI;
922         return CA_STATUS_OK;
923     }
924     if (number & CA_EDR)
925     {
926         gSelectedNwType = CA_EDR;
927         return CA_STATUS_OK;
928     }
929     if (number & CA_LE)
930     {
931         gSelectedNwType = CA_LE;
932         return CA_STATUS_OK;
933     }
934
935     return CA_NOT_SUPPORTED;
936 }
937
938 void callback(char *subject, char *receivedData)
939 {
940     JNIEnv* env = NULL;
941     int status = (*g_jvm)->GetEnv(g_jvm, (void **) &env, JNI_VERSION_1_6);
942     int res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
943
944     jclass cls = (*env)->GetObjectClass(env, gResponseListenerObject);
945     jmethodID mid = (*env)->GetMethodID(env, cls, "OnResponseReceived", "(Ljava/lang/String;Ljava/lang/String;)V");
946
947     jstring jsubject = (*env)->NewStringUTF(env, (char*)subject);
948     jstring jreceivedData = (*env)->NewStringUTF(env, (char*)receivedData);
949     (*env)->CallVoidMethod(env, gResponseListenerObject, mid, jsubject, jreceivedData);
950
951 }