display_service.cpp revision 7480c060cb3466d97ec3125d61bbace153f534c8
1#include "display_service.h" 2 3#include <vector> 4 5#include <pdx/default_transport/service_endpoint.h> 6#include <pdx/rpc/remote_method.h> 7#include <private/dvr/composite_hmd.h> 8#include <private/dvr/display_rpc.h> 9#include <private/dvr/display_types.h> 10#include <private/dvr/lucid_metrics.h> 11#include <private/dvr/numeric.h> 12#include <private/dvr/polynomial_radial_distortion.h> 13#include <private/dvr/types.h> 14 15using android::pdx::Channel; 16using android::pdx::Message; 17using android::pdx::default_transport::Endpoint; 18using android::pdx::rpc::DispatchRemoteMethod; 19using android::pdx::rpc::WrapBuffer; 20 21namespace android { 22namespace dvr { 23 24DisplayService::DisplayService() : DisplayService(nullptr) {} 25 26DisplayService::DisplayService(Hwc2::Composer* hidl) 27 : BASE("DisplayService", Endpoint::Create(DisplayRPC::kClientPath)), 28 hardware_composer_(hidl) { 29 hardware_composer_.Initialize(); 30} 31 32bool DisplayService::IsInitialized() const { 33 return BASE::IsInitialized() && hardware_composer_.IsInitialized(); 34} 35 36std::string DisplayService::DumpState(size_t max_length) { 37 std::vector<char> buffer(max_length); 38 uint32_t max_len_p = static_cast<uint32_t>(max_length); 39 hardware_composer_.Dump(buffer.data(), &max_len_p); 40 return std::string(buffer.data()); 41} 42 43void DisplayService::OnChannelClose(pdx::Message& /*message*/, 44 const std::shared_ptr<Channel>& channel) { 45 auto surface = std::static_pointer_cast<SurfaceChannel>(channel); 46 if (surface && surface->type() == SurfaceTypeEnum::Normal) { 47 auto display_surface = std::static_pointer_cast<DisplaySurface>(surface); 48 display_surface->ManagerSetVisible(false); 49 display_surface->ClientSetVisible(false); 50 NotifyDisplayConfigurationUpdate(); 51 } 52 // TODO(jwcai) Handle ChannelClose of VideoMeshSurface. 53} 54 55// First-level dispatch for display service messages. Directly handles messages 56// that are independent of the display surface (metrics, creation) and routes 57// surface-specific messages to the per-instance handlers. 58int DisplayService::HandleMessage(pdx::Message& message) { 59 auto channel = message.GetChannel<SurfaceChannel>(); 60 61 switch (message.GetOp()) { 62 case DisplayRPC::GetMetrics::Opcode: 63 DispatchRemoteMethod<DisplayRPC::GetMetrics>( 64 *this, &DisplayService::OnGetMetrics, message); 65 return 0; 66 67 case DisplayRPC::GetEdsCapture::Opcode: 68 DispatchRemoteMethod<DisplayRPC::GetEdsCapture>( 69 *this, &DisplayService::OnGetEdsCapture, message); 70 return 0; 71 72 case DisplayRPC::CreateSurface::Opcode: 73 DispatchRemoteMethod<DisplayRPC::CreateSurface>( 74 *this, &DisplayService::OnCreateSurface, message); 75 return 0; 76 77 case DisplayRPC::EnterVrMode::Opcode: 78 DispatchRemoteMethod<DisplayRPC::EnterVrMode>( 79 *this, &DisplayService::OnEnterVrMode, message); 80 return 0; 81 82 case DisplayRPC::ExitVrMode::Opcode: 83 DispatchRemoteMethod<DisplayRPC::ExitVrMode>( 84 *this, &DisplayService::OnExitVrMode, message); 85 return 0; 86 87 case DisplayRPC::SetViewerParams::Opcode: 88 DispatchRemoteMethod<DisplayRPC::SetViewerParams>( 89 *this, &DisplayService::OnSetViewerParams, message); 90 return 0; 91 92 // Direct the surface specific messages to the surface instance. 93 case DisplayRPC::CreateBufferQueue::Opcode: 94 case DisplayRPC::SetAttributes::Opcode: 95 case DisplayRPC::GetMetadataBuffer::Opcode: 96 case DisplayRPC::CreateVideoMeshSurface::Opcode: 97 case DisplayRPC::VideoMeshSurfaceCreateProducerQueue::Opcode: 98 return HandleSurfaceMessage(message); 99 100 default: 101 return Service::HandleMessage(message); 102 } 103} 104 105SystemDisplayMetrics DisplayService::OnGetMetrics(pdx::Message& message) { 106 const Compositor* compositor = hardware_composer_.GetCompositor(); 107 if (compositor == nullptr) 108 REPLY_ERROR_RETURN(message, EINVAL, {}); 109 110 HeadMountMetrics head_mount = compositor->head_mount_metrics(); 111 CompositeHmd hmd(head_mount, hardware_composer_.GetHmdDisplayMetrics()); 112 vec2i distorted_render_size = hmd.GetRecommendedRenderTargetSize(); 113 FieldOfView left_fov = hmd.GetEyeFov(kLeftEye); 114 FieldOfView right_fov = hmd.GetEyeFov(kRightEye); 115 116 SystemDisplayMetrics metrics; 117 118 metrics.display_native_width = GetDisplayMetrics().width; 119 metrics.display_native_height = GetDisplayMetrics().height; 120 metrics.display_x_dpi = GetDisplayMetrics().dpi.x; 121 metrics.display_y_dpi = GetDisplayMetrics().dpi.y; 122 metrics.distorted_width = distorted_render_size[0]; 123 metrics.distorted_height = distorted_render_size[1]; 124 metrics.vsync_period_ns = 125 hardware_composer_.native_display_metrics().vsync_period_ns; 126 metrics.hmd_ipd_mm = 0; 127 metrics.inter_lens_distance_m = head_mount.GetInterLensDistance(); 128 metrics.left_fov_lrbt[0] = left_fov.GetLeft(); 129 metrics.left_fov_lrbt[1] = left_fov.GetRight(); 130 metrics.left_fov_lrbt[2] = left_fov.GetBottom(); 131 metrics.left_fov_lrbt[3] = left_fov.GetTop(); 132 metrics.right_fov_lrbt[0] = right_fov.GetLeft(); 133 metrics.right_fov_lrbt[1] = right_fov.GetRight(); 134 metrics.right_fov_lrbt[2] = right_fov.GetBottom(); 135 metrics.right_fov_lrbt[3] = right_fov.GetTop(); 136 137 return metrics; 138} 139 140// Creates a new DisplaySurface and associates it with this channel. This may 141// only be done once per channel. 142int DisplayService::OnCreateSurface(pdx::Message& message, int width, 143 int height, int format, int usage, 144 DisplaySurfaceFlags flags) { 145 // A surface may only be created once per channel. 146 if (message.GetChannel()) 147 return -EINVAL; 148 149 ALOGI_IF(TRACE, "DisplayService::OnCreateSurface: cid=%d", 150 message.GetChannelId()); 151 152 // Use the channel id as the unique surface id. 153 const int surface_id = message.GetChannelId(); 154 const int process_id = message.GetProcessId(); 155 156 ALOGI_IF(TRACE, 157 "DisplayService::OnCreateSurface: surface_id=%d process_id=%d " 158 "width=%d height=%d format=%x usage=%x flags=%x", 159 surface_id, process_id, width, height, format, usage, flags); 160 161 // TODO(eieio,jbates): Validate request parameters. 162 auto channel = std::make_shared<DisplaySurface>( 163 this, surface_id, process_id, width, height, format, usage, flags); 164 165 message.SetChannel(channel); 166 NotifyDisplayConfigurationUpdate(); 167 return 0; 168} 169 170DisplayRPC::ByteBuffer DisplayService::OnGetEdsCapture(pdx::Message& message) { 171 Compositor* compositor = hardware_composer_.GetCompositor(); 172 if (compositor == nullptr) 173 REPLY_ERROR_RETURN(message, EINVAL, {}); 174 175 std::vector<std::uint8_t> buffer(sizeof(LateLatchOutput)); 176 177 if (!compositor->GetLastEdsPose( 178 reinterpret_cast<LateLatchOutput*>(buffer.data()))) { 179 REPLY_ERROR_RETURN(message, EPERM, {}); 180 } 181 182 return WrapBuffer(std::move(buffer)); 183} 184 185int DisplayService::OnEnterVrMode(pdx::Message& /*message*/) { 186 hardware_composer_.Resume(); 187 return 0; 188} 189 190int DisplayService::OnExitVrMode(pdx::Message& /*message*/) { 191 hardware_composer_.Suspend(); 192 return 0; 193} 194 195void DisplayService::OnSetViewerParams(pdx::Message& message, 196 const ViewerParams& view_params) { 197 Compositor* compositor = hardware_composer_.GetCompositor(); 198 if (compositor == nullptr) 199 REPLY_ERROR_RETURN(message, EINVAL); 200 201 FieldOfView left(55.0f, 55.0f, 55.0f, 55.0f); 202 FieldOfView right(55.0f, 55.0f, 55.0f, 55.0f); 203 if (view_params.left_eye_field_of_view_angles.size() >= 4) { 204 left = FieldOfView(ToRad(view_params.left_eye_field_of_view_angles[0]), 205 ToRad(view_params.left_eye_field_of_view_angles[1]), 206 ToRad(view_params.left_eye_field_of_view_angles[2]), 207 ToRad(view_params.left_eye_field_of_view_angles[3])); 208 right = FieldOfView(ToRad(view_params.left_eye_field_of_view_angles[1]), 209 ToRad(view_params.left_eye_field_of_view_angles[0]), 210 ToRad(view_params.left_eye_field_of_view_angles[2]), 211 ToRad(view_params.left_eye_field_of_view_angles[3])); 212 } 213 214 std::shared_ptr<ColorChannelDistortion> red_distortion; 215 std::shared_ptr<ColorChannelDistortion> green_distortion; 216 std::shared_ptr<ColorChannelDistortion> blue_distortion; 217 218 // We should always have a red distortion. 219 LOG_FATAL_IF(view_params.distortion_coefficients_r.empty()); 220 red_distortion = std::make_shared<PolynomialRadialDistortion>( 221 view_params.distortion_coefficients_r); 222 223 if (!view_params.distortion_coefficients_g.empty()) { 224 green_distortion = std::make_shared<PolynomialRadialDistortion>( 225 view_params.distortion_coefficients_g); 226 } 227 228 if (!view_params.distortion_coefficients_b.empty()) { 229 blue_distortion = std::make_shared<PolynomialRadialDistortion>( 230 view_params.distortion_coefficients_b); 231 } 232 233 HeadMountMetrics::EyeOrientation left_orientation = 234 HeadMountMetrics::EyeOrientation::kCCW0Degrees; 235 HeadMountMetrics::EyeOrientation right_orientation = 236 HeadMountMetrics::EyeOrientation::kCCW0Degrees; 237 238 if (view_params.eye_orientations.size() > 1) { 239 left_orientation = static_cast<HeadMountMetrics::EyeOrientation>( 240 view_params.eye_orientations[0]); 241 right_orientation = static_cast<HeadMountMetrics::EyeOrientation>( 242 view_params.eye_orientations[1]); 243 } 244 245 HeadMountMetrics head_mount_metrics( 246 view_params.inter_lens_distance, view_params.tray_to_lens_distance, 247 view_params.screen_to_lens_distance, 248 static_cast<HeadMountMetrics::VerticalAlignment>( 249 view_params.vertical_alignment), 250 left, right, red_distortion, green_distortion, blue_distortion, 251 left_orientation, right_orientation, 252 view_params.screen_center_to_lens_distance); 253 254 compositor->UpdateHeadMountMetrics(head_mount_metrics); 255} 256 257// Calls the message handler for the DisplaySurface associated with this 258// channel. 259int DisplayService::HandleSurfaceMessage(pdx::Message& message) { 260 auto surface = std::static_pointer_cast<SurfaceChannel>(message.GetChannel()); 261 ALOGW_IF(!surface, 262 "DisplayService::HandleSurfaceMessage: surface is nullptr!"); 263 264 if (surface) 265 return surface->HandleMessage(message); 266 else 267 REPLY_ERROR_RETURN(message, EINVAL, 0); 268} 269 270std::shared_ptr<DisplaySurface> DisplayService::GetDisplaySurface( 271 int surface_id) const { 272 return std::static_pointer_cast<DisplaySurface>(GetChannel(surface_id)); 273} 274 275std::vector<std::shared_ptr<DisplaySurface>> 276DisplayService::GetDisplaySurfaces() const { 277 return GetChannels<DisplaySurface>(); 278} 279 280std::vector<std::shared_ptr<DisplaySurface>> 281DisplayService::GetVisibleDisplaySurfaces() const { 282 std::vector<std::shared_ptr<DisplaySurface>> visible_surfaces; 283 284 ForEachDisplaySurface( 285 [&](const std::shared_ptr<DisplaySurface>& surface) mutable { 286 if (surface->IsVisible()) 287 visible_surfaces.push_back(surface); 288 }); 289 290 return visible_surfaces; 291} 292 293int DisplayService::UpdateActiveDisplaySurfaces() { 294 auto visible_surfaces = GetVisibleDisplaySurfaces(); 295 296 // Sort the surfaces based on manager z order first, then client z order. 297 std::sort(visible_surfaces.begin(), visible_surfaces.end(), 298 [](const std::shared_ptr<DisplaySurface>& a, 299 const std::shared_ptr<DisplaySurface>& b) { 300 return a->manager_z_order() != b->manager_z_order() 301 ? a->manager_z_order() < b->manager_z_order() 302 : a->client_z_order() < b->client_z_order(); 303 }); 304 305 ALOGD_IF(TRACE, 306 "DisplayService::UpdateActiveDisplaySurfaces: %zd visible surfaces", 307 visible_surfaces.size()); 308 309 // TODO(jbates) Have the shell manage blurred layers. 310 bool blur_requested = false; 311 auto end = visible_surfaces.crend(); 312 for (auto it = visible_surfaces.crbegin(); it != end; ++it) { 313 auto surface = *it; 314 // Surfaces with exclude_from_blur==true are not blurred 315 // and are excluded from blur computation of other layers. 316 if (surface->client_exclude_from_blur()) { 317 surface->ManagerSetBlur(0.0f); 318 continue; 319 } 320 surface->ManagerSetBlur(blur_requested ? 1.0f : 0.0f); 321 if (surface->client_blur_behind()) 322 blur_requested = true; 323 } 324 return hardware_composer_.SetDisplaySurfaces(std::move(visible_surfaces)); 325} 326 327void DisplayService::OnHardwareComposerRefresh() { 328 hardware_composer_.OnHardwareComposerRefresh(); 329} 330 331void DisplayService::SetDisplayConfigurationUpdateNotifier( 332 DisplayConfigurationUpdateNotifier update_notifier) { 333 update_notifier_ = update_notifier; 334} 335 336void DisplayService::NotifyDisplayConfigurationUpdate() { 337 if (update_notifier_) 338 update_notifier_(); 339} 340 341} // namespace dvr 342} // namespace android 343