#pragma once template struct marked_ptr { static constexpr size_t mask = (1 << bits_to_store) - 1; // static_assert(alignof(T) >= (1 << bits_to_store)); marked_ptr(T* ptr = nullptr) : ptr(ptr) {} marked_ptr(T* ptr, size_t mark) : ptr((T*)((size_t)ptr | (mark & mask))) {} T* get_ptr() const { return (T*)((size_t)ptr & ~1); } size_t get_mark() const { return (size_t)ptr & mask; } void set_ptr(T* ptr) { this->ptr = (T*)((size_t)ptr | is_marked()); } void set_mark(size_t mark) { ptr = (T*)((size_t)ptr | (mark & mask)); } operator T*() const { return get_ptr(); } operator size_t() const { return get_mark(); } protected: T* ptr{nullptr}; }; template struct marked_ptr { // static_assert(alignof(T) >= 1); marked_ptr(T* ptr = nullptr) : ptr(ptr) {} marked_ptr(T* ptr, bool mark) : ptr((T*)((size_t)ptr | mark)) {} T* get_ptr() const { return (T*)((size_t)ptr & ~1); } bool is_marked() const { return (size_t)ptr & 1; } void set_ptr(T* ptr) { this->ptr = (T*)((size_t)ptr | is_marked()); } void set_mark(bool mark) { ptr = (T*)((size_t)ptr | mark); } operator T*() const { return get_ptr(); } operator bool() const { return is_marked(); } protected: T* ptr{nullptr}; };