diff options
author | Lingfeng Yang <lfy@google.com> | 2020-10-29 08:52:13 -0700 |
---|---|---|
committer | Lingfeng Yang <lfy@google.com> | 2020-10-29 08:52:13 -0700 |
commit | ee4aea3ef44ae88b2e048f3b0d63f070e5b28926 (patch) | |
tree | 93655a59aeeade1438033b1b71300419be7616a2 /stream-servers/ReadBuffer.cpp | |
parent | 187b9d36a6d18c4dfb46a7a079354d1e0a20213c (diff) | |
download | vulkan-cereal-ee4aea3ef44ae88b2e048f3b0d63f070e5b28926.tar.gz |
Start building libOpenglRender and add more host support files
Bug: 171711491
Change-Id: Ie1a6ca9cc5310e5ee2a72ae558450bcb4f2b9263
Diffstat (limited to 'stream-servers/ReadBuffer.cpp')
-rw-r--r-- | stream-servers/ReadBuffer.cpp | 140 |
1 files changed, 140 insertions, 0 deletions
diff --git a/stream-servers/ReadBuffer.cpp b/stream-servers/ReadBuffer.cpp new file mode 100644 index 00000000..8bc52379 --- /dev/null +++ b/stream-servers/ReadBuffer.cpp @@ -0,0 +1,140 @@ +/* +* Copyright (C) 2011 The Android Open Source Project +* +* Licensed under the Apache License, Version 2.0 (the "License"); +* you may not use this file except in compliance with the License. +* You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +#include "ReadBuffer.h" + +#include "ErrorLog.h" + +#include <algorithm> + +#include <assert.h> +#include <string.h> +#include <limits.h> + +namespace emugl { + +ReadBuffer::ReadBuffer(size_t bufsize) { + m_size = bufsize; + m_buf = (unsigned char*)malloc(m_size); + m_validData = 0; + m_readPtr = m_buf; +} + +ReadBuffer::~ReadBuffer() { + free(m_buf); +} + +void ReadBuffer::setNeededFreeTailSize(int size) { + m_neededFreeTailSize = size; +} + +int ReadBuffer::getData(IOStream* stream, int minSize) { + assert(stream); + assert(minSize > (int)m_validData); + + const int minSizeToRead = minSize - m_validData; + const int neededFreeTailThisTime = + std::max(minSizeToRead, + m_neededFreeTailSize); + + int maxSizeToRead; + const int freeTailSize = m_buf + m_size - (m_readPtr + m_validData); + if (freeTailSize >= neededFreeTailThisTime) { + maxSizeToRead = freeTailSize; + } else { + if (freeTailSize + (m_readPtr - m_buf) >= neededFreeTailThisTime) { + // There's some gap in the beginning, if we move the data over it + // that's going to be enough. + memmove(m_buf, m_readPtr, m_validData); + } else { + // Not enough space even with moving, reallocate. + // Note: make sure we can fit at least two of the requested packets + // into the new buffer to minimize the reallocations and + // memmove()-ing stuff around. + size_t new_size = std::max<size_t>( + 2 * minSizeToRead + m_validData, + 2 * m_size); + if (new_size < m_size) { // overflow check + new_size = INT_MAX; + } + + const auto new_buf = (unsigned char*)malloc(new_size); + if (!new_buf) { + ERR("Failed to alloc %zu bytes for ReadBuffer\n", new_size); + return -1; + } + + memcpy(new_buf, m_readPtr, m_validData); + free(m_buf); + m_buf = new_buf; + m_size = new_size; + } + // We can read more now, let's request it in case all data is ready + // for reading. + maxSizeToRead = m_size - m_validData; + m_readPtr = m_buf; + } + + // get fresh data into the buffer; + int readTotal = 0; + do { + const size_t readNow = stream->read(m_readPtr + m_validData, + maxSizeToRead - readTotal); + + if (!readNow) { + if (readTotal > 0) { + return readTotal; + } else { + return -1; + } + } + readTotal += readNow; + m_validData += readNow; + } while (readTotal < minSizeToRead); + + return readTotal; +} + +void ReadBuffer::consume(size_t amount) { + assert(amount <= m_validData); + m_validData -= amount; + m_readPtr += amount; +} + +void ReadBuffer::onSave(android::base::Stream* stream) { + stream->putBe32(m_size); + stream->putBe32(m_validData); + stream->write(m_readPtr, m_validData); +} + +void ReadBuffer::onLoad(android::base::Stream* stream) { + const auto size = stream->getBe32(); + if (size > m_size) { + m_size = size; + free(m_buf); + m_buf = (unsigned char*)malloc(m_size); + } + m_readPtr = m_buf; + m_validData = stream->getBe32(); + assert(m_validData <= m_size); + stream->read(m_readPtr, m_validData); +} + +void ReadBuffer::printStats() { + printf("ReadBuffer::%s: tail move time %f ms\n", __func__, + (float)m_tailMoveTimeUs / 1000.0f); + m_tailMoveTimeUs = 0; +} +} // namespace emugl |