kong.internal.image_reflect
proxy generatator - maps 32/64 bit backends and endian conversion
Template : reflect
example:
mixin (reflect!("Ehdr", ["Elf32_Ehdr", "Elf64_Ehdr"],
"e_type",
"e_machine",
"e_version",
etc...
));
Generated code:
struct Ehdr
{
union {
Elf32_Ehdr* __Elf32_Ehdr__;
Elf64_Ehdr* __Elf64_Ehdr__;
void* address;
void* __R3FL3CTtyp31d__; // used by image_interface.link to identify proxy structs.
}
short type;
extern(C) void* function(void* dst, void* src, size_t n) copy;
static const ushort[][] offset = [[Elf32_Ehdr.e_type.offsetof, ...], [Elf64_Ehdr.e_type.offsetof, ...]];
static const ushort[][] size = [[Elf32_Ehdr.e_type.sizeof, ...], [Elf64_Ehdr.e_type.sizeof, ...]];
enum { e_type, e_machine, ... };
uint64_t opIndex(int i)
{
uint64_t val;
copy(&val, address + offset[type][i], size[type][i]);
return val;
}
void opIndexAssign(uint64_t val, int i)
{ copy(address + offset[type][i], &val, size[type][i]); }
ushort tsize()
{ return t_size[type]; }
}
}
Common case intialization:
* image_interface.link and related normally take care of this
// endian swap
extern (C)
void*
swpcpy(void* dst, void* src, size_t n)
{
for (int i = 0; i < n; ++i)
(cast(ubyte*)dst)[i] = (cast(ubyte*)src)[n - i - 1];
return dst;
}
void
reflect_init(alias a)(int type, bool endian)
{
a.type = type;
a.address = xxx;
if (endian)
a.copy = cast(copy_callback) &swpcpy;
else a.copy = cast(copy_callback) &memcpy;
}
