frameworks/av
修訂 | ae3c407137c42d4842b50105f2d549954206fedf (tree) |
---|---|
時間 | 2019-10-27 08:10:59 |
作者 | android-build-team Robot <android-build-team-robot@goog...> |
Commiter | android-build-team Robot |
Snap for 5968679 from dac33eaf3984c3f80b51800f0e350bfbded8a1a6 to qt-qpr2-release
Change-Id: I4bb5a31a12a1a7230837691a56573848a19a0945
@@ -125,6 +125,9 @@ public: | ||
125 | 125 | if (!mClient) { |
126 | 126 | mClient = Codec2Client::_CreateFromIndex(mIndex); |
127 | 127 | } |
128 | + CHECK(mClient) << "Failed to create Codec2Client to service \"" | |
129 | + << GetServiceNames()[mIndex] << "\". (Index = " | |
130 | + << mIndex << ")."; | |
128 | 131 | return mClient; |
129 | 132 | } |
130 | 133 |
@@ -832,6 +835,7 @@ std::shared_ptr<Codec2Client> Codec2Client::_CreateFromIndex(size_t index) { | ||
832 | 835 | |
833 | 836 | c2_status_t Codec2Client::ForAllServices( |
834 | 837 | const std::string &key, |
838 | + size_t numberOfAttempts, | |
835 | 839 | std::function<c2_status_t(const std::shared_ptr<Codec2Client>&)> |
836 | 840 | predicate) { |
837 | 841 | c2_status_t status = C2_NO_INIT; // no IComponentStores present |
@@ -860,23 +864,31 @@ c2_status_t Codec2Client::ForAllServices( | ||
860 | 864 | |
861 | 865 | for (size_t index : indices) { |
862 | 866 | Cache& cache = Cache::List()[index]; |
863 | - std::shared_ptr<Codec2Client> client{cache.getClient()}; | |
864 | - if (client) { | |
867 | + for (size_t tries = numberOfAttempts; tries > 0; --tries) { | |
868 | + std::shared_ptr<Codec2Client> client{cache.getClient()}; | |
865 | 869 | status = predicate(client); |
866 | 870 | if (status == C2_OK) { |
867 | 871 | std::scoped_lock lock{key2IndexMutex}; |
868 | 872 | key2Index[key] = index; // update last known client index |
869 | 873 | return C2_OK; |
874 | + } else if (status == C2_TRANSACTION_FAILED) { | |
875 | + LOG(WARNING) << "\"" << key << "\" failed for service \"" | |
876 | + << client->getName() | |
877 | + << "\" due to transaction failure. " | |
878 | + << "(Service may have crashed.)" | |
879 | + << (tries > 1 ? " Retrying..." : ""); | |
880 | + cache.invalidate(); | |
881 | + continue; | |
870 | 882 | } |
871 | - } | |
872 | - if (wasMapped) { | |
873 | - LOG(INFO) << "Could not find \"" << key << "\"" | |
874 | - " in the last instance. Retrying..."; | |
875 | - wasMapped = false; | |
876 | - cache.invalidate(); | |
883 | + if (wasMapped) { | |
884 | + LOG(INFO) << "\"" << key << "\" became invalid in service \"" | |
885 | + << client->getName() << "\". Retrying..."; | |
886 | + wasMapped = false; | |
887 | + } | |
888 | + break; | |
877 | 889 | } |
878 | 890 | } |
879 | - return status; // return the last status from a valid client | |
891 | + return status; // return the last status from a valid client | |
880 | 892 | } |
881 | 893 | |
882 | 894 | std::shared_ptr<Codec2Client::Component> |
@@ -885,35 +897,37 @@ std::shared_ptr<Codec2Client::Component> | ||
885 | 897 | const std::shared_ptr<Listener>& listener, |
886 | 898 | std::shared_ptr<Codec2Client>* owner, |
887 | 899 | size_t numberOfAttempts) { |
888 | - while (true) { | |
889 | - std::shared_ptr<Component> component; | |
890 | - c2_status_t status = ForAllServices( | |
891 | - componentName, | |
892 | - [owner, &component, componentName, &listener]( | |
893 | - const std::shared_ptr<Codec2Client> &client) | |
894 | - -> c2_status_t { | |
895 | - c2_status_t status = client->createComponent(componentName, | |
896 | - listener, | |
897 | - &component); | |
898 | - if (status == C2_OK) { | |
899 | - if (owner) { | |
900 | - *owner = client; | |
901 | - } | |
902 | - } else if (status != C2_NOT_FOUND) { | |
903 | - LOG(DEBUG) << "IComponentStore(" | |
904 | - << client->getServiceName() | |
905 | - << ")::createComponent(\"" << componentName | |
906 | - << "\") returned status = " | |
907 | - << status << "."; | |
900 | + std::string key{"create:"}; | |
901 | + key.append(componentName); | |
902 | + std::shared_ptr<Component> component; | |
903 | + c2_status_t status = ForAllServices( | |
904 | + key, | |
905 | + numberOfAttempts, | |
906 | + [owner, &component, componentName, &listener]( | |
907 | + const std::shared_ptr<Codec2Client> &client) | |
908 | + -> c2_status_t { | |
909 | + c2_status_t status = client->createComponent(componentName, | |
910 | + listener, | |
911 | + &component); | |
912 | + if (status == C2_OK) { | |
913 | + if (owner) { | |
914 | + *owner = client; | |
908 | 915 | } |
909 | - return status; | |
910 | - }); | |
911 | - if (numberOfAttempts > 0 && status == C2_TRANSACTION_FAILED) { | |
912 | - --numberOfAttempts; | |
913 | - continue; | |
914 | - } | |
915 | - return component; | |
916 | + } else if (status != C2_NOT_FOUND) { | |
917 | + LOG(DEBUG) << "IComponentStore(" | |
918 | + << client->getServiceName() | |
919 | + << ")::createComponent(\"" << componentName | |
920 | + << "\") returned status = " | |
921 | + << status << "."; | |
922 | + } | |
923 | + return status; | |
924 | + }); | |
925 | + if (status != C2_OK) { | |
926 | + LOG(DEBUG) << "Failed to create component \"" << componentName | |
927 | + << "\" from all known services. " | |
928 | + "Last returned status = " << status << "."; | |
916 | 929 | } |
930 | + return component; | |
917 | 931 | } |
918 | 932 | |
919 | 933 | std::shared_ptr<Codec2Client::Interface> |
@@ -921,34 +935,36 @@ std::shared_ptr<Codec2Client::Interface> | ||
921 | 935 | const char* interfaceName, |
922 | 936 | std::shared_ptr<Codec2Client>* owner, |
923 | 937 | size_t numberOfAttempts) { |
924 | - while (true) { | |
925 | - std::shared_ptr<Interface> interface; | |
926 | - c2_status_t status = ForAllServices( | |
927 | - interfaceName, | |
928 | - [owner, &interface, interfaceName]( | |
929 | - const std::shared_ptr<Codec2Client> &client) | |
930 | - -> c2_status_t { | |
931 | - c2_status_t status = client->createInterface(interfaceName, | |
932 | - &interface); | |
933 | - if (status == C2_OK) { | |
934 | - if (owner) { | |
935 | - *owner = client; | |
936 | - } | |
937 | - } else if (status != C2_NOT_FOUND) { | |
938 | - LOG(DEBUG) << "IComponentStore(" | |
939 | - << client->getServiceName() | |
940 | - << ")::createInterface(\"" << interfaceName | |
941 | - << "\") returned status = " | |
942 | - << status << "."; | |
938 | + std::string key{"create:"}; | |
939 | + key.append(interfaceName); | |
940 | + std::shared_ptr<Interface> interface; | |
941 | + c2_status_t status = ForAllServices( | |
942 | + key, | |
943 | + numberOfAttempts, | |
944 | + [owner, &interface, interfaceName]( | |
945 | + const std::shared_ptr<Codec2Client> &client) | |
946 | + -> c2_status_t { | |
947 | + c2_status_t status = client->createInterface(interfaceName, | |
948 | + &interface); | |
949 | + if (status == C2_OK) { | |
950 | + if (owner) { | |
951 | + *owner = client; | |
943 | 952 | } |
944 | - return status; | |
945 | - }); | |
946 | - if (numberOfAttempts > 0 && status == C2_TRANSACTION_FAILED) { | |
947 | - --numberOfAttempts; | |
948 | - continue; | |
949 | - } | |
950 | - return interface; | |
953 | + } else if (status != C2_NOT_FOUND) { | |
954 | + LOG(DEBUG) << "IComponentStore(" | |
955 | + << client->getServiceName() | |
956 | + << ")::createInterface(\"" << interfaceName | |
957 | + << "\") returned status = " | |
958 | + << status << "."; | |
959 | + } | |
960 | + return status; | |
961 | + }); | |
962 | + if (status != C2_OK) { | |
963 | + LOG(DEBUG) << "Failed to create interface \"" << interfaceName | |
964 | + << "\" from all known services. " | |
965 | + "Last returned status = " << status << "."; | |
951 | 966 | } |
967 | + return interface; | |
952 | 968 | } |
953 | 969 | |
954 | 970 | std::vector<C2Component::Traits> const& Codec2Client::ListComponents() { |
@@ -208,11 +208,25 @@ struct Codec2Client : public Codec2ConfigurableClient { | ||
208 | 208 | protected: |
209 | 209 | sp<Base> mBase; |
210 | 210 | |
211 | - // Finds the first store where the predicate returns OK, and returns the last | |
212 | - // predicate result. Uses key to remember the last store found, and if cached, | |
213 | - // it tries that store before trying all stores (one retry). | |
211 | + // Finds the first store where the predicate returns C2_OK and returns the | |
212 | + // last predicate result. The predicate will be tried on all stores. The | |
213 | + // function will return C2_OK the first time the predicate returns C2_OK, | |
214 | + // or it will return the value from the last time that predicate is tried. | |
215 | + // (The latter case corresponds to a failure on every store.) The order of | |
216 | + // the stores to try is the same as the return value of GetServiceNames(). | |
217 | + // | |
218 | + // key is used to remember the last store with which the predicate last | |
219 | + // succeeded. If the last successful store is cached, it will be tried | |
220 | + // first before all the stores are tried. Note that the last successful | |
221 | + // store will be tried twice---first before all the stores, and another time | |
222 | + // with all the stores. | |
223 | + // | |
224 | + // If an attempt to evaluate the predicate results in a transaction failure, | |
225 | + // repeated attempts will be made until the predicate returns without a | |
226 | + // transaction failure or numberOfAttempts attempts have been made. | |
214 | 227 | static c2_status_t ForAllServices( |
215 | 228 | const std::string& key, |
229 | + size_t numberOfAttempts, | |
216 | 230 | std::function<c2_status_t(std::shared_ptr<Codec2Client> const&)> |
217 | 231 | predicate); |
218 | 232 |