1 #include <dvr/vr_flinger.h>
2
3 #include <errno.h>
4 #include <fcntl.h>
5 #include <poll.h>
6 #include <signal.h>
7 #include <string.h>
8 #include <time.h>
9 #include <unistd.h>
10 #include <memory>
11
12 #include <binder/IServiceManager.h>
13 #include <binder/ProcessState.h>
14 #include <cutils/properties.h>
15 #include <cutils/sched_policy.h>
16 #include <log/log.h>
17 #include <private/dvr/display_client.h>
18 #include <sys/prctl.h>
19 #include <sys/resource.h>
20
21 #include <functional>
22
23 #include "DisplayHardware/ComposerHal.h"
24 #include "display_manager_service.h"
25 #include "display_service.h"
26 #include "vsync_service.h"
27
28 namespace android {
29 namespace dvr {
30
Create(Hwc2::Composer * hidl,RequestDisplayCallback request_display_callback)31 std::unique_ptr<VrFlinger> VrFlinger::Create(
32 Hwc2::Composer* hidl, RequestDisplayCallback request_display_callback) {
33 std::unique_ptr<VrFlinger> vr_flinger(new VrFlinger);
34 if (vr_flinger->Init(hidl, request_display_callback))
35 return vr_flinger;
36 else
37 return nullptr;
38 }
39
VrFlinger()40 VrFlinger::VrFlinger() {}
41
~VrFlinger()42 VrFlinger::~VrFlinger() {
43 if (persistent_vr_state_callback_.get()) {
44 sp<IVrManager> vr_manager = interface_cast<IVrManager>(
45 defaultServiceManager()->checkService(String16("vrmanager")));
46 if (vr_manager.get()) {
47 vr_manager->unregisterPersistentVrStateListener(
48 persistent_vr_state_callback_);
49 }
50 }
51
52 if (dispatcher_)
53 dispatcher_->SetCanceled(true);
54 if (dispatcher_thread_.joinable())
55 dispatcher_thread_.join();
56 }
57
Init(Hwc2::Composer * hidl,RequestDisplayCallback request_display_callback)58 bool VrFlinger::Init(Hwc2::Composer* hidl,
59 RequestDisplayCallback request_display_callback) {
60 if (!hidl || !request_display_callback)
61 return false;
62
63 std::shared_ptr<android::pdx::Service> service;
64
65 ALOGI("Starting up VrFlinger...");
66
67 // We need to be able to create endpoints with full perms.
68 umask(0000);
69
70 android::ProcessState::self()->startThreadPool();
71
72 request_display_callback_ = request_display_callback;
73
74 dispatcher_ = android::pdx::ServiceDispatcher::Create();
75 CHECK_ERROR(!dispatcher_, error, "Failed to create service dispatcher.");
76
77 display_service_ =
78 android::dvr::DisplayService::Create(hidl, request_display_callback);
79 CHECK_ERROR(!display_service_, error, "Failed to create display service.");
80 dispatcher_->AddService(display_service_);
81
82 service = android::dvr::DisplayManagerService::Create(display_service_);
83 CHECK_ERROR(!service, error, "Failed to create display manager service.");
84 dispatcher_->AddService(service);
85
86 service = android::dvr::VSyncService::Create();
87 CHECK_ERROR(!service, error, "Failed to create vsync service.");
88 dispatcher_->AddService(service);
89
90 display_service_->SetVSyncCallback(
91 std::bind(&android::dvr::VSyncService::VSyncEvent,
92 std::static_pointer_cast<android::dvr::VSyncService>(service),
93 std::placeholders::_1, std::placeholders::_2,
94 std::placeholders::_3, std::placeholders::_4));
95
96 dispatcher_thread_ = std::thread([this]() {
97 prctl(PR_SET_NAME, reinterpret_cast<unsigned long>("VrDispatch"), 0, 0, 0);
98 ALOGI("Entering message loop.");
99
100 setpriority(PRIO_PROCESS, 0, android::PRIORITY_URGENT_DISPLAY);
101 set_sched_policy(0, SP_FOREGROUND);
102
103 int ret = dispatcher_->EnterDispatchLoop();
104 if (ret < 0) {
105 ALOGE("Dispatch loop exited because: %s\n", strerror(-ret));
106 }
107 });
108
109 return true;
110
111 error:
112 return false;
113 }
114
OnBootFinished()115 void VrFlinger::OnBootFinished() {
116 sp<IVrManager> vr_manager = interface_cast<IVrManager>(
117 defaultServiceManager()->checkService(String16("vrmanager")));
118 if (vr_manager.get()) {
119 persistent_vr_state_callback_ =
120 new PersistentVrStateCallback(request_display_callback_);
121 vr_manager->registerPersistentVrStateListener(
122 persistent_vr_state_callback_);
123 } else {
124 ALOGE("Unable to register vr flinger for persistent vr mode changes");
125 }
126 }
127
GrantDisplayOwnership()128 void VrFlinger::GrantDisplayOwnership() {
129 display_service_->GrantDisplayOwnership();
130 }
131
SeizeDisplayOwnership()132 void VrFlinger::SeizeDisplayOwnership() {
133 display_service_->SeizeDisplayOwnership();
134 }
135
Dump()136 std::string VrFlinger::Dump() {
137 // TODO(karthikrs): Add more state information here.
138 return display_service_->DumpState(0/*unused*/);
139 }
140
onPersistentVrStateChanged(bool enabled)141 void VrFlinger::PersistentVrStateCallback::onPersistentVrStateChanged(
142 bool enabled) {
143 ALOGV("Notified persistent vr mode is %s", enabled ? "on" : "off");
144 // TODO(eieio): Determine the correct signal to request display control.
145 // Persistent VR mode is not enough.
146 // request_display_callback_(enabled);
147 }
148 } // namespace dvr
149 } // namespace android
150