- fix thread pool bug

- cleanup byte buffer support
This commit is contained in:
Dmytro Bogovych 2019-06-24 18:45:52 +03:00
parent 682362c6fe
commit b7524918fa
4 changed files with 260 additions and 257 deletions

View File

@ -62,7 +62,7 @@ set (USE_EVS_CODEC OFF CACHE BOOL "Use EVS codec.")
set(CMAKE_POSITION_INDEPENDENT_CODE ON) set(CMAKE_POSITION_INDEPENDENT_CODE ON)
set (OPENSSL_INCLUDE ${PLATFORM_LIBS}/openssl/1.0/include) set (OPENSSL_INCLUDE ${LIB_PLATFORM}/openssl/1.0/include)
message ("Using OpenSSL include files from ${OPENSSL_INCLUDE}") message ("Using OpenSSL include files from ${OPENSSL_INCLUDE}")
if (CMAKE_SYSTEM MATCHES "Windows*") if (CMAKE_SYSTEM MATCHES "Windows*")
@ -176,7 +176,7 @@ target_include_directories(rtphone
$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}> $<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}>
$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/engine> $<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/engine>
${CMAKE_CURRENT_SOURCE_DIR}/libs ${CMAKE_CURRENT_SOURCE_DIR}/libs
${PLATFORM_LIBS}/opus/include ${LIB_PLATFORM}/opus/include
PRIVATE PRIVATE
${CMAKE_CURRENT_SOURCE_DIR}/libs/ ${CMAKE_CURRENT_SOURCE_DIR}/libs/
${CMAKE_CURRENT_SOURCE_DIR}/libs/speex/include ${CMAKE_CURRENT_SOURCE_DIR}/libs/speex/include

View File

@ -10,6 +10,7 @@
#include <future> #include <future>
#include <functional> #include <functional>
#include <stdexcept> #include <stdexcept>
#include <optional>
class ThreadPool class ThreadPool
{ {
@ -42,7 +43,7 @@ inline ThreadPool::ThreadPool(size_t threads)
{ {
for(;;) for(;;)
{ {
std::function<void()> task; std::function<void()> task; bool task_assigned = false;
{ {
std::unique_lock<std::mutex> lock(this->queue_mutex); std::unique_lock<std::mutex> lock(this->queue_mutex);
@ -54,11 +55,14 @@ inline ThreadPool::ThreadPool(size_t threads)
return; return;
if(this->pause) if(this->pause)
continue; continue;
task = std::move(this->tasks.front()); if (this->tasks.size())
this->tasks.pop(); {
task = std::move(this->tasks.front()); task_assigned = true;
this->tasks.pop();
}
} }
if (task_assigned)
task(); task();
} }
} }
); );

View File

@ -14,261 +14,260 @@
using namespace ice; using namespace ice;
ByteBuffer::ByteBuffer() ByteBuffer::ByteBuffer()
{ {
initEmpty(); initEmpty();
mData.reserve(512); mData.reserve(512);
} }
ByteBuffer::ByteBuffer(size_t initialCapacity) ByteBuffer::ByteBuffer(size_t initialCapacity)
{ {
initEmpty(); initEmpty();
mData.reserve(initialCapacity); mData.reserve(initialCapacity);
} }
ByteBuffer::ByteBuffer(const ByteBuffer& src) ByteBuffer::ByteBuffer(const ByteBuffer& src)
:mData(src.mData), mComponent(src.mComponent), mTag(nullptr), :mData(src.mData), mComponent(src.mComponent), mTag(nullptr),
mRelayed(src.mRelayed), mCopyBehavior(src.mCopyBehavior), mRelayed(src.mRelayed), mCopyBehavior(src.mCopyBehavior),
mDataPtr(src.mDataPtr), mDataSize(src.mDataSize) mDataPtr(src.mDataPtr), mDataSize(src.mDataSize)
{ {
if (mCopyBehavior == CopyBehavior::CopyMemory && mData.size()) if (mCopyBehavior == CopyBehavior::CopyMemory && mData.size())
mDataPtr = &mData[0]; mDataPtr = &mData[0];
} }
ByteBuffer::ByteBuffer(const void* packetPtr, size_t packetSize, CopyBehavior behavior) ByteBuffer::ByteBuffer(const void* packetPtr, size_t packetSize, CopyBehavior behavior)
:mComponent(-1), mTag(nullptr), mRelayed(false), mCopyBehavior(behavior), mDataPtr(nullptr), mDataSize(packetSize) :mComponent(-1), mTag(nullptr), mRelayed(false), mCopyBehavior(behavior), mDataPtr(nullptr), mDataSize(packetSize)
{ {
switch (behavior) switch (behavior)
{ {
case CopyBehavior::CopyMemory: case CopyBehavior::CopyMemory:
mData.resize(packetSize); mData.resize(packetSize);
memcpy(&mData[0], packetPtr, packetSize); memcpy(&mData[0], packetPtr, packetSize);
mDataPtr = &mData[0]; mDataPtr = &mData[0];
break; break;
case CopyBehavior::UseExternal: case CopyBehavior::UseExternal:
mDataPtr = (uint8_t*)packetPtr; mDataPtr = reinterpret_cast<uint8_t*>(const_cast<void*>(packetPtr));
break; break;
default: default:
break; break;
} }
} }
ByteBuffer::~ByteBuffer() ByteBuffer::~ByteBuffer()
{ {
if (mCopyBehavior == CopyBehavior::CopyMemory) if (mCopyBehavior == CopyBehavior::CopyMemory)
memset(mDataPtr, 0, mDataSize); memset(mDataPtr, 0, mDataSize);
} }
ByteBuffer& ByteBuffer::operator = (const ByteBuffer& src) ByteBuffer& ByteBuffer::operator = (const ByteBuffer& src)
{ {
mRelayed = src.mRelayed; mRelayed = src.mRelayed;
mComment = src.mComment; mComment = src.mComment;
mComponent = src.mComponent; mComponent = src.mComponent;
mRemoteAddress = src.mRemoteAddress; mRemoteAddress = src.mRemoteAddress;
mTag = src.mTag; mTag = src.mTag;
if (src.mCopyBehavior == CopyBehavior::CopyMemory) if (src.mCopyBehavior == CopyBehavior::CopyMemory)
{ {
mData = src.mData; mData = src.mData;
mCopyBehavior = CopyBehavior::CopyMemory; mCopyBehavior = CopyBehavior::CopyMemory;
syncPointer(); syncPointer();
}
else
{
mDataPtr = src.mDataPtr;
mDataSize = src.mDataSize;
mCopyBehavior = CopyBehavior::UseExternal;
}
} return *this;
else
{
mDataPtr = src.mDataPtr;
mDataSize = src.mDataSize;
mCopyBehavior = CopyBehavior::UseExternal;
}
return *this;
} }
void ByteBuffer::clear() void ByteBuffer::clear()
{ {
mData.resize(0); mData.resize(0);
mDataSize = 0; mDataSize = 0;
mDataPtr = nullptr; mDataPtr = nullptr;
} }
size_t ByteBuffer::size() const size_t ByteBuffer::size() const
{ {
return mDataSize; return mDataSize;
} }
const uint8_t* ByteBuffer::data() const const uint8_t* ByteBuffer::data() const
{ {
return (const uint8_t*)mDataPtr; return reinterpret_cast<const uint8_t*>(mDataPtr);
} }
uint8_t* ByteBuffer::mutableData() uint8_t* ByteBuffer::mutableData()
{ {
return mDataPtr; return mDataPtr;
} }
NetworkAddress& ByteBuffer::remoteAddress() NetworkAddress& ByteBuffer::remoteAddress()
{ {
return mRemoteAddress; return mRemoteAddress;
} }
void ByteBuffer::setRemoteAddress(const NetworkAddress& addr) void ByteBuffer::setRemoteAddress(const NetworkAddress& addr)
{ {
mRemoteAddress = addr; mRemoteAddress = addr;
} }
void ByteBuffer::setComment(std::string comment) void ByteBuffer::setComment(std::string comment)
{ {
mComment = comment; mComment = comment;
} }
std::string ByteBuffer::comment() std::string ByteBuffer::comment()
{ {
return mComment; return mComment;
} }
std::string ByteBuffer::hexstring() std::string ByteBuffer::hexstring()
{ {
std::string result; std::string result;
result.resize(mDataSize * 2, (char)0xCC); result.resize(mDataSize * 2, (char)0xCC);
for (std::vector<uint8_t>::size_type index = 0; index < mDataSize; index++) for (std::vector<uint8_t>::size_type index = 0; index < mDataSize; index++)
{ {
char value[3]; char value[3];
sprintf(value, "%02X", (unsigned char)mDataPtr[index]); sprintf(value, "%02X", (unsigned char)mDataPtr[index]);
result[index*2] = value[0]; result[index*2] = value[0];
result[index*2+1] = value[1]; result[index*2+1] = value[1];
} }
return result; return result;
} }
void ByteBuffer::reserve(size_t capacity) void ByteBuffer::reserve(size_t capacity)
{ {
mData.reserve(capacity); mData.reserve(capacity);
syncPointer(); syncPointer();
} }
void ByteBuffer::insertTurnPrefix(unsigned short prefix) void ByteBuffer::insertTurnPrefix(unsigned short prefix)
{ {
assert(mCopyBehavior == CopyBehavior::CopyMemory); assert(mCopyBehavior == CopyBehavior::CopyMemory);
mData.insert(mData.begin(), 2, 32); mData.insert(mData.begin(), 2, 32);
unsigned short nprefix = htons(prefix); unsigned short nprefix = htons(prefix);
mData[0] = nprefix & 0xFF; mData[0] = nprefix & 0xFF;
mData[1] = (nprefix & 0xFF00) >> 8; mData[1] = (nprefix & 0xFF00) >> 8;
syncPointer(); syncPointer();
} }
int ByteBuffer::component() int ByteBuffer::component()
{ {
return mComponent; return mComponent;
} }
void ByteBuffer::setComponent(int component) void ByteBuffer::setComponent(int component)
{ {
mComponent = component; mComponent = component;
} }
void ByteBuffer::truncate(size_t newsize) void ByteBuffer::truncate(size_t newsize)
{ {
assert (mCopyBehavior == CopyBehavior::CopyMemory); assert (mCopyBehavior == CopyBehavior::CopyMemory);
mData.erase(mData.begin() + newsize, mData.end()); mData.erase(mData.begin() + newsize, mData.end());
syncPointer(); syncPointer();
} }
void ByteBuffer::erase(size_t p, size_t l) void ByteBuffer::erase(size_t p, size_t l)
{ {
assert (mCopyBehavior == CopyBehavior::CopyMemory); assert (mCopyBehavior == CopyBehavior::CopyMemory);
mData.erase(mData.begin()+p, mData.begin()+p+l); mData.erase(mData.begin() + p, mData.begin() + p + l);
syncPointer(); syncPointer();
} }
void ByteBuffer::resize(size_t newsize) void ByteBuffer::resize(size_t newsize)
{ {
assert (mCopyBehavior == CopyBehavior::CopyMemory); assert (mCopyBehavior == CopyBehavior::CopyMemory);
std::vector<uint8_t>::size_type sz = mData.size(); std::vector<uint8_t>::size_type sz = mData.size();
mData.resize(newsize); mData.resize(newsize);
if (newsize > sz) if (newsize > sz)
memset(&mData[sz], 0, newsize - sz); memset(&mData[sz], 0, newsize - sz);
syncPointer(); syncPointer();
} }
void ByteBuffer::appendBuffer(const void *data, size_t size) void ByteBuffer::appendBuffer(const void *data, size_t size)
{ {
assert (mCopyBehavior == CopyBehavior::CopyMemory); assert (mCopyBehavior == CopyBehavior::CopyMemory);
size_t len = mData.size(); size_t len = mData.size();
mData.resize(len + size); mData.resize(len + size);
memmove(mData.data() + len, data, size); memmove(mData.data() + len, data, size);
syncPointer(); syncPointer();
} }
void* ByteBuffer::tag() void* ByteBuffer::tag()
{ {
return mTag; return mTag;
} }
void ByteBuffer::setTag(void* tag) void ByteBuffer::setTag(void* tag)
{ {
mTag = tag; mTag = tag;
} }
bool ByteBuffer::relayed() bool ByteBuffer::relayed()
{ {
return mRelayed; return mRelayed;
} }
void ByteBuffer::setRelayed(bool value) void ByteBuffer::setRelayed(bool value)
{ {
mRelayed = value; mRelayed = value;
} }
void ByteBuffer::initEmpty() void ByteBuffer::initEmpty()
{ {
mDataPtr = nullptr; mDataPtr = nullptr;
mDataSize = 0; mDataSize = 0;
mCopyBehavior = CopyBehavior::CopyMemory; mCopyBehavior = CopyBehavior::CopyMemory;
mRelayed = false; mRelayed = false;
mComponent = -1; mComponent = -1;
mTag = nullptr; mTag = nullptr;
} }
void ByteBuffer::syncPointer() void ByteBuffer::syncPointer()
{ {
mDataPtr = mData.empty() ? nullptr : &mData[0]; mDataPtr = mData.empty() ? nullptr : mData.data();
mDataSize = mData.size(); mDataSize = mData.size();
} }
uint8_t ByteBuffer::operator[](int index) const uint8_t ByteBuffer::operator[](int index) const
{ {
return mDataPtr[index]; return mDataPtr[index];
} }
uint8_t& ByteBuffer::operator[](int index) uint8_t& ByteBuffer::operator[](int index)
{ {
return mDataPtr[index]; return mDataPtr[index];
} }
// ----------------- BitReader ------------------- // ----------------- BitReader -------------------
BitReader::BitReader(const ByteBuffer &buffer) BitReader::BitReader(const ByteBuffer &buffer)
:mStream(buffer.data()), mStreamLen(buffer.size()), mStreamOffset(0), mCurrentBit(0) :mStream(buffer.data()), mStreamLen(buffer.size()), mStreamOffset(0), mCurrentBit(0)
{ {
init(); init();
} }
BitReader::BitReader(const void *input, size_t bytes) BitReader::BitReader(const void *input, size_t bytes)
:mStream((const uint8_t*)input), mStreamLen(bytes), mStreamOffset(0), mCurrentBit(0) :mStream(reinterpret_cast<const uint8_t*>(input)), mStreamLen(bytes), mStreamOffset(0), mCurrentBit(0)
{ {
init(); init();
} }
void BitReader::init() void BitReader::init()
{ {
mStreamOffset = mStreamLen << 3; mStreamOffset = mStreamLen << 3;
mCurrentPosition = 0;//mStreamOffset - 1; mCurrentPosition = 0;//mStreamOffset - 1;
mCurrentBit = 0; mCurrentBit = 0;
} }
BitReader::~BitReader() BitReader::~BitReader()
@ -277,71 +276,71 @@ BitReader::~BitReader()
// Check for valid position // Check for valid position
uint8_t BitReader::readBit() uint8_t BitReader::readBit()
{ {
uint8_t value = 0x00; uint8_t value = 0x00;
if (mCurrentPosition < mStreamOffset) if (mCurrentPosition < mStreamOffset)
{ {
// Read single BIT // Read single BIT
size_t currentByte = mCurrentPosition >> 3; size_t currentByte = mCurrentPosition >> 3;
uint8_t currentBit = (uint8_t)(mCurrentPosition % 8); uint8_t currentBit = (uint8_t)(mCurrentPosition % 8);
value = ((uint8_t)(mStream[currentByte] << currentBit) >> 7); value = ((uint8_t)(mStream[currentByte] << currentBit) >> 7);
mCurrentPosition = std::max((size_t)0, std::min(mStreamOffset-1, mCurrentPosition+1)); mCurrentPosition = std::max((size_t)0, std::min(mStreamOffset-1, mCurrentPosition+1));
} }
return value; return value;
} }
uint32_t BitReader::readBits(size_t nrOfBits) uint32_t BitReader::readBits(size_t nrOfBits)
{ {
assert (nrOfBits <= 32); assert (nrOfBits <= 32);
uint32_t result = 0; uint32_t result = 0;
BitWriter bw(&result); BitWriter bw(&result);
for (int i=0; i<(int)nrOfBits; i++) for (int i=0; i<static_cast<int>(nrOfBits); i++)
bw.writeBit(readBit()); bw.writeBit(readBit());
return result; return result;
} }
size_t BitReader::readBits(void *output, size_t nrOfBits) size_t BitReader::readBits(void *output, size_t nrOfBits)
{ {
// Check how much bits available // Check how much bits available
nrOfBits = std::min(nrOfBits, mStreamOffset - mCurrentPosition); nrOfBits = std::min(nrOfBits, mStreamOffset - mCurrentPosition);
BitWriter bw(output); BitWriter bw(output);
for (int i=0; i<(int)nrOfBits; i++) for (int i=0; i<static_cast<int>(nrOfBits); i++)
bw.writeBit(readBit()); bw.writeBit(readBit());
return nrOfBits; return nrOfBits;
} }
size_t BitReader::count() const size_t BitReader::count() const
{ {
return mStreamOffset; return mStreamOffset;
} }
size_t BitReader::position() const size_t BitReader::position() const
{ {
return mCurrentPosition; return mCurrentPosition;
} }
// ----------------- BitWriter ------------------- // ----------------- BitWriter -------------------
BitWriter::BitWriter(ByteBuffer &buffer) BitWriter::BitWriter(ByteBuffer &buffer)
:mStream(buffer.mutableData()), mStreamLen(0), mStreamOffset(0), mCurrentBit(0) :mStream(buffer.mutableData()), mStreamLen(0), mStreamOffset(0), mCurrentBit(0)
{ {
init(); init();
} }
BitWriter::BitWriter(void *output) BitWriter::BitWriter(void *output)
:mStream((uint8_t*)output), mStreamLen(0), mStreamOffset(0), mCurrentBit(0) :mStream((uint8_t*)output), mStreamLen(0), mStreamOffset(0), mCurrentBit(0)
{ {
init(); init();
} }
void BitWriter::init() void BitWriter::init()
{ {
mStreamOffset = mStreamLen << 3; mStreamOffset = mStreamLen << 3;
mCurrentPosition = 0;//mStreamOffset - 1; mCurrentPosition = 0;//mStreamOffset - 1;
mCurrentBit = 0; mCurrentBit = 0;
} }
BitWriter::~BitWriter() BitWriter::~BitWriter()
@ -349,212 +348,212 @@ BitWriter::~BitWriter()
BitWriter& BitWriter::writeBit(int bit) BitWriter& BitWriter::writeBit(int bit)
{ {
bit = bit ? 1 : 0; bit = bit ? 1 : 0;
// Check for current bit offset // Check for current bit offset
if ((mCurrentBit % 8) == 0) if ((mCurrentBit % 8) == 0)
{ {
// Write new zero byte to the end of stream // Write new zero byte to the end of stream
mCurrentBit = 0; mCurrentBit = 0;
mStreamLen++; mStreamLen++;
mStream[mStreamLen-1] = 0; mStream[mStreamLen-1] = 0;
} }
// Write single BIT // Write single BIT
mStream[mStreamLen-1] <<= 1; mStream[mStreamLen-1] <<= 1;
mStream[mStreamLen-1] |= bit; mStream[mStreamLen-1] |= bit;
mStreamOffset++; mStreamOffset++;
mCurrentPosition = mStreamOffset - 1; mCurrentPosition = mStreamOffset - 1;
mCurrentBit++; mCurrentBit++;
return *this; return *this;
} }
size_t BitWriter::count() const size_t BitWriter::count() const
{ {
return mStreamOffset; return mStreamOffset;
} }
// ----------------- BufferReader ---------------- // ----------------- BufferReader ----------------
BufferReader::BufferReader(const ByteBuffer &buffer) BufferReader::BufferReader(const ByteBuffer &buffer)
:mData(buffer.data()), mSize(buffer.size()), mIndex(0) :mData(buffer.data()), mSize(buffer.size()), mIndex(0)
{} {}
BufferReader::BufferReader(const void *input, size_t bytes) BufferReader::BufferReader(const void *input, size_t bytes)
:mData((const uint8_t*)input), mSize(bytes), mIndex(0) :mData(reinterpret_cast<const uint8_t*>(input)), mSize(bytes), mIndex(0)
{} {}
uint32_t BufferReader::readUInt() uint32_t BufferReader::readUInt()
{ {
uint32_t nresult = 0; uint32_t nresult = 0;
readBuffer(&nresult, 4); readBuffer(&nresult, 4);
return ntohl(nresult); return ntohl(nresult);
} }
uint32_t BufferReader::readNativeUInt() uint32_t BufferReader::readNativeUInt()
{ {
uint32_t nresult = 0; uint32_t nresult = 0;
readBuffer(&nresult, 4); readBuffer(&nresult, 4);
return nresult; return nresult;
} }
uint16_t BufferReader::readUShort() uint16_t BufferReader::readUShort()
{ {
uint16_t result = 0; uint16_t result = 0;
readBuffer(&result, 2); readBuffer(&result, 2);
return ntohs(result); return ntohs(result);
} }
uint16_t BufferReader::readNativeUShort() uint16_t BufferReader::readNativeUShort()
{ {
uint16_t result = 0; uint16_t result = 0;
readBuffer(&result, 2); readBuffer(&result, 2);
return result; return result;
} }
uint8_t BufferReader::readUChar() uint8_t BufferReader::readUChar()
{ {
uint8_t result = 0; uint8_t result = 0;
readBuffer(&result, 1); readBuffer(&result, 1);
return result; return result;
} }
NetworkAddress BufferReader::readIp(int family) NetworkAddress BufferReader::readIp(int family)
{ {
if (family == AF_INET) if (family == AF_INET)
{ {
sockaddr_in addr; sockaddr_in addr;
memset(&addr, 0, sizeof(addr)); memset(&addr, 0, sizeof(addr));
addr.sin_family = AF_INET; addr.sin_family = AF_INET;
addr.sin_port = 0; addr.sin_port = 0;
readBuffer(&addr.sin_addr.s_addr, 4); readBuffer(&addr.sin_addr.s_addr, 4);
return NetworkAddress((sockaddr&)addr, sizeof(addr)); return NetworkAddress(reinterpret_cast<sockaddr&>(addr), sizeof(addr));
} }
else else
if (family == AF_INET6) if (family == AF_INET6)
{ {
sockaddr_in6 addr; sockaddr_in6 addr;
memset(&addr, 0, sizeof(addr)); memset(&addr, 0, sizeof(addr));
addr.sin6_family = AF_INET6; addr.sin6_family = AF_INET6;
addr.sin6_port = 0; addr.sin6_port = 0;
readBuffer(&addr.sin6_addr, 16); readBuffer(&addr.sin6_addr, 16);
return NetworkAddress((sockaddr&)addr, sizeof(addr)); return NetworkAddress(reinterpret_cast<sockaddr&>(addr), sizeof(addr));
} }
return NetworkAddress(); return NetworkAddress();
} }
size_t BufferReader::readBuffer(void* dataPtr, size_t dataSize) size_t BufferReader::readBuffer(void* dataPtr, size_t dataSize)
{ {
if (dataSize > 0) if (dataSize > 0)
{ {
size_t available = mSize - mIndex; size_t available = mSize - mIndex;
if (available < dataSize) if (available < dataSize)
dataSize = available; dataSize = available;
if (NULL != dataPtr) if (nullptr != dataPtr)
memcpy(dataPtr, mData + mIndex, dataSize); memcpy(dataPtr, mData + mIndex, dataSize);
mIndex += dataSize; mIndex += dataSize;
return dataSize; return dataSize;
} }
return 0; return 0;
} }
size_t BufferReader::readBuffer(ByteBuffer& bb, size_t dataSize) size_t BufferReader::readBuffer(ByteBuffer& bb, size_t dataSize)
{ {
if (dataSize > 0) if (dataSize > 0)
{ {
// Find how much data are available in fact // Find how much data are available in fact
size_t available = mSize - mIndex; size_t available = mSize - mIndex;
if (available < dataSize) if (available < dataSize)
dataSize = available; dataSize = available;
// Extend byte buffer // Extend byte buffer
size_t startIndex = bb.size(); size_t startIndex = bb.size();
bb.resize(bb.size() + dataSize); bb.resize(bb.size() + dataSize);
memcpy(bb.mutableData() + startIndex, mData + mIndex, dataSize); memcpy(bb.mutableData() + startIndex, mData + mIndex, dataSize);
mIndex += dataSize; mIndex += dataSize;
return dataSize; return dataSize;
} }
return 0; return 0;
} }
size_t BufferReader::count() const size_t BufferReader::count() const
{ {
return mIndex; return mIndex;
} }
// -------------- BufferWriter ---------------------- // -------------- BufferWriter ----------------------
BufferWriter::BufferWriter(ByteBuffer &buffer) BufferWriter::BufferWriter(ByteBuffer &buffer)
:mData(buffer.mutableData()), mIndex(0) :mData(buffer.mutableData()), mIndex(0)
{} {}
BufferWriter::BufferWriter(void *output) BufferWriter::BufferWriter(void *output)
:mData((uint8_t*)output), mIndex(0) :mData(reinterpret_cast<uint8_t*>(output)), mIndex(0)
{} {}
void BufferWriter::writeUInt(uint32_t value) void BufferWriter::writeUInt(uint32_t value)
{ {
// Convert to network order bytes // Convert to network order bytes
uint32_t nvalue = htonl(value); uint32_t nvalue = htonl(value);
writeBuffer(&nvalue, 4); writeBuffer(&nvalue, 4);
} }
void BufferWriter::writeUShort(uint16_t value) void BufferWriter::writeUShort(uint16_t value)
{ {
uint16_t nvalue = htons(value); uint16_t nvalue = htons(value);
writeBuffer(&nvalue, 2); writeBuffer(&nvalue, 2);
} }
void BufferWriter::writeUChar(uint8_t value) void BufferWriter::writeUChar(uint8_t value)
{ {
writeBuffer(&value, 1); writeBuffer(&value, 1);
} }
void BufferWriter::writeIp(const NetworkAddress& ip) void BufferWriter::writeIp(const NetworkAddress& ip)
{ {
switch (ip.stunType()) switch (ip.stunType())
{ {
case 1/*IPv4*/: case 1/*IPv4*/:
writeBuffer(&ip.sockaddr4()->sin_addr, 4); writeBuffer(&ip.sockaddr4()->sin_addr, 4);
break; break;
case 2/*IPv6*/: case 2/*IPv6*/:
writeBuffer(&ip.sockaddr6()->sin6_addr, 16); writeBuffer(&ip.sockaddr6()->sin6_addr, 16);
break; break;
default: default:
assert(0); assert(0);
} }
} }
void BufferWriter::writeBuffer(const void* dataPtr, size_t dataSize) void BufferWriter::writeBuffer(const void* dataPtr, size_t dataSize)
{ {
memmove(mData + mIndex, dataPtr, dataSize); memmove(mData + mIndex, dataPtr, dataSize);
mIndex += dataSize; mIndex += dataSize;
} }
void BufferWriter::rewind() void BufferWriter::rewind()
{ {
mIndex = 0; mIndex = 0;
} }
void BufferWriter::skip(int count) void BufferWriter::skip(int count)
{ {
mIndex += count; mIndex += count;
} }
size_t BufferWriter::offset() const size_t BufferWriter::offset() const
{ {
return mIndex; return mIndex;
} }

View File

@ -68,7 +68,7 @@ namespace ice
protected: protected:
std::vector<uint8_t> mData; // Internal storage std::vector<uint8_t> mData; // Internal storage
uint8_t* mDataPtr; // Pointer to internal storage or external data uint8_t* mDataPtr; // Pointer to internal storage or external data
uint32_t mDataSize; // Used only for mCopyBehavior == UseExternal size_t mDataSize; // Used only for mCopyBehavior == UseExternal
NetworkAddress mRemoteAddress; // Associates buffer with IP address NetworkAddress mRemoteAddress; // Associates buffer with IP address
int mComponent; // Associates buffer with component ID int mComponent; // Associates buffer with component ID
std::string mComment; // Comment's for this buffer - useful in debugging std::string mComment; // Comment's for this buffer - useful in debugging