diff options
author | Steven Moreland <smoreland@google.com> | 2019-11-05 16:39:53 -0800 |
---|---|---|
committer | Steven Moreland <smoreland@google.com> | 2019-11-05 16:43:47 -0800 |
commit | d85fcd17653339a3121b3e47b4ed66f3d34e49f9 (patch) | |
tree | 905f57019108ffc6a034bc4c9fd71d37403ddde2 | |
parent | becd44e026ff67cfd3f102fbba543434f5bf5ed2 (diff) | |
download | platform_system_libhidl-d85fcd17653339a3121b3e47b4ed66f3d34e49f9.tar.gz platform_system_libhidl-d85fcd17653339a3121b3e47b4ed66f3d34e49f9.tar.bz2 platform_system_libhidl-d85fcd17653339a3121b3e47b4ed66f3d34e49f9.zip |
Fix HidlReturnRestriction for operator= case.
elsk@ noticed we were missing this case.
Bug: N/A
Test: added test fails w/o fix, but now succeeds
Change-Id: I2984e7b680144a7fe0d243e45be80461149176c8
-rw-r--r-- | base/Status.cpp | 27 | ||||
-rw-r--r-- | base/include/hidl/Status.h | 5 | ||||
-rw-r--r-- | test_main.cpp | 30 |
3 files changed, 51 insertions, 11 deletions
diff --git a/base/Status.cpp b/base/Status.cpp index 08631cc3..7698ff82 100644 --- a/base/Status.cpp +++ b/base/Status.cpp @@ -155,6 +155,20 @@ namespace details { } } + void return_status::onIgnored() const { + if (gReturnRestriction == HidlReturnRestriction::NONE) { + return; + } + + if (gReturnRestriction == HidlReturnRestriction::ERROR_IF_UNCHECKED) { + LOG(ERROR) << "Failed to check status of HIDL Return."; + CallStack::logStack("unchecked HIDL return", CallStack::getCurrent(10).get(), + ANDROID_LOG_ERROR); + } else { + LOG(FATAL) << "Failed to check status of HIDL Return."; + } + } + void return_status::assertOk() const { if (!isOk()) { LOG(FATAL) << "Failed HIDL return status not checked. Usually this happens because of " @@ -171,22 +185,13 @@ namespace details { if (mCheckedStatus) return; assertOk(); - - if (gReturnRestriction == HidlReturnRestriction::NONE) { - return; - } - - if (gReturnRestriction == HidlReturnRestriction::ERROR_IF_UNCHECKED) { - LOG(ERROR) << "Failed to check status of HIDL Return."; - CallStack::logStack("unchecked HIDL return", CallStack::getCurrent(10).get(), ANDROID_LOG_ERROR); - } else { - LOG(FATAL) << "Failed to check status of HIDL Return."; - } + onIgnored(); } return_status& return_status::operator=(return_status&& other) noexcept { if (!mCheckedStatus) { assertOk(); + onIgnored(); } std::swap(mStatus, other.mStatus); diff --git a/base/include/hidl/Status.h b/base/include/hidl/Status.h index 07d352fa..74901bb3 100644 --- a/base/include/hidl/Status.h +++ b/base/include/hidl/Status.h @@ -141,6 +141,11 @@ namespace details { Status mStatus {}; mutable bool mCheckedStatus = false; + // called when an unchecked status is discarded + // makes sure this status is checked according to the preference + // set by setProcessHidlReturnRestriction + void onIgnored() const; + template <typename T, typename U> friend Return<U> StatusOf(const Return<T> &other); protected: diff --git a/test_main.cpp b/test_main.cpp index fc712317..e4cdd29b 100644 --- a/test_main.cpp +++ b/test_main.cpp @@ -546,6 +546,36 @@ TEST_F(LibHidlTest, ReturnDies) { ""); } +TEST_F(LibHidlTest, DetectUncheckedReturn) { + using ::android::hardware::HidlReturnRestriction; + using ::android::hardware::Return; + using ::android::hardware::setProcessHidlReturnRestriction; + using ::android::hardware::Status; + + setProcessHidlReturnRestriction(HidlReturnRestriction::FATAL_IF_UNCHECKED); + + EXPECT_DEATH( + { + auto ret = Return<void>(Status::ok()); + (void)ret; + }, + ""); + EXPECT_DEATH( + { + auto ret = Return<void>(Status::ok()); + ret = Return<void>(Status::ok()); + ret.isOk(); + }, + ""); + + auto ret = Return<void>(Status::ok()); + (void)ret.isOk(); + ret = Return<void>(Status::ok()); + (void)ret.isOk(); + + setProcessHidlReturnRestriction(HidlReturnRestriction::NONE); +} + std::string toString(const ::android::hardware::Status &s) { using ::android::hardware::operator<<; std::ostringstream oss; |