1 /*
2 * Copyright (C) 2018 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 <android-base/properties.h>
18
19 #include <hidl/AidlCameraDeviceCallbacks.h>
20 #include <hidl/AidlCameraServiceListener.h>
21 #include <hidl/HidlCameraService.h>
22 #include <hidl/HidlCameraDeviceUser.h>
23 #include <hidl/Utils.h>
24
25 #include <hidl/HidlTransportSupport.h>
26
27 namespace android {
28 namespace frameworks {
29 namespace cameraservice {
30 namespace service {
31 namespace V2_0 {
32 namespace implementation {
33
34 using frameworks::cameraservice::service::V2_0::implementation::HidlCameraService;
35 using hardware::hidl_vec;
36 using hardware::cameraservice::utils::conversion::convertToHidl;
37 using hardware::cameraservice::utils::conversion::filterVndkKeys;
38 using hardware::cameraservice::utils::conversion::B2HStatus;
39 using hardware::Void;
40
41 using device::V2_0::implementation::H2BCameraDeviceCallbacks;
42 using device::V2_1::implementation::HidlCameraDeviceUser;
43 using service::V2_0::implementation::H2BCameraServiceListener;
44 using HCameraMetadataType = frameworks::cameraservice::common::V2_0::CameraMetadataType;
45 using HVendorTag = frameworks::cameraservice::common::V2_0::VendorTag;
46 using HVendorTagSection = frameworks::cameraservice::common::V2_0::VendorTagSection;
47 using HProviderIdAndVendorTagSections =
48 frameworks::cameraservice::common::V2_0::ProviderIdAndVendorTagSections;
49
50 sp<HidlCameraService> gHidlCameraService;
51
getInstance(android::CameraService * cs)52 sp<HidlCameraService> HidlCameraService::getInstance(android::CameraService *cs) {
53 gHidlCameraService = new HidlCameraService(cs);
54 return gHidlCameraService;
55 }
56
HidlCameraService(android::CameraService * cs)57 HidlCameraService::HidlCameraService(android::CameraService *cs) : mAidlICameraService(cs) {
58 mVndkVersion = base::GetIntProperty("ro.vndk.version", __ANDROID_API_FUTURE__);
59 };
60
61 Return<void>
getCameraCharacteristics(const hidl_string & cameraId,getCameraCharacteristics_cb _hidl_cb)62 HidlCameraService::getCameraCharacteristics(const hidl_string& cameraId,
63 getCameraCharacteristics_cb _hidl_cb) {
64 android::CameraMetadata cameraMetadata;
65 HStatus status = HStatus::NO_ERROR;
66 binder::Status serviceRet =
67 mAidlICameraService->getCameraCharacteristics(String16(cameraId.c_str()),
68 /*targetSdkVersion*/__ANDROID_API_FUTURE__, /*overrideToPortrait*/false,
69 &cameraMetadata);
70 HCameraMetadata hidlMetadata;
71 if (!serviceRet.isOk()) {
72 switch(serviceRet.serviceSpecificErrorCode()) {
73 // No ERROR_CAMERA_DISCONNECTED since we're in the same process.
74 case hardware::ICameraService::ERROR_ILLEGAL_ARGUMENT:
75 ALOGE("%s: Camera ID %s does not exist!", __FUNCTION__, cameraId.c_str());
76 status = HStatus::ILLEGAL_ARGUMENT;
77 break;
78 default:
79 ALOGE("Get camera characteristics from camera service failed: %s",
80 serviceRet.toString8().string());
81 status = B2HStatus(serviceRet);
82 }
83 _hidl_cb(status, hidlMetadata);
84 return Void();
85 }
86 if (filterVndkKeys(mVndkVersion, cameraMetadata) != OK) {
87 ALOGE("%s: Unable to filter vndk metadata keys for version %d", __FUNCTION__, mVndkVersion);
88 _hidl_cb(HStatus::UNKNOWN_ERROR, hidlMetadata);
89 return Void();
90 }
91 const camera_metadata_t *rawMetadata = cameraMetadata.getAndLock();
92 convertToHidl(rawMetadata, &hidlMetadata);
93 _hidl_cb(status, hidlMetadata);
94 cameraMetadata.unlock(rawMetadata);
95 return Void();
96 }
97
connectDevice(const sp<HCameraDeviceCallback> & hCallback,const hidl_string & cameraId,connectDevice_cb _hidl_cb)98 Return<void> HidlCameraService::connectDevice(const sp<HCameraDeviceCallback>& hCallback,
99 const hidl_string& cameraId,
100 connectDevice_cb _hidl_cb) {
101 // Here, we first get ICameraDeviceUser from mAidlICameraService, then save
102 // that interface in the newly created HidlCameraDeviceUser impl class.
103 if (mAidlICameraService == nullptr) {
104 _hidl_cb(HStatus::UNKNOWN_ERROR, nullptr);
105 return Void();
106 }
107 sp<hardware::camera2::ICameraDeviceUser> deviceRemote = nullptr;
108 // Create a hardware::camera2::ICameraDeviceCallback object which internally
109 // calls callback functions passed through hCallback.
110 sp<H2BCameraDeviceCallbacks> hybridCallbacks = new H2BCameraDeviceCallbacks(hCallback);
111 if (!hybridCallbacks->initializeLooper(mVndkVersion)) {
112 ALOGE("Unable to handle callbacks on device, cannot connect");
113 _hidl_cb(HStatus::UNKNOWN_ERROR, nullptr);
114 return Void();
115 }
116 sp<hardware::camera2::ICameraDeviceCallbacks> callbacks = hybridCallbacks;
117 binder::Status serviceRet = mAidlICameraService->connectDevice(
118 callbacks, String16(cameraId.c_str()), String16(""), {},
119 hardware::ICameraService::USE_CALLING_UID, 0/*oomScoreOffset*/,
120 /*targetSdkVersion*/__ANDROID_API_FUTURE__, /*overrideToPortrait*/false,
121 /*out*/&deviceRemote);
122 HStatus status = HStatus::NO_ERROR;
123 if (!serviceRet.isOk()) {
124 ALOGE("%s: Unable to connect to camera device", __FUNCTION__);
125 status = B2HStatus(serviceRet);
126 _hidl_cb(status, nullptr);
127 return Void();
128 }
129 // Now we create a HidlCameraDeviceUser class, store the deviceRemote in it,
130 // and return that back. All calls on that interface will be forwarded to
131 // the AIDL interface.
132 sp<HidlCameraDeviceUser> hDeviceRemote = new HidlCameraDeviceUser(deviceRemote);
133 if (!hDeviceRemote->initStatus()) {
134 ALOGE("%s: Unable to initialize camera device HIDL wrapper", __FUNCTION__);
135 _hidl_cb(HStatus::UNKNOWN_ERROR, nullptr);
136 return Void();
137 }
138 hybridCallbacks->setCaptureResultMetadataQueue(hDeviceRemote->getCaptureResultMetadataQueue());
139 _hidl_cb(status, hDeviceRemote);
140 return Void();
141 }
142
addToListenerCacheLocked(sp<HCameraServiceListener> hListener,sp<hardware::ICameraServiceListener> csListener)143 void HidlCameraService::addToListenerCacheLocked(sp<HCameraServiceListener> hListener,
144 sp<hardware::ICameraServiceListener> csListener) {
145 mListeners.emplace_back(std::make_pair(hListener, csListener));
146 }
147
148 sp<hardware::ICameraServiceListener>
searchListenerCacheLocked(sp<HCameraServiceListener> hListener,bool shouldRemove)149 HidlCameraService::searchListenerCacheLocked(sp<HCameraServiceListener> hListener,
150 bool shouldRemove) {
151 // Go through the mListeners list and compare the listener with the HIDL
152 // listener registered.
153 auto it = mListeners.begin();
154 sp<ICameraServiceListener> csListener = nullptr;
155 for (;it != mListeners.end(); it++) {
156 if (hardware::interfacesEqual(it->first, hListener)) {
157 break;
158 }
159 }
160 if (it != mListeners.end()) {
161 csListener = it->second;
162 if (shouldRemove) {
163 mListeners.erase(it);
164 }
165 }
166 return csListener;
167 }
168
addListener(const sp<HCameraServiceListener> & hCsListener,addListener_cb _hidl_cb)169 Return<void> HidlCameraService::addListener(const sp<HCameraServiceListener>& hCsListener,
170 addListener_cb _hidl_cb) {
171 std::vector<hardware::CameraStatus> cameraStatusAndIds{};
172 HStatus status = addListenerInternal<HCameraServiceListener>(
173 hCsListener, &cameraStatusAndIds);
174 if (status != HStatus::NO_ERROR) {
175 _hidl_cb(status, {});
176 return Void();
177 }
178
179 hidl_vec<HCameraStatusAndId> hCameraStatusAndIds;
180 //Convert cameraStatusAndIds to HIDL and call callback
181 convertToHidl(cameraStatusAndIds, &hCameraStatusAndIds);
182 _hidl_cb(status, hCameraStatusAndIds);
183
184 return Void();
185 }
186
addListener_2_1(const sp<HCameraServiceListener2_1> & hCsListener,addListener_2_1_cb _hidl_cb)187 Return<void> HidlCameraService::addListener_2_1(const sp<HCameraServiceListener2_1>& hCsListener,
188 addListener_2_1_cb _hidl_cb) {
189 std::vector<hardware::CameraStatus> cameraStatusAndIds{};
190 HStatus status = addListenerInternal<HCameraServiceListener2_1>(
191 hCsListener, &cameraStatusAndIds);
192 if (status != HStatus::NO_ERROR) {
193 _hidl_cb(status, {});
194 return Void();
195 }
196
197 hidl_vec<frameworks::cameraservice::service::V2_1::CameraStatusAndId> hCameraStatusAndIds;
198 //Convert cameraStatusAndIds to HIDL and call callback
199 convertToHidl(cameraStatusAndIds, &hCameraStatusAndIds);
200 _hidl_cb(status, hCameraStatusAndIds);
201
202 return Void();
203 }
204
205 template<class T>
addListenerInternal(const sp<T> & hCsListener,std::vector<hardware::CameraStatus> * cameraStatusAndIds)206 HStatus HidlCameraService::addListenerInternal(const sp<T>& hCsListener,
207 std::vector<hardware::CameraStatus>* cameraStatusAndIds) {
208 if (mAidlICameraService == nullptr) {
209 return HStatus::UNKNOWN_ERROR;
210 }
211 if (hCsListener == nullptr || cameraStatusAndIds == nullptr) {
212 ALOGE("%s listener and cameraStatusAndIds must not be NULL", __FUNCTION__);
213 return HStatus::ILLEGAL_ARGUMENT;
214 }
215 sp<hardware::ICameraServiceListener> csListener = nullptr;
216 // Check the cache for previously registered callbacks
217 {
218 Mutex::Autolock l(mListenerListLock);
219 csListener = searchListenerCacheLocked(hCsListener);
220 if (csListener == nullptr) {
221 // Wrap an hCsListener with AidlCameraServiceListener and pass it to
222 // CameraService.
223 csListener = new H2BCameraServiceListener(hCsListener);
224 // Add to cache
225 addToListenerCacheLocked(hCsListener, csListener);
226 } else {
227 ALOGE("%s: Trying to add a listener %p already registered",
228 __FUNCTION__, hCsListener.get());
229 return HStatus::ILLEGAL_ARGUMENT;
230 }
231 }
232 binder::Status serviceRet =
233 mAidlICameraService->addListenerHelper(csListener, cameraStatusAndIds, true);
234 HStatus status = HStatus::NO_ERROR;
235 if (!serviceRet.isOk()) {
236 ALOGE("%s: Unable to add camera device status listener", __FUNCTION__);
237 status = B2HStatus(serviceRet);
238 return status;
239 }
240 cameraStatusAndIds->erase(std::remove_if(cameraStatusAndIds->begin(), cameraStatusAndIds->end(),
241 [this](const hardware::CameraStatus& s) {
242 bool supportsHAL3 = false;
243 binder::Status sRet =
244 mAidlICameraService->supportsCameraApi(String16(s.cameraId),
245 hardware::ICameraService::API_VERSION_2, &supportsHAL3);
246 return !sRet.isOk() || !supportsHAL3;
247 }), cameraStatusAndIds->end());
248
249 return HStatus::NO_ERROR;
250 }
251
removeListener(const sp<HCameraServiceListener> & hCsListener)252 Return<HStatus> HidlCameraService::removeListener(const sp<HCameraServiceListener>& hCsListener) {
253 if (hCsListener == nullptr) {
254 ALOGE("%s listener must not be NULL", __FUNCTION__);
255 return HStatus::ILLEGAL_ARGUMENT;
256 }
257 sp<ICameraServiceListener> csListener = nullptr;
258 {
259 Mutex::Autolock l(mListenerListLock);
260 csListener = searchListenerCacheLocked(hCsListener, /*removeIfFound*/true);
261 }
262 if (csListener != nullptr) {
263 mAidlICameraService->removeListener(csListener);
264 } else {
265 ALOGE("%s Removing unregistered listener %p", __FUNCTION__, hCsListener.get());
266 return HStatus::ILLEGAL_ARGUMENT;
267 }
268 return HStatus::NO_ERROR;
269 }
270
getCameraVendorTagSections(getCameraVendorTagSections_cb _hidl_cb)271 Return<void> HidlCameraService::getCameraVendorTagSections(getCameraVendorTagSections_cb _hidl_cb) {
272 sp<VendorTagDescriptorCache> gCache = VendorTagDescriptorCache::getGlobalVendorTagCache();
273 if (gCache == nullptr) {
274 _hidl_cb(HStatus::UNKNOWN_ERROR, {});
275 return Void();
276 }
277 const std::unordered_map<metadata_vendor_id_t, sp<android::VendorTagDescriptor>>
278 &vendorIdsAndTagDescs = gCache->getVendorIdsAndTagDescriptors();
279 if (vendorIdsAndTagDescs.size() == 0) {
280 _hidl_cb(HStatus::UNKNOWN_ERROR, {});
281 return Void();
282 }
283
284 hidl_vec<HProviderIdAndVendorTagSections> hTagIdsAndVendorTagSections;
285 hTagIdsAndVendorTagSections.resize(vendorIdsAndTagDescs.size());
286 size_t j = 0;
287 for (auto &vendorIdAndTagDescs : vendorIdsAndTagDescs) {
288 hidl_vec<HVendorTagSection> hVendorTagSections;
289 sp<VendorTagDescriptor> desc = vendorIdAndTagDescs.second;
290 const SortedVector<String8>* sectionNames = desc->getAllSectionNames();
291 size_t numSections = sectionNames->size();
292 std::vector<std::vector<HVendorTag>> tagsBySection(numSections);
293 int tagCount = desc->getTagCount();
294 if (tagCount <= 0) {
295 continue;
296 }
297 std::vector<uint32_t> tags(tagCount);
298 desc->getTagArray(tags.data());
299 for (int i = 0; i < tagCount; i++) {
300 HVendorTag vt;
301 vt.tagId = tags[i];
302 vt.tagName = desc->getTagName(tags[i]);
303 vt.tagType = (HCameraMetadataType) desc->getTagType(tags[i]);
304 ssize_t sectionIdx = desc->getSectionIndex(tags[i]);
305 tagsBySection[sectionIdx].push_back(vt);
306 }
307 hVendorTagSections.resize(numSections);
308 for (size_t s = 0; s < numSections; s++) {
309 hVendorTagSections[s].sectionName = (*sectionNames)[s].string();
310 hVendorTagSections[s].tags = tagsBySection[s];
311 }
312 HProviderIdAndVendorTagSections &hProviderIdAndVendorTagSections =
313 hTagIdsAndVendorTagSections[j];
314 hProviderIdAndVendorTagSections.providerId = vendorIdAndTagDescs.first;
315 hProviderIdAndVendorTagSections.vendorTagSections = std::move(hVendorTagSections);
316 j++;
317 }
318 _hidl_cb(HStatus::NO_ERROR, hTagIdsAndVendorTagSections);
319 return Void();
320 }
321
322 } // implementation
323 } // V2_0
324 } // service
325 } // cameraservice
326 } // frameworks
327 } // android
328
329