blob: 52005c2c16e82ded7abef04a00060f64565cc87e [file] [log] [blame]
Hongguang093c5f32021-08-09 19:46:34 -07001/**
2 * Copyright (c) 2021, 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//#define LOG_NDEBUG 0
18#define LOG_TAG "TunerHidlService"
19
20#include "TunerHidlService.h"
21
Hongguang15758a82021-10-29 13:32:07 -070022#include <aidl/android/hardware/tv/tuner/FrontendIsdbtTimeInterleaveMode.h>
Hongguang093c5f32021-08-09 19:46:34 -070023#include <aidl/android/hardware/tv/tuner/Result.h>
24#include <android/binder_manager.h>
Hongguang34a479e2021-10-04 16:14:47 -070025#include <binder/IPCThreadState.h>
26#include <binder/PermissionCache.h>
Hongguang5eef5142022-08-09 20:26:42 -070027#include <cutils/properties.h>
Hongguang093c5f32021-08-09 19:46:34 -070028#include <utils/Log.h>
29
30#include "TunerHelper.h"
31#include "TunerHidlDemux.h"
32#include "TunerHidlDescrambler.h"
33#include "TunerHidlFrontend.h"
34#include "TunerHidlLnb.h"
35
36using ::aidl::android::hardware::tv::tuner::FrontendAnalogCapabilities;
37using ::aidl::android::hardware::tv::tuner::FrontendAtsc3Capabilities;
38using ::aidl::android::hardware::tv::tuner::FrontendAtscCapabilities;
39using ::aidl::android::hardware::tv::tuner::FrontendCapabilities;
40using ::aidl::android::hardware::tv::tuner::FrontendDtmbCapabilities;
41using ::aidl::android::hardware::tv::tuner::FrontendDvbcCapabilities;
42using ::aidl::android::hardware::tv::tuner::FrontendDvbsCapabilities;
43using ::aidl::android::hardware::tv::tuner::FrontendDvbtCapabilities;
44using ::aidl::android::hardware::tv::tuner::FrontendIsdbs3Capabilities;
45using ::aidl::android::hardware::tv::tuner::FrontendIsdbsCapabilities;
46using ::aidl::android::hardware::tv::tuner::FrontendIsdbtCapabilities;
Hongguang15758a82021-10-29 13:32:07 -070047using ::aidl::android::hardware::tv::tuner::FrontendIsdbtTimeInterleaveMode;
Hongguang093c5f32021-08-09 19:46:34 -070048using ::aidl::android::hardware::tv::tuner::FrontendType;
49using ::aidl::android::hardware::tv::tuner::Result;
Hongguang34a479e2021-10-04 16:14:47 -070050using ::android::IPCThreadState;
51using ::android::PermissionCache;
Hongguang093c5f32021-08-09 19:46:34 -070052using ::android::hardware::hidl_vec;
53
54using HidlFrontendId = ::android::hardware::tv::tuner::V1_0::FrontendId;
55using HidlLnbId = ::android::hardware::tv::tuner::V1_0::LnbId;
56using HidlFrontendType = ::android::hardware::tv::tuner::V1_1::FrontendType;
57
58using namespace std;
59
60namespace aidl {
61namespace android {
62namespace media {
63namespace tv {
64namespace tuner {
65
66TunerHidlService::TunerHidlService() {
Hongguang093c5f32021-08-09 19:46:34 -070067 mTuner = HidlITuner::getService();
Hongguang5eef5142022-08-09 20:26:42 -070068 ALOGE_IF(mTuner == nullptr, "Failed to get ITuner service");
Hongguang093c5f32021-08-09 19:46:34 -070069 mTunerVersion = TUNER_HAL_VERSION_1_0;
70
71 mTuner_1_1 = ::android::hardware::tv::tuner::V1_1::ITuner::castFrom(mTuner);
72 if (mTuner_1_1 != nullptr) {
73 mTunerVersion = TUNER_HAL_VERSION_1_1;
74 } else {
75 ALOGD("Failed to get ITuner_1_1 service");
76 }
77
Hongguang5eef5142022-08-09 20:26:42 -070078 // Register tuner resources to TRM.
79 updateTunerResources();
Hongguang093c5f32021-08-09 19:46:34 -070080}
81
Hongguang5eef5142022-08-09 20:26:42 -070082TunerHidlService::~TunerHidlService() {
83 mOpenedFrontends.clear();
84 mLnaStatus = -1;
85 mTuner = nullptr;
86 mTuner_1_1 = nullptr;
87}
88
89binder_status_t TunerHidlService::instantiate() {
90 if (HidlITuner::getService() == nullptr) {
91 ALOGD("Failed to get ITuner HIDL HAL");
92 return STATUS_NAME_NOT_FOUND;
93 }
94
95 shared_ptr<TunerHidlService> tunerService = ::ndk::SharedRefBase::make<TunerHidlService>();
96 bool lazyHal = property_get_bool("ro.tuner.lazyhal", false);
97 if (lazyHal) {
98 return AServiceManager_registerLazyService(tunerService->asBinder().get(),
99 getServiceName());
100 }
101 return AServiceManager_addService(tunerService->asBinder().get(), getServiceName());
Hongguang093c5f32021-08-09 19:46:34 -0700102}
103
104::ndk::ScopedAStatus TunerHidlService::openDemux(int32_t /* in_demuxHandle */,
105 shared_ptr<ITunerDemux>* _aidl_return) {
106 ALOGV("openDemux");
Hongguang093c5f32021-08-09 19:46:34 -0700107 HidlResult res;
108 uint32_t id;
109 sp<IDemux> demuxSp = nullptr;
110 mTuner->openDemux([&](HidlResult r, uint32_t demuxId, const sp<IDemux>& demux) {
111 demuxSp = demux;
112 id = demuxId;
113 res = r;
114 ALOGD("open demux, id = %d", demuxId);
115 });
116 if (res == HidlResult::SUCCESS) {
Hongguang5eef5142022-08-09 20:26:42 -0700117 *_aidl_return = ::ndk::SharedRefBase::make<TunerHidlDemux>(demuxSp, id,
118 this->ref<TunerHidlService>());
Hongguang093c5f32021-08-09 19:46:34 -0700119 return ::ndk::ScopedAStatus::ok();
120 }
121
122 ALOGW("open demux failed, res = %d", res);
123 return ::ndk::ScopedAStatus::fromServiceSpecificError(static_cast<int32_t>(res));
124}
125
126::ndk::ScopedAStatus TunerHidlService::getDemuxCaps(DemuxCapabilities* _aidl_return) {
127 ALOGV("getDemuxCaps");
Hongguang093c5f32021-08-09 19:46:34 -0700128 HidlResult res;
129 HidlDemuxCapabilities caps;
130 mTuner->getDemuxCaps([&](HidlResult r, const HidlDemuxCapabilities& demuxCaps) {
131 caps = demuxCaps;
132 res = r;
133 });
134 if (res == HidlResult::SUCCESS) {
135 *_aidl_return = getAidlDemuxCaps(caps);
136 return ::ndk::ScopedAStatus::ok();
137 }
138
139 ALOGW("Get demux caps failed, res = %d", res);
140 return ::ndk::ScopedAStatus::fromServiceSpecificError(static_cast<int32_t>(res));
141}
142
143::ndk::ScopedAStatus TunerHidlService::getFrontendIds(vector<int32_t>* ids) {
Hongguang093c5f32021-08-09 19:46:34 -0700144 hidl_vec<HidlFrontendId> feIds;
145 HidlResult res = getHidlFrontendIds(feIds);
146 if (res != HidlResult::SUCCESS) {
147 return ::ndk::ScopedAStatus::fromServiceSpecificError(static_cast<int32_t>(res));
148 }
149 ids->resize(feIds.size());
150 copy(feIds.begin(), feIds.end(), ids->begin());
151
152 return ::ndk::ScopedAStatus::ok();
153}
154
155::ndk::ScopedAStatus TunerHidlService::getFrontendInfo(int32_t id, FrontendInfo* _aidl_return) {
Hongguang093c5f32021-08-09 19:46:34 -0700156 HidlFrontendInfo info;
157 HidlResult res = getHidlFrontendInfo(id, info);
158 if (res != HidlResult::SUCCESS) {
159 return ::ndk::ScopedAStatus::fromServiceSpecificError(static_cast<int32_t>(res));
160 }
161
162 HidlFrontendDtmbCapabilities dtmbCaps;
163 if (static_cast<HidlFrontendType>(info.type) == HidlFrontendType::DTMB) {
Hongguang5eef5142022-08-09 20:26:42 -0700164 if (mTuner_1_1 == nullptr) {
Hongguang093c5f32021-08-09 19:46:34 -0700165 ALOGE("ITuner_1_1 service is not init.");
166 return ::ndk::ScopedAStatus::fromServiceSpecificError(
167 static_cast<int32_t>(Result::UNAVAILABLE));
168 }
169
170 mTuner_1_1->getFrontendDtmbCapabilities(
171 id, [&](HidlResult r, const HidlFrontendDtmbCapabilities& caps) {
172 dtmbCaps = caps;
173 res = r;
174 });
175 if (res != HidlResult::SUCCESS) {
176 return ::ndk::ScopedAStatus::fromServiceSpecificError(static_cast<int32_t>(res));
177 }
178 }
179
180 *_aidl_return = getAidlFrontendInfo(info, dtmbCaps);
181 return ::ndk::ScopedAStatus::ok();
182}
183
184::ndk::ScopedAStatus TunerHidlService::openFrontend(int32_t frontendHandle,
185 shared_ptr<ITunerFrontend>* _aidl_return) {
Hongguang093c5f32021-08-09 19:46:34 -0700186 HidlResult status;
187 sp<HidlIFrontend> frontend;
188 int id = TunerHelper::getResourceIdFromHandle(frontendHandle, FRONTEND);
189 mTuner->openFrontendById(id, [&](HidlResult result, const sp<HidlIFrontend>& fe) {
190 frontend = fe;
191 status = result;
192 });
193 if (status != HidlResult::SUCCESS) {
194 return ::ndk::ScopedAStatus::fromServiceSpecificError(static_cast<int32_t>(status));
195 }
Hongguangd8ccaae2021-12-13 18:07:10 -0800196
Hongguang5eef5142022-08-09 20:26:42 -0700197 shared_ptr<TunerHidlFrontend> tunerFrontend = ::ndk::SharedRefBase::make<TunerHidlFrontend>(
198 frontend, id, this->ref<TunerHidlService>());
Hongguangd8ccaae2021-12-13 18:07:10 -0800199 if (mLnaStatus != -1) {
200 tunerFrontend->setLna(mLnaStatus == 1);
201 }
202 {
203 Mutex::Autolock _l(mOpenedFrontendsLock);
204 mOpenedFrontends.insert(tunerFrontend);
205 }
206 *_aidl_return = tunerFrontend;
Hongguang093c5f32021-08-09 19:46:34 -0700207 return ::ndk::ScopedAStatus::ok();
208}
209
210::ndk::ScopedAStatus TunerHidlService::openLnb(int lnbHandle, shared_ptr<ITunerLnb>* _aidl_return) {
Hongguang093c5f32021-08-09 19:46:34 -0700211 HidlResult status;
212 sp<HidlILnb> lnb;
213 int id = TunerHelper::getResourceIdFromHandle(lnbHandle, LNB);
214 mTuner->openLnbById(id, [&](HidlResult result, const sp<HidlILnb>& lnbSp) {
215 lnb = lnbSp;
216 status = result;
217 });
218 if (status != HidlResult::SUCCESS) {
219 return ::ndk::ScopedAStatus::fromServiceSpecificError(static_cast<int32_t>(status));
220 }
221
222 *_aidl_return = ::ndk::SharedRefBase::make<TunerHidlLnb>(lnb, id);
223 return ::ndk::ScopedAStatus::ok();
224}
225
226::ndk::ScopedAStatus TunerHidlService::openLnbByName(const string& lnbName,
227 shared_ptr<ITunerLnb>* _aidl_return) {
Hongguang093c5f32021-08-09 19:46:34 -0700228 int lnbId;
229 HidlResult status;
230 sp<HidlILnb> lnb;
231 mTuner->openLnbByName(lnbName, [&](HidlResult r, HidlLnbId id, const sp<HidlILnb>& lnbSp) {
232 status = r;
233 lnb = lnbSp;
234 lnbId = static_cast<int32_t>(id);
235 });
236 if (status != HidlResult::SUCCESS) {
237 return ::ndk::ScopedAStatus::fromServiceSpecificError(static_cast<int32_t>(status));
238 }
239
240 *_aidl_return = ::ndk::SharedRefBase::make<TunerHidlLnb>(lnb, lnbId);
241 return ::ndk::ScopedAStatus::ok();
242}
243
244::ndk::ScopedAStatus TunerHidlService::openDescrambler(
245 int32_t /*descramblerHandle*/, shared_ptr<ITunerDescrambler>* _aidl_return) {
Hongguang093c5f32021-08-09 19:46:34 -0700246 HidlResult status;
247 sp<HidlIDescrambler> descrambler;
248 //int id = TunerHelper::getResourceIdFromHandle(descramblerHandle, DESCRAMBLER);
249 mTuner->openDescrambler([&](HidlResult r, const sp<HidlIDescrambler>& descramblerSp) {
250 status = r;
251 descrambler = descramblerSp;
252 });
253 if (status != HidlResult::SUCCESS) {
254 return ::ndk::ScopedAStatus::fromServiceSpecificError(static_cast<int32_t>(status));
255 }
256
257 *_aidl_return = ::ndk::SharedRefBase::make<TunerHidlDescrambler>(descrambler);
258 return ::ndk::ScopedAStatus::ok();
259}
260
261::ndk::ScopedAStatus TunerHidlService::getTunerHalVersion(int* _aidl_return) {
Hongguang093c5f32021-08-09 19:46:34 -0700262 *_aidl_return = mTunerVersion;
263 return ::ndk::ScopedAStatus::ok();
264}
265
Hongguang34a479e2021-10-04 16:14:47 -0700266::ndk::ScopedAStatus TunerHidlService::openSharedFilter(
267 const string& in_filterToken, const shared_ptr<ITunerFilterCallback>& in_cb,
268 shared_ptr<ITunerFilter>* _aidl_return) {
Hongguang5eef5142022-08-09 20:26:42 -0700269 if (mTuner == nullptr) {
Hongguang34a479e2021-10-04 16:14:47 -0700270 ALOGE("get ITuner failed");
271 return ::ndk::ScopedAStatus::fromServiceSpecificError(
272 static_cast<int32_t>(Result::UNAVAILABLE));
273 }
274
275 if (!PermissionCache::checkCallingPermission(sSharedFilterPermission)) {
276 ALOGE("Request requires android.permission.ACCESS_TV_SHARED_FILTER");
277 return ::ndk::ScopedAStatus::fromServiceSpecificError(
278 static_cast<int32_t>(Result::UNAVAILABLE));
279 }
280
281 Mutex::Autolock _l(mSharedFiltersLock);
282 if (mSharedFilters.find(in_filterToken) == mSharedFilters.end()) {
283 *_aidl_return = nullptr;
284 ALOGD("fail to find %s", in_filterToken.c_str());
285 return ::ndk::ScopedAStatus::fromServiceSpecificError(
286 static_cast<int32_t>(Result::INVALID_STATE));
287 }
288
289 shared_ptr<TunerHidlFilter> filter = mSharedFilters.at(in_filterToken);
290 IPCThreadState* ipc = IPCThreadState::self();
291 const int pid = ipc->getCallingPid();
292 if (!filter->isSharedFilterAllowed(pid)) {
293 *_aidl_return = nullptr;
294 ALOGD("shared filter %s is opened in the same process", in_filterToken.c_str());
295 return ::ndk::ScopedAStatus::fromServiceSpecificError(
296 static_cast<int32_t>(Result::INVALID_STATE));
297 }
298
299 filter->attachSharedFilterCallback(in_cb);
300
301 *_aidl_return = filter;
302 return ::ndk::ScopedAStatus::ok();
303}
304
Ray China9cb8652022-11-01 11:50:46 +0800305::ndk::ScopedAStatus TunerHidlService::isLnaSupported(bool* /* _aidl_return */) {
306 return ::ndk::ScopedAStatus::fromServiceSpecificError(
307 static_cast<int32_t>(Result::UNAVAILABLE));
308}
309
Hongguangd8ccaae2021-12-13 18:07:10 -0800310::ndk::ScopedAStatus TunerHidlService::setLna(bool bEnable) {
Hongguang5eef5142022-08-09 20:26:42 -0700311 if (mTuner == nullptr) {
Hongguangd8ccaae2021-12-13 18:07:10 -0800312 ALOGE("get ITuner failed");
313 return ::ndk::ScopedAStatus::fromServiceSpecificError(
314 static_cast<int32_t>(Result::UNAVAILABLE));
315 }
316
317 mLnaStatus = bEnable ? 1 : 0;
318
319 {
320 Mutex::Autolock _l(mOpenedFrontendsLock);
321 for (auto it = mOpenedFrontends.begin(); it != mOpenedFrontends.end(); ++it) {
322 (*it)->setLna(mLnaStatus == 1);
323 }
324 }
325
326 return ::ndk::ScopedAStatus::ok();
327}
328
Hongguang9fc18a92021-12-22 15:15:04 -0800329::ndk::ScopedAStatus TunerHidlService::setMaxNumberOfFrontends(FrontendType /* in_frontendType */,
330 int32_t /* in_maxNumber */) {
331 return ::ndk::ScopedAStatus::fromServiceSpecificError(
332 static_cast<int32_t>(Result::UNAVAILABLE));
333}
334
335::ndk::ScopedAStatus TunerHidlService::getMaxNumberOfFrontends(FrontendType /* in_frontendType */,
336 int32_t* _aidl_return) {
337 *_aidl_return = -1;
338 return ::ndk::ScopedAStatus::fromServiceSpecificError(
339 static_cast<int32_t>(Result::UNAVAILABLE));
340}
341
Hongguang34a479e2021-10-04 16:14:47 -0700342string TunerHidlService::addFilterToShared(const shared_ptr<TunerHidlFilter>& sharedFilter) {
343 Mutex::Autolock _l(mSharedFiltersLock);
344
345 // Use sharedFilter address as token.
346 string token = to_string(reinterpret_cast<std::uintptr_t>(sharedFilter.get()));
347 mSharedFilters[token] = sharedFilter;
348
349 return token;
350}
351
352void TunerHidlService::removeSharedFilter(const shared_ptr<TunerHidlFilter>& sharedFilter) {
353 Mutex::Autolock _l(mSharedFiltersLock);
354
355 // Use sharedFilter address as token.
356 mSharedFilters.erase(to_string(reinterpret_cast<std::uintptr_t>(sharedFilter.get())));
357}
358
Hongguangd8ccaae2021-12-13 18:07:10 -0800359void TunerHidlService::removeFrontend(const shared_ptr<TunerHidlFrontend>& frontend) {
360 Mutex::Autolock _l(mOpenedFrontendsLock);
361 for (auto it = mOpenedFrontends.begin(); it != mOpenedFrontends.end(); ++it) {
362 if (it->get() == frontend.get()) {
363 mOpenedFrontends.erase(it);
364 break;
365 }
366 }
367}
368
Hongguang093c5f32021-08-09 19:46:34 -0700369void TunerHidlService::updateTunerResources() {
Hongguang093c5f32021-08-09 19:46:34 -0700370 TunerHelper::updateTunerResources(getTRMFrontendInfos(), getTRMLnbHandles());
371}
372
373vector<TunerFrontendInfo> TunerHidlService::getTRMFrontendInfos() {
374 vector<TunerFrontendInfo> infos;
375 hidl_vec<HidlFrontendId> ids;
376 HidlResult res = getHidlFrontendIds(ids);
377 if (res != HidlResult::SUCCESS) {
378 return infos;
379 }
380
381 for (int i = 0; i < ids.size(); i++) {
382 HidlFrontendInfo frontendInfo;
383 HidlResult res = getHidlFrontendInfo(static_cast<int32_t>(ids[i]), frontendInfo);
384 if (res != HidlResult::SUCCESS) {
385 continue;
386 }
387 TunerFrontendInfo tunerFrontendInfo{
388 .handle = TunerHelper::getResourceHandleFromId(static_cast<int32_t>(ids[i]),
389 FRONTEND),
390 .type = static_cast<int32_t>(frontendInfo.type),
391 .exclusiveGroupId = static_cast<int32_t>(frontendInfo.exclusiveGroupId),
392 };
393 infos.push_back(tunerFrontendInfo);
394 }
395
396 return infos;
397}
398
399vector<int32_t> TunerHidlService::getTRMLnbHandles() {
400 vector<int32_t> lnbHandles;
401 if (mTuner != nullptr) {
402 HidlResult res;
403 vector<HidlLnbId> lnbIds;
404 mTuner->getLnbIds([&](HidlResult r, const hidl_vec<HidlLnbId>& ids) {
405 lnbIds = ids;
406 res = r;
407 });
408 if (res == HidlResult::SUCCESS && lnbIds.size() > 0) {
409 for (int i = 0; i < lnbIds.size(); i++) {
410 lnbHandles.push_back(
411 TunerHelper::getResourceHandleFromId(static_cast<int32_t>(lnbIds[i]), LNB));
412 }
413 }
414 }
415
416 return lnbHandles;
417}
418
419HidlResult TunerHidlService::getHidlFrontendIds(hidl_vec<HidlFrontendId>& ids) {
420 if (mTuner == nullptr) {
421 return HidlResult::NOT_INITIALIZED;
422 }
423 HidlResult res;
424 mTuner->getFrontendIds([&](HidlResult r, const hidl_vec<HidlFrontendId>& frontendIds) {
425 ids = frontendIds;
426 res = r;
427 });
428 return res;
429}
430
431HidlResult TunerHidlService::getHidlFrontendInfo(const int id, HidlFrontendInfo& info) {
432 if (mTuner == nullptr) {
433 return HidlResult::NOT_INITIALIZED;
434 }
435 HidlResult res;
436 mTuner->getFrontendInfo(id, [&](HidlResult r, const HidlFrontendInfo& feInfo) {
437 info = feInfo;
438 res = r;
439 });
440 return res;
441}
442
443DemuxCapabilities TunerHidlService::getAidlDemuxCaps(const HidlDemuxCapabilities& caps) {
444 DemuxCapabilities aidlCaps{
445 .numDemux = static_cast<int32_t>(caps.numDemux),
446 .numRecord = static_cast<int32_t>(caps.numRecord),
447 .numPlayback = static_cast<int32_t>(caps.numPlayback),
448 .numTsFilter = static_cast<int32_t>(caps.numTsFilter),
449 .numSectionFilter = static_cast<int32_t>(caps.numSectionFilter),
450 .numAudioFilter = static_cast<int32_t>(caps.numAudioFilter),
451 .numVideoFilter = static_cast<int32_t>(caps.numVideoFilter),
452 .numPesFilter = static_cast<int32_t>(caps.numPesFilter),
453 .numPcrFilter = static_cast<int32_t>(caps.numPcrFilter),
454 .numBytesInSectionFilter = static_cast<int64_t>(caps.numBytesInSectionFilter),
455 .filterCaps = static_cast<int32_t>(caps.filterCaps),
456 .bTimeFilter = caps.bTimeFilter,
457 };
458 aidlCaps.linkCaps.resize(caps.linkCaps.size());
459 copy(caps.linkCaps.begin(), caps.linkCaps.end(), aidlCaps.linkCaps.begin());
460 return aidlCaps;
461}
462
463FrontendInfo TunerHidlService::getAidlFrontendInfo(
464 const HidlFrontendInfo& halInfo, const HidlFrontendDtmbCapabilities& halDtmbCaps) {
465 FrontendInfo info{
466 .type = static_cast<FrontendType>(halInfo.type),
467 .minFrequency = static_cast<int64_t>(halInfo.minFrequency),
468 .maxFrequency = static_cast<int64_t>(halInfo.maxFrequency),
469 .minSymbolRate = static_cast<int32_t>(halInfo.minSymbolRate),
470 .maxSymbolRate = static_cast<int32_t>(halInfo.maxSymbolRate),
471 .acquireRange = static_cast<int64_t>(halInfo.acquireRange),
472 .exclusiveGroupId = static_cast<int32_t>(halInfo.exclusiveGroupId),
473 };
474 for (int i = 0; i < halInfo.statusCaps.size(); i++) {
475 info.statusCaps.push_back(static_cast<FrontendStatusType>(halInfo.statusCaps[i]));
476 }
477
478 FrontendCapabilities caps;
479 switch (halInfo.type) {
480 case ::android::hardware::tv::tuner::V1_0::FrontendType::ANALOG: {
481 if (HidlFrontendInfo::FrontendCapabilities::hidl_discriminator::analogCaps ==
482 halInfo.frontendCaps.getDiscriminator()) {
483 FrontendAnalogCapabilities analogCaps{
484 .typeCap = static_cast<int32_t>(halInfo.frontendCaps.analogCaps().typeCap),
485 .sifStandardCap =
486 static_cast<int32_t>(halInfo.frontendCaps.analogCaps().sifStandardCap),
487 };
488 caps.set<FrontendCapabilities::analogCaps>(analogCaps);
489 }
490 break;
491 }
492 case ::android::hardware::tv::tuner::V1_0::FrontendType::ATSC: {
493 if (HidlFrontendInfo::FrontendCapabilities::hidl_discriminator::atscCaps ==
494 halInfo.frontendCaps.getDiscriminator()) {
495 FrontendAtscCapabilities atscCaps{
496 .modulationCap =
497 static_cast<int32_t>(halInfo.frontendCaps.atscCaps().modulationCap),
498 };
499 caps.set<FrontendCapabilities::atscCaps>(atscCaps);
500 }
501 break;
502 }
503 case ::android::hardware::tv::tuner::V1_0::FrontendType::ATSC3: {
504 if (HidlFrontendInfo::FrontendCapabilities::hidl_discriminator::atsc3Caps ==
505 halInfo.frontendCaps.getDiscriminator()) {
506 FrontendAtsc3Capabilities atsc3Caps{
507 .bandwidthCap =
508 static_cast<int32_t>(halInfo.frontendCaps.atsc3Caps().bandwidthCap),
509 .modulationCap =
510 static_cast<int32_t>(halInfo.frontendCaps.atsc3Caps().modulationCap),
511 .timeInterleaveModeCap = static_cast<int32_t>(
512 halInfo.frontendCaps.atsc3Caps().timeInterleaveModeCap),
513 .codeRateCap =
514 static_cast<int32_t>(halInfo.frontendCaps.atsc3Caps().codeRateCap),
515 .demodOutputFormatCap = static_cast<int8_t>(
516 halInfo.frontendCaps.atsc3Caps().demodOutputFormatCap),
517 .fecCap = static_cast<int32_t>(halInfo.frontendCaps.atsc3Caps().fecCap),
518 };
519 caps.set<FrontendCapabilities::atsc3Caps>(atsc3Caps);
520 }
521 break;
522 }
523 case ::android::hardware::tv::tuner::V1_0::FrontendType::DVBC: {
524 if (HidlFrontendInfo::FrontendCapabilities::hidl_discriminator::dvbcCaps ==
525 halInfo.frontendCaps.getDiscriminator()) {
526 FrontendDvbcCapabilities dvbcCaps{
527 .modulationCap =
528 static_cast<int32_t>(halInfo.frontendCaps.dvbcCaps().modulationCap),
529 .fecCap = static_cast<int64_t>(halInfo.frontendCaps.dvbcCaps().fecCap),
530 .annexCap = static_cast<int8_t>(halInfo.frontendCaps.dvbcCaps().annexCap),
531 };
532 caps.set<FrontendCapabilities::dvbcCaps>(dvbcCaps);
533 }
534 break;
535 }
536 case ::android::hardware::tv::tuner::V1_0::FrontendType::DVBS: {
537 if (HidlFrontendInfo::FrontendCapabilities::hidl_discriminator::dvbsCaps ==
538 halInfo.frontendCaps.getDiscriminator()) {
539 FrontendDvbsCapabilities dvbsCaps{
540 .modulationCap =
541 static_cast<int32_t>(halInfo.frontendCaps.dvbsCaps().modulationCap),
542 .innerfecCap =
543 static_cast<int64_t>(halInfo.frontendCaps.dvbsCaps().innerfecCap),
544 .standard = static_cast<int8_t>(halInfo.frontendCaps.dvbsCaps().standard),
545 };
546 caps.set<FrontendCapabilities::dvbsCaps>(dvbsCaps);
547 }
548 break;
549 }
550 case ::android::hardware::tv::tuner::V1_0::FrontendType::DVBT: {
551 if (HidlFrontendInfo::FrontendCapabilities::hidl_discriminator::dvbtCaps ==
552 halInfo.frontendCaps.getDiscriminator()) {
553 FrontendDvbtCapabilities dvbtCaps{
554 .transmissionModeCap = static_cast<int32_t>(
555 halInfo.frontendCaps.dvbtCaps().transmissionModeCap),
556 .bandwidthCap =
557 static_cast<int32_t>(halInfo.frontendCaps.dvbtCaps().bandwidthCap),
558 .constellationCap =
559 static_cast<int32_t>(halInfo.frontendCaps.dvbtCaps().constellationCap),
560 .coderateCap =
561 static_cast<int32_t>(halInfo.frontendCaps.dvbtCaps().coderateCap),
562 .hierarchyCap =
563 static_cast<int32_t>(halInfo.frontendCaps.dvbtCaps().hierarchyCap),
564 .guardIntervalCap =
565 static_cast<int32_t>(halInfo.frontendCaps.dvbtCaps().guardIntervalCap),
566 .isT2Supported = halInfo.frontendCaps.dvbtCaps().isT2Supported,
567 .isMisoSupported = halInfo.frontendCaps.dvbtCaps().isMisoSupported,
568 };
569 caps.set<FrontendCapabilities::dvbtCaps>(dvbtCaps);
570 }
571 break;
572 }
573 case ::android::hardware::tv::tuner::V1_0::FrontendType::ISDBS: {
574 if (HidlFrontendInfo::FrontendCapabilities::hidl_discriminator::isdbsCaps ==
575 halInfo.frontendCaps.getDiscriminator()) {
576 FrontendIsdbsCapabilities isdbsCaps{
577 .modulationCap =
578 static_cast<int32_t>(halInfo.frontendCaps.isdbsCaps().modulationCap),
579 .coderateCap =
580 static_cast<int32_t>(halInfo.frontendCaps.isdbsCaps().coderateCap),
581 };
582 caps.set<FrontendCapabilities::isdbsCaps>(isdbsCaps);
583 }
584 break;
585 }
586 case ::android::hardware::tv::tuner::V1_0::FrontendType::ISDBS3: {
587 if (HidlFrontendInfo::FrontendCapabilities::hidl_discriminator::isdbs3Caps ==
588 halInfo.frontendCaps.getDiscriminator()) {
589 FrontendIsdbs3Capabilities isdbs3Caps{
590 .modulationCap =
591 static_cast<int32_t>(halInfo.frontendCaps.isdbs3Caps().modulationCap),
592 .coderateCap =
593 static_cast<int32_t>(halInfo.frontendCaps.isdbs3Caps().coderateCap),
594 };
595 caps.set<FrontendCapabilities::isdbs3Caps>(isdbs3Caps);
596 }
597 break;
598 }
599 case ::android::hardware::tv::tuner::V1_0::FrontendType::ISDBT: {
600 if (HidlFrontendInfo::FrontendCapabilities::hidl_discriminator::isdbtCaps ==
601 halInfo.frontendCaps.getDiscriminator()) {
602 FrontendIsdbtCapabilities isdbtCaps{
603 .modeCap = static_cast<int32_t>(halInfo.frontendCaps.isdbtCaps().modeCap),
604 .bandwidthCap =
605 static_cast<int32_t>(halInfo.frontendCaps.isdbtCaps().bandwidthCap),
606 .modulationCap =
607 static_cast<int32_t>(halInfo.frontendCaps.isdbtCaps().modulationCap),
608 .coderateCap =
609 static_cast<int32_t>(halInfo.frontendCaps.isdbtCaps().coderateCap),
610 .guardIntervalCap =
611 static_cast<int32_t>(halInfo.frontendCaps.isdbtCaps().guardIntervalCap),
Hongguang15758a82021-10-29 13:32:07 -0700612 .timeInterleaveCap =
613 static_cast<int32_t>(FrontendIsdbtTimeInterleaveMode::UNDEFINED),
614 .isSegmentAuto = false,
615 .isFullSegment = false,
Hongguang093c5f32021-08-09 19:46:34 -0700616 };
617 caps.set<FrontendCapabilities::isdbtCaps>(isdbtCaps);
618 }
619 break;
620 }
621 default: {
622 if (static_cast<HidlFrontendType>(info.type) == HidlFrontendType::DTMB) {
623 FrontendDtmbCapabilities dtmbCaps{
624 .transmissionModeCap = static_cast<int32_t>(halDtmbCaps.transmissionModeCap),
625 .bandwidthCap = static_cast<int32_t>(halDtmbCaps.bandwidthCap),
626 .modulationCap = static_cast<int32_t>(halDtmbCaps.modulationCap),
627 .codeRateCap = static_cast<int32_t>(halDtmbCaps.codeRateCap),
628 .guardIntervalCap = static_cast<int32_t>(halDtmbCaps.guardIntervalCap),
629 .interleaveModeCap = static_cast<int32_t>(halDtmbCaps.interleaveModeCap),
630 };
631 caps.set<FrontendCapabilities::dtmbCaps>(dtmbCaps);
632 }
633 break;
634 }
635 }
636
637 info.frontendCaps = caps;
638 return info;
639}
640
641} // namespace tuner
642} // namespace tv
643} // namespace media
644} // namespace android
645} // namespace aidl