// // Copyright (C) 2016 The Android Open Source Project // // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. // You may obtain a copy of the License at // // http://www.apache.org/licenses/LICENSE-2.0 // // Unless required by applicable law or agreed to in writing, software // distributed under the License is distributed on an "AS IS" BASIS, // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. // #include "tpm_manager/server/binder_service.h" #include #include #include #include "tpm_manager/common/tpm_manager.pb.h" #include "tpm_manager/common/tpm_manager_constants.h" namespace { // Sends a |response_proto| to |client| for an arbitrary protobuf type. template void ResponseHandler( const android::sp& client, const ResponseProtobufType& response_proto) { VLOG(2) << __func__; std::vector binder_response; binder_response.resize(response_proto.ByteSize()); CHECK(response_proto.SerializeToArray(binder_response.data(), binder_response.size())) << "BinderService: Failed to serialize protobuf."; android::binder::Status status = client->OnCommandResponse(binder_response); if (!status.isOk()) { LOG(ERROR) << "BinderService: Failed to send response to client: " << status.toString8(); } } // Creates an error protobuf for NVRAM commands. template void CreateNvramErrorResponse(ResponseProtobufType* proto) { proto->set_result(tpm_manager::NVRAM_RESULT_IPC_ERROR); } // Creates an error protobuf for ownership commands. template void CreateOwnershipErrorResponse(ResponseProtobufType* proto) { proto->set_status(tpm_manager::STATUS_DEVICE_ERROR); } // Calls |method| with a protobuf decoded from |request| using ResponseHandler() // and |client| to handle the response. On error, uses |get_error_response| to // construct a response and sends that to |client|. template void RequestHandler( const std::vector& request, const base::Callback< void(const RequestProtobufType&, const base::Callback&)>& method, const base::Callback& get_error_response, const android::sp& client) { VLOG(2) << __func__; base::Callback callback = base::Bind(ResponseHandler, client); RequestProtobufType request_proto; if (!request_proto.ParseFromArray(request.data(), request.size())) { LOG(ERROR) << "BinderService: Bad request data."; // Send an error response. ResponseProtobufType response_proto; get_error_response.Run(&response_proto); callback.Run(response_proto); return; } method.Run(request_proto, callback); } } // namespace namespace tpm_manager { BinderService::BinderService(TpmNvramInterface* nvram_service, TpmOwnershipInterface* ownership_service) : nvram_service_(nvram_service), ownership_service_(ownership_service) {} void BinderService::InitForTesting() { nvram_binder_ = new NvramServiceInternal(nvram_service_); ownership_binder_ = new OwnershipServiceInternal(ownership_service_); } int BinderService::OnInit() { if (!watcher_.Init()) { LOG(ERROR) << "BinderService: BinderWatcher::Init failed."; return EX_UNAVAILABLE; } nvram_binder_ = new NvramServiceInternal(nvram_service_); ownership_binder_ = new OwnershipServiceInternal(ownership_service_); if (!android::BinderWrapper::GetOrCreateInstance()->RegisterService( kTpmNvramBinderName, android::IInterface::asBinder(nvram_binder_))) { LOG(ERROR) << "BinderService: RegisterService failed (nvram)."; return EX_UNAVAILABLE; } if (!android::BinderWrapper::GetOrCreateInstance()->RegisterService( kTpmOwnershipBinderName, android::IInterface::asBinder(ownership_binder_))) { LOG(ERROR) << "BinderService: RegisterService failed (ownership)."; return EX_UNAVAILABLE; } LOG(INFO) << "TpmManager: Binder services registered."; return brillo::Daemon::OnInit(); } android::tpm_manager::ITpmNvram* BinderService::GetITpmNvram() { return nvram_binder_.get(); } android::tpm_manager::ITpmOwnership* BinderService::GetITpmOwnership() { return ownership_binder_.get(); } BinderService::NvramServiceInternal::NvramServiceInternal( TpmNvramInterface* nvram_service) : nvram_service_(nvram_service) {} android::binder::Status BinderService::NvramServiceInternal::DefineSpace( const std::vector& command_proto, const android::sp& client) { RequestHandler( command_proto, base::Bind(&TpmNvramInterface::DefineSpace, base::Unretained(nvram_service_)), base::Bind(CreateNvramErrorResponse), client); return android::binder::Status::ok(); } android::binder::Status BinderService::NvramServiceInternal::DestroySpace( const std::vector& command_proto, const android::sp& client) { RequestHandler( command_proto, base::Bind(&TpmNvramInterface::DestroySpace, base::Unretained(nvram_service_)), base::Bind(CreateNvramErrorResponse), client); return android::binder::Status::ok(); } android::binder::Status BinderService::NvramServiceInternal::WriteSpace( const std::vector& command_proto, const android::sp& client) { RequestHandler( command_proto, base::Bind(&TpmNvramInterface::WriteSpace, base::Unretained(nvram_service_)), base::Bind(CreateNvramErrorResponse), client); return android::binder::Status::ok(); } android::binder::Status BinderService::NvramServiceInternal::ReadSpace( const std::vector& command_proto, const android::sp& client) { RequestHandler( command_proto, base::Bind(&TpmNvramInterface::ReadSpace, base::Unretained(nvram_service_)), base::Bind(CreateNvramErrorResponse), client); return android::binder::Status::ok(); } android::binder::Status BinderService::NvramServiceInternal::LockSpace( const std::vector& command_proto, const android::sp& client) { RequestHandler( command_proto, base::Bind(&TpmNvramInterface::LockSpace, base::Unretained(nvram_service_)), base::Bind(CreateNvramErrorResponse), client); return android::binder::Status::ok(); } android::binder::Status BinderService::NvramServiceInternal::ListSpaces( const std::vector& command_proto, const android::sp& client) { RequestHandler( command_proto, base::Bind(&TpmNvramInterface::ListSpaces, base::Unretained(nvram_service_)), base::Bind(CreateNvramErrorResponse), client); return android::binder::Status::ok(); } android::binder::Status BinderService::NvramServiceInternal::GetSpaceInfo( const std::vector& command_proto, const android::sp& client) { RequestHandler( command_proto, base::Bind(&TpmNvramInterface::GetSpaceInfo, base::Unretained(nvram_service_)), base::Bind(CreateNvramErrorResponse), client); return android::binder::Status::ok(); } BinderService::OwnershipServiceInternal::OwnershipServiceInternal( TpmOwnershipInterface* ownership_service) : ownership_service_(ownership_service) {} android::binder::Status BinderService::OwnershipServiceInternal::GetTpmStatus( const std::vector& command_proto, const android::sp& client) { RequestHandler( command_proto, base::Bind(&TpmOwnershipInterface::GetTpmStatus, base::Unretained(ownership_service_)), base::Bind(CreateOwnershipErrorResponse), client); return android::binder::Status::ok(); } android::binder::Status BinderService::OwnershipServiceInternal::TakeOwnership( const std::vector& command_proto, const android::sp& client) { RequestHandler( command_proto, base::Bind(&TpmOwnershipInterface::TakeOwnership, base::Unretained(ownership_service_)), base::Bind(CreateOwnershipErrorResponse), client); return android::binder::Status::ok(); } android::binder::Status BinderService::OwnershipServiceInternal::RemoveOwnerDependency( const std::vector& command_proto, const android::sp& client) { RequestHandler( command_proto, base::Bind(&TpmOwnershipInterface::RemoveOwnerDependency, base::Unretained(ownership_service_)), base::Bind(CreateOwnershipErrorResponse), client); return android::binder::Status::ok(); } } // namespace tpm_manager