Merge remote-tracking branch 'origin/feature/vector_external_buffer' into development

This commit is contained in:
John Wellbelove 2019-03-28 21:23:13 +00:00
commit aa286a5126
8 changed files with 3280 additions and 5 deletions

View File

@ -952,7 +952,25 @@ namespace etl
etl::destroy(p_buffer, p_end);
ETL_SUBTRACT_DEBUG_COUNT(int32_t(std::distance(p_buffer, p_end)))
p_end = p_buffer;
p_end = p_buffer;
}
//*********************************************************************
/// Initialise the source vector after a move.
//*********************************************************************
void initialise_source_external_buffer_after_move()
{
ETL_SUBTRACT_DEBUG_COUNT(int32_t(std::distance(p_buffer, p_end)))
p_end = p_buffer;
}
//*********************************************************************
/// Initialise the destination vector after a move.
//*********************************************************************
void initialise_destination_external_buffer_after_move()
{
ETL_ADD_DEBUG_COUNT(int32_t(std::distance(p_buffer, p_end)))
}
//*************************************************************************
@ -962,14 +980,14 @@ namespace etl
{
uintptr_t length = p_end - p_buffer;
p_buffer = p_buffer_;
p_end = p_buffer_ + length;
p_end = p_buffer_ + length;
}
private:
pointer p_buffer; ///< Pointer to the start of the buffer.
pointer p_end; ///< Pointer to one past the last element in the buffer.
private:
//*********************************************************************
/// Create a new element with a default value at the back.
//*********************************************************************
@ -1281,6 +1299,157 @@ namespace etl
typename etl::aligned_storage<sizeof(T) * MAX_SIZE, etl::alignment_of<T>::value>::type buffer;
};
//***************************************************************************
/// A vector implementation that uses a fixed size buffer.
/// The buffer is supplied on construction.
///\tparam T The element type.
///\ingroup vector
//***************************************************************************
template <typename T>
class vector<T, 0> : public etl::ivector<T>
{
public:
//*************************************************************************
/// Constructor.
//*************************************************************************
vector(void* buffer, size_t max_size)
: etl::ivector<T>(reinterpret_cast<T*>(buffer), max_size)
{
this->initialise();
}
//*************************************************************************
/// Constructor, with size.
///\param initial_size The initial size of the vector.
//*************************************************************************
explicit vector(size_t initial_size, void* buffer, size_t max_size)
: etl::ivector<T>(reinterpret_cast<T*>(buffer), max_size)
{
this->initialise();
this->resize(initial_size);
}
//*************************************************************************
/// Constructor, from initial size and value.
///\param initial_size The initial size of the vector.
///\param value The value to fill the vector with.
//*************************************************************************
vector(size_t initial_size, typename etl::ivector<T>::parameter_t value, void* buffer, size_t max_size)
: etl::ivector<T>(reinterpret_cast<T*>(buffer), max_size)
{
this->initialise();
this->resize(initial_size, value);
}
//*************************************************************************
/// Constructor, from an iterator range.
///\tparam TIterator The iterator type.
///\param first The iterator to the first element.
///\param last The iterator to the last element + 1.
//*************************************************************************
template <typename TIterator>
vector(TIterator first, TIterator last, void* buffer, size_t max_size)
: etl::ivector<T>(reinterpret_cast<T*>(buffer), max_size)
{
this->assign(first, last);
}
#if ETL_CPP11_SUPPORTED && !defined(ETL_STLPORT) && !defined(ETL_NO_STL)
//*************************************************************************
/// Constructor, from an initializer_list.
//*************************************************************************
vector(std::initializer_list<T> init, void* buffer, size_t max_size)
: etl::ivector<T>(reinterpret_cast<T*>(buffer), max_size)
{
this->assign(init.begin(), init.end());
}
#endif
//*************************************************************************
/// Copy constructor.
//*************************************************************************
vector(const vector& other, void* buffer, size_t max_size)
: etl::ivector<T>(reinterpret_cast<T*>(buffer), max_size)
{
this->assign(other.begin(), other.end());
}
//*************************************************************************
/// Assignment operator.
//*************************************************************************
vector& operator = (const vector& rhs)
{
if (&rhs != this)
{
this->assign(rhs.cbegin(), rhs.cend());
}
return *this;
}
#if ETL_CPP11_SUPPORTED
//*************************************************************************
/// Move constructor.
//*************************************************************************
vector(vector&& other, void* buffer, size_t max_size)
: etl::ivector<T>(reinterpret_cast<T*>(buffer), max_size)
{
if (this != &other)
{
this->initialise();
this->p_buffer = other.p_buffer;
this->p_end = other.p_end;
this->initialise_destination_external_buffer_after_move();
other.initialise_source_external_buffer_after_move();
}
}
//*************************************************************************
/// Move assignment operator.
//*************************************************************************
vector& operator = (vector&& rhs)
{
if (&rhs != this)
{
this->clear();
this->p_buffer = rhs.p_buffer;
this->p_end = rhs.p_end;
this->initialise_destination_external_buffer_after_move();
rhs.initialise_source_external_buffer_after_move();
}
return *this;
}
#endif
//*************************************************************************
/// Destructor.
//*************************************************************************
~vector()
{
this->clear();
}
//*************************************************************************
/// Fix the internal pointers after a low level memory copy.
//*************************************************************************
#ifdef ETL_IVECTOR_REPAIR_ENABLE
virtual
#endif
void repair()
{
#if ETL_CPP11_TYPE_TRAITS_IS_TRIVIAL_SUPPORTED
ETL_ASSERT(std::is_trivially_copyable<T>::value, ETL_ERROR(etl::vector_incompatible_type));
#endif
etl::ivector<T>::repair_buffer(this->p_buffer);
}
};
//***************************************************************************
/// A vector implementation that uses a fixed size buffer.
///\tparam T The element type.
@ -1375,6 +1544,50 @@ namespace etl
return *this;
}
#if ETL_CPP11_SUPPORTED
//*************************************************************************
/// Move constructor.
//*************************************************************************
vector(vector&& other)
: etl::ivector<T*>(reinterpret_cast<T**>(&buffer), MAX_SIZE)
{
if (this != &other)
{
this->initialise();
typename etl::ivector<T>::iterator itr = other.begin();
while (itr != other.end())
{
this->push_back(std::move(*itr));
++itr;
}
other.initialise_source_external_buffer_after_move();
}
}
//*************************************************************************
/// Move assignment operator.
//*************************************************************************
vector& operator = (vector&& rhs)
{
if (&rhs != this)
{
this->clear();
typename etl::ivector<T>::iterator itr = rhs.begin();
while (itr != rhs.end())
{
this->push_back(std::move(*itr));
++itr;
}
rhs.initialise_source_external_buffer_after_move();
}
return *this;
}
#endif
//*************************************************************************
/// Fix the internal pointers after a low level memory copy.
//*************************************************************************
@ -1387,6 +1600,151 @@ namespace etl
typename etl::aligned_storage<sizeof(T*) * MAX_SIZE, etl::alignment_of<T*>::value>::type buffer;
};
//***************************************************************************
/// A vector implementation that uses a fixed size buffer.
/// The buffer is supplied on construction.
///\tparam T The element type that is pointed to.
///\ingroup vector
//***************************************************************************
template <typename T>
class vector<T*, 0> : public etl::ivector<T*>
{
public:
//*************************************************************************
/// Constructor.
//*************************************************************************
vector(void* buffer, size_t max_size)
: etl::ivector<T*>(reinterpret_cast<T**>(buffer), max_size)
{
this->initialise();
}
//*************************************************************************
/// Constructor, with size.
///\param initial_size The initial size of the vector.
//*************************************************************************
explicit vector(size_t initial_size, void* buffer, size_t max_size)
: etl::ivector<T*>(reinterpret_cast<T**>(buffer), max_size)
{
this->initialise();
this->resize(initial_size);
}
//*************************************************************************
/// Constructor, from initial size and value.
///\param initial_size The initial size of the vector.
///\param value The value to fill the vector with.
//*************************************************************************
vector(size_t initial_size, typename etl::ivector<T*>::parameter_t value, void* buffer, size_t max_size)
: etl::ivector<T*>(reinterpret_cast<T**>(buffer), max_size)
{
this->initialise();
this->resize(initial_size, value);
}
//*************************************************************************
/// Constructor, from an iterator range.
///\tparam TIterator The iterator type.
///\param first The iterator to the first element.
///\param last The iterator to the last element + 1.
//*************************************************************************
template <typename TIterator>
vector(TIterator first, TIterator last, void* buffer, size_t max_size)
: etl::ivector<T*>(reinterpret_cast<T**>(buffer), max_size)
{
this->assign(first, last);
}
#if ETL_CPP11_SUPPORTED && !defined(ETL_STLPORT) && !defined(ETL_NO_STL)
//*************************************************************************
/// Constructor, from an initializer_list.
//*************************************************************************
vector(std::initializer_list<T*> init, void* buffer, size_t max_size)
: etl::ivector<T*>(reinterpret_cast<T**>(buffer), max_size)
{
this->assign(init.begin(), init.end());
}
#endif
//*************************************************************************
/// Copy constructor.
//*************************************************************************
vector(const vector& other, void* buffer, size_t max_size)
: etl::ivector<T*>(reinterpret_cast<T**>(buffer), max_size)
{
this->assign(other.begin(), other.end());
}
//*************************************************************************
/// Assignment operator.
//*************************************************************************
vector& operator = (const vector& rhs)
{
if (&rhs != this)
{
this->assign(rhs.cbegin(), rhs.cend());
}
return *this;
}
#if ETL_CPP11_SUPPORTED
//*************************************************************************
/// Move constructor.
//*************************************************************************
vector(vector&& other, void* buffer, size_t max_size)
: etl::ivector<T*>(reinterpret_cast<T**>(buffer), max_size)
{
if (this != &other)
{
this->p_buffer = other.p_buffer;
this->p_end = other.p_end;
this->initialise_destination_external_buffer_after_move();
other.initialise_source_external_buffer_after_move();
}
}
//*************************************************************************
/// Move assignment operator.
//*************************************************************************
vector& operator = (vector&& rhs)
{
if (&rhs != this)
{
this->clear();
this->p_buffer = rhs.p_buffer;
this->p_end = rhs.p_end;
this->initialise_destination_external_buffer_after_move();
rhs.initialise_source_external_buffer_after_move();
}
return *this;
}
#endif
//*************************************************************************
/// Destructor.
//*************************************************************************
~vector()
{
this->clear();
}
//*************************************************************************
/// Fix the internal pointers after a low level memory copy.
//*************************************************************************
#ifdef ETL_IVECTOR_REPAIR_ENABLE
virtual
#endif
void repair()
{
etl::ivector<T*>::repair_buffer(this->p_buffer);
}
};
}
#ifdef ETL_COMPILER_GCC

View File

@ -9,7 +9,7 @@ Fixed bug where 'truncated' was not always set correctly for strings.
===============================================================================
14.14.0
Fixed string push_back() bug where ther internal terminator was not updated.
Fixed string push_back() bug where the internal terminator was not updated.
Basic Conan package added.
Added const ref istring constructors.
Updated profiles for C++17.

View File

@ -441,8 +441,10 @@
<Unit filename="../test_variant.cpp" />
<Unit filename="../test_variant_pool.cpp" />
<Unit filename="../test_vector.cpp" />
<Unit filename="../test_vector_external_buffer.cpp" />
<Unit filename="../test_vector_non_trivial.cpp" />
<Unit filename="../test_vector_pointer.cpp" />
<Unit filename="../test_vector_pointer_external_buffer.cpp" />
<Unit filename="../test_visitor.cpp" />
<Unit filename="../test_xor_checksum.cpp" />
<Unit filename="../test_xor_rotate_checksum.cpp" />

View File

@ -163,6 +163,16 @@ namespace
CHECK(data2 != data);
}
//*************************************************************************
TEST_FIXTURE(SetupFixture, test_move_constructor)
{
Data data(initial_data.begin(), initial_data.end());
Data data2(std::move(data));
CHECK(data.size() == 0);
CHECK(data2.size() == initial_data.size());
CHECK(data2 != data);
}
//*************************************************************************
TEST_FIXTURE(SetupFixture, test_assignment)
{
@ -178,6 +188,19 @@ namespace
CHECK(is_equal);
}
//*************************************************************************
TEST_FIXTURE(SetupFixture, test_move_assignment)
{
Data data(initial_data.begin(), initial_data.end());
Data other_data;
other_data = std::move(data);
CHECK(data.size() == 0);
CHECK(other_data.size() == initial_data.size());
CHECK(data != other_data);
}
//*************************************************************************
TEST_FIXTURE(SetupFixture, test_assignment_iterface)
{

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -758,8 +758,10 @@
<ClCompile Include="..\test_variant.cpp" />
<ClCompile Include="..\test_variant_pool.cpp" />
<ClCompile Include="..\test_vector.cpp" />
<ClCompile Include="..\test_vector_external_buffer.cpp" />
<ClCompile Include="..\test_vector_non_trivial.cpp" />
<ClCompile Include="..\test_vector_pointer.cpp" />
<ClCompile Include="..\test_vector_pointer_external_buffer.cpp" />
<ClCompile Include="..\test_visitor.cpp" />
<ClCompile Include="..\test_xor_checksum.cpp" />
<ClCompile Include="..\test_xor_rotate_checksum.cpp" />

View File

@ -1163,6 +1163,12 @@
<ClCompile Include="..\test_queue_spsc_locked_small.cpp">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="..\test_vector_external_buffer.cpp">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="..\test_vector_pointer_external_buffer.cpp">
<Filter>Source Files</Filter>
</ClCompile>
</ItemGroup>
<ItemGroup>
<None Include="..\..\library.properties">