com_android_bluetooth_btservice_AdapterService.cpp revision b241cda1eec2fbefd6d21e0819532f7a76947635
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"
24ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
25ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh#include <string.h>
26ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh#include <pthread.h>
27ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
28ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh#include <sys/stat.h>
29ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh#include <fcntl.h>
30ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
31ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshnamespace android {
32ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
336c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie#define ADDITIONAL_NREFS 50
34ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jmethodID method_stateChangeCallback;
35ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jmethodID method_adapterPropertyChangedCallback;
36ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jmethodID method_devicePropertyChangedCallback;
37ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jmethodID method_deviceFoundCallback;
38ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jmethodID method_pinRequestCallback;
39ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jmethodID method_sspRequestCallback;
40ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jmethodID method_bondStateChangeCallback;
4101a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamystatic jmethodID method_aclStateChangeCallback;
42ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jmethodID method_discoveryStateChangeCallback;
43ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
44ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic const bt_interface_t *sBluetoothInterface = NULL;
45cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xiestatic const btsock_interface_t *sBluetoothSocketInterface = NULL;
46ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic JNIEnv *callbackEnv = NULL;
47ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
48ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jobject sJniCallbacksObj;
49ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jfieldID sJniCallbacksField;
50ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
51cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie
526c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xieconst bt_interface_t* getBluetoothInterface() {
536c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie    return sBluetoothInterface;
546c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie}
556c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie
566c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew XieJNIEnv* getCallbackEnv() {
57b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    return callbackEnv;
586c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie}
596c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie
606c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xievoid checkAndClearExceptionFromCallback(JNIEnv* env,
61ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                               const char* methodName) {
62ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (env->ExceptionCheck()) {
63c55a9837c004044051b71bb47182ace156691283Matthew Xie        ALOGE("An exception was thrown by callback '%s'.", methodName);
64ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        LOGE_EX(env);
65ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        env->ExceptionClear();
66ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
67ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
68ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
69ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic bool checkCallbackThread() {
70ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    JNIEnv* env = AndroidRuntime::getJNIEnv();
71676cb1bdd1c14c7af56562bab51f168e7f8f6d62Matthew Xie    if (callbackEnv != env || callbackEnv == NULL) {
72c55a9837c004044051b71bb47182ace156691283Matthew Xie        ALOGE("Callback env check fail: env: %p, callback: %p", env, callbackEnv);
73676cb1bdd1c14c7af56562bab51f168e7f8f6d62Matthew Xie        return false;
74676cb1bdd1c14c7af56562bab51f168e7f8f6d62Matthew Xie    }
75ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return true;
76ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
77ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
78ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void adapter_state_change_callback(bt_state_t status) {
79ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!checkCallbackThread()) {
80c55a9837c004044051b71bb47182ace156691283Matthew Xie       ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__);
81ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh       return;
82ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
83c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s: Status is: %d", __FUNCTION__, status);
84ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
85ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    callbackEnv->CallVoidMethod(sJniCallbacksObj, method_stateChangeCallback, (jint)status);
86ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
87ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__);
88ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
89ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
90ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic int get_properties(int num_properties, bt_property_t *properties, jintArray *types,
91ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                        jobjectArray *props) {
92edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    jbyteArray propVal;
93ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    for (int i = 0; i < num_properties; i++) {
94f8d98da947bbb9e2380a60df89acbcbd4ca680afKausik Sinnaswamy
95b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        /* The higher layers expect rssi as a short int value, while the value is sent as a byte
96b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom         * to jni. Converting rssi value to the expected format.*/
97b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        if (properties[i].type == BT_PROPERTY_REMOTE_RSSI)
98b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        {
99b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom            jbyte rssi = *((jbyte *) properties[i].val);
100b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom            short rssiValue = rssi;
101b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom            properties[i].len = sizeof(rssiValue);
102b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom            properties[i].val = &rssiValue;
103b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        }
104b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom
105b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        propVal = callbackEnv->NewByteArray(properties[i].len);
106b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        if (propVal == NULL) goto Fail;
107b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom
108b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        callbackEnv->SetByteArrayRegion(propVal, 0, properties[i].len,
109b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom                                             (jbyte*)properties[i].val);
110b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        callbackEnv->SetObjectArrayElement(*props, i, propVal);
111b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        // Delete reference to propVal
112b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        callbackEnv->DeleteLocalRef(propVal);
113b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        callbackEnv->SetIntArrayRegion(*types, i, 1, (jint *)&properties[i].type);
114ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
115ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return 0;
116ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar GaneshFail:
117ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (propVal) callbackEnv->DeleteLocalRef(propVal);
118c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGE("Error while allocation of array in %s", __FUNCTION__);
119ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return -1;
120ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
121ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
122ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void adapter_properties_callback(bt_status_t status, int num_properties,
123ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                        bt_property_t *properties) {
124ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jobjectArray props;
125ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jintArray types;
126edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    jbyteArray val;
127edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    jclass mclass;
128edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M
129ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!checkCallbackThread()) {
130c55a9837c004044051b71bb47182ace156691283Matthew Xie       ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__);
131ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh       return;
132ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
133ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
134c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s: Status is: %d, Properties: %d", __FUNCTION__, status, num_properties);
135ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
136ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (status != BT_STATUS_SUCCESS) {
137c55a9837c004044051b71bb47182ace156691283Matthew Xie        ALOGE("%s: Status %d is incorrect", __FUNCTION__, status);
138ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        return;
139ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
140ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
141edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    val = (jbyteArray) callbackEnv->NewByteArray(num_properties);
142edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    if (val == NULL) {
143e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie        ALOGE("%s: Error allocating byteArray", __FUNCTION__);
144edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M        return;
145edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    }
146edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M
147edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    mclass = callbackEnv->GetObjectClass(val);
148edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M
149edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    /* (BT) Initialize the jobjectArray and jintArray here itself and send the
150edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M     initialized array pointers alone to get_properties */
151edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M
152edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    props = callbackEnv->NewObjectArray(num_properties, mclass,
153edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M                                             NULL);
154edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    if (props == NULL) {
155e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie        ALOGE("%s: Error allocating object Array for properties", __FUNCTION__);
156edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M        return;
157edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    }
158edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M
159edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    types = (jintArray)callbackEnv->NewIntArray(num_properties);
160edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M
161edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    if (types == NULL) {
162e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie        ALOGE("%s: Error allocating int Array for values", __FUNCTION__);
163edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M        return;
164edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    }
165edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    // Delete the reference to val and mclass
166edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    callbackEnv->DeleteLocalRef(mclass);
167edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    callbackEnv->DeleteLocalRef(val);
168edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M
169ff68148a7fb74947ea5e7a337161108363cbe9f5Jaikumar Ganesh    if (get_properties(num_properties, properties, &types, &props) < 0) {
170ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        if (props) callbackEnv->DeleteLocalRef(props);
171ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        if (types) callbackEnv->DeleteLocalRef(types);
172ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        return;
173ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
174ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
175ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    callbackEnv->CallVoidMethod(sJniCallbacksObj, method_adapterPropertyChangedCallback, types,
176ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                props);
177ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__);
1786c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie    callbackEnv->DeleteLocalRef(props);
1796c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie    callbackEnv->DeleteLocalRef(types);
180ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return;
181ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
182ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
183ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
184ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void remote_device_properties_callback(bt_status_t status, bt_bdaddr_t *bd_addr,
185ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                              int num_properties, bt_property_t *properties) {
186ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!checkCallbackThread()) {
187c55a9837c004044051b71bb47182ace156691283Matthew Xie       ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__);
188ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh       return;
189ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
190ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
191c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s: Status is: %d, Properties: %d", __FUNCTION__, status, num_properties);
192ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
193ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (status != BT_STATUS_SUCCESS) {
194c55a9837c004044051b71bb47182ace156691283Matthew Xie        ALOGE("%s: Status %d is incorrect", __FUNCTION__, status);
195ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        return;
196ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
197ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
1986c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie    callbackEnv->PushLocalFrame(ADDITIONAL_NREFS);
1996c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie
2006c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie    jobjectArray props;
2016c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie    jbyteArray addr;
2026c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie    jintArray types;
203edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    jbyteArray val;
204edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    jclass mclass;
205edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M
206edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    val = (jbyteArray) callbackEnv->NewByteArray(num_properties);
207edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    if (val == NULL) {
208e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie        ALOGE("%s: Error allocating byteArray", __FUNCTION__);
209edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M        return;
210edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    }
211edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M
212edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    mclass = callbackEnv->GetObjectClass(val);
213edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M
214edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    /* Initialize the jobjectArray and jintArray here itself and send the
215edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M     initialized array pointers alone to get_properties */
216edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M
217edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    props = callbackEnv->NewObjectArray(num_properties, mclass,
218edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M                                             NULL);
219edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    if (props == NULL) {
220e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie        ALOGE("%s: Error allocating object Array for properties", __FUNCTION__);
221edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M        return;
222edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    }
223edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M
224edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    types = (jintArray)callbackEnv->NewIntArray(num_properties);
225edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M
226edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    if (types == NULL) {
227e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie        ALOGE("%s: Error allocating int Array for values", __FUNCTION__);
228edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M        return;
229edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    }
230edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    // Delete the reference to val and mclass
231edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    callbackEnv->DeleteLocalRef(mclass);
232edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    callbackEnv->DeleteLocalRef(val);
2336c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie
234ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    addr = callbackEnv->NewByteArray(sizeof(bt_bdaddr_t));
235ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (addr == NULL) goto Fail;
236ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (addr) callbackEnv->SetByteArrayRegion(addr, 0, sizeof(bt_bdaddr_t), (jbyte*)bd_addr);
237ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
238ff68148a7fb74947ea5e7a337161108363cbe9f5Jaikumar Ganesh    if (get_properties(num_properties, properties, &types, &props) < 0) {
239ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        if (props) callbackEnv->DeleteLocalRef(props);
240ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        if (types) callbackEnv->DeleteLocalRef(types);
2416c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie        callbackEnv->PopLocalFrame(NULL);
242ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        return;
243ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
244ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
245ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    callbackEnv->CallVoidMethod(sJniCallbacksObj, method_devicePropertyChangedCallback, addr,
246ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                types, props);
247ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__);
2486c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie    callbackEnv->DeleteLocalRef(props);
2496c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie    callbackEnv->DeleteLocalRef(types);
250edb14a4944d66ca9255b2ab9b384c583b626fd94Syed Ibrahim M    callbackEnv->DeleteLocalRef(addr);
2516c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie    callbackEnv->PopLocalFrame(NULL);
252ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return;
253ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
254ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar GaneshFail:
255c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGE("Error while allocation byte array in %s", __FUNCTION__);
256ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
257ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
258ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
259ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void device_found_callback(int num_properties, bt_property_t *properties) {
260ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jbyteArray addr = NULL;
261ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    int addr_index;
262ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
263ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    for (int i = 0; i < num_properties; i++) {
264ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        if (properties[i].type == BT_PROPERTY_BDADDR) {
265ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh            addr = callbackEnv->NewByteArray(properties[i].len);
266ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh            if (addr) {
267ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                callbackEnv->SetByteArrayRegion(addr, 0, properties[i].len,
268ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                                (jbyte*)properties[i].val);
269ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                addr_index = i;
270ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh            } else {
271c55a9837c004044051b71bb47182ace156691283Matthew Xie                ALOGE("Address is NULL (unable to allocate) in %s", __FUNCTION__);
272ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                return;
273ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh            }
274ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        }
275ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
276ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (addr == NULL) {
277c55a9837c004044051b71bb47182ace156691283Matthew Xie        ALOGE("Address is NULL in %s", __FUNCTION__);
278ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        return;
279ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
280ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
281c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s: Properties: %d, Address: %s", __FUNCTION__, num_properties,
282ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        (const char *)properties[addr_index].val);
283ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
284ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    remote_device_properties_callback(BT_STATUS_SUCCESS, (bt_bdaddr_t *)properties[addr_index].val,
285ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                      num_properties, properties);
286ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
287ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    callbackEnv->CallVoidMethod(sJniCallbacksObj, method_deviceFoundCallback, addr);
288ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__);
2896c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie    callbackEnv->DeleteLocalRef(addr);
290ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
291ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
292ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void bond_state_changed_callback(bt_status_t status, bt_bdaddr_t *bd_addr,
293ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                        bt_bond_state_t state) {
294ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jbyteArray addr;
295ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    int i;
296ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!checkCallbackThread()) {
297c55a9837c004044051b71bb47182ace156691283Matthew Xie       ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__);
298ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh       return;
299ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
300ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!bd_addr) {
301c55a9837c004044051b71bb47182ace156691283Matthew Xie        ALOGE("Address is null in %s", __FUNCTION__);
302ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        return;
303ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
304ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    addr = callbackEnv->NewByteArray(sizeof(bt_bdaddr_t));
305ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (addr == NULL) {
306c55a9837c004044051b71bb47182ace156691283Matthew Xie       ALOGE("Address allocation failed in %s", __FUNCTION__);
307ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh       return;
308ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
309ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    callbackEnv->SetByteArrayRegion(addr, 0, sizeof(bt_bdaddr_t), (jbyte *)bd_addr);
310ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
311ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    callbackEnv->CallVoidMethod(sJniCallbacksObj, method_bondStateChangeCallback, (jint) status,
312ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                addr, (jint)state);
313ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__);
3146c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie    callbackEnv->DeleteLocalRef(addr);
315ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
316ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
31701a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamystatic void acl_state_changed_callback(bt_status_t status, bt_bdaddr_t *bd_addr,
31801a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy                                       bt_acl_state_t state)
31901a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy{
32001a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy    jbyteArray addr;
32101a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy    int i;
32201a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy    if (!checkCallbackThread()) {
323e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie       ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__);
32401a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy       return;
32501a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy    }
32601a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy    if (!bd_addr) {
327e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie        ALOGE("Address is null in %s", __FUNCTION__);
32801a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy        return;
32901a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy    }
33001a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy    addr = callbackEnv->NewByteArray(sizeof(bt_bdaddr_t));
33101a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy    if (addr == NULL) {
332e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie       ALOGE("Address allocation failed in %s", __FUNCTION__);
33301a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy       return;
33401a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy    }
33501a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy    callbackEnv->SetByteArrayRegion(addr, 0, sizeof(bt_bdaddr_t), (jbyte *)bd_addr);
33601a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy
33701a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy    callbackEnv->CallVoidMethod(sJniCallbacksObj, method_aclStateChangeCallback, (jint) status,
33801a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy                                addr, (jint)state);
33901a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy    checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__);
34001a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy    callbackEnv->DeleteLocalRef(addr);
34101a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy}
34201a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy
343ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void discovery_state_changed_callback(bt_discovery_state_t state) {
344ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jbyteArray addr;
345ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!checkCallbackThread()) {
346c55a9837c004044051b71bb47182ace156691283Matthew Xie       ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__);
347ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh       return;
348ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
349ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
350c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s: DiscoveryState:%d ", __FUNCTION__, state);
351ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
352ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    callbackEnv->CallVoidMethod(sJniCallbacksObj, method_discoveryStateChangeCallback,
353ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                (jint)state);
354ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
355ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__);
356ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
357ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
358ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void pin_request_callback(bt_bdaddr_t *bd_addr, bt_bdname_t *bdname, uint32_t cod) {
359ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jbyteArray addr, devname;
360ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!checkCallbackThread()) {
361c55a9837c004044051b71bb47182ace156691283Matthew Xie       ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__);
362ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh       return;
363ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
364ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!bd_addr) {
365c55a9837c004044051b71bb47182ace156691283Matthew Xie        ALOGE("Address is null in %s", __FUNCTION__);
366ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        return;
367ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
368ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
369ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    addr = callbackEnv->NewByteArray(sizeof(bt_bdaddr_t));
370ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (addr == NULL) goto Fail;
37161c4100eb0606f8ba630f5c45d07a88d612fbc85Matthew Xie    callbackEnv->SetByteArrayRegion(addr, 0, sizeof(bt_bdaddr_t), (jbyte*)bd_addr);
372ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
373ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    devname = callbackEnv->NewByteArray(sizeof(bt_bdname_t));
374ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (devname == NULL) goto Fail;
375ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
376ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    callbackEnv->SetByteArrayRegion(devname, 0, sizeof(bt_bdname_t), (jbyte*)bdname);
377ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
378ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    callbackEnv->CallVoidMethod(sJniCallbacksObj, method_pinRequestCallback, addr, devname, cod);
379ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
380ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__);
3816c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie    callbackEnv->DeleteLocalRef(addr);
3826c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie    callbackEnv->DeleteLocalRef(devname);
383ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return;
384ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
385ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar GaneshFail:
386ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (addr) callbackEnv->DeleteLocalRef(addr);
387ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (devname) callbackEnv->DeleteLocalRef(devname);
388c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGE("Error while allocating in: %s", __FUNCTION__);
389ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
390ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
391ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void ssp_request_callback(bt_bdaddr_t *bd_addr, bt_bdname_t *bdname, uint32_t cod,
392ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                 bt_ssp_variant_t pairing_variant, uint32_t pass_key) {
393ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jbyteArray addr, devname;
394ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!checkCallbackThread()) {
395c55a9837c004044051b71bb47182ace156691283Matthew Xie       ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__);
396ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh       return;
397ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
398ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!bd_addr) {
399c55a9837c004044051b71bb47182ace156691283Matthew Xie        ALOGE("Address is null in %s", __FUNCTION__);
400ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        return;
401ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
402ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
403ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    addr = callbackEnv->NewByteArray(sizeof(bt_bdaddr_t));
404ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (addr == NULL) goto Fail;
405ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    callbackEnv->SetByteArrayRegion(addr, 0, sizeof(bt_bdaddr_t), (jbyte *)bd_addr);
406ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
407ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    devname = callbackEnv->NewByteArray(sizeof(bt_bdname_t));
408ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (devname == NULL) goto Fail;
409ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    callbackEnv->SetByteArrayRegion(devname, 0, sizeof(bt_bdname_t), (jbyte*)bdname);
410ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
411ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    callbackEnv->CallVoidMethod(sJniCallbacksObj, method_sspRequestCallback, addr, devname, cod,
412ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                (jint) pairing_variant, pass_key);
413ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
414ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    checkAndClearExceptionFromCallback(callbackEnv, __FUNCTION__);
4156c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie    callbackEnv->DeleteLocalRef(addr);
4166c91bc0a163cc7600c40d7fb979777fd911d1ef1Matthew Xie    callbackEnv->DeleteLocalRef(devname);
417ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return;
418ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
419ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar GaneshFail:
420ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (addr) callbackEnv->DeleteLocalRef(addr);
421ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (devname) callbackEnv->DeleteLocalRef(devname);
422ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
423c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGE("Error while allocating in: %s", __FUNCTION__);
424ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
425ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
426ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void callback_thread_event(bt_cb_thread_evt event) {
427ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    JavaVM* vm = AndroidRuntime::getJavaVM();
428ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (event  == ASSOCIATE_JVM) {
429ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        JavaVMAttachArgs args;
430ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        char name[] = "BT Service Callback Thread";
431b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        args.version = JNI_VERSION_1_6;
432ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        args.name = name;
433ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        args.group = NULL;
434ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        vm->AttachCurrentThread(&callbackEnv, &args);
435c55a9837c004044051b71bb47182ace156691283Matthew Xie        ALOGV("Callback thread attached: %p", callbackEnv);
436ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    } else if (event == DISASSOCIATE_JVM) {
437ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        if (!checkCallbackThread()) {
438c55a9837c004044051b71bb47182ace156691283Matthew Xie            ALOGE("Callback: '%s' is not called on the correct thread", __FUNCTION__);
439ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh            return;
440ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        }
441ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        vm->DetachCurrentThread();
442ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
443ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
444ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
44503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Battastatic void dut_mode_recv_callback (uint16_t opcode, uint8_t *buf, uint8_t len) {
44603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta
44703b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta}
44803b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Battastatic void le_test_mode_recv_callback (bt_status_t status, uint16_t packet_count) {
44903b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta
45003b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta    ALOGV("%s: status:%d packet_count:%d ", __FUNCTION__, status, packet_count);
45103b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta}
452ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshbt_callbacks_t sBluetoothCallbacks = {
453ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    sizeof(sBluetoothCallbacks),
454ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    adapter_state_change_callback,
455ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    adapter_properties_callback,
456ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    remote_device_properties_callback,
457ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    device_found_callback,
458ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    discovery_state_changed_callback,
459ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    pin_request_callback,
460ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    ssp_request_callback,
461ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    bond_state_changed_callback,
46201a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy    acl_state_changed_callback,
463ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    callback_thread_event,
46403b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta    dut_mode_recv_callback,
46503b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta
46603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta    le_test_mode_recv_callback
467ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh};
468ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
469ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic void classInitNative(JNIEnv* env, jclass clazz) {
470ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    int err;
471ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    hw_module_t* module;
472ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
473ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jclass jniCallbackClass =
474ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        env->FindClass("com/android/bluetooth/btservice/JniCallbacks");
475ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    sJniCallbacksField = env->GetFieldID(clazz, "mJniCallbacks",
476ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        "Lcom/android/bluetooth/btservice/JniCallbacks;");
477ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
478ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    method_stateChangeCallback = env->GetMethodID(jniCallbackClass, "stateChangeCallback", "(I)V");
479ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
480ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    method_adapterPropertyChangedCallback = env->GetMethodID(jniCallbackClass,
481ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                                             "adapterPropertyChangedCallback",
482ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                                             "([I[[B)V");
483ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    method_discoveryStateChangeCallback = env->GetMethodID(jniCallbackClass,
484ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                                           "discoveryStateChangeCallback", "(I)V");
485ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
486ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    method_devicePropertyChangedCallback = env->GetMethodID(jniCallbackClass,
487ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                                            "devicePropertyChangedCallback",
488ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                                            "([B[I[[B)V");
489ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    method_deviceFoundCallback = env->GetMethodID(jniCallbackClass, "deviceFoundCallback", "([B)V");
490ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    method_pinRequestCallback = env->GetMethodID(jniCallbackClass, "pinRequestCallback",
491ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                                 "([B[BI)V");
492ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    method_sspRequestCallback = env->GetMethodID(jniCallbackClass, "sspRequestCallback",
493ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                                 "([B[BIII)V");
494ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
495ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    method_bondStateChangeCallback = env->GetMethodID(jniCallbackClass,
496ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                                     "bondStateChangeCallback", "(I[BI)V");
497ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
49801a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy    method_aclStateChangeCallback = env->GetMethodID(jniCallbackClass,
49901a8cf98f070a6996b2e8974edc229ac402f3f0cKausik Sinnaswamy                                                    "aclStateChangeCallback", "(I[BI)V");
500ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    char value[PROPERTY_VALUE_MAX];
501ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    property_get("bluetooth.mock_stack", value, "");
502ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
503ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    const char *id = (strcmp(value, "1")? BT_STACK_MODULE_ID : BT_STACK_TEST_MODULE_ID);
504ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
505ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    err = hw_get_module(id, (hw_module_t const**)&module);
506ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
507ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (err == 0) {
508ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        hw_device_t* abstraction;
509ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        err = module->methods->open(module, id, &abstraction);
510ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        if (err == 0) {
511ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh            bluetooth_module_t* btStack = (bluetooth_module_t *)abstraction;
512ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh            sBluetoothInterface = btStack->get_bluetooth_interface();
513ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        } else {
514c55a9837c004044051b71bb47182ace156691283Matthew Xie           ALOGE("Error while opening Bluetooth library");
515ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        }
516ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    } else {
517c55a9837c004044051b71bb47182ace156691283Matthew Xie        ALOGE("No Bluetooth Library found");
518ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
519ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
520ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
521ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic bool initNative(JNIEnv* env, jobject obj) {
522c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s:",__FUNCTION__);
523ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
524ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    sJniCallbacksObj = env->NewGlobalRef(env->GetObjectField(obj, sJniCallbacksField));
525ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
526ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (sBluetoothInterface) {
527ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        int ret = sBluetoothInterface->init(&sBluetoothCallbacks);
528ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        if (ret != BT_STATUS_SUCCESS) {
529c55a9837c004044051b71bb47182ace156691283Matthew Xie            ALOGE("Error while setting the callbacks \n");
530ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh            sBluetoothInterface = NULL;
531ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh            return JNI_FALSE;
532ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        }
533cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie        if ( (sBluetoothSocketInterface = (btsock_interface_t *)
534cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie                  sBluetoothInterface->get_profile_interface(BT_PROFILE_SOCKETS_ID)) == NULL) {
535c55a9837c004044051b71bb47182ace156691283Matthew Xie                ALOGE("Error getting socket interface");
536cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie        }
537ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        return JNI_TRUE;
538ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
539ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return JNI_FALSE;
540ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
541ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
542ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic bool cleanupNative(JNIEnv *env, jobject obj) {
543c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s:",__FUNCTION__);
544ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
545ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jboolean result = JNI_FALSE;
546ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!sBluetoothInterface) return result;
547ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
548ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    sBluetoothInterface->cleanup();
549e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie    ALOGI("%s: return from cleanup",__FUNCTION__);
5506654f5c903de510a70f9e72cd5ad7837b615d93ffredc
551ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    env->DeleteGlobalRef(sJniCallbacksObj);
552ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return JNI_TRUE;
553ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
554ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
555ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean enableNative(JNIEnv* env, jobject obj) {
556c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s:",__FUNCTION__);
557ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
558ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jboolean result = JNI_FALSE;
559ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!sBluetoothInterface) return result;
560ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
561ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    int ret = sBluetoothInterface->enable();
562ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE;
563ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return result;
564ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
565ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
566ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean disableNative(JNIEnv* env, jobject obj) {
567c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s:",__FUNCTION__);
568ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
569ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jboolean result = JNI_FALSE;
570ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!sBluetoothInterface) return result;
571ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
572ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    int ret = sBluetoothInterface->disable();
573ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE;
574ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return result;
575ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
576ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
577ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean startDiscoveryNative(JNIEnv* env, jobject obj) {
578c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s:",__FUNCTION__);
579ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
580ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jboolean result = JNI_FALSE;
581ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!sBluetoothInterface) return result;
582ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
583ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    int ret = sBluetoothInterface->start_discovery();
584ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE;
585ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return result;
586ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
587ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
588ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean cancelDiscoveryNative(JNIEnv* env, jobject obj) {
589c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s:",__FUNCTION__);
590ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
591ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jboolean result = JNI_FALSE;
592ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!sBluetoothInterface) return result;
593ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
594ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    int ret = sBluetoothInterface->cancel_discovery();
595ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE;
596ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return result;
597ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
598ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
599ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean createBondNative(JNIEnv* env, jobject obj, jbyteArray address) {
600c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s:",__FUNCTION__);
601ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
602ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jbyte *addr;
603ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jboolean result = JNI_FALSE;
604ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
605ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!sBluetoothInterface) return result;
606ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
607ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    addr = env->GetByteArrayElements(address, NULL);
608ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (addr == NULL) {
609ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        jniThrowIOException(env, EINVAL);
610ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        return result;
611ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
612ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
613ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    int ret = sBluetoothInterface->create_bond((bt_bdaddr_t *)addr);
614b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    env->ReleaseByteArrayElements(address, addr, 0);
615ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE;
616ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
617ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return result;
618ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
619ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
620ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean removeBondNative(JNIEnv* env, jobject obj, jbyteArray address) {
621c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s:",__FUNCTION__);
622ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
623ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jbyte *addr;
624ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jboolean result;
625ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!sBluetoothInterface) return JNI_FALSE;
626ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
627ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    addr = env->GetByteArrayElements(address, NULL);
628ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (addr == NULL) {
629ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        jniThrowIOException(env, EINVAL);
630ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        return JNI_FALSE;
631ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
632ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
633ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    int ret = sBluetoothInterface->remove_bond((bt_bdaddr_t *)addr);
634b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    env->ReleaseByteArrayElements(address, addr, 0);
635ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE;
636ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
637ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return result;
638ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
639ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
640ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean cancelBondNative(JNIEnv* env, jobject obj, jbyteArray address) {
641c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s:",__FUNCTION__);
642ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
643ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jbyte *addr;
644ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jboolean result;
645ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!sBluetoothInterface) return JNI_FALSE;
646ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
647ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    addr = env->GetByteArrayElements(address, NULL);
648ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (addr == NULL) {
649ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        jniThrowIOException(env, EINVAL);
650ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        return JNI_FALSE;
651ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
652ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
653ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    int ret = sBluetoothInterface->cancel_bond((bt_bdaddr_t *)addr);
654b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    env->ReleaseByteArrayElements(address, addr, 0);
655ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE;
656ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
657ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return result;
658ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
659ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
660ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean pinReplyNative(JNIEnv *env, jobject obj, jbyteArray address, jboolean accept,
661ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                               jint len, jbyteArray pinArray) {
662c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s:",__FUNCTION__);
663ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
664ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jbyte *addr, *pinPtr = NULL;
665ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jboolean result = JNI_FALSE;
666ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!sBluetoothInterface) return result;
667ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
668ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    addr = env->GetByteArrayElements(address, NULL);
669ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (addr == NULL) {
670ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        jniThrowIOException(env, EINVAL);
671ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        return result;
672ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
673ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
674ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (accept) {
675ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        pinPtr = env->GetByteArrayElements(pinArray, NULL);
676ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        if (pinPtr == NULL) {
677ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh           jniThrowIOException(env, EINVAL);
678b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom           env->ReleaseByteArrayElements(address, addr, 0);
679ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh           return result;
680ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        }
681ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
682ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
683ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    int ret = sBluetoothInterface->pin_reply((bt_bdaddr_t*)addr, accept, len,
684ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                              (bt_pin_code_t *) pinPtr);
685b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    env->ReleaseByteArrayElements(address, addr, 0);
686b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    env->ReleaseByteArrayElements(pinArray, pinPtr, 0);
687ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE;
688ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
689ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return result;
690ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
691ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
692ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean sspReplyNative(JNIEnv *env, jobject obj, jbyteArray address,
693581bb31a8165ff0f9c7d638cfe4a81aaaafa2dedJaikumar Ganesh                               jint type, jboolean accept, jint passkey) {
694c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s:",__FUNCTION__);
695ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
696ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jbyte *addr;
697ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jboolean result = JNI_FALSE;
698ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!sBluetoothInterface) return result;
699ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
700ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    addr = env->GetByteArrayElements(address, NULL);
701ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (addr == NULL) {
702ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        jniThrowIOException(env, EINVAL);
703ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        return result;
704ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
705ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
706581bb31a8165ff0f9c7d638cfe4a81aaaafa2dedJaikumar Ganesh    int ret = sBluetoothInterface->ssp_reply((bt_bdaddr_t *)addr,
707581bb31a8165ff0f9c7d638cfe4a81aaaafa2dedJaikumar Ganesh         (bt_ssp_variant_t) type, accept, passkey);
708b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    env->ReleaseByteArrayElements(address, addr, 0);
709ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE;
710ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
711ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return result;
712ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
713ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
714ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean setAdapterPropertyNative(JNIEnv *env, jobject obj, jint type, jbyteArray value) {
715c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s:",__FUNCTION__);
716ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
717ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jbyte *val;
718ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jboolean result = JNI_FALSE;
719ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!sBluetoothInterface) return result;
720ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
721ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    val = env->GetByteArrayElements(value, NULL);
722ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    bt_property_t prop;
723ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    prop.type = (bt_property_type_t) type;
724ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    prop.len = env->GetArrayLength(value);
725ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    prop.val = val;
726ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
727ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    int ret = sBluetoothInterface->set_adapter_property(&prop);
728b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    env->ReleaseByteArrayElements(value, val, 0);
729ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE;
730ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
731ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return result;
732ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
733ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
734ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean getAdapterPropertiesNative(JNIEnv *env, jobject obj) {
735c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s:",__FUNCTION__);
736ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
737ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jboolean result = JNI_FALSE;
738ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!sBluetoothInterface) return result;
739ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
740ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    int ret = sBluetoothInterface->get_adapter_properties();
741ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE;
742ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
743ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return result;
744ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
745ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
746ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean getAdapterPropertyNative(JNIEnv *env, jobject obj, jint type) {
747c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s:",__FUNCTION__);
748ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
749ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jboolean result = JNI_FALSE;
750ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!sBluetoothInterface) return result;
751ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
752ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    int ret = sBluetoothInterface->get_adapter_property((bt_property_type_t) type);
753ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE;
754ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
755ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return result;
756ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
757ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
758ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean getDevicePropertyNative(JNIEnv *env, jobject obj, jbyteArray address, jint type) {
759c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s:",__FUNCTION__);
760ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
761ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jbyte *addr = NULL;
762ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jboolean result = JNI_FALSE;
763ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!sBluetoothInterface) return result;
764ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
765ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    addr = env->GetByteArrayElements(address, NULL);
766ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (addr == NULL) {
767ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        jniThrowIOException(env, EINVAL);
768ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        return result;
769ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
770ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
771ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    int ret = sBluetoothInterface->get_remote_device_property((bt_bdaddr_t *)addr,
772ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                                              (bt_property_type_t) type);
773b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    env->ReleaseByteArrayElements(address, addr, 0);
774ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE;
775ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
776ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return result;
777ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
778ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
779ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic jboolean setDevicePropertyNative(JNIEnv *env, jobject obj, jbyteArray address,
780ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                        jint type, jbyteArray value) {
781c55a9837c004044051b71bb47182ace156691283Matthew Xie    ALOGV("%s:",__FUNCTION__);
782ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
783ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jbyte *val, *addr;
784ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    jboolean result = JNI_FALSE;
785ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (!sBluetoothInterface) return result;
786ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
787ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    val = env->GetByteArrayElements(value, NULL);
788ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (val == NULL) {
789ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        jniThrowIOException(env, EINVAL);
790ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        return result;
791ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
792ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
793ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    addr = env->GetByteArrayElements(address, NULL);
794ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    if (addr == NULL) {
795b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        env->ReleaseByteArrayElements(value, val, 0);
796ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        jniThrowIOException(env, EINVAL);
797ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh        return result;
798ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    }
799ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
800ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
801ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    bt_property_t prop;
802ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    prop.type = (bt_property_type_t) type;
803ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    prop.len = env->GetArrayLength(value);
804ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    prop.val = val;
805ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
806ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    int ret = sBluetoothInterface->set_remote_device_property((bt_bdaddr_t *)addr, &prop);
807b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    env->ReleaseByteArrayElements(value, val, 0);
808b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    env->ReleaseByteArrayElements(address, addr, 0);
809ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
810ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE;
811ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
812ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return result;
813ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
814ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
815c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredcstatic jboolean getRemoteServicesNative(JNIEnv *env, jobject obj, jbyteArray address) {
816e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie    ALOGV("%s:",__FUNCTION__);
817c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc
818c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc    jbyte *addr = NULL;
819c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc    jboolean result = JNI_FALSE;
820c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc    if (!sBluetoothInterface) return result;
821c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc
822c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc    addr = env->GetByteArrayElements(address, NULL);
823c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc    if (addr == NULL) {
824c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc        jniThrowIOException(env, EINVAL);
825c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc        return result;
826c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc    }
827c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc
828c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc    int ret = sBluetoothInterface->get_remote_services((bt_bdaddr_t *)addr);
829b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    env->ReleaseByteArrayElements(address, addr, 0);
830c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc    result = (ret == BT_STATUS_SUCCESS) ? JNI_TRUE : JNI_FALSE;
831c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc    return result;
832c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc}
833c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc
834cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xiestatic int connectSocketNative(JNIEnv *env, jobject object, jbyteArray address, jint type,
835cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie                                   jbyteArray uuidObj, jint channel, jint flag) {
836cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    jbyte *addr = NULL, *uuid = NULL;
837cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    int socket_fd;
838cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    bt_status_t status;
839cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie
840b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    if (!sBluetoothSocketInterface) return -1;
841cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie
842cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    addr = env->GetByteArrayElements(address, NULL);
843cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    if (!addr) {
844c55a9837c004044051b71bb47182ace156691283Matthew Xie        ALOGE("failed to get Bluetooth device address");
845cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie        goto Fail;
846cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    }
847cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie
848cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    uuid = env->GetByteArrayElements(uuidObj, NULL);
849cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    if (!uuid) {
850c55a9837c004044051b71bb47182ace156691283Matthew Xie        ALOGE("failed to get uuid");
851cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie        goto Fail;
852cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    }
853cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie
854cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    if ( (status = sBluetoothSocketInterface->connect((bt_bdaddr_t *) addr, (btsock_type_t) type,
855cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie                       (const uint8_t*) uuid, channel, &socket_fd, flag)) != BT_STATUS_SUCCESS) {
856c55a9837c004044051b71bb47182ace156691283Matthew Xie        ALOGE("Socket connection failed: %d", status);
857cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie        goto Fail;
858cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    }
859cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie
860cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie
861cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    if (socket_fd < 0) {
862c55a9837c004044051b71bb47182ace156691283Matthew Xie        ALOGE("Fail to creat file descriptor on socket fd");
863cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie        goto Fail;
864cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    }
865cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    env->ReleaseByteArrayElements(address, addr, 0);
866cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    env->ReleaseByteArrayElements(uuidObj, uuid, 0);
867cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    return socket_fd;
868cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie
869cc80b2261351dc74ad1bed237b0423c12d340514Matthew XieFail:
870cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    if (addr) env->ReleaseByteArrayElements(address, addr, 0);
871cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    if (uuid) env->ReleaseByteArrayElements(uuidObj, uuid, 0);
872cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie
873cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    return -1;
874cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie}
875cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie
876cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xiestatic int createSocketChannelNative(JNIEnv *env, jobject object, jint type,
877b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom                                     jstring name_str, jbyteArray uuidObj, jint channel, jint flag) {
878cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    const char *service_name;
879cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    jbyte *uuid = NULL;
880cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    int socket_fd;
881cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    bt_status_t status;
882cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie
883b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    if (!sBluetoothSocketInterface) return -1;
884cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie
885cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    service_name = env->GetStringUTFChars(name_str, NULL);
886cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie
887cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    uuid = env->GetByteArrayElements(uuidObj, NULL);
888cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    if (!uuid) {
889c55a9837c004044051b71bb47182ace156691283Matthew Xie        ALOGE("failed to get uuid");
890cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie        goto Fail;
891cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    }
892e469f16e5a7d99471d7db1b216d422e8d12cc4cfMatthew Xie    ALOGE("SOCK FLAG = %x ***********************",flag);
893cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    if ( (status = sBluetoothSocketInterface->listen((btsock_type_t) type, service_name,
894cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie                       (const uint8_t*) uuid, channel, &socket_fd, flag)) != BT_STATUS_SUCCESS) {
895c55a9837c004044051b71bb47182ace156691283Matthew Xie        ALOGE("Socket listen failed: %d", status);
896cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie        goto Fail;
897cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    }
898cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie
899cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    if (socket_fd < 0) {
900c55a9837c004044051b71bb47182ace156691283Matthew Xie        ALOGE("Fail to creat file descriptor on socket fd");
901cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie        goto Fail;
902cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    }
903cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    if (service_name) env->ReleaseStringUTFChars(name_str, service_name);
904cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    if (uuid) env->ReleaseByteArrayElements(uuidObj, uuid, 0);
905cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    return socket_fd;
906cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie
907cc80b2261351dc74ad1bed237b0423c12d340514Matthew XieFail:
908cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    if (service_name) env->ReleaseStringUTFChars(name_str, service_name);
909cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    if (uuid) env->ReleaseByteArrayElements(uuidObj, uuid, 0);
910cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie
911cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    return -1;
912cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie}
913cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie
914ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshstatic JNINativeMethod sMethods[] = {
915b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    /* name, signature, funcPtr */
916ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    {"classInitNative", "()V", (void *) classInitNative},
917ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    {"initNative", "()Z", (void *) initNative},
918ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    {"cleanupNative", "()V", (void*) cleanupNative},
919ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    {"enableNative", "()Z",  (void*) enableNative},
920ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    {"disableNative", "()Z",  (void*) disableNative},
921ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    {"setAdapterPropertyNative", "(I[B)Z", (void*) setAdapterPropertyNative},
922ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    {"getAdapterPropertiesNative", "()Z", (void*) getAdapterPropertiesNative},
923ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    {"getAdapterPropertyNative", "(I)Z", (void*) getAdapterPropertyNative},
924ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    {"getDevicePropertyNative", "([BI)Z", (void*) getDevicePropertyNative},
925ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    {"setDevicePropertyNative", "([BI[B)Z", (void*) setDevicePropertyNative},
926ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    {"startDiscoveryNative", "()Z", (void*) startDiscoveryNative},
927ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    {"cancelDiscoveryNative", "()Z", (void*) cancelDiscoveryNative},
928ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    {"createBondNative", "([B)Z", (void*) createBondNative},
929ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    {"removeBondNative", "([B)Z", (void*) removeBondNative},
930ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    {"cancelBondNative", "([B)Z", (void*) cancelBondNative},
931ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    {"pinReplyNative", "([BZI[B)Z", (void*) pinReplyNative},
932581bb31a8165ff0f9c7d638cfe4a81aaaafa2dedJaikumar Ganesh    {"sspReplyNative", "([BIZI)Z", (void*) sspReplyNative},
933c55ac7d42cf2d78c7edc67abf6c66813245b2c93fredc    {"getRemoteServicesNative", "([B)Z", (void*) getRemoteServicesNative},
934cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    {"connectSocketNative", "([BI[BII)I", (void*) connectSocketNative},
935cc80b2261351dc74ad1bed237b0423c12d340514Matthew Xie    {"createSocketChannelNative", "(ILjava/lang/String;[BII)I",
93603b8386de26ba6500af2d66687bff9b01f2cbbd7Ganesh Ganapathi Batta     (void*) createSocketChannelNative}
937ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh};
938ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
939ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshint register_com_android_bluetooth_btservice_AdapterService(JNIEnv* env)
940ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh{
941ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh    return jniRegisterNativeMethods(env, "com/android/bluetooth/btservice/AdapterService",
942ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh                                    sMethods, NELEM(sMethods));
943ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
944ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
945ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh} /* namespace android */
946ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
947ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh
948ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh/*
949ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh * JNI Initialization
950ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh */
951ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganeshjint JNI_OnLoad(JavaVM *jvm, void *reserved)
952ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh{
953b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    JNIEnv *e;
954b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    int status;
955b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom
956b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    ALOGV("Bluetooth Adapter Service : loading JNI\n");
957b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom
958b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    // Check JNI version
959b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    if (jvm->GetEnv((void **)&e, JNI_VERSION_1_6)) {
960b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        ALOGE("JNI version mismatch error");
961b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        return JNI_ERR;
962b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    }
963b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom
964b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    if ((status = android::register_com_android_bluetooth_btservice_AdapterService(e)) < 0) {
965b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        ALOGE("jni adapter service registration failure, status: %d", status);
966b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        return JNI_ERR;
967b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    }
968b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom
969b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    if ((status = android::register_com_android_bluetooth_hfp(e)) < 0) {
970b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        ALOGE("jni hfp registration failure, status: %d", status);
971b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        return JNI_ERR;
972b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    }
973b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom
974b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    if ((status = android::register_com_android_bluetooth_a2dp(e)) < 0) {
975b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        ALOGE("jni a2dp registration failure: %d", status);
976b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        return JNI_ERR;
977b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    }
978b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom
979b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    if ((status = android::register_com_android_bluetooth_hid(e)) < 0) {
980b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        ALOGE("jni hid registration failure: %d", status);
981b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        return JNI_ERR;
982b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    }
983b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom
984b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    if ((status = android::register_com_android_bluetooth_hdp(e)) < 0) {
985b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        ALOGE("jni hdp registration failure: %d", status);
986b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        return JNI_ERR;
987b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    }
988b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom
989b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    if ((status = android::register_com_android_bluetooth_pan(e)) < 0) {
990b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        ALOGE("jni pan registration failure: %d", status);
991b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        return JNI_ERR;
992b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    }
993b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom
994b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    if ((status = android::register_com_android_bluetooth_gatt(e)) < 0) {
995b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        ALOGE("jni gatt registration failure: %d", status);
996b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom        return JNI_ERR;
997b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    }
998b241cda1eec2fbefd6d21e0819532f7a76947635Brian Carlstrom    return JNI_VERSION_1_6;
999ff4f17bf64978d0738c66e1b6dd70be8664efc24Jaikumar Ganesh}
1000