com_android_bluetooth_btservice_AdapterService.cpp revision 1e9f8a14e120e8786711abdd4a965236191c87ad
1ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh/* 2ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * Copyright (C) 2012 The Android Open Source Project 3ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * 4ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * Licensed under the Apache License, Version 2.0 (the "License"); 5ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * you may not use this file except in compliance with the License. 6ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * You may obtain a copy of the License at 7ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * 8ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * http://www.apache.org/licenses/LICENSE-2.0 9ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * 10ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * Unless required by applicable law or agreed to in writing, software 11ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * distributed under the License is distributed on an "AS IS" BASIS, 12ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * See the License for the specific language governing permissions and 14ede67c26e7b2564ea35db6d9b3027a269c150e13Zhihai Xu * limitations under the License. 15ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh */ 16ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 17ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh#define LOG_TAG "BluetoothServiceJni" 186c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie#include "com_android_bluetooth.h" 19cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie#include "hardware/bt_sock.h" 20ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh#include "utils/Log.h" 21ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh#include "utils/misc.h" 22ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh#include "cutils/properties.h" 23ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh#include "android_runtime/AndroidRuntime.h" 24dc8c533e030e6b8625da3dc75c8f768a3242fe16Ruben Brunk#include "android_runtime/Log.h" 25ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 26ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh#include <string.h> 27ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh#include <pthread.h> 28ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 29ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh#include <sys/stat.h> 30ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh#include <fcntl.h> 31ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 32ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshnamespace android { 33ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 346c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie#define ADDITIONAL_NREFS 50 35ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jmethodID method_stateChangeCallback; 36ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jmethodID method_adapterPropertyChangedCallback; 37ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jmethodID method_devicePropertyChangedCallback; 38ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jmethodID method_deviceFoundCallback; 39ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jmethodID method_pinRequestCallback; 40ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jmethodID method_sspRequestCallback; 41ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jmethodID method_bondStateChangeCallback; 4201a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamystatic jmethodID method_aclStateChangeCallback; 43ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jmethodID method_discoveryStateChangeCallback; 441e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavatistatic jmethodID method_setWakeAlarm; 451e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavatistatic jmethodID method_acquireWakeLock; 461e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavatistatic jmethodID method_releaseWakeLock; 47ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 48ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic const bt_interface_t *sBluetoothInterface = NULL; 49cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xiestatic const btsock_interface_t *sBluetoothSocketInterface = NULL; 50ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic JNIEnv *callbackEnv = NULL; 51ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 521e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavatistatic jobject sJniAdapterServiceObj; 53ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jobject sJniCallbacksObj; 54ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jfieldID sJniCallbacksField; 55ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 56cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie 576c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xieconst bt_interface_t* getBluetoothInterface() { 586c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie return sBluetoothInterface; 596c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie} 606c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie 616c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew XieJNIEnv* getCallbackEnv() { 62b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom return callbackEnv; 636c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie} 646c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie 656c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xievoid checkAndClearExceptionFromCallback(JNIEnv* env, 66ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh const char* methodName) { 67ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (env->ExceptionCheck()) { 68c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("An exception was thrown by callback '%s'.", methodName); 69ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh LOGE_EX(env); 70ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh env->ExceptionClear(); 71ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 72ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 73ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 74ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic bool checkCallbackThread() { 75ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh JNIEnv* env = AndroidRuntime::getJNIEnv(); 76676cb1bdd1c14c7af56562bab51f168e7f8f6d62Matthew Xie if (callbackEnv != env || callbackEnv == NULL) { 77c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Callback env check fail: env: %p, callback: %p", env, callbackEnv); 78676cb1bdd1c14c7af56562bab51f168e7f8f6d62Matthew Xie return false; 79676cb1bdd1c14c7af56562bab51f168e7f8f6d62Matthew Xie } 80ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return true; 81ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 82ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 83ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void adapter_state_change_callback(bt_state_t status) { 84ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!checkCallbackThread()) { 85c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__); 86ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 87ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 88c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s: Status is: %d", __FUNCTION__, status); 89ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 90ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh callbackEnv->CallVoidMethod(sJniCallbacksObj, method_stateChangeCallback, (jint)status); 91ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 92ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__); 93ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 94ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 95ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic int get_properties(int num_properties, bt_property_t *properties, jintArray *types, 96ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jobjectArray *props) { 97edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M jbyteArray propVal; 98ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh for (int i = 0; i < num_properties; i++) { 99b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom propVal = callbackEnv->NewByteArray(properties[i].len); 100b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom if (propVal == NULL) goto Fail; 101b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom 102b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom callbackEnv->SetByteArrayRegion(propVal, 0, properties[i].len, 103b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom (jbyte*)properties[i].val); 104b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom callbackEnv->SetObjectArrayElement(*props, i, propVal); 105b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom // Delete reference to propVal 106b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom callbackEnv->DeleteLocalRef(propVal); 107b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom callbackEnv->SetIntArrayRegion(*types, i, 1, (jint *)&properties[i].type); 108ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 109ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return 0; 110ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar GaneshFail: 111ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (propVal) callbackEnv->DeleteLocalRef(propVal); 112c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Error while allocation of array in %s", __FUNCTION__); 113ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return -1; 114ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 115ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 116ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void adapter_properties_callback(bt_status_t status, int num_properties, 117ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh bt_property_t *properties) { 118ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jobjectArray props; 119ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jintArray types; 120edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M jbyteArray val; 121edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M jclass mclass; 122edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M 123ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!checkCallbackThread()) { 124c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__); 125ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 126ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 127ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 128c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s: Status is: %d, Properties: %d", __FUNCTION__, status, num_properties); 129ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 130ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (status != BT_STATUS_SUCCESS) { 131c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("%s: Status %d is incorrect", __FUNCTION__, status); 132ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 133ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 134ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 135edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M val = (jbyteArray) callbackEnv->NewByteArray(num_properties); 136edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M if (val == NULL) { 137e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie ALOGE("%s: Error allocating byteArray", __FUNCTION__); 138edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M return; 139edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M } 140edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M 141edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M mclass = callbackEnv->GetObjectClass(val); 142edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M 143edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M /* (BT) Initialize the jobjectArray and jintArray here itself and send the 144edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M initialized array pointers alone to get_properties */ 145edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M 146edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M props = callbackEnv->NewObjectArray(num_properties, mclass, 147edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M NULL); 148edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M if (props == NULL) { 149e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie ALOGE("%s: Error allocating object Array for properties", __FUNCTION__); 150edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M return; 151edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M } 152edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M 153edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M types = (jintArray)callbackEnv->NewIntArray(num_properties); 154edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M 155edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M if (types == NULL) { 156e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie ALOGE("%s: Error allocating int Array for values", __FUNCTION__); 157edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M return; 158edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M } 159edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M // Delete the reference to val and mclass 160edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M callbackEnv->DeleteLocalRef(mclass); 161edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M callbackEnv->DeleteLocalRef(val); 162edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M 163ff68148a7fb74947ea5e7a337161108363cbe9f5Jaikumar Ganesh if (get_properties(num_properties, properties, &types, &props) < 0) { 164ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (props) callbackEnv->DeleteLocalRef(props); 165ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (types) callbackEnv->DeleteLocalRef(types); 166ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 167ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 168ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 169ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh callbackEnv->CallVoidMethod(sJniCallbacksObj, method_adapterPropertyChangedCallback, types, 170ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh props); 171ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__); 1726c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie callbackEnv->DeleteLocalRef(props); 1736c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie callbackEnv->DeleteLocalRef(types); 174ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 175ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 176ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 177ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 178ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void remote_device_properties_callback(bt_status_t status, bt_bdaddr_t *bd_addr, 179ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int num_properties, bt_property_t *properties) { 180ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!checkCallbackThread()) { 181c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__); 182ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 183ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 184ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 185c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s: Status is: %d, Properties: %d", __FUNCTION__, status, num_properties); 186ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 187ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (status != BT_STATUS_SUCCESS) { 188c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("%s: Status %d is incorrect", __FUNCTION__, status); 189ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 190ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 191ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 1926c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie callbackEnv->PushLocalFrame(ADDITIONAL_NREFS); 1936c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie 1946c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie jobjectArray props; 1956c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie jbyteArray addr; 1966c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie jintArray types; 197edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M jbyteArray val; 198edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M jclass mclass; 199edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M 200edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M val = (jbyteArray) callbackEnv->NewByteArray(num_properties); 201edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M if (val == NULL) { 202e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie ALOGE("%s: Error allocating byteArray", __FUNCTION__); 203edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M return; 204edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M } 205edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M 206edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M mclass = callbackEnv->GetObjectClass(val); 207edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M 208edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M /* Initialize the jobjectArray and jintArray here itself and send the 209edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M initialized array pointers alone to get_properties */ 210edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M 211edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M props = callbackEnv->NewObjectArray(num_properties, mclass, 212edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M NULL); 213edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M if (props == NULL) { 214e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie ALOGE("%s: Error allocating object Array for properties", __FUNCTION__); 215edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M return; 216edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M } 217edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M 218edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M types = (jintArray)callbackEnv->NewIntArray(num_properties); 219edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M 220edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M if (types == NULL) { 221e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie ALOGE("%s: Error allocating int Array for values", __FUNCTION__); 222edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M return; 223edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M } 224edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M // Delete the reference to val and mclass 225edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M callbackEnv->DeleteLocalRef(mclass); 226edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M callbackEnv->DeleteLocalRef(val); 2276c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie 228ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh addr = callbackEnv->NewByteArray(sizeof(bt_bdaddr_t)); 229ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (addr == NULL) goto Fail; 230ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (addr) callbackEnv->SetByteArrayRegion(addr, 0, sizeof(bt_bdaddr_t), (jbyte*)bd_addr); 231ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 232ff68148a7fb74947ea5e7a337161108363cbe9f5Jaikumar Ganesh if (get_properties(num_properties, properties, &types, &props) < 0) { 233ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (props) callbackEnv->DeleteLocalRef(props); 234ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (types) callbackEnv->DeleteLocalRef(types); 2356c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie callbackEnv->PopLocalFrame(NULL); 236ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 237ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 238ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 239ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh callbackEnv->CallVoidMethod(sJniCallbacksObj, method_devicePropertyChangedCallback, addr, 240ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh types, props); 241ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__); 2426c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie callbackEnv->DeleteLocalRef(props); 2436c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie callbackEnv->DeleteLocalRef(types); 244edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M callbackEnv->DeleteLocalRef(addr); 2456c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie callbackEnv->PopLocalFrame(NULL); 246ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 247ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 248ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar GaneshFail: 249c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Error while allocation byte array in %s", __FUNCTION__); 250ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 251ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 252ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 253ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void device_found_callback(int num_properties, bt_property_t *properties) { 254ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jbyteArray addr = NULL; 255ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int addr_index; 256ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 257ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh for (int i = 0; i < num_properties; i++) { 258ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (properties[i].type == BT_PROPERTY_BDADDR) { 259ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh addr = callbackEnv->NewByteArray(properties[i].len); 260ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (addr) { 261ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh callbackEnv->SetByteArrayRegion(addr, 0, properties[i].len, 262ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh (jbyte*)properties[i].val); 263ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh addr_index = i; 264ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } else { 265c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Address is NULL (unable to allocate) in %s", __FUNCTION__); 266ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 267ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 268ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 269ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 270ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (addr == NULL) { 271c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Address is NULL in %s", __FUNCTION__); 272ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 273ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 274ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 275c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s: Properties: %d, Address: %s", __FUNCTION__, num_properties, 276ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh (const char *)properties[addr_index].val); 277ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 278ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh remote_device_properties_callback(BT_STATUS_SUCCESS, (bt_bdaddr_t *)properties[addr_index].val, 279ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh num_properties, properties); 280ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 281ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh callbackEnv->CallVoidMethod(sJniCallbacksObj, method_deviceFoundCallback, addr); 282ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__); 2836c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie callbackEnv->DeleteLocalRef(addr); 284ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 285ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 286ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void bond_state_changed_callback(bt_status_t status, bt_bdaddr_t *bd_addr, 287ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh bt_bond_state_t state) { 288ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jbyteArray addr; 289ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int i; 290ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!checkCallbackThread()) { 291c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__); 292ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 293ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 294ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!bd_addr) { 295c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Address is null in %s", __FUNCTION__); 296ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 297ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 298ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh addr = callbackEnv->NewByteArray(sizeof(bt_bdaddr_t)); 299ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (addr == NULL) { 300c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Address allocation failed in %s", __FUNCTION__); 301ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 302ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 303ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh callbackEnv->SetByteArrayRegion(addr, 0, sizeof(bt_bdaddr_t), (jbyte *)bd_addr); 304ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 305ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh callbackEnv->CallVoidMethod(sJniCallbacksObj, method_bondStateChangeCallback, (jint) status, 306ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh addr, (jint)state); 307ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__); 3086c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie callbackEnv->DeleteLocalRef(addr); 309ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 310ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 31101a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamystatic void acl_state_changed_callback(bt_status_t status, bt_bdaddr_t *bd_addr, 31201a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy bt_acl_state_t state) 31301a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy{ 31401a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy jbyteArray addr; 31501a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy int i; 31601a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy if (!checkCallbackThread()) { 317e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__); 31801a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy return; 31901a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy } 32001a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy if (!bd_addr) { 321e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie ALOGE("Address is null in %s", __FUNCTION__); 32201a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy return; 32301a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy } 32401a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy addr = callbackEnv->NewByteArray(sizeof(bt_bdaddr_t)); 32501a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy if (addr == NULL) { 326e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie ALOGE("Address allocation failed in %s", __FUNCTION__); 32701a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy return; 32801a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy } 32901a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy callbackEnv->SetByteArrayRegion(addr, 0, sizeof(bt_bdaddr_t), (jbyte *)bd_addr); 33001a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy 33101a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy callbackEnv->CallVoidMethod(sJniCallbacksObj, method_aclStateChangeCallback, (jint) status, 33201a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy addr, (jint)state); 33301a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__); 33401a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy callbackEnv->DeleteLocalRef(addr); 33501a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy} 33601a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy 337ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void discovery_state_changed_callback(bt_discovery_state_t state) { 338ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jbyteArray addr; 339ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!checkCallbackThread()) { 340c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__); 341ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 342ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 343ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 344c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s: DiscoveryState:%d ", __FUNCTION__, state); 345ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 346ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh callbackEnv->CallVoidMethod(sJniCallbacksObj, method_discoveryStateChangeCallback, 347ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh (jint)state); 348ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 349ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__); 350ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 351ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 352ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void pin_request_callback(bt_bdaddr_t *bd_addr, bt_bdname_t *bdname, uint32_t cod) { 353ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jbyteArray addr, devname; 354ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!checkCallbackThread()) { 355c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__); 356ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 357ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 358ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!bd_addr) { 359c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Address is null in %s", __FUNCTION__); 360ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 361ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 362ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 363ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh addr = callbackEnv->NewByteArray(sizeof(bt_bdaddr_t)); 364ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (addr == NULL) goto Fail; 36561c4100eb0606f8ba630f5c45d07a88d612fbc85Matthew Xie callbackEnv->SetByteArrayRegion(addr, 0, sizeof(bt_bdaddr_t), (jbyte*)bd_addr); 366ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 367ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh devname = callbackEnv->NewByteArray(sizeof(bt_bdname_t)); 368ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (devname == NULL) goto Fail; 369ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 370ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh callbackEnv->SetByteArrayRegion(devname, 0, sizeof(bt_bdname_t), (jbyte*)bdname); 371ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 372ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh callbackEnv->CallVoidMethod(sJniCallbacksObj, method_pinRequestCallback, addr, devname, cod); 373ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 374ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__); 3756c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie callbackEnv->DeleteLocalRef(addr); 3766c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie callbackEnv->DeleteLocalRef(devname); 377ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 378ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 379ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar GaneshFail: 380ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (addr) callbackEnv->DeleteLocalRef(addr); 381ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (devname) callbackEnv->DeleteLocalRef(devname); 382c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Error while allocating in: %s", __FUNCTION__); 383ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 384ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 385ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void ssp_request_callback(bt_bdaddr_t *bd_addr, bt_bdname_t *bdname, uint32_t cod, 386ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh bt_ssp_variant_t pairing_variant, uint32_t pass_key) { 387ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jbyteArray addr, devname; 388ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!checkCallbackThread()) { 389c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__); 390ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 391ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 392ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!bd_addr) { 393c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Address is null in %s", __FUNCTION__); 394ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 395ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 396ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 397ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh addr = callbackEnv->NewByteArray(sizeof(bt_bdaddr_t)); 398ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (addr == NULL) goto Fail; 399ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh callbackEnv->SetByteArrayRegion(addr, 0, sizeof(bt_bdaddr_t), (jbyte *)bd_addr); 400ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 401ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh devname = callbackEnv->NewByteArray(sizeof(bt_bdname_t)); 402ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (devname == NULL) goto Fail; 403ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh callbackEnv->SetByteArrayRegion(devname, 0, sizeof(bt_bdname_t), (jbyte*)bdname); 404ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 405ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh callbackEnv->CallVoidMethod(sJniCallbacksObj, method_sspRequestCallback, addr, devname, cod, 406ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh (jint) pairing_variant, pass_key); 407ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 408ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__); 4096c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie callbackEnv->DeleteLocalRef(addr); 4106c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie callbackEnv->DeleteLocalRef(devname); 411ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 412ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 413ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar GaneshFail: 414ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (addr) callbackEnv->DeleteLocalRef(addr); 415ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (devname) callbackEnv->DeleteLocalRef(devname); 416ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 417c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Error while allocating in: %s", __FUNCTION__); 418ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 419ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 420ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void callback_thread_event(bt_cb_thread_evt event) { 421ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh JavaVM* vm = AndroidRuntime::getJavaVM(); 422ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (event == ASSOCIATE_JVM) { 423ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh JavaVMAttachArgs args; 424ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh char name[] = "BT Service Callback Thread"; 425b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom args.version = JNI_VERSION_1_6; 426ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh args.name = name; 427ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh args.group = NULL; 428ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh vm->AttachCurrentThread(&callbackEnv, &args); 429c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("Callback thread attached: %p", callbackEnv); 430ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } else if (event == DISASSOCIATE_JVM) { 431ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!checkCallbackThread()) { 432c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__); 433ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return; 434ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 435ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh vm->DetachCurrentThread(); 436ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 437ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 438ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 43903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Battastatic void dut_mode_recv_callback (uint16_t opcode, uint8_t *buf, uint8_t len) { 44003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 44103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta} 44203b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Battastatic void le_test_mode_recv_callback (bt_status_t status, uint16_t packet_count) { 44303b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 44403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta ALOGV("%s: status:%d packet_count:%d ", __FUNCTION__, status, packet_count); 44503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta} 4461e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavatistatic bt_callbacks_t sBluetoothCallbacks = { 447ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh sizeof(sBluetoothCallbacks), 448ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh adapter_state_change_callback, 449ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh adapter_properties_callback, 450ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh remote_device_properties_callback, 451ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh device_found_callback, 452ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh discovery_state_changed_callback, 453ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh pin_request_callback, 454ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh ssp_request_callback, 455ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh bond_state_changed_callback, 45601a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy acl_state_changed_callback, 457ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh callback_thread_event, 45803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta dut_mode_recv_callback, 45903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta 46003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta le_test_mode_recv_callback 461ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}; 462ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 4631e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati// The callback to call when the wake alarm fires. 4641e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavatistatic alarm_cb sAlarmCallback; 4651e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 4661e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati// The data to pass to the wake alarm callback. 4671e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavatistatic void *sAlarmCallbackData; 4681e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 4691e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavatistatic bool set_wake_alarm_callout(uint64_t delay_millis, bool should_wake, alarm_cb cb, void *data) { 4701e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati JNIEnv *env; 4711e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati JavaVM *vm = AndroidRuntime::getJavaVM(); 4721e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati jint status = vm->GetEnv((void **)&env, JNI_VERSION_1_6); 4731e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 4741e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati if (status != JNI_OK && status != JNI_EDETACHED) { 4751e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati ALOGE("%s unable to get environment for JNI call", __func__); 4761e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati return false; 4771e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati } 4781e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 4791e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati if (status == JNI_EDETACHED && vm->AttachCurrentThread(&env, NULL) != 0) { 4801e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati ALOGE("%s unable to attach thread to VM", __func__); 4811e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati return false; 4821e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati } 4831e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 4841e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati jboolean jshould_wake = should_wake ? JNI_TRUE : JNI_FALSE; 4851e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati jboolean ret = env->CallBooleanMethod(sJniAdapterServiceObj, method_setWakeAlarm, (jlong)delay_millis, jshould_wake); 4861e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati if (ret) { 4871e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati sAlarmCallback = cb; 4881e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati sAlarmCallbackData = data; 4891e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati } 4901e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 4911e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati if (status == JNI_EDETACHED) { 4921e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati vm->DetachCurrentThread(); 4931e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati } 4941e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 4951e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati return !!ret; 4961e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati} 4971e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 4981e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavatistatic int acquire_wake_lock_callout(const char *lock_name) { 4991e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati JNIEnv *env; 5001e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati JavaVM *vm = AndroidRuntime::getJavaVM(); 5011e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati jint status = vm->GetEnv((void **)&env, JNI_VERSION_1_6); 5021e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 5031e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati if (status != JNI_OK && status != JNI_EDETACHED) { 5041e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati ALOGE("%s unable to get environment for JNI call", __func__); 5051e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati return BT_STATUS_FAIL; 5061e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati } 5071e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 5081e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati if (status == JNI_EDETACHED && vm->AttachCurrentThread(&env, NULL) != 0) { 5091e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati ALOGE("%s unable to attach thread to VM", __func__); 5101e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati return BT_STATUS_FAIL; 5111e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati } 5121e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 5131e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati jboolean ret = JNI_FALSE; 5141e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati jstring lock_name_jni = env->NewStringUTF(lock_name); 5151e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati if (lock_name_jni) { 5161e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati ret = env->CallBooleanMethod(sJniAdapterServiceObj, method_acquireWakeLock, lock_name_jni); 5171e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati env->DeleteLocalRef(lock_name_jni); 5181e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati } else { 5191e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati ALOGE("%s unable to allocate string: %s", __func__, lock_name); 5201e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati } 5211e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 5221e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati if (status == JNI_EDETACHED) { 5231e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati vm->DetachCurrentThread(); 5241e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati } 5251e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 5261e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati return ret ? BT_STATUS_SUCCESS : BT_STATUS_FAIL; 5271e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati} 5281e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 5291e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavatistatic int release_wake_lock_callout(const char *lock_name) { 5301e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati JNIEnv *env; 5311e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati JavaVM *vm = AndroidRuntime::getJavaVM(); 5321e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati jint status = vm->GetEnv((void **)&env, JNI_VERSION_1_6); 5331e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 5341e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati if (status != JNI_OK && status != JNI_EDETACHED) { 5351e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati ALOGE("%s unable to get environment for JNI call", __func__); 5361e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati return BT_STATUS_FAIL; 5371e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati } 5381e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 5391e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati if (status == JNI_EDETACHED && vm->AttachCurrentThread(&env, NULL) != 0) { 5401e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati ALOGE("%s unable to attach thread to VM", __func__); 5411e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati return BT_STATUS_FAIL; 5421e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati } 5431e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 5441e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati jboolean ret = JNI_FALSE; 5451e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati jstring lock_name_jni = env->NewStringUTF(lock_name); 5461e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati if (lock_name_jni) { 5471e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati ret = env->CallBooleanMethod(sJniAdapterServiceObj, method_releaseWakeLock, lock_name_jni); 5481e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati env->DeleteLocalRef(lock_name_jni); 5491e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati } else { 5501e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati ALOGE("%s unable to allocate string: %s", __func__, lock_name); 5511e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati } 5521e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 5531e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati if (status == JNI_EDETACHED) { 5541e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati vm->DetachCurrentThread(); 5551e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati } 5561e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 5571e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati return ret ? BT_STATUS_SUCCESS : BT_STATUS_FAIL; 5581e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati} 5591e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 5601e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati// Called by Java code when alarm is fired. A wake lock is held by the caller 5611e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati// over the duration of this callback. 5621e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavatistatic void alarmFiredNative(JNIEnv *env, jobject obj) { 5631e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati sAlarmCallback(sAlarmCallbackData); 5641e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati} 5651e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 5661e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavatistatic bt_os_callouts_t sBluetoothOsCallouts = { 5671e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati sizeof(sBluetoothOsCallouts), 5681e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati set_wake_alarm_callout, 5691e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati acquire_wake_lock_callout, 5701e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati release_wake_lock_callout, 5711e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati}; 5721e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 573ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void classInitNative(JNIEnv* env, jclass clazz) { 574ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int err; 575ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh hw_module_t* module; 576ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 577ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jclass jniCallbackClass = 578ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh env->FindClass("com/android/bluetooth/btservice/JniCallbacks"); 579ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh sJniCallbacksField = env->GetFieldID(clazz, "mJniCallbacks", 580ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh "Lcom/android/bluetooth/btservice/JniCallbacks;"); 581ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 582ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh method_stateChangeCallback = env->GetMethodID(jniCallbackClass, "stateChangeCallback", "(I)V"); 583ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 584ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh method_adapterPropertyChangedCallback = env->GetMethodID(jniCallbackClass, 585ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh "adapterPropertyChangedCallback", 586ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh "([I[[B)V"); 587ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh method_discoveryStateChangeCallback = env->GetMethodID(jniCallbackClass, 588ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh "discoveryStateChangeCallback", "(I)V"); 589ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 590ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh method_devicePropertyChangedCallback = env->GetMethodID(jniCallbackClass, 591ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh "devicePropertyChangedCallback", 592ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh "([B[I[[B)V"); 593ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh method_deviceFoundCallback = env->GetMethodID(jniCallbackClass, "deviceFoundCallback", "([B)V"); 594ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh method_pinRequestCallback = env->GetMethodID(jniCallbackClass, "pinRequestCallback", 595ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh "([B[BI)V"); 596ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh method_sspRequestCallback = env->GetMethodID(jniCallbackClass, "sspRequestCallback", 597ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh "([B[BIII)V"); 598ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 599ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh method_bondStateChangeCallback = env->GetMethodID(jniCallbackClass, 600ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh "bondStateChangeCallback", "(I[BI)V"); 601ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 60201a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy method_aclStateChangeCallback = env->GetMethodID(jniCallbackClass, 60301a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy "aclStateChangeCallback", "(I[BI)V"); 6041e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 6051e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati method_setWakeAlarm = env->GetMethodID(clazz, "setWakeAlarm", "(JZ)Z"); 6061e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati method_acquireWakeLock = env->GetMethodID(clazz, "acquireWakeLock", "(Ljava/lang/String;)Z"); 6071e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati method_releaseWakeLock = env->GetMethodID(clazz, "releaseWakeLock", "(Ljava/lang/String;)Z"); 6081e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 609ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh char value[PROPERTY_VALUE_MAX]; 610ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh property_get("bluetooth.mock_stack", value, ""); 611ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 612ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh const char *id = (strcmp(value, "1")? BT_STACK_MODULE_ID : BT_STACK_TEST_MODULE_ID); 613ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 614ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh err = hw_get_module(id, (hw_module_t const**)&module); 615ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 616ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (err == 0) { 617ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh hw_device_t* abstraction; 618ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh err = module->methods->open(module, id, &abstraction); 619ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (err == 0) { 620ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh bluetooth_module_t* btStack = (bluetooth_module_t *)abstraction; 621ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh sBluetoothInterface = btStack->get_bluetooth_interface(); 622ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } else { 623c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Error while opening Bluetooth library"); 624ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 625ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } else { 626c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("No Bluetooth Library found"); 627ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 628ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 629ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 630ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic bool initNative(JNIEnv* env, jobject obj) { 631c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s:",__FUNCTION__); 632ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 6331e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati sJniAdapterServiceObj = env->NewGlobalRef(obj); 634ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh sJniCallbacksObj = env->NewGlobalRef(env->GetObjectField(obj, sJniCallbacksField)); 635ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 636ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (sBluetoothInterface) { 637ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int ret = sBluetoothInterface->init(&sBluetoothCallbacks); 638ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (ret != BT_STATUS_SUCCESS) { 6391e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati ALOGE("Error while setting the callbacks: %d\n", ret); 6401e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati sBluetoothInterface = NULL; 6411e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati return JNI_FALSE; 6421e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati } 6431e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati ret = sBluetoothInterface->set_os_callouts(&sBluetoothOsCallouts); 6441e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati if (ret != BT_STATUS_SUCCESS) { 6451e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati ALOGE("Error while setting Bluetooth callouts: %d\n", ret); 6461e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati sBluetoothInterface->cleanup(); 647ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh sBluetoothInterface = NULL; 648ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return JNI_FALSE; 649ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 6501e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati 651cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie if ( (sBluetoothSocketInterface = (btsock_interface_t *) 652cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie sBluetoothInterface->get_profile_interface(BT_PROFILE_SOCKETS_ID)) == NULL) { 653c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Error getting socket interface"); 654cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie } 655ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return JNI_TRUE; 656ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 657ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return JNI_FALSE; 658ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 659ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 660ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic bool cleanupNative(JNIEnv *env, jobject obj) { 661c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s:",__FUNCTION__); 662ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 663ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jboolean result = JNI_FALSE; 664ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!sBluetoothInterface) return result; 665ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 666ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh sBluetoothInterface->cleanup(); 667e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie ALOGI("%s: return from cleanup",__FUNCTION__); 6686654f5c903de510a70f9e72cd5ad7837b615d93ffredc 669ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh env->DeleteGlobalRef(sJniCallbacksObj); 6701e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati env->DeleteGlobalRef(sJniAdapterServiceObj); 671ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return JNI_TRUE; 672ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 673ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 674ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean enableNative(JNIEnv* env, jobject obj) { 675c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s:",__FUNCTION__); 676ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 677ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jboolean result = JNI_FALSE; 678ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!sBluetoothInterface) return result; 679ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 680ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int ret = sBluetoothInterface->enable(); 681ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE; 682ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 683ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 684ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 685ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean disableNative(JNIEnv* env, jobject obj) { 686c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s:",__FUNCTION__); 687ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 688ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jboolean result = JNI_FALSE; 689ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!sBluetoothInterface) return result; 690ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 691ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int ret = sBluetoothInterface->disable(); 692ad9fff218081d2f49471487d37387c764d69ed29YK Jeffrey Chao /* Retrun JNI_FALSE only when BTIF explicitly reports 693ad9fff218081d2f49471487d37387c764d69ed29YK Jeffrey Chao BT_STATUS_FAIL. It is fine for the BT_STATUS_NOT_READY 694ad9fff218081d2f49471487d37387c764d69ed29YK Jeffrey Chao case which indicates that stack had not been enabled. 695ad9fff218081d2f49471487d37387c764d69ed29YK Jeffrey Chao */ 696ad9fff218081d2f49471487d37387c764d69ed29YK Jeffrey Chao result = (ret == BT_STATUS_FAIL) ? JNI_FALSE : JNI_TRUE; 697ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 698ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 699ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 700ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean startDiscoveryNative(JNIEnv* env, jobject obj) { 701c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s:",__FUNCTION__); 702ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 703ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jboolean result = JNI_FALSE; 704ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!sBluetoothInterface) return result; 705ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 706ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int ret = sBluetoothInterface->start_discovery(); 707ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE; 708ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 709ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 710ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 711ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean cancelDiscoveryNative(JNIEnv* env, jobject obj) { 712c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s:",__FUNCTION__); 713ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 714ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jboolean result = JNI_FALSE; 715ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!sBluetoothInterface) return result; 716ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 717ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int ret = sBluetoothInterface->cancel_discovery(); 718ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE; 719ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 720ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 721ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 722ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean createBondNative(JNIEnv* env, jobject obj, jbyteArray address) { 723c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s:",__FUNCTION__); 724ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 725ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jbyte *addr; 726ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jboolean result = JNI_FALSE; 727ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 728ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!sBluetoothInterface) return result; 729ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 730ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh addr = env->GetByteArrayElements(address, NULL); 731ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (addr == NULL) { 732ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jniThrowIOException(env, EINVAL); 733ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 734ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 735ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 736ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int ret = sBluetoothInterface->create_bond((bt_bdaddr_t *)addr); 737b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom env->ReleaseByteArrayElements(address, addr, 0); 738ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE; 739ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 740ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 741ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 742ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 743ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean removeBondNative(JNIEnv* env, jobject obj, jbyteArray address) { 744c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s:",__FUNCTION__); 745ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 746ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jbyte *addr; 747ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jboolean result; 748ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!sBluetoothInterface) return JNI_FALSE; 749ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 750ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh addr = env->GetByteArrayElements(address, NULL); 751ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (addr == NULL) { 752ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jniThrowIOException(env, EINVAL); 753ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return JNI_FALSE; 754ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 755ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 756ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int ret = sBluetoothInterface->remove_bond((bt_bdaddr_t *)addr); 757b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom env->ReleaseByteArrayElements(address, addr, 0); 758ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE; 759ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 760ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 761ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 762ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 763ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean cancelBondNative(JNIEnv* env, jobject obj, jbyteArray address) { 764c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s:",__FUNCTION__); 765ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 766ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jbyte *addr; 767ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jboolean result; 768ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!sBluetoothInterface) return JNI_FALSE; 769ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 770ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh addr = env->GetByteArrayElements(address, NULL); 771ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (addr == NULL) { 772ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jniThrowIOException(env, EINVAL); 773ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return JNI_FALSE; 774ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 775ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 776ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int ret = sBluetoothInterface->cancel_bond((bt_bdaddr_t *)addr); 777b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom env->ReleaseByteArrayElements(address, addr, 0); 778ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE; 779ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 780ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 781ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 782ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 783ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean pinReplyNative(JNIEnv *env, jobject obj, jbyteArray address, jboolean accept, 784ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jint len, jbyteArray pinArray) { 785c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s:",__FUNCTION__); 786ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 787ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jbyte *addr, *pinPtr = NULL; 788ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jboolean result = JNI_FALSE; 789ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!sBluetoothInterface) return result; 790ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 791ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh addr = env->GetByteArrayElements(address, NULL); 792ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (addr == NULL) { 793ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jniThrowIOException(env, EINVAL); 794ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 795ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 796ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 797ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (accept) { 798ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh pinPtr = env->GetByteArrayElements(pinArray, NULL); 799ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (pinPtr == NULL) { 800ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jniThrowIOException(env, EINVAL); 801b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom env->ReleaseByteArrayElements(address, addr, 0); 802ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 803ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 804ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 805ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 806ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int ret = sBluetoothInterface->pin_reply((bt_bdaddr_t*)addr, accept, len, 807ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh (bt_pin_code_t *) pinPtr); 808b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom env->ReleaseByteArrayElements(address, addr, 0); 809b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom env->ReleaseByteArrayElements(pinArray, pinPtr, 0); 810ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE; 811ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 812ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 813ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 814ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 815ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean sspReplyNative(JNIEnv *env, jobject obj, jbyteArray address, 816581bb31a8165ff0f9c7d638cfe4a81aaaafa2dedJaikumar Ganesh jint type, jboolean accept, jint passkey) { 817c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s:",__FUNCTION__); 818ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 819ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jbyte *addr; 820ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jboolean result = JNI_FALSE; 821ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!sBluetoothInterface) return result; 822ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 823ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh addr = env->GetByteArrayElements(address, NULL); 824ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (addr == NULL) { 825ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jniThrowIOException(env, EINVAL); 826ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 827ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 828ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 829581bb31a8165ff0f9c7d638cfe4a81aaaafa2dedJaikumar Ganesh int ret = sBluetoothInterface->ssp_reply((bt_bdaddr_t *)addr, 830581bb31a8165ff0f9c7d638cfe4a81aaaafa2dedJaikumar Ganesh (bt_ssp_variant_t) type, accept, passkey); 831b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom env->ReleaseByteArrayElements(address, addr, 0); 832ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE; 833ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 834ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 835ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 836ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 837ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean setAdapterPropertyNative(JNIEnv *env, jobject obj, jint type, jbyteArray value) { 838c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s:",__FUNCTION__); 839ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 840ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jbyte *val; 841ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jboolean result = JNI_FALSE; 842ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!sBluetoothInterface) return result; 843ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 844ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh val = env->GetByteArrayElements(value, NULL); 845ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh bt_property_t prop; 846ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh prop.type = (bt_property_type_t) type; 847ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh prop.len = env->GetArrayLength(value); 848ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh prop.val = val; 849ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 850ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int ret = sBluetoothInterface->set_adapter_property(&prop); 851b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom env->ReleaseByteArrayElements(value, val, 0); 852ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE; 853ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 854ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 855ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 856ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 857ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean getAdapterPropertiesNative(JNIEnv *env, jobject obj) { 858c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s:",__FUNCTION__); 859ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 860ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jboolean result = JNI_FALSE; 861ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!sBluetoothInterface) return result; 862ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 863ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int ret = sBluetoothInterface->get_adapter_properties(); 864ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE; 865ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 866ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 867ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 868ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 869ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean getAdapterPropertyNative(JNIEnv *env, jobject obj, jint type) { 870c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s:",__FUNCTION__); 871ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 872ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jboolean result = JNI_FALSE; 873ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!sBluetoothInterface) return result; 874ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 875ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int ret = sBluetoothInterface->get_adapter_property((bt_property_type_t) type); 876ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE; 877ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 878ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 879ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 880ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 881ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean getDevicePropertyNative(JNIEnv *env, jobject obj, jbyteArray address, jint type) { 882c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s:",__FUNCTION__); 883ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 884ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jbyte *addr = NULL; 885ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jboolean result = JNI_FALSE; 886ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!sBluetoothInterface) return result; 887ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 888ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh addr = env->GetByteArrayElements(address, NULL); 889ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (addr == NULL) { 890ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jniThrowIOException(env, EINVAL); 891ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 892ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 893ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 894ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int ret = sBluetoothInterface->get_remote_device_property((bt_bdaddr_t *)addr, 895ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh (bt_property_type_t) type); 896b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom env->ReleaseByteArrayElements(address, addr, 0); 897ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE; 898ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 899ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 900ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 901ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 902ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean setDevicePropertyNative(JNIEnv *env, jobject obj, jbyteArray address, 903ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jint type, jbyteArray value) { 904c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGV("%s:",__FUNCTION__); 905ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 906ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jbyte *val, *addr; 907ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jboolean result = JNI_FALSE; 908ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (!sBluetoothInterface) return result; 909ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 910ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh val = env->GetByteArrayElements(value, NULL); 911ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (val == NULL) { 912ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jniThrowIOException(env, EINVAL); 913ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 914ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 915ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 916ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh addr = env->GetByteArrayElements(address, NULL); 917ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh if (addr == NULL) { 918b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom env->ReleaseByteArrayElements(value, val, 0); 919ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh jniThrowIOException(env, EINVAL); 920ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 921ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh } 922ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 923ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 924ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh bt_property_t prop; 925ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh prop.type = (bt_property_type_t) type; 926ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh prop.len = env->GetArrayLength(value); 927ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh prop.val = val; 928ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 929ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh int ret = sBluetoothInterface->set_remote_device_property((bt_bdaddr_t *)addr, &prop); 930b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom env->ReleaseByteArrayElements(value, val, 0); 931b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom env->ReleaseByteArrayElements(address, addr, 0); 932ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 933ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE; 934ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 935ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return result; 936ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 937ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 938c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredcstatic jboolean getRemoteServicesNative(JNIEnv *env, jobject obj, jbyteArray address) { 939e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie ALOGV("%s:",__FUNCTION__); 940c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc 941c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc jbyte *addr = NULL; 942c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc jboolean result = JNI_FALSE; 943c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc if (!sBluetoothInterface) return result; 944c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc 945c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc addr = env->GetByteArrayElements(address, NULL); 946c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc if (addr == NULL) { 947c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc jniThrowIOException(env, EINVAL); 948c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc return result; 949c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc } 950c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc 951c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc int ret = sBluetoothInterface->get_remote_services((bt_bdaddr_t *)addr); 952b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom env->ReleaseByteArrayElements(address, addr, 0); 953c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE; 954c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc return result; 955c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc} 956c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc 957cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xiestatic int connectSocketNative(JNIEnv *env, jobject object, jbyteArray address, jint type, 958cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie jbyteArray uuidObj, jint channel, jint flag) { 959cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie jbyte *addr = NULL, *uuid = NULL; 960cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie int socket_fd; 961cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie bt_status_t status; 962cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie 963b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom if (!sBluetoothSocketInterface) return -1; 964cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie 965cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie addr = env->GetByteArrayElements(address, NULL); 966cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie if (!addr) { 967c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("failed to get Bluetooth device address"); 968cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie goto Fail; 969cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie } 970cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie 971cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie uuid = env->GetByteArrayElements(uuidObj, NULL); 972cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie if (!uuid) { 973c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("failed to get uuid"); 974cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie goto Fail; 975cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie } 976cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie 977cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie if ( (status = sBluetoothSocketInterface->connect((bt_bdaddr_t *) addr, (btsock_type_t) type, 978cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie (const uint8_t*) uuid, channel, &socket_fd, flag)) != BT_STATUS_SUCCESS) { 979c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Socket connection failed: %d", status); 980cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie goto Fail; 981cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie } 982cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie 983cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie 984cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie if (socket_fd < 0) { 985c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Fail to creat file descriptor on socket fd"); 986cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie goto Fail; 987cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie } 988cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie env->ReleaseByteArrayElements(address, addr, 0); 989cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie env->ReleaseByteArrayElements(uuidObj, uuid, 0); 990cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie return socket_fd; 991cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie 992cc80b2261351dc74ad1bed237b0423c12d340514Matthew XieFail: 993cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie if (addr) env->ReleaseByteArrayElements(address, addr, 0); 994cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie if (uuid) env->ReleaseByteArrayElements(uuidObj, uuid, 0); 995cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie 996cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie return -1; 997cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie} 998cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie 999cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xiestatic int createSocketChannelNative(JNIEnv *env, jobject object, jint type, 1000b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom jstring name_str, jbyteArray uuidObj, jint channel, jint flag) { 1001cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie const char *service_name; 1002cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie jbyte *uuid = NULL; 1003cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie int socket_fd; 1004cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie bt_status_t status; 1005cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie 1006b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom if (!sBluetoothSocketInterface) return -1; 1007cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie 10088799f44e07ff7cde70a8d58893e995d3a9fa1e76Matthew Xie ALOGV("%s: SOCK FLAG = %x", __FUNCTION__, flag); 10098799f44e07ff7cde70a8d58893e995d3a9fa1e76Matthew Xie 1010cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie service_name = env->GetStringUTFChars(name_str, NULL); 1011cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie 1012cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie uuid = env->GetByteArrayElements(uuidObj, NULL); 1013cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie if (!uuid) { 1014c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("failed to get uuid"); 1015cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie goto Fail; 1016cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie } 1017cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie if ( (status = sBluetoothSocketInterface->listen((btsock_type_t) type, service_name, 1018cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie (const uint8_t*) uuid, channel, &socket_fd, flag)) != BT_STATUS_SUCCESS) { 1019c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Socket listen failed: %d", status); 1020cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie goto Fail; 1021cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie } 1022cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie 1023cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie if (socket_fd < 0) { 1024c55a9837c004044051b71bb47182ace156691283Matthew Xie ALOGE("Fail to creat file descriptor on socket fd"); 1025cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie goto Fail; 1026cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie } 1027cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie if (service_name) env->ReleaseStringUTFChars(name_str, service_name); 1028cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie if (uuid) env->ReleaseByteArrayElements(uuidObj, uuid, 0); 1029cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie return socket_fd; 1030cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie 1031cc80b2261351dc74ad1bed237b0423c12d340514Matthew XieFail: 1032cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie if (service_name) env->ReleaseStringUTFChars(name_str, service_name); 1033cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie if (uuid) env->ReleaseByteArrayElements(uuidObj, uuid, 0); 1034cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie 1035cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie return -1; 1036cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie} 1037cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie 10389d80b509f715a3c3f2ebd0de373d427fc31a6e6cZhihai Xustatic jboolean configHciSnoopLogNative(JNIEnv* env, jobject obj, jboolean enable) { 10399d80b509f715a3c3f2ebd0de373d427fc31a6e6cZhihai Xu ALOGV("%s:",__FUNCTION__); 10409d80b509f715a3c3f2ebd0de373d427fc31a6e6cZhihai Xu 10419d80b509f715a3c3f2ebd0de373d427fc31a6e6cZhihai Xu jboolean result = JNI_FALSE; 10429d80b509f715a3c3f2ebd0de373d427fc31a6e6cZhihai Xu 10439d80b509f715a3c3f2ebd0de373d427fc31a6e6cZhihai Xu if (!sBluetoothInterface) return result; 10449d80b509f715a3c3f2ebd0de373d427fc31a6e6cZhihai Xu 10459d80b509f715a3c3f2ebd0de373d427fc31a6e6cZhihai Xu int ret = sBluetoothInterface->config_hci_snoop_log(enable); 10469d80b509f715a3c3f2ebd0de373d427fc31a6e6cZhihai Xu 10479d80b509f715a3c3f2ebd0de373d427fc31a6e6cZhihai Xu result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE; 10489d80b509f715a3c3f2ebd0de373d427fc31a6e6cZhihai Xu 10499d80b509f715a3c3f2ebd0de373d427fc31a6e6cZhihai Xu return result; 10509d80b509f715a3c3f2ebd0de373d427fc31a6e6cZhihai Xu} 10519d80b509f715a3c3f2ebd0de373d427fc31a6e6cZhihai Xu 1052ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic JNINativeMethod sMethods[] = { 1053b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom /* name, signature, funcPtr */ 1054ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh {"classInitNative", "()V", (void *) classInitNative}, 1055ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh {"initNative", "()Z", (void *) initNative}, 1056ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh {"cleanupNative", "()V", (void*) cleanupNative}, 1057ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh {"enableNative", "()Z", (void*) enableNative}, 1058ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh {"disableNative", "()Z", (void*) disableNative}, 1059ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh {"setAdapterPropertyNative", "(I[B)Z", (void*) setAdapterPropertyNative}, 1060ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh {"getAdapterPropertiesNative", "()Z", (void*) getAdapterPropertiesNative}, 1061ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh {"getAdapterPropertyNative", "(I)Z", (void*) getAdapterPropertyNative}, 1062ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh {"getDevicePropertyNative", "([BI)Z", (void*) getDevicePropertyNative}, 1063ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh {"setDevicePropertyNative", "([BI[B)Z", (void*) setDevicePropertyNative}, 1064ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh {"startDiscoveryNative", "()Z", (void*) startDiscoveryNative}, 1065ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh {"cancelDiscoveryNative", "()Z", (void*) cancelDiscoveryNative}, 1066ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh {"createBondNative", "([B)Z", (void*) createBondNative}, 1067ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh {"removeBondNative", "([B)Z", (void*) removeBondNative}, 1068ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh {"cancelBondNative", "([B)Z", (void*) cancelBondNative}, 1069ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh {"pinReplyNative", "([BZI[B)Z", (void*) pinReplyNative}, 1070581bb31a8165ff0f9c7d638cfe4a81aaaafa2dedJaikumar Ganesh {"sspReplyNative", "([BIZI)Z", (void*) sspReplyNative}, 1071c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc {"getRemoteServicesNative", "([B)Z", (void*) getRemoteServicesNative}, 1072cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie {"connectSocketNative", "([BI[BII)I", (void*) connectSocketNative}, 1073cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie {"createSocketChannelNative", "(ILjava/lang/String;[BII)I", 10749d80b509f715a3c3f2ebd0de373d427fc31a6e6cZhihai Xu (void*) createSocketChannelNative}, 10751e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati {"configHciSnoopLogNative", "(Z)Z", (void*) configHciSnoopLogNative}, 10761e9f8a14e120e8786711abdd4a965236191c87adSharvil Nanavati {"alarmFiredNative", "()V", (void *) alarmFiredNative}, 1077ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}; 1078ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 1079ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshint register_com_android_bluetooth_btservice_AdapterService(JNIEnv* env) 1080ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh{ 1081ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh return jniRegisterNativeMethods(env, "com/android/bluetooth/btservice/AdapterService", 1082ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh sMethods, NELEM(sMethods)); 1083ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 1084ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 1085ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} /* namespace android */ 1086ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 1087ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh 1088ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh/* 1089ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh * JNI Initialization 1090ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh */ 1091ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshjint JNI_OnLoad(JavaVM *jvm, void *reserved) 1092ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh{ 1093b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom JNIEnv *e; 1094b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom int status; 1095b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom 1096b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom ALOGV("Bluetooth Adapter Service : loading JNI\n"); 1097b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom 1098b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom // Check JNI version 1099b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom if (jvm->GetEnv((void **)&e, JNI_VERSION_1_6)) { 1100b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom ALOGE("JNI version mismatch error"); 1101b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom return JNI_ERR; 1102b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom } 1103b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom 1104b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom if ((status = android::register_com_android_bluetooth_btservice_AdapterService(e)) < 0) { 1105b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom ALOGE("jni adapter service registration failure, status: %d", status); 1106b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom return JNI_ERR; 1107b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom } 1108b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom 1109b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom if ((status = android::register_com_android_bluetooth_hfp(e)) < 0) { 1110b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom ALOGE("jni hfp registration failure, status: %d", status); 1111b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom return JNI_ERR; 1112b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom } 1113b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom 1114b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom if ((status = android::register_com_android_bluetooth_a2dp(e)) < 0) { 1115b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom ALOGE("jni a2dp registration failure: %d", status); 1116b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom return JNI_ERR; 1117b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom } 1118b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom 1119c1c259c0ace7195240f1443c805995bfe8692a72Zhihai Xu if ((status = android::register_com_android_bluetooth_avrcp(e)) < 0) { 1120c1c259c0ace7195240f1443c805995bfe8692a72Zhihai Xu ALOGE("jni avrcp registration failure: %d", status); 1121c1c259c0ace7195240f1443c805995bfe8692a72Zhihai Xu return JNI_ERR; 1122c1c259c0ace7195240f1443c805995bfe8692a72Zhihai Xu } 1123c1c259c0ace7195240f1443c805995bfe8692a72Zhihai Xu 1124b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom if ((status = android::register_com_android_bluetooth_hid(e)) < 0) { 1125b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom ALOGE("jni hid registration failure: %d", status); 1126b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom return JNI_ERR; 1127b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom } 1128b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom 1129b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom if ((status = android::register_com_android_bluetooth_hdp(e)) < 0) { 1130b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom ALOGE("jni hdp registration failure: %d", status); 1131b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom return JNI_ERR; 1132b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom } 1133b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom 1134b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom if ((status = android::register_com_android_bluetooth_pan(e)) < 0) { 1135b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom ALOGE("jni pan registration failure: %d", status); 1136b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom return JNI_ERR; 1137b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom } 1138b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom 1139b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom if ((status = android::register_com_android_bluetooth_gatt(e)) < 0) { 1140b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom ALOGE("jni gatt registration failure: %d", status); 1141b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom return JNI_ERR; 1142b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom } 1143b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom return JNI_VERSION_1_6; 1144ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} 1145