| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 1 | /* | 
 | 2 |  * Copyright (C) 2019 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 "BLASTBufferQueue_test" | 
 | 18 |  | 
 | 19 | #include <gui/BLASTBufferQueue.h> | 
 | 20 |  | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 21 | #include <android/hardware/graphics/common/1.2/types.h> | 
| Huihong Luo | 3bdef86 | 2022-03-03 11:57:19 -0800 | [diff] [blame] | 22 | #include <gui/AidlStatusUtil.h> | 
| Valerie Hau | d3b90d2 | 2019-11-06 09:37:31 -0800 | [diff] [blame] | 23 | #include <gui/BufferQueueCore.h> | 
 | 24 | #include <gui/BufferQueueProducer.h> | 
| Valerie Hau | 871d635 | 2020-01-29 08:44:02 -0800 | [diff] [blame] | 25 | #include <gui/FrameTimestamps.h> | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 26 | #include <gui/IGraphicBufferProducer.h> | 
 | 27 | #include <gui/IProducerListener.h> | 
| Vishnu Nair | 17dde61 | 2020-12-28 11:39:59 -0800 | [diff] [blame] | 28 | #include <gui/Surface.h> | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 29 | #include <gui/SurfaceComposerClient.h> | 
| chaviw | e7b9f27 | 2020-08-18 16:08:59 -0700 | [diff] [blame] | 30 | #include <gui/SyncScreenCaptureListener.h> | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 31 | #include <gui/test/CallbackUtils.h> | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 32 | #include <private/gui/ComposerService.h> | 
| Huihong Luo | 9e84f33 | 2021-12-16 14:33:46 -0800 | [diff] [blame] | 33 | #include <private/gui/ComposerServiceAIDL.h> | 
| Marin Shalamanov | a7fe304 | 2021-01-29 21:02:08 +0100 | [diff] [blame] | 34 | #include <ui/DisplayMode.h> | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 35 | #include <ui/GraphicBuffer.h> | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 36 | #include <ui/GraphicTypes.h> | 
| Valerie Hau | 8cee3f9 | 2019-11-06 10:06:28 -0800 | [diff] [blame] | 37 | #include <ui/Transform.h> | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 38 |  | 
 | 39 | #include <gtest/gtest.h> | 
 | 40 |  | 
 | 41 | using namespace std::chrono_literals; | 
 | 42 |  | 
 | 43 | namespace android { | 
 | 44 |  | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 45 | using Transaction = SurfaceComposerClient::Transaction; | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 46 | using android::hardware::graphics::common::V1_2::BufferUsage; | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 47 |  | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 48 | class CountProducerListener : public BnProducerListener { | 
 | 49 | public: | 
 | 50 |     void onBufferReleased() override { | 
 | 51 |         std::scoped_lock<std::mutex> lock(mMutex); | 
 | 52 |         mNumReleased++; | 
 | 53 |         mReleaseCallback.notify_one(); | 
 | 54 |     } | 
 | 55 |  | 
 | 56 |     void waitOnNumberReleased(int32_t expectedNumReleased) { | 
 | 57 |         std::unique_lock<std::mutex> lock(mMutex); | 
 | 58 |         while (mNumReleased < expectedNumReleased) { | 
 | 59 |             ASSERT_NE(mReleaseCallback.wait_for(lock, std::chrono::seconds(3)), | 
 | 60 |                       std::cv_status::timeout) | 
 | 61 |                     << "did not receive release"; | 
 | 62 |         } | 
 | 63 |     } | 
 | 64 |  | 
 | 65 | private: | 
 | 66 |     std::mutex mMutex; | 
 | 67 |     std::condition_variable mReleaseCallback; | 
 | 68 |     int32_t mNumReleased GUARDED_BY(mMutex) = 0; | 
 | 69 | }; | 
 | 70 |  | 
| chaviw | f10b904 | 2021-10-13 15:48:59 -0500 | [diff] [blame] | 71 | class TestBLASTBufferQueue : public BLASTBufferQueue { | 
 | 72 | public: | 
 | 73 |     TestBLASTBufferQueue(const std::string& name, const sp<SurfaceControl>& surface, int width, | 
 | 74 |                          int height, int32_t format) | 
 | 75 |           : BLASTBufferQueue(name, surface, width, height, format) {} | 
 | 76 |  | 
| chaviw | 6b9ffea | 2021-11-08 09:25:48 -0600 | [diff] [blame] | 77 |     void transactionCallback(nsecs_t latchTime, const sp<Fence>& presentFence, | 
 | 78 |                              const std::vector<SurfaceControlStats>& stats) override { | 
 | 79 |         BLASTBufferQueue::transactionCallback(latchTime, presentFence, stats); | 
| chaviw | f10b904 | 2021-10-13 15:48:59 -0500 | [diff] [blame] | 80 |         uint64_t frameNumber = stats[0].frameEventStats.frameNumber; | 
 | 81 |  | 
 | 82 |         { | 
 | 83 |             std::unique_lock lock{frameNumberMutex}; | 
| chaviw | 6b9ffea | 2021-11-08 09:25:48 -0600 | [diff] [blame] | 84 |             mLastTransactionFrameNumber = frameNumber; | 
 | 85 |             mWaitForCallbackCV.notify_all(); | 
| chaviw | f10b904 | 2021-10-13 15:48:59 -0500 | [diff] [blame] | 86 |         } | 
 | 87 |     } | 
 | 88 |  | 
 | 89 |     void waitForCallback(int64_t frameNumber) { | 
 | 90 |         std::unique_lock lock{frameNumberMutex}; | 
 | 91 |         // Wait until all but one of the submitted buffers have been released. | 
| chaviw | 6b9ffea | 2021-11-08 09:25:48 -0600 | [diff] [blame] | 92 |         while (mLastTransactionFrameNumber < frameNumber) { | 
 | 93 |             mWaitForCallbackCV.wait(lock); | 
| chaviw | f10b904 | 2021-10-13 15:48:59 -0500 | [diff] [blame] | 94 |         } | 
 | 95 |     } | 
 | 96 |  | 
 | 97 | private: | 
 | 98 |     std::mutex frameNumberMutex; | 
| chaviw | 6b9ffea | 2021-11-08 09:25:48 -0600 | [diff] [blame] | 99 |     std::condition_variable mWaitForCallbackCV; | 
 | 100 |     int64_t mLastTransactionFrameNumber = -1; | 
| chaviw | f10b904 | 2021-10-13 15:48:59 -0500 | [diff] [blame] | 101 | }; | 
 | 102 |  | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 103 | class BLASTBufferQueueHelper { | 
 | 104 | public: | 
 | 105 |     BLASTBufferQueueHelper(const sp<SurfaceControl>& sc, int width, int height) { | 
| chaviw | f10b904 | 2021-10-13 15:48:59 -0500 | [diff] [blame] | 106 |         mBlastBufferQueueAdapter = new TestBLASTBufferQueue("TestBLASTBufferQueue", sc, width, | 
 | 107 |                                                             height, PIXEL_FORMAT_RGBA_8888); | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 108 |     } | 
 | 109 |  | 
 | 110 |     void update(const sp<SurfaceControl>& sc, int width, int height) { | 
| chaviw | 565ee54 | 2021-01-14 10:21:23 -0800 | [diff] [blame] | 111 |         mBlastBufferQueueAdapter->update(sc, width, height, PIXEL_FORMAT_RGBA_8888); | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 112 |     } | 
 | 113 |  | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 114 |     void setSyncTransaction(Transaction& next, bool acquireSingleBuffer = true) { | 
 | 115 |         auto callback = [&next](Transaction* t) { next.merge(std::move(*t)); }; | 
 | 116 |         mBlastBufferQueueAdapter->syncNextTransaction(callback, acquireSingleBuffer); | 
 | 117 |     } | 
 | 118 |  | 
 | 119 |     void syncNextTransaction(std::function<void(Transaction*)> callback, | 
 | 120 |                              bool acquireSingleBuffer = true) { | 
 | 121 |         mBlastBufferQueueAdapter->syncNextTransaction(callback, acquireSingleBuffer); | 
 | 122 |     } | 
 | 123 |  | 
 | 124 |     void stopContinuousSyncTransaction() { | 
 | 125 |         mBlastBufferQueueAdapter->stopContinuousSyncTransaction(); | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 126 |     } | 
 | 127 |  | 
| Vishnu Nair | ea0de00 | 2020-11-17 17:42:37 -0800 | [diff] [blame] | 128 |     int getWidth() { return mBlastBufferQueueAdapter->mSize.width; } | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 129 |  | 
| Vishnu Nair | ea0de00 | 2020-11-17 17:42:37 -0800 | [diff] [blame] | 130 |     int getHeight() { return mBlastBufferQueueAdapter->mSize.height; } | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 131 |  | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 132 |     std::function<void(Transaction*)> getTransactionReadyCallback() { | 
 | 133 |         return mBlastBufferQueueAdapter->mTransactionReadyCallback; | 
 | 134 |     } | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 135 |  | 
 | 136 |     sp<IGraphicBufferProducer> getIGraphicBufferProducer() { | 
 | 137 |         return mBlastBufferQueueAdapter->getIGraphicBufferProducer(); | 
 | 138 |     } | 
 | 139 |  | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 140 |     const sp<SurfaceControl> getSurfaceControl() { | 
 | 141 |         return mBlastBufferQueueAdapter->mSurfaceControl; | 
 | 142 |     } | 
 | 143 |  | 
| Vishnu Nair | a4fbca5 | 2021-07-07 16:52:34 -0700 | [diff] [blame] | 144 |     sp<Surface> getSurface() { | 
 | 145 |         return mBlastBufferQueueAdapter->getSurface(false /* includeSurfaceControlHandle */); | 
 | 146 |     } | 
 | 147 |  | 
| Valerie Hau | d3b90d2 | 2019-11-06 09:37:31 -0800 | [diff] [blame] | 148 |     void waitForCallbacks() { | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 149 |         std::unique_lock lock{mBlastBufferQueueAdapter->mMutex}; | 
| Vishnu Nair | 1506b18 | 2021-02-22 14:35:15 -0800 | [diff] [blame] | 150 |         // Wait until all but one of the submitted buffers have been released. | 
 | 151 |         while (mBlastBufferQueueAdapter->mSubmitted.size() > 1) { | 
| Valerie Hau | d3b90d2 | 2019-11-06 09:37:31 -0800 | [diff] [blame] | 152 |             mBlastBufferQueueAdapter->mCallbackCV.wait(lock); | 
 | 153 |         } | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 154 |     } | 
 | 155 |  | 
| Vishnu Nair | 1506b18 | 2021-02-22 14:35:15 -0800 | [diff] [blame] | 156 |     void waitForCallback(int64_t frameNumber) { | 
| chaviw | f10b904 | 2021-10-13 15:48:59 -0500 | [diff] [blame] | 157 |         mBlastBufferQueueAdapter->waitForCallback(frameNumber); | 
| Vishnu Nair | 1506b18 | 2021-02-22 14:35:15 -0800 | [diff] [blame] | 158 |     } | 
 | 159 |  | 
| chaviw | 0acd33a | 2021-11-02 11:55:37 -0500 | [diff] [blame] | 160 |     void validateNumFramesSubmitted(int64_t numFramesSubmitted) { | 
 | 161 |         std::unique_lock lock{mBlastBufferQueueAdapter->mMutex}; | 
 | 162 |         ASSERT_EQ(numFramesSubmitted, mBlastBufferQueueAdapter->mSubmitted.size()); | 
 | 163 |     } | 
 | 164 |  | 
| chaviw | c1cf402 | 2022-06-03 13:32:33 -0500 | [diff] [blame] | 165 |     void mergeWithNextTransaction(Transaction* merge, uint64_t frameNumber) { | 
 | 166 |         mBlastBufferQueueAdapter->mergeWithNextTransaction(merge, frameNumber); | 
 | 167 |     } | 
 | 168 |  | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 169 | private: | 
| chaviw | f10b904 | 2021-10-13 15:48:59 -0500 | [diff] [blame] | 170 |     sp<TestBLASTBufferQueue> mBlastBufferQueueAdapter; | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 171 | }; | 
 | 172 |  | 
 | 173 | class BLASTBufferQueueTest : public ::testing::Test { | 
 | 174 | public: | 
 | 175 | protected: | 
 | 176 |     BLASTBufferQueueTest() { | 
 | 177 |         const ::testing::TestInfo* const testInfo = | 
 | 178 |                 ::testing::UnitTest::GetInstance()->current_test_info(); | 
 | 179 |         ALOGV("Begin test: %s.%s", testInfo->test_case_name(), testInfo->name()); | 
 | 180 |     } | 
 | 181 |  | 
 | 182 |     ~BLASTBufferQueueTest() { | 
 | 183 |         const ::testing::TestInfo* const testInfo = | 
 | 184 |                 ::testing::UnitTest::GetInstance()->current_test_info(); | 
 | 185 |         ALOGV("End test:   %s.%s", testInfo->test_case_name(), testInfo->name()); | 
 | 186 |     } | 
 | 187 |  | 
 | 188 |     void SetUp() { | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 189 |         mComposer = ComposerService::getComposerService(); | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 190 |         mClient = new SurfaceComposerClient(); | 
| Huihong Luo | 31b5ac2 | 2022-08-15 20:38:10 -0700 | [diff] [blame] | 191 |         const auto ids = SurfaceComposerClient::getPhysicalDisplayIds(); | 
 | 192 |         ASSERT_FALSE(ids.empty()); | 
 | 193 |         // display 0 is picked as this test is not much display depedent | 
 | 194 |         mDisplayToken = SurfaceComposerClient::getPhysicalDisplayToken(ids.front()); | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 195 |         ASSERT_NE(nullptr, mDisplayToken.get()); | 
 | 196 |         Transaction t; | 
| Dominik Laskowski | 29fa146 | 2021-04-27 15:51:50 -0700 | [diff] [blame] | 197 |         t.setDisplayLayerStack(mDisplayToken, ui::DEFAULT_LAYER_STACK); | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 198 |         t.apply(); | 
 | 199 |         t.clear(); | 
 | 200 |  | 
| Marin Shalamanov | a7fe304 | 2021-01-29 21:02:08 +0100 | [diff] [blame] | 201 |         ui::DisplayMode mode; | 
 | 202 |         ASSERT_EQ(NO_ERROR, SurfaceComposerClient::getActiveDisplayMode(mDisplayToken, &mode)); | 
 | 203 |         const ui::Size& resolution = mode.resolution; | 
| Dominik Laskowski | 3cb3d4e | 2019-11-21 11:14:45 -0800 | [diff] [blame] | 204 |         mDisplayWidth = resolution.getWidth(); | 
 | 205 |         mDisplayHeight = resolution.getHeight(); | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 206 |  | 
 | 207 |         mSurfaceControl = mClient->createSurface(String8("TestSurface"), mDisplayWidth, | 
 | 208 |                                                  mDisplayHeight, PIXEL_FORMAT_RGBA_8888, | 
 | 209 |                                                  ISurfaceComposerClient::eFXSurfaceBufferState, | 
 | 210 |                                                  /*parent*/ nullptr); | 
| Dominik Laskowski | 29fa146 | 2021-04-27 15:51:50 -0700 | [diff] [blame] | 211 |         t.setLayerStack(mSurfaceControl, ui::DEFAULT_LAYER_STACK) | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 212 |                 .setLayer(mSurfaceControl, std::numeric_limits<int32_t>::max()) | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 213 |                 .show(mSurfaceControl) | 
 | 214 |                 .setDataspace(mSurfaceControl, ui::Dataspace::V0_SRGB) | 
 | 215 |                 .apply(); | 
| chaviw | d243289 | 2020-07-24 17:42:39 -0700 | [diff] [blame] | 216 |  | 
 | 217 |         mCaptureArgs.displayToken = mDisplayToken; | 
| arthurhung | 6fa58b7 | 2020-11-05 11:56:00 +0800 | [diff] [blame] | 218 |         mCaptureArgs.dataspace = ui::Dataspace::V0_SRGB; | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 219 |     } | 
 | 220 |  | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 221 |     void setUpProducer(BLASTBufferQueueHelper& adapter, sp<IGraphicBufferProducer>& producer, | 
 | 222 |                        int32_t maxBufferCount = 2) { | 
| Vishnu Nair | 083efd3 | 2021-02-12 09:32:30 -0800 | [diff] [blame] | 223 |         producer = adapter.getIGraphicBufferProducer(); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 224 |         setUpProducer(producer, maxBufferCount); | 
| Vishnu Nair | 083efd3 | 2021-02-12 09:32:30 -0800 | [diff] [blame] | 225 |     } | 
 | 226 |  | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 227 |     void setUpProducer(sp<IGraphicBufferProducer>& igbProducer, int32_t maxBufferCount) { | 
| Valerie Hau | d3b90d2 | 2019-11-06 09:37:31 -0800 | [diff] [blame] | 228 |         ASSERT_NE(nullptr, igbProducer.get()); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 229 |         ASSERT_EQ(NO_ERROR, igbProducer->setMaxDequeuedBufferCount(maxBufferCount)); | 
| Valerie Hau | d3b90d2 | 2019-11-06 09:37:31 -0800 | [diff] [blame] | 230 |         IGraphicBufferProducer::QueueBufferOutput qbOutput; | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 231 |         mProducerListener = new CountProducerListener(); | 
| Valerie Hau | d3b90d2 | 2019-11-06 09:37:31 -0800 | [diff] [blame] | 232 |         ASSERT_EQ(NO_ERROR, | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 233 |                   igbProducer->connect(mProducerListener, NATIVE_WINDOW_API_CPU, false, &qbOutput)); | 
| Dominik Laskowski | 718f960 | 2019-11-09 20:01:35 -0800 | [diff] [blame] | 234 |         ASSERT_NE(ui::Transform::ROT_INVALID, qbOutput.transformHint); | 
| Valerie Hau | d3b90d2 | 2019-11-06 09:37:31 -0800 | [diff] [blame] | 235 |     } | 
 | 236 |  | 
| Valerie Hau | 45e4b3b | 2019-12-03 10:49:17 -0800 | [diff] [blame] | 237 |     void fillBuffer(uint32_t* bufData, Rect rect, uint32_t stride, uint8_t r, uint8_t g, | 
 | 238 |                     uint8_t b) { | 
 | 239 |         for (uint32_t row = rect.top; row < rect.bottom; row++) { | 
 | 240 |             for (uint32_t col = rect.left; col < rect.right; col++) { | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 241 |                 uint8_t* pixel = (uint8_t*)(bufData + (row * stride) + col); | 
 | 242 |                 *pixel = r; | 
 | 243 |                 *(pixel + 1) = g; | 
 | 244 |                 *(pixel + 2) = b; | 
 | 245 |                 *(pixel + 3) = 255; | 
 | 246 |             } | 
 | 247 |         } | 
 | 248 |     } | 
 | 249 |  | 
| Valerie Hau | 5977fc8 | 2019-12-05 15:56:39 -0800 | [diff] [blame] | 250 |     void fillQuadrants(sp<GraphicBuffer>& buf) { | 
 | 251 |         const auto bufWidth = buf->getWidth(); | 
 | 252 |         const auto bufHeight = buf->getHeight(); | 
 | 253 |         uint32_t* bufData; | 
 | 254 |         buf->lock(static_cast<uint32_t>(GraphicBuffer::USAGE_SW_WRITE_OFTEN), | 
 | 255 |                   reinterpret_cast<void**>(&bufData)); | 
 | 256 |         fillBuffer(bufData, Rect(0, 0, bufWidth / 2, bufHeight / 2), buf->getStride(), 0, 0, 0); | 
 | 257 |         fillBuffer(bufData, Rect(bufWidth / 2, 0, bufWidth, bufHeight / 2), buf->getStride(), 255, | 
 | 258 |                    0, 0); | 
 | 259 |         fillBuffer(bufData, Rect(bufWidth / 2, bufHeight / 2, bufWidth, bufHeight), | 
 | 260 |                    buf->getStride(), 0, 255, 0); | 
 | 261 |         fillBuffer(bufData, Rect(0, bufHeight / 2, bufWidth / 2, bufHeight), buf->getStride(), 0, 0, | 
 | 262 |                    255); | 
 | 263 |         buf->unlock(); | 
 | 264 |     } | 
 | 265 |  | 
 | 266 |     void checkScreenCapture(uint8_t r, uint8_t g, uint8_t b, Rect region, int32_t border = 0, | 
 | 267 |                             bool outsideRegion = false) { | 
| chaviw | d243289 | 2020-07-24 17:42:39 -0700 | [diff] [blame] | 268 |         sp<GraphicBuffer>& captureBuf = mCaptureResults.buffer; | 
| Valerie Hau | 5977fc8 | 2019-12-05 15:56:39 -0800 | [diff] [blame] | 269 |         const auto epsilon = 3; | 
| chaviw | d243289 | 2020-07-24 17:42:39 -0700 | [diff] [blame] | 270 |         const auto width = captureBuf->getWidth(); | 
 | 271 |         const auto height = captureBuf->getHeight(); | 
 | 272 |         const auto stride = captureBuf->getStride(); | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 273 |  | 
 | 274 |         uint32_t* bufData; | 
| chaviw | d243289 | 2020-07-24 17:42:39 -0700 | [diff] [blame] | 275 |         captureBuf->lock(static_cast<uint32_t>(GraphicBuffer::USAGE_SW_READ_OFTEN), | 
 | 276 |                          reinterpret_cast<void**>(&bufData)); | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 277 |  | 
 | 278 |         for (uint32_t row = 0; row < height; row++) { | 
 | 279 |             for (uint32_t col = 0; col < width; col++) { | 
 | 280 |                 uint8_t* pixel = (uint8_t*)(bufData + (row * stride) + col); | 
| arthurhung | 6fa58b7 | 2020-11-05 11:56:00 +0800 | [diff] [blame] | 281 |                 ASSERT_NE(nullptr, pixel); | 
| Valerie Hau | 5977fc8 | 2019-12-05 15:56:39 -0800 | [diff] [blame] | 282 |                 bool inRegion; | 
 | 283 |                 if (!outsideRegion) { | 
 | 284 |                     inRegion = row >= region.top + border && row < region.bottom - border && | 
 | 285 |                             col >= region.left + border && col < region.right - border; | 
| Valerie Hau | 45e4b3b | 2019-12-03 10:49:17 -0800 | [diff] [blame] | 286 |                 } else { | 
| Valerie Hau | 5977fc8 | 2019-12-05 15:56:39 -0800 | [diff] [blame] | 287 |                     inRegion = row >= region.top - border && row < region.bottom + border && | 
 | 288 |                             col >= region.left - border && col < region.right + border; | 
 | 289 |                 } | 
 | 290 |                 if (!outsideRegion && inRegion) { | 
| Chavi Weingarten | a5aedbd | 2021-04-09 13:37:33 +0000 | [diff] [blame] | 291 |                     ASSERT_GE(epsilon, abs(r - *(pixel))); | 
 | 292 |                     ASSERT_GE(epsilon, abs(g - *(pixel + 1))); | 
 | 293 |                     ASSERT_GE(epsilon, abs(b - *(pixel + 2))); | 
| Valerie Hau | 5977fc8 | 2019-12-05 15:56:39 -0800 | [diff] [blame] | 294 |                 } else if (outsideRegion && !inRegion) { | 
| Chavi Weingarten | a5aedbd | 2021-04-09 13:37:33 +0000 | [diff] [blame] | 295 |                     ASSERT_GE(epsilon, abs(r - *(pixel))); | 
 | 296 |                     ASSERT_GE(epsilon, abs(g - *(pixel + 1))); | 
 | 297 |                     ASSERT_GE(epsilon, abs(b - *(pixel + 2))); | 
| Valerie Hau | 45e4b3b | 2019-12-03 10:49:17 -0800 | [diff] [blame] | 298 |                 } | 
| Vishnu Nair | 1506b18 | 2021-02-22 14:35:15 -0800 | [diff] [blame] | 299 |                 ASSERT_EQ(false, ::testing::Test::HasFailure()); | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 300 |             } | 
 | 301 |         } | 
| chaviw | d243289 | 2020-07-24 17:42:39 -0700 | [diff] [blame] | 302 |         captureBuf->unlock(); | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 303 |     } | 
 | 304 |  | 
| chaviw | 8ffc7b8 | 2020-08-18 11:25:37 -0700 | [diff] [blame] | 305 |     static status_t captureDisplay(DisplayCaptureArgs& captureArgs, | 
 | 306 |                                    ScreenCaptureResults& captureResults) { | 
| Huihong Luo | 9e84f33 | 2021-12-16 14:33:46 -0800 | [diff] [blame] | 307 |         const auto sf = ComposerServiceAIDL::getComposerService(); | 
| chaviw | 8ffc7b8 | 2020-08-18 11:25:37 -0700 | [diff] [blame] | 308 |         SurfaceComposerClient::Transaction().apply(true); | 
 | 309 |  | 
 | 310 |         const sp<SyncScreenCaptureListener> captureListener = new SyncScreenCaptureListener(); | 
| Huihong Luo | 9e84f33 | 2021-12-16 14:33:46 -0800 | [diff] [blame] | 311 |         binder::Status status = sf->captureDisplay(captureArgs, captureListener); | 
| Huihong Luo | 3bdef86 | 2022-03-03 11:57:19 -0800 | [diff] [blame] | 312 |         status_t err = gui::aidl_utils::statusTFromBinderStatus(status); | 
 | 313 |         if (err != NO_ERROR) { | 
 | 314 |             return err; | 
| chaviw | 8ffc7b8 | 2020-08-18 11:25:37 -0700 | [diff] [blame] | 315 |         } | 
 | 316 |         captureResults = captureListener->waitForResults(); | 
| Patrick Williams | fdb57bb | 2022-08-09 22:48:18 +0000 | [diff] [blame] | 317 |         return fenceStatus(captureResults.fenceResult); | 
| chaviw | 8ffc7b8 | 2020-08-18 11:25:37 -0700 | [diff] [blame] | 318 |     } | 
 | 319 |  | 
| Vishnu Nair | 277142c | 2021-01-05 18:35:29 -0800 | [diff] [blame] | 320 |     void queueBuffer(sp<IGraphicBufferProducer> igbp, uint8_t r, uint8_t g, uint8_t b, | 
 | 321 |                      nsecs_t presentTimeDelay) { | 
 | 322 |         int slot; | 
 | 323 |         sp<Fence> fence; | 
 | 324 |         sp<GraphicBuffer> buf; | 
 | 325 |         auto ret = igbp->dequeueBuffer(&slot, &fence, mDisplayWidth, mDisplayHeight, | 
 | 326 |                                        PIXEL_FORMAT_RGBA_8888, GRALLOC_USAGE_SW_WRITE_OFTEN, | 
 | 327 |                                        nullptr, nullptr); | 
| chaviw | 0acd33a | 2021-11-02 11:55:37 -0500 | [diff] [blame] | 328 |         ASSERT_TRUE(ret == IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION || ret == NO_ERROR); | 
| Vishnu Nair | 277142c | 2021-01-05 18:35:29 -0800 | [diff] [blame] | 329 |         ASSERT_EQ(OK, igbp->requestBuffer(slot, &buf)); | 
 | 330 |  | 
 | 331 |         uint32_t* bufData; | 
 | 332 |         buf->lock(static_cast<uint32_t>(GraphicBuffer::USAGE_SW_WRITE_OFTEN), | 
 | 333 |                   reinterpret_cast<void**>(&bufData)); | 
 | 334 |         fillBuffer(bufData, Rect(buf->getWidth(), buf->getHeight() / 2), buf->getStride(), r, g, b); | 
 | 335 |         buf->unlock(); | 
 | 336 |  | 
 | 337 |         IGraphicBufferProducer::QueueBufferOutput qbOutput; | 
 | 338 |         nsecs_t timestampNanos = systemTime() + presentTimeDelay; | 
 | 339 |         IGraphicBufferProducer::QueueBufferInput input(timestampNanos, false, HAL_DATASPACE_UNKNOWN, | 
 | 340 |                                                        Rect(mDisplayWidth, mDisplayHeight / 2), | 
 | 341 |                                                        NATIVE_WINDOW_SCALING_MODE_FREEZE, 0, | 
 | 342 |                                                        Fence::NO_FENCE); | 
 | 343 |         igbp->queueBuffer(slot, input, &qbOutput); | 
 | 344 |     } | 
 | 345 |  | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 346 |     sp<SurfaceComposerClient> mClient; | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 347 |     sp<ISurfaceComposer> mComposer; | 
 | 348 |  | 
 | 349 |     sp<IBinder> mDisplayToken; | 
 | 350 |  | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 351 |     sp<SurfaceControl> mSurfaceControl; | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 352 |  | 
 | 353 |     uint32_t mDisplayWidth; | 
 | 354 |     uint32_t mDisplayHeight; | 
| chaviw | d243289 | 2020-07-24 17:42:39 -0700 | [diff] [blame] | 355 |  | 
 | 356 |     DisplayCaptureArgs mCaptureArgs; | 
 | 357 |     ScreenCaptureResults mCaptureResults; | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 358 |     sp<CountProducerListener> mProducerListener; | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 359 | }; | 
 | 360 |  | 
 | 361 | TEST_F(BLASTBufferQueueTest, CreateBLASTBufferQueue) { | 
 | 362 |     // create BLASTBufferQueue adapter associated with this surface | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 363 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 364 |     ASSERT_EQ(mSurfaceControl, adapter.getSurfaceControl()); | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 365 |     ASSERT_EQ(mDisplayWidth, adapter.getWidth()); | 
 | 366 |     ASSERT_EQ(mDisplayHeight, adapter.getHeight()); | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 367 |     ASSERT_EQ(nullptr, adapter.getTransactionReadyCallback()); | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 368 | } | 
 | 369 |  | 
 | 370 | TEST_F(BLASTBufferQueueTest, Update) { | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 371 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 372 |     sp<SurfaceControl> updateSurface = | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 373 |             mClient->createSurface(String8("UpdateTest"), mDisplayWidth / 2, mDisplayHeight / 2, | 
 | 374 |                                    PIXEL_FORMAT_RGBA_8888); | 
 | 375 |     adapter.update(updateSurface, mDisplayWidth / 2, mDisplayHeight / 2); | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 376 |     ASSERT_EQ(updateSurface, adapter.getSurfaceControl()); | 
| Vishnu Nair | ea0de00 | 2020-11-17 17:42:37 -0800 | [diff] [blame] | 377 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 378 |     setUpProducer(adapter, igbProducer); | 
 | 379 |  | 
 | 380 |     int32_t width; | 
 | 381 |     igbProducer->query(NATIVE_WINDOW_WIDTH, &width); | 
 | 382 |     ASSERT_EQ(mDisplayWidth / 2, width); | 
 | 383 |     int32_t height; | 
 | 384 |     igbProducer->query(NATIVE_WINDOW_HEIGHT, &height); | 
 | 385 |     ASSERT_EQ(mDisplayHeight / 2, height); | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 386 | } | 
 | 387 |  | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 388 | TEST_F(BLASTBufferQueueTest, SyncNextTransaction) { | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 389 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 390 |     ASSERT_EQ(nullptr, adapter.getTransactionReadyCallback()); | 
 | 391 |     auto callback = [](Transaction*) {}; | 
 | 392 |     adapter.syncNextTransaction(callback); | 
 | 393 |     ASSERT_NE(nullptr, adapter.getTransactionReadyCallback()); | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 394 | } | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 395 |  | 
| Valerie Hau | bf29e04 | 2020-02-06 11:40:38 -0800 | [diff] [blame] | 396 | TEST_F(BLASTBufferQueueTest, DISABLED_onFrameAvailable_ApplyDesiredPresentTime) { | 
| Valerie Hau | 181abd3 | 2020-01-27 14:18:28 -0800 | [diff] [blame] | 397 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 398 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 399 |     setUpProducer(adapter, igbProducer); | 
 | 400 |  | 
 | 401 |     int slot; | 
 | 402 |     sp<Fence> fence; | 
 | 403 |     sp<GraphicBuffer> buf; | 
 | 404 |     auto ret = igbProducer->dequeueBuffer(&slot, &fence, mDisplayWidth, mDisplayHeight, | 
 | 405 |                                           PIXEL_FORMAT_RGBA_8888, GRALLOC_USAGE_SW_WRITE_OFTEN, | 
 | 406 |                                           nullptr, nullptr); | 
 | 407 |     ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION, ret); | 
 | 408 |     ASSERT_EQ(OK, igbProducer->requestBuffer(slot, &buf)); | 
 | 409 |  | 
 | 410 |     nsecs_t desiredPresentTime = systemTime() + nsecs_t(5 * 1e8); | 
 | 411 |     IGraphicBufferProducer::QueueBufferOutput qbOutput; | 
| Vishnu Nair | 1506b18 | 2021-02-22 14:35:15 -0800 | [diff] [blame] | 412 |     IGraphicBufferProducer::QueueBufferInput input(desiredPresentTime, true /* autotimestamp */, | 
 | 413 |                                                    HAL_DATASPACE_UNKNOWN, | 
| Valerie Hau | 181abd3 | 2020-01-27 14:18:28 -0800 | [diff] [blame] | 414 |                                                    Rect(mDisplayWidth, mDisplayHeight), | 
 | 415 |                                                    NATIVE_WINDOW_SCALING_MODE_FREEZE, 0, | 
 | 416 |                                                    Fence::NO_FENCE); | 
 | 417 |     igbProducer->queueBuffer(slot, input, &qbOutput); | 
 | 418 |     ASSERT_NE(ui::Transform::ROT_INVALID, qbOutput.transformHint); | 
 | 419 |  | 
 | 420 |     adapter.waitForCallbacks(); | 
 | 421 |     ASSERT_GE(systemTime(), desiredPresentTime); | 
 | 422 | } | 
 | 423 |  | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 424 | TEST_F(BLASTBufferQueueTest, onFrameAvailable_Apply) { | 
 | 425 |     uint8_t r = 255; | 
 | 426 |     uint8_t g = 0; | 
 | 427 |     uint8_t b = 0; | 
 | 428 |  | 
 | 429 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
| Valerie Hau | d3b90d2 | 2019-11-06 09:37:31 -0800 | [diff] [blame] | 430 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 431 |     setUpProducer(adapter, igbProducer); | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 432 |  | 
 | 433 |     int slot; | 
 | 434 |     sp<Fence> fence; | 
 | 435 |     sp<GraphicBuffer> buf; | 
 | 436 |     auto ret = igbProducer->dequeueBuffer(&slot, &fence, mDisplayWidth, mDisplayHeight, | 
 | 437 |                                           PIXEL_FORMAT_RGBA_8888, GRALLOC_USAGE_SW_WRITE_OFTEN, | 
 | 438 |                                           nullptr, nullptr); | 
 | 439 |     ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION, ret); | 
 | 440 |     ASSERT_EQ(OK, igbProducer->requestBuffer(slot, &buf)); | 
 | 441 |  | 
 | 442 |     uint32_t* bufData; | 
 | 443 |     buf->lock(static_cast<uint32_t>(GraphicBuffer::USAGE_SW_WRITE_OFTEN), | 
 | 444 |               reinterpret_cast<void**>(&bufData)); | 
| Valerie Hau | 45e4b3b | 2019-12-03 10:49:17 -0800 | [diff] [blame] | 445 |     fillBuffer(bufData, Rect(buf->getWidth(), buf->getHeight()), buf->getStride(), r, g, b); | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 446 |     buf->unlock(); | 
 | 447 |  | 
| Valerie Hau | d3b90d2 | 2019-11-06 09:37:31 -0800 | [diff] [blame] | 448 |     IGraphicBufferProducer::QueueBufferOutput qbOutput; | 
| Vishnu Nair | 1506b18 | 2021-02-22 14:35:15 -0800 | [diff] [blame] | 449 |     IGraphicBufferProducer::QueueBufferInput input(systemTime(), true /* autotimestamp */, | 
 | 450 |                                                    HAL_DATASPACE_UNKNOWN, | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 451 |                                                    Rect(mDisplayWidth, mDisplayHeight), | 
 | 452 |                                                    NATIVE_WINDOW_SCALING_MODE_FREEZE, 0, | 
 | 453 |                                                    Fence::NO_FENCE); | 
 | 454 |     igbProducer->queueBuffer(slot, input, &qbOutput); | 
| Dominik Laskowski | 718f960 | 2019-11-09 20:01:35 -0800 | [diff] [blame] | 455 |     ASSERT_NE(ui::Transform::ROT_INVALID, qbOutput.transformHint); | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 456 |  | 
| Valerie Hau | 45e4b3b | 2019-12-03 10:49:17 -0800 | [diff] [blame] | 457 |     adapter.waitForCallbacks(); | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 458 |  | 
 | 459 |     // capture screen and verify that it is red | 
| chaviw | 8ffc7b8 | 2020-08-18 11:25:37 -0700 | [diff] [blame] | 460 |     ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
| Valerie Hau | 45e4b3b | 2019-12-03 10:49:17 -0800 | [diff] [blame] | 461 |     ASSERT_NO_FATAL_FAILURE( | 
 | 462 |             checkScreenCapture(r, g, b, {0, 0, (int32_t)mDisplayWidth, (int32_t)mDisplayHeight})); | 
| Valerie Hau | da3446e | 2019-10-14 15:49:22 -0700 | [diff] [blame] | 463 | } | 
| Valerie Hau | d3b90d2 | 2019-11-06 09:37:31 -0800 | [diff] [blame] | 464 |  | 
 | 465 | TEST_F(BLASTBufferQueueTest, TripleBuffering) { | 
 | 466 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 467 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 468 |     setUpProducer(adapter, igbProducer); | 
 | 469 |  | 
 | 470 |     std::vector<std::pair<int, sp<Fence>>> allocated; | 
| Ady Abraham | 0bde6b5 | 2021-05-18 13:57:02 -0700 | [diff] [blame] | 471 |     int minUndequeuedBuffers = 0; | 
 | 472 |     ASSERT_EQ(OK, igbProducer->query(NATIVE_WINDOW_MIN_UNDEQUEUED_BUFFERS, &minUndequeuedBuffers)); | 
 | 473 |     const auto bufferCount = minUndequeuedBuffers + 2; | 
 | 474 |  | 
 | 475 |     for (int i = 0; i < bufferCount; i++) { | 
| Valerie Hau | d3b90d2 | 2019-11-06 09:37:31 -0800 | [diff] [blame] | 476 |         int slot; | 
 | 477 |         sp<Fence> fence; | 
 | 478 |         sp<GraphicBuffer> buf; | 
 | 479 |         auto ret = igbProducer->dequeueBuffer(&slot, &fence, mDisplayWidth, mDisplayHeight, | 
 | 480 |                                               PIXEL_FORMAT_RGBA_8888, GRALLOC_USAGE_SW_WRITE_OFTEN, | 
 | 481 |                                               nullptr, nullptr); | 
 | 482 |         ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION, ret); | 
 | 483 |         ASSERT_EQ(OK, igbProducer->requestBuffer(slot, &buf)); | 
 | 484 |         allocated.push_back({slot, fence}); | 
 | 485 |     } | 
 | 486 |     for (int i = 0; i < allocated.size(); i++) { | 
 | 487 |         igbProducer->cancelBuffer(allocated[i].first, allocated[i].second); | 
 | 488 |     } | 
 | 489 |  | 
| Valerie Hau | a32c552 | 2019-12-09 10:11:08 -0800 | [diff] [blame] | 490 |     for (int i = 0; i < 100; i++) { | 
| Valerie Hau | d3b90d2 | 2019-11-06 09:37:31 -0800 | [diff] [blame] | 491 |         int slot; | 
 | 492 |         sp<Fence> fence; | 
 | 493 |         sp<GraphicBuffer> buf; | 
 | 494 |         auto ret = igbProducer->dequeueBuffer(&slot, &fence, mDisplayWidth, mDisplayHeight, | 
 | 495 |                                               PIXEL_FORMAT_RGBA_8888, GRALLOC_USAGE_SW_WRITE_OFTEN, | 
 | 496 |                                               nullptr, nullptr); | 
 | 497 |         ASSERT_EQ(NO_ERROR, ret); | 
 | 498 |         IGraphicBufferProducer::QueueBufferOutput qbOutput; | 
| Vishnu Nair | 1506b18 | 2021-02-22 14:35:15 -0800 | [diff] [blame] | 499 |         IGraphicBufferProducer::QueueBufferInput input(systemTime(), true /* autotimestamp */, | 
 | 500 |                                                        HAL_DATASPACE_UNKNOWN, | 
| Valerie Hau | d3b90d2 | 2019-11-06 09:37:31 -0800 | [diff] [blame] | 501 |                                                        Rect(mDisplayWidth, mDisplayHeight), | 
 | 502 |                                                        NATIVE_WINDOW_SCALING_MODE_FREEZE, 0, | 
 | 503 |                                                        Fence::NO_FENCE); | 
 | 504 |         igbProducer->queueBuffer(slot, input, &qbOutput); | 
 | 505 |     } | 
 | 506 |     adapter.waitForCallbacks(); | 
 | 507 | } | 
| Valerie Hau | 45e4b3b | 2019-12-03 10:49:17 -0800 | [diff] [blame] | 508 |  | 
 | 509 | TEST_F(BLASTBufferQueueTest, SetCrop_Item) { | 
 | 510 |     uint8_t r = 255; | 
 | 511 |     uint8_t g = 0; | 
 | 512 |     uint8_t b = 0; | 
 | 513 |  | 
 | 514 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 515 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 516 |     setUpProducer(adapter, igbProducer); | 
 | 517 |     int slot; | 
 | 518 |     sp<Fence> fence; | 
 | 519 |     sp<GraphicBuffer> buf; | 
 | 520 |     auto ret = igbProducer->dequeueBuffer(&slot, &fence, mDisplayWidth, mDisplayHeight, | 
 | 521 |                                           PIXEL_FORMAT_RGBA_8888, GRALLOC_USAGE_SW_WRITE_OFTEN, | 
 | 522 |                                           nullptr, nullptr); | 
 | 523 |     ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION, ret); | 
 | 524 |     ASSERT_EQ(OK, igbProducer->requestBuffer(slot, &buf)); | 
 | 525 |  | 
 | 526 |     uint32_t* bufData; | 
 | 527 |     buf->lock(static_cast<uint32_t>(GraphicBuffer::USAGE_SW_WRITE_OFTEN), | 
 | 528 |               reinterpret_cast<void**>(&bufData)); | 
 | 529 |     fillBuffer(bufData, Rect(buf->getWidth(), buf->getHeight() / 2), buf->getStride(), r, g, b); | 
 | 530 |     buf->unlock(); | 
 | 531 |  | 
 | 532 |     IGraphicBufferProducer::QueueBufferOutput qbOutput; | 
| Vishnu Nair | 1506b18 | 2021-02-22 14:35:15 -0800 | [diff] [blame] | 533 |     IGraphicBufferProducer::QueueBufferInput input(systemTime(), true /* autotimestamp */, | 
 | 534 |                                                    HAL_DATASPACE_UNKNOWN, | 
| Valerie Hau | 45e4b3b | 2019-12-03 10:49:17 -0800 | [diff] [blame] | 535 |                                                    Rect(mDisplayWidth, mDisplayHeight / 2), | 
 | 536 |                                                    NATIVE_WINDOW_SCALING_MODE_FREEZE, 0, | 
 | 537 |                                                    Fence::NO_FENCE); | 
 | 538 |     igbProducer->queueBuffer(slot, input, &qbOutput); | 
| Dominik Laskowski | 718f960 | 2019-11-09 20:01:35 -0800 | [diff] [blame] | 539 |     ASSERT_NE(ui::Transform::ROT_INVALID, qbOutput.transformHint); | 
| Valerie Hau | 45e4b3b | 2019-12-03 10:49:17 -0800 | [diff] [blame] | 540 |  | 
 | 541 |     adapter.waitForCallbacks(); | 
 | 542 |     // capture screen and verify that it is red | 
| chaviw | 8ffc7b8 | 2020-08-18 11:25:37 -0700 | [diff] [blame] | 543 |     ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
| chaviw | d243289 | 2020-07-24 17:42:39 -0700 | [diff] [blame] | 544 |  | 
| Valerie Hau | 45e4b3b | 2019-12-03 10:49:17 -0800 | [diff] [blame] | 545 |     ASSERT_NO_FATAL_FAILURE( | 
| Chavi Weingarten | a5aedbd | 2021-04-09 13:37:33 +0000 | [diff] [blame] | 546 |             checkScreenCapture(r, g, b, | 
 | 547 |                                {0, 0, (int32_t)mDisplayWidth, (int32_t)mDisplayHeight / 2})); | 
| Valerie Hau | 45e4b3b | 2019-12-03 10:49:17 -0800 | [diff] [blame] | 548 | } | 
 | 549 |  | 
 | 550 | TEST_F(BLASTBufferQueueTest, SetCrop_ScalingModeScaleCrop) { | 
 | 551 |     uint8_t r = 255; | 
 | 552 |     uint8_t g = 0; | 
 | 553 |     uint8_t b = 0; | 
 | 554 |  | 
 | 555 |     int32_t bufferSideLength = | 
 | 556 |             (mDisplayWidth < mDisplayHeight) ? mDisplayWidth / 2 : mDisplayHeight / 2; | 
 | 557 |     int32_t finalCropSideLength = bufferSideLength / 2; | 
 | 558 |  | 
 | 559 |     auto bg = mClient->createSurface(String8("BGTest"), 0, 0, PIXEL_FORMAT_RGBA_8888, | 
| Vishnu Nair | fa247b1 | 2020-02-11 08:58:26 -0800 | [diff] [blame] | 560 |                                      ISurfaceComposerClient::eFXSurfaceEffect); | 
| Valerie Hau | 45e4b3b | 2019-12-03 10:49:17 -0800 | [diff] [blame] | 561 |     ASSERT_NE(nullptr, bg.get()); | 
 | 562 |     Transaction t; | 
| Dominik Laskowski | 29fa146 | 2021-04-27 15:51:50 -0700 | [diff] [blame] | 563 |     t.setLayerStack(bg, ui::DEFAULT_LAYER_STACK) | 
| chaviw | 2571450 | 2021-02-11 10:01:08 -0800 | [diff] [blame] | 564 |             .setCrop(bg, Rect(0, 0, mDisplayWidth, mDisplayHeight)) | 
| Valerie Hau | 45e4b3b | 2019-12-03 10:49:17 -0800 | [diff] [blame] | 565 |             .setColor(bg, half3{0, 0, 0}) | 
 | 566 |             .setLayer(bg, 0) | 
 | 567 |             .apply(); | 
 | 568 |  | 
 | 569 |     BLASTBufferQueueHelper adapter(mSurfaceControl, bufferSideLength, bufferSideLength); | 
 | 570 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 571 |     setUpProducer(adapter, igbProducer); | 
 | 572 |     int slot; | 
 | 573 |     sp<Fence> fence; | 
 | 574 |     sp<GraphicBuffer> buf; | 
 | 575 |     auto ret = igbProducer->dequeueBuffer(&slot, &fence, bufferSideLength, bufferSideLength, | 
 | 576 |                                           PIXEL_FORMAT_RGBA_8888, GRALLOC_USAGE_SW_WRITE_OFTEN, | 
 | 577 |                                           nullptr, nullptr); | 
 | 578 |     ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION, ret); | 
 | 579 |     ASSERT_EQ(OK, igbProducer->requestBuffer(slot, &buf)); | 
 | 580 |  | 
 | 581 |     uint32_t* bufData; | 
 | 582 |     buf->lock(static_cast<uint32_t>(GraphicBuffer::USAGE_SW_WRITE_OFTEN), | 
 | 583 |               reinterpret_cast<void**>(&bufData)); | 
 | 584 |     fillBuffer(bufData, Rect(buf->getWidth(), buf->getHeight()), buf->getStride(), 0, 0, 0); | 
 | 585 |     fillBuffer(bufData, | 
 | 586 |                Rect(finalCropSideLength / 2, 0, buf->getWidth() - finalCropSideLength / 2, | 
 | 587 |                     buf->getHeight()), | 
 | 588 |                buf->getStride(), r, g, b); | 
 | 589 |     buf->unlock(); | 
 | 590 |  | 
 | 591 |     IGraphicBufferProducer::QueueBufferOutput qbOutput; | 
| Vishnu Nair | 1506b18 | 2021-02-22 14:35:15 -0800 | [diff] [blame] | 592 |     IGraphicBufferProducer::QueueBufferInput input(systemTime(), true /* autotimestamp */, | 
 | 593 |                                                    HAL_DATASPACE_UNKNOWN, | 
| Valerie Hau | 45e4b3b | 2019-12-03 10:49:17 -0800 | [diff] [blame] | 594 |                                                    Rect(bufferSideLength, finalCropSideLength), | 
 | 595 |                                                    NATIVE_WINDOW_SCALING_MODE_SCALE_CROP, 0, | 
 | 596 |                                                    Fence::NO_FENCE); | 
 | 597 |     igbProducer->queueBuffer(slot, input, &qbOutput); | 
| Dominik Laskowski | 718f960 | 2019-11-09 20:01:35 -0800 | [diff] [blame] | 598 |     ASSERT_NE(ui::Transform::ROT_INVALID, qbOutput.transformHint); | 
| Valerie Hau | 45e4b3b | 2019-12-03 10:49:17 -0800 | [diff] [blame] | 599 |  | 
 | 600 |     adapter.waitForCallbacks(); | 
 | 601 |     // capture screen and verify that it is red | 
| chaviw | 8ffc7b8 | 2020-08-18 11:25:37 -0700 | [diff] [blame] | 602 |     ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
| Vishnu Nair | 5cc9ac0 | 2021-04-19 13:23:38 -0700 | [diff] [blame] | 603 |     ASSERT_NO_FATAL_FAILURE(checkScreenCapture(r, g, b, | 
 | 604 |                                                {10, 10, (int32_t)bufferSideLength - 10, | 
 | 605 |                                                 (int32_t)bufferSideLength - 10})); | 
| Valerie Hau | 45e4b3b | 2019-12-03 10:49:17 -0800 | [diff] [blame] | 606 |     ASSERT_NO_FATAL_FAILURE( | 
| Vishnu Nair | 5cc9ac0 | 2021-04-19 13:23:38 -0700 | [diff] [blame] | 607 |             checkScreenCapture(0, 0, 0, | 
 | 608 |                                {0, 0, (int32_t)bufferSideLength, (int32_t)bufferSideLength}, | 
 | 609 |                                /*border*/ 0, /*outsideRegion*/ true)); | 
 | 610 | } | 
 | 611 |  | 
 | 612 | TEST_F(BLASTBufferQueueTest, ScaleCroppedBufferToBufferSize) { | 
 | 613 |     // add black background | 
 | 614 |     auto bg = mClient->createSurface(String8("BGTest"), 0, 0, PIXEL_FORMAT_RGBA_8888, | 
 | 615 |                                      ISurfaceComposerClient::eFXSurfaceEffect); | 
 | 616 |     ASSERT_NE(nullptr, bg.get()); | 
 | 617 |     Transaction t; | 
| Dominik Laskowski | 29fa146 | 2021-04-27 15:51:50 -0700 | [diff] [blame] | 618 |     t.setLayerStack(bg, ui::DEFAULT_LAYER_STACK) | 
| Vishnu Nair | 5cc9ac0 | 2021-04-19 13:23:38 -0700 | [diff] [blame] | 619 |             .setCrop(bg, Rect(0, 0, mDisplayWidth, mDisplayHeight)) | 
 | 620 |             .setColor(bg, half3{0, 0, 0}) | 
 | 621 |             .setLayer(bg, 0) | 
 | 622 |             .apply(); | 
 | 623 |  | 
 | 624 |     Rect windowSize(1000, 1000); | 
 | 625 |     Rect bufferSize(windowSize); | 
 | 626 |     Rect bufferCrop(200, 200, 700, 700); | 
 | 627 |  | 
 | 628 |     BLASTBufferQueueHelper adapter(mSurfaceControl, windowSize.getWidth(), windowSize.getHeight()); | 
 | 629 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 630 |     setUpProducer(adapter, igbProducer); | 
 | 631 |     int slot; | 
 | 632 |     sp<Fence> fence; | 
 | 633 |     sp<GraphicBuffer> buf; | 
 | 634 |     auto ret = igbProducer->dequeueBuffer(&slot, &fence, bufferSize.getWidth(), | 
 | 635 |                                           bufferSize.getHeight(), PIXEL_FORMAT_RGBA_8888, | 
 | 636 |                                           GRALLOC_USAGE_SW_WRITE_OFTEN, nullptr, nullptr); | 
 | 637 |     ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION, ret); | 
 | 638 |     ASSERT_EQ(OK, igbProducer->requestBuffer(slot, &buf)); | 
 | 639 |  | 
 | 640 |     uint32_t* bufData; | 
 | 641 |     buf->lock(static_cast<uint32_t>(GraphicBuffer::USAGE_SW_WRITE_OFTEN), | 
 | 642 |               reinterpret_cast<void**>(&bufData)); | 
 | 643 |     // fill buffer with grey | 
 | 644 |     fillBuffer(bufData, bufferSize, buf->getStride(), 127, 127, 127); | 
 | 645 |  | 
 | 646 |     // fill crop area with different colors so we can verify the cropped region has been scaled | 
 | 647 |     // correctly. | 
 | 648 |     fillBuffer(bufData, Rect(200, 200, 450, 450), buf->getStride(), /* rgb */ 255, 0, 0); | 
 | 649 |     fillBuffer(bufData, Rect(200, 451, 450, 700), buf->getStride(), /* rgb */ 0, 255, 0); | 
 | 650 |     fillBuffer(bufData, Rect(451, 200, 700, 450), buf->getStride(), /* rgb */ 0, 0, 255); | 
 | 651 |     fillBuffer(bufData, Rect(451, 451, 700, 700), buf->getStride(), /* rgb */ 255, 0, 0); | 
 | 652 |     buf->unlock(); | 
 | 653 |  | 
 | 654 |     IGraphicBufferProducer::QueueBufferOutput qbOutput; | 
 | 655 |     IGraphicBufferProducer::QueueBufferInput input(systemTime(), true /* autotimestamp */, | 
 | 656 |                                                    HAL_DATASPACE_UNKNOWN, | 
 | 657 |                                                    bufferCrop /* Rect::INVALID_RECT */, | 
 | 658 |                                                    NATIVE_WINDOW_SCALING_MODE_SCALE_TO_WINDOW, 0, | 
 | 659 |                                                    Fence::NO_FENCE); | 
 | 660 |     igbProducer->queueBuffer(slot, input, &qbOutput); | 
 | 661 |     ASSERT_NE(ui::Transform::ROT_INVALID, qbOutput.transformHint); | 
 | 662 |  | 
 | 663 |     adapter.waitForCallbacks(); | 
 | 664 |  | 
 | 665 |     ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
 | 666 |  | 
 | 667 |     // Verify cropped region is scaled correctly. | 
 | 668 |     ASSERT_NO_FATAL_FAILURE(checkScreenCapture(255, 0, 0, {10, 10, 490, 490})); | 
 | 669 |     ASSERT_NO_FATAL_FAILURE(checkScreenCapture(0, 255, 0, {10, 510, 490, 990})); | 
 | 670 |     ASSERT_NO_FATAL_FAILURE(checkScreenCapture(0, 0, 255, {510, 10, 990, 490})); | 
 | 671 |     ASSERT_NO_FATAL_FAILURE(checkScreenCapture(255, 0, 0, {510, 510, 990, 990})); | 
 | 672 |     // Verify outside region is black. | 
 | 673 |     ASSERT_NO_FATAL_FAILURE(checkScreenCapture(0, 0, 0, | 
 | 674 |                                                {0, 0, (int32_t)windowSize.getWidth(), | 
 | 675 |                                                 (int32_t)windowSize.getHeight()}, | 
 | 676 |                                                /*border*/ 0, /*outsideRegion*/ true)); | 
 | 677 | } | 
 | 678 |  | 
 | 679 | TEST_F(BLASTBufferQueueTest, ScaleCroppedBufferToWindowSize) { | 
 | 680 |     // add black background | 
 | 681 |     auto bg = mClient->createSurface(String8("BGTest"), 0, 0, PIXEL_FORMAT_RGBA_8888, | 
 | 682 |                                      ISurfaceComposerClient::eFXSurfaceEffect); | 
 | 683 |     ASSERT_NE(nullptr, bg.get()); | 
 | 684 |     Transaction t; | 
| Dominik Laskowski | 29fa146 | 2021-04-27 15:51:50 -0700 | [diff] [blame] | 685 |     t.setLayerStack(bg, ui::DEFAULT_LAYER_STACK) | 
| Vishnu Nair | 5cc9ac0 | 2021-04-19 13:23:38 -0700 | [diff] [blame] | 686 |             .setCrop(bg, Rect(0, 0, mDisplayWidth, mDisplayHeight)) | 
 | 687 |             .setColor(bg, half3{0, 0, 0}) | 
 | 688 |             .setLayer(bg, 0) | 
 | 689 |             .apply(); | 
 | 690 |  | 
 | 691 |     Rect windowSize(1000, 1000); | 
 | 692 |     Rect bufferSize(500, 500); | 
 | 693 |     Rect bufferCrop(100, 100, 350, 350); | 
 | 694 |  | 
 | 695 |     BLASTBufferQueueHelper adapter(mSurfaceControl, windowSize.getWidth(), windowSize.getHeight()); | 
 | 696 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 697 |     setUpProducer(adapter, igbProducer); | 
 | 698 |     int slot; | 
 | 699 |     sp<Fence> fence; | 
 | 700 |     sp<GraphicBuffer> buf; | 
 | 701 |     auto ret = igbProducer->dequeueBuffer(&slot, &fence, bufferSize.getWidth(), | 
 | 702 |                                           bufferSize.getHeight(), PIXEL_FORMAT_RGBA_8888, | 
 | 703 |                                           GRALLOC_USAGE_SW_WRITE_OFTEN, nullptr, nullptr); | 
 | 704 |     ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION, ret); | 
 | 705 |     ASSERT_EQ(OK, igbProducer->requestBuffer(slot, &buf)); | 
 | 706 |  | 
 | 707 |     uint32_t* bufData; | 
 | 708 |     buf->lock(static_cast<uint32_t>(GraphicBuffer::USAGE_SW_WRITE_OFTEN), | 
 | 709 |               reinterpret_cast<void**>(&bufData)); | 
 | 710 |     // fill buffer with grey | 
 | 711 |     fillBuffer(bufData, bufferSize, buf->getStride(), 127, 127, 127); | 
 | 712 |  | 
 | 713 |     // fill crop area with different colors so we can verify the cropped region has been scaled | 
 | 714 |     // correctly. | 
 | 715 |     fillBuffer(bufData, Rect(100, 100, 225, 225), buf->getStride(), /* rgb */ 255, 0, 0); | 
 | 716 |     fillBuffer(bufData, Rect(100, 226, 225, 350), buf->getStride(), /* rgb */ 0, 255, 0); | 
 | 717 |     fillBuffer(bufData, Rect(226, 100, 350, 225), buf->getStride(), /* rgb */ 0, 0, 255); | 
 | 718 |     fillBuffer(bufData, Rect(226, 226, 350, 350), buf->getStride(), /* rgb */ 255, 0, 0); | 
 | 719 |     buf->unlock(); | 
 | 720 |  | 
 | 721 |     IGraphicBufferProducer::QueueBufferOutput qbOutput; | 
 | 722 |     IGraphicBufferProducer::QueueBufferInput input(systemTime(), true /* autotimestamp */, | 
 | 723 |                                                    HAL_DATASPACE_UNKNOWN, | 
 | 724 |                                                    bufferCrop /* Rect::INVALID_RECT */, | 
 | 725 |                                                    NATIVE_WINDOW_SCALING_MODE_SCALE_TO_WINDOW, 0, | 
 | 726 |                                                    Fence::NO_FENCE); | 
 | 727 |     igbProducer->queueBuffer(slot, input, &qbOutput); | 
 | 728 |     ASSERT_NE(ui::Transform::ROT_INVALID, qbOutput.transformHint); | 
 | 729 |  | 
 | 730 |     adapter.waitForCallbacks(); | 
 | 731 |  | 
 | 732 |     ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
 | 733 |     // Verify cropped region is scaled correctly. | 
 | 734 |     ASSERT_NO_FATAL_FAILURE(checkScreenCapture(255, 0, 0, {10, 10, 490, 490})); | 
 | 735 |     ASSERT_NO_FATAL_FAILURE(checkScreenCapture(0, 255, 0, {10, 510, 490, 990})); | 
 | 736 |     ASSERT_NO_FATAL_FAILURE(checkScreenCapture(0, 0, 255, {510, 10, 990, 490})); | 
 | 737 |     ASSERT_NO_FATAL_FAILURE(checkScreenCapture(255, 0, 0, {510, 510, 990, 990})); | 
 | 738 |     // Verify outside region is black. | 
 | 739 |     ASSERT_NO_FATAL_FAILURE(checkScreenCapture(0, 0, 0, | 
 | 740 |                                                {0, 0, (int32_t)windowSize.getWidth(), | 
 | 741 |                                                 (int32_t)windowSize.getHeight()}, | 
 | 742 |                                                /*border*/ 0, /*outsideRegion*/ true)); | 
| Valerie Hau | 45e4b3b | 2019-12-03 10:49:17 -0800 | [diff] [blame] | 743 | } | 
 | 744 |  | 
| Vishnu Nair | 932f6ae | 2021-09-29 17:33:10 -0700 | [diff] [blame] | 745 | // b/196339769 verify we can can update the requested size while the in FREEZE scaling mode and | 
 | 746 | // scale the buffer properly when the mode changes to SCALE_TO_WINDOW | 
 | 747 | TEST_F(BLASTBufferQueueTest, ScalingModeChanges) { | 
 | 748 |     uint8_t r = 255; | 
 | 749 |     uint8_t g = 0; | 
 | 750 |     uint8_t b = 0; | 
 | 751 |  | 
 | 752 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight / 4); | 
 | 753 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 754 |     setUpProducer(adapter, igbProducer); | 
 | 755 |     { | 
 | 756 |         int slot; | 
 | 757 |         sp<Fence> fence; | 
 | 758 |         sp<GraphicBuffer> buf; | 
 | 759 |         auto ret = igbProducer->dequeueBuffer(&slot, &fence, mDisplayWidth, mDisplayHeight / 4, | 
 | 760 |                                               PIXEL_FORMAT_RGBA_8888, GRALLOC_USAGE_SW_WRITE_OFTEN, | 
 | 761 |                                               nullptr, nullptr); | 
 | 762 |         ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION, ret); | 
 | 763 |         ASSERT_EQ(OK, igbProducer->requestBuffer(slot, &buf)); | 
 | 764 |  | 
 | 765 |         uint32_t* bufData; | 
 | 766 |         buf->lock(static_cast<uint32_t>(GraphicBuffer::USAGE_SW_WRITE_OFTEN), | 
 | 767 |                   reinterpret_cast<void**>(&bufData)); | 
 | 768 |         fillBuffer(bufData, Rect(buf->getWidth(), buf->getHeight()), buf->getStride(), r, g, b); | 
 | 769 |         buf->unlock(); | 
 | 770 |  | 
 | 771 |         IGraphicBufferProducer::QueueBufferOutput qbOutput; | 
 | 772 |         IGraphicBufferProducer::QueueBufferInput input(systemTime(), true /* autotimestamp */, | 
 | 773 |                                                        HAL_DATASPACE_UNKNOWN, {}, | 
 | 774 |                                                        NATIVE_WINDOW_SCALING_MODE_FREEZE, 0, | 
 | 775 |                                                        Fence::NO_FENCE); | 
 | 776 |         igbProducer->queueBuffer(slot, input, &qbOutput); | 
 | 777 |         adapter.waitForCallbacks(); | 
 | 778 |     } | 
 | 779 |     // capture screen and verify that it is red | 
 | 780 |     ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
 | 781 |  | 
 | 782 |     ASSERT_NO_FATAL_FAILURE( | 
 | 783 |             checkScreenCapture(r, g, b, | 
 | 784 |                                {0, 0, (int32_t)mDisplayWidth, (int32_t)mDisplayHeight / 4})); | 
 | 785 |  | 
 | 786 |     // update the size to half the display and dequeue a buffer quarter of the display. | 
 | 787 |     adapter.update(mSurfaceControl, mDisplayWidth, mDisplayHeight / 2); | 
 | 788 |  | 
 | 789 |     { | 
 | 790 |         int slot; | 
 | 791 |         sp<Fence> fence; | 
 | 792 |         sp<GraphicBuffer> buf; | 
 | 793 |         auto ret = igbProducer->dequeueBuffer(&slot, &fence, mDisplayWidth, mDisplayHeight / 8, | 
 | 794 |                                               PIXEL_FORMAT_RGBA_8888, GRALLOC_USAGE_SW_WRITE_OFTEN, | 
 | 795 |                                               nullptr, nullptr); | 
 | 796 |         ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION, ret); | 
 | 797 |         ASSERT_EQ(OK, igbProducer->requestBuffer(slot, &buf)); | 
 | 798 |  | 
 | 799 |         uint32_t* bufData; | 
 | 800 |         buf->lock(static_cast<uint32_t>(GraphicBuffer::USAGE_SW_WRITE_OFTEN), | 
 | 801 |                   reinterpret_cast<void**>(&bufData)); | 
 | 802 |         g = 255; | 
 | 803 |         fillBuffer(bufData, Rect(buf->getWidth(), buf->getHeight()), buf->getStride(), r, g, b); | 
 | 804 |         buf->unlock(); | 
 | 805 |  | 
 | 806 |         IGraphicBufferProducer::QueueBufferOutput qbOutput; | 
 | 807 |         IGraphicBufferProducer::QueueBufferInput input(systemTime(), true /* autotimestamp */, | 
 | 808 |                                                        HAL_DATASPACE_UNKNOWN, {}, | 
 | 809 |                                                        NATIVE_WINDOW_SCALING_MODE_SCALE_TO_WINDOW, | 
 | 810 |                                                        0, Fence::NO_FENCE); | 
 | 811 |         igbProducer->queueBuffer(slot, input, &qbOutput); | 
 | 812 |         adapter.waitForCallbacks(); | 
 | 813 |     } | 
 | 814 |     // capture screen and verify that it is red | 
 | 815 |     ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
 | 816 |     // verify we still scale the buffer to the new size (half the screen height) | 
 | 817 |     ASSERT_NO_FATAL_FAILURE( | 
 | 818 |             checkScreenCapture(r, g, b, | 
 | 819 |                                {0, 0, (int32_t)mDisplayWidth, (int32_t)mDisplayHeight / 2})); | 
 | 820 | } | 
 | 821 |  | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 822 | TEST_F(BLASTBufferQueueTest, SyncThenNoSync) { | 
 | 823 |     uint8_t r = 255; | 
 | 824 |     uint8_t g = 0; | 
 | 825 |     uint8_t b = 0; | 
 | 826 |  | 
 | 827 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 828 |  | 
 | 829 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 830 |     setUpProducer(adapter, igbProducer); | 
 | 831 |  | 
| chaviw | a1c4c82 | 2021-11-10 18:11:58 -0600 | [diff] [blame] | 832 |     Transaction sync; | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 833 |     adapter.setSyncTransaction(sync); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 834 |     queueBuffer(igbProducer, 0, 255, 0, 0); | 
 | 835 |  | 
 | 836 |     // queue non sync buffer, so this one should get blocked | 
 | 837 |     // Add a present delay to allow the first screenshot to get taken. | 
 | 838 |     nsecs_t presentTimeDelay = std::chrono::nanoseconds(500ms).count(); | 
 | 839 |     queueBuffer(igbProducer, r, g, b, presentTimeDelay); | 
 | 840 |  | 
 | 841 |     CallbackHelper transactionCallback; | 
| chaviw | a1c4c82 | 2021-11-10 18:11:58 -0600 | [diff] [blame] | 842 |     sync.addTransactionCompletedCallback(transactionCallback.function, | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 843 |                                          transactionCallback.getContext()) | 
 | 844 |             .apply(); | 
 | 845 |  | 
 | 846 |     CallbackData callbackData; | 
 | 847 |     transactionCallback.getCallbackData(&callbackData); | 
 | 848 |  | 
| chaviw | 0acd33a | 2021-11-02 11:55:37 -0500 | [diff] [blame] | 849 |     // capture screen and verify that it is green | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 850 |     ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
 | 851 |     ASSERT_NO_FATAL_FAILURE( | 
 | 852 |             checkScreenCapture(0, 255, 0, {0, 0, (int32_t)mDisplayWidth, (int32_t)mDisplayHeight})); | 
 | 853 |  | 
 | 854 |     mProducerListener->waitOnNumberReleased(1); | 
 | 855 |     ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
 | 856 |     ASSERT_NO_FATAL_FAILURE( | 
 | 857 |             checkScreenCapture(r, g, b, {0, 0, (int32_t)mDisplayWidth, (int32_t)mDisplayHeight})); | 
 | 858 | } | 
 | 859 |  | 
 | 860 | TEST_F(BLASTBufferQueueTest, MultipleSyncTransactions) { | 
 | 861 |     uint8_t r = 255; | 
 | 862 |     uint8_t g = 0; | 
 | 863 |     uint8_t b = 0; | 
 | 864 |  | 
 | 865 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 866 |  | 
 | 867 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 868 |     setUpProducer(adapter, igbProducer); | 
 | 869 |  | 
 | 870 |     Transaction mainTransaction; | 
 | 871 |  | 
| chaviw | a1c4c82 | 2021-11-10 18:11:58 -0600 | [diff] [blame] | 872 |     Transaction sync; | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 873 |     adapter.setSyncTransaction(sync); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 874 |     queueBuffer(igbProducer, 0, 255, 0, 0); | 
 | 875 |  | 
| chaviw | a1c4c82 | 2021-11-10 18:11:58 -0600 | [diff] [blame] | 876 |     mainTransaction.merge(std::move(sync)); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 877 |  | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 878 |     adapter.setSyncTransaction(sync); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 879 |     queueBuffer(igbProducer, r, g, b, 0); | 
 | 880 |  | 
| chaviw | a1c4c82 | 2021-11-10 18:11:58 -0600 | [diff] [blame] | 881 |     mainTransaction.merge(std::move(sync)); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 882 |     // Expect 1 buffer to be released even before sending to SurfaceFlinger | 
 | 883 |     mProducerListener->waitOnNumberReleased(1); | 
 | 884 |  | 
 | 885 |     CallbackHelper transactionCallback; | 
 | 886 |     mainTransaction | 
 | 887 |             .addTransactionCompletedCallback(transactionCallback.function, | 
 | 888 |                                              transactionCallback.getContext()) | 
 | 889 |             .apply(); | 
 | 890 |  | 
 | 891 |     CallbackData callbackData; | 
 | 892 |     transactionCallback.getCallbackData(&callbackData); | 
 | 893 |  | 
 | 894 |     // capture screen and verify that it is red | 
 | 895 |     ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
 | 896 |     ASSERT_NO_FATAL_FAILURE( | 
 | 897 |             checkScreenCapture(r, g, b, {0, 0, (int32_t)mDisplayWidth, (int32_t)mDisplayHeight})); | 
 | 898 | } | 
 | 899 |  | 
 | 900 | TEST_F(BLASTBufferQueueTest, MultipleSyncTransactionWithNonSync) { | 
 | 901 |     uint8_t r = 255; | 
 | 902 |     uint8_t g = 0; | 
 | 903 |     uint8_t b = 0; | 
 | 904 |  | 
 | 905 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 906 |  | 
 | 907 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 908 |     setUpProducer(adapter, igbProducer); | 
 | 909 |  | 
 | 910 |     Transaction mainTransaction; | 
 | 911 |  | 
| chaviw | a1c4c82 | 2021-11-10 18:11:58 -0600 | [diff] [blame] | 912 |     Transaction sync; | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 913 |     // queue a sync transaction | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 914 |     adapter.setSyncTransaction(sync); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 915 |     queueBuffer(igbProducer, 0, 255, 0, 0); | 
 | 916 |  | 
| chaviw | a1c4c82 | 2021-11-10 18:11:58 -0600 | [diff] [blame] | 917 |     mainTransaction.merge(std::move(sync)); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 918 |  | 
| chaviw | a1c4c82 | 2021-11-10 18:11:58 -0600 | [diff] [blame] | 919 |     // queue another buffer without setting sync transaction | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 920 |     queueBuffer(igbProducer, 0, 0, 255, 0); | 
 | 921 |  | 
 | 922 |     // queue another sync transaction | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 923 |     adapter.setSyncTransaction(sync); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 924 |     queueBuffer(igbProducer, r, g, b, 0); | 
 | 925 |     // Expect 1 buffer to be released because the non sync transaction should merge | 
 | 926 |     // with the sync | 
 | 927 |     mProducerListener->waitOnNumberReleased(1); | 
 | 928 |  | 
| chaviw | a1c4c82 | 2021-11-10 18:11:58 -0600 | [diff] [blame] | 929 |     mainTransaction.merge(std::move(sync)); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 930 |     // Expect 2 buffers to be released due to merging the two syncs. | 
 | 931 |     mProducerListener->waitOnNumberReleased(2); | 
 | 932 |  | 
 | 933 |     CallbackHelper transactionCallback; | 
 | 934 |     mainTransaction | 
 | 935 |             .addTransactionCompletedCallback(transactionCallback.function, | 
 | 936 |                                              transactionCallback.getContext()) | 
 | 937 |             .apply(); | 
 | 938 |  | 
 | 939 |     CallbackData callbackData; | 
 | 940 |     transactionCallback.getCallbackData(&callbackData); | 
 | 941 |  | 
 | 942 |     // capture screen and verify that it is red | 
 | 943 |     ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
 | 944 |     ASSERT_NO_FATAL_FAILURE( | 
 | 945 |             checkScreenCapture(r, g, b, {0, 0, (int32_t)mDisplayWidth, (int32_t)mDisplayHeight})); | 
 | 946 | } | 
 | 947 |  | 
 | 948 | TEST_F(BLASTBufferQueueTest, MultipleSyncRunOutOfBuffers) { | 
 | 949 |     uint8_t r = 255; | 
 | 950 |     uint8_t g = 0; | 
 | 951 |     uint8_t b = 0; | 
 | 952 |  | 
 | 953 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 954 |  | 
 | 955 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 956 |     setUpProducer(adapter, igbProducer, 3); | 
 | 957 |  | 
 | 958 |     Transaction mainTransaction; | 
 | 959 |  | 
| chaviw | a1c4c82 | 2021-11-10 18:11:58 -0600 | [diff] [blame] | 960 |     Transaction sync; | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 961 |     // queue a sync transaction | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 962 |     adapter.setSyncTransaction(sync); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 963 |     queueBuffer(igbProducer, 0, 255, 0, 0); | 
 | 964 |  | 
| chaviw | a1c4c82 | 2021-11-10 18:11:58 -0600 | [diff] [blame] | 965 |     mainTransaction.merge(std::move(sync)); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 966 |  | 
| chaviw | a1c4c82 | 2021-11-10 18:11:58 -0600 | [diff] [blame] | 967 |     // queue a few buffers without setting sync transaction | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 968 |     queueBuffer(igbProducer, 0, 0, 255, 0); | 
 | 969 |     queueBuffer(igbProducer, 0, 0, 255, 0); | 
 | 970 |     queueBuffer(igbProducer, 0, 0, 255, 0); | 
 | 971 |  | 
 | 972 |     // queue another sync transaction | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 973 |     adapter.setSyncTransaction(sync); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 974 |     queueBuffer(igbProducer, r, g, b, 0); | 
 | 975 |     // Expect 3 buffers to be released because the non sync transactions should merge | 
 | 976 |     // with the sync | 
 | 977 |     mProducerListener->waitOnNumberReleased(3); | 
 | 978 |  | 
| chaviw | a1c4c82 | 2021-11-10 18:11:58 -0600 | [diff] [blame] | 979 |     mainTransaction.merge(std::move(sync)); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 980 |     // Expect 4 buffers to be released due to merging the two syncs. | 
 | 981 |     mProducerListener->waitOnNumberReleased(4); | 
 | 982 |  | 
 | 983 |     CallbackHelper transactionCallback; | 
 | 984 |     mainTransaction | 
 | 985 |             .addTransactionCompletedCallback(transactionCallback.function, | 
 | 986 |                                              transactionCallback.getContext()) | 
 | 987 |             .apply(); | 
 | 988 |  | 
 | 989 |     CallbackData callbackData; | 
 | 990 |     transactionCallback.getCallbackData(&callbackData); | 
 | 991 |  | 
 | 992 |     // capture screen and verify that it is red | 
 | 993 |     ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
 | 994 |     ASSERT_NO_FATAL_FAILURE( | 
 | 995 |             checkScreenCapture(r, g, b, {0, 0, (int32_t)mDisplayWidth, (int32_t)mDisplayHeight})); | 
 | 996 | } | 
 | 997 |  | 
 | 998 | // Tests BBQ with a sync transaction when the buffers acquired reaches max and the only way to | 
 | 999 | // continue processing is for a release callback from SurfaceFlinger. | 
 | 1000 | // This is done by sending a buffer to SF so it can release the previous one and allow BBQ to | 
 | 1001 | // continue acquiring buffers. | 
 | 1002 | TEST_F(BLASTBufferQueueTest, RunOutOfBuffersWaitingOnSF) { | 
 | 1003 |     uint8_t r = 255; | 
 | 1004 |     uint8_t g = 0; | 
 | 1005 |     uint8_t b = 0; | 
 | 1006 |  | 
 | 1007 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 1008 |  | 
 | 1009 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 1010 |     setUpProducer(adapter, igbProducer, 4); | 
 | 1011 |  | 
 | 1012 |     Transaction mainTransaction; | 
 | 1013 |  | 
 | 1014 |     // Send a buffer to SF | 
 | 1015 |     queueBuffer(igbProducer, 0, 255, 0, 0); | 
 | 1016 |  | 
| chaviw | a1c4c82 | 2021-11-10 18:11:58 -0600 | [diff] [blame] | 1017 |     Transaction sync; | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 1018 |     // queue a sync transaction | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 1019 |     adapter.setSyncTransaction(sync); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 1020 |     queueBuffer(igbProducer, 0, 255, 0, 0); | 
 | 1021 |  | 
| chaviw | a1c4c82 | 2021-11-10 18:11:58 -0600 | [diff] [blame] | 1022 |     mainTransaction.merge(std::move(sync)); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 1023 |  | 
| chaviw | a1c4c82 | 2021-11-10 18:11:58 -0600 | [diff] [blame] | 1024 |     // queue a few buffers without setting sync transaction | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 1025 |     queueBuffer(igbProducer, 0, 0, 255, 0); | 
 | 1026 |     queueBuffer(igbProducer, 0, 0, 255, 0); | 
 | 1027 |     queueBuffer(igbProducer, 0, 0, 255, 0); | 
 | 1028 |  | 
 | 1029 |     // apply the first synced buffer to ensure we have to wait on SF | 
 | 1030 |     mainTransaction.apply(); | 
 | 1031 |  | 
 | 1032 |     // queue another sync transaction | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 1033 |     adapter.setSyncTransaction(sync); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 1034 |     queueBuffer(igbProducer, r, g, b, 0); | 
 | 1035 |     // Expect 2 buffers to be released because the non sync transactions should merge | 
 | 1036 |     // with the sync | 
 | 1037 |     mProducerListener->waitOnNumberReleased(3); | 
 | 1038 |  | 
| chaviw | a1c4c82 | 2021-11-10 18:11:58 -0600 | [diff] [blame] | 1039 |     mainTransaction.merge(std::move(sync)); | 
| chaviw | d7deef7 | 2021-10-06 11:53:40 -0500 | [diff] [blame] | 1040 |  | 
 | 1041 |     CallbackHelper transactionCallback; | 
 | 1042 |     mainTransaction | 
 | 1043 |             .addTransactionCompletedCallback(transactionCallback.function, | 
 | 1044 |                                              transactionCallback.getContext()) | 
 | 1045 |             .apply(); | 
 | 1046 |  | 
 | 1047 |     CallbackData callbackData; | 
 | 1048 |     transactionCallback.getCallbackData(&callbackData); | 
 | 1049 |  | 
 | 1050 |     // capture screen and verify that it is red | 
 | 1051 |     ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
 | 1052 |     ASSERT_NO_FATAL_FAILURE( | 
 | 1053 |             checkScreenCapture(r, g, b, {0, 0, (int32_t)mDisplayWidth, (int32_t)mDisplayHeight})); | 
 | 1054 | } | 
 | 1055 |  | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 1056 | TEST_F(BLASTBufferQueueTest, SyncNextTransactionAcquireMultipleBuffers) { | 
| chaviw | 0acd33a | 2021-11-02 11:55:37 -0500 | [diff] [blame] | 1057 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 1058 |  | 
 | 1059 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 1060 |     setUpProducer(adapter, igbProducer); | 
 | 1061 |  | 
 | 1062 |     Transaction next; | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 1063 |     adapter.setSyncTransaction(next, false); | 
| chaviw | 0acd33a | 2021-11-02 11:55:37 -0500 | [diff] [blame] | 1064 |     queueBuffer(igbProducer, 0, 255, 0, 0); | 
 | 1065 |     queueBuffer(igbProducer, 0, 0, 255, 0); | 
 | 1066 |     // There should only be one frame submitted since the first frame will be released. | 
 | 1067 |     adapter.validateNumFramesSubmitted(1); | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 1068 |     adapter.stopContinuousSyncTransaction(); | 
| chaviw | 0acd33a | 2021-11-02 11:55:37 -0500 | [diff] [blame] | 1069 |  | 
 | 1070 |     // queue non sync buffer, so this one should get blocked | 
 | 1071 |     // Add a present delay to allow the first screenshot to get taken. | 
 | 1072 |     nsecs_t presentTimeDelay = std::chrono::nanoseconds(500ms).count(); | 
 | 1073 |     queueBuffer(igbProducer, 255, 0, 0, presentTimeDelay); | 
 | 1074 |  | 
 | 1075 |     CallbackHelper transactionCallback; | 
 | 1076 |     next.addTransactionCompletedCallback(transactionCallback.function, | 
 | 1077 |                                          transactionCallback.getContext()) | 
 | 1078 |             .apply(); | 
 | 1079 |  | 
 | 1080 |     CallbackData callbackData; | 
 | 1081 |     transactionCallback.getCallbackData(&callbackData); | 
 | 1082 |  | 
 | 1083 |     // capture screen and verify that it is blue | 
 | 1084 |     ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
 | 1085 |     ASSERT_NO_FATAL_FAILURE( | 
 | 1086 |             checkScreenCapture(0, 0, 255, {0, 0, (int32_t)mDisplayWidth, (int32_t)mDisplayHeight})); | 
 | 1087 |  | 
 | 1088 |     mProducerListener->waitOnNumberReleased(2); | 
 | 1089 |     // capture screen and verify that it is red | 
 | 1090 |     ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
 | 1091 |     ASSERT_NO_FATAL_FAILURE( | 
 | 1092 |             checkScreenCapture(255, 0, 0, {0, 0, (int32_t)mDisplayWidth, (int32_t)mDisplayHeight})); | 
 | 1093 | } | 
 | 1094 |  | 
| chaviw | 3b4bdcf | 2022-03-17 09:27:03 -0500 | [diff] [blame] | 1095 | TEST_F(BLASTBufferQueueTest, SyncNextTransactionOverwrite) { | 
 | 1096 |     std::mutex mutex; | 
 | 1097 |     std::condition_variable callbackReceivedCv; | 
 | 1098 |     bool receivedCallback = false; | 
 | 1099 |  | 
 | 1100 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 1101 |     ASSERT_EQ(nullptr, adapter.getTransactionReadyCallback()); | 
 | 1102 |     auto callback = [&](Transaction*) { | 
 | 1103 |         std::unique_lock<std::mutex> lock(mutex); | 
 | 1104 |         receivedCallback = true; | 
 | 1105 |         callbackReceivedCv.notify_one(); | 
 | 1106 |     }; | 
 | 1107 |     adapter.syncNextTransaction(callback); | 
 | 1108 |     ASSERT_NE(nullptr, adapter.getTransactionReadyCallback()); | 
 | 1109 |  | 
 | 1110 |     auto callback2 = [](Transaction*) {}; | 
 | 1111 |     adapter.syncNextTransaction(callback2); | 
 | 1112 |  | 
 | 1113 |     std::unique_lock<std::mutex> lock(mutex); | 
 | 1114 |     if (!receivedCallback) { | 
 | 1115 |         ASSERT_NE(callbackReceivedCv.wait_for(lock, std::chrono::seconds(3)), | 
 | 1116 |                   std::cv_status::timeout) | 
 | 1117 |                 << "did not receive callback"; | 
 | 1118 |     } | 
 | 1119 |  | 
 | 1120 |     ASSERT_TRUE(receivedCallback); | 
 | 1121 | } | 
 | 1122 |  | 
| chaviw | c1cf402 | 2022-06-03 13:32:33 -0500 | [diff] [blame] | 1123 | TEST_F(BLASTBufferQueueTest, SyncNextTransactionDropBuffer) { | 
 | 1124 |     uint8_t r = 255; | 
 | 1125 |     uint8_t g = 0; | 
 | 1126 |     uint8_t b = 0; | 
 | 1127 |  | 
 | 1128 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 1129 |  | 
 | 1130 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 1131 |     setUpProducer(adapter, igbProducer); | 
 | 1132 |  | 
 | 1133 |     Transaction sync; | 
 | 1134 |     adapter.setSyncTransaction(sync); | 
 | 1135 |     queueBuffer(igbProducer, 0, 255, 0, 0); | 
 | 1136 |  | 
 | 1137 |     // Merge a transaction that has a complete callback into the next frame so we can get notified | 
 | 1138 |     // when to take a screenshot | 
 | 1139 |     CallbackHelper transactionCallback; | 
 | 1140 |     Transaction t; | 
 | 1141 |     t.addTransactionCompletedCallback(transactionCallback.function, | 
 | 1142 |                                       transactionCallback.getContext()); | 
 | 1143 |     adapter.mergeWithNextTransaction(&t, 2); | 
 | 1144 |     queueBuffer(igbProducer, r, g, b, 0); | 
 | 1145 |  | 
 | 1146 |     // Drop the buffer, but ensure the next one continues to get processed. | 
 | 1147 |     sync.setBuffer(mSurfaceControl, nullptr); | 
 | 1148 |  | 
 | 1149 |     CallbackData callbackData; | 
 | 1150 |     transactionCallback.getCallbackData(&callbackData); | 
 | 1151 |     ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
 | 1152 |     ASSERT_NO_FATAL_FAILURE( | 
 | 1153 |             checkScreenCapture(r, g, b, {0, 0, (int32_t)mDisplayWidth, (int32_t)mDisplayHeight})); | 
| Rob Carr | 4f797ab | 2022-07-07 18:29:22 +0000 | [diff] [blame] | 1154 |     sync.apply(); | 
| chaviw | c1cf402 | 2022-06-03 13:32:33 -0500 | [diff] [blame] | 1155 | } | 
 | 1156 |  | 
| Vishnu Nair | 1e8bf10 | 2021-12-28 14:36:59 -0800 | [diff] [blame] | 1157 | // This test will currently fail because the old surfacecontrol will steal the last presented buffer | 
 | 1158 | // until the old surface control is destroyed. This is not necessarily a bug but to document a | 
 | 1159 | // limitation with the update API and to test any changes to make the api more robust. The current | 
 | 1160 | // approach for the client is to recreate the blastbufferqueue when the surfacecontrol updates. | 
 | 1161 | TEST_F(BLASTBufferQueueTest, DISABLED_DisconnectProducerTest) { | 
 | 1162 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 1163 |     std::vector<sp<SurfaceControl>> surfaceControls; | 
 | 1164 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 1165 |     for (int i = 0; i < 10; i++) { | 
 | 1166 |         sp<SurfaceControl> sc = | 
 | 1167 |                 mClient->createSurface(String8("TestSurface"), mDisplayWidth, mDisplayHeight, | 
 | 1168 |                                        PIXEL_FORMAT_RGBA_8888, | 
 | 1169 |                                        ISurfaceComposerClient::eFXSurfaceBufferState, | 
 | 1170 |                                        /*parent*/ nullptr); | 
 | 1171 |         Transaction() | 
 | 1172 |                 .setLayerStack(mSurfaceControl, ui::DEFAULT_LAYER_STACK) | 
 | 1173 |                 .setLayer(mSurfaceControl, std::numeric_limits<int32_t>::max()) | 
 | 1174 |                 .show(mSurfaceControl) | 
 | 1175 |                 .setDataspace(mSurfaceControl, ui::Dataspace::V0_SRGB) | 
 | 1176 |                 .apply(true); | 
 | 1177 |         surfaceControls.push_back(sc); | 
 | 1178 |         adapter.update(sc, mDisplayWidth, mDisplayHeight); | 
 | 1179 |  | 
 | 1180 |         setUpProducer(adapter, igbProducer); | 
 | 1181 |         Transaction next; | 
 | 1182 |         queueBuffer(igbProducer, 0, 255, 0, 0); | 
 | 1183 |         queueBuffer(igbProducer, 0, 0, 255, 0); | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 1184 |         adapter.setSyncTransaction(next, true); | 
| Vishnu Nair | 1e8bf10 | 2021-12-28 14:36:59 -0800 | [diff] [blame] | 1185 |         queueBuffer(igbProducer, 255, 0, 0, 0); | 
 | 1186 |  | 
 | 1187 |         CallbackHelper transactionCallback; | 
 | 1188 |         next.addTransactionCompletedCallback(transactionCallback.function, | 
 | 1189 |                                              transactionCallback.getContext()) | 
 | 1190 |                 .apply(); | 
 | 1191 |  | 
 | 1192 |         CallbackData callbackData; | 
 | 1193 |         transactionCallback.getCallbackData(&callbackData); | 
 | 1194 |         // capture screen and verify that it is red | 
 | 1195 |         ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
 | 1196 |         ASSERT_NO_FATAL_FAILURE( | 
 | 1197 |                 checkScreenCapture(255, 0, 0, | 
 | 1198 |                                    {0, 0, (int32_t)mDisplayWidth, (int32_t)mDisplayHeight})); | 
 | 1199 |         igbProducer->disconnect(NATIVE_WINDOW_API_CPU); | 
 | 1200 |     } | 
 | 1201 | } | 
 | 1202 |  | 
 | 1203 | // See DISABLED_DisconnectProducerTest | 
 | 1204 | TEST_F(BLASTBufferQueueTest, DISABLED_UpdateSurfaceControlTest) { | 
 | 1205 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 1206 |     std::vector<sp<SurfaceControl>> surfaceControls; | 
 | 1207 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 1208 |     for (int i = 0; i < 10; i++) { | 
 | 1209 |         sp<SurfaceControl> sc = | 
 | 1210 |                 mClient->createSurface(String8("TestSurface"), mDisplayWidth, mDisplayHeight, | 
 | 1211 |                                        PIXEL_FORMAT_RGBA_8888, | 
 | 1212 |                                        ISurfaceComposerClient::eFXSurfaceBufferState, | 
 | 1213 |                                        /*parent*/ nullptr); | 
 | 1214 |         Transaction() | 
 | 1215 |                 .setLayerStack(mSurfaceControl, ui::DEFAULT_LAYER_STACK) | 
 | 1216 |                 .setLayer(mSurfaceControl, std::numeric_limits<int32_t>::max()) | 
 | 1217 |                 .show(mSurfaceControl) | 
 | 1218 |                 .setDataspace(mSurfaceControl, ui::Dataspace::V0_SRGB) | 
 | 1219 |                 .apply(true); | 
 | 1220 |         surfaceControls.push_back(sc); | 
 | 1221 |         adapter.update(sc, mDisplayWidth, mDisplayHeight); | 
 | 1222 |         setUpProducer(adapter, igbProducer); | 
 | 1223 |  | 
 | 1224 |         Transaction next; | 
 | 1225 |         queueBuffer(igbProducer, 0, 255, 0, 0); | 
 | 1226 |         queueBuffer(igbProducer, 0, 0, 255, 0); | 
| Tianhao Yao | 4861b10 | 2022-02-03 20:18:35 +0000 | [diff] [blame] | 1227 |         adapter.setSyncTransaction(next, true); | 
| Vishnu Nair | 1e8bf10 | 2021-12-28 14:36:59 -0800 | [diff] [blame] | 1228 |         queueBuffer(igbProducer, 255, 0, 0, 0); | 
 | 1229 |  | 
 | 1230 |         CallbackHelper transactionCallback; | 
 | 1231 |         next.addTransactionCompletedCallback(transactionCallback.function, | 
 | 1232 |                                              transactionCallback.getContext()) | 
 | 1233 |                 .apply(); | 
 | 1234 |  | 
 | 1235 |         CallbackData callbackData; | 
 | 1236 |         transactionCallback.getCallbackData(&callbackData); | 
 | 1237 |         // capture screen and verify that it is red | 
 | 1238 |         ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
 | 1239 |         ASSERT_NO_FATAL_FAILURE( | 
 | 1240 |                 checkScreenCapture(255, 0, 0, | 
 | 1241 |                                    {0, 0, (int32_t)mDisplayWidth, (int32_t)mDisplayHeight})); | 
 | 1242 |     } | 
 | 1243 | } | 
 | 1244 |  | 
| Vishnu Nair | 8949612 | 2020-12-14 17:14:53 -0800 | [diff] [blame] | 1245 | class TestProducerListener : public BnProducerListener { | 
 | 1246 | public: | 
 | 1247 |     sp<IGraphicBufferProducer> mIgbp; | 
 | 1248 |     TestProducerListener(const sp<IGraphicBufferProducer>& igbp) : mIgbp(igbp) {} | 
 | 1249 |     void onBufferReleased() override { | 
 | 1250 |         sp<GraphicBuffer> buffer; | 
 | 1251 |         sp<Fence> fence; | 
 | 1252 |         mIgbp->detachNextBuffer(&buffer, &fence); | 
 | 1253 |     } | 
 | 1254 | }; | 
 | 1255 |  | 
 | 1256 | TEST_F(BLASTBufferQueueTest, CustomProducerListener) { | 
 | 1257 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 1258 |     sp<IGraphicBufferProducer> igbProducer = adapter.getIGraphicBufferProducer(); | 
 | 1259 |     ASSERT_NE(nullptr, igbProducer.get()); | 
 | 1260 |     ASSERT_EQ(NO_ERROR, igbProducer->setMaxDequeuedBufferCount(2)); | 
 | 1261 |     IGraphicBufferProducer::QueueBufferOutput qbOutput; | 
 | 1262 |     ASSERT_EQ(NO_ERROR, | 
 | 1263 |               igbProducer->connect(new TestProducerListener(igbProducer), NATIVE_WINDOW_API_CPU, | 
 | 1264 |                                    false, &qbOutput)); | 
 | 1265 |     ASSERT_NE(ui::Transform::ROT_INVALID, qbOutput.transformHint); | 
 | 1266 |     for (int i = 0; i < 3; i++) { | 
 | 1267 |         int slot; | 
 | 1268 |         sp<Fence> fence; | 
 | 1269 |         sp<GraphicBuffer> buf; | 
 | 1270 |         auto ret = igbProducer->dequeueBuffer(&slot, &fence, mDisplayWidth, mDisplayHeight, | 
 | 1271 |                                               PIXEL_FORMAT_RGBA_8888, GRALLOC_USAGE_SW_WRITE_OFTEN, | 
 | 1272 |                                               nullptr, nullptr); | 
 | 1273 |         ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION, ret); | 
 | 1274 |         ASSERT_EQ(OK, igbProducer->requestBuffer(slot, &buf)); | 
 | 1275 |         IGraphicBufferProducer::QueueBufferOutput qbOutput; | 
| Vishnu Nair | 1506b18 | 2021-02-22 14:35:15 -0800 | [diff] [blame] | 1276 |         IGraphicBufferProducer::QueueBufferInput input(systemTime(), true /* autotimestamp */, | 
 | 1277 |                                                        HAL_DATASPACE_UNKNOWN, | 
| Vishnu Nair | 8949612 | 2020-12-14 17:14:53 -0800 | [diff] [blame] | 1278 |                                                        Rect(mDisplayWidth, mDisplayHeight), | 
 | 1279 |                                                        NATIVE_WINDOW_SCALING_MODE_FREEZE, 0, | 
 | 1280 |                                                        Fence::NO_FENCE); | 
 | 1281 |         igbProducer->queueBuffer(slot, input, &qbOutput); | 
 | 1282 |     } | 
 | 1283 |     adapter.waitForCallbacks(); | 
 | 1284 | } | 
 | 1285 |  | 
| Vishnu Nair | 17dde61 | 2020-12-28 11:39:59 -0800 | [diff] [blame] | 1286 | TEST_F(BLASTBufferQueueTest, QueryNativeWindowQueuesToWindowComposer) { | 
 | 1287 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 1288 |  | 
 | 1289 |     sp<android::Surface> surface = new Surface(adapter.getIGraphicBufferProducer()); | 
 | 1290 |     ANativeWindow* nativeWindow = (ANativeWindow*)(surface.get()); | 
 | 1291 |     int queuesToNativeWindow = 0; | 
 | 1292 |     int err = nativeWindow->query(nativeWindow, NATIVE_WINDOW_QUEUES_TO_WINDOW_COMPOSER, | 
 | 1293 |                                   &queuesToNativeWindow); | 
 | 1294 |     ASSERT_EQ(NO_ERROR, err); | 
 | 1295 |     ASSERT_EQ(queuesToNativeWindow, 1); | 
 | 1296 | } | 
 | 1297 |  | 
| Vishnu Nair | 083efd3 | 2021-02-12 09:32:30 -0800 | [diff] [blame] | 1298 | // Test a slow producer doesn't hold up a faster producer from the same client. Essentially tests | 
 | 1299 | // BBQ uses separate transaction queues. | 
| Vishnu Nair | 277142c | 2021-01-05 18:35:29 -0800 | [diff] [blame] | 1300 | TEST_F(BLASTBufferQueueTest, OutOfOrderTransactionTest) { | 
 | 1301 |     sp<SurfaceControl> bgSurface = | 
 | 1302 |             mClient->createSurface(String8("BGTest"), 0, 0, PIXEL_FORMAT_RGBA_8888, | 
 | 1303 |                                    ISurfaceComposerClient::eFXSurfaceBufferState); | 
 | 1304 |     ASSERT_NE(nullptr, bgSurface.get()); | 
 | 1305 |     Transaction t; | 
| Dominik Laskowski | 29fa146 | 2021-04-27 15:51:50 -0700 | [diff] [blame] | 1306 |     t.setLayerStack(bgSurface, ui::DEFAULT_LAYER_STACK) | 
| Vishnu Nair | 277142c | 2021-01-05 18:35:29 -0800 | [diff] [blame] | 1307 |             .show(bgSurface) | 
 | 1308 |             .setDataspace(bgSurface, ui::Dataspace::V0_SRGB) | 
| Vishnu Nair | 277142c | 2021-01-05 18:35:29 -0800 | [diff] [blame] | 1309 |             .setLayer(bgSurface, std::numeric_limits<int32_t>::max() - 1) | 
 | 1310 |             .apply(); | 
 | 1311 |  | 
 | 1312 |     BLASTBufferQueueHelper slowAdapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 1313 |     sp<IGraphicBufferProducer> slowIgbProducer; | 
 | 1314 |     setUpProducer(slowAdapter, slowIgbProducer); | 
 | 1315 |     nsecs_t presentTimeDelay = std::chrono::nanoseconds(500ms).count(); | 
| Vishnu Nair | 1506b18 | 2021-02-22 14:35:15 -0800 | [diff] [blame] | 1316 |     queueBuffer(slowIgbProducer, 0 /* r */, 255 /* g */, 0 /* b */, presentTimeDelay); | 
| Vishnu Nair | 277142c | 2021-01-05 18:35:29 -0800 | [diff] [blame] | 1317 |  | 
 | 1318 |     BLASTBufferQueueHelper fastAdapter(bgSurface, mDisplayWidth, mDisplayHeight); | 
 | 1319 |     sp<IGraphicBufferProducer> fastIgbProducer; | 
 | 1320 |     setUpProducer(fastAdapter, fastIgbProducer); | 
 | 1321 |     uint8_t r = 255; | 
 | 1322 |     uint8_t g = 0; | 
 | 1323 |     uint8_t b = 0; | 
 | 1324 |     queueBuffer(fastIgbProducer, r, g, b, 0 /* presentTimeDelay */); | 
 | 1325 |     fastAdapter.waitForCallbacks(); | 
 | 1326 |  | 
 | 1327 |     // capture screen and verify that it is red | 
 | 1328 |     ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
 | 1329 |  | 
 | 1330 |     ASSERT_NO_FATAL_FAILURE( | 
| Chavi Weingarten | a5aedbd | 2021-04-09 13:37:33 +0000 | [diff] [blame] | 1331 |             checkScreenCapture(r, g, b, | 
 | 1332 |                                {0, 0, (int32_t)mDisplayWidth, (int32_t)mDisplayHeight / 2})); | 
| Vishnu Nair | 277142c | 2021-01-05 18:35:29 -0800 | [diff] [blame] | 1333 | } | 
 | 1334 |  | 
| Vishnu Nair | a4fbca5 | 2021-07-07 16:52:34 -0700 | [diff] [blame] | 1335 | TEST_F(BLASTBufferQueueTest, TransformHint) { | 
 | 1336 |     // Transform hint is provided to BBQ via the surface control passed by WM | 
 | 1337 |     mSurfaceControl->setTransformHint(ui::Transform::ROT_90); | 
 | 1338 |  | 
 | 1339 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 1340 |     sp<IGraphicBufferProducer> igbProducer = adapter.getIGraphicBufferProducer(); | 
 | 1341 |     ASSERT_NE(nullptr, igbProducer.get()); | 
 | 1342 |     ASSERT_EQ(NO_ERROR, igbProducer->setMaxDequeuedBufferCount(2)); | 
 | 1343 |     sp<Surface> surface = adapter.getSurface(); | 
 | 1344 |  | 
 | 1345 |     // Before connecting to the surface, we do not get a valid transform hint | 
 | 1346 |     int transformHint; | 
 | 1347 |     surface->query(NATIVE_WINDOW_TRANSFORM_HINT, &transformHint); | 
 | 1348 |     ASSERT_EQ(ui::Transform::ROT_0, transformHint); | 
 | 1349 |  | 
 | 1350 |     ASSERT_EQ(NO_ERROR, | 
 | 1351 |               surface->connect(NATIVE_WINDOW_API_CPU, new TestProducerListener(igbProducer))); | 
 | 1352 |  | 
 | 1353 |     // After connecting to the surface, we should get the correct hint. | 
 | 1354 |     surface->query(NATIVE_WINDOW_TRANSFORM_HINT, &transformHint); | 
 | 1355 |     ASSERT_EQ(ui::Transform::ROT_90, transformHint); | 
 | 1356 |  | 
 | 1357 |     ANativeWindow_Buffer buffer; | 
 | 1358 |     surface->lock(&buffer, nullptr /* inOutDirtyBounds */); | 
 | 1359 |  | 
 | 1360 |     // Transform hint is updated via callbacks or surface control updates | 
 | 1361 |     mSurfaceControl->setTransformHint(ui::Transform::ROT_0); | 
 | 1362 |     adapter.update(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 1363 |  | 
 | 1364 |     // The hint does not change and matches the value used when dequeueing the buffer. | 
 | 1365 |     surface->query(NATIVE_WINDOW_TRANSFORM_HINT, &transformHint); | 
 | 1366 |     ASSERT_EQ(ui::Transform::ROT_90, transformHint); | 
 | 1367 |  | 
 | 1368 |     surface->unlockAndPost(); | 
 | 1369 |  | 
 | 1370 |     // After queuing the buffer, we get the updated transform hint | 
 | 1371 |     surface->query(NATIVE_WINDOW_TRANSFORM_HINT, &transformHint); | 
 | 1372 |     ASSERT_EQ(ui::Transform::ROT_0, transformHint); | 
 | 1373 |  | 
 | 1374 |     adapter.waitForCallbacks(); | 
 | 1375 | } | 
 | 1376 |  | 
| Valerie Hau | 5977fc8 | 2019-12-05 15:56:39 -0800 | [diff] [blame] | 1377 | class BLASTBufferQueueTransformTest : public BLASTBufferQueueTest { | 
 | 1378 | public: | 
 | 1379 |     void test(uint32_t tr) { | 
 | 1380 |         BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 1381 |         sp<IGraphicBufferProducer> igbProducer; | 
 | 1382 |         setUpProducer(adapter, igbProducer); | 
 | 1383 |  | 
 | 1384 |         auto bufWidth = mDisplayWidth; | 
 | 1385 |         auto bufHeight = mDisplayHeight; | 
 | 1386 |         int slot; | 
 | 1387 |         sp<Fence> fence; | 
 | 1388 |         sp<GraphicBuffer> buf; | 
 | 1389 |  | 
 | 1390 |         auto ret = igbProducer->dequeueBuffer(&slot, &fence, bufWidth, bufHeight, | 
 | 1391 |                                               PIXEL_FORMAT_RGBA_8888, GRALLOC_USAGE_SW_WRITE_OFTEN, | 
 | 1392 |                                               nullptr, nullptr); | 
 | 1393 |         ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION, ret); | 
 | 1394 |         ASSERT_EQ(OK, igbProducer->requestBuffer(slot, &buf)); | 
 | 1395 |  | 
 | 1396 |         fillQuadrants(buf); | 
 | 1397 |  | 
 | 1398 |         IGraphicBufferProducer::QueueBufferOutput qbOutput; | 
| Vishnu Nair | 1506b18 | 2021-02-22 14:35:15 -0800 | [diff] [blame] | 1399 |         IGraphicBufferProducer::QueueBufferInput input(systemTime(), true /* autotimestamp */, | 
 | 1400 |                                                        HAL_DATASPACE_UNKNOWN, | 
| Valerie Hau | 5977fc8 | 2019-12-05 15:56:39 -0800 | [diff] [blame] | 1401 |                                                        Rect(bufWidth, bufHeight), | 
| Vishnu Nair | e1a4232 | 2020-10-02 17:42:04 -0700 | [diff] [blame] | 1402 |                                                        NATIVE_WINDOW_SCALING_MODE_SCALE_TO_WINDOW, | 
 | 1403 |                                                        tr, Fence::NO_FENCE); | 
| Valerie Hau | 5977fc8 | 2019-12-05 15:56:39 -0800 | [diff] [blame] | 1404 |         igbProducer->queueBuffer(slot, input, &qbOutput); | 
| Dominik Laskowski | 718f960 | 2019-11-09 20:01:35 -0800 | [diff] [blame] | 1405 |         ASSERT_NE(ui::Transform::ROT_INVALID, qbOutput.transformHint); | 
| Valerie Hau | 5977fc8 | 2019-12-05 15:56:39 -0800 | [diff] [blame] | 1406 |  | 
 | 1407 |         adapter.waitForCallbacks(); | 
| chaviw | 8ffc7b8 | 2020-08-18 11:25:37 -0700 | [diff] [blame] | 1408 |         ASSERT_EQ(NO_ERROR, captureDisplay(mCaptureArgs, mCaptureResults)); | 
| chaviw | d243289 | 2020-07-24 17:42:39 -0700 | [diff] [blame] | 1409 |  | 
| Valerie Hau | 5977fc8 | 2019-12-05 15:56:39 -0800 | [diff] [blame] | 1410 |         switch (tr) { | 
 | 1411 |             case ui::Transform::ROT_0: | 
 | 1412 |                 ASSERT_NO_FATAL_FAILURE(checkScreenCapture(0, 0, 0, | 
 | 1413 |                                                            {0, 0, (int32_t)mDisplayWidth / 2, | 
 | 1414 |                                                             (int32_t)mDisplayHeight / 2}, | 
 | 1415 |                                                            1)); | 
 | 1416 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1417 |                         checkScreenCapture(255, 0, 0, | 
 | 1418 |                                            {(int32_t)mDisplayWidth / 2, 0, (int32_t)mDisplayWidth, | 
 | 1419 |                                             (int32_t)mDisplayHeight / 2}, | 
 | 1420 |                                            1)); | 
 | 1421 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1422 |                         checkScreenCapture(0, 255, 0, | 
 | 1423 |                                            {(int32_t)mDisplayWidth / 2, (int32_t)mDisplayHeight / 2, | 
 | 1424 |                                             (int32_t)mDisplayWidth, (int32_t)mDisplayHeight}, | 
 | 1425 |                                            1)); | 
 | 1426 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1427 |                         checkScreenCapture(0, 0, 255, | 
 | 1428 |                                            {0, (int32_t)mDisplayHeight / 2, | 
 | 1429 |                                             (int32_t)mDisplayWidth / 2, (int32_t)mDisplayHeight}, | 
 | 1430 |                                            1)); | 
 | 1431 |                 break; | 
 | 1432 |             case ui::Transform::FLIP_H: | 
 | 1433 |                 ASSERT_NO_FATAL_FAILURE(checkScreenCapture(255, 0, 0, | 
 | 1434 |                                                            {0, 0, (int32_t)mDisplayWidth / 2, | 
 | 1435 |                                                             (int32_t)mDisplayHeight / 2}, | 
 | 1436 |                                                            1)); | 
 | 1437 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1438 |                         checkScreenCapture(0, 0, 0, | 
 | 1439 |                                            {(int32_t)mDisplayWidth / 2, 0, (int32_t)mDisplayWidth, | 
 | 1440 |                                             (int32_t)mDisplayHeight / 2}, | 
 | 1441 |                                            1)); | 
 | 1442 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1443 |                         checkScreenCapture(0, 0, 255, | 
 | 1444 |                                            {(int32_t)mDisplayWidth / 2, (int32_t)mDisplayHeight / 2, | 
 | 1445 |                                             (int32_t)mDisplayWidth, (int32_t)mDisplayHeight}, | 
 | 1446 |                                            1)); | 
 | 1447 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1448 |                         checkScreenCapture(0, 255, 0, | 
 | 1449 |                                            {0, (int32_t)mDisplayHeight / 2, | 
 | 1450 |                                             (int32_t)mDisplayWidth / 2, (int32_t)mDisplayHeight}, | 
 | 1451 |                                            1)); | 
 | 1452 |                 break; | 
 | 1453 |             case ui::Transform::FLIP_V: | 
 | 1454 |                 ASSERT_NO_FATAL_FAILURE(checkScreenCapture(0, 0, 255, | 
 | 1455 |                                                            {0, 0, (int32_t)mDisplayWidth / 2, | 
 | 1456 |                                                             (int32_t)mDisplayHeight / 2}, | 
 | 1457 |                                                            1)); | 
 | 1458 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1459 |                         checkScreenCapture(0, 255, 0, | 
 | 1460 |                                            {(int32_t)mDisplayWidth / 2, 0, (int32_t)mDisplayWidth, | 
 | 1461 |                                             (int32_t)mDisplayHeight / 2}, | 
 | 1462 |                                            1)); | 
 | 1463 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1464 |                         checkScreenCapture(255, 0, 0, | 
 | 1465 |                                            {(int32_t)mDisplayWidth / 2, (int32_t)mDisplayHeight / 2, | 
 | 1466 |                                             (int32_t)mDisplayWidth, (int32_t)mDisplayHeight}, | 
 | 1467 |                                            1)); | 
 | 1468 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1469 |                         checkScreenCapture(0, 0, 0, | 
 | 1470 |                                            {0, (int32_t)mDisplayHeight / 2, | 
 | 1471 |                                             (int32_t)mDisplayWidth / 2, (int32_t)mDisplayHeight}, | 
 | 1472 |                                            1)); | 
 | 1473 |                 break; | 
 | 1474 |             case ui::Transform::ROT_90: | 
 | 1475 |                 ASSERT_NO_FATAL_FAILURE(checkScreenCapture(0, 0, 255, | 
 | 1476 |                                                            {0, 0, (int32_t)mDisplayWidth / 2, | 
 | 1477 |                                                             (int32_t)mDisplayHeight / 2}, | 
 | 1478 |                                                            1)); | 
 | 1479 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1480 |                         checkScreenCapture(0, 0, 0, | 
 | 1481 |                                            {(int32_t)mDisplayWidth / 2, 0, (int32_t)mDisplayWidth, | 
 | 1482 |                                             (int32_t)mDisplayHeight / 2}, | 
 | 1483 |                                            1)); | 
 | 1484 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1485 |                         checkScreenCapture(255, 0, 0, | 
 | 1486 |                                            {(int32_t)mDisplayWidth / 2, (int32_t)mDisplayHeight / 2, | 
 | 1487 |                                             (int32_t)mDisplayWidth, (int32_t)mDisplayHeight}, | 
 | 1488 |                                            1)); | 
 | 1489 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1490 |                         checkScreenCapture(0, 255, 0, | 
 | 1491 |                                            {0, (int32_t)mDisplayHeight / 2, | 
 | 1492 |                                             (int32_t)mDisplayWidth / 2, (int32_t)mDisplayHeight}, | 
 | 1493 |                                            1)); | 
 | 1494 |                 break; | 
 | 1495 |             case ui::Transform::ROT_180: | 
 | 1496 |                 ASSERT_NO_FATAL_FAILURE(checkScreenCapture(0, 255, 0, | 
 | 1497 |                                                            {0, 0, (int32_t)mDisplayWidth / 2, | 
 | 1498 |                                                             (int32_t)mDisplayHeight / 2}, | 
 | 1499 |                                                            1)); | 
 | 1500 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1501 |                         checkScreenCapture(0, 0, 255, | 
 | 1502 |                                            {(int32_t)mDisplayWidth / 2, 0, (int32_t)mDisplayWidth, | 
 | 1503 |                                             (int32_t)mDisplayHeight / 2}, | 
 | 1504 |                                            1)); | 
 | 1505 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1506 |                         checkScreenCapture(0, 0, 0, | 
 | 1507 |                                            {(int32_t)mDisplayWidth / 2, (int32_t)mDisplayHeight / 2, | 
 | 1508 |                                             (int32_t)mDisplayWidth, (int32_t)mDisplayHeight}, | 
 | 1509 |                                            1)); | 
 | 1510 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1511 |                         checkScreenCapture(255, 0, 0, | 
 | 1512 |                                            {0, (int32_t)mDisplayHeight / 2, | 
 | 1513 |                                             (int32_t)mDisplayWidth / 2, (int32_t)mDisplayHeight}, | 
 | 1514 |                                            1)); | 
 | 1515 |                 break; | 
 | 1516 |             case ui::Transform::ROT_270: | 
 | 1517 |                 ASSERT_NO_FATAL_FAILURE(checkScreenCapture(255, 0, 0, | 
 | 1518 |                                                            {0, 0, (int32_t)mDisplayWidth / 2, | 
 | 1519 |                                                             (int32_t)mDisplayHeight / 2}, | 
 | 1520 |                                                            1)); | 
 | 1521 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1522 |                         checkScreenCapture(0, 255, 0, | 
 | 1523 |                                            {(int32_t)mDisplayWidth / 2, 0, (int32_t)mDisplayWidth, | 
 | 1524 |                                             (int32_t)mDisplayHeight / 2}, | 
 | 1525 |                                            1)); | 
 | 1526 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1527 |                         checkScreenCapture(0, 0, 255, | 
 | 1528 |                                            {(int32_t)mDisplayWidth / 2, (int32_t)mDisplayHeight / 2, | 
 | 1529 |                                             (int32_t)mDisplayWidth, (int32_t)mDisplayHeight}, | 
 | 1530 |                                            1)); | 
 | 1531 |                 ASSERT_NO_FATAL_FAILURE( | 
 | 1532 |                         checkScreenCapture(0, 0, 0, | 
 | 1533 |                                            {0, (int32_t)mDisplayHeight / 2, | 
 | 1534 |                                             (int32_t)mDisplayWidth / 2, (int32_t)mDisplayHeight}, | 
 | 1535 |                                            1)); | 
 | 1536 |         } | 
 | 1537 |     } | 
 | 1538 | }; | 
 | 1539 |  | 
 | 1540 | TEST_F(BLASTBufferQueueTransformTest, setTransform_ROT_0) { | 
 | 1541 |     test(ui::Transform::ROT_0); | 
 | 1542 | } | 
 | 1543 |  | 
 | 1544 | TEST_F(BLASTBufferQueueTransformTest, setTransform_FLIP_H) { | 
 | 1545 |     test(ui::Transform::FLIP_H); | 
 | 1546 | } | 
 | 1547 |  | 
 | 1548 | TEST_F(BLASTBufferQueueTransformTest, setTransform_FLIP_V) { | 
 | 1549 |     test(ui::Transform::FLIP_V); | 
 | 1550 | } | 
 | 1551 |  | 
 | 1552 | TEST_F(BLASTBufferQueueTransformTest, setTransform_ROT_90) { | 
 | 1553 |     test(ui::Transform::ROT_90); | 
 | 1554 | } | 
 | 1555 |  | 
 | 1556 | TEST_F(BLASTBufferQueueTransformTest, setTransform_ROT_180) { | 
 | 1557 |     test(ui::Transform::ROT_180); | 
 | 1558 | } | 
 | 1559 |  | 
 | 1560 | TEST_F(BLASTBufferQueueTransformTest, setTransform_ROT_270) { | 
 | 1561 |     test(ui::Transform::ROT_270); | 
 | 1562 | } | 
| Valerie Hau | 871d635 | 2020-01-29 08:44:02 -0800 | [diff] [blame] | 1563 |  | 
 | 1564 | class BLASTFrameEventHistoryTest : public BLASTBufferQueueTest { | 
 | 1565 | public: | 
 | 1566 |     void setUpAndQueueBuffer(const sp<IGraphicBufferProducer>& igbProducer, | 
| Vishnu Nair | de66dc7 | 2021-06-17 17:54:41 -0700 | [diff] [blame] | 1567 |                              nsecs_t* outRequestedPresentTime, nsecs_t* postedTime, | 
| Valerie Hau | 871d635 | 2020-01-29 08:44:02 -0800 | [diff] [blame] | 1568 |                              IGraphicBufferProducer::QueueBufferOutput* qbOutput, | 
| Vishnu Nair | de66dc7 | 2021-06-17 17:54:41 -0700 | [diff] [blame] | 1569 |                              bool getFrameTimestamps, nsecs_t requestedPresentTime = systemTime()) { | 
| Valerie Hau | 871d635 | 2020-01-29 08:44:02 -0800 | [diff] [blame] | 1570 |         int slot; | 
 | 1571 |         sp<Fence> fence; | 
 | 1572 |         sp<GraphicBuffer> buf; | 
 | 1573 |         auto ret = igbProducer->dequeueBuffer(&slot, &fence, mDisplayWidth, mDisplayHeight, | 
 | 1574 |                                               PIXEL_FORMAT_RGBA_8888, GRALLOC_USAGE_SW_WRITE_OFTEN, | 
 | 1575 |                                               nullptr, nullptr); | 
| Vishnu Nair | de66dc7 | 2021-06-17 17:54:41 -0700 | [diff] [blame] | 1576 |         if (IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION == ret) { | 
 | 1577 |             ASSERT_EQ(OK, igbProducer->requestBuffer(slot, &buf)); | 
 | 1578 |         } | 
| Valerie Hau | 871d635 | 2020-01-29 08:44:02 -0800 | [diff] [blame] | 1579 |  | 
| Vishnu Nair | de66dc7 | 2021-06-17 17:54:41 -0700 | [diff] [blame] | 1580 |         *outRequestedPresentTime = requestedPresentTime; | 
 | 1581 |         IGraphicBufferProducer::QueueBufferInput input(requestedPresentTime, false, | 
 | 1582 |                                                        HAL_DATASPACE_UNKNOWN, | 
| Valerie Hau | 871d635 | 2020-01-29 08:44:02 -0800 | [diff] [blame] | 1583 |                                                        Rect(mDisplayWidth, mDisplayHeight), | 
 | 1584 |                                                        NATIVE_WINDOW_SCALING_MODE_FREEZE, 0, | 
 | 1585 |                                                        Fence::NO_FENCE, /*sticky*/ 0, | 
 | 1586 |                                                        getFrameTimestamps); | 
 | 1587 |         if (postedTime) *postedTime = systemTime(); | 
 | 1588 |         igbProducer->queueBuffer(slot, input, qbOutput); | 
 | 1589 |     } | 
| Vishnu Nair | 083efd3 | 2021-02-12 09:32:30 -0800 | [diff] [blame] | 1590 |     sp<SurfaceControl> mBufferQueueSurfaceControl; | 
| Valerie Hau | 871d635 | 2020-01-29 08:44:02 -0800 | [diff] [blame] | 1591 | }; | 
 | 1592 |  | 
 | 1593 | TEST_F(BLASTFrameEventHistoryTest, FrameEventHistory_Basic) { | 
 | 1594 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 1595 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 1596 |     ProducerFrameEventHistory history; | 
 | 1597 |     setUpProducer(adapter, igbProducer); | 
 | 1598 |  | 
 | 1599 |     IGraphicBufferProducer::QueueBufferOutput qbOutput; | 
 | 1600 |     nsecs_t requestedPresentTimeA = 0; | 
 | 1601 |     nsecs_t postedTimeA = 0; | 
 | 1602 |     setUpAndQueueBuffer(igbProducer, &requestedPresentTimeA, &postedTimeA, &qbOutput, true); | 
 | 1603 |     history.applyDelta(qbOutput.frameTimestamps); | 
 | 1604 |  | 
 | 1605 |     FrameEvents* events = nullptr; | 
 | 1606 |     events = history.getFrame(1); | 
 | 1607 |     ASSERT_NE(nullptr, events); | 
 | 1608 |     ASSERT_EQ(1, events->frameNumber); | 
 | 1609 |     ASSERT_EQ(requestedPresentTimeA, events->requestedPresentTime); | 
 | 1610 |     ASSERT_GE(events->postedTime, postedTimeA); | 
 | 1611 |  | 
| Vishnu Nair | 1506b18 | 2021-02-22 14:35:15 -0800 | [diff] [blame] | 1612 |     adapter.waitForCallback(1); | 
| Valerie Hau | 871d635 | 2020-01-29 08:44:02 -0800 | [diff] [blame] | 1613 |  | 
 | 1614 |     // queue another buffer so we query for frame event deltas | 
 | 1615 |     nsecs_t requestedPresentTimeB = 0; | 
 | 1616 |     nsecs_t postedTimeB = 0; | 
 | 1617 |     setUpAndQueueBuffer(igbProducer, &requestedPresentTimeB, &postedTimeB, &qbOutput, true); | 
 | 1618 |     history.applyDelta(qbOutput.frameTimestamps); | 
 | 1619 |     events = history.getFrame(1); | 
 | 1620 |     ASSERT_NE(nullptr, events); | 
 | 1621 |  | 
 | 1622 |     // frame number, requestedPresentTime, and postTime should not have changed | 
 | 1623 |     ASSERT_EQ(1, events->frameNumber); | 
 | 1624 |     ASSERT_EQ(requestedPresentTimeA, events->requestedPresentTime); | 
 | 1625 |     ASSERT_GE(events->postedTime, postedTimeA); | 
 | 1626 |  | 
 | 1627 |     ASSERT_GE(events->latchTime, postedTimeA); | 
 | 1628 |     ASSERT_GE(events->dequeueReadyTime, events->latchTime); | 
 | 1629 |     ASSERT_NE(nullptr, events->gpuCompositionDoneFence); | 
 | 1630 |     ASSERT_NE(nullptr, events->displayPresentFence); | 
 | 1631 |     ASSERT_NE(nullptr, events->releaseFence); | 
 | 1632 |  | 
 | 1633 |     // we should also have gotten the initial values for the next frame | 
 | 1634 |     events = history.getFrame(2); | 
 | 1635 |     ASSERT_NE(nullptr, events); | 
 | 1636 |     ASSERT_EQ(2, events->frameNumber); | 
 | 1637 |     ASSERT_EQ(requestedPresentTimeB, events->requestedPresentTime); | 
 | 1638 |     ASSERT_GE(events->postedTime, postedTimeB); | 
| Valerie Hau | 78491e9 | 2020-04-15 13:10:56 -0700 | [diff] [blame] | 1639 |  | 
 | 1640 |     // wait for any callbacks that have not been received | 
 | 1641 |     adapter.waitForCallbacks(); | 
| Valerie Hau | 871d635 | 2020-01-29 08:44:02 -0800 | [diff] [blame] | 1642 | } | 
| Vishnu Nair | 083efd3 | 2021-02-12 09:32:30 -0800 | [diff] [blame] | 1643 |  | 
| Vishnu Nair | 083efd3 | 2021-02-12 09:32:30 -0800 | [diff] [blame] | 1644 | TEST_F(BLASTFrameEventHistoryTest, FrameEventHistory_DroppedFrame) { | 
 | 1645 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 1646 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 1647 |     setUpProducer(adapter, igbProducer); | 
 | 1648 |  | 
 | 1649 |     ProducerFrameEventHistory history; | 
 | 1650 |     IGraphicBufferProducer::QueueBufferOutput qbOutput; | 
 | 1651 |     nsecs_t requestedPresentTimeA = 0; | 
 | 1652 |     nsecs_t postedTimeA = 0; | 
| Vishnu Nair | de66dc7 | 2021-06-17 17:54:41 -0700 | [diff] [blame] | 1653 |     // Present the frame sometime in the future so we can add two frames to the queue so the older | 
 | 1654 |     // one will be dropped. | 
 | 1655 |     nsecs_t presentTime = systemTime() + std::chrono::nanoseconds(500ms).count(); | 
| Vishnu Nair | 083efd3 | 2021-02-12 09:32:30 -0800 | [diff] [blame] | 1656 |     setUpAndQueueBuffer(igbProducer, &requestedPresentTimeA, &postedTimeA, &qbOutput, true, | 
| Vishnu Nair | de66dc7 | 2021-06-17 17:54:41 -0700 | [diff] [blame] | 1657 |                         presentTime); | 
| Vishnu Nair | 083efd3 | 2021-02-12 09:32:30 -0800 | [diff] [blame] | 1658 |     history.applyDelta(qbOutput.frameTimestamps); | 
 | 1659 |  | 
 | 1660 |     FrameEvents* events = nullptr; | 
 | 1661 |     events = history.getFrame(1); | 
 | 1662 |     ASSERT_NE(nullptr, events); | 
 | 1663 |     ASSERT_EQ(1, events->frameNumber); | 
 | 1664 |     ASSERT_EQ(requestedPresentTimeA, events->requestedPresentTime); | 
 | 1665 |     ASSERT_GE(events->postedTime, postedTimeA); | 
 | 1666 |  | 
 | 1667 |     // queue another buffer so the first can be dropped | 
 | 1668 |     nsecs_t requestedPresentTimeB = 0; | 
 | 1669 |     nsecs_t postedTimeB = 0; | 
| Vishnu Nair | de66dc7 | 2021-06-17 17:54:41 -0700 | [diff] [blame] | 1670 |     presentTime = systemTime() + std::chrono::nanoseconds(1ms).count(); | 
 | 1671 |     setUpAndQueueBuffer(igbProducer, &requestedPresentTimeB, &postedTimeB, &qbOutput, true, | 
 | 1672 |                         presentTime); | 
| Vishnu Nair | 083efd3 | 2021-02-12 09:32:30 -0800 | [diff] [blame] | 1673 |     history.applyDelta(qbOutput.frameTimestamps); | 
 | 1674 |     events = history.getFrame(1); | 
 | 1675 |     ASSERT_NE(nullptr, events); | 
 | 1676 |  | 
 | 1677 |     // frame number, requestedPresentTime, and postTime should not have changed | 
 | 1678 |     ASSERT_EQ(1, events->frameNumber); | 
 | 1679 |     ASSERT_EQ(requestedPresentTimeA, events->requestedPresentTime); | 
 | 1680 |     ASSERT_GE(events->postedTime, postedTimeA); | 
 | 1681 |  | 
| Vishnu Nair | de66dc7 | 2021-06-17 17:54:41 -0700 | [diff] [blame] | 1682 |     // a valid latchtime and pre and post composition info should not be set for the dropped frame | 
| Vishnu Nair | 083efd3 | 2021-02-12 09:32:30 -0800 | [diff] [blame] | 1683 |     ASSERT_FALSE(events->hasLatchInfo()); | 
 | 1684 |     ASSERT_FALSE(events->hasDequeueReadyInfo()); | 
| Vishnu Nair | de66dc7 | 2021-06-17 17:54:41 -0700 | [diff] [blame] | 1685 |     ASSERT_FALSE(events->hasGpuCompositionDoneInfo()); | 
 | 1686 |     ASSERT_FALSE(events->hasDisplayPresentInfo()); | 
 | 1687 |     ASSERT_FALSE(events->hasReleaseInfo()); | 
| Vishnu Nair | 083efd3 | 2021-02-12 09:32:30 -0800 | [diff] [blame] | 1688 |  | 
| Vishnu Nair | de66dc7 | 2021-06-17 17:54:41 -0700 | [diff] [blame] | 1689 |     // wait for the last transaction to be completed. | 
 | 1690 |     adapter.waitForCallback(2); | 
| Vishnu Nair | 083efd3 | 2021-02-12 09:32:30 -0800 | [diff] [blame] | 1691 |  | 
| Vishnu Nair | de66dc7 | 2021-06-17 17:54:41 -0700 | [diff] [blame] | 1692 |     // queue another buffer so we query for frame event deltas | 
 | 1693 |     nsecs_t requestedPresentTimeC = 0; | 
 | 1694 |     nsecs_t postedTimeC = 0; | 
 | 1695 |     setUpAndQueueBuffer(igbProducer, &requestedPresentTimeC, &postedTimeC, &qbOutput, true); | 
 | 1696 |     history.applyDelta(qbOutput.frameTimestamps); | 
 | 1697 |  | 
 | 1698 |     // frame number, requestedPresentTime, and postTime should not have changed | 
 | 1699 |     ASSERT_EQ(1, events->frameNumber); | 
 | 1700 |     ASSERT_EQ(requestedPresentTimeA, events->requestedPresentTime); | 
 | 1701 |     ASSERT_GE(events->postedTime, postedTimeA); | 
 | 1702 |  | 
 | 1703 |     // a valid latchtime and pre and post composition info should not be set for the dropped frame | 
 | 1704 |     ASSERT_FALSE(events->hasLatchInfo()); | 
 | 1705 |     ASSERT_FALSE(events->hasDequeueReadyInfo()); | 
 | 1706 |     ASSERT_FALSE(events->hasGpuCompositionDoneInfo()); | 
 | 1707 |     ASSERT_FALSE(events->hasDisplayPresentInfo()); | 
 | 1708 |     ASSERT_FALSE(events->hasReleaseInfo()); | 
 | 1709 |  | 
 | 1710 |     // we should also have gotten values for the presented frame | 
| Vishnu Nair | 083efd3 | 2021-02-12 09:32:30 -0800 | [diff] [blame] | 1711 |     events = history.getFrame(2); | 
 | 1712 |     ASSERT_NE(nullptr, events); | 
 | 1713 |     ASSERT_EQ(2, events->frameNumber); | 
 | 1714 |     ASSERT_EQ(requestedPresentTimeB, events->requestedPresentTime); | 
 | 1715 |     ASSERT_GE(events->postedTime, postedTimeB); | 
| Vishnu Nair | de66dc7 | 2021-06-17 17:54:41 -0700 | [diff] [blame] | 1716 |     ASSERT_GE(events->latchTime, postedTimeB); | 
 | 1717 |     ASSERT_GE(events->dequeueReadyTime, events->latchTime); | 
 | 1718 |     ASSERT_NE(nullptr, events->gpuCompositionDoneFence); | 
 | 1719 |     ASSERT_NE(nullptr, events->displayPresentFence); | 
 | 1720 |     ASSERT_NE(nullptr, events->releaseFence); | 
 | 1721 |  | 
 | 1722 |     // wait for any callbacks that have not been received | 
 | 1723 |     adapter.waitForCallbacks(); | 
| Vishnu Nair | 083efd3 | 2021-02-12 09:32:30 -0800 | [diff] [blame] | 1724 | } | 
 | 1725 |  | 
| Vishnu Nair | 9a69a04 | 2021-06-18 13:19:49 -0700 | [diff] [blame] | 1726 | TEST_F(BLASTFrameEventHistoryTest, FrameEventHistory_CompositorTimings) { | 
 | 1727 |     BLASTBufferQueueHelper adapter(mSurfaceControl, mDisplayWidth, mDisplayHeight); | 
 | 1728 |     sp<IGraphicBufferProducer> igbProducer; | 
 | 1729 |     ProducerFrameEventHistory history; | 
 | 1730 |     setUpProducer(adapter, igbProducer); | 
 | 1731 |  | 
 | 1732 |     IGraphicBufferProducer::QueueBufferOutput qbOutput; | 
 | 1733 |     nsecs_t requestedPresentTimeA = 0; | 
 | 1734 |     nsecs_t postedTimeA = 0; | 
| Vishnu Nair | 9a69a04 | 2021-06-18 13:19:49 -0700 | [diff] [blame] | 1735 |     setUpAndQueueBuffer(igbProducer, &requestedPresentTimeA, &postedTimeA, &qbOutput, true); | 
 | 1736 |     history.applyDelta(qbOutput.frameTimestamps); | 
 | 1737 |     adapter.waitForCallback(1); | 
 | 1738 |  | 
 | 1739 |     // queue another buffer so we query for frame event deltas | 
 | 1740 |     nsecs_t requestedPresentTimeB = 0; | 
 | 1741 |     nsecs_t postedTimeB = 0; | 
 | 1742 |     setUpAndQueueBuffer(igbProducer, &requestedPresentTimeB, &postedTimeB, &qbOutput, true); | 
 | 1743 |     history.applyDelta(qbOutput.frameTimestamps); | 
 | 1744 |  | 
 | 1745 |     // check for a valid compositor deadline | 
 | 1746 |     ASSERT_NE(0, history.getReportedCompositeDeadline()); | 
 | 1747 |  | 
 | 1748 |     // wait for any callbacks that have not been received | 
 | 1749 |     adapter.waitForCallbacks(); | 
 | 1750 | } | 
 | 1751 |  | 
| Valerie Hau | c5011f9 | 2019-10-11 09:52:07 -0700 | [diff] [blame] | 1752 | } // namespace android |