Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
cmake_minimum_required( VERSION 3.14 )

project( "daw-header-libraries"
VERSION "2.133.0"
VERSION "2.134.0"
DESCRIPTION "Various headers"
HOMEPAGE_URL "https://github.com/beached/header_libraries"
LANGUAGES C CXX
Expand Down
2 changes: 1 addition & 1 deletion include/daw/daw_attributes.h
Original file line number Diff line number Diff line change
Expand Up @@ -130,7 +130,7 @@
#define DAW_ATTRIB_RET_NONNULL
#endif

#if defined( DAW_NO_LIFETIME_BOUND )
#if not defined( DAW_NO_LIFETIME_BOUND )
#if not defined( __has_cpp_attribute )
#define DAW_LIFETIME_BOUND
#elif __has_cpp_attribute( clang::lifetimebound )
Expand Down
4 changes: 2 additions & 2 deletions include/daw/daw_enable_if.h
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,8 @@

#pragma once

#include "cpp_17.h"
#include "daw_cpp_feature_check.h"
#include "daw/cpp_17.h"
#include "daw/daw_cpp_feature_check.h"

#include <cstddef>
#include <type_traits>
Expand Down
15 changes: 0 additions & 15 deletions include/daw/daw_heap_value.h

This file was deleted.

2 changes: 1 addition & 1 deletion include/daw/daw_ignored.h
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
namespace daw {
namespace {
struct ignored_t {
ignored_t( ) = default;
explicit ignored_t( ) = default;

template<typename T>
DAW_ATTRIB_INLINE constexpr ignored_t( T && ) noexcept {}
Expand Down
279 changes: 279 additions & 0 deletions include/daw/daw_mutable_function_ref.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,279 @@
// Copyright (c) Darrell Wright
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying
// file LICENSE or copy at http://www.boost.org/LICENSE_1_0.txt)
//
// Official repository: https://github.com/beached/header_libraries
//

#pragma once

#include <cassert>
#include <concepts>
#include <cstdlib>
#include <memory>
#include <type_traits>
#include <utility>

#ifdef DAW_CPP26_CONSTEXPR
#undef DAW_CPP26_CONSTEXPR
#endif
#ifdef DAW_CPP26_CONSTEVAL
#undef DAW_CPP26_CONSTEVAL
#endif
#if __cpp_constexpr >= 202306L
#define DAW_CPP26_CONSTEXPR constexpr
#define DAW_CPP26_CONSTEVAL consteval
#else
#define DAW_CPP26_CONSTEXPR
#define DAW_CPP26_CONSTEVAL
#endif

namespace daw {
namespace mutable_function_ref_details {
template<typename Ret, typename T, typename... Ps>
concept class_invocable_r = std::is_class_v<std::remove_cvref_t<T>> and
std::is_invocable_r_v<Ret, T, Ps...>;

template<typename T, typename U>
concept different_from = not std::same_as<std::remove_cvref_t<T>, U>;
} // namespace mutable_function_ref_details

template<typename>
class mutable_function_ref;

template<typename Result, typename... Params>
class mutable_function_ref<Result( Params... )> {
union data_t {
void *obj_ptr;
void const *const_obj_ptr;
Result ( *func_ptr )( Params... );

constexpr data_t( void *ptr ) noexcept
: obj_ptr( ptr ) {}

constexpr data_t( void const *ptr ) noexcept
: const_obj_ptr( ptr ) {}

constexpr data_t( Result ( *ptr )( Params... ) ) noexcept
: func_ptr( ptr ) {}
};

data_t m_data;
Result ( *m_thunk )( data_t const &, Params... );

template<typename Func>
static DAW_CPP26_CONSTEXPR Result obj_thunk( data_t const &d,
Params... params ) {
auto &obj = *static_cast<Func *>( d.obj_ptr );
return obj( std::forward<Params>( params )... );
}

template<typename Func>
static DAW_CPP26_CONSTEXPR Result const_obj_thunk( data_t const &d,
Params... params ) {
auto const &obj = *static_cast<Func const *>( d.const_obj_ptr );
return obj( std::forward<Params>( params )... );
}

static constexpr Result fp_thunk( data_t const &d, Params... params ) {
return d.func_ptr( params... );
}

struct empty_call {
explicit empty_call( ) = default;
[[noreturn]] Result operator( )( Params... ) const {
std::abort( );
}
};

public:
constexpr mutable_function_ref( ) noexcept
: mutable_function_ref( empty_call{ } ) {}

template<typename Func>
requires( mutable_function_ref_details::different_from<
Func, mutable_function_ref> and
not std::is_const_v<Func> and
mutable_function_ref_details::class_invocable_r<Result, Func &,
Params...> ) //
constexpr mutable_function_ref( Func &func ) noexcept
: m_data( static_cast<void *>( std::addressof( func ) ) )
, m_thunk( obj_thunk<Func> ) {}

template<typename Func>
requires(
mutable_function_ref_details::different_from<Func, mutable_function_ref>
and mutable_function_ref_details::class_invocable_r<
Result, Func const &, Params...> ) //
constexpr mutable_function_ref( Func const &func ) noexcept
: m_data( static_cast<void const *>( std::addressof( func ) ) )
, m_thunk( const_obj_thunk<Func> ) {}

template<typename Func>
requires( not std::is_lvalue_reference_v<Func> and
mutable_function_ref_details::different_from<
Func, mutable_function_ref> and
not std::is_const_v<Func> and
mutable_function_ref_details::class_invocable_r<Result, Func &,
Params...> ) //
constexpr mutable_function_ref( Func &&func ) noexcept
: m_data( static_cast<void *>( std::addressof( func ) ) )
, m_thunk( obj_thunk<Func> ) {}

template<typename Func>
requires( mutable_function_ref_details::different_from<
Func, mutable_function_ref> and
not std::is_const_v<Func> and
mutable_function_ref_details::class_invocable_r<Result, Func &,
Params...> ) //
constexpr mutable_function_ref &operator=( Func &func ) noexcept {
m_data = static_cast<void *>( std::addressof( func ) );
m_thunk = obj_thunk<Func>;
return *this;
}

template<typename Func>
requires(
mutable_function_ref_details::different_from<Func, mutable_function_ref>
and mutable_function_ref_details::class_invocable_r<
Result, Func const &, Params...> ) //
constexpr mutable_function_ref &operator=( Func const &func ) noexcept {
m_data = static_cast<void const *>( std::addressof( func ) );
m_thunk = const_obj_thunk<Func>;
return *this;
}

constexpr mutable_function_ref( Result ( *ptr )( Params... ) ) noexcept
: m_data( ptr )
, m_thunk( nullptr ) {
assert( ptr );
}

constexpr mutable_function_ref &
operator=( Result ( *ptr )( Params... ) ) noexcept {
m_data = ptr;
m_thunk = nullptr;
assert( ptr );
return *this;
}

constexpr Result operator( )( Params... params ) const {
if( not m_thunk ) {
return m_data.func_ptr( std::forward<Params>( params )... );
}
return m_thunk( m_data, std::forward<Params>( params )... );
}
};

template<typename... Params>
class mutable_function_ref<void( Params... )> {
union data_t {
void *obj_ptr;
void const *const_obj_ptr;
void ( *func_ptr )( Params... );

constexpr data_t( void *ptr ) noexcept
: obj_ptr( ptr ) {}

constexpr data_t( void const *ptr ) noexcept
: const_obj_ptr( ptr ) {}

constexpr data_t( void ( *ptr )( Params... ) ) noexcept
: func_ptr( ptr ) {}
};

data_t m_data;
void ( *m_thunk )( data_t const &, Params... );

template<typename Func>
static DAW_CPP26_CONSTEXPR void obj_thunk( data_t const &d,
Params... params ) {
auto &obj = *static_cast<Func *>( d.obj_ptr );
(void)obj( std::forward<Params>( params )... );
}

template<typename Func>
static DAW_CPP26_CONSTEXPR void const_obj_thunk( data_t const &d,
Params... params ) {
auto const &obj = *static_cast<Func const *>( d.const_obj_ptr );
(void)obj( std::forward<Params>( params )... );
}

static constexpr void fp_thunk( data_t const &d, Params... params ) {
d.func_ptr( params... );
}

public:
template<typename Func>
requires( mutable_function_ref_details::different_from<
Func, mutable_function_ref> and
not std::is_const_v<Func> and
mutable_function_ref_details::class_invocable_r<void, Func &,
Params...> ) //
constexpr mutable_function_ref( Func &func ) noexcept
: m_data( static_cast<void *>( std::addressof( func ) ) )
, m_thunk( obj_thunk<Func> ) {}

template<typename Func>
requires(
mutable_function_ref_details::different_from<Func, mutable_function_ref>
and mutable_function_ref_details::class_invocable_r<void, Func const &,
Params...> ) //
constexpr mutable_function_ref( Func const &func ) noexcept
: m_data( static_cast<void const *>( std::addressof( func ) ) )
, m_thunk( const_obj_thunk<Func> ) {}

template<typename Func>
requires( not std::is_lvalue_reference_v<Func> and
mutable_function_ref_details::different_from<
Func, mutable_function_ref> and
not std::is_const_v<Func> and
mutable_function_ref_details::class_invocable_r<void, Func &,
Params...> ) //
constexpr mutable_function_ref( Func &&func ) noexcept
: m_data( static_cast<void *>( std::addressof( func ) ) )
, m_thunk( obj_thunk<Func> ) {}

template<typename Func>
requires( mutable_function_ref_details::different_from<
Func, mutable_function_ref> and
not std::is_const_v<Func> and
mutable_function_ref_details::class_invocable_r<void, Func &,
Params...> ) //
constexpr mutable_function_ref &operator=( Func &func ) noexcept {
m_data = static_cast<void *>( std::addressof( func ) );
m_thunk = obj_thunk<Func>;
return *this;
}

template<typename Func>
requires(
mutable_function_ref_details::different_from<Func, mutable_function_ref>
and mutable_function_ref_details::class_invocable_r<void, Func const &,
Params...> ) //
constexpr mutable_function_ref &operator=( Func const &func ) noexcept {
m_data = static_cast<void const *>( std::addressof( func ) );
m_thunk = const_obj_thunk<Func>;
return *this;
}

constexpr mutable_function_ref( void ( *ptr )( Params... ) ) noexcept
: m_data( ptr )
, m_thunk( fp_thunk ) {
assert( ptr );
}

constexpr mutable_function_ref &
operator=( void ( *ptr )( Params... ) ) noexcept {
m_data = ptr;
m_thunk = fp_thunk;
assert( ptr );
return *this;
}

constexpr void operator( )( Params... params ) const {
m_thunk( m_data, params... );
}
};
} // namespace daw
5 changes: 2 additions & 3 deletions include/daw/daw_poly_value.h
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,8 @@

#pragma once

#include "ciso646.h"
#include "daw_enable_if.h"
#include "daw_traits.h"
#include "daw/ciso646.h"
#include "daw/daw_traits.h"

#include <functional>
#include <memory>
Expand Down
6 changes: 3 additions & 3 deletions include/daw/daw_poly_var.h
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,9 @@

#pragma once

#include "ciso646.h"
#include "daw_enable_if.h"
#include "daw_visit.h"
#include "daw/ciso646.h"
#include "daw/daw_enable_if.h"
#include "daw/daw_visit.h"

#include <type_traits>
#include <variant>
Expand Down
6 changes: 4 additions & 2 deletions include/daw/daw_read_file.h
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ namespace daw {
template<typename CharT = char>
DAW_ATTRIB_NOINLINE std::optional<std::basic_string<CharT>>
read_file( std::string const &path ) {
auto ec = std::error_code{};
auto ec = std::error_code{ };
auto const fsize = std::filesystem::file_size( path, ec );
if( ec ) {
return std::nullopt;
Expand Down Expand Up @@ -54,8 +54,10 @@ namespace daw {
#endif
auto num_read = fread( result.data( ), sizeof( CharT ), result.size( ), f );
if( num_read != ( result.size( ) / sizeof( CharT ) ) ) {
fclose( f );
return std::nullopt;
}
fclose( f );
return result;
}

Expand All @@ -77,7 +79,7 @@ namespace daw {
DAW_ATTRIB_NOINLINE inline std::optional<std::wstring>
read_wfile( std::wstring path ) {
using CharT = wchar_t;
auto ec = std::error_code{};
auto ec = std::error_code{ };
auto const fsize = std::filesystem::file_size( path, ec );
if( ec ) {
return std::nullopt;
Expand Down
Loading
Loading