blob: 5aa34a575d06db428aa0e993e3a60a31906b417e [file] [log] [blame]
Jamie Gennis9e75ddd2012-08-31 15:32:45 -07001/*
2 * Copyright (C) 2012 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 "BufferQueue_test"
18//#define LOG_NDEBUG 0
19
20#include <gtest/gtest.h>
21
22#include <utils/String8.h>
23#include <utils/threads.h>
24
25#include <ui/GraphicBuffer.h>
Jamie Gennis9e75ddd2012-08-31 15:32:45 -070026
Dan Stoza9f3053d2014-03-06 15:14:33 -080027#include <binder/IServiceManager.h>
Jamie Gennis9e75ddd2012-08-31 15:32:45 -070028#include <gui/BufferQueue.h>
29
30namespace android {
31
32class BufferQueueTest : public ::testing::Test {
Dan Stoza9f3053d2014-03-06 15:14:33 -080033
34public:
35 static const String16 PRODUCER_NAME;
36 static const String16 CONSUMER_NAME;
37
Jamie Gennis9e75ddd2012-08-31 15:32:45 -070038protected:
Dan Stoza9f3053d2014-03-06 15:14:33 -080039 BufferQueueTest() {
Jamie Gennis9e75ddd2012-08-31 15:32:45 -070040 const ::testing::TestInfo* const testInfo =
41 ::testing::UnitTest::GetInstance()->current_test_info();
42 ALOGV("Begin test: %s.%s", testInfo->test_case_name(),
43 testInfo->name());
44
Dan Stoza9f3053d2014-03-06 15:14:33 -080045 BufferQueue::createBufferQueue(&mProducer, &mConsumer);
46 sp<IServiceManager> serviceManager = defaultServiceManager();
47 serviceManager->addService(PRODUCER_NAME, mProducer.get());
48 serviceManager->addService(CONSUMER_NAME, mConsumer.get());
Jamie Gennis9e75ddd2012-08-31 15:32:45 -070049 }
50
Dan Stoza9f3053d2014-03-06 15:14:33 -080051 ~BufferQueueTest() {
Jamie Gennis9e75ddd2012-08-31 15:32:45 -070052 const ::testing::TestInfo* const testInfo =
53 ::testing::UnitTest::GetInstance()->current_test_info();
54 ALOGV("End test: %s.%s", testInfo->test_case_name(),
55 testInfo->name());
56 }
57
Igor Murashkin7ea777f2013-11-18 16:58:36 -080058 void GetMinUndequeuedBufferCount(int* bufferCount) {
Dan Stoza9f3053d2014-03-06 15:14:33 -080059 ASSERT_TRUE(bufferCount != NULL);
60 ASSERT_EQ(OK, mProducer->query(NATIVE_WINDOW_MIN_UNDEQUEUED_BUFFERS,
61 bufferCount));
62 ASSERT_GE(*bufferCount, 0);
Igor Murashkin7ea777f2013-11-18 16:58:36 -080063 }
64
Dan Stoza9f3053d2014-03-06 15:14:33 -080065 sp<BnGraphicBufferProducer> mProducer;
66 sp<BnGraphicBufferConsumer> mConsumer;
Jamie Gennis9e75ddd2012-08-31 15:32:45 -070067};
68
Dan Stoza9f3053d2014-03-06 15:14:33 -080069const String16 BufferQueueTest::PRODUCER_NAME = String16("BQTestProducer");
70const String16 BufferQueueTest::CONSUMER_NAME = String16("BQTestConsumer");
71
Mathias Agopiana4e19522013-07-31 20:09:53 -070072struct DummyConsumer : public BnConsumerListener {
Jamie Gennis9e75ddd2012-08-31 15:32:45 -070073 virtual void onFrameAvailable() {}
74 virtual void onBuffersReleased() {}
Jesse Hall49bfda12014-03-13 15:09:17 -070075 virtual void onSidebandStreamChanged() {}
Jamie Gennis9e75ddd2012-08-31 15:32:45 -070076};
77
78TEST_F(BufferQueueTest, AcquireBuffer_ExceedsMaxAcquireCount_Fails) {
79 sp<DummyConsumer> dc(new DummyConsumer);
Dan Stoza9f3053d2014-03-06 15:14:33 -080080 mConsumer->consumerConnect(dc, false);
Andy McFadden2adaf042012-12-18 09:49:45 -080081 IGraphicBufferProducer::QueueBufferOutput qbo;
Dan Stoza9f3053d2014-03-06 15:14:33 -080082 mProducer->connect(NULL, NATIVE_WINDOW_API_CPU, false, &qbo);
83 mProducer->setBufferCount(4);
Jamie Gennis9e75ddd2012-08-31 15:32:45 -070084
85 int slot;
86 sp<Fence> fence;
87 sp<GraphicBuffer> buf;
Andy McFadden8b308ed2013-08-19 08:56:07 -070088 IGraphicBufferProducer::QueueBufferInput qbi(0, false, Rect(0, 0, 1, 1),
Mathias Agopian7cdd7862013-07-18 22:10:56 -070089 NATIVE_WINDOW_SCALING_MODE_FREEZE, 0, false, Fence::NO_FENCE);
Jamie Gennis9e75ddd2012-08-31 15:32:45 -070090 BufferQueue::BufferItem item;
91
92 for (int i = 0; i < 2; i++) {
Andy McFadden2adaf042012-12-18 09:49:45 -080093 ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION,
Dan Stoza9f3053d2014-03-06 15:14:33 -080094 mProducer->dequeueBuffer(&slot, &fence, false, 1, 1, 0,
Jamie Gennis9e75ddd2012-08-31 15:32:45 -070095 GRALLOC_USAGE_SW_READ_OFTEN));
Dan Stoza9f3053d2014-03-06 15:14:33 -080096 ASSERT_EQ(OK, mProducer->requestBuffer(slot, &buf));
97 ASSERT_EQ(OK, mProducer->queueBuffer(slot, qbi, &qbo));
98 ASSERT_EQ(OK, mConsumer->acquireBuffer(&item, 0));
Jamie Gennis9e75ddd2012-08-31 15:32:45 -070099 }
100
Andy McFadden2adaf042012-12-18 09:49:45 -0800101 ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION,
Dan Stoza9f3053d2014-03-06 15:14:33 -0800102 mProducer->dequeueBuffer(&slot, &fence, false, 1, 1, 0,
Jamie Gennis9e75ddd2012-08-31 15:32:45 -0700103 GRALLOC_USAGE_SW_READ_OFTEN));
Dan Stoza9f3053d2014-03-06 15:14:33 -0800104 ASSERT_EQ(OK, mProducer->requestBuffer(slot, &buf));
105 ASSERT_EQ(OK, mProducer->queueBuffer(slot, qbi, &qbo));
Jamie Gennis9e75ddd2012-08-31 15:32:45 -0700106
107 // Acquire the third buffer, which should fail.
Dan Stoza9f3053d2014-03-06 15:14:33 -0800108 ASSERT_EQ(INVALID_OPERATION, mConsumer->acquireBuffer(&item, 0));
Jamie Gennis9e75ddd2012-08-31 15:32:45 -0700109}
110
Jamie Gennisc68f2ec2012-08-30 18:36:22 -0700111TEST_F(BufferQueueTest, SetMaxAcquiredBufferCountWithIllegalValues_ReturnsError) {
112 sp<DummyConsumer> dc(new DummyConsumer);
Dan Stoza9f3053d2014-03-06 15:14:33 -0800113 mConsumer->consumerConnect(dc, false);
Jamie Gennisc68f2ec2012-08-30 18:36:22 -0700114
Igor Murashkin7ea777f2013-11-18 16:58:36 -0800115 int minBufferCount;
116 ASSERT_NO_FATAL_FAILURE(GetMinUndequeuedBufferCount(&minBufferCount));
Dan Stoza9f3053d2014-03-06 15:14:33 -0800117 EXPECT_EQ(BAD_VALUE, mConsumer->setMaxAcquiredBufferCount(
118 minBufferCount - 1));
Igor Murashkin7ea777f2013-11-18 16:58:36 -0800119
Dan Stoza9f3053d2014-03-06 15:14:33 -0800120 EXPECT_EQ(BAD_VALUE, mConsumer->setMaxAcquiredBufferCount(0));
121 EXPECT_EQ(BAD_VALUE, mConsumer->setMaxAcquiredBufferCount(-3));
122 EXPECT_EQ(BAD_VALUE, mConsumer->setMaxAcquiredBufferCount(
Jamie Gennisc68f2ec2012-08-30 18:36:22 -0700123 BufferQueue::MAX_MAX_ACQUIRED_BUFFERS+1));
Dan Stoza9f3053d2014-03-06 15:14:33 -0800124 EXPECT_EQ(BAD_VALUE, mConsumer->setMaxAcquiredBufferCount(100));
Jamie Gennisc68f2ec2012-08-30 18:36:22 -0700125}
126
127TEST_F(BufferQueueTest, SetMaxAcquiredBufferCountWithLegalValues_Succeeds) {
128 sp<DummyConsumer> dc(new DummyConsumer);
Dan Stoza9f3053d2014-03-06 15:14:33 -0800129 mConsumer->consumerConnect(dc, false);
Jamie Gennisc68f2ec2012-08-30 18:36:22 -0700130
Igor Murashkin7ea777f2013-11-18 16:58:36 -0800131 int minBufferCount;
132 ASSERT_NO_FATAL_FAILURE(GetMinUndequeuedBufferCount(&minBufferCount));
133
Dan Stoza9f3053d2014-03-06 15:14:33 -0800134 EXPECT_EQ(OK, mConsumer->setMaxAcquiredBufferCount(1));
135 EXPECT_EQ(OK, mConsumer->setMaxAcquiredBufferCount(2));
136 EXPECT_EQ(OK, mConsumer->setMaxAcquiredBufferCount(minBufferCount));
137 EXPECT_EQ(OK, mConsumer->setMaxAcquiredBufferCount(
Jamie Gennisc68f2ec2012-08-30 18:36:22 -0700138 BufferQueue::MAX_MAX_ACQUIRED_BUFFERS));
139}
140
Dan Stoza9f3053d2014-03-06 15:14:33 -0800141TEST_F(BufferQueueTest, DetachAndReattachOnProducerSide) {
142 sp<DummyConsumer> dc(new DummyConsumer);
143 ASSERT_EQ(OK, mConsumer->consumerConnect(dc, false));
144 IGraphicBufferProducer::QueueBufferOutput output;
145 ASSERT_EQ(OK,
146 mProducer->connect(NULL, NATIVE_WINDOW_API_CPU, false, &output));
147
148 ASSERT_EQ(BAD_VALUE, mProducer->detachBuffer(-1)); // Index too low
149 ASSERT_EQ(BAD_VALUE, mProducer->detachBuffer(
150 BufferQueueDefs::NUM_BUFFER_SLOTS)); // Index too high
151 ASSERT_EQ(BAD_VALUE, mProducer->detachBuffer(0)); // Not dequeued
152
153 int slot;
154 sp<Fence> fence;
155 sp<GraphicBuffer> buffer;
156 ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION,
157 mProducer->dequeueBuffer(&slot, &fence, false, 0, 0, 0,
158 GRALLOC_USAGE_SW_WRITE_OFTEN));
159 ASSERT_EQ(BAD_VALUE, mProducer->detachBuffer(slot)); // Not requested
160 ASSERT_EQ(OK, mProducer->requestBuffer(slot, &buffer));
161 ASSERT_EQ(OK, mProducer->detachBuffer(slot));
162 ASSERT_EQ(BAD_VALUE, mProducer->detachBuffer(slot)); // Not dequeued
163
164 sp<GraphicBuffer> safeToClobberBuffer;
165 // Can no longer request buffer from this slot
166 ASSERT_EQ(BAD_VALUE, mProducer->requestBuffer(slot, &safeToClobberBuffer));
167
168 uint32_t* dataIn;
169 ASSERT_EQ(OK, buffer->lock(GraphicBuffer::USAGE_SW_WRITE_OFTEN,
170 reinterpret_cast<void**>(&dataIn)));
171 *dataIn = 0x12345678;
172 ASSERT_EQ(OK, buffer->unlock());
173
174 int newSlot;
175 ASSERT_EQ(BAD_VALUE, mProducer->attachBuffer(NULL, safeToClobberBuffer));
176 ASSERT_EQ(BAD_VALUE, mProducer->attachBuffer(&newSlot, NULL));
177
178 ASSERT_EQ(OK, mProducer->attachBuffer(&newSlot, buffer));
179 IGraphicBufferProducer::QueueBufferInput input(0, false, Rect(0, 0, 1, 1),
180 NATIVE_WINDOW_SCALING_MODE_FREEZE, 0, false, Fence::NO_FENCE);
181 ASSERT_EQ(OK, mProducer->queueBuffer(newSlot, input, &output));
182
183 IGraphicBufferConsumer::BufferItem item;
184 ASSERT_EQ(OK, mConsumer->acquireBuffer(&item, static_cast<nsecs_t>(0)));
185
186 uint32_t* dataOut;
187 ASSERT_EQ(OK, item.mGraphicBuffer->lock(GraphicBuffer::USAGE_SW_READ_OFTEN,
188 reinterpret_cast<void**>(&dataOut)));
189 ASSERT_EQ(*dataOut, 0x12345678);
190}
191
192TEST_F(BufferQueueTest, DetachAndReattachOnConsumerSide) {
193 sp<DummyConsumer> dc(new DummyConsumer);
194 ASSERT_EQ(OK, mConsumer->consumerConnect(dc, false));
195 IGraphicBufferProducer::QueueBufferOutput output;
196 ASSERT_EQ(OK,
197 mProducer->connect(NULL, NATIVE_WINDOW_API_CPU, false, &output));
198
199 int slot;
200 sp<Fence> fence;
201 sp<GraphicBuffer> buffer;
202 ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION,
203 mProducer->dequeueBuffer(&slot, &fence, false, 0, 0, 0,
204 GRALLOC_USAGE_SW_WRITE_OFTEN));
205 ASSERT_EQ(OK, mProducer->requestBuffer(slot, &buffer));
206 IGraphicBufferProducer::QueueBufferInput input(0, false, Rect(0, 0, 1, 1),
207 NATIVE_WINDOW_SCALING_MODE_FREEZE, 0, false, Fence::NO_FENCE);
208 ASSERT_EQ(OK, mProducer->queueBuffer(slot, input, &output));
209
210 ASSERT_EQ(BAD_VALUE, mConsumer->detachBuffer(-1)); // Index too low
211 ASSERT_EQ(BAD_VALUE, mConsumer->detachBuffer(
212 BufferQueueDefs::NUM_BUFFER_SLOTS)); // Index too high
213 ASSERT_EQ(BAD_VALUE, mConsumer->detachBuffer(0)); // Not acquired
214
215 IGraphicBufferConsumer::BufferItem item;
216 ASSERT_EQ(OK, mConsumer->acquireBuffer(&item, static_cast<nsecs_t>(0)));
217
218 ASSERT_EQ(OK, mConsumer->detachBuffer(item.mBuf));
219 ASSERT_EQ(BAD_VALUE, mConsumer->detachBuffer(item.mBuf)); // Not acquired
220
221 uint32_t* dataIn;
222 ASSERT_EQ(OK, item.mGraphicBuffer->lock(
223 GraphicBuffer::USAGE_SW_WRITE_OFTEN,
224 reinterpret_cast<void**>(&dataIn)));
225 *dataIn = 0x12345678;
226 ASSERT_EQ(OK, item.mGraphicBuffer->unlock());
227
228 int newSlot;
229 sp<GraphicBuffer> safeToClobberBuffer;
230 ASSERT_EQ(BAD_VALUE, mConsumer->attachBuffer(NULL, safeToClobberBuffer));
231 ASSERT_EQ(BAD_VALUE, mConsumer->attachBuffer(&newSlot, NULL));
232 ASSERT_EQ(OK, mConsumer->attachBuffer(&newSlot, item.mGraphicBuffer));
233
234 ASSERT_EQ(OK, mConsumer->releaseBuffer(item.mBuf, 0, EGL_NO_DISPLAY,
235 EGL_NO_SYNC_KHR, Fence::NO_FENCE));
236
237 ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION,
238 mProducer->dequeueBuffer(&slot, &fence, false, 0, 0, 0,
239 GRALLOC_USAGE_SW_WRITE_OFTEN));
240 ASSERT_EQ(OK, mProducer->requestBuffer(slot, &buffer));
241
242 uint32_t* dataOut;
243 ASSERT_EQ(OK, buffer->lock(GraphicBuffer::USAGE_SW_READ_OFTEN,
244 reinterpret_cast<void**>(&dataOut)));
245 ASSERT_EQ(*dataOut, 0x12345678);
246}
247
248TEST_F(BufferQueueTest, MoveFromConsumerToProducer) {
249 sp<DummyConsumer> dc(new DummyConsumer);
250 ASSERT_EQ(OK, mConsumer->consumerConnect(dc, false));
251 IGraphicBufferProducer::QueueBufferOutput output;
252 ASSERT_EQ(OK,
253 mProducer->connect(NULL, NATIVE_WINDOW_API_CPU, false, &output));
254
255 int slot;
256 sp<Fence> fence;
257 sp<GraphicBuffer> buffer;
258 ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION,
259 mProducer->dequeueBuffer(&slot, &fence, false, 0, 0, 0,
260 GRALLOC_USAGE_SW_WRITE_OFTEN));
261 ASSERT_EQ(OK, mProducer->requestBuffer(slot, &buffer));
262
263 uint32_t* dataIn;
264 ASSERT_EQ(OK, buffer->lock(GraphicBuffer::USAGE_SW_WRITE_OFTEN,
265 reinterpret_cast<void**>(&dataIn)));
266 *dataIn = 0x12345678;
267 ASSERT_EQ(OK, buffer->unlock());
268
269 IGraphicBufferProducer::QueueBufferInput input(0, false, Rect(0, 0, 1, 1),
270 NATIVE_WINDOW_SCALING_MODE_FREEZE, 0, false, Fence::NO_FENCE);
271 ASSERT_EQ(OK, mProducer->queueBuffer(slot, input, &output));
272
273 IGraphicBufferConsumer::BufferItem item;
274 ASSERT_EQ(OK, mConsumer->acquireBuffer(&item, static_cast<nsecs_t>(0)));
275 ASSERT_EQ(OK, mConsumer->detachBuffer(item.mBuf));
276
277 int newSlot;
278 ASSERT_EQ(OK, mProducer->attachBuffer(&newSlot, item.mGraphicBuffer));
279 ASSERT_EQ(OK, mProducer->queueBuffer(newSlot, input, &output));
280 ASSERT_EQ(OK, mConsumer->acquireBuffer(&item, static_cast<nsecs_t>(0)));
281
282 uint32_t* dataOut;
283 ASSERT_EQ(OK, item.mGraphicBuffer->lock(GraphicBuffer::USAGE_SW_READ_OFTEN,
284 reinterpret_cast<void**>(&dataOut)));
285 ASSERT_EQ(*dataOut, 0x12345678);
286}
287
Jamie Gennis9e75ddd2012-08-31 15:32:45 -0700288} // namespace android