BufferItem.cpp revision 1c87e474d87d6d1380fb61d476d606b1a2fda1c1
1/*
2 * Copyright 2014 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#include <gui/BufferItem.h>
18
19#include <ui/Fence.h>
20#include <ui/GraphicBuffer.h>
21
22#include <system/window.h>
23
24namespace android {
25
26BufferItem::BufferItem() :
27    mTransform(0),
28    mScalingMode(NATIVE_WINDOW_SCALING_MODE_FREEZE),
29    mTimestamp(0),
30    mIsAutoTimestamp(false),
31    mDataSpace(HAL_DATASPACE_UNKNOWN),
32    mFrameNumber(0),
33    mSlot(INVALID_BUFFER_SLOT),
34    mIsDroppable(false),
35    mAcquireCalled(false),
36    mTransformToDisplayInverse(false) {
37    mCrop.makeInvalid();
38}
39
40BufferItem::~BufferItem() {}
41
42size_t BufferItem::getPodSize() const {
43    size_t c =  sizeof(mCrop) +
44            sizeof(mTransform) +
45            sizeof(mScalingMode) +
46            sizeof(mTimestamp) +
47            sizeof(mIsAutoTimestamp) +
48            sizeof(mDataSpace) +
49            sizeof(mFrameNumber) +
50            sizeof(mSlot) +
51            sizeof(mIsDroppable) +
52            sizeof(mAcquireCalled) +
53            sizeof(mTransformToDisplayInverse);
54    return c;
55}
56
57size_t BufferItem::getFlattenedSize() const {
58    size_t c = 0;
59    if (mGraphicBuffer != 0) {
60        c += mGraphicBuffer->getFlattenedSize();
61        FlattenableUtils::align<4>(c);
62    }
63    if (mFence != 0) {
64        c += mFence->getFlattenedSize();
65        FlattenableUtils::align<4>(c);
66    }
67    return sizeof(int32_t) + c + getPodSize();
68}
69
70size_t BufferItem::getFdCount() const {
71    size_t c = 0;
72    if (mGraphicBuffer != 0) {
73        c += mGraphicBuffer->getFdCount();
74    }
75    if (mFence != 0) {
76        c += mFence->getFdCount();
77    }
78    return c;
79}
80
81status_t BufferItem::flatten(
82        void*& buffer, size_t& size, int*& fds, size_t& count) const {
83
84    // make sure we have enough space
85    if (count < BufferItem::getFlattenedSize()) {
86        return NO_MEMORY;
87    }
88
89    // content flags are stored first
90    uint32_t& flags = *static_cast<uint32_t*>(buffer);
91
92    // advance the pointer
93    FlattenableUtils::advance(buffer, size, sizeof(uint32_t));
94
95    flags = 0;
96    if (mGraphicBuffer != 0) {
97        status_t err = mGraphicBuffer->flatten(buffer, size, fds, count);
98        if (err) return err;
99        size -= FlattenableUtils::align<4>(buffer);
100        flags |= 1;
101    }
102    if (mFence != 0) {
103        status_t err = mFence->flatten(buffer, size, fds, count);
104        if (err) return err;
105        size -= FlattenableUtils::align<4>(buffer);
106        flags |= 2;
107    }
108
109    // check we have enough space (in case flattening the fence/graphicbuffer lied to us)
110    if (size < getPodSize()) {
111        return NO_MEMORY;
112    }
113
114    FlattenableUtils::write(buffer, size, mCrop);
115    FlattenableUtils::write(buffer, size, mTransform);
116    FlattenableUtils::write(buffer, size, mScalingMode);
117    FlattenableUtils::write(buffer, size, mTimestamp);
118    FlattenableUtils::write(buffer, size, mIsAutoTimestamp);
119    FlattenableUtils::write(buffer, size, mDataSpace);
120    FlattenableUtils::write(buffer, size, mFrameNumber);
121    FlattenableUtils::write(buffer, size, mSlot);
122    FlattenableUtils::write(buffer, size, mIsDroppable);
123    FlattenableUtils::write(buffer, size, mAcquireCalled);
124    FlattenableUtils::write(buffer, size, mTransformToDisplayInverse);
125
126    return NO_ERROR;
127}
128
129status_t BufferItem::unflatten(
130        void const*& buffer, size_t& size, int const*& fds, size_t& count) {
131
132    if (size < sizeof(uint32_t))
133        return NO_MEMORY;
134
135    uint32_t flags = 0;
136    FlattenableUtils::read(buffer, size, flags);
137
138    if (flags & 1) {
139        mGraphicBuffer = new GraphicBuffer();
140        status_t err = mGraphicBuffer->unflatten(buffer, size, fds, count);
141        if (err) return err;
142        size -= FlattenableUtils::align<4>(buffer);
143    }
144
145    if (flags & 2) {
146        mFence = new Fence();
147        status_t err = mFence->unflatten(buffer, size, fds, count);
148        if (err) return err;
149        size -= FlattenableUtils::align<4>(buffer);
150    }
151
152    // check we have enough space
153    if (size < getPodSize()) {
154        return NO_MEMORY;
155    }
156
157    FlattenableUtils::read(buffer, size, mCrop);
158    FlattenableUtils::read(buffer, size, mTransform);
159    FlattenableUtils::read(buffer, size, mScalingMode);
160    FlattenableUtils::read(buffer, size, mTimestamp);
161    FlattenableUtils::read(buffer, size, mIsAutoTimestamp);
162    FlattenableUtils::read(buffer, size, mDataSpace);
163    FlattenableUtils::read(buffer, size, mFrameNumber);
164    FlattenableUtils::read(buffer, size, mSlot);
165    FlattenableUtils::read(buffer, size, mIsDroppable);
166    FlattenableUtils::read(buffer, size, mAcquireCalled);
167    FlattenableUtils::read(buffer, size, mTransformToDisplayInverse);
168
169    return NO_ERROR;
170}
171
172const char* BufferItem::scalingModeName(uint32_t scalingMode) {
173    switch (scalingMode) {
174        case NATIVE_WINDOW_SCALING_MODE_FREEZE: return "FREEZE";
175        case NATIVE_WINDOW_SCALING_MODE_SCALE_TO_WINDOW: return "SCALE_TO_WINDOW";
176        case NATIVE_WINDOW_SCALING_MODE_SCALE_CROP: return "SCALE_CROP";
177        default: return "Unknown";
178    }
179}
180
181} // namespace android
182