1 /*
2 * Copyright 2014 The Android Open Source Project
3 * Copyright (C) 2014 Mozilla Foundation
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 */
17
18 #include "GonkBufferItem.h"
19
20 #include <ui/Fence.h>
21 #include <ui/GraphicBuffer.h>
22
23 #include <system/window.h>
24
25 namespace android {
26
GonkBufferItem()27 GonkBufferItem::GonkBufferItem() :
28 mTransform(0),
29 mScalingMode(NATIVE_WINDOW_SCALING_MODE_FREEZE),
30 mTimestamp(0),
31 mIsAutoTimestamp(false),
32 mFrameNumber(0),
33 mSlot(INVALID_BUFFER_SLOT),
34 mIsDroppable(false),
35 mAcquireCalled(false),
36 mTransformToDisplayInverse(false) {
37 mCrop.makeInvalid();
38 }
39
operator IGonkGraphicBufferConsumer::BufferItem() const40 GonkBufferItem::operator IGonkGraphicBufferConsumer::BufferItem() const {
41 IGonkGraphicBufferConsumer::BufferItem bufferItem;
42 bufferItem.mGraphicBuffer = mGraphicBuffer;
43 bufferItem.mFence = mFence;
44 bufferItem.mCrop = mCrop;
45 bufferItem.mTransform = mTransform;
46 bufferItem.mScalingMode = mScalingMode;
47 bufferItem.mTimestamp = mTimestamp;
48 bufferItem.mIsAutoTimestamp = mIsAutoTimestamp;
49 bufferItem.mFrameNumber = mFrameNumber;
50 bufferItem.mBuf = mSlot;
51 bufferItem.mIsDroppable = mIsDroppable;
52 bufferItem.mAcquireCalled = mAcquireCalled;
53 bufferItem.mTransformToDisplayInverse = mTransformToDisplayInverse;
54 return bufferItem;
55 }
56
getPodSize() const57 size_t GonkBufferItem::getPodSize() const {
58 size_t c = sizeof(mCrop) +
59 sizeof(mTransform) +
60 sizeof(mScalingMode) +
61 sizeof(mTimestamp) +
62 sizeof(mIsAutoTimestamp) +
63 sizeof(mFrameNumber) +
64 sizeof(mSlot) +
65 sizeof(mIsDroppable) +
66 sizeof(mAcquireCalled) +
67 sizeof(mTransformToDisplayInverse);
68 return c;
69 }
70
getFlattenedSize() const71 size_t GonkBufferItem::getFlattenedSize() const {
72 size_t c = 0;
73 if (mGraphicBuffer != 0) {
74 c += mGraphicBuffer->getFlattenedSize();
75 FlattenableUtils::align<4>(c);
76 }
77 if (mFence != 0) {
78 c += mFence->getFlattenedSize();
79 FlattenableUtils::align<4>(c);
80 }
81 return sizeof(int32_t) + c + getPodSize();
82 }
83
getFdCount() const84 size_t GonkBufferItem::getFdCount() const {
85 size_t c = 0;
86 if (mGraphicBuffer != 0) {
87 c += mGraphicBuffer->getFdCount();
88 }
89 if (mFence != 0) {
90 c += mFence->getFdCount();
91 }
92 return c;
93 }
94
flatten(void * & buffer,size_t & size,int * & fds,size_t & count) const95 status_t GonkBufferItem::flatten(
96 void*& buffer, size_t& size, int*& fds, size_t& count) const {
97
98 // make sure we have enough space
99 if (count < GonkBufferItem::getFlattenedSize()) {
100 return NO_MEMORY;
101 }
102
103 // content flags are stored first
104 uint32_t& flags = *static_cast<uint32_t*>(buffer);
105
106 // advance the pointer
107 FlattenableUtils::advance(buffer, size, sizeof(uint32_t));
108
109 flags = 0;
110 if (mGraphicBuffer != 0) {
111 status_t err = mGraphicBuffer->flatten(buffer, size, fds, count);
112 if (err) return err;
113 size -= FlattenableUtils::align<4>(buffer);
114 flags |= 1;
115 }
116 if (mFence != 0) {
117 status_t err = mFence->flatten(buffer, size, fds, count);
118 if (err) return err;
119 size -= FlattenableUtils::align<4>(buffer);
120 flags |= 2;
121 }
122
123 // check we have enough space (in case flattening the fence/graphicbuffer lied to us)
124 if (size < getPodSize()) {
125 return NO_MEMORY;
126 }
127
128 FlattenableUtils::write(buffer, size, mCrop);
129 FlattenableUtils::write(buffer, size, mTransform);
130 FlattenableUtils::write(buffer, size, mScalingMode);
131 FlattenableUtils::write(buffer, size, mTimestamp);
132 FlattenableUtils::write(buffer, size, mIsAutoTimestamp);
133 FlattenableUtils::write(buffer, size, mFrameNumber);
134 FlattenableUtils::write(buffer, size, mSlot);
135 FlattenableUtils::write(buffer, size, mIsDroppable);
136 FlattenableUtils::write(buffer, size, mAcquireCalled);
137 FlattenableUtils::write(buffer, size, mTransformToDisplayInverse);
138
139 return NO_ERROR;
140 }
141
unflatten(void const * & buffer,size_t & size,int const * & fds,size_t & count)142 status_t GonkBufferItem::unflatten(
143 void const*& buffer, size_t& size, int const*& fds, size_t& count) {
144
145 if (size < sizeof(uint32_t))
146 return NO_MEMORY;
147
148 uint32_t flags = 0;
149 FlattenableUtils::read(buffer, size, flags);
150
151 if (flags & 1) {
152 mGraphicBuffer = new GraphicBuffer();
153 status_t err = mGraphicBuffer->unflatten(buffer, size, fds, count);
154 if (err) return err;
155 size -= FlattenableUtils::align<4>(buffer);
156 }
157
158 if (flags & 2) {
159 mFence = new Fence();
160 status_t err = mFence->unflatten(buffer, size, fds, count);
161 if (err) return err;
162 size -= FlattenableUtils::align<4>(buffer);
163 }
164
165 // check we have enough space
166 if (size < getPodSize()) {
167 return NO_MEMORY;
168 }
169
170 FlattenableUtils::read(buffer, size, mCrop);
171 FlattenableUtils::read(buffer, size, mTransform);
172 FlattenableUtils::read(buffer, size, mScalingMode);
173 FlattenableUtils::read(buffer, size, mTimestamp);
174 FlattenableUtils::read(buffer, size, mIsAutoTimestamp);
175 FlattenableUtils::read(buffer, size, mFrameNumber);
176 FlattenableUtils::read(buffer, size, mSlot);
177 FlattenableUtils::read(buffer, size, mIsDroppable);
178 FlattenableUtils::read(buffer, size, mAcquireCalled);
179 FlattenableUtils::read(buffer, size, mTransformToDisplayInverse);
180
181 return NO_ERROR;
182 }
183
scalingModeName(uint32_t scalingMode)184 const char* GonkBufferItem::scalingModeName(uint32_t scalingMode) {
185 switch (scalingMode) {
186 case NATIVE_WINDOW_SCALING_MODE_FREEZE: return "FREEZE";
187 case NATIVE_WINDOW_SCALING_MODE_SCALE_TO_WINDOW: return "SCALE_TO_WINDOW";
188 case NATIVE_WINDOW_SCALING_MODE_SCALE_CROP: return "SCALE_CROP";
189 default: return "Unknown";
190 }
191 }
192
193 } // namespace android
194