1 /* 2 * Copyright (C) 2022 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #include "EvsEnumerator.h" 18 #include "EvsGlDisplay.h" 19 20 #include <android/binder_manager.h> 21 #include <android/binder_process.h> 22 #include <utils/Log.h> 23 24 #include <unistd.h> 25 26 #include <atomic> 27 #include <cstdlib> 28 #include <string_view> 29 30 namespace { 31 32 using ::aidl::android::frameworks::automotive::display::ICarDisplayProxy; 33 using ::aidl::android::hardware::automotive::evs::implementation::EvsEnumerator; 34 35 constexpr std::string_view kDisplayServiceInstanceName = "/default"; 36 constexpr std::string_view kHwInstanceName = "/hw/0"; 37 constexpr int kNumBinderThreads = 1; 38 39 } // namespace 40 main()41int main() { 42 LOG(INFO) << "EVS Hardware Enumerator service is starting"; 43 44 const std::string displayServiceInstanceName = 45 std::string(ICarDisplayProxy::descriptor) + std::string(kDisplayServiceInstanceName); 46 if (!AServiceManager_isDeclared(displayServiceInstanceName.data())) { 47 // TODO: We may just want to disable EVS display. 48 LOG(ERROR) << displayServiceInstanceName << " is required."; 49 return EXIT_FAILURE; 50 } 51 52 std::shared_ptr<ICarDisplayProxy> displayService = ICarDisplayProxy::fromBinder( 53 ::ndk::SpAIBinder(AServiceManager_waitForService(displayServiceInstanceName.data()))); 54 if (!displayService) { 55 LOG(ERROR) << "Cannot use " << displayServiceInstanceName << ". Exiting."; 56 return EXIT_FAILURE; 57 } 58 59 // Register our service -- if somebody is already registered by our name, 60 // they will be killed (their thread pool will throw an exception). 61 std::shared_ptr<EvsEnumerator> service = 62 ndk::SharedRefBase::make<EvsEnumerator>(displayService); 63 if (!service) { 64 LOG(ERROR) << "Failed to instantiate the service"; 65 return EXIT_FAILURE; 66 } 67 68 const std::string instanceName = 69 std::string(EvsEnumerator::descriptor) + std::string(kHwInstanceName); 70 auto err = AServiceManager_addService(service->asBinder().get(), instanceName.data()); 71 if (err != EX_NONE) { 72 LOG(ERROR) << "Failed to register " << instanceName << ", exception = " << err; 73 return EXIT_FAILURE; 74 } 75 76 if (!ABinderProcess_setThreadPoolMaxThreadCount(kNumBinderThreads)) { 77 LOG(ERROR) << "Failed to set thread pool"; 78 return EXIT_FAILURE; 79 } 80 81 ABinderProcess_startThreadPool(); 82 LOG(INFO) << "EVS Hardware Enumerator is ready"; 83 84 ABinderProcess_joinThreadPool(); 85 // In normal operation, we don't expect the thread pool to exit 86 LOG(INFO) << "EVS Hardware Enumerator is shutting down"; 87 return EXIT_SUCCESS; 88 } 89