Android 12(S) ALooper AHandler AMessage(二)
来写个demo试试看到底是ALooper AHandler AMessage是怎么运行的,源文件以及Android.bp如下:
// EvenHandler.h #ifndef __MESSAGE_TEST_H__ #define __MESSAGE_TEST_H__ #include <media/stagefright/foundation/AMessage.h> #include <media/stagefright/foundation/AHandler.h> #include <media/stagefright/foundation/ALooper.h> #include <media/stagefright/foundation/ADebug.h> namespace android{ class EventHandler : public AHandler { public: EventHandler(); enum { kWhatSetDataSource, kWhatPrepare, kWhatStart, kWhatStop }; void setDataSource(const char* url); void prepare(); void start(); void stop(); protected: virtual void onMessageReceived(const sp<AMessage> &msg); private: void onSetDataSource(const char* url); void onPrepare(); void onStart(); void onStop(); }; } #endif
// EventHandler.cpp #define LOG_TAG "MyEventHandler" #include "EventHandler.h" #include <string.h> namespace android{ EventHandler::EventHandler() { ALOGD("tid = %d, func = %s", gettid(), __func__); } void EventHandler::onMessageReceived(const sp<AMessage> &msg) { ALOGD("(%d)oMessageReceived: %s", gettid() ,msg->debugString().c_str()); switch(msg->what()){ case kWhatSetDataSource: { AString url; CHECK(msg->findString("url", &url)); onSetDataSource(url.c_str()); break; } case kWhatPrepare: { sp<AReplyToken> replyID; CHECK(msg->senderAwaitsResponse(&replyID)); onPrepare(); sp<AMessage> response = new AMessage; response->setInt32("err", 0); response->postReply(replyID); break; } case kWhatStart: { onStart(); break; } case kWhatStop: { onStop(); break; } default: break; } } void EventHandler::setDataSource(const char* url) { ALOGD("tid = %d, func = %s", gettid(), __func__); sp<AMessage> msg = new AMessage(kWhatSetDataSource, this); msg->setString("url", url, strlen(url)); msg->post(); } void EventHandler::prepare() { ALOGD("tid = %d, func = %s", gettid(), __func__); sp<AMessage> msg = new AMessage(kWhatPrepare, this); sp<AMessage> response; msg->postAndAwaitResponse(&response); int err; CHECK(response->findInt32("err", &err)); ALOGD("tid = %d, func = %s, err = %d", gettid(), __func__, err); } void EventHandler::start() { ALOGD("tid = %d, func = %s", gettid(), __func__); sp<AMessage> msg = new AMessage(kWhatStart, this); msg->post(); } void EventHandler::stop() { ALOGD("tid = %d, func = %s", gettid(), __func__); sp<AMessage> msg = new AMessage(kWhatStop, this); msg->post(); } void EventHandler::onSetDataSource(const char *url) { ALOGD("tid = %d, func = %s, url = %s", gettid(), __func__, url); } void EventHandler::onPrepare() { ALOGD("tid = %d, func = %s", gettid(), __func__); int cnt = 0; while(cnt < 3) { ALOGD("tid = %d, func = %s, cnt = %d", gettid(), __func__, cnt); sleep(1); cnt++; } } void EventHandler::onStart() { ALOGD("tid = %d, func = %s", gettid(), __func__); int cnt = 0; while(cnt < 10) { ALOGD("tid = %d, func = %s, cnt = %d", gettid(), __func__, cnt); sleep(1); cnt++; } } void EventHandler::onStop() { ALOGD("tid = %d, func = %s", gettid(), __func__); } }
// main.cpp #define LOG_TAG "MyEventHandlerTest" #include "EventHandler.h" using namespace android; int main(int argc, char **argv) { ALOGD("tid = %d, func = %s", gettid(), __func__); sp<EventHandler> handler = new EventHandler; sp<ALooper> looper = new ALooper; looper->setName("MyLooper"); looper->start(); looper->registerHandler(handler); handler->setDataSource("ABC"); handler->prepare(); handler->start(); handler->stop(); int wait = 0; while(wait < 20) { ALOGD("wait = %d", wait); sleep(1); wait++; } }
// Android.bp cc_binary { name: "EventHandlerTest", srcs: [ "EventHandler.cpp", "main.cpp" ], shared_libs: [ "libstagefright_foundation", "libutils", "liblog" ], include_dirs: [ "frameworks/av/media/libstagefright/foundation/include" ], cflags: [ "-Wno-unused-parameter" ] }
来看执行结果吧,试验了两种情况:
1、先说失败的,将looper->start(true),这个时候好像直接卡住不动了,
2、直接调用looper->start(),这里的参数默认为false,也就是会在一个新的线程当中做消息处理。从log中来看onMessageReceived方法都是在子线程中完成,在非阻塞的情况下是和主线程并行执行的。
这边还有个现象,main函数最后没有加while循环等待时,子线程执行完onStart方法进程就结束了,并没有等待处理完stop消息
03-25 17:08:23.437 16962 16962 D MyEventHandlerTest: tid = 16962, func = main 03-25 17:08:23.437 16962 16962 D MyEventHandler: tid = 16962, func = EventHandler 03-25 17:08:23.437 16962 16962 D MyEventHandler: tid = 16962, func = setDataSource 03-25 17:08:23.438 16962 16962 D MyEventHandler: tid = 16962, func = prepare 03-25 17:08:23.438 16962 16963 D MyEventHandler: (16963)oMessageReceived: AMessage(what = 0x00000000, target = 1) = { 03-25 17:08:23.438 16962 16963 D MyEventHandler: string url = "ABC" 03-25 17:08:23.438 16962 16963 D MyEventHandler: } 03-25 17:08:23.438 16962 16963 D MyEventHandler: tid = 16963, func = onSetDataSource, url = ABC 03-25 17:08:23.438 16962 16963 D MyEventHandler: (16963)oMessageReceived: AMessage(what = 0x00000001, target = 1) = { 03-25 17:08:23.438 16962 16963 D MyEventHandler: RefBase *replyID = 0xf5b01180 03-25 17:08:23.438 16962 16963 D MyEventHandler: } 03-25 17:08:23.438 16962 16963 D MyEventHandler: tid = 16963, func = onPrepare 03-25 17:08:23.438 16962 16963 D MyEventHandler: tid = 16963, func = onPrepare, cnt = 0 03-25 17:08:24.438 16962 16963 D MyEventHandler: tid = 16963, func = onPrepare, cnt = 1 03-25 17:08:25.438 16962 16963 D MyEventHandler: tid = 16963, func = onPrepare, cnt = 2 03-25 17:08:26.438 16962 16962 D MyEventHandler: tid = 16962, func = prepare, err = 0 03-25 17:08:26.439 16962 16962 D MyEventHandler: tid = 16962, func = start 03-25 17:08:26.439 16962 16962 D MyEventHandler: tid = 16962, func = stop 03-25 17:08:26.439 16962 16962 D MyEventHandlerTest: wait = 0 03-25 17:08:26.439 16962 16963 D MyEventHandler: (16963)oMessageReceived: AMessage(what = 0x00000002, target = 1) = { 03-25 17:08:26.439 16962 16963 D MyEventHandler: } 03-25 17:08:26.439 16962 16963 D MyEventHandler: tid = 16963, func = onStart 03-25 17:08:26.439 16962 16963 D MyEventHandler: tid = 16963, func = onStart, cnt = 0 03-25 17:08:27.439 16962 16962 D MyEventHandlerTest: wait = 1 03-25 17:08:27.439 16962 16963 D MyEventHandler: tid = 16963, func = onStart, cnt = 1 03-25 17:08:28.439 16962 16962 D MyEventHandlerTest: wait = 2 03-25 17:08:28.439 16962 16963 D MyEventHandler: tid = 16963, func = onStart, cnt = 2 03-25 17:08:29.439 16962 16963 D MyEventHandler: tid = 16963, func = onStart, cnt = 3 03-25 17:08:29.439 16962 16962 D MyEventHandlerTest: wait = 3 03-25 17:08:30.439 16962 16963 D MyEventHandler: tid = 16963, func = onStart, cnt = 4 03-25 17:08:30.439 16962 16962 D MyEventHandlerTest: wait = 4 03-25 17:08:31.439 16962 16963 D MyEventHandler: tid = 16963, func = onStart, cnt = 5 03-25 17:08:31.440 16962 16962 D MyEventHandlerTest: wait = 5 03-25 17:08:32.439 16962 16963 D MyEventHandler: tid = 16963, func = onStart, cnt = 6 03-25 17:08:32.440 16962 16962 D MyEventHandlerTest: wait = 6 03-25 17:08:33.440 16962 16963 D MyEventHandler: tid = 16963, func = onStart, cnt = 7 03-25 17:08:33.440 16962 16962 D MyEventHandlerTest: wait = 7 03-25 17:08:34.440 16962 16963 D MyEventHandler: tid = 16963, func = onStart, cnt = 8 03-25 17:08:34.440 16962 16962 D MyEventHandlerTest: wait = 8 03-25 17:08:35.440 16962 16963 D MyEventHandler: tid = 16963, func = onStart, cnt = 9 03-25 17:08:35.440 16962 16962 D MyEventHandlerTest: wait = 9 03-25 17:08:36.440 16962 16963 D MyEventHandler: (16963)oMessageReceived: AMessage(what = 0x00000003, target = 1) = { 03-25 17:08:36.440 16962 16963 D MyEventHandler: } 03-25 17:08:36.440 16962 16963 D MyEventHandler: tid = 16963, func = onStop 03-25 17:08:36.441 16962 16962 D MyEventHandlerTest: wait = 10 03-25 17:08:37.441 16962 16962 D MyEventHandlerTest: wait = 11 03-25 17:08:38.441 16962 16962 D MyEventHandlerTest: wait = 12 03-25 17:08:39.441 16962 16962 D MyEventHandlerTest: wait = 13 03-25 17:08:40.441 16962 16962 D MyEventHandlerTest: wait = 14 03-25 17:08:41.441 16962 16962 D MyEventHandlerTest: wait = 15 03-25 17:08:42.441 16962 16962 D MyEventHandlerTest: wait = 16 03-25 17:08:43.442 16962 16962 D MyEventHandlerTest: wait = 17 03-25 17:08:44.442 16962 16962 D MyEventHandlerTest: wait = 18 03-25 17:08:45.442 16962 16962 D MyEventHandlerTest: wait = 19