1 /*
2 * Copyright 2020 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_TAG "DemuxClient"
18
19 #include <android-base/logging.h>
20 #include <utils/Log.h>
21
22 #include "DemuxClient.h"
23
24 using ::aidl::android::media::tv::tuner::TunerFrontendSettings;
25
26 using ::android::hardware::tv::tuner::V1_0::DemuxFilterMainType;
27 using ::android::hardware::tv::tuner::V1_0::Result;
28
29 namespace android {
30
31 /////////////// DemuxClient ///////////////////////
32
DemuxClient(shared_ptr<ITunerDemux> tunerDemux)33 DemuxClient::DemuxClient(shared_ptr<ITunerDemux> tunerDemux) {
34 mTunerDemux = tunerDemux;
35 mId = -1;
36 }
37
~DemuxClient()38 DemuxClient::~DemuxClient() {
39 mTunerDemux = NULL;
40 mDemux = NULL;
41 mId = -1;
42 }
43
44 // TODO: remove after migration to Tuner Service is done.
setHidlDemux(sp<IDemux> demux)45 void DemuxClient::setHidlDemux(sp<IDemux> demux) {
46 mDemux = demux;
47 }
48
setFrontendDataSource(sp<FrontendClient> frontendClient)49 Result DemuxClient::setFrontendDataSource(sp<FrontendClient> frontendClient) {
50 if (mTunerDemux != NULL) {
51 Status s = mTunerDemux->setFrontendDataSource(frontendClient->getAidlFrontend());
52 return ClientHelper::getServiceSpecificErrorCode(s);
53 }
54
55 if (mDemux != NULL) {
56 Result res = mDemux->setFrontendDataSource(frontendClient->getId());
57 return res;
58 }
59
60 return Result::INVALID_STATE;
61 }
62
openFilter(DemuxFilterType type,int bufferSize,sp<FilterClientCallback> cb)63 sp<FilterClient> DemuxClient::openFilter(DemuxFilterType type, int bufferSize,
64 sp<FilterClientCallback> cb) {
65 if (mTunerDemux != NULL) {
66 shared_ptr<ITunerFilter> tunerFilter;
67 shared_ptr<TunerFilterCallback> callback =
68 ::ndk::SharedRefBase::make<TunerFilterCallback>(cb);
69 Status s = mTunerDemux->openFilter((int)type.mainType, getSubType(type),
70 bufferSize, callback, &tunerFilter);
71 if (ClientHelper::getServiceSpecificErrorCode(s) != Result::SUCCESS) {
72 return NULL;
73 }
74 return new FilterClient(type, tunerFilter);
75 }
76
77 if (mDemux != NULL) {
78 sp<HidlFilterCallback> callback = new HidlFilterCallback(cb);
79 sp<IFilter> hidlFilter = openHidlFilter(type, bufferSize, callback);
80 if (hidlFilter != NULL) {
81 sp<FilterClient> filterClient = new FilterClient(type, NULL);
82 filterClient->setHidlFilter(hidlFilter);
83 return filterClient;
84 }
85 }
86
87 return NULL;
88 }
89
openTimeFilter()90 sp<TimeFilterClient> DemuxClient::openTimeFilter() {
91 if (mTunerDemux != NULL) {
92 shared_ptr<ITunerTimeFilter> tunerTimeFilter;
93 Status s = mTunerDemux->openTimeFilter(&tunerTimeFilter);
94 if (ClientHelper::getServiceSpecificErrorCode(s) != Result::SUCCESS) {
95 return NULL;
96 }
97 return new TimeFilterClient(tunerTimeFilter);
98 }
99
100 if (mDemux != NULL) {
101 sp<ITimeFilter> hidlTimeFilter = openHidlTimeFilter();
102 if (hidlTimeFilter != NULL) {
103 sp<TimeFilterClient> timeFilterClient = new TimeFilterClient(NULL);
104 timeFilterClient->setHidlTimeFilter(hidlTimeFilter);
105 return timeFilterClient;
106 }
107 }
108
109 return NULL;
110 }
111
getAvSyncHwId(sp<FilterClient> filterClient)112 int DemuxClient::getAvSyncHwId(sp<FilterClient> filterClient) {
113 if (mTunerDemux != NULL) {
114 int hwId;
115 Status s = mTunerDemux->getAvSyncHwId(filterClient->getAidlFilter(), &hwId);
116 if (ClientHelper::getServiceSpecificErrorCode(s) != Result::SUCCESS) {
117 return INVALID_AV_SYNC_HW_ID;
118 }
119 return hwId;
120 }
121
122 if (mDemux != NULL) {
123 uint32_t avSyncHwId;
124 Result res;
125 sp<IFilter> halFilter = filterClient->getHalFilter();
126 mDemux->getAvSyncHwId(halFilter,
127 [&](Result r, uint32_t id) {
128 res = r;
129 avSyncHwId = id;
130 });
131 if (res == Result::SUCCESS) {
132 return (int) avSyncHwId;
133 }
134 }
135
136 return INVALID_AV_SYNC_HW_ID;
137 }
138
getAvSyncTime(int avSyncHwId)139 long DemuxClient::getAvSyncTime(int avSyncHwId) {
140 if (mTunerDemux != NULL) {
141 int64_t time;
142 Status s = mTunerDemux->getAvSyncTime(avSyncHwId, &time);
143 if (ClientHelper::getServiceSpecificErrorCode(s) != Result::SUCCESS) {
144 return INVALID_AV_SYNC_TIME;
145 }
146 return time;
147 }
148
149 if (mDemux != NULL) {
150 uint64_t time;
151 Result res;
152 mDemux->getAvSyncTime(static_cast<uint32_t>(avSyncHwId),
153 [&](Result r, uint64_t ts) {
154 res = r;
155 time = ts;
156 });
157 if (res == Result::SUCCESS) {
158 return (long) time;
159 }
160 }
161
162 return INVALID_AV_SYNC_TIME;
163 }
164
openDvr(DvrType dvbType,int bufferSize,sp<DvrClientCallback> cb)165 sp<DvrClient> DemuxClient::openDvr(DvrType dvbType, int bufferSize, sp<DvrClientCallback> cb) {
166 if (mTunerDemux != NULL) {
167 shared_ptr<ITunerDvr> tunerDvr;
168 shared_ptr<TunerDvrCallback> callback =
169 ::ndk::SharedRefBase::make<TunerDvrCallback>(cb);
170 Status s = mTunerDemux->openDvr((int)dvbType, bufferSize, callback, &tunerDvr);
171 if (ClientHelper::getServiceSpecificErrorCode(s) != Result::SUCCESS) {
172 return NULL;
173 }
174 return new DvrClient(tunerDvr);
175 }
176
177 if (mDemux != NULL) {
178 sp<HidlDvrCallback> callback = new HidlDvrCallback(cb);
179 sp<IDvr> hidlDvr = openHidlDvr(dvbType, bufferSize, callback);
180 if (hidlDvr != NULL) {
181 sp<DvrClient> dvrClient = new DvrClient(NULL);
182 dvrClient->setHidlDvr(hidlDvr);
183 return dvrClient;
184 }
185 }
186
187 return NULL;
188 }
189
connectCiCam(int ciCamId)190 Result DemuxClient::connectCiCam(int ciCamId) {
191 if (mTunerDemux != NULL) {
192 Status s = mTunerDemux->connectCiCam(ciCamId);
193 return ClientHelper::getServiceSpecificErrorCode(s);
194 }
195
196 if (mDemux != NULL) {
197 return mDemux->connectCiCam(static_cast<uint32_t>(ciCamId));
198 }
199
200 return Result::INVALID_STATE;
201 }
202
disconnectCiCam()203 Result DemuxClient::disconnectCiCam() {
204 if (mTunerDemux != NULL) {
205 Status s = mTunerDemux->disconnectCiCam();
206 return ClientHelper::getServiceSpecificErrorCode(s);
207 }
208
209 if (mDemux != NULL) {
210 return mDemux->disconnectCiCam();
211 }
212
213 return Result::INVALID_STATE;
214 }
215
close()216 Result DemuxClient::close() {
217 if (mTunerDemux != NULL) {
218 Status s = mTunerDemux->close();
219 mTunerDemux = NULL;
220 return ClientHelper::getServiceSpecificErrorCode(s);
221 }
222
223 if (mDemux != NULL) {
224 Result res = mDemux->close();
225 mDemux = NULL;
226 return res;
227 }
228
229 return Result::INVALID_STATE;
230 }
231
232 /////////////// DemuxClient Helper Methods ///////////////////////
233
openHidlFilter(DemuxFilterType type,int bufferSize,sp<HidlFilterCallback> callback)234 sp<IFilter> DemuxClient::openHidlFilter(DemuxFilterType type, int bufferSize,
235 sp<HidlFilterCallback> callback) {
236 if (mDemux == NULL) {
237 return NULL;
238 }
239
240 sp<IFilter> hidlFilter;
241 Result res;
242 mDemux->openFilter(type, bufferSize, callback,
243 [&](Result r, const sp<IFilter>& filter) {
244 hidlFilter = filter;
245 res = r;
246 });
247 if (res != Result::SUCCESS || hidlFilter == NULL) {
248 return NULL;
249 }
250
251 return hidlFilter;
252 }
253
openHidlTimeFilter()254 sp<ITimeFilter> DemuxClient::openHidlTimeFilter() {
255 if (mDemux == NULL) {
256 return NULL;
257 }
258
259 sp<ITimeFilter> timeFilter;
260 Result res;
261 mDemux->openTimeFilter(
262 [&](Result r, const sp<ITimeFilter>& timeFilterSp) {
263 timeFilter = timeFilterSp;
264 res = r;
265 });
266
267 if (res != Result::SUCCESS || timeFilter == NULL) {
268 return NULL;
269 }
270
271 return timeFilter;
272 }
273
openHidlDvr(DvrType dvrType,int bufferSize,sp<HidlDvrCallback> callback)274 sp<IDvr> DemuxClient::openHidlDvr(DvrType dvrType, int bufferSize,
275 sp<HidlDvrCallback> callback) {
276 if (mDemux == NULL) {
277 return NULL;
278 }
279
280 sp<IDvr> hidlDvr;
281 Result res;
282 mDemux->openDvr(dvrType, bufferSize, callback,
283 [&](Result r, const sp<IDvr>& dvr) {
284 hidlDvr = dvr;
285 res = r;
286 });
287 if (res != Result::SUCCESS || hidlDvr == NULL) {
288 return NULL;
289 }
290
291 return hidlDvr;
292 }
293
getSubType(DemuxFilterType filterType)294 int DemuxClient::getSubType(DemuxFilterType filterType) {
295 switch (filterType.mainType) {
296 case DemuxFilterMainType::TS:
297 return (int)filterType.subType.tsFilterType();
298 case DemuxFilterMainType::MMTP:
299 return (int)filterType.subType.mmtpFilterType();
300 case DemuxFilterMainType::IP:
301 return (int)filterType.subType.ipFilterType();
302 case DemuxFilterMainType::TLV:
303 return (int)filterType.subType.tlvFilterType();
304 case DemuxFilterMainType::ALP:
305 return (int)filterType.subType.alpFilterType();
306 default:
307 return -1;
308 }
309 }
310 } // namespace android
311