allocator alignment issues...

C

Chris Thomasson

I found some time to work a little more on my C++ allocator project. Here is
some of the basic alignment code that I am thinking about using:

----------------
#include <cstdio>
#include <cstring>
#include <cassert>


// attempts to extract the alignemnt of a type T
template<typename T>
class align_of {
struct temp {
char m_offset;
T m_object;
};

public:
enum result_e {
c_result = sizeof(temp) > sizeof(T) ?
sizeof(temp) - sizeof(T) : sizeof(T)
};
};


// attempts to extract an aligned buffer from _this
template<typename T>
static char* align_ptr(
char const* const _this,
ptrdiff_t alignsz = align_of<T>::c_result
) {
ptrdiff_t offsetsz =
reinterpret_cast<ptrdiff_t>(_this) % alignsz;

if (offsetsz) {
assert(offsetsz < alignsz);

char const* const offsetptr =
reinterpret_cast<char const*>(_this) + alignsz - offsetsz;

if (reinterpret_cast<ptrdiff_t>(offsetptr) % alignsz) {
assert(! (reinterpret_cast<ptrdiff_t>(offsetptr) % alignsz));
throw;
}

printf("%p alignptr(%p, %i); // offset %i\n",
(void*)offsetptr, (void*)_this, alignsz, offsetsz);

return const_cast<char*>(offsetptr);
}

printf("%p alignptr(%p, %i);\n",
(void*)_this, (void*)_this, alignsz);

return const_cast<char*>(_this);
}


// a buffer and an aligned pointer into it...
template<size_t T_sz, ptrdiff_t T_alignsz = T_sz>
struct aligned_buf {
enum const_e {
c_alignsz = T_alignsz,
c_alignobjsz = T_sz + c_alignsz - 1
};

char c_bufraw[c_alignobjsz];
char* const c_bufalign;

aligned_buf() :
c_bufalign(align_ptr<char>(c_bufraw, c_alignsz)) {
memset(c_bufraw, 0, c_alignobjsz);
}

char* load_align_ptr(ptrdiff_t alignsz) const {
char* const ptr = align_ptr<char>(c_bufalign, alignsz);
return ptr;
}
};


/* App
____________________________________________________*/


// platform specific
namespace platform {
namespace os {
enum const_e {
c_pagesz = 8192
};
}

namespace arch {
enum const_e {
c_l2cachelinesz = 128
};
}
}


// misc types...
struct temp1 {
char m_1;
short m_2;
};

struct temp2 {
char m_1;
temp1 m_2;
float m_3;
};

struct temp3 {
char m_1;
temp2 m_2;
double m_3;
};


// os page(s) w/ page-boundary alignment type
template<size_t T_pages>
struct pagebuf {
typedef aligned_buf<
platform::eek:s::c_pagesz * T_pages,
platform::eek:s::c_pagesz> pagebuf_t;

// pagebuf is os page aligned on page-boundary
pagebuf_t m_buf;
};


int main(void) {
{
// create 4 pages on the stack.
typedef pagebuf<4> pages_t;
pages_t pages;

// l2cachebuf is aligned off of pagebuf
char* const l2cachebuf =
pages.m_buf.load_align_ptr(platform::arch::c_l2cachelinesz);


// display page alignment info
printf("\n\n\
(%u)-pages sizeof\n\
(%p)-pages.m_buf.c_bufraw\n\
(%p)-pages.m_buf.c_bufalign\n\
(%p)-l2cachebuf\n",
sizeof(pages),
(void*)pages.m_buf.c_bufraw,
(void*)pages.m_buf.c_bufalign,
(void*)l2cachebuf);


// display basic type alignment info
printf("\n\n\
(sz:%u\talign:%i)-char\n\
(sz:%u\talign:%i)-short\n\
(sz:%u\talign:%i)-long\n\
(sz:%u\talign:%i)-float\n\
(sz:%u\talign:%i)-double\n\
(sz:%u\talign:%i)-long double\n\
(sz:%u\talign:%i)-void* align\n\
(sz:%u\talign:%i)-void* (*) (void*)\n\
(sz:%u\talign:%i)-temp1\n\
(sz:%u\talign:%i)-temp2\n\
(sz:%u\talign:%i)-temp3\n",
sizeof(char), align_of<char>::c_result,
sizeof(short), align_of<short>::c_result,
sizeof(long), align_of<long>::c_result,
sizeof(float), align_of<float>::c_result,
sizeof(double), align_of<double>::c_result,
sizeof(long double), align_of<long double>::c_result,
sizeof(void*), align_of<void*>::c_result,
sizeof(void* (*) (void*)), align_of<void* (*) (void*)>::c_result,
sizeof(temp1), align_of<temp1>::c_result,
sizeof(temp2), align_of<temp2>::c_result,
sizeof(temp3), align_of<temp3>::c_result);
}

puts("\n\n\n\
_______________________\npress <enter> to exit...\n");
return getchar();
}

----------------


This alignment code will be used in a per-thread C++ allocator scheme. I am
always looking for better ways of doing the "alignment" stuff. If you have
any suggestions I would like to hear them...
 
C

Chris Thomasson

Chris Thomasson said:
I found some time to work a little more on my C++ allocator project. Here
is some of the basic alignment code that I am thinking about using:
[...]

OOPS!

I forgot to add:

#include <cstddef>


darn. Sorry about that.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,954
Messages
2,570,116
Members
46,704
Latest member
BernadineF

Latest Threads

Top