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 ******************************************************************/
24 #include <android/log.h>
26 #include "caleserver.h"
27 #include "caleutils.h"
28 #include "caleinterface.h"
29 #include "caadapterutils.h"
32 #include "oic_malloc.h"
33 #include "cathreadpool.h"
35 #include "uarraylist.h"
36 #include "org_iotivity_ca_CaLeServerInterface.h"
38 #define TAG PCF("OIC_CA_LE_SERVER")
40 #define WAIT_TIME_WRITE_CHARACTERISTIC 10000000
42 static JavaVM *g_jvm = NULL;
43 static jobject g_context = NULL;
44 static jobject g_bluetoothGattServer = NULL;
45 static jobject g_bluetoothGattServerCallback = NULL;
46 static jobject g_leAdvertiseCallback = NULL;
48 static CAPacketReceiveCallback g_packetReceiveCallback = NULL;
49 static CABLEErrorHandleCallback g_serverErrorCallback;
51 static u_arraylist_t *g_connectedDeviceList = NULL;
53 static bool g_isStartServer = false;
54 static bool g_isInitializedServer = false;
56 static jbyteArray g_sendBuffer = NULL;
58 static CABLEDataReceivedCallback g_CABLEServerDataReceivedCallback = NULL;
59 static ca_mutex g_bleReqRespCbMutex = NULL;
60 static ca_mutex g_bleClientBDAddressMutex = NULL;
61 static ca_mutex g_connectedDeviceListMutex = NULL;
63 static ca_mutex g_threadSendMutex = NULL;
64 static ca_mutex g_threadSendNotifyMutex = NULL;
65 static ca_cond g_threadSendNotifyCond = NULL;
66 static bool g_isSignalSetFlag = false;
68 void CALEServerJNISetContext()
70 OIC_LOG(DEBUG, TAG, "CALEServerJNISetContext");
71 g_context = (jobject) CANativeJNIGetContext();
74 void CALeServerJniInit()
76 OIC_LOG(DEBUG, TAG, "CALeServerJniInit");
77 g_jvm = (JavaVM*) CANativeJNIGetJavaVM();
80 CAResult_t CALEServerCreateJniInterfaceObject()
82 OIC_LOG(DEBUG, TAG, "CALEServerCreateJniInterfaceObject");
86 OIC_LOG(ERROR, TAG, "g_context is null");
87 return CA_STATUS_FAILED;
92 OIC_LOG(ERROR, TAG, "g_jvm is null");
93 return CA_STATUS_FAILED;
96 bool isAttached = false;
98 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
101 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
102 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
106 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
107 return CA_STATUS_FAILED;
112 jclass jni_LEInterface = (*env)->FindClass(env, "org/iotivity/ca/CaLeServerInterface");
113 if (!jni_LEInterface)
115 OIC_LOG(ERROR, TAG, "Could not get CaLeServerInterface class");
119 jmethodID LeInterfaceConstructorMethod = (*env)->GetMethodID(env, jni_LEInterface, "<init>",
121 if (!LeInterfaceConstructorMethod)
123 OIC_LOG(ERROR, TAG, "Could not get CaLeServerInterface constructor method");
127 (*env)->NewObject(env, jni_LEInterface, LeInterfaceConstructorMethod, g_context);
128 OIC_LOG(DEBUG, TAG, "Create instance for CaLeServerInterface");
132 (*g_jvm)->DetachCurrentThread(g_jvm);
141 (*g_jvm)->DetachCurrentThread(g_jvm);
144 return CA_STATUS_FAILED;
147 jobject CALEServerSetResponseData(JNIEnv *env, jbyteArray responseData)
149 OIC_LOG(DEBUG, TAG, "IN - CALEServerSetResponseData");
150 VERIFY_NON_NULL_RET(env, TAG, "env is null", NULL);
151 VERIFY_NON_NULL_RET(responseData, TAG, "responseData is null", NULL);
153 if (!g_bluetoothGattServer)
155 OIC_LOG(ERROR, TAG, "Check BluetoothGattServer status");
159 if (!CALEIsEnableBTAdapter(env))
161 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
165 OIC_LOG(DEBUG, TAG, "CALEServerSetResponseData");
167 jclass jni_cid_bluetoothGattServer = (*env)->FindClass(env,
168 "android/bluetooth/BluetoothGattServer");
169 if (!jni_cid_bluetoothGattServer)
171 OIC_LOG(ERROR, TAG, "jni_cid_bluetoothGattServer is null");
175 jclass jni_cid_bluetoothGattService = (*env)->FindClass(env, "android/bluetooth/"
176 "BluetoothGattService");
177 if (!jni_cid_bluetoothGattService)
179 OIC_LOG(ERROR, TAG, "jni_cid_bluetoothGattService is null");
183 jclass jni_cid_bluetoothGattCharacteristic = (*env)->FindClass(env, "android/bluetooth/"
184 "BluetoothGattCharacteristic");
185 if (!jni_cid_bluetoothGattCharacteristic)
187 OIC_LOG(ERROR, TAG, "jni_cid_bluetoothGattCharacteristic is null");
191 jmethodID jni_mid_getService = (*env)->GetMethodID(env, jni_cid_bluetoothGattServer,
193 "(Ljava/util/UUID;)Landroid/bluetooth/"
194 "BluetoothGattService;");
195 if (!jni_mid_getService)
197 OIC_LOG(ERROR, TAG, "jni_mid_getService is null");
201 jobject jni_obj_serviceUUID = CALEGetUuidFromString(env, OIC_GATT_SERVICE_UUID);
202 if (!jni_obj_serviceUUID)
204 OIC_LOG(ERROR, TAG, "jni_obj_serviceUUID is null");
208 jobject jni_obj_bluetoothGattService = (*env)->CallObjectMethod(env, g_bluetoothGattServer,
210 jni_obj_serviceUUID);
211 if (!jni_obj_bluetoothGattService)
213 OIC_LOG(ERROR, TAG, "jni_obj_bluetoothGattService is null");
217 jmethodID jni_mid_getCharacteristic = (*env)->GetMethodID(env, jni_cid_bluetoothGattService,
220 "Landroid/bluetooth/"
221 "BluetoothGattCharacteristic;");
222 if (!jni_mid_getCharacteristic)
224 OIC_LOG(ERROR, TAG, "jni_mid_getCharacteristic is null");
228 jobject jni_obj_responseUUID = CALEGetUuidFromString(env,
229 OIC_GATT_CHARACTERISTIC_RESPONSE_UUID);
230 if (!jni_obj_responseUUID)
232 OIC_LOG(ERROR, TAG, "jni_obj_responseUUID is null");
236 jobject jni_obj_bluetoothGattCharacteristic = (*env)->CallObjectMethod(
237 env, jni_obj_bluetoothGattService, jni_mid_getCharacteristic, jni_obj_responseUUID);
238 if (!jni_obj_bluetoothGattCharacteristic)
240 OIC_LOG(ERROR, TAG, "jni_obj_bluetoothGattCharacteristic is null");
244 jmethodID jni_mid_setValue = (*env)->GetMethodID(env, jni_cid_bluetoothGattCharacteristic,
245 "setValue", "([B)Z");
246 if (!jni_mid_setValue)
248 OIC_LOG(ERROR, TAG, "jni_mid_setValue is null");
252 jboolean jni_boolean_setValue = (*env)->CallBooleanMethod(env,
253 jni_obj_bluetoothGattCharacteristic,
254 jni_mid_setValue, responseData);
255 if (JNI_FALSE == jni_boolean_setValue)
257 OIC_LOG(ERROR, TAG, "Fail to set response data");
260 OIC_LOG(DEBUG, TAG, "OUT - CALEServerSetResponseData");
261 return jni_obj_bluetoothGattCharacteristic;
264 CAResult_t CALEServerSendResponseData(JNIEnv *env, jobject device, jobject responseData)
266 OIC_LOG(DEBUG, TAG, "CALEServerSendResponseData");
267 VERIFY_NON_NULL(responseData, TAG, "responseData is null");
268 VERIFY_NON_NULL(device, TAG, "device is null");
269 VERIFY_NON_NULL(env, TAG, "env is null");
271 if (!CALEIsEnableBTAdapter(env))
273 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
274 return CA_ADAPTER_NOT_ENABLED;
277 jclass jni_cid_bluetoothGattServer = (*env)->FindClass(env,
278 "android/bluetooth/BluetoothGattServer");
279 if (!jni_cid_bluetoothGattServer)
281 OIC_LOG(ERROR, TAG, "jni_cid_bluetoothGattServer is null");
282 return CA_STATUS_FAILED;
285 jmethodID jni_mid_notifyCharacteristicChanged = (*env)->GetMethodID(
286 env, jni_cid_bluetoothGattServer, "notifyCharacteristicChanged",
287 "(Landroid/bluetooth/BluetoothDevice;"
288 "Landroid/bluetooth/BluetoothGattCharacteristic;Z)Z");
289 if (!jni_mid_notifyCharacteristicChanged)
291 OIC_LOG(ERROR, TAG, "jni_mid_notifyCharacteristicChanged is null");
292 return CA_STATUS_FAILED;
295 jboolean jni_boolean_notifyCharacteristicChanged = (*env)->CallBooleanMethod(
296 env, g_bluetoothGattServer, jni_mid_notifyCharacteristicChanged, device, responseData,
298 if (JNI_FALSE == jni_boolean_notifyCharacteristicChanged)
300 OIC_LOG(ERROR, TAG, "Fail to notify characteristic");
301 return CA_SEND_FAILED;
304 OIC_LOG_V(DEBUG, TAG, "callback flag is %d", g_isSignalSetFlag);
305 ca_mutex_lock(g_threadSendNotifyMutex);
306 if (!g_isSignalSetFlag)
308 OIC_LOG(DEBUG, TAG, "wait for callback to notify notifyCharacteristic is success");
309 if (0 != ca_cond_wait_for(g_threadSendNotifyCond, g_threadSendNotifyMutex,
310 WAIT_TIME_WRITE_CHARACTERISTIC))
312 OIC_LOG(ERROR, TAG, "there is no response. notifyCharacteristic has failed");
313 ca_mutex_unlock(g_threadSendNotifyMutex);
314 return CA_STATUS_FAILED;
317 // reset flag set by writeCharacteristic Callback
318 g_isSignalSetFlag = false;
319 ca_mutex_unlock(g_threadSendNotifyMutex);
320 OIC_LOG(INFO, TAG, "notifyCharacteristic success");
324 CAResult_t CALEServerSendResponse(JNIEnv *env, jobject device, jint requestId, jint status,
325 jint offset, jbyteArray value)
327 OIC_LOG(DEBUG, TAG, "IN - CALEServerSendResponse");
328 VERIFY_NON_NULL(env, TAG, "env is null");
329 VERIFY_NON_NULL(device, TAG, "device is null");
330 VERIFY_NON_NULL(value, TAG, "value is null");
332 OIC_LOG(DEBUG, TAG, "CALEServerSendResponse");
334 if (!CALEIsEnableBTAdapter(env))
336 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
337 return CA_ADAPTER_NOT_ENABLED;
340 jclass jni_cid_bluetoothGattServer = (*env)->FindClass(env,
341 "android/bluetooth/BluetoothGattServer");
342 if (!jni_cid_bluetoothGattServer)
344 OIC_LOG(ERROR, TAG, "jni_cid_bluetoothGattServer is null");
345 return CA_STATUS_FAILED;
348 jmethodID jni_mid_sendResponse = (*env)->GetMethodID(env, jni_cid_bluetoothGattServer,
350 "(Landroid/bluetooth/BluetoothDevice;"
352 if (!jni_mid_sendResponse)
354 OIC_LOG(ERROR, TAG, "jni_mid_sendResponse is null");
355 return CA_STATUS_FAILED;
358 jboolean jni_boolean_sendResponse = (*env)->CallBooleanMethod(env, g_bluetoothGattServer,
359 jni_mid_sendResponse, device,
360 requestId, status, offset,
362 if (JNI_FALSE == jni_boolean_sendResponse)
364 OIC_LOG(ERROR, TAG, "Fail to send response for gatt characteristic write request");
365 return CA_SEND_FAILED;
368 OIC_LOG(DEBUG, TAG, "OUT - CALEServerSendResponse");
372 CAResult_t CALEStartAdvertise()
376 OIC_LOG(ERROR, TAG, "g_jvm is null");
377 return CA_STATUS_FAILED;
380 bool isAttached = false;
382 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
385 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
386 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
390 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
391 return CA_STATUS_FAILED;
397 CAResult_t ret = CALEServerStartAdvertise(env, g_leAdvertiseCallback);
398 if (CA_STATUS_OK != ret)
400 OIC_LOG(ERROR, TAG, "CALEServerStartAdvertise has failed");
405 (*g_jvm)->DetachCurrentThread(g_jvm);
410 CAResult_t CALEServerStartAdvertise(JNIEnv *env, jobject advertiseCallback)
412 OIC_LOG(DEBUG, TAG, "IN - CALEServerStartAdvertise");
413 VERIFY_NON_NULL(env, TAG, "env is null");
414 VERIFY_NON_NULL(advertiseCallback, TAG, "advertiseCallback is null");
416 if (!CALEIsEnableBTAdapter(env))
418 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
419 return CA_ADAPTER_NOT_ENABLED;
422 jclass jni_cid_AdvertiseSettings = (*env)->FindClass(env,
423 "android/bluetooth/le/"
424 "AdvertiseSettings$Builder");
425 if (!jni_cid_AdvertiseSettings)
427 OIC_LOG(ERROR, TAG, "jni_cid_AdvertiseSettings is null");
428 return CA_STATUS_FAILED;
431 jmethodID jni_mid_AdvertiseSettings = (*env)->GetMethodID(env, jni_cid_AdvertiseSettings,
433 if (!jni_mid_AdvertiseSettings)
435 OIC_LOG(ERROR, TAG, "jni_mid_AdvertiseSettings is null");
436 return CA_STATUS_FAILED;
439 jobject jni_AdvertiseSettings = (*env)->NewObject(env, jni_cid_AdvertiseSettings,
440 jni_mid_AdvertiseSettings);
441 if (!jni_AdvertiseSettings)
443 OIC_LOG(ERROR, TAG, "jni_AdvertiseSettings is null");
444 return CA_STATUS_FAILED;
447 jmethodID jni_mid_setAdvertiseMode = (*env)->GetMethodID(env, jni_cid_AdvertiseSettings,
449 "(I)Landroid/bluetooth/le/"
450 "AdvertiseSettings$Builder;");
451 if (!jni_mid_setAdvertiseMode)
453 OIC_LOG(ERROR, TAG, "jni_mid_setAdvertiseMode is null");
454 return CA_STATUS_FAILED;
457 // 0: Low power, 1: Balanced
458 jobject jni_obj_setAdvertiseMode = (*env)->CallObjectMethod(env, jni_AdvertiseSettings,
459 jni_mid_setAdvertiseMode, 0);
460 if (!jni_obj_setAdvertiseMode)
462 OIC_LOG(ERROR, TAG, "jni_obj_setAdvertiseMode is null");
463 return CA_STATUS_FAILED;
466 jmethodID jni_mid_setConnectable = (*env)->GetMethodID(env, jni_cid_AdvertiseSettings,
468 "(Z)Landroid/bluetooth/le/"
469 "AdvertiseSettings$Builder;");
470 if (!jni_mid_setConnectable)
472 OIC_LOG(ERROR, TAG, "jni_mid_setConnectable is null");
473 return CA_STATUS_FAILED;
476 jobject jni_obj_setConnectable = (*env)->CallObjectMethod(env, jni_AdvertiseSettings,
477 jni_mid_setConnectable, JNI_TRUE);
478 if (!jni_obj_setConnectable)
480 OIC_LOG(ERROR, TAG, "jni_obj_setConnectable is null");
481 return CA_STATUS_FAILED;
484 jmethodID jni_mid_setTimeout = (*env)->GetMethodID(env, jni_cid_AdvertiseSettings, "setTimeout",
485 "(I)Landroid/bluetooth/le/"
486 "AdvertiseSettings$Builder;");
487 if (!jni_mid_setTimeout)
489 OIC_LOG(ERROR, TAG, "jni_mid_setTimeout is null");
490 return CA_STATUS_FAILED;
493 //A value of 0 will disable the time limit
494 jobject jni_obj_setTimeout = (*env)->CallObjectMethod(env, jni_AdvertiseSettings,
495 jni_mid_setTimeout, 0);
496 if (!jni_obj_setTimeout)
498 OIC_LOG(ERROR, TAG, "jni_obj_setTimeout is null");
499 return CA_STATUS_FAILED;
502 jclass jni_cid_AdvertiseDataBuilder = (*env)->FindClass(env,
503 "android/bluetooth/le/"
504 "AdvertiseData$Builder");
505 if (!jni_cid_AdvertiseDataBuilder)
507 OIC_LOG(ERROR, TAG, "jni_cid_AdvertiseDataBuilder is null");
508 return CA_STATUS_FAILED;
511 jmethodID jni_mid_AdvertiseDataBuilder = (*env)->GetMethodID(env, jni_cid_AdvertiseDataBuilder,
513 if (!jni_mid_AdvertiseDataBuilder)
515 OIC_LOG(ERROR, TAG, "jni_mid_AdvertiseDataBuilder is null");
516 return CA_STATUS_FAILED;
519 jobject jni_AdvertiseDataBuilder = (*env)->NewObject(env, jni_cid_AdvertiseDataBuilder,
520 jni_mid_AdvertiseDataBuilder);
521 if (!jni_AdvertiseDataBuilder)
523 OIC_LOG(ERROR, TAG, "jni_AdvertiseDataBuilder is null");
524 return CA_STATUS_FAILED;
527 jobject jni_obj_serviceUUID = CALEGetUuidFromString(env, OIC_GATT_SERVICE_UUID);
528 if (!jni_obj_serviceUUID)
530 OIC_LOG(ERROR, TAG, "jni_obj_serviceUUID is null");
531 return CA_STATUS_FAILED;
534 jobject jni_ParcelUuid = CALEGetParcelUuid(env, jni_obj_serviceUUID);
537 OIC_LOG(ERROR, TAG, "jni_ParcelUuid is null");
538 return CA_STATUS_FAILED;
541 jmethodID jni_mid_addServiceUuid = (*env)->GetMethodID(env, jni_cid_AdvertiseDataBuilder,
543 "(Landroid/os/ParcelUuid;)Landroid/"
544 "bluetooth/le/AdvertiseData$Builder;");
545 if (!jni_mid_addServiceUuid)
547 OIC_LOG(ERROR, TAG, "jni_mid_addServiceUuid is null");
548 return CA_STATUS_FAILED;
551 jobject jni_obj_addServiceUuid = (*env)->CallObjectMethod(env, jni_AdvertiseDataBuilder,
552 jni_mid_addServiceUuid,
554 if (!jni_obj_addServiceUuid)
556 OIC_LOG(ERROR, TAG, "jni_obj_addServiceUuid is null");
557 return CA_STATUS_FAILED;
560 jclass jni_cid_BTAdapter = (*env)->FindClass(env, "android/bluetooth/BluetoothAdapter");
561 if (!jni_cid_BTAdapter)
563 OIC_LOG(ERROR, TAG, "jni_cid_BTAdapter is null");
564 return CA_STATUS_FAILED;
567 jmethodID jni_mid_getDefaultAdapter = (*env)->GetStaticMethodID(env, jni_cid_BTAdapter,
569 "()Landroid/bluetooth/"
570 "BluetoothAdapter;");
571 if (!jni_mid_getDefaultAdapter)
573 OIC_LOG(ERROR, TAG, "jni_mid_getDefaultAdapter is null");
574 return CA_STATUS_FAILED;
577 jobject jni_obj_BTAdapter = (*env)->CallStaticObjectMethod(env, jni_cid_BTAdapter,
578 jni_mid_getDefaultAdapter);
579 if (!jni_obj_BTAdapter)
581 OIC_LOG(ERROR, TAG, "jni_obj_BTAdapter is null");
582 return CA_STATUS_FAILED;
585 jmethodID jni_mid_getBluetoothLeAdvertiser = (*env)->GetMethodID(env, jni_cid_BTAdapter,
586 "getBluetoothLeAdvertiser",
587 "()Landroid/bluetooth/le/"
588 "BluetoothLeAdvertiser;");
589 if (!jni_mid_getBluetoothLeAdvertiser)
591 OIC_LOG(ERROR, TAG, "jni_mid_getBluetoothLeAdvertiser is null");
592 return CA_STATUS_FAILED;
595 jobject jni_obj_getBluetoothLeAdvertiser = (*env)->CallObjectMethod(
596 env, jni_obj_BTAdapter, jni_mid_getBluetoothLeAdvertiser);
597 if (!jni_obj_getBluetoothLeAdvertiser)
599 OIC_LOG(ERROR, TAG, "jni_obj_getBluetoothLeAdvertiser is null");
600 return CA_STATUS_FAILED;
603 jmethodID jni_mid_build_LeAdvertiseSettings = (*env)->GetMethodID(env,
604 jni_cid_AdvertiseSettings,
606 "()Landroid/bluetooth/le/"
607 "AdvertiseSettings;");
608 if (!jni_mid_build_LeAdvertiseSettings)
610 OIC_LOG(ERROR, TAG, "jni_mid_build_LeAdvertiseSettings is null");
611 return CA_STATUS_FAILED;
614 jobject jni_obj_build_LeAdvertiseSettings = (*env)->CallObjectMethod(
615 env, jni_AdvertiseSettings, jni_mid_build_LeAdvertiseSettings);
616 if (!jni_obj_build_LeAdvertiseSettings)
618 OIC_LOG(ERROR, TAG, "jni_obj_build_LeAdvertiseSettings is null");
619 return CA_STATUS_FAILED;
622 jmethodID jni_mid_build_LeAdvertiseData = (*env)->GetMethodID(env, jni_cid_AdvertiseDataBuilder,
624 "()Landroid/bluetooth/le/"
626 if (!jni_mid_build_LeAdvertiseData)
628 OIC_LOG(ERROR, TAG, "jni_mid_build_LeAdvertiseData is null");
629 return CA_STATUS_FAILED;
632 jobject jni_obj_build_LeAdvertiseData = (*env)->CallObjectMethod(env, jni_AdvertiseDataBuilder,
633 jni_mid_build_LeAdvertiseData);
634 if (!jni_obj_build_LeAdvertiseData)
636 OIC_LOG(ERROR, TAG, "jni_obj_build_LeAdvertiseData is null");
637 return CA_STATUS_FAILED;
640 jclass jni_cid_leAdvertiser = (*env)->FindClass(env,
641 "android/bluetooth/le/BluetoothLeAdvertiser");
642 if (!jni_cid_leAdvertiser)
644 OIC_LOG(ERROR, TAG, "jni_cid_leAdvertiser is null");
645 return CA_STATUS_FAILED;
648 jmethodID jni_mid_startAdvertising = (*env)->GetMethodID(env, jni_cid_leAdvertiser,
650 "(Landroid/bluetooth/le/"
651 "AdvertiseSettings;Landroid/bluetooth/"
652 "le/AdvertiseData;Landroid/bluetooth/"
653 "le/AdvertiseCallback;)V");
654 if (!jni_mid_startAdvertising)
656 OIC_LOG(ERROR, TAG, "jni_mid_startAdvertising is null");
657 return CA_STATUS_FAILED;
660 (*env)->CallVoidMethod(env, jni_obj_getBluetoothLeAdvertiser, jni_mid_startAdvertising,
661 jni_obj_build_LeAdvertiseSettings, jni_obj_build_LeAdvertiseData,
664 if ((*env)->ExceptionCheck(env))
666 OIC_LOG(ERROR, TAG, "StartAdvertising has failed");
667 (*env)->ExceptionDescribe(env);
668 (*env)->ExceptionClear(env);
669 return CA_STATUS_FAILED;
672 OIC_LOG(DEBUG, TAG, "Advertising started!!");
674 OIC_LOG(DEBUG, TAG, "OUT - CALEServerStartAdvertise");
678 CAResult_t CALEServerStopAdvertise(JNIEnv *env, jobject advertiseCallback)
680 OIC_LOG(DEBUG, TAG, "LEServerStopAdvertise");
681 VERIFY_NON_NULL(env, TAG, "env is null");
682 VERIFY_NON_NULL(advertiseCallback, TAG, "advertiseCallback is null");
684 if (!CALEIsEnableBTAdapter(env))
686 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
687 return CA_ADAPTER_NOT_ENABLED;
690 jclass jni_cid_BTAdapter = (*env)->FindClass(env, "android/bluetooth/BluetoothAdapter");
691 if (!jni_cid_BTAdapter)
693 OIC_LOG(ERROR, TAG, "jni_cid_BTAdapter is null");
694 return CA_STATUS_FAILED;
697 jclass jni_cid_leAdvertiser = (*env)->FindClass(env,
698 "android/bluetooth/le/BluetoothLeAdvertiser");
699 if (!jni_cid_leAdvertiser)
701 OIC_LOG(ERROR, TAG, "jni_cid_leAdvertiser is null");
702 return CA_STATUS_FAILED;
705 jmethodID jni_mid_getDefaultAdapter = (*env)->GetStaticMethodID(env, jni_cid_BTAdapter,
707 "()Landroid/bluetooth/"
708 "BluetoothAdapter;");
709 if (!jni_mid_getDefaultAdapter)
711 OIC_LOG(ERROR, TAG, "jni_mid_getDefaultAdapter is null");
712 return CA_STATUS_FAILED;
715 jmethodID jni_mid_getBTLeAdvertiser = (*env)->GetMethodID(env, jni_cid_BTAdapter,
716 "getBluetoothLeAdvertiser",
717 "()Landroid/bluetooth/le/"
718 "BluetoothLeAdvertiser;");
719 if (!jni_mid_getBTLeAdvertiser)
721 OIC_LOG(ERROR, TAG, "jni_mid_getBTLeAdvertiser is null");
722 return CA_STATUS_FAILED;
725 jmethodID jni_mid_stopAdvertising = (*env)->GetMethodID(env, jni_cid_leAdvertiser,
727 "(Landroid/bluetooth/le/"
728 "AdvertiseCallback;)V");
729 if (!jni_mid_stopAdvertising)
731 OIC_LOG(ERROR, TAG, "jni_mid_stopAdvertising is null");
732 return CA_STATUS_FAILED;
735 jobject jni_obj_BTAdapter = (*env)->CallStaticObjectMethod(env, jni_cid_BTAdapter,
736 jni_mid_getDefaultAdapter);
737 if (!jni_obj_BTAdapter)
739 OIC_LOG(ERROR, TAG, "jni_obj_BTAdapter is null");
740 return CA_STATUS_FAILED;
743 jobject jni_obj_getBluetoothLeAdvertiser = (*env)->CallObjectMethod(env, jni_obj_BTAdapter,
744 jni_mid_getBTLeAdvertiser);
745 if (!jni_obj_getBluetoothLeAdvertiser)
747 OIC_LOG(ERROR, TAG, "jni_obj_getBluetoothLeAdvertiser is null");
748 return CA_STATUS_FAILED;
751 (*env)->CallVoidMethod(env, jni_obj_getBluetoothLeAdvertiser, jni_mid_stopAdvertising,
753 if ((*env)->ExceptionCheck(env))
755 OIC_LOG(ERROR, TAG, "getBluetoothLeAdvertiser has failed");
756 (*env)->ExceptionDescribe(env);
757 (*env)->ExceptionClear(env);
758 return CA_STATUS_FAILED;
761 OIC_LOG(DEBUG, TAG, "Advertising stopped!!");
765 CAResult_t CALEServerStartGattServer(JNIEnv *env, jobject gattServerCallback)
767 OIC_LOG(DEBUG, TAG, "IN - CALEServerStartGattServer");
768 VERIFY_NON_NULL(env, TAG, "env is null");
769 VERIFY_NON_NULL(gattServerCallback, TAG, "gattServerCallback is null");
771 if (!CALEIsEnableBTAdapter(env))
773 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
774 return CA_ADAPTER_NOT_ENABLED;
779 OIC_LOG(DEBUG, TAG, "Gatt server already started");
782 g_bluetoothGattServerCallback = (*env)->NewGlobalRef(env, gattServerCallback);
785 jobject bluetoothGattServer = CALEServerOpenGattServer(env);
786 if (!bluetoothGattServer)
788 OIC_LOG(ERROR, TAG, "bluetoothGattServer is null");
789 return CA_STATUS_FAILED;
792 g_bluetoothGattServer = (*env)->NewGlobalRef(env, bluetoothGattServer);
793 if (!g_bluetoothGattServer)
795 OIC_LOG(ERROR, TAG, "g_bluetoothGattServer is null");
796 return CA_STATUS_FAILED;
799 // create gatt service
800 jobject bluetoothGattService = CALEServerCreateGattService(env);
801 if (!bluetoothGattService)
803 OIC_LOG(ERROR, TAG, "bluetoothGattService is null");
804 return CA_STATUS_FAILED;
808 CAResult_t res = CALEServerAddGattService(env, g_bluetoothGattServer,
809 bluetoothGattService);
810 if (CA_STATUS_OK != res)
812 OIC_LOG(ERROR, TAG, "CALEServerAddGattService has failed");
817 jobject CALEServerOpenGattServer(JNIEnv *env)
819 OIC_LOG(DEBUG, TAG, "IN - CALEServerOpenGattServer");
820 VERIFY_NON_NULL_RET(env, TAG, "env is null", NULL);
822 if (!CALEIsEnableBTAdapter(env))
824 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
828 jclass jni_cid_context = (*env)->FindClass(env, "android/content/Context");
829 if (!jni_cid_context)
831 OIC_LOG(ERROR, TAG, "jni_cid_context is null");
835 jclass jni_cid_bluetoothManager = (*env)->FindClass(env, "android/bluetooth/BluetoothManager");
836 if (!jni_cid_bluetoothManager)
838 OIC_LOG(ERROR, TAG, "jni_cid_bluetoothManager is null");
842 jfieldID jni_fid_bluetoothService = (*env)->GetStaticFieldID(env, jni_cid_context,
844 "Ljava/lang/String;");
845 if (!jni_fid_bluetoothService)
847 OIC_LOG(ERROR, TAG, "jni_fid_bluetoothService is null");
851 jmethodID jni_mid_getSystemService = (*env)->GetMethodID(env, jni_cid_context,
853 "(Ljava/lang/String;)"
854 "Ljava/lang/Object;");
855 if (!jni_mid_getSystemService)
857 OIC_LOG(ERROR, TAG, "jni_mid_getSystemService is null");
861 jmethodID jni_mid_openGattServer = (*env)->GetMethodID(env, jni_cid_bluetoothManager,
863 "(Landroid/content/Context;"
864 "Landroid/bluetooth/"
865 "BluetoothGattServerCallback;)"
866 "Landroid/bluetooth/"
867 "BluetoothGattServer;");
868 if (!jni_mid_openGattServer)
870 OIC_LOG(ERROR, TAG, "jni_mid_openGattServer is null");
874 jobject jni_obj_bluetoothService = (*env)->GetStaticObjectField(env, jni_cid_context,
875 jni_fid_bluetoothService);
876 if (!jni_obj_bluetoothService)
878 OIC_LOG(ERROR, TAG, "jni_obj_bluetoothService is null");
882 jobject jni_obj_bluetoothManager = (*env)->CallObjectMethod(env, g_context,
883 jni_mid_getSystemService,
884 jni_obj_bluetoothService);
885 if (!jni_obj_bluetoothManager)
887 OIC_LOG(ERROR, TAG, "jni_obj_bluetoothManager is null");
891 jobject jni_obj_bluetoothGattServer = (*env)->CallObjectMethod(env, jni_obj_bluetoothManager,
892 jni_mid_openGattServer,
894 g_bluetoothGattServerCallback);
895 if (!jni_obj_bluetoothGattServer)
897 OIC_LOG(ERROR, TAG, "jni_obj_bluetoothGattServer is null");
901 OIC_LOG(DEBUG, TAG, "OUT - CALEServerOpenGattServer");
902 return jni_obj_bluetoothGattServer;
905 jobject CALEServerCreateGattService(JNIEnv *env)
907 OIC_LOG(DEBUG, TAG, "IN - CALEServerCreateGattService");
908 VERIFY_NON_NULL_RET(env, TAG, "env is null", NULL);
910 if (!CALEIsEnableBTAdapter(env))
912 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
916 jclass jni_cid_bluetoothGattService = (*env)->FindClass(env, "android/bluetooth/"
917 "BluetoothGattService");
918 if (!jni_cid_bluetoothGattService)
920 OIC_LOG(ERROR, TAG, "jni_cid_bluetoothGattService is null");
924 jclass jni_cid_bluetoothGattCharacteristic = (*env)->FindClass(env, "android/bluetooth/"
925 "BluetoothGattCharacteristic");
926 if (!jni_cid_bluetoothGattCharacteristic)
928 OIC_LOG(ERROR, TAG, "jni_cid_bluetoothGattCharacteristic is null");
932 jfieldID jni_fid_serviceType = (*env)->GetStaticFieldID(env, jni_cid_bluetoothGattService,
933 "SERVICE_TYPE_PRIMARY", "I");
934 if (!jni_fid_serviceType)
936 OIC_LOG(ERROR, TAG, "jni_fid_serviceType is null");
940 jfieldID jni_fid_readProperties = (*env)->GetStaticFieldID(env,
941 jni_cid_bluetoothGattCharacteristic,
942 "PROPERTY_NOTIFY", "I");
943 if (!jni_fid_readProperties)
945 OIC_LOG(ERROR, TAG, "jni_fid_readProperties is null");
949 jfieldID jni_fid_writeProperties = (*env)->GetStaticFieldID(env,
950 jni_cid_bluetoothGattCharacteristic,
951 "PROPERTY_WRITE_NO_RESPONSE", "I");
952 if (!jni_fid_writeProperties)
954 OIC_LOG(ERROR, TAG, "jni_fid_writeProperties is null");
958 jfieldID jni_fid_readPermissions = (*env)->GetStaticFieldID(env,
959 jni_cid_bluetoothGattCharacteristic,
960 "PERMISSION_READ", "I");
961 if (!jni_fid_readPermissions)
963 OIC_LOG(ERROR, TAG, "jni_fid_readPermissions is null");
967 jfieldID jni_fid_writePermissions = (*env)->GetStaticFieldID(
968 env, jni_cid_bluetoothGattCharacteristic, "PERMISSION_WRITE", "I");
969 if (!jni_fid_writePermissions)
971 OIC_LOG(ERROR, TAG, "jni_fid_writePermissions is null");
975 jmethodID jni_mid_bluetoothGattService = (*env)->GetMethodID(env, jni_cid_bluetoothGattService,
976 "<init>", "(Ljava/util/UUID;I)V");
977 if (!jni_mid_bluetoothGattService)
979 OIC_LOG(ERROR, TAG, "jni_mid_bluetoothGattService is null");
983 jmethodID jni_mid_addCharacteristic = (*env)->GetMethodID(env, jni_cid_bluetoothGattService,
985 "(Landroid/bluetooth/"
986 "BluetoothGattCharacteristic;)Z");
987 if (!jni_mid_addCharacteristic)
989 OIC_LOG(ERROR, TAG, "jni_mid_addCharacteristic is null");
993 jmethodID jni_mid_bluetoothGattCharacteristic = (*env)->GetMethodID(
994 env, jni_cid_bluetoothGattCharacteristic, "<init>", "(Ljava/util/UUID;II)V");
995 if (!jni_mid_bluetoothGattCharacteristic)
997 OIC_LOG(ERROR, TAG, "jni_mid_bluetoothGattCharacteristic is null");
1001 jobject jni_obj_serviceUUID = CALEGetUuidFromString(env, OIC_GATT_SERVICE_UUID);
1002 if (!jni_obj_serviceUUID)
1004 OIC_LOG(ERROR, TAG, "jni_obj_serviceUUID is null");
1008 jint jni_int_serviceType = (*env)->GetStaticIntField(env, jni_cid_bluetoothGattService,
1009 jni_fid_serviceType);
1010 jobject jni_bluetoothGattService = (*env)->NewObject(env, jni_cid_bluetoothGattService,
1011 jni_mid_bluetoothGattService,
1012 jni_obj_serviceUUID, jni_int_serviceType);
1013 if (!jni_bluetoothGattService)
1015 OIC_LOG(ERROR, TAG, "jni_bluetoothGattService is null");
1019 jobject jni_obj_readUuid = CALEGetUuidFromString(env, OIC_GATT_CHARACTERISTIC_RESPONSE_UUID);
1020 if (!jni_obj_readUuid)
1022 OIC_LOG(ERROR, TAG, "jni_obj_readUuid is null");
1026 jint jni_int_readProperties = (*env)->GetStaticIntField(env,
1027 jni_cid_bluetoothGattCharacteristic,
1028 jni_fid_readProperties);
1030 jint jni_int_readPermissions = (*env)->GetStaticIntField(env,
1031 jni_cid_bluetoothGattCharacteristic,
1032 jni_fid_readPermissions);
1034 jint jni_int_writePermissions = (*env)->GetStaticIntField(env,
1035 jni_cid_bluetoothGattCharacteristic,
1036 jni_fid_writePermissions);
1038 jobject jni_readCharacteristic = (*env)->NewObject(env, jni_cid_bluetoothGattCharacteristic,
1039 jni_mid_bluetoothGattCharacteristic,
1040 jni_obj_readUuid, jni_int_readProperties,
1041 jni_int_readPermissions|
1042 jni_int_writePermissions);
1043 if (!jni_readCharacteristic)
1045 OIC_LOG(ERROR, TAG, "jni_readCharacteristic is null");
1049 jboolean jni_boolean_addReadCharacteristic = (*env)->CallBooleanMethod(
1050 env, jni_bluetoothGattService, jni_mid_addCharacteristic, jni_readCharacteristic);
1051 if (!jni_boolean_addReadCharacteristic)
1053 OIC_LOG(ERROR, TAG, "jni_boolean_addReadCharacteristic is null");
1057 jobject jni_obj_writeUuid = CALEGetUuidFromString(env, OIC_GATT_CHARACTERISTIC_REQUEST_UUID);
1058 if (!jni_obj_writeUuid)
1060 OIC_LOG(ERROR, TAG, "jni_obj_bluetoothGattServer is null");
1064 jint jni_int_writeProperties = (*env)->GetStaticIntField(env,
1065 jni_cid_bluetoothGattCharacteristic,
1066 jni_fid_writeProperties);
1068 jobject jni_writeCharacteristic = (*env)->NewObject(env, jni_cid_bluetoothGattCharacteristic,
1069 jni_mid_bluetoothGattCharacteristic,
1070 jni_obj_writeUuid, jni_int_writeProperties,
1071 jni_int_writePermissions);
1072 if (!jni_writeCharacteristic)
1074 OIC_LOG(ERROR, TAG, "jni_writeCharacteristic is null");
1078 jboolean jni_boolean_addWriteCharacteristic = (*env)->CallBooleanMethod(
1079 env, jni_bluetoothGattService, jni_mid_addCharacteristic, jni_writeCharacteristic);
1080 if (JNI_FALSE == jni_boolean_addWriteCharacteristic)
1082 OIC_LOG(ERROR, TAG, "Fail to add jni_boolean_addReadCharacteristic");
1086 OIC_LOG(DEBUG, TAG, "OUT - CALEServerCreateGattService");
1087 return jni_bluetoothGattService;
1090 CAResult_t CALEServerAddDescriptor(JNIEnv *env, jobject characteristic)
1092 OIC_LOG(DEBUG, TAG, "CALEServerAddDescriptor");
1093 VERIFY_NON_NULL(env, TAG, "env is null");
1094 VERIFY_NON_NULL(characteristic, TAG, "characteristic is null");
1096 jclass jni_cid_bluetoothGattDescriptor = (*env)->FindClass(env, "android/bluetooth/"
1097 "BluetoothGattDescriptor");
1098 if (!jni_cid_bluetoothGattDescriptor)
1100 OIC_LOG(ERROR, TAG, "jni_cid_bluetoothGattDescriptor is null");
1101 return CA_STATUS_FAILED;
1104 jmethodID jni_mid_bluetoothGattDescriptor = (*env)->GetMethodID(env,
1105 jni_cid_bluetoothGattDescriptor,
1107 "(Ljava/util/UUID;I)V");
1108 if (!jni_mid_bluetoothGattDescriptor)
1110 OIC_LOG(ERROR, TAG, "jni_mid_bluetoothGattDescriptor is null");
1111 return CA_STATUS_FAILED;
1114 jfieldID jni_fid_readPermissions = (*env)->GetStaticFieldID(env,
1115 jni_cid_bluetoothGattDescriptor,
1116 "PERMISSION_READ", "I");
1117 if (!jni_fid_readPermissions)
1119 OIC_LOG(ERROR, TAG, "jni_fid_readPermissions is null");
1120 return CA_STATUS_FAILED;
1123 jobject jni_obj_readUuid = CALEGetUuidFromString(env, OIC_GATT_CHARACTERISTIC_CONFIG_UUID);
1124 if (!jni_obj_readUuid)
1126 OIC_LOG(ERROR, TAG, "jni_obj_readUuid is null");
1127 return CA_STATUS_FAILED;
1130 jint jni_int_readPermissions = (*env)->GetStaticIntField(env, jni_cid_bluetoothGattDescriptor,
1131 jni_fid_readPermissions);
1133 OIC_LOG(DEBUG, TAG, "initialize new Descriptor");
1135 jobject jni_readDescriptor = (*env)->NewObject(env, jni_cid_bluetoothGattDescriptor,
1136 jni_mid_bluetoothGattDescriptor,
1137 jni_obj_readUuid, jni_int_readPermissions);
1138 if (!jni_readDescriptor)
1140 OIC_LOG(ERROR, TAG, "jni_readDescriptor is null");
1141 return CA_STATUS_FAILED;
1144 jclass jni_cid_GattCharacteristic = (*env)->FindClass(env, "android/bluetooth/"
1145 "BluetoothGattCharacteristic");
1146 if (!jni_cid_GattCharacteristic)
1148 OIC_LOG(ERROR, TAG, "jni_cid_GattCharacteristic is null");
1149 return CA_STATUS_FAILED;
1152 jmethodID jni_mid_addDescriptor = (*env)->GetMethodID(env, jni_cid_GattCharacteristic,
1154 "(Landroid/bluetooth/"
1155 "BluetoothGattDescriptor;)Z");
1156 if (!jni_mid_addDescriptor)
1158 OIC_LOG(ERROR, TAG, "jni_mid_addDescriptor is null");
1159 return CA_STATUS_FAILED;
1162 jboolean jni_boolean_addDescriptor = (*env)->CallBooleanMethod(env, characteristic,
1163 jni_mid_addDescriptor,
1164 jni_readDescriptor);
1166 if (JNI_FALSE == jni_boolean_addDescriptor)
1168 OIC_LOG(ERROR, TAG, "addDescriptor has failed");
1169 return CA_STATUS_FAILED;
1173 OIC_LOG(DEBUG, TAG, "addDescriptor success");
1175 return CA_STATUS_OK;
1178 CAResult_t CALEServerAddGattService(JNIEnv *env, jobject bluetoothGattServer,
1179 jobject bluetoothGattService)
1181 OIC_LOG(DEBUG, TAG, "IN - CALEServerAddGattService");
1182 VERIFY_NON_NULL(env, TAG, "env is null");
1183 VERIFY_NON_NULL(bluetoothGattServer, TAG, "bluetoothGattServer is null");
1184 VERIFY_NON_NULL(bluetoothGattService, TAG, "bluetoothGattService is null");
1186 if (!CALEIsEnableBTAdapter(env))
1188 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
1189 return CA_ADAPTER_NOT_ENABLED;
1192 jclass jni_cid_bluetoothGattServer = (*env)->FindClass(env,
1193 "android/bluetooth/BluetoothGattServer");
1194 if (!jni_cid_bluetoothGattServer)
1196 OIC_LOG(ERROR, TAG, "jni_cid_bluetoothGattServer is null");
1197 return CA_STATUS_FAILED;
1200 jmethodID jni_mid_addService = (*env)->GetMethodID(env, jni_cid_bluetoothGattServer,
1202 "(Landroid/bluetooth/BluetoothGattService;)"
1204 if (!jni_mid_addService)
1206 OIC_LOG(ERROR, TAG, "jni_mid_addService is null");
1207 return CA_STATUS_FAILED;
1210 jboolean jni_boolean_addService = (*env)->CallBooleanMethod(env, bluetoothGattServer,
1212 bluetoothGattService);
1214 if (JNI_FALSE == jni_boolean_addService)
1216 OIC_LOG(ERROR, TAG, "Fail to add GATT service");
1217 return CA_STATUS_FAILED;
1220 OIC_LOG(DEBUG, TAG, "OUT - CALEServerAddGattService");
1221 return CA_STATUS_OK;
1224 CAResult_t CALEServerConnect(JNIEnv *env, jobject bluetoothDevice)
1226 OIC_LOG(DEBUG, TAG, "IN - CALEServerConnect");
1227 VERIFY_NON_NULL(env, TAG, "env is null");
1228 VERIFY_NON_NULL(bluetoothDevice, TAG, "bluetoothDevice is null");
1230 if (!CALEIsEnableBTAdapter(env))
1232 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
1233 return CA_ADAPTER_NOT_ENABLED;
1236 jclass jni_cid_bluetoothGattServer = (*env)->FindClass(env,
1237 "android/bluetooth/BluetoothGattServer");
1238 if (!jni_cid_bluetoothGattServer)
1240 OIC_LOG(ERROR, TAG, "jni_cid_bluetoothGattServer is null");
1241 return CA_STATUS_FAILED;
1244 jmethodID jni_mid_connect = (*env)->GetMethodID(env, jni_cid_bluetoothGattServer, "connect",
1245 "(Landroid/bluetooth/BluetoothDevice;Z)Z");
1246 if (!jni_mid_connect)
1248 OIC_LOG(ERROR, TAG, "jni_mid_connect is null");
1249 return CA_STATUS_FAILED;
1252 jboolean jni_boolean_connect = (*env)->CallBooleanMethod(env, g_bluetoothGattServer,
1253 jni_mid_connect, bluetoothDevice,
1255 if (JNI_FALSE == jni_boolean_connect)
1257 OIC_LOG(ERROR, TAG, "Fail to connect");
1258 return CA_STATUS_FAILED;
1261 OIC_LOG(DEBUG, TAG, "OUT - CALEServerConnect");
1262 return CA_STATUS_OK;
1265 CAResult_t CALEServerDisconnectAllDevices(JNIEnv *env)
1267 OIC_LOG(DEBUG, TAG, "IN - CALEServerDisconnectAllDevices");
1268 VERIFY_NON_NULL(env, TAG, "env is null");
1270 ca_mutex_lock(g_connectedDeviceListMutex);
1271 if (!g_connectedDeviceList)
1273 OIC_LOG(ERROR, TAG, "g_connectedDeviceList is null");
1274 ca_mutex_unlock(g_connectedDeviceListMutex);
1275 return CA_STATUS_FAILED;
1278 uint32_t length = u_arraylist_length(g_connectedDeviceList);
1279 for (uint32_t index = 0; index < length; index++)
1281 jobject jarrayObj = (jobject) u_arraylist_get(g_connectedDeviceList, index);
1284 OIC_LOG_V(ERROR, TAG, "object[%d] is null", index);
1288 // disconnect for device obj
1289 CAResult_t res = CALEServerDisconnect(env, jarrayObj);
1290 if (CA_STATUS_OK != res)
1292 OIC_LOG_V(ERROR, TAG, "Disconnect for this device[%d] has failed", index);
1297 ca_mutex_unlock(g_connectedDeviceListMutex);
1298 OIC_LOG(DEBUG, TAG, "OUT - CALEServerDisconnectAllDevices");
1299 return CA_STATUS_OK;
1302 CAResult_t CALEServerDisconnect(JNIEnv *env, jobject bluetoothDevice)
1304 OIC_LOG(DEBUG, TAG, "IN - CALEServerDisconnect");
1305 VERIFY_NON_NULL(env, TAG, "env is null");
1306 VERIFY_NON_NULL(bluetoothDevice, TAG, "bluetoothDevice is null");
1308 if (!CALEIsEnableBTAdapter(env))
1310 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
1311 return CA_ADAPTER_NOT_ENABLED;
1314 jclass jni_cid_bluetoothGattServer = (*env)->FindClass(env,
1315 "android/bluetooth/BluetoothGattServer");
1316 if (!jni_cid_bluetoothGattServer)
1318 OIC_LOG(ERROR, TAG, "jni_cid_bluetoothGattServer is null");
1319 return CA_STATUS_FAILED;
1322 jmethodID jni_mid_cancelConnection = (*env)->GetMethodID(env, jni_cid_bluetoothGattServer,
1324 "(Landroid/bluetooth/BluetoothDevice;)"
1326 if (!jni_mid_cancelConnection)
1328 OIC_LOG(ERROR, TAG, "jni_mid_cancelConnection is null");
1329 return CA_STATUS_FAILED;
1332 (*env)->CallVoidMethod(env, g_bluetoothGattServer, jni_mid_cancelConnection, bluetoothDevice);
1334 if ((*env)->ExceptionCheck(env))
1336 OIC_LOG(ERROR, TAG, "cancelConnection has failed");
1337 (*env)->ExceptionDescribe(env);
1338 (*env)->ExceptionClear(env);
1339 return CA_STATUS_FAILED;
1342 OIC_LOG(DEBUG, TAG, "OUT - CALEServerDisconnect");
1343 return CA_STATUS_OK;
1346 CAResult_t CALEServerGattClose(JNIEnv *env, jobject bluetoothGattServer)
1349 OIC_LOG(DEBUG, TAG, "GattServer Close");
1350 VERIFY_NON_NULL(bluetoothGattServer, TAG, "bluetoothGattServer is null");
1351 VERIFY_NON_NULL(env, TAG, "env is null");
1353 // get BluetoothGatt class
1354 OIC_LOG(DEBUG, TAG, "get BluetoothGatt class");
1355 jclass jni_cid_BluetoothGatt = (*env)->FindClass(env, "android/bluetooth/BluetoothGattServer");
1356 if (!jni_cid_BluetoothGatt)
1358 OIC_LOG(ERROR, TAG, "jni_cid_BluetoothGatt is null");
1359 return CA_STATUS_FAILED;
1362 jmethodID jni_mid_closeGatt = (*env)->GetMethodID(env, jni_cid_BluetoothGatt, "close", "()V");
1363 if (!jni_mid_closeGatt)
1365 OIC_LOG(ERROR, TAG, "jni_mid_closeGatt is null");
1366 return CA_STATUS_OK;
1369 // call disconnect gatt method
1370 OIC_LOG(DEBUG, TAG, "request to close GATT");
1371 (*env)->CallVoidMethod(env, bluetoothGattServer, jni_mid_closeGatt);
1373 if ((*env)->ExceptionCheck(env))
1375 OIC_LOG(ERROR, TAG, "closeGATT has failed");
1376 (*env)->ExceptionDescribe(env);
1377 (*env)->ExceptionClear(env);
1378 return CA_STATUS_FAILED;
1381 return CA_STATUS_OK;
1384 CAResult_t CALEServerSend(JNIEnv *env, jobject bluetoothDevice, jbyteArray responseData)
1386 OIC_LOG(DEBUG, TAG, "IN - CALEServerSend");
1387 VERIFY_NON_NULL(env, TAG, "env is null");
1388 VERIFY_NON_NULL(bluetoothDevice, TAG, "bluetoothDevice is null");
1389 VERIFY_NON_NULL(responseData, TAG, "responseData is null");
1391 if (!CALEIsEnableBTAdapter(env))
1393 OIC_LOG(ERROR, TAG, "BT adapter is not enabled");
1394 return CA_ADAPTER_NOT_ENABLED;
1397 jobject responseChar = CALEServerSetResponseData(env, responseData);
1400 OIC_LOG(ERROR, TAG, "responseChar is null");
1401 return CA_STATUS_FAILED;
1404 CAResult_t result = CALEServerSendResponseData(env, bluetoothDevice, responseChar);
1405 if (CA_STATUS_OK != result)
1407 OIC_LOG(ERROR, TAG, "Fail to send response data");
1411 OIC_LOG(DEBUG, TAG, "OUT - CALEServerSend");
1415 CAResult_t CALEServerInitialize()
1417 OIC_LOG(DEBUG, TAG, "IN - CALEServerInitialize");
1419 CALeServerJniInit();
1423 OIC_LOG(ERROR, TAG, "g_jvm is null");
1424 return CA_STATUS_FAILED;
1427 bool isAttached = false;
1429 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
1432 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
1433 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
1437 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
1438 return CA_STATUS_FAILED;
1443 CAResult_t ret = CALECheckPlatformVersion(env, 21);
1444 if (CA_STATUS_OK != ret)
1446 OIC_LOG(ERROR, TAG, "it is not supported");
1450 (*g_jvm)->DetachCurrentThread(g_jvm);
1455 g_threadSendNotifyCond = ca_cond_new();
1457 ret = CALEServerInitMutexVaraibles();
1458 if (CA_STATUS_OK != ret)
1460 OIC_LOG(ERROR, TAG, "CALEServerInitMutexVaraibles has failed");
1464 (*g_jvm)->DetachCurrentThread(g_jvm);
1466 return CA_STATUS_FAILED;
1469 CALEServerJNISetContext();
1470 CALEServerCreateCachedDeviceList();
1472 ret = CALEServerCreateJniInterfaceObject();
1473 if (CA_STATUS_OK != ret)
1475 OIC_LOG(ERROR, TAG, "CALEServerCreateJniInterfaceObject has failed");
1479 (*g_jvm)->DetachCurrentThread(g_jvm);
1481 return CA_STATUS_FAILED;
1486 (*g_jvm)->DetachCurrentThread(g_jvm);
1489 g_isInitializedServer = true;
1490 OIC_LOG(DEBUG, TAG, "OUT - CALEServerInitialize");
1491 return CA_STATUS_OK;
1494 void CALEServerTerminate()
1496 OIC_LOG(DEBUG, TAG, "IN - CALEServerTerminate");
1500 OIC_LOG(ERROR, TAG, "g_jvm is null");
1504 bool isAttached = false;
1506 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
1509 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
1510 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
1514 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
1522 (*env)->DeleteGlobalRef(env, g_sendBuffer);
1523 g_sendBuffer = NULL;
1526 ca_cond_free(g_threadSendNotifyCond);
1527 g_threadSendNotifyCond = NULL;
1529 CALEServerTerminateMutexVaraibles();
1530 CALEServerTerminateConditionVaraibles();
1532 g_isInitializedServer = false;
1536 (*g_jvm)->DetachCurrentThread(g_jvm);
1539 OIC_LOG(DEBUG, TAG, "OUT - CALEServerTerminate");
1542 CAResult_t CALEServerSendUnicastMessage(const char* address, const uint8_t* data, uint32_t dataLen)
1544 OIC_LOG_V(DEBUG, TAG, "CALEServerSendUnicastMessage(%s, %p)", address, data);
1545 VERIFY_NON_NULL(address, TAG, "address is null");
1546 VERIFY_NON_NULL(data, TAG, "data is null");
1550 OIC_LOG(ERROR, TAG, "g_jvm is null");
1551 return CA_STATUS_FAILED;
1554 bool isAttached = false;
1556 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
1559 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
1560 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
1564 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
1565 return CA_STATUS_FAILED;
1570 CAResult_t ret = CALEServerSendUnicastMessageImpl(env, address, data, dataLen);
1571 if (CA_STATUS_OK != ret)
1573 OIC_LOG(ERROR, TAG, "CALEServerSendUnicastMessageImpl has failed");
1578 (*g_jvm)->DetachCurrentThread(g_jvm);
1584 CAResult_t CALEServerSendMulticastMessage(const uint8_t* data, uint32_t dataLen)
1586 OIC_LOG_V(DEBUG, TAG, "CALEServerSendMulticastMessage(%p)", data);
1587 VERIFY_NON_NULL(data, TAG, "data is null");
1591 OIC_LOG(ERROR, TAG, "g_jvm is null");
1592 return CA_STATUS_FAILED;
1595 bool isAttached = false;
1597 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
1600 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
1601 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
1605 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
1606 return CA_STATUS_FAILED;
1611 CAResult_t ret = CALEServerSendMulticastMessageImpl(env, data, dataLen);
1612 if (CA_STATUS_OK != ret)
1614 OIC_LOG(ERROR, TAG, "CALEServerSendMulticastMessageImpl has failed");
1619 (*g_jvm)->DetachCurrentThread(g_jvm);
1625 CAResult_t CALEServerStartMulticastServer()
1627 OIC_LOG(DEBUG, TAG, "IN - CALEServerStartMulticastServer");
1629 if (!g_isInitializedServer)
1631 OIC_LOG(INFO, TAG, "server is not initialized");
1632 return CA_STATUS_FAILED;
1635 if (g_isStartServer)
1637 OIC_LOG(INFO, TAG, "server is already started..it will be skipped");
1638 return CA_STATUS_FAILED;
1643 OIC_LOG(ERROR, TAG, "g_jvm is null");
1644 return CA_STATUS_FAILED;
1647 bool isAttached = false;
1649 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
1652 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
1653 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
1657 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
1658 return CA_STATUS_FAILED;
1663 g_isStartServer = true;
1665 // start gatt server
1666 CAResult_t ret = CALEServerStartGattServer(env, g_bluetoothGattServerCallback);
1667 if (CA_STATUS_OK != ret)
1669 OIC_LOG(ERROR, TAG, "Fail to start gatt server");
1674 ret = CALEServerStartAdvertise(env, g_leAdvertiseCallback);
1675 if (CA_STATUS_OK != ret)
1677 OIC_LOG(ERROR, TAG, "CALEServerStartAdvertise has failed");
1682 (*g_jvm)->DetachCurrentThread(g_jvm);
1685 OIC_LOG(DEBUG, TAG, "OUT - CALEServerStartMulticastServer");
1689 CAResult_t CALEServerStopMulticastServer()
1691 OIC_LOG(DEBUG, TAG, "IN - CALEServerStopMulticastServer");
1693 if (false == g_isStartServer)
1695 OIC_LOG(INFO, TAG, "server is already stopped..it will be skipped");
1696 return CA_STATUS_FAILED;
1701 OIC_LOG(ERROR, TAG, "g_jvm is null");
1702 return CA_STATUS_FAILED;
1705 bool isAttached = false;
1707 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
1710 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
1711 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
1715 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
1716 return CA_STATUS_FAILED;
1721 CAResult_t ret = CALEServerStopAdvertise(env, g_leAdvertiseCallback);
1722 if (CA_STATUS_OK != ret)
1724 OIC_LOG(ERROR, TAG, "CALEServerStopAdvertise has failed");
1727 g_isStartServer = false;
1731 (*g_jvm)->DetachCurrentThread(g_jvm);
1734 OIC_LOG(DEBUG, TAG, "OUT - CALEServerStopMulticastServer");
1738 void CALEServerSetCallback(CAPacketReceiveCallback callback)
1740 OIC_LOG(DEBUG, TAG, "CALEServerSetCallback");
1741 g_packetReceiveCallback = callback;
1744 CAResult_t CALEServerSendUnicastMessageImpl(JNIEnv *env, const char* address, const uint8_t* data,
1747 OIC_LOG_V(DEBUG, TAG, "CALEServerSendUnicastMessageImpl, address: %s, data: %p",
1749 VERIFY_NON_NULL(env, TAG, "env is null");
1750 VERIFY_NON_NULL(address, TAG, "address is null");
1751 VERIFY_NON_NULL(data, TAG, "data is null");
1753 if (!g_connectedDeviceList)
1755 OIC_LOG(ERROR, TAG, "g_connectedDeviceList is null");
1756 return CA_STATUS_FAILED;
1759 ca_mutex_lock(g_threadSendMutex);
1761 jobject jni_obj_bluetoothDevice = NULL;
1762 uint32_t length = u_arraylist_length(g_connectedDeviceList);
1763 for (uint32_t index = 0; index < length; index++)
1765 OIC_LOG(DEBUG, TAG, "check device address");
1766 jobject jarrayObj = (jobject) u_arraylist_get(g_connectedDeviceList, index);
1769 OIC_LOG(ERROR, TAG, "jarrayObj is null");
1773 jstring jni_setAddress = CALEGetAddressFromBTDevice(env, jarrayObj);
1774 if (!jni_setAddress)
1776 OIC_LOG(ERROR, TAG, "jni_setAddress is null");
1779 const char* setAddress = (*env)->GetStringUTFChars(env, jni_setAddress, NULL);
1782 OIC_LOG(ERROR, TAG, "setAddress is null");
1786 OIC_LOG_V(DEBUG, TAG, "setAddress : %s", setAddress);
1787 OIC_LOG_V(DEBUG, TAG, "address : %s", address);
1789 if (!strcmp(setAddress, address))
1791 OIC_LOG(DEBUG, TAG, "found the device");
1792 jni_obj_bluetoothDevice = jarrayObj;
1793 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
1796 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
1799 if (jni_obj_bluetoothDevice)
1801 jbyteArray jni_arr = (*env)->NewByteArray(env, dataLen);
1802 (*env)->SetByteArrayRegion(env, jni_arr, 0, dataLen, (jbyte*) data);
1803 g_sendBuffer = (jbyteArray)(*env)->NewGlobalRef(env, jni_arr);
1805 CAResult_t res = CALEServerSend(env, jni_obj_bluetoothDevice, g_sendBuffer);
1806 if (CA_STATUS_OK != res)
1808 OIC_LOG(ERROR, TAG, "send has failed");
1814 OIC_LOG(ERROR, TAG, "There are no device to send in the list");
1820 (*env)->DeleteGlobalRef(env, g_sendBuffer);
1821 g_sendBuffer = NULL;
1824 ca_mutex_unlock(g_threadSendMutex);
1825 OIC_LOG(INFO, TAG, "unicast - send request is successful");
1826 return CA_STATUS_OK;
1831 (*env)->DeleteGlobalRef(env, g_sendBuffer);
1832 g_sendBuffer = NULL;
1835 ca_mutex_unlock(g_threadSendMutex);
1836 return CA_SEND_FAILED;
1839 CAResult_t CALEServerSendMulticastMessageImpl(JNIEnv *env, const uint8_t *data, uint32_t dataLen)
1841 OIC_LOG_V(DEBUG, TAG, "CALEServerSendMulticastMessageImpl, send to, data: %s", data);
1842 VERIFY_NON_NULL(env, TAG, "env is null");
1843 VERIFY_NON_NULL(data, TAG, "data is null");
1845 if (!g_connectedDeviceList)
1847 OIC_LOG(ERROR, TAG, "g_connectedDeviceList is null");
1848 return CA_STATUS_FAILED;
1851 ca_mutex_lock(g_threadSendMutex);
1853 OIC_LOG(DEBUG, TAG, "set data into g_sendBuffer for notify");
1856 (*env)->DeleteGlobalRef(env, g_sendBuffer);
1857 g_sendBuffer = NULL;
1859 jbyteArray jni_arr = (*env)->NewByteArray(env, dataLen);
1860 (*env)->SetByteArrayRegion(env, jni_arr, 0, dataLen, (jbyte*) data);
1861 g_sendBuffer = (jbyteArray)(*env)->NewGlobalRef(env, jni_arr);
1863 uint32_t length = u_arraylist_length(g_connectedDeviceList);
1864 for (uint32_t index = 0; index < length; index++)
1866 jobject jarrayObj = (jobject) u_arraylist_get(g_connectedDeviceList, index);
1869 OIC_LOG(ERROR, TAG, "jarrayObj is null");
1873 // send data for all device
1874 jbyteArray jni_bytearr_data = (*env)->NewByteArray(env, dataLen);
1875 (*env)->SetByteArrayRegion(env, jni_bytearr_data, 0, dataLen, (jbyte*) data);
1877 jstring jni_address = CALEGetAddressFromBTDevice(env, jarrayObj);
1880 OIC_LOG(ERROR, TAG, "CALEGetAddressFromBTDevice has failed");
1884 const char* address = (*env)->GetStringUTFChars(env, jni_address, NULL);
1887 OIC_LOG(ERROR, TAG, "address is not available");
1891 CAResult_t res = CALEServerSend(env, jarrayObj, jni_bytearr_data);
1892 if (CA_STATUS_OK != res)
1894 OIC_LOG_V(ERROR, TAG, "send has failed for the device[%s]", address);
1895 (*env)->ReleaseStringUTFChars(env, jni_address, address);
1899 OIC_LOG_V(INFO, TAG, "unicast - send request is successful for a device[%s]", address);
1900 (*env)->ReleaseStringUTFChars(env, jni_address, address);
1905 (*env)->DeleteGlobalRef(env, g_sendBuffer);
1906 g_sendBuffer = NULL;
1909 ca_mutex_unlock(g_threadSendMutex);
1910 return CA_STATUS_OK;
1913 void CALEServerCreateCachedDeviceList()
1915 ca_mutex_lock(g_connectedDeviceListMutex);
1916 // create new object array
1917 if (!g_connectedDeviceList)
1919 OIC_LOG(DEBUG, TAG, "Create device list");
1920 g_connectedDeviceList = u_arraylist_create();
1922 ca_mutex_unlock(g_connectedDeviceListMutex);
1925 bool CALEServerIsDeviceInList(JNIEnv *env, const char* remoteAddress)
1927 VERIFY_NON_NULL_RET(env, TAG, "env is null", false);
1928 VERIFY_NON_NULL_RET(remoteAddress, TAG, "remoteAddress is null", false);
1930 if (!g_connectedDeviceList)
1932 OIC_LOG(ERROR, TAG, "list is null");
1936 uint32_t length = u_arraylist_length(g_connectedDeviceList);
1937 for (uint32_t index = 0; index < length; index++)
1939 jobject jarrayObj = (jobject) u_arraylist_get(g_connectedDeviceList, index);
1943 OIC_LOG(ERROR, TAG, "jarrayObj is null");
1947 jstring jni_setAddress = CALEGetAddressFromBTDevice(env, jarrayObj);
1948 if (!jni_setAddress)
1950 OIC_LOG(ERROR, TAG, "jni_setAddress is null");
1954 const char* setAddress = (*env)->GetStringUTFChars(env, jni_setAddress, NULL);
1957 OIC_LOG(ERROR, TAG, "setAddress is null");
1961 if (!strcmp(remoteAddress, setAddress))
1963 OIC_LOG(ERROR, TAG, "the device is already set");
1964 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
1969 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
1974 OIC_LOG(DEBUG, TAG, "there are no device in the list");
1978 CAResult_t CALEServerAddDeviceToList(JNIEnv *env, jobject device)
1980 OIC_LOG(DEBUG, TAG, "IN - CALEServerAddDeviceToList");
1981 VERIFY_NON_NULL(device, TAG, "device is null");
1982 VERIFY_NON_NULL(env, TAG, "env is null");
1984 ca_mutex_lock(g_connectedDeviceListMutex);
1986 if (!g_connectedDeviceList)
1988 OIC_LOG(ERROR, TAG, "list is null");
1989 ca_mutex_unlock(g_connectedDeviceListMutex);
1990 return CA_STATUS_FAILED;
1993 jstring jni_remoteAddress = CALEGetAddressFromBTDevice(env, device);
1994 if (!jni_remoteAddress)
1996 OIC_LOG(ERROR, TAG, "jni_remoteAddress is null");
1997 ca_mutex_unlock(g_connectedDeviceListMutex);
1998 return CA_STATUS_FAILED;
2001 const char* remoteAddress = (*env)->GetStringUTFChars(env, jni_remoteAddress, NULL);
2004 OIC_LOG(ERROR, TAG, "remoteAddress is null");
2005 ca_mutex_unlock(g_connectedDeviceListMutex);
2006 return CA_STATUS_FAILED;
2009 if (false == CALEServerIsDeviceInList(env, remoteAddress))
2011 jobject jni_obj_device = (*env)->NewGlobalRef(env, device);
2012 u_arraylist_add(g_connectedDeviceList, jni_obj_device);
2013 OIC_LOG_V(DEBUG, TAG, "Set the object to ArrayList as Element : %s", remoteAddress);
2016 (*env)->ReleaseStringUTFChars(env, jni_remoteAddress, remoteAddress);
2017 ca_mutex_unlock(g_connectedDeviceListMutex);
2018 OIC_LOG(DEBUG, TAG, "OUT - CALEServerAddDeviceToList");
2019 return CA_STATUS_OK;
2022 CAResult_t CALEServerRemoveAllDevices(JNIEnv *env)
2024 OIC_LOG(DEBUG, TAG, "IN - CALEServerRemoveAllDevices");
2025 VERIFY_NON_NULL(env, TAG, "env is null");
2027 ca_mutex_lock(g_connectedDeviceListMutex);
2028 if (!g_connectedDeviceList)
2030 OIC_LOG(ERROR, TAG, "g_connectedDeviceList is null");
2031 ca_mutex_unlock(g_connectedDeviceListMutex);
2032 return CA_STATUS_FAILED;
2035 uint32_t length = u_arraylist_length(g_connectedDeviceList);
2036 for (uint32_t index = 0; index < length; index++)
2038 jobject jarrayObj = (jobject) u_arraylist_get(g_connectedDeviceList, index);
2041 (*env)->DeleteGlobalRef(env, jarrayObj);
2045 OICFree(g_connectedDeviceList);
2046 g_connectedDeviceList = NULL;
2047 ca_mutex_unlock(g_connectedDeviceListMutex);
2049 OIC_LOG(DEBUG, TAG, "OUT - CALEServerRemoveAllDevices");
2050 return CA_STATUS_OK;
2053 CAResult_t CALEServerRemoveDevice(JNIEnv *env, jstring address)
2055 OIC_LOG(DEBUG, TAG, "IN CALEServerRemoveDevice");
2056 VERIFY_NON_NULL(env, TAG, "env is null");
2057 VERIFY_NON_NULL(address, TAG, "address is null");
2059 ca_mutex_lock(g_connectedDeviceListMutex);
2060 if (!g_connectedDeviceList)
2062 OIC_LOG(ERROR, TAG, "no deviceList");
2063 ca_mutex_unlock(g_connectedDeviceListMutex);
2064 return CA_STATUS_FAILED;
2067 uint32_t length = u_arraylist_length(g_connectedDeviceList);
2068 for (uint32_t index = 0; index < length; index++)
2070 jobject jarrayObj = (jobject) u_arraylist_get(g_connectedDeviceList, index);
2074 jstring jni_setAddress = CALEGetAddressFromBTDevice(env, jarrayObj);
2075 if (!jni_setAddress)
2077 OIC_LOG(ERROR, TAG, "wrong device address");
2080 const char* setAddress = (*env)->GetStringUTFChars(env, jni_setAddress, NULL);
2083 OIC_LOG(ERROR, TAG, "setAddress is null");
2087 const char* remoteAddress = (*env)->GetStringUTFChars(env, address, NULL);
2090 OIC_LOG(ERROR, TAG, "remoteAddress is null");
2091 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2095 if (!strcmp(setAddress, remoteAddress))
2097 OIC_LOG_V(DEBUG, TAG, "device address : %s", remoteAddress);
2099 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2100 (*env)->ReleaseStringUTFChars(env, address, remoteAddress);
2101 (*env)->DeleteGlobalRef(env, jarrayObj);
2103 if (NULL == u_arraylist_remove(g_connectedDeviceList, index))
2105 OIC_LOG(ERROR, TAG, "List removal failed.");
2106 ca_mutex_unlock(g_connectedDeviceListMutex);
2107 return CA_STATUS_FAILED;
2109 ca_mutex_unlock(g_connectedDeviceListMutex);
2110 return CA_STATUS_OK;
2112 (*env)->ReleaseStringUTFChars(env, jni_setAddress, setAddress);
2113 (*env)->ReleaseStringUTFChars(env, address, remoteAddress);
2117 ca_mutex_unlock(g_connectedDeviceListMutex);
2119 OIC_LOG(DEBUG, TAG, "there are no device in the device list");
2121 OIC_LOG(DEBUG, TAG, "IN CALEServerRemoveDevice");
2122 return CA_STATUS_FAILED;
2125 JNIEXPORT void JNICALL
2126 Java_org_iotivity_ca_CaLeServerInterface_caLeRegisterGattServerCallback(JNIEnv *env, jobject obj,
2129 OIC_LOG(DEBUG, TAG, "Register Le Gatt Server Callback");
2130 VERIFY_NON_NULL_VOID(env, TAG, "env");
2131 VERIFY_NON_NULL_VOID(obj, TAG, "obj");
2132 VERIFY_NON_NULL_VOID(callback, TAG, "callback");
2134 g_bluetoothGattServerCallback = (*env)->NewGlobalRef(env, callback);
2137 JNIEXPORT void JNICALL
2138 Java_org_iotivity_ca_CaLeServerInterface_caLeRegisterBluetoothLeAdvertiseCallback(JNIEnv *env,
2142 OIC_LOG(DEBUG, TAG, "Register Le Advertise Callback");
2143 VERIFY_NON_NULL_VOID(env, TAG, "env");
2144 VERIFY_NON_NULL_VOID(obj, TAG, "obj");
2145 VERIFY_NON_NULL_VOID(callback, TAG, "callback");
2147 g_leAdvertiseCallback = (*env)->NewGlobalRef(env, callback);
2150 JNIEXPORT void JNICALL
2151 Java_org_iotivity_ca_CaLeServerInterface_caLeGattServerConnectionStateChangeCallback(
2152 JNIEnv *env, jobject obj, jobject device, jint status, jint newState)
2154 OIC_LOG(DEBUG, TAG, " Gatt Server ConnectionStateChange Callback");
2155 OIC_LOG_V(DEBUG, TAG, "New connection State: %d", newState);
2157 VERIFY_NON_NULL_VOID(env, TAG, "env");
2158 VERIFY_NON_NULL_VOID(obj, TAG, "obj");
2159 VERIFY_NON_NULL_VOID(device, TAG, "device");
2162 jint state_connected = CALEGetConstantsValue(env, CLASSPATH_BT_PROFILE, "STATE_CONNECTED");
2164 // STATE_DISCONNECTED
2165 jint state_disconnected = CALEGetConstantsValue(env, CLASSPATH_BT_PROFILE, "STATE_DISCONNECTED");
2167 if (newState == state_connected)
2170 OIC_LOG(DEBUG, TAG, "LE CONNECTED");
2172 jstring jni_remoteAddress = CALEGetAddressFromBTDevice(env, device);
2173 if (!jni_remoteAddress)
2175 OIC_LOG(ERROR, TAG, "jni_remoteAddress is null");
2179 const char* remoteAddress = (*env)->GetStringUTFChars(env, jni_remoteAddress, NULL);
2182 OIC_LOG(ERROR, TAG, "remoteAddress is null");
2186 if (false == CALEServerIsDeviceInList(env, remoteAddress))
2188 OIC_LOG(DEBUG, TAG, "add connected device to cache");
2189 CALEServerAddDeviceToList(env, device);
2191 (*env)->ReleaseStringUTFChars(env, jni_remoteAddress, remoteAddress);
2193 else if (newState == state_disconnected)
2195 OIC_LOG(DEBUG, TAG, "LE DISCONNECTED");
2197 jstring jni_remoteAddress = CALEGetAddressFromBTDevice(env, device);
2198 CAResult_t ret = CALEServerRemoveDevice(env, jni_remoteAddress);
2199 if (CA_STATUS_OK != ret)
2201 OIC_LOG(ERROR, TAG, "CALEServerRemoveDevice has failed");
2205 ret = CALEServerStartAdvertise(env, g_leAdvertiseCallback);
2206 if (CA_STATUS_OK != ret)
2208 OIC_LOG(ERROR, TAG, "CALEServerStartAdvertise has failed");
2213 OIC_LOG_V(DEBUG, TAG, "LE Connection state is [newState : %d, status %d]", newState,
2218 JNIEXPORT void JNICALL
2219 Java_org_iotivity_ca_CaLeServerInterface_caLeGattServerServiceAddedCallback(JNIEnv *env,
2222 jobject gattService)
2224 VERIFY_NON_NULL_VOID(env, TAG, "env");
2225 VERIFY_NON_NULL_VOID(obj, TAG, "obj");
2226 VERIFY_NON_NULL_VOID(gattService, TAG, "gattService");
2228 OIC_LOG_V(DEBUG, TAG, "Gatt Service Added Callback(%d)", status);
2231 JNIEXPORT void JNICALL
2232 Java_org_iotivity_ca_CaLeServerInterface_caLeGattServerCharacteristicReadRequestCallback(
2233 JNIEnv *env, jobject obj, jobject device, jbyteArray data)
2235 OIC_LOG(DEBUG, TAG, " Gatt Server Characteristic Read Request Callback");
2236 VERIFY_NON_NULL_VOID(env, TAG, "env");
2237 VERIFY_NON_NULL_VOID(obj, TAG, "obj");
2238 VERIFY_NON_NULL_VOID(device, TAG, "device");
2239 VERIFY_NON_NULL_VOID(data, TAG, "data");
2242 JNIEXPORT void JNICALL
2243 Java_org_iotivity_ca_CaLeServerInterface_caLeGattServerCharacteristicWriteRequestCallback(
2244 JNIEnv *env, jobject obj, jobject device, jbyteArray data)
2246 OIC_LOG_V(DEBUG, TAG, "Gatt Server Characteristic Write Request Callback");
2247 VERIFY_NON_NULL_VOID(env, TAG, "env");
2248 VERIFY_NON_NULL_VOID(obj, TAG, "obj");
2249 VERIFY_NON_NULL_VOID(device, TAG, "device");
2250 VERIFY_NON_NULL_VOID(data, TAG, "data");
2252 // get Byte Array and covert to uint8_t*
2253 jint length = (*env)->GetArrayLength(env, data);
2256 jbyte *jni_byte_requestData = (jbyte *) (*env)->GetByteArrayElements(env, data, &isCopy);
2258 uint8_t* requestData = NULL;
2259 requestData = OICMalloc(length);
2262 OIC_LOG(ERROR, TAG, "requestData is null");
2266 memcpy(requestData, jni_byte_requestData, length);
2267 (*env)->ReleaseByteArrayElements(env, data, jni_byte_requestData, JNI_ABORT);
2269 jstring jni_address = CALEGetAddressFromBTDevice(env, device);
2272 OIC_LOG(ERROR, TAG, "jni_address is null");
2273 OICFree(requestData);
2277 const char* address = (*env)->GetStringUTFChars(env, jni_address, NULL);
2280 OIC_LOG(ERROR, TAG, "address is null");
2281 OICFree(requestData);
2285 OIC_LOG_V(DEBUG, TAG, "remote device address : %s, %p, %d", address, requestData, length);
2287 ca_mutex_lock(g_bleClientBDAddressMutex);
2288 uint32_t sentLength = 0;
2289 g_CABLEServerDataReceivedCallback(address, requestData, length,
2291 ca_mutex_unlock(g_bleClientBDAddressMutex);
2293 (*env)->ReleaseStringUTFChars(env, jni_address, address);
2296 JNIEXPORT void JNICALL
2297 Java_org_iotivity_ca_CaLeServerInterface_caLeGattServerNotificationSentCallback(JNIEnv *env,
2302 VERIFY_NON_NULL_VOID(env, TAG, "env");
2303 VERIFY_NON_NULL_VOID(obj, TAG, "obj");
2304 VERIFY_NON_NULL_VOID(device, TAG, "device");
2306 OIC_LOG_V(DEBUG, TAG, "Gatt Server Notification Sent Callback (status : %d)",
2309 jint gatt_success = CALEGetConstantsValue(env, CLASSPATH_BT_GATT, "GATT_SUCCESS");
2310 if (gatt_success != status) // error case
2312 OIC_LOG(ERROR, TAG, "it will be sent again.");
2314 CAResult_t res = CALEServerSend(env, device, g_sendBuffer);
2315 if (CA_STATUS_OK != res)
2317 OIC_LOG(ERROR, TAG, "send has failed");
2318 ca_mutex_lock(g_threadSendNotifyMutex);
2319 g_isSignalSetFlag = true;
2320 ca_cond_signal(g_threadSendNotifyCond);
2321 ca_mutex_unlock(g_threadSendNotifyMutex);
2327 OIC_LOG(DEBUG, TAG, "notify success");
2329 // next data can be sent
2330 ca_mutex_lock(g_threadSendNotifyMutex);
2331 OIC_LOG(DEBUG, TAG, "g_isSignalSetFlag is set true and signal");
2332 g_isSignalSetFlag = true;
2333 ca_cond_signal(g_threadSendNotifyCond);
2334 ca_mutex_unlock(g_threadSendNotifyMutex);
2339 JNIEXPORT void JNICALL
2340 Java_org_iotivity_ca_CaLeServerInterface_caLeAdvertiseStartSuccessCallback(JNIEnv *env,
2342 jobject settingsInEffect)
2344 VERIFY_NON_NULL_VOID(env, TAG, "env");
2345 VERIFY_NON_NULL_VOID(obj, TAG, "obj");
2346 VERIFY_NON_NULL_VOID(settingsInEffect, TAG, "settingsInEffect");
2348 OIC_LOG(DEBUG, TAG, "LE Advertise Start Success Callback");
2351 JNIEXPORT void JNICALL
2352 Java_org_iotivity_ca_CaLeServerInterface_caLeAdvertiseStartFailureCallback(JNIEnv *env,
2356 VERIFY_NON_NULL_VOID(env, TAG, "env");
2357 VERIFY_NON_NULL_VOID(obj, TAG, "obj");
2359 OIC_LOG_V(INFO, TAG, "LE Advertise Start Failure Callback(%d)", errorCode);
2366 CAResult_t CAStartLEGattServer()
2368 // start gatt service
2369 CALEServerStartMulticastServer();
2371 return CA_STATUS_OK;
2374 CAResult_t CAStopLEGattServer()
2376 OIC_LOG(DEBUG, TAG, "CAStopLEGattServer");
2380 OIC_LOG(ERROR, TAG, "g_jvm is null");
2381 return CA_STATUS_FAILED;
2384 bool isAttached = false;
2386 jint res = (*g_jvm)->GetEnv(g_jvm, (void**) &env, JNI_VERSION_1_6);
2389 OIC_LOG(INFO, TAG, "Could not get JNIEnv pointer");
2390 res = (*g_jvm)->AttachCurrentThread(g_jvm, &env, NULL);
2394 OIC_LOG(ERROR, TAG, "AttachCurrentThread has failed");
2395 return CA_STATUS_FAILED;
2400 CAResult_t ret = CALEServerGattClose(env, g_bluetoothGattServer);
2401 if (CA_STATUS_OK != ret)
2403 OIC_LOG(ERROR, TAG, "CALEServerGattClose has failed");
2404 return CA_STATUS_FAILED;
2407 ret = CALEServerStopMulticastServer();
2408 if (CA_STATUS_OK != ret)
2410 OIC_LOG(ERROR, TAG, "CALEServerStopMulticastServer has failed");
2411 return CA_STATUS_FAILED;
2414 ret = CALEServerDisconnectAllDevices(env);
2415 if (CA_STATUS_OK != ret)
2417 OIC_LOG(ERROR, TAG, "CALEServerDisconnectAllDevices has failed");
2418 return CA_STATUS_FAILED;
2421 ret = CALEServerRemoveAllDevices(env);
2422 if (CA_STATUS_OK != ret)
2424 OIC_LOG(ERROR, TAG, "CALEServerRemoveAllDevices has failed");
2425 return CA_STATUS_FAILED;
2428 if (g_leAdvertiseCallback)
2430 (*env)->DeleteGlobalRef(env, g_leAdvertiseCallback);
2433 if (g_bluetoothGattServer)
2435 (*env)->DeleteGlobalRef(env, g_bluetoothGattServer);
2438 if (g_bluetoothGattServerCallback)
2440 (*env)->DeleteGlobalRef(env, g_bluetoothGattServerCallback);
2443 ca_mutex_lock(g_threadSendNotifyMutex);
2444 ca_cond_signal(g_threadSendNotifyCond);
2445 ca_mutex_unlock(g_threadSendNotifyMutex);
2447 g_isStartServer = false;
2451 (*g_jvm)->DetachCurrentThread(g_jvm);
2454 return CA_STATUS_OK;
2457 CAResult_t CAInitializeLEGattServer()
2459 OIC_LOG(DEBUG, TAG, "Initialize Gatt Server");
2460 return CALEServerInitialize();
2463 void CATerminateLEGattServer()
2465 OIC_LOG(DEBUG, TAG, "Terminate Gatt Server");
2466 CALEServerTerminate();
2469 void CASetLEReqRespServerCallback(CABLEDataReceivedCallback callback)
2471 ca_mutex_lock(g_bleReqRespCbMutex);
2472 g_CABLEServerDataReceivedCallback = callback;
2473 ca_mutex_unlock(g_bleReqRespCbMutex);
2476 void CASetBLEServerErrorHandleCallback(CABLEErrorHandleCallback callback)
2478 g_serverErrorCallback = callback;
2481 CAResult_t CAUpdateCharacteristicsToGattClient(const char *address,
2482 const uint8_t *charValue,
2483 uint32_t charValueLen)
2485 CAResult_t result = CA_SEND_FAILED;
2486 VERIFY_NON_NULL(address, TAG, "env is null");
2487 VERIFY_NON_NULL(charValue, TAG, "device is null");
2491 result = CALEServerSendUnicastMessage(address, charValue, charValueLen);
2497 CAResult_t CAUpdateCharacteristicsToAllGattClients(const uint8_t *charValue,
2498 uint32_t charValueLen)
2500 VERIFY_NON_NULL(charValue, TAG, "device is null");
2502 CAResult_t result = CALEServerSendMulticastMessage(charValue, charValueLen);
2507 void CASetLEServerThreadPoolHandle(ca_thread_pool_t handle)
2509 OIC_LOG(INFO, TAG, "CASetLEServerThreadPoolHandle is not support");
2513 CAResult_t CALEServerInitMutexVaraibles()
2515 if (NULL == g_bleReqRespCbMutex)
2517 g_bleReqRespCbMutex = ca_mutex_new();
2518 if (NULL == g_bleReqRespCbMutex)
2520 OIC_LOG(ERROR, TAG, "ca_mutex_new has failed");
2521 return CA_STATUS_FAILED;
2525 if (NULL == g_bleClientBDAddressMutex)
2527 g_bleClientBDAddressMutex = ca_mutex_new();
2528 if (NULL == g_bleClientBDAddressMutex)
2530 OIC_LOG(ERROR, TAG, "ca_mutex_new has failed");
2531 return CA_STATUS_FAILED;
2535 if (NULL == g_connectedDeviceListMutex)
2537 g_connectedDeviceListMutex = ca_mutex_new();
2538 if (NULL == g_connectedDeviceListMutex)
2540 OIC_LOG(ERROR, TAG, "ca_mutex_new has failed");
2541 return CA_STATUS_FAILED;
2545 if (NULL == g_threadSendMutex)
2547 g_threadSendMutex = ca_mutex_new();
2548 if (NULL == g_threadSendMutex)
2550 OIC_LOG(ERROR, TAG, "ca_mutex_new has failed");
2551 return CA_STATUS_FAILED;
2555 if (NULL == g_threadSendNotifyMutex)
2557 g_threadSendNotifyMutex = ca_mutex_new();
2558 if (NULL == g_threadSendNotifyMutex)
2560 OIC_LOG(ERROR, TAG, "ca_mutex_new has failed");
2561 return CA_STATUS_FAILED;
2565 return CA_STATUS_OK;
2568 void CALEServerTerminateMutexVaraibles()
2570 ca_mutex_free(g_bleReqRespCbMutex);
2571 g_bleReqRespCbMutex = NULL;
2573 ca_mutex_free(g_bleClientBDAddressMutex);
2574 g_bleClientBDAddressMutex = NULL;
2576 ca_mutex_free(g_connectedDeviceListMutex);
2577 g_connectedDeviceListMutex = NULL;
2579 ca_mutex_free(g_threadSendMutex);
2580 g_threadSendMutex = NULL;
2582 ca_mutex_free(g_threadSendNotifyMutex);
2583 g_threadSendNotifyMutex = NULL;
2586 void CALEServerTerminateConditionVaraibles()
2588 OIC_LOG(DEBUG, TAG, "this method is not supported");