Implement TunerFrontendClientCallback in FrontendClient

Test: make libmedia_tv_tuner
Bug: 174095851
Change-Id: I5b7966887a395ef4cc4207b22fcb6c31676d8738
diff --git a/media/jni/tuner/FrontendClient.cpp b/media/jni/tuner/FrontendClient.cpp
index 14761a6..d6d64f6 100644
--- a/media/jni/tuner/FrontendClient.cpp
+++ b/media/jni/tuner/FrontendClient.cpp
@@ -21,18 +21,39 @@
 
 #include "FrontendClient.h"
 
+using ::aidl::android::media::tv::tuner::TunerFrontendScanAtsc3PlpInfo;
 using ::aidl::android::media::tv::tuner::TunerFrontendSettings;
+
+using ::android::hardware::tv::tuner::V1_0::FrontendAnalogSifStandard;
+using ::android::hardware::tv::tuner::V1_0::FrontendAnalogType;
+using ::android::hardware::tv::tuner::V1_0::FrontendAtscModulation;
+using ::android::hardware::tv::tuner::V1_0::FrontendAtsc3Modulation;
+using ::android::hardware::tv::tuner::V1_0::FrontendDvbcAnnex;
+using ::android::hardware::tv::tuner::V1_0::FrontendDvbcModulation;
+using ::android::hardware::tv::tuner::V1_0::FrontendDvbsModulation;
+using ::android::hardware::tv::tuner::V1_0::FrontendDvbsStandard;
+using ::android::hardware::tv::tuner::V1_0::FrontendDvbtHierarchy;
+using ::android::hardware::tv::tuner::V1_0::FrontendDvbtStandard;
+using ::android::hardware::tv::tuner::V1_0::FrontendIsdbsModulation;
+using ::android::hardware::tv::tuner::V1_0::FrontendIsdbs3Modulation;
+using ::android::hardware::tv::tuner::V1_0::FrontendIsdbtModulation;
+using ::android::hardware::tv::tuner::V1_0::FrontendScanAtsc3PlpInfo;
+using ::android::hardware::tv::tuner::V1_0::FrontendType;
 using ::android::hardware::tv::tuner::V1_1::Constant;
+using ::android::hardware::tv::tuner::V1_1::FrontendDtmbModulation;
+using ::android::hardware::tv::tuner::V1_1::FrontendDvbtConstellation;
+using ::android::hardware::tv::tuner::V1_1::FrontendModulation;
 
 namespace android {
 
 /////////////// FrontendClient ///////////////////////
 
-FrontendClient::FrontendClient(shared_ptr<ITunerFrontend> tunerFrontend, int id) {
+FrontendClient::FrontendClient(shared_ptr<ITunerFrontend> tunerFrontend, int id, int type) {
     mTunerFrontend = tunerFrontend;
     mAidlCallback = NULL;
     mHidlCallback = NULL;
     mId = id;
+    mType = type;
 }
 
 FrontendClient::~FrontendClient() {
@@ -42,11 +63,13 @@
     mAidlCallback = NULL;
     mHidlCallback = NULL;
     mId = -1;
+    mType = -1;
 }
 
 Result FrontendClient::setCallback(sp<FrontendClientCallback> frontendClientCallback) {
     if (mTunerFrontend != NULL) {
         mAidlCallback = ::ndk::SharedRefBase::make<TunerFrontendCallback>(frontendClientCallback);
+        mAidlCallback->setFrontendType(mType);
         mTunerFrontend->setCallback(mAidlCallback);
         return Result::SUCCESS;
     }
@@ -298,56 +321,21 @@
     return Status::fromServiceSpecificError(static_cast<int32_t>(Result::INVALID_STATE));
 }
 
-Status TunerFrontendCallback::onLocked() {
-    return Status::ok();
-}
-
-Status TunerFrontendCallback::onScanStopped() {
-    return Status::ok();
-}
-
-Status TunerFrontendCallback::onProgress(int /*percent*/) {
-    return Status::ok();
-}
-
-Status TunerFrontendCallback::onFrequenciesReport(const vector<int>& /*frequency*/) {
-    return Status::ok();
-}
-
-Status TunerFrontendCallback::onSymbolRates(const vector<int>& /*rates*/) {
-    return Status::ok();
-}
-
-Status TunerFrontendCallback::onHierarchy(int /*hierarchy*/) {
-    return Status::ok();
-}
-
-Status TunerFrontendCallback::onSignalType(int /*signalType*/) {
-    return Status::ok();
-}
-
-Status TunerFrontendCallback::onPlpIds(const vector<int>& /*plpIds*/) {
-    return Status::ok();
-}
-
-Status TunerFrontendCallback::onGroupIds(const vector<int>& /*groupIds*/) {
-    return Status::ok();
-}
-
-Status TunerFrontendCallback::onInputStreamIds(const vector<int>& /*inputStreamIds*/) {
-    return Status::ok();
-}
-
-Status TunerFrontendCallback::onDvbsStandard(int /*dvbsStandandard*/) {
-    return Status::ok();
-}
-
-Status TunerFrontendCallback::onAnalogSifStandard(int /*sifStandandard*/) {
-    return Status::ok();
-}
-
-Status TunerFrontendCallback::onAtsc3PlpInfos(const vector<TunerAtsc3PlpInfo>& /*atsc3PlpInfos*/) {
-    return Status::ok();
+Status TunerFrontendCallback::onScanMessage(int messageType,
+        const TunerFrontendScanMessage& message) {
+    if (mFrontendClientCallback != NULL) {
+        if (!is1_1ExtendedScanMessage(messageType)) {
+            mFrontendClientCallback->onScanMessage(
+                    static_cast<FrontendScanMessageType>(messageType),
+                    getHalScanMessage(messageType, message));
+        } else {
+            mFrontendClientCallback->onScanMessageExt1_1(
+                    static_cast<FrontendScanMessageTypeExt1_1>(messageType),
+                    getHalScanMessageExt1_1(messageType, message));
+        }
+        return Status::ok();
+    }
+    return Status::fromServiceSpecificError(static_cast<int32_t>(Result::INVALID_STATE));
 }
 
 /////////////// IFrontendCallback ///////////////////////
@@ -377,4 +365,167 @@
     }
     return Void();
 }
+
+/////////////// FrontendClientCallback Helper Methods ///////////////////////
+
+FrontendScanMessage TunerFrontendCallback::getHalScanMessage(
+        int messageType, const TunerFrontendScanMessage& message) {
+    FrontendScanMessage scanMessage;
+    switch (messageType) {
+        case (int) FrontendScanMessageType::LOCKED:
+            scanMessage.isLocked(message.get<TunerFrontendScanMessage::isLocked>());
+            break;
+        case (int) FrontendScanMessageType::END:
+            scanMessage.isEnd(message.get<TunerFrontendScanMessage::isEnd>());
+            break;
+        case (int) FrontendScanMessageType::PROGRESS_PERCENT:
+            scanMessage.progressPercent(message.get<TunerFrontendScanMessage::progressPercent>());
+            break;
+        case (int) FrontendScanMessageType::FREQUENCY: {
+            vector<int> f = message.get<TunerFrontendScanMessage::frequencies>();
+            hidl_vec<uint32_t> frequencies(begin(f), end(f));
+            scanMessage.frequencies(frequencies);
+            break;
+        }
+        case (int) FrontendScanMessageType::SYMBOL_RATE: {
+            vector<int> s = message.get<TunerFrontendScanMessage::symbolRates>();
+            hidl_vec<uint32_t> symbolRates(begin(s), end(s));
+            scanMessage.symbolRates(symbolRates);
+            break;
+        }
+        case (int) FrontendScanMessageType::HIERARCHY:
+            scanMessage.hierarchy(static_cast<FrontendDvbtHierarchy>(
+                    message.get<TunerFrontendScanMessage::hierarchy>()));
+            break;
+        case (int) FrontendScanMessageType::ANALOG_TYPE:
+            scanMessage.analogType(static_cast<FrontendAnalogType>(
+                    message.get<TunerFrontendScanMessage::analogType>()));
+            break;
+        case (int) FrontendScanMessageType::PLP_IDS: {
+            vector<uint8_t> p = message.get<TunerFrontendScanMessage::plpIds>();
+            hidl_vec<uint8_t> plpIds(begin(p), end(p));
+            scanMessage.plpIds(plpIds);
+            break;
+        }
+        case (int) FrontendScanMessageType::GROUP_IDS: {
+            vector<uint8_t> g = message.get<TunerFrontendScanMessage::groupIds>();
+            hidl_vec<uint8_t> groupIds(begin(g), end(g));
+            scanMessage.groupIds(groupIds);
+            break;
+        }
+        case (int) FrontendScanMessageType::INPUT_STREAM_IDS: {
+            vector<char16_t> i = message.get<TunerFrontendScanMessage::inputStreamIds>();
+            hidl_vec<uint16_t> inputStreamIds(begin(i), end(i));
+            scanMessage.inputStreamIds(inputStreamIds);
+            break;
+        }
+        case (int) FrontendScanMessageType::STANDARD: {
+            FrontendScanMessage::Standard std;
+            int standard = message.get<TunerFrontendScanMessage::std>();
+            switch (mType) {
+                case (int) FrontendType::DVBS:
+                    std.sStd(static_cast<FrontendDvbsStandard>(standard));
+                    scanMessage.std(std);
+                    break;
+                case (int) FrontendType::DVBT:
+                    std.tStd(static_cast<FrontendDvbtStandard>(standard));
+                    scanMessage.std(std);
+                    break;
+                case (int) FrontendType::ANALOG:
+                    std.sifStd(static_cast<FrontendAnalogSifStandard>(standard));
+                    scanMessage.std(std);
+                    break;
+                default:
+                    break;
+            }
+            break;
+        }
+        case (int) FrontendScanMessageType::ATSC3_PLP_INFO: {
+            vector<TunerFrontendScanAtsc3PlpInfo> plp =
+                    message.get<TunerFrontendScanMessage::atsc3PlpInfos>();
+            hidl_vec<FrontendScanAtsc3PlpInfo> plpInfo;
+            for (TunerFrontendScanAtsc3PlpInfo info : plp) {
+                FrontendScanAtsc3PlpInfo p{
+                    .plpId = static_cast<uint8_t>(info.plpId),
+                    .bLlsFlag = info.llsFlag,
+                };
+                int size = plpInfo.size();
+                plpInfo.resize(size + 1);
+                plpInfo[size] = p;
+            }
+            scanMessage.atsc3PlpInfos(plpInfo);
+            break;
+        }
+        default:
+            break;
+    }
+    return scanMessage;
+}
+
+FrontendScanMessageExt1_1 TunerFrontendCallback::getHalScanMessageExt1_1(
+        int messageType, const TunerFrontendScanMessage& message) {
+    FrontendScanMessageExt1_1 scanMessage;
+    switch (messageType) {
+        case (int) FrontendScanMessageTypeExt1_1::HIGH_PRIORITY:
+            scanMessage.isHighPriority(message.get<TunerFrontendScanMessage::isHighPriority>());
+            break;
+        case (int) FrontendScanMessageTypeExt1_1::DVBC_ANNEX:
+            scanMessage.annex(static_cast<FrontendDvbcAnnex>(
+                    message.get<TunerFrontendScanMessage::annex>()));
+            break;
+        case (int) FrontendScanMessageTypeExt1_1::MODULATION: {
+            FrontendModulation m;
+            int modulation = message.get<TunerFrontendScanMessage::modulation>();
+            switch (mType) {
+                case (int) FrontendType::DVBC:
+                    m.dvbc(static_cast<FrontendDvbcModulation>(modulation));
+                    scanMessage.modulation(m);
+                    break;
+                case (int) FrontendType::DVBS:
+                    m.dvbs(static_cast<FrontendDvbsModulation>(modulation));
+                    scanMessage.modulation(m);
+                    break;
+                case (int) FrontendType::DVBT:
+                    m.dvbt(static_cast<FrontendDvbtConstellation>(modulation));
+                    scanMessage.modulation(m);
+                    break;
+                case (int) FrontendType::ISDBS:
+                    m.isdbs(static_cast<FrontendIsdbsModulation>(modulation));
+                    scanMessage.modulation(m);
+                    break;
+                case (int) FrontendType::ISDBS3:
+                    m.isdbs3(static_cast<FrontendIsdbs3Modulation>(modulation));
+                    scanMessage.modulation(m);
+                    break;
+                case (int) FrontendType::ISDBT:
+                    m.isdbt(static_cast<FrontendIsdbtModulation>(modulation));
+                    scanMessage.modulation(m);
+                    break;
+                case (int) FrontendType::ATSC:
+                    m.atsc(static_cast<FrontendAtscModulation>(modulation));
+                    scanMessage.modulation(m);
+                    break;
+                case (int) FrontendType::ATSC3:
+                    m.atsc3(static_cast<FrontendAtsc3Modulation>(modulation));
+                    scanMessage.modulation(m);
+                    break;
+                case (int) hardware::tv::tuner::V1_1::FrontendType::DTMB:
+                    m.dtmb(static_cast<FrontendDtmbModulation>(modulation));
+                    scanMessage.modulation(m);
+                    break;
+                default:
+                    break;
+            }
+            break;
+        }
+        default:
+            break;
+    }
+    return scanMessage;
+}
+
+bool TunerFrontendCallback::is1_1ExtendedScanMessage(int messageType) {
+    return messageType >= (int)FrontendScanMessageTypeExt1_1::MODULATION
+            && messageType <= (int)FrontendScanMessageTypeExt1_1::HIGH_PRIORITY;
+}
 }  // namespace android
diff --git a/media/jni/tuner/FrontendClient.h b/media/jni/tuner/FrontendClient.h
index 32356744..4f95c22 100644
--- a/media/jni/tuner/FrontendClient.h
+++ b/media/jni/tuner/FrontendClient.h
@@ -30,7 +30,7 @@
 
 using ::aidl::android::media::tv::tuner::BnTunerFrontendCallback;
 using ::aidl::android::media::tv::tuner::ITunerFrontend;
-using ::aidl::android::media::tv::tuner::TunerAtsc3PlpInfo;
+using ::aidl::android::media::tv::tuner::TunerFrontendScanMessage;
 
 using ::android::hardware::Return;
 using ::android::hardware::Void;
@@ -63,34 +63,18 @@
 
     Status onEvent(int frontendEventType);
 
-    Status onLocked();
+    Status onScanMessage(int messageType, const TunerFrontendScanMessage& message);
 
-    Status onScanStopped();
-
-    Status onProgress(int percent);
-
-    Status onFrequenciesReport(const vector<int>& frequency);
-
-    Status onSymbolRates(const vector<int>& rates);
-
-    Status onHierarchy(int hierarchy);
-
-    Status onSignalType(int signalType);
-
-    Status onPlpIds(const vector<int>& plpIds);
-
-    Status onGroupIds(const vector<int>& groupIds);
-
-    Status onInputStreamIds(const vector<int>& inputStreamIds);
-
-    Status onDvbsStandard(int dvbsStandandard);
-
-    Status onAnalogSifStandard(int sifStandandard);
-
-    Status onAtsc3PlpInfos(const vector<TunerAtsc3PlpInfo>& atsc3PlpInfos);
+    void setFrontendType(int frontendType) { mType = frontendType; }
 
 private:
+    FrontendScanMessage getHalScanMessage(int messageType, const TunerFrontendScanMessage& message);
+    FrontendScanMessageExt1_1 getHalScanMessageExt1_1(int messageType,
+            const TunerFrontendScanMessage& message);
+    bool is1_1ExtendedScanMessage(int messageType);
+
     sp<FrontendClientCallback> mFrontendClientCallback;
+    int mType;
 };
 
 struct HidlFrontendCallback : public IFrontendCallback {
@@ -111,7 +95,7 @@
 struct FrontendClient : public RefBase {
 
 public:
-    FrontendClient(shared_ptr<ITunerFrontend> tunerFrontend, int id);
+    FrontendClient(shared_ptr<ITunerFrontend> tunerFrontend, int id, int type);
     ~FrontendClient();
 
     /**
@@ -210,6 +194,7 @@
     sp<HidlFrontendCallback> mHidlCallback;
 
     int mId;
+    int mType;
 };
 }  // namespace android
 
diff --git a/media/jni/tuner/TunerClient.cpp b/media/jni/tuner/TunerClient.cpp
index 39e6ba2..a26753d 100644
--- a/media/jni/tuner/TunerClient.cpp
+++ b/media/jni/tuner/TunerClient.cpp
@@ -98,14 +98,28 @@
         // TODO: handle error code
         shared_ptr<ITunerFrontend> tunerFrontend;
         mTunerService->openFrontend(frontendHandle, &tunerFrontend);
-        return new FrontendClient(tunerFrontend, frontendHandle);
+        if (tunerFrontend == NULL) {
+            return NULL;
+        }
+        int id;
+        // TODO: handle error code
+        tunerFrontend->getFrontendId(&id);
+        TunerServiceFrontendInfo aidlFrontendInfo;
+        // TODO: handle error code
+        mTunerService->getFrontendInfo(id, &aidlFrontendInfo);
+        return new FrontendClient(tunerFrontend, frontendHandle, aidlFrontendInfo.type);
     }
 
     if (mTuner != NULL) {
         int id = getResourceIdFromHandle(frontendHandle, FRONTEND);
         sp<IFrontend> hidlFrontend = openHidlFrontendById(id);
         if (hidlFrontend != NULL) {
-            sp<FrontendClient> frontendClient = new FrontendClient(NULL, id);
+            FrontendInfo hidlInfo;
+            Result res = getHidlFrontendInfo(id, hidlInfo);
+            if (res != Result::SUCCESS) {
+                return NULL;
+            }
+            sp<FrontendClient> frontendClient = new FrontendClient(NULL, id, (int)hidlInfo.type);
             frontendClient->setHidlFrontend(hidlFrontend);
             return frontendClient;
         }