Merge "Update for namespaced services in hwservicemanager."
This commit is contained in:
@@ -16,6 +16,7 @@
|
|||||||
|
|
||||||
package android.os;
|
package android.os;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
import libcore.util.NativeAllocationRegistry;
|
import libcore.util.NativeAllocationRegistry;
|
||||||
|
|
||||||
/** @hide */
|
/** @hide */
|
||||||
@@ -39,10 +40,12 @@ public abstract class HwBinder implements IHwBinder {
|
|||||||
int code, HwParcel request, HwParcel reply, int flags);
|
int code, HwParcel request, HwParcel reply, int flags);
|
||||||
|
|
||||||
public native final void registerService(
|
public native final void registerService(
|
||||||
String serviceName, int versionMajor, int versionMinor);
|
ArrayList<String> interfaceChain,
|
||||||
|
String serviceName);
|
||||||
|
|
||||||
public static native final IHwBinder getService(
|
public static native final IHwBinder getService(
|
||||||
String serviceName, int versionMajor, int versionMinor);
|
String iface,
|
||||||
|
String serviceName);
|
||||||
|
|
||||||
// Returns address of the "freeFunction".
|
// Returns address of the "freeFunction".
|
||||||
private static native final long native_init();
|
private static native final long native_init();
|
||||||
|
|||||||
@@ -34,6 +34,8 @@
|
|||||||
#include "core_jni_helpers.h"
|
#include "core_jni_helpers.h"
|
||||||
|
|
||||||
using android::AndroidRuntime;
|
using android::AndroidRuntime;
|
||||||
|
using android::hardware::hidl_vec;
|
||||||
|
using android::hardware::hidl_string;
|
||||||
|
|
||||||
#define PACKAGE_PATH "android/os"
|
#define PACKAGE_PATH "android/os"
|
||||||
#define CLASS_NAME "HwBinder"
|
#define CLASS_NAME "HwBinder"
|
||||||
@@ -41,10 +43,15 @@ using android::AndroidRuntime;
|
|||||||
|
|
||||||
namespace android {
|
namespace android {
|
||||||
|
|
||||||
|
static jclass gArrayListClass;
|
||||||
|
static struct {
|
||||||
|
jmethodID size;
|
||||||
|
jmethodID get;
|
||||||
|
} gArrayListMethods;
|
||||||
|
|
||||||
static struct fields_t {
|
static struct fields_t {
|
||||||
jfieldID contextID;
|
jfieldID contextID;
|
||||||
jmethodID onTransactID;
|
jmethodID onTransactID;
|
||||||
|
|
||||||
} gFields;
|
} gFields;
|
||||||
|
|
||||||
// static
|
// static
|
||||||
@@ -199,45 +206,46 @@ static void JHwBinder_native_transact(
|
|||||||
static void JHwBinder_native_registerService(
|
static void JHwBinder_native_registerService(
|
||||||
JNIEnv *env,
|
JNIEnv *env,
|
||||||
jobject thiz,
|
jobject thiz,
|
||||||
jstring serviceNameObj,
|
jobject interfaceChainArrayList,
|
||||||
jint versionMajor,
|
jstring serviceNameObj) {
|
||||||
jint versionMinor) {
|
|
||||||
if (serviceNameObj == NULL) {
|
if (serviceNameObj == NULL) {
|
||||||
jniThrowException(env, "java/lang/NullPointerException", NULL);
|
jniThrowException(env, "java/lang/NullPointerException", NULL);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (versionMajor < 0
|
const char *serviceName = env->GetStringUTFChars(serviceNameObj, NULL);
|
||||||
|| versionMajor > 65535
|
|
||||||
|| versionMinor < 0
|
|
||||||
|| versionMinor > 65535) {
|
|
||||||
jniThrowException(env, "java/lang/IllegalArgumentException", NULL);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
const jchar *serviceName = env->GetStringCritical(serviceNameObj, NULL);
|
|
||||||
|
|
||||||
if (serviceName == NULL) {
|
if (serviceName == NULL) {
|
||||||
return; // XXX exception already pending?
|
return; // XXX exception already pending?
|
||||||
}
|
}
|
||||||
|
|
||||||
using android::hidl::manager::V1_0::IServiceManager;
|
jint numInterfaces = env->CallIntMethod(interfaceChainArrayList,
|
||||||
|
gArrayListMethods.size);
|
||||||
|
hidl_string *strings = new hidl_string[numInterfaces];
|
||||||
|
|
||||||
const IServiceManager::Version kVersion {
|
for (jint i = 0; i < numInterfaces; i++) {
|
||||||
.major = static_cast<uint16_t>(versionMajor),
|
jstring strObj = static_cast<jstring>(
|
||||||
.minor = static_cast<uint16_t>(versionMinor),
|
env->CallObjectMethod(interfaceChainArrayList,
|
||||||
};
|
gArrayListMethods.get,
|
||||||
|
i)
|
||||||
|
);
|
||||||
|
const char * str = env->GetStringUTFChars(strObj, nullptr);
|
||||||
|
strings[i] = hidl_string(str);
|
||||||
|
env->ReleaseStringUTFChars(strObj, str);
|
||||||
|
}
|
||||||
|
|
||||||
|
hidl_vec<hidl_string> interfaceChain;
|
||||||
|
interfaceChain.setToExternal(strings, numInterfaces, true /* shouldOwn */);
|
||||||
|
|
||||||
|
using android::hidl::manager::V1_0::IServiceManager;
|
||||||
|
|
||||||
sp<hardware::IBinder> binder = JHwBinder::GetNativeContext(env, thiz);
|
sp<hardware::IBinder> binder = JHwBinder::GetNativeContext(env, thiz);
|
||||||
|
|
||||||
bool ok = hardware::defaultServiceManager()->add(
|
bool ok = hardware::defaultServiceManager()->add(
|
||||||
String8(String16(
|
interfaceChain,
|
||||||
reinterpret_cast<const char16_t *>(serviceName),
|
serviceName,
|
||||||
env->GetStringLength(serviceNameObj))).string(),
|
binder);
|
||||||
binder,
|
|
||||||
kVersion);
|
|
||||||
|
|
||||||
env->ReleaseStringCritical(serviceNameObj, serviceName);
|
env->ReleaseStringUTFChars(serviceNameObj, serviceName);
|
||||||
serviceName = NULL;
|
serviceName = NULL;
|
||||||
|
|
||||||
if (ok) {
|
if (ok) {
|
||||||
@@ -251,52 +259,43 @@ static void JHwBinder_native_registerService(
|
|||||||
static jobject JHwBinder_native_getService(
|
static jobject JHwBinder_native_getService(
|
||||||
JNIEnv *env,
|
JNIEnv *env,
|
||||||
jclass /* clazzObj */,
|
jclass /* clazzObj */,
|
||||||
jstring serviceNameObj,
|
jstring ifaceNameObj,
|
||||||
jint versionMajor,
|
jstring serviceNameObj) {
|
||||||
jint versionMinor) {
|
|
||||||
|
if (ifaceNameObj == NULL) {
|
||||||
|
jniThrowException(env, "java/lang/NullPointerException", NULL);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
if (serviceNameObj == NULL) {
|
if (serviceNameObj == NULL) {
|
||||||
jniThrowException(env, "java/lang/NullPointerException", NULL);
|
jniThrowException(env, "java/lang/NullPointerException", NULL);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (versionMajor < 0
|
const char *ifaceName = env->GetStringUTFChars(ifaceNameObj, NULL);
|
||||||
|| versionMajor > 65535
|
if (ifaceName == NULL) {
|
||||||
|| versionMinor < 0
|
return NULL; // XXX exception already pending?
|
||||||
|| versionMinor > 65535) {
|
|
||||||
jniThrowException(env, "java/lang/IllegalArgumentException", NULL);
|
|
||||||
return NULL;
|
|
||||||
}
|
}
|
||||||
|
const char *serviceName = env->GetStringUTFChars(serviceNameObj, NULL);
|
||||||
const jchar *serviceName = env->GetStringCritical(serviceNameObj, NULL);
|
|
||||||
|
|
||||||
if (serviceName == NULL) {
|
if (serviceName == NULL) {
|
||||||
|
env->ReleaseStringUTFChars(ifaceNameObj, ifaceName);
|
||||||
return NULL; // XXX exception already pending?
|
return NULL; // XXX exception already pending?
|
||||||
}
|
}
|
||||||
|
|
||||||
using android::hidl::manager::V1_0::IServiceManager;
|
|
||||||
|
|
||||||
const IServiceManager::Version kVersion {
|
|
||||||
.major = static_cast<uint16_t>(versionMajor),
|
|
||||||
.minor = static_cast<uint16_t>(versionMinor),
|
|
||||||
};
|
|
||||||
|
|
||||||
LOG(INFO) << "looking for service '"
|
LOG(INFO) << "looking for service '"
|
||||||
<< String8(String16(
|
<< serviceName
|
||||||
reinterpret_cast<const char16_t *>(serviceName),
|
|
||||||
env->GetStringLength(serviceNameObj))).string()
|
|
||||||
<< "'";
|
<< "'";
|
||||||
|
|
||||||
sp<hardware::IBinder> service;
|
sp<hardware::IBinder> service;
|
||||||
hardware::defaultServiceManager()->get(
|
hardware::defaultServiceManager()->get(
|
||||||
String8(String16(
|
ifaceName,
|
||||||
reinterpret_cast<const char16_t *>(serviceName),
|
serviceName,
|
||||||
env->GetStringLength(serviceNameObj))).string(),
|
|
||||||
kVersion,
|
|
||||||
[&service](sp<hardware::IBinder> out) {
|
[&service](sp<hardware::IBinder> out) {
|
||||||
service = out;
|
service = out;
|
||||||
});
|
});
|
||||||
|
|
||||||
env->ReleaseStringCritical(serviceNameObj, serviceName);
|
env->ReleaseStringUTFChars(ifaceNameObj, ifaceName);
|
||||||
|
ifaceName = NULL;
|
||||||
|
env->ReleaseStringUTFChars(serviceNameObj, serviceName);
|
||||||
serviceName = NULL;
|
serviceName = NULL;
|
||||||
|
|
||||||
if (service == NULL) {
|
if (service == NULL) {
|
||||||
@@ -318,16 +317,21 @@ static JNINativeMethod gMethods[] = {
|
|||||||
"(IL" PACKAGE_PATH "/HwParcel;L" PACKAGE_PATH "/HwParcel;I)V",
|
"(IL" PACKAGE_PATH "/HwParcel;L" PACKAGE_PATH "/HwParcel;I)V",
|
||||||
(void *)JHwBinder_native_transact },
|
(void *)JHwBinder_native_transact },
|
||||||
|
|
||||||
{ "registerService", "(Ljava/lang/String;II)V",
|
{ "registerService", "(Ljava/util/ArrayList;Ljava/lang/String;)V",
|
||||||
(void *)JHwBinder_native_registerService },
|
(void *)JHwBinder_native_registerService },
|
||||||
|
|
||||||
{ "getService", "(Ljava/lang/String;II)L" PACKAGE_PATH "/IHwBinder;",
|
{ "getService", "(Ljava/lang/String;Ljava/lang/String;)L" PACKAGE_PATH "/IHwBinder;",
|
||||||
(void *)JHwBinder_native_getService },
|
(void *)JHwBinder_native_getService },
|
||||||
};
|
};
|
||||||
|
|
||||||
namespace android {
|
namespace android {
|
||||||
|
|
||||||
int register_android_os_HwBinder(JNIEnv *env) {
|
int register_android_os_HwBinder(JNIEnv *env) {
|
||||||
|
jclass arrayListClass = FindClassOrDie(env, "java/util/ArrayList");
|
||||||
|
gArrayListClass = MakeGlobalRefOrDie(env, arrayListClass);
|
||||||
|
gArrayListMethods.size = GetMethodIDOrDie(env, arrayListClass, "size", "()I");
|
||||||
|
gArrayListMethods.get = GetMethodIDOrDie(env, arrayListClass, "get", "(I)Ljava/lang/Object;");
|
||||||
|
|
||||||
return RegisterMethodsOrDie(env, CLASS_PATH, gMethods, NELEM(gMethods));
|
return RegisterMethodsOrDie(env, CLASS_PATH, gMethods, NELEM(gMethods));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user