#pragma once
#if !defined( CLFFT_BUFFER_MEMORY_H )
#define CLFFT_BUFFER_MEMORY_H
#include <vector>
#include <stdexcept>
#include <stdint.h>
uint32_t float_as_hex( float a );
uint64_t float_as_hex( double a );
uint32_t nan_as_hex( float a );
uint64_t nan_as_hex( double a );
template <class T>
class buffer_memory {
private:
size_t cookie_size;
size_t requested_floats;
size_t memory_size_including_cookies;
std::vector<T> memory;
public:
buffer_memory( size_t requested_number_of_floats )
: cookie_size( 4 )
, requested_floats( requested_number_of_floats )
, memory_size_including_cookies( requested_number_of_floats + 2 * cookie_size )
, memory( memory_size_including_cookies )
{
clear();
}
~buffer_memory() {
}
buffer_memory<T> & operator=( const buffer_memory<T> & that )
{
this->cookie_size = that.cookie_size;
this->requested_floats = that.requested_floats;
this->memory_size_including_cookies = that.memory_size_including_cookies;
this->memory = that.memory;
return *this;
}
void check_memory_boundaries() {
for( size_t i = 0; i < cookie_size; ++i) {
if( float_as_hex(memory[i]) != nan_as_hex(memory[0]) ||
float_as_hex( memory[ memory.size()-1-i ] ) != nan_as_hex(memory[0]) )
throw std::runtime_error("some operation wrote beyond bounds of memory");
}
}
void clear()
{
memset(&memory[0], ~0x0, memory_size_including_cookies * sizeof(T));
}
size_t size()
{
return size_in_bytes() / sizeof(T);
}
size_t size_in_bytes()
{
return (memory_size_including_cookies - 2 * cookie_size) * sizeof(T);
}
void increase_allocated_memory( size_t amount )
{
size_t new_memory_size = memory_size_including_cookies + amount;
memory.resize( new_memory_size );
memory_size_including_cookies = new_memory_size;
clear();
}
T* ptr()
{
return &memory[0] + cookie_size;
}
T& operator[]( size_t index ) {
if( index >= size() )
throw std::runtime_error( "operator[] write out of bounds" );
return memory[0 + cookie_size + index];
}
};
#endif