Autonomy Software C++ 24.5.1
Welcome to the Autonomy Software repository of the Mars Rover Design Team (MRDT) at Missouri University of Science and Technology (Missouri S&T)! API reference contains the source code and other resources for the development of the autonomy software for our Mars rover. The Autonomy Software project aims to compete in the University Rover Challenge (URC) by demonstrating advanced autonomous capabilities and robust navigation algorithms.
|
BS::thread_pool: a fast, lightweight, and easy-to-use C++17 thread pool library. This program tests all aspects of the library, but is not needed in order to use the library. More...
#include <algorithm>
#include <atomic>
#include <chrono>
#include <cmath>
#include <cstddef>
#include <cstdint>
#include <cstdlib>
#include <ctime>
#include <fstream>
#include <functional>
#include <future>
#include <iomanip>
#include <ios>
#include <limits>
#include <mutex>
#include <random>
#include <sstream>
#include <string>
#include <string_view>
#include <thread>
#include <tuple>
#include <utility>
#include <vector>
#include <stdexcept>
#include "BS_thread_pool.hpp"
#include "BS_thread_pool_utils.hpp"
Classes | |
class | detect_copy_move |
A class to detect when a copy or move constructor has been invoked. More... | |
class | flag_class |
A class to facilitate checking that member functions of different types have been successfully submitted. More... | |
struct | test_exception |
An exception class to be thrown when testing exception handling. More... | |
class | arg_parser |
A class to parse command line arguments. More... | |
Typedefs | |
using | int64 = std::int_fast64_t |
Functions | |
template<typename... T> | |
void | dual_print (T &&... items) |
Print any number of items into the standard output and the log file, syncing both independently. | |
template<typename... T> | |
void | dual_println (T &&... items) |
Print any number of items into both std::cout and the log file, syncing both independently. Also prints a newline character, and flushes the stream. | |
void | print_header (const std::string_view text, const char symbol='=') |
Print a stylized header. | |
void | check (const bool condition) |
Check if a condition is met, report the result, and keep count of the total number of successes and failures. | |
template<typename T1 , typename T2 > | |
void | check (const T1 expected, const T2 obtained) |
Check if the expected result has been obtained, report the result, and keep count of the total number of successes and failures. | |
template<typename T > | |
bool | all_flags_set (const T &flags) |
Check if all of the flags in a container are set. | |
template<typename T > | |
bool | no_flags_set (const T &flags) |
Check if none of the flags in a container are set. | |
template<typename T > | |
T | random (const T min, const T max) |
Obtain a random number in a specified range. | |
template<typename T > | |
std::pair< T, T > | random_pair (const T min, const T max) |
Obtain an ordered pair of two distinct random numbers in a specified range. | |
template<typename... T> | |
std::string | make_string (T &&... items) |
Make a string out of items of various types. | |
std::string | detect_compiler () |
Detect the compiler used to compile this program. | |
std::string | detect_os () |
Detect the operating system used to compile this program. | |
std::string | get_time () |
Get a string representing the current time. If MSVC is detected, localtime_s will be used to avoid warning C4996. | |
std::vector< std::thread::id > | obtain_unique_threads (BS::thread_pool &pool) |
Obtain a list of unique thread IDs in the pool. Submits a number of tasks equal to twice the thread count into the pool. Each task stores the ID of the thread running it, and then waits until as many tasks as the thread count are finished. This ensures that each thread in the pool runs at least one task, as the pool gets filled completely. | |
void | check_constructor () |
Check that the constructor works. Also checks that get_thread_ids() reports the correct IDs. | |
void | check_reset () |
Check that reset() works. | |
void | check_task (const std::string_view which_func) |
Check that detach_task() or submit_task() work. | |
void | check_member_function () |
Check that submitting member functions works. | |
void | check_member_function_within_object () |
Check that submitting member functions within an object works. | |
void | check_wait () |
Check that wait() works. | |
void | check_wait_blocks () |
Check that wait() correctly blocks all external threads that call it. | |
void | check_wait_for () |
Check that wait_for() works. | |
void | check_wait_until () |
Check that wait_until() works. | |
void | check_wait_multiple_deadlock () |
Check that calling wait() more than once doesn't create a deadlock. | |
void | check_wait_self_deadlock () |
Check that calling wait() from within a thread of the same pool throws an exception instead of creating a deadlock. | |
bool | check_loop_no_return (BS::thread_pool &pool, const int64 random_start, const int64 random_end, const BS::concurrency_t num_tasks, const std::string_view which_func) |
Check that detach_loop() or submit_loop() work for a specific range of indices split over a specific number of tasks, with no return value. | |
void | check_loop () |
Check that detach_loop() and submit_loop() work using several different random values for the range of indices and number of tasks. | |
bool | check_blocks_no_return (BS::thread_pool &pool, const int64 random_start, const int64 random_end, const BS::concurrency_t num_tasks, const std::string_view which_func) |
Check that detach_blocks() or submit_blocks() work for a specific range of indices split over a specific number of tasks, with no return value. | |
void | check_blocks_return (BS::thread_pool &pool, const int64 random_start, const int64 random_end, const BS::concurrency_t num_tasks) |
Check that submit_blocks() works for a specific range of indices split over a specific number of tasks, with a return value. | |
void | check_blocks () |
Check that detach_blocks() and submit_blocks() work using several different random values for the range of indices and number of tasks. | |
bool | check_sequence_no_return (BS::thread_pool &pool, const int64 random_start, const int64 random_end, const std::string_view which_func) |
Check that detach_sequence() or submit_sequence() work for a specific range of indices, with no return value. | |
void | check_sequence_return (BS::thread_pool &pool, const int64 random_start, const int64 random_end) |
Check that submit_sequence() works for a specific range of indices, with a return value. | |
void | check_sequence () |
Check that detach_sequence() and submit_sequence() work using several different random values for the range of indices. | |
void | check_task_monitoring () |
Check that task monitoring works. | |
void | check_pausing () |
Check that pausing works. | |
void | check_purge () |
Check that purge() works. | |
void | throws () |
A function that throws a test_exception . | |
void | check_exceptions_submit () |
Check that exceptions are forwarded correctly by submit_task(). | |
void | check_exceptions_multi_future () |
Check that exceptions are forwarded correctly by BS::multi_future . | |
bool | check_vector_of_size (BS::thread_pool &pool, const size_t vector_size, const BS::concurrency_t num_tasks) |
Check that parallelized vector operations work as expected by calculating the sum of two randomized vectors of a specific size in two ways, single-threaded and multithreaded, and comparing the results. | |
void | check_vectors () |
Check that parallelized vector operations work as expected. | |
void | check_priority () |
Check that task priority works as expected with all task submission methods. | |
void | check_init () |
Check that thread initialization functions and get_index() work. | |
void | check_get_pool () |
Check that get_pool() works. | |
template<typename F > | |
void | check_deadlock (const F &&task) |
Check that the specified function does not create deadlocks. The function will be run many times to increase the probability of encountering a deadlock as a result of subtle timing issues. Uses an auxiliary pool so the whole test doesn't get stuck if a deadlock is encountered. | |
void | print_timing (const BS::concurrency_t num_tasks, const std::pair< double, double > &mean_sd) |
Print the timing of a specific test. | |
template<typename T > | |
size_t | min_element (const std::vector< T > &vec) |
Find the minimum element in a vector. | |
void | print_speedup (const std::vector< double > &timings, const std::vector< BS::concurrency_t > &try_tasks) |
Calculate and print the speedup obtained by multithreading. | |
std::pair< double, double > | analyze (const std::vector< std::chrono::milliseconds::rep > &timings) |
Calculate the mean and standard deviation of a set of integers. | |
double | generate_element (const size_t idx) |
A function to generate vector elements. Chosen arbitrarily to simulate a typical numerical calculation. | |
void | check_performance () |
Benchmark multithreaded performance. | |
void | show_intro () |
Show basic information about the program. | |
void | show_help () |
Show the available command line options. | |
int | main (int argc, char *argv[]) |
Variables | |
bool | enable_benchmarks = true |
bool | enable_log = true |
bool | enable_long_deadlock_tests = false |
bool | enable_tests = true |
BS::synced_stream | sync_cout |
std::ofstream | log_file |
BS::synced_stream | sync_file (log_file) |
size_t | tests_succeeded = 0 |
size_t | tests_failed = 0 |
BS::thread_pool | check_wait_multiple_deadlock_pool |
BS::thread_pool | check_wait_self_deadlock_pool |
BS::thread_pool | check_deadlock_pool |
BS::thread_pool: a fast, lightweight, and easy-to-use C++17 thread pool library. This program tests all aspects of the library, but is not needed in order to use the library.
void dual_print | ( | T &&... | items | ) |
Print any number of items into the standard output and the log file, syncing both independently.
T | The types of the items. |
items | The items to print. |
void dual_println | ( | T &&... | items | ) |
Print any number of items into both std::cout and the log file, syncing both independently. Also prints a newline character, and flushes the stream.
T | The types of the items. |
items | The items to print. |
void print_header | ( | const std::string_view | text, |
const char | symbol = '=' |
||
) |
Print a stylized header.
text | The text of the header. Will appear between two lines. |
symbol | The symbol to use for the lines. Default is '='. |
void check | ( | const bool | condition | ) |
Check if a condition is met, report the result, and keep count of the total number of successes and failures.
condition | The condition to check. |
void check | ( | const T1 | expected, |
const T2 | obtained | ||
) |
Check if the expected result has been obtained, report the result, and keep count of the total number of successes and failures.
condition | The condition to check. |
bool all_flags_set | ( | const T & | flags | ) |
Check if all of the flags in a container are set.
flags | The container. |
true
if all flags are set, or false
otherwise. bool no_flags_set | ( | const T & | flags | ) |
Check if none of the flags in a container are set.
flags | The container. |
true
if no flags are set, or false
otherwise. T random | ( | const T | min, |
const T | max | ||
) |
Obtain a random number in a specified range.
T | The type of the values in the range. |
min | The minimum value of the range. |
max | The maximum value of the range. |
std::pair< T, T > random_pair | ( | const T | min, |
const T | max | ||
) |
Obtain an ordered pair of two distinct random numbers in a specified range.
T | The type of the values in the range. |
min | The minimum value of the range. |
max | The maximum value of the range. Must be larger than min . |
std::string make_string | ( | T &&... | items | ) |
Make a string out of items of various types.
T | The types of the items. |
items | The items. |
std::string detect_compiler | ( | ) |
Detect the compiler used to compile this program.
std::string detect_os | ( | ) |
Detect the operating system used to compile this program.
std::string get_time | ( | ) |
Get a string representing the current time. If MSVC is detected, localtime_s
will be used to avoid warning C4996.
std::vector< std::thread::id > obtain_unique_threads | ( | BS::thread_pool & | pool | ) |
Obtain a list of unique thread IDs in the pool. Submits a number of tasks equal to twice the thread count into the pool. Each task stores the ID of the thread running it, and then waits until as many tasks as the thread count are finished. This ensures that each thread in the pool runs at least one task, as the pool gets filled completely.
pool | The thread pool to check. |
void check_constructor | ( | ) |
Check that the constructor works. Also checks that get_thread_ids() reports the correct IDs.
void check_reset | ( | ) |
Check that reset() works.
void check_task | ( | const std::string_view | which_func | ) |
Check that detach_task() or submit_task() work.
which_func | A string naming the function to check. |
void check_member_function | ( | ) |
Check that submitting member functions works.
void check_member_function_within_object | ( | ) |
Check that submitting member functions within an object works.
void check_wait | ( | ) |
Check that wait() works.
void check_wait_blocks | ( | ) |
Check that wait() correctly blocks all external threads that call it.
void check_wait_for | ( | ) |
Check that wait_for() works.
void check_wait_until | ( | ) |
Check that wait_until() works.
void check_wait_multiple_deadlock | ( | ) |
Check that calling wait() more than once doesn't create a deadlock.
void check_wait_self_deadlock | ( | ) |
Check that calling wait() from within a thread of the same pool throws an exception instead of creating a deadlock.
bool check_loop_no_return | ( | BS::thread_pool & | pool, |
const int64 | random_start, | ||
const int64 | random_end, | ||
const BS::concurrency_t | num_tasks, | ||
const std::string_view | which_func | ||
) |
Check that detach_loop() or submit_loop() work for a specific range of indices split over a specific number of tasks, with no return value.
pool | The thread pool to check. |
random_start | The first index in the loop. |
random_end | The last index in the loop plus 1. |
num_tasks | The number of tasks. |
which_func | A string naming the function to check. |
true
if the check succeeded, false
otherwise. void check_loop | ( | ) |
Check that detach_loop() and submit_loop() work using several different random values for the range of indices and number of tasks.
bool check_blocks_no_return | ( | BS::thread_pool & | pool, |
const int64 | random_start, | ||
const int64 | random_end, | ||
const BS::concurrency_t | num_tasks, | ||
const std::string_view | which_func | ||
) |
Check that detach_blocks() or submit_blocks() work for a specific range of indices split over a specific number of tasks, with no return value.
pool | The thread pool to check. |
random_start | The first index in the loop. |
random_end | The last index in the loop plus 1. |
num_tasks | The number of tasks. |
which_func | A string naming the function to check. |
true
if the check succeeded, false
otherwise. void check_blocks_return | ( | BS::thread_pool & | pool, |
const int64 | random_start, | ||
const int64 | random_end, | ||
const BS::concurrency_t | num_tasks | ||
) |
Check that submit_blocks() works for a specific range of indices split over a specific number of tasks, with a return value.
pool | The thread pool to check. |
random_start | The first index in the loop. |
random_end | The last index in the loop plus 1. |
num_tasks | The number of tasks. |
void check_blocks | ( | ) |
Check that detach_blocks() and submit_blocks() work using several different random values for the range of indices and number of tasks.
bool check_sequence_no_return | ( | BS::thread_pool & | pool, |
const int64 | random_start, | ||
const int64 | random_end, | ||
const std::string_view | which_func | ||
) |
Check that detach_sequence() or submit_sequence() work for a specific range of indices, with no return value.
pool | The thread pool to check. |
random_start | The first index in the sequence. |
random_end | The last index in the sequence plus 1. |
which_func | A string naming the function to check. |
true
if the check succeeded, false
otherwise. void check_sequence_return | ( | BS::thread_pool & | pool, |
const int64 | random_start, | ||
const int64 | random_end | ||
) |
Check that submit_sequence() works for a specific range of indices, with a return value.
pool | The thread pool to check. |
random_start | The first index in the sequence. |
random_end | The last index in the sequence plus 1. |
void check_sequence | ( | ) |
Check that detach_sequence() and submit_sequence() work using several different random values for the range of indices.
void check_task_monitoring | ( | ) |
Check that task monitoring works.
void check_pausing | ( | ) |
Check that pausing works.
void check_purge | ( | ) |
Check that purge() works.
void throws | ( | ) |
A function that throws a test_exception
.
void check_exceptions_submit | ( | ) |
Check that exceptions are forwarded correctly by submit_task().
void check_exceptions_multi_future | ( | ) |
Check that exceptions are forwarded correctly by BS::multi_future
.
bool check_vector_of_size | ( | BS::thread_pool & | pool, |
const size_t | vector_size, | ||
const BS::concurrency_t | num_tasks | ||
) |
Check that parallelized vector operations work as expected by calculating the sum of two randomized vectors of a specific size in two ways, single-threaded and multithreaded, and comparing the results.
pool | The thread pool to check. |
vector_size | The size of the vectors. |
num_tasks | The number of tasks to split the calculation into. |
true
if the single-threaded and multithreaded results are equal, false
otherwise. void check_vectors | ( | ) |
Check that parallelized vector operations work as expected.
void check_priority | ( | ) |
Check that task priority works as expected with all task submission methods.
void check_init | ( | ) |
Check that thread initialization functions and get_index() work.
void check_get_pool | ( | ) |
Check that get_pool() works.
void check_deadlock | ( | const F && | task | ) |
Check that the specified function does not create deadlocks. The function will be run many times to increase the probability of encountering a deadlock as a result of subtle timing issues. Uses an auxiliary pool so the whole test doesn't get stuck if a deadlock is encountered.
F | The type of the function. |
task | The function to try. |
void print_timing | ( | const BS::concurrency_t | num_tasks, |
const std::pair< double, double > & | mean_sd | ||
) |
Print the timing of a specific test.
num_tasks | The number of tasks. |
mean_sd | An std::pair containing the mean as the first member and standard deviation as the second member. |
size_t min_element | ( | const std::vector< T > & | vec | ) |
Find the minimum element in a vector.
T | The type of elements in the vector. |
vec | The vector. |
void print_speedup | ( | const std::vector< double > & | timings, |
const std::vector< BS::concurrency_t > & | try_tasks | ||
) |
Calculate and print the speedup obtained by multithreading.
timings | A vector of the timings corresponding to different numbers of tasks. |
std::pair< double, double > analyze | ( | const std::vector< std::chrono::milliseconds::rep > & | timings | ) |
Calculate the mean and standard deviation of a set of integers.
timings | The integers. |
std::pair
containing the mean as the first member and standard deviation as the second member. double generate_element | ( | const size_t | idx | ) |
A function to generate vector elements. Chosen arbitrarily to simulate a typical numerical calculation.
idx | The element index. |
void check_performance | ( | ) |
Benchmark multithreaded performance.
void show_intro | ( | ) |
Show basic information about the program.
void show_help | ( | ) |
Show the available command line options.
int main | ( | int | argc, |
char * | argv[] | ||
) |