Cum*_*tru 15 c++ java-native-interface android android-ndk android-binder
我只能找到有关Parcelable的Java示例.我的目标是在本机C++(而不是NDK)中创建一个简单的服务和客户端,它将使用Binder来接收和发送序列化的自定义对象.
MyClass
+ std::string
+ enum
+ int
+ bool
Run Code Online (Sandbox Code Playgroud)
由于您使用的是 Android 5.1,我将坚持使用 Lollipop 上提供的版本。有更好的工具(例如aidl-cpp)可以完成此任务,这可以省去大量手动滚动样板代码的麻烦。
首先,在IFooService.h.
class IFooService: public IInterface {
public:
DECLARE_META_INTERFACE(FooService);
virtual int myFunc(const String8& str, int enumParam, int intParam, int boolParam) = 0;
};
Run Code Online (Sandbox Code Playgroud)
然后编写服务的编组代码,根据问题中的要求实现功能
class BnFooService: public BnInterface<IFooService>
{
public:
virtual status_t onTransact( uint32_t code,
const Parcel& data,
Parcel* reply,
uint32_t flags = 0);
};
enum {
MY_FUNC = IBinder::FIRST_CALL_TRANSACTION,
};
/* BinderProxy code, for clients of the service to call into the service and have
the paremeters marshalled properly across the Binder interface. Executes in the
client process context
*/
class BpFooService: public BpInterface<IFooService> {
public:
virtual int myFunc(const String8& str, int enumParam, int intParam, int boolParam) {
//2 Parcel objects, 1 to write the data to and another to receive it in
Parcel data, reply;
//This serves as the token for the Binder framework for a sanity check
data.writeInterfaceToken(IFooService::getInterfaceDescriptor());
data.writeString8(str);
data.writeInt32(enumParam);
data.writeInt32(intParam);
data.writeInt32(boolParam);
return remote()->transact(MY_FUNC, data, &reply);
}
}
IMPLEMENT_META_INTERFACE(MediaPlayerService, "com.somedomain.IFooService");
/* Actual Binder implementation of the service which unpacks the data from the
incoming Parcel and handles the call accordingly
*/
status_t BnFooService::onTransact(uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags) {
switch (code) {
case MY_FUNC: {
//The same token is checked
CHECK_INTERFACE(IFooService, data, reply);
//Read off in exact same order as written to the data Parcel above
String8 str = data.readString8();
int enumParam = data.readInt32();
int intParam = data.readInt32();
int boolParam = data.readInt32();
reply->writeInt32(myFunc(str, enumParam, intParam, boolParam));
return NO_ERROR;
}
break;
default:
}
Run Code Online (Sandbox Code Playgroud)
main_foo.cpp然后使用如下代码创建,作为服务进程的入口点:
int main() {
if(!FooService::publish()) { //Call into your code to register with ServiceManager
ALOGE("Can't instantiate FooService! Exiting");
return 1;
}
ProcessState::self()->startThreadPool(); //Required for the binder threads
IPCThreadState::self()->joinThreadPool(); //Infinite loop that waits for inbound connections
}
Run Code Online (Sandbox Code Playgroud)
最后,实现服务的接口FooService.cpp
bool FooService::publish() {
defaultServiceManager()->addService(String16("foo_service"), new FooService());
sp<IBinder> binder = defaultServiceManager()->checkService(String16("foo_service"));
while(binder == NULL && /*some upper time limit*/){
ALOGI("Waiting for foo_service");
}
return binder != NULL;
}
int FooService::myFunc(const String8& str, int enumParam, int intParam, int boolParam) {
//business logic
return 0;
}
Run Code Online (Sandbox Code Playgroud)
请注意,这不是适用于常规应用程序开发人员的代码,而是适用于在 Android 框架中运行的本机服务InputFlinger(如 等) 。SurfaceFlinger此代码需要框架头文件(如等) Parcel.h,IInterface.h而这些文件在 SDK 中不可用。
| 归档时间: |
|
| 查看次数: |
660 次 |
| 最近记录: |