From 2e0980420b32fcb2667e291f6b8493e9e68f30f9 Mon Sep 17 00:00:00 2001 From: John Wellbelove Date: Mon, 27 Aug 2018 23:33:45 +0100 Subject: [PATCH 01/12] Merge remote-tracking branch 'origin/development' --- .../ArmTimerCallbacks.uvoptx | 2 + .../ArmTimerCallbacks.uvprojx | 27 +- .../ArmTimerCallbacks - C++/etl_profile.h | 3 +- include/etl/atomic/atomic_gcc_sync.h | 6 +- include/etl/atomic/atomic_llvm_sync.h | 785 ++++++++++++++++++ include/etl/atomic/atomic_std.h | 1 + include/etl/basic_string.h | 2 +- include/etl/callback_timer.h | 3 +- include/etl/cstring.h | 5 +- include/etl/deque.h | 7 +- include/etl/memory.h | 4 +- include/etl/private/pvoidvector.h | 2 +- include/etl/stl/alternate/algorithm.h | 259 ++++-- include/etl/stl/alternate/functional.h | 16 +- include/etl/stl/alternate/iterator.h | 124 ++- include/etl/stl/alternate/limits.h | 12 +- include/etl/stl/alternate/utility.h | 21 +- include/etl/u16string.h | 5 +- include/etl/u32string.h | 5 +- include/etl/vector.h | 9 +- include/etl/version.h | 10 +- include/etl/wstring.h | 5 +- src/private/pvoidvector.cpp | 2 +- support/Release notes.txt | 5 + test/codeblocks/ETL.cbp | 1 + test/no_stl_test_iterators.h | 206 +++++ test/test_no_stl_algorithm.cpp | 191 +++-- test/test_no_stl_iterator.cpp | 96 +++ test/vs2017/etl.vcxproj | 3 + test/vs2017/etl.vcxproj.filters | 9 + 30 files changed, 1581 insertions(+), 245 deletions(-) create mode 100644 include/etl/atomic/atomic_llvm_sync.h create mode 100644 test/no_stl_test_iterators.h create mode 100644 test/test_no_stl_iterator.cpp diff --git a/examples/ArmTimerCallbacks - C++/ArmTimerCallbacks.uvoptx b/examples/ArmTimerCallbacks - C++/ArmTimerCallbacks.uvoptx index 8a5d0503..040f00a1 100644 --- a/examples/ArmTimerCallbacks - C++/ArmTimerCallbacks.uvoptx +++ b/examples/ArmTimerCallbacks - C++/ArmTimerCallbacks.uvoptx @@ -101,6 +101,8 @@ 0 0 1 + 0 + 0 5 diff --git a/examples/ArmTimerCallbacks - C++/ArmTimerCallbacks.uvprojx b/examples/ArmTimerCallbacks - C++/ArmTimerCallbacks.uvprojx index b7fa094b..d92ef376 100644 --- a/examples/ArmTimerCallbacks - C++/ArmTimerCallbacks.uvprojx +++ b/examples/ArmTimerCallbacks - C++/ArmTimerCallbacks.uvprojx @@ -10,13 +10,13 @@ Target 1 0x4 ARM-ADS - 6070000::V6.7::.\ARMCLANG - 1 + 5060750::V5.06 update 6 (build 750)::ARMCC + 0 STM32F401RETx STMicroelectronics - Keil.STM32F4xx_DFP.2.11.0 + Keil.STM32F4xx_DFP.2.13.0 http://www.keil.com/pack IRAM(0x20000000,0x18000) IROM(0x08000000,0x80000) CPUTYPE("Cortex-M4") FPU2 CLOCK(12000000) ELITTLE @@ -311,7 +311,7 @@ 1 - 7 + 1 0 0 1 @@ -320,10 +320,11 @@ 1 0 0 - 3 + 2 0 0 1 + 0 0 3 3 @@ -421,8 +422,8 @@ - - + + @@ -439,8 +440,8 @@ - - + + @@ -449,16 +450,16 @@ RTE\Device\STM32F401RETx\startup_stm32f401xe.s - - + + RTE\Device\STM32F401RETx\system_stm32f4xx.c - - + + diff --git a/examples/ArmTimerCallbacks - C++/etl_profile.h b/examples/ArmTimerCallbacks - C++/etl_profile.h index a2e2f33f..0e874e1e 100644 --- a/examples/ArmTimerCallbacks - C++/etl_profile.h +++ b/examples/ArmTimerCallbacks - C++/etl_profile.h @@ -2,14 +2,13 @@ #ifndef __ETL_PROFILE_H__ #define __ETL_PROFILE_H__ -#define ETL_THROW_EXCEPTIONS #define ETL_VERBOSE_ERRORS #define ETL_CHECK_PUSH_POP #define ETL_ISTRING_REPAIR_ENABLE #define ETL_IVECTOR_REPAIR_ENABLE #define ETL_IDEQUE_REPAIR_ENABLE -#define ETL_IN_UNIT_TEST #define ETL_CALLBACK_TIMER_USE_ATOMIC_LOCK +#define ETL_NO_STL #if (__CC_ARM == 1) // ARM5 compiler diff --git a/include/etl/atomic/atomic_gcc_sync.h b/include/etl/atomic/atomic_gcc_sync.h index 725c44ac..80ce7c2d 100644 --- a/include/etl/atomic/atomic_gcc_sync.h +++ b/include/etl/atomic/atomic_gcc_sync.h @@ -33,12 +33,14 @@ SOFTWARE. #include "../type_traits.h" #include "../static_assert.h" #include "../nullptr.h" +#include "../char_traits.h" -//#include #include +#if defined(ETL_COMPILER_GCC) #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wunused-parameter" +#endif namespace etl { @@ -785,6 +787,8 @@ namespace etl typedef etl::atomic atomic_uintmax_t; } +#if defined(ETL_COMPILER_GCC) #pragma GCC diagnostic pop +#endif #endif diff --git a/include/etl/atomic/atomic_llvm_sync.h b/include/etl/atomic/atomic_llvm_sync.h new file mode 100644 index 00000000..50e0be01 --- /dev/null +++ b/include/etl/atomic/atomic_llvm_sync.h @@ -0,0 +1,785 @@ +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2017 jwellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#ifndef ETL_ATOMIC_LLVM_SYNC_INCLUDED +#define ETL_ATOMIC_LLVM_SYNC_INCLUDED + +//#include "../platform.h" +//#include "../type_traits.h" +//#include "../static_assert.h" +//#include "../nullptr.h" +//#include "../char_traits.h" +// +//#include +// +//namespace etl +//{ +// //*************************************************************************** +// // Atomic type for pre C++11 GCC compilers that support the builtin '__sync' functions. +// // Only integral and pointer types are supported. +// //*************************************************************************** +// +// typedef enum memory_order +// { +// memory_order_relaxed, +// memory_order_consume, +// memory_order_acquire, +// memory_order_release, +// memory_order_acq_rel, +// memory_order_seq_cst +// } memory_order; +// +// template +// class atomic +// { +// public: +// +// ETL_STATIC_ASSERT(etl::is_integral::value, "Only integral types are supported"); +// +// atomic() +// : value(0) +// { +// } +// +// atomic(T v) +// : value(v) +// { +// } +// +// // Assignment +// T operator =(T v) +// { +// store(v); +// +// return v; +// } +// +// T operator =(T v) volatile +// { +// store(v); +// +// return v; +// } +// +// // Pre-increment +// T operator ++() +// { +// return fetch_add(1) + 1; +// } +// +// T operator ++() volatile +// { +// return fetch_add(1) + 1; +// } +// +// // Post-increment +// T operator ++(int) +// { +// return fetch_add(1); +// } +// +// T operator ++(int) volatile +// { +// return fetch_add(1); +// } +// +// // Pre-decrement +// T operator --() +// { +// return fetch_sub(1) + 1; +// } +// +// T operator --() volatile +// { +// return fetch_sub(1) + 1; +// } +// +// // Post-decrement +// T operator --(int) +// { +// return fetch_sub(1); +// } +// +// T operator --(int) volatile +// { +// return fetch_sub(1); +// } +// +// // Add +// T operator +=(T v) +// { +// return fetch_add(v) + v; +// } +// +// T operator +=(T v) volatile +// { +// return fetch_add(v) + v; +// } +// +// // Subtract +// T operator -=(T v) +// { +// return fetch_sub(v) - v; +// } +// +// T operator -=(T v) volatile +// { +// return fetch_sub(v) - v; +// } +// +// // And +// T operator &=(T v) +// { +// return fetch_and(v) & v; +// } +// +// T operator &=(T v) volatile +// { +// return fetch_and(v) & v; +// } +// +// // Or +// T operator |=(T v) +// { +// return fetch_or(v) | v; +// } +// +// T operator |=(T v) volatile +// { +// return fetch_or(v) | v; +// } +// +// // Exclusive or +// T operator ^=(T v) +// { +// return fetch_xor(v) ^ v; +// } +// +// T operator ^=(T v) volatile +// { +// return fetch_xor(v) ^ v; +// } +// +// // Conversion operator +// operator T () const +// { +// return __sync_fetch_and_add(&value, 0); +// } +// +// operator T() volatile const +// { +// return __sync_fetch_and_add(&value, 0); +// } +// +// // Is lock free? +// bool is_lock_free() const +// { +// return true; +// } +// +// bool is_lock_free() const volatile +// { +// return true; +// } +// +// // Store +// void store(T v, etl::memory_order order = etl::memory_order_seq_cst) +// { +// __sync_lock_test_and_set(&value, v); +// } +// +// void store(T v, etl::memory_order order = etl::memory_order_seq_cst) volatile +// { +// __sync_lock_test_and_set(&value, v); +// } +// +// // Load +// T load(etl::memory_order order = etl::memory_order_seq_cst) const +// { +// return __sync_fetch_and_add(&value, 0); +// } +// +// T load(etl::memory_order order = etl::memory_order_seq_cst) const volatile +// { +// return __sync_fetch_and_add(&value, 0); +// } +// +// // Fetch add +// T fetch_add(T v, etl::memory_order order = etl::memory_order_seq_cst) +// { +// return __sync_fetch_and_add(&value, v); +// } +// +// T fetch_add(T v, etl::memory_order order = etl::memory_order_seq_cst) volatile +// { +// return __sync_fetch_and_add(&value, v); +// } +// +// // Fetch subtract +// T fetch_sub(T v, etl::memory_order order = etl::memory_order_seq_cst) +// { +// return __sync_fetch_and_sub(&value, v); +// } +// +// T fetch_sub(T v, etl::memory_order order = etl::memory_order_seq_cst) volatile +// { +// return __sync_fetch_and_sub(&value, v); +// } +// +// // Fetch or +// T fetch_or(T v, etl::memory_order order = etl::memory_order_seq_cst) +// { +// return __sync_fetch_and_or(&value, v); +// } +// +// T fetch_or(T v, etl::memory_order order = etl::memory_order_seq_cst) volatile +// { +// return __sync_fetch_and_or(&value, v); +// } +// +// // Fetch and +// T fetch_and(T v, etl::memory_order order = etl::memory_order_seq_cst) +// { +// return __sync_fetch_and_and(&value, v); +// } +// +// T fetch_and(T v, etl::memory_order order = etl::memory_order_seq_cst) volatile +// { +// return __sync_fetch_and_and(&value, v); +// } +// +// // Fetch exclusive or +// T fetch_xor(T v, etl::memory_order order = etl::memory_order_seq_cst) +// { +// return __sync_fetch_and_xor(&value, v); +// } +// +// T fetch_xor(T v, etl::memory_order order = etl::memory_order_seq_cst) volatile +// { +// return __sync_fetch_and_xor(&value, v); +// } +// +// // Exchange +// T exchange(T v, etl::memory_order order = etl::memory_order_seq_cst) +// { +// return __sync_lock_test_and_set(&value, v); +// } +// +// T exchange(T v, etl::memory_order order = etl::memory_order_seq_cst) volatile +// { +// return __sync_lock_test_and_set(&value, v); +// } +// +// // Compare exchange weak +// bool compare_exchange_weak(T& expected, T desired, etl::memory_order order = etl::memory_order_seq_cst) +// { +// T old = __sync_val_compare_and_swap(&value, expected, desired); +// +// if (old == expected) +// { +// return true; +// } +// else +// { +// expected = old; +// return false; +// } +// } +// +// bool compare_exchange_weak(T& expected, T desired, etl::memory_order order = etl::memory_order_seq_cst) volatile +// { +// T old = __sync_val_compare_and_swap(&value, expected, desired); +// +// if (old == expected) +// { +// return true; +// } +// else +// { +// expected = old; +// return false; +// } +// } +// +// bool compare_exchange_weak(T& expected, T desired, etl::memory_order success, etl::memory_order failure) +// { +// T old = __sync_val_compare_and_swap(&value, expected, desired); +// +// if (old == expected) +// { +// return true; +// } +// else +// { +// expected = old; +// return false; +// } +// } +// +// bool compare_exchange_weak(T& expected, T desired, etl::memory_order success, etl::memory_order failure) volatile +// { +// T old = __sync_val_compare_and_swap(&value, expected, desired); +// +// if (old == expected) +// { +// return true; +// } +// else +// { +// expected = old; +// return false; +// } +// } +// +// // Compare exchange strong +// bool compare_exchange_strong(T& expected, T desired, etl::memory_order order = etl::memory_order_seq_cst) +// { +// T old = expected; +// +// while (!compare_exchange_weak(old, desired)) +// { +// if (memcmp(&old, &expected, sizeof(T))) +// { +// expected = old; +// return false; +// } +// } +// +// return true; +// } +// +// bool compare_exchange_strong(T& expected, T desired, etl::memory_order order = etl::memory_order_seq_cst) volatile +// { +// T old = expected; +// +// while (!compare_exchange_weak(old, desired)) +// { +// if (memcmp(&old, &expected, sizeof(T))) +// { +// expected = old; +// return false; +// } +// } +// +// return true; +// } +// +// bool compare_exchange_strong(T& expected, T desired, etl::memory_order success, etl::memory_order failure) +// { +// T old = expected; +// +// while (!compare_exchange_weak(old, desired)) +// { +// if (memcmp(&old, &expected, sizeof(T))) +// { +// expected = old; +// return false; +// } +// } +// +// return true; +// } +// +// bool compare_exchange_strong(T& expected, T desired, etl::memory_order success, etl::memory_order failure) volatile +// { +// T old = expected; +// +// while (!compare_exchange_weak(old, desired)) +// { +// if (memcmp(&old, &expected, sizeof(T))) +// { +// expected = old; +// return false; +// } +// } +// +// return true; +// } +// +// private: +// +// atomic& operator =(const atomic&); +// atomic& operator =(const atomic&) volatile; +// +// mutable volatile T value; +// }; +// +// template +// class atomic +// { +// public: +// +// atomic() +// : value(nullptr) +// { +// } +// +// atomic(T* v) +// : value(v) +// { +// } +// +// // Assignment +// T* operator =(T* v) +// { +// store(v); +// +// return v; +// } +// +// T* operator =(T* v) volatile +// { +// store(v); +// +// return v; +// } +// +// // Pre-increment +// T* operator ++() +// { +// return fetch_add(1) + 1; +// } +// +// T* operator ++() volatile +// { +// return fetch_add(1) + 1; +// } +// +// // Post-increment +// T* operator ++(int) +// { +// return fetch_add(1); +// } +// +// T* operator ++(int) volatile +// { +// return fetch_add(1); +// } +// +// // Pre-decrement +// T* operator --() +// { +// return fetch_sub(1) + 1; +// } +// +// T* operator --() volatile +// { +// return fetch_sub(1) + 1; +// } +// +// // Post-decrement +// T* operator --(int) +// { +// return fetch_sub(1); +// } +// +// T* operator --(int) volatile +// { +// return fetch_sub(1); +// } +// +// // Add +// T* operator +=(ptrdiff_t v) +// { +// return fetch_add(v) + v; +// } +// +// T* operator +=(ptrdiff_t v) volatile +// { +// return fetch_add(v) + v; +// } +// +// // Subtract +// T* operator -=(ptrdiff_t v) +// { +// return fetch_sub(v) - v; +// } +// +// T* operator -=(ptrdiff_t v) volatile +// { +// return fetch_sub(v) - v; +// } +// +// // Conversion operator +// operator T* () const +// { +// return __sync_fetch_and_add(&value, 0); +// } +// +// operator T*() volatile const +// { +// return __sync_fetch_and_add(&value, 0); +// } +// +// // Is lock free? +// bool is_lock_free() const +// { +// return true; +// } +// +// bool is_lock_free() const volatile +// { +// return true; +// } +// +// // Store +// void store(T* v, etl::memory_order order = etl::memory_order_seq_cst) +// { +// __sync_lock_test_and_set(&value, v); +// } +// +// void store(T* v, etl::memory_order order = etl::memory_order_seq_cst) volatile +// { +// __sync_lock_test_and_set(&value, v); +// } +// +// // Load +// T* load(etl::memory_order order = etl::memory_order_seq_cst) const +// { +// return __sync_fetch_and_add(&value, 0); +// } +// +// T* load(etl::memory_order order = etl::memory_order_seq_cst) const volatile +// { +// return __sync_fetch_and_add(&value, 0); +// } +// +// // Fetch add +// T* fetch_add(ptrdiff_t v, etl::memory_order order = etl::memory_order_seq_cst) +// { +// return __sync_fetch_and_add(&value, v); +// } +// +// T* fetch_add(ptrdiff_t v, etl::memory_order order = etl::memory_order_seq_cst) volatile +// { +// return __sync_fetch_and_add(&value, v); +// } +// +// // Fetch subtract +// T* fetch_sub(ptrdiff_t v, etl::memory_order order = etl::memory_order_seq_cst) +// { +// return __sync_fetch_and_sub(&value, v); +// } +// +// T* fetch_sub(ptrdiff_t v, etl::memory_order order = etl::memory_order_seq_cst) volatile +// { +// return __sync_fetch_and_sub(&value, v); +// } +// +// // Exchange +// T* exchange(T* v, etl::memory_order order = etl::memory_order_seq_cst) +// { +// return __sync_lock_test_and_set(&value, v); +// } +// +// T* exchange(T* v, etl::memory_order order = etl::memory_order_seq_cst) volatile +// { +// return __sync_lock_test_and_set(&value, v); +// } +// +// // Compare exchange weak +// bool compare_exchange_weak(T*& expected, T* desired, etl::memory_order order = etl::memory_order_seq_cst) +// { +// T* old = __sync_val_compare_and_swap(&value, expected, desired); +// +// if (old == expected) +// { +// return true; +// } +// else +// { +// expected = old; +// return false; +// } +// } +// +// bool compare_exchange_weak(T*& expected, T* desired, etl::memory_order order = etl::memory_order_seq_cst) volatile +// { +// T* old = __sync_val_compare_and_swap(&value, expected, desired); +// +// if (old == expected) +// { +// return true; +// } +// else +// { +// expected = old; +// return false; +// } +// } +// +// bool compare_exchange_weak(T*& expected, T* desired, etl::memory_order success, etl::memory_order failure) +// { +// T* old = __sync_val_compare_and_swap(&value, expected, desired); +// +// if (old == expected) +// { +// return true; +// } +// else +// { +// expected = old; +// return false; +// } +// } +// +// bool compare_exchange_weak(T*& expected, T* desired, etl::memory_order success, etl::memory_order failure) volatile +// { +// T* old = __sync_val_compare_and_swap(&value, expected, desired); +// +// if (old == expected) +// { +// return true; +// } +// else +// { +// expected = old; +// return false; +// } +// } +// +// // Compare exchange strong +// bool compare_exchange_strong(T*& expected, T* desired, etl::memory_order order = etl::memory_order_seq_cst) +// { +// T* old = expected; +// +// while (!compare_exchange_weak(old, desired)) +// { +// if (memcmp(&old, &expected, sizeof(T*))) +// { +// expected = old; +// return false; +// } +// } +// +// return true; +// } +// +// bool compare_exchange_strong(T*& expected, T* desired, etl::memory_order order = etl::memory_order_seq_cst) volatile +// { +// T* old = expected; +// +// while (!compare_exchange_weak(old, desired)) +// { +// if (memcmp(&old, &expected, sizeof(T*))) +// { +// expected = old; +// return false; +// } +// } +// +// return true; +// } +// +// bool compare_exchange_strong(T*& expected, T* desired, etl::memory_order success, etl::memory_order failure) +// { +// T* old = expected; +// +// while (!compare_exchange_weak(old, desired)) +// { +// if (memcmp(&old, &expected, sizeof(T*))) +// { +// expected = old; +// return false; +// } +// } +// +// return true; +// } +// +// bool compare_exchange_strong(T*& expected, T* desired, etl::memory_order success, etl::memory_order failure) volatile +// { +// T* old = expected; +// +// while (!compare_exchange_weak(old, desired)) +// { +// if (memcmp(&old, &expected, sizeof(T*))) +// { +// expected = old; +// return false; +// } +// } +// +// return true; +// } +// +// private: +// +// atomic& operator =(const atomic&); +// atomic& operator =(const atomic&) volatile; +// +// mutable volatile T* value; +// }; +// +// typedef etl::atomic atomic_char; +// typedef etl::atomic atomic_schar; +// typedef etl::atomic atomic_uchar; +// typedef etl::atomic atomic_short; +// typedef etl::atomic atomic_ushort; +// typedef etl::atomic atomic_int; +// typedef etl::atomic atomic_uint; +// typedef etl::atomic atomic_long; +// typedef etl::atomic atomic_ulong; +// typedef etl::atomic atomic_llong; +// typedef etl::atomic atomic_ullong; +// typedef etl::atomic atomic_wchar_t; +// typedef etl::atomic atomic_char16_t; +// typedef etl::atomic atomic_char32_t; +// typedef etl::atomic atomic_uint8_t; +// typedef etl::atomic atomic_int8_t; +// typedef etl::atomic atomic_uint16_t; +// typedef etl::atomic atomic_int16_t; +// typedef etl::atomic atomic_uint32_t; +// typedef etl::atomic atomic_int32_t; +// typedef etl::atomic atomic_uint64_t; +// typedef etl::atomic atomic_int64_t; +// typedef etl::atomic atomic_int_least8_t; +// typedef etl::atomic atomic_uint_least8_t; +// typedef etl::atomic atomic_int_least16_t; +// typedef etl::atomic atomic_uint_least16_t; +// typedef etl::atomic atomic_int_least32_t; +// typedef etl::atomic atomic_uint_least32_t; +// typedef etl::atomic atomic_int_least64_t; +// typedef etl::atomic atomic_uint_least64_t; +// typedef etl::atomic atomic_int_fast8_t; +// typedef etl::atomic atomic_uint_fast8_t; +// typedef etl::atomic atomic_int_fast16_t; +// typedef etl::atomic atomic_uint_fast16_t; +// typedef etl::atomic atomic_int_fast32_t; +// typedef etl::atomic atomic_uint_fast32_t; +// typedef etl::atomic atomic_int_fast64_t; +// typedef etl::atomic atomic_uint_fast64_t; +// typedef etl::atomic atomic_intptr_t; +// typedef etl::atomic atomic_uintptr_t; +// typedef etl::atomic atomic_size_t; +// typedef etl::atomic atomic_ptrdiff_t; +// typedef etl::atomic atomic_intmax_t; +// typedef etl::atomic atomic_uintmax_t; +//} + +#endif diff --git a/include/etl/atomic/atomic_std.h b/include/etl/atomic/atomic_std.h index eb3cd146..e2e7fea9 100644 --- a/include/etl/atomic/atomic_std.h +++ b/include/etl/atomic/atomic_std.h @@ -31,6 +31,7 @@ SOFTWARE. #include "../platform.h" #include "../nullptr.h" +#include "../char_traits.h" #include #include diff --git a/include/etl/basic_string.h b/include/etl/basic_string.h index b87f989b..b823293d 100644 --- a/include/etl/basic_string.h +++ b/include/etl/basic_string.h @@ -1922,7 +1922,7 @@ namespace etl //************************************************************************* /// Fix the internal pointers after a low level memory copy. //************************************************************************* - void repair(T* p_buffer_) + void repair_buffer(T* p_buffer_) { p_buffer = p_buffer_; } diff --git a/include/etl/callback_timer.h b/include/etl/callback_timer.h index a57f9d5d..0d1ff258 100644 --- a/include/etl/callback_timer.h +++ b/include/etl/callback_timer.h @@ -30,9 +30,10 @@ SOFTWARE. #define ETL_CALLBACK_TIMER_INCLUDED #include -#include "algorithm.h" +#include #include "platform.h" +#include "algorithm.h" #include "nullptr.h" #include "function.h" #include "static_assert.h" diff --git a/include/etl/cstring.h b/include/etl/cstring.h index 87ab5d5a..01ff2d12 100644 --- a/include/etl/cstring.h +++ b/include/etl/cstring.h @@ -189,9 +189,12 @@ namespace etl //************************************************************************* /// Fix the internal pointers after a low level memory copy. //************************************************************************* +#ifdef ETL_ISTRING_REPAIR_ENABLE + virtual +#endif void repair() { - etl::istring::repair(buffer); + etl::istring::repair_buffer(buffer); } private: diff --git a/include/etl/deque.h b/include/etl/deque.h index 98e2feef..bdcd4b85 100644 --- a/include/etl/deque.h +++ b/include/etl/deque.h @@ -1828,7 +1828,7 @@ namespace etl //************************************************************************* /// Fix the internal pointers after a low level memory copy. //************************************************************************* - void repair(pointer p_buffer_) + void repair_buffer(pointer p_buffer_) { p_buffer = p_buffer_; @@ -2095,13 +2095,16 @@ namespace etl //************************************************************************* /// Fix the internal pointers after a low level memory copy. //************************************************************************* +#ifdef ETL_IDEQUE_REPAIR_ENABLE + virtual +#endif void repair() { #if ETL_CPP11_TYPE_TRAITS_IS_TRIVIAL_SUPPORTED ETL_ASSERT(std::is_trivially_copyable::value, ETL_ERROR(etl::deque_incompatible_type)); #endif - etl::ideque::repair(reinterpret_cast(&buffer[0])); + etl::ideque::repair_buffer(reinterpret_cast(&buffer[0])); } private: diff --git a/include/etl/memory.h b/include/etl/memory.h index de82cc95..fca5ff44 100644 --- a/include/etl/memory.h +++ b/include/etl/memory.h @@ -872,7 +872,7 @@ namespace etl std::swap(p, value.p); } - ETL_CONSTEXPR explicit operator bool() const + ETL_CONSTEXPR operator bool() const { return (p != nullptr); } @@ -1006,7 +1006,7 @@ namespace etl std::swap(p, v.p); } - ETL_CONSTEXPR explicit operator bool() const + ETL_CONSTEXPR operator bool() const { return (p != nullptr); } diff --git a/include/etl/private/pvoidvector.h b/include/etl/private/pvoidvector.h index 07692a61..f3ec0716 100644 --- a/include/etl/private/pvoidvector.h +++ b/include/etl/private/pvoidvector.h @@ -184,7 +184,7 @@ namespace etl void initialise(); - void repair(void** p_buffer_); + void repair_buffer(void** p_buffer_); void** p_buffer; void** p_end; diff --git a/include/etl/stl/alternate/algorithm.h b/include/etl/stl/alternate/algorithm.h index 74291034..f234b132 100644 --- a/include/etl/stl/alternate/algorithm.h +++ b/include/etl/stl/alternate/algorithm.h @@ -39,70 +39,30 @@ SOFTWARE. #include "iterator.h" #include "functional.h" +#include "utility.h" #if defined(ETL_IN_UNIT_TEST) -#define ETLSTD etlstd -namespace etlstd + #if !defined(ETLSTD) + #define ETLSTD etlstd + #endif + namespace etlstd #else -#define ETLSTD std -namespace std + #if !defined(ETLSTD) + #define ETLSTD std + #endif + namespace std #endif { - //*************************************************************************** - // distance - template - typename etl::enable_if::iterator_category, std::random_access_iterator_tag>::value, - typename std::iterator_traits::difference_type>::type - distance(TIterator first, TIterator last) - { - typename std::iterator_traits::difference_type count = 0; - - while (first != last) - { - ++count; - ++first; - } - - return count; - } - - template - typename etl::enable_if::iterator_category, std::random_access_iterator_tag>::value, - typename std::iterator_traits::difference_type>::type - distance(TIterator first, TIterator last) - { - return last - first; - } - - //*************************************************************************** - // advance - template - typename etl::enable_if::iterator_tag, std::random_access_iterator_tag>::value, void>::type - advance(TIterator itr, TDistance distance) - { - while (distance-- != 0) - { - ++itr; - } - } - - template - typename etl::enable_if::iterator_tag, std::random_access_iterator_tag>::value, void>::type - advance(TIterator itr, TDistance distance) - { - return itr += distance; - } - //*************************************************************************** // copy // Pointer template typename etl::enable_if::value && etl::is_pointer::value && - etl::is_pod::value_type>::value, TIterator2>::type + etl::is_pod::value_type>::value, TIterator2>::type copy(TIterator1 sb, TIterator1 se, TIterator2 db) { - typedef typename std::iterator_traits::value_type value_t; + typedef typename ETLSTD::iterator_traits::value_type value_t; return TIterator2(memcpy(db, sb, sizeof(value_t) * (se - sb))); } @@ -111,7 +71,7 @@ namespace std template typename etl::enable_if::value || !etl::is_pointer::value || - !etl::is_pod::value_type>::value, TIterator2>::type + !etl::is_pod::value_type>::value, TIterator2>::type copy(TIterator1 sb, TIterator1 se, TIterator2 db) { while (sb != se) @@ -128,10 +88,10 @@ namespace std template typename etl::enable_if::value && etl::is_pointer::value && - etl::is_pod::value_type>::value, TIterator2>::type + etl::is_pod::value_type>::value, TIterator2>::type copy_n(TIterator1 sb, TSize count, TIterator2 db) { - typedef typename std::iterator_traits::value_type value_t; + typedef typename ETLSTD::iterator_traits::value_type value_t; return TIterator2(memcpy(db, sb, sizeof(value_t) * count)); } @@ -140,7 +100,7 @@ namespace std template typename etl::enable_if::value || !etl::is_pointer::value || - !etl::is_pod::value_type>::value, TIterator2>::type + !etl::is_pod::value_type>::value, TIterator2>::type copy_n(TIterator1 sb, TSize count, TIterator2 db) { while (count != 0) @@ -158,10 +118,10 @@ namespace std template typename etl::enable_if::value && etl::is_pointer::value && - etl::is_pod::value_type>::value, TIterator2>::type + etl::is_pod::value_type>::value, TIterator2>::type copy_backward(TIterator1 sb, TIterator1 se, TIterator2 de) { - typedef typename std::iterator_traits::value_type value_t; + typedef typename ETLSTD::iterator_traits::value_type value_t; const size_t length = (se - sb); @@ -172,7 +132,7 @@ namespace std template typename etl::enable_if::value || !etl::is_pointer::value || - !etl::is_pod::value_type>::value, TIterator2>::type + !etl::is_pod::value_type>::value, TIterator2>::type copy_backward(TIterator1 sb, TIterator1 se, TIterator2 de) { while (se != sb) @@ -188,16 +148,16 @@ namespace std template TIterator lower_bound(TIterator first, TIterator last, const TValue& value, TCompare compare) { - typedef typename std::iterator_traits::difference_type difference_t; + typedef typename ETLSTD::iterator_traits::difference_type difference_t; - difference_t count = std::distance(first, last); + difference_t count = ETLSTD::distance(first, last); while (count > 0) { TIterator itr = first; difference_t step = count / 2; - std::advance(itr, step); + ETLSTD::advance(itr, step); if (compare(*itr, value)) { @@ -216,7 +176,7 @@ namespace std template TIterator lower_bound(TIterator first, TIterator last, const TValue& value) { - typedef std::less::value_type> compare; + typedef ETLSTD::less::value_type> compare; return ETLSTD::lower_bound(first, last, value, compare()); } @@ -226,16 +186,16 @@ namespace std template TIterator upper_bound(TIterator first, TIterator last, const TValue& value, TCompare compare) { - typedef typename std::iterator_traits::difference_type difference_t; + typedef typename ETLSTD::iterator_traits::difference_type difference_t; - difference_t count = std::distance(first, last); + difference_t count = ETLSTD::distance(first, last); while (count > 0) { TIterator itr = first; difference_t step = count / 2; - std::advance(itr, step); + ETLSTD::advance(itr, step); if (!compare(value, *itr)) { @@ -254,7 +214,7 @@ namespace std template TIterator upper_bound(TIterator first, TIterator last, const TValue& value) { - typedef std::less::value_type> compare; + typedef ETLSTD::less::value_type> compare; return ETLSTD::upper_bound(first, last, value, compare()); } @@ -262,19 +222,55 @@ namespace std //*************************************************************************** // equal_range template - std::pair equal_range(TIterator first, TIterator last, const TValue& value, TCompare compare) + ETLSTD::pair equal_range(TIterator first, TIterator last, const TValue& value, TCompare compare) { - return std::make_pair(ETLSTD::lower_bound(first, last, value, compare), + return ETLSTD::make_pair(ETLSTD::lower_bound(first, last, value, compare), ETLSTD::upper_bound(first, last, value, compare)); } template - std::pair equal_range(TIterator first, TIterator last, const TValue& value) + ETLSTD::pair equal_range(TIterator first, TIterator last, const TValue& value) { - typedef std::less::value_type> compare; + typedef ETLSTD::less::value_type> compare; - return std::make_pair(ETLSTD::lower_bound(first, last, value, compare()), - ETLSTD::upper_bound(first, last, value, compare())); + return ETLSTD::make_pair(ETLSTD::lower_bound(first, last, value, compare()), + ETLSTD::upper_bound(first, last, value, compare())); + } + + //*************************************************************************** + // find_if + template + TIterator find_if(TIterator first, TIterator last, TUnaryPredicate predicate) + { + while (first != last) + { + if (predicate(*first)) + { + return first; + } + + ++first; + } + + return last; + } + + //*************************************************************************** + // find + template + TIterator find(TIterator first, TIterator last, const T& value) + { + while (first != last) + { + if (*first == value) + { + return first; + } + + ++first; + } + + return last; } //*************************************************************************** @@ -296,6 +292,67 @@ namespace std memset(first, value, last - first); } + //*************************************************************************** + // fill_n + template + typename etl::enable_if::value || etl::is_same::value) || !etl::is_pointer::value, TIterator>::type + fill_n(TIterator first, TSize count, const TValue& value) + { + for (TSize i = 0; i < count; ++i) + { + *first++ = value; + } + + return first; + } + + template + typename etl::enable_if<(etl::is_same::value || etl::is_same::value) && etl::is_pointer::value, void>::type + fill_n(TIterator first, TSize count, const TValue& value) + { + memset(first, value, count); + } + + //*************************************************************************** + // count + template + typename iterator_traits::difference_type count(TIterator first, TIterator last, const T& value) + { + typename iterator_traits::difference_type n = 0; + + while (first != last) + { + if (*first == value) + { + ++n; + } + + ++first; + } + + return n; + } + + //*************************************************************************** + // count + template + typename iterator_traits::difference_type count_if(TIterator first, TIterator last, TUnaryPredicate predicate) + { + typename iterator_traits::difference_type n = 0; + + while (first != last) + { + if (predicate(*first)) + { + ++n; + } + + ++first; + } + + return n; + } + //*************************************************************************** // swap template @@ -311,7 +368,7 @@ namespace std template void iter_swap(TIterator1 a, TIterator2 b) { - typename std::iterator_traits::value_type c = *a; + typename ETLSTD::iterator_traits::value_type c = *a; *a = *b; *b = c; } @@ -319,7 +376,7 @@ namespace std //*************************************************************************** // equal template - typename etl::enable_if::value || !etl::is_pointer::value || !etl::is_pod::value_type>::value, bool>::type + typename etl::enable_if::value || !etl::is_pointer::value || !etl::is_pod::value_type>::value, bool>::type equal(TIterator1 first1, TIterator1 last1, TIterator2 first2) { while (first1 != last1) @@ -334,10 +391,10 @@ namespace std } template - typename etl::enable_if::value && etl::is_pointer::value && etl::is_pod::value_type>::value, bool>::type + typename etl::enable_if::value && etl::is_pointer::value && etl::is_pod::value_type>::value, bool>::type equal(TIterator1 first1, TIterator1 last1, TIterator2 first2) { - typedef typename std::iterator_traits::value_type value_t; + typedef typename ETLSTD::iterator_traits::value_type value_t; return (memcmp(first1, first2, sizeof(value_t) * (last1 - last1)) == 0); } @@ -374,7 +431,7 @@ namespace std bool lexicographical_compare(TIterator1 first1, TIterator1 last1, TIterator2 first2, TIterator2 last2) { - typedef std::less::value_type> compare; + typedef ETLSTD::less::value_type> compare; return ETLSTD::lexicographical_compare(first1, last1, first2, last2, compare()); } @@ -390,7 +447,7 @@ namespace std template const T& min(const T& a, const T& b) { - typedef std::less compare; + typedef ETLSTD::less compare; return ETLSTD::min(a, b, compare()); } @@ -406,11 +463,35 @@ namespace std template const T& max(const T& a, const T& b) { - typedef std::less compare; + typedef ETLSTD::less compare; return ETLSTD::max(a, b, compare()); } + //*************************************************************************** + // transform + template + TIteratorOut transform(TIteratorIn first1, TIteratorIn last1, TIteratorOut d_first, TUnaryOperation unary_operation) + { + while (first1 != last1) + { + *d_first++ = unary_operation(*first1++); + } + + return d_first; + } + + template + TIteratorOut transform(TIteratorIn1 first1, TIteratorIn1 last1, TIteratorIn2 first2, TIteratorOut d_first, TBinaryOperation binary_operation) + { + while (first1 != last1) + { + *d_first++ = binary_operation(*first1++, *first2++); + } + + return d_first; + } + //*************************************************************************** // Heap namespace private_heap @@ -486,8 +567,8 @@ namespace std template void pop_heap(TIterator first, TIterator last, TCompare compare) { - typedef typename std::iterator_traits::value_type value_t; - typedef typename std::iterator_traits::difference_type distance_t; + typedef typename ETLSTD::iterator_traits::value_type value_t; + typedef typename ETLSTD::iterator_traits::difference_type distance_t; value_t value = last[-1]; last[-1] = first[0]; @@ -499,7 +580,7 @@ namespace std template void pop_heap(TIterator first, TIterator last) { - typedef std::less::value_type> compare; + typedef ETLSTD::less::value_type> compare; ETLSTD::pop_heap(first, last, compare()); } @@ -508,8 +589,8 @@ namespace std template void push_heap(TIterator first, TIterator last, TCompare compare) { - typedef typename std::iterator_traits::difference_type difference_t; - typedef typename std::iterator_traits::value_type value_t; + typedef typename ETLSTD::iterator_traits::difference_type difference_t; + typedef typename ETLSTD::iterator_traits::value_type value_t; private_heap::push_heap(first, difference_t(last - first - 1), difference_t(0), value_t(*(last - 1)), compare); } @@ -518,7 +599,7 @@ namespace std template void push_heap(TIterator first, TIterator last) { - typedef std::less::value_type> compare; + typedef ETLSTD::less::value_type> compare; ETLSTD::push_heap(first, last, compare()); } @@ -527,7 +608,7 @@ namespace std template void make_heap(TIterator first, TIterator last, TCompare compare) { - typedef typename std::iterator_traits::difference_type difference_t; + typedef typename ETLSTD::iterator_traits::difference_type difference_t; if ((last - first) < 2) { @@ -554,7 +635,7 @@ namespace std template void make_heap(TIterator first, TIterator last) { - typedef std::less::value_type> compare; + typedef ETLSTD::less::value_type> compare; ETLSTD::make_heap(first, last, compare()); } @@ -563,7 +644,7 @@ namespace std template bool is_heap(TIterator first, TIterator last) { - typedef std::less::value_type> compare; + typedef ETLSTD::less::value_type> compare; return private_heap::is_heap(first, last - first, compare()); } @@ -615,7 +696,7 @@ namespace std template TIterator1 search(TIterator1 first, TIterator1 last, TIterator2 search_first, TIterator2 search_last) { - typedef std::equal_to::value_type> compare; + typedef ETLSTD::equal_to::value_type> compare; return ETLSTD::search(first, last, search_first, search_last, compare()); } diff --git a/include/etl/stl/alternate/functional.h b/include/etl/stl/alternate/functional.h index 5ba390a3..58adcdbf 100644 --- a/include/etl/stl/alternate/functional.h +++ b/include/etl/stl/alternate/functional.h @@ -5,9 +5,15 @@ #include "../../platform.h" #if defined(ETL_IN_UNIT_TEST) -namespace etlstd + #if !defined(ETLSTD) + #define ETLSTD etlstd + #endif + namespace etlstd #else -namespace std + #if !defined(ETLSTD) + #define ETLSTD std + #endif + namespace std #endif { //*************************************************************************** @@ -72,7 +78,7 @@ namespace std //*************************************************************************** template - class binder1st : public etlstd::unary_function + class binder1st : public ETLSTD::unary_function { protected: @@ -106,7 +112,7 @@ namespace std //*************************************************************************** template - class binder2nd : public etlstd::unary_function + class binder2nd : public ETLSTD::unary_function { protected: TFunction operation; @@ -135,4 +141,4 @@ namespace std } } -#endif \ No newline at end of file +#endif diff --git a/include/etl/stl/alternate/iterator.h b/include/etl/stl/alternate/iterator.h index 45ea129a..59c8c715 100644 --- a/include/etl/stl/alternate/iterator.h +++ b/include/etl/stl/alternate/iterator.h @@ -38,8 +38,14 @@ SOFTWARE. #include "../../type_traits.h" #if defined(ETL_IN_UNIT_TEST) + #if !defined(ETLSTD) + #define ETLSTD etlstd + #endif namespace etlstd #else + #if !defined(ETLSTD) + #define ETLSTD std + #endif namespace std #endif { @@ -82,7 +88,7 @@ namespace std typedef T value_type; typedef T* pointer; typedef T& reference; - typedef random_access_iterator_tag iterator_category ; + typedef random_access_iterator_tag iterator_category; }; template @@ -92,14 +98,19 @@ namespace std typedef T value_type; typedef T* pointer; typedef T& reference; - typedef random_access_iterator_tag iterator_category ; + typedef random_access_iterator_tag iterator_category; }; //*************************************************************************** // advance template - typename etl::enable_if::iterator_catagory, input_iterator_tag>::value, void>::type - advance(TIterator& itr, TDistance n) + void advance(TIterator& itr, TDistance n) + { + advance_helper(itr, n, typename ETLSTD::iterator_traits::iterator_category()); + } + + template + void advance_helper(TIterator& itr, TDistance n, ETLSTD::input_iterator_tag) { while (n--) { @@ -108,8 +119,7 @@ namespace std } template - typename etl::enable_if::iterator_catagory, output_iterator_tag>::value, void>::type - advance(TIterator& itr, TDistance n) + void advance_helper(TIterator& itr, TDistance n, ETLSTD::output_iterator_tag) { while (n--) { @@ -118,8 +128,7 @@ namespace std } template - typename etl::enable_if::iterator_catagory, forward_iterator_tag>::value, void>::type - advance(TIterator& itr, TDistance n) + void advance_helper(TIterator& itr, TDistance n, ETLSTD::forward_iterator_tag) { while (n--) { @@ -128,8 +137,7 @@ namespace std } template - typename etl::enable_if::iterator_catagory, bidirectional_iterator_tag>::value, void>::type - advance(TIterator& itr, TDistance n) + void advance_helper(TIterator& itr, TDistance n, ETLSTD::bidirectional_iterator_tag) { if (n > 0) { @@ -140,7 +148,7 @@ namespace std } else { - while (n--) + while (n++) { --itr; } @@ -148,8 +156,7 @@ namespace std } template - typename etl::enable_if::iterator_catagory, random_access_iterator_tag>::value, void>::type - advance(TIterator& itr, TDistance n) + void advance_helper(TIterator& itr, TDistance n, ETLSTD::random_access_iterator_tag) { itr += n; } @@ -157,24 +164,55 @@ namespace std //*************************************************************************** // distance template - typename etl::enable_if::iterator_catagory, random_access_iterator_tag>::value, - typename iterator_traits::difference_type>::type - distance(TIterator first, TIterator last) + typename ETLSTD::iterator_traits::difference_type distance(TIterator first, TIterator last) { - typename iterator_traits::difference_type d = 0; + return distance_helper(first, last, typename ETLSTD::iterator_traits::iterator_category()); + } + + template + typename ETLSTD::iterator_traits::difference_type distance_helper(TIterator first, TIterator last, ETLSTD::input_iterator_tag) + { + typename ETLSTD::iterator_traits::difference_type d = 0; while (first != last) { ++d; + ++first; } return d; } template - typename etl::enable_if::iterator_catagory, random_access_iterator_tag>::value, - typename iterator_traits::difference_type>::type - distance(TIterator first, TIterator last) + typename ETLSTD::iterator_traits::difference_type distance_helper(TIterator first, TIterator last, ETLSTD::forward_iterator_tag) + { + typename ETLSTD::iterator_traits::difference_type d = 0; + + while (first != last) + { + ++d; + ++first; + } + + return d; + } + + template + typename ETLSTD::iterator_traits::difference_type distance_helper(TIterator first, TIterator last, ETLSTD::bidirectional_iterator_tag) + { + typename ETLSTD::iterator_traits::difference_type d = 0; + + while (first != last) + { + ++d; + ++first; + } + + return d; + } + + template + typename ETLSTD::iterator_traits::difference_type distance_helper(TIterator first, TIterator last, ETLSTD::random_access_iterator_tag) { return last - first; } @@ -186,11 +224,11 @@ namespace std { public: - typedef typename iterator_traits::difference_type difference_type; - typedef typename iterator_traits::value_type value_type; - typedef typename iterator_traits::pointer pointer; - typedef typename iterator_traits::reference reference; - typedef typename iterator_traits::iterator_category iterator_category; + typedef typename ETLSTD::iterator_traits::difference_type difference_type; + typedef typename ETLSTD::iterator_traits::value_type value_type; + typedef typename ETLSTD::iterator_traits::pointer pointer; + typedef typename ETLSTD::iterator_traits::reference reference; + typedef typename ETLSTD::iterator_traits::iterator_category iterator_category; reverse_iterator() { @@ -229,69 +267,69 @@ namespace std return current; } - ETL_CONSTEXPR reference operator *() const + reference operator *() const { TIterator temp = current; --temp; return *temp; } - ETL_CONSTEXPR pointer operator ->() const + pointer operator ->() const { TIterator temp = current; --temp; return &(*temp); } - ETL_CONSTEXPR reverse_iterator& operator ++() + reverse_iterator& operator ++() { --current; return *this; } - ETL_CONSTEXPR reverse_iterator operator ++(int) + reverse_iterator operator ++(int) { reverse_iterator temp = *this; --current; return temp; } - ETL_CONSTEXPR reverse_iterator& operator --() + reverse_iterator& operator --() { ++current; return *this; } - ETL_CONSTEXPR reverse_iterator operator --(int) + reverse_iterator operator --(int) { reverse_iterator temp = *this; ++current; return temp; } - ETL_CONSTEXPR reverse_iterator operator +(difference_type n) const + reverse_iterator operator +(difference_type n) const { return reverse_iterator(current - n); } - ETL_CONSTEXPR reverse_iterator& operator +=(difference_type n) + reverse_iterator& operator +=(difference_type n) { current -= n; return *this; } - ETL_CONSTEXPR reverse_iterator operator -(difference_type n) const + reverse_iterator operator -(difference_type n) const { return reverse_iterator(current + n); } - ETL_CONSTEXPR reverse_iterator& operator -=(difference_type n) + reverse_iterator& operator -=(difference_type n) { current += n; return *this; } - ETL_CONSTEXPR reference operator [](difference_type n) const + reference operator [](difference_type n) const { return *(*this + n); } @@ -302,43 +340,43 @@ namespace std }; template - inline ETL_CONSTEXPR bool operator <(const reverse_iterator& lhs, const reverse_iterator& rhs) + inline bool operator <(const reverse_iterator& lhs, const reverse_iterator& rhs) { return rhs.base() < lhs.base(); } template - inline ETL_CONSTEXPR bool operator !=(const reverse_iterator& lhs, const reverse_iterator& rhs) + inline bool operator !=(const reverse_iterator& lhs, const reverse_iterator& rhs) { return !(lhs == rhs); } template - inline ETL_CONSTEXPR bool operator >(const reverse_iterator& lhs, const reverse_iterator& rhs) + inline bool operator >(const reverse_iterator& lhs, const reverse_iterator& rhs) { return rhs < lhs; } template - inline ETL_CONSTEXPR bool operator <=(const reverse_iterator& lhs, const reverse_iterator& rhs) + inline bool operator <=(const reverse_iterator& lhs, const reverse_iterator& rhs) { return !(rhs < lhs); } template - inline ETL_CONSTEXPR bool operator >=(const reverse_iterator& lhs, const reverse_iterator& rhs) + inline bool operator >=(const reverse_iterator& lhs, const reverse_iterator& rhs) { return !(lhs < rhs); } template - inline ETL_CONSTEXPR typename reverse_iterator::difference_type operator -(const reverse_iterator& lhs, const reverse_iterator& rhs) + inline typename reverse_iterator::difference_type operator -(const reverse_iterator& lhs, const reverse_iterator& rhs) { return rhs.base() - lhs.base(); } template - inline ETL_CONSTEXPR reverse_iterator operator +(TDifference n, const reverse_iterator& itr) + inline reverse_iterator operator +(TDifference n, const reverse_iterator& itr) { return itr.operator +(n); } diff --git a/include/etl/stl/alternate/limits.h b/include/etl/stl/alternate/limits.h index 680cf7f9..231d7736 100644 --- a/include/etl/stl/alternate/limits.h +++ b/include/etl/stl/alternate/limits.h @@ -43,11 +43,15 @@ SOFTWARE. #define ETL_LOG2(x) (((x) * 301) / 1000) #if defined(ETL_IN_UNIT_TEST) -#define ETLSTD etlstd -namespace etlstd + #if !defined(ETLSTD) + #define ETLSTD etlstd + #endif + namespace etlstd #else -#define ETLSTD std -namespace std + #if !defined(ETLSTD) + #define ETLSTD std + #endif + namespace std #endif { template class numeric_limits; diff --git a/include/etl/stl/alternate/utility.h b/include/etl/stl/alternate/utility.h index 4fe77726..947b9109 100644 --- a/include/etl/stl/alternate/utility.h +++ b/include/etl/stl/alternate/utility.h @@ -32,14 +32,17 @@ SOFTWARE. #define ETL_STL_ALTERNATE_UTILITY_INCLUDED #include "../../platform.h" -#include "algorithm.h" #if defined(ETL_IN_UNIT_TEST) -#define ETLSTD etlstd -namespace etlstd + #if !defined(ETLSTD) + #define ETLSTD etlstd + #endif + namespace etlstd #else -#define ETLSTD std -namespace std + #if !defined(ETLSTD) + #define ETLSTD std + #endif + namespace std #endif { //****************************************************************************** @@ -79,8 +82,12 @@ namespace std void swap(pair& other) { - ETLSTD::swap(first, other.first); - ETLSTD::swap(second, other.second); + T1 temp1 = first; + T2 temp2 = second; + first = other.first; + second = other.second; + other.first = temp1; + other.second = temp2; } }; diff --git a/include/etl/u16string.h b/include/etl/u16string.h index 4dd9b990..d496f094 100644 --- a/include/etl/u16string.h +++ b/include/etl/u16string.h @@ -193,9 +193,12 @@ namespace etl //************************************************************************* /// Fix the internal pointers after a low level memory copy. //************************************************************************* +#ifdef ETL_ISTRING_REPAIR_ENABLE + virtual +#endif void repair() { - etl::iu16string::repair(buffer); + etl::iu16string::repair_buffer(buffer); } private: diff --git a/include/etl/u32string.h b/include/etl/u32string.h index 3edc3465..bc076373 100644 --- a/include/etl/u32string.h +++ b/include/etl/u32string.h @@ -193,9 +193,12 @@ namespace etl //************************************************************************* /// Fix the internal pointers after a low level memory copy. //************************************************************************* +#ifdef ETL_ISTRING_REPAIR_ENABLE + virtual +#endif void repair() { - etl::iu32string::repair(buffer); + etl::iu32string::repair_buffer(buffer); } private: diff --git a/include/etl/vector.h b/include/etl/vector.h index 2d5f2fb2..decc9577 100644 --- a/include/etl/vector.h +++ b/include/etl/vector.h @@ -868,7 +868,7 @@ namespace etl //************************************************************************* /// Fix the internal pointers after a low level memory copy. //************************************************************************* - void repair(T* p_buffer_) + void repair_buffer(T* p_buffer_) { uintptr_t length = p_end - p_buffer; p_buffer = p_buffer_; @@ -1112,13 +1112,16 @@ namespace etl //************************************************************************* /// 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::value, ETL_ERROR(etl::vector_incompatible_type)); #endif - etl::ivector::repair(buffer); + etl::ivector::repair_buffer(buffer); } private: @@ -1222,7 +1225,7 @@ namespace etl //************************************************************************* void repair() { - etl::ivector::repair(buffer); + etl::ivector::repair_buffer(buffer); } private: diff --git a/include/etl/version.h b/include/etl/version.h index 4ec67f8b..c52bc4b9 100644 --- a/include/etl/version.h +++ b/include/etl/version.h @@ -37,13 +37,13 @@ SOFTWARE. /// Definitions of the ETL version ///\ingroup utilities -#define ETL_VERSION "11.16.2" -#define ETL_VERSION_W L"11.16.2" -#define ETL_VERSION_U16 u"11.16.2" -#define ETL_VERSION_U32 U"11.16.2" +#define ETL_VERSION "11.16.3" +#define ETL_VERSION_W L"11.16.3" +#define ETL_VERSION_U16 u"11.16.3" +#define ETL_VERSION_U32 U"11.16.3" #define ETL_VERSION_MAJOR 11 #define ETL_VERSION_MINOR 16 -#define ETL_VERSION_PATCH 2 +#define ETL_VERSION_PATCH 3 #define ETL_VERSION_VALUE ((ETL_VERSION_MAJOR * 10000) + (ETL_VERSION_MINOR * 100) + ETL_VERSION_PATCH) #endif diff --git a/include/etl/wstring.h b/include/etl/wstring.h index 1ab83a02..206f7253 100644 --- a/include/etl/wstring.h +++ b/include/etl/wstring.h @@ -194,9 +194,12 @@ namespace etl //************************************************************************* /// Fix the internal pointers after a low level memory copy. //************************************************************************* +#ifdef ETL_ISTRING_REPAIR_ENABLE + virtual +#endif void repair() { - etl::iwstring::repair(buffer); + etl::iwstring::repair_buffer(buffer); } private: diff --git a/src/private/pvoidvector.cpp b/src/private/pvoidvector.cpp index 814abbd4..985b72ee 100644 --- a/src/private/pvoidvector.cpp +++ b/src/private/pvoidvector.cpp @@ -479,7 +479,7 @@ void etl::pvoidvector::initialise() //************************************************************************* /// Fix the internal pointers after a low level memory copy. //************************************************************************* -void etl::pvoidvector::repair(void** p_buffer_) +void etl::pvoidvector::repair_buffer(void** p_buffer_) { uintptr_t length = p_end - p_buffer; diff --git a/support/Release notes.txt b/support/Release notes.txt index f977f9d7..85a6cf0a 100644 --- a/support/Release notes.txt +++ b/support/Release notes.txt @@ -1,3 +1,8 @@ +=============================================================================== +11.16.3 +Fixed missing algorithms for No STL option. +Improved Keil compatibility. + =============================================================================== 11.15.1 io_port_test Fixed unaligned access error. diff --git a/test/codeblocks/ETL.cbp b/test/codeblocks/ETL.cbp index 090872e2..e66e4acd 100644 --- a/test/codeblocks/ETL.cbp +++ b/test/codeblocks/ETL.cbp @@ -337,6 +337,7 @@ + diff --git a/test/no_stl_test_iterators.h b/test/no_stl_test_iterators.h new file mode 100644 index 00000000..69def7fc --- /dev/null +++ b/test/no_stl_test_iterators.h @@ -0,0 +1,206 @@ +///\file + +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2018 jwellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#ifndef ETL_NO_STL_TEST_ITERATORS_INCLUDED +#define ETL_NO_STL_TEST_ITERATORS_INCLUDED + +#include "etl/stl/alternate/iterator.h" + +template +struct non_random_iterator : public etlstd::iterator +{ + non_random_iterator() + : ptr(nullptr) + { + } + + non_random_iterator(T* v) + : ptr(v) + { + } + + non_random_iterator(const non_random_iterator& other) + { + ptr = other.ptr; + } + + T& operator *() + { + return *ptr; + } + + const T& operator *() const + { + return *ptr; + } + + non_random_iterator& operator ++() + { + ++ptr; + return *this; + } + + non_random_iterator operator ++(int) + { + T* temp = ptr; + ++ptr; + return non_random_iterator(temp); + } + + non_random_iterator& operator --() + { + --ptr; + return *this; + } + + non_random_iterator operator --(int) + { + T* temp = ptr; + --ptr; + return non_random_iterator(temp); + } + + non_random_iterator& operator =(T* other) + { + ptr = other; + return *this; + } + + operator T*() + { + return ptr; + } + + operator const T*() + { + return ptr; + } + + T* ptr; +}; + +template +bool operator !=(const non_random_iterator& lhs, const non_random_iterator& rhs) +{ + return lhs.ptr != rhs.ptr; +} + +template +struct random_iterator : public etlstd::iterator +{ + random_iterator() + : ptr(nullptr) + { + } + + random_iterator(T* v) + : ptr(v) + { + } + + random_iterator(const random_iterator& other) + { + ptr = other.ptr; + } + + T& operator *() + { + return *ptr; + } + + const T& operator *() const + { + return *ptr; + } + + random_iterator& operator ++() + { + ++ptr; + return *this; + } + + random_iterator operator ++(int) + { + T* temp = ptr; + ++ptr; + return random_iterator(temp); + } + + random_iterator& operator --() + { + --ptr; + return *this; + } + + random_iterator operator --(int) + { + T* temp = ptr; + --ptr; + return random_iterator(temp); + } + + random_iterator& operator +=(int n) + { + ptr += n; + return *this; + } + + random_iterator& operator -=(int n) + { + ptr -= n; + return *this; + } + + random_iterator& operator =(T* other) + { + ptr = other; + return *this; + } + + operator T*() + { + return ptr; + } + + operator const T*() + { + return ptr; + } + + T* ptr; +}; + +template +ptrdiff_t operator -(const random_iterator& lhs, const random_iterator& rhs) +{ + return lhs.ptr - rhs.ptr; +} + +#endif \ No newline at end of file diff --git a/test/test_no_stl_algorithm.cpp b/test/test_no_stl_algorithm.cpp index 23ae4ef9..36c75673 100644 --- a/test/test_no_stl_algorithm.cpp +++ b/test/test_no_stl_algorithm.cpp @@ -37,15 +37,19 @@ SOFTWARE. #include #include +#include "no_stl_test_iterators.h" + namespace { - int dataEQ[10] = { 1, 1, 3, 3, 5, 5, 7, 7, 9, 9 }; + const size_t SIZE = 10; + + int dataEQ[SIZE] = { 1, 1, 3, 3, 5, 5, 7, 7, 9, 9 }; std::list dataEQL = { 1, 1, 3, 3, 5, 5, 7, 7, 9, 9 }; - int dataS[10] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 }; + int dataS[SIZE] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 }; std::list dataSL = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 }; - int dataA[10] = { 2, 1, 4, 3, 6, 5, 8, 7, 10, 9 }; + int dataA[SIZE] = { 2, 1, 4, 3, 6, 5, 8, 7, 10, 9 }; typedef std::vector Vector; Vector dataV = { 2, 1, 4, 3, 6, 5, 8, 7, 10, 9 }; @@ -53,6 +57,9 @@ namespace typedef std::list List; List dataL = { 2, 1, 4, 3, 6, 5, 8, 7, 10, 9 }; + int dataD1[SIZE] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; + int dataD2[SIZE] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; + class Data { public: @@ -112,48 +119,6 @@ namespace SUITE(test_no_stl_algorithm) { - //************************************************************************* - TEST(distance_non_random) - { - ptrdiff_t d1 = std::distance(dataL.begin(), dataL.end()); - ptrdiff_t d2 = etlstd::distance(dataL.begin(), dataL.end()); - - CHECK_EQUAL(d1, d2); - } - - //************************************************************************* - TEST(distance_random) - { - ptrdiff_t d1 = std::distance(dataV.begin(), dataV.end()); - ptrdiff_t d2 = etlstd::distance(dataV.begin(), dataV.end()); - - CHECK_EQUAL(d1, d2); - } - - //************************************************************************* - TEST(advance_non_random) - { - List::const_iterator itr1 = dataL.begin(); - List::const_iterator itr2 = dataL.begin(); - - std::advance(itr1, 4); - std::advance(itr2, 4); - - CHECK_EQUAL(*itr1, *itr2); - } - - //************************************************************************* - TEST(advance_random) - { - Vector::const_iterator itr1 = dataV.begin(); - Vector::const_iterator itr2 = dataV.begin(); - - std::advance(itr1, 4); - std::advance(itr2, 4); - - CHECK_EQUAL(*itr1, *itr2); - } - //************************************************************************* TEST(min) { @@ -317,7 +282,7 @@ namespace for (int i = 0; i < 11; ++i) { int* lb1 = std::lower_bound(std::begin(dataS), std::end(dataS), i); - int* lb2 = etlstd::lower_bound(std::begin(dataS), std::end(dataS), i); + int* lb2 = etlstd::lower_bound(random_iterator(std::begin(dataS)), random_iterator(std::end(dataS)), i); CHECK_EQUAL(lb1, lb2); } @@ -328,10 +293,10 @@ namespace { for (int i = 0; i < 11; ++i) { - std::list::iterator lb1 = std::lower_bound(std::begin(dataSL), std::end(dataSL), i); - std::list::iterator lb2 = etlstd::lower_bound(std::begin(dataSL), std::end(dataSL), i); + int* lb1 = std::lower_bound(std::begin(dataS), std::end(dataS), i); + int* lb2 = etlstd::lower_bound(non_random_iterator(std::begin(dataS)), non_random_iterator(std::end(dataS)), i); - CHECK_EQUAL(std::distance(std::begin(dataSL), lb1), std::distance(std::begin(dataSL), lb2)); + CHECK_EQUAL(std::distance(std::begin(dataS), lb1), std::distance(std::begin(dataS), lb2)); } } @@ -341,7 +306,7 @@ namespace for (int i = 0; i < 11; ++i) { int* lb1 = std::upper_bound(std::begin(dataS), std::end(dataS), i); - int* lb2 = etlstd::upper_bound(std::begin(dataS), std::end(dataS), i); + int* lb2 = etlstd::upper_bound(random_iterator(std::begin(dataS)), random_iterator(std::end(dataS)), i); CHECK_EQUAL(std::distance(std::begin(dataS), lb1), std::distance(std::begin(dataS), lb2)); } @@ -352,10 +317,10 @@ namespace { for (int i = 0; i < 11; ++i) { - std::list::iterator lb1 = std::upper_bound(std::begin(dataSL), std::end(dataSL), i); - std::list::iterator lb2 = etlstd::upper_bound(std::begin(dataSL), std::end(dataSL), i); + int* lb1 = std::upper_bound(std::begin(dataS), std::end(dataS), i); + int* lb2 = etlstd::upper_bound(non_random_iterator(std::begin(dataS)), non_random_iterator(std::end(dataS)), i); - CHECK_EQUAL(std::distance(std::begin(dataSL), lb1), std::distance(std::begin(dataSL), lb2)); + CHECK_EQUAL(std::distance(std::begin(dataS), lb1), std::distance(std::begin(dataS), lb2)); } } @@ -364,11 +329,11 @@ namespace { for (int i = 0; i < 11; ++i) { - std::pair lb1 = std::equal_range(std::begin(dataEQ), std::end(dataEQ), i); - std::pair lb2 = etlstd::equal_range(std::begin(dataEQ), std::end(dataEQ), i); + std::pair lb1 = std::equal_range(std::begin(dataEQ), std::end(dataEQ), i); + etlstd::pair, random_iterator> lb2 = etlstd::equal_range(random_iterator(std::begin(dataEQ)), random_iterator(std::end(dataEQ)), i); - CHECK_EQUAL(std::distance(std::begin(dataEQ), lb1.first), std::distance(std::begin(dataEQ), lb2.first)); - CHECK_EQUAL(std::distance(lb1.first, lb1.second), std::distance(lb2.first, lb2.second)); + CHECK_EQUAL(std::distance(std::begin(dataEQ), lb1.first), std::distance(std::begin(dataEQ), lb2.first)); + CHECK_EQUAL(std::distance(lb1.first, lb1.second), std::distance(lb2.first, lb2.second)); } } @@ -377,11 +342,11 @@ namespace { for (int i = 0; i < 11; ++i) { - std::pair::iterator, std::list::iterator> lb1 = std::equal_range(std::begin(dataEQL), std::end(dataEQL), i); - std::pair::iterator, std::list::iterator> lb2 = etlstd::equal_range(std::begin(dataEQL), std::end(dataEQL), i); + std::pair lb1 = std::equal_range(std::begin(dataEQ), std::end(dataEQ), i); + etlstd::pair, non_random_iterator> lb2 = etlstd::equal_range(non_random_iterator(std::begin(dataEQ)), non_random_iterator(std::end(dataEQ)), i); - CHECK_EQUAL(std::distance(std::begin(dataEQL), lb1.first), std::distance(std::begin(dataEQL), lb2.first)); - CHECK_EQUAL(std::distance(lb1.first, lb1.second), std::distance(lb2.first, lb2.second)); + CHECK_EQUAL(std::distance(std::begin(dataEQ), lb1.first), std::distance(std::begin(dataEQ), lb2.first)); + CHECK_EQUAL(std::distance(lb1.first, lb1.second), std::distance(lb2.first, lb2.second)); } } @@ -577,5 +542,109 @@ namespace isEqual = std::equal(std::begin(data1), std::end(data1), std::begin(data2)); CHECK(isEqual); } + + //************************************************************************* + TEST(find) + { + int* itr1 = std::find(std::begin(dataA), std::end(dataA), 5); + int* itr2 = etlstd::find(std::begin(dataA), std::end(dataA), 5); + + CHECK(itr1 == itr2); + } + + //************************************************************************* + TEST(find_if) + { + struct predicate + { + bool operator()(int i) const + { + return (i == 5); + } + }; + + int* itr1 = std::find_if(std::begin(dataA), std::end(dataA), predicate()); + int* itr2 = etlstd::find_if(std::begin(dataA), std::end(dataA), predicate()); + + CHECK(itr1 == itr2); + } + + //************************************************************************* + TEST(count) + { + size_t c1 = std::count(std::begin(dataEQ), std::end(dataEQ), 5); + size_t c2 = etlstd::count(std::begin(dataEQ), std::end(dataEQ), 5); + + CHECK(c1 == c2); + } + + //************************************************************************* + TEST(count_if) + { + struct predicate + { + bool operator()(int i) const + { + return (i == 5); + } + }; + + size_t c1 = std::count_if(std::begin(dataEQ), std::end(dataEQ), predicate()); + size_t c2 = etlstd::count_if(std::begin(dataEQ), std::end(dataEQ), predicate()); + + CHECK(c1 == c2); + } + + //************************************************************************* + TEST(fill_n) + { + int* p1 = std::fill_n(std::begin(dataD1), SIZE, 5); + int* p2 = etlstd::fill_n(std::begin(dataD2), SIZE, 5); + + CHECK(p2 == std::end(dataD2)); + + bool isEqual = std::equal(std::begin(dataD1), std::end(dataD1), std::begin(dataD2)); + CHECK(isEqual); + } + + //************************************************************************* + TEST(transform1) + { + struct Function + { + int operator()(int d) const + { + return d * 2; + } + }; + + int* p1 = std::transform(std::begin(dataS), std::end(dataS), std::begin(dataD1), Function()); + int* p2 = etlstd::transform(std::begin(dataS), std::end(dataS), std::begin(dataD2), Function()); + + CHECK(p2 == std::end(dataD2)); + + bool isEqual = std::equal(std::begin(dataD1), std::end(dataD1), std::begin(dataD2)); + CHECK(isEqual); + } + + //************************************************************************* + TEST(transform2) + { + struct Function + { + int operator()(int d1, int d2) const + { + return d1 + d2; + } + }; + + int* p1 = std::transform(std::begin(dataS), std::end(dataS), std::begin(dataA), std::begin(dataD1), Function()); + int* p2 = etlstd::transform(std::begin(dataS), std::end(dataS), std::begin(dataA), std::begin(dataD2), Function()); + + CHECK(p2 == std::end(dataD2)); + + bool isEqual = std::equal(std::begin(dataD1), std::end(dataD1), std::begin(dataD2)); + CHECK(isEqual); + } }; } diff --git a/test/test_no_stl_iterator.cpp b/test/test_no_stl_iterator.cpp new file mode 100644 index 00000000..74edfd1b --- /dev/null +++ b/test/test_no_stl_iterator.cpp @@ -0,0 +1,96 @@ +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2018 jwellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#include "UnitTest++.h" + +#undef min +#undef max + +#include "etl/stl/alternate/iterator.h" + +#include +#include +#include + +#include "no_stl_test_iterators.h" + +namespace +{ + const size_t SIZE = 10; + + int dataA[SIZE] = { 2, 1, 4, 3, 6, 5, 8, 7, 10, 9 }; + + SUITE(test_no_stl_iterator) + { + //************************************************************************* + TEST(distance_non_random) + { + ptrdiff_t d = etlstd::distance(non_random_iterator(&dataA[0]), non_random_iterator(&dataA[SIZE])); + + CHECK_EQUAL(SIZE, d); + } + + //************************************************************************* + TEST(distance_random) + { + ptrdiff_t d = etlstd::distance(random_iterator(&dataA[0]), random_iterator(&dataA[SIZE])); + + CHECK_EQUAL(SIZE, d); + } + + //************************************************************************* + TEST(advance_non_random) + { + int* itr1 = std::begin(dataA); + non_random_iterator itr2 = std::begin(dataA); + + std::advance(itr1, 4); + etlstd::advance(itr2, 4); + CHECK_EQUAL(*itr1, *itr2); + + std::advance(itr1, -3); + etlstd::advance(itr2, -3); + CHECK_EQUAL(*itr1, *itr2); + } + + //************************************************************************* + TEST(advance_random) + { + int* itr1 = std::begin(dataA); + random_iterator itr2 = std::begin(dataA); + + std::advance(itr1, 4); + etlstd::advance(itr2, 4); + CHECK_EQUAL(*itr1, *itr2); + + std::advance(itr1, -3); + etlstd::advance(itr2, -3); + CHECK_EQUAL(*itr1, *itr2); + } + }; +} diff --git a/test/vs2017/etl.vcxproj b/test/vs2017/etl.vcxproj index e304e478..7c97660e 100644 --- a/test/vs2017/etl.vcxproj +++ b/test/vs2017/etl.vcxproj @@ -360,6 +360,7 @@ + @@ -525,6 +526,7 @@ + @@ -688,6 +690,7 @@ + diff --git a/test/vs2017/etl.vcxproj.filters b/test/vs2017/etl.vcxproj.filters index 6ad8cfc2..b4225aba 100644 --- a/test/vs2017/etl.vcxproj.filters +++ b/test/vs2017/etl.vcxproj.filters @@ -687,6 +687,12 @@ ETL\Maths + + Source Files + + + ETL\Utilities\Atomic + @@ -1127,6 +1133,9 @@ Source Files + + Source Files + From 0c721be429f2f9c8981d0accab76edb3feea4ca9 Mon Sep 17 00:00:00 2001 From: John Wellbelove Date: Sat, 1 Sep 2018 08:06:56 +0100 Subject: [PATCH 02/12] Merge remote-tracking branch 'origin/development' # Conflicts: # include/etl/version.h # support/Release notes.txt --- include/etl/atomic.h | 5 ++++- include/etl/nullptr.h | 2 +- include/etl/profiles/armv5.h | 2 +- include/etl/profiles/armv5_no_stl.h | 2 +- include/etl/profiles/armv6.h | 2 +- include/etl/profiles/armv6_no_stl.h | 2 +- include/etl/version.h | 10 +++++----- support/Release notes.txt | 4 ++++ 8 files changed, 18 insertions(+), 11 deletions(-) diff --git a/include/etl/atomic.h b/include/etl/atomic.h index 5d247356..cbf31394 100644 --- a/include/etl/atomic.h +++ b/include/etl/atomic.h @@ -34,9 +34,12 @@ SOFTWARE. #if ETL_CPP11_SUPPORTED == 1 && !defined(ETL_NO_STL) #include "atomic/atomic_std.h" #define ETL_HAS_ATOMIC 1 -#elif defined(ETL_COMPILER_ARM) +#elif defined(ETL_COMPILER_ARM5) #include "atomic/atomic_arm.h" #define ETL_HAS_ATOMIC 1 +#elif defined(ETL_COMPILER_ARM6) +#include "atomic/atomic_arm.h" +#define ETL_HAS_ATOMIC 1 #elif defined(ETL_COMPILER_GCC) #include "atomic/atomic_gcc_sync.h" #define ETL_HAS_ATOMIC 1 diff --git a/include/etl/nullptr.h b/include/etl/nullptr.h index 1fd946c6..99dfc2f5 100644 --- a/include/etl/nullptr.h +++ b/include/etl/nullptr.h @@ -73,7 +73,7 @@ namespace std /// A null pointer. ///\ingroup nullptr //***************************************************************************** -#if !defined(ETL_STLPORT) +#if !defined(ETL_STLPORT) || !defined(ETL_COMPILER_ARM5) const std::nullptr_t nullptr = {}; #endif diff --git a/include/etl/profiles/armv5.h b/include/etl/profiles/armv5.h index 6d8f8746..07918cda 100644 --- a/include/etl/profiles/armv5.h +++ b/include/etl/profiles/armv5.h @@ -37,7 +37,7 @@ SOFTWARE. #define ETL_TARGET_DEVICE_ARM #define ETL_TARGET_OS_NONE -#define ETL_COMPILER_ARM +#define ETL_COMPILER_ARM5 #define ETL_CPP11_SUPPORTED 0 #define ETL_CPP14_SUPPORTED 0 #define ETL_CPP17_SUPPORTED 0 diff --git a/include/etl/profiles/armv5_no_stl.h b/include/etl/profiles/armv5_no_stl.h index d69fcbf6..cc8fabb3 100644 --- a/include/etl/profiles/armv5_no_stl.h +++ b/include/etl/profiles/armv5_no_stl.h @@ -37,7 +37,7 @@ SOFTWARE. #define ETL_TARGET_DEVICE_ARM #define ETL_TARGET_OS_NONE -#define ETL_COMPILER_ARM +#define ETL_COMPILER_ARM5 #define ETL_CPP11_SUPPORTED 0 #define ETL_CPP14_SUPPORTED 0 #define ETL_CPP17_SUPPORTED 0 diff --git a/include/etl/profiles/armv6.h b/include/etl/profiles/armv6.h index f8f59ad4..9e39d018 100644 --- a/include/etl/profiles/armv6.h +++ b/include/etl/profiles/armv6.h @@ -37,7 +37,7 @@ SOFTWARE. #define ETL_TARGET_DEVICE_ARM #define ETL_TARGET_OS_NONE -#define ETL_COMPILER_LLVM +#define ETL_COMPILER_ARM6 #define ETL_CPP11_SUPPORTED 1 #define ETL_CPP14_SUPPORTED 0 #define ETL_CPP17_SUPPORTED 0 diff --git a/include/etl/profiles/armv6_no_stl.h b/include/etl/profiles/armv6_no_stl.h index 0c25c3c1..fbf4fc6e 100644 --- a/include/etl/profiles/armv6_no_stl.h +++ b/include/etl/profiles/armv6_no_stl.h @@ -37,7 +37,7 @@ SOFTWARE. #define ETL_TARGET_DEVICE_ARM #define ETL_TARGET_OS_NONE -#define ETL_COMPILER_LLVM +#define ETL_COMPILER_ARM6 #define ETL_CPP11_SUPPORTED 1 #define ETL_CPP14_SUPPORTED 0 #define ETL_CPP17_SUPPORTED 0 diff --git a/include/etl/version.h b/include/etl/version.h index c52bc4b9..db36b7ce 100644 --- a/include/etl/version.h +++ b/include/etl/version.h @@ -37,13 +37,13 @@ SOFTWARE. /// Definitions of the ETL version ///\ingroup utilities -#define ETL_VERSION "11.16.3" -#define ETL_VERSION_W L"11.16.3" -#define ETL_VERSION_U16 u"11.16.3" -#define ETL_VERSION_U32 U"11.16.3" +#define ETL_VERSION "11.16.4" +#define ETL_VERSION_W L"11.16.4" +#define ETL_VERSION_U16 u"11.16.4" +#define ETL_VERSION_U32 U"11.16.4" #define ETL_VERSION_MAJOR 11 #define ETL_VERSION_MINOR 16 -#define ETL_VERSION_PATCH 3 +#define ETL_VERSION_PATCH 4 #define ETL_VERSION_VALUE ((ETL_VERSION_MAJOR * 10000) + (ETL_VERSION_MINOR * 100) + ETL_VERSION_PATCH) #endif diff --git a/support/Release notes.txt b/support/Release notes.txt index 85a6cf0a..d6100415 100644 --- a/support/Release notes.txt +++ b/support/Release notes.txt @@ -1,3 +1,7 @@ +=============================================================================== +11.16.4 +Fixed nullptr compatibility for ARM5 compiler. + =============================================================================== 11.16.3 Fixed missing algorithms for No STL option. From aff5e2f7aa6593bc7848dbb04e8c09e57ea4e55c Mon Sep 17 00:00:00 2001 From: John Wellbelove Date: Sun, 2 Sep 2018 14:07:17 +0100 Subject: [PATCH 03/12] Merge remote-tracking branch 'origin/development' # Conflicts: # examples/ArmTimerCallbacks - C++/ArmTimerCallbacks.uvprojx # include/etl/nullptr.h --- .../ArmTimerCallbacks.uvprojx | 4 ++-- examples/ArmTimerCallbacks - C++/etl_profile.h | 8 ++++++++ examples/ArmTimerCallbacks - C++/main.cpp | 18 ++++++++++++++---- include/etl/nullptr.h | 4 ++-- include/etl/profiles/armv5.h | 4 ++-- include/etl/profiles/armv5_no_stl.h | 4 ++-- include/etl/stl/alternate/utility.h | 7 +++++-- 7 files changed, 35 insertions(+), 14 deletions(-) diff --git a/examples/ArmTimerCallbacks - C++/ArmTimerCallbacks.uvprojx b/examples/ArmTimerCallbacks - C++/ArmTimerCallbacks.uvprojx index d92ef376..497bc1bd 100644 --- a/examples/ArmTimerCallbacks - C++/ArmTimerCallbacks.uvprojx +++ b/examples/ArmTimerCallbacks - C++/ArmTimerCallbacks.uvprojx @@ -10,8 +10,8 @@ Target 1 0x4 ARM-ADS - 5060750::V5.06 update 6 (build 750)::ARMCC - 0 + 6090000::V6.9::.\ARMCLANG + 1 STM32F401RETx diff --git a/examples/ArmTimerCallbacks - C++/etl_profile.h b/examples/ArmTimerCallbacks - C++/etl_profile.h index 0e874e1e..6362a416 100644 --- a/examples/ArmTimerCallbacks - C++/etl_profile.h +++ b/examples/ArmTimerCallbacks - C++/etl_profile.h @@ -12,10 +12,18 @@ #if (__CC_ARM == 1) // ARM5 compiler + #if defined(ETL_NO_STL) + #include "etl/profiles/armv5_no_stl.h" + #else #include "etl/profiles/armv5.h" + #endif #else // ARM6 compiler + #if defined(ETL_NO_STL) + #include "etl/profiles/armv6_no_stl.h" + #else #include "etl/profiles/armv6.h" + #endif #endif #endif diff --git a/examples/ArmTimerCallbacks - C++/main.cpp b/examples/ArmTimerCallbacks - C++/main.cpp index d2d0e5a3..9a25db0d 100644 --- a/examples/ArmTimerCallbacks - C++/main.cpp +++ b/examples/ArmTimerCallbacks - C++/main.cpp @@ -1,13 +1,17 @@ #include +//#if (__cplusplus < 201103L) extern "C" { - #include "Board_LED.h" // ::Board Support:LED - #include "Board_Buttons.h" // ::Board Support:Buttons - - #include "stm32f4xx.h" // Device header +//#endif +#include "Board_LED.h" // ::Board Support:LED +#include "Board_Buttons.h" // ::Board Support:Buttons +//#if (__cplusplus < 201103L) } +//#endif + +#include "stm32f4xx.h" // Device header #include "etl/function.h" #include "etl/callback_timer.h" @@ -124,6 +128,12 @@ int main() LED_Initialize(); Buttons_Initialize(); + long int v = __cplusplus; + + char16_t c16; + + int* p = nullptr; + // The LEDs will start flashing fast after 2 seconds. // After another 5 seconds they will start flashing slower. short_toggle = callback_timer.register_timer(LedToggle, 50, etl::timer::mode::REPEATING); diff --git a/include/etl/nullptr.h b/include/etl/nullptr.h index 99dfc2f5..1ee34149 100644 --- a/include/etl/nullptr.h +++ b/include/etl/nullptr.h @@ -37,7 +37,7 @@ SOFTWARE. /// A definition of nullptr for compilers that don't support it as standard. ///\ingroup utilities -#if (ETL_NO_NULLPTR_SUPPORT && !defined(ARDUINO)) +#if (ETL_NO_NULLPTR_SUPPORT && !defined(ARDUINO)) || defined(ETL_COMPILER_ARM5) namespace std { //***************************************************************************** @@ -73,7 +73,7 @@ namespace std /// A null pointer. ///\ingroup nullptr //***************************************************************************** -#if !defined(ETL_STLPORT) || !defined(ETL_COMPILER_ARM5) +#if !defined(ETL_STLPORT) && (defined(ETL_COMPILER_ARM5) && (__cplusplus < 201103L)) const std::nullptr_t nullptr = {}; #endif diff --git a/include/etl/profiles/armv5.h b/include/etl/profiles/armv5.h index 07918cda..b17f64dd 100644 --- a/include/etl/profiles/armv5.h +++ b/include/etl/profiles/armv5.h @@ -41,8 +41,8 @@ SOFTWARE. #define ETL_CPP11_SUPPORTED 0 #define ETL_CPP14_SUPPORTED 0 #define ETL_CPP17_SUPPORTED 0 -#define ETL_NO_NULLPTR_SUPPORT 1 -#define ETL_NO_LARGE_CHAR_SUPPORT 1 +#define ETL_NO_NULLPTR_SUPPORT (__cplusplus < 201103L) +#define ETL_NO_LARGE_CHAR_SUPPORT (__cplusplus < 201103L) #define ETL_CPP11_TYPE_TRAITS_IS_TRIVIAL_SUPPORTED 0 #endif diff --git a/include/etl/profiles/armv5_no_stl.h b/include/etl/profiles/armv5_no_stl.h index cc8fabb3..4da2cbb5 100644 --- a/include/etl/profiles/armv5_no_stl.h +++ b/include/etl/profiles/armv5_no_stl.h @@ -41,8 +41,8 @@ SOFTWARE. #define ETL_CPP11_SUPPORTED 0 #define ETL_CPP14_SUPPORTED 0 #define ETL_CPP17_SUPPORTED 0 -#define ETL_NO_NULLPTR_SUPPORT 1 -#define ETL_NO_LARGE_CHAR_SUPPORT 1 +#define ETL_NO_NULLPTR_SUPPORT (__cplusplus < 201103L) +#define ETL_NO_LARGE_CHAR_SUPPORT (__cplusplus < 201103L) #define ETL_CPP11_TYPE_TRAITS_IS_TRIVIAL_SUPPORTED 0 #define ETL_NO_STL diff --git a/include/etl/stl/alternate/utility.h b/include/etl/stl/alternate/utility.h index 947b9109..41cf3dec 100644 --- a/include/etl/stl/alternate/utility.h +++ b/include/etl/stl/alternate/utility.h @@ -45,6 +45,7 @@ SOFTWARE. namespace std #endif { +#if !defined(ETL_COMPILER_ARM6) //****************************************************************************** template struct pair @@ -90,7 +91,7 @@ SOFTWARE. other.second = temp2; } }; - +#endif //****************************************************************************** template inline pair make_pair(T1 a, T2 b) @@ -98,6 +99,7 @@ SOFTWARE. return pair(a, b); } +#if !defined(ETL_COMPILER_ARM6) //****************************************************************************** template inline void swap(pair& a, pair& b) @@ -107,7 +109,7 @@ SOFTWARE. //****************************************************************************** template - inline bool operator ==(const pair& a, const pair& b) + inline bool operator ==(const pair& a, const pair& b) { return (a.first == b.first) && (a.second == b.second); } @@ -142,6 +144,7 @@ SOFTWARE. { return !(a < b); } +#endif } #endif From 7b8f8b08f7d2b8c2fde9c0d8d7aeb48d6479584c Mon Sep 17 00:00:00 2001 From: John Wellbelove Date: Tue, 4 Sep 2018 17:51:28 +0100 Subject: [PATCH 04/12] Merge remote-tracking branch 'origin/development' # Conflicts: # include/etl/version.h # support/Release notes.txt --- include/etl/fnv_1.h | 8 +-- include/etl/version.h | 10 +-- src/binary.cpp | 18 +++--- src/crc64_ecma.cpp | 128 +++++++++++++++++++------------------- support/Release notes.txt | 4 ++ 5 files changed, 86 insertions(+), 82 deletions(-) diff --git a/include/etl/fnv_1.h b/include/etl/fnv_1.h index c5704454..21065e1f 100644 --- a/include/etl/fnv_1.h +++ b/include/etl/fnv_1.h @@ -74,8 +74,8 @@ namespace etl return hash; } - static const uint64_t OFFSET_BASIS = 0xCBF29CE484222325; - static const uint64_t PRIME = 0x00000100000001b3; + static const uint64_t OFFSET_BASIS = 0xCBF29CE484222325ull; + static const uint64_t PRIME = 0x00000100000001b3ull; }; //*************************************************************************** @@ -132,8 +132,8 @@ namespace etl return hash; } - static const uint64_t OFFSET_BASIS = 0xCBF29CE484222325; - static const uint64_t PRIME = 0x00000100000001b3; + static const uint64_t OFFSET_BASIS = 0xCBF29CE484222325ull; + static const uint64_t PRIME = 0x00000100000001b3ull; }; //*************************************************************************** diff --git a/include/etl/version.h b/include/etl/version.h index db36b7ce..32094197 100644 --- a/include/etl/version.h +++ b/include/etl/version.h @@ -37,13 +37,13 @@ SOFTWARE. /// Definitions of the ETL version ///\ingroup utilities -#define ETL_VERSION "11.16.4" -#define ETL_VERSION_W L"11.16.4" -#define ETL_VERSION_U16 u"11.16.4" -#define ETL_VERSION_U32 U"11.16.4" +#define ETL_VERSION "11.16.5" +#define ETL_VERSION_W L"11.16.5" +#define ETL_VERSION_U16 u"11.16.5" +#define ETL_VERSION_U32 U"11.16.5" #define ETL_VERSION_MAJOR 11 #define ETL_VERSION_MINOR 16 -#define ETL_VERSION_PATCH 4 +#define ETL_VERSION_PATCH 5 #define ETL_VERSION_VALUE ((ETL_VERSION_MAJOR * 10000) + (ETL_VERSION_MINOR * 100) + ETL_VERSION_PATCH) #endif diff --git a/src/binary.cpp b/src/binary.cpp index 0024e56e..073955ed 100644 --- a/src/binary.cpp +++ b/src/binary.cpp @@ -79,11 +79,11 @@ namespace etl //*************************************************************************** uint64_t reverse_bits(uint64_t value) { - value = ((value & 0xAAAAAAAAAAAAAAAA) >> 1) | ((value & 0x5555555555555555) << 1); - value = ((value & 0xCCCCCCCCCCCCCCCC) >> 2) | ((value & 0x3333333333333333) << 2); - value = ((value & 0xF0F0F0F0F0F0F0F0) >> 4) | ((value & 0x0F0F0F0F0F0F0F0F) << 4); - value = ((value & 0xFF00FF00FF00FF00) >> 8) | ((value & 0x00FF00FF00FF00FF) << 8); - value = ((value & 0xFFFF0000FFFF0000) >> 16) | ((value & 0x0000FFFF0000FFFF) << 16); + value = ((value & 0xAAAAAAAAAAAAAAAAull) >> 1) | ((value & 0x5555555555555555ull) << 1); + value = ((value & 0xCCCCCCCCCCCCCCCCull) >> 2) | ((value & 0x3333333333333333ull) << 2); + value = ((value & 0xF0F0F0F0F0F0F0F0ull) >> 4) | ((value & 0x0F0F0F0F0F0F0F0Full) << 4); + value = ((value & 0xFF00FF00FF00FF00ull) >> 8) | ((value & 0x00FF00FF00FF00FFull) << 8); + value = ((value & 0xFFFF0000FFFF0000ull) >> 16) | ((value & 0x0000FFFF0000FFFFull) << 16); value = (value >> 32) | (value << 32); return value; @@ -115,8 +115,8 @@ namespace etl //*************************************************************************** uint64_t reverse_bytes(uint64_t value) { - value = ((value & 0xFF00FF00FF00FF00) >> 8) | ((value & 0x00FF00FF00FF00FF) << 8); - value = ((value & 0xFFFF0000FFFF0000) >> 16) | ((value & 0x0000FFFF0000FFFF) << 16); + value = ((value & 0xFF00FF00FF00FF00ull) >> 8) | ((value & 0x00FF00FF00FF00FFull) << 8); + value = ((value & 0xFFFF0000FFFF0000ull) >> 16) | ((value & 0x0000FFFF0000FFFFull) << 16); value = (value >> 32) | (value << 32); return value; @@ -234,7 +234,7 @@ namespace etl { uint64_t count; static const int S[] = { 1, 2, 4, 8, 16, 32 }; - static const uint64_t B[] = { 0x5555555555555555, 0x3333333333333333, 0x0F0F0F0F0F0F0F0F, 0x00FF00FF00FF00FF, 0x0000FFFF0000FFFF, 0x00000000FFFFFFFF }; + static const uint64_t B[] = { 0x5555555555555555ull, 0x3333333333333333ull, 0x0F0F0F0F0F0F0F0Full, 0x00FF00FF00FF00FFull, 0x0000FFFF0000FFFFull, 0x00000000FFFFFFFFull }; count = value - ((value >> 1) & B[0]); count = ((count >> S[1]) & B[1]) + (count & B[1]); @@ -519,7 +519,7 @@ namespace etl //***************************************************************************** uint64_t binary_interleave(uint32_t first, uint32_t second) { - static const uint64_t mask[] = { 0x5555555555555555, 0x3333333333333333, 0x0F0F0F0F0F0F0F0F, 0x00FF00FF00FF00FF, 0x0000FFFF0000FFFF }; + static const uint64_t mask[] = { 0x5555555555555555ull, 0x3333333333333333ull, 0x0F0F0F0F0F0F0F0Full, 0x00FF00FF00FF00FFull, 0x0000FFFF0000FFFFull }; uint64_t f = first; uint64_t s = second; diff --git a/src/crc64_ecma.cpp b/src/crc64_ecma.cpp index f818611e..2a664f84 100644 --- a/src/crc64_ecma.cpp +++ b/src/crc64_ecma.cpp @@ -40,69 +40,69 @@ namespace etl //*************************************************************************** extern const uint64_t CRC64_ECMA[] = { - 0x0000000000000000, 0x42F0E1EBA9EA3693, 0x85E1C3D753D46D26, 0xC711223CFA3E5BB5, - 0x493366450E42ECDF, 0x0BC387AEA7A8DA4C, 0xCCD2A5925D9681F9, 0x8E224479F47CB76A, - 0x9266CC8A1C85D9BE, 0xD0962D61B56FEF2D, 0x17870F5D4F51B498, 0x5577EEB6E6BB820B, - 0xDB55AACF12C73561, 0x99A54B24BB2D03F2, 0x5EB4691841135847, 0x1C4488F3E8F96ED4, - 0x663D78FF90E185EF, 0x24CD9914390BB37C, 0xE3DCBB28C335E8C9, 0xA12C5AC36ADFDE5A, - 0x2F0E1EBA9EA36930, 0x6DFEFF5137495FA3, 0xAAEFDD6DCD770416, 0xE81F3C86649D3285, - 0xF45BB4758C645C51, 0xB6AB559E258E6AC2, 0x71BA77A2DFB03177, 0x334A9649765A07E4, - 0xBD68D2308226B08E, 0xFF9833DB2BCC861D, 0x388911E7D1F2DDA8, 0x7A79F00C7818EB3B, - 0xCC7AF1FF21C30BDE, 0x8E8A101488293D4D, 0x499B3228721766F8, 0x0B6BD3C3DBFD506B, - 0x854997BA2F81E701, 0xC7B97651866BD192, 0x00A8546D7C558A27, 0x4258B586D5BFBCB4, - 0x5E1C3D753D46D260, 0x1CECDC9E94ACE4F3, 0xDBFDFEA26E92BF46, 0x990D1F49C77889D5, - 0x172F5B3033043EBF, 0x55DFBADB9AEE082C, 0x92CE98E760D05399, 0xD03E790CC93A650A, - 0xAA478900B1228E31, 0xE8B768EB18C8B8A2, 0x2FA64AD7E2F6E317, 0x6D56AB3C4B1CD584, - 0xE374EF45BF6062EE, 0xA1840EAE168A547D, 0x66952C92ECB40FC8, 0x2465CD79455E395B, - 0x3821458AADA7578F, 0x7AD1A461044D611C, 0xBDC0865DFE733AA9, 0xFF3067B657990C3A, - 0x711223CFA3E5BB50, 0x33E2C2240A0F8DC3, 0xF4F3E018F031D676, 0xB60301F359DBE0E5, - 0xDA050215EA6C212F, 0x98F5E3FE438617BC, 0x5FE4C1C2B9B84C09, 0x1D14202910527A9A, - 0x93366450E42ECDF0, 0xD1C685BB4DC4FB63, 0x16D7A787B7FAA0D6, 0x5427466C1E109645, - 0x4863CE9FF6E9F891, 0x0A932F745F03CE02, 0xCD820D48A53D95B7, 0x8F72ECA30CD7A324, - 0x0150A8DAF8AB144E, 0x43A04931514122DD, 0x84B16B0DAB7F7968, 0xC6418AE602954FFB, - 0xBC387AEA7A8DA4C0, 0xFEC89B01D3679253, 0x39D9B93D2959C9E6, 0x7B2958D680B3FF75, - 0xF50B1CAF74CF481F, 0xB7FBFD44DD257E8C, 0x70EADF78271B2539, 0x321A3E938EF113AA, - 0x2E5EB66066087D7E, 0x6CAE578BCFE24BED, 0xABBF75B735DC1058, 0xE94F945C9C3626CB, - 0x676DD025684A91A1, 0x259D31CEC1A0A732, 0xE28C13F23B9EFC87, 0xA07CF2199274CA14, - 0x167FF3EACBAF2AF1, 0x548F120162451C62, 0x939E303D987B47D7, 0xD16ED1D631917144, - 0x5F4C95AFC5EDC62E, 0x1DBC74446C07F0BD, 0xDAAD56789639AB08, 0x985DB7933FD39D9B, - 0x84193F60D72AF34F, 0xC6E9DE8B7EC0C5DC, 0x01F8FCB784FE9E69, 0x43081D5C2D14A8FA, - 0xCD2A5925D9681F90, 0x8FDAB8CE70822903, 0x48CB9AF28ABC72B6, 0x0A3B7B1923564425, - 0x70428B155B4EAF1E, 0x32B26AFEF2A4998D, 0xF5A348C2089AC238, 0xB753A929A170F4AB, - 0x3971ED50550C43C1, 0x7B810CBBFCE67552, 0xBC902E8706D82EE7, 0xFE60CF6CAF321874, - 0xE224479F47CB76A0, 0xA0D4A674EE214033, 0x67C58448141F1B86, 0x253565A3BDF52D15, - 0xAB1721DA49899A7F, 0xE9E7C031E063ACEC, 0x2EF6E20D1A5DF759, 0x6C0603E6B3B7C1CA, - 0xF6FAE5C07D3274CD, 0xB40A042BD4D8425E, 0x731B26172EE619EB, 0x31EBC7FC870C2F78, - 0xBFC9838573709812, 0xFD39626EDA9AAE81, 0x3A28405220A4F534, 0x78D8A1B9894EC3A7, - 0x649C294A61B7AD73, 0x266CC8A1C85D9BE0, 0xE17DEA9D3263C055, 0xA38D0B769B89F6C6, - 0x2DAF4F0F6FF541AC, 0x6F5FAEE4C61F773F, 0xA84E8CD83C212C8A, 0xEABE6D3395CB1A19, - 0x90C79D3FEDD3F122, 0xD2377CD44439C7B1, 0x15265EE8BE079C04, 0x57D6BF0317EDAA97, - 0xD9F4FB7AE3911DFD, 0x9B041A914A7B2B6E, 0x5C1538ADB04570DB, 0x1EE5D94619AF4648, - 0x02A151B5F156289C, 0x4051B05E58BC1E0F, 0x87409262A28245BA, 0xC5B073890B687329, - 0x4B9237F0FF14C443, 0x0962D61B56FEF2D0, 0xCE73F427ACC0A965, 0x8C8315CC052A9FF6, - 0x3A80143F5CF17F13, 0x7870F5D4F51B4980, 0xBF61D7E80F251235, 0xFD913603A6CF24A6, - 0x73B3727A52B393CC, 0x31439391FB59A55F, 0xF652B1AD0167FEEA, 0xB4A25046A88DC879, - 0xA8E6D8B54074A6AD, 0xEA16395EE99E903E, 0x2D071B6213A0CB8B, 0x6FF7FA89BA4AFD18, - 0xE1D5BEF04E364A72, 0xA3255F1BE7DC7CE1, 0x64347D271DE22754, 0x26C49CCCB40811C7, - 0x5CBD6CC0CC10FAFC, 0x1E4D8D2B65FACC6F, 0xD95CAF179FC497DA, 0x9BAC4EFC362EA149, - 0x158E0A85C2521623, 0x577EEB6E6BB820B0, 0x906FC95291867B05, 0xD29F28B9386C4D96, - 0xCEDBA04AD0952342, 0x8C2B41A1797F15D1, 0x4B3A639D83414E64, 0x09CA82762AAB78F7, - 0x87E8C60FDED7CF9D, 0xC51827E4773DF90E, 0x020905D88D03A2BB, 0x40F9E43324E99428, - 0x2CFFE7D5975E55E2, 0x6E0F063E3EB46371, 0xA91E2402C48A38C4, 0xEBEEC5E96D600E57, - 0x65CC8190991CB93D, 0x273C607B30F68FAE, 0xE02D4247CAC8D41B, 0xA2DDA3AC6322E288, - 0xBE992B5F8BDB8C5C, 0xFC69CAB42231BACF, 0x3B78E888D80FE17A, 0x7988096371E5D7E9, - 0xF7AA4D1A85996083, 0xB55AACF12C735610, 0x724B8ECDD64D0DA5, 0x30BB6F267FA73B36, - 0x4AC29F2A07BFD00D, 0x08327EC1AE55E69E, 0xCF235CFD546BBD2B, 0x8DD3BD16FD818BB8, - 0x03F1F96F09FD3CD2, 0x41011884A0170A41, 0x86103AB85A2951F4, 0xC4E0DB53F3C36767, - 0xD8A453A01B3A09B3, 0x9A54B24BB2D03F20, 0x5D45907748EE6495, 0x1FB5719CE1045206, - 0x919735E51578E56C, 0xD367D40EBC92D3FF, 0x1476F63246AC884A, 0x568617D9EF46BED9, - 0xE085162AB69D5E3C, 0xA275F7C11F7768AF, 0x6564D5FDE549331A, 0x279434164CA30589, - 0xA9B6706FB8DFB2E3, 0xEB46918411358470, 0x2C57B3B8EB0BDFC5, 0x6EA7525342E1E956, - 0x72E3DAA0AA188782, 0x30133B4B03F2B111, 0xF7021977F9CCEAA4, 0xB5F2F89C5026DC37, - 0x3BD0BCE5A45A6B5D, 0x79205D0E0DB05DCE, 0xBE317F32F78E067B, 0xFCC19ED95E6430E8, - 0x86B86ED5267CDBD3, 0xC4488F3E8F96ED40, 0x0359AD0275A8B6F5, 0x41A94CE9DC428066, - 0xCF8B0890283E370C, 0x8D7BE97B81D4019F, 0x4A6ACB477BEA5A2A, 0x089A2AACD2006CB9, - 0x14DEA25F3AF9026D, 0x562E43B4931334FE, 0x913F6188692D6F4B, 0xD3CF8063C0C759D8, - 0x5DEDC41A34BBEEB2, 0x1F1D25F19D51D821, 0xD80C07CD676F8394, 0x9AFCE626CE85B507 + 0x0000000000000000ull, 0x42F0E1EBA9EA3693ull, 0x85E1C3D753D46D26ull, 0xC711223CFA3E5BB5ull, + 0x493366450E42ECDFull, 0x0BC387AEA7A8DA4Cull, 0xCCD2A5925D9681F9ull, 0x8E224479F47CB76Aull, + 0x9266CC8A1C85D9BEull, 0xD0962D61B56FEF2Dull, 0x17870F5D4F51B498ull, 0x5577EEB6E6BB820Bull, + 0xDB55AACF12C73561ull, 0x99A54B24BB2D03F2ull, 0x5EB4691841135847ull, 0x1C4488F3E8F96ED4ull, + 0x663D78FF90E185EFull, 0x24CD9914390BB37Cull, 0xE3DCBB28C335E8C9ull, 0xA12C5AC36ADFDE5Aull, + 0x2F0E1EBA9EA36930ull, 0x6DFEFF5137495FA3ull, 0xAAEFDD6DCD770416ull, 0xE81F3C86649D3285ull, + 0xF45BB4758C645C51ull, 0xB6AB559E258E6AC2ull, 0x71BA77A2DFB03177ull, 0x334A9649765A07E4ull, + 0xBD68D2308226B08Eull, 0xFF9833DB2BCC861Dull, 0x388911E7D1F2DDA8ull, 0x7A79F00C7818EB3Bull, + 0xCC7AF1FF21C30BDEull, 0x8E8A101488293D4Dull, 0x499B3228721766F8ull, 0x0B6BD3C3DBFD506Bull, + 0x854997BA2F81E701ull, 0xC7B97651866BD192ull, 0x00A8546D7C558A27ull, 0x4258B586D5BFBCB4ull, + 0x5E1C3D753D46D260ull, 0x1CECDC9E94ACE4F3ull, 0xDBFDFEA26E92BF46ull, 0x990D1F49C77889D5ull, + 0x172F5B3033043EBFull, 0x55DFBADB9AEE082Cull, 0x92CE98E760D05399ull, 0xD03E790CC93A650Aull, + 0xAA478900B1228E31ull, 0xE8B768EB18C8B8A2ull, 0x2FA64AD7E2F6E317ull, 0x6D56AB3C4B1CD584ull, + 0xE374EF45BF6062EEull, 0xA1840EAE168A547Dull, 0x66952C92ECB40FC8ull, 0x2465CD79455E395Bull, + 0x3821458AADA7578Full, 0x7AD1A461044D611Cull, 0xBDC0865DFE733AA9ull, 0xFF3067B657990C3Aull, + 0x711223CFA3E5BB50ull, 0x33E2C2240A0F8DC3ull, 0xF4F3E018F031D676ull, 0xB60301F359DBE0E5ull, + 0xDA050215EA6C212Full, 0x98F5E3FE438617BCull, 0x5FE4C1C2B9B84C09ull, 0x1D14202910527A9Aull, + 0x93366450E42ECDF0ull, 0xD1C685BB4DC4FB63ull, 0x16D7A787B7FAA0D6ull, 0x5427466C1E109645ull, + 0x4863CE9FF6E9F891ull, 0x0A932F745F03CE02ull, 0xCD820D48A53D95B7ull, 0x8F72ECA30CD7A324ull, + 0x0150A8DAF8AB144Eull, 0x43A04931514122DDull, 0x84B16B0DAB7F7968ull, 0xC6418AE602954FFBull, + 0xBC387AEA7A8DA4C0ull, 0xFEC89B01D3679253ull, 0x39D9B93D2959C9E6ull, 0x7B2958D680B3FF75ull, + 0xF50B1CAF74CF481Full, 0xB7FBFD44DD257E8Cull, 0x70EADF78271B2539ull, 0x321A3E938EF113AAull, + 0x2E5EB66066087D7Eull, 0x6CAE578BCFE24BEDull, 0xABBF75B735DC1058ull, 0xE94F945C9C3626CBull, + 0x676DD025684A91A1ull, 0x259D31CEC1A0A732ull, 0xE28C13F23B9EFC87ull, 0xA07CF2199274CA14ull, + 0x167FF3EACBAF2AF1ull, 0x548F120162451C62ull, 0x939E303D987B47D7ull, 0xD16ED1D631917144ull, + 0x5F4C95AFC5EDC62Eull, 0x1DBC74446C07F0BDull, 0xDAAD56789639AB08ull, 0x985DB7933FD39D9Bull, + 0x84193F60D72AF34Full, 0xC6E9DE8B7EC0C5DCull, 0x01F8FCB784FE9E69ull, 0x43081D5C2D14A8FAull, + 0xCD2A5925D9681F90ull, 0x8FDAB8CE70822903ull, 0x48CB9AF28ABC72B6ull, 0x0A3B7B1923564425ull, + 0x70428B155B4EAF1Eull, 0x32B26AFEF2A4998Dull, 0xF5A348C2089AC238ull, 0xB753A929A170F4ABull, + 0x3971ED50550C43C1ull, 0x7B810CBBFCE67552ull, 0xBC902E8706D82EE7ull, 0xFE60CF6CAF321874ull, + 0xE224479F47CB76A0ull, 0xA0D4A674EE214033ull, 0x67C58448141F1B86ull, 0x253565A3BDF52D15ull, + 0xAB1721DA49899A7Full, 0xE9E7C031E063ACECull, 0x2EF6E20D1A5DF759ull, 0x6C0603E6B3B7C1CAull, + 0xF6FAE5C07D3274CDull, 0xB40A042BD4D8425Eull, 0x731B26172EE619EBull, 0x31EBC7FC870C2F78ull, + 0xBFC9838573709812ull, 0xFD39626EDA9AAE81ull, 0x3A28405220A4F534ull, 0x78D8A1B9894EC3A7ull, + 0x649C294A61B7AD73ull, 0x266CC8A1C85D9BE0ull, 0xE17DEA9D3263C055ull, 0xA38D0B769B89F6C6ull, + 0x2DAF4F0F6FF541ACull, 0x6F5FAEE4C61F773Full, 0xA84E8CD83C212C8Aull, 0xEABE6D3395CB1A19ull, + 0x90C79D3FEDD3F122ull, 0xD2377CD44439C7B1ull, 0x15265EE8BE079C04ull, 0x57D6BF0317EDAA97ull, + 0xD9F4FB7AE3911DFDull, 0x9B041A914A7B2B6Eull, 0x5C1538ADB04570DBull, 0x1EE5D94619AF4648ull, + 0x02A151B5F156289Cull, 0x4051B05E58BC1E0Full, 0x87409262A28245BAull, 0xC5B073890B687329ull, + 0x4B9237F0FF14C443ull, 0x0962D61B56FEF2D0ull, 0xCE73F427ACC0A965ull, 0x8C8315CC052A9FF6ull, + 0x3A80143F5CF17F13ull, 0x7870F5D4F51B4980ull, 0xBF61D7E80F251235ull, 0xFD913603A6CF24A6ull, + 0x73B3727A52B393CCull, 0x31439391FB59A55Full, 0xF652B1AD0167FEEAull, 0xB4A25046A88DC879ull, + 0xA8E6D8B54074A6ADull, 0xEA16395EE99E903Eull, 0x2D071B6213A0CB8Bull, 0x6FF7FA89BA4AFD18ull, + 0xE1D5BEF04E364A72ull, 0xA3255F1BE7DC7CE1ull, 0x64347D271DE22754ull, 0x26C49CCCB40811C7ull, + 0x5CBD6CC0CC10FAFCull, 0x1E4D8D2B65FACC6Full, 0xD95CAF179FC497DAull, 0x9BAC4EFC362EA149ull, + 0x158E0A85C2521623ull, 0x577EEB6E6BB820B0ull, 0x906FC95291867B05ull, 0xD29F28B9386C4D96ull, + 0xCEDBA04AD0952342ull, 0x8C2B41A1797F15D1ull, 0x4B3A639D83414E64ull, 0x09CA82762AAB78F7ull, + 0x87E8C60FDED7CF9Dull, 0xC51827E4773DF90Eull, 0x020905D88D03A2BBull, 0x40F9E43324E99428ull, + 0x2CFFE7D5975E55E2ull, 0x6E0F063E3EB46371ull, 0xA91E2402C48A38C4ull, 0xEBEEC5E96D600E57ull, + 0x65CC8190991CB93Dull, 0x273C607B30F68FAEull, 0xE02D4247CAC8D41Bull, 0xA2DDA3AC6322E288ull, + 0xBE992B5F8BDB8C5Cull, 0xFC69CAB42231BACFull, 0x3B78E888D80FE17Aull, 0x7988096371E5D7E9ull, + 0xF7AA4D1A85996083ull, 0xB55AACF12C735610ull, 0x724B8ECDD64D0DA5ull, 0x30BB6F267FA73B36ull, + 0x4AC29F2A07BFD00Dull, 0x08327EC1AE55E69Eull, 0xCF235CFD546BBD2Bull, 0x8DD3BD16FD818BB8ull, + 0x03F1F96F09FD3CD2ull, 0x41011884A0170A41ull, 0x86103AB85A2951F4ull, 0xC4E0DB53F3C36767ull, + 0xD8A453A01B3A09B3ull, 0x9A54B24BB2D03F20ull, 0x5D45907748EE6495ull, 0x1FB5719CE1045206ull, + 0x919735E51578E56Cull, 0xD367D40EBC92D3FFull, 0x1476F63246AC884Aull, 0x568617D9EF46BED9ull, + 0xE085162AB69D5E3Cull, 0xA275F7C11F7768AFull, 0x6564D5FDE549331Aull, 0x279434164CA30589ull, + 0xA9B6706FB8DFB2E3ull, 0xEB46918411358470ull, 0x2C57B3B8EB0BDFC5ull, 0x6EA7525342E1E956ull, + 0x72E3DAA0AA188782ull, 0x30133B4B03F2B111ull, 0xF7021977F9CCEAA4ull, 0xB5F2F89C5026DC37ull, + 0x3BD0BCE5A45A6B5Dull, 0x79205D0E0DB05DCEull, 0xBE317F32F78E067Bull, 0xFCC19ED95E6430E8ull, + 0x86B86ED5267CDBD3ull, 0xC4488F3E8F96ED40ull, 0x0359AD0275A8B6F5ull, 0x41A94CE9DC428066ull, + 0xCF8B0890283E370Cull, 0x8D7BE97B81D4019Full, 0x4A6ACB477BEA5A2Aull, 0x089A2AACD2006CB9ull, + 0x14DEA25F3AF9026Dull, 0x562E43B4931334FEull, 0x913F6188692D6F4Bull, 0xD3CF8063C0C759D8ull, + 0x5DEDC41A34BBEEB2ull, 0x1F1D25F19D51D821ull, 0xD80C07CD676F8394ull, 0x9AFCE626CE85B507ull }; } diff --git a/support/Release notes.txt b/support/Release notes.txt index d6100415..d3293ecf 100644 --- a/support/Release notes.txt +++ b/support/Release notes.txt @@ -1,3 +1,7 @@ +=============================================================================== +11.16.5 +Added 'ull' suffix to 64bit literals + =============================================================================== 11.16.4 Fixed nullptr compatibility for ARM5 compiler. From 9302a2a2b75bf544f42b93f09132f8c497b93012 Mon Sep 17 00:00:00 2001 From: John Wellbelove Date: Tue, 4 Sep 2018 23:27:56 +0100 Subject: [PATCH 05/12] Merge remote-tracking branch 'origin/development' --- include/etl/map.h | 49 +++++++++++++++++++++++++----------------- include/etl/multimap.h | 49 +++++++++++++++++++++++++----------------- include/etl/multiset.h | 38 ++++++++++++++------------------ include/etl/set.h | 38 ++++++++++++++------------------ test/test_map.cpp | 37 +++++++++++++++++++++++++++++++ test/test_multimap.cpp | 37 +++++++++++++++++++++++++++++++ test/test_multiset.cpp | 37 +++++++++++++++++++++++++++++++ test/test_set.cpp | 37 +++++++++++++++++++++++++++++++ 8 files changed, 238 insertions(+), 84 deletions(-) diff --git a/include/etl/map.h b/include/etl/map.h index 785e566f..e5529ce3 100644 --- a/include/etl/map.h +++ b/include/etl/map.h @@ -474,26 +474,18 @@ namespace etl typedef const value_type* const_pointer; typedef size_t size_type; - //************************************************************************* - /// How to compare two key elements. - //************************************************************************* - struct key_comp + class value_compare { - bool operator ()(const key_type& key1, const key_type& key2) const - { - return compare(key1, key2); - } - }; + public: - //************************************************************************* - /// How to compare two value elements. - //************************************************************************* - struct value_comp - { - bool operator ()(const value_type& value1, const value_type& value2) const + bool operator()(const value_type& lhs, const value_type& rhs) const { - return compare(value1.first, value2.first); + return (kcompare(lhs.first, rhs.first)); } + + private: + + key_compare kcompare; }; protected: @@ -524,15 +516,15 @@ namespace etl //************************************************************************* bool node_comp(const Data_Node& node1, const Data_Node& node2) const { - return compare(node1.value.first, node2.value.first); + return kcompare(node1.value.first, node2.value.first); } bool node_comp(const Data_Node& node, key_parameter_t key) const { - return compare(node.value.first, key); + return kcompare(node.value.first, key); } bool node_comp(key_parameter_t key, const Data_Node& node) const { - return compare(key, node.value.first); + return kcompare(key, node.value.first); } private: @@ -540,7 +532,8 @@ namespace etl /// The pool of data nodes used in the map. ipool* p_node_pool; - key_compare compare; + key_compare kcompare; + value_compare vcompare; //************************************************************************* /// Downcast a Node* to a Data_Node* @@ -1236,6 +1229,22 @@ namespace etl return *this; } + //************************************************************************* + /// How to compare two key elements. + //************************************************************************* + key_compare key_comp() const + { + return kcompare; + }; + + //************************************************************************* + /// How to compare two value elements. + //************************************************************************* + value_compare value_comp() const + { + return vcompare; + }; + protected: //************************************************************************* diff --git a/include/etl/multimap.h b/include/etl/multimap.h index 8f151884..a50f0aa3 100644 --- a/include/etl/multimap.h +++ b/include/etl/multimap.h @@ -631,26 +631,18 @@ namespace etl typedef const value_type* const_pointer; typedef size_t size_type; - //************************************************************************* - /// How to compare two key elements. - //************************************************************************* - struct key_comp + class value_compare { - bool operator ()(const key_type& key1, const key_type& key2) const - { - return compare(key1, key2); - } - }; + public: - //************************************************************************* - /// How to compare two value elements. - //************************************************************************* - struct value_comp - { - bool operator ()(const value_type& value1, const value_type& value2) const + bool operator()(const value_type& lhs, const value_type& rhs) const { - return compare(value1.first, value2.first); + return (kcompare(lhs.first, rhs.first)); } + + private: + + key_compare kcompare; }; protected: @@ -676,17 +668,17 @@ namespace etl //************************************************************************* bool node_comp(const Data_Node& node1, const Data_Node& node2) const { - return compare(node1.value.first, node2.value.first); + return kcompare(node1.value.first, node2.value.first); } bool node_comp(const Data_Node& node, key_parameter_t key) const { - return compare(node.value.first, key); + return kcompare(node.value.first, key); } bool node_comp(key_parameter_t key, const Data_Node& node) const { - return compare(key, node.value.first); + return kcompare(key, node.value.first); } private: @@ -694,7 +686,8 @@ namespace etl /// The pool of data nodes used in the multimap. ipool* p_node_pool; - key_compare compare; + key_compare kcompare; + value_compare vcompare; //************************************************************************* /// Downcast a Node* to a Data_Node* @@ -1330,6 +1323,22 @@ namespace etl return *this; } + //************************************************************************* + /// How to compare two key elements. + //************************************************************************* + key_compare key_comp() const + { + return kcompare; + }; + + //************************************************************************* + /// How to compare two value elements. + //************************************************************************* + value_compare value_comp() const + { + return vcompare; + }; + protected: //************************************************************************* diff --git a/include/etl/multiset.h b/include/etl/multiset.h index 8f78dc7f..cf79c76e 100644 --- a/include/etl/multiset.h +++ b/include/etl/multiset.h @@ -629,28 +629,6 @@ namespace etl typedef value_type* const_pointer; typedef size_t size_type; - //************************************************************************* - /// How to compare two key elements. - //************************************************************************* - struct key_comp - { - bool operator ()(key_type& key1, key_type& key2) const - { - return compare(key1, key2); - } - }; - - //************************************************************************* - /// How to compare two value elements. - //************************************************************************* - struct value_comp - { - bool operator ()(value_type& value1, value_type& value2) const - { - return compare(value1, value2); - } - }; - protected: //************************************************************************* @@ -1311,6 +1289,22 @@ namespace etl return *this; } + //************************************************************************* + /// How to compare two key elements. + //************************************************************************* + key_compare key_comp() const + { + return compare; + }; + + //************************************************************************* + /// How to compare two value elements. + //************************************************************************* + value_compare value_comp() const + { + return compare; + }; + protected: //************************************************************************* diff --git a/include/etl/set.h b/include/etl/set.h index 9736b005..26a172ce 100644 --- a/include/etl/set.h +++ b/include/etl/set.h @@ -467,28 +467,6 @@ namespace etl typedef value_type* const_pointer; typedef size_t size_type; - //************************************************************************* - /// How to compare two key elements. - //************************************************************************* - struct key_comp - { - bool operator ()(key_type& key1, key_type& key2) const - { - return compare(key1, key2); - } - }; - - //************************************************************************* - /// How to compare two value elements. - //************************************************************************* - struct value_comp - { - bool operator ()(value_type& value1, value_type& value2) const - { - return compare(value1, value2); - } - }; - protected: //************************************************************************* @@ -1159,6 +1137,22 @@ namespace etl return const_iterator(*this, find_upper_node(root_node, key)); } + //************************************************************************* + /// How to compare two key elements. + //************************************************************************* + key_compare key_comp() const + { + return compare; + }; + + //************************************************************************* + /// How to compare two value elements. + //************************************************************************* + value_compare value_comp() const + { + return compare; + }; + protected: //************************************************************************* diff --git a/test/test_map.cpp b/test/test_map.cpp index c1cdedec..686089e1 100644 --- a/test/test_map.cpp +++ b/test/test_map.cpp @@ -1055,5 +1055,42 @@ namespace #endif } + //************************************************************************* + TEST_FIXTURE(SetupFixture, test_key_compare) + { + const Data data(initial_data.begin(), initial_data.end()); + + Data::key_compare compare = data.key_comp(); + + Data::key_type a("A"); + Data::key_type b("B"); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } + + //************************************************************************* + TEST_FIXTURE(SetupFixture, test_value_compare) + { + const Data data(initial_data.begin(), initial_data.end()); + + Data::value_compare compare = data.value_comp(); + + Data::value_type a(std::string("A"), 0); + Data::value_type b(std::string("B"), 1); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } }; } diff --git a/test/test_multimap.cpp b/test/test_multimap.cpp index 018ff277..c221a34d 100644 --- a/test/test_multimap.cpp +++ b/test/test_multimap.cpp @@ -1010,5 +1010,42 @@ namespace #endif } + //************************************************************************* + TEST_FIXTURE(SetupFixture, test_key_compare) + { + const Data data(initial_data.begin(), initial_data.end()); + + Data::key_compare compare = data.key_comp(); + + Data::key_type a("A"); + Data::key_type b("B"); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } + + //************************************************************************* + TEST_FIXTURE(SetupFixture, test_value_compare) + { + const Data data(initial_data.begin(), initial_data.end()); + + Data::value_compare compare = data.value_comp(); + + Data::value_type a(std::string("A"), 0); + Data::value_type b(std::string("B"), 1); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } }; } diff --git a/test/test_multiset.cpp b/test/test_multiset.cpp index 14982819..28397153 100644 --- a/test/test_multiset.cpp +++ b/test/test_multiset.cpp @@ -968,5 +968,42 @@ namespace #endif } + //************************************************************************* + TEST_FIXTURE(SetupFixture, test_key_compare) + { + const Data data(initial_data.begin(), initial_data.end()); + + Data::key_compare compare = data.key_comp(); + + Data::key_type a(1); + Data::key_type b(2); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } + + //************************************************************************* + TEST_FIXTURE(SetupFixture, test_value_compare) + { + const Data data(initial_data.begin(), initial_data.end()); + + Data::value_compare compare = data.value_comp(); + + Data::value_type a(1); + Data::value_type b(2); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } }; } diff --git a/test/test_set.cpp b/test/test_set.cpp index 57bfc7ea..7892c8b5 100644 --- a/test/test_set.cpp +++ b/test/test_set.cpp @@ -945,5 +945,42 @@ namespace #endif } + //************************************************************************* + TEST_FIXTURE(SetupFixture, test_key_compare) + { + const Data data(initial_data.begin(), initial_data.end()); + + Data::key_compare compare = data.key_comp(); + + Data::key_type a(1); + Data::key_type b(2); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } + + //************************************************************************* + TEST_FIXTURE(SetupFixture, test_value_compare) + { + const Data data(initial_data.begin(), initial_data.end()); + + Data::value_compare compare = data.value_comp(); + + Data::value_type a(1); + Data::value_type b(2); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } }; } From ede3a19edd781732bc048c96cbfc3478ad1676ab Mon Sep 17 00:00:00 2001 From: John Wellbelove Date: Sat, 8 Sep 2018 15:57:37 +0100 Subject: [PATCH 06/12] Merge remote-tracking branch 'origin/development' # Conflicts: # include/etl/version.h # support/Release notes.txt # test/vs2017/etl.vcxproj.filters --- include/etl/list.h | 4 +- include/etl/platform.h | 12 +- include/etl/profiles/cpp17.h | 48 ++++ include/etl/profiles/cpp17_no_stl.h | 49 ++++ include/etl/profiles/etl_profile.h | 6 +- include/etl/state_chart.h | 289 +++++++++++++++++++++ include/etl/version.h | 12 +- support/Release notes.txt | 8 + test/codeblocks/ETL.cbp | 2 + test/test_state_chart.cpp | 387 ++++++++++++++++++++++++++++ test/vs2017/cpp.hint | 8 + test/vs2017/etl.vcxproj | 3 + test/vs2017/etl.vcxproj.filters | 7 + 13 files changed, 824 insertions(+), 11 deletions(-) create mode 100644 include/etl/profiles/cpp17.h create mode 100644 include/etl/profiles/cpp17_no_stl.h create mode 100644 include/etl/state_chart.h create mode 100644 test/test_state_chart.cpp create mode 100644 test/vs2017/cpp.hint diff --git a/include/etl/list.h b/include/etl/list.h index 84045b1b..4adedcab 100644 --- a/include/etl/list.h +++ b/include/etl/list.h @@ -392,8 +392,8 @@ namespace etl etl::ipool* p_node_pool; ///< The pool of data nodes used in the list. node_t terminal_node; ///< The node that acts as the list start and end. size_type MAX_SIZE; ///< The maximum size of the list. - bool pool_is_shared; ///< If true then the pool is shared between lists. - ETL_DECLARE_DEBUG_COUNT; ///< Internal debugging. + bool pool_is_shared; ///< If true then the pool is shared between lists. + ETL_DECLARE_DEBUG_COUNT ///< Internal debugging. }; //*************************************************************************** diff --git a/include/etl/platform.h b/include/etl/platform.h index 0034c1cc..cab27d25 100644 --- a/include/etl/platform.h +++ b/include/etl/platform.h @@ -69,7 +69,11 @@ SOFTWARE. #endif #if defined(ETL_COMPILER_GCC) - #define GCC_VERSION ((__GNUC__ * 10000) + (__GNUC_MINOR__ * 100) + __GNUC_PATCHLEVEL__) + #define ETL_COMPILER_VERSION __GNUC__ + #define ETL_COMPILER_FULL_VERSION ((__GNUC__ * 10000) + (__GNUC_MINOR__ * 100) + __GNUC_PATCHLEVEL__) +#elif defined ETL_COMPILER_MICROSOFT + #define ETL_COMPILER_VERSION _MSC_VER + #define ETL_COMPILER_FULL_VERSION _MSC_FULL_VER #endif #if ETL_CPP11_SUPPORTED @@ -84,4 +88,10 @@ SOFTWARE. #define ETL_IF_CONSTEXPR #endif +#if ETL_CPP11_SUPPORTED + #define ETL_DELETE = delete +#else + #define ETL_DELETE +#endif + #endif diff --git a/include/etl/profiles/cpp17.h b/include/etl/profiles/cpp17.h new file mode 100644 index 00000000..d65c45e6 --- /dev/null +++ b/include/etl/profiles/cpp17.h @@ -0,0 +1,48 @@ +///\file + +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2018 jwellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#ifndef ETL_CPP17_INCLUDED +#define ETL_CPP17_INCLUDED + +//***************************************************************************** +// Generic C++17 +//***************************************************************************** + +#define ETL_TARGET_DEVICE_GENERIC +#define ETL_TARGET_OS_NONE +#define ETL_COMPILER_GENERIC +#define ETL_CPP11_SUPPORTED 1 +#define ETL_CPP14_SUPPORTED 1 +#define ETL_CPP17_SUPPORTED 1 +#define ETL_NO_NULLPTR_SUPPORT 0 +#define ETL_NO_LARGE_CHAR_SUPPORT 0 +#define ETL_CPP11_TYPE_TRAITS_IS_TRIVIAL_SUPPORTED 1 + +#endif diff --git a/include/etl/profiles/cpp17_no_stl.h b/include/etl/profiles/cpp17_no_stl.h new file mode 100644 index 00000000..46b67c53 --- /dev/null +++ b/include/etl/profiles/cpp17_no_stl.h @@ -0,0 +1,49 @@ +///\file + +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2018 jwellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#ifndef ETL_CPP17_NO_STL_INCLUDED +#define ETL_CPP17_NO_STL_INCLUDED + +//***************************************************************************** +// Generic C++17 without STL support +//***************************************************************************** + +#define ETL_TARGET_DEVICE_GENERIC +#define ETL_TARGET_OS_NONE +#define ETL_COMPILER_GENERIC +#define ETL_CPP11_SUPPORTED 1 +#define ETL_CPP14_SUPPORTED 1 +#define ETL_CPP17_SUPPORTED 1 +#define ETL_NO_NULLPTR_SUPPORT 0 +#define ETL_NO_LARGE_CHAR_SUPPORT 0 +#define ETL_CPP11_TYPE_TRAITS_IS_TRIVIAL_SUPPORTED 0 +#define ETL_NO_STL + +#endif diff --git a/include/etl/profiles/etl_profile.h b/include/etl/profiles/etl_profile.h index 45596b1a..187bcb5b 100644 --- a/include/etl/profiles/etl_profile.h +++ b/include/etl/profiles/etl_profile.h @@ -29,7 +29,7 @@ SOFTWARE. ******************************************************************************/ #ifndef __ETL_PROFILE_H__ #define __ETL_PROFILE_H__ -#ifdef PROFILE_MSVC +#ifdef PROFILE_MSVC #include "msvc_x86.h" #elif PROFILE_GCC_GENERIC #include "gcc_generic.h" @@ -51,9 +51,11 @@ SOFTWARE. #include "cpp11.h" #elif PROFILE_CPP14_GENERIC #include "cpp14.h" +#elif PROFILE_CPP17_GENERIC + #include "cpp17.h" #elif PROFILE_CUSTOM #include "custom_profile.h" -#else +#else #error Must provide a profile header file when buiding ETL. See https://www.etlcpp.com/setup.html #endif diff --git a/include/etl/state_chart.h b/include/etl/state_chart.h new file mode 100644 index 00000000..692c6322 --- /dev/null +++ b/include/etl/state_chart.h @@ -0,0 +1,289 @@ +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2018 jwellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#ifndef ETL_STATE_CHART_INCLUDED +#define ETL_STATE_CHART_INCLUDED + +#include + +#include "etl/platform.h" +#include "etl/nullptr.h" +#include "etl/array.h" +#include "etl/array_view.h" + +namespace etl +{ + //*************************************************************************** + /// Simple Finite State Machine Interface + //*************************************************************************** + class istate_chart + { + public: + + typedef uint32_t state_id_t; + typedef uint32_t event_id_t; + + virtual state_id_t get_state_id() const = 0; + virtual void process_event(const event_id_t event_id) = 0; + + virtual ~istate_chart() + { + } + }; + + //*************************************************************************** + /// Simple Finite State Machine + //*************************************************************************** + template + class state_chart : public istate_chart + { + public: + + //************************************************************************* + /// Transition definition + //************************************************************************* + struct transition + { + transition(const event_id_t event_id_, + const state_id_t current_state_id_, + const state_id_t next_state_id_, + void (TObject::* const action_)() = nullptr, + bool (TObject::* const guard_)() = nullptr) + : event_id(event_id_), + current_state_id(current_state_id_), + next_state_id(next_state_id_), + action(action_), + guard(guard_) + { + } + + const event_id_t event_id; + const state_id_t current_state_id; + const state_id_t next_state_id; + void (TObject::* const action)(); + bool (TObject::* const guard)(); + }; + + //************************************************************************* + /// State definition + //************************************************************************* + struct state + { + state(const state_id_t state_id_, + void (TObject::* const on_entry_)() = nullptr, + void (TObject::* const on_exit_)() = nullptr) + : state_id(state_id_), + on_entry(on_entry_), + on_exit(on_exit_) + { + } + + state_id_t state_id; + void (TObject::* const on_entry)(); + void (TObject::* const on_exit)(); + }; + + //************************************************************************* + /// Constructor. + /// \tparam TRANSITION_TABLE_SIZE The transition table size. + /// \param object_ A reference to the implementation object. + /// \param transition_table_ The table of transitions. + /// \param state_id_ The initial state id. + //************************************************************************* + template + state_chart(TObject& object_, + const etl::array& transition_table_, + const state_id_t state_id_) + : object(object_), + current_state_id(state_id_), + transition_table(transition_table_.begin(), transition_table_.end()) + { + } + + //************************************************************************* + /// Sets the state table. + /// \tparam STATE_TABLE_SIZE The state table size. + /// \param state_table_ A reference to the state table. + //************************************************************************* + template + void set_state_table(const etl::array& state_table_) + { + state_table.assign(state_table_.begin(), state_table_.end()); + } + + //************************************************************************* + /// Gets a reference to the implementation object. + /// \return Reference to the implementation object. + //************************************************************************* + TObject& get_object() + { + return object; + } + + //************************************************************************* + /// Gets a const reference to the implementation object. + /// \return Const reference to the implementation object. + //************************************************************************* + const TObject& get_object() const + { + return object; + } + + //************************************************************************* + /// Gets the current state id. + /// \return The current state id. + //************************************************************************* + state_id_t get_state_id() const + { + return current_state_id; + } + + //************************************************************************* + /// Gets the current state id. + /// \return The current state id. + //************************************************************************* + const state* find_state(state_id_t state_id) + { + if (state_table.empty()) + { + return state_table.end(); + } + else + { + return std::find_if(state_table.begin(), + state_table.end(), + is_state(state_id)); + } + } + + //************************************************************************* + /// Processes the specified event. + /// The state machine will action the first item in the transition table + /// that satisfies the conditions for executing the action. + /// \param event_id The id of the event to process. + //************************************************************************* + void process_event(const event_id_t event_id) + { + // Scan the transition table. + const transition* t = std::find_if(transition_table.begin(), + transition_table.end(), + is_transition(event_id, current_state_id)); + + // Found an entry? + if (t != transition_table.end()) + { + // Shall we execute the transition? + if ((t->guard == nullptr) || ((object.*t->guard)())) + { + const bool to_new_state = (current_state_id != t->next_state_id); + + // Execute the state exit if necessary. + if (to_new_state) + { + // See if we have a state item for the current state. + const state* s = find_state(current_state_id); + + // If the current state has an 'on_exit' then call it. + if ((s != state_table.end()) && (s->on_exit != nullptr)) + { + (object.*(s->on_exit))(); + } + } + + // Shall we execute the action? + if (t->action != nullptr) + { + (object.*t->action)(); + } + + // Execute the state entry if necessary. + if (to_new_state) + { + // See if we have a state item for the next state. + const state* s = find_state(t->next_state_id); + + // If the new state has an 'on_entry' then call it. + if ((s != state_table.end()) && (s->on_entry != nullptr)) + { + (object.*(s->on_entry))(); + } + } + + current_state_id = t->next_state_id; + } + } + } + + private: + + //************************************************************************* + struct is_transition + { + is_transition(event_id_t event_id_, state_id_t state_id_) + : event_id(event_id_), + state_id(state_id_) + { + } + + bool operator()(const transition& t) const + { + return (t.event_id == event_id) && (t.current_state_id == state_id); + } + + const event_id_t event_id; + const state_id_t state_id; + }; + + //************************************************************************* + struct is_state + { + is_state(state_id_t state_id_) + : state_id(state_id_) + { + } + + bool operator()(const state& s) const + { + return (s.state_id == state_id); + } + + const state_id_t state_id; + }; + + // Disabled + state_chart(const state_chart&) ETL_DELETE; + state_chart& operator =(const state_chart&) ETL_DELETE; + + TObject& object; ///< The object that supplies guard and action member functions. + state_id_t current_state_id; ///< The current state id. + const etl::array_view transition_table; ///< The table of transitions. + etl::array_view state_table; ///< The table of states. + }; +} + +#endif diff --git a/include/etl/version.h b/include/etl/version.h index 32094197..c5444289 100644 --- a/include/etl/version.h +++ b/include/etl/version.h @@ -37,13 +37,13 @@ SOFTWARE. /// Definitions of the ETL version ///\ingroup utilities -#define ETL_VERSION "11.16.5" -#define ETL_VERSION_W L"11.16.5" -#define ETL_VERSION_U16 u"11.16.5" -#define ETL_VERSION_U32 U"11.16.5" +#define ETL_VERSION "11.17.0" +#define ETL_VERSION_W L"11.17.0" +#define ETL_VERSION_U16 u"11.17.0" +#define ETL_VERSION_U32 U"11.17.0" #define ETL_VERSION_MAJOR 11 -#define ETL_VERSION_MINOR 16 -#define ETL_VERSION_PATCH 5 +#define ETL_VERSION_MINOR 17 +#define ETL_VERSION_PATCH 0 #define ETL_VERSION_VALUE ((ETL_VERSION_MAJOR * 10000) + (ETL_VERSION_MINOR * 100) + ETL_VERSION_PATCH) #endif diff --git a/support/Release notes.txt b/support/Release notes.txt index d3293ecf..69a38502 100644 --- a/support/Release notes.txt +++ b/support/Release notes.txt @@ -1,3 +1,11 @@ +=============================================================================== +11.17.0 +Added etl::state_chart + +=============================================================================== +11.16.6 +Fixed implementations of key_comp and value_comp for maps and sets + =============================================================================== 11.16.5 Added 'ull' suffix to 64bit literals diff --git a/test/codeblocks/ETL.cbp b/test/codeblocks/ETL.cbp index e66e4acd..b4a78c2f 100644 --- a/test/codeblocks/ETL.cbp +++ b/test/codeblocks/ETL.cbp @@ -279,6 +279,7 @@ + @@ -423,6 +424,7 @@ + diff --git a/test/test_state_chart.cpp b/test/test_state_chart.cpp new file mode 100644 index 00000000..a7730ce8 --- /dev/null +++ b/test/test_state_chart.cpp @@ -0,0 +1,387 @@ +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2018 jwellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#include "UnitTest++.h" + +#include "etl/state_chart.h" +#include "etl/enum_type.h" +#include "etl/queue.h" +#include "etl/array.h" + +#include + +namespace +{ + //*************************************************************************** + // Events + struct EventId + { + enum enum_type + { + START, + STOP, + EMERGENCY_STOP, + STOPPED, + SET_SPEED + }; + + ETL_DECLARE_ENUM_TYPE(EventId, etl::istate_chart::event_id_t) + ETL_ENUM_TYPE(START, "Start") + ETL_ENUM_TYPE(STOP, "Stop") + ETL_ENUM_TYPE(EMERGENCY_STOP, "Emergency Stop") + ETL_ENUM_TYPE(STOPPED, "Stopped") + ETL_ENUM_TYPE(SET_SPEED, "Set Speed") + ETL_END_ENUM_TYPE + }; + + //*************************************************************************** + // States + struct StateId + { + enum enum_type + { + IDLE, + RUNNING, + WINDING_DOWN, + NUMBER_OF_STATES + }; + + ETL_DECLARE_ENUM_TYPE(StateId, etl::istate_chart::state_id_t) + ETL_ENUM_TYPE(IDLE, "Idle") + ETL_ENUM_TYPE(RUNNING, "Running") + ETL_ENUM_TYPE(WINDING_DOWN, "Winding Down") + ETL_END_ENUM_TYPE + }; + + //*********************************** + // The motor control FSM. + //*********************************** + class MotorControl : public etl::state_chart + { + public: + + MotorControl() + : state_chart(*this, transitionTable, StateId::IDLE) + { + this->set_state_table(stateTable); + ClearStatistics(); + } + + //*********************************** + void ClearStatistics() + { + startCount = 0; + stopCount = 0; + setSpeedCount = 0; + stoppedCount = 0; + isLampOn = false; + speed = 0; + windingDown = 0; + } + + //*********************************** + void OnStart() + { + ++startCount; + } + + //*********************************** + void OnStop() + { + ++stopCount; + } + + //*********************************** + void OnStopped() + { + ++stoppedCount; + } + + //*********************************** + void OnSetSpeed() + { + ++setSpeedCount; + SetSpeedValue(100); + } + + //*********************************** + void OnEnterIdle() + { + TurnRunningLampOff(); + } + + //*********************************** + void OnEnterRunning() + { + TurnRunningLampOn(); + } + + //*********************************** + void OnEnterWindingDown() + { + ++windingDown; + } + + //*********************************** + void OnExitWindingDown() + { + --windingDown; + } + + //*********************************** + void SetSpeedValue(int speed_) + { + speed = speed_; + } + + //*********************************** + bool Guard() + { + return guard; + } + + //*********************************** + void TurnRunningLampOn() + { + isLampOn = true; + } + + //*********************************** + void TurnRunningLampOff() + { + isLampOn = false; + } + + int startCount; + int stopCount; + int setSpeedCount; + int stoppedCount; + bool isLampOn; + int speed; + int windingDown; + + bool guard; + + static const etl::array transitionTable; + static const etl::array stateTable; + }; + + //*************************************************************************** + const etl::array MotorControl::transitionTable = + { + MotorControl::transition(EventId::START, StateId::IDLE, StateId::RUNNING, &MotorControl::OnStart, &MotorControl::Guard), + MotorControl::transition(EventId::STOP, StateId::RUNNING, StateId::WINDING_DOWN, &MotorControl::OnStop), + MotorControl::transition(EventId::STOPPED, StateId::WINDING_DOWN, StateId::IDLE, &MotorControl::OnStopped), + MotorControl::transition(EventId::EMERGENCY_STOP, StateId::RUNNING, StateId::IDLE, &MotorControl::OnStop), + MotorControl::transition(EventId::SET_SPEED, StateId::RUNNING, StateId::RUNNING, &MotorControl::OnSetSpeed) + }; + + //*************************************************************************** + const etl::array MotorControl::stateTable = + { + MotorControl::state(StateId::IDLE, &MotorControl::OnEnterIdle, nullptr), + MotorControl::state(StateId::RUNNING, &MotorControl::OnEnterRunning, nullptr), + MotorControl::state(StateId::WINDING_DOWN, &MotorControl::OnEnterWindingDown, &MotorControl::OnExitWindingDown) + }; + + MotorControl motorControl; + + SUITE(test_state_chart_class) + { + //************************************************************************* + TEST(test_state_chart) + { + motorControl.ClearStatistics(); + + // Now in Idle state. + CHECK_EQUAL(StateId::IDLE, int(motorControl.get_state_id())); + + CHECK_EQUAL(false, motorControl.isLampOn); + CHECK_EQUAL(0, motorControl.setSpeedCount); + CHECK_EQUAL(0, motorControl.speed); + CHECK_EQUAL(0, motorControl.startCount); + CHECK_EQUAL(0, motorControl.stopCount); + CHECK_EQUAL(0, motorControl.stoppedCount); + CHECK_EQUAL(0, motorControl.windingDown); + + // Send unhandled events. + motorControl.process_event(EventId::STOP); + motorControl.process_event(EventId::STOPPED); + + CHECK_EQUAL(StateId::IDLE, motorControl.get_state_id()); + + CHECK_EQUAL(false, motorControl.isLampOn); + CHECK_EQUAL(0, motorControl.setSpeedCount); + CHECK_EQUAL(0, motorControl.speed); + CHECK_EQUAL(0, motorControl.startCount); + CHECK_EQUAL(0, motorControl.stopCount); + CHECK_EQUAL(0, motorControl.stoppedCount); + + // Send Start event. + motorControl.guard = false; + motorControl.process_event(EventId::START); + + // Still in Idle state. + + CHECK_EQUAL(StateId::IDLE, int(motorControl.get_state_id())); + + CHECK_EQUAL(false, motorControl.isLampOn); + CHECK_EQUAL(0, motorControl.setSpeedCount); + CHECK_EQUAL(0, motorControl.speed); + CHECK_EQUAL(0, motorControl.startCount); + CHECK_EQUAL(0, motorControl.stopCount); + CHECK_EQUAL(0, motorControl.stoppedCount); + CHECK_EQUAL(0, motorControl.windingDown); + + // Send Start event. + motorControl.guard = true; + motorControl.process_event(EventId::START); + + // Now in Running state. + + CHECK_EQUAL(StateId::RUNNING, int(motorControl.get_state_id())); + + CHECK_EQUAL(true, motorControl.isLampOn); + CHECK_EQUAL(0, motorControl.setSpeedCount); + CHECK_EQUAL(0, motorControl.speed); + CHECK_EQUAL(1, motorControl.startCount); + CHECK_EQUAL(0, motorControl.stopCount); + CHECK_EQUAL(0, motorControl.stoppedCount); + CHECK_EQUAL(0, motorControl.windingDown); + + // Send unhandled events. + motorControl.process_event(EventId::START); + motorControl.process_event(EventId::STOPPED); + + CHECK_EQUAL(StateId::RUNNING, int(motorControl.get_state_id())); + + CHECK_EQUAL(true, motorControl.isLampOn); + CHECK_EQUAL(0, motorControl.setSpeedCount); + CHECK_EQUAL(0, motorControl.speed); + CHECK_EQUAL(1, motorControl.startCount); + CHECK_EQUAL(0, motorControl.stopCount); + CHECK_EQUAL(0, motorControl.stoppedCount); + CHECK_EQUAL(0, motorControl.windingDown); + + // Send SetSpeed event. + motorControl.process_event(EventId::SET_SPEED); + + // Still in Running state. + + CHECK_EQUAL(StateId::RUNNING, int(motorControl.get_state_id())); + + CHECK_EQUAL(true, motorControl.isLampOn); + CHECK_EQUAL(1, motorControl.setSpeedCount); + CHECK_EQUAL(100, motorControl.speed); + CHECK_EQUAL(1, motorControl.startCount); + CHECK_EQUAL(0, motorControl.stopCount); + CHECK_EQUAL(0, motorControl.stoppedCount); + CHECK_EQUAL(0, motorControl.windingDown); + + // Send Stop event. + motorControl.process_event(EventId::STOP); + + // Now in WindingDown state. + + CHECK_EQUAL(StateId::WINDING_DOWN, int(motorControl.get_state_id())); + + CHECK_EQUAL(true, motorControl.isLampOn); + CHECK_EQUAL(1, motorControl.setSpeedCount); + CHECK_EQUAL(100, motorControl.speed); + CHECK_EQUAL(1, motorControl.startCount); + CHECK_EQUAL(1, motorControl.stopCount); + CHECK_EQUAL(0, motorControl.stoppedCount); + CHECK_EQUAL(1, motorControl.windingDown); + + // Send unhandled events. + motorControl.process_event(EventId::START); + motorControl.process_event(EventId::STOP); + + CHECK_EQUAL(StateId::WINDING_DOWN, int(motorControl.get_state_id())); + + CHECK_EQUAL(true, motorControl.isLampOn); + CHECK_EQUAL(1, motorControl.setSpeedCount); + CHECK_EQUAL(100, motorControl.speed); + CHECK_EQUAL(1, motorControl.startCount); + CHECK_EQUAL(1, motorControl.stopCount); + CHECK_EQUAL(0, motorControl.stoppedCount); + CHECK_EQUAL(1, motorControl.windingDown); + + // Send Stopped event. + motorControl.process_event(EventId::STOPPED); + + // Now in Idle state. + CHECK_EQUAL(StateId::IDLE, int(motorControl.get_state_id())); + + CHECK_EQUAL(false, motorControl.isLampOn); + CHECK_EQUAL(1, motorControl.setSpeedCount); + CHECK_EQUAL(100, motorControl.speed); + CHECK_EQUAL(1, motorControl.startCount); + CHECK_EQUAL(1, motorControl.stopCount); + CHECK_EQUAL(1, motorControl.stoppedCount); + CHECK_EQUAL(0, motorControl.windingDown); + } + + //************************************************************************* + TEST(test_fsm_emergency_stop) + { + motorControl.ClearStatistics(); + + // Now in Idle state. + + // Send Start event. + motorControl.process_event(EventId::START); + + // Now in Running state. + + CHECK_EQUAL(StateId::RUNNING, int(motorControl.get_state_id())); + + CHECK_EQUAL(true, motorControl.isLampOn); + CHECK_EQUAL(0, motorControl.setSpeedCount); + CHECK_EQUAL(0, motorControl.speed); + CHECK_EQUAL(1, motorControl.startCount); + CHECK_EQUAL(0, motorControl.stopCount); + CHECK_EQUAL(0, motorControl.stoppedCount); + CHECK_EQUAL(0, motorControl.windingDown); + + // Send emergency Stop event. + motorControl.process_event(EventId::EMERGENCY_STOP); + + // Now in Idle state. + CHECK_EQUAL(StateId::IDLE, int(motorControl.get_state_id())); + + CHECK_EQUAL(false, motorControl.isLampOn); + CHECK_EQUAL(0, motorControl.setSpeedCount); + CHECK_EQUAL(0, motorControl.speed); + CHECK_EQUAL(1, motorControl.startCount); + CHECK_EQUAL(1, motorControl.stopCount); + CHECK_EQUAL(0, motorControl.stoppedCount); + CHECK_EQUAL(0, motorControl.windingDown); + } + }; +} diff --git a/test/vs2017/cpp.hint b/test/vs2017/cpp.hint new file mode 100644 index 00000000..82067cca --- /dev/null +++ b/test/vs2017/cpp.hint @@ -0,0 +1,8 @@ +// Hint files help the Visual Studio IDE interpret Visual C++ identifiers +// such as names of functions and macros. +// For more information see https://go.microsoft.com/fwlink/?linkid=865984 +#define ETL_CONSTEXPR +#define ETL_CONSTEXPR_IF +#define ETL_DELETE + + diff --git a/test/vs2017/etl.vcxproj b/test/vs2017/etl.vcxproj index 7c97660e..fd081b11 100644 --- a/test/vs2017/etl.vcxproj +++ b/test/vs2017/etl.vcxproj @@ -371,6 +371,7 @@ + @@ -728,6 +729,7 @@ true true + @@ -768,6 +770,7 @@ + diff --git a/test/vs2017/etl.vcxproj.filters b/test/vs2017/etl.vcxproj.filters index b4225aba..32db94a6 100644 --- a/test/vs2017/etl.vcxproj.filters +++ b/test/vs2017/etl.vcxproj.filters @@ -693,6 +693,9 @@ ETL\Utilities\Atomic + + ETL\Frameworks + @@ -1136,6 +1139,9 @@ Source Files + + Source Files + @@ -1174,6 +1180,7 @@ Resource Files\Generators + From 7eb0077a4858da914e23ccca6810deb67eec7ea8 Mon Sep 17 00:00:00 2001 From: John Wellbelove Date: Sat, 8 Sep 2018 15:57:37 +0100 Subject: [PATCH 07/12] Merge remote-tracking branch 'origin/development' # Conflicts: # include/etl/state_chart.h --- include/etl/state_chart.h | 35 +++++++++++++++++++++-------------- 1 file changed, 21 insertions(+), 14 deletions(-) diff --git a/include/etl/state_chart.h b/include/etl/state_chart.h index 692c6322..1657e174 100644 --- a/include/etl/state_chart.h +++ b/include/etl/state_chart.h @@ -48,12 +48,29 @@ namespace etl typedef uint32_t state_id_t; typedef uint32_t event_id_t; - virtual state_id_t get_state_id() const = 0; virtual void process_event(const event_id_t event_id) = 0; + //************************************************************************* + /// Gets the current state id. + /// \return The current state id. + //************************************************************************* + state_id_t get_state_id() const + { + return current_state_id; + } + virtual ~istate_chart() { } + + protected: + + istate_chart(state_id_t current_state_id_) + : current_state_id(current_state_id_) + { + } + + state_id_t current_state_id; ///< The current state id. }; //*************************************************************************** @@ -75,7 +92,7 @@ namespace etl void (TObject::* const action_)() = nullptr, bool (TObject::* const guard_)() = nullptr) : event_id(event_id_), - current_state_id(current_state_id_), + current_state_id(current_state_id_), next_state_id(next_state_id_), action(action_), guard(guard_) @@ -119,8 +136,8 @@ namespace etl state_chart(TObject& object_, const etl::array& transition_table_, const state_id_t state_id_) - : object(object_), - current_state_id(state_id_), + : istate_chart(state_id_), + object(object_), transition_table(transition_table_.begin(), transition_table_.end()) { } @@ -154,15 +171,6 @@ namespace etl return object; } - //************************************************************************* - /// Gets the current state id. - /// \return The current state id. - //************************************************************************* - state_id_t get_state_id() const - { - return current_state_id; - } - //************************************************************************* /// Gets the current state id. /// \return The current state id. @@ -280,7 +288,6 @@ namespace etl state_chart& operator =(const state_chart&) ETL_DELETE; TObject& object; ///< The object that supplies guard and action member functions. - state_id_t current_state_id; ///< The current state id. const etl::array_view transition_table; ///< The table of transitions. etl::array_view state_table; ///< The table of states. }; From 36a2c5b00456dfeb9f0e461f3a7cf26c5de98547 Mon Sep 17 00:00:00 2001 From: John Wellbelove Date: Mon, 10 Sep 2018 20:46:39 +0100 Subject: [PATCH 08/12] Merge remote-tracking branch 'origin/development' # Conflicts: # include/etl/state_chart.h # test/test_state_chart.cpp --- include/etl/state_chart.h | 102 +++++++++++++++++++++++--------------- test/test_state_chart.cpp | 36 ++++++++++++-- 2 files changed, 94 insertions(+), 44 deletions(-) diff --git a/include/etl/state_chart.h b/include/etl/state_chart.h index 1657e174..b37f6578 100644 --- a/include/etl/state_chart.h +++ b/include/etl/state_chart.h @@ -138,7 +138,8 @@ namespace etl const state_id_t state_id_) : istate_chart(state_id_), object(object_), - transition_table(transition_table_.begin(), transition_table_.end()) + transition_table(transition_table_.begin(), transition_table_.end()), + started(false) { } @@ -189,6 +190,29 @@ namespace etl } } + //************************************************************************* + /// + //************************************************************************* + void start(const bool on_entry_initial = true) + { + if (!started) + { + if (on_entry_initial) + { + // See if we have a state item for the initial state. + const state* s = find_state(current_state_id); + + // If the initial state has an 'on_entry' then call it. + if ((s != state_table.end()) && (s->on_entry != nullptr)) + { + (object.*(s->on_entry))(); + } + } + + started = true; + } + } + //************************************************************************* /// Processes the specified event. /// The state machine will action the first item in the transition table @@ -197,52 +221,51 @@ namespace etl //************************************************************************* void process_event(const event_id_t event_id) { - // Scan the transition table. - const transition* t = std::find_if(transition_table.begin(), - transition_table.end(), - is_transition(event_id, current_state_id)); - - // Found an entry? - if (t != transition_table.end()) + if (started) { - // Shall we execute the transition? - if ((t->guard == nullptr) || ((object.*t->guard)())) + // Scan the transition table. + const transition* t = std::find_if(transition_table.begin(), + transition_table.end(), + is_transition(event_id, current_state_id)); + + // Found an entry? + if (t != transition_table.end()) { - const bool to_new_state = (current_state_id != t->next_state_id); - - // Execute the state exit if necessary. - if (to_new_state) + // Shall we execute the transition? + if ((t->guard == nullptr) || ((object.*t->guard)())) { - // See if we have a state item for the current state. - const state* s = find_state(current_state_id); - - // If the current state has an 'on_exit' then call it. - if ((s != state_table.end()) && (s->on_exit != nullptr)) + // Shall we execute the action? + if (t->action != nullptr) { - (object.*(s->on_exit))(); + (object.*t->action)(); } - } - // Shall we execute the action? - if (t->action != nullptr) - { - (object.*t->action)(); - } - - // Execute the state entry if necessary. - if (to_new_state) - { - // See if we have a state item for the next state. - const state* s = find_state(t->next_state_id); - - // If the new state has an 'on_entry' then call it. - if ((s != state_table.end()) && (s->on_entry != nullptr)) + // Changing state? + if (current_state_id != t->next_state_id) { - (object.*(s->on_entry))(); - } - } + const state* s; - current_state_id = t->next_state_id; + // See if we have a state item for the current state. + s = find_state(current_state_id); + + // If the current state has an 'on_exit' then call it. + if ((s != state_table.end()) && (s->on_exit != nullptr)) + { + (object.*(s->on_exit))(); + } + + // See if we have a state item for the next state. + s = find_state(t->next_state_id); + + // If the new state has an 'on_entry' then call it. + if ((s != state_table.end()) && (s->on_entry != nullptr)) + { + (object.*(s->on_entry))(); + } + } + + current_state_id = t->next_state_id; + } } } } @@ -290,6 +313,7 @@ namespace etl TObject& object; ///< The object that supplies guard and action member functions. const etl::array_view transition_table; ///< The table of transitions. etl::array_view state_table; ///< The table of states. + bool started; ///< Set if the state chart has been started. }; } diff --git a/test/test_state_chart.cpp b/test/test_state_chart.cpp index a7730ce8..61f4bf07 100644 --- a/test/test_state_chart.cpp +++ b/test/test_state_chart.cpp @@ -102,6 +102,7 @@ namespace isLampOn = false; speed = 0; windingDown = 0; + entered_idle = false; } //*********************************** @@ -133,6 +134,7 @@ namespace void OnEnterIdle() { TurnRunningLampOff(); + entered_idle = true; } //*********************************** @@ -184,6 +186,7 @@ namespace bool isLampOn; int speed; int windingDown; + bool entered_idle; bool guard; @@ -218,7 +221,7 @@ namespace { motorControl.ClearStatistics(); - // Now in Idle state. + // In Idle state. CHECK_EQUAL(StateId::IDLE, int(motorControl.get_state_id())); CHECK_EQUAL(false, motorControl.isLampOn); @@ -228,12 +231,13 @@ namespace CHECK_EQUAL(0, motorControl.stopCount); CHECK_EQUAL(0, motorControl.stoppedCount); CHECK_EQUAL(0, motorControl.windingDown); + CHECK_EQUAL(false, motorControl.entered_idle); - // Send unhandled events. - motorControl.process_event(EventId::STOP); - motorControl.process_event(EventId::STOPPED); + // Send Start event (state chart not started). + motorControl.guard = true; + motorControl.process_event(EventId::START); - CHECK_EQUAL(StateId::IDLE, motorControl.get_state_id()); + CHECK_EQUAL(StateId::IDLE, int(motorControl.get_state_id())); CHECK_EQUAL(false, motorControl.isLampOn); CHECK_EQUAL(0, motorControl.setSpeedCount); @@ -241,7 +245,29 @@ namespace CHECK_EQUAL(0, motorControl.startCount); CHECK_EQUAL(0, motorControl.stopCount); CHECK_EQUAL(0, motorControl.stoppedCount); + CHECK_EQUAL(0, motorControl.windingDown); + CHECK_EQUAL(false, motorControl.entered_idle); + // Start the state chart + motorControl.guard = true; + motorControl.start(); + + CHECK_EQUAL(true, motorControl.entered_idle); + + // Send unhandled events. + motorControl.process_event(EventId::STOP); + motorControl.process_event(EventId::STOPPED); + + CHECK_EQUAL(StateId::IDLE, int(motorControl.get_state_id())); + + CHECK_EQUAL(false, motorControl.isLampOn); + CHECK_EQUAL(0, motorControl.setSpeedCount); + CHECK_EQUAL(0, motorControl.speed); + CHECK_EQUAL(0, motorControl.startCount); + CHECK_EQUAL(0, motorControl.stopCount); + CHECK_EQUAL(0, motorControl.stoppedCount); + CHECK_EQUAL(0, motorControl.windingDown); + // Send Start event. motorControl.guard = false; motorControl.process_event(EventId::START); From 45ff002610ceb3546a240cea0dde7a3bf68d8f3b Mon Sep 17 00:00:00 2001 From: John Wellbelove Date: Tue, 11 Sep 2018 23:03:26 +0100 Subject: [PATCH 09/12] Merge remote-tracking branch 'origin/development' # Conflicts: # include/etl/state_chart.h # test/test_state_chart.cpp --- include/etl/state_chart.h | 79 +++++++++++++++++++++++---------------- test/test_state_chart.cpp | 26 ++++++++++++- 2 files changed, 70 insertions(+), 35 deletions(-) diff --git a/include/etl/state_chart.h b/include/etl/state_chart.h index b37f6578..94667279 100644 --- a/include/etl/state_chart.h +++ b/include/etl/state_chart.h @@ -223,48 +223,61 @@ namespace etl { if (started) { - // Scan the transition table. - const transition* t = std::find_if(transition_table.begin(), - transition_table.end(), - is_transition(event_id, current_state_id)); + const transition* t = transition_table.begin(); - // Found an entry? - if (t != transition_table.end()) + // Keep looping until we execute a transition or reach the end of the table. + while (t != transition_table.end()) { - // Shall we execute the transition? - if ((t->guard == nullptr) || ((object.*t->guard)())) + // Scan the transition table from the latest position. + t = std::find_if(t, + transition_table.end(), + is_transition(event_id, current_state_id)); + + // Found an entry? + if (t != transition_table.end()) { - // Shall we execute the action? - if (t->action != nullptr) + // Shall we execute the transition? + if ((t->guard == nullptr) || ((object.*t->guard)())) { - (object.*t->action)(); - } - - // Changing state? - if (current_state_id != t->next_state_id) - { - const state* s; - - // See if we have a state item for the current state. - s = find_state(current_state_id); - - // If the current state has an 'on_exit' then call it. - if ((s != state_table.end()) && (s->on_exit != nullptr)) + // Shall we execute the action? + if (t->action != nullptr) { - (object.*(s->on_exit))(); + (object.*t->action)(); } - // See if we have a state item for the next state. - s = find_state(t->next_state_id); - - // If the new state has an 'on_entry' then call it. - if ((s != state_table.end()) && (s->on_entry != nullptr)) + // Changing state? + if (current_state_id != t->next_state_id) { - (object.*(s->on_entry))(); - } - } + const state* s; - current_state_id = t->next_state_id; + // See if we have a state item for the current state. + s = find_state(current_state_id); + + // If the current state has an 'on_exit' then call it. + if ((s != state_table.end()) && (s->on_exit != nullptr)) + { + (object.*(s->on_exit))(); + } + + // See if we have a state item for the next state. + s = find_state(t->next_state_id); + + // If the new state has an 'on_entry' then call it. + if ((s != state_table.end()) && (s->on_entry != nullptr)) + { + (object.*(s->on_entry))(); + } + + current_state_id = t->next_state_id; + } + + t = transition_table.end(); + } + else + { + // Start the search from the next item in the table. + ++t; + } } } } diff --git a/test/test_state_chart.cpp b/test/test_state_chart.cpp index 61f4bf07..2134ed6b 100644 --- a/test/test_state_chart.cpp +++ b/test/test_state_chart.cpp @@ -103,6 +103,7 @@ namespace speed = 0; windingDown = 0; entered_idle = false; + null = 0; } //*********************************** @@ -167,6 +168,12 @@ namespace return guard; } + //*********************************** + bool NotGuard() + { + return !guard; + } + //*********************************** void TurnRunningLampOn() { @@ -179,6 +186,12 @@ namespace isLampOn = false; } + //*********************************** + void Null() + { + ++null; + } + int startCount; int stopCount; int setSpeedCount; @@ -187,17 +200,19 @@ namespace int speed; int windingDown; bool entered_idle; + int null; bool guard; - static const etl::array transitionTable; + static const etl::array transitionTable; static const etl::array stateTable; }; //*************************************************************************** - const etl::array MotorControl::transitionTable = + const etl::array MotorControl::transitionTable = { MotorControl::transition(EventId::START, StateId::IDLE, StateId::RUNNING, &MotorControl::OnStart, &MotorControl::Guard), + MotorControl::transition(EventId::START, StateId::IDLE, StateId::IDLE, &MotorControl::Null, &MotorControl::NotGuard), MotorControl::transition(EventId::STOP, StateId::RUNNING, StateId::WINDING_DOWN, &MotorControl::OnStop), MotorControl::transition(EventId::STOPPED, StateId::WINDING_DOWN, StateId::IDLE, &MotorControl::OnStopped), MotorControl::transition(EventId::EMERGENCY_STOP, StateId::RUNNING, StateId::IDLE, &MotorControl::OnStop), @@ -283,6 +298,7 @@ namespace CHECK_EQUAL(0, motorControl.stopCount); CHECK_EQUAL(0, motorControl.stoppedCount); CHECK_EQUAL(0, motorControl.windingDown); + CHECK_EQUAL(1, motorControl.null); // Send Start event. motorControl.guard = true; @@ -299,6 +315,7 @@ namespace CHECK_EQUAL(0, motorControl.stopCount); CHECK_EQUAL(0, motorControl.stoppedCount); CHECK_EQUAL(0, motorControl.windingDown); + CHECK_EQUAL(1, motorControl.null); // Send unhandled events. motorControl.process_event(EventId::START); @@ -313,6 +330,7 @@ namespace CHECK_EQUAL(0, motorControl.stopCount); CHECK_EQUAL(0, motorControl.stoppedCount); CHECK_EQUAL(0, motorControl.windingDown); + CHECK_EQUAL(1, motorControl.null); // Send SetSpeed event. motorControl.process_event(EventId::SET_SPEED); @@ -328,6 +346,7 @@ namespace CHECK_EQUAL(0, motorControl.stopCount); CHECK_EQUAL(0, motorControl.stoppedCount); CHECK_EQUAL(0, motorControl.windingDown); + CHECK_EQUAL(1, motorControl.null); // Send Stop event. motorControl.process_event(EventId::STOP); @@ -343,6 +362,7 @@ namespace CHECK_EQUAL(1, motorControl.stopCount); CHECK_EQUAL(0, motorControl.stoppedCount); CHECK_EQUAL(1, motorControl.windingDown); + CHECK_EQUAL(1, motorControl.null); // Send unhandled events. motorControl.process_event(EventId::START); @@ -357,6 +377,7 @@ namespace CHECK_EQUAL(1, motorControl.stopCount); CHECK_EQUAL(0, motorControl.stoppedCount); CHECK_EQUAL(1, motorControl.windingDown); + CHECK_EQUAL(1, motorControl.null); // Send Stopped event. motorControl.process_event(EventId::STOPPED); @@ -371,6 +392,7 @@ namespace CHECK_EQUAL(1, motorControl.stopCount); CHECK_EQUAL(1, motorControl.stoppedCount); CHECK_EQUAL(0, motorControl.windingDown); + CHECK_EQUAL(1, motorControl.null); } //************************************************************************* From b72aee854e32ae3ee7b4e1b7950aded96e4b9771 Mon Sep 17 00:00:00 2001 From: John Wellbelove Date: Wed, 12 Sep 2018 17:40:13 +0100 Subject: [PATCH 10/12] Merge remote-tracking branch 'origin/development' # Conflicts: # include/etl/state_chart.h # include/etl/version.h # support/Release notes.txt # test/test_state_chart.cpp --- include/etl/state_chart.h | 10 +++++----- include/etl/version.h | 10 +++++----- support/Release notes.txt | 4 ++++ test/test_state_chart.cpp | 12 ++++++------ 4 files changed, 20 insertions(+), 16 deletions(-) diff --git a/include/etl/state_chart.h b/include/etl/state_chart.h index 94667279..18fab61b 100644 --- a/include/etl/state_chart.h +++ b/include/etl/state_chart.h @@ -86,21 +86,21 @@ namespace etl //************************************************************************* struct transition { - transition(const event_id_t event_id_, - const state_id_t current_state_id_, + transition(const state_id_t current_state_id_, + const event_id_t event_id_, const state_id_t next_state_id_, void (TObject::* const action_)() = nullptr, bool (TObject::* const guard_)() = nullptr) - : event_id(event_id_), - current_state_id(current_state_id_), + : current_state_id(current_state_id_), + event_id(event_id_), next_state_id(next_state_id_), action(action_), guard(guard_) { } - const event_id_t event_id; const state_id_t current_state_id; + const event_id_t event_id; const state_id_t next_state_id; void (TObject::* const action)(); bool (TObject::* const guard)(); diff --git a/include/etl/version.h b/include/etl/version.h index c5444289..7b124c71 100644 --- a/include/etl/version.h +++ b/include/etl/version.h @@ -37,13 +37,13 @@ SOFTWARE. /// Definitions of the ETL version ///\ingroup utilities -#define ETL_VERSION "11.17.0" -#define ETL_VERSION_W L"11.17.0" -#define ETL_VERSION_U16 u"11.17.0" -#define ETL_VERSION_U32 U"11.17.0" +#define ETL_VERSION "11.17.1" +#define ETL_VERSION_W L"11.17.1" +#define ETL_VERSION_U16 u"11.17.1" +#define ETL_VERSION_U32 U"11.17.1" #define ETL_VERSION_MAJOR 11 #define ETL_VERSION_MINOR 17 -#define ETL_VERSION_PATCH 0 +#define ETL_VERSION_PATCH 1 #define ETL_VERSION_VALUE ((ETL_VERSION_MAJOR * 10000) + (ETL_VERSION_MINOR * 100) + ETL_VERSION_PATCH) #endif diff --git a/support/Release notes.txt b/support/Release notes.txt index 69a38502..a00ad58c 100644 --- a/support/Release notes.txt +++ b/support/Release notes.txt @@ -1,3 +1,7 @@ +=============================================================================== +11.17.1 +Swapped event and current state parameters for transition constructor. + =============================================================================== 11.17.0 Added etl::state_chart diff --git a/test/test_state_chart.cpp b/test/test_state_chart.cpp index 2134ed6b..6cfb651c 100644 --- a/test/test_state_chart.cpp +++ b/test/test_state_chart.cpp @@ -211,12 +211,12 @@ namespace //*************************************************************************** const etl::array MotorControl::transitionTable = { - MotorControl::transition(EventId::START, StateId::IDLE, StateId::RUNNING, &MotorControl::OnStart, &MotorControl::Guard), - MotorControl::transition(EventId::START, StateId::IDLE, StateId::IDLE, &MotorControl::Null, &MotorControl::NotGuard), - MotorControl::transition(EventId::STOP, StateId::RUNNING, StateId::WINDING_DOWN, &MotorControl::OnStop), - MotorControl::transition(EventId::STOPPED, StateId::WINDING_DOWN, StateId::IDLE, &MotorControl::OnStopped), - MotorControl::transition(EventId::EMERGENCY_STOP, StateId::RUNNING, StateId::IDLE, &MotorControl::OnStop), - MotorControl::transition(EventId::SET_SPEED, StateId::RUNNING, StateId::RUNNING, &MotorControl::OnSetSpeed) + MotorControl::transition(StateId::IDLE, EventId::START, StateId::RUNNING, &MotorControl::OnStart, &MotorControl::Guard), + MotorControl::transition(StateId::IDLE, EventId::START, StateId::IDLE, &MotorControl::Null, &MotorControl::NotGuard), + MotorControl::transition(StateId::RUNNING, EventId::STOP, StateId::WINDING_DOWN, &MotorControl::OnStop), + MotorControl::transition(StateId::RUNNING, EventId::EMERGENCY_STOP, StateId::IDLE, &MotorControl::OnStop), + MotorControl::transition(StateId::RUNNING, EventId::SET_SPEED, StateId::RUNNING, &MotorControl::OnSetSpeed), + MotorControl::transition(StateId::WINDING_DOWN, EventId::STOPPED, StateId::IDLE, &MotorControl::OnStopped) }; //*************************************************************************** From c3dc3000b3a1622dd8afe21bae9cb3b611651e08 Mon Sep 17 00:00:00 2001 From: John Wellbelove Date: Fri, 14 Sep 2018 19:26:43 +0100 Subject: [PATCH 11/12] Merge remote-tracking branch 'origin/development' # Conflicts: # include/etl/version.h # support/Release notes.txt # test/vs2017/etl.vcxproj.filters --- include/etl/crc16.h | 4 +- include/etl/crc16_ccitt.h | 4 +- include/etl/crc16_kermit.h | 4 +- include/etl/crc16_modbus.h | 109 ++++++++++++++++++++++++++++++++ include/etl/crc32.h | 4 +- include/etl/version.h | 12 ++-- src/crc16.cpp | 2 +- src/crc16_ccitt.cpp | 2 +- src/crc16_kermit.cpp | 2 +- src/crc16_modbus.cpp | 76 ++++++++++++++++++++++ src/crc32.cpp | 2 +- src/crc32_c.cpp | 6 +- support/Release notes.txt | 4 ++ test/test_crc.cpp | 57 +++++++++++++++++ test/vs2017/etl.vcxproj | 2 + test/vs2017/etl.vcxproj.filters | 6 ++ 16 files changed, 275 insertions(+), 21 deletions(-) create mode 100644 include/etl/crc16_modbus.h create mode 100644 src/crc16_modbus.cpp diff --git a/include/etl/crc16.h b/include/etl/crc16.h index 9fa21d8b..e517c77b 100644 --- a/include/etl/crc16.h +++ b/include/etl/crc16.h @@ -51,7 +51,7 @@ namespace etl /// CRC16 table /// \ingroup crc16 //*************************************************************************** - extern const uint16_t CRC16[]; + extern const uint16_t ETL_CRC16[]; //*************************************************************************** /// CRC16 policy. @@ -68,7 +68,7 @@ namespace etl inline uint16_t add(uint16_t crc, uint8_t value) const { - return (crc >> 8) ^ CRC16[(crc ^ value) & 0xFF]; + return (crc >> 8) ^ ETL_CRC16[(crc ^ value) & 0xFF]; } inline uint16_t final(uint16_t crc) const diff --git a/include/etl/crc16_ccitt.h b/include/etl/crc16_ccitt.h index 28ef7054..a9f6c7e9 100644 --- a/include/etl/crc16_ccitt.h +++ b/include/etl/crc16_ccitt.h @@ -51,7 +51,7 @@ namespace etl /// CRC-CCITT table /// \ingroup crc16_ccitt //*************************************************************************** - extern const uint16_t CRC_CCITT[]; + extern const uint16_t ETL_CRC_CCITT[]; //*************************************************************************** /// CRC16 CCITT policy. @@ -68,7 +68,7 @@ namespace etl inline uint16_t add(uint16_t crc, uint8_t value) const { - return (crc << 8) ^ CRC_CCITT[((crc >> 8) ^ value) & 0xFF]; + return (crc << 8) ^ ETL_CRC_CCITT[((crc >> 8) ^ value) & 0xFF]; } inline uint16_t final(uint16_t crc) const diff --git a/include/etl/crc16_kermit.h b/include/etl/crc16_kermit.h index dffc6ed2..baa1456d 100644 --- a/include/etl/crc16_kermit.h +++ b/include/etl/crc16_kermit.h @@ -51,7 +51,7 @@ namespace etl /// CRC Kermit table /// \ingroup crc //*************************************************************************** - extern const uint16_t CRC_KERMIT[]; + extern const uint16_t ETL_CRC_KERMIT[]; //*************************************************************************** /// CRC16 Kermit policy. @@ -68,7 +68,7 @@ namespace etl inline uint16_t add(uint16_t crc, uint8_t value) const { - return (crc >> 8) ^ CRC_KERMIT[(crc ^ value) & 0xFF]; + return (crc >> 8) ^ ETL_CRC_KERMIT[(crc ^ value) & 0xFF]; } inline uint16_t final(uint16_t crc) const diff --git a/include/etl/crc16_modbus.h b/include/etl/crc16_modbus.h new file mode 100644 index 00000000..f962664a --- /dev/null +++ b/include/etl/crc16_modbus.h @@ -0,0 +1,109 @@ +///\file + +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2018 jwellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#ifndef ETL_CRC16_MODBUS_INCLUDED +#define ETL_CRC16_MODBUS_INCLUDED + +#include + +#include "platform.h" +#include "frame_check_sequence.h" + +#include "stl/iterator.h" + +#if defined(ETL_COMPILER_KEIL) +#pragma diag_suppress 1300 +#endif + +///\defgroup crc16_modbus 16 bit CRC MODBUS calculation +///\ingroup crc + +namespace etl +{ + //*************************************************************************** + /// CRC-MODBUS table + /// \ingroup crc16_modbus + //*************************************************************************** + extern const uint16_t ETL_CRC_MODBUS[]; + + //*************************************************************************** + /// CRC16 MODBUS policy. + /// Calculates CRC16 MODBUS using polynomial 0x + //*************************************************************************** + struct crc_policy_16_modbus + { + typedef uint16_t value_type; + + inline uint16_t initial() const + { + return 0xFFFF; + } + + inline uint16_t add(uint16_t crc, uint8_t value) const + { + return (crc >> 8) ^ ETL_CRC_MODBUS[(crc ^ value) & 0xFF]; + } + + inline uint16_t final(uint16_t crc) const + { + return crc; + } + }; + + //************************************************************************* + /// CRC16 MODBUS + //************************************************************************* + class crc16_modbus : public etl::frame_check_sequence + { + public: + + //************************************************************************* + /// Default constructor. + //************************************************************************* + crc16_modbus() + { + this->reset(); + } + + //************************************************************************* + /// Constructor from range. + /// \param begin Start of the range. + /// \param end End of the range. + //************************************************************************* + template + crc16_modbus(TIterator begin, const TIterator end) + { + this->reset(); + this->add(begin, end); + } + }; +} + +#endif diff --git a/include/etl/crc32.h b/include/etl/crc32.h index 8f78e429..141c32b4 100644 --- a/include/etl/crc32.h +++ b/include/etl/crc32.h @@ -51,7 +51,7 @@ namespace etl /// CRC32 table /// \ingroup crc32 //*************************************************************************** - extern const uint32_t CRC32[]; + extern const uint32_t ETL_CRC32[]; //*************************************************************************** /// CRC32 policy. @@ -68,7 +68,7 @@ namespace etl inline uint32_t add(uint32_t crc, uint8_t value) const { - return (crc >> 8) ^ CRC32[(crc ^ value) & 0xFF]; + return (crc >> 8) ^ ETL_CRC32[(crc ^ value) & 0xFF]; } inline uint32_t final(uint32_t crc) const diff --git a/include/etl/version.h b/include/etl/version.h index 7b124c71..cdf62feb 100644 --- a/include/etl/version.h +++ b/include/etl/version.h @@ -37,13 +37,13 @@ SOFTWARE. /// Definitions of the ETL version ///\ingroup utilities -#define ETL_VERSION "11.17.1" -#define ETL_VERSION_W L"11.17.1" -#define ETL_VERSION_U16 u"11.17.1" -#define ETL_VERSION_U32 U"11.17.1" +#define ETL_VERSION "11.18.0" +#define ETL_VERSION_W L"11.18.0" +#define ETL_VERSION_U16 u"11.18.0" +#define ETL_VERSION_U32 U"11.18.0" #define ETL_VERSION_MAJOR 11 -#define ETL_VERSION_MINOR 17 -#define ETL_VERSION_PATCH 1 +#define ETL_VERSION_MINOR 18 +#define ETL_VERSION_PATCH 0 #define ETL_VERSION_VALUE ((ETL_VERSION_MAJOR * 10000) + (ETL_VERSION_MINOR * 100) + ETL_VERSION_PATCH) #endif diff --git a/src/crc16.cpp b/src/crc16.cpp index 9ac1d710..512b6ae9 100644 --- a/src/crc16.cpp +++ b/src/crc16.cpp @@ -38,7 +38,7 @@ namespace etl /// CRC16 table /// \ingroup crc16 //*************************************************************************** - extern const uint16_t CRC16[] = + extern const uint16_t ETL_CRC16[] = { 0x0000, 0xC0C1, 0xC181, 0x0140, 0xC301, 0x03C0, 0x0280, 0xC241, 0xC601, 0x06C0, 0x0780, 0xC741, 0x0500, 0xC5C1, 0xC481, 0x0440, 0xCC01, 0x0CC0, 0x0D80, 0xCD41, 0x0F00, 0xCFC1, 0xCE81, 0x0E40, 0x0A00, 0xCAC1, 0xCB81, 0x0B40, 0xC901, 0x09C0, 0x0880, 0xC841, diff --git a/src/crc16_ccitt.cpp b/src/crc16_ccitt.cpp index 12b79a76..09cced20 100644 --- a/src/crc16_ccitt.cpp +++ b/src/crc16_ccitt.cpp @@ -38,7 +38,7 @@ namespace etl /// CRC-CCITT table /// \ingroup crc16_ccitt //*************************************************************************** - extern const uint16_t CRC_CCITT[] = + extern const uint16_t ETL_CRC_CCITT[] = { 0x0000, 0x1021, 0x2042, 0x3063, 0x4084, 0x50A5, 0x60C6, 0x70E7, 0x8108, 0x9129, 0xA14A, 0xB16B, 0xC18C, 0xD1AD, 0xE1CE, 0xF1EF, 0x1231, 0x0210, 0x3273, 0x2252, 0x52B5, 0x4294, 0x72F7, 0x62D6, 0x9339, 0x8318, 0xB37B, 0xA35A, 0xD3BD, 0xC39C, 0xF3FF, 0xE3DE, diff --git a/src/crc16_kermit.cpp b/src/crc16_kermit.cpp index 3c44e043..5e89a96f 100644 --- a/src/crc16_kermit.cpp +++ b/src/crc16_kermit.cpp @@ -38,7 +38,7 @@ namespace etl /// CRC Kermit table /// \ingroup crc16_kermit //*************************************************************************** - extern const uint16_t CRC_KERMIT[] = + extern const uint16_t ETL_CRC_KERMIT[] = { 0x0000, 0x1189, 0x2312, 0x329B, 0x4624, 0x57AD, 0x6536, 0x74BF, 0x8C48, 0x9DC1, 0xAF5A, 0xBED3, 0xCA6C, 0xDBE5, 0xE97E, 0xF8F7, 0x1081, 0x0108, 0x3393, 0x221A, 0x56A5, 0x472C, 0x75B7, 0x643E, 0x9CC9, 0x8D40, 0xBFDB, 0xAE52, 0xDAED, 0xCB64, 0xF9FF, 0xE876, diff --git a/src/crc16_modbus.cpp b/src/crc16_modbus.cpp new file mode 100644 index 00000000..43f02df3 --- /dev/null +++ b/src/crc16_modbus.cpp @@ -0,0 +1,76 @@ +///\file + +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2018 jwellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, ExPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#include + +#include "etl/platform.h" + +namespace etl +{ + //*************************************************************************** + /// CRC-MODBUS table + /// \ingroup crc16_modbus + //*************************************************************************** + extern const uint16_t ETL_CRC_MODBUS[] = + { + 0x0000, 0xC0C1, 0xC181, 0x0140, 0xC301, 0x03C0, 0x0280, 0xC241, + 0xC601, 0x06C0, 0x0780, 0xC741, 0x0500, 0xC5C1, 0xC481, 0x0440, + 0xCC01, 0x0CC0, 0x0D80, 0xCD41, 0x0F00, 0xCFC1, 0xCE81, 0x0E40, + 0x0A00, 0xCAC1, 0xCB81, 0x0B40, 0xC901, 0x09C0, 0x0880, 0xC841, + 0xD801, 0x18C0, 0x1980, 0xD941, 0x1B00, 0xDBC1, 0xDA81, 0x1A40, + 0x1E00, 0xDEC1, 0xDF81, 0x1F40, 0xDD01, 0x1DC0, 0x1C80, 0xDC41, + 0x1400, 0xD4C1, 0xD581, 0x1540, 0xD701, 0x17C0, 0x1680, 0xD641, + 0xD201, 0x12C0, 0x1380, 0xD341, 0x1100, 0xD1C1, 0xD081, 0x1040, + 0xF001, 0x30C0, 0x3180, 0xF141, 0x3300, 0xF3C1, 0xF281, 0x3240, + 0x3600, 0xF6C1, 0xF781, 0x3740, 0xF501, 0x35C0, 0x3480, 0xF441, + 0x3C00, 0xFCC1, 0xFD81, 0x3D40, 0xFF01, 0x3FC0, 0x3E80, 0xFE41, + 0xFA01, 0x3AC0, 0x3B80, 0xFB41, 0x3900, 0xF9C1, 0xF881, 0x3840, + 0x2800, 0xE8C1, 0xE981, 0x2940, 0xEB01, 0x2BC0, 0x2A80, 0xEA41, + 0xEE01, 0x2EC0, 0x2F80, 0xEF41, 0x2D00, 0xEDC1, 0xEC81, 0x2C40, + 0xE401, 0x24C0, 0x2580, 0xE541, 0x2700, 0xE7C1, 0xE681, 0x2640, + 0x2200, 0xE2C1, 0xE381, 0x2340, 0xE101, 0x21C0, 0x2080, 0xE041, + 0xA001, 0x60C0, 0x6180, 0xA141, 0x6300, 0xA3C1, 0xA281, 0x6240, + 0x6600, 0xA6C1, 0xA781, 0x6740, 0xA501, 0x65C0, 0x6480, 0xA441, + 0x6C00, 0xACC1, 0xAD81, 0x6D40, 0xAF01, 0x6FC0, 0x6E80, 0xAE41, + 0xAA01, 0x6AC0, 0x6B80, 0xAB41, 0x6900, 0xA9C1, 0xA881, 0x6840, + 0x7800, 0xB8C1, 0xB981, 0x7940, 0xBB01, 0x7BC0, 0x7A80, 0xBA41, + 0xBE01, 0x7EC0, 0x7F80, 0xBF41, 0x7D00, 0xBDC1, 0xBC81, 0x7C40, + 0xB401, 0x74C0, 0x7580, 0xB541, 0x7700, 0xB7C1, 0xB681, 0x7640, + 0x7200, 0xB2C1, 0xB381, 0x7340, 0xB101, 0x71C0, 0x7080, 0xB041, + 0x5000, 0x90C1, 0x9181, 0x5140, 0x9301, 0x53C0, 0x5280, 0x9241, + 0x9601, 0x56C0, 0x5780, 0x9741, 0x5500, 0x95C1, 0x9481, 0x5440, + 0x9C01, 0x5CC0, 0x5D80, 0x9D41, 0x5F00, 0x9FC1, 0x9E81, 0x5E40, + 0x5A00, 0x9AC1, 0x9B81, 0x5B40, 0x9901, 0x59C0, 0x5880, 0x9841, + 0x8801, 0x48C0, 0x4980, 0x8941, 0x4B00, 0x8BC1, 0x8A81, 0x4A40, + 0x4E00, 0x8EC1, 0x8F81, 0x4F40, 0x8D01, 0x4DC0, 0x4C80, 0x8C41, + 0x4400, 0x84C1, 0x8581, 0x4540, 0x8701, 0x47C0, 0x4680, 0x8641, + 0x8201, 0x42C0, 0x4380, 0x8341, 0x4100, 0x81C1, 0x8081, 0x4040 + }; +} diff --git a/src/crc32.cpp b/src/crc32.cpp index c9217577..771f2ad3 100644 --- a/src/crc32.cpp +++ b/src/crc32.cpp @@ -38,7 +38,7 @@ namespace etl /// CRC32 table /// \ingroup crc32 //*************************************************************************** - extern const uint32_t CRC32[] = + extern const uint32_t ETL_CRC32[] = { 0x00000000, 0x77073096, 0xEE0E612C, 0x990951BA, 0x076DC419, 0x706AF48F, 0xE963A535, 0x9E6495A3, 0x0EDB8832, 0x79DCB8A4, 0xE0D5E91E, 0x97D2D988, 0x09B64C2B, 0x7EB17CBD, 0xE7B82D07, 0x90BF1D91, diff --git a/src/crc32_c.cpp b/src/crc32_c.cpp index 1c54c3f6..b255af0d 100644 --- a/src/crc32_c.cpp +++ b/src/crc32_c.cpp @@ -35,10 +35,10 @@ SOFTWARE. namespace etl { //*************************************************************************** - /// CRC32_C table - /// \ingroup CRC32_C + /// ETL_CRC32_C table + /// \ingroup ETL_CRC32_C //*************************************************************************** - extern const uint32_t CRC32_C[] = + extern const uint32_t ETL_CRC32_C[] = { 0x00000000L, 0xF26B8303L, 0xE13B70F7L, 0x1350F3F4L, 0xC79A971FL, 0x35F1141CL, 0x26A1E7E8L, 0xD4CA64EBL, 0x8AD958CFL, 0x78B2DBCCL, 0x6BE22838L, 0x9989AB3BL, 0x4D43CFD0L, 0xBF284CD3L, 0xAC78BF27L, 0x5E133C24L, diff --git a/support/Release notes.txt b/support/Release notes.txt index a00ad58c..8d08d7b8 100644 --- a/support/Release notes.txt +++ b/support/Release notes.txt @@ -1,3 +1,7 @@ +=============================================================================== +11.18.0 +Added CRC16 MODBUS + =============================================================================== 11.17.1 Swapped event and current state parameters for transition constructor. diff --git a/test/test_crc.cpp b/test/test_crc.cpp index 9cb3bc5b..c5adaf02 100644 --- a/test/test_crc.cpp +++ b/test/test_crc.cpp @@ -37,6 +37,7 @@ SOFTWARE. #include "etl/crc16.h" #include "etl/crc16_ccitt.h" #include "etl/crc16_kermit.h" +#include "etl/crc16_modbus.h" #include "etl/crc32.h" #include "etl/crc64_ecma.h" @@ -268,6 +269,62 @@ namespace CHECK_EQUAL(crc1, crc3); } + //************************************************************************* + TEST(test_crc16_modbus) + { + std::string data("123456789"); + + uint16_t crc = etl::crc16_modbus(data.begin(), data.end()); + + CHECK_EQUAL(0x4B37, crc); + } + + //************************************************************************* + TEST(test_crc16_modbus_add_values) + { + std::string data("123456789"); + + etl::crc16_modbus crc_calculator; + + for (size_t i = 0; i < data.size(); ++i) + { + crc_calculator.add(data[i]); + } + + uint16_t crc = crc_calculator; + + CHECK_EQUAL(0x4B37, crc); + } + + //************************************************************************* + TEST(test_crc16_modbus_add_range) + { + std::string data("123456789"); + + etl::crc16_modbus crc_calculator; + + crc_calculator.add(data.begin(), data.end()); + + uint16_t crc = crc_calculator.value(); + + CHECK_EQUAL(0x4B37, crc); + } + + //************************************************************************* + TEST(test_crc16_modbus_add_range_endian) + { + std::vector data1 = { 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08 }; + std::vector data2 = { 0x04030201, 0x08070605 }; + std::vector data3 = { 0x08, 0x07, 0x06, 0x05, 0x04, 0x03, 0x02, 0x01 }; + + uint16_t crc1 = etl::crc16_modbus(data1.begin(), data1.end()); + uint16_t crc2 = etl::crc16_modbus((uint8_t*)&data2[0], (uint8_t*)(&data2[0] + data2.size())); + CHECK_EQUAL(crc1, crc2); + + uint16_t crc3 = etl::crc16_modbus(data3.rbegin(), data3.rend()); + CHECK_EQUAL(crc1, crc3); + } + //************************************************************************* TEST(test_crc32) { diff --git a/test/vs2017/etl.vcxproj b/test/vs2017/etl.vcxproj index fd081b11..628b95d8 100644 --- a/test/vs2017/etl.vcxproj +++ b/test/vs2017/etl.vcxproj @@ -366,6 +366,7 @@ + @@ -555,6 +556,7 @@ + diff --git a/test/vs2017/etl.vcxproj.filters b/test/vs2017/etl.vcxproj.filters index 32db94a6..454cab6a 100644 --- a/test/vs2017/etl.vcxproj.filters +++ b/test/vs2017/etl.vcxproj.filters @@ -696,6 +696,9 @@ ETL\Frameworks + + ETL\Maths + @@ -1142,6 +1145,9 @@ Source Files + + ETL\Maths + From 0e6bad5c9147068da8596810a69c6f14ab24b938 Mon Sep 17 00:00:00 2001 From: John Wellbelove Date: Sat, 15 Sep 2018 09:48:52 +0100 Subject: [PATCH 12/12] Modified the API of etl::state_chart constructors. --- include/etl/private/ivectorpointer.h | 18 --------- include/etl/state_chart.h | 60 ++++++++++++++++++++++------ include/etl/version.h | 12 +++--- support/Release notes.txt | 4 ++ test/codeblocks/ETL.cbp | 1 + test/test_state_chart.cpp | 4 +- 6 files changed, 60 insertions(+), 39 deletions(-) diff --git a/include/etl/private/ivectorpointer.h b/include/etl/private/ivectorpointer.h index 4a24a186..a24f2bad 100644 --- a/include/etl/private/ivectorpointer.h +++ b/include/etl/private/ivectorpointer.h @@ -335,15 +335,6 @@ namespace etl base_t::clear(); } - //************************************************************************* - /// Increases the size of the vector by one, but does not initialise the new element. - /// If asserts or exceptions are enabled, throws a vector_full if the vector is already full. - //************************************************************************* - void push_back() - { - base_t::push_back(); - } - //********************************************************************* /// Inserts a value at the end of the vector. /// If asserts or exceptions are enabled, emits vector_full if the vector is already full. @@ -737,15 +728,6 @@ namespace etl base_t::clear(); } - //************************************************************************* - /// Increases the size of the vector by one, but does not initialise the new element. - /// If asserts or exceptions are enabled, throws a vector_full if the vector is already full. - //************************************************************************* - void push_back() - { - base_t::push_back(); - } - //********************************************************************* /// Inserts a value at the end of the vector. /// If asserts or exceptions are enabled, emits vector_full if the vector is already full. diff --git a/include/etl/state_chart.h b/include/etl/state_chart.h index 18fab61b..486316a1 100644 --- a/include/etl/state_chart.h +++ b/include/etl/state_chart.h @@ -127,31 +127,65 @@ namespace etl //************************************************************************* /// Constructor. - /// \tparam TRANSITION_TABLE_SIZE The transition table size. - /// \param object_ A reference to the implementation object. - /// \param transition_table_ The table of transitions. - /// \param state_id_ The initial state id. + /// \param object_ A reference to the implementation object. + /// \param transition_table_begin_ The start of the table of transitions. + /// \param transition_table_end_ The end of the table of transitions. + /// \param state_id_ The initial state id. //************************************************************************* - template state_chart(TObject& object_, - const etl::array& transition_table_, + const transition* transition_table_begin_, + const transition* transition_table_end_, const state_id_t state_id_) : istate_chart(state_id_), object(object_), - transition_table(transition_table_.begin(), transition_table_.end()), + transition_table(transition_table_begin_, transition_table_end_), started(false) { } //************************************************************************* - /// Sets the state table. - /// \tparam STATE_TABLE_SIZE The state table size. - /// \param state_table_ A reference to the state table. + /// Constructor. + /// \param object_ A reference to the implementation object. + /// \param transition_table_begin_ The start of the table of transitions. + /// \param transition_table_end_ The end of the table of transitions. + /// \param state_table_begin_ The start of the state table. + /// \param state_table_end_ The end of the state table. + /// \param state_id_ The initial state id. //************************************************************************* - template - void set_state_table(const etl::array& state_table_) + state_chart(TObject& object_, + const transition* transition_table_begin_, + const transition* transition_table_end_, + const state* state_table_begin_, + const state* state_table_end_, + const state_id_t state_id_) + : istate_chart(state_id_), + object(object_), + transition_table(transition_table_begin_, transition_table_end_), + state_table(state_table_begin_, state_table_end_), + started(false) { - state_table.assign(state_table_.begin(), state_table_.end()); + } + + //************************************************************************* + /// Sets the transition table. + /// \param state_table_begin_ The start of the state table. + /// \param state_table_end_ The end of the state table. + //************************************************************************* + void set_transition_table(const transition* transition_table_begin_, + const transition* transition_table_end_) + { + transition_table.assign(transition_table_begin_, transition_table_end_); + } + + //************************************************************************* + /// Sets the state table. + /// \param state_table_begin_ The start of the state table. + /// \param state_table_end_ The end of the state table. + //************************************************************************* + void set_state_table(const state* state_table_begin_, + const state* state_table_end_) + { + state_table.assign(state_table_begin_, state_table_end_); } //************************************************************************* diff --git a/include/etl/version.h b/include/etl/version.h index 64ee56ab..569fe3f8 100644 --- a/include/etl/version.h +++ b/include/etl/version.h @@ -37,12 +37,12 @@ SOFTWARE. /// Definitions of the ETL version ///\ingroup utilities -#define ETL_VERSION "11.19.0" -#define ETL_VERSION_W L"11.19.0" -#define ETL_VERSION_U16 u"11.19.0" -#define ETL_VERSION_U32 U"11.19.0" -#define ETL_VERSION_MAJOR 11 -#define ETL_VERSION_MINOR 19 +#define ETL_VERSION "12.0.0" +#define ETL_VERSION_W L"12.0.0" +#define ETL_VERSION_U16 u"12.0.0" +#define ETL_VERSION_U32 U"12.0.0" +#define ETL_VERSION_MAJOR 12 +#define ETL_VERSION_MINOR 0 #define ETL_VERSION_PATCH 0 #define ETL_VERSION_VALUE ((ETL_VERSION_MAJOR * 10000) + (ETL_VERSION_MINOR * 100) + ETL_VERSION_PATCH) diff --git a/support/Release notes.txt b/support/Release notes.txt index 762780bf..7c2f5f3f 100644 --- a/support/Release notes.txt +++ b/support/Release notes.txt @@ -1,3 +1,7 @@ +=============================================================================== +12.0.0 +Modified the API of etl::state_chart constructors. + =============================================================================== 11.19.0 Removed push(void) push_back(void) and push_front(void) function for containers. diff --git a/test/codeblocks/ETL.cbp b/test/codeblocks/ETL.cbp index b4a78c2f..8c0190fe 100644 --- a/test/codeblocks/ETL.cbp +++ b/test/codeblocks/ETL.cbp @@ -323,6 +323,7 @@ + diff --git a/test/test_state_chart.cpp b/test/test_state_chart.cpp index 6cfb651c..2760afd0 100644 --- a/test/test_state_chart.cpp +++ b/test/test_state_chart.cpp @@ -86,9 +86,9 @@ namespace public: MotorControl() - : state_chart(*this, transitionTable, StateId::IDLE) + : state_chart(*this, transitionTable.begin(), transitionTable.end(), StateId::IDLE) { - this->set_state_table(stateTable); + this->set_state_table(stateTable.begin(), stateTable.end()); ClearStatistics(); }