Header-only lock-free synchronization utilities (one writer, many readers).

stupid

Header-only lock-free synchronization utilities (one writer, many readers). No queues

Base functionality

The base functionality of this library is provided by the classes:

  • stupid::Object
  • stupid::Immutable

Very basic usage example

stupid::Object
    thing;
  

In the writer thread

// Initialize the object
thing.write().commit_new(...);

// That's equivalent to doing this
thing.write().commit(new Thing{...});

// Create a copy of the object to modify
auto copy = thing.write().copy();

copy->modify();
copy->the();
copy->object();

// Commit the modified object
thing.write().commit(copy);

In the reader thread

// Get a reference to the most recently committed version of the object
stupid::Immutable
    ref = thing.read().get();

ref->
   access();
ref->
   read_only();
ref->
   stuff();


   // stupid::Immutable is a reference counted type. The referenced version of

   // the object will remain valid as long as there are references to it, even

   // if the writer thread commits new versions of the object.

  

Caveats

  • Multiple simultaneous writer threads are not supported
  • All stupid::Immutable's for a stupid::Object must be deleted before the stupid::Object is destructed

Notes

  • Only these methods allocate memory:

    • stupid::Write::commit_new()
    • stupid::Write::copy()
  • Only these methods deallocate memory (in the form of garbage collection of old versions of the object):

    • stupid::Object::~Object()
    • stupid::Write::commit()
    • stupid::Write::commit_new()
  • Memory is deallocated using delete

Additional classes

Some additional, higher-level classes are provided for more specific use cases:

  • stupid::SyncSignal
  • stupid::SignalSyncObject
  • stupid::SignalSyncObjectPair
  • stupid::QuickSync

Possible SignalSyncObject usage in an audio application

The audio callback in this example has the following stipulations:

  • May not allocate or deallocate memory
  • May not lock a mutex
  • Should be able to get a reference to some immutable data by calling some function e.g. get_data()
  • Repeated calls to get_data() within the same invocation of the audio callback must return the same reference
  • The reference returned from get_data() must remain valid for the duration of the current invocation of the audio callback
struct
{
	stupid::SyncSignal signal;
	stupid::SignalSyncObject
    data;
	
	
   Sync() : data(signal) {}
} sync;
  

UI thread

void update_audio_data()
{
	auto copy = sync.data.copy();

	copy->modify();
	copy->the();
	copy->data();
	
	sync.data.commit(copy);
}

Audio thread

void audio_callback(...)
{
	// stupid::SyncSignal::operator() is called once at the start
	// of each audio buffer, and nowhere else.

	// This increments its value by 1.

	// The signal's value is checked whenever
	// stupid::SignalSyncObject::get_data() is called.
	sync.signal();

	...

	// stupid::SignalSyncObject::get_data() is guaranteed to always
	// return a reference to the same data unless:
	//  1. there is new data available, AND
	//  2. the current signal value is greater than the previous
	//     call to get_data().

	// Therefore new data (if there is any) is only retrieved on
	// the first call to get_data() per audio buffer.
	const AudioData& data1 = sync.data.get_data();
	
	data1.use();
	data1.the();
	data1.data();

	/**** UI thread could write new data here, for example ****/
	
	const auto& data2 = sync.data.get_data();
	
	// Will always pass. If new data was written by the UI thread
	// then it won't be picked up until the next audio buffer.
	assert(&data1 == &data2);
}

More Stuff

stupid::AtomicTrigger

It's a tiny wrapper around std::atomic_flag.

  • stupid::AtomicTrigger::operator() primes the trigger
  • stupid::AtomicTrigger::operator bool returns true if the trigger was primed, and resets it

Example usage

struct
{
	stupid::AtomicTrigger start_playback;
	stupid::AtomicTrigger stop_playback;
} sync;

UI thread

void process_ui_events()
{
	if (start_button_pressed)
	{
		sync.start_playback(); // Tell the audio thread to start playback ASAP
	}
	
	if (stop_button_pressed)
	{
		sync.stop_playback(); // Tell the audio thread to stop playback ASAP
	}
}

Audio thread

void audio_process()
{
	switch (current_state)
	{
		case Playing:
		{
			if (sync.stop_playback) stop();
			break;
		}
		
		case Stopped:
		{
			if (sync.start_playback) start();
			break;
		}
	}
}
Similar Resources

Isaac ROS common utilities and scripts for use in conjunction with the Isaac ROS suite of packages.

Isaac ROS Common Isaac ROS common utilities and scripts for use in conjunction with the Isaac ROS suite of packages. Docker Scripts run_dev.sh creates

Jan 8, 2023

provide SFML Time utilities in pure C++20, no dependencies

SFML-Time-utilities-without-SFML provide SFML Time utilities in pure C++20, no dependencies Example int main() { Clock clock; Sleep(1000);

Apr 28, 2022

Small header-only C++ library that helps to initialize Vulkan instance and device object

Vulkan Extensions & Features Help, or VkExtensionsFeaturesHelp, is a small, header-only, C++ library for developers who use Vulkan API.

Oct 12, 2022

A Header-Only Engine that tries to use SFML in a deeper level

⚙️ SFML-Low-Level-Engine ⚙️ A header-only library that tries to use SFML at a deeper level 💾 Instalation Download the source code and put the GLD fol

Aug 27, 2021

C++ header-only library for generic data validation.

C++ header-only library for generic data validation.

Dec 6, 2022

a compile-time, header-only, dimensional analysis and unit conversion library built on c++14 with no dependencies.

UNITS A compile-time, header-only, dimensional analysis library built on c++14 with no dependencies. Get in touch If you are using units.h in producti

Dec 29, 2022

A header only C++ library that provides type safety and user defined literals for physical units

SI - Type safety for physical units A header only c++ library that provides type safety and user defined literals for handling pyhsical values defined

Dec 25, 2022

Header-only C++20 wrapper for MPI 4.0.

MPI Modern C++20 message passing interface wrapper. Examples Initialization: mpi::environment environment; const auto& communicator = mpi::world_c

Apr 8, 2022

Small Header only library to parse argv for flags

Small Header only library to parse argv for flags

Nov 9, 2022
Related tags
Utilities and common code for use with raylib

Utilities and shared components for use with raylib

Dec 1, 2022
MacFlim flim player source code and utilities

MacFlim Video player source code Please do not barf on code quality. It was not in releasable state, but people wanted to use it. You may even be one

Jan 1, 2023
Panda - is a set of utilities used to research how PsExec encrypts its traffic.

Panda Panda - is a set of utilities used to research how PsExec encrypts its traffic. Shared library used to inject into lsass.exe process to log NTLM

Jul 17, 2022
Dead by Daylight utilities created while researching

DeadByDaylight Research material and PoC for bugs found during the reversal of the game Dead by Daylight. All information provided is for educational

Dec 26, 2022
Utilities to extract secrets from 1Password

1PasswordSuite Blog https://posts.specterops.io/1password-secret-retrieval-methodology-and-implementation-6a9db3f3c709 1PasswordExtract This .NET appl

Dec 7, 2022
mpiFileUtils - File utilities designed for scalability and performance.

mpiFileUtils provides both a library called libmfu and a suite of MPI-based tools to manage large datasets, which may vary from large directory trees to large files.

Jan 4, 2023
cavi is an open-source library that aims to provide performant utilities for closed hierarchies (i.e. all class types of the hierarchy are known at compile time).

cavi cavi is an open-source library that aims to provide performant utilities for closed hierarchies (i.e. all class types of the hierarchy are known

Mar 9, 2022
personal organization utilities

orgutils: Personal Organization Utilities orgutils are a set of utilities for personal and project organization. Each program has

Dec 8, 2021
A combined suite of utilities for manipulating binary data files.

BinaryTools A combined suite of utilities for manipulating binary data files. It was developed for use on Windows but might compile on other systems.

Oct 1, 2022
Utilities for use in a DPP based discord bot

DPPUtils NOTE: This repo is in development, use these utilities at your own risk Numerous utilities for use in your DPP bot. List of Utilities Youtube

Nov 5, 2022