1 /******************************************************************
3 * Copyright 2014 Samsung Electronics All Rights Reserved.
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
11 * http://www.apache.org/licenses/LICENSE-2.0
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.
19 ******************************************************************/
26 #include "caleclient.h"
27 #include "caleserver.h"
28 #include "caleutils.h"
29 #include "caleinterface.h"
30 #include "caadapterutils.h"
33 #include "oic_malloc.h"
34 #include "oic_string.h"
35 #include "cathreadpool.h" /* for thread pool */
37 #include "uarraylist.h"
38 #include "org_iotivity_ca_CaLeClientInterface.h"
40 #define TAG PCF("CA_LE_CLIENT")
42 #define MICROSECS_PER_SEC 1000000
44 static const char METHODID_OBJECTNONPARAM[] = "()Landroid/bluetooth/BluetoothAdapter;";
45 static const char CLASSPATH_BT_ADAPTER[] = "android/bluetooth/BluetoothAdapter";
46 static const char CLASSPATH_BT_UUID[] = "java/util/UUID";
47 static const char CLASSPATH_BT_GATT[] = "android/bluetooth/BluetoothGatt";
50 static u_arraylist_t *g_deviceList = NULL; // device list to have same UUID
51 static u_arraylist_t *g_gattObjectList = NULL;
52 static u_arraylist_t *g_deviceStateList = NULL;
54 static CAPacketReceiveCallback g_packetReceiveCallback = NULL;
55 static CABLEErrorHandleCallback g_clientErrorCallback;
56 static ca_thread_pool_t g_threadPoolHandle = NULL;
57 static jobject g_leScanCallback = NULL;
58 static jobject g_leGattCallback = NULL;
59 static jobject g_context = NULL;
60 static jobjectArray g_uuidList = NULL;
62 // it will be prevent to start send logic when adapter has stopped.
63 static bool g_isStartedLEClient = false;
64 static bool g_isStartedMulticastServer = false;
65 static bool g_isStartedScan = false;
67 static jbyteArray g_sendBuffer = NULL;
68 static uint32_t g_targetCnt = 0;
69 static uint32_t g_currentSentCnt = 0;
70 static bool g_isFinishedSendData = false;
71 static ca_mutex g_SendFinishMutex = NULL;
72 static ca_mutex g_threadMutex = NULL;
73 static ca_cond g_threadCond = NULL;
74 static ca_cond g_deviceDescCond = NULL;
76 static ca_mutex g_threadSendMutex = NULL;
78 static ca_mutex g_bleReqRespClientCbMutex = NULL;
79 static ca_mutex g_bleServerBDAddressMutex = NULL;
81 static ca_mutex g_deviceListMutex = NULL;
82 static ca_mutex g_gattObjectMutex = NULL;
83 static ca_mutex g_deviceStateListMutex = NULL;
85 static ca_mutex g_scanMutex = NULL;
87 static CABLEDataReceivedCallback g_CABLEClientDataReceivedCallback = NULL;
90 void CALEClientJniInit()
92 OIC_LOG(DEBUG, TAG, "CALEClientJniInit");
93 g_jvm = (JavaVM*) CANativeJNIGetJavaVM();
96 void CALEClientJNISetContext()
98 OIC_LOG(DEBUG, TAG, "CALEClientJNISetContext");
99 g_context = (jobject) CANativeJNIGetContext();
102 CAResult_t CALECreateJniInterfaceObject()
104 OIC_LOG(DEBUG, TAG, "CALECreateJniInterfaceObject");
108 OIC_LOG(ERROR, TAG, "g_context is null");
109 return CA_STATUS_FAILED;
114 OIC_LOG(ERROR, TAG, "g_jvm is null");
115 return CA_STATUS_FAILED;
118 bool isAttached = false;
120 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
123 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
124 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
128 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
129 return CA_STATUS_FAILED;
134 jclass jni_LEInterface = (*env)->FindClass(env, "org/iotivity/ca/CaLeClientInterface");
135 if (!jni_LEInterface)
137 OIC_LOG(ERROR, TAG, "Could not get CaLeClientInterface class");
141 jmethodID LeInterfaceConstructorMethod = (*env)->GetMethodID(env, jni_LEInterface, "<init>",
142 "(Landroid/content/Context;)V");
143 if (!LeInterfaceConstructorMethod)
145 OIC_LOG(ERROR, TAG, "Could not get CaLeClientInterface constructor method");
149 (*env)->NewObject(env, jni_LEInterface, LeInterfaceConstructorMethod, g_context);
150 OIC_LOG(DEBUG, TAG, "Create instance for CaLeClientInterface");
154 (*g_jvm)->DetachCurrentThread(g_jvm);
163 (*g_jvm)->DetachCurrentThread(g_jvm);
166 return CA_STATUS_FAILED;
169 CAResult_t CALEClientInitialize(ca_thread_pool_t handle)
171 OIC_LOG(DEBUG, TAG, "CALEClientInitialize");
177 OIC_LOG(ERROR, TAG, "g_jvm is null");
178 return CA_STATUS_FAILED;
181 bool isAttached = false;
183 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
186 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
187 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
191 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
192 return CA_STATUS_FAILED;
197 CAResult_t ret = CALECheckPlatformVersion(env, 18);
198 if (CA_STATUS_OK != ret)
200 OIC_LOG(ERROR, TAG, "it is not supported");
204 (*g_jvm)->DetachCurrentThread(g_jvm);
210 g_threadPoolHandle = handle;
212 ret = CALEClientInitGattMutexVaraibles();
213 if (CA_STATUS_OK != ret)
215 OIC_LOG(ERROR, TAG, "CALEClientInitGattMutexVaraibles has failed!");
216 CALEClientTerminateGattMutexVariables();
220 (*g_jvm)->DetachCurrentThread(g_jvm);
226 g_deviceDescCond = ca_cond_new();
228 // init mutex for send logic
229 g_threadCond = ca_cond_new();
231 CALEClientCreateDeviceList();
232 CALEClientJNISetContext();
234 ret = CALEClientCreateUUIDList();
235 if (CA_STATUS_OK != ret)
237 OIC_LOG(ERROR, TAG, "CALEClientCreateUUIDList has failed");
241 (*g_jvm)->DetachCurrentThread(g_jvm);
247 ret = CALECreateJniInterfaceObject(); /* create java caleinterface instance*/
248 if (CA_STATUS_OK != ret)
250 OIC_LOG(ERROR, TAG, "CALECreateJniInterfaceObject has failed");
254 (*g_jvm)->DetachCurrentThread(g_jvm);
259 g_isStartedLEClient = true;
263 (*g_jvm)->DetachCurrentThread(g_jvm);
269 void CALEClientTerminate()
271 OIC_LOG(DEBUG, TAG, "CALEClientTerminate");
275 OIC_LOG(ERROR, TAG, "g_jvm is null");
279 bool isAttached = false;
281 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
284 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
285 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
289 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
295 if (g_leScanCallback)
297 (*env)->DeleteGlobalRef(env, g_leScanCallback);
300 if (g_leGattCallback)
302 (*env)->DeleteGlobalRef(env, g_leGattCallback);
307 (*env)->DeleteGlobalRef(env, g_sendBuffer);
312 (*env)->DeleteGlobalRef(env, g_uuidList);
315 CAResult_t ret = CALEClientRemoveAllDeviceState();
316 if (CA_STATUS_OK != ret)
318 OIC_LOG(ERROR, TAG, "CALEClientRemoveAllDeviceState has failed");
321 ret = CALEClientRemoveAllScanDevices(env);
322 if (CA_STATUS_OK != ret)
324 OIC_LOG(ERROR, TAG, "CALEClientRemoveAllScanDevices has failed");
327 ret = CALEClientRemoveAllGattObjs(env);
328 if (CA_STATUS_OK != ret)
330 OIC_LOG(ERROR, TAG, "CALEClientRemoveAllGattObjs has failed");
333 g_isStartedMulticastServer = false;
334 CALEClientSetScanFlag(false);
335 CALEClientSetSendFinishFlag(false);
337 CALEClientTerminateGattMutexVariables();
339 ca_cond_free(g_deviceDescCond);
340 ca_cond_free(g_threadCond);
342 g_deviceDescCond = NULL;
347 (*g_jvm)->DetachCurrentThread(g_jvm);
351 void CALEClientSendFinish(JNIEnv *env, jobject gatt)
353 OIC_LOG(DEBUG, TAG, "CALEClientSendFinish");
354 VERIFY_NON_NULL_VOID(env, TAG, "env is null");
358 CAResult_t res = CALEClientDisconnect(env, gatt);
359 if (CA_STATUS_OK != res)
361 OIC_LOG(ERROR, TAG, "CALEClientDisconnect has failed");
364 CALEClientUpdateSendCnt(env);
367 CAResult_t CALEClientSendUnicastMessage(const char* address,
369 const uint32_t dataLen)
371 OIC_LOG_V(DEBUG, TAG, "CALEClientSendUnicastMessage(%s, %p)", address, data);
372 VERIFY_NON_NULL(address, TAG, "address is null");
373 VERIFY_NON_NULL(data, TAG, "data is null");
375 return CALEClientSendUnicastMessageImpl(address, data, dataLen);
378 CAResult_t CALEClientSendMulticastMessage(const uint8_t* data,
379 const uint32_t dataLen)
381 OIC_LOG_V(DEBUG, TAG, "CALEClientSendMulticastMessage(%p)", data);
382 VERIFY_NON_NULL(data, TAG, "data is null");
386 OIC_LOG(ERROR, TAG, "g_jvm is null");
387 return CA_STATUS_FAILED;
390 bool isAttached = false;
392 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
395 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
396 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
400 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
401 return CA_STATUS_FAILED;
406 CAResult_t ret = CALEClientSendMulticastMessageImpl(env, data, dataLen);
407 if (CA_STATUS_OK != ret)
409 OIC_LOG(ERROR, TAG, "CALEClientSendMulticastMessageImpl has failed");
414 (*g_jvm)->DetachCurrentThread(g_jvm);
420 CAResult_t CALEClientStartUnicastServer(const char* address)
422 OIC_LOG_V(DEBUG, TAG, "it is not needed in this platform (%s)", address);
424 return CA_NOT_SUPPORTED;
427 CAResult_t CALEClientStartMulticastServer()
429 OIC_LOG(DEBUG, TAG, "CALEClientStartMulticastServer");
431 if (g_isStartedMulticastServer)
433 OIC_LOG(ERROR, TAG, "server is already started..it will be skipped");
434 return CA_STATUS_FAILED;
439 OIC_LOG(ERROR, TAG, "g_jvm is null");
440 return CA_STATUS_FAILED;
443 bool isAttached = false;
445 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
448 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
449 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
453 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
454 return CA_STATUS_FAILED;
459 g_isStartedMulticastServer = true;
460 CAResult_t ret = CALEClientStartScan();
461 if (CA_STATUS_OK != ret)
463 OIC_LOG(ERROR, TAG, "CALEClientStartScan has failed");
468 (*g_jvm)->DetachCurrentThread(g_jvm);
474 void CALEClientStopUnicastServer()
476 OIC_LOG(DEBUG, TAG, "CALEClientStopUnicastServer");
479 void CALEClientStopMulticastServer()
481 OIC_LOG(DEBUG, TAG, "CALEClientStopMulticastServer");
482 g_isStartedMulticastServer = false;
483 CAResult_t res = CALEClientStopScan();
484 if (CA_STATUS_OK != res)
486 OIC_LOG(ERROR, TAG, "CALEClientStartScan has failed");
491 void CALEClientSetCallback(CAPacketReceiveCallback callback)
493 g_packetReceiveCallback = callback;
496 void CASetBLEClientErrorHandleCallback(CABLEErrorHandleCallback callback)
498 g_clientErrorCallback = callback;
501 CAResult_t CALEClientSendUnicastMessageImpl(const char* address, const uint8_t* data,
502 const uint32_t dataLen)
504 OIC_LOG_V(DEBUG, TAG, "CALEClientSendUnicastMessageImpl, address: %s, data: %p", address,
506 VERIFY_NON_NULL(address, TAG, "address is null");
507 VERIFY_NON_NULL(data, TAG, "data is null");
511 OIC_LOG(ERROR, TAG, "g_jvm is null");
512 return CA_STATUS_FAILED;
515 bool isAttached = false;
517 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
520 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
521 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
524 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
525 return CA_STATUS_FAILED;
530 ca_mutex_lock(g_threadSendMutex);
532 CAResult_t ret = CA_STATUS_OK;
533 if (g_context && g_deviceList)
535 uint32_t length = u_arraylist_length(g_deviceList);
536 for (uint32_t index = 0; index < length; index++)
538 jobject jarrayObj = (jobject) u_arraylist_get(g_deviceList, index);
541 OIC_LOG(ERROR, TAG, "jarrayObj is null");
545 jstring jni_setAddress = CALEGetAddressFromBTDevice(env, jarrayObj);
548 OIC_LOG(ERROR, TAG, "jni_setAddress is null");
552 const char* setAddress = (*env)->GetStringUTFChars(env, jni_setAddress, NULL);
555 OIC_LOG(ERROR, TAG, "setAddress is null");
559 OIC_LOG_V(DEBUG, TAG, "remote device address is %s", setAddress);
561 if (!strcmp(setAddress, address))
563 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
565 // connect to gatt server
566 ret = CALEClientStopScan();
567 if (CA_STATUS_OK != ret)
569 OIC_LOG(ERROR, TAG, "CALEClientStopScan has failed");
575 (*env)->DeleteGlobalRef(env, g_sendBuffer);
577 jbyteArray jni_arr = (*env)->NewByteArray(env, dataLen);
578 (*env)->SetByteArrayRegion(env, jni_arr, 0, dataLen, (jbyte*) data);
579 g_sendBuffer = (jbyteArray)(*env)->NewGlobalRef(env, jni_arr);
581 ret = CALEClientSendData(env, jarrayObj);
582 if (CA_STATUS_OK != ret)
584 OIC_LOG(ERROR, TAG, "CALEClientSendData in unicast is failed");
588 OIC_LOG(INFO, TAG, "wake up");
591 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
597 (*g_jvm)->DetachCurrentThread(g_jvm);
600 // start LE Scan again
601 ret = CALEClientStartScan();
602 if (CA_STATUS_OK != ret)
604 OIC_LOG(ERROR, TAG, "CALEClientStartScan has failed");
605 ca_mutex_unlock(g_threadSendMutex);
609 ca_mutex_unlock(g_threadSendMutex);
610 OIC_LOG(INFO, TAG, "unicast - send success");
616 // start LE Scan again
617 ret = CALEClientStartScan();
618 if (CA_STATUS_OK != ret)
620 OIC_LOG(ERROR, TAG, "CALEClientStartScan has failed");
621 ca_mutex_unlock(g_threadSendMutex);
624 (*g_jvm)->DetachCurrentThread(g_jvm);
631 (*g_jvm)->DetachCurrentThread(g_jvm);
634 if (g_clientErrorCallback)
636 g_clientErrorCallback(address, data, dataLen, CA_SEND_FAILED);
638 ca_mutex_unlock(g_threadSendMutex);
639 return CA_SEND_FAILED;
642 CAResult_t CALEClientSendMulticastMessageImpl(JNIEnv *env, const uint8_t* data,
643 const uint32_t dataLen)
645 OIC_LOG_V(DEBUG, TAG, "CASendMulticastMessageImpl, send to, data: %p, %u", data, dataLen);
646 VERIFY_NON_NULL(data, TAG, "data is null");
647 VERIFY_NON_NULL(env, TAG, "env is null");
651 OIC_LOG(ERROR, TAG, "g_deviceList is null");
652 return CA_STATUS_FAILED;
655 ca_mutex_lock(g_threadSendMutex);
657 CALEClientSetSendFinishFlag(false);
659 OIC_LOG(DEBUG, TAG, "set byteArray for data");
662 (*env)->DeleteGlobalRef(env, g_sendBuffer);
665 if (0 == u_arraylist_length(g_deviceList))
667 // Wait for LE peripherals to be discovered.
669 // Number of times to wait for discovery to complete.
670 static size_t const RETRIES = 5;
672 static uint64_t const TIMEOUT =
673 2 * MICROSECS_PER_SEC; // Microseconds
675 bool devicesDiscovered = false;
677 0 == u_arraylist_length(g_deviceList) && i < RETRIES;
680 if (ca_cond_wait_for(g_deviceDescCond,
684 devicesDiscovered = true;
688 if (!devicesDiscovered)
694 // connect to gatt server
695 CAResult_t res = CALEClientStopScan();
696 if (CA_STATUS_OK != res)
698 OIC_LOG(ERROR, TAG, "CALEClientStopScan has failed");
699 ca_mutex_unlock(g_threadSendMutex);
702 uint32_t length = u_arraylist_length(g_deviceList);
703 g_targetCnt = length;
705 jbyteArray jni_arr = (*env)->NewByteArray(env, dataLen);
706 (*env)->SetByteArrayRegion(env, jni_arr, 0, dataLen, (jbyte*) data);
707 g_sendBuffer = (jbyteArray)(*env)->NewGlobalRef(env, jni_arr);
709 for (uint32_t index = 0; index < length; index++)
711 jobject jarrayObj = (jobject) u_arraylist_get(g_deviceList, index);
714 OIC_LOG(ERROR, TAG, "jarrayObj is not available");
718 res = CALEClientSendData(env, jarrayObj);
719 if (res != CA_STATUS_OK)
721 OIC_LOG(ERROR, TAG, "BT device - send has failed");
724 jstring jni_address = CALEGetAddressFromBTDevice(env, jarrayObj);
727 OIC_LOG(ERROR, TAG, "CALEGetAddressFromBTDevice has failed");
731 const char* address = (*env)->GetStringUTFChars(env, jni_address, NULL);
734 OIC_LOG(ERROR, TAG, "address is not available");
738 (*env)->ReleaseStringUTFChars(env, jni_address, address);
741 OIC_LOG(DEBUG, TAG, "connection routine is finished");
743 // wait for finish to send data through "CALeGattServicesDiscoveredCallback"
744 if (!g_isFinishedSendData)
746 ca_mutex_lock(g_threadMutex);
747 ca_cond_wait(g_threadCond, g_threadMutex);
748 OIC_LOG(DEBUG, TAG, "the data was sent for All devices");
749 ca_mutex_unlock(g_threadMutex);
752 // start LE Scan again
753 res = CALEClientStartScan();
754 if (CA_STATUS_OK != res)
756 OIC_LOG(ERROR, TAG, "CALEClientStartScan has failed");
757 ca_mutex_unlock(g_threadSendMutex);
761 ca_mutex_unlock(g_threadSendMutex);
762 OIC_LOG(DEBUG, TAG, "OUT - CALEClientSendMulticastMessageImpl");
766 res = CALEClientStartScan();
767 if (CA_STATUS_OK != res)
769 OIC_LOG(ERROR, TAG, "CALEClientStartScan has failed");
770 ca_mutex_unlock(g_threadSendMutex);
774 ca_mutex_unlock(g_threadSendMutex);
775 OIC_LOG(DEBUG, TAG, "OUT - CALEClientSendMulticastMessageImpl");
776 return CA_SEND_FAILED;
779 CAResult_t CALECheckSendState(const char* address)
781 VERIFY_NON_NULL(address, TAG, "address is null");
783 ca_mutex_lock(g_deviceStateListMutex);
784 CALEState_t* state = CALEClientGetStateInfo(address);
787 OIC_LOG(ERROR, TAG, "state is null");
788 ca_mutex_unlock(g_deviceStateListMutex);
789 return CA_SEND_FAILED;
792 if (STATE_SEND_SUCCESS != state->sendState)
794 OIC_LOG(ERROR, TAG, "sendstate is not STATE_SEND_SUCCESS");
795 ca_mutex_unlock(g_deviceStateListMutex);
796 return CA_SEND_FAILED;
798 ca_mutex_unlock(g_deviceStateListMutex);
802 CAResult_t CALEClientSendData(JNIEnv *env, jobject device)
804 OIC_LOG(DEBUG, TAG, "IN - CALEClientSendData");
805 VERIFY_NON_NULL(device, TAG, "device is null");
806 VERIFY_NON_NULL(env, TAG, "env is null");
808 jstring jni_address = CALEGetAddressFromBTDevice(env, device);
811 OIC_LOG(ERROR, TAG, "CALEGetAddressFromBTDevice has failed");
812 return CA_STATUS_FAILED;
815 const char* address = (*env)->GetStringUTFChars(env, jni_address, NULL);
818 OIC_LOG(ERROR, TAG, "address is not available");
819 return CA_STATUS_FAILED;
822 ca_mutex_lock(g_deviceStateListMutex);
823 CALEState_t* state = CALEClientGetStateInfo(address);
824 ca_mutex_unlock(g_deviceStateListMutex);
827 OIC_LOG(DEBUG, TAG, "state is empty..start to connect LE");
828 CAResult_t ret = CALEClientConnect(env, device, JNI_FALSE, g_leGattCallback);
829 if (CA_STATUS_OK != ret)
831 OIC_LOG(ERROR, TAG, "CALEClientConnect has failed");
832 (*env)->ReleaseStringUTFChars(env, jni_address, address);
838 if (STATE_CONNECTED == state->connectedState)
840 OIC_LOG(INFO, TAG, "GATT has already connected");
841 jobject gatt = CALEClientGetGattObjInList(env, address);
844 OIC_LOG(ERROR, TAG, "CALEClientGetGattObjInList has failed");
845 (*env)->ReleaseStringUTFChars(env, jni_address, address);
846 return CA_STATUS_FAILED;
849 CAResult_t ret = CALEClientWriteCharacteristic(env, gatt);
850 if (CA_STATUS_OK != ret)
852 OIC_LOG(ERROR, TAG, "CALEClientWriteCharacteristic has failed");
853 (*env)->ReleaseStringUTFChars(env, jni_address, address);
859 OIC_LOG(DEBUG, TAG, "start to connect LE");
860 CAResult_t ret = CALEClientConnect(env, device, JNI_FALSE, g_leGattCallback);
861 if (CA_STATUS_OK != ret)
863 OIC_LOG(ERROR, TAG, "CALEClientConnect has failed");
864 (*env)->ReleaseStringUTFChars(env, jni_address, address);
870 (*env)->ReleaseStringUTFChars(env, jni_address, address);
874 jstring CALEClientGetAddressFromGattObj(JNIEnv *env, jobject gatt)
876 VERIFY_NON_NULL_RET(gatt, TAG, "gatt is null", NULL);
877 VERIFY_NON_NULL_RET(env, TAG, "env is null", NULL);
879 jclass jni_cid_gattdevice_list = (*env)->FindClass(env, CLASSPATH_BT_GATT);
880 if (!jni_cid_gattdevice_list)
882 OIC_LOG(ERROR, TAG, "jni_cid_gattdevice_list is null");
886 jmethodID jni_mid_getDevice = (*env)->GetMethodID(env, jni_cid_gattdevice_list, "getDevice",
887 "()Landroid/bluetooth/BluetoothDevice;");
888 if (!jni_mid_getDevice)
890 OIC_LOG(ERROR, TAG, "jni_mid_getDevice is null");
894 jobject jni_obj_device = (*env)->CallObjectMethod(env, gatt, jni_mid_getDevice);
897 OIC_LOG(ERROR, TAG, "jni_obj_device is null");
901 jstring jni_address = CALEGetAddressFromBTDevice(env, jni_obj_device);
904 OIC_LOG(ERROR, TAG, "jni_address is null");
914 CAResult_t CALEClientGattClose(JNIEnv *env, jobject bluetoothGatt)
917 OIC_LOG(DEBUG, TAG, "Gatt Close");
918 VERIFY_NON_NULL(bluetoothGatt, TAG, "bluetoothGatt is null");
919 VERIFY_NON_NULL(env, TAG, "env is null");
921 // get BluetoothGatt class
922 OIC_LOG(DEBUG, TAG, "get BluetoothGatt class");
923 jclass jni_cid_BluetoothGatt = (*env)->FindClass(env, CLASSPATH_BT_GATT);
924 if (!jni_cid_BluetoothGatt)
926 OIC_LOG(ERROR, TAG, "jni_cid_BluetoothGatt is null");
927 return CA_STATUS_FAILED;
930 jmethodID jni_mid_closeGatt = (*env)->GetMethodID(env, jni_cid_BluetoothGatt, "close", "()V");
931 if (!jni_mid_closeGatt)
933 OIC_LOG(ERROR, TAG, "jni_mid_closeGatt is null");
937 // call disconnect gatt method
938 OIC_LOG(DEBUG, TAG, "request to close GATT");
939 (*env)->CallVoidMethod(env, bluetoothGatt, jni_mid_closeGatt);
941 if ((*env)->ExceptionCheck(env))
943 OIC_LOG(ERROR, TAG, "closeGATT has failed");
944 (*env)->ExceptionDescribe(env);
945 (*env)->ExceptionClear(env);
946 return CA_STATUS_FAILED;
952 CAResult_t CALEClientStartScan()
954 if (!g_isStartedMulticastServer)
956 OIC_LOG(ERROR, TAG, "server is not started yet..scan will be passed");
957 return CA_STATUS_FAILED;
960 if (!g_isStartedLEClient)
962 OIC_LOG(ERROR, TAG, "LE client is not started");
963 return CA_STATUS_FAILED;
968 OIC_LOG(ERROR, TAG, "g_jvm is null");
969 return CA_STATUS_FAILED;
974 OIC_LOG(INFO, TAG, "scanning is already started");
978 bool isAttached = false;
980 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
983 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
985 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
988 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
989 return CA_STATUS_FAILED;
994 OIC_LOG(DEBUG, TAG, "CALEClientStartScan");
996 CAResult_t ret = CA_STATUS_OK;
997 // scan gatt server with UUID
998 if (g_leScanCallback && g_uuidList)
1001 ret = CALEClientStartScanWithUUIDImpl(env, g_uuidList, g_leScanCallback);
1002 if(CA_STATUS_OK != ret)
1004 OIC_LOG(ERROR, TAG, "CALEClientStartScanWithUUIDImpl has failed");
1007 ret = CALEClientStartScanImpl(env, g_leScanCallback);
1008 if (CA_STATUS_OK != ret)
1010 OIC_LOG(ERROR, TAG, "CALEClientStartScanImpl has failed");
1017 (*g_jvm)->DetachCurrentThread(g_jvm);
1023 CAResult_t CALEClientStartScanImpl(JNIEnv *env, jobject callback)
1025 VERIFY_NON_NULL(callback, TAG, "callback is null");
1026 VERIFY_NON_NULL(env, TAG, "env is null");
1028 if (!CALEIsEnableBTAdapter(env))
1030 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
1031 return CA_ADAPTER_NOT_ENABLED;
1034 // get default bt adapter class
1035 jclass jni_cid_BTAdapter = (*env)->FindClass(env, CLASSPATH_BT_ADAPTER);
1036 if (!jni_cid_BTAdapter)
1038 OIC_LOG(ERROR, TAG, "getState From BTAdapter: jni_cid_BTAdapter is null");
1039 return CA_STATUS_FAILED;
1042 // get remote bt adapter method
1043 jmethodID jni_mid_getDefaultAdapter = (*env)->GetStaticMethodID(env, jni_cid_BTAdapter,
1044 "getDefaultAdapter",
1045 METHODID_OBJECTNONPARAM);
1046 if (!jni_mid_getDefaultAdapter)
1048 OIC_LOG(ERROR, TAG, "jni_mid_getDefaultAdapter is null");
1049 return CA_STATUS_FAILED;
1052 // get start le scan method
1053 jmethodID jni_mid_startLeScan = (*env)->GetMethodID(env, jni_cid_BTAdapter, "startLeScan",
1054 "(Landroid/bluetooth/BluetoothAdapter$"
1055 "LeScanCallback;)Z");
1056 if (!jni_mid_startLeScan)
1058 OIC_LOG(ERROR, TAG, "startLeScan: jni_mid_startLeScan is null");
1059 return CA_STATUS_FAILED;
1062 // gat bt adapter object
1063 jobject jni_obj_BTAdapter = (*env)->CallStaticObjectMethod(env, jni_cid_BTAdapter,
1064 jni_mid_getDefaultAdapter);
1065 if (!jni_obj_BTAdapter)
1067 OIC_LOG(ERROR, TAG, "getState From BTAdapter: jni_obj_BTAdapter is null");
1068 return CA_STATUS_FAILED;
1071 // call start le scan method
1072 jboolean jni_obj_startLeScan = (*env)->CallBooleanMethod(env, jni_obj_BTAdapter,
1073 jni_mid_startLeScan, callback);
1074 if (!jni_obj_startLeScan)
1076 OIC_LOG(ERROR, TAG, "startLeScan is failed");
1077 return CA_STATUS_FAILED;
1081 OIC_LOG(DEBUG, TAG, "startLeScan is started");
1082 CALEClientSetScanFlag(true);
1085 return CA_STATUS_OK;
1088 CAResult_t CALEClientStartScanWithUUIDImpl(JNIEnv *env, jobjectArray uuids, jobject callback)
1090 VERIFY_NON_NULL(callback, TAG, "callback is null");
1091 VERIFY_NON_NULL(uuids, TAG, "uuids is null");
1092 VERIFY_NON_NULL(env, TAG, "env is null");
1094 if (!CALEIsEnableBTAdapter(env))
1096 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
1097 return CA_ADAPTER_NOT_ENABLED;
1100 jclass jni_cid_BTAdapter = (*env)->FindClass(env, CLASSPATH_BT_ADAPTER);
1101 if (!jni_cid_BTAdapter)
1103 OIC_LOG(ERROR, TAG, "getState From BTAdapter: jni_cid_BTAdapter is null");
1104 return CA_STATUS_FAILED;
1107 // get remote bt adapter method
1108 jmethodID jni_mid_getDefaultAdapter = (*env)->GetStaticMethodID(env, jni_cid_BTAdapter,
1109 "getDefaultAdapter",
1110 METHODID_OBJECTNONPARAM);
1111 if (!jni_mid_getDefaultAdapter)
1113 OIC_LOG(ERROR, TAG, "jni_mid_getDefaultAdapter is null");
1114 return CA_STATUS_FAILED;
1117 // get start le scan method
1118 jmethodID jni_mid_startLeScan = (*env)->GetMethodID(env, jni_cid_BTAdapter, "startLeScan",
1119 "([Ljava/util/UUID;Landroid/bluetooth/"
1120 "BluetoothAdapter$LeScanCallback;)Z");
1121 if (!jni_mid_startLeScan)
1123 OIC_LOG(ERROR, TAG, "startLeScan: jni_mid_startLeScan is null");
1124 return CA_STATUS_FAILED;
1127 // get bt adapter object
1128 jobject jni_obj_BTAdapter = (*env)->CallStaticObjectMethod(env, jni_cid_BTAdapter,
1129 jni_mid_getDefaultAdapter);
1130 if (!jni_obj_BTAdapter)
1132 OIC_LOG(ERROR, TAG, "getState From BTAdapter: jni_obj_BTAdapter is null");
1133 return CA_STATUS_FAILED;
1136 // call start le scan method
1137 jboolean jni_obj_startLeScan = (*env)->CallBooleanMethod(env, jni_obj_BTAdapter,
1138 jni_mid_startLeScan, uuids, callback);
1139 if (!jni_obj_startLeScan)
1141 OIC_LOG(ERROR, TAG, "startLeScan With UUID is failed");
1142 return CA_STATUS_FAILED;
1146 OIC_LOG(DEBUG, TAG, "startLeScan With UUID is started");
1147 CALEClientSetScanFlag(true);
1150 return CA_STATUS_OK;
1153 jobject CALEClientGetUUIDObject(JNIEnv *env, const char* uuid)
1155 VERIFY_NON_NULL_RET(uuid, TAG, "uuid is null", NULL);
1156 VERIFY_NON_NULL_RET(env, TAG, "env is null", NULL);
1159 jclass jni_cid_uuid = (*env)->FindClass(env, CLASSPATH_BT_UUID);
1162 OIC_LOG(ERROR, TAG, "jni_cid_uuid is null");
1166 jmethodID jni_mid_fromString = (*env)->GetStaticMethodID(env, jni_cid_uuid, "fromString",
1167 "(Ljava/lang/String;)"
1168 "Ljava/util/UUID;");
1169 if (!jni_mid_fromString)
1171 OIC_LOG(ERROR, TAG, "jni_mid_fromString is null");
1175 jstring jni_uuid = (*env)->NewStringUTF(env, uuid);
1176 jobject jni_obj_uuid = (*env)->CallStaticObjectMethod(env, jni_cid_uuid, jni_mid_fromString,
1180 OIC_LOG(ERROR, TAG, "jni_obj_uuid is null");
1184 return jni_obj_uuid;
1187 CAResult_t CALEClientStopScan()
1191 OIC_LOG(ERROR, TAG, "g_jvm is null");
1192 return CA_STATUS_FAILED;
1195 if (!g_isStartedScan)
1197 OIC_LOG(INFO, TAG, "scanning is already stopped");
1198 return CA_STATUS_OK;
1201 bool isAttached = false;
1203 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
1206 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
1207 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
1210 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
1211 return CA_STATUS_FAILED;
1216 CAResult_t ret = CALEClientStopScanImpl(env, g_leScanCallback);
1217 if (CA_STATUS_OK != ret)
1219 OIC_LOG(ERROR, TAG, "CALEClientStopScanImpl has failed");
1223 CALEClientSetScanFlag(false);
1228 (*g_jvm)->DetachCurrentThread(g_jvm);
1234 void CALEClientSetScanFlag(bool flag)
1236 ca_mutex_lock(g_scanMutex);
1237 g_isStartedScan = flag;
1238 ca_mutex_unlock(g_scanMutex);
1241 CAResult_t CALEClientStopScanImpl(JNIEnv *env, jobject callback)
1243 OIC_LOG(DEBUG, TAG, "CALEClientStopScanImpl");
1244 VERIFY_NON_NULL(callback, TAG, "callback is null");
1245 VERIFY_NON_NULL(env, TAG, "env is null");
1247 if (!CALEIsEnableBTAdapter(env))
1249 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
1250 return CA_ADAPTER_NOT_ENABLED;
1253 // get default bt adapter class
1254 jclass jni_cid_BTAdapter = (*env)->FindClass(env, CLASSPATH_BT_ADAPTER);
1255 if (!jni_cid_BTAdapter)
1257 OIC_LOG(ERROR, TAG, "getState From BTAdapter: jni_cid_BTAdapter is null");
1258 return CA_STATUS_FAILED;
1261 // get remote bt adapter method
1262 jmethodID jni_mid_getDefaultAdapter = (*env)->GetStaticMethodID(env, jni_cid_BTAdapter,
1263 "getDefaultAdapter",
1264 METHODID_OBJECTNONPARAM);
1265 if (!jni_mid_getDefaultAdapter)
1267 OIC_LOG(ERROR, TAG, "jni_mid_getDefaultAdapter is null");
1268 return CA_STATUS_FAILED;
1271 // get start le scan method
1272 jmethodID jni_mid_stopLeScan = (*env)->GetMethodID(env, jni_cid_BTAdapter, "stopLeScan",
1273 "(Landroid/bluetooth/"
1274 "BluetoothAdapter$LeScanCallback;)V");
1275 if (!jni_mid_stopLeScan)
1277 OIC_LOG(ERROR, TAG, "stopLeScan: jni_mid_stopLeScan is null");
1278 return CA_STATUS_FAILED;
1281 // gat bt adapter object
1282 jobject jni_obj_BTAdapter = (*env)->CallStaticObjectMethod(env, jni_cid_BTAdapter,
1283 jni_mid_getDefaultAdapter);
1284 if (!jni_obj_BTAdapter)
1286 OIC_LOG(ERROR, TAG, "jni_obj_BTAdapter is null");
1287 return CA_STATUS_FAILED;
1290 OIC_LOG(DEBUG, TAG, "CALL API - request to stop LE Scan");
1291 // call start le scan method
1292 (*env)->CallVoidMethod(env, jni_obj_BTAdapter, jni_mid_stopLeScan, callback);
1293 if ((*env)->ExceptionCheck(env))
1295 OIC_LOG(ERROR, TAG, "stopLeScan has failed");
1296 (*env)->ExceptionDescribe(env);
1297 (*env)->ExceptionClear(env);
1298 return CA_STATUS_FAILED;
1301 return CA_STATUS_OK;
1304 CAResult_t CALEClientConnect(JNIEnv *env, jobject bluetoothDevice, jboolean autoconnect,
1307 OIC_LOG(DEBUG, TAG, "GATT CONNECT");
1308 VERIFY_NON_NULL(env, TAG, "env is null");
1309 VERIFY_NON_NULL(bluetoothDevice, TAG, "bluetoothDevice is null");
1310 VERIFY_NON_NULL(callback, TAG, "callback is null");
1312 if (!CALEIsEnableBTAdapter(env))
1314 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
1315 return CA_ADAPTER_NOT_ENABLED;
1318 jstring jni_address = CALEGetAddressFromBTDevice(env, bluetoothDevice);
1321 OIC_LOG(ERROR, TAG, "bleConnect: CALEGetAddressFromBTDevice is null");
1322 return CA_STATUS_FAILED;
1325 // get BluetoothDevice class
1326 OIC_LOG(DEBUG, TAG, "get BluetoothDevice class");
1327 jclass jni_cid_BluetoothDevice = (*env)->FindClass(env, "android/bluetooth/BluetoothDevice");
1328 if (!jni_cid_BluetoothDevice)
1330 OIC_LOG(ERROR, TAG, "bleConnect: jni_cid_BluetoothDevice is null");
1331 return CA_STATUS_FAILED;
1334 // get connectGatt method
1335 OIC_LOG(DEBUG, TAG, "get connectGatt method");
1336 jmethodID jni_mid_connectGatt = (*env)->GetMethodID(env, jni_cid_BluetoothDevice, "connectGatt",
1337 "(Landroid/content/Context;ZLandroid/"
1338 "bluetooth/BluetoothGattCallback;)"
1339 "Landroid/bluetooth/BluetoothGatt;");
1340 if (!jni_mid_connectGatt)
1342 OIC_LOG(ERROR, TAG, "bleConnect: jni_mid_connectGatt is null");
1343 return CA_STATUS_FAILED;
1346 OIC_LOG(DEBUG, TAG, "Call object method - connectGatt");
1347 jobject jni_obj_connectGatt = (*env)->CallObjectMethod(env, bluetoothDevice,
1348 jni_mid_connectGatt,
1350 autoconnect, callback);
1351 if (!jni_obj_connectGatt)
1353 OIC_LOG(ERROR, TAG, "CALL API - connectGatt was failed..it will be removed");
1354 CALEClientRemoveDeviceInScanDeviceList(env, jni_address);
1355 CALEClientUpdateSendCnt(env);
1356 return CA_STATUS_FAILED;
1360 OIC_LOG(DEBUG, TAG, "le connecting..please wait..");
1362 return CA_STATUS_OK;
1365 CAResult_t CALEClientDisconnect(JNIEnv *env, jobject bluetoothGatt)
1367 OIC_LOG(DEBUG, TAG, "GATT DISCONNECT");
1368 VERIFY_NON_NULL(env, TAG, "env is null");
1369 VERIFY_NON_NULL(bluetoothGatt, TAG, "bluetoothGatt is null");
1371 if (!CALEIsEnableBTAdapter(env))
1373 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
1374 return CA_ADAPTER_NOT_ENABLED;
1377 // get BluetoothGatt class
1378 jclass jni_cid_BluetoothGatt = (*env)->FindClass(env, CLASSPATH_BT_GATT);
1379 if (!jni_cid_BluetoothGatt)
1381 OIC_LOG(ERROR, TAG, "jni_cid_BluetoothGatt is null");
1382 return CA_STATUS_FAILED;
1385 OIC_LOG(DEBUG, TAG, "get gatt disconnect method");
1386 jmethodID jni_mid_disconnectGatt = (*env)->GetMethodID(env, jni_cid_BluetoothGatt,
1387 "disconnect", "()V");
1388 if (!jni_mid_disconnectGatt)
1390 OIC_LOG(ERROR, TAG, "jni_mid_disconnectGatt is null");
1391 return CA_STATUS_FAILED;
1394 // call disconnect gatt method
1395 (*env)->CallVoidMethod(env, bluetoothGatt, jni_mid_disconnectGatt);
1396 if ((*env)->ExceptionCheck(env))
1398 OIC_LOG(ERROR, TAG, "disconnect has failed");
1399 (*env)->ExceptionDescribe(env);
1400 (*env)->ExceptionClear(env);
1401 return CA_STATUS_FAILED;
1404 OIC_LOG(DEBUG, TAG, "disconnecting Gatt...");
1406 return CA_STATUS_OK;
1409 CAResult_t CALEClientDisconnectAll(JNIEnv *env)
1411 OIC_LOG(DEBUG, TAG, "CALEClientDisconnectAll");
1412 VERIFY_NON_NULL(env, TAG, "env is null");
1414 if (!g_gattObjectList)
1416 OIC_LOG(ERROR, TAG, "g_gattObjectList is null");
1417 return CA_STATUS_FAILED;
1420 uint32_t length = u_arraylist_length(g_gattObjectList);
1421 for (uint32_t index = 0; index < length; index++)
1423 jobject jarrayObj = (jobject) u_arraylist_get(g_gattObjectList, index);
1426 OIC_LOG(ERROR, TAG, "jarrayObj is null");
1429 CAResult_t res = CALEClientDisconnect(env, jarrayObj);
1430 if (CA_STATUS_OK != res)
1432 OIC_LOG(ERROR, TAG, "CALEClientDisconnect has failed");
1437 OICFree(g_gattObjectList);
1438 g_gattObjectList = NULL;
1440 return CA_STATUS_OK;
1443 CAResult_t CALEClientDiscoverServices(JNIEnv *env, jobject bluetoothGatt)
1445 VERIFY_NON_NULL(env, TAG, "env is null");
1446 VERIFY_NON_NULL(bluetoothGatt, TAG, "bluetoothGatt is null");
1448 if (!CALEIsEnableBTAdapter(env))
1450 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
1451 return CA_ADAPTER_NOT_ENABLED;
1454 // get BluetoothGatt class
1455 OIC_LOG(DEBUG, TAG, "get BluetoothGatt class");
1456 jclass jni_cid_BluetoothGatt = (*env)->FindClass(env, CLASSPATH_BT_GATT);
1457 if (!jni_cid_BluetoothGatt)
1459 OIC_LOG(ERROR, TAG, "jni_cid_BluetoothGatt is null");
1460 return CA_STATUS_FAILED;
1463 OIC_LOG(DEBUG, TAG, "discovery gatt services method");
1464 jmethodID jni_mid_discoverServices = (*env)->GetMethodID(env, jni_cid_BluetoothGatt,
1465 "discoverServices", "()Z");
1466 if (!jni_mid_discoverServices)
1468 OIC_LOG(ERROR, TAG, "jni_mid_discoverServices is null");
1469 return CA_STATUS_FAILED;
1471 // call disconnect gatt method
1472 OIC_LOG(DEBUG, TAG, "CALL API - request discovery gatt services");
1473 jboolean ret = (*env)->CallBooleanMethod(env, bluetoothGatt, jni_mid_discoverServices);
1476 OIC_LOG(ERROR, TAG, "discoverServices has not been started");
1477 return CA_STATUS_FAILED;
1480 return CA_STATUS_OK;
1483 CAResult_t CALEClientWriteCharacteristic(JNIEnv *env, jobject gatt)
1485 VERIFY_NON_NULL(env, TAG, "env is null");
1486 VERIFY_NON_NULL(gatt, TAG, "gatt is null");
1489 jobject jni_obj_character = CALEClientCreateGattCharacteristic(env, gatt, g_sendBuffer);
1490 if (!jni_obj_character)
1492 CALEClientSendFinish(env, gatt);
1493 return CA_STATUS_FAILED;
1496 CAResult_t ret = CALEClientWriteCharacteristicImpl(env, gatt, jni_obj_character);
1497 if (CA_STATUS_OK != ret)
1499 CALEClientSendFinish(env, gatt);
1503 return CA_STATUS_OK;
1506 CAResult_t CALEClientWriteCharacteristicImpl(JNIEnv *env, jobject bluetoothGatt,
1507 jobject gattCharacteristic)
1509 OIC_LOG(DEBUG, TAG, "WRITE GATT CHARACTERISTIC");
1510 VERIFY_NON_NULL(env, TAG, "env is null");
1511 VERIFY_NON_NULL(bluetoothGatt, TAG, "bluetoothGatt is null");
1512 VERIFY_NON_NULL(gattCharacteristic, TAG, "gattCharacteristic is null");
1514 if (!CALEIsEnableBTAdapter(env))
1516 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
1517 return CA_STATUS_FAILED;
1520 // get BluetoothGatt class
1521 OIC_LOG(DEBUG, TAG, "get BluetoothGatt class");
1522 jclass jni_cid_BluetoothGatt = (*env)->FindClass(env, CLASSPATH_BT_GATT);
1523 if (!jni_cid_BluetoothGatt)
1525 OIC_LOG(ERROR, TAG, "jni_cid_BluetoothGatt is null");
1526 return CA_STATUS_FAILED;
1529 OIC_LOG(DEBUG, TAG, "write characteristic method");
1530 jmethodID jni_mid_writeCharacteristic = (*env)->GetMethodID(env, jni_cid_BluetoothGatt,
1531 "writeCharacteristic",
1532 "(Landroid/bluetooth/"
1533 "BluetoothGattCharacteristic;)Z");
1534 if (!jni_mid_writeCharacteristic)
1536 OIC_LOG(ERROR, TAG, "jni_mid_writeCharacteristic is null");
1537 return CA_STATUS_FAILED;
1540 // call disconnect gatt method
1541 OIC_LOG(DEBUG, TAG, "CALL API - request to write gatt characteristic");
1542 jboolean ret = (jboolean)(*env)->CallBooleanMethod(env, bluetoothGatt,
1543 jni_mid_writeCharacteristic,
1544 gattCharacteristic);
1547 OIC_LOG(DEBUG, TAG, "writeCharacteristic success");
1551 OIC_LOG(ERROR, TAG, "writeCharacteristic has failed");
1552 return CA_STATUS_FAILED;
1555 return CA_STATUS_OK;
1558 CAResult_t CALEClientReadCharacteristic(JNIEnv *env, jobject bluetoothGatt)
1560 VERIFY_NON_NULL(env, TAG, "env is null");
1561 VERIFY_NON_NULL(bluetoothGatt, TAG, "bluetoothGatt is null");
1563 if (!CALEIsEnableBTAdapter(env))
1565 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
1566 return CA_STATUS_FAILED;
1569 jclass jni_cid_BluetoothGatt = (*env)->FindClass(env, CLASSPATH_BT_GATT);
1570 if (!jni_cid_BluetoothGatt)
1572 OIC_LOG(ERROR, TAG, "jni_cid_BluetoothGatt is null");
1573 return CA_STATUS_FAILED;
1576 jstring jni_uuid = (*env)->NewStringUTF(env, OIC_GATT_CHARACTERISTIC_RESPONSE_UUID);
1579 OIC_LOG(ERROR, TAG, "jni_uuid is null");
1580 return CA_STATUS_FAILED;
1583 jobject jni_obj_GattCharacteristic = CALEClientGetGattService(env, bluetoothGatt, jni_uuid);
1584 if (!jni_obj_GattCharacteristic)
1586 OIC_LOG(ERROR, TAG, "jni_obj_GattCharacteristic is null");
1587 return CA_STATUS_FAILED;
1590 OIC_LOG(DEBUG, TAG, "read characteristic method");
1591 jmethodID jni_mid_readCharacteristic = (*env)->GetMethodID(env, jni_cid_BluetoothGatt,
1592 "readCharacteristic",
1593 "(Landroid/bluetooth/"
1594 "BluetoothGattCharacteristic;)Z");
1595 if (!jni_mid_readCharacteristic)
1597 OIC_LOG(ERROR, TAG, "jni_mid_readCharacteristic is null");
1598 return CA_STATUS_FAILED;
1601 // call disconnect gatt method
1602 OIC_LOG(DEBUG, TAG, "CALL API - request to read gatt characteristic");
1603 jboolean ret = (*env)->CallBooleanMethod(env, bluetoothGatt, jni_mid_readCharacteristic,
1604 jni_obj_GattCharacteristic);
1607 OIC_LOG(DEBUG, TAG, "readCharacteristic success");
1611 OIC_LOG(ERROR, TAG, "readCharacteristic has failed");
1612 return CA_STATUS_FAILED;
1615 return CA_STATUS_OK;
1618 CAResult_t CALEClientSetCharacteristicNotification(JNIEnv *env, jobject bluetoothGatt,
1619 jobject characteristic)
1621 VERIFY_NON_NULL(env, TAG, "env is null");
1622 VERIFY_NON_NULL(bluetoothGatt, TAG, "bluetoothGatt is null");
1623 VERIFY_NON_NULL(characteristic, TAG, "characteristic is null");
1625 if (!CALEIsEnableBTAdapter(env))
1627 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
1628 return CA_ADAPTER_NOT_ENABLED;
1631 // get BluetoothGatt class
1632 OIC_LOG(DEBUG, TAG, "CALEClientSetCharacteristicNotification");
1633 jclass jni_cid_BluetoothGatt = (*env)->FindClass(env, CLASSPATH_BT_GATT);
1634 if (!jni_cid_BluetoothGatt)
1636 OIC_LOG(ERROR, TAG, "jni_cid_BluetoothGatt is null");
1637 return CA_STATUS_FAILED;
1640 // set Characteristic Notification
1641 jmethodID jni_mid_setNotification = (*env)->GetMethodID(env, jni_cid_BluetoothGatt,
1642 "setCharacteristicNotification",
1643 "(Landroid/bluetooth/"
1644 "BluetoothGattCharacteristic;Z)Z");
1645 if (!jni_mid_setNotification)
1647 OIC_LOG(ERROR, TAG, "jni_mid_getService is null");
1648 return CA_STATUS_FAILED;
1651 jboolean ret = (*env)->CallBooleanMethod(env, bluetoothGatt, jni_mid_setNotification,
1652 characteristic, JNI_TRUE);
1653 if (JNI_TRUE == ret)
1655 OIC_LOG(DEBUG, TAG, "CALL API - setCharacteristicNotification success");
1659 OIC_LOG(ERROR, TAG, "CALL API - setCharacteristicNotification has failed");
1660 return CA_STATUS_FAILED;
1663 return CA_STATUS_OK;
1666 jobject CALEClientGetGattService(JNIEnv *env, jobject bluetoothGatt, jstring characterUUID)
1668 VERIFY_NON_NULL_RET(env, TAG, "env is null", NULL);
1669 VERIFY_NON_NULL_RET(bluetoothGatt, TAG, "bluetoothGatt is null", NULL);
1670 VERIFY_NON_NULL_RET(characterUUID, TAG, "characterUUID is null", NULL);
1672 if (!CALEIsEnableBTAdapter(env))
1674 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
1678 // get BluetoothGatt class
1679 OIC_LOG(DEBUG, TAG, "CALEClientGetGattService");
1680 jclass jni_cid_BluetoothGatt = (*env)->FindClass(env, CLASSPATH_BT_GATT);
1681 if (!jni_cid_BluetoothGatt)
1683 OIC_LOG(ERROR, TAG, "jni_cid_BluetoothGatt is null");
1687 jmethodID jni_mid_getService = (*env)->GetMethodID(
1688 env, jni_cid_BluetoothGatt, "getService",
1689 "(Ljava/util/UUID;)Landroid/bluetooth/BluetoothGattService;");
1690 if (!jni_mid_getService)
1692 OIC_LOG(ERROR, TAG, "jni_mid_getService is null");
1696 jobject jni_obj_service_uuid = CALEClientGetUUIDObject(env, OIC_GATT_SERVICE_UUID);
1697 if (!jni_obj_service_uuid)
1699 OIC_LOG(ERROR, TAG, "jni_obj_service_uuid is null");
1703 // get bluetooth gatt service
1704 OIC_LOG(DEBUG, TAG, "request to get service");
1705 jobject jni_obj_gattService = (*env)->CallObjectMethod(env, bluetoothGatt, jni_mid_getService,
1706 jni_obj_service_uuid);
1707 if (!jni_obj_gattService)
1709 OIC_LOG(ERROR, TAG, "jni_obj_gattService is null");
1713 // get bluetooth gatt service class
1714 jclass jni_cid_BluetoothGattService = (*env)->FindClass(
1715 env, "android/bluetooth/BluetoothGattService");
1716 if (!jni_cid_BluetoothGattService)
1718 OIC_LOG(ERROR, TAG, "jni_cid_BluetoothGattService is null");
1722 OIC_LOG(DEBUG, TAG, "get gatt getCharacteristic method");
1723 jmethodID jni_mid_getCharacteristic = (*env)->GetMethodID(env, jni_cid_BluetoothGattService,
1724 "getCharacteristic",
1725 "(Ljava/util/UUID;)"
1726 "Landroid/bluetooth/"
1727 "BluetoothGattCharacteristic;");
1728 if (!jni_mid_getCharacteristic)
1730 OIC_LOG(ERROR, TAG, "jni_mid_getCharacteristic is null");
1734 const char* uuid = (*env)->GetStringUTFChars(env, characterUUID, NULL);
1737 OIC_LOG(ERROR, TAG, "uuid is null");
1741 jobject jni_obj_tx_uuid = CALEClientGetUUIDObject(env, uuid);
1742 if (!jni_obj_tx_uuid)
1744 OIC_LOG(ERROR, TAG, "jni_obj_tx_uuid is null");
1745 (*env)->ReleaseStringUTFChars(env, characterUUID, uuid);
1749 OIC_LOG(DEBUG, TAG, "request to get Characteristic");
1750 jobject jni_obj_GattCharacteristic = (*env)->CallObjectMethod(env, jni_obj_gattService,
1751 jni_mid_getCharacteristic,
1754 (*env)->ReleaseStringUTFChars(env, characterUUID, uuid);
1755 return jni_obj_GattCharacteristic;
1758 jobject CALEClientCreateGattCharacteristic(JNIEnv *env, jobject bluetoothGatt, jbyteArray data)
1760 OIC_LOG(DEBUG, TAG, "CALEClientCreateGattCharacteristic");
1761 VERIFY_NON_NULL_RET(env, TAG, "env is null", NULL);
1762 VERIFY_NON_NULL_RET(bluetoothGatt, TAG, "bluetoothGatt is null", NULL);
1763 VERIFY_NON_NULL_RET(data, TAG, "data is null", NULL);
1765 if (!CALEIsEnableBTAdapter(env))
1767 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
1771 jstring jni_uuid = (*env)->NewStringUTF(env, OIC_GATT_CHARACTERISTIC_REQUEST_UUID);
1774 OIC_LOG(ERROR, TAG, "jni_uuid is null");
1778 jobject jni_obj_GattCharacteristic = CALEClientGetGattService(env, bluetoothGatt, jni_uuid);
1779 if (!jni_obj_GattCharacteristic)
1781 OIC_LOG(ERROR, TAG, "jni_obj_GattCharacteristic is null");
1785 jclass jni_cid_BTGattCharacteristic = (*env)->FindClass(env, "android/bluetooth"
1786 "/BluetoothGattCharacteristic");
1787 if (!jni_cid_BTGattCharacteristic)
1789 OIC_LOG(ERROR, TAG, "jni_cid_BTGattCharacteristic is null");
1793 OIC_LOG(DEBUG, TAG, "set value in Characteristic");
1794 jmethodID jni_mid_setValue = (*env)->GetMethodID(env, jni_cid_BTGattCharacteristic, "setValue",
1796 if (!jni_mid_setValue)
1798 OIC_LOG(ERROR, TAG, "jni_mid_setValue is null");
1802 jboolean ret = (*env)->CallBooleanMethod(env, jni_obj_GattCharacteristic, jni_mid_setValue,
1804 if (JNI_TRUE == ret)
1806 OIC_LOG(DEBUG, TAG, "the locally stored value has been set");
1810 OIC_LOG(ERROR, TAG, "the locally stored value hasn't been set");
1815 jmethodID jni_mid_setWriteType = (*env)->GetMethodID(env, jni_cid_BTGattCharacteristic,
1816 "setWriteType", "(I)V");
1817 if (!jni_mid_setWriteType)
1819 OIC_LOG(ERROR, TAG, "jni_mid_setWriteType is null");
1823 jfieldID jni_fid_no_response = (*env)->GetStaticFieldID(env, jni_cid_BTGattCharacteristic,
1824 "WRITE_TYPE_NO_RESPONSE", "I");
1825 if (!jni_fid_no_response)
1827 OIC_LOG(ERROR, TAG, "jni_fid_no_response is not available");
1831 jint jni_int_val = (*env)->GetStaticIntField(env, jni_cid_BTGattCharacteristic,
1832 jni_fid_no_response);
1834 (*env)->CallVoidMethod(env, jni_obj_GattCharacteristic, jni_mid_setWriteType, jni_int_val);
1836 return jni_obj_GattCharacteristic;
1839 jbyteArray CALEClientGetValueFromCharacteristic(JNIEnv *env, jobject characteristic)
1841 VERIFY_NON_NULL_RET(characteristic, TAG, "characteristic is null", NULL);
1842 VERIFY_NON_NULL_RET(env, TAG, "env is null", NULL);
1844 if (!CALEIsEnableBTAdapter(env))
1846 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
1850 jclass jni_cid_BTGattCharacteristic = (*env)->FindClass(env, "android/bluetooth/"
1851 "BluetoothGattCharacteristic");
1852 if (!jni_cid_BTGattCharacteristic)
1854 OIC_LOG(ERROR, TAG, "jni_cid_BTGattCharacteristic is null");
1858 OIC_LOG(DEBUG, TAG, "get value in Characteristic");
1859 jmethodID jni_mid_getValue = (*env)->GetMethodID(env, jni_cid_BTGattCharacteristic, "getValue",
1861 if (!jni_mid_getValue)
1863 OIC_LOG(ERROR, TAG, "jni_mid_getValue is null");
1867 jbyteArray jni_obj_data_array = (*env)->CallObjectMethod(env, characteristic,
1869 return jni_obj_data_array;
1872 CAResult_t CALEClientCreateUUIDList()
1876 OIC_LOG(ERROR, TAG, "g_jvm is null");
1877 return CA_STATUS_FAILED;
1880 bool isAttached = false;
1882 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
1885 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
1886 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
1890 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
1891 return CA_STATUS_FAILED;
1896 // create new object array
1897 jclass jni_cid_uuid_list = (*env)->FindClass(env, CLASSPATH_BT_UUID);
1898 if (!jni_cid_uuid_list)
1900 OIC_LOG(ERROR, TAG, "jni_cid_uuid_list is null");
1904 jobjectArray jni_obj_uuid_list = (jobjectArray)(*env)->NewObjectArray(env, 1,
1905 jni_cid_uuid_list, NULL);
1906 if (!jni_obj_uuid_list)
1908 OIC_LOG(ERROR, TAG, "jni_obj_uuid_list is null");
1913 jobject jni_obj_uuid = CALEClientGetUUIDObject(env, OIC_GATT_SERVICE_UUID);
1916 OIC_LOG(ERROR, TAG, "jni_obj_uuid is null");
1919 (*env)->SetObjectArrayElement(env, jni_obj_uuid_list, 0, jni_obj_uuid);
1921 g_uuidList = (jobjectArray)(*env)->NewGlobalRef(env, jni_obj_uuid_list);
1925 (*g_jvm)->DetachCurrentThread(g_jvm);
1928 return CA_STATUS_OK;
1935 (*g_jvm)->DetachCurrentThread(g_jvm);
1937 return CA_STATUS_FAILED;
1940 CAResult_t CALEClientSetUUIDToDescriptor(JNIEnv *env, jobject bluetoothGatt,
1941 jobject characteristic)
1943 VERIFY_NON_NULL(env, TAG, "env is null");
1944 VERIFY_NON_NULL(bluetoothGatt, TAG, "bluetoothGatt is null");
1945 VERIFY_NON_NULL(characteristic, TAG, "characteristic is null");
1947 if (!CALEIsEnableBTAdapter(env))
1949 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
1950 return CA_ADAPTER_NOT_ENABLED;
1953 OIC_LOG(DEBUG, TAG, "CALEClientSetUUIDToDescriptor");
1954 jclass jni_cid_BTGattCharacteristic = (*env)->FindClass(env, "android/bluetooth/"
1955 "BluetoothGattCharacteristic");
1956 if (!jni_cid_BTGattCharacteristic)
1958 OIC_LOG(ERROR, TAG, "jni_cid_BTGattCharacteristic is null");
1959 return CA_STATUS_FAILED;
1962 OIC_LOG(DEBUG, TAG, "set value in Characteristic");
1963 jmethodID jni_mid_getDescriptor = (*env)->GetMethodID(env, jni_cid_BTGattCharacteristic,
1965 "(Ljava/util/UUID;)Landroid/bluetooth/"
1966 "BluetoothGattDescriptor;");
1967 if (!jni_mid_getDescriptor)
1969 OIC_LOG(ERROR, TAG, "jni_mid_getDescriptor is null");
1970 return CA_STATUS_FAILED;
1973 jobject jni_obj_cc_uuid = CALEClientGetUUIDObject(env, OIC_GATT_CHARACTERISTIC_CONFIG_UUID);
1974 if (!jni_obj_cc_uuid)
1976 OIC_LOG(ERROR, TAG, "jni_obj_cc_uuid is null");
1977 return CA_STATUS_FAILED;
1980 OIC_LOG(DEBUG, TAG, "request to get descriptor");
1981 jobject jni_obj_descriptor = (*env)->CallObjectMethod(env, characteristic,
1982 jni_mid_getDescriptor, jni_obj_cc_uuid);
1983 if (!jni_obj_descriptor)
1985 OIC_LOG(ERROR, TAG, "jni_obj_descriptor is null");
1986 return CA_STATUS_FAILED;
1989 OIC_LOG(DEBUG, TAG, "set value in descriptor");
1990 jclass jni_cid_descriptor = (*env)->FindClass(env,
1991 "android/bluetooth/BluetoothGattDescriptor");
1992 if (!jni_cid_descriptor)
1994 OIC_LOG(ERROR, TAG, "jni_cid_descriptor is null");
1995 return CA_STATUS_FAILED;
1998 jmethodID jni_mid_setValue = (*env)->GetMethodID(env, jni_cid_descriptor, "setValue", "([B)Z");
1999 if (!jni_mid_setValue)
2001 OIC_LOG(ERROR, TAG, "jni_mid_setValue is null");
2002 return CA_STATUS_FAILED;
2005 jfieldID jni_fid_NotiValue = (*env)->GetStaticFieldID(env, jni_cid_descriptor,
2006 "ENABLE_NOTIFICATION_VALUE", "[B");
2007 if (!jni_fid_NotiValue)
2009 OIC_LOG(ERROR, TAG, "jni_fid_NotiValue is null");
2010 return CA_STATUS_FAILED;
2013 OIC_LOG(DEBUG, TAG, "get ENABLE_NOTIFICATION_VALUE");
2015 jboolean jni_setvalue = (*env)->CallBooleanMethod(
2016 env, jni_obj_descriptor, jni_mid_setValue,
2017 (jbyteArray)(*env)->GetStaticObjectField(env, jni_cid_descriptor, jni_fid_NotiValue));
2020 OIC_LOG(DEBUG, TAG, "setValue success");
2024 OIC_LOG(ERROR, TAG, "setValue has failed");
2025 return CA_STATUS_FAILED;
2028 jclass jni_cid_gatt = (*env)->FindClass(env, "android/bluetooth/BluetoothGatt");
2031 OIC_LOG(ERROR, TAG, "jni_cid_gatt is null");
2032 return CA_STATUS_FAILED;
2035 OIC_LOG(DEBUG, TAG, "write Descriptor in gatt object");
2036 jmethodID jni_mid_writeDescriptor = (*env)->GetMethodID(env, jni_cid_gatt, "writeDescriptor",
2037 "(Landroid/bluetooth/"
2038 "BluetoothGattDescriptor;)Z");
2039 if (!jni_mid_writeDescriptor)
2041 OIC_LOG(ERROR, TAG, "jni_mid_writeDescriptor is null");
2042 return CA_STATUS_FAILED;
2045 OIC_LOG(DEBUG, TAG, "request to write descriptor");
2046 jboolean jni_ret = (*env)->CallBooleanMethod(env, bluetoothGatt, jni_mid_writeDescriptor,
2047 jni_obj_descriptor);
2050 OIC_LOG(DEBUG, TAG, "writeDescriptor success");
2054 OIC_LOG(ERROR, TAG, "writeDescriptor has failed");
2055 return CA_STATUS_FAILED;
2058 return CA_STATUS_OK;
2061 void CALEClientCreateScanDeviceList(JNIEnv *env)
2063 OIC_LOG(DEBUG, TAG, "CALEClientCreateScanDeviceList");
2064 VERIFY_NON_NULL_VOID(env, TAG, "env is null");
2066 ca_mutex_lock(g_deviceListMutex);
2067 // create new object array
2068 if (g_deviceList == NULL)
2070 OIC_LOG(DEBUG, TAG, "Create device list");
2072 g_deviceList = u_arraylist_create();
2074 ca_mutex_unlock(g_deviceListMutex);
2077 CAResult_t CALEClientAddScanDeviceToList(JNIEnv *env, jobject device)
2079 OIC_LOG(DEBUG, TAG, "IN - CALEClientAddScanDeviceToList");
2080 VERIFY_NON_NULL(device, TAG, "device is null");
2081 VERIFY_NON_NULL(env, TAG, "env is null");
2083 ca_mutex_lock(g_deviceListMutex);
2087 OIC_LOG(ERROR, TAG, "gdevice_list is null");
2088 ca_mutex_unlock(g_deviceListMutex);
2089 return CA_STATUS_FAILED;
2092 jstring jni_remoteAddress = CALEGetAddressFromBTDevice(env, device);
2093 if (!jni_remoteAddress)
2095 OIC_LOG(ERROR, TAG, "jni_remoteAddress is null");
2096 ca_mutex_unlock(g_deviceListMutex);
2097 return CA_STATUS_FAILED;
2100 const char* remoteAddress = (*env)->GetStringUTFChars(env, jni_remoteAddress, NULL);
2103 OIC_LOG(ERROR, TAG, "remoteAddress is null");
2104 ca_mutex_unlock(g_deviceListMutex);
2105 return CA_STATUS_FAILED;
2108 if (!CALEClientIsDeviceInScanDeviceList(env, remoteAddress))
2110 jobject gdevice = (*env)->NewGlobalRef(env, device);
2111 u_arraylist_add(g_deviceList, gdevice);
2112 ca_cond_signal(g_deviceDescCond);
2113 OIC_LOG(DEBUG, TAG, "Set Object to Array as Element");
2115 (*env)->ReleaseStringUTFChars(env, jni_remoteAddress, remoteAddress);
2117 ca_mutex_unlock(g_deviceListMutex);
2119 OIC_LOG(DEBUG, TAG, "OUT - CALEClientAddScanDeviceToList");
2120 return CA_STATUS_OK;
2123 bool CALEClientIsDeviceInScanDeviceList(JNIEnv *env, const char* remoteAddress)
2125 OIC_LOG(DEBUG, TAG, "IN - CALEClientIsDeviceInScanDeviceList");
2126 VERIFY_NON_NULL_RET(env, TAG, "env is null", NULL);
2127 VERIFY_NON_NULL_RET(remoteAddress, TAG, "remoteAddress is null", true);
2131 OIC_LOG(DEBUG, TAG, "g_deviceList is null");
2135 uint32_t length = u_arraylist_length(g_deviceList);
2136 for (uint32_t index = 0; index < length; index++)
2138 jobject jarrayObj = (jobject) u_arraylist_get(g_deviceList, index);
2141 OIC_LOG(ERROR, TAG, "jarrayObj is null");
2145 jstring jni_setAddress = CALEGetAddressFromBTDevice(env, jarrayObj);
2146 if (!jni_setAddress)
2148 OIC_LOG(ERROR, TAG, "jni_setAddress is null");
2152 const char* setAddress = (*env)->GetStringUTFChars(env, jni_setAddress, NULL);
2155 OIC_LOG(ERROR, TAG, "setAddress is null");
2159 if (!strcmp(remoteAddress, setAddress))
2161 OIC_LOG(DEBUG, TAG, "the device is already set");
2162 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2166 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2169 OIC_LOG(DEBUG, TAG, "OUT - CALEClientIsDeviceInScanDeviceList");
2170 OIC_LOG(DEBUG, TAG, "there are no the device in list. we can add");
2175 CAResult_t CALEClientRemoveAllScanDevices(JNIEnv *env)
2177 OIC_LOG(DEBUG, TAG, "CALEClientRemoveAllScanDevices");
2178 VERIFY_NON_NULL(env, TAG, "env is null");
2180 ca_mutex_lock(g_deviceListMutex);
2184 OIC_LOG(ERROR, TAG, "g_deviceList is null");
2185 ca_mutex_unlock(g_deviceListMutex);
2186 return CA_STATUS_FAILED;
2189 uint32_t length = u_arraylist_length(g_deviceList);
2190 for (uint32_t index = 0; index < length; index++)
2192 jobject jarrayObj = (jobject) u_arraylist_get(g_deviceList, index);
2195 OIC_LOG(ERROR, TAG, "jarrayObj is null");
2198 (*env)->DeleteGlobalRef(env, jarrayObj);
2201 OICFree(g_deviceList);
2202 g_deviceList = NULL;
2204 ca_mutex_unlock(g_deviceListMutex);
2205 return CA_STATUS_OK;
2208 CAResult_t CALEClientRemoveDeviceInScanDeviceList(JNIEnv *env, jstring address)
2210 OIC_LOG(DEBUG, TAG, "CALEClientRemoveDeviceInScanDeviceList");
2211 VERIFY_NON_NULL(address, TAG, "address is null");
2212 VERIFY_NON_NULL(env, TAG, "env is null");
2214 ca_mutex_lock(g_deviceListMutex);
2218 OIC_LOG(ERROR, TAG, "g_deviceList is null");
2219 ca_mutex_unlock(g_deviceListMutex);
2220 return CA_STATUS_FAILED;
2223 uint32_t length = u_arraylist_length(g_deviceList);
2224 for (uint32_t index = 0; index < length; index++)
2226 jobject jarrayObj = (jobject) u_arraylist_get(g_deviceList, index);
2229 OIC_LOG(ERROR, TAG, "jarrayObj is null");
2230 ca_mutex_unlock(g_deviceListMutex);
2231 return CA_STATUS_FAILED;
2234 jstring jni_setAddress = CALEGetAddressFromBTDevice(env, jarrayObj);
2235 if (!jni_setAddress)
2237 OIC_LOG(ERROR, TAG, "jni_setAddress is null");
2238 ca_mutex_unlock(g_deviceListMutex);
2239 return CA_STATUS_FAILED;
2242 const char* setAddress = (*env)->GetStringUTFChars(env, jni_setAddress, NULL);
2245 OIC_LOG(ERROR, TAG, "setAddress is null");
2246 ca_mutex_unlock(g_deviceListMutex);
2247 return CA_STATUS_FAILED;
2250 const char* remoteAddress = (*env)->GetStringUTFChars(env, address, NULL);
2253 OIC_LOG(ERROR, TAG, "remoteAddress is null");
2254 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2255 ca_mutex_unlock(g_deviceListMutex);
2256 return CA_STATUS_FAILED;
2259 if (!strcmp(setAddress, remoteAddress))
2261 OIC_LOG_V(DEBUG, TAG, "remove object : %s", remoteAddress);
2262 (*env)->DeleteGlobalRef(env, jarrayObj);
2263 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2264 (*env)->ReleaseStringUTFChars(env, address, remoteAddress);
2266 if (NULL == u_arraylist_remove(g_deviceList, index))
2268 OIC_LOG(ERROR, TAG, "List removal failed.");
2269 ca_mutex_unlock(g_deviceListMutex);
2270 return CA_STATUS_FAILED;
2272 ca_mutex_unlock(g_deviceListMutex);
2273 return CA_STATUS_OK;
2275 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2276 (*env)->ReleaseStringUTFChars(env, address, remoteAddress);
2279 ca_mutex_unlock(g_deviceListMutex);
2280 OIC_LOG(DEBUG, TAG, "There are no object in the device list");
2282 return CA_STATUS_OK;
2289 CAResult_t CALEClientAddGattobjToList(JNIEnv *env, jobject gatt)
2291 OIC_LOG(DEBUG, TAG, "CALEClientAddGattobjToList");
2292 VERIFY_NON_NULL(env, TAG, "env is null");
2293 VERIFY_NON_NULL(gatt, TAG, "gatt is null");
2295 ca_mutex_lock(g_gattObjectMutex);
2297 jstring jni_remoteAddress = CALEClientGetAddressFromGattObj(env, gatt);
2298 if (!jni_remoteAddress)
2300 OIC_LOG(ERROR, TAG, "jni_remoteAddress is null");
2301 ca_mutex_unlock(g_gattObjectMutex);
2302 return CA_STATUS_FAILED;
2305 const char* remoteAddress = (*env)->GetStringUTFChars(env, jni_remoteAddress, NULL);
2308 OIC_LOG(ERROR, TAG, "remoteAddress is null");
2309 ca_mutex_unlock(g_gattObjectMutex);
2310 return CA_STATUS_FAILED;
2313 if (!CALEClientIsGattObjInList(env, remoteAddress))
2315 jobject newGatt = (*env)->NewGlobalRef(env, gatt);
2316 u_arraylist_add(g_gattObjectList, newGatt);
2317 OIC_LOG(DEBUG, TAG, "Set GATT Object to Array as Element");
2320 (*env)->ReleaseStringUTFChars(env, jni_remoteAddress, remoteAddress);
2321 ca_mutex_unlock(g_gattObjectMutex);
2322 return CA_STATUS_OK;
2325 bool CALEClientIsGattObjInList(JNIEnv *env, const char* remoteAddress)
2327 OIC_LOG(DEBUG, TAG, "CALEClientIsGattObjInList");
2328 VERIFY_NON_NULL(env, TAG, "env is null");
2329 VERIFY_NON_NULL_RET(remoteAddress, TAG, "remoteAddress is null", true);
2331 uint32_t length = u_arraylist_length(g_gattObjectList);
2332 for (uint32_t index = 0; index < length; index++)
2335 jobject jarrayObj = (jobject) u_arraylist_get(g_gattObjectList, index);
2338 OIC_LOG(ERROR, TAG, "jarrayObj is null");
2342 jstring jni_setAddress = CALEClientGetAddressFromGattObj(env, jarrayObj);
2343 if (!jni_setAddress)
2345 OIC_LOG(ERROR, TAG, "jni_setAddress is null");
2349 const char* setAddress = (*env)->GetStringUTFChars(env, jni_setAddress, NULL);
2352 OIC_LOG(ERROR, TAG, "setAddress is null");
2356 if (!strcmp(remoteAddress, setAddress))
2358 OIC_LOG(DEBUG, TAG, "the device is already set");
2359 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2364 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2369 OIC_LOG(DEBUG, TAG, "There are no GATT object in list. it can be added");
2373 jobject CALEClientGetGattObjInList(JNIEnv *env, const char* remoteAddress)
2375 OIC_LOG(DEBUG, TAG, "CALEClientGetGattObjInList");
2376 VERIFY_NON_NULL_RET(env, TAG, "env is null", NULL);
2377 VERIFY_NON_NULL_RET(remoteAddress, TAG, "remoteAddress is null", NULL);
2379 ca_mutex_lock(g_gattObjectMutex);
2380 uint32_t length = u_arraylist_length(g_gattObjectList);
2381 for (uint32_t index = 0; index < length; index++)
2383 jobject jarrayObj = (jobject) u_arraylist_get(g_gattObjectList, index);
2386 OIC_LOG(ERROR, TAG, "jarrayObj is null");
2387 ca_mutex_unlock(g_gattObjectMutex);
2391 jstring jni_setAddress = CALEClientGetAddressFromGattObj(env, jarrayObj);
2392 if (!jni_setAddress)
2394 OIC_LOG(ERROR, TAG, "jni_setAddress is null");
2395 ca_mutex_unlock(g_gattObjectMutex);
2399 const char* setAddress = (*env)->GetStringUTFChars(env, jni_setAddress, NULL);
2402 OIC_LOG(ERROR, TAG, "setAddress is null");
2403 ca_mutex_unlock(g_gattObjectMutex);
2407 if (!strcmp(remoteAddress, setAddress))
2409 OIC_LOG(DEBUG, TAG, "the device is already set");
2410 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2411 ca_mutex_unlock(g_gattObjectMutex);
2414 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2417 ca_mutex_unlock(g_gattObjectMutex);
2418 OIC_LOG(DEBUG, TAG, "There are no the gatt object in list");
2422 CAResult_t CALEClientRemoveAllGattObjs(JNIEnv *env)
2424 OIC_LOG(DEBUG, TAG, "CALEClientRemoveAllGattObjs");
2425 VERIFY_NON_NULL(env, TAG, "env is null");
2427 ca_mutex_lock(g_gattObjectMutex);
2428 if (!g_gattObjectList)
2430 OIC_LOG(ERROR, TAG, "g_gattObjectList is null");
2431 ca_mutex_unlock(g_gattObjectMutex);
2432 return CA_STATUS_FAILED;
2435 uint32_t length = u_arraylist_length(g_gattObjectList);
2436 for (uint32_t index = 0; index < length; index++)
2438 jobject jarrayObj = (jobject) u_arraylist_get(g_gattObjectList, index);
2441 OIC_LOG(ERROR, TAG, "jarrayObj is null");
2444 (*env)->DeleteGlobalRef(env, jarrayObj);
2447 OICFree(g_gattObjectList);
2448 g_gattObjectList = NULL;
2449 ca_mutex_unlock(g_gattObjectMutex);
2450 return CA_STATUS_OK;
2453 CAResult_t CALEClientRemoveGattObj(JNIEnv *env, jobject gatt)
2455 OIC_LOG(DEBUG, TAG, "CALEClientRemoveGattObj");
2456 VERIFY_NON_NULL(gatt, TAG, "gatt is null");
2457 VERIFY_NON_NULL(env, TAG, "env is null");
2459 ca_mutex_lock(g_gattObjectMutex);
2460 if (!g_gattObjectList)
2462 OIC_LOG(ERROR, TAG, "g_gattObjectList is null");
2463 ca_mutex_unlock(g_gattObjectMutex);
2464 return CA_STATUS_FAILED;
2467 uint32_t length = u_arraylist_length(g_gattObjectList);
2468 for (uint32_t index = 0; index < length; index++)
2470 jobject jarrayObj = (jobject) u_arraylist_get(g_gattObjectList, index);
2473 OIC_LOG(ERROR, TAG, "jarrayObj is null");
2474 ca_mutex_unlock(g_gattObjectMutex);
2475 return CA_STATUS_FAILED;
2478 jstring jni_setAddress = CALEClientGetAddressFromGattObj(env, jarrayObj);
2479 if (!jni_setAddress)
2481 OIC_LOG(ERROR, TAG, "jni_setAddress is null");
2482 ca_mutex_unlock(g_gattObjectMutex);
2483 return CA_STATUS_FAILED;
2486 const char* setAddress = (*env)->GetStringUTFChars(env, jni_setAddress, NULL);
2489 OIC_LOG(ERROR, TAG, "setAddress is null");
2490 ca_mutex_unlock(g_gattObjectMutex);
2491 return CA_STATUS_FAILED;
2494 jstring jni_remoteAddress = CALEClientGetAddressFromGattObj(env, gatt);
2495 if (!jni_remoteAddress)
2497 OIC_LOG(ERROR, TAG, "jni_remoteAddress is null");
2498 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2499 ca_mutex_unlock(g_gattObjectMutex);
2500 return CA_STATUS_FAILED;
2503 const char* remoteAddress = (*env)->GetStringUTFChars(env, jni_remoteAddress, NULL);
2506 OIC_LOG(ERROR, TAG, "remoteAddress is null");
2507 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2508 ca_mutex_unlock(g_gattObjectMutex);
2509 return CA_STATUS_FAILED;
2512 if (!strcmp(setAddress, remoteAddress))
2514 OIC_LOG_V(DEBUG, TAG, "remove object : %s", remoteAddress);
2515 (*env)->DeleteGlobalRef(env, jarrayObj);
2516 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2517 (*env)->ReleaseStringUTFChars(env, jni_remoteAddress, remoteAddress);
2519 if (NULL == u_arraylist_remove(g_gattObjectList, index))
2521 OIC_LOG(ERROR, TAG, "List removal failed.");
2522 ca_mutex_unlock(g_gattObjectMutex);
2523 return CA_STATUS_FAILED;
2525 ca_mutex_unlock(g_gattObjectMutex);
2526 return CA_STATUS_OK;
2528 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2529 (*env)->ReleaseStringUTFChars(env, jni_remoteAddress, remoteAddress);
2532 ca_mutex_unlock(g_gattObjectMutex);
2533 OIC_LOG(DEBUG, TAG, "there are no target object");
2534 return CA_STATUS_OK;
2537 CAResult_t CALEClientRemoveGattObjForAddr(JNIEnv *env, jstring addr)
2539 OIC_LOG(DEBUG, TAG, "CALEClientRemoveGattObjForAddr");
2540 VERIFY_NON_NULL(addr, TAG, "addr is null");
2541 VERIFY_NON_NULL(env, TAG, "env is null");
2543 ca_mutex_lock(g_gattObjectMutex);
2544 if (!g_gattObjectList)
2546 OIC_LOG(ERROR, TAG, "g_gattObjectList is null");
2547 ca_mutex_unlock(g_gattObjectMutex);
2548 return CA_STATUS_FAILED;
2551 uint32_t length = u_arraylist_length(g_gattObjectList);
2552 for (uint32_t index = 0; index < length; index++)
2554 jobject jarrayObj = (jobject) u_arraylist_get(g_gattObjectList, index);
2557 OIC_LOG(ERROR, TAG, "jarrayObj is null");
2558 ca_mutex_unlock(g_gattObjectMutex);
2559 return CA_STATUS_FAILED;
2562 jstring jni_setAddress = CALEClientGetAddressFromGattObj(env, jarrayObj);
2563 if (!jni_setAddress)
2565 OIC_LOG(ERROR, TAG, "jni_setAddress is null");
2566 ca_mutex_unlock(g_gattObjectMutex);
2567 return CA_STATUS_FAILED;
2570 const char* setAddress = (*env)->GetStringUTFChars(env, jni_setAddress, NULL);
2573 OIC_LOG(ERROR, TAG, "setAddress is null");
2574 ca_mutex_unlock(g_gattObjectMutex);
2575 return CA_STATUS_FAILED;
2578 const char* remoteAddress = (*env)->GetStringUTFChars(env, addr, NULL);
2581 OIC_LOG(ERROR, TAG, "remoteAddress is null");
2582 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2583 ca_mutex_unlock(g_gattObjectMutex);
2584 return CA_STATUS_FAILED;
2587 if (!strcmp(setAddress, remoteAddress))
2589 OIC_LOG_V(DEBUG, TAG, "remove object : %s", remoteAddress);
2590 (*env)->DeleteGlobalRef(env, jarrayObj);
2592 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2593 (*env)->ReleaseStringUTFChars(env, addr, remoteAddress);
2594 if (NULL == u_arraylist_remove(g_gattObjectList, index))
2596 OIC_LOG(ERROR, TAG, "List removal failed.");
2597 ca_mutex_unlock(g_gattObjectMutex);
2598 return CA_STATUS_FAILED;
2600 ca_mutex_unlock(g_gattObjectMutex);
2601 return CA_STATUS_OK;
2603 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2604 (*env)->ReleaseStringUTFChars(env, addr, remoteAddress);
2607 ca_mutex_unlock(g_gattObjectMutex);
2608 OIC_LOG(DEBUG, TAG, "there are no target object");
2609 return CA_STATUS_FAILED;
2616 CAResult_t CALEClientUpdateDeviceState(const char* address, uint32_t connectedState,
2617 uint16_t notificationState, uint16_t sendState)
2619 VERIFY_NON_NULL(address, TAG, "address is null");
2621 CALEState_t *newstate = (CALEState_t*) OICMalloc(sizeof(CALEState_t));
2624 OIC_LOG(ERROR, TAG, "out of memory");
2625 return CA_MEMORY_ALLOC_FAILED;
2628 if (strlen(address) > CA_MACADDR_SIZE)
2630 OIC_LOG(ERROR, TAG, "address is not proper");
2632 return CA_STATUS_FAILED;
2635 OICStrcpy(newstate->address, sizeof(newstate->address), address);
2636 newstate->connectedState = connectedState;
2637 newstate->notificationState = notificationState;
2638 newstate->sendState = sendState;
2639 return CALEClientAddDeviceStateToList(newstate);
2642 CAResult_t CALEClientAddDeviceStateToList(CALEState_t* state)
2644 VERIFY_NON_NULL(state, TAG, "state is null");
2646 ca_mutex_lock(g_deviceStateListMutex);
2648 if (!g_deviceStateList)
2650 OIC_LOG(ERROR, TAG, "gdevice_list is null");
2651 ca_mutex_unlock(g_deviceStateListMutex);
2652 return CA_STATUS_FAILED;
2655 if (CALEClientIsDeviceInList(state->address))
2657 CALEState_t* curState = CALEClientGetStateInfo(state->address);
2660 OIC_LOG(ERROR, TAG, "curState is null");
2661 ca_mutex_unlock(g_deviceStateListMutex);
2662 return CA_STATUS_FAILED;
2665 if (STATE_CHARACTER_NO_CHANGE == state->notificationState)
2667 state->notificationState = curState->notificationState;
2670 // delete previous state for update new state
2671 CAResult_t res = CALEClientRemoveDeviceState(state->address);
2672 if (CA_STATUS_OK != res)
2674 OIC_LOG(ERROR, TAG, "CALEClientRemoveDeviceState has failed");
2675 ca_mutex_unlock(g_deviceStateListMutex);
2679 u_arraylist_add(g_deviceStateList, state); // update new state
2680 OIC_LOG_V(DEBUG, TAG, "Set State Info to List : %d, %d",
2681 state->connectedState, state->notificationState);
2683 ca_mutex_unlock(g_deviceStateListMutex);
2684 return CA_STATUS_OK;
2687 bool CALEClientIsDeviceInList(const char* remoteAddress)
2689 VERIFY_NON_NULL_RET(remoteAddress, TAG, "remoteAddress is null", false);
2691 if (!g_deviceStateList)
2693 OIC_LOG(ERROR, TAG, "g_deviceStateList is null");
2697 uint32_t length = u_arraylist_length(g_deviceStateList);
2698 for (uint32_t index = 0; index < length; index++)
2700 CALEState_t* state = (CALEState_t*) u_arraylist_get(g_deviceStateList, index);
2703 OIC_LOG(ERROR, TAG, "CALEState_t object is null");
2707 if (!strcmp(remoteAddress, state->address))
2709 OIC_LOG(DEBUG, TAG, "the device is already set");
2718 OIC_LOG(DEBUG, TAG, "there are no the device in list.");
2722 CAResult_t CALEClientRemoveAllDeviceState()
2724 OIC_LOG(DEBUG, TAG, "CALENativeRemoveAllDevices");
2726 ca_mutex_lock(g_deviceStateListMutex);
2727 if (!g_deviceStateList)
2729 OIC_LOG(ERROR, TAG, "g_deviceStateList is null");
2730 ca_mutex_unlock(g_deviceStateListMutex);
2731 return CA_STATUS_FAILED;
2734 uint32_t length = u_arraylist_length(g_deviceStateList);
2735 for (uint32_t index = 0; index < length; index++)
2737 CALEState_t* state = (CALEState_t*) u_arraylist_get(g_deviceStateList, index);
2740 OIC_LOG(ERROR, TAG, "jarrayObj is null");
2746 OICFree(g_deviceStateList);
2747 g_deviceStateList = NULL;
2748 ca_mutex_unlock(g_deviceStateListMutex);
2750 return CA_STATUS_OK;
2753 CAResult_t CALEClientRemoveDeviceState(const char* remoteAddress)
2755 OIC_LOG(DEBUG, TAG, "CALEClientRemoveDeviceState");
2756 VERIFY_NON_NULL(remoteAddress, TAG, "remoteAddress is null");
2758 if (!g_deviceStateList)
2760 OIC_LOG(ERROR, TAG, "g_deviceStateList is null");
2761 return CA_STATUS_FAILED;
2764 uint32_t length = u_arraylist_length(g_deviceStateList);
2765 for (uint32_t index = 0; index < length; index++)
2767 CALEState_t* state = (CALEState_t*) u_arraylist_get(g_deviceStateList, index);
2770 OIC_LOG(ERROR, TAG, "CALEState_t object is null");
2774 if (!strcmp(state->address, remoteAddress))
2776 OIC_LOG_V(DEBUG, TAG, "remove state : %s", remoteAddress);
2779 if (NULL == u_arraylist_remove(g_deviceStateList, index))
2781 OIC_LOG(ERROR, TAG, "List removal failed.");
2782 return CA_STATUS_FAILED;
2785 return CA_STATUS_OK;
2789 return CA_STATUS_FAILED;
2792 CALEState_t* CALEClientGetStateInfo(const char* remoteAddress)
2794 OIC_LOG(DEBUG, TAG, "CALEClientGetStateInfo");
2795 VERIFY_NON_NULL_RET(remoteAddress, TAG, "remoteAddress is null", NULL);
2797 if (!g_deviceStateList)
2799 OIC_LOG(ERROR, TAG, "g_deviceStateList is null");
2803 uint32_t length = u_arraylist_length(g_deviceStateList);
2804 for (uint32_t index = 0; index < length; index++)
2806 CALEState_t* state = (CALEState_t*) u_arraylist_get(g_deviceStateList, index);
2809 OIC_LOG(ERROR, TAG, "CALEState_t object is null");
2813 if (!strcmp(state->address, remoteAddress))
2815 OIC_LOG_V(DEBUG, TAG, "get state : %s", remoteAddress);
2822 bool CALEClientIsConnectedDevice(const char* remoteAddress)
2824 OIC_LOG(DEBUG, TAG, "CALEClientIsConnectedDevice");
2825 VERIFY_NON_NULL_RET(remoteAddress, TAG, "remoteAddress is null", false);
2827 ca_mutex_lock(g_deviceStateListMutex);
2828 if (!g_deviceStateList)
2830 OIC_LOG(ERROR, TAG, "g_deviceStateList is null");
2831 ca_mutex_unlock(g_deviceStateListMutex);
2835 uint32_t length = u_arraylist_length(g_deviceStateList);
2836 for (uint32_t index = 0; index < length; index++)
2838 CALEState_t* state = (CALEState_t*) u_arraylist_get(g_deviceStateList, index);
2841 OIC_LOG(ERROR, TAG, "CALEState_t object is null");
2845 if (!strcmp(state->address, remoteAddress))
2847 OIC_LOG(DEBUG, TAG, "check whether it is connected or not");
2849 if (STATE_CONNECTED == state->connectedState)
2851 ca_mutex_unlock(g_deviceStateListMutex);
2856 ca_mutex_unlock(g_deviceStateListMutex);
2861 ca_mutex_unlock(g_deviceStateListMutex);
2865 bool CALEClientIsSetCharacteristic(const char* remoteAddress)
2867 OIC_LOG(DEBUG, TAG, "CALEClientIsSetCharacteristic");
2868 VERIFY_NON_NULL_RET(remoteAddress, TAG, "remoteAddress is null", false);
2870 ca_mutex_lock(g_deviceStateListMutex);
2871 if (!g_deviceStateList)
2873 OIC_LOG(ERROR, TAG, "g_deviceStateList is null");
2874 ca_mutex_unlock(g_deviceStateListMutex);
2878 uint32_t length = u_arraylist_length(g_deviceStateList);
2879 for (uint32_t index = 0; index < length; index++)
2881 CALEState_t* state = (CALEState_t*) u_arraylist_get(g_deviceStateList, index);
2884 OIC_LOG(ERROR, TAG, "CALEState_t object is null");
2888 if (!strcmp(state->address, remoteAddress))
2890 OIC_LOG_V(DEBUG, TAG, "check whether it was set or not:%d", state->notificationState);
2892 if (STATE_CHARACTER_SET == state->notificationState)
2894 ca_mutex_unlock(g_deviceStateListMutex);
2899 ca_mutex_unlock(g_deviceStateListMutex);
2905 ca_mutex_unlock(g_deviceStateListMutex);
2909 void CALEClientCreateDeviceList()
2911 OIC_LOG(DEBUG, TAG, "CALEClientCreateDeviceList");
2913 // create new object array
2914 if (!g_gattObjectList)
2916 OIC_LOG(DEBUG, TAG, "Create g_gattObjectList");
2918 g_gattObjectList = u_arraylist_create();
2921 if (!g_deviceStateList)
2923 OIC_LOG(DEBUG, TAG, "Create g_deviceStateList");
2925 g_deviceStateList = u_arraylist_create();
2930 OIC_LOG(DEBUG, TAG, "Create g_deviceList");
2932 g_deviceList = u_arraylist_create();
2937 * Check Sent Count for remove g_sendBuffer
2939 void CALEClientUpdateSendCnt(JNIEnv *env)
2941 VERIFY_NON_NULL_VOID(env, TAG, "env is null");
2943 ca_mutex_lock(g_threadMutex);
2947 if (g_targetCnt <= g_currentSentCnt)
2950 g_currentSentCnt = 0;
2954 (*env)->DeleteGlobalRef(env, g_sendBuffer);
2955 g_sendBuffer = NULL;
2957 // notity the thread
2958 ca_cond_signal(g_threadCond);
2959 CALEClientSetSendFinishFlag(true);
2960 OIC_LOG(DEBUG, TAG, "set signal for send data");
2963 ca_mutex_unlock(g_threadMutex);
2966 CAResult_t CALEClientInitGattMutexVaraibles()
2968 OIC_LOG(DEBUG, TAG, "IN");
2970 if (NULL == g_bleReqRespClientCbMutex)
2972 g_bleReqRespClientCbMutex = ca_mutex_new();
2973 if (NULL == g_bleReqRespClientCbMutex)
2975 OIC_LOG(ERROR, TAG, "ca_mutex_new has failed");
2976 return CA_STATUS_FAILED;
2980 if (NULL == g_bleServerBDAddressMutex)
2982 g_bleServerBDAddressMutex = ca_mutex_new();
2983 if (NULL == g_bleServerBDAddressMutex)
2985 OIC_LOG(ERROR, TAG, "ca_mutex_new has failed");
2986 return CA_STATUS_FAILED;
2990 if (NULL == g_threadMutex)
2992 g_threadMutex = ca_mutex_new();
2993 if (NULL == g_threadMutex)
2995 OIC_LOG(ERROR, TAG, "ca_mutex_new has failed");
2996 return CA_STATUS_FAILED;
3000 if (NULL == g_threadSendMutex)
3002 g_threadSendMutex = ca_mutex_new();
3003 if (NULL == g_threadSendMutex)
3005 OIC_LOG(ERROR, TAG, "ca_mutex_new has failed");
3006 return CA_STATUS_FAILED;
3010 if (NULL == g_deviceListMutex)
3012 g_deviceListMutex = ca_mutex_new();
3013 if (NULL == g_deviceListMutex)
3015 OIC_LOG(ERROR, TAG, "ca_mutex_new has failed");
3016 return CA_STATUS_FAILED;
3020 if (NULL == g_gattObjectMutex)
3022 g_gattObjectMutex = ca_mutex_new();
3023 if (NULL == g_gattObjectMutex)
3025 OIC_LOG(ERROR, TAG, "ca_mutex_new has failed");
3026 return CA_STATUS_FAILED;
3030 if (NULL == g_deviceStateListMutex)
3032 g_deviceStateListMutex = ca_mutex_new();
3033 if (NULL == g_deviceStateListMutex)
3035 OIC_LOG(ERROR, TAG, "ca_mutex_new has failed");
3036 return CA_STATUS_FAILED;
3040 if (NULL == g_SendFinishMutex)
3042 g_SendFinishMutex = ca_mutex_new();
3043 if (NULL == g_SendFinishMutex)
3045 OIC_LOG(ERROR, TAG, "ca_mutex_new has failed");
3046 return CA_STATUS_FAILED;
3050 if (NULL == g_scanMutex)
3052 g_scanMutex = ca_mutex_new();
3053 if (NULL == g_scanMutex)
3055 OIC_LOG(ERROR, TAG, "ca_mutex_new has failed");
3056 return CA_STATUS_FAILED;
3060 OIC_LOG(DEBUG, TAG, "OUT");
3061 return CA_STATUS_OK;
3064 void CALEClientTerminateGattMutexVariables()
3066 OIC_LOG(DEBUG, TAG, "IN");
3068 ca_mutex_free(g_bleReqRespClientCbMutex);
3069 g_bleReqRespClientCbMutex = NULL;
3071 ca_mutex_free(g_bleServerBDAddressMutex);
3072 g_bleServerBDAddressMutex = NULL;
3074 ca_mutex_free(g_threadMutex);
3075 g_threadMutex = NULL;
3077 ca_mutex_free(g_threadSendMutex);
3078 g_threadSendMutex = NULL;
3080 ca_mutex_free(g_deviceListMutex);
3081 g_deviceListMutex = NULL;
3083 ca_mutex_free(g_SendFinishMutex);
3084 g_SendFinishMutex = NULL;
3086 ca_mutex_free(g_scanMutex);
3089 OIC_LOG(DEBUG, TAG, "OUT");
3092 void CALEClientSetSendFinishFlag(bool flag)
3094 OIC_LOG_V(DEBUG, TAG, "g_isFinishedSendData is %d", flag);
3096 ca_mutex_lock(g_SendFinishMutex);
3097 g_isFinishedSendData = flag;
3098 ca_mutex_unlock(g_SendFinishMutex);
3105 CAResult_t CAStartLEGattClient()
3107 CAResult_t res = CALEClientStartMulticastServer();
3108 if (CA_STATUS_OK != res)
3110 OIC_LOG(ERROR, TAG, "CALEClientStartMulticastServer has failed");
3114 g_isStartedLEClient = true;
3120 void CAStopLEGattClient()
3122 OIC_LOG(DEBUG, TAG, "CAStopBLEGattClient");
3126 OIC_LOG(ERROR, TAG, "g_jvm is null");
3130 bool isAttached = false;
3132 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
3135 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
3136 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
3140 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
3146 CAResult_t ret = CALEClientDisconnectAll(env);
3147 if (CA_STATUS_OK != ret)
3149 OIC_LOG(ERROR, TAG, "CALEClientDisconnectAll has failed");
3152 ret = CALEClientStopScan();
3153 if(CA_STATUS_OK != ret)
3155 OIC_LOG(ERROR, TAG, "CALEClientStopScan has failed");
3158 ca_cond_signal(g_threadCond);
3162 (*g_jvm)->DetachCurrentThread(g_jvm);
3167 void CATerminateLEGattClient()
3169 OIC_LOG(DEBUG, TAG, "Terminate GATT Client");
3170 CALEClientTerminate();
3173 CAResult_t CAUpdateCharacteristicsToGattServer(const char *remoteAddress, const uint8_t *data,
3174 uint32_t dataLen, CALETransferType_t type,
3177 OIC_LOG(DEBUG, TAG, "call CALEClientSendUnicastMessage");
3178 VERIFY_NON_NULL(data, TAG, "data is null");
3179 VERIFY_NON_NULL(remoteAddress, TAG, "remoteAddress is null");
3181 if (LE_UNICAST != type || position < 0)
3183 OIC_LOG(ERROR, TAG, "this request is not unicast");
3184 return CA_STATUS_INVALID_PARAM;
3187 return CALEClientSendUnicastMessage(remoteAddress, data, dataLen);
3190 CAResult_t CAUpdateCharacteristicsToAllGattServers(const uint8_t *data, uint32_t dataLen)
3192 OIC_LOG(DEBUG, TAG, "call CALEClientSendMulticastMessage");
3193 VERIFY_NON_NULL(data, TAG, "data is null");
3195 return CALEClientSendMulticastMessage(data, dataLen);
3198 void CASetLEReqRespClientCallback(CABLEDataReceivedCallback callback)
3200 OIC_LOG(DEBUG, TAG, "IN");
3202 ca_mutex_lock(g_bleReqRespClientCbMutex);
3203 g_CABLEClientDataReceivedCallback = callback;
3204 ca_mutex_unlock(g_bleReqRespClientCbMutex);
3206 OIC_LOG(DEBUG, TAG, "OUT");
3209 void CASetLEClientThreadPoolHandle(ca_thread_pool_t handle)
3211 OIC_LOG(DEBUG, TAG, "IN");
3213 CALEClientInitialize(handle);
3215 OIC_LOG(DEBUG, TAG, "OUT");
3218 CAResult_t CAGetLEAddress(char **local_address)
3220 VERIFY_NON_NULL(local_address, TAG, "local_address");
3221 OIC_LOG(INFO, TAG, "CAGetLEAddress is not support");
3222 return CA_NOT_SUPPORTED;
3225 JNIEXPORT void JNICALL
3226 Java_org_iotivity_ca_CaLeClientInterface_caLeRegisterLeScanCallback(JNIEnv *env, jobject obj,
3229 OIC_LOG(DEBUG, TAG, "CaLeRegisterLeScanCallback");
3230 VERIFY_NON_NULL_VOID(env, TAG, "env is null");
3231 VERIFY_NON_NULL_VOID(obj, TAG, "obj is null");
3232 VERIFY_NON_NULL_VOID(callback, TAG, "callback is null");
3234 g_leScanCallback = (*env)->NewGlobalRef(env, callback);
3237 JNIEXPORT void JNICALL
3238 Java_org_iotivity_ca_CaLeClientInterface_caLeRegisterGattCallback(JNIEnv *env, jobject obj,
3241 OIC_LOG(DEBUG, TAG, "CaLeRegisterGattCallback");
3242 VERIFY_NON_NULL_VOID(env, TAG, "env is null");
3243 VERIFY_NON_NULL_VOID(obj, TAG, "obj is null");
3244 VERIFY_NON_NULL_VOID(callback, TAG, "callback is null");
3246 g_leGattCallback = (*env)->NewGlobalRef(env, callback);
3249 JNIEXPORT void JNICALL
3250 Java_org_iotivity_ca_CaLeClientInterface_caLeScanCallback(JNIEnv *env, jobject obj,
3253 VERIFY_NON_NULL_VOID(env, TAG, "env is null");
3254 VERIFY_NON_NULL_VOID(obj, TAG, "obj is null");
3255 VERIFY_NON_NULL_VOID(device, TAG, "device is null");
3257 CAResult_t res = CALEClientAddScanDeviceToList(env, device);
3258 if (CA_STATUS_OK != res)
3260 OIC_LOG_V(ERROR, TAG, "CALEClientAddScanDeviceToList has failed : %d", res);
3265 * Class: org_iotivity_ca_jar_caleinterface
3266 * Method: CALeGattConnectionStateChangeCallback
3267 * Signature: (Landroid/bluetooth/BluetoothGatt;II)V
3269 JNIEXPORT void JNICALL
3270 Java_org_iotivity_ca_CaLeClientInterface_caLeGattConnectionStateChangeCallback(JNIEnv *env,
3276 OIC_LOG_V(DEBUG, TAG, "CALeGattConnectionStateChangeCallback - status %d, newstate %d", status,
3278 VERIFY_NON_NULL_VOID(env, TAG, "env is null");
3279 VERIFY_NON_NULL_VOID(obj, TAG, "obj is null");
3280 VERIFY_NON_NULL_VOID(gatt, TAG, "gatt is null");
3282 if (GATT_SUCCESS == status && STATE_CONNECTED == newstate) // le connected
3284 jstring jni_address = CALEClientGetAddressFromGattObj(env, gatt);
3290 const char* address = (*env)->GetStringUTFChars(env, jni_address, NULL);
3293 CAResult_t res = CALEClientUpdateDeviceState(address, STATE_CONNECTED,
3294 STATE_CHARACTER_NO_CHANGE,
3296 if (CA_STATUS_OK != res)
3298 OIC_LOG(ERROR, TAG, "CALEClientUpdateDeviceState has failed");
3299 (*env)->ReleaseStringUTFChars(env, jni_address, address);
3302 (*env)->ReleaseStringUTFChars(env, jni_address, address);
3305 CAResult_t res = CALEClientAddGattobjToList(env, gatt);
3306 if (CA_STATUS_OK != res)
3308 OIC_LOG(ERROR, TAG, "CALEClientAddGattobjToList has failed");
3312 res = CALEClientDiscoverServices(env, gatt);
3313 if (CA_STATUS_OK != res)
3315 OIC_LOG(ERROR, TAG, "CALEClientDiscoverServices has failed");
3319 else // le disconnected
3321 CAResult_t res = CALEClientStartScan();
3322 if (CA_STATUS_OK != res)
3324 OIC_LOG(ERROR, TAG, "CALEClientStartScan has failed");
3328 jstring jni_address = CALEClientGetAddressFromGattObj(env, gatt);
3331 OIC_LOG(ERROR, TAG, "CALEClientGetAddressFromGattObj has failed");
3335 const char* address = (*env)->GetStringUTFChars(env, jni_address, NULL);
3338 res = CALEClientRemoveDeviceState(address);
3339 if (CA_STATUS_OK != res)
3341 OIC_LOG(ERROR, TAG, "CALEClientRemoveDeviceState has failed");
3345 res = CALEClientRemoveGattObjForAddr(env, jni_address);
3346 if (CA_STATUS_OK != res)
3348 OIC_LOG(ERROR, TAG, "CALEClientRemoveGattObjForAddr has failed");
3352 (*env)->ReleaseStringUTFChars(env, jni_address, address);
3355 res = CALEClientGattClose(env, gatt);
3356 if (CA_STATUS_OK != res)
3358 OIC_LOG(ERROR, TAG, "CALEClientGattClose has failed");
3366 CALEClientSendFinish(env, gatt);
3371 * Class: org_iotivity_ca_jar_caleinterface
3372 * Method: CALeGattServicesDiscoveredCallback
3373 * Signature: (Landroid/bluetooth/BluetoothGatt;I)V
3375 JNIEXPORT void JNICALL
3376 Java_org_iotivity_ca_CaLeClientInterface_caLeGattServicesDiscoveredCallback(JNIEnv *env,
3381 OIC_LOG_V(DEBUG, TAG, "CALeGattServicesDiscoveredCallback - status %d: ", status);
3382 VERIFY_NON_NULL_VOID(env, TAG, "env is null");
3383 VERIFY_NON_NULL_VOID(obj, TAG, "obj is null");
3384 VERIFY_NON_NULL_VOID(gatt, TAG, "gatt is null");
3386 if (0 != status) // discovery error
3388 CALEClientSendFinish(env, gatt);
3392 jstring jni_address = CALEClientGetAddressFromGattObj(env, gatt);
3395 CALEClientSendFinish(env, gatt);
3399 const char* address = (*env)->GetStringUTFChars(env, jni_address, NULL);
3402 CALEClientSendFinish(env, gatt);
3406 if (!CALEClientIsSetCharacteristic(address))
3408 jstring jni_uuid = (*env)->NewStringUTF(env, OIC_GATT_CHARACTERISTIC_RESPONSE_UUID);
3411 OIC_LOG(ERROR, TAG, "jni_uuid is null");
3415 jobject jni_obj_GattCharacteristic = CALEClientGetGattService(env, gatt, jni_uuid);
3416 if (!jni_obj_GattCharacteristic)
3418 OIC_LOG(ERROR, TAG, "jni_obj_GattCharacteristic is null");
3422 CAResult_t res = CALEClientSetCharacteristicNotification(env, gatt,
3423 jni_obj_GattCharacteristic);
3424 if (CA_STATUS_OK != res)
3426 OIC_LOG(ERROR, TAG, "CALEClientSetCharacteristicNotification has failed");
3430 res = CALEClientSetUUIDToDescriptor(env, gatt, jni_obj_GattCharacteristic);
3431 if (CA_STATUS_OK != res)
3433 OIC_LOG(INFO, TAG, "Descriptor of the uuid is not found");
3434 CAResult_t res = CALEClientWriteCharacteristic(env, gatt);
3435 if (CA_STATUS_OK != res)
3437 OIC_LOG(ERROR, TAG, "CALEClientWriteCharacteristic has failed");
3442 res = CALEClientUpdateDeviceState(address, STATE_CONNECTED, STATE_CHARACTER_SET,
3444 if (CA_STATUS_OK != res)
3446 OIC_LOG(ERROR, TAG, "CALEClientUpdateDeviceState has failed");
3452 CAResult_t res = CALEClientWriteCharacteristic(env, gatt);
3453 if (CA_STATUS_OK != res)
3455 OIC_LOG(ERROR, TAG, "CALEClientWriteCharacteristic has failed");
3459 (*env)->ReleaseStringUTFChars(env, jni_address, address);
3464 (*env)->ReleaseStringUTFChars(env, jni_address, address);
3465 CALEClientSendFinish(env, gatt);
3470 * Class: org_iotivity_ca_jar_caleinterface
3471 * Method: CALeGattCharacteristicWritjclasseCallback
3472 * Signature: (Landroid/bluetooth/BluetoothGatt;Landroid/bluetooth/BluetoothGattCharacteristic;I)V
3474 JNIEXPORT void JNICALL
3475 Java_org_iotivity_ca_CaLeClientInterface_caLeGattCharacteristicWriteCallback(
3476 JNIEnv *env, jobject obj, jobject gatt, jbyteArray data,
3479 OIC_LOG_V(DEBUG, TAG, "CALeGattCharacteristicWriteCallback - status : %d", status);
3480 VERIFY_NON_NULL_VOID(env, TAG, "env is null");
3481 VERIFY_NON_NULL_VOID(obj, TAG, "obj is null");
3482 VERIFY_NON_NULL_VOID(gatt, TAG, "gatt is null");
3485 char* wroteData = (char*) (*env)->GetByteArrayElements(env, data, &isCopy);
3487 OIC_LOG_V(DEBUG, TAG, "CALeGattCharacteristicWriteCallback - write data : %s", wroteData);
3489 // send success & signal
3490 jstring jni_address = CALEClientGetAddressFromGattObj(env, gatt);
3496 const char* address = (*env)->GetStringUTFChars(env, jni_address, NULL);
3502 if (GATT_SUCCESS != status) // error case
3504 OIC_LOG(ERROR, TAG, "send failure");
3505 CAResult_t res = CALEClientUpdateDeviceState(address, STATE_CONNECTED, STATE_CHARACTER_SET,
3507 if (CA_STATUS_OK != res)
3509 OIC_LOG(ERROR, TAG, "CALEClientUpdateDeviceState has failed");
3512 if (g_clientErrorCallback)
3514 jint length = (*env)->GetArrayLength(env, data);
3515 g_clientErrorCallback(address, data, length, CA_SEND_FAILED);
3518 CALEClientSendFinish(env, gatt);
3522 OIC_LOG(DEBUG, TAG, "send success");
3523 CAResult_t res = CALEClientUpdateDeviceState(address, STATE_CONNECTED, STATE_CHARACTER_SET,
3524 STATE_SEND_SUCCESS);
3525 if (CA_STATUS_OK != res)
3527 OIC_LOG(ERROR, TAG, "CALEClientUpdateDeviceState has failed");
3529 CALEClientUpdateSendCnt(env);
3532 (*env)->ReleaseStringUTFChars(env, jni_address, address);
3538 CALEClientSendFinish(env, gatt);
3543 * Class: org_iotivity_ca_jar_caleinterface
3544 * Method: CALeGattCharacteristicChangedCallback
3545 * Signature: (Landroid/bluetooth/BluetoothGatt;Landroid/bluetooth/BluetoothGattCharacteristic;)V
3547 JNIEXPORT void JNICALL
3548 Java_org_iotivity_ca_CaLeClientInterface_caLeGattCharacteristicChangedCallback(
3549 JNIEnv *env, jobject obj, jobject gatt, jbyteArray data)
3551 OIC_LOG(DEBUG, TAG, "CALeGattCharacteristicChangedCallback");
3552 VERIFY_NON_NULL_VOID(env, TAG, "env is null");
3553 VERIFY_NON_NULL_VOID(obj, TAG, "obj is null");
3554 VERIFY_NON_NULL_VOID(gatt, TAG, "gatt is null");
3555 VERIFY_NON_NULL_VOID(data, TAG, "data is null");
3557 // get Byte Array and convert to uint8_t*
3558 jint length = (*env)->GetArrayLength(env, data);
3561 jbyte *jni_byte_responseData = (jbyte*) (*env)->GetByteArrayElements(env, data, &isCopy);
3563 OIC_LOG_V(DEBUG, TAG, "CALeGattCharacteristicChangedCallback - raw data received : %p",
3564 jni_byte_responseData);
3566 uint8_t* receivedData = OICMalloc(length);
3569 OIC_LOG(ERROR, TAG, "receivedData is null");
3573 memcpy(receivedData, jni_byte_responseData, length);
3574 (*env)->ReleaseByteArrayElements(env, data, jni_byte_responseData, JNI_ABORT);
3576 jstring jni_address = CALEClientGetAddressFromGattObj(env, gatt);
3579 OIC_LOG(ERROR, TAG, "jni_address is null");
3580 OICFree(receivedData);
3584 const char* address = (*env)->GetStringUTFChars(env, jni_address, NULL);
3587 OIC_LOG(ERROR, TAG, "address is null");
3588 OICFree(receivedData);
3592 OIC_LOG_V(DEBUG, TAG, "CALeGattCharacteristicChangedCallback - data. : %p, %d",
3593 receivedData, length);
3595 ca_mutex_lock(g_bleServerBDAddressMutex);
3596 uint32_t sentLength = 0;
3597 g_CABLEClientDataReceivedCallback(address, receivedData, length,
3599 ca_mutex_unlock(g_bleServerBDAddressMutex);
3601 (*env)->ReleaseStringUTFChars(env, jni_address, address);
3605 * Class: org_iotivity_ca_jar_caleinterface
3606 * Method: CALeGattDescriptorWriteCallback
3607 * Signature: (Landroid/bluetooth/BluetoothGatt;Landroid/bluetooth/BluetoothGattDescriptor;I)V
3609 JNIEXPORT void JNICALL
3610 Java_org_iotivity_ca_CaLeClientInterface_caLeGattDescriptorWriteCallback(JNIEnv *env, jobject obj,
3614 OIC_LOG_V(DEBUG, TAG, "CALeGattDescriptorWriteCallback - status %d: ", status);
3615 VERIFY_NON_NULL_VOID(env, TAG, "env is null");
3616 VERIFY_NON_NULL_VOID(obj, TAG, "obj is null");
3617 VERIFY_NON_NULL_VOID(gatt, TAG, "gatt is null");
3619 CAResult_t res = CALEClientWriteCharacteristic(env, gatt);
3620 if (CA_STATUS_OK != res)
3622 OIC_LOG(ERROR, TAG, "CALEClientWriteCharacteristic has failed");
3630 CALEClientSendFinish(env, gatt);