diff --git a/include/etl/indirect_vector.h b/include/etl/indirect_vector.h index 2fcac9ba..217e6380 100644 --- a/include/etl/indirect_vector.h +++ b/include/etl/indirect_vector.h @@ -724,7 +724,7 @@ namespace etl ///\param last The iterator to the last element + 1. //********************************************************************* template - void assign(TIterator first, TIterator last) + typename etl::enable_if::value, void>::type assign(TIterator first, TIterator last) { ETL_STATIC_ASSERT((etl::is_same::type, typename etl::remove_cv< typename etl::iterator_traits< TIterator>::value_type>::type>::value), @@ -1071,7 +1071,7 @@ namespace etl ///\param last The last + 1 element to add. //********************************************************************* template - iterator insert(const_iterator position, TIterator first, TIterator last) + typename etl::enable_if::value, iterator>::type insert(const_iterator position, TIterator first, TIterator last) { size_t count = size_t(etl::distance(first, last)); @@ -1462,7 +1462,7 @@ namespace etl ///\param last The iterator to the last element + 1. //************************************************************************* template - indirect_vector(TIterator first, TIterator last) + indirect_vector(TIterator first, TIterator last, typename etl::enable_if::value, int>::type = 0) : etl::iindirect_vector(lookup_vector, storage_pool) { this->assign(first, last); @@ -1613,7 +1613,8 @@ namespace etl ///\param last The iterator to the last element + 1. //************************************************************************* template - indirect_vector_ext(TIterator first, TIterator last, etl::ivector& lookup_, etl::ipool& pool_) + indirect_vector_ext(TIterator first, TIterator last, etl::ivector& lookup_, etl::ipool& pool_, + typename etl::enable_if::value, int>::type = 0) : etl::iindirect_vector(lookup_, pool_) { ETL_ASSERT(lookup_.capacity() <= pool_.capacity(), ETL_ERROR(indirect_vector_buffer_missmatch)); diff --git a/test/test_indirect_vector.cpp b/test/test_indirect_vector.cpp index f9973441..75dc1293 100644 --- a/test/test_indirect_vector.cpp +++ b/test/test_indirect_vector.cpp @@ -1201,6 +1201,42 @@ namespace CHECK_THROW(data.insert(data.begin() + static_cast(offset), INSERT_SIZE, INITIAL_VALUE), etl::vector_full); } + //************************************************************************* + TEST(test_constructor_two_parameter_same_type_not_iterator) + { + std::vector compare_data(5, 7); + etl::indirect_vector data(5, 7); + + CHECK_EQUAL(compare_data.size(), data.size()); + CHECK(std::equal(data.begin(), data.end(), compare_data.begin())); + } + + //************************************************************************* + TEST(test_assign_two_parameter_same_type_not_iterator) + { + std::vector compare_data; + etl::indirect_vector data; + + compare_data.assign(5, 7); + data.assign(5, 7); + + CHECK_EQUAL(compare_data.size(), data.size()); + CHECK(std::equal(data.begin(), data.end(), compare_data.begin())); + } + + //************************************************************************* + TEST(test_insert_three_parameter_same_type_not_iterator) + { + std::vector compare_data(3UL, 1); + etl::indirect_vector data(3UL, 1); + + compare_data.insert(compare_data.begin(), 2, 7); + data.insert(data.begin(), 2, 7); + + CHECK_EQUAL(compare_data.size(), data.size()); + CHECK(std::equal(data.begin(), data.end(), compare_data.begin())); + } + //************************************************************************* TEST_FIXTURE(SetupFixture, test_insert_position_range) { diff --git a/test/test_indirect_vector_external_buffer.cpp b/test/test_indirect_vector_external_buffer.cpp index a699834a..0223f7ee 100644 --- a/test/test_indirect_vector_external_buffer.cpp +++ b/test/test_indirect_vector_external_buffer.cpp @@ -335,6 +335,22 @@ namespace CHECK_EQUAL(4U, *data2[3]); } + //************************************************************************* + TEST(test_constructor_two_parameter_same_type_not_iterator) + { + LookupInt lookup; + PoolInt pool; + + etl::indirect_vector_ext data(5, 7, lookup, pool); + + CHECK_EQUAL(5U, data.size()); + CHECK_EQUAL(7, data[0]); + CHECK_EQUAL(7, data[1]); + CHECK_EQUAL(7, data[2]); + CHECK_EQUAL(7, data[3]); + CHECK_EQUAL(7, data[4]); + } + //************************************************************************* TEST_FIXTURE(SetupFixture, test_assignment) { diff --git a/zephyr/CMakeLists.txt b/zephyr/CMakeLists.txt index 60e5c2fb..4c360584 100644 --- a/zephyr/CMakeLists.txt +++ b/zephyr/CMakeLists.txt @@ -3,6 +3,16 @@ if(CONFIG_ETL) zephyr_link_libraries(etl::etl) zephyr_compile_definitions_ifdef(CONFIG_ETL_DEBUG ETL_DEBUG) - zephyr_compile_definitions_ifdef(CONFIG_ETL_CHECK_PUSH_POP ETL_CHECK_PUSH_POP) + zephyr_compile_definitions_ifdef(CONFIG_ETL_LOG_ERRORS ETL_LOG_ERRORS) + zephyr_compile_definitions_ifdef(CONFIG_ETL_USE_ASSERT_FUNCTION ETL_USE_ASSERT_FUNCTION) + zephyr_compile_definitions_ifdef(CONFIG_ETL_THROW_EXCEPTIONS ETL_THROW_EXCEPTIONS) + zephyr_compile_definitions_ifdef(CONFIG_ETL_NO_CHECKS ETL_NO_CHECKS) + + zephyr_compile_definitions_ifdef(CONFIG_ETL_VERBOSE_ERRORS ETL_VERBOSE_ERRORS) + zephyr_compile_definitions_ifdef(CONFIG_ETL_MINIMAL_ERRORS ETL_MINIMAL_ERRORS) + + zephyr_compile_definitions_ifdef(CONFIG_ETL_CHECK_PUSH_POP ETL_CHECK_PUSH_POP) + zephyr_compile_definitions_ifdef(CONFIG_ETL_CHECK_INDEX_OPERATOR ETL_CHECK_INDEX_OPERATOR) + zephyr_compile_definitions_ifdef(CONFIG_ETL_CHECK_EXTRA ETL_CHECK_EXTRA) endif() diff --git a/zephyr/Kconfig b/zephyr/Kconfig index ad8cd12d..b5ac8b47 100644 --- a/zephyr/Kconfig +++ b/zephyr/Kconfig @@ -8,12 +8,78 @@ if ETL config ETL_DEBUG bool "Build ETL with debugging checks" - default y if DEBUG + default y if ASSERT + +choice ETL_ERROR_MODE + prompt "ETL error handling mode" + help + What ETL does when one of its checks fails. + +config ETL_ASSERT_ERRORS + bool "Assert in ETL_DEBUG builds, otherwise ignore" + help + With ETL_DEBUG, a failed check calls assert(). Without it, nothing + is reported, but checks that guard an operation still skip it. + With ETL_LOG_ERRORS, a failed check calls the error handler instead, + with or without ETL_DEBUG. + +config ETL_USE_ASSERT_FUNCTION + bool "Call a user assert function" + help + A failed check calls the function registered with + etl::set_assert_function(), and checks that guard an operation + still skip it. Until one is registered, it calls assert(false). + +config ETL_THROW_EXCEPTIONS + bool "Throw an exception" + depends on CPP_EXCEPTIONS + help + A failed check throws an etl::exception. + +config ETL_NO_CHECKS + bool "No checks" + help + Check conditions are not evaluated. + +endchoice # ETL_ERROR_MODE + +config ETL_LOG_ERRORS + bool "Call the ETL error handler" + depends on !ETL_USE_ASSERT_FUNCTION && !ETL_NO_CHECKS + help + A failed check calls the callback registered with + etl::error_handler::set_callback(). With ETL_THROW_EXCEPTIONS it + then throws; otherwise, checks that guard an operation still skip + it. With no callback registered, errors are discarded. + +choice ETL_ERROR_DETAIL + prompt "ETL error detail level" + help + What information the etl::exception for a failed check carries, + whether it is thrown or passed to the error handler or assert + function. Unused when a failed check calls plain assert(). + +config ETL_TERSE_ERRORS + bool "Short error code only" + +config ETL_VERBOSE_ERRORS + bool "Message, file and line" + +config ETL_MINIMAL_ERRORS + bool "Nothing" + +endchoice # ETL_ERROR_DETAIL config ETL_CHECK_PUSH_POP bool "Enable push/pop checks in ETL" + depends on !ETL_NO_CHECKS -config ETL_LOG_ERRORS - bool "Call ETL error handler instead of assert" +config ETL_CHECK_INDEX_OPERATOR + bool "Enable bounds checks on ETL operator[]" + depends on !ETL_NO_CHECKS + +config ETL_CHECK_EXTRA + bool "Enable extra bounds and empty checks in ETL containers" + depends on !ETL_NO_CHECKS endif # ETL